📄 plan9.c
字号:
#include "mk.h"char *shell = "/bin/rc";char *shellname = "rc";static Word *encodenulls(char*, int);voidreadenv(void){ char *p; int envf, f; Dir *e; char nam[1024]; int i, n, len; Word *w; rfork(RFENVG); /* use copy of the current environment variables */ envf = open("/env", OREAD); if(envf < 0) return; while((n = dirread(envf, &e)) > 0){ for(i = 0; i < n; i++){ len = e[i].length; /* don't import funny names, NULL values, * or internal mk variables */ if(len <= 0 || *shname(e[i].name) != '\0') continue; if (symlook(e[i].name, S_INTERNAL, 0)) continue; sprint(nam, "/env/%s", e[i].name); f = open(nam, OREAD); if(f < 0) continue; p = Malloc(len+1); if(read(f, p, len) != len){ perror(nam); close(f); continue; } close(f); if (p[len-1] == 0) len--; else p[len] = 0; w = encodenulls(p, len); free(p); p = strdup(e[i].name); setvar(p, (void *) w); symlook(p, S_EXPORTED, (void*)"")->u.ptr = ""; } free(e); } close(envf);}/* break string of values into words at 01's or nulls*/static Word *encodenulls(char *s, int n){ Word *w, *head; char *cp; head = w = 0; while (n-- > 0) { for (cp = s; *cp && *cp != '\0'; cp++) n--; *cp = 0; if (w) { w->next = newword(s); w = w->next; } else head = w = newword(s); s = cp+1; } if (!head) head = newword(""); return head;}/* as well as 01's, change blanks to nulls, so that rc will * treat the words as separate arguments */voidexportenv(Envy *e){ int f, n, hasvalue, first; Word *w; Symtab *sy; char nam[256]; for(;e->name; e++){ sy = symlook(e->name, S_VAR, 0); if (e->values == 0 || e->values->s == 0 || e->values->s[0] == 0) hasvalue = 0; else hasvalue = 1; if(sy == 0 && !hasvalue) /* non-existant null symbol */ continue; sprint(nam, "/env/%s", e->name); if (sy != 0 && !hasvalue) { /* Remove from environment */ /* we could remove it from the symbol table * too, but we're in the child copy, and it * would still remain in the parent's table. */ remove(nam); delword(e->values); e->values = 0; /* memory leak */ continue; } f = create(nam, OWRITE, 0666L); if(f < 0) { fprint(2, "can't create %s, f=%d\n", nam, f); perror(nam); continue; } first = 1; for (w = e->values; w; w = w->next) { n = strlen(w->s); if (n) { if(first) first = 0; else{ if (write (f, "\0", 1) != 1) perror(nam); } if (write(f, w->s, n) != n) perror(nam); } } close(f); }}intwaitfor(char *msg){ Waitmsg *w; int pid; if((w=wait()) == nil) return -1; strecpy(msg, msg+ERRMAX, w->msg); pid = w->pid; free(w); return pid;}voidexpunge(int pid, char *msg){ postnote(PNPROC, pid, msg);}intexecsh(char *args, char *cmd, Bufblock *buf, Envy *e){ char *p; int tot, n, pid, in[2], out[2]; if(buf && pipe(out) < 0){ perror("pipe"); Exit(); } pid = rfork(RFPROC|RFFDG|RFENVG); if(pid < 0){ perror("mk rfork"); Exit(); } if(pid == 0){ if(buf) close(out[0]); if(pipe(in) < 0){ perror("pipe"); Exit(); } pid = fork(); if(pid < 0){ perror("mk fork"); Exit(); } if(pid != 0){ dup(in[0], 0); if(buf){ dup(out[1], 1); close(out[1]); } close(in[0]); close(in[1]); if (e) exportenv(e); if(shflags) execl(shell, shellname, shflags, args, nil); else execl(shell, shellname, args, nil); perror(shell); _exits("exec"); } close(out[1]); close(in[0]); p = cmd+strlen(cmd); while(cmd < p){ n = write(in[1], cmd, p-cmd); if(n < 0) break; cmd += n; } close(in[1]); _exits(0); } if(buf){ close(out[1]); tot = 0; for(;;){ if (buf->current >= buf->end) growbuf(buf); n = read(out[0], buf->current, buf->end-buf->current); if(n <= 0) break; buf->current += n; tot += n; } if (tot && buf->current[-1] == '\n') buf->current--; close(out[0]); } return pid;}intpipecmd(char *cmd, Envy *e, int *fd){ int pid, pfd[2]; if(DEBUG(D_EXEC)) fprint(1, "pipecmd='%s'\n", cmd);/**/ if(fd && pipe(pfd) < 0){ perror("pipe"); Exit(); } pid = rfork(RFPROC|RFFDG|RFENVG); if(pid < 0){ perror("mk fork"); Exit(); } if(pid == 0){ if(fd){ close(pfd[0]); dup(pfd[1], 1); close(pfd[1]); } if(e) exportenv(e); if(shflags) execl(shell, shellname, shflags, "-c", cmd, nil); else execl(shell, shellname, "-c", cmd, nil); perror(shell); _exits("exec"); } if(fd){ close(pfd[1]); *fd = pfd[0]; } return pid;}voidExit(void){ while(waitpid() >= 0) ; exits("error");}intnotifyf(void *a, char *msg){ static int nnote; USED(a); if(++nnote > 100){ /* until andrew fixes his program */ fprint(2, "mk: too many notes\n"); notify(0); abort(); } if(strcmp(msg, "interrupt")!=0 && strcmp(msg, "hangup")!=0) return 0; killchildren(msg); return -1;}voidcatchnotes(){ atnotify(notifyf, 1);}char*maketmp(void){ static char temp[] = "/tmp/mkargXXXXXX"; mktemp(temp); return temp;}intchgtime(char *name){ Dir sbuf; if(access(name, AEXIST) >= 0) { nulldir(&sbuf); sbuf.mtime = time((long *)0); return dirwstat(name, &sbuf); } return close(create(name, OWRITE, 0666));}voidrcopy(char **to, Resub *match, int n){ int c; char *p; *to = match->sp; /* stem0 matches complete target */ for(to++, match++; --n > 0; to++, match++){ if(match->sp && match->ep){ p = match->ep; c = *p; *p = 0; *to = strdup(match->sp); *p = c; } else *to = 0; }}voiddirtime(char *dir, char *path){ int i, fd, n; Dir *d; char buf[4096]; fd = open(dir, OREAD); if(fd >= 0){ while((n = dirread(fd, &d)) > 0){ for(i=0; i<n; i++){ if(d[i].mtime == 0) /* yeah, this is likely */ continue; sprint(buf, "%s%s", path, d[i].name); if(symlook(buf, S_TIME, 0)) continue; symlook(strdup(buf), S_TIME, (void*)d[i].mtime)->u.value = d[i].mtime; } free(d); } close(fd); }}voidbulkmtime(char *dir){ char buf[4096]; char *ss, *s, *sym; if(dir){ sym = dir; s = dir; if(strcmp(dir, "/") == 0) strcpy(buf, dir); else sprint(buf, "%s/", dir); }else{ s = "."; sym = ""; buf[0] = 0; } if(symlook(sym, S_BULKED, 0)) return; ss = strdup(sym); symlook(ss, S_BULKED, (void*)ss); dirtime(s, buf);}ulongmkmtime(char *name, int force){ Dir *d; char *s, *ss, carry; ulong t; Symtab *sym; char buf[4096]; strcpy(buf, name); cleanname(buf); name = buf; s = utfrrune(name, '/'); if(s == name) s++; if(s){ ss = name; carry = *s; *s = 0; }else{ ss = 0; carry = 0; } bulkmtime(ss); if(carry) *s = carry; if(!force){ sym = symlook(name, S_TIME, 0); if(sym) return sym->u.value; return 0; } if((d = dirstat(name)) == nil) return 0; t = d->mtime; free(d); return t;}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -