Mail Archives: djgpp-workers/1996/09/24/08:27:10
The following changes cause `system' to immediately call the shell if
$SHELL or $COMSPEC point to a program whose name is known to be a unixy
shell. They also change the way such shells are called (the previous
method broke the ``here document'' feature of the shell).
*** src/libc/ansi/stdlib/system.c~9 Sun Sep 15 16:38:42 1996
--- src/libc/ansi/stdlib/system.c Sun Sep 22 14:14:28 1996
***************
*** 122,146 ****
}
else
{
! /* Assume this is a `sh' work-alike. What's below should
! work with `ms_sh'; others should be fine if they support
! the response file method (but I didn't test anything
! except `ms_sh'). */
FILE *respf;
int e = errno;
char *atfile = (char *) alloca (L_tmpnam);
! char *cmd_tail = (char *)alloca (L_tmpnam + 5);
errno = 0;
respf = fopen (tmpnam (atfile), "wb");
- /* Note that the command line is written to the response file
- as a single (possibly long) line. The docs of `ms_sh' tells
- that when invoking other programs, it writes each argument
- on a separate line, but the shell itself doesn't seem to
- care when it gets everything as a single line. */
-
if (respf)
{
int retval;
--- 122,143 ----
}
else
{
! /* Assume this is a `sh' work-alike which can be invoked like
! this:
! sh file
+ where `file' holds the entire command line.
+
+ (Another possibility is a response file, but that breaks the
+ ``here document'' feature of the shell.) */
FILE *respf;
int e = errno;
char *atfile = (char *) alloca (L_tmpnam);
! char *cmd_tail = (char *)alloca (L_tmpnam + 1);
errno = 0;
respf = fopen (tmpnam (atfile), "wb");
if (respf)
{
int retval;
***************
*** 154,167 ****
fputs (cmdline, respf);
fputc ('\n', respf);
fclose (respf);
! strcpy (cmd_tail, "-c @");
strcat (cmd_tail, atfile);
retval = _dos_exec (shell, cmd_tail, environ);
remove (atfile);
return retval;
}
else
! return emiterror ("Cannot open response file for SH", errno);
}
}
--- 151,164 ----
fputs (cmdline, respf);
fputc ('\n', respf);
fclose (respf);
! strcpy (cmd_tail, " ");
strcat (cmd_tail, atfile);
retval = _dos_exec (shell, cmd_tail, environ);
remove (atfile);
return retval;
}
else
! return emiterror ("Cannot open script file for $SHELL", errno);
}
}
***************
*** 485,502 ****
{
/* Set the feature bits for this run: either from the
environment or from global variable. */
! const char *p = getenv ("DJSYSFLAGS");
sys_flags = __system_flags;
! if (p && *p)
{
char *stop;
! long flags = strtol (p, &stop, 0);
if (*stop == '\0')
sys_flags = flags;
}
/* Special case: NULL means just exec the command interpreter. */
if (cmdline == 0)
cmdline = "";
--- 482,506 ----
{
/* Set the feature bits for this run: either from the
environment or from global variable. */
! const char *envflags = getenv ("DJSYSFLAGS");
! const char *comspec = getenv ("COMSPEC");
! const char *shell = 0;
sys_flags = __system_flags;
! if (envflags && *envflags)
{
char *stop;
! long flags = strtol (envflags, &stop, 0);
if (*stop == '\0')
sys_flags = flags;
}
+ if (sys_flags & __system_use_shell)
+ shell = getenv ("SHELL");
+ if (!shell)
+ shell = comspec;
+
/* Special case: NULL means just exec the command interpreter. */
if (cmdline == 0)
cmdline = "";
***************
*** 506,513 ****
while (isspace(*cmdline))
cmdline++;
! /* If they want to always do it via command processor, comply. */
! if (!*cmdline || (sys_flags & __system_call_cmdproc))
return _shell_command ("", cmdline);
else
{
--- 510,525 ----
while (isspace(*cmdline))
cmdline++;
! /* Call the shell if:
!
! the command line is empty
! or
! they want to always do it via command processor
! or
! $SHELL or $COMSPEC point to a unixy shell */
! if (!*cmdline
! || (sys_flags & __system_call_cmdproc)
! || (!(sys_flags & __system_emulate_command) && _is_unixy_shell (shell)))
return _shell_command ("", cmdline);
else
{
***************
*** 572,578 ****
{
__unquote (prog, t, u); /* unquote and copy to prog */
/* We can't grok commands in parentheses, so assume they
! use a shell that knows about these, like 4DOS or `sh'. */
if (prog[0] == '(')
return _shell_command ("", cmdline);
strcpy (s, u); /* remove program name from cmdline */
--- 584,593 ----
{
__unquote (prog, t, u); /* unquote and copy to prog */
/* We can't grok commands in parentheses, so assume they
! use a shell that knows about these, like 4DOS or `sh'.
!
! FIXME: if the parenthesized group is NOT the first command
! in a pipe, the commands that preceed it will be run twice. */
if (prog[0] == '(')
return _shell_command ("", cmdline);
strcpy (s, u); /* remove program name from cmdline */
*** include/stdlib.h~3 Fri Sep 13 18:27:24 1996
--- include/stdlib.h Sun Sep 22 11:53:56 1996
***************
*** 102,107 ****
--- 102,108 ----
#define __system_use_shell 0x0004 /* use $SHELL if set */
#define __system_allow_multiple_cmds 0x0008 /* allow `cmd1; cmd2; ...' */
#define __system_allow_long_cmds 0x0010 /* handle commands > 126 chars */
+ #define __system_emulate_command 0x0020 /* try to emulate the shell */
#define __system_handle_null_commands 0x1000 /* ignore cmds with no effect */
#define __system_ignore_chdir 0x2000 /* make `cd' be a null command */
#define __system_emulate_chdir 0x4000 /* handle `cd' internally */
*** src/libc/ansi/stdlib/system.t~2 Sat Aug 31 18:56:10 1996
--- src/libc/ansi/stdlib/system.txh Mon Sep 23 18:06:08 1996
***************
*** 86,91 ****
--- 86,99 ----
detect early that the command line is longer than 126 characters and
refuse to run it.
+ @item __system_emulate_command
+ If reset (the default), @code{system} will pass the entire command line
+ to the shell if its name is one of the following: @file{sh.exe},
+ @file{sh16.exe}, @file{sh32.exe}, @file{bash.exe}, @file{tcsh.exe}.
+ When set, @code{system} will attempt to emulate redirection and pipes
+ internally, even if @samp{COMSPEC} or @samp{SHELL} point to a Unix-style
+ shell.
+
@item __system_handle_null_commands
When set (the default), commands internal to @file{COMMAND.COM} and
compatible shells which have no effect in the context of @code{system},
- Raw text -