1 /*
2  * File automatically generated by
3  * gengen 1.4.2 by Lorenzo Bettini
4  * http://www.gnu.org/software/gengen
5  */
6 
7 #include "c_source.h"
8 
9 void
generate_c_source(ostream & stream,unsigned int indent)10 c_source_gen_class::generate_c_source(ostream &stream, unsigned int indent)
11 {
12   string indent_str (indent, ' ');
13   indent = 0;
14 
15   stream << "/*";
16   stream << "\n";
17   stream << indent_str;
18   stream << "  File autogenerated by gengetopt ";
19   generate_string (generator_version, stream, indent + indent_str.length ());
20   stream << "\n";
21   stream << indent_str;
22   stream << "  generated with the following command:";
23   stream << "\n";
24   stream << indent_str;
25   indent = 2;
26   stream << "  ";
27   generate_string (command_line, stream, indent + indent_str.length ());
28   indent = 0;
29   stream << "\n";
30   stream << indent_str;
31   stream << "\n";
32   stream << indent_str;
33   stream << "  The developers of gengetopt consider the fixed text that goes in all";
34   stream << "\n";
35   stream << indent_str;
36   stream << "  gengetopt output files to be in the public domain:";
37   stream << "\n";
38   stream << indent_str;
39   stream << "  we make no copyright claims on it.";
40   stream << "\n";
41   stream << indent_str;
42   stream << "*/";
43   stream << "\n";
44   stream << indent_str;
45   stream << "\n";
46   stream << indent_str;
47   stream << "/* If we use autoconf.  */";
48   stream << "\n";
49   stream << indent_str;
50   stream << "#ifdef HAVE_CONFIG_H";
51   stream << "\n";
52   stream << indent_str;
53   stream << "#include \"config.h\"";
54   stream << "\n";
55   stream << indent_str;
56   stream << "#endif";
57   stream << "\n";
58   stream << indent_str;
59   stream << "\n";
60   stream << indent_str;
61   stream << "#include <stdio.h>";
62   stream << "\n";
63   stream << indent_str;
64   stream << "#include <stdlib.h>";
65   stream << "\n";
66   stream << indent_str;
67   stream << "#include <string.h>";
68   stream << "\n";
69   stream << indent_str;
70   stream << "\n";
71   stream << indent_str;
72   stream << "#ifndef FIX_UNUSED";
73   stream << "\n";
74   stream << indent_str;
75   stream << "#define FIX_UNUSED(X) (void) (X) /* avoid warnings for unused params */";
76   stream << "\n";
77   stream << indent_str;
78   stream << "#endif";
79   stream << "\n";
80   stream << indent_str;
81   stream << "\n";
82   stream << indent_str;
83   if (( ! include_getopt ))
84     {
85       stream << "#include <getopt.h>";
86       stream << "\n";
87       stream << indent_str;
88     }
89   stream << "\n";
90   stream << indent_str;
91   stream << "#include \"";
92   generate_string (source_name, stream, indent + indent_str.length ());
93   stream << ".";
94   generate_string (header_file_ext, stream, indent + indent_str.length ());
95   stream << "\"";
96   stream << "\n";
97   stream << indent_str;
98   stream << "\n";
99   stream << indent_str;
100   stream << "const char *";
101   generate_string (args_info, stream, indent + indent_str.length ());
102   stream << "_purpose = \"";
103   generate_string (purpose, stream, indent + indent_str.length ());
104   stream << "\";";
105   stream << "\n";
106   stream << indent_str;
107   stream << "\n";
108   stream << indent_str;
109   stream << "const char *";
110   generate_string (args_info, stream, indent + indent_str.length ());
111   stream << "_usage = \"Usage: ";
112   if (no_package)
113     {
114       stream << "\" ";
115       generate_string (package_var_name, stream, indent + indent_str.length ());
116       stream << " \"";
117     }
118   generate_string (usage_string, stream, indent + indent_str.length ());
119   stream << "\";";
120   stream << "\n";
121   stream << indent_str;
122   stream << "\n";
123   stream << indent_str;
124   stream << "const char *";
125   generate_string (args_info, stream, indent + indent_str.length ());
126   stream << "_versiontext = \"";
127   generate_string (versiontext, stream, indent + indent_str.length ());
128   stream << "\";";
129   stream << "\n";
130   stream << indent_str;
131   stream << "\n";
132   stream << indent_str;
133   stream << "const char *";
134   generate_string (args_info, stream, indent + indent_str.length ());
135   stream << "_description = \"";
136   generate_string (description, stream, indent + indent_str.length ());
137   stream << "\";";
138   stream << "\n";
139   stream << indent_str;
140   stream << "\n";
141   stream << indent_str;
142   if (( has_hidden || has_details ))
143     {
144       if (has_details)
145         {
146           stream << "const char *";
147           generate_string (args_info, stream, indent + indent_str.length ());
148           stream << "_detailed_help[] = {";
149           stream << "\n";
150           stream << indent_str;
151           indent = 2;
152           stream << "  ";
153           if (detailed_help_option_print.size () > 0)
154             generate_string (detailed_help_option_print, stream, indent + indent_str.length ());
155           else
156             generate_detailed_help_option_print (stream, indent + indent_str.length ());
157           stream << "  0";
158           indent = 0;
159           stream << "\n";
160           stream << indent_str;
161           stream << "};";
162           stream << "\n";
163           stream << indent_str;
164           if (has_hidden)
165             {
166               stream << "static void";
167               stream << "\n";
168               stream << indent_str;
169               stream << "init_full_help_array(void)";
170               stream << "\n";
171               stream << indent_str;
172               stream << "{";
173               stream << "\n";
174               stream << indent_str;
175               indent = 2;
176               stream << "  ";
177               if (full_help_option_print.size () > 0)
178                 generate_string (full_help_option_print, stream, indent + indent_str.length ());
179               else
180                 generate_full_help_option_print (stream, indent + indent_str.length ());
181               indent = 0;
182               stream << "\n";
183               stream << indent_str;
184               stream << "}";
185               stream << "\n";
186               stream << indent_str;
187               stream << "\n";
188               stream << indent_str;
189               stream << "const char *";
190               generate_string (args_info, stream, indent + indent_str.length ());
191               stream << "_full_help[";
192               generate_string (help_string_num, stream, indent + indent_str.length ());
193               stream << "];";
194               stream << "\n";
195               stream << indent_str;
196             }
197         }
198       else
199         {
200           if (has_hidden)
201             {
202               stream << "const char *";
203               generate_string (args_info, stream, indent + indent_str.length ());
204               stream << "_full_help[] = {";
205               stream << "\n";
206               stream << indent_str;
207               indent = 2;
208               stream << "  ";
209               if (full_help_option_print.size () > 0)
210                 generate_string (full_help_option_print, stream, indent + indent_str.length ());
211               else
212                 generate_full_help_option_print (stream, indent + indent_str.length ());
213               stream << "  0";
214               indent = 0;
215               stream << "\n";
216               stream << indent_str;
217               stream << "};";
218               stream << "\n";
219               stream << indent_str;
220             }
221         }
222       stream << "\n";
223       stream << indent_str;
224       stream << "static void";
225       stream << "\n";
226       stream << indent_str;
227       stream << "init_help_array(void)";
228       stream << "\n";
229       stream << indent_str;
230       stream << "{";
231       stream << "\n";
232       stream << indent_str;
233       indent = 2;
234       stream << "  ";
235       if (help_option_print.size () > 0)
236         generate_string (help_option_print, stream, indent + indent_str.length ());
237       else
238         generate_help_option_print (stream, indent + indent_str.length ());
239       indent = 0;
240       stream << "\n";
241       stream << indent_str;
242       stream << "}";
243       stream << "\n";
244       stream << indent_str;
245       stream << "\n";
246       stream << indent_str;
247       stream << "const char *";
248       generate_string (args_info, stream, indent + indent_str.length ());
249       stream << "_help[";
250       generate_string (help_string_num, stream, indent + indent_str.length ());
251       stream << "];";
252       stream << "\n";
253       stream << indent_str;
254     }
255   else
256     {
257       stream << "const char *";
258       generate_string (args_info, stream, indent + indent_str.length ());
259       stream << "_help[] = {";
260       stream << "\n";
261       stream << indent_str;
262       indent = 2;
263       stream << "  ";
264       if (help_option_print.size () > 0)
265         generate_string (help_option_print, stream, indent + indent_str.length ());
266       else
267         generate_help_option_print (stream, indent + indent_str.length ());
268       stream << "  0";
269       indent = 0;
270       stream << "\n";
271       stream << indent_str;
272       stream << "};";
273       stream << "\n";
274       stream << indent_str;
275     }
276   stream << "\n";
277   stream << indent_str;
278   stream << "typedef enum {ARG_NO";
279   stream << "\n";
280   stream << indent_str;
281   if (has_arg_flag)
282     {
283       stream << "  , ARG_FLAG";
284       stream << "\n";
285       stream << indent_str;
286     }
287   if (has_arg_string)
288     {
289       stream << "  , ARG_STRING";
290       stream << "\n";
291       stream << indent_str;
292     }
293   if (has_arg_int)
294     {
295       stream << "  , ARG_INT";
296       stream << "\n";
297       stream << indent_str;
298     }
299   if (has_arg_short)
300     {
301       stream << "  , ARG_SHORT";
302       stream << "\n";
303       stream << indent_str;
304     }
305   if (has_arg_long)
306     {
307       stream << "  , ARG_LONG";
308       stream << "\n";
309       stream << indent_str;
310     }
311   if (has_arg_float)
312     {
313       stream << "  , ARG_FLOAT";
314       stream << "\n";
315       stream << indent_str;
316     }
317   if (has_arg_double)
318     {
319       stream << "  , ARG_DOUBLE";
320       stream << "\n";
321       stream << indent_str;
322     }
323   if (has_arg_longdouble)
324     {
325       stream << "  , ARG_LONGDOUBLE";
326       stream << "\n";
327       stream << indent_str;
328     }
329   if (has_arg_longlong)
330     {
331       stream << "  , ARG_LONGLONG";
332       stream << "\n";
333       stream << indent_str;
334     }
335   if (has_arg_enum)
336     {
337       stream << "  , ARG_ENUM";
338       stream << "\n";
339       stream << indent_str;
340     }
341   stream << "} ";
342   generate_string (parser_name, stream, indent + indent_str.length ());
343   stream << "_arg_type;";
344   stream << "\n";
345   stream << indent_str;
346   stream << "\n";
347   stream << indent_str;
348   stream << "static";
349   stream << "\n";
350   stream << indent_str;
351   stream << "void clear_given (struct ";
352   generate_string (args_info, stream, indent + indent_str.length ());
353   stream << " *args_info);";
354   stream << "\n";
355   stream << indent_str;
356   stream << "static";
357   stream << "\n";
358   stream << indent_str;
359   stream << "void clear_args (struct ";
360   generate_string (args_info, stream, indent + indent_str.length ());
361   stream << " *args_info);";
362   stream << "\n";
363   stream << indent_str;
364   stream << "\n";
365   stream << indent_str;
366   stream << "static int";
367   stream << "\n";
368   stream << indent_str;
369   generate_string (parser_name, stream, indent + indent_str.length ());
370   stream << "_internal (int argc, char **argv, struct ";
371   generate_string (args_info, stream, indent + indent_str.length ());
372   stream << " *args_info,";
373   stream << "\n";
374   stream << indent_str;
375   stream << "                        struct ";
376   generate_string (parser_name, stream, indent + indent_str.length ());
377   stream << "_params *params, const char *additional_error);";
378   stream << "\n";
379   stream << indent_str;
380   stream << "\n";
381   stream << indent_str;
382   if (check_required_options)
383     {
384       stream << "static int";
385       stream << "\n";
386       stream << indent_str;
387       generate_string (parser_name, stream, indent + indent_str.length ());
388       stream << "_required2 (struct ";
389       generate_string (args_info, stream, indent + indent_str.length ());
390       stream << " *args_info, const char *prog_name, const char *additional_error);";
391       stream << "\n";
392       stream << indent_str;
393     }
394   if (cmd_list)
395     {
396       stream << "struct line_list";
397       stream << "\n";
398       stream << indent_str;
399       stream << "{";
400       stream << "\n";
401       stream << indent_str;
402       stream << "  char * string_arg;";
403       stream << "\n";
404       stream << indent_str;
405       stream << "  struct line_list * next;";
406       stream << "\n";
407       stream << indent_str;
408       stream << "};";
409       stream << "\n";
410       stream << indent_str;
411       stream << "\n";
412       stream << indent_str;
413       stream << "static struct line_list *cmd_line_list = 0;";
414       stream << "\n";
415       stream << indent_str;
416       stream << "static struct line_list *cmd_line_list_tmp = 0;";
417       stream << "\n";
418       stream << indent_str;
419       stream << "\n";
420       stream << indent_str;
421       stream << "static void";
422       stream << "\n";
423       stream << indent_str;
424       stream << "free_cmd_list(void)";
425       stream << "\n";
426       stream << indent_str;
427       stream << "{";
428       stream << "\n";
429       stream << indent_str;
430       stream << "  /* free the list of a previous call */";
431       stream << "\n";
432       stream << indent_str;
433       stream << "  if (cmd_line_list)";
434       stream << "\n";
435       stream << indent_str;
436       stream << "    {";
437       stream << "\n";
438       stream << indent_str;
439       stream << "      while (cmd_line_list) {";
440       stream << "\n";
441       stream << indent_str;
442       stream << "        cmd_line_list_tmp = cmd_line_list;";
443       stream << "\n";
444       stream << indent_str;
445       stream << "        cmd_line_list = cmd_line_list->next;";
446       stream << "\n";
447       stream << indent_str;
448       stream << "        free (cmd_line_list_tmp->string_arg);";
449       stream << "\n";
450       stream << indent_str;
451       stream << "        free (cmd_line_list_tmp);";
452       stream << "\n";
453       stream << indent_str;
454       stream << "      }";
455       stream << "\n";
456       stream << indent_str;
457       stream << "    }";
458       stream << "\n";
459       stream << indent_str;
460       stream << "}";
461       stream << "\n";
462       stream << indent_str;
463       stream << "\n";
464       stream << indent_str;
465     }
466   stream << "\n";
467   stream << indent_str;
468   if (option_values.size () > 0)
469     generate_string (option_values, stream, indent + indent_str.length ());
470   else
471     generate_option_values (stream, indent + indent_str.length ());
472   stream << indent_str;
473   if (do_generate_strdup)
474     {
475       stream << "static char *";
476       stream << "\n";
477       stream << indent_str;
478       stream << "gengetopt_strdup (const char *s);";
479       stream << "\n";
480       stream << indent_str;
481       stream << "\n";
482       stream << indent_str;
483     }
484   stream << "static";
485   stream << "\n";
486   stream << indent_str;
487   stream << "void clear_given (struct ";
488   generate_string (args_info, stream, indent + indent_str.length ());
489   stream << " *args_info)";
490   stream << "\n";
491   stream << indent_str;
492   stream << "{";
493   stream << "\n";
494   stream << indent_str;
495   indent = 2;
496   if (given_init.size () > 0)
497     generate_string (given_init, stream, indent + indent_str.length ());
498   else
499     generate_given_init (stream, indent + indent_str.length ());
500   indent = 0;
501   stream << indent_str;
502   stream << "}";
503   stream << "\n";
504   stream << indent_str;
505   stream << "\n";
506   stream << indent_str;
507   stream << "static";
508   stream << "\n";
509   stream << indent_str;
510   stream << "void clear_args (struct ";
511   generate_string (args_info, stream, indent + indent_str.length ());
512   stream << " *args_info)";
513   stream << "\n";
514   stream << indent_str;
515   stream << "{";
516   stream << "\n";
517   stream << indent_str;
518   stream << "  FIX_UNUSED (args_info);";
519   stream << "\n";
520   stream << indent_str;
521   indent = 2;
522   stream << "  ";
523   if (clear_arg.size () > 0)
524     generate_string (clear_arg, stream, indent + indent_str.length ());
525   else
526     generate_clear_arg (stream, indent + indent_str.length ());
527   indent = 0;
528   stream << "\n";
529   stream << indent_str;
530   stream << "}";
531   stream << "\n";
532   stream << indent_str;
533   stream << "\n";
534   stream << indent_str;
535   stream << "static";
536   stream << "\n";
537   stream << indent_str;
538   stream << "void init_args_info(struct ";
539   generate_string (args_info, stream, indent + indent_str.length ());
540   stream << " *args_info)";
541   stream << "\n";
542   stream << indent_str;
543   stream << "{";
544   stream << "\n";
545   stream << indent_str;
546   if (( has_hidden && has_details ))
547     {
548       stream << "  init_full_help_array(); ";
549     }
550   stream << "\n";
551   stream << indent_str;
552   if (( has_hidden || has_details ))
553     {
554       stream << "  init_help_array(); ";
555     }
556   stream << "\n";
557   stream << indent_str;
558   indent = 2;
559   stream << "  ";
560   if (init_args_info.size () > 0)
561     generate_string (init_args_info, stream, indent + indent_str.length ());
562   else
563     generate_init_args_info (stream, indent + indent_str.length ());
564   indent = 0;
565   stream << "\n";
566   stream << indent_str;
567   stream << "}";
568   stream << "\n";
569   stream << indent_str;
570   stream << "\n";
571   stream << indent_str;
572   stream << "void";
573   stream << "\n";
574   stream << indent_str;
575   generate_string (parser_name, stream, indent + indent_str.length ());
576   stream << "_print_version (void)";
577   stream << "\n";
578   stream << indent_str;
579   stream << "{";
580   stream << "\n";
581   stream << indent_str;
582   stream << "  printf (\"%s %s\\n\",";
583   stream << "\n";
584   stream << indent_str;
585   stream << "     (strlen(";
586   generate_string (package_var_name, stream, indent + indent_str.length ());
587   stream << "_NAME) ? ";
588   generate_string (package_var_name, stream, indent + indent_str.length ());
589   stream << "_NAME : ";
590   generate_string (package_var_name, stream, indent + indent_str.length ());
591   stream << "),";
592   stream << "\n";
593   stream << indent_str;
594   indent = 5;
595   stream << "     ";
596   generate_string (version_var_name, stream, indent + indent_str.length ());
597   stream << ");";
598   indent = 0;
599   stream << "\n";
600   stream << indent_str;
601   stream << "\n";
602   stream << indent_str;
603   stream << "  if (strlen(";
604   generate_string (args_info, stream, indent + indent_str.length ());
605   stream << "_versiontext) > 0)";
606   stream << "\n";
607   stream << indent_str;
608   stream << "    printf(\"\\n%s\\n\", ";
609   generate_string (args_info, stream, indent + indent_str.length ());
610   stream << "_versiontext);";
611   stream << "\n";
612   stream << indent_str;
613   stream << "}";
614   stream << "\n";
615   stream << indent_str;
616   stream << "\n";
617   stream << indent_str;
618   stream << "static void print_help_common(void)";
619   stream << "\n";
620   stream << indent_str;
621   stream << "{";
622   stream << "\n";
623   stream << indent_str;
624   stream << "	size_t len_purpose = strlen(";
625   generate_string (args_info, stream, indent + indent_str.length ());
626   stream << "_purpose);";
627   stream << "\n";
628   stream << indent_str;
629   stream << "	size_t len_usage = strlen(";
630   generate_string (args_info, stream, indent + indent_str.length ());
631   stream << "_usage);";
632   stream << "\n";
633   stream << indent_str;
634   stream << "\n";
635   stream << indent_str;
636   stream << "	if (len_usage > 0) {";
637   stream << "\n";
638   stream << indent_str;
639   stream << "		printf(\"%s\\n\", ";
640   generate_string (args_info, stream, indent + indent_str.length ());
641   stream << "_usage);";
642   stream << "\n";
643   stream << indent_str;
644   stream << "	}";
645   stream << "\n";
646   stream << indent_str;
647   stream << "	if (len_purpose > 0) {";
648   stream << "\n";
649   stream << indent_str;
650   stream << "		printf(\"%s\\n\", ";
651   generate_string (args_info, stream, indent + indent_str.length ());
652   stream << "_purpose);";
653   stream << "\n";
654   stream << indent_str;
655   stream << "	}";
656   stream << "\n";
657   stream << indent_str;
658   stream << "\n";
659   stream << indent_str;
660   stream << "	if (len_usage || len_purpose) {";
661   stream << "\n";
662   stream << indent_str;
663   stream << "		printf(\"\\n\");";
664   stream << "\n";
665   stream << indent_str;
666   stream << "	}";
667   stream << "\n";
668   stream << indent_str;
669   stream << "\n";
670   stream << indent_str;
671   stream << "	if (strlen(";
672   generate_string (args_info, stream, indent + indent_str.length ());
673   stream << "_description) > 0) {";
674   stream << "\n";
675   stream << indent_str;
676   stream << "		printf(\"%s\\n\\n\", ";
677   generate_string (args_info, stream, indent + indent_str.length ());
678   stream << "_description);";
679   stream << "\n";
680   stream << indent_str;
681   stream << "	}";
682   stream << "\n";
683   stream << indent_str;
684   stream << "}";
685   stream << "\n";
686   stream << indent_str;
687   stream << "\n";
688   stream << indent_str;
689   stream << "void";
690   stream << "\n";
691   stream << indent_str;
692   generate_string (parser_name, stream, indent + indent_str.length ());
693   stream << "_print_help (void)";
694   stream << "\n";
695   stream << indent_str;
696   stream << "{";
697   stream << "\n";
698   stream << indent_str;
699   stream << "  int i = 0;";
700   stream << "\n";
701   stream << indent_str;
702   stream << "  print_help_common();";
703   stream << "\n";
704   stream << indent_str;
705   stream << "  while (";
706   generate_string (args_info, stream, indent + indent_str.length ());
707   stream << "_help[i])";
708   stream << "\n";
709   stream << indent_str;
710   stream << "    printf(\"%s\\n\", ";
711   generate_string (args_info, stream, indent + indent_str.length ());
712   stream << "_help[i++]);";
713   stream << "\n";
714   stream << indent_str;
715   stream << "}";
716   stream << "\n";
717   stream << indent_str;
718   stream << "\n";
719   stream << indent_str;
720   if (has_hidden)
721     {
722       stream << "void";
723       stream << "\n";
724       stream << indent_str;
725       generate_string (parser_name, stream, indent + indent_str.length ());
726       stream << "_print_full_help (void)";
727       stream << "\n";
728       stream << indent_str;
729       stream << "{";
730       stream << "\n";
731       stream << indent_str;
732       stream << "  int i = 0;";
733       stream << "\n";
734       stream << indent_str;
735       stream << "  print_help_common();";
736       stream << "\n";
737       stream << indent_str;
738       stream << "  while (";
739       generate_string (args_info, stream, indent + indent_str.length ());
740       stream << "_full_help[i])";
741       stream << "\n";
742       stream << indent_str;
743       stream << "    printf(\"%s\\n\", ";
744       generate_string (args_info, stream, indent + indent_str.length ());
745       stream << "_full_help[i++]);";
746       stream << "\n";
747       stream << indent_str;
748       stream << "}";
749       stream << "\n";
750       stream << indent_str;
751       stream << "\n";
752       stream << indent_str;
753     }
754   if (has_details)
755     {
756       stream << "void";
757       stream << "\n";
758       stream << indent_str;
759       generate_string (parser_name, stream, indent + indent_str.length ());
760       stream << "_print_detailed_help (void)";
761       stream << "\n";
762       stream << indent_str;
763       stream << "{";
764       stream << "\n";
765       stream << indent_str;
766       stream << "  int i = 0;";
767       stream << "\n";
768       stream << indent_str;
769       stream << "  print_help_common();";
770       stream << "\n";
771       stream << indent_str;
772       stream << "  while (";
773       generate_string (args_info, stream, indent + indent_str.length ());
774       stream << "_detailed_help[i])";
775       stream << "\n";
776       stream << indent_str;
777       stream << "    printf(\"%s\\n\", ";
778       generate_string (args_info, stream, indent + indent_str.length ());
779       stream << "_detailed_help[i++]);";
780       stream << "\n";
781       stream << indent_str;
782       stream << "}";
783       stream << "\n";
784       stream << indent_str;
785       stream << "\n";
786       stream << indent_str;
787     }
788   stream << "void";
789   stream << "\n";
790   stream << indent_str;
791   generate_string (parser_name, stream, indent + indent_str.length ());
792   stream << "_init (struct ";
793   generate_string (args_info, stream, indent + indent_str.length ());
794   stream << " *args_info)";
795   stream << "\n";
796   stream << indent_str;
797   stream << "{";
798   stream << "\n";
799   stream << indent_str;
800   stream << "  clear_given (args_info);";
801   stream << "\n";
802   stream << indent_str;
803   stream << "  clear_args (args_info);";
804   stream << "\n";
805   stream << indent_str;
806   stream << "  init_args_info (args_info);";
807   stream << "\n";
808   stream << indent_str;
809   if (handle_unnamed)
810     {
811       stream << "\n";
812       stream << indent_str;
813       stream << "  args_info->inputs = 0;";
814       stream << "\n";
815       stream << indent_str;
816       stream << "  args_info->inputs_num = 0;";
817       stream << "\n";
818       stream << indent_str;
819     }
820   stream << "}";
821   stream << "\n";
822   stream << indent_str;
823   stream << "\n";
824   stream << indent_str;
825   stream << "void";
826   stream << "\n";
827   stream << indent_str;
828   generate_string (parser_name, stream, indent + indent_str.length ());
829   stream << "_params_init(struct ";
830   generate_string (parser_name, stream, indent + indent_str.length ());
831   stream << "_params *params)";
832   stream << "\n";
833   stream << indent_str;
834   stream << "{";
835   stream << "\n";
836   stream << indent_str;
837   stream << "  if (params)";
838   stream << "\n";
839   stream << indent_str;
840   stream << "    { ";
841   stream << "\n";
842   stream << indent_str;
843   stream << "      params->override = 0;";
844   stream << "\n";
845   stream << indent_str;
846   stream << "      params->initialize = 1;";
847   stream << "\n";
848   stream << indent_str;
849   stream << "      params->check_required = 1;";
850   stream << "\n";
851   stream << indent_str;
852   stream << "      params->check_ambiguity = 0;";
853   stream << "\n";
854   stream << indent_str;
855   stream << "      params->print_errors = 1;";
856   stream << "\n";
857   stream << indent_str;
858   stream << "    }";
859   stream << "\n";
860   stream << indent_str;
861   stream << "}";
862   stream << "\n";
863   stream << indent_str;
864   stream << "\n";
865   stream << indent_str;
866   stream << "struct ";
867   generate_string (parser_name, stream, indent + indent_str.length ());
868   stream << "_params *";
869   stream << "\n";
870   stream << indent_str;
871   generate_string (parser_name, stream, indent + indent_str.length ());
872   stream << "_params_create(void)";
873   stream << "\n";
874   stream << indent_str;
875   stream << "{";
876   stream << "\n";
877   stream << indent_str;
878   stream << "  struct ";
879   generate_string (parser_name, stream, indent + indent_str.length ());
880   stream << "_params *params = ";
881   stream << "\n";
882   stream << indent_str;
883   stream << "    (struct ";
884   generate_string (parser_name, stream, indent + indent_str.length ());
885   stream << "_params *)malloc(sizeof(struct ";
886   generate_string (parser_name, stream, indent + indent_str.length ());
887   stream << "_params));";
888   stream << "\n";
889   stream << indent_str;
890   indent = 2;
891   stream << "  ";
892   generate_string (parser_name, stream, indent + indent_str.length ());
893   stream << "_params_init(params);  ";
894   indent = 0;
895   stream << "\n";
896   stream << indent_str;
897   stream << "  return params;";
898   stream << "\n";
899   stream << indent_str;
900   stream << "}";
901   stream << "\n";
902   stream << indent_str;
903   stream << "\n";
904   stream << indent_str;
905   if (has_typed_options)
906     {
907       stream << "static void";
908       stream << "\n";
909       stream << indent_str;
910       stream << "free_string_field (char **s)";
911       stream << "\n";
912       stream << indent_str;
913       stream << "{";
914       stream << "\n";
915       stream << indent_str;
916       stream << "  if (*s)";
917       stream << "\n";
918       stream << indent_str;
919       stream << "    {";
920       stream << "\n";
921       stream << indent_str;
922       stream << "      free (*s);";
923       stream << "\n";
924       stream << indent_str;
925       stream << "      *s = 0;";
926       stream << "\n";
927       stream << indent_str;
928       stream << "    }";
929       stream << "\n";
930       stream << indent_str;
931       stream << "}";
932       stream << "\n";
933       stream << indent_str;
934     }
935   stream << "\n";
936   stream << indent_str;
937   if (multiple_token_functions)
938     {
939       stream << "/** ";
940       stream << "@";
941       stream << "brief generic value variable */";
942       stream << "\n";
943       stream << indent_str;
944       stream << "union generic_value {";
945       stream << "\n";
946       stream << indent_str;
947       if (( has_arg_int || has_arg_enum ))
948         {
949           stream << "    int int_arg;";
950           stream << "\n";
951           stream << indent_str;
952         }
953       if (has_arg_short)
954         {
955           stream << "    short short_arg;";
956           stream << "\n";
957           stream << indent_str;
958         }
959       if (has_arg_long)
960         {
961           stream << "    long long_arg;";
962           stream << "\n";
963           stream << indent_str;
964         }
965       if (has_arg_float)
966         {
967           stream << "    float float_arg;";
968           stream << "\n";
969           stream << indent_str;
970         }
971       if (has_arg_double)
972         {
973           stream << "    double double_arg;";
974           stream << "\n";
975           stream << indent_str;
976         }
977       if (has_arg_longdouble)
978         {
979           stream << "    long double longdouble_arg;";
980           stream << "\n";
981           stream << indent_str;
982         }
983       if (has_arg_longlong)
984         {
985           stream << "#if defined(HAVE_LONG_LONG) || defined(HAVE_LONG_LONG_INT)";
986           stream << "\n";
987           stream << indent_str;
988           stream << "    long long int longlong_arg;";
989           stream << "\n";
990           stream << indent_str;
991           stream << "#else";
992           stream << "\n";
993           stream << indent_str;
994           stream << "    long longlong_arg;";
995           stream << "\n";
996           stream << indent_str;
997           stream << "#endif";
998           stream << "\n";
999           stream << indent_str;
1000         }
1001       stream << "    char *string_arg;";
1002       stream << "\n";
1003       stream << indent_str;
1004       stream << "    const char *default_string_arg;";
1005       stream << "\n";
1006       stream << indent_str;
1007       stream << "};";
1008       stream << "\n";
1009       stream << indent_str;
1010       stream << "\n";
1011       stream << indent_str;
1012       stream << "/** ";
1013       stream << "@";
1014       stream << "brief holds temporary values for multiple options */";
1015       stream << "\n";
1016       stream << indent_str;
1017       stream << "struct generic_list";
1018       stream << "\n";
1019       stream << indent_str;
1020       stream << "{";
1021       stream << "\n";
1022       stream << indent_str;
1023       stream << "  union generic_value arg;";
1024       stream << "\n";
1025       stream << indent_str;
1026       stream << "  char *orig;";
1027       stream << "\n";
1028       stream << indent_str;
1029       stream << "  struct generic_list *next;";
1030       stream << "\n";
1031       stream << indent_str;
1032       stream << "};";
1033       stream << "\n";
1034       stream << indent_str;
1035       stream << "\n";
1036       stream << indent_str;
1037       stream << "/**";
1038       stream << "\n";
1039       stream << indent_str;
1040       stream << " * ";
1041       stream << "@";
1042       stream << "brief add a node at the head of the list ";
1043       stream << "\n";
1044       stream << indent_str;
1045       stream << " */";
1046       stream << "\n";
1047       stream << indent_str;
1048       stream << "static void add_node(struct generic_list **list) {";
1049       stream << "\n";
1050       stream << indent_str;
1051       stream << "  struct generic_list *new_node = (struct generic_list *) malloc (sizeof (struct generic_list));";
1052       stream << "\n";
1053       stream << indent_str;
1054       stream << "  new_node->next = *list;";
1055       stream << "\n";
1056       stream << indent_str;
1057       stream << "  *list = new_node;";
1058       stream << "\n";
1059       stream << indent_str;
1060       stream << "  new_node->arg.string_arg = 0;";
1061       stream << "\n";
1062       stream << indent_str;
1063       stream << "  new_node->orig = 0;";
1064       stream << "\n";
1065       stream << indent_str;
1066       stream << "}";
1067       stream << "\n";
1068       stream << indent_str;
1069       stream << "\n";
1070       stream << indent_str;
1071       if (( ( ! multiple_options_all_string ) && multiple_token_functions ))
1072         {
1073           stream << "/**";
1074           stream << "\n";
1075           stream << indent_str;
1076           stream << " * The passed arg parameter is NOT set to 0 from this function";
1077           stream << "\n";
1078           stream << indent_str;
1079           stream << " */";
1080           stream << "\n";
1081           stream << indent_str;
1082           stream << "static void";
1083           stream << "\n";
1084           stream << indent_str;
1085           stream << "free_multiple_field(unsigned int len, void *arg, char ***orig)";
1086           stream << "\n";
1087           stream << indent_str;
1088           stream << "{";
1089           stream << "\n";
1090           stream << indent_str;
1091           stream << "  unsigned int i;";
1092           stream << "\n";
1093           stream << indent_str;
1094           stream << "  if (arg) {";
1095           stream << "\n";
1096           stream << indent_str;
1097           stream << "    for (i = 0; i < len; ++i)";
1098           stream << "\n";
1099           stream << indent_str;
1100           stream << "      {";
1101           stream << "\n";
1102           stream << indent_str;
1103           stream << "        free_string_field(&((*orig)[i]));";
1104           stream << "\n";
1105           stream << indent_str;
1106           stream << "      }";
1107           stream << "\n";
1108           stream << indent_str;
1109           stream << "\n";
1110           stream << indent_str;
1111           stream << "    free (arg);";
1112           stream << "\n";
1113           stream << indent_str;
1114           stream << "    free (*orig);";
1115           stream << "\n";
1116           stream << indent_str;
1117           stream << "    *orig = 0;";
1118           stream << "\n";
1119           stream << indent_str;
1120           stream << "  }";
1121           stream << "\n";
1122           stream << indent_str;
1123           stream << "}";
1124           stream << "\n";
1125           stream << indent_str;
1126         }
1127       stream << "\n";
1128       stream << indent_str;
1129       if (multiple_options_string)
1130         {
1131           stream << "static void";
1132           stream << "\n";
1133           stream << indent_str;
1134           stream << "free_multiple_string_field(unsigned int len, char ***arg, char ***orig)";
1135           stream << "\n";
1136           stream << indent_str;
1137           stream << "{";
1138           stream << "\n";
1139           stream << indent_str;
1140           stream << "  unsigned int i;";
1141           stream << "\n";
1142           stream << indent_str;
1143           stream << "  if (*arg) {";
1144           stream << "\n";
1145           stream << indent_str;
1146           stream << "    for (i = 0; i < len; ++i)";
1147           stream << "\n";
1148           stream << indent_str;
1149           stream << "      {";
1150           stream << "\n";
1151           stream << indent_str;
1152           stream << "        free_string_field(&((*arg)[i]));";
1153           stream << "\n";
1154           stream << indent_str;
1155           stream << "        free_string_field(&((*orig)[i]));";
1156           stream << "\n";
1157           stream << indent_str;
1158           stream << "      }";
1159           stream << "\n";
1160           stream << indent_str;
1161           stream << "    free_string_field(&((*arg)[0])); /* free default string */";
1162           stream << "\n";
1163           stream << indent_str;
1164           stream << "\n";
1165           stream << indent_str;
1166           stream << "    free (*arg);";
1167           stream << "\n";
1168           stream << indent_str;
1169           stream << "    *arg = 0;";
1170           stream << "\n";
1171           stream << indent_str;
1172           stream << "    free (*orig);";
1173           stream << "\n";
1174           stream << indent_str;
1175           stream << "    *orig = 0;";
1176           stream << "\n";
1177           stream << indent_str;
1178           stream << "  }";
1179           stream << "\n";
1180           stream << indent_str;
1181           stream << "}";
1182           stream << "\n";
1183           stream << indent_str;
1184         }
1185     }
1186   stream << "\n";
1187   stream << indent_str;
1188   stream << "static void";
1189   stream << "\n";
1190   stream << indent_str;
1191   generate_string (parser_name, stream, indent + indent_str.length ());
1192   stream << "_release (struct ";
1193   generate_string (args_info, stream, indent + indent_str.length ());
1194   stream << " *args_info)";
1195   stream << "\n";
1196   stream << indent_str;
1197   stream << "{";
1198   stream << "\n";
1199   stream << indent_str;
1200   if (handle_unnamed)
1201     {
1202       stream << "  unsigned int i;";
1203     }
1204   stream << "\n";
1205   stream << indent_str;
1206   indent = 2;
1207   stream << "  ";
1208   if (free.size () > 0)
1209     generate_string (free, stream, indent + indent_str.length ());
1210   else
1211     generate_free (stream, indent + indent_str.length ());
1212   indent = 0;
1213   stream << "\n";
1214   stream << indent_str;
1215   indent = 2;
1216   stream << "  ";
1217   indent = 0;
1218   stream << "\n";
1219   stream << indent_str;
1220   if (handle_unnamed)
1221     {
1222       stream << "  for (i = 0; i < args_info->inputs_num; ++i)";
1223       stream << "\n";
1224       stream << indent_str;
1225       stream << "    free (args_info->inputs [i]);";
1226       stream << "\n";
1227       stream << indent_str;
1228       stream << "\n";
1229       stream << indent_str;
1230       stream << "  if (args_info->inputs_num)";
1231       stream << "\n";
1232       stream << indent_str;
1233       stream << "    free (args_info->inputs);";
1234       stream << "\n";
1235       stream << indent_str;
1236     }
1237   stream << "\n";
1238   stream << indent_str;
1239   stream << "  clear_given (args_info);";
1240   stream << "\n";
1241   stream << indent_str;
1242   stream << "}";
1243   stream << "\n";
1244   stream << indent_str;
1245   stream << "\n";
1246   stream << indent_str;
1247   if (check_possible_values)
1248     {
1249       stream << "/**";
1250       stream << "\n";
1251       stream << indent_str;
1252       stream << " * ";
1253       stream << "@";
1254       stream << "param val the value to check";
1255       stream << "\n";
1256       stream << indent_str;
1257       stream << " * ";
1258       stream << "@";
1259       stream << "param values the possible values";
1260       stream << "\n";
1261       stream << indent_str;
1262       stream << " * ";
1263       stream << "@";
1264       stream << "return the index of the matched value:";
1265       stream << "\n";
1266       stream << indent_str;
1267       stream << " * -1 if no value matched,";
1268       stream << "\n";
1269       stream << indent_str;
1270       stream << " * -2 if more than one value has matched";
1271       stream << "\n";
1272       stream << indent_str;
1273       stream << " */";
1274       stream << "\n";
1275       stream << indent_str;
1276       stream << "static int";
1277       stream << "\n";
1278       stream << indent_str;
1279       stream << "check_possible_values(const char *val, const char *values[])";
1280       stream << "\n";
1281       stream << indent_str;
1282       stream << "{";
1283       stream << "\n";
1284       stream << indent_str;
1285       stream << "  int i, found, last;";
1286       stream << "\n";
1287       stream << indent_str;
1288       stream << "  size_t len;";
1289       stream << "\n";
1290       stream << indent_str;
1291       stream << "\n";
1292       stream << indent_str;
1293       stream << "  if (!val)   /* otherwise strlen() crashes below */";
1294       stream << "\n";
1295       stream << indent_str;
1296       stream << "    return -1; /* -1 means no argument for the option */";
1297       stream << "\n";
1298       stream << indent_str;
1299       stream << "\n";
1300       stream << indent_str;
1301       stream << "  found = last = 0;";
1302       stream << "\n";
1303       stream << indent_str;
1304       stream << "\n";
1305       stream << indent_str;
1306       stream << "  for (i = 0, len = strlen(val); values[i]; ++i)";
1307       stream << "\n";
1308       stream << indent_str;
1309       stream << "    {";
1310       stream << "\n";
1311       stream << indent_str;
1312       stream << "      if (strncmp(val, values[i], len) == 0)";
1313       stream << "\n";
1314       stream << indent_str;
1315       stream << "        {";
1316       stream << "\n";
1317       stream << indent_str;
1318       stream << "          ++found;";
1319       stream << "\n";
1320       stream << indent_str;
1321       stream << "          last = i;";
1322       stream << "\n";
1323       stream << indent_str;
1324       stream << "          if (strlen(values[i]) == len)";
1325       stream << "\n";
1326       stream << indent_str;
1327       stream << "            return i; /* exact macth no need to check more */";
1328       stream << "\n";
1329       stream << indent_str;
1330       stream << "        }";
1331       stream << "\n";
1332       stream << indent_str;
1333       stream << "    }";
1334       stream << "\n";
1335       stream << indent_str;
1336       stream << "\n";
1337       stream << indent_str;
1338       stream << "  if (found == 1) /* one match: OK */";
1339       stream << "\n";
1340       stream << indent_str;
1341       stream << "    return last;";
1342       stream << "\n";
1343       stream << indent_str;
1344       stream << "\n";
1345       stream << indent_str;
1346       stream << "  return (found ? -2 : -1); /* return many values or none matched */";
1347       stream << "\n";
1348       stream << indent_str;
1349       stream << "}";
1350       stream << "\n";
1351       stream << indent_str;
1352       stream << "\n";
1353       stream << indent_str;
1354     }
1355   stream << "\n";
1356   stream << indent_str;
1357   stream << "static void";
1358   stream << "\n";
1359   stream << indent_str;
1360   stream << "write_into_file(FILE *outfile, const char *opt, const char *arg, const char *values[])";
1361   stream << "\n";
1362   stream << indent_str;
1363   stream << "{";
1364   stream << "\n";
1365   stream << indent_str;
1366   if (check_possible_values)
1367     {
1368       stream << "  int found = -1;";
1369       stream << "\n";
1370       stream << indent_str;
1371     }
1372   else
1373     {
1374       stream << "  FIX_UNUSED (values);";
1375       stream << "\n";
1376       stream << indent_str;
1377     }
1378   stream << "  if (arg) {";
1379   stream << "\n";
1380   stream << indent_str;
1381   if (check_possible_values)
1382     {
1383       stream << "    if (values) {";
1384       stream << "\n";
1385       stream << indent_str;
1386       stream << "      found = check_possible_values(arg, values);      ";
1387       stream << "\n";
1388       stream << indent_str;
1389       stream << "    }";
1390       stream << "\n";
1391       stream << indent_str;
1392       stream << "    if (found >= 0)";
1393       stream << "\n";
1394       stream << indent_str;
1395       stream << "      fprintf(outfile, \"%s=\\\"%s\\\" # %s\\n\", opt, arg, values[found]);";
1396       stream << "\n";
1397       stream << indent_str;
1398       stream << "    else";
1399       stream << "\n";
1400       stream << indent_str;
1401       stream << "      fprintf(outfile, \"%s=\\\"%s\\\"\\n\", opt, arg);";
1402       stream << "\n";
1403       stream << indent_str;
1404     }
1405   else
1406     {
1407       stream << "    fprintf(outfile, \"%s=\\\"%s\\\"\\n\", opt, arg);";
1408       stream << "\n";
1409       stream << indent_str;
1410     }
1411   stream << "  } else {";
1412   stream << "\n";
1413   stream << indent_str;
1414   stream << "    fprintf(outfile, \"%s\\n\", opt);";
1415   stream << "\n";
1416   stream << indent_str;
1417   stream << "  }";
1418   stream << "\n";
1419   stream << indent_str;
1420   stream << "}";
1421   stream << "\n";
1422   stream << indent_str;
1423   stream << "\n";
1424   stream << indent_str;
1425   if (multiple_options)
1426     {
1427       stream << "static void";
1428       stream << "\n";
1429       stream << indent_str;
1430       stream << "write_multiple_into_file(FILE *outfile, int len, const char *opt, char **arg, const char *values[])";
1431       stream << "\n";
1432       stream << indent_str;
1433       stream << "{";
1434       stream << "\n";
1435       stream << indent_str;
1436       stream << "  int i;";
1437       stream << "\n";
1438       stream << indent_str;
1439       indent = 2;
1440       stream << "  ";
1441       indent = 0;
1442       stream << "\n";
1443       stream << indent_str;
1444       stream << "  for (i = 0; i < len; ++i)";
1445       stream << "\n";
1446       stream << indent_str;
1447       stream << "    write_into_file(outfile, opt, (arg ? arg[i] : 0), values);";
1448       stream << "\n";
1449       stream << indent_str;
1450       stream << "}";
1451       stream << "\n";
1452       stream << indent_str;
1453     }
1454   stream << "\n";
1455   stream << indent_str;
1456   stream << "int";
1457   stream << "\n";
1458   stream << indent_str;
1459   generate_string (parser_name, stream, indent + indent_str.length ());
1460   stream << "_dump(FILE *outfile, struct ";
1461   generate_string (args_info, stream, indent + indent_str.length ());
1462   stream << " *args_info)";
1463   stream << "\n";
1464   stream << indent_str;
1465   stream << "{";
1466   stream << "\n";
1467   stream << indent_str;
1468   stream << "  int i = 0;";
1469   stream << "\n";
1470   stream << indent_str;
1471   stream << "\n";
1472   stream << indent_str;
1473   stream << "  if (!outfile)";
1474   stream << "\n";
1475   stream << indent_str;
1476   stream << "    {";
1477   stream << "\n";
1478   stream << indent_str;
1479   stream << "      fprintf (stderr, \"%s: cannot dump options to stream\\n\", ";
1480   generate_string (package_var_name, stream, indent + indent_str.length ());
1481   stream << ");";
1482   stream << "\n";
1483   stream << indent_str;
1484   stream << "      return EXIT_FAILURE;";
1485   stream << "\n";
1486   stream << indent_str;
1487   stream << "    }";
1488   stream << "\n";
1489   stream << indent_str;
1490   stream << "\n";
1491   stream << indent_str;
1492   indent = 2;
1493   stream << "  ";
1494   if (file_save_loop.size () > 0)
1495     generate_string (file_save_loop, stream, indent + indent_str.length ());
1496   else
1497     generate_file_save_loop (stream, indent + indent_str.length ());
1498   indent = 0;
1499   stream << "\n";
1500   stream << indent_str;
1501   stream << "\n";
1502   stream << indent_str;
1503   stream << "  i = EXIT_SUCCESS;";
1504   stream << "\n";
1505   stream << indent_str;
1506   stream << "  return i;";
1507   stream << "\n";
1508   stream << indent_str;
1509   stream << "}";
1510   stream << "\n";
1511   stream << indent_str;
1512   stream << "\n";
1513   stream << indent_str;
1514   stream << "int";
1515   stream << "\n";
1516   stream << indent_str;
1517   generate_string (parser_name, stream, indent + indent_str.length ());
1518   stream << "_file_save(const char *filename, struct ";
1519   generate_string (args_info, stream, indent + indent_str.length ());
1520   stream << " *args_info)";
1521   stream << "\n";
1522   stream << indent_str;
1523   stream << "{";
1524   stream << "\n";
1525   stream << indent_str;
1526   stream << "  FILE *outfile;";
1527   stream << "\n";
1528   stream << indent_str;
1529   stream << "  int i = 0;";
1530   stream << "\n";
1531   stream << indent_str;
1532   stream << "\n";
1533   stream << indent_str;
1534   stream << "  outfile = fopen(filename, \"w\");";
1535   stream << "\n";
1536   stream << indent_str;
1537   stream << "\n";
1538   stream << indent_str;
1539   stream << "  if (!outfile)";
1540   stream << "\n";
1541   stream << indent_str;
1542   stream << "    {";
1543   stream << "\n";
1544   stream << indent_str;
1545   stream << "      fprintf (stderr, \"%s: cannot open file for writing: %s\\n\", ";
1546   generate_string (package_var_name, stream, indent + indent_str.length ());
1547   stream << ", filename);";
1548   stream << "\n";
1549   stream << indent_str;
1550   stream << "      return EXIT_FAILURE;";
1551   stream << "\n";
1552   stream << indent_str;
1553   stream << "    }";
1554   stream << "\n";
1555   stream << indent_str;
1556   stream << "\n";
1557   stream << indent_str;
1558   stream << "  i = ";
1559   generate_string (parser_name, stream, indent + indent_str.length ());
1560   stream << "_dump(outfile, args_info);";
1561   stream << "\n";
1562   stream << indent_str;
1563   stream << "  fclose (outfile);";
1564   stream << "\n";
1565   stream << indent_str;
1566   stream << "\n";
1567   stream << indent_str;
1568   stream << "  return i;";
1569   stream << "\n";
1570   stream << indent_str;
1571   stream << "}";
1572   stream << "\n";
1573   stream << indent_str;
1574   stream << "\n";
1575   stream << indent_str;
1576   stream << "void";
1577   stream << "\n";
1578   stream << indent_str;
1579   generate_string (parser_name, stream, indent + indent_str.length ());
1580   stream << "_free (struct ";
1581   generate_string (args_info, stream, indent + indent_str.length ());
1582   stream << " *args_info)";
1583   stream << "\n";
1584   stream << indent_str;
1585   stream << "{";
1586   stream << "\n";
1587   stream << indent_str;
1588   indent = 2;
1589   stream << "  ";
1590   generate_string (parser_name, stream, indent + indent_str.length ());
1591   stream << "_release (args_info);";
1592   indent = 0;
1593   stream << "\n";
1594   stream << indent_str;
1595   stream << "}";
1596   stream << "\n";
1597   stream << indent_str;
1598   stream << "\n";
1599   stream << indent_str;
1600   if (do_generate_strdup)
1601     {
1602       stream << "/** ";
1603       stream << "@";
1604       stream << "brief replacement of strdup, which is not standard */";
1605       stream << "\n";
1606       stream << indent_str;
1607       stream << "char *";
1608       stream << "\n";
1609       stream << indent_str;
1610       stream << "gengetopt_strdup (const char *s)";
1611       stream << "\n";
1612       stream << indent_str;
1613       stream << "{";
1614       stream << "\n";
1615       stream << indent_str;
1616       stream << "  char *result = 0;";
1617       stream << "\n";
1618       stream << indent_str;
1619       stream << "  if (!s)";
1620       stream << "\n";
1621       stream << indent_str;
1622       stream << "    return result;";
1623       stream << "\n";
1624       stream << indent_str;
1625       stream << "\n";
1626       stream << indent_str;
1627       stream << "  result = (char*)malloc(strlen(s) + 1);";
1628       stream << "\n";
1629       stream << indent_str;
1630       stream << "  if (result == (char*)0)";
1631       stream << "\n";
1632       stream << indent_str;
1633       stream << "    return (char*)0;";
1634       stream << "\n";
1635       stream << indent_str;
1636       stream << "  strcpy(result, s);";
1637       stream << "\n";
1638       stream << indent_str;
1639       stream << "  return result;";
1640       stream << "\n";
1641       stream << indent_str;
1642       stream << "}";
1643       stream << "\n";
1644       stream << indent_str;
1645       stream << "\n";
1646       stream << indent_str;
1647     }
1648   if (multiple_token_functions)
1649     {
1650       stream << "static char *";
1651       stream << "\n";
1652       stream << indent_str;
1653       stream << "get_multiple_arg_token(const char *arg)";
1654       stream << "\n";
1655       stream << indent_str;
1656       stream << "{";
1657       stream << "\n";
1658       stream << indent_str;
1659       stream << "  const char *tok;";
1660       stream << "\n";
1661       stream << indent_str;
1662       stream << "  char *ret;";
1663       stream << "\n";
1664       stream << indent_str;
1665       stream << "  size_t len, num_of_escape, i, j;";
1666       stream << "\n";
1667       stream << indent_str;
1668       stream << "\n";
1669       stream << indent_str;
1670       stream << "  if (!arg)";
1671       stream << "\n";
1672       stream << indent_str;
1673       stream << "    return 0;";
1674       stream << "\n";
1675       stream << indent_str;
1676       stream << "\n";
1677       stream << indent_str;
1678       stream << "  tok = strchr (arg, ',');";
1679       stream << "\n";
1680       stream << indent_str;
1681       stream << "  num_of_escape = 0;";
1682       stream << "\n";
1683       stream << indent_str;
1684       stream << "\n";
1685       stream << indent_str;
1686       stream << "  /* make sure it is not escaped */";
1687       stream << "\n";
1688       stream << indent_str;
1689       stream << "  while (tok)";
1690       stream << "\n";
1691       stream << indent_str;
1692       stream << "    {";
1693       stream << "\n";
1694       stream << indent_str;
1695       stream << "      if (*(tok-1) == '\\\\')";
1696       stream << "\n";
1697       stream << indent_str;
1698       stream << "        {";
1699       stream << "\n";
1700       stream << indent_str;
1701       stream << "          /* find the next one */";
1702       stream << "\n";
1703       stream << indent_str;
1704       stream << "          tok = strchr (tok+1, ',');";
1705       stream << "\n";
1706       stream << indent_str;
1707       stream << "          ++num_of_escape;";
1708       stream << "\n";
1709       stream << indent_str;
1710       stream << "        }";
1711       stream << "\n";
1712       stream << indent_str;
1713       stream << "      else";
1714       stream << "\n";
1715       stream << indent_str;
1716       stream << "        break;";
1717       stream << "\n";
1718       stream << indent_str;
1719       stream << "    }";
1720       stream << "\n";
1721       stream << indent_str;
1722       stream << "\n";
1723       stream << indent_str;
1724       stream << "  if (tok)";
1725       stream << "\n";
1726       stream << indent_str;
1727       stream << "    len = (size_t)(tok - arg + 1);";
1728       stream << "\n";
1729       stream << indent_str;
1730       stream << "  else";
1731       stream << "\n";
1732       stream << indent_str;
1733       stream << "    len = strlen (arg) + 1;";
1734       stream << "\n";
1735       stream << indent_str;
1736       stream << "\n";
1737       stream << indent_str;
1738       stream << "  len -= num_of_escape;";
1739       stream << "\n";
1740       stream << indent_str;
1741       stream << "\n";
1742       stream << indent_str;
1743       stream << "  ret = (char *) malloc (len);";
1744       stream << "\n";
1745       stream << indent_str;
1746       stream << "\n";
1747       stream << indent_str;
1748       stream << "  i = 0;";
1749       stream << "\n";
1750       stream << indent_str;
1751       stream << "  j = 0;";
1752       stream << "\n";
1753       stream << indent_str;
1754       stream << "  while (arg[i] && (j < len-1))";
1755       stream << "\n";
1756       stream << indent_str;
1757       stream << "    {";
1758       stream << "\n";
1759       stream << indent_str;
1760       stream << "      if (arg[i] == '\\\\' && ";
1761       stream << "\n";
1762       stream << indent_str;
1763       stream << "	  arg[ i + 1 ] && ";
1764       stream << "\n";
1765       stream << indent_str;
1766       stream << "	  arg[ i + 1 ] == ',')";
1767       stream << "\n";
1768       stream << indent_str;
1769       stream << "        ++i;";
1770       stream << "\n";
1771       stream << indent_str;
1772       stream << "\n";
1773       stream << indent_str;
1774       stream << "      ret[j++] = arg[i++];";
1775       stream << "\n";
1776       stream << indent_str;
1777       stream << "    }";
1778       stream << "\n";
1779       stream << indent_str;
1780       stream << "\n";
1781       stream << indent_str;
1782       stream << "  ret[len-1] = '\\0';";
1783       stream << "\n";
1784       stream << indent_str;
1785       stream << "\n";
1786       stream << indent_str;
1787       stream << "  return ret;";
1788       stream << "\n";
1789       stream << indent_str;
1790       stream << "}";
1791       stream << "\n";
1792       stream << indent_str;
1793       stream << "\n";
1794       stream << indent_str;
1795       stream << "static const char *";
1796       stream << "\n";
1797       stream << indent_str;
1798       stream << "get_multiple_arg_token_next(const char *arg)";
1799       stream << "\n";
1800       stream << indent_str;
1801       stream << "{";
1802       stream << "\n";
1803       stream << indent_str;
1804       stream << "  const char *tok;";
1805       stream << "\n";
1806       stream << indent_str;
1807       stream << "\n";
1808       stream << indent_str;
1809       stream << "  if (!arg)";
1810       stream << "\n";
1811       stream << indent_str;
1812       stream << "    return 0;";
1813       stream << "\n";
1814       stream << indent_str;
1815       stream << "\n";
1816       stream << indent_str;
1817       stream << "  tok = strchr (arg, ',');";
1818       stream << "\n";
1819       stream << indent_str;
1820       stream << "\n";
1821       stream << indent_str;
1822       stream << "  /* make sure it is not escaped */";
1823       stream << "\n";
1824       stream << indent_str;
1825       stream << "  while (tok)";
1826       stream << "\n";
1827       stream << indent_str;
1828       stream << "    {";
1829       stream << "\n";
1830       stream << indent_str;
1831       stream << "      if (*(tok-1) == '\\\\')";
1832       stream << "\n";
1833       stream << indent_str;
1834       stream << "        {";
1835       stream << "\n";
1836       stream << indent_str;
1837       stream << "          /* find the next one */";
1838       stream << "\n";
1839       stream << indent_str;
1840       stream << "          tok = strchr (tok+1, ',');";
1841       stream << "\n";
1842       stream << indent_str;
1843       stream << "        }";
1844       stream << "\n";
1845       stream << indent_str;
1846       stream << "      else";
1847       stream << "\n";
1848       stream << indent_str;
1849       stream << "        break;";
1850       stream << "\n";
1851       stream << indent_str;
1852       stream << "    }";
1853       stream << "\n";
1854       stream << indent_str;
1855       stream << "\n";
1856       stream << indent_str;
1857       stream << "  if (! tok || strlen(tok) == 1)";
1858       stream << "\n";
1859       stream << indent_str;
1860       stream << "    return 0;";
1861       stream << "\n";
1862       stream << indent_str;
1863       stream << "\n";
1864       stream << indent_str;
1865       stream << "  return tok+1;";
1866       stream << "\n";
1867       stream << indent_str;
1868       stream << "}";
1869       stream << "\n";
1870       stream << indent_str;
1871       stream << "\n";
1872       stream << indent_str;
1873     }
1874   if (multiple_options)
1875     {
1876       stream << "static int";
1877       stream << "\n";
1878       stream << indent_str;
1879       stream << "check_multiple_option_occurrences(const char *prog_name, unsigned int option_given, unsigned int min, unsigned int max, const char *option_desc);";
1880       stream << "\n";
1881       stream << indent_str;
1882       stream << "\n";
1883       stream << indent_str;
1884       stream << "int";
1885       stream << "\n";
1886       stream << indent_str;
1887       stream << "check_multiple_option_occurrences(const char *prog_name, unsigned int option_given, unsigned int min, unsigned int max, const char *option_desc)";
1888       stream << "\n";
1889       stream << indent_str;
1890       stream << "{";
1891       stream << "\n";
1892       stream << indent_str;
1893       stream << "  int error_occurred = 0;";
1894       stream << "\n";
1895       stream << indent_str;
1896       stream << "\n";
1897       stream << indent_str;
1898       stream << "  if (option_given && (min > 0 || max > 0))";
1899       stream << "\n";
1900       stream << indent_str;
1901       stream << "    {";
1902       stream << "\n";
1903       stream << indent_str;
1904       stream << "      if (min > 0 && max > 0)";
1905       stream << "\n";
1906       stream << indent_str;
1907       stream << "        {";
1908       stream << "\n";
1909       stream << indent_str;
1910       stream << "          if (min == max)";
1911       stream << "\n";
1912       stream << indent_str;
1913       stream << "            {";
1914       stream << "\n";
1915       stream << indent_str;
1916       stream << "              /* specific occurrences */";
1917       stream << "\n";
1918       stream << indent_str;
1919       stream << "              if (option_given != (unsigned int) min)";
1920       stream << "\n";
1921       stream << indent_str;
1922       stream << "                {";
1923       stream << "\n";
1924       stream << indent_str;
1925       stream << "                  fprintf (stderr, \"%s: %s option occurrences must be %d\\n\",";
1926       stream << "\n";
1927       stream << indent_str;
1928       stream << "                    prog_name, option_desc, min);";
1929       stream << "\n";
1930       stream << indent_str;
1931       stream << "                  error_occurred = 1;";
1932       stream << "\n";
1933       stream << indent_str;
1934       stream << "                }";
1935       stream << "\n";
1936       stream << indent_str;
1937       stream << "            }";
1938       stream << "\n";
1939       stream << indent_str;
1940       stream << "          else if (option_given < (unsigned int) min";
1941       stream << "\n";
1942       stream << indent_str;
1943       stream << "                || option_given > (unsigned int) max)";
1944       stream << "\n";
1945       stream << indent_str;
1946       stream << "            {";
1947       stream << "\n";
1948       stream << indent_str;
1949       stream << "              /* range occurrences */";
1950       stream << "\n";
1951       stream << indent_str;
1952       stream << "              fprintf (stderr, \"%s: %s option occurrences must be between %d and %d\\n\",";
1953       stream << "\n";
1954       stream << indent_str;
1955       stream << "                prog_name, option_desc, min, max);";
1956       stream << "\n";
1957       stream << indent_str;
1958       stream << "              error_occurred = 1;";
1959       stream << "\n";
1960       stream << indent_str;
1961       stream << "            }";
1962       stream << "\n";
1963       stream << indent_str;
1964       stream << "        }";
1965       stream << "\n";
1966       stream << indent_str;
1967       stream << "      else if (min > 0)";
1968       stream << "\n";
1969       stream << indent_str;
1970       stream << "        {";
1971       stream << "\n";
1972       stream << indent_str;
1973       stream << "          /* at least check */";
1974       stream << "\n";
1975       stream << indent_str;
1976       stream << "          if (option_given < min)";
1977       stream << "\n";
1978       stream << indent_str;
1979       stream << "            {";
1980       stream << "\n";
1981       stream << indent_str;
1982       stream << "              fprintf (stderr, \"%s: %s option occurrences must be at least %d\\n\",";
1983       stream << "\n";
1984       stream << indent_str;
1985       stream << "                prog_name, option_desc, min);";
1986       stream << "\n";
1987       stream << indent_str;
1988       stream << "              error_occurred = 1;";
1989       stream << "\n";
1990       stream << indent_str;
1991       stream << "            }";
1992       stream << "\n";
1993       stream << indent_str;
1994       stream << "        }";
1995       stream << "\n";
1996       stream << indent_str;
1997       stream << "      else if (max > 0)";
1998       stream << "\n";
1999       stream << indent_str;
2000       stream << "        {";
2001       stream << "\n";
2002       stream << indent_str;
2003       stream << "          /* at most check */";
2004       stream << "\n";
2005       stream << indent_str;
2006       stream << "          if (option_given > max)";
2007       stream << "\n";
2008       stream << indent_str;
2009       stream << "            {";
2010       stream << "\n";
2011       stream << indent_str;
2012       stream << "              fprintf (stderr, \"%s: %s option occurrences must be at most %d\\n\",";
2013       stream << "\n";
2014       stream << indent_str;
2015       stream << "                prog_name, option_desc, max);";
2016       stream << "\n";
2017       stream << indent_str;
2018       stream << "              error_occurred = 1;";
2019       stream << "\n";
2020       stream << indent_str;
2021       stream << "            }";
2022       stream << "\n";
2023       stream << indent_str;
2024       stream << "        }";
2025       stream << "\n";
2026       stream << indent_str;
2027       stream << "    }";
2028       stream << "\n";
2029       stream << indent_str;
2030       indent = 4;
2031       stream << "    ";
2032       indent = 0;
2033       stream << "\n";
2034       stream << indent_str;
2035       stream << "  return error_occurred;";
2036       stream << "\n";
2037       stream << indent_str;
2038       stream << "}";
2039       stream << "\n";
2040       stream << indent_str;
2041     }
2042   if (reset_groups.size () > 0)
2043     generate_string (reset_groups, stream, indent + indent_str.length ());
2044   else
2045     generate_reset_groups (stream, indent + indent_str.length ());
2046   stream << indent_str;
2047   stream << "int";
2048   stream << "\n";
2049   stream << indent_str;
2050   generate_string (parser_name, stream, indent + indent_str.length ());
2051   stream << " (int argc, char **argv, struct ";
2052   generate_string (args_info, stream, indent + indent_str.length ());
2053   stream << " *args_info)";
2054   stream << "\n";
2055   stream << indent_str;
2056   stream << "{";
2057   stream << "\n";
2058   stream << indent_str;
2059   stream << "  return ";
2060   generate_string (parser_name, stream, indent + indent_str.length ());
2061   stream << "2 (argc, argv, args_info, 0, 1, 1);";
2062   stream << "\n";
2063   stream << indent_str;
2064   stream << "}";
2065   stream << "\n";
2066   stream << indent_str;
2067   stream << "\n";
2068   stream << indent_str;
2069   stream << "int";
2070   stream << "\n";
2071   stream << indent_str;
2072   generate_string (parser_name, stream, indent + indent_str.length ());
2073   stream << "_ext (int argc, char **argv, struct ";
2074   generate_string (args_info, stream, indent + indent_str.length ());
2075   stream << " *args_info,";
2076   stream << "\n";
2077   stream << indent_str;
2078   stream << "                   struct ";
2079   generate_string (parser_name, stream, indent + indent_str.length ());
2080   stream << "_params *params)";
2081   stream << "\n";
2082   stream << indent_str;
2083   stream << "{";
2084   stream << "\n";
2085   stream << indent_str;
2086   stream << "  int result;";
2087   stream << "\n";
2088   stream << indent_str;
2089   stream << "  result = ";
2090   generate_string (parser_name, stream, indent + indent_str.length ());
2091   stream << "_internal (argc, argv, args_info, params, 0);";
2092   stream << "\n";
2093   stream << indent_str;
2094   stream << "\n";
2095   stream << indent_str;
2096   indent = 2;
2097   stream << "  ";
2098   generate_string (final_exit, stream, indent + indent_str.length ());
2099   indent = 0;
2100   stream << "\n";
2101   stream << indent_str;
2102   stream << "}";
2103   stream << "\n";
2104   stream << indent_str;
2105   stream << "\n";
2106   stream << indent_str;
2107   stream << "int";
2108   stream << "\n";
2109   stream << indent_str;
2110   generate_string (parser_name, stream, indent + indent_str.length ());
2111   stream << "2 (int argc, char **argv, struct ";
2112   generate_string (args_info, stream, indent + indent_str.length ());
2113   stream << " *args_info, int override, int initialize, int check_required)";
2114   stream << "\n";
2115   stream << indent_str;
2116   stream << "{";
2117   stream << "\n";
2118   stream << indent_str;
2119   stream << "  int result;";
2120   stream << "\n";
2121   stream << indent_str;
2122   stream << "  struct ";
2123   generate_string (parser_name, stream, indent + indent_str.length ());
2124   stream << "_params params;";
2125   stream << "\n";
2126   stream << indent_str;
2127   indent = 2;
2128   stream << "  ";
2129   indent = 0;
2130   stream << "\n";
2131   stream << indent_str;
2132   stream << "  params.override = override;";
2133   stream << "\n";
2134   stream << indent_str;
2135   stream << "  params.initialize = initialize;";
2136   stream << "\n";
2137   stream << indent_str;
2138   stream << "  params.check_required = check_required;";
2139   stream << "\n";
2140   stream << indent_str;
2141   stream << "  params.check_ambiguity = 0;";
2142   stream << "\n";
2143   stream << indent_str;
2144   stream << "  params.print_errors = 1;";
2145   stream << "\n";
2146   stream << indent_str;
2147   stream << "\n";
2148   stream << indent_str;
2149   stream << "  result = ";
2150   generate_string (parser_name, stream, indent + indent_str.length ());
2151   stream << "_internal (argc, argv, args_info, &params, 0);";
2152   stream << "\n";
2153   stream << indent_str;
2154   stream << "\n";
2155   stream << indent_str;
2156   indent = 2;
2157   stream << "  ";
2158   generate_string (final_exit, stream, indent + indent_str.length ());
2159   indent = 0;
2160   stream << "\n";
2161   stream << indent_str;
2162   stream << "}";
2163   stream << "\n";
2164   stream << indent_str;
2165   stream << "\n";
2166   stream << indent_str;
2167   stream << "int";
2168   stream << "\n";
2169   stream << indent_str;
2170   generate_string (parser_name, stream, indent + indent_str.length ());
2171   stream << "_required (struct ";
2172   generate_string (args_info, stream, indent + indent_str.length ());
2173   stream << " *args_info, const char *prog_name)";
2174   stream << "\n";
2175   stream << indent_str;
2176   stream << "{";
2177   stream << "\n";
2178   stream << indent_str;
2179   if (check_required_options)
2180     {
2181       stream << "  int result = EXIT_SUCCESS;";
2182       stream << "\n";
2183       stream << indent_str;
2184       stream << "\n";
2185       stream << indent_str;
2186       stream << "  if (";
2187       generate_string (parser_name, stream, indent + indent_str.length ());
2188       stream << "_required2(args_info, prog_name, 0) > 0)";
2189       stream << "\n";
2190       stream << indent_str;
2191       stream << "    result = EXIT_FAILURE;";
2192       stream << "\n";
2193       stream << indent_str;
2194       stream << "\n";
2195       stream << indent_str;
2196       indent = 2;
2197       stream << "  ";
2198       generate_string (final_exit, stream, indent + indent_str.length ());
2199       indent = 0;
2200       stream << "\n";
2201       stream << indent_str;
2202     }
2203   else
2204     {
2205       stream << "  FIX_UNUSED (args_info);";
2206       stream << "\n";
2207       stream << indent_str;
2208       stream << "  FIX_UNUSED (prog_name);";
2209       stream << "\n";
2210       stream << indent_str;
2211       stream << "  return EXIT_SUCCESS;";
2212       stream << "\n";
2213       stream << indent_str;
2214     }
2215   stream << "}";
2216   stream << "\n";
2217   stream << indent_str;
2218   stream << "\n";
2219   stream << indent_str;
2220   if (check_required_options)
2221     {
2222       stream << "int";
2223       stream << "\n";
2224       stream << indent_str;
2225       generate_string (parser_name, stream, indent + indent_str.length ());
2226       stream << "_required2 (struct ";
2227       generate_string (args_info, stream, indent + indent_str.length ());
2228       stream << " *args_info, const char *prog_name, const char *additional_error)";
2229       stream << "\n";
2230       stream << indent_str;
2231       stream << "{";
2232       stream << "\n";
2233       stream << indent_str;
2234       stream << "  int error_occurred = 0;";
2235       stream << "\n";
2236       stream << indent_str;
2237       stream << "  FIX_UNUSED (additional_error);";
2238       stream << "\n";
2239       stream << indent_str;
2240       stream << "\n";
2241       stream << indent_str;
2242       stream << "  /* checks for required options */";
2243       stream << "\n";
2244       stream << indent_str;
2245       indent = 2;
2246       stream << "  ";
2247       if (handle_required.size () > 0)
2248         generate_string (handle_required, stream, indent + indent_str.length ());
2249       else
2250         generate_handle_required (stream, indent + indent_str.length ());
2251       indent = 0;
2252       stream << "\n";
2253       stream << indent_str;
2254       stream << "  /* checks for dependences among options */";
2255       stream << "\n";
2256       stream << indent_str;
2257       indent = 2;
2258       if (handle_dependencies.size () > 0)
2259         generate_string (handle_dependencies, stream, indent + indent_str.length ());
2260       else
2261         generate_handle_dependencies (stream, indent + indent_str.length ());
2262       indent = 0;
2263       stream << indent_str;
2264       stream << "\n";
2265       stream << indent_str;
2266       stream << "  return error_occurred;";
2267       stream << "\n";
2268       stream << indent_str;
2269       stream << "}";
2270       stream << "\n";
2271       stream << indent_str;
2272       stream << "\n";
2273       stream << indent_str;
2274     }
2275   if (include_getopt)
2276     {
2277       if (custom_getopt.size () > 0)
2278         generate_string (custom_getopt, stream, indent + indent_str.length ());
2279       else
2280         generate_custom_getopt (stream, indent + indent_str.length ());
2281       stream << "\n";
2282       stream << indent_str;
2283     }
2284   stream << "\n";
2285   stream << indent_str;
2286   stream << "static char *package_name = 0;";
2287   stream << "\n";
2288   stream << indent_str;
2289   stream << "\n";
2290   stream << indent_str;
2291   if (( ! no_options ))
2292     {
2293       stream << "/**";
2294       stream << "\n";
2295       stream << indent_str;
2296       stream << " * ";
2297       stream << "@";
2298       stream << "brief updates an option";
2299       stream << "\n";
2300       stream << indent_str;
2301       stream << " * ";
2302       stream << "@";
2303       stream << "param field the generic pointer to the field to update";
2304       stream << "\n";
2305       stream << indent_str;
2306       stream << " * ";
2307       stream << "@";
2308       stream << "param orig_field the pointer to the orig field";
2309       stream << "\n";
2310       stream << indent_str;
2311       stream << " * ";
2312       stream << "@";
2313       stream << "param field_given the pointer to the number of occurrence of this option";
2314       stream << "\n";
2315       stream << indent_str;
2316       stream << " * ";
2317       stream << "@";
2318       stream << "param prev_given the pointer to the number of occurrence already seen";
2319       stream << "\n";
2320       stream << indent_str;
2321       stream << " * ";
2322       stream << "@";
2323       stream << "param value the argument for this option (if null no arg was specified)";
2324       stream << "\n";
2325       stream << indent_str;
2326       stream << " * ";
2327       stream << "@";
2328       stream << "param possible_values the possible values for this option (if specified)";
2329       stream << "\n";
2330       stream << indent_str;
2331       stream << " * ";
2332       stream << "@";
2333       stream << "param default_value the default value (in case the option only accepts fixed values)";
2334       stream << "\n";
2335       stream << indent_str;
2336       stream << " * ";
2337       stream << "@";
2338       stream << "param arg_type the type of this option";
2339       stream << "\n";
2340       stream << indent_str;
2341       stream << " * ";
2342       stream << "@";
2343       stream << "param check_ambiguity ";
2344       stream << "@";
2345       stream << "see ";
2346       generate_string (parser_name, stream, indent + indent_str.length ());
2347       stream << "_params.check_ambiguity";
2348       stream << "\n";
2349       stream << indent_str;
2350       stream << " * ";
2351       stream << "@";
2352       stream << "param override ";
2353       stream << "@";
2354       stream << "see ";
2355       generate_string (parser_name, stream, indent + indent_str.length ());
2356       stream << "_params.override";
2357       stream << "\n";
2358       stream << indent_str;
2359       stream << " * ";
2360       stream << "@";
2361       stream << "param no_free whether to free a possible previous value";
2362       stream << "\n";
2363       stream << indent_str;
2364       stream << " * ";
2365       stream << "@";
2366       stream << "param multiple_option whether this is a multiple option";
2367       stream << "\n";
2368       stream << indent_str;
2369       stream << " * ";
2370       stream << "@";
2371       stream << "param long_opt the corresponding long option";
2372       stream << "\n";
2373       stream << indent_str;
2374       stream << " * ";
2375       stream << "@";
2376       stream << "param short_opt the corresponding short option (or '-' if none)";
2377       stream << "\n";
2378       stream << indent_str;
2379       stream << " * ";
2380       stream << "@";
2381       stream << "param additional_error possible further error specification";
2382       stream << "\n";
2383       stream << indent_str;
2384       stream << " */";
2385       stream << "\n";
2386       stream << indent_str;
2387       stream << "static";
2388       stream << "\n";
2389       stream << indent_str;
2390       stream << "int update_arg(void *field, char **orig_field,";
2391       stream << "\n";
2392       stream << indent_str;
2393       stream << "               unsigned int *field_given, unsigned int *prev_given, ";
2394       stream << "\n";
2395       stream << indent_str;
2396       stream << "               char *value, const char *possible_values[],";
2397       stream << "\n";
2398       stream << indent_str;
2399       stream << "               const char *default_value,";
2400       stream << "\n";
2401       stream << indent_str;
2402       indent = 15;
2403       stream << "               ";
2404       generate_string (parser_name, stream, indent + indent_str.length ());
2405       stream << "_arg_type arg_type,";
2406       indent = 0;
2407       stream << "\n";
2408       stream << indent_str;
2409       stream << "               int check_ambiguity, int override,";
2410       stream << "\n";
2411       stream << indent_str;
2412       stream << "               int no_free, int multiple_option,";
2413       stream << "\n";
2414       stream << indent_str;
2415       stream << "               const char *long_opt, char short_opt,";
2416       stream << "\n";
2417       stream << indent_str;
2418       stream << "               const char *additional_error)";
2419       stream << "\n";
2420       stream << indent_str;
2421       stream << "{";
2422       stream << "\n";
2423       stream << indent_str;
2424       stream << "  char *stop_char = 0;";
2425       stream << "\n";
2426       stream << indent_str;
2427       stream << "  const char *val = value;";
2428       stream << "\n";
2429       stream << indent_str;
2430       stream << "  int found;";
2431       stream << "\n";
2432       stream << indent_str;
2433       if (has_arg_string)
2434         {
2435           stream << "  char **string_field;";
2436           stream << "\n";
2437           stream << indent_str;
2438         }
2439       stream << "  FIX_UNUSED (field);";
2440       stream << "\n";
2441       stream << indent_str;
2442       stream << "\n";
2443       stream << indent_str;
2444       stream << "  stop_char = 0;";
2445       stream << "\n";
2446       stream << indent_str;
2447       stream << "  found = 0;";
2448       stream << "\n";
2449       stream << indent_str;
2450       stream << "\n";
2451       stream << indent_str;
2452       stream << "  if (!multiple_option && prev_given && (*prev_given || (check_ambiguity && *field_given)))";
2453       stream << "\n";
2454       stream << indent_str;
2455       stream << "    {";
2456       stream << "\n";
2457       stream << indent_str;
2458       stream << "      if (short_opt != '-')";
2459       stream << "\n";
2460       stream << indent_str;
2461       stream << "        fprintf (stderr, \"%s: `--%s' (`-%c') option given more than once%s\\n\", ";
2462       stream << "\n";
2463       stream << indent_str;
2464       stream << "               package_name, long_opt, short_opt,";
2465       stream << "\n";
2466       stream << indent_str;
2467       stream << "               (additional_error ? additional_error : \"\"));";
2468       stream << "\n";
2469       stream << indent_str;
2470       stream << "      else";
2471       stream << "\n";
2472       stream << indent_str;
2473       stream << "        fprintf (stderr, \"%s: `--%s' option given more than once%s\\n\", ";
2474       stream << "\n";
2475       stream << indent_str;
2476       stream << "               package_name, long_opt,";
2477       stream << "\n";
2478       stream << indent_str;
2479       stream << "               (additional_error ? additional_error : \"\"));";
2480       stream << "\n";
2481       stream << indent_str;
2482       stream << "      return 1; /* failure */";
2483       stream << "\n";
2484       stream << indent_str;
2485       stream << "    }";
2486       stream << "\n";
2487       stream << indent_str;
2488       stream << "\n";
2489       stream << indent_str;
2490       if (check_possible_values)
2491         {
2492           stream << "  if (possible_values && (found = check_possible_values((value ? value : default_value), possible_values)) < 0)";
2493           stream << "\n";
2494           stream << indent_str;
2495           stream << "    {";
2496           stream << "\n";
2497           stream << indent_str;
2498           stream << "      if (short_opt != '-')";
2499           stream << "\n";
2500           stream << indent_str;
2501           stream << "        fprintf (stderr, \"%s: %s argument, \\\"%s\\\", for option `--%s' (`-%c')%s\\n\", ";
2502           stream << "\n";
2503           stream << indent_str;
2504           stream << "          package_name, (found == -2) ? \"ambiguous\" : \"invalid\", value, long_opt, short_opt,";
2505           stream << "\n";
2506           stream << indent_str;
2507           stream << "          (additional_error ? additional_error : \"\"));";
2508           stream << "\n";
2509           stream << indent_str;
2510           stream << "      else";
2511           stream << "\n";
2512           stream << indent_str;
2513           stream << "        fprintf (stderr, \"%s: %s argument, \\\"%s\\\", for option `--%s'%s\\n\", ";
2514           stream << "\n";
2515           stream << indent_str;
2516           stream << "          package_name, (found == -2) ? \"ambiguous\" : \"invalid\", value, long_opt,";
2517           stream << "\n";
2518           stream << indent_str;
2519           stream << "          (additional_error ? additional_error : \"\"));";
2520           stream << "\n";
2521           stream << indent_str;
2522           stream << "      return 1; /* failure */";
2523           stream << "\n";
2524           stream << indent_str;
2525           stream << "    }";
2526           stream << "\n";
2527           stream << indent_str;
2528         }
2529       else
2530         {
2531           stream << "  FIX_UNUSED (default_value);";
2532           stream << "\n";
2533           stream << indent_str;
2534         }
2535       stream << "    ";
2536       stream << "\n";
2537       stream << indent_str;
2538       stream << "  if (field_given && *field_given && ! override)";
2539       stream << "\n";
2540       stream << indent_str;
2541       stream << "    return 0;";
2542       stream << "\n";
2543       stream << indent_str;
2544       stream << "  if (prev_given)";
2545       stream << "\n";
2546       stream << indent_str;
2547       stream << "    (*prev_given)++;";
2548       stream << "\n";
2549       stream << indent_str;
2550       stream << "  if (field_given)";
2551       stream << "\n";
2552       stream << indent_str;
2553       stream << "    (*field_given)++;";
2554       stream << "\n";
2555       stream << indent_str;
2556       stream << "  if (possible_values)";
2557       stream << "\n";
2558       stream << indent_str;
2559       stream << "    val = possible_values[found];";
2560       stream << "\n";
2561       stream << indent_str;
2562       stream << "\n";
2563       stream << indent_str;
2564       stream << "  switch(arg_type) {";
2565       stream << "\n";
2566       stream << indent_str;
2567       if (has_arg_flag)
2568         {
2569           stream << "  case ARG_FLAG:";
2570           stream << "\n";
2571           stream << indent_str;
2572           stream << "    *((int *)field) = !*((int *)field);";
2573           stream << "\n";
2574           stream << indent_str;
2575           stream << "    break;";
2576           stream << "\n";
2577           stream << indent_str;
2578         }
2579       if (has_arg_int)
2580         {
2581           stream << "  case ARG_INT:";
2582           stream << "\n";
2583           stream << indent_str;
2584           stream << "    if (val) *((int *)field) = strtol (val, &stop_char, 0);";
2585           stream << "\n";
2586           stream << indent_str;
2587           stream << "    break;";
2588           stream << "\n";
2589           stream << indent_str;
2590         }
2591       if (has_arg_short)
2592         {
2593           stream << "  case ARG_SHORT:";
2594           stream << "\n";
2595           stream << indent_str;
2596           stream << "    if (val) *((short *)field) = (short)strtol (val, &stop_char, 0);";
2597           stream << "\n";
2598           stream << indent_str;
2599           stream << "    break;";
2600           stream << "\n";
2601           stream << indent_str;
2602         }
2603       if (has_arg_long)
2604         {
2605           stream << "  case ARG_LONG:";
2606           stream << "\n";
2607           stream << indent_str;
2608           stream << "    if (val) *((long *)field) = (long)strtol (val, &stop_char, 0);";
2609           stream << "\n";
2610           stream << indent_str;
2611           stream << "    break;";
2612           stream << "\n";
2613           stream << indent_str;
2614         }
2615       if (has_arg_float)
2616         {
2617           stream << "  case ARG_FLOAT:";
2618           stream << "\n";
2619           stream << indent_str;
2620           stream << "    if (val) *((float *)field) = (float)strtod (val, &stop_char);";
2621           stream << "\n";
2622           stream << indent_str;
2623           stream << "    break;";
2624           stream << "\n";
2625           stream << indent_str;
2626         }
2627       if (has_arg_double)
2628         {
2629           stream << "  case ARG_DOUBLE:";
2630           stream << "\n";
2631           stream << indent_str;
2632           stream << "    if (val) *((double *)field) = strtod (val, &stop_char);";
2633           stream << "\n";
2634           stream << indent_str;
2635           stream << "    break;";
2636           stream << "\n";
2637           stream << indent_str;
2638         }
2639       if (has_arg_longdouble)
2640         {
2641           stream << "  case ARG_LONGDOUBLE:";
2642           stream << "\n";
2643           stream << indent_str;
2644           stream << "    if (val) *((long double *)field) = (long double)strtod (val, &stop_char);";
2645           stream << "\n";
2646           stream << indent_str;
2647           stream << "    break;";
2648           stream << "\n";
2649           stream << indent_str;
2650         }
2651       if (has_arg_longlong)
2652         {
2653           stream << "  case ARG_LONGLONG:";
2654           stream << "\n";
2655           stream << indent_str;
2656           stream << "#if defined(HAVE_LONG_LONG) || defined(HAVE_LONG_LONG_INT)";
2657           stream << "\n";
2658           stream << indent_str;
2659           stream << "    if (val) *((long long int*)field) = (long long int) strtoll (val, &stop_char, 0);";
2660           stream << "\n";
2661           stream << indent_str;
2662           stream << "#else";
2663           stream << "\n";
2664           stream << indent_str;
2665           stream << "    if (val) *((long *)field) = (long)strtol (val, &stop_char, 0);";
2666           stream << "\n";
2667           stream << indent_str;
2668           stream << "#endif";
2669           stream << "\n";
2670           stream << indent_str;
2671           stream << "    break;";
2672           stream << "\n";
2673           stream << indent_str;
2674         }
2675       if (has_arg_enum)
2676         {
2677           stream << "  case ARG_ENUM:";
2678           stream << "\n";
2679           stream << indent_str;
2680           stream << "    if (val) *((int *)field) = found;";
2681           stream << "\n";
2682           stream << indent_str;
2683           stream << "    break;";
2684           stream << "\n";
2685           stream << indent_str;
2686         }
2687       if (has_arg_string)
2688         {
2689           stream << "  case ARG_STRING:";
2690           stream << "\n";
2691           stream << indent_str;
2692           stream << "    if (val) {";
2693           stream << "\n";
2694           stream << indent_str;
2695           stream << "      string_field = (char **)field;";
2696           stream << "\n";
2697           stream << indent_str;
2698           stream << "      if (!no_free && *string_field)";
2699           stream << "\n";
2700           stream << indent_str;
2701           stream << "        free (*string_field); /* free previous string */";
2702           stream << "\n";
2703           stream << indent_str;
2704           stream << "      *string_field = gengetopt_strdup (val);";
2705           stream << "\n";
2706           stream << indent_str;
2707           stream << "    }";
2708           stream << "\n";
2709           stream << indent_str;
2710           stream << "    break;";
2711           stream << "\n";
2712           stream << indent_str;
2713         }
2714       stream << "  default:";
2715       stream << "\n";
2716       stream << indent_str;
2717       stream << "    break;";
2718       stream << "\n";
2719       stream << indent_str;
2720       stream << "  };";
2721       stream << "\n";
2722       stream << indent_str;
2723       stream << "\n";
2724       stream << indent_str;
2725       if (( ( ( ( ( ( has_arg_int || has_arg_short ) || has_arg_long ) || has_arg_float ) || has_arg_double ) || has_arg_longdouble ) || has_arg_longlong ))
2726         {
2727           stream << "  /* check numeric conversion */";
2728           stream << "\n";
2729           stream << indent_str;
2730           stream << "  switch(arg_type) {";
2731           stream << "\n";
2732           stream << indent_str;
2733           if (has_arg_int)
2734             {
2735               stream << "  case ARG_INT:";
2736               stream << "\n";
2737               stream << indent_str;
2738             }
2739           if (has_arg_short)
2740             {
2741               stream << "  case ARG_SHORT:";
2742               stream << "\n";
2743               stream << indent_str;
2744             }
2745           if (has_arg_long)
2746             {
2747               stream << "  case ARG_LONG:";
2748               stream << "\n";
2749               stream << indent_str;
2750             }
2751           if (has_arg_float)
2752             {
2753               stream << "  case ARG_FLOAT:";
2754               stream << "\n";
2755               stream << indent_str;
2756             }
2757           if (has_arg_double)
2758             {
2759               stream << "  case ARG_DOUBLE:";
2760               stream << "\n";
2761               stream << indent_str;
2762             }
2763           if (has_arg_longdouble)
2764             {
2765               stream << "  case ARG_LONGDOUBLE:";
2766               stream << "\n";
2767               stream << indent_str;
2768             }
2769           if (has_arg_longlong)
2770             {
2771               stream << "  case ARG_LONGLONG:";
2772               stream << "\n";
2773               stream << indent_str;
2774             }
2775           stream << "    if (val && !(stop_char && *stop_char == '\\0')) {";
2776           stream << "\n";
2777           stream << indent_str;
2778           stream << "      fprintf(stderr, \"%s: invalid numeric value: %s\\n\", package_name, val);";
2779           stream << "\n";
2780           stream << indent_str;
2781           stream << "      return 1; /* failure */";
2782           stream << "\n";
2783           stream << indent_str;
2784           stream << "    }";
2785           stream << "\n";
2786           stream << indent_str;
2787           stream << "    break;";
2788           stream << "\n";
2789           stream << indent_str;
2790           stream << "  default:";
2791           stream << "\n";
2792           stream << indent_str;
2793           stream << "    ;";
2794           stream << "\n";
2795           stream << indent_str;
2796           stream << "  };";
2797           stream << "\n";
2798           stream << indent_str;
2799         }
2800       else
2801         {
2802           stream << "	FIX_UNUSED(stop_char);";
2803           stream << "\n";
2804           stream << indent_str;
2805           stream << "	";
2806           if (( ! ( has_arg_enum || has_arg_string ) ))
2807             {
2808               stream << "		FIX_UNUSED(val);";
2809               stream << "\n";
2810               stream << indent_str;
2811               stream << "	";
2812             }
2813         }
2814       stream << "\n";
2815       stream << indent_str;
2816       stream << "  /* store the original value */";
2817       stream << "\n";
2818       stream << indent_str;
2819       stream << "  switch(arg_type) {";
2820       stream << "\n";
2821       stream << indent_str;
2822       stream << "  case ARG_NO:";
2823       stream << "\n";
2824       stream << indent_str;
2825       if (has_arg_flag)
2826         {
2827           stream << "  case ARG_FLAG:";
2828           stream << "\n";
2829           stream << indent_str;
2830         }
2831       stream << "    break;";
2832       stream << "\n";
2833       stream << indent_str;
2834       stream << "  default:";
2835       stream << "\n";
2836       stream << indent_str;
2837       stream << "    if (value && orig_field) {";
2838       stream << "\n";
2839       stream << indent_str;
2840       stream << "      if (no_free) {";
2841       stream << "\n";
2842       stream << indent_str;
2843       stream << "        *orig_field = value;";
2844       stream << "\n";
2845       stream << indent_str;
2846       stream << "      } else {";
2847       stream << "\n";
2848       stream << indent_str;
2849       stream << "        if (*orig_field)";
2850       stream << "\n";
2851       stream << indent_str;
2852       stream << "          free (*orig_field); /* free previous string */";
2853       stream << "\n";
2854       stream << indent_str;
2855       stream << "        *orig_field = gengetopt_strdup (value);";
2856       stream << "\n";
2857       stream << indent_str;
2858       stream << "      }";
2859       stream << "\n";
2860       stream << indent_str;
2861       stream << "    }";
2862       stream << "\n";
2863       stream << indent_str;
2864       stream << "  };";
2865       stream << "\n";
2866       stream << indent_str;
2867       stream << "\n";
2868       stream << indent_str;
2869       stream << "  return 0; /* OK */";
2870       stream << "\n";
2871       stream << indent_str;
2872       stream << "}";
2873       stream << "\n";
2874       stream << indent_str;
2875     }
2876   stream << "\n";
2877   stream << indent_str;
2878   if (multiple_token_functions)
2879     {
2880       stream << "/**";
2881       stream << "\n";
2882       stream << indent_str;
2883       stream << " * ";
2884       stream << "@";
2885       stream << "brief store information about a multiple option in a temporary list";
2886       stream << "\n";
2887       stream << indent_str;
2888       stream << " * ";
2889       stream << "@";
2890       stream << "param list where to (temporarily) store multiple options";
2891       stream << "\n";
2892       stream << indent_str;
2893       stream << " */";
2894       stream << "\n";
2895       stream << indent_str;
2896       stream << "static";
2897       stream << "\n";
2898       stream << indent_str;
2899       stream << "int update_multiple_arg_temp(struct generic_list **list,";
2900       stream << "\n";
2901       stream << indent_str;
2902       stream << "               unsigned int *prev_given, const char *val,";
2903       stream << "\n";
2904       stream << indent_str;
2905       stream << "               const char *possible_values[], const char *default_value,";
2906       stream << "\n";
2907       stream << indent_str;
2908       indent = 15;
2909       stream << "               ";
2910       generate_string (parser_name, stream, indent + indent_str.length ());
2911       stream << "_arg_type arg_type,";
2912       indent = 0;
2913       stream << "\n";
2914       stream << indent_str;
2915       stream << "               const char *long_opt, char short_opt,";
2916       stream << "\n";
2917       stream << indent_str;
2918       stream << "               const char *additional_error)";
2919       stream << "\n";
2920       stream << indent_str;
2921       stream << "{";
2922       stream << "\n";
2923       stream << indent_str;
2924       stream << "  /* store single arguments */";
2925       stream << "\n";
2926       stream << indent_str;
2927       stream << "  char *multi_token;";
2928       stream << "\n";
2929       stream << indent_str;
2930       stream << "  const char *multi_next;";
2931       stream << "\n";
2932       stream << indent_str;
2933       stream << "\n";
2934       stream << indent_str;
2935       stream << "  if (arg_type == ARG_NO) {";
2936       stream << "\n";
2937       stream << indent_str;
2938       stream << "    (*prev_given)++;";
2939       stream << "\n";
2940       stream << indent_str;
2941       stream << "    return 0; /* OK */";
2942       stream << "\n";
2943       stream << indent_str;
2944       stream << "  }";
2945       stream << "\n";
2946       stream << indent_str;
2947       stream << "\n";
2948       stream << indent_str;
2949       stream << "  multi_token = get_multiple_arg_token(val);";
2950       stream << "\n";
2951       stream << indent_str;
2952       stream << "  multi_next = get_multiple_arg_token_next (val);";
2953       stream << "\n";
2954       stream << indent_str;
2955       stream << "\n";
2956       stream << indent_str;
2957       stream << "  while (1)";
2958       stream << "\n";
2959       stream << indent_str;
2960       stream << "    {";
2961       stream << "\n";
2962       stream << indent_str;
2963       stream << "      add_node (list);";
2964       stream << "\n";
2965       stream << indent_str;
2966       stream << "      if (update_arg((void *)&((*list)->arg), &((*list)->orig), 0,";
2967       stream << "\n";
2968       stream << indent_str;
2969       stream << "          prev_given, multi_token, possible_values, default_value, ";
2970       stream << "\n";
2971       stream << indent_str;
2972       stream << "          arg_type, 0, 1, 1, 1, long_opt, short_opt, additional_error)) {";
2973       stream << "\n";
2974       stream << indent_str;
2975       stream << "        if (multi_token) free(multi_token);";
2976       stream << "\n";
2977       stream << indent_str;
2978       stream << "        return 1; /* failure */";
2979       stream << "\n";
2980       stream << indent_str;
2981       stream << "      }";
2982       stream << "\n";
2983       stream << indent_str;
2984       stream << "\n";
2985       stream << indent_str;
2986       stream << "      if (multi_next)";
2987       stream << "\n";
2988       stream << indent_str;
2989       stream << "        {";
2990       stream << "\n";
2991       stream << indent_str;
2992       stream << "          multi_token = get_multiple_arg_token(multi_next);";
2993       stream << "\n";
2994       stream << indent_str;
2995       stream << "          multi_next = get_multiple_arg_token_next (multi_next);";
2996       stream << "\n";
2997       stream << indent_str;
2998       stream << "        }";
2999       stream << "\n";
3000       stream << indent_str;
3001       stream << "      else";
3002       stream << "\n";
3003       stream << indent_str;
3004       stream << "        break;";
3005       stream << "\n";
3006       stream << indent_str;
3007       stream << "    }";
3008       stream << "\n";
3009       stream << indent_str;
3010       stream << "\n";
3011       stream << indent_str;
3012       stream << "  return 0; /* OK */";
3013       stream << "\n";
3014       stream << indent_str;
3015       stream << "}";
3016       stream << "\n";
3017       stream << indent_str;
3018       stream << "\n";
3019       stream << indent_str;
3020       stream << "/**";
3021       stream << "\n";
3022       stream << indent_str;
3023       stream << " * ";
3024       stream << "@";
3025       stream << "brief free the passed list (including possible string argument)";
3026       stream << "\n";
3027       stream << indent_str;
3028       stream << " */";
3029       stream << "\n";
3030       stream << indent_str;
3031       stream << "static";
3032       stream << "\n";
3033       stream << indent_str;
3034       stream << "void free_list(struct generic_list *list, short string_arg)";
3035       stream << "\n";
3036       stream << indent_str;
3037       stream << "{";
3038       stream << "\n";
3039       stream << indent_str;
3040       stream << "  if (list) {";
3041       stream << "\n";
3042       stream << indent_str;
3043       stream << "    struct generic_list *tmp;";
3044       stream << "\n";
3045       stream << indent_str;
3046       stream << "    while (list)";
3047       stream << "\n";
3048       stream << indent_str;
3049       stream << "      {";
3050       stream << "\n";
3051       stream << indent_str;
3052       stream << "        tmp = list;";
3053       stream << "\n";
3054       stream << indent_str;
3055       stream << "        if (string_arg && list->arg.string_arg)";
3056       stream << "\n";
3057       stream << indent_str;
3058       stream << "          free (list->arg.string_arg);";
3059       stream << "\n";
3060       stream << indent_str;
3061       stream << "        if (list->orig)";
3062       stream << "\n";
3063       stream << indent_str;
3064       stream << "          free (list->orig);";
3065       stream << "\n";
3066       stream << indent_str;
3067       stream << "        list = list->next;";
3068       stream << "\n";
3069       stream << indent_str;
3070       stream << "        free (tmp);";
3071       stream << "\n";
3072       stream << indent_str;
3073       stream << "      }";
3074       stream << "\n";
3075       stream << indent_str;
3076       stream << "  }";
3077       stream << "\n";
3078       stream << indent_str;
3079       stream << "}";
3080       stream << "\n";
3081       stream << indent_str;
3082       stream << "\n";
3083       stream << indent_str;
3084       stream << "/**";
3085       stream << "\n";
3086       stream << indent_str;
3087       stream << " * ";
3088       stream << "@";
3089       stream << "brief updates a multiple option starting from the passed list";
3090       stream << "\n";
3091       stream << indent_str;
3092       stream << " */";
3093       stream << "\n";
3094       stream << indent_str;
3095       stream << "static";
3096       stream << "\n";
3097       stream << indent_str;
3098       stream << "void update_multiple_arg(void *field, char ***orig_field,";
3099       stream << "\n";
3100       stream << indent_str;
3101       stream << "               unsigned int field_given, unsigned int prev_given, union generic_value *default_value,";
3102       stream << "\n";
3103       stream << indent_str;
3104       indent = 15;
3105       stream << "               ";
3106       generate_string (parser_name, stream, indent + indent_str.length ());
3107       stream << "_arg_type arg_type,";
3108       indent = 0;
3109       stream << "\n";
3110       stream << indent_str;
3111       stream << "               struct generic_list *list)";
3112       stream << "\n";
3113       stream << indent_str;
3114       stream << "{";
3115       stream << "\n";
3116       stream << indent_str;
3117       stream << "  int i;";
3118       stream << "\n";
3119       stream << indent_str;
3120       stream << "  struct generic_list *tmp;";
3121       stream << "\n";
3122       stream << indent_str;
3123       stream << "\n";
3124       stream << indent_str;
3125       stream << "  if (prev_given && list) {";
3126       stream << "\n";
3127       stream << indent_str;
3128       stream << "    *orig_field = (char **) realloc (*orig_field, (field_given + prev_given) * sizeof (char *));";
3129       stream << "\n";
3130       stream << indent_str;
3131       stream << "\n";
3132       stream << indent_str;
3133       stream << "    switch(arg_type) {";
3134       stream << "\n";
3135       stream << indent_str;
3136       if (( has_arg_int || has_arg_enum ))
3137         {
3138           if (has_arg_int)
3139             {
3140               stream << "    case ARG_INT:";
3141               stream << "\n";
3142               stream << indent_str;
3143             }
3144           if (has_arg_enum)
3145             {
3146               stream << "    case ARG_ENUM:";
3147               stream << "\n";
3148               stream << indent_str;
3149             }
3150           stream << "      *((int **)field) = (int *)realloc (*((int **)field), (field_given + prev_given) * sizeof (int)); break;";
3151           stream << "\n";
3152           stream << indent_str;
3153         }
3154       if (has_arg_short)
3155         {
3156           stream << "    case ARG_SHORT:";
3157           stream << "\n";
3158           stream << indent_str;
3159           stream << "      *((short **)field) = (short *)realloc (*((short **)field), (field_given + prev_given) * sizeof (short)); break;";
3160           stream << "\n";
3161           stream << indent_str;
3162         }
3163       if (has_arg_long)
3164         {
3165           stream << "    case ARG_LONG:";
3166           stream << "\n";
3167           stream << indent_str;
3168           stream << "      *((long **)field) = (long *)realloc (*((long **)field), (field_given + prev_given) * sizeof (long)); break;";
3169           stream << "\n";
3170           stream << indent_str;
3171         }
3172       if (has_arg_float)
3173         {
3174           stream << "    case ARG_FLOAT:";
3175           stream << "\n";
3176           stream << indent_str;
3177           stream << "      *((float **)field) = (float *)realloc (*((float **)field), (field_given + prev_given) * sizeof (float)); break;";
3178           stream << "\n";
3179           stream << indent_str;
3180         }
3181       if (has_arg_double)
3182         {
3183           stream << "    case ARG_DOUBLE:";
3184           stream << "\n";
3185           stream << indent_str;
3186           stream << "      *((double **)field) = (double *)realloc (*((double **)field), (field_given + prev_given) * sizeof (double)); break;";
3187           stream << "\n";
3188           stream << indent_str;
3189         }
3190       if (has_arg_longdouble)
3191         {
3192           stream << "    case ARG_LONGDOUBLE:";
3193           stream << "\n";
3194           stream << indent_str;
3195           stream << "      *((long double **)field) = (long double *)realloc (*((long double **)field), (field_given + prev_given) * sizeof (long double)); break;";
3196           stream << "\n";
3197           stream << indent_str;
3198         }
3199       if (has_arg_longlong)
3200         {
3201           stream << "    case ARG_LONGLONG:";
3202           stream << "\n";
3203           stream << indent_str;
3204           stream << "#if defined(HAVE_LONG_LONG) || defined(HAVE_LONG_LONG_INT)";
3205           stream << "\n";
3206           stream << indent_str;
3207           stream << "      *((long long int **)field) = (long long int *)realloc (*((long long int **)field), (field_given + prev_given) * sizeof (long long int)); break;";
3208           stream << "\n";
3209           stream << indent_str;
3210           stream << "#else";
3211           stream << "\n";
3212           stream << indent_str;
3213           stream << "      *((long **)field) = (long *)realloc (*((long **)field), (field_given + prev_given) * sizeof (long)); break;";
3214           stream << "\n";
3215           stream << indent_str;
3216           stream << "#endif";
3217           stream << "\n";
3218           stream << indent_str;
3219         }
3220       if (has_arg_string)
3221         {
3222           stream << "    case ARG_STRING:";
3223           stream << "\n";
3224           stream << indent_str;
3225           stream << "      *((char ***)field) = (char **)realloc (*((char ***)field), (field_given + prev_given) * sizeof (char *)); break;";
3226           stream << "\n";
3227           stream << indent_str;
3228         }
3229       stream << "    default:";
3230       stream << "\n";
3231       stream << indent_str;
3232       stream << "      break;";
3233       stream << "\n";
3234       stream << indent_str;
3235       stream << "    };";
3236       stream << "\n";
3237       stream << indent_str;
3238       indent = 4;
3239       stream << "    ";
3240       indent = 0;
3241       stream << "\n";
3242       stream << indent_str;
3243       stream << "    for (i = (prev_given - 1); i >= 0; --i)";
3244       stream << "\n";
3245       stream << indent_str;
3246       stream << "      {";
3247       stream << "\n";
3248       stream << indent_str;
3249       stream << "        tmp = list;";
3250       stream << "\n";
3251       stream << indent_str;
3252       indent = 8;
3253       stream << "        ";
3254       indent = 0;
3255       stream << "\n";
3256       stream << indent_str;
3257       stream << "        switch(arg_type) {";
3258       stream << "\n";
3259       stream << indent_str;
3260       if (has_arg_int)
3261         {
3262           stream << "        case ARG_INT:";
3263           stream << "\n";
3264           stream << indent_str;
3265           stream << "          (*((int **)field))[i + field_given] = tmp->arg.int_arg; break;";
3266           stream << "\n";
3267           stream << indent_str;
3268         }
3269       if (has_arg_short)
3270         {
3271           stream << "        case ARG_SHORT:";
3272           stream << "\n";
3273           stream << indent_str;
3274           stream << "          (*((short **)field))[i + field_given] = tmp->arg.short_arg; break;";
3275           stream << "\n";
3276           stream << indent_str;
3277         }
3278       if (has_arg_long)
3279         {
3280           stream << "        case ARG_LONG:";
3281           stream << "\n";
3282           stream << indent_str;
3283           stream << "          (*((long **)field))[i + field_given] = tmp->arg.long_arg; break;";
3284           stream << "\n";
3285           stream << indent_str;
3286         }
3287       if (has_arg_float)
3288         {
3289           stream << "        case ARG_FLOAT:";
3290           stream << "\n";
3291           stream << indent_str;
3292           stream << "          (*((float **)field))[i + field_given] = tmp->arg.float_arg; break;";
3293           stream << "\n";
3294           stream << indent_str;
3295         }
3296       if (has_arg_double)
3297         {
3298           stream << "        case ARG_DOUBLE:";
3299           stream << "\n";
3300           stream << indent_str;
3301           stream << "          (*((double **)field))[i + field_given] = tmp->arg.double_arg; break;";
3302           stream << "\n";
3303           stream << indent_str;
3304         }
3305       if (has_arg_longdouble)
3306         {
3307           stream << "        case ARG_LONGDOUBLE:";
3308           stream << "\n";
3309           stream << indent_str;
3310           stream << "          (*((long double **)field))[i + field_given] = tmp->arg.longdouble_arg; break;";
3311           stream << "\n";
3312           stream << indent_str;
3313         }
3314       if (has_arg_longlong)
3315         {
3316           stream << "        case ARG_LONGLONG:";
3317           stream << "\n";
3318           stream << indent_str;
3319           stream << "#if defined(HAVE_LONG_LONG) || defined(HAVE_LONG_LONG_INT)";
3320           stream << "\n";
3321           stream << indent_str;
3322           stream << "          (*((long long int **)field))[i + field_given] = tmp->arg.longlong_arg; break;";
3323           stream << "\n";
3324           stream << indent_str;
3325           stream << "#else";
3326           stream << "\n";
3327           stream << indent_str;
3328           stream << "          (*((long **)field))[i + field_given] = tmp->arg.longlong_arg; break;";
3329           stream << "\n";
3330           stream << indent_str;
3331           stream << "#endif";
3332           stream << "\n";
3333           stream << indent_str;
3334         }
3335       if (has_arg_enum)
3336         {
3337           stream << "        case ARG_ENUM:";
3338           stream << "\n";
3339           stream << indent_str;
3340           stream << "          (*((int **)field))[i + field_given] = tmp->arg.int_arg; break;";
3341           stream << "\n";
3342           stream << indent_str;
3343         }
3344       if (has_arg_string)
3345         {
3346           stream << "        case ARG_STRING:";
3347           stream << "\n";
3348           stream << indent_str;
3349           stream << "          (*((char ***)field))[i + field_given] = tmp->arg.string_arg; break;";
3350           stream << "\n";
3351           stream << indent_str;
3352         }
3353       stream << "        default:";
3354       stream << "\n";
3355       stream << indent_str;
3356       stream << "          break;";
3357       stream << "\n";
3358       stream << indent_str;
3359       stream << "        }        ";
3360       stream << "\n";
3361       stream << indent_str;
3362       stream << "        (*orig_field) [i + field_given] = list->orig;";
3363       stream << "\n";
3364       stream << indent_str;
3365       stream << "        list = list->next;";
3366       stream << "\n";
3367       stream << indent_str;
3368       stream << "        free (tmp);";
3369       stream << "\n";
3370       stream << indent_str;
3371       stream << "      }";
3372       stream << "\n";
3373       stream << indent_str;
3374       stream << "  } else { /* set the default value */";
3375       stream << "\n";
3376       stream << indent_str;
3377       stream << "    if (default_value && ! field_given) {";
3378       stream << "\n";
3379       stream << indent_str;
3380       stream << "      switch(arg_type) {";
3381       stream << "\n";
3382       stream << indent_str;
3383       if (( has_arg_int || has_arg_enum ))
3384         {
3385           if (has_arg_int)
3386             {
3387               stream << "      case ARG_INT:";
3388               stream << "\n";
3389               stream << indent_str;
3390             }
3391           if (has_arg_enum)
3392             {
3393               stream << "      case ARG_ENUM:";
3394               stream << "\n";
3395               stream << indent_str;
3396             }
3397           stream << "        if (! *((int **)field)) {";
3398           stream << "\n";
3399           stream << indent_str;
3400           stream << "          *((int **)field) = (int *)malloc (sizeof (int));";
3401           stream << "\n";
3402           stream << indent_str;
3403           stream << "          (*((int **)field))[0] = default_value->int_arg; ";
3404           stream << "\n";
3405           stream << indent_str;
3406           stream << "        }";
3407           stream << "\n";
3408           stream << indent_str;
3409           stream << "        break;";
3410           stream << "\n";
3411           stream << indent_str;
3412         }
3413       if (has_arg_short)
3414         {
3415           stream << "      case ARG_SHORT:";
3416           stream << "\n";
3417           stream << indent_str;
3418           stream << "        if (! *((short **)field)) {";
3419           stream << "\n";
3420           stream << indent_str;
3421           stream << "          *((short **)field) = (short *)malloc (sizeof (short));";
3422           stream << "\n";
3423           stream << indent_str;
3424           stream << "          (*((short **)field))[0] = default_value->short_arg;";
3425           stream << "\n";
3426           stream << indent_str;
3427           stream << "        }";
3428           stream << "\n";
3429           stream << indent_str;
3430           stream << "        break;";
3431           stream << "\n";
3432           stream << indent_str;
3433         }
3434       if (has_arg_long)
3435         {
3436           stream << "      case ARG_LONG:";
3437           stream << "\n";
3438           stream << indent_str;
3439           stream << "        if (! *((long **)field)) {";
3440           stream << "\n";
3441           stream << indent_str;
3442           stream << "          *((long **)field) = (long *)malloc (sizeof (long));";
3443           stream << "\n";
3444           stream << indent_str;
3445           stream << "          (*((long **)field))[0] = default_value->long_arg;";
3446           stream << "\n";
3447           stream << indent_str;
3448           stream << "        }";
3449           stream << "\n";
3450           stream << indent_str;
3451           stream << "        break;";
3452           stream << "\n";
3453           stream << indent_str;
3454         }
3455       if (has_arg_float)
3456         {
3457           stream << "      case ARG_FLOAT:";
3458           stream << "\n";
3459           stream << indent_str;
3460           stream << "        if (! *((float **)field)) {";
3461           stream << "\n";
3462           stream << indent_str;
3463           stream << "          *((float **)field) = (float *)malloc (sizeof (float));";
3464           stream << "\n";
3465           stream << indent_str;
3466           stream << "          (*((float **)field))[0] = default_value->float_arg;";
3467           stream << "\n";
3468           stream << indent_str;
3469           stream << "        }";
3470           stream << "\n";
3471           stream << indent_str;
3472           stream << "        break;";
3473           stream << "\n";
3474           stream << indent_str;
3475         }
3476       if (has_arg_double)
3477         {
3478           stream << "      case ARG_DOUBLE:";
3479           stream << "\n";
3480           stream << indent_str;
3481           stream << "        if (! *((double **)field)) {";
3482           stream << "\n";
3483           stream << indent_str;
3484           stream << "          *((double **)field) = (double *)malloc (sizeof (double));";
3485           stream << "\n";
3486           stream << indent_str;
3487           stream << "          (*((double **)field))[0] = default_value->double_arg;";
3488           stream << "\n";
3489           stream << indent_str;
3490           stream << "        }";
3491           stream << "\n";
3492           stream << indent_str;
3493           stream << "        break;";
3494           stream << "\n";
3495           stream << indent_str;
3496         }
3497       if (has_arg_longdouble)
3498         {
3499           stream << "      case ARG_LONGDOUBLE:";
3500           stream << "\n";
3501           stream << indent_str;
3502           stream << "        if (! *((long double **)field)) {";
3503           stream << "\n";
3504           stream << indent_str;
3505           stream << "          *((long double **)field) = (long double *)malloc (sizeof (long double));";
3506           stream << "\n";
3507           stream << indent_str;
3508           stream << "          (*((long double **)field))[0] = default_value->longdouble_arg;";
3509           stream << "\n";
3510           stream << indent_str;
3511           stream << "        }";
3512           stream << "\n";
3513           stream << indent_str;
3514           stream << "        break;";
3515           stream << "\n";
3516           stream << indent_str;
3517         }
3518       if (has_arg_longlong)
3519         {
3520           stream << "      case ARG_LONGLONG:";
3521           stream << "\n";
3522           stream << indent_str;
3523           stream << "#if defined(HAVE_LONG_LONG) || defined(HAVE_LONG_LONG_INT)";
3524           stream << "\n";
3525           stream << indent_str;
3526           stream << "        if (! *((long long int **)field)) {";
3527           stream << "\n";
3528           stream << indent_str;
3529           stream << "          *((long long int **)field) = (long long int *)malloc (sizeof (long long int));";
3530           stream << "\n";
3531           stream << indent_str;
3532           stream << "          (*((long long int **)field))[0] = default_value->longlong_arg;";
3533           stream << "\n";
3534           stream << indent_str;
3535           stream << "        }";
3536           stream << "\n";
3537           stream << indent_str;
3538           stream << "#else";
3539           stream << "\n";
3540           stream << indent_str;
3541           stream << "        if (! *((long **)field)) {";
3542           stream << "\n";
3543           stream << indent_str;
3544           stream << "          *((long **)field) = (long *)malloc (sizeof (long));";
3545           stream << "\n";
3546           stream << indent_str;
3547           stream << "          (*((long **)field))[0] = default_value->longlong_arg;";
3548           stream << "\n";
3549           stream << indent_str;
3550           stream << "        }";
3551           stream << "\n";
3552           stream << indent_str;
3553           stream << "#endif";
3554           stream << "\n";
3555           stream << indent_str;
3556           stream << "        break;";
3557           stream << "\n";
3558           stream << indent_str;
3559         }
3560       if (has_arg_string)
3561         {
3562           stream << "      case ARG_STRING:";
3563           stream << "\n";
3564           stream << indent_str;
3565           stream << "        if (! *((char ***)field)) {";
3566           stream << "\n";
3567           stream << indent_str;
3568           stream << "          *((char ***)field) = (char **)malloc (sizeof (char *));";
3569           stream << "\n";
3570           stream << indent_str;
3571           stream << "          (*((char ***)field))[0] = gengetopt_strdup(default_value->string_arg);";
3572           stream << "\n";
3573           stream << indent_str;
3574           stream << "        }";
3575           stream << "\n";
3576           stream << indent_str;
3577           stream << "        break;";
3578           stream << "\n";
3579           stream << indent_str;
3580         }
3581       stream << "      default: break;";
3582       stream << "\n";
3583       stream << indent_str;
3584       stream << "      }";
3585       stream << "\n";
3586       stream << indent_str;
3587       stream << "      if (!(*orig_field)) {";
3588       stream << "\n";
3589       stream << indent_str;
3590       stream << "        *orig_field = (char **) malloc (sizeof (char *));";
3591       stream << "\n";
3592       stream << indent_str;
3593       stream << "        (*orig_field)[0] = 0;";
3594       stream << "\n";
3595       stream << indent_str;
3596       stream << "      }";
3597       stream << "\n";
3598       stream << indent_str;
3599       stream << "    }";
3600       stream << "\n";
3601       stream << indent_str;
3602       stream << "  }";
3603       stream << "\n";
3604       stream << indent_str;
3605       stream << "}";
3606       stream << "\n";
3607       stream << indent_str;
3608     }
3609   if (has_modes)
3610     {
3611       stream << "\n";
3612       stream << indent_str;
3613       stream << "static int check_modes(";
3614       stream << "\n";
3615       stream << indent_str;
3616       stream << "  int given1[], const char *options1[],";
3617       stream << "\n";
3618       stream << indent_str;
3619       stream << "                       int given2[], const char *options2[])";
3620       stream << "\n";
3621       stream << indent_str;
3622       stream << "{";
3623       stream << "\n";
3624       stream << indent_str;
3625       stream << "  int i = 0, j = 0, errors = 0;";
3626       stream << "\n";
3627       stream << indent_str;
3628       indent = 2;
3629       stream << "  ";
3630       indent = 0;
3631       stream << "\n";
3632       stream << indent_str;
3633       stream << "  while (given1[i] >= 0) {";
3634       stream << "\n";
3635       stream << indent_str;
3636       stream << "    if (given1[i]) {";
3637       stream << "\n";
3638       stream << indent_str;
3639       stream << "      while (given2[j] >= 0) {";
3640       stream << "\n";
3641       stream << indent_str;
3642       stream << "        if (given2[j]) {";
3643       stream << "\n";
3644       stream << indent_str;
3645       stream << "          ++errors;";
3646       stream << "\n";
3647       stream << indent_str;
3648       stream << "          fprintf(stderr, \"%s: option %s conflicts with option %s\\n\",";
3649       stream << "\n";
3650       stream << indent_str;
3651       stream << "                  package_name, options1[i], options2[j]);";
3652       stream << "\n";
3653       stream << indent_str;
3654       stream << "        }";
3655       stream << "\n";
3656       stream << indent_str;
3657       stream << "        ++j;";
3658       stream << "\n";
3659       stream << indent_str;
3660       stream << "      }";
3661       stream << "\n";
3662       stream << indent_str;
3663       stream << "    }";
3664       stream << "\n";
3665       stream << indent_str;
3666       stream << "    ++i;";
3667       stream << "\n";
3668       stream << indent_str;
3669       stream << "  }";
3670       stream << "\n";
3671       stream << indent_str;
3672       indent = 2;
3673       stream << "  ";
3674       indent = 0;
3675       stream << "\n";
3676       stream << indent_str;
3677       stream << "  return errors;";
3678       stream << "\n";
3679       stream << indent_str;
3680       stream << "}";
3681       stream << "\n";
3682       stream << indent_str;
3683     }
3684   stream << "\n";
3685   stream << indent_str;
3686   stream << "int";
3687   stream << "\n";
3688   stream << indent_str;
3689   generate_string (parser_name, stream, indent + indent_str.length ());
3690   stream << "_internal (";
3691   stream << "\n";
3692   stream << indent_str;
3693   stream << "  int argc, char **argv, struct ";
3694   generate_string (args_info, stream, indent + indent_str.length ());
3695   stream << " *args_info,";
3696   stream << "\n";
3697   stream << indent_str;
3698   stream << "                        struct ";
3699   generate_string (parser_name, stream, indent + indent_str.length ());
3700   stream << "_params *params, const char *additional_error)";
3701   stream << "\n";
3702   stream << indent_str;
3703   stream << "{";
3704   stream << "\n";
3705   stream << indent_str;
3706   stream << "  int c;	/* Character of the parsed option.  */";
3707   stream << "\n";
3708   stream << indent_str;
3709   if (multiple_options_with_default)
3710     {
3711       stream << "  union generic_value multiple_default_value;";
3712       stream << "\n";
3713       stream << indent_str;
3714     }
3715   stream << "\n";
3716   stream << indent_str;
3717   indent = 2;
3718   if (list_def.size () > 0)
3719     generate_string (list_def, stream, indent + indent_str.length ());
3720   else
3721     generate_list_def (stream, indent + indent_str.length ());
3722   indent = 0;
3723   stream << indent_str;
3724   stream << "  int error_occurred = 0;";
3725   stream << "\n";
3726   stream << indent_str;
3727   stream << "  struct ";
3728   generate_string (args_info, stream, indent + indent_str.length ());
3729   stream << " local_args_info;";
3730   stream << "\n";
3731   stream << indent_str;
3732   indent = 2;
3733   stream << "  ";
3734   indent = 0;
3735   stream << "\n";
3736   stream << indent_str;
3737   stream << "  int override;";
3738   stream << "\n";
3739   stream << indent_str;
3740   stream << "  int initialize;";
3741   stream << "\n";
3742   stream << indent_str;
3743   stream << "  int check_required;";
3744   stream << "\n";
3745   stream << indent_str;
3746   stream << "  int check_ambiguity;";
3747   stream << "\n";
3748   stream << indent_str;
3749   if (include_getopt)
3750     {
3751       stream << "\n";
3752       stream << indent_str;
3753       stream << "  char *optarg;";
3754       stream << "\n";
3755       stream << indent_str;
3756       stream << "  int optind;";
3757       stream << "\n";
3758       stream << indent_str;
3759       stream << "  int opterr;";
3760       stream << "\n";
3761       stream << indent_str;
3762       stream << "  int optopt;";
3763       stream << "\n";
3764       stream << indent_str;
3765     }
3766   stream << "  ";
3767   stream << "\n";
3768   stream << indent_str;
3769   stream << "  package_name = argv[0];";
3770   stream << "\n";
3771   stream << indent_str;
3772   indent = 2;
3773   stream << "  ";
3774   indent = 0;
3775   stream << "\n";
3776   stream << indent_str;
3777   stream << "  /* TODO: Why is this here? It is not used anywhere. */";
3778   stream << "\n";
3779   stream << indent_str;
3780   stream << "  override = params->override;";
3781   stream << "\n";
3782   stream << indent_str;
3783   stream << "  FIX_UNUSED(override);";
3784   stream << "\n";
3785   stream << indent_str;
3786   stream << "\n";
3787   stream << indent_str;
3788   stream << "  initialize = params->initialize;";
3789   stream << "\n";
3790   stream << indent_str;
3791   stream << "  check_required = params->check_required;";
3792   stream << "\n";
3793   stream << indent_str;
3794   stream << "\n";
3795   stream << indent_str;
3796   stream << "  /* TODO: Why is this here? It is not used anywhere. */";
3797   stream << "\n";
3798   stream << indent_str;
3799   stream << "  check_ambiguity = params->check_ambiguity;";
3800   stream << "\n";
3801   stream << indent_str;
3802   stream << "  FIX_UNUSED(check_ambiguity);";
3803   stream << "\n";
3804   stream << indent_str;
3805   stream << "\n";
3806   stream << indent_str;
3807   stream << "  if (initialize)";
3808   stream << "\n";
3809   stream << indent_str;
3810   indent = 4;
3811   stream << "    ";
3812   generate_string (parser_name, stream, indent + indent_str.length ());
3813   stream << "_init (args_info);";
3814   indent = 0;
3815   stream << "\n";
3816   stream << indent_str;
3817   stream << "\n";
3818   stream << indent_str;
3819   indent = 2;
3820   stream << "  ";
3821   generate_string (parser_name, stream, indent + indent_str.length ());
3822   stream << "_init (&local_args_info);";
3823   indent = 0;
3824   stream << "\n";
3825   stream << indent_str;
3826   stream << "\n";
3827   stream << indent_str;
3828   stream << "  optarg = 0;";
3829   stream << "\n";
3830   stream << indent_str;
3831   stream << "  optind = 0;";
3832   stream << "\n";
3833   stream << indent_str;
3834   stream << "  opterr = params->print_errors;";
3835   stream << "\n";
3836   stream << indent_str;
3837   stream << "  optopt = '?';";
3838   stream << "\n";
3839   stream << indent_str;
3840   stream << "\n";
3841   stream << indent_str;
3842   stream << "  while (1)";
3843   stream << "\n";
3844   stream << indent_str;
3845   stream << "    {";
3846   stream << "\n";
3847   stream << indent_str;
3848   stream << "      int option_index = 0;";
3849   stream << "\n";
3850   stream << indent_str;
3851   stream << "\n";
3852   stream << indent_str;
3853   stream << "      static struct option long_options[] = {";
3854   stream << "\n";
3855   stream << indent_str;
3856   indent = 8;
3857   if (long_option_struct.size () > 0)
3858     generate_string (long_option_struct, stream, indent + indent_str.length ());
3859   else
3860     generate_long_option_struct (stream, indent + indent_str.length ());
3861   indent = 0;
3862   stream << indent_str;
3863   stream << "        { 0,  0, 0, 0 }";
3864   stream << "\n";
3865   stream << indent_str;
3866   stream << "      };";
3867   stream << "\n";
3868   stream << indent_str;
3869   stream << "\n";
3870   stream << indent_str;
3871   if (include_getopt)
3872     {
3873       stream << "      custom_optarg = optarg;";
3874       stream << "\n";
3875       stream << indent_str;
3876       stream << "      custom_optind = optind;";
3877       stream << "\n";
3878       stream << indent_str;
3879       stream << "      custom_opterr = opterr;";
3880       stream << "\n";
3881       stream << indent_str;
3882       stream << "      custom_optopt = optopt;";
3883       stream << "\n";
3884       stream << indent_str;
3885       stream << "\n";
3886       stream << indent_str;
3887       stream << "      c = custom_getopt_long (argc, argv, \"";
3888       generate_string (getopt_string, stream, indent + indent_str.length ());
3889       stream << "\", long_options, &option_index);";
3890       stream << "\n";
3891       stream << indent_str;
3892       stream << "\n";
3893       stream << indent_str;
3894       stream << "      optarg = custom_optarg;";
3895       stream << "\n";
3896       stream << indent_str;
3897       stream << "      optind = custom_optind;";
3898       stream << "\n";
3899       stream << indent_str;
3900       stream << "      opterr = custom_opterr;";
3901       stream << "\n";
3902       stream << indent_str;
3903       stream << "      optopt = custom_optopt;";
3904       stream << "\n";
3905       stream << indent_str;
3906     }
3907   else
3908     {
3909       stream << "      c = getopt_long (argc, argv, \"";
3910       generate_string (getopt_string, stream, indent + indent_str.length ());
3911       stream << "\", long_options, &option_index);";
3912       stream << "\n";
3913       stream << indent_str;
3914     }
3915   stream << "\n";
3916   stream << indent_str;
3917   stream << "      if (c == -1) break;	/* Exit from `while (1)' loop.  */";
3918   stream << "\n";
3919   stream << indent_str;
3920   stream << "\n";
3921   stream << indent_str;
3922   stream << "      switch (c)";
3923   stream << "\n";
3924   stream << indent_str;
3925   stream << "        {";
3926   stream << "\n";
3927   stream << indent_str;
3928   indent = 8;
3929   if (handle_option.size () > 0)
3930     generate_string (handle_option, stream, indent + indent_str.length ());
3931   else
3932     generate_handle_option (stream, indent + indent_str.length ());
3933   indent = 0;
3934   stream << indent_str;
3935   stream << "\n";
3936   stream << indent_str;
3937   stream << "        case 0:	/* Long option with no short option */";
3938   stream << "\n";
3939   stream << indent_str;
3940   indent = 10;
3941   if (handle_no_short_option.size () > 0)
3942     generate_string (handle_no_short_option, stream, indent + indent_str.length ());
3943   else
3944     generate_handle_no_short_option (stream, indent + indent_str.length ());
3945   indent = 0;
3946   stream << indent_str;
3947   if (handle_question_mark)
3948     {
3949       stream << "        case '?':	/* Invalid option.  */";
3950       stream << "\n";
3951       stream << indent_str;
3952       stream << "          /* `getopt_long' already printed an error message.  */";
3953       stream << "\n";
3954       stream << indent_str;
3955       stream << "          goto failure;";
3956       stream << "\n";
3957       stream << indent_str;
3958     }
3959   stream << "\n";
3960   stream << indent_str;
3961   stream << "        default:	/* bug: option not considered.  */";
3962   stream << "\n";
3963   stream << indent_str;
3964   stream << "          fprintf (stderr, \"%s: option unknown: %c%s\\n\", ";
3965   generate_string (package_var_name, stream, indent + indent_str.length ());
3966   stream << ", c, (additional_error ? additional_error : \"\"));";
3967   stream << "\n";
3968   stream << indent_str;
3969   stream << "          abort ();";
3970   stream << "\n";
3971   stream << indent_str;
3972   stream << "        } /* switch */";
3973   stream << "\n";
3974   stream << indent_str;
3975   stream << "    } /* while */";
3976   stream << "\n";
3977   stream << indent_str;
3978   stream << "\n";
3979   stream << indent_str;
3980   indent = 2;
3981   if (handle_group.size () > 0)
3982     generate_string (handle_group, stream, indent + indent_str.length ());
3983   else
3984     generate_handle_group (stream, indent + indent_str.length ());
3985   indent = 0;
3986   stream << indent_str;
3987   stream << "\n";
3988   stream << indent_str;
3989   indent = 2;
3990   if (multiple_fill_array.size () > 0)
3991     generate_string (multiple_fill_array, stream, indent + indent_str.length ());
3992   else
3993     generate_multiple_fill_array (stream, indent + indent_str.length ());
3994   indent = 0;
3995   stream << indent_str;
3996   indent = 2;
3997   if (update_multiple_given.size () > 0)
3998     generate_string (update_multiple_given, stream, indent + indent_str.length ());
3999   else
4000     generate_update_multiple_given (stream, indent + indent_str.length ());
4001   indent = 0;
4002   stream << indent_str;
4003   indent = 2;
4004   if (check_modes.size () > 0)
4005     generate_string (check_modes, stream, indent + indent_str.length ());
4006   else
4007     generate_check_modes (stream, indent + indent_str.length ());
4008   indent = 0;
4009   stream << indent_str;
4010   stream << "\n";
4011   stream << indent_str;
4012   if (check_required_options)
4013     {
4014       stream << "  if (check_required)";
4015       stream << "\n";
4016       stream << indent_str;
4017       stream << "    {";
4018       stream << "\n";
4019       stream << indent_str;
4020       stream << "      error_occurred += ";
4021       generate_string (parser_name, stream, indent + indent_str.length ());
4022       stream << "_required2 (args_info, argv[0], additional_error);";
4023       stream << "\n";
4024       stream << indent_str;
4025       stream << "    }";
4026       stream << "\n";
4027       stream << indent_str;
4028     }
4029   else
4030     {
4031       stream << "	FIX_UNUSED(check_required);";
4032       stream << "\n";
4033       stream << indent_str;
4034     }
4035   stream << "\n";
4036   stream << indent_str;
4037   indent = 2;
4038   stream << "  ";
4039   generate_string (parser_name, stream, indent + indent_str.length ());
4040   stream << "_release (&local_args_info);";
4041   indent = 0;
4042   stream << "\n";
4043   stream << indent_str;
4044   stream << "\n";
4045   stream << indent_str;
4046   stream << "  if ( error_occurred )";
4047   stream << "\n";
4048   stream << indent_str;
4049   stream << "    return (EXIT_FAILURE);";
4050   stream << "\n";
4051   stream << indent_str;
4052   stream << "\n";
4053   stream << indent_str;
4054   if (handle_unnamed)
4055     {
4056       stream << "  if (optind < argc)";
4057       stream << "\n";
4058       stream << indent_str;
4059       stream << "    {";
4060       stream << "\n";
4061       stream << indent_str;
4062       stream << "      int i = 0 ;";
4063       stream << "\n";
4064       stream << indent_str;
4065       stream << "      int found_prog_name = 0;";
4066       stream << "\n";
4067       stream << indent_str;
4068       stream << "      /* whether program name, i.e., argv[0], is in the remaining args";
4069       stream << "\n";
4070       stream << indent_str;
4071       stream << "         (this may happen with some implementations of getopt,";
4072       stream << "\n";
4073       stream << indent_str;
4074       stream << "          but surely not with the one included by gengetopt) */";
4075       stream << "\n";
4076       stream << indent_str;
4077       stream << "\n";
4078       stream << indent_str;
4079       if (include_getopt)
4080         {
4081 
4082 
4083         }
4084       else
4085         {
4086           stream << "      i = optind;";
4087           stream << "\n";
4088           stream << indent_str;
4089           stream << "      while (i < argc)";
4090           stream << "\n";
4091           stream << indent_str;
4092           stream << "        if (argv[i++] == argv[0]) {";
4093           stream << "\n";
4094           stream << indent_str;
4095           stream << "          found_prog_name = 1;";
4096           stream << "\n";
4097           stream << indent_str;
4098           stream << "          break;";
4099           stream << "\n";
4100           stream << indent_str;
4101           stream << "        }";
4102           stream << "\n";
4103           stream << indent_str;
4104           stream << "      i = 0;";
4105           stream << "\n";
4106           stream << indent_str;
4107         }
4108       stream << "\n";
4109       stream << indent_str;
4110       stream << "      args_info->inputs_num = argc - optind - found_prog_name;";
4111       stream << "\n";
4112       stream << indent_str;
4113       stream << "      args_info->inputs =";
4114       stream << "\n";
4115       stream << indent_str;
4116       stream << "        (char **)(malloc ((args_info->inputs_num)*sizeof(char *))) ;";
4117       stream << "\n";
4118       stream << indent_str;
4119       stream << "      while (optind < argc)";
4120       stream << "\n";
4121       stream << indent_str;
4122       if (include_getopt)
4123         {
4124           stream << "        args_info->inputs[ i++ ] = gengetopt_strdup (argv[optind++]) ;";
4125           stream << "\n";
4126           stream << indent_str;
4127         }
4128       else
4129         {
4130           stream << "        if (argv[optind++] != argv[0])";
4131           stream << "\n";
4132           stream << indent_str;
4133           stream << "          args_info->inputs[ i++ ] = gengetopt_strdup (argv[optind-1]) ;";
4134           stream << "\n";
4135           stream << indent_str;
4136         }
4137       stream << "    }";
4138       stream << "\n";
4139       stream << indent_str;
4140       stream << "\n";
4141       stream << indent_str;
4142     }
4143   stream << "  return 0;";
4144   stream << "\n";
4145   stream << indent_str;
4146   stream << "\n";
4147   stream << indent_str;
4148   stream << "failure:";
4149   stream << "\n";
4150   stream << indent_str;
4151   indent = 2;
4152   stream << "  ";
4153   if (list_free.size () > 0)
4154     generate_string (list_free, stream, indent + indent_str.length ());
4155   else
4156     generate_list_free (stream, indent + indent_str.length ());
4157   indent = 0;
4158   stream << "\n";
4159   stream << indent_str;
4160   indent = 2;
4161   stream << "  ";
4162   generate_string (parser_name, stream, indent + indent_str.length ());
4163   stream << "_release (&local_args_info);";
4164   indent = 0;
4165   stream << "\n";
4166   stream << indent_str;
4167   stream << "  return (EXIT_FAILURE);";
4168   stream << "\n";
4169   stream << indent_str;
4170   stream << "}";
4171   stream << "\n";
4172   stream << indent_str;
4173   if (conf_parser)
4174     {
4175       stream << "\n";
4176       stream << indent_str;
4177       stream << "#ifndef CONFIG_FILE_LINE_SIZE";
4178       stream << "\n";
4179       stream << indent_str;
4180       stream << "#define CONFIG_FILE_LINE_SIZE 2048";
4181       stream << "\n";
4182       stream << indent_str;
4183       stream << "#endif";
4184       stream << "\n";
4185       stream << indent_str;
4186       stream << "#define ADDITIONAL_ERROR \" in configuration file \"";
4187       stream << "\n";
4188       stream << indent_str;
4189       stream << "\n";
4190       stream << indent_str;
4191       stream << "#define CONFIG_FILE_LINE_BUFFER_SIZE (CONFIG_FILE_LINE_SIZE+3)";
4192       stream << "\n";
4193       stream << indent_str;
4194       stream << "/* 3 is for \"--\" and \"=\" */";
4195       stream << "\n";
4196       stream << indent_str;
4197       stream << "\n";
4198       stream << indent_str;
4199       stream << "static int";
4200       stream << "\n";
4201       stream << indent_str;
4202       stream << "_";
4203       generate_string (parser_name, stream, indent + indent_str.length ());
4204       stream << "_configfile (const char *filename, int *my_argc)";
4205       stream << "\n";
4206       stream << indent_str;
4207       stream << "{";
4208       stream << "\n";
4209       stream << indent_str;
4210       stream << "  FILE* file;";
4211       stream << "\n";
4212       stream << indent_str;
4213       stream << "  char my_argv[CONFIG_FILE_LINE_BUFFER_SIZE+1];";
4214       stream << "\n";
4215       stream << indent_str;
4216       stream << "  char linebuf[CONFIG_FILE_LINE_SIZE];";
4217       stream << "\n";
4218       stream << indent_str;
4219       stream << "  int line_num = 0;";
4220       stream << "\n";
4221       stream << indent_str;
4222       stream << "  int result = 0, equal;";
4223       stream << "\n";
4224       stream << indent_str;
4225       stream << "  char *fopt, *farg;";
4226       stream << "\n";
4227       stream << indent_str;
4228       stream << "  char *str_index;";
4229       stream << "\n";
4230       stream << indent_str;
4231       stream << "  size_t len, next_token;";
4232       stream << "\n";
4233       stream << indent_str;
4234       stream << "  char delimiter;";
4235       stream << "\n";
4236       stream << indent_str;
4237       stream << "\n";
4238       stream << indent_str;
4239       stream << "  if ((file = fopen(filename, \"r\")) == 0)";
4240       stream << "\n";
4241       stream << indent_str;
4242       stream << "    {";
4243       stream << "\n";
4244       stream << indent_str;
4245       stream << "      fprintf (stderr, \"%s: Error opening configuration file '%s'\\n\",";
4246       stream << "\n";
4247       stream << indent_str;
4248       indent = 15;
4249       stream << "               ";
4250       generate_string (package_var_name, stream, indent + indent_str.length ());
4251       stream << ", filename);";
4252       indent = 0;
4253       stream << "\n";
4254       stream << indent_str;
4255       stream << "      return EXIT_FAILURE;";
4256       stream << "\n";
4257       stream << indent_str;
4258       stream << "    }";
4259       stream << "\n";
4260       stream << indent_str;
4261       stream << "\n";
4262       stream << indent_str;
4263       stream << "  while ((fgets(linebuf, CONFIG_FILE_LINE_SIZE, file)) != 0)";
4264       stream << "\n";
4265       stream << indent_str;
4266       stream << "    {";
4267       stream << "\n";
4268       stream << indent_str;
4269       stream << "      ++line_num;";
4270       stream << "\n";
4271       stream << indent_str;
4272       stream << "      my_argv[0] = '\\0';";
4273       stream << "\n";
4274       stream << indent_str;
4275       stream << "      len = strlen(linebuf);";
4276       stream << "\n";
4277       stream << indent_str;
4278       stream << "      if (len > (CONFIG_FILE_LINE_BUFFER_SIZE-1))";
4279       stream << "\n";
4280       stream << indent_str;
4281       stream << "        {";
4282       stream << "\n";
4283       stream << indent_str;
4284       stream << "          fprintf (stderr, \"%s:%s:%d: Line too long in configuration file\\n\",";
4285       stream << "\n";
4286       stream << indent_str;
4287       indent = 19;
4288       stream << "                   ";
4289       generate_string (package_var_name, stream, indent + indent_str.length ());
4290       stream << ", filename, line_num);";
4291       indent = 0;
4292       stream << "\n";
4293       stream << indent_str;
4294       stream << "          result = EXIT_FAILURE;";
4295       stream << "\n";
4296       stream << indent_str;
4297       stream << "          break;";
4298       stream << "\n";
4299       stream << indent_str;
4300       stream << "        }";
4301       stream << "\n";
4302       stream << indent_str;
4303       stream << "\n";
4304       stream << indent_str;
4305       stream << "      /* find first non-whitespace character in the line */";
4306       stream << "\n";
4307       stream << indent_str;
4308       stream << "      next_token = strspn (linebuf, \" \\t\\r\\n\");";
4309       stream << "\n";
4310       stream << indent_str;
4311       stream << "      str_index  = linebuf + next_token;";
4312       stream << "\n";
4313       stream << indent_str;
4314       stream << "\n";
4315       stream << indent_str;
4316       stream << "      if ( str_index[0] == '\\0' || str_index[0] == '#')";
4317       stream << "\n";
4318       stream << indent_str;
4319       stream << "        continue; /* empty line or comment line is skipped */";
4320       stream << "\n";
4321       stream << indent_str;
4322       stream << "\n";
4323       stream << indent_str;
4324       stream << "      fopt = str_index;";
4325       stream << "\n";
4326       stream << indent_str;
4327       stream << "\n";
4328       stream << indent_str;
4329       stream << "      /* truncate fopt at the end of the first non-valid character */";
4330       stream << "\n";
4331       stream << indent_str;
4332       stream << "      next_token = strcspn (fopt, \" \\t\\r\\n=\");";
4333       stream << "\n";
4334       stream << indent_str;
4335       stream << "\n";
4336       stream << indent_str;
4337       stream << "      if (fopt[next_token] == '\\0') /* the line is over */";
4338       stream << "\n";
4339       stream << indent_str;
4340       stream << "        {";
4341       stream << "\n";
4342       stream << indent_str;
4343       stream << "          farg  = 0;";
4344       stream << "\n";
4345       stream << indent_str;
4346       stream << "          equal = 0;";
4347       stream << "\n";
4348       stream << indent_str;
4349       stream << "          goto noarg;";
4350       stream << "\n";
4351       stream << indent_str;
4352       stream << "        }";
4353       stream << "\n";
4354       stream << indent_str;
4355       stream << "\n";
4356       stream << indent_str;
4357       stream << "      /* remember if equal sign is present */";
4358       stream << "\n";
4359       stream << indent_str;
4360       stream << "      equal = (fopt[next_token] == '=');";
4361       stream << "\n";
4362       stream << indent_str;
4363       stream << "      fopt[next_token++] = '\\0';";
4364       stream << "\n";
4365       stream << indent_str;
4366       stream << "\n";
4367       stream << indent_str;
4368       stream << "      /* advance pointers to the next token after the end of fopt */";
4369       stream << "\n";
4370       stream << indent_str;
4371       stream << "      next_token += strspn (fopt + next_token, \" \\t\\r\\n\");";
4372       stream << "\n";
4373       stream << indent_str;
4374       stream << "\n";
4375       stream << indent_str;
4376       stream << "      /* check for the presence of equal sign, and if so, skip it */";
4377       stream << "\n";
4378       stream << indent_str;
4379       stream << "      if ( !equal )";
4380       stream << "\n";
4381       stream << indent_str;
4382       stream << "        if ((equal = (fopt[next_token] == '=')))";
4383       stream << "\n";
4384       stream << indent_str;
4385       stream << "          {";
4386       stream << "\n";
4387       stream << indent_str;
4388       stream << "            next_token++;";
4389       stream << "\n";
4390       stream << indent_str;
4391       stream << "            next_token += strspn (fopt + next_token, \" \\t\\r\\n\");";
4392       stream << "\n";
4393       stream << indent_str;
4394       stream << "          }";
4395       stream << "\n";
4396       stream << indent_str;
4397       stream << "      str_index  += next_token;";
4398       stream << "\n";
4399       stream << indent_str;
4400       stream << "\n";
4401       stream << indent_str;
4402       stream << "      /* find argument */";
4403       stream << "\n";
4404       stream << indent_str;
4405       stream << "      farg = str_index;";
4406       stream << "\n";
4407       stream << indent_str;
4408       stream << "      if ( farg[0] == '\\\"' || farg[0] == '\\'' )";
4409       stream << "\n";
4410       stream << indent_str;
4411       stream << "        { /* quoted argument */";
4412       stream << "\n";
4413       stream << indent_str;
4414       stream << "          str_index = strchr (++farg, str_index[0] ); /* skip opening quote */";
4415       stream << "\n";
4416       stream << indent_str;
4417       stream << "          if (! str_index)";
4418       stream << "\n";
4419       stream << indent_str;
4420       stream << "            {";
4421       stream << "\n";
4422       stream << indent_str;
4423       stream << "              fprintf";
4424       stream << "\n";
4425       stream << indent_str;
4426       stream << "                (stderr,";
4427       stream << "\n";
4428       stream << indent_str;
4429       stream << "                 \"%s:%s:%d: unterminated string in configuration file\\n\",";
4430       stream << "\n";
4431       stream << indent_str;
4432       indent = 17;
4433       stream << "                 ";
4434       generate_string (package_var_name, stream, indent + indent_str.length ());
4435       stream << ", filename, line_num);";
4436       indent = 0;
4437       stream << "\n";
4438       stream << indent_str;
4439       stream << "              result = EXIT_FAILURE;";
4440       stream << "\n";
4441       stream << indent_str;
4442       stream << "              break;";
4443       stream << "\n";
4444       stream << indent_str;
4445       stream << "            }";
4446       stream << "\n";
4447       stream << indent_str;
4448       stream << "        }";
4449       stream << "\n";
4450       stream << indent_str;
4451       stream << "      else";
4452       stream << "\n";
4453       stream << indent_str;
4454       stream << "        { /* read up the remaining part up to a delimiter */";
4455       stream << "\n";
4456       stream << indent_str;
4457       stream << "          next_token = strcspn (farg, \" \\t\\r\\n#\\'\\\"\");";
4458       stream << "\n";
4459       stream << indent_str;
4460       stream << "          str_index += next_token;";
4461       stream << "\n";
4462       stream << indent_str;
4463       stream << "        }";
4464       stream << "\n";
4465       stream << indent_str;
4466       stream << "\n";
4467       stream << indent_str;
4468       stream << "      /* truncate farg at the delimiter and store it for further check */";
4469       stream << "\n";
4470       stream << indent_str;
4471       stream << "      delimiter = *str_index, *str_index++ = '\\0';";
4472       stream << "\n";
4473       stream << indent_str;
4474       stream << "\n";
4475       stream << indent_str;
4476       stream << "      /* everything but comment is illegal at the end of line */";
4477       stream << "\n";
4478       stream << indent_str;
4479       stream << "      if (delimiter != '\\0' && delimiter != '#')";
4480       stream << "\n";
4481       stream << indent_str;
4482       stream << "        {";
4483       stream << "\n";
4484       stream << indent_str;
4485       stream << "          str_index += strspn(str_index, \" \\t\\r\\n\");";
4486       stream << "\n";
4487       stream << indent_str;
4488       stream << "          if (*str_index != '\\0' && *str_index != '#')";
4489       stream << "\n";
4490       stream << indent_str;
4491       stream << "            {";
4492       stream << "\n";
4493       stream << indent_str;
4494       stream << "              fprintf";
4495       stream << "\n";
4496       stream << indent_str;
4497       stream << "                (stderr,";
4498       stream << "\n";
4499       stream << indent_str;
4500       stream << "                 \"%s:%s:%d: malformed string in configuration file\\n\",";
4501       stream << "\n";
4502       stream << indent_str;
4503       indent = 17;
4504       stream << "                 ";
4505       generate_string (package_var_name, stream, indent + indent_str.length ());
4506       stream << ", filename, line_num);";
4507       indent = 0;
4508       stream << "\n";
4509       stream << indent_str;
4510       stream << "              result = EXIT_FAILURE;";
4511       stream << "\n";
4512       stream << indent_str;
4513       stream << "              break;";
4514       stream << "\n";
4515       stream << indent_str;
4516       stream << "            }";
4517       stream << "\n";
4518       stream << indent_str;
4519       stream << "        }";
4520       stream << "\n";
4521       stream << indent_str;
4522       stream << "\n";
4523       stream << indent_str;
4524       stream << "    noarg:";
4525       stream << "\n";
4526       stream << indent_str;
4527       stream << "      if (!strcmp(fopt,\"include\")) {";
4528       stream << "\n";
4529       stream << indent_str;
4530       stream << "        if (farg && *farg) {";
4531       stream << "\n";
4532       stream << indent_str;
4533       stream << "          result = _";
4534       generate_string (parser_name, stream, indent + indent_str.length ());
4535       stream << "_configfile(farg, my_argc);";
4536       stream << "\n";
4537       stream << indent_str;
4538       stream << "        } else {";
4539       stream << "\n";
4540       stream << indent_str;
4541       stream << "          fprintf(stderr, \"%s:%s:%d: include requires a filename argument.\\n\",";
4542       stream << "\n";
4543       stream << indent_str;
4544       indent = 18;
4545       stream << "                  ";
4546       generate_string (package_var_name, stream, indent + indent_str.length ());
4547       stream << ", filename, line_num);";
4548       indent = 0;
4549       stream << "\n";
4550       stream << indent_str;
4551       stream << "        }";
4552       stream << "\n";
4553       stream << indent_str;
4554       stream << "        continue;";
4555       stream << "\n";
4556       stream << indent_str;
4557       stream << "      }";
4558       stream << "\n";
4559       stream << indent_str;
4560       stream << "      len = strlen(fopt);";
4561       stream << "\n";
4562       stream << indent_str;
4563       stream << "      strcat (my_argv, len > 1 ? \"--\" : \"-\");";
4564       stream << "\n";
4565       stream << indent_str;
4566       stream << "      strcat (my_argv, fopt);";
4567       stream << "\n";
4568       stream << indent_str;
4569       stream << "      if (len > 1 && ((farg && *farg) || equal))";
4570       stream << "\n";
4571       stream << indent_str;
4572       stream << "        strcat (my_argv, \"=\");";
4573       stream << "\n";
4574       stream << indent_str;
4575       stream << "      if (farg && *farg)";
4576       stream << "\n";
4577       stream << indent_str;
4578       stream << "        strcat (my_argv, farg);";
4579       stream << "\n";
4580       stream << indent_str;
4581       stream << "      ++(*my_argc);";
4582       stream << "\n";
4583       stream << indent_str;
4584       stream << "\n";
4585       stream << indent_str;
4586       stream << "      cmd_line_list_tmp = (struct line_list *) malloc (sizeof (struct line_list));";
4587       stream << "\n";
4588       stream << indent_str;
4589       stream << "      cmd_line_list_tmp->next = cmd_line_list;";
4590       stream << "\n";
4591       stream << indent_str;
4592       stream << "      cmd_line_list = cmd_line_list_tmp;";
4593       stream << "\n";
4594       stream << indent_str;
4595       stream << "      cmd_line_list->string_arg = gengetopt_strdup(my_argv);";
4596       stream << "\n";
4597       stream << indent_str;
4598       stream << "    } /* while */";
4599       stream << "\n";
4600       stream << indent_str;
4601       stream << "\n";
4602       stream << indent_str;
4603       stream << "  if (file)";
4604       stream << "\n";
4605       stream << indent_str;
4606       stream << "    fclose(file);";
4607       stream << "\n";
4608       stream << indent_str;
4609       stream << "  return result;";
4610       stream << "\n";
4611       stream << indent_str;
4612       stream << "}";
4613       stream << "\n";
4614       stream << indent_str;
4615       stream << "\n";
4616       stream << indent_str;
4617       stream << "int";
4618       stream << "\n";
4619       stream << indent_str;
4620       generate_string (parser_name, stream, indent + indent_str.length ());
4621       stream << "_configfile (";
4622       stream << "\n";
4623       stream << indent_str;
4624       stream << "  const char *filename,";
4625       stream << "\n";
4626       stream << indent_str;
4627       stream << "                           struct ";
4628       generate_string (args_info, stream, indent + indent_str.length ());
4629       stream << " *args_info,";
4630       stream << "\n";
4631       stream << indent_str;
4632       stream << "                           int override, int initialize, int check_required)";
4633       stream << "\n";
4634       stream << indent_str;
4635       stream << "{";
4636       stream << "\n";
4637       stream << indent_str;
4638       stream << "  struct ";
4639       generate_string (parser_name, stream, indent + indent_str.length ());
4640       stream << "_params params;";
4641       stream << "\n";
4642       stream << indent_str;
4643       stream << "\n";
4644       stream << indent_str;
4645       stream << "  params.override = override;";
4646       stream << "\n";
4647       stream << indent_str;
4648       stream << "  params.initialize = initialize;";
4649       stream << "\n";
4650       stream << indent_str;
4651       stream << "  params.check_required = check_required;";
4652       stream << "\n";
4653       stream << indent_str;
4654       stream << "  params.check_ambiguity = 0;";
4655       stream << "\n";
4656       stream << indent_str;
4657       stream << "  params.print_errors = 1;";
4658       stream << "\n";
4659       stream << indent_str;
4660       indent = 2;
4661       stream << "  ";
4662       indent = 0;
4663       stream << "\n";
4664       stream << indent_str;
4665       stream << "  return ";
4666       generate_string (parser_name, stream, indent + indent_str.length ());
4667       stream << "_config_file (filename, args_info, &params);";
4668       stream << "\n";
4669       stream << indent_str;
4670       stream << "}";
4671       stream << "\n";
4672       stream << indent_str;
4673       stream << "\n";
4674       stream << indent_str;
4675       stream << "int";
4676       stream << "\n";
4677       stream << indent_str;
4678       generate_string (parser_name, stream, indent + indent_str.length ());
4679       stream << "_config_file (const char *filename,";
4680       stream << "\n";
4681       stream << indent_str;
4682       stream << "                           struct ";
4683       generate_string (args_info, stream, indent + indent_str.length ());
4684       stream << " *args_info,";
4685       stream << "\n";
4686       stream << indent_str;
4687       stream << "                           struct ";
4688       generate_string (parser_name, stream, indent + indent_str.length ());
4689       stream << "_params *params)";
4690       stream << "\n";
4691       stream << indent_str;
4692       stream << "{";
4693       stream << "\n";
4694       stream << indent_str;
4695       stream << "  int i, result;";
4696       stream << "\n";
4697       stream << indent_str;
4698       stream << "  int my_argc = 1;";
4699       stream << "\n";
4700       stream << indent_str;
4701       stream << "  char **my_argv_arg;";
4702       stream << "\n";
4703       stream << indent_str;
4704       stream << "  char *additional_error;";
4705       stream << "\n";
4706       stream << indent_str;
4707       stream << "\n";
4708       stream << indent_str;
4709       stream << "  /* store the program name */";
4710       stream << "\n";
4711       stream << indent_str;
4712       stream << "  cmd_line_list_tmp = (struct line_list *) malloc (sizeof (struct line_list));";
4713       stream << "\n";
4714       stream << indent_str;
4715       stream << "  cmd_line_list_tmp->next = cmd_line_list;";
4716       stream << "\n";
4717       stream << indent_str;
4718       stream << "  cmd_line_list = cmd_line_list_tmp;";
4719       stream << "\n";
4720       stream << indent_str;
4721       stream << "  cmd_line_list->string_arg = gengetopt_strdup (";
4722       generate_string (package_var_name, stream, indent + indent_str.length ());
4723       stream << ");";
4724       stream << "\n";
4725       stream << indent_str;
4726       stream << "\n";
4727       stream << indent_str;
4728       stream << "  result = _";
4729       generate_string (parser_name, stream, indent + indent_str.length ());
4730       stream << "_configfile(filename, &my_argc);";
4731       stream << "\n";
4732       stream << indent_str;
4733       stream << "\n";
4734       stream << indent_str;
4735       stream << "  if (result != EXIT_FAILURE) {";
4736       stream << "\n";
4737       stream << indent_str;
4738       stream << "    my_argv_arg = (char **) malloc((my_argc+1) * sizeof(char *));";
4739       stream << "\n";
4740       stream << indent_str;
4741       stream << "    cmd_line_list_tmp = cmd_line_list;";
4742       stream << "\n";
4743       stream << indent_str;
4744       stream << "\n";
4745       stream << indent_str;
4746       stream << "    for (i = my_argc - 1; i >= 0; --i) {";
4747       stream << "\n";
4748       stream << indent_str;
4749       stream << "      my_argv_arg[i] = cmd_line_list_tmp->string_arg;";
4750       stream << "\n";
4751       stream << indent_str;
4752       stream << "      cmd_line_list_tmp = cmd_line_list_tmp->next;";
4753       stream << "\n";
4754       stream << indent_str;
4755       stream << "    }";
4756       stream << "\n";
4757       stream << indent_str;
4758       stream << "\n";
4759       stream << indent_str;
4760       stream << "    my_argv_arg[my_argc] = 0;";
4761       stream << "\n";
4762       stream << indent_str;
4763       stream << "\n";
4764       stream << indent_str;
4765       stream << "    additional_error = (char *)malloc(strlen(filename) + strlen(ADDITIONAL_ERROR) + 1);";
4766       stream << "\n";
4767       stream << indent_str;
4768       stream << "    strcpy (additional_error, ADDITIONAL_ERROR);";
4769       stream << "\n";
4770       stream << indent_str;
4771       stream << "    strcat (additional_error, filename);";
4772       stream << "\n";
4773       stream << indent_str;
4774       stream << "    result =";
4775       stream << "\n";
4776       stream << indent_str;
4777       indent = 6;
4778       stream << "      ";
4779       generate_string (parser_name, stream, indent + indent_str.length ());
4780       stream << "_internal (my_argc, my_argv_arg, args_info,";
4781       indent = 0;
4782       stream << "\n";
4783       stream << indent_str;
4784       stream << "                              params,";
4785       stream << "\n";
4786       stream << indent_str;
4787       stream << "                              additional_error);";
4788       stream << "\n";
4789       stream << indent_str;
4790       stream << "\n";
4791       stream << indent_str;
4792       stream << "    free (additional_error);";
4793       stream << "\n";
4794       stream << indent_str;
4795       stream << "    free (my_argv_arg);";
4796       stream << "\n";
4797       stream << indent_str;
4798       stream << "  }";
4799       stream << "\n";
4800       stream << indent_str;
4801       stream << "\n";
4802       stream << indent_str;
4803       stream << "  free_cmd_list();";
4804       stream << "\n";
4805       stream << indent_str;
4806       indent = 2;
4807       stream << "  ";
4808       generate_string (final_exit, stream, indent + indent_str.length ());
4809       indent = 0;
4810       stream << "\n";
4811       stream << indent_str;
4812       stream << "}";
4813       stream << "\n";
4814       stream << indent_str;
4815     }
4816   if (generate_string_parser)
4817     {
4818       stream << "\n";
4819       stream << indent_str;
4820       stream << "static unsigned int";
4821       stream << "\n";
4822       stream << indent_str;
4823       generate_string (parser_name, stream, indent + indent_str.length ());
4824       stream << "_create_argv(const char *cmdline_, char ***argv_ptr, const char *prog_name)";
4825       stream << "\n";
4826       stream << indent_str;
4827       stream << "{";
4828       stream << "\n";
4829       stream << indent_str;
4830       stream << "  char *cmdline, *p;";
4831       stream << "\n";
4832       stream << indent_str;
4833       stream << "  size_t n = 0, j;";
4834       stream << "\n";
4835       stream << indent_str;
4836       stream << "  int i;";
4837       stream << "\n";
4838       stream << indent_str;
4839       stream << "\n";
4840       stream << indent_str;
4841       stream << "  if (prog_name) {";
4842       stream << "\n";
4843       stream << indent_str;
4844       stream << "    cmd_line_list_tmp = (struct line_list *) malloc (sizeof (struct line_list));";
4845       stream << "\n";
4846       stream << indent_str;
4847       stream << "    cmd_line_list_tmp->next = cmd_line_list;";
4848       stream << "\n";
4849       stream << indent_str;
4850       stream << "    cmd_line_list = cmd_line_list_tmp;";
4851       stream << "\n";
4852       stream << indent_str;
4853       stream << "    cmd_line_list->string_arg = gengetopt_strdup (prog_name);";
4854       stream << "\n";
4855       stream << indent_str;
4856       stream << "\n";
4857       stream << indent_str;
4858       stream << "    ++n;";
4859       stream << "\n";
4860       stream << indent_str;
4861       stream << "  }";
4862       stream << "\n";
4863       stream << indent_str;
4864       stream << "\n";
4865       stream << indent_str;
4866       stream << "  cmdline = gengetopt_strdup(cmdline_);";
4867       stream << "\n";
4868       stream << indent_str;
4869       stream << "  p = cmdline;";
4870       stream << "\n";
4871       stream << indent_str;
4872       stream << "\n";
4873       stream << indent_str;
4874       stream << "  while (p && strlen(p))";
4875       stream << "\n";
4876       stream << indent_str;
4877       stream << "    {";
4878       stream << "\n";
4879       stream << indent_str;
4880       stream << "      j = strcspn(p, \" \\t\");";
4881       stream << "\n";
4882       stream << indent_str;
4883       stream << "      ++n;";
4884       stream << "\n";
4885       stream << indent_str;
4886       stream << "      if (j && j < strlen(p))";
4887       stream << "\n";
4888       stream << indent_str;
4889       stream << "        {";
4890       stream << "\n";
4891       stream << indent_str;
4892       stream << "          p[j] = '\\0';";
4893       stream << "\n";
4894       stream << indent_str;
4895       stream << "\n";
4896       stream << indent_str;
4897       stream << "          cmd_line_list_tmp = (struct line_list *) malloc (sizeof (struct line_list));";
4898       stream << "\n";
4899       stream << indent_str;
4900       stream << "          cmd_line_list_tmp->next = cmd_line_list;";
4901       stream << "\n";
4902       stream << indent_str;
4903       stream << "          cmd_line_list = cmd_line_list_tmp;";
4904       stream << "\n";
4905       stream << indent_str;
4906       stream << "          cmd_line_list->string_arg = gengetopt_strdup (p);";
4907       stream << "\n";
4908       stream << indent_str;
4909       stream << "\n";
4910       stream << indent_str;
4911       stream << "          p += (j+1);";
4912       stream << "\n";
4913       stream << indent_str;
4914       stream << "          p += strspn(p, \" \\t\");";
4915       stream << "\n";
4916       stream << indent_str;
4917       stream << "        }";
4918       stream << "\n";
4919       stream << indent_str;
4920       stream << "      else";
4921       stream << "\n";
4922       stream << indent_str;
4923       stream << "        {";
4924       stream << "\n";
4925       stream << indent_str;
4926       stream << "          cmd_line_list_tmp = (struct line_list *) malloc (sizeof (struct line_list));";
4927       stream << "\n";
4928       stream << indent_str;
4929       stream << "          cmd_line_list_tmp->next = cmd_line_list;";
4930       stream << "\n";
4931       stream << indent_str;
4932       stream << "          cmd_line_list = cmd_line_list_tmp;";
4933       stream << "\n";
4934       stream << indent_str;
4935       stream << "          cmd_line_list->string_arg = gengetopt_strdup (p);";
4936       stream << "\n";
4937       stream << indent_str;
4938       stream << "\n";
4939       stream << indent_str;
4940       stream << "          break;";
4941       stream << "\n";
4942       stream << indent_str;
4943       stream << "        }";
4944       stream << "\n";
4945       stream << indent_str;
4946       stream << "    }";
4947       stream << "\n";
4948       stream << indent_str;
4949       stream << "\n";
4950       stream << indent_str;
4951       stream << "  *argv_ptr = (char **) malloc((n + 1) * sizeof(char *));";
4952       stream << "\n";
4953       stream << indent_str;
4954       stream << "  cmd_line_list_tmp = cmd_line_list;";
4955       stream << "\n";
4956       stream << indent_str;
4957       stream << "  for (i = (n-1); i >= 0; --i)";
4958       stream << "\n";
4959       stream << indent_str;
4960       stream << "    {";
4961       stream << "\n";
4962       stream << indent_str;
4963       stream << "      (*argv_ptr)[i] = cmd_line_list_tmp->string_arg;";
4964       stream << "\n";
4965       stream << indent_str;
4966       stream << "      cmd_line_list_tmp = cmd_line_list_tmp->next;";
4967       stream << "\n";
4968       stream << indent_str;
4969       stream << "    }";
4970       stream << "\n";
4971       stream << indent_str;
4972       stream << "\n";
4973       stream << indent_str;
4974       stream << "  (*argv_ptr)[n] = 0;";
4975       stream << "\n";
4976       stream << indent_str;
4977       stream << "\n";
4978       stream << indent_str;
4979       stream << "  free(cmdline);";
4980       stream << "\n";
4981       stream << indent_str;
4982       stream << "  return n;";
4983       stream << "\n";
4984       stream << indent_str;
4985       stream << "}";
4986       stream << "\n";
4987       stream << indent_str;
4988       stream << "\n";
4989       stream << indent_str;
4990       stream << "int";
4991       stream << "\n";
4992       stream << indent_str;
4993       generate_string (parser_name, stream, indent + indent_str.length ());
4994       stream << "_string(const char *cmdline, struct ";
4995       generate_string (args_info, stream, indent + indent_str.length ());
4996       stream << " *args_info, const char *prog_name)";
4997       stream << "\n";
4998       stream << indent_str;
4999       stream << "{";
5000       stream << "\n";
5001       stream << indent_str;
5002       stream << "  return ";
5003       generate_string (parser_name, stream, indent + indent_str.length ());
5004       stream << "_string2(cmdline, args_info, prog_name, 0, 1, 1);";
5005       stream << "\n";
5006       stream << indent_str;
5007       stream << "}";
5008       stream << "\n";
5009       stream << indent_str;
5010       stream << "\n";
5011       stream << indent_str;
5012       stream << "int";
5013       stream << "\n";
5014       stream << indent_str;
5015       generate_string (parser_name, stream, indent + indent_str.length ());
5016       stream << "_string2(const char *cmdline, struct ";
5017       generate_string (args_info, stream, indent + indent_str.length ());
5018       stream << " *args_info, const char *prog_name,";
5019       stream << "\n";
5020       stream << indent_str;
5021       stream << "    int override, int initialize, int check_required)";
5022       stream << "\n";
5023       stream << indent_str;
5024       stream << "{";
5025       stream << "\n";
5026       stream << indent_str;
5027       stream << "  struct ";
5028       generate_string (parser_name, stream, indent + indent_str.length ());
5029       stream << "_params params;";
5030       stream << "\n";
5031       stream << indent_str;
5032       stream << "\n";
5033       stream << indent_str;
5034       stream << "  params.override = override;";
5035       stream << "\n";
5036       stream << indent_str;
5037       stream << "  params.initialize = initialize;";
5038       stream << "\n";
5039       stream << indent_str;
5040       stream << "  params.check_required = check_required;";
5041       stream << "\n";
5042       stream << indent_str;
5043       stream << "  params.check_ambiguity = 0;";
5044       stream << "\n";
5045       stream << indent_str;
5046       stream << "  params.print_errors = 1;";
5047       stream << "\n";
5048       stream << indent_str;
5049       stream << "\n";
5050       stream << indent_str;
5051       stream << "  return ";
5052       generate_string (parser_name, stream, indent + indent_str.length ());
5053       stream << "_string_ext(cmdline, args_info, prog_name, &params);";
5054       stream << "\n";
5055       stream << indent_str;
5056       stream << "}";
5057       stream << "\n";
5058       stream << indent_str;
5059       stream << "\n";
5060       stream << indent_str;
5061       stream << "int";
5062       stream << "\n";
5063       stream << indent_str;
5064       generate_string (parser_name, stream, indent + indent_str.length ());
5065       stream << "_string_ext(const char *cmdline, struct ";
5066       generate_string (args_info, stream, indent + indent_str.length ());
5067       stream << " *args_info, const char *prog_name,";
5068       stream << "\n";
5069       stream << indent_str;
5070       stream << "    struct ";
5071       generate_string (parser_name, stream, indent + indent_str.length ());
5072       stream << "_params *params)";
5073       stream << "\n";
5074       stream << indent_str;
5075       stream << "{";
5076       stream << "\n";
5077       stream << indent_str;
5078       stream << "  char **argv_ptr = 0;";
5079       stream << "\n";
5080       stream << indent_str;
5081       stream << "  int result;";
5082       stream << "\n";
5083       stream << indent_str;
5084       stream << "  unsigned int argc;";
5085       stream << "\n";
5086       stream << indent_str;
5087       indent = 2;
5088       stream << "  ";
5089       indent = 0;
5090       stream << "\n";
5091       stream << indent_str;
5092       stream << "  argc = ";
5093       generate_string (parser_name, stream, indent + indent_str.length ());
5094       stream << "_create_argv(cmdline, &argv_ptr, prog_name);";
5095       stream << "\n";
5096       stream << indent_str;
5097       indent = 2;
5098       stream << "  ";
5099       indent = 0;
5100       stream << "\n";
5101       stream << indent_str;
5102       stream << "  result =";
5103       stream << "\n";
5104       stream << indent_str;
5105       indent = 4;
5106       stream << "    ";
5107       generate_string (parser_name, stream, indent + indent_str.length ());
5108       stream << "_internal (argc, argv_ptr, args_info, params, 0);";
5109       indent = 0;
5110       stream << "\n";
5111       stream << indent_str;
5112       indent = 2;
5113       stream << "  ";
5114       indent = 0;
5115       stream << "\n";
5116       stream << indent_str;
5117       stream << "  if (argv_ptr)";
5118       stream << "\n";
5119       stream << indent_str;
5120       stream << "    {";
5121       stream << "\n";
5122       stream << indent_str;
5123       stream << "      free (argv_ptr);";
5124       stream << "\n";
5125       stream << indent_str;
5126       stream << "    }";
5127       stream << "\n";
5128       stream << indent_str;
5129       stream << "\n";
5130       stream << indent_str;
5131       stream << "  free_cmd_list();";
5132       stream << "\n";
5133       stream << indent_str;
5134       indent = 2;
5135       stream << "  ";
5136       indent = 0;
5137       stream << "\n";
5138       stream << indent_str;
5139       indent = 2;
5140       stream << "  ";
5141       generate_string (final_exit, stream, indent + indent_str.length ());
5142       indent = 0;
5143       stream << "\n";
5144       stream << indent_str;
5145       stream << "}";
5146       stream << "\n";
5147       stream << indent_str;
5148       stream << "\n";
5149       stream << indent_str;
5150     }
5151   stream << "/* vim: set ft=c noet ts=8 sts=8 sw=8 tw=80 nojs spell : */";
5152   stream << "\n";
5153   stream << indent_str;
5154 }
5155