SemaAttr.cpp 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626
  1. //===--- SemaAttr.cpp - Semantic Analysis for Attributes ------------------===//
  2. //
  3. // The LLVM Compiler Infrastructure
  4. //
  5. // This file is distributed under the University of Illinois Open Source
  6. // License. See LICENSE.TXT for details.
  7. //
  8. //===----------------------------------------------------------------------===//
  9. //
  10. // This file implements semantic analysis for non-trivial attributes and
  11. // pragmas.
  12. //
  13. //===----------------------------------------------------------------------===//
  14. #include "clang/Sema/SemaInternal.h"
  15. #include "clang/AST/ASTConsumer.h"
  16. #include "clang/AST/Attr.h"
  17. #include "clang/AST/Expr.h"
  18. #include "clang/Basic/TargetInfo.h"
  19. #include "clang/Lex/Preprocessor.h"
  20. #include "clang/Sema/Lookup.h"
  21. using namespace clang;
  22. //===----------------------------------------------------------------------===//
  23. // Pragma 'pack' and 'options align'
  24. //===----------------------------------------------------------------------===//
  25. namespace {
  26. struct PackStackEntry {
  27. // We just use a sentinel to represent when the stack is set to mac68k
  28. // alignment.
  29. static const unsigned kMac68kAlignmentSentinel = ~0U;
  30. unsigned Alignment;
  31. IdentifierInfo *Name;
  32. };
  33. /// PragmaPackStack - Simple class to wrap the stack used by #pragma
  34. /// pack.
  35. class PragmaPackStack {
  36. typedef std::vector<PackStackEntry> stack_ty;
  37. /// Alignment - The current user specified alignment.
  38. unsigned Alignment;
  39. /// Stack - Entries in the #pragma pack stack, consisting of saved
  40. /// alignments and optional names.
  41. stack_ty Stack;
  42. public:
  43. PragmaPackStack() : Alignment(0) {}
  44. void setAlignment(unsigned A) { Alignment = A; }
  45. unsigned getAlignment() { return Alignment; }
  46. /// push - Push the current alignment onto the stack, optionally
  47. /// using the given \arg Name for the record, if non-zero.
  48. void push(IdentifierInfo *Name) {
  49. PackStackEntry PSE = { Alignment, Name };
  50. Stack.push_back(PSE);
  51. }
  52. /// pop - Pop a record from the stack and restore the current
  53. /// alignment to the previous value. If \arg Name is non-zero then
  54. /// the first such named record is popped, otherwise the top record
  55. /// is popped. Returns true if the pop succeeded.
  56. bool pop(IdentifierInfo *Name, bool IsReset);
  57. };
  58. } // end anonymous namespace.
  59. bool PragmaPackStack::pop(IdentifierInfo *Name, bool IsReset) {
  60. // If name is empty just pop top.
  61. if (!Name) {
  62. // An empty stack is a special case...
  63. if (Stack.empty()) {
  64. // If this isn't a reset, it is always an error.
  65. if (!IsReset)
  66. return false;
  67. // Otherwise, it is an error only if some alignment has been set.
  68. if (!Alignment)
  69. return false;
  70. // Otherwise, reset to the default alignment.
  71. Alignment = 0;
  72. } else {
  73. Alignment = Stack.back().Alignment;
  74. Stack.pop_back();
  75. }
  76. return true;
  77. }
  78. // Otherwise, find the named record.
  79. for (unsigned i = Stack.size(); i != 0; ) {
  80. --i;
  81. if (Stack[i].Name == Name) {
  82. // Found it, pop up to and including this record.
  83. Alignment = Stack[i].Alignment;
  84. Stack.erase(Stack.begin() + i, Stack.end());
  85. return true;
  86. }
  87. }
  88. return false;
  89. }
  90. /// FreePackedContext - Deallocate and null out PackContext.
  91. void Sema::FreePackedContext() {
  92. delete static_cast<PragmaPackStack*>(PackContext);
  93. PackContext = nullptr;
  94. }
  95. void Sema::AddAlignmentAttributesForRecord(RecordDecl *RD) {
  96. // If there is no pack context, we don't need any attributes.
  97. if (!PackContext)
  98. return;
  99. PragmaPackStack *Stack = static_cast<PragmaPackStack*>(PackContext);
  100. // Otherwise, check to see if we need a max field alignment attribute.
  101. if (unsigned Alignment = Stack->getAlignment()) {
  102. if (Alignment == PackStackEntry::kMac68kAlignmentSentinel)
  103. RD->addAttr(AlignMac68kAttr::CreateImplicit(Context));
  104. else
  105. RD->addAttr(MaxFieldAlignmentAttr::CreateImplicit(Context,
  106. Alignment * 8));
  107. }
  108. }
  109. void Sema::AddMsStructLayoutForRecord(RecordDecl *RD) {
  110. if (MSStructPragmaOn)
  111. RD->addAttr(MSStructAttr::CreateImplicit(Context));
  112. // FIXME: We should merge AddAlignmentAttributesForRecord with
  113. // AddMsStructLayoutForRecord into AddPragmaAttributesForRecord, which takes
  114. // all active pragmas and applies them as attributes to class definitions.
  115. if (VtorDispModeStack.back() != getLangOpts().VtorDispMode)
  116. RD->addAttr(
  117. MSVtorDispAttr::CreateImplicit(Context, VtorDispModeStack.back()));
  118. }
  119. void Sema::ActOnPragmaOptionsAlign(PragmaOptionsAlignKind Kind,
  120. SourceLocation PragmaLoc) {
  121. if (!PackContext)
  122. PackContext = new PragmaPackStack();
  123. PragmaPackStack *Context = static_cast<PragmaPackStack*>(PackContext);
  124. switch (Kind) {
  125. // For all targets we support native and natural are the same.
  126. //
  127. // FIXME: This is not true on Darwin/PPC.
  128. case POAK_Native:
  129. case POAK_Power:
  130. case POAK_Natural:
  131. Context->push(nullptr);
  132. Context->setAlignment(0);
  133. break;
  134. // Note that '#pragma options align=packed' is not equivalent to attribute
  135. // packed, it has a different precedence relative to attribute aligned.
  136. case POAK_Packed:
  137. Context->push(nullptr);
  138. Context->setAlignment(1);
  139. break;
  140. case POAK_Mac68k:
  141. // Check if the target supports this.
  142. if (!this->Context.getTargetInfo().hasAlignMac68kSupport()) {
  143. Diag(PragmaLoc, diag::err_pragma_options_align_mac68k_target_unsupported);
  144. return;
  145. }
  146. Context->push(nullptr);
  147. Context->setAlignment(PackStackEntry::kMac68kAlignmentSentinel);
  148. break;
  149. case POAK_Reset:
  150. // Reset just pops the top of the stack, or resets the current alignment to
  151. // default.
  152. if (!Context->pop(nullptr, /*IsReset=*/true)) {
  153. Diag(PragmaLoc, diag::warn_pragma_options_align_reset_failed)
  154. << "stack empty";
  155. }
  156. break;
  157. }
  158. }
  159. void Sema::ActOnPragmaPack(PragmaPackKind Kind, IdentifierInfo *Name,
  160. Expr *alignment, SourceLocation PragmaLoc,
  161. SourceLocation LParenLoc, SourceLocation RParenLoc) {
  162. Expr *Alignment = static_cast<Expr *>(alignment);
  163. // If specified then alignment must be a "small" power of two.
  164. unsigned AlignmentVal = 0;
  165. if (Alignment) {
  166. llvm::APSInt Val;
  167. // pack(0) is like pack(), which just works out since that is what
  168. // we use 0 for in PackAttr.
  169. if (Alignment->isTypeDependent() ||
  170. Alignment->isValueDependent() ||
  171. !Alignment->isIntegerConstantExpr(Val, Context) ||
  172. !(Val == 0 || Val.isPowerOf2()) ||
  173. Val.getZExtValue() > 16) {
  174. Diag(PragmaLoc, diag::warn_pragma_pack_invalid_alignment);
  175. return; // Ignore
  176. }
  177. AlignmentVal = (unsigned) Val.getZExtValue();
  178. }
  179. if (!PackContext)
  180. PackContext = new PragmaPackStack();
  181. PragmaPackStack *Context = static_cast<PragmaPackStack*>(PackContext);
  182. switch (Kind) {
  183. case Sema::PPK_Default: // pack([n])
  184. Context->setAlignment(AlignmentVal);
  185. break;
  186. case Sema::PPK_Show: // pack(show)
  187. // Show the current alignment, making sure to show the right value
  188. // for the default.
  189. AlignmentVal = Context->getAlignment();
  190. // FIXME: This should come from the target.
  191. if (AlignmentVal == 0)
  192. AlignmentVal = 8;
  193. if (AlignmentVal == PackStackEntry::kMac68kAlignmentSentinel)
  194. Diag(PragmaLoc, diag::warn_pragma_pack_show) << "mac68k";
  195. else
  196. Diag(PragmaLoc, diag::warn_pragma_pack_show) << AlignmentVal;
  197. break;
  198. case Sema::PPK_Push: // pack(push [, id] [, [n])
  199. Context->push(Name);
  200. // Set the new alignment if specified.
  201. if (Alignment)
  202. Context->setAlignment(AlignmentVal);
  203. break;
  204. case Sema::PPK_Pop: // pack(pop [, id] [, n])
  205. // MSDN, C/C++ Preprocessor Reference > Pragma Directives > pack:
  206. // "#pragma pack(pop, identifier, n) is undefined"
  207. if (Alignment && Name)
  208. Diag(PragmaLoc, diag::warn_pragma_pack_pop_identifer_and_alignment);
  209. // Do the pop.
  210. if (!Context->pop(Name, /*IsReset=*/false)) {
  211. // If a name was specified then failure indicates the name
  212. // wasn't found. Otherwise failure indicates the stack was
  213. // empty.
  214. Diag(PragmaLoc, diag::warn_pragma_pop_failed)
  215. << "pack" << (Name ? "no record matching name" : "stack empty");
  216. // FIXME: Warn about popping named records as MSVC does.
  217. } else {
  218. // Pop succeeded, set the new alignment if specified.
  219. if (Alignment)
  220. Context->setAlignment(AlignmentVal);
  221. }
  222. break;
  223. }
  224. }
  225. void Sema::ActOnPragmaPackMatrix(bool bRowMajor, SourceLocation PragmaLoc) {
  226. // Once we've encountered one #pragma pack_matrix, we have a well-defined
  227. // default orientation for the rest of the program, even if we're rewriting.
  228. HasDefaultMatrixPack = true;
  229. DefaultMatrixPackRowMajor = bRowMajor;
  230. }
  231. void Sema::ActOnPragmaMSStruct(PragmaMSStructKind Kind) {
  232. MSStructPragmaOn = (Kind == PMSST_ON);
  233. }
  234. void Sema::ActOnPragmaMSComment(PragmaMSCommentKind Kind, StringRef Arg) {
  235. // FIXME: Serialize this.
  236. switch (Kind) {
  237. case PCK_Unknown:
  238. llvm_unreachable("unexpected pragma comment kind");
  239. case PCK_Linker:
  240. Consumer.HandleLinkerOptionPragma(Arg);
  241. return;
  242. case PCK_Lib:
  243. Consumer.HandleDependentLibrary(Arg);
  244. return;
  245. case PCK_Compiler:
  246. case PCK_ExeStr:
  247. case PCK_User:
  248. return; // We ignore all of these.
  249. }
  250. llvm_unreachable("invalid pragma comment kind");
  251. }
  252. void Sema::ActOnPragmaDetectMismatch(StringRef Name, StringRef Value) {
  253. // FIXME: Serialize this.
  254. Consumer.HandleDetectMismatch(Name, Value);
  255. }
  256. void Sema::ActOnPragmaMSPointersToMembers(
  257. LangOptions::PragmaMSPointersToMembersKind RepresentationMethod,
  258. SourceLocation PragmaLoc) {
  259. MSPointerToMemberRepresentationMethod = RepresentationMethod;
  260. ImplicitMSInheritanceAttrLoc = PragmaLoc;
  261. }
  262. void Sema::ActOnPragmaMSVtorDisp(PragmaVtorDispKind Kind,
  263. SourceLocation PragmaLoc,
  264. MSVtorDispAttr::Mode Mode) {
  265. switch (Kind) {
  266. case PVDK_Set:
  267. VtorDispModeStack.back() = Mode;
  268. break;
  269. case PVDK_Push:
  270. VtorDispModeStack.push_back(Mode);
  271. break;
  272. case PVDK_Reset:
  273. VtorDispModeStack.clear();
  274. VtorDispModeStack.push_back(MSVtorDispAttr::Mode(LangOpts.VtorDispMode));
  275. break;
  276. case PVDK_Pop:
  277. VtorDispModeStack.pop_back();
  278. if (VtorDispModeStack.empty()) {
  279. Diag(PragmaLoc, diag::warn_pragma_pop_failed) << "vtordisp"
  280. << "stack empty";
  281. VtorDispModeStack.push_back(MSVtorDispAttr::Mode(LangOpts.VtorDispMode));
  282. }
  283. break;
  284. }
  285. }
  286. template<typename ValueType>
  287. void Sema::PragmaStack<ValueType>::Act(SourceLocation PragmaLocation,
  288. PragmaMsStackAction Action,
  289. llvm::StringRef StackSlotLabel,
  290. ValueType Value) {
  291. if (Action == PSK_Reset) {
  292. CurrentValue = nullptr;
  293. return;
  294. }
  295. if (Action & PSK_Push)
  296. Stack.push_back(Slot(StackSlotLabel, CurrentValue, CurrentPragmaLocation));
  297. else if (Action & PSK_Pop) {
  298. if (!StackSlotLabel.empty()) {
  299. // If we've got a label, try to find it and jump there.
  300. auto I = std::find_if(Stack.rbegin(), Stack.rend(),
  301. [&](const Slot &x) { return x.StackSlotLabel == StackSlotLabel; });
  302. // If we found the label so pop from there.
  303. if (I != Stack.rend()) {
  304. CurrentValue = I->Value;
  305. CurrentPragmaLocation = I->PragmaLocation;
  306. Stack.erase(std::prev(I.base()), Stack.end());
  307. }
  308. } else if (!Stack.empty()) {
  309. // We don't have a label, just pop the last entry.
  310. CurrentValue = Stack.back().Value;
  311. CurrentPragmaLocation = Stack.back().PragmaLocation;
  312. Stack.pop_back();
  313. }
  314. }
  315. if (Action & PSK_Set) {
  316. CurrentValue = Value;
  317. CurrentPragmaLocation = PragmaLocation;
  318. }
  319. }
  320. bool Sema::UnifySection(StringRef SectionName,
  321. int SectionFlags,
  322. DeclaratorDecl *Decl) {
  323. auto Section = Context.SectionInfos.find(SectionName);
  324. if (Section == Context.SectionInfos.end()) {
  325. Context.SectionInfos[SectionName] =
  326. ASTContext::SectionInfo(Decl, SourceLocation(), SectionFlags);
  327. return false;
  328. }
  329. // A pre-declared section takes precedence w/o diagnostic.
  330. if (Section->second.SectionFlags == SectionFlags ||
  331. !(Section->second.SectionFlags & ASTContext::PSF_Implicit))
  332. return false;
  333. auto OtherDecl = Section->second.Decl;
  334. Diag(Decl->getLocation(), diag::err_section_conflict)
  335. << Decl << OtherDecl;
  336. Diag(OtherDecl->getLocation(), diag::note_declared_at)
  337. << OtherDecl->getName();
  338. if (auto A = Decl->getAttr<SectionAttr>())
  339. if (A->isImplicit())
  340. Diag(A->getLocation(), diag::note_pragma_entered_here);
  341. if (auto A = OtherDecl->getAttr<SectionAttr>())
  342. if (A->isImplicit())
  343. Diag(A->getLocation(), diag::note_pragma_entered_here);
  344. return true;
  345. }
  346. bool Sema::UnifySection(StringRef SectionName,
  347. int SectionFlags,
  348. SourceLocation PragmaSectionLocation) {
  349. auto Section = Context.SectionInfos.find(SectionName);
  350. if (Section != Context.SectionInfos.end()) {
  351. if (Section->second.SectionFlags == SectionFlags)
  352. return false;
  353. if (!(Section->second.SectionFlags & ASTContext::PSF_Implicit)) {
  354. Diag(PragmaSectionLocation, diag::err_section_conflict)
  355. << "this" << "a prior #pragma section";
  356. Diag(Section->second.PragmaSectionLocation,
  357. diag::note_pragma_entered_here);
  358. return true;
  359. }
  360. }
  361. Context.SectionInfos[SectionName] =
  362. ASTContext::SectionInfo(nullptr, PragmaSectionLocation, SectionFlags);
  363. return false;
  364. }
  365. /// \brief Called on well formed \#pragma bss_seg().
  366. void Sema::ActOnPragmaMSSeg(SourceLocation PragmaLocation,
  367. PragmaMsStackAction Action,
  368. llvm::StringRef StackSlotLabel,
  369. StringLiteral *SegmentName,
  370. llvm::StringRef PragmaName) {
  371. PragmaStack<StringLiteral *> *Stack =
  372. llvm::StringSwitch<PragmaStack<StringLiteral *> *>(PragmaName)
  373. .Case("data_seg", &DataSegStack)
  374. .Case("bss_seg", &BSSSegStack)
  375. .Case("const_seg", &ConstSegStack)
  376. .Case("code_seg", &CodeSegStack);
  377. if (Action & PSK_Pop && Stack->Stack.empty())
  378. Diag(PragmaLocation, diag::warn_pragma_pop_failed) << PragmaName
  379. << "stack empty";
  380. if (SegmentName &&
  381. !checkSectionName(SegmentName->getLocStart(), SegmentName->getString()))
  382. return;
  383. Stack->Act(PragmaLocation, Action, StackSlotLabel, SegmentName);
  384. }
  385. /// \brief Called on well formed \#pragma bss_seg().
  386. void Sema::ActOnPragmaMSSection(SourceLocation PragmaLocation,
  387. int SectionFlags, StringLiteral *SegmentName) {
  388. UnifySection(SegmentName->getString(), SectionFlags, PragmaLocation);
  389. }
  390. void Sema::ActOnPragmaMSInitSeg(SourceLocation PragmaLocation,
  391. StringLiteral *SegmentName) {
  392. // There's no stack to maintain, so we just have a current section. When we
  393. // see the default section, reset our current section back to null so we stop
  394. // tacking on unnecessary attributes.
  395. CurInitSeg = SegmentName->getString() == ".CRT$XCU" ? nullptr : SegmentName;
  396. CurInitSegLoc = PragmaLocation;
  397. }
  398. void Sema::ActOnPragmaUnused(const Token &IdTok, Scope *curScope,
  399. SourceLocation PragmaLoc) {
  400. IdentifierInfo *Name = IdTok.getIdentifierInfo();
  401. LookupResult Lookup(*this, Name, IdTok.getLocation(), LookupOrdinaryName);
  402. LookupParsedName(Lookup, curScope, nullptr, true);
  403. if (Lookup.empty()) {
  404. Diag(PragmaLoc, diag::warn_pragma_unused_undeclared_var)
  405. << Name << SourceRange(IdTok.getLocation());
  406. return;
  407. }
  408. VarDecl *VD = Lookup.getAsSingle<VarDecl>();
  409. if (!VD) {
  410. Diag(PragmaLoc, diag::warn_pragma_unused_expected_var_arg)
  411. << Name << SourceRange(IdTok.getLocation());
  412. return;
  413. }
  414. // Warn if this was used before being marked unused.
  415. if (VD->isUsed())
  416. Diag(PragmaLoc, diag::warn_used_but_marked_unused) << Name;
  417. VD->addAttr(UnusedAttr::CreateImplicit(Context, IdTok.getLocation()));
  418. }
  419. void Sema::AddCFAuditedAttribute(Decl *D) {
  420. SourceLocation Loc = PP.getPragmaARCCFCodeAuditedLoc();
  421. if (!Loc.isValid()) return;
  422. // Don't add a redundant or conflicting attribute.
  423. if (D->hasAttr<CFAuditedTransferAttr>() ||
  424. D->hasAttr<CFUnknownTransferAttr>())
  425. return;
  426. D->addAttr(CFAuditedTransferAttr::CreateImplicit(Context, Loc));
  427. }
  428. void Sema::ActOnPragmaOptimize(bool On, SourceLocation PragmaLoc) {
  429. if(On)
  430. OptimizeOffPragmaLocation = SourceLocation();
  431. else
  432. OptimizeOffPragmaLocation = PragmaLoc;
  433. }
  434. void Sema::AddRangeBasedOptnone(FunctionDecl *FD) {
  435. // In the future, check other pragmas if they're implemented (e.g. pragma
  436. // optimize 0 will probably map to this functionality too).
  437. if(OptimizeOffPragmaLocation.isValid())
  438. AddOptnoneAttributeIfNoConflicts(FD, OptimizeOffPragmaLocation);
  439. }
  440. void Sema::AddOptnoneAttributeIfNoConflicts(FunctionDecl *FD,
  441. SourceLocation Loc) {
  442. // Don't add a conflicting attribute. No diagnostic is needed.
  443. if (FD->hasAttr<MinSizeAttr>() || FD->hasAttr<AlwaysInlineAttr>())
  444. return;
  445. // Add attributes only if required. Optnone requires noinline as well, but if
  446. // either is already present then don't bother adding them.
  447. if (!FD->hasAttr<OptimizeNoneAttr>())
  448. FD->addAttr(OptimizeNoneAttr::CreateImplicit(Context, Loc));
  449. if (!FD->hasAttr<NoInlineAttr>())
  450. FD->addAttr(NoInlineAttr::CreateImplicit(Context, Loc));
  451. }
  452. typedef std::vector<std::pair<unsigned, SourceLocation> > VisStack;
  453. enum : unsigned { NoVisibility = ~0U };
  454. void Sema::AddPushedVisibilityAttribute(Decl *D) {
  455. if (!VisContext)
  456. return;
  457. NamedDecl *ND = dyn_cast<NamedDecl>(D);
  458. if (ND && ND->getExplicitVisibility(NamedDecl::VisibilityForValue))
  459. return;
  460. VisStack *Stack = static_cast<VisStack*>(VisContext);
  461. unsigned rawType = Stack->back().first;
  462. if (rawType == NoVisibility) return;
  463. VisibilityAttr::VisibilityType type
  464. = (VisibilityAttr::VisibilityType) rawType;
  465. SourceLocation loc = Stack->back().second;
  466. D->addAttr(VisibilityAttr::CreateImplicit(Context, type, loc));
  467. }
  468. /// FreeVisContext - Deallocate and null out VisContext.
  469. void Sema::FreeVisContext() {
  470. delete static_cast<VisStack*>(VisContext);
  471. VisContext = nullptr;
  472. }
  473. static void PushPragmaVisibility(Sema &S, unsigned type, SourceLocation loc) {
  474. // Put visibility on stack.
  475. if (!S.VisContext)
  476. S.VisContext = new VisStack;
  477. VisStack *Stack = static_cast<VisStack*>(S.VisContext);
  478. Stack->push_back(std::make_pair(type, loc));
  479. }
  480. void Sema::ActOnPragmaVisibility(const IdentifierInfo* VisType,
  481. SourceLocation PragmaLoc) {
  482. if (VisType) {
  483. // Compute visibility to use.
  484. VisibilityAttr::VisibilityType T;
  485. if (!VisibilityAttr::ConvertStrToVisibilityType(VisType->getName(), T)) {
  486. Diag(PragmaLoc, diag::warn_attribute_unknown_visibility) << VisType;
  487. return;
  488. }
  489. PushPragmaVisibility(*this, T, PragmaLoc);
  490. } else {
  491. PopPragmaVisibility(false, PragmaLoc);
  492. }
  493. }
  494. void Sema::ActOnPragmaFPContract(tok::OnOffSwitch OOS) {
  495. switch (OOS) {
  496. case tok::OOS_ON:
  497. FPFeatures.fp_contract = 1;
  498. break;
  499. case tok::OOS_OFF:
  500. FPFeatures.fp_contract = 0;
  501. break;
  502. case tok::OOS_DEFAULT:
  503. FPFeatures.fp_contract = getLangOpts().DefaultFPContract;
  504. break;
  505. }
  506. }
  507. void Sema::PushNamespaceVisibilityAttr(const VisibilityAttr *Attr,
  508. SourceLocation Loc) {
  509. // Visibility calculations will consider the namespace's visibility.
  510. // Here we just want to note that we're in a visibility context
  511. // which overrides any enclosing #pragma context, but doesn't itself
  512. // contribute visibility.
  513. PushPragmaVisibility(*this, NoVisibility, Loc);
  514. }
  515. void Sema::PopPragmaVisibility(bool IsNamespaceEnd, SourceLocation EndLoc) {
  516. if (!VisContext) {
  517. Diag(EndLoc, diag::err_pragma_pop_visibility_mismatch);
  518. return;
  519. }
  520. // Pop visibility from stack
  521. VisStack *Stack = static_cast<VisStack*>(VisContext);
  522. const std::pair<unsigned, SourceLocation> *Back = &Stack->back();
  523. bool StartsWithPragma = Back->first != NoVisibility;
  524. if (StartsWithPragma && IsNamespaceEnd) {
  525. Diag(Back->second, diag::err_pragma_push_visibility_mismatch);
  526. Diag(EndLoc, diag::note_surrounding_namespace_ends_here);
  527. // For better error recovery, eat all pushes inside the namespace.
  528. do {
  529. Stack->pop_back();
  530. Back = &Stack->back();
  531. StartsWithPragma = Back->first != NoVisibility;
  532. } while (StartsWithPragma);
  533. } else if (!StartsWithPragma && !IsNamespaceEnd) {
  534. Diag(EndLoc, diag::err_pragma_pop_visibility_mismatch);
  535. Diag(Back->second, diag::note_surrounding_namespace_starts_here);
  536. return;
  537. }
  538. Stack->pop_back();
  539. // To simplify the implementation, never keep around an empty stack.
  540. if (Stack->empty())
  541. FreeVisContext();
  542. }