[exim-cvs] Limit expanded References header to RFC max size.…

Top Page
Delete this message
Reply to this message
Author: Exim Git Commits Mailing List
Date:  
To: exim-cvs
Subject: [exim-cvs] Limit expanded References header to RFC max size. Bug 2827
Gitweb: https://git.exim.org/exim.git/commitdiff/3607e3e00236f6039b765882edd0200dff6a31fc
Commit:     3607e3e00236f6039b765882edd0200dff6a31fc
Parent:     3af9f77fb401fe0e77a46a88415c6e45ed1a47bf
Author:     Jeremy Harris <jgh146exb@???>
AuthorDate: Thu Mar 16 15:49:59 2023 +0000
Committer:  Jeremy Harris <jgh146exb@???>
CommitDate: Thu Mar 16 17:04:28 2023 +0000


    Limit expanded References header to RFC max size.  Bug 2827
---
 doc/doc-txt/ChangeLog |  5 +++++
 src/src/deliver.c     |  1 +
 src/src/moan.c        | 35 +++++++++++++++++++++++++++--------
 test/confs/0032       | 27 +++++++++++++++++++++++++++
 test/mail/0032.CALLER |  3 ++-
 5 files changed, 62 insertions(+), 9 deletions(-)


diff --git a/doc/doc-txt/ChangeLog b/doc/doc-txt/ChangeLog
index 860e95d9d..71f71a6ca 100644
--- a/doc/doc-txt/ChangeLog
+++ b/doc/doc-txt/ChangeLog
@@ -114,6 +114,11 @@ JH/24 Bug 2997: When built with EXPERIMENTAL_DSN_INFO, bounce messages can
       by the delivering transport.  Alleviate by wrapping such lines before
       column 80.


+JH/25 Bug 2827: Restrict size of References: header in bounce messages to 998
+      chars (RFC limit).  Previously a limit of 12 items was made, which with
+      a not-impossible References: in the message being bounced could still
+      be over-large and get stopped in the transport.
+


Exim version 4.96
-----------------
diff --git a/src/src/deliver.c b/src/src/deliver.c
index e2994b116..57a435eeb 100644
--- a/src/src/deliver.c
+++ b/src/src/deliver.c
@@ -6178,6 +6178,7 @@ return_path = sender_address; /* In case not previously set */

/* Write the original email out */
/*XXX no checking for failure! buggy! */
+/*XXX overlong headers in the original become overlong body lines here*/
transport_write_message(&tctx, 0);
fflush(f);

diff --git a/src/src/moan.c b/src/src/moan.c
index ebfd440f6..9c30c8edd 100644
--- a/src/src/moan.c
+++ b/src/src/moan.c
@@ -80,11 +80,17 @@ if (!h)
/* We limit the total length of references. Although there is no fixed
limit, some systems do not like headers growing beyond recognition.
Keep the first message ID for the thread root and the last few for
-the position inside the thread, up to a maximum of 12 altogether. */
+the position inside the thread, up to a maximum of 12 altogether.
+Also apply the max line length limit from RFC 2822 2.1.1
+
+XXX preferably we would get any limit from the outbound transport,
+passed in here for a limit value.
+*/

 if (h || message_id)
   {
-  fprintf(fp, "References:");
+  unsigned use = fprintf(fp, "References:");
+  if (message_id) use += Ustrlen(message_id) + 1;
   if (h)
     {
     const uschar * s;
@@ -95,14 +101,27 @@ if (h || message_id)
     s = Ustrchr(h->text, ':') + 1;
     f.parse_allow_group = FALSE;
     while (*s && (s = parse_message_id(s, &id, &error)))
-      if (reference_count == nelem(referenced_ids))
-        {
-        memmove(referenced_ids + 1, referenced_ids + 2,
-           sizeof(referenced_ids) - 2*sizeof(uschar *));
-        referenced_ids[reference_count - 1] = id;
-        }
+      {
+      unsigned this = Ustrlen(id);
+      if (  reference_count == nelem(referenced_ids)
+     || use + this + reference_count > 998
+         )
+    {
+    if (reference_count > 1)
+      {
+      /* drop position 1 and shuffle down */
+      use -= Ustrlen(referenced_ids + 1);
+      memmove(referenced_ids + 1, referenced_ids + 2,
+         sizeof(referenced_ids) - 2*sizeof(*referenced_ids));
+
+      /* append new one */
+      referenced_ids[reference_count - 1] = id;
+      }
+    }
       else
     referenced_ids[reference_count++] = id;
+      use += this;
+      }


     for (int i = 0; i < reference_count; ++i)
       fprintf(fp, " %s", referenced_ids[i]);
diff --git a/test/confs/0032 b/test/confs/0032
index 8af551b0c..df02a034a 100644
--- a/test/confs/0032
+++ b/test/confs/0032
@@ -9,6 +9,33 @@ primary_hostname = myhost.ex


dsn_from = MailProgram <xyz@???>

+acl_not_smtp = add_insane_refs
+
+
+# ----- ACL -----
+
+begin acl
+
+# Put an overlong refs header on the message-to-be-bounced, so we can check the
+# bounce has a sane header
+
+add_insane_refs:
+  warn    !senders =    :
+      add_header =    References: \
+            <0.ZERO.78901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.ONE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.TWO.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.THREE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.FOUR.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.FIVE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.SIX.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.SEVEN.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.EIGHT.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.NINE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.TEN.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.ELEVEN.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> \
+            <0.TWELVE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???>
+  accept


# ----- Routers -----

diff --git a/test/mail/0032.CALLER b/test/mail/0032.CALLER
index ef3e2dde6..76aa97c73 100644
--- a/test/mail/0032.CALLER
+++ b/test/mail/0032.CALLER
@@ -10,7 +10,7 @@ X-Failed-Recipients: userx@???
Auto-Submitted: auto-replied
From: MailProgram <xyz@???>
To: CALLER@???
-References: <E10HmaX-0005vi-00@???>
+References: <0.ZERO.78901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.SIX.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.SEVEN.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.EIGHT.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.NINE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.TEN.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.ELEVEN.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.TWELVE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <E10HmaX-0005vi-00@???>
Content-Type: multipart/report; report-type=delivery-status; boundary=NNNNNNNNNN-eximdsn-MMMMMMMMMM
MIME-Version: 1.0
Subject: Mail delivery failed: returning message to sender
@@ -49,6 +49,7 @@ Received: from CALLER by myhost.ex with local (Exim x.yz)
Message-Id: <E10HmaX-0005vi-00@???>
From: CALLER_NAME <CALLER@???>
Date: Tue, 2 Mar 1999 09:44:33 +0000
+References: <0.ZERO.78901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.ONE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.TWO.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.THREE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.FOUR.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.FIVE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.SIX.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.SEVEN.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.EIGHT.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.NINE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.TEN.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.ELEVEN.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???> <0.TWELVE.678901234567890123456789012345678901234567890123456789012345678901234567890123456789012345678@???>

This is a test message.