[cfe-commits] r38597 - in /cfe/cfe/trunk: Lex/MacroExpander.cpp Lex/Preprocessor.cpp include/clang/Lex/MacroExpander.h include/clang/Lex/Preprocessor.h

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


Author: sabre
Date: Wed Jul 11 11:23:03 2007
New Revision: 38597

URL: http://llvm.org/viewvc/llvm-project?rev=38597&view=rev
Log:
Implement the __TIME__ and __DATE__ builtin macros.

Modified:
    cfe/cfe/trunk/Lex/MacroExpander.cpp
    cfe/cfe/trunk/Lex/Preprocessor.cpp
    cfe/cfe/trunk/include/clang/Lex/MacroExpander.h
    cfe/cfe/trunk/include/clang/Lex/Preprocessor.h

Modified: cfe/cfe/trunk/Lex/MacroExpander.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/Lex/MacroExpander.cpp?rev=38597&r1=38596&r2=38597&view=diff

==============================================================================
--- cfe/cfe/trunk/Lex/MacroExpander.cpp (original)
+++ cfe/cfe/trunk/Lex/MacroExpander.cpp Wed Jul 11 11:23:03 2007
@@ -26,26 +26,6 @@
 }
 
 
-/// getInstantiationLoc - Return a SourceLocation that specifies a macro
-/// instantiation whose physical location is PhysLoc but the logical location
-/// is InstantiationLoc.
-SourceLocation MacroExpander::
-getInstantiationLoc(Preprocessor &PP,
-                    SourceLocation PhysLoc, SourceLocation InstantiationLoc) {
-  // The token's current location indicate where the token was lexed from.  We
-  // need this information to compute the spelling of the token, but any
-  // diagnostics for the expanded token should appear as if they came from
-  // InstantiationLoc.  Pull this information together into a new SourceLocation
-  // that captures all of this.
-  unsigned CharFilePos = PhysLoc.getRawFilePos();
-  unsigned CharFileID  = PhysLoc.getFileID();
-  
-  unsigned InstantiationFileID =
-    PP.getSourceManager().createFileIDForMacroExp(InstantiationLoc, CharFileID);
-  return SourceLocation(InstantiationFileID, CharFilePos);
-}
-
-
 /// Lex - Lex and return a token from this macro stream.
 ///
 void MacroExpander::Lex(LexerToken &Tok) {
@@ -56,9 +36,13 @@
   // Get the next token to return.
   Tok = Macro.getReplacementToken(CurToken++);
 
-  // Update the tokens location to include both its logical and physical
-  // locations.
-  Tok.SetLocation(getInstantiationLoc(PP, Tok.getLocation(), InstantiateLoc));
+  // The token's current location indicate where the token was lexed from.  We
+  // need this information to compute the spelling of the token, but any
+  // diagnostics for the expanded token should appear as if they came from
+  // InstantiationLoc.  Pull this information together into a new SourceLocation
+  // that captures all of this.
+  Tok.SetLocation(PP.getSourceManager().getInstantiationLoc(Tok.getLocation(),
+                                                            InstantiateLoc));
 
   // If this is the first token, set the lexical properties of the token to
   // match the lexical properties of the macro identifier.

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

==============================================================================
--- cfe/cfe/trunk/Lex/Preprocessor.cpp (original)
+++ cfe/cfe/trunk/Lex/Preprocessor.cpp Wed Jul 11 11:23:03 2007
@@ -434,6 +434,8 @@
 void Preprocessor::RegisterBuiltinMacros() {
   // FIXME: implement them all, including _Pragma.
   Ident__LINE__ = RegisterBuiltinMacro("__LINE__");
+  Ident__DATE__ = RegisterBuiltinMacro("__DATE__");
+  Ident__TIME__ = RegisterBuiltinMacro("__TIME__");
 }
 
 
@@ -498,8 +500,7 @@
     // Update the tokens location to include both its logical and physical
     // locations.
     SourceLocation Loc =
-      MacroExpander::getInstantiationLoc(*this, Identifier.getLocation(),
-                                         InstantiateLoc);
+      SourceMgr.getInstantiationLoc(Identifier.getLocation(), InstantiateLoc);
     Identifier.SetLocation(Loc);
     
     // Since this is not an identifier token, it can't be macro expanded, so
@@ -516,6 +517,27 @@
   return Lex(Identifier);
 }
 
