diff options
Diffstat (limited to 'clang/lib/CodeGen/CodeGenModule.cpp')
-rw-r--r-- | clang/lib/CodeGen/CodeGenModule.cpp | 47 |
1 files changed, 36 insertions, 11 deletions
diff --git a/clang/lib/CodeGen/CodeGenModule.cpp b/clang/lib/CodeGen/CodeGenModule.cpp index 76112e191c7..2654247b959 100644 --- a/clang/lib/CodeGen/CodeGenModule.cpp +++ b/clang/lib/CodeGen/CodeGenModule.cpp @@ -2399,9 +2399,22 @@ void CodeGenModule::EmitGlobalDefinition(GlobalDecl GD, llvm::GlobalValue *GV) { static void ReplaceUsesOfNonProtoTypeWithRealFunction(llvm::GlobalValue *Old, llvm::Function *NewFn); +static unsigned +TargetMVPriority(const TargetInfo &TI, + const CodeGenFunction::MultiVersionResolverOption &RO) { + unsigned Priority = 0; + for (StringRef Feat : RO.Conditions.Features) + Priority = std::max(Priority, TI.multiVersionSortPriority(Feat)); + + if (!RO.Conditions.Architecture.empty()) + Priority = std::max( + Priority, TI.multiVersionSortPriority(RO.Conditions.Architecture)); + return Priority; +} + void CodeGenModule::emitMultiVersionFunctions() { for (GlobalDecl GD : MultiVersionFuncs) { - SmallVector<CodeGenFunction::TargetMultiVersionResolverOption, 10> Options; + SmallVector<CodeGenFunction::MultiVersionResolverOption, 10> Options; const FunctionDecl *FD = cast<FunctionDecl>(GD.getDecl()); getContext().forEachMultiversionedFunctionVersion( FD, [this, &GD, &Options](const FunctionDecl *CurFD) { @@ -2422,8 +2435,13 @@ void CodeGenModule::emitMultiVersionFunctions() { } assert(Func && "This should have just been created"); } - Options.emplace_back(getTarget(), cast<llvm::Function>(Func), - CurFD->getAttr<TargetAttr>()->parse()); + + const auto *TA = CurFD->getAttr<TargetAttr>(); + llvm::SmallVector<StringRef, 8> Feats; + TA->getAddedFeatures(Feats); + + Options.emplace_back(cast<llvm::Function>(Func), + TA->getArchitecture(), Feats); }); llvm::Function *ResolverFunc = cast<llvm::Function>( @@ -2431,11 +2449,16 @@ void CodeGenModule::emitMultiVersionFunctions() { if (supportsCOMDAT()) ResolverFunc->setComdat( getModule().getOrInsertComdat(ResolverFunc->getName())); + + const TargetInfo &TI = getTarget(); std::stable_sort( Options.begin(), Options.end(), - std::greater<CodeGenFunction::TargetMultiVersionResolverOption>()); + [&TI](const CodeGenFunction::MultiVersionResolverOption &LHS, + const CodeGenFunction::MultiVersionResolverOption &RHS) { + return TargetMVPriority(TI, LHS) > TargetMVPriority(TI, RHS); + }); CodeGenFunction CGF(*this); - CGF.EmitTargetMultiVersionResolver(ResolverFunc, Options); + CGF.EmitMultiVersionResolver(ResolverFunc, Options); } } @@ -2455,8 +2478,7 @@ void CodeGenModule::emitCPUDispatchDefinition(GlobalDecl GD) { GetOrCreateLLVMFunction(ResolverName, ResolverType, GlobalDecl{}, /*ForVTable=*/false)); - SmallVector<CodeGenFunction::CPUDispatchMultiVersionResolverOption, 10> - Options; + SmallVector<CodeGenFunction::MultiVersionResolverOption, 10> Options; const TargetInfo &Target = getTarget(); for (const IdentifierInfo *II : DD->cpus()) { // Get the name of the target function so we can look it up/create it. @@ -2473,15 +2495,18 @@ void CodeGenModule::emitCPUDispatchDefinition(GlobalDecl GD) { Features.begin(), Features.end(), [&Target](StringRef Feat) { return !Target.validateCpuSupports(Feat); }), Features.end()); - Options.emplace_back(cast<llvm::Function>(Func), - CodeGenFunction::GetX86CpuSupportsMask(Features)); + Options.emplace_back(cast<llvm::Function>(Func), StringRef{}, Features); } llvm::sort( Options.begin(), Options.end(), - std::greater<CodeGenFunction::CPUDispatchMultiVersionResolverOption>()); + [](const CodeGenFunction::MultiVersionResolverOption &LHS, + const CodeGenFunction::MultiVersionResolverOption &RHS) { + return CodeGenFunction::GetX86CpuSupportsMask(LHS.Conditions.Features) > + CodeGenFunction::GetX86CpuSupportsMask(RHS.Conditions.Features); + }); CodeGenFunction CGF(*this); - CGF.EmitCPUDispatchMultiVersionResolver(ResolverFunc, Options); + CGF.EmitMultiVersionResolver(ResolverFunc, Options); } /// If an ifunc for the specified mangled name is not in the module, create and |