Annotation of coherent/a/usr/bob/korn/c_ksh.c, revision 1.1

1.1     ! root        1: /*
        !             2:  * built-in Korn commands: c_*
        !             3:  */
        !             4: 
        !             5: static char *RCSid = "$Header: c_ksh.c,v 3.1 88/11/03 09:14:21 egisin Exp $";
        !             6: 
        !             7: #include <stddef.h>
        !             8: #include <stdlib.h>
        !             9: #include <stdio.h>
        !            10: #include <string.h>
        !            11: #include <errno.h>
        !            12: #include <setjmp.h>
        !            13: #include <signal.h>
        !            14: #include "sh.h"
        !            15: #include "table.h"
        !            16: 
        !            17: int
        !            18: c_hash(wp)
        !            19:        register char **wp;
        !            20: {
        !            21:        register int i;
        !            22:        register struct tbl *tp, **p;
        !            23: 
        !            24:        wp++;
        !            25:        if (*wp == NULL) {
        !            26:                for (p = tsort(&commands); (tp = *p++) != NULL; )
        !            27:                        if ((tp->flag&ISSET))
        !            28:                                printf("%s\n", tp->val.s);
        !            29:                return 0;
        !            30:        }
        !            31: 
        !            32:        if (strcmp(*wp, "-r") == 0)
        !            33:                flushcom(1);
        !            34:        while (*wp != NULL)
        !            35:                findcom(*wp++, 1);
        !            36:        return 0;
        !            37: }
        !            38: 
        !            39: int
        !            40: c_print(wp)
        !            41:        register char **wp;
        !            42: {
        !            43:        int nl = 1;
        !            44:        int expand = 1;
        !            45:        FILE *f = stdout;
        !            46: 
        !            47:        for (wp++; *wp != NULL && **wp == '-'; wp++) {
        !            48:                register char *s = *wp + 1;
        !            49:                if (*s == '\0') {
        !            50:                        wp++;
        !            51:                        break;
        !            52:                }
        !            53:                while (*s) switch (*s++) {
        !            54:                  case 'n':
        !            55:                        nl = 0;
        !            56:                        break;
        !            57:                  case 'e':
        !            58:                        expand = 1;
        !            59:                        break;
        !            60:                  case 'r':
        !            61:                        expand = 0;
        !            62:                        break;
        !            63:                  case 'u':
        !            64:                        if (!digit(*s) || (f = shf[*s++-'0']) == NULL)
        !            65:                                errorf("bad -u argument\n");
        !            66:                        break;
        !            67:                }
        !            68:        }
        !            69: 
        !            70:        while (*wp != NULL) {
        !            71:                register char *s = *wp;
        !            72:                register int c;
        !            73:                while ((c = *s++) != '\0')
        !            74:                        if (expand && c == '\\') {
        !            75:                                switch ((c = *s++)) {
        !            76:                                case 'b': c = '\b'; break;
        !            77:                                case 'c': nl = 0; continue; /* AT&T brain damage */
        !            78:                                case 'f': c = '\f'; break;
        !            79:                                case 'n': c = '\n'; break;
        !            80:                                case 'r': c = '\r'; break;
        !            81:                                case 't': c = '\t'; break;
        !            82:                                case 'v': c = 0x0B; break;
        !            83:                                case '0': case '1': case '2': case '3':
        !            84:                                case '4': case '5': case '6': case '7':
        !            85:                                        c = c - '0';
        !            86:                                        if (*s >= '0' && *s <= '7')
        !            87:                                                c = 8*c + *s++ - '0';
        !            88:                                        if (*s >= '0' && *s <= '7')
        !            89:                                                c = 8*c + *s++ - '0';
        !            90:                                        break;
        !            91:                                case '\\': break;
        !            92:                                default:
        !            93:                                        putc('\\', f);
        !            94:                                }
        !            95:                                putc(c, f);
        !            96:                        } else
        !            97:                                putc(c, f);
        !            98:                if (*++wp != NULL)
        !            99:                        putc(' ', f);
        !           100:        }
        !           101:        if (nl)
        !           102:                putc('\n', f);
        !           103:        return 0;
        !           104: }
        !           105: 
        !           106: /* todo: handle case where id is both lexical and command */
        !           107: int
        !           108: c_whence(wp)
        !           109:        register char **wp;
        !           110: {
        !           111:        register struct tbl *tp;
        !           112:        char *id;
        !           113:        int vflag = 0;
        !           114: 
        !           115:        for (wp++; (id = *wp) != NULL && *id == '-'; wp++)
        !           116:                if (id[1] == 'v')
        !           117:                        vflag = 1;
        !           118: 
        !           119:        while ((id = *wp++) != NULL) {
        !           120:                tp = tsearch(&lexicals, id, hash(id));
        !           121:                if (tp == NULL)
        !           122:                        tp = findcom(id, 1);
        !           123:                if (vflag)
        !           124:                        switch ((tp == NULL) ? CNONE : tp->type) {
        !           125:                          case CNONE:
        !           126:                                printf("%s is unknown\n", id);
        !           127:                                break;
        !           128:                          case CSHELL:
        !           129:                                printf("%s is a shell builtin\n", id);
        !           130:                                break;
        !           131:                          case CFUNC:
        !           132:                                printf("%s is a function\n", id);
        !           133:                                fptreef(stdout, "function %s %T\n", id, tp->val.t);
        !           134:                                break;
        !           135:                          case CEXEC:
        !           136:                                printf("%s is %s\n", id,
        !           137:                                       (tp->flag&ISSET) ? tp->val.s : "unknown");
        !           138:                                break;
        !           139:                          case CALIAS:
        !           140:                                printf("%s is the alias '%s'\n", id, tp->val.s);
        !           141:                                break;
        !           142:                          case CKEYWD:
        !           143:                                printf("%s is a shell keyword\n", id);
        !           144:                                break;
        !           145:                          default:
        !           146:                                printf("%s is *GOK*\n", id);
        !           147:                                break;
        !           148:                        }
        !           149:                else
        !           150:                        switch ((tp == NULL) ? CNONE : tp->type) {
        !           151:                          case CNONE:
        !           152:                                printf("\n");
        !           153:                                break;
        !           154:                          case CSHELL:
        !           155:                                printf("builtin %s\n", id);
        !           156:                                break;
        !           157:                          case CFUNC:
        !           158:                                printf("%s\n", id);
        !           159:                                break;
        !           160:                          case CEXEC:
        !           161:                                printf("%s\n", (tp->flag&ISSET) ? tp->val.s : id);
        !           162:                                break;
        !           163:                          case CALIAS:
        !           164:                                printf("%s\n", tp->val.s);
        !           165:                                break;
        !           166:                          case CKEYWD:
        !           167:                                printf("%s\n", id);
        !           168:                                break;
        !           169:                          default:
        !           170:                                printf("*GOK*\n");
        !           171:                                break;
        !           172:                        }
        !           173:        }
        !           174:        return 0;
        !           175: }
        !           176: 
        !           177: int
        !           178: c_typeset(wp)
        !           179:        register char **wp;
        !           180: {
        !           181:        register char *id;
        !           182:        struct block *l = e.loc;
        !           183:        register struct tbl *vp, **p;
        !           184:        int fset = 0, fclr = 0;
        !           185:        int thing = 0, func = 0;
        !           186: 
        !           187:        for (wp++; (id = *wp) != NULL && (*id == '-' || *id == '+'); wp++) {
        !           188:                int flag = 0;
        !           189:                thing = *id;
        !           190:                while (*++id != '\0') switch (*id) {
        !           191:                  case 'f':
        !           192:                        flag |= FUNCT;
        !           193:                        func = 1;
        !           194:                        break;
        !           195:                  case 'i':
        !           196:                        flag |= INTEGER;
        !           197:                        break;
        !           198:                  case 'r':
        !           199:                        flag |= RDONLY;
        !           200:                        break;
        !           201:                  case 'x':
        !           202:                        flag |= EXPORT;
        !           203:                        break;
        !           204:                  case 't':
        !           205:                        flag |= TRACE;
        !           206:                        break;
        !           207:                  default:
        !           208:                        errorf("unknown flag -%c\n", *id);
        !           209:                }
        !           210:                if (flag != 0) { /* + or - with options */
        !           211:                        if (thing == '-')
        !           212:                                fset |= flag;
        !           213:                        else
        !           214:                                fclr |= flag;
        !           215:                        thing = 0;
        !           216:                }
        !           217:        }
        !           218: 
        !           219:        /* list variables and attributes */
        !           220:        if (*wp == NULL) {
        !           221:                for (l = e.loc; l != NULL; l = l->next) {
        !           222:                    for (p = tsort((func==0) ? &l->vars : &l->funs);
        !           223:                         (vp = *p++) != NULL; )
        !           224:                        if ((vp->flag&ISSET))
        !           225:                            if (thing == 0 && fclr == 0 && fset == 0) {
        !           226:                                printf("typeset ");
        !           227:                                if ((vp->flag&INTEGER))
        !           228:                                        printf("-i ");
        !           229:                                if ((vp->flag&EXPORT))
        !           230:                                        printf("-x ");
        !           231:                                if ((vp->flag&RDONLY))
        !           232:                                        printf("-r ");
        !           233:                                if ((vp->flag&TRACE)) 
        !           234:                                        printf("-t ");
        !           235:                                printf("%s\n", vp->name);
        !           236:                            } else
        !           237:                            if (thing == '+' ||
        !           238:                                fclr && (vp->flag&fclr) == fclr) {
        !           239:                                printf("%s\n", vp->name);
        !           240:                            } else
        !           241:                            if (thing == '-' ||
        !           242:                                fset && (vp->flag&fset) == fset) {
        !           243:                                if (fset&FUNCT)
        !           244:                                    printf("function %s\n", vp->name);
        !           245:                                else
        !           246:                                    printf("%s=%s\n", vp->name, strval(vp));
        !           247:                            }
        !           248:                }
        !           249:                return (0);
        !           250:        }
        !           251: 
        !           252:        fset |= LOCAL;
        !           253:        for (; *wp != NULL; wp++)
        !           254: #if 0
        !           255:                if (func) {
        !           256:                } else
        !           257: #endif
        !           258:                if (typeset(*wp, fset, fclr) == NULL)
        !           259:                        errorf("%s: not identifier\n", *wp);
        !           260:        return 0;
        !           261: }
        !           262:        
        !           263: int
        !           264: c_alias(wp)
        !           265:        register char **wp;
        !           266: {
        !           267:        register struct table *t = &lexicals;
        !           268:        register struct tbl *ap, **p;
        !           269:        register int i;
        !           270:        int rv = 0;
        !           271: 
        !           272:        if (*++wp != NULL && strcmp(*wp, "-d") == 0) {
        !           273:                t = &homedirs;
        !           274:                wp++;
        !           275:        }
        !           276: 
        !           277:        if (*wp == NULL)
        !           278:                for (p = tsort(t); (ap = *p++) != NULL; )
        !           279:                        if (ap->type == CALIAS && (ap->flag&DEFINED))
        !           280:                                printf("%s='%s'\n", ap->name, ap->val.s);
        !           281: 
        !           282:        for (; *wp != NULL; wp++) {
        !           283:                register char *id = *wp;
        !           284:                register char *val = strchr(id, '=');
        !           285: 
        !           286:                if (val == NULL) {
        !           287:                        ap = tsearch(t, id, hash(id));
        !           288:                        if (ap != NULL && ap->type == CALIAS && (ap->flag&DEFINED))
        !           289:                                printf("%s='%s'\n", ap->name, ap->val.s);
        !           290:                        else
        !           291:                                rv = 1;
        !           292:                } else {
        !           293:                        *val++ = '\0';
        !           294:                        ap = tenter(t, id, hash(id));
        !           295:                        if (ap->type == CKEYWD)
        !           296:                                errorf("cannot alias keyword\n");
        !           297:                        if ((ap->flag&ALLOC)) {
        !           298:                                afree((Void*)ap->val.s, APERM);
        !           299:                                ap->flag &=~ ALLOC|ISSET;
        !           300:                        }
        !           301:                        ap->type = CALIAS;
        !           302:                        ap->val.s = strsave(val, APERM);
        !           303:                        ap->flag |= DEFINED|ALLOC|ISSET;
        !           304:                }
        !           305:        }
        !           306:        return rv;
        !           307: }
        !           308: 
        !           309: int
        !           310: c_unalias(wp)
        !           311:        register char **wp;
        !           312: {
        !           313:        register struct table *t = &lexicals;
        !           314:        register struct tbl *ap;
        !           315: 
        !           316:        if (*++wp != NULL && strcmp(*wp, "-d") == 0) {
        !           317:                t = &homedirs;
        !           318:                wp++;
        !           319:        }
        !           320: 
        !           321:        for (; *wp != NULL; wp++) {
        !           322:                ap = tsearch(t, *wp, hash(*wp));
        !           323:                if (ap == NULL || ap->type != CALIAS)
        !           324:                        continue;
        !           325:                if ((ap->flag&ALLOC))
        !           326:                        afree((Void*)ap->val.s, APERM);
        !           327:                ap->flag &=~ DEFINED|ISSET|ALLOC;
        !           328:        }
        !           329:        return 0;
        !           330: }
        !           331: 
        !           332: int
        !           333: c_let(wp)
        !           334:        char **wp;
        !           335: {
        !           336:        int rv = 1;
        !           337: 
        !           338:        for (wp++; *wp; wp++)
        !           339:                rv = evaluate(*wp) == 0;
        !           340:        return rv;
        !           341: }
        !           342: 
        !           343: int
        !           344: c_jobs(wp)
        !           345:        char **wp;
        !           346: {
        !           347:        j_jobs();
        !           348:        return 0;
        !           349: }
        !           350: 
        !           351: #if JOBS
        !           352: int
        !           353: c_fgbg(wp)
        !           354:        register char **wp;
        !           355: {
        !           356:        int bg = strcmp(*wp, "bg") == 0;
        !           357: 
        !           358:        if (!flag[FMONITOR])
        !           359:                errorf("Job control not enabled\n");
        !           360:        wp++;
        !           361:        j_resume(j_lookup((*wp == NULL) ? "%" : *wp), bg);
        !           362:        return 0;
        !           363: }
        !           364: #endif
        !           365: 
        !           366: int
        !           367: c_kill(wp)
        !           368:        register char **wp;
        !           369: {
        !           370:        register char *cp;
        !           371:        int sig = SIGTERM;
        !           372:        int rv = 0;
        !           373: 
        !           374:        if (*++wp == NULL)
        !           375:                errorf("Usage: kill [-l] [-signal] {pid|job} ...\n");
        !           376:        if (strcmp(*wp, "-l") == 0) {
        !           377:                register struct trap *p = sigtraps;
        !           378:                for (sig = 0; sig < SIGNALS; sig++, p++)
        !           379:                        if (p->signal)
        !           380:                                printf("%2d %8s %s\n", p->signal, p->name, p->mess);
        !           381:                return 0;
        !           382:        }
        !           383: 
        !           384:        for (; (cp = *wp) != NULL; wp++)
        !           385:                if (*cp == '-' || isalpha(*cp)) {
        !           386:                        struct trap *p;
        !           387:                        p = gettrap((*cp == '-') ? cp+1 : cp);
        !           388:                        if (p == NULL)
        !           389:                                errorf("bad signal %s\n",
        !           390:                                        (*cp == '-') ? cp+1 : cp);
        !           391:                        sig = p->signal;
        !           392:                } else if (digit(*cp)) {
        !           393:                        if (kill(atoi(cp), sig) < 0) {
        !           394:                                shellf("%s: %s\n", cp, strerror(errno));
        !           395:                                rv++;
        !           396:                        }
        !           397:                } else if (*cp == '%')
        !           398:                        j_kill(j_lookup(cp), sig);
        !           399:                else
        !           400:                        errorf("invalid argument\n");
        !           401:        return rv;
        !           402: }
        !           403: 
        !           404: int
        !           405: c_bind(wp)
        !           406:        register char **wp;
        !           407: {
        !           408:        int macro = 0;
        !           409:        register char *cp;
        !           410: 
        !           411:        for (wp++; (cp = *wp) != NULL && *cp == '-'; wp++)
        !           412:                if (cp[1] == 'm')
        !           413:                        macro = 1;
        !           414: 
        !           415:        if (*wp == NULL)        /* list all */
        !           416:                x_bind((char*)NULL, (char*)NULL, 0);
        !           417: 
        !           418:        for (; *wp != NULL; wp++) {
        !           419:                cp = strchr(*wp, '=');
        !           420:                if (cp != NULL)
        !           421:                        *cp++ = 0;
        !           422:                x_bind(*wp, cp, macro);
        !           423:        }
        !           424: 
        !           425:        return 0;
        !           426: }
        !           427: 
        !           428: extern c_fc();
        !           429: extern c_getopts();
        !           430: 
        !           431: Const struct builtin kshbuiltins [] = {
        !           432:        {"print", c_print},
        !           433:        {"getopts", c_getopts},
        !           434:        {"=typeset", c_typeset},
        !           435:        {"whence", c_whence},
        !           436:        {"alias", c_alias},
        !           437:        {"unalias", c_unalias},
        !           438:        {"hash", c_hash},
        !           439:        {"let", c_let},
        !           440:        {"fc", c_fc},
        !           441:        {"jobs", c_jobs},
        !           442:        {"kill", c_kill},
        !           443: #if JOBS
        !           444:        {"fg", c_fgbg},
        !           445:        {"bg", c_fgbg},
        !           446: #endif
        !           447: #if EDIT
        !           448:        {"bind", c_bind},
        !           449: #endif
        !           450:        {NULL, NULL}
        !           451: };
        !           452: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.