1: /* $Header: /home/hyperion/mu/christos/src/sys/tcsh-6.00/RCS/sh.err.c,v 3.0 1991/07/04 21:49:28 christos Exp $ */ 2: /* 3: * sh.err.c: Error printing routines. There are lots of them 4: * and none does the right thing! 5: */ 6: /*- 7: * Copyright (c) 1980, 1991 The Regents of the University of California. 8: * All rights reserved. 9: * 10: * Redistribution and use in source and binary forms, with or without 11: * modification, are permitted provided that the following conditions 12: * are met: 13: * 1. Redistributions of source code must retain the above copyright 14: * notice, this list of conditions and the following disclaimer. 15: * 2. Redistributions in binary form must reproduce the above copyright 16: * notice, this list of conditions and the following disclaimer in the 17: * documentation and/or other materials provided with the distribution. 18: * 3. All advertising materials mentioning features or use of this software 19: * must display the following acknowledgement: 20: * This product includes software developed by the University of 21: * California, Berkeley and its contributors. 22: * 4. Neither the name of the University nor the names of its contributors 23: * may be used to endorse or promote products derived from this software 24: * without specific prior written permission. 25: * 26: * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 27: * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 28: * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 29: * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 30: * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 31: * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 32: * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 33: * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 34: * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 35: * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 36: * SUCH DAMAGE. 37: */ 38: #include "config.h" 39: #if !defined(lint) && !defined(pdp11) 40: static char *rcsid() 41: { return "$Id: sh.err.c,v 3.0 1991/07/04 21:49:28 christos Exp $"; } 42: #endif 43: 44: #define _h_tc_err /* Don't redefine the errors */ 45: #include "sh.h" 46: 47: /* 48: * C Shell 49: */ 50: 51: char *seterr = NULL; /* Holds last error if there was one */ 52: 53: #ifndef pdp11 54: #define ERR_FLAGS 0xf0000000 55: #define ERR_NAME 0x10000000 56: #define ERR_SILENT 0x20000000 57: #define ERR_OLD 0x40000000 58: #else 59: #define ERR_FLAGS 070000 60: #define ERR_NAME 010000 61: #define ERR_SILENT 020000 62: #define ERR_OLD 040000 63: #endif /* pdp11 */ 64: 65: static char *errorlist[] = 66: { 67: #define ERR_SYNTAX 0 68: "Syntax Error", 69: #define ERR_NOTALLOWED 1 70: "%s is not allowed", 71: #define ERR_WTOOLONG 2 72: "Word too long", 73: #define ERR_LTOOLONG 3 74: "$< line too long", 75: #define ERR_DOLZERO 4 76: "No file for $0", 77: #define ERR_DOLQUEST 5 78: "$? not allowed here", 79: #define ERR_INCBR 6 80: "Incomplete [] modifier", 81: #define ERR_EXPORD 7 82: "$ expansion must end before ]", 83: #define ERR_BADMOD 8 84: "Bad : modifier in $ (%c)", 85: #define ERR_SUBSCRIPT 9 86: "Subscript error", 87: #define ERR_BADNUM 10 88: "Badly formed number", 89: #define ERR_NOMORE 11 90: "No more words", 91: #define ERR_FILENAME 12 92: "Missing file name", 93: #define ERR_GLOB 13 94: "Internal glob error", 95: #define ERR_COMMAND 14 96: "Command not found", 97: #define ERR_TOOFEW 15 98: "Too few arguments", 99: #define ERR_TOOMANY 16 100: "Too many arguments", 101: #define ERR_DANGER 17 102: "Too dangerous to alias that", 103: #define ERR_EMPTYIF 18 104: "Empty if", 105: #define ERR_IMPRTHEN 19 106: "Improper then", 107: #define ERR_NOPAREN 20 108: "Words not parenthesized", 109: #define ERR_NOTFOUND 21 110: "%s not found", 111: #define ERR_MASK 22 112: "Improper mask", 113: #define ERR_LIMIT 23 114: "No such limit", 115: #define ERR_TOOLARGE 24 116: "Argument too large", 117: #define ERR_SCALEF 25 118: "Improper or unknown scale factor", 119: #define ERR_UNDVAR 26 120: "Undefined variable", 121: #define ERR_DEEP 27 122: "Directory stack not that deep", 123: #define ERR_BADSIG 28 124: "Bad signal number", 125: #define ERR_UNKSIG 29 126: "Unknown signal; kill -l lists signals", 127: #define ERR_VARBEGIN 30 128: "Variable name must begin with a letter", 129: #define ERR_VARTOOLONG 31 130: "Variable name too long", 131: #define ERR_VARALNUM 32 132: "Variable name must contain alphanumeric characters", 133: #define ERR_JOBCONTROL 33 134: "No job control in this shell", 135: #define ERR_EXPRESSION 34 136: "Expression Syntax", 137: #define ERR_NOHOMEDIR 35 138: "No home directory", 139: #define ERR_CANTCHANGE 36 140: "Can't change to home directory", 141: #define ERR_NULLCOM 37 142: "Invalid null command", 143: #define ERR_ASSIGN 38 144: "Assignment missing expression", 145: #define ERR_UNKNOWNOP 39 146: "Unknown operator", 147: #define ERR_AMBIG 40 148: "Ambiguous", 149: #define ERR_EXISTS 41 150: "%s: File exists", 151: #define ERR_ARGC 42 152: "Argument for -c ends in backslash", 153: #define ERR_INTR 43 154: "Interrupted", 155: #define ERR_RANGE 44 156: "Subscript out of range", 157: #define ERR_OVERFLOW 45 158: "Line overflow", 159: #define ERR_NOSUCHJOB 46 160: "No such job", 161: #define ERR_TERMINAL 47 162: "Can't from terminal", 163: #define ERR_NOTWHILE 48 164: "Not in while/foreach", 165: #define ERR_NOPROC 49 166: "No more processes", 167: #define ERR_NOMATCH 50 168: "No match", 169: #define ERR_MISSING 51 170: "Missing %c", 171: #define ERR_UNMATCHED 52 172: "Unmatched %c", 173: #define ERR_NOMEM 53 174: "Out of memory", 175: #define ERR_PIPE 54 176: "Can't make pipe", 177: #define ERR_SYSTEM 55 178: "%s: %s", 179: #define ERR_STRING 56 180: "%s", 181: #define ERR_JOBS 57 182: "Usage: jobs [ -l ]", 183: #define ERR_JOBARGS 58 184: "Arguments should be jobs or process id's", 185: #define ERR_JOBCUR 59 186: "No current job", 187: #define ERR_JOBPREV 60 188: "No previous job", 189: #define ERR_JOBPAT 61 190: "No job matches pattern", 191: #define ERR_NESTING 62 192: "Fork nesting > %d; maybe `...` loop", 193: #define ERR_JOBCTRLSUB 63 194: "No job control in subshells", 195: #define ERR_SYNC 64 196: "Sunc fault: Process %d not found", 197: #define ERR_STOPPED 65 198: #ifdef SUSPENDED 199: "%sThere are suspended jobs", 200: #else 201: "%sThere are stopped jobs", 202: #endif /* SUSPENDED */ 203: #define ERR_NODIR 66 204: "No other directory", 205: #define ERR_EMPTY 67 206: "Directory stack empty", 207: #define ERR_BADDIR 68 208: "Bad directory", 209: #define ERR_DIRUS 69 210: "Usage: %s [-lvn]%s", 211: #define ERR_HFLAG 70 212: "No operand for -h flag", 213: #define ERR_NOTLOGIN 71 214: "Not a login shell", 215: #define ERR_DIV0 72 216: "Division by 0", 217: #define ERR_MOD0 73 218: "Mod by 0", 219: #define ERR_BADSCALE 74 220: "Bad scaling; did you mean \"%s\"?", 221: #define ERR_SUSPLOG 75 222: "Can't suspend a login shell (yet)", 223: #define ERR_UNKUSER 76 224: "Unknown user: %s", 225: #define ERR_NOHOME 77 226: "No $home variable set", 227: #define ERR_HISTUS 78 228: "Usage: history [-rht] [# number of events]", 229: #define ERR_SPDOLLT 79 230: "$ or < not allowed with $# or $?", 231: #define ERR_NEWLINE 80 232: "Newline in variable name", 233: #define ERR_SPSTAR 81 234: "* not allowed with $# or $?", 235: #define ERR_DIGIT 82 236: "$?<digit> or $#<digit> not allowed", 237: #define ERR_VARILL 83 238: "Illegal variable name", 239: #define ERR_NLINDEX 84 240: "Newline in variable index", 241: #define ERR_EXPOVFL 85 242: "Expansion buffer overflow", 243: #define ERR_VARSYN 86 244: "Variable syntax", 245: #define ERR_BADBANG 87 246: "Bad ! form", 247: #define ERR_NOSUBST 88 248: "No previous substitute", 249: #define ERR_BADSUBST 89 250: "Bad substitute", 251: #define ERR_LHS 90 252: "No previous left hand side", 253: #define ERR_RHSLONG 91 254: "Right hand side too long", 255: #define ERR_BADBANGMOD 92 256: "Bad ! modifier: %c", 257: #define ERR_MODFAIL 93 258: "Modifier failed", 259: #define ERR_SUBOVFL 94 260: "Substitution buffer overflow", 261: #define ERR_BADBANGARG 95 262: "Bad ! arg selector", 263: #define ERR_NOSEARCH 96 264: "No prev search", 265: #define ERR_NOEVENT 97 266: "%s: Event not found", 267: #define ERR_TOOMANYRP 98 268: "Too many )'s", 269: #define ERR_TOOMANYLP 99 270: "Too many ('s", 271: #define ERR_BADPLP 100 272: "Badly placed (", 273: #define ERR_MISRED 101 274: "Missing name for redirect", 275: #define ERR_OUTRED 102 276: "Ambiguous output redirect", 277: #define ERR_REDPAR 103 278: "Can't << within ()'s", 279: #define ERR_INRED 104 280: "Ambiguous input redirect", 281: #define ERR_BADPLPS 105 282: "Badly placed ()'s", 283: #define ERR_VARMOD 106 284: "Unknown variable modifier", 285: #define ERR_ALIASLOOP 107 286: "Alias loop", 287: #define ERR_NOWATCH 108 288: "No $watch variable set", 289: #define ERR_NOSCHED 109 290: "No scheduled events", 291: #define ERR_SCHEDUSAGE 110 292: "Usage: sched -<item#>.\nUsage: sched [+]hh:mm <command>", 293: #define ERR_SCHEDEV 111 294: "Not that many scheduled events", 295: #define ERR_SCHEDCOM 112 296: "No command to run", 297: #define ERR_SCHEDTIME 113 298: "Invalid time for event", 299: #define ERR_SCHEDREL 114 300: "Relative time inconsistent with am/pm", 301: #define ERR_TCNOSTR 115 302: "Out of t_c_ string space", 303: #define ERR_SETTCUS 116 304: "Usage: settc %s [yes|no]", 305: #define ERR_TCCAP 117 306: "Unknown capability `%s'", 307: #define ERR_TCPARM 118 308: "Unknown t_c_ parameter `%%%c'", 309: #define ERR_TCARGS 119 310: "Too many arguments for `%s' (%d)", 311: #define ERR_TCNARGS 120 312: "`%s' requires %d arguments", 313: #define ERR_TCUSAGE 121 314: "Usage: echotc [-v|-s] [<capability> [<args>]]", 315: #define ERR_ARCH 122 316: "%s: %s. Wrong Architecture", 317: #define ERR_HISTLOOP 123 318: "!# History loop", 319: #define ERR_FILEINQ 124 320: "Malformed file inquiry", 321: #define ERR_SELOVFL 125 322: "Selector overflow", 323: #define ERR_INVALID 126 324: "Invalid Error" 325: }; 326: 327: /* 328: * The parser and scanner set up errors for later by calling seterr, 329: * which sets the variable err as a side effect; later to be tested, 330: * e.g. in process. 331: */ 332: void 333: /*VARARGS1*/ 334: #if __STDC__ 335: seterror(int id, ...) 336: #else 337: seterror(va_alist) 338: va_dcl 339: #endif 340: { 341: 342: if (seterr == 0) { 343: va_list va; 344: char berr[BUFSIZ]; 345: #if __STDC__ 346: va_start(va, id); 347: #else 348: int id; 349: va_start(va); 350: id = va_arg(va, int); 351: #endif 352: 353: if (id < 0 || id > sizeof(errorlist) / sizeof(errorlist[0])) 354: id = ERR_INVALID; 355: /* xprintf("error id is %d\n",id); /* jpn */ 356: xvsprintf(berr, errorlist[id], va); 357: va_end(va); 358: 359: seterr = strsave(berr); 360: } 361: } 362: 363: /* 364: * Print the error with the given id. 365: * 366: * Special ids: 367: * ERR_SILENT: Print nothing. 368: * ERR_OLD: Print the previously set error if one was there. 369: * otherwise return. 370: * ERR_NAME: If this bit is set, print the name of the function 371: * in bname 372: * 373: * This routine always resets or exits. The flag haderr 374: * is set so the routine who catches the unwind can propogate 375: * it if they want. 376: * 377: * Note that any open files at the point of error will eventually 378: * be closed in the routine process in sh.c which is the only 379: * place error unwinds are ever caught. 380: */ 381: void 382: /*VARARGS*/ 383: #if __STDC__ 384: stderror(int id, ...) 385: #else 386: stderror(va_alist) 387: va_dcl 388: #endif 389: { 390: va_list va; 391: register Char **v; 392: int flags; 393: 394: #if __STDC__ 395: va_start(va, id); 396: #else 397: int id; 398: 399: va_start(va); 400: id = va_arg(va, int); 401: #endif 402: 403: flags = id & ERR_FLAGS; 404: id &= ~ERR_FLAGS; 405: 406: if ((flags & ERR_OLD) && seterr == NULL) { 407: va_end(va); 408: return; 409: } 410: 411: if (id < 0 || id > sizeof(errorlist) / sizeof(errorlist[0])) 412: id = ERR_INVALID; 413: 414: /* 415: * Must flush before we print as we wish output before the error to go on 416: * (some form of) standard output, while output after goes on (some form 417: * of) diagnostic output. If didfds then output will go to 1/2 else to 418: * FSHOUT/FSHDIAG. See flush in sh.print.c. 419: */ 420: flush(); 421: haderr = 1; /* Now to diagnostic output */ 422: timflg = 0; /* This isn't otherwise reset */ 423: 424: /* jpn debug */ 425: /* 426: if (flags & ERR_NOMEM) 427: abort(); 428: */ 429: 430: if (!(flags & ERR_SILENT)) { 431: if (flags & ERR_NAME) 432: xprintf("%s: ", bname); 433: if ((flags & ERR_OLD)) 434: /* Old error. */ 435: xprintf("%s.\n", seterr); 436: else { 437: xvprintf(errorlist[id], va); 438: xprintf(".\n"); 439: } 440: } 441: va_end(va); 442: 443: if (seterr) { 444: xfree((ptr_t) seterr); 445: seterr = NULL; 446: } 447: 448: if (v = pargv) 449: pargv = 0, blkfree(v); 450: if (v = gargv) 451: gargv = 0, blkfree(v); 452: 453: didfds = 0; /* Forget about 0,1,2 */ 454: /* 455: * Go away if -e or we are a child shell 456: */ 457: if (exiterr || child) 458: xexit(1); 459: 460: /* 461: * Reset the state of the input. This buffered seek to end of file will 462: * also clear the while/foreach stack. 463: */ 464: btoeof(); 465: 466: set(STRstatus, Strsave(STR1)); 467: #ifdef BSDJOBS 468: if (tpgrp > 0) 469: (void) tcsetpgrp(FSHTTY, tpgrp); 470: #endif 471: reset(); /* Unwind */ 472: }