1 /*************
2 * com_shell.c
3 ************/
4 #include <stdio.h>
5 
6 #include "ngspice/ngspice.h"
7 #include "ngspice/wordlist.h"
8 
9 #include "com_shell.h"
10 #include "streams.h"
11 #include "ngspice/cpextern.h"
12 
13 
14 #ifdef _WIN32
15 #define SHELL "cmd /k"
16 #else
17 #define SHELL "/bin/csh"
18 #endif
19 
20 /* Fork a shell. */
21 void
com_shell(wordlist * wl)22 com_shell(wordlist *wl)
23 {
24     char *shell = NULL;
25 
26     shell = getenv("SHELL");
27     if (shell == NULL) {
28         shell = SHELL;
29     }
30 
31     cp_ccon(FALSE);
32 
33 #ifdef HAVE_VFORK_H
34     /* XXX Needs to switch process groups.  Also, worry about suspend */
35     /* Only bother for efficiency */
36     pid = vfork();
37     if (pid == 0) {
38         fixdescriptors();
39         if (wl == NULL) {
40             execl(shell, shell, 0);
41             _exit(99);
42         } else {
43             char * const com = wl_flatten(wl);
44             execl("/bin/sh", "sh", "-c", com, 0);
45             txfree(com);
46         }
47     } else {
48         /* XXX Better have all these signals */
49         svint = signal(SIGINT, SIG_DFL);
50         svquit = signal(SIGQUIT, SIG_DFL);
51         svtstp = signal(SIGTSTP, SIG_DFL);
52         /* XXX Sig on proc group */
53         do
54             r = wait(NULL);
55         while ((r != pid) && pid != -1);
56         signal(SIGINT, (SIGNAL_FUNCTION) svint);
57         signal(SIGQUIT, (SIGNAL_FUNCTION) svquit);
58         signal(SIGTSTP, (SIGNAL_FUNCTION) svtstp);
59     }
60 #else
61     /* Easier to forget about changing the io descriptors. */
62     if (wl) {
63         char * const com = wl_flatten(wl);
64         if (system(com) == -1) {
65             (void) fprintf(cp_err, "Unable to execute \"%s\".\n", com);
66         }
67         txfree(com);
68     }
69     else {
70         if (system(shell) == -1) {
71             (void) fprintf(cp_err, "Unable to execute \"%s\".\n", shell);
72         }
73     }
74 #endif
75 
76 } /* end of function com_shell */
77 
78 
79 
80