tc-bfin.c revision 1.1.1.3 1 1.1 christos /* tc-bfin.c -- Assembler for the ADI Blackfin.
2 1.1.1.3 christos Copyright (C) 2005-2016 Free Software Foundation, Inc.
3 1.1 christos
4 1.1 christos This file is part of GAS, the GNU Assembler.
5 1.1 christos
6 1.1 christos GAS is free software; you can redistribute it and/or modify
7 1.1 christos it under the terms of the GNU General Public License as published by
8 1.1 christos the Free Software Foundation; either version 3, or (at your option)
9 1.1 christos any later version.
10 1.1 christos
11 1.1 christos GAS is distributed in the hope that it will be useful,
12 1.1 christos but WITHOUT ANY WARRANTY; without even the implied warranty of
13 1.1 christos MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 1.1 christos GNU General Public License for more details.
15 1.1 christos
16 1.1 christos You should have received a copy of the GNU General Public License
17 1.1 christos along with GAS; see the file COPYING. If not, write to the Free
18 1.1 christos Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
19 1.1 christos 02110-1301, USA. */
20 1.1 christos
21 1.1 christos #include "as.h"
22 1.1 christos #include "struc-symbol.h"
23 1.1 christos #include "bfin-defs.h"
24 1.1 christos #include "obstack.h"
25 1.1 christos #include "safe-ctype.h"
26 1.1 christos #ifdef OBJ_ELF
27 1.1 christos #include "dwarf2dbg.h"
28 1.1 christos #endif
29 1.1 christos #include "libbfd.h"
30 1.1 christos #include "elf/common.h"
31 1.1 christos #include "elf/bfin.h"
32 1.1 christos
33 1.1 christos extern int yyparse (void);
34 1.1 christos struct yy_buffer_state;
35 1.1 christos typedef struct yy_buffer_state *YY_BUFFER_STATE;
36 1.1 christos extern YY_BUFFER_STATE yy_scan_string (const char *yy_str);
37 1.1 christos extern void yy_delete_buffer (YY_BUFFER_STATE b);
38 1.1 christos static parse_state parse (char *line);
39 1.1 christos
40 1.1 christos /* Global variables. */
41 1.1 christos struct bfin_insn *insn;
42 1.1 christos int last_insn_size;
43 1.1 christos
44 1.1 christos extern struct obstack mempool;
45 1.1 christos FILE *errorf;
46 1.1 christos
47 1.1 christos /* Flags to set in the elf header */
48 1.1 christos #define DEFAULT_FLAGS 0
49 1.1 christos
50 1.1 christos #ifdef OBJ_FDPIC_ELF
51 1.1 christos # define DEFAULT_FDPIC EF_BFIN_FDPIC
52 1.1 christos #else
53 1.1 christos # define DEFAULT_FDPIC 0
54 1.1 christos #endif
55 1.1 christos
56 1.1 christos static flagword bfin_flags = DEFAULT_FLAGS | DEFAULT_FDPIC;
57 1.1 christos static const char *bfin_pic_flag = DEFAULT_FDPIC ? "-mfdpic" : (const char *)0;
58 1.1 christos
59 1.1 christos /* Blackfin specific function to handle FD-PIC pointer initializations. */
60 1.1 christos
61 1.1 christos static void
62 1.1 christos bfin_pic_ptr (int nbytes)
63 1.1 christos {
64 1.1 christos expressionS exp;
65 1.1 christos char *p;
66 1.1 christos
67 1.1 christos if (nbytes != 4)
68 1.1 christos abort ();
69 1.1 christos
70 1.1 christos #ifdef md_flush_pending_output
71 1.1 christos md_flush_pending_output ();
72 1.1 christos #endif
73 1.1 christos
74 1.1 christos if (is_it_end_of_statement ())
75 1.1 christos {
76 1.1 christos demand_empty_rest_of_line ();
77 1.1 christos return;
78 1.1 christos }
79 1.1 christos
80 1.1 christos #ifdef md_cons_align
81 1.1 christos md_cons_align (nbytes);
82 1.1 christos #endif
83 1.1 christos
84 1.1 christos do
85 1.1 christos {
86 1.1 christos bfd_reloc_code_real_type reloc_type = BFD_RELOC_BFIN_FUNCDESC;
87 1.1 christos
88 1.1 christos if (strncasecmp (input_line_pointer, "funcdesc(", 9) == 0)
89 1.1 christos {
90 1.1 christos input_line_pointer += 9;
91 1.1 christos expression (&exp);
92 1.1 christos if (*input_line_pointer == ')')
93 1.1 christos input_line_pointer++;
94 1.1 christos else
95 1.1 christos as_bad (_("missing ')'"));
96 1.1 christos }
97 1.1 christos else
98 1.1 christos error ("missing funcdesc in picptr");
99 1.1 christos
100 1.1 christos p = frag_more (4);
101 1.1 christos memset (p, 0, 4);
102 1.1 christos fix_new_exp (frag_now, p - frag_now->fr_literal, 4, &exp, 0,
103 1.1 christos reloc_type);
104 1.1 christos }
105 1.1 christos while (*input_line_pointer++ == ',');
106 1.1 christos
107 1.1 christos input_line_pointer--; /* Put terminator back into stream. */
108 1.1 christos demand_empty_rest_of_line ();
109 1.1 christos }
110 1.1 christos
111 1.1 christos static void
112 1.1 christos bfin_s_bss (int ignore ATTRIBUTE_UNUSED)
113 1.1 christos {
114 1.1.1.2 christos int temp;
115 1.1 christos
116 1.1 christos temp = get_absolute_expression ();
117 1.1 christos subseg_set (bss_section, (subsegT) temp);
118 1.1 christos demand_empty_rest_of_line ();
119 1.1 christos }
120 1.1 christos
121 1.1 christos const pseudo_typeS md_pseudo_table[] = {
122 1.1 christos {"align", s_align_bytes, 0},
123 1.1 christos {"byte2", cons, 2},
124 1.1 christos {"byte4", cons, 4},
125 1.1 christos {"picptr", bfin_pic_ptr, 4},
126 1.1 christos {"code", obj_elf_section, 0},
127 1.1 christos {"db", cons, 1},
128 1.1 christos {"dd", cons, 4},
129 1.1 christos {"dw", cons, 2},
130 1.1 christos {"p", s_ignore, 0},
131 1.1 christos {"pdata", s_ignore, 0},
132 1.1 christos {"var", s_ignore, 0},
133 1.1 christos {"bss", bfin_s_bss, 0},
134 1.1 christos {0, 0, 0}
135 1.1 christos };
136 1.1 christos
137 1.1 christos /* Characters that are used to denote comments and line separators. */
138 1.1 christos const char comment_chars[] = "#";
139 1.1 christos const char line_comment_chars[] = "#";
140 1.1 christos const char line_separator_chars[] = ";";
141 1.1 christos
142 1.1 christos /* Characters that can be used to separate the mantissa from the
143 1.1 christos exponent in floating point numbers. */
144 1.1 christos const char EXP_CHARS[] = "eE";
145 1.1 christos
146 1.1 christos /* Characters that mean this number is a floating point constant.
147 1.1 christos As in 0f12.456 or 0d1.2345e12. */
148 1.1 christos const char FLT_CHARS[] = "fFdDxX";
149 1.1 christos
150 1.1 christos typedef enum bfin_cpu_type
151 1.1 christos {
152 1.1 christos BFIN_CPU_UNKNOWN,
153 1.1 christos BFIN_CPU_BF504,
154 1.1 christos BFIN_CPU_BF506,
155 1.1 christos BFIN_CPU_BF512,
156 1.1 christos BFIN_CPU_BF514,
157 1.1 christos BFIN_CPU_BF516,
158 1.1 christos BFIN_CPU_BF518,
159 1.1 christos BFIN_CPU_BF522,
160 1.1 christos BFIN_CPU_BF523,
161 1.1 christos BFIN_CPU_BF524,
162 1.1 christos BFIN_CPU_BF525,
163 1.1 christos BFIN_CPU_BF526,
164 1.1 christos BFIN_CPU_BF527,
165 1.1 christos BFIN_CPU_BF531,
166 1.1 christos BFIN_CPU_BF532,
167 1.1 christos BFIN_CPU_BF533,
168 1.1 christos BFIN_CPU_BF534,
169 1.1 christos BFIN_CPU_BF536,
170 1.1 christos BFIN_CPU_BF537,
171 1.1 christos BFIN_CPU_BF538,
172 1.1 christos BFIN_CPU_BF539,
173 1.1 christos BFIN_CPU_BF542,
174 1.1 christos BFIN_CPU_BF542M,
175 1.1 christos BFIN_CPU_BF544,
176 1.1 christos BFIN_CPU_BF544M,
177 1.1 christos BFIN_CPU_BF547,
178 1.1 christos BFIN_CPU_BF547M,
179 1.1 christos BFIN_CPU_BF548,
180 1.1 christos BFIN_CPU_BF548M,
181 1.1 christos BFIN_CPU_BF549,
182 1.1 christos BFIN_CPU_BF549M,
183 1.1 christos BFIN_CPU_BF561,
184 1.1 christos BFIN_CPU_BF592,
185 1.1 christos } bfin_cpu_t;
186 1.1 christos
187 1.1 christos bfin_cpu_t bfin_cpu_type = BFIN_CPU_UNKNOWN;
188 1.1 christos /* -msi-revision support. There are three special values:
189 1.1 christos -1 -msi-revision=none.
190 1.1 christos 0xffff -msi-revision=any. */
191 1.1 christos int bfin_si_revision;
192 1.1 christos
193 1.1 christos unsigned int bfin_anomaly_checks = 0;
194 1.1 christos
195 1.1 christos struct bfin_cpu
196 1.1 christos {
197 1.1 christos const char *name;
198 1.1 christos bfin_cpu_t type;
199 1.1 christos int si_revision;
200 1.1 christos unsigned int anomaly_checks;
201 1.1 christos };
202 1.1 christos
203 1.1 christos struct bfin_cpu bfin_cpus[] =
204 1.1 christos {
205 1.1 christos {"bf504", BFIN_CPU_BF504, 0x0000, AC_05000074},
206 1.1 christos
207 1.1 christos {"bf506", BFIN_CPU_BF506, 0x0000, AC_05000074},
208 1.1 christos
209 1.1 christos {"bf512", BFIN_CPU_BF512, 0x0002, AC_05000074},
210 1.1 christos {"bf512", BFIN_CPU_BF512, 0x0001, AC_05000074},
211 1.1 christos {"bf512", BFIN_CPU_BF512, 0x0000, AC_05000074},
212 1.1 christos
213 1.1 christos {"bf514", BFIN_CPU_BF514, 0x0002, AC_05000074},
214 1.1 christos {"bf514", BFIN_CPU_BF514, 0x0001, AC_05000074},
215 1.1 christos {"bf514", BFIN_CPU_BF514, 0x0000, AC_05000074},
216 1.1 christos
217 1.1 christos {"bf516", BFIN_CPU_BF516, 0x0002, AC_05000074},
218 1.1 christos {"bf516", BFIN_CPU_BF516, 0x0001, AC_05000074},
219 1.1 christos {"bf516", BFIN_CPU_BF516, 0x0000, AC_05000074},
220 1.1 christos
221 1.1 christos {"bf518", BFIN_CPU_BF518, 0x0002, AC_05000074},
222 1.1 christos {"bf518", BFIN_CPU_BF518, 0x0001, AC_05000074},
223 1.1 christos {"bf518", BFIN_CPU_BF518, 0x0000, AC_05000074},
224 1.1 christos
225 1.1 christos {"bf522", BFIN_CPU_BF522, 0x0002, AC_05000074},
226 1.1 christos {"bf522", BFIN_CPU_BF522, 0x0001, AC_05000074},
227 1.1 christos {"bf522", BFIN_CPU_BF522, 0x0000, AC_05000074},
228 1.1 christos
229 1.1 christos {"bf523", BFIN_CPU_BF523, 0x0002, AC_05000074},
230 1.1 christos {"bf523", BFIN_CPU_BF523, 0x0001, AC_05000074},
231 1.1 christos {"bf523", BFIN_CPU_BF523, 0x0000, AC_05000074},
232 1.1 christos
233 1.1 christos {"bf524", BFIN_CPU_BF524, 0x0002, AC_05000074},
234 1.1 christos {"bf524", BFIN_CPU_BF524, 0x0001, AC_05000074},
235 1.1 christos {"bf524", BFIN_CPU_BF524, 0x0000, AC_05000074},
236 1.1 christos
237 1.1 christos {"bf525", BFIN_CPU_BF525, 0x0002, AC_05000074},
238 1.1 christos {"bf525", BFIN_CPU_BF525, 0x0001, AC_05000074},
239 1.1 christos {"bf525", BFIN_CPU_BF525, 0x0000, AC_05000074},
240 1.1 christos
241 1.1 christos {"bf526", BFIN_CPU_BF526, 0x0002, AC_05000074},
242 1.1 christos {"bf526", BFIN_CPU_BF526, 0x0001, AC_05000074},
243 1.1 christos {"bf526", BFIN_CPU_BF526, 0x0000, AC_05000074},
244 1.1 christos
245 1.1 christos {"bf527", BFIN_CPU_BF527, 0x0002, AC_05000074},
246 1.1 christos {"bf527", BFIN_CPU_BF527, 0x0001, AC_05000074},
247 1.1 christos {"bf527", BFIN_CPU_BF527, 0x0000, AC_05000074},
248 1.1 christos
249 1.1 christos {"bf531", BFIN_CPU_BF531, 0x0006, AC_05000074},
250 1.1 christos {"bf531", BFIN_CPU_BF531, 0x0005, AC_05000074},
251 1.1 christos {"bf531", BFIN_CPU_BF531, 0x0004, AC_05000074},
252 1.1 christos {"bf531", BFIN_CPU_BF531, 0x0003, AC_05000074},
253 1.1 christos
254 1.1 christos {"bf532", BFIN_CPU_BF532, 0x0006, AC_05000074},
255 1.1 christos {"bf532", BFIN_CPU_BF532, 0x0005, AC_05000074},
256 1.1 christos {"bf532", BFIN_CPU_BF532, 0x0004, AC_05000074},
257 1.1 christos {"bf532", BFIN_CPU_BF532, 0x0003, AC_05000074},
258 1.1 christos
259 1.1 christos {"bf533", BFIN_CPU_BF533, 0x0006, AC_05000074},
260 1.1 christos {"bf533", BFIN_CPU_BF533, 0x0005, AC_05000074},
261 1.1 christos {"bf533", BFIN_CPU_BF533, 0x0004, AC_05000074},
262 1.1 christos {"bf533", BFIN_CPU_BF533, 0x0003, AC_05000074},
263 1.1 christos
264 1.1 christos {"bf534", BFIN_CPU_BF534, 0x0003, AC_05000074},
265 1.1 christos {"bf534", BFIN_CPU_BF534, 0x0002, AC_05000074},
266 1.1 christos {"bf534", BFIN_CPU_BF534, 0x0001, AC_05000074},
267 1.1 christos
268 1.1 christos {"bf536", BFIN_CPU_BF536, 0x0003, AC_05000074},
269 1.1 christos {"bf536", BFIN_CPU_BF536, 0x0002, AC_05000074},
270 1.1 christos {"bf536", BFIN_CPU_BF536, 0x0001, AC_05000074},
271 1.1 christos
272 1.1 christos {"bf537", BFIN_CPU_BF537, 0x0003, AC_05000074},
273 1.1 christos {"bf537", BFIN_CPU_BF537, 0x0002, AC_05000074},
274 1.1 christos {"bf537", BFIN_CPU_BF537, 0x0001, AC_05000074},
275 1.1 christos
276 1.1 christos {"bf538", BFIN_CPU_BF538, 0x0005, AC_05000074},
277 1.1 christos {"bf538", BFIN_CPU_BF538, 0x0004, AC_05000074},
278 1.1 christos {"bf538", BFIN_CPU_BF538, 0x0003, AC_05000074},
279 1.1 christos {"bf538", BFIN_CPU_BF538, 0x0002, AC_05000074},
280 1.1 christos
281 1.1 christos {"bf539", BFIN_CPU_BF539, 0x0005, AC_05000074},
282 1.1 christos {"bf539", BFIN_CPU_BF539, 0x0004, AC_05000074},
283 1.1 christos {"bf539", BFIN_CPU_BF539, 0x0003, AC_05000074},
284 1.1 christos {"bf539", BFIN_CPU_BF539, 0x0002, AC_05000074},
285 1.1 christos
286 1.1 christos {"bf542m", BFIN_CPU_BF542M, 0x0003, AC_05000074},
287 1.1 christos
288 1.1 christos {"bf542", BFIN_CPU_BF542, 0x0004, AC_05000074},
289 1.1 christos {"bf542", BFIN_CPU_BF542, 0x0002, AC_05000074},
290 1.1 christos {"bf542", BFIN_CPU_BF542, 0x0001, AC_05000074},
291 1.1 christos {"bf542", BFIN_CPU_BF542, 0x0000, AC_05000074},
292 1.1 christos
293 1.1 christos {"bf544m", BFIN_CPU_BF544M, 0x0003, AC_05000074},
294 1.1 christos
295 1.1 christos {"bf544", BFIN_CPU_BF544, 0x0004, AC_05000074},
296 1.1 christos {"bf544", BFIN_CPU_BF544, 0x0002, AC_05000074},
297 1.1 christos {"bf544", BFIN_CPU_BF544, 0x0001, AC_05000074},
298 1.1 christos {"bf544", BFIN_CPU_BF544, 0x0000, AC_05000074},
299 1.1 christos
300 1.1 christos {"bf547m", BFIN_CPU_BF547M, 0x0003, AC_05000074},
301 1.1 christos
302 1.1 christos {"bf547", BFIN_CPU_BF547, 0x0004, AC_05000074},
303 1.1 christos {"bf547", BFIN_CPU_BF547, 0x0002, AC_05000074},
304 1.1 christos {"bf547", BFIN_CPU_BF547, 0x0001, AC_05000074},
305 1.1 christos {"bf547", BFIN_CPU_BF547, 0x0000, AC_05000074},
306 1.1 christos
307 1.1 christos {"bf548m", BFIN_CPU_BF548M, 0x0003, AC_05000074},
308 1.1 christos
309 1.1 christos {"bf548", BFIN_CPU_BF548, 0x0004, AC_05000074},
310 1.1 christos {"bf548", BFIN_CPU_BF548, 0x0002, AC_05000074},
311 1.1 christos {"bf548", BFIN_CPU_BF548, 0x0001, AC_05000074},
312 1.1 christos {"bf548", BFIN_CPU_BF548, 0x0000, AC_05000074},
313 1.1 christos
314 1.1 christos {"bf549m", BFIN_CPU_BF549M, 0x0003, AC_05000074},
315 1.1 christos
316 1.1 christos {"bf549", BFIN_CPU_BF549, 0x0004, AC_05000074},
317 1.1 christos {"bf549", BFIN_CPU_BF549, 0x0002, AC_05000074},
318 1.1 christos {"bf549", BFIN_CPU_BF549, 0x0001, AC_05000074},
319 1.1 christos {"bf549", BFIN_CPU_BF549, 0x0000, AC_05000074},
320 1.1 christos
321 1.1 christos {"bf561", BFIN_CPU_BF561, 0x0005, AC_05000074},
322 1.1 christos {"bf561", BFIN_CPU_BF561, 0x0003, AC_05000074},
323 1.1 christos {"bf561", BFIN_CPU_BF561, 0x0002, AC_05000074},
324 1.1 christos
325 1.1 christos {"bf592", BFIN_CPU_BF592, 0x0001, AC_05000074},
326 1.1 christos {"bf592", BFIN_CPU_BF592, 0x0000, AC_05000074},
327 1.1 christos };
328 1.1 christos
329 1.1 christos /* Define bfin-specific command-line options (there are none). */
330 1.1 christos const char *md_shortopts = "";
331 1.1 christos
332 1.1 christos #define OPTION_FDPIC (OPTION_MD_BASE)
333 1.1 christos #define OPTION_NOPIC (OPTION_MD_BASE + 1)
334 1.1 christos #define OPTION_MCPU (OPTION_MD_BASE + 2)
335 1.1 christos
336 1.1 christos struct option md_longopts[] =
337 1.1 christos {
338 1.1 christos { "mcpu", required_argument, NULL, OPTION_MCPU },
339 1.1 christos { "mfdpic", no_argument, NULL, OPTION_FDPIC },
340 1.1 christos { "mnopic", no_argument, NULL, OPTION_NOPIC },
341 1.1 christos { "mno-fdpic", no_argument, NULL, OPTION_NOPIC },
342 1.1 christos { NULL, no_argument, NULL, 0 },
343 1.1 christos };
344 1.1 christos
345 1.1 christos size_t md_longopts_size = sizeof (md_longopts);
346 1.1 christos
347 1.1 christos
348 1.1 christos int
349 1.1.1.3 christos md_parse_option (int c ATTRIBUTE_UNUSED, const char *arg ATTRIBUTE_UNUSED)
350 1.1 christos {
351 1.1 christos switch (c)
352 1.1 christos {
353 1.1 christos default:
354 1.1 christos return 0;
355 1.1 christos
356 1.1 christos case OPTION_MCPU:
357 1.1 christos {
358 1.1.1.3 christos const char *q;
359 1.1.1.3 christos unsigned int i;
360 1.1 christos
361 1.1.1.3 christos for (i = 0; i < ARRAY_SIZE (bfin_cpus); i++)
362 1.1 christos {
363 1.1.1.3 christos const char *p = bfin_cpus[i].name;
364 1.1 christos if (strncmp (arg, p, strlen (p)) == 0)
365 1.1 christos break;
366 1.1 christos }
367 1.1 christos
368 1.1.1.3 christos if (i == ARRAY_SIZE (bfin_cpus))
369 1.1 christos as_fatal ("-mcpu=%s is not valid", arg);
370 1.1 christos
371 1.1 christos bfin_cpu_type = bfin_cpus[i].type;
372 1.1 christos
373 1.1.1.3 christos q = arg + strlen (bfin_cpus[i].name);
374 1.1 christos
375 1.1 christos if (*q == '\0')
376 1.1 christos {
377 1.1 christos bfin_si_revision = bfin_cpus[i].si_revision;
378 1.1 christos bfin_anomaly_checks |= bfin_cpus[i].anomaly_checks;
379 1.1 christos }
380 1.1 christos else if (strcmp (q, "-none") == 0)
381 1.1 christos bfin_si_revision = -1;
382 1.1 christos else if (strcmp (q, "-any") == 0)
383 1.1 christos {
384 1.1 christos bfin_si_revision = 0xffff;
385 1.1.1.3 christos while (i < ARRAY_SIZE (bfin_cpus)
386 1.1.1.3 christos && bfin_cpus[i].type == bfin_cpu_type)
387 1.1 christos {
388 1.1 christos bfin_anomaly_checks |= bfin_cpus[i].anomaly_checks;
389 1.1 christos i++;
390 1.1 christos }
391 1.1 christos }
392 1.1 christos else
393 1.1 christos {
394 1.1 christos unsigned int si_major, si_minor;
395 1.1 christos int rev_len, n;
396 1.1 christos
397 1.1 christos rev_len = strlen (q);
398 1.1 christos
399 1.1 christos if (sscanf (q, "-%u.%u%n", &si_major, &si_minor, &n) != 2
400 1.1 christos || n != rev_len
401 1.1 christos || si_major > 0xff || si_minor > 0xff)
402 1.1 christos {
403 1.1 christos invalid_silicon_revision:
404 1.1 christos as_fatal ("-mcpu=%s has invalid silicon revision", arg);
405 1.1 christos }
406 1.1 christos
407 1.1 christos bfin_si_revision = (si_major << 8) | si_minor;
408 1.1 christos
409 1.1.1.3 christos while (i < ARRAY_SIZE (bfin_cpus)
410 1.1.1.3 christos && bfin_cpus[i].type == bfin_cpu_type
411 1.1 christos && bfin_cpus[i].si_revision != bfin_si_revision)
412 1.1 christos i++;
413 1.1 christos
414 1.1.1.3 christos if (i == ARRAY_SIZE (bfin_cpus)
415 1.1.1.3 christos || bfin_cpus[i].type != bfin_cpu_type)
416 1.1 christos goto invalid_silicon_revision;
417 1.1 christos
418 1.1 christos bfin_anomaly_checks |= bfin_cpus[i].anomaly_checks;
419 1.1 christos }
420 1.1 christos
421 1.1 christos break;
422 1.1 christos }
423 1.1 christos
424 1.1 christos case OPTION_FDPIC:
425 1.1 christos bfin_flags |= EF_BFIN_FDPIC;
426 1.1 christos bfin_pic_flag = "-mfdpic";
427 1.1 christos break;
428 1.1 christos
429 1.1 christos case OPTION_NOPIC:
430 1.1 christos bfin_flags &= ~(EF_BFIN_FDPIC);
431 1.1 christos bfin_pic_flag = 0;
432 1.1 christos break;
433 1.1 christos }
434 1.1 christos
435 1.1 christos return 1;
436 1.1 christos }
437 1.1 christos
438 1.1 christos void
439 1.1 christos md_show_usage (FILE * stream)
440 1.1 christos {
441 1.1 christos fprintf (stream, _(" Blackfin specific assembler options:\n"));
442 1.1 christos fprintf (stream, _(" -mcpu=<cpu[-sirevision]> specify the name of the target CPU\n"));
443 1.1 christos fprintf (stream, _(" -mfdpic assemble for the FDPIC ABI\n"));
444 1.1 christos fprintf (stream, _(" -mno-fdpic/-mnopic disable -mfdpic\n"));
445 1.1 christos }
446 1.1 christos
447 1.1 christos /* Perform machine-specific initializations. */
448 1.1 christos void
449 1.1.1.3 christos md_begin (void)
450 1.1 christos {
451 1.1 christos /* Set the ELF flags if desired. */
452 1.1 christos if (bfin_flags)
453 1.1 christos bfd_set_private_flags (stdoutput, bfin_flags);
454 1.1 christos
455 1.1 christos /* Set the default machine type. */
456 1.1 christos if (!bfd_set_arch_mach (stdoutput, bfd_arch_bfin, 0))
457 1.1 christos as_warn (_("Could not set architecture and machine."));
458 1.1 christos
459 1.1 christos /* Ensure that lines can begin with '(', for multiple
460 1.1 christos register stack pops. */
461 1.1 christos lex_type ['('] = LEX_BEGIN_NAME;
462 1.1 christos
463 1.1 christos #ifdef OBJ_ELF
464 1.1 christos record_alignment (text_section, 2);
465 1.1 christos record_alignment (data_section, 2);
466 1.1 christos record_alignment (bss_section, 2);
467 1.1 christos #endif
468 1.1 christos
469 1.1 christos errorf = stderr;
470 1.1 christos obstack_init (&mempool);
471 1.1 christos
472 1.1 christos #ifdef DEBUG
473 1.1 christos extern int debug_codeselection;
474 1.1 christos debug_codeselection = 1;
475 1.1 christos #endif
476 1.1 christos
477 1.1 christos last_insn_size = 0;
478 1.1 christos }
479 1.1 christos
480 1.1 christos /* Perform the main parsing, and assembly of the input here. Also,
481 1.1 christos call the required routines for alignment and fixups here.
482 1.1 christos This is called for every line that contains real assembly code. */
483 1.1 christos
484 1.1 christos void
485 1.1 christos md_assemble (char *line)
486 1.1 christos {
487 1.1 christos char *toP = 0;
488 1.1 christos int size, insn_size;
489 1.1 christos struct bfin_insn *tmp_insn;
490 1.1 christos size_t len;
491 1.1 christos static size_t buffer_len = 0;
492 1.1.1.3 christos static char *current_inputline;
493 1.1 christos parse_state state;
494 1.1 christos
495 1.1 christos len = strlen (line);
496 1.1 christos if (len + 2 > buffer_len)
497 1.1 christos {
498 1.1 christos buffer_len = len + 40;
499 1.1.1.3 christos current_inputline = XRESIZEVEC (char, current_inputline, buffer_len);
500 1.1 christos }
501 1.1 christos memcpy (current_inputline, line, len);
502 1.1 christos current_inputline[len] = ';';
503 1.1 christos current_inputline[len + 1] = '\0';
504 1.1 christos
505 1.1 christos state = parse (current_inputline);
506 1.1 christos if (state == NO_INSN_GENERATED)
507 1.1 christos return;
508 1.1 christos
509 1.1 christos for (insn_size = 0, tmp_insn = insn; tmp_insn; tmp_insn = tmp_insn->next)
510 1.1 christos if (!tmp_insn->reloc || !tmp_insn->exp->symbol)
511 1.1 christos insn_size += 2;
512 1.1 christos
513 1.1 christos if (insn_size)
514 1.1 christos toP = frag_more (insn_size);
515 1.1 christos
516 1.1 christos last_insn_size = insn_size;
517 1.1 christos
518 1.1 christos #ifdef DEBUG
519 1.1 christos printf ("INS:");
520 1.1 christos #endif
521 1.1 christos while (insn)
522 1.1 christos {
523 1.1 christos if (insn->reloc && insn->exp->symbol)
524 1.1 christos {
525 1.1 christos char *prev_toP = toP - 2;
526 1.1 christos switch (insn->reloc)
527 1.1 christos {
528 1.1 christos case BFD_RELOC_BFIN_24_PCREL_JUMP_L:
529 1.1 christos case BFD_RELOC_24_PCREL:
530 1.1 christos case BFD_RELOC_BFIN_16_LOW:
531 1.1 christos case BFD_RELOC_BFIN_16_HIGH:
532 1.1 christos size = 4;
533 1.1 christos break;
534 1.1 christos default:
535 1.1 christos size = 2;
536 1.1 christos }
537 1.1 christos
538 1.1 christos /* Following if condition checks for the arithmetic relocations.
539 1.1 christos If the case then it doesn't required to generate the code.
540 1.1 christos It has been assumed that, their ID will be contiguous. */
541 1.1 christos if ((BFD_ARELOC_BFIN_PUSH <= insn->reloc
542 1.1 christos && BFD_ARELOC_BFIN_COMP >= insn->reloc)
543 1.1 christos || insn->reloc == BFD_RELOC_BFIN_16_IMM)
544 1.1 christos {
545 1.1 christos size = 2;
546 1.1 christos }
547 1.1 christos if (insn->reloc == BFD_ARELOC_BFIN_CONST
548 1.1 christos || insn->reloc == BFD_ARELOC_BFIN_PUSH)
549 1.1 christos size = 4;
550 1.1 christos
551 1.1 christos fix_new (frag_now,
552 1.1 christos (prev_toP - frag_now->fr_literal),
553 1.1 christos size, insn->exp->symbol, insn->exp->value,
554 1.1 christos insn->pcrel, insn->reloc);
555 1.1 christos }
556 1.1 christos else
557 1.1 christos {
558 1.1 christos md_number_to_chars (toP, insn->value, 2);
559 1.1 christos toP += 2;
560 1.1 christos }
561 1.1 christos
562 1.1 christos #ifdef DEBUG
563 1.1 christos printf (" reloc :");
564 1.1 christos printf (" %02x%02x", ((unsigned char *) &insn->value)[0],
565 1.1 christos ((unsigned char *) &insn->value)[1]);
566 1.1 christos printf ("\n");
567 1.1 christos #endif
568 1.1 christos insn = insn->next;
569 1.1 christos }
570 1.1 christos #ifdef OBJ_ELF
571 1.1 christos dwarf2_emit_insn (insn_size);
572 1.1 christos #endif
573 1.1 christos
574 1.1 christos while (*line++ != '\0')
575 1.1 christos if (*line == '\n')
576 1.1 christos bump_line_counters ();
577 1.1 christos }
578 1.1 christos
579 1.1 christos /* Parse one line of instructions, and generate opcode for it.
580 1.1 christos To parse the line, YACC and LEX are used, because the instruction set
581 1.1 christos syntax doesn't confirm to the AT&T assembly syntax.
582 1.1 christos To call a YACC & LEX generated parser, we must provide the input via
583 1.1 christos a FILE stream, otherwise stdin is used by default. Below the input
584 1.1 christos to the function will be put into a temporary file, then the generated
585 1.1 christos parser uses the temporary file for parsing. */
586 1.1 christos
587 1.1 christos static parse_state
588 1.1 christos parse (char *line)
589 1.1 christos {
590 1.1 christos parse_state state;
591 1.1 christos YY_BUFFER_STATE buffstate;
592 1.1 christos
593 1.1 christos buffstate = yy_scan_string (line);
594 1.1 christos
595 1.1 christos /* our lex requires setting the start state to keyword
596 1.1 christos every line as the first word may be a keyword.
597 1.1 christos Fixes a bug where we could not have keywords as labels. */
598 1.1 christos set_start_state ();
599 1.1 christos
600 1.1 christos /* Call yyparse here. */
601 1.1 christos state = yyparse ();
602 1.1 christos if (state == SEMANTIC_ERROR)
603 1.1 christos {
604 1.1 christos as_bad (_("Parse failed."));
605 1.1 christos insn = 0;
606 1.1 christos }
607 1.1 christos
608 1.1 christos yy_delete_buffer (buffstate);
609 1.1 christos return state;
610 1.1 christos }
611 1.1 christos
612 1.1 christos /* We need to handle various expressions properly.
613 1.1 christos Such as, [SP--] = 34, concerned by md_assemble(). */
614 1.1 christos
615 1.1 christos void
616 1.1 christos md_operand (expressionS * expressionP)
617 1.1 christos {
618 1.1 christos if (*input_line_pointer == '[')
619 1.1 christos {
620 1.1 christos as_tsktsk ("We found a '['!");
621 1.1 christos input_line_pointer++;
622 1.1 christos expression (expressionP);
623 1.1 christos }
624 1.1 christos }
625 1.1 christos
626 1.1 christos /* Handle undefined symbols. */
627 1.1 christos symbolS *
628 1.1 christos md_undefined_symbol (char *name ATTRIBUTE_UNUSED)
629 1.1 christos {
630 1.1 christos return (symbolS *) 0;
631 1.1 christos }
632 1.1 christos
633 1.1 christos int
634 1.1 christos md_estimate_size_before_relax (fragS * fragP ATTRIBUTE_UNUSED,
635 1.1 christos segT segment ATTRIBUTE_UNUSED)
636 1.1 christos {
637 1.1 christos return 0;
638 1.1 christos }
639 1.1 christos
640 1.1 christos /* Convert from target byte order to host byte order. */
641 1.1 christos
642 1.1 christos static int
643 1.1 christos md_chars_to_number (char *val, int n)
644 1.1 christos {
645 1.1 christos int retval;
646 1.1 christos
647 1.1 christos for (retval = 0; n--;)
648 1.1 christos {
649 1.1 christos retval <<= 8;
650 1.1 christos retval |= val[n];
651 1.1 christos }
652 1.1 christos return retval;
653 1.1 christos }
654 1.1 christos
655 1.1 christos void
656 1.1 christos md_apply_fix (fixS *fixP, valueT *valueP, segT seg ATTRIBUTE_UNUSED)
657 1.1 christos {
658 1.1 christos char *where = fixP->fx_frag->fr_literal + fixP->fx_where;
659 1.1 christos
660 1.1 christos long value = *valueP;
661 1.1 christos long newval;
662 1.1 christos
663 1.1 christos switch (fixP->fx_r_type)
664 1.1 christos {
665 1.1 christos case BFD_RELOC_BFIN_GOT:
666 1.1 christos case BFD_RELOC_BFIN_GOT17M4:
667 1.1 christos case BFD_RELOC_BFIN_FUNCDESC_GOT17M4:
668 1.1 christos fixP->fx_no_overflow = 1;
669 1.1 christos newval = md_chars_to_number (where, 2);
670 1.1 christos newval |= 0x0 & 0x7f;
671 1.1 christos md_number_to_chars (where, newval, 2);
672 1.1 christos break;
673 1.1 christos
674 1.1 christos case BFD_RELOC_BFIN_10_PCREL:
675 1.1 christos if (!value)
676 1.1 christos break;
677 1.1 christos if (value < -1024 || value > 1022)
678 1.1 christos as_bad_where (fixP->fx_file, fixP->fx_line,
679 1.1 christos _("pcrel too far BFD_RELOC_BFIN_10"));
680 1.1 christos
681 1.1 christos /* 11 bit offset even numbered, so we remove right bit. */
682 1.1 christos value = value >> 1;
683 1.1 christos newval = md_chars_to_number (where, 2);
684 1.1 christos newval |= value & 0x03ff;
685 1.1 christos md_number_to_chars (where, newval, 2);
686 1.1 christos break;
687 1.1 christos
688 1.1 christos case BFD_RELOC_BFIN_12_PCREL_JUMP:
689 1.1 christos case BFD_RELOC_BFIN_12_PCREL_JUMP_S:
690 1.1 christos case BFD_RELOC_12_PCREL:
691 1.1 christos if (!value)
692 1.1 christos break;
693 1.1 christos
694 1.1 christos if (value < -4096 || value > 4094)
695 1.1 christos as_bad_where (fixP->fx_file, fixP->fx_line, _("pcrel too far BFD_RELOC_BFIN_12"));
696 1.1 christos /* 13 bit offset even numbered, so we remove right bit. */
697 1.1 christos value = value >> 1;
698 1.1 christos newval = md_chars_to_number (where, 2);
699 1.1 christos newval |= value & 0xfff;
700 1.1 christos md_number_to_chars (where, newval, 2);
701 1.1 christos break;
702 1.1 christos
703 1.1 christos case BFD_RELOC_BFIN_16_LOW:
704 1.1 christos case BFD_RELOC_BFIN_16_HIGH:
705 1.1 christos fixP->fx_done = FALSE;
706 1.1 christos break;
707 1.1 christos
708 1.1 christos case BFD_RELOC_BFIN_24_PCREL_JUMP_L:
709 1.1 christos case BFD_RELOC_BFIN_24_PCREL_CALL_X:
710 1.1 christos case BFD_RELOC_24_PCREL:
711 1.1 christos if (!value)
712 1.1 christos break;
713 1.1 christos
714 1.1 christos if (value < -16777216 || value > 16777214)
715 1.1 christos as_bad_where (fixP->fx_file, fixP->fx_line, _("pcrel too far BFD_RELOC_BFIN_24"));
716 1.1 christos
717 1.1 christos /* 25 bit offset even numbered, so we remove right bit. */
718 1.1 christos value = value >> 1;
719 1.1 christos value++;
720 1.1 christos
721 1.1 christos md_number_to_chars (where - 2, value >> 16, 1);
722 1.1 christos md_number_to_chars (where, value, 1);
723 1.1 christos md_number_to_chars (where + 1, value >> 8, 1);
724 1.1 christos break;
725 1.1 christos
726 1.1 christos case BFD_RELOC_BFIN_5_PCREL: /* LSETUP (a, b) : "a" */
727 1.1 christos if (!value)
728 1.1 christos break;
729 1.1 christos if (value < 4 || value > 30)
730 1.1 christos as_bad_where (fixP->fx_file, fixP->fx_line, _("pcrel too far BFD_RELOC_BFIN_5"));
731 1.1 christos value = value >> 1;
732 1.1 christos newval = md_chars_to_number (where, 1);
733 1.1 christos newval = (newval & 0xf0) | (value & 0xf);
734 1.1 christos md_number_to_chars (where, newval, 1);
735 1.1 christos break;
736 1.1 christos
737 1.1 christos case BFD_RELOC_BFIN_11_PCREL: /* LSETUP (a, b) : "b" */
738 1.1 christos if (!value)
739 1.1 christos break;
740 1.1 christos value += 2;
741 1.1 christos if (value < 4 || value > 2046)
742 1.1 christos as_bad_where (fixP->fx_file, fixP->fx_line, _("pcrel too far BFD_RELOC_BFIN_11_PCREL"));
743 1.1 christos /* 11 bit unsigned even, so we remove right bit. */
744 1.1 christos value = value >> 1;
745 1.1 christos newval = md_chars_to_number (where, 2);
746 1.1 christos newval |= value & 0x03ff;
747 1.1 christos md_number_to_chars (where, newval, 2);
748 1.1 christos break;
749 1.1 christos
750 1.1 christos case BFD_RELOC_8:
751 1.1 christos if (value < -0x80 || value >= 0x7f)
752 1.1 christos as_bad_where (fixP->fx_file, fixP->fx_line, _("rel too far BFD_RELOC_8"));
753 1.1 christos md_number_to_chars (where, value, 1);
754 1.1 christos break;
755 1.1 christos
756 1.1 christos case BFD_RELOC_BFIN_16_IMM:
757 1.1 christos case BFD_RELOC_16:
758 1.1 christos if (value < -0x8000 || value >= 0x7fff)
759 1.1 christos as_bad_where (fixP->fx_file, fixP->fx_line, _("rel too far BFD_RELOC_16"));
760 1.1 christos md_number_to_chars (where, value, 2);
761 1.1 christos break;
762 1.1 christos
763 1.1 christos case BFD_RELOC_32:
764 1.1 christos md_number_to_chars (where, value, 4);
765 1.1 christos break;
766 1.1 christos
767 1.1 christos case BFD_RELOC_BFIN_PLTPC:
768 1.1 christos md_number_to_chars (where, value, 2);
769 1.1 christos break;
770 1.1 christos
771 1.1 christos case BFD_RELOC_BFIN_FUNCDESC:
772 1.1 christos case BFD_RELOC_VTABLE_INHERIT:
773 1.1 christos case BFD_RELOC_VTABLE_ENTRY:
774 1.1 christos fixP->fx_done = FALSE;
775 1.1 christos break;
776 1.1 christos
777 1.1 christos default:
778 1.1 christos if ((BFD_ARELOC_BFIN_PUSH > fixP->fx_r_type) || (BFD_ARELOC_BFIN_COMP < fixP->fx_r_type))
779 1.1 christos {
780 1.1 christos fprintf (stderr, "Relocation %d not handled in gas." " Contact support.\n", fixP->fx_r_type);
781 1.1 christos return;
782 1.1 christos }
783 1.1 christos }
784 1.1 christos
785 1.1 christos if (!fixP->fx_addsy)
786 1.1 christos fixP->fx_done = TRUE;
787 1.1 christos
788 1.1 christos }
789 1.1 christos
790 1.1 christos /* Round up a section size to the appropriate boundary. */
791 1.1 christos valueT
792 1.1.1.3 christos md_section_align (segT segment, valueT size)
793 1.1 christos {
794 1.1 christos int boundary = bfd_get_section_alignment (stdoutput, segment);
795 1.1.1.2 christos return ((size + (1 << boundary) - 1) & -(1 << boundary));
796 1.1 christos }
797 1.1 christos
798 1.1 christos
799 1.1.1.3 christos const char *
800 1.1 christos md_atof (int type, char * litP, int * sizeP)
801 1.1 christos {
802 1.1 christos return ieee_md_atof (type, litP, sizeP, FALSE);
803 1.1 christos }
804 1.1 christos
805 1.1 christos
806 1.1 christos /* If while processing a fixup, a reloc really needs to be created
807 1.1 christos then it is done here. */
808 1.1 christos
809 1.1 christos arelent *
810 1.1.1.3 christos tc_gen_reloc (asection *seg ATTRIBUTE_UNUSED, fixS *fixp)
811 1.1 christos {
812 1.1 christos arelent *reloc;
813 1.1 christos
814 1.1.1.3 christos reloc = XNEW (arelent);
815 1.1.1.3 christos reloc->sym_ptr_ptr = XNEW (asymbol *);
816 1.1 christos *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
817 1.1 christos reloc->address = fixp->fx_frag->fr_address + fixp->fx_where;
818 1.1 christos
819 1.1 christos reloc->addend = fixp->fx_offset;
820 1.1 christos reloc->howto = bfd_reloc_type_lookup (stdoutput, fixp->fx_r_type);
821 1.1 christos
822 1.1 christos if (reloc->howto == (reloc_howto_type *) NULL)
823 1.1 christos {
824 1.1 christos as_bad_where (fixp->fx_file, fixp->fx_line,
825 1.1 christos /* xgettext:c-format. */
826 1.1 christos _("reloc %d not supported by object file format"),
827 1.1 christos (int) fixp->fx_r_type);
828 1.1 christos
829 1.1 christos xfree (reloc);
830 1.1 christos
831 1.1 christos return NULL;
832 1.1 christos }
833 1.1 christos
834 1.1 christos return reloc;
835 1.1 christos }
836 1.1 christos
837 1.1 christos /* The location from which a PC relative jump should be calculated,
838 1.1 christos given a PC relative reloc. */
839 1.1 christos
840 1.1 christos long
841 1.1.1.3 christos md_pcrel_from_section (fixS *fixP, segT sec)
842 1.1 christos {
843 1.1 christos if (fixP->fx_addsy != (symbolS *) NULL
844 1.1 christos && (!S_IS_DEFINED (fixP->fx_addsy)
845 1.1 christos || S_GET_SEGMENT (fixP->fx_addsy) != sec))
846 1.1 christos {
847 1.1 christos /* The symbol is undefined (or is defined but not in this section).
848 1.1 christos Let the linker figure it out. */
849 1.1 christos return 0;
850 1.1 christos }
851 1.1 christos return fixP->fx_frag->fr_address + fixP->fx_where;
852 1.1 christos }
853 1.1 christos
854 1.1 christos /* Return true if the fix can be handled by GAS, false if it must
855 1.1 christos be passed through to the linker. */
856 1.1 christos
857 1.1 christos bfd_boolean
858 1.1 christos bfin_fix_adjustable (fixS *fixP)
859 1.1 christos {
860 1.1 christos switch (fixP->fx_r_type)
861 1.1 christos {
862 1.1 christos /* Adjust_reloc_syms doesn't know about the GOT. */
863 1.1 christos case BFD_RELOC_BFIN_GOT:
864 1.1 christos case BFD_RELOC_BFIN_PLTPC:
865 1.1 christos /* We need the symbol name for the VTABLE entries. */
866 1.1 christos case BFD_RELOC_VTABLE_INHERIT:
867 1.1 christos case BFD_RELOC_VTABLE_ENTRY:
868 1.1 christos return 0;
869 1.1 christos
870 1.1 christos default:
871 1.1 christos return 1;
872 1.1 christos }
873 1.1 christos }
874 1.1 christos
875 1.1 christos /* Special extra functions that help bfin-parse.y perform its job. */
876 1.1 christos
877 1.1 christos struct obstack mempool;
878 1.1 christos
879 1.1 christos INSTR_T
880 1.1 christos conscode (INSTR_T head, INSTR_T tail)
881 1.1 christos {
882 1.1 christos if (!head)
883 1.1 christos return tail;
884 1.1 christos head->next = tail;
885 1.1 christos return head;
886 1.1 christos }
887 1.1 christos
888 1.1 christos INSTR_T
889 1.1 christos conctcode (INSTR_T head, INSTR_T tail)
890 1.1 christos {
891 1.1 christos INSTR_T temp = (head);
892 1.1 christos if (!head)
893 1.1 christos return tail;
894 1.1 christos while (temp->next)
895 1.1 christos temp = temp->next;
896 1.1 christos temp->next = tail;
897 1.1 christos
898 1.1 christos return head;
899 1.1 christos }
900 1.1 christos
901 1.1 christos INSTR_T
902 1.1 christos note_reloc (INSTR_T code, Expr_Node * symbol, int reloc, int pcrel)
903 1.1 christos {
904 1.1 christos /* Assert that the symbol is not an operator. */
905 1.1 christos gas_assert (symbol->type == Expr_Node_Reloc);
906 1.1 christos
907 1.1 christos return note_reloc1 (code, symbol->value.s_value, reloc, pcrel);
908 1.1 christos
909 1.1 christos }
910 1.1 christos
911 1.1 christos INSTR_T
912 1.1 christos note_reloc1 (INSTR_T code, const char *symbol, int reloc, int pcrel)
913 1.1 christos {
914 1.1 christos code->reloc = reloc;
915 1.1 christos code->exp = mkexpr (0, symbol_find_or_make (symbol));
916 1.1 christos code->pcrel = pcrel;
917 1.1 christos return code;
918 1.1 christos }
919 1.1 christos
920 1.1 christos INSTR_T
921 1.1 christos note_reloc2 (INSTR_T code, const char *symbol, int reloc, int value, int pcrel)
922 1.1 christos {
923 1.1 christos code->reloc = reloc;
924 1.1 christos code->exp = mkexpr (value, symbol_find_or_make (symbol));
925 1.1 christos code->pcrel = pcrel;
926 1.1 christos return code;
927 1.1 christos }
928 1.1 christos
929 1.1 christos INSTR_T
930 1.1 christos gencode (unsigned long x)
931 1.1 christos {
932 1.1.1.3 christos INSTR_T cell = XOBNEW (&mempool, struct bfin_insn);
933 1.1 christos memset (cell, 0, sizeof (struct bfin_insn));
934 1.1 christos cell->value = (x);
935 1.1 christos return cell;
936 1.1 christos }
937 1.1 christos
938 1.1 christos int reloc;
939 1.1 christos int ninsns;
940 1.1 christos int count_insns;
941 1.1 christos
942 1.1 christos static void *
943 1.1.1.2 christos allocate (size_t n)
944 1.1 christos {
945 1.1 christos return obstack_alloc (&mempool, n);
946 1.1 christos }
947 1.1 christos
948 1.1 christos Expr_Node *
949 1.1 christos Expr_Node_Create (Expr_Node_Type type,
950 1.1 christos Expr_Node_Value value,
951 1.1 christos Expr_Node *Left_Child,
952 1.1 christos Expr_Node *Right_Child)
953 1.1 christos {
954 1.1 christos
955 1.1 christos
956 1.1 christos Expr_Node *node = (Expr_Node *) allocate (sizeof (Expr_Node));
957 1.1 christos node->type = type;
958 1.1 christos node->value = value;
959 1.1 christos node->Left_Child = Left_Child;
960 1.1 christos node->Right_Child = Right_Child;
961 1.1 christos return node;
962 1.1 christos }
963 1.1 christos
964 1.1 christos static const char *con = ".__constant";
965 1.1 christos static const char *op = ".__operator";
966 1.1 christos static INSTR_T Expr_Node_Gen_Reloc_R (Expr_Node * head);
967 1.1 christos INSTR_T Expr_Node_Gen_Reloc (Expr_Node *head, int parent_reloc);
968 1.1 christos
969 1.1 christos INSTR_T
970 1.1 christos Expr_Node_Gen_Reloc (Expr_Node * head, int parent_reloc)
971 1.1 christos {
972 1.1 christos /* Top level reloction expression generator VDSP style.
973 1.1 christos If the relocation is just by itself, generate one item
974 1.1 christos else generate this convoluted expression. */
975 1.1 christos
976 1.1 christos INSTR_T note = NULL_CODE;
977 1.1 christos INSTR_T note1 = NULL_CODE;
978 1.1 christos int pcrel = 1; /* Is the parent reloc pcrelative?
979 1.1 christos This calculation here and HOWTO should match. */
980 1.1 christos
981 1.1 christos if (parent_reloc)
982 1.1 christos {
983 1.1 christos /* If it's 32 bit quantity then 16bit code needs to be added. */
984 1.1 christos int value = 0;
985 1.1 christos
986 1.1 christos if (head->type == Expr_Node_Constant)
987 1.1 christos {
988 1.1 christos /* If note1 is not null code, we have to generate a right
989 1.1 christos aligned value for the constant. Otherwise the reloc is
990 1.1 christos a part of the basic command and the yacc file
991 1.1 christos generates this. */
992 1.1 christos value = head->value.i_value;
993 1.1 christos }
994 1.1 christos switch (parent_reloc)
995 1.1 christos {
996 1.1 christos /* Some relocations will need to allocate extra words. */
997 1.1 christos case BFD_RELOC_BFIN_16_IMM:
998 1.1 christos case BFD_RELOC_BFIN_16_LOW:
999 1.1 christos case BFD_RELOC_BFIN_16_HIGH:
1000 1.1 christos note1 = conscode (gencode (value), NULL_CODE);
1001 1.1 christos pcrel = 0;
1002 1.1 christos break;
1003 1.1 christos case BFD_RELOC_BFIN_PLTPC:
1004 1.1 christos note1 = conscode (gencode (value), NULL_CODE);
1005 1.1 christos pcrel = 0;
1006 1.1 christos break;
1007 1.1 christos case BFD_RELOC_16:
1008 1.1 christos case BFD_RELOC_BFIN_GOT:
1009 1.1 christos case BFD_RELOC_BFIN_GOT17M4:
1010 1.1 christos case BFD_RELOC_BFIN_FUNCDESC_GOT17M4:
1011 1.1 christos note1 = conscode (gencode (value), NULL_CODE);
1012 1.1 christos pcrel = 0;
1013 1.1 christos break;
1014 1.1 christos case BFD_RELOC_24_PCREL:
1015 1.1 christos case BFD_RELOC_BFIN_24_PCREL_JUMP_L:
1016 1.1 christos case BFD_RELOC_BFIN_24_PCREL_CALL_X:
1017 1.1 christos /* These offsets are even numbered pcrel. */
1018 1.1 christos note1 = conscode (gencode (value >> 1), NULL_CODE);
1019 1.1 christos break;
1020 1.1 christos default:
1021 1.1 christos note1 = NULL_CODE;
1022 1.1 christos }
1023 1.1 christos }
1024 1.1 christos if (head->type == Expr_Node_Constant)
1025 1.1 christos note = note1;
1026 1.1 christos else if (head->type == Expr_Node_Reloc)
1027 1.1 christos {
1028 1.1 christos note = note_reloc1 (gencode (0), head->value.s_value, parent_reloc, pcrel);
1029 1.1 christos if (note1 != NULL_CODE)
1030 1.1 christos note = conscode (note1, note);
1031 1.1 christos }
1032 1.1 christos else if (head->type == Expr_Node_Binop
1033 1.1 christos && (head->value.op_value == Expr_Op_Type_Add
1034 1.1 christos || head->value.op_value == Expr_Op_Type_Sub)
1035 1.1 christos && head->Left_Child->type == Expr_Node_Reloc
1036 1.1 christos && head->Right_Child->type == Expr_Node_Constant)
1037 1.1 christos {
1038 1.1 christos int val = head->Right_Child->value.i_value;
1039 1.1 christos if (head->value.op_value == Expr_Op_Type_Sub)
1040 1.1 christos val = -val;
1041 1.1 christos note = conscode (note_reloc2 (gencode (0), head->Left_Child->value.s_value,
1042 1.1 christos parent_reloc, val, 0),
1043 1.1 christos NULL_CODE);
1044 1.1 christos if (note1 != NULL_CODE)
1045 1.1 christos note = conscode (note1, note);
1046 1.1 christos }
1047 1.1 christos else
1048 1.1 christos {
1049 1.1 christos /* Call the recursive function. */
1050 1.1 christos note = note_reloc1 (gencode (0), op, parent_reloc, pcrel);
1051 1.1 christos if (note1 != NULL_CODE)
1052 1.1 christos note = conscode (note1, note);
1053 1.1 christos note = conctcode (Expr_Node_Gen_Reloc_R (head), note);
1054 1.1 christos }
1055 1.1 christos return note;
1056 1.1 christos }
1057 1.1 christos
1058 1.1 christos static INSTR_T
1059 1.1 christos Expr_Node_Gen_Reloc_R (Expr_Node * head)
1060 1.1 christos {
1061 1.1 christos
1062 1.1 christos INSTR_T note = 0;
1063 1.1 christos INSTR_T note1 = 0;
1064 1.1 christos
1065 1.1 christos switch (head->type)
1066 1.1 christos {
1067 1.1 christos case Expr_Node_Constant:
1068 1.1 christos note = conscode (note_reloc2 (gencode (0), con, BFD_ARELOC_BFIN_CONST, head->value.i_value, 0), NULL_CODE);
1069 1.1 christos break;
1070 1.1 christos case Expr_Node_Reloc:
1071 1.1 christos note = conscode (note_reloc (gencode (0), head, BFD_ARELOC_BFIN_PUSH, 0), NULL_CODE);
1072 1.1 christos break;
1073 1.1 christos case Expr_Node_Binop:
1074 1.1 christos note1 = conctcode (Expr_Node_Gen_Reloc_R (head->Left_Child), Expr_Node_Gen_Reloc_R (head->Right_Child));
1075 1.1 christos switch (head->value.op_value)
1076 1.1 christos {
1077 1.1 christos case Expr_Op_Type_Add:
1078 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_ADD, 0), NULL_CODE));
1079 1.1 christos break;
1080 1.1 christos case Expr_Op_Type_Sub:
1081 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_SUB, 0), NULL_CODE));
1082 1.1 christos break;
1083 1.1 christos case Expr_Op_Type_Mult:
1084 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_MULT, 0), NULL_CODE));
1085 1.1 christos break;
1086 1.1 christos case Expr_Op_Type_Div:
1087 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_DIV, 0), NULL_CODE));
1088 1.1 christos break;
1089 1.1 christos case Expr_Op_Type_Mod:
1090 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_MOD, 0), NULL_CODE));
1091 1.1 christos break;
1092 1.1 christos case Expr_Op_Type_Lshift:
1093 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_LSHIFT, 0), NULL_CODE));
1094 1.1 christos break;
1095 1.1 christos case Expr_Op_Type_Rshift:
1096 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_RSHIFT, 0), NULL_CODE));
1097 1.1 christos break;
1098 1.1 christos case Expr_Op_Type_BAND:
1099 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_AND, 0), NULL_CODE));
1100 1.1 christos break;
1101 1.1 christos case Expr_Op_Type_BOR:
1102 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_OR, 0), NULL_CODE));
1103 1.1 christos break;
1104 1.1 christos case Expr_Op_Type_BXOR:
1105 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_XOR, 0), NULL_CODE));
1106 1.1 christos break;
1107 1.1 christos case Expr_Op_Type_LAND:
1108 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_LAND, 0), NULL_CODE));
1109 1.1 christos break;
1110 1.1 christos case Expr_Op_Type_LOR:
1111 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_LOR, 0), NULL_CODE));
1112 1.1 christos break;
1113 1.1 christos default:
1114 1.1 christos fprintf (stderr, "%s:%d:Unknown operator found for arithmetic" " relocation", __FILE__, __LINE__);
1115 1.1 christos
1116 1.1 christos
1117 1.1 christos }
1118 1.1 christos break;
1119 1.1 christos case Expr_Node_Unop:
1120 1.1 christos note1 = conscode (Expr_Node_Gen_Reloc_R (head->Left_Child), NULL_CODE);
1121 1.1 christos switch (head->value.op_value)
1122 1.1 christos {
1123 1.1 christos case Expr_Op_Type_NEG:
1124 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_NEG, 0), NULL_CODE));
1125 1.1 christos break;
1126 1.1 christos case Expr_Op_Type_COMP:
1127 1.1 christos note = conctcode (note1, conscode (note_reloc1 (gencode (0), op, BFD_ARELOC_BFIN_COMP, 0), NULL_CODE));
1128 1.1 christos break;
1129 1.1 christos default:
1130 1.1 christos fprintf (stderr, "%s:%d:Unknown operator found for arithmetic" " relocation", __FILE__, __LINE__);
1131 1.1 christos }
1132 1.1 christos break;
1133 1.1 christos default:
1134 1.1 christos fprintf (stderr, "%s:%d:Unknown node expression found during " "arithmetic relocation generation", __FILE__, __LINE__);
1135 1.1 christos }
1136 1.1 christos return note;
1137 1.1 christos }
1138 1.1 christos
1139 1.1 christos /* Blackfin opcode generation. */
1141 1.1 christos
1142 1.1 christos /* These functions are called by the generated parser
1143 1.1 christos (from bfin-parse.y), the register type classification
1144 1.1 christos happens in bfin-lex.l. */
1145 1.1 christos
1146 1.1 christos #include "bfin-aux.h"
1147 1.1 christos #include "opcode/bfin.h"
1148 1.1 christos
1149 1.1 christos #define INIT(t) t c_code = init_##t
1150 1.1 christos #define ASSIGN(x) c_code.opcode |= ((x & c_code.mask_##x)<<c_code.bits_##x)
1151 1.1 christos #define ASSIGNF(x,f) c_code.opcode |= ((x & c_code.mask_##f)<<c_code.bits_##f)
1152 1.1 christos #define ASSIGN_R(x) c_code.opcode |= (((x ? (x->regno & CODE_MASK) : 0) & c_code.mask_##x)<<c_code.bits_##x)
1153 1.1 christos
1154 1.1 christos #define HI(x) ((x >> 16) & 0xffff)
1155 1.1 christos #define LO(x) ((x ) & 0xffff)
1156 1.1 christos
1157 1.1 christos #define GROUP(x) ((x->regno & CLASS_MASK) >> 4)
1158 1.1 christos
1159 1.1 christos #define GEN_OPCODE32() \
1160 1.1 christos conscode (gencode (HI (c_code.opcode)), \
1161 1.1 christos conscode (gencode (LO (c_code.opcode)), NULL_CODE))
1162 1.1 christos
1163 1.1 christos #define GEN_OPCODE16() \
1164 1.1 christos conscode (gencode (c_code.opcode), NULL_CODE)
1165 1.1 christos
1166 1.1 christos
1167 1.1 christos /* 32 BIT INSTRUCTIONS. */
1168 1.1 christos
1169 1.1 christos
1170 1.1 christos /* DSP32 instruction generation. */
1171 1.1 christos
1172 1.1 christos INSTR_T
1173 1.1 christos bfin_gen_dsp32mac (int op1, int MM, int mmod, int w1, int P,
1174 1.1 christos int h01, int h11, int h00, int h10, int op0,
1175 1.1 christos REG_T dst, REG_T src0, REG_T src1, int w0)
1176 1.1 christos {
1177 1.1 christos INIT (DSP32Mac);
1178 1.1 christos
1179 1.1 christos ASSIGN (op0);
1180 1.1 christos ASSIGN (op1);
1181 1.1 christos ASSIGN (MM);
1182 1.1 christos ASSIGN (mmod);
1183 1.1 christos ASSIGN (w0);
1184 1.1 christos ASSIGN (w1);
1185 1.1 christos ASSIGN (h01);
1186 1.1 christos ASSIGN (h11);
1187 1.1 christos ASSIGN (h00);
1188 1.1 christos ASSIGN (h10);
1189 1.1 christos ASSIGN (P);
1190 1.1 christos
1191 1.1 christos /* If we have full reg assignments, mask out LSB to encode
1192 1.1 christos single or simultaneous even/odd register moves. */
1193 1.1 christos if (P)
1194 1.1 christos {
1195 1.1 christos dst->regno &= 0x06;
1196 1.1 christos }
1197 1.1 christos
1198 1.1 christos ASSIGN_R (dst);
1199 1.1 christos ASSIGN_R (src0);
1200 1.1 christos ASSIGN_R (src1);
1201 1.1 christos
1202 1.1 christos return GEN_OPCODE32 ();
1203 1.1 christos }
1204 1.1 christos
1205 1.1 christos INSTR_T
1206 1.1 christos bfin_gen_dsp32mult (int op1, int MM, int mmod, int w1, int P,
1207 1.1 christos int h01, int h11, int h00, int h10, int op0,
1208 1.1 christos REG_T dst, REG_T src0, REG_T src1, int w0)
1209 1.1 christos {
1210 1.1 christos INIT (DSP32Mult);
1211 1.1 christos
1212 1.1 christos ASSIGN (op0);
1213 1.1 christos ASSIGN (op1);
1214 1.1 christos ASSIGN (MM);
1215 1.1 christos ASSIGN (mmod);
1216 1.1 christos ASSIGN (w0);
1217 1.1 christos ASSIGN (w1);
1218 1.1 christos ASSIGN (h01);
1219 1.1 christos ASSIGN (h11);
1220 1.1 christos ASSIGN (h00);
1221 1.1 christos ASSIGN (h10);
1222 1.1 christos ASSIGN (P);
1223 1.1 christos
1224 1.1 christos if (P)
1225 1.1 christos {
1226 1.1 christos dst->regno &= 0x06;
1227 1.1 christos }
1228 1.1 christos
1229 1.1 christos ASSIGN_R (dst);
1230 1.1 christos ASSIGN_R (src0);
1231 1.1 christos ASSIGN_R (src1);
1232 1.1 christos
1233 1.1 christos return GEN_OPCODE32 ();
1234 1.1 christos }
1235 1.1 christos
1236 1.1 christos INSTR_T
1237 1.1 christos bfin_gen_dsp32alu (int HL, int aopcde, int aop, int s, int x,
1238 1.1 christos REG_T dst0, REG_T dst1, REG_T src0, REG_T src1)
1239 1.1 christos {
1240 1.1 christos INIT (DSP32Alu);
1241 1.1 christos
1242 1.1 christos ASSIGN (HL);
1243 1.1 christos ASSIGN (aopcde);
1244 1.1 christos ASSIGN (aop);
1245 1.1 christos ASSIGN (s);
1246 1.1 christos ASSIGN (x);
1247 1.1 christos ASSIGN_R (dst0);
1248 1.1 christos ASSIGN_R (dst1);
1249 1.1 christos ASSIGN_R (src0);
1250 1.1 christos ASSIGN_R (src1);
1251 1.1 christos
1252 1.1 christos return GEN_OPCODE32 ();
1253 1.1 christos }
1254 1.1 christos
1255 1.1 christos INSTR_T
1256 1.1 christos bfin_gen_dsp32shift (int sopcde, REG_T dst0, REG_T src0,
1257 1.1 christos REG_T src1, int sop, int HLs)
1258 1.1 christos {
1259 1.1 christos INIT (DSP32Shift);
1260 1.1 christos
1261 1.1 christos ASSIGN (sopcde);
1262 1.1 christos ASSIGN (sop);
1263 1.1 christos ASSIGN (HLs);
1264 1.1 christos
1265 1.1 christos ASSIGN_R (dst0);
1266 1.1 christos ASSIGN_R (src0);
1267 1.1 christos ASSIGN_R (src1);
1268 1.1 christos
1269 1.1 christos return GEN_OPCODE32 ();
1270 1.1 christos }
1271 1.1 christos
1272 1.1 christos INSTR_T
1273 1.1 christos bfin_gen_dsp32shiftimm (int sopcde, REG_T dst0, int immag,
1274 1.1 christos REG_T src1, int sop, int HLs)
1275 1.1 christos {
1276 1.1 christos INIT (DSP32ShiftImm);
1277 1.1 christos
1278 1.1 christos ASSIGN (sopcde);
1279 1.1 christos ASSIGN (sop);
1280 1.1 christos ASSIGN (HLs);
1281 1.1 christos
1282 1.1 christos ASSIGN_R (dst0);
1283 1.1 christos ASSIGN (immag);
1284 1.1 christos ASSIGN_R (src1);
1285 1.1 christos
1286 1.1 christos return GEN_OPCODE32 ();
1287 1.1 christos }
1288 1.1 christos
1289 1.1 christos /* LOOP SETUP. */
1290 1.1 christos
1291 1.1 christos INSTR_T
1292 1.1 christos bfin_gen_loopsetup (Expr_Node * psoffset, REG_T c, int rop,
1293 1.1 christos Expr_Node * peoffset, REG_T reg)
1294 1.1 christos {
1295 1.1 christos int soffset, eoffset;
1296 1.1 christos INIT (LoopSetup);
1297 1.1 christos
1298 1.1 christos soffset = (EXPR_VALUE (psoffset) >> 1);
1299 1.1 christos ASSIGN (soffset);
1300 1.1 christos eoffset = (EXPR_VALUE (peoffset) >> 1);
1301 1.1 christos ASSIGN (eoffset);
1302 1.1 christos ASSIGN (rop);
1303 1.1 christos ASSIGN_R (c);
1304 1.1 christos ASSIGN_R (reg);
1305 1.1 christos
1306 1.1 christos return
1307 1.1 christos conscode (gencode (HI (c_code.opcode)),
1308 1.1 christos conctcode (Expr_Node_Gen_Reloc (psoffset, BFD_RELOC_BFIN_5_PCREL),
1309 1.1 christos conctcode (gencode (LO (c_code.opcode)), Expr_Node_Gen_Reloc (peoffset, BFD_RELOC_BFIN_11_PCREL))));
1310 1.1 christos
1311 1.1 christos }
1312 1.1 christos
1313 1.1 christos /* Call, Link. */
1314 1.1 christos
1315 1.1 christos INSTR_T
1316 1.1 christos bfin_gen_calla (Expr_Node * addr, int S)
1317 1.1 christos {
1318 1.1 christos int val;
1319 1.1 christos int high_val;
1320 1.1 christos int rel = 0;
1321 1.1 christos INIT (CALLa);
1322 1.1 christos
1323 1.1 christos switch(S){
1324 1.1 christos case 0 : rel = BFD_RELOC_BFIN_24_PCREL_JUMP_L; break;
1325 1.1 christos case 1 : rel = BFD_RELOC_24_PCREL; break;
1326 1.1 christos case 2 : rel = BFD_RELOC_BFIN_PLTPC; break;
1327 1.1 christos default : break;
1328 1.1 christos }
1329 1.1 christos
1330 1.1 christos ASSIGN (S);
1331 1.1 christos
1332 1.1 christos val = EXPR_VALUE (addr) >> 1;
1333 1.1 christos high_val = val >> 16;
1334 1.1 christos
1335 1.1 christos return conscode (gencode (HI (c_code.opcode) | (high_val & 0xff)),
1336 1.1 christos Expr_Node_Gen_Reloc (addr, rel));
1337 1.1 christos }
1338 1.1 christos
1339 1.1 christos INSTR_T
1340 1.1 christos bfin_gen_linkage (int R, int framesize)
1341 1.1 christos {
1342 1.1 christos INIT (Linkage);
1343 1.1 christos
1344 1.1 christos ASSIGN (R);
1345 1.1 christos ASSIGN (framesize);
1346 1.1 christos
1347 1.1 christos return GEN_OPCODE32 ();
1348 1.1 christos }
1349 1.1 christos
1350 1.1 christos
1351 1.1 christos /* Load and Store. */
1352 1.1 christos
1353 1.1 christos INSTR_T
1354 1.1 christos bfin_gen_ldimmhalf (REG_T reg, int H, int S, int Z, Expr_Node * phword, int rel)
1355 1.1 christos {
1356 1.1 christos int grp, hword;
1357 1.1 christos unsigned val = EXPR_VALUE (phword);
1358 1.1 christos INIT (LDIMMhalf);
1359 1.1 christos
1360 1.1 christos ASSIGN (H);
1361 1.1 christos ASSIGN (S);
1362 1.1 christos ASSIGN (Z);
1363 1.1 christos
1364 1.1 christos ASSIGN_R (reg);
1365 1.1 christos grp = (GROUP (reg));
1366 1.1 christos ASSIGN (grp);
1367 1.1 christos if (rel == 2)
1368 1.1 christos {
1369 1.1 christos return conscode (gencode (HI (c_code.opcode)), Expr_Node_Gen_Reloc (phword, BFD_RELOC_BFIN_16_IMM));
1370 1.1 christos }
1371 1.1 christos else if (rel == 1)
1372 1.1 christos {
1373 1.1 christos return conscode (gencode (HI (c_code.opcode)), Expr_Node_Gen_Reloc (phword, IS_H (*reg) ? BFD_RELOC_BFIN_16_HIGH : BFD_RELOC_BFIN_16_LOW));
1374 1.1 christos }
1375 1.1 christos else
1376 1.1 christos {
1377 1.1 christos hword = val;
1378 1.1 christos ASSIGN (hword);
1379 1.1 christos }
1380 1.1 christos return GEN_OPCODE32 ();
1381 1.1 christos }
1382 1.1 christos
1383 1.1 christos INSTR_T
1384 1.1 christos bfin_gen_ldstidxi (REG_T ptr, REG_T reg, int W, int sz, int Z, Expr_Node * poffset)
1385 1.1 christos {
1386 1.1 christos INIT (LDSTidxI);
1387 1.1 christos
1388 1.1 christos if (!IS_PREG (*ptr) || (!IS_DREG (*reg) && !Z))
1389 1.1 christos {
1390 1.1 christos fprintf (stderr, "Warning: possible mixup of Preg/Dreg\n");
1391 1.1 christos return 0;
1392 1.1 christos }
1393 1.1 christos
1394 1.1 christos ASSIGN_R (ptr);
1395 1.1 christos ASSIGN_R (reg);
1396 1.1 christos ASSIGN (W);
1397 1.1 christos ASSIGN (sz);
1398 1.1 christos
1399 1.1 christos ASSIGN (Z);
1400 1.1 christos
1401 1.1 christos if (poffset->type != Expr_Node_Constant)
1402 1.1 christos {
1403 1.1 christos /* a GOT relocation such as R0 = [P5 + symbol@GOT] */
1404 1.1 christos /* distinguish between R0 = [P5 + symbol@GOT] and
1405 1.1 christos P5 = [P5 + _current_shared_library_p5_offset_]
1406 1.1 christos */
1407 1.1 christos if (poffset->type == Expr_Node_Reloc
1408 1.1 christos && !strcmp (poffset->value.s_value,
1409 1.1 christos "_current_shared_library_p5_offset_"))
1410 1.1 christos {
1411 1.1 christos return conscode (gencode (HI (c_code.opcode)),
1412 1.1 christos Expr_Node_Gen_Reloc(poffset, BFD_RELOC_16));
1413 1.1 christos }
1414 1.1 christos else if (poffset->type != Expr_Node_GOT_Reloc)
1415 1.1 christos abort ();
1416 1.1 christos
1417 1.1 christos return conscode (gencode (HI (c_code.opcode)),
1418 1.1 christos Expr_Node_Gen_Reloc(poffset->Left_Child,
1419 1.1 christos poffset->value.i_value));
1420 1.1 christos }
1421 1.1 christos else
1422 1.1 christos {
1423 1.1 christos int value, offset;
1424 1.1 christos switch (sz)
1425 1.1 christos { /* load/store access size */
1426 1.1 christos case 0: /* 32 bit */
1427 1.1 christos value = EXPR_VALUE (poffset) >> 2;
1428 1.1 christos break;
1429 1.1 christos case 1: /* 16 bit */
1430 1.1 christos value = EXPR_VALUE (poffset) >> 1;
1431 1.1 christos break;
1432 1.1 christos case 2: /* 8 bit */
1433 1.1 christos value = EXPR_VALUE (poffset);
1434 1.1 christos break;
1435 1.1 christos default:
1436 1.1 christos abort ();
1437 1.1 christos }
1438 1.1 christos
1439 1.1 christos offset = (value & 0xffff);
1440 1.1 christos ASSIGN (offset);
1441 1.1 christos return GEN_OPCODE32 ();
1442 1.1 christos }
1443 1.1 christos }
1444 1.1 christos
1445 1.1 christos
1446 1.1 christos INSTR_T
1447 1.1 christos bfin_gen_ldst (REG_T ptr, REG_T reg, int aop, int sz, int Z, int W)
1448 1.1 christos {
1449 1.1 christos INIT (LDST);
1450 1.1 christos
1451 1.1 christos if (!IS_PREG (*ptr) || (!IS_DREG (*reg) && !Z))
1452 1.1 christos {
1453 1.1 christos fprintf (stderr, "Warning: possible mixup of Preg/Dreg\n");
1454 1.1 christos return 0;
1455 1.1 christos }
1456 1.1 christos
1457 1.1 christos ASSIGN_R (ptr);
1458 1.1 christos ASSIGN_R (reg);
1459 1.1 christos ASSIGN (aop);
1460 1.1 christos ASSIGN (sz);
1461 1.1 christos ASSIGN (Z);
1462 1.1 christos ASSIGN (W);
1463 1.1 christos
1464 1.1 christos return GEN_OPCODE16 ();
1465 1.1 christos }
1466 1.1 christos
1467 1.1 christos INSTR_T
1468 1.1 christos bfin_gen_ldstii (REG_T ptr, REG_T reg, Expr_Node * poffset, int W, int opc)
1469 1.1 christos {
1470 1.1 christos int offset;
1471 1.1 christos int value = 0;
1472 1.1 christos INIT (LDSTii);
1473 1.1 christos
1474 1.1 christos if (!IS_PREG (*ptr))
1475 1.1 christos {
1476 1.1 christos fprintf (stderr, "Warning: possible mixup of Preg/Dreg\n");
1477 1.1 christos return 0;
1478 1.1 christos }
1479 1.1 christos
1480 1.1 christos switch (opc)
1481 1.1 christos {
1482 1.1 christos case 1:
1483 1.1 christos case 2:
1484 1.1 christos value = EXPR_VALUE (poffset) >> 1;
1485 1.1 christos break;
1486 1.1 christos case 0:
1487 1.1 christos case 3:
1488 1.1 christos value = EXPR_VALUE (poffset) >> 2;
1489 1.1 christos break;
1490 1.1 christos }
1491 1.1 christos
1492 1.1 christos ASSIGN_R (ptr);
1493 1.1 christos ASSIGN_R (reg);
1494 1.1 christos
1495 1.1 christos offset = value;
1496 1.1 christos ASSIGN (offset);
1497 1.1 christos ASSIGN (W);
1498 1.1 christos ASSIGNF (opc, op);
1499 1.1 christos
1500 1.1 christos return GEN_OPCODE16 ();
1501 1.1 christos }
1502 1.1 christos
1503 1.1 christos INSTR_T
1504 1.1 christos bfin_gen_ldstiifp (REG_T sreg, Expr_Node * poffset, int W)
1505 1.1 christos {
1506 1.1 christos /* Set bit 4 if it's a Preg. */
1507 1.1 christos int reg = (sreg->regno & CODE_MASK) | (IS_PREG (*sreg) ? 0x8 : 0x0);
1508 1.1 christos int offset = ((~(EXPR_VALUE (poffset) >> 2)) & 0x1f) + 1;
1509 1.1 christos INIT (LDSTiiFP);
1510 1.1 christos ASSIGN (reg);
1511 1.1 christos ASSIGN (offset);
1512 1.1 christos ASSIGN (W);
1513 1.1 christos
1514 1.1 christos return GEN_OPCODE16 ();
1515 1.1 christos }
1516 1.1 christos
1517 1.1 christos INSTR_T
1518 1.1 christos bfin_gen_ldstpmod (REG_T ptr, REG_T reg, int aop, int W, REG_T idx)
1519 1.1 christos {
1520 1.1 christos INIT (LDSTpmod);
1521 1.1 christos
1522 1.1 christos ASSIGN_R (ptr);
1523 1.1 christos ASSIGN_R (reg);
1524 1.1 christos ASSIGN (aop);
1525 1.1 christos ASSIGN (W);
1526 1.1 christos ASSIGN_R (idx);
1527 1.1 christos
1528 1.1 christos return GEN_OPCODE16 ();
1529 1.1 christos }
1530 1.1 christos
1531 1.1 christos INSTR_T
1532 1.1 christos bfin_gen_dspldst (REG_T i, REG_T reg, int aop, int W, int m)
1533 1.1 christos {
1534 1.1 christos INIT (DspLDST);
1535 1.1 christos
1536 1.1 christos ASSIGN_R (i);
1537 1.1 christos ASSIGN_R (reg);
1538 1.1 christos ASSIGN (aop);
1539 1.1 christos ASSIGN (W);
1540 1.1 christos ASSIGN (m);
1541 1.1 christos
1542 1.1 christos return GEN_OPCODE16 ();
1543 1.1 christos }
1544 1.1 christos
1545 1.1 christos INSTR_T
1546 1.1 christos bfin_gen_logi2op (int opc, int src, int dst)
1547 1.1 christos {
1548 1.1 christos INIT (LOGI2op);
1549 1.1 christos
1550 1.1 christos ASSIGN (opc);
1551 1.1 christos ASSIGN (src);
1552 1.1 christos ASSIGN (dst);
1553 1.1 christos
1554 1.1 christos return GEN_OPCODE16 ();
1555 1.1 christos }
1556 1.1 christos
1557 1.1 christos INSTR_T
1558 1.1 christos bfin_gen_brcc (int T, int B, Expr_Node * poffset)
1559 1.1 christos {
1560 1.1 christos int offset;
1561 1.1 christos INIT (BRCC);
1562 1.1 christos
1563 1.1 christos ASSIGN (T);
1564 1.1 christos ASSIGN (B);
1565 1.1 christos offset = ((EXPR_VALUE (poffset) >> 1));
1566 1.1 christos ASSIGN (offset);
1567 1.1 christos return conscode (gencode (c_code.opcode), Expr_Node_Gen_Reloc (poffset, BFD_RELOC_BFIN_10_PCREL));
1568 1.1 christos }
1569 1.1 christos
1570 1.1 christos INSTR_T
1571 1.1 christos bfin_gen_ujump (Expr_Node * poffset)
1572 1.1 christos {
1573 1.1 christos int offset;
1574 1.1 christos INIT (UJump);
1575 1.1 christos
1576 1.1 christos offset = ((EXPR_VALUE (poffset) >> 1));
1577 1.1 christos ASSIGN (offset);
1578 1.1 christos
1579 1.1 christos return conscode (gencode (c_code.opcode),
1580 1.1 christos Expr_Node_Gen_Reloc (
1581 1.1 christos poffset, BFD_RELOC_BFIN_12_PCREL_JUMP_S));
1582 1.1 christos }
1583 1.1 christos
1584 1.1 christos INSTR_T
1585 1.1 christos bfin_gen_alu2op (REG_T dst, REG_T src, int opc)
1586 1.1 christos {
1587 1.1 christos INIT (ALU2op);
1588 1.1 christos
1589 1.1 christos ASSIGN_R (dst);
1590 1.1 christos ASSIGN_R (src);
1591 1.1 christos ASSIGN (opc);
1592 1.1 christos
1593 1.1 christos return GEN_OPCODE16 ();
1594 1.1 christos }
1595 1.1 christos
1596 1.1 christos INSTR_T
1597 1.1 christos bfin_gen_compi2opd (REG_T dst, int src, int opc)
1598 1.1 christos {
1599 1.1 christos INIT (COMPI2opD);
1600 1.1 christos
1601 1.1 christos ASSIGN_R (dst);
1602 1.1 christos ASSIGN (src);
1603 1.1 christos ASSIGNF (opc, op);
1604 1.1 christos
1605 1.1 christos return GEN_OPCODE16 ();
1606 1.1 christos }
1607 1.1 christos
1608 1.1 christos INSTR_T
1609 1.1 christos bfin_gen_compi2opp (REG_T dst, int src, int opc)
1610 1.1 christos {
1611 1.1 christos INIT (COMPI2opP);
1612 1.1 christos
1613 1.1 christos ASSIGN_R (dst);
1614 1.1 christos ASSIGN (src);
1615 1.1 christos ASSIGNF (opc, op);
1616 1.1 christos
1617 1.1 christos return GEN_OPCODE16 ();
1618 1.1 christos }
1619 1.1 christos
1620 1.1 christos INSTR_T
1621 1.1 christos bfin_gen_dagmodik (REG_T i, int opc)
1622 1.1 christos {
1623 1.1 christos INIT (DagMODik);
1624 1.1 christos
1625 1.1 christos ASSIGN_R (i);
1626 1.1 christos ASSIGNF (opc, op);
1627 1.1 christos
1628 1.1 christos return GEN_OPCODE16 ();
1629 1.1 christos }
1630 1.1 christos
1631 1.1 christos INSTR_T
1632 1.1 christos bfin_gen_dagmodim (REG_T i, REG_T m, int opc, int br)
1633 1.1 christos {
1634 1.1 christos INIT (DagMODim);
1635 1.1 christos
1636 1.1 christos ASSIGN_R (i);
1637 1.1 christos ASSIGN_R (m);
1638 1.1 christos ASSIGNF (opc, op);
1639 1.1 christos ASSIGN (br);
1640 1.1 christos
1641 1.1 christos return GEN_OPCODE16 ();
1642 1.1 christos }
1643 1.1 christos
1644 1.1 christos INSTR_T
1645 1.1 christos bfin_gen_ptr2op (REG_T dst, REG_T src, int opc)
1646 1.1 christos {
1647 1.1 christos INIT (PTR2op);
1648 1.1 christos
1649 1.1 christos ASSIGN_R (dst);
1650 1.1 christos ASSIGN_R (src);
1651 1.1 christos ASSIGN (opc);
1652 1.1 christos
1653 1.1 christos return GEN_OPCODE16 ();
1654 1.1 christos }
1655 1.1 christos
1656 1.1 christos INSTR_T
1657 1.1 christos bfin_gen_comp3op (REG_T src0, REG_T src1, REG_T dst, int opc)
1658 1.1 christos {
1659 1.1 christos INIT (COMP3op);
1660 1.1 christos
1661 1.1 christos ASSIGN_R (src0);
1662 1.1 christos ASSIGN_R (src1);
1663 1.1 christos ASSIGN_R (dst);
1664 1.1 christos ASSIGN (opc);
1665 1.1 christos
1666 1.1 christos return GEN_OPCODE16 ();
1667 1.1 christos }
1668 1.1 christos
1669 1.1 christos INSTR_T
1670 1.1 christos bfin_gen_ccflag (REG_T x, int y, int opc, int I, int G)
1671 1.1 christos {
1672 1.1 christos INIT (CCflag);
1673 1.1 christos
1674 1.1 christos ASSIGN_R (x);
1675 1.1 christos ASSIGN (y);
1676 1.1 christos ASSIGN (opc);
1677 1.1 christos ASSIGN (I);
1678 1.1 christos ASSIGN (G);
1679 1.1 christos
1680 1.1 christos return GEN_OPCODE16 ();
1681 1.1 christos }
1682 1.1 christos
1683 1.1 christos INSTR_T
1684 1.1 christos bfin_gen_ccmv (REG_T src, REG_T dst, int T)
1685 1.1 christos {
1686 1.1 christos int s, d;
1687 1.1 christos INIT (CCmv);
1688 1.1 christos
1689 1.1 christos ASSIGN_R (src);
1690 1.1 christos ASSIGN_R (dst);
1691 1.1 christos s = (GROUP (src));
1692 1.1 christos ASSIGN (s);
1693 1.1 christos d = (GROUP (dst));
1694 1.1 christos ASSIGN (d);
1695 1.1 christos ASSIGN (T);
1696 1.1 christos
1697 1.1 christos return GEN_OPCODE16 ();
1698 1.1 christos }
1699 1.1 christos
1700 1.1 christos INSTR_T
1701 1.1 christos bfin_gen_cc2stat (int cbit, int opc, int D)
1702 1.1 christos {
1703 1.1 christos INIT (CC2stat);
1704 1.1 christos
1705 1.1 christos ASSIGN (cbit);
1706 1.1 christos ASSIGNF (opc, op);
1707 1.1 christos ASSIGN (D);
1708 1.1 christos
1709 1.1 christos return GEN_OPCODE16 ();
1710 1.1 christos }
1711 1.1 christos
1712 1.1 christos INSTR_T
1713 1.1 christos bfin_gen_regmv (REG_T src, REG_T dst)
1714 1.1 christos {
1715 1.1 christos int gs, gd;
1716 1.1 christos INIT (RegMv);
1717 1.1 christos
1718 1.1 christos ASSIGN_R (src);
1719 1.1 christos ASSIGN_R (dst);
1720 1.1 christos
1721 1.1 christos gs = (GROUP (src));
1722 1.1 christos ASSIGN (gs);
1723 1.1 christos gd = (GROUP (dst));
1724 1.1 christos ASSIGN (gd);
1725 1.1 christos
1726 1.1 christos return GEN_OPCODE16 ();
1727 1.1 christos }
1728 1.1 christos
1729 1.1 christos INSTR_T
1730 1.1 christos bfin_gen_cc2dreg (int opc, REG_T reg)
1731 1.1 christos {
1732 1.1 christos INIT (CC2dreg);
1733 1.1 christos
1734 1.1 christos ASSIGNF (opc, op);
1735 1.1 christos ASSIGN_R (reg);
1736 1.1 christos
1737 1.1 christos return GEN_OPCODE16 ();
1738 1.1 christos }
1739 1.1 christos
1740 1.1 christos INSTR_T
1741 1.1 christos bfin_gen_progctrl (int prgfunc, int poprnd)
1742 1.1 christos {
1743 1.1 christos INIT (ProgCtrl);
1744 1.1 christos
1745 1.1 christos ASSIGN (prgfunc);
1746 1.1 christos ASSIGN (poprnd);
1747 1.1 christos
1748 1.1 christos return GEN_OPCODE16 ();
1749 1.1 christos }
1750 1.1 christos
1751 1.1 christos INSTR_T
1752 1.1 christos bfin_gen_cactrl (REG_T reg, int a, int opc)
1753 1.1 christos {
1754 1.1 christos INIT (CaCTRL);
1755 1.1 christos
1756 1.1 christos ASSIGN_R (reg);
1757 1.1 christos ASSIGN (a);
1758 1.1 christos ASSIGNF (opc, op);
1759 1.1 christos
1760 1.1 christos return GEN_OPCODE16 ();
1761 1.1 christos }
1762 1.1 christos
1763 1.1 christos INSTR_T
1764 1.1 christos bfin_gen_pushpopmultiple (int dr, int pr, int d, int p, int W)
1765 1.1 christos {
1766 1.1 christos INIT (PushPopMultiple);
1767 1.1 christos
1768 1.1 christos ASSIGN (dr);
1769 1.1 christos ASSIGN (pr);
1770 1.1 christos ASSIGN (d);
1771 1.1 christos ASSIGN (p);
1772 1.1 christos ASSIGN (W);
1773 1.1 christos
1774 1.1 christos return GEN_OPCODE16 ();
1775 1.1 christos }
1776 1.1 christos
1777 1.1 christos INSTR_T
1778 1.1 christos bfin_gen_pushpopreg (REG_T reg, int W)
1779 1.1 christos {
1780 1.1 christos int grp;
1781 1.1 christos INIT (PushPopReg);
1782 1.1 christos
1783 1.1 christos ASSIGN_R (reg);
1784 1.1 christos grp = (GROUP (reg));
1785 1.1 christos ASSIGN (grp);
1786 1.1 christos ASSIGN (W);
1787 1.1 christos
1788 1.1 christos return GEN_OPCODE16 ();
1789 1.1 christos }
1790 1.1 christos
1791 1.1 christos /* Pseudo Debugging Support. */
1792 1.1 christos
1793 1.1 christos INSTR_T
1794 1.1 christos bfin_gen_pseudodbg (int fn, int reg, int grp)
1795 1.1 christos {
1796 1.1 christos INIT (PseudoDbg);
1797 1.1 christos
1798 1.1 christos ASSIGN (fn);
1799 1.1 christos ASSIGN (reg);
1800 1.1 christos ASSIGN (grp);
1801 1.1 christos
1802 1.1 christos return GEN_OPCODE16 ();
1803 1.1 christos }
1804 1.1 christos
1805 1.1 christos INSTR_T
1806 1.1 christos bfin_gen_pseudodbg_assert (int dbgop, REG_T regtest, int expected)
1807 1.1 christos {
1808 1.1 christos int grp;
1809 1.1 christos INIT (PseudoDbg_Assert);
1810 1.1 christos
1811 1.1 christos ASSIGN (dbgop);
1812 1.1 christos ASSIGN_R (regtest);
1813 1.1 christos grp = GROUP (regtest);
1814 1.1 christos ASSIGN (grp);
1815 1.1 christos ASSIGN (expected);
1816 1.1 christos
1817 1.1 christos return GEN_OPCODE32 ();
1818 1.1 christos }
1819 1.1 christos
1820 1.1 christos INSTR_T
1821 1.1 christos bfin_gen_pseudochr (int ch)
1822 1.1 christos {
1823 1.1 christos INIT (PseudoChr);
1824 1.1 christos
1825 1.1 christos ASSIGN (ch);
1826 1.1 christos
1827 1.1 christos return GEN_OPCODE16 ();
1828 1.1 christos }
1829 1.1 christos
1830 1.1 christos /* Multiple instruction generation. */
1831 1.1 christos
1832 1.1 christos INSTR_T
1833 1.1 christos bfin_gen_multi_instr (INSTR_T dsp32, INSTR_T dsp16_grp1, INSTR_T dsp16_grp2)
1834 1.1 christos {
1835 1.1 christos INSTR_T walk;
1836 1.1 christos
1837 1.1 christos /* If it's a 0, convert into MNOP. */
1838 1.1 christos if (dsp32)
1839 1.1 christos {
1840 1.1 christos walk = dsp32->next;
1841 1.1 christos SET_MULTI_INSTRUCTION_BIT (dsp32);
1842 1.1 christos }
1843 1.1 christos else
1844 1.1 christos {
1845 1.1 christos dsp32 = gencode (0xc803);
1846 1.1 christos walk = gencode (0x1800);
1847 1.1 christos dsp32->next = walk;
1848 1.1 christos }
1849 1.1 christos
1850 1.1 christos if (!dsp16_grp1)
1851 1.1 christos {
1852 1.1 christos dsp16_grp1 = gencode (0x0000);
1853 1.1 christos }
1854 1.1 christos
1855 1.1 christos if (!dsp16_grp2)
1856 1.1 christos {
1857 1.1 christos dsp16_grp2 = gencode (0x0000);
1858 1.1 christos }
1859 1.1 christos
1860 1.1 christos walk->next = dsp16_grp1;
1861 1.1 christos dsp16_grp1->next = dsp16_grp2;
1862 1.1 christos dsp16_grp2->next = NULL_CODE;
1863 1.1 christos
1864 1.1 christos return dsp32;
1865 1.1 christos }
1866 1.1 christos
1867 1.1 christos INSTR_T
1868 1.1 christos bfin_gen_loop (Expr_Node *exp, REG_T reg, int rop, REG_T preg)
1869 1.1 christos {
1870 1.1 christos const char *loopsym;
1871 1.1 christos char *lbeginsym, *lendsym;
1872 1.1 christos Expr_Node_Value lbeginval, lendval;
1873 1.1 christos Expr_Node *lbegin, *lend;
1874 1.1 christos symbolS *sym;
1875 1.1 christos
1876 1.1 christos loopsym = exp->value.s_value;
1877 1.1 christos lbeginsym = (char *) xmalloc (strlen (loopsym) + strlen ("__BEGIN") + 5);
1878 1.1 christos lendsym = (char *) xmalloc (strlen (loopsym) + strlen ("__END") + 5);
1879 1.1 christos
1880 1.1 christos lbeginsym[0] = 0;
1881 1.1 christos lendsym[0] = 0;
1882 1.1 christos
1883 1.1 christos strcat (lbeginsym, "L$L$");
1884 1.1 christos strcat (lbeginsym, loopsym);
1885 1.1 christos strcat (lbeginsym, "__BEGIN");
1886 1.1 christos
1887 1.1 christos strcat (lendsym, "L$L$");
1888 1.1 christos strcat (lendsym, loopsym);
1889 1.1 christos strcat (lendsym, "__END");
1890 1.1 christos
1891 1.1 christos lbeginval.s_value = lbeginsym;
1892 1.1 christos lendval.s_value = lendsym;
1893 1.1 christos
1894 1.1 christos lbegin = Expr_Node_Create (Expr_Node_Reloc, lbeginval, NULL, NULL);
1895 1.1 christos lend = Expr_Node_Create (Expr_Node_Reloc, lendval, NULL, NULL);
1896 1.1 christos
1897 1.1 christos sym = symbol_find(loopsym);
1898 1.1 christos if (!S_IS_LOCAL (sym) || (S_IS_LOCAL (sym) && !symbol_used_p (sym)))
1899 1.1 christos symbol_remove (sym, &symbol_rootP, &symbol_lastP);
1900 1.1 christos
1901 1.1 christos return bfin_gen_loopsetup (lbegin, reg, rop, lend, preg);
1902 1.1 christos }
1903 1.1 christos
1904 1.1 christos void
1905 1.1 christos bfin_loop_attempt_create_label (Expr_Node *exp, int is_begin)
1906 1.1 christos {
1907 1.1 christos char *name;
1908 1.1 christos name = fb_label_name (exp->value.i_value, is_begin);
1909 1.1 christos exp->value.s_value = xstrdup (name);
1910 1.1 christos exp->type = Expr_Node_Reloc;
1911 1.1 christos }
1912 1.1 christos
1913 1.1 christos void
1914 1.1 christos bfin_loop_beginend (Expr_Node *exp, int begin)
1915 1.1 christos {
1916 1.1 christos const char *loopsym;
1917 1.1 christos char *label_name;
1918 1.1 christos symbolS *linelabel;
1919 1.1 christos const char *suffix = begin ? "__BEGIN" : "__END";
1920 1.1 christos
1921 1.1 christos loopsym = exp->value.s_value;
1922 1.1 christos label_name = (char *) xmalloc (strlen (loopsym) + strlen (suffix) + 5);
1923 1.1 christos
1924 1.1 christos label_name[0] = 0;
1925 1.1 christos
1926 1.1 christos strcat (label_name, "L$L$");
1927 1.1 christos strcat (label_name, loopsym);
1928 1.1 christos strcat (label_name, suffix);
1929 1.1 christos
1930 1.1 christos linelabel = colon (label_name);
1931 1.1 christos
1932 1.1 christos /* LOOP_END follows the last instruction in the loop.
1933 1.1 christos Adjust label address. */
1934 1.1 christos if (!begin)
1935 1.1 christos ((struct local_symbol *) linelabel)->lsy_value -= last_insn_size;
1936 1.1 christos }
1937 1.1 christos
1938 1.1 christos bfd_boolean
1939 1.1 christos bfin_eol_in_insn (char *line)
1940 1.1 christos {
1941 1.1 christos /* Allow a new-line to appear in the middle of a multi-issue instruction. */
1942 1.1 christos
1943 1.1 christos char *temp = line;
1944 1.1 christos
1945 1.1 christos if (*line != '\n')
1946 1.1 christos return FALSE;
1947 1.1 christos
1948 1.1 christos /* A semi-colon followed by a newline is always the end of a line. */
1949 1.1 christos if (line[-1] == ';')
1950 1.1 christos return FALSE;
1951 1.1 christos
1952 1.1 christos if (line[-1] == '|')
1953 1.1 christos return TRUE;
1954 1.1 christos
1955 1.1 christos /* If the || is on the next line, there might be leading whitespace. */
1956 1.1 christos temp++;
1957 1.1 christos while (*temp == ' ' || *temp == '\t') temp++;
1958 1.1 christos
1959 1.1 christos if (*temp == '|')
1960 1.1 christos return TRUE;
1961 1.1 christos
1962 1.1 christos return FALSE;
1963 1.1 christos }
1964 1.1 christos
1965 1.1.1.2 christos bfd_boolean
1966 1.1 christos bfin_start_label (char *s)
1967 1.1.1.2 christos {
1968 1.1 christos while (*s != 0)
1969 1.1 christos {
1970 1.1 christos if (*s == '(' || *s == '[')
1971 1.1 christos return FALSE;
1972 1.1 christos s++;
1973 1.1 christos }
1974 1.1 christos
1975 1.1 christos return TRUE;
1976 1.1 christos }
1977 1.1 christos
1978 1.1 christos int
1979 1.1 christos bfin_force_relocation (struct fix *fixp)
1980 1.1 christos {
1981 1.1 christos if (fixp->fx_r_type ==BFD_RELOC_BFIN_16_LOW
1982 1.1 christos || fixp->fx_r_type == BFD_RELOC_BFIN_16_HIGH)
1983 1.1 christos return TRUE;
1984 1.1 christos
1985 1.1 christos return generic_force_reloc (fixp);
1986 1.1 christos }
1987 1.1 christos
1988 1.1 christos /* This is a stripped down version of the disassembler. The only thing it
1990 1.1 christos does is return a mask of registers modified by an instruction. Only
1991 1.1 christos instructions that can occur in a parallel-issue bundle are handled, and
1992 1.1 christos only the registers that can cause a conflict are recorded. */
1993 1.1 christos
1994 1.1 christos #define DREG_MASK(n) (0x101 << (n))
1995 1.1 christos #define DREGH_MASK(n) (0x100 << (n))
1996 1.1 christos #define DREGL_MASK(n) (0x001 << (n))
1997 1.1 christos #define IREG_MASK(n) (1 << ((n) + 16))
1998 1.1 christos
1999 1.1 christos static int
2000 1.1 christos decode_ProgCtrl_0 (int iw0)
2001 1.1 christos {
2002 1.1 christos if (iw0 == 0)
2003 1.1 christos return 0;
2004 1.1 christos abort ();
2005 1.1 christos }
2006 1.1 christos
2007 1.1 christos static int
2008 1.1 christos decode_LDSTpmod_0 (int iw0)
2009 1.1 christos {
2010 1.1 christos /* LDSTpmod
2011 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2012 1.1 christos | 1 | 0 | 0 | 0 |.W.|.aop...|.reg.......|.idx.......|.ptr.......|
2013 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2014 1.1 christos int W = ((iw0 >> LDSTpmod_W_bits) & LDSTpmod_W_mask);
2015 1.1 christos int aop = ((iw0 >> LDSTpmod_aop_bits) & LDSTpmod_aop_mask);
2016 1.1 christos int idx = ((iw0 >> LDSTpmod_idx_bits) & LDSTpmod_idx_mask);
2017 1.1 christos int ptr = ((iw0 >> LDSTpmod_ptr_bits) & LDSTpmod_ptr_mask);
2018 1.1 christos int reg = ((iw0 >> LDSTpmod_reg_bits) & LDSTpmod_reg_mask);
2019 1.1 christos
2020 1.1 christos if (aop == 1 && W == 0 && idx == ptr)
2021 1.1 christos return DREGL_MASK (reg);
2022 1.1 christos else if (aop == 2 && W == 0 && idx == ptr)
2023 1.1 christos return DREGH_MASK (reg);
2024 1.1 christos else if (aop == 1 && W == 1 && idx == ptr)
2025 1.1 christos return 0;
2026 1.1 christos else if (aop == 2 && W == 1 && idx == ptr)
2027 1.1 christos return 0;
2028 1.1 christos else if (aop == 0 && W == 0)
2029 1.1 christos return DREG_MASK (reg);
2030 1.1 christos else if (aop == 1 && W == 0)
2031 1.1 christos return DREGL_MASK (reg);
2032 1.1 christos else if (aop == 2 && W == 0)
2033 1.1 christos return DREGH_MASK (reg);
2034 1.1 christos else if (aop == 3 && W == 0)
2035 1.1 christos return DREG_MASK (reg);
2036 1.1 christos else if (aop == 3 && W == 1)
2037 1.1 christos return DREG_MASK (reg);
2038 1.1 christos else if (aop == 0 && W == 1)
2039 1.1 christos return 0;
2040 1.1 christos else if (aop == 1 && W == 1)
2041 1.1 christos return 0;
2042 1.1 christos else if (aop == 2 && W == 1)
2043 1.1 christos return 0;
2044 1.1 christos else
2045 1.1 christos return 0;
2046 1.1 christos
2047 1.1 christos return 2;
2048 1.1 christos }
2049 1.1 christos
2050 1.1 christos static int
2051 1.1 christos decode_dagMODim_0 (int iw0)
2052 1.1 christos {
2053 1.1 christos /* dagMODim
2054 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2055 1.1 christos | 1 | 0 | 0 | 1 | 1 | 1 | 1 | 0 |.br| 1 | 1 |.op|.m.....|.i.....|
2056 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2057 1.1 christos int i = ((iw0 >> DagMODim_i_bits) & DagMODim_i_mask);
2058 1.1 christos int opc = ((iw0 >> DagMODim_op_bits) & DagMODim_op_mask);
2059 1.1 christos
2060 1.1 christos if (opc == 0 || opc == 1)
2061 1.1 christos return IREG_MASK (i);
2062 1.1 christos else
2063 1.1 christos return 0;
2064 1.1 christos
2065 1.1 christos return 2;
2066 1.1 christos }
2067 1.1 christos
2068 1.1 christos static int
2069 1.1 christos decode_dagMODik_0 (int iw0)
2070 1.1 christos {
2071 1.1 christos /* dagMODik
2072 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2073 1.1 christos | 1 | 0 | 0 | 1 | 1 | 1 | 1 | 1 | 0 | 1 | 1 | 0 |.op....|.i.....|
2074 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2075 1.1 christos int i = ((iw0 >> DagMODik_i_bits) & DagMODik_i_mask);
2076 1.1 christos return IREG_MASK (i);
2077 1.1 christos }
2078 1.1 christos
2079 1.1 christos /* GOOD */
2080 1.1 christos static int
2081 1.1 christos decode_dspLDST_0 (int iw0)
2082 1.1 christos {
2083 1.1 christos /* dspLDST
2084 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2085 1.1 christos | 1 | 0 | 0 | 1 | 1 | 1 |.W.|.aop...|.m.....|.i.....|.reg.......|
2086 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2087 1.1 christos int i = ((iw0 >> DspLDST_i_bits) & DspLDST_i_mask);
2088 1.1 christos int m = ((iw0 >> DspLDST_m_bits) & DspLDST_m_mask);
2089 1.1 christos int W = ((iw0 >> DspLDST_W_bits) & DspLDST_W_mask);
2090 1.1 christos int aop = ((iw0 >> DspLDST_aop_bits) & DspLDST_aop_mask);
2091 1.1 christos int reg = ((iw0 >> DspLDST_reg_bits) & DspLDST_reg_mask);
2092 1.1 christos
2093 1.1 christos if (aop == 0 && W == 0 && m == 0)
2094 1.1 christos return DREG_MASK (reg) | IREG_MASK (i);
2095 1.1 christos else if (aop == 0 && W == 0 && m == 1)
2096 1.1 christos return DREGL_MASK (reg) | IREG_MASK (i);
2097 1.1 christos else if (aop == 0 && W == 0 && m == 2)
2098 1.1 christos return DREGH_MASK (reg) | IREG_MASK (i);
2099 1.1 christos else if (aop == 1 && W == 0 && m == 0)
2100 1.1 christos return DREG_MASK (reg) | IREG_MASK (i);
2101 1.1 christos else if (aop == 1 && W == 0 && m == 1)
2102 1.1 christos return DREGL_MASK (reg) | IREG_MASK (i);
2103 1.1 christos else if (aop == 1 && W == 0 && m == 2)
2104 1.1 christos return DREGH_MASK (reg) | IREG_MASK (i);
2105 1.1 christos else if (aop == 2 && W == 0 && m == 0)
2106 1.1 christos return DREG_MASK (reg);
2107 1.1 christos else if (aop == 2 && W == 0 && m == 1)
2108 1.1 christos return DREGL_MASK (reg);
2109 1.1 christos else if (aop == 2 && W == 0 && m == 2)
2110 1.1 christos return DREGH_MASK (reg);
2111 1.1 christos else if (aop == 0 && W == 1 && m == 0)
2112 1.1 christos return IREG_MASK (i);
2113 1.1 christos else if (aop == 0 && W == 1 && m == 1)
2114 1.1 christos return IREG_MASK (i);
2115 1.1 christos else if (aop == 0 && W == 1 && m == 2)
2116 1.1 christos return IREG_MASK (i);
2117 1.1 christos else if (aop == 1 && W == 1 && m == 0)
2118 1.1 christos return IREG_MASK (i);
2119 1.1 christos else if (aop == 1 && W == 1 && m == 1)
2120 1.1 christos return IREG_MASK (i);
2121 1.1 christos else if (aop == 1 && W == 1 && m == 2)
2122 1.1 christos return IREG_MASK (i);
2123 1.1 christos else if (aop == 2 && W == 1 && m == 0)
2124 1.1 christos return 0;
2125 1.1 christos else if (aop == 2 && W == 1 && m == 1)
2126 1.1 christos return 0;
2127 1.1 christos else if (aop == 2 && W == 1 && m == 2)
2128 1.1 christos return 0;
2129 1.1 christos else if (aop == 3 && W == 0)
2130 1.1 christos return DREG_MASK (reg) | IREG_MASK (i);
2131 1.1 christos else if (aop == 3 && W == 1)
2132 1.1 christos return IREG_MASK (i);
2133 1.1 christos
2134 1.1 christos abort ();
2135 1.1 christos }
2136 1.1 christos
2137 1.1 christos /* GOOD */
2138 1.1 christos static int
2139 1.1 christos decode_LDST_0 (int iw0)
2140 1.1 christos {
2141 1.1 christos /* LDST
2142 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2143 1.1 christos | 1 | 0 | 0 | 1 |.sz....|.W.|.aop...|.Z.|.ptr.......|.reg.......|
2144 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2145 1.1 christos int Z = ((iw0 >> LDST_Z_bits) & LDST_Z_mask);
2146 1.1 christos int W = ((iw0 >> LDST_W_bits) & LDST_W_mask);
2147 1.1 christos int sz = ((iw0 >> LDST_sz_bits) & LDST_sz_mask);
2148 1.1 christos int aop = ((iw0 >> LDST_aop_bits) & LDST_aop_mask);
2149 1.1 christos int reg = ((iw0 >> LDST_reg_bits) & LDST_reg_mask);
2150 1.1 christos
2151 1.1 christos if (aop == 0 && sz == 0 && Z == 0 && W == 0)
2152 1.1 christos return DREG_MASK (reg);
2153 1.1 christos else if (aop == 0 && sz == 0 && Z == 1 && W == 0)
2154 1.1 christos return 0;
2155 1.1 christos else if (aop == 0 && sz == 1 && Z == 0 && W == 0)
2156 1.1 christos return DREG_MASK (reg);
2157 1.1 christos else if (aop == 0 && sz == 1 && Z == 1 && W == 0)
2158 1.1 christos return DREG_MASK (reg);
2159 1.1 christos else if (aop == 0 && sz == 2 && Z == 0 && W == 0)
2160 1.1 christos return DREG_MASK (reg);
2161 1.1 christos else if (aop == 0 && sz == 2 && Z == 1 && W == 0)
2162 1.1 christos return DREG_MASK (reg);
2163 1.1 christos else if (aop == 1 && sz == 0 && Z == 0 && W == 0)
2164 1.1 christos return DREG_MASK (reg);
2165 1.1 christos else if (aop == 1 && sz == 0 && Z == 1 && W == 0)
2166 1.1 christos return 0;
2167 1.1 christos else if (aop == 1 && sz == 1 && Z == 0 && W == 0)
2168 1.1 christos return DREG_MASK (reg);
2169 1.1 christos else if (aop == 1 && sz == 1 && Z == 1 && W == 0)
2170 1.1 christos return DREG_MASK (reg);
2171 1.1 christos else if (aop == 1 && sz == 2 && Z == 0 && W == 0)
2172 1.1 christos return DREG_MASK (reg);
2173 1.1 christos else if (aop == 1 && sz == 2 && Z == 1 && W == 0)
2174 1.1 christos return DREG_MASK (reg);
2175 1.1 christos else if (aop == 2 && sz == 0 && Z == 0 && W == 0)
2176 1.1 christos return DREG_MASK (reg);
2177 1.1 christos else if (aop == 2 && sz == 0 && Z == 1 && W == 0)
2178 1.1 christos return 0;
2179 1.1 christos else if (aop == 2 && sz == 1 && Z == 0 && W == 0)
2180 1.1 christos return DREG_MASK (reg);
2181 1.1 christos else if (aop == 2 && sz == 1 && Z == 1 && W == 0)
2182 1.1 christos return DREG_MASK (reg);
2183 1.1 christos else if (aop == 2 && sz == 2 && Z == 0 && W == 0)
2184 1.1 christos return DREG_MASK (reg);
2185 1.1 christos else if (aop == 2 && sz == 2 && Z == 1 && W == 0)
2186 1.1 christos return DREG_MASK (reg);
2187 1.1 christos else if (aop == 0 && sz == 0 && Z == 0 && W == 1)
2188 1.1 christos return 0;
2189 1.1 christos else if (aop == 0 && sz == 0 && Z == 1 && W == 1)
2190 1.1 christos return 0;
2191 1.1 christos else if (aop == 0 && sz == 1 && Z == 0 && W == 1)
2192 1.1 christos return 0;
2193 1.1 christos else if (aop == 0 && sz == 2 && Z == 0 && W == 1)
2194 1.1 christos return 0;
2195 1.1 christos else if (aop == 1 && sz == 0 && Z == 0 && W == 1)
2196 1.1 christos return 0;
2197 1.1 christos else if (aop == 1 && sz == 0 && Z == 1 && W == 1)
2198 1.1 christos return 0;
2199 1.1 christos else if (aop == 1 && sz == 1 && Z == 0 && W == 1)
2200 1.1 christos return 0;
2201 1.1 christos else if (aop == 1 && sz == 2 && Z == 0 && W == 1)
2202 1.1 christos return 0;
2203 1.1 christos else if (aop == 2 && sz == 0 && Z == 0 && W == 1)
2204 1.1 christos return 0;
2205 1.1 christos else if (aop == 2 && sz == 0 && Z == 1 && W == 1)
2206 1.1 christos return 0;
2207 1.1 christos else if (aop == 2 && sz == 1 && Z == 0 && W == 1)
2208 1.1 christos return 0;
2209 1.1 christos else if (aop == 2 && sz == 2 && Z == 0 && W == 1)
2210 1.1 christos return 0;
2211 1.1 christos
2212 1.1 christos abort ();
2213 1.1 christos }
2214 1.1 christos
2215 1.1 christos static int
2216 1.1 christos decode_LDSTiiFP_0 (int iw0)
2217 1.1 christos {
2218 1.1 christos /* LDSTiiFP
2219 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2220 1.1 christos | 1 | 0 | 1 | 1 | 1 | 0 |.W.|.offset............|.reg...........|
2221 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2222 1.1 christos int reg = ((iw0 >> LDSTiiFP_reg_bits) & LDSTiiFP_reg_mask);
2223 1.1 christos int W = ((iw0 >> LDSTiiFP_W_bits) & LDSTiiFP_W_mask);
2224 1.1 christos
2225 1.1 christos if (W == 0)
2226 1.1 christos return reg < 8 ? DREG_MASK (reg) : 0;
2227 1.1 christos else
2228 1.1 christos return 0;
2229 1.1 christos }
2230 1.1 christos
2231 1.1 christos static int
2232 1.1 christos decode_LDSTii_0 (int iw0)
2233 1.1 christos {
2234 1.1 christos /* LDSTii
2235 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2236 1.1 christos | 1 | 0 | 1 |.W.|.op....|.offset........|.ptr.......|.reg.......|
2237 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2238 1.1 christos int reg = ((iw0 >> LDSTii_reg_bit) & LDSTii_reg_mask);
2239 1.1 christos int opc = ((iw0 >> LDSTii_op_bit) & LDSTii_op_mask);
2240 1.1 christos int W = ((iw0 >> LDSTii_W_bit) & LDSTii_W_mask);
2241 1.1 christos
2242 1.1 christos if (W == 0 && opc != 3)
2243 1.1 christos return DREG_MASK (reg);
2244 1.1 christos else if (W == 0 && opc == 3)
2245 1.1 christos return 0;
2246 1.1 christos else if (W == 1 && opc == 0)
2247 1.1 christos return 0;
2248 1.1 christos else if (W == 1 && opc == 1)
2249 1.1 christos return 0;
2250 1.1 christos else if (W == 1 && opc == 3)
2251 1.1 christos return 0;
2252 1.1 christos
2253 1.1 christos abort ();
2254 1.1 christos }
2255 1.1 christos
2256 1.1 christos static int
2257 1.1 christos decode_dsp32mac_0 (int iw0, int iw1)
2258 1.1 christos {
2259 1.1 christos int result = 0;
2260 1.1 christos /* dsp32mac
2261 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2262 1.1 christos | 1 | 1 | 0 | 0 |.M.| 0 | 0 |.mmod..........|.MM|.P.|.w1|.op1...|
2263 1.1 christos |.h01|.h11|.w0|.op0...|.h00|.h10|.dst.......|.src0......|.src1..|
2264 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2265 1.1 christos int op1 = ((iw0 >> (DSP32Mac_op1_bits - 16)) & DSP32Mac_op1_mask);
2266 1.1 christos int w1 = ((iw0 >> (DSP32Mac_w1_bits - 16)) & DSP32Mac_w1_mask);
2267 1.1 christos int P = ((iw0 >> (DSP32Mac_p_bits - 16)) & DSP32Mac_p_mask);
2268 1.1 christos int mmod = ((iw0 >> (DSP32Mac_mmod_bits - 16)) & DSP32Mac_mmod_mask);
2269 1.1 christos int w0 = ((iw1 >> DSP32Mac_w0_bits) & DSP32Mac_w0_mask);
2270 1.1 christos int MM = ((iw1 >> DSP32Mac_MM_bits) & DSP32Mac_MM_mask);
2271 1.1 christos int dst = ((iw1 >> DSP32Mac_dst_bits) & DSP32Mac_dst_mask);
2272 1.1 christos int op0 = ((iw1 >> DSP32Mac_op0_bits) & DSP32Mac_op0_mask);
2273 1.1 christos
2274 1.1 christos if (w0 == 0 && w1 == 0 && op1 == 3 && op0 == 3)
2275 1.1 christos return 0;
2276 1.1 christos
2277 1.1 christos if (op1 == 3 && MM)
2278 1.1 christos return 0;
2279 1.1 christos
2280 1.1 christos if ((w1 || w0) && mmod == M_W32)
2281 1.1 christos return 0;
2282 1.1 christos
2283 1.1 christos if (((1 << mmod) & (P ? 0x131b : 0x1b5f)) == 0)
2284 1.1 christos return 0;
2285 1.1 christos
2286 1.1 christos if (w1 == 1 || op1 != 3)
2287 1.1 christos {
2288 1.1 christos if (w1)
2289 1.1 christos {
2290 1.1 christos if (P)
2291 1.1 christos return DREG_MASK (dst + 1);
2292 1.1 christos else
2293 1.1 christos return DREGH_MASK (dst);
2294 1.1 christos }
2295 1.1 christos }
2296 1.1 christos
2297 1.1 christos if (w0 == 1 || op0 != 3)
2298 1.1 christos {
2299 1.1 christos if (w0)
2300 1.1 christos {
2301 1.1 christos if (P)
2302 1.1 christos return DREG_MASK (dst);
2303 1.1 christos else
2304 1.1 christos return DREGL_MASK (dst);
2305 1.1 christos }
2306 1.1 christos }
2307 1.1 christos
2308 1.1 christos return result;
2309 1.1 christos }
2310 1.1 christos
2311 1.1 christos static int
2312 1.1 christos decode_dsp32mult_0 (int iw0, int iw1)
2313 1.1 christos {
2314 1.1 christos /* dsp32mult
2315 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2316 1.1 christos | 1 | 1 | 0 | 0 |.M.| 0 | 1 |.mmod..........|.MM|.P.|.w1|.op1...|
2317 1.1 christos |.h01|.h11|.w0|.op0...|.h00|.h10|.dst.......|.src0......|.src1..|
2318 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2319 1.1 christos int w1 = ((iw0 >> (DSP32Mac_w1_bits - 16)) & DSP32Mac_w1_mask);
2320 1.1 christos int P = ((iw0 >> (DSP32Mac_p_bits - 16)) & DSP32Mac_p_mask);
2321 1.1 christos int mmod = ((iw0 >> (DSP32Mac_mmod_bits - 16)) & DSP32Mac_mmod_mask);
2322 1.1 christos int w0 = ((iw1 >> DSP32Mac_w0_bits) & DSP32Mac_w0_mask);
2323 1.1 christos int dst = ((iw1 >> DSP32Mac_dst_bits) & DSP32Mac_dst_mask);
2324 1.1 christos int result = 0;
2325 1.1 christos
2326 1.1 christos if (w1 == 0 && w0 == 0)
2327 1.1 christos return 0;
2328 1.1 christos
2329 1.1 christos if (((1 << mmod) & (P ? 0x313 : 0x1b57)) == 0)
2330 1.1 christos return 0;
2331 1.1 christos
2332 1.1 christos if (w1)
2333 1.1 christos {
2334 1.1 christos if (P)
2335 1.1 christos return DREG_MASK (dst | 1);
2336 1.1 christos else
2337 1.1 christos return DREGH_MASK (dst);
2338 1.1 christos }
2339 1.1 christos
2340 1.1 christos if (w0)
2341 1.1 christos {
2342 1.1 christos if (P)
2343 1.1 christos return DREG_MASK (dst);
2344 1.1 christos else
2345 1.1 christos return DREGL_MASK (dst);
2346 1.1 christos }
2347 1.1 christos
2348 1.1 christos return result;
2349 1.1 christos }
2350 1.1 christos
2351 1.1 christos static int
2352 1.1 christos decode_dsp32alu_0 (int iw0, int iw1)
2353 1.1 christos {
2354 1.1 christos /* dsp32alu
2355 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2356 1.1 christos | 1 | 1 | 0 | 0 |.M.| 1 | 0 | - | - | - |.HL|.aopcde............|
2357 1.1 christos |.aop...|.s.|.x.|.dst0......|.dst1......|.src0......|.src1......|
2358 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2359 1.1 christos int s = ((iw1 >> DSP32Alu_s_bits) & DSP32Alu_s_mask);
2360 1.1 christos int x = ((iw1 >> DSP32Alu_x_bits) & DSP32Alu_x_mask);
2361 1.1 christos int aop = ((iw1 >> DSP32Alu_aop_bits) & DSP32Alu_aop_mask);
2362 1.1 christos int dst0 = ((iw1 >> DSP32Alu_dst0_bits) & DSP32Alu_dst0_mask);
2363 1.1 christos int dst1 = ((iw1 >> DSP32Alu_dst1_bits) & DSP32Alu_dst1_mask);
2364 1.1 christos int HL = ((iw0 >> (DSP32Alu_HL_bits - 16)) & DSP32Alu_HL_mask);
2365 1.1 christos int aopcde = ((iw0 >> (DSP32Alu_aopcde_bits - 16)) & DSP32Alu_aopcde_mask);
2366 1.1 christos
2367 1.1 christos if (aop == 0 && aopcde == 9 && s == 0)
2368 1.1 christos return 0;
2369 1.1 christos else if (aop == 2 && aopcde == 9 && HL == 0 && s == 0)
2370 1.1 christos return 0;
2371 1.1 christos else if (aop >= x * 2 && aopcde == 5)
2372 1.1 christos return HL ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2373 1.1 christos else if (HL == 0 && aopcde == 2)
2374 1.1 christos return DREGL_MASK (dst0);
2375 1.1 christos else if (HL == 1 && aopcde == 2)
2376 1.1 christos return DREGH_MASK (dst0);
2377 1.1 christos else if (HL == 0 && aopcde == 3)
2378 1.1 christos return DREGL_MASK (dst0);
2379 1.1 christos else if (HL == 1 && aopcde == 3)
2380 1.1 christos return DREGH_MASK (dst0);
2381 1.1 christos
2382 1.1 christos else if (aop == 0 && aopcde == 9 && s == 1)
2383 1.1 christos return 0;
2384 1.1 christos else if (aop == 1 && aopcde == 9 && s == 0)
2385 1.1 christos return 0;
2386 1.1 christos else if (aop == 2 && aopcde == 9 && s == 1)
2387 1.1 christos return 0;
2388 1.1 christos else if (aop == 3 && aopcde == 9 && s == 0)
2389 1.1 christos return 0;
2390 1.1 christos else if (aopcde == 8)
2391 1.1 christos return 0;
2392 1.1 christos else if (aop == 0 && aopcde == 11)
2393 1.1 christos return DREG_MASK (dst0);
2394 1.1 christos else if (aop == 1 && aopcde == 11)
2395 1.1 christos return HL ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2396 1.1 christos else if (aopcde == 11)
2397 1.1 christos return 0;
2398 1.1 christos else if (aopcde == 22)
2399 1.1 christos return DREG_MASK (dst0);
2400 1.1 christos
2401 1.1 christos else if ((aop == 0 || aop == 1) && aopcde == 14)
2402 1.1 christos return 0;
2403 1.1 christos else if (aop == 3 && HL == 0 && aopcde == 14)
2404 1.1 christos return 0;
2405 1.1 christos
2406 1.1 christos else if (aop == 3 && HL == 0 && aopcde == 15)
2407 1.1 christos return DREG_MASK (dst0);
2408 1.1 christos
2409 1.1 christos else if (aop == 1 && aopcde == 16)
2410 1.1 christos return 0;
2411 1.1 christos
2412 1.1 christos else if (aop == 0 && aopcde == 16)
2413 1.1 christos return 0;
2414 1.1 christos
2415 1.1 christos else if (aop == 3 && HL == 0 && aopcde == 16)
2416 1.1 christos return 0;
2417 1.1 christos
2418 1.1 christos else if (aop == 3 && HL == 0 && aopcde == 7)
2419 1.1 christos return DREG_MASK (dst0);
2420 1.1 christos else if ((aop == 0 || aop == 1 || aop == 2) && aopcde == 7)
2421 1.1 christos return DREG_MASK (dst0);
2422 1.1 christos
2423 1.1 christos else if (aop == 0 && aopcde == 12)
2424 1.1 christos return DREG_MASK (dst0);
2425 1.1 christos else if (aop == 1 && aopcde == 12)
2426 1.1 christos return DREG_MASK (dst0) | DREG_MASK (dst1);
2427 1.1 christos else if (aop == 3 && aopcde == 12)
2428 1.1 christos return HL ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2429 1.1 christos
2430 1.1 christos else if (aopcde == 0)
2431 1.1 christos return DREG_MASK (dst0);
2432 1.1 christos else if (aopcde == 1)
2433 1.1 christos return DREG_MASK (dst0) | DREG_MASK (dst1);
2434 1.1 christos
2435 1.1 christos else if (aop == 0 && aopcde == 10)
2436 1.1 christos return DREGL_MASK (dst0);
2437 1.1 christos else if (aop == 1 && aopcde == 10)
2438 1.1 christos return DREGL_MASK (dst0);
2439 1.1 christos
2440 1.1 christos else if ((aop == 1 || aop == 0) && aopcde == 4)
2441 1.1 christos return DREG_MASK (dst0);
2442 1.1 christos else if (aop == 2 && aopcde == 4)
2443 1.1 christos return DREG_MASK (dst0) | DREG_MASK (dst1);
2444 1.1 christos
2445 1.1 christos else if (aop == 0 && aopcde == 17)
2446 1.1 christos return DREG_MASK (dst0) | DREG_MASK (dst1);
2447 1.1 christos else if (aop == 1 && aopcde == 17)
2448 1.1 christos return DREG_MASK (dst0) | DREG_MASK (dst1);
2449 1.1 christos else if (aop == 0 && aopcde == 18)
2450 1.1 christos return 0;
2451 1.1 christos else if (aop == 3 && aopcde == 18)
2452 1.1 christos return 0;
2453 1.1 christos
2454 1.1 christos else if ((aop == 0 || aop == 1 || aop == 2) && aopcde == 6)
2455 1.1 christos return DREG_MASK (dst0);
2456 1.1 christos
2457 1.1 christos else if ((aop == 0 || aop == 1) && aopcde == 20)
2458 1.1 christos return DREG_MASK (dst0);
2459 1.1 christos
2460 1.1 christos else if ((aop == 0 || aop == 1) && aopcde == 21)
2461 1.1 christos return DREG_MASK (dst0) | DREG_MASK (dst1);
2462 1.1 christos
2463 1.1 christos else if (aop == 0 && aopcde == 23 && HL == 1)
2464 1.1 christos return DREG_MASK (dst0);
2465 1.1 christos else if (aop == 0 && aopcde == 23 && HL == 0)
2466 1.1 christos return DREG_MASK (dst0);
2467 1.1 christos
2468 1.1 christos else if (aop == 0 && aopcde == 24)
2469 1.1 christos return DREG_MASK (dst0);
2470 1.1 christos else if (aop == 1 && aopcde == 24)
2471 1.1 christos return DREG_MASK (dst0) | DREG_MASK (dst1);
2472 1.1 christos else if (aopcde == 13)
2473 1.1 christos return DREG_MASK (dst0) | DREG_MASK (dst1);
2474 1.1 christos else
2475 1.1 christos return 0;
2476 1.1 christos
2477 1.1 christos return 4;
2478 1.1 christos }
2479 1.1 christos
2480 1.1 christos static int
2481 1.1 christos decode_dsp32shift_0 (int iw0, int iw1)
2482 1.1 christos {
2483 1.1 christos /* dsp32shift
2484 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2485 1.1 christos | 1 | 1 | 0 | 0 |.M.| 1 | 1 | 0 | 0 | - | - |.sopcde............|
2486 1.1 christos |.sop...|.HLs...|.dst0......| - | - | - |.src0......|.src1......|
2487 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2488 1.1 christos int HLs = ((iw1 >> DSP32Shift_HLs_bits) & DSP32Shift_HLs_mask);
2489 1.1 christos int sop = ((iw1 >> DSP32Shift_sop_bits) & DSP32Shift_sop_mask);
2490 1.1 christos int src0 = ((iw1 >> DSP32Shift_src0_bits) & DSP32Shift_src0_mask);
2491 1.1 christos int src1 = ((iw1 >> DSP32Shift_src1_bits) & DSP32Shift_src1_mask);
2492 1.1 christos int dst0 = ((iw1 >> DSP32Shift_dst0_bits) & DSP32Shift_dst0_mask);
2493 1.1 christos int sopcde = ((iw0 >> (DSP32Shift_sopcde_bits - 16)) & DSP32Shift_sopcde_mask);
2494 1.1 christos
2495 1.1 christos if (sop == 0 && sopcde == 0)
2496 1.1 christos return HLs & 2 ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2497 1.1 christos else if (sop == 1 && sopcde == 0)
2498 1.1 christos return HLs & 2 ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2499 1.1 christos else if (sop == 2 && sopcde == 0)
2500 1.1 christos return HLs & 2 ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2501 1.1 christos else if (sop == 0 && sopcde == 3)
2502 1.1 christos return 0;
2503 1.1 christos else if (sop == 1 && sopcde == 3)
2504 1.1 christos return 0;
2505 1.1 christos else if (sop == 2 && sopcde == 3)
2506 1.1 christos return 0;
2507 1.1 christos else if (sop == 3 && sopcde == 3)
2508 1.1 christos return DREG_MASK (dst0);
2509 1.1 christos else if (sop == 0 && sopcde == 1)
2510 1.1 christos return DREG_MASK (dst0);
2511 1.1 christos else if (sop == 1 && sopcde == 1)
2512 1.1 christos return DREG_MASK (dst0);
2513 1.1 christos else if (sop == 2 && sopcde == 1)
2514 1.1 christos return DREG_MASK (dst0);
2515 1.1 christos else if (sopcde == 2)
2516 1.1 christos return DREG_MASK (dst0);
2517 1.1 christos else if (sopcde == 4)
2518 1.1 christos return DREG_MASK (dst0);
2519 1.1 christos else if (sop == 0 && sopcde == 5)
2520 1.1 christos return DREGL_MASK (dst0);
2521 1.1 christos else if (sop == 1 && sopcde == 5)
2522 1.1 christos return DREGL_MASK (dst0);
2523 1.1 christos else if (sop == 2 && sopcde == 5)
2524 1.1 christos return DREGL_MASK (dst0);
2525 1.1 christos else if (sop == 0 && sopcde == 6)
2526 1.1 christos return DREGL_MASK (dst0);
2527 1.1 christos else if (sop == 1 && sopcde == 6)
2528 1.1 christos return DREGL_MASK (dst0);
2529 1.1 christos else if (sop == 3 && sopcde == 6)
2530 1.1 christos return DREGL_MASK (dst0);
2531 1.1 christos else if (sop == 0 && sopcde == 7)
2532 1.1 christos return DREGL_MASK (dst0);
2533 1.1 christos else if (sop == 1 && sopcde == 7)
2534 1.1 christos return DREGL_MASK (dst0);
2535 1.1 christos else if (sop == 2 && sopcde == 7)
2536 1.1 christos return DREGL_MASK (dst0);
2537 1.1 christos else if (sop == 3 && sopcde == 7)
2538 1.1 christos return DREGL_MASK (dst0);
2539 1.1 christos else if (sop == 0 && sopcde == 8)
2540 1.1 christos return DREG_MASK (src0) | DREG_MASK (src1);
2541 1.1 christos #if 0
2542 1.1 christos {
2543 1.1 christos OUTS (outf, "BITMUX (");
2544 1.1 christos OUTS (outf, dregs (src0));
2545 1.1 christos OUTS (outf, ", ");
2546 1.1 christos OUTS (outf, dregs (src1));
2547 1.1 christos OUTS (outf, ", A0) (ASR)");
2548 1.1 christos }
2549 1.1 christos #endif
2550 1.1 christos else if (sop == 1 && sopcde == 8)
2551 1.1 christos return DREG_MASK (src0) | DREG_MASK (src1);
2552 1.1 christos #if 0
2553 1.1 christos {
2554 1.1 christos OUTS (outf, "BITMUX (");
2555 1.1 christos OUTS (outf, dregs (src0));
2556 1.1 christos OUTS (outf, ", ");
2557 1.1 christos OUTS (outf, dregs (src1));
2558 1.1 christos OUTS (outf, ", A0) (ASL)");
2559 1.1 christos }
2560 1.1 christos #endif
2561 1.1 christos else if (sopcde == 9)
2562 1.1 christos return sop < 2 ? DREGL_MASK (dst0) : DREG_MASK (dst0);
2563 1.1 christos else if (sopcde == 10)
2564 1.1 christos return DREG_MASK (dst0);
2565 1.1 christos else if (sop == 0 && sopcde == 11)
2566 1.1 christos return DREGL_MASK (dst0);
2567 1.1 christos else if (sop == 1 && sopcde == 11)
2568 1.1 christos return DREGL_MASK (dst0);
2569 1.1 christos else if (sop == 0 && sopcde == 12)
2570 1.1 christos return 0;
2571 1.1 christos else if (sop == 1 && sopcde == 12)
2572 1.1 christos return DREGL_MASK (dst0);
2573 1.1 christos else if (sop == 0 && sopcde == 13)
2574 1.1 christos return DREG_MASK (dst0);
2575 1.1 christos else if (sop == 1 && sopcde == 13)
2576 1.1 christos return DREG_MASK (dst0);
2577 1.1 christos else if (sop == 2 && sopcde == 13)
2578 1.1 christos return DREG_MASK (dst0);
2579 1.1 christos
2580 1.1 christos abort ();
2581 1.1 christos }
2582 1.1 christos
2583 1.1 christos static int
2584 1.1 christos decode_dsp32shiftimm_0 (int iw0, int iw1)
2585 1.1 christos {
2586 1.1 christos /* dsp32shiftimm
2587 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+
2588 1.1 christos | 1 | 1 | 0 | 0 |.M.| 1 | 1 | 0 | 1 | - | - |.sopcde............|
2589 1.1 christos |.sop...|.HLs...|.dst0......|.immag.................|.src1......|
2590 1.1 christos +---+---+---+---|---+---+---+---|---+---+---+---|---+---+---+---+ */
2591 1.1 christos int sop = ((iw1 >> DSP32ShiftImm_sop_bits) & DSP32ShiftImm_sop_mask);
2592 1.1 christos int bit8 = ((iw1 >> 8) & 0x1);
2593 1.1 christos int dst0 = ((iw1 >> DSP32ShiftImm_dst0_bits) & DSP32ShiftImm_dst0_mask);
2594 1.1 christos int sopcde = ((iw0 >> (DSP32ShiftImm_sopcde_bits - 16)) & DSP32ShiftImm_sopcde_mask);
2595 1.1 christos int HLs = ((iw1 >> DSP32ShiftImm_HLs_bits) & DSP32ShiftImm_HLs_mask);
2596 1.1 christos
2597 1.1 christos
2598 1.1 christos if (sop == 0 && sopcde == 0)
2599 1.1 christos return HLs & 2 ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2600 1.1 christos else if (sop == 1 && sopcde == 0 && bit8 == 0)
2601 1.1 christos return HLs & 2 ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2602 1.1 christos else if (sop == 1 && sopcde == 0 && bit8 == 1)
2603 1.1 christos return HLs & 2 ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2604 1.1 christos else if (sop == 2 && sopcde == 0 && bit8 == 0)
2605 1.1 christos return HLs & 2 ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2606 1.1 christos else if (sop == 2 && sopcde == 0 && bit8 == 1)
2607 1.1 christos return HLs & 2 ? DREGH_MASK (dst0) : DREGL_MASK (dst0);
2608 1.1 christos else if (sop == 2 && sopcde == 3 && HLs == 1)
2609 1.1 christos return 0;
2610 1.1 christos else if (sop == 0 && sopcde == 3 && HLs == 0 && bit8 == 0)
2611 1.1 christos return 0;
2612 1.1 christos else if (sop == 0 && sopcde == 3 && HLs == 0 && bit8 == 1)
2613 1.1 christos return 0;
2614 1.1 christos else if (sop == 0 && sopcde == 3 && HLs == 1 && bit8 == 0)
2615 1.1 christos return 0;
2616 1.1 christos else if (sop == 0 && sopcde == 3 && HLs == 1 && bit8 == 1)
2617 1.1 christos return 0;
2618 1.1 christos else if (sop == 1 && sopcde == 3 && HLs == 0)
2619 1.1 christos return 0;
2620 1.1 christos else if (sop == 1 && sopcde == 3 && HLs == 1)
2621 1.1 christos return 0;
2622 1.1 christos else if (sop == 2 && sopcde == 3 && HLs == 0)
2623 1.1 christos return 0;
2624 1.1 christos else if (sop == 1 && sopcde == 1 && bit8 == 0)
2625 1.1 christos return DREG_MASK (dst0);
2626 1.1 christos else if (sop == 1 && sopcde == 1 && bit8 == 1)
2627 1.1 christos return DREG_MASK (dst0);
2628 1.1 christos else if (sop == 2 && sopcde == 1 && bit8 == 1)
2629 1.1 christos return DREG_MASK (dst0);
2630 1.1 christos else if (sop == 2 && sopcde == 1 && bit8 == 0)
2631 1.1 christos return DREG_MASK (dst0);
2632 1.1 christos else if (sop == 0 && sopcde == 1)
2633 1.1 christos return DREG_MASK (dst0);
2634 1.1 christos else if (sop == 1 && sopcde == 2)
2635 1.1 christos return DREG_MASK (dst0);
2636 1.1 christos else if (sop == 2 && sopcde == 2 && bit8 == 1)
2637 1.1 christos return DREG_MASK (dst0);
2638 1.1 christos else if (sop == 2 && sopcde == 2 && bit8 == 0)
2639 1.1 christos return DREG_MASK (dst0);
2640 1.1 christos else if (sop == 3 && sopcde == 2)
2641 1.1 christos return DREG_MASK (dst0);
2642 1.1 christos else if (sop == 0 && sopcde == 2)
2643 1.1 christos return DREG_MASK (dst0);
2644 1.1 christos
2645 1.1 christos abort ();
2646 1.1 christos }
2647 1.1 christos
2648 1.1 christos int
2649 1.1 christos insn_regmask (int iw0, int iw1)
2650 1.1 christos {
2651 1.1 christos if ((iw0 & 0xf7ff) == 0xc003 && iw1 == 0x1800)
2652 1.1 christos return 0; /* MNOP */
2653 1.1 christos else if ((iw0 & 0xff00) == 0x0000)
2654 1.1 christos return decode_ProgCtrl_0 (iw0);
2655 1.1 christos else if ((iw0 & 0xffc0) == 0x0240)
2656 1.1 christos abort ();
2657 1.1 christos else if ((iw0 & 0xff80) == 0x0100)
2658 1.1 christos abort ();
2659 1.1 christos else if ((iw0 & 0xfe00) == 0x0400)
2660 1.1 christos abort ();
2661 1.1 christos else if ((iw0 & 0xfe00) == 0x0600)
2662 1.1 christos abort ();
2663 1.1 christos else if ((iw0 & 0xf800) == 0x0800)
2664 1.1 christos abort ();
2665 1.1 christos else if ((iw0 & 0xffe0) == 0x0200)
2666 1.1 christos abort ();
2667 1.1 christos else if ((iw0 & 0xff00) == 0x0300)
2668 1.1 christos abort ();
2669 1.1 christos else if ((iw0 & 0xf000) == 0x1000)
2670 1.1 christos abort ();
2671 1.1 christos else if ((iw0 & 0xf000) == 0x2000)
2672 1.1 christos abort ();
2673 1.1 christos else if ((iw0 & 0xf000) == 0x3000)
2674 1.1 christos abort ();
2675 1.1 christos else if ((iw0 & 0xfc00) == 0x4000)
2676 1.1 christos abort ();
2677 1.1 christos else if ((iw0 & 0xfe00) == 0x4400)
2678 1.1 christos abort ();
2679 1.1 christos else if ((iw0 & 0xf800) == 0x4800)
2680 1.1 christos abort ();
2681 1.1 christos else if ((iw0 & 0xf000) == 0x5000)
2682 1.1 christos abort ();
2683 1.1 christos else if ((iw0 & 0xf800) == 0x6000)
2684 1.1 christos abort ();
2685 1.1 christos else if ((iw0 & 0xf800) == 0x6800)
2686 1.1 christos abort ();
2687 1.1 christos else if ((iw0 & 0xf000) == 0x8000)
2688 1.1 christos return decode_LDSTpmod_0 (iw0);
2689 1.1 christos else if ((iw0 & 0xff60) == 0x9e60)
2690 1.1 christos return decode_dagMODim_0 (iw0);
2691 1.1 christos else if ((iw0 & 0xfff0) == 0x9f60)
2692 1.1 christos return decode_dagMODik_0 (iw0);
2693 1.1 christos else if ((iw0 & 0xfc00) == 0x9c00)
2694 1.1 christos return decode_dspLDST_0 (iw0);
2695 1.1 christos else if ((iw0 & 0xf000) == 0x9000)
2696 1.1 christos return decode_LDST_0 (iw0);
2697 1.1 christos else if ((iw0 & 0xfc00) == 0xb800)
2698 1.1 christos return decode_LDSTiiFP_0 (iw0);
2699 1.1 christos else if ((iw0 & 0xe000) == 0xA000)
2700 1.1 christos return decode_LDSTii_0 (iw0);
2701 1.1 christos else if ((iw0 & 0xff80) == 0xe080 && (iw1 & 0x0C00) == 0x0000)
2702 1.1 christos abort ();
2703 1.1 christos else if ((iw0 & 0xff00) == 0xe100 && (iw1 & 0x0000) == 0x0000)
2704 1.1 christos abort ();
2705 1.1 christos else if ((iw0 & 0xfe00) == 0xe200 && (iw1 & 0x0000) == 0x0000)
2706 1.1 christos abort ();
2707 1.1 christos else if ((iw0 & 0xfc00) == 0xe400 && (iw1 & 0x0000) == 0x0000)
2708 1.1 christos abort ();
2709 1.1 christos else if ((iw0 & 0xfffe) == 0xe800 && (iw1 & 0x0000) == 0x0000)
2710 1.1 christos abort ();
2711 1.1 christos else if ((iw0 & 0xf600) == 0xc000 && (iw1 & 0x0000) == 0x0000)
2712 1.1 christos return decode_dsp32mac_0 (iw0, iw1);
2713 1.1 christos else if ((iw0 & 0xf600) == 0xc200 && (iw1 & 0x0000) == 0x0000)
2714 1.1 christos return decode_dsp32mult_0 (iw0, iw1);
2715 1.1 christos else if ((iw0 & 0xf7c0) == 0xc400 && (iw1 & 0x0000) == 0x0000)
2716 1.1 christos return decode_dsp32alu_0 (iw0, iw1);
2717 1.1 christos else if ((iw0 & 0xf780) == 0xc600 && (iw1 & 0x01c0) == 0x0000)
2718 1.1 christos return decode_dsp32shift_0 (iw0, iw1);
2719 1.1 christos else if ((iw0 & 0xf780) == 0xc680 && (iw1 & 0x0000) == 0x0000)
2720 1.1 christos return decode_dsp32shiftimm_0 (iw0, iw1);
2721 1.1 christos else if ((iw0 & 0xff00) == 0xf800)
2722 1.1 christos abort ();
2723 1.1 christos else if ((iw0 & 0xFFC0) == 0xf000 && (iw1 & 0x0000) == 0x0000)
2724 1.1 christos abort ();
2725 1.1 christos
2726 abort ();
2727 }
2728