summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/llvm/IR/Attributes.h15
-rw-r--r--lib/AsmParser/LLParser.cpp28
-rw-r--r--lib/AsmParser/LLParser.h8
-rw-r--r--lib/IR/Attributes.cpp3
4 files changed, 30 insertions, 24 deletions
diff --git a/include/llvm/IR/Attributes.h b/include/llvm/IR/Attributes.h
index 1b8195ff05..29eaec1d0d 100644
--- a/include/llvm/IR/Attributes.h
+++ b/include/llvm/IR/Attributes.h
@@ -41,13 +41,13 @@ class Type;
class Attribute {
public:
/// This enumeration lists the attributes that can be associated with
- /// parameters, function results or the function itself.
+ /// parameters, function results, or the function itself.
///
- /// Note: uwtable is about the ABI or the user mandating an entry in the
- /// unwind table. The nounwind attribute is about an exception passing by the
- /// function.
+ /// Note: The `uwtable' attribute is about the ABI or the user mandating an
+ /// entry in the unwind table. The `nounwind' attribute is about an exception
+ /// passing by the function.
///
- /// In a theoretical system that uses tables for profiling and sjlj for
+ /// In a theoretical system that uses tables for profiling and SjLj for
/// exceptions, they would be fully independent. In a normal system that uses
/// tables for both, the semantics are:
///
@@ -181,12 +181,11 @@ private:
friend class AttrBuilder;
friend class AttributeSetImpl;
- /// \brief The attributes that we are managing. This can be null to represent
+ /// \brief The attributes that we are managing. This can be null to represent
/// the empty attributes list.
AttributeSetImpl *pImpl;
- /// \brief The attributes for the specified index are returned. Attributes
- /// for the result are denoted with Idx = 0.
+ /// \brief The attributes for the specified index are returned.
AttributeSetNode *getAttributes(unsigned Idx) const;
/// \brief Create an AttributeSet with the specified parameters in it.
diff --git a/lib/AsmParser/LLParser.cpp b/lib/AsmParser/LLParser.cpp
index a38f9ea4db..491022245e 100644
--- a/lib/AsmParser/LLParser.cpp
+++ b/lib/AsmParser/LLParser.cpp
@@ -1472,6 +1472,7 @@ bool LLParser::ParseParameterList(SmallVectorImpl<ParamInfo> &ArgList,
if (ParseToken(lltok::lparen, "expected '(' in call"))
return true;
+ unsigned AttrIndex = 1;
while (Lex.getKind() != lltok::rparen) {
// If this isn't the first argument, we need a comma.
if (!ArgList.empty() &&
@@ -1489,8 +1490,9 @@ bool LLParser::ParseParameterList(SmallVectorImpl<ParamInfo> &ArgList,
// Otherwise, handle normal operands.
if (ParseOptionalParamAttrs(ArgAttrs) || ParseValue(ArgTy, V, PFS))
return true;
- ArgList.push_back(ParamInfo(ArgLoc, V, Attribute::get(V->getContext(),
- ArgAttrs)));
+ ArgList.push_back(ParamInfo(ArgLoc, V, AttributeSet::get(V->getContext(),
+ AttrIndex++,
+ ArgAttrs)));
}
Lex.Lex(); // Lex the ')'.
@@ -1539,9 +1541,10 @@ bool LLParser::ParseArgumentList(SmallVectorImpl<ArgInfo> &ArgList,
if (!FunctionType::isValidArgumentType(ArgTy))
return Error(TypeLoc, "invalid type for function argument");
+ unsigned AttrIndex = 1;
ArgList.push_back(ArgInfo(TypeLoc, ArgTy,
- Attribute::get(ArgTy->getContext(),
- Attrs), Name));
+ AttributeSet::get(ArgTy->getContext(),
+ AttrIndex++, Attrs), Name));
while (EatIfPresent(lltok::comma)) {
// Handle ... at end of arg list.
@@ -1568,7 +1571,8 @@ bool LLParser::ParseArgumentList(SmallVectorImpl<ArgInfo> &ArgList,
return Error(TypeLoc, "invalid type for function argument");
ArgList.push_back(ArgInfo(TypeLoc, ArgTy,
- Attribute::get(ArgTy->getContext(), Attrs),
+ AttributeSet::get(ArgTy->getContext(),
+ AttrIndex++, Attrs),
Name));
}
}
@@ -1593,7 +1597,7 @@ bool LLParser::ParseFunctionType(Type *&Result) {
for (unsigned i = 0, e = ArgList.size(); i != e; ++i) {
if (!ArgList[i].Name.empty())
return Error(ArgList[i].Loc, "argument name invalid in function type");
- if (ArgList[i].Attrs.hasAttributes())
+ if (ArgList[i].Attrs.hasAttributes(i + 1))
return Error(ArgList[i].Loc,
"argument attributes invalid in function type");
}
@@ -2822,8 +2826,8 @@ bool LLParser::ParseFunctionHeader(Function *&Fn, bool isDefine) {
for (unsigned i = 0, e = ArgList.size(); i != e; ++i) {
ParamTypeList.push_back(ArgList[i].Ty);
- if (ArgList[i].Attrs.hasAttributes()) {
- AttrBuilder B(ArgList[i].Attrs);
+ if (ArgList[i].Attrs.hasAttributes(i + 1)) {
+ AttrBuilder B(ArgList[i].Attrs, i + 1);
Attrs.push_back(AttributeSet::get(RetType->getContext(), i + 1, B));
}
}
@@ -3382,8 +3386,8 @@ bool LLParser::ParseInvoke(Instruction *&Inst, PerFunctionState &PFS) {
return Error(ArgList[i].Loc, "argument is not of expected type '" +
getTypeString(ExpectedTy) + "'");
Args.push_back(ArgList[i].V);
- if (ArgList[i].Attrs.hasAttributes()) {
- AttrBuilder B(ArgList[i].Attrs);
+ if (ArgList[i].Attrs.hasAttributes(i + 1)) {
+ AttrBuilder B(ArgList[i].Attrs, i + 1);
Attrs.push_back(AttributeSet::get(RetType->getContext(), i + 1, B));
}
}
@@ -3784,8 +3788,8 @@ bool LLParser::ParseCall(Instruction *&Inst, PerFunctionState &PFS,
return Error(ArgList[i].Loc, "argument is not of expected type '" +
getTypeString(ExpectedTy) + "'");
Args.push_back(ArgList[i].V);
- if (ArgList[i].Attrs.hasAttributes()) {
- AttrBuilder B(ArgList[i].Attrs);
+ if (ArgList[i].Attrs.hasAttributes(i + 1)) {
+ AttrBuilder B(ArgList[i].Attrs, i + 1);
Attrs.push_back(AttributeSet::get(RetType->getContext(), i + 1, B));
}
}
diff --git a/lib/AsmParser/LLParser.h b/lib/AsmParser/LLParser.h
index f255897ce3..d8de77908c 100644
--- a/lib/AsmParser/LLParser.h
+++ b/lib/AsmParser/LLParser.h
@@ -326,8 +326,8 @@ namespace llvm {
struct ParamInfo {
LocTy Loc;
Value *V;
- Attribute Attrs;
- ParamInfo(LocTy loc, Value *v, Attribute attrs)
+ AttributeSet Attrs;
+ ParamInfo(LocTy loc, Value *v, AttributeSet attrs)
: Loc(loc), V(v), Attrs(attrs) {}
};
bool ParseParameterList(SmallVectorImpl<ParamInfo> &ArgList,
@@ -347,9 +347,9 @@ namespace llvm {
struct ArgInfo {
LocTy Loc;
Type *Ty;
- Attribute Attrs;
+ AttributeSet Attrs;
std::string Name;
- ArgInfo(LocTy L, Type *ty, Attribute Attr, const std::string &N)
+ ArgInfo(LocTy L, Type *ty, AttributeSet Attr, const std::string &N)
: Loc(L), Ty(ty), Attrs(Attr), Name(N) {}
};
bool ParseArgumentList(SmallVectorImpl<ArgInfo> &ArgList, bool &isVarArg);
diff --git a/lib/IR/Attributes.cpp b/lib/IR/Attributes.cpp
index 75ba93a106..98c12b5d85 100644
--- a/lib/IR/Attributes.cpp
+++ b/lib/IR/Attributes.cpp
@@ -40,6 +40,9 @@ Attribute Attribute::get(LLVMContext &Context, AttrBuilder &B) {
if (!B.hasAttributes())
return Attribute();
+ assert(std::distance(B.begin(), B.end()) == 1 &&
+ "The Attribute object should represent one attribute only!");
+
// Otherwise, build a key to look up the existing attributes.
LLVMContextImpl *pImpl = Context.pImpl;
FoldingSetNodeID ID;