1 /* tc-maxq.c -- assembler code for a MAXQ chip. 2 3 Copyright 2004, 2005 Free Software Foundation, Inc. 4 5 Contributed by HCL Technologies Pvt. Ltd. 6 7 Author: Vineet Sharma(vineets@noida.hcltech.com) Inderpreet 8 S.(inderpreetb@noida.hcltech.com) 9 10 This file is part of GAS. 11 12 GAS is free software; you can redistribute it and/or modify it under the 13 terms of the GNU General Public License as published by the Free Software 14 Foundation; either version 2, or (at your option) any later version. 15 16 GAS is distributed in the hope that it will be useful, but WITHOUT ANY 17 WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS 18 FOR A PARTICULAR PURPOSE. See the GNU General Public License for more 19 details. 20 21 You should have received a copy of the GNU General Public License along 22 with GAS; see the file COPYING. If not, write to the Free Software 23 Foundation, 51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA. */ 24 25 #include "as.h" 26 #include "safe-ctype.h" 27 #include "subsegs.h" 28 #include "dwarf2dbg.h" 29 #include "tc-maxq.h" 30 #include "opcode/maxq.h" 31 #include "ctype.h" 32 33 #ifndef MAXQ10S 34 #define MAXQ10S 1 35 #endif 36 37 #ifndef _STRING_H 38 #include "string.h" 39 #endif 40 41 #ifndef DEFAULT_ARCH 42 #define DEFAULT_ARCH "MAXQ20" 43 #endif 44 45 #ifndef MAX_OPERANDS 46 #define MAX_OPERANDS 2 47 #endif 48 49 #ifndef MAX_MNEM_SIZE 50 #define MAX_MNEM_SIZE 8 51 #endif 52 53 #ifndef END_OF_INSN 54 #define END_OF_INSN '\0' 55 #endif 56 57 #ifndef IMMEDIATE_PREFIX 58 #define IMMEDIATE_PREFIX '#' 59 #endif 60 61 #ifndef MAX_REG_NAME_SIZE 62 #define MAX_REG_NAME_SIZE 4 63 #endif 64 65 #ifndef MAX_MEM_NAME_SIZE 66 #define MAX_MEM_NAME_SIZE 9 67 #endif 68 69 /* opcode for PFX[0]. */ 70 #define PFX0 0x0b 71 72 /* Set default to MAXQ20. */ 73 unsigned int max_version = bfd_mach_maxq20; 74 75 const char *default_arch = DEFAULT_ARCH; 76 77 /* Type of the operand: Register,Immediate,Memory access,flag or bit. */ 78 79 union _maxq20_op 80 { 81 const reg_entry * reg; 82 char imms; /* This is to store the immediate value operand. */ 83 expressionS * disps; 84 symbolS * data; 85 const mem_access * mem; 86 int flag; 87 const reg_bit * r_bit; 88 }; 89 90 typedef union _maxq20_op maxq20_opcode; 91 92 /* For handling optional L/S in Maxq20. */ 93 94 /* Exposed For Linker - maps indirectly to the liker relocations. */ 95 #define LONG_PREFIX MAXQ_LONGJUMP /* BFD_RELOC_16 */ 96 #define SHORT_PREFIX MAXQ_SHORTJUMP /* BFD_RELOC_16_PCREL_S2 */ 97 #define ABSOLUTE_ADDR_FOR_DATA MAXQ_INTERSEGMENT 98 99 #define NO_PREFIX 0 100 #define EXPLICT_LONG_PREFIX 14 101 102 /* The main instruction structure containing fields to describe instrn */ 103 typedef struct _maxq20_insn 104 { 105 /* The opcode information for the MAXQ20 */ 106 MAXQ20_OPCODE_INFO op; 107 108 /* The number of operands */ 109 unsigned int operands; 110 111 /* Number of different types of operands - Comments can be removed if reqd. 112 */ 113 unsigned int reg_operands, mem_operands, disp_operands, data_operands; 114 unsigned int imm_operands, imm_bit_operands, bit_operands, flag_operands; 115 116 /* Types of the individual operands */ 117 UNKNOWN_OP types[MAX_OPERANDS]; 118 119 /* Relocation type for operand : to be investigated into */ 120 int reloc[MAX_OPERANDS]; 121 122 /* Complete information of the Operands */ 123 maxq20_opcode maxq20_op[MAX_OPERANDS]; 124 125 /* Choice of prefix register whenever needed */ 126 int prefix; 127 128 /* Optional Prefix for Instructions like LJUMP, SJUMP etc */ 129 unsigned char Instr_Prefix; 130 131 /* 16 bit Instruction word */ 132 unsigned char instr[2]; 133 } 134 maxq20_insn; 135 136 /* Definitions of all possible characters that can start an operand. */ 137 const char *extra_symbol_chars = "@(#"; 138 139 /* Special Character that would start a comment. */ 140 const char comment_chars[] = ";"; 141 142 /* Starts a comment when it appears at the start of a line. */ 143 const char line_comment_chars[] = ";#"; 144 145 const char line_separator_chars[] = ""; /* originally may b by sudeep "\n". */ 146 147 /* The following are used for option processing. */ 148 149 /* This is added to the mach independent string passed to getopt. */ 150 const char *md_shortopts = "q"; 151 152 /* Characters for exponent and floating point. */ 153 const char EXP_CHARS[] = "eE"; 154 const char FLT_CHARS[] = ""; 155 156 /* This is for the machine dependent option handling. */ 157 #define OPTION_EB (OPTION_MD_BASE + 0) 158 #define OPTION_EL (OPTION_MD_BASE + 1) 159 #define MAXQ_10 (OPTION_MD_BASE + 2) 160 #define MAXQ_20 (OPTION_MD_BASE + 3) 161 162 struct option md_longopts[] = 163 { 164 {"MAXQ10", no_argument, NULL, MAXQ_10}, 165 {"MAXQ20", no_argument, NULL, MAXQ_20}, 166 {NULL, no_argument, NULL, 0} 167 }; 168 size_t md_longopts_size = sizeof (md_longopts); 169 170 /* md_undefined_symbol We have no need for this function. */ 171 172 symbolS * 173 md_undefined_symbol (char * name ATTRIBUTE_UNUSED) 174 { 175 return NULL; 176 } 177 178 static void 179 maxq_target (int target) 180 { 181 max_version = target; 182 bfd_set_arch_mach (stdoutput, bfd_arch_maxq, max_version); 183 } 184 185 int 186 md_parse_option (int c, char *arg ATTRIBUTE_UNUSED) 187 { 188 /* Any options support will be added onto this switch case. */ 189 switch (c) 190 { 191 case MAXQ_10: 192 max_version = bfd_mach_maxq10; 193 break; 194 case MAXQ_20: 195 max_version = bfd_mach_maxq20; 196 break; 197 198 default: 199 return 0; 200 } 201 202 return 1; 203 } 204 205 /* When a usage message is printed, this function is called and 206 it prints a description of the machine specific options. */ 207 208 void 209 md_show_usage (FILE * stream) 210 { 211 /* Over here we will fill the description of the machine specific options. */ 212 213 fprintf (stream, _(" MAXQ-specific assembler options:\n")); 214 215 fprintf (stream, _("\ 216 -MAXQ20 generate obj for MAXQ20(default)\n\ 217 -MAXQ10 generate obj for MAXQ10\n\ 218 ")); 219 } 220 221 unsigned long 222 maxq20_mach (void) 223 { 224 if (!(strcmp (default_arch, "MAXQ20"))) 225 return 0; 226 227 as_fatal (_("Unknown architecture")); 228 return 1; 229 } 230 231 arelent * 232 tc_gen_reloc (asection *section ATTRIBUTE_UNUSED, fixS *fixp) 233 { 234 arelent *rel; 235 bfd_reloc_code_real_type code; 236 237 switch (fixp->fx_r_type) 238 { 239 case MAXQ_INTERSEGMENT: 240 case MAXQ_LONGJUMP: 241 case BFD_RELOC_16_PCREL_S2: 242 code = fixp->fx_r_type; 243 break; 244 245 case 0: 246 default: 247 switch (fixp->fx_size) 248 { 249 default: 250 as_bad_where (fixp->fx_file, fixp->fx_line, 251 _("can not do %d byte relocation"), fixp->fx_size); 252 code = BFD_RELOC_32; 253 break; 254 255 case 1: 256 code = BFD_RELOC_8; 257 break; 258 case 2: 259 code = BFD_RELOC_16; 260 break; 261 case 4: 262 code = BFD_RELOC_32; 263 break; 264 } 265 } 266 267 rel = xmalloc (sizeof (arelent)); 268 rel->sym_ptr_ptr = xmalloc (sizeof (asymbol *)); 269 *rel->sym_ptr_ptr = symbol_get_bfdsym (fixp->fx_addsy); 270 271 rel->address = fixp->fx_frag->fr_address + fixp->fx_where; 272 rel->addend = fixp->fx_addnumber; 273 rel->howto = bfd_reloc_type_lookup (stdoutput, code); 274 275 if (rel->howto == NULL) 276 { 277 as_bad_where (fixp->fx_file, fixp->fx_line, 278 _("cannot represent relocation type %s"), 279 bfd_get_reloc_code_name (code)); 280 281 /* Set howto to a garbage value so that we can keep going. */ 282 rel->howto = bfd_reloc_type_lookup (stdoutput, BFD_RELOC_32); 283 assert (rel->howto != NULL); 284 } 285 286 return rel; 287 } 288 289 /* md_estimate_size_before_relax() 290 291 Called just before relax() for rs_machine_dependent frags. The MAXQ 292 assembler uses these frags to handle 16 bit absolute jumps which require a 293 prefix instruction to be inserted. Any symbol that is now undefined will 294 not become defined. Return the correct fr_subtype in the frag. Return the 295 initial "guess for variable size of frag"(This will be eiter 2 or 0) to 296 caller. The guess is actually the growth beyond the fixed part. Whatever 297 we do to grow the fixed or variable part contributes to our returned 298 value. */ 299 300 int 301 md_estimate_size_before_relax (fragS *fragP, segT segment) 302 { 303 /* Check whether the symbol has been resolved or not. 304 Otherwise we will have to generate a fixup. */ 305 if ((S_GET_SEGMENT (fragP->fr_symbol) != segment) 306 || fragP->fr_subtype == EXPLICT_LONG_PREFIX) 307 { 308 RELOC_ENUM reloc_type; 309 unsigned char *opcode; 310 int old_fr_fix; 311 312 /* Now this symbol has not been defined in this file. 313 Hence we will have to create a fixup. */ 314 int size = 2; 315 316 /* This is for the prefix instruction. */ 317 318 if (fragP->fr_subtype == EXPLICT_LONG_PREFIX) 319 fragP->fr_subtype = LONG_PREFIX; 320 321 if (S_GET_SEGMENT (fragP->fr_symbol) != segment 322 && ((!(fragP->fr_subtype) == EXPLICT_LONG_PREFIX))) 323 fragP->fr_subtype = ABSOLUTE_ADDR_FOR_DATA; 324 325 reloc_type = 326 (fragP->fr_subtype ? fragP->fr_subtype : ABSOLUTE_ADDR_FOR_DATA); 327 328 fragP->fr_subtype = reloc_type; 329 330 if (reloc_type == SHORT_PREFIX) 331 size = 0; 332 old_fr_fix = fragP->fr_fix; 333 opcode = (unsigned char *) fragP->fr_opcode; 334 335 fragP->fr_fix += (size); 336 337 fix_new (fragP, old_fr_fix - 2, size + 2, 338 fragP->fr_symbol, fragP->fr_offset, 0, reloc_type); 339 frag_wane (fragP); 340 return fragP->fr_fix - old_fr_fix; 341 } 342 343 if (fragP->fr_subtype == SHORT_PREFIX) 344 { 345 fragP->fr_subtype = SHORT_PREFIX; 346 return 0; 347 } 348 349 if (fragP->fr_subtype == NO_PREFIX || fragP->fr_subtype == LONG_PREFIX) 350 { 351 unsigned long instr; 352 unsigned long call_addr; 353 long diff; 354 fragS *f; 355 diff = diff ^ diff;; 356 call_addr = call_addr ^ call_addr; 357 instr = 0; 358 f = NULL; 359 360 /* segment_info_type *seginfo = seg_info (segment); */ 361 instr = fragP->fr_address + fragP->fr_fix - 2; 362 363 /* This is the offset if it is a PC relative jump. */ 364 call_addr = S_GET_VALUE (fragP->fr_symbol) + fragP->fr_offset; 365 366 /* PC stores the value of the next instruction. */ 367 diff = (call_addr - instr) - 1; 368 369 if (diff >= (-128 * 2) && diff <= (2 * 127)) 370 { 371 /* Now as offset is an 8 bit value, we will pass 372 that to the jump instruction directly. */ 373 fragP->fr_subtype = NO_PREFIX; 374 return 0; 375 } 376 377 fragP->fr_subtype = LONG_PREFIX; 378 return 2; 379 } 380 381 as_fatal (_("Illegal Reloc type in md_estimate_size_before_relax for line : %d"), 382 frag_now->fr_line); 383 return 0; 384 } 385 386 /* Equal to MAX_PRECISION in atof-ieee.c */ 387 #define MAX_LITTLENUMS 6 388 389 /* Turn a string in input_line_pointer into a floating point constant of type 390 TYPE, and store the appropriate bytes in *LITP. The number of LITTLENUMS 391 emitted is stored in *SIZEP. An error message is returned, or NULL on OK. */ 392 393 char * 394 md_atof (int type, char * litP, int * sizeP) 395 { 396 int prec; 397 LITTLENUM_TYPE words[4]; 398 char *t; 399 int i; 400 401 switch (type) 402 { 403 case 'f': 404 prec = 2; 405 break; 406 407 case 'd': 408 prec = 2; 409 /* The size of Double has been changed to 2 words ie 32 bits. */ 410 /* prec = 4; */ 411 break; 412 413 default: 414 *sizeP = 0; 415 return _("bad call to md_atof"); 416 } 417 418 t = atof_ieee (input_line_pointer, type, words); 419 if (t) 420 input_line_pointer = t; 421 422 *sizeP = prec * 2; 423 424 for (i = prec - 1; i >= 0; i--) 425 { 426 md_number_to_chars (litP, (valueT) words[i], 2); 427 litP += 2; 428 } 429 430 return NULL; 431 } 432 433 void 434 maxq20_cons_fix_new (fragS * frag, unsigned int off, unsigned int len, 435 expressionS * exp) 436 { 437 int r = 0; 438 439 switch (len) 440 { 441 case 2: 442 r = MAXQ_WORDDATA; /* Word+n */ 443 break; 444 case 4: 445 r = MAXQ_LONGDATA; /* Long+n */ 446 break; 447 } 448 449 fix_new_exp (frag, off, len, exp, 0, r); 450 return; 451 } 452 453 /* GAS will call this for every rs_machine_dependent fragment. The 454 instruction is compleated using the data from the relaxation pass. It may 455 also create any necessary relocations. */ 456 void 457 md_convert_frag (bfd * headers ATTRIBUTE_UNUSED, 458 segT seg ATTRIBUTE_UNUSED, 459 fragS * fragP) 460 { 461 char *opcode; 462 offsetT target_address; 463 offsetT opcode_address; 464 offsetT displacement_from_opcode_start; 465 int address; 466 467 opcode = fragP->fr_opcode; 468 address = 0; 469 target_address = opcode_address = displacement_from_opcode_start = 0; 470 471 target_address = 472 (S_GET_VALUE (fragP->fr_symbol) / MAXQ_OCTETS_PER_BYTE) + 473 (fragP->fr_offset / MAXQ_OCTETS_PER_BYTE); 474 475 opcode_address = 476 (fragP->fr_address / MAXQ_OCTETS_PER_BYTE) + 477 ((fragP->fr_fix - 2) / MAXQ_OCTETS_PER_BYTE); 478 479 /* PC points to the next Instruction. */ 480 displacement_from_opcode_start = ((target_address - opcode_address) - 1); 481 482 if ((displacement_from_opcode_start >= -128 483 && displacement_from_opcode_start <= 127) 484 && (fragP->fr_subtype == SHORT_PREFIX 485 || fragP->fr_subtype == NO_PREFIX)) 486 { 487 /* Its a displacement. */ 488 *opcode = (char) displacement_from_opcode_start; 489 } 490 else 491 { 492 /* Its an absolute 16 bit jump. Now we have to 493 load the prefix operator with the upper 8 bits. */ 494 if (fragP->fr_subtype == SHORT_PREFIX) 495 { 496 as_bad (_("Cant make long jump/call into short jump/call : %d"), 497 fragP->fr_line); 498 return; 499 } 500 501 /* Check whether the symbol has been resolved or not. 502 Otherwise we will have to generate a fixup. */ 503 504 if (fragP->fr_subtype != SHORT_PREFIX) 505 { 506 RELOC_ENUM reloc_type; 507 int old_fr_fix; 508 int size = 2; 509 510 /* Now this is a basolute jump/call. 511 Hence we will have to create a fixup. */ 512 if (fragP->fr_subtype == NO_PREFIX) 513 fragP->fr_subtype = LONG_PREFIX; 514 515 reloc_type = 516 (fragP->fr_subtype ? fragP->fr_subtype : LONG_PREFIX); 517 518 if (reloc_type == 1) 519 size = 0; 520 old_fr_fix = fragP->fr_fix; 521 522 fragP->fr_fix += (size); 523 524 fix_new (fragP, old_fr_fix - 2, size + 2, 525 fragP->fr_symbol, fragP->fr_offset, 0, reloc_type); 526 frag_wane (fragP); 527 } 528 } 529 } 530 531 long 532 md_pcrel_from (fixS *fixP) 533 { 534 return fixP->fx_size + fixP->fx_where + fixP->fx_frag->fr_address; 535 } 536 537 /* Writes the val to the buf, where n is the nuumber of bytes to write. */ 538 539 void 540 maxq_number_to_chars (char *buf, valueT val, int n) 541 { 542 if (target_big_endian) 543 number_to_chars_bigendian (buf, val, n); 544 else 545 number_to_chars_littleendian (buf, val, n); 546 } 547 548 /* GAS will call this for each fixup. It's main objective is to store the 549 correct value in the object file. 'fixup_segment' performs the generic 550 overflow check on the 'valueT *val' argument after md_apply_fix returns. 551 If the overflow check is relevant for the target machine, then 552 'md_apply_fix' should modify 'valueT *val', typically to the value stored 553 in the object file (not to be done in MAXQ). */ 554 555 void 556 md_apply_fix (fixS *fixP, valueT *valT, segT seg ATTRIBUTE_UNUSED) 557 { 558 char *p = fixP->fx_frag->fr_literal + fixP->fx_where; 559 char *frag_to_fix_at = 560 fixP->fx_frag->fr_literal + fixP->fx_frag->fr_fix - 2; 561 562 if (fixP) 563 { 564 if (fixP->fx_frag && valT) 565 { 566 /* If the relaxation substate is not defined we make it equal 567 to the kind of relocation the fixup is generated for. */ 568 if (!fixP->fx_frag->fr_subtype) 569 fixP->fx_frag->fr_subtype = fixP->fx_r_type; 570 571 /* For any instruction in which either we have specified an 572 absolute address or it is a long jump we need to add a PFX0 573 instruction to it. In this case as the instruction has already 574 being written at 'fx_where' in the frag we copy it at the end of 575 the frag(which is where the relocation was generated) as when 576 the relocation is generated the frag is grown by 2 type, this is 577 where we copy the contents of fx_where and add a pfx0 at 578 fx_where. */ 579 if ((fixP->fx_frag->fr_subtype == ABSOLUTE_ADDR_FOR_DATA) 580 || (fixP->fx_frag->fr_subtype == LONG_PREFIX)) 581 { 582 *(frag_to_fix_at + 1) = *(p + 1); 583 maxq_number_to_chars (p + 1, PFX0, 1); 584 } 585 586 /* Remember value for tc_gen_reloc. */ 587 fixP->fx_addnumber = *valT; 588 } 589 590 /* Some fixups generated by GAS which gets resovled before this this 591 func. is called need to be wriiten to the frag as here we are going 592 to go away with the relocations fx_done=1. */ 593 if (fixP->fx_addsy == NULL) 594 { 595 maxq_number_to_chars (p, *valT, fixP->fx_size); 596 fixP->fx_addnumber = *valT; 597 fixP->fx_done = 1; 598 } 599 } 600 } 601 602 /* Tables for lexical analysis. */ 603 static char mnemonic_chars[256]; 604 static char register_chars[256]; 605 static char operand_chars[256]; 606 static char identifier_chars[256]; 607 static char digit_chars[256]; 608 609 /* Lexical Macros. */ 610 #define is_mnemonic_char(x) (mnemonic_chars[(unsigned char)(x)]) 611 #define is_register_char(x) (register_chars[(unsigned char)(x)]) 612 #define is_operand_char(x) (operand_chars[(unsigned char)(x)]) 613 #define is_space_char(x) (x==' ') 614 #define is_identifier_char(x) (identifier_chars[(unsigned char)(x)]) 615 #define is_digit_char(x) (identifier_chars[(unsigned char)(x)]) 616 617 /* Special characters for operands. */ 618 static char operand_special_chars[] = "[]@.-+"; 619 620 /* md_assemble() will always leave the instruction passed to it unaltered. 621 To do this we store the instruction in a special stack. */ 622 static char save_stack[32]; 623 static char *save_stack_p; 624 625 #define END_STRING_AND_SAVE(s) \ 626 do \ 627 { \ 628 *save_stack_p++ = *(s); \ 629 *s = '\0'; \ 630 } \ 631 while (0) 632 633 #define RESTORE_END_STRING(s) \ 634 do \ 635 { \ 636 *(s) = *(--save_stack_p); \ 637 } \ 638 while (0) 639 640 /* The instruction we are assembling. */ 641 static maxq20_insn i; 642 643 /* The current template. */ 644 static MAXQ20_OPCODES *current_templates; 645 646 /* The displacement operand if any. */ 647 static expressionS disp_expressions; 648 649 /* Current Operand we are working on (0:1st operand,1:2nd operand). */ 650 static int this_operand; 651 652 /* The prefix instruction if used. */ 653 static char PFX_INSN[2]; 654 static char INSERT_BUFFER[2]; 655 656 /* For interface with expression() ????? */ 657 extern char *input_line_pointer; 658 659 /* The HASH Tables: */ 660 661 /* Operand Hash Table. */ 662 static struct hash_control *op_hash; 663 664 /* Register Hash Table. */ 665 static struct hash_control *reg_hash; 666 667 /* Memory reference Hash Table. */ 668 static struct hash_control *mem_hash; 669 670 /* Bit hash table. */ 671 static struct hash_control *bit_hash; 672 673 /* Memory Access syntax table. */ 674 static struct hash_control *mem_syntax_hash; 675 676 /* This is a mapping from pseudo-op names to functions. */ 677 678 const pseudo_typeS md_pseudo_table[] = 679 { 680 {"int", cons, 2}, /* size of 'int' has been changed to 1 word 681 (i.e) 16 bits. */ 682 {"maxq10", maxq_target, bfd_mach_maxq10}, 683 {"maxq20", maxq_target, bfd_mach_maxq20}, 684 {NULL, 0, 0}, 685 }; 686 687 #define SET_PFX_ARG(x) (PFX_INSN[1] = x) 688 689 690 /* This function sets the PFX value coresponding to the specs. Source 691 Destination Index Selection ---------------------------------- Write To| 692 SourceRegRange | Dest Addr Range 693 ------------------------------------------------------ PFX[0] | 0h-Fh | 694 0h-7h PFX[1] | 10h-1Fh | 0h-7h PFX[2] | 0h-Fh | 8h-Fh PFX[3] | 10h-1Fh | 695 8h-Fh PFX[4] | 0h-Fh | 10h-17h PFX[5] | 10h-1Fh | 10h-17h PFX[6] | 0h-Fh | 696 18h-1Fh PFX[7] | 0h-Fh | 18h-1Fh */ 697 698 static void 699 set_prefix (void) 700 { 701 short int src_index = 0, dst_index = 0; 702 703 if (i.operands == 0) 704 return; 705 if (i.operands == 1) /* Only SRC is Present */ 706 { 707 if (i.types[0] == REG) 708 { 709 if (!strcmp (i.op.name, "POP") || !strcmp (i.op.name, "POPI")) 710 { 711 dst_index = i.maxq20_op[0].reg[0].Mod_index; 712 src_index = 0x00; 713 } 714 else 715 { 716 src_index = i.maxq20_op[0].reg[0].Mod_index; 717 dst_index = 0x00; 718 } 719 } 720 } 721 722 if (i.operands == 2) 723 { 724 if (i.types[0] == REG && i.types[1] == REG) 725 { 726 dst_index = i.maxq20_op[0].reg[0].Mod_index; 727 src_index = i.maxq20_op[1].reg[0].Mod_index; 728 } 729 else if (i.types[0] != REG && i.types[1] == REG) /* DST is Absent */ 730 { 731 src_index = i.maxq20_op[1].reg[0].Mod_index; 732 dst_index = 0x00; 733 } 734 else if (i.types[0] == REG && i.types[1] != REG) /* Id SRC is Absent */ 735 { 736 dst_index = i.maxq20_op[0].reg[0].Mod_index; 737 src_index = 0x00; 738 } 739 else if (i.types[0] == BIT && i.maxq20_op[0].r_bit) 740 { 741 dst_index = i.maxq20_op[0].r_bit->reg->Mod_index; 742 src_index = 0x00; 743 } 744 745 else if (i.types[1] == BIT && i.maxq20_op[1].r_bit) 746 { 747 dst_index = 0x00; 748 src_index = i.maxq20_op[1].r_bit->reg->Mod_index; 749 } 750 } 751 752 if (src_index >= 0x00 && src_index <= 0xF) 753 { 754 if (dst_index >= 0x00 && dst_index <= 0x07) 755 /* Set PFX[0] */ 756 i.prefix = 0; 757 758 else if (dst_index >= 0x08 && dst_index <= 0x0F) 759 /* Set PFX[2] */ 760 i.prefix = 2; 761 762 else if (dst_index >= 0x10 && dst_index <= 0x17) 763 /* Set PFX[4] */ 764 i.prefix = 4; 765 766 else if (dst_index >= 0x18 && dst_index <= 0x1F) 767 /* Set PFX[6] */ 768 i.prefix = 6; 769 } 770 else if (src_index >= 0x10 && src_index <= 0x1F) 771 { 772 if (dst_index >= 0x00 && dst_index <= 0x07) 773 /* Set PFX[1] */ 774 i.prefix = 1; 775 776 else if (dst_index >= 0x08 && dst_index <= 0x0F) 777 /* Set PFX[3] */ 778 i.prefix = 3; 779 780 else if (dst_index >= 0x10 && dst_index <= 0x17) 781 /* Set PFX[5] */ 782 i.prefix = 5; 783 784 else if (dst_index >= 0x18 && dst_index <= 0x1F) 785 /* Set PFX[7] */ 786 i.prefix = 7; 787 } 788 } 789 790 static unsigned char 791 is_a_LSinstr (const char *ln_pointer) 792 { 793 int i = 0; 794 795 for (i = 0; LSInstr[i] != NULL; i++) 796 if (!strcmp (LSInstr[i], ln_pointer)) 797 return 1; 798 799 return 0; 800 } 801 802 static void 803 LS_processing (const char *line) 804 { 805 if (is_a_LSinstr (line)) 806 { 807 if ((line[0] == 'L') || (line[0] == 'l')) 808 { 809 i.prefix = 0; 810 INSERT_BUFFER[0] = PFX0; 811 i.Instr_Prefix = LONG_PREFIX; 812 } 813 else if ((line[0] == 'S') || (line[0] == 's')) 814 i.Instr_Prefix = SHORT_PREFIX; 815 else 816 i.Instr_Prefix = NO_PREFIX; 817 } 818 else 819 i.Instr_Prefix = LONG_PREFIX; 820 } 821 822 /* Separate mnemonics and the operands. */ 823 824 static char * 825 parse_insn (char *line, char *mnemonic) 826 { 827 char *l = line; 828 char *token_start = l; 829 char *mnem_p; 830 char temp[MAX_MNEM_SIZE]; 831 int ii = 0; 832 833 memset (temp, END_OF_INSN, MAX_MNEM_SIZE); 834 mnem_p = mnemonic; 835 836 while ((*mnem_p = mnemonic_chars[(unsigned char) *l]) != 0) 837 { 838 ii++; 839 mnem_p++; 840 if (mnem_p >= mnemonic + MAX_MNEM_SIZE) 841 { 842 as_bad (_("no such instruction: `%s'"), token_start); 843 return NULL; 844 } 845 l++; 846 } 847 848 if (!is_space_char (*l) && *l != END_OF_INSN) 849 { 850 as_bad (_("invalid character %s in mnemonic"), l); 851 return NULL; 852 } 853 854 while (ii) 855 { 856 temp[ii - 1] = toupper ((char) mnemonic[ii - 1]); 857 ii--; 858 } 859 860 LS_processing (temp); 861 862 if (i.Instr_Prefix != 0 && is_a_LSinstr (temp)) 863 /* Skip the optional L-S. */ 864 memcpy (temp, temp + 1, MAX_MNEM_SIZE); 865 866 /* Look up instruction (or prefix) via hash table. */ 867 current_templates = (MAXQ20_OPCODES *) hash_find (op_hash, temp); 868 869 if (current_templates != NULL) 870 return l; 871 872 as_bad (_("no such instruction: `%s'"), token_start); 873 return NULL; 874 } 875 876 /* Function to calculate x to the power of y. 877 Just to avoid including the math libraries. */ 878 879 static int 880 pwr (int x, int y) 881 { 882 int k, ans = 1; 883 884 for (k = 0; k < y; k++) 885 ans *= x; 886 887 return ans; 888 } 889 890 static reg_entry * 891 parse_reg_by_index (char *imm_start) 892 { 893 int k = 0, mid = 0, rid = 0, val = 0, j = 0; 894 char temp[4] = { 0 }; 895 reg_entry *reg = NULL; 896 897 do 898 { 899 if (isdigit (imm_start[k])) 900 temp[k] = imm_start[k] - '0'; 901 902 else if (isalpha (imm_start[k]) 903 && (imm_start[k] = tolower (imm_start[k])) < 'g') 904 temp[k] = 10 + (int) (imm_start[k] - 'a'); 905 906 else if (imm_start[k] == 'h') 907 break; 908 909 else if (imm_start[k] == END_OF_INSN) 910 { 911 imm_start[k] = 'd'; 912 break; 913 } 914 915 else 916 return NULL; /* not a hex digit */ 917 918 k++; 919 } 920 while (imm_start[k] != '\n'); 921 922 switch (imm_start[k]) 923 { 924 case 'h': 925 for (j = 0; j < k; j++) 926 val += temp[j] * pwr (16, k - j - 1); 927 break; 928 929 case 'd': 930 for (j = 0; j < k; j++) 931 { 932 if (temp[j] > 9) 933 return NULL; /* not a number */ 934 935 val += temp[j] * pwr (10, k - j - 1); 936 break; 937 } 938 } 939 940 /* Get the module and register id's. */ 941 mid = val & 0x0f; 942 rid = (val >> 4) & 0x0f; 943 944 if (mid < 6) 945 { 946 /* Search the pheripheral reg table. */ 947 for (j = 0; j < num_of_reg; j++) 948 { 949 if (new_reg_table[j].opcode == val) 950 { 951 reg = (reg_entry *) & new_reg_table[j]; 952 break; 953 } 954 } 955 } 956 957 else 958 { 959 /* Search the system register table. */ 960 j = 0; 961 962 while (system_reg_table[j].reg_name != NULL) 963 { 964 if (system_reg_table[j].opcode == val) 965 { 966 reg = (reg_entry *) & system_reg_table[j]; 967 break; 968 } 969 j++; 970 } 971 } 972 973 if (reg == NULL) 974 { 975 as_bad (_("Invalid register value %s"), imm_start); 976 return reg; 977 } 978 979 #if CHANGE_PFX 980 if (this_operand == 0 && reg != NULL) 981 { 982 if (reg->Mod_index > 7) 983 i.prefix = 2; 984 else 985 i.prefix = 0; 986 } 987 #endif 988 return (reg_entry *) reg; 989 } 990 991 /* REG_STRING starts *before* REGISTER_PREFIX. */ 992 993 static reg_entry * 994 parse_register (char *reg_string, char **end_op) 995 { 996 char *s = reg_string; 997 char *p = NULL; 998 char reg_name_given[MAX_REG_NAME_SIZE + 1]; 999 reg_entry *r = NULL; 1000 1001 r = NULL; 1002 p = NULL; 1003 1004 /* Skip possible REGISTER_PREFIX and possible whitespace. */ 1005 if (is_space_char (*s)) 1006 ++s; 1007 1008 p = reg_name_given; 1009 while ((*p++ = register_chars[(unsigned char) *s]) != '\0') 1010 { 1011 if (p >= reg_name_given + MAX_REG_NAME_SIZE) 1012 return (reg_entry *) NULL; 1013 s++; 1014 } 1015 1016 *end_op = s; 1017 1018 r = (reg_entry *) hash_find (reg_hash, reg_name_given); 1019 1020 #if CHANGE_PFX 1021 if (this_operand == 0 && r != NULL) 1022 { 1023 if (r->Mod_index > 7) 1024 i.prefix = 2; 1025 else 1026 i.prefix = 0; 1027 } 1028 #endif 1029 return r; 1030 } 1031 1032 static reg_bit * 1033 parse_register_bit (char *reg_string, char **end_op) 1034 { 1035 const char *s = reg_string; 1036 short k = 0; 1037 char diff = 0; 1038 reg_bit *rb = NULL; 1039 reg_entry *r = NULL; 1040 bit_name *b = NULL; 1041 char temp_bitname[MAX_REG_NAME_SIZE + 2]; 1042 char temp[MAX_REG_NAME_SIZE + 1]; 1043 1044 memset (&temp, '\0', (MAX_REG_NAME_SIZE + 1)); 1045 memset (&temp_bitname, '\0', (MAX_REG_NAME_SIZE + 2)); 1046 1047 diff = 0; 1048 r = NULL; 1049 rb = NULL; 1050 rb = xmalloc (sizeof (reg_bit)); 1051 rb->reg = xmalloc (sizeof (reg_entry)); 1052 k = 0; 1053 1054 /* For supporting bit names. */ 1055 b = (bit_name *) hash_find (bit_hash, reg_string); 1056 1057 if (b != NULL) 1058 { 1059 *end_op = reg_string + strlen (reg_string); 1060 strcpy (temp_bitname, b->reg_bit); 1061 s = temp_bitname; 1062 } 1063 1064 if (strchr (s, '.')) 1065 { 1066 while (*s != '.') 1067 { 1068 if (*s == '\0') 1069 return NULL; 1070 temp[k] = *s++; 1071 1072 k++; 1073 } 1074 temp[k] = '\0'; 1075 } 1076 1077 if ((r = parse_register (temp, end_op)) == NULL) 1078 return NULL; 1079 1080 rb->reg = r; 1081 1082 /* Skip the "." */ 1083 s++; 1084 1085 if (isdigit ((char) *s)) 1086 rb->bit = atoi (s); 1087 else if (isalpha ((char) *s)) 1088 { 1089 rb->bit = (char) *s - 'a'; 1090 rb->bit += 10; 1091 if (rb->bit > 15) 1092 { 1093 as_bad (_("Invalid bit number : '%c'"), (char) *s); 1094 return NULL; 1095 } 1096 } 1097 1098 if (b != NULL) 1099 diff = strlen (temp_bitname) - strlen (temp) - 1; 1100 else 1101 diff = strlen (reg_string) - strlen (temp) - 1; 1102 1103 if (*(s + diff) != '\0') 1104 { 1105 as_bad (_("Illegal character after operand '%s'"), reg_string); 1106 return NULL; 1107 } 1108 1109 return rb; 1110 } 1111 1112 static void 1113 pfx_for_imm_val (int arg) 1114 { 1115 if (i.prefix == -1) 1116 return; 1117 1118 if (i.prefix == 0 && arg == 0 && PFX_INSN[1] == 0 && !(i.data_operands)) 1119 return; 1120 1121 if (!(i.prefix < 0) && !(i.prefix > 7)) 1122 PFX_INSN[0] = (i.prefix << 4) | PFX0; 1123 1124 if (!PFX_INSN[1]) 1125 PFX_INSN[1] = arg; 1126 1127 } 1128 1129 static int 1130 maxq20_immediate (char *imm_start) 1131 { 1132 int val = 0, val_pfx = 0; 1133 char sign_val = 0; 1134 int k = 0, j; 1135 int temp[4] = { 0 }; 1136 1137 imm_start++; 1138 1139 if (imm_start[1] == '\0' && (imm_start[0] == '0' || imm_start[0] == '1') 1140 && (this_operand == 1 && ((i.types[0] == BIT || i.types[0] == FLAG)))) 1141 { 1142 val = imm_start[0] - '0'; 1143 i.imm_bit_operands++; 1144 i.types[this_operand] = IMMBIT; 1145 i.maxq20_op[this_operand].imms = (char) val; 1146 #if CHANGE_PFX 1147 if (i.prefix == 2) 1148 pfx_for_imm_val (0); 1149 #endif 1150 return 1; 1151 } 1152 1153 /* Check For Sign Charcater. */ 1154 sign_val = 0; 1155 1156 do 1157 { 1158 if (imm_start[k] == '-' && k == 0) 1159 sign_val = -1; 1160 1161 else if (imm_start[k] == '+' && k == 0) 1162 sign_val = 1; 1163 1164 else if (isdigit (imm_start[k])) 1165 temp[k] = imm_start[k] - '0'; 1166 1167 else if (isalpha (imm_start[k]) 1168 && (imm_start[k] = tolower (imm_start[k])) < 'g') 1169 temp[k] = 10 + (int) (imm_start[k] - 'a'); 1170 1171 else if (imm_start[k] == 'h') 1172 break; 1173 1174 else if (imm_start[k] == '\0') 1175 { 1176 imm_start[k] = 'd'; 1177 break; 1178 } 1179 else 1180 { 1181 as_bad (_("Invalid Character in immediate Value : %c"), 1182 imm_start[k]); 1183 return 0; 1184 } 1185 k++; 1186 } 1187 while (imm_start[k] != '\n'); 1188 1189 switch (imm_start[k]) 1190 { 1191 case 'h': 1192 for (j = (sign_val ? 1 : 0); j < k; j++) 1193 val += temp[j] * pwr (16, k - j - 1); 1194 break; 1195 1196 case 'd': 1197 for (j = (sign_val ? 1 : 0); j < k; j++) 1198 { 1199 if (temp[j] > 9) 1200 { 1201 as_bad (_("Invalid Character in immediate value : %c"), 1202 imm_start[j]); 1203 return 0; 1204 } 1205 val += temp[j] * pwr (10, k - j - 1); 1206 } 1207 } 1208 1209 if (!sign_val) 1210 sign_val = 1; 1211 1212 /* Now over here the value val stores the 8 bit/16 bit value. We will put a 1213 check if we are moving a 16 bit immediate value into an 8 bit register. 1214 In that case we will generate a warning and move only the lower 8 bits */ 1215 if (val > 65535) 1216 { 1217 as_bad (_("Immediate value greater than 16 bits")); 1218 return 0; 1219 } 1220 1221 val = val * sign_val; 1222 1223 /* If it is a stack pointer and the value is greater than the maximum 1224 permissible size */ 1225 if (this_operand == 1) 1226 { 1227 if ((val * sign_val) > MAX_STACK && i.types[0] == REG 1228 && !strcmp (i.maxq20_op[0].reg->reg_name, "SP")) 1229 { 1230 as_warn (_ 1231 ("Attempt to move a value in the stack pointer greater than the size of the stack")); 1232 val = val & MAX_STACK; 1233 } 1234 1235 /* Check the range for 8 bit registers. */ 1236 else if (((val * sign_val) > 0xFF) && (i.types[0] == REG) 1237 && (i.maxq20_op[0].reg->rtype == Reg_8W)) 1238 { 1239 as_warn (_ 1240 ("Attempt to move 16 bit value into an 8 bit register.Truncating..\n")); 1241 val = val & 0xfe; 1242 } 1243 1244 else if (((sign_val == -1) || (val > 0xFF)) && (i.types[0] == REG) 1245 && (i.maxq20_op[0].reg->rtype == Reg_8W)) 1246 { 1247 val_pfx = val >> 8; 1248 val = ((val) & 0x00ff); 1249 SET_PFX_ARG (val_pfx); 1250 i.maxq20_op[this_operand].imms = (char) val; 1251 } 1252 1253 else if ((val <= 0xff) && (i.types[0] == REG) 1254 && (i.maxq20_op[0].reg->rtype == Reg_8W)) 1255 i.maxq20_op[this_operand].imms = (char) val; 1256 1257 1258 /* Check for 16 bit registers. */ 1259 else if (((sign_val == -1) || val > 0xFE) && i.types[0] == REG 1260 && i.maxq20_op[0].reg->rtype == Reg_16W) 1261 { 1262 /* Add PFX for any negative value -> 16bit register. */ 1263 val_pfx = val >> 8; 1264 val = ((val) & 0x00ff); 1265 SET_PFX_ARG (val_pfx); 1266 i.maxq20_op[this_operand].imms = (char) val; 1267 } 1268 1269 else if (val < 0xFF && i.types[0] == REG 1270 && i.maxq20_op[0].reg->rtype == Reg_16W) 1271 { 1272 i.maxq20_op[this_operand].imms = (char) val; 1273 } 1274 1275 /* All the immediate memory access - no PFX. */ 1276 else if (i.types[0] == MEM) 1277 { 1278 if ((sign_val == -1) || val > 0xFE) 1279 { 1280 val_pfx = val >> 8; 1281 val = ((val) & 0x00ff); 1282 SET_PFX_ARG (val_pfx); 1283 i.maxq20_op[this_operand].imms = (char) val; 1284 } 1285 else 1286 i.maxq20_op[this_operand].imms = (char) val; 1287 } 1288 1289 /* Special handling for immediate jumps like jump nz, #03h etc. */ 1290 else if (val < 0xFF && i.types[0] == FLAG) 1291 i.maxq20_op[this_operand].imms = (char) val; 1292 1293 else if ((((sign_val == -1) || val > 0xFE)) && i.types[0] == FLAG) 1294 { 1295 val_pfx = val >> 8; 1296 val = ((val) & 0x00ff); 1297 SET_PFX_ARG (val_pfx); 1298 i.maxq20_op[this_operand].imms = (char) val; 1299 } 1300 else 1301 { 1302 as_bad (_("Invalid immediate move operation")); 1303 return 0; 1304 } 1305 } 1306 else 1307 { 1308 /* All the instruction with operation on ACC: like ADD src, etc. */ 1309 if ((sign_val == -1) || val > 0xFE) 1310 { 1311 val_pfx = val >> 8; 1312 val = ((val) & 0x00ff); 1313 SET_PFX_ARG (val_pfx); 1314 i.maxq20_op[this_operand].imms = (char) val; 1315 } 1316 else 1317 i.maxq20_op[this_operand].imms = (char) val; 1318 } 1319 1320 i.imm_operands++; 1321 return 1; 1322 } 1323 1324 static int 1325 extract_int_val (const char *imm_start) 1326 { 1327 int k, j, val; 1328 char sign_val; 1329 int temp[4]; 1330 1331 k = 0; 1332 j = 0; 1333 val = 0; 1334 sign_val = 0; 1335 do 1336 { 1337 if (imm_start[k] == '-' && k == 0) 1338 sign_val = -1; 1339 1340 else if (imm_start[k] == '+' && k == 0) 1341 sign_val = 1; 1342 1343 else if (isdigit (imm_start[k])) 1344 temp[k] = imm_start[k] - '0'; 1345 1346 else if (isalpha (imm_start[k]) && (tolower (imm_start[k])) < 'g') 1347 temp[k] = 10 + (int) (tolower (imm_start[k]) - 'a'); 1348 1349 else if (tolower (imm_start[k]) == 'h') 1350 break; 1351 1352 else if ((imm_start[k] == '\0') || (imm_start[k] == ']')) 1353 /* imm_start[k]='d'; */ 1354 break; 1355 1356 else 1357 { 1358 as_bad (_("Invalid Character in immediate Value : %c"), 1359 imm_start[k]); 1360 return 0; 1361 } 1362 k++; 1363 } 1364 while (imm_start[k] != '\n'); 1365 1366 switch (imm_start[k]) 1367 { 1368 case 'h': 1369 for (j = (sign_val ? 1 : 0); j < k; j++) 1370 val += temp[j] * pwr (16, k - j - 1); 1371 break; 1372 1373 default: 1374 for (j = (sign_val ? 1 : 0); j < k; j++) 1375 { 1376 if (temp[j] > 9) 1377 { 1378 as_bad (_("Invalid Character in immediate value : %c"), 1379 imm_start[j]); 1380 return 0; 1381 } 1382 val += temp[j] * pwr (10, k - j - 1); 1383 } 1384 } 1385 1386 if (!sign_val) 1387 sign_val = 1; 1388 1389 return val * sign_val; 1390 } 1391 1392 static char 1393 check_for_parse (const char *line) 1394 { 1395 int val; 1396 1397 if (*(line + 1) == '[') 1398 { 1399 do 1400 { 1401 line++; 1402 if ((*line == '-') || (*line == '+')) 1403 break; 1404 } 1405 while (!is_space_char (*line)); 1406 1407 if ((*line == '-') || (*line == '+')) 1408 val = extract_int_val (line); 1409 else 1410 val = extract_int_val (line + 1); 1411 1412 INSERT_BUFFER[0] = 0x3E; 1413 INSERT_BUFFER[1] = val; 1414 1415 return 1; 1416 } 1417 1418 return 0; 1419 } 1420 1421 static mem_access * 1422 maxq20_mem_access (char *mem_string, char **end_op) 1423 { 1424 char *s = mem_string; 1425 char *p; 1426 char mem_name_given[MAX_MEM_NAME_SIZE + 1]; 1427 mem_access *m; 1428 1429 m = NULL; 1430 1431 /* Skip possible whitespace. */ 1432 if (is_space_char (*s)) 1433 ++s; 1434 1435 p = mem_name_given; 1436 while ((*p++ = register_chars[(unsigned char) *s]) != '\0') 1437 { 1438 if (p >= mem_name_given + MAX_MEM_NAME_SIZE) 1439 return (mem_access *) NULL; 1440 s++; 1441 } 1442 1443 *end_op = s; 1444 1445 m = (mem_access *) hash_find (mem_hash, mem_name_given); 1446 1447 return m; 1448 } 1449 1450 /* This function checks whether the operand is a variable in the data segment 1451 and if so, it returns its symbol entry from the symbol table. */ 1452 1453 static symbolS * 1454 maxq20_data (char *op_string) 1455 { 1456 symbolS *symbolP; 1457 symbolP = symbol_find (op_string); 1458 1459 if (symbolP != NULL 1460 && S_GET_SEGMENT (symbolP) != now_seg 1461 && S_GET_SEGMENT (symbolP) != bfd_und_section_ptr) 1462 { 1463 /* In case we do not want to always include the prefix instruction and 1464 let the loader handle the job or in case of a 8 bit addressing mode, 1465 we will just check for val_pfx to be equal to zero and then load the 1466 prefix instruction. Otherwise no prefix instruction needs to be 1467 loaded. */ 1468 /* The prefix register will have to be loaded automatically as we have 1469 a 16 bit addressing field. */ 1470 pfx_for_imm_val (0); 1471 return symbolP; 1472 } 1473 1474 return NULL; 1475 } 1476 1477 static int 1478 maxq20_displacement (char *disp_start, char *disp_end) 1479 { 1480 expressionS *exp; 1481 segT exp_seg = 0; 1482 char *save_input_line_pointer; 1483 #ifndef LEX_AT 1484 char *gotfree_input_line; 1485 #endif 1486 1487 gotfree_input_line = NULL; 1488 exp = &disp_expressions; 1489 i.maxq20_op[this_operand].disps = exp; 1490 i.disp_operands++; 1491 save_input_line_pointer = input_line_pointer; 1492 input_line_pointer = disp_start; 1493 1494 END_STRING_AND_SAVE (disp_end); 1495 1496 #ifndef LEX_AT 1497 /* gotfree_input_line = lex_got (&i.reloc[this_operand], NULL); if 1498 (gotfree_input_line) input_line_pointer = gotfree_input_line; */ 1499 #endif 1500 exp_seg = expression (exp); 1501 1502 SKIP_WHITESPACE (); 1503 if (*input_line_pointer) 1504 as_bad (_("junk `%s' after expression"), input_line_pointer); 1505 #if GCC_ASM_O_HACK 1506 RESTORE_END_STRING (disp_end + 1); 1507 #endif 1508 RESTORE_END_STRING (disp_end); 1509 input_line_pointer = save_input_line_pointer; 1510 #ifndef LEX_AT 1511 if (gotfree_input_line) 1512 free (gotfree_input_line); 1513 #endif 1514 if (exp->X_op == O_absent || exp->X_op == O_big) 1515 { 1516 /* Missing or bad expr becomes absolute 0. */ 1517 as_bad (_("missing or invalid displacement expression `%s' taken as 0"), 1518 disp_start); 1519 exp->X_op = O_constant; 1520 exp->X_add_number = 0; 1521 exp->X_add_symbol = (symbolS *) 0; 1522 exp->X_op_symbol = (symbolS *) 0; 1523 } 1524 #if (defined (OBJ_AOUT) || defined (OBJ_MAYBE_AOUT)) 1525 1526 if (exp->X_op != O_constant 1527 && OUTPUT_FLAVOR == bfd_target_aout_flavour 1528 && exp_seg != absolute_section 1529 && exp_seg != text_section 1530 && exp_seg != data_section 1531 && exp_seg != bss_section && exp_seg != undefined_section 1532 && !bfd_is_com_section (exp_seg)) 1533 { 1534 as_bad (_("unimplemented segment %s in operand"), exp_seg->name); 1535 return 0; 1536 } 1537 #endif 1538 i.maxq20_op[this_operand].disps = exp; 1539 return 1; 1540 } 1541 1542 /* Parse OPERAND_STRING into the maxq20_insn structure I. 1543 Returns non-zero on error. */ 1544 1545 static int 1546 maxq20_operand (char *operand_string) 1547 { 1548 reg_entry *r = NULL; 1549 reg_bit *rb = NULL; 1550 mem_access *m = NULL; 1551 char *end_op = NULL; 1552 symbolS *sym = NULL; 1553 char *base_string = NULL; 1554 int ii = 0; 1555 /* Start and end of displacement string expression (if found). */ 1556 char *displacement_string_start = NULL; 1557 char *displacement_string_end = NULL; 1558 /* This maintains the case sentivness. */ 1559 char case_str_op_string[MAX_OPERAND_SIZE + 1]; 1560 char str_op_string[MAX_OPERAND_SIZE + 1]; 1561 char *org_case_op_string = case_str_op_string; 1562 char *op_string = str_op_string; 1563 1564 1565 memset (op_string, END_OF_INSN, (MAX_OPERAND_SIZE + 1)); 1566 memset (org_case_op_string, END_OF_INSN, (MAX_OPERAND_SIZE + 1)); 1567 1568 memcpy (op_string, operand_string, strlen (operand_string) + 1); 1569 memcpy (org_case_op_string, operand_string, strlen (operand_string) + 1); 1570 1571 ii = strlen (operand_string) + 1; 1572 1573 if (ii > MAX_OPERAND_SIZE) 1574 { 1575 as_bad (_("Size of Operand '%s' greater than %d"), op_string, 1576 MAX_OPERAND_SIZE); 1577 return 0; 1578 } 1579 1580 while (ii) 1581 { 1582 op_string[ii - 1] = toupper ((char) op_string[ii - 1]); 1583 ii--; 1584 } 1585 1586 if (is_space_char (*op_string)) 1587 ++op_string; 1588 1589 if (isxdigit (operand_string[0])) 1590 { 1591 /* Now the operands can start with an Integer. */ 1592 r = parse_reg_by_index (op_string); 1593 if (r != NULL) 1594 { 1595 if (is_space_char (*op_string)) 1596 ++op_string; 1597 i.types[this_operand] = REG; /* Set the type. */ 1598 i.maxq20_op[this_operand].reg = r; /* Set the Register value. */ 1599 i.reg_operands++; 1600 return 1; 1601 } 1602 1603 /* Get the origanal string. */ 1604 memcpy (op_string, operand_string, strlen (operand_string) + 1); 1605 ii = strlen (operand_string) + 1; 1606 1607 while (ii) 1608 { 1609 op_string[ii - 1] = toupper ((char) op_string[ii - 1]); 1610 ii--; 1611 } 1612 } 1613 1614 /* Check for flags. */ 1615 if (!strcmp (op_string, "Z")) 1616 { 1617 if (is_space_char (*op_string)) 1618 ++op_string; 1619 1620 i.types[this_operand] = FLAG; /* Set the type. */ 1621 i.maxq20_op[this_operand].flag = FLAG_Z; /* Set the Register value. */ 1622 1623 i.flag_operands++; 1624 1625 return 1; 1626 } 1627 1628 else if (!strcmp (op_string, "NZ")) 1629 { 1630 if (is_space_char (*op_string)) 1631 ++op_string; 1632 1633 i.types[this_operand] = FLAG; /* Set the type. */ 1634 i.maxq20_op[this_operand].flag = FLAG_NZ; /* Set the Register value. */ 1635 i.flag_operands++; 1636 return 1; 1637 } 1638 1639 else if (!strcmp (op_string, "NC")) 1640 { 1641 if (is_space_char (*op_string)) 1642 ++op_string; 1643 1644 i.types[this_operand] = FLAG; /* Set the type. */ 1645 i.maxq20_op[this_operand].flag = FLAG_NC; /* Set the Register value. */ 1646 i.flag_operands++; 1647 return 1; 1648 } 1649 1650 else if (!strcmp (op_string, "E")) 1651 { 1652 if (is_space_char (*op_string)) 1653 ++op_string; 1654 1655 i.types[this_operand] = FLAG; /* Set the type. */ 1656 i.maxq20_op[this_operand].flag = FLAG_E; /* Set the Register value. */ 1657 1658 i.flag_operands++; 1659 1660 return 1; 1661 } 1662 1663 else if (!strcmp (op_string, "S")) 1664 { 1665 if (is_space_char (*op_string)) 1666 ++op_string; 1667 1668 i.types[this_operand] = FLAG; /* Set the type. */ 1669 i.maxq20_op[this_operand].flag = FLAG_S; /* Set the Register value. */ 1670 1671 i.flag_operands++; 1672 1673 return 1; 1674 } 1675 1676 else if (!strcmp (op_string, "C")) 1677 { 1678 if (is_space_char (*op_string)) 1679 ++op_string; 1680 1681 i.types[this_operand] = FLAG; /* Set the type. */ 1682 i.maxq20_op[this_operand].flag = FLAG_C; /* Set the Register value. */ 1683 1684 i.flag_operands++; 1685 1686 return 1; 1687 } 1688 1689 else if (!strcmp (op_string, "NE")) 1690 { 1691 1692 if (is_space_char (*op_string)) 1693 ++op_string; 1694 1695 i.types[this_operand] = FLAG; /* Set the type. */ 1696 1697 i.maxq20_op[this_operand].flag = FLAG_NE; /* Set the Register value. */ 1698 1699 i.flag_operands++; 1700 1701 return 1; 1702 } 1703 1704 /* CHECK FOR REGISTER BIT */ 1705 else if ((rb = parse_register_bit (op_string, &end_op)) != NULL) 1706 { 1707 op_string = end_op; 1708 1709 if (is_space_char (*op_string)) 1710 ++op_string; 1711 1712 i.types[this_operand] = BIT; 1713 1714 i.maxq20_op[this_operand].r_bit = rb; 1715 1716 i.bit_operands++; 1717 1718 return 1; 1719 } 1720 1721 else if (*op_string == IMMEDIATE_PREFIX) /* FOR IMMEDITE. */ 1722 { 1723 if (is_space_char (*op_string)) 1724 ++op_string; 1725 1726 i.types[this_operand] = IMM; 1727 1728 if (!maxq20_immediate (op_string)) 1729 { 1730 as_bad (_("illegal immediate operand '%s'"), op_string); 1731 return 0; 1732 } 1733 return 1; 1734 } 1735 1736 else if (*op_string == ABSOLUTE_PREFIX || !strcmp (op_string, "NUL")) 1737 { 1738 if (is_space_char (*op_string)) 1739 ++op_string; 1740 1741 /* For new requiremnt of copiler of for, @(BP,cons). */ 1742 if (check_for_parse (op_string)) 1743 { 1744 memset (op_string, '\0', strlen (op_string) + 1); 1745 memcpy (op_string, "@BP[OFFS]\0", 11); 1746 } 1747 1748 i.types[this_operand] = MEM; 1749 1750 if ((m = maxq20_mem_access (op_string, &end_op)) == NULL) 1751 { 1752 as_bad (_("Invalid operand for memory access '%s'"), op_string); 1753 return 0; 1754 } 1755 i.maxq20_op[this_operand].mem = m; 1756 1757 i.mem_operands++; 1758 1759 return 1; 1760 } 1761 1762 else if ((r = parse_register (op_string, &end_op)) != NULL) /* Check for register. */ 1763 { 1764 op_string = end_op; 1765 1766 if (is_space_char (*op_string)) 1767 ++op_string; 1768 1769 i.types[this_operand] = REG; /* Set the type. */ 1770 i.maxq20_op[this_operand].reg = r; /* Set the Register value. */ 1771 i.reg_operands++; 1772 return 1; 1773 } 1774 1775 if (this_operand == 1) 1776 { 1777 /* Changed for orginal case of data refrence on 30 Nov 2003. */ 1778 /* The operand can either be a data reference or a symbol reference. */ 1779 if ((sym = maxq20_data (org_case_op_string)) != NULL) /* Check for data memory. */ 1780 { 1781 while (is_space_char (*op_string)) 1782 ++op_string; 1783 1784 /* Set the type of the operand. */ 1785 i.types[this_operand] = DATA; 1786 1787 /* Set the value of the data. */ 1788 i.maxq20_op[this_operand].data = sym; 1789 i.data_operands++; 1790 1791 return 1; 1792 } 1793 1794 else if (is_digit_char (*op_string) || is_identifier_char (*op_string)) 1795 { 1796 /* This is a memory reference of some sort. char *base_string; 1797 Start and end of displacement string expression (if found). char 1798 *displacement_string_start; char *displacement_string_end. */ 1799 base_string = org_case_op_string + strlen (org_case_op_string); 1800 1801 --base_string; 1802 if (is_space_char (*base_string)) 1803 --base_string; 1804 1805 /* If we only have a displacement, set-up for it to be parsed 1806 later. */ 1807 displacement_string_start = org_case_op_string; 1808 displacement_string_end = base_string + 1; 1809 if (displacement_string_start != displacement_string_end) 1810 { 1811 if (!maxq20_displacement (displacement_string_start, 1812 displacement_string_end)) 1813 { 1814 as_bad (_("illegal displacement operand ")); 1815 return 0; 1816 } 1817 /* A displacement operand found. */ 1818 i.types[this_operand] = DISP; /* Set the type. */ 1819 return 1; 1820 } 1821 } 1822 } 1823 1824 /* Check for displacement. */ 1825 else if (is_digit_char (*op_string) || is_identifier_char (*op_string)) 1826 { 1827 /* This is a memory reference of some sort. char *base_string; 1828 Start and end of displacement string expression (if found). char 1829 *displacement_string_start; char *displacement_string_end; */ 1830 base_string = org_case_op_string + strlen (org_case_op_string); 1831 1832 --base_string; 1833 if (is_space_char (*base_string)) 1834 --base_string; 1835 1836 /* If we only have a displacement, set-up for it to be parsed later. */ 1837 displacement_string_start = org_case_op_string; 1838 displacement_string_end = base_string + 1; 1839 if (displacement_string_start != displacement_string_end) 1840 { 1841 if (!maxq20_displacement (displacement_string_start, 1842 displacement_string_end)) 1843 return 0; 1844 /* A displacement operand found. */ 1845 i.types[this_operand] = DISP; /* Set the type. */ 1846 } 1847 } 1848 return 1; 1849 } 1850 1851 /* Parse_operand takes as input instruction and operands and Parse operands 1852 and makes entry in the template. */ 1853 1854 static char * 1855 parse_operands (char *l, const char *mnemonic) 1856 { 1857 char *token_start; 1858 1859 /* 1 if operand is pending after ','. */ 1860 short int expecting_operand = 0; 1861 1862 /* Non-zero if operand parens not balanced. */ 1863 short int paren_not_balanced; 1864 1865 int operand_ok; 1866 1867 /* For Overcoming Warning of unused variable. */ 1868 if (mnemonic) 1869 operand_ok = 0; 1870 1871 while (*l != END_OF_INSN) 1872 { 1873 /* Skip optional white space before operand. */ 1874 if (is_space_char (*l)) 1875 ++l; 1876 1877 if (!is_operand_char (*l) && *l != END_OF_INSN) 1878 { 1879 as_bad (_("invalid character %c before operand %d"), 1880 (char) (*l), i.operands + 1); 1881 return NULL; 1882 } 1883 token_start = l; 1884 1885 paren_not_balanced = 0; 1886 while (paren_not_balanced || *l != ',') 1887 { 1888 if (*l == END_OF_INSN) 1889 { 1890 if (paren_not_balanced) 1891 { 1892 as_bad (_("unbalanced brackets in operand %d."), 1893 i.operands + 1); 1894 return NULL; 1895 } 1896 1897 break; 1898 } 1899 else if (!is_operand_char (*l) && !is_space_char (*l)) 1900 { 1901 as_bad (_("invalid character %c in operand %d"), 1902 (char) (*l), i.operands + 1); 1903 return NULL; 1904 } 1905 if (*l == '[') 1906 ++paren_not_balanced; 1907 if (*l == ']') 1908 --paren_not_balanced; 1909 l++; 1910 } 1911 1912 if (l != token_start) 1913 { 1914 /* Yes, we've read in another operand. */ 1915 this_operand = i.operands++; 1916 if (i.operands > MAX_OPERANDS) 1917 { 1918 as_bad (_("spurious operands; (%d operands/instruction max)"), 1919 MAX_OPERANDS); 1920 return NULL; 1921 } 1922 1923 /* Now parse operand adding info to 'i' as we go along. */ 1924 END_STRING_AND_SAVE (l); 1925 1926 operand_ok = maxq20_operand (token_start); 1927 1928 RESTORE_END_STRING (l); 1929 1930 if (!operand_ok) 1931 return NULL; 1932 } 1933 else 1934 { 1935 if (expecting_operand) 1936 { 1937 expecting_operand_after_comma: 1938 as_bad (_("expecting operand after ','; got nothing")); 1939 return NULL; 1940 } 1941 } 1942 1943 if (*l == ',') 1944 { 1945 if (*(++l) == END_OF_INSN) 1946 /* Just skip it, if it's \n complain. */ 1947 goto expecting_operand_after_comma; 1948 1949 expecting_operand = 1; 1950 } 1951 } 1952 1953 return l; 1954 } 1955 1956 static int 1957 match_operands (int type, MAX_ARG_TYPE flag_type, MAX_ARG_TYPE arg_type, 1958 int op_num) 1959 { 1960 switch (type) 1961 { 1962 case REG: 1963 if ((arg_type & A_REG) == A_REG) 1964 return 1; 1965 break; 1966 case IMM: 1967 if ((arg_type & A_IMM) == A_IMM) 1968 return 1; 1969 break; 1970 case IMMBIT: 1971 if ((arg_type & A_BIT_0) == A_BIT_0 && (i.maxq20_op[op_num].imms == 0)) 1972 return 1; 1973 else if ((arg_type & A_BIT_1) == A_BIT_1 1974 && (i.maxq20_op[op_num].imms == 1)) 1975 return 1; 1976 break; 1977 case MEM: 1978 if ((arg_type & A_MEM) == A_MEM) 1979 return 1; 1980 break; 1981 1982 case FLAG: 1983 if ((arg_type & flag_type) == flag_type) 1984 return 1; 1985 1986 break; 1987 1988 case BIT: 1989 if ((arg_type & ACC_BIT) == ACC_BIT && !strcmp (i.maxq20_op[op_num].r_bit->reg->reg_name, "ACC")) 1990 return 1; 1991 else if ((arg_type & SRC_BIT) == SRC_BIT && (op_num == 1)) 1992 return 1; 1993 else if ((op_num == 0) && (arg_type & DST_BIT) == DST_BIT) 1994 return 1; 1995 break; 1996 case DISP: 1997 if ((arg_type & A_DISP) == A_DISP) 1998 return 1; 1999 case DATA: 2000 if ((arg_type & A_DATA) == A_DATA) 2001 return 1; 2002 case BIT_BUCKET: 2003 if ((arg_type & A_BIT_BUCKET) == A_BIT_BUCKET) 2004 return 1; 2005 } 2006 return 0; 2007 } 2008 2009 static int 2010 match_template (void) 2011 { 2012 /* Points to template once we've found it. */ 2013 const MAXQ20_OPCODE_INFO *t; 2014 char inv_oper; 2015 inv_oper = 0; 2016 2017 for (t = current_templates->start; t < current_templates->end; t++) 2018 { 2019 /* Must have right number of operands. */ 2020 if (i.operands != t->op_number) 2021 continue; 2022 else if (!t->op_number) 2023 break; 2024 2025 switch (i.operands) 2026 { 2027 case 2: 2028 if (!match_operands (i.types[1], i.maxq20_op[1].flag, t->arg[1], 1)) 2029 { 2030 inv_oper = 1; 2031 continue; 2032 } 2033 case 1: 2034 if (!match_operands (i.types[0], i.maxq20_op[0].flag, t->arg[0], 0)) 2035 { 2036 inv_oper = 2; 2037 continue; 2038 } 2039 } 2040 break; 2041 } 2042 2043 if (t == current_templates->end) 2044 { 2045 /* We found no match. */ 2046 as_bad (_("operand %d is invalid for `%s'"), 2047 inv_oper, current_templates->start->name); 2048 return 0; 2049 } 2050 2051 /* Copy the template we have found. */ 2052 i.op = *t; 2053 return 1; 2054 } 2055 2056 /* This function filters out the various combinations of operands which are 2057 not allowed for a particular instruction. */ 2058 2059 static int 2060 match_filters (void) 2061 { 2062 /* Now we have at our disposal the instruction i. We will be using the 2063 following fields i.op.name : This is the mnemonic name. i.types[2] : 2064 These are the types of the operands (REG/IMM/DISP/MEM/BIT/FLAG/IMMBIT) 2065 i.maxq20_op[2] : This contains the specific info of the operands. */ 2066 2067 /* Our first filter : NO ALU OPERATIONS CAN HAVE THE ACTIVE ACCUMULATOR AS 2068 SOURCE. */ 2069 if (!strcmp (i.op.name, "AND") || !strcmp (i.op.name, "OR") 2070 || !strcmp (i.op.name, "XOR") || !strcmp (i.op.name, "ADD") 2071 || !strcmp (i.op.name, "ADDC") || !strcmp (i.op.name, "SUB") 2072 || !strcmp (i.op.name, "SUBB")) 2073 { 2074 if (i.types[0] == REG) 2075 { 2076 if (i.maxq20_op[0].reg->Mod_name == 0xa) 2077 { 2078 as_bad (_ 2079 ("The Accumulator cannot be used as a source in ALU instructions\n")); 2080 return 0; 2081 } 2082 } 2083 } 2084 2085 if (!strcmp (i.op.name, "MOVE") && (i.types[0] == MEM || i.types[1] == MEM) 2086 && i.operands == 2) 2087 { 2088 mem_access_syntax *mem_op = NULL; 2089 2090 if (i.types[0] == MEM) 2091 { 2092 mem_op = 2093 (mem_access_syntax *) hash_find (mem_syntax_hash, 2094 i.maxq20_op[0].mem->name); 2095 if ((mem_op->type == SRC) && mem_op) 2096 { 2097 as_bad (_("'%s' operand cant be used as destination in %s"), 2098 mem_op->name, i.op.name); 2099 return 0; 2100 } 2101 else if ((mem_op->invalid_op != NULL) && (i.types[1] == MEM) 2102 && mem_op) 2103 { 2104 int k = 0; 2105 2106 for (k = 0; k < 5 || !mem_op->invalid_op[k]; k++) 2107 { 2108 if (mem_op->invalid_op[k] != NULL) 2109 if (!strcmp 2110 (mem_op->invalid_op[k], i.maxq20_op[1].mem->name)) 2111 { 2112 as_bad (_ 2113 ("Invalid Instruction '%s' operand cant be used with %s"), 2114 mem_op->name, i.maxq20_op[1].mem->name); 2115 return 0; 2116 } 2117 } 2118 } 2119 } 2120 2121 if (i.types[1] == MEM) 2122 { 2123 mem_op = NULL; 2124 mem_op = 2125 (mem_access_syntax *) hash_find (mem_syntax_hash, 2126 i.maxq20_op[1].mem->name); 2127 if (mem_op->type == DST && mem_op) 2128 { 2129 as_bad (_("'%s' operand cant be used as source in %s"), 2130 mem_op->name, i.op.name); 2131 return 0; 2132 } 2133 else if (mem_op->invalid_op != NULL && i.types[0] == MEM && mem_op) 2134 { 2135 int k = 0; 2136 2137 for (k = 0; k < 5 || !mem_op->invalid_op[k]; k++) 2138 { 2139 if (mem_op->invalid_op[k] != NULL) 2140 if (!strcmp 2141 (mem_op->invalid_op[k], i.maxq20_op[0].mem->name)) 2142 { 2143 as_bad (_ 2144 ("Invalid Instruction '%s' operand cant be used with %s"), 2145 mem_op->name, i.maxq20_op[0].mem->name); 2146 return 0; 2147 } 2148 } 2149 } 2150 else if (i.types[0] == REG 2151 && !strcmp (i.maxq20_op[0].reg->reg_name, "OFFS") 2152 && mem_op) 2153 { 2154 if (!strcmp (mem_op->name, "@BP[OFFS--]") 2155 || !strcmp (mem_op->name, "@BP[OFFS++]")) 2156 { 2157 as_bad (_ 2158 ("Invalid Instruction '%s' operand cant be used with %s"), 2159 mem_op->name, i.maxq20_op[0].mem->name); 2160 return 0; 2161 } 2162 } 2163 } 2164 } 2165 2166 /* Added for SRC and DST in one operand instructioni i.e OR @--DP[1] added 2167 on 10-March-2004. */ 2168 if ((i.types[0] == MEM) && (i.operands == 1) 2169 && !(!strcmp (i.op.name, "POP") || !strcmp (i.op.name, "POPI"))) 2170 { 2171 mem_access_syntax *mem_op = NULL; 2172 2173 if (i.types[0] == MEM) 2174 { 2175 mem_op = 2176 (mem_access_syntax *) hash_find (mem_syntax_hash, 2177 i.maxq20_op[0].mem->name); 2178 if (mem_op->type == DST && mem_op) 2179 { 2180 as_bad (_("'%s' operand cant be used as source in %s"), 2181 mem_op->name, i.op.name); 2182 return 0; 2183 } 2184 } 2185 } 2186 2187 if (i.operands == 2 && i.types[0] == IMM) 2188 { 2189 as_bad (_("'%s' instruction cant have first operand as Immediate vale"), 2190 i.op.name); 2191 return 0; 2192 } 2193 2194 /* Our second filter : SP or @SP-- cannot be used with PUSH or POP */ 2195 if (!strcmp (i.op.name, "PUSH") || !strcmp (i.op.name, "POP") 2196 || !strcmp (i.op.name, "POPI")) 2197 { 2198 if (i.types[0] == REG) 2199 { 2200 if (!strcmp (i.maxq20_op[0].reg->reg_name, "SP")) 2201 { 2202 as_bad (_("SP cannot be used with %s\n"), i.op.name); 2203 return 0; 2204 } 2205 } 2206 else if (i.types[0] == MEM 2207 && !strcmp (i.maxq20_op[0].mem->name, "@SP--")) 2208 { 2209 as_bad (_("@SP-- cannot be used with PUSH\n")); 2210 return 0; 2211 } 2212 } 2213 2214 /* This filter checks that two memory references using DP's cannot be used 2215 together in an instruction */ 2216 if (!strcmp (i.op.name, "MOVE") && i.mem_operands == 2) 2217 { 2218 if (strlen (i.maxq20_op[0].mem->name) != 6 || 2219 strcmp (i.maxq20_op[0].mem->name, i.maxq20_op[1].mem->name)) 2220 { 2221 if (!strncmp (i.maxq20_op[0].mem->name, "@DP", 3) 2222 && !strncmp (i.maxq20_op[1].mem->name, "@DP", 3)) 2223 { 2224 as_bad (_ 2225 ("Operands either contradictory or use the data bus in read/write state together")); 2226 return 0; 2227 } 2228 2229 if (!strncmp (i.maxq20_op[0].mem->name, "@SP", 3) 2230 && !strncmp (i.maxq20_op[1].mem->name, "@SP", 3)) 2231 { 2232 as_bad (_ 2233 ("Operands either contradictory or use the data bus in read/write state together")); 2234 return 0; 2235 } 2236 } 2237 if ((i.maxq20_op[1].mem != NULL) 2238 && !strncmp (i.maxq20_op[1].mem->name, "NUL", 3)) 2239 { 2240 as_bad (_("MOVE Cant Use NUL as SRC")); 2241 return 0; 2242 } 2243 } 2244 2245 /* This filter checks that contradictory movement between DP register and 2246 Memory access using DP followed by increment or decrement. */ 2247 2248 if (!strcmp (i.op.name, "MOVE") && i.mem_operands == 1 2249 && i.reg_operands == 1) 2250 { 2251 int memnum, regnum; 2252 2253 memnum = (i.types[0] == MEM) ? 0 : 1; 2254 regnum = (memnum == 0) ? 1 : 0; 2255 if (!strncmp (i.maxq20_op[regnum].reg->reg_name, "DP", 2) && 2256 !strncmp ((i.maxq20_op[memnum].mem->name) + 1, 2257 i.maxq20_op[regnum].reg->reg_name, 5) 2258 && strcmp ((i.maxq20_op[memnum].mem->name) + 1, 2259 i.maxq20_op[regnum].reg->reg_name)) 2260 { 2261 as_bad (_ 2262 ("Contradictory movement between DP register and memory access using DP")); 2263 return 0; 2264 } 2265 else if (!strcmp (i.maxq20_op[regnum].reg->reg_name, "SP") && 2266 !strncmp ((i.maxq20_op[memnum].mem->name) + 1, 2267 i.maxq20_op[regnum].reg->reg_name, 2)) 2268 { 2269 as_bad (_ 2270 ("SP and @SP-- cannot be used together in a move instruction")); 2271 return 0; 2272 } 2273 } 2274 2275 /* This filter restricts the instructions containing source and destination 2276 bits to only CTRL module of the serial registers. Peripheral registers 2277 yet to be defined. */ 2278 2279 if (i.bit_operands == 1 && i.operands == 2) 2280 { 2281 int bitnum = (i.types[0] == BIT) ? 0 : 1; 2282 2283 if (strcmp (i.maxq20_op[bitnum].r_bit->reg->reg_name, "ACC")) 2284 { 2285 if (i.maxq20_op[bitnum].r_bit->reg->Mod_name >= 0x7 && 2286 i.maxq20_op[bitnum].r_bit->reg->Mod_name != CTRL) 2287 { 2288 as_bad (_ 2289 ("Only Module 8 system registers allowed in this operation")); 2290 return 0; 2291 } 2292 } 2293 } 2294 2295 /* This filter is for checking the register bits. */ 2296 if (i.bit_operands == 1 || i.operands == 2) 2297 { 2298 int bitnum = 0, size = 0; 2299 2300 bitnum = (i.types[0] == BIT) ? 0 : 1; 2301 if (i.bit_operands == 1) 2302 { 2303 switch (i.maxq20_op[bitnum].r_bit->reg->rtype) 2304 { 2305 case Reg_8W: 2306 size = 7; /* 8 bit register, both read and write. */ 2307 break; 2308 case Reg_16W: 2309 size = 15; 2310 break; 2311 case Reg_8R: 2312 size = 7; 2313 if (bitnum == 0) 2314 { 2315 as_fatal (_("Read only Register used as destination")); 2316 return 0; 2317 } 2318 break; 2319 2320 case Reg_16R: 2321 size = 15; 2322 if (bitnum == 0) 2323 { 2324 as_fatal (_("Read only Register used as destination")); 2325 return 0; 2326 } 2327 break; 2328 } 2329 2330 if (size < (i.maxq20_op[bitnum].r_bit)->bit) 2331 { 2332 as_bad (_("Bit No '%d'exceeds register size in this operation"), 2333 (i.maxq20_op[bitnum].r_bit)->bit); 2334 return 0; 2335 } 2336 } 2337 2338 if (i.bit_operands == 2) 2339 { 2340 switch ((i.maxq20_op[0].r_bit)->reg->rtype) 2341 { 2342 case Reg_8W: 2343 size = 7; /* 8 bit register, both read and write. */ 2344 break; 2345 case Reg_16W: 2346 size = 15; 2347 break; 2348 case Reg_8R: 2349 case Reg_16R: 2350 as_fatal (_("Read only Register used as destination")); 2351 return 0; 2352 } 2353 2354 if (size < (i.maxq20_op[0].r_bit)->bit) 2355 { 2356 as_bad (_ 2357 ("Bit No '%d' exceeds register size in this operation"), 2358 (i.maxq20_op[0].r_bit)->bit); 2359 return 0; 2360 } 2361 2362 size = 0; 2363 switch ((i.maxq20_op[1].r_bit)->reg->rtype) 2364 { 2365 case Reg_8R: 2366 case Reg_8W: 2367 size = 7; /* 8 bit register, both read and write. */ 2368 break; 2369 case Reg_16R: 2370 case Reg_16W: 2371 size = 15; 2372 break; 2373 } 2374 2375 if (size < (i.maxq20_op[1].r_bit)->bit) 2376 { 2377 as_bad (_ 2378 ("Bit No '%d' exceeds register size in this operation"), 2379 (i.maxq20_op[1].r_bit)->bit); 2380 return 0; 2381 } 2382 } 2383 } 2384 2385 /* No branch operations should occur into the data memory. Hence any memory 2386 references have to be filtered out when used with instructions like 2387 jump, djnz[] and call. */ 2388 2389 if (!strcmp (i.op.name, "JUMP") || !strcmp (i.op.name, "CALL") 2390 || !strncmp (i.op.name, "DJNZ", 4)) 2391 { 2392 if (i.mem_operands) 2393 as_warn (_ 2394 ("Memory References cannot be used with branching operations\n")); 2395 } 2396 2397 if (!strcmp (i.op.name, "DJNZ")) 2398 { 2399 if (! 2400 (strcmp (i.maxq20_op[0].reg->reg_name, "LC[0]") 2401 || strcmp (i.maxq20_op[0].reg->reg_name, "LC[1]"))) 2402 { 2403 as_bad (_("DJNZ uses only LC[n] register \n")); 2404 return 0; 2405 } 2406 } 2407 2408 /* No destination register used should be read only! */ 2409 if ((i.operands == 2 && i.types[0] == REG) || !strcmp (i.op.name, "POP") 2410 || !strcmp (i.op.name, "POPI")) 2411 { /* The destination is a register */ 2412 int regnum = 0; 2413 2414 if (!strcmp (i.op.name, "POP") || !strcmp (i.op.name, "POPI")) 2415 { 2416 regnum = 0; 2417 2418 if (i.types[regnum] == MEM) 2419 { 2420 mem_access_syntax *mem_op = NULL; 2421 2422 mem_op = 2423 (mem_access_syntax *) hash_find (mem_syntax_hash, 2424 i.maxq20_op[regnum].mem-> 2425 name); 2426 if (mem_op->type == SRC && mem_op) 2427 { 2428 as_bad (_ 2429 ("'%s' operand cant be used as destination in %s"), 2430 mem_op->name, i.op.name); 2431 return 0; 2432 } 2433 } 2434 } 2435 2436 if (i.maxq20_op[regnum].reg->rtype == Reg_8R 2437 || i.maxq20_op[regnum].reg->rtype == Reg_16R) 2438 { 2439 as_bad (_("Read only register used for writing purposes '%s'"), 2440 i.maxq20_op[regnum].reg->reg_name); 2441 return 0; 2442 } 2443 } 2444 2445 /* While moving the address of a data in the data section, the destination 2446 should be either data pointers only. */ 2447 if ((i.data_operands) && (i.operands == 2)) 2448 { 2449 if ((i.types[0] != REG) && (i.types[0] != MEM)) 2450 { 2451 as_bad (_("Invalid destination for this kind of source.")); 2452 return 0; 2453 } 2454 2455 if (i.types[0] == REG && i.maxq20_op[0].reg->rtype == Reg_8W) 2456 { 2457 as_bad (_ 2458 ("Invalid register as destination for this kind of source.Only data pointers can be used.")); 2459 return 0; 2460 } 2461 } 2462 return 1; 2463 } 2464 2465 static int 2466 decode_insn (void) 2467 { 2468 /* Check for the format Bit if defined. */ 2469 if (i.op.format == 0 || i.op.format == 1) 2470 i.instr[0] = i.op.format << 7; 2471 else 2472 { 2473 /* Format bit not defined. We will have to be find it out ourselves. */ 2474 if (i.imm_operands == 1 || i.data_operands == 1 || i.disp_operands == 1) 2475 i.op.format = 0; 2476 else 2477 i.op.format = 1; 2478 i.instr[0] = i.op.format << 7; 2479 } 2480 2481 /* Now for the destination register. */ 2482 2483 /* If destination register is already defined . The conditions are the 2484 following: (1) The second entry in the destination array should be 0 (2) 2485 If there are two operands then the first entry should not be a register, 2486 memory or a register bit (3) If there are less than two operands and the 2487 it is not a pop operation (4) The second argument is the carry 2488 flag(applicable to move Acc.<b>,C. */ 2489 if (i.op.dst[1] == 0 2490 && 2491 ((i.types[0] != REG && i.types[0] != MEM && i.types[0] != BIT 2492 && i.operands == 2) || (i.operands < 2 && strcmp (i.op.name, "POP") 2493 && strcmp (i.op.name, "POPI")) 2494 || (i.op.arg[1] == FLAG_C))) 2495 { 2496 i.op.dst[0] &= 0x7f; 2497 i.instr[0] |= i.op.dst[0]; 2498 } 2499 else if (i.op.dst[1] == 0 && !strcmp (i.op.name, "DJNZ") 2500 && 2501 (((i.types[0] == REG) 2502 && (!strcmp (i.maxq20_op[0].reg->reg_name, "LC[0]") 2503 || !strcmp (i.maxq20_op[0].reg->reg_name, "LC[1]"))))) 2504 { 2505 i.op.dst[0] &= 0x7f; 2506 if (!strcmp (i.maxq20_op[0].reg->reg_name, "LC[0]")) 2507 i.instr[0] |= 0x4D; 2508 2509 if (!strcmp (i.maxq20_op[0].reg->reg_name, "LC[1]")) 2510 i.instr[0] |= 0x5D; 2511 } 2512 else 2513 { 2514 unsigned char temp; 2515 2516 /* Target register will have to be specified. */ 2517 if (i.types[0] == REG 2518 && (i.op.dst[0] == REG || i.op.dst[0] == (REG | MEM))) 2519 { 2520 temp = (i.maxq20_op[0].reg)->opcode; 2521 temp &= 0x7f; 2522 i.instr[0] |= temp; 2523 } 2524 else if (i.types[0] == MEM && (i.op.dst[0] == (REG | MEM))) 2525 { 2526 temp = (i.maxq20_op[0].mem)->opcode; 2527 temp &= 0x7f; 2528 i.instr[0] |= temp; 2529 } 2530 else if (i.types[0] == BIT && (i.op.dst[0] == REG)) 2531 { 2532 temp = (i.maxq20_op[0].r_bit)->reg->opcode; 2533 temp &= 0x7f; 2534 i.instr[0] |= temp; 2535 } 2536 else if (i.types[1] == BIT && (i.op.dst[0] == BIT)) 2537 { 2538 temp = (i.maxq20_op[1].r_bit)->bit; 2539 temp = temp << 4; 2540 temp |= i.op.dst[1]; 2541 temp &= 0x7f; 2542 i.instr[0] |= temp; 2543 } 2544 else 2545 { 2546 as_bad (_("Invalid Instruction")); 2547 return 0; 2548 } 2549 } 2550 2551 /* Now for the source register. */ 2552 2553 /* If Source register is already known. The following conditions are 2554 checked: (1) There are no operands (2) If there is only one operand and 2555 it is a flag (3) If the operation is MOVE C,#0/#1 (4) If it is a POP 2556 operation. */ 2557 2558 if (i.operands == 0 || (i.operands == 1 && i.types[0] == FLAG) 2559 || (i.types[0] == FLAG && i.types[1] == IMMBIT) 2560 || !strcmp (i.op.name, "POP") || !strcmp (i.op.name, "POPI")) 2561 i.instr[1] = i.op.src[0]; 2562 2563 else if (i.imm_operands == 1 && ((i.op.src[0] & IMM) == IMM)) 2564 i.instr[1] = i.maxq20_op[this_operand].imms; 2565 2566 else if (i.types[this_operand] == REG && ((i.op.src[0] & REG) == REG)) 2567 i.instr[1] = (char) ((i.maxq20_op[this_operand].reg)->opcode); 2568 2569 else if (i.types[this_operand] == BIT && ((i.op.src[0] & REG) == REG)) 2570 i.instr[1] = (char) (i.maxq20_op[this_operand].r_bit->reg->opcode); 2571 2572 else if (i.types[this_operand] == MEM && ((i.op.src[0] & MEM) == MEM)) 2573 i.instr[1] = (char) ((i.maxq20_op[this_operand].mem)->opcode); 2574 2575 else if (i.types[this_operand] == DATA && ((i.op.src[0] & DATA) == DATA)) 2576 /* This will copy only the lower order bytes into the instruction. The 2577 higher order bytes have already been copied into the prefix register. */ 2578 i.instr[1] = 0; 2579 2580 /* Decoding the source in the case when the second array entry is not 0. 2581 This means that the source register has been divided into two nibbles. */ 2582 2583 else if (i.op.src[1] != 0) 2584 { 2585 /* If the first operand is a accumulator bit then 2586 the first 4 bits will be filled with the bit number. */ 2587 if (i.types[0] == BIT && ((i.op.src[0] & BIT) == BIT)) 2588 { 2589 unsigned char temp = (i.maxq20_op[0].r_bit)->bit; 2590 2591 temp = temp << 4; 2592 temp |= i.op.src[1]; 2593 i.instr[1] = temp; 2594 } 2595 /* In case of MOVE dst.<b>,#1 The first nibble in the source register 2596 has to start with a zero. This is called a ZEROBIT */ 2597 else if (i.types[0] == BIT && ((i.op.src[0] & ZEROBIT) == ZEROBIT)) 2598 { 2599 char temp = (i.maxq20_op[0].r_bit)->bit; 2600 2601 temp = temp << 4; 2602 temp |= i.op.src[1]; 2603 temp &= 0x7f; 2604 i.instr[1] = temp; 2605 } 2606 /* Similarly for a ONEBIT */ 2607 else if (i.types[0] == BIT && ((i.op.src[0] & ONEBIT) == ONEBIT)) 2608 { 2609 char temp = (i.maxq20_op[0].r_bit)->bit; 2610 2611 temp = temp << 4; 2612 temp |= i.op.src[1]; 2613 temp |= 0x80; 2614 i.instr[1] = temp; 2615 } 2616 /* In case the second operand is a register bit (MOVE C,Acc.<b> or MOVE 2617 C,src.<b> */ 2618 else if (i.types[1] == BIT) 2619 { 2620 if (i.op.src[1] == 0 && i.op.src[1] == REG) 2621 i.instr[1] = (i.maxq20_op[1].r_bit)->reg->opcode; 2622 2623 else if (i.op.src[0] == BIT && i.op.src) 2624 { 2625 char temp = (i.maxq20_op[1].r_bit)->bit; 2626 2627 temp = temp << 4; 2628 temp |= i.op.src[1]; 2629 i.instr[1] = temp; 2630 } 2631 } 2632 else 2633 { 2634 as_bad (_("Invalid Instruction")); 2635 return 0; 2636 } 2637 } 2638 return 1; 2639 } 2640 2641 /* This is a function for outputting displacement operands. */ 2642 2643 static void 2644 output_disp (fragS *insn_start_frag, offsetT insn_start_off) 2645 { 2646 char *p; 2647 relax_substateT subtype; 2648 symbolS *sym; 2649 offsetT off; 2650 int diff; 2651 2652 diff = 0; 2653 insn_start_frag = frag_now; 2654 insn_start_off = frag_now_fix (); 2655 2656 switch (i.Instr_Prefix) 2657 { 2658 case LONG_PREFIX: 2659 subtype = EXPLICT_LONG_PREFIX; 2660 break; 2661 case SHORT_PREFIX: 2662 subtype = SHORT_PREFIX; 2663 break; 2664 default: 2665 subtype = NO_PREFIX; 2666 break; 2667 } 2668 2669 /* Its a symbol. Here we end the frag and start the relaxation. Now in our 2670 case there is no need for relaxation. But we do need support for a 2671 prefix operator. Hence we will check whethere is room for 4 bytes ( 2 2672 for prefix + 2 for the current instruction ) Hence if at a particular 2673 time we find out whether the prefix operator is reqd , we shift the 2674 current instruction two places ahead and insert the prefix instruction. */ 2675 frag_grow (2 + 2); 2676 p = frag_more (2); 2677 2678 sym = i.maxq20_op[this_operand].disps->X_add_symbol; 2679 off = i.maxq20_op[this_operand].disps->X_add_number; 2680 2681 if (i.maxq20_op[this_operand].disps->X_add_symbol != NULL && sym && frag_now 2682 && (subtype != EXPLICT_LONG_PREFIX)) 2683 { 2684 /* If in the same frag. */ 2685 if (frag_now == symbol_get_frag (sym)) 2686 { 2687 diff = 2688 ((((expressionS *) symbol_get_value_expression (sym))-> 2689 X_add_number) - insn_start_off); 2690 2691 /* PC points to the next instruction. */ 2692 diff = (diff / MAXQ_OCTETS_PER_BYTE) - 1; 2693 2694 if (diff >= -128 && diff <= 127) 2695 { 2696 i.instr[1] = (char) diff; 2697 2698 /* This will be overwritten later when the symbol is resolved. */ 2699 *p = i.instr[1]; 2700 *(p + 1) = i.instr[0]; 2701 2702 /* No Need to create a FIXUP. */ 2703 return; 2704 } 2705 } 2706 } 2707 2708 /* This will be overwritten later when the symbol is resolved. */ 2709 *p = i.instr[1]; 2710 *(p + 1) = i.instr[0]; 2711 2712 if (i.maxq20_op[this_operand].disps->X_op != O_constant 2713 && i.maxq20_op[this_operand].disps->X_op != O_symbol) 2714 { 2715 /* Handle complex expressions. */ 2716 sym = make_expr_symbol (i.maxq20_op[this_operand].disps); 2717 off = 0; 2718 } 2719 2720 /* Vineet : This has been added for md_estimate_size_before_relax to 2721 estimate the correct size. */ 2722 if (subtype != SHORT_PREFIX) 2723 i.reloc[this_operand] = LONG_PREFIX; 2724 2725 frag_var (rs_machine_dependent, 2, i.reloc[this_operand], subtype, sym, off, p); 2726 } 2727 2728 /* This is a function for outputting displacement operands. */ 2729 2730 static void 2731 output_data (fragS *insn_start_frag, offsetT insn_start_off) 2732 { 2733 char *p; 2734 relax_substateT subtype; 2735 symbolS *sym; 2736 offsetT off; 2737 int diff; 2738 2739 diff = 0; 2740 off = 0; 2741 insn_start_frag = frag_now; 2742 insn_start_off = frag_now_fix (); 2743 2744 subtype = EXPLICT_LONG_PREFIX; 2745 2746 frag_grow (2 + 2); 2747 p = frag_more (2); 2748 2749 sym = i.maxq20_op[this_operand].data; 2750 off = 0; 2751 2752 /* This will be overwritten later when the symbol is resolved. */ 2753 *p = i.instr[1]; 2754 *(p + 1) = i.instr[0]; 2755 2756 if (i.maxq20_op[this_operand].disps->X_op != O_constant 2757 && i.maxq20_op[this_operand].disps->X_op != O_symbol) 2758 /* Handle complex expressions. */ 2759 /* Because data is already in terms of symbol so no 2760 need to convert it from expression to symbol. */ 2761 off = 0; 2762 2763 frag_var (rs_machine_dependent, 2, i.reloc[this_operand], subtype, sym, off, p); 2764 } 2765 2766 static void 2767 output_insn (void) 2768 { 2769 fragS *insn_start_frag; 2770 offsetT insn_start_off; 2771 char *p; 2772 2773 /* Tie dwarf2 debug info to the address at the start of the insn. We can't 2774 do this after the insn has been output as the current frag may have been 2775 closed off. eg. by frag_var. */ 2776 dwarf2_emit_insn (0); 2777 2778 /* To ALign the text section on word. */ 2779 2780 frag_align (1, 0, 1); 2781 2782 /* We initialise the frags for this particular instruction. */ 2783 insn_start_frag = frag_now; 2784 insn_start_off = frag_now_fix (); 2785 2786 /* If there are displacement operators(unresolved) present, then handle 2787 them separately. */ 2788 if (i.disp_operands) 2789 { 2790 output_disp (insn_start_frag, insn_start_off); 2791 return; 2792 } 2793 2794 if (i.data_operands) 2795 { 2796 output_data (insn_start_frag, insn_start_off); 2797 return; 2798 } 2799 2800 /* Check whether the INSERT_BUFFER has to be written. */ 2801 if (strcmp (INSERT_BUFFER, "")) 2802 { 2803 p = frag_more (2); 2804 2805 *p++ = INSERT_BUFFER[1]; 2806 *p = INSERT_BUFFER[0]; 2807 } 2808 2809 /* Check whether the prefix instruction has to be written. */ 2810 if (strcmp (PFX_INSN, "")) 2811 { 2812 p = frag_more (2); 2813 2814 *p++ = PFX_INSN[1]; 2815 *p = PFX_INSN[0]; 2816 } 2817 2818 p = frag_more (2); 2819 /* For Little endian. */ 2820 *p++ = i.instr[1]; 2821 *p = i.instr[0]; 2822 } 2823 2824 static void 2825 make_new_reg_table (void) 2826 { 2827 unsigned long size_pm = sizeof (peripheral_reg_table); 2828 num_of_reg = ARRAY_SIZE (peripheral_reg_table); 2829 2830 new_reg_table = xmalloc (size_pm); 2831 if (new_reg_table == NULL) 2832 as_bad (_("Cannot allocate memory")); 2833 2834 memcpy (new_reg_table, peripheral_reg_table, size_pm); 2835 } 2836 2837 /* pmmain performs the initilizations for the pheripheral modules. */ 2838 2839 static void 2840 pmmain (void) 2841 { 2842 make_new_reg_table (); 2843 return; 2844 } 2845 2846 void 2847 md_begin (void) 2848 { 2849 const char *hash_err = NULL; 2850 int c = 0; 2851 char *p; 2852 const MAXQ20_OPCODE_INFO *optab; 2853 MAXQ20_OPCODES *core_optab; /* For opcodes of the same name. This will 2854 be inserted into the hash table. */ 2855 struct reg *reg_tab; 2856 struct mem_access_syntax const *memsyntab; 2857 struct mem_access *memtab; 2858 struct bit_name *bittab; 2859 2860 /* Initilize pherioipheral modules. */ 2861 pmmain (); 2862 2863 /* Initialise the opcode hash table. */ 2864 op_hash = hash_new (); 2865 2866 optab = op_table; /* Initialise it to the first entry of the 2867 maxq20 operand table. */ 2868 2869 /* Setup for loop. */ 2870 core_optab = xmalloc (sizeof (MAXQ20_OPCODES)); 2871 core_optab->start = optab; 2872 2873 while (1) 2874 { 2875 ++optab; 2876 if (optab->name == NULL || strcmp (optab->name, (optab - 1)->name) != 0) 2877 { 2878 /* different name --> ship out current template list; add to hash 2879 table; & begin anew. */ 2880 2881 core_optab->end = optab; 2882 #ifdef MAXQ10S 2883 if (max_version == bfd_mach_maxq10) 2884 { 2885 if (((optab - 1)->arch == MAXQ10) || ((optab - 1)->arch == MAX)) 2886 { 2887 hash_err = hash_insert (op_hash, 2888 (optab - 1)->name, 2889 (PTR) core_optab); 2890 } 2891 } 2892 else if (max_version == bfd_mach_maxq20) 2893 { 2894 if (((optab - 1)->arch == MAXQ20) || ((optab - 1)->arch == MAX)) 2895 { 2896 #endif 2897 hash_err = hash_insert (op_hash, 2898 (optab - 1)->name, 2899 (PTR) core_optab); 2900 #if MAXQ10S 2901 } 2902 } 2903 else 2904 as_fatal (_("Internal Error: Illegal Architecure specified")); 2905 #endif 2906 if (hash_err) 2907 as_fatal (_("Internal Error: Can't hash %s: %s"), 2908 (optab - 1)->name, hash_err); 2909 2910 if (optab->name == NULL) 2911 break; 2912 core_optab = xmalloc (sizeof (MAXQ20_OPCODES)); 2913 core_optab->start = optab; 2914 } 2915 } 2916 2917 /* Initialise a new register table. */ 2918 reg_hash = hash_new (); 2919 2920 for (reg_tab = system_reg_table; 2921 reg_tab < (system_reg_table + ARRAY_SIZE (system_reg_table)); 2922 reg_tab++) 2923 { 2924 #if MAXQ10S 2925 switch (max_version) 2926 { 2927 case bfd_mach_maxq10: 2928 if ((reg_tab->arch == MAXQ10) || (reg_tab->arch == MAX)) 2929 hash_err = hash_insert (reg_hash, reg_tab->reg_name, (PTR) reg_tab); 2930 break; 2931 2932 case bfd_mach_maxq20: 2933 if ((reg_tab->arch == MAXQ20) || (reg_tab->arch == MAX)) 2934 { 2935 #endif 2936 hash_err = 2937 hash_insert (reg_hash, reg_tab->reg_name, (PTR) reg_tab); 2938 #if MAXQ10S 2939 } 2940 break; 2941 default: 2942 as_fatal (_("Invalid architecture type")); 2943 } 2944 #endif 2945 2946 if (hash_err) 2947 as_fatal (_("Internal Error : Can't Hash %s : %s"), 2948 reg_tab->reg_name, hash_err); 2949 } 2950 2951 /* Pheripheral Registers Entry. */ 2952 for (reg_tab = new_reg_table; 2953 reg_tab < (new_reg_table + num_of_reg - 1); reg_tab++) 2954 { 2955 hash_err = hash_insert (reg_hash, reg_tab->reg_name, (PTR) reg_tab); 2956 2957 if (hash_err) 2958 as_fatal (_("Internal Error : Can't Hash %s : %s"), 2959 reg_tab->reg_name, hash_err); 2960 } 2961 2962 /* Initialise a new memory operand table. */ 2963 mem_hash = hash_new (); 2964 2965 for (memtab = mem_table; 2966 memtab < mem_table + ARRAY_SIZE (mem_table); 2967 memtab++) 2968 { 2969 hash_err = hash_insert (mem_hash, memtab->name, (PTR) memtab); 2970 if (hash_err) 2971 as_fatal (_("Internal Error : Can't Hash %s : %s"), 2972 memtab->name, hash_err); 2973 } 2974 2975 bit_hash = hash_new (); 2976 2977 for (bittab = bit_table; 2978 bittab < bit_table + ARRAY_SIZE (bit_table); 2979 bittab++) 2980 { 2981 hash_err = hash_insert (bit_hash, bittab->name, (PTR) bittab); 2982 if (hash_err) 2983 as_fatal (_("Internal Error : Can't Hash %s : %s"), 2984 bittab->name, hash_err); 2985 } 2986 2987 mem_syntax_hash = hash_new (); 2988 2989 for (memsyntab = mem_access_syntax_table; 2990 memsyntab < mem_access_syntax_table + ARRAY_SIZE (mem_access_syntax_table); 2991 memsyntab++) 2992 { 2993 hash_err = 2994 hash_insert (mem_syntax_hash, memsyntab->name, (PTR) memsyntab); 2995 if (hash_err) 2996 as_fatal (_("Internal Error : Can't Hash %s : %s"), 2997 memsyntab->name, hash_err); 2998 } 2999 3000 /* Initialise the lexical tables,mnemonic chars,operand chars. */ 3001 for (c = 0; c < 256; c++) 3002 { 3003 if (ISDIGIT (c)) 3004 { 3005 digit_chars[c] = c; 3006 mnemonic_chars[c] = c; 3007 operand_chars[c] = c; 3008 register_chars[c] = c; 3009 } 3010 else if (ISLOWER (c)) 3011 { 3012 mnemonic_chars[c] = c; 3013 operand_chars[c] = c; 3014 register_chars[c] = c; 3015 } 3016 else if (ISUPPER (c)) 3017 { 3018 mnemonic_chars[c] = TOLOWER (c); 3019 register_chars[c] = c; 3020 operand_chars[c] = c; 3021 } 3022 3023 if (ISALPHA (c) || ISDIGIT (c)) 3024 { 3025 identifier_chars[c] = c; 3026 } 3027 else if (c > 128) 3028 { 3029 identifier_chars[c] = c; 3030 operand_chars[c] = c; 3031 } 3032 } 3033 3034 /* All the special characters. */ 3035 register_chars['@'] = '@'; 3036 register_chars['+'] = '+'; 3037 register_chars['-'] = '-'; 3038 digit_chars['-'] = '-'; 3039 identifier_chars['_'] = '_'; 3040 identifier_chars['.'] = '.'; 3041 register_chars['['] = '['; 3042 register_chars[']'] = ']'; 3043 operand_chars['_'] = '_'; 3044 operand_chars['#'] = '#'; 3045 mnemonic_chars['['] = '['; 3046 mnemonic_chars[']'] = ']'; 3047 3048 for (p = operand_special_chars; *p != '\0'; p++) 3049 operand_chars[(unsigned char) *p] = (unsigned char) *p; 3050 3051 /* Set the maxq arch type. */ 3052 maxq_target (max_version); 3053 } 3054 3055 /* md_assemble - Parse Instr - Seprate menmonics and operands - lookup the 3056 menmunonic in the operand table - Parse operands and populate the 3057 structure/template - Match the operand with opcode and its validity - 3058 Output Instr. */ 3059 3060 void 3061 md_assemble (char *line) 3062 { 3063 int j; 3064 3065 char mnemonic[MAX_MNEM_SIZE]; 3066 char temp4prev[256]; 3067 static char prev_insn[256]; 3068 3069 /* Initialize globals. */ 3070 memset (&i, '\0', sizeof (i)); 3071 for (j = 0; j < MAX_OPERANDS; j++) 3072 i.reloc[j] = NO_RELOC; 3073 3074 i.prefix = -1; 3075 PFX_INSN[0] = 0; 3076 PFX_INSN[1] = 0; 3077 INSERT_BUFFER[0] = 0; 3078 INSERT_BUFFER[1] = 0; 3079 3080 memcpy (temp4prev, line, strlen (line) + 1); 3081 3082 save_stack_p = save_stack; 3083 3084 line = (char *) parse_insn (line, mnemonic); 3085 if (line == NULL) 3086 return; 3087 3088 line = (char *) parse_operands (line, mnemonic); 3089 if (line == NULL) 3090 return; 3091 3092 /* Next, we find a template that matches the given insn, making sure the 3093 overlap of the given operands types is consistent with the template 3094 operand types. */ 3095 if (!match_template ()) 3096 return; 3097 3098 /* In the MAXQ20, there are certain register combinations, and other 3099 restrictions which are not allowed. We will try to resolve these right 3100 now. */ 3101 if (!match_filters ()) 3102 return; 3103 3104 /* Check for the approprate PFX register. */ 3105 set_prefix (); 3106 pfx_for_imm_val (0); 3107 3108 if (!decode_insn ()) /* decode insn. */ 3109 need_pass_2 = 1; 3110 3111 /* Check for Exlipct PFX instruction. */ 3112 if (PFX_INSN[0] && (strstr (prev_insn, "PFX") || strstr (prev_insn, "pfx"))) 3113 as_warn (_("Ineffective insntruction %s \n"), prev_insn); 3114 3115 memcpy (prev_insn, temp4prev, strlen (temp4prev) + 1); 3116 3117 /* We are ready to output the insn. */ 3118 output_insn (); 3119 } 3120