aboutsummaryrefslogtreecommitdiff
path: root/lib/CodeGen/CodeGenModule.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'lib/CodeGen/CodeGenModule.cpp')
-rw-r--r--lib/CodeGen/CodeGenModule.cpp687
1 files changed, 489 insertions, 198 deletions
diff --git a/lib/CodeGen/CodeGenModule.cpp b/lib/CodeGen/CodeGenModule.cpp
index c9c48c7628de..173b0dcba1c2 100644
--- a/lib/CodeGen/CodeGenModule.cpp
+++ b/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);
+ }
}