[cfe-commits] r38643 - in /cfe/cfe/trunk: Driver/clang.cpp Lex/Preprocessor.cpp include/clang/Basic/DiagnosticKinds.def include/clang/Lex/Preprocessor.h

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


Author: sabre
Date: Wed Jul 11 11:23:27 2007
New Revision: 38643

URL: http://llvm.org/viewvc/llvm-project?rev=38643&view=rev
Log:
Implement #ident and #sccs

Modified:
    cfe/cfe/trunk/Driver/clang.cpp
    cfe/cfe/trunk/Lex/Preprocessor.cpp
    cfe/cfe/trunk/include/clang/Basic/DiagnosticKinds.def
    cfe/cfe/trunk/include/clang/Lex/Preprocessor.h

Modified: cfe/cfe/trunk/Driver/clang.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/Driver/clang.cpp?rev=38643&r1=38642&r2=38643&view=diff

==============================================================================
--- cfe/cfe/trunk/Driver/clang.cpp (original)
+++ cfe/cfe/trunk/Driver/clang.cpp Wed Jul 11 11:23:27 2007
@@ -674,6 +674,13 @@
   std::cout << "\n";
 }
 
+static void HandleIdent(SourceLocation Loc, const std::string &Val) {
+  SourceManager &SourceMgr = EModePP->getSourceManager();
+  MoveToLine(SourceMgr.getLineNumber(Loc));
+
+  std::cout << "#ident " << Val;
+  EmodeEmittedTokensOnThisLine = true;
+}
 
 /// HandleFirstTokOnLine - When emitting a preprocessed file in -E mode, this
 /// is called for the first token on each new line.
@@ -733,6 +740,7 @@
   EModeCurLine = 0;
   EModeCurFilename = "\"<uninit>\"";
   PP.setFileChangeHandler(HandleFileChange);
+  PP.setIdentHandler(HandleIdent);
   EModePP = &PP;
   EmodeEmittedTokensOnThisLine = false;
   

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

==============================================================================
--- cfe/cfe/trunk/Lex/Preprocessor.cpp (original)
+++ cfe/cfe/trunk/Lex/Preprocessor.cpp Wed Jul 11 11:23:27 2007
@@ -65,6 +65,7 @@
 
   // There is no file-change handler yet.
   FileChangeHandler = 0;
+  IdentHandler = 0;
   
   // Initialize the pragma handlers.
   PragmaHandlers = new PragmaNamespace(0);
@@ -1082,10 +1083,8 @@
         ;  // FIXME: implement #line
       if (Directive[0] == 'e' && !strcmp(Directive, "elif"))
         return HandleElifDirective(Result);
-      if (Directive[0] == 's' && !strcmp(Directive, "sccs")) {
-        isExtension = true;  // FIXME: implement #sccs
-        // SCCS is the same as #ident.
-      }
+      if (Directive[0] == 's' && !strcmp(Directive, "sccs"))
+        return HandleIdentSCCSDirective(Result);
       break;
     case 5:
       if (Directive[0] == 'e' && !strcmp(Directive, "endif"))
@@ -1097,7 +1096,7 @@
       if (Directive[0] == 'e' && !strcmp(Directive, "error"))
         return HandleUserDiagnosticDirective(Result, false);
       if (Directive[0] == 'i' && !strcmp(Directive, "ident"))
-        isExtension = true;  // FIXME: implement #ident
+        return HandleIdentSCCSDirective(Result);
       break;
     case 6:
       if (Directive[0] == 'd' && !strcmp(Directive, "define"))
@@ -1143,7 +1142,7 @@
   // Okay, we're done parsing the directive.
 }
 
