[cfe-commits] r38671 - in /cfe/cfe/trunk: Driver/PrintPreprocessedOutput.cpp Lex/Lexer.cpp Lex/Preprocessor.cpp include/clang/Lex/Preprocessor.h

sabre at cs.uiuc.edu sabre at cs.uiuc.edu
Wed Jul 11 09:23:41 PDT 2007


Author: sabre
Date: Wed Jul 11 11:23:41 2007
New Revision: 38671

URL: http://llvm.org/viewvc/llvm-project?rev=38671&view=rev
Log:
Change the Preprocessor::getSpelling interface to let it be zero-copy in
the common case.

Modified:
    cfe/cfe/trunk/Driver/PrintPreprocessedOutput.cpp
    cfe/cfe/trunk/Lex/Lexer.cpp
    cfe/cfe/trunk/Lex/Preprocessor.cpp
    cfe/cfe/trunk/include/clang/Lex/Preprocessor.h

Modified: cfe/cfe/trunk/Driver/PrintPreprocessedOutput.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/Driver/PrintPreprocessedOutput.cpp?rev=38671&r1=38670&r2=38671&view=diff

==============================================================================
--- cfe/cfe/trunk/Driver/PrintPreprocessedOutput.cpp (original)
+++ cfe/cfe/trunk/Driver/PrintPreprocessedOutput.cpp Wed Jul 11 11:23:41 2007
@@ -297,9 +297,9 @@
     }
     
     if (Tok.getLength() < 256) {
-      unsigned Len = PP.getSpelling(Tok, Buffer);
-      Buffer[Len] = 0;
-      OutputString(Buffer, Len);
+      const char *TokPtr = Buffer;
+      unsigned Len = PP.getSpelling(Tok, TokPtr);
+      OutputString(TokPtr, Len);
     } else {
       std::string S = PP.getSpelling(Tok);
       OutputString(&S[0], S.size());

Modified: cfe/cfe/trunk/Lex/Lexer.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/Lex/Lexer.cpp?rev=38671&r1=38670&r2=38671&view=diff

==============================================================================
--- cfe/cfe/trunk/Lex/Lexer.cpp (original)
+++ cfe/cfe/trunk/Lex/Lexer.cpp Wed Jul 11 11:23:41 2007
@@ -360,7 +360,7 @@
       II = PP.getIdentifierInfo(IdStart, IdEnd);
     } else {
       // Cleaning needed, alloca a buffer, clean into it, then use the buffer.
-      char *TmpBuf = (char*)alloca(Result.getLength());
+      const char *TmpBuf = (char*)alloca(Result.getLength());
       unsigned Size = PP.getSpelling(Result, TmpBuf);
       II = PP.getIdentifierInfo(TmpBuf, TmpBuf+Size);
     }

Modified: cfe/cfe/trunk/Lex/Preprocessor.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/Lex/Preprocessor.cpp?rev=38671&r1=38670&r2=38671&view=diff

==============================================================================
--- cfe/cfe/trunk/Lex/Preprocessor.cpp (original)
+++ cfe/cfe/trunk/Lex/Preprocessor.cpp Wed Jul 11 11:23:41 2007
@@ -218,10 +218,10 @@
   if (!Tok.needsCleaning())
     return std::string(TokStart, TokStart+Tok.getLength());
   
-  // Otherwise, hard case, relex the characters into the string.
   std::string Result;
   Result.reserve(Tok.getLength());
   
+  // Otherwise, hard case, relex the characters into the string.
   for (const char *Ptr = TokStart, *End = TokStart+Tok.getLength();
        Ptr != End; ) {
     unsigned CharSize;
@@ -237,7 +237,14 @@
 /// preallocated buffer, instead of as an std::string.  The caller is required
 /// to allocate enough space for the token, which is guaranteed to be at least
 /// Tok.getLength() bytes long.  The actual length of the token is returned.
-unsigned Preprocessor::getSpelling(const LexerToken &Tok, char *Buffer) const {
+///
+/// Note that this method may do two possible things: it may either fill in
+/// the buffer specified with characters, or it may *change the input pointer*
+/// to point to a constant buffer with the data already in it (avoiding a
+/// copy).  The caller is not allowed to modify the returned buffer pointer
+/// if an internal buffer is returned.
+unsigned Preprocessor::getSpelling(const LexerToken &Tok,
+                                   const char *&Buffer) const {
   assert((int)Tok.getLength() >= 0 && "Token character range is bogus!");
   
   const char *TokStart = SourceMgr.getCharacterData(Tok.getLocation());
@@ -245,15 +252,11 @@
 
   // If this token contains nothing interesting, return it directly.
   if (!Tok.needsCleaning()) {
-    unsigned Size = Tok.getLength();
-    memcpy(Buffer, TokStart, Size);
-    return Size;
+    Buffer = TokStart;
+    return Tok.getLength();
   }
   // Otherwise, hard case, relex the characters into the string.
-  std::string Result;
-  Result.reserve(Tok.getLength());
-  
-  char *OutBuf = Buffer;
+  char *OutBuf = const_cast<char*>(Buffer);
   for (const char *Ptr = TokStart, *End = TokStart+Tok.getLength();
        Ptr != End; ) {
     unsigned CharSize;

Modified: cfe/cfe/trunk/include/clang/Lex/Preprocessor.h
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/include/clang/Lex/Preprocessor.h?rev=38671&r1=38670&r2=38671&view=diff

==============================================================================
--- cfe/cfe/trunk/include/clang/Lex/Preprocessor.h (original)
+++ cfe/cfe/trunk/include/clang/Lex/Preprocessor.h Wed Jul 11 11:23:41 2007
@@ -365,7 +365,13 @@
   /// preallocated buffer, instead of as an std::string.  The caller is required
   /// to allocate enough space for the token, which is guaranteed to be at least
   /// Tok.getLength() bytes long.  The length of the actual result is returned.
-  unsigned getSpelling(const LexerToken &Tok, char *Buffer) const;
+  ///
+  /// Note that this method may do two possible things: it may either fill in
+  /// the buffer specified with characters, or it may *change the input pointer*
+  /// to point to a constant buffer with the data already in it (avoiding a
+  /// copy).  The caller is not allowed to modify the returned buffer pointer
+  /// if an internal buffer is returned.
+  unsigned getSpelling(const LexerToken &Tok, const char *&Buffer) const;
   
   /// DumpToken - Print the token to stderr, used for debugging.
   ///





More information about the cfe-commits mailing list