llvm.org GIT mirror llvm / e99f8be
PR12696: Attribute bits above 1<<30 are not encoded in bitcode Attribute bits above 1<<30 are now encoded correctly. Additionally, the encoding/decoding functionality has been hoisted to helper functions in Attributes.h in an effort to help the encoding/decoding to stay in sync with the Attribute bitcode definitions. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@157581 91177308-0d34-0410-b5e6-96231b3b80d8 Meador Inge 8 years ago
4 changed file(s) with 211 addition(s) and 26 deletion(s). Raw diff Collapse all Expand all
222222 return 1U << ((StackAlign.Raw() >> 26) - 1);
223223 }
224224
225 /// This returns an integer containing an encoding of all the
226 /// LLVM attributes found in the given attribute bitset. Any
227 /// change to this encoding is a breaking change to bitcode
228 /// compatibility.
229 inline uint64_t encodeLLVMAttributesForBitcode(Attributes Attrs) {
230 // FIXME: It doesn't make sense to store the alignment information as an
231 // expanded out value, we should store it as a log2 value. However, we can't
232 // just change that here without breaking bitcode compatibility. If this ever
233 // becomes a problem in practice, we should introduce new tag numbers in the
234 // bitcode file and have those tags use a more efficiently encoded alignment
235 // field.
236
237 // Store the alignment in the bitcode as a 16-bit raw value instead of a
238 // 5-bit log2 encoded value. Shift the bits above the alignment up by
239 // 11 bits.
240
241 uint64_t EncodedAttrs = Attrs.Raw() & 0xffff;
242 if (Attrs & Attribute::Alignment)
243 EncodedAttrs |= (1ull << 16) <<
244 (((Attrs & Attribute::Alignment).Raw()-1) >> 16);
245 EncodedAttrs |= (Attrs.Raw() & (0xfffull << 21)) << 11;
246
247 return EncodedAttrs;
248 }
249
250 /// This returns an attribute bitset containing the LLVM attributes
251 /// that have been decoded from the given integer. This function
252 /// must stay in sync with 'encodeLLVMAttributesForBitcode'.
253 inline Attributes decodeLLVMAttributesForBitcode(uint64_t EncodedAttrs) {
254 // The alignment is stored as a 16-bit raw value from bits 31--16.
255 // We shift the bits above 31 down by 11 bits.
256
257 unsigned Alignment = (EncodedAttrs & (0xffffull << 16)) >> 16;
258 assert((!Alignment || isPowerOf2_32(Alignment)) &&
259 "Alignment must be a power of two.");
260
261 Attributes Attrs(EncodedAttrs & 0xffff);
262 if (Alignment)
263 Attrs |= Attribute::constructAlignmentFromInt(Alignment);
264 Attrs |= Attributes((EncodedAttrs & (0xfffull << 32)) >> 11);
265
266 return Attrs;
267 }
268
225269
226270 /// The set of Attributes set in Attributes is converted to a
227271 /// string of equivalent mnemonics. This is, presumably, for writing out
462462 return Error("Invalid ENTRY record");
463463
464464 for (unsigned i = 0, e = Record.size(); i != e; i += 2) {
465 // FIXME: remove in LLVM 3.0
466 // The alignment is stored as a 16-bit raw value from bits 31--16.
467 // We shift the bits above 31 down by 11 bits.
468
469 unsigned Alignment = (Record[i+1] & (0xffffull << 16)) >> 16;
470 if (Alignment && !isPowerOf2_32(Alignment))
471 return Error("Alignment is not a power of two.");
472
473 Attributes ReconstitutedAttr(Record[i+1] & 0xffff);
474 if (Alignment)
475 ReconstitutedAttr |= Attribute::constructAlignmentFromInt(Alignment);
476 ReconstitutedAttr |=
477 Attributes((Record[i+1] & (0xffffull << 32)) >> 11);
478
465 Attributes ReconstitutedAttr =
466 Attribute::decodeLLVMAttributesForBitcode(Record[i+1]);
479467 Record[i+1] = ReconstitutedAttr.Raw();
480468 }
481469
176176 for (unsigned i = 0, e = A.getNumSlots(); i != e; ++i) {
177177 const AttributeWithIndex &PAWI = A.getSlot(i);
178178 Record.push_back(PAWI.Index);
179
180 // FIXME: remove in LLVM 3.0
181 // Store the alignment in the bitcode as a 16-bit raw value instead of a
182 // 5-bit log2 encoded value. Shift the bits above the alignment up by
183 // 11 bits.
184 uint64_t FauxAttr = PAWI.Attrs.Raw() & 0xffff;
185 if (PAWI.Attrs & Attribute::Alignment)
186 FauxAttr |= (1ull<<16)<<
187 (((PAWI.Attrs & Attribute::Alignment).Raw()-1) >> 16);
188 FauxAttr |= (PAWI.Attrs.Raw() & (0x3FFull << 21)) << 11;
189
190 Record.push_back(FauxAttr);
179 Record.push_back(Attribute::encodeLLVMAttributesForBitcode(PAWI.Attrs));
191180 }
192181
193182 Stream.EmitRecord(bitc::PARAMATTR_CODE_ENTRY, Record);
0 ; RUN: llvm-as < %s | llvm-dis | FileCheck %s
1 ; PR12696
2
3 define void @f1(i8 zeroext)
4 ; CHECK: define void @f1(i8 zeroext)
5 {
6 ret void;
7 }
8
9 define void @f2(i8 signext)
10 ; CHECK: define void @f2(i8 signext)
11 {
12 ret void;
13 }
14
15 define void @f3() noreturn
16 ; CHECK: define void @f3() noreturn
17 {
18 ret void;
19 }
20
21 define void @f4(i8 inreg)
22 ; CHECK: define void @f4(i8 inreg)
23 {
24 ret void;
25 }
26
27 define void @f5(i8* sret)
28 ; CHECK: define void @f5(i8* sret)
29 {
30 ret void;
31 }
32
33 define void @f6() nounwind
34 ; CHECK: define void @f6() nounwind
35 {
36 ret void;
37 }
38
39 define void @f7(i8* noalias)
40 ; CHECK: define void @f7(i8* noalias)
41 {
42 ret void;
43 }
44
45 define void @f8(i8* byval)
46 ; CHECK: define void @f8(i8* byval)
47 {
48 ret void;
49 }
50
51 define void @f9(i8* nest)
52 ; CHECK: define void @f9(i8* nest)
53 {
54 ret void;
55 }
56
57 define void @f10() readnone
58 ; CHECK: define void @f10() readnone
59 {
60 ret void;
61 }
62
63 define void @f11() readonly
64 ; CHECK: define void @f11() readonly
65 {
66 ret void;
67 }
68
69 define void @f12() noinline
70 ; CHECK: define void @f12() noinline
71 {
72 ret void;
73 }
74
75 define void @f13() alwaysinline
76 ; CHECK: define void @f13() alwaysinline
77 {
78 ret void;
79 }
80
81 define void @f14() optsize
82 ; CHECK: define void @f14() optsize
83 {
84 ret void;
85 }
86
87 define void @f15() ssp
88 ; CHECK: define void @f15() ssp
89 {
90 ret void;
91 }
92
93 define void @f16() sspreq
94 ; CHECK: define void @f16() sspreq
95 {
96 ret void;
97 }
98
99 define void @f17(i8 align 4)
100 ; CHECK: define void @f17(i8 align 4)
101 {
102 ret void;
103 }
104
105 define void @f18(i8* nocapture)
106 ; CHECK: define void @f18(i8* nocapture)
107 {
108 ret void;
109 }
110
111 define void @f19() noredzone
112 ; CHECK: define void @f19() noredzone
113 {
114 ret void;
115 }
116
117 define void @f20() noimplicitfloat
118 ; CHECK: define void @f20() noimplicitfloat
119 {
120 ret void;
121 }
122
123 define void @f21() naked
124 ; CHECK: define void @f21() naked
125 {
126 ret void;
127 }
128
129 define void @f22() inlinehint
130 ; CHECK: define void @f22() inlinehint
131 {
132 ret void;
133 }
134
135 define void @f23() alignstack(4)
136 ; CHECK: define void @f23() alignstack(4)
137 {
138 ret void;
139 }
140
141 define void @f24() returns_twice
142 ; CHECK: define void @f24() returns_twice
143 {
144 ret void;
145 }
146
147 define void @f25() uwtable
148 ; CHECK: define void @f25() uwtable
149 {
150 ret void;
151 }
152
153 define void @f26() nonlazybind
154 ; CHECK: define void @f26() nonlazybind
155 {
156 ret void;
157 }
158
159 define void @f27() address_safety
160 ; CHECK: define void @f27() address_safety
161 {
162 ret void;
163 }