]> granicus.if.org Git - clang/commitdiff
Serialize `pragma pointers_to_members` state.
authorNico Weber <nicolasweber@gmx.de>
Thu, 3 Mar 2016 00:17:35 +0000 (00:17 +0000)
committerNico Weber <nicolasweber@gmx.de>
Thu, 3 Mar 2016 00:17:35 +0000 (00:17 +0000)
Like r262539, but for pointers_to_members.

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

include/clang/Serialization/ASTBitCodes.h
include/clang/Serialization/ASTReader.h
include/clang/Serialization/ASTWriter.h
lib/Serialization/ASTReader.cpp
lib/Serialization/ASTWriter.cpp
test/PCH/pragma-pointers_to_members.cpp [new file with mode: 0644]

index a47888ab06d23c0466574858c679601d71a498eb..c9dcdf696d3d20b7e1b3fbb64763a1c939fe3273 100644 (file)
@@ -578,7 +578,10 @@ namespace clang {
       DELETE_EXPRS_TO_ANALYZE = 54,
 
       /// \brief Record code for \#pragma ms_struct options.
-      MSSTRUCT_PRAGMA_OPTIONS = 55
+      MSSTRUCT_PRAGMA_OPTIONS = 55,
+
+      /// \brief Record code for \#pragma ms_struct options.
+      POINTERS_TO_MEMBERS_PRAGMA_OPTIONS = 56
     };
 
     /// \brief Record types used within a source manager block.
index cb092344bbdf4dc777212df5e05c01420cd5e44a..e789c1e9d1ef56bb9ea42e515a92c4fa79fd047d 100644 (file)
@@ -788,6 +788,10 @@ private:
   /// \brief The PragmaMSStructKind pragma ms_struct state if set, or -1.
   int PragmaMSStructState;
 
+  /// \brief The PragmaMSPointersToMembersKind pragma pointers_to_members state.
+  int PragmaMSPointersToMembersState;
+  SourceLocation PointersToMembersPragmaLocation;
+
   /// \brief The OpenCL extension settings.
   SmallVector<uint64_t, 1> OpenCLExtensions;
 
index e31f6e98370266a404ed35c93e708247f5711af4..7a77aab488012c5589791d14ea04a0457a0fb60c 100644 (file)
@@ -552,6 +552,7 @@ private:
   void WriteLateParsedTemplates(Sema &SemaRef);
   void WriteOptimizePragmaOptions(Sema &SemaRef);
   void WriteMSStructPragmaOptions(Sema &SemaRef);
+  void WriteMSPointersToMembersPragmaOptions(Sema &SemaRef);
   void WriteModuleFileExtension(Sema &SemaRef,
                                 ModuleFileExtensionWriter &Writer);
 
