diff options
Diffstat (limited to 'contrib/llvm/tools/clang/lib/CodeGen/CodeGenModule.cpp')
-rw-r--r-- | contrib/llvm/tools/clang/lib/CodeGen/CodeGenModule.cpp | 687 |
1 files changed, 489 insertions, 198 deletions
diff --git a/contrib/llvm/tools/clang/lib/CodeGen/CodeGenModule.cpp b/contrib/llvm/tools/clang/lib/CodeGen/CodeGenModule.cpp index c9c48c7..173b0dc 100644 --- a/contrib/llvm/tools/clang/lib/CodeGen/CodeGenModule.cpp +++ b/contrib/llvm/tools/clang/lib/CodeGen/CodeGenModule.cpp @@ -12,6 +12,7 @@ //===----------------------------------------------------------------------===// #include "CodeGenModule.h" +#include "CGBlocks.h" #include "CGCUDARuntime.h" #include "CGCXXABI.h" #include "CGCall.h" @@ -52,6 +53,7 @@ #include "llvm/ProfileData/InstrProfReader.h" #include "llvm/Support/ConvertUTF.h" #include "llvm/Support/ErrorHandling.h" +#include "llvm/Support/MD5.h" using namespace clang; using namespace CodeGen; @@ -64,8 +66,10 @@ static CGCXXABI *createCXXABI(CodeGenModule &CGM) { case TargetCXXABI::GenericARM: case TargetCXXABI::iOS: case TargetCXXABI::iOS64: + case TargetCXXABI::WatchOS: case TargetCXXABI::GenericMIPS: case TargetCXXABI::GenericItanium: + case TargetCXXABI::WebAssembly: return CreateItaniumCXXABI(CGM); case TargetCXXABI::Microsoft: return CreateMicrosoftCXXABI(CGM); @@ -77,17 +81,16 @@ static CGCXXABI *createCXXABI(CodeGenModule &CGM) { CodeGenModule::CodeGenModule(ASTContext &C, const HeaderSearchOptions &HSO, const PreprocessorOptions &PPO, const CodeGenOptions &CGO, llvm::Module &M, - const llvm::DataLayout &TD, DiagnosticsEngine &diags, CoverageSourceInfo *CoverageInfo) : Context(C), LangOpts(C.getLangOpts()), HeaderSearchOpts(HSO), PreprocessorOpts(PPO), CodeGenOpts(CGO), TheModule(M), Diags(diags), - TheDataLayout(TD), Target(C.getTargetInfo()), ABI(createCXXABI(*this)), + Target(C.getTargetInfo()), ABI(createCXXABI(*this)), VMContext(M.getContext()), TBAA(nullptr), TheTargetCodeGenInfo(nullptr), Types(*this), VTables(*this), ObjCRuntime(nullptr), OpenCLRuntime(nullptr), OpenMPRuntime(nullptr), CUDARuntime(nullptr), - DebugInfo(nullptr), ARCData(nullptr), - NoObjCARCExceptionsMetadata(nullptr), RRData(nullptr), PGOReader(nullptr), + DebugInfo(nullptr), ObjCData(nullptr), + NoObjCARCExceptionsMetadata(nullptr), PGOReader(nullptr), CFConstantStringClassRef(nullptr), ConstantStringClassRef(nullptr), NSConstantStringType(nullptr), NSConcreteGlobalBlock(nullptr), NSConcreteStackBlock(nullptr), BlockObjectAssign(nullptr), @@ -106,7 +109,9 @@ CodeGenModule::CodeGenModule(ASTContext &C, const HeaderSearchOptions &HSO, DoubleTy = llvm::Type::getDoubleTy(LLVMContext); PointerWidthInBits = C.getTargetInfo().getPointerWidth(0); PointerAlignInBytes = - C.toCharUnitsFromBits(C.getTargetInfo().getPointerAlign(0)).getQuantity(); + C.toCharUnitsFromBits(C.getTargetInfo().getPointerAlign(0)).getQuantity(); + IntAlignInBytes = + C.toCharUnitsFromBits(C.getTargetInfo().getIntAlign()).getQuantity(); IntTy = llvm::IntegerType::get(LLVMContext, C.getTargetInfo().getIntWidth()); IntPtrTy = llvm::IntegerType::get(LLVMContext, PointerWidthInBits); Int8PtrTy = Int8Ty->getPointerTo(0); @@ -139,9 +144,8 @@ CodeGenModule::CodeGenModule(ASTContext &C, const HeaderSearchOptions &HSO, Block.GlobalUniqueCount = 0; - if (C.getLangOpts().ObjCAutoRefCount) - ARCData = new ARCEntrypoints(); - RRData = new RREntrypoints(); + if (C.getLangOpts().ObjC1) + ObjCData = new ObjCEntrypoints(); if (!CodeGenOpts.InstrProfileInput.empty()) { auto ReaderOrErr = @@ -169,8 +173,7 @@ CodeGenModule::~CodeGenModule() { delete TheTargetCodeGenInfo; delete TBAA; delete DebugInfo; - delete ARCData; - delete RRData; + delete ObjCData; } void CodeGenModule::createObjCRuntime() { @@ -186,6 +189,7 @@ void CodeGenModule::createObjCRuntime() { case ObjCRuntime::FragileMacOSX: case ObjCRuntime::MacOSX: case ObjCRuntime::iOS: + case ObjCRuntime::WatchOS: ObjCRuntime = CreateMacObjCRuntime(*this); return; } @@ -232,12 +236,27 @@ void CodeGenModule::applyReplacements() { OldF->replaceAllUsesWith(Replacement); if (NewF) { NewF->removeFromParent(); - OldF->getParent()->getFunctionList().insertAfter(OldF, NewF); + OldF->getParent()->getFunctionList().insertAfter(OldF->getIterator(), + NewF); } OldF->eraseFromParent(); } } +void CodeGenModule::addGlobalValReplacement(llvm::GlobalValue *GV, llvm::Constant *C) { + GlobalValReplacements.push_back(std::make_pair(GV, C)); +} + +void CodeGenModule::applyGlobalValReplacements() { + for (auto &I : GlobalValReplacements) { + llvm::GlobalValue *GV = I.first; + llvm::Constant *C = I.second; + + GV->replaceAllUsesWith(C); + GV->eraseFromParent(); + } +} + // This is only used in aliases that we created and we know they have a // linear structure. static const llvm::GlobalObject *getAliasedGlobal(const llvm::GlobalAlias &GA) { @@ -340,6 +359,7 @@ void InstrProfStats::reportDiagnostics(DiagnosticsEngine &Diags, void CodeGenModule::Release() { EmitDeferred(); + applyGlobalValReplacements(); applyReplacements(); checkAliases(); EmitCXXGlobalInitFunc(); @@ -355,8 +375,11 @@ void CodeGenModule::Release() { if (llvm::Function *CudaDtorFunction = CUDARuntime->makeModuleDtorFunction()) AddGlobalDtor(CudaDtorFunction); } - if (PGOReader && PGOStats.hasDiagnostics()) - PGOStats.reportDiagnostics(getDiags(), getCodeGenOpts().MainFileName); + if (PGOReader) { + getModule().setMaximumFunctionCount(PGOReader->getMaximumFunctionCount()); + if (PGOStats.hasDiagnostics()) + PGOStats.reportDiagnostics(getDiags(), getCodeGenOpts().MainFileName); + } EmitCtorList(GlobalCtors, "llvm.global_ctors"); EmitCtorList(GlobalDtors, "llvm.global_dtors"); EmitGlobalAnnotations(); @@ -370,11 +393,32 @@ void CodeGenModule::Release() { (Context.getLangOpts().Modules || !LinkerOptionsMetadata.empty())) { EmitModuleLinkOptions(); } - if (CodeGenOpts.DwarfVersion) + if (CodeGenOpts.DwarfVersion) { // We actually want the latest version when there are conflicts. // We can change from Warning to Latest if such mode is supported. getModule().addModuleFlag(llvm::Module::Warning, "Dwarf Version", CodeGenOpts.DwarfVersion); + } + if (CodeGenOpts.EmitCodeView) { + // Indicate that we want CodeView in the metadata. + getModule().addModuleFlag(llvm::Module::Warning, "CodeView", 1); + } + if (CodeGenOpts.OptimizationLevel > 0 && CodeGenOpts.StrictVTablePointers) { + // We don't support LTO with 2 with different StrictVTablePointers + // FIXME: we could support it by stripping all the information introduced + // by StrictVTablePointers. + + getModule().addModuleFlag(llvm::Module::Error, "StrictVTablePointers",1); + + llvm::Metadata *Ops[2] = { + llvm::MDString::get(VMContext, "StrictVTablePointers"), + llvm::ConstantAsMetadata::get(llvm::ConstantInt::get( + llvm::Type::getInt32Ty(VMContext), 1))}; + + getModule().addModuleFlag(llvm::Module::Require, + "StrictVTablePointersRequirement", + llvm::MDNode::get(VMContext, Ops)); + } if (DebugInfo) // We support a single version in the linked module. The LLVM // parser will drop debug info with a different version number @@ -399,6 +443,11 @@ void CodeGenModule::Release() { getModule().addModuleFlag(llvm::Module::Error, "min_enum_size", EnumWidth); } + if (CodeGenOpts.SanitizeCfiCrossDso) { + // Indicate that we want cross-DSO control flow integrity checks. + getModule().addModuleFlag(llvm::Module::Override, "Cross-DSO CFI", 1); + } + if (uint32_t PLevel = Context.getLangOpts().PICLevel) { llvm::PICLevel::Level PL = llvm::PICLevel::Default; switch (PLevel) { @@ -450,12 +499,6 @@ llvm::MDNode *CodeGenModule::getTBAAStructInfo(QualType QTy) { return TBAA->getTBAAStructInfo(QTy); } -llvm::MDNode *CodeGenModule::getTBAAStructTypeInfo(QualType QTy) { - if (!TBAA) - return nullptr; - return TBAA->getTBAAStructTypeInfo(QTy); -} - llvm::MDNode *CodeGenModule::getTBAAStructTagInfo(QualType BaseTy, llvm::MDNode *AccessN, uint64_t O) { @@ -468,9 +511,9 @@ llvm::MDNode *CodeGenModule::getTBAAStructTagInfo(QualType BaseTy, /// and struct-path aware TBAA, the tag has the same format: /// base type, access type and offset. /// When ConvertTypeToTag is true, we create a tag based on the scalar type. -void CodeGenModule::DecorateInstruction(llvm::Instruction *Inst, - llvm::MDNode *TBAAInfo, - bool ConvertTypeToTag) { +void CodeGenModule::DecorateInstructionWithTBAA(llvm::Instruction *Inst, + llvm::MDNode *TBAAInfo, + bool ConvertTypeToTag) { if (ConvertTypeToTag && TBAA) Inst->setMetadata(llvm::LLVMContext::MD_tbaa, TBAA->getTBAAScalarTagInfo(TBAAInfo)); @@ -478,6 +521,16 @@ void CodeGenModule::DecorateInstruction(llvm::Instruction *Inst, Inst->setMetadata(llvm::LLVMContext::MD_tbaa, TBAAInfo); } +void CodeGenModule::DecorateInstructionWithInvariantGroup( + llvm::Instruction *I, const CXXRecordDecl *RD) { + llvm::Metadata *MD = CreateMetadataIdentifierForType(QualType(RD->getTypeForDecl(), 0)); + auto *MetaDataNode = dyn_cast<llvm::MDNode>(MD); + // Check if we have to wrap MDString in MDNode. + if (!MetaDataNode) + MetaDataNode = llvm::MDNode::get(getLLVMContext(), MD); + I->setMetadata(llvm::LLVMContext::MD_invariant_group, MetaDataNode); +} + void CodeGenModule::Error(SourceLocation loc, StringRef message) { unsigned diagID = getDiags().getCustomDiagID(DiagnosticsEngine::Error, "%0"); getDiags().Report(Context.getFullLoc(loc), diagID) << message; @@ -692,6 +745,21 @@ void CodeGenModule::setFunctionDLLStorageClass(GlobalDecl GD, llvm::Function *F) F->setDLLStorageClass(llvm::GlobalVariable::DefaultStorageClass); } +llvm::ConstantInt * +CodeGenModule::CreateCfiIdForTypeMetadata(llvm::Metadata *MD) { + llvm::MDString *MDS = dyn_cast<llvm::MDString>(MD); + if (!MDS) return nullptr; + + llvm::MD5 md5; + llvm::MD5::MD5Result result; + md5.update(MDS->getString()); + md5.final(result); + uint64_t id = 0; + for (int i = 0; i < 8; ++i) + id |= static_cast<uint64_t>(result[i]) << (i * 8); + return llvm::ConstantInt::get(Int64Ty, id); +} + void CodeGenModule::setFunctionDefinitionAttributes(const FunctionDecl *D, llvm::Function *F) { setNonAliasAttributes(D, F); @@ -737,6 +805,21 @@ void CodeGenModule::SetLLVMFunctionAttributesForDefinition(const Decl *D, if (!hasUnwindExceptions(LangOpts)) B.addAttribute(llvm::Attribute::NoUnwind); + if (LangOpts.getStackProtector() == LangOptions::SSPOn) + B.addAttribute(llvm::Attribute::StackProtect); + else if (LangOpts.getStackProtector() == LangOptions::SSPStrong) + B.addAttribute(llvm::Attribute::StackProtectStrong); + else if (LangOpts.getStackProtector() == LangOptions::SSPReq) + B.addAttribute(llvm::Attribute::StackProtectReq); + + if (!D) { + F->addAttributes(llvm::AttributeSet::FunctionIndex, + llvm::AttributeSet::get( + F->getContext(), + llvm::AttributeSet::FunctionIndex, B)); + return; + } + if (D->hasAttr<NakedAttr>()) { // Naked implies noinline: we should not be inlining such functions. B.addAttribute(llvm::Attribute::Naked); @@ -761,13 +844,6 @@ void CodeGenModule::SetLLVMFunctionAttributesForDefinition(const Decl *D, if (D->hasAttr<MinSizeAttr>()) B.addAttribute(llvm::Attribute::MinSize); - if (LangOpts.getStackProtector() == LangOptions::SSPOn) - B.addAttribute(llvm::Attribute::StackProtect); - else if (LangOpts.getStackProtector() == LangOptions::SSPStrong) - B.addAttribute(llvm::Attribute::StackProtectStrong); - else if (LangOpts.getStackProtector() == LangOptions::SSPReq) - B.addAttribute(llvm::Attribute::StackProtectReq); - F->addAttributes(llvm::AttributeSet::FunctionIndex, llvm::AttributeSet::get( F->getContext(), llvm::AttributeSet::FunctionIndex, B)); @@ -778,10 +854,8 @@ void CodeGenModule::SetLLVMFunctionAttributesForDefinition(const Decl *D, F->addFnAttr(llvm::Attribute::NoInline); // OptimizeNone wins over OptimizeForSize, MinSize, AlwaysInline. - assert(!F->hasFnAttribute(llvm::Attribute::OptimizeForSize) && - "OptimizeNone and OptimizeForSize on same function!"); - assert(!F->hasFnAttribute(llvm::Attribute::MinSize) && - "OptimizeNone and MinSize on same function!"); + F->removeFnAttr(llvm::Attribute::OptimizeForSize); + F->removeFnAttr(llvm::Attribute::MinSize); assert(!F->hasFnAttribute(llvm::Attribute::AlwaysInline) && "OptimizeNone and AlwaysInline on same function!"); @@ -800,19 +874,24 @@ void CodeGenModule::SetLLVMFunctionAttributesForDefinition(const Decl *D, if (alignment) F->setAlignment(alignment); - // C++ ABI requires 2-byte alignment for member functions. - if (F->getAlignment() < 2 && isa<CXXMethodDecl>(D)) - F->setAlignment(2); + // Some C++ ABIs require 2-byte alignment for member functions, in order to + // reserve a bit for differentiating between virtual and non-virtual member + // functions. If the current target's C++ ABI requires this and this is a + // member function, set its alignment accordingly. + if (getTarget().getCXXABI().areMemberFunctionsAligned()) { + if (F->getAlignment() < 2 && isa<CXXMethodDecl>(D)) + F->setAlignment(2); + } } void CodeGenModule::SetCommonAttributes(const Decl *D, llvm::GlobalValue *GV) { - if (const auto *ND = dyn_cast<NamedDecl>(D)) + if (const auto *ND = dyn_cast_or_null<NamedDecl>(D)) setGlobalVisibility(GV, ND); else GV->setVisibility(llvm::GlobalValue::DefaultVisibility); - if (D->hasAttr<UsedAttr>()) + if (D && D->hasAttr<UsedAttr>()) addUsedGlobal(GV); } @@ -830,8 +909,9 @@ void CodeGenModule::setNonAliasAttributes(const Decl *D, llvm::GlobalObject *GO) { SetCommonAttributes(D, GO); - if (const SectionAttr *SA = D->getAttr<SectionAttr>()) - GO->setSection(SA->getName()); + if (D) + if (const SectionAttr *SA = D->getAttr<SectionAttr>()) + GO->setSection(SA->getName()); getTargetCodeGenInfo().setTargetAttributes(D, GO, *this); } @@ -872,6 +952,49 @@ static void setLinkageAndVisibilityForGV(llvm::GlobalValue *GV, } } +void CodeGenModule::CreateFunctionBitSetEntry(const FunctionDecl *FD, + llvm::Function *F) { + // Only if we are checking indirect calls. + if (!LangOpts.Sanitize.has(SanitizerKind::CFIICall)) + return; + + // Non-static class methods are handled via vtable pointer checks elsewhere. + if (isa<CXXMethodDecl>(FD) && !cast<CXXMethodDecl>(FD)->isStatic()) + return; + + // Additionally, if building with cross-DSO support... + if (CodeGenOpts.SanitizeCfiCrossDso) { + // Don't emit entries for function declarations. In cross-DSO mode these are + // handled with better precision at run time. + if (!FD->hasBody()) + return; + // Skip available_externally functions. They won't be codegen'ed in the + // current module anyway. + if (getContext().GetGVALinkageForFunction(FD) == GVA_AvailableExternally) + return; + } + + llvm::NamedMDNode *BitsetsMD = + getModule().getOrInsertNamedMetadata("llvm.bitsets"); + + llvm::Metadata *MD = CreateMetadataIdentifierForType(FD->getType()); + llvm::Metadata *BitsetOps[] = { + MD, llvm::ConstantAsMetadata::get(F), + llvm::ConstantAsMetadata::get(llvm::ConstantInt::get(Int64Ty, 0))}; + BitsetsMD->addOperand(llvm::MDTuple::get(getLLVMContext(), BitsetOps)); + + // Emit a hash-based bit set entry for cross-DSO calls. + if (CodeGenOpts.SanitizeCfiCrossDso) { + if (auto TypeId = CreateCfiIdForTypeMetadata(MD)) { + llvm::Metadata *BitsetOps2[] = { + llvm::ConstantAsMetadata::get(TypeId), + llvm::ConstantAsMetadata::get(F), + llvm::ConstantAsMetadata::get(llvm::ConstantInt::get(Int64Ty, 0))}; + BitsetsMD->addOperand(llvm::MDTuple::get(getLLVMContext(), BitsetOps2)); + } + } +} + void CodeGenModule::SetFunctionAttributes(GlobalDecl GD, llvm::Function *F, bool IsIncompleteFunction, bool IsThunk) { @@ -913,6 +1036,8 @@ void CodeGenModule::SetFunctionAttributes(GlobalDecl GD, llvm::Function *F, if (FD->isReplaceableGlobalAllocationFunction()) F->addAttribute(llvm::AttributeSet::FunctionIndex, llvm::Attribute::NoBuiltin); + + CreateFunctionBitSetEntry(FD, F); } void CodeGenModule::addUsedGlobal(llvm::GlobalValue *GV) { @@ -1104,9 +1229,16 @@ void CodeGenModule::EmitDeferred() { llvm::GlobalValue *GV = G.GV; G.GV = nullptr; - assert(!GV || GV == GetGlobalValue(getMangledName(D))); - if (!GV) - GV = GetGlobalValue(getMangledName(D)); + // We should call GetAddrOfGlobal with IsForDefinition set to true in order + // to get GlobalValue with exactly the type we need, not something that + // might had been created for another decl with the same mangled name but + // different type. + // FIXME: Support for variables is not implemented yet. + if (isa<FunctionDecl>(D.getDecl())) + GV = cast<llvm::GlobalValue>(GetAddrOfGlobal(D, /*IsForDefinition=*/true)); + else + if (!GV) + GV = GetGlobalValue(getMangledName(D)); // Check to see if we've already emitted this. This is necessary // for a couple of reasons: first, decls can end up in the @@ -1208,7 +1340,7 @@ bool CodeGenModule::isInSanitizerBlacklist(llvm::Function *Fn, if (SanitizerBL.isBlacklistedFunction(Fn->getName())) return true; // Blacklist by location. - if (!Loc.isInvalid()) + if (Loc.isValid()) return SanitizerBL.isBlacklistedLocation(Loc); // If location is unknown, this may be a compiler-generated function. Assume // it's located in the main file. @@ -1271,7 +1403,7 @@ bool CodeGenModule::MayBeEmittedEagerly(const ValueDecl *Global) { return true; } -llvm::Constant *CodeGenModule::GetAddrOfUuidDescriptor( +ConstantAddress CodeGenModule::GetAddrOfUuidDescriptor( const CXXUuidofExpr* E) { // Sema has verified that IIDSource has a __declspec(uuid()), and that its // well-formed. @@ -1279,9 +1411,12 @@ llvm::Constant *CodeGenModule::GetAddrOfUuidDescriptor( std::string Name = "_GUID_" + Uuid.lower(); std::replace(Name.begin(), Name.end(), '-', '_'); + // Contains a 32-bit field. + CharUnits Alignment = CharUnits::fromQuantity(4); + // Look for an existing global. if (llvm::GlobalVariable *GV = getModule().getNamedGlobal(Name)) - return GV; + return ConstantAddress(GV, Alignment); llvm::Constant *Init = EmitUuidofInitializer(Uuid); assert(Init && "failed to initialize as constant"); @@ -1291,20 +1426,22 @@ llvm::Constant *CodeGenModule::GetAddrOfUuidDescriptor( /*isConstant=*/true, llvm::GlobalValue::LinkOnceODRLinkage, Init, Name); if (supportsCOMDAT()) GV->setComdat(TheModule.getOrInsertComdat(GV->getName())); - return GV; + return ConstantAddress(GV, Alignment); } -llvm::Constant *CodeGenModule::GetWeakRefReference(const ValueDecl *VD) { +ConstantAddress CodeGenModule::GetWeakRefReference(const ValueDecl *VD) { const AliasAttr *AA = VD->getAttr<AliasAttr>(); assert(AA && "No alias?"); + CharUnits Alignment = getContext().getDeclAlign(VD); llvm::Type *DeclTy = getTypes().ConvertTypeForMem(VD->getType()); // See if there is already something with the target's name in the module. llvm::GlobalValue *Entry = GetGlobalValue(AA->getAliasee()); if (Entry) { unsigned AS = getContext().getTargetAddressSpace(VD->getType()); - return llvm::ConstantExpr::getBitCast(Entry, DeclTy->getPointerTo(AS)); + auto Ptr = llvm::ConstantExpr::getBitCast(Entry, DeclTy->getPointerTo(AS)); + return ConstantAddress(Ptr, Alignment); } llvm::Constant *Aliasee; @@ -1321,7 +1458,7 @@ llvm::Constant *CodeGenModule::GetWeakRefReference(const ValueDecl *VD) { F->setLinkage(llvm::Function::ExternalWeakLinkage); WeakRefReferences.insert(F); - return Aliasee; + return ConstantAddress(Aliasee, Alignment); } void CodeGenModule::EmitGlobal(GlobalDecl GD) { @@ -1435,7 +1572,7 @@ namespace { unsigned BuiltinID = FD->getBuiltinID(); if (!BuiltinID || !BI.isLibFunction(BuiltinID)) return true; - StringRef BuiltinName = BI.GetName(BuiltinID); + StringRef BuiltinName = BI.getName(BuiltinID); if (BuiltinName.startswith("__builtin_") && Name == BuiltinName.slice(strlen("__builtin_"), StringRef::npos)) { Result = true; @@ -1444,6 +1581,35 @@ namespace { return true; } }; + + struct DLLImportFunctionVisitor + : public RecursiveASTVisitor<DLLImportFunctionVisitor> { + bool SafeToInline = true; + + bool VisitVarDecl(VarDecl *VD) { + // A thread-local variable cannot be imported. + SafeToInline = !VD->getTLSKind(); + return SafeToInline; + } + + // Make sure we're not referencing non-imported vars or functions. + bool VisitDeclRefExpr(DeclRefExpr *E) { + ValueDecl *VD = E->getDecl(); + if (isa<FunctionDecl>(VD)) + SafeToInline = VD->hasAttr<DLLImportAttr>(); + else if (VarDecl *V = dyn_cast<VarDecl>(VD)) + SafeToInline = !V->hasGlobalStorage() || V->hasAttr<DLLImportAttr>(); + return SafeToInline; + } + bool VisitCXXDeleteExpr(CXXDeleteExpr *E) { + SafeToInline = E->getOperatorDelete()->hasAttr<DLLImportAttr>(); + return SafeToInline; + } + bool VisitCXXNewExpr(CXXNewExpr *E) { + SafeToInline = E->getOperatorNew()->hasAttr<DLLImportAttr>(); + return SafeToInline; + } + }; } // isTriviallyRecursive - Check if this function calls another @@ -1474,6 +1640,15 @@ CodeGenModule::shouldEmitFunction(GlobalDecl GD) { const auto *F = cast<FunctionDecl>(GD.getDecl()); if (CodeGenOpts.OptimizationLevel == 0 && !F->hasAttr<AlwaysInlineAttr>()) return false; + + if (F->hasAttr<DLLImportAttr>()) { + // Check whether it would be safe to inline this dllimport function. + DLLImportFunctionVisitor Visitor; + Visitor.TraverseFunctionDecl(const_cast<FunctionDecl*>(F)); + if (!Visitor.SafeToInline) + return false; + } + // PR9614. Avoid cases where the source code is lying to us. An available // externally function should have an equivalent function somewhere else, // but a function that calls itself is clearly not equivalent to the real @@ -1537,6 +1712,9 @@ void CodeGenModule::EmitGlobalDefinition(GlobalDecl GD, llvm::GlobalValue *GV) { llvm_unreachable("Invalid argument to EmitGlobalDefinition()"); } +static void ReplaceUsesOfNonProtoTypeWithRealFunction(llvm::GlobalValue *Old, + llvm::Function *NewFn); + /// GetOrCreateLLVMFunction - If the specified mangled name is not in the /// module, create and return an llvm Function with the specified type. If there /// is something in the module with the specified name, return it potentially @@ -1549,7 +1727,8 @@ CodeGenModule::GetOrCreateLLVMFunction(StringRef MangledName, llvm::Type *Ty, GlobalDecl GD, bool ForVTable, bool DontDefer, bool IsThunk, - llvm::AttributeSet ExtraAttrs) { + llvm::AttributeSet ExtraAttrs, + bool IsForDefinition) { const Decl *D = GD.getDecl(); // Lookup the entry, lazily creating it if necessary. @@ -1565,11 +1744,33 @@ CodeGenModule::GetOrCreateLLVMFunction(StringRef MangledName, if (D && !D->hasAttr<DLLImportAttr>() && !D->hasAttr<DLLExportAttr>()) Entry->setDLLStorageClass(llvm::GlobalValue::DefaultStorageClass); - if (Entry->getType()->getElementType() == Ty) + // If there are two attempts to define the same mangled name, issue an + // error. + if (IsForDefinition && !Entry->isDeclaration()) { + GlobalDecl OtherGD; + // Check that GD is not yet in ExplicitDefinitions is required to make + // sure that we issue an error only once. + if (lookupRepresentativeDecl(MangledName, OtherGD) && + (GD.getCanonicalDecl().getDecl() != + OtherGD.getCanonicalDecl().getDecl()) && + DiagnosedConflictingDefinitions.insert(GD).second) { + getDiags().Report(D->getLocation(), + diag::err_duplicate_mangled_name); + getDiags().Report(OtherGD.getDecl()->getLocation(), + diag::note_previous_definition); + } + } + + if ((isa<llvm::Function>(Entry) || isa<llvm::GlobalAlias>(Entry)) && + (Entry->getType()->getElementType() == Ty)) { return Entry; + } // Make sure the result is of the correct type. - return llvm::ConstantExpr::getBitCast(Entry, Ty->getPointerTo()); + // (If function is requested for a definition, we always need to create a new + // function, not just return a bitcast.) + if (!IsForDefinition) + return llvm::ConstantExpr::getBitCast(Entry, Ty->getPointerTo()); } // This function doesn't have a complete type (for example, the return @@ -1584,10 +1785,36 @@ CodeGenModule::GetOrCreateLLVMFunction(StringRef MangledName, FTy = llvm::FunctionType::get(VoidTy, false); IsIncompleteFunction = true; } - - llvm::Function *F = llvm::Function::Create(FTy, - llvm::Function::ExternalLinkage, - MangledName, &getModule()); + + llvm::Function *F = + llvm::Function::Create(FTy, llvm::Function::ExternalLinkage, + Entry ? StringRef() : MangledName, &getModule()); + + // If we already created a function with the same mangled name (but different + // type) before, take its name and add it to the list of functions to be + // replaced with F at the end of CodeGen. + // + // This happens if there is a prototype for a function (e.g. "int f()") and + // then a definition of a different type (e.g. "int f(int x)"). + if (Entry) { + F->takeName(Entry); + + // This might be an implementation of a function without a prototype, in + // which case, try to do special replacement of calls which match the new + // prototype. The really key thing here is that we also potentially drop + // arguments from the call site so as to make a direct call, which makes the + // inliner happier and suppresses a number of optimizer warnings (!) about + // dropping arguments. + if (!Entry->use_empty()) { + ReplaceUsesOfNonProtoTypeWithRealFunction(Entry, F); + Entry->removeDeadConstantUsers(); + } + + llvm::Constant *BC = llvm::ConstantExpr::getBitCast( + F, Entry->getType()->getElementType()->getPointerTo()); + addGlobalValReplacement(Entry, BC); + } + assert(F->getName() == MangledName && "name was uniqued!"); if (D) SetFunctionAttributes(GD, F, IsIncompleteFunction, IsThunk); @@ -1660,13 +1887,19 @@ CodeGenModule::GetOrCreateLLVMFunction(StringRef MangledName, llvm::Constant *CodeGenModule::GetAddrOfFunction(GlobalDecl GD, llvm::Type *Ty, bool ForVTable, - bool DontDefer) { + bool DontDefer, + bool IsForDefinition) { // If there was no specific requested type, just convert it now. - if (!Ty) - Ty = getTypes().ConvertType(cast<ValueDecl>(GD.getDecl())->getType()); - + if (!Ty) { + const auto *FD = cast<FunctionDecl>(GD.getDecl()); + auto CanonTy = Context.getCanonicalType(FD->getType()); + Ty = getTypes().ConvertFunctionType(CanonTy, FD); + } + StringRef MangledName = getMangledName(GD); - return GetOrCreateLLVMFunction(MangledName, Ty, GD, ForVTable, DontDefer); + return GetOrCreateLLVMFunction(MangledName, Ty, GD, ForVTable, DontDefer, + /*IsThunk=*/false, llvm::AttributeSet(), + IsForDefinition); } /// CreateRuntimeFunction - Create a new runtime function with the specified @@ -1781,7 +2014,7 @@ CodeGenModule::GetOrCreateLLVMGlobal(StringRef MangledName, if (D->getTLSKind()) { if (D->getTLSKind() == VarDecl::TLS_Dynamic) - CXXThreadLocals.push_back(std::make_pair(D, GV)); + CXXThreadLocals.push_back(D); setTLSMode(GV, *D); } @@ -1805,6 +2038,33 @@ CodeGenModule::GetOrCreateLLVMGlobal(StringRef MangledName, return GV; } +llvm::Constant * +CodeGenModule::GetAddrOfGlobal(GlobalDecl GD, + bool IsForDefinition) { + if (isa<CXXConstructorDecl>(GD.getDecl())) + return getAddrOfCXXStructor(cast<CXXConstructorDecl>(GD.getDecl()), + getFromCtorType(GD.getCtorType()), + /*FnInfo=*/nullptr, /*FnType=*/nullptr, + /*DontDefer=*/false, IsForDefinition); + else if (isa<CXXDestructorDecl>(GD.getDecl())) + return getAddrOfCXXStructor(cast<CXXDestructorDecl>(GD.getDecl()), + getFromDtorType(GD.getDtorType()), + /*FnInfo=*/nullptr, /*FnType=*/nullptr, + /*DontDefer=*/false, IsForDefinition); + else if (isa<CXXMethodDecl>(GD.getDecl())) { + auto FInfo = &getTypes().arrangeCXXMethodDeclaration( + cast<CXXMethodDecl>(GD.getDecl())); + auto Ty = getTypes().GetFunctionType(*FInfo); + return GetAddrOfFunction(GD, Ty, /*ForVTable=*/false, /*DontDefer=*/false, + IsForDefinition); + } else if (isa<FunctionDecl>(GD.getDecl())) { + const CGFunctionInfo &FI = getTypes().arrangeGlobalDeclaration(GD); + llvm::FunctionType *Ty = getTypes().GetFunctionType(FI); + return GetAddrOfFunction(GD, Ty, /*ForVTable=*/false, /*DontDefer=*/false, + IsForDefinition); + } else + return GetAddrOfGlobalVar(cast<VarDecl>(GD.getDecl())); +} llvm::GlobalVariable * CodeGenModule::CreateOrReplaceCXXRuntimeVariable(StringRef Name, @@ -1893,8 +2153,8 @@ void CodeGenModule::EmitTentativeDefinition(const VarDecl *D) { } CharUnits CodeGenModule::GetTargetTypeStoreSize(llvm::Type *Ty) const { - return Context.toCharUnitsFromBits( - TheDataLayout.getTypeStoreSizeInBits(Ty)); + return Context.toCharUnitsFromBits( + getDataLayout().getTypeStoreSizeInBits(Ty)); } unsigned CodeGenModule::GetGlobalVarAddressSpace(const VarDecl *D, @@ -1986,7 +2246,18 @@ void CodeGenModule::EmitGlobalVarDefinition(const VarDecl *D) { const VarDecl *InitDecl; const Expr *InitExpr = D->getAnyInitializer(InitDecl); - if (!InitExpr) { + // CUDA E.2.4.1 "__shared__ variables cannot have an initialization as part + // of their declaration." + if (getLangOpts().CPlusPlus && getLangOpts().CUDAIsDevice + && D->hasAttr<CUDASharedAttr>()) { + if (InitExpr) { + const auto *C = dyn_cast<CXXConstructExpr>(InitExpr); + if (C == nullptr || !C->getConstructor()->hasTrivialBody()) + Error(D->getLocation(), + "__shared__ variable cannot have an initialization."); + } + Init = llvm::UndefValue::get(getTypes().ConvertType(ASTTy)); + } else if (!InitExpr) { // This is a tentative definition; tentative definitions are // implicitly initialized with { 0 }. // @@ -2072,6 +2343,17 @@ void CodeGenModule::EmitGlobalVarDefinition(const VarDecl *D) { if (D->hasAttr<AnnotateAttr>()) AddGlobalAnnotations(D, GV); + // CUDA B.2.1 "The __device__ qualifier declares a variable that resides on + // the device. [...]" + // CUDA B.2.2 "The __constant__ qualifier, optionally used together with + // __device__, declares a variable that: [...] + // Is accessible from all the threads within the grid and from the host + // through the runtime library (cudaGetSymbolAddress() / cudaGetSymbolSize() + // / cudaMemcpyToSymbol() / cudaMemcpyFromSymbol())." + if (GV && LangOpts.CUDA && LangOpts.CUDAIsDevice && + (D->hasAttr<CUDAConstantAttr>() || D->hasAttr<CUDADeviceAttr>())) { + GV->setExternallyInitialized(true); + } GV->setInitializer(Init); // If it is safe to mark the global 'constant', do so now. @@ -2091,12 +2373,17 @@ void CodeGenModule::EmitGlobalVarDefinition(const VarDecl *D) { llvm::GlobalValue::LinkageTypes Linkage = getLLVMLinkageVarDefinition(D, GV->isConstant()); - // On Darwin, the backing variable for a C++11 thread_local variable always - // has internal linkage; all accesses should just be calls to the + // On Darwin, if the normal linkage of a C++ thread_local variable is + // LinkOnce or Weak, we keep the normal linkage to prevent multiple + // copies within a linkage unit; otherwise, the backing variable has + // internal linkage and all accesses should just be calls to the // Itanium-specified entry point, which has the normal linkage of the - // variable. + // variable. This is to preserve the ability to change the implementation + // behind the scenes. if (!D->isStaticLocal() && D->getTLSKind() == VarDecl::TLS_Dynamic && - Context.getTargetInfo().getTriple().isMacOSX()) + Context.getTargetInfo().getTriple().isOSDarwin() && + !llvm::GlobalVariable::isLinkOnceLinkage(Linkage) && + !llvm::GlobalVariable::isWeakLinkage(Linkage)) Linkage = llvm::GlobalValue::InternalLinkage; GV->setLinkage(Linkage); @@ -2115,7 +2402,7 @@ void CodeGenModule::EmitGlobalVarDefinition(const VarDecl *D) { if (D->getTLSKind() && !GV->isThreadLocal()) { if (D->getTLSKind() == VarDecl::TLS_Dynamic) - CXXThreadLocals.push_back(std::make_pair(D, GV)); + CXXThreadLocals.push_back(D); setTLSMode(GV, *D); } @@ -2166,7 +2453,7 @@ static bool isVarDeclStrongDefinition(const ASTContext &Context, // Declarations with a required alignment do not have common linakge in MSVC // mode. - if (Context.getLangOpts().MSVCCompat) { + if (Context.getTargetInfo().getCXXABI().isMicrosoft()) { if (D->hasAttr<AlignedAttr>()) return true; QualType VarType = D->getType(); @@ -2263,6 +2550,7 @@ static void replaceUsesOfNonProtoConstant(llvm::Constant *old, llvm::Type *newRetTy = newFn->getReturnType(); SmallVector<llvm::Value*, 4> newArgs; + SmallVector<llvm::OperandBundleDef, 1> newBundles; for (llvm::Value::use_iterator ui = old->use_begin(), ue = old->use_end(); ui != ue; ) { @@ -2330,16 +2618,19 @@ static void replaceUsesOfNonProtoConstant(llvm::Constant *old, // over the required information. newArgs.append(callSite.arg_begin(), callSite.arg_begin() + argNo); + // Copy over any operand bundles. + callSite.getOperandBundlesAsDefs(newBundles); + llvm::CallSite newCall; if (callSite.isCall()) { - newCall = llvm::CallInst::Create(newFn, newArgs, "", + newCall = llvm::CallInst::Create(newFn, newArgs, newBundles, "", callSite.getInstruction()); } else { auto *oldInvoke = cast<llvm::InvokeInst>(callSite.getInstruction()); newCall = llvm::InvokeInst::Create(newFn, oldInvoke->getNormalDest(), oldInvoke->getUnwindDest(), - newArgs, "", + newArgs, newBundles, "", callSite.getInstruction()); } newArgs.clear(); // for the next iteration @@ -2357,6 +2648,7 @@ static void replaceUsesOfNonProtoConstant(llvm::Constant *old, // Copy debug location attached to CI. if (callSite->getDebugLoc()) newCall->setDebugLoc(callSite->getDebugLoc()); + callSite->eraseFromParent(); } } @@ -2397,66 +2689,14 @@ void CodeGenModule::EmitGlobalFunctionDefinition(GlobalDecl GD, llvm::FunctionType *Ty = getTypes().GetFunctionType(FI); // Get or create the prototype for the function. - if (!GV) { - llvm::Constant *C = - GetAddrOfFunction(GD, Ty, /*ForVTable=*/false, /*DontDefer*/ true); - - // Strip off a bitcast if we got one back. - if (auto *CE = dyn_cast<llvm::ConstantExpr>(C)) { - assert(CE->getOpcode() == llvm::Instruction::BitCast); - GV = cast<llvm::GlobalValue>(CE->getOperand(0)); - } else { - GV = cast<llvm::GlobalValue>(C); - } - } + if (!GV || (GV->getType()->getElementType() != Ty)) + GV = cast<llvm::GlobalValue>(GetAddrOfFunction(GD, Ty, /*ForVTable=*/false, + /*DontDefer=*/true, + /*IsForDefinition=*/true)); - if (!GV->isDeclaration()) { - getDiags().Report(D->getLocation(), diag::err_duplicate_mangled_name); - GlobalDecl OldGD = Manglings.lookup(GV->getName()); - if (auto *Prev = OldGD.getDecl()) - getDiags().Report(Prev->getLocation(), diag::note_previous_definition); + // Already emitted. + if (!GV->isDeclaration()) return; - } - - if (GV->getType()->getElementType() != Ty) { - // If the types mismatch then we have to rewrite the definition. - assert(GV->isDeclaration() && "Shouldn't replace non-declaration"); - - // F is the Function* for the one with the wrong type, we must make a new - // Function* and update everything that used F (a declaration) with the new - // Function* (which will be a definition). - // - // This happens if there is a prototype for a function - // (e.g. "int f()") and then a definition of a different type - // (e.g. "int f(int x)"). Move the old function aside so that it - // doesn't interfere with GetAddrOfFunction. - GV->setName(StringRef()); - auto *NewFn = cast<llvm::Function>(GetAddrOfFunction(GD, Ty)); - - // This might be an implementation of a function without a - // prototype, in which case, try to do special replacement of - // calls which match the new prototype. The really key thing here - // is that we also potentially drop arguments from the call site - // so as to make a direct call, which makes the inliner happier - // and suppresses a number of optimizer warnings (!) about - // dropping arguments. - if (!GV->use_empty()) { - ReplaceUsesOfNonProtoTypeWithRealFunction(GV, NewFn); - GV->removeDeadConstantUsers(); - } - - // Replace uses of F with the Function we will endow with a body. - if (!GV->use_empty()) { - llvm::Constant *NewPtrForOldDecl = - llvm::ConstantExpr::getBitCast(NewFn, GV->getType()); - GV->replaceAllUsesWith(NewPtrForOldDecl); - } - - // Ok, delete the old function now, which is dead. - GV->eraseFromParent(); - - GV = NewFn; - } // We need to set linkage and visibility on the function before // generating code for it because various parts of IR generation @@ -2521,8 +2761,7 @@ void CodeGenModule::EmitAliasDefinition(GlobalDecl GD) { // Create the new alias itself, but don't set a name yet. auto *GA = llvm::GlobalAlias::create( - cast<llvm::PointerType>(Aliasee->getType()), - llvm::Function::ExternalLinkage, "", Aliasee, &getModule()); + DeclTy, 0, llvm::Function::ExternalLinkage, "", Aliasee, &getModule()); if (Entry) { if (GA->getAliasee() == Entry) { @@ -2612,7 +2851,7 @@ GetConstantStringEntry(llvm::StringMap<llvm::GlobalVariable *> &Map, return *Map.insert(std::make_pair(String, nullptr)).first; } -llvm::Constant * +ConstantAddress CodeGenModule::GetAddrOfConstantCFString(const StringLiteral *Literal) { unsigned StringLength = 0; bool isUTF16 = false; @@ -2622,7 +2861,7 @@ CodeGenModule::GetAddrOfConstantCFString(const StringLiteral *Literal) { StringLength); if (auto *C = Entry.second) - return C; + return ConstantAddress(C, CharUnits::fromQuantity(C->getAlignment())); llvm::Constant *Zero = llvm::Constant::getNullValue(Int32Ty); llvm::Constant *Zeros[] = { Zero, Zero }; @@ -2658,7 +2897,7 @@ CodeGenModule::GetAddrOfConstantCFString(const StringLiteral *Literal) { // String pointer. llvm::Constant *C = nullptr; if (isUTF16) { - ArrayRef<uint16_t> Arr = llvm::makeArrayRef<uint16_t>( + auto Arr = llvm::makeArrayRef( reinterpret_cast<uint16_t *>(const_cast<char *>(Entry.first().data())), Entry.first().size() / 2); C = llvm::ConstantDataArray::get(VMContext, Arr); @@ -2699,25 +2938,28 @@ CodeGenModule::GetAddrOfConstantCFString(const StringLiteral *Literal) { Ty = getTypes().ConvertType(getContext().LongTy); Fields[3] = llvm::ConstantInt::get(Ty, StringLength); + CharUnits Alignment = getPointerAlign(); + // The struct. C = llvm::ConstantStruct::get(STy, Fields); GV = new llvm::GlobalVariable(getModule(), C->getType(), true, llvm::GlobalVariable::PrivateLinkage, C, "_unnamed_cfstring_"); GV->setSection("__DATA,__cfstring"); + GV->setAlignment(Alignment.getQuantity()); Entry.second = GV; - return GV; + return ConstantAddress(GV, Alignment); } -llvm::GlobalVariable * +ConstantAddress CodeGenModule::GetAddrOfConstantString(const StringLiteral *Literal) { unsigned StringLength = 0; llvm::StringMapEntry<llvm::GlobalVariable *> &Entry = GetConstantStringEntry(CFConstantStringMap, Literal, StringLength); if (auto *C = Entry.second) - return C; + return ConstantAddress(C, CharUnits::fromQuantity(C->getAlignment())); llvm::Constant *Zero = llvm::Constant::getNullValue(Int32Ty); llvm::Constant *Zeros[] = { Zero, Zero }; @@ -2810,10 +3052,12 @@ CodeGenModule::GetAddrOfConstantString(const StringLiteral *Literal) { Fields[2] = llvm::ConstantInt::get(Ty, StringLength); // The struct. + CharUnits Alignment = getPointerAlign(); C = llvm::ConstantStruct::get(NSConstantStringType, Fields); GV = new llvm::GlobalVariable(getModule(), C->getType(), true, llvm::GlobalVariable::PrivateLinkage, C, "_unnamed_nsstring_"); + GV->setAlignment(Alignment.getQuantity()); const char *NSStringSection = "__OBJC,__cstring_object,regular,no_dead_strip"; const char *NSStringNonFragileABISection = "__DATA,__objc_stringobj,regular,no_dead_strip"; @@ -2823,7 +3067,7 @@ CodeGenModule::GetAddrOfConstantString(const StringLiteral *Literal) { : NSStringSection); Entry.second = GV; - return GV; + return ConstantAddress(GV, Alignment); } QualType CodeGenModule::getObjCFastEnumerationStateType() { @@ -2902,7 +3146,7 @@ CodeGenModule::GetConstantArrayFromStringLiteral(const StringLiteral *E) { static llvm::GlobalVariable * GenerateStringLiteral(llvm::Constant *C, llvm::GlobalValue::LinkageTypes LT, CodeGenModule &CGM, StringRef GlobalName, - unsigned Alignment) { + CharUnits Alignment) { // OpenCL v1.2 s6.5.3: a string literal is in the constant address space. unsigned AddrSpace = 0; if (CGM.getLangOpts().OpenCL) @@ -2913,7 +3157,7 @@ GenerateStringLiteral(llvm::Constant *C, llvm::GlobalValue::LinkageTypes LT, auto *GV = new llvm::GlobalVariable( M, C->getType(), !CGM.getLangOpts().WritableStrings, LT, C, GlobalName, nullptr, llvm::GlobalVariable::NotThreadLocal, AddrSpace); - GV->setAlignment(Alignment); + GV->setAlignment(Alignment.getQuantity()); GV->setUnnamedAddr(true); if (GV->isWeakForLinker()) { assert(CGM.supportsCOMDAT() && "Only COFF uses weak string literals"); @@ -2925,20 +3169,19 @@ GenerateStringLiteral(llvm::Constant *C, llvm::GlobalValue::LinkageTypes LT, /// GetAddrOfConstantStringFromLiteral - Return a pointer to a /// constant array for the given string literal. -llvm::GlobalVariable * +ConstantAddress CodeGenModule::GetAddrOfConstantStringFromLiteral(const StringLiteral *S, StringRef Name) { - auto Alignment = - getContext().getAlignOfGlobalVarInChars(S->getType()).getQuantity(); + CharUnits Alignment = getContext().getAlignOfGlobalVarInChars(S->getType()); llvm::Constant *C = GetConstantArrayFromStringLiteral(S); llvm::GlobalVariable **Entry = nullptr; if (!LangOpts.WritableStrings) { Entry = &ConstantStringMap[C]; if (auto GV = *Entry) { - if (Alignment > GV->getAlignment()) - GV->setAlignment(Alignment); - return GV; + if (Alignment.getQuantity() > GV->getAlignment()) + GV->setAlignment(Alignment.getQuantity()); + return ConstantAddress(GV, Alignment); } } @@ -2954,7 +3197,6 @@ CodeGenModule::GetAddrOfConstantStringFromLiteral(const StringLiteral *S, getCXXABI().getMangleContext().shouldMangleStringLiteral(S)) { llvm::raw_svector_ostream Out(MangledNameBuffer); getCXXABI().getMangleContext().mangleStringLiteral(S, Out); - Out.flush(); LT = llvm::GlobalValue::LinkOnceODRLinkage; GlobalVariableName = MangledNameBuffer; @@ -2969,12 +3211,12 @@ CodeGenModule::GetAddrOfConstantStringFromLiteral(const StringLiteral *S, SanitizerMD->reportGlobalToASan(GV, S->getStrTokenLoc(0), "<string literal>", QualType()); - return GV; + return ConstantAddress(GV, Alignment); } /// GetAddrOfConstantStringFromObjCEncode - Return a pointer to a constant /// array for the given ObjCEncodeExpr node. -llvm::GlobalVariable * +ConstantAddress CodeGenModule::GetAddrOfConstantStringFromObjCEncode(const ObjCEncodeExpr *E) { std::string Str; getContext().getObjCEncodingForType(E->getEncodedType(), Str); @@ -2985,14 +3227,11 @@ CodeGenModule::GetAddrOfConstantStringFromObjCEncode(const ObjCEncodeExpr *E) { /// GetAddrOfConstantCString - Returns a pointer to a character array containing /// the literal and a terminating '\0' character. /// The result has pointer to array type. -llvm::GlobalVariable *CodeGenModule::GetAddrOfConstantCString( - const std::string &Str, const char *GlobalName, unsigned Alignment) { +ConstantAddress CodeGenModule::GetAddrOfConstantCString( + const std::string &Str, const char *GlobalName) { StringRef StrWithNull(Str.c_str(), Str.size() + 1); - if (Alignment == 0) { - Alignment = getContext() - .getAlignOfGlobalVarInChars(getContext().CharTy) - .getQuantity(); - } + CharUnits Alignment = + getContext().getAlignOfGlobalVarInChars(getContext().CharTy); llvm::Constant *C = llvm::ConstantDataArray::getString(getLLVMContext(), StrWithNull, false); @@ -3002,9 +3241,9 @@ llvm::GlobalVariable *CodeGenModule::GetAddrOfConstantCString( if (!LangOpts.WritableStrings) { Entry = &ConstantStringMap[C]; if (auto GV = *Entry) { - if (Alignment > GV->getAlignment()) - GV->setAlignment(Alignment); - return GV; + if (Alignment.getQuantity() > GV->getAlignment()) + GV->setAlignment(Alignment.getQuantity()); + return ConstantAddress(GV, Alignment); } } @@ -3016,10 +3255,10 @@ llvm::GlobalVariable *CodeGenModule::GetAddrOfConstantCString( GlobalName, Alignment); if (Entry) *Entry = GV; - return GV; + return ConstantAddress(GV, Alignment); } -llvm::Constant *CodeGenModule::GetAddrOfGlobalTemporary( +ConstantAddress CodeGenModule::GetAddrOfGlobalTemporary( const MaterializeTemporaryExpr *E, const Expr *Init) { assert((E->getStorageDuration() == SD_Static || E->getStorageDuration() == SD_Thread) && "not a global temporary"); @@ -3031,9 +3270,10 @@ llvm::Constant *CodeGenModule::GetAddrOfGlobalTemporary( if (Init == E->GetTemporaryExpr()) MaterializedType = E->getType(); - llvm::Constant *&Slot = MaterializedGlobalTemporaryMap[E]; - if (Slot) - return Slot; + CharUnits Align = getContext().getTypeAlignInChars(MaterializedType); + + if (llvm::Constant *Slot = MaterializedGlobalTemporaryMap[E]) + return ConstantAddress(Slot, Align); // FIXME: If an externally-visible declaration extends multiple temporaries, // we need to give each temporary the same name in every translation unit (and @@ -3042,7 +3282,6 @@ llvm::Constant *CodeGenModule::GetAddrOfGlobalTemporary( llvm::raw_svector_ostream Out(Name); getCXXABI().getMangleContext().mangleReferenceTemporary( VD, E->getManglingNumber(), Out); - Out.flush(); APValue *Value = nullptr; if (E->getStorageDuration() == SD_Static) { @@ -3098,14 +3337,13 @@ llvm::Constant *CodeGenModule::GetAddrOfGlobalTemporary( /*InsertBefore=*/nullptr, llvm::GlobalVariable::NotThreadLocal, AddrSpace); setGlobalVisibility(GV, VD); - GV->setAlignment( - getContext().getTypeAlignInChars(MaterializedType).getQuantity()); + GV->setAlignment(Align.getQuantity()); if (supportsCOMDAT() && GV->isWeakForLinker()) GV->setComdat(TheModule.getOrInsertComdat(GV->getName())); if (VD->getTLSKind()) setTLSMode(GV, *VD); - Slot = GV; - return GV; + MaterializedGlobalTemporaryMap[E] = GV; + return ConstantAddress(GV, Align); } /// EmitObjCPropertyImplementations - Emit information for synthesized @@ -3367,11 +3605,8 @@ void CodeGenModule::EmitTopLevelDecl(Decl *D) { auto *Import = cast<ImportDecl>(D); // Ignore import declarations that come from imported modules. - if (clang::Module *Owner = Import->getImportedOwningModule()) { - if (getLangOpts().CurrentModule.empty() || - Owner->getTopLevelModule()->Name == getLangOpts().CurrentModule) - break; - } + if (Import->getImportedOwningModule()) + break; if (CGDebugInfo *DI = getModuleDebugInfo()) DI->EmitImportDecl(*Import); @@ -3412,7 +3647,7 @@ void CodeGenModule::AddDeferredUnusedCoverageMapping(Decl *D) { case Decl::ObjCMethod: case Decl::CXXConstructor: case Decl::CXXDestructor: { - if (!cast<FunctionDecl>(D)->hasBody()) + if (!cast<FunctionDecl>(D)->doesThisDeclarationHaveABody()) return; auto I = DeferredEmptyCoverageMappingDecls.find(D); if (I == DeferredEmptyCoverageMappingDecls.end()) @@ -3541,10 +3776,12 @@ bool CodeGenModule::lookupRepresentativeDecl(StringRef MangledName, void CodeGenModule::EmitDeclMetadata() { llvm::NamedMDNode *GlobalMetadata = nullptr; - // StaticLocalDeclMap for (auto &I : MangledDeclNames) { llvm::GlobalValue *Addr = getModule().getNamedValue(I.second); - EmitGlobalDeclMetadata(*this, GlobalMetadata, I.first, Addr); + // Some mangled names don't necessarily have an associated GlobalValue + // in this module, e.g. if we mangled it for DebugInfo. + if (Addr) + EmitGlobalDeclMetadata(*this, GlobalMetadata, I.first, Addr); } } @@ -3562,7 +3799,7 @@ void CodeGenFunction::EmitDeclMetadata() { for (auto &I : LocalDeclMap) { const Decl *D = I.first; - llvm::Value *Addr = I.second; + llvm::Value *Addr = I.second.getPointer(); if (auto *Alloca = dyn_cast<llvm::AllocaInst>(Addr)) { llvm::Value *DAddr = GetPointerConstant(getLLVMContext(), D); Alloca->setMetadata( @@ -3643,12 +3880,6 @@ llvm::Constant *CodeGenModule::EmitUuidofInitializer(StringRef Uuid) { return llvm::ConstantStruct::getAnon(Fields); } -llvm::Constant * -CodeGenModule::getAddrOfCXXCatchHandlerType(QualType Ty, - QualType CatchHandlerType) { - return getCXXABI().getAddrOfCXXCatchHandlerType(Ty, CatchHandlerType); -} - llvm::Constant *CodeGenModule::GetAddrOfRTTIDescriptor(QualType Ty, bool ForEH) { // Return a bogus pointer if RTTI is disabled, unless it's for EH. @@ -3671,22 +3902,82 @@ void CodeGenModule::EmitOMPThreadPrivateDecl(const OMPThreadPrivateDecl *D) { VD->getAnyInitializer() && !VD->getAnyInitializer()->isConstantInitializer(getContext(), /*ForRef=*/false); + + Address Addr(GetAddrOfGlobalVar(VD), getContext().getDeclAlign(VD)); if (auto InitFunction = getOpenMPRuntime().emitThreadPrivateVarDefinition( - VD, GetAddrOfGlobalVar(VD), RefExpr->getLocStart(), PerformInit)) + VD, Addr, RefExpr->getLocStart(), PerformInit)) CXXGlobalInits.push_back(InitFunction); } } -llvm::MDTuple *CodeGenModule::CreateVTableBitSetEntry( - llvm::GlobalVariable *VTable, CharUnits Offset, const CXXRecordDecl *RD) { - std::string OutName; - llvm::raw_string_ostream Out(OutName); - getCXXABI().getMangleContext().mangleCXXVTableBitSet(RD, Out); +llvm::Metadata *CodeGenModule::CreateMetadataIdentifierForType(QualType T) { + llvm::Metadata *&InternalId = MetadataIdMap[T.getCanonicalType()]; + if (InternalId) + return InternalId; + + if (isExternallyVisible(T->getLinkage())) { + std::string OutName; + llvm::raw_string_ostream Out(OutName); + getCXXABI().getMangleContext().mangleTypeName(T, Out); + + InternalId = llvm::MDString::get(getLLVMContext(), Out.str()); + } else { + InternalId = llvm::MDNode::getDistinct(getLLVMContext(), + llvm::ArrayRef<llvm::Metadata *>()); + } + + return InternalId; +} +void CodeGenModule::CreateVTableBitSetEntry(llvm::NamedMDNode *BitsetsMD, + llvm::GlobalVariable *VTable, + CharUnits Offset, + const CXXRecordDecl *RD) { + llvm::Metadata *MD = + CreateMetadataIdentifierForType(QualType(RD->getTypeForDecl(), 0)); llvm::Metadata *BitsetOps[] = { - llvm::MDString::get(getLLVMContext(), Out.str()), - llvm::ConstantAsMetadata::get(VTable), + MD, llvm::ConstantAsMetadata::get(VTable), llvm::ConstantAsMetadata::get( llvm::ConstantInt::get(Int64Ty, Offset.getQuantity()))}; - return llvm::MDTuple::get(getLLVMContext(), BitsetOps); + BitsetsMD->addOperand(llvm::MDTuple::get(getLLVMContext(), BitsetOps)); + + if (CodeGenOpts.SanitizeCfiCrossDso) { + if (auto TypeId = CreateCfiIdForTypeMetadata(MD)) { + llvm::Metadata *BitsetOps2[] = { + llvm::ConstantAsMetadata::get(TypeId), + llvm::ConstantAsMetadata::get(VTable), + llvm::ConstantAsMetadata::get( + llvm::ConstantInt::get(Int64Ty, Offset.getQuantity()))}; + BitsetsMD->addOperand(llvm::MDTuple::get(getLLVMContext(), BitsetOps2)); + } + } +} + +// Fills in the supplied string map with the set of target features for the +// passed in function. +void CodeGenModule::getFunctionFeatureMap(llvm::StringMap<bool> &FeatureMap, + const FunctionDecl *FD) { + StringRef TargetCPU = Target.getTargetOpts().CPU; + if (const auto *TD = FD->getAttr<TargetAttr>()) { + // If we have a TargetAttr build up the feature map based on that. + TargetAttr::ParsedTargetAttr ParsedAttr = TD->parse(); + + // Make a copy of the features as passed on the command line into the + // beginning of the additional features from the function to override. + ParsedAttr.first.insert(ParsedAttr.first.begin(), + Target.getTargetOpts().FeaturesAsWritten.begin(), + Target.getTargetOpts().FeaturesAsWritten.end()); + + if (ParsedAttr.second != "") + TargetCPU = ParsedAttr.second; + + // Now populate the feature map, first with the TargetCPU which is either + // the default or a new one from the target attribute string. Then we'll use + // the passed in features (FeaturesAsWritten) along with the new ones from + // the attribute. + Target.initFeatureMap(FeatureMap, getDiags(), TargetCPU, ParsedAttr.first); + } else { + Target.initFeatureMap(FeatureMap, getDiags(), TargetCPU, + Target.getTargetOpts().Features); + } } |