1/* macro.c - macro support for gas 2 Copyright 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 3 2004, 2005, 2006 Free Software Foundation, Inc. 4 5 Written by Steve and Judy Chamberlain of Cygnus Support, 6 sac@cygnus.com 7 8 This file is part of GAS, the GNU Assembler. 9 10 GAS is free software; you can redistribute it and/or modify 11 it under the terms of the GNU General Public License as published by 12 the Free Software Foundation; either version 2, or (at your option) 13 any later version. 14 15 GAS is distributed in the hope that it will be useful, 16 but WITHOUT ANY WARRANTY; without even the implied warranty of 17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 GNU General Public License for more details. 19 20 You should have received a copy of the GNU General Public License 21 along with GAS; see the file COPYING. If not, write to the Free 22 Software Foundation, 51 Franklin Street - Fifth Floor, Boston, MA 23 02110-1301, USA. */ 24 25#include "as.h" 26#include "safe-ctype.h" 27#include "sb.h" 28#include "macro.h" 29 30/* The routines in this file handle macro definition and expansion. 31 They are called by gas. */ 32 33/* Internal functions. */ 34 35static int get_token (int, sb *, sb *); 36static int getstring (int, sb *, sb *); 37static int get_any_string (int, sb *, sb *); 38static formal_entry *new_formal (void); 39static void del_formal (formal_entry *); 40static int do_formals (macro_entry *, int, sb *); 41static int get_apost_token (int, sb *, sb *, int); 42static int sub_actual (int, sb *, sb *, struct hash_control *, int, sb *, int); 43static const char *macro_expand_body 44 (sb *, sb *, formal_entry *, struct hash_control *, const macro_entry *); 45static const char *macro_expand (int, sb *, macro_entry *, sb *); 46static void free_macro(macro_entry *); 47 48#define ISWHITE(x) ((x) == ' ' || (x) == '\t') 49 50#define ISSEP(x) \ 51 ((x) == ' ' || (x) == '\t' || (x) == ',' || (x) == '"' || (x) == ';' \ 52 || (x) == ')' || (x) == '(' \ 53 || ((macro_alternate || macro_mri) && ((x) == '<' || (x) == '>'))) 54 55#define ISBASE(x) \ 56 ((x) == 'b' || (x) == 'B' \ 57 || (x) == 'q' || (x) == 'Q' \ 58 || (x) == 'h' || (x) == 'H' \ 59 || (x) == 'd' || (x) == 'D') 60 61/* The macro hash table. */ 62 63struct hash_control *macro_hash; 64 65/* Whether any macros have been defined. */ 66 67int macro_defined; 68 69/* Whether we are in alternate syntax mode. */ 70 71static int macro_alternate; 72 73/* Whether we are in MRI mode. */ 74 75static int macro_mri; 76 77/* Whether we should strip '@' characters. */ 78 79static int macro_strip_at; 80 81/* Function to use to parse an expression. */ 82 83static int (*macro_expr) (const char *, int, sb *, int *); 84 85/* Number of macro expansions that have been done. */ 86 87static int macro_number; 88 89/* Initialize macro processing. */ 90 91void 92macro_init (int alternate, int mri, int strip_at, 93 int (*expr) (const char *, int, sb *, int *)) 94{ 95 macro_hash = hash_new (); 96 macro_defined = 0; 97 macro_alternate = alternate; 98 macro_mri = mri; 99 macro_strip_at = strip_at; 100 macro_expr = expr; 101} 102 103/* Switch in and out of alternate mode on the fly. */ 104 105void 106macro_set_alternate (int alternate) 107{ 108 macro_alternate = alternate; 109} 110 111/* Switch in and out of MRI mode on the fly. */ 112 113void 114macro_mri_mode (int mri) 115{ 116 macro_mri = mri; 117} 118 119/* Read input lines till we get to a TO string. 120 Increase nesting depth if we get a FROM string. 121 Put the results into sb at PTR. 122 FROM may be NULL (or will be ignored) if TO is "ENDR". 123 Add a new input line to an sb using GET_LINE. 124 Return 1 on success, 0 on unexpected EOF. */ 125 126int 127buffer_and_nest (const char *from, const char *to, sb *ptr, 128 int (*get_line) (sb *)) 129{ 130 int from_len; 131 int to_len = strlen (to); 132 int depth = 1; 133 int line_start = ptr->len; 134 135 int more = get_line (ptr); 136 137 if (to_len == 4 && strcasecmp(to, "ENDR") == 0) 138 { 139 from = NULL; 140 from_len = 0; 141 } 142 else 143 from_len = strlen (from); 144 145 while (more) 146 { 147 /* Try to find the first pseudo op on the line. */ 148 int i = line_start; 149 150 /* With normal syntax we can suck what we want till we get 151 to the dot. With the alternate, labels have to start in 152 the first column, since we can't tell what's a label and 153 what's a pseudoop. */ 154 155 if (! LABELS_WITHOUT_COLONS) 156 { 157 /* Skip leading whitespace. */ 158 while (i < ptr->len && ISWHITE (ptr->ptr[i])) 159 i++; 160 } 161 162 for (;;) 163 { 164 /* Skip over a label, if any. */ 165 if (i >= ptr->len || ! is_name_beginner (ptr->ptr[i])) 166 break; 167 i++; 168 while (i < ptr->len && is_part_of_name (ptr->ptr[i])) 169 i++; 170 if (i < ptr->len && is_name_ender (ptr->ptr[i])) 171 i++; 172 if (LABELS_WITHOUT_COLONS) 173 break; 174 /* Skip whitespace. */ 175 while (i < ptr->len && ISWHITE (ptr->ptr[i])) 176 i++; 177 /* Check for the colon. */ 178 if (i >= ptr->len || ptr->ptr[i] != ':') 179 { 180 i = line_start; 181 break; 182 } 183 i++; 184 line_start = i; 185 } 186 187 /* Skip trailing whitespace. */ 188 while (i < ptr->len && ISWHITE (ptr->ptr[i])) 189 i++; 190 191 if (i < ptr->len && (ptr->ptr[i] == '.' 192 || NO_PSEUDO_DOT 193 || macro_mri)) 194 { 195 if (! flag_m68k_mri && ptr->ptr[i] == '.') 196 i++; 197 if (from == NULL 198 && strncasecmp (ptr->ptr + i, "IRPC", from_len = 4) != 0 199 && strncasecmp (ptr->ptr + i, "IRP", from_len = 3) != 0 200 && strncasecmp (ptr->ptr + i, "IREPC", from_len = 5) != 0 201 && strncasecmp (ptr->ptr + i, "IREP", from_len = 4) != 0 202 && strncasecmp (ptr->ptr + i, "REPT", from_len = 4) != 0 203 && strncasecmp (ptr->ptr + i, "REP", from_len = 3) != 0) 204 from_len = 0; 205 if ((from != NULL 206 ? strncasecmp (ptr->ptr + i, from, from_len) == 0 207 : from_len > 0) 208 && (ptr->len == (i + from_len) 209 || ! (is_part_of_name (ptr->ptr[i + from_len]) 210 || is_name_ender (ptr->ptr[i + from_len])))) 211 depth++; 212 if (strncasecmp (ptr->ptr + i, to, to_len) == 0 213 && (ptr->len == (i + to_len) 214 || ! (is_part_of_name (ptr->ptr[i + to_len]) 215 || is_name_ender (ptr->ptr[i + to_len])))) 216 { 217 depth--; 218 if (depth == 0) 219 { 220 /* Reset the string to not include the ending rune. */ 221 ptr->len = line_start; 222 break; 223 } 224 } 225 } 226 227 /* Add the original end-of-line char to the end and keep running. */ 228 sb_add_char (ptr, more); 229 line_start = ptr->len; 230 more = get_line (ptr); 231 } 232 233 /* Return 1 on success, 0 on unexpected EOF. */ 234 return depth == 0; 235} 236 237/* Pick up a token. */ 238 239static int 240get_token (int idx, sb *in, sb *name) 241{ 242 if (idx < in->len 243 && is_name_beginner (in->ptr[idx])) 244 { 245 sb_add_char (name, in->ptr[idx++]); 246 while (idx < in->len 247 && is_part_of_name (in->ptr[idx])) 248 { 249 sb_add_char (name, in->ptr[idx++]); 250 } 251 if (idx < in->len 252 && is_name_ender (in->ptr[idx])) 253 { 254 sb_add_char (name, in->ptr[idx++]); 255 } 256 } 257 /* Ignore trailing &. */ 258 if (macro_alternate && idx < in->len && in->ptr[idx] == '&') 259 idx++; 260 return idx; 261} 262 263/* Pick up a string. */ 264 265static int 266getstring (int idx, sb *in, sb *acc) 267{ 268 while (idx < in->len 269 && (in->ptr[idx] == '"' 270 || (in->ptr[idx] == '<' && (macro_alternate || macro_mri)) 271 || (in->ptr[idx] == '\'' && macro_alternate))) 272 { 273 if (in->ptr[idx] == '<') 274 { 275 int nest = 0; 276 idx++; 277 while ((in->ptr[idx] != '>' || nest) 278 && idx < in->len) 279 { 280 if (in->ptr[idx] == '!') 281 { 282 idx++; 283 sb_add_char (acc, in->ptr[idx++]); 284 } 285 else 286 { 287 if (in->ptr[idx] == '>') 288 nest--; 289 if (in->ptr[idx] == '<') 290 nest++; 291 sb_add_char (acc, in->ptr[idx++]); 292 } 293 } 294 idx++; 295 } 296 else if (in->ptr[idx] == '"' || in->ptr[idx] == '\'') 297 { 298 char tchar = in->ptr[idx]; 299 int escaped = 0; 300 301 idx++; 302 303 while (idx < in->len) 304 { 305 if (in->ptr[idx - 1] == '\\') 306 escaped ^= 1; 307 else 308 escaped = 0; 309 310 if (macro_alternate && in->ptr[idx] == '!') 311 { 312 idx ++; 313 314 sb_add_char (acc, in->ptr[idx]); 315 316 idx ++; 317 } 318 else if (escaped && in->ptr[idx] == tchar) 319 { 320 sb_add_char (acc, tchar); 321 idx ++; 322 } 323 else 324 { 325 if (in->ptr[idx] == tchar) 326 { 327 idx ++; 328 329 if (idx >= in->len || in->ptr[idx] != tchar) 330 break; 331 } 332 333 sb_add_char (acc, in->ptr[idx]); 334 idx ++; 335 } 336 } 337 } 338 } 339 340 return idx; 341} 342 343/* Fetch string from the input stream, 344 rules: 345 'Bxyx<whitespace> -> return 'Bxyza 346 %<expr> -> return string of decimal value of <expr> 347 "string" -> return string 348 (string) -> return (string-including-whitespaces) 349 xyx<whitespace> -> return xyz. */ 350 351static int 352get_any_string (int idx, sb *in, sb *out) 353{ 354 sb_reset (out); 355 idx = sb_skip_white (idx, in); 356 357 if (idx < in->len) 358 { 359 if (in->len > idx + 2 && in->ptr[idx + 1] == '\'' && ISBASE (in->ptr[idx])) 360 { 361 while (!ISSEP (in->ptr[idx])) 362 sb_add_char (out, in->ptr[idx++]); 363 } 364 else if (in->ptr[idx] == '%' && macro_alternate) 365 { 366 int val; 367 char buf[20]; 368 369 /* Turns the next expression into a string. */ 370 /* xgettext: no-c-format */ 371 idx = (*macro_expr) (_("% operator needs absolute expression"), 372 idx + 1, 373 in, 374 &val); 375 sprintf (buf, "%d", val); 376 sb_add_string (out, buf); 377 } 378 else if (in->ptr[idx] == '"' 379 || (in->ptr[idx] == '<' && (macro_alternate || macro_mri)) 380 || (macro_alternate && in->ptr[idx] == '\'')) 381 { 382 if (macro_alternate && ! macro_strip_at && in->ptr[idx] != '<') 383 { 384 /* Keep the quotes. */ 385 sb_add_char (out, '"'); 386 idx = getstring (idx, in, out); 387 sb_add_char (out, '"'); 388 } 389 else 390 { 391 idx = getstring (idx, in, out); 392 } 393 } 394 else 395 { 396 char *br_buf = xmalloc(1); 397 char *in_br = br_buf; 398 399 *in_br = '\0'; 400 while (idx < in->len 401 && (*in_br 402 || (in->ptr[idx] != ' ' 403 && in->ptr[idx] != '\t')) 404 && in->ptr[idx] != ',' 405 && (in->ptr[idx] != '<' 406 || (! macro_alternate && ! macro_mri))) 407 { 408 char tchar = in->ptr[idx]; 409 410 switch (tchar) 411 { 412 case '"': 413 case '\'': 414 sb_add_char (out, in->ptr[idx++]); 415 while (idx < in->len 416 && in->ptr[idx] != tchar) 417 sb_add_char (out, in->ptr[idx++]); 418 if (idx == in->len) 419 return idx; 420 break; 421 case '(': 422 case '[': 423 if (in_br > br_buf) 424 --in_br; 425 else 426 { 427 br_buf = xmalloc(strlen(in_br) + 2); 428 strcpy(br_buf + 1, in_br); 429 free(in_br); 430 in_br = br_buf; 431 } 432 *in_br = tchar; 433 break; 434 case ')': 435 if (*in_br == '(') 436 ++in_br; 437 break; 438 case ']': 439 if (*in_br == '[') 440 ++in_br; 441 break; 442 } 443 sb_add_char (out, tchar); 444 ++idx; 445 } 446 free(br_buf); 447 } 448 } 449 450 return idx; 451} 452 453/* Allocate a new formal. */ 454 455static formal_entry * 456new_formal (void) 457{ 458 formal_entry *formal; 459 460 formal = xmalloc (sizeof (formal_entry)); 461 462 sb_new (&formal->name); 463 sb_new (&formal->def); 464 sb_new (&formal->actual); 465 formal->next = NULL; 466 formal->type = FORMAL_OPTIONAL; 467 return formal; 468} 469 470/* Free a formal. */ 471 472static void 473del_formal (formal_entry *formal) 474{ 475 sb_kill (&formal->actual); 476 sb_kill (&formal->def); 477 sb_kill (&formal->name); 478 free (formal); 479} 480 481/* Pick up the formal parameters of a macro definition. */ 482 483static int 484do_formals (macro_entry *macro, int idx, sb *in) 485{ 486 formal_entry **p = ¯o->formals; 487 const char *name; 488 489 idx = sb_skip_white (idx, in); 490 while (idx < in->len) 491 { 492 formal_entry *formal = new_formal (); 493 int cidx; 494 495 idx = get_token (idx, in, &formal->name); 496 if (formal->name.len == 0) 497 { 498 if (macro->formal_count) 499 --idx; 500 break; 501 } 502 idx = sb_skip_white (idx, in); 503 /* This is a formal. */ 504 name = sb_terminate (&formal->name); 505 if (! macro_mri 506 && idx < in->len 507 && in->ptr[idx] == ':' 508 && (! is_name_beginner (':') 509 || idx + 1 >= in->len 510 || ! is_part_of_name (in->ptr[idx + 1]))) 511 { 512 /* Got a qualifier. */ 513 sb qual; 514 515 sb_new (&qual); 516 idx = get_token (sb_skip_white (idx + 1, in), in, &qual); 517 sb_terminate (&qual); 518 if (qual.len == 0) 519 as_bad_where (macro->file, 520 macro->line, 521 _("Missing parameter qualifier for `%s' in macro `%s'"), 522 name, 523 macro->name); 524 else if (strcmp (qual.ptr, "req") == 0) 525 formal->type = FORMAL_REQUIRED; 526 else if (strcmp (qual.ptr, "vararg") == 0) 527 formal->type = FORMAL_VARARG; 528 else 529 as_bad_where (macro->file, 530 macro->line, 531 _("`%s' is not a valid parameter qualifier for `%s' in macro `%s'"), 532 qual.ptr, 533 name, 534 macro->name); 535 sb_kill (&qual); 536 idx = sb_skip_white (idx, in); 537 } 538 if (idx < in->len && in->ptr[idx] == '=') 539 { 540 /* Got a default. */ 541 idx = get_any_string (idx + 1, in, &formal->def); 542 idx = sb_skip_white (idx, in); 543 if (formal->type == FORMAL_REQUIRED) 544 { 545 sb_reset (&formal->def); 546 as_warn_where (macro->file, 547 macro->line, 548 _("Pointless default value for required parameter `%s' in macro `%s'"), 549 name, 550 macro->name); 551 } 552 } 553 554 /* Add to macro's hash table. */ 555 if (! hash_find (macro->formal_hash, name)) 556 hash_jam (macro->formal_hash, name, formal); 557 else 558 as_bad_where (macro->file, 559 macro->line, 560 _("A parameter named `%s' already exists for macro `%s'"), 561 name, 562 macro->name); 563 564 formal->index = macro->formal_count++; 565 *p = formal; 566 p = &formal->next; 567 if (formal->type == FORMAL_VARARG) 568 break; 569 cidx = idx; 570 idx = sb_skip_comma (idx, in); 571 if (idx != cidx && idx >= in->len) 572 { 573 idx = cidx; 574 break; 575 } 576 } 577 578 if (macro_mri) 579 { 580 formal_entry *formal = new_formal (); 581 582 /* Add a special NARG formal, which macro_expand will set to the 583 number of arguments. */ 584 /* The same MRI assemblers which treat '@' characters also use 585 the name $NARG. At least until we find an exception. */ 586 if (macro_strip_at) 587 name = "$NARG"; 588 else 589 name = "NARG"; 590 591 sb_add_string (&formal->name, name); 592 593 /* Add to macro's hash table. */ 594 if (hash_find (macro->formal_hash, name)) 595 as_bad_where (macro->file, 596 macro->line, 597 _("Reserved word `%s' used as parameter in macro `%s'"), 598 name, 599 macro->name); 600 hash_jam (macro->formal_hash, name, formal); 601 602 formal->index = NARG_INDEX; 603 *p = formal; 604 } 605 606 return idx; 607} 608 609/* Define a new macro. Returns NULL on success, otherwise returns an 610 error message. If NAMEP is not NULL, *NAMEP is set to the name of 611 the macro which was defined. */ 612 613const char * 614define_macro (int idx, sb *in, sb *label, 615 int (*get_line) (sb *), 616 char *file, unsigned int line, 617 const char **namep) 618{ 619 macro_entry *macro; 620 sb name; 621 const char *error = NULL; 622 623 macro = (macro_entry *) xmalloc (sizeof (macro_entry)); 624 sb_new (¯o->sub); 625 sb_new (&name); 626 macro->file = file; 627 macro->line = line; 628 629 macro->formal_count = 0; 630 macro->formals = 0; 631 macro->formal_hash = hash_new (); 632 633 idx = sb_skip_white (idx, in); 634 if (! buffer_and_nest ("MACRO", "ENDM", ¯o->sub, get_line)) 635 error = _("unexpected end of file in macro `%s' definition"); 636 if (label != NULL && label->len != 0) 637 { 638 sb_add_sb (&name, label); 639 macro->name = sb_terminate (&name); 640 if (idx < in->len && in->ptr[idx] == '(') 641 { 642 /* It's the label: MACRO (formals,...) sort */ 643 idx = do_formals (macro, idx + 1, in); 644 if (idx < in->len && in->ptr[idx] == ')') 645 idx = sb_skip_white (idx + 1, in); 646 else if (!error) 647 error = _("missing `)' after formals in macro definition `%s'"); 648 } 649 else 650 { 651 /* It's the label: MACRO formals,... sort */ 652 idx = do_formals (macro, idx, in); 653 } 654 } 655 else 656 { 657 int cidx; 658 659 idx = get_token (idx, in, &name); 660 macro->name = sb_terminate (&name); 661 if (name.len == 0) 662 error = _("Missing macro name"); 663 cidx = sb_skip_white (idx, in); 664 idx = sb_skip_comma (cidx, in); 665 if (idx == cidx || idx < in->len) 666 idx = do_formals (macro, idx, in); 667 else 668 idx = cidx; 669 } 670 if (!error && idx < in->len) 671 error = _("Bad parameter list for macro `%s'"); 672 673 /* And stick it in the macro hash table. */ 674 for (idx = 0; idx < name.len; idx++) 675 name.ptr[idx] = TOLOWER (name.ptr[idx]); 676 if (hash_find (macro_hash, macro->name)) 677 error = _("Macro `%s' was already defined"); 678 if (!error) 679 error = hash_jam (macro_hash, macro->name, (PTR) macro); 680 681 if (namep != NULL) 682 *namep = macro->name; 683 684 if (!error) 685 macro_defined = 1; 686 else 687 free_macro (macro); 688 689 return error; 690} 691 692/* Scan a token, and then skip KIND. */ 693 694static int 695get_apost_token (int idx, sb *in, sb *name, int kind) 696{ 697 idx = get_token (idx, in, name); 698 if (idx < in->len 699 && in->ptr[idx] == kind 700 && (! macro_mri || macro_strip_at) 701 && (! macro_strip_at || kind == '@')) 702 idx++; 703 return idx; 704} 705 706/* Substitute the actual value for a formal parameter. */ 707 708static int 709sub_actual (int start, sb *in, sb *t, struct hash_control *formal_hash, 710 int kind, sb *out, int copyifnotthere) 711{ 712 int src; 713 formal_entry *ptr; 714 715 src = get_apost_token (start, in, t, kind); 716 /* See if it's in the macro's hash table, unless this is 717 macro_strip_at and kind is '@' and the token did not end in '@'. */ 718 if (macro_strip_at 719 && kind == '@' 720 && (src == start || in->ptr[src - 1] != '@')) 721 ptr = NULL; 722 else 723 ptr = (formal_entry *) hash_find (formal_hash, sb_terminate (t)); 724 if (ptr) 725 { 726 if (ptr->actual.len) 727 { 728 sb_add_sb (out, &ptr->actual); 729 } 730 else 731 { 732 sb_add_sb (out, &ptr->def); 733 } 734 } 735 else if (kind == '&') 736 { 737 /* Doing this permits people to use & in macro bodies. */ 738 sb_add_char (out, '&'); 739 sb_add_sb (out, t); 740 } 741 else if (copyifnotthere) 742 { 743 sb_add_sb (out, t); 744 } 745 else 746 { 747 sb_add_char (out, '\\'); 748 sb_add_sb (out, t); 749 } 750 return src; 751} 752 753/* Expand the body of a macro. */ 754 755static const char * 756macro_expand_body (sb *in, sb *out, formal_entry *formals, 757 struct hash_control *formal_hash, const macro_entry *macro) 758{ 759 sb t; 760 int src = 0, inquote = 0, macro_line = 0; 761 formal_entry *loclist = NULL; 762 const char *err = NULL; 763 764 sb_new (&t); 765 766 while (src < in->len && !err) 767 { 768 if (in->ptr[src] == '&') 769 { 770 sb_reset (&t); 771 if (macro_mri) 772 { 773 if (src + 1 < in->len && in->ptr[src + 1] == '&') 774 src = sub_actual (src + 2, in, &t, formal_hash, '\'', out, 1); 775 else 776 sb_add_char (out, in->ptr[src++]); 777 } 778 else 779 { 780 /* FIXME: Why do we do this? */ 781 /* At least in alternate mode this seems correct; without this 782 one can't append a literal to a parameter. */ 783 src = sub_actual (src + 1, in, &t, formal_hash, '&', out, 0); 784 } 785 } 786 else if (in->ptr[src] == '\\') 787 { 788 src++; 789 if (src < in->len && in->ptr[src] == '(') 790 { 791 /* Sub in till the next ')' literally. */ 792 src++; 793 while (src < in->len && in->ptr[src] != ')') 794 { 795 sb_add_char (out, in->ptr[src++]); 796 } 797 if (src < in->len) 798 src++; 799 else if (!macro) 800 err = _("missing `)'"); 801 else 802 as_bad_where (macro->file, macro->line + macro_line, _("missing `)'")); 803 } 804 else if (src < in->len && in->ptr[src] == '@') 805 { 806 /* Sub in the macro invocation number. */ 807 808 char buffer[10]; 809 src++; 810 sprintf (buffer, "%d", macro_number); 811 sb_add_string (out, buffer); 812 } 813 else if (src < in->len && in->ptr[src] == '&') 814 { 815 /* This is a preprocessor variable name, we don't do them 816 here. */ 817 sb_add_char (out, '\\'); 818 sb_add_char (out, '&'); 819 src++; 820 } 821 else if (macro_mri && src < in->len && ISALNUM (in->ptr[src])) 822 { 823 int ind; 824 formal_entry *f; 825 826 if (ISDIGIT (in->ptr[src])) 827 ind = in->ptr[src] - '0'; 828 else if (ISUPPER (in->ptr[src])) 829 ind = in->ptr[src] - 'A' + 10; 830 else 831 ind = in->ptr[src] - 'a' + 10; 832 ++src; 833 for (f = formals; f != NULL; f = f->next) 834 { 835 if (f->index == ind - 1) 836 { 837 if (f->actual.len != 0) 838 sb_add_sb (out, &f->actual); 839 else 840 sb_add_sb (out, &f->def); 841 break; 842 } 843 } 844 } 845 else 846 { 847 sb_reset (&t); 848 src = sub_actual (src, in, &t, formal_hash, '\'', out, 0); 849 } 850 } 851 else if ((macro_alternate || macro_mri) 852 && is_name_beginner (in->ptr[src]) 853 && (! inquote 854 || ! macro_strip_at 855 || (src > 0 && in->ptr[src - 1] == '@'))) 856 { 857 if (! macro 858 || src + 5 >= in->len 859 || strncasecmp (in->ptr + src, "LOCAL", 5) != 0 860 || ! ISWHITE (in->ptr[src + 5])) 861 { 862 sb_reset (&t); 863 src = sub_actual (src, in, &t, formal_hash, 864 (macro_strip_at && inquote) ? '@' : '\'', 865 out, 1); 866 } 867 else 868 { 869 src = sb_skip_white (src + 5, in); 870 while (in->ptr[src] != '\n') 871 { 872 const char *name; 873 formal_entry *f = new_formal (); 874 875 src = get_token (src, in, &f->name); 876 name = sb_terminate (&f->name); 877 if (! hash_find (formal_hash, name)) 878 { 879 static int loccnt; 880 char buf[20]; 881 882 f->index = LOCAL_INDEX; 883 f->next = loclist; 884 loclist = f; 885 886 sprintf (buf, IS_ELF ? ".LL%04x" : "LL%04x", ++loccnt); 887 sb_add_string (&f->actual, buf); 888 889 err = hash_jam (formal_hash, name, f); 890 if (err != NULL) 891 break; 892 } 893 else 894 { 895 as_bad_where (macro->file, 896 macro->line + macro_line, 897 _("`%s' was already used as parameter (or another local) name"), 898 name); 899 del_formal (f); 900 } 901 902 src = sb_skip_comma (src, in); 903 } 904 } 905 } 906 else if (in->ptr[src] == '"' 907 || (macro_mri && in->ptr[src] == '\'')) 908 { 909 inquote = !inquote; 910 sb_add_char (out, in->ptr[src++]); 911 } 912 else if (in->ptr[src] == '@' && macro_strip_at) 913 { 914 ++src; 915 if (src < in->len 916 && in->ptr[src] == '@') 917 { 918 sb_add_char (out, '@'); 919 ++src; 920 } 921 } 922 else if (macro_mri 923 && in->ptr[src] == '=' 924 && src + 1 < in->len 925 && in->ptr[src + 1] == '=') 926 { 927 formal_entry *ptr; 928 929 sb_reset (&t); 930 src = get_token (src + 2, in, &t); 931 ptr = (formal_entry *) hash_find (formal_hash, sb_terminate (&t)); 932 if (ptr == NULL) 933 { 934 /* FIXME: We should really return a warning string here, 935 but we can't, because the == might be in the MRI 936 comment field, and, since the nature of the MRI 937 comment field depends upon the exact instruction 938 being used, we don't have enough information here to 939 figure out whether it is or not. Instead, we leave 940 the == in place, which should cause a syntax error if 941 it is not in a comment. */ 942 sb_add_char (out, '='); 943 sb_add_char (out, '='); 944 sb_add_sb (out, &t); 945 } 946 else 947 { 948 if (ptr->actual.len) 949 { 950 sb_add_string (out, "-1"); 951 } 952 else 953 { 954 sb_add_char (out, '0'); 955 } 956 } 957 } 958 else 959 { 960 if (in->ptr[src] == '\n') 961 ++macro_line; 962 sb_add_char (out, in->ptr[src++]); 963 } 964 } 965 966 sb_kill (&t); 967 968 while (loclist != NULL) 969 { 970 formal_entry *f; 971 972 f = loclist->next; 973 /* Setting the value to NULL effectively deletes the entry. We 974 avoid calling hash_delete because it doesn't reclaim memory. */ 975 hash_jam (formal_hash, sb_terminate (&loclist->name), NULL); 976 del_formal (loclist); 977 loclist = f; 978 } 979 980 return err; 981} 982 983/* Assign values to the formal parameters of a macro, and expand the 984 body. */ 985 986static const char * 987macro_expand (int idx, sb *in, macro_entry *m, sb *out) 988{ 989 sb t; 990 formal_entry *ptr; 991 formal_entry *f; 992 int is_keyword = 0; 993 int narg = 0; 994 const char *err = NULL; 995 996 sb_new (&t); 997 998 /* Reset any old value the actuals may have. */ 999 for (f = m->formals; f; f = f->next) 1000 sb_reset (&f->actual); 1001 f = m->formals; 1002 while (f != NULL && f->index < 0) 1003 f = f->next; 1004 1005 if (macro_mri) 1006 { 1007 /* The macro may be called with an optional qualifier, which may 1008 be referred to in the macro body as \0. */ 1009 if (idx < in->len && in->ptr[idx] == '.') 1010 { 1011 /* The Microtec assembler ignores this if followed by a white space. 1012 (Macro invocation with empty extension) */ 1013 idx++; 1014 if ( idx < in->len 1015 && in->ptr[idx] != ' ' 1016 && in->ptr[idx] != '\t') 1017 { 1018 formal_entry *n = new_formal (); 1019 1020 n->index = QUAL_INDEX; 1021 1022 n->next = m->formals; 1023 m->formals = n; 1024 1025 idx = get_any_string (idx, in, &n->actual); 1026 } 1027 } 1028 } 1029 1030 /* Peel off the actuals and store them away in the hash tables' actuals. */ 1031 idx = sb_skip_white (idx, in); 1032 while (idx < in->len) 1033 { 1034 int scan; 1035 1036 /* Look and see if it's a positional or keyword arg. */ 1037 scan = idx; 1038 while (scan < in->len 1039 && !ISSEP (in->ptr[scan]) 1040 && !(macro_mri && in->ptr[scan] == '\'') 1041 && (!macro_alternate && in->ptr[scan] != '=')) 1042 scan++; 1043 if (scan < in->len && !macro_alternate && in->ptr[scan] == '=') 1044 { 1045 is_keyword = 1; 1046 1047 /* It's OK to go from positional to keyword. */ 1048 1049 /* This is a keyword arg, fetch the formal name and 1050 then the actual stuff. */ 1051 sb_reset (&t); 1052 idx = get_token (idx, in, &t); 1053 if (in->ptr[idx] != '=') 1054 { 1055 err = _("confusion in formal parameters"); 1056 break; 1057 } 1058 1059 /* Lookup the formal in the macro's list. */ 1060 ptr = (formal_entry *) hash_find (m->formal_hash, sb_terminate (&t)); 1061 if (!ptr) 1062 as_bad (_("Parameter named `%s' does not exist for macro `%s'"), 1063 t.ptr, 1064 m->name); 1065 else 1066 { 1067 /* Insert this value into the right place. */ 1068 if (ptr->actual.len) 1069 { 1070 as_warn (_("Value for parameter `%s' of macro `%s' was already specified"), 1071 ptr->name.ptr, 1072 m->name); 1073 sb_reset (&ptr->actual); 1074 } 1075 idx = get_any_string (idx + 1, in, &ptr->actual); 1076 if (ptr->actual.len > 0) 1077 ++narg; 1078 } 1079 } 1080 else 1081 { 1082 if (is_keyword) 1083 { 1084 err = _("can't mix positional and keyword arguments"); 1085 break; 1086 } 1087 1088 if (!f) 1089 { 1090 formal_entry **pf; 1091 int c; 1092 1093 if (!macro_mri) 1094 { 1095 err = _("too many positional arguments"); 1096 break; 1097 } 1098 1099 f = new_formal (); 1100 1101 c = -1; 1102 for (pf = &m->formals; *pf != NULL; pf = &(*pf)->next) 1103 if ((*pf)->index >= c) 1104 c = (*pf)->index + 1; 1105 if (c == -1) 1106 c = 0; 1107 *pf = f; 1108 f->index = c; 1109 } 1110 1111 if (f->type != FORMAL_VARARG) 1112 idx = get_any_string (idx, in, &f->actual); 1113 else 1114 { 1115 sb_add_buffer (&f->actual, in->ptr + idx, in->len - idx); 1116 idx = in->len; 1117 } 1118 if (f->actual.len > 0) 1119 ++narg; 1120 do 1121 { 1122 f = f->next; 1123 } 1124 while (f != NULL && f->index < 0); 1125 } 1126 1127 if (! macro_mri) 1128 idx = sb_skip_comma (idx, in); 1129 else 1130 { 1131 if (in->ptr[idx] == ',') 1132 ++idx; 1133 if (ISWHITE (in->ptr[idx])) 1134 break; 1135 } 1136 } 1137 1138 if (! err) 1139 { 1140 for (ptr = m->formals; ptr; ptr = ptr->next) 1141 { 1142 if (ptr->type == FORMAL_REQUIRED && ptr->actual.len == 0) 1143 as_bad (_("Missing value for required parameter `%s' of macro `%s'"), 1144 ptr->name.ptr, 1145 m->name); 1146 } 1147 1148 if (macro_mri) 1149 { 1150 char buffer[20]; 1151 1152 sb_reset (&t); 1153 sb_add_string (&t, macro_strip_at ? "$NARG" : "NARG"); 1154 ptr = (formal_entry *) hash_find (m->formal_hash, sb_terminate (&t)); 1155 sprintf (buffer, "%d", narg); 1156 sb_add_string (&ptr->actual, buffer); 1157 } 1158 1159 err = macro_expand_body (&m->sub, out, m->formals, m->formal_hash, m); 1160 } 1161 1162 /* Discard any unnamed formal arguments. */ 1163 if (macro_mri) 1164 { 1165 formal_entry **pf; 1166 1167 pf = &m->formals; 1168 while (*pf != NULL) 1169 { 1170 if ((*pf)->name.len != 0) 1171 pf = &(*pf)->next; 1172 else 1173 { 1174 f = (*pf)->next; 1175 del_formal (*pf); 1176 *pf = f; 1177 } 1178 } 1179 } 1180 1181 sb_kill (&t); 1182 if (!err) 1183 macro_number++; 1184 1185 return err; 1186} 1187 1188/* Check for a macro. If one is found, put the expansion into 1189 *EXPAND. Return 1 if a macro is found, 0 otherwise. */ 1190 1191int 1192check_macro (const char *line, sb *expand, 1193 const char **error, macro_entry **info) 1194{ 1195 const char *s; 1196 char *copy, *cs; 1197 macro_entry *macro; 1198 sb line_sb; 1199 1200 if (! is_name_beginner (*line) 1201 && (! macro_mri || *line != '.')) 1202 return 0; 1203 1204 s = line + 1; 1205 while (is_part_of_name (*s)) 1206 ++s; 1207 if (is_name_ender (*s)) 1208 ++s; 1209 1210 copy = (char *) alloca (s - line + 1); 1211 memcpy (copy, line, s - line); 1212 copy[s - line] = '\0'; 1213 for (cs = copy; *cs != '\0'; cs++) 1214 *cs = TOLOWER (*cs); 1215 1216 macro = (macro_entry *) hash_find (macro_hash, copy); 1217 1218 if (macro == NULL) 1219 return 0; 1220 1221 /* Wrap the line up in an sb. */ 1222 sb_new (&line_sb); 1223 while (*s != '\0' && *s != '\n' && *s != '\r') 1224 sb_add_char (&line_sb, *s++); 1225 1226 sb_new (expand); 1227 *error = macro_expand (0, &line_sb, macro, expand); 1228 1229 sb_kill (&line_sb); 1230 1231 /* Export the macro information if requested. */ 1232 if (info) 1233 *info = macro; 1234 1235 return 1; 1236} 1237 1238/* Free the memory allocated to a macro. */ 1239 1240static void 1241free_macro(macro_entry *macro) 1242{ 1243 formal_entry *formal; 1244 1245 for (formal = macro->formals; formal; ) 1246 { 1247 formal_entry *f; 1248 1249 f = formal; 1250 formal = formal->next; 1251 del_formal (f); 1252 } 1253 hash_die (macro->formal_hash); 1254 sb_kill (¯o->sub); 1255 free (macro); 1256} 1257 1258/* Delete a macro. */ 1259 1260void 1261delete_macro (const char *name) 1262{ 1263 char *copy; 1264 size_t i, len; 1265 macro_entry *macro; 1266 1267 len = strlen (name); 1268 copy = (char *) alloca (len + 1); 1269 for (i = 0; i < len; ++i) 1270 copy[i] = TOLOWER (name[i]); 1271 copy[i] = '\0'; 1272 1273 /* Since hash_delete doesn't free memory, just clear out the entry. */ 1274 if ((macro = hash_find (macro_hash, copy)) != NULL) 1275 { 1276 hash_jam (macro_hash, copy, NULL); 1277 free_macro (macro); 1278 } 1279 else 1280 as_warn (_("Attempt to purge non-existant macro `%s'"), copy); 1281} 1282 1283/* Handle the MRI IRP and IRPC pseudo-ops. These are handled as a 1284 combined macro definition and execution. This returns NULL on 1285 success, or an error message otherwise. */ 1286 1287const char * 1288expand_irp (int irpc, int idx, sb *in, sb *out, int (*get_line) (sb *)) 1289{ 1290 sb sub; 1291 formal_entry f; 1292 struct hash_control *h; 1293 const char *err; 1294 1295 idx = sb_skip_white (idx, in); 1296 1297 sb_new (&sub); 1298 if (! buffer_and_nest (NULL, "ENDR", &sub, get_line)) 1299 return _("unexpected end of file in irp or irpc"); 1300 1301 sb_new (&f.name); 1302 sb_new (&f.def); 1303 sb_new (&f.actual); 1304 1305 idx = get_token (idx, in, &f.name); 1306 if (f.name.len == 0) 1307 return _("missing model parameter"); 1308 1309 h = hash_new (); 1310 err = hash_jam (h, sb_terminate (&f.name), &f); 1311 if (err != NULL) 1312 return err; 1313 1314 f.index = 1; 1315 f.next = NULL; 1316 f.type = FORMAL_OPTIONAL; 1317 1318 sb_reset (out); 1319 1320 idx = sb_skip_comma (idx, in); 1321 if (idx >= in->len) 1322 { 1323 /* Expand once with a null string. */ 1324 err = macro_expand_body (&sub, out, &f, h, 0); 1325 } 1326 else 1327 { 1328 bfd_boolean in_quotes = FALSE; 1329 1330 if (irpc && in->ptr[idx] == '"') 1331 { 1332 in_quotes = TRUE; 1333 ++idx; 1334 } 1335 1336 while (idx < in->len) 1337 { 1338 if (!irpc) 1339 idx = get_any_string (idx, in, &f.actual); 1340 else 1341 { 1342 if (in->ptr[idx] == '"') 1343 { 1344 int nxt; 1345 1346 if (irpc) 1347 in_quotes = ! in_quotes; 1348 1349 nxt = sb_skip_white (idx + 1, in); 1350 if (nxt >= in->len) 1351 { 1352 idx = nxt; 1353 break; 1354 } 1355 } 1356 sb_reset (&f.actual); 1357 sb_add_char (&f.actual, in->ptr[idx]); 1358 ++idx; 1359 } 1360 1361 err = macro_expand_body (&sub, out, &f, h, 0); 1362 if (err != NULL) 1363 break; 1364 if (!irpc) 1365 idx = sb_skip_comma (idx, in); 1366 else if (! in_quotes) 1367 idx = sb_skip_white (idx, in); 1368 } 1369 } 1370 1371 hash_die (h); 1372 sb_kill (&f.actual); 1373 sb_kill (&f.def); 1374 sb_kill (&f.name); 1375 sb_kill (&sub); 1376 1377 return err; 1378} 1379