index 57dc611c7e00dab73afd88dc03ccab6054354388..f730d6f4f202419997bfe91fa7632b5848a53ef0 100644 (file)
@@ -3225,6 +3225,15 @@ ASTReader::ReadASTBlock(ModuleFile &F, unsigned ClientLoadCapabilities) {
       PragmaMSStructState = Record[0];
       break;
 
+    case POINTERS_TO_MEMBERS_PRAGMA_OPTIONS:
+      if (Record.size() != 2) {
+        Error("invalid pragma ms_struct record");
+        return Failure;
+      }
+      PragmaMSPointersToMembersState = Record[0];
+      PointersToMembersPragmaLocation = ReadSourceLocation(F, Record[1]);
+      break;
+
     case UNUSED_LOCAL_TYPEDEF_NAME_CANDIDATES:
       for (unsigned I = 0, N = Record.size(); I != N; ++I)
         UnusedLocalTypedefNameCandidates.push_back(
@@ -7012,6 +7021,12 @@ void ASTReader::UpdateSema() {
     SemaObj->ActOnPragmaOptimize(/* IsOn = */ false, OptimizeOffPragmaLocation);
   if (PragmaMSStructState != -1)
     SemaObj->ActOnPragmaMSStruct((PragmaMSStructKind)PragmaMSStructState);
+  if (PointersToMembersPragmaLocation.isValid()) {
+    SemaObj->ActOnPragmaMSPointersToMembers(
+        (LangOptions::PragmaMSPointersToMembersKind)
+            PragmaMSPointersToMembersState,
+        PointersToMembersPragmaLocation);
+  }
 }
 
 IdentifierInfo *ASTReader::get(StringRef Name) {
@@ -8707,6 +8722,7 @@ ASTReader::ASTReader(
       Consumer(nullptr), ModuleMgr(PP.getFileManager(), PCHContainerRdr),
       ReadTimer(std::move(ReadTimer)),
       PragmaMSStructState(-1),
+      PragmaMSPointersToMembersState(-1),
       isysroot(isysroot), DisableValidation(DisableValidation),
       AllowASTWithCompilerErrors(AllowASTWithCompilerErrors),
       AllowConfigurationMismatch(AllowConfigurationMismatch),
index bef7fc267ebf27144f730c19a1c062ff7d8aefe7..ee475d3cc520fb4e792baaeb0edb926be75d1df7 100644 (file)
@@ -961,6 +961,7 @@ void ASTWriter::WriteBlockInfoBlock() {
   RECORD(LATE_PARSED_TEMPLATE);
   RECORD(OPTIMIZE_PRAGMA_OPTIONS);
   RECORD(MSSTRUCT_PRAGMA_OPTIONS);
+  RECORD(POINTERS_TO_MEMBERS_PRAGMA_OPTIONS);
   RECORD(UNUSED_LOCAL_TYPEDEF_NAME_CANDIDATES);
   RECORD(CXX_CTOR_INITIALIZERS_OFFSETS);
   RECORD(DELETE_EXPRS_TO_ANALYZE);
@@ -3936,6 +3937,15 @@ void ASTWriter::WriteMSStructPragmaOptions(Sema &SemaRef) {
   Stream.EmitRecord(MSSTRUCT_PRAGMA_OPTIONS, Record);
 }
 
+/// \brief Write the state of 'pragma pointers_to_members' at the end of the
+//module.
+void ASTWriter::WriteMSPointersToMembersPragmaOptions(Sema &SemaRef) {
+  RecordData Record;
+  Record.push_back(SemaRef.MSPointerToMemberRepresentationMethod);
+  AddSourceLocation(SemaRef.ImplicitMSInheritanceAttrLoc, Record);
+  Stream.EmitRecord(POINTERS_TO_MEMBERS_PRAGMA_OPTIONS, Record);
+}
+
 void ASTWriter::WriteModuleFileExtension(Sema &SemaRef,
                                          ModuleFileExtensionWriter &Writer) {
   // Enter the extension block.
@@ -4616,6 +4626,7 @@ uint64_t ASTWriter::WriteASTCore(Sema &SemaRef, StringRef isysroot,
   if(!WritingModule) {
     WriteOptimizePragmaOptions(SemaRef);
     WriteMSStructPragmaOptions(SemaRef);
+    WriteMSPointersToMembersPragmaOptions(SemaRef);
   }
 
   // Some simple statistics
diff --git a/test/PCH/pragma-pointers_to_members.cpp b/test/PCH/pragma-pointers_to_members.cpp
new file mode 100644 (file)
index 0000000..53edd6b
--- /dev/null
@@ -0,0 +1,34 @@
+// Test this without pch.
+// RUN: %clang_cc1 %s -Wunknown-pragmas -Werror -triple i386-pc-win32 -fms-extensions -fsyntax-only -include %s -verify -std=c++11
+
+// Test with pch.
+// RUN: %clang_cc1 %s -Wunknown-pragmas -Werror -triple i386-pc-win32  -fms-extensions -emit-pch -o %t -std=c++11
+// RUN: %clang_cc1 %s -Wunknown-pragmas -Werror -triple i386-pc-win32  -fms-extensions -fsyntax-only -include-pch %t -verify -std=c++11
+
+// The first run line creates a pch, and since at that point HEADER is not
+// defined, the only thing contained in the pch is the pragma. The second line
+// then includes that pch, so HEADER is defined and the actual code is compiled.
+// The check then makes sure that the pragma is in effect in the file that
+// includes the pch.
+
+// expected-no-diagnostics
+
+#ifndef HEADER
+#define HEADER
+
+struct S0;
+static_assert(sizeof(int S0::*) == 12, "");
+
+struct S1;
+struct S2;
+
+#pragma pointers_to_members(full_generality, single_inheritance)
+
+static_assert(sizeof(int S1::*) == 4, "");
+
+#else
+
+static_assert(sizeof(int S2::*) == 4, "");
+static_assert(sizeof(int S0::*) == 12, "");
+
+#endif