When compiling a program with clang I observe the following in the LLVM IR:
Given the following function declaration:
declare i32 @atoi(i8*) #2
Which has the following attributes:
attributes #2 = { nounwind readonly "correctly-rounded-divide-sqrt-fp-math"="false" "disable-tail-calls"="false" "less-precise-fpmad"="false" "no-frame-pointer-elim"="true" "no-frame-pointer-elim-non-leaf" "no-infs-fp-math"="false" "no-nans-fp-math"="false" "no-signed-zeros-fp-math"="false" "no-trapping-math"="false" "stack-protector-buffer-size"="8" "target-cpu"="x86-64" "target-features"="+fxsr,+mmx,+sse,+sse2,+x87" "unsafe-fp-math"="false" "use-soft-float"="false" }
I can see that when the function is called:
%26 = call i32 @atoi(i8* %25) #5
More attributes get defined/re-defined for it:
attributes #5 = { nounwind readonly }
I know that the #2
attribute group contains "Function attributes" that can be added to a Function
with the addFnAttr(Attribute Attr)
method. I also know that there are "Return attributes" that I can add to a CallInst
with addAttribute(0, Attribute Attr)
as well as "Parameter attributes" that I can add with the same method or with an AttributeList
/Set
. This gives me, for example, %26 = call nounwind i32 @atoi(i8* nounwind %25)
.
But how are the attributes in the #5
attribute group added? What are they called? Are they different from the other kinds of attributes? Are they redundant in this case?