Commit | Line | Data |
---|---|---|
07c1b327 | 1 | /* bfin-defs.h ADI Blackfin gas header file |
aa820537 | 2 | Copyright 2005, 2006, 2007, 2009 |
07c1b327 CM |
3 | Free Software Foundation, Inc. |
4 | ||
5 | This file is part of GAS, the GNU Assembler. | |
6 | ||
7 | GAS is free software; you can redistribute it and/or modify | |
8 | it under the terms of the GNU General Public License as published by | |
ec2655a6 | 9 | the Free Software Foundation; either version 3, or (at your option) |
07c1b327 CM |
10 | any later version. |
11 | ||
12 | GAS is distributed in the hope that it will be useful, | |
13 | but WITHOUT ANY WARRANTY; without even the implied warranty of | |
14 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the | |
15 | GNU General Public License for more details. | |
16 | ||
17 | You should have received a copy of the GNU General Public License | |
18 | along with GAS; see the file COPYING. If not, write to the Free | |
19 | Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA | |
20 | 02110-1301, USA. */ | |
21 | ||
22 | #ifndef BFIN_PARSE_H | |
23 | #define BFIN_PARSE_H | |
24 | ||
07c1b327 CM |
25 | #define PCREL 1 |
26 | #define CODE_FRAG_SIZE 4096 /* 1 page. */ | |
27 | ||
28 | ||
29 | /* Definition for all status bits. */ | |
30 | typedef enum | |
31 | { | |
32 | c_0, | |
33 | c_1, | |
34 | c_4, | |
35 | c_2, | |
36 | c_uimm2, | |
37 | c_uimm3, | |
38 | c_imm3, | |
39 | c_pcrel4, | |
40 | c_imm4, | |
41 | c_uimm4s4, | |
42 | c_uimm4, | |
43 | c_uimm4s2, | |
44 | c_negimm5s4, | |
45 | c_imm5, | |
46 | c_uimm5, | |
47 | c_imm6, | |
48 | c_imm7, | |
49 | c_imm8, | |
50 | c_uimm8, | |
51 | c_pcrel8, | |
52 | c_uimm8s4, | |
53 | c_pcrel8s4, | |
54 | c_lppcrel10, | |
55 | c_pcrel10, | |
56 | c_pcrel12, | |
57 | c_imm16s4, | |
58 | c_luimm16, | |
59 | c_imm16, | |
60 | c_huimm16, | |
61 | c_rimm16, | |
62 | c_imm16s2, | |
63 | c_uimm16s4, | |
64 | c_uimm16, | |
65 | c_pcrel24 | |
66 | } const_forms_t; | |
67 | ||
68 | ||
69 | /* High-Nibble: group code, low nibble: register code. */ | |
70 | ||
71 | ||
72 | #define T_REG_R 0x00 | |
73 | #define T_REG_P 0x10 | |
74 | #define T_REG_I 0x20 | |
75 | #define T_REG_B 0x30 | |
76 | #define T_REG_L 0x34 | |
77 | #define T_REG_M 0x24 | |
78 | #define T_REG_A 0x40 | |
79 | ||
80 | /* All registers above this value don't | |
81 | belong to a usuable register group. */ | |
82 | #define T_NOGROUP 0xa0 | |
83 | ||
84 | /* Flags. */ | |
f31bf2c6 JZ |
85 | #define F_REG_NONE 0 |
86 | #define F_REG_HIGH 1 | |
87 | #define F_REG_LOW 2 | |
07c1b327 CM |
88 | |
89 | enum machine_registers | |
90 | { | |
91 | REG_R0 = T_REG_R, REG_R1, REG_R2, REG_R3, REG_R4, REG_R5, REG_R6, REG_R7, | |
92 | REG_P0 = T_REG_P, REG_P1, REG_P2, REG_P3, REG_P4, REG_P5, REG_SP, REG_FP, | |
93 | REG_I0 = T_REG_I, REG_I1, REG_I2, REG_I3, | |
94 | REG_M0 = T_REG_M, REG_M1, REG_M2, REG_M3, | |
95 | REG_B0 = T_REG_B, REG_B1, REG_B2, REG_B3, | |
96 | REG_L0 = T_REG_L, REG_L1, REG_L2, REG_L3, | |
97 | REG_A0x = T_REG_A, REG_A0w, REG_A1x, REG_A1w, | |
98 | REG_ASTAT = 0x46, | |
99 | REG_RETS = 0x47, | |
100 | REG_LC0 = 0x60, REG_LT0, REG_LB0, REG_LC1, REG_LT1, REG_LB1, | |
101 | REG_CYCLES, REG_CYCLES2, | |
102 | REG_USP = 0x70, REG_SEQSTAT, REG_SYSCFG, | |
103 | REG_RETI, REG_RETX, REG_RETN, REG_RETE, REG_EMUDAT, | |
104 | ||
105 | /* These don't have groups. */ | |
106 | REG_sftreset = T_NOGROUP, REG_omode, REG_excause, REG_emucause, | |
107 | REG_idle_req, REG_hwerrcause, | |
108 | REG_A0 = 0xc0, REG_A1, REG_CC, | |
109 | /* Pseudo registers, used only for distinction from symbols. */ | |
110 | REG_RL0, REG_RL1, REG_RL2, REG_RL3, | |
111 | REG_RL4, REG_RL5, REG_RL6, REG_RL7, | |
112 | REG_RH0, REG_RH1, REG_RH2, REG_RH3, | |
113 | REG_RH4, REG_RH5, REG_RH6, REG_RH7, | |
114 | REG_LASTREG | |
115 | }; | |
116 | ||
117 | /* Status register flags. */ | |
118 | ||
119 | enum statusflags | |
120 | { | |
121 | S_AZ = 0, | |
122 | S_AN, | |
123 | S_AQ = 6, | |
124 | S_AC0 = 12, | |
125 | S_AC1, | |
126 | S_AV0 = 16, | |
127 | S_AV0S, | |
128 | S_AV1, | |
129 | S_AV1S, | |
130 | S_V = 24, | |
131 | S_VS = 25 | |
132 | }; | |
133 | ||
134 | ||
135 | enum reg_class | |
136 | { | |
137 | rc_dregs_lo, | |
138 | rc_dregs_hi, | |
139 | rc_dregs, | |
140 | rc_dregs_pair, | |
141 | rc_pregs, | |
142 | rc_spfp, | |
143 | rc_dregs_hilo, | |
144 | rc_accum_ext, | |
145 | rc_accum_word, | |
146 | rc_accum, | |
147 | rc_iregs, | |
148 | rc_mregs, | |
149 | rc_bregs, | |
150 | rc_lregs, | |
151 | rc_dpregs, | |
152 | rc_gregs, | |
153 | rc_regs, | |
154 | rc_statbits, | |
155 | rc_ignore_bits, | |
156 | rc_ccstat, | |
157 | rc_counters, | |
158 | rc_dregs2_sysregs1, | |
159 | rc_open, | |
160 | rc_sysregs2, | |
161 | rc_sysregs3, | |
162 | rc_allregs, | |
163 | LIM_REG_CLASSES | |
164 | }; | |
165 | ||
166 | /* mmod field. */ | |
167 | #define M_S2RND 1 | |
168 | #define M_T 2 | |
169 | #define M_W32 3 | |
170 | #define M_FU 4 | |
171 | #define M_TFU 6 | |
172 | #define M_IS 8 | |
173 | #define M_ISS2 9 | |
174 | #define M_IH 11 | |
175 | #define M_IU 12 | |
176 | ||
177 | /* Register type checking macros. */ | |
178 | ||
179 | #define CODE_MASK 0x07 | |
180 | #define CLASS_MASK 0xf0 | |
181 | ||
182 | #define REG_SAME(a, b) ((a).regno == (b).regno) | |
183 | #define REG_EQUAL(a, b) (((a).regno & CODE_MASK) == ((b).regno & CODE_MASK)) | |
f31bf2c6 | 184 | #define REG_CLASS(a) ((a).regno & 0xf0) |
07c1b327 | 185 | #define IS_A1(a) ((a).regno == REG_A1) |
f31bf2c6 JZ |
186 | #define IS_H(a) ((a).flags & F_REG_HIGH ? 1: 0) |
187 | #define IS_EVEN(r) ((r).regno % 2 == 0) | |
07c1b327 | 188 | #define IS_HCOMPL(a, b) (REG_EQUAL(a, b) && \ |
f31bf2c6 | 189 | ((a).flags & F_REG_HIGH) != ((b).flags & F_REG_HIGH)) |
07c1b327 CM |
190 | |
191 | /* register type checking. */ | |
192 | #define _TYPECHECK(r, x) (((r).regno & CLASS_MASK) == T_REG_##x) | |
193 | ||
194 | #define IS_DREG(r) _TYPECHECK(r, R) | |
195 | #define IS_DREG_H(r) (_TYPECHECK(r, R) && IS_H(r)) | |
196 | #define IS_DREG_L(r) (_TYPECHECK(r, R) && !IS_H(r)) | |
197 | #define IS_PREG(r) _TYPECHECK(r, P) | |
198 | #define IS_IREG(r) (((r).regno & 0xf4) == T_REG_I) | |
199 | #define IS_MREG(r) (((r).regno & 0xf4) == T_REG_M) | |
73562ad0 JZ |
200 | #define IS_BREG(r) (((r).regno & 0xf4) == T_REG_B) |
201 | #define IS_LREG(r) (((r).regno & 0xf4) == T_REG_L) | |
07c1b327 CM |
202 | #define IS_CREG(r) ((r).regno == REG_LC0 || (r).regno == REG_LC1) |
203 | #define IS_ALLREG(r) ((r).regno < T_NOGROUP) | |
204 | ||
c958a8a8 JZ |
205 | #define IS_GENREG(r) \ |
206 | (IS_DREG (r) || IS_PREG (r) \ | |
207 | || (r).regno == REG_A0x || (r).regno == REG_A0w \ | |
208 | || (r).regno == REG_A1x || (r).regno == REG_A1w) | |
209 | ||
210 | #define IS_DAGREG(r) \ | |
211 | (IS_IREG (r) || IS_MREG (r) || IS_BREG (r) || IS_LREG (r)) | |
212 | ||
213 | #define IS_SYSREG(r) \ | |
214 | ((r).regno == REG_ASTAT || (r).regno == REG_SEQSTAT \ | |
215 | || (r).regno == REG_SYSCFG || (r).regno == REG_RETI \ | |
216 | || (r).regno == REG_RETX || (r).regno == REG_RETN \ | |
217 | || (r).regno == REG_RETE || (r).regno == REG_RETS \ | |
218 | || (r).regno == REG_LC0 || (r).regno == REG_LC1 \ | |
219 | || (r).regno == REG_LT0 || (r).regno == REG_LT1 \ | |
220 | || (r).regno == REG_LB0 || (r).regno == REG_LB1 \ | |
221 | || (r).regno == REG_CYCLES || (r).regno == REG_CYCLES2 \ | |
222 | || (r).regno == REG_EMUDAT) | |
223 | ||
07c1b327 CM |
224 | /* Expression value macros. */ |
225 | ||
226 | typedef enum | |
227 | { | |
228 | ones_compl, | |
229 | twos_compl, | |
230 | mult, | |
231 | divide, | |
232 | mod, | |
233 | add, | |
234 | sub, | |
235 | lsh, | |
236 | rsh, | |
237 | logand, | |
238 | logior, | |
239 | logxor | |
240 | } expr_opcodes_t; | |
241 | ||
242 | struct expressionS; | |
243 | ||
244 | #define SYMBOL_T symbolS* | |
245 | ||
246 | struct expression_cell | |
247 | { | |
248 | int value; | |
249 | SYMBOL_T symbol; | |
250 | }; | |
251 | ||
252 | /* User Type Definitions. */ | |
253 | struct bfin_insn | |
254 | { | |
255 | unsigned long value; | |
256 | struct bfin_insn *next; | |
257 | struct expression_cell *exp; | |
258 | int pcrel; | |
259 | int reloc; | |
260 | }; | |
261 | ||
262 | #define INSTR_T struct bfin_insn* | |
263 | #define EXPR_T struct expression_cell* | |
264 | ||
265 | typedef struct expr_node_struct Expr_Node; | |
266 | ||
267 | extern INSTR_T gencode (unsigned long x); | |
268 | extern INSTR_T conscode (INSTR_T head, INSTR_T tail); | |
269 | extern INSTR_T conctcode (INSTR_T head, INSTR_T tail); | |
270 | extern INSTR_T note_reloc | |
271 | (INSTR_T code, Expr_Node *, int reloc,int pcrel); | |
272 | extern INSTR_T note_reloc1 | |
273 | (INSTR_T code, const char * sym, int reloc, int pcrel); | |
274 | extern INSTR_T note_reloc2 | |
275 | (INSTR_T code, const char *symbol, int reloc, int value, int pcrel); | |
276 | ||
277 | /* Types of expressions. */ | |
278 | typedef enum | |
279 | { | |
280 | Expr_Node_Binop, /* Binary operator. */ | |
281 | Expr_Node_Unop, /* Unary operator. */ | |
282 | Expr_Node_Reloc, /* Symbol to be relocated. */ | |
1ac4baed | 283 | Expr_Node_GOT_Reloc, /* Symbol to be relocated using the GOT. */ |
07c1b327 CM |
284 | Expr_Node_Constant /* Constant. */ |
285 | } Expr_Node_Type; | |
286 | ||
287 | /* Types of operators. */ | |
288 | typedef enum | |
289 | { | |
290 | Expr_Op_Type_Add, | |
291 | Expr_Op_Type_Sub, | |
292 | Expr_Op_Type_Mult, | |
293 | Expr_Op_Type_Div, | |
294 | Expr_Op_Type_Mod, | |
295 | Expr_Op_Type_Lshift, | |
296 | Expr_Op_Type_Rshift, | |
297 | Expr_Op_Type_BAND, /* Bitwise AND. */ | |
298 | Expr_Op_Type_BOR, /* Bitwise OR. */ | |
299 | Expr_Op_Type_BXOR, /* Bitwise exclusive OR. */ | |
300 | Expr_Op_Type_LAND, /* Logical AND. */ | |
301 | Expr_Op_Type_LOR, /* Logical OR. */ | |
302 | Expr_Op_Type_NEG, | |
303 | Expr_Op_Type_COMP /* Complement. */ | |
304 | } Expr_Op_Type; | |
305 | ||
306 | /* The value that can be stored ... depends on type. */ | |
307 | typedef union | |
308 | { | |
309 | const char *s_value; /* if relocation symbol, the text. */ | |
958cff2f | 310 | long long i_value; /* if constant, the value. */ |
07c1b327 CM |
311 | Expr_Op_Type op_value; /* if operator, the value. */ |
312 | } Expr_Node_Value; | |
313 | ||
314 | /* The expression node. */ | |
315 | struct expr_node_struct | |
316 | { | |
317 | Expr_Node_Type type; | |
318 | Expr_Node_Value value; | |
319 | Expr_Node *Left_Child; | |
320 | Expr_Node *Right_Child; | |
321 | }; | |
322 | ||
323 | ||
324 | /* Operations on the expression node. */ | |
325 | Expr_Node *Expr_Node_Create (Expr_Node_Type type, | |
326 | Expr_Node_Value value, | |
327 | Expr_Node *Left_Child, | |
328 | Expr_Node *Right_Child); | |
329 | ||
330 | /* Generate the reloc structure as a series of instructions. */ | |
331 | INSTR_T Expr_Node_Gen_Reloc (Expr_Node *head, int parent_reloc); | |
332 | ||
333 | #define MKREF(x) mkexpr (0,x) | |
334 | #define ALLOCATE(x) malloc (x) | |
335 | ||
336 | #define NULL_CODE ((INSTR_T) 0) | |
337 | ||
338 | #ifndef EXPR_VALUE | |
339 | #define EXPR_VALUE(x) (((x)->type == Expr_Node_Constant) ? ((x)->value.i_value) : 0) | |
340 | #endif | |
341 | #ifndef EXPR_SYMBOL | |
342 | #define EXPR_SYMBOL(x) ((x)->symbol) | |
343 | #endif | |
344 | ||
345 | ||
346 | typedef long reg_t; | |
347 | ||
348 | ||
349 | typedef struct _register | |
350 | { | |
351 | reg_t regno; /* Register ID as defined in machine_registers. */ | |
352 | int flags; | |
353 | } Register; | |
354 | ||
355 | ||
356 | typedef struct _macfunc | |
357 | { | |
358 | char n; | |
359 | char op; | |
360 | char w; | |
361 | char P; | |
362 | Register dst; | |
363 | Register s0; | |
364 | Register s1; | |
365 | } Macfunc; | |
366 | ||
367 | typedef struct _opt_mode | |
368 | { | |
369 | int MM; | |
370 | int mod; | |
371 | } Opt_mode; | |
372 | ||
373 | typedef enum | |
374 | { | |
375 | SEMANTIC_ERROR, | |
376 | NO_INSN_GENERATED, | |
377 | INSN_GENERATED | |
378 | } parse_state; | |
379 | ||
380 | ||
381 | #ifdef __cplusplus | |
382 | extern "C" { | |
383 | #endif | |
384 | ||
385 | extern int debug_codeselection; | |
386 | ||
387 | void error (char *format, ...); | |
388 | void warn (char *format, ...); | |
389 | int semantic_error (char *syntax); | |
390 | void semantic_error_2 (char *syntax); | |
391 | ||
392 | EXPR_T mkexpr (int, SYMBOL_T); | |
393 | ||
07c1b327 CM |
394 | /* Defined in bfin-lex.l. */ |
395 | void set_start_state (void); | |
396 | ||
d55cb1c5 | 397 | extern int insn_regmask (int, int); |
07c1b327 CM |
398 | #ifdef __cplusplus |
399 | } | |
400 | #endif | |
401 | ||
402 | #endif /* BFIN_PARSE_H */ | |
403 |