-void Preprocessor::HandleUserDiagnosticDirective(LexerToken &Result, 
+void Preprocessor::HandleUserDiagnosticDirective(LexerToken &Tok, 
                                                  bool isWarning) {
   // Read the rest of the line raw.  We do this because we don't want macros
   // to be expanded and we don't require that the tokens be valid preprocessing
@@ -1153,7 +1152,26 @@
   std::string Message = CurLexer->ReadToEndOfLine();
 
   unsigned DiagID = isWarning ? diag::pp_hash_warning : diag::err_pp_hash_error;
-  return Diag(Result, DiagID, Message);
+  return Diag(Tok, DiagID, Message);
+}
+
+/// HandleIdentSCCSDirective - Handle a #ident/#sccs directive.
+///
+void Preprocessor::HandleIdentSCCSDirective(LexerToken &Tok) {
+  Diag(Tok, diag::ext_pp_ident_directive);
+  
+  LexerToken StrTok;
+  Lex(StrTok);
+  
+  // If the token kind isn't a string, it's a malformed directive.
+  if (StrTok.getKind() != tok::string_literal)
+    return Diag(StrTok, diag::err_pp_malformed_ident);
+  
+  // Verify that there is nothing after the string, other than EOM.
+  CheckEndOfDirective("#ident");
+
+  if (IdentHandler)
+    IdentHandler(Tok.getLocation(), getSpelling(StrTok));
 }
 
 //===----------------------------------------------------------------------===//

Modified: cfe/cfe/trunk/include/clang/Basic/DiagnosticKinds.def
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/include/clang/Basic/DiagnosticKinds.def?rev=38643&r1=38642&r2=38643&view=diff

==============================================================================
--- cfe/cfe/trunk/include/clang/Basic/DiagnosticKinds.def (original)
+++ cfe/cfe/trunk/include/clang/Basic/DiagnosticKinds.def Wed Jul 11 11:23:27 2007
@@ -103,6 +103,8 @@
 
 DIAG(ext_pp_import_directive, EXTENSION,
      "#import is a language extension")
+DIAG(ext_pp_ident_directive, EXTENSION,
+     "#ident is a language extension")
 DIAG(ext_pp_include_next_directive, EXTENSION,
      "#include_next is a language extension")
 DIAG(ext_pp_warning_directive, EXTENSION,
@@ -135,6 +137,8 @@
      "macro names must be identifiers")
 DIAG(err_pp_missing_macro_name, ERROR,
      "macro name missing")
+DIAG(err_pp_malformed_ident, ERROR,
+     "invalid #ident directive")
 DIAG(err_pp_unterminated_conditional, ERROR,
      "unterminated conditional directive")
 DIAG(pp_err_else_after_else, ERROR,

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=38643&r1=38642&r2=38643&view=diff

==============================================================================
--- cfe/cfe/trunk/include/clang/Lex/Preprocessor.h (original)
+++ cfe/cfe/trunk/include/clang/Lex/Preprocessor.h Wed Jul 11 11:23:27 2007
@@ -105,14 +105,22 @@
   enum FileChangeReason {
     EnterFile, ExitFile, SystemHeaderPragma, RenameFile
   };
+  typedef void (*FileChangeHandler_t)(SourceLocation Loc, 
+                                      FileChangeReason Reason,
+                                      DirectoryLookup::DirType FileType);
+  typedef void (*IdentHandler_t)(SourceLocation Loc, const std::string &str);
+  
 private:
   /// FileChangeHandler - This callback is invoked whenever a source file is
   /// entered or exited.  The SourceLocation indicates the new location, and
   /// EnteringFile indicates whether this is because we are entering a new
   /// #include'd file (when true) or whether we're exiting one because we ran
   /// off the end (when false).
-  void (*FileChangeHandler)(SourceLocation Loc, FileChangeReason Reason,
-                            DirectoryLookup::DirType FileType);
+  FileChangeHandler_t FileChangeHandler;
+  
+  /// IdentHandler - This is called whenever a #ident or #sccs directive is
+  /// found.
+  IdentHandler_t IdentHandler;
   
   enum {
     /// MaxIncludeStackDepth - Maximum depth of #includes.
@@ -234,11 +242,15 @@
   /// EnteringFile indicates whether this is because we are entering a new
   /// #include'd file (when true) or whether we're exiting one because we ran
   /// off the end (when false).
-  void setFileChangeHandler(void (*Handler)(SourceLocation, FileChangeReason,
-                                            DirectoryLookup::DirType)) {
+  void setFileChangeHandler(FileChangeHandler_t Handler) {
     FileChangeHandler = Handler;
   }
-  
+
+  /// setIdentHandler - Set the callback invoked whenever a #ident/#sccs
+  /// directive is found.
+  void setIdentHandler(IdentHandler_t Handler) {
+    IdentHandler = Handler;
+  }
   
   /// getIdentifierInfo - Return information about the specified preprocessor
   /// identifier token.  The version of this method that takes two character
@@ -453,7 +465,8 @@
   /// should side-effect the current preprocessor object so that the next call
   /// to Lex() will return the appropriate token next.
   
-  void HandleUserDiagnosticDirective(LexerToken &Result, bool isWarning);
+  void HandleUserDiagnosticDirective(LexerToken &Tok, bool isWarning);
+  void HandleIdentSCCSDirective(LexerToken &Tok);
   
   // File inclusion.
   void HandleIncludeDirective(LexerToken &Tok,





More information about the cfe-commits mailing list