[Attributes] Fix a bug in AttributeList::get so it can handle a mix of FunctionIndex and ReturnIndex/arg indices at the same time

The code uses the index of the last element in the sorted array to determine the maximum size needed for the vector. But if the last index is a FunctionIndex(~0), attrIdxToArrayIdx will return 0 and the vector will have size 1. If there are any indices before FunctionIndex, those values would return a value larger than 0 from attrIdxToArrayIdx. So in this case we need to look in front of the FunctionIndex to get the true size needed.

Differential Revision: https://reviews.llvm.org/D45632

llvm-svn: 330136
This commit is contained in:
Craig Topper 2018-04-16 17:05:01 +00:00
parent 5a218694ff
commit 34799aaa25
2 changed files with 12 additions and 0 deletions

View File

@ -922,6 +922,10 @@ AttributeList::get(LLVMContext &C,
"Pointless attribute!");
unsigned MaxIndex = Attrs.back().first;
// If the MaxIndex is FunctionIndex and there are other indices in front
// of it, we need to use the largest of those to get the right size.
if (MaxIndex == FunctionIndex && Attrs.size() > 1)
MaxIndex = Attrs[Attrs.size() - 2].first;
SmallVector<AttributeSet, 4> AttrVec(attrIdxToArrayIdx(MaxIndex) + 1);
for (const auto Pair : Attrs)

View File

@ -159,4 +159,12 @@ TEST(Attributes, EmptyGet) {
EXPECT_TRUE(AL.isEmpty());
}
TEST(Attributes, OverflowGet) {
LLVMContext C;
std::pair<unsigned, Attribute> Attrs[] = { { AttributeList::ReturnIndex, Attribute::get(C, Attribute::SExt) },
{ AttributeList::FunctionIndex, Attribute::get(C, Attribute::ReadOnly) } };
AttributeList AL = AttributeList::get(C, Attrs);
EXPECT_EQ(2U, AL.getNumAttrSets());
}
} // end anonymous namespace