There have been some rather important fixes to smtpd since 5.5
release. If you're using smtpd on 5.5, you probably want to apply them.

(My plan is to commit to stable eventually, but since it's very
important not to introduce regressions, I'm asking for a little help
testing the backport.)

++
fix writing of multiline To and Cc headers

issue spotted, fix tested and okayed krw@

++
fix header parsing issue in enqueuer leading to From: header being
stripped in some cases

ok eric@

++
when locally enqueuing messages without specifying a domain for sender
or recipient, the local domain is assumed. this was correctly handled
at the smtp level, but headers were not updated to reflect that.

issue experienced by several people, fix tested by ajacoutot@ and I
ok eric@

++
The enqueue utility should not add a User-Agent header to emails.

ok gilles jcs


Index: enqueue.c
===================================================================
RCS file: /cvs/src/usr.sbin/smtpd/enqueue.c,v
retrieving revision 1.75
diff -u -p -r1.75 enqueue.c
--- enqueue.c   4 Feb 2014 15:44:05 -0000       1.75
+++ enqueue.c   30 May 2014 19:59:19 -0000
@@ -159,6 +159,47 @@ qp_encoded_write(FILE *fp, char *buf, si
        }
 }
 
+static void
+send_header(FILE *fout, const char *line, size_t len)
+{
+       int     i;
+
+       if (strncasecmp("To:", line, 3) != 0 &&
+           strncasecmp("Cc:", line, 3) != 0 &&
+           strncasecmp("Bcc:", line, 4) != 0 &&
+           strncasecmp("From:", line, 5) != 0) {
+               send_line(fout, 0, "%.*s", (int)len, line);
+               return;
+       }
+       if (len >= sizeof pstate.buf) {
+               send_line(fout, 0, "%.*s", (int)len, line);
+               return;
+       }
+
+       /* XXX
+        * To, Cc and Bcc may need rewrite, we can reuse the
+        * msg recipients field since former content has already
+        * been used at this point.
+        */
+       memset(&pstate, 0, sizeof(pstate));
+       memcpy(pstate.buf, line, len);
+       pstate.buf[len] = 0;
+       pstate.wpos = len - 1;
+       msg.rcpts = NULL;
+       msg.rcpt_cnt = 0;
+
+       if (strncasecmp("From:", line, 5) == 0) {
+               parse_addr_terminal(1);
+               send_line(fout, 0, "%s\n", msg.from);
+       }
+       else {
+               parse_addr_terminal(0);
+               for (i = 0; i < msg.rcpt_cnt; ++i)
+                       send_line(fout, 0, "%s%s%s\n", i > 0 ? "\t" : "",
+                           msg.rcpts[i], i < msg.rcpt_cnt - 1 ? "," : "");
+       }
+}
+
 int
 enqueue(int argc, char *argv[])
 {
@@ -336,9 +377,6 @@ enqueue(int argc, char *argv[])
                        send_line(fout, 0, "Content-Transfer-Encoding: "
                            "quoted-printable\n");
        }
-       if (!msg.saw_user_agent)
-               send_line(fout, 0, "User-Agent: %s enqueuer (%s)\n",
-                   SMTPD_NAME, "Demoostik");
 
        /* add separating newline */
        if (noheader)
@@ -366,7 +404,10 @@ enqueue(int argc, char *argv[])
 
                if (msg.saw_content_transfer_encoding || noheader ||
                    inheaders || !msg.need_linesplit) {
-                       send_line(fout, 0, "%.*s", (int)len, line);
+                       if (inheaders)
+                               send_header(fout, line, len);
+                       else
+                               send_line(fout, 0, "%.*s", (int)len, line);
                        if (inheaders && buf[0] == '\n')
                                inheaders = 0;
                        continue;


Reply via email to