diff options
Diffstat (limited to 'clang/lib/CodeGen/CGVTables.cpp')
-rw-r--r-- | clang/lib/CodeGen/CGVTables.cpp | 57 |
1 files changed, 26 insertions, 31 deletions
diff --git a/clang/lib/CodeGen/CGVTables.cpp b/clang/lib/CodeGen/CGVTables.cpp index 478164e273b..f139e2c8504 100644 --- a/clang/lib/CodeGen/CGVTables.cpp +++ b/clang/lib/CodeGen/CGVTables.cpp @@ -902,43 +902,34 @@ void CodeGenModule::EmitDeferredVTables() { DeferredVTables.clear(); } -bool CodeGenModule::HasHiddenLTOVisibility(const CXXRecordDecl *RD) { - LinkageInfo LV = RD->getLinkageAndVisibility(); - if (!isExternallyVisible(LV.getLinkage())) - return true; - - if (RD->hasAttr<LTOVisibilityPublicAttr>() || RD->hasAttr<UuidAttr>()) - return false; +bool CodeGenModule::NeedVTableBitSets() { + return getCodeGenOpts().WholeProgramVTables || + getLangOpts().Sanitize.has(SanitizerKind::CFIVCall) || + getLangOpts().Sanitize.has(SanitizerKind::CFINVCall) || + getLangOpts().Sanitize.has(SanitizerKind::CFIDerivedCast) || + getLangOpts().Sanitize.has(SanitizerKind::CFIUnrelatedCast); +} - if (getTriple().isOSBinFormatCOFF()) { - if (RD->hasAttr<DLLExportAttr>() || RD->hasAttr<DLLImportAttr>()) - return false; - } else { - if (LV.getVisibility() != HiddenVisibility) - return false; - } +bool CodeGenModule::IsBitSetBlacklistedRecord(const CXXRecordDecl *RD) { + std::string TypeName = RD->getQualifiedNameAsString(); + auto isInBlacklist = [&](const SanitizerBlacklist &BL) { + if (RD->hasAttr<UuidAttr>() && BL.isBlacklistedType("attr:uuid")) + return true; - if (getCodeGenOpts().LTOVisibilityPublicStd) { - const DeclContext *DC = RD; - while (1) { - auto *D = cast<Decl>(DC); - DC = DC->getParent(); - if (isa<TranslationUnitDecl>(DC->getRedeclContext())) { - if (auto *ND = dyn_cast<NamespaceDecl>(D)) - if (const IdentifierInfo *II = ND->getIdentifier()) - if (II->isStr("std") || II->isStr("stdext")) - return false; - break; - } - } - } + return BL.isBlacklistedType(TypeName); + }; - return true; + return isInBlacklist(WholeProgramVTablesBlacklist) || + ((LangOpts.Sanitize.has(SanitizerKind::CFIVCall) || + LangOpts.Sanitize.has(SanitizerKind::CFINVCall) || + LangOpts.Sanitize.has(SanitizerKind::CFIDerivedCast) || + LangOpts.Sanitize.has(SanitizerKind::CFIUnrelatedCast)) && + isInBlacklist(getContext().getSanitizerBlacklist())); } void CodeGenModule::EmitVTableBitSetEntries(llvm::GlobalVariable *VTable, const VTableLayout &VTLayout) { - if (!getCodeGenOpts().PrepareForLTO) + if (!NeedVTableBitSets()) return; CharUnits PointerWidth = @@ -947,8 +938,12 @@ void CodeGenModule::EmitVTableBitSetEntries(llvm::GlobalVariable *VTable, typedef std::pair<const CXXRecordDecl *, unsigned> BSEntry; std::vector<BSEntry> BitsetEntries; // Create a bit set entry for each address point. - for (auto &&AP : VTLayout.getAddressPoints()) + for (auto &&AP : VTLayout.getAddressPoints()) { + if (IsBitSetBlacklistedRecord(AP.first.getBase())) + continue; + BitsetEntries.push_back(std::make_pair(AP.first.getBase(), AP.second)); + } // Sort the bit set entries for determinism. std::sort(BitsetEntries.begin(), BitsetEntries.end(), |