1 /* print_command -- A way to make readable commands from a command tree. */
2 /* Copyright (C) 1989 Free Software Foundation, Inc.
4 This file is part of GNU Bash, the Bourne Again SHell.
6 Bash is free software; you can redistribute it and/or modify it under
7 the terms of the GNU General Public License as published by the Free
8 Software Foundation; either version 2, or (at your option) any later
11 Bash is distributed in the hope that it will be useful, but WITHOUT ANY
12 WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
16 You should have received a copy of the GNU General Public License along
17 with Bash; see the file COPYING. If not, write to the Free Software
18 Foundation, 59 Temple Place, Suite 330, Boston, MA 02111 USA. */
24 #if defined (HAVE_UNISTD_H)
26 # include <sys/types.h>
31 #if defined (PREFER_STDARG)
41 #include <y.tab.h> /* use <...> so we pick it up from the build directory */
42 #include "builtins/common.h"
45 extern int printf
__P((const char *, ...)); /* Yuck. Double yuck. */
48 extern int indirection_level
;
50 static int indentation
;
51 static int indentation_amount
= 4;
53 #if defined (PREFER_STDARG)
54 typedef void PFUNC
__P((const char *, ...));
56 static void cprintf
__P((const char *, ...)) __attribute__((__format__ (printf
, 1, 2)));
57 static void xprintf
__P((const char *, ...)) __attribute__((__format__ (printf
, 1, 2)));
59 #define PFUNC VFunction
60 static void cprintf ();
61 static void xprintf ();
64 static void reset_locals
__P((void));
65 static void newline
__P((char *));
66 static void indent
__P((int));
67 static void semicolon
__P((void));
68 static void the_printed_command_resize
__P((int));
70 static void make_command_string_internal
__P((COMMAND
*));
71 static void _print_word_list
__P((WORD_LIST
*, char *, PFUNC
*));
72 static void command_print_word_list
__P((WORD_LIST
*, char *));
73 static void print_case_clauses
__P((PATTERN_LIST
*));
74 static void print_redirection_list
__P((REDIRECT
*));
75 static void print_redirection
__P((REDIRECT
*));
77 static void print_for_command
__P((FOR_COM
*));
78 #if defined (ARITH_FOR_COMMAND)
79 static void print_arith_for_command
__P((ARITH_FOR_COM
*));
81 #if defined (SELECT_COMMAND)
82 static void print_select_command
__P((SELECT_COM
*));
84 static void print_group_command
__P((GROUP_COM
*));
85 static void print_case_command
__P((CASE_COM
*));
86 static void print_while_command
__P((WHILE_COM
*));
87 static void print_until_command
__P((WHILE_COM
*));
88 static void print_until_or_while
__P((WHILE_COM
*, char *));
89 static void print_if_command
__P((IF_COM
*));
90 #if defined (DPAREN_ARITHMETIC)
91 static void print_arith_command
__P((ARITH_COM
*));
93 #if defined (COND_COMMAND)
94 static void print_cond_node
__P((COND_COM
*));
95 static void print_cond_command
__P((COND_COM
*));
97 static void print_function_def
__P((FUNCTION_DEF
*));
99 #define PRINTED_COMMAND_INITIAL_SIZE 64
100 #define PRINTED_COMMAND_GROW_SIZE 128
102 char *the_printed_command
= (char *)NULL
;
103 int the_printed_command_size
= 0;
104 int command_string_index
= 0;
106 /* Non-zero means the stuff being printed is inside of a function def. */
107 static int inside_function_def
;
108 static int skip_this_indent
;
109 static int was_heredoc
;
111 /* The depth of the group commands that we are currently printing. This
112 includes the group command that is a function body. */
113 static int group_command_nesting
;
115 /* A buffer to indicate the indirection level (PS4) when set -x is enabled. */
116 static char indirection_string
[100];
118 /* Print COMMAND (a command tree) on standard output. */
120 print_command (command
)
123 command_string_index
= 0;
124 printf ("%s", make_command_string (command
));
127 /* Make a string which is the printed representation of the command
128 tree in COMMAND. We return this string. However, the string is
129 not consed, so you have to do that yourself if you want it to
132 make_command_string (command
)
135 command_string_index
= was_heredoc
= 0;
136 make_command_string_internal (command
);
137 return (the_printed_command
);
140 /* The internal function. This is the real workhorse. */
142 make_command_string_internal (command
)
149 if (skip_this_indent
)
152 indent (indentation
);
154 if (command
->flags
& CMD_TIME_PIPELINE
)
157 if (command
->flags
& CMD_TIME_POSIX
)
161 if (command
->flags
& CMD_INVERT_RETURN
)
164 switch (command
->type
)
167 print_for_command (command
->value
.For
);
170 #if defined (ARITH_FOR_COMMAND)
172 print_arith_for_command (command
->value
.ArithFor
);
176 #if defined (SELECT_COMMAND)
178 print_select_command (command
->value
.Select
);
183 print_case_command (command
->value
.Case
);
187 print_while_command (command
->value
.While
);
191 print_until_command (command
->value
.While
);
195 print_if_command (command
->value
.If
);
198 #if defined (DPAREN_ARITHMETIC)
200 print_arith_command (command
->value
.Arith
);
204 #if defined (COND_COMMAND)
206 print_cond_command (command
->value
.Cond
);
211 print_simple_command (command
->value
.Simple
);
217 make_command_string_internal (command
->value
.Connection
->first
);
219 switch (command
->value
.Connection
->connector
)
224 char c
= command
->value
.Connection
->connector
;
226 if (c
!= '&' || command
->value
.Connection
->second
)
236 if (command
->value
.Connection
->second
)
242 if (command
->value
.Connection
->second
)
247 if (was_heredoc
== 0)
252 if (inside_function_def
)
257 if (command
->value
.Connection
->second
)
263 cprintf ("print_command: bad connector `%d'",
264 command
->value
.Connection
->connector
);
268 make_command_string_internal (command
->value
.Connection
->second
);
271 case cm_function_def
:
272 print_function_def (command
->value
.Function_def
);
276 print_group_command (command
->value
.Group
);
282 make_command_string_internal (command
->value
.Subshell
->command
);
287 command_error ("print_command", CMDERR_BADTYPE
, command
->type
, 0);
292 if (command
->redirects
)
295 print_redirection_list (command
->redirects
);
301 _print_word_list (list
, separator
, pfunc
)
308 for (w
= list
; w
; w
= w
->next
)
309 (*pfunc
) ("%s%s", w
->word
->word
, w
->next
? separator
: "");
313 print_word_list (list
, separator
)
317 _print_word_list (list
, separator
, xprintf
);
320 /* Return a string denoting what our indirection level is. */
323 indirection_level_string ()
328 indirection_string
[0] = '\0';
329 ps4
= get_string_value ("PS4");
331 if (ps4
== 0 || *ps4
== '\0')
332 return (indirection_string
);
334 change_flag ('x', FLAG_OFF
);
335 ps4
= decode_prompt_string (ps4
);
336 change_flag ('x', FLAG_ON
);
338 for (i
= 0; *ps4
&& i
< indirection_level
&& i
< 99; i
++)
339 indirection_string
[i
] = *ps4
;
341 for (j
= 1; *ps4
&& ps4
[j
] && i
< 99; i
++, j
++)
342 indirection_string
[i
] = ps4
[j
];
344 indirection_string
[i
] = '\0';
346 return (indirection_string
);
349 /* A function to print the words of a simple command when set -x is on. */
351 xtrace_print_word_list (list
)
357 fprintf (stderr
, "%s", indirection_level_string ());
358 for (w
= list
; w
; w
= w
->next
)
361 if (t
== 0 || *t
== '\0')
362 fprintf (stderr
, "''%s", w
->next
? " " : "");
363 else if (sh_contains_shell_metas (t
))
365 x
= sh_single_quote (t
);
366 fprintf (stderr
, "%s%s", x
, w
->next
? " " : "");
369 else if (ansic_shouldquote (t
))
371 x
= ansic_quote (t
, 0, (int *)0);
372 fprintf (stderr
, "%s%s", x
, w
->next
? " " : "");
376 fprintf (stderr
, "%s%s", t
, w
->next
? " " : "");
378 fprintf (stderr
, "\n");
382 command_print_word_list (list
, separator
)
386 _print_word_list (list
, separator
, cprintf
);
390 print_for_command (for_command
)
391 FOR_COM
*for_command
;
393 cprintf ("for %s in ", for_command
->name
->word
);
394 command_print_word_list (for_command
->map_list
, " ");
397 indentation
+= indentation_amount
;
398 make_command_string_internal (for_command
->action
);
400 indentation
-= indentation_amount
;
404 #if defined (ARITH_FOR_COMMAND)
406 print_arith_for_command (arith_for_command
)
407 ARITH_FOR_COM
*arith_for_command
;
410 command_print_word_list (arith_for_command
->init
, " ");
412 command_print_word_list (arith_for_command
->test
, " ");
414 command_print_word_list (arith_for_command
->step
, " ");
417 indentation
+= indentation_amount
;
418 make_command_string_internal (arith_for_command
->action
);
420 indentation
-= indentation_amount
;
423 #endif /* ARITH_FOR_COMMAND */
425 #if defined (SELECT_COMMAND)
427 print_select_command (select_command
)
428 SELECT_COM
*select_command
;
430 cprintf ("select %s in ", select_command
->name
->word
);
431 command_print_word_list (select_command
->map_list
, " ");
434 indentation
+= indentation_amount
;
435 make_command_string_internal (select_command
->action
);
437 indentation
-= indentation_amount
;
440 #endif /* SELECT_COMMAND */
443 print_group_command (group_command
)
444 GROUP_COM
*group_command
;
446 group_command_nesting
++;
449 if (inside_function_def
== 0)
453 /* This is a group command { ... } inside of a function
454 definition, and should be printed as a multiline group
455 command, using the current indentation. */
457 indentation
+= indentation_amount
;
460 make_command_string_internal (group_command
->command
);
462 if (inside_function_def
)
465 indentation
-= indentation_amount
;
466 indent (indentation
);
476 group_command_nesting
--;
480 print_case_command (case_command
)
481 CASE_COM
*case_command
;
483 cprintf ("case %s in ", case_command
->word
->word
);
484 if (case_command
->clauses
)
485 print_case_clauses (case_command
->clauses
);
490 print_case_clauses (clauses
)
491 PATTERN_LIST
*clauses
;
493 indentation
+= indentation_amount
;
497 command_print_word_list (clauses
->patterns
, " | ");
499 indentation
+= indentation_amount
;
500 make_command_string_internal (clauses
->action
);
501 indentation
-= indentation_amount
;
503 clauses
= clauses
->next
;
505 indentation
-= indentation_amount
;
509 print_while_command (while_command
)
510 WHILE_COM
*while_command
;
512 print_until_or_while (while_command
, "while");
516 print_until_command (while_command
)
517 WHILE_COM
*while_command
;
519 print_until_or_while (while_command
, "until");
523 print_until_or_while (while_command
, which
)
524 WHILE_COM
*while_command
;
527 cprintf ("%s ", which
);
529 make_command_string_internal (while_command
->test
);
531 cprintf (" do\n"); /* was newline ("do\n"); */
532 indentation
+= indentation_amount
;
533 make_command_string_internal (while_command
->action
);
534 indentation
-= indentation_amount
;
540 print_if_command (if_command
)
545 make_command_string_internal (if_command
->test
);
548 indentation
+= indentation_amount
;
549 make_command_string_internal (if_command
->true_case
);
550 indentation
-= indentation_amount
;
552 if (if_command
->false_case
)
556 indentation
+= indentation_amount
;
557 make_command_string_internal (if_command
->false_case
);
558 indentation
-= indentation_amount
;
564 #if defined (DPAREN_ARITHMETIC)
566 print_arith_command (arith_command
)
567 ARITH_COM
*arith_command
;
570 command_print_word_list (arith_command
->exp
, " ");
575 #if defined (COND_COMMAND)
577 print_cond_node (cond
)
580 if (cond
->flags
& CMD_INVERT_RETURN
)
583 if (cond
->type
== COND_EXPR
)
586 print_cond_node (cond
->left
);
589 else if (cond
->type
== COND_AND
)
591 print_cond_node (cond
->left
);
593 print_cond_node (cond
->right
);
595 else if (cond
->type
== COND_OR
)
597 print_cond_node (cond
->left
);
599 print_cond_node (cond
->right
);
601 else if (cond
->type
== COND_UNARY
)
603 cprintf ("%s", cond
->op
->word
);
605 print_cond_node (cond
->left
);
607 else if (cond
->type
== COND_BINARY
)
609 print_cond_node (cond
->left
);
611 cprintf ("%s", cond
->op
->word
);
613 print_cond_node (cond
->right
);
615 else if (cond
->type
== COND_TERM
)
617 cprintf ("%s", cond
->op
->word
); /* need to add quoting here */
622 print_cond_command (cond
)
626 print_cond_node (cond
);
632 debug_print_cond_command (cond
)
635 fprintf (stderr
, "DEBUG: ");
636 command_string_index
= 0;
637 print_cond_command (cond
);
638 fprintf (stderr
, "%s\n", the_printed_command
);
643 xtrace_print_cond_term (type
, invert
, op
, arg1
, arg2
)
648 command_string_index
= 0;
649 fprintf (stderr
, "%s", indirection_level_string ());
650 fprintf (stderr
, "[[ ");
652 fprintf (stderr
, "! ");
654 if (type
== COND_UNARY
)
656 fprintf (stderr
, "%s ", op
->word
);
657 fprintf (stderr
, "%s", (arg1
&& *arg1
) ? arg1
: "''");
659 else if (type
== COND_BINARY
)
661 fprintf (stderr
, "%s", (arg1
&& *arg1
) ? arg1
: "''");
662 fprintf (stderr
, " %s ", op
->word
);
663 fprintf (stderr
, "%s", (arg2
&& *arg2
) ? arg2
: "''");
666 fprintf (stderr
, " ]]\n");
668 #endif /* COND_COMMAND */
670 #if defined (DPAREN_ARITHMETIC) || defined (ARITH_FOR_COMMAND)
671 /* A function to print the words of an arithmetic command when set -x is on. */
673 xtrace_print_arith_cmd (list
)
678 fprintf (stderr
, "%s", indirection_level_string ());
679 fprintf (stderr
, "(( ");
680 for (w
= list
; w
; w
= w
->next
)
681 fprintf (stderr
, "%s%s", w
->word
->word
, w
->next
? " " : "");
682 fprintf (stderr
, " ))\n");
687 print_simple_command (simple_command
)
688 SIMPLE_COM
*simple_command
;
690 command_print_word_list (simple_command
->words
, " ");
692 if (simple_command
->redirects
)
695 print_redirection_list (simple_command
->redirects
);
700 print_redirection_list (redirects
)
703 REDIRECT
*heredocs
, *hdtail
, *newredir
;
705 heredocs
= (REDIRECT
*)NULL
;
711 /* Defer printing the here documents until we've printed the
712 rest of the redirections. */
713 if (redirects
->instruction
== r_reading_until
|| redirects
->instruction
== r_deblank_reading_until
)
715 newredir
= copy_redirect (redirects
);
716 newredir
->next
= (REDIRECT
*)NULL
;
719 hdtail
->next
= newredir
;
723 hdtail
= heredocs
= newredir
;
726 print_redirection (redirects
);
728 redirects
= redirects
->next
;
733 /* Now that we've printed all the other redirections (on one line),
734 print the here documents. */
738 for (hdtail
= heredocs
; hdtail
; hdtail
= hdtail
->next
)
740 print_redirection (hdtail
);
743 dispose_redirects (heredocs
);
749 print_redirection (redirect
)
752 int kill_leading
, redirector
, redir_fd
;
753 WORD_DESC
*redirectee
;
756 redirectee
= redirect
->redirectee
.filename
;
757 redirector
= redirect
->redirector
;
758 redir_fd
= redirect
->redirectee
.dest
;
760 switch (redirect
->instruction
)
762 case r_output_direction
:
764 cprintf ("%d", redirector
);
765 cprintf (">%s", redirectee
->word
);
768 case r_input_direction
:
770 cprintf ("%d", redirector
);
771 cprintf ("<%s", redirectee
->word
);
774 case r_inputa_direction
: /* Redirection created by the shell. */
780 cprintf ("%d", redirector
);
781 cprintf (">>%s", redirectee
->word
);
784 case r_deblank_reading_until
:
787 case r_reading_until
:
789 cprintf ("%d", redirector
);
790 /* If the here document delimiter is quoted, single-quote it. */
791 if (redirect
->redirectee
.filename
->flags
& W_QUOTED
)
794 x
= sh_single_quote (redirect
->here_doc_eof
);
795 cprintf ("<<%s%s\n", kill_leading
? "-" : "", x
);
799 cprintf ("<<%s%s\n", kill_leading
? "-" : "", redirect
->here_doc_eof
);
801 redirect
->redirectee
.filename
->word
, redirect
->here_doc_eof
);
804 case r_reading_string
:
806 cprintf ("%d", redirector
);
807 if (ansic_shouldquote (redirect
->redirectee
.filename
->word
))
810 x
= ansic_quote (redirect
->redirectee
.filename
->word
, 0, (int *)0);
811 cprintf ("<<< %s", x
);
815 cprintf ("<<< %s", redirect
->redirectee
.filename
->word
);
818 case r_duplicating_input
:
819 cprintf ("%d<&%d", redirector
, redir_fd
);
822 case r_duplicating_output
:
823 cprintf ("%d>&%d", redirector
, redir_fd
);
826 case r_duplicating_input_word
:
827 cprintf ("%d<&%s", redirector
, redirectee
->word
);
830 case r_duplicating_output_word
:
831 cprintf ("%d>&%s", redirector
, redirectee
->word
);
835 cprintf ("%d<&%d-", redirector
, redir_fd
);
839 cprintf ("%d>&%d-", redirector
, redir_fd
);
842 case r_move_input_word
:
843 cprintf ("%d<&%s-", redirector
, redirectee
->word
);
846 case r_move_output_word
:
847 cprintf ("%d>&%s-", redirector
, redirectee
->word
);
851 cprintf ("%d>&-", redirector
);
855 cprintf (">&%s", redirectee
->word
);
860 cprintf ("%d", redirector
);
861 cprintf ("<>%s", redirectee
->word
);
866 cprintf ("%d", redirector
);
867 cprintf (">|%s", redirectee
->word
);
875 inside_function_def
= 0;
880 print_function_def (func
)
884 REDIRECT
*func_redirects
;
886 func_redirects
= NULL
;
887 cprintf ("function %s () \n", func
->name
->word
);
888 add_unwind_protect (reset_locals
, 0);
890 indent (indentation
);
893 inside_function_def
++;
894 indentation
+= indentation_amount
;
896 cmdcopy
= copy_command (func
->command
);
897 if (cmdcopy
->type
== cm_group
)
899 func_redirects
= cmdcopy
->redirects
;
900 cmdcopy
->redirects
= (REDIRECT
*)NULL
;
902 make_command_string_internal (cmdcopy
->type
== cm_group
903 ? cmdcopy
->value
.Group
->command
906 remove_unwind_protect ();
907 indentation
-= indentation_amount
;
908 inside_function_def
--;
913 print_redirection_list (func_redirects
);
914 cmdcopy
->redirects
= func_redirects
;
919 dispose_command (cmdcopy
);
922 /* Return the string representation of the named function.
923 NAME is the name of the function.
924 COMMAND is the function body. It should be a GROUP_COM.
925 MULTI_LINE is non-zero to pretty-print, or zero for all on one line.
928 named_function_string (name
, command
, multi_line
)
934 int old_indent
, old_amount
;
936 REDIRECT
*func_redirects
;
938 old_indent
= indentation
;
939 old_amount
= indentation_amount
;
940 command_string_index
= was_heredoc
= 0;
943 cprintf ("%s ", name
);
950 indentation_amount
= 0;
955 indentation
+= indentation_amount
;
958 inside_function_def
++;
960 cprintf (multi_line
? "{ \n" : "{ ");
962 cmdcopy
= copy_command (command
);
963 /* Take any redirections specified in the function definition (which should
964 apply to the function as a whole) and save them for printing later. */
965 func_redirects
= (REDIRECT
*)NULL
;
966 if (cmdcopy
->type
== cm_group
)
968 func_redirects
= cmdcopy
->redirects
;
969 cmdcopy
->redirects
= (REDIRECT
*)NULL
;
971 make_command_string_internal (cmdcopy
->type
== cm_group
972 ? cmdcopy
->value
.Group
->command
975 indentation
= old_indent
;
976 indentation_amount
= old_amount
;
977 inside_function_def
--;
982 print_redirection_list (func_redirects
);
983 cmdcopy
->redirects
= func_redirects
;
988 result
= the_printed_command
;
994 for (i
= 0; result
[i
]; i
++)
995 if (result
[i
] == '\n')
997 strcpy (result
+ i
, result
+ i
+ 1);
1001 if (result
[2] == '\n') /* XXX -- experimental */
1002 strcpy (result
+ 2, result
+ 3);
1006 dispose_command (cmdcopy
);
1016 indent (indentation
);
1017 if (string
&& *string
)
1018 cprintf ("%s", string
);
1021 static char *indentation_string
;
1022 static int indentation_size
;
1030 RESIZE_MALLOCED_BUFFER (indentation_string
, 0, amount
, indentation_size
, 16);
1032 for (i
= 0; amount
> 0; amount
--)
1033 indentation_string
[i
++] = ' ';
1034 indentation_string
[i
] = '\0';
1035 cprintf (indentation_string
);
1041 if (command_string_index
> 0 &&
1042 (the_printed_command
[command_string_index
- 1] == '&' ||
1043 the_printed_command
[command_string_index
- 1] == '\n'))
1048 /* How to make the string. */
1050 #if defined (PREFER_STDARG)
1051 cprintf (const char *control
, ...)
1053 cprintf (control
, va_alist
)
1054 const char *control
;
1058 register const char *s
;
1059 char char_arg
[2], *argp
, intbuf
[INT_STRLEN_BOUND (int) + 1];
1060 int digit_arg
, arg_len
, c
;
1063 SH_VA_START (args
, control
);
1065 arg_len
= strlen (control
);
1066 the_printed_command_resize (arg_len
+ 1);
1073 argp
= (char *)NULL
;
1074 if (c
!= '%' || !*s
)
1092 argp
= va_arg (args
, char *);
1093 arg_len
= strlen (argp
);
1097 /* Represent an out-of-range file descriptor with an out-of-range
1098 integer value. We can do this because the only use of `%d' in
1099 the calls to cprintf is to output a file descriptor number for
1101 digit_arg
= va_arg (args
, int);
1104 sprintf (intbuf
, "%u", (unsigned)-1);
1108 argp
= inttostr (digit_arg
, intbuf
, sizeof (intbuf
));
1109 arg_len
= strlen (argp
);
1113 char_arg
[0] = va_arg (args
, int);
1119 programming_error ("cprintf: bad `%%' argument (%c)", c
);
1124 if (argp
&& arg_len
)
1126 the_printed_command_resize (arg_len
+ 1);
1127 FASTCOPY (argp
, the_printed_command
+ command_string_index
, arg_len
);
1128 command_string_index
+= arg_len
;
1132 the_printed_command
[command_string_index
] = '\0';
1135 /* Ensure that there is enough space to stuff LENGTH characters into
1136 THE_PRINTED_COMMAND. */
1138 the_printed_command_resize (length
)
1141 if (the_printed_command
== 0)
1143 the_printed_command_size
= (length
+ PRINTED_COMMAND_INITIAL_SIZE
- 1) & ~(PRINTED_COMMAND_INITIAL_SIZE
- 1);
1144 the_printed_command
= (char *)xmalloc (the_printed_command_size
);
1145 command_string_index
= 0;
1147 else if ((command_string_index
+ length
) >= the_printed_command_size
)
1150 new = command_string_index
+ length
+ 1;
1152 /* Round up to the next multiple of PRINTED_COMMAND_GROW_SIZE. */
1153 new = (new + PRINTED_COMMAND_GROW_SIZE
- 1) & ~(PRINTED_COMMAND_GROW_SIZE
- 1);
1154 the_printed_command_size
= new;
1156 the_printed_command
= (char *)xrealloc (the_printed_command
, the_printed_command_size
);
1160 #if defined (HAVE_VPRINTF)
1161 /* ``If vprintf is available, you may assume that vfprintf and vsprintf are
1162 also available.'' */
1165 #if defined (PREFER_STDARG)
1166 xprintf (const char *format
, ...)
1168 xprintf (format
, va_alist
)
1175 SH_VA_START (args
, format
);
1177 vfprintf (stdout
, format
, args
);
1184 xprintf (format
, arg1
, arg2
, arg3
, arg4
, arg5
)
1187 printf (format
, arg1
, arg2
, arg3
, arg4
, arg5
);
1190 #endif /* !HAVE_VPRINTF */