Commit | Line | Data |
---|---|---|
fe663dea CT |
1 | /* |
2 | * Copyright (c) 1992 The Regents of the University of California. | |
3 | * All rights reserved. | |
4 | * | |
5 | * This software was developed by the Computer Systems Engineering group | |
6 | * at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and | |
7 | * contributed to Berkeley. | |
8 | * | |
9 | * %sccs.include.redist.c% | |
10 | * | |
11 | * @(#)instr.h 7.1 (Berkeley) %G% | |
12 | * | |
13 | * from: $Header: instr.h,v 1.5 92/06/17 06:10:19 torek Exp $ | |
14 | */ | |
15 | ||
16 | /* see also Appendix F of the SPARC version 8 document */ | |
17 | enum IOP { IOP_OP2, IOP_CALL, IOP_reg, IOP_mem }; | |
18 | enum IOP2 { IOP2_UNIMP, IOP2_err1, IOP2_Bicc, IOP2_err3, | |
19 | IOP2_SETHI, IOP2_err5, IOP2_FBfcc, IOP2_CBccc }; | |
20 | enum IOP3_reg { | |
21 | IOP3_ADD, IOP3_AND, IOP3_OR, IOP3_XOR, | |
22 | IOP3_SUB, IOP3_ANDN, IOP3_ORN, IOP3_XNOR, | |
23 | IOP3_ADDX, IOP3_rerr09, IOP3_UMUL, IOP3_SMUL, | |
24 | IOP3_SUBX, IOP3_rerr0d, IOP3_UDIV, IOP3_SDIV, | |
25 | IOP3_ADDcc, IOP3_ANDcc, IOP3_ORcc, IOP3_XORcc, | |
26 | IOP3_SUBcc, IOP3_ANDNcc, IOP3_ORNcc, IOP3_XNORcc, | |
27 | IOP3_ADDXcc, IOP3_rerr19, IOP3_UMULcc, IOP3_SMULcc, | |
28 | IOP3_SUBXcc, IOP3_rerr1d, IOP3_UDIVcc, IOP3_SDIVcc, | |
29 | IOP3_TADDcc, IOP3_TSUBcc, IOP3_TADDccTV, IOP3_TSUBccTV, | |
30 | IOP3_MULScc, IOP3_SLL, IOP3_SRL, IOP3_SRA, | |
31 | IOP3_RDASR_RDY_STBAR, IOP3_RDPSR, IOP3_RDWIM, IOP3_RDTGBR, | |
32 | IOP3_rerr2c, IOP3_rerr2d, IOP3_rerr2e, IOP3_rerr2f, | |
33 | IOP3_WRASR_WRY, IOP3_WRPSR, IOP3_WRWIM, IOP3_WRTBR, | |
34 | IOP3_FPop1, IOP3_FPop2, IOP3_CPop1, IOP3_CPop2, | |
35 | IOP3_JMPL, IOP3_RETT, IOP3_Ticc, IOP3_FLUSH, | |
36 | IOP3_SAVE, IOP3_RESTORE, IOP3_rerr3e, IOP3_rerr3f | |
37 | }; | |
38 | enum IOP3_mem { | |
39 | IOP3_LD, IOP3_LDUB, IOP3_LDUH, IOP3_LDD, | |
40 | IOP3_ST, IOP3_STB, IOP3_STH, IOP3_STD, | |
41 | IOP3_merr08, IOP3_LDSB, IOP3_LDSH, IOP3_merr0b, | |
42 | IOP3_merr0c, IOP3_LDSTUB, IOP3_merr0f, IOP3_SWAP, | |
43 | IOP3_LDA, IOP3_LDUBA, IOP3_LDUHA, IOP3_LDDA, | |
44 | IOP3_STA, IOP3_STBA, IOP3_STHA, IOP3_STDA, | |
45 | IOP3_merr18, IOP3_LDSBA, IOP3_LDSHA, IOP3_merr1b, | |
46 | IOP3_merr1c, IOP3_LDSTUBA, IOP3_merr1f, IOP3_SWAPA, | |
47 | IOP3_LDF, IOP3_LDFSR, IOP3_merr22, IOP3_LDDF, | |
48 | IOP3_STF, IOP3_STFSR, IOP3_STDFQ, IOP3_STDF, | |
49 | IOP3_merr28, IOP3_merr29, IOP3_merr2a, IOP3_merr2b, | |
50 | IOP3_merr2c, IOP3_merr2d, IOP3_merr2e, IOP3_merr2f, | |
51 | IOP3_LFC, IOP3_LDCSR, IOP3_merr32, IOP3_LDDC, | |
52 | IOP3_STC, IOP3_STCSR, IOP3_STDCQ, IOP3_STDC, | |
53 | IOP3_merr38, IOP3_merr39, IOP3_merr3a, IOP3_merr3b, | |
54 | IOP3_merr3c, IOP3_merr3d, IOP3_merr3e, IOP3_merr3f | |
55 | }; | |
56 | ||
57 | /* | |
58 | * Integer condition codes. | |
59 | */ | |
60 | #define Icc_N 0x0 /* never */ | |
61 | #define Icc_E 0x1 /* equal (equiv. zero) */ | |
62 | #define Icc_LE 0x2 /* less or equal */ | |
63 | #define Icc_L 0x3 /* less */ | |
64 | #define Icc_LEU 0x4 /* less or equal unsigned */ | |
65 | #define Icc_CS 0x5 /* carry set (equiv. less unsigned) */ | |
66 | #define Icc_NEG 0x6 /* negative */ | |
67 | #define Icc_VS 0x7 /* overflow set */ | |
68 | #define Icc_A 0x8 /* always */ | |
69 | #define Icc_NE 0x9 /* not equal (equiv. not zero) */ | |
70 | #define Icc_G 0xa /* greater */ | |
71 | #define Icc_GE 0xb /* greater or equal */ | |
72 | #define Icc_GU 0xc /* greater unsigned */ | |
73 | #define Icc_CC 0xd /* carry clear (equiv. gtr or eq unsigned) */ | |
74 | #define Icc_POS 0xe /* positive */ | |
75 | #define Icc_VC 0xf /* overflow clear */ | |
76 | ||
77 | /* | |
78 | * Integer registers. | |
79 | */ | |
80 | #define I_G0 0 | |
81 | #define I_G1 1 | |
82 | #define I_G2 2 | |
83 | #define I_G3 3 | |
84 | #define I_G4 4 | |
85 | #define I_G5 5 | |
86 | #define I_G6 6 | |
87 | #define I_G7 7 | |
88 | #define I_O0 8 | |
89 | #define I_O1 9 | |
90 | #define I_O2 10 | |
91 | #define I_O3 11 | |
92 | #define I_O4 12 | |
93 | #define I_O5 13 | |
94 | #define I_O6 14 | |
95 | #define I_O7 15 | |
96 | #define I_L0 16 | |
97 | #define I_L1 17 | |
98 | #define I_L2 18 | |
99 | #define I_L3 19 | |
100 | #define I_L4 20 | |
101 | #define I_L5 21 | |
102 | #define I_L6 22 | |
103 | #define I_L7 23 | |
104 | #define I_I0 24 | |
105 | #define I_I1 25 | |
106 | #define I_I2 26 | |
107 | #define I_I3 27 | |
108 | #define I_I4 28 | |
109 | #define I_I5 29 | |
110 | #define I_I6 30 | |
111 | #define I_I7 31 | |
112 | ||
113 | /* | |
114 | * An instruction. | |
115 | */ | |
116 | union instr { | |
117 | int i_int; /* as a whole */ | |
118 | ||
119 | /* | |
120 | * The first level of decoding is to use the top 2 bits. | |
121 | * This gives us one of three `formats', which usually give | |
122 | * a second level of decoding. | |
123 | */ | |
124 | struct { | |
125 | u_int i_op:2; /* first-level decode */ | |
126 | u_int :30; | |
127 | } i_any; | |
128 | ||
129 | /* | |
130 | * Format 1 instructions: CALL (undifferentiated). | |
131 | */ | |
132 | struct { | |
133 | u_int :2; /* 01 */ | |
134 | int i_disp:30; /* displacement */ | |
135 | } i_call; | |
136 | ||
137 | /* | |
138 | * Format 2 instructions (SETHI, UNIMP, and branches, plus illegal | |
139 | * unused codes). | |
140 | */ | |
141 | struct { | |
142 | u_int :2; /* 00 */ | |
143 | u_int :5; | |
144 | u_int i_op2:3; /* second-level decode */ | |
145 | u_int :22; | |
146 | } i_op2; | |
147 | ||
148 | /* UNIMP, SETHI */ | |
149 | struct { | |
150 | u_int :2; /* 00 */ | |
151 | u_int i_rd:5; /* destination register */ | |
152 | u_int i_op2:3; /* opcode: UNIMP or SETHI */ | |
153 | u_int i_imm:22; /* immediate value */ | |
154 | } i_imm22; | |
155 | ||
156 | /* branches: Bicc, FBfcc, CBccc */ | |
157 | struct { | |
158 | u_int :2; /* 00 */ | |
159 | u_int i_annul:1; /* annul bit */ | |
160 | u_int i_cond:4; /* condition codes */ | |
161 | u_int i_op2:3; /* opcode: {Bi,FBf,CBc}cc */ | |
162 | int i_disp:22; /* branch displacement */ | |
163 | } i_branch; | |
164 | ||
165 | /* | |
166 | * Format 3 instructions (memory reference; arithmetic, logical, | |
167 | * shift, and other miscellaneous operations). The second-level | |
168 | * decode almost always makes use of an `rd' and `rs1', however | |
169 | * (see also IOP3_reg and IOP3_mem). | |
170 | * | |
171 | * Beyond that, the low 14 bits may be broken up in one of three | |
172 | * different ways, if at all: | |
173 | * 1 bit of imm=0 + 8 bits of asi + 5 bits of rs2 [reg & mem] | |
174 | * 1 bit of imm=1 + 13 bits of signed immediate [reg & mem] | |
175 | * 9 bits of copressor `opf' opcode + 5 bits of rs2 [reg only] | |
176 | */ | |
177 | struct { | |
178 | u_int :2; /* 10 or 11 */ | |
179 | u_int i_rd:5; /* destination register */ | |
180 | u_int i_op3:6; /* second-level decode */ | |
181 | u_int i_rs1:5; /* source register 1 */ | |
182 | u_int i_low14:14; /* varies */ | |
183 | } i_op3; | |
184 | ||
185 | /* | |
186 | * Memory forms. These set i_op=3 and use simm13 or asi layout. | |
187 | * Memory references without an ASI should use 0, but the actual | |
188 | * ASI field is simply ignored. | |
189 | */ | |
190 | struct { | |
191 | u_int :2; /* 11 only */ | |
192 | u_int i_rd:5; /* destination register */ | |
193 | u_int i_op3:6; /* second-level decode (see IOP3_mem) */ | |
194 | u_int i_i:1; /* immediate vs asi */ | |
195 | u_int i_low13:13; /* depend on i bit */ | |
196 | } i_loadstore; | |
197 | ||
198 | /* | |
199 | * Memory and register forms. | |
200 | * These come in quite a variety and we do not | |
201 | * attempt to break them down much. | |
202 | */ | |
203 | struct { | |
204 | u_int :2; /* 10 or 11 */ | |
205 | u_int i_rd:5; /* destination register */ | |
206 | u_int i_op3:6; /* second-level decode */ | |
207 | u_int i_rs1:5; /* source register 1 */ | |
208 | u_int i_i:1; /* immediate bit (1) */ | |
209 | int i_simm13:13; /* signed immediate */ | |
210 | } i_simm13; | |
211 | struct { | |
212 | u_int :2; /* 10 or 11 */ | |
213 | u_int i_rd:5; /* destination register */ | |
214 | u_int i_op3:6; /* second-level decode */ | |
215 | u_int i_rs1:5; /* source register 1 */ | |
216 | u_int i_asi:8; /* asi */ | |
217 | u_int i_rs2:5; /* source register 2 */ | |
218 | } i_asi; | |
219 | struct { | |
220 | u_int :2; /* 10 only (register, no memory) */ | |
221 | u_int i_rd:5; /* destination register */ | |
222 | u_int i_op3:6; /* second-level decode (see IOP3_reg) */ | |
223 | u_int i_rs1:5; /* source register 1 */ | |
224 | u_int i_opf:9; /* coprocessor 3rd-level decode */ | |
225 | u_int i_rs2:5; /* source register 2 */ | |
226 | } i_opf; | |
227 | ||
228 | }; | |
229 | ||
230 | /* | |
231 | * Internal macros for building instructions. These correspond 1-to-1 to | |
232 | * the names above. Note that x << y | z == (x << y) | z. | |
233 | */ | |
234 | #define _I_ANY(op, b) ((op) << 30 | (b)) | |
235 | ||
236 | #define _I_OP2(high, op2, low) \ | |
237 | _I_ANY(IOP_OP2, (high) << 25 | (op2) << 22 | (low)) | |
238 | #define _I_IMM22(rd, op2, imm) \ | |
239 | _I_ANY(IOP_OP2, (rd) << 25 | (op2) << 22 | (imm)) | |
240 | #define _I_BRANCH(a, c, op2, disp) \ | |
241 | _I_ANY(IOP_OP2, (a) << 29 | (c) << 25 | (op2) << 22 | (disp)) | |
242 | #define _I_FBFCC(a, cond, disp) \ | |
243 | _I_BRANCH(a, cond, IOP2_FBfcc, disp) | |
244 | #define _I_CBCCC(a, cond, disp) \ | |
245 | _I_BRANCH(a, cond, IOP2_CBccc, disp) | |
246 | ||
247 | #define _I_SIMM(simm) (1 << 13 | ((simm) & 0x1fff)) | |
248 | ||
249 | #define _I_OP3_GEN(form, rd, op3, rs1, low14) \ | |
250 | _I_ANY(form, (rd) << 25 | (op3) << 19 | (rs1) << 14 | (low14)) | |
251 | #define _I_OP3_LS_RAR(rd, op3, rs1, asi, rs2) \ | |
252 | _I_OP3_GEN(IOP_mem, rd, op3, rs1, (asi) << 5 | (rs2)) | |
253 | #define _I_OP3_LS_RI(rd, op3, rs1, simm13) \ | |
254 | _I_OP3_GEN(IOP_mem, rd, op3, rs1, _I_SIMM(simm13)) | |
255 | #define _I_OP3_LS_RR(rd, op3, rs1, rs2) \ | |
256 | _I_OP3_GEN(IOP_mem, rd, op3, rs1, rs2) | |
257 | #define _I_OP3_R_RAR(rd, op3, rs1, asi, rs2) \ | |
258 | _I_OP3_GEN(IOP_reg, rd, op3, rs1, (asi) << 5 | (rs2)) | |
259 | #define _I_OP3_R_RI(rd, op3, rs1, simm13) \ | |
260 | _I_OP3_GEN(IOP_reg, rd, op3, rs1, _I_SIMM(simm13)) | |
261 | #define _I_OP3_R_RR(rd, op3, rs1, rs2) \ | |
262 | _I_OP3_GEN(IOP_reg, rd, op3, rs1, rs2) | |
263 | ||
264 | #define I_CALL(d) _I_ANY(IOP_CALL, d) | |
265 | #define I_UNIMP(v) _I_IMM22(0, IOP2_UNIMP, v) | |
266 | #define I_BN(a, d) _I_BRANCH(a, Icc_N, IOP2_Bicc, d) | |
267 | #define I_BE(a, d) _I_BRANCH(a, Icc_E, IOP2_Bicc, d) | |
268 | #define I_BZ(a, d) _I_BRANCH(a, Icc_E, IOP2_Bicc, d) | |
269 | #define I_BLE(a, d) _I_BRANCH(a, Icc_LE, IOP2_Bicc, d) | |
270 | #define I_BL(a, d) _I_BRANCH(a, Icc_L, IOP2_Bicc, d) | |
271 | #define I_BLEU(a, d) _I_BRANCH(a, Icc_LEU, IOP2_Bicc, d) | |
272 | #define I_BCS(a, d) _I_BRANCH(a, Icc_CS, IOP2_Bicc, d) | |
273 | #define I_BLU(a, d) _I_BRANCH(a, Icc_CS, IOP2_Bicc, d) | |
274 | #define I_BNEG(a, d) _I_BRANCH(a, Icc_NEG, IOP2_Bicc, d) | |
275 | #define I_BVS(a, d) _I_BRANCH(a, Icc_VS, IOP2_Bicc, d) | |
276 | #define I_BA(a, d) _I_BRANCH(a, Icc_A, IOP2_Bicc, d) | |
277 | #define I_B(a, d) _I_BRANCH(a, Icc_A, IOP2_Bicc, d) | |
278 | #define I_BNE(a, d) _I_BRANCH(a, Icc_NE, IOP2_Bicc, d) | |
279 | #define I_BNZ(a, d) _I_BRANCH(a, Icc_NE, IOP2_Bicc, d) | |
280 | #define I_BG(a, d) _I_BRANCH(a, Icc_G, IOP2_Bicc, d) | |
281 | #define I_BGE(a, d) _I_BRANCH(a, Icc_GE, IOP2_Bicc, d) | |
282 | #define I_BGU(a, d) _I_BRANCH(a, Icc_GU, IOP2_Bicc, d) | |
283 | #define I_BCC(a, d) _I_BRANCH(a, Icc_CC, IOP2_Bicc, d) | |
284 | #define I_BGEU(a, d) _I_BRANCH(a, Icc_CC, IOP2_Bicc, d) | |
285 | #define I_BPOS(a, d) _I_BRANCH(a, Icc_POS, IOP2_Bicc, d) | |
286 | #define I_BVC(a, d) _I_BRANCH(a, Icc_VC, IOP2_Bicc, d) | |
287 | #define I_SETHI(r, v) _I_IMM22(r, 4, v) | |
288 | ||
289 | #define I_ORri(rd, rs1, imm) _I_OP3_R_RI(rd, IOP3_OR, rs1, imm) | |
290 | #define I_ORrr(rd, rs1, rs2) _I_OP3_R_RR(rd, IOP3_OR, rs1, rs2) | |
291 | ||
292 | #define I_MOVi(rd, imm) _I_OP3_R_RI(rd, IOP3_OR, I_G0, imm) | |
293 | #define I_MOVr(rd, rs) _I_OP3_R_RR(rd, IOP3_OR, I_G0, rs) | |
294 | ||
295 | #define I_RDPSR(rd) _I_OP3_R_RR(rd, IOP3_RDPSR, 0, 0) | |
296 | ||
297 | #define I_JMPLri(rd, rs1, imm) _I_OP3_R_RI(rd, IOP3_JMPL, rs1, imm) | |
298 | #define I_JMPLrr(rd, rs1, rs2) _I_OP3_R_RR(rd, IOP3_JMPL, rs1, rs2) | |
299 | ||
300 | /* | |
301 | * (Since these are sparse, we skip the enumerations for now.) | |
302 | * FPop values. All appear in both FPop1 and FPop2 spaces, but arithmetic | |
303 | * ops should happen only with FPop1 and comparison only with FPop2. | |
304 | * The type sits in the low two bits; those bits are given as zero here. | |
305 | */ | |
306 | #define FMOV 0x00 | |
307 | #define FNEG 0x04 | |
308 | #define FABS 0x08 | |
309 | #define FSQRT 0x28 | |
310 | #define FADD 0x40 | |
311 | #define FSUB 0x44 | |
312 | #define FMUL 0x48 | |
313 | #define FDIV 0x4c | |
314 | #define FCMP 0x50 | |
315 | #define FCMPE 0x54 | |
316 | #define FSMULD 0x68 | |
317 | #define FDMULX 0x6c | |
318 | #define FTOS 0xc4 | |
319 | #define FTOD 0xc8 | |
320 | #define FTOX 0xcc | |
321 | #define FTOI 0xd0 | |
322 | ||
323 | /* | |
324 | * FPU data types. | |
325 | */ | |
326 | #define FTYPE_INT 0 /* data = 32-bit signed integer */ | |
327 | #define FTYPE_SNG 1 /* data = 32-bit float */ | |
328 | #define FTYPE_DBL 2 /* data = 64-bit double */ | |
329 | #define FTYPE_EXT 3 /* data = 128-bit extended (quad-prec) */ |