diff options
-rw-r--r-- | clang/include/clang/Basic/Attr.td | 25 | ||||
-rw-r--r-- | clang/lib/CodeGen/CGCall.cpp | 22 |
2 files changed, 18 insertions, 29 deletions
diff --git a/clang/include/clang/Basic/Attr.td b/clang/include/clang/Basic/Attr.td index 58d82ae326a..c765d08a3c2 100644 --- a/clang/include/clang/Basic/Attr.td +++ b/clang/include/clang/Basic/Attr.td @@ -1321,20 +1321,9 @@ def Target : InheritableAttr { let Subjects = SubjectList<[Function], ErrorDiag>; let Documentation = [TargetDocs]; let AdditionalMembers = [{ - StringRef CPU; - std::vector<std::string> Features; - bool Parsed = false; - StringRef getCPU() { - if (!Parsed) - parse(); - return CPU; - } - std::vector<std::string> &getFeatures() { - if (!Parsed) - parse(); - return Features; - } - void parse() { + typedef std::pair<std::vector<std::string>, StringRef> ParsedTargetAttr; + ParsedTargetAttr parse() const { + ParsedTargetAttr Ret; SmallVector<StringRef, 1> AttrFeatures; getFeaturesStr().split(AttrFeatures, ","); @@ -1354,13 +1343,13 @@ def Target : InheritableAttr { // While we're here iterating check for a different target cpu. if (Feature.startswith("arch=")) - CPU = Feature.split("=").second.trim(); + Ret.second = Feature.split("=").second.trim(); else if (Feature.startswith("no-")) - Features.push_back("-" + Feature.split("-").second.str()); + Ret.first.push_back("-" + Feature.split("-").second.str()); else - Features.push_back("+" + Feature.str()); + Ret.first.push_back("+" + Feature.str()); } - Parsed = true; + return Ret; } }]; } diff --git a/clang/lib/CodeGen/CGCall.cpp b/clang/lib/CodeGen/CGCall.cpp index ed7bf60c024..2dc68622e77 100644 --- a/clang/lib/CodeGen/CGCall.cpp +++ b/clang/lib/CodeGen/CGCall.cpp @@ -1499,24 +1499,24 @@ void CodeGenModule::ConstructAttributeList(const CGFunctionInfo &FI, const FunctionDecl *FD = dyn_cast_or_null<FunctionDecl>(TargetDecl); if (FD && FD->hasAttr<TargetAttr>()) { llvm::StringMap<bool> FeatureMap; - auto *TD = FD->getAttr<TargetAttr>(); + const auto *TD = FD->getAttr<TargetAttr>(); + TargetAttr::ParsedTargetAttr ParsedAttr = TD->parse(); - // Make a copy of the features as passed on the command line. - std::vector<std::string> FnFeatures = - getTarget().getTargetOpts().FeaturesAsWritten; + // 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(), + getTarget().getTargetOpts().FeaturesAsWritten.begin(), + getTarget().getTargetOpts().FeaturesAsWritten.end()); - std::vector<std::string> &AttrFeatures = TD->getFeatures(); - std::copy(AttrFeatures.begin(), AttrFeatures.end(), - std::back_inserter(FnFeatures)); - - if (TD->getCPU() != "") - TargetCPU = TD->getCPU(); + 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. - getTarget().initFeatureMap(FeatureMap, Diags, TargetCPU, FnFeatures); + getTarget().initFeatureMap(FeatureMap, Diags, TargetCPU, ParsedAttr.first); // Produce the canonical string for this set of features. std::vector<std::string> Features; |