1//=- AArch64SchedThunderX3T110.td - Marvell ThunderX3 T110 ---*- tablegen -*-=//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// This file defines the scheduling model for Marvell ThunderX3T110
10// family of processors.
11//
12//===----------------------------------------------------------------------===//
13
14//===----------------------------------------------------------------------===//
15// Pipeline Description.
16
17def ThunderX3T110Model : SchedMachineModel {
18  let IssueWidth            =   4; // 4 micro-ops dispatched at a time.
19  let MicroOpBufferSize     =  70; // 70 entries in micro-op re-order buffer.
20  let LoadLatency           =   4; // Optimistic load latency.
21  let MispredictPenalty     =  12; // Extra cycles for mispredicted branch.
22  // Determined via a mix of micro-arch details and experimentation.
23  let LoopMicroOpBufferSize = 128; // FIXME: might be much bigger in TX3.
24  let PostRAScheduler       =   1; // Using PostRA sched.
25  let CompleteModel         =   1;
26
27  list<Predicate> UnsupportedFeatures = !listconcat(SVEUnsupported.F,
28                                                    PAUnsupported.F,
29                                                    [HasMTE]);
30  // FIXME: Remove when all errors have been fixed.
31  let FullInstRWOverlapCheck = 0;
32}
33
34let SchedModel = ThunderX3T110Model in {
35
36// Issue ports.
37
38// Port 0: ALU.
39def THX3T110P0 : ProcResource<1>;
40
41// Port 1: ALU.
42def THX3T110P1 : ProcResource<1>;
43
44// Port 2: ALU/Branch.
45def THX3T110P2 : ProcResource<1>;
46
47// Port 3: ALU/Branch.
48def THX3T110P3 : ProcResource<1>;
49
50// Port 4: Load/Store.
51def THX3T110P4 : ProcResource<1>;
52
53// Port 5: Load/store.
54def THX3T110P5 : ProcResource<1>;
55
56// Port 6: FP/Neon/SIMD/Crypto.
57def THX3T110P6FP0 : ProcResource<1>;
58
59// Port 7: FP/Neon/SIMD/Crypto.
60def THX3T110P7FP1 : ProcResource<1>;
61
62// Port 8: FP/Neon/SIMD/Crypto.
63def THX3T110P8FP2 : ProcResource<1>;
64
65// Port 9: FP/Neon/SIMD/Crypto.
66def THX3T110P9FP3 : ProcResource<1>;
67
68// Port 10: Store Data Unit.
69def THX3T110SD0 : ProcResource<1>;
70
71// Define groups for the functional units on each issue port.  Each group
72// created will be used by a WriteRes.
73
74// Integer divide/mulhi micro-ops only on port I1.
75def THX3T110I1 : ProcResGroup<[THX3T110P1]>;
76
77// Branch micro-ops on ports I2/I3.
78def THX3T110I23 : ProcResGroup<[THX3T110P2, THX3T110P3]>;
79
80// Branch micro-ops on ports I1/I2/I3.
81def THX3T110I123 : ProcResGroup<[THX3T110P1, THX3T110P2, THX3T110P3]>;
82
83// Integer micro-ops on ports I0/I1/I2.
84def THX3T110I012 : ProcResGroup<[THX3T110P0, THX3T110P1, THX3T110P2]>;
85
86// Integer micro-ops on ports I0/I1/I2/I3.
87def THX3T110I0123 : ProcResGroup<[THX3T110P0, THX3T110P1,
88                                  THX3T110P2, THX3T110P3]>;
89
90// FP micro-ops on ports FP0/FP1/FP2/FP3.
91def THX3T110FP0123 : ProcResGroup<[THX3T110P6FP0, THX3T110P7FP1,
92                                   THX3T110P8FP2, THX3T110P9FP3]>;
93
94// FP micro-ops on ports FP2/FP3.
95def THX3T110FP23 : ProcResGroup<[THX3T110P8FP2, THX3T110P9FP3]>;
96
97// ASIMD micro-ops on ports FP0/FP1/FP2/FP3.
98def THX3T110SIMD : ProcResGroup<[THX3T110P6FP0, THX3T110P7FP1,
99                                 THX3T110P8FP2, THX3T110P9FP3]>;
100
101// Store data micro-ops only on port 10.
102def THX3T110SD : ProcResGroup<[THX3T110SD0]>;
103
104// Load/store micro-ops on ports P4/P5.
105def THX3T110LS : ProcResGroup<[THX3T110P4, THX3T110P5]>;
106
107// 70 entry unified scheduler.
108def THX3T110ANY: ProcResGroup<[THX3T110P0, THX3T110P1, THX3T110P2,
109                               THX3T110P3, THX3T110P4, THX3T110P5,
110                               THX3T110P6FP0, THX3T110P7FP1,
111                               THX3T110P8FP2, THX3T110P9FP3]> {
112  let BufferSize = 70;
113}
114
115// Define commonly used write types for InstRW specializations.
116// All definitions follow the format: THX3T110Write_<NumCycles>Cyc_<Resources>.
117
118// 3 cycles on I1.
119def THX3T110Write_3Cyc_I1 : SchedWriteRes<[THX3T110I1]> {
120  let Latency = 3;
121  let NumMicroOps = 2;
122}
123
124// 4 cycles on I1.
125def THX3T110Write_4Cyc_I1 : SchedWriteRes<[THX3T110I1]> {
126  let Latency = 4;
127  let NumMicroOps = 2;
128}
129
130// 5 cycles on I1.
131def THX3T110Write_5Cyc_I1 : SchedWriteRes<[THX3T110I1]> {
132  let Latency = 5;
133  let NumMicroOps = 2;
134}
135
136// 7 cycles on I1.
137def THX3T110Write_7Cyc_I1 : SchedWriteRes<[THX3T110I1]> {
138  let Latency = 7;
139  let NumMicroOps = 3;
140}
141
142// 23 cycles on I1.
143def THX3T110Write_23Cyc_I1 : SchedWriteRes<[THX3T110I1]> {
144  let Latency = 23;
145  let ResourceCycles = [13, 23];
146  let NumMicroOps = 4;
147}
148
149// 39 cycles on I1.
150def THX3T110Write_39Cyc_I1 : SchedWriteRes<[THX3T110I1]> {
151  let Latency = 39;
152  let ResourceCycles = [13, 39];
153  let NumMicroOps = 4;
154}
155
156// 1 cycle on I2/I3
157def THX3T110Write_1Cyc_I23 : SchedWriteRes<[THX3T110I23]> {
158  let Latency = 1;
159  let NumMicroOps = 2;
160}
161
162// 8 cycles on I2/I3
163def THX3T110Write_8Cyc_I23 : SchedWriteRes<[THX3T110I23]> {
164  let Latency = 8;
165  let NumMicroOps = 3;
166}
167
168// 1 cycle on I1/I2/I3
169def THX3T110Write_1Cyc_I123 : SchedWriteRes<[THX3T110I123]> {
170  let Latency = 1;
171  let NumMicroOps = 2;
172}
173
174// 8 cycles on I1/I2/I3
175def THX3T110Write_8Cyc_I123 : SchedWriteRes<[THX3T110I123]> {
176  let Latency = 8;
177  let NumMicroOps = 3;
178}
179
180// 1 cycle on I0/I1/I2/I3.
181def THX3T110Write_1Cyc_I0123 : SchedWriteRes<[THX3T110I0123]> {
182  let Latency = 1;
183  let NumMicroOps = 2;
184}
185
186// 2 cycles on I0/I1/I2/I3.
187def THX3T110Write_2Cyc_I0123 : SchedWriteRes<[THX3T110I0123]> {
188  let Latency = 2;
189  let NumMicroOps = 2;
190}
191
192// 3 cycles on I0/I1/I2/I3.
193def THX3T110Write_3Cyc_I0123 : SchedWriteRes<[THX3T110I0123]> {
194  let Latency = 3;
195  let NumMicroOps = 2;
196}
197
198// 4 cycles on I0/I1/I2/I3.
199def THX3T110Write_4Cyc_I0123 : SchedWriteRes<[THX3T110I0123]> {
200  let Latency = 4;
201  let NumMicroOps = 3;
202}
203
204// 5 cycles on I0/I1/I2/I3.
205def THX3T110Write_5Cyc_I0123 : SchedWriteRes<[THX3T110I0123]> {
206  let Latency = 5;
207  let NumMicroOps = 3;
208}
209
210// 6 cycles on I0/I1/I2/I3.
211def THX3T110Write_6Cyc_I0123 : SchedWriteRes<[THX3T110I0123]> {
212  let Latency = 6;
213  let NumMicroOps = 3;
214}
215
216// 8 cycles on I0/I1/I2/I3.
217def THX3T110Write_8Cyc_I0123 : SchedWriteRes<[THX3T110I0123]> {
218  let Latency = 8;
219  let NumMicroOps = 4;
220}
221
222// 13 cycles on I0/I1/I2/I3.
223def THX3T110Write_13Cyc_I0123 : SchedWriteRes<[THX3T110I0123]> {
224  let Latency = 13;
225  let NumMicroOps = 3;
226}
227
228// 23 cycles on I0/I1/I2/I3.
229def THX3T110Write_23Cyc_I0123 : SchedWriteRes<[THX3T110I0123]> {
230  let Latency = 23;
231  let NumMicroOps = 3;
232}
233
234// 39 cycles on I0/I1/I2/I3.
235def THX3T110Write_39Cyc_I0123 : SchedWriteRes<[THX3T110I0123]> {
236  let Latency = 39;
237  let NumMicroOps = 3;
238}
239
240// 4 cycles on F2/F3.
241def THX3T110Write_4Cyc_F23 : SchedWriteRes<[THX3T110FP23]> {
242  let Latency = 4;
243  let NumMicroOps = 2;
244}
245
246// 5 cycles on F0/F1/F2/F3.
247def THX3T110Write_5Cyc_F01 : SchedWriteRes<[THX3T110FP0123]> {
248  let Latency = 5;
249  let NumMicroOps = 2;
250}
251
252// 6 cycles on F0/F1/F2/F3.
253def THX3T110Write_6Cyc_F01 : SchedWriteRes<[THX3T110FP0123]> {
254  let Latency = 6;
255  let NumMicroOps = 3;
256}
257
258// 7 cycles on F0/F1/F2/F3.
259def THX3T110Write_7Cyc_F01 : SchedWriteRes<[THX3T110FP0123]> {
260  let Latency = 7;
261  let NumMicroOps = 3;
262}
263
264// 8 cycles on F0/F1/F2/F3.
265def THX3T110Write_8Cyc_F01 : SchedWriteRes<[THX3T110FP0123]> {
266  let Latency = 8;
267  let NumMicroOps = 3;
268}
269
270// 10 cycles on F0/F1/F2/F3.
271def THX3T110Write_10Cyc_F01 : SchedWriteRes<[THX3T110FP0123]> {
272  let Latency = 10;
273  let NumMicroOps = 3;
274}
275
276// 16 cycles on F0/F1/F2/F3.
277def THX3T110Write_16Cyc_F01 : SchedWriteRes<[THX3T110FP0123]> {
278  let Latency = 16;
279  let NumMicroOps = 3;
280  let ResourceCycles = [8];
281}
282
283// 23 cycles on F0/F1/F2/F3.
284def THX3T110Write_23Cyc_F01 : SchedWriteRes<[THX3T110FP0123]> {
285  let Latency = 23;
286  let NumMicroOps = 3;
287  let ResourceCycles = [11];
288}
289
290// 1 cycle on LS0/LS1.
291def THX3T110Write_1Cyc_LS01 : SchedWriteRes<[THX3T110LS]> {
292  let Latency = 1;
293  let NumMicroOps = 1;
294}
295
296// 2 cycles on LS0/LS1.
297def THX3T110Write_2Cyc_LS01 : SchedWriteRes<[THX3T110LS]> {
298  let Latency = 2;
299  let NumMicroOps = 2;
300}
301
302// 4 cycles on LS0/LS1.
303def THX3T110Write_4Cyc_LS01 : SchedWriteRes<[THX3T110LS]> {
304  let Latency = 4;
305  let NumMicroOps = 2;
306  let ResourceCycles = [2];
307}
308
309// 5 cycles on LS0/LS1.
310def THX3T110Write_5Cyc_LS01 : SchedWriteRes<[THX3T110LS]> {
311  let Latency = 5;
312  let NumMicroOps = 3;
313}
314
315// 6 cycles on LS0/LS1.
316def THX3T110Write_6Cyc_LS01 : SchedWriteRes<[THX3T110LS]> {
317  let Latency = 6;
318  let NumMicroOps = 3;
319}
320
321// 4 + 5 cycles on LS0/LS1.
322// First resource is available after 4 cycles.
323// Second resource is available after 5 cycles.
324// Load vector pair, immed offset, Q-form [LDP/LDNP].
325def THX3T110Write_4_5Cyc_LS01 : SchedWriteRes<[THX3T110LS]> {
326  let Latency = 4;
327  let NumMicroOps = 2;
328  let ResourceCycles = [4, 5];
329}
330
331// 4 + 8 cycles on LS0/LS1.
332// First resource is available after 4 cycles.
333// Second resource is available after 8 cycles.
334// Load vector pair, immed offset, S/D-form [LDP/LDNP].
335def THX3T110Write_4_8Cyc_LS01 : SchedWriteRes<[THX3T110LS]> {
336  let Latency = 4;
337  let NumMicroOps = 2;
338  let ResourceCycles = [4, 8];
339}
340
341// 11 cycles on LS0/LS1 and I1.
342def THX3T110Write_11Cyc_LS01_I1 :
343  SchedWriteRes<[THX3T110LS, THX3T110I1]> {
344  let Latency = 11;
345  let NumMicroOps = 4;
346}
347
348// 1 cycles on LS0/LS1 and I0/I1/I2/I3.
349def THX3T110Write_1Cyc_LS01_I0123 :
350  SchedWriteRes<[THX3T110LS, THX3T110I0123]> {
351  let Latency = 1;
352  let NumMicroOps = 2;
353}
354
355// 1 cycles on LS0/LS1 and 2 of I0/I1/I2/I3.
356def THX3T110Write_1Cyc_LS01_I0123_I0123 :
357  SchedWriteRes<[THX3T110LS, THX3T110I0123, THX3T110I0123]> {
358  let Latency = 1;
359  let NumMicroOps = 3;
360}
361
362// 4 cycles on LS0/LS1 and I0/I1/I2/I3.
363def THX3T110Write_4Cyc_LS01_I0123 :
364  SchedWriteRes<[THX3T110LS, THX3T110I0123]> {
365  let Latency = 4;
366  let NumMicroOps = 3;
367}
368
369// 4 cycles on LS0/LS1 and 2 of I0/I1/I2/I3.
370def THX3T110Write_4Cyc_LS01_I0123_I0123 :
371  SchedWriteRes<[THX3T110LS, THX3T110I0123, THX3T110I0123]> {
372  let Latency = 4;
373  let NumMicroOps = 3;
374}
375
376// 5 cycles on LS0/LS1 and I0/I1/I2/I3.
377def THX3T110Write_5Cyc_LS01_I0123 :
378  SchedWriteRes<[THX3T110LS, THX3T110I0123]> {
379  let Latency = 5;
380  let NumMicroOps = 3;
381}
382
383// 5 cycles on LS0/LS1 and 2 of I0/I1/I2/I3.
384def THX3T110Write_5Cyc_LS01_I0123_I0123 :
385  SchedWriteRes<[THX3T110LS, THX3T110I0123, THX3T110I0123]> {
386  let Latency = 5;
387  let NumMicroOps = 3;
388}
389
390// 6 cycles on LS0/LS1 and I0/I1/I2/I3.
391def THX3T110Write_6Cyc_LS01_I012 :
392  SchedWriteRes<[THX3T110LS, THX3T110I0123]> {
393  let Latency = 6;
394  let NumMicroOps = 4;
395}
396
397// 6 cycles on LS0/LS1 and 2 of I0/I1/I2/I3.
398def THX3T110Write_6Cyc_LS01_I0123_I0123 :
399  SchedWriteRes<[THX3T110LS, THX3T110I0123, THX3T110I0123]> {
400  let Latency = 6;
401  let NumMicroOps = 3;
402}
403
404// 1 cycle on LS0/LS1 and SD.
405def THX3T110Write_1Cyc_LS01_SD :
406  SchedWriteRes<[THX3T110LS, THX3T110SD]> {
407  let Latency = 1;
408  let NumMicroOps = 2;
409}
410
411// 2 cycles on LS0/LS1 and SD.
412def THX3T110Write_2Cyc_LS01_SD :
413  SchedWriteRes<[THX3T110LS, THX3T110SD]> {
414  let Latency = 2;
415  let NumMicroOps = 2;
416}
417
418// 4 cycles on LS0/LS1 and SD.
419def THX3T110Write_4Cyc_LS01_SD :
420  SchedWriteRes<[THX3T110LS, THX3T110SD]> {
421  let Latency = 4;
422  let NumMicroOps = 3;
423}
424
425// 5 cycles on LS0/LS1 and SD.
426def THX3T110Write_5Cyc_LS01_SD :
427  SchedWriteRes<[THX3T110LS, THX3T110SD]> {
428  let Latency = 5;
429  let NumMicroOps = 4;
430}
431
432// 6 cycles on LS0/LS1 and SD.
433def THX3T110Write_6Cyc_LS01_SD :
434  SchedWriteRes<[THX3T110LS, THX3T110SD]> {
435  let Latency = 6;
436  let NumMicroOps = 5;
437}
438
439// 1 cycle on LS0/LS1, SD and I0/I1/I2/I3.
440def THX3T110Write_1Cyc_LS01_SD_I0123 :
441  SchedWriteRes<[THX3T110LS, THX3T110SD, THX3T110I0123]> {
442  let Latency = 1;
443  let NumMicroOps = 2;
444}
445
446// 2 cycles on LS0/LS1, SD and I0/I1/I2/I3.
447def THX3T110Write_2Cyc_LS01_SD_I0123 :
448  SchedWriteRes<[THX3T110LS, THX3T110SD, THX3T110I0123]> {
449  let Latency = 2;
450  let NumMicroOps = 2;
451}
452
453// 4 cycles on LS0/LS1, SD and I0/I1/I2/I3.
454def THX3T110Write_4Cyc_LS01_SD_I0123 :
455  SchedWriteRes<[THX3T110LS, THX3T110SD, THX3T110I0123]> {
456  let Latency = 4;
457  let NumMicroOps = 3;
458}
459
460// 5 cycles on LS0/LS1, SD and I0/I1/I2/I3.
461def THX3T110Write_5Cyc_LS01_SD_I0123 :
462  SchedWriteRes<[THX3T110LS, THX3T110SD, THX3T110I0123]> {
463  let Latency = 5;
464  let NumMicroOps = 4;
465}
466
467// 6 cycles on LS0/LS1, SD and I0/I1/I2/I3.
468def THX3T110Write_6Cyc_LS01_SD_I0123 :
469  SchedWriteRes<[THX3T110LS, THX3T110SD, THX3T110I0123]> {
470  let Latency = 6;
471  let NumMicroOps = 5;
472}
473
474// 1 cycles on LS0/LS1 and F0/F1/F2/F3.
475def THX3T110Write_1Cyc_LS01_F0123 :
476  SchedWriteRes<[THX3T110LS, THX3T110FP0123]> {
477  let Latency = 1;
478  let NumMicroOps = 2;
479}
480
481// 5 cycles on LS0/LS1 and F0/F1/F2/F3.
482def THX3T110Write_5Cyc_LS01_F0123 :
483  SchedWriteRes<[THX3T110LS, THX3T110FP0123]> {
484  let Latency = 5;
485  let NumMicroOps = 3;
486}
487
488// 6 cycles on LS0/LS1 and F0/F1/F2/F3.
489def THX3T110Write_6Cyc_LS01_F0123 :
490  SchedWriteRes<[THX3T110LS, THX3T110FP0123]> {
491  let Latency = 6;
492  let NumMicroOps = 3;
493}
494
495// 7 cycles on LS0/LS1 and F0/F1/F2/F3.
496def THX3T110Write_7Cyc_LS01_F0123 :
497  SchedWriteRes<[THX3T110LS, THX3T110FP0123]> {
498  let Latency = 7;
499  let NumMicroOps = 3;
500}
501
502// 8 cycles on LS0/LS1 and F0/F1/F2/F3.
503def THX3T110Write_8Cyc_LS01_F0123 :
504  SchedWriteRes<[THX3T110LS, THX3T110FP0123]> {
505  let Latency = 8;
506  let NumMicroOps = 3;
507}
508
509// 8 cycles on LS0/LS1 and I0/I1/I2/I3.
510def THX3T110Write_8Cyc_LS01_I0123 :
511  SchedWriteRes<[THX3T110LS, THX3T110I0123]> {
512  let Latency = 8;
513  let NumMicroOps = 3;
514}
515
516// 12 cycles on LS0/LS1 and I0/I1/I2/I3.
517def THX3T110Write_12Cyc_LS01_I0123 :
518  SchedWriteRes<[THX3T110LS, THX3T110I0123]> {
519  let Latency = 12;
520  let NumMicroOps = 4;
521}
522
523// 16 cycles on LS0/LS1 and I0/I1/I2/I3.
524def THX3T110Write_16Cyc_LS01_I0123 :
525  SchedWriteRes<[THX3T110LS, THX3T110I0123]> {
526  let Latency = 16;
527  let NumMicroOps = 5;
528}
529
530// 24 cycles on LS0/LS1 and I0/I1/I2/I3.
531def THX3T110Write_24Cyc_LS01_I0123 :
532  SchedWriteRes<[THX3T110LS, THX3T110I0123]> {
533  let Latency = 24;
534  let NumMicroOps = 10;
535}
536
537// 32 cycles on LS0/LS1 and I0/I1/I2/I3.
538def THX3T110Write_32Cyc_LS01_I0123 :
539  SchedWriteRes<[THX3T110LS, THX3T110I0123]> {
540  let Latency = 32;
541  let NumMicroOps = 14;
542}
543
544// 3 cycles on F0/F1/F2/F3.
545def THX3T110Write_3Cyc_F0123 : SchedWriteRes<[THX3T110FP0123]> {
546  let Latency = 3;
547  let NumMicroOps = 2;
548}
549
550// 4 cycles on F0/F1/F2/F3.
551def THX3T110Write_4Cyc_F0123 : SchedWriteRes<[THX3T110FP0123]> {
552  let Latency = 4;
553  let NumMicroOps = 2;
554}
555
556// 5 cycles on F0/F1/F2/F3.
557def THX3T110Write_5Cyc_F0123 : SchedWriteRes<[THX3T110FP0123]> {
558  let Latency = 5;
559  let NumMicroOps = 2;
560}
561
562// 10 cycles on F0/F1/F2/F3.
563def THX3T110Write_10Cyc_F0123 : SchedWriteRes<[THX3T110FP0123]> {
564  let Latency = 10;
565  let NumMicroOps = 4;
566}
567
568// 15 cycles on F0/F1/F2/F3.
569def THX3T110Write_15Cyc_F0123 : SchedWriteRes<[THX3T110FP0123]> {
570  let Latency = 15;
571  let NumMicroOps = 7;
572}
573
574// 16 cycles on F0/F1/F2/F3.
575def THX3T110Write_16Cyc_F0123 : SchedWriteRes<[THX3T110FP0123]> {
576  let Latency = 16;
577  let NumMicroOps = 3;
578}
579
580// 18 cycles on F0/F1/F2/F3.
581def THX3T110Write_18Cyc_F0123 : SchedWriteRes<[THX3T110FP0123]> {
582  let Latency = 18;
583  let NumMicroOps = 3;
584}
585
586// 19 cycles on F0/F1/F2/F3.
587def THX3T110Write_19Cyc_F0123 : SchedWriteRes<[THX3T110FP0123]> {
588  let Latency = 19;
589  let NumMicroOps = 4;
590}
591
592// 20 cycles on F0/F1/F2/F3.
593def THX3T110Write_20Cyc_F0123 : SchedWriteRes<[THX3T110FP0123]> {
594  let Latency = 20;
595  let NumMicroOps = 4;
596}
597
598// 23 cycles on F0/F1/F2/F3.
599def THX3T110Write_23Cyc_F0123 : SchedWriteRes<[THX3T110FP0123]> {
600  let Latency = 23;
601  let NumMicroOps = 4;
602}
603
604// 3 cycles on F2/F3 and 4 cycles on F0/F1/F2/F3.
605def THX3T110Write_3_4Cyc_F23_F0123 :
606  SchedWriteRes<[THX3T110FP23, THX3T110FP0123]> {
607  let Latency = 3;
608  let NumMicroOps = 2;
609  let ResourceCycles = [3, 4];
610}
611
612
613// Define commonly used read types.
614
615// No forwarding is provided for these types.
616def : ReadAdvance<ReadI,       0>;
617def : ReadAdvance<ReadISReg,   0>;
618def : ReadAdvance<ReadIEReg,   0>;
619def : ReadAdvance<ReadIM,      0>;
620def : ReadAdvance<ReadIMA,     0>;
621def : ReadAdvance<ReadID,      0>;
622def : ReadAdvance<ReadExtrHi,  0>;
623def : ReadAdvance<ReadAdrBase, 0>;
624def : ReadAdvance<ReadVLD,     0>;
625def : ReadAdvance<ReadST,      0>;
626
627//===----------------------------------------------------------------------===//
628// 3. Instruction Tables.
629
630//---
631// 3.1 Branch Instructions
632//---
633
634// Branch, immed
635// Branch and link, immed
636// Compare and branch
637def : WriteRes<WriteBr,      [THX3T110I23]> {
638  let Latency = 1;
639  let NumMicroOps = 2;
640}
641
642// Branch, register
643// Branch and link, register != LR
644// Branch and link, register = LR
645def : WriteRes<WriteBrReg,   [THX3T110I23]> {
646  let Latency = 1;
647  let NumMicroOps = 2;
648}
649
650def : WriteRes<WriteSys,     []> { let Latency = 1; }
651def : WriteRes<WriteBarrier, []> { let Latency = 1; }
652def : WriteRes<WriteHint,    []> { let Latency = 1; }
653
654def : WriteRes<WriteAtomic,  []> {
655  let Latency = 4;
656  let NumMicroOps = 2;
657}
658
659//---
660// Branch
661//---
662def : InstRW<[THX3T110Write_1Cyc_I23], (instrs B, BL, BR, BLR)>;
663def : InstRW<[THX3T110Write_1Cyc_I23], (instrs Bcc)>;
664def : InstRW<[THX3T110Write_1Cyc_I23], (instrs RET)>;
665def : InstRW<[THX3T110Write_1Cyc_I23],
666            (instrs CBZW, CBZX, CBNZW, CBNZX, TBZW, TBZX, TBNZW, TBNZX)>;
667
668//---
669// 3.2 Arithmetic and Logical Instructions
670// 3.3 Move and Shift Instructions
671//---
672
673
674// ALU, basic
675// Conditional compare
676// Conditional select
677// Address generation
678def : WriteRes<WriteI,       [THX3T110I0123]> {
679  let Latency = 1;
680  let ResourceCycles = [1];
681  let NumMicroOps = 2;
682}
683
684def : InstRW<[WriteI],
685            (instregex "ADD?(W|X)r(i|r|s|x)",   "ADDS?(W|X)r(i|r|s|x)(64)?",
686                       "AND?(W|X)r(i|r|s|x)",   "ANDS?(W|X)r(i|r|s|x)",
687                       "ADC(W|X)r",
688                       "BIC?(W|X)r(i|r|s|x)",   "BICS?(W|X)r(i|r|s|x)",
689                       "EON?(W|X)r(i|r|s|x)",   "ORN?(W|X)r(i|r|s|x)",
690                       "ORR?(W|X)r(i|r|s|x)",   "SUB?(W|X)r(i|r|s|x)",
691                       "SUBS?(W|X)r(i|r|s|x)",  "SBC(W|X)r",
692                       "SBCS(W|X)r",            "CCMN(W|X)(i|r)",
693                       "CCMP(W|X)(i|r)",        "CSEL(W|X)r",
694                       "CSINC(W|X)r",           "CSINV(W|X)r",
695                       "CSNEG(W|X)r")>;
696
697def : InstRW<[WriteI], (instrs COPY)>;
698
699// ALU, extend and/or shift
700def : WriteRes<WriteISReg,   [THX3T110I0123]> {
701  let Latency = 2;
702  let ResourceCycles = [2];
703  let NumMicroOps = 2;
704}
705
706def : InstRW<[WriteISReg],
707            (instregex "ADD?(W|X)r(i|r|s|x)",   "ADDS?(W|X)r(i|r|s|x)(64)?",
708                       "AND?(W|X)r(i|r|s|x)",   "ANDS?(W|X)r(i|r|s|x)",
709                       "ADC(W|X)r",
710                       "BIC?(W|X)r(i|r|s|x)",   "BICS?(W|X)r(i|r|s|x)",
711                       "EON?(W|X)r(i|r|s|x)",   "ORN?(W|X)r(i|r|s|x)",
712                       "ORR?(W|X)r(i|r|s|x)",   "SUB?(W|X)r(i|r|s|x)",
713                       "SUBS?(W|X)r(i|r|s|x)",  "SBC(W|X)r",
714                       "SBCS(W|X)r",            "CCMN(W|X)(i|r)",
715                       "CCMP(W|X)(i|r)",        "CSEL(W|X)r",
716                       "CSINC(W|X)r",           "CSINV(W|X)r",
717                       "CSNEG(W|X)r")>;
718
719def : WriteRes<WriteIEReg,   [THX3T110I0123]> {
720  let Latency = 1;
721  let ResourceCycles = [1];
722  let NumMicroOps = 2;
723}
724
725def : InstRW<[WriteIEReg],
726            (instregex "ADD?(W|X)r(i|r|s|x)",   "ADDS?(W|X)r(i|r|s|x)(64)?",
727                       "AND?(W|X)r(i|r|s|x)",   "ANDS?(W|X)r(i|r|s|x)",
728                       "ADC(W|X)r",
729                       "BIC?(W|X)r(i|r|s|x)",   "BICS?(W|X)r(i|r|s|x)",
730                       "EON?(W|X)r(i|r|s|x)",   "ORN?(W|X)r(i|r|s|x)",
731                       "ORR?(W|X)r(i|r|s|x)",   "SUB?(W|X)r(i|r|s|x)",
732                       "SUBS?(W|X)r(i|r|s|x)",  "SBC(W|X)r",
733                       "SBCS(W|X)r",            "CCMN(W|X)(i|r)",
734                       "CCMP(W|X)(i|r)",        "CSEL(W|X)r",
735                       "CSINC(W|X)r",           "CSINV(W|X)r",
736                       "CSNEG(W|X)r")>;
737
738// Move immed
739def : WriteRes<WriteImm,     [THX3T110I0123]> {
740  let Latency = 1;
741  let NumMicroOps = 2;
742}
743
744def : InstRW<[THX3T110Write_1Cyc_I0123],
745            (instrs MOVKWi, MOVKXi, MOVNWi, MOVNXi, MOVZWi, MOVZXi)>;
746
747def : InstRW<[THX3T110Write_1Cyc_I0123],
748            (instrs ASRVWr, ASRVXr, LSLVWr, LSLVXr, RORVWr, RORVXr)>;
749
750// Variable shift
751def : WriteRes<WriteIS,      [THX3T110I0123]> {
752  let Latency = 1;
753  let NumMicroOps = 2;
754}
755
756//---
757// 3.4 Divide and Multiply Instructions
758//---
759
760// Divide, W-form
761// Latency range of 13-23/13-39.
762def : WriteRes<WriteID32,    [THX3T110I1]> {
763  let Latency = 39;
764  let ResourceCycles = [39];
765  let NumMicroOps = 4;
766}
767
768// Divide, X-form
769def : WriteRes<WriteID64,    [THX3T110I1]> {
770  let Latency = 23;
771  let ResourceCycles = [23];
772  let NumMicroOps = 4;
773}
774
775// Multiply accumulate, W-form
776def : WriteRes<WriteIM32,    [THX3T110I0123]> {
777  let Latency = 5;
778  let NumMicroOps = 3;
779}
780
781// Multiply accumulate, X-form
782def : WriteRes<WriteIM64,    [THX3T110I0123]> {
783  let Latency = 5;
784  let NumMicroOps = 3;
785}
786
787//def : InstRW<[WriteIM32, ReadIM, ReadIM, ReadIMA, THX3T110Write_5Cyc_I012],
788//             (instrs MADDWrrr, MSUBWrrr)>;
789def : InstRW<[WriteIM32], (instrs MADDWrrr, MSUBWrrr)>;
790def : InstRW<[WriteIM32], (instrs MADDXrrr, MSUBXrrr)>;
791def : InstRW<[THX3T110Write_5Cyc_I0123],
792            (instregex "(S|U)(MADDL|MSUBL)rrr")>;
793
794def : InstRW<[WriteID32], (instrs SDIVWr, UDIVWr)>;
795def : InstRW<[WriteID64], (instrs SDIVXr, UDIVXr)>;
796
797// Bitfield extract, two reg
798def : WriteRes<WriteExtr,    [THX3T110I0123]> {
799  let Latency = 1;
800  let NumMicroOps = 2;
801}
802
803// Multiply high
804def : InstRW<[THX3T110Write_4Cyc_I1], (instrs SMULHrr, UMULHrr)>;
805
806// Miscellaneous Data-Processing Instructions
807// Bitfield extract
808def : InstRW<[THX3T110Write_1Cyc_I0123], (instrs EXTRWrri, EXTRXrri)>;
809
810// Bitifield move - basic
811def : InstRW<[THX3T110Write_1Cyc_I0123],
812            (instrs SBFMWri, SBFMXri, UBFMWri, UBFMXri)>;
813
814// Bitfield move, insert
815def : InstRW<[THX3T110Write_1Cyc_I0123], (instregex "^BFM")>;
816def : InstRW<[THX3T110Write_1Cyc_I0123], (instregex "(S|U)?BFM.*")>;
817
818// Count leading
819def : InstRW<[THX3T110Write_3_4Cyc_F23_F0123],
820            (instregex "^CLS(W|X)r$", "^CLZ(W|X)r$")>;
821
822// Reverse bits
823def : InstRW<[THX3T110Write_3_4Cyc_F23_F0123], (instrs RBITWr, RBITXr)>;
824
825// Cryptography Extensions
826def : InstRW<[THX3T110Write_4Cyc_F0123], (instregex "^AES[DE]")>;
827def : InstRW<[THX3T110Write_4Cyc_F0123], (instregex "^AESI?MC")>;
828def : InstRW<[THX3T110Write_4Cyc_F0123], (instregex "^PMULL")>;
829def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^SHA1SU0")>;
830def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^SHA1(H|SU1)")>;
831def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^SHA1[CMP]")>;
832def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^SHA256SU0")>;
833def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^SHA256(H|H2|SU1)")>;
834
835// CRC Instructions
836// def : InstRW<[THX3T110Write_4Cyc_I1], (instregex "^CRC32", "^CRC32C")>;
837def : InstRW<[THX3T110Write_4Cyc_I1],
838            (instrs CRC32Brr, CRC32Hrr, CRC32Wrr, CRC32Xrr)>;
839
840def : InstRW<[THX3T110Write_4Cyc_I1],
841            (instrs CRC32CBrr, CRC32CHrr, CRC32CWrr, CRC32CXrr)>;
842
843// Reverse bits/bytes
844// NOTE: Handled by WriteI.
845
846//---
847// 3.6 Load Instructions
848// 3.10 FP Load Instructions
849//---
850
851// Load register, literal
852// Load register, unscaled immed
853// Load register, immed unprivileged
854// Load register, unsigned immed
855def : WriteRes<WriteLD,      [THX3T110LS]> {
856  let Latency = 4;
857  let NumMicroOps = 4;
858}
859
860// Load register, immed post-index
861// NOTE: Handled by WriteLD, WriteI.
862// Load register, immed pre-index
863// NOTE: Handled by WriteLD, WriteAdr.
864def : WriteRes<WriteAdr,     [THX3T110I0123]> {
865  let Latency = 1;
866  let NumMicroOps = 2;
867}
868
869// Load pair, immed offset, normal
870// Load pair, immed offset, signed words, base != SP
871// Load pair, immed offset signed words, base = SP
872// LDP only breaks into *one* LS micro-op.  Thus
873// the resources are handled by WriteLD.
874def : WriteRes<WriteLDHi,    []> {
875  let Latency = 4;
876  let NumMicroOps = 4;
877}
878
879// Load register offset, basic
880// Load register, register offset, scale by 4/8
881// Load register, register offset, scale by 2
882// Load register offset, extend
883// Load register, register offset, extend, scale by 4/8
884// Load register, register offset, extend, scale by 2
885def THX3T110WriteLDIdx : SchedWriteVariant<[
886  SchedVar<ScaledIdxPred, [THX3T110Write_4Cyc_LS01_I0123_I0123]>,
887  SchedVar<NoSchedPred,   [THX3T110Write_4Cyc_LS01_I0123]>]>;
888def : SchedAlias<WriteLDIdx, THX3T110WriteLDIdx>;
889
890def THX3T110ReadAdrBase : SchedReadVariant<[
891  SchedVar<ScaledIdxPred, [ReadDefault]>,
892  SchedVar<NoSchedPred,   [ReadDefault]>]>;
893def : SchedAlias<ReadAdrBase, THX3T110ReadAdrBase>;
894
895// Load pair, immed pre-index, normal
896// Load pair, immed pre-index, signed words
897// Load pair, immed post-index, normal
898// Load pair, immed post-index, signed words
899def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDNPDi)>;
900def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDNPQi)>;
901def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDNPSi)>;
902def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDNPWi)>;
903def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDNPXi)>;
904
905def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDPDi)>;
906def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDPQi)>;
907def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDPSi)>;
908def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDPSWi)>;
909def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDPWi)>;
910def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, WriteLDHi], (instrs LDPXi)>;
911
912def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDRBui)>;
913def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDRDui)>;
914def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDRHui)>;
915def : InstRW<[THX3T110Write_5Cyc_LS01], (instrs LDRQui)>;
916def : InstRW<[THX3T110Write_5Cyc_LS01], (instrs LDRSui)>;
917
918def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDRDl)>;
919def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDRQl)>;
920def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDRWl)>;
921def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDRXl)>;
922
923def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDTRBi)>;
924def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDTRHi)>;
925def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDTRWi)>;
926def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDTRXi)>;
927
928def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDTRSBWi)>;
929def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDTRSBXi)>;
930def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDTRSHWi)>;
931def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDTRSHXi)>;
932def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDTRSWi)>;
933
934def : InstRW<[THX3T110Write_5Cyc_LS01_I0123, WriteLDHi, WriteAdr],
935            (instrs LDPDpre)>;
936def : InstRW<[THX3T110Write_5Cyc_LS01_I0123, WriteLDHi, WriteAdr],
937            (instrs LDPQpre)>;
938def : InstRW<[THX3T110Write_5Cyc_LS01_I0123, WriteLDHi, WriteAdr],
939            (instrs LDPSpre)>;
940def : InstRW<[THX3T110Write_5Cyc_LS01_I0123, WriteLDHi, WriteAdr],
941            (instrs LDPWpre)>;
942def : InstRW<[THX3T110Write_5Cyc_LS01_I0123, WriteLDHi, WriteAdr],
943            (instrs LDPWpre)>;
944
945def : InstRW<[THX3T110Write_4Cyc_LS01, WriteAdr],
946            (instrs LDRBpre, LDRDpre, LDRHpre, LDRQpre,
947                    LDRSpre, LDRWpre, LDRXpre,
948                    LDRSBWpre, LDRSBXpre, LDRSBWpost, LDRSBXpost,
949                    LDRSHWpre, LDRSHXpre, LDRSHWpost, LDRSHXpost,
950                    LDRBBpre, LDRBBpost, LDRHHpre, LDRHHpost)>;
951
952def : InstRW<[THX3T110Write_5Cyc_LS01_I0123, WriteLDHi, WriteAdr],
953            (instrs LDPDpost, LDPQpost, LDPSpost, LDPWpost, LDPXpost)>;
954
955def : InstRW<[THX3T110Write_5Cyc_LS01_I0123, WriteI],
956            (instrs LDRBpost, LDRDpost, LDRHpost,
957                    LDRQpost, LDRSpost, LDRWpost, LDRXpost)>;
958
959def : InstRW<[THX3T110Write_4Cyc_LS01_I0123_I0123, WriteLDHi, WriteAdr],
960            (instrs LDPDpre, LDPQpre, LDPSpre, LDPWpre, LDPXpre)>;
961
962def : InstRW<[THX3T110Write_4Cyc_LS01_I0123_I0123, WriteAdr],
963            (instrs LDRBpre, LDRDpre, LDRHpre, LDRQpre,
964                    LDRSpre, LDRWpre, LDRXpre)>;
965
966def : InstRW<[THX3T110Write_4Cyc_LS01_I0123_I0123, WriteLDHi, WriteAdr],
967            (instrs LDPDpost, LDPQpost, LDPSpost, LDPWpost, LDPXpost)>;
968
969def : InstRW<[THX3T110Write_4Cyc_LS01_I0123_I0123, WriteI],
970            (instrs LDRBpost, LDRDpost, LDRHpost, LDRQpost,
971                    LDRSpost, LDRWpost, LDRXpost)>;
972
973def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRBroW)>;
974def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRDroW)>;
975def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRHroW)>;
976def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRHHroW)>;
977def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRQroW)>;
978def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRSroW)>;
979def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRSHWroW)>;
980def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRSHXroW)>;
981def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRWroW)>;
982def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRXroW)>;
983
984def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRBroX)>;
985def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRDroX)>;
986def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRHHroX)>;
987def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRHroX)>;
988def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRQroX)>;
989def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRSroX)>;
990def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRSHWroX)>;
991def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRSHXroX)>;
992def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRWroX)>;
993def : InstRW<[THX3T110Write_4Cyc_LS01_I0123, ReadAdrBase], (instrs LDRXroX)>;
994
995def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURBi)>;
996def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURBBi)>;
997def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURDi)>;
998def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURHi)>;
999def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURHHi)>;
1000def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURQi)>;
1001def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURSi)>;
1002def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURXi)>;
1003def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURSBWi)>;
1004def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURSBXi)>;
1005def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURSHWi)>;
1006def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURSHXi)>;
1007def : InstRW<[THX3T110Write_4Cyc_LS01], (instrs LDURSWi)>;
1008
1009// Load exclusive
1010def : InstRW<[THX3T110Write_4Cyc_LS01], (instregex "^LDAR(B|H|W|X)$")>;
1011def : InstRW<[THX3T110Write_4Cyc_LS01], (instregex "^LDAXR(B|H|W|X)$")>;
1012def : InstRW<[THX3T110Write_4Cyc_LS01], (instregex "^LDXR(B|H|W|X)$")>;
1013def : InstRW<[THX3T110Write_4Cyc_LS01], (instregex "^LDAXP(W|X)$")>;
1014def : InstRW<[THX3T110Write_4Cyc_LS01], (instregex "^LDXP(W|X)$")>;
1015
1016//---
1017// Prefetch
1018//---
1019def : InstRW<[THX3T110Write_6Cyc_LS01_I012], (instrs PRFMl)>;
1020def : InstRW<[THX3T110Write_6Cyc_LS01_I012], (instrs PRFUMi)>;
1021def : InstRW<[THX3T110Write_6Cyc_LS01_I012], (instrs PRFMui)>;
1022def : InstRW<[THX3T110Write_6Cyc_LS01_I012], (instrs PRFMroW)>;
1023def : InstRW<[THX3T110Write_6Cyc_LS01_I012], (instrs PRFMroX)>;
1024
1025//--
1026// 3.7 Store Instructions
1027// 3.11 FP Store Instructions
1028//--
1029
1030// Store register, unscaled immed
1031// Store register, immed unprivileged
1032// Store register, unsigned immed
1033def : WriteRes<WriteST,      [THX3T110LS, THX3T110SD]> {
1034  let Latency = 1;
1035  let NumMicroOps = 2;
1036}
1037
1038// Store register, immed post-index
1039// NOTE: Handled by WriteAdr, WriteST, ReadAdrBase
1040
1041// Store register, immed pre-index
1042// NOTE: Handled by WriteAdr, WriteST
1043
1044// Store register, register offset, basic
1045// Store register, register offset, scaled by 4/8
1046// Store register, register offset, scaled by 2
1047// Store register, register offset, extend
1048// Store register, register offset, extend, scale by 4/8
1049// Store register, register offset, extend, scale by 1
1050def : WriteRes<WriteSTIdx, [THX3T110LS, THX3T110SD, THX3T110I0123]> {
1051  let Latency = 1;
1052  let NumMicroOps = 2;
1053}
1054
1055// Store pair, immed offset, W-form
1056// Store pair, immed offset, X-form
1057def : WriteRes<WriteSTP,     [THX3T110LS, THX3T110SD]> {
1058  let Latency = 1;
1059  let NumMicroOps = 2;
1060}
1061
1062// Store pair, immed post-index, W-form
1063// Store pair, immed post-index, X-form
1064// Store pair, immed pre-index, W-form
1065// Store pair, immed pre-index, X-form
1066// NOTE: Handled by WriteAdr, WriteSTP.
1067def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STURBi)>;
1068def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STURBBi)>;
1069def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STURDi)>;
1070def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STURHi)>;
1071def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STURHHi)>;
1072def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STURQi)>;
1073def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STURSi)>;
1074def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STURWi)>;
1075def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STURXi)>;
1076
1077def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_SD], (instrs STTRBi)>;
1078def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_SD], (instrs STTRHi)>;
1079def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_SD], (instrs STTRWi)>;
1080def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_SD], (instrs STTRXi)>;
1081
1082def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STNPDi)>;
1083def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STNPQi)>;
1084def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STNPXi)>;
1085def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STNPWi)>;
1086
1087def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STPDi)>;
1088def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STPQi)>;
1089def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STPXi)>;
1090def : InstRW<[THX3T110Write_1Cyc_LS01_SD], (instrs STPWi)>;
1091
1092def : InstRW<[THX3T110Write_1Cyc_LS01_I0123], (instrs STRBui)>;
1093def : InstRW<[THX3T110Write_1Cyc_LS01_I0123], (instrs STRDui)>;
1094def : InstRW<[THX3T110Write_1Cyc_LS01_I0123], (instrs STRHui)>;
1095def : InstRW<[THX3T110Write_1Cyc_LS01_I0123], (instrs STRQui)>;
1096def : InstRW<[THX3T110Write_1Cyc_LS01_I0123], (instrs STRXui)>;
1097def : InstRW<[THX3T110Write_1Cyc_LS01_I0123], (instrs STRWui)>;
1098
1099def : InstRW<[WriteSTP, THX3T110Write_1Cyc_LS01_SD], (instrs STRBui)>;
1100def : InstRW<[WriteSTP, THX3T110Write_1Cyc_LS01_SD], (instrs STRDui)>;
1101def : InstRW<[WriteSTP, THX3T110Write_1Cyc_LS01_SD], (instrs STRHui)>;
1102def : InstRW<[WriteSTP, THX3T110Write_1Cyc_LS01_SD], (instrs STRQui)>;
1103def : InstRW<[WriteSTP, THX3T110Write_1Cyc_LS01_SD], (instrs STRXui)>;
1104def : InstRW<[WriteSTP, THX3T110Write_1Cyc_LS01_SD], (instrs STRWui)>;
1105
1106def : InstRW<[WriteSTIdx, THX3T110Write_1Cyc_LS01_SD_I0123], (instrs STRBui)>;
1107def : InstRW<[WriteSTIdx, THX3T110Write_1Cyc_LS01_SD_I0123], (instrs STRDui)>;
1108def : InstRW<[WriteSTIdx, THX3T110Write_1Cyc_LS01_SD_I0123], (instrs STRHui)>;
1109def : InstRW<[WriteSTIdx, THX3T110Write_1Cyc_LS01_SD_I0123], (instrs STRQui)>;
1110def : InstRW<[WriteSTIdx, THX3T110Write_1Cyc_LS01_SD_I0123], (instrs STRXui)>;
1111def : InstRW<[WriteSTIdx, THX3T110Write_1Cyc_LS01_SD_I0123], (instrs STRWui)>;
1112
1113def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1114            (instrs STPDpre, STPDpost)>;
1115def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1116            (instrs STPDpre, STPDpost)>;
1117def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1118            (instrs STPQpre, STPQpost)>;
1119def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1120            (instrs STPQpre, STPQpost)>;
1121def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1122            (instrs STPSpre, STPSpost)>;
1123def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1124            (instrs STPSpre, STPSpost)>;
1125def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1126            (instrs STPWpre, STPWpost)>;
1127def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1128            (instrs STPWpre, STPWpost)>;
1129def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1130            (instrs STPXpre, STPXpost)>;
1131def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1132            (instrs STPXpre, STPXpost)>;
1133def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1134            (instrs STRBpre, STRBpost)>;
1135def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1136            (instrs STRBpre, STRBpost)>;
1137def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1138            (instrs STRBBpre, STRBBpost)>;
1139def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1140            (instrs STRBBpre, STRBBpost)>;
1141def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1142            (instrs STRDpre, STRDpost)>;
1143def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1144            (instrs STRDpre, STRDpost)>;
1145def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1146            (instrs STRHpre, STRHpost)>;
1147def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1148            (instrs STRHpre, STRHpost)>;
1149def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1150            (instrs STRHHpre, STRHHpost)>;
1151def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1152            (instrs STRHHpre, STRHHpost)>;
1153def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1154            (instrs STRQpre, STRQpost)>;
1155def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1156            (instrs STRQpre, STRQpost)>;
1157def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1158            (instrs STRSpre, STRSpost)>;
1159def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1160            (instrs STRSpre, STRSpost)>;
1161def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1162            (instrs STRWpre, STRWpost)>;
1163def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1164            (instrs STRWpre, STRWpost)>;
1165def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123],
1166            (instrs STRXpre, STRXpost)>;
1167def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1168            (instrs STRXpre, STRXpost)>;
1169def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1170            (instrs STRBroW, STRBroX)>;
1171def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1172            (instrs STRBBroW, STRBBroX)>;
1173def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1174            (instrs STRDroW, STRDroX)>;
1175def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1176            (instrs STRHroW, STRHroX)>;
1177def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1178            (instrs STRHHroW, STRHHroX)>;
1179def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1180            (instrs STRQroW, STRQroX)>;
1181def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1182            (instrs STRSroW, STRSroX)>;
1183def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1184            (instrs STRWroW, STRWroX)>;
1185def : InstRW<[WriteAdr, THX3T110Write_1Cyc_LS01_I0123, ReadAdrBase],
1186            (instrs STRXroW, STRXroX)>;
1187
1188// Store exclusive
1189def : InstRW<[THX3T110Write_4Cyc_LS01_SD], (instrs STNPWi, STNPXi)>;
1190def : InstRW<[THX3T110Write_4Cyc_LS01_SD], (instregex "^STLR(B|H|W|X)$")>;
1191def : InstRW<[THX3T110Write_4Cyc_LS01_SD], (instregex "^STXP(W|X)$")>;
1192def : InstRW<[THX3T110Write_4Cyc_LS01_SD], (instregex "^STXR(B|H|W|X)$")>;
1193def : InstRW<[THX3T110Write_4Cyc_LS01_SD], (instregex "^STLXP(W|X)$")>;
1194def : InstRW<[THX3T110Write_4Cyc_LS01_SD], (instregex "^STLXR(B|H|W|X)$")>;
1195
1196//---
1197// 3.8 FP Data Processing Instructions
1198//---
1199
1200// FP absolute value
1201// FP min/max
1202// FP negate
1203def : WriteRes<WriteF,       [THX3T110FP0123]> {
1204  let Latency = 5;
1205  let NumMicroOps = 2;
1206}
1207
1208// FP arithmetic
1209def : InstRW<[THX3T110Write_6Cyc_F01], (instregex "^FADD", "^FSUB")>;
1210
1211// FP compare
1212def : WriteRes<WriteFCmp,    [THX3T110FP0123]> {
1213  let Latency = 5;
1214  let NumMicroOps = 2;
1215}
1216
1217// FP Mul, Div, Sqrt
1218def : WriteRes<WriteFDiv, [THX3T110FP0123]> {
1219  let Latency = 22;
1220  let ResourceCycles = [19];
1221}
1222
1223def THX3T110XWriteFDiv : SchedWriteRes<[THX3T110FP0123]> {
1224  let Latency = 16;
1225  let ResourceCycles = [8];
1226  let NumMicroOps = 4;
1227}
1228
1229def THX3T110XWriteFDivSP : SchedWriteRes<[THX3T110FP0123]> {
1230  let Latency = 16;
1231  let ResourceCycles = [8];
1232  let NumMicroOps = 4;
1233}
1234
1235def THX3T110XWriteFDivDP : SchedWriteRes<[THX3T110FP0123]> {
1236  let Latency = 23;
1237  let ResourceCycles = [12];
1238  let NumMicroOps = 4;
1239}
1240
1241def THX3T110XWriteFSqrtSP : SchedWriteRes<[THX3T110FP0123]> {
1242  let Latency = 16;
1243  let ResourceCycles = [8];
1244  let NumMicroOps = 4;
1245}
1246
1247def THX3T110XWriteFSqrtDP : SchedWriteRes<[THX3T110FP0123]> {
1248  let Latency = 23;
1249  let ResourceCycles = [12];
1250  let NumMicroOps = 4;
1251}
1252
1253// FP divide, S-form
1254// FP square root, S-form
1255def : InstRW<[THX3T110XWriteFDivSP], (instrs FDIVSrr)>;
1256def : InstRW<[THX3T110XWriteFSqrtSP], (instrs FSQRTSr)>;
1257def : InstRW<[THX3T110XWriteFDivSP], (instregex "^FDIVv.*32$")>;
1258def : InstRW<[THX3T110XWriteFSqrtSP], (instregex "^.*SQRT.*32$")>;
1259def : InstRW<[THX3T110Write_16Cyc_F01], (instregex "^FDIVSrr", "^FSQRTSr")>;
1260
1261// FP divide, D-form
1262// FP square root, D-form
1263def : InstRW<[THX3T110XWriteFDivDP], (instrs FDIVDrr)>;
1264def : InstRW<[THX3T110XWriteFSqrtDP], (instrs FSQRTDr)>;
1265def : InstRW<[THX3T110XWriteFDivDP], (instregex "^FDIVv.*64$")>;
1266def : InstRW<[THX3T110XWriteFSqrtDP], (instregex "^.*SQRT.*64$")>;
1267def : InstRW<[THX3T110Write_23Cyc_F01], (instregex "^FDIVDrr", "^FSQRTDr")>;
1268
1269// FP multiply
1270// FP multiply accumulate
1271def : WriteRes<WriteFMul, [THX3T110FP0123]> {
1272  let Latency = 6;
1273  let ResourceCycles = [2];
1274  let NumMicroOps = 3;
1275}
1276
1277def THX3T110XWriteFMul : SchedWriteRes<[THX3T110FP0123]> {
1278  let Latency = 6;
1279  let ResourceCycles = [2];
1280  let NumMicroOps = 3;
1281}
1282
1283def THX3T110XWriteFMulAcc : SchedWriteRes<[THX3T110FP0123]> {
1284  let Latency = 6;
1285  let ResourceCycles = [2];
1286  let NumMicroOps = 3;
1287}
1288
1289def : InstRW<[THX3T110XWriteFMul], (instregex "^FMUL", "^FNMUL")>;
1290def : InstRW<[THX3T110XWriteFMulAcc],
1291            (instregex "^FMADD", "^FMSUB", "^FNMADD", "^FNMSUB")>;
1292
1293// FP round to integral
1294def : InstRW<[THX3T110Write_7Cyc_F01],
1295            (instregex "^FRINT(A|I|M|N|P|X|Z)(Sr|Dr)")>;
1296
1297// FP select
1298def : InstRW<[THX3T110Write_3_4Cyc_F23_F0123], (instregex "^FCSEL")>;
1299
1300//---
1301// 3.9 FP Miscellaneous Instructions
1302//---
1303
1304// FP convert, from vec to vec reg
1305// FP convert, from gen to vec reg
1306// FP convert, from vec to gen reg
1307def : WriteRes<WriteFCvt, [THX3T110FP0123]> {
1308  let Latency = 7;
1309  let NumMicroOps = 3;
1310}
1311
1312// FP move, immed
1313// FP move, register
1314def : WriteRes<WriteFImm, [THX3T110FP0123]> {
1315  let Latency = 4;
1316  let NumMicroOps = 2;
1317}
1318
1319// FP transfer, from gen to vec reg
1320// FP transfer, from vec to gen reg
1321def : WriteRes<WriteFCopy, [THX3T110FP0123]> {
1322  let Latency = 4;
1323  let NumMicroOps = 2;
1324}
1325
1326def : InstRW<[THX3T110Write_5Cyc_F01], (instrs FMOVXDHighr, FMOVDXHighr)>;
1327
1328//---
1329// 3.12 ASIMD Integer Instructions
1330//---
1331
1332// ASIMD absolute diff, D-form
1333// ASIMD absolute diff, Q-form
1334// ASIMD absolute diff accum, D-form
1335// ASIMD absolute diff accum, Q-form
1336// ASIMD absolute diff accum long
1337// ASIMD absolute diff long
1338// ASIMD arith, basic
1339// ASIMD arith, complex
1340// ASIMD compare
1341// ASIMD logical (AND, BIC, EOR)
1342// ASIMD max/min, basic
1343// ASIMD max/min, reduce, 4H/4S
1344// ASIMD max/min, reduce, 8B/8H
1345// ASIMD max/min, reduce, 16B
1346// ASIMD multiply, D-form
1347// ASIMD multiply, Q-form
1348// ASIMD multiply accumulate long
1349// ASIMD multiply accumulate saturating long
1350// ASIMD multiply long
1351// ASIMD pairwise add and accumulate
1352// ASIMD shift accumulate
1353// ASIMD shift by immed, basic
1354// ASIMD shift by immed and insert, basic, D-form
1355// ASIMD shift by immed and insert, basic, Q-form
1356// ASIMD shift by immed, complex
1357// ASIMD shift by register, basic, D-form
1358// ASIMD shift by register, basic, Q-form
1359// ASIMD shift by register, complex, D-form
1360// ASIMD shift by register, complex, Q-form
1361def : WriteRes<WriteVd, [THX3T110FP0123]> {
1362  let Latency = 5;
1363  let NumMicroOps = 4;
1364  let ResourceCycles = [4];
1365}
1366def : WriteRes<WriteVq, [THX3T110FP0123]> {
1367  let Latency = 5;
1368  let NumMicroOps = 4;
1369  let ResourceCycles = [4];
1370}
1371
1372// ASIMD arith, reduce, 4H/4S
1373// ASIMD arith, reduce, 8B/8H
1374// ASIMD arith, reduce, 16B
1375
1376// ASIMD logical (MVN (alias for NOT), ORN, ORR)
1377def : InstRW<[THX3T110Write_5Cyc_F0123],
1378            (instregex "^ANDv", "^BICv", "^EORv", "^ORRv", "^ORNv", "^NOTv")>;
1379
1380// ASIMD arith, reduce
1381def : InstRW<[THX3T110Write_5Cyc_F0123],
1382            (instregex "^ADDVv", "^SADDLVv", "^UADDLVv")>;
1383
1384// ASIMD polynomial (8x8) multiply long
1385def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^(S|U|SQD)MULL")>;
1386def : InstRW<[THX3T110Write_5Cyc_F0123],
1387            (instregex "(S|U|SQD)(MLAL|MLSL|MULL)v.*")>;
1388def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^PMULL(v8i8|v16i8)")>;
1389def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^PMULL(v1i64|v2i64)")>;
1390
1391// ASIMD absolute diff accum, D-form
1392def : InstRW<[THX3T110Write_5Cyc_F0123],
1393            (instregex "^[SU]ABA(v8i8|v4i16|v2i32)$")>;
1394// ASIMD absolute diff accum, Q-form
1395def : InstRW<[THX3T110Write_5Cyc_F0123],
1396            (instregex "^[SU]ABA(v16i8|v8i16|v4i32)$")>;
1397// ASIMD absolute diff accum long
1398def : InstRW<[THX3T110Write_5Cyc_F0123],
1399            (instregex "^[SU]ABAL")>;
1400// ASIMD arith, reduce, 4H/4S
1401def : InstRW<[THX3T110Write_5Cyc_F0123],
1402            (instregex "^[SU]?ADDL?V(v8i8|v4i16|v2i32)v$")>;
1403// ASIMD arith, reduce, 8B
1404def : InstRW<[THX3T110Write_5Cyc_F0123],
1405            (instregex "^[SU]?ADDL?V(v8i16|v4i32)v$")>;
1406// ASIMD arith, reduce, 16B/16H
1407def : InstRW<[THX3T110Write_10Cyc_F0123],
1408            (instregex "^[SU]?ADDL?Vv16i8v$")>;
1409// ASIMD max/min, reduce, 4H/4S
1410def : InstRW<[THX3T110Write_5Cyc_F0123],
1411            (instregex "^[SU](MIN|MAX)V(v4i16|v4i32)v$")>;
1412// ASIMD max/min, reduce, 8B/8H
1413def : InstRW<[THX3T110Write_5Cyc_F0123],
1414            (instregex "^[SU](MIN|MAX)V(v8i8|v8i16)v$")>;
1415// ASIMD max/min, reduce, 16B/16H
1416def : InstRW<[THX3T110Write_5Cyc_F0123],
1417            (instregex "^[SU](MIN|MAX)Vv16i8v$")>;
1418// ASIMD multiply, D-form
1419def : InstRW<[THX3T110Write_5Cyc_F0123],
1420            (instregex "^(P?MUL|SQR?DMULH)" #
1421                       "(v8i8|v4i16|v2i32|v1i8|v1i16|v1i32|v1i64)" #
1422                       "(_indexed)?$")>;
1423// ASIMD multiply, Q-form
1424def : InstRW<[THX3T110Write_5Cyc_F0123],
1425            (instregex "^(P?MUL|SQR?DMULH)(v16i8|v8i16|v4i32)(_indexed)?$")>;
1426// ASIMD multiply accumulate, D-form
1427def : InstRW<[THX3T110Write_5Cyc_F0123],
1428            (instregex "^ML[AS](v8i8|v4i16|v2i32)(_indexed)?$")>;
1429// ASIMD multiply accumulate, Q-form
1430def : InstRW<[THX3T110Write_5Cyc_F0123],
1431            (instregex "^ML[AS](v16i8|v8i16|v4i32)(_indexed)?$")>;
1432// ASIMD shift accumulate
1433def : InstRW<[THX3T110Write_5Cyc_F0123],
1434            (instregex "SRSRAv","SSRAv","URSRAv","USRAv")>;
1435
1436// ASIMD shift by immed, basic
1437def : InstRW<[THX3T110Write_5Cyc_F0123],
1438            (instregex "RSHRNv","SHRNv", "SQRSHRNv","SQRSHRUNv",
1439                       "SQSHRNv","SQSHRUNv", "UQRSHRNv",
1440                       "UQSHRNv","SQXTNv","SQXTUNv","UQXTNv")>;
1441// ASIMD shift by immed, complex
1442def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^[SU]?(Q|R){1,2}SHR")>;
1443def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^SQSHLU")>;
1444// ASIMD shift by register, basic, Q-form
1445def : InstRW<[THX3T110Write_5Cyc_F01],
1446            (instregex "^[SU]SHL(v16i8|v8i16|v4i32|v2i64)")>;
1447// ASIMD shift by register, complex, D-form
1448def : InstRW<[THX3T110Write_5Cyc_F0123],
1449            (instregex "^[SU][QR]{1,2}SHL" #
1450                       "(v1i8|v1i16|v1i32|v1i64|v8i8|v4i16|v2i32|b|d|h|s)")>;
1451// ASIMD shift by register, complex, Q-form
1452def : InstRW<[THX3T110Write_5Cyc_F0123],
1453            (instregex "^[SU][QR]{1,2}SHL(v16i8|v8i16|v4i32|v2i64)")>;
1454
1455// ASIMD Arithmetic
1456def : InstRW<[THX3T110Write_5Cyc_F0123],
1457            (instregex "(ADD|SUB)(v8i8|v4i16|v2i32|v1i64)")>;
1458def : InstRW<[THX3T110Write_5Cyc_F0123],
1459            (instregex "(ADD|SUB)(v16i8|v8i16|v4i32|v2i64)")>;
1460def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "(ADD|SUB)HNv.*")>;
1461def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "(RADD|RSUB)HNv.*")>;
1462def : InstRW<[THX3T110Write_5Cyc_F0123],
1463            (instregex "^SQADD", "^SQNEG", "^SQSUB", "^SRHADD",
1464                       "^SUQADD", "^UQADD", "^UQSUB", "^URHADD", "^USQADD")>;
1465def : InstRW<[THX3T110Write_5Cyc_F0123],
1466            (instregex "ADDP(v16i8|v8i16|v4i32|v2i64)")>;
1467def : InstRW<[THX3T110Write_5Cyc_F0123],
1468            (instregex "((AND|ORN|EOR|EON)S?(Xr[rsi]|v16i8|v8i16|v4i32)|" #
1469                       "(ORR|BIC)S?(Xr[rs]|v16i8|v8i16|v4i32))")>;
1470def : InstRW<[THX3T110Write_5Cyc_F0123],
1471            (instregex "(CLS|CLZ|CNT)(v4i32|v8i16|v16i8)")>;
1472def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^SADALP","^UADALP")>;
1473def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^SADDLPv","^UADDLPv")>;
1474def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^SADDLV","^UADDLV")>;
1475def : InstRW<[THX3T110Write_5Cyc_F0123],
1476             (instregex "^ADDVv","^SMAXVv","^UMAXVv","^SMINVv","^UMINVv")>;
1477def : InstRW<[THX3T110Write_5Cyc_F0123],
1478             (instregex "^SABAv","^UABAv","^SABALv","^UABALv")>;
1479def : InstRW<[THX3T110Write_5Cyc_F0123],
1480            (instregex "^SQADDv","^SQSUBv","^UQADDv","^UQSUBv")>;
1481def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^SUQADDv","^USQADDv")>;
1482def : InstRW<[THX3T110Write_5Cyc_F0123],
1483            (instregex "^ADDHNv","^RADDHNv", "^RSUBHNv",
1484                       "^SQABS", "^SQADD", "^SQNEG", "^SQSUB",
1485                       "^SRHADD", "^SUBHNv", "^SUQADD",
1486                       "^UQADD", "^UQSUB", "^URHADD", "^USQADD")>;
1487def : InstRW<[THX3T110Write_5Cyc_F0123],
1488            (instregex "^CMEQv","^CMGEv","^CMGTv",
1489                       "^CMLEv","^CMLTv", "^CMHIv","^CMHSv")>;
1490def : InstRW<[THX3T110Write_5Cyc_F0123],
1491            (instregex "^SMAXv","^SMINv","^UMAXv","^UMINv",
1492                       "^SMAXPv","^SMINPv","^UMAXPv","^UMINPv")>;
1493def : InstRW<[THX3T110Write_5Cyc_F0123],
1494            (instregex "^SABDv","^UABDv", "^SABDLv","^UABDLv")>;
1495
1496//---
1497// 3.13 ASIMD Floating-point Instructions
1498//---
1499
1500// ASIMD FP absolute value
1501def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^FABSv")>;
1502
1503// ASIMD FP arith, normal, D-form
1504// ASIMD FP arith, normal, Q-form
1505def : InstRW<[THX3T110Write_3_4Cyc_F23_F0123],
1506            (instregex "^FABDv", "^FADDv", "^FSUBv")>;
1507
1508// ASIMD FP arith,pairwise, D-form
1509// ASIMD FP arith, pairwise, Q-form
1510def : InstRW<[THX3T110Write_3_4Cyc_F23_F0123], (instregex "^FADDPv")>;
1511
1512// ASIMD FP compare, D-form
1513// ASIMD FP compare, Q-form
1514def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^FACGEv", "^FACGTv")>;
1515def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^FCMEQv", "^FCMGEv",
1516                                                 "^FCMGTv", "^FCMLEv",
1517                                                 "^FCMLTv")>;
1518
1519// ASIMD FP round, D-form
1520def : InstRW<[THX3T110Write_5Cyc_F0123],
1521            (instregex "^FRINT[AIMNPXZ](v2f32)")>;
1522// ASIMD FP round, Q-form
1523def : InstRW<[THX3T110Write_5Cyc_F0123],
1524            (instregex "^FRINT[AIMNPXZ](v4f32|v2f64)")>;
1525
1526// ASIMD FP convert, long
1527// ASIMD FP convert, narrow
1528// ASIMD FP convert, other, D-form
1529// ASIMD FP convert, other, Q-form
1530// NOTE: Handled by WriteV.
1531
1532// ASIMD FP convert, long and narrow
1533def : InstRW<[THX3T110Write_5Cyc_F01], (instregex "^FCVT(L|N|XN)v")>;
1534// ASIMD FP convert, other, D-form
1535def : InstRW<[THX3T110Write_5Cyc_F01],
1536      (instregex "^[FVSU]CVT([AMNPZ][SU])?(_Int)?(v2f32|v1i32|v2i32|v1i64)")>;
1537// ASIMD FP convert, other, Q-form
1538def : InstRW<[THX3T110Write_5Cyc_F01],
1539      (instregex "^[FVSU]CVT([AMNPZ][SU])?(_Int)?(v4f32|v2f64|v4i32|v2i64)")>;
1540
1541// ASIMD FP divide, D-form, F32
1542def : InstRW<[THX3T110Write_16Cyc_F0123], (instrs FDIVv2f32)>;
1543def : InstRW<[THX3T110Write_16Cyc_F0123], (instregex "FDIVv2f32")>;
1544
1545// ASIMD FP divide, Q-form, F32
1546def : InstRW<[THX3T110Write_16Cyc_F0123], (instrs FDIVv4f32)>;
1547def : InstRW<[THX3T110Write_16Cyc_F0123], (instregex "FDIVv4f32")>;
1548
1549// ASIMD FP divide, Q-form, F64
1550def : InstRW<[THX3T110Write_23Cyc_F0123], (instrs FDIVv2f64)>;
1551def : InstRW<[THX3T110Write_23Cyc_F0123], (instregex "FDIVv2f64")>;
1552
1553// ASIMD FP max/min, normal, D-form
1554// ASIMD FP max/min, normal, Q-form
1555def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^FMAXv", "^FMAXNMv",
1556                                                "^FMINv", "^FMINNMv")>;
1557
1558// ASIMD FP max/min, pairwise, D-form
1559// ASIMD FP max/min, pairwise, Q-form
1560def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^FMAXPv", "^FMAXNMPv",
1561                                                "^FMINPv", "^FMINNMPv")>;
1562
1563// ASIMD FP max/min, reduce
1564def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^FMAXVv", "^FMAXNMVv",
1565                                                "^FMINVv", "^FMINNMVv")>;
1566
1567// ASIMD FP multiply, D-form, FZ
1568// ASIMD FP multiply, D-form, no FZ
1569// ASIMD FP multiply, Q-form, FZ
1570// ASIMD FP multiply, Q-form, no FZ
1571def : InstRW<[THX3T110Write_5Cyc_F0123],
1572            (instregex "^FMULv", "^FMULXv")>;
1573def : InstRW<[THX3T110Write_5Cyc_F0123],
1574            (instregex "^FMULX?(v2f32|v1i32|v2i32|v1i64|32|64)")>;
1575def : InstRW<[THX3T110Write_5Cyc_F0123],
1576            (instregex "^FMULX?(v4f32|v2f64|v4i32|v2i64)")>;
1577
1578// ASIMD FP multiply accumulate, Dform, FZ
1579// ASIMD FP multiply accumulate, Dform, no FZ
1580// ASIMD FP multiply accumulate, Qform, FZ
1581// ASIMD FP multiply accumulate, Qform, no FZ
1582def : InstRW<[THX3T110Write_5Cyc_F0123],
1583            (instregex "^FMLAv", "^FMLSv")>;
1584def : InstRW<[THX3T110Write_5Cyc_F0123],
1585            (instregex "^FML[AS](v2f32|v1i32|v2i32|v1i64)")>;
1586def : InstRW<[THX3T110Write_5Cyc_F0123],
1587            (instregex "^FML[AS](v4f32|v2f64|v4i32|v2i64)")>;
1588
1589// ASIMD FP negate
1590def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^FNEGv")>;
1591
1592//--
1593// 3.14 ASIMD Miscellaneous Instructions
1594//--
1595
1596// ASIMD bit reverse
1597def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^RBITv")>;
1598
1599// ASIMD bitwise insert, D-form
1600// ASIMD bitwise insert, Q-form
1601def : InstRW<[THX3T110Write_3_4Cyc_F23_F0123],
1602            (instregex "^BIFv", "^BITv", "^BSLv")>;
1603
1604// ASIMD count, D-form
1605// ASIMD count, Q-form
1606def : InstRW<[THX3T110Write_3_4Cyc_F23_F0123],
1607            (instregex "^CLSv", "^CLZv", "^CNTv")>;
1608
1609// ASIMD duplicate, gen reg
1610// ASIMD duplicate, element
1611def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^DUPv")>;
1612def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^DUP(i8|i16|i32|i64)$")>;
1613def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^DUPv.+gpr")>;
1614
1615// ASIMD extract
1616def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^EXTv")>;
1617
1618// ASIMD extract narrow
1619def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^XTNv")>;
1620
1621// ASIMD extract narrow, saturating
1622def : InstRW<[THX3T110Write_5Cyc_F0123],
1623            (instregex "^SQXTNv", "^SQXTUNv", "^UQXTNv")>;
1624
1625// ASIMD insert, element to element
1626def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^INSv")>;
1627
1628// ASIMD transfer, element to gen reg
1629def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^[SU]MOVv")>;
1630
1631// ASIMD move, integer immed
1632def : InstRW<[THX3T110Write_3_4Cyc_F23_F0123], (instregex "^MOVIv")>;
1633
1634// ASIMD move, FP immed
1635def : InstRW<[THX3T110Write_3_4Cyc_F23_F0123], (instregex "^FMOVv")>;
1636
1637// ASIMD transpose
1638def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^TRN1", "^TRN2")>;
1639
1640// ASIMD unzip/zip
1641def : InstRW<[THX3T110Write_5Cyc_F0123],
1642            (instregex "^UZP1", "^UZP2", "^ZIP1", "^ZIP2")>;
1643
1644// ASIMD reciprocal estimate, D-form
1645// ASIMD reciprocal estimate, Q-form
1646def : InstRW<[THX3T110Write_5Cyc_F0123],
1647            (instregex "^FRECPEv", "^FRECPXv", "^URECPEv",
1648                       "^FRSQRTEv", "^URSQRTEv")>;
1649
1650// ASIMD reciprocal step, D-form, FZ
1651// ASIMD reciprocal step, D-form, no FZ
1652// ASIMD reciprocal step, Q-form, FZ
1653// ASIMD reciprocal step, Q-form, no FZ
1654def : InstRW<[THX3T110Write_5Cyc_F0123],
1655              (instregex "^FRECPSv", "^FRSQRTSv")>;
1656
1657// ASIMD reverse
1658def : InstRW<[THX3T110Write_5Cyc_F0123],
1659            (instregex "^REV16v", "^REV32v", "^REV64v")>;
1660
1661// ASIMD table lookup, D-form
1662// ASIMD table lookup, Q-form
1663def : InstRW<[THX3T110Write_5Cyc_F0123],
1664            (instrs TBLv8i8One, TBLv16i8One, TBXv8i8One, TBXv16i8One)>;
1665def : InstRW<[THX3T110Write_10Cyc_F0123],
1666            (instrs TBLv8i8Two, TBLv16i8Two, TBXv8i8Two, TBXv16i8Two)>;
1667def : InstRW<[THX3T110Write_15Cyc_F0123],
1668            (instrs TBLv8i8Three, TBLv16i8Three, TBXv8i8Three, TBXv16i8Three)>;
1669def : InstRW<[THX3T110Write_20Cyc_F0123],
1670            (instrs TBLv8i8Four, TBLv16i8Four, TBXv8i8Four, TBXv16i8Four)>;
1671
1672// ASIMD transfer, element to word or word
1673def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^[SU]MOVv")>;
1674
1675// ASIMD transfer, element to gen reg
1676def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "(S|U)MOVv.*")>;
1677
1678// ASIMD transfer gen reg to element
1679def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^INSv")>;
1680
1681// ASIMD transpose
1682def : InstRW<[THX3T110Write_5Cyc_F0123],
1683              (instregex "^TRN1v", "^TRN2v", "^UZP1v", "^UZP2v")>;
1684
1685// ASIMD unzip/zip
1686def : InstRW<[THX3T110Write_5Cyc_F0123], (instregex "^ZIP1v", "^ZIP2v")>;
1687
1688//--
1689// 3.15 ASIMD Load Instructions
1690//--
1691
1692// ASIMD load, 1 element, multiple, 1 reg, D-form
1693// ASIMD load, 1 element, multiple, 1 reg, Q-form
1694def : InstRW<[THX3T110Write_4Cyc_LS01],
1695            (instregex "^LD1Onev(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1696def : InstRW<[THX3T110Write_4Cyc_LS01, WriteAdr],
1697            (instregex "^LD1Onev(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1698
1699// ASIMD load, 1 element, multiple, 2 reg, D-form
1700// ASIMD load, 1 element, multiple, 2 reg, Q-form
1701def : InstRW<[THX3T110Write_4Cyc_LS01],
1702            (instregex "^LD1Twov(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1703def : InstRW<[THX3T110Write_4Cyc_LS01, WriteAdr],
1704            (instregex "^LD1Twov(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1705
1706// ASIMD load, 1 element, multiple, 3 reg, D-form
1707// ASIMD load, 1 element, multiple, 3 reg, Q-form
1708def : InstRW<[THX3T110Write_5Cyc_LS01],
1709            (instregex "^LD1Threev(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1710def : InstRW<[THX3T110Write_5Cyc_LS01, WriteAdr],
1711            (instregex "^LD1Threev(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1712
1713// ASIMD load, 1 element, multiple, 4 reg, D-form
1714// ASIMD load, 1 element, multiple, 4 reg, Q-form
1715def : InstRW<[THX3T110Write_6Cyc_LS01],
1716            (instregex "^LD1Fourv(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1717def : InstRW<[THX3T110Write_6Cyc_LS01, WriteAdr],
1718            (instregex "^LD1Fourv(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1719
1720// ASIMD load, 1 element, one lane, B/H/S
1721// ASIMD load, 1 element, one lane, D
1722def : InstRW<[THX3T110Write_5Cyc_LS01_F0123],
1723            (instregex "^LD1i(8|16|32|64)$")>;
1724def : InstRW<[THX3T110Write_5Cyc_LS01_F0123, WriteAdr],
1725            (instregex "^LD1i(8|16|32|64)_POST$")>;
1726
1727// ASIMD load, 1 element, all lanes, D-form, B/H/S
1728// ASIMD load, 1 element, all lanes, D-form, D
1729// ASIMD load, 1 element, all lanes, Q-form
1730def : InstRW<[THX3T110Write_5Cyc_LS01_F0123],
1731            (instregex "^LD1Rv(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1732def : InstRW<[THX3T110Write_5Cyc_LS01_F0123, WriteAdr],
1733            (instregex "^LD1Rv(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1734
1735// ASIMD load, 2 element, multiple, D-form, B/H/S
1736// ASIMD load, 2 element, multiple, Q-form, D
1737def : InstRW<[THX3T110Write_5Cyc_LS01_F0123],
1738            (instregex "^LD2Twov(8b|4h|2s|16b|8h|4s|2d)$")>;
1739def : InstRW<[THX3T110Write_5Cyc_LS01_F0123, WriteAdr],
1740            (instregex "^LD2Twov(8b|4h|2s|16b|8h|4s|2d)_POST$")>;
1741
1742// ASIMD load, 2 element, one lane, B/H
1743// ASIMD load, 2 element, one lane, S
1744// ASIMD load, 2 element, one lane, D
1745def : InstRW<[THX3T110Write_5Cyc_LS01_F0123],
1746            (instregex "^LD2i(8|16|32|64)$")>;
1747def : InstRW<[THX3T110Write_5Cyc_LS01_F0123, WriteAdr],
1748            (instregex "^LD2i(8|16|32|64)_POST$")>;
1749
1750// ASIMD load, 2 element, all lanes, D-form, B/H/S
1751// ASIMD load, 2 element, all lanes, D-form, D
1752// ASIMD load, 2 element, all lanes, Q-form
1753def : InstRW<[THX3T110Write_5Cyc_LS01_F0123],
1754            (instregex "^LD2Rv(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1755def : InstRW<[THX3T110Write_5Cyc_LS01_F0123, WriteAdr],
1756            (instregex "^LD2Rv(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1757
1758// ASIMD load, 3 element, multiple, D-form, B/H/S
1759// ASIMD load, 3 element, multiple, Q-form, B/H/S
1760// ASIMD load, 3 element, multiple, Q-form, D
1761def : InstRW<[THX3T110Write_8Cyc_LS01_F0123],
1762            (instregex "^LD3Threev(8b|4h|2s|16b|8h|4s|2d)$")>;
1763def : InstRW<[THX3T110Write_8Cyc_LS01_F0123, WriteAdr],
1764            (instregex "^LD3Threev(8b|4h|2s|16b|8h|4s|2d)_POST$")>;
1765
1766// ASIMD load, 3 element, one lone, B/H
1767// ASIMD load, 3 element, one lane, S
1768// ASIMD load, 3 element, one lane, D
1769def : InstRW<[THX3T110Write_7Cyc_LS01_F0123],
1770            (instregex "^LD3i(8|16|32|64)$")>;
1771def : InstRW<[THX3T110Write_7Cyc_LS01_F0123, WriteAdr],
1772            (instregex "^LD3i(8|16|32|64)_POST$")>;
1773
1774// ASIMD load, 3 element, all lanes, D-form, B/H/S
1775// ASIMD load, 3 element, all lanes, D-form, D
1776// ASIMD load, 3 element, all lanes, Q-form, B/H/S
1777// ASIMD load, 3 element, all lanes, Q-form, D
1778def : InstRW<[THX3T110Write_7Cyc_LS01_F0123],
1779            (instregex "^LD3Rv(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1780def : InstRW<[THX3T110Write_7Cyc_LS01_F0123, WriteAdr],
1781            (instregex "^LD3Rv(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1782
1783// ASIMD load, 4 element, multiple, D-form, B/H/S
1784// ASIMD load, 4 element, multiple, Q-form, B/H/S
1785// ASIMD load, 4 element, multiple, Q-form, D
1786def : InstRW<[THX3T110Write_8Cyc_LS01_F0123],
1787            (instregex "^LD4Fourv(8b|4h|2s|16b|8h|4s|2d)$")>;
1788def : InstRW<[THX3T110Write_8Cyc_LS01_F0123, WriteAdr],
1789            (instregex "^LD4Fourv(8b|4h|2s|16b|8h|4s|2d)_POST$")>;
1790
1791// ASIMD load, 4 element, one lane, B/H
1792// ASIMD load, 4 element, one lane, S
1793// ASIMD load, 4 element, one lane, D
1794def : InstRW<[THX3T110Write_6Cyc_LS01_F0123],
1795            (instregex "^LD4i(8|16|32|64)$")>;
1796def : InstRW<[THX3T110Write_6Cyc_LS01_F0123, WriteAdr],
1797            (instregex "^LD4i(8|16|32|64)_POST$")>;
1798
1799// ASIMD load, 4 element, all lanes, D-form, B/H/S
1800// ASIMD load, 4 element, all lanes, D-form, D
1801// ASIMD load, 4 element, all lanes, Q-form, B/H/S
1802// ASIMD load, 4 element, all lanes, Q-form, D
1803def : InstRW<[THX3T110Write_6Cyc_LS01_F0123],
1804            (instregex "^LD4Rv(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1805def : InstRW<[THX3T110Write_6Cyc_LS01_F0123, WriteAdr],
1806            (instregex "^LD4Rv(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1807
1808//--
1809// 3.16 ASIMD Store Instructions
1810//--
1811
1812// ASIMD store, 1 element, multiple, 1 reg, D-form
1813// ASIMD store, 1 element, multiple, 1 reg, Q-form
1814def : InstRW<[THX3T110Write_1Cyc_LS01],
1815            (instregex "^ST1Onev(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1816def : InstRW<[THX3T110Write_1Cyc_LS01, WriteAdr],
1817            (instregex "^ST1Onev(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1818
1819// ASIMD store, 1 element, multiple, 2 reg, D-form
1820// ASIMD store, 1 element, multiple, 2 reg, Q-form
1821def : InstRW<[THX3T110Write_1Cyc_LS01],
1822            (instregex "^ST1Twov(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1823def : InstRW<[THX3T110Write_1Cyc_LS01, WriteAdr],
1824            (instregex "^ST1Twov(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1825
1826// ASIMD store, 1 element, multiple, 3 reg, D-form
1827// ASIMD store, 1 element, multiple, 3 reg, Q-form
1828def : InstRW<[THX3T110Write_1Cyc_LS01],
1829            (instregex "^ST1Threev(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1830def : InstRW<[THX3T110Write_1Cyc_LS01, WriteAdr],
1831            (instregex "^ST1Threev(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1832
1833// ASIMD store, 1 element, multiple, 4 reg, D-form
1834// ASIMD store, 1 element, multiple, 4 reg, Q-form
1835def : InstRW<[THX3T110Write_1Cyc_LS01],
1836            (instregex "^ST1Fourv(8b|4h|2s|1d|16b|8h|4s|2d)$")>;
1837def : InstRW<[THX3T110Write_1Cyc_LS01, WriteAdr],
1838            (instregex "^ST1Fourv(8b|4h|2s|1d|16b|8h|4s|2d)_POST$")>;
1839
1840// ASIMD store, 1 element, one lane, B/H/S
1841// ASIMD store, 1 element, one lane, D
1842def : InstRW<[THX3T110Write_1Cyc_LS01_F0123],
1843            (instregex "^ST1i(8|16|32|64)$")>;
1844def : InstRW<[THX3T110Write_1Cyc_LS01_F0123, WriteAdr],
1845            (instregex "^ST1i(8|16|32|64)_POST$")>;
1846
1847// ASIMD store, 2 element, multiple, D-form, B/H/S
1848// ASIMD store, 2 element, multiple, Q-form, B/H/S
1849// ASIMD store, 2 element, multiple, Q-form, D
1850def : InstRW<[THX3T110Write_1Cyc_LS01_F0123],
1851            (instregex "^ST2Twov(8b|4h|2s|16b|8h|4s|2d)$")>;
1852def : InstRW<[THX3T110Write_1Cyc_LS01_F0123, WriteAdr],
1853            (instregex "^ST2Twov(8b|4h|2s|16b|8h|4s|2d)_POST$")>;
1854
1855// ASIMD store, 2 element, one lane, B/H/S
1856// ASIMD store, 2 element, one lane, D
1857def : InstRW<[THX3T110Write_1Cyc_LS01_F0123],
1858            (instregex "^ST2i(8|16|32|64)$")>;
1859def : InstRW<[THX3T110Write_1Cyc_LS01_F0123, WriteAdr],
1860            (instregex "^ST2i(8|16|32|64)_POST$")>;
1861
1862// ASIMD store, 3 element, multiple, D-form, B/H/S
1863// ASIMD store, 3 element, multiple, Q-form, B/H/S
1864// ASIMD store, 3 element, multiple, Q-form, D
1865def : InstRW<[THX3T110Write_1Cyc_LS01_F0123],
1866            (instregex "^ST3Threev(8b|4h|2s|16b|8h|4s|2d)$")>;
1867def : InstRW<[THX3T110Write_1Cyc_LS01_F0123, WriteAdr],
1868            (instregex "^ST3Threev(8b|4h|2s|16b|8h|4s|2d)_POST$")>;
1869
1870// ASIMD store, 3 element, one lane, B/H
1871// ASIMD store, 3 element, one lane, S
1872// ASIMD store, 3 element, one lane, D
1873def : InstRW<[THX3T110Write_1Cyc_LS01_F0123],
1874            (instregex "^ST3i(8|16|32|64)$")>;
1875def : InstRW<[THX3T110Write_1Cyc_LS01_F0123, WriteAdr],
1876            (instregex "^ST3i(8|16|32|64)_POST$")>;
1877
1878// ASIMD store, 4 element, multiple, D-form, B/H/S
1879// ASIMD store, 4 element, multiple, Q-form, B/H/S
1880// ASIMD store, 4 element, multiple, Q-form, D
1881def : InstRW<[THX3T110Write_1Cyc_LS01_F0123],
1882            (instregex "^ST4Fourv(8b|4h|2s|16b|8h|4s|2d)$")>;
1883def : InstRW<[THX3T110Write_1Cyc_LS01_F0123, WriteAdr],
1884            (instregex "^ST4Fourv(8b|4h|2s|16b|8h|4s|2d)_POST$")>;
1885
1886// ASIMD store, 4 element, one lane, B/H
1887// ASIMD store, 4 element, one lane, S
1888// ASIMD store, 4 element, one lane, D
1889def : InstRW<[THX3T110Write_1Cyc_LS01_F0123],
1890            (instregex "^ST4i(8|16|32|64)$")>;
1891def : InstRW<[THX3T110Write_1Cyc_LS01_F0123, WriteAdr],
1892            (instregex "^ST4i(8|16|32|64)_POST$")>;
1893
1894// V8.1a Atomics (LSE)
1895def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1896            (instrs CASB, CASH, CASW, CASX)>;
1897
1898def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1899            (instrs CASAB, CASAH, CASAW, CASAX)>;
1900
1901def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1902            (instrs CASLB, CASLH, CASLW, CASLX)>;
1903
1904def : InstRW<[THX3T110Write_8Cyc_I0123, WriteAtomic],
1905            (instrs CASALB, CASALH, CASALW, CASALX)>;
1906
1907def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1908            (instrs LDLARB, LDLARH, LDLARW, LDLARX)>;
1909
1910def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1911            (instrs LDADDB, LDADDH, LDADDW, LDADDX)>;
1912
1913def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1914            (instrs LDADDAB, LDADDAH, LDADDAW, LDADDAX)>;
1915
1916def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1917            (instrs LDADDLB, LDADDLH, LDADDLW, LDADDLX)>;
1918
1919def : InstRW<[THX3T110Write_8Cyc_I0123, WriteAtomic],
1920            (instrs LDADDALB, LDADDALH, LDADDALW, LDADDALX)>;
1921
1922def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1923            (instrs LDCLRB, LDCLRH, LDCLRW, LDCLRX)>;
1924
1925def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1926            (instrs LDCLRAB, LDCLRAH, LDCLRAW, LDCLRAX)>;
1927
1928def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1929            (instrs LDCLRLB, LDCLRLH, LDCLRLW, LDCLRLX)>;
1930
1931def : InstRW<[THX3T110Write_8Cyc_I0123, WriteAtomic],
1932            (instrs LDCLRALB, LDCLRALH, LDCLRALW, LDCLRALX)>;
1933
1934def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1935            (instrs LDEORB, LDEORH, LDEORW, LDEORX)>;
1936
1937def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1938            (instrs LDEORAB, LDEORAH, LDEORAW, LDEORAX)>;
1939
1940def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1941            (instrs LDEORLB, LDEORLH, LDEORLW, LDEORLX)>;
1942
1943def : InstRW<[THX3T110Write_8Cyc_I0123, WriteAtomic],
1944            (instrs LDEORALB, LDEORALH, LDEORALW, LDEORALX)>;
1945
1946def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1947            (instrs LDSETB, LDSETH, LDSETW, LDSETX)>;
1948
1949def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1950            (instrs LDSETAB, LDSETAH, LDSETAW, LDSETAX)>;
1951
1952def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1953            (instrs LDSETLB, LDSETLH, LDSETLW, LDSETLX)>;
1954
1955def : InstRW<[THX3T110Write_8Cyc_I0123, WriteAtomic],
1956            (instrs LDSETALB, LDSETALH, LDSETALW, LDSETALX)>;
1957
1958def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1959            (instrs LDSMAXB, LDSMAXH, LDSMAXW, LDSMAXX,
1960             LDSMAXAB, LDSMAXAH, LDSMAXAW, LDSMAXAX,
1961             LDSMAXLB, LDSMAXLH, LDSMAXLW, LDSMAXLX,
1962             LDSMAXALB, LDSMAXALH, LDSMAXALW, LDSMAXALX)>;
1963
1964def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1965            (instrs LDSMINB, LDSMINH, LDSMINW, LDSMINX,
1966             LDSMINAB, LDSMINAH, LDSMINAW, LDSMINAX,
1967             LDSMINLB, LDSMINLH, LDSMINLW, LDSMINLX,
1968             LDSMINALB, LDSMINALH, LDSMINALW, LDSMINALX)>;
1969
1970def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1971            (instrs LDUMAXB, LDUMAXH, LDUMAXW, LDUMAXX,
1972             LDUMAXAB, LDUMAXAH, LDUMAXAW, LDUMAXAX,
1973             LDUMAXLB, LDUMAXLH, LDUMAXLW, LDUMAXLX,
1974             LDUMAXALB, LDUMAXALH, LDUMAXALW, LDUMAXALX)>;
1975
1976def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1977            (instrs LDUMINB, LDUMINH, LDUMINW, LDUMINX,
1978             LDUMINAB, LDUMINAH, LDUMINAW, LDUMINAX,
1979             LDUMINLB, LDUMINLH, LDUMINLW, LDUMINLX,
1980             LDUMINALB, LDUMINALH, LDUMINALW, LDUMINALX)>;
1981
1982def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1983            (instrs SWPB, SWPH, SWPW, SWPX)>;
1984
1985def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1986            (instrs SWPAB, SWPAH, SWPAW, SWPAX)>;
1987
1988def : InstRW<[THX3T110Write_6Cyc_I0123, WriteAtomic],
1989            (instrs SWPLB, SWPLH, SWPLW, SWPLX)>;
1990
1991def : InstRW<[THX3T110Write_8Cyc_I0123, WriteAtomic],
1992            (instrs SWPALB, SWPALH, SWPALW, SWPALX)>;
1993
1994def : InstRW<[THX3T110Write_4Cyc_I0123, WriteAtomic],
1995            (instrs STLLRB, STLLRH, STLLRW, STLLRX)>;
1996
1997// V8.3a PAC
1998def : InstRW<[THX3T110Write_11Cyc_LS01_I1], (instregex "^LDRAA", "^LDRAB")>;
1999def : InstRW<[THX3T110Write_8Cyc_I123],
2000            (instrs BLRAA, BLRAAZ, BLRAB, BLRABZ,
2001                    BRAA, BRAAZ, BRAB, BRABZ)>;
2002def : InstRW<[THX3T110Write_8Cyc_I123], (instrs RETAA, RETAB)>;
2003
2004} // SchedModel = ThunderX3T110Model
2005