13e12c5d1SDavid du Colombier #include "lib.h" 23e12c5d1SDavid du Colombier #include <unistd.h> 33e12c5d1SDavid du Colombier #include <errno.h> 43e12c5d1SDavid du Colombier #include <string.h> 5*219b2ee8SDavid du Colombier #include <signal.h> 63e12c5d1SDavid du Colombier #include "sys9.h" 73e12c5d1SDavid du Colombier 83e12c5d1SDavid du Colombier extern char **environ; 93e12c5d1SDavid du Colombier 103e12c5d1SDavid du Colombier int 113e12c5d1SDavid du Colombier execve(const char *name, const char *argv[], const char *envp[]) 123e12c5d1SDavid du Colombier { 133e12c5d1SDavid du Colombier int n, f, i; 143e12c5d1SDavid du Colombier char **e, *ss, *se; 153e12c5d1SDavid du Colombier Fdinfo *fi; 16*219b2ee8SDavid du Colombier unsigned long flags; 173e12c5d1SDavid du Colombier char nam[NAMELEN+5]; 183e12c5d1SDavid du Colombier char buf[1000]; 193e12c5d1SDavid du Colombier 20*219b2ee8SDavid du Colombier _RFORK(RFCENVG); 213e12c5d1SDavid du Colombier /* 223e12c5d1SDavid du Colombier * To pass _fdinfo[] across exec, put lines like 233e12c5d1SDavid du Colombier * fd flags oflags 243e12c5d1SDavid du Colombier * in $_fdinfo (for open fd's) 253e12c5d1SDavid du Colombier */ 263e12c5d1SDavid du Colombier 273e12c5d1SDavid du Colombier f = _CREATE("#e/_fdinfo", OWRITE, 0666); 283e12c5d1SDavid du Colombier ss = buf; 293e12c5d1SDavid du Colombier for(n = 0; n<OPEN_MAX; n++){ 303e12c5d1SDavid du Colombier fi = &_fdinfo[n]; 31*219b2ee8SDavid du Colombier flags = fi->flags; 32*219b2ee8SDavid du Colombier if(flags&FD_CLOEXEC){ 333e12c5d1SDavid du Colombier _CLOSE(n); 343e12c5d1SDavid du Colombier fi->flags = 0; 353e12c5d1SDavid du Colombier fi->oflags = 0; 36*219b2ee8SDavid du Colombier }else if(flags&FD_ISOPEN){ 373e12c5d1SDavid du Colombier ss = _ultoa(ss, n); 383e12c5d1SDavid du Colombier *ss++ = ' '; 39*219b2ee8SDavid du Colombier ss = _ultoa(ss, flags); 403e12c5d1SDavid du Colombier *ss++ = ' '; 413e12c5d1SDavid du Colombier ss = _ultoa(ss, fi->oflags); 423e12c5d1SDavid du Colombier *ss++ = '\n'; 433e12c5d1SDavid du Colombier if(ss-buf < sizeof(buf)-50){ 443e12c5d1SDavid du Colombier _WRITE(f, buf, ss-buf); 453e12c5d1SDavid du Colombier ss = buf; 463e12c5d1SDavid du Colombier } 473e12c5d1SDavid du Colombier } 483e12c5d1SDavid du Colombier } 493e12c5d1SDavid du Colombier if(ss > buf) 503e12c5d1SDavid du Colombier _WRITE(f, buf, ss-buf); 513e12c5d1SDavid du Colombier _CLOSE(f); 52*219b2ee8SDavid du Colombier /* 53*219b2ee8SDavid du Colombier * To pass _sighdlr[] across exec, set $_sighdlr 54*219b2ee8SDavid du Colombier * to list of blank separated fd's that have 55*219b2ee8SDavid du Colombier * SIG_IGN (the rest will be SIG_DFL). 56*219b2ee8SDavid du Colombier * We write the variable, even if no signals 57*219b2ee8SDavid du Colombier * are ignored, in case the current value of the 58*219b2ee8SDavid du Colombier * variable ignored some. 59*219b2ee8SDavid du Colombier */ 60*219b2ee8SDavid du Colombier f = _CREATE("#e/_sighdlr", OWRITE, 0666); 61*219b2ee8SDavid du Colombier if(f >= 0){ 62*219b2ee8SDavid du Colombier ss = buf; 63*219b2ee8SDavid du Colombier for(i = 0, n=0; i <=MAXSIG && ss < &buf[sizeof(buf)]-5; i++) { 64*219b2ee8SDavid du Colombier if(_sighdlr[i] == SIG_IGN) { 65*219b2ee8SDavid du Colombier ss = _ultoa(ss, i); 66*219b2ee8SDavid du Colombier *ss++ = ' '; 67*219b2ee8SDavid du Colombier } 68*219b2ee8SDavid du Colombier } 69*219b2ee8SDavid du Colombier _WRITE(f, buf, ss-buf); 70*219b2ee8SDavid du Colombier _CLOSE(f); 71*219b2ee8SDavid du Colombier } 72*219b2ee8SDavid du Colombier if(envp){ 733e12c5d1SDavid du Colombier strcpy(nam, "#e/"); 743e12c5d1SDavid du Colombier for(e = envp; (ss = *e); e++) { 753e12c5d1SDavid du Colombier se = strchr(ss, '='); 763e12c5d1SDavid du Colombier if(!se || ss==se) 773e12c5d1SDavid du Colombier continue; /* what is name? value? */ 783e12c5d1SDavid du Colombier n = se-ss; 793e12c5d1SDavid du Colombier if(n > NAMELEN-1) 803e12c5d1SDavid du Colombier n = NAMELEN-1; 813e12c5d1SDavid du Colombier memcpy(nam+3, ss, n); 823e12c5d1SDavid du Colombier nam[3+n] = 0; 833e12c5d1SDavid du Colombier f = _CREATE(nam, OWRITE, 0666); 843e12c5d1SDavid du Colombier if(f < 0) 853e12c5d1SDavid du Colombier continue; 863e12c5d1SDavid du Colombier se++; /* past = */ 873e12c5d1SDavid du Colombier n = strlen(se); 883e12c5d1SDavid du Colombier /* temporarily decode nulls (see _envsetup()) */ 893e12c5d1SDavid du Colombier for(i=0; i < n; i++) 903e12c5d1SDavid du Colombier if(se[i] == 1) 913e12c5d1SDavid du Colombier se[i] = 0; 923e12c5d1SDavid du Colombier _WRITE(f, se, n); 933e12c5d1SDavid du Colombier /* put nulls back */ 943e12c5d1SDavid du Colombier for(i=0; i < n; i++) 953e12c5d1SDavid du Colombier if(se[i] == 0) 963e12c5d1SDavid du Colombier se[i] = 1; 973e12c5d1SDavid du Colombier _CLOSE(f); 983e12c5d1SDavid du Colombier } 993e12c5d1SDavid du Colombier } 1003e12c5d1SDavid du Colombier n = _EXEC(name, argv); 1013e12c5d1SDavid du Colombier _syserrno(); 1023e12c5d1SDavid du Colombier return n; 1033e12c5d1SDavid du Colombier } 104