]> granicus.if.org Git - clang/commitdiff
Recognize gcc's ms_struct pragma (and ignore for now).
authorFariborz Jahanian <fjahanian@apple.com>
Mon, 25 Apr 2011 18:49:15 +0000 (18:49 +0000)
committerFariborz Jahanian <fjahanian@apple.com>
Mon, 25 Apr 2011 18:49:15 +0000 (18:49 +0000)
This is wip.

git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@130138 91177308-0d34-0410-b5e6-96231b3b80d8

include/clang/Basic/DiagnosticParseKinds.td
include/clang/Parse/Parser.h
include/clang/Sema/Sema.h
lib/Parse/ParsePragma.cpp
lib/Parse/ParsePragma.h
lib/Parse/Parser.cpp
lib/Sema/Sema.cpp
lib/Sema/SemaAttr.cpp
test/Sema/pragma-ms_struct.c [new file with mode: 0644]

index 6e1e1e46849c1530857001ed05ae6d695c1fdf9a..ccd48daca6a71427c447d4c1ddfe453458436881 100644 (file)
@@ -485,6 +485,8 @@ def warn_pragma_expected_rparen : Warning<
   "missing ')' after '#pragma %0' - ignoring">;
 def warn_pragma_expected_identifier : Warning<
   "expected identifier in '#pragma %0' - ignored">;  
+def warn_pragma_ms_struct : Warning<
+  "incorrect use of '#pragma ms_struct on|off' - ignored">;  
 def warn_pragma_extra_tokens_at_eol : Warning<
   "extra tokens at end of '#pragma %0' - ignored">; 
 // - #pragma options
index de4904a9a9812d56ae93af3eee9004f103b64edf..0311c06ece84825b2efc1f7236a5cf4057621fe8 100644 (file)
@@ -131,6 +131,7 @@ class Parser : public CodeCompletionHandler {
   llvm::OwningPtr<PragmaHandler> GCCVisibilityHandler;
   llvm::OwningPtr<PragmaHandler> OptionsHandler;
   llvm::OwningPtr<PragmaHandler> PackHandler;
+  llvm::OwningPtr<PragmaHandler> MSStructHandler;
   llvm::OwningPtr<PragmaHandler> UnusedHandler;
   llvm::OwningPtr<PragmaHandler> WeakHandler;
   llvm::OwningPtr<PragmaHandler> FPContractHandler;
index 6c08712fe715c87dec66087aba5396571d557f31..e635526ebdfdcadfbdf69920607434bcdcd28863 100644 (file)
@@ -240,6 +240,8 @@ public:
   /// PackContext - Manages the stack for #pragma pack. An alignment
   /// of 0 indicates default alignment.
   void *PackContext; // Really a "PragmaPackStack*"
+    
+  bool MSStructPragmaOn; // True when #pragma ms_struct on
 
   /// VisContext - Manages the stack for #pragma GCC visibility.
   void *VisContext; // Really a "PragmaVisStack*"
@@ -4855,6 +4857,11 @@ public:
     PPK_Pop      // #pragma pack(pop, [identifier], [n])
   };
 
+  enum PragmaMSStructKind {
+    PMSST_OFF,  // #pragms ms_struct off
+    PMSST_ON    // #pragms ms_struct on
+  };
+
   /// ActOnPragmaPack - Called on well formed #pragma pack(...).
   void ActOnPragmaPack(PragmaPackKind Kind,
                        IdentifierInfo *Name,
@@ -4862,6 +4869,9 @@ public:
                        SourceLocation PragmaLoc,
                        SourceLocation LParenLoc,
                        SourceLocation RParenLoc);
+    
+  /// ActOnPragmaMSStruct - Called on well formed #pragms ms_struct [on|off].
+  void ActOnPragmaMSStruct(PragmaMSStructKind Kind);
 
   /// ActOnPragmaUnused - Called on well-formed '#pragma unused'.
   void ActOnPragmaUnused(const Token &Identifier,
index beb1af67acccaa77768b298a56e5619f09fbfcdd..46225c8e79109bdc5e28cc24429d4768e4cdb8ad 100644 (file)
@@ -177,6 +177,38 @@ void PragmaPackHandler::HandlePragma(Preprocessor &PP,
                           LParenLoc, RParenLoc);
 }
 
+// #pragma ms_struct on
+// #pragma ms_struct off
+void PragmaMSStructHandler::HandlePragma(Preprocessor &PP, 
+                                         PragmaIntroducerKind Introducer,
+                                         Token &MSStructTok) {
+  Sema::PragmaMSStructKind Kind = Sema::PMSST_OFF;
+  
+  Token Tok;
+  PP.Lex(Tok);
+  if (Tok.isNot(tok::identifier)) {
+    PP.Diag(Tok.getLocation(), diag::warn_pragma_ms_struct);
+    return;
+  }
+  const IdentifierInfo *II = Tok.getIdentifierInfo();
+  if (II->isStr("on")) {
+    Kind = Sema::PMSST_ON;
+    PP.Lex(Tok);
+  }
+  else if (II->isStr("off") || II->isStr("reset"))
+    PP.Lex(Tok);
+  else {
+    PP.Diag(Tok.getLocation(), diag::warn_pragma_ms_struct);
+    return;
+  }
+  
+  if (Tok.isNot(tok::eod)) {
+    PP.Diag(Tok.getLocation(), diag::warn_pragma_extra_tokens_at_eol) << "ms_struct";
+    return;
+  }
+  Actions.ActOnPragmaMSStruct(Kind);
+}
+
 // #pragma 'align' '=' {'native','natural','mac68k','power','reset'}
 // #pragma 'options 'align' '=' {'native','natural','mac68k','power','reset'}
 static void ParseAlignPragma(Sema &Actions, Preprocessor &PP, Token &FirstTok,
index bee6af3f4cfddef17188725e238c0c13b25ed965..1d3138fa70a8266016bc167fb838e161141333a8 100644 (file)
@@ -58,6 +58,16 @@ public:
   virtual void HandlePragma(Preprocessor &PP, PragmaIntroducerKind Introducer,
                             Token &FirstToken);
 };
