Annotation of 41BSD/cmd/delivermail/maketemp.c, revision 1.1.1.1

1.1       root        1: # include <stdio.h>
                      2: # include <ctype.h>
                      3: # include <errno.h>
                      4: # include "dlvrmail.h"
                      5: 
                      6: static char    SccsId[] = "@(#)maketemp.c      1.6     10/27/80";
                      7: 
                      8: /*
                      9: **  MAKETEMP -- read & parse message header & make temp file.
                     10: **
                     11: **     Creates a temporary file name and copies the standard
                     12: **     input to that file.  While it is doing it, it looks for
                     13: **     "From:" and "Sender:" fields to use as the from-person
                     14: **     (but only if the -a flag is specified).  It prefers to
                     15: **     to use the "Sender:" field.
                     16: **
                     17: **     MIT seems to like to produce "Sent-By:" fields instead
                     18: **     of "Sender:" fields.  We used to catch this, but it turns
                     19: **     out that the "Sent-By:" field doesn't always correspond
                     20: **     to someone real ("___057", for instance), as required by
                     21: **     the protocol.  So we limp by.....
                     22: **
                     23: **     Parameters:
                     24: **             none
                     25: **
                     26: **     Returns:
                     27: **             Name of temp file.
                     28: **
                     29: **     Side Effects:
                     30: **             Temp file is created and filled.
                     31: **
                     32: **     Called By:
                     33: **             main
                     34: **
                     35: **     Notes:
                     36: **             This is broken off from main largely so that the
                     37: **             temp buffer can be deallocated.
                     38: */
                     39: 
                     40: char   MsgId[MAXNAME];         /* message-id, determined or created */
                     41: long   MsgSize;                /* size of message in bytes */
                     42: 
                     43: char *
                     44: maketemp()
                     45: {
                     46:        register FILE *tf;
                     47:        char buf[MAXFIELD+1];
                     48:        static char fbuf[sizeof buf];
                     49:        extern char *prescan();
                     50:        extern char *matchhdr();
                     51:        register char *p;
                     52:        register bool inheader;
                     53:        bool firstline;
                     54:        char c;
                     55:        extern int errno;
                     56: 
                     57:        /*
                     58:        **  Create the temp file name and create the file.
                     59:        */
                     60: 
                     61:        mktemp(InFileName);
                     62:        close(creat(InFileName, 0600));
                     63:        if ((tf = fopen(InFileName, "w")) == NULL)
                     64:        {
                     65:                syserr("Cannot create %s", InFileName);
                     66:                return (NULL);
                     67:        }
                     68: 
                     69:        /*
                     70:        **  Copy stdin to temp file & do message editting.
                     71:        **      From person gets copied into fbuf.  At the end of
                     72:        **      this loop, if fbuf[0] == '\0' then there was no
                     73:        **      recognized from person in the message.  We also
                     74:        **      save the message id in MsgId.  The
                     75:        **      flag 'inheader' keeps track of whether we are
                     76:        **      in the header or in the body of the message.
                     77:        **      The flag 'firstline' is only true on the first
                     78:        **      line of a message.
                     79:        **      To keep certain mailers from getting confused,
                     80:        **      and to keep the output clean, lines that look
                     81:        **      like UNIX "From" lines are deleted in the header,
                     82:        **      and prepended with ">" in the body.
                     83:        */
                     84: 
                     85:        inheader = TRUE;
                     86:        firstline = TRUE;
                     87:        fbuf[0] = '\0';
                     88:        while (fgets(buf, sizeof buf, stdin) != NULL)
                     89:        {
                     90:                if (inheader && isalnum(buf[0]))
                     91:                {
                     92:                        /* get the rest of this field */
                     93:                        while ((c = getc(stdin)) == ' ' || c == '\t')
                     94:                        {
                     95:                                p = &buf[strlen(buf)];
                     96:                                *p++ = c;
                     97:                                if (fgets(p, sizeof buf - (p - buf), stdin) == NULL)
                     98:                                        break;
                     99:                        }
                    100:                        if (c != EOF)
                    101:                                ungetc(c, stdin);
                    102:                }
                    103: 
                    104:                if (!IgnrDot && buf[0] == '.' && (buf[1] == '\n' || buf[1] == '\0'))
                    105:                        break;
                    106: 
                    107:                /* are we still in the header? */
                    108:                if ((buf[0] == '\n' || buf[0] == '\0') && inheader)
                    109:                {
                    110:                        inheader = FALSE;
                    111:                        if (MsgId[0] == '\0')
                    112:                        {
                    113:                                makemsgid();
                    114:                                if (UseMsgId)
                    115:                                        fprintf(tf, "Message-Id: <%s>\n", MsgId);
                    116:                        }
                    117: # ifdef DEBUG
                    118:                        if (Debug)
                    119:                                printf("EOH\n");
                    120: # endif DEBUG
                    121:                }
                    122: 
                    123:                /* Hide UNIX-like From lines */
                    124:                if (buf[0] == 'F' && buf[1] == 'r' && buf[2] == 'o' &&
                    125:                    buf[3] == 'm' && buf[4] == ' ')
                    126:                {
                    127:                        if (firstline && !SaveFrom)
                    128:                                continue;
                    129:                        fputs(">", tf);
                    130:                        MsgSize++;
                    131:                }
                    132: 
                    133:                if (inheader && !isspace(buf[0]))
                    134:                {
                    135:                        /* find out if this is really a header */
                    136:                        for (p = buf; *p != ':' && *p != '\0' && !isspace(*p); p++)
                    137:                                continue;
                    138:                        while (*p != ':' && isspace(*p))
                    139:                                p++;
                    140:                        if (*p != ':')
                    141:                        {
                    142:                                inheader = FALSE;
                    143: # ifdef DEBUG
                    144:                                if (Debug)
                    145:                                        printf("EOH?\n");
                    146: # endif DEBUG
                    147:                        }
                    148:                }
                    149: 
                    150:                if (inheader)
                    151:                {
                    152:                        /* find the sender */
                    153:                        p = matchhdr(buf, "sender");
                    154:                        if (p == NULL && fbuf[0] == '\0')
                    155:                                p = matchhdr(buf, "from");
                    156:                        if (p != NULL)
                    157:                                prescan(p, fbuf, &fbuf[sizeof fbuf - 1], '\0');
                    158: 
                    159:                        /* find the message id */
                    160:                        p = matchhdr(buf, "message-id");
                    161:                        if (p != NULL && MsgId[0] == '\0')
                    162:                                prescan(p, MsgId, &MsgId[sizeof MsgId - 1], '\0');
                    163:                }
                    164:                MsgSize += strlen(buf);
                    165:                fputs(buf, tf);
                    166:                firstline = FALSE;
                    167:                if (ferror(tf))
                    168:                {
                    169:                        if (errno == ENOSPC)
                    170:                        {
                    171:                                freopen(InFileName, "w", tf);
                    172:                                fputs("\nMAIL DELETED BECAUSE OF LACK OF DISK SPACE\n\n", tf);
                    173:                                syserr("Out of disk space for temp file");
                    174:                        }
                    175:                        else
                    176:                                syserr("Cannot write %s", InFileName);
                    177:                        freopen("/dev/null", "w", tf);
                    178:                }
                    179:        }
                    180:        fclose(tf);
                    181:        if (MsgId[0] == '\0')
                    182:                makemsgid();
                    183:        if (freopen(InFileName, "r", stdin) == NULL)
                    184:                syserr("Cannot reopen %s", InFileName);
                    185:        return (ArpaFmt && fbuf[0] != '\0' ? fbuf : NULL);
                    186: }
                    187: /*
                    188: **  MAKEMSGID -- Compute a message id for this process.
                    189: **
                    190: **     This routine creates a message id for a message if
                    191: **     it did not have one already.  If the MESSAGEID compile
                    192: **     flag is set, the messageid will be added to any message
                    193: **     that does not already have one.  Currently it is more
                    194: **     of an artifact, but I suggest that if you are hacking,
                    195: **     you leave it in -- I may want to use it someday if
                    196: **     duplicate messages turn out to be a problem.
                    197: **
                    198: **     Parameters:
                    199: **             none.
                    200: **
                    201: **     Returns:
                    202: **             none.
                    203: **
                    204: **     Side Effects:
                    205: **             Stores a message-id into MsgId.
                    206: **
                    207: **     Called By:
                    208: **             maketemp
                    209: */
                    210: 
                    211: makemsgid()
                    212: {
                    213:        auto long t;
                    214:        extern char *MyLocName;
                    215:        extern char *ArpaHost;
                    216: 
                    217:        time(&t);
                    218:        sprintf(MsgId, "%ld.%d.%s@%s", t, getpid(), MyLocName, ArpaHost);
                    219: }

unix.superglobalmegacorp.com

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