]> git.ipfire.org Git - thirdparty/binutils-gdb.git/blob - gas/config/tc-z80.c
Add support for 8-bit and 24-bit shifts in the z80 assembler.
[thirdparty/binutils-gdb.git] / gas / config / tc-z80.c
1 /* tc-z80.c -- Assemble code for the Zilog Z80, Z180, EZ80 and ASCII R800
2 Copyright (C) 2005-2021 Free Software Foundation, Inc.
3 Contributed by Arnold Metselaar <arnold_m@operamail.com>
4
5 This file is part of GAS, the GNU Assembler.
6
7 GAS is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3, or (at your option)
10 any later version.
11
12 GAS is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
16
17 You should have received a copy of the GNU General Public License
18 along with GAS; see the file COPYING. If not, write to the Free
19 Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA
20 02110-1301, USA. */
21
22 #include "as.h"
23 #include "safe-ctype.h"
24 #include "subsegs.h"
25 #include "elf/z80.h"
26 #include "dwarf2dbg.h"
27 #include "dw2gencfi.h"
28
29 /* Exported constants. */
30 const char comment_chars[] = ";\0";
31 const char line_comment_chars[] = "#;\0";
32 const char line_separator_chars[] = "\0";
33 const char EXP_CHARS[] = "eE\0";
34 const char FLT_CHARS[] = "RrDdFfSsHh\0";
35
36 /* For machine specific options. */
37 const char * md_shortopts = ""; /* None yet. */
38
39 enum options
40 {
41 OPTION_MARCH = OPTION_MD_BASE,
42 OPTION_MACH_Z80,
43 OPTION_MACH_R800,
44 OPTION_MACH_Z180,
45 OPTION_MACH_EZ80_Z80,
46 OPTION_MACH_EZ80_ADL,
47 OPTION_MACH_INST,
48 OPTION_MACH_NO_INST,
49 OPTION_MACH_IUD,
50 OPTION_MACH_WUD,
51 OPTION_MACH_FUD,
52 OPTION_MACH_IUP,
53 OPTION_MACH_WUP,
54 OPTION_MACH_FUP,
55 OPTION_FP_SINGLE_FORMAT,
56 OPTION_FP_DOUBLE_FORMAT,
57 OPTION_COMPAT_LL_PREFIX,
58 OPTION_COMPAT_COLONLESS,
59 OPTION_COMPAT_SDCC
60 };
61
62 #define INS_Z80 (1 << 0)
63 #define INS_R800 (1 << 1)
64 #define INS_GBZ80 (1 << 2)
65 #define INS_Z180 (1 << 3)
66 #define INS_EZ80 (1 << 4)
67 #define INS_Z80N (1 << 5)
68 #define INS_MARCH_MASK 0xffff
69
70 #define INS_IDX_HALF (1 << 16)
71 #define INS_IN_F_C (1 << 17)
72 #define INS_OUT_C_0 (1 << 18)
73 #define INS_SLI (1 << 19)
74 #define INS_ROT_II_LD (1 << 20) /* instructions like SLA (ii+d),r; which is: LD r,(ii+d); SLA r; LD (ii+d),r */
75 #define INS_TUNE_MASK 0xffff0000
76
77 #define INS_NOT_GBZ80 (INS_Z80 | INS_Z180 | INS_R800 | INS_EZ80 | INS_Z80N)
78
79 #define INS_ALL 0
80 #define INS_UNDOC (INS_IDX_HALF | INS_IN_F_C)
81 #define INS_UNPORT (INS_OUT_C_0 | INS_SLI | INS_ROT_II_LD)
82
83 struct option md_longopts[] =
84 {
85 { "march", required_argument, NULL, OPTION_MARCH},
86 { "z80", no_argument, NULL, OPTION_MACH_Z80},
87 { "r800", no_argument, NULL, OPTION_MACH_R800},
88 { "z180", no_argument, NULL, OPTION_MACH_Z180},
89 { "ez80", no_argument, NULL, OPTION_MACH_EZ80_Z80},
90 { "ez80-adl", no_argument, NULL, OPTION_MACH_EZ80_ADL},
91 { "fp-s", required_argument, NULL, OPTION_FP_SINGLE_FORMAT},
92 { "fp-d", required_argument, NULL, OPTION_FP_DOUBLE_FORMAT},
93 { "strict", no_argument, NULL, OPTION_MACH_FUD},
94 { "full", no_argument, NULL, OPTION_MACH_IUP},
95 { "with-inst", required_argument, NULL, OPTION_MACH_INST},
96 { "Wnins", required_argument, NULL, OPTION_MACH_INST},
97 { "without-inst", required_argument, NULL, OPTION_MACH_NO_INST},
98 { "local-prefix", required_argument, NULL, OPTION_COMPAT_LL_PREFIX},
99 { "colonless", no_argument, NULL, OPTION_COMPAT_COLONLESS},
100 { "sdcc", no_argument, NULL, OPTION_COMPAT_SDCC},
101 { "Fins", required_argument, NULL, OPTION_MACH_NO_INST},
102 { "ignore-undocumented-instructions", no_argument, NULL, OPTION_MACH_IUD },
103 { "Wnud", no_argument, NULL, OPTION_MACH_IUD },
104 { "warn-undocumented-instructions", no_argument, NULL, OPTION_MACH_WUD },
105 { "Wud", no_argument, NULL, OPTION_MACH_WUD },
106 { "forbid-undocumented-instructions", no_argument, NULL, OPTION_MACH_FUD },
107 { "Fud", no_argument, NULL, OPTION_MACH_FUD },
108 { "ignore-unportable-instructions", no_argument, NULL, OPTION_MACH_IUP },
109 { "Wnup", no_argument, NULL, OPTION_MACH_IUP },
110 { "warn-unportable-instructions", no_argument, NULL, OPTION_MACH_WUP },
111 { "Wup", no_argument, NULL, OPTION_MACH_WUP },
112 { "forbid-unportable-instructions", no_argument, NULL, OPTION_MACH_FUP },
113 { "Fup", no_argument, NULL, OPTION_MACH_FUP },
114
115 { NULL, no_argument, NULL, 0 }
116 } ;
117
118 size_t md_longopts_size = sizeof (md_longopts);
119
120 extern int coff_flags;
121 /* Instruction classes that silently assembled. */
122 static int ins_ok = INS_Z80 | INS_UNDOC;
123 /* Instruction classes that generate errors. */
124 static int ins_err = ~(INS_Z80 | INS_UNDOC);
125 /* eZ80 CPU mode (ADL or Z80) */
126 static int cpu_mode = 0; /* 0 - Z80, 1 - ADL */
127 /* accept SDCC specific instruction encoding */
128 static int sdcc_compat = 0;
129 /* accept colonless labels */
130 static int colonless_labels = 0;
131 /* local label prefix (NULL - default) */
132 static const char *local_label_prefix = NULL;
133 /* floating point support */
134 typedef const char *(*str_to_float_t)(char *litP, int *sizeP);
135 static str_to_float_t str_to_float;
136 static str_to_float_t str_to_double;
137
138 /* mode of current instruction */
139 #define INST_MODE_S 0 /* short data mode */
140 #define INST_MODE_IS 0 /* short instruction mode */
141 #define INST_MODE_L 2 /* long data mode */
142 #define INST_MODE_IL 1 /* long instruction mode */
143 #define INST_MODE_FORCED 4 /* CPU mode changed by instruction suffix*/
144 static char inst_mode;
145
146 struct match_info
147 {
148 const char *name;
149 int ins_ok;
150 int ins_err;
151 int cpu_mode;
152 const char *comment;
153 };
154
155 static const struct match_info
156 match_cpu_table [] =
157 {
158 {"z80", INS_Z80, 0, 0, "Zilog Z80" },
159 {"ez80", INS_EZ80, 0, 0, "Zilog eZ80" },
160 {"gbz80", INS_GBZ80, INS_UNDOC|INS_UNPORT, 0, "GameBoy Z80" },
161 {"r800", INS_R800, INS_UNPORT, 0, "Ascii R800" },
162 {"z180", INS_Z180, INS_UNDOC|INS_UNPORT, 0, "Zilog Z180" },
163 {"z80n", INS_Z80N, 0, 0, "Z80 Next" }
164 };
165
166 static const struct match_info
167 match_ext_table [] =
168 {
169 {"full", INS_UNDOC|INS_UNPORT, 0, 0, "assemble all known instructions" },
170 {"adl", 0, 0, 1, "eZ80 ADL mode by default" },
171 {"xyhl", INS_IDX_HALF, 0, 0, "instructions with halves of index registers" },
172 {"infc", INS_IN_F_C, 0, 0, "instruction IN F,(C)" },
173 {"outc0", INS_OUT_C_0, 0, 0, "instruction OUT (C),0" },
174 {"sli", INS_SLI, 0, 0, "instruction known as SLI, SLL, or SL1" },
175 {"xdcb", INS_ROT_II_LD, 0, 0, "instructions like RL (IX+d),R (DD/FD CB dd oo)" }
176 };
177
178 static void
179 setup_march (const char *name, int *ok, int *err, int *mode)
180 {
181 unsigned i;
182 size_t len = strcspn (name, "+-");
183 for (i = 0; i < ARRAY_SIZE (match_cpu_table); ++i)
184 if (!strncasecmp (name, match_cpu_table[i].name, len)
185 && strlen (match_cpu_table[i].name) == len)
186 {
187 *ok = match_cpu_table[i].ins_ok;
188 *err = match_cpu_table[i].ins_err;
189 *mode = match_cpu_table[i].cpu_mode;
190 break;
191 }
192
193 if (i >= ARRAY_SIZE (match_cpu_table))
194 as_fatal (_("Invalid CPU is specified: %s"), name);
195
196 while (name[len])
197 {
198 name = &name[len + 1];
199 len = strcspn (name, "+-");
200 for (i = 0; i < ARRAY_SIZE (match_ext_table); ++i)
201 if (!strncasecmp (name, match_ext_table[i].name, len)
202 && strlen (match_ext_table[i].name) == len)
203 {
204 if (name[-1] == '+')
205 {
206 *ok |= match_ext_table[i].ins_ok;
207 *err &= ~match_ext_table[i].ins_ok;
208 *mode |= match_ext_table[i].cpu_mode;
209 }
210 else
211 {
212 *ok &= ~match_ext_table[i].ins_ok;
213 *err |= match_ext_table[i].ins_ok;
214 *mode &= ~match_ext_table[i].cpu_mode;
215 }
216 break;
217 }
218 if (i >= ARRAY_SIZE (match_ext_table))
219 as_fatal (_("Invalid EXTENSION is specified: %s"), name);
220 }
221 }
222
223 static int
224 setup_instruction (const char *inst, int *add, int *sub)
225 {
226 int n;
227 if (!strcmp (inst, "idx-reg-halves"))
228 n = INS_IDX_HALF;
229 else if (!strcmp (inst, "sli"))
230 n = INS_SLI;
231 else if (!strcmp (inst, "op-ii-ld"))
232 n = INS_ROT_II_LD;
233 else if (!strcmp (inst, "in-f-c"))
234 n = INS_IN_F_C;
235 else if (!strcmp (inst, "out-c-0"))
236 n = INS_OUT_C_0;
237 else
238 return 0;
239 *add |= n;
240 *sub &= ~n;
241 return 1;
242 }
243
244 static const char *
245 str_to_zeda32 (char *litP, int *sizeP);
246 static const char *
247 str_to_float48 (char *litP, int *sizeP);
248 static const char *
249 str_to_ieee754_h (char *litP, int *sizeP);
250 static const char *
251 str_to_ieee754_s (char *litP, int *sizeP);
252 static const char *
253 str_to_ieee754_d (char *litP, int *sizeP);
254
255 static str_to_float_t
256 get_str_to_float (const char *arg)
257 {
258 if (strcasecmp (arg, "zeda32") == 0)
259 return str_to_zeda32;
260
261 if (strcasecmp (arg, "math48") == 0)
262 return str_to_float48;
263
264 if (strcasecmp (arg, "half") != 0)
265 return str_to_ieee754_h;
266
267 if (strcasecmp (arg, "single") != 0)
268 return str_to_ieee754_s;
269
270 if (strcasecmp (arg, "double") != 0)
271 return str_to_ieee754_d;
272
273 if (strcasecmp (arg, "ieee754") == 0)
274 as_fatal (_("invalid floating point numbers type `%s'"), arg);
275 return NULL;
276 }
277
278 static int
279 setup_instruction_list (const char *list, int *add, int *sub)
280 {
281 char buf[16];
282 const char *b;
283 const char *e;
284 int sz;
285 int res = 0;
286 for (b = list; *b != '\0';)
287 {
288 e = strchr (b, ',');
289 if (e == NULL)
290 sz = strlen (b);
291 else
292 sz = e - b;
293 if (sz == 0 || sz >= (int)sizeof (buf))
294 {
295 as_bad (_("invalid INST in command line: %s"), b);
296 return 0;
297 }
298 memcpy (buf, b, sz);
299 buf[sz] = '\0';
300 if (setup_instruction (buf, add, sub))
301 res++;
302 else
303 {
304 as_bad (_("invalid INST in command line: %s"), buf);
305 return 0;
306 }
307 b = &b[sz];
308 if (*b == ',')
309 ++b;
310 }
311 return res;
312 }
313
314 int
315 md_parse_option (int c, const char* arg)
316 {
317 switch (c)
318 {
319 default:
320 return 0;
321 case OPTION_MARCH:
322 setup_march (arg, & ins_ok, & ins_err, & cpu_mode);
323 break;
324 case OPTION_MACH_Z80:
325 setup_march ("z80", & ins_ok, & ins_err, & cpu_mode);
326 break;
327 case OPTION_MACH_R800:
328 setup_march ("r800", & ins_ok, & ins_err, & cpu_mode);
329 break;
330 case OPTION_MACH_Z180:
331 setup_march ("z180", & ins_ok, & ins_err, & cpu_mode);
332 break;
333 case OPTION_MACH_EZ80_Z80:
334 setup_march ("ez80", & ins_ok, & ins_err, & cpu_mode);
335 break;
336 case OPTION_MACH_EZ80_ADL:
337 setup_march ("ez80+adl", & ins_ok, & ins_err, & cpu_mode);
338 break;
339 case OPTION_FP_SINGLE_FORMAT:
340 str_to_float = get_str_to_float (arg);
341 break;
342 case OPTION_FP_DOUBLE_FORMAT:
343 str_to_double = get_str_to_float (arg);
344 break;
345 case OPTION_MACH_INST:
346 if ((ins_ok & INS_GBZ80) == 0)
347 return setup_instruction_list (arg, & ins_ok, & ins_err);
348 break;
349 case OPTION_MACH_NO_INST:
350 if ((ins_ok & INS_GBZ80) == 0)
351 return setup_instruction_list (arg, & ins_err, & ins_ok);
352 break;
353 case OPTION_MACH_WUD:
354 case OPTION_MACH_IUD:
355 if ((ins_ok & INS_GBZ80) == 0)
356 {
357 ins_ok |= INS_UNDOC;
358 ins_err &= ~INS_UNDOC;
359 }
360 break;
361 case OPTION_MACH_WUP:
362 case OPTION_MACH_IUP:
363 if ((ins_ok & INS_GBZ80) == 0)
364 {
365 ins_ok |= INS_UNDOC | INS_UNPORT;
366 ins_err &= ~(INS_UNDOC | INS_UNPORT);
367 }
368 break;
369 case OPTION_MACH_FUD:
370 if ((ins_ok & (INS_R800 | INS_GBZ80)) == 0)
371 {
372 ins_ok &= (INS_UNDOC | INS_UNPORT);
373 ins_err |= INS_UNDOC | INS_UNPORT;
374 }
375 break;
376 case OPTION_MACH_FUP:
377 ins_ok &= ~INS_UNPORT;
378 ins_err |= INS_UNPORT;
379 break;
380 case OPTION_COMPAT_LL_PREFIX:
381 local_label_prefix = (arg && *arg) ? arg : NULL;
382 break;
383 case OPTION_COMPAT_SDCC:
384 sdcc_compat = 1;
385 break;
386 case OPTION_COMPAT_COLONLESS:
387 colonless_labels = 1;
388 break;
389 }
390
391 return 1;
392 }
393
394 void
395 md_show_usage (FILE * f)
396 {
397 unsigned i;
398 fprintf (f, _("\n\
399 CPU model options:\n\
400 -march=CPU[+EXT...][-EXT...]\n\
401 \t\t\t generate code for CPU, where CPU is one of:\n"));
402 for (i = 0; i < ARRAY_SIZE(match_cpu_table); ++i)
403 fprintf (f, " %-8s\t\t %s\n", match_cpu_table[i].name, match_cpu_table[i].comment);
404 fprintf (f, _("And EXT is combination (+EXT - add, -EXT - remove) of:\n"));
405 for (i = 0; i < ARRAY_SIZE(match_ext_table); ++i)
406 fprintf (f, " %-8s\t\t %s\n", match_ext_table[i].name, match_ext_table[i].comment);
407 fprintf (f, _("\n\
408 Compatibility options:\n\
409 -local-prefix=TEXT\t treat labels prefixed by TEXT as local\n\
410 -colonless\t\t permit colonless labels\n\
411 -sdcc\t\t\t accept SDCC specific instruction syntax\n\
412 -fp-s=FORMAT\t\t set single precision FP numbers format\n\
413 -fp-d=FORMAT\t\t set double precision FP numbers format\n\
414 Where FORMAT one of:\n\
415 ieee754\t\t IEEE754 compatible (depends on directive)\n\
416 half\t\t\t IEEE754 half precision (16 bit)\n\
417 single\t\t IEEE754 single precision (32 bit)\n\
418 double\t\t IEEE754 double precision (64 bit)\n\
419 zeda32\t\t Zeda z80float library 32 bit format\n\
420 math48\t\t 48 bit format from Math48 library\n\
421 \n\
422 Default: -march=z80+xyhl+infc\n"));
423 }
424
425 static symbolS * zero;
426
427 struct reg_entry
428 {
429 const char* name;
430 int number;
431 int isa;
432 };
433 #define R_STACKABLE (0x80)
434 #define R_ARITH (0x40)
435 #define R_IX (0x20)
436 #define R_IY (0x10)
437 #define R_INDEX (R_IX | R_IY)
438
439 #define REG_A (7)
440 #define REG_B (0)
441 #define REG_C (1)
442 #define REG_D (2)
443 #define REG_E (3)
444 #define REG_H (4)
445 #define REG_L (5)
446 #define REG_F (6 | 8)
447 #define REG_I (9)
448 #define REG_R (10)
449 #define REG_MB (11)
450
451 #define REG_AF (3 | R_STACKABLE)
452 #define REG_BC (0 | R_STACKABLE | R_ARITH)
453 #define REG_DE (1 | R_STACKABLE | R_ARITH)
454 #define REG_HL (2 | R_STACKABLE | R_ARITH)
455 #define REG_IX (REG_HL | R_IX)
456 #define REG_IY (REG_HL | R_IY)
457 #define REG_SP (3 | R_ARITH)
458
459 static const struct reg_entry regtable[] =
460 {
461 {"a", REG_A, INS_ALL },
462 {"af", REG_AF, INS_ALL },
463 {"b", REG_B, INS_ALL },
464 {"bc", REG_BC, INS_ALL },
465 {"c", REG_C, INS_ALL },
466 {"d", REG_D, INS_ALL },
467 {"de", REG_DE, INS_ALL },
468 {"e", REG_E, INS_ALL },
469 {"f", REG_F, INS_IN_F_C | INS_Z80N | INS_R800 },
470 {"h", REG_H, INS_ALL },
471 {"hl", REG_HL, INS_ALL },
472 {"i", REG_I, INS_NOT_GBZ80 },
473 {"ix", REG_IX, INS_NOT_GBZ80 },
474 {"ixh", REG_H | R_IX, INS_IDX_HALF | INS_EZ80 | INS_R800 | INS_Z80N },
475 {"ixl", REG_L | R_IX, INS_IDX_HALF | INS_EZ80 | INS_R800 | INS_Z80N },
476 {"iy", REG_IY, INS_NOT_GBZ80 },
477 {"iyh", REG_H | R_IY, INS_IDX_HALF | INS_EZ80 | INS_R800 | INS_Z80N },
478 {"iyl", REG_L | R_IY, INS_IDX_HALF | INS_EZ80 | INS_R800 | INS_Z80N },
479 {"l", REG_L, INS_ALL },
480 {"mb", REG_MB, INS_EZ80 },
481 {"r", REG_R, INS_NOT_GBZ80 },
482 {"sp", REG_SP, INS_ALL },
483 } ;
484
485 #define BUFLEN 8 /* Large enough for any keyword. */
486
487 void
488 md_begin (void)
489 {
490 expressionS nul, reg;
491 char * p;
492 unsigned int i, j, k;
493 char buf[BUFLEN];
494
495 memset (&reg, 0, sizeof (reg));
496 memset (&nul, 0, sizeof (nul));
497
498 if (ins_ok & INS_EZ80) /* if select EZ80 cpu then */
499 listing_lhs_width = 6; /* use 6 bytes per line in the listing */
500
501 reg.X_op = O_register;
502 reg.X_md = 0;
503 reg.X_add_symbol = reg.X_op_symbol = 0;
504 for ( i = 0 ; i < ARRAY_SIZE ( regtable ) ; ++i )
505 {
506 if (regtable[i].isa && !(regtable[i].isa & ins_ok))
507 continue;
508 reg.X_add_number = regtable[i].number;
509 k = strlen ( regtable[i].name );
510 buf[k] = 0;
511 if ( k+1 < BUFLEN )
512 {
513 for ( j = ( 1<<k ) ; j ; --j )
514 {
515 for ( k = 0 ; regtable[i].name[k] ; ++k )
516 {
517 buf[k] = ( j & ( 1<<k ) ) ? TOUPPER (regtable[i].name[k]) : regtable[i].name[k];
518 }
519 symbolS * psym = symbol_find_or_make (buf);
520 S_SET_SEGMENT (psym, reg_section);
521 symbol_set_value_expression (psym, &reg);
522 }
523 }
524 }
525 p = input_line_pointer;
526 input_line_pointer = (char *) "0";
527 nul.X_md=0;
528 expression (& nul);
529 input_line_pointer = p;
530 zero = make_expr_symbol (& nul);
531 /* We do not use relaxation (yet). */
532 linkrelax = 0;
533 }
534
535 void
536 z80_md_end (void)
537 {
538 int mach_type;
539
540 switch (ins_ok & INS_MARCH_MASK)
541 {
542 case INS_Z80:
543 mach_type = bfd_mach_z80;
544 break;
545 case INS_R800:
546 mach_type = bfd_mach_r800;
547 break;
548 case INS_Z180:
549 mach_type = bfd_mach_z180;
550 break;
551 case INS_GBZ80:
552 mach_type = bfd_mach_gbz80;
553 break;
554 case INS_EZ80:
555 mach_type = cpu_mode ? bfd_mach_ez80_adl : bfd_mach_ez80_z80;
556 break;
557 case INS_Z80N:
558 mach_type = bfd_mach_z80n;
559 break;
560 default:
561 mach_type = 0;
562 }
563 bfd_set_arch_mach (stdoutput, TARGET_ARCH, mach_type);
564 }
565
566 #if defined (OBJ_ELF) || defined (OBJ_MAYBE_ELF)
567 void
568 z80_elf_final_processing (void)
569 {/* nothing to do, all is done by BFD itself */
570 /*
571 unsigned elf_flags;
572 elf_elfheader (stdoutput)->e_flags = elf_flags;
573 */
574 }
575 #endif
576
577 static const char *
578 skip_space (const char *s)
579 {
580 while (*s == ' ' || *s == '\t')
581 ++s;
582 return s;
583 }
584
585 /* A non-zero return-value causes a continue in the
586 function read_a_source_file () in ../read.c. */
587 int
588 z80_start_line_hook (void)
589 {
590 char *p, quote;
591 char buf[4];
592
593 /* Convert one character constants. */
594 for (p = input_line_pointer; *p && *p != '\n'; ++p)
595 {
596 switch (*p)
597 {
598 case '\'':
599 if (p[1] != 0 && p[1] != '\'' && p[2] == '\'')
600 {
601 snprintf (buf, 4, "%3d", (unsigned char)p[1]);
602 *p++ = buf[0];
603 *p++ = buf[1];
604 *p++ = buf[2];
605 break;
606 }
607 /* Fall through. */
608 case '"':
609 for (quote = *p++; quote != *p && '\n' != *p; ++p)
610 /* No escapes. */ ;
611 if (quote != *p)
612 {
613 as_bad (_("-- unterminated string"));
614 ignore_rest_of_line ();
615 return 1;
616 }
617 break;
618 case '#': /* force to use next expression as immediate value in SDCC */
619 if (!sdcc_compat)
620 break;
621 if (ISSPACE(p[1]) && *skip_space (p + 1) == '(')
622 { /* ld a,# (expr)... -> ld a,0+(expr)... */
623 *p++ = '0';
624 *p = '+';
625 }
626 else /* ld a,#(expr)... -> ld a,+(expr); ld a,#expr -> ld a, expr */
627 *p = (p[1] == '(') ? '+' : ' ';
628 break;
629 }
630 }
631 /* Check for <label>[:] =|([.](EQU|DEFL)) <value>. */
632 if (is_name_beginner (*input_line_pointer))
633 {
634 char *name;
635 char c, *rest, *line_start;
636 int len;
637
638 line_start = input_line_pointer;
639 if (ignore_input ())
640 return 0;
641 c = get_symbol_name (&name);
642 rest = input_line_pointer + 1;
643 if (c == ':' && *rest == ':')
644 {
645 /* remove second colon if SDCC compatibility enabled */
646 if (sdcc_compat)
647 *rest = ' ';
648 ++rest;
649 }
650 rest = (char*)skip_space (rest);
651 if (*rest == '=')
652 len = (rest[1] == '=') ? 2 : 1;
653 else
654 {
655 if (*rest == '.')
656 ++rest;
657 if (strncasecmp (rest, "EQU", 3) == 0)
658 len = 3;
659 else if (strncasecmp (rest, "DEFL", 4) == 0)
660 len = 4;
661 else
662 len = 0;
663 }
664 if (len && (len <= 2 || !ISALPHA (rest[len])))
665 {
666 /* Handle assignment here. */
667 if (line_start[-1] == '\n')
668 {
669 bump_line_counters ();
670 LISTING_NEWLINE ();
671 }
672 input_line_pointer = rest + len - 1;
673 /* Allow redefining with "DEFL" (len == 4), but not with "EQU". */
674 switch (len)
675 {
676 case 1: /* label = expr */
677 case 4: /* label DEFL expr */
678 equals (name, 1);
679 break;
680 case 2: /* label == expr */
681 case 3: /* label EQU expr */
682 equals (name, 0);
683 break;
684 }
685 return 1;
686 }
687 else
688 {
689 /* Restore line and pointer. */
690 (void) restore_line_pointer (c);
691 input_line_pointer = line_start;
692 }
693 }
694 return 0;
695 }
696
697 symbolS *
698 md_undefined_symbol (char *name ATTRIBUTE_UNUSED)
699 {
700 return NULL;
701 }
702
703 const char *
704 md_atof (int type, char *litP, int *sizeP)
705 {
706 switch (type)
707 {
708 case 'f':
709 case 'F':
710 case 's':
711 case 'S':
712 if (str_to_float)
713 return str_to_float (litP, sizeP);
714 break;
715 case 'd':
716 case 'D':
717 case 'r':
718 case 'R':
719 if (str_to_double)
720 return str_to_double (litP, sizeP);
721 break;
722 }
723 return ieee_md_atof (type, litP, sizeP, false);
724 }
725
726 valueT
727 md_section_align (segT seg ATTRIBUTE_UNUSED, valueT size)
728 {
729 return size;
730 }
731
732 long
733 md_pcrel_from (fixS * fixp)
734 {
735 return fixp->fx_where + fixp->fx_frag->fr_address;
736 }
737
738 typedef const char * (asfunc)(char, char, const char*);
739
740 typedef struct _table_t
741 {
742 const char* name;
743 unsigned char prefix;
744 unsigned char opcode;
745 asfunc * fp;
746 unsigned inss; /*0 - all CPU types or list of supported INS_* */
747 } table_t;
748
749 /* Compares the key for structs that start with a char * to the key. */
750 static int
751 key_cmp (const void * a, const void * b)
752 {
753 const char *str_a, *str_b;
754
755 str_a = *((const char**)a);
756 str_b = *((const char**)b);
757 return strcmp (str_a, str_b);
758 }
759
760 char buf[BUFLEN];
761 const char *key = buf;
762
763 /* Prevent an error on a line from also generating
764 a "junk at end of line" error message. */
765 static char err_flag;
766
767 static void
768 error (const char * message)
769 {
770 if (err_flag)
771 return;
772
773 as_bad ("%s", message);
774 err_flag = 1;
775 }
776
777 static void
778 ill_op (void)
779 {
780 error (_("illegal operand"));
781 }
782
783 static void
784 wrong_mach (int ins_type)
785 {
786 if (ins_type & ins_err)
787 ill_op ();
788 else
789 as_warn (_("undocumented instruction"));
790 }
791
792 static void
793 check_mach (int ins_type)
794 {
795 if ((ins_type & ins_ok) == 0)
796 wrong_mach (ins_type);
797 }
798
799 /* Check whether an expression is indirect. */
800 static int
801 is_indir (const char *s)
802 {
803 char quote;
804 const char *p;
805 int indir, depth;
806
807 /* Indirection is indicated with parentheses. */
808 indir = (*s == '(');
809
810 for (p = s, depth = 0; *p && *p != ','; ++p)
811 {
812 switch (*p)
813 {
814 case '"':
815 case '\'':
816 for (quote = *p++; quote != *p && *p != '\n'; ++p)
817 if (*p == '\\' && p[1])
818 ++p;
819 break;
820 case '(':
821 ++ depth;
822 break;
823 case ')':
824 -- depth;
825 if (depth == 0)
826 {
827 p = skip_space (p + 1);
828 if (*p && *p != ',')
829 indir = 0;
830 --p;
831 }
832 if (depth < 0)
833 error (_("mismatched parentheses"));
834 break;
835 }
836 }
837
838 if (depth != 0)
839 error (_("mismatched parentheses"));
840
841 return indir;
842 }
843
844 /* Check whether a symbol involves a register. */
845 static bool
846 contains_register (symbolS *sym)
847 {
848 if (sym)
849 {
850 expressionS * ex = symbol_get_value_expression (sym);
851
852 switch (ex->X_op)
853 {
854 case O_register:
855 return true;
856
857 case O_add:
858 case O_subtract:
859 if (ex->X_op_symbol && contains_register (ex->X_op_symbol))
860 return true;
861 /* Fall through. */
862 case O_uminus:
863 case O_symbol:
864 if (ex->X_add_symbol && contains_register (ex->X_add_symbol))
865 return true;
866 break;
867
868 default:
869 break;
870 }
871 }
872
873 return false;
874 }
875
876 /* Parse general expression, not looking for indexed addressing. */
877 static const char *
878 parse_exp_not_indexed (const char *s, expressionS *op)
879 {
880 const char *p;
881 int indir;
882 int make_shift = -1;
883
884 memset (op, 0, sizeof (*op));
885 p = skip_space (s);
886 if (sdcc_compat && (*p == '<' || *p == '>'))
887 {
888 switch (*p)
889 {
890 case '<': /* LSB request */
891 make_shift = 0;
892 break;
893 case '>': /* MSB request */
894 make_shift = cpu_mode ? 16 : 8;
895 break;
896 }
897 s = ++p;
898 p = skip_space (p);
899 }
900
901 if (make_shift == -1)
902 indir = is_indir (p);
903 else
904 indir = 0;
905 op->X_md = indir;
906 if (indir && (ins_ok & INS_GBZ80))
907 { /* check for instructions like ld a,(hl+), ld (hl-),a */
908 p = skip_space (p+1);
909 if (!strncasecmp (p, "hl", 2))
910 {
911 p = skip_space(p+2);
912 if (*skip_space(p+1) == ')' && (*p == '+' || *p == '-'))
913 {
914 op->X_op = O_md1;
915 op->X_add_symbol = NULL;
916 op->X_add_number = (*p == '+') ? REG_HL : -REG_HL;
917 input_line_pointer = (char*)skip_space(p + 1) + 1;
918 return input_line_pointer;
919 }
920 }
921 }
922 input_line_pointer = (char*) s ;
923 expression (op);
924 switch (op->X_op)
925 {
926 case O_absent:
927 error (_("missing operand"));
928 break;
929 case O_illegal:
930 error (_("bad expression syntax"));
931 break;
932 default:
933 break;
934 }
935
936 if (make_shift >= 0)
937 {
938 /* replace [op] by [op >> shift] */
939 expressionS data;
940 op->X_add_symbol = make_expr_symbol (op);
941 op->X_add_number = 0;
942 op->X_op = O_right_shift;
943 memset (&data, 0, sizeof (data));
944 data.X_op = O_constant;
945 data.X_add_number = make_shift;
946 op->X_op_symbol = make_expr_symbol (&data);
947 }
948 return input_line_pointer;
949 }
950
951 static int
952 unify_indexed (expressionS *op)
953 {
954 if (O_register != symbol_get_value_expression (op->X_add_symbol)->X_op)
955 return 0;
956
957 int rnum = symbol_get_value_expression (op->X_add_symbol)->X_add_number;
958 if ( ((REG_IX != rnum) && (REG_IY != rnum)) || contains_register (op->X_op_symbol))
959 {
960 ill_op ();
961 return 0;
962 }
963
964 /* Convert subtraction to addition of negative value. */
965 if (O_subtract == op->X_op)
966 {
967 expressionS minus;
968 memset (&minus, 0, sizeof (minus));
969 minus.X_op = O_uminus;
970 minus.X_add_symbol = op->X_op_symbol;
971 op->X_op_symbol = make_expr_symbol (&minus);
972 op->X_op = O_add;
973 }
974
975 /* Clear X_add_number of the expression. */
976 if (op->X_add_number != 0)
977 {
978 expressionS add;
979 memset (&add, 0, sizeof (add));
980 add.X_op = O_symbol;
981 add.X_add_number = op->X_add_number;
982 add.X_add_symbol = op->X_op_symbol;
983 op->X_add_symbol = make_expr_symbol (&add);
984 }
985 else
986 op->X_add_symbol = op->X_op_symbol;
987
988 op->X_add_number = rnum;
989 op->X_op_symbol = 0;
990 return 1;
991 }
992
993 /* Parse expression, change operator to O_md1 for indexed addressing. */
994 static const char *
995 parse_exp (const char *s, expressionS *op)
996 {
997 const char* res = parse_exp_not_indexed (s, op);
998 switch (op->X_op)
999 {
1000 case O_add:
1001 case O_subtract:
1002 if (unify_indexed (op) && op->X_md)
1003 op->X_op = O_md1;
1004 break;
1005 case O_register:
1006 if (op->X_md && ((REG_IX == op->X_add_number) || (REG_IY == op->X_add_number)))
1007 {
1008 op->X_add_symbol = zero;
1009 op->X_op = O_md1;
1010 }
1011 break;
1012 case O_constant:
1013 /* parse SDCC syntax where index register offset placed before parentheses */
1014 if (sdcc_compat && is_indir (res))
1015 {
1016 expressionS off;
1017 off = *op;
1018 res = parse_exp (res, op);
1019 if (op->X_op != O_md1 || op->X_add_symbol != zero)
1020 ill_op ();
1021 else
1022 op->X_add_symbol = make_expr_symbol (&off);
1023 }
1024 break;
1025 default:
1026 break;
1027 }
1028 return res;
1029 }
1030
1031 /* Condition codes, including some synonyms provided by HiTech zas. */
1032 static const struct reg_entry cc_tab[] =
1033 {
1034 { "age", 6 << 3, INS_ALL },
1035 { "alt", 7 << 3, INS_ALL },
1036 { "c", 3 << 3, INS_ALL },
1037 { "di", 4 << 3, INS_ALL },
1038 { "ei", 5 << 3, INS_ALL },
1039 { "lge", 2 << 3, INS_ALL },
1040 { "llt", 3 << 3, INS_ALL },
1041 { "m", 7 << 3, INS_ALL },
1042 { "nc", 2 << 3, INS_ALL },
1043 { "nz", 0 << 3, INS_ALL },
1044 { "p", 6 << 3, INS_ALL },
1045 { "pe", 5 << 3, INS_ALL },
1046 { "po", 4 << 3, INS_ALL },
1047 { "z", 1 << 3, INS_ALL },
1048 } ;
1049
1050 /* Parse condition code. */
1051 static const char *
1052 parse_cc (const char *s, char * op)
1053 {
1054 const char *p;
1055 int i;
1056 struct reg_entry * cc_p;
1057
1058 for (i = 0; i < BUFLEN; ++i)
1059 {
1060 if (!ISALPHA (s[i])) /* Condition codes consist of letters only. */
1061 break;
1062 buf[i] = TOLOWER (s[i]);
1063 }
1064
1065 if ((i < BUFLEN)
1066 && ((s[i] == 0) || (s[i] == ',')))
1067 {
1068 buf[i] = 0;
1069 cc_p = bsearch (&key, cc_tab, ARRAY_SIZE (cc_tab),
1070 sizeof (cc_tab[0]), key_cmp);
1071 }
1072 else
1073 cc_p = NULL;
1074
1075 if (cc_p)
1076 {
1077 *op = cc_p->number;
1078 p = s + i;
1079 }
1080 else
1081 p = NULL;
1082
1083 return p;
1084 }
1085
1086 static const char *
1087 emit_insn (char prefix, char opcode, const char * args)
1088 {
1089 char *p;
1090
1091 if (prefix)
1092 {
1093 p = frag_more (2);
1094 *p++ = prefix;
1095 }
1096 else
1097 p = frag_more (1);
1098 *p = opcode;
1099 return args;
1100 }
1101
1102 void z80_cons_fix_new (fragS *frag_p, int offset, int nbytes, expressionS *exp)
1103 {
1104 bfd_reloc_code_real_type r[4] =
1105 {
1106 BFD_RELOC_8,
1107 BFD_RELOC_16,
1108 BFD_RELOC_24,
1109 BFD_RELOC_32
1110 };
1111
1112 if (nbytes < 1 || nbytes > 4)
1113 {
1114 as_bad (_("unsupported BFD relocation size %u"), nbytes);
1115 }
1116 else
1117 {
1118 fix_new_exp (frag_p, offset, nbytes, exp, 0, r[nbytes-1]);
1119 }
1120 }
1121
1122 static void
1123 emit_data_val (expressionS * val, int size)
1124 {
1125 char *p;
1126 bfd_reloc_code_real_type r_type;
1127
1128 p = frag_more (size);
1129 if (val->X_op == O_constant)
1130 {
1131 int i;
1132 for (i = 0; i < size; ++i)
1133 p[i] = (char)(val->X_add_number >> (i*8));
1134 return;
1135 }
1136
1137 switch (size)
1138 {
1139 case 1: r_type = BFD_RELOC_8; break;
1140 case 2: r_type = BFD_RELOC_16; break;
1141 case 3: r_type = BFD_RELOC_24; break;
1142 case 4: r_type = BFD_RELOC_32; break;
1143 case 8: r_type = BFD_RELOC_64; break;
1144 default:
1145 as_fatal (_("invalid data size %d"), size);
1146 }
1147
1148 if ( (val->X_op == O_register)
1149 || (val->X_op == O_md1)
1150 || contains_register (val->X_add_symbol)
1151 || contains_register (val->X_op_symbol))
1152 ill_op ();
1153
1154 if (size <= 2 && val->X_op_symbol)
1155 {
1156 bool simplify = true;
1157 int shift = symbol_get_value_expression (val->X_op_symbol)->X_add_number;
1158 if (val->X_op == O_bit_and && shift == (1 << (size*8))-1)
1159 shift = 0;
1160 else if (val->X_op != O_right_shift)
1161 shift = -1;
1162
1163 if (size == 1)
1164 {
1165 switch (shift)
1166 {
1167 case 0: r_type = BFD_RELOC_Z80_BYTE0; break;
1168 case 8: r_type = BFD_RELOC_Z80_BYTE1; break;
1169 case 16: r_type = BFD_RELOC_Z80_BYTE2; break;
1170 case 24: r_type = BFD_RELOC_Z80_BYTE3; break;
1171 default: simplify = false;
1172 }
1173 }
1174 else /* if (size == 2) */
1175 {
1176 switch (shift)
1177 {
1178 case 0: r_type = BFD_RELOC_Z80_WORD0; break;
1179 case 16: r_type = BFD_RELOC_Z80_WORD1; break;
1180 case 8:
1181 case 24: /* add two byte fixups */
1182 val->X_op = O_symbol;
1183 val->X_op_symbol = NULL;
1184 val->X_add_number = 0;
1185 if (shift == 8)
1186 {
1187 fix_new_exp (frag_now, p++ - frag_now->fr_literal, 1, val, false,
1188 BFD_RELOC_Z80_BYTE1);
1189 /* prepare to next byte */
1190 r_type = BFD_RELOC_Z80_BYTE2;
1191 }
1192 else
1193 r_type = BFD_RELOC_Z80_BYTE3; /* high byte will be 0 */
1194 size = 1;
1195 simplify = false;
1196 break;
1197 default: simplify = false;
1198 }
1199 }
1200
1201 if (simplify)
1202 {
1203 val->X_op = O_symbol;
1204 val->X_op_symbol = NULL;
1205 val->X_add_number = 0;
1206 }
1207 }
1208
1209 fix_new_exp (frag_now, p - frag_now->fr_literal, size, val, false, r_type);
1210 }
1211
1212 static void
1213 emit_byte (expressionS * val, bfd_reloc_code_real_type r_type)
1214 {
1215 char *p;
1216
1217 if (r_type == BFD_RELOC_8)
1218 {
1219 emit_data_val (val, 1);
1220 return;
1221 }
1222 p = frag_more (1);
1223 *p = val->X_add_number;
1224 if (contains_register (val->X_add_symbol) || contains_register (val->X_op_symbol))
1225 {
1226 ill_op ();
1227 }
1228 else if ((r_type == BFD_RELOC_8_PCREL) && (val->X_op == O_constant))
1229 {
1230 as_bad (_("cannot make a relative jump to an absolute location"));
1231 }
1232 else if (val->X_op == O_constant)
1233 {
1234 if ((val->X_add_number < -128) || (val->X_add_number >= 128))
1235 {
1236 if (r_type == BFD_RELOC_Z80_DISP8)
1237 as_bad (_("index overflow (%+ld)"), val->X_add_number);
1238 else
1239 as_bad (_("offset overflow (%+ld)"), val->X_add_number);
1240 }
1241 }
1242 else
1243 {
1244 /* For symbols only, constants are stored at begin of function. */
1245 fix_new_exp (frag_now, p - frag_now->fr_literal, 1, val,
1246 r_type == BFD_RELOC_8_PCREL, r_type);
1247 }
1248 }
1249
1250 static void
1251 emit_word (expressionS * val)
1252 {
1253 emit_data_val (val, (inst_mode & INST_MODE_IL) ? 3 : 2);
1254 }
1255
1256 static void
1257 emit_mx (char prefix, char opcode, int shift, expressionS * arg)
1258 /* The operand m may be r, (hl), (ix+d), (iy+d),
1259 if 0 == prefix m may also be ixl, ixh, iyl, iyh. */
1260 {
1261 char *q;
1262 int rnum;
1263
1264 rnum = arg->X_add_number;
1265 switch (arg->X_op)
1266 {
1267 case O_register:
1268 if (arg->X_md)
1269 {
1270 if (rnum != REG_HL)
1271 {
1272 ill_op ();
1273 break;
1274 }
1275 else
1276 rnum = 6;
1277 }
1278 else
1279 {
1280 if ((prefix == 0) && (rnum & R_INDEX))
1281 {
1282 prefix = (rnum & R_IX) ? 0xDD : 0xFD;
1283 if (!(ins_ok & (INS_EZ80|INS_R800|INS_Z80N)))
1284 check_mach (INS_IDX_HALF);
1285 rnum &= ~R_INDEX;
1286 }
1287 if (rnum > 7)
1288 {
1289 ill_op ();
1290 break;
1291 }
1292 }
1293 q = frag_more (prefix ? 2 : 1);
1294 if (prefix)
1295 * q ++ = prefix;
1296 * q ++ = opcode + (rnum << shift);
1297 break;
1298 case O_md1:
1299 if (ins_ok & INS_GBZ80)
1300 {
1301 ill_op ();
1302 break;
1303 }
1304 q = frag_more (2);
1305 *q++ = (rnum & R_IX) ? 0xDD : 0xFD;
1306 *q = (prefix) ? prefix : (opcode + (6 << shift));
1307 {
1308 expressionS offset = *arg;
1309 offset.X_op = O_symbol;
1310 offset.X_add_number = 0;
1311 emit_byte (&offset, BFD_RELOC_Z80_DISP8);
1312 }
1313 if (prefix)
1314 {
1315 q = frag_more (1);
1316 *q = opcode+(6<<shift);
1317 }
1318 break;
1319 default:
1320 abort ();
1321 }
1322 }
1323
1324 /* The operand m may be r, (hl), (ix+d), (iy+d),
1325 if 0 = prefix m may also be ixl, ixh, iyl, iyh. */
1326 static const char *
1327 emit_m (char prefix, char opcode, const char *args)
1328 {
1329 expressionS arg_m;
1330 const char *p;
1331
1332 p = parse_exp (args, &arg_m);
1333 switch (arg_m.X_op)
1334 {
1335 case O_md1:
1336 case O_register:
1337 emit_mx (prefix, opcode, 0, &arg_m);
1338 break;
1339 default:
1340 ill_op ();
1341 }
1342 return p;
1343 }
1344
1345 /* The operand m may be as above or one of the undocumented
1346 combinations (ix+d),r and (iy+d),r (if unportable instructions
1347 are allowed). */
1348
1349 static const char *
1350 emit_mr (char prefix, char opcode, const char *args)
1351 {
1352 expressionS arg_m, arg_r;
1353 const char *p;
1354
1355 p = parse_exp (args, & arg_m);
1356
1357 switch (arg_m.X_op)
1358 {
1359 case O_md1:
1360 if (*p == ',')
1361 {
1362 p = parse_exp (p + 1, & arg_r);
1363
1364 if ((arg_r.X_md == 0)
1365 && (arg_r.X_op == O_register)
1366 && (arg_r.X_add_number < 8))
1367 opcode += arg_r.X_add_number - 6; /* Emit_mx () will add 6. */
1368 else
1369 {
1370 ill_op ();
1371 break;
1372 }
1373 if (!(ins_ok & INS_Z80N))
1374 check_mach (INS_ROT_II_LD);
1375 }
1376 /* Fall through. */
1377 case O_register:
1378 emit_mx (prefix, opcode, 0, & arg_m);
1379 break;
1380 default:
1381 ill_op ();
1382 }
1383 return p;
1384 }
1385
1386 static void
1387 emit_sx (char prefix, char opcode, expressionS * arg_p)
1388 {
1389 char *q;
1390
1391 switch (arg_p->X_op)
1392 {
1393 case O_register:
1394 case O_md1:
1395 emit_mx (prefix, opcode, 0, arg_p);
1396 break;
1397 default:
1398 if (arg_p->X_md)
1399 ill_op ();
1400 else
1401 {
1402 q = frag_more (prefix ? 2 : 1);
1403 if (prefix)
1404 *q++ = prefix;
1405 *q = opcode ^ 0x46;
1406 emit_byte (arg_p, BFD_RELOC_8);
1407 }
1408 }
1409 }
1410
1411 /* The operand s may be r, (hl), (ix+d), (iy+d), n. */
1412 static const char *
1413 emit_s (char prefix, char opcode, const char *args)
1414 {
1415 expressionS arg_s;
1416 const char *p;
1417
1418 p = parse_exp (args, & arg_s);
1419 if (*p == ',' && arg_s.X_md == 0 && arg_s.X_op == O_register && arg_s.X_add_number == REG_A)
1420 { /* possible instruction in generic format op A,x */
1421 if (!(ins_ok & INS_EZ80) && !sdcc_compat)
1422 ill_op ();
1423 ++p;
1424 p = parse_exp (p, & arg_s);
1425 }
1426 emit_sx (prefix, opcode, & arg_s);
1427 return p;
1428 }
1429
1430 static const char *
1431 emit_sub (char prefix, char opcode, const char *args)
1432 {
1433 expressionS arg_s;
1434 const char *p;
1435
1436 if (!(ins_ok & INS_GBZ80))
1437 return emit_s (prefix, opcode, args);
1438 p = parse_exp (args, & arg_s);
1439 if (*p++ != ',')
1440 {
1441 error (_("bad instruction syntax"));
1442 return p;
1443 }
1444
1445 if (arg_s.X_md != 0 || arg_s.X_op != O_register || arg_s.X_add_number != REG_A)
1446 ill_op ();
1447
1448 p = parse_exp (p, & arg_s);
1449
1450 emit_sx (prefix, opcode, & arg_s);
1451 return p;
1452 }
1453
1454 static const char *
1455 emit_swap (char prefix, char opcode, const char *args)
1456 {
1457 expressionS reg;
1458 const char *p;
1459 char *q;
1460
1461 if (!(ins_ok & INS_Z80N))
1462 return emit_mr (prefix, opcode, args);
1463
1464 /* check for alias swap a for swapnib of Z80N */
1465 p = parse_exp (args, &reg);
1466 if (reg.X_md != 0 || reg.X_op != O_register || reg.X_add_number != REG_A)
1467 ill_op ();
1468
1469 q = frag_more (2);
1470 *q++ = 0xED;
1471 *q = 0x23;
1472 return p;
1473 }
1474
1475 static const char *
1476 emit_call (char prefix ATTRIBUTE_UNUSED, char opcode, const char * args)
1477 {
1478 expressionS addr;
1479 const char *p; char *q;
1480
1481 p = parse_exp_not_indexed (args, &addr);
1482 if (addr.X_md)
1483 ill_op ();
1484 else
1485 {
1486 q = frag_more (1);
1487 *q = opcode;
1488 emit_word (& addr);
1489 }
1490 return p;
1491 }
1492
1493 /* Operand may be rr, r, (hl), (ix+d), (iy+d). */
1494 static const char *
1495 emit_incdec (char prefix, char opcode, const char * args)
1496 {
1497 expressionS operand;
1498 int rnum;
1499 const char *p; char *q;
1500
1501 p = parse_exp (args, &operand);
1502 rnum = operand.X_add_number;
1503 if ((! operand.X_md)
1504 && (operand.X_op == O_register)
1505 && (R_ARITH&rnum))
1506 {
1507 q = frag_more ((rnum & R_INDEX) ? 2 : 1);
1508 if (rnum & R_INDEX)
1509 *q++ = (rnum & R_IX) ? 0xDD : 0xFD;
1510 *q = prefix + ((rnum & 3) << 4);
1511 }
1512 else
1513 {
1514 if ((operand.X_op == O_md1) || (operand.X_op == O_register))
1515 emit_mx (0, opcode, 3, & operand);
1516 else
1517 ill_op ();
1518 }
1519 return p;
1520 }
1521
1522 static const char *
1523 emit_jr (char prefix ATTRIBUTE_UNUSED, char opcode, const char * args)
1524 {
1525 expressionS addr;
1526 const char *p;
1527 char *q;
1528
1529 p = parse_exp_not_indexed (args, &addr);
1530 if (addr.X_md)
1531 ill_op ();
1532 else
1533 {
1534 q = frag_more (1);
1535 *q = opcode;
1536 addr.X_add_number--; /* pcrel computes after offset code */
1537 emit_byte (&addr, BFD_RELOC_8_PCREL);
1538 }
1539 return p;
1540 }
1541
1542 static const char *
1543 emit_jp (char prefix, char opcode, const char * args)
1544 {
1545 expressionS addr;
1546 const char *p;
1547 char *q;
1548 int rnum;
1549
1550 p = parse_exp_not_indexed (args, & addr);
1551 if (addr.X_md)
1552 {
1553 rnum = addr.X_add_number;
1554 if ((O_register == addr.X_op) && (REG_HL == (rnum & ~R_INDEX)))
1555 {
1556 q = frag_more ((rnum & R_INDEX) ? 2 : 1);
1557 if (rnum & R_INDEX)
1558 *q++ = (rnum & R_IX) ? 0xDD : 0xFD;
1559 *q = prefix;
1560 }
1561 else if (addr.X_op == O_register && rnum == REG_C && (ins_ok & INS_Z80N))
1562 {
1563 q = frag_more (2);
1564 *q++ = 0xED;
1565 *q = 0x98;
1566 }
1567 else
1568 ill_op ();
1569 }
1570 else
1571 {
1572 q = frag_more (1);
1573 *q = opcode;
1574 emit_word (& addr);
1575 }
1576 return p;
1577 }
1578
1579 static const char *
1580 emit_im (char prefix, char opcode, const char * args)
1581 {
1582 expressionS mode;
1583 const char *p;
1584 char *q;
1585
1586 p = parse_exp (args, & mode);
1587 if (mode.X_md || (mode.X_op != O_constant))
1588 ill_op ();
1589 else
1590 switch (mode.X_add_number)
1591 {
1592 case 1:
1593 case 2:
1594 ++mode.X_add_number;
1595 /* Fall through. */
1596 case 0:
1597 q = frag_more (2);
1598 *q++ = prefix;
1599 *q = opcode + 8*mode.X_add_number;
1600 break;
1601 default:
1602 ill_op ();
1603 }
1604 return p;
1605 }
1606
1607 static const char *
1608 emit_pop (char prefix ATTRIBUTE_UNUSED, char opcode, const char * args)
1609 {
1610 expressionS regp;
1611 const char *p;
1612 char *q;
1613
1614 p = parse_exp (args, & regp);
1615 if ((!regp.X_md)
1616 && (regp.X_op == O_register)
1617 && (regp.X_add_number & R_STACKABLE))
1618 {
1619 int rnum;
1620
1621 rnum = regp.X_add_number;
1622 if (rnum&R_INDEX)
1623 {
1624 q = frag_more (2);
1625 *q++ = (rnum&R_IX)?0xDD:0xFD;
1626 }
1627 else
1628 q = frag_more (1);
1629 *q = opcode + ((rnum & 3) << 4);
1630 }
1631 else
1632 ill_op ();
1633
1634 return p;
1635 }
1636
1637 static const char *
1638 emit_push (char prefix, char opcode, const char * args)
1639 {
1640 expressionS arg;
1641 const char *p;
1642 char *q;
1643
1644 p = parse_exp (args, & arg);
1645 if (arg.X_op == O_register)
1646 return emit_pop (prefix, opcode, args);
1647
1648 if (arg.X_md || arg.X_op == O_md1 || !(ins_ok & INS_Z80N))
1649 ill_op ();
1650
1651 q = frag_more (2);
1652 *q++ = 0xED;
1653 *q = 0x8A;
1654
1655 q = frag_more (2);
1656 fix_new_exp (frag_now, q - frag_now->fr_literal, 2, &arg, false,
1657 BFD_RELOC_Z80_16_BE);
1658
1659 return p;
1660 }
1661
1662 static const char *
1663 emit_retcc (char prefix ATTRIBUTE_UNUSED, char opcode, const char * args)
1664 {
1665 char cc, *q;
1666 const char *p;
1667
1668 p = parse_cc (args, &cc);
1669 q = frag_more (1);
1670 if (p)
1671 *q = opcode + cc;
1672 else
1673 *q = prefix;
1674 return p ? p : args;
1675 }
1676
1677 static const char *
1678 emit_adc (char prefix, char opcode, const char * args)
1679 {
1680 expressionS term;
1681 int rnum;
1682 const char *p;
1683 char *q;
1684
1685 p = parse_exp (args, &term);
1686 if (*p++ != ',')
1687 {
1688 error (_("bad instruction syntax"));
1689 return p;
1690 }
1691
1692 if ((term.X_md) || (term.X_op != O_register))
1693 ill_op ();
1694 else
1695 switch (term.X_add_number)
1696 {
1697 case REG_A:
1698 p = emit_s (0, prefix, p);
1699 break;
1700 case REG_HL:
1701 p = parse_exp (p, &term);
1702 if ((!term.X_md) && (term.X_op == O_register))
1703 {
1704 rnum = term.X_add_number;
1705 if (R_ARITH == (rnum & (R_ARITH | R_INDEX)))
1706 {
1707 q = frag_more (2);
1708 *q++ = 0xED;
1709 *q = opcode + ((rnum & 3) << 4);
1710 break;
1711 }
1712 }
1713 /* Fall through. */
1714 default:
1715 ill_op ();
1716 }
1717 return p;
1718 }
1719
1720 static const char *
1721 emit_add (char prefix, char opcode, const char * args)
1722 {
1723 expressionS term;
1724 int lhs, rhs;
1725 const char *p;
1726 char *q;
1727
1728 p = parse_exp (args, &term);
1729 if (*p++ != ',')
1730 {
1731 error (_("bad instruction syntax"));
1732 return p;
1733 }
1734
1735 if ((term.X_md) || (term.X_op != O_register))
1736 ill_op ();
1737 else
1738 switch (term.X_add_number)
1739 {
1740 case REG_A:
1741 p = emit_s (0, prefix, p);
1742 break;
1743 case REG_SP:
1744 p = parse_exp (p, &term);
1745 if (!(ins_ok & INS_GBZ80) || term.X_md || term.X_op == O_register)
1746 ill_op ();
1747 q = frag_more (1);
1748 *q = 0xE8;
1749 emit_byte (&term, BFD_RELOC_Z80_DISP8);
1750 break;
1751 case REG_BC:
1752 case REG_DE:
1753 if (!(ins_ok & INS_Z80N))
1754 {
1755 ill_op ();
1756 break;
1757 }
1758 /* Fall through. */
1759 case REG_HL:
1760 case REG_IX:
1761 case REG_IY:
1762 lhs = term.X_add_number;
1763 p = parse_exp (p, &term);
1764 rhs = term.X_add_number;
1765 if (term.X_md != 0 || term.X_op == O_md1)
1766 ill_op ();
1767 else if ((term.X_op == O_register) && (rhs & R_ARITH) && (rhs == lhs || (rhs & ~R_INDEX) != REG_HL))
1768 {
1769 if (1)
1770 {
1771 q = frag_more ((lhs & R_INDEX) ? 2 : 1);
1772 if (lhs & R_INDEX)
1773 *q++ = (lhs & R_IX) ? 0xDD : 0xFD;
1774 *q = opcode + ((rhs & 3) << 4);
1775 break;
1776 }
1777 }
1778 else if (!(lhs & R_INDEX) && (ins_ok & INS_Z80N))
1779 {
1780 if (term.X_op == O_register && rhs == REG_A)
1781 { /* ADD BC/DE/HL,A */
1782 q = frag_more (2);
1783 *q++ = 0xED;
1784 *q = 0x33 - (lhs & 3);
1785 break;
1786 }
1787 else if (term.X_op != O_register && term.X_op != O_md1)
1788 { /* ADD BC/DE/HL,nn */
1789 q = frag_more (2);
1790 *q++ = 0xED;
1791 *q = 0x36 - (lhs & 3);
1792 emit_word (&term);
1793 break;
1794 }
1795 }
1796 /* Fall through. */
1797 default:
1798 ill_op ();
1799 }
1800 return p;
1801 }
1802
1803 static const char *
1804 emit_bit (char prefix, char opcode, const char * args)
1805 {
1806 expressionS b;
1807 int bn;
1808 const char *p;
1809
1810 p = parse_exp (args, &b);
1811 if (*p++ != ',')
1812 error (_("bad instruction syntax"));
1813
1814 bn = b.X_add_number;
1815 if ((!b.X_md)
1816 && (b.X_op == O_constant)
1817 && (0 <= bn)
1818 && (bn < 8))
1819 {
1820 if (opcode == 0x40)
1821 /* Bit : no optional third operand. */
1822 p = emit_m (prefix, opcode + (bn << 3), p);
1823 else
1824 /* Set, res : resulting byte can be copied to register. */
1825 p = emit_mr (prefix, opcode + (bn << 3), p);
1826 }
1827 else
1828 ill_op ();
1829 return p;
1830 }
1831
1832 /* BSLA DE,B; BSRA DE,B; BSRL DE,B; BSRF DE,B; BRLC DE,B (Z80N only) */
1833 static const char *
1834 emit_bshft (char prefix, char opcode, const char * args)
1835 {
1836 expressionS r1, r2;
1837 const char *p;
1838 char *q;
1839
1840 p = parse_exp (args, & r1);
1841 if (*p++ != ',')
1842 error (_("bad instruction syntax"));
1843 p = parse_exp (p, & r2);
1844 if (r1.X_md || r1.X_op != O_register || r1.X_add_number != REG_DE ||
1845 r2.X_md || r2.X_op != O_register || r2.X_add_number != REG_B)
1846 ill_op ();
1847 q = frag_more (2);
1848 *q++ = prefix;
1849 *q = opcode;
1850 return p;
1851 }
1852
1853 static const char *
1854 emit_jpcc (char prefix, char opcode, const char * args)
1855 {
1856 char cc;
1857 const char *p;
1858
1859 p = parse_cc (args, & cc);
1860 if (p && *p++ == ',')
1861 p = emit_call (0, opcode + cc, p);
1862 else
1863 p = (prefix == (char)0xC3)
1864 ? emit_jp (0xE9, prefix, args)
1865 : emit_call (0, prefix, args);
1866 return p;
1867 }
1868
1869 static const char *
1870 emit_jrcc (char prefix, char opcode, const char * args)
1871 {
1872 char cc;
1873 const char *p;
1874
1875 p = parse_cc (args, &cc);
1876 if (p && *p++ == ',')
1877 {
1878 if (cc > (3 << 3))
1879 error (_("condition code invalid for jr"));
1880 else
1881 p = emit_jr (0, opcode + cc, p);
1882 }
1883 else
1884 p = emit_jr (0, prefix, args);
1885
1886 return p;
1887 }
1888
1889 static const char *
1890 emit_ex (char prefix_in ATTRIBUTE_UNUSED,
1891 char opcode_in ATTRIBUTE_UNUSED, const char * args)
1892 {
1893 expressionS op;
1894 const char * p;
1895 char prefix, opcode;
1896
1897 p = parse_exp_not_indexed (args, &op);
1898 p = skip_space (p);
1899 if (*p++ != ',')
1900 {
1901 error (_("bad instruction syntax"));
1902 return p;
1903 }
1904
1905 prefix = opcode = 0;
1906 if (op.X_op == O_register)
1907 switch (op.X_add_number | (op.X_md ? 0x8000 : 0))
1908 {
1909 case REG_AF:
1910 if (TOLOWER (*p++) == 'a' && TOLOWER (*p++) == 'f')
1911 {
1912 /* The scrubber changes '\'' to '`' in this context. */
1913 if (*p == '`')
1914 ++p;
1915 opcode = 0x08;
1916 }
1917 break;
1918 case REG_DE:
1919 if (TOLOWER (*p++) == 'h' && TOLOWER (*p++) == 'l')
1920 opcode = 0xEB;
1921 break;
1922 case REG_SP|0x8000:
1923 p = parse_exp (p, & op);
1924 if (op.X_op == O_register
1925 && op.X_md == 0
1926 && (op.X_add_number & ~R_INDEX) == REG_HL)
1927 {
1928 opcode = 0xE3;
1929 if (R_INDEX & op.X_add_number)
1930 prefix = (R_IX & op.X_add_number) ? 0xDD : 0xFD;
1931 }
1932 break;
1933 }
1934 if (opcode)
1935 emit_insn (prefix, opcode, p);
1936 else
1937 ill_op ();
1938
1939 return p;
1940 }
1941
1942 static const char *
1943 emit_in (char prefix ATTRIBUTE_UNUSED, char opcode ATTRIBUTE_UNUSED,
1944 const char * args)
1945 {
1946 expressionS reg, port;
1947 const char *p;
1948 char *q;
1949
1950 p = parse_exp (args, &reg);
1951 if (reg.X_md && reg.X_op == O_register && reg.X_add_number == REG_C)
1952 { /* permit instruction in (c) as alias for in f,(c) */
1953 port = reg;
1954 reg.X_md = 0;
1955 reg.X_add_number = REG_F;
1956 }
1957 else
1958 {
1959 if (*p++ != ',')
1960 {
1961 error (_("bad instruction syntax"));
1962 return p;
1963 }
1964 p = parse_exp (p, &port);
1965 }
1966 if (reg.X_md == 0
1967 && reg.X_op == O_register
1968 && (reg.X_add_number <= 7 || reg.X_add_number == REG_F)
1969 && (port.X_md))
1970 {
1971 if (port.X_op != O_md1 && port.X_op != O_register)
1972 {
1973 if (REG_A == reg.X_add_number)
1974 {
1975 q = frag_more (1);
1976 *q = 0xDB;
1977 emit_byte (&port, BFD_RELOC_8);
1978 }
1979 else
1980 ill_op ();
1981 }
1982 else
1983 {
1984 if (port.X_add_number == REG_C || port.X_add_number == REG_BC)
1985 {
1986 if (port.X_add_number == REG_BC && !(ins_ok & INS_EZ80))
1987 ill_op ();
1988 else if (reg.X_add_number == REG_F && !(ins_ok & (INS_R800|INS_Z80N)))
1989 check_mach (INS_IN_F_C);
1990 q = frag_more (2);
1991 *q++ = 0xED;
1992 *q = 0x40|((reg.X_add_number&7)<<3);
1993 }
1994 else
1995 ill_op ();
1996 }
1997 }
1998 else
1999 ill_op ();
2000 return p;
2001 }
2002
2003 static const char *
2004 emit_in0 (char prefix ATTRIBUTE_UNUSED, char opcode ATTRIBUTE_UNUSED,
2005 const char * args)
2006 {
2007 expressionS reg, port;
2008 const char *p;
2009 char *q;
2010
2011 p = parse_exp (args, &reg);
2012 if (*p++ != ',')
2013 {
2014 error (_("bad instruction syntax"));
2015 return p;
2016 }
2017
2018 p = parse_exp (p, &port);
2019 if (reg.X_md == 0
2020 && reg.X_op == O_register
2021 && reg.X_add_number <= 7
2022 && port.X_md
2023 && port.X_op != O_md1
2024 && port.X_op != O_register)
2025 {
2026 q = frag_more (2);
2027 *q++ = 0xED;
2028 *q = 0x00|(reg.X_add_number << 3);
2029 emit_byte (&port, BFD_RELOC_8);
2030 }
2031 else
2032 ill_op ();
2033 return p;
2034 }
2035
2036 static const char *
2037 emit_out (char prefix ATTRIBUTE_UNUSED, char opcode ATTRIBUTE_UNUSED,
2038 const char * args)
2039 {
2040 expressionS reg, port;
2041 const char *p;
2042 char *q;
2043
2044 p = parse_exp (args, & port);
2045 if (*p++ != ',')
2046 {
2047 error (_("bad instruction syntax"));
2048 return p;
2049 }
2050 p = parse_exp (p, &reg);
2051 if (!port.X_md)
2052 { ill_op (); return p; }
2053 /* Allow "out (c), 0" as unportable instruction. */
2054 if (reg.X_op == O_constant && reg.X_add_number == 0)
2055 {
2056 if (!(ins_ok & INS_Z80N))
2057 check_mach (INS_OUT_C_0);
2058 reg.X_op = O_register;
2059 reg.X_add_number = 6;
2060 }
2061 if (reg.X_md
2062 || reg.X_op != O_register
2063 || reg.X_add_number > 7)
2064 ill_op ();
2065 else
2066 if (port.X_op != O_register && port.X_op != O_md1)
2067 {
2068 if (REG_A == reg.X_add_number)
2069 {
2070 q = frag_more (1);
2071 *q = 0xD3;
2072 emit_byte (&port, BFD_RELOC_8);
2073 }
2074 else
2075 ill_op ();
2076 }
2077 else
2078 {
2079 if (REG_C == port.X_add_number || port.X_add_number == REG_BC)
2080 {
2081 if (port.X_add_number == REG_BC && !(ins_ok & INS_EZ80))
2082 ill_op ();
2083 q = frag_more (2);
2084 *q++ = 0xED;
2085 *q = 0x41 | (reg.X_add_number << 3);
2086 }
2087 else
2088 ill_op ();
2089 }
2090 return p;
2091 }
2092
2093 static const char *
2094 emit_out0 (char prefix ATTRIBUTE_UNUSED, char opcode ATTRIBUTE_UNUSED,
2095 const char * args)
2096 {
2097 expressionS reg, port;
2098 const char *p;
2099 char *q;
2100
2101 p = parse_exp (args, & port);
2102 if (*p++ != ',')
2103 {
2104 error (_("bad instruction syntax"));
2105 return p;
2106 }
2107 p = parse_exp (p, &reg);
2108 if (port.X_md != 0
2109 && port.X_op != O_register
2110 && port.X_op != O_md1
2111 && reg.X_md == 0
2112 && reg.X_op == O_register
2113 && reg.X_add_number <= 7)
2114 {
2115 q = frag_more (2);
2116 *q++ = 0xED;
2117 *q = 0x01 | (reg.X_add_number << 3);
2118 emit_byte (&port, BFD_RELOC_8);
2119 }
2120 else
2121 ill_op ();
2122 return p;
2123 }
2124
2125 static const char *
2126 emit_rst (char prefix ATTRIBUTE_UNUSED, char opcode, const char * args)
2127 {
2128 expressionS addr;
2129 const char *p;
2130 char *q;
2131
2132 p = parse_exp_not_indexed (args, &addr);
2133 if (addr.X_op != O_constant)
2134 {
2135 error ("rst needs constant address");
2136 return p;
2137 }
2138
2139 if (addr.X_add_number & ~(7 << 3))
2140 ill_op ();
2141 else
2142 {
2143 q = frag_more (1);
2144 *q = opcode + (addr.X_add_number & (7 << 3));
2145 }
2146 return p;
2147 }
2148
2149 /* For 8-bit indirect load to memory instructions like: LD (HL),n or LD (ii+d),n. */
2150 static void
2151 emit_ld_m_n (expressionS *dst, expressionS *src)
2152 {
2153 char *q;
2154 char prefix;
2155 expressionS dst_offset;
2156
2157 switch (dst->X_add_number)
2158 {
2159 case REG_HL: prefix = 0x00; break;
2160 case REG_IX: prefix = 0xDD; break;
2161 case REG_IY: prefix = 0xFD; break;
2162 default:
2163 ill_op ();
2164 return;
2165 }
2166
2167 q = frag_more (prefix ? 2 : 1);
2168 if (prefix)
2169 *q++ = prefix;
2170 *q = 0x36;
2171 if (prefix)
2172 {
2173 dst_offset = *dst;
2174 dst_offset.X_op = O_symbol;
2175 dst_offset.X_add_number = 0;
2176 emit_byte (& dst_offset, BFD_RELOC_Z80_DISP8);
2177 }
2178 emit_byte (src, BFD_RELOC_8);
2179 }
2180
2181 /* For 8-bit load register to memory instructions: LD (<expression>),r. */
2182 static void
2183 emit_ld_m_r (expressionS *dst, expressionS *src)
2184 {
2185 char *q;
2186 char prefix = 0;
2187 expressionS dst_offset;
2188
2189 switch (dst->X_op)
2190 {
2191 case O_md1:
2192 if (ins_ok & INS_GBZ80)
2193 { /* LD (HL+),A or LD (HL-),A */
2194 if (src->X_op != O_register || src->X_add_number != REG_A)
2195 break;
2196 *frag_more (1) = (dst->X_add_number == REG_HL) ? 0x22 : 0x32;
2197 return;
2198 }
2199 else
2200 prefix = (dst->X_add_number == REG_IX) ? 0xDD : 0xFD;
2201 /* Fall through. */
2202 case O_register:
2203 switch (dst->X_add_number)
2204 {
2205 case REG_BC: /* LD (BC),A */
2206 case REG_DE: /* LD (DE),A */
2207 if (src->X_add_number == REG_A)
2208 {
2209 q = frag_more (1);
2210 *q = 0x02 | ((dst->X_add_number & 3) << 4);
2211 return;
2212 }
2213 break;
2214 case REG_IX:
2215 case REG_IY:
2216 case REG_HL: /* LD (HL),r or LD (ii+d),r */
2217 if (src->X_add_number <= 7)
2218 {
2219 q = frag_more (prefix ? 2 : 1);
2220 if (prefix)
2221 *q++ = prefix;
2222 *q = 0x70 | src->X_add_number;
2223 if (prefix)
2224 {
2225 dst_offset = *dst;
2226 dst_offset.X_op = O_symbol;
2227 dst_offset.X_add_number = 0;
2228 emit_byte (& dst_offset, BFD_RELOC_Z80_DISP8);
2229 }
2230 return;
2231 }
2232 break;
2233 default:;
2234 }
2235 break;
2236 default: /* LD (nn),A */
2237 if (src->X_add_number == REG_A)
2238 {
2239 q = frag_more (1);
2240 *q = (ins_ok & INS_GBZ80) ? 0xEA : 0x32;
2241 emit_word (dst);
2242 return;
2243 }
2244 break;
2245 }
2246 ill_op ();
2247 }
2248
2249 /* For 16-bit load register to memory instructions: LD (<expression>),rr. */
2250 static void
2251 emit_ld_m_rr (expressionS *dst, expressionS *src)
2252 {
2253 char *q;
2254 int prefix = 0;
2255 int opcode = 0;
2256 expressionS dst_offset;
2257
2258 switch (dst->X_op)
2259 {
2260 case O_md1: /* eZ80 instructions LD (ii+d),rr */
2261 case O_register: /* eZ80 instructions LD (HL),rr */
2262 if (!(ins_ok & INS_EZ80)) /* 16-bit indirect load group is supported by eZ80 only */
2263 ill_op ();
2264 switch (dst->X_add_number)
2265 {
2266 case REG_IX: prefix = 0xDD; break;
2267 case REG_IY: prefix = 0xFD; break;
2268 case REG_HL: prefix = 0xED; break;
2269 default:
2270 ill_op ();
2271 }
2272 switch (src->X_add_number)
2273 {
2274 case REG_BC: opcode = 0x0F; break;
2275 case REG_DE: opcode = 0x1F; break;
2276 case REG_HL: opcode = 0x2F; break;
2277 case REG_IX: opcode = (prefix != 0xFD) ? 0x3F : 0x3E; break;
2278 case REG_IY: opcode = (prefix != 0xFD) ? 0x3E : 0x3F; break;
2279 default:
2280 ill_op ();
2281 }
2282 q = frag_more (prefix ? 2 : 1);
2283 *q++ = prefix;
2284 *q = opcode;
2285 if (prefix == 0xFD || prefix == 0xDD)
2286 {
2287 dst_offset = *dst;
2288 dst_offset.X_op = O_symbol;
2289 dst_offset.X_add_number = 0;
2290 emit_byte (& dst_offset, BFD_RELOC_Z80_DISP8);
2291 }
2292 break;
2293 default: /* LD (nn),rr */
2294 if (ins_ok & INS_GBZ80)
2295 {
2296 /* GBZ80 supports only LD (nn),SP */
2297 if (src->X_add_number == REG_SP)
2298 {
2299 prefix = 0x00;
2300 opcode = 0x08;
2301 }
2302 else
2303 ill_op ();
2304 }
2305 else
2306 {
2307 switch (src->X_add_number)
2308 {
2309 case REG_BC: prefix = 0xED; opcode = 0x43; break;
2310 case REG_DE: prefix = 0xED; opcode = 0x53; break;
2311 case REG_HL: prefix = 0x00; opcode = 0x22; break;
2312 case REG_IX: prefix = 0xDD; opcode = 0x22; break;
2313 case REG_IY: prefix = 0xFD; opcode = 0x22; break;
2314 case REG_SP: prefix = 0xED; opcode = 0x73; break;
2315 default:
2316 ill_op ();
2317 }
2318 }
2319 q = frag_more (prefix ? 2 : 1);
2320 if (prefix)
2321 *q++ = prefix;
2322 *q = opcode;
2323 emit_word (dst);
2324 }
2325 }
2326
2327 static void
2328 emit_ld_r_m (expressionS *dst, expressionS *src)
2329 { /* for 8-bit memory load to register: LD r,(xxx) */
2330 char *q;
2331 char prefix = 0;
2332 char opcode = 0;
2333 expressionS src_offset;
2334
2335 if (dst->X_add_number == REG_A && src->X_op == O_register)
2336 { /* LD A,(BC) or LD A,(DE) */
2337 switch (src->X_add_number)
2338 {
2339 case REG_BC: opcode = 0x0A; break;
2340 case REG_DE: opcode = 0x1A; break;
2341 default: break;
2342 }
2343 if (opcode != 0)
2344 {
2345 q = frag_more (1);
2346 *q = opcode;
2347 return;
2348 }
2349 }
2350
2351 switch (src->X_op)
2352 {
2353 case O_md1:
2354 if (ins_ok & INS_GBZ80)
2355 { /* LD A,(HL+) or LD A,(HL-) */
2356 if (dst->X_op == O_register && dst->X_add_number == REG_A)
2357 *frag_more (1) = (src->X_add_number == REG_HL) ? 0x2A : 0x3A;
2358 else
2359 ill_op ();
2360 break;
2361 }
2362 /* Fall through. */
2363 case O_register:
2364 if (dst->X_add_number > 7)
2365 ill_op ();
2366 opcode = 0x46; /* LD B,(HL) */
2367 switch (src->X_add_number)
2368 {
2369 case REG_HL: prefix = 0x00; break;
2370 case REG_IX: prefix = 0xDD; break;
2371 case REG_IY: prefix = 0xFD; break;
2372 default:
2373 ill_op ();
2374 }
2375 q = frag_more (prefix ? 2 : 1);
2376 if (prefix)
2377 *q++ = prefix;
2378 *q = opcode | ((dst->X_add_number & 7) << 3);
2379 if (prefix)
2380 {
2381 src_offset = *src;
2382 src_offset.X_op = O_symbol;
2383 src_offset.X_add_number = 0;
2384 emit_byte (& src_offset, BFD_RELOC_Z80_DISP8);
2385 }
2386 break;
2387 default: /* LD A,(nn) */
2388 if (dst->X_add_number == REG_A)
2389 {
2390 q = frag_more (1);
2391 *q = (ins_ok & INS_GBZ80) ? 0xFA : 0x3A;
2392 emit_word (src);
2393 }
2394 }
2395 }
2396
2397 static void
2398 emit_ld_r_n (expressionS *dst, expressionS *src)
2399 { /* for 8-bit immediate value load to register: LD r,n */
2400 char *q;
2401 char prefix = 0;
2402
2403 switch (dst->X_add_number)
2404 {
2405 case REG_H|R_IX:
2406 case REG_L|R_IX:
2407 prefix = 0xDD;
2408 break;
2409 case REG_H|R_IY:
2410 case REG_L|R_IY:
2411 prefix = 0xFD;
2412 break;
2413 case REG_A:
2414 case REG_B:
2415 case REG_C:
2416 case REG_D:
2417 case REG_E:
2418 case REG_H:
2419 case REG_L:
2420 break;
2421 default:
2422 ill_op ();
2423 }
2424
2425 q = frag_more (prefix ? 2 : 1);
2426 if (prefix)
2427 {
2428 if (ins_ok & INS_GBZ80)
2429 ill_op ();
2430 else if (!(ins_ok & (INS_EZ80|INS_R800|INS_Z80N)))
2431 check_mach (INS_IDX_HALF);
2432 *q++ = prefix;
2433 }
2434 *q = 0x06 | ((dst->X_add_number & 7) << 3);
2435 emit_byte (src, BFD_RELOC_8);
2436 }
2437
2438 static void
2439 emit_ld_r_r (expressionS *dst, expressionS *src)
2440 { /* mostly 8-bit load register from register instructions: LD r,r */
2441 /* there are some exceptions: LD SP,HL/IX/IY; LD I,HL and LD HL,I */
2442 char *q;
2443 int prefix = 0;
2444 int opcode = 0;
2445 int ii_halves = 0;
2446
2447 switch (dst->X_add_number)
2448 {
2449 case REG_SP:
2450 switch (src->X_add_number)
2451 {
2452 case REG_HL: prefix = 0x00; break;
2453 case REG_IX: prefix = 0xDD; break;
2454 case REG_IY: prefix = 0xFD; break;
2455 default:
2456 ill_op ();
2457 }
2458 opcode = 0xF9;
2459 break;
2460 case REG_HL:
2461 if (!(ins_ok & INS_EZ80))
2462 ill_op ();
2463 if (src->X_add_number != REG_I)
2464 ill_op ();
2465 if (cpu_mode < 1)
2466 error (_("ADL mode instruction"));
2467 /* LD HL,I */
2468 prefix = 0xED;
2469 opcode = 0xD7;
2470 break;
2471 case REG_I:
2472 if (src->X_add_number == REG_HL)
2473 {
2474 if (!(ins_ok & INS_EZ80))
2475 ill_op ();
2476 if (cpu_mode < 1)
2477 error (_("ADL mode instruction"));
2478 prefix = 0xED;
2479 opcode = 0xC7;
2480 }
2481 else if (src->X_add_number == REG_A)
2482 {
2483 prefix = 0xED;
2484 opcode = 0x47;
2485 }
2486 else
2487 ill_op ();
2488 break;
2489 case REG_MB:
2490 if (!(ins_ok & INS_EZ80) || (src->X_add_number != REG_A))
2491 ill_op ();
2492 if (cpu_mode < 1)
2493 error (_("ADL mode instruction"));
2494 prefix = 0xED;
2495 opcode = 0x6D;
2496 break;
2497 case REG_R:
2498 if (src->X_add_number == REG_A) /* LD R,A */
2499 {
2500 prefix = 0xED;
2501 opcode = 0x4F;
2502 }
2503 else
2504 ill_op ();
2505 break;
2506 case REG_A:
2507 if (src->X_add_number == REG_I) /* LD A,I */
2508 {
2509 prefix = 0xED;
2510 opcode = 0x57;
2511 break;
2512 }
2513 else if (src->X_add_number == REG_R) /* LD A,R */
2514 {
2515 prefix = 0xED;
2516 opcode = 0x5F;
2517 break;
2518 }
2519 else if (src->X_add_number == REG_MB) /* LD A,MB */
2520 {
2521 if (!(ins_ok & INS_EZ80))
2522 ill_op ();
2523 else
2524 {
2525 if (cpu_mode < 1)
2526 error (_("ADL mode instruction"));
2527 prefix = 0xED;
2528 opcode = 0x6E;
2529 }
2530 break;
2531 }
2532 /* Fall through. */
2533 case REG_B:
2534 case REG_C:
2535 case REG_D:
2536 case REG_E:
2537 case REG_H:
2538 case REG_L:
2539 prefix = 0x00;
2540 break;
2541 case REG_H|R_IX:
2542 case REG_L|R_IX:
2543 prefix = 0xDD;
2544 ii_halves = 1;
2545 break;
2546 case REG_H|R_IY:
2547 case REG_L|R_IY:
2548 prefix = 0xFD;
2549 ii_halves = 1;
2550 break;
2551 default:
2552 ill_op ();
2553 }
2554
2555 if (opcode == 0)
2556 {
2557 switch (src->X_add_number)
2558 {
2559 case REG_A:
2560 case REG_B:
2561 case REG_C:
2562 case REG_D:
2563 case REG_E:
2564 break;
2565 case REG_H:
2566 case REG_L:
2567 if (prefix != 0)
2568 ill_op (); /* LD iiH/L,H/L are not permitted */
2569 break;
2570 case REG_H|R_IX:
2571 case REG_L|R_IX:
2572 if (prefix == 0xFD || dst->X_add_number == REG_H || dst->X_add_number == REG_L)
2573 ill_op (); /* LD IYL,IXL and LD H,IXH are not permitted */
2574 prefix = 0xDD;
2575 ii_halves = 1;
2576 break;
2577 case REG_H|R_IY:
2578 case REG_L|R_IY:
2579 if (prefix == 0xDD || dst->X_add_number == REG_H || dst->X_add_number == REG_L)
2580 ill_op (); /* LD IXH,IYH and LD L,IYL are not permitted */
2581 prefix = 0xFD;
2582 ii_halves = 1;
2583 break;
2584 default:
2585 ill_op ();
2586 }
2587 opcode = 0x40 + ((dst->X_add_number & 7) << 3) + (src->X_add_number & 7);
2588 }
2589 if ((ins_ok & INS_GBZ80) && prefix != 0)
2590 ill_op ();
2591 if (ii_halves && !(ins_ok & (INS_EZ80|INS_R800|INS_Z80N)))
2592 check_mach (INS_IDX_HALF);
2593 if (prefix == 0 && (ins_ok & INS_EZ80))
2594 {
2595 switch (opcode)
2596 {
2597 case 0x40: /* SIS prefix, in Z80 it is LD B,B */
2598 case 0x49: /* LIS prefix, in Z80 it is LD C,C */
2599 case 0x52: /* SIL prefix, in Z80 it is LD D,D */
2600 case 0x5B: /* LIL prefix, in Z80 it is LD E,E */
2601 as_warn (_("unsupported instruction, assembled as NOP"));
2602 opcode = 0x00;
2603 break;
2604 default:;
2605 }
2606 }
2607 q = frag_more (prefix ? 2 : 1);
2608 if (prefix)
2609 *q++ = prefix;
2610 *q = opcode;
2611 }
2612
2613 static void
2614 emit_ld_rr_m (expressionS *dst, expressionS *src)
2615 { /* for 16-bit indirect load from memory to register: LD rr,(xxx) */
2616 char *q;
2617 int prefix = 0;
2618 int opcode = 0;
2619 expressionS src_offset;
2620
2621 /* GBZ80 has no support for 16-bit load from memory instructions */
2622 if (ins_ok & INS_GBZ80)
2623 ill_op ();
2624
2625 prefix = 0xED;
2626 switch (src->X_op)
2627 {
2628 case O_md1: /* LD rr,(ii+d) */
2629 prefix = (src->X_add_number == REG_IX) ? 0xDD : 0xFD;
2630 /* Fall through. */
2631 case O_register: /* LD rr,(HL) */
2632 /* currently only EZ80 has support for 16bit indirect memory load instructions */
2633 if (!(ins_ok & INS_EZ80))
2634 ill_op ();
2635 switch (dst->X_add_number)
2636 {
2637 case REG_BC: opcode = 0x07; break;
2638 case REG_DE: opcode = 0x17; break;
2639 case REG_HL: opcode = 0x27; break;
2640 case REG_IX: opcode = (prefix == 0xED || prefix == 0xDD) ? 0x37 : 0x31; break;
2641 case REG_IY: opcode = (prefix == 0xED || prefix == 0xDD) ? 0x31 : 0x37; break;
2642 default:
2643 ill_op ();
2644 }
2645 q = frag_more (2);
2646 *q++ = prefix;
2647 *q = opcode;
2648 if (prefix != 0xED)
2649 {
2650 src_offset = *src;
2651 src_offset.X_op = O_symbol;
2652 src_offset.X_add_number = 0;
2653 emit_byte (& src_offset, BFD_RELOC_Z80_DISP8);
2654 }
2655 break;
2656 default: /* LD rr,(nn) */
2657 switch (dst->X_add_number)
2658 {
2659 case REG_BC: prefix = 0xED; opcode = 0x4B; break;
2660 case REG_DE: prefix = 0xED; opcode = 0x5B; break;
2661 case REG_HL: prefix = 0x00; opcode = 0x2A; break;
2662 case REG_SP: prefix = 0xED; opcode = 0x7B; break;
2663 case REG_IX: prefix = 0xDD; opcode = 0x2A; break;
2664 case REG_IY: prefix = 0xFD; opcode = 0x2A; break;
2665 default:
2666 ill_op ();
2667 }
2668 q = frag_more (prefix ? 2 : 1);
2669 if (prefix)
2670 *q++ = prefix;
2671 *q = opcode;
2672 emit_word (src);
2673 }
2674 return;
2675 }
2676
2677 static void
2678 emit_ld_rr_nn (expressionS *dst, expressionS *src)
2679 { /* mostly load imediate value to multibyte register instructions: LD rr,nn */
2680 char *q;
2681 int prefix = 0x00;
2682 int opcode = 0x21; /* LD HL,nn */
2683 switch (dst->X_add_number)
2684 {
2685 case REG_IX:
2686 prefix = 0xDD;
2687 break;
2688 case REG_IY:
2689 prefix = 0xFD;
2690 break;
2691 case REG_HL:
2692 break;
2693 case REG_BC:
2694 case REG_DE:
2695 case REG_SP:
2696 opcode = 0x01 + ((dst->X_add_number & 3) << 4);
2697 break;
2698 default:
2699 ill_op ();
2700 return;
2701 }
2702 if (prefix && (ins_ok & INS_GBZ80))
2703 ill_op ();
2704 q = frag_more (prefix ? 2 : 1);
2705 if (prefix)
2706 *q++ = prefix;
2707 *q = opcode;
2708 emit_word (src);
2709 }
2710
2711 static const char *
2712 emit_ld (char prefix_in ATTRIBUTE_UNUSED, char opcode_in ATTRIBUTE_UNUSED,
2713 const char * args)
2714 {
2715 expressionS dst, src;
2716 const char *p;
2717
2718 p = parse_exp (args, & dst);
2719 if (*p++ != ',')
2720 error (_("bad instruction syntax"));
2721 p = parse_exp (p, & src);
2722
2723 if (dst.X_md)
2724 {
2725 if (src.X_op == O_register)
2726 {
2727 if (src.X_add_number <= 7)
2728 emit_ld_m_r (& dst, & src); /* LD (xxx),r */
2729 else
2730 emit_ld_m_rr (& dst, & src); /* LD (xxx),rr */
2731 }
2732 else
2733 emit_ld_m_n (& dst, & src); /* LD (hl),n or LD (ix/y+r),n */
2734 }
2735 else if (dst.X_op == O_register)
2736 {
2737 if (src.X_md)
2738 {
2739 if (dst.X_add_number <= 7)
2740 emit_ld_r_m (& dst, & src);
2741 else
2742 emit_ld_rr_m (& dst, & src);
2743 }
2744 else if (src.X_op == O_register)
2745 emit_ld_r_r (& dst, & src);
2746 else if ((dst.X_add_number & ~R_INDEX) <= 7)
2747 emit_ld_r_n (& dst, & src);
2748 else
2749 emit_ld_rr_nn (& dst, & src);
2750 }
2751 else
2752 ill_op ();
2753
2754 return p;
2755 }
2756
2757 static const char *
2758 emit_lddldi (char prefix, char opcode, const char * args)
2759 {
2760 expressionS dst, src;
2761 const char *p;
2762 char *q;
2763
2764 if (!(ins_ok & INS_GBZ80))
2765 return emit_insn (prefix, opcode, args);
2766
2767 p = parse_exp (args, & dst);
2768 if (*p++ != ',')
2769 error (_("bad instruction syntax"));
2770 p = parse_exp (p, & src);
2771
2772 if (dst.X_op != O_register || src.X_op != O_register)
2773 ill_op ();
2774
2775 /* convert opcode 0xA0 . 0x22, 0xA8 . 0x32 */
2776 opcode = (opcode & 0x08) * 2 + 0x22;
2777
2778 if (dst.X_md != 0
2779 && dst.X_add_number == REG_HL
2780 && src.X_md == 0
2781 && src.X_add_number == REG_A)
2782 opcode |= 0x00; /* LDx (HL),A */
2783 else if (dst.X_md == 0
2784 && dst.X_add_number == REG_A
2785 && src.X_md != 0
2786 && src.X_add_number == REG_HL)
2787 opcode |= 0x08; /* LDx A,(HL) */
2788 else
2789 ill_op ();
2790
2791 q = frag_more (1);
2792 *q = opcode;
2793 return p;
2794 }
2795
2796 static const char *
2797 emit_ldh (char prefix ATTRIBUTE_UNUSED, char opcode ATTRIBUTE_UNUSED,
2798 const char * args)
2799 {
2800 expressionS dst, src;
2801 const char *p;
2802 char *q;
2803
2804 p = parse_exp (args, & dst);
2805 if (*p++ != ',')
2806 {
2807 error (_("bad instruction syntax"));
2808 return p;
2809 }
2810
2811 p = parse_exp (p, & src);
2812 if (dst.X_md == 0
2813 && dst.X_op == O_register
2814 && dst.X_add_number == REG_A
2815 && src.X_md != 0
2816 && src.X_op != O_md1)
2817 {
2818 if (src.X_op != O_register)
2819 {
2820 q = frag_more (1);
2821 *q = 0xF0;
2822 emit_byte (& src, BFD_RELOC_8);
2823 }
2824 else if (src.X_add_number == REG_C)
2825 *frag_more (1) = 0xF2;
2826 else
2827 ill_op ();
2828 }
2829 else if (dst.X_md != 0
2830 && dst.X_op != O_md1
2831 && src.X_md == 0
2832 && src.X_op == O_register
2833 && src.X_add_number == REG_A)
2834 {
2835 if (dst.X_op == O_register)
2836 {
2837 if (dst.X_add_number == REG_C)
2838 {
2839 q = frag_more (1);
2840 *q = 0xE2;
2841 }
2842 else
2843 ill_op ();
2844 }
2845 else
2846 {
2847 q = frag_more (1);
2848 *q = 0xE0;
2849 emit_byte (& dst, BFD_RELOC_8);
2850 }
2851 }
2852 else
2853 ill_op ();
2854
2855 return p;
2856 }
2857
2858 static const char *
2859 emit_ldhl (char prefix ATTRIBUTE_UNUSED, char opcode, const char * args)
2860 {
2861 expressionS dst, src;
2862 const char *p;
2863 char *q;
2864 p = parse_exp (args, & dst);
2865 if (*p++ != ',')
2866 {
2867 error (_("bad instruction syntax"));
2868 return p;
2869 }
2870
2871 p = parse_exp (p, & src);
2872 if (dst.X_md || dst.X_op != O_register || dst.X_add_number != REG_SP
2873 || src.X_md || src.X_op == O_register || src.X_op == O_md1)
2874 ill_op ();
2875 q = frag_more (1);
2876 *q = opcode;
2877 emit_byte (& src, BFD_RELOC_Z80_DISP8);
2878 return p;
2879 }
2880
2881 static const char *
2882 parse_lea_pea_args (const char * args, expressionS *op)
2883 {
2884 const char *p;
2885 p = parse_exp (args, op);
2886 if (sdcc_compat && *p == ',' && op->X_op == O_register)
2887 {
2888 expressionS off;
2889 p = parse_exp (p + 1, &off);
2890 op->X_op = O_add;
2891 op->X_add_symbol = make_expr_symbol (&off);
2892 }
2893 return p;
2894 }
2895
2896 static const char *
2897 emit_lea (char prefix, char opcode, const char * args)
2898 {
2899 expressionS dst, src;
2900 const char *p;
2901 char *q;
2902 int rnum;
2903
2904 p = parse_exp (args, & dst);
2905 if (dst.X_md != 0 || dst.X_op != O_register)
2906 ill_op ();
2907
2908 rnum = dst.X_add_number;
2909 switch (rnum)
2910 {
2911 case REG_BC:
2912 case REG_DE:
2913 case REG_HL:
2914 opcode = 0x02 | ((rnum & 0x03) << 4);
2915 break;
2916 case REG_IX:
2917 opcode = 0x32; /* lea ix,ix+d has opcode 0x32; lea ix,iy+d has opcode 0x54 */
2918 break;
2919 case REG_IY:
2920 opcode = 0x33; /* lea iy,iy+d has opcode 0x33; lea iy,ix+d has opcode 0x55 */
2921 break;
2922 default:
2923 ill_op ();
2924 }
2925
2926 if (*p++ != ',')
2927 error (_("bad instruction syntax"));
2928
2929 p = parse_lea_pea_args (p, & src);
2930 if (src.X_md != 0 || src.X_op != O_add /*&& src.X_op != O_register*/)
2931 ill_op ();
2932
2933 rnum = src.X_add_number;
2934 switch (src.X_op)
2935 {
2936 case O_add:
2937 break;
2938 case O_register: /* permit instructions like LEA rr,IX without displacement specified */
2939 src.X_add_symbol = zero;
2940 break;
2941 default:
2942 ill_op ();
2943 }
2944
2945 switch (rnum)
2946 {
2947 case REG_IX:
2948 opcode = (opcode == (char)0x33) ? 0x55 : (opcode|0x00);
2949 break;
2950 case REG_IY:
2951 opcode = (opcode == (char)0x32) ? 0x54 : (opcode|0x01);
2952 }
2953
2954 q = frag_more (2);
2955 *q++ = prefix;
2956 *q = opcode;
2957
2958 src.X_op = O_symbol;
2959 src.X_add_number = 0;
2960 emit_byte (& src, BFD_RELOC_Z80_DISP8);
2961
2962 return p;
2963 }
2964
2965 static const char *
2966 emit_mlt (char prefix, char opcode, const char * args)
2967 {
2968 expressionS arg;
2969 const char *p;
2970 char *q;
2971
2972 p = parse_exp (args, & arg);
2973 if (arg.X_md != 0 || arg.X_op != O_register || !(arg.X_add_number & R_ARITH))
2974 ill_op ();
2975
2976 q = frag_more (2);
2977 if (ins_ok & INS_Z80N)
2978 {
2979 if (arg.X_add_number != REG_DE)
2980 ill_op ();
2981 *q++ = 0xED;
2982 *q = 0x30;
2983 }
2984 else
2985 {
2986 *q++ = prefix;
2987 *q = opcode | ((arg.X_add_number & 3) << 4);
2988 }
2989
2990 return p;
2991 }
2992
2993 /* MUL D,E (Z80N only) */
2994 static const char *
2995 emit_mul (char prefix, char opcode, const char * args)
2996 {
2997 expressionS r1, r2;
2998 const char *p;
2999 char *q;
3000
3001 p = parse_exp (args, & r1);
3002 if (*p++ != ',')
3003 error (_("bad instruction syntax"));
3004 p = parse_exp (p, & r2);
3005
3006 if (r1.X_md != 0 || r1.X_op != O_register || r1.X_add_number != REG_D ||
3007 r2.X_md != 0 || r2.X_op != O_register || r2.X_add_number != REG_E)
3008 ill_op ();
3009
3010 q = frag_more (2);
3011 *q++ = prefix;
3012 *q = opcode;
3013
3014 return p;
3015 }
3016
3017 static const char *
3018 emit_nextreg (char prefix, char opcode ATTRIBUTE_UNUSED, const char * args)
3019 {
3020 expressionS rr, nn;
3021 const char *p;
3022 char *q;
3023
3024 p = parse_exp (args, & rr);
3025 if (*p++ != ',')
3026 error (_("bad instruction syntax"));
3027 p = parse_exp (p, & nn);
3028 if (rr.X_md != 0 || rr.X_op == O_register || rr.X_op == O_md1 ||
3029 nn.X_md != 0 || nn.X_op == O_md1)
3030 ill_op ();
3031 q = frag_more (2);
3032 *q++ = prefix;
3033 emit_byte (&rr, BFD_RELOC_8);
3034 if (nn.X_op == O_register && nn.X_add_number == REG_A)
3035 *q = 0x92;
3036 else if (nn.X_op != O_register)
3037 {
3038 *q = 0x91;
3039 emit_byte (&nn, BFD_RELOC_8);
3040 }
3041 else
3042 ill_op ();
3043 return p;
3044 }
3045
3046 static const char *
3047 emit_pea (char prefix, char opcode, const char * args)
3048 {
3049 expressionS arg;
3050 const char *p;
3051 char *q;
3052
3053 p = parse_lea_pea_args (args, & arg);
3054 if (arg.X_md != 0
3055 || (/*arg.X_op != O_register &&*/ arg.X_op != O_add)
3056 || !(arg.X_add_number & R_INDEX))
3057 ill_op ();
3058 /* PEA ii without displacement is mostly typo,
3059 because there is PUSH instruction which is shorter and faster */
3060 /*if (arg.X_op == O_register)
3061 as_warn (_("PEA is used without displacement, use PUSH instead"));*/
3062
3063 q = frag_more (2);
3064 *q++ = prefix;
3065 *q = opcode + (arg.X_add_number == REG_IY ? 1 : 0);
3066
3067 arg.X_op = O_symbol;
3068 arg.X_add_number = 0;
3069 emit_byte (& arg, BFD_RELOC_Z80_DISP8);
3070
3071 return p;
3072 }
3073
3074 static const char *
3075 emit_reti (char prefix, char opcode, const char * args)
3076 {
3077 if (ins_ok & INS_GBZ80)
3078 return emit_insn (0x00, 0xD9, args);
3079
3080 return emit_insn (prefix, opcode, args);
3081 }
3082
3083 static const char *
3084 emit_tst (char prefix, char opcode, const char *args)
3085 {
3086 expressionS arg_s;
3087 const char *p;
3088 char *q;
3089 int rnum;
3090
3091 p = parse_exp (args, & arg_s);
3092 if (*p == ',' && arg_s.X_md == 0 && arg_s.X_op == O_register && arg_s.X_add_number == REG_A)
3093 {
3094 if (!(ins_ok & INS_EZ80))
3095 ill_op ();
3096 ++p;
3097 p = parse_exp (p, & arg_s);
3098 }
3099
3100 rnum = arg_s.X_add_number;
3101 switch (arg_s.X_op)
3102 {
3103 case O_md1:
3104 ill_op ();
3105 break;
3106 case O_register:
3107 rnum = arg_s.X_add_number;
3108 if (arg_s.X_md != 0)
3109 {
3110 if (rnum != REG_HL)
3111 ill_op ();
3112 else
3113 rnum = 6;
3114 }
3115 q = frag_more (2);
3116 *q++ = prefix;
3117 *q = opcode | (rnum << 3);
3118 break;
3119 default:
3120 if (arg_s.X_md)
3121 ill_op ();
3122 q = frag_more (2);
3123 if (ins_ok & INS_Z80N)
3124 {
3125 *q++ = 0xED;
3126 *q = 0x27;
3127 }
3128 else
3129 {
3130 *q++ = prefix;
3131 *q = opcode | 0x60;
3132 }
3133 emit_byte (& arg_s, BFD_RELOC_8);
3134 }
3135 return p;
3136 }
3137
3138 static const char *
3139 emit_insn_n (char prefix, char opcode, const char *args)
3140 {
3141 expressionS arg;
3142 const char *p;
3143 char *q;
3144
3145 p = parse_exp (args, & arg);
3146 if (arg.X_md || arg.X_op == O_register || arg.X_op == O_md1)
3147 ill_op ();
3148
3149 q = frag_more (2);
3150 *q++ = prefix;
3151 *q = opcode;
3152 emit_byte (& arg, BFD_RELOC_8);
3153
3154 return p;
3155 }
3156
3157 static void
3158 emit_data (int size ATTRIBUTE_UNUSED)
3159 {
3160 const char *p, *q;
3161 char *u, quote;
3162 int cnt;
3163 expressionS exp;
3164
3165 if (is_it_end_of_statement ())
3166 {
3167 demand_empty_rest_of_line ();
3168 return;
3169 }
3170 p = skip_space (input_line_pointer);
3171
3172 do
3173 {
3174 if (*p == '\"' || *p == '\'')
3175 {
3176 for (quote = *p, q = ++p, cnt = 0; *p && quote != *p; ++p, ++cnt)
3177 ;
3178 u = frag_more (cnt);
3179 memcpy (u, q, cnt);
3180 if (!*p)
3181 as_warn (_("unterminated string"));
3182 else
3183 p = skip_space (p+1);
3184 }
3185 else
3186 {
3187 p = parse_exp (p, &exp);
3188 if (exp.X_op == O_md1 || exp.X_op == O_register)
3189 {
3190 ill_op ();
3191 break;
3192 }
3193 if (exp.X_md)
3194 as_warn (_("parentheses ignored"));
3195 emit_byte (&exp, BFD_RELOC_8);
3196 p = skip_space (p);
3197 }
3198 }
3199 while (*p++ == ',') ;
3200 input_line_pointer = (char *)(p-1);
3201 }
3202
3203 static void
3204 z80_cons (int size)
3205 {
3206 const char *p;
3207 expressionS exp;
3208
3209 if (is_it_end_of_statement ())
3210 {
3211 demand_empty_rest_of_line ();
3212 return;
3213 }
3214 p = skip_space (input_line_pointer);
3215
3216 do
3217 {
3218 p = parse_exp (p, &exp);
3219 if (exp.X_op == O_md1 || exp.X_op == O_register)
3220 {
3221 ill_op ();
3222 break;
3223 }
3224 if (exp.X_md)
3225 as_warn (_("parentheses ignored"));
3226 emit_data_val (&exp, size);
3227 p = skip_space (p);
3228 } while (*p++ == ',') ;
3229 input_line_pointer = (char *)(p-1);
3230 }
3231
3232 /* next functions were commented out because it is difficult to mix
3233 both ADL and Z80 mode instructions within one COFF file:
3234 objdump cannot recognize point of mode switching.
3235 */
3236 static void
3237 set_cpu_mode (int mode)
3238 {
3239 if (ins_ok & INS_EZ80)
3240 cpu_mode = mode;
3241 else
3242 error (_("CPU mode is unsupported by target"));
3243 }
3244
3245 static void
3246 assume (int arg ATTRIBUTE_UNUSED)
3247 {
3248 char *name;
3249 char c;
3250 int n;
3251
3252 input_line_pointer = (char*)skip_space (input_line_pointer);
3253 c = get_symbol_name (& name);
3254 if (strncasecmp (name, "ADL", 4) != 0)
3255 {
3256 ill_op ();
3257 return;
3258 }
3259
3260 restore_line_pointer (c);
3261 input_line_pointer = (char*)skip_space (input_line_pointer);
3262 if (*input_line_pointer++ != '=')
3263 {
3264 error (_("assignment expected"));
3265 return;
3266 }
3267 input_line_pointer = (char*)skip_space (input_line_pointer);
3268 n = get_single_number ();
3269
3270 set_cpu_mode (n);
3271 }
3272
3273 static const char *
3274 emit_mulub (char prefix ATTRIBUTE_UNUSED, char opcode, const char * args)
3275 {
3276 const char *p;
3277
3278 p = skip_space (args);
3279 if (TOLOWER (*p++) != 'a' || *p++ != ',')
3280 ill_op ();
3281 else
3282 {
3283 char *q, reg;
3284
3285 reg = TOLOWER (*p++);
3286 switch (reg)
3287 {
3288 case 'b':
3289 case 'c':
3290 case 'd':
3291 case 'e':
3292 check_mach (INS_R800);
3293 if (!*skip_space (p))
3294 {
3295 q = frag_more (2);
3296 *q++ = prefix;
3297 *q = opcode + ((reg - 'b') << 3);
3298 break;
3299 }
3300 /* Fall through. */
3301 default:
3302 ill_op ();
3303 }
3304 }
3305 return p;
3306 }
3307
3308 static const char *
3309 emit_muluw (char prefix ATTRIBUTE_UNUSED, char opcode, const char * args)
3310 {
3311 const char *p;
3312
3313 p = skip_space (args);
3314 if (TOLOWER (*p++) != 'h' || TOLOWER (*p++) != 'l' || *p++ != ',')
3315 ill_op ();
3316 else
3317 {
3318 expressionS reg;
3319 char *q;
3320
3321 p = parse_exp (p, & reg);
3322
3323 if ((!reg.X_md) && reg.X_op == O_register)
3324 switch (reg.X_add_number)
3325 {
3326 case REG_BC:
3327 case REG_SP:
3328 check_mach (INS_R800);
3329 q = frag_more (2);
3330 *q++ = prefix;
3331 *q = opcode + ((reg.X_add_number & 3) << 4);
3332 break;
3333 default:
3334 ill_op ();
3335 }
3336 }
3337 return p;
3338 }
3339
3340 static int
3341 assemble_suffix (const char **suffix)
3342 {
3343 static
3344 const char sf[8][4] =
3345 {
3346 "il",
3347 "is",
3348 "l",
3349 "lil",
3350 "lis",
3351 "s",
3352 "sil",
3353 "sis"
3354 };
3355 const char *p;
3356 const char (*t)[4];
3357 char sbuf[4];
3358 int i;
3359
3360 p = *suffix;
3361 if (*p++ != '.')
3362 return 0;
3363
3364 for (i = 0; (i < 3) && (ISALPHA (*p)); i++)
3365 sbuf[i] = TOLOWER (*p++);
3366 if (*p && !ISSPACE (*p))
3367 return 0;
3368 *suffix = p;
3369 sbuf[i] = 0;
3370
3371 t = bsearch (sbuf, sf, ARRAY_SIZE (sf), sizeof (sf[0]), (int(*)(const void*, const void*)) strcmp);
3372 if (t == NULL)
3373 return 0;
3374 i = t - sf;
3375 switch (i)
3376 {
3377 case 0: /* IL */
3378 i = cpu_mode ? 0x5B : 0x52;
3379 break;
3380 case 1: /* IS */
3381 i = cpu_mode ? 0x49 : 0x40;
3382 break;
3383 case 2: /* L */
3384 i = cpu_mode ? 0x5B : 0x49;
3385 break;
3386 case 3: /* LIL */
3387 i = 0x5B;
3388 break;
3389 case 4: /* LIS */
3390 i = 0x49;
3391 break;
3392 case 5: /* S */
3393 i = cpu_mode ? 0x52 : 0x40;
3394 break;
3395 case 6: /* SIL */
3396 i = 0x52;
3397 break;
3398 case 7: /* SIS */
3399 i = 0x40;
3400 break;
3401 }
3402 *frag_more (1) = (char)i;
3403 switch (i)
3404 {
3405 case 0x40: inst_mode = INST_MODE_FORCED | INST_MODE_S | INST_MODE_IS; break;
3406 case 0x49: inst_mode = INST_MODE_FORCED | INST_MODE_L | INST_MODE_IS; break;
3407 case 0x52: inst_mode = INST_MODE_FORCED | INST_MODE_S | INST_MODE_IL; break;
3408 case 0x5B: inst_mode = INST_MODE_FORCED | INST_MODE_L | INST_MODE_IL; break;
3409 }
3410 return 1;
3411 }
3412
3413 static void
3414 psect (int arg)
3415 {
3416 #if defined(OBJ_ELF)
3417 return obj_elf_section (arg);
3418 #elif defined(OBJ_COFF)
3419 return obj_coff_section (arg);
3420 #else
3421 #error Unknown object format
3422 #endif
3423 }
3424
3425 static void
3426 set_inss (int inss)
3427 {
3428 int old_ins;
3429
3430 if (!sdcc_compat)
3431 as_fatal (_("Invalid directive"));
3432
3433 old_ins = ins_ok;
3434 ins_ok &= INS_MARCH_MASK;
3435 ins_ok |= inss;
3436 if (old_ins != ins_ok)
3437 cpu_mode = 0;
3438 }
3439
3440 static void
3441 ignore (int arg ATTRIBUTE_UNUSED)
3442 {
3443 ignore_rest_of_line ();
3444 }
3445
3446 static void
3447 area (int arg)
3448 {
3449 char *p;
3450 if (!sdcc_compat)
3451 as_fatal (_("Invalid directive"));
3452 for (p = input_line_pointer; *p && *p != '(' && *p != '\n'; p++)
3453 ;
3454 if (*p == '(')
3455 {
3456 *p = '\n';
3457 psect (arg);
3458 *p++ = '(';
3459 ignore_rest_of_line ();
3460 }
3461 else
3462 psect (arg);
3463 }
3464
3465 /* Handle the .bss pseudo-op. */
3466
3467 static void
3468 s_bss (int ignore ATTRIBUTE_UNUSED)
3469 {
3470 subseg_set (bss_section, 0);
3471 demand_empty_rest_of_line ();
3472 }
3473
3474 /* Port specific pseudo ops. */
3475 const pseudo_typeS md_pseudo_table[] =
3476 {
3477 { ".area", area, 0},
3478 { ".assume", assume, 0},
3479 { ".ez80", set_inss, INS_EZ80},
3480 { ".gbz80", set_inss, INS_GBZ80},
3481 { ".module", ignore, 0},
3482 { ".optsdcc", ignore, 0},
3483 { ".r800", set_inss, INS_R800},
3484 { ".set", s_set, 0},
3485 { ".z180", set_inss, INS_Z180},
3486 { ".hd64", set_inss, INS_Z180},
3487 { ".z80", set_inss, INS_Z80},
3488 { ".z80n", set_inss, INS_Z80N},
3489 { "bss", s_bss, 0},
3490 { "db" , emit_data, 1},
3491 { "d24", z80_cons, 3},
3492 { "d32", z80_cons, 4},
3493 { "def24", z80_cons, 3},
3494 { "def32", z80_cons, 4},
3495 { "defb", emit_data, 1},
3496 { "defm", emit_data, 1},
3497 { "defs", s_space, 1}, /* Synonym for ds on some assemblers. */
3498 { "defw", z80_cons, 2},
3499 { "ds", s_space, 1}, /* Fill with bytes rather than words. */
3500 { "dw", z80_cons, 2},
3501 { "psect", psect, 0}, /* TODO: Translate attributes. */
3502 { "set", 0, 0}, /* Real instruction on z80. */
3503 { "xdef", s_globl, 0}, /* Synonym for .GLOBAL */
3504 { "xref", s_ignore, 0}, /* Synonym for .EXTERN */
3505 { NULL, 0, 0 }
3506 } ;
3507
3508 static table_t instab[] =
3509 {
3510 { "adc", 0x88, 0x4A, emit_adc, INS_ALL },
3511 { "add", 0x80, 0x09, emit_add, INS_ALL },
3512 { "and", 0x00, 0xA0, emit_s, INS_ALL },
3513 { "bit", 0xCB, 0x40, emit_bit, INS_ALL },
3514 { "brlc", 0xED, 0x2C, emit_bshft,INS_Z80N },
3515 { "bsla", 0xED, 0x28, emit_bshft,INS_Z80N },
3516 { "bsra", 0xED, 0x29, emit_bshft,INS_Z80N },
3517 { "bsrf", 0xED, 0x2B, emit_bshft,INS_Z80N },
3518 { "bsrl", 0xED, 0x2A, emit_bshft,INS_Z80N },
3519 { "call", 0xCD, 0xC4, emit_jpcc, INS_ALL },
3520 { "ccf", 0x00, 0x3F, emit_insn, INS_ALL },
3521 { "cp", 0x00, 0xB8, emit_s, INS_ALL },
3522 { "cpd", 0xED, 0xA9, emit_insn, INS_NOT_GBZ80 },
3523 { "cpdr", 0xED, 0xB9, emit_insn, INS_NOT_GBZ80 },
3524 { "cpi", 0xED, 0xA1, emit_insn, INS_NOT_GBZ80 },
3525 { "cpir", 0xED, 0xB1, emit_insn, INS_NOT_GBZ80 },
3526 { "cpl", 0x00, 0x2F, emit_insn, INS_ALL },
3527 { "daa", 0x00, 0x27, emit_insn, INS_ALL },
3528 { "dec", 0x0B, 0x05, emit_incdec,INS_ALL },
3529 { "di", 0x00, 0xF3, emit_insn, INS_ALL },
3530 { "djnz", 0x00, 0x10, emit_jr, INS_NOT_GBZ80 },
3531 { "ei", 0x00, 0xFB, emit_insn, INS_ALL },
3532 { "ex", 0x00, 0x00, emit_ex, INS_NOT_GBZ80 },
3533 { "exx", 0x00, 0xD9, emit_insn, INS_NOT_GBZ80 },
3534 { "halt", 0x00, 0x76, emit_insn, INS_ALL },
3535 { "im", 0xED, 0x46, emit_im, INS_NOT_GBZ80 },
3536 { "in", 0x00, 0x00, emit_in, INS_NOT_GBZ80 },
3537 { "in0", 0xED, 0x00, emit_in0, INS_Z180|INS_EZ80 },
3538 { "inc", 0x03, 0x04, emit_incdec,INS_ALL },
3539 { "ind", 0xED, 0xAA, emit_insn, INS_NOT_GBZ80 },
3540 { "ind2", 0xED, 0x8C, emit_insn, INS_EZ80 },
3541 { "ind2r",0xED, 0x9C, emit_insn, INS_EZ80 },
3542 { "indm", 0xED, 0x8A, emit_insn, INS_EZ80 },
3543 { "indmr",0xED, 0x9A, emit_insn, INS_EZ80 },
3544 { "indr", 0xED, 0xBA, emit_insn, INS_NOT_GBZ80 },
3545 { "indrx",0xED, 0xCA, emit_insn, INS_EZ80 },
3546 { "ini", 0xED, 0xA2, emit_insn, INS_NOT_GBZ80 },
3547 { "ini2", 0xED, 0x84, emit_insn, INS_EZ80 },
3548 { "ini2r",0xED, 0x94, emit_insn, INS_EZ80 },
3549 { "inim", 0xED, 0x82, emit_insn, INS_EZ80 },
3550 { "inimr",0xED, 0x92, emit_insn, INS_EZ80 },
3551 { "inir", 0xED, 0xB2, emit_insn, INS_NOT_GBZ80 },
3552 { "inirx",0xED, 0xC2, emit_insn, INS_EZ80 },
3553 { "jp", 0xC3, 0xC2, emit_jpcc, INS_ALL },
3554 { "jr", 0x18, 0x20, emit_jrcc, INS_ALL },
3555 { "ld", 0x00, 0x00, emit_ld, INS_ALL },
3556 { "ldd", 0xED, 0xA8, emit_lddldi,INS_ALL }, /* GBZ80 has special meaning */
3557 { "lddr", 0xED, 0xB8, emit_insn, INS_NOT_GBZ80 },
3558 { "lddrx",0xED, 0xBC, emit_insn, INS_Z80N },
3559 { "lddx", 0xED, 0xAC, emit_insn, INS_Z80N },
3560 { "ldh", 0xE0, 0x00, emit_ldh, INS_GBZ80 },
3561 { "ldhl", 0x00, 0xF8, emit_ldhl, INS_GBZ80 },
3562 { "ldi", 0xED, 0xA0, emit_lddldi,INS_ALL }, /* GBZ80 has special meaning */
3563 { "ldir", 0xED, 0xB0, emit_insn, INS_NOT_GBZ80 },
3564 { "ldirx",0xED, 0xB4, emit_insn, INS_Z80N },
3565 { "ldix", 0xED, 0xA4, emit_insn, INS_Z80N },
3566 { "ldpirx",0xED,0xB7, emit_insn, INS_Z80N },
3567 { "ldws", 0xED, 0xA5, emit_insn, INS_Z80N },
3568 { "lea", 0xED, 0x02, emit_lea, INS_EZ80 },
3569 { "mirror",0xED,0x24, emit_insn, INS_Z80N },
3570 { "mlt", 0xED, 0x4C, emit_mlt, INS_Z180|INS_EZ80|INS_Z80N },
3571 { "mul", 0xED, 0x30, emit_mul, INS_Z80N },
3572 { "mulub",0xED, 0xC5, emit_mulub,INS_R800 },
3573 { "muluw",0xED, 0xC3, emit_muluw,INS_R800 },
3574 { "neg", 0xED, 0x44, emit_insn, INS_NOT_GBZ80 },
3575 { "nextreg",0xED,0x91,emit_nextreg,INS_Z80N },
3576 { "nop", 0x00, 0x00, emit_insn, INS_ALL },
3577 { "or", 0x00, 0xB0, emit_s, INS_ALL },
3578 { "otd2r",0xED, 0xBC, emit_insn, INS_EZ80 },
3579 { "otdm", 0xED, 0x8B, emit_insn, INS_Z180|INS_EZ80 },
3580 { "otdmr",0xED, 0x9B, emit_insn, INS_Z180|INS_EZ80 },
3581 { "otdr", 0xED, 0xBB, emit_insn, INS_NOT_GBZ80 },
3582 { "otdrx",0xED, 0xCB, emit_insn, INS_EZ80 },
3583 { "oti2r",0xED, 0xB4, emit_insn, INS_EZ80 },
3584 { "otim", 0xED, 0x83, emit_insn, INS_Z180|INS_EZ80 },
3585 { "otimr",0xED, 0x93, emit_insn, INS_Z180|INS_EZ80 },
3586 { "otir", 0xED, 0xB3, emit_insn, INS_NOT_GBZ80 },
3587 { "otirx",0xED, 0xC3, emit_insn, INS_EZ80 },
3588 { "out", 0x00, 0x00, emit_out, INS_NOT_GBZ80 },
3589 { "out0", 0xED, 0x01, emit_out0, INS_Z180|INS_EZ80 },
3590 { "outd", 0xED, 0xAB, emit_insn, INS_NOT_GBZ80 },
3591 { "outd2",0xED, 0xAC, emit_insn, INS_EZ80 },
3592 { "outi", 0xED, 0xA3, emit_insn, INS_NOT_GBZ80 },
3593 { "outi2",0xED, 0xA4, emit_insn, INS_EZ80 },
3594 { "outinb",0xED,0x90, emit_insn, INS_Z80N },
3595 { "pea", 0xED, 0x65, emit_pea, INS_EZ80 },
3596 { "pixelad",0xED,0x94,emit_insn, INS_Z80N },
3597 { "pixeldn",0xED,0x93,emit_insn, INS_Z80N },
3598 { "pop", 0x00, 0xC1, emit_pop, INS_ALL },
3599 { "push", 0x00, 0xC5, emit_push, INS_ALL },
3600 { "res", 0xCB, 0x80, emit_bit, INS_ALL },
3601 { "ret", 0xC9, 0xC0, emit_retcc,INS_ALL },
3602 { "reti", 0xED, 0x4D, emit_reti, INS_ALL }, /*GBZ80 has its own opcode for it*/
3603 { "retn", 0xED, 0x45, emit_insn, INS_NOT_GBZ80 },
3604 { "rl", 0xCB, 0x10, emit_mr, INS_ALL },
3605 { "rla", 0x00, 0x17, emit_insn, INS_ALL },
3606 { "rlc", 0xCB, 0x00, emit_mr, INS_ALL },
3607 { "rlca", 0x00, 0x07, emit_insn, INS_ALL },
3608 { "rld", 0xED, 0x6F, emit_insn, INS_NOT_GBZ80 },
3609 { "rr", 0xCB, 0x18, emit_mr, INS_ALL },
3610 { "rra", 0x00, 0x1F, emit_insn, INS_ALL },
3611 { "rrc", 0xCB, 0x08, emit_mr, INS_ALL },
3612 { "rrca", 0x00, 0x0F, emit_insn, INS_ALL },
3613 { "rrd", 0xED, 0x67, emit_insn, INS_NOT_GBZ80 },
3614 { "rsmix",0xED, 0x7E, emit_insn, INS_EZ80 },
3615 { "rst", 0x00, 0xC7, emit_rst, INS_ALL },
3616 { "sbc", 0x98, 0x42, emit_adc, INS_ALL },
3617 { "scf", 0x00, 0x37, emit_insn, INS_ALL },
3618 { "set", 0xCB, 0xC0, emit_bit, INS_ALL },
3619 { "setae",0xED, 0x95, emit_insn, INS_Z80N },
3620 { "sl1", 0xCB, 0x30, emit_mr, INS_SLI|INS_Z80N },
3621 { "sla", 0xCB, 0x20, emit_mr, INS_ALL },
3622 { "sli", 0xCB, 0x30, emit_mr, INS_SLI|INS_Z80N },
3623 { "sll", 0xCB, 0x30, emit_mr, INS_SLI|INS_Z80N },
3624 { "slp", 0xED, 0x76, emit_insn, INS_Z180|INS_EZ80 },
3625 { "sra", 0xCB, 0x28, emit_mr, INS_ALL },
3626 { "srl", 0xCB, 0x38, emit_mr, INS_ALL },
3627 { "stmix",0xED, 0x7D, emit_insn, INS_EZ80 },
3628 { "stop", 0x00, 0x10, emit_insn, INS_GBZ80 },
3629 { "sub", 0x00, 0x90, emit_sub, INS_ALL },
3630 { "swap", 0xCB, 0x30, emit_swap, INS_GBZ80|INS_Z80N },
3631 { "swapnib",0xED,0x23,emit_insn, INS_Z80N },
3632 { "test", 0xED, 0x27, emit_insn_n, INS_Z80N },
3633 { "tst", 0xED, 0x04, emit_tst, INS_Z180|INS_EZ80|INS_Z80N },
3634 { "tstio",0xED, 0x74, emit_insn_n,INS_Z180|INS_EZ80 },
3635 { "xor", 0x00, 0xA8, emit_s, INS_ALL },
3636 } ;
3637
3638 void
3639 md_assemble (char *str)
3640 {
3641 const char *p;
3642 char * old_ptr;
3643 int i;
3644 table_t *insp;
3645
3646 err_flag = 0;
3647 inst_mode = cpu_mode ? (INST_MODE_L | INST_MODE_IL) : (INST_MODE_S | INST_MODE_IS);
3648 old_ptr = input_line_pointer;
3649 p = skip_space (str);
3650 for (i = 0; (i < BUFLEN) && (ISALPHA (*p) || ISDIGIT (*p));)
3651 buf[i++] = TOLOWER (*p++);
3652
3653 if (i == BUFLEN)
3654 {
3655 buf[BUFLEN-3] = buf[BUFLEN-2] = '.'; /* Mark opcode as abbreviated. */
3656 buf[BUFLEN-1] = 0;
3657 as_bad (_("Unknown instruction '%s'"), buf);
3658 }
3659 else
3660 {
3661 dwarf2_emit_insn (0);
3662 if ((*p) && (!ISSPACE (*p)))
3663 {
3664 if (*p != '.' || !(ins_ok & INS_EZ80) || !assemble_suffix (&p))
3665 {
3666 as_bad (_("syntax error"));
3667 goto end;
3668 }
3669 }
3670 buf[i] = 0;
3671 p = skip_space (p);
3672 key = buf;
3673
3674 insp = bsearch (&key, instab, ARRAY_SIZE (instab),
3675 sizeof (instab[0]), key_cmp);
3676 if (!insp || (insp->inss && !(insp->inss & ins_ok)))
3677 {
3678 *frag_more (1) = 0;
3679 as_bad (_("Unknown instruction `%s'"), buf);
3680 }
3681 else
3682 {
3683 p = insp->fp (insp->prefix, insp->opcode, p);
3684 p = skip_space (p);
3685 if ((!err_flag) && *p)
3686 as_bad (_("junk at end of line, "
3687 "first unrecognized character is `%c'"), *p);
3688 }
3689 }
3690 end:
3691 input_line_pointer = old_ptr;
3692 }
3693
3694 static int
3695 is_overflow (long value, unsigned bitsize)
3696 {
3697 long fieldmask = (2UL << (bitsize - 1)) - 1;
3698 long signmask = ~fieldmask;
3699 long a = value & fieldmask;
3700 long ss = a & signmask;
3701 if (ss != 0 && ss != (signmask & fieldmask))
3702 return 1;
3703 return 0;
3704 }
3705
3706 void
3707 md_apply_fix (fixS * fixP, valueT* valP, segT seg)
3708 {
3709 long val = *valP;
3710 char *p_lit = fixP->fx_where + fixP->fx_frag->fr_literal;
3711
3712 if (fixP->fx_addsy == NULL)
3713 fixP->fx_done = 1;
3714 else if (fixP->fx_pcrel)
3715 {
3716 segT s = S_GET_SEGMENT (fixP->fx_addsy);
3717 if (s == seg || s == absolute_section)
3718 {
3719 val += S_GET_VALUE (fixP->fx_addsy);
3720 fixP->fx_done = 1;
3721 }
3722 }
3723
3724 switch (fixP->fx_r_type)
3725 {
3726 case BFD_RELOC_8_PCREL:
3727 case BFD_RELOC_Z80_DISP8:
3728 case BFD_RELOC_8:
3729 case BFD_RELOC_16:
3730 case BFD_RELOC_24:
3731 case BFD_RELOC_32:
3732 case BFD_RELOC_Z80_16_BE:
3733 fixP->fx_no_overflow = 0;
3734 break;
3735 default:
3736 fixP->fx_no_overflow = 1;
3737 break;
3738 }
3739
3740 switch (fixP->fx_r_type)
3741 {
3742 case BFD_RELOC_8_PCREL:
3743 case BFD_RELOC_Z80_DISP8:
3744 if (fixP->fx_done && (val < -0x80 || val > 0x7f))
3745 as_bad_where (fixP->fx_file, fixP->fx_line,
3746 _("8-bit signed offset out of range (%+ld)"), val);
3747 *p_lit++ = val;
3748 break;
3749
3750 case BFD_RELOC_Z80_BYTE0:
3751 *p_lit++ = val;
3752 break;
3753
3754 case BFD_RELOC_Z80_BYTE1:
3755 *p_lit++ = (val >> 8);
3756 break;
3757
3758 case BFD_RELOC_Z80_BYTE2:
3759 *p_lit++ = (val >> 16);
3760 break;
3761
3762 case BFD_RELOC_Z80_BYTE3:
3763 *p_lit++ = (val >> 24);
3764 break;
3765
3766 case BFD_RELOC_8:
3767 if (fixP->fx_done && is_overflow(val, 8))
3768 as_warn_where (fixP->fx_file, fixP->fx_line,
3769 _("8-bit overflow (%+ld)"), val);
3770 *p_lit++ = val;
3771 break;
3772
3773 case BFD_RELOC_Z80_WORD1:
3774 *p_lit++ = (val >> 16);
3775 *p_lit++ = (val >> 24);
3776 break;
3777
3778 case BFD_RELOC_Z80_WORD0:
3779 *p_lit++ = val;
3780 *p_lit++ = (val >> 8);
3781 break;
3782
3783 case BFD_RELOC_16:
3784 if (fixP->fx_done && is_overflow(val, 16))
3785 as_warn_where (fixP->fx_file, fixP->fx_line,
3786 _("16-bit overflow (%+ld)"), val);
3787 *p_lit++ = val;
3788 *p_lit++ = (val >> 8);
3789 break;
3790
3791 case BFD_RELOC_24: /* Def24 may produce this. */
3792 if (fixP->fx_done && is_overflow(val, 24))
3793 as_warn_where (fixP->fx_file, fixP->fx_line,
3794 _("24-bit overflow (%+ld)"), val);
3795 *p_lit++ = val;
3796 *p_lit++ = (val >> 8);
3797 *p_lit++ = (val >> 16);
3798 break;
3799
3800 case BFD_RELOC_32: /* Def32 and .long may produce this. */
3801 if (fixP->fx_done && is_overflow(val, 32))
3802 as_warn_where (fixP->fx_file, fixP->fx_line,
3803 _("32-bit overflow (%+ld)"), val);
3804 *p_lit++ = val;
3805 *p_lit++ = (val >> 8);
3806 *p_lit++ = (val >> 16);
3807 *p_lit++ = (val >> 24);
3808 break;
3809
3810 case BFD_RELOC_Z80_16_BE: /* Z80N PUSH nn instruction produce this. */
3811 *p_lit++ = val >> 8;
3812 *p_lit++ = val;
3813 break;
3814
3815 default:
3816 printf (_("md_apply_fix: unknown reloc type 0x%x\n"), fixP->fx_r_type);
3817 abort ();
3818 }
3819 }
3820
3821 /* GAS will call this to generate a reloc. GAS will pass the
3822 resulting reloc to `bfd_install_relocation'. This currently works
3823 poorly, as `bfd_install_relocation' often does the wrong thing, and
3824 instances of `tc_gen_reloc' have been written to work around the
3825 problems, which in turns makes it difficult to fix
3826 `bfd_install_relocation'. */
3827
3828 /* If while processing a fixup, a reloc really
3829 needs to be created then it is done here. */
3830
3831 arelent *
3832 tc_gen_reloc (asection *seg ATTRIBUTE_UNUSED , fixS *fixp)
3833 {
3834 arelent *reloc;
3835
3836 if (fixp->fx_subsy != NULL)
3837 {
3838 as_bad_where (fixp->fx_file, fixp->fx_line, _("expression too complex"));
3839 return NULL;
3840 }
3841
3842 reloc = XNEW (arelent);
3843 reloc->sym_ptr_ptr = XNEW (asymbol *);
3844 *reloc->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy);
3845 reloc->address = fixp->fx_frag->fr_address + fixp->fx_where;
3846 reloc->addend = fixp->fx_offset;
3847 reloc->howto = bfd_reloc_type_lookup (stdoutput, fixp->fx_r_type);
3848 if (reloc->howto == NULL)
3849 {
3850 as_bad_where (fixp->fx_file, fixp->fx_line,
3851 _("reloc %d not supported by object file format"),
3852 (int) fixp->fx_r_type);
3853 return NULL;
3854 }
3855
3856 if (fixp->fx_r_type == BFD_RELOC_VTABLE_INHERIT
3857 || fixp->fx_r_type == BFD_RELOC_VTABLE_ENTRY)
3858 reloc->address = fixp->fx_offset;
3859
3860 return reloc;
3861 }
3862
3863 int
3864 z80_tc_labels_without_colon (void)
3865 {
3866 return colonless_labels;
3867 }
3868
3869 int
3870 z80_tc_label_is_local (const char *name)
3871 {
3872 const char *n;
3873 const char *p;
3874 if (local_label_prefix == NULL)
3875 return 0;
3876 for (p = local_label_prefix, n = name; *p && *n && *n == *p; p++, n++)
3877 ;
3878 return *p == '\0';
3879 }
3880
3881 /* Parse floating point number from string and compute mantissa and
3882 exponent. Mantissa is normalized.
3883 */
3884 #define EXP_MIN -0x10000
3885 #define EXP_MAX 0x10000
3886 static int
3887 str_to_broken_float (bool *signP, bfd_uint64_t *mantissaP, int *expP)
3888 {
3889 char *p;
3890 bool sign;
3891 bfd_uint64_t mantissa = 0;
3892 int exponent = 0;
3893 int i;
3894
3895 p = (char*)skip_space (input_line_pointer);
3896 sign = (*p == '-');
3897 *signP = sign;
3898 if (sign || *p == '+')
3899 ++p;
3900 if (strncasecmp (p, "NaN", 3) == 0)
3901 {
3902 *mantissaP = 0;
3903 *expP = 0;
3904 input_line_pointer = p + 3;
3905 return 1;
3906 }
3907 if (strncasecmp (p, "inf", 3) == 0)
3908 {
3909 *mantissaP = 1ull << 63;
3910 *expP = EXP_MAX;
3911 input_line_pointer = p + 3;
3912 return 1;
3913 }
3914 for (; ISDIGIT (*p); ++p)
3915 {
3916 if (mantissa >> 60)
3917 {
3918 if (*p >= '5')
3919 mantissa++;
3920 break;
3921 }
3922 mantissa = mantissa * 10 + (*p - '0');
3923 }
3924 /* skip non-significant digits */
3925 for (; ISDIGIT (*p); ++p)
3926 exponent++;
3927
3928 if (*p == '.')
3929 {
3930 p++;
3931 if (!exponent) /* If no precision overflow. */
3932 {
3933 for (; ISDIGIT (*p); ++p, --exponent)
3934 {
3935 if (mantissa >> 60)
3936 {
3937 if (*p >= '5')
3938 mantissa++;
3939 break;
3940 }
3941 mantissa = mantissa * 10 + (*p - '0');
3942 }
3943 }
3944 for (; ISDIGIT (*p); ++p)
3945 ;
3946 }
3947 if (*p == 'e' || *p == 'E')
3948 {
3949 int es;
3950 int t = 0;
3951 ++p;
3952 es = (*p == '-');
3953 if (es || *p == '+')
3954 p++;
3955 for (; ISDIGIT (*p); ++p)
3956 {
3957 if (t < 100)
3958 t = t * 10 + (*p - '0');
3959 }
3960 exponent += (es) ? -t : t;
3961 }
3962 if (ISALNUM (*p) || *p == '.')
3963 return 0;
3964 input_line_pointer = p;
3965 if (mantissa == 0)
3966 {
3967 *mantissaP = 1ull << 63;
3968 *expP = EXP_MIN;
3969 return 1; /* result is 0 */
3970 }
3971 /* normalization */
3972 for (; mantissa <= ~0ull/10; --exponent)
3973 mantissa *= 10;
3974 /* Now we have sign, mantissa, and signed decimal exponent
3975 need to recompute to binary exponent. */
3976 for (i = 64; exponent > 0; --exponent)
3977 {
3978 /* be sure that no integer overflow */
3979 while (mantissa > ~0ull/10)
3980 {
3981 mantissa >>= 1;
3982 i += 1;
3983 }
3984 mantissa *= 10;
3985 }
3986 for (; exponent < 0; ++exponent)
3987 {
3988 while (!(mantissa >> 63))
3989 {
3990 mantissa <<= 1;
3991 i -= 1;
3992 }
3993 mantissa /= 10;
3994 }
3995 /* normalization */
3996 for (; !(mantissa >> 63); --i)
3997 mantissa <<= 1;
3998 *mantissaP = mantissa;
3999 *expP = i;
4000 return 1;
4001 }
4002
4003 static const char *
4004 str_to_zeda32(char *litP, int *sizeP)
4005 {
4006 bfd_uint64_t mantissa;
4007 bool sign;
4008 int exponent;
4009 unsigned i;
4010
4011 *sizeP = 4;
4012 if (!str_to_broken_float (&sign, &mantissa, &exponent))
4013 return _("invalid syntax");
4014 /* I do not know why decrement is needed */
4015 --exponent;
4016 /* shift by 39 bits right keeping 25 bit mantissa for rounding */
4017 mantissa >>= 39;
4018 /* do rounding */
4019 ++mantissa;
4020 /* make 24 bit mantissa */
4021 mantissa >>= 1;
4022 /* check for overflow */
4023 if (mantissa >> 24)
4024 {
4025 mantissa >>= 1;
4026 ++exponent;
4027 }
4028 /* check for 0 */
4029 if (exponent < -127)
4030 {
4031 exponent = -128;
4032 mantissa = 0;
4033 }
4034 else if (exponent > 127)
4035 {
4036 exponent = -128;
4037 mantissa = sign ? 0xc00000 : 0x400000;
4038 }
4039 else if (mantissa == 0)
4040 {
4041 exponent = -128;
4042 mantissa = 0x200000;
4043 }
4044 else if (!sign)
4045 mantissa &= (1ull << 23) - 1;
4046 for (i = 0; i < 24; i += 8)
4047 *litP++ = (char)(mantissa >> i);
4048 *litP = (char)(0x80 + exponent);
4049 return NULL;
4050 }
4051
4052 /*
4053 Math48 by Anders Hejlsberg support.
4054 Mantissa is 39 bits wide, exponent 8 bit wide.
4055 Format is:
4056 bit 47: sign
4057 bit 46-8: normalized mantissa (bits 38-0, bit39 assumed to be 1)
4058 bit 7-0: exponent+128 (0 - value is null)
4059 MIN: 2.938735877e-39
4060 MAX: 1.701411835e+38
4061 */
4062 static const char *
4063 str_to_float48(char *litP, int *sizeP)
4064 {
4065 bfd_uint64_t mantissa;
4066 bool sign;
4067 int exponent;
4068 unsigned i;
4069
4070 *sizeP = 6;
4071 if (!str_to_broken_float (&sign, &mantissa, &exponent))
4072 return _("invalid syntax");
4073 /* shift by 23 bits right keeping 41 bit mantissa for rounding */
4074 mantissa >>= 23;
4075 /* do rounding */
4076 ++mantissa;
4077 /* make 40 bit mantissa */
4078 mantissa >>= 1;
4079 /* check for overflow */
4080 if (mantissa >> 40)
4081 {
4082 mantissa >>= 1;
4083 ++exponent;
4084 }
4085 if (exponent < -127)
4086 {
4087 memset (litP, 0, 6);
4088 return NULL;
4089 }
4090 if (exponent > 127)
4091 return _("overflow");
4092 if (!sign)
4093 mantissa &= (1ull << 39) - 1;
4094 *litP++ = (char)(0x80 + exponent);
4095 for (i = 0; i < 40; i += 8)
4096 *litP++ = (char)(mantissa >> i);
4097 return NULL;
4098 }
4099
4100 static const char *
4101 str_to_ieee754_h(char *litP, int *sizeP)
4102 {
4103 return ieee_md_atof ('h', litP, sizeP, false);
4104 }
4105
4106 static const char *
4107 str_to_ieee754_s(char *litP, int *sizeP)
4108 {
4109 return ieee_md_atof ('s', litP, sizeP, false);
4110 }
4111
4112 static const char *
4113 str_to_ieee754_d(char *litP, int *sizeP)
4114 {
4115 return ieee_md_atof ('d', litP, sizeP, false);
4116 }
4117
4118 #ifdef TARGET_USE_CFIPOP
4119 /* Initialize the DWARF-2 unwind information for this procedure. */
4120 void
4121 z80_tc_frame_initial_instructions (void)
4122 {
4123 static int sp_regno = -1;
4124
4125 if (sp_regno < 0)
4126 sp_regno = z80_tc_regname_to_dw2regnum ("sp");
4127
4128 cfi_add_CFA_def_cfa (sp_regno, 0);
4129 }
4130
4131 int
4132 z80_tc_regname_to_dw2regnum (const char *regname)
4133 {
4134 static const char *regs[] =
4135 { /* same registers as for GDB */
4136 "af", "bc", "de", "hl",
4137 "sp", "pc", "ix", "iy",
4138 "af_", "bc_", "de_", "hl_",
4139 "ir"
4140 };
4141 unsigned i;
4142
4143 for (i = 0; i < ARRAY_SIZE(regs); ++i)
4144 if (!strcasecmp (regs[i], regname))
4145 return i;
4146
4147 return -1;
4148 }
4149 #endif
4150
4151 /* Implement DWARF2_ADDR_SIZE. */
4152 int
4153 z80_dwarf2_addr_size (const bfd *abfd)
4154 {
4155 switch (bfd_get_mach (abfd))
4156 {
4157 case bfd_mach_ez80_adl:
4158 return 3;
4159 default:
4160 return 2;
4161 }
4162 }