lexer: Add tokens for '{', '}', ':', ';' for use in the matrix language.
[pspp] / src / language / lexer / macro.c
1 /* PSPP - a program for statistical analysis.
2    Copyright (C) 2021 Free Software Foundation, Inc.
3
4    This program is free software: you can redistribute it and/or modify
5    it under the terms of the GNU General Public License as published by
6    the Free Software Foundation, either version 3 of the License, or
7    (at your option) any later version.
8
9    This program is distributed in the hope that it will be useful,
10    but WITHOUT ANY WARRANTY; without even the implied warranty of
11    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12    GNU General Public License for more details.
13
14    You should have received a copy of the GNU General Public License
15    along with this program.  If not, see <http://www.gnu.org/licenses/>. */
16
17 #include <config.h>
18
19 #include "language/lexer/macro.h"
20
21 #include <errno.h>
22 #include <limits.h>
23 #include <stdlib.h>
24
25 #include "data/settings.h"
26 #include "language/lexer/lexer.h"
27 #include "language/lexer/segment.h"
28 #include "language/lexer/scan.h"
29 #include "libpspp/assertion.h"
30 #include "libpspp/cast.h"
31 #include "libpspp/i18n.h"
32 #include "libpspp/message.h"
33 #include "libpspp/str.h"
34 #include "libpspp/string-array.h"
35 #include "libpspp/stringi-map.h"
36 #include "libpspp/stringi-set.h"
37
38 #include "gl/c-ctype.h"
39 #include "gl/ftoastr.h"
40
41 #include "gettext.h"
42 #define _(msgid) gettext (msgid)
43
44 /* An entry in the stack of macros and macro directives being expanded.  The
45    stack is maintained as a linked list.  Entries are not dynamically allocated
46    but on the program stack.
47
48    The outermost entry, where 'next' is NULL, represents the source location of
49    the call to the macro. */
50 struct macro_expansion_stack
51   {
52     const struct macro_expansion_stack *next; /* Next outer stack entry. */
53     const char *name;                    /* A macro name or !IF, !DO, etc. */
54     const struct msg_location *location; /* Source location if available. */
55   };
56
57 /* Reports an error during macro expansion.  STACK is the stack for reporting
58    the location of the error, MT is the optional token at which the error was
59    detected, and FORMAT along with the varargs is the message to report. */
60 static void PRINTF_FORMAT (3, 0)
61 macro_error_valist (const struct macro_expansion_stack *stack,
62                     const struct macro_token *mt, const char *format,
63                     va_list args)
64 {
65   struct msg_stack **ms = NULL;
66   size_t allocated_ms = 0;
67   size_t n_ms = 0;
68
69   const struct macro_expansion_stack *p;
70   for (p = stack; p && p->next; p = p->next)
71     {
72       if (n_ms >= allocated_ms)
73         ms = x2nrealloc (ms, &allocated_ms, sizeof *ms);
74
75       /* TRANSLATORS: These strings are used for explaining the context of an
76          error.  The "While expanding" message appears first, followed by zero
77          or more of the "inside expansion" messages.  `innermost',
78          `next_inner`, etc., are names of macros, and `foobar' is a piece of
79          PSPP syntax:
80
81          foo.sps:12: At `foobar' in the expansion of 'innermost',
82          foo.sps:23: inside the expansion of 'next_inner',
83          foo.sps:34: inside the expansion of 'next_inner2',
84          foo.sps:45: inside the expansion of 'outermost',
85          foo.sps:76: This is the actual error message. */
86       char *description;
87       if (p == stack)
88         {
89           if (mt && mt->syntax.length)
90             {
91               char syntax[64];
92               str_ellipsize (mt->syntax, syntax, sizeof syntax);
93               description = xasprintf (_("At `%s' in the expansion of `%s',"),
94                                        syntax, p->name);
95             }
96           else
97             description = xasprintf (_("In the expansion of `%s',"), p->name);
98         }
99       else
100         description = xasprintf (_("inside the expansion of `%s',"), p->name);
101
102       ms[n_ms] = xmalloc (sizeof *ms[n_ms]);
103       *ms[n_ms] = (struct msg_stack) {
104         .location = msg_location_dup (p->location),
105         .description = description,
106       };
107       n_ms++;
108     }
109
110   struct msg *m = xmalloc (sizeof *m);
111   *m = (struct msg) {
112     .category = MSG_C_SYNTAX,
113     .severity = MSG_S_ERROR,
114     .stack = ms,
115     .n_stack = n_ms,
116     .location = msg_location_dup (p ? p->location : NULL),
117     .text = xvasprintf (format, args),
118   };
119   msg_emit (m);
120 }
121
122 /* Reports an error during macro expansion.  STACK is the stack for reporting
123    the location of the error, MT is the optional token at which the error was
124    detected, and FORMAT along with the varargs is the message to report. */
125 static void PRINTF_FORMAT (3, 4)
126 macro_error (const struct macro_expansion_stack *stack,
127              const struct macro_token *mt, const char *format, ...)
128 {
129   va_list args;
130   va_start (args, format);
131   macro_error_valist (stack, mt, format, args);
132   va_end (args);
133 }
134
135 void
136 macro_token_copy (struct macro_token *dst, const struct macro_token *src)
137 {
138   token_copy (&dst->token, &src->token);
139   ss_alloc_substring (&dst->syntax, src->syntax);
140 }
141
142 void
143 macro_token_uninit (struct macro_token *mt)
144 {
145   token_uninit (&mt->token);
146   ss_dealloc (&mt->syntax);
147 }
148
149 void
150 macro_token_to_syntax (struct macro_token *mt, struct string *s)
151 {
152   ds_put_substring (s, mt->syntax);
153 }
154 bool
155 is_macro_keyword (struct substring s)
156 {
157   static struct stringi_set keywords = STRINGI_SET_INITIALIZER (keywords);
158   if (stringi_set_is_empty (&keywords))
159     {
160       static const char *kws[] = {
161         "BREAK",
162         "CHAREND",
163         "CMDEND",
164         "DEFAULT",
165         "DO",
166         "DOEND",
167         "ELSE",
168         "ENCLOSE",
169         "ENDDEFINE",
170         "IF",
171         "IFEND",
172         "IN",
173         "LET",
174         "NOEXPAND",
175         "OFFEXPAND",
176         "ONEXPAND",
177         "POSITIONAL",
178         "THEN",
179         "TOKENS",
180       };
181       for (size_t i = 0; i < sizeof kws / sizeof *kws; i++)
182         stringi_set_insert (&keywords, kws[i]);
183     }
184
185   ss_ltrim (&s, ss_cstr ("!"));
186   return stringi_set_contains_len (&keywords, s.string, s.length);
187 }
188 \f
189 void
190 macro_tokens_copy (struct macro_tokens *dst, const struct macro_tokens *src)
191 {
192   *dst = (struct macro_tokens) {
193     .mts = xmalloc (src->n * sizeof *dst->mts),
194     .n = src->n,
195     .allocated = src->n,
196   };
197   for (size_t i = 0; i < src->n; i++)
198     macro_token_copy (&dst->mts[i], &src->mts[i]);
199 }
200
201 void
202 macro_tokens_uninit (struct macro_tokens *mts)
203 {
204   for (size_t i = 0; i < mts->n; i++)
205     macro_token_uninit (&mts->mts[i]);
206   free (mts->mts);
207 }
208
209 struct macro_token *
210 macro_tokens_add_uninit (struct macro_tokens *mts)
211 {
212   if (mts->n >= mts->allocated)
213     mts->mts = x2nrealloc (mts->mts, &mts->allocated, sizeof *mts->mts);
214   return &mts->mts[mts->n++];
215 }
216
217 void
218 macro_tokens_add (struct macro_tokens *mts, const struct macro_token *mt)
219 {
220   macro_token_copy (macro_tokens_add_uninit (mts), mt);
221 }
222
223 /* Tokenizes SRC according to MODE and appends the tokens to MTS.  Uses STACK,
224    if nonull, for error reporting. */
225 static void
226 macro_tokens_from_string__ (struct macro_tokens *mts, const struct substring src,
227                             enum segmenter_mode mode,
228                             const struct macro_expansion_stack *stack)
229 {
230   struct segmenter segmenter = segmenter_init (mode, true);
231   struct substring body = src;
232
233   while (body.length > 0)
234     {
235       struct macro_token mt = {
236         .token = { .type = T_STOP },
237         .syntax = { .string = body.string },
238       };
239       struct token *token = &mt.token;
240
241       enum segment_type type;
242       int seg_len = segmenter_push (&segmenter, body.string,
243                                     body.length, true, &type);
244       assert (seg_len >= 0);
245
246       struct substring segment = ss_head (body, seg_len);
247       enum tokenize_result result = token_from_segment (type, segment, token);
248       ss_advance (&body, seg_len);
249
250       switch (result)
251         {
252         case TOKENIZE_EMPTY:
253           break;
254
255         case TOKENIZE_TOKEN:
256           mt.syntax.length = body.string - mt.syntax.string;
257           macro_tokens_add (mts, &mt);
258           break;
259
260         case TOKENIZE_ERROR:
261           mt.syntax.length = body.string - mt.syntax.string;
262           macro_error (stack, &mt, "%s", token->string.string);
263           break;
264         }
265
266       token_uninit (token);
267     }
268 }
269
270 /* Tokenizes SRC according to MODE and appends the tokens to MTS. */
271 void
272 macro_tokens_from_string (struct macro_tokens *mts, const struct substring src,
273                           enum segmenter_mode mode)
274 {
275   macro_tokens_from_string__ (mts, src, mode, NULL);
276 }
277
278 void
279 macro_tokens_print (const struct macro_tokens *mts, FILE *stream)
280 {
281   for (size_t i = 0; i < mts->n; i++)
282     token_print (&mts->mts[i].token, stream);
283 }
284
285 enum token_class
286   {
287     TC_ENDCMD,                  /* No space before or after (new-line after). */
288     TC_BINOP,                   /* Space on both sides. */
289     TC_COMMA,                   /* Space afterward. */
290     TC_ID,                      /* Don't need spaces except sequentially. */
291     TC_PUNCT,                   /* Don't need spaces except sequentially. */
292   };
293
294 static bool
295 needs_space (enum token_class prev, enum token_class next)
296 {
297   /* Don't need a space before or after the end of a command.
298      (A new-line is needed afterward as a special case.) */
299   if (prev == TC_ENDCMD || next == TC_ENDCMD)
300     return false;
301
302   /* Binary operators always have a space on both sides. */
303   if (prev == TC_BINOP || next == TC_BINOP)
304     return true;
305
306   /* A comma always has a space afterward. */
307   if (prev == TC_COMMA)
308     return true;
309
310   /* Otherwise, PREV is TC_ID or TC_PUNCT, which only need a space if there are
311      two or them in a row. */
312   return prev == next;
313 }
314
315 static enum token_class
316 classify_token (enum token_type type)
317 {
318   switch (type)
319     {
320     case T_ID:
321     case T_MACRO_ID:
322     case T_POS_NUM:
323     case T_NEG_NUM:
324     case T_STRING:
325       return TC_ID;
326
327     case T_STOP:
328       return TC_PUNCT;
329
330     case T_ENDCMD:
331       return TC_ENDCMD;
332
333     case T_LPAREN:
334     case T_RPAREN:
335     case T_LBRACK:
336     case T_RBRACK:
337     case T_LCURLY:
338     case T_RCURLY:
339       return TC_PUNCT;
340
341     case T_PLUS:
342     case T_DASH:
343     case T_ASTERISK:
344     case T_SLASH:
345     case T_EQUALS:
346     case T_COLON:
347     case T_AND:
348     case T_OR:
349     case T_NOT:
350     case T_EQ:
351     case T_GE:
352     case T_GT:
353     case T_LE:
354     case T_LT:
355     case T_NE:
356     case T_ALL:
357     case T_BY:
358     case T_TO:
359     case T_WITH:
360     case T_EXP:
361     case T_MACRO_PUNCT:
362       return TC_BINOP;
363
364     case T_COMMA:
365     case T_SEMICOLON:
366       return TC_COMMA;
367     }
368
369   NOT_REACHED ();
370 }
371
372 /* Appends syntax for the tokens in MTS to S.  If OFS and LEN are nonnull, sets
373    OFS[i] to the offset within S of the start of token 'i' in MTS and LEN[i] to
374    its length.  OFS[i] + LEN[i] is not necessarily OFS[i + 1] because some
375    tokens are separated by white space.  */
376 void
377 macro_tokens_to_syntax (struct macro_tokens *mts, struct string *s,
378                         size_t *ofs, size_t *len)
379 {
380   assert ((ofs != NULL) == (len != NULL));
381
382   if (!mts->n)
383     return;
384
385   for (size_t i = 0; i < mts->n; i++)
386     {
387       if (i > 0)
388         {
389           enum token_type prev = mts->mts[i - 1].token.type;
390           enum token_type next = mts->mts[i].token.type;
391
392           if (prev == T_ENDCMD)
393             ds_put_byte (s, '\n');
394           else
395             {
396               enum token_class pc = classify_token (prev);
397               enum token_class nc = classify_token (next);
398               if (needs_space (pc, nc))
399                 ds_put_byte (s, ' ');
400             }
401         }
402
403       if (ofs)
404         ofs[i] = s->ss.length;
405       macro_token_to_syntax (&mts->mts[i], s);
406       if (len)
407         len[i] = s->ss.length - ofs[i];
408     }
409 }
410
411 void
412 macro_destroy (struct macro *m)
413 {
414   if (!m)
415     return;
416
417   free (m->name);
418   msg_location_destroy (m->location);
419   for (size_t i = 0; i < m->n_params; i++)
420     {
421       struct macro_param *p = &m->params[i];
422       free (p->name);
423
424       macro_tokens_uninit (&p->def);
425       token_uninit (&p->start);
426       token_uninit (&p->end);
427     }
428   free (m->params);
429   macro_tokens_uninit (&m->body);
430   free (m);
431 }
432 \f
433 struct macro_set *
434 macro_set_create (void)
435 {
436   struct macro_set *set = xmalloc (sizeof *set);
437   *set = (struct macro_set) {
438     .macros = HMAP_INITIALIZER (set->macros),
439   };
440   return set;
441 }
442
443 void
444 macro_set_destroy (struct macro_set *set)
445 {
446   if (!set)
447     return;
448
449   struct macro *macro, *next;
450   HMAP_FOR_EACH_SAFE (macro, next, struct macro, hmap_node, &set->macros)
451     {
452       hmap_delete (&set->macros, &macro->hmap_node);
453       macro_destroy (macro);
454     }
455   hmap_destroy (&set->macros);
456   free (set);
457 }
458
459 static unsigned int
460 hash_macro_name (const char *name)
461 {
462   return utf8_hash_case_string (name, 0);
463 }
464
465 static struct macro *
466 macro_set_find__ (struct macro_set *set, const char *name)
467 {
468   if (macro_set_is_empty (set))
469     return NULL;
470
471   struct macro *macro;
472   HMAP_FOR_EACH_WITH_HASH (macro, struct macro, hmap_node,
473                            hash_macro_name (name), &set->macros)
474     if (!utf8_strcasecmp (macro->name, name))
475       return macro;
476
477   return NULL;
478 }
479
480 const struct macro *
481 macro_set_find (const struct macro_set *set, const char *name)
482 {
483   return macro_set_find__ (CONST_CAST (struct macro_set *, set), name);
484 }
485
486 /* Adds M to SET.  M replaces any existing macro with the same name.  Takes
487    ownership of M. */
488 void
489 macro_set_add (struct macro_set *set, struct macro *m)
490 {
491   struct macro *victim = macro_set_find__ (set, m->name);
492   if (victim)
493     {
494       hmap_delete (&set->macros, &victim->hmap_node);
495       macro_destroy (victim);
496     }
497
498   hmap_insert (&set->macros, &m->hmap_node, hash_macro_name (m->name));
499 }
500 \f
501 /* Macro call parsing. */
502
503 enum mc_state
504   {
505     /* Accumulating tokens in mc->params toward the end of any type of
506        argument. */
507     MC_ARG,
508
509     /* Expecting the opening delimiter of an ARG_ENCLOSE argument. */
510     MC_ENCLOSE,
511
512     /* Expecting a keyword for a keyword argument. */
513     MC_KEYWORD,
514
515     /* Expecting an equal sign for a keyword argument. */
516     MC_EQUALS,
517
518     /* Macro fully parsed and ready for expansion. */
519     MC_FINISHED,
520   };
521
522 /* Parsing macro calls.  This is a FSM driven by macro_call_create() and
523    macro_call_add() to identify the macro being called and obtain its
524    arguments.  'state' identifies the FSM state. */
525 struct macro_call
526   {
527     const struct macro_set *macros;
528     const struct macro *macro;
529     struct macro_tokens **args;
530     const struct macro_expansion_stack *stack;
531     const struct macro_expander *me;
532
533     enum mc_state state;
534     size_t n_tokens;
535     const struct macro_param *param; /* Parameter currently being parsed. */
536   };
537
538 static bool macro_expand_arg (const struct token *,
539                               const struct macro_expander *,
540                               struct macro_tokens *exp);
541
542 /* Completes macro expansion by initializing arguments that weren't supplied to
543    their defaults. */
544 static int
545 mc_finished (struct macro_call *mc)
546 {
547   mc->state = MC_FINISHED;
548   for (size_t i = 0; i < mc->macro->n_params; i++)
549     if (!mc->args[i])
550       mc->args[i] = &mc->macro->params[i].def;
551   return mc->n_tokens;
552 }
553
554 static int
555 mc_next_arg (struct macro_call *mc)
556 {
557   if (!mc->param)
558     {
559       assert (!mc->macro->n_params);
560       return mc_finished (mc);
561     }
562   else if (mc->param->positional)
563     {
564       mc->param++;
565       if (mc->param >= &mc->macro->params[mc->macro->n_params])
566         return mc_finished (mc);
567       else
568         {
569           mc->state = (!mc->param->positional ? MC_KEYWORD
570                        : mc->param->arg_type == ARG_ENCLOSE ? MC_ENCLOSE
571                        : MC_ARG);
572           return 0;
573         }
574     }
575   else
576     {
577       for (size_t i = 0; i < mc->macro->n_params; i++)
578         if (!mc->args[i])
579           {
580             mc->state = MC_KEYWORD;
581             return 0;
582           }
583       return mc_finished (mc);
584     }
585 }
586
587 static void PRINTF_FORMAT (3, 4)
588 mc_error (const struct macro_call *mc, const struct msg_location *loc,
589           const char *format, ...)
590 {
591   va_list args;
592   va_start (args, format);
593   if (!mc->stack)
594     {
595       const struct macro_expansion_stack stack = { .location = loc };
596       macro_error_valist (&stack, NULL, format, args);
597     }
598   else
599     macro_error_valist (mc->stack, NULL, format, args);
600   va_end (args);
601 }
602
603 static int
604 mc_add_arg (struct macro_call *mc, const struct macro_token *mt,
605             const struct msg_location *loc)
606 {
607   const struct macro_param *p = mc->param;
608   struct macro_tokens **argp = &mc->args[p - mc->macro->params];
609
610   const struct token *token = &mt->token;
611   if (token->type == T_ENDCMD || token->type == T_STOP)
612     {
613       if (*argp)
614         {
615           switch (p->arg_type)
616             {
617             case ARG_CMDEND:
618               /* This is OK, it's the expected way to end the argument. */
619               break;
620
621             case ARG_N_TOKENS:
622               mc_error (mc, loc,
623                         ngettext (_("Reached end of command expecting %zu "
624                                     "more token in argument %s to macro %s."),
625                                   _("Reached end of command expecting %zu "
626                                     "more tokens in argument %s to macro %s."),
627                                   p->n_tokens - (*argp)->n),
628                         p->n_tokens - (*argp)->n, p->name, mc->macro->name);
629               break;
630
631             case ARG_CHAREND:
632             case ARG_ENCLOSE:
633               {
634                 char *end = token_to_string (&p->end);
635                 mc_error (mc, loc, _("Reached end of command expecting \"%s\" "
636                                      "in argument %s to macro %s."),
637                           end, p->name, mc->macro->name);
638                 free (end);
639               }
640               break;
641             }
642         }
643
644       /* The end of a command ends the current argument, precludes any further
645          arguments, and is not itself part of the argument. */
646       return mc_finished (mc);
647     }
648
649   mc->n_tokens++;
650
651   if (!*argp)
652     *argp = xzalloc (sizeof **argp);
653
654   bool add_token;               /* Should we add 'mt' to the current arg? */
655   bool next_arg;                /* Should we advance to the next arg? */
656   switch (p->arg_type)
657     {
658     case ARG_N_TOKENS:
659       next_arg = (*argp)->n + 1 >= p->n_tokens;
660       add_token = true;
661       break;
662
663     case ARG_CHAREND:
664     case ARG_ENCLOSE:
665       next_arg = token_equal (token, &p->end);
666       add_token = !next_arg;
667       break;
668
669     case ARG_CMDEND:
670       next_arg = false;
671       add_token = true;
672       break;
673
674     default:
675       NOT_REACHED ();
676     }
677
678   if (add_token)
679     {
680       if (!macro_expand_arg (&mt->token, mc->me, *argp))
681         macro_tokens_add (*argp, mt);
682     }
683   return next_arg ? mc_next_arg (mc) : 0;
684 }
685
686 static int
687 mc_expected (struct macro_call *mc, const struct macro_token *actual,
688              const struct msg_location *loc, const struct token *expected)
689 {
690   const struct substring actual_s = (actual->syntax.length ? actual->syntax
691                                      : ss_cstr (_("<end of input>")));
692   char *expected_s = token_to_string (expected);
693   mc_error (mc, loc,
694             _("Found `%.*s' while expecting `%s' reading argument %s "
695               "to macro %s."),
696             (int) actual_s.length, actual_s.string, expected_s,
697             mc->param->name, mc->macro->name);
698   free (expected_s);
699
700   return mc_finished (mc);
701 }
702
703 static int
704 mc_enclose (struct macro_call *mc, const struct macro_token *mt,
705             const struct msg_location *loc)
706 {
707   const struct token *token = &mt->token;
708   const struct macro_param *p = mc->param;
709   if (token_equal (&p->start, token))
710     {
711       mc->n_tokens++;
712
713       struct macro_tokens **argp = &mc->args[p - mc->macro->params];
714       if (!*argp)
715         *argp = xzalloc (sizeof **argp);
716       mc->state = MC_ARG;
717       return 0;
718     }
719   else if (p->positional && (token->type == T_ENDCMD || token->type == T_STOP))
720     return mc_finished (mc);
721   else
722     return mc_expected (mc, mt, loc, &p->start);
723 }
724
725 static const struct macro_param *
726 macro_find_parameter_by_name (const struct macro *m, struct substring name)
727 {
728   if (!m)
729     return NULL;
730
731   ss_ltrim (&name, ss_cstr ("!"));
732
733   for (size_t i = 0; i < m->n_params; i++)
734     {
735       const struct macro_param *p = &m->params[i];
736       struct substring p_name = ss_cstr (p->name + 1);
737       if (!utf8_strncasecmp (p_name.string, p_name.length,
738                              name.string, name.length))
739         return p;
740     }
741   return NULL;
742 }
743
744 static int
745 mc_keyword (struct macro_call *mc, const struct macro_token *mt,
746             const struct msg_location *loc)
747 {
748   const struct token *token = &mt->token;
749   if (token->type != T_ID)
750     return mc_finished (mc);
751
752   const struct macro_param *p = macro_find_parameter_by_name (mc->macro,
753                                                               token->string);
754   if (p)
755     {
756       struct macro_tokens **argp = &mc->args[p - mc->macro->params];
757       if (*argp)
758         mc_error (mc, loc,
759                   _("Argument %s multiply specified in call to macro %s."),
760                   p->name, mc->macro->name);
761
762       *argp = xzalloc (sizeof **argp);
763       mc->param = p;
764       mc->n_tokens++;
765       mc->state = MC_EQUALS;
766       return 0;
767     }
768
769   return mc_finished (mc);
770 }
771
772 static int
773 mc_equals (struct macro_call *mc, const struct macro_token *mt,
774            const struct msg_location *loc)
775 {
776   if (mt->token.type == T_EQUALS)
777     {
778       mc->n_tokens++;
779       mc->state = mc->param->arg_type == ARG_ENCLOSE ? MC_ENCLOSE : MC_ARG;
780       return 0;
781     }
782
783   return mc_expected (mc, mt, loc, &(struct token) { .type = T_EQUALS });
784 }
785
786 static int
787 macro_call_create__ (const struct macro_set *macros,
788                      const struct macro_expansion_stack *stack,
789                      const struct macro_expander *me,
790                      const struct token *token,
791                      struct macro_call **mcp)
792 {
793   const struct macro *macro = (token->type == T_ID || token->type == T_MACRO_ID
794                                ? macro_set_find (macros, token->string.string)
795                                : NULL);
796   if (!macro)
797     {
798       *mcp = NULL;
799       return -1;
800     }
801
802   struct macro_call *mc = xmalloc (sizeof *mc);
803   *mc = (struct macro_call) {
804     .macros = macros,
805     .macro = macro,
806     .n_tokens = 1,
807     .state = (!macro->n_params ? MC_FINISHED
808               : !macro->params[0].positional ? MC_KEYWORD
809               : macro->params[0].arg_type == ARG_ENCLOSE ? MC_ENCLOSE
810               : MC_ARG),
811     .args = macro->n_params ? xcalloc (macro->n_params, sizeof *mc->args) : NULL,
812     .param = macro->params,
813     .stack = stack,
814     .me = me,
815   };
816   *mcp = mc;
817
818   return mc->state == MC_FINISHED ? 1 : 0;
819 }
820
821 /* If TOKEN is the first token of a call to a macro in MACROS, create a new
822    macro expander, initializes *MCP to it.  Returns 0 if more tokens are needed
823    and should be added via macro_call_add() or 1 if the caller should next call
824    macro_call_get_expansion().
825
826    If TOKEN is not the first token of a macro call, returns -1 and sets *MCP to
827    NULL. */
828 int
829 macro_call_create (const struct macro_set *macros,
830                    const struct token *token,
831                    struct macro_call **mcp)
832 {
833   return macro_call_create__ (macros, NULL, NULL, token, mcp);
834 }
835
836 void
837 macro_call_destroy (struct macro_call *mc)
838 {
839   if (!mc)
840     return;
841
842   for (size_t i = 0; i < mc->macro->n_params; i++)
843     {
844       struct macro_tokens *a = mc->args[i];
845       if (a && a != &mc->macro->params[i].def)
846         {
847           macro_tokens_uninit (a);
848           free (a);
849         }
850     }
851   free (mc->args);
852   free (mc);
853 }
854
855 /* Adds TOKEN to the collection of tokens in MC that potentially need to be
856    macro expanded.
857
858    Returns -1 if the tokens added do not actually invoke a macro.  The caller
859    should consume the first token without expanding it.  (Later tokens might
860    invoke a macro so it's best to feed the second token into a new expander.)
861
862    Returns 0 if the macro expander needs more tokens, for macro arguments or to
863    decide whether this is actually a macro invocation.  The caller should call
864    macro_call_add() again with the next token.
865
866    Returns a positive number to indicate that the returned number of tokens
867    invoke a macro.  The number returned might be less than the number of tokens
868    added because it can take a few tokens of lookahead to determine whether the
869    macro invocation is finished.  The caller should call
870    macro_call_get_expansion() to obtain the expansion. */
871 int
872 macro_call_add (struct macro_call *mc, const struct macro_token *mt,
873                 const struct msg_location *loc)
874 {
875   switch (mc->state)
876     {
877     case MC_ARG:
878       return mc_add_arg (mc, mt, loc);
879
880     case MC_ENCLOSE:
881       return mc_enclose (mc, mt, loc);
882
883     case MC_KEYWORD:
884       return mc_keyword (mc, mt, loc);
885
886     case MC_EQUALS:
887       return mc_equals (mc, mt, loc);
888
889     default:
890       NOT_REACHED ();
891     }
892 }
893 \f
894 /* Macro expansion. */
895
896 struct macro_expander
897   {
898     /* Always available. */
899     const struct macro_set *macros;     /* Macros to expand recursively. */
900     enum segmenter_mode segmenter_mode; /* Mode for tokenization. */
901     int nesting_countdown;              /* Remaining nesting levels. */
902     const struct macro_expansion_stack *stack; /* Stack for error reporting. */
903     bool *expand;                       /* May macro calls be expanded? */
904     struct stringi_map *vars;           /* Variables from !do and !let. */
905
906     /* Only nonnull if inside a !DO loop. */
907     bool *break_;                       /* Set to true to break out of loop. */
908
909     /* Only nonnull if expanding a macro (and not, say, a macro argument). */
910     const struct macro *macro;
911     struct macro_tokens **args;
912   };
913
914 static void
915 macro_expand (const struct macro_token *mts, size_t n_mts,
916               const struct macro_expander *, struct macro_tokens *);
917
918 static size_t
919 expand_macro_function (const struct macro_expander *me,
920                        const struct macro_token *input, size_t n_input,
921                        struct string *output);
922
923 /* Parses one function argument from the N_INPUT tokens in INPUT
924    Each argument to a macro function is one of:
925
926        - A quoted string or other single literal token.
927
928        - An argument to the macro being expanded, e.g. !1 or a named argument.
929
930        - !*.
931
932        - A function invocation.
933
934    Each function invocation yields a character sequence to be turned into a
935    sequence of tokens.  The case where that character sequence is a single
936    quoted string is an important special case.
937 */
938 static size_t
939 parse_function_arg (const struct macro_expander *me,
940                     const struct macro_token *input, size_t n_input,
941                     struct string *farg)
942 {
943   assert (n_input > 0);
944
945   const struct token *token = &input[0].token;
946   if (token->type == T_MACRO_ID && me->macro)
947     {
948       const struct macro_param *param = macro_find_parameter_by_name (
949         me->macro, token->string);
950       if (param)
951         {
952           size_t param_idx = param - me->macro->params;
953           macro_tokens_to_syntax (me->args[param_idx], farg, NULL, NULL);
954           return 1;
955         }
956
957       if (ss_equals (token->string, ss_cstr ("!*")))
958         {
959           for (size_t i = 0; i < me->macro->n_params; i++)
960             {
961               if (!me->macro->params[i].positional)
962                 break;
963               if (i)
964                 ds_put_byte (farg, ' ');
965               macro_tokens_to_syntax (me->args[i], farg, NULL, NULL);
966             }
967           return 1;
968         }
969
970       const char *var = stringi_map_find__ (me->vars,
971                                             token->string.string,
972                                             token->string.length);
973       if (var)
974         {
975           ds_put_cstr (farg, var);
976           return 1;
977         }
978
979       size_t n_function = expand_macro_function (me, input, n_input, farg);
980       if (n_function)
981         return n_function;
982     }
983
984   ds_put_substring (farg, input[0].syntax);
985   return 1;
986 }
987
988 static size_t
989 parse_function_args (const struct macro_expander *me,
990                      const struct macro_token *mts, size_t n,
991                      const char *function,
992                      struct string_array *args)
993 {
994   assert (n >= 2 && mts[1].token.type == T_LPAREN);
995
996   for (size_t i = 2; i < n; )
997     {
998       if (mts[i].token.type == T_RPAREN)
999         return i + 1;
1000
1001       struct string s = DS_EMPTY_INITIALIZER;
1002       i += parse_function_arg (me, mts + i, n - i, &s);
1003       string_array_append_nocopy (args, ds_steal_cstr (&s));
1004
1005       if (i >= n)
1006         break;
1007       else if (mts[i].token.type == T_COMMA)
1008         i++;
1009       else if (mts[i].token.type != T_RPAREN)
1010         {
1011           macro_error (me->stack, &mts[i],
1012                        _("`,' or `)' expected in call to macro function %s."),
1013                        function);
1014           return 0;
1015         }
1016     }
1017
1018   macro_error (me->stack, NULL, _("Missing `)' in call to macro function %s."),
1019                function);
1020   return 0;
1021 }
1022
1023 static bool
1024 unquote_string (const char *s, enum segmenter_mode segmenter_mode,
1025                 struct string *content)
1026 {
1027   struct string_lexer slex;
1028   string_lexer_init (&slex, s, strlen (s), segmenter_mode, true);
1029
1030   struct token token1;
1031   if (string_lexer_next (&slex, &token1) != SLR_TOKEN
1032       || token1.type != T_STRING)
1033     {
1034       token_uninit (&token1);
1035       return false;
1036     }
1037
1038   struct token token2;
1039   if (string_lexer_next (&slex, &token2) != SLR_END)
1040     {
1041       token_uninit (&token1);
1042       token_uninit (&token2);
1043       return false;
1044     }
1045
1046   if (content)
1047     ds_put_substring (content, token1.string);
1048   token_uninit (&token1);
1049   return true;
1050 }
1051
1052 static const char *
1053 unquote_string_in_place (const char *s, enum segmenter_mode segmenter_mode,
1054                          struct string *tmp)
1055 {
1056   ds_init_empty (tmp);
1057   return unquote_string (s, segmenter_mode, tmp) ? ds_cstr (tmp) : s;
1058 }
1059
1060 static bool
1061 parse_integer (const char *s, int *np)
1062 {
1063   errno = 0;
1064
1065   char *tail;
1066   long int n = strtol (s, &tail, 10);
1067   *np = n < INT_MIN ? INT_MIN : n > INT_MAX ? INT_MAX : n;
1068   tail += strspn (tail, CC_SPACES);
1069   return *tail == '\0' && errno != ERANGE && n == *np;
1070 }
1071
1072 static size_t
1073 expand_macro_function (const struct macro_expander *me,
1074                        const struct macro_token *input, size_t n_input,
1075                        struct string *output)
1076 {
1077   if (!n_input || input[0].token.type != T_MACRO_ID)
1078     return 0;
1079
1080   struct macro_function
1081     {
1082       const char *name;
1083       int min_args;
1084       int max_args;
1085     };
1086   enum macro_function_id
1087     {
1088       MF_BLANKS,
1089       MF_CONCAT,
1090       MF_EVAL,
1091       MF_HEAD,
1092       MF_INDEX,
1093       MF_LENGTH,
1094       MF_QUOTE,
1095       MF_SUBSTR,
1096       MF_TAIL,
1097       MF_UNQUOTE,
1098       MF_UPCASE,
1099     };
1100   static const struct macro_function mfs[] = {
1101     [MF_BLANKS]  = { "!BLANKS",  1, 1 },
1102     [MF_CONCAT]  = { "!CONCAT",  1, INT_MAX },
1103     [MF_EVAL]    = { "!EVAL",    1, 1 },
1104     [MF_HEAD]    = { "!HEAD",    1, 1 },
1105     [MF_INDEX]   = { "!INDEX",   2, 2 },
1106     [MF_LENGTH]  = { "!LENGTH",  1, 1 },
1107     [MF_QUOTE]   = { "!QUOTE",   1, 1 },
1108     [MF_SUBSTR]  = { "!SUBSTR",  2, 3 },
1109     [MF_TAIL]    = { "!TAIL",    1, 1 },
1110     [MF_UNQUOTE] = { "!UNQUOTE", 1, 1 },
1111     [MF_UPCASE]  = { "!UPCASE",  1, 1 },
1112   };
1113
1114   if (lex_id_match_n (ss_cstr ("!NULL"), input[0].token.string, 4))
1115     return 1;
1116
1117   if (n_input < 2 || input[1].token.type != T_LPAREN)
1118     {
1119       /* Only consider macro functions when the name is followed by '('. */
1120       return 0;
1121     }
1122
1123   /* Is this a macro function name? */
1124   const struct macro_function *mf;
1125   for (mf = mfs; ; mf++)
1126     {
1127       if (mf >= mfs + sizeof mfs / sizeof *mfs)
1128         {
1129           /* Not a macro function. */
1130           return 0;
1131         }
1132
1133       if (lex_id_match_n (ss_cstr (mf->name), input[0].token.string, 4))
1134         break;
1135     }
1136
1137   enum macro_function_id id = mf - mfs;
1138
1139   struct string_array args = STRING_ARRAY_INITIALIZER;
1140   size_t n_consumed = parse_function_args (me, input, n_input, mf->name, &args);
1141   if (!n_consumed)
1142     {
1143       string_array_destroy (&args);
1144       return 0;
1145     }
1146
1147   if (args.n < mf->min_args || args.n > mf->max_args)
1148     {
1149       if (mf->min_args == 1 && mf->max_args == 1)
1150         macro_error (me->stack, NULL,
1151                      _("Macro function %s takes one argument (not %zu)."),
1152                      mf->name, args.n);
1153       else if (mf->min_args == 2 && mf->max_args == 2)
1154         macro_error (me->stack, NULL,
1155                      _("Macro function %s takes two arguments (not %zu)."),
1156                      mf->name, args.n);
1157       else if (mf->min_args == 2 && mf->max_args == 3)
1158         macro_error (me->stack, NULL,
1159                      _("Macro function %s takes two or three arguments "
1160                        "(not %zu)."),
1161                      mf->name, args.n);
1162       else if (mf->min_args == 1 && mf->max_args == INT_MAX)
1163         macro_error (me->stack, NULL,
1164                      _("Macro function %s needs at least one argument."),
1165                      mf->name);
1166       else
1167         NOT_REACHED ();
1168       string_array_destroy (&args);
1169       return 0;
1170     }
1171
1172   switch (id)
1173     {
1174     case MF_LENGTH:
1175       ds_put_format (output, "%zu", strlen (args.strings[0]));
1176       break;
1177
1178     case MF_BLANKS:
1179       {
1180         int n;
1181         if (!parse_integer (args.strings[0], &n))
1182           {
1183             macro_error (me->stack, NULL,
1184                          _("Argument to !BLANKS must be non-negative integer "
1185                            "(not \"%s\")."), args.strings[0]);
1186             string_array_destroy (&args);
1187             return 0;
1188           }
1189
1190         ds_put_byte_multiple (output, ' ', n);
1191       }
1192       break;
1193
1194     case MF_CONCAT:
1195       for (size_t i = 0; i < args.n; i++)
1196         if (!unquote_string (args.strings[i], me->segmenter_mode, output))
1197           ds_put_cstr (output, args.strings[i]);
1198       break;
1199
1200     case MF_HEAD:
1201       {
1202         struct string tmp;
1203         const char *s = unquote_string_in_place (args.strings[0],
1204                                                  me->segmenter_mode, &tmp);
1205
1206         struct macro_tokens mts = { .n = 0 };
1207         macro_tokens_from_string__ (&mts, ss_cstr (s), me->segmenter_mode,
1208                                     me->stack);
1209         if (mts.n > 0)
1210           ds_put_substring (output, mts.mts[0].syntax);
1211         macro_tokens_uninit (&mts);
1212         ds_destroy (&tmp);
1213       }
1214       break;
1215
1216     case MF_INDEX:
1217       {
1218         const char *haystack = args.strings[0];
1219         const char *needle = strstr (haystack, args.strings[1]);
1220         ds_put_format (output, "%zu", needle ? needle - haystack + 1 : 0);
1221       }
1222       break;
1223
1224     case MF_QUOTE:
1225       if (unquote_string (args.strings[0], me->segmenter_mode, NULL))
1226         ds_put_cstr (output, args.strings[0]);
1227       else
1228         {
1229           ds_extend (output, strlen (args.strings[0]) + 2);
1230           ds_put_byte (output, '\'');
1231           for (const char *p = args.strings[0]; *p; p++)
1232             {
1233               if (*p == '\'')
1234                 ds_put_byte (output, '\'');
1235               ds_put_byte (output, *p);
1236             }
1237           ds_put_byte (output, '\'');
1238         }
1239       break;
1240
1241     case MF_SUBSTR:
1242       {
1243         int start;
1244         if (!parse_integer (args.strings[1], &start) || start < 1)
1245           {
1246             macro_error (me->stack, NULL,
1247                          _("Second argument of !SUBSTR must be "
1248                            "positive integer (not \"%s\")."),
1249                          args.strings[1]);
1250             string_array_destroy (&args);
1251             return 0;
1252           }
1253
1254         int count = INT_MAX;
1255         if (args.n > 2 && (!parse_integer (args.strings[2], &count) || count < 0))
1256           {
1257             macro_error (me->stack, NULL,
1258                          _("Third argument of !SUBSTR must be "
1259                            "non-negative integer (not \"%s\")."),
1260                          args.strings[2]);
1261             string_array_destroy (&args);
1262             return 0;
1263           }
1264
1265         struct substring s = ss_cstr (args.strings[0]);
1266         ds_put_substring (output, ss_substr (s, start - 1, count));
1267       }
1268       break;
1269
1270     case MF_TAIL:
1271       {
1272         struct string tmp;
1273         const char *s = unquote_string_in_place (args.strings[0],
1274                                                  me->segmenter_mode, &tmp);
1275
1276         struct macro_tokens mts = { .n = 0 };
1277         macro_tokens_from_string__ (&mts, ss_cstr (s), me->segmenter_mode,
1278                                     me->stack);
1279         if (mts.n > 1)
1280           {
1281             struct macro_tokens tail = { .mts = mts.mts + 1, .n = mts.n - 1 };
1282             macro_tokens_to_syntax (&tail, output, NULL, NULL);
1283           }
1284         macro_tokens_uninit (&mts);
1285         ds_destroy (&tmp);
1286       }
1287       break;
1288
1289     case MF_UNQUOTE:
1290       if (!unquote_string (args.strings[0], me->segmenter_mode, output))
1291         ds_put_cstr (output, args.strings[0]);
1292       break;
1293
1294     case MF_UPCASE:
1295       {
1296         struct string tmp;
1297         const char *s = unquote_string_in_place (args.strings[0],
1298                                                  me->segmenter_mode, &tmp);
1299         char *upper = utf8_to_upper (s);
1300         ds_put_cstr (output, upper);
1301         free (upper);
1302         ds_destroy (&tmp);
1303       }
1304       break;
1305
1306     case MF_EVAL:
1307       {
1308         struct macro_tokens mts = { .n = 0 };
1309         macro_tokens_from_string__ (&mts, ss_cstr (args.strings[0]),
1310                                     me->segmenter_mode, me->stack);
1311         struct macro_tokens exp = { .n = 0 };
1312         struct macro_expansion_stack stack = {
1313           .name = "!EVAL",
1314           .next = me->stack
1315         };
1316         struct macro_expander subme = *me;
1317         subme.break_ = NULL;
1318         subme.stack = &stack;
1319
1320         macro_expand (mts.mts, mts.n, &subme, &exp);
1321         macro_tokens_to_syntax (&exp, output, NULL, NULL);
1322         macro_tokens_uninit (&exp);
1323         macro_tokens_uninit (&mts);
1324       }
1325       break;
1326
1327     default:
1328       NOT_REACHED ();
1329     }
1330
1331   string_array_destroy (&args);
1332   return n_consumed;
1333 }
1334
1335 static char *macro_evaluate_or (const struct macro_expander *me,
1336                                 const struct macro_token **tokens,
1337                                 const struct macro_token *end);
1338
1339 static char *
1340 macro_evaluate_literal (const struct macro_expander *me,
1341                         const struct macro_token **tokens,
1342                         const struct macro_token *end)
1343 {
1344   const struct macro_token *p = *tokens;
1345   if (p >= end)
1346     return NULL;
1347   if (p->token.type == T_LPAREN)
1348     {
1349       p++;
1350       char *value = macro_evaluate_or (me, &p, end);
1351       if (!value)
1352         return NULL;
1353       if (p >= end || p->token.type != T_RPAREN)
1354         {
1355           free (value);
1356           macro_error (me->stack, p < end ? p : NULL,
1357                        _("Expecting ')' in macro expression."));
1358           return NULL;
1359         }
1360       p++;
1361       *tokens = p;
1362       return value;
1363     }
1364   else if (p->token.type == T_RPAREN)
1365     {
1366       macro_error (me->stack, p, _("Expecting literal or function invocation "
1367                                    "in macro expression."));
1368       return NULL;
1369     }
1370
1371   struct string function_output = DS_EMPTY_INITIALIZER;
1372   size_t function_consumed = parse_function_arg (me, p, end - p,
1373                                                  &function_output);
1374   struct string unquoted = DS_EMPTY_INITIALIZER;
1375   if (unquote_string (ds_cstr (&function_output), me->segmenter_mode,
1376                       &unquoted))
1377     {
1378       ds_swap (&function_output, &unquoted);
1379       ds_destroy (&unquoted);
1380     }
1381   *tokens = p + function_consumed;
1382   return ds_steal_cstr (&function_output);
1383 }
1384
1385 /* Returns true if MT is valid as a macro operator.  Only operators written as
1386    symbols (e.g. <>) are usable in macro expressions, not operator written as
1387    letters (e.g. EQ). */
1388 static bool
1389 is_macro_operator (const struct macro_token *mt)
1390 {
1391   return mt->syntax.length > 0 && !c_isalpha (mt->syntax.string[0]);
1392 }
1393
1394 static enum token_type
1395 parse_relational_op (const struct macro_token *mt)
1396 {
1397   switch (mt->token.type)
1398     {
1399     case T_EQUALS:
1400       return T_EQ;
1401
1402     case T_NE:
1403     case T_LT:
1404     case T_GT:
1405     case T_LE:
1406     case T_GE:
1407       return is_macro_operator (mt) ? mt->token.type : T_STOP;
1408
1409     case T_MACRO_ID:
1410       return (ss_equals_case (mt->token.string, ss_cstr ("!EQ")) ? T_EQ
1411               : ss_equals_case (mt->token.string, ss_cstr ("!NE")) ? T_NE
1412               : ss_equals_case (mt->token.string, ss_cstr ("!LT")) ? T_LT
1413               : ss_equals_case (mt->token.string, ss_cstr ("!GT")) ? T_GT
1414               : ss_equals_case (mt->token.string, ss_cstr ("!LE")) ? T_LE
1415               : ss_equals_case (mt->token.string, ss_cstr ("!GE")) ? T_GE
1416               : T_STOP);
1417
1418     default:
1419       return T_STOP;
1420     }
1421 }
1422
1423 static char *
1424 macro_evaluate_relational (const struct macro_expander *me,
1425                            const struct macro_token **tokens,
1426                            const struct macro_token *end)
1427 {
1428   const struct macro_token *p = *tokens;
1429   char *lhs = macro_evaluate_literal (me, &p, end);
1430   if (!lhs)
1431     return NULL;
1432
1433   enum token_type op = p >= end ? T_STOP : parse_relational_op (p);
1434   if (op == T_STOP)
1435     {
1436       *tokens = p;
1437       return lhs;
1438     }
1439   p++;
1440
1441   char *rhs = macro_evaluate_literal (me, &p, end);
1442   if (!rhs)
1443     {
1444       free (lhs);
1445       return NULL;
1446     }
1447
1448   struct string lhs_tmp, rhs_tmp;
1449   int cmp = strcmp (unquote_string_in_place (lhs, me->segmenter_mode,
1450                                              &lhs_tmp),
1451                     unquote_string_in_place (rhs, me->segmenter_mode,
1452                                              &rhs_tmp));
1453   ds_destroy (&lhs_tmp);
1454   ds_destroy (&rhs_tmp);
1455
1456   free (lhs);
1457   free (rhs);
1458
1459   bool b = (op == T_EQUALS || op == T_EQ ? !cmp
1460             : op == T_NE ? cmp
1461             : op == T_LT ? cmp < 0
1462             : op == T_GT ? cmp > 0
1463             : op == T_LE ? cmp <= 0
1464             : /* T_GE */ cmp >= 0);
1465
1466   *tokens = p;
1467   return xstrdup (b ? "1" : "0");
1468 }
1469
1470 static char *
1471 macro_evaluate_not (const struct macro_expander *me,
1472                     const struct macro_token **tokens,
1473                     const struct macro_token *end)
1474 {
1475   const struct macro_token *p = *tokens;
1476
1477   unsigned int negations = 0;
1478   while (p < end
1479          && (ss_equals_case (p->syntax, ss_cstr ("!NOT"))
1480              || ss_equals (p->syntax, ss_cstr ("~"))))
1481     {
1482       p++;
1483       negations++;
1484     }
1485
1486   char *operand = macro_evaluate_relational (me, &p, end);
1487   if (!operand || !negations)
1488     {
1489       *tokens = p;
1490       return operand;
1491     }
1492
1493   bool b = strcmp (operand, "0") ^ (negations & 1);
1494   free (operand);
1495   *tokens = p;
1496   return xstrdup (b ? "1" : "0");
1497 }
1498
1499 static char *
1500 macro_evaluate_and (const struct macro_expander *me,
1501                     const struct macro_token **tokens,
1502                     const struct macro_token *end)
1503 {
1504   const struct macro_token *p = *tokens;
1505   char *lhs = macro_evaluate_not (me, &p, end);
1506   if (!lhs)
1507     return NULL;
1508
1509   while (p < end
1510          && (ss_equals_case (p->syntax, ss_cstr ("!AND"))
1511              || ss_equals (p->syntax, ss_cstr ("&"))))
1512     {
1513       p++;
1514       char *rhs = macro_evaluate_not (me, &p, end);
1515       if (!rhs)
1516         {
1517           free (lhs);
1518           return NULL;
1519         }
1520
1521       bool b = strcmp (lhs, "0") && strcmp (rhs, "0");
1522       free (lhs);
1523       free (rhs);
1524       lhs = xstrdup (b ? "1" : "0");
1525     }
1526   *tokens = p;
1527   return lhs;
1528 }
1529
1530 static char *
1531 macro_evaluate_or (const struct macro_expander *me,
1532                    const struct macro_token **tokens,
1533                    const struct macro_token *end)
1534 {
1535   const struct macro_token *p = *tokens;
1536   char *lhs = macro_evaluate_and (me, &p, end);
1537   if (!lhs)
1538     return NULL;
1539
1540   while (p < end
1541          && (ss_equals_case (p->syntax, ss_cstr ("!OR"))
1542              || ss_equals (p->syntax, ss_cstr ("|"))))
1543     {
1544       p++;
1545       char *rhs = macro_evaluate_and (me, &p, end);
1546       if (!rhs)
1547         {
1548           free (lhs);
1549           return NULL;
1550         }
1551
1552       bool b = strcmp (lhs, "0") || strcmp (rhs, "0");
1553       free (lhs);
1554       free (rhs);
1555       lhs = xstrdup (b ? "1" : "0");
1556     }
1557   *tokens = p;
1558   return lhs;
1559 }
1560
1561 static char *
1562 macro_evaluate_expression (const struct macro_token **tokens, size_t n_tokens,
1563                            const struct macro_expander *me)
1564 {
1565   return macro_evaluate_or (me, tokens, *tokens + n_tokens);
1566 }
1567
1568 static bool
1569 macro_evaluate_number (const struct macro_token **tokens, size_t n_tokens,
1570                        const struct macro_expander *me,
1571                        double *number)
1572 {
1573   char *s = macro_evaluate_expression (tokens, n_tokens, me);
1574   if (!s)
1575     return false;
1576
1577   struct macro_tokens mts = { .n = 0 };
1578   macro_tokens_from_string__ (&mts, ss_cstr (s), me->segmenter_mode, me->stack);
1579   if (mts.n != 1 || !token_is_number (&mts.mts[0].token))
1580     {
1581       macro_error (me->stack, mts.n > 0 ? &mts.mts[0] : NULL,
1582                    _("Macro expression must evaluate to "
1583                      "a number (not \"%s\")."), s);
1584       free (s);
1585       macro_tokens_uninit (&mts);
1586       return false;
1587     }
1588
1589   *number = token_number (&mts.mts[0].token);
1590   free (s);
1591   macro_tokens_uninit (&mts);
1592   return true;
1593 }
1594
1595 static const struct macro_token *
1596 find_ifend_clause (const struct macro_token *p, const struct macro_token *end)
1597 {
1598   size_t nesting = 0;
1599   for (; p < end; p++)
1600     {
1601       if (p->token.type != T_MACRO_ID)
1602         continue;
1603
1604       if (ss_equals_case (p->token.string, ss_cstr ("!IF")))
1605         nesting++;
1606       else if (lex_id_match_n (p->token.string, ss_cstr ("!IFEND"), 4))
1607         {
1608           if (!nesting)
1609             return p;
1610           nesting--;
1611         }
1612       else if (lex_id_match_n (p->token.string, ss_cstr ("!ELSE"), 4)
1613                && !nesting)
1614         return p;
1615     }
1616   return NULL;
1617 }
1618
1619 static size_t
1620 macro_expand_if (const struct macro_token *tokens, size_t n_tokens,
1621                  const struct macro_expander *me,
1622                  struct macro_tokens *exp)
1623 {
1624   const struct macro_token *p = tokens;
1625   const struct macro_token *end = tokens + n_tokens;
1626
1627   if (p >= end || !ss_equals_case (p->token.string, ss_cstr ("!IF")))
1628     return 0;
1629
1630   p++;
1631   char *result = macro_evaluate_expression (&p, end - p, me);
1632   if (!result)
1633     return 0;
1634   bool b = strcmp (result, "0");
1635   free (result);
1636
1637   if (p >= end
1638       || p->token.type != T_MACRO_ID
1639       || !lex_id_match_n (p->token.string, ss_cstr ("!THEN"), 4))
1640     {
1641       macro_error (me->stack, p < end ? p : NULL,
1642                    _("!THEN expected in macro !IF construct."));
1643       return 0;
1644     }
1645
1646   const struct macro_token *start_then = p + 1;
1647   const struct macro_token *end_then = find_ifend_clause (start_then, end);
1648   if (!end_then)
1649     {
1650       macro_error (me->stack, NULL,
1651                    _("!ELSE or !IFEND expected in macro !IF construct."));
1652       return 0;
1653     }
1654
1655   const struct macro_token *start_else, *end_if;
1656   if (lex_id_match_n (end_then->token.string, ss_cstr ("!ELSE"), 4))
1657     {
1658       start_else = end_then + 1;
1659       end_if = find_ifend_clause (start_else, end);
1660       if (!end_if
1661           || !lex_id_match_n (end_if->token.string, ss_cstr ("!IFEND"), 4))
1662         {
1663           macro_error (me->stack, end_if ? end_if : NULL,
1664                        _("!IFEND expected in macro !IF construct."));
1665           return 0;
1666         }
1667     }
1668   else
1669     {
1670       start_else = NULL;
1671       end_if = end_then;
1672     }
1673
1674   const struct macro_token *start;
1675   size_t n;
1676   if (b)
1677     {
1678       start = start_then;
1679       n = end_then - start_then;
1680     }
1681   else if (start_else)
1682     {
1683       start = start_else;
1684       n = end_if - start_else;
1685     }
1686   else
1687     {
1688       start = NULL;
1689       n = 0;
1690     }
1691
1692   if (n)
1693     {
1694       struct macro_expansion_stack stack = {
1695         .name = "!IF",
1696         .next = me->stack,
1697       };
1698       struct macro_expander subme = *me;
1699       subme.stack = &stack;
1700       macro_expand (start, n, &subme, exp);
1701     }
1702   return (end_if + 1) - tokens;
1703 }
1704
1705 static size_t
1706 macro_parse_let (const struct macro_token *tokens, size_t n_tokens,
1707                  const struct macro_expander *me)
1708 {
1709   const struct macro_token *p = tokens;
1710   const struct macro_token *end = tokens + n_tokens;
1711
1712   if (p >= end || !ss_equals_case (p->token.string, ss_cstr ("!LET")))
1713     return 0;
1714   p++;
1715
1716   if (p >= end || p->token.type != T_MACRO_ID)
1717     {
1718       macro_error (me->stack, p < end ? p : NULL,
1719                    _("Expected macro variable name following !LET."));
1720       return 0;
1721     }
1722   const struct substring var_name = p->token.string;
1723   if (is_macro_keyword (var_name)
1724       || macro_find_parameter_by_name (me->macro, var_name))
1725     {
1726       macro_error (me->stack, p < end ? p : NULL,
1727                    _("Cannot use argument name or macro keyword "
1728                      "\"%.*s\" as !LET variable."),
1729                    (int) var_name.length, var_name.string);
1730       return 0;
1731     }
1732   p++;
1733
1734   if (p >= end || p->token.type != T_EQUALS)
1735     {
1736       macro_error (me->stack, p < end ? p : NULL,
1737                    _("Expected `=' following !LET."));
1738       return 0;
1739     }
1740   p++;
1741
1742   char *value = macro_evaluate_expression (&p, end - p, me);
1743   if (!value)
1744     return 0;
1745
1746   stringi_map_replace_nocopy (me->vars, ss_xstrdup (var_name), value);
1747   return p - tokens;
1748 }
1749
1750 static const struct macro_token *
1751 find_doend (const struct macro_expansion_stack *stack,
1752             const struct macro_token *p, const struct macro_token *end)
1753 {
1754   size_t nesting = 0;
1755   for (; p < end; p++)
1756     {
1757       if (p->token.type != T_MACRO_ID)
1758         continue;
1759
1760       if (ss_equals_case (p->token.string, ss_cstr ("!DO")))
1761         nesting++;
1762       else if (lex_id_match_n (p->token.string, ss_cstr ("!DOEND"), 4))
1763         {
1764           if (!nesting)
1765             return p;
1766           nesting--;
1767         }
1768     }
1769   macro_error (stack, NULL, _("Missing !DOEND."));
1770   return NULL;
1771 }
1772
1773 static size_t
1774 macro_expand_do (const struct macro_token *tokens, size_t n_tokens,
1775                  const struct macro_expander *me,
1776                  struct macro_tokens *exp)
1777 {
1778   const struct macro_token *p = tokens;
1779   const struct macro_token *end = tokens + n_tokens;
1780
1781   if (p >= end || !ss_equals_case (p->token.string, ss_cstr ("!DO")))
1782     return 0;
1783   p++;
1784
1785   if (p >= end || p->token.type != T_MACRO_ID)
1786     {
1787       macro_error (me->stack, p < end ? p : NULL,
1788                    _("Expected macro variable name following !DO."));
1789       return 0;
1790     }
1791   const struct substring var_name = p->token.string;
1792   if (is_macro_keyword (var_name)
1793       || macro_find_parameter_by_name (me->macro, var_name))
1794     {
1795       macro_error (me->stack, p, _("Cannot use argument name or macro "
1796                                    "keyword as !DO variable."));
1797       return 0;
1798     }
1799   p++;
1800
1801   struct macro_expansion_stack substack = {
1802     .name = "!DO",
1803     .next = me->stack,
1804   };
1805   bool break_ = false;
1806   struct macro_expander subme = *me;
1807   subme.break_ = &break_;
1808   subme.stack = &substack;
1809
1810   int miterate = settings_get_miterate ();
1811   if (p < end && p->token.type == T_MACRO_ID
1812       && ss_equals_case (p->token.string, ss_cstr ("!IN")))
1813     {
1814       p++;
1815       char *list = macro_evaluate_expression (&p, end - p, &subme);
1816       if (!list)
1817         return 0;
1818
1819       struct macro_tokens items = { .n = 0 };
1820       macro_tokens_from_string__ (&items, ss_cstr (list), me->segmenter_mode,
1821                                   me->stack);
1822       free (list);
1823
1824       const struct macro_token *do_end = find_doend (subme.stack, p, end);
1825       if (!do_end)
1826         {
1827           macro_tokens_uninit (&items);
1828           return 0;
1829         }
1830
1831       for (size_t i = 0; i < items.n && !break_; i++)
1832         {
1833           if (i >= miterate)
1834             {
1835               macro_error (&substack, NULL,
1836                            _("!DO loop over list exceeded "
1837                              "maximum number of iterations %d.  "
1838                              "(Use SET MITERATE to change the limit.)"),
1839                            miterate);
1840               break;
1841             }
1842           stringi_map_replace_nocopy (me->vars, ss_xstrdup (var_name),
1843                                       ss_xstrdup (items.mts[i].syntax));
1844
1845           macro_expand (p, do_end - p, &subme, exp);
1846         }
1847       macro_tokens_uninit (&items);
1848       return do_end - tokens + 1;
1849     }
1850   else if (p < end && p->token.type == T_EQUALS)
1851     {
1852       p++;
1853       double first;
1854       if (!macro_evaluate_number (&p, end - p, &subme, &first))
1855         return 0;
1856
1857       if (p >= end || p->token.type != T_MACRO_ID
1858           || !ss_equals_case (p->token.string, ss_cstr ("!TO")))
1859         {
1860           macro_error (subme.stack, p < end ? p : NULL,
1861                        _("Expected !TO in numerical !DO loop."));
1862           return 0;
1863         }
1864       p++;
1865
1866       double last;
1867       if (!macro_evaluate_number (&p, end - p, &subme, &last))
1868         return 0;
1869
1870       double by = 1.0;
1871       if (p < end && p->token.type == T_MACRO_ID
1872           && ss_equals_case (p->token.string, ss_cstr ("!BY")))
1873         {
1874           p++;
1875           if (!macro_evaluate_number (&p, end - p, &subme, &by))
1876             return 0;
1877
1878           if (by == 0.0)
1879             {
1880               macro_error (subme.stack, NULL, _("!BY value cannot be zero."));
1881               return 0;
1882             }
1883         }
1884
1885       const struct macro_token *do_end = find_doend (subme.stack, p, end);
1886       if (!do_end)
1887         return 0;
1888       if ((by > 0 && first <= last) || (by < 0 && first >= last))
1889         {
1890           int i = 0;
1891           for (double index = first;
1892                by > 0 ? (index <= last) : (index >= last) && !break_;
1893                index += by)
1894             {
1895               if (i++ > miterate)
1896                 {
1897                   macro_error (subme.stack, NULL,
1898                                _("Numerical !DO loop exceeded "
1899                                  "maximum number of iterations %d.  "
1900                                  "(Use SET MITERATE to change the limit.)"),
1901                                miterate);
1902                   break;
1903                 }
1904
1905               char index_s[DBL_BUFSIZE_BOUND];
1906               c_dtoastr (index_s, sizeof index_s, 0, 0, index);
1907               stringi_map_replace_nocopy (me->vars, ss_xstrdup (var_name),
1908                                           xstrdup (index_s));
1909
1910               macro_expand (p, do_end - p, &subme, exp);
1911             }
1912         }
1913
1914       return do_end - tokens + 1;
1915     }
1916   else
1917     {
1918       macro_error (me->stack, p < end ? p : NULL,
1919                    _("Expected `=' or !IN in !DO loop."));
1920       return 0;
1921     }
1922 }
1923
1924 static void
1925 macro_expand_arg__ (const struct macro_expander *me, size_t idx,
1926                   struct macro_tokens *exp)
1927 {
1928   const struct macro_param *param = &me->macro->params[idx];
1929   const struct macro_tokens *arg = me->args[idx];
1930
1931   if (*me->expand && param->expand_arg)
1932     {
1933       struct stringi_map vars = STRINGI_MAP_INITIALIZER (vars);
1934       struct macro_expansion_stack stack = {
1935         .name = param->name,
1936         .next = me->stack,
1937       };
1938       struct macro_expander subme = {
1939         .macros = me->macros,
1940         .macro = NULL,
1941         .args = NULL,
1942         .segmenter_mode = me->segmenter_mode,
1943         .expand = me->expand,
1944         .break_ = NULL,
1945         .vars = &vars,
1946         .nesting_countdown = me->nesting_countdown,
1947         .stack = &stack,
1948       };
1949       macro_expand (arg->mts, arg->n, &subme, exp);
1950       stringi_map_destroy (&vars);
1951     }
1952   else
1953     for (size_t i = 0; i < arg->n; i++)
1954       macro_tokens_add (exp, &arg->mts[i]);
1955 }
1956
1957 static bool
1958 macro_expand_arg (const struct token *token, const struct macro_expander *me,
1959                   struct macro_tokens *exp)
1960 {
1961   if (!me || token->type != T_MACRO_ID)
1962     return false;
1963
1964   /* Macro arguments. */
1965   if (me->macro)
1966     {
1967       const struct macro_param *param = macro_find_parameter_by_name (
1968         me->macro, token->string);
1969       if (param)
1970         {
1971           macro_expand_arg__ (me, param - me->macro->params, exp);
1972           return true;
1973         }
1974       else if (ss_equals (token->string, ss_cstr ("!*")))
1975         {
1976           for (size_t j = 0; j < me->macro->n_params; j++)
1977             macro_expand_arg__ (me, j, exp);
1978           return true;
1979         }
1980     }
1981
1982   /* Variables set by !DO or !LET. */
1983   const char *var = stringi_map_find__ (me->vars, token->string.string,
1984                                         token->string.length);
1985   if (var)
1986     {
1987       macro_tokens_from_string__ (exp, ss_cstr (var),
1988                                   me->segmenter_mode, me->stack);
1989       return true;
1990     }
1991
1992   return false;
1993 }
1994
1995 static size_t
1996 macro_expand__ (const struct macro_token *mts, size_t n,
1997                 const struct macro_expander *me,
1998                 struct macro_tokens *exp)
1999 {
2000   const struct token *token = &mts[0].token;
2001
2002   /* Recursive macro calls. */
2003   if (*me->expand)
2004     {
2005       struct macro_call *submc;
2006       int n_call = macro_call_create__ (me->macros, me->stack, me,
2007                                         token, &submc);
2008       for (size_t j = 1; !n_call; j++)
2009         {
2010           const struct macro_token endcmd
2011             = { .token = { .type = T_ENDCMD } };
2012           n_call = macro_call_add (submc, j < n ? &mts[j] : &endcmd, NULL);
2013         }
2014       if (n_call > 0)
2015         {
2016           struct stringi_map vars = STRINGI_MAP_INITIALIZER (vars);
2017           struct macro_expansion_stack stack = {
2018             .name = submc->macro->name,
2019             .location = submc->macro->location,
2020             .next = me->stack,
2021           };
2022           struct macro_expander subme = {
2023             .macros = submc->macros,
2024             .macro = submc->macro,
2025             .args = submc->args,
2026             .segmenter_mode = me->segmenter_mode,
2027             .expand = me->expand,
2028             .break_ = NULL,
2029             .vars = &vars,
2030             .nesting_countdown = me->nesting_countdown - 1,
2031             .stack = &stack,
2032           };
2033           const struct macro_tokens *body = &submc->macro->body;
2034           macro_expand (body->mts, body->n, &subme, exp);
2035           macro_call_destroy (submc);
2036           stringi_map_destroy (&vars);
2037           return n_call;
2038         }
2039
2040       macro_call_destroy (submc);
2041     }
2042
2043   if (token->type != T_MACRO_ID)
2044     {
2045       macro_tokens_add (exp, &mts[0]);
2046       return 1;
2047     }
2048
2049   /* Parameters and macro variables. */
2050   if (macro_expand_arg (token, me, exp))
2051     return 1;
2052
2053   /* Macro functions. */
2054   struct string function_output = DS_EMPTY_INITIALIZER;
2055   size_t n_function = expand_macro_function (me, mts, n, &function_output);
2056   if (n_function)
2057     {
2058       macro_tokens_from_string__ (exp, function_output.ss,
2059                                   me->segmenter_mode, me->stack);
2060       ds_destroy (&function_output);
2061
2062       return n_function;
2063     }
2064
2065   size_t n_if = macro_expand_if (mts, n, me, exp);
2066   if (n_if > 0)
2067     return n_if;
2068
2069   size_t n_let = macro_parse_let (mts, n, me);
2070   if (n_let > 0)
2071     return n_let;
2072
2073   size_t n_do = macro_expand_do (mts, n, me, exp);
2074   if (n_do > 0)
2075     return n_do;
2076
2077   if (lex_id_match_n (token->string, ss_cstr ("!break"), 4))
2078     {
2079       if (me->break_)
2080         *me->break_ = true;
2081       else
2082         macro_error (me->stack, &mts[0], _("!BREAK outside !DO."));
2083     }
2084   else if (lex_id_match_n (token->string, ss_cstr ("!onexpand"), 4))
2085     *me->expand = true;
2086   else if (lex_id_match_n (token->string, ss_cstr ("!offexpand"), 4))
2087     *me->expand = false;
2088   else
2089     macro_tokens_add (exp, &mts[0]);
2090   return 1;
2091 }
2092
2093 static void
2094 macro_expand (const struct macro_token *mts, size_t n,
2095               const struct macro_expander *me,
2096               struct macro_tokens *exp)
2097 {
2098   if (me->nesting_countdown <= 0)
2099     {
2100       macro_error (me->stack, NULL, _("Maximum nesting level %d exceeded.  "
2101                                       "(Use SET MNEST to change the limit.)"),
2102                    settings_get_mnest ());
2103       for (size_t i = 0; i < n; i++)
2104         macro_tokens_add (exp, &mts[i]);
2105       return;
2106     }
2107
2108   for (size_t i = 0; i < n; )
2109     {
2110       if (me->break_ && *me->break_)
2111         break;
2112
2113       size_t consumed = macro_expand__ (&mts[i], n - i, me, exp);
2114       assert (consumed > 0 && i + consumed <= n);
2115       i += consumed;
2116     }
2117 }
2118
2119 void
2120 macro_call_expand (struct macro_call *mc, enum segmenter_mode segmenter_mode,
2121                    const struct msg_location *call_loc,
2122                    struct macro_tokens *exp)
2123 {
2124   assert (mc->state == MC_FINISHED);
2125
2126   bool expand = true;
2127   struct stringi_map vars = STRINGI_MAP_INITIALIZER (vars);
2128   struct macro_expansion_stack stack0 = {
2129     .location = call_loc,
2130   };
2131   struct macro_expansion_stack stack1 = {
2132     .next = &stack0,
2133     .name = mc->macro->name,
2134     .location = mc->macro->location,
2135   };
2136   struct macro_expander me = {
2137     .macros = mc->macros,
2138     .macro = mc->macro,
2139     .args = mc->args,
2140     .segmenter_mode = segmenter_mode,
2141     .expand = &expand,
2142     .break_ = NULL,
2143     .vars = &vars,
2144     .nesting_countdown = settings_get_mnest (),
2145     .stack = &stack1,
2146   };
2147
2148   const struct macro_tokens *body = &mc->macro->body;
2149   macro_expand (body->mts, body->n, &me, exp);
2150
2151   stringi_map_destroy (&vars);
2152 }
2153