+  
+class PragmaMSStructHandler : public PragmaHandler {
+  Sema &Actions;
+public:
+  explicit PragmaMSStructHandler(Sema &A) : PragmaHandler("ms_struct"),
+  Actions(A) {}
+    
+  virtual void HandlePragma(Preprocessor &PP, PragmaIntroducerKind Introducer,
+                            Token &FirstToken);
+};
 
 class PragmaUnusedHandler : public PragmaHandler {
   Sema &Actions;
index 9244b99492c8fdeebf488496bcfec061963263ea..debc7404b914614ed1fe77bfbcf38b0845eed964 100644 (file)
@@ -45,6 +45,9 @@ Parser::Parser(Preprocessor &pp, Sema &actions)
 
   PackHandler.reset(new PragmaPackHandler(actions));
   PP.AddPragmaHandler(PackHandler.get());
+    
+  MSStructHandler.reset(new PragmaMSStructHandler(actions));
+  PP.AddPragmaHandler(MSStructHandler.get());
 
   UnusedHandler.reset(new PragmaUnusedHandler(actions, *this));
   PP.AddPragmaHandler(UnusedHandler.get());
@@ -377,6 +380,8 @@ Parser::~Parser() {
   OptionsHandler.reset();
   PP.RemovePragmaHandler(PackHandler.get());
   PackHandler.reset();
+  PP.RemovePragmaHandler(MSStructHandler.get());
+  MSStructHandler.reset();
   PP.RemovePragmaHandler(UnusedHandler.get());
   UnusedHandler.reset();
   PP.RemovePragmaHandler(WeakHandler.get());
index 3ce1d82c8811c3c0943b709be1eae0a053ef67b8..7707fb1104be5b2d780b11c74c8fe3b9d7736db1 100644 (file)
@@ -141,7 +141,7 @@ Sema::Sema(Preprocessor &pp, ASTContext &ctxt, ASTConsumer &consumer,
     LangOpts(pp.getLangOptions()), PP(pp), Context(ctxt), Consumer(consumer),
     Diags(PP.getDiagnostics()), SourceMgr(PP.getSourceManager()),
     ExternalSource(0), CodeCompleter(CodeCompleter), CurContext(0), 
-    PackContext(0), VisContext(0),
+    PackContext(0), MSStructPragmaOn(false), VisContext(0),
     LateTemplateParser(0), OpaqueParser(0),
     IdResolver(pp.getLangOptions()), CXXTypeInfoDecl(0), MSVCGuidDecl(0),
     GlobalNewDeleteDeclared(false), 
@@ -184,7 +184,7 @@ Sema::~Sema() {
   if (PackContext) FreePackedContext();
   if (VisContext) FreeVisContext();
   delete TheTargetAttributesSema;
-
+  MSStructPragmaOn = false;
   // Kill all the active scopes.
   for (unsigned I = 1, E = FunctionScopes.size(); I != E; ++I)
     delete FunctionScopes[I];
index 4fad1730487212cb0dd5a8e8710ef2cc7449cfc6..7a50356fedbba0761192fabdb1b1621a0bd0611a 100644 (file)
@@ -263,6 +263,10 @@ void Sema::ActOnPragmaPack(PragmaPackKind Kind, IdentifierInfo *Name,
   }
 }
 
+void Sema::ActOnPragmaMSStruct(PragmaMSStructKind Kind) { 
+  MSStructPragmaOn = (Kind == PMSST_ON);
+}
+
 void Sema::ActOnPragmaUnused(const Token &IdTok, Scope *curScope,
                              SourceLocation PragmaLoc) {
 
diff --git a/test/Sema/pragma-ms_struct.c b/test/Sema/pragma-ms_struct.c
new file mode 100644 (file)
index 0000000..61047c0
--- /dev/null
@@ -0,0 +1,19 @@
+// RUN: %clang_cc1 -fsyntax-only -verify -triple x86_64-apple-darwin9 %s
+
+#pragma ms_struct on
+
+#pragma ms_struct off
+
+#pragma ms_struct reset
+
+#pragma ms_struct // expected-warning {{incorrect use of '#pragma ms_struct on|off' - ignored}}
+
+#pragma ms_struct on top of spaghetti  // expected-warning {{extra tokens at end of '#pragma ms_struct' - ignored}}
+
+struct foo
+{
+  int a;
+  int b;
+  char c;
+};
+