1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31 package arm64
32
33 import (
34 "cmd/internal/obj"
35 "cmd/internal/objabi"
36 "fmt"
37 "log"
38 "math"
39 "sort"
40 "strings"
41 )
42
43
44
45
46 type ctxt7 struct {
47 ctxt *obj.Link
48 newprog obj.ProgAlloc
49 cursym *obj.LSym
50 blitrl *obj.Prog
51 elitrl *obj.Prog
52 autosize int32
53 extrasize int32
54 instoffset int64
55 pc int64
56 pool struct {
57 start uint32
58 size uint32
59 }
60 }
61
62 const (
63 funcAlign = 16
64 )
65
66 const (
67 REGFROM = 1
68 )
69
70 type Optab struct {
71 as obj.As
72 a1 uint8
73 a2 uint8
74 a3 uint8
75 a4 uint8
76 a5 uint8
77 type_ int8
78 size_ int8
79 param int16
80 flag int8
81 scond uint8
82 }
83
84 func IsAtomicInstruction(as obj.As) bool {
85 if _, ok := atomicLDADD[as]; ok {
86 return true
87 }
88 if _, ok := atomicSWP[as]; ok {
89 return true
90 }
91 return false
92 }
93
94
95 var atomicLDADD = map[obj.As]uint32{
96 ALDADDAD: 3<<30 | 0x1c5<<21 | 0x00<<10,
97 ALDADDAW: 2<<30 | 0x1c5<<21 | 0x00<<10,
98 ALDADDAH: 1<<30 | 0x1c5<<21 | 0x00<<10,
99 ALDADDAB: 0<<30 | 0x1c5<<21 | 0x00<<10,
100 ALDADDALD: 3<<30 | 0x1c7<<21 | 0x00<<10,
101 ALDADDALW: 2<<30 | 0x1c7<<21 | 0x00<<10,
102 ALDADDALH: 1<<30 | 0x1c7<<21 | 0x00<<10,
103 ALDADDALB: 0<<30 | 0x1c7<<21 | 0x00<<10,
104 ALDADDD: 3<<30 | 0x1c1<<21 | 0x00<<10,
105 ALDADDW: 2<<30 | 0x1c1<<21 | 0x00<<10,
106 ALDADDH: 1<<30 | 0x1c1<<21 | 0x00<<10,
107 ALDADDB: 0<<30 | 0x1c1<<21 | 0x00<<10,
108 ALDADDLD: 3<<30 | 0x1c3<<21 | 0x00<<10,
109 ALDADDLW: 2<<30 | 0x1c3<<21 | 0x00<<10,
110 ALDADDLH: 1<<30 | 0x1c3<<21 | 0x00<<10,
111 ALDADDLB: 0<<30 | 0x1c3<<21 | 0x00<<10,
112 ALDCLRAD: 3<<30 | 0x1c5<<21 | 0x04<<10,
113 ALDCLRAW: 2<<30 | 0x1c5<<21 | 0x04<<10,
114 ALDCLRAH: 1<<30 | 0x1c5<<21 | 0x04<<10,
115 ALDCLRAB: 0<<30 | 0x1c5<<21 | 0x04<<10,
116 ALDCLRALD: 3<<30 | 0x1c7<<21 | 0x04<<10,
117 ALDCLRALW: 2<<30 | 0x1c7<<21 | 0x04<<10,
118 ALDCLRALH: 1<<30 | 0x1c7<<21 | 0x04<<10,
119 ALDCLRALB: 0<<30 | 0x1c7<<21 | 0x04<<10,
120 ALDCLRD: 3<<30 | 0x1c1<<21 | 0x04<<10,
121 ALDCLRW: 2<<30 | 0x1c1<<21 | 0x04<<10,
122 ALDCLRH: 1<<30 | 0x1c1<<21 | 0x04<<10,
123 ALDCLRB: 0<<30 | 0x1c1<<21 | 0x04<<10,
124 ALDCLRLD: 3<<30 | 0x1c3<<21 | 0x04<<10,
125 ALDCLRLW: 2<<30 | 0x1c3<<21 | 0x04<<10,
126 ALDCLRLH: 1<<30 | 0x1c3<<21 | 0x04<<10,
127 ALDCLRLB: 0<<30 | 0x1c3<<21 | 0x04<<10,
128 ALDEORAD: 3<<30 | 0x1c5<<21 | 0x08<<10,
129 ALDEORAW: 2<<30 | 0x1c5<<21 | 0x08<<10,
130 ALDEORAH: 1<<30 | 0x1c5<<21 | 0x08<<10,
131 ALDEORAB: 0<<30 | 0x1c5<<21 | 0x08<<10,
132 ALDEORALD: 3<<30 | 0x1c7<<21 | 0x08<<10,
133 ALDEORALW: 2<<30 | 0x1c7<<21 | 0x08<<10,
134 ALDEORALH: 1<<30 | 0x1c7<<21 | 0x08<<10,
135 ALDEORALB: 0<<30 | 0x1c7<<21 | 0x08<<10,
136 ALDEORD: 3<<30 | 0x1c1<<21 | 0x08<<10,
137 ALDEORW: 2<<30 | 0x1c1<<21 | 0x08<<10,
138 ALDEORH: 1<<30 | 0x1c1<<21 | 0x08<<10,
139 ALDEORB: 0<<30 | 0x1c1<<21 | 0x08<<10,
140 ALDEORLD: 3<<30 | 0x1c3<<21 | 0x08<<10,
141 ALDEORLW: 2<<30 | 0x1c3<<21 | 0x08<<10,
142 ALDEORLH: 1<<30 | 0x1c3<<21 | 0x08<<10,
143 ALDEORLB: 0<<30 | 0x1c3<<21 | 0x08<<10,
144 ALDORAD: 3<<30 | 0x1c5<<21 | 0x0c<<10,
145 ALDORAW: 2<<30 | 0x1c5<<21 | 0x0c<<10,
146 ALDORAH: 1<<30 | 0x1c5<<21 | 0x0c<<10,
147 ALDORAB: 0<<30 | 0x1c5<<21 | 0x0c<<10,
148 ALDORALD: 3<<30 | 0x1c7<<21 | 0x0c<<10,
149 ALDORALW: 2<<30 | 0x1c7<<21 | 0x0c<<10,
150 ALDORALH: 1<<30 | 0x1c7<<21 | 0x0c<<10,
151 ALDORALB: 0<<30 | 0x1c7<<21 | 0x0c<<10,
152 ALDORD: 3<<30 | 0x1c1<<21 | 0x0c<<10,
153 ALDORW: 2<<30 | 0x1c1<<21 | 0x0c<<10,
154 ALDORH: 1<<30 | 0x1c1<<21 | 0x0c<<10,
155 ALDORB: 0<<30 | 0x1c1<<21 | 0x0c<<10,
156 ALDORLD: 3<<30 | 0x1c3<<21 | 0x0c<<10,
157 ALDORLW: 2<<30 | 0x1c3<<21 | 0x0c<<10,
158 ALDORLH: 1<<30 | 0x1c3<<21 | 0x0c<<10,
159 ALDORLB: 0<<30 | 0x1c3<<21 | 0x0c<<10,
160 }
161
162 var atomicSWP = map[obj.As]uint32{
163 ASWPAD: 3<<30 | 0x1c5<<21 | 0x20<<10,
164 ASWPAW: 2<<30 | 0x1c5<<21 | 0x20<<10,
165 ASWPAH: 1<<30 | 0x1c5<<21 | 0x20<<10,
166 ASWPAB: 0<<30 | 0x1c5<<21 | 0x20<<10,
167 ASWPALD: 3<<30 | 0x1c7<<21 | 0x20<<10,
168 ASWPALW: 2<<30 | 0x1c7<<21 | 0x20<<10,
169 ASWPALH: 1<<30 | 0x1c7<<21 | 0x20<<10,
170 ASWPALB: 0<<30 | 0x1c7<<21 | 0x20<<10,
171 ASWPD: 3<<30 | 0x1c1<<21 | 0x20<<10,
172 ASWPW: 2<<30 | 0x1c1<<21 | 0x20<<10,
173 ASWPH: 1<<30 | 0x1c1<<21 | 0x20<<10,
174 ASWPB: 0<<30 | 0x1c1<<21 | 0x20<<10,
175 ASWPLD: 3<<30 | 0x1c3<<21 | 0x20<<10,
176 ASWPLW: 2<<30 | 0x1c3<<21 | 0x20<<10,
177 ASWPLH: 1<<30 | 0x1c3<<21 | 0x20<<10,
178 ASWPLB: 0<<30 | 0x1c3<<21 | 0x20<<10,
179 ACASD: 3<<30 | 0x45<<21 | 0x1f<<10,
180 ACASW: 2<<30 | 0x45<<21 | 0x1f<<10,
181 ACASH: 1<<30 | 0x45<<21 | 0x1f<<10,
182 ACASB: 0<<30 | 0x45<<21 | 0x1f<<10,
183 ACASAD: 3<<30 | 0x47<<21 | 0x1f<<10,
184 ACASAW: 2<<30 | 0x47<<21 | 0x1f<<10,
185 ACASLD: 3<<30 | 0x45<<21 | 0x3f<<10,
186 ACASLW: 2<<30 | 0x45<<21 | 0x3f<<10,
187 ACASALD: 3<<30 | 0x47<<21 | 0x3f<<10,
188 ACASALW: 2<<30 | 0x47<<21 | 0x3f<<10,
189 ACASALH: 1<<30 | 0x47<<21 | 0x3f<<10,
190 ACASALB: 0<<30 | 0x47<<21 | 0x3f<<10,
191 }
192 var atomicCASP = map[obj.As]uint32{
193 ACASPD: 1<<30 | 0x41<<21 | 0x1f<<10,
194 ACASPW: 0<<30 | 0x41<<21 | 0x1f<<10,
195 }
196
197 var oprange [ALAST & obj.AMask][]Optab
198
199 var xcmp [C_NCLASS][C_NCLASS]bool
200
201 const (
202 S32 = 0 << 31
203 S64 = 1 << 31
204 Sbit = 1 << 29
205 LSL0_32 = 2 << 13
206 LSL0_64 = 3 << 13
207 )
208
209 func OPDP2(x uint32) uint32 {
210 return 0<<30 | 0<<29 | 0xd6<<21 | x<<10
211 }
212
213 func OPDP3(sf uint32, op54 uint32, op31 uint32, o0 uint32) uint32 {
214 return sf<<31 | op54<<29 | 0x1B<<24 | op31<<21 | o0<<15
215 }
216
217 func OPBcc(x uint32) uint32 {
218 return 0x2A<<25 | 0<<24 | 0<<4 | x&15
219 }
220
221 func OPBLR(x uint32) uint32 {
222
223 return 0x6B<<25 | 0<<23 | x<<21 | 0x1F<<16 | 0<<10
224 }
225
226 func SYSOP(l uint32, op0 uint32, op1 uint32, crn uint32, crm uint32, op2 uint32, rt uint32) uint32 {
227 return 0x354<<22 | l<<21 | op0<<19 | op1<<16 | crn&15<<12 | crm&15<<8 | op2<<5 | rt
228 }
229
230 func SYSHINT(x uint32) uint32 {
231 return SYSOP(0, 0, 3, 2, 0, x, 0x1F)
232 }
233
234 func LDSTR(sz uint32, v uint32, opc uint32) uint32 {
235 return sz<<30 | 7<<27 | v<<26 | opc<<22
236 }
237
238 func LD2STR(o uint32) uint32 {
239 return o &^ (3 << 22)
240 }
241
242 func LDSTX(sz uint32, o2 uint32, l uint32, o1 uint32, o0 uint32) uint32 {
243 return sz<<30 | 0x8<<24 | o2<<23 | l<<22 | o1<<21 | o0<<15
244 }
245
246 func FPCMP(m uint32, s uint32, type_ uint32, op uint32, op2 uint32) uint32 {
247 return m<<31 | s<<29 | 0x1E<<24 | type_<<22 | 1<<21 | op<<14 | 8<<10 | op2
248 }
249
250 func FPCCMP(m uint32, s uint32, type_ uint32, op uint32) uint32 {
251 return m<<31 | s<<29 | 0x1E<<24 | type_<<22 | 1<<21 | 1<<10 | op<<4
252 }
253
254 func FPOP1S(m uint32, s uint32, type_ uint32, op uint32) uint32 {
255 return m<<31 | s<<29 | 0x1E<<24 | type_<<22 | 1<<21 | op<<15 | 0x10<<10
256 }
257
258 func FPOP2S(m uint32, s uint32, type_ uint32, op uint32) uint32 {
259 return m<<31 | s<<29 | 0x1E<<24 | type_<<22 | 1<<21 | op<<12 | 2<<10
260 }
261
262 func FPOP3S(m uint32, s uint32, type_ uint32, op uint32, op2 uint32) uint32 {
263 return m<<31 | s<<29 | 0x1F<<24 | type_<<22 | op<<21 | op2<<15
264 }
265
266 func FPCVTI(sf uint32, s uint32, type_ uint32, rmode uint32, op uint32) uint32 {
267 return sf<<31 | s<<29 | 0x1E<<24 | type_<<22 | 1<<21 | rmode<<19 | op<<16 | 0<<10
268 }
269
270 func ADR(p uint32, o uint32, rt uint32) uint32 {
271 return p<<31 | (o&3)<<29 | 0x10<<24 | ((o>>2)&0x7FFFF)<<5 | rt&31
272 }
273
274 func OPBIT(x uint32) uint32 {
275 return 1<<30 | 0<<29 | 0xD6<<21 | 0<<16 | x<<10
276 }
277
278 func MOVCONST(d int64, s int, rt int) uint32 {
279 return uint32(((d>>uint(s*16))&0xFFFF)<<5) | uint32(s)&3<<21 | uint32(rt&31)
280 }
281
282 const (
283
284 LFROM = 1 << iota
285 LTO
286 NOTUSETMP
287 BRANCH14BITS
288 BRANCH19BITS
289 )
290
291 var optab = []Optab{
292
294 {obj.ATEXT, C_ADDR, C_NONE, C_NONE, C_TEXTSIZE, C_NONE, 0, 0, 0, 0, 0},
295
296
297 {AADD, C_ZREG, C_ZREG, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
298 {AADD, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
299 {AADC, C_ZREG, C_ZREG, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
300 {AADC, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
301 {ANEG, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 25, 4, 0, 0, 0},
302 {ANEG, C_NONE, C_NONE, C_NONE, C_ZREG, C_NONE, 25, 4, 0, 0, 0},
303 {ANGC, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 17, 4, 0, 0, 0},
304 {ACMP, C_ZREG, C_ZREG, C_NONE, C_NONE, C_NONE, 1, 4, 0, 0, 0},
305 {AADD, C_ADDCON, C_RSP, C_NONE, C_RSP, C_NONE, 2, 4, 0, 0, 0},
306 {AADD, C_ADDCON, C_NONE, C_NONE, C_RSP, C_NONE, 2, 4, 0, 0, 0},
307 {ACMP, C_ADDCON, C_RSP, C_NONE, C_NONE, C_NONE, 2, 4, 0, 0, 0},
308 {AADD, C_MOVCON, C_RSP, C_NONE, C_RSP, C_NONE, 62, 8, 0, 0, 0},
309 {AADD, C_MOVCON, C_NONE, C_NONE, C_RSP, C_NONE, 62, 8, 0, 0, 0},
310 {ACMP, C_MOVCON, C_RSP, C_NONE, C_NONE, C_NONE, 62, 8, 0, 0, 0},
311 {AADD, C_BITCON, C_RSP, C_NONE, C_RSP, C_NONE, 62, 8, 0, 0, 0},
312 {AADD, C_BITCON, C_NONE, C_NONE, C_RSP, C_NONE, 62, 8, 0, 0, 0},
313 {ACMP, C_BITCON, C_RSP, C_NONE, C_NONE, C_NONE, 62, 8, 0, 0, 0},
314 {AADD, C_ADDCON2, C_RSP, C_NONE, C_RSP, C_NONE, 48, 8, 0, NOTUSETMP, 0},
315 {AADD, C_ADDCON2, C_NONE, C_NONE, C_RSP, C_NONE, 48, 8, 0, NOTUSETMP, 0},
316 {AADD, C_MOVCON2, C_RSP, C_NONE, C_RSP, C_NONE, 13, 12, 0, 0, 0},
317 {AADD, C_MOVCON2, C_NONE, C_NONE, C_RSP, C_NONE, 13, 12, 0, 0, 0},
318 {AADD, C_MOVCON3, C_RSP, C_NONE, C_RSP, C_NONE, 13, 16, 0, 0, 0},
319 {AADD, C_MOVCON3, C_NONE, C_NONE, C_RSP, C_NONE, 13, 16, 0, 0, 0},
320 {AADD, C_VCON, C_RSP, C_NONE, C_RSP, C_NONE, 13, 20, 0, 0, 0},
321 {AADD, C_VCON, C_NONE, C_NONE, C_RSP, C_NONE, 13, 20, 0, 0, 0},
322 {ACMP, C_MOVCON2, C_ZREG, C_NONE, C_NONE, C_NONE, 13, 12, 0, 0, 0},
323 {ACMP, C_MOVCON3, C_ZREG, C_NONE, C_NONE, C_NONE, 13, 16, 0, 0, 0},
324 {ACMP, C_VCON, C_ZREG, C_NONE, C_NONE, C_NONE, 13, 20, 0, 0, 0},
325 {AADD, C_SHIFT, C_ZREG, C_NONE, C_ZREG, C_NONE, 3, 4, 0, 0, 0},
326 {AADD, C_SHIFT, C_NONE, C_NONE, C_ZREG, C_NONE, 3, 4, 0, 0, 0},
327 {AMVN, C_SHIFT, C_NONE, C_NONE, C_ZREG, C_NONE, 3, 4, 0, 0, 0},
328 {ACMP, C_SHIFT, C_ZREG, C_NONE, C_NONE, C_NONE, 3, 4, 0, 0, 0},
329 {ANEG, C_SHIFT, C_NONE, C_NONE, C_ZREG, C_NONE, 3, 4, 0, 0, 0},
330 {AADD, C_ZREG, C_RSP, C_NONE, C_RSP, C_NONE, 27, 4, 0, 0, 0},
331 {AADD, C_ZREG, C_NONE, C_NONE, C_RSP, C_NONE, 27, 4, 0, 0, 0},
332 {ACMP, C_ZREG, C_RSP, C_NONE, C_NONE, C_NONE, 27, 4, 0, 0, 0},
333 {AADD, C_EXTREG, C_RSP, C_NONE, C_RSP, C_NONE, 27, 4, 0, 0, 0},
334 {AADD, C_EXTREG, C_NONE, C_NONE, C_RSP, C_NONE, 27, 4, 0, 0, 0},
335 {ACMP, C_EXTREG, C_RSP, C_NONE, C_NONE, C_NONE, 27, 4, 0, 0, 0},
336 {AADD, C_ZREG, C_ZREG, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
337 {AADD, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
338 {AMUL, C_ZREG, C_ZREG, C_NONE, C_ZREG, C_NONE, 15, 4, 0, 0, 0},
339 {AMUL, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 15, 4, 0, 0, 0},
340 {AMADD, C_ZREG, C_ZREG, C_ZREG, C_ZREG, C_NONE, 15, 4, 0, 0, 0},
341 {AREM, C_ZREG, C_ZREG, C_NONE, C_ZREG, C_NONE, 16, 8, 0, 0, 0},
342 {AREM, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 16, 8, 0, 0, 0},
343 {ASDIV, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
344 {ASDIV, C_ZREG, C_ZREG, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
345
346 {AFADDS, C_FREG, C_NONE, C_NONE, C_FREG, C_NONE, 54, 4, 0, 0, 0},
347 {AFADDS, C_FREG, C_FREG, C_NONE, C_FREG, C_NONE, 54, 4, 0, 0, 0},
348 {AFMSUBD, C_FREG, C_FREG, C_FREG, C_FREG, C_NONE, 15, 4, 0, 0, 0},
349 {AFCMPS, C_FREG, C_FREG, C_NONE, C_NONE, C_NONE, 56, 4, 0, 0, 0},
350 {AFCMPS, C_FCON, C_FREG, C_NONE, C_NONE, C_NONE, 56, 4, 0, 0, 0},
351 {AVADDP, C_ARNG, C_ARNG, C_NONE, C_ARNG, C_NONE, 72, 4, 0, 0, 0},
352 {AVADD, C_ARNG, C_ARNG, C_NONE, C_ARNG, C_NONE, 72, 4, 0, 0, 0},
353 {AVADD, C_VREG, C_VREG, C_NONE, C_VREG, C_NONE, 89, 4, 0, 0, 0},
354 {AVADD, C_VREG, C_NONE, C_NONE, C_VREG, C_NONE, 89, 4, 0, 0, 0},
355 {AVADDV, C_ARNG, C_NONE, C_NONE, C_VREG, C_NONE, 85, 4, 0, 0, 0},
356
357
358 {AAND, C_ZREG, C_ZREG, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
359 {AAND, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
360 {AANDS, C_ZREG, C_ZREG, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
361 {AANDS, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 1, 4, 0, 0, 0},
362 {ATST, C_ZREG, C_ZREG, C_NONE, C_NONE, C_NONE, 1, 4, 0, 0, 0},
363 {AAND, C_MBCON, C_ZREG, C_NONE, C_RSP, C_NONE, 53, 4, 0, 0, 0},
364 {AAND, C_MBCON, C_NONE, C_NONE, C_RSP, C_NONE, 53, 4, 0, 0, 0},
365 {AANDS, C_MBCON, C_ZREG, C_NONE, C_ZREG, C_NONE, 53, 4, 0, 0, 0},
366 {AANDS, C_MBCON, C_NONE, C_NONE, C_ZREG, C_NONE, 53, 4, 0, 0, 0},
367 {ATST, C_MBCON, C_ZREG, C_NONE, C_NONE, C_NONE, 53, 4, 0, 0, 0},
368 {AAND, C_BITCON, C_ZREG, C_NONE, C_RSP, C_NONE, 53, 4, 0, 0, 0},
369 {AAND, C_BITCON, C_NONE, C_NONE, C_RSP, C_NONE, 53, 4, 0, 0, 0},
370 {AANDS, C_BITCON, C_ZREG, C_NONE, C_ZREG, C_NONE, 53, 4, 0, 0, 0},
371 {AANDS, C_BITCON, C_NONE, C_NONE, C_ZREG, C_NONE, 53, 4, 0, 0, 0},
372 {ATST, C_BITCON, C_ZREG, C_NONE, C_NONE, C_NONE, 53, 4, 0, 0, 0},
373 {AAND, C_MOVCON, C_ZREG, C_NONE, C_ZREG, C_NONE, 62, 8, 0, 0, 0},
374 {AAND, C_MOVCON, C_NONE, C_NONE, C_ZREG, C_NONE, 62, 8, 0, 0, 0},
375 {AANDS, C_MOVCON, C_ZREG, C_NONE, C_ZREG, C_NONE, 62, 8, 0, 0, 0},
376 {AANDS, C_MOVCON, C_NONE, C_NONE, C_ZREG, C_NONE, 62, 8, 0, 0, 0},
377 {ATST, C_MOVCON, C_ZREG, C_NONE, C_NONE, C_NONE, 62, 8, 0, 0, 0},
378 {AAND, C_MOVCON2, C_ZREG, C_NONE, C_ZREG, C_NONE, 28, 12, 0, 0, 0},
379 {AAND, C_MOVCON2, C_NONE, C_NONE, C_ZREG, C_NONE, 28, 12, 0, 0, 0},
380 {AAND, C_MOVCON3, C_ZREG, C_NONE, C_ZREG, C_NONE, 28, 16, 0, 0, 0},
381 {AAND, C_MOVCON3, C_NONE, C_NONE, C_ZREG, C_NONE, 28, 16, 0, 0, 0},
382 {AAND, C_VCON, C_ZREG, C_NONE, C_ZREG, C_NONE, 28, 20, 0, 0, 0},
383 {AAND, C_VCON, C_NONE, C_NONE, C_ZREG, C_NONE, 28, 20, 0, 0, 0},
384 {AANDS, C_MOVCON2, C_ZREG, C_NONE, C_ZREG, C_NONE, 28, 12, 0, 0, 0},
385 {AANDS, C_MOVCON2, C_NONE, C_NONE, C_ZREG, C_NONE, 28, 12, 0, 0, 0},
386 {AANDS, C_MOVCON3, C_ZREG, C_NONE, C_ZREG, C_NONE, 28, 16, 0, 0, 0},
387 {AANDS, C_MOVCON3, C_NONE, C_NONE, C_ZREG, C_NONE, 28, 16, 0, 0, 0},
388 {AANDS, C_VCON, C_ZREG, C_NONE, C_ZREG, C_NONE, 28, 20, 0, 0, 0},
389 {AANDS, C_VCON, C_NONE, C_NONE, C_ZREG, C_NONE, 28, 20, 0, 0, 0},
390 {ATST, C_MOVCON2, C_ZREG, C_NONE, C_NONE, C_NONE, 28, 12, 0, 0, 0},
391 {ATST, C_MOVCON3, C_ZREG, C_NONE, C_NONE, C_NONE, 28, 16, 0, 0, 0},
392 {ATST, C_VCON, C_ZREG, C_NONE, C_NONE, C_NONE, 28, 20, 0, 0, 0},
393 {AAND, C_SHIFT, C_ZREG, C_NONE, C_ZREG, C_NONE, 3, 4, 0, 0, 0},
394 {AAND, C_SHIFT, C_NONE, C_NONE, C_ZREG, C_NONE, 3, 4, 0, 0, 0},
395 {AANDS, C_SHIFT, C_ZREG, C_NONE, C_ZREG, C_NONE, 3, 4, 0, 0, 0},
396 {AANDS, C_SHIFT, C_NONE, C_NONE, C_ZREG, C_NONE, 3, 4, 0, 0, 0},
397 {ATST, C_SHIFT, C_ZREG, C_NONE, C_NONE, C_NONE, 3, 4, 0, 0, 0},
398 {AMOVD, C_RSP, C_NONE, C_NONE, C_RSP, C_NONE, 24, 4, 0, 0, 0},
399 {AMOVD, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 24, 4, 0, 0, 0},
400 {AMVN, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 24, 4, 0, 0, 0},
401 {AMOVB, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 45, 4, 0, 0, 0},
402 {AMOVH, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 45, 4, 0, 0, 0},
403 {AMOVW, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 45, 4, 0, 0, 0},
404
405
406
407 {AMOVW, C_MBCON, C_NONE, C_NONE, C_ZREG, C_NONE, 32, 4, 0, 0, 0},
408 {AMOVD, C_MBCON, C_NONE, C_NONE, C_ZREG, C_NONE, 32, 4, 0, 0, 0},
409 {AMOVW, C_MOVCON, C_NONE, C_NONE, C_ZREG, C_NONE, 32, 4, 0, 0, 0},
410 {AMOVD, C_MOVCON, C_NONE, C_NONE, C_ZREG, C_NONE, 32, 4, 0, 0, 0},
411 {AMOVW, C_BITCON, C_NONE, C_NONE, C_RSP, C_NONE, 32, 4, 0, 0, 0},
412 {AMOVD, C_BITCON, C_NONE, C_NONE, C_RSP, C_NONE, 32, 4, 0, 0, 0},
413 {AMOVW, C_MOVCON2, C_NONE, C_NONE, C_ZREG, C_NONE, 12, 8, 0, NOTUSETMP, 0},
414 {AMOVD, C_MOVCON2, C_NONE, C_NONE, C_ZREG, C_NONE, 12, 8, 0, NOTUSETMP, 0},
415 {AMOVD, C_MOVCON3, C_NONE, C_NONE, C_ZREG, C_NONE, 12, 12, 0, NOTUSETMP, 0},
416 {AMOVD, C_VCON, C_NONE, C_NONE, C_ZREG, C_NONE, 12, 16, 0, NOTUSETMP, 0},
417
418 {AMOVK, C_VCON, C_NONE, C_NONE, C_ZREG, C_NONE, 33, 4, 0, 0, 0},
419 {AMOVD, C_AACON, C_NONE, C_NONE, C_RSP, C_NONE, 4, 4, REGFROM, 0, 0},
420 {AMOVD, C_AACON2, C_NONE, C_NONE, C_RSP, C_NONE, 4, 8, REGFROM, NOTUSETMP, 0},
421
422
423 {AMOVD, C_LACON, C_NONE, C_NONE, C_RSP, C_NONE, 34, 8, REGSP, LFROM, 0},
424
425
426 {AVMOVS, C_ADDR, C_NONE, C_NONE, C_VREG, C_NONE, 65, 12, 0, 0, 0},
427 {AVMOVD, C_ADDR, C_NONE, C_NONE, C_VREG, C_NONE, 65, 12, 0, 0, 0},
428 {AVMOVQ, C_ADDR, C_NONE, C_NONE, C_VREG, C_NONE, 65, 12, 0, 0, 0},
429
430
431 {AB, C_NONE, C_NONE, C_NONE, C_SBRA, C_NONE, 5, 4, 0, 0, 0},
432 {ABL, C_NONE, C_NONE, C_NONE, C_SBRA, C_NONE, 5, 4, 0, 0, 0},
433 {AB, C_NONE, C_NONE, C_NONE, C_ZOREG, C_NONE, 6, 4, 0, 0, 0},
434 {ABL, C_NONE, C_NONE, C_NONE, C_ZREG, C_NONE, 6, 4, 0, 0, 0},
435 {ABL, C_NONE, C_NONE, C_NONE, C_ZOREG, C_NONE, 6, 4, 0, 0, 0},
436 {obj.ARET, C_NONE, C_NONE, C_NONE, C_ZREG, C_NONE, 6, 4, 0, 0, 0},
437 {obj.ARET, C_NONE, C_NONE, C_NONE, C_ZOREG, C_NONE, 6, 4, 0, 0, 0},
438 {ABEQ, C_NONE, C_NONE, C_NONE, C_SBRA, C_NONE, 7, 4, 0, BRANCH19BITS, 0},
439 {ACBZ, C_ZREG, C_NONE, C_NONE, C_SBRA, C_NONE, 39, 4, 0, BRANCH19BITS, 0},
440 {ATBZ, C_VCON, C_ZREG, C_NONE, C_SBRA, C_NONE, 40, 4, 0, BRANCH14BITS, 0},
441 {AERET, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 41, 4, 0, 0, 0},
442
443
444 {AADRP, C_SBRA, C_NONE, C_NONE, C_ZREG, C_NONE, 60, 4, 0, 0, 0},
445 {AADR, C_SBRA, C_NONE, C_NONE, C_ZREG, C_NONE, 61, 4, 0, 0, 0},
446
447 {ACLREX, C_NONE, C_NONE, C_NONE, C_VCON, C_NONE, 38, 4, 0, 0, 0},
448 {ACLREX, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 38, 4, 0, 0, 0},
449 {ABFM, C_VCON, C_ZREG, C_VCON, C_ZREG, C_NONE, 42, 4, 0, 0, 0},
450 {ABFI, C_VCON, C_ZREG, C_VCON, C_ZREG, C_NONE, 43, 4, 0, 0, 0},
451 {AEXTR, C_VCON, C_ZREG, C_ZREG, C_ZREG, C_NONE, 44, 4, 0, 0, 0},
452 {ASXTB, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 45, 4, 0, 0, 0},
453 {ACLS, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 46, 4, 0, 0, 0},
454 {ALSL, C_VCON, C_ZREG, C_NONE, C_ZREG, C_NONE, 8, 4, 0, 0, 0},
455 {ALSL, C_VCON, C_NONE, C_NONE, C_ZREG, C_NONE, 8, 4, 0, 0, 0},
456 {ALSL, C_ZREG, C_NONE, C_NONE, C_ZREG, C_NONE, 9, 4, 0, 0, 0},
457 {ALSL, C_ZREG, C_ZREG, C_NONE, C_ZREG, C_NONE, 9, 4, 0, 0, 0},
458 {ASVC, C_VCON, C_NONE, C_NONE, C_NONE, C_NONE, 10, 4, 0, 0, 0},
459 {ASVC, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 10, 4, 0, 0, 0},
460 {ADWORD, C_NONE, C_NONE, C_NONE, C_VCON, C_NONE, 11, 8, 0, NOTUSETMP, 0},
461 {ADWORD, C_NONE, C_NONE, C_NONE, C_LEXT, C_NONE, 11, 8, 0, NOTUSETMP, 0},
462 {ADWORD, C_NONE, C_NONE, C_NONE, C_ADDR, C_NONE, 11, 8, 0, NOTUSETMP, 0},
463 {ADWORD, C_NONE, C_NONE, C_NONE, C_LACON, C_NONE, 11, 8, 0, NOTUSETMP, 0},
464 {AWORD, C_NONE, C_NONE, C_NONE, C_LCON, C_NONE, 14, 4, 0, 0, 0},
465 {AWORD, C_NONE, C_NONE, C_NONE, C_LEXT, C_NONE, 14, 4, 0, 0, 0},
466 {AWORD, C_NONE, C_NONE, C_NONE, C_ADDR, C_NONE, 14, 4, 0, 0, 0},
467 {AMOVW, C_VCONADDR, C_NONE, C_NONE, C_ZREG, C_NONE, 68, 8, 0, NOTUSETMP, 0},
468 {AMOVD, C_VCONADDR, C_NONE, C_NONE, C_ZREG, C_NONE, 68, 8, 0, NOTUSETMP, 0},
469 {AMOVB, C_ZREG, C_NONE, C_NONE, C_ADDR, C_NONE, 64, 12, 0, 0, 0},
470 {AMOVH, C_ZREG, C_NONE, C_NONE, C_ADDR, C_NONE, 64, 12, 0, 0, 0},
471 {AMOVW, C_ZREG, C_NONE, C_NONE, C_ADDR, C_NONE, 64, 12, 0, 0, 0},
472 {AMOVD, C_ZREG, C_NONE, C_NONE, C_ADDR, C_NONE, 64, 12, 0, 0, 0},
473 {AMOVB, C_ADDR, C_NONE, C_NONE, C_ZREG, C_NONE, 65, 12, 0, 0, 0},
474 {AMOVH, C_ADDR, C_NONE, C_NONE, C_ZREG, C_NONE, 65, 12, 0, 0, 0},
475 {AMOVW, C_ADDR, C_NONE, C_NONE, C_ZREG, C_NONE, 65, 12, 0, 0, 0},
476 {AMOVD, C_ADDR, C_NONE, C_NONE, C_ZREG, C_NONE, 65, 12, 0, 0, 0},
477 {AMOVD, C_GOTADDR, C_NONE, C_NONE, C_ZREG, C_NONE, 71, 8, 0, 0, 0},
478 {AMOVD, C_TLS_LE, C_NONE, C_NONE, C_ZREG, C_NONE, 69, 4, 0, 0, 0},
479 {AMOVD, C_TLS_IE, C_NONE, C_NONE, C_ZREG, C_NONE, 70, 8, 0, 0, 0},
480
481 {AFMOVS, C_FREG, C_NONE, C_NONE, C_ADDR, C_NONE, 64, 12, 0, 0, 0},
482 {AFMOVS, C_ADDR, C_NONE, C_NONE, C_FREG, C_NONE, 65, 12, 0, 0, 0},
483 {AFMOVD, C_FREG, C_NONE, C_NONE, C_ADDR, C_NONE, 64, 12, 0, 0, 0},
484 {AFMOVD, C_ADDR, C_NONE, C_NONE, C_FREG, C_NONE, 65, 12, 0, 0, 0},
485 {AFMOVS, C_FCON, C_NONE, C_NONE, C_FREG, C_NONE, 55, 4, 0, 0, 0},
486 {AFMOVS, C_FREG, C_NONE, C_NONE, C_FREG, C_NONE, 54, 4, 0, 0, 0},
487 {AFMOVD, C_FCON, C_NONE, C_NONE, C_FREG, C_NONE, 55, 4, 0, 0, 0},
488 {AFMOVD, C_FREG, C_NONE, C_NONE, C_FREG, C_NONE, 54, 4, 0, 0, 0},
489 {AFMOVS, C_ZREG, C_NONE, C_NONE, C_FREG, C_NONE, 29, 4, 0, 0, 0},
490 {AFMOVS, C_FREG, C_NONE, C_NONE, C_ZREG, C_NONE, 29, 4, 0, 0, 0},
491 {AFMOVD, C_ZREG, C_NONE, C_NONE, C_FREG, C_NONE, 29, 4, 0, 0, 0},
492 {AFMOVD, C_FREG, C_NONE, C_NONE, C_ZREG, C_NONE, 29, 4, 0, 0, 0},
493 {AFCVTZSD, C_FREG, C_NONE, C_NONE, C_ZREG, C_NONE, 29, 4, 0, 0, 0},
494 {ASCVTFD, C_ZREG, C_NONE, C_NONE, C_FREG, C_NONE, 29, 4, 0, 0, 0},
495 {AFCVTSD, C_FREG, C_NONE, C_NONE, C_FREG, C_NONE, 29, 4, 0, 0, 0},
496 {AVMOV, C_ELEM, C_NONE, C_NONE, C_ZREG, C_NONE, 73, 4, 0, 0, 0},
497 {AVMOV, C_ELEM, C_NONE, C_NONE, C_ELEM, C_NONE, 92, 4, 0, 0, 0},
498 {AVMOV, C_ELEM, C_NONE, C_NONE, C_VREG, C_NONE, 80, 4, 0, 0, 0},
499 {AVMOV, C_ZREG, C_NONE, C_NONE, C_ARNG, C_NONE, 82, 4, 0, 0, 0},
500 {AVMOV, C_ZREG, C_NONE, C_NONE, C_ELEM, C_NONE, 78, 4, 0, 0, 0},
501 {AVMOV, C_ARNG, C_NONE, C_NONE, C_ARNG, C_NONE, 83, 4, 0, 0, 0},
502 {AVDUP, C_ELEM, C_NONE, C_NONE, C_ARNG, C_NONE, 79, 4, 0, 0, 0},
503 {AVDUP, C_ELEM, C_NONE, C_NONE, C_VREG, C_NONE, 80, 4, 0, 0, 0},
504 {AVDUP, C_ZREG, C_NONE, C_NONE, C_ARNG, C_NONE, 82, 4, 0, 0, 0},
505 {AVMOVI, C_ADDCON, C_NONE, C_NONE, C_ARNG, C_NONE, 86, 4, 0, 0, 0},
506 {AVFMLA, C_ARNG, C_ARNG, C_NONE, C_ARNG, C_NONE, 72, 4, 0, 0, 0},
507 {AVEXT, C_VCON, C_ARNG, C_ARNG, C_ARNG, C_NONE, 94, 4, 0, 0, 0},
508 {AVTBL, C_ARNG, C_NONE, C_LIST, C_ARNG, C_NONE, 100, 4, 0, 0, 0},
509 {AVUSHR, C_VCON, C_ARNG, C_NONE, C_ARNG, C_NONE, 95, 4, 0, 0, 0},
510 {AVZIP1, C_ARNG, C_ARNG, C_NONE, C_ARNG, C_NONE, 72, 4, 0, 0, 0},
511 {AVUSHLL, C_VCON, C_ARNG, C_NONE, C_ARNG, C_NONE, 102, 4, 0, 0, 0},
512 {AVUXTL, C_ARNG, C_NONE, C_NONE, C_ARNG, C_NONE, 102, 4, 0, 0, 0},
513 {AVUADDW, C_ARNG, C_ARNG, C_NONE, C_ARNG, C_NONE, 105, 4, 0, 0, 0},
514
515
516 {ACSEL, C_COND, C_ZREG, C_ZREG, C_ZREG, C_NONE, 18, 4, 0, 0, 0},
517 {ACINC, C_COND, C_ZREG, C_NONE, C_ZREG, C_NONE, 18, 4, 0, 0, 0},
518 {ACSET, C_COND, C_NONE, C_NONE, C_ZREG, C_NONE, 18, 4, 0, 0, 0},
519 {AFCSELD, C_COND, C_FREG, C_FREG, C_FREG, C_NONE, 18, 4, 0, 0, 0},
520 {ACCMN, C_COND, C_ZREG, C_ZREG, C_VCON, C_NONE, 19, 4, 0, 0, 0},
521 {ACCMN, C_COND, C_ZREG, C_VCON, C_VCON, C_NONE, 19, 4, 0, 0, 0},
522 {AFCCMPS, C_COND, C_FREG, C_FREG, C_VCON, C_NONE, 57, 4, 0, 0, 0},
523
524
525 {AMOVB, C_ZREG, C_NONE, C_NONE, C_UAUTO4K, C_NONE, 20, 4, REGSP, 0, 0},
526 {AMOVB, C_ZREG, C_NONE, C_NONE, C_UOREG4K, C_NONE, 20, 4, 0, 0, 0},
527 {AMOVH, C_ZREG, C_NONE, C_NONE, C_UAUTO8K, C_NONE, 20, 4, REGSP, 0, 0},
528 {AMOVH, C_ZREG, C_NONE, C_NONE, C_UOREG8K, C_NONE, 20, 4, 0, 0, 0},
529 {AMOVW, C_ZREG, C_NONE, C_NONE, C_UAUTO16K, C_NONE, 20, 4, REGSP, 0, 0},
530 {AMOVW, C_ZREG, C_NONE, C_NONE, C_UOREG16K, C_NONE, 20, 4, 0, 0, 0},
531 {AMOVD, C_ZREG, C_NONE, C_NONE, C_UAUTO32K, C_NONE, 20, 4, REGSP, 0, 0},
532 {AMOVD, C_ZREG, C_NONE, C_NONE, C_UOREG32K, C_NONE, 20, 4, 0, 0, 0},
533
534 {AFMOVS, C_FREG, C_NONE, C_NONE, C_UAUTO16K, C_NONE, 20, 4, REGSP, 0, 0},
535 {AFMOVS, C_FREG, C_NONE, C_NONE, C_UOREG16K, C_NONE, 20, 4, 0, 0, 0},
536 {AFMOVD, C_FREG, C_NONE, C_NONE, C_UAUTO32K, C_NONE, 20, 4, REGSP, 0, 0},
537 {AFMOVD, C_FREG, C_NONE, C_NONE, C_UOREG32K, C_NONE, 20, 4, 0, 0, 0},
538 {AFMOVQ, C_FREG, C_NONE, C_NONE, C_UAUTO64K, C_NONE, 20, 4, REGSP, 0, 0},
539 {AFMOVQ, C_FREG, C_NONE, C_NONE, C_UOREG64K, C_NONE, 20, 4, 0, 0, 0},
540
541
542 {AMOVB, C_ZREG, C_NONE, C_NONE, C_NSAUTO, C_NONE, 20, 4, REGSP, 0, 0},
543 {AMOVB, C_ZREG, C_NONE, C_NONE, C_NSOREG, C_NONE, 20, 4, 0, 0, 0},
544 {AMOVH, C_ZREG, C_NONE, C_NONE, C_NSAUTO, C_NONE, 20, 4, REGSP, 0, 0},
545 {AMOVH, C_ZREG, C_NONE, C_NONE, C_NSOREG, C_NONE, 20, 4, 0, 0, 0},
546 {AMOVW, C_ZREG, C_NONE, C_NONE, C_NSAUTO, C_NONE, 20, 4, REGSP, 0, 0},
547 {AMOVW, C_ZREG, C_NONE, C_NONE, C_NSOREG, C_NONE, 20, 4, 0, 0, 0},
548 {AMOVD, C_ZREG, C_NONE, C_NONE, C_NSAUTO, C_NONE, 20, 4, REGSP, 0, 0},
549 {AMOVD, C_ZREG, C_NONE, C_NONE, C_NSOREG, C_NONE, 20, 4, 0, 0, 0},
550
551 {AFMOVS, C_FREG, C_NONE, C_NONE, C_NSAUTO, C_NONE, 20, 4, REGSP, 0, 0},
552 {AFMOVS, C_FREG, C_NONE, C_NONE, C_NSOREG, C_NONE, 20, 4, 0, 0, 0},
553 {AFMOVD, C_FREG, C_NONE, C_NONE, C_NSAUTO, C_NONE, 20, 4, REGSP, 0, 0},
554 {AFMOVD, C_FREG, C_NONE, C_NONE, C_NSOREG, C_NONE, 20, 4, 0, 0, 0},
555 {AFMOVQ, C_FREG, C_NONE, C_NONE, C_NSAUTO, C_NONE, 20, 4, REGSP, 0, 0},
556 {AFMOVQ, C_FREG, C_NONE, C_NONE, C_NSOREG, C_NONE, 20, 4, 0, 0, 0},
557
558
559 {AMOVB, C_UAUTO4K, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, REGSP, 0, 0},
560 {AMOVB, C_UOREG4K, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, 0, 0, 0},
561 {AMOVH, C_UAUTO8K, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, REGSP, 0, 0},
562 {AMOVH, C_UOREG8K, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, 0, 0, 0},
563 {AMOVW, C_UAUTO16K, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, REGSP, 0, 0},
564 {AMOVW, C_UOREG16K, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, 0, 0, 0},
565 {AMOVD, C_UAUTO32K, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, REGSP, 0, 0},
566 {AMOVD, C_UOREG32K, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, 0, 0, 0},
567
568 {AFMOVS, C_UAUTO16K, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, REGSP, 0, 0},
569 {AFMOVS, C_UOREG16K, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, 0, 0, 0},
570 {AFMOVD, C_UAUTO32K, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, REGSP, 0, 0},
571 {AFMOVD, C_UOREG32K, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, 0, 0, 0},
572 {AFMOVQ, C_UAUTO64K, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, REGSP, 0, 0},
573 {AFMOVQ, C_UOREG64K, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, 0, 0, 0},
574
575
576 {AMOVB, C_NSAUTO, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, REGSP, 0, 0},
577 {AMOVB, C_NSOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, 0, 0, 0},
578 {AMOVH, C_NSAUTO, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, REGSP, 0, 0},
579 {AMOVH, C_NSOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, 0, 0, 0},
580 {AMOVW, C_NSAUTO, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, REGSP, 0, 0},
581 {AMOVW, C_NSOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, 0, 0, 0},
582 {AMOVD, C_NSAUTO, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, REGSP, 0, 0},
583 {AMOVD, C_NSOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 21, 4, 0, 0, 0},
584
585 {AFMOVS, C_NSAUTO, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, REGSP, 0, 0},
586 {AFMOVS, C_NSOREG, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, 0, 0, 0},
587 {AFMOVD, C_NSAUTO, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, REGSP, 0, 0},
588 {AFMOVD, C_NSOREG, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, 0, 0, 0},
589 {AFMOVQ, C_NSAUTO, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, REGSP, 0, 0},
590 {AFMOVQ, C_NSOREG, C_NONE, C_NONE, C_FREG, C_NONE, 21, 4, 0, 0, 0},
591
592
593 {AMOVB, C_ZREG, C_NONE, C_NONE, C_LAUTO, C_NONE, 30, 8, REGSP, 0, 0},
594 {AMOVB, C_ZREG, C_NONE, C_NONE, C_LAUTOPOOL, C_NONE, 30, 8, REGSP, LTO, 0},
595 {AMOVB, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 30, 8, 0, 0, 0},
596 {AMOVB, C_ZREG, C_NONE, C_NONE, C_LOREGPOOL, C_NONE, 30, 8, 0, LTO, 0},
597 {AMOVH, C_ZREG, C_NONE, C_NONE, C_LAUTO, C_NONE, 30, 8, REGSP, 0, 0},
598 {AMOVH, C_ZREG, C_NONE, C_NONE, C_LAUTOPOOL, C_NONE, 30, 8, REGSP, LTO, 0},
599 {AMOVH, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 30, 8, 0, 0, 0},
600 {AMOVH, C_ZREG, C_NONE, C_NONE, C_LOREGPOOL, C_NONE, 30, 8, 0, LTO, 0},
601 {AMOVW, C_ZREG, C_NONE, C_NONE, C_LAUTO, C_NONE, 30, 8, REGSP, 0, 0},
602 {AMOVW, C_ZREG, C_NONE, C_NONE, C_LAUTOPOOL, C_NONE, 30, 8, REGSP, LTO, 0},
603 {AMOVW, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 30, 8, 0, 0, 0},
604 {AMOVW, C_ZREG, C_NONE, C_NONE, C_LOREGPOOL, C_NONE, 30, 8, 0, LTO, 0},
605 {AMOVD, C_ZREG, C_NONE, C_NONE, C_LAUTO, C_NONE, 30, 8, REGSP, 0, 0},
606 {AMOVD, C_ZREG, C_NONE, C_NONE, C_LAUTOPOOL, C_NONE, 30, 8, REGSP, LTO, 0},
607 {AMOVD, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 30, 8, 0, 0, 0},
608 {AMOVD, C_ZREG, C_NONE, C_NONE, C_LOREGPOOL, C_NONE, 30, 8, 0, LTO, 0},
609
610 {AFMOVS, C_FREG, C_NONE, C_NONE, C_LAUTO, C_NONE, 30, 8, REGSP, 0, 0},
611 {AFMOVS, C_FREG, C_NONE, C_NONE, C_LAUTOPOOL, C_NONE, 30, 8, REGSP, LTO, 0},
612 {AFMOVS, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 30, 8, 0, 0, 0},
613 {AFMOVS, C_FREG, C_NONE, C_NONE, C_LOREGPOOL, C_NONE, 30, 8, 0, LTO, 0},
614 {AFMOVD, C_FREG, C_NONE, C_NONE, C_LAUTO, C_NONE, 30, 8, REGSP, 0, 0},
615 {AFMOVD, C_FREG, C_NONE, C_NONE, C_LAUTOPOOL, C_NONE, 30, 8, REGSP, LTO, 0},
616 {AFMOVD, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 30, 8, 0, 0, 0},
617 {AFMOVD, C_FREG, C_NONE, C_NONE, C_LOREGPOOL, C_NONE, 30, 8, 0, LTO, 0},
618 {AFMOVQ, C_FREG, C_NONE, C_NONE, C_LAUTO, C_NONE, 30, 8, REGSP, 0, 0},
619 {AFMOVQ, C_FREG, C_NONE, C_NONE, C_LAUTOPOOL, C_NONE, 30, 8, REGSP, LTO, 0},
620 {AFMOVQ, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 30, 8, 0, 0, 0},
621 {AFMOVQ, C_FREG, C_NONE, C_NONE, C_LOREGPOOL, C_NONE, 30, 8, 0, LTO, 0},
622
623
624 {AMOVB, C_LAUTO, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, REGSP, 0, 0},
625 {AMOVB, C_LAUTOPOOL, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, REGSP, LFROM, 0},
626 {AMOVB, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, 0, 0, 0},
627 {AMOVB, C_LOREGPOOL, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, 0, LFROM, 0},
628 {AMOVH, C_LAUTO, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, REGSP, 0, 0},
629 {AMOVH, C_LAUTOPOOL, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, REGSP, LFROM, 0},
630 {AMOVH, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, 0, 0, 0},
631 {AMOVH, C_LOREGPOOL, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, 0, LFROM, 0},
632 {AMOVW, C_LAUTO, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, REGSP, 0, 0},
633 {AMOVW, C_LAUTOPOOL, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, REGSP, LFROM, 0},
634 {AMOVW, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, 0, 0, 0},
635 {AMOVW, C_LOREGPOOL, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, 0, LFROM, 0},
636 {AMOVD, C_LAUTO, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, REGSP, 0, 0},
637 {AMOVD, C_LAUTOPOOL, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, REGSP, LFROM, 0},
638 {AMOVD, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, 0, 0, 0},
639 {AMOVD, C_LOREGPOOL, C_NONE, C_NONE, C_ZREG, C_NONE, 31, 8, 0, LFROM, 0},
640
641 {AFMOVS, C_LAUTO, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, REGSP, 0, 0},
642 {AFMOVS, C_LAUTOPOOL, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, REGSP, LFROM, 0},
643 {AFMOVS, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, 0, 0, 0},
644 {AFMOVS, C_LOREGPOOL, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, 0, LFROM, 0},
645 {AFMOVD, C_LAUTO, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, REGSP, 0, 0},
646 {AFMOVD, C_LAUTOPOOL, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, REGSP, LFROM, 0},
647 {AFMOVD, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, 0, 0, 0},
648 {AFMOVD, C_LOREGPOOL, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, 0, LFROM, 0},
649 {AFMOVQ, C_LAUTO, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, REGSP, 0, 0},
650 {AFMOVQ, C_LAUTOPOOL, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, REGSP, LFROM, 0},
651 {AFMOVQ, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, 0, 0, 0},
652 {AFMOVQ, C_LOREGPOOL, C_NONE, C_NONE, C_FREG, C_NONE, 31, 8, 0, LFROM, 0},
653
654
655 {AMOVD, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 22, 4, 0, 0, C_XPOST},
656 {AMOVW, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 22, 4, 0, 0, C_XPOST},
657 {AMOVH, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 22, 4, 0, 0, C_XPOST},
658 {AMOVB, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 22, 4, 0, 0, C_XPOST},
659 {AFMOVS, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 22, 4, 0, 0, C_XPOST},
660 {AFMOVD, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 22, 4, 0, 0, C_XPOST},
661 {AFMOVQ, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 22, 4, 0, 0, C_XPOST},
662
663 {AMOVD, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 22, 4, 0, 0, C_XPRE},
664 {AMOVW, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 22, 4, 0, 0, C_XPRE},
665 {AMOVH, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 22, 4, 0, 0, C_XPRE},
666 {AMOVB, C_LOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 22, 4, 0, 0, C_XPRE},
667 {AFMOVS, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 22, 4, 0, 0, C_XPRE},
668 {AFMOVD, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 22, 4, 0, 0, C_XPRE},
669 {AFMOVQ, C_LOREG, C_NONE, C_NONE, C_FREG, C_NONE, 22, 4, 0, 0, C_XPRE},
670
671
672 {AMOVD, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPOST},
673 {AMOVW, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPOST},
674 {AMOVH, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPOST},
675 {AMOVB, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPOST},
676 {AFMOVS, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPOST},
677 {AFMOVD, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPOST},
678 {AFMOVQ, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPOST},
679
680 {AMOVD, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPRE},
681 {AMOVW, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPRE},
682 {AMOVH, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPRE},
683 {AMOVB, C_ZREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPRE},
684 {AFMOVS, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPRE},
685 {AFMOVD, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPRE},
686 {AFMOVQ, C_FREG, C_NONE, C_NONE, C_LOREG, C_NONE, 23, 4, 0, 0, C_XPRE},
687
688
689 {AMOVD, C_ROFF, C_NONE, C_NONE, C_ZREG, C_NONE, 98, 4, 0, 0, 0},
690 {AMOVW, C_ROFF, C_NONE, C_NONE, C_ZREG, C_NONE, 98, 4, 0, 0, 0},
691 {AMOVH, C_ROFF, C_NONE, C_NONE, C_ZREG, C_NONE, 98, 4, 0, 0, 0},
692 {AMOVB, C_ROFF, C_NONE, C_NONE, C_ZREG, C_NONE, 98, 4, 0, 0, 0},
693 {AFMOVS, C_ROFF, C_NONE, C_NONE, C_FREG, C_NONE, 98, 4, 0, 0, 0},
694 {AFMOVD, C_ROFF, C_NONE, C_NONE, C_FREG, C_NONE, 98, 4, 0, 0, 0},
695
696
697 {AMOVD, C_ZREG, C_NONE, C_NONE, C_ROFF, C_NONE, 99, 4, 0, 0, 0},
698 {AMOVW, C_ZREG, C_NONE, C_NONE, C_ROFF, C_NONE, 99, 4, 0, 0, 0},
699 {AMOVH, C_ZREG, C_NONE, C_NONE, C_ROFF, C_NONE, 99, 4, 0, 0, 0},
700 {AMOVB, C_ZREG, C_NONE, C_NONE, C_ROFF, C_NONE, 99, 4, 0, 0, 0},
701 {AFMOVS, C_FREG, C_NONE, C_NONE, C_ROFF, C_NONE, 99, 4, 0, 0, 0},
702 {AFMOVD, C_FREG, C_NONE, C_NONE, C_ROFF, C_NONE, 99, 4, 0, 0, 0},
703
704
709 {AFLDPQ, C_NQAUTO_16, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, REGSP, 0, 0},
710 {AFLDPQ, C_PQAUTO_16, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, REGSP, 0, 0},
711 {AFLDPQ, C_UAUTO4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, REGSP, 0, 0},
712 {AFLDPQ, C_NAUTO4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, REGSP, 0, 0},
713 {AFLDPQ, C_LAUTO, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, REGSP, 0, 0},
714 {AFLDPQ, C_LAUTOPOOL, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, REGSP, LFROM, 0},
715 {AFLDPQ, C_NQOREG_16, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, 0},
716 {AFLDPQ, C_NQOREG_16, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPRE},
717 {AFLDPQ, C_NQOREG_16, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPOST},
718 {AFLDPQ, C_PQOREG_16, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, 0},
719 {AFLDPQ, C_PQOREG_16, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPRE},
720 {AFLDPQ, C_PQOREG_16, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPOST},
721 {AFLDPQ, C_UOREG4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, 0, 0, 0},
722 {AFLDPQ, C_NOREG4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, 0, 0, 0},
723 {AFLDPQ, C_LOREG, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, 0, 0, 0},
724 {AFLDPQ, C_LOREGPOOL, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, 0, LFROM, 0},
725 {AFLDPQ, C_ADDR, C_NONE, C_NONE, C_PAIR, C_NONE, 88, 12, 0, 0, 0},
726
727 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_NQAUTO_16, C_NONE, 67, 4, REGSP, 0, 0},
728 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_PQAUTO_16, C_NONE, 67, 4, REGSP, 0, 0},
729 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_UAUTO4K, C_NONE, 76, 8, REGSP, 0, 0},
730 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_NAUTO4K, C_NONE, 76, 8, REGSP, 0, 0},
731 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_LAUTO, C_NONE, 77, 12, REGSP, 0, 0},
732 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_LAUTOPOOL, C_NONE, 77, 12, REGSP, LTO, 0},
733 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_NQOREG_16, C_NONE, 67, 4, 0, 0, 0},
734 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_NQOREG_16, C_NONE, 67, 4, 0, 0, C_XPRE},
735 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_NQOREG_16, C_NONE, 67, 4, 0, 0, C_XPOST},
736 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_PQOREG_16, C_NONE, 67, 4, 0, 0, 0},
737 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_PQOREG_16, C_NONE, 67, 4, 0, 0, C_XPRE},
738 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_PQOREG_16, C_NONE, 67, 4, 0, 0, C_XPOST},
739 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_UOREG4K, C_NONE, 76, 8, 0, 0, 0},
740 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_NOREG4K, C_NONE, 76, 8, 0, 0, 0},
741 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_LOREG, C_NONE, 77, 12, 0, 0, 0},
742 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_LOREGPOOL, C_NONE, 77, 12, 0, LTO, 0},
743 {AFSTPQ, C_PAIR, C_NONE, C_NONE, C_ADDR, C_NONE, 87, 12, 0, 0, 0},
744
745 {ALDP, C_NPAUTO, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, REGSP, 0, 0},
746 {ALDP, C_PPAUTO, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, REGSP, 0, 0},
747 {ALDP, C_UAUTO4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, REGSP, 0, 0},
748 {ALDP, C_NAUTO4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, REGSP, 0, 0},
749 {ALDP, C_LAUTO, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, REGSP, 0, 0},
750 {ALDP, C_LAUTOPOOL, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, REGSP, LFROM, 0},
751 {ALDP, C_NPOREG, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, 0},
752 {ALDP, C_NPOREG, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPRE},
753 {ALDP, C_NPOREG, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPOST},
754 {ALDP, C_PPOREG, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, 0},
755 {ALDP, C_PPOREG, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPRE},
756 {ALDP, C_PPOREG, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPOST},
757 {ALDP, C_UOREG4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, 0, 0, 0},
758 {ALDP, C_NOREG4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, 0, 0, 0},
759 {ALDP, C_LOREG, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, 0, 0, 0},
760 {ALDP, C_LOREGPOOL, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, 0, LFROM, 0},
761 {ALDP, C_ADDR, C_NONE, C_NONE, C_PAIR, C_NONE, 88, 12, 0, 0, 0},
762
763 {ASTP, C_PAIR, C_NONE, C_NONE, C_NPAUTO, C_NONE, 67, 4, REGSP, 0, 0},
764 {ASTP, C_PAIR, C_NONE, C_NONE, C_PPAUTO, C_NONE, 67, 4, REGSP, 0, 0},
765 {ASTP, C_PAIR, C_NONE, C_NONE, C_UAUTO4K, C_NONE, 76, 8, REGSP, 0, 0},
766 {ASTP, C_PAIR, C_NONE, C_NONE, C_NAUTO4K, C_NONE, 76, 8, REGSP, 0, 0},
767 {ASTP, C_PAIR, C_NONE, C_NONE, C_LAUTO, C_NONE, 77, 12, REGSP, 0, 0},
768 {ASTP, C_PAIR, C_NONE, C_NONE, C_LAUTOPOOL, C_NONE, 77, 12, REGSP, LTO, 0},
769 {ASTP, C_PAIR, C_NONE, C_NONE, C_NPOREG, C_NONE, 67, 4, 0, 0, 0},
770 {ASTP, C_PAIR, C_NONE, C_NONE, C_NPOREG, C_NONE, 67, 4, 0, 0, C_XPRE},
771 {ASTP, C_PAIR, C_NONE, C_NONE, C_NPOREG, C_NONE, 67, 4, 0, 0, C_XPOST},
772 {ASTP, C_PAIR, C_NONE, C_NONE, C_PPOREG, C_NONE, 67, 4, 0, 0, 0},
773 {ASTP, C_PAIR, C_NONE, C_NONE, C_PPOREG, C_NONE, 67, 4, 0, 0, C_XPRE},
774 {ASTP, C_PAIR, C_NONE, C_NONE, C_PPOREG, C_NONE, 67, 4, 0, 0, C_XPOST},
775 {ASTP, C_PAIR, C_NONE, C_NONE, C_UOREG4K, C_NONE, 76, 8, 0, 0, 0},
776 {ASTP, C_PAIR, C_NONE, C_NONE, C_NOREG4K, C_NONE, 76, 8, 0, 0, 0},
777 {ASTP, C_PAIR, C_NONE, C_NONE, C_LOREG, C_NONE, 77, 12, 0, 0, 0},
778 {ASTP, C_PAIR, C_NONE, C_NONE, C_LOREGPOOL, C_NONE, 77, 12, 0, LTO, 0},
779 {ASTP, C_PAIR, C_NONE, C_NONE, C_ADDR, C_NONE, 87, 12, 0, 0, 0},
780
781
782 {ALDPW, C_NSAUTO_4, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, REGSP, 0, 0},
783 {ALDPW, C_PSAUTO_4, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, REGSP, 0, 0},
784 {ALDPW, C_UAUTO4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, REGSP, 0, 0},
785 {ALDPW, C_NAUTO4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, REGSP, 0, 0},
786 {ALDPW, C_LAUTO, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, REGSP, 0, 0},
787 {ALDPW, C_LAUTOPOOL, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, REGSP, LFROM, 0},
788 {ALDPW, C_NSOREG_4, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, 0},
789 {ALDPW, C_NSOREG_4, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPRE},
790 {ALDPW, C_NSOREG_4, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPOST},
791 {ALDPW, C_PSOREG_4, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, 0},
792 {ALDPW, C_PSOREG_4, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPRE},
793 {ALDPW, C_PSOREG_4, C_NONE, C_NONE, C_PAIR, C_NONE, 66, 4, 0, 0, C_XPOST},
794 {ALDPW, C_UOREG4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, 0, 0, 0},
795 {ALDPW, C_NOREG4K, C_NONE, C_NONE, C_PAIR, C_NONE, 74, 8, 0, 0, 0},
796 {ALDPW, C_LOREG, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, 0, 0, 0},
797 {ALDPW, C_LOREGPOOL, C_NONE, C_NONE, C_PAIR, C_NONE, 75, 12, 0, LFROM, 0},
798 {ALDPW, C_ADDR, C_NONE, C_NONE, C_PAIR, C_NONE, 88, 12, 0, 0, 0},
799
800 {ASTPW, C_PAIR, C_NONE, C_NONE, C_NSAUTO_4, C_NONE, 67, 4, REGSP, 0, 0},
801 {ASTPW, C_PAIR, C_NONE, C_NONE, C_PSAUTO_4, C_NONE, 67, 4, REGSP, 0, 0},
802 {ASTPW, C_PAIR, C_NONE, C_NONE, C_UAUTO4K, C_NONE, 76, 8, REGSP, 0, 0},
803 {ASTPW, C_PAIR, C_NONE, C_NONE, C_NAUTO4K, C_NONE, 76, 8, REGSP, 0, 0},
804 {ASTPW, C_PAIR, C_NONE, C_NONE, C_LAUTO, C_NONE, 77, 12, REGSP, 0, 0},
805 {ASTPW, C_PAIR, C_NONE, C_NONE, C_LAUTOPOOL, C_NONE, 77, 12, REGSP, LTO, 0},
806 {ASTPW, C_PAIR, C_NONE, C_NONE, C_NSOREG_4, C_NONE, 67, 4, 0, 0, 0},
807 {ASTPW, C_PAIR, C_NONE, C_NONE, C_NSOREG_4, C_NONE, 67, 4, 0, 0, C_XPRE},
808 {ASTPW, C_PAIR, C_NONE, C_NONE, C_NSOREG_4, C_NONE, 67, 4, 0, 0, C_XPOST},
809 {ASTPW, C_PAIR, C_NONE, C_NONE, C_PSOREG_4, C_NONE, 67, 4, 0, 0, 0},
810 {ASTPW, C_PAIR, C_NONE, C_NONE, C_PSOREG_4, C_NONE, 67, 4, 0, 0, C_XPRE},
811 {ASTPW, C_PAIR, C_NONE, C_NONE, C_PSOREG_4, C_NONE, 67, 4, 0, 0, C_XPOST},
812 {ASTPW, C_PAIR, C_NONE, C_NONE, C_UOREG4K, C_NONE, 76, 8, 0, 0, 0},
813 {ASTPW, C_PAIR, C_NONE, C_NONE, C_NOREG4K, C_NONE, 76, 8, 0, 0, 0},
814 {ASTPW, C_PAIR, C_NONE, C_NONE, C_LOREG, C_NONE, 77, 12, 0, 0, 0},
815 {ASTPW, C_PAIR, C_NONE, C_NONE, C_LOREGPOOL, C_NONE, 77, 12, 0, LTO, 0},
816 {ASTPW, C_PAIR, C_NONE, C_NONE, C_ADDR, C_NONE, 87, 12, 0, 0, 0},
817
818 {ASWPD, C_ZREG, C_NONE, C_NONE, C_ZOREG, C_ZREG, 47, 4, 0, 0, 0},
819 {ASWPD, C_ZREG, C_NONE, C_NONE, C_ZAUTO, C_ZREG, 47, 4, REGSP, 0, 0},
820 {ACASPD, C_PAIR, C_NONE, C_NONE, C_ZOREG, C_PAIR, 106, 4, 0, 0, 0},
821 {ACASPD, C_PAIR, C_NONE, C_NONE, C_ZAUTO, C_PAIR, 106, 4, REGSP, 0, 0},
822 {ALDAR, C_ZOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 58, 4, 0, 0, 0},
823 {ALDXR, C_ZOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 58, 4, 0, 0, 0},
824 {ALDAXR, C_ZOREG, C_NONE, C_NONE, C_ZREG, C_NONE, 58, 4, 0, 0, 0},
825 {ALDXP, C_ZOREG, C_NONE, C_NONE, C_PAIR, C_NONE, 58, 4, 0, 0, 0},
826 {ASTLR, C_ZREG, C_NONE, C_NONE, C_ZOREG, C_NONE, 59, 4, 0, 0, 0},
827 {ASTXR, C_ZREG, C_NONE, C_NONE, C_ZOREG, C_ZREG, 59, 4, 0, 0, 0},
828 {ASTLXR, C_ZREG, C_NONE, C_NONE, C_ZOREG, C_ZREG, 59, 4, 0, 0, 0},
829 {ASTXP, C_PAIR, C_NONE, C_NONE, C_ZOREG, C_ZREG, 59, 4, 0, 0, 0},
830
831
832 {AVLD1, C_ZOREG, C_NONE, C_NONE, C_LIST, C_NONE, 81, 4, 0, 0, 0},
833 {AVLD1, C_LOREG, C_NONE, C_NONE, C_LIST, C_NONE, 81, 4, 0, 0, C_XPOST},
834 {AVLD1, C_ROFF, C_NONE, C_NONE, C_LIST, C_NONE, 81, 4, 0, 0, C_XPOST},
835 {AVLD1R, C_ZOREG, C_NONE, C_NONE, C_LIST, C_NONE, 81, 4, 0, 0, 0},
836 {AVLD1R, C_LOREG, C_NONE, C_NONE, C_LIST, C_NONE, 81, 4, 0, 0, C_XPOST},
837 {AVLD1R, C_ROFF, C_NONE, C_NONE, C_LIST, C_NONE, 81, 4, 0, 0, C_XPOST},
838 {AVLD1, C_LOREG, C_NONE, C_NONE, C_ELEM, C_NONE, 97, 4, 0, 0, C_XPOST},
839 {AVLD1, C_ROFF, C_NONE, C_NONE, C_ELEM, C_NONE, 97, 4, 0, 0, C_XPOST},
840 {AVLD1, C_LOREG, C_NONE, C_NONE, C_ELEM, C_NONE, 97, 4, 0, 0, 0},
841 {AVST1, C_LIST, C_NONE, C_NONE, C_ZOREG, C_NONE, 84, 4, 0, 0, 0},
842 {AVST1, C_LIST, C_NONE, C_NONE, C_LOREG, C_NONE, 84, 4, 0, 0, C_XPOST},
843 {AVST1, C_LIST, C_NONE, C_NONE, C_ROFF, C_NONE, 84, 4, 0, 0, C_XPOST},
844 {AVST2, C_LIST, C_NONE, C_NONE, C_ZOREG, C_NONE, 84, 4, 0, 0, 0},
845 {AVST2, C_LIST, C_NONE, C_NONE, C_LOREG, C_NONE, 84, 4, 0, 0, C_XPOST},
846 {AVST2, C_LIST, C_NONE, C_NONE, C_ROFF, C_NONE, 84, 4, 0, 0, C_XPOST},
847 {AVST3, C_LIST, C_NONE, C_NONE, C_ZOREG, C_NONE, 84, 4, 0, 0, 0},
848 {AVST3, C_LIST, C_NONE, C_NONE, C_LOREG, C_NONE, 84, 4, 0, 0, C_XPOST},
849 {AVST3, C_LIST, C_NONE, C_NONE, C_ROFF, C_NONE, 84, 4, 0, 0, C_XPOST},
850 {AVST4, C_LIST, C_NONE, C_NONE, C_ZOREG, C_NONE, 84, 4, 0, 0, 0},
851 {AVST4, C_LIST, C_NONE, C_NONE, C_LOREG, C_NONE, 84, 4, 0, 0, C_XPOST},
852 {AVST4, C_LIST, C_NONE, C_NONE, C_ROFF, C_NONE, 84, 4, 0, 0, C_XPOST},
853 {AVST1, C_ELEM, C_NONE, C_NONE, C_LOREG, C_NONE, 96, 4, 0, 0, C_XPOST},
854 {AVST1, C_ELEM, C_NONE, C_NONE, C_ROFF, C_NONE, 96, 4, 0, 0, C_XPOST},
855 {AVST1, C_ELEM, C_NONE, C_NONE, C_LOREG, C_NONE, 96, 4, 0, 0, 0},
856
857
858 {AMOVD, C_SPR, C_NONE, C_NONE, C_ZREG, C_NONE, 35, 4, 0, 0, 0},
859 {AMRS, C_SPR, C_NONE, C_NONE, C_ZREG, C_NONE, 35, 4, 0, 0, 0},
860 {AMOVD, C_ZREG, C_NONE, C_NONE, C_SPR, C_NONE, 36, 4, 0, 0, 0},
861 {AMSR, C_ZREG, C_NONE, C_NONE, C_SPR, C_NONE, 36, 4, 0, 0, 0},
862 {AMOVD, C_VCON, C_NONE, C_NONE, C_SPR, C_NONE, 37, 4, 0, 0, 0},
863 {AMSR, C_VCON, C_NONE, C_NONE, C_SPR, C_NONE, 37, 4, 0, 0, 0},
864 {AMSR, C_VCON, C_NONE, C_NONE, C_SPOP, C_NONE, 37, 4, 0, 0, 0},
865 {APRFM, C_UOREG32K, C_NONE, C_NONE, C_SPOP, C_NONE, 91, 4, 0, 0, 0},
866 {APRFM, C_UOREG32K, C_NONE, C_NONE, C_LCON, C_NONE, 91, 4, 0, 0, 0},
867 {ADMB, C_VCON, C_NONE, C_NONE, C_NONE, C_NONE, 51, 4, 0, 0, 0},
868 {AHINT, C_VCON, C_NONE, C_NONE, C_NONE, C_NONE, 52, 4, 0, 0, 0},
869 {ASYS, C_VCON, C_NONE, C_NONE, C_NONE, C_NONE, 50, 4, 0, 0, 0},
870 {ASYS, C_VCON, C_NONE, C_NONE, C_ZREG, C_NONE, 50, 4, 0, 0, 0},
871 {ASYSL, C_VCON, C_NONE, C_NONE, C_ZREG, C_NONE, 50, 4, 0, 0, 0},
872 {ATLBI, C_SPOP, C_NONE, C_NONE, C_NONE, C_NONE, 107, 4, 0, 0, 0},
873 {ATLBI, C_SPOP, C_NONE, C_NONE, C_ZREG, C_NONE, 107, 4, 0, 0, 0},
874
875
876 {AAESD, C_VREG, C_NONE, C_NONE, C_VREG, C_NONE, 26, 4, 0, 0, 0},
877 {AAESD, C_ARNG, C_NONE, C_NONE, C_ARNG, C_NONE, 26, 4, 0, 0, 0},
878 {ASHA1C, C_VREG, C_VREG, C_NONE, C_VREG, C_NONE, 49, 4, 0, 0, 0},
879 {ASHA1C, C_ARNG, C_VREG, C_NONE, C_VREG, C_NONE, 49, 4, 0, 0, 0},
880 {ASHA1SU0, C_ARNG, C_ARNG, C_NONE, C_ARNG, C_NONE, 63, 4, 0, 0, 0},
881 {AVREV32, C_ARNG, C_NONE, C_NONE, C_ARNG, C_NONE, 83, 4, 0, 0, 0},
882 {AVPMULL, C_ARNG, C_ARNG, C_NONE, C_ARNG, C_NONE, 93, 4, 0, 0, 0},
883 {AVEOR3, C_ARNG, C_ARNG, C_ARNG, C_ARNG, C_NONE, 103, 4, 0, 0, 0},
884 {AVXAR, C_VCON, C_ARNG, C_ARNG, C_ARNG, C_NONE, 104, 4, 0, 0, 0},
885 {obj.AUNDEF, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 90, 4, 0, 0, 0},
886 {obj.APCDATA, C_VCON, C_NONE, C_NONE, C_VCON, C_NONE, 0, 0, 0, 0, 0},
887 {obj.AFUNCDATA, C_VCON, C_NONE, C_NONE, C_ADDR, C_NONE, 0, 0, 0, 0, 0},
888 {obj.ANOP, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0, 0},
889 {obj.ANOP, C_LCON, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0, 0},
890 {obj.ANOP, C_ZREG, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0, 0},
891 {obj.ANOP, C_VREG, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0, 0},
892 {obj.ADUFFZERO, C_NONE, C_NONE, C_NONE, C_SBRA, C_NONE, 5, 4, 0, 0, 0},
893 {obj.ADUFFCOPY, C_NONE, C_NONE, C_NONE, C_SBRA, C_NONE, 5, 4, 0, 0, 0},
894 {obj.APCALIGN, C_LCON, C_NONE, C_NONE, C_NONE, C_NONE, 0, 0, 0, 0, 0},
895 {obj.APCALIGNMAX, C_LCON, C_NONE, C_NONE, C_LCON, C_NONE, 0, 0, 0, 0, 0},
896 }
897
898
899
900 var pstatefield = []struct {
901 opd SpecialOperand
902 enc uint32
903 }{
904 {SPOP_DAIFSet, 3<<16 | 4<<12 | 6<<5},
905 {SPOP_DAIFClr, 3<<16 | 4<<12 | 7<<5},
906 }
907
908 var prfopfield = map[SpecialOperand]uint32{
909 SPOP_PLDL1KEEP: 0,
910 SPOP_PLDL1STRM: 1,
911 SPOP_PLDL2KEEP: 2,
912 SPOP_PLDL2STRM: 3,
913 SPOP_PLDL3KEEP: 4,
914 SPOP_PLDL3STRM: 5,
915 SPOP_PLIL1KEEP: 8,
916 SPOP_PLIL1STRM: 9,
917 SPOP_PLIL2KEEP: 10,
918 SPOP_PLIL2STRM: 11,
919 SPOP_PLIL3KEEP: 12,
920 SPOP_PLIL3STRM: 13,
921 SPOP_PSTL1KEEP: 16,
922 SPOP_PSTL1STRM: 17,
923 SPOP_PSTL2KEEP: 18,
924 SPOP_PSTL2STRM: 19,
925 SPOP_PSTL3KEEP: 20,
926 SPOP_PSTL3STRM: 21,
927 }
928
929
930
931
932
933
934 var sysInstFields = map[SpecialOperand]struct {
935 op1 uint8
936 cn uint8
937 cm uint8
938 op2 uint8
939 hasOperand2 bool
940 }{
941
942 SPOP_VMALLE1IS: {0, 8, 3, 0, false},
943 SPOP_VAE1IS: {0, 8, 3, 1, true},
944 SPOP_ASIDE1IS: {0, 8, 3, 2, true},
945 SPOP_VAAE1IS: {0, 8, 3, 3, true},
946 SPOP_VALE1IS: {0, 8, 3, 5, true},
947 SPOP_VAALE1IS: {0, 8, 3, 7, true},
948 SPOP_VMALLE1: {0, 8, 7, 0, false},
949 SPOP_VAE1: {0, 8, 7, 1, true},
950 SPOP_ASIDE1: {0, 8, 7, 2, true},
951 SPOP_VAAE1: {0, 8, 7, 3, true},
952 SPOP_VALE1: {0, 8, 7, 5, true},
953 SPOP_VAALE1: {0, 8, 7, 7, true},
954 SPOP_IPAS2E1IS: {4, 8, 0, 1, true},
955 SPOP_IPAS2LE1IS: {4, 8, 0, 5, true},
956 SPOP_ALLE2IS: {4, 8, 3, 0, false},
957 SPOP_VAE2IS: {4, 8, 3, 1, true},
958 SPOP_ALLE1IS: {4, 8, 3, 4, false},
959 SPOP_VALE2IS: {4, 8, 3, 5, true},
960 SPOP_VMALLS12E1IS: {4, 8, 3, 6, false},
961 SPOP_IPAS2E1: {4, 8, 4, 1, true},
962 SPOP_IPAS2LE1: {4, 8, 4, 5, true},
963 SPOP_ALLE2: {4, 8, 7, 0, false},
964 SPOP_VAE2: {4, 8, 7, 1, true},
965 SPOP_ALLE1: {4, 8, 7, 4, false},
966 SPOP_VALE2: {4, 8, 7, 5, true},
967 SPOP_VMALLS12E1: {4, 8, 7, 6, false},
968 SPOP_ALLE3IS: {6, 8, 3, 0, false},
969 SPOP_VAE3IS: {6, 8, 3, 1, true},
970 SPOP_VALE3IS: {6, 8, 3, 5, true},
971 SPOP_ALLE3: {6, 8, 7, 0, false},
972 SPOP_VAE3: {6, 8, 7, 1, true},
973 SPOP_VALE3: {6, 8, 7, 5, true},
974 SPOP_VMALLE1OS: {0, 8, 1, 0, false},
975 SPOP_VAE1OS: {0, 8, 1, 1, true},
976 SPOP_ASIDE1OS: {0, 8, 1, 2, true},
977 SPOP_VAAE1OS: {0, 8, 1, 3, true},
978 SPOP_VALE1OS: {0, 8, 1, 5, true},
979 SPOP_VAALE1OS: {0, 8, 1, 7, true},
980 SPOP_RVAE1IS: {0, 8, 2, 1, true},
981 SPOP_RVAAE1IS: {0, 8, 2, 3, true},
982 SPOP_RVALE1IS: {0, 8, 2, 5, true},
983 SPOP_RVAALE1IS: {0, 8, 2, 7, true},
984 SPOP_RVAE1OS: {0, 8, 5, 1, true},
985 SPOP_RVAAE1OS: {0, 8, 5, 3, true},
986 SPOP_RVALE1OS: {0, 8, 5, 5, true},
987 SPOP_RVAALE1OS: {0, 8, 5, 7, true},
988 SPOP_RVAE1: {0, 8, 6, 1, true},
989 SPOP_RVAAE1: {0, 8, 6, 3, true},
990 SPOP_RVALE1: {0, 8, 6, 5, true},
991 SPOP_RVAALE1: {0, 8, 6, 7, true},
992 SPOP_RIPAS2E1IS: {4, 8, 0, 2, true},
993 SPOP_RIPAS2LE1IS: {4, 8, 0, 6, true},
994 SPOP_ALLE2OS: {4, 8, 1, 0, false},
995 SPOP_VAE2OS: {4, 8, 1, 1, true},
996 SPOP_ALLE1OS: {4, 8, 1, 4, false},
997 SPOP_VALE2OS: {4, 8, 1, 5, true},
998 SPOP_VMALLS12E1OS: {4, 8, 1, 6, false},
999 SPOP_RVAE2IS: {4, 8, 2, 1, true},
1000 SPOP_RVALE2IS: {4, 8, 2, 5, true},
1001 SPOP_IPAS2E1OS: {4, 8, 4, 0, true},
1002 SPOP_RIPAS2E1: {4, 8, 4, 2, true},
1003 SPOP_RIPAS2E1OS: {4, 8, 4, 3, true},
1004 SPOP_IPAS2LE1OS: {4, 8, 4, 4, true},
1005 SPOP_RIPAS2LE1: {4, 8, 4, 6, true},
1006 SPOP_RIPAS2LE1OS: {4, 8, 4, 7, true},
1007 SPOP_RVAE2OS: {4, 8, 5, 1, true},
1008 SPOP_RVALE2OS: {4, 8, 5, 5, true},
1009 SPOP_RVAE2: {4, 8, 6, 1, true},
1010 SPOP_RVALE2: {4, 8, 6, 5, true},
1011 SPOP_ALLE3OS: {6, 8, 1, 0, false},
1012 SPOP_VAE3OS: {6, 8, 1, 1, true},
1013 SPOP_VALE3OS: {6, 8, 1, 5, true},
1014 SPOP_RVAE3IS: {6, 8, 2, 1, true},
1015 SPOP_RVALE3IS: {6, 8, 2, 5, true},
1016 SPOP_RVAE3OS: {6, 8, 5, 1, true},
1017 SPOP_RVALE3OS: {6, 8, 5, 5, true},
1018 SPOP_RVAE3: {6, 8, 6, 1, true},
1019 SPOP_RVALE3: {6, 8, 6, 5, true},
1020
1021 SPOP_IVAC: {0, 7, 6, 1, true},
1022 SPOP_ISW: {0, 7, 6, 2, true},
1023 SPOP_CSW: {0, 7, 10, 2, true},
1024 SPOP_CISW: {0, 7, 14, 2, true},
1025 SPOP_ZVA: {3, 7, 4, 1, true},
1026 SPOP_CVAC: {3, 7, 10, 1, true},
1027 SPOP_CVAU: {3, 7, 11, 1, true},
1028 SPOP_CIVAC: {3, 7, 14, 1, true},
1029 SPOP_IGVAC: {0, 7, 6, 3, true},
1030 SPOP_IGSW: {0, 7, 6, 4, true},
1031 SPOP_IGDVAC: {0, 7, 6, 5, true},
1032 SPOP_IGDSW: {0, 7, 6, 6, true},
1033 SPOP_CGSW: {0, 7, 10, 4, true},
1034 SPOP_CGDSW: {0, 7, 10, 6, true},
1035 SPOP_CIGSW: {0, 7, 14, 4, true},
1036 SPOP_CIGDSW: {0, 7, 14, 6, true},
1037 SPOP_GVA: {3, 7, 4, 3, true},
1038 SPOP_GZVA: {3, 7, 4, 4, true},
1039 SPOP_CGVAC: {3, 7, 10, 3, true},
1040 SPOP_CGDVAC: {3, 7, 10, 5, true},
1041 SPOP_CGVAP: {3, 7, 12, 3, true},
1042 SPOP_CGDVAP: {3, 7, 12, 5, true},
1043 SPOP_CGVADP: {3, 7, 13, 3, true},
1044 SPOP_CGDVADP: {3, 7, 13, 5, true},
1045 SPOP_CIGVAC: {3, 7, 14, 3, true},
1046 SPOP_CIGDVAC: {3, 7, 14, 5, true},
1047 SPOP_CVAP: {3, 7, 12, 1, true},
1048 SPOP_CVADP: {3, 7, 13, 1, true},
1049 }
1050
1051
1052 const OP_NOOP = 0xd503201f
1053
1054
1055
1056 func pcAlignPadLength(ctxt *obj.Link, pc int64, alignedValue int64) int {
1057 if !((alignedValue&(alignedValue-1) == 0) && 8 <= alignedValue && alignedValue <= 2048) {
1058 ctxt.Diag("alignment value of an instruction must be a power of two and in the range [8, 2048], got %d\n", alignedValue)
1059 }
1060 return int(-pc & (alignedValue - 1))
1061 }
1062
1063
1064
1065
1066
1067 func (o *Optab) size(ctxt *obj.Link, p *obj.Prog) int {
1068
1069 sz := movesize(p.As)
1070 if sz != -1 {
1071
1072
1073
1074
1075 align := int64(1 << sz)
1076 if o.a1 == C_ADDR && p.From.Offset%align == 0 && !strings.HasPrefix(p.From.Sym.Name, "go:string.") ||
1077 o.a4 == C_ADDR && p.To.Offset%align == 0 && !strings.HasPrefix(p.To.Sym.Name, "go:string.") {
1078 return 8
1079 }
1080 }
1081 return int(o.size_)
1082 }
1083
1084 func span7(ctxt *obj.Link, cursym *obj.LSym, newprog obj.ProgAlloc) {
1085 if ctxt.Retpoline {
1086 ctxt.Diag("-spectre=ret not supported on arm64")
1087 ctxt.Retpoline = false
1088 }
1089
1090 p := cursym.Func().Text
1091 if p == nil || p.Link == nil {
1092 return
1093 }
1094
1095 if oprange[AAND&obj.AMask] == nil {
1096 ctxt.Diag("arm64 ops not initialized, call arm64.buildop first")
1097 }
1098
1099 c := ctxt7{ctxt: ctxt, newprog: newprog, cursym: cursym, autosize: int32(p.To.Offset & 0xffffffff), extrasize: int32(p.To.Offset >> 32)}
1100 p.To.Offset &= 0xffffffff
1101
1102 bflag := 1
1103 pc := int64(0)
1104 p.Pc = pc
1105 var m int
1106 var o *Optab
1107 for p = p.Link; p != nil; p = p.Link {
1108 p.Pc = pc
1109 o = c.oplook(p)
1110 m = o.size(c.ctxt, p)
1111 if m == 0 {
1112 switch p.As {
1113 case obj.APCALIGN, obj.APCALIGNMAX:
1114 m = obj.AlignmentPadding(int32(pc), p, ctxt, cursym)
1115 break
1116 case obj.ANOP, obj.AFUNCDATA, obj.APCDATA:
1117 continue
1118 default:
1119 c.ctxt.Diag("zero-width instruction\n%v", p)
1120 }
1121 }
1122 pc += int64(m)
1123
1124 if o.flag&LFROM != 0 {
1125 c.addpool(p, &p.From)
1126 }
1127 if o.flag<O != 0 {
1128 c.addpool(p, &p.To)
1129 }
1130 if c.blitrl != nil {
1131 c.checkpool(p)
1132 }
1133 }
1134
1135 c.cursym.Size = pc
1136
1137
1143 for bflag != 0 {
1144 bflag = 0
1145 pc = 0
1146 for p = c.cursym.Func().Text.Link; p != nil; p = p.Link {
1147 p.Pc = pc
1148 o = c.oplook(p)
1149
1150
1151 if (o.flag&BRANCH14BITS != 0 || o.flag&BRANCH19BITS != 0) && p.To.Target() != nil {
1152 otxt := p.To.Target().Pc - pc
1153 var toofar bool
1154 if o.flag&BRANCH14BITS != 0 {
1155 toofar = otxt <= -(1<<15)+10 || otxt >= (1<<15)-10
1156 } else if o.flag&BRANCH19BITS != 0 {
1157 toofar = otxt <= -(1<<20)+10 || otxt >= (1<<20)-10
1158 }
1159 if toofar {
1160 q := c.newprog()
1161 q.Link = p.Link
1162 p.Link = q
1163 q.As = AB
1164 q.To.Type = obj.TYPE_BRANCH
1165 q.To.SetTarget(p.To.Target())
1166 p.To.SetTarget(q)
1167 q = c.newprog()
1168 q.Link = p.Link
1169 p.Link = q
1170 q.As = AB
1171 q.To.Type = obj.TYPE_BRANCH
1172 q.To.SetTarget(q.Link.Link)
1173 bflag = 1
1174 }
1175 }
1176 m = o.size(c.ctxt, p)
1177
1178 if m == 0 {
1179 switch p.As {
1180 case obj.APCALIGN, obj.APCALIGNMAX:
1181 m = obj.AlignmentPaddingLength(int32(pc), p, ctxt)
1182 break
1183 case obj.ANOP, obj.AFUNCDATA, obj.APCDATA:
1184 continue
1185 default:
1186 c.ctxt.Diag("zero-width instruction\n%v", p)
1187 }
1188 }
1189
1190 pc += int64(m)
1191 }
1192 }
1193
1194 pc += -pc & (funcAlign - 1)
1195 c.cursym.Size = pc
1196
1197
1200 c.cursym.Grow(c.cursym.Size)
1201 bp := c.cursym.P
1202 psz := int32(0)
1203 var i int
1204 var out [6]uint32
1205 for p := c.cursym.Func().Text.Link; p != nil; p = p.Link {
1206 c.pc = p.Pc
1207 o = c.oplook(p)
1208 sz := o.size(c.ctxt, p)
1209 if sz > 4*len(out) {
1210 log.Fatalf("out array in span7 is too small, need at least %d for %v", sz/4, p)
1211 }
1212 if p.As == obj.APCALIGN || p.As == obj.APCALIGNMAX {
1213 v := obj.AlignmentPaddingLength(int32(p.Pc), p, c.ctxt)
1214 for i = 0; i < int(v/4); i++ {
1215
1216 c.ctxt.Arch.ByteOrder.PutUint32(bp, OP_NOOP)
1217 bp = bp[4:]
1218 psz += 4
1219 }
1220 } else {
1221 c.asmout(p, o, out[:])
1222 for i = 0; i < sz/4; i++ {
1223 c.ctxt.Arch.ByteOrder.PutUint32(bp, out[i])
1224 bp = bp[4:]
1225 psz += 4
1226 }
1227 }
1228 }
1229
1230
1231
1232
1233
1234 obj.MarkUnsafePoints(c.ctxt, c.cursym.Func().Text, c.newprog, c.isUnsafePoint, c.isRestartable)
1235
1236
1237 for _, jt := range cursym.Func().JumpTables {
1238 for i, p := range jt.Targets {
1239
1240
1241
1242 jt.Sym.WriteAddr(ctxt, int64(i)*8, 8, cursym, p.Pc)
1243 }
1244 }
1245 }
1246
1247
1248 func (c *ctxt7) isUnsafePoint(p *obj.Prog) bool {
1249
1250
1251 return p.From.Reg == REGTMP || p.To.Reg == REGTMP || p.Reg == REGTMP ||
1252 p.From.Type == obj.TYPE_REGREG && p.From.Offset == REGTMP ||
1253 p.To.Type == obj.TYPE_REGREG && p.To.Offset == REGTMP
1254 }
1255
1256
1257
1258 func (c *ctxt7) isRestartable(p *obj.Prog) bool {
1259 if c.isUnsafePoint(p) {
1260 return false
1261 }
1262
1263
1264
1265
1266
1267
1268
1269 o := c.oplook(p)
1270 return o.size(c.ctxt, p) > 4 && o.flag&NOTUSETMP == 0
1271 }
1272
1273
1278 func (c *ctxt7) checkpool(p *obj.Prog) {
1279
1280
1281 if c.pool.size >= 0xffff0 || !ispcdisp(int32(p.Pc+4+int64(c.pool.size)-int64(c.pool.start)+8)) || p.Link == nil {
1282 c.flushpool(p)
1283 }
1284 }
1285
1286 func (c *ctxt7) flushpool(p *obj.Prog) {
1287
1288
1289
1290 if !(p.As == AB || p.As == obj.ARET || p.As == AERET) {
1291 if c.ctxt.Debugvlog {
1292 fmt.Printf("note: flush literal pool at %#x: len=%d ref=%x\n", uint64(p.Pc+4), c.pool.size, c.pool.start)
1293 }
1294 q := c.newprog()
1295 if p.Link == nil {
1296
1297
1298 q.As = obj.AUNDEF
1299 } else {
1300
1301 q.As = AB
1302 q.To.Type = obj.TYPE_BRANCH
1303 q.To.SetTarget(p.Link)
1304 }
1305 q.Link = c.blitrl
1306 q.Pos = p.Pos
1307 c.blitrl = q
1308 }
1309
1310
1311
1312
1313 for q := c.blitrl; q != nil; q = q.Link {
1314 q.Pos = p.Pos
1315 }
1316
1317 c.elitrl.Link = p.Link
1318 p.Link = c.blitrl
1319
1320 c.blitrl = nil
1321 c.elitrl = nil
1322 c.pool.size = 0
1323 c.pool.start = 0
1324 }
1325
1326
1334 func (c *ctxt7) addpool(p *obj.Prog, a *obj.Addr) {
1335 cls := c.aclass(a)
1336 lit := c.instoffset
1337 t := c.newprog()
1338 t.As = AWORD
1339 sz := 4
1340
1341 if a.Type == obj.TYPE_CONST {
1342 if lit != int64(int32(lit)) && uint64(lit) != uint64(uint32(lit)) {
1343
1344 t.As = ADWORD
1345 sz = 8
1346 }
1347 } else if p.As == AMOVD && a.Type != obj.TYPE_MEM || cls == C_ADDR || cls == C_VCON || lit != int64(int32(lit)) || uint64(lit) != uint64(uint32(lit)) {
1348
1349
1350 t.As = ADWORD
1351 sz = 8
1352 }
1353
1354 t.To.Type = obj.TYPE_CONST
1355 t.To.Offset = lit
1356
1357 for q := c.blitrl; q != nil; q = q.Link {
1358 if q.To == t.To {
1359 p.Pool = q
1360 return
1361 }
1362 }
1363
1364 if c.blitrl == nil {
1365 c.blitrl = t
1366 c.pool.start = uint32(p.Pc)
1367 } else {
1368 c.elitrl.Link = t
1369 }
1370 c.elitrl = t
1371 if t.As == ADWORD {
1372
1373
1374
1375 c.pool.size = roundUp(c.pool.size, 8)
1376 }
1377 c.pool.size += uint32(sz)
1378 p.Pool = t
1379 }
1380
1381
1382 func roundUp(x, to uint32) uint32 {
1383 if to == 0 || to&(to-1) != 0 {
1384 log.Fatalf("rounded up to a value that is not a power of 2: %d\n", to)
1385 }
1386 return (x + to - 1) &^ (to - 1)
1387 }
1388
1389
1390
1391
1392
1393 func splitImm24uScaled(v int32, shift int) (int32, int32, error) {
1394 if v < 0 {
1395 return 0, 0, fmt.Errorf("%d is not a 24 bit unsigned immediate", v)
1396 }
1397 if v > 0xfff000+0xfff<<shift {
1398 return 0, 0, fmt.Errorf("%d is too large for a scaled 24 bit unsigned immediate", v)
1399 }
1400 if v&((1<<shift)-1) != 0 {
1401 return 0, 0, fmt.Errorf("%d is not a multiple of %d", v, 1<<shift)
1402 }
1403 lo := (v >> shift) & 0xfff
1404 hi := v - (lo << shift)
1405 if hi > 0xfff000 {
1406 hi = 0xfff000
1407 lo = (v - hi) >> shift
1408 }
1409 if hi & ^0xfff000 != 0 {
1410 panic(fmt.Sprintf("bad split for %x with shift %v (%x, %x)", v, shift, hi, lo))
1411 }
1412 return hi, lo, nil
1413 }
1414
1415 func (c *ctxt7) regoff(a *obj.Addr) int32 {
1416 c.instoffset = 0
1417 c.aclass(a)
1418 return int32(c.instoffset)
1419 }
1420
1421 func isSTLXRop(op obj.As) bool {
1422 switch op {
1423 case ASTLXR, ASTLXRW, ASTLXRB, ASTLXRH,
1424 ASTXR, ASTXRW, ASTXRB, ASTXRH:
1425 return true
1426 }
1427 return false
1428 }
1429
1430 func isSTXPop(op obj.As) bool {
1431 switch op {
1432 case ASTXP, ASTLXP, ASTXPW, ASTLXPW:
1433 return true
1434 }
1435 return false
1436 }
1437
1438 func isANDop(op obj.As) bool {
1439 switch op {
1440 case AAND, AORR, AEOR, AANDS, ATST,
1441 ABIC, AEON, AORN, ABICS:
1442 return true
1443 }
1444 return false
1445 }
1446
1447 func isANDWop(op obj.As) bool {
1448 switch op {
1449 case AANDW, AORRW, AEORW, AANDSW, ATSTW,
1450 ABICW, AEONW, AORNW, ABICSW:
1451 return true
1452 }
1453 return false
1454 }
1455
1456 func isADDop(op obj.As) bool {
1457 switch op {
1458 case AADD, AADDS, ASUB, ASUBS, ACMN, ACMP:
1459 return true
1460 }
1461 return false
1462 }
1463
1464 func isADDWop(op obj.As) bool {
1465 switch op {
1466 case AADDW, AADDSW, ASUBW, ASUBSW, ACMNW, ACMPW:
1467 return true
1468 }
1469 return false
1470 }
1471
1472 func isADDSop(op obj.As) bool {
1473 switch op {
1474 case AADDS, AADDSW, ASUBS, ASUBSW:
1475 return true
1476 }
1477 return false
1478 }
1479
1480 func isNEGop(op obj.As) bool {
1481 switch op {
1482 case ANEG, ANEGW, ANEGS, ANEGSW:
1483 return true
1484 }
1485 return false
1486 }
1487
1488 func isLoadStorePairOp(op obj.As) bool {
1489 switch op {
1490 case AFLDPQ, AFSTPQ, ALDP, ASTP, ALDPW, ASTPW:
1491 return true
1492 }
1493 return false
1494 }
1495
1496 func isMOVop(op obj.As) bool {
1497 switch op {
1498 case AMOVB, AMOVBU, AMOVH, AMOVHU, AMOVW, AMOVWU, AMOVD, AFMOVS, AFMOVD, AFMOVQ:
1499 return true
1500 }
1501 return false
1502 }
1503
1504 func isRegShiftOrExt(a *obj.Addr) bool {
1505 return (a.Index-obj.RBaseARM64)®_EXT != 0 || (a.Index-obj.RBaseARM64)®_LSL != 0
1506 }
1507
1508
1509
1510
1511
1512 const maxPCDisp = 512 * 1024
1513
1514
1515 func ispcdisp(v int32) bool {
1516 return -maxPCDisp < v && v < maxPCDisp && v&3 == 0
1517 }
1518
1519 func isaddcon(v int64) bool {
1520
1521 if v < 0 {
1522 return false
1523 }
1524 if (v & 0xFFF) == 0 {
1525 v >>= 12
1526 }
1527 return v <= 0xFFF
1528 }
1529
1530 func isaddcon2(v int64) bool {
1531 return 0 <= v && v <= 0xFFFFFF
1532 }
1533
1534
1535
1536
1537
1538
1539
1540 func isbitcon(x uint64) bool {
1541 if x == 1<<64-1 || x == 0 {
1542 return false
1543 }
1544
1545 switch {
1546 case x != x>>32|x<<32:
1547
1548
1549 case x != x>>16|x<<48:
1550
1551 x = uint64(int64(int32(x)))
1552 case x != x>>8|x<<56:
1553
1554 x = uint64(int64(int16(x)))
1555 case x != x>>4|x<<60:
1556
1557 x = uint64(int64(int8(x)))
1558 default:
1559
1560
1561
1562
1563
1564 return true
1565 }
1566 return sequenceOfOnes(x) || sequenceOfOnes(^x)
1567 }
1568
1569
1570 func sequenceOfOnes(x uint64) bool {
1571 y := x & -x
1572 y += x
1573 return (y-1)&y == 0
1574 }
1575
1576
1577
1578
1579
1580
1581
1582
1583
1584
1585
1586
1587
1588
1589 func bitconEncode(x uint64, mode int) uint32 {
1590 if mode == 32 {
1591 x &= 0xffffffff
1592 x = x<<32 | x
1593 }
1594 var period uint32
1595
1596 switch {
1597 case x != x>>32|x<<32:
1598 period = 64
1599 case x != x>>16|x<<48:
1600 period = 32
1601 x = uint64(int64(int32(x)))
1602 case x != x>>8|x<<56:
1603 period = 16
1604 x = uint64(int64(int16(x)))
1605 case x != x>>4|x<<60:
1606 period = 8
1607 x = uint64(int64(int8(x)))
1608 case x != x>>2|x<<62:
1609 period = 4
1610 x = uint64(int64(x<<60) >> 60)
1611 default:
1612 period = 2
1613 x = uint64(int64(x<<62) >> 62)
1614 }
1615 neg := false
1616 if int64(x) < 0 {
1617 x = ^x
1618 neg = true
1619 }
1620 y := x & -x
1621 s := log2(y)
1622 n := log2(x+y) - s
1623 if neg {
1624
1625
1626 s = n + s
1627 n = period - n
1628 }
1629
1630 N := uint32(0)
1631 if mode == 64 && period == 64 {
1632 N = 1
1633 }
1634 R := (period - s) & (period - 1) & uint32(mode-1)
1635 S := (n - 1) | 63&^(period<<1-1)
1636 return N<<22 | R<<16 | S<<10
1637 }
1638
1639 func log2(x uint64) uint32 {
1640 if x == 0 {
1641 panic("log2 of 0")
1642 }
1643 n := uint32(0)
1644 if x >= 1<<32 {
1645 x >>= 32
1646 n += 32
1647 }
1648 if x >= 1<<16 {
1649 x >>= 16
1650 n += 16
1651 }
1652 if x >= 1<<8 {
1653 x >>= 8
1654 n += 8
1655 }
1656 if x >= 1<<4 {
1657 x >>= 4
1658 n += 4
1659 }
1660 if x >= 1<<2 {
1661 x >>= 2
1662 n += 2
1663 }
1664 if x >= 1<<1 {
1665 x >>= 1
1666 n += 1
1667 }
1668 return n
1669 }
1670
1671 func autoclass(l int64) int {
1672 if l == 0 {
1673 return C_ZAUTO
1674 }
1675
1676 if l < 0 {
1677 if l >= -256 && (l&15) == 0 {
1678 return C_NSAUTO_16
1679 }
1680 if l >= -256 && (l&7) == 0 {
1681 return C_NSAUTO_8
1682 }
1683 if l >= -256 && (l&3) == 0 {
1684 return C_NSAUTO_4
1685 }
1686 if l >= -256 {
1687 return C_NSAUTO
1688 }
1689 if l >= -512 && (l&15) == 0 {
1690 return C_NPAUTO_16
1691 }
1692 if l >= -512 && (l&7) == 0 {
1693 return C_NPAUTO
1694 }
1695 if l >= -1024 && (l&15) == 0 {
1696 return C_NQAUTO_16
1697 }
1698 if l >= -4095 {
1699 return C_NAUTO4K
1700 }
1701 return C_LAUTO
1702 }
1703
1704 if l <= 255 {
1705 if (l & 15) == 0 {
1706 return C_PSAUTO_16
1707 }
1708 if (l & 7) == 0 {
1709 return C_PSAUTO_8
1710 }
1711 if (l & 3) == 0 {
1712 return C_PSAUTO_4
1713 }
1714 return C_PSAUTO
1715 }
1716 if l <= 504 {
1717 if l&15 == 0 {
1718 return C_PPAUTO_16
1719 }
1720 if l&7 == 0 {
1721 return C_PPAUTO
1722 }
1723 }
1724 if l <= 1008 {
1725 if l&15 == 0 {
1726 return C_PQAUTO_16
1727 }
1728 }
1729 if l <= 4095 {
1730 if l&15 == 0 {
1731 return C_UAUTO4K_16
1732 }
1733 if l&7 == 0 {
1734 return C_UAUTO4K_8
1735 }
1736 if l&3 == 0 {
1737 return C_UAUTO4K_4
1738 }
1739 if l&1 == 0 {
1740 return C_UAUTO4K_2
1741 }
1742 return C_UAUTO4K
1743 }
1744 if l <= 8190 {
1745 if l&15 == 0 {
1746 return C_UAUTO8K_16
1747 }
1748 if l&7 == 0 {
1749 return C_UAUTO8K_8
1750 }
1751 if l&3 == 0 {
1752 return C_UAUTO8K_4
1753 }
1754 if l&1 == 0 {
1755 return C_UAUTO8K
1756 }
1757 }
1758 if l <= 16380 {
1759 if l&15 == 0 {
1760 return C_UAUTO16K_16
1761 }
1762 if l&7 == 0 {
1763 return C_UAUTO16K_8
1764 }
1765 if l&3 == 0 {
1766 return C_UAUTO16K
1767 }
1768 }
1769 if l <= 32760 {
1770 if l&15 == 0 {
1771 return C_UAUTO32K_16
1772 }
1773 if l&7 == 0 {
1774 return C_UAUTO32K
1775 }
1776 }
1777 if l <= 65520 && (l&15) == 0 {
1778 return C_UAUTO64K
1779 }
1780 return C_LAUTO
1781 }
1782
1783 func oregclass(l int64) int {
1784 return autoclass(l) - C_ZAUTO + C_ZOREG
1785 }
1786
1787
1792 func (c *ctxt7) offsetshift(p *obj.Prog, v int64, cls int) int64 {
1793 s := 0
1794 if cls >= C_SEXT1 && cls <= C_SEXT16 {
1795 s = cls - C_SEXT1
1796 } else {
1797 switch cls {
1798 case C_UAUTO4K, C_UOREG4K, C_ZOREG:
1799 s = 0
1800 case C_UAUTO8K, C_UOREG8K:
1801 s = 1
1802 case C_UAUTO16K, C_UOREG16K:
1803 s = 2
1804 case C_UAUTO32K, C_UOREG32K:
1805 s = 3
1806 case C_UAUTO64K, C_UOREG64K:
1807 s = 4
1808 default:
1809 c.ctxt.Diag("bad class: %v\n%v", DRconv(cls), p)
1810 }
1811 }
1812 vs := v >> uint(s)
1813 if vs<<uint(s) != v {
1814 c.ctxt.Diag("odd offset: %d\n%v", v, p)
1815 }
1816 return vs
1817 }
1818
1819
1824 func movcon(v int64) int {
1825 for s := 0; s < 64; s += 16 {
1826 if (uint64(v) &^ (uint64(0xFFFF) << uint(s))) == 0 {
1827 return s / 16
1828 }
1829 }
1830 return -1
1831 }
1832
1833 func rclass(r int16) int {
1834 switch {
1835 case REG_R0 <= r && r <= REG_R30:
1836 return C_REG
1837 case r == REGZERO:
1838 return C_ZREG
1839 case REG_F0 <= r && r <= REG_F31:
1840 return C_FREG
1841 case REG_V0 <= r && r <= REG_V31:
1842 return C_VREG
1843 case r == REGSP:
1844 return C_RSP
1845 case r >= REG_ARNG && r < REG_ELEM:
1846 return C_ARNG
1847 case r >= REG_ELEM && r < REG_ELEM_END:
1848 return C_ELEM
1849 case r >= REG_UXTB && r < REG_SPECIAL,
1850 r >= REG_LSL && r < REG_ARNG:
1851 return C_EXTREG
1852 case r >= REG_SPECIAL:
1853 return C_SPR
1854 }
1855 return C_GOK
1856 }
1857
1858
1859
1860 func (c *ctxt7) con32class(a *obj.Addr) int {
1861 v := uint32(a.Offset)
1862
1863
1864
1865
1866
1867
1868 vbitcon := uint64(v)<<32 | uint64(v)
1869 if v == 0 {
1870 return C_ZCON
1871 }
1872 if isaddcon(int64(v)) {
1873 if v <= 0xFFF {
1874 if isbitcon(vbitcon) {
1875 return C_ABCON0
1876 }
1877 return C_ADDCON0
1878 }
1879 if isbitcon(vbitcon) {
1880 return C_ABCON
1881 }
1882 if movcon(int64(v)) >= 0 {
1883 return C_AMCON
1884 }
1885 if movcon(int64(^v)) >= 0 {
1886 return C_AMCON
1887 }
1888 return C_ADDCON
1889 }
1890
1891 t := movcon(int64(v))
1892 if t >= 0 {
1893 if isbitcon(vbitcon) {
1894 return C_MBCON
1895 }
1896 return C_MOVCON
1897 }
1898
1899 t = movcon(int64(^v))
1900 if t >= 0 {
1901 if isbitcon(vbitcon) {
1902 return C_MBCON
1903 }
1904 return C_MOVCON
1905 }
1906
1907 if isbitcon(vbitcon) {
1908 return C_BITCON
1909 }
1910
1911 if 0 <= v && v <= 0xffffff {
1912 return C_ADDCON2
1913 }
1914 return C_LCON
1915 }
1916
1917
1918 func (c *ctxt7) con64class(a *obj.Addr) int {
1919 zeroCount := 0
1920 negCount := 0
1921 for i := uint(0); i < 4; i++ {
1922 immh := uint32(a.Offset >> (i * 16) & 0xffff)
1923 if immh == 0 {
1924 zeroCount++
1925 } else if immh == 0xffff {
1926 negCount++
1927 }
1928 }
1929 if zeroCount >= 3 || negCount >= 3 {
1930 return C_MOVCON
1931 } else if zeroCount == 2 || negCount == 2 {
1932 return C_MOVCON2
1933 } else if zeroCount == 1 || negCount == 1 {
1934 return C_MOVCON3
1935 } else {
1936 return C_VCON
1937 }
1938 }
1939
1940
1941 func (c *ctxt7) loadStoreClass(p *obj.Prog, lsc int, v int64) int {
1942
1943 if p.Scond == C_XPRE || p.Scond == C_XPOST {
1944 return lsc
1945 }
1946 if cmp(C_NSAUTO, lsc) || cmp(C_NSOREG, lsc) {
1947 return lsc
1948 }
1949
1950 needsPool := true
1951 if v >= -4095 && v <= 4095 {
1952 needsPool = false
1953 }
1954
1955 switch p.As {
1956 case AMOVB, AMOVBU:
1957 if cmp(C_UAUTO4K, lsc) || cmp(C_UOREG4K, lsc) {
1958 return lsc
1959 }
1960 if v >= 0 && v <= 0xffffff {
1961 needsPool = false
1962 }
1963 case AMOVH, AMOVHU:
1964 if cmp(C_UAUTO8K, lsc) || cmp(C_UOREG8K, lsc) {
1965 return lsc
1966 }
1967 if v >= 0 && v <= 0xfff000+0xfff<<1 && v&1 == 0 {
1968 needsPool = false
1969 }
1970 case AMOVW, AMOVWU, AFMOVS:
1971 if cmp(C_UAUTO16K, lsc) || cmp(C_UOREG16K, lsc) {
1972 return lsc
1973 }
1974 if v >= 0 && v <= 0xfff000+0xfff<<2 && v&3 == 0 {
1975 needsPool = false
1976 }
1977 case AMOVD, AFMOVD:
1978 if cmp(C_UAUTO32K, lsc) || cmp(C_UOREG32K, lsc) {
1979 return lsc
1980 }
1981 if v >= 0 && v <= 0xfff000+0xfff<<3 && v&7 == 0 {
1982 needsPool = false
1983 }
1984 case AFMOVQ:
1985 if cmp(C_UAUTO64K, lsc) || cmp(C_UOREG64K, lsc) {
1986 return lsc
1987 }
1988 if v >= 0 && v <= 0xfff000+0xfff<<4 && v&15 == 0 {
1989 needsPool = false
1990 }
1991 }
1992 if needsPool && cmp(C_LAUTO, lsc) {
1993 return C_LAUTOPOOL
1994 }
1995 if needsPool && cmp(C_LOREG, lsc) {
1996 return C_LOREGPOOL
1997 }
1998 return lsc
1999 }
2000
2001
2002 func (c *ctxt7) loadStorePairClass(p *obj.Prog, lsc int, v int64) int {
2003
2004 if p.Scond == C_XPRE || p.Scond == C_XPOST {
2005 return lsc
2006 }
2007
2008 if cmp(C_NAUTO4K, lsc) || cmp(C_NOREG4K, lsc) {
2009 return lsc
2010 }
2011 if cmp(C_UAUTO4K, lsc) || cmp(C_UOREG4K, lsc) {
2012 return lsc
2013 }
2014
2015 needsPool := true
2016 if v >= 0 && v <= 0xffffff {
2017 needsPool = false
2018 }
2019 if needsPool && cmp(C_LAUTO, lsc) {
2020 return C_LAUTOPOOL
2021 }
2022 if needsPool && cmp(C_LOREG, lsc) {
2023 return C_LOREGPOOL
2024 }
2025 return lsc
2026 }
2027
2028 func (c *ctxt7) aclass(a *obj.Addr) int {
2029 switch a.Type {
2030 case obj.TYPE_NONE:
2031 return C_NONE
2032
2033 case obj.TYPE_REG:
2034 return rclass(a.Reg)
2035
2036 case obj.TYPE_REGREG:
2037 return C_PAIR
2038
2039 case obj.TYPE_SHIFT:
2040 return C_SHIFT
2041
2042 case obj.TYPE_REGLIST:
2043 return C_LIST
2044
2045 case obj.TYPE_MEM:
2046
2047 if int16(REG_F0) <= a.Reg && a.Reg <= int16(REG_V31) {
2048 break
2049 }
2050 switch a.Name {
2051 case obj.NAME_EXTERN, obj.NAME_STATIC:
2052 if a.Sym == nil {
2053 break
2054 }
2055 c.instoffset = a.Offset
2056 if a.Sym != nil {
2057 if a.Sym.Type == objabi.STLSBSS {
2058 if c.ctxt.Flag_shared {
2059 return C_TLS_IE
2060 } else {
2061 return C_TLS_LE
2062 }
2063 }
2064 return C_ADDR
2065 }
2066 return C_LEXT
2067
2068 case obj.NAME_GOTREF:
2069 return C_GOTADDR
2070
2071 case obj.NAME_AUTO:
2072 if a.Reg == REGSP {
2073
2074
2075 a.Reg = obj.REG_NONE
2076 }
2077
2078 c.instoffset = int64(c.autosize) + a.Offset - int64(c.extrasize)
2079 return autoclass(c.instoffset)
2080
2081 case obj.NAME_PARAM:
2082 if a.Reg == REGSP {
2083
2084
2085 a.Reg = obj.REG_NONE
2086 }
2087 c.instoffset = int64(c.autosize) + a.Offset + 8
2088 return autoclass(c.instoffset)
2089
2090 case obj.NAME_NONE:
2091 if a.Index != 0 {
2092 if a.Offset != 0 {
2093 if isRegShiftOrExt(a) {
2094
2095 return C_ROFF
2096 }
2097 return C_GOK
2098 }
2099
2100 return C_ROFF
2101 }
2102 c.instoffset = a.Offset
2103 return oregclass(c.instoffset)
2104 }
2105 return C_GOK
2106
2107 case obj.TYPE_FCONST:
2108 return C_FCON
2109
2110 case obj.TYPE_TEXTSIZE:
2111 return C_TEXTSIZE
2112
2113 case obj.TYPE_CONST, obj.TYPE_ADDR:
2114 switch a.Name {
2115 case obj.NAME_NONE:
2116 c.instoffset = a.Offset
2117 if a.Reg != 0 && a.Reg != REGZERO {
2118 break
2119 }
2120 v := c.instoffset
2121 if v == 0 {
2122 return C_ZCON
2123 }
2124 if isaddcon(v) {
2125 if v <= 0xFFF {
2126 if isbitcon(uint64(v)) {
2127 return C_ABCON0
2128 }
2129 return C_ADDCON0
2130 }
2131 if isbitcon(uint64(v)) {
2132 return C_ABCON
2133 }
2134 if movcon(v) >= 0 {
2135 return C_AMCON
2136 }
2137 if movcon(^v) >= 0 {
2138 return C_AMCON
2139 }
2140 return C_ADDCON
2141 }
2142
2143 t := movcon(v)
2144 if t >= 0 {
2145 if isbitcon(uint64(v)) {
2146 return C_MBCON
2147 }
2148 return C_MOVCON
2149 }
2150
2151 t = movcon(^v)
2152 if t >= 0 {
2153 if isbitcon(uint64(v)) {
2154 return C_MBCON
2155 }
2156 return C_MOVCON
2157 }
2158
2159 if isbitcon(uint64(v)) {
2160 return C_BITCON
2161 }
2162
2163 if 0 <= v && v <= 0xffffff {
2164 return C_ADDCON2
2165 }
2166
2167 if uint64(v) == uint64(uint32(v)) || v == int64(int32(v)) {
2168 return C_LCON
2169 }
2170 return C_VCON
2171
2172 case obj.NAME_EXTERN, obj.NAME_STATIC:
2173 if a.Sym == nil {
2174 return C_GOK
2175 }
2176 if a.Sym.Type == objabi.STLSBSS {
2177 c.ctxt.Diag("taking address of TLS variable is not supported")
2178 }
2179 c.instoffset = a.Offset
2180 return C_VCONADDR
2181
2182 case obj.NAME_AUTO:
2183 if a.Reg == REGSP {
2184
2185
2186 a.Reg = obj.REG_NONE
2187 }
2188
2189 c.instoffset = int64(c.autosize) + a.Offset - int64(c.extrasize)
2190
2191 case obj.NAME_PARAM:
2192 if a.Reg == REGSP {
2193
2194
2195 a.Reg = obj.REG_NONE
2196 }
2197 c.instoffset = int64(c.autosize) + a.Offset + 8
2198 default:
2199 return C_GOK
2200 }
2201 cf := c.instoffset
2202 if isaddcon(cf) || isaddcon(-cf) {
2203 return C_AACON
2204 }
2205 if isaddcon2(cf) {
2206 return C_AACON2
2207 }
2208
2209 return C_LACON
2210
2211 case obj.TYPE_BRANCH:
2212 return C_SBRA
2213
2214 case obj.TYPE_SPECIAL:
2215 opd := SpecialOperand(a.Offset)
2216 if SPOP_EQ <= opd && opd <= SPOP_NV {
2217 return C_COND
2218 }
2219 return C_SPOP
2220 }
2221 return C_GOK
2222 }
2223
2224 func (c *ctxt7) oplook(p *obj.Prog) *Optab {
2225 a1 := int(p.Optab)
2226 if a1 != 0 {
2227 return &optab[a1-1]
2228 }
2229 a1 = int(p.From.Class)
2230 if a1 == 0 {
2231 a1 = c.aclass(&p.From)
2232
2233 if (p.As == AADDS || p.As == AADDSW || p.As == ASUBS || p.As == ASUBSW) && a1 == C_ADDCON2 {
2234 a1 = C_LCON
2235 }
2236 if p.From.Type == obj.TYPE_CONST && p.From.Name == obj.NAME_NONE {
2237 if p.As == AMOVW || isADDWop(p.As) || isANDWop(p.As) {
2238
2239
2240 a1 = c.con32class(&p.From)
2241
2242 if (p.As == AADDSW || p.As == ASUBSW) && a1 == C_ADDCON2 {
2243 a1 = C_LCON
2244 }
2245 }
2246 if ((p.As == AMOVD) || isANDop(p.As) || isADDop(p.As)) && (a1 == C_LCON || a1 == C_VCON) {
2247
2248 a1 = c.con64class(&p.From)
2249 }
2250 }
2251 if p.From.Type == obj.TYPE_MEM {
2252 if isMOVop(p.As) && (cmp(C_LAUTO, a1) || cmp(C_LOREG, a1)) {
2253
2254 a1 = c.loadStoreClass(p, a1, c.instoffset)
2255 }
2256 if isLoadStorePairOp(p.As) && (cmp(C_LAUTO, a1) || cmp(C_LOREG, a1)) {
2257
2258 a1 = c.loadStorePairClass(p, a1, c.instoffset)
2259 }
2260 }
2261 p.From.Class = int8(a1)
2262 }
2263
2264 a2 := C_NONE
2265 if p.Reg != 0 {
2266 a2 = rclass(p.Reg)
2267 }
2268
2269 a3 := C_NONE
2270 if p.GetFrom3() != nil {
2271 a3 = int(p.GetFrom3().Class)
2272 if a3 == 0 {
2273 a3 = c.aclass(p.GetFrom3())
2274 p.GetFrom3().Class = int8(a3)
2275 }
2276 }
2277
2278 a4 := int(p.To.Class)
2279 if a4 == 0 {
2280 a4 = c.aclass(&p.To)
2281 if p.To.Type == obj.TYPE_MEM {
2282 if isMOVop(p.As) && (cmp(C_LAUTO, a4) || cmp(C_LOREG, a4)) {
2283
2284 a4 = c.loadStoreClass(p, a4, c.instoffset)
2285 }
2286 if isLoadStorePairOp(p.As) && (cmp(C_LAUTO, a4) || cmp(C_LOREG, a4)) {
2287
2288 a4 = c.loadStorePairClass(p, a4, c.instoffset)
2289 }
2290 }
2291 p.To.Class = int8(a4)
2292 }
2293
2294 a5 := C_NONE
2295 if p.RegTo2 != 0 {
2296 a5 = rclass(p.RegTo2)
2297 } else if p.GetTo2() != nil {
2298 a5 = int(p.GetTo2().Class)
2299 if a5 == 0 {
2300 a5 = c.aclass(p.GetTo2())
2301 p.GetTo2().Class = int8(a5)
2302 }
2303 }
2304
2305 if false {
2306 fmt.Printf("oplook %v %d %d %d %d %d\n", p.As, a1, a2, a3, a4, a5)
2307 fmt.Printf("\t\t%d %d\n", p.From.Type, p.To.Type)
2308 }
2309
2310 ops := oprange[p.As&obj.AMask]
2311 c1 := &xcmp[a1]
2312 c2 := &xcmp[a2]
2313 c3 := &xcmp[a3]
2314 c4 := &xcmp[a4]
2315 c5 := &xcmp[a5]
2316 for i := range ops {
2317 op := &ops[i]
2318 if c1[op.a1] && c2[op.a2] && c3[op.a3] && c4[op.a4] && c5[op.a5] && p.Scond == op.scond {
2319 p.Optab = uint16(cap(optab) - cap(ops) + i + 1)
2320 return op
2321 }
2322 }
2323
2324 c.ctxt.Diag("illegal combination: %v %v %v %v %v %v, %d %d", p, DRconv(a1), DRconv(a2), DRconv(a3), DRconv(a4), DRconv(a5), p.From.Type, p.To.Type)
2325
2326 return &Optab{obj.AUNDEF, C_NONE, C_NONE, C_NONE, C_NONE, C_NONE, 90, 4, 0, 0, 0}
2327 }
2328
2329 func cmp(a int, b int) bool {
2330 if a == b {
2331 return true
2332 }
2333 switch a {
2334 case C_RSP:
2335 if b == C_REG {
2336 return true
2337 }
2338
2339 case C_ZREG:
2340 if b == C_REG {
2341 return true
2342 }
2343
2344 case C_ADDCON0:
2345 if b == C_ZCON || b == C_ABCON0 {
2346 return true
2347 }
2348
2349 case C_ADDCON:
2350 if b == C_ZCON || b == C_ABCON0 || b == C_ADDCON0 || b == C_ABCON || b == C_AMCON {
2351 return true
2352 }
2353
2354 case C_MBCON:
2355 if b == C_ABCON0 {
2356 return true
2357 }
2358
2359 case C_BITCON:
2360 if b == C_ABCON0 || b == C_ABCON || b == C_MBCON {
2361 return true
2362 }
2363
2364 case C_MOVCON:
2365 if b == C_MBCON || b == C_ZCON || b == C_ADDCON0 || b == C_ABCON0 || b == C_AMCON {
2366 return true
2367 }
2368
2369 case C_ADDCON2:
2370 if b == C_ZCON || b == C_ADDCON || b == C_ADDCON0 {
2371 return true
2372 }
2373
2374 case C_LCON:
2375 if b == C_ZCON || b == C_BITCON || b == C_ADDCON || b == C_ADDCON0 || b == C_ABCON || b == C_ABCON0 || b == C_MBCON || b == C_MOVCON || b == C_ADDCON2 || b == C_AMCON {
2376 return true
2377 }
2378
2379 case C_MOVCON2:
2380 return cmp(C_LCON, b)
2381
2382 case C_VCON:
2383 return cmp(C_LCON, b)
2384
2385 case C_LACON:
2386 if b == C_AACON || b == C_AACON2 {
2387 return true
2388 }
2389
2390 case C_SEXT2:
2391 if b == C_SEXT1 {
2392 return true
2393 }
2394
2395 case C_SEXT4:
2396 if b == C_SEXT1 || b == C_SEXT2 {
2397 return true
2398 }
2399
2400 case C_SEXT8:
2401 if b >= C_SEXT1 && b <= C_SEXT4 {
2402 return true
2403 }
2404
2405 case C_SEXT16:
2406 if b >= C_SEXT1 && b <= C_SEXT8 {
2407 return true
2408 }
2409
2410 case C_LEXT:
2411 if b >= C_SEXT1 && b <= C_SEXT16 {
2412 return true
2413 }
2414
2415 case C_NSAUTO_8:
2416 if b == C_NSAUTO_16 {
2417 return true
2418 }
2419
2420 case C_NSAUTO_4:
2421 if b == C_NSAUTO_16 || b == C_NSAUTO_8 {
2422 return true
2423 }
2424
2425 case C_NSAUTO:
2426 switch b {
2427 case C_NSAUTO_4, C_NSAUTO_8, C_NSAUTO_16:
2428 return true
2429 }
2430
2431 case C_NPAUTO_16:
2432 switch b {
2433 case C_NSAUTO_16:
2434 return true
2435 }
2436
2437 case C_NPAUTO:
2438 switch b {
2439 case C_NSAUTO_16, C_NSAUTO_8, C_NPAUTO_16:
2440 return true
2441 }
2442
2443 case C_NQAUTO_16:
2444 switch b {
2445 case C_NSAUTO_16, C_NPAUTO_16:
2446 return true
2447 }
2448
2449 case C_NAUTO4K:
2450 switch b {
2451 case C_NSAUTO_16, C_NSAUTO_8, C_NSAUTO_4, C_NSAUTO, C_NPAUTO_16,
2452 C_NPAUTO, C_NQAUTO_16:
2453 return true
2454 }
2455
2456 case C_PSAUTO_16:
2457 if b == C_ZAUTO {
2458 return true
2459 }
2460
2461 case C_PSAUTO_8:
2462 if b == C_ZAUTO || b == C_PSAUTO_16 {
2463 return true
2464 }
2465
2466 case C_PSAUTO_4:
2467 switch b {
2468 case C_ZAUTO, C_PSAUTO_16, C_PSAUTO_8:
2469 return true
2470 }
2471
2472 case C_PSAUTO:
2473 switch b {
2474 case C_ZAUTO, C_PSAUTO_16, C_PSAUTO_8, C_PSAUTO_4:
2475 return true
2476 }
2477
2478 case C_PPAUTO_16:
2479 switch b {
2480 case C_ZAUTO, C_PSAUTO_16:
2481 return true
2482 }
2483
2484 case C_PPAUTO:
2485 switch b {
2486 case C_ZAUTO, C_PSAUTO_16, C_PSAUTO_8, C_PPAUTO_16:
2487 return true
2488 }
2489
2490 case C_PQAUTO_16:
2491 switch b {
2492 case C_ZAUTO, C_PSAUTO_16, C_PPAUTO_16:
2493 return true
2494 }
2495
2496 case C_UAUTO4K:
2497 switch b {
2498 case C_ZAUTO, C_PSAUTO, C_PSAUTO_4, C_PSAUTO_8, C_PSAUTO_16,
2499 C_PPAUTO, C_PPAUTO_16, C_PQAUTO_16,
2500 C_UAUTO4K_2, C_UAUTO4K_4, C_UAUTO4K_8, C_UAUTO4K_16:
2501 return true
2502 }
2503
2504 case C_UAUTO8K:
2505 switch b {
2506 case C_ZAUTO, C_PSAUTO, C_PSAUTO_4, C_PSAUTO_8, C_PSAUTO_16,
2507 C_PPAUTO, C_PPAUTO_16, C_PQAUTO_16,
2508 C_UAUTO4K_2, C_UAUTO4K_4, C_UAUTO4K_8, C_UAUTO4K_16,
2509 C_UAUTO8K_4, C_UAUTO8K_8, C_UAUTO8K_16:
2510 return true
2511 }
2512
2513 case C_UAUTO16K:
2514 switch b {
2515 case C_ZAUTO, C_PSAUTO, C_PSAUTO_4, C_PSAUTO_8, C_PSAUTO_16,
2516 C_PPAUTO, C_PPAUTO_16, C_PQAUTO_16,
2517 C_UAUTO4K_4, C_UAUTO4K_8, C_UAUTO4K_16,
2518 C_UAUTO8K_4, C_UAUTO8K_8, C_UAUTO8K_16,
2519 C_UAUTO16K_8, C_UAUTO16K_16:
2520 return true
2521 }
2522
2523 case C_UAUTO32K:
2524 switch b {
2525 case C_ZAUTO, C_PSAUTO, C_PSAUTO_4, C_PSAUTO_8, C_PSAUTO_16,
2526 C_PPAUTO, C_PPAUTO_16, C_PQAUTO_16,
2527 C_UAUTO4K_8, C_UAUTO4K_16,
2528 C_UAUTO8K_8, C_UAUTO8K_16,
2529 C_UAUTO16K_8, C_UAUTO16K_16,
2530 C_UAUTO32K_16:
2531 return true
2532 }
2533
2534 case C_UAUTO64K:
2535 switch b {
2536 case C_ZAUTO, C_PSAUTO, C_PSAUTO_4, C_PSAUTO_8, C_PSAUTO_16,
2537 C_PPAUTO_16, C_PQAUTO_16, C_UAUTO4K_16, C_UAUTO8K_16, C_UAUTO16K_16,
2538 C_UAUTO32K_16:
2539 return true
2540 }
2541
2542 case C_LAUTO:
2543 switch b {
2544 case C_ZAUTO, C_NSAUTO, C_NSAUTO_4, C_NSAUTO_8, C_NSAUTO_16, C_NPAUTO_16, C_NPAUTO, C_NQAUTO_16, C_NAUTO4K,
2545 C_PSAUTO, C_PSAUTO_4, C_PSAUTO_8, C_PSAUTO_16,
2546 C_PPAUTO, C_PPAUTO_16, C_PQAUTO_16,
2547 C_UAUTO4K, C_UAUTO4K_2, C_UAUTO4K_4, C_UAUTO4K_8, C_UAUTO4K_16,
2548 C_UAUTO8K, C_UAUTO8K_4, C_UAUTO8K_8, C_UAUTO8K_16,
2549 C_UAUTO16K, C_UAUTO16K_8, C_UAUTO16K_16,
2550 C_UAUTO32K, C_UAUTO32K_16,
2551 C_UAUTO64K:
2552 return true
2553 }
2554
2555 case C_NSOREG_8:
2556 if b == C_NSOREG_16 {
2557 return true
2558 }
2559
2560 case C_NSOREG_4:
2561 if b == C_NSOREG_8 || b == C_NSOREG_16 {
2562 return true
2563 }
2564
2565 case C_NSOREG:
2566 switch b {
2567 case C_NSOREG_4, C_NSOREG_8, C_NSOREG_16:
2568 return true
2569 }
2570
2571 case C_NPOREG_16:
2572 switch b {
2573 case C_NSOREG_16:
2574 return true
2575 }
2576
2577 case C_NPOREG:
2578 switch b {
2579 case C_NSOREG_16, C_NSOREG_8, C_NPOREG_16:
2580 return true
2581 }
2582
2583 case C_NQOREG_16:
2584 switch b {
2585 case C_NSOREG_16, C_NPOREG_16:
2586 return true
2587 }
2588
2589 case C_NOREG4K:
2590 switch b {
2591 case C_NSOREG_16, C_NSOREG_8, C_NSOREG_4, C_NSOREG, C_NPOREG_16, C_NPOREG, C_NQOREG_16:
2592 return true
2593 }
2594
2595 case C_PSOREG_16:
2596 if b == C_ZOREG {
2597 return true
2598 }
2599
2600 case C_PSOREG_8:
2601 if b == C_ZOREG || b == C_PSOREG_16 {
2602 return true
2603 }
2604
2605 case C_PSOREG_4:
2606 switch b {
2607 case C_ZOREG, C_PSOREG_16, C_PSOREG_8:
2608 return true
2609 }
2610
2611 case C_PSOREG:
2612 switch b {
2613 case C_ZOREG, C_PSOREG_16, C_PSOREG_8, C_PSOREG_4:
2614 return true
2615 }
2616
2617 case C_PPOREG_16:
2618 switch b {
2619 case C_ZOREG, C_PSOREG_16:
2620 return true
2621 }
2622
2623 case C_PPOREG:
2624 switch b {
2625 case C_ZOREG, C_PSOREG_16, C_PSOREG_8, C_PPOREG_16:
2626 return true
2627 }
2628
2629 case C_PQOREG_16:
2630 switch b {
2631 case C_ZOREG, C_PSOREG_16, C_PPOREG_16:
2632 return true
2633 }
2634
2635 case C_UOREG4K:
2636 switch b {
2637 case C_ZOREG, C_PSOREG, C_PSOREG_4, C_PSOREG_8, C_PSOREG_16,
2638 C_PPOREG, C_PPOREG_16, C_PQOREG_16,
2639 C_UOREG4K_2, C_UOREG4K_4, C_UOREG4K_8, C_UOREG4K_16:
2640 return true
2641 }
2642
2643 case C_UOREG8K:
2644 switch b {
2645 case C_ZOREG, C_PSOREG, C_PSOREG_4, C_PSOREG_8, C_PSOREG_16,
2646 C_PPOREG, C_PPOREG_16, C_PQOREG_16,
2647 C_UOREG4K_2, C_UOREG4K_4, C_UOREG4K_8, C_UOREG4K_16,
2648 C_UOREG8K_4, C_UOREG8K_8, C_UOREG8K_16:
2649 return true
2650 }
2651
2652 case C_UOREG16K:
2653 switch b {
2654 case C_ZOREG, C_PSOREG, C_PSOREG_4, C_PSOREG_8, C_PSOREG_16,
2655 C_PPOREG, C_PPOREG_16, C_PQOREG_16,
2656 C_UOREG4K_4, C_UOREG4K_8, C_UOREG4K_16,
2657 C_UOREG8K_4, C_UOREG8K_8, C_UOREG8K_16,
2658 C_UOREG16K_8, C_UOREG16K_16:
2659 return true
2660 }
2661
2662 case C_UOREG32K:
2663 switch b {
2664 case C_ZOREG, C_PSOREG, C_PSOREG_4, C_PSOREG_8, C_PSOREG_16,
2665 C_PPOREG, C_PPOREG_16, C_PQOREG_16,
2666 C_UOREG4K_8, C_UOREG4K_16,
2667 C_UOREG8K_8, C_UOREG8K_16,
2668 C_UOREG16K_8, C_UOREG16K_16,
2669 C_UOREG32K_16:
2670 return true
2671 }
2672
2673 case C_UOREG64K:
2674 switch b {
2675 case C_ZOREG, C_PSOREG, C_PSOREG_4, C_PSOREG_8, C_PSOREG_16,
2676 C_PPOREG_16, C_PQOREG_16, C_UOREG4K_16, C_UOREG8K_16, C_UOREG16K_16,
2677 C_UOREG32K_16:
2678 return true
2679 }
2680
2681 case C_LOREG:
2682 switch b {
2683 case C_ZOREG, C_NSOREG, C_NSOREG_4, C_NSOREG_8, C_NSOREG_16, C_NPOREG, C_NPOREG_16, C_NQOREG_16, C_NOREG4K,
2684 C_PSOREG, C_PSOREG_4, C_PSOREG_8, C_PSOREG_16,
2685 C_PPOREG, C_PPOREG_16, C_PQOREG_16,
2686 C_UOREG4K, C_UOREG4K_2, C_UOREG4K_4, C_UOREG4K_8, C_UOREG4K_16,
2687 C_UOREG8K, C_UOREG8K_4, C_UOREG8K_8, C_UOREG8K_16,
2688 C_UOREG16K, C_UOREG16K_8, C_UOREG16K_16,
2689 C_UOREG32K, C_UOREG32K_16,
2690 C_UOREG64K:
2691 return true
2692 }
2693
2694 case C_LBRA:
2695 if b == C_SBRA {
2696 return true
2697 }
2698 }
2699
2700 return false
2701 }
2702
2703 type ocmp []Optab
2704
2705 func (x ocmp) Len() int {
2706 return len(x)
2707 }
2708
2709 func (x ocmp) Swap(i, j int) {
2710 x[i], x[j] = x[j], x[i]
2711 }
2712
2713 func (x ocmp) Less(i, j int) bool {
2714 p1 := &x[i]
2715 p2 := &x[j]
2716 if p1.as != p2.as {
2717 return p1.as < p2.as
2718 }
2719 if p1.a1 != p2.a1 {
2720 return p1.a1 < p2.a1
2721 }
2722 if p1.a2 != p2.a2 {
2723 return p1.a2 < p2.a2
2724 }
2725 if p1.a3 != p2.a3 {
2726 return p1.a3 < p2.a3
2727 }
2728 if p1.a4 != p2.a4 {
2729 return p1.a4 < p2.a4
2730 }
2731 if p1.scond != p2.scond {
2732 return p1.scond < p2.scond
2733 }
2734 return false
2735 }
2736
2737 func oprangeset(a obj.As, t []Optab) {
2738 oprange[a&obj.AMask] = t
2739 }
2740
2741 func buildop(ctxt *obj.Link) {
2742 if oprange[AAND&obj.AMask] != nil {
2743
2744
2745
2746 return
2747 }
2748
2749 for i := 0; i < C_GOK; i++ {
2750 for j := 0; j < C_GOK; j++ {
2751 if cmp(j, i) {
2752 xcmp[i][j] = true
2753 }
2754 }
2755 }
2756
2757 sort.Sort(ocmp(optab))
2758 for i := 0; i < len(optab); i++ {
2759 as, start := optab[i].as, i
2760 for ; i < len(optab)-1; i++ {
2761 if optab[i+1].as != as {
2762 break
2763 }
2764 }
2765 t := optab[start : i+1]
2766 oprangeset(as, t)
2767 switch as {
2768 default:
2769 ctxt.Diag("unknown op in build: %v", as)
2770 ctxt.DiagFlush()
2771 log.Fatalf("bad code")
2772
2773 case AADD:
2774 oprangeset(AADDS, t)
2775 oprangeset(ASUB, t)
2776 oprangeset(ASUBS, t)
2777 oprangeset(AADDW, t)
2778 oprangeset(AADDSW, t)
2779 oprangeset(ASUBW, t)
2780 oprangeset(ASUBSW, t)
2781
2782 case AAND:
2783 oprangeset(AANDW, t)
2784 oprangeset(AEOR, t)
2785 oprangeset(AEORW, t)
2786 oprangeset(AORR, t)
2787 oprangeset(AORRW, t)
2788 oprangeset(ABIC, t)
2789 oprangeset(ABICW, t)
2790 oprangeset(AEON, t)
2791 oprangeset(AEONW, t)
2792 oprangeset(AORN, t)
2793 oprangeset(AORNW, t)
2794
2795 case AANDS:
2796 oprangeset(AANDSW, t)
2797 oprangeset(ABICS, t)
2798 oprangeset(ABICSW, t)
2799
2800 case ANEG:
2801 oprangeset(ANEGS, t)
2802 oprangeset(ANEGSW, t)
2803 oprangeset(ANEGW, t)
2804
2805 case AADC:
2806 oprangeset(AADCW, t)
2807
2808 oprangeset(AADCS, t)
2809 oprangeset(AADCSW, t)
2810 oprangeset(ASBC, t)
2811 oprangeset(ASBCW, t)
2812 oprangeset(ASBCS, t)
2813 oprangeset(ASBCSW, t)
2814
2815 case ANGC:
2816 oprangeset(ANGCW, t)
2817
2818 oprangeset(ANGCS, t)
2819 oprangeset(ANGCSW, t)
2820
2821 case ACMP:
2822 oprangeset(ACMPW, t)
2823 oprangeset(ACMN, t)
2824 oprangeset(ACMNW, t)
2825
2826 case ATST:
2827 oprangeset(ATSTW, t)
2828
2829
2830 case AMVN:
2831 oprangeset(AMVNW, t)
2832
2833 case AMOVK:
2834 oprangeset(AMOVKW, t)
2835 oprangeset(AMOVN, t)
2836 oprangeset(AMOVNW, t)
2837 oprangeset(AMOVZ, t)
2838 oprangeset(AMOVZW, t)
2839
2840 case ASWPD:
2841 for i := range atomicLDADD {
2842 oprangeset(i, t)
2843 }
2844 for i := range atomicSWP {
2845 if i == ASWPD {
2846 continue
2847 }
2848 oprangeset(i, t)
2849 }
2850
2851 case ACASPD:
2852 oprangeset(ACASPW, t)
2853 case ABEQ:
2854 oprangeset(ABNE, t)
2855 oprangeset(ABCS, t)
2856 oprangeset(ABHS, t)
2857 oprangeset(ABCC, t)
2858 oprangeset(ABLO, t)
2859 oprangeset(ABMI, t)
2860 oprangeset(ABPL, t)
2861 oprangeset(ABVS, t)
2862 oprangeset(ABVC, t)
2863 oprangeset(ABHI, t)
2864 oprangeset(ABLS, t)
2865 oprangeset(ABGE, t)
2866 oprangeset(ABLT, t)
2867 oprangeset(ABGT, t)
2868 oprangeset(ABLE, t)
2869
2870 case ALSL:
2871 oprangeset(ALSLW, t)
2872 oprangeset(ALSR, t)
2873 oprangeset(ALSRW, t)
2874 oprangeset(AASR, t)
2875 oprangeset(AASRW, t)
2876 oprangeset(AROR, t)
2877 oprangeset(ARORW, t)
2878
2879 case ACLS:
2880 oprangeset(ACLSW, t)
2881 oprangeset(ACLZ, t)
2882 oprangeset(ACLZW, t)
2883 oprangeset(ARBIT, t)
2884 oprangeset(ARBITW, t)
2885 oprangeset(AREV, t)
2886 oprangeset(AREVW, t)
2887 oprangeset(AREV16, t)
2888 oprangeset(AREV16W, t)
2889 oprangeset(AREV32, t)
2890
2891 case ASDIV:
2892 oprangeset(ASDIVW, t)
2893 oprangeset(AUDIV, t)
2894 oprangeset(AUDIVW, t)
2895 oprangeset(ACRC32B, t)
2896 oprangeset(ACRC32CB, t)
2897 oprangeset(ACRC32CH, t)
2898 oprangeset(ACRC32CW, t)
2899 oprangeset(ACRC32CX, t)
2900 oprangeset(ACRC32H, t)
2901 oprangeset(ACRC32W, t)
2902 oprangeset(ACRC32X, t)
2903
2904 case AMADD:
2905 oprangeset(AMADDW, t)
2906 oprangeset(AMSUB, t)
2907 oprangeset(AMSUBW, t)
2908 oprangeset(ASMADDL, t)
2909 oprangeset(ASMSUBL, t)
2910 oprangeset(AUMADDL, t)
2911 oprangeset(AUMSUBL, t)
2912
2913 case AREM:
2914 oprangeset(AREMW, t)
2915 oprangeset(AUREM, t)
2916 oprangeset(AUREMW, t)
2917
2918 case AMUL:
2919 oprangeset(AMULW, t)
2920 oprangeset(AMNEG, t)
2921 oprangeset(AMNEGW, t)
2922 oprangeset(ASMNEGL, t)
2923 oprangeset(ASMULL, t)
2924 oprangeset(ASMULH, t)
2925 oprangeset(AUMNEGL, t)
2926 oprangeset(AUMULH, t)
2927 oprangeset(AUMULL, t)
2928
2929 case AMOVB:
2930 oprangeset(AMOVBU, t)
2931
2932 case AMOVH:
2933 oprangeset(AMOVHU, t)
2934
2935 case AMOVW:
2936 oprangeset(AMOVWU, t)
2937
2938 case ABFM:
2939 oprangeset(ABFMW, t)
2940 oprangeset(ASBFM, t)
2941 oprangeset(ASBFMW, t)
2942 oprangeset(AUBFM, t)
2943 oprangeset(AUBFMW, t)
2944
2945 case ABFI:
2946 oprangeset(ABFIW, t)
2947 oprangeset(ABFXIL, t)
2948 oprangeset(ABFXILW, t)
2949 oprangeset(ASBFIZ, t)
2950 oprangeset(ASBFIZW, t)
2951 oprangeset(ASBFX, t)
2952 oprangeset(ASBFXW, t)
2953 oprangeset(AUBFIZ, t)
2954 oprangeset(AUBFIZW, t)
2955 oprangeset(AUBFX, t)
2956 oprangeset(AUBFXW, t)
2957
2958 case AEXTR:
2959 oprangeset(AEXTRW, t)
2960
2961 case ASXTB:
2962 oprangeset(ASXTBW, t)
2963 oprangeset(ASXTH, t)
2964 oprangeset(ASXTHW, t)
2965 oprangeset(ASXTW, t)
2966 oprangeset(AUXTB, t)
2967 oprangeset(AUXTH, t)
2968 oprangeset(AUXTW, t)
2969 oprangeset(AUXTBW, t)
2970 oprangeset(AUXTHW, t)
2971
2972 case ACCMN:
2973 oprangeset(ACCMNW, t)
2974 oprangeset(ACCMP, t)
2975 oprangeset(ACCMPW, t)
2976
2977 case ACSEL:
2978 oprangeset(ACSELW, t)
2979 oprangeset(ACSINC, t)
2980 oprangeset(ACSINCW, t)
2981 oprangeset(ACSINV, t)
2982 oprangeset(ACSINVW, t)
2983 oprangeset(ACSNEG, t)
2984 oprangeset(ACSNEGW, t)
2985
2986 case ACINC:
2987
2988 oprangeset(ACINCW, t)
2989 oprangeset(ACINV, t)
2990 oprangeset(ACINVW, t)
2991 oprangeset(ACNEG, t)
2992 oprangeset(ACNEGW, t)
2993
2994
2995 case ACSET:
2996 oprangeset(ACSETW, t)
2997
2998 oprangeset(ACSETM, t)
2999 oprangeset(ACSETMW, t)
3000
3001 case AMOVD,
3002 AB,
3003 ABL,
3004 AWORD,
3005 ADWORD,
3006 obj.ARET,
3007 obj.ATEXT:
3008 break
3009
3010 case AFLDPQ:
3011 break
3012 case AFSTPQ:
3013 break
3014 case ALDP:
3015 oprangeset(AFLDPD, t)
3016
3017 case ASTP:
3018 oprangeset(AFSTPD, t)
3019
3020 case ASTPW:
3021 oprangeset(AFSTPS, t)
3022
3023 case ALDPW:
3024 oprangeset(ALDPSW, t)
3025 oprangeset(AFLDPS, t)
3026
3027 case AERET:
3028 oprangeset(AWFE, t)
3029 oprangeset(AWFI, t)
3030 oprangeset(AYIELD, t)
3031 oprangeset(ASEV, t)
3032 oprangeset(ASEVL, t)
3033 oprangeset(ANOOP, t)
3034 oprangeset(ADRPS, t)
3035
3036 case ACBZ:
3037 oprangeset(ACBZW, t)
3038 oprangeset(ACBNZ, t)
3039 oprangeset(ACBNZW, t)
3040
3041 case ATBZ:
3042 oprangeset(ATBNZ, t)
3043
3044 case AADR, AADRP:
3045 break
3046
3047 case ACLREX:
3048 break
3049
3050 case ASVC:
3051 oprangeset(AHVC, t)
3052 oprangeset(AHLT, t)
3053 oprangeset(ASMC, t)
3054 oprangeset(ABRK, t)
3055 oprangeset(ADCPS1, t)
3056 oprangeset(ADCPS2, t)
3057 oprangeset(ADCPS3, t)
3058
3059 case AFADDS:
3060 oprangeset(AFADDD, t)
3061 oprangeset(AFSUBS, t)
3062 oprangeset(AFSUBD, t)
3063 oprangeset(AFMULS, t)
3064 oprangeset(AFMULD, t)
3065 oprangeset(AFNMULS, t)
3066 oprangeset(AFNMULD, t)
3067 oprangeset(AFDIVS, t)
3068 oprangeset(AFMAXD, t)
3069 oprangeset(AFMAXS, t)
3070 oprangeset(AFMIND, t)
3071 oprangeset(AFMINS, t)
3072 oprangeset(AFMAXNMD, t)
3073 oprangeset(AFMAXNMS, t)
3074 oprangeset(AFMINNMD, t)
3075 oprangeset(AFMINNMS, t)
3076 oprangeset(AFDIVD, t)
3077
3078 case AFMSUBD:
3079 oprangeset(AFMSUBS, t)
3080 oprangeset(AFMADDS, t)
3081 oprangeset(AFMADDD, t)
3082 oprangeset(AFNMSUBS, t)
3083 oprangeset(AFNMSUBD, t)
3084 oprangeset(AFNMADDS, t)
3085 oprangeset(AFNMADDD, t)
3086
3087 case AFCVTSD:
3088 oprangeset(AFCVTDS, t)
3089 oprangeset(AFABSD, t)
3090 oprangeset(AFABSS, t)
3091 oprangeset(AFNEGD, t)
3092 oprangeset(AFNEGS, t)
3093 oprangeset(AFSQRTD, t)
3094 oprangeset(AFSQRTS, t)
3095 oprangeset(AFRINTNS, t)
3096 oprangeset(AFRINTND, t)
3097 oprangeset(AFRINTPS, t)
3098 oprangeset(AFRINTPD, t)
3099 oprangeset(AFRINTMS, t)
3100 oprangeset(AFRINTMD, t)
3101 oprangeset(AFRINTZS, t)
3102 oprangeset(AFRINTZD, t)
3103 oprangeset(AFRINTAS, t)
3104 oprangeset(AFRINTAD, t)
3105 oprangeset(AFRINTXS, t)
3106 oprangeset(AFRINTXD, t)
3107 oprangeset(AFRINTIS, t)
3108 oprangeset(AFRINTID, t)
3109 oprangeset(AFCVTDH, t)
3110 oprangeset(AFCVTHS, t)
3111 oprangeset(AFCVTHD, t)
3112 oprangeset(AFCVTSH, t)
3113
3114 case AFCMPS:
3115 oprangeset(AFCMPD, t)
3116 oprangeset(AFCMPES, t)
3117 oprangeset(AFCMPED, t)
3118
3119 case AFCCMPS:
3120 oprangeset(AFCCMPD, t)
3121 oprangeset(AFCCMPES, t)
3122 oprangeset(AFCCMPED, t)
3123
3124 case AFCSELD:
3125 oprangeset(AFCSELS, t)
3126
3127 case AFMOVQ, AFMOVD, AFMOVS,
3128 AVMOVQ, AVMOVD, AVMOVS:
3129 break
3130
3131 case AFCVTZSD:
3132 oprangeset(AFCVTZSDW, t)
3133 oprangeset(AFCVTZSS, t)
3134 oprangeset(AFCVTZSSW, t)
3135 oprangeset(AFCVTZUD, t)
3136 oprangeset(AFCVTZUDW, t)
3137 oprangeset(AFCVTZUS, t)
3138 oprangeset(AFCVTZUSW, t)
3139
3140 case ASCVTFD:
3141 oprangeset(ASCVTFS, t)
3142 oprangeset(ASCVTFWD, t)
3143 oprangeset(ASCVTFWS, t)
3144 oprangeset(AUCVTFD, t)
3145 oprangeset(AUCVTFS, t)
3146 oprangeset(AUCVTFWD, t)
3147 oprangeset(AUCVTFWS, t)
3148
3149 case ASYS:
3150 oprangeset(AAT, t)
3151 oprangeset(AIC, t)
3152
3153 case ATLBI:
3154 oprangeset(ADC, t)
3155
3156 case ASYSL, AHINT:
3157 break
3158
3159 case ADMB:
3160 oprangeset(ADSB, t)
3161 oprangeset(AISB, t)
3162
3163 case AMRS, AMSR:
3164 break
3165
3166 case ALDAR:
3167 oprangeset(ALDARW, t)
3168 oprangeset(ALDARB, t)
3169 oprangeset(ALDARH, t)
3170 fallthrough
3171
3172 case ALDXR:
3173 oprangeset(ALDXRB, t)
3174 oprangeset(ALDXRH, t)
3175 oprangeset(ALDXRW, t)
3176
3177 case ALDAXR:
3178 oprangeset(ALDAXRB, t)
3179 oprangeset(ALDAXRH, t)
3180 oprangeset(ALDAXRW, t)
3181
3182 case ALDXP:
3183 oprangeset(ALDXPW, t)
3184 oprangeset(ALDAXP, t)
3185 oprangeset(ALDAXPW, t)
3186
3187 case ASTLR:
3188 oprangeset(ASTLRB, t)
3189 oprangeset(ASTLRH, t)
3190 oprangeset(ASTLRW, t)
3191
3192 case ASTXR:
3193 oprangeset(ASTXRB, t)
3194 oprangeset(ASTXRH, t)
3195 oprangeset(ASTXRW, t)
3196
3197 case ASTLXR:
3198 oprangeset(ASTLXRB, t)
3199 oprangeset(ASTLXRH, t)
3200 oprangeset(ASTLXRW, t)
3201
3202 case ASTXP:
3203 oprangeset(ASTLXP, t)
3204 oprangeset(ASTLXPW, t)
3205 oprangeset(ASTXPW, t)
3206
3207 case AVADDP:
3208 oprangeset(AVAND, t)
3209 oprangeset(AVCMEQ, t)
3210 oprangeset(AVORR, t)
3211 oprangeset(AVEOR, t)
3212 oprangeset(AVBSL, t)
3213 oprangeset(AVBIT, t)
3214 oprangeset(AVCMTST, t)
3215 oprangeset(AVUMAX, t)
3216 oprangeset(AVUMIN, t)
3217 oprangeset(AVUZP1, t)
3218 oprangeset(AVUZP2, t)
3219 oprangeset(AVBIF, t)
3220
3221 case AVADD:
3222 oprangeset(AVSUB, t)
3223 oprangeset(AVRAX1, t)
3224
3225 case AAESD:
3226 oprangeset(AAESE, t)
3227 oprangeset(AAESMC, t)
3228 oprangeset(AAESIMC, t)
3229 oprangeset(ASHA1SU1, t)
3230 oprangeset(ASHA256SU0, t)
3231 oprangeset(ASHA512SU0, t)
3232 oprangeset(ASHA1H, t)
3233
3234 case ASHA1C:
3235 oprangeset(ASHA1P, t)
3236 oprangeset(ASHA1M, t)
3237 oprangeset(ASHA256H, t)
3238 oprangeset(ASHA256H2, t)
3239 oprangeset(ASHA512H, t)
3240 oprangeset(ASHA512H2, t)
3241
3242 case ASHA1SU0:
3243 oprangeset(ASHA256SU1, t)
3244 oprangeset(ASHA512SU1, t)
3245
3246 case AVADDV:
3247 oprangeset(AVUADDLV, t)
3248
3249 case AVFMLA:
3250 oprangeset(AVFMLS, t)
3251
3252 case AVPMULL:
3253 oprangeset(AVPMULL2, t)
3254
3255 case AVUSHR:
3256 oprangeset(AVSHL, t)
3257 oprangeset(AVSRI, t)
3258 oprangeset(AVSLI, t)
3259 oprangeset(AVUSRA, t)
3260
3261 case AVREV32:
3262 oprangeset(AVCNT, t)
3263 oprangeset(AVRBIT, t)
3264 oprangeset(AVREV64, t)
3265 oprangeset(AVREV16, t)
3266
3267 case AVZIP1:
3268 oprangeset(AVZIP2, t)
3269 oprangeset(AVTRN1, t)
3270 oprangeset(AVTRN2, t)
3271
3272 case AVUXTL:
3273 oprangeset(AVUXTL2, t)
3274
3275 case AVUSHLL:
3276 oprangeset(AVUSHLL2, t)
3277
3278 case AVLD1R:
3279 oprangeset(AVLD2, t)
3280 oprangeset(AVLD2R, t)
3281 oprangeset(AVLD3, t)
3282 oprangeset(AVLD3R, t)
3283 oprangeset(AVLD4, t)
3284 oprangeset(AVLD4R, t)
3285
3286 case AVEOR3:
3287 oprangeset(AVBCAX, t)
3288
3289 case AVUADDW:
3290 oprangeset(AVUADDW2, t)
3291
3292 case AVTBL:
3293 oprangeset(AVTBX, t)
3294
3295 case AVCNT,
3296 AVMOV,
3297 AVLD1,
3298 AVST1,
3299 AVST2,
3300 AVST3,
3301 AVST4,
3302 AVDUP,
3303 AVMOVI,
3304 APRFM,
3305 AVEXT,
3306 AVXAR:
3307 break
3308
3309 case obj.ANOP,
3310 obj.AUNDEF,
3311 obj.AFUNCDATA,
3312 obj.APCALIGN,
3313 obj.APCALIGNMAX,
3314 obj.APCDATA,
3315 obj.ADUFFZERO,
3316 obj.ADUFFCOPY:
3317 break
3318 }
3319 }
3320 }
3321
3322
3323
3324
3325 func (c *ctxt7) chipfloat7(e float64) int {
3326 ei := math.Float64bits(e)
3327 l := uint32(int32(ei))
3328 h := uint32(int32(ei >> 32))
3329
3330 if l != 0 || h&0xffff != 0 {
3331 return -1
3332 }
3333 h1 := h & 0x7fc00000
3334 if h1 != 0x40000000 && h1 != 0x3fc00000 {
3335 return -1
3336 }
3337 n := 0
3338
3339
3340 if h&0x80000000 != 0 {
3341 n |= 1 << 7
3342 }
3343
3344
3345 if h1 == 0x3fc00000 {
3346 n |= 1 << 6
3347 }
3348
3349
3350 n |= int((h >> 16) & 0x3f)
3351
3352
3353 return n
3354 }
3355
3356
3357 func SYSARG5(op0 int, op1 int, Cn int, Cm int, op2 int) int {
3358 return op0<<19 | op1<<16 | Cn<<12 | Cm<<8 | op2<<5
3359 }
3360
3361 func SYSARG4(op1 int, Cn int, Cm int, op2 int) int {
3362 return SYSARG5(0, op1, Cn, Cm, op2)
3363 }
3364
3365
3366
3367 func (c *ctxt7) checkUnpredictable(p *obj.Prog, isload bool, wback bool, rn int16, rt1 int16, rt2 int16) {
3368 if wback && rn != REGSP && (rn == rt1 || rn == rt2) {
3369 c.ctxt.Diag("constrained unpredictable behavior: %v", p)
3370 }
3371 if isload && rt1 == rt2 {
3372 c.ctxt.Diag("constrained unpredictable behavior: %v", p)
3373 }
3374 }
3375
3376
3377 func (c *ctxt7) checkindex(p *obj.Prog, index, maxindex int) {
3378 if index < 0 || index > maxindex {
3379 c.ctxt.Diag("register element index out of range 0 to %d: %v", maxindex, p)
3380 }
3381 }
3382
3383
3384 func (c *ctxt7) checkoffset(p *obj.Prog, as obj.As) {
3385 var offset, list, n, expect int64
3386 switch as {
3387 case AVLD1, AVLD2, AVLD3, AVLD4, AVLD1R, AVLD2R, AVLD3R, AVLD4R:
3388 offset = p.From.Offset
3389 list = p.To.Offset
3390 case AVST1, AVST2, AVST3, AVST4:
3391 offset = p.To.Offset
3392 list = p.From.Offset
3393 default:
3394 c.ctxt.Diag("invalid operation on op %v", p.As)
3395 }
3396 opcode := (list >> 12) & 15
3397 q := (list >> 30) & 1
3398 size := (list >> 10) & 3
3399 if offset == 0 {
3400 return
3401 }
3402 switch opcode {
3403 case 0x7:
3404 n = 1
3405 case 0xa:
3406 n = 2
3407 case 0x6:
3408 n = 3
3409 case 0x2:
3410 n = 4
3411 default:
3412 c.ctxt.Diag("invalid register numbers in ARM64 register list: %v", p)
3413 }
3414
3415 switch as {
3416 case AVLD1R, AVLD2R, AVLD3R, AVLD4R:
3417 if offset != n*(1<<uint(size)) {
3418 c.ctxt.Diag("invalid post-increment offset: %v", p)
3419 }
3420 default:
3421 if !(q == 0 && offset == n*8) && !(q == 1 && offset == n*16) {
3422 c.ctxt.Diag("invalid post-increment offset: %v", p)
3423 }
3424 }
3425
3426 switch as {
3427 case AVLD1, AVST1:
3428 return
3429 case AVLD1R:
3430 expect = 1
3431 case AVLD2, AVST2, AVLD2R:
3432 expect = 2
3433 case AVLD3, AVST3, AVLD3R:
3434 expect = 3
3435 case AVLD4, AVST4, AVLD4R:
3436 expect = 4
3437 }
3438
3439 if expect != n {
3440 c.ctxt.Diag("expected %d registers, got %d: %v.", expect, n, p)
3441 }
3442 }
3443
3444
3445
3446 func (c *ctxt7) checkShiftAmount(p *obj.Prog, a *obj.Addr) {
3447 var amount int16
3448 amount = (a.Index >> 5) & 7
3449 switch p.As {
3450 case AMOVB, AMOVBU:
3451 if amount != 0 {
3452 c.ctxt.Diag("invalid index shift amount: %v", p)
3453 }
3454 case AMOVH, AMOVHU:
3455 if amount != 1 && amount != 0 {
3456 c.ctxt.Diag("invalid index shift amount: %v", p)
3457 }
3458 case AMOVW, AMOVWU, AFMOVS:
3459 if amount != 2 && amount != 0 {
3460 c.ctxt.Diag("invalid index shift amount: %v", p)
3461 }
3462 case AMOVD, AFMOVD:
3463 if amount != 3 && amount != 0 {
3464 c.ctxt.Diag("invalid index shift amount: %v", p)
3465 }
3466 default:
3467 panic("invalid operation")
3468 }
3469 }
3470
3471 func (c *ctxt7) asmout(p *obj.Prog, o *Optab, out []uint32) {
3472 var os [5]uint32
3473 o1 := uint32(0)
3474 o2 := uint32(0)
3475 o3 := uint32(0)
3476 o4 := uint32(0)
3477 o5 := uint32(0)
3478 if false {
3479 fmt.Printf("%x: %v\ttype %d\n", uint32(p.Pc), p, o.type_)
3480 }
3481 switch o.type_ {
3482 default:
3483 c.ctxt.Diag("%v: unknown asm %d", p, o.type_)
3484
3485 case 0:
3486 break
3487
3488 case 1:
3489 o1 = c.oprrr(p, p.As)
3490
3491 rf := int(p.From.Reg)
3492 rt := int(p.To.Reg)
3493 r := int(p.Reg)
3494 if p.To.Type == obj.TYPE_NONE {
3495 rt = REGZERO
3496 }
3497 if r == obj.REG_NONE {
3498 r = rt
3499 }
3500 o1 |= (uint32(rf&31) << 16) | (uint32(r&31) << 5) | uint32(rt&31)
3501
3502 case 2:
3503 if p.To.Reg == REG_RSP && isADDSop(p.As) {
3504 c.ctxt.Diag("illegal destination register: %v\n", p)
3505 }
3506 o1 = c.opirr(p, p.As)
3507
3508 rt, r := p.To.Reg, p.Reg
3509 if p.To.Type == obj.TYPE_NONE {
3510 if (o1 & Sbit) == 0 {
3511 c.ctxt.Diag("ineffective ZR destination\n%v", p)
3512 }
3513 rt = REGZERO
3514 }
3515 if r == obj.REG_NONE {
3516 r = rt
3517 }
3518 v := c.regoff(&p.From)
3519 o1 = c.oaddi(p, p.As, v, rt, r)
3520
3521 case 3:
3522 o1 = c.oprrr(p, p.As)
3523
3524 amount := (p.From.Offset >> 10) & 63
3525 is64bit := o1 & (1 << 31)
3526 if is64bit == 0 && amount >= 32 {
3527 c.ctxt.Diag("shift amount out of range 0 to 31: %v", p)
3528 }
3529 shift := (p.From.Offset >> 22) & 3
3530 if (shift > 2 || shift < 0) && (isADDop(p.As) || isADDWop(p.As) || isNEGop(p.As)) {
3531 c.ctxt.Diag("unsupported shift operator: %v", p)
3532 }
3533 o1 |= uint32(p.From.Offset)
3534 rt := int(p.To.Reg)
3535 if p.To.Type == obj.TYPE_NONE {
3536 rt = REGZERO
3537 }
3538 r := int(p.Reg)
3539 if p.As == AMVN || p.As == AMVNW || isNEGop(p.As) {
3540 r = REGZERO
3541 } else if r == obj.REG_NONE {
3542 r = rt
3543 }
3544 o1 |= (uint32(r&31) << 5) | uint32(rt&31)
3545
3546 case 4:
3547 rt, r := p.To.Reg, o.param
3548 if r == obj.REG_NONE {
3549 r = REGZERO
3550 } else if r == REGFROM {
3551 r = p.From.Reg
3552 }
3553 if r == obj.REG_NONE {
3554 r = REGSP
3555 }
3556
3557 v := c.regoff(&p.From)
3558 a := AADD
3559 if v < 0 {
3560 a = ASUB
3561 v = -v
3562 }
3563
3564 if o.size(c.ctxt, p) == 8 {
3565
3566
3567 o1 = c.oaddi(p, a, v&0xfff000, rt, r)
3568 o2 = c.oaddi(p, a, v&0x000fff, rt, rt)
3569 break
3570 }
3571
3572 o1 = c.oaddi(p, a, v, rt, r)
3573
3574 case 5:
3575 o1 = c.opbra(p, p.As)
3576
3577 if p.To.Sym == nil {
3578 o1 |= uint32(c.brdist(p, 0, 26, 2))
3579 break
3580 }
3581
3582 rel := obj.Addrel(c.cursym)
3583 rel.Off = int32(c.pc)
3584 rel.Siz = 4
3585 rel.Sym = p.To.Sym
3586 rel.Add = p.To.Offset
3587 rel.Type = objabi.R_CALLARM64
3588
3589 case 6:
3590 o1 = c.opbrr(p, p.As)
3591 o1 |= uint32(p.To.Reg&31) << 5
3592 if p.As == obj.ACALL {
3593 rel := obj.Addrel(c.cursym)
3594 rel.Off = int32(c.pc)
3595 rel.Siz = 0
3596 rel.Type = objabi.R_CALLIND
3597 }
3598
3599 case 7:
3600 o1 = c.opbra(p, p.As)
3601
3602 o1 |= uint32(c.brdist(p, 0, 19, 2) << 5)
3603
3604 case 8:
3605 rt, rf := p.To.Reg, p.Reg
3606 if rf == obj.REG_NONE {
3607 rf = rt
3608 }
3609 v := p.From.Offset
3610 switch p.As {
3611 case AASR:
3612 o1 = c.opbfm(p, ASBFM, v, 63, rf, rt)
3613
3614 case AASRW:
3615 o1 = c.opbfm(p, ASBFMW, v, 31, rf, rt)
3616
3617 case ALSL:
3618 o1 = c.opbfm(p, AUBFM, (64-v)&63, 63-v, rf, rt)
3619
3620 case ALSLW:
3621 o1 = c.opbfm(p, AUBFMW, (32-v)&31, 31-v, rf, rt)
3622
3623 case ALSR:
3624 o1 = c.opbfm(p, AUBFM, v, 63, rf, rt)
3625
3626 case ALSRW:
3627 o1 = c.opbfm(p, AUBFMW, v, 31, rf, rt)
3628
3629 case AROR:
3630 o1 = c.opextr(p, AEXTR, v, rf, rf, rt)
3631
3632 case ARORW:
3633 o1 = c.opextr(p, AEXTRW, v, rf, rf, rt)
3634
3635 default:
3636 c.ctxt.Diag("bad shift $con\n%v", p)
3637 break
3638 }
3639
3640 case 9:
3641 o1 = c.oprrr(p, p.As)
3642
3643 r := int(p.Reg)
3644 if r == obj.REG_NONE {
3645 r = int(p.To.Reg)
3646 }
3647 o1 |= (uint32(p.From.Reg&31) << 16) | (uint32(r&31) << 5) | uint32(p.To.Reg&31)
3648
3649 case 10:
3650 o1 = c.opimm(p, p.As)
3651
3652 if p.From.Type != obj.TYPE_NONE {
3653 o1 |= uint32((p.From.Offset & 0xffff) << 5)
3654 }
3655
3656 case 11:
3657 c.aclass(&p.To)
3658
3659 o1 = uint32(c.instoffset)
3660 o2 = uint32(c.instoffset >> 32)
3661 if p.To.Sym != nil {
3662 rel := obj.Addrel(c.cursym)
3663 rel.Off = int32(c.pc)
3664 rel.Siz = 8
3665 rel.Sym = p.To.Sym
3666 rel.Add = p.To.Offset
3667 rel.Type = objabi.R_ADDR
3668 o2 = 0
3669 o1 = o2
3670 }
3671
3672 case 12:
3673
3674
3675 num := c.omovlconst(p.As, p, &p.From, int(p.To.Reg), os[:])
3676 if num == 0 {
3677 c.ctxt.Diag("invalid constant: %v", p)
3678 }
3679 o1 = os[0]
3680 o2 = os[1]
3681 o3 = os[2]
3682 o4 = os[3]
3683
3684 case 13:
3685 if p.Reg == REGTMP {
3686 c.ctxt.Diag("cannot use REGTMP as source: %v\n", p)
3687 }
3688 if p.To.Reg == REG_RSP && isADDSop(p.As) {
3689 c.ctxt.Diag("illegal destination register: %v\n", p)
3690 }
3691 o := uint32(0)
3692 num := uint8(0)
3693 cls := int(p.From.Class)
3694 if isADDWop(p.As) {
3695 if !cmp(C_LCON, cls) {
3696 c.ctxt.Diag("illegal combination: %v", p)
3697 }
3698 num = c.omovlconst(AMOVW, p, &p.From, REGTMP, os[:])
3699 } else {
3700 num = c.omovlconst(AMOVD, p, &p.From, REGTMP, os[:])
3701 }
3702 if num == 0 {
3703 c.ctxt.Diag("invalid constant: %v", p)
3704 }
3705
3706 rt, r, rf := p.To.Reg, p.Reg, int16(REGTMP)
3707 if p.To.Type == obj.TYPE_NONE {
3708 rt = REGZERO
3709 }
3710 if r == obj.REG_NONE {
3711 r = rt
3712 }
3713 if p.To.Type != obj.TYPE_NONE && (rt == REGSP || r == REGSP) {
3714 o = c.opxrrr(p, p.As, rt, r, rf, false)
3715 o |= LSL0_64
3716 } else {
3717 o = c.oprrr(p, p.As)
3718 o |= uint32(rf&31) << 16
3719 o |= uint32(r&31) << 5
3720 o |= uint32(rt & 31)
3721 }
3722
3723 os[num] = o
3724 o1 = os[0]
3725 o2 = os[1]
3726 o3 = os[2]
3727 o4 = os[3]
3728 o5 = os[4]
3729
3730 case 14:
3731 if c.aclass(&p.To) == C_ADDR {
3732 c.ctxt.Diag("address constant needs DWORD\n%v", p)
3733 }
3734 o1 = uint32(c.instoffset)
3735 if p.To.Sym != nil {
3736
3737
3738 rel := obj.Addrel(c.cursym)
3739
3740 rel.Off = int32(c.pc)
3741 rel.Siz = 4
3742 rel.Sym = p.To.Sym
3743 rel.Add = p.To.Offset
3744 rel.Type = objabi.R_ADDR
3745 o1 = 0
3746 }
3747
3748 case 15:
3749 o1 = c.oprrr(p, p.As)
3750
3751 rf := int(p.From.Reg)
3752 rt := int(p.To.Reg)
3753 var r int
3754 var ra int
3755 if p.From3Type() == obj.TYPE_REG {
3756 r = int(p.GetFrom3().Reg)
3757 ra = int(p.Reg)
3758 if ra == obj.REG_NONE {
3759 ra = REGZERO
3760 }
3761 } else {
3762 r = int(p.Reg)
3763 if r == obj.REG_NONE {
3764 r = rt
3765 }
3766 ra = REGZERO
3767 }
3768
3769 o1 |= (uint32(rf&31) << 16) | (uint32(ra&31) << 10) | (uint32(r&31) << 5) | uint32(rt&31)
3770
3771 case 16:
3772 o1 = c.oprrr(p, p.As)
3773
3774 rf := int(p.From.Reg)
3775 rt := int(p.To.Reg)
3776 r := int(p.Reg)
3777 if r == obj.REG_NONE {
3778 r = rt
3779 }
3780 o1 |= (uint32(rf&31) << 16) | (uint32(r&31) << 5) | REGTMP&31
3781 o2 = c.oprrr(p, AMSUBW)
3782 o2 |= o1 & (1 << 31)
3783 o2 |= (uint32(rf&31) << 16) | (uint32(r&31) << 10) | (REGTMP & 31 << 5) | uint32(rt&31)
3784
3785 case 17:
3786 o1 = c.oprrr(p, p.As)
3787
3788 rf := int(p.From.Reg)
3789 rt := int(p.To.Reg)
3790 r := int(p.Reg)
3791 if p.To.Type == obj.TYPE_NONE {
3792 rt = REGZERO
3793 }
3794 if r == obj.REG_NONE {
3795 r = REGZERO
3796 }
3797 o1 |= (uint32(rf&31) << 16) | (uint32(r&31) << 5) | uint32(rt&31)
3798
3799 case 18:
3800 o1 = c.oprrr(p, p.As)
3801
3802 cond := SpecialOperand(p.From.Offset)
3803 if cond < SPOP_EQ || cond > SPOP_NV || (cond == SPOP_AL || cond == SPOP_NV) && p.From3Type() == obj.TYPE_NONE {
3804 c.ctxt.Diag("invalid condition: %v", p)
3805 } else {
3806 cond -= SPOP_EQ
3807 }
3808
3809 r := int(p.Reg)
3810 var rf int = r
3811 if p.From3Type() == obj.TYPE_NONE {
3812
3813 if r == obj.REG_NONE {
3814
3815 rf = REGZERO
3816 r = rf
3817 }
3818 cond ^= 1
3819 } else {
3820 rf = int(p.GetFrom3().Reg)
3821 }
3822
3823 rt := int(p.To.Reg)
3824 o1 |= (uint32(rf&31) << 16) | (uint32(cond&15) << 12) | (uint32(r&31) << 5) | uint32(rt&31)
3825
3826 case 19:
3827 nzcv := int(p.To.Offset)
3828
3829 cond := SpecialOperand(p.From.Offset)
3830 if cond < SPOP_EQ || cond > SPOP_NV {
3831 c.ctxt.Diag("invalid condition\n%v", p)
3832 } else {
3833 cond -= SPOP_EQ
3834 }
3835 var rf int
3836 if p.GetFrom3().Type == obj.TYPE_REG {
3837 o1 = c.oprrr(p, p.As)
3838 rf = int(p.GetFrom3().Reg)
3839 } else {
3840 o1 = c.opirr(p, p.As)
3841 rf = int(p.GetFrom3().Offset & 0x1F)
3842 }
3843
3844 o1 |= (uint32(rf&31) << 16) | (uint32(cond&15) << 12) | (uint32(p.Reg&31) << 5) | uint32(nzcv)
3845
3846 case 20:
3847 v := c.regoff(&p.To)
3848 sz := int32(1 << uint(movesize(p.As)))
3849
3850 rt, rf := p.To.Reg, p.From.Reg
3851 if rt == obj.REG_NONE {
3852 rt = o.param
3853 }
3854 if v < 0 || v%sz != 0 {
3855 o1 = c.olsr9s(p, c.opstr(p, p.As), v, rt, rf)
3856 } else {
3857 v = int32(c.offsetshift(p, int64(v), int(o.a4)))
3858 o1 = c.olsr12u(p, c.opstr(p, p.As), v, rt, rf)
3859 }
3860
3861 case 21:
3862 v := c.regoff(&p.From)
3863 sz := int32(1 << uint(movesize(p.As)))
3864
3865 rt, rf := p.To.Reg, p.From.Reg
3866 if rf == obj.REG_NONE {
3867 rf = o.param
3868 }
3869 if v < 0 || v%sz != 0 {
3870 o1 = c.olsr9s(p, c.opldr(p, p.As), v, rf, rt)
3871 } else {
3872 v = int32(c.offsetshift(p, int64(v), int(o.a1)))
3873 o1 = c.olsr12u(p, c.opldr(p, p.As), v, rf, rt)
3874 }
3875
3876 case 22:
3877 if p.From.Reg != REGSP && p.From.Reg == p.To.Reg {
3878 c.ctxt.Diag("constrained unpredictable behavior: %v", p)
3879 }
3880
3881 v := int32(p.From.Offset)
3882
3883 if v < -256 || v > 255 {
3884 c.ctxt.Diag("offset out of range [-256,255]: %v", p)
3885 }
3886 o1 = c.opldr(p, p.As)
3887 if o.scond == C_XPOST {
3888 o1 |= 1 << 10
3889 } else {
3890 o1 |= 3 << 10
3891 }
3892 o1 |= ((uint32(v) & 0x1FF) << 12) | (uint32(p.From.Reg&31) << 5) | uint32(p.To.Reg&31)
3893
3894 case 23:
3895 if p.To.Reg != REGSP && p.From.Reg == p.To.Reg {
3896 c.ctxt.Diag("constrained unpredictable behavior: %v", p)
3897 }
3898
3899 v := int32(p.To.Offset)
3900
3901 if v < -256 || v > 255 {
3902 c.ctxt.Diag("offset out of range [-256,255]: %v", p)
3903 }
3904 o1 = c.opstr(p, p.As)
3905 if o.scond == C_XPOST {
3906 o1 |= 1 << 10
3907 } else {
3908 o1 |= 3 << 10
3909 }
3910 o1 |= ((uint32(v) & 0x1FF) << 12) | (uint32(p.To.Reg&31) << 5) | uint32(p.From.Reg&31)
3911
3912 case 24:
3913 rf := int(p.From.Reg)
3914 rt := int(p.To.Reg)
3915 if rf == REGSP || rt == REGSP {
3916 if p.As == AMVN || p.As == AMVNW {
3917 c.ctxt.Diag("illegal SP reference\n%v", p)
3918 }
3919 o1 = c.opirr(p, p.As)
3920 o1 |= (uint32(rf&31) << 5) | uint32(rt&31)
3921 } else {
3922 o1 = c.oprrr(p, p.As)
3923 o1 |= (uint32(rf&31) << 16) | (REGZERO & 31 << 5) | uint32(rt&31)
3924 }
3925
3926 case 25:
3927 o1 = c.oprrr(p, p.As)
3928
3929 rf := int(p.From.Reg)
3930 if rf == C_NONE {
3931 rf = int(p.To.Reg)
3932 }
3933 rt := int(p.To.Reg)
3934 o1 |= (uint32(rf&31) << 16) | (REGZERO & 31 << 5) | uint32(rt&31)
3935
3936 case 26:
3937 o1 = c.oprrr(p, p.As)
3938 cf := c.aclass(&p.From)
3939 af := (p.From.Reg >> 5) & 15
3940 at := (p.To.Reg >> 5) & 15
3941 var sz int16
3942 switch p.As {
3943 case AAESD, AAESE, AAESIMC, AAESMC:
3944 sz = ARNG_16B
3945 case ASHA1SU1, ASHA256SU0:
3946 sz = ARNG_4S
3947 case ASHA512SU0:
3948 sz = ARNG_2D
3949 }
3950
3951 if cf == C_ARNG {
3952 if p.As == ASHA1H {
3953 c.ctxt.Diag("invalid operands: %v", p)
3954 } else {
3955 if af != sz || af != at {
3956 c.ctxt.Diag("invalid arrangement: %v", p)
3957 }
3958 }
3959 }
3960 o1 |= uint32(p.From.Reg&31)<<5 | uint32(p.To.Reg&31)
3961
3962 case 27:
3963 if p.To.Reg == REG_RSP && isADDSop(p.As) {
3964 c.ctxt.Diag("illegal destination register: %v\n", p)
3965 }
3966 rt, r, rf := p.To.Reg, p.Reg, p.From.Reg
3967 if p.To.Type == obj.TYPE_NONE {
3968 rt = REGZERO
3969 }
3970 if r == obj.REG_NONE {
3971 r = rt
3972 }
3973 if (p.From.Reg-obj.RBaseARM64)®_EXT != 0 ||
3974 (p.From.Reg >= REG_LSL && p.From.Reg < REG_ARNG) {
3975 amount := (p.From.Reg >> 5) & 7
3976 if amount > 4 {
3977 c.ctxt.Diag("shift amount out of range 0 to 4: %v", p)
3978 }
3979 o1 = c.opxrrr(p, p.As, rt, r, obj.REG_NONE, true)
3980 o1 |= c.encRegShiftOrExt(p, &p.From, p.From.Reg)
3981 } else {
3982 o1 = c.opxrrr(p, p.As, rt, r, rf, false)
3983 }
3984
3985 case 28:
3986 if p.Reg == REGTMP {
3987 c.ctxt.Diag("cannot use REGTMP as source: %v\n", p)
3988 }
3989 o := uint32(0)
3990 num := uint8(0)
3991 cls := int(p.From.Class)
3992 if isANDWop(p.As) {
3993 if !cmp(C_LCON, cls) {
3994 c.ctxt.Diag("illegal combination: %v", p)
3995 }
3996 num = c.omovlconst(AMOVW, p, &p.From, REGTMP, os[:])
3997 } else {
3998 num = c.omovlconst(AMOVD, p, &p.From, REGTMP, os[:])
3999 }
4000
4001 if num == 0 {
4002 c.ctxt.Diag("invalid constant: %v", p)
4003 }
4004 rt := int(p.To.Reg)
4005 if p.To.Type == obj.TYPE_NONE {
4006 rt = REGZERO
4007 }
4008 r := int(p.Reg)
4009 if r == obj.REG_NONE {
4010 r = rt
4011 }
4012 o = c.oprrr(p, p.As)
4013 o |= REGTMP & 31 << 16
4014 o |= uint32(r&31) << 5
4015 o |= uint32(rt & 31)
4016
4017 os[num] = o
4018 o1 = os[0]
4019 o2 = os[1]
4020 o3 = os[2]
4021 o4 = os[3]
4022 o5 = os[4]
4023
4024 case 29:
4025 fc := c.aclass(&p.From)
4026 tc := c.aclass(&p.To)
4027 if (p.As == AFMOVD || p.As == AFMOVS) && (fc == C_REG || fc == C_ZREG || tc == C_REG || tc == C_ZREG) {
4028
4029 o1 = FPCVTI(0, 0, 0, 0, 6)
4030 if p.As == AFMOVD {
4031 o1 |= 1<<31 | 1<<22
4032 }
4033 if fc == C_REG || fc == C_ZREG {
4034 o1 |= 1 << 16
4035 }
4036 } else {
4037 o1 = c.oprrr(p, p.As)
4038 }
4039 o1 |= uint32(p.From.Reg&31)<<5 | uint32(p.To.Reg&31)
4040
4041 case 30:
4042
4043
4044
4045
4046
4047
4048
4049
4050
4051 s := movesize(o.as)
4052 if s < 0 {
4053 c.ctxt.Diag("unexpected long move, op %v tab %v\n%v", p.As, o.as, p)
4054 }
4055
4056 r := p.To.Reg
4057 if r == obj.REG_NONE {
4058 r = o.param
4059 }
4060
4061 v := c.regoff(&p.To)
4062 if v >= -256 && v <= 256 {
4063 c.ctxt.Diag("%v: bad type for offset %d (should be 9 bit signed immediate store)", p, v)
4064 }
4065 if v >= 0 && v <= 4095 && v&((1<<int32(s))-1) == 0 {
4066 c.ctxt.Diag("%v: bad type for offset %d (should be 12 bit unsigned immediate store)", p, v)
4067 }
4068
4069
4070 if v >= -4095 && v <= 4095 {
4071 o1 = c.oaddi12(p, v, REGTMP, int16(r))
4072 o2 = c.olsr12u(p, c.opstr(p, p.As), 0, REGTMP, p.From.Reg)
4073 break
4074 }
4075
4076 hi, lo, err := splitImm24uScaled(v, s)
4077 if err != nil {
4078 goto storeusepool
4079 }
4080 if p.Pool != nil {
4081 c.ctxt.Diag("%v: unused constant in pool (%v)\n", p, v)
4082 }
4083 o1 = c.oaddi(p, AADD, hi, REGTMP, r)
4084 o2 = c.olsr12u(p, c.opstr(p, p.As), lo, REGTMP, p.From.Reg)
4085 break
4086
4087 storeusepool:
4088 if p.Pool == nil {
4089 c.ctxt.Diag("%v: constant is not in pool", p)
4090 }
4091 if r == REGTMP || p.From.Reg == REGTMP {
4092 c.ctxt.Diag("REGTMP used in large offset store: %v", p)
4093 }
4094 o1 = c.omovlit(AMOVD, p, &p.To, REGTMP)
4095 o2 = c.olsxrr(p, int32(c.opstrr(p, p.As, false)), int(p.From.Reg), int(r), REGTMP)
4096
4097 case 31:
4098
4099
4100
4101
4102
4103
4104
4105
4106
4107 s := movesize(o.as)
4108 if s < 0 {
4109 c.ctxt.Diag("unexpected long move, op %v tab %v\n%v", p.As, o.as, p)
4110 }
4111
4112 r := p.From.Reg
4113 if r == obj.REG_NONE {
4114 r = o.param
4115 }
4116
4117 v := c.regoff(&p.From)
4118 if v >= -256 && v <= 256 {
4119 c.ctxt.Diag("%v: bad type for offset %d (should be 9 bit signed immediate load)", p, v)
4120 }
4121 if v >= 0 && v <= 4095 && v&((1<<int32(s))-1) == 0 {
4122 c.ctxt.Diag("%v: bad type for offset %d (should be 12 bit unsigned immediate load)", p, v)
4123 }
4124
4125
4126 if v >= -4095 && v <= 4095 {
4127 o1 = c.oaddi12(p, v, REGTMP, int16(r))
4128 o2 = c.olsr12u(p, c.opldr(p, p.As), 0, REGTMP, p.To.Reg)
4129 break
4130 }
4131
4132 hi, lo, err := splitImm24uScaled(v, s)
4133 if err != nil {
4134 goto loadusepool
4135 }
4136 if p.Pool != nil {
4137 c.ctxt.Diag("%v: unused constant in pool (%v)\n", p, v)
4138 }
4139 o1 = c.oaddi(p, AADD, hi, REGTMP, r)
4140 o2 = c.olsr12u(p, c.opldr(p, p.As), lo, REGTMP, p.To.Reg)
4141 break
4142
4143 loadusepool:
4144 if p.Pool == nil {
4145 c.ctxt.Diag("%v: constant is not in pool", p)
4146 }
4147 if r == REGTMP || p.From.Reg == REGTMP {
4148 c.ctxt.Diag("REGTMP used in large offset load: %v", p)
4149 }
4150 o1 = c.omovlit(AMOVD, p, &p.From, REGTMP)
4151 o2 = c.olsxrr(p, int32(c.opldrr(p, p.As, false)), int(p.To.Reg), int(r), REGTMP)
4152
4153 case 32:
4154 o1 = c.omovconst(p.As, p, &p.From, int(p.To.Reg))
4155
4156 case 33:
4157 o1 = c.opirr(p, p.As)
4158
4159 d := p.From.Offset
4160 if d == 0 {
4161 c.ctxt.Diag("zero shifts cannot be handled correctly: %v", p)
4162 }
4163 s := movcon(d)
4164 if s < 0 || s >= 4 {
4165 c.ctxt.Diag("bad constant for MOVK: %#x\n%v", uint64(d), p)
4166 }
4167 if (o1&S64) == 0 && s >= 2 {
4168 c.ctxt.Diag("illegal bit position\n%v", p)
4169 }
4170 if ((uint64(d) >> uint(s*16)) >> 16) != 0 {
4171 c.ctxt.Diag("requires uimm16\n%v", p)
4172 }
4173 rt := int(p.To.Reg)
4174
4175 o1 |= uint32((((d >> uint(s*16)) & 0xFFFF) << 5) | int64((uint32(s)&3)<<21) | int64(rt&31))
4176
4177 case 34:
4178 o1 = c.omovlit(AMOVD, p, &p.From, REGTMP)
4179 rt, r, rf := p.To.Reg, p.From.Reg, int16(REGTMP)
4180 if r == obj.REG_NONE {
4181 r = o.param
4182 }
4183 o2 = c.opxrrr(p, AADD, rt, r, rf, false)
4184 o2 |= LSL0_64
4185
4186 case 35:
4187 o1 = c.oprrr(p, AMRS)
4188
4189
4190 _, v, accessFlags := SysRegEnc(p.From.Reg)
4191 if v == 0 {
4192 c.ctxt.Diag("illegal system register:\n%v", p)
4193 }
4194 if (o1 & (v &^ (3 << 19))) != 0 {
4195 c.ctxt.Diag("MRS register value overlap\n%v", p)
4196 }
4197 if accessFlags&SR_READ == 0 {
4198 c.ctxt.Diag("system register is not readable: %v", p)
4199 }
4200
4201 o1 |= v
4202 o1 |= uint32(p.To.Reg & 31)
4203
4204 case 36:
4205 o1 = c.oprrr(p, AMSR)
4206
4207
4208 _, v, accessFlags := SysRegEnc(p.To.Reg)
4209 if v == 0 {
4210 c.ctxt.Diag("illegal system register:\n%v", p)
4211 }
4212 if (o1 & (v &^ (3 << 19))) != 0 {
4213 c.ctxt.Diag("MSR register value overlap\n%v", p)
4214 }
4215 if accessFlags&SR_WRITE == 0 {
4216 c.ctxt.Diag("system register is not writable: %v", p)
4217 }
4218
4219 o1 |= v
4220 o1 |= uint32(p.From.Reg & 31)
4221
4222 case 37:
4223 if (uint64(p.From.Offset) &^ uint64(0xF)) != 0 {
4224 c.ctxt.Diag("illegal immediate for PSTATE field\n%v", p)
4225 }
4226 o1 = c.opirr(p, AMSR)
4227 o1 |= uint32((p.From.Offset & 0xF) << 8)
4228 v := uint32(0)
4229
4230 if p.To.Type == obj.TYPE_REG && p.To.Reg == REG_SPSel {
4231 v = 0<<16 | 4<<12 | 5<<5
4232 } else if p.To.Type == obj.TYPE_SPECIAL {
4233 opd := SpecialOperand(p.To.Offset)
4234 for _, pf := range pstatefield {
4235 if pf.opd == opd {
4236 v = pf.enc
4237 break
4238 }
4239 }
4240 }
4241
4242 if v == 0 {
4243 c.ctxt.Diag("illegal PSTATE field for immediate move\n%v", p)
4244 }
4245 o1 |= v
4246
4247 case 38:
4248 o1 = c.opimm(p, p.As)
4249
4250 if p.To.Type == obj.TYPE_NONE {
4251 o1 |= 0xF << 8
4252 } else {
4253 o1 |= uint32((p.To.Offset & 0xF) << 8)
4254 }
4255
4256 case 39:
4257 o1 = c.opirr(p, p.As)
4258
4259 o1 |= uint32(p.From.Reg & 31)
4260 o1 |= uint32(c.brdist(p, 0, 19, 2) << 5)
4261
4262 case 40:
4263 o1 = c.opirr(p, p.As)
4264
4265 v := int32(p.From.Offset)
4266 if v < 0 || v > 63 {
4267 c.ctxt.Diag("illegal bit number\n%v", p)
4268 }
4269 o1 |= ((uint32(v) & 0x20) << (31 - 5)) | ((uint32(v) & 0x1F) << 19)
4270 o1 |= uint32(c.brdist(p, 0, 14, 2) << 5)
4271 o1 |= uint32(p.Reg & 31)
4272
4273 case 41:
4274 o1 = c.op0(p, p.As)
4275
4276 case 42:
4277 o1 = c.opbfm(p, p.As, p.From.Offset, p.GetFrom3().Offset, p.Reg, p.To.Reg)
4278
4279 case 43:
4280 rt, rf := p.To.Reg, p.Reg
4281 if rf == obj.REG_NONE {
4282 rf = rt
4283 }
4284 r, s := p.From.Offset, p.GetFrom3().Offset
4285 switch p.As {
4286 case ABFI:
4287 if r != 0 {
4288 r = 64 - r
4289 }
4290 o1 = c.opbfm(p, ABFM, r, s-1, rf, rt)
4291
4292 case ABFIW:
4293 if r != 0 {
4294 r = 32 - r
4295 }
4296 o1 = c.opbfm(p, ABFMW, r, s-1, rf, rt)
4297
4298 case ABFXIL:
4299 o1 = c.opbfm(p, ABFM, r, r+s-1, rf, rt)
4300
4301 case ABFXILW:
4302 o1 = c.opbfm(p, ABFMW, r, r+s-1, rf, rt)
4303
4304 case ASBFIZ:
4305 if r != 0 {
4306 r = 64 - r
4307 }
4308 o1 = c.opbfm(p, ASBFM, r, s-1, rf, rt)
4309
4310 case ASBFIZW:
4311 if r != 0 {
4312 r = 32 - r
4313 }
4314 o1 = c.opbfm(p, ASBFMW, r, s-1, rf, rt)
4315
4316 case ASBFX:
4317 o1 = c.opbfm(p, ASBFM, r, r+s-1, rf, rt)
4318
4319 case ASBFXW:
4320 o1 = c.opbfm(p, ASBFMW, r, r+s-1, rf, rt)
4321
4322 case AUBFIZ:
4323 if r != 0 {
4324 r = 64 - r
4325 }
4326 o1 = c.opbfm(p, AUBFM, r, s-1, rf, rt)
4327
4328 case AUBFIZW:
4329 if r != 0 {
4330 r = 32 - r
4331 }
4332 o1 = c.opbfm(p, AUBFMW, r, s-1, rf, rt)
4333
4334 case AUBFX:
4335 o1 = c.opbfm(p, AUBFM, r, r+s-1, rf, rt)
4336
4337 case AUBFXW:
4338 o1 = c.opbfm(p, AUBFMW, r, r+s-1, rf, rt)
4339
4340 default:
4341 c.ctxt.Diag("bad bfm alias\n%v", p)
4342 break
4343 }
4344
4345 case 44:
4346 o1 = c.opextr(p, p.As, p.From.Offset, p.GetFrom3().Reg, p.Reg, p.To.Reg)
4347
4348 case 45:
4349 as := p.As
4350 rt, rf := p.To.Reg, p.From.Reg
4351 if rf == REGZERO {
4352 as = AMOVWU
4353 }
4354 switch as {
4355 case AMOVB, ASXTB:
4356 o1 = c.opbfm(p, ASBFM, 0, 7, rf, rt)
4357
4358 case AMOVH, ASXTH:
4359 o1 = c.opbfm(p, ASBFM, 0, 15, rf, rt)
4360
4361 case AMOVW, ASXTW:
4362 o1 = c.opbfm(p, ASBFM, 0, 31, rf, rt)
4363
4364 case AMOVBU, AUXTB:
4365 o1 = c.opbfm(p, AUBFM, 0, 7, rf, rt)
4366
4367 case AMOVHU, AUXTH:
4368 o1 = c.opbfm(p, AUBFM, 0, 15, rf, rt)
4369
4370 case AMOVWU:
4371 o1 = c.oprrr(p, as) | (uint32(rf&31) << 16) | (REGZERO & 31 << 5) | uint32(rt&31)
4372
4373 case AUXTW:
4374 o1 = c.opbfm(p, AUBFM, 0, 31, rf, rt)
4375
4376 case ASXTBW:
4377 o1 = c.opbfm(p, ASBFMW, 0, 7, rf, rt)
4378
4379 case ASXTHW:
4380 o1 = c.opbfm(p, ASBFMW, 0, 15, rf, rt)
4381
4382 case AUXTBW:
4383 o1 = c.opbfm(p, AUBFMW, 0, 7, rf, rt)
4384
4385 case AUXTHW:
4386 o1 = c.opbfm(p, AUBFMW, 0, 15, rf, rt)
4387
4388 default:
4389 c.ctxt.Diag("bad sxt %v", as)
4390 break
4391 }
4392
4393 case 46:
4394 o1 = c.opbit(p, p.As)
4395
4396 o1 |= uint32(p.From.Reg&31) << 5
4397 o1 |= uint32(p.To.Reg & 31)
4398
4399 case 47:
4400 rs := p.From.Reg
4401 rt := p.RegTo2
4402 rb := p.To.Reg
4403
4404
4405 if rt == REG_RSP {
4406 c.ctxt.Diag("illegal destination register: %v\n", p)
4407 }
4408
4409 o1 = atomicLDADD[p.As] | atomicSWP[p.As]
4410 o1 |= uint32(rs&31)<<16 | uint32(rb&31)<<5 | uint32(rt&31)
4411
4412 case 48:
4413
4414
4415 op := c.opirr(p, p.As)
4416 if op&Sbit != 0 {
4417 c.ctxt.Diag("can not break addition/subtraction when S bit is set", p)
4418 }
4419 rt, r := p.To.Reg, p.Reg
4420 if r == obj.REG_NONE {
4421 r = rt
4422 }
4423 o1 = c.oaddi(p, p.As, c.regoff(&p.From)&0x000fff, rt, r)
4424 o2 = c.oaddi(p, p.As, c.regoff(&p.From)&0xfff000, rt, rt)
4425
4426 case 49:
4427 o1 = c.oprrr(p, p.As)
4428 cf := c.aclass(&p.From)
4429 af := (p.From.Reg >> 5) & 15
4430 sz := ARNG_4S
4431 if p.As == ASHA512H || p.As == ASHA512H2 {
4432 sz = ARNG_2D
4433 }
4434 if cf == C_ARNG && af != int16(sz) {
4435 c.ctxt.Diag("invalid arrangement: %v", p)
4436 }
4437 o1 |= uint32(p.From.Reg&31)<<16 | uint32(p.Reg&31)<<5 | uint32(p.To.Reg&31)
4438
4439 case 50:
4440 o1 = c.opirr(p, p.As)
4441
4442 if (p.From.Offset &^ int64(SYSARG4(0x7, 0xF, 0xF, 0x7))) != 0 {
4443 c.ctxt.Diag("illegal SYS argument\n%v", p)
4444 }
4445 o1 |= uint32(p.From.Offset)
4446 if p.To.Type == obj.TYPE_REG {
4447 o1 |= uint32(p.To.Reg & 31)
4448 } else {
4449 o1 |= 0x1F
4450 }
4451
4452 case 51:
4453 o1 = c.opirr(p, p.As)
4454
4455 if p.From.Type == obj.TYPE_CONST {
4456 o1 |= uint32((p.From.Offset & 0xF) << 8)
4457 }
4458
4459 case 52:
4460 o1 = c.opirr(p, p.As)
4461
4462 o1 |= uint32((p.From.Offset & 0x7F) << 5)
4463
4464 case 53:
4465 a := p.As
4466 rt := int(p.To.Reg)
4467 if p.To.Type == obj.TYPE_NONE {
4468 rt = REGZERO
4469 }
4470 r := int(p.Reg)
4471 if r == obj.REG_NONE {
4472 r = rt
4473 }
4474 if r == REG_RSP {
4475 c.ctxt.Diag("illegal source register: %v", p)
4476 break
4477 }
4478 mode := 64
4479 v := uint64(p.From.Offset)
4480 switch p.As {
4481 case AANDW, AORRW, AEORW, AANDSW, ATSTW:
4482 mode = 32
4483 case ABIC, AORN, AEON, ABICS:
4484 v = ^v
4485 case ABICW, AORNW, AEONW, ABICSW:
4486 v = ^v
4487 mode = 32
4488 }
4489 o1 = c.opirr(p, a)
4490 o1 |= bitconEncode(v, mode) | uint32(r&31)<<5 | uint32(rt&31)
4491
4492 case 54:
4493 o1 = c.oprrr(p, p.As)
4494 rf := int(p.From.Reg)
4495 rt := int(p.To.Reg)
4496 r := int(p.Reg)
4497 if (o1&(0x1F<<24)) == (0x1E<<24) && (o1&(1<<11)) == 0 {
4498 r = rf
4499 rf = 0
4500 } else if r == obj.REG_NONE {
4501 r = rt
4502 }
4503 o1 |= (uint32(rf&31) << 16) | (uint32(r&31) << 5) | uint32(rt&31)
4504
4505 case 55:
4506 var rf int
4507 o1 = 0xf<<25 | 1<<21 | 1<<12
4508 rf = c.chipfloat7(p.From.Val.(float64))
4509 if rf < 0 {
4510 c.ctxt.Diag("invalid floating-point immediate\n%v", p)
4511 }
4512 if p.As == AFMOVD {
4513 o1 |= 1 << 22
4514 }
4515 o1 |= (uint32(rf&0xff) << 13) | uint32(p.To.Reg&31)
4516
4517 case 56:
4518 o1 = c.oprrr(p, p.As)
4519
4520 var rf int
4521 if p.From.Type == obj.TYPE_FCONST {
4522 o1 |= 8
4523 rf = 0
4524 } else {
4525 rf = int(p.From.Reg)
4526 }
4527 rt := int(p.Reg)
4528 o1 |= uint32(rf&31)<<16 | uint32(rt&31)<<5
4529
4530 case 57:
4531 o1 = c.oprrr(p, p.As)
4532
4533 cond := SpecialOperand(p.From.Offset)
4534 if cond < SPOP_EQ || cond > SPOP_NV {
4535 c.ctxt.Diag("invalid condition\n%v", p)
4536 } else {
4537 cond -= SPOP_EQ
4538 }
4539
4540 nzcv := int(p.To.Offset)
4541 if nzcv&^0xF != 0 {
4542 c.ctxt.Diag("implausible condition\n%v", p)
4543 }
4544 rf := int(p.Reg)
4545 if p.GetFrom3() == nil || p.GetFrom3().Reg < REG_F0 || p.GetFrom3().Reg > REG_F31 {
4546 c.ctxt.Diag("illegal FCCMP\n%v", p)
4547 break
4548 }
4549 rt := int(p.GetFrom3().Reg)
4550 o1 |= uint32(rf&31)<<16 | uint32(cond&15)<<12 | uint32(rt&31)<<5 | uint32(nzcv)
4551
4552 case 58:
4553 o1 = c.opload(p, p.As)
4554
4555 o1 |= 0x1F << 16
4556 o1 |= uint32(p.From.Reg&31) << 5
4557 if p.As == ALDXP || p.As == ALDXPW || p.As == ALDAXP || p.As == ALDAXPW {
4558 if int(p.To.Reg) == int(p.To.Offset) {
4559 c.ctxt.Diag("constrained unpredictable behavior: %v", p)
4560 }
4561 o1 |= uint32(p.To.Offset&31) << 10
4562 } else {
4563 o1 |= 0x1F << 10
4564 }
4565 o1 |= uint32(p.To.Reg & 31)
4566
4567 case 59:
4568 s := p.RegTo2
4569 n := p.To.Reg
4570 t := p.From.Reg
4571 if isSTLXRop(p.As) {
4572 if s == t || (s == n && n != REGSP) {
4573 c.ctxt.Diag("constrained unpredictable behavior: %v", p)
4574 }
4575 } else if isSTXPop(p.As) {
4576 t2 := int16(p.From.Offset)
4577 if (s == t || s == t2) || (s == n && n != REGSP) {
4578 c.ctxt.Diag("constrained unpredictable behavior: %v", p)
4579 }
4580 }
4581 if s == REG_RSP {
4582 c.ctxt.Diag("illegal destination register: %v\n", p)
4583 }
4584 o1 = c.opstore(p, p.As)
4585
4586 if p.RegTo2 != obj.REG_NONE {
4587 o1 |= uint32(p.RegTo2&31) << 16
4588 } else {
4589 o1 |= 0x1F << 16
4590 }
4591 if isSTXPop(p.As) {
4592 o1 |= uint32(p.From.Offset&31) << 10
4593 }
4594 o1 |= uint32(p.To.Reg&31)<<5 | uint32(p.From.Reg&31)
4595
4596 case 60:
4597 d := c.brdist(p, 12, 21, 0)
4598
4599 o1 = ADR(1, uint32(d), uint32(p.To.Reg))
4600
4601 case 61:
4602 d := c.brdist(p, 0, 21, 0)
4603
4604 o1 = ADR(0, uint32(d), uint32(p.To.Reg))
4605
4606 case 62:
4607 if p.Reg == REGTMP {
4608 c.ctxt.Diag("cannot use REGTMP as source: %v\n", p)
4609 }
4610 if p.To.Reg == REG_RSP && isADDSop(p.As) {
4611 c.ctxt.Diag("illegal destination register: %v\n", p)
4612 }
4613 lsl0 := LSL0_64
4614 if isADDWop(p.As) || isANDWop(p.As) {
4615 o1 = c.omovconst(AMOVW, p, &p.From, REGTMP)
4616 lsl0 = LSL0_32
4617 } else {
4618 o1 = c.omovconst(AMOVD, p, &p.From, REGTMP)
4619 }
4620
4621 rt, r, rf := p.To.Reg, p.Reg, int16(REGTMP)
4622 if p.To.Type == obj.TYPE_NONE {
4623 rt = REGZERO
4624 }
4625 if r == obj.REG_NONE {
4626 r = rt
4627 }
4628 if rt == REGSP || r == REGSP {
4629 o2 = c.opxrrr(p, p.As, rt, r, rf, false)
4630 o2 |= uint32(lsl0)
4631 } else {
4632 o2 = c.oprrr(p, p.As)
4633 o2 |= uint32(rf&31) << 16
4634 o2 |= uint32(r&31) << 5
4635 o2 |= uint32(rt & 31)
4636 }
4637
4638 case 63:
4639 o1 |= c.oprrr(p, p.As)
4640 af := (p.From.Reg >> 5) & 15
4641 at := (p.To.Reg >> 5) & 15
4642 ar := (p.Reg >> 5) & 15
4643 sz := ARNG_4S
4644 if p.As == ASHA512SU1 {
4645 sz = ARNG_2D
4646 }
4647 if af != at || af != ar || af != int16(sz) {
4648 c.ctxt.Diag("invalid arrangement: %v", p)
4649 }
4650 o1 |= uint32(p.From.Reg&31)<<16 | uint32(p.Reg&31)<<5 | uint32(p.To.Reg&31)
4651
4652
4653 case 64:
4654 if p.From.Reg == REGTMP {
4655 c.ctxt.Diag("cannot use REGTMP as source: %v\n", p)
4656 }
4657 o1 = ADR(1, 0, REGTMP)
4658 rel := obj.Addrel(c.cursym)
4659 rel.Off = int32(c.pc)
4660 rel.Siz = 8
4661 rel.Sym = p.To.Sym
4662 rel.Add = p.To.Offset
4663
4664 if o.size(c.ctxt, p) != 8 {
4665 o2 = c.opirr(p, AADD) | REGTMP&31<<5 | REGTMP&31
4666 o3 = c.olsr12u(p, c.opstr(p, p.As), 0, REGTMP, p.From.Reg)
4667 rel.Type = objabi.R_ADDRARM64
4668 break
4669 }
4670 o2 = c.olsr12u(p, c.opstr(p, p.As), 0, REGTMP, p.From.Reg)
4671 rel.Type = c.addrRelocType(p)
4672
4673 case 65:
4674 o1 = ADR(1, 0, REGTMP)
4675 rel := obj.Addrel(c.cursym)
4676 rel.Off = int32(c.pc)
4677 rel.Siz = 8
4678 rel.Sym = p.From.Sym
4679 rel.Add = p.From.Offset
4680
4681 if o.size(c.ctxt, p) != 8 {
4682 o2 = c.opirr(p, AADD) | REGTMP&31<<5 | REGTMP&31
4683 o3 = c.olsr12u(p, c.opldr(p, p.As), 0, REGTMP, p.To.Reg)
4684 rel.Type = objabi.R_ADDRARM64
4685 break
4686 }
4687 o2 = c.olsr12u(p, c.opldr(p, p.As), 0, REGTMP, p.To.Reg)
4688 rel.Type = c.addrRelocType(p)
4689
4690 case 66:
4691 rf, rt1, rt2 := p.From.Reg, p.To.Reg, int16(p.To.Offset)
4692 if rf == obj.REG_NONE {
4693 rf = o.param
4694 }
4695 if rf == obj.REG_NONE {
4696 c.ctxt.Diag("invalid ldp source: %v\n", p)
4697 }
4698 v := c.regoff(&p.From)
4699 o1 = c.opldpstp(p, o, v, rf, rt1, rt2, 1)
4700
4701 case 67:
4702 rt, rf1, rf2 := p.To.Reg, p.From.Reg, int16(p.From.Offset)
4703 if rt == obj.REG_NONE {
4704 rt = o.param
4705 }
4706 if rt == obj.REG_NONE {
4707 c.ctxt.Diag("invalid stp destination: %v\n", p)
4708 }
4709 v := c.regoff(&p.To)
4710 o1 = c.opldpstp(p, o, v, rt, rf1, rf2, 0)
4711
4712 case 68:
4713
4714
4715 if p.As == AMOVW {
4716 c.ctxt.Diag("invalid load of 32-bit address: %v", p)
4717 }
4718 o1 = ADR(1, 0, uint32(p.To.Reg))
4719 o2 = c.opirr(p, AADD) | uint32(p.To.Reg&31)<<5 | uint32(p.To.Reg&31)
4720 rel := obj.Addrel(c.cursym)
4721 rel.Off = int32(c.pc)
4722 rel.Siz = 8
4723 rel.Sym = p.From.Sym
4724 rel.Add = p.From.Offset
4725 rel.Type = objabi.R_ADDRARM64
4726
4727 case 69:
4728 o1 = c.opirr(p, AMOVZ)
4729 o1 |= uint32(p.To.Reg & 31)
4730 rel := obj.Addrel(c.cursym)
4731 rel.Off = int32(c.pc)
4732 rel.Siz = 4
4733 rel.Sym = p.From.Sym
4734 rel.Type = objabi.R_ARM64_TLS_LE
4735 if p.From.Offset != 0 {
4736 c.ctxt.Diag("invalid offset on MOVW $tlsvar")
4737 }
4738
4739 case 70:
4740 o1 = ADR(1, 0, REGTMP)
4741 o2 = c.olsr12u(p, c.opldr(p, AMOVD), 0, REGTMP, p.To.Reg)
4742 rel := obj.Addrel(c.cursym)
4743 rel.Off = int32(c.pc)
4744 rel.Siz = 8
4745 rel.Sym = p.From.Sym
4746 rel.Add = 0
4747 rel.Type = objabi.R_ARM64_TLS_IE
4748 if p.From.Offset != 0 {
4749 c.ctxt.Diag("invalid offset on MOVW $tlsvar")
4750 }
4751
4752 case 71:
4753 o1 = ADR(1, 0, REGTMP)
4754 o2 = c.olsr12u(p, c.opldr(p, AMOVD), 0, REGTMP, p.To.Reg)
4755 rel := obj.Addrel(c.cursym)
4756 rel.Off = int32(c.pc)
4757 rel.Siz = 8
4758 rel.Sym = p.From.Sym
4759 rel.Add = 0
4760 rel.Type = objabi.R_ARM64_GOTPCREL
4761
4762 case 72:
4763 af := int((p.From.Reg >> 5) & 15)
4764 af3 := int((p.Reg >> 5) & 15)
4765 at := int((p.To.Reg >> 5) & 15)
4766 if af != af3 || af != at {
4767 c.ctxt.Diag("operand mismatch: %v", p)
4768 break
4769 }
4770 o1 = c.oprrr(p, p.As)
4771 rf := int((p.From.Reg) & 31)
4772 rt := int((p.To.Reg) & 31)
4773 r := int((p.Reg) & 31)
4774
4775 Q := 0
4776 size := 0
4777 switch af {
4778 case ARNG_16B:
4779 Q = 1
4780 size = 0
4781 case ARNG_2D:
4782 Q = 1
4783 size = 3
4784 case ARNG_2S:
4785 Q = 0
4786 size = 2
4787 case ARNG_4H:
4788 Q = 0
4789 size = 1
4790 case ARNG_4S:
4791 Q = 1
4792 size = 2
4793 case ARNG_8B:
4794 Q = 0
4795 size = 0
4796 case ARNG_8H:
4797 Q = 1
4798 size = 1
4799 default:
4800 c.ctxt.Diag("invalid arrangement: %v", p)
4801 }
4802
4803 switch p.As {
4804 case AVORR, AVAND, AVEOR, AVBIT, AVBSL, AVBIF:
4805 if af != ARNG_16B && af != ARNG_8B {
4806 c.ctxt.Diag("invalid arrangement: %v", p)
4807 }
4808 case AVFMLA, AVFMLS:
4809 if af != ARNG_2D && af != ARNG_2S && af != ARNG_4S {
4810 c.ctxt.Diag("invalid arrangement: %v", p)
4811 }
4812 case AVUMAX, AVUMIN:
4813 if af == ARNG_2D {
4814 c.ctxt.Diag("invalid arrangement: %v", p)
4815 }
4816 }
4817 switch p.As {
4818 case AVAND, AVEOR:
4819 size = 0
4820 case AVBSL:
4821 size = 1
4822 case AVORR, AVBIT, AVBIF:
4823 size = 2
4824 case AVFMLA, AVFMLS:
4825 if af == ARNG_2D {
4826 size = 1
4827 } else {
4828 size = 0
4829 }
4830 case AVRAX1:
4831 if af != ARNG_2D {
4832 c.ctxt.Diag("invalid arrangement: %v", p)
4833 }
4834 size = 0
4835 Q = 0
4836 }
4837
4838 o1 |= (uint32(Q&1) << 30) | (uint32(size&3) << 22) | (uint32(rf&31) << 16) | (uint32(r&31) << 5) | uint32(rt&31)
4839
4840 case 73:
4841 rf := int(p.From.Reg)
4842 rt := int(p.To.Reg)
4843 imm5 := 0
4844 o1 = 7<<25 | 0xf<<10
4845 index := int(p.From.Index)
4846 switch (p.From.Reg >> 5) & 15 {
4847 case ARNG_B:
4848 c.checkindex(p, index, 15)
4849 imm5 |= 1
4850 imm5 |= index << 1
4851 case ARNG_H:
4852 c.checkindex(p, index, 7)
4853 imm5 |= 2
4854 imm5 |= index << 2
4855 case ARNG_S:
4856 c.checkindex(p, index, 3)
4857 imm5 |= 4
4858 imm5 |= index << 3
4859 case ARNG_D:
4860 c.checkindex(p, index, 1)
4861 imm5 |= 8
4862 imm5 |= index << 4
4863 o1 |= 1 << 30
4864 default:
4865 c.ctxt.Diag("invalid arrangement: %v", p)
4866 }
4867 o1 |= (uint32(imm5&0x1f) << 16) | (uint32(rf&31) << 5) | uint32(rt&31)
4868
4869 case 74:
4870
4871
4872 rf, rt1, rt2 := p.From.Reg, p.To.Reg, int16(p.To.Offset)
4873 if rf == obj.REG_NONE {
4874 rf = o.param
4875 }
4876 if rf == obj.REG_NONE {
4877 c.ctxt.Diag("invalid ldp source: %v", p)
4878 }
4879 v := c.regoff(&p.From)
4880 o1 = c.oaddi12(p, v, REGTMP, rf)
4881 o2 = c.opldpstp(p, o, 0, REGTMP, rt1, rt2, 1)
4882
4883 case 75:
4884
4885
4886
4887
4888
4889
4890
4891
4892 rf, rt1, rt2 := p.From.Reg, p.To.Reg, int16(p.To.Offset)
4893 if rf == REGTMP {
4894 c.ctxt.Diag("REGTMP used in large offset load: %v", p)
4895 }
4896 if rf == obj.REG_NONE {
4897 rf = o.param
4898 }
4899 if rf == obj.REG_NONE {
4900 c.ctxt.Diag("invalid ldp source: %v", p)
4901 }
4902
4903 v := c.regoff(&p.From)
4904 if v >= -4095 && v <= 4095 {
4905 c.ctxt.Diag("%v: bad type for offset %d (should be add/sub+ldp)", p, v)
4906 }
4907
4908 hi, lo, err := splitImm24uScaled(v, 0)
4909 if err != nil {
4910 goto loadpairusepool
4911 }
4912 if p.Pool != nil {
4913 c.ctxt.Diag("%v: unused constant in pool (%v)\n", p, v)
4914 }
4915 o1 = c.oaddi(p, AADD, lo, REGTMP, int16(rf))
4916 o2 = c.oaddi(p, AADD, hi, REGTMP, REGTMP)
4917 o3 = c.opldpstp(p, o, 0, REGTMP, rt1, rt2, 1)
4918 break
4919
4920 loadpairusepool:
4921 if p.Pool == nil {
4922 c.ctxt.Diag("%v: constant is not in pool", p)
4923 }
4924 if rf == REGTMP || p.From.Reg == REGTMP {
4925 c.ctxt.Diag("REGTMP used in large offset load: %v", p)
4926 }
4927 o1 = c.omovlit(AMOVD, p, &p.From, REGTMP)
4928 o2 = c.opxrrr(p, AADD, REGTMP, rf, REGTMP, false)
4929 o3 = c.opldpstp(p, o, 0, REGTMP, rt1, rt2, 1)
4930
4931 case 76:
4932
4933
4934 rt, rf1, rf2 := p.To.Reg, p.From.Reg, int16(p.From.Offset)
4935 if rf1 == REGTMP || rf2 == REGTMP {
4936 c.ctxt.Diag("cannot use REGTMP as source: %v", p)
4937 }
4938 if rt == obj.REG_NONE {
4939 rt = o.param
4940 }
4941 if rt == obj.REG_NONE {
4942 c.ctxt.Diag("invalid stp destination: %v", p)
4943 }
4944 v := c.regoff(&p.To)
4945 o1 = c.oaddi12(p, v, REGTMP, rt)
4946 o2 = c.opldpstp(p, o, 0, REGTMP, rf1, rf2, 0)
4947
4948 case 77:
4949
4950
4951
4952
4953
4954
4955
4956
4957 rt, rf1, rf2 := p.To.Reg, p.From.Reg, int16(p.From.Offset)
4958 if rt == REGTMP || rf1 == REGTMP || rf2 == REGTMP {
4959 c.ctxt.Diag("REGTMP used in large offset store: %v", p)
4960 }
4961 if rt == obj.REG_NONE {
4962 rt = o.param
4963 }
4964 if rt == obj.REG_NONE {
4965 c.ctxt.Diag("invalid stp destination: %v", p)
4966 }
4967
4968 v := c.regoff(&p.To)
4969 if v >= -4095 && v <= 4095 {
4970 c.ctxt.Diag("%v: bad type for offset %d (should be add/sub+stp)", p, v)
4971 }
4972
4973 hi, lo, err := splitImm24uScaled(v, 0)
4974 if err != nil {
4975 goto storepairusepool
4976 }
4977 if p.Pool != nil {
4978 c.ctxt.Diag("%v: unused constant in pool (%v)\n", p, v)
4979 }
4980 o1 = c.oaddi(p, AADD, lo, REGTMP, int16(rt))
4981 o2 = c.oaddi(p, AADD, hi, REGTMP, REGTMP)
4982 o3 = c.opldpstp(p, o, 0, REGTMP, rf1, rf2, 0)
4983 break
4984
4985 storepairusepool:
4986 if p.Pool == nil {
4987 c.ctxt.Diag("%v: constant is not in pool", p)
4988 }
4989 if rt == REGTMP || p.From.Reg == REGTMP {
4990 c.ctxt.Diag("REGTMP used in large offset store: %v", p)
4991 }
4992 o1 = c.omovlit(AMOVD, p, &p.To, REGTMP)
4993 o2 = c.opxrrr(p, AADD, REGTMP, rt, REGTMP, false)
4994 o3 = c.opldpstp(p, o, 0, REGTMP, rf1, rf2, 0)
4995
4996 case 78:
4997 rf := int(p.From.Reg)
4998 rt := int(p.To.Reg)
4999 imm5 := 0
5000 o1 = 1<<30 | 7<<25 | 7<<10
5001 index := int(p.To.Index)
5002 switch (p.To.Reg >> 5) & 15 {
5003 case ARNG_B:
5004 c.checkindex(p, index, 15)
5005 imm5 |= 1
5006 imm5 |= index << 1
5007 case ARNG_H:
5008 c.checkindex(p, index, 7)
5009 imm5 |= 2
5010 imm5 |= index << 2
5011 case ARNG_S:
5012 c.checkindex(p, index, 3)
5013 imm5 |= 4
5014 imm5 |= index << 3
5015 case ARNG_D:
5016 c.checkindex(p, index, 1)
5017 imm5 |= 8
5018 imm5 |= index << 4
5019 default:
5020 c.ctxt.Diag("invalid arrangement: %v", p)
5021 }
5022 o1 |= (uint32(imm5&0x1f) << 16) | (uint32(rf&31) << 5) | uint32(rt&31)
5023
5024 case 79:
5025 rf := int(p.From.Reg)
5026 rt := int(p.To.Reg)
5027 o1 = 7<<25 | 1<<10
5028 var imm5, Q int
5029 index := int(p.From.Index)
5030 switch (p.To.Reg >> 5) & 15 {
5031 case ARNG_16B:
5032 c.checkindex(p, index, 15)
5033 Q = 1
5034 imm5 = 1
5035 imm5 |= index << 1
5036 case ARNG_2D:
5037 c.checkindex(p, index, 1)
5038 Q = 1
5039 imm5 = 8
5040 imm5 |= index << 4
5041 case ARNG_2S:
5042 c.checkindex(p, index, 3)
5043 Q = 0
5044 imm5 = 4
5045 imm5 |= index << 3
5046 case ARNG_4H:
5047 c.checkindex(p, index, 7)
5048 Q = 0
5049 imm5 = 2
5050 imm5 |= index << 2
5051 case ARNG_4S:
5052 c.checkindex(p, index, 3)
5053 Q = 1
5054 imm5 = 4
5055 imm5 |= index << 3
5056 case ARNG_8B:
5057 c.checkindex(p, index, 15)
5058 Q = 0
5059 imm5 = 1
5060 imm5 |= index << 1
5061 case ARNG_8H:
5062 c.checkindex(p, index, 7)
5063 Q = 1
5064 imm5 = 2
5065 imm5 |= index << 2
5066 default:
5067 c.ctxt.Diag("invalid arrangement: %v", p)
5068 }
5069 o1 |= (uint32(Q&1) << 30) | (uint32(imm5&0x1f) << 16)
5070 o1 |= (uint32(rf&31) << 5) | uint32(rt&31)
5071
5072 case 80:
5073 rf := int(p.From.Reg)
5074 rt := int(p.To.Reg)
5075 imm5 := 0
5076 index := int(p.From.Index)
5077 switch p.As {
5078 case AVMOV, AVDUP:
5079 o1 = 1<<30 | 15<<25 | 1<<10
5080 switch (p.From.Reg >> 5) & 15 {
5081 case ARNG_B:
5082 c.checkindex(p, index, 15)
5083 imm5 |= 1
5084 imm5 |= index << 1
5085 case ARNG_H:
5086 c.checkindex(p, index, 7)
5087 imm5 |= 2
5088 imm5 |= index << 2
5089 case ARNG_S:
5090 c.checkindex(p, index, 3)
5091 imm5 |= 4
5092 imm5 |= index << 3
5093 case ARNG_D:
5094 c.checkindex(p, index, 1)
5095 imm5 |= 8
5096 imm5 |= index << 4
5097 default:
5098 c.ctxt.Diag("invalid arrangement: %v", p)
5099 }
5100 default:
5101 c.ctxt.Diag("unsupported op %v", p.As)
5102 }
5103 o1 |= (uint32(imm5&0x1f) << 16) | (uint32(rf&31) << 5) | uint32(rt&31)
5104
5105 case 81:
5106 c.checkoffset(p, p.As)
5107 r := int(p.From.Reg)
5108 o1 = c.oprrr(p, p.As)
5109 if o.scond == C_XPOST {
5110 o1 |= 1 << 23
5111 if p.From.Index == 0 {
5112
5113 o1 |= 0x1f << 16
5114 } else {
5115
5116 if isRegShiftOrExt(&p.From) {
5117 c.ctxt.Diag("invalid extended register op: %v\n", p)
5118 }
5119 o1 |= uint32(p.From.Index&0x1f) << 16
5120 }
5121 }
5122 o1 |= uint32(p.To.Offset)
5123
5124
5125 o1 = c.maskOpvldvst(p, o1)
5126 o1 |= uint32(r&31) << 5
5127
5128 case 82:
5129 rf := int(p.From.Reg)
5130 rt := int(p.To.Reg)
5131 o1 = 7<<25 | 3<<10
5132 var imm5, Q uint32
5133 switch (p.To.Reg >> 5) & 15 {
5134 case ARNG_16B:
5135 Q = 1
5136 imm5 = 1
5137 case ARNG_2D:
5138 Q = 1
5139 imm5 = 8
5140 case ARNG_2S:
5141 Q = 0
5142 imm5 = 4
5143 case ARNG_4H:
5144 Q = 0
5145 imm5 = 2
5146 case ARNG_4S:
5147 Q = 1
5148 imm5 = 4
5149 case ARNG_8B:
5150 Q = 0
5151 imm5 = 1
5152 case ARNG_8H:
5153 Q = 1
5154 imm5 = 2
5155 default:
5156 c.ctxt.Diag("invalid arrangement: %v\n", p)
5157 }
5158 o1 |= (Q & 1 << 30) | (imm5 & 0x1f << 16)
5159 o1 |= (uint32(rf&31) << 5) | uint32(rt&31)
5160
5161 case 83:
5162 af := int((p.From.Reg >> 5) & 15)
5163 at := int((p.To.Reg >> 5) & 15)
5164 if af != at {
5165 c.ctxt.Diag("invalid arrangement: %v\n", p)
5166 }
5167 o1 = c.oprrr(p, p.As)
5168 rf := int((p.From.Reg) & 31)
5169 rt := int((p.To.Reg) & 31)
5170
5171 var Q, size uint32
5172 switch af {
5173 case ARNG_8B:
5174 Q = 0
5175 size = 0
5176 case ARNG_16B:
5177 Q = 1
5178 size = 0
5179 case ARNG_4H:
5180 Q = 0
5181 size = 1
5182 case ARNG_8H:
5183 Q = 1
5184 size = 1
5185 case ARNG_2S:
5186 Q = 0
5187 size = 2
5188 case ARNG_4S:
5189 Q = 1
5190 size = 2
5191 default:
5192 c.ctxt.Diag("invalid arrangement: %v\n", p)
5193 }
5194
5195 if (p.As == AVMOV || p.As == AVRBIT || p.As == AVCNT) && (af != ARNG_16B && af != ARNG_8B) {
5196 c.ctxt.Diag("invalid arrangement: %v", p)
5197 }
5198
5199 if p.As == AVREV32 && (af == ARNG_2S || af == ARNG_4S) {
5200 c.ctxt.Diag("invalid arrangement: %v", p)
5201 }
5202
5203 if p.As == AVREV16 && af != ARNG_8B && af != ARNG_16B {
5204 c.ctxt.Diag("invalid arrangement: %v", p)
5205 }
5206
5207 if p.As == AVMOV {
5208 o1 |= uint32(rf&31) << 16
5209 }
5210
5211 if p.As == AVRBIT {
5212 size = 1
5213 }
5214
5215 o1 |= (Q&1)<<30 | (size&3)<<22 | uint32(rf&31)<<5 | uint32(rt&31)
5216
5217 case 84:
5218 c.checkoffset(p, p.As)
5219 r := int(p.To.Reg)
5220 o1 = 3 << 26
5221 if o.scond == C_XPOST {
5222 o1 |= 1 << 23
5223 if p.To.Index == 0 {
5224
5225 o1 |= 0x1f << 16
5226 } else {
5227
5228 if isRegShiftOrExt(&p.To) {
5229 c.ctxt.Diag("invalid extended register: %v\n", p)
5230 }
5231 o1 |= uint32(p.To.Index&31) << 16
5232 }
5233 }
5234 o1 |= uint32(p.From.Offset)
5235
5236
5237 o1 = c.maskOpvldvst(p, o1)
5238 o1 |= uint32(r&31) << 5
5239
5240 case 85:
5241 af := int((p.From.Reg >> 5) & 15)
5242 o1 = c.oprrr(p, p.As)
5243 rf := int((p.From.Reg) & 31)
5244 rt := int((p.To.Reg) & 31)
5245 Q := 0
5246 size := 0
5247 switch af {
5248 case ARNG_8B:
5249 Q = 0
5250 size = 0
5251 case ARNG_16B:
5252 Q = 1
5253 size = 0
5254 case ARNG_4H:
5255 Q = 0
5256 size = 1
5257 case ARNG_8H:
5258 Q = 1
5259 size = 1
5260 case ARNG_4S:
5261 Q = 1
5262 size = 2
5263 default:
5264 c.ctxt.Diag("invalid arrangement: %v\n", p)
5265 }
5266 o1 |= (uint32(Q&1) << 30) | (uint32(size&3) << 22) | (uint32(rf&31) << 5) | uint32(rt&31)
5267
5268 case 86:
5269 at := int((p.To.Reg >> 5) & 15)
5270 r := int(p.From.Offset)
5271 if r > 255 || r < 0 {
5272 c.ctxt.Diag("immediate constant out of range: %v\n", p)
5273 }
5274 rt := int((p.To.Reg) & 31)
5275 Q := 0
5276 switch at {
5277 case ARNG_8B:
5278 Q = 0
5279 case ARNG_16B:
5280 Q = 1
5281 default:
5282 c.ctxt.Diag("invalid arrangement: %v\n", p)
5283 }
5284 o1 = 0xf<<24 | 0xe<<12 | 1<<10
5285 o1 |= (uint32(Q&1) << 30) | (uint32((r>>5)&7) << 16) | (uint32(r&0x1f) << 5) | uint32(rt&31)
5286
5287 case 87:
5288 rf1, rf2 := p.From.Reg, int16(p.From.Offset)
5289 if rf1 == REGTMP || rf2 == REGTMP {
5290 c.ctxt.Diag("cannot use REGTMP as source: %v", p)
5291 }
5292 o1 = ADR(1, 0, REGTMP)
5293 o2 = c.opirr(p, AADD) | REGTMP&31<<5 | REGTMP&31
5294 rel := obj.Addrel(c.cursym)
5295 rel.Off = int32(c.pc)
5296 rel.Siz = 8
5297 rel.Sym = p.To.Sym
5298 rel.Add = p.To.Offset
5299 rel.Type = objabi.R_ADDRARM64
5300 o3 = c.opldpstp(p, o, 0, REGTMP, rf1, rf2, 0)
5301
5302 case 88:
5303 rt1, rt2 := p.To.Reg, int16(p.To.Offset)
5304 o1 = ADR(1, 0, REGTMP)
5305 o2 = c.opirr(p, AADD) | REGTMP&31<<5 | REGTMP&31
5306 rel := obj.Addrel(c.cursym)
5307 rel.Off = int32(c.pc)
5308 rel.Siz = 8
5309 rel.Sym = p.From.Sym
5310 rel.Add = p.From.Offset
5311 rel.Type = objabi.R_ADDRARM64
5312 o3 = c.opldpstp(p, o, 0, REGTMP, rt1, rt2, 1)
5313
5314 case 89:
5315 switch p.As {
5316 case AVADD:
5317 o1 = 5<<28 | 7<<25 | 7<<21 | 1<<15 | 1<<10
5318
5319 case AVSUB:
5320 o1 = 7<<28 | 7<<25 | 7<<21 | 1<<15 | 1<<10
5321
5322 default:
5323 c.ctxt.Diag("bad opcode: %v\n", p)
5324 break
5325 }
5326
5327 rf := int(p.From.Reg)
5328 rt := int(p.To.Reg)
5329 r := int(p.Reg)
5330 if r == obj.REG_NONE {
5331 r = rt
5332 }
5333 o1 |= (uint32(rf&31) << 16) | (uint32(r&31) << 5) | uint32(rt&31)
5334
5335
5336
5337
5338
5339
5340 case 90:
5341 o1 = 0xbea71700
5342
5343 case 91:
5344 imm := uint32(p.From.Offset)
5345 r := p.From.Reg
5346 var v uint32
5347 var ok bool
5348 if p.To.Type == obj.TYPE_CONST {
5349 v = uint32(p.To.Offset)
5350 ok = v <= 31
5351 } else {
5352 v, ok = prfopfield[SpecialOperand(p.To.Offset)]
5353 }
5354 if !ok {
5355 c.ctxt.Diag("illegal prefetch operation:\n%v", p)
5356 }
5357
5358 o1 = c.opirr(p, p.As)
5359 o1 |= (uint32(r&31) << 5) | (uint32((imm>>3)&0xfff) << 10) | (uint32(v & 31))
5360
5361 case 92:
5362 rf := int(p.From.Reg)
5363 rt := int(p.To.Reg)
5364 imm4 := 0
5365 imm5 := 0
5366 o1 = 3<<29 | 7<<25 | 1<<10
5367 index1 := int(p.To.Index)
5368 index2 := int(p.From.Index)
5369 if ((p.To.Reg >> 5) & 15) != ((p.From.Reg >> 5) & 15) {
5370 c.ctxt.Diag("operand mismatch: %v", p)
5371 }
5372 switch (p.To.Reg >> 5) & 15 {
5373 case ARNG_B:
5374 c.checkindex(p, index1, 15)
5375 c.checkindex(p, index2, 15)
5376 imm5 |= 1
5377 imm5 |= index1 << 1
5378 imm4 |= index2
5379 case ARNG_H:
5380 c.checkindex(p, index1, 7)
5381 c.checkindex(p, index2, 7)
5382 imm5 |= 2
5383 imm5 |= index1 << 2
5384 imm4 |= index2 << 1
5385 case ARNG_S:
5386 c.checkindex(p, index1, 3)
5387 c.checkindex(p, index2, 3)
5388 imm5 |= 4
5389 imm5 |= index1 << 3
5390 imm4 |= index2 << 2
5391 case ARNG_D:
5392 c.checkindex(p, index1, 1)
5393 c.checkindex(p, index2, 1)
5394 imm5 |= 8
5395 imm5 |= index1 << 4
5396 imm4 |= index2 << 3
5397 default:
5398 c.ctxt.Diag("invalid arrangement: %v", p)
5399 }
5400 o1 |= (uint32(imm5&0x1f) << 16) | (uint32(imm4&0xf) << 11) | (uint32(rf&31) << 5) | uint32(rt&31)
5401
5402 case 93:
5403 af := uint8((p.From.Reg >> 5) & 15)
5404 at := uint8((p.To.Reg >> 5) & 15)
5405 a := uint8((p.Reg >> 5) & 15)
5406 if af != a {
5407 c.ctxt.Diag("invalid arrangement: %v", p)
5408 }
5409
5410 var Q, size uint32
5411 if p.As == AVPMULL2 {
5412 Q = 1
5413 }
5414 switch pack(Q, at, af) {
5415 case pack(0, ARNG_8H, ARNG_8B), pack(1, ARNG_8H, ARNG_16B):
5416 size = 0
5417 case pack(0, ARNG_1Q, ARNG_1D), pack(1, ARNG_1Q, ARNG_2D):
5418 size = 3
5419 default:
5420 c.ctxt.Diag("operand mismatch: %v\n", p)
5421 }
5422
5423 o1 = c.oprrr(p, p.As)
5424 rf := int((p.From.Reg) & 31)
5425 rt := int((p.To.Reg) & 31)
5426 r := int((p.Reg) & 31)
5427 o1 |= ((Q & 1) << 30) | ((size & 3) << 22) | (uint32(rf&31) << 16) | (uint32(r&31) << 5) | uint32(rt&31)
5428
5429 case 94:
5430 af := int(((p.GetFrom3().Reg) >> 5) & 15)
5431 at := int((p.To.Reg >> 5) & 15)
5432 a := int((p.Reg >> 5) & 15)
5433 index := int(p.From.Offset)
5434
5435 if af != a || af != at {
5436 c.ctxt.Diag("invalid arrangement: %v", p)
5437 break
5438 }
5439
5440 var Q uint32
5441 var b int
5442 if af == ARNG_8B {
5443 Q = 0
5444 b = 7
5445 } else if af == ARNG_16B {
5446 Q = 1
5447 b = 15
5448 } else {
5449 c.ctxt.Diag("invalid arrangement, should be B8 or B16: %v", p)
5450 break
5451 }
5452
5453 if index < 0 || index > b {
5454 c.ctxt.Diag("illegal offset: %v", p)
5455 }
5456
5457 o1 = c.opirr(p, p.As)
5458 rf := int((p.GetFrom3().Reg) & 31)
5459 rt := int((p.To.Reg) & 31)
5460 r := int((p.Reg) & 31)
5461
5462 o1 |= ((Q & 1) << 30) | (uint32(r&31) << 16) | (uint32(index&15) << 11) | (uint32(rf&31) << 5) | uint32(rt&31)
5463
5464 case 95:
5465 at := int((p.To.Reg >> 5) & 15)
5466 af := int((p.Reg >> 5) & 15)
5467 shift := int(p.From.Offset)
5468
5469 if af != at {
5470 c.ctxt.Diag("invalid arrangement on op Vn.<T>, Vd.<T>: %v", p)
5471 }
5472
5473 var Q uint32
5474 var imax, esize int
5475
5476 switch af {
5477 case ARNG_8B, ARNG_4H, ARNG_2S:
5478 Q = 0
5479 case ARNG_16B, ARNG_8H, ARNG_4S, ARNG_2D:
5480 Q = 1
5481 default:
5482 c.ctxt.Diag("invalid arrangement on op Vn.<T>, Vd.<T>: %v", p)
5483 }
5484
5485 switch af {
5486 case ARNG_8B, ARNG_16B:
5487 imax = 15
5488 esize = 8
5489 case ARNG_4H, ARNG_8H:
5490 imax = 31
5491 esize = 16
5492 case ARNG_2S, ARNG_4S:
5493 imax = 63
5494 esize = 32
5495 case ARNG_2D:
5496 imax = 127
5497 esize = 64
5498 }
5499
5500 imm := 0
5501 switch p.As {
5502 case AVUSHR, AVSRI, AVUSRA:
5503 imm = esize*2 - shift
5504 if imm < esize || imm > imax {
5505 c.ctxt.Diag("shift out of range: %v", p)
5506 }
5507 case AVSHL, AVSLI:
5508 imm = esize + shift
5509 if imm > imax {
5510 c.ctxt.Diag("shift out of range: %v", p)
5511 }
5512 default:
5513 c.ctxt.Diag("invalid instruction %v\n", p)
5514 }
5515
5516 o1 = c.opirr(p, p.As)
5517 rt := int((p.To.Reg) & 31)
5518 rf := int((p.Reg) & 31)
5519
5520 o1 |= ((Q & 1) << 30) | (uint32(imm&0x7f) << 16) | (uint32(rf&31) << 5) | uint32(rt&31)
5521
5522 case 96:
5523 af := int((p.From.Reg >> 5) & 15)
5524 rt := int((p.From.Reg) & 31)
5525 rf := int((p.To.Reg) & 31)
5526 r := int(p.To.Index & 31)
5527 index := int(p.From.Index)
5528 offset := c.regoff(&p.To)
5529
5530 if o.scond == C_XPOST {
5531 if (p.To.Index != 0) && (offset != 0) {
5532 c.ctxt.Diag("invalid offset: %v", p)
5533 }
5534 if p.To.Index == 0 && offset == 0 {
5535 c.ctxt.Diag("invalid offset: %v", p)
5536 }
5537 }
5538
5539 if offset != 0 {
5540 r = 31
5541 }
5542
5543 var Q, S, size int
5544 var opcode uint32
5545 switch af {
5546 case ARNG_B:
5547 c.checkindex(p, index, 15)
5548 if o.scond == C_XPOST && offset != 0 && offset != 1 {
5549 c.ctxt.Diag("invalid offset: %v", p)
5550 }
5551 Q = index >> 3
5552 S = (index >> 2) & 1
5553 size = index & 3
5554 opcode = 0
5555 case ARNG_H:
5556 c.checkindex(p, index, 7)
5557 if o.scond == C_XPOST && offset != 0 && offset != 2 {
5558 c.ctxt.Diag("invalid offset: %v", p)
5559 }
5560 Q = index >> 2
5561 S = (index >> 1) & 1
5562 size = (index & 1) << 1
5563 opcode = 2
5564 case ARNG_S:
5565 c.checkindex(p, index, 3)
5566 if o.scond == C_XPOST && offset != 0 && offset != 4 {
5567 c.ctxt.Diag("invalid offset: %v", p)
5568 }
5569 Q = index >> 1
5570 S = index & 1
5571 size = 0
5572 opcode = 4
5573 case ARNG_D:
5574 c.checkindex(p, index, 1)
5575 if o.scond == C_XPOST && offset != 0 && offset != 8 {
5576 c.ctxt.Diag("invalid offset: %v", p)
5577 }
5578 Q = index
5579 S = 0
5580 size = 1
5581 opcode = 4
5582 default:
5583 c.ctxt.Diag("invalid arrangement: %v", p)
5584 }
5585
5586 if o.scond == C_XPOST {
5587 o1 |= 27 << 23
5588 } else {
5589 o1 |= 26 << 23
5590 }
5591
5592 o1 |= (uint32(Q&1) << 30) | (uint32(r&31) << 16) | ((opcode & 7) << 13) | (uint32(S&1) << 12) | (uint32(size&3) << 10) | (uint32(rf&31) << 5) | uint32(rt&31)
5593
5594 case 97:
5595 at := int((p.To.Reg >> 5) & 15)
5596 rt := int((p.To.Reg) & 31)
5597 rf := int((p.From.Reg) & 31)
5598 r := int(p.From.Index & 31)
5599 index := int(p.To.Index)
5600 offset := c.regoff(&p.From)
5601
5602 if o.scond == C_XPOST {
5603 if (p.From.Index != 0) && (offset != 0) {
5604 c.ctxt.Diag("invalid offset: %v", p)
5605 }
5606 if p.From.Index == 0 && offset == 0 {
5607 c.ctxt.Diag("invalid offset: %v", p)
5608 }
5609 }
5610
5611 if offset != 0 {
5612 r = 31
5613 }
5614
5615 Q := 0
5616 S := 0
5617 size := 0
5618 var opcode uint32
5619 switch at {
5620 case ARNG_B:
5621 c.checkindex(p, index, 15)
5622 if o.scond == C_XPOST && offset != 0 && offset != 1 {
5623 c.ctxt.Diag("invalid offset: %v", p)
5624 }
5625 Q = index >> 3
5626 S = (index >> 2) & 1
5627 size = index & 3
5628 opcode = 0
5629 case ARNG_H:
5630 c.checkindex(p, index, 7)
5631 if o.scond == C_XPOST && offset != 0 && offset != 2 {
5632 c.ctxt.Diag("invalid offset: %v", p)
5633 }
5634 Q = index >> 2
5635 S = (index >> 1) & 1
5636 size = (index & 1) << 1
5637 opcode = 2
5638 case ARNG_S:
5639 c.checkindex(p, index, 3)
5640 if o.scond == C_XPOST && offset != 0 && offset != 4 {
5641 c.ctxt.Diag("invalid offset: %v", p)
5642 }
5643 Q = index >> 1
5644 S = index & 1
5645 size = 0
5646 opcode = 4
5647 case ARNG_D:
5648 c.checkindex(p, index, 1)
5649 if o.scond == C_XPOST && offset != 0 && offset != 8 {
5650 c.ctxt.Diag("invalid offset: %v", p)
5651 }
5652 Q = index
5653 S = 0
5654 size = 1
5655 opcode = 4
5656 default:
5657 c.ctxt.Diag("invalid arrangement: %v", p)
5658 }
5659
5660 if o.scond == C_XPOST {
5661 o1 |= 110 << 21
5662 } else {
5663 o1 |= 106 << 21
5664 }
5665
5666 o1 |= (uint32(Q&1) << 30) | (uint32(r&31) << 16) | ((opcode & 7) << 13) | (uint32(S&1) << 12) | (uint32(size&3) << 10) | (uint32(rf&31) << 5) | uint32(rt&31)
5667
5668 case 98:
5669 if isRegShiftOrExt(&p.From) {
5670
5671 c.checkShiftAmount(p, &p.From)
5672
5673 o1 = c.opldrr(p, p.As, true)
5674 o1 |= c.encRegShiftOrExt(p, &p.From, p.From.Index)
5675 } else {
5676
5677 o1 = c.opldrr(p, p.As, false)
5678 o1 |= uint32(p.From.Index&31) << 16
5679 }
5680 o1 |= uint32(p.From.Reg&31) << 5
5681 rt := int(p.To.Reg)
5682 o1 |= uint32(rt & 31)
5683
5684 case 99:
5685 if isRegShiftOrExt(&p.To) {
5686
5687 c.checkShiftAmount(p, &p.To)
5688
5689 o1 = c.opstrr(p, p.As, true)
5690 o1 |= c.encRegShiftOrExt(p, &p.To, p.To.Index)
5691 } else {
5692
5693 o1 = c.opstrr(p, p.As, false)
5694 o1 |= uint32(p.To.Index&31) << 16
5695 }
5696 o1 |= uint32(p.To.Reg&31) << 5
5697 rf := int(p.From.Reg)
5698 o1 |= uint32(rf & 31)
5699
5700 case 100:
5701 af := int((p.From.Reg >> 5) & 15)
5702 at := int((p.To.Reg >> 5) & 15)
5703 if af != at {
5704 c.ctxt.Diag("invalid arrangement: %v\n", p)
5705 }
5706 var q, len uint32
5707 switch af {
5708 case ARNG_8B:
5709 q = 0
5710 case ARNG_16B:
5711 q = 1
5712 default:
5713 c.ctxt.Diag("invalid arrangement: %v", p)
5714 }
5715 rf := int(p.From.Reg)
5716 rt := int(p.To.Reg)
5717 offset := int(p.GetFrom3().Offset)
5718 opcode := (offset >> 12) & 15
5719 switch opcode {
5720 case 0x7:
5721 len = 0
5722 case 0xa:
5723 len = 1
5724 case 0x6:
5725 len = 2
5726 case 0x2:
5727 len = 3
5728 default:
5729 c.ctxt.Diag("invalid register numbers in ARM64 register list: %v", p)
5730 }
5731 var op uint32
5732 switch p.As {
5733 case AVTBL:
5734 op = 0
5735 case AVTBX:
5736 op = 1
5737 }
5738 o1 = q<<30 | 0xe<<24 | len<<13 | op<<12
5739 o1 |= (uint32(rf&31) << 16) | uint32(offset&31)<<5 | uint32(rt&31)
5740
5741 case 102:
5742 o1 = c.opirr(p, p.As)
5743 rf := p.Reg
5744 af := uint8((p.Reg >> 5) & 15)
5745 at := uint8((p.To.Reg >> 5) & 15)
5746 shift := int(p.From.Offset)
5747 if p.As == AVUXTL || p.As == AVUXTL2 {
5748 rf = p.From.Reg
5749 af = uint8((p.From.Reg >> 5) & 15)
5750 shift = 0
5751 }
5752
5753 Q := (o1 >> 30) & 1
5754 var immh, width uint8
5755 switch pack(Q, af, at) {
5756 case pack(0, ARNG_8B, ARNG_8H):
5757 immh, width = 1, 8
5758 case pack(1, ARNG_16B, ARNG_8H):
5759 immh, width = 1, 8
5760 case pack(0, ARNG_4H, ARNG_4S):
5761 immh, width = 2, 16
5762 case pack(1, ARNG_8H, ARNG_4S):
5763 immh, width = 2, 16
5764 case pack(0, ARNG_2S, ARNG_2D):
5765 immh, width = 4, 32
5766 case pack(1, ARNG_4S, ARNG_2D):
5767 immh, width = 4, 32
5768 default:
5769 c.ctxt.Diag("operand mismatch: %v\n", p)
5770 }
5771 if !(0 <= shift && shift <= int(width-1)) {
5772 c.ctxt.Diag("shift amount out of range: %v\n", p)
5773 }
5774 o1 |= uint32(immh)<<19 | uint32(shift)<<16 | uint32(rf&31)<<5 | uint32(p.To.Reg&31)
5775
5776 case 103:
5777 ta := (p.From.Reg >> 5) & 15
5778 tm := (p.Reg >> 5) & 15
5779 td := (p.To.Reg >> 5) & 15
5780 tn := ((p.GetFrom3().Reg) >> 5) & 15
5781
5782 if ta != tm || ta != tn || ta != td || ta != ARNG_16B {
5783 c.ctxt.Diag("invalid arrangement: %v", p)
5784 break
5785 }
5786
5787 o1 = c.oprrr(p, p.As)
5788 ra := int(p.From.Reg)
5789 rm := int(p.Reg)
5790 rn := int(p.GetFrom3().Reg)
5791 rd := int(p.To.Reg)
5792 o1 |= uint32(rm&31)<<16 | uint32(ra&31)<<10 | uint32(rn&31)<<5 | uint32(rd)&31
5793
5794 case 104:
5795 af := ((p.GetFrom3().Reg) >> 5) & 15
5796 at := (p.To.Reg >> 5) & 15
5797 a := (p.Reg >> 5) & 15
5798 index := int(p.From.Offset)
5799
5800 if af != a || af != at {
5801 c.ctxt.Diag("invalid arrangement: %v", p)
5802 break
5803 }
5804
5805 if af != ARNG_2D {
5806 c.ctxt.Diag("invalid arrangement, should be D2: %v", p)
5807 break
5808 }
5809
5810 if index < 0 || index > 63 {
5811 c.ctxt.Diag("illegal offset: %v", p)
5812 }
5813
5814 o1 = c.opirr(p, p.As)
5815 rf := (p.GetFrom3().Reg) & 31
5816 rt := (p.To.Reg) & 31
5817 r := (p.Reg) & 31
5818
5819 o1 |= (uint32(r&31) << 16) | (uint32(index&63) << 10) | (uint32(rf&31) << 5) | uint32(rt&31)
5820
5821 case 105:
5822 af := uint8((p.From.Reg >> 5) & 15)
5823 at := uint8((p.To.Reg >> 5) & 15)
5824 a := uint8((p.Reg >> 5) & 15)
5825 if at != a {
5826 c.ctxt.Diag("invalid arrangement: %v", p)
5827 break
5828 }
5829
5830 var Q, size uint32
5831 if p.As == AVUADDW2 {
5832 Q = 1
5833 }
5834 switch pack(Q, at, af) {
5835 case pack(0, ARNG_8H, ARNG_8B), pack(1, ARNG_8H, ARNG_16B):
5836 size = 0
5837 case pack(0, ARNG_4S, ARNG_4H), pack(1, ARNG_4S, ARNG_8H):
5838 size = 1
5839 case pack(0, ARNG_2D, ARNG_2S), pack(1, ARNG_2D, ARNG_4S):
5840 size = 2
5841 default:
5842 c.ctxt.Diag("operand mismatch: %v\n", p)
5843 }
5844
5845 o1 = c.oprrr(p, p.As)
5846 rf := int((p.From.Reg) & 31)
5847 rt := int((p.To.Reg) & 31)
5848 r := int((p.Reg) & 31)
5849 o1 |= ((Q & 1) << 30) | ((size & 3) << 22) | (uint32(rf&31) << 16) | (uint32(r&31) << 5) | uint32(rt&31)
5850
5851 case 106:
5852 rs := p.From.Reg
5853 rt := p.GetTo2().Reg
5854 rb := p.To.Reg
5855 rs1 := int16(p.From.Offset)
5856 rt1 := int16(p.GetTo2().Offset)
5857
5858 enc, ok := atomicCASP[p.As]
5859 if !ok {
5860 c.ctxt.Diag("invalid CASP-like atomic instructions: %v\n", p)
5861 }
5862
5863 switch {
5864 case rs&1 != 0:
5865 c.ctxt.Diag("source register pair must start from even register: %v\n", p)
5866 break
5867 case rt&1 != 0:
5868 c.ctxt.Diag("destination register pair must start from even register: %v\n", p)
5869 break
5870 case rs != rs1-1:
5871 c.ctxt.Diag("source register pair must be contiguous: %v\n", p)
5872 break
5873 case rt != rt1-1:
5874 c.ctxt.Diag("destination register pair must be contiguous: %v\n", p)
5875 break
5876 }
5877
5878 if rt == REG_RSP {
5879 c.ctxt.Diag("illegal destination register: %v\n", p)
5880 }
5881 o1 |= enc | uint32(rs&31)<<16 | uint32(rb&31)<<5 | uint32(rt&31)
5882
5883 case 107:
5884 op, ok := sysInstFields[SpecialOperand(p.From.Offset)]
5885 if !ok || (p.As == ATLBI && op.cn != 8) || (p.As == ADC && op.cn != 7) {
5886 c.ctxt.Diag("illegal argument: %v\n", p)
5887 break
5888 }
5889 o1 = c.opirr(p, p.As)
5890 if op.hasOperand2 {
5891 if p.To.Reg == obj.REG_NONE {
5892 c.ctxt.Diag("missing register at operand 2: %v\n", p)
5893 }
5894 o1 |= uint32(p.To.Reg & 0x1F)
5895 } else {
5896 if p.To.Reg != obj.REG_NONE || p.Reg != obj.REG_NONE {
5897 c.ctxt.Diag("extraneous register at operand 2: %v\n", p)
5898 }
5899 o1 |= uint32(0x1F)
5900 }
5901 o1 |= uint32(SYSARG4(int(op.op1), int(op.cn), int(op.cm), int(op.op2)))
5902 }
5903 out[0] = o1
5904 out[1] = o2
5905 out[2] = o3
5906 out[3] = o4
5907 out[4] = o5
5908 }
5909
5910 func (c *ctxt7) addrRelocType(p *obj.Prog) objabi.RelocType {
5911 switch movesize(p.As) {
5912 case 0:
5913 return objabi.R_ARM64_PCREL_LDST8
5914 case 1:
5915 return objabi.R_ARM64_PCREL_LDST16
5916 case 2:
5917 return objabi.R_ARM64_PCREL_LDST32
5918 case 3:
5919 return objabi.R_ARM64_PCREL_LDST64
5920 default:
5921 c.ctxt.Diag("use R_ADDRARM64 relocation type for: %v\n", p)
5922 }
5923 return -1
5924 }
5925
5926
5932 func (c *ctxt7) oprrr(p *obj.Prog, a obj.As) uint32 {
5933 switch a {
5934 case AADC:
5935 return S64 | 0<<30 | 0<<29 | 0xd0<<21 | 0<<10
5936
5937 case AADCW:
5938 return S32 | 0<<30 | 0<<29 | 0xd0<<21 | 0<<10
5939
5940 case AADCS:
5941 return S64 | 0<<30 | 1<<29 | 0xd0<<21 | 0<<10
5942
5943 case AADCSW:
5944 return S32 | 0<<30 | 1<<29 | 0xd0<<21 | 0<<10
5945
5946 case ANGC, ASBC:
5947 return S64 | 1<<30 | 0<<29 | 0xd0<<21 | 0<<10
5948
5949 case ANGCS, ASBCS:
5950 return S64 | 1<<30 | 1<<29 | 0xd0<<21 | 0<<10
5951
5952 case ANGCW, ASBCW:
5953 return S32 | 1<<30 | 0<<29 | 0xd0<<21 | 0<<10
5954
5955 case ANGCSW, ASBCSW:
5956 return S32 | 1<<30 | 1<<29 | 0xd0<<21 | 0<<10
5957
5958 case AADD:
5959 return S64 | 0<<30 | 0<<29 | 0x0b<<24 | 0<<22 | 0<<21 | 0<<10
5960
5961 case AADDW:
5962 return S32 | 0<<30 | 0<<29 | 0x0b<<24 | 0<<22 | 0<<21 | 0<<10
5963
5964 case ACMN, AADDS:
5965 return S64 | 0<<30 | 1<<29 | 0x0b<<24 | 0<<22 | 0<<21 | 0<<10
5966
5967 case ACMNW, AADDSW:
5968 return S32 | 0<<30 | 1<<29 | 0x0b<<24 | 0<<22 | 0<<21 | 0<<10
5969
5970 case ASUB:
5971 return S64 | 1<<30 | 0<<29 | 0x0b<<24 | 0<<22 | 0<<21 | 0<<10
5972
5973 case ASUBW:
5974 return S32 | 1<<30 | 0<<29 | 0x0b<<24 | 0<<22 | 0<<21 | 0<<10
5975
5976 case ACMP, ASUBS:
5977 return S64 | 1<<30 | 1<<29 | 0x0b<<24 | 0<<22 | 0<<21 | 0<<10
5978
5979 case ACMPW, ASUBSW:
5980 return S32 | 1<<30 | 1<<29 | 0x0b<<24 | 0<<22 | 0<<21 | 0<<10
5981
5982 case AAND:
5983 return S64 | 0<<29 | 0xA<<24
5984
5985 case AANDW:
5986 return S32 | 0<<29 | 0xA<<24
5987
5988 case AMOVD, AORR:
5989 return S64 | 1<<29 | 0xA<<24
5990
5991
5992 case AMOVWU, AORRW:
5993 return S32 | 1<<29 | 0xA<<24
5994
5995 case AEOR:
5996 return S64 | 2<<29 | 0xA<<24
5997
5998 case AEORW:
5999 return S32 | 2<<29 | 0xA<<24
6000
6001 case AANDS, ATST:
6002 return S64 | 3<<29 | 0xA<<24
6003
6004 case AANDSW, ATSTW:
6005 return S32 | 3<<29 | 0xA<<24
6006
6007 case ABIC:
6008 return S64 | 0<<29 | 0xA<<24 | 1<<21
6009
6010 case ABICW:
6011 return S32 | 0<<29 | 0xA<<24 | 1<<21
6012
6013 case ABICS:
6014 return S64 | 3<<29 | 0xA<<24 | 1<<21
6015
6016 case ABICSW:
6017 return S32 | 3<<29 | 0xA<<24 | 1<<21
6018
6019 case AEON:
6020 return S64 | 2<<29 | 0xA<<24 | 1<<21
6021
6022 case AEONW:
6023 return S32 | 2<<29 | 0xA<<24 | 1<<21
6024
6025 case AMVN, AORN:
6026 return S64 | 1<<29 | 0xA<<24 | 1<<21
6027
6028 case AMVNW, AORNW:
6029 return S32 | 1<<29 | 0xA<<24 | 1<<21
6030
6031 case AASR:
6032 return S64 | OPDP2(10)
6033
6034 case AASRW:
6035 return S32 | OPDP2(10)
6036
6037 case ALSL:
6038 return S64 | OPDP2(8)
6039
6040 case ALSLW:
6041 return S32 | OPDP2(8)
6042
6043 case ALSR:
6044 return S64 | OPDP2(9)
6045
6046 case ALSRW:
6047 return S32 | OPDP2(9)
6048
6049 case AROR:
6050 return S64 | OPDP2(11)
6051
6052 case ARORW:
6053 return S32 | OPDP2(11)
6054
6055 case ACCMN:
6056 return S64 | 0<<30 | 1<<29 | 0xD2<<21 | 0<<11 | 0<<10 | 0<<4
6057
6058 case ACCMNW:
6059 return S32 | 0<<30 | 1<<29 | 0xD2<<21 | 0<<11 | 0<<10 | 0<<4
6060
6061 case ACCMP:
6062 return S64 | 1<<30 | 1<<29 | 0xD2<<21 | 0<<11 | 0<<10 | 0<<4
6063
6064 case ACCMPW:
6065 return S32 | 1<<30 | 1<<29 | 0xD2<<21 | 0<<11 | 0<<10 | 0<<4
6066
6067 case ACRC32B:
6068 return S32 | OPDP2(16)
6069
6070 case ACRC32H:
6071 return S32 | OPDP2(17)
6072
6073 case ACRC32W:
6074 return S32 | OPDP2(18)
6075
6076 case ACRC32X:
6077 return S64 | OPDP2(19)
6078
6079 case ACRC32CB:
6080 return S32 | OPDP2(20)
6081
6082 case ACRC32CH:
6083 return S32 | OPDP2(21)
6084
6085 case ACRC32CW:
6086 return S32 | OPDP2(22)
6087
6088 case ACRC32CX:
6089 return S64 | OPDP2(23)
6090
6091 case ACSEL:
6092 return S64 | 0<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 0<<10
6093
6094 case ACSELW:
6095 return S32 | 0<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 0<<10
6096
6097 case ACSET:
6098 return S64 | 0<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 1<<10
6099
6100 case ACSETW:
6101 return S32 | 0<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 1<<10
6102
6103 case ACSETM:
6104 return S64 | 1<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 0<<10
6105
6106 case ACSETMW:
6107 return S32 | 1<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 0<<10
6108
6109 case ACINC, ACSINC:
6110 return S64 | 0<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 1<<10
6111
6112 case ACINCW, ACSINCW:
6113 return S32 | 0<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 1<<10
6114
6115 case ACINV, ACSINV:
6116 return S64 | 1<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 0<<10
6117
6118 case ACINVW, ACSINVW:
6119 return S32 | 1<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 0<<10
6120
6121 case ACNEG, ACSNEG:
6122 return S64 | 1<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 1<<10
6123
6124 case ACNEGW, ACSNEGW:
6125 return S32 | 1<<30 | 0<<29 | 0xD4<<21 | 0<<11 | 1<<10
6126
6127 case AMUL, AMADD:
6128 return S64 | 0<<29 | 0x1B<<24 | 0<<21 | 0<<15
6129
6130 case AMULW, AMADDW:
6131 return S32 | 0<<29 | 0x1B<<24 | 0<<21 | 0<<15
6132
6133 case AMNEG, AMSUB:
6134 return S64 | 0<<29 | 0x1B<<24 | 0<<21 | 1<<15
6135
6136 case AMNEGW, AMSUBW:
6137 return S32 | 0<<29 | 0x1B<<24 | 0<<21 | 1<<15
6138
6139 case AMRS:
6140 return SYSOP(1, 2, 0, 0, 0, 0, 0)
6141
6142 case AMSR:
6143 return SYSOP(0, 2, 0, 0, 0, 0, 0)
6144
6145 case ANEG:
6146 return S64 | 1<<30 | 0<<29 | 0xB<<24 | 0<<21
6147
6148 case ANEGW:
6149 return S32 | 1<<30 | 0<<29 | 0xB<<24 | 0<<21
6150
6151 case ANEGS:
6152 return S64 | 1<<30 | 1<<29 | 0xB<<24 | 0<<21
6153
6154 case ANEGSW:
6155 return S32 | 1<<30 | 1<<29 | 0xB<<24 | 0<<21
6156
6157 case AREM, ASDIV:
6158 return S64 | OPDP2(3)
6159
6160 case AREMW, ASDIVW:
6161 return S32 | OPDP2(3)
6162
6163 case ASMULL, ASMADDL:
6164 return OPDP3(1, 0, 1, 0)
6165
6166 case ASMNEGL, ASMSUBL:
6167 return OPDP3(1, 0, 1, 1)
6168
6169 case ASMULH:
6170 return OPDP3(1, 0, 2, 0)
6171
6172 case AUMULL, AUMADDL:
6173 return OPDP3(1, 0, 5, 0)
6174
6175 case AUMNEGL, AUMSUBL:
6176 return OPDP3(1, 0, 5, 1)
6177
6178 case AUMULH:
6179 return OPDP3(1, 0, 6, 0)
6180
6181 case AUREM, AUDIV:
6182 return S64 | OPDP2(2)
6183
6184 case AUREMW, AUDIVW:
6185 return S32 | OPDP2(2)
6186
6187 case AAESE:
6188 return 0x4E<<24 | 2<<20 | 8<<16 | 4<<12 | 2<<10
6189
6190 case AAESD:
6191 return 0x4E<<24 | 2<<20 | 8<<16 | 5<<12 | 2<<10
6192
6193 case AAESMC:
6194 return 0x4E<<24 | 2<<20 | 8<<16 | 6<<12 | 2<<10
6195
6196 case AAESIMC:
6197 return 0x4E<<24 | 2<<20 | 8<<16 | 7<<12 | 2<<10
6198
6199 case ASHA1C:
6200 return 0x5E<<24 | 0<<12
6201
6202 case ASHA1P:
6203 return 0x5E<<24 | 1<<12
6204
6205 case ASHA1M:
6206 return 0x5E<<24 | 2<<12
6207
6208 case ASHA1SU0:
6209 return 0x5E<<24 | 3<<12
6210
6211 case ASHA256H:
6212 return 0x5E<<24 | 4<<12
6213
6214 case ASHA256H2:
6215 return 0x5E<<24 | 5<<12
6216
6217 case ASHA256SU1:
6218 return 0x5E<<24 | 6<<12
6219
6220 case ASHA1H:
6221 return 0x5E<<24 | 2<<20 | 8<<16 | 0<<12 | 2<<10
6222
6223 case ASHA1SU1:
6224 return 0x5E<<24 | 2<<20 | 8<<16 | 1<<12 | 2<<10
6225
6226 case ASHA256SU0:
6227 return 0x5E<<24 | 2<<20 | 8<<16 | 2<<12 | 2<<10
6228
6229 case ASHA512H:
6230 return 0xCE<<24 | 3<<21 | 8<<12
6231
6232 case ASHA512H2:
6233 return 0xCE<<24 | 3<<21 | 8<<12 | 4<<8
6234
6235 case ASHA512SU1:
6236 return 0xCE<<24 | 3<<21 | 8<<12 | 8<<8
6237
6238 case ASHA512SU0:
6239 return 0xCE<<24 | 3<<22 | 8<<12
6240
6241 case AFCVTZSD:
6242 return FPCVTI(1, 0, 1, 3, 0)
6243
6244 case AFCVTZSDW:
6245 return FPCVTI(0, 0, 1, 3, 0)
6246
6247 case AFCVTZSS:
6248 return FPCVTI(1, 0, 0, 3, 0)
6249
6250 case AFCVTZSSW:
6251 return FPCVTI(0, 0, 0, 3, 0)
6252
6253 case AFCVTZUD:
6254 return FPCVTI(1, 0, 1, 3, 1)
6255
6256 case AFCVTZUDW:
6257 return FPCVTI(0, 0, 1, 3, 1)
6258
6259 case AFCVTZUS:
6260 return FPCVTI(1, 0, 0, 3, 1)
6261
6262 case AFCVTZUSW:
6263 return FPCVTI(0, 0, 0, 3, 1)
6264
6265 case ASCVTFD:
6266 return FPCVTI(1, 0, 1, 0, 2)
6267
6268 case ASCVTFS:
6269 return FPCVTI(1, 0, 0, 0, 2)
6270
6271 case ASCVTFWD:
6272 return FPCVTI(0, 0, 1, 0, 2)
6273
6274 case ASCVTFWS:
6275 return FPCVTI(0, 0, 0, 0, 2)
6276
6277 case AUCVTFD:
6278 return FPCVTI(1, 0, 1, 0, 3)
6279
6280 case AUCVTFS:
6281 return FPCVTI(1, 0, 0, 0, 3)
6282
6283 case AUCVTFWD:
6284 return FPCVTI(0, 0, 1, 0, 3)
6285
6286 case AUCVTFWS:
6287 return FPCVTI(0, 0, 0, 0, 3)
6288
6289 case AFADDS:
6290 return FPOP2S(0, 0, 0, 2)
6291
6292 case AFADDD:
6293 return FPOP2S(0, 0, 1, 2)
6294
6295 case AFSUBS:
6296 return FPOP2S(0, 0, 0, 3)
6297
6298 case AFSUBD:
6299 return FPOP2S(0, 0, 1, 3)
6300
6301 case AFMADDD:
6302 return FPOP3S(0, 0, 1, 0, 0)
6303
6304 case AFMADDS:
6305 return FPOP3S(0, 0, 0, 0, 0)
6306
6307 case AFMSUBD:
6308 return FPOP3S(0, 0, 1, 0, 1)
6309
6310 case AFMSUBS:
6311 return FPOP3S(0, 0, 0, 0, 1)
6312
6313 case AFNMADDD:
6314 return FPOP3S(0, 0, 1, 1, 0)
6315
6316 case AFNMADDS:
6317 return FPOP3S(0, 0, 0, 1, 0)
6318
6319 case AFNMSUBD:
6320 return FPOP3S(0, 0, 1, 1, 1)
6321
6322 case AFNMSUBS:
6323 return FPOP3S(0, 0, 0, 1, 1)
6324
6325 case AFMULS:
6326 return FPOP2S(0, 0, 0, 0)
6327
6328 case AFMULD:
6329 return FPOP2S(0, 0, 1, 0)
6330
6331 case AFDIVS:
6332 return FPOP2S(0, 0, 0, 1)
6333
6334 case AFDIVD:
6335 return FPOP2S(0, 0, 1, 1)
6336
6337 case AFMAXS:
6338 return FPOP2S(0, 0, 0, 4)
6339
6340 case AFMINS:
6341 return FPOP2S(0, 0, 0, 5)
6342
6343 case AFMAXD:
6344 return FPOP2S(0, 0, 1, 4)
6345
6346 case AFMIND:
6347 return FPOP2S(0, 0, 1, 5)
6348
6349 case AFMAXNMS:
6350 return FPOP2S(0, 0, 0, 6)
6351
6352 case AFMAXNMD:
6353 return FPOP2S(0, 0, 1, 6)
6354
6355 case AFMINNMS:
6356 return FPOP2S(0, 0, 0, 7)
6357
6358 case AFMINNMD:
6359 return FPOP2S(0, 0, 1, 7)
6360
6361 case AFNMULS:
6362 return FPOP2S(0, 0, 0, 8)
6363
6364 case AFNMULD:
6365 return FPOP2S(0, 0, 1, 8)
6366
6367 case AFCMPS:
6368 return FPCMP(0, 0, 0, 0, 0)
6369
6370 case AFCMPD:
6371 return FPCMP(0, 0, 1, 0, 0)
6372
6373 case AFCMPES:
6374 return FPCMP(0, 0, 0, 0, 16)
6375
6376 case AFCMPED:
6377 return FPCMP(0, 0, 1, 0, 16)
6378
6379 case AFCCMPS:
6380 return FPCCMP(0, 0, 0, 0)
6381
6382 case AFCCMPD:
6383 return FPCCMP(0, 0, 1, 0)
6384
6385 case AFCCMPES:
6386 return FPCCMP(0, 0, 0, 1)
6387
6388 case AFCCMPED:
6389 return FPCCMP(0, 0, 1, 1)
6390
6391 case AFCSELS:
6392 return 0x1E<<24 | 0<<22 | 1<<21 | 3<<10
6393
6394 case AFCSELD:
6395 return 0x1E<<24 | 1<<22 | 1<<21 | 3<<10
6396
6397 case AFMOVS:
6398 return FPOP1S(0, 0, 0, 0)
6399
6400 case AFABSS:
6401 return FPOP1S(0, 0, 0, 1)
6402
6403 case AFNEGS:
6404 return FPOP1S(0, 0, 0, 2)
6405
6406 case AFSQRTS:
6407 return FPOP1S(0, 0, 0, 3)
6408
6409 case AFCVTSD:
6410 return FPOP1S(0, 0, 0, 5)
6411
6412 case AFCVTSH:
6413 return FPOP1S(0, 0, 0, 7)
6414
6415 case AFRINTNS:
6416 return FPOP1S(0, 0, 0, 8)
6417
6418 case AFRINTPS:
6419 return FPOP1S(0, 0, 0, 9)
6420
6421 case AFRINTMS:
6422 return FPOP1S(0, 0, 0, 10)
6423
6424 case AFRINTZS:
6425 return FPOP1S(0, 0, 0, 11)
6426
6427 case AFRINTAS:
6428 return FPOP1S(0, 0, 0, 12)
6429
6430 case AFRINTXS:
6431 return FPOP1S(0, 0, 0, 14)
6432
6433 case AFRINTIS:
6434 return FPOP1S(0, 0, 0, 15)
6435
6436 case AFMOVD:
6437 return FPOP1S(0, 0, 1, 0)
6438
6439 case AFABSD:
6440 return FPOP1S(0, 0, 1, 1)
6441
6442 case AFNEGD:
6443 return FPOP1S(0, 0, 1, 2)
6444
6445 case AFSQRTD:
6446 return FPOP1S(0, 0, 1, 3)
6447
6448 case AFCVTDS:
6449 return FPOP1S(0, 0, 1, 4)
6450
6451 case AFCVTDH:
6452 return FPOP1S(0, 0, 1, 7)
6453
6454 case AFRINTND:
6455 return FPOP1S(0, 0, 1, 8)
6456
6457 case AFRINTPD:
6458 return FPOP1S(0, 0, 1, 9)
6459
6460 case AFRINTMD:
6461 return FPOP1S(0, 0, 1, 10)
6462
6463 case AFRINTZD:
6464 return FPOP1S(0, 0, 1, 11)
6465
6466 case AFRINTAD:
6467 return FPOP1S(0, 0, 1, 12)
6468
6469 case AFRINTXD:
6470 return FPOP1S(0, 0, 1, 14)
6471
6472 case AFRINTID:
6473 return FPOP1S(0, 0, 1, 15)
6474
6475 case AFCVTHS:
6476 return FPOP1S(0, 0, 3, 4)
6477
6478 case AFCVTHD:
6479 return FPOP1S(0, 0, 3, 5)
6480
6481 case AVADD:
6482 return 7<<25 | 1<<21 | 1<<15 | 1<<10
6483
6484 case AVSUB:
6485 return 0x17<<25 | 1<<21 | 1<<15 | 1<<10
6486
6487 case AVADDP:
6488 return 7<<25 | 1<<21 | 1<<15 | 15<<10
6489
6490 case AVAND:
6491 return 7<<25 | 1<<21 | 7<<10
6492
6493 case AVBCAX:
6494 return 0xCE<<24 | 1<<21
6495
6496 case AVCMEQ:
6497 return 1<<29 | 0x71<<21 | 0x23<<10
6498
6499 case AVCNT:
6500 return 0xE<<24 | 0x10<<17 | 5<<12 | 2<<10
6501
6502 case AVZIP1:
6503 return 0xE<<24 | 3<<12 | 2<<10
6504
6505 case AVZIP2:
6506 return 0xE<<24 | 1<<14 | 3<<12 | 2<<10
6507
6508 case AVEOR:
6509 return 1<<29 | 0x71<<21 | 7<<10
6510
6511 case AVEOR3:
6512 return 0xCE << 24
6513
6514 case AVORR:
6515 return 7<<25 | 5<<21 | 7<<10
6516
6517 case AVREV16:
6518 return 3<<26 | 2<<24 | 1<<21 | 3<<11
6519
6520 case AVRAX1:
6521 return 0xCE<<24 | 3<<21 | 1<<15 | 3<<10
6522
6523 case AVREV32:
6524 return 11<<26 | 2<<24 | 1<<21 | 1<<11
6525
6526 case AVREV64:
6527 return 3<<26 | 2<<24 | 1<<21 | 1<<11
6528
6529 case AVMOV:
6530 return 7<<25 | 5<<21 | 7<<10
6531
6532 case AVADDV:
6533 return 7<<25 | 3<<20 | 3<<15 | 7<<11
6534
6535 case AVUADDLV:
6536 return 1<<29 | 7<<25 | 3<<20 | 7<<11
6537
6538 case AVFMLA:
6539 return 7<<25 | 0<<23 | 1<<21 | 3<<14 | 3<<10
6540
6541 case AVFMLS:
6542 return 7<<25 | 1<<23 | 1<<21 | 3<<14 | 3<<10
6543
6544 case AVPMULL, AVPMULL2:
6545 return 0xE<<24 | 1<<21 | 0x38<<10
6546
6547 case AVRBIT:
6548 return 0x2E<<24 | 1<<22 | 0x10<<17 | 5<<12 | 2<<10
6549
6550 case AVLD1, AVLD2, AVLD3, AVLD4:
6551 return 3<<26 | 1<<22
6552
6553 case AVLD1R, AVLD3R:
6554 return 0xD<<24 | 1<<22
6555
6556 case AVLD2R, AVLD4R:
6557 return 0xD<<24 | 3<<21
6558
6559 case AVBIF:
6560 return 1<<29 | 7<<25 | 7<<21 | 7<<10
6561
6562 case AVBIT:
6563 return 1<<29 | 0x75<<21 | 7<<10
6564
6565 case AVBSL:
6566 return 1<<29 | 0x73<<21 | 7<<10
6567
6568 case AVCMTST:
6569 return 0xE<<24 | 1<<21 | 0x23<<10
6570
6571 case AVUMAX:
6572 return 1<<29 | 7<<25 | 1<<21 | 0x19<<10
6573
6574 case AVUMIN:
6575 return 1<<29 | 7<<25 | 1<<21 | 0x1b<<10
6576
6577 case AVUZP1:
6578 return 7<<25 | 3<<11
6579
6580 case AVUZP2:
6581 return 7<<25 | 1<<14 | 3<<11
6582
6583 case AVUADDW, AVUADDW2:
6584 return 0x17<<25 | 1<<21 | 1<<12
6585
6586 case AVTRN1:
6587 return 7<<25 | 5<<11
6588
6589 case AVTRN2:
6590 return 7<<25 | 1<<14 | 5<<11
6591 }
6592
6593 c.ctxt.Diag("%v: bad rrr %d %v", p, a, a)
6594 return 0
6595 }
6596
6597
6601 func (c *ctxt7) opirr(p *obj.Prog, a obj.As) uint32 {
6602 switch a {
6603
6604 case AMOVD, AADD:
6605 return S64 | 0<<30 | 0<<29 | 0x11<<24
6606
6607 case ACMN, AADDS:
6608 return S64 | 0<<30 | 1<<29 | 0x11<<24
6609
6610 case AMOVW, AADDW:
6611 return S32 | 0<<30 | 0<<29 | 0x11<<24
6612
6613 case ACMNW, AADDSW:
6614 return S32 | 0<<30 | 1<<29 | 0x11<<24
6615
6616 case ASUB:
6617 return S64 | 1<<30 | 0<<29 | 0x11<<24
6618
6619 case ACMP, ASUBS:
6620 return S64 | 1<<30 | 1<<29 | 0x11<<24
6621
6622 case ASUBW:
6623 return S32 | 1<<30 | 0<<29 | 0x11<<24
6624
6625 case ACMPW, ASUBSW:
6626 return S32 | 1<<30 | 1<<29 | 0x11<<24
6627
6628
6629 case AADR:
6630 return 0<<31 | 0x10<<24
6631
6632 case AADRP:
6633 return 1<<31 | 0x10<<24
6634
6635
6636 case AAND, ABIC:
6637 return S64 | 0<<29 | 0x24<<23
6638
6639 case AANDW, ABICW:
6640 return S32 | 0<<29 | 0x24<<23 | 0<<22
6641
6642 case AORR, AORN:
6643 return S64 | 1<<29 | 0x24<<23
6644
6645 case AORRW, AORNW:
6646 return S32 | 1<<29 | 0x24<<23 | 0<<22
6647
6648 case AEOR, AEON:
6649 return S64 | 2<<29 | 0x24<<23
6650
6651 case AEORW, AEONW:
6652 return S32 | 2<<29 | 0x24<<23 | 0<<22
6653
6654 case AANDS, ABICS, ATST:
6655 return S64 | 3<<29 | 0x24<<23
6656
6657 case AANDSW, ABICSW, ATSTW:
6658 return S32 | 3<<29 | 0x24<<23 | 0<<22
6659
6660 case AASR:
6661 return S64 | 0<<29 | 0x26<<23
6662
6663 case AASRW:
6664 return S32 | 0<<29 | 0x26<<23 | 0<<22
6665
6666
6667 case ABFI:
6668 return S64 | 2<<29 | 0x26<<23 | 1<<22
6669
6670
6671 case ABFIW:
6672 return S32 | 2<<29 | 0x26<<23 | 0<<22
6673
6674
6675 case ABFM:
6676 return S64 | 1<<29 | 0x26<<23 | 1<<22
6677
6678 case ABFMW:
6679 return S32 | 1<<29 | 0x26<<23 | 0<<22
6680
6681 case ASBFM:
6682 return S64 | 0<<29 | 0x26<<23 | 1<<22
6683
6684 case ASBFMW:
6685 return S32 | 0<<29 | 0x26<<23 | 0<<22
6686
6687 case AUBFM:
6688 return S64 | 2<<29 | 0x26<<23 | 1<<22
6689
6690 case AUBFMW:
6691 return S32 | 2<<29 | 0x26<<23 | 0<<22
6692
6693 case ABFXIL:
6694 return S64 | 1<<29 | 0x26<<23 | 1<<22
6695
6696 case ABFXILW:
6697 return S32 | 1<<29 | 0x26<<23 | 0<<22
6698
6699 case AEXTR:
6700 return S64 | 0<<29 | 0x27<<23 | 1<<22 | 0<<21
6701
6702 case AEXTRW:
6703 return S32 | 0<<29 | 0x27<<23 | 0<<22 | 0<<21
6704
6705 case ACBNZ:
6706 return S64 | 0x1A<<25 | 1<<24
6707
6708 case ACBNZW:
6709 return S32 | 0x1A<<25 | 1<<24
6710
6711 case ACBZ:
6712 return S64 | 0x1A<<25 | 0<<24
6713
6714 case ACBZW:
6715 return S32 | 0x1A<<25 | 0<<24
6716
6717 case ACCMN:
6718 return S64 | 0<<30 | 1<<29 | 0xD2<<21 | 1<<11 | 0<<10 | 0<<4
6719
6720 case ACCMNW:
6721 return S32 | 0<<30 | 1<<29 | 0xD2<<21 | 1<<11 | 0<<10 | 0<<4
6722
6723 case ACCMP:
6724 return S64 | 1<<30 | 1<<29 | 0xD2<<21 | 1<<11 | 0<<10 | 0<<4
6725
6726 case ACCMPW:
6727 return S32 | 1<<30 | 1<<29 | 0xD2<<21 | 1<<11 | 0<<10 | 0<<4
6728
6729 case AMOVK:
6730 return S64 | 3<<29 | 0x25<<23
6731
6732 case AMOVKW:
6733 return S32 | 3<<29 | 0x25<<23
6734
6735 case AMOVN:
6736 return S64 | 0<<29 | 0x25<<23
6737
6738 case AMOVNW:
6739 return S32 | 0<<29 | 0x25<<23
6740
6741 case AMOVZ:
6742 return S64 | 2<<29 | 0x25<<23
6743
6744 case AMOVZW:
6745 return S32 | 2<<29 | 0x25<<23
6746
6747 case AMSR:
6748 return SYSOP(0, 0, 0, 4, 0, 0, 0x1F)
6749
6750 case AAT,
6751 ADC,
6752 AIC,
6753 ATLBI,
6754 ASYS:
6755 return SYSOP(0, 1, 0, 0, 0, 0, 0)
6756
6757 case ASYSL:
6758 return SYSOP(1, 1, 0, 0, 0, 0, 0)
6759
6760 case ATBZ:
6761 return 0x36 << 24
6762
6763 case ATBNZ:
6764 return 0x37 << 24
6765
6766 case ADSB:
6767 return SYSOP(0, 0, 3, 3, 0, 4, 0x1F)
6768
6769 case ADMB:
6770 return SYSOP(0, 0, 3, 3, 0, 5, 0x1F)
6771
6772 case AISB:
6773 return SYSOP(0, 0, 3, 3, 0, 6, 0x1F)
6774
6775 case AHINT:
6776 return SYSOP(0, 0, 3, 2, 0, 0, 0x1F)
6777
6778 case AVEXT:
6779 return 0x2E<<24 | 0<<23 | 0<<21 | 0<<15
6780
6781 case AVUSHR:
6782 return 0x5E<<23 | 1<<10
6783
6784 case AVSHL:
6785 return 0x1E<<23 | 21<<10
6786
6787 case AVSRI:
6788 return 0x5E<<23 | 17<<10
6789
6790 case AVSLI:
6791 return 0x5E<<23 | 21<<10
6792
6793 case AVUSHLL, AVUXTL:
6794 return 1<<29 | 15<<24 | 0x29<<10
6795
6796 case AVUSHLL2, AVUXTL2:
6797 return 3<<29 | 15<<24 | 0x29<<10
6798
6799 case AVXAR:
6800 return 0xCE<<24 | 1<<23
6801
6802 case AVUSRA:
6803 return 1<<29 | 15<<24 | 5<<10
6804
6805 case APRFM:
6806 return 0xf9<<24 | 2<<22
6807 }
6808
6809 c.ctxt.Diag("%v: bad irr %v", p, a)
6810 return 0
6811 }
6812
6813 func (c *ctxt7) opbit(p *obj.Prog, a obj.As) uint32 {
6814 switch a {
6815 case ACLS:
6816 return S64 | OPBIT(5)
6817
6818 case ACLSW:
6819 return S32 | OPBIT(5)
6820
6821 case ACLZ:
6822 return S64 | OPBIT(4)
6823
6824 case ACLZW:
6825 return S32 | OPBIT(4)
6826
6827 case ARBIT:
6828 return S64 | OPBIT(0)
6829
6830 case ARBITW:
6831 return S32 | OPBIT(0)
6832
6833 case AREV:
6834 return S64 | OPBIT(3)
6835
6836 case AREVW:
6837 return S32 | OPBIT(2)
6838
6839 case AREV16:
6840 return S64 | OPBIT(1)
6841
6842 case AREV16W:
6843 return S32 | OPBIT(1)
6844
6845 case AREV32:
6846 return S64 | OPBIT(2)
6847
6848 default:
6849 c.ctxt.Diag("bad bit op\n%v", p)
6850 return 0
6851 }
6852 }
6853
6854
6857 func (c *ctxt7) opxrrr(p *obj.Prog, a obj.As, rd, rn, rm int16, extend bool) uint32 {
6858 extension := uint32(0)
6859 if !extend {
6860 if isADDop(a) {
6861 extension = LSL0_64
6862 }
6863 if isADDWop(a) {
6864 extension = LSL0_32
6865 }
6866 }
6867
6868 var op uint32
6869
6870 switch a {
6871 case AADD:
6872 op = S64 | 0<<30 | 0<<29 | 0x0b<<24 | 0<<22 | 1<<21 | extension
6873
6874 case AADDW:
6875 op = S32 | 0<<30 | 0<<29 | 0x0b<<24 | 0<<22 | 1<<21 | extension
6876
6877 case ACMN, AADDS:
6878 op = S64 | 0<<30 | 1<<29 | 0x0b<<24 | 0<<22 | 1<<21 | extension
6879
6880 case ACMNW, AADDSW:
6881 op = S32 | 0<<30 | 1<<29 | 0x0b<<24 | 0<<22 | 1<<21 | extension
6882
6883 case ASUB:
6884 op = S64 | 1<<30 | 0<<29 | 0x0b<<24 | 0<<22 | 1<<21 | extension
6885
6886 case ASUBW:
6887 op = S32 | 1<<30 | 0<<29 | 0x0b<<24 | 0<<22 | 1<<21 | extension
6888
6889 case ACMP, ASUBS:
6890 op = S64 | 1<<30 | 1<<29 | 0x0b<<24 | 0<<22 | 1<<21 | extension
6891
6892 case ACMPW, ASUBSW:
6893 op = S32 | 1<<30 | 1<<29 | 0x0b<<24 | 0<<22 | 1<<21 | extension
6894
6895 default:
6896 c.ctxt.Diag("bad opxrrr %v\n%v", a, p)
6897 return 0
6898 }
6899
6900 op |= uint32(rm&0x1f)<<16 | uint32(rn&0x1f)<<5 | uint32(rd&0x1f)
6901
6902 return op
6903 }
6904
6905 func (c *ctxt7) opimm(p *obj.Prog, a obj.As) uint32 {
6906 switch a {
6907 case ASVC:
6908 return 0xD4<<24 | 0<<21 | 1
6909
6910 case AHVC:
6911 return 0xD4<<24 | 0<<21 | 2
6912
6913 case ASMC:
6914 return 0xD4<<24 | 0<<21 | 3
6915
6916 case ABRK:
6917 return 0xD4<<24 | 1<<21 | 0
6918
6919 case AHLT:
6920 return 0xD4<<24 | 2<<21 | 0
6921
6922 case ADCPS1:
6923 return 0xD4<<24 | 5<<21 | 1
6924
6925 case ADCPS2:
6926 return 0xD4<<24 | 5<<21 | 2
6927
6928 case ADCPS3:
6929 return 0xD4<<24 | 5<<21 | 3
6930
6931 case ACLREX:
6932 return SYSOP(0, 0, 3, 3, 0, 2, 0x1F)
6933 }
6934
6935 c.ctxt.Diag("%v: bad imm %v", p, a)
6936 return 0
6937 }
6938
6939 func (c *ctxt7) brdist(p *obj.Prog, preshift int, flen int, shift int) int64 {
6940 v := int64(0)
6941 t := int64(0)
6942 var q *obj.Prog
6943 if p.To.Type == obj.TYPE_BRANCH {
6944 q = p.To.Target()
6945 } else if p.From.Type == obj.TYPE_BRANCH {
6946 q = p.From.Target()
6947 }
6948 if q == nil {
6949
6950
6951 q = p.Pool
6952 }
6953 if q != nil {
6954 v = (q.Pc >> uint(preshift)) - (c.pc >> uint(preshift))
6955 if (v & ((1 << uint(shift)) - 1)) != 0 {
6956 c.ctxt.Diag("misaligned label\n%v", p)
6957 }
6958 v >>= uint(shift)
6959 t = int64(1) << uint(flen-1)
6960 if v < -t || v >= t {
6961 c.ctxt.Diag("branch too far %#x vs %#x [%p]\n%v\n%v", v, t, c.blitrl, p, q)
6962 panic("branch too far")
6963 }
6964 }
6965
6966 return v & ((t << 1) - 1)
6967 }
6968
6969
6972 func (c *ctxt7) opbra(p *obj.Prog, a obj.As) uint32 {
6973 switch a {
6974 case ABEQ:
6975 return OPBcc(0x0)
6976
6977 case ABNE:
6978 return OPBcc(0x1)
6979
6980 case ABCS:
6981 return OPBcc(0x2)
6982
6983 case ABHS:
6984 return OPBcc(0x2)
6985
6986 case ABCC:
6987 return OPBcc(0x3)
6988
6989 case ABLO:
6990 return OPBcc(0x3)
6991
6992 case ABMI:
6993 return OPBcc(0x4)
6994
6995 case ABPL:
6996 return OPBcc(0x5)
6997
6998 case ABVS:
6999 return OPBcc(0x6)
7000
7001 case ABVC:
7002 return OPBcc(0x7)
7003
7004 case ABHI:
7005 return OPBcc(0x8)
7006
7007 case ABLS:
7008 return OPBcc(0x9)
7009
7010 case ABGE:
7011 return OPBcc(0xa)
7012
7013 case ABLT:
7014 return OPBcc(0xb)
7015
7016 case ABGT:
7017 return OPBcc(0xc)
7018
7019 case ABLE:
7020 return OPBcc(0xd)
7021
7022 case AB:
7023 return 0<<31 | 5<<26
7024
7025 case obj.ADUFFZERO, obj.ADUFFCOPY, ABL:
7026 return 1<<31 | 5<<26
7027 }
7028
7029 c.ctxt.Diag("%v: bad bra %v", p, a)
7030 return 0
7031 }
7032
7033 func (c *ctxt7) opbrr(p *obj.Prog, a obj.As) uint32 {
7034 switch a {
7035 case ABL:
7036 return OPBLR(1)
7037
7038 case AB:
7039 return OPBLR(0)
7040
7041 case obj.ARET:
7042 return OPBLR(2)
7043 }
7044
7045 c.ctxt.Diag("%v: bad brr %v", p, a)
7046 return 0
7047 }
7048
7049 func (c *ctxt7) op0(p *obj.Prog, a obj.As) uint32 {
7050 switch a {
7051 case ADRPS:
7052 return 0x6B<<25 | 5<<21 | 0x1F<<16 | 0x1F<<5
7053
7054 case AERET:
7055 return 0x6B<<25 | 4<<21 | 0x1F<<16 | 0<<10 | 0x1F<<5
7056
7057 case ANOOP:
7058 return SYSHINT(0)
7059
7060 case AYIELD:
7061 return SYSHINT(1)
7062
7063 case AWFE:
7064 return SYSHINT(2)
7065
7066 case AWFI:
7067 return SYSHINT(3)
7068
7069 case ASEV:
7070 return SYSHINT(4)
7071
7072 case ASEVL:
7073 return SYSHINT(5)
7074 }
7075
7076 c.ctxt.Diag("%v: bad op0 %v", p, a)
7077 return 0
7078 }
7079
7080
7083 func (c *ctxt7) opload(p *obj.Prog, a obj.As) uint32 {
7084 switch a {
7085 case ALDAR:
7086 return LDSTX(3, 1, 1, 0, 1) | 0x1F<<10
7087
7088 case ALDARW:
7089 return LDSTX(2, 1, 1, 0, 1) | 0x1F<<10
7090
7091 case ALDARB:
7092 return LDSTX(0, 1, 1, 0, 1) | 0x1F<<10
7093
7094 case ALDARH:
7095 return LDSTX(1, 1, 1, 0, 1) | 0x1F<<10
7096
7097 case ALDAXP:
7098 return LDSTX(3, 0, 1, 1, 1)
7099
7100 case ALDAXPW:
7101 return LDSTX(2, 0, 1, 1, 1)
7102
7103 case ALDAXR:
7104 return LDSTX(3, 0, 1, 0, 1) | 0x1F<<10
7105
7106 case ALDAXRW:
7107 return LDSTX(2, 0, 1, 0, 1) | 0x1F<<10
7108
7109 case ALDAXRB:
7110 return LDSTX(0, 0, 1, 0, 1) | 0x1F<<10
7111
7112 case ALDAXRH:
7113 return LDSTX(1, 0, 1, 0, 1) | 0x1F<<10
7114
7115 case ALDXR:
7116 return LDSTX(3, 0, 1, 0, 0) | 0x1F<<10
7117
7118 case ALDXRB:
7119 return LDSTX(0, 0, 1, 0, 0) | 0x1F<<10
7120
7121 case ALDXRH:
7122 return LDSTX(1, 0, 1, 0, 0) | 0x1F<<10
7123
7124 case ALDXRW:
7125 return LDSTX(2, 0, 1, 0, 0) | 0x1F<<10
7126
7127 case ALDXP:
7128 return LDSTX(3, 0, 1, 1, 0)
7129
7130 case ALDXPW:
7131 return LDSTX(2, 0, 1, 1, 0)
7132 }
7133
7134 c.ctxt.Diag("bad opload %v\n%v", a, p)
7135 return 0
7136 }
7137
7138 func (c *ctxt7) opstore(p *obj.Prog, a obj.As) uint32 {
7139 switch a {
7140 case ASTLR:
7141 return LDSTX(3, 1, 0, 0, 1) | 0x1F<<10
7142
7143 case ASTLRB:
7144 return LDSTX(0, 1, 0, 0, 1) | 0x1F<<10
7145
7146 case ASTLRH:
7147 return LDSTX(1, 1, 0, 0, 1) | 0x1F<<10
7148
7149 case ASTLRW:
7150 return LDSTX(2, 1, 0, 0, 1) | 0x1F<<10
7151
7152 case ASTLXP:
7153 return LDSTX(3, 0, 0, 1, 1)
7154
7155 case ASTLXPW:
7156 return LDSTX(2, 0, 0, 1, 1)
7157
7158 case ASTLXR:
7159 return LDSTX(3, 0, 0, 0, 1) | 0x1F<<10
7160
7161 case ASTLXRB:
7162 return LDSTX(0, 0, 0, 0, 1) | 0x1F<<10
7163
7164 case ASTLXRH:
7165 return LDSTX(1, 0, 0, 0, 1) | 0x1F<<10
7166
7167 case ASTLXRW:
7168 return LDSTX(2, 0, 0, 0, 1) | 0x1F<<10
7169
7170 case ASTXR:
7171 return LDSTX(3, 0, 0, 0, 0) | 0x1F<<10
7172
7173 case ASTXRB:
7174 return LDSTX(0, 0, 0, 0, 0) | 0x1F<<10
7175
7176 case ASTXRH:
7177 return LDSTX(1, 0, 0, 0, 0) | 0x1F<<10
7178
7179 case ASTXP:
7180 return LDSTX(3, 0, 0, 1, 0)
7181
7182 case ASTXPW:
7183 return LDSTX(2, 0, 0, 1, 0)
7184
7185 case ASTXRW:
7186 return LDSTX(2, 0, 0, 0, 0) | 0x1F<<10
7187 }
7188
7189 c.ctxt.Diag("bad opstore %v\n%v", a, p)
7190 return 0
7191 }
7192
7193
7197 func (c *ctxt7) olsr12u(p *obj.Prog, o uint32, v int32, rn, rt int16) uint32 {
7198 if v < 0 || v >= (1<<12) {
7199 c.ctxt.Diag("offset out of range: %d\n%v", v, p)
7200 }
7201 o |= uint32(v&0xFFF) << 10
7202 o |= uint32(rn&31) << 5
7203 o |= uint32(rt & 31)
7204 o |= 1 << 24
7205 return o
7206 }
7207
7208
7211 func (c *ctxt7) olsr9s(p *obj.Prog, o uint32, v int32, rn, rt int16) uint32 {
7212 if v < -256 || v > 255 {
7213 c.ctxt.Diag("offset out of range: %d\n%v", v, p)
7214 }
7215 o |= uint32((v & 0x1FF) << 12)
7216 o |= uint32(rn&31) << 5
7217 o |= uint32(rt & 31)
7218 return o
7219 }
7220
7221
7222
7223
7224
7225
7226 func (c *ctxt7) opstr(p *obj.Prog, a obj.As) uint32 {
7227 enc := c.opldr(p, a)
7228 switch p.As {
7229 case AFMOVQ:
7230 enc = enc &^ (1 << 22)
7231 default:
7232 enc = LD2STR(enc)
7233 }
7234 return enc
7235 }
7236
7237
7238
7239
7240
7241
7242 func (c *ctxt7) opldr(p *obj.Prog, a obj.As) uint32 {
7243 switch a {
7244 case AMOVD:
7245 return LDSTR(3, 0, 1)
7246
7247 case AMOVW:
7248 return LDSTR(2, 0, 2)
7249
7250 case AMOVWU:
7251 return LDSTR(2, 0, 1)
7252
7253 case AMOVH:
7254 return LDSTR(1, 0, 2)
7255
7256 case AMOVHU:
7257 return LDSTR(1, 0, 1)
7258
7259 case AMOVB:
7260 return LDSTR(0, 0, 2)
7261
7262 case AMOVBU:
7263 return LDSTR(0, 0, 1)
7264
7265 case AFMOVS, AVMOVS:
7266 return LDSTR(2, 1, 1)
7267
7268 case AFMOVD, AVMOVD:
7269 return LDSTR(3, 1, 1)
7270
7271 case AFMOVQ, AVMOVQ:
7272 return LDSTR(0, 1, 3)
7273 }
7274
7275 c.ctxt.Diag("bad opldr %v\n%v", a, p)
7276 return 0
7277 }
7278
7279
7280
7281 func (c *ctxt7) olsxrr(p *obj.Prog, o int32, r int, r1 int, r2 int) uint32 {
7282 o |= int32(r1&31) << 5
7283 o |= int32(r2&31) << 16
7284 o |= int32(r & 31)
7285 return uint32(o)
7286 }
7287
7288
7289
7290
7291 func (c *ctxt7) opldrr(p *obj.Prog, a obj.As, extension bool) uint32 {
7292 OptionS := uint32(0x1a)
7293 if extension {
7294 OptionS = uint32(0)
7295 }
7296 switch a {
7297 case AMOVD:
7298 return OptionS<<10 | 0x3<<21 | 0x1f<<27
7299 case AMOVW:
7300 return OptionS<<10 | 0x5<<21 | 0x17<<27
7301 case AMOVWU:
7302 return OptionS<<10 | 0x3<<21 | 0x17<<27
7303 case AMOVH:
7304 return OptionS<<10 | 0x5<<21 | 0x0f<<27
7305 case AMOVHU:
7306 return OptionS<<10 | 0x3<<21 | 0x0f<<27
7307 case AMOVB:
7308 return OptionS<<10 | 0x5<<21 | 0x07<<27
7309 case AMOVBU:
7310 return OptionS<<10 | 0x3<<21 | 0x07<<27
7311 case AFMOVS:
7312 return OptionS<<10 | 0x3<<21 | 0x17<<27 | 1<<26
7313 case AFMOVD:
7314 return OptionS<<10 | 0x3<<21 | 0x1f<<27 | 1<<26
7315 }
7316 c.ctxt.Diag("bad opldrr %v\n%v", a, p)
7317 return 0
7318 }
7319
7320
7321
7322
7323 func (c *ctxt7) opstrr(p *obj.Prog, a obj.As, extension bool) uint32 {
7324 OptionS := uint32(0x1a)
7325 if extension {
7326 OptionS = uint32(0)
7327 }
7328 switch a {
7329 case AMOVD:
7330 return OptionS<<10 | 0x1<<21 | 0x1f<<27
7331 case AMOVW, AMOVWU:
7332 return OptionS<<10 | 0x1<<21 | 0x17<<27
7333 case AMOVH, AMOVHU:
7334 return OptionS<<10 | 0x1<<21 | 0x0f<<27
7335 case AMOVB, AMOVBU:
7336 return OptionS<<10 | 0x1<<21 | 0x07<<27
7337 case AFMOVS:
7338 return OptionS<<10 | 0x1<<21 | 0x17<<27 | 1<<26
7339 case AFMOVD:
7340 return OptionS<<10 | 0x1<<21 | 0x1f<<27 | 1<<26
7341 }
7342 c.ctxt.Diag("bad opstrr %v\n%v", a, p)
7343 return 0
7344 }
7345
7346 func (c *ctxt7) oaddi(p *obj.Prog, a obj.As, v int32, rd, rn int16) uint32 {
7347 op := c.opirr(p, a)
7348
7349 if (v & 0xFFF000) != 0 {
7350 if v&0xFFF != 0 {
7351 c.ctxt.Diag("%v misuses oaddi", p)
7352 }
7353 v >>= 12
7354 op |= 1 << 22
7355 }
7356
7357 op |= (uint32(v&0xFFF) << 10) | (uint32(rn&31) << 5) | uint32(rd&31)
7358
7359 return op
7360 }
7361
7362 func (c *ctxt7) oaddi12(p *obj.Prog, v int32, rd, rn int16) uint32 {
7363 if v < -4095 || v > 4095 {
7364 c.ctxt.Diag("%v is not a 12 bit immediate: %v", v, p)
7365 return 0
7366 }
7367 a := AADD
7368 if v < 0 {
7369 a = ASUB
7370 v = -v
7371 }
7372 return c.oaddi(p, a, v, rd, rn)
7373 }
7374
7375
7378 func (c *ctxt7) omovlit(as obj.As, p *obj.Prog, a *obj.Addr, dr int) uint32 {
7379 var o1 int32
7380 if p.Pool == nil {
7381 c.aclass(a)
7382 c.ctxt.Logf("omovlit add %d (%#x)\n", c.instoffset, uint64(c.instoffset))
7383
7384
7385 o1 = int32(c.opirr(p, AADD))
7386
7387 v := int32(c.instoffset)
7388 if v != 0 && (v&0xFFF) == 0 {
7389 v >>= 12
7390 o1 |= 1 << 22
7391 }
7392
7393 o1 |= ((v & 0xFFF) << 10) | (REGZERO & 31 << 5) | int32(dr&31)
7394 } else {
7395 fp, w := 0, 0
7396 switch as {
7397 case AFMOVS, AVMOVS:
7398 fp = 1
7399 w = 0
7400
7401 case AFMOVD, AVMOVD:
7402 fp = 1
7403 w = 1
7404
7405 case AVMOVQ:
7406 fp = 1
7407 w = 2
7408
7409 case AMOVD:
7410 if p.Pool.As == ADWORD {
7411 w = 1
7412 } else if p.Pool.To.Offset < 0 {
7413 w = 2
7414 } else if p.Pool.To.Offset >= 0 {
7415 w = 0
7416 } else {
7417 c.ctxt.Diag("invalid operand %v in %v", a, p)
7418 }
7419
7420 case AMOVBU, AMOVHU, AMOVWU:
7421 w = 0
7422
7423 case AMOVB, AMOVH, AMOVW:
7424 w = 2
7425
7426 default:
7427 c.ctxt.Diag("invalid operation %v in %v", as, p)
7428 }
7429
7430 v := int32(c.brdist(p, 0, 19, 2))
7431 o1 = (int32(w) << 30) | (int32(fp) << 26) | (3 << 27)
7432 o1 |= (v & 0x7FFFF) << 5
7433 o1 |= int32(dr & 31)
7434 }
7435
7436 return uint32(o1)
7437 }
7438
7439
7440 func (c *ctxt7) omovconst(as obj.As, p *obj.Prog, a *obj.Addr, rt int) (o1 uint32) {
7441 if cls := int(a.Class); (cls == C_BITCON || cls == C_ABCON || cls == C_ABCON0) && rt != REGZERO {
7442
7443 mode := 64
7444 var as1 obj.As
7445 switch as {
7446 case AMOVW:
7447 as1 = AORRW
7448 mode = 32
7449 case AMOVD:
7450 as1 = AORR
7451 }
7452 o1 = c.opirr(p, as1)
7453 o1 |= bitconEncode(uint64(a.Offset), mode) | uint32(REGZERO&31)<<5 | uint32(rt&31)
7454 return o1
7455 }
7456
7457 if as == AMOVW {
7458 d := uint32(a.Offset)
7459 s := movcon(int64(d))
7460 if s < 0 || 16*s >= 32 {
7461 d = ^d
7462 s = movcon(int64(d))
7463 if s < 0 || 16*s >= 32 {
7464 c.ctxt.Diag("impossible 32-bit move wide: %#x\n%v", uint32(a.Offset), p)
7465 }
7466 o1 = c.opirr(p, AMOVNW)
7467 } else {
7468 o1 = c.opirr(p, AMOVZW)
7469 }
7470 o1 |= MOVCONST(int64(d), s, rt)
7471 }
7472 if as == AMOVD {
7473 d := a.Offset
7474 s := movcon(d)
7475 if s < 0 || 16*s >= 64 {
7476 d = ^d
7477 s = movcon(d)
7478 if s < 0 || 16*s >= 64 {
7479 c.ctxt.Diag("impossible 64-bit move wide: %#x\n%v", uint64(a.Offset), p)
7480 }
7481 o1 = c.opirr(p, AMOVN)
7482 } else {
7483 o1 = c.opirr(p, AMOVZ)
7484 }
7485 o1 |= MOVCONST(d, s, rt)
7486 }
7487 return o1
7488 }
7489
7490
7491
7492 func (c *ctxt7) omovlconst(as obj.As, p *obj.Prog, a *obj.Addr, rt int, os []uint32) (num uint8) {
7493 switch as {
7494 case AMOVW:
7495 d := uint32(a.Offset)
7496
7497 os[0] = c.opirr(p, AMOVZW)
7498 os[0] |= MOVCONST(int64(d), 0, rt)
7499 os[1] = c.opirr(p, AMOVKW)
7500 os[1] |= MOVCONST(int64(d), 1, rt)
7501 return 2
7502
7503 case AMOVD:
7504 d := a.Offset
7505 dn := ^d
7506 var immh [4]uint64
7507 var i int
7508 zeroCount := int(0)
7509 negCount := int(0)
7510 for i = 0; i < 4; i++ {
7511 immh[i] = uint64((d >> uint(i*16)) & 0xffff)
7512 if immh[i] == 0 {
7513 zeroCount++
7514 } else if immh[i] == 0xffff {
7515 negCount++
7516 }
7517 }
7518
7519 if zeroCount == 4 || negCount == 4 {
7520 c.ctxt.Diag("the immediate should be MOVCON: %v", p)
7521 }
7522 switch {
7523 case zeroCount == 3:
7524
7525 for i = 0; i < 4; i++ {
7526 if immh[i] != 0 {
7527 os[0] = c.opirr(p, AMOVZ)
7528 os[0] |= MOVCONST(d, i, rt)
7529 break
7530 }
7531 }
7532 return 1
7533
7534 case negCount == 3:
7535
7536 for i = 0; i < 4; i++ {
7537 if immh[i] != 0xffff {
7538 os[0] = c.opirr(p, AMOVN)
7539 os[0] |= MOVCONST(dn, i, rt)
7540 break
7541 }
7542 }
7543 return 1
7544
7545 case zeroCount == 2:
7546
7547 for i = 0; i < 4; i++ {
7548 if immh[i] != 0 {
7549 os[0] = c.opirr(p, AMOVZ)
7550 os[0] |= MOVCONST(d, i, rt)
7551 i++
7552 break
7553 }
7554 }
7555 for ; i < 4; i++ {
7556 if immh[i] != 0 {
7557 os[1] = c.opirr(p, AMOVK)
7558 os[1] |= MOVCONST(d, i, rt)
7559 }
7560 }
7561 return 2
7562
7563 case negCount == 2:
7564
7565 for i = 0; i < 4; i++ {
7566 if immh[i] != 0xffff {
7567 os[0] = c.opirr(p, AMOVN)
7568 os[0] |= MOVCONST(dn, i, rt)
7569 i++
7570 break
7571 }
7572 }
7573 for ; i < 4; i++ {
7574 if immh[i] != 0xffff {
7575 os[1] = c.opirr(p, AMOVK)
7576 os[1] |= MOVCONST(d, i, rt)
7577 }
7578 }
7579 return 2
7580
7581 case zeroCount == 1:
7582
7583 for i = 0; i < 4; i++ {
7584 if immh[i] != 0 {
7585 os[0] = c.opirr(p, AMOVZ)
7586 os[0] |= MOVCONST(d, i, rt)
7587 i++
7588 break
7589 }
7590 }
7591
7592 for j := 1; i < 4; i++ {
7593 if immh[i] != 0 {
7594 os[j] = c.opirr(p, AMOVK)
7595 os[j] |= MOVCONST(d, i, rt)
7596 j++
7597 }
7598 }
7599 return 3
7600
7601 case negCount == 1:
7602
7603 for i = 0; i < 4; i++ {
7604 if immh[i] != 0xffff {
7605 os[0] = c.opirr(p, AMOVN)
7606 os[0] |= MOVCONST(dn, i, rt)
7607 i++
7608 break
7609 }
7610 }
7611
7612 for j := 1; i < 4; i++ {
7613 if immh[i] != 0xffff {
7614 os[j] = c.opirr(p, AMOVK)
7615 os[j] |= MOVCONST(d, i, rt)
7616 j++
7617 }
7618 }
7619 return 3
7620
7621 default:
7622
7623 os[0] = c.opirr(p, AMOVZ)
7624 os[0] |= MOVCONST(d, 0, rt)
7625 for i = 1; i < 4; i++ {
7626 os[i] = c.opirr(p, AMOVK)
7627 os[i] |= MOVCONST(d, i, rt)
7628 }
7629 return 4
7630 }
7631 default:
7632 return 0
7633 }
7634 }
7635
7636 func (c *ctxt7) opbfm(p *obj.Prog, a obj.As, r, s int64, rf, rt int16) uint32 {
7637 var b uint32
7638 o := c.opirr(p, a)
7639 if (o & (1 << 31)) == 0 {
7640 b = 32
7641 } else {
7642 b = 64
7643 }
7644 if r < 0 || uint32(r) >= b {
7645 c.ctxt.Diag("illegal bit number\n%v", p)
7646 }
7647 o |= (uint32(r) & 0x3F) << 16
7648 if s < 0 || uint32(s) >= b {
7649 c.ctxt.Diag("illegal bit number\n%v", p)
7650 }
7651 o |= (uint32(s) & 0x3F) << 10
7652 o |= (uint32(rf&31) << 5) | uint32(rt&31)
7653 return o
7654 }
7655
7656 func (c *ctxt7) opextr(p *obj.Prog, a obj.As, v int64, rn, rm, rt int16) uint32 {
7657 var b uint32
7658 o := c.opirr(p, a)
7659 if (o & (1 << 31)) != 0 {
7660 b = 63
7661 } else {
7662 b = 31
7663 }
7664 if v < 0 || uint32(v) > b {
7665 c.ctxt.Diag("illegal bit number\n%v", p)
7666 }
7667 o |= uint32(v) << 10
7668 o |= uint32(rn&31) << 5
7669 o |= uint32(rm&31) << 16
7670 o |= uint32(rt & 31)
7671 return o
7672 }
7673
7674
7675 func (c *ctxt7) opldpstp(p *obj.Prog, o *Optab, vo int32, rbase, rl, rh int16, ldp uint32) uint32 {
7676 wback := false
7677 if o.scond == C_XPOST || o.scond == C_XPRE {
7678 wback = true
7679 }
7680 switch p.As {
7681 case ALDP, ALDPW, ALDPSW:
7682 c.checkUnpredictable(p, true, wback, p.From.Reg, p.To.Reg, int16(p.To.Offset))
7683 case ASTP, ASTPW:
7684 if wback {
7685 c.checkUnpredictable(p, false, true, p.To.Reg, p.From.Reg, int16(p.From.Offset))
7686 }
7687 case AFLDPD, AFLDPQ, AFLDPS:
7688 c.checkUnpredictable(p, true, false, p.From.Reg, p.To.Reg, int16(p.To.Offset))
7689 }
7690 var ret uint32
7691
7692 switch p.As {
7693 case AFLDPQ, AFSTPQ:
7694 if vo < -1024 || vo > 1008 || vo%16 != 0 {
7695 c.ctxt.Diag("invalid offset %v\n", p)
7696 }
7697 vo /= 16
7698 ret = 2<<30 | 1<<26
7699 case AFLDPD, AFSTPD:
7700 if vo < -512 || vo > 504 || vo%8 != 0 {
7701 c.ctxt.Diag("invalid offset %v\n", p)
7702 }
7703 vo /= 8
7704 ret = 1<<30 | 1<<26
7705 case AFLDPS, AFSTPS:
7706 if vo < -256 || vo > 252 || vo%4 != 0 {
7707 c.ctxt.Diag("invalid offset %v\n", p)
7708 }
7709 vo /= 4
7710 ret = 1 << 26
7711 case ALDP, ASTP:
7712 if vo < -512 || vo > 504 || vo%8 != 0 {
7713 c.ctxt.Diag("invalid offset %v\n", p)
7714 }
7715 vo /= 8
7716 ret = 2 << 30
7717 case ALDPW, ASTPW:
7718 if vo < -256 || vo > 252 || vo%4 != 0 {
7719 c.ctxt.Diag("invalid offset %v\n", p)
7720 }
7721 vo /= 4
7722 ret = 0
7723 case ALDPSW:
7724 if vo < -256 || vo > 252 || vo%4 != 0 {
7725 c.ctxt.Diag("invalid offset %v\n", p)
7726 }
7727 vo /= 4
7728 ret = 1 << 30
7729 default:
7730 c.ctxt.Diag("invalid instruction %v\n", p)
7731 }
7732
7733 switch p.As {
7734 case AFLDPQ, AFLDPD, AFLDPS, AFSTPQ, AFSTPD, AFSTPS:
7735 if rl < REG_F0 || REG_F31 < rl || rh < REG_F0 || REG_F31 < rh {
7736 c.ctxt.Diag("invalid register pair %v\n", p)
7737 }
7738 case ALDP, ALDPW, ALDPSW:
7739 if rl < REG_R0 || REG_R31 < rl || rh < REG_R0 || REG_R31 < rh {
7740 c.ctxt.Diag("invalid register pair %v\n", p)
7741 }
7742 case ASTP, ASTPW:
7743 if rl < REG_R0 || REG_R31 < rl || rh < REG_R0 || REG_R31 < rh {
7744 c.ctxt.Diag("invalid register pair %v\n", p)
7745 }
7746 }
7747
7748 switch o.scond {
7749 case C_XPOST:
7750 ret |= 1 << 23
7751 case C_XPRE:
7752 ret |= 3 << 23
7753 default:
7754 ret |= 2 << 23
7755 }
7756 ret |= 5<<27 | (ldp&1)<<22 | uint32(vo&0x7f)<<15 | uint32(rh&31)<<10 | uint32(rbase&31)<<5 | uint32(rl&31)
7757 return ret
7758 }
7759
7760 func (c *ctxt7) maskOpvldvst(p *obj.Prog, o1 uint32) uint32 {
7761 if p.As == AVLD1 || p.As == AVST1 {
7762 return o1
7763 }
7764
7765 o1 &^= 0xf000
7766 switch p.As {
7767 case AVLD1R, AVLD2R:
7768 o1 |= 0xC << 12
7769 case AVLD3R, AVLD4R:
7770 o1 |= 0xE << 12
7771 case AVLD2, AVST2:
7772 o1 |= 8 << 12
7773 case AVLD3, AVST3:
7774 o1 |= 4 << 12
7775 case AVLD4, AVST4:
7776 default:
7777 c.ctxt.Diag("unsupported instruction:%v\n", p.As)
7778 }
7779 return o1
7780 }
7781
7782
7785 func movesize(a obj.As) int {
7786 switch a {
7787 case AFMOVQ:
7788 return 4
7789
7790 case AMOVD, AFMOVD:
7791 return 3
7792
7793 case AMOVW, AMOVWU, AFMOVS:
7794 return 2
7795
7796 case AMOVH, AMOVHU:
7797 return 1
7798
7799 case AMOVB, AMOVBU:
7800 return 0
7801
7802 default:
7803 return -1
7804 }
7805 }
7806
7807
7808 func roff(rm int16, o uint32, amount int16) uint32 {
7809 return uint32(rm&31)<<16 | o<<13 | uint32(amount)<<10
7810 }
7811
7812
7813 func (c *ctxt7) encRegShiftOrExt(p *obj.Prog, a *obj.Addr, r int16) uint32 {
7814 var num, rm int16
7815 num = (r >> 5) & 7
7816 rm = r & 31
7817 switch {
7818 case REG_UXTB <= r && r < REG_UXTH:
7819 return roff(rm, 0, num)
7820 case REG_UXTH <= r && r < REG_UXTW:
7821 return roff(rm, 1, num)
7822 case REG_UXTW <= r && r < REG_UXTX:
7823 if a.Type == obj.TYPE_MEM {
7824 if num == 0 {
7825
7826
7827
7828
7829
7830 return roff(rm, 2, 2)
7831 } else {
7832 return roff(rm, 2, 6)
7833 }
7834 } else {
7835 return roff(rm, 2, num)
7836 }
7837 case REG_UXTX <= r && r < REG_SXTB:
7838 return roff(rm, 3, num)
7839 case REG_SXTB <= r && r < REG_SXTH:
7840 return roff(rm, 4, num)
7841 case REG_SXTH <= r && r < REG_SXTW:
7842 return roff(rm, 5, num)
7843 case REG_SXTW <= r && r < REG_SXTX:
7844 if a.Type == obj.TYPE_MEM {
7845 if num == 0 {
7846 return roff(rm, 6, 2)
7847 } else {
7848 return roff(rm, 6, 6)
7849 }
7850 } else {
7851 return roff(rm, 6, num)
7852 }
7853 case REG_SXTX <= r && r < REG_SPECIAL:
7854 if a.Type == obj.TYPE_MEM {
7855 if num == 0 {
7856 return roff(rm, 7, 2)
7857 } else {
7858 return roff(rm, 7, 6)
7859 }
7860 } else {
7861 return roff(rm, 7, num)
7862 }
7863 case REG_LSL <= r && r < REG_ARNG:
7864 if a.Type == obj.TYPE_MEM {
7865 if num == 0 {
7866 return roff(rm, 3, 2)
7867 } else {
7868 return roff(rm, 3, 6)
7869 }
7870 } else if isADDWop(p.As) {
7871 return roff(rm, 2, num)
7872 }
7873 return roff(rm, 3, num)
7874 default:
7875 c.ctxt.Diag("unsupported register extension type.")
7876 }
7877
7878 return 0
7879 }
7880
7881
7882 func pack(q uint32, arngA, arngB uint8) uint32 {
7883 return uint32(q)<<16 | uint32(arngA)<<8 | uint32(arngB)
7884 }
7885
View as plain text