Add manpage for stge(4)
[dragonfly.git] / contrib / texinfo-4 / makeinfo / defun.c
1 /* defun.c -- @defun and friends.
2    $Id: defun.c,v 1.11 2004/04/11 17:56:46 karl Exp $
3
4    Copyright (C) 1998, 1999, 2000, 2001, 2002, 2003, 2004 Free Software
5    Foundation, Inc.
6
7    This program is free software; you can redistribute it and/or modify
8    it under the terms of the GNU General Public License as published by
9    the Free Software Foundation; either version 2, or (at your option)
10    any later version.
11
12    This program is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15    GNU General Public License for more details.
16
17    You should have received a copy of the GNU General Public License
18    along with this program; if not, write to the Free Software Foundation,
19    Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.  */
20
21 #include "system.h"
22 #include "defun.h"
23 #include "xml.h"
24 #include "insertion.h"
25 #include "makeinfo.h"
26 #include "cmds.h"
27 #include "html.h"
28
29
30 #define DEFUN_SELF_DELIMITING(c) \
31   ((c) == '(' || (c) == ')' || (c) == '[' || (c) == ']')
32
33 struct token_accumulator
34 {
35   unsigned int length;
36   unsigned int index;
37   char **tokens;
38 };
39
40 static void
41 initialize_token_accumulator (struct token_accumulator *accumulator)
42 {
43   accumulator->length = 0;
44   accumulator->index = 0;
45   accumulator->tokens = NULL;
46 }
47
48 static void
49 accumulate_token (struct token_accumulator *accumulator, char *token)
50 {
51   if (accumulator->index >= accumulator->length)
52     {
53       accumulator->length += 10;
54       accumulator->tokens = xrealloc (accumulator->tokens,
55                                       (accumulator->length * sizeof (char *)));
56     }
57   accumulator->tokens[accumulator->index] = token;
58   accumulator->index += 1;
59 }
60
61 /* Given STRING_POINTER pointing at an open brace, skip forward and return a
62    pointer to just past the matching close brace. */
63 static int
64 scan_group_in_string (char **string_pointer)
65 {
66   char *scan_string = (*string_pointer) + 1;
67   unsigned int level = 1;
68   int started_command = 0;
69
70   for (;;)
71     {
72       int c;
73       if (level == 0)
74         {
75           *string_pointer = scan_string;
76           return 1;
77         }
78       c = *scan_string++;
79       if (c == 0)
80         {
81           /* Tweak line_number to compensate for fact that
82              we gobbled the whole line before coming here. */
83           line_number--;
84           line_error (_("Missing `}' in @def arg"));
85           line_number++;
86           *string_pointer = scan_string - 1;
87           return 0;
88         }
89
90       if (c == '{' && !started_command)
91         level++;
92       if (c == '}' && !started_command)
93         level--;
94
95       /* remember if at @.  */
96       started_command = (c == '@' && !started_command);
97     }
98 }
99
100 /* Return a list of tokens from the contents of STRING.
101    Commands and brace-delimited groups count as single tokens.
102    Contiguous whitespace characters are converted to a token
103    consisting of a single space. */
104 static char **
105 args_from_string (char *string)
106 {
107   struct token_accumulator accumulator;
108   char *token_start, *token_end;
109   char *scan_string = string;
110
111   initialize_token_accumulator (&accumulator);
112
113   while (*scan_string)
114     { /* Replace arbitrary whitespace by a single space. */
115       if (whitespace (*scan_string))
116         {
117           scan_string += 1;
118           while (whitespace (*scan_string))
119             scan_string += 1;
120           accumulate_token ((&accumulator), (xstrdup (" ")));
121           continue;
122         }
123
124       /* Commands count as single tokens. */
125       if (*scan_string == COMMAND_PREFIX)
126         {
127           token_start = scan_string;
128           scan_string += 1;
129           if (self_delimiting (*scan_string))
130             scan_string += 1;
131           else
132             {
133               int c;
134               while (1)
135                 {
136                   c = *scan_string++;
137
138                   if ((c == 0) || (c == '{') || (whitespace (c)))
139                     {
140                       scan_string -= 1;
141                       break;
142                     }
143                 }
144
145               if (*scan_string == '{')
146                 {
147                   char *s = scan_string;
148                   (void) scan_group_in_string (&s);
149                   scan_string = s;
150                 }
151             }
152           token_end = scan_string;
153         }
154
155       /* Parentheses and brackets are self-delimiting. */
156       else if (DEFUN_SELF_DELIMITING (*scan_string))
157         {
158           token_start = scan_string;
159           scan_string += 1;
160           token_end = scan_string;
161         }
162
163       /* Open brace introduces a group that is a single token. */
164       else if (*scan_string == '{')
165         {
166           char *s = scan_string;
167           int balanced = scan_group_in_string (&s);
168
169           token_start = scan_string + 1;
170           scan_string = s;
171           token_end = balanced ? (scan_string - 1) : scan_string;
172         }
173
174       /* Make commas separate tokens so to differentiate them from
175          parameter types in XML output. */
176       else if (*scan_string == ',')
177         {
178           token_start = scan_string;
179           scan_string += 1;
180           token_end = scan_string;
181         }
182
183       /* Otherwise a token is delimited by whitespace, parentheses,
184          brackets, or braces.  A token is also ended by a command. */
185       else
186         {
187           token_start = scan_string;
188
189           for (;;)
190             {
191               int c;
192
193               c = *scan_string++;
194
195               /* Do not back up if we're looking at a }; since the only
196                  valid }'s are those matched with {'s, we want to give
197                  an error.  If we back up, we go into an infinite loop.  */
198               if (!c || whitespace (c) || DEFUN_SELF_DELIMITING (c)
199                   || c == '{')
200                 {
201                   scan_string--;
202                   break;
203                 }
204
205               /* End token if we are looking at a comma, as commas are
206                  delimiters too. */
207               if (c == ',')
208                 {
209                   scan_string--;
210                   break;
211                 }
212
213               /* If we encounter a command embedded within a token,
214                  then end the token. */
215               if (c == COMMAND_PREFIX)
216                 {
217                   scan_string--;
218                   break;
219                 }
220             }
221           token_end = scan_string;
222         }
223
224       accumulate_token (&accumulator, substring (token_start, token_end));
225     }
226   accumulate_token (&accumulator, NULL);
227   return accumulator.tokens;
228 }
229
230 static void
231 process_defun_args (char **defun_args, int auto_var_p)
232 {
233   int pending_space = 0;
234
235   if (xml)
236     {
237       xml_process_defun_args (defun_args, auto_var_p);
238       return;
239     }
240
241   for (;;)
242     {
243       char *defun_arg = *defun_args++;
244
245       if (defun_arg == NULL)
246         break;
247
248       if (defun_arg[0] == ' ')
249         {
250           pending_space = 1;
251           continue;
252         }
253
254       if (pending_space)
255         {
256           add_char (' ');
257           pending_space = 0;
258         }
259
260       if (DEFUN_SELF_DELIMITING (defun_arg[0]))
261         {
262           /* Within @deffn and friends, texinfo.tex makes parentheses
263              sans serif and brackets bold.  We use roman instead.  */
264           if (html)
265             insert_html_tag (START, "");
266             
267           add_char (defun_arg[0]);
268           
269           if (html)
270             insert_html_tag (END, "");
271         }
272       /* else if (defun_arg[0] == '&' || defun_arg[0] == COMMAND_PREFIX) */
273         /* execute_string ("%s", defun_arg); */
274       /* else if (auto_var_p) */
275         /* execute_string ("%s", defun_arg); */
276       else
277         execute_string ("%s", defun_arg);
278     }
279 }
280
281 static char *
282 next_nonwhite_defun_arg (char ***arg_pointer)
283 {
284   char **scan = (*arg_pointer);
285   char *arg = (*scan++);
286
287   if ((arg != 0) && (*arg == ' '))
288     arg = *scan++;
289
290   if (arg == 0)
291     scan -= 1;
292
293   *arg_pointer = scan;
294
295   return (arg == 0) ? "" : arg;
296 }
297
298
299 /* This is needed also in insertion.c.  */
300
301 enum insertion_type
302 get_base_type (int type)
303 {
304   int base_type;
305   switch (type)
306     {
307     case defivar:       base_type = defcv; break;
308     case defmac:        base_type = deffn; break;
309     case defmethod:     base_type = defop; break;
310     case defopt:        base_type = defvr; break;
311     case defspec:       base_type = deffn; break;
312     case deftypecv:     base_type = deftypecv; break;
313     case deftypefun:    base_type = deftypefn; break;
314     case deftypeivar:   base_type = deftypeivar; break;
315     case deftypemethod: base_type = deftypemethod; break;
316     case deftypeop:     base_type = deftypeop; break;
317     case deftypevar:    base_type = deftypevr; break;
318     case defun:         base_type = deffn; break;
319     case defvar:        base_type = defvr; break;
320     default:
321       base_type = type;
322       break;
323     }
324
325   return base_type;
326 }
327 \f
328 /* Make the defun type insertion.
329    TYPE says which insertion this is.
330    X_P, if nonzero, says not to start a new insertion. */
331 static void
332 defun_internal (int type, int x_p)
333 {
334   int base_type;
335   char **defun_args, **scan_args;
336   const char *category;
337   char *defined_name;
338   char *type_name = NULL;
339   char *type_name2 = NULL;
340
341   {
342     char *line;
343
344     /* The @def.. line is the only place in Texinfo where you are
345        allowed to use unquoted braces that don't delimit arguments of
346        a command or a macro; in any other place it will trigger an
347        error message from the reader loop.  The special handling of
348        this case inside `args_from_string' is an extra special hack
349        which allows this.  The side effect is that if we try to expand
350        the rest of the line below, the recursive reader loop will
351        signal an error if there are brace-delimited arguments on that line.
352
353        The best solution to this would be to change the syntax of
354        @def.. commands so that it doesn't violate Texinfo's own rules.
355        But it's probably too late for this now, as it will break a lot
356        of existing manuals.
357
358        Unfortunately, this means that you can't call macros, use @value, etc.
359        inside @def.. commands, sigh.  */
360     get_rest_of_line (0, &line);
361
362     /* Basic line continuation.  If a line ends with \s*@\s* concatanate
363        the next line. */
364     {
365       char *next_line, *new_line;
366       int i;
367
368       line_continuation:
369         i = strlen (line) - 1;
370
371         if (line[i] == '@' && line[i-1] != '@')
372           {
373             get_rest_of_line (0, &next_line);
374             new_line = (char *) xmalloc (i + strlen (next_line) + 2);
375             strncpy (new_line, line, i);
376             new_line[i] = '\0';
377             free (line);
378             strcat (new_line, " ");
379             strcat (new_line, next_line);
380             line = xstrdup (new_line);
381             free (next_line);
382             free (new_line);
383
384             goto line_continuation;
385           }
386     }
387
388     defun_args = (args_from_string (line));
389     free (line);
390   }
391
392   scan_args = defun_args;
393
394   /* Get base type and category string.  */
395   base_type = get_base_type (type);
396
397   /* xx all these const strings should be determined upon
398      documentlanguage argument and NOT via gettext  (kama).  */
399   switch (type)
400     {
401     case defun:
402     case deftypefun:
403       category = _("Function");
404       break;
405     case defmac:
406       category = _("Macro");
407       break;
408     case defspec:
409       category = _("Special Form");
410       break;
411     case defvar:
412     case deftypevar:
413       category = _("Variable");
414       break;
415     case defopt:
416       category = _("User Option");
417       break;
418     case defivar:
419     case deftypeivar:
420       category = _("Instance Variable");
421       break;
422     case defmethod:
423     case deftypemethod:
424       category = _("Method");
425       break;
426     default:
427       category = next_nonwhite_defun_arg (&scan_args);
428       break;
429     }
430
431   /* The class name.  */
432   if ((base_type == deftypecv)
433       || (base_type == deftypefn)
434       || (base_type == deftypevr)
435       || (base_type == defcv)
436       || (base_type == defop)
437       || (base_type == deftypeivar)
438       || (base_type == deftypemethod)
439       || (base_type == deftypeop)
440      )
441     type_name = next_nonwhite_defun_arg (&scan_args);
442
443   /* The type name for typed languages.  */
444   if ((base_type == deftypecv)
445       || (base_type == deftypeivar)
446       || (base_type == deftypemethod)
447       || (base_type == deftypeop)
448      )
449     type_name2 = next_nonwhite_defun_arg (&scan_args);
450
451   /* The function or whatever that's actually being defined.  */
452   defined_name = next_nonwhite_defun_arg (&scan_args);
453
454   /* This hack exists solely for the purposes of formatting the Texinfo
455      manual.  I couldn't think of a better way.  The token might be a
456      simple @@ followed immediately by more text.  If this is the case,
457      then the next defun arg is part of this one, and we should
458      concatenate them. */
459   if (*scan_args && **scan_args && !whitespace (**scan_args)
460        && STREQ (defined_name, "@@"))
461     {
462       char *tem = xmalloc (3 + strlen (scan_args[0]));
463
464       sprintf (tem, "@@%s", scan_args[0]);
465
466       free (scan_args[0]);
467       scan_args[0] = tem;
468       scan_args++;
469       defined_name = tem;
470     }
471
472   /* It's easy to write @defun foo(arg1 arg2), but a following ( is
473      misparsed by texinfo.tex and this is next to impossible to fix.
474      Warn about it.  */
475   if (*scan_args && **scan_args && **scan_args == '(')
476     warning ("`%c' follows defined name `%s' instead of whitespace",
477              **scan_args, defined_name);
478
479   if (!x_p)
480     begin_insertion (type);
481
482   /* Write the definition header line.
483      This should start at the normal indentation.  */
484   current_indent -= default_indentation_increment;
485   start_paragraph ();
486
487   if (!html && !xml)
488     switch (base_type)
489       {
490       case deffn:
491       case defvr:
492       case deftp:
493         execute_string (" --- %s: %s", category, defined_name);
494         break;
495       case deftypefn:
496       case deftypevr:
497         execute_string (" --- %s: %s %s", category, type_name, defined_name);
498         break;
499       case defcv:
500         execute_string (" --- %s %s %s: %s", category, _("of"), type_name,
501                         defined_name);
502         break;
503       case deftypecv:
504       case deftypeivar:
505         execute_string (" --- %s %s %s: %s %s", category, _("of"), type_name,
506                         type_name2, defined_name);
507         break;
508       case defop:
509         execute_string (" --- %s %s %s: %s", category, _("on"), type_name,
510                         defined_name);
511         break;
512       case deftypeop:
513         execute_string (" --- %s %s %s: %s %s", category, _("on"), type_name,
514                         type_name2, defined_name);
515         break;
516       case deftypemethod:
517         execute_string (" --- %s %s %s: %s %s", category, _("on"), type_name,
518                         type_name2, defined_name);
519         break;
520       }
521   else if (html)
522     {
523       /* If this is not a @def...x version, it could only
524          be a normal version @def.... So start the table here.  */
525       if (!x_p)
526         insert_string ("<div class=\"defun\">\n");
527       else
528         rollback_empty_tag ("blockquote");
529
530       /* xx The single words (on, off) used here, should depend on
531          documentlanguage and NOT on gettext  --kama.  */
532       switch (base_type)
533         {
534         case deffn:
535         case defvr:
536         case deftp:
537         case deftypefn:
538         case deftypevr:
539           execute_string ("--- %s: ", category);
540           break;
541
542         case defcv:
543         case deftypecv:
544         case deftypeivar:
545           execute_string ("--- %s %s %s: ", category, _("of"), type_name);
546           break;
547
548         case defop:
549         case deftypemethod:
550         case deftypeop:
551           execute_string ("--- %s %s %s: ", category, _("on"), type_name);
552           break;
553         } /* switch (base_type)... */
554
555       switch (base_type)
556         {
557         case deffn:
558         case defvr:
559         case deftp:
560           /* <var> is for the following function arguments.  */
561           insert_html_tag (START, "b");
562           execute_string ("%s", defined_name);
563           insert_html_tag (END, "b");
564           insert_html_tag (START, "var");
565           break;
566         case deftypefn:
567         case deftypevr:
568           execute_string ("%s ", type_name);
569           insert_html_tag (START, "b");
570           execute_string ("%s", defined_name);
571           insert_html_tag (END, "b");
572           insert_html_tag (START, "var");
573           break;
574         case defcv:
575         case defop:
576           insert_html_tag (START, "b");
577           execute_string ("%s", defined_name);
578           insert_html_tag (END, "b");
579           insert_html_tag (START, "var");
580           break;
581         case deftypecv:
582         case deftypeivar:
583         case deftypemethod:
584         case deftypeop:
585           execute_string ("%s ", type_name2);
586           insert_html_tag (START, "b");
587           execute_string ("%s", defined_name);
588           insert_html_tag (END, "b");
589           insert_html_tag (START, "var");
590           break;
591         }
592     }
593   else if (xml)
594     xml_begin_def_term (base_type, category, defined_name, type_name,
595         type_name2);
596
597   current_indent += default_indentation_increment;
598
599   /* Now process the function arguments, if any.  If these carry onto
600      the next line, they should be indented by two increments to
601      distinguish them from the body of the definition, which is indented
602      by one increment.  */
603   current_indent += default_indentation_increment;
604
605   switch (base_type)
606     {
607     case deffn:
608     case defop:
609       process_defun_args (scan_args, 1);
610       break;
611
612       /* Through Makeinfo 1.67 we processed remaining args only for deftp,
613          deftypefn, and deftypemethod.  But the libc manual, for example,
614          needs to say:
615             @deftypevar {char *} tzname[2]
616          And simply allowing the extra text seems far simpler than trying
617          to invent yet more defn commands.  In any case, we should either
618          output it or give an error, not silently ignore it.  */
619     default:
620       process_defun_args (scan_args, 0);
621       break;
622     }
623
624   current_indent -= default_indentation_increment;
625   if (!html)
626     close_single_paragraph ();
627
628   /* Make an entry in the appropriate index.  (XML and
629      Docbook already got their entries, so skip them.)  */
630   if (!xml)
631     switch (base_type)
632       {
633       case deffn:
634       case deftypefn:
635         execute_string ("@findex %s\n", defined_name);
636         break;
637       case defcv:
638       case deftypecv:
639       case deftypevr:
640       case defvr:
641         execute_string ("@vindex %s\n", defined_name);
642         break;
643       case deftypeivar:
644         execute_string ("@vindex %s %s %s\n", defined_name, _("of"),
645                         type_name);
646         break;
647       case defop:
648       case deftypeop:
649       case deftypemethod:
650         execute_string ("@findex %s %s %s\n", defined_name, _("on"),
651                         type_name);
652         break;
653       case deftp:
654         execute_string ("@tindex %s\n", defined_name);
655         break;
656       }
657
658   if (xml)
659     xml_end_def_term ();
660   else if (html)
661     {
662       inhibit_paragraph_indentation = 1;
663       no_indent = 1;
664       insert_html_tag (END, "var");
665       insert_string ("<br>\n");
666       /* Indent the definition a bit.  */
667       add_html_block_elt ("<blockquote>");
668       no_indent = 0;
669       inhibit_paragraph_indentation = 0;
670       paragraph_is_open = 0;
671     }
672
673   /* Deallocate the token list. */
674   scan_args = defun_args;
675   while (1)
676     {
677       char * arg = (*scan_args++);
678       if (arg == NULL)
679         break;
680       free (arg);
681     }
682   free (defun_args);
683 }
684
685 /* Add an entry for a function, macro, special form, variable, or option.
686    If the name of the calling command ends in `x', then this is an extra
687    entry included in the body of an insertion of the same type. */
688 void
689 cm_defun (void)
690 {
691   int type;
692   char *base_command = xstrdup (command);  /* command with any `x' removed */
693   int x_p = (command[strlen (command) - 1] == 'x');
694
695   if (x_p)
696     base_command[strlen (base_command) - 1] = 0;
697
698   type = find_type_from_name (base_command);
699
700   /* If we are adding to an already existing insertion, then make sure
701      that we are already in an insertion of type TYPE. */
702   if (x_p)
703     {
704       INSERTION_ELT *i = insertion_stack;
705       /* Skip over ifclear and ifset conditionals.  */
706       while (i && (i->insertion == ifset || i->insertion == ifclear))
707         i = i->next;
708         
709       if (!i || i->insertion != type)
710         {
711           line_error (_("Must be in `@%s' environment to use `@%s'"),
712                       base_command, command);
713           discard_until ("\n");
714           return;
715         }
716     }
717
718   defun_internal (type, x_p);
719   free (base_command);
720 }