1 //===--- SemaAttr.cpp - Semantic Analysis for Attributes ------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file implements semantic analysis for non-trivial attributes and 10 // pragmas. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #include "clang/AST/ASTConsumer.h" 15 #include "clang/AST/Attr.h" 16 #include "clang/AST/Expr.h" 17 #include "clang/Basic/TargetInfo.h" 18 #include "clang/Lex/Preprocessor.h" 19 #include "clang/Sema/Lookup.h" 20 #include "clang/Sema/SemaInternal.h" 21 using namespace clang; 22 23 //===----------------------------------------------------------------------===// 24 // Pragma 'pack' and 'options align' 25 //===----------------------------------------------------------------------===// 26 27 Sema::PragmaStackSentinelRAII::PragmaStackSentinelRAII(Sema &S, 28 StringRef SlotLabel, 29 bool ShouldAct) 30 : S(S), SlotLabel(SlotLabel), ShouldAct(ShouldAct) { 31 if (ShouldAct) { 32 S.VtorDispStack.SentinelAction(PSK_Push, SlotLabel); 33 S.DataSegStack.SentinelAction(PSK_Push, SlotLabel); 34 S.BSSSegStack.SentinelAction(PSK_Push, SlotLabel); 35 S.ConstSegStack.SentinelAction(PSK_Push, SlotLabel); 36 S.CodeSegStack.SentinelAction(PSK_Push, SlotLabel); 37 } 38 } 39 40 Sema::PragmaStackSentinelRAII::~PragmaStackSentinelRAII() { 41 if (ShouldAct) { 42 S.VtorDispStack.SentinelAction(PSK_Pop, SlotLabel); 43 S.DataSegStack.SentinelAction(PSK_Pop, SlotLabel); 44 S.BSSSegStack.SentinelAction(PSK_Pop, SlotLabel); 45 S.ConstSegStack.SentinelAction(PSK_Pop, SlotLabel); 46 S.CodeSegStack.SentinelAction(PSK_Pop, SlotLabel); 47 } 48 } 49 50 void Sema::AddAlignmentAttributesForRecord(RecordDecl *RD) { 51 // If there is no pack value, we don't need any attributes. 52 if (!PackStack.CurrentValue) 53 return; 54 55 // Otherwise, check to see if we need a max field alignment attribute. 56 if (unsigned Alignment = PackStack.CurrentValue) { 57 if (Alignment == Sema::kMac68kAlignmentSentinel) 58 RD->addAttr(AlignMac68kAttr::CreateImplicit(Context)); 59 else 60 RD->addAttr(MaxFieldAlignmentAttr::CreateImplicit(Context, 61 Alignment * 8)); 62 } 63 if (PackIncludeStack.empty()) 64 return; 65 // The #pragma pack affected a record in an included file, so Clang should 66 // warn when that pragma was written in a file that included the included 67 // file. 68 for (auto &PackedInclude : llvm::reverse(PackIncludeStack)) { 69 if (PackedInclude.CurrentPragmaLocation != PackStack.CurrentPragmaLocation) 70 break; 71 if (PackedInclude.HasNonDefaultValue) 72 PackedInclude.ShouldWarnOnInclude = true; 73 } 74 } 75 76 void Sema::AddMsStructLayoutForRecord(RecordDecl *RD) { 77 if (MSStructPragmaOn) 78 RD->addAttr(MSStructAttr::CreateImplicit(Context)); 79 80 // FIXME: We should merge AddAlignmentAttributesForRecord with 81 // AddMsStructLayoutForRecord into AddPragmaAttributesForRecord, which takes 82 // all active pragmas and applies them as attributes to class definitions. 83 if (VtorDispStack.CurrentValue != getLangOpts().getVtorDispMode()) 84 RD->addAttr(MSVtorDispAttr::CreateImplicit( 85 Context, unsigned(VtorDispStack.CurrentValue))); 86 } 87 88 template <typename Attribute> 89 static void addGslOwnerPointerAttributeIfNotExisting(ASTContext &Context, 90 CXXRecordDecl *Record) { 91 if (Record->hasAttr<OwnerAttr>() || Record->hasAttr<PointerAttr>()) 92 return; 93 94 for (Decl *Redecl : Record->redecls()) 95 Redecl->addAttr(Attribute::CreateImplicit(Context, /*DerefType=*/nullptr)); 96 } 97 98 void Sema::inferGslPointerAttribute(NamedDecl *ND, 99 CXXRecordDecl *UnderlyingRecord) { 100 if (!UnderlyingRecord) 101 return; 102 103 const auto *Parent = dyn_cast<CXXRecordDecl>(ND->getDeclContext()); 104 if (!Parent) 105 return; 106 107 static llvm::StringSet<> Containers{ 108 "array", 109 "basic_string", 110 "deque", 111 "forward_list", 112 "vector", 113 "list", 114 "map", 115 "multiset", 116 "multimap", 117 "priority_queue", 118 "queue", 119 "set", 120 "stack", 121 "unordered_set", 122 "unordered_map", 123 "unordered_multiset", 124 "unordered_multimap", 125 }; 126 127 static llvm::StringSet<> Iterators{"iterator", "const_iterator", 128 "reverse_iterator", 129 "const_reverse_iterator"}; 130 131 if (Parent->isInStdNamespace() && Iterators.count(ND->getName()) && 132 Containers.count(Parent->getName())) 133 addGslOwnerPointerAttributeIfNotExisting<PointerAttr>(Context, 134 UnderlyingRecord); 135 } 136 137 void Sema::inferGslPointerAttribute(TypedefNameDecl *TD) { 138 139 QualType Canonical = TD->getUnderlyingType().getCanonicalType(); 140 141 CXXRecordDecl *RD = Canonical->getAsCXXRecordDecl(); 142 if (!RD) { 143 if (auto *TST = 144 dyn_cast<TemplateSpecializationType>(Canonical.getTypePtr())) { 145 146 RD = dyn_cast_or_null<CXXRecordDecl>( 147 TST->getTemplateName().getAsTemplateDecl()->getTemplatedDecl()); 148 } 149 } 150 151 inferGslPointerAttribute(TD, RD); 152 } 153 154 void Sema::inferGslOwnerPointerAttribute(CXXRecordDecl *Record) { 155 static llvm::StringSet<> StdOwners{ 156 "any", 157 "array", 158 "basic_regex", 159 "basic_string", 160 "deque", 161 "forward_list", 162 "vector", 163 "list", 164 "map", 165 "multiset", 166 "multimap", 167 "optional", 168 "priority_queue", 169 "queue", 170 "set", 171 "stack", 172 "unique_ptr", 173 "unordered_set", 174 "unordered_map", 175 "unordered_multiset", 176 "unordered_multimap", 177 "variant", 178 }; 179 static llvm::StringSet<> StdPointers{ 180 "basic_string_view", 181 "reference_wrapper", 182 "regex_iterator", 183 }; 184 185 if (!Record->getIdentifier()) 186 return; 187 188 // Handle classes that directly appear in std namespace. 189 if (Record->isInStdNamespace()) { 190 if (Record->hasAttr<OwnerAttr>() || Record->hasAttr<PointerAttr>()) 191 return; 192 193 if (StdOwners.count(Record->getName())) 194 addGslOwnerPointerAttributeIfNotExisting<OwnerAttr>(Context, Record); 195 else if (StdPointers.count(Record->getName())) 196 addGslOwnerPointerAttributeIfNotExisting<PointerAttr>(Context, Record); 197 198 return; 199 } 200 201 // Handle nested classes that could be a gsl::Pointer. 202 inferGslPointerAttribute(Record, Record); 203 } 204 205 void Sema::ActOnPragmaOptionsAlign(PragmaOptionsAlignKind Kind, 206 SourceLocation PragmaLoc) { 207 PragmaMsStackAction Action = Sema::PSK_Reset; 208 unsigned Alignment = 0; 209 switch (Kind) { 210 // For all targets we support native and natural are the same. 211 // 212 // FIXME: This is not true on Darwin/PPC. 213 case POAK_Native: 214 case POAK_Power: 215 case POAK_Natural: 216 Action = Sema::PSK_Push_Set; 217 Alignment = 0; 218 break; 219 220 // Note that '#pragma options align=packed' is not equivalent to attribute 221 // packed, it has a different precedence relative to attribute aligned. 222 case POAK_Packed: 223 Action = Sema::PSK_Push_Set; 224 Alignment = 1; 225 break; 226 227 case POAK_Mac68k: 228 // Check if the target supports this. 229 if (!this->Context.getTargetInfo().hasAlignMac68kSupport()) { 230 Diag(PragmaLoc, diag::err_pragma_options_align_mac68k_target_unsupported); 231 return; 232 } 233 Action = Sema::PSK_Push_Set; 234 Alignment = Sema::kMac68kAlignmentSentinel; 235 break; 236 237 case POAK_Reset: 238 // Reset just pops the top of the stack, or resets the current alignment to 239 // default. 240 Action = Sema::PSK_Pop; 241 if (PackStack.Stack.empty()) { 242 if (PackStack.CurrentValue) { 243 Action = Sema::PSK_Reset; 244 } else { 245 Diag(PragmaLoc, diag::warn_pragma_options_align_reset_failed) 246 << "stack empty"; 247 return; 248 } 249 } 250 break; 251 } 252 253 PackStack.Act(PragmaLoc, Action, StringRef(), Alignment); 254 } 255 256 void Sema::ActOnPragmaClangSection(SourceLocation PragmaLoc, PragmaClangSectionAction Action, 257 PragmaClangSectionKind SecKind, StringRef SecName) { 258 PragmaClangSection *CSec; 259 int SectionFlags = ASTContext::PSF_Read; 260 switch (SecKind) { 261 case PragmaClangSectionKind::PCSK_BSS: 262 CSec = &PragmaClangBSSSection; 263 SectionFlags |= ASTContext::PSF_Write | ASTContext::PSF_ZeroInit; 264 break; 265 case PragmaClangSectionKind::PCSK_Data: 266 CSec = &PragmaClangDataSection; 267 SectionFlags |= ASTContext::PSF_Write; 268 break; 269 case PragmaClangSectionKind::PCSK_Rodata: 270 CSec = &PragmaClangRodataSection; 271 break; 272 case PragmaClangSectionKind::PCSK_Relro: 273 CSec = &PragmaClangRelroSection; 274 break; 275 case PragmaClangSectionKind::PCSK_Text: 276 CSec = &PragmaClangTextSection; 277 SectionFlags |= ASTContext::PSF_Execute; 278 break; 279 default: 280 llvm_unreachable("invalid clang section kind"); 281 } 282 283 if (Action == PragmaClangSectionAction::PCSA_Clear) { 284 CSec->Valid = false; 285 return; 286 } 287 288 if (UnifySection(SecName, SectionFlags, PragmaLoc)) 289 return; 290 291 CSec->Valid = true; 292 CSec->SectionName = std::string(SecName); 293 CSec->PragmaLocation = PragmaLoc; 294 } 295 296 void Sema::ActOnPragmaPack(SourceLocation PragmaLoc, PragmaMsStackAction Action, 297 StringRef SlotLabel, Expr *alignment) { 298 Expr *Alignment = static_cast<Expr *>(alignment); 299 300 // If specified then alignment must be a "small" power of two. 301 unsigned AlignmentVal = 0; 302 if (Alignment) { 303 llvm::APSInt Val; 304 305 // pack(0) is like pack(), which just works out since that is what 306 // we use 0 for in PackAttr. 307 if (Alignment->isTypeDependent() || 308 Alignment->isValueDependent() || 309 !Alignment->isIntegerConstantExpr(Val, Context) || 310 !(Val == 0 || Val.isPowerOf2()) || 311 Val.getZExtValue() > 16) { 312 Diag(PragmaLoc, diag::warn_pragma_pack_invalid_alignment); 313 return; // Ignore 314 } 315 316 AlignmentVal = (unsigned) Val.getZExtValue(); 317 } 318 if (Action == Sema::PSK_Show) { 319 // Show the current alignment, making sure to show the right value 320 // for the default. 321 // FIXME: This should come from the target. 322 AlignmentVal = PackStack.CurrentValue; 323 if (AlignmentVal == 0) 324 AlignmentVal = 8; 325 if (AlignmentVal == Sema::kMac68kAlignmentSentinel) 326 Diag(PragmaLoc, diag::warn_pragma_pack_show) << "mac68k"; 327 else 328 Diag(PragmaLoc, diag::warn_pragma_pack_show) << AlignmentVal; 329 } 330 // MSDN, C/C++ Preprocessor Reference > Pragma Directives > pack: 331 // "#pragma pack(pop, identifier, n) is undefined" 332 if (Action & Sema::PSK_Pop) { 333 if (Alignment && !SlotLabel.empty()) 334 Diag(PragmaLoc, diag::warn_pragma_pack_pop_identifier_and_alignment); 335 if (PackStack.Stack.empty()) 336 Diag(PragmaLoc, diag::warn_pragma_pop_failed) << "pack" << "stack empty"; 337 } 338 339 PackStack.Act(PragmaLoc, Action, SlotLabel, AlignmentVal); 340 } 341 342 void Sema::DiagnoseNonDefaultPragmaPack(PragmaPackDiagnoseKind Kind, 343 SourceLocation IncludeLoc) { 344 if (Kind == PragmaPackDiagnoseKind::NonDefaultStateAtInclude) { 345 SourceLocation PrevLocation = PackStack.CurrentPragmaLocation; 346 // Warn about non-default alignment at #includes (without redundant 347 // warnings for the same directive in nested includes). 348 // The warning is delayed until the end of the file to avoid warnings 349 // for files that don't have any records that are affected by the modified 350 // alignment. 351 bool HasNonDefaultValue = 352 PackStack.hasValue() && 353 (PackIncludeStack.empty() || 354 PackIncludeStack.back().CurrentPragmaLocation != PrevLocation); 355 PackIncludeStack.push_back( 356 {PackStack.CurrentValue, 357 PackStack.hasValue() ? PrevLocation : SourceLocation(), 358 HasNonDefaultValue, /*ShouldWarnOnInclude*/ false}); 359 return; 360 } 361 362 assert(Kind == PragmaPackDiagnoseKind::ChangedStateAtExit && "invalid kind"); 363 PackIncludeState PrevPackState = PackIncludeStack.pop_back_val(); 364 if (PrevPackState.ShouldWarnOnInclude) { 365 // Emit the delayed non-default alignment at #include warning. 366 Diag(IncludeLoc, diag::warn_pragma_pack_non_default_at_include); 367 Diag(PrevPackState.CurrentPragmaLocation, diag::note_pragma_pack_here); 368 } 369 // Warn about modified alignment after #includes. 370 if (PrevPackState.CurrentValue != PackStack.CurrentValue) { 371 Diag(IncludeLoc, diag::warn_pragma_pack_modified_after_include); 372 Diag(PackStack.CurrentPragmaLocation, diag::note_pragma_pack_here); 373 } 374 } 375 376 void Sema::DiagnoseUnterminatedPragmaPack() { 377 if (PackStack.Stack.empty()) 378 return; 379 bool IsInnermost = true; 380 for (const auto &StackSlot : llvm::reverse(PackStack.Stack)) { 381 Diag(StackSlot.PragmaPushLocation, diag::warn_pragma_pack_no_pop_eof); 382 // The user might have already reset the alignment, so suggest replacing 383 // the reset with a pop. 384 if (IsInnermost && PackStack.CurrentValue == PackStack.DefaultValue) { 385 DiagnosticBuilder DB = Diag(PackStack.CurrentPragmaLocation, 386 diag::note_pragma_pack_pop_instead_reset); 387 SourceLocation FixItLoc = Lexer::findLocationAfterToken( 388 PackStack.CurrentPragmaLocation, tok::l_paren, SourceMgr, LangOpts, 389 /*SkipTrailing=*/false); 390 if (FixItLoc.isValid()) 391 DB << FixItHint::CreateInsertion(FixItLoc, "pop"); 392 } 393 IsInnermost = false; 394 } 395 } 396 397 void Sema::ActOnPragmaMSStruct(PragmaMSStructKind Kind) { 398 MSStructPragmaOn = (Kind == PMSST_ON); 399 } 400 401 void Sema::ActOnPragmaMSComment(SourceLocation CommentLoc, 402 PragmaMSCommentKind Kind, StringRef Arg) { 403 auto *PCD = PragmaCommentDecl::Create( 404 Context, Context.getTranslationUnitDecl(), CommentLoc, Kind, Arg); 405 Context.getTranslationUnitDecl()->addDecl(PCD); 406 Consumer.HandleTopLevelDecl(DeclGroupRef(PCD)); 407 } 408 409 void Sema::ActOnPragmaDetectMismatch(SourceLocation Loc, StringRef Name, 410 StringRef Value) { 411 auto *PDMD = PragmaDetectMismatchDecl::Create( 412 Context, Context.getTranslationUnitDecl(), Loc, Name, Value); 413 Context.getTranslationUnitDecl()->addDecl(PDMD); 414 Consumer.HandleTopLevelDecl(DeclGroupRef(PDMD)); 415 } 416 417 void Sema::ActOnPragmaFloatControl(SourceLocation Loc, 418 PragmaMsStackAction Action, 419 PragmaFloatControlKind Value) { 420 unsigned NewValue = FpPragmaStack.hasValue() 421 ? FpPragmaStack.CurrentValue 422 : CurFPFeatureOverrides().getAsOpaqueInt(); 423 FPOptionsOverride NewFPFeatures(NewValue); 424 if ((Action == PSK_Push_Set || Action == PSK_Push || Action == PSK_Pop) && 425 !(CurContext->isTranslationUnit()) && !CurContext->isNamespace()) { 426 // Push and pop can only occur at file or namespace scope. 427 Diag(Loc, diag::err_pragma_fc_pp_scope); 428 return; 429 } 430 switch (Value) { 431 default: 432 llvm_unreachable("invalid pragma float_control kind"); 433 case PFC_Precise: 434 NewFPFeatures.setFPPreciseEnabled(true); 435 NewValue = NewFPFeatures.getAsOpaqueInt(); 436 FpPragmaStack.Act(Loc, Action, StringRef(), NewValue); 437 break; 438 case PFC_NoPrecise: 439 if (CurFPFeatures.getFPExceptionMode() == LangOptions::FPE_Strict) 440 Diag(Loc, diag::err_pragma_fc_noprecise_requires_noexcept); 441 else if (CurFPFeatures.getAllowFEnvAccess()) 442 Diag(Loc, diag::err_pragma_fc_noprecise_requires_nofenv); 443 else 444 NewFPFeatures.setFPPreciseEnabled(false); 445 NewValue = NewFPFeatures.getAsOpaqueInt(); 446 FpPragmaStack.Act(Loc, Action, StringRef(), NewValue); 447 break; 448 case PFC_Except: 449 if (!isPreciseFPEnabled()) 450 Diag(Loc, diag::err_pragma_fc_except_requires_precise); 451 else 452 NewFPFeatures.setFPExceptionModeOverride(LangOptions::FPE_Strict); 453 NewValue = NewFPFeatures.getAsOpaqueInt(); 454 FpPragmaStack.Act(Loc, Action, StringRef(), NewValue); 455 break; 456 case PFC_NoExcept: 457 NewFPFeatures.setFPExceptionModeOverride(LangOptions::FPE_Ignore); 458 NewValue = NewFPFeatures.getAsOpaqueInt(); 459 FpPragmaStack.Act(Loc, Action, StringRef(), NewValue); 460 break; 461 case PFC_Push: 462 FpPragmaStack.Act(Loc, Sema::PSK_Push_Set, StringRef(), 463 NewFPFeatures.getAsOpaqueInt()); 464 break; 465 case PFC_Pop: 466 if (FpPragmaStack.Stack.empty()) { 467 Diag(Loc, diag::warn_pragma_pop_failed) << "float_control" 468 << "stack empty"; 469 return; 470 } 471 FpPragmaStack.Act(Loc, Action, StringRef(), NewFPFeatures.getAsOpaqueInt()); 472 NewValue = FpPragmaStack.CurrentValue; 473 break; 474 } 475 FPOptionsOverride NewOverrides; 476 if (NewValue != FpPragmaStack.DefaultValue) 477 NewOverrides.getFromOpaqueInt(NewValue); 478 CurFPFeatures = NewOverrides.applyOverrides(getLangOpts()); 479 } 480 481 void Sema::ActOnPragmaMSPointersToMembers( 482 LangOptions::PragmaMSPointersToMembersKind RepresentationMethod, 483 SourceLocation PragmaLoc) { 484 MSPointerToMemberRepresentationMethod = RepresentationMethod; 485 ImplicitMSInheritanceAttrLoc = PragmaLoc; 486 } 487 488 void Sema::ActOnPragmaMSVtorDisp(PragmaMsStackAction Action, 489 SourceLocation PragmaLoc, 490 MSVtorDispMode Mode) { 491 if (Action & PSK_Pop && VtorDispStack.Stack.empty()) 492 Diag(PragmaLoc, diag::warn_pragma_pop_failed) << "vtordisp" 493 << "stack empty"; 494 VtorDispStack.Act(PragmaLoc, Action, StringRef(), Mode); 495 } 496 497 bool Sema::UnifySection(StringRef SectionName, 498 int SectionFlags, 499 DeclaratorDecl *Decl) { 500 SourceLocation PragmaLocation; 501 if (auto A = Decl->getAttr<SectionAttr>()) 502 if (A->isImplicit()) 503 PragmaLocation = A->getLocation(); 504 auto SectionIt = Context.SectionInfos.find(SectionName); 505 if (SectionIt == Context.SectionInfos.end()) { 506 Context.SectionInfos[SectionName] = 507 ASTContext::SectionInfo(Decl, PragmaLocation, SectionFlags); 508 return false; 509 } 510 // A pre-declared section takes precedence w/o diagnostic. 511 const auto &Section = SectionIt->second; 512 if (Section.SectionFlags == SectionFlags || 513 ((SectionFlags & ASTContext::PSF_Implicit) && 514 !(Section.SectionFlags & ASTContext::PSF_Implicit))) 515 return false; 516 Diag(Decl->getLocation(), diag::err_section_conflict) << Decl << Section; 517 if (Section.Decl) 518 Diag(Section.Decl->getLocation(), diag::note_declared_at) 519 << Section.Decl->getName(); 520 if (PragmaLocation.isValid()) 521 Diag(PragmaLocation, diag::note_pragma_entered_here); 522 if (Section.PragmaSectionLocation.isValid()) 523 Diag(Section.PragmaSectionLocation, diag::note_pragma_entered_here); 524 return true; 525 } 526 527 bool Sema::UnifySection(StringRef SectionName, 528 int SectionFlags, 529 SourceLocation PragmaSectionLocation) { 530 auto SectionIt = Context.SectionInfos.find(SectionName); 531 if (SectionIt != Context.SectionInfos.end()) { 532 const auto &Section = SectionIt->second; 533 if (Section.SectionFlags == SectionFlags) 534 return false; 535 if (!(Section.SectionFlags & ASTContext::PSF_Implicit)) { 536 Diag(PragmaSectionLocation, diag::err_section_conflict) 537 << "this" << Section; 538 if (Section.Decl) 539 Diag(Section.Decl->getLocation(), diag::note_declared_at) 540 << Section.Decl->getName(); 541 if (Section.PragmaSectionLocation.isValid()) 542 Diag(Section.PragmaSectionLocation, diag::note_pragma_entered_here); 543 return true; 544 } 545 } 546 Context.SectionInfos[SectionName] = 547 ASTContext::SectionInfo(nullptr, PragmaSectionLocation, SectionFlags); 548 return false; 549 } 550 551 /// Called on well formed \#pragma bss_seg(). 552 void Sema::ActOnPragmaMSSeg(SourceLocation PragmaLocation, 553 PragmaMsStackAction Action, 554 llvm::StringRef StackSlotLabel, 555 StringLiteral *SegmentName, 556 llvm::StringRef PragmaName) { 557 PragmaStack<StringLiteral *> *Stack = 558 llvm::StringSwitch<PragmaStack<StringLiteral *> *>(PragmaName) 559 .Case("data_seg", &DataSegStack) 560 .Case("bss_seg", &BSSSegStack) 561 .Case("const_seg", &ConstSegStack) 562 .Case("code_seg", &CodeSegStack); 563 if (Action & PSK_Pop && Stack->Stack.empty()) 564 Diag(PragmaLocation, diag::warn_pragma_pop_failed) << PragmaName 565 << "stack empty"; 566 if (SegmentName) { 567 if (!checkSectionName(SegmentName->getBeginLoc(), SegmentName->getString())) 568 return; 569 570 if (SegmentName->getString() == ".drectve" && 571 Context.getTargetInfo().getCXXABI().isMicrosoft()) 572 Diag(PragmaLocation, diag::warn_attribute_section_drectve) << PragmaName; 573 } 574 575 Stack->Act(PragmaLocation, Action, StackSlotLabel, SegmentName); 576 } 577 578 /// Called on well formed \#pragma bss_seg(). 579 void Sema::ActOnPragmaMSSection(SourceLocation PragmaLocation, 580 int SectionFlags, StringLiteral *SegmentName) { 581 UnifySection(SegmentName->getString(), SectionFlags, PragmaLocation); 582 } 583 584 void Sema::ActOnPragmaMSInitSeg(SourceLocation PragmaLocation, 585 StringLiteral *SegmentName) { 586 // There's no stack to maintain, so we just have a current section. When we 587 // see the default section, reset our current section back to null so we stop 588 // tacking on unnecessary attributes. 589 CurInitSeg = SegmentName->getString() == ".CRT$XCU" ? nullptr : SegmentName; 590 CurInitSegLoc = PragmaLocation; 591 } 592 593 void Sema::ActOnPragmaUnused(const Token &IdTok, Scope *curScope, 594 SourceLocation PragmaLoc) { 595 596 IdentifierInfo *Name = IdTok.getIdentifierInfo(); 597 LookupResult Lookup(*this, Name, IdTok.getLocation(), LookupOrdinaryName); 598 LookupParsedName(Lookup, curScope, nullptr, true); 599 600 if (Lookup.empty()) { 601 Diag(PragmaLoc, diag::warn_pragma_unused_undeclared_var) 602 << Name << SourceRange(IdTok.getLocation()); 603 return; 604 } 605 606 VarDecl *VD = Lookup.getAsSingle<VarDecl>(); 607 if (!VD) { 608 Diag(PragmaLoc, diag::warn_pragma_unused_expected_var_arg) 609 << Name << SourceRange(IdTok.getLocation()); 610 return; 611 } 612 613 // Warn if this was used before being marked unused. 614 if (VD->isUsed()) 615 Diag(PragmaLoc, diag::warn_used_but_marked_unused) << Name; 616 617 VD->addAttr(UnusedAttr::CreateImplicit(Context, IdTok.getLocation(), 618 AttributeCommonInfo::AS_Pragma, 619 UnusedAttr::GNU_unused)); 620 } 621 622 void Sema::AddCFAuditedAttribute(Decl *D) { 623 IdentifierInfo *Ident; 624 SourceLocation Loc; 625 std::tie(Ident, Loc) = PP.getPragmaARCCFCodeAuditedInfo(); 626 if (!Loc.isValid()) return; 627 628 // Don't add a redundant or conflicting attribute. 629 if (D->hasAttr<CFAuditedTransferAttr>() || 630 D->hasAttr<CFUnknownTransferAttr>()) 631 return; 632 633 AttributeCommonInfo Info(Ident, SourceRange(Loc), 634 AttributeCommonInfo::AS_Pragma); 635 D->addAttr(CFAuditedTransferAttr::CreateImplicit(Context, Info)); 636 } 637 638 namespace { 639 640 Optional<attr::SubjectMatchRule> 641 getParentAttrMatcherRule(attr::SubjectMatchRule Rule) { 642 using namespace attr; 643 switch (Rule) { 644 default: 645 return None; 646 #define ATTR_MATCH_RULE(Value, Spelling, IsAbstract) 647 #define ATTR_MATCH_SUB_RULE(Value, Spelling, IsAbstract, Parent, IsNegated) \ 648 case Value: \ 649 return Parent; 650 #include "clang/Basic/AttrSubMatchRulesList.inc" 651 } 652 } 653 654 bool isNegatedAttrMatcherSubRule(attr::SubjectMatchRule Rule) { 655 using namespace attr; 656 switch (Rule) { 657 default: 658 return false; 659 #define ATTR_MATCH_RULE(Value, Spelling, IsAbstract) 660 #define ATTR_MATCH_SUB_RULE(Value, Spelling, IsAbstract, Parent, IsNegated) \ 661 case Value: \ 662 return IsNegated; 663 #include "clang/Basic/AttrSubMatchRulesList.inc" 664 } 665 } 666 667 CharSourceRange replacementRangeForListElement(const Sema &S, 668 SourceRange Range) { 669 // Make sure that the ',' is removed as well. 670 SourceLocation AfterCommaLoc = Lexer::findLocationAfterToken( 671 Range.getEnd(), tok::comma, S.getSourceManager(), S.getLangOpts(), 672 /*SkipTrailingWhitespaceAndNewLine=*/false); 673 if (AfterCommaLoc.isValid()) 674 return CharSourceRange::getCharRange(Range.getBegin(), AfterCommaLoc); 675 else 676 return CharSourceRange::getTokenRange(Range); 677 } 678 679 std::string 680 attrMatcherRuleListToString(ArrayRef<attr::SubjectMatchRule> Rules) { 681 std::string Result; 682 llvm::raw_string_ostream OS(Result); 683 for (const auto &I : llvm::enumerate(Rules)) { 684 if (I.index()) 685 OS << (I.index() == Rules.size() - 1 ? ", and " : ", "); 686 OS << "'" << attr::getSubjectMatchRuleSpelling(I.value()) << "'"; 687 } 688 return OS.str(); 689 } 690 691 } // end anonymous namespace 692 693 void Sema::ActOnPragmaAttributeAttribute( 694 ParsedAttr &Attribute, SourceLocation PragmaLoc, 695 attr::ParsedSubjectMatchRuleSet Rules) { 696 Attribute.setIsPragmaClangAttribute(); 697 SmallVector<attr::SubjectMatchRule, 4> SubjectMatchRules; 698 // Gather the subject match rules that are supported by the attribute. 699 SmallVector<std::pair<attr::SubjectMatchRule, bool>, 4> 700 StrictSubjectMatchRuleSet; 701 Attribute.getMatchRules(LangOpts, StrictSubjectMatchRuleSet); 702 703 // Figure out which subject matching rules are valid. 704 if (StrictSubjectMatchRuleSet.empty()) { 705 // Check for contradicting match rules. Contradicting match rules are 706 // either: 707 // - a top-level rule and one of its sub-rules. E.g. variable and 708 // variable(is_parameter). 709 // - a sub-rule and a sibling that's negated. E.g. 710 // variable(is_thread_local) and variable(unless(is_parameter)) 711 llvm::SmallDenseMap<int, std::pair<int, SourceRange>, 2> 712 RulesToFirstSpecifiedNegatedSubRule; 713 for (const auto &Rule : Rules) { 714 attr::SubjectMatchRule MatchRule = attr::SubjectMatchRule(Rule.first); 715 Optional<attr::SubjectMatchRule> ParentRule = 716 getParentAttrMatcherRule(MatchRule); 717 if (!ParentRule) 718 continue; 719 auto It = Rules.find(*ParentRule); 720 if (It != Rules.end()) { 721 // A sub-rule contradicts a parent rule. 722 Diag(Rule.second.getBegin(), 723 diag::err_pragma_attribute_matcher_subrule_contradicts_rule) 724 << attr::getSubjectMatchRuleSpelling(MatchRule) 725 << attr::getSubjectMatchRuleSpelling(*ParentRule) << It->second 726 << FixItHint::CreateRemoval( 727 replacementRangeForListElement(*this, Rule.second)); 728 // Keep going without removing this rule as it won't change the set of 729 // declarations that receive the attribute. 730 continue; 731 } 732 if (isNegatedAttrMatcherSubRule(MatchRule)) 733 RulesToFirstSpecifiedNegatedSubRule.insert( 734 std::make_pair(*ParentRule, Rule)); 735 } 736 bool IgnoreNegatedSubRules = false; 737 for (const auto &Rule : Rules) { 738 attr::SubjectMatchRule MatchRule = attr::SubjectMatchRule(Rule.first); 739 Optional<attr::SubjectMatchRule> ParentRule = 740 getParentAttrMatcherRule(MatchRule); 741 if (!ParentRule) 742 continue; 743 auto It = RulesToFirstSpecifiedNegatedSubRule.find(*ParentRule); 744 if (It != RulesToFirstSpecifiedNegatedSubRule.end() && 745 It->second != Rule) { 746 // Negated sub-rule contradicts another sub-rule. 747 Diag( 748 It->second.second.getBegin(), 749 diag:: 750 err_pragma_attribute_matcher_negated_subrule_contradicts_subrule) 751 << attr::getSubjectMatchRuleSpelling( 752 attr::SubjectMatchRule(It->second.first)) 753 << attr::getSubjectMatchRuleSpelling(MatchRule) << Rule.second 754 << FixItHint::CreateRemoval( 755 replacementRangeForListElement(*this, It->second.second)); 756 // Keep going but ignore all of the negated sub-rules. 757 IgnoreNegatedSubRules = true; 758 RulesToFirstSpecifiedNegatedSubRule.erase(It); 759 } 760 } 761 762 if (!IgnoreNegatedSubRules) { 763 for (const auto &Rule : Rules) 764 SubjectMatchRules.push_back(attr::SubjectMatchRule(Rule.first)); 765 } else { 766 for (const auto &Rule : Rules) { 767 if (!isNegatedAttrMatcherSubRule(attr::SubjectMatchRule(Rule.first))) 768 SubjectMatchRules.push_back(attr::SubjectMatchRule(Rule.first)); 769 } 770 } 771 Rules.clear(); 772 } else { 773 for (const auto &Rule : StrictSubjectMatchRuleSet) { 774 if (Rules.erase(Rule.first)) { 775 // Add the rule to the set of attribute receivers only if it's supported 776 // in the current language mode. 777 if (Rule.second) 778 SubjectMatchRules.push_back(Rule.first); 779 } 780 } 781 } 782 783 if (!Rules.empty()) { 784 auto Diagnostic = 785 Diag(PragmaLoc, diag::err_pragma_attribute_invalid_matchers) 786 << Attribute; 787 SmallVector<attr::SubjectMatchRule, 2> ExtraRules; 788 for (const auto &Rule : Rules) { 789 ExtraRules.push_back(attr::SubjectMatchRule(Rule.first)); 790 Diagnostic << FixItHint::CreateRemoval( 791 replacementRangeForListElement(*this, Rule.second)); 792 } 793 Diagnostic << attrMatcherRuleListToString(ExtraRules); 794 } 795 796 if (PragmaAttributeStack.empty()) { 797 Diag(PragmaLoc, diag::err_pragma_attr_attr_no_push); 798 return; 799 } 800 801 PragmaAttributeStack.back().Entries.push_back( 802 {PragmaLoc, &Attribute, std::move(SubjectMatchRules), /*IsUsed=*/false}); 803 } 804 805 void Sema::ActOnPragmaAttributeEmptyPush(SourceLocation PragmaLoc, 806 const IdentifierInfo *Namespace) { 807 PragmaAttributeStack.emplace_back(); 808 PragmaAttributeStack.back().Loc = PragmaLoc; 809 PragmaAttributeStack.back().Namespace = Namespace; 810 } 811 812 void Sema::ActOnPragmaAttributePop(SourceLocation PragmaLoc, 813 const IdentifierInfo *Namespace) { 814 if (PragmaAttributeStack.empty()) { 815 Diag(PragmaLoc, diag::err_pragma_attribute_stack_mismatch) << 1; 816 return; 817 } 818 819 // Dig back through the stack trying to find the most recently pushed group 820 // that in Namespace. Note that this works fine if no namespace is present, 821 // think of push/pops without namespaces as having an implicit "nullptr" 822 // namespace. 823 for (size_t Index = PragmaAttributeStack.size(); Index;) { 824 --Index; 825 if (PragmaAttributeStack[Index].Namespace == Namespace) { 826 for (const PragmaAttributeEntry &Entry : 827 PragmaAttributeStack[Index].Entries) { 828 if (!Entry.IsUsed) { 829 assert(Entry.Attribute && "Expected an attribute"); 830 Diag(Entry.Attribute->getLoc(), diag::warn_pragma_attribute_unused) 831 << *Entry.Attribute; 832 Diag(PragmaLoc, diag::note_pragma_attribute_region_ends_here); 833 } 834 } 835 PragmaAttributeStack.erase(PragmaAttributeStack.begin() + Index); 836 return; 837 } 838 } 839 840 if (Namespace) 841 Diag(PragmaLoc, diag::err_pragma_attribute_stack_mismatch) 842 << 0 << Namespace->getName(); 843 else 844 Diag(PragmaLoc, diag::err_pragma_attribute_stack_mismatch) << 1; 845 } 846 847 void Sema::AddPragmaAttributes(Scope *S, Decl *D) { 848 if (PragmaAttributeStack.empty()) 849 return; 850 for (auto &Group : PragmaAttributeStack) { 851 for (auto &Entry : Group.Entries) { 852 ParsedAttr *Attribute = Entry.Attribute; 853 assert(Attribute && "Expected an attribute"); 854 assert(Attribute->isPragmaClangAttribute() && 855 "expected #pragma clang attribute"); 856 857 // Ensure that the attribute can be applied to the given declaration. 858 bool Applies = false; 859 for (const auto &Rule : Entry.MatchRules) { 860 if (Attribute->appliesToDecl(D, Rule)) { 861 Applies = true; 862 break; 863 } 864 } 865 if (!Applies) 866 continue; 867 Entry.IsUsed = true; 868 PragmaAttributeCurrentTargetDecl = D; 869 ParsedAttributesView Attrs; 870 Attrs.addAtEnd(Attribute); 871 ProcessDeclAttributeList(S, D, Attrs); 872 PragmaAttributeCurrentTargetDecl = nullptr; 873 } 874 } 875 } 876 877 void Sema::PrintPragmaAttributeInstantiationPoint() { 878 assert(PragmaAttributeCurrentTargetDecl && "Expected an active declaration"); 879 Diags.Report(PragmaAttributeCurrentTargetDecl->getBeginLoc(), 880 diag::note_pragma_attribute_applied_decl_here); 881 } 882 883 void Sema::DiagnoseUnterminatedPragmaAttribute() { 884 if (PragmaAttributeStack.empty()) 885 return; 886 Diag(PragmaAttributeStack.back().Loc, diag::err_pragma_attribute_no_pop_eof); 887 } 888 889 void Sema::ActOnPragmaOptimize(bool On, SourceLocation PragmaLoc) { 890 if(On) 891 OptimizeOffPragmaLocation = SourceLocation(); 892 else 893 OptimizeOffPragmaLocation = PragmaLoc; 894 } 895 896 void Sema::AddRangeBasedOptnone(FunctionDecl *FD) { 897 // In the future, check other pragmas if they're implemented (e.g. pragma 898 // optimize 0 will probably map to this functionality too). 899 if(OptimizeOffPragmaLocation.isValid()) 900 AddOptnoneAttributeIfNoConflicts(FD, OptimizeOffPragmaLocation); 901 } 902 903 void Sema::AddOptnoneAttributeIfNoConflicts(FunctionDecl *FD, 904 SourceLocation Loc) { 905 // Don't add a conflicting attribute. No diagnostic is needed. 906 if (FD->hasAttr<MinSizeAttr>() || FD->hasAttr<AlwaysInlineAttr>()) 907 return; 908 909 // Add attributes only if required. Optnone requires noinline as well, but if 910 // either is already present then don't bother adding them. 911 if (!FD->hasAttr<OptimizeNoneAttr>()) 912 FD->addAttr(OptimizeNoneAttr::CreateImplicit(Context, Loc)); 913 if (!FD->hasAttr<NoInlineAttr>()) 914 FD->addAttr(NoInlineAttr::CreateImplicit(Context, Loc)); 915 } 916 917 typedef std::vector<std::pair<unsigned, SourceLocation> > VisStack; 918 enum : unsigned { NoVisibility = ~0U }; 919 920 void Sema::AddPushedVisibilityAttribute(Decl *D) { 921 if (!VisContext) 922 return; 923 924 NamedDecl *ND = dyn_cast<NamedDecl>(D); 925 if (ND && ND->getExplicitVisibility(NamedDecl::VisibilityForValue)) 926 return; 927 928 VisStack *Stack = static_cast<VisStack*>(VisContext); 929 unsigned rawType = Stack->back().first; 930 if (rawType == NoVisibility) return; 931 932 VisibilityAttr::VisibilityType type 933 = (VisibilityAttr::VisibilityType) rawType; 934 SourceLocation loc = Stack->back().second; 935 936 D->addAttr(VisibilityAttr::CreateImplicit(Context, type, loc)); 937 } 938 939 /// FreeVisContext - Deallocate and null out VisContext. 940 void Sema::FreeVisContext() { 941 delete static_cast<VisStack*>(VisContext); 942 VisContext = nullptr; 943 } 944 945 static void PushPragmaVisibility(Sema &S, unsigned type, SourceLocation loc) { 946 // Put visibility on stack. 947 if (!S.VisContext) 948 S.VisContext = new VisStack; 949 950 VisStack *Stack = static_cast<VisStack*>(S.VisContext); 951 Stack->push_back(std::make_pair(type, loc)); 952 } 953 954 void Sema::ActOnPragmaVisibility(const IdentifierInfo* VisType, 955 SourceLocation PragmaLoc) { 956 if (VisType) { 957 // Compute visibility to use. 958 VisibilityAttr::VisibilityType T; 959 if (!VisibilityAttr::ConvertStrToVisibilityType(VisType->getName(), T)) { 960 Diag(PragmaLoc, diag::warn_attribute_unknown_visibility) << VisType; 961 return; 962 } 963 PushPragmaVisibility(*this, T, PragmaLoc); 964 } else { 965 PopPragmaVisibility(false, PragmaLoc); 966 } 967 } 968 969 void Sema::ActOnPragmaFPContract(SourceLocation Loc, 970 LangOptions::FPModeKind FPC) { 971 unsigned NewValue = FpPragmaStack.hasValue() 972 ? FpPragmaStack.CurrentValue 973 : CurFPFeatureOverrides().getAsOpaqueInt(); 974 FPOptionsOverride NewFPFeatures(NewValue); 975 switch (FPC) { 976 case LangOptions::FPM_On: 977 NewFPFeatures.setAllowFPContractWithinStatement(); 978 break; 979 case LangOptions::FPM_Fast: 980 NewFPFeatures.setAllowFPContractAcrossStatement(); 981 break; 982 case LangOptions::FPM_Off: 983 NewFPFeatures.setDisallowFPContract(); 984 break; 985 } 986 CurFPFeatures = NewFPFeatures.applyOverrides(getLangOpts()); 987 FpPragmaStack.Act(Loc, Sema::PSK_Set, StringRef(), 988 NewFPFeatures.getAsOpaqueInt()); 989 } 990 991 void Sema::ActOnPragmaFPReassociate(SourceLocation Loc, bool IsEnabled) { 992 unsigned NewValue = FpPragmaStack.hasValue() 993 ? FpPragmaStack.CurrentValue 994 : CurFPFeatureOverrides().getAsOpaqueInt(); 995 FPOptionsOverride NewFPFeatures(NewValue); 996 NewFPFeatures.setAllowFPReassociateOverride(IsEnabled); 997 NewValue = NewFPFeatures.getAsOpaqueInt(); 998 FpPragmaStack.Act(Loc, PSK_Set, StringRef(), NewValue); 999 FPOptionsOverride NewOverrides(NewValue); 1000 CurFPFeatures = NewOverrides.applyOverrides(getLangOpts()); 1001 } 1002 1003 void Sema::setRoundingMode(SourceLocation Loc, llvm::RoundingMode FPR) { 1004 unsigned NewValue = FpPragmaStack.hasValue() 1005 ? FpPragmaStack.CurrentValue 1006 : CurFPFeatureOverrides().getAsOpaqueInt(); 1007 FPOptionsOverride NewFPFeatures(NewValue); 1008 NewFPFeatures.setRoundingModeOverride(FPR); 1009 NewValue = NewFPFeatures.getAsOpaqueInt(); 1010 FpPragmaStack.Act(Loc, PSK_Set, StringRef(), NewValue); 1011 FPOptionsOverride NewOverrides(NewValue); 1012 CurFPFeatures = NewOverrides.applyOverrides(getLangOpts()); 1013 } 1014 1015 void Sema::setExceptionMode(SourceLocation Loc, 1016 LangOptions::FPExceptionModeKind FPE) { 1017 unsigned NewValue = FpPragmaStack.hasValue() 1018 ? FpPragmaStack.CurrentValue 1019 : CurFPFeatureOverrides().getAsOpaqueInt(); 1020 FPOptionsOverride NewFPFeatures(NewValue); 1021 NewFPFeatures.setFPExceptionModeOverride(FPE); 1022 NewValue = NewFPFeatures.getAsOpaqueInt(); 1023 FpPragmaStack.Act(Loc, PSK_Set, StringRef(), NewValue); 1024 FPOptionsOverride NewOverrides(NewValue); 1025 CurFPFeatures = NewOverrides.applyOverrides(getLangOpts()); 1026 } 1027 1028 void Sema::ActOnPragmaFEnvAccess(SourceLocation Loc, bool IsEnabled) { 1029 unsigned NewValue = FpPragmaStack.hasValue() 1030 ? FpPragmaStack.CurrentValue 1031 : CurFPFeatureOverrides().getAsOpaqueInt(); 1032 FPOptionsOverride NewFPFeatures(NewValue); 1033 if (IsEnabled) { 1034 // Verify Microsoft restriction: 1035 // You can't enable fenv_access unless precise semantics are enabled. 1036 // Precise semantics can be enabled either by the float_control 1037 // pragma, or by using the /fp:precise or /fp:strict compiler options 1038 if (!isPreciseFPEnabled()) 1039 Diag(Loc, diag::err_pragma_fenv_requires_precise); 1040 NewFPFeatures.setAllowFEnvAccessOverride(true); 1041 } else 1042 NewFPFeatures.setAllowFEnvAccessOverride(false); 1043 NewValue = NewFPFeatures.getAsOpaqueInt(); 1044 FpPragmaStack.Act(Loc, PSK_Set, StringRef(), NewValue); 1045 FPOptionsOverride NewOverrides(NewValue); 1046 CurFPFeatures = NewOverrides.applyOverrides(getLangOpts()); 1047 } 1048 1049 void Sema::PushNamespaceVisibilityAttr(const VisibilityAttr *Attr, 1050 SourceLocation Loc) { 1051 // Visibility calculations will consider the namespace's visibility. 1052 // Here we just want to note that we're in a visibility context 1053 // which overrides any enclosing #pragma context, but doesn't itself 1054 // contribute visibility. 1055 PushPragmaVisibility(*this, NoVisibility, Loc); 1056 } 1057 1058 void Sema::PopPragmaVisibility(bool IsNamespaceEnd, SourceLocation EndLoc) { 1059 if (!VisContext) { 1060 Diag(EndLoc, diag::err_pragma_pop_visibility_mismatch); 1061 return; 1062 } 1063 1064 // Pop visibility from stack 1065 VisStack *Stack = static_cast<VisStack*>(VisContext); 1066 1067 const std::pair<unsigned, SourceLocation> *Back = &Stack->back(); 1068 bool StartsWithPragma = Back->first != NoVisibility; 1069 if (StartsWithPragma && IsNamespaceEnd) { 1070 Diag(Back->second, diag::err_pragma_push_visibility_mismatch); 1071 Diag(EndLoc, diag::note_surrounding_namespace_ends_here); 1072 1073 // For better error recovery, eat all pushes inside the namespace. 1074 do { 1075 Stack->pop_back(); 1076 Back = &Stack->back(); 1077 StartsWithPragma = Back->first != NoVisibility; 1078 } while (StartsWithPragma); 1079 } else if (!StartsWithPragma && !IsNamespaceEnd) { 1080 Diag(EndLoc, diag::err_pragma_pop_visibility_mismatch); 1081 Diag(Back->second, diag::note_surrounding_namespace_starts_here); 1082 return; 1083 } 1084 1085 Stack->pop_back(); 1086 // To simplify the implementation, never keep around an empty stack. 1087 if (Stack->empty()) 1088 FreeVisContext(); 1089 } 1090