00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034 #include "sysdep.h"
00035 #include <stdio.h>
00036 #include "ansidecl.h"
00037 #include "bfd.h"
00038 #include "symcat.h"
00039 #include "ip2k-desc.h"
00040 #include "ip2k-opc.h"
00041 #include "opintl.h"
00042 #include "xregex.h"
00043 #include "libiberty.h"
00044 #include "safe-ctype.h"
00045
00046 #undef min
00047 #define min(a,b) ((a) < (b) ? (a) : (b))
00048 #undef max
00049 #define max(a,b) ((a) > (b) ? (a) : (b))
00050
00051 static const char * parse_insn_normal
00052 (CGEN_CPU_DESC, const CGEN_INSN *, const char **, CGEN_FIELDS *);
00053
00054
00055
00056
00057
00058 #define PARSE_FUNC_DECL(name) \
00059 static const char *name (CGEN_CPU_DESC, const char **, int, long *)
00060 #define PARSE_UFUNC_DECL(name) \
00061 static const char *name (CGEN_CPU_DESC, const char **, int, unsigned long *)
00062
00063 PARSE_UFUNC_DECL (parse_fr);
00064 PARSE_UFUNC_DECL (parse_addr16);
00065 PARSE_UFUNC_DECL (parse_addr16_cjp);
00066 PARSE_FUNC_DECL (parse_lit8);
00067 PARSE_UFUNC_DECL (parse_bit3);
00068
00069
00070 static const char *
00071 parse_fr (cd, strp, opindex, valuep)
00072 CGEN_CPU_DESC cd;
00073 const char **strp;
00074 int opindex;
00075 unsigned long *valuep;
00076 {
00077 const char *errmsg;
00078 const char *old_strp;
00079 char *afteroffset;
00080 enum cgen_parse_operand_result result_type;
00081 bfd_vma value;
00082 extern CGEN_KEYWORD ip2k_cgen_opval_register_names;
00083 bfd_vma tempvalue;
00084
00085 old_strp = *strp;
00086 afteroffset = NULL;
00087
00088
00089
00090 if ((strncmp (*strp, "w", 1) == 0) || (strncmp (*strp, "W", 1) == 0))
00091 {
00092 (*strp)++;
00093
00094 if ((strncmp (*strp, ",", 1) == 0) || ISSPACE (**strp))
00095 {
00096
00097
00098 errmsg = _("W keyword invalid in FR operand slot.");
00099 return errmsg;
00100 }
00101 *strp = old_strp;
00102 }
00103
00104
00105 errmsg = cgen_parse_keyword (cd, strp, & ip2k_cgen_opval_register_names,
00106 (long *) valuep);
00107 if (*strp != NULL
00108 && errmsg == NULL)
00109 return errmsg;
00110
00111
00112 afteroffset = strstr (*strp, "(IP)");
00113
00114 if (afteroffset == NULL)
00115
00116 afteroffset = strstr (*strp, "(ip)");
00117
00118 if (afteroffset != NULL)
00119 {
00120 if (afteroffset != *strp)
00121 {
00122
00123 errmsg = _("offset(IP) is not a valid form");
00124 return errmsg;
00125 }
00126 else
00127 {
00128 *strp += 4;
00129 *valuep = 0;
00130 errmsg = NULL;
00131 return errmsg;
00132 }
00133 }
00134
00135
00136
00137
00138
00139 afteroffset = strstr (*strp, "(DP)");
00140
00141 if (afteroffset == NULL)
00142
00143 afteroffset = strstr (*strp, "(dp)");
00144
00145 if (afteroffset != NULL)
00146 {
00147 if (afteroffset == *strp)
00148 {
00149
00150 tempvalue = 0;
00151 errmsg = NULL;
00152 }
00153 else
00154 errmsg = cgen_parse_address (cd, strp, opindex,
00155 BFD_RELOC_IP2K_FR_OFFSET,
00156 & result_type, & tempvalue);
00157
00158 if (errmsg == NULL)
00159 {
00160 if (tempvalue <= 127)
00161 {
00162
00163 *valuep = 0x0100 | tempvalue;
00164 *strp += 4;
00165 return errmsg;
00166 }
00167 else
00168 {
00169
00170
00171 errmsg = _("(DP) offset out of range.");
00172 return errmsg;
00173 }
00174 }
00175 }
00176
00177
00178
00179
00180 afteroffset = strstr (*strp, "(SP)");
00181
00182 if (afteroffset == NULL)
00183
00184 afteroffset = strstr (*strp, "(sp)");
00185
00186 if (afteroffset != NULL)
00187 {
00188 if (afteroffset == *strp)
00189 {
00190
00191 tempvalue = 0;
00192 errmsg = NULL;
00193 }
00194 else
00195 errmsg = cgen_parse_address (cd, strp, opindex,
00196 BFD_RELOC_IP2K_FR_OFFSET,
00197 & result_type, & tempvalue);
00198
00199 if (errmsg == NULL)
00200 {
00201 if (tempvalue <= 127)
00202 {
00203
00204 *valuep = 0x0180 | tempvalue;
00205 *strp += 4;
00206 return errmsg;
00207 }
00208 else
00209 {
00210
00211
00212 errmsg = _("(SP) offset out of range.");
00213 return errmsg;
00214 }
00215 }
00216 }
00217
00218
00219 *strp = old_strp;
00220 errmsg = cgen_parse_address (cd, strp, opindex, BFD_RELOC_IP2K_FR9,
00221 & result_type, & value);
00222 if (errmsg == NULL)
00223 {
00224 *valuep = value;
00225
00226
00227 if (**strp == '(')
00228 errmsg = _("illegal use of parentheses");
00229
00230
00231
00232 else if (result_type == CGEN_PARSE_OPERAND_RESULT_NUMBER)
00233 {
00234 if (value < 0x1 || value > 0xff)
00235 errmsg = _("operand out of range (not between 1 and 255)");
00236 }
00237 }
00238 return errmsg;
00239 }
00240
00241 static const char *
00242 parse_addr16 (cd, strp, opindex, valuep)
00243 CGEN_CPU_DESC cd;
00244 const char **strp;
00245 int opindex;
00246 unsigned long *valuep;
00247 {
00248 const char *errmsg;
00249 enum cgen_parse_operand_result result_type;
00250 bfd_reloc_code_real_type code = BFD_RELOC_NONE;
00251 bfd_vma value;
00252
00253 if (opindex == (CGEN_OPERAND_TYPE) IP2K_OPERAND_ADDR16H)
00254 code = BFD_RELOC_IP2K_HI8DATA;
00255 else if (opindex == (CGEN_OPERAND_TYPE) IP2K_OPERAND_ADDR16L)
00256 code = BFD_RELOC_IP2K_LO8DATA;
00257 else
00258 {
00259
00260 errmsg = _("parse_addr16: invalid opindex.");
00261 return errmsg;
00262 }
00263
00264 errmsg = cgen_parse_address (cd, strp, opindex, code,
00265 & result_type, & value);
00266 if (errmsg == NULL)
00267 {
00268
00269 if (result_type == CGEN_PARSE_OPERAND_RESULT_NUMBER)
00270 {
00271
00272 if (code == BFD_RELOC_IP2K_HI8DATA)
00273 value >>= 8;
00274 else
00275 value &= 0x00FF;
00276 }
00277 *valuep = value;
00278 }
00279
00280 return errmsg;
00281 }
00282
00283
00284 static const char *
00285 parse_addr16_cjp (cd, strp, opindex, valuep)
00286 CGEN_CPU_DESC cd;
00287 const char **strp;
00288 int opindex;
00289 unsigned long *valuep;
00290 {
00291 const char *errmsg;
00292 enum cgen_parse_operand_result result_type;
00293 bfd_reloc_code_real_type code = BFD_RELOC_NONE;
00294 bfd_vma value;
00295
00296 if (opindex == (CGEN_OPERAND_TYPE) IP2K_OPERAND_ADDR16CJP)
00297 code = BFD_RELOC_IP2K_ADDR16CJP;
00298 else if (opindex == (CGEN_OPERAND_TYPE) IP2K_OPERAND_ADDR16P)
00299 code = BFD_RELOC_IP2K_PAGE3;
00300
00301 errmsg = cgen_parse_address (cd, strp, opindex, code,
00302 & result_type, & value);
00303 if (errmsg == NULL)
00304 {
00305 if (result_type == CGEN_PARSE_OPERAND_RESULT_NUMBER)
00306 {
00307 if ((value & 0x1) == 0)
00308 {
00309 if (opindex == (CGEN_OPERAND_TYPE) IP2K_OPERAND_ADDR16CJP)
00310 *valuep = (value >> 1) & 0x1FFF;
00311 else if (opindex == (CGEN_OPERAND_TYPE) IP2K_OPERAND_ADDR16P)
00312 *valuep = (value >> 14) & 0x7;
00313 }
00314 else
00315 errmsg = _("Byte address required. - must be even.");
00316 }
00317 else if (result_type == CGEN_PARSE_OPERAND_RESULT_QUEUED)
00318 {
00319
00320
00321 *valuep = value;
00322 }
00323 else
00324 errmsg = _("cgen_parse_address returned a symbol. Literal required.");
00325 }
00326 return errmsg;
00327 }
00328
00329
00330 static const char *
00331 parse_lit8 (cd, strp, opindex, valuep)
00332 CGEN_CPU_DESC cd;
00333 const char **strp;
00334 int opindex;
00335 long *valuep;
00336 {
00337 const char *errmsg;
00338 enum cgen_parse_operand_result result_type;
00339 bfd_reloc_code_real_type code = BFD_RELOC_NONE;
00340 bfd_vma value;
00341
00342
00343 if (strncmp (*strp, "%bank", 5) == 0)
00344 {
00345 *strp += 5;
00346 code = BFD_RELOC_IP2K_BANK;
00347 }
00348 else if (strncmp (*strp, "%lo8data", 8) == 0)
00349 {
00350 *strp += 8;
00351 code = BFD_RELOC_IP2K_LO8DATA;
00352 }
00353 else if (strncmp (*strp, "%hi8data", 8) == 0)
00354 {
00355 *strp += 8;
00356 code = BFD_RELOC_IP2K_HI8DATA;
00357 }
00358 else if (strncmp (*strp, "%ex8data", 8) == 0)
00359 {
00360 *strp += 8;
00361 code = BFD_RELOC_IP2K_EX8DATA;
00362 }
00363 else if (strncmp (*strp, "%lo8insn", 8) == 0)
00364 {
00365 *strp += 8;
00366 code = BFD_RELOC_IP2K_LO8INSN;
00367 }
00368 else if (strncmp (*strp, "%hi8insn", 8) == 0)
00369 {
00370 *strp += 8;
00371 code = BFD_RELOC_IP2K_HI8INSN;
00372 }
00373
00374
00375
00376 if (code != BFD_RELOC_NONE)
00377 {
00378 errmsg = cgen_parse_address (cd, strp, opindex, code,
00379 & result_type, & value);
00380 if ((errmsg == NULL) &&
00381 (result_type != CGEN_PARSE_OPERAND_RESULT_QUEUED))
00382 errmsg = _("%operator operand is not a symbol");
00383
00384 *valuep = value;
00385 }
00386
00387 else
00388 {
00389 errmsg = cgen_parse_signed_integer (cd, strp, opindex, valuep);
00390
00391
00392 if (errmsg == NULL)
00393 *valuep &= 0xFF;
00394 }
00395
00396 return errmsg;
00397 }
00398
00399 static const char *
00400 parse_bit3 (cd, strp, opindex, valuep)
00401 CGEN_CPU_DESC cd;
00402 const char **strp;
00403 int opindex;
00404 unsigned long *valuep;
00405 {
00406 const char *errmsg;
00407 char mode = 0;
00408 long count = 0;
00409 unsigned long value;
00410
00411 if (strncmp (*strp, "%bit", 4) == 0)
00412 {
00413 *strp += 4;
00414 mode = 1;
00415 }
00416 else if (strncmp (*strp, "%msbbit", 7) == 0)
00417 {
00418 *strp += 7;
00419 mode = 1;
00420 }
00421 else if (strncmp (*strp, "%lsbbit", 7) == 0)
00422 {
00423 *strp += 7;
00424 mode = 2;
00425 }
00426
00427 errmsg = cgen_parse_unsigned_integer (cd, strp, opindex, valuep);
00428 if (errmsg)
00429 return errmsg;
00430
00431 if (mode)
00432 {
00433 value = * valuep;
00434 if (value == 0)
00435 {
00436 errmsg = _("Attempt to find bit index of 0");
00437 return errmsg;
00438 }
00439
00440 if (mode == 1)
00441 {
00442 count = 31;
00443 while ((value & 0x80000000) == 0)
00444 {
00445 count--;
00446 value <<= 1;
00447 }
00448 }
00449 else if (mode == 2)
00450 {
00451 count = 0;
00452 while ((value & 0x00000001) == 0)
00453 {
00454 count++;
00455 value >>= 1;
00456 }
00457 }
00458
00459 *valuep = count;
00460 }
00461
00462 return errmsg;
00463 }
00464
00465
00466
00467
00468 const char * ip2k_cgen_parse_operand
00469 PARAMS ((CGEN_CPU_DESC, int, const char **, CGEN_FIELDS *));
00470
00471
00472
00473
00474
00475
00476
00477
00478
00479
00480
00481
00482
00483
00484 const char *
00485 ip2k_cgen_parse_operand (cd, opindex, strp, fields)
00486 CGEN_CPU_DESC cd;
00487 int opindex;
00488 const char ** strp;
00489 CGEN_FIELDS * fields;
00490 {
00491 const char * errmsg = NULL;
00492
00493 long junk ATTRIBUTE_UNUSED;
00494
00495 switch (opindex)
00496 {
00497 case IP2K_OPERAND_ADDR16CJP :
00498 errmsg = parse_addr16_cjp (cd, strp, IP2K_OPERAND_ADDR16CJP, (unsigned long *) (& fields->f_addr16cjp));
00499 break;
00500 case IP2K_OPERAND_ADDR16H :
00501 errmsg = parse_addr16 (cd, strp, IP2K_OPERAND_ADDR16H, (unsigned long *) (& fields->f_imm8));
00502 break;
00503 case IP2K_OPERAND_ADDR16L :
00504 errmsg = parse_addr16 (cd, strp, IP2K_OPERAND_ADDR16L, (unsigned long *) (& fields->f_imm8));
00505 break;
00506 case IP2K_OPERAND_ADDR16P :
00507 errmsg = parse_addr16_cjp (cd, strp, IP2K_OPERAND_ADDR16P, (unsigned long *) (& fields->f_page3));
00508 break;
00509 case IP2K_OPERAND_BITNO :
00510 errmsg = parse_bit3 (cd, strp, IP2K_OPERAND_BITNO, (unsigned long *) (& fields->f_bitno));
00511 break;
00512 case IP2K_OPERAND_CBIT :
00513 errmsg = cgen_parse_unsigned_integer (cd, strp, IP2K_OPERAND_CBIT, (unsigned long *) (& junk));
00514 break;
00515 case IP2K_OPERAND_DCBIT :
00516 errmsg = cgen_parse_unsigned_integer (cd, strp, IP2K_OPERAND_DCBIT, (unsigned long *) (& junk));
00517 break;
00518 case IP2K_OPERAND_FR :
00519 errmsg = parse_fr (cd, strp, IP2K_OPERAND_FR, (unsigned long *) (& fields->f_reg));
00520 break;
00521 case IP2K_OPERAND_LIT8 :
00522 errmsg = parse_lit8 (cd, strp, IP2K_OPERAND_LIT8, (long *) (& fields->f_imm8));
00523 break;
00524 case IP2K_OPERAND_PABITS :
00525 errmsg = cgen_parse_unsigned_integer (cd, strp, IP2K_OPERAND_PABITS, (unsigned long *) (& junk));
00526 break;
00527 case IP2K_OPERAND_RETI3 :
00528 errmsg = cgen_parse_unsigned_integer (cd, strp, IP2K_OPERAND_RETI3, (unsigned long *) (& fields->f_reti3));
00529 break;
00530 case IP2K_OPERAND_ZBIT :
00531 errmsg = cgen_parse_unsigned_integer (cd, strp, IP2K_OPERAND_ZBIT, (unsigned long *) (& junk));
00532 break;
00533
00534 default :
00535
00536 fprintf (stderr, _("Unrecognized field %d while parsing.\n"), opindex);
00537 abort ();
00538 }
00539
00540 return errmsg;
00541 }
00542
00543 cgen_parse_fn * const ip2k_cgen_parse_handlers[] =
00544 {
00545 parse_insn_normal,
00546 };
00547
00548 void
00549 ip2k_cgen_init_asm (cd)
00550 CGEN_CPU_DESC cd;
00551 {
00552 ip2k_cgen_init_opcode_table (cd);
00553 ip2k_cgen_init_ibld_table (cd);
00554 cd->parse_handlers = & ip2k_cgen_parse_handlers[0];
00555 cd->parse_operand = ip2k_cgen_parse_operand;
00556 }
00557
00558
00559
00560
00561
00562
00563
00564
00565
00566
00567
00568
00569
00570
00571 char *
00572 ip2k_cgen_build_insn_regex (CGEN_INSN *insn)
00573 {
00574 CGEN_OPCODE *opc = (CGEN_OPCODE *) CGEN_INSN_OPCODE (insn);
00575 const char *mnem = CGEN_INSN_MNEMONIC (insn);
00576 char rxbuf[CGEN_MAX_RX_ELEMENTS];
00577 char *rx = rxbuf;
00578 const CGEN_SYNTAX_CHAR_TYPE *syn;
00579 int reg_err;
00580
00581 syn = CGEN_SYNTAX_STRING (CGEN_OPCODE_SYNTAX (opc));
00582
00583
00584 if (! CGEN_SYNTAX_MNEMONIC_P (* syn))
00585 return _("missing mnemonic in syntax string");
00586 ++syn;
00587
00588
00589
00590
00591
00592
00593
00594 for (; *mnem; mnem++)
00595 {
00596 char c = *mnem;
00597
00598 if (ISALPHA (c))
00599 {
00600 *rx++ = '[';
00601 *rx++ = TOLOWER (c);
00602 *rx++ = TOUPPER (c);
00603 *rx++ = ']';
00604 }
00605 else
00606 *rx++ = c;
00607 }
00608
00609
00610 for(; * syn != 0 && rx <= rxbuf + (CGEN_MAX_RX_ELEMENTS - 7 - 4); ++syn)
00611 {
00612 if (CGEN_SYNTAX_CHAR_P (* syn))
00613 {
00614 char c = CGEN_SYNTAX_CHAR (* syn);
00615
00616 switch (c)
00617 {
00618
00619 case '.': case '[': case '\\':
00620 case '*': case '^': case '$':
00621
00622 #ifdef CGEN_ESCAPE_EXTENDED_REGEX
00623 case '?': case '{': case '}':
00624 case '(': case ')': case '*':
00625 case '|': case '+': case ']':
00626 #endif
00627 *rx++ = '\\';
00628 *rx++ = c;
00629 break;
00630
00631 default:
00632 if (ISALPHA (c))
00633 {
00634 *rx++ = '[';
00635 *rx++ = TOLOWER (c);
00636 *rx++ = TOUPPER (c);
00637 *rx++ = ']';
00638 }
00639 else
00640 *rx++ = c;
00641 break;
00642 }
00643 }
00644 else
00645 {
00646
00647 *rx++ = '.';
00648 *rx++ = '*';
00649 }
00650 }
00651
00652
00653 * rx++ = '[';
00654 * rx++ = ' ';
00655 * rx++ = '\t';
00656 * rx++ = ']';
00657 * rx++ = '*';
00658
00659
00660 * rx++ = '$';
00661 * rx = '\0';
00662
00663 CGEN_INSN_RX (insn) = xmalloc (sizeof (regex_t));
00664 reg_err = regcomp ((regex_t *) CGEN_INSN_RX (insn), rxbuf, REG_NOSUB);
00665
00666 if (reg_err == 0)
00667 return NULL;
00668 else
00669 {
00670 static char msg[80];
00671
00672 regerror (reg_err, (regex_t *) CGEN_INSN_RX (insn), msg, 80);
00673 regfree ((regex_t *) CGEN_INSN_RX (insn));
00674 free (CGEN_INSN_RX (insn));
00675 (CGEN_INSN_RX (insn)) = NULL;
00676 return msg;
00677 }
00678 }
00679
00680
00681
00682
00683
00684
00685
00686
00687
00688
00689
00690
00691
00692
00693
00694 static const char *
00695 parse_insn_normal (CGEN_CPU_DESC cd,
00696 const CGEN_INSN *insn,
00697 const char **strp,
00698 CGEN_FIELDS *fields)
00699 {
00700
00701 const CGEN_SYNTAX *syntax = CGEN_INSN_SYNTAX (insn);
00702 const char *str = *strp;
00703 const char *errmsg;
00704 const char *p;
00705 const CGEN_SYNTAX_CHAR_TYPE * syn;
00706 #ifdef CGEN_MNEMONIC_OPERANDS
00707
00708 int past_opcode_p;
00709 #endif
00710
00711
00712
00713
00714
00715 p = CGEN_INSN_MNEMONIC (insn);
00716 while (*p && TOLOWER (*p) == TOLOWER (*str))
00717 ++p, ++str;
00718
00719 if (* p)
00720 return _("unrecognized instruction");
00721
00722 #ifndef CGEN_MNEMONIC_OPERANDS
00723 if (* str && ! ISSPACE (* str))
00724 return _("unrecognized instruction");
00725 #endif
00726
00727 CGEN_INIT_PARSE (cd);
00728 cgen_init_parse_operand (cd);
00729 #ifdef CGEN_MNEMONIC_OPERANDS
00730 past_opcode_p = 0;
00731 #endif
00732
00733
00734
00735 syn = CGEN_SYNTAX_STRING (syntax);
00736
00737
00738 if (! CGEN_SYNTAX_MNEMONIC_P (* syn))
00739 abort ();
00740
00741 ++syn;
00742
00743 while (* syn != 0)
00744 {
00745
00746 if (CGEN_SYNTAX_CHAR_P (* syn))
00747 {
00748
00749
00750
00751
00752 if (TOLOWER (*str) == TOLOWER (CGEN_SYNTAX_CHAR (* syn)))
00753 {
00754 #ifdef CGEN_MNEMONIC_OPERANDS
00755 if (CGEN_SYNTAX_CHAR(* syn) == ' ')
00756 past_opcode_p = 1;
00757 #endif
00758 ++ syn;
00759 ++ str;
00760 }
00761 else if (*str)
00762 {
00763
00764 static char msg [80];
00765
00766
00767 sprintf (msg, _("syntax error (expected char `%c', found `%c')"),
00768 CGEN_SYNTAX_CHAR(*syn), *str);
00769 return msg;
00770 }
00771 else
00772 {
00773
00774 static char msg [80];
00775
00776
00777 sprintf (msg, _("syntax error (expected char `%c', found end of instruction)"),
00778 CGEN_SYNTAX_CHAR(*syn));
00779 return msg;
00780 }
00781 continue;
00782 }
00783
00784
00785 errmsg = cd->parse_operand (cd, CGEN_SYNTAX_FIELD (*syn),
00786 &str, fields);
00787 if (errmsg)
00788 return errmsg;
00789
00790
00791 ++ syn;
00792 }
00793
00794
00795 if (* syn == 0)
00796 {
00797
00798
00799
00800
00801 while (ISSPACE (* str))
00802 ++ str;
00803
00804 if (* str != '\0')
00805 return _("junk at end of line");
00806
00807 return NULL;
00808 }
00809
00810
00811 return _("unrecognized instruction");
00812 }
00813
00814
00815
00816
00817
00818
00819
00820
00821
00822
00823
00824
00825
00826
00827
00828
00829
00830
00831
00832
00833
00834
00835 const CGEN_INSN *
00836 ip2k_cgen_assemble_insn (CGEN_CPU_DESC cd,
00837 const char *str,
00838 CGEN_FIELDS *fields,
00839 CGEN_INSN_BYTES_PTR buf,
00840 char **errmsg)
00841 {
00842 const char *start;
00843 CGEN_INSN_LIST *ilist;
00844 const char *parse_errmsg = NULL;
00845 const char *insert_errmsg = NULL;
00846 int recognized_mnemonic = 0;
00847
00848
00849 while (ISSPACE (* str))
00850 ++ str;
00851
00852
00853
00854 ilist = CGEN_ASM_LOOKUP_INSN (cd, str);
00855
00856
00857 start = str;
00858 for ( ; ilist != NULL ; ilist = CGEN_ASM_NEXT_INSN (ilist))
00859 {
00860 const CGEN_INSN *insn = ilist->insn;
00861 recognized_mnemonic = 1;
00862
00863 #ifdef CGEN_VALIDATE_INSN_SUPPORTED
00864
00865
00866
00867 if (! ip2k_cgen_insn_supported (cd, insn))
00868 continue;
00869 #endif
00870
00871
00872
00873 if (CGEN_INSN_ATTR_VALUE (insn, CGEN_INSN_RELAXED) != 0)
00874 continue;
00875
00876 str = start;
00877
00878
00879 if (CGEN_INSN_RX (insn) != NULL &&
00880 regexec ((regex_t *) CGEN_INSN_RX (insn), str, 0, NULL, 0) == REG_NOMATCH)
00881 continue;
00882
00883
00884 CGEN_FIELDS_BITSIZE (fields) = CGEN_INSN_BITSIZE (insn);
00885
00886 parse_errmsg = CGEN_PARSE_FN (cd, insn) (cd, insn, & str, fields);
00887 if (parse_errmsg != NULL)
00888 continue;
00889
00890
00891 insert_errmsg = CGEN_INSERT_FN (cd, insn) (cd, insn, fields, buf,
00892 (bfd_vma) 0);
00893 if (insert_errmsg != NULL)
00894 continue;
00895
00896
00897
00898 return insn;
00899 }
00900
00901 {
00902 static char errbuf[150];
00903 #ifdef CGEN_VERBOSE_ASSEMBLER_ERRORS
00904 const char *tmp_errmsg;
00905
00906
00907
00908 tmp_errmsg = (insert_errmsg ? insert_errmsg :
00909 parse_errmsg ? parse_errmsg :
00910 recognized_mnemonic ?
00911 _("unrecognized form of instruction") :
00912 _("unrecognized instruction"));
00913
00914 if (strlen (start) > 50)
00915
00916 sprintf (errbuf, "%s `%.50s...'", tmp_errmsg, start);
00917 else
00918
00919 sprintf (errbuf, "%s `%.50s'", tmp_errmsg, start);
00920 #else
00921 if (strlen (start) > 50)
00922
00923 sprintf (errbuf, _("bad instruction `%.50s...'"), start);
00924 else
00925
00926 sprintf (errbuf, _("bad instruction `%.50s'"), start);
00927 #endif
00928
00929 *errmsg = errbuf;
00930 return NULL;
00931 }
00932 }
00933
00934 #if 0
00935
00936
00937
00938
00939
00940
00941
00942
00943 void
00944 ip2k_cgen_asm_hash_keywords (CGEN_CPU_DESC cd, CGEN_KEYWORD *opvals)
00945 {
00946 CGEN_KEYWORD_SEARCH search = cgen_keyword_search_init (opvals, NULL);
00947 const CGEN_KEYWORD_ENTRY * ke;
00948
00949 while ((ke = cgen_keyword_search_next (& search)) != NULL)
00950 {
00951 #if 0
00952 if (! ip2k_cgen_opval_supported (ke))
00953 continue;
00954 #endif
00955 cgen_asm_record_register (cd, ke->name, ke->value);
00956 }
00957 }
00958
00959 #endif