Annotation of coherent/d/bin/mail/usermail/send.c, revision 1.1

1.1     ! root        1: /*
        !             2:  *     The code that passes an individual message to the mail system.
        !             3:  */
        !             4: 
        !             5: #include "mail.h"
        !             6: 
        !             7: #define SITENAMELEN    32      /* max length of sitename */
        !             8: #define NODENAME       "/etc/uucpname"
        !             9: #define DOMAINNAME     "/etc/domain"
        !            10: char   domain [64];
        !            11: 
        !            12: extern char    *strtok();
        !            13: static char    **allist;
        !            14: static char    **tolist;
        !            15: static char    **cclist = NULL;
        !            16: 
        !            17: char   mysite[SITENAMELEN];    /* this host's uucpname */
        !            18: 
        !            19: extern char    *temp;
        !            20: extern int     myuid;          /* User-id of mail user */
        !            21: extern int     mygid;          /* Group-id of mail user */
        !            22: extern char    cmdname[];      /* Command for x{en,de}code filter */
        !            23:                                /* and for tail recursion to uumail */
        !            24:                                /* and for editor recursion */
        !            25: extern char    *editname;      /* name of editor          */
        !            26: extern char    *askcc;         /* Ask for CC: list? (YES/NO) */
        !            27: extern int     callmexmail;    /* Xmail modifier present */
        !            28: extern char    wrerr[];
        !            29: extern char    myname[];       /* User name */
        !            30: extern char    myfullname[];   /* full user name */
        !            31: extern int     mflag;          /* `You have mail.' message to recipient */
        !            32: extern int     verbflag;       /* verbose flag */
        !            33: extern char    templ[];        /* Temp file name template */
        !            34: extern char    mydead[];       /* $HOME/dead.letter */
        !            35: extern char    mysig[];
        !            36: extern char    nosave[];
        !            37: extern int     callmermail;
        !            38: 
        !            39: static int     eflag;          /* Edit this mail */
        !            40: static int     senderr;
        !            41: struct tm      *tp;
        !            42: char   toerr[] = "Cannot create temporary file\n";
        !            43: char   header[BUFSIZ];         /* Message header */
        !            44: char   boxname[256];           /* Destination mailbox */
        !            45: char   remotefrom [32];        /* "remote from uucp" */
        !            46: 
        !            47: char   nosend[] = "Can't send mail to '%s'\n";
        !            48: char   nopubk[] = "Can't send xmail to '%s'\n";
        !            49: static int fromtty;
        !            50: 
        !            51: /*
        !            52:  * Send the message found on
        !            53:  * the file pointer to the list
        !            54:  * of people (argv style) with
        !            55:  * a NULL pointer at the end.
        !            56:  * The message is copied to a temp-file
        !            57:  * from position `start' to `end' (or EOF).
        !            58:  */
        !            59: send2(fp, users, start, end, asksubj)
        !            60: FILE *fp;
        !            61: register char **users;
        !            62: fsize_t start, end;
        !            63: int    asksubj;
        !            64: {
        !            65:        char    **getcc(), **listpp;
        !            66:        FILE    *xfp, *tfp, *sigfp;
        !            67:        time_t  curtime;
        !            68: 
        !            69:        uucpname();
        !            70:        domainname();
        !            71:        senderr = 0;
        !            72:        temp = templ;
        !            73: 
        !            74:        fromtty = isatty(fileno(stdin));
        !            75:        if ((tfp = fopen(temp, "w")) != NULL) {
        !            76:                fclose(tfp);
        !            77:                if ((tfp = fopen(temp, "r+w")) == NULL)
        !            78:                        merr(toerr);
        !            79:        } else
        !            80:                merr(toerr);
        !            81:        chown(temp, myuid, mygid);
        !            82:        unlink(temp);
        !            83:        temp = NULL;
        !            84:        fseek(fp, start, 0);
        !            85:        end -= start;
        !            86: 
        !            87:        eflag = 0;
        !            88:        if (fromtty && asksubj && !callmermail) {
        !            89:                fprintf(stdout, "Subject: ");
        !            90:                fflush(stdout);
        !            91:                if (fgets(msgline, NLINE, fp) != NULL) {
        !            92:                        if (strlen(msgline) > 1)
        !            93:                                fprintf(tfp, "Subject: %s", msgline);
        !            94:                }
        !            95:        }
        !            96: 
        !            97:        if (intcheck()) {
        !            98:                fclose(tfp);
        !            99:                return(1);
        !           100:        }
        !           101: 
        !           102:        for (;;) {
        !           103:                if (fgets(msgline, NLINE, fp) == NULL)
        !           104:                        break;
        !           105:                if (fp == stdin)
        !           106:                        if ((strcmp(".\n", msgline)==0))
        !           107:                                break;
        !           108:                        else if ((strcmp("?\n", msgline)==0)) {
        !           109:                                eflag = 1;
        !           110:                                break;
        !           111:                        }
        !           112:                fputs(msgline, tfp);
        !           113:                if ( (end-=strlen(msgline)) <= 0 )
        !           114:                        break;
        !           115:        }
        !           116: 
        !           117:        if (intcheck()) {
        !           118:                fclose(tfp);
        !           119:                return(1);
        !           120:        }
        !           121: 
        !           122:        if (!callmermail && (sigfp = fopen(mysig, "r")) != NULL) {
        !           123:                fputs("\n", tfp);
        !           124:                while (fgets(msgline, NLINE, sigfp) != NULL)
        !           125:                        fputs(msgline, tfp);
        !           126:                fclose(sigfp);
        !           127:        }
        !           128: 
        !           129:        /*
        !           130:         * Now, see if user wants to edit the message
        !           131:         */
        !           132: 
        !           133:        if (eflag) {
        !           134:                xfp = tfp;
        !           135:                temp = templ;
        !           136:                if ((tfp = fopen(temp, "wr")) == NULL)
        !           137:                        merr(toerr);
        !           138:                chown(temp, myuid, mygid);
        !           139:                mcopy(xfp, tfp, (fsize_t)0, (fsize_t)MAXLONG, 0);
        !           140:                fclose(xfp);
        !           141:                sprintf(cmdname, "exec %s %s", editname, templ);
        !           142:                system(cmdname);
        !           143:                unlink(temp);
        !           144:                temp = NULL;
        !           145:        }
        !           146: 
        !           147:        /*
        !           148:         * if empty message, bug out.
        !           149:         */
        !           150: 
        !           151:        if (ftell(tfp) == 0) {
        !           152:                fclose(tfp);
        !           153:                return(1);
        !           154:        }
        !           155: 
        !           156:        /*
        !           157:         * Now see if a copy list is requested.
        !           158:         */
        !           159: 
        !           160:        tolist = users;
        !           161:        cclist = (askcc && fromtty && !callmermail) ? getcc(): NULL;
        !           162:        allist = listcat(tolist, cclist);
        !           163:        
        !           164:        if ( verbflag ) {
        !           165:                mmsg(
        !           166:        "Recipient List:\n\n");
        !           167:                for (listpp=allist; *listpp != NULL; listpp++)
        !           168:                        mmsg("\t%s\n", *listpp);
        !           169:        }
        !           170: 
        !           171:        /*
        !           172:         * Now send the message.
        !           173:         */
        !           174: 
        !           175:        time(&curtime);
        !           176:        tp = localtime(&curtime);
        !           177: 
        !           178:        if (callmexmail)
        !           179:                xsend(allist, tfp);
        !           180:        else
        !           181:                usend(allist, tfp);
        !           182: 
        !           183:        return( senderr );
        !           184: }
        !           185: 
        !           186: usend(users, tfp)
        !           187: char **users;
        !           188: FILE *tfp;
        !           189: {
        !           190:        FILE *xfp;
        !           191:        char *name;
        !           192:        char **ulist, **listpp;
        !           193:        char command[CMDLINE];
        !           194:        char *arpadate();
        !           195:        FILE *popen();
        !           196: 
        !           197:        logdump("Date: %s  From: %s!%s (%s)\n",
        !           198:                        arpadate(tp), mysite, myname, myfullname);
        !           199:        for (ulist = users; (name=*ulist) != NULL; ulist++)
        !           200:                logdump("To: \"%s\"\n", name);
        !           201: 
        !           202:        /* Build the command line to the delivery program.  */
        !           203:        if ( callmexmail ) {
        !           204:                strcpy(command, XDELIVER); /* usually "/bin/rxmail" */
        !           205:        } else {
        !           206:                strcpy(command, DELIVER); /* usually "/bin/rmail" */
        !           207:        } /* if ( callmexmail ) */
        !           208: 
        !           209:        /* Add the list of recipients to the command line.  */
        !           210:        for (listpp = users; *listpp != NULL; listpp++) {
        !           211:                strcat(command, " ");
        !           212:                strcat(command, *listpp);
        !           213:        }
        !           214:        
        !           215:        /* NB:  I think there may be a security problem
        !           216:           here, since popen ought to exec $SHELL.  Check this.  */
        !           217:        /* Now actually call the mail delivery agent.  */
        !           218:        if ( (xfp = popen(command, "w")) == NULL ) {
        !           219:                /* Report a send error and return.  */
        !           220:        }
        !           221: 
        !           222:        /* Pump the headers into the delivery agent. */
        !           223:        build_header(xfp);
        !           224: 
        !           225:        /* Pump the message into the delivery agent.  */
        !           226:        rewind(tfp);
        !           227:        mcopy(tfp, xfp, (fsize_t)0, (fsize_t)MAXLONG, 0);
        !           228: 
        !           229:        fclose(xfp);
        !           230:        fclose(tfp);
        !           231: }
        !           232: 
        !           233: xsend(users, tfp) char **users; FILE *tfp;
        !           234: {
        !           235:        register char **ulist;
        !           236:        register char *cp;
        !           237:        register struct passwd *pwp;
        !           238:        FILE *xfp;
        !           239: 
        !           240:        for (ulist = users; *ulist!=NULL; ulist++) {
        !           241:                rewind(tfp);
        !           242:                sprintf(boxname, "%s%s", SPOOLDIR, *ulist);
        !           243:                sprintf(cmdname, "xencode %s >> %s", *ulist, boxname);
        !           244:                if (index(*ulist, '!') != NULL
        !           245:                 || (pwp = getpwnam(*ulist)) == NULL) {
        !           246:                        mmsg(nosend, *ulist);
        !           247:                        continue;
        !           248:                }
        !           249:                if (xaccess(*ulist) == 0) {
        !           250:                        mmsg(nopubk, *ulist);
        !           251:                        continue;
        !           252:                }
        !           253:                mlock(pwp->pw_uid);
        !           254:                if ((xfp = fopen(boxname, "a")) == NULL) {
        !           255:                        mmsg(nosend, *ulist);
        !           256:                        munlock();
        !           257:                        continue;
        !           258:                }
        !           259:                chown(boxname, pwp->pw_uid, pwp->pw_gid);
        !           260:                fprintf(xfp, "From xmail %s %s\n", cp,
        !           261:                        tzname[tp->tm_isdst ? 1 : 0]);
        !           262:                fclose(xfp);
        !           263:                if ((xfp = popen(cmdname, "w")) == NULL) {
        !           264:                        mmsg("Can't pipe to xencode\n");
        !           265:                        continue;
        !           266:                }
        !           267:                if (fwrite(header, strlen(header), 1, xfp) != 1
        !           268:                 || mcopy(tfp, xfp, (fsize_t)0, (fsize_t)MAXLONG, 0)) {
        !           269:                        merr(wrerr, cmdname);
        !           270:                }
        !           271:                pclose(xfp);
        !           272:                munlock();
        !           273:        }
        !           274:        fclose(tfp);
        !           275: }
        !           276: 
        !           277: uucpname()
        !           278: {
        !           279:        FILE *uufile;
        !           280: 
        !           281:        if (NULL == (uufile = fopen(NODENAME, "r"))) {
        !           282:                strcpy(mysite, "<unknown>");
        !           283:                return;
        !           284:        }
        !           285:        fgets(mysite, sizeof mysite, uufile);
        !           286:        mysite[strlen(mysite) - 1] = '\0';      /* remove '\n' */
        !           287:        fclose(uufile);
        !           288:        return;
        !           289: }
        !           290: 
        !           291: domainname()
        !           292: {
        !           293:        FILE *domfile;
        !           294:        if((domfile = fopen(DOMAINNAME, "r")) == NULL) {
        !           295:                strcpy(domain, ".UNKNOWN");
        !           296:                return;
        !           297:        }
        !           298:        fgets(domain, sizeof domain, domfile);
        !           299:        domain [strlen(domain) - 1] = '\0';
        !           300:        fclose (domfile);
        !           301:        return;
        !           302: }
        !           303: 
        !           304: char *
        !           305: arpadate(tp)
        !           306: struct tm      *tp;
        !           307: {
        !           308:        static  char arpabuf [64];
        !           309:        static  char months[] = "JanFebMarAprMayJunJulAugSepOctNovDec";
        !           310:        sprintf(arpabuf, "%d %c%c%c %d %02d:%02d:%02d",
        !           311:                tp->tm_mday,
        !           312:                months[tp->tm_mon * 3],
        !           313:                months[tp->tm_mon * 3 + 1],
        !           314:                months[tp->tm_mon * 3 + 2],
        !           315:                tp->tm_year,
        !           316:                tp->tm_hour, tp->tm_min, tp->tm_sec);
        !           317:        return arpabuf;
        !           318: }
        !           319: 
        !           320: char *
        !           321: msgid(tp)
        !           322: struct tm      *tp;
        !           323: {
        !           324:        static  char    msgidbuf [32];
        !           325:        sprintf(msgidbuf, "%02d%02d%02d%02d%02d",
        !           326:        tp->tm_year, tp->tm_mon + 1, tp->tm_mday, tp->tm_hour, tp->tm_min);
        !           327:        return msgidbuf;
        !           328: }
        !           329: 
        !           330: build_header(xfp)
        !           331: FILE   *xfp;
        !           332: {
        !           333:        char    **ulist;
        !           334:        int     processid;
        !           335: 
        !           336:        /* Generate a Message-Id.  */
        !           337:        processid = getpid();
        !           338:        sprintf(header, "Message-Id: <%s.AA%d.V%s@%s.%s>\n",
        !           339:                msgid(tp), processid, revnop(), mysite, domain);
        !           340:        if (fwrite(header, strlen(header), 1, xfp) != 1)
        !           341:                return 0;
        !           342: 
        !           343:        /* generate Date: and From: lines.  */
        !           344:        sprintf(header, "Date: %s\nFrom: %s@%s.%s (%s)\n",
        !           345:                arpadate(tp), myname, mysite, domain, myfullname);
        !           346:        if (fwrite(header, strlen(header), 1, xfp) != 1)
        !           347:                return 0;
        !           348: 
        !           349:        /* Generate the full To: lines.  We just spit addresses out
        !           350:           verbatum, with no cleanup.  */
        !           351:        strcpy(header, "To:");
        !           352:        for (ulist=tolist; *ulist != NULL; ulist++) {
        !           353:                strcat(header, " ");
        !           354:                strcat(header, *ulist);
        !           355:        }
        !           356:        strcat(header, "\n");
        !           357:        if (fwrite(header, strlen(header), 1, xfp) != 1)
        !           358:                return 0;
        !           359: 
        !           360:        /* Generate a Cc: line if needed.  */
        !           361:        if (cclist[0] != NULL) {
        !           362:                strcpy(header, "Cc:");
        !           363:                for (ulist=cclist; *ulist != NULL; ulist++) {
        !           364:                        strcat(header, " ");
        !           365:                        strcat(header, *ulist);
        !           366:                }
        !           367:                strcat(header, "\n");
        !           368:                if (fwrite(header, strlen(header), 1, xfp) != 1)
        !           369:                        return 0;
        !           370:        }
        !           371:        return 1;
        !           372: }
        !           373: 

unix.superglobalmegacorp.com

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