+/// ComputeDATE_TIME - Compute the current time, enter it into the specified
+/// scratch buffer, then return DATELoc/TIMELoc locations with the position of
+/// the identifier tokens inserted.
+static void ComputeDATE_TIME(SourceLocation &DATELoc, SourceLocation &TIMELoc,
+                             ScratchBuffer *ScratchBuf) {
+  time_t TT = time(0);
+  struct tm *TM = localtime(&TT);
+  
+  static const char * const Months[] = {
+    "Jan","Feb","Mar","Apr","May","Jun","Jul","Aug","Sep","Oct","Nov","Dec"
+  };
+  
+  char TmpBuffer[100];
+  sprintf(TmpBuffer, "\"%s %2d %4d\"", Months[TM->tm_mon], TM->tm_mday, 
+          TM->tm_year+1900);
+  DATELoc = ScratchBuf->getToken(TmpBuffer, strlen(TmpBuffer));
+
+  sprintf(TmpBuffer, "\"%02d:%02d:%02d\"", TM->tm_hour, TM->tm_min, TM->tm_sec);
+  TIMELoc = ScratchBuf->getToken(TmpBuffer, strlen(TmpBuffer));
+}
+
 /// ExpandBuiltinMacro - If an identifier token is read that is to be expanded
 /// as a builtin macro, handle it and return the next token as 'Tok'.
 void Preprocessor::ExpandBuiltinMacro(LexerToken &Tok, MacroInfo *MI) {
@@ -524,6 +546,7 @@
   assert(ITI && "Can't be a macro without id info!");
   char TmpBuffer[100];
   
+  
   if (ITI == Ident__LINE__) {
     // __LINE__ expands to a simple numeric value.
     sprintf(TmpBuffer, "%u", SourceMgr.getLineNumber(Tok.getLocation()));
@@ -533,7 +556,24 @@
     Tok.SetLocation(ScratchBuf->getToken(TmpBuffer, Length, Tok.getLocation()));
     Tok.SetIdentifierInfo(0);
     Tok.ClearFlag(LexerToken::NeedsCleaning);
-    return;
+  } else if (ITI == Ident__DATE__) {
+    if (!DATELoc.isValid())
+      ComputeDATE_TIME(DATELoc, TIMELoc, ScratchBuf);
+    Tok.SetKind(tok::string_literal);
+    Tok.SetLength(strlen("\"Mmm dd yyyy\""));
+    Tok.SetLocation(SourceMgr.getInstantiationLoc(DATELoc, Tok.getLocation()));
+    Tok.SetIdentifierInfo(0);
+    Tok.ClearFlag(LexerToken::NeedsCleaning);
+    
+  } else if (ITI == Ident__TIME__) {
+    if (!TIMELoc.isValid())
+      ComputeDATE_TIME(DATELoc, TIMELoc, ScratchBuf);
+    Tok.SetKind(tok::string_literal);
+    Tok.SetLength(strlen("\"hh:mm:ss\""));
+    Tok.SetLocation(SourceMgr.getInstantiationLoc(TIMELoc, Tok.getLocation()));
+    Tok.SetIdentifierInfo(0);
+    Tok.ClearFlag(LexerToken::NeedsCleaning);
+   
   } else {
     assert(0 && "Unknown identifier!");
   }  

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

==============================================================================
--- cfe/cfe/trunk/include/clang/Lex/MacroExpander.h (original)
+++ cfe/cfe/trunk/include/clang/Lex/MacroExpander.h Wed Jul 11 11:23:03 2007
@@ -50,13 +50,6 @@
   
   MacroInfo &getMacro() const { return Macro; }
 
-  /// getInstantiationLoc - Return a SourceLocation that specifies a macro
-  /// instantiation whose physical location is PhysLoc but the logical location
-  /// is InstantiationLoc.
-  static SourceLocation getInstantiationLoc(Preprocessor &PP,
-                                            SourceLocation PhysLoc,
-                                            SourceLocation InstantiationLoc);
-  
   /// Lex - Lex and return a token from this macro stream.
   void Lex(LexerToken &Tok);
 };

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=38597&r1=38596&r2=38597&view=diff

==============================================================================
--- cfe/cfe/trunk/include/clang/Lex/Preprocessor.h (original)
+++ cfe/cfe/trunk/include/clang/Lex/Preprocessor.h Wed Jul 11 11:23:03 2007
@@ -94,6 +94,8 @@
   
   /// Identifiers for builtin macros.
   IdentifierTokenInfo *Ident__LINE__; // __LINE__
+  IdentifierTokenInfo *Ident__DATE__, *Ident__TIME__; // __DATE__, __TIME__
+  SourceLocation DATELoc, TIMELoc;
 public:
   enum FileChangeReason {
     EnterFile, ExitFile, SystemHeaderPragma, RenameFile





More information about the cfe-commits mailing list