1 #include <stdlib.h> 2 #include <string.h> 3 #include <unistd.h> 4 #include <fcntl.h> 5 6 /* Need a way to have void used for ANSI, nothing for K&R. */ 7 #ifndef _ANSI 8 #undef _VOID 9 #define _VOID 10 #endif 11 12 /* -------- sh.h -------- */ 13 /* 14 * shell 15 */ 16 17 #define LINELIM 2100 18 #define NPUSH 8 /* limit to input nesting */ 19 20 #define NOFILE 20 /* Number of open files */ 21 #define NUFILE 10 /* Number of user-accessible files */ 22 #define FDBASE 10 /* First file usable by Shell */ 23 24 /* 25 * values returned by wait 26 */ 27 #define WAITSIG(s) ((s)&0177) 28 #define WAITVAL(s) (((s)>>8)&0377) 29 #define WAITCORE(s) (((s)&0200)!=0) 30 31 /* 32 * library and system defintions 33 */ 34 #ifdef __STDC__ 35 typedef void xint; /* base type of jmp_buf, for not broken compilers */ 36 #else 37 typedef char * xint; /* base type of jmp_buf, for broken compilers */ 38 #endif 39 40 /* 41 * shell components 42 */ 43 /* #include "area.h" */ 44 /* #include "word.h" */ 45 /* #include "io.h" */ 46 /* #include "var.h" */ 47 48 #define QUOTE 0200 49 50 #define NOBLOCK ((struct op *)NULL) 51 #define NOWORD ((char *)NULL) 52 #define NOWORDS ((char **)NULL) 53 #define NOPIPE ((int *)NULL) 54 55 /* 56 * Description of a command or an operation on commands. 57 * Might eventually use a union. 58 */ 59 struct op { 60 int type; /* operation type, see below */ 61 char **words; /* arguments to a command */ 62 struct ioword **ioact; /* IO actions (eg, < > >>) */ 63 struct op *left; 64 struct op *right; 65 char *str; /* identifier for case and for */ 66 }; 67 68 #define TCOM 1 /* command */ 69 #define TPAREN 2 /* (c-list) */ 70 #define TPIPE 3 /* a | b */ 71 #define TLIST 4 /* a [&;] b */ 72 #define TOR 5 /* || */ 73 #define TAND 6 /* && */ 74 #define TFOR 7 75 #define TDO 8 76 #define TCASE 9 77 #define TIF 10 78 #define TWHILE 11 79 #define TUNTIL 12 80 #define TELIF 13 81 #define TPAT 14 /* pattern in case */ 82 #define TBRACE 15 /* {c-list} */ 83 #define TASYNC 16 /* c & */ 84 85 /* 86 * actions determining the environment of a process 87 */ 88 #define BIT(i) (1<<(i)) 89 #define FEXEC BIT(0) /* execute without forking */ 90 91 /* 92 * flags to control evaluation of words 93 */ 94 #define DOSUB 1 /* interpret $, `, and quotes */ 95 #define DOBLANK 2 /* perform blank interpretation */ 96 #define DOGLOB 4 /* interpret [?* */ 97 #define DOKEY 8 /* move words with `=' to 2nd arg. list */ 98 #define DOTRIM 16 /* trim resulting string */ 99 100 #define DOALL (DOSUB|DOBLANK|DOGLOB|DOKEY|DOTRIM) 101 102 Extern char **dolv; 103 Extern int dolc; 104 Extern int exstat; 105 Extern char gflg; 106 Extern int talking; /* interactive (talking-type wireless) */ 107 Extern int execflg; 108 Extern int multiline; /* \n changed to ; */ 109 Extern struct op *outtree; /* result from parser */ 110 111 Extern xint *failpt; 112 Extern xint *errpt; 113 114 struct brkcon { 115 jmp_buf brkpt; 116 struct brkcon *nextlev; 117 } ; 118 Extern struct brkcon *brklist; 119 Extern int isbreak; 120 121 /* 122 * redirection 123 */ 124 struct ioword { 125 short io_unit; /* unit affected */ 126 short io_flag; /* action (below) */ 127 char *io_name; /* file name */ 128 }; 129 #define IOREAD 1 /* < */ 130 #define IOHERE 2 /* << (here file) */ 131 #define IOWRITE 4 /* > */ 132 #define IOCAT 8 /* >> */ 133 #define IOXHERE 16 /* ${}, ` in << */ 134 #define IODUP 32 /* >&digit */ 135 #define IOCLOSE 64 /* >&- */ 136 137 #define IODEFAULT (-1) /* token for default IO unit */ 138 139 Extern struct wdblock *wdlist; 140 Extern struct wdblock *iolist; 141 142 /* 143 * parsing & execution environment 144 */ 145 extern struct env { 146 char *linep; 147 struct io *iobase; 148 struct io *iop; 149 xint *errpt; 150 int iofd; 151 struct env *oenv; 152 } e; 153 154 /* 155 * flags: 156 * -e: quit on error 157 * -k: look for name=value everywhere on command line 158 * -n: no execution 159 * -t: exit after reading and executing one command 160 * -v: echo as read 161 * -x: trace 162 * -u: unset variables net diagnostic 163 */ 164 extern char *flag; 165 166 extern char *null; /* null value for variable */ 167 extern int intr; /* interrupt pending */ 168 169 Extern char *trap[_NSIG+1]; 170 Extern char ourtrap[_NSIG+1]; 171 Extern int trapset; /* trap pending */ 172 173 extern int heedint; /* heed interrupt signals */ 174 175 Extern int yynerrs; /* yacc */ 176 177 Extern char line[LINELIM]; 178 extern char *elinep; 179 180 /* 181 * other functions 182 */ 183 #ifdef __STDC__ 184 int (*inbuilt(char *s ))(void); 185 #else 186 int (*inbuilt())(); 187 #endif 188 189 #ifdef __FreeBSD__ 190 #define _PROTOTYPE(x,y) x ## y 191 #endif 192 193 _PROTOTYPE(char *rexecve , (char *c , char **v , char **envp )); 194 _PROTOTYPE(char *space , (int n )); 195 _PROTOTYPE(char *strsave , (char *s , int a )); 196 _PROTOTYPE(char *evalstr , (char *cp , int f )); 197 _PROTOTYPE(char *putn , (int n )); 198 _PROTOTYPE(char *itoa , (unsigned u , int n )); 199 _PROTOTYPE(char *unquote , (char *as )); 200 _PROTOTYPE(struct var *lookup , (char *n )); 201 _PROTOTYPE(int rlookup , (char *n )); 202 _PROTOTYPE(struct wdblock *glob , (char *cp , struct wdblock *wb )); 203 _PROTOTYPE(int subgetc , (int ec , int quoted )); 204 _PROTOTYPE(char **makenv , (void)); 205 _PROTOTYPE(char **eval , (char **ap , int f )); 206 _PROTOTYPE(int setstatus , (int s )); 207 _PROTOTYPE(int waitfor , (int lastpid , int canintr )); 208 209 _PROTOTYPE(void onintr , (int s )); /* SIGINT handler */ 210 211 _PROTOTYPE(int newenv , (int f )); 212 _PROTOTYPE(void quitenv , (void)); 213 _PROTOTYPE(void err , (char *s )); 214 _PROTOTYPE(int anys , (char *s1 , char *s2 )); 215 _PROTOTYPE(int any , (int c , char *s )); 216 _PROTOTYPE(void next , (int f )); 217 _PROTOTYPE(void setdash , (void)); 218 _PROTOTYPE(void onecommand , (void)); 219 _PROTOTYPE(void runtrap , (int i )); 220 _PROTOTYPE(void xfree , (char *s )); 221 _PROTOTYPE(int letter , (int c )); 222 _PROTOTYPE(int digit , (int c )); 223 _PROTOTYPE(int letnum , (int c )); 224 _PROTOTYPE(int gmatch , (char *s , char *p )); 225 226 /* 227 * error handling 228 */ 229 _PROTOTYPE(void leave , (void)); /* abort shell (or fail in subshell) */ 230 _PROTOTYPE(void fail , (void)); /* fail but return to process next command */ 231 _PROTOTYPE(void warn , (char *s )); 232 _PROTOTYPE(void sig , (int i )); /* default signal handler */ 233 234 /* -------- var.h -------- */ 235 236 struct var { 237 char *value; 238 char *name; 239 struct var *next; 240 char status; 241 }; 242 #define COPYV 1 /* flag to setval, suggesting copy */ 243 #define RONLY 01 /* variable is read-only */ 244 #define EXPORT 02 /* variable is to be exported */ 245 #define GETCELL 04 /* name & value space was got with getcell */ 246 247 Extern struct var *vlist; /* dictionary */ 248 249 Extern struct var *homedir; /* home directory */ 250 Extern struct var *prompt; /* main prompt */ 251 Extern struct var *cprompt; /* continuation prompt */ 252 Extern struct var *path; /* search path for commands */ 253 Extern struct var *shell; /* shell to interpret command files */ 254 Extern struct var *ifs; /* field separators */ 255 256 _PROTOTYPE(int yyparse , (void)); 257 _PROTOTYPE(struct var *lookup , (char *n )); 258 _PROTOTYPE(void setval , (struct var *vp , char *val )); 259 _PROTOTYPE(void nameval , (struct var *vp , char *val , char *name )); 260 _PROTOTYPE(void export , (struct var *vp )); 261 _PROTOTYPE(void ronly , (struct var *vp )); 262 _PROTOTYPE(int isassign , (char *s )); 263 _PROTOTYPE(int checkname , (char *cp )); 264 _PROTOTYPE(int assign , (char *s , int cf )); 265 _PROTOTYPE(void putvlist , (int f , int out )); 266 _PROTOTYPE(int eqname , (char *n1 , char *n2 )); 267 268 _PROTOTYPE(int execute , (struct op *t , int *pin , int *pout , int act )); 269 270 /* -------- io.h -------- */ 271 /* io buffer */ 272 struct iobuf { 273 unsigned id; /* buffer id */ 274 char buf[512]; /* buffer */ 275 char *bufp; /* pointer into buffer */ 276 char *ebufp; /* pointer to end of buffer */ 277 }; 278 279 /* possible arguments to an IO function */ 280 struct ioarg { 281 char *aword; 282 char **awordlist; 283 int afile; /* file descriptor */ 284 unsigned afid; /* buffer id */ 285 long afpos; /* file position */ 286 struct iobuf *afbuf; /* buffer for this file */ 287 }; 288 Extern struct ioarg ioargstack[NPUSH]; 289 #define AFID_NOBUF (~0) 290 #define AFID_ID 0 291 292 /* an input generator's state */ 293 struct io { 294 int (*iofn)(_VOID); 295 struct ioarg *argp; 296 int peekc; 297 char prev; /* previous character read by readc() */ 298 char nlcount; /* for `'s */ 299 char xchar; /* for `'s */ 300 char task; /* reason for pushed IO */ 301 }; 302 Extern struct io iostack[NPUSH]; 303 #define XOTHER 0 /* none of the below */ 304 #define XDOLL 1 /* expanding ${} */ 305 #define XGRAVE 2 /* expanding `'s */ 306 #define XIO 3 /* file IO */ 307 308 /* in substitution */ 309 #define INSUB() (e.iop->task == XGRAVE || e.iop->task == XDOLL) 310 311 /* 312 * input generators for IO structure 313 */ 314 _PROTOTYPE(int nlchar , (struct ioarg *ap )); 315 _PROTOTYPE(int strchar , (struct ioarg *ap )); 316 _PROTOTYPE(int qstrchar , (struct ioarg *ap )); 317 _PROTOTYPE(int filechar , (struct ioarg *ap )); 318 _PROTOTYPE(int herechar , (struct ioarg *ap )); 319 _PROTOTYPE(int linechar , (struct ioarg *ap )); 320 _PROTOTYPE(int gravechar , (struct ioarg *ap , struct io *iop )); 321 _PROTOTYPE(int qgravechar , (struct ioarg *ap , struct io *iop )); 322 _PROTOTYPE(int dolchar , (struct ioarg *ap )); 323 _PROTOTYPE(int wdchar , (struct ioarg *ap )); 324 _PROTOTYPE(void scraphere , (void)); 325 _PROTOTYPE(void freehere , (int area )); 326 _PROTOTYPE(void gethere , (void)); 327 _PROTOTYPE(void markhere , (char *s , struct ioword *iop )); 328 _PROTOTYPE(int herein , (char *hname , int xdoll )); 329 _PROTOTYPE(int run , (struct ioarg *argp , int (*f)(_VOID))); 330 331 /* 332 * IO functions 333 */ 334 _PROTOTYPE(int eofc , (void)); 335 _PROTOTYPE(int getc , (int ec )); 336 _PROTOTYPE(int readc , (void)); 337 _PROTOTYPE(void unget , (int c )); 338 _PROTOTYPE(void ioecho , (int c )); 339 _PROTOTYPE(void prs , (char *s )); 340 _PROTOTYPE(void putc , (int c )); 341 _PROTOTYPE(void prn , (unsigned u )); 342 _PROTOTYPE(void closef , (int i )); 343 _PROTOTYPE(void closeall , (void)); 344 345 /* 346 * IO control 347 */ 348 _PROTOTYPE(void pushio , (struct ioarg *argp , int (*fn)(_VOID))); 349 _PROTOTYPE(int remap , (int fd )); 350 _PROTOTYPE(int openpipe , (int *pv )); 351 _PROTOTYPE(void closepipe , (int *pv )); 352 _PROTOTYPE(struct io *setbase , (struct io *ip )); 353 354 extern struct ioarg temparg; /* temporary for PUSHIO */ 355 #define PUSHIO(what,arg,gen) ((temparg.what = (arg)),pushio(&temparg,(gen))) 356 #define RUN(what,arg,gen) ((temparg.what = (arg)), run(&temparg,(gen))) 357 358 /* -------- word.h -------- */ 359 #ifndef WORD_H 360 #define WORD_H 1 361 struct wdblock { 362 short w_bsize; 363 short w_nword; 364 /* bounds are arbitrary */ 365 char *w_words[1]; 366 }; 367 368 _PROTOTYPE(struct wdblock *addword , (char *wd , struct wdblock *wb )); 369 _PROTOTYPE(struct wdblock *newword , (int nw )); 370 _PROTOTYPE(char **getwords , (struct wdblock *wb )); 371 #endif 372 373 /* -------- area.h -------- */ 374 375 /* 376 * storage allocation 377 */ 378 _PROTOTYPE(char *getcell , (unsigned nbytes )); 379 _PROTOTYPE(void garbage , (void)); 380 _PROTOTYPE(void setarea , (char *cp , int a )); 381 _PROTOTYPE(int getarea , (char *cp )); 382 _PROTOTYPE(void freearea , (int a )); 383 _PROTOTYPE(void freecell , (char *cp )); 384 385 Extern int areanum; /* current allocation area */ 386 387 #define NEW(type) (type *)getcell(sizeof(type)) 388 #define DELETE(obj) freecell((char *)obj) 389