|
|
1.1 ! root 1: #ifndef lint ! 2: static char sccsid[] = "@(#)cmd3.c 2.14 (Berkeley) 8/11/83"; ! 3: #endif ! 4: ! 5: #include "rcv.h" ! 6: #include <sys/stat.h> ! 7: ! 8: /* ! 9: * Mail -- a mail program ! 10: * ! 11: * Still more user commands. ! 12: */ ! 13: ! 14: /* ! 15: * Process a shell escape by saving signals, ignoring signals, ! 16: * and forking a sh -c ! 17: */ ! 18: ! 19: shell(str) ! 20: char *str; ! 21: { ! 22: int (*sig[2])(), stat[1]; ! 23: register int t; ! 24: char *Shell; ! 25: char cmd[BUFSIZ]; ! 26: ! 27: strcpy(cmd, str); ! 28: if (bangexp(cmd) < 0) ! 29: return(-1); ! 30: if ((Shell = value("SHELL")) == NOSTR) ! 31: Shell = SHELL; ! 32: for (t = 2; t < 4; t++) ! 33: sig[t-2] = sigset(t, SIG_IGN); ! 34: t = vfork(); ! 35: if (t == 0) { ! 36: sigchild(); ! 37: for (t = 2; t < 4; t++) ! 38: if (sig[t-2] != SIG_IGN) ! 39: sigsys(t, SIG_DFL); ! 40: execl(Shell, Shell, "-c", cmd, 0); ! 41: perror(Shell); ! 42: _exit(1); ! 43: } ! 44: while (wait(stat) != t) ! 45: ; ! 46: if (t == -1) ! 47: perror("fork"); ! 48: for (t = 2; t < 4; t++) ! 49: sigset(t, sig[t-2]); ! 50: printf("!\n"); ! 51: return(0); ! 52: } ! 53: ! 54: /* ! 55: * Fork an interactive shell. ! 56: */ ! 57: ! 58: dosh(str) ! 59: char *str; ! 60: { ! 61: int (*sig[2])(), stat[1]; ! 62: register int t; ! 63: char *Shell; ! 64: if ((Shell = value("SHELL")) == NOSTR) ! 65: Shell = SHELL; ! 66: for (t = 2; t < 4; t++) ! 67: sig[t-2] = sigset(t, SIG_IGN); ! 68: t = vfork(); ! 69: if (t == 0) { ! 70: sigchild(); ! 71: for (t = 2; t < 4; t++) ! 72: if (sig[t-2] != SIG_IGN) ! 73: sigsys(t, SIG_DFL); ! 74: execl(Shell, Shell, 0); ! 75: perror(Shell); ! 76: _exit(1); ! 77: } ! 78: while (wait(stat) != t) ! 79: ; ! 80: if (t == -1) ! 81: perror("fork"); ! 82: for (t = 2; t < 4; t++) ! 83: sigsys(t, sig[t-2]); ! 84: putchar('\n'); ! 85: return(0); ! 86: } ! 87: ! 88: /* ! 89: * Expand the shell escape by expanding unescaped !'s into the ! 90: * last issued command where possible. ! 91: */ ! 92: ! 93: char lastbang[128]; ! 94: ! 95: bangexp(str) ! 96: char *str; ! 97: { ! 98: char bangbuf[BUFSIZ]; ! 99: register char *cp, *cp2; ! 100: register int n; ! 101: int changed = 0; ! 102: ! 103: cp = str; ! 104: cp2 = bangbuf; ! 105: n = BUFSIZ; ! 106: while (*cp) { ! 107: if (*cp == '!') { ! 108: if (n < strlen(lastbang)) { ! 109: overf: ! 110: printf("Command buffer overflow\n"); ! 111: return(-1); ! 112: } ! 113: changed++; ! 114: strcpy(cp2, lastbang); ! 115: cp2 += strlen(lastbang); ! 116: n -= strlen(lastbang); ! 117: cp++; ! 118: continue; ! 119: } ! 120: if (*cp == '\\' && cp[1] == '!') { ! 121: if (--n <= 1) ! 122: goto overf; ! 123: *cp2++ = '!'; ! 124: cp += 2; ! 125: changed++; ! 126: } ! 127: if (--n <= 1) ! 128: goto overf; ! 129: *cp2++ = *cp++; ! 130: } ! 131: *cp2 = 0; ! 132: if (changed) { ! 133: printf("!%s\n", bangbuf); ! 134: fflush(stdout); ! 135: } ! 136: strcpy(str, bangbuf); ! 137: strncpy(lastbang, bangbuf, 128); ! 138: lastbang[127] = 0; ! 139: return(0); ! 140: } ! 141: ! 142: /* ! 143: * Print out a nice help message from some file or another. ! 144: */ ! 145: ! 146: help() ! 147: { ! 148: register c; ! 149: register FILE *f; ! 150: ! 151: if ((f = fopen(HELPFILE, "r")) == NULL) { ! 152: perror(HELPFILE); ! 153: return(1); ! 154: } ! 155: while ((c = getc(f)) != EOF) ! 156: putchar(c); ! 157: fclose(f); ! 158: return(0); ! 159: } ! 160: ! 161: /* ! 162: * Change user's working directory. ! 163: */ ! 164: ! 165: schdir(str) ! 166: char *str; ! 167: { ! 168: register char *cp; ! 169: ! 170: for (cp = str; *cp == ' '; cp++) ! 171: ; ! 172: if (*cp == '\0') ! 173: cp = homedir; ! 174: else ! 175: if ((cp = expand(cp)) == NOSTR) ! 176: return(1); ! 177: if (chdir(cp) < 0) { ! 178: perror(cp); ! 179: return(1); ! 180: } ! 181: return(0); ! 182: } ! 183: ! 184: /* ! 185: * Reply to a list of messages. Extract each name from the ! 186: * message header and send them off to mail1() ! 187: */ ! 188: ! 189: respond(msgvec) ! 190: int *msgvec; ! 191: { ! 192: struct message *mp; ! 193: char *cp, *cp2, *cp3, *rcv, *replyto; ! 194: char buf[2 * LINESIZE], **ap; ! 195: struct name *np; ! 196: struct header head; ! 197: ! 198: if (msgvec[1] != 0) { ! 199: printf("Sorry, can't reply to multiple messages at once\n"); ! 200: return(1); ! 201: } ! 202: mp = &message[msgvec[0] - 1]; ! 203: dot = mp; ! 204: rcv = NOSTR; ! 205: cp = skin(nameof(mp, 1)); ! 206: if (cp != NOSTR) ! 207: rcv = cp; ! 208: cp = skin(hfield("from", mp)); ! 209: if (cp != NOSTR) ! 210: rcv = cp; ! 211: replyto = skin(hfield("reply-to", mp)); ! 212: strcpy(buf, ""); ! 213: if (replyto != NOSTR) ! 214: strcpy(buf, replyto); ! 215: else { ! 216: cp = skin(hfield("to", mp)); ! 217: if (cp != NOSTR) ! 218: strcpy(buf, cp); ! 219: } ! 220: np = elide(extract(buf, GTO)); ! 221: /* rcv = rename(rcv); */ ! 222: mapf(np, rcv); ! 223: /* ! 224: * Delete my name from the reply list, ! 225: * and with it, all my alternate names. ! 226: */ ! 227: np = delname(np, myname, icequal); ! 228: if (altnames) ! 229: for (ap = altnames; *ap; ap++) ! 230: np = delname(np, *ap, icequal); ! 231: head.h_seq = 1; ! 232: cp = detract(np, 0); ! 233: if (cp != NOSTR && replyto == NOSTR) { ! 234: strcpy(buf, cp); ! 235: strcat(buf, " "); ! 236: strcat(buf, rcv); ! 237: } ! 238: else { ! 239: if (cp == NOSTR && replyto != NOSTR) ! 240: printf("Empty reply-to field -- replying to author\n"); ! 241: if (cp == NOSTR) ! 242: strcpy(buf, rcv); ! 243: else ! 244: strcpy(buf, cp); ! 245: } ! 246: head.h_to = buf; ! 247: head.h_subject = hfield("subject", mp); ! 248: if (head.h_subject == NOSTR) ! 249: head.h_subject = hfield("subj", mp); ! 250: head.h_subject = reedit(head.h_subject); ! 251: head.h_cc = NOSTR; ! 252: if (replyto == NOSTR) { ! 253: cp = hfield("cc", mp); ! 254: if (cp != NOSTR) { ! 255: np = elide(extract(cp, GCC)); ! 256: mapf(np, rcv); ! 257: np = delname(np, myname, icequal); ! 258: if (altnames != 0) ! 259: for (ap = altnames; *ap; ap++) ! 260: np = delname(np, *ap, icequal); ! 261: head.h_cc = detract(np, 0); ! 262: } ! 263: } ! 264: head.h_bcc = NOSTR; ! 265: mail1(&head); ! 266: return(0); ! 267: } ! 268: ! 269: /* ! 270: * Modify the subject we are replying to to begin with Re: if ! 271: * it does not already. ! 272: */ ! 273: ! 274: char * ! 275: reedit(subj) ! 276: char *subj; ! 277: { ! 278: char sbuf[10]; ! 279: register char *newsubj; ! 280: ! 281: if (subj == NOSTR) ! 282: return(NOSTR); ! 283: strncpy(sbuf, subj, 3); ! 284: sbuf[3] = 0; ! 285: if (icequal(sbuf, "re:")) ! 286: return(subj); ! 287: newsubj = salloc(strlen(subj) + 6); ! 288: sprintf(newsubj, "Re: %s", subj); ! 289: return(newsubj); ! 290: } ! 291: ! 292: /* ! 293: * Preserve the named messages, so that they will be sent ! 294: * back to the system mailbox. ! 295: */ ! 296: ! 297: preserve(msgvec) ! 298: int *msgvec; ! 299: { ! 300: register struct message *mp; ! 301: register int *ip, mesg; ! 302: ! 303: if (edit) { ! 304: printf("Cannot \"preserve\" in edit mode\n"); ! 305: return(1); ! 306: } ! 307: for (ip = msgvec; *ip != NULL; ip++) { ! 308: mesg = *ip; ! 309: mp = &message[mesg-1]; ! 310: mp->m_flag |= MPRESERVE; ! 311: mp->m_flag &= ~MBOX; ! 312: dot = mp; ! 313: } ! 314: return(0); ! 315: } ! 316: ! 317: /* ! 318: * Print the size of each message. ! 319: */ ! 320: ! 321: messize(msgvec) ! 322: int *msgvec; ! 323: { ! 324: register struct message *mp; ! 325: register int *ip, mesg; ! 326: ! 327: for (ip = msgvec; *ip != NULL; ip++) { ! 328: mesg = *ip; ! 329: mp = &message[mesg-1]; ! 330: printf("%d: %ld\n", mesg, mp->m_size); ! 331: } ! 332: return(0); ! 333: } ! 334: ! 335: /* ! 336: * Quit quickly. If we are sourcing, just pop the input level ! 337: * by returning an error. ! 338: */ ! 339: ! 340: rexit(e) ! 341: { ! 342: if (sourcing) ! 343: return(1); ! 344: if (Tflag != NOSTR) ! 345: close(creat(Tflag, 0600)); ! 346: exit(e); ! 347: } ! 348: ! 349: /* ! 350: * Set or display a variable value. Syntax is similar to that ! 351: * of csh. ! 352: */ ! 353: ! 354: set(arglist) ! 355: char **arglist; ! 356: { ! 357: register struct var *vp; ! 358: register char *cp, *cp2; ! 359: char varbuf[BUFSIZ], **ap, **p; ! 360: int errs, h, s; ! 361: ! 362: if (argcount(arglist) == 0) { ! 363: for (h = 0, s = 1; h < HSHSIZE; h++) ! 364: for (vp = variables[h]; vp != NOVAR; vp = vp->v_link) ! 365: s++; ! 366: ap = (char **) salloc(s * sizeof *ap); ! 367: for (h = 0, p = ap; h < HSHSIZE; h++) ! 368: for (vp = variables[h]; vp != NOVAR; vp = vp->v_link) ! 369: *p++ = vp->v_name; ! 370: *p = NOSTR; ! 371: sort(ap); ! 372: for (p = ap; *p != NOSTR; p++) ! 373: printf("%s\t%s\n", *p, value(*p)); ! 374: return(0); ! 375: } ! 376: errs = 0; ! 377: for (ap = arglist; *ap != NOSTR; ap++) { ! 378: cp = *ap; ! 379: cp2 = varbuf; ! 380: while (*cp != '=' && *cp != '\0') ! 381: *cp2++ = *cp++; ! 382: *cp2 = '\0'; ! 383: if (*cp == '\0') ! 384: cp = ""; ! 385: else ! 386: cp++; ! 387: if (equal(varbuf, "")) { ! 388: printf("Non-null variable name required\n"); ! 389: errs++; ! 390: continue; ! 391: } ! 392: assign(varbuf, cp); ! 393: } ! 394: return(errs); ! 395: } ! 396: ! 397: /* ! 398: * Unset a bunch of variable values. ! 399: */ ! 400: ! 401: unset(arglist) ! 402: char **arglist; ! 403: { ! 404: register struct var *vp, *vp2; ! 405: register char *cp; ! 406: int errs, h; ! 407: char **ap; ! 408: ! 409: errs = 0; ! 410: for (ap = arglist; *ap != NOSTR; ap++) { ! 411: if ((vp2 = lookup(*ap)) == NOVAR) { ! 412: if (!sourcing) { ! 413: printf("\"%s\": undefined variable\n", *ap); ! 414: errs++; ! 415: } ! 416: continue; ! 417: } ! 418: h = hash(*ap); ! 419: if (vp2 == variables[h]) { ! 420: variables[h] = variables[h]->v_link; ! 421: vfree(vp2->v_name); ! 422: vfree(vp2->v_value); ! 423: cfree(vp2); ! 424: continue; ! 425: } ! 426: for (vp = variables[h]; vp->v_link != vp2; vp = vp->v_link) ! 427: ; ! 428: vp->v_link = vp2->v_link; ! 429: vfree(vp2->v_name); ! 430: vfree(vp2->v_value); ! 431: cfree(vp2); ! 432: } ! 433: return(errs); ! 434: } ! 435: ! 436: /* ! 437: * Put add users to a group. ! 438: */ ! 439: ! 440: group(argv) ! 441: char **argv; ! 442: { ! 443: register struct grouphead *gh; ! 444: register struct group *gp; ! 445: register int h; ! 446: int s; ! 447: char **ap, *gname, **p; ! 448: ! 449: if (argcount(argv) == 0) { ! 450: for (h = 0, s = 1; h < HSHSIZE; h++) ! 451: for (gh = groups[h]; gh != NOGRP; gh = gh->g_link) ! 452: s++; ! 453: ap = (char **) salloc(s * sizeof *ap); ! 454: for (h = 0, p = ap; h < HSHSIZE; h++) ! 455: for (gh = groups[h]; gh != NOGRP; gh = gh->g_link) ! 456: *p++ = gh->g_name; ! 457: *p = NOSTR; ! 458: sort(ap); ! 459: for (p = ap; *p != NOSTR; p++) ! 460: printgroup(*p); ! 461: return(0); ! 462: } ! 463: if (argcount(argv) == 1) { ! 464: printgroup(*argv); ! 465: return(0); ! 466: } ! 467: gname = *argv; ! 468: h = hash(gname); ! 469: if ((gh = findgroup(gname)) == NOGRP) { ! 470: gh = (struct grouphead *) calloc(sizeof *gh, 1); ! 471: gh->g_name = vcopy(gname); ! 472: gh->g_list = NOGE; ! 473: gh->g_link = groups[h]; ! 474: groups[h] = gh; ! 475: } ! 476: ! 477: /* ! 478: * Insert names from the command list into the group. ! 479: * Who cares if there are duplicates? They get tossed ! 480: * later anyway. ! 481: */ ! 482: ! 483: for (ap = argv+1; *ap != NOSTR; ap++) { ! 484: gp = (struct group *) calloc(sizeof *gp, 1); ! 485: gp->ge_name = vcopy(*ap); ! 486: gp->ge_link = gh->g_list; ! 487: gh->g_list = gp; ! 488: } ! 489: return(0); ! 490: } ! 491: ! 492: /* ! 493: * Sort the passed string vecotor into ascending dictionary ! 494: * order. ! 495: */ ! 496: ! 497: sort(list) ! 498: char **list; ! 499: { ! 500: register char **ap; ! 501: int diction(); ! 502: ! 503: for (ap = list; *ap != NOSTR; ap++) ! 504: ; ! 505: if (ap-list < 2) ! 506: return; ! 507: qsort(list, ap-list, sizeof *list, diction); ! 508: } ! 509: ! 510: /* ! 511: * Do a dictionary order comparison of the arguments from ! 512: * qsort. ! 513: */ ! 514: ! 515: diction(a, b) ! 516: register char **a, **b; ! 517: { ! 518: return(strcmp(*a, *b)); ! 519: } ! 520: ! 521: /* ! 522: * The do nothing command for comments. ! 523: */ ! 524: ! 525: null(e) ! 526: { ! 527: return(0); ! 528: } ! 529: ! 530: /* ! 531: * Print out the current edit file, if we are editing. ! 532: * Otherwise, print the name of the person who's mail ! 533: * we are reading. ! 534: */ ! 535: ! 536: file(argv) ! 537: char **argv; ! 538: { ! 539: register char *cp; ! 540: char fname[BUFSIZ]; ! 541: int edit; ! 542: ! 543: if (argv[0] == NOSTR) { ! 544: newfileinfo(); ! 545: return(0); ! 546: } ! 547: ! 548: /* ! 549: * Acker's! Must switch to the new file. ! 550: * We use a funny interpretation -- ! 551: * # -- gets the previous file ! 552: * % -- gets the invoker's post office box ! 553: * %user -- gets someone else's post office box ! 554: * & -- gets invoker's mbox file ! 555: * string -- reads the given file ! 556: */ ! 557: ! 558: cp = getfilename(argv[0], &edit); ! 559: if (cp == NOSTR) ! 560: return(-1); ! 561: if (setfile(cp, edit)) { ! 562: perror(cp); ! 563: return(-1); ! 564: } ! 565: newfileinfo(); ! 566: } ! 567: ! 568: /* ! 569: * Evaluate the string given as a new mailbox name. ! 570: * Ultimately, we want this to support a number of meta characters. ! 571: * Possibly: ! 572: * % -- for my system mail box ! 573: * %user -- for user's system mail box ! 574: * # -- for previous file ! 575: * & -- get's invoker's mbox file ! 576: * file name -- for any other file ! 577: */ ! 578: ! 579: char prevfile[PATHSIZE]; ! 580: ! 581: char * ! 582: getfilename(name, aedit) ! 583: char *name; ! 584: int *aedit; ! 585: { ! 586: register char *cp; ! 587: char savename[BUFSIZ]; ! 588: char oldmailname[BUFSIZ]; ! 589: ! 590: /* ! 591: * Assume we will be in "edit file" mode, until ! 592: * proven wrong. ! 593: */ ! 594: *aedit = 1; ! 595: switch (*name) { ! 596: case '%': ! 597: *aedit = 0; ! 598: strcpy(prevfile, mailname); ! 599: if (name[1] != 0) { ! 600: strcpy(savename, myname); ! 601: strcpy(oldmailname, mailname); ! 602: strncpy(myname, name+1, PATHSIZE-1); ! 603: myname[PATHSIZE-1] = 0; ! 604: findmail(); ! 605: cp = savestr(mailname); ! 606: strcpy(myname, savename); ! 607: strcpy(mailname, oldmailname); ! 608: return(cp); ! 609: } ! 610: strcpy(oldmailname, mailname); ! 611: findmail(); ! 612: cp = savestr(mailname); ! 613: strcpy(mailname, oldmailname); ! 614: return(cp); ! 615: ! 616: case '#': ! 617: if (name[1] != 0) ! 618: goto regular; ! 619: if (prevfile[0] == 0) { ! 620: printf("No previous file\n"); ! 621: return(NOSTR); ! 622: } ! 623: cp = savestr(prevfile); ! 624: strcpy(prevfile, mailname); ! 625: return(cp); ! 626: ! 627: case '&': ! 628: strcpy(prevfile, mailname); ! 629: if (name[1] == 0) ! 630: return(mbox); ! 631: /* Fall into . . . */ ! 632: ! 633: default: ! 634: regular: ! 635: strcpy(prevfile, mailname); ! 636: cp = expand(name); ! 637: return(cp); ! 638: } ! 639: } ! 640: ! 641: /* ! 642: * Expand file names like echo ! 643: */ ! 644: ! 645: echo(argv) ! 646: char **argv; ! 647: { ! 648: register char **ap; ! 649: register char *cp; ! 650: ! 651: for (ap = argv; *ap != NOSTR; ap++) { ! 652: cp = *ap; ! 653: if ((cp = expand(cp)) != NOSTR) ! 654: printf("%s ", cp); ! 655: } ! 656: return(0); ! 657: } ! 658: ! 659: /* ! 660: * Reply to a series of messages by simply mailing to the senders ! 661: * and not messing around with the To: and Cc: lists as in normal ! 662: * reply. ! 663: */ ! 664: ! 665: Respond(msgvec) ! 666: int msgvec[]; ! 667: { ! 668: struct header head; ! 669: struct message *mp; ! 670: register int i, s, *ap; ! 671: register char *cp, *cp2, *subject; ! 672: ! 673: for (s = 0, ap = msgvec; *ap != 0; ap++) { ! 674: mp = &message[*ap - 1]; ! 675: dot = mp; ! 676: if ((cp = skin(hfield("from", mp))) != NOSTR) ! 677: s+= strlen(cp) + 1; ! 678: else ! 679: s += strlen(skin(nameof(mp, 2))) + 1; ! 680: } ! 681: if (s == 0) ! 682: return(0); ! 683: cp = salloc(s + 2); ! 684: head.h_to = cp; ! 685: for (ap = msgvec; *ap != 0; ap++) { ! 686: mp = &message[*ap - 1]; ! 687: if ((cp2 = skin(hfield("from", mp))) == NOSTR) ! 688: cp2 = skin(nameof(mp, 2)); ! 689: cp = copy(cp2, cp); ! 690: *cp++ = ' '; ! 691: } ! 692: *--cp = 0; ! 693: mp = &message[msgvec[0] - 1]; ! 694: subject = hfield("subject", mp); ! 695: head.h_seq = 0; ! 696: if (subject == NOSTR) ! 697: subject = hfield("subj", mp); ! 698: head.h_subject = reedit(subject); ! 699: if (subject != NOSTR) ! 700: head.h_seq++; ! 701: head.h_cc = NOSTR; ! 702: head.h_bcc = NOSTR; ! 703: mail1(&head); ! 704: return(0); ! 705: } ! 706: ! 707: /* ! 708: * Conditional commands. These allow one to parameterize one's ! 709: * .mailrc and do some things if sending, others if receiving. ! 710: */ ! 711: ! 712: ifcmd(argv) ! 713: char **argv; ! 714: { ! 715: register char *cp; ! 716: ! 717: if (cond != CANY) { ! 718: printf("Illegal nested \"if\"\n"); ! 719: return(1); ! 720: } ! 721: cond = CANY; ! 722: cp = argv[0]; ! 723: switch (*cp) { ! 724: case 'r': case 'R': ! 725: cond = CRCV; ! 726: break; ! 727: ! 728: case 's': case 'S': ! 729: cond = CSEND; ! 730: break; ! 731: ! 732: default: ! 733: printf("Unrecognized if-keyword: \"%s\"\n", cp); ! 734: return(1); ! 735: } ! 736: return(0); ! 737: } ! 738: ! 739: /* ! 740: * Implement 'else'. This is pretty simple -- we just ! 741: * flip over the conditional flag. ! 742: */ ! 743: ! 744: elsecmd() ! 745: { ! 746: ! 747: switch (cond) { ! 748: case CANY: ! 749: printf("\"Else\" without matching \"if\"\n"); ! 750: return(1); ! 751: ! 752: case CSEND: ! 753: cond = CRCV; ! 754: break; ! 755: ! 756: case CRCV: ! 757: cond = CSEND; ! 758: break; ! 759: ! 760: default: ! 761: printf("Mail's idea of conditions is screwed up\n"); ! 762: cond = CANY; ! 763: break; ! 764: } ! 765: return(0); ! 766: } ! 767: ! 768: /* ! 769: * End of if statement. Just set cond back to anything. ! 770: */ ! 771: ! 772: endifcmd() ! 773: { ! 774: ! 775: if (cond == CANY) { ! 776: printf("\"Endif\" without matching \"if\"\n"); ! 777: return(1); ! 778: } ! 779: cond = CANY; ! 780: return(0); ! 781: } ! 782: ! 783: /* ! 784: * Set the list of alternate names. ! 785: */ ! 786: alternates(namelist) ! 787: char **namelist; ! 788: { ! 789: register int c; ! 790: register char **ap, **ap2, *cp; ! 791: ! 792: c = argcount(namelist) + 1; ! 793: if (c == 1) { ! 794: if (altnames == 0) ! 795: return(0); ! 796: for (ap = altnames; *ap; ap++) ! 797: printf("%s ", *ap); ! 798: printf("\n"); ! 799: return(0); ! 800: } ! 801: if (altnames != 0) ! 802: cfree((char *) altnames); ! 803: altnames = (char **) calloc(c, sizeof (char *)); ! 804: for (ap = namelist, ap2 = altnames; *ap; ap++, ap2++) { ! 805: cp = (char *) calloc(strlen(*ap) + 1, sizeof (char)); ! 806: strcpy(cp, *ap); ! 807: *ap2 = cp; ! 808: } ! 809: *ap2 = 0; ! 810: return(0); ! 811: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.