1 /* macro.c - macro support for gas and gasp
2 Copyright (C) 1994, 95, 96, 97, 98, 99, 2000
3 Free Software Foundation, Inc.
5 Written by Steve and Judy Chamberlain of Cygnus Support,
8 This file is part of GAS, the GNU Assembler.
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)
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.
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, 59 Temple Place - Suite 330, Boston, MA
27 /* AIX requires this to be the first thing in the file. */
31 extern void *alloca ();
33 extern char *alloca ();
43 # ifndef alloca /* predefined by HP cc +Olibcalls */
44 # if !defined (__STDC__) && !defined (__hpux)
45 extern char *alloca ();
47 extern void *alloca ();
48 # endif /* __STDC__, __hpux */
51 # endif /* HAVE_ALLOCA_H */
64 #include "libiberty.h"
71 /* The routines in this file handle macro definition and expansion.
72 They are called by both gasp and gas. */
74 /* Internal functions. */
76 static int get_token
PARAMS ((int, sb
*, sb
*));
77 static int getstring
PARAMS ((int, sb
*, sb
*));
78 static int get_any_string
PARAMS ((int, sb
*, sb
*, int, int));
79 static int do_formals
PARAMS ((macro_entry
*, int, sb
*));
80 static int get_apost_token
PARAMS ((int, sb
*, sb
*, int));
82 PARAMS ((int, sb
*, sb
*, struct hash_control
*, int, sb
*, int));
83 static const char *macro_expand_body
84 PARAMS ((sb
*, sb
*, formal_entry
*, struct hash_control
*, int, int));
85 static const char *macro_expand
PARAMS ((int, sb
*, macro_entry
*, sb
*, int));
87 #define ISWHITE(x) ((x) == ' ' || (x) == '\t')
90 ((x) == ' ' || (x) == '\t' || (x) == ',' || (x) == '"' || (x) == ';' \
91 || (x) == ')' || (x) == '(' \
92 || ((macro_alternate || macro_mri) && ((x) == '<' || (x) == '>')))
95 ((x) == 'b' || (x) == 'B' \
96 || (x) == 'q' || (x) == 'Q' \
97 || (x) == 'h' || (x) == 'H' \
98 || (x) == 'd' || (x) == 'D')
100 /* The macro hash table. */
102 static struct hash_control
*macro_hash
;
104 /* Whether any macros have been defined. */
108 /* Whether we are in GASP alternate mode. */
110 static int macro_alternate
;
112 /* Whether we are in MRI mode. */
114 static int macro_mri
;
116 /* Whether we should strip '@' characters. */
118 static int macro_strip_at
;
120 /* Function to use to parse an expression. */
122 static int (*macro_expr
) PARAMS ((const char *, int, sb
*, int *));
124 /* Number of macro expansions that have been done. */
126 static int macro_number
;
128 /* Initialize macro processing. */
131 macro_init (alternate
, mri
, strip_at
, expr
)
135 int (*expr
) PARAMS ((const char *, int, sb
*, int *));
137 macro_hash
= hash_new ();
139 macro_alternate
= alternate
;
141 macro_strip_at
= strip_at
;
145 /* Switch in and out of MRI mode on the fly. */
154 /* Read input lines till we get to a TO string.
155 Increase nesting depth if we get a FROM string.
156 Put the results into sb at PTR.
157 Add a new input line to an sb using GET_LINE.
158 Return 1 on success, 0 on unexpected EOF. */
161 buffer_and_nest (from
, to
, ptr
, get_line
)
165 int (*get_line
) PARAMS ((sb
*));
167 int from_len
= strlen (from
);
168 int to_len
= strlen (to
);
170 int line_start
= ptr
->len
;
172 int more
= get_line (ptr
);
176 /* Try and find the first pseudo op on the line. */
179 if (! macro_alternate
&& ! macro_mri
)
181 /* With normal syntax we can suck what we want till we get
182 to the dot. With the alternate, labels have to start in
183 the first column, since we cant tell what's a label and
186 /* Skip leading whitespace. */
187 while (i
< ptr
->len
&& ISWHITE (ptr
->ptr
[i
]))
190 /* Skip over a label. */
192 && (isalnum ((unsigned char) ptr
->ptr
[i
])
193 || ptr
->ptr
[i
] == '_'
194 || ptr
->ptr
[i
] == '$'))
199 && ptr
->ptr
[i
] == ':')
203 /* Skip trailing whitespace. */
204 while (i
< ptr
->len
&& ISWHITE (ptr
->ptr
[i
]))
207 if (i
< ptr
->len
&& (ptr
->ptr
[i
] == '.'
211 if (ptr
->ptr
[i
] == '.')
213 if (strncasecmp (ptr
->ptr
+ i
, from
, from_len
) == 0
214 && (ptr
->len
== (i
+ from_len
)
215 || ! isalnum (ptr
->ptr
[i
+ from_len
])))
217 if (strncasecmp (ptr
->ptr
+ i
, to
, to_len
) == 0
218 && (ptr
->len
== (i
+ to_len
)
219 || ! isalnum (ptr
->ptr
[i
+ to_len
])))
224 /* Reset the string to not include the ending rune. */
225 ptr
->len
= line_start
;
231 /* Add a CR to the end and keep running. */
232 sb_add_char (ptr
, '\n');
233 line_start
= ptr
->len
;
234 more
= get_line (ptr
);
237 /* Return 1 on success, 0 on unexpected EOF. */
241 /* Pick up a token. */
244 get_token (idx
, in
, name
)
250 && (isalpha ((unsigned char) in
->ptr
[idx
])
251 || in
->ptr
[idx
] == '_'
252 || in
->ptr
[idx
] == '$'))
254 sb_add_char (name
, in
->ptr
[idx
++]);
256 && (isalnum ((unsigned char) in
->ptr
[idx
])
257 || in
->ptr
[idx
] == '_'
258 || in
->ptr
[idx
] == '$'))
260 sb_add_char (name
, in
->ptr
[idx
++]);
263 /* Ignore trailing &. */
264 if (macro_alternate
&& idx
< in
->len
&& in
->ptr
[idx
] == '&')
269 /* Pick up a string. */
272 getstring (idx
, in
, acc
)
277 idx
= sb_skip_white (idx
, in
);
280 && (in
->ptr
[idx
] == '"'
281 || (in
->ptr
[idx
] == '<' && (macro_alternate
|| macro_mri
))
282 || (in
->ptr
[idx
] == '\'' && macro_alternate
)))
284 if (in
->ptr
[idx
] == '<')
288 while ((in
->ptr
[idx
] != '>' || nest
)
291 if (in
->ptr
[idx
] == '!')
294 sb_add_char (acc
, in
->ptr
[idx
++]);
298 if (in
->ptr
[idx
] == '>')
300 if (in
->ptr
[idx
] == '<')
302 sb_add_char (acc
, in
->ptr
[idx
++]);
307 else if (in
->ptr
[idx
] == '"' || in
->ptr
[idx
] == '\'')
309 char tchar
= in
->ptr
[idx
];
314 while (idx
< in
->len
)
316 if (in
->ptr
[idx
- 1] == '\\')
321 if (macro_alternate
&& in
->ptr
[idx
] == '!')
325 sb_add_char (acc
, in
->ptr
[idx
]);
329 else if (escaped
&& in
->ptr
[idx
] == tchar
)
331 sb_add_char (acc
, tchar
);
336 if (in
->ptr
[idx
] == tchar
)
340 if (idx
>= in
->len
|| in
->ptr
[idx
] != tchar
)
344 sb_add_char (acc
, in
->ptr
[idx
]);
354 /* Fetch string from the input stream,
356 'Bxyx<whitespace> -> return 'Bxyza
357 %<char> -> return string of decimal value of x
358 "<string>" -> return string
359 xyx<whitespace> -> return xyz
363 get_any_string (idx
, in
, out
, expand
, pretend_quoted
)
371 idx
= sb_skip_white (idx
, in
);
375 if (in
->len
> 2 && in
->ptr
[idx
+ 1] == '\'' && ISBASE (in
->ptr
[idx
]))
377 while (!ISSEP (in
->ptr
[idx
]))
378 sb_add_char (out
, in
->ptr
[idx
++]);
380 else if (in
->ptr
[idx
] == '%'
386 /* Turns the next expression into a string. */
387 idx
= (*macro_expr
) (_("% operator needs absolute expression"),
391 sprintf(buf
, "%d", val
);
392 sb_add_string (out
, buf
);
394 else if (in
->ptr
[idx
] == '"'
395 || (in
->ptr
[idx
] == '<' && (macro_alternate
|| macro_mri
))
396 || (macro_alternate
&& in
->ptr
[idx
] == '\''))
402 /* Keep the quotes. */
403 sb_add_char (out
, '\"');
405 idx
= getstring (idx
, in
, out
);
406 sb_add_char (out
, '\"');
410 idx
= getstring (idx
, in
, out
);
416 && (in
->ptr
[idx
] == '"'
417 || in
->ptr
[idx
] == '\''
419 || (in
->ptr
[idx
] != ' '
420 && in
->ptr
[idx
] != '\t'
421 && in
->ptr
[idx
] != ','
422 && (in
->ptr
[idx
] != '<'
423 || (! macro_alternate
&& ! macro_mri
)))))
425 if (in
->ptr
[idx
] == '"'
426 || in
->ptr
[idx
] == '\'')
428 char tchar
= in
->ptr
[idx
];
429 sb_add_char (out
, in
->ptr
[idx
++]);
431 && in
->ptr
[idx
] != tchar
)
432 sb_add_char (out
, in
->ptr
[idx
++]);
436 sb_add_char (out
, in
->ptr
[idx
++]);
444 /* Pick up the formal parameters of a macro definition. */
447 do_formals (macro
, idx
, in
)
452 formal_entry
**p
= ¯o
->formals
;
454 macro
->formal_count
= 0;
455 macro
->formal_hash
= hash_new ();
456 while (idx
< in
->len
)
458 formal_entry
*formal
;
460 formal
= (formal_entry
*) xmalloc (sizeof (formal_entry
));
462 sb_new (&formal
->name
);
463 sb_new (&formal
->def
);
464 sb_new (&formal
->actual
);
466 idx
= sb_skip_white (idx
, in
);
467 idx
= get_token (idx
, in
, &formal
->name
);
468 if (formal
->name
.len
== 0)
470 idx
= sb_skip_white (idx
, in
);
471 if (formal
->name
.len
)
473 /* This is a formal. */
474 if (idx
< in
->len
&& in
->ptr
[idx
] == '=')
477 idx
= get_any_string (idx
+ 1, in
, &formal
->def
, 1, 0);
481 /* Add to macro's hash table. */
482 hash_jam (macro
->formal_hash
, sb_terminate (&formal
->name
), formal
);
484 formal
->index
= macro
->formal_count
;
485 idx
= sb_skip_comma (idx
, in
);
486 macro
->formal_count
++;
494 formal_entry
*formal
;
497 /* Add a special NARG formal, which macro_expand will set to the
498 number of arguments. */
499 formal
= (formal_entry
*) xmalloc (sizeof (formal_entry
));
501 sb_new (&formal
->name
);
502 sb_new (&formal
->def
);
503 sb_new (&formal
->actual
);
505 /* The same MRI assemblers which treat '@' characters also use
506 the name $NARG. At least until we find an exception. */
512 sb_add_string (&formal
->name
, name
);
514 /* Add to macro's hash table. */
515 hash_jam (macro
->formal_hash
, name
, formal
);
517 formal
->index
= NARG_INDEX
;
525 /* Define a new macro. Returns NULL on success, otherwise returns an
526 error message. If NAMEP is not NULL, *NAMEP is set to the name of
527 the macro which was defined. */
530 define_macro (idx
, in
, label
, get_line
, namep
)
534 int (*get_line
) PARAMS ((sb
*));
541 macro
= (macro_entry
*) xmalloc (sizeof (macro_entry
));
542 sb_new (¯o
->sub
);
545 macro
->formal_count
= 0;
548 idx
= sb_skip_white (idx
, in
);
549 if (! buffer_and_nest ("MACRO", "ENDM", ¯o
->sub
, get_line
))
550 return _("unexpected end of file in macro definition");
551 if (label
!= NULL
&& label
->len
!= 0)
553 sb_add_sb (&name
, label
);
554 if (idx
< in
->len
&& in
->ptr
[idx
] == '(')
556 /* It's the label: MACRO (formals,...) sort */
557 idx
= do_formals (macro
, idx
+ 1, in
);
558 if (in
->ptr
[idx
] != ')')
559 return _("missing ) after formals");
563 /* It's the label: MACRO formals,... sort */
564 idx
= do_formals (macro
, idx
, in
);
569 idx
= get_token (idx
, in
, &name
);
570 idx
= sb_skip_comma (idx
, in
);
571 idx
= do_formals (macro
, idx
, in
);
574 /* And stick it in the macro hash table. */
575 for (idx
= 0; idx
< name
.len
; idx
++)
576 if (isupper ((unsigned char) name
.ptr
[idx
]))
577 name
.ptr
[idx
] = tolower (name
.ptr
[idx
]);
578 namestr
= sb_terminate (&name
);
579 hash_jam (macro_hash
, namestr
, (PTR
) macro
);
589 /* Scan a token, and then skip KIND. */
592 get_apost_token (idx
, in
, name
, kind
)
598 idx
= get_token (idx
, in
, name
);
600 && in
->ptr
[idx
] == kind
601 && (! macro_mri
|| macro_strip_at
)
602 && (! macro_strip_at
|| kind
== '@'))
607 /* Substitute the actual value for a formal parameter. */
610 sub_actual (start
, in
, t
, formal_hash
, kind
, out
, copyifnotthere
)
614 struct hash_control
*formal_hash
;
622 src
= get_apost_token (start
, in
, t
, kind
);
623 /* See if it's in the macro's hash table, unless this is
624 macro_strip_at and kind is '@' and the token did not end in '@'. */
627 && (src
== start
|| in
->ptr
[src
- 1] != '@'))
630 ptr
= (formal_entry
*) hash_find (formal_hash
, sb_terminate (t
));
635 sb_add_sb (out
, &ptr
->actual
);
639 sb_add_sb (out
, &ptr
->def
);
642 else if (kind
== '&')
644 /* Doing this permits people to use & in macro bodies. */
645 sb_add_char (out
, '&');
647 else if (copyifnotthere
)
653 sb_add_char (out
, '\\');
659 /* Expand the body of a macro. */
662 macro_expand_body (in
, out
, formals
, formal_hash
, comment_char
, locals
)
665 formal_entry
*formals
;
666 struct hash_control
*formal_hash
;
673 formal_entry
*loclist
= NULL
;
677 while (src
< in
->len
)
679 if (in
->ptr
[src
] == '&')
684 if (src
+ 1 < in
->len
&& in
->ptr
[src
+ 1] == '&')
685 src
= sub_actual (src
+ 2, in
, &t
, formal_hash
, '\'', out
, 1);
687 sb_add_char (out
, in
->ptr
[src
++]);
691 /* FIXME: Why do we do this? */
692 src
= sub_actual (src
+ 1, in
, &t
, formal_hash
, '&', out
, 0);
695 else if (in
->ptr
[src
] == '\\')
698 if (in
->ptr
[src
] == comment_char
&& comment_char
!= '\0')
700 /* This is a comment, just drop the rest of the line. */
702 && in
->ptr
[src
] != '\n')
705 else if (in
->ptr
[src
] == '(')
707 /* Sub in till the next ')' literally. */
709 while (src
< in
->len
&& in
->ptr
[src
] != ')')
711 sb_add_char (out
, in
->ptr
[src
++]);
713 if (in
->ptr
[src
] == ')')
716 return _("missplaced )");
718 else if (in
->ptr
[src
] == '@')
720 /* Sub in the macro invocation number. */
724 sprintf (buffer
, "%d", macro_number
);
725 sb_add_string (out
, buffer
);
727 else if (in
->ptr
[src
] == '&')
729 /* This is a preprocessor variable name, we don't do them
731 sb_add_char (out
, '\\');
732 sb_add_char (out
, '&');
736 && isalnum ((unsigned char) in
->ptr
[src
]))
741 if (isdigit ((unsigned char) in
->ptr
[src
]))
742 ind
= in
->ptr
[src
] - '0';
743 else if (isupper ((unsigned char) in
->ptr
[src
]))
744 ind
= in
->ptr
[src
] - 'A' + 10;
746 ind
= in
->ptr
[src
] - 'a' + 10;
748 for (f
= formals
; f
!= NULL
; f
= f
->next
)
750 if (f
->index
== ind
- 1)
752 if (f
->actual
.len
!= 0)
753 sb_add_sb (out
, &f
->actual
);
755 sb_add_sb (out
, &f
->def
);
763 src
= sub_actual (src
, in
, &t
, formal_hash
, '\'', out
, 0);
766 else if ((macro_alternate
|| macro_mri
)
767 && (isalpha ((unsigned char) in
->ptr
[src
])
768 || in
->ptr
[src
] == '_'
769 || in
->ptr
[src
] == '$')
772 || (src
> 0 && in
->ptr
[src
- 1] == '@')))
775 || src
+ 5 >= in
->len
776 || strncasecmp (in
->ptr
+ src
, "LOCAL", 5) != 0
777 || ! ISWHITE (in
->ptr
[src
+ 5]))
780 src
= sub_actual (src
, in
, &t
, formal_hash
,
781 (macro_strip_at
&& inquote
) ? '@' : '\'',
788 src
= sb_skip_white (src
+ 5, in
);
789 while (in
->ptr
[src
] != '\n' && in
->ptr
[src
] != comment_char
)
795 f
= (formal_entry
*) xmalloc (sizeof (formal_entry
));
799 f
->index
= LOCAL_INDEX
;
803 src
= get_token (src
, in
, &f
->name
);
805 sprintf (buf
, "LL%04x", loccnt
);
806 sb_add_string (&f
->actual
, buf
);
808 err
= hash_jam (formal_hash
, sb_terminate (&f
->name
), f
);
812 src
= sb_skip_comma (src
, in
);
816 else if (comment_char
!= '\0'
817 && in
->ptr
[src
] == comment_char
819 && in
->ptr
[src
+ 1] == comment_char
822 /* Two comment chars in a row cause the rest of the line to
824 while (src
< in
->len
&& in
->ptr
[src
] != '\n')
827 else if (in
->ptr
[src
] == '"'
828 || (macro_mri
&& in
->ptr
[src
] == '\''))
831 sb_add_char (out
, in
->ptr
[src
++]);
833 else if (in
->ptr
[src
] == '@' && macro_strip_at
)
837 && in
->ptr
[src
] == '@')
839 sb_add_char (out
, '@');
844 && in
->ptr
[src
] == '='
846 && in
->ptr
[src
+ 1] == '=')
851 src
= get_token (src
+ 2, in
, &t
);
852 ptr
= (formal_entry
*) hash_find (formal_hash
, sb_terminate (&t
));
855 /* FIXME: We should really return a warning string here,
856 but we can't, because the == might be in the MRI
857 comment field, and, since the nature of the MRI
858 comment field depends upon the exact instruction
859 being used, we don't have enough information here to
860 figure out whether it is or not. Instead, we leave
861 the == in place, which should cause a syntax error if
862 it is not in a comment. */
863 sb_add_char (out
, '=');
864 sb_add_char (out
, '=');
871 sb_add_string (out
, "-1");
875 sb_add_char (out
, '0');
881 sb_add_char (out
, in
->ptr
[src
++]);
887 while (loclist
!= NULL
)
892 /* Setting the value to NULL effectively deletes the entry. We
893 avoid calling hash_delete because it doesn't reclaim memory. */
894 hash_jam (formal_hash
, sb_terminate (&loclist
->name
), NULL
);
895 sb_kill (&loclist
->name
);
896 sb_kill (&loclist
->def
);
897 sb_kill (&loclist
->actual
);
905 /* Assign values to the formal parameters of a macro, and expand the
909 macro_expand (idx
, in
, m
, out
, comment_char
)
919 int is_positional
= 0;
926 /* Reset any old value the actuals may have. */
927 for (f
= m
->formals
; f
; f
= f
->next
)
928 sb_reset (&f
->actual
);
930 while (f
!= NULL
&& f
->index
< 0)
935 /* The macro may be called with an optional qualifier, which may
936 be referred to in the macro body as \0. */
937 if (idx
< in
->len
&& in
->ptr
[idx
] == '.')
941 n
= (formal_entry
*) xmalloc (sizeof (formal_entry
));
945 n
->index
= QUAL_INDEX
;
947 n
->next
= m
->formals
;
950 idx
= get_any_string (idx
+ 1, in
, &n
->actual
, 1, 0);
954 /* Peel off the actuals and store them away in the hash tables' actuals. */
955 idx
= sb_skip_white (idx
, in
);
956 while (idx
< in
->len
&& in
->ptr
[idx
] != comment_char
)
960 /* Look and see if it's a positional or keyword arg. */
962 while (scan
< in
->len
963 && !ISSEP (in
->ptr
[scan
])
964 && !(macro_mri
&& in
->ptr
[scan
] == '\'')
965 && (!macro_alternate
&& in
->ptr
[scan
] != '='))
967 if (scan
< in
->len
&& !macro_alternate
&& in
->ptr
[scan
] == '=')
971 /* It's OK to go from positional to keyword. */
973 /* This is a keyword arg, fetch the formal name and
974 then the actual stuff. */
976 idx
= get_token (idx
, in
, &t
);
977 if (in
->ptr
[idx
] != '=')
978 return _("confusion in formal parameters");
980 /* Lookup the formal in the macro's list. */
981 ptr
= (formal_entry
*) hash_find (m
->formal_hash
, sb_terminate (&t
));
983 return _("macro formal argument does not exist");
986 /* Insert this value into the right place. */
987 sb_reset (&ptr
->actual
);
988 idx
= get_any_string (idx
+ 1, in
, &ptr
->actual
, 0, 0);
989 if (ptr
->actual
.len
> 0)
995 /* This is a positional arg. */
998 return _("can't mix positional and keyword arguments");
1006 return _("too many positional arguments");
1008 f
= (formal_entry
*) xmalloc (sizeof (formal_entry
));
1011 sb_new (&f
->actual
);
1015 for (pf
= &m
->formals
; *pf
!= NULL
; pf
= &(*pf
)->next
)
1016 if ((*pf
)->index
>= c
)
1017 c
= (*pf
)->index
+ 1;
1024 sb_reset (&f
->actual
);
1025 idx
= get_any_string (idx
, in
, &f
->actual
, 1, 0);
1026 if (f
->actual
.len
> 0)
1032 while (f
!= NULL
&& f
->index
< 0);
1036 idx
= sb_skip_comma (idx
, in
);
1039 if (in
->ptr
[idx
] == ',')
1041 if (ISWHITE (in
->ptr
[idx
]))
1051 sb_add_string (&t
, macro_strip_at
? "$NARG" : "NARG");
1052 ptr
= (formal_entry
*) hash_find (m
->formal_hash
, sb_terminate (&t
));
1053 sb_reset (&ptr
->actual
);
1054 sprintf (buffer
, "%d", narg
);
1055 sb_add_string (&ptr
->actual
, buffer
);
1058 err
= macro_expand_body (&m
->sub
, out
, m
->formals
, m
->formal_hash
,
1063 /* Discard any unnamed formal arguments. */
1071 if ((*pf
)->name
.len
!= 0)
1075 sb_kill (&(*pf
)->name
);
1076 sb_kill (&(*pf
)->def
);
1077 sb_kill (&(*pf
)->actual
);
1091 /* Check for a macro. If one is found, put the expansion into
1092 *EXPAND. COMMENT_CHAR is the comment character--this is used by
1093 gasp. Return 1 if a macro is found, 0 otherwise. */
1096 check_macro (line
, expand
, comment_char
, error
, info
)
1108 if (! isalpha ((unsigned char) *line
)
1111 && (! macro_mri
|| *line
!= '.'))
1115 while (isalnum ((unsigned char) *s
)
1120 copy
= (char *) alloca (s
- line
+ 1);
1121 memcpy (copy
, line
, s
- line
);
1122 copy
[s
- line
] = '\0';
1123 for (cs
= copy
; *cs
!= '\0'; cs
++)
1124 if (isupper ((unsigned char) *cs
))
1125 *cs
= tolower (*cs
);
1127 macro
= (macro_entry
*) hash_find (macro_hash
, copy
);
1132 /* Wrap the line up in an sb. */
1134 while (*s
!= '\0' && *s
!= '\n' && *s
!= '\r')
1135 sb_add_char (&line_sb
, *s
++);
1138 *error
= macro_expand (0, &line_sb
, macro
, expand
, comment_char
);
1142 /* Export the macro information if requested. */
1149 /* Delete a macro. */
1155 hash_delete (macro_hash
, name
);
1158 /* Handle the MRI IRP and IRPC pseudo-ops. These are handled as a
1159 combined macro definition and execution. This returns NULL on
1160 success, or an error message otherwise. */
1163 expand_irp (irpc
, idx
, in
, out
, get_line
, comment_char
)
1168 int (*get_line
) PARAMS ((sb
*));
1174 struct hash_control
*h
;
1182 idx
= sb_skip_white (idx
, in
);
1185 if (! buffer_and_nest (mn
, "ENDR", &sub
, get_line
))
1186 return _("unexpected end of file in irp or irpc");
1192 idx
= get_token (idx
, in
, &f
.name
);
1193 if (f
.name
.len
== 0)
1194 return _("missing model parameter");
1197 err
= hash_jam (h
, sb_terminate (&f
.name
), &f
);
1206 idx
= sb_skip_comma (idx
, in
);
1207 if (idx
>= in
->len
|| in
->ptr
[idx
] == comment_char
)
1209 /* Expand once with a null string. */
1210 err
= macro_expand_body (&sub
, out
, &f
, h
, comment_char
, 0);
1216 if (irpc
&& in
->ptr
[idx
] == '"')
1218 while (idx
< in
->len
&& in
->ptr
[idx
] != comment_char
)
1221 idx
= get_any_string (idx
, in
, &f
.actual
, 1, 0);
1224 if (in
->ptr
[idx
] == '"')
1228 nxt
= sb_skip_white (idx
+ 1, in
);
1229 if (nxt
>= in
->len
|| in
->ptr
[nxt
] == comment_char
)
1235 sb_reset (&f
.actual
);
1236 sb_add_char (&f
.actual
, in
->ptr
[idx
]);
1239 err
= macro_expand_body (&sub
, out
, &f
, h
, comment_char
, 0);
1243 idx
= sb_skip_comma (idx
, in
);
1245 idx
= sb_skip_white (idx
, in
);