]> diplodocus.org Git - nmh/commitdiff
Require From: header in all outgoing messages.
authorKen Hornstein <kenh@pobox.com>
Mon, 12 Mar 2012 01:47:04 +0000 (21:47 -0400)
committerKen Hornstein <kenh@pobox.com>
Mon, 12 Mar 2012 01:56:18 +0000 (21:56 -0400)
Allow Sender: header (require if multiple addresses are in From:).
Support new Envelope-From: header for overriding post's choice of
SMTP envelope-from address.

man/mh-mail.man
man/send.man
uip/post.c

index 69e5fe4..87a0535 100644 (file)
@@ -99,12 +99,11 @@ profile entry.  It
 contains the address of the author or authors
 (may be more than one if a \*(lqSender:\*(rq field is present).  For a
 standard reply (using
 contains the address of the author or authors
 (may be more than one if a \*(lqSender:\*(rq field is present).  For a
 standard reply (using
-.BR repl ,
+.BR repl ),
 the reply address is constructed by
 checking the following headers (in this order): \*(lqMail-Reply\-To:\*(rq,
 \*(lqReply\-To:\*(rq, \*(lqFrom:\*(rq, \*(lqSender:\*(rq.
 the reply address is constructed by
 checking the following headers (in this order): \*(lqMail-Reply\-To:\*(rq,
 \*(lqReply\-To:\*(rq, \*(lqFrom:\*(rq, \*(lqSender:\*(rq.
-A
-.BR From :
+A \*(lqFrom:\*(rq
 header MUST exist when the message is sent to
 .BR post,
 otherwise the message will be rejected.
 header MUST exist when the message is sent to
 .BR post,
 otherwise the message will be rejected.
@@ -145,10 +144,11 @@ constructed by checking the following headers (in this order):
 .PP
 .BR Sender :
 .RS 5
 .PP
 .BR Sender :
 .RS 5
-Added by
+Required by
 .B post
 .B post
-in the event that the message already has a
-\*(lqFrom:\*(rq line.  This line contains the address of the actual
+in the event that the message has multiple addresses on the
+\*(lqFrom:\*(rq line.  It is otherwise optional.  This line should
+contain the address of the actual
 sender.
 .RE
 .PP
 sender.
 .RE
 .PP
@@ -162,14 +162,24 @@ Contains addresses of primary recipients.
 Contains addresses of secondary recipients.
 .RE
 .PP
 Contains addresses of secondary recipients.
 .RE
 .PP
-Bcc:
+.BR Bcc :
 .RS 5
 Still more recipients.  However, the \*(lqBcc:\*(rq line is not
 copied onto the message as delivered, so these recipients are not
 listed.
 .B nmh
 uses an encapsulation method for blind copies, see
 .RS 5
 Still more recipients.  However, the \*(lqBcc:\*(rq line is not
 copied onto the message as delivered, so these recipients are not
 listed.
 .B nmh
 uses an encapsulation method for blind copies, see
-.BR send .
+.BR send (1).
+.RE
+.PP
+.BR Dcc :
+.RS 5
+Still more recipients.  However, the \*(lqDcc:\*(rq line is not
+copied onto the messages as delivered.  Recipients on the \*(lqDcc:\*(rq
+line receive the same messsage as recipients on the \*(lqTo:\*(rq and
+\*(lqcc:\*(rq lines.  See
+.BR send (1)
+for more details.
 .RE
 .PP
 .BR Fcc :
 .RE
 .PP
 .BR Fcc :
index faf4d08..f4fea40 100644 (file)
@@ -278,16 +278,7 @@ switch, then
 will
 use the MIME rules for encapsulation.
 .PP
 will
 use the MIME rules for encapsulation.
 .PP
-Prior to sending the message, the fields \*(lqFrom:\ user@local\*(rq,
-and \*(lqDate:\ now\*(rq will be appended to the headers in the message.
-If the environment variable
-.B $SIGNATURE
-is set, then its value
-is used as your personal name when constructing the \*(lqFrom:\*(rq
-line of the message.  If this environment variable is not set, then
-.B send
-will consult the profile entry \*(lqSignature\*(rq for
-this information.
+Prior to sending the message, the \*(lqDate:\ now\*(rq field will be appended to the headers in the message.
 If
 .B \-msgid
 is specified, then a \*(lqMessage\-ID:\*(rq field will also
 If
 .B \-msgid
 is specified, then a \*(lqMessage\-ID:\*(rq field will also
@@ -299,9 +290,19 @@ is re\-distributing a message (when invoked by
 .BR dist ),
 then \*(lqResent\-\*(rq will be prepended to each of these
 fields: \*(lqFrom:\*(rq, \*(lqDate:\*(rq, and \*(lqMessage\-ID:\*(rq.
 .BR dist ),
 then \*(lqResent\-\*(rq will be prepended to each of these
 fields: \*(lqFrom:\*(rq, \*(lqDate:\*(rq, and \*(lqMessage\-ID:\*(rq.
-If the message already contains a \*(lqFrom:\*(rq field, then a
-\*(lqSender: user@local\*(rq field will be added as well.  (An already
-existing \*(lqSender:\*(rq field is an error!)
+.PP
+A \*(lqFrom:\*(rq field is required for all outgoing messages.  Multiple
+addresses are permitted in the \*(lqFrom:\*(rq field, but a \*(lqSender:\*(rq
+field is required in this case.  Otherwise a \*(lqSender:\*(rq field
+is optional.
+.PP
+When using SMTP for mail submission, the envelope\-from used for SMTP
+transaction is derived from the \*(lqFrom:\*(rq field.  If multiple
+addresses are in the \*(lqFrom:\*(rq field, the address in the
+\*(lqSender\*(rq field is used instead.  This behavior can be overridden
+by using the \*(lqEnvelope\-From:\*(rq field.  When \*(lqEnvelope\-From\*(rq
+appears in the message, its address will be used as the SMTP envelope\-from
+address and the field will be removed from the message.
 .PP
 By using the
 .B \-format
 .PP
 By using the
 .B \-format
index 83e008d..79a53aa 100644 (file)
@@ -158,6 +158,8 @@ struct headers {
 #define        HNIL  0x0100            /* okay for this header not to have addrs */
 #define        HIGN  0x0200            /* ignore this header                     */
 #define        HDCC  0x0400            /* another undocumented feature           */
 #define        HNIL  0x0100            /* okay for this header not to have addrs */
 #define        HIGN  0x0200            /* ignore this header                     */
 #define        HDCC  0x0400            /* another undocumented feature           */
+#define HONE  0x0800           /* Only one address allowed               */
+#define HEFM  0x1000           /* Envelope-From: header                  */
 
 /*
  * flags for headers->set
 
 /*
  * flags for headers->set
@@ -167,29 +169,33 @@ struct headers {
 #define        MRFM  0x0004            /* we've seen a Resent-From: */
 #define        MVIS  0x0008            /* we've seen sighted addrs  */
 #define        MINV  0x0010            /* we've seen blind addrs    */
 #define        MRFM  0x0004            /* we've seen a Resent-From: */
 #define        MVIS  0x0008            /* we've seen sighted addrs  */
 #define        MINV  0x0010            /* we've seen blind addrs    */
+#define MSND  0x0020           /* we've seen a Sender:      */
+#define MRSN  0x0040           /* We've seen a Resent-Sendr:*/
+#define MEFM  0x0080           /* We've seen Envelope-From: */
 
 
 static struct headers NHeaders[] = {
 
 
 static struct headers NHeaders[] = {
-    { "Return-Path", HBAD,                0 },
-    { "Received",    HBAD,                0 },
-    { "Reply-To",    HADR|HNGR,           0 },
-    { "From",        HADR|HNGR,           MFRM },
-    { "Sender",      HADR|HBAD,           0 },
-    { "Date",        HBAD,                0 },
-    { "Subject",     HSUB,                0 },
-    { "To",          HADR|HTRY,           MVIS },
-    { "cc",          HADR|HTRY,           MVIS },
-    { "Bcc",         HADR|HTRY|HBCC|HNIL, MINV },
-    { "Dcc",         HADR|HTRY|HDCC|HNIL, MVIS },      /* sorta cc & bcc combined */
-    { "Message-ID",  HBAD,                0 },
-    { "Fcc",         HFCC,                0 },
-    { NULL,          0,                   0 }
+    { "Return-Path",   HBAD,                0 },
+    { "Received",      HBAD,                0 },
+    { "Reply-To",      HADR|HNGR,           0 },
+    { "From",          HADR|HNGR,           MFRM },
+    { "Sender",        HADR|HNGR|HONE,      MSND },
+    { "Date",          HBAD,                0 },
+    { "Subject",       HSUB,                0 },
+    { "To",            HADR|HTRY,           MVIS },
+    { "cc",            HADR|HTRY,           MVIS },
+    { "Bcc",           HADR|HTRY|HBCC|HNIL, MINV },
+    { "Dcc",           HADR|HTRY|HDCC|HNIL, MVIS },    /* sorta cc & bcc combined */
+    { "Message-ID",    HBAD,                0 },
+    { "Fcc",           HFCC,                0 },
+    { "Envelope-From", HADR|HONE|HEFM,      MEFM },
+    { NULL,            0,                   0 }
 };
 
 static struct headers RHeaders[] = {
     { "Resent-Reply-To",   HADR|HNGR,           0 },
     { "Resent-From",       HADR|HNGR,           MRFM },
 };
 
 static struct headers RHeaders[] = {
     { "Resent-Reply-To",   HADR|HNGR,           0 },
     { "Resent-From",       HADR|HNGR,           MRFM },
-    { "Resent-Sender",     HADR|HBAD,           0 },
+    { "Resent-Sender",     HADR|HNGR,           MRSN },
     { "Resent-Date",       HBAD,                0 },
     { "Resent-Subject",    HSUB,                0 },
     { "Resent-To",         HADR|HTRY,           MVIS },
     { "Resent-Date",       HBAD,                0 },
     { "Resent-Subject",    HSUB,                0 },
     { "Resent-To",         HADR|HTRY,           MVIS },
@@ -199,12 +205,13 @@ static struct headers RHeaders[] = {
     { "Resent-Fcc",        HFCC,                0 },
     { "Reply-To",          HADR,                0 },
     { "From",              HADR|HNGR,           MFRM },
     { "Resent-Fcc",        HFCC,                0 },
     { "Reply-To",          HADR,                0 },
     { "From",              HADR|HNGR,           MFRM },
-    { "Sender",            HADR|HNGR,           0 },
+    { "Sender",            HADR|HNGR,           MSND },
     { "Date",              HNOP,                MDAT },
     { "To",                HADR|HNIL,           0 },
     { "cc",                HADR|HNIL,           0 },
     { "Bcc",               HADR|HTRY|HBCC|HNIL, 0 },
     { "Fcc",               HIGN,                0 },
     { "Date",              HNOP,                MDAT },
     { "To",                HADR|HNIL,           0 },
     { "cc",                HADR|HNIL,           0 },
     { "Bcc",               HADR|HTRY|HBCC|HNIL, 0 },
     { "Fcc",               HIGN,                0 },
+    { "Envelope-From",     HADR|HONE|HEFM,      MEFM },
     { NULL,                0,                   0 }
 };
 
     { NULL,                0,                   0 }
 };
 
@@ -234,6 +241,8 @@ static char *saslmech=NULL; /* Force use of particular SASL mech     */
 static char *user=NULL;                /* Authenticate as this user             */
 static char *port="smtp";      /* Name of server port for SMTP          */
 static int tls=0;              /* Use TLS for encryption                */
 static char *user=NULL;                /* Authenticate as this user             */
 static char *port="smtp";      /* Name of server port for SMTP          */
 static int tls=0;              /* Use TLS for encryption                */
+static int fromcount=0;                /* Count of addresses on From: header    */
+static int seensender=0;       /* Have we seen a Sender: header?        */
 
 static unsigned msgflags = 0;  /* what we've seen */
 
 
 static unsigned msgflags = 0;  /* what we've seen */
 
@@ -249,6 +258,8 @@ static char tmpfil[BUFSIZ];
 static char bccfil[BUFSIZ];
 
 static char from[BUFSIZ];      /* my network address            */
 static char bccfil[BUFSIZ];
 
 static char from[BUFSIZ];      /* my network address            */
+static char sender[BUFSIZ];    /* my Sender: header             */
+static char efrom[BUFSIZ];     /* my Envelope-From: header      */
 static char signature[BUFSIZ]; /* my signature                  */
 static char *filter = NULL;    /* the filter for BCC'ing        */
 static char *subject = NULL;   /* the subject field for BCC'ing */
 static char signature[BUFSIZ]; /* my signature                  */
 static char *filter = NULL;    /* the filter for BCC'ing        */
 static char *subject = NULL;   /* the subject field for BCC'ing */
@@ -272,8 +283,6 @@ static char prefix[] = "----- =_aaaaaaaaaa";
 static char *partno = NULL;
 static int queued = 0;
 
 static char *partno = NULL;
 static int queued = 0;
 
-extern boolean  draft_from_masquerading;  /* defined in mts.c */
-
 /*
  * static prototypes
  */
 /*
  * static prototypes
  */
@@ -289,14 +298,14 @@ static void anno (void);
 static int annoaux (struct mailname *);
 static void insert_fcc (struct headers *, unsigned char *);
 static void make_bcc_file (int);
 static int annoaux (struct mailname *);
 static void insert_fcc (struct headers *, unsigned char *);
 static void make_bcc_file (int);
-static void verify_all_addresses (int);
+static void verify_all_addresses (int, char *);
 static void chkadr (void);
 static void sigon (void);
 static void sigoff (void);
 static void p_refile (char *);
 static void fcc (char *, char *);
 static void die (char *, char *, ...);
 static void chkadr (void);
 static void sigon (void);
 static void sigoff (void);
 static void p_refile (char *);
 static void fcc (char *, char *);
 static void die (char *, char *, ...);
-static void post (char *, int, int);
+static void post (char *, int, int, char *);
 static void do_text (char *file, int fd);
 static void do_an_address (struct mailname *, int);
 static void do_addresses (int, int);
 static void do_text (char *file, int fd);
 static void do_an_address (struct mailname *, int);
 static void do_addresses (int, int);
@@ -307,7 +316,7 @@ int
 main (int argc, char **argv)
 {
     int state, compnum, dashstuff = 0;
 main (int argc, char **argv)
 {
     int state, compnum, dashstuff = 0;
-    char *cp, *msg = NULL, **argp, **arguments;
+    char *cp, *msg = NULL, **argp, **arguments, *envelope;
     char buf[BUFSIZ], name[NAMESZ];
     FILE *in, *out;
 
     char buf[BUFSIZ], name[NAMESZ];
     FILE *in, *out;
 
@@ -608,22 +617,40 @@ main (int argc, char **argv)
        fclose (out);
     }
 
        fclose (out);
     }
 
+    /*
+     * Here's how we decide which address to use as the envelope-from
+     * address for SMTP.
+     *
+     * - If we were given an Envelope-From header, use that.
+     * - If we were given multiple addresses in the From: header, use
+     *   the Sender: address
+     * - Otherwise, use the address on the From: line
+     */
+
+    if (msgflags & MEFM) {
+       envelope = efrom;
+    } else if (fromcount > 1) {
+       envelope = sender;
+    } else {
+       envelope = from;
+    }
+
     /* If we are doing a "whom" check */
     if (whomsw) {
     /* If we are doing a "whom" check */
     if (whomsw) {
-       verify_all_addresses (1);
+       verify_all_addresses (1, envelope);
        done (0);
     }
 
     if (msgflags & MINV) {
        make_bcc_file (dashstuff);
        if (msgflags & MVIS) {
        done (0);
     }
 
     if (msgflags & MINV) {
        make_bcc_file (dashstuff);
        if (msgflags & MVIS) {
-           verify_all_addresses (verbose);
-           post (tmpfil, 0, verbose);
+           verify_all_addresses (verbose, envelope);
+           post (tmpfil, 0, verbose, envelope);
        }
        }
-       post (bccfil, 1, verbose);
+       post (bccfil, 1, verbose, envelope);
        unlink (bccfil);
     } else {
        unlink (bccfil);
     } else {
-       post (tmpfil, 0, isatty (1));
+       post (tmpfil, 0, isatty (1), envelope);
     }
 
     p_refile (tmpfil);
     }
 
     p_refile (tmpfil);
@@ -720,6 +747,12 @@ putfmt (char *name, char *str, FILE *out)
        return;
     }
 
        return;
     }
 
+    if (count > 1 && (hdr->flags & HONE)) {
+       advise (NULL, "%s: field only permits one address", name);
+       badmsg++;
+       return;
+    }
+
     nameoutput = linepos = 0;
     snprintf (namep, sizeof(namep), "%s%s",
                (hdr->flags & HMNG) ? "Original-" : "", name);
     nameoutput = linepos = 0;
     snprintf (namep, sizeof(namep), "%s%s",
                (hdr->flags & HMNG) ? "Original-" : "", name);
@@ -738,17 +771,37 @@ putfmt (char *name, char *str, FILE *out)
                    continue;
                }
 
                    continue;
                }
 
-               if (draft_from_masquerading && ((msgstate == RESENT)
-                                               ? (hdr->set & MRFM)
-                                               : (hdr->set & MFRM)))
-                   /* The user manually specified a [Resent-]From: address in
-                      their draft and the "masquerade:" line in mts.conf
-                      doesn't contain "draft_from", so we'll set things up to
-                      use the actual email address embedded in the draft
-                      [Resent-]From: (after alias substitution, and without the
-                      GECOS full name or angle brackets) as the envelope
-                      From:. */
+               /*
+                * If it's a From: or Resent-From: header, save the address
+                * for later possible use (as the envelope address for SMTP)
+                */
+
+               if ((msgstate == RESENT) ? (hdr->set & MRFM)
+                                               : (hdr->set & MFRM)) {
                    strncpy(from, auxformat(mp, 0), sizeof(from) - 1);
                    strncpy(from, auxformat(mp, 0), sizeof(from) - 1);
+                   from[sizeof(from) - 1] = '\0';
+                   fromcount = count;
+               }
+
+               /*
+                * Also save the Sender: or Resent-Sender: header as well
+                */
+
+               if ((msgstate == RESENT) ? (hdr->set & MRSN)
+                                               : (hdr->set & MSND)) {
+                   strncpy(sender, auxformat(mp, 0), sizeof(sender) - 1);
+                   sender[sizeof(sender) - 1] = '\0';
+                   seensender++;
+               }
+
+               /*
+                * ALSO ... save Envelope-From
+                */
+
+               if (hdr->set & MEFM) {
+                   strncpy(efrom, auxformat(mp, 0), sizeof(efrom) - 1);
+                   efrom[sizeof(efrom) - 1] = '\0';
+               }
 
                if (hdr->flags & HBCC)
                    mp->m_bcc++;
 
                if (hdr->flags & HBCC)
                    mp->m_bcc++;
@@ -770,17 +823,37 @@ putfmt (char *name, char *str, FILE *out)
        }
        else {
            /* Address includes a host, so no alias substitution is needed. */
        }
        else {
            /* Address includes a host, so no alias substitution is needed. */
-           if (draft_from_masquerading && ((msgstate == RESENT)
-                                           ? (hdr->set & MRFM)
-                                           : (hdr->set & MFRM)))
-               /* The user manually specified a [Resent-]From: address in
-                  their draft and the "masquerade:" line in mts.conf
-                  doesn't contain "draft_from", so we'll set things up to
-                  use the actual email address embedded in the draft
-                  [Resent-]From: (after alias substitution, and without the
-                  GECOS full name or angle brackets) as the envelope
-                  From:. */
+
+           /*
+            * If it's a From: or Resent-From header, save the address
+            * for later possible use (as the envelope address for SMTP)
+            */
+
+           if ((msgstate == RESENT) ? (hdr->set & MRFM)
+                                           : (hdr->set & MFRM)) {
                strncpy(from, auxformat(mp, 0), sizeof(from) - 1);
                strncpy(from, auxformat(mp, 0), sizeof(from) - 1);
+               fromcount = count;
+           }
+
+           /*
+            * Also save the Sender: header as well
+            */
+
+           if ((msgstate == RESENT) ? (hdr->set & MRSN)
+                                           : (hdr->set & MSND)) {
+               strncpy(sender, auxformat(mp, 0), sizeof(sender) - 1);
+               sender[sizeof(sender) - 1] = '\0';
+               seensender++;
+           }
+
+           /*
+            * ALSO ... save Envelope-From
+            */
+
+           if (hdr->set & MEFM) {
+               strncpy(efrom, auxformat(mp, 0), sizeof(efrom) - 1);
+               efrom[sizeof(efrom) - 1] = '\0';
+           }
 
            if (hdr->flags & HBCC)
                mp->m_bcc++;
 
            if (hdr->flags & HBCC)
                mp->m_bcc++;
@@ -853,6 +926,21 @@ finish_headers (FILE *out)
 {
     switch (msgstate) {
        case NORMAL: 
 {
     switch (msgstate) {
        case NORMAL: 
+           if (!(msgflags & MFRM)) {
+               /*
+                * A From: header is now required in the draft.
+                */
+               advise (NULL, "message has no From: header");
+               advise (NULL, "See default components files for examples");
+               badmsg++;
+           }
+
+           if (fromcount > 1 && seensender == 0) {
+               advise (NULL, "A Sender: header is required with multiple "
+                       "From: addresses");
+               badmsg++;
+           }
+
            if (whomsw)
                break;
 
            if (whomsw)
                break;
 
@@ -860,21 +948,6 @@ finish_headers (FILE *out)
            if (msgid)
                fprintf (out, "Message-ID: <%d.%ld@%s>\n",
                        (int) getpid (), (long) tclock, LocalName (1));
            if (msgid)
                fprintf (out, "Message-ID: <%d.%ld@%s>\n",
                        (int) getpid (), (long) tclock, LocalName (1));
-           if (msgflags & MFRM) {
-               /* There was already a From: in the draft.  Don't add one. */
-               if (!draft_from_masquerading)
-                   /* mts.conf didn't contain "masquerade:[...]draft_from[...]"
-                      so we'll reveal the user's actual account@thismachine
-                      address in a Sender: header (and use it as the envelope
-                      From: later). */
-                   fprintf (out, "Sender: %s\n", from);
-           }
-           else
-               /* Construct a From: header. */
-               fprintf (out, "From: %s\n", signature);
-           if (whomsw)
-               break;
-
            if (!(msgflags & MVIS))
                fprintf (out, "Bcc: Blind Distribution List: ;\n");
            break;
            if (!(msgflags & MVIS))
                fprintf (out, "Bcc: Blind Distribution List: ;\n");
            break;
@@ -888,6 +961,17 @@ finish_headers (FILE *out)
                advise (NULL, "message has no From: header");
                badmsg++;
            }
                advise (NULL, "message has no From: header");
                badmsg++;
            }
+           if (!(msgflags & MRFM)) {
+               advise (NULL, "message has no Resent-From: header");
+               advise (NULL, "See default components files for examples");
+               badmsg++;
+           }
+           if (fromcount > 1 && seensender == 0) {
+               advise (NULL, "A Resent-Sender: header is required with "
+                       "multiple Resent-From: addresses");
+               badmsg++;
+           }
+
            if (whomsw)
                break;
 
            if (whomsw)
                break;
 
@@ -895,20 +979,6 @@ finish_headers (FILE *out)
            if (msgid)
                fprintf (out, "Resent-Message-ID: <%d.%ld@%s>\n",
                        (int) getpid (), (long) tclock, LocalName (1));
            if (msgid)
                fprintf (out, "Resent-Message-ID: <%d.%ld@%s>\n",
                        (int) getpid (), (long) tclock, LocalName (1));
-           if (msgflags & MRFM) {
-               /* There was already a Resent-From: in draft.  Don't add one. */
-               if (!draft_from_masquerading)
-                   /* mts.conf didn't contain "masquerade:[...]draft_from[...]"
-                      so we'll reveal the user's actual account@thismachine
-                      address in a Sender: header (and use it as the envelope
-                      From: later). */
-                   fprintf (out, "Resent-Sender: %s\n", from);
-           }
-           else
-               /* Construct a Resent-From: header. */
-               fprintf (out, "Resent-From: %s\n", signature);
-           if (whomsw)
-               break;
            if (!(msgflags & MVIS))
                fprintf (out, "Resent-Bcc: Blind Re-Distribution List: ;\n");
            break;
            if (!(msgflags & MVIS))
                fprintf (out, "Resent-Bcc: Blind Re-Distribution List: ;\n");
            break;
@@ -943,7 +1013,7 @@ putadr (char *name, char *aka, struct mailname *mp, FILE *out, unsigned int flag
 
     if (mp->m_mbox == NULL || ((flags & HTRY) && !insert (mp)))
        return 0;
 
     if (mp->m_mbox == NULL || ((flags & HTRY) && !insert (mp)))
        return 0;
-    if ((flags & (HBCC | HDCC)) || mp->m_ingrp)
+    if ((flags & (HBCC | HDCC | HEFM)) || mp->m_ingrp)
        return 1;
 
     if (!nameoutput) {
        return 1;
 
     if (!nameoutput) {
@@ -1147,18 +1217,6 @@ make_bcc_file (int dashstuff)
     if (msgid)
        fprintf (out, "Message-ID: <%d.%ld@%s>\n",
                (int) getpid (), (long) tclock, LocalName (1));
     if (msgid)
        fprintf (out, "Message-ID: <%d.%ld@%s>\n",
                (int) getpid (), (long) tclock, LocalName (1));
-    if (msgflags & MFRM) {
-      /* There was already a From: in the draft.  Don't add one. */
-      if (!draft_from_masquerading)
-        /* mts.conf didn't contain "masquerade:[...]draft_from[...]"
-           so we'll reveal the user's actual account@thismachine
-           address in a Sender: header (and use it as the envelope
-           From: later). */
-        fprintf (out, "Sender: %s\n", from);
-    }
-    else
-      /* Construct a From: header. */
-      fprintf (out, "From: %s\n", signature);
     if (subject)
        fprintf (out, "Subject: %s", subject);
     fprintf (out, "BCC:\n");
     if (subject)
        fprintf (out, "Subject: %s", subject);
     fprintf (out, "BCC:\n");
@@ -1359,7 +1417,7 @@ do_addresses (int bccque, int talk)
  */
 
 static void
  */
 
 static void
-post (char *file, int bccque, int talk)
+post (char *file, int bccque, int talk, char *envelope)
 {
     int fd, onex;
     int        retval;
 {
     int fd, onex;
     int        retval;
@@ -1378,7 +1436,7 @@ post (char *file, int bccque, int talk)
     if (rp_isbad (retval = sm_init (clientsw, serversw, port, watch, verbose,
                                    snoop, onex, queued, sasl, saslssf,
                                    saslmech, user, tls))
     if (rp_isbad (retval = sm_init (clientsw, serversw, port, watch, verbose,
                                    snoop, onex, queued, sasl, saslssf,
                                    saslmech, user, tls))
-           || rp_isbad (retval = sm_winit (from)))
+           || rp_isbad (retval = sm_winit (envelope)))
        die (NULL, "problem initializing server; %s", rp_string (retval));
 
     do_addresses (bccque, talk && verbose);
        die (NULL, "problem initializing server; %s", rp_string (retval));
 
     do_addresses (bccque, talk && verbose);
@@ -1406,7 +1464,7 @@ post (char *file, int bccque, int talk)
 /* Address Verification */
 
 static void
 /* Address Verification */
 
 static void
-verify_all_addresses (int talk)
+verify_all_addresses (int talk, char *envelope)
 {
     int retval;
     struct mailname *lp;
 {
     int retval;
     struct mailname *lp;
@@ -1417,7 +1475,7 @@ verify_all_addresses (int talk)
        if (rp_isbad (retval = sm_init (clientsw, serversw, port, watch,
                                        verbose, snoop, 0, queued, sasl,
                                        saslssf, saslmech, user, tls))
        if (rp_isbad (retval = sm_init (clientsw, serversw, port, watch,
                                        verbose, snoop, 0, queued, sasl,
                                        saslssf, saslmech, user, tls))
-               || rp_isbad (retval = sm_winit (from)))
+               || rp_isbad (retval = sm_winit (envelope)))
            die (NULL, "problem initializing server; %s", rp_string (retval));
 
     if (talk && !whomsw)
            die (NULL, "problem initializing server; %s", rp_string (retval));
 
     if (talk && !whomsw)