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