diff options
author | Dima Panov <fluffy@FreeBSD.org> | 2021-05-04 15:57:17 +0000 |
---|---|---|
committer | Dima Panov <fluffy@FreeBSD.org> | 2021-05-04 15:57:17 +0000 |
commit | 0a629bd71087f75c3b334edb53b01ec68709ab60 (patch) | |
tree | 7d9c838702ca91a5b1b07b7364b739220ccbd5c2 /mail/exim | |
parent | 0a60c9a8dca065d347dd71fa461393735f93490a (diff) |
mail/exim: update to 4.94.2 security release
* New upstream security release.
+ Release based on +fixes branch.
+ Fixes multiple security vulnerabilities reported by Qualys and adds
related robustness improvements. (Special thanks to Heiko)
CVE-2020-28023: Out-of-bounds read in smtp_setup_msg()
CVE-2020-28007: Link attack in Exim's log directory
CVE-2020-28016: Heap out-of-bounds write in parse_fix_phrase()
CVE-2020-28012: Missing close-on-exec flag for privileged pipe
CVE-2020-28024: Heap buffer underflow in smtp_ungetc()
CVE-2020-28009: Integer overflow in get_stdinput()
CVE-2020-28015, CVE-28021: New-line injection into spool header file
CVE-2020-28026: Line truncation and injection in spool_read_header()
CVE-2020-28022: Heap out-of-bounds read and write in extract_option()
CVE-2020-28017: Integer overflow in receive_add_recipient()
CVE-2020-28013: Heap buffer overflow in parse_fix_phrase()
CVE-2020-28011: Heap buffer overflow in queue_run()
CVE-2020-28010: Heap out-of-bounds write in main()
CVE-2020-28018: Use-after-free in tls-openssl.c
CVE-2020-28025: Heap out-of-bounds read in pdkim_finish_bodyhash()
CVE-2020-28014, CVE-2021-27216: PID file handling
CVE-2020-28008: Assorted attacks in Exim's spool directory
CVE-2020-28019: Failure to reset function pointer after BDAT error
* Incorporate debian patches to turn taint failures into warnings.
Diffstat (limited to 'mail/exim')
65 files changed, 1674 insertions, 3653 deletions
diff --git a/mail/exim/Makefile b/mail/exim/Makefile index 03104b5be175..b66114db3c6b 100644 --- a/mail/exim/Makefile +++ b/mail/exim/Makefile @@ -2,7 +2,7 @@ PORTNAME= exim PORTVERSION?= ${EXIM_VERSION} -PORTREVISION?= 5 +PORTREVISION?= 0 CATEGORIES= mail MASTER_SITES= EXIM:exim MASTER_SITE_SUBDIR= /exim4/:exim \ @@ -65,6 +65,33 @@ SPF_LIB_DEPENDS= libspf2.so:mail/libspf2 SQLITE_LIB_DEPENDS= libicudata.so:devel/icu SQLITE_USES= pkgconfig sqlite +TAINTWARN_PATCHES_PREFIX= ${FILESDIR}/debian/75 +TAINTWARN_EXTRA_PATCHES= \ + ${TAINTWARN_PATCHES_PREFIX}_01-Introduce-main-config-option-allow_insecure_tainted_.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_02-search.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_03-dbstuff.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_04-acl.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_05-parse.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_06-rda.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_07-appendfile.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_08-autoreply.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_09-pipe.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_10-deliver.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_11-directory.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_12-expand.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_13-lf_sqlperform.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_14-rf_get_transport.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_15-deliver.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_16-smtp_out.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_17-smtp.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_18-update-doc.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_20-Set-mainlog_name-and-rejectlog_name-unconditionally.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_21-tidy-log.c.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_22-Silence-compiler.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_23-Do-not-close-the-main-_log-if-we-do-not-see-a-chance.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_24-Silence-the-compiler.patch:-p1 \ + ${TAINTWARN_PATCHES_PREFIX}_26-Disable-taintchecks-for-mkdir-this-isn-t-part-of-4.9.patch:-p1 + .include <bsd.port.options.mk> # OCSP is supported for openssl only @@ -104,7 +131,7 @@ EXTRA_PATCHES+= ${FILESDIR}/extra-patch-Local-sa-exim.c EXTRA_PATCHES+= ${FILESDIR}/extra-patch-Local-sa-exim.conf .endif -EXIM_VERSION= 4.94 +EXIM_VERSION= 4.94.2 SA_EXIM_VERSION=4.2.1 EXIM_INSTALL_ARG+= "-no_chown" "-no_symlink" EXTRA_PATCHES+= `${FIND} ${PATCHDIR} -name '74_*.patch'|${SORT} -h` diff --git a/mail/exim/distinfo b/mail/exim/distinfo index 64c610468f1b..cf1ae320eaa8 100644 --- a/mail/exim/distinfo +++ b/mail/exim/distinfo @@ -1,5 +1,5 @@ -TIMESTAMP = 1591032067 -SHA256 (exim/exim-4.94.tar.bz2) = 73feeaa5ddb43363782db0c307b593aacb49542dd7e4b795a2880779595affe5 -SIZE (exim/exim-4.94.tar.bz2) = 1997217 +TIMESTAMP = 1620141511 +SHA256 (exim/exim-4.94.2.tar.bz2) = 902e611486400608691dff31e1d8725eb9e23602399ad75670ec18878643bc4f +SIZE (exim/exim-4.94.2.tar.bz2) = 2007178 SHA256 (exim/sa-exim-4.2.1.tar.gz) = 24d4bf7b0fdddaea11f132981cebb6a86a4ab20ef54111a8ebd481b421c6e2c1 SIZE (exim/sa-exim-4.2.1.tar.gz) = 68933 diff --git a/mail/exim/files/debian/75_01-Introduce-main-config-option-allow_insecure_tainted_.patch b/mail/exim/files/debian/75_01-Introduce-main-config-option-allow_insecure_tainted_.patch new file mode 100644 index 000000000000..0295ec18fa6e --- /dev/null +++ b/mail/exim/files/debian/75_01-Introduce-main-config-option-allow_insecure_tainted_.patch @@ -0,0 +1,230 @@ +From ec06d64532e4952fc36429f73e0222d26997ef7c Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Thu, 1 Apr 2021 22:44:31 +0200 +Subject: [PATCH 01/23] Introduce main config option + allow_insecure_tainted_data + +This option is deprecated already now. +--- + src/EDITME | 7 +++++ + src/config.h.defaults | 2 ++ + src/functions.h | 54 ++++++++++++++++++++++++++++++--------- + src/globals.c | 10 ++++++++ + src/globals.h | 4 +++ + src/macros.h | 3 +++ + src/readconf.c | 3 +++ + 7 files changed, 71 insertions(+), 12 deletions(-) + +diff --git a/src/EDITME b/src/EDITME +index 8da36a353..cebb8e2ec 100644 +--- a/src/EDITME ++++ b/src/EDITME +@@ -749,6 +749,13 @@ FIXED_NEVER_USERS=root + + # WHITELIST_D_MACROS=TLS:SPOOL + ++# The next setting enables a main config option ++# "allow_insecure_tainted_data" to turn taint failures into warnings. ++# Though this option is new, it is deprecated already now, and will be ++# ignored in future releases of Exim. It is meant as mitigation for ++# upgrading old (possibly insecure) configurations to more secure ones. ++ALLOW_INSECURE_TAINTED_DATA=yes ++ + #------------------------------------------------------------------------------ + # Exim has support for the AUTH (authentication) extension of the SMTP + # protocol, as defined by RFC 2554. If you don't know what SMTP authentication +diff --git a/src/config.h.defaults b/src/config.h.defaults +index e17f015f9..4e8b18904 100644 +--- a/src/config.h.defaults ++++ b/src/config.h.defaults +@@ -17,6 +17,8 @@ Do not put spaces between # and the 'define'. + #define ALT_CONFIG_PREFIX + #define TRUSTED_CONFIG_LIST + ++#define ALLOW_INSECURE_TAINTED_DATA ++ + #define APPENDFILE_MODE 0600 + #define APPENDFILE_DIRECTORY_MODE 0700 + #define APPENDFILE_LOCKFILE_MODE 0600 +diff --git a/src/functions.h b/src/functions.h +index 51bb17a09..1e8083673 100644 +--- a/src/functions.h ++++ b/src/functions.h +@@ -1083,36 +1083,66 @@ if (f.running_in_test_harness && f.testsuite_delays) millisleep(millisec); + + /******************************************************************************/ + /* Taint-checked file opens */ ++static inline uschar * ++is_tainted2(const void *p, int lflags, const uschar* fmt, ...) ++{ ++va_list ap; ++uschar *msg; ++rmark mark; ++ ++if (!is_tainted(p)) ++ return NULL; ++ ++mark = store_mark(); ++va_start(ap, fmt); ++msg = string_from_gstring(string_vformat(NULL, SVFMT_TAINT_NOCHK|SVFMT_EXTEND, fmt, ap)); ++va_end(ap); ++ ++#ifdef ALLOW_INSECURE_TAINTED_DATA ++if (allow_insecure_tainted_data) ++ { ++ if LOGGING(tainted) log_write(0, LOG_MAIN, "Warning: %s", msg); ++ store_reset(mark); ++ return NULL; ++ } ++#endif ++ ++if (lflags) log_write(0, lflags, "%s", msg); ++return msg; /* no store_reset(), as the message might be used afterwards and Exim ++ is expected to exit anyway, so we do not care about the leaked ++ storage */ ++} + + static inline int + exim_open2(const char *pathname, int flags) + { +-if (!is_tainted(pathname)) return open(pathname, flags); +-log_write(0, LOG_MAIN|LOG_PANIC, "Tainted filename '%s'", pathname); ++if (!is_tainted2(pathname, LOG_MAIN|LOG_PANIC, "Tainted filename '%s'", pathname)) ++ return open(pathname, flags); + errno = EACCES; + return -1; + } ++ + static inline int + exim_open(const char *pathname, int flags, mode_t mode) + { +-if (!is_tainted(pathname)) return open(pathname, flags, mode); +-log_write(0, LOG_MAIN|LOG_PANIC, "Tainted filename '%s'", pathname); ++if (!is_tainted2(pathname, LOG_MAIN|LOG_PANIC, "Tainted filename '%s'", pathname)) ++ return open(pathname, flags, mode); + errno = EACCES; + return -1; + } + static inline int + exim_openat(int dirfd, const char *pathname, int flags) + { +-if (!is_tainted(pathname)) return openat(dirfd, pathname, flags); +-log_write(0, LOG_MAIN|LOG_PANIC, "Tainted filename '%s'", pathname); ++if (!is_tainted2(pathname, LOG_MAIN|LOG_PANIC, "Tainted filename '%s'", pathname)) ++ return openat(dirfd, pathname, flags); + errno = EACCES; + return -1; + } + static inline int + exim_openat4(int dirfd, const char *pathname, int flags, mode_t mode) + { +-if (!is_tainted(pathname)) return openat(dirfd, pathname, flags, mode); +-log_write(0, LOG_MAIN|LOG_PANIC, "Tainted filename '%s'", pathname); ++if (!is_tainted2(pathname, LOG_MAIN|LOG_PANIC, "Tainted filename '%s'", pathname)) ++ return openat(dirfd, pathname, flags, mode); + errno = EACCES; + return -1; + } +@@ -1120,8 +1150,8 @@ return -1; + static inline FILE * + exim_fopen(const char *pathname, const char *mode) + { +-if (!is_tainted(pathname)) return fopen(pathname, mode); +-log_write(0, LOG_MAIN|LOG_PANIC, "Tainted filename '%s'", pathname); ++if (!is_tainted2(pathname, LOG_MAIN|LOG_PANIC, "Tainted filename '%s'", pathname)) ++ return fopen(pathname, mode); + errno = EACCES; + return NULL; + } +@@ -1129,8 +1159,8 @@ return NULL; + static inline DIR * + exim_opendir(const uschar * name) + { +-if (!is_tainted(name)) return opendir(CCS name); +-log_write(0, LOG_MAIN|LOG_PANIC, "Tainted dirname '%s'", name); ++if (!is_tainted2(name, LOG_MAIN|LOG_PANIC, "Tainted dirname '%s'", name)) ++ return opendir(CCS name); + errno = EACCES; + return NULL; + } +diff --git a/src/globals.c b/src/globals.c +index c34ac9ddd..ff660c352 100644 +--- a/src/globals.c ++++ b/src/globals.c +@@ -98,6 +98,10 @@ int sqlite_lock_timeout = 5; + BOOL move_frozen_messages = FALSE; + #endif + ++#ifdef ALLOW_INSECURE_TAINTED_DATA ++BOOL allow_insecure_tainted_data = FALSE; ++#endif ++ + /* These variables are outside the #ifdef because it keeps the code less + cluttered in several places (e.g. during logging) if we can always refer to + them. Also, the tls_ variables are now always visible. Note that these are +@@ -1033,6 +1037,9 @@ int log_default[] = { /* for initializing log_selector */ + Li_size_reject, + Li_skip_delivery, + Li_smtp_confirmation, ++#ifdef ALLOW_INSECURE_TAINTED_DATA ++ Li_tainted, ++#endif + Li_tls_certificate_verified, + Li_tls_cipher, + -1 +@@ -1100,6 +1107,9 @@ bit_table log_options[] = { /* must be in alphabetical order, + BIT_TABLE(L, smtp_protocol_error), + BIT_TABLE(L, smtp_syntax_error), + BIT_TABLE(L, subject), ++#ifdef ALLOW_INSECURE_TAINTED_DATA ++ BIT_TABLE(L, tainted), ++#endif + BIT_TABLE(L, tls_certificate_verified), + BIT_TABLE(L, tls_cipher), + BIT_TABLE(L, tls_peerdn), +diff --git a/src/globals.h b/src/globals.h +index a4c1143b7..8d72577e0 100644 +--- a/src/globals.h ++++ b/src/globals.h +@@ -77,6 +77,10 @@ extern int sqlite_lock_timeout; /* Internal lock waiting timeout */ + extern BOOL move_frozen_messages; /* Get them out of the normal directory */ + #endif + ++#ifdef ALLOW_INSECURE_TAINTED_DATA ++extern BOOL allow_insecure_tainted_data; ++#endif ++ + /* These variables are outside the #ifdef because it keeps the code less + cluttered in several places (e.g. during logging) if we can always refer to + them. Also, the tls_ variables are now always visible. */ +diff --git a/src/macros.h b/src/macros.h +index f78ae2e3d..322ddbf56 100644 +--- a/src/macros.h ++++ b/src/macros.h +@@ -498,6 +498,9 @@ enum logbit { + Li_smtp_mailauth, + Li_smtp_no_mail, + Li_subject, ++#ifdef ALLOW_INSECURE_TAINTED_DATA ++ Li_tainted, ++#endif + Li_tls_certificate_verified, + Li_tls_cipher, + Li_tls_peerdn, +diff --git a/src/readconf.c b/src/readconf.c +index 948fa2403..133135f8f 100644 +--- a/src/readconf.c ++++ b/src/readconf.c +@@ -68,6 +68,9 @@ static optionlist optionlist_config[] = { + { "add_environment", opt_stringptr, {&add_environment} }, + { "admin_groups", opt_gidlist, {&admin_groups} }, + { "allow_domain_literals", opt_bool, {&allow_domain_literals} }, ++#ifdef ALLOW_INSECURE_TAINTED_DATA ++ { "allow_insecure_tainted_data", opt_bool, {&allow_insecure_tainted_data} }, ++#endif + { "allow_mx_to_ip", opt_bool, {&allow_mx_to_ip} }, + { "allow_utf8_domains", opt_bool, {&allow_utf8_domains} }, + { "auth_advertise_hosts", opt_stringptr, {&auth_advertise_hosts} }, +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_02-search.patch b/mail/exim/files/debian/75_02-search.patch new file mode 100644 index 000000000000..226a350af10d --- /dev/null +++ b/mail/exim/files/debian/75_02-search.patch @@ -0,0 +1,39 @@ +From b71d675f695c2cf17357b190476129535d5f446c Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Thu, 1 Apr 2021 22:45:03 +0200 +Subject: [PATCH 02/23] search + +--- + src/search.c | 8 ++------ + 1 file changed, 2 insertions(+), 6 deletions(-) + +diff --git a/src/search.c b/src/search.c +index f8aaacb04..f6e4d1f5b 100644 +--- a/src/search.c ++++ b/src/search.c +@@ -343,12 +343,8 @@ lookup_info *lk = lookup_list[search_type]; + uschar keybuffer[256]; + int old_pool = store_pool; + +-if (filename && is_tainted(filename)) +- { +- log_write(0, LOG_MAIN|LOG_PANIC, +- "Tainted filename for search: '%s'", filename); ++if (filename && is_tainted2(filename, LOG_MAIN|LOG_PANIC, "Tainted filename for search '%s'", filename)) + return NULL; +- } + + /* Change to the search store pool and remember our reset point */ + +@@ -639,7 +635,7 @@ DEBUG(D_lookup) + /* Arrange to put this database at the top of the LRU chain if it is a type + that opens real files. */ + +-if ( open_top != (tree_node *)handle ++if ( open_top != (tree_node *)handle + && lookup_list[t->name[0]-'0']->type == lookup_absfile) + { + search_cache *c = (search_cache *)(t->data.ptr); +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_03-dbstuff.patch b/mail/exim/files/debian/75_03-dbstuff.patch new file mode 100644 index 000000000000..dc9da8e44c54 --- /dev/null +++ b/mail/exim/files/debian/75_03-dbstuff.patch @@ -0,0 +1,30 @@ +From 35b11dd0e52b5ac176849f807cca8898bcaf0c3d Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Sun, 28 Mar 2021 10:49:49 +0200 +Subject: [PATCH 03/23] dbstuff + +--- + src/dbstuff.h | 6 ++---- + 1 file changed, 2 insertions(+), 4 deletions(-) + +diff --git a/src/dbstuff.h b/src/dbstuff.h +index c1fb54346..dcee78696 100644 +--- a/src/dbstuff.h ++++ b/src/dbstuff.h +@@ -643,11 +643,9 @@ after reading data. */ + : (flags) == O_RDWR ? "O_RDWR" \ + : (flags) == (O_RDWR|O_CREAT) ? "O_RDWR|O_CREAT" \ + : "??"); \ +- if (is_tainted(name) || is_tainted(dirname)) \ +- { \ +- log_write(0, LOG_MAIN|LOG_PANIC, "Tainted name for DB file not permitted"); \ ++ if (is_tainted2(name, LOG_MAIN|LOG_PANIC, "Tainted name '%s' for DB file not permitted", name) \ ++ || is_tainted2(dirname, LOG_MAIN|LOG_PANIC, "Tainted name '%s' for DB directory not permitted", dirname)) \ + *dbpp = NULL; \ +- } \ + else \ + { EXIM_DBOPEN__(name, dirname, flags, mode, dbpp); } \ + DEBUG(D_hints_lookup) debug_printf_indent("returned from EXIM_DBOPEN: %p\n", *dbpp); \ +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_04-acl.patch b/mail/exim/files/debian/75_04-acl.patch new file mode 100644 index 000000000000..810b2e591675 --- /dev/null +++ b/mail/exim/files/debian/75_04-acl.patch @@ -0,0 +1,67 @@ +From 44fd80ad8abcd885fc1c8dbb294fc2140e4ef481 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Sun, 28 Mar 2021 10:50:14 +0200 +Subject: [PATCH 04/23] acl +Last-Update: 2021-05-01 + +--- + src/acl.c | 32 ++++++++++++++++---------------- + 1 file changed, 16 insertions(+), 16 deletions(-) + +--- a/src/acl.c ++++ b/src/acl.c +@@ -3596,24 +3596,26 @@ + rc = mime_regex(&arg); + break; + #endif + + case ACLC_QUEUE: +- if (is_tainted(arg)) + { +- *log_msgptr = string_sprintf("Tainted name '%s' for queue not permitted", +- arg); +- return ERROR; ++ uschar *m; ++ if (m = is_tainted2(arg, 0, "Tainted name '%s' for queue not permitted", arg)) ++ { ++ *log_msgptr = m; ++ return ERROR; ++ } ++ if (Ustrchr(arg, '/')) ++ { ++ *log_msgptr = string_sprintf( ++ "Directory separator not permitted in queue name: '%s'", arg); ++ return ERROR; ++ } ++ queue_name = string_copy_perm(arg, FALSE); ++ break; + } +- if (Ustrchr(arg, '/')) +- { +- *log_msgptr = string_sprintf( +- "Directory separator not permitted in queue name: '%s'", arg); +- return ERROR; +- } +- queue_name = string_copy_perm(arg, FALSE); +- break; + + case ACLC_RATELIMIT: + rc = acl_ratelimit(arg, where, log_msgptr); + break; + +@@ -4005,14 +4007,12 @@ + } + + else if (*ss == '/') + { + struct stat statbuf; +- if (is_tainted(ss)) ++ if (is_tainted2(ss, LOG_MAIN|LOG_PANIC, "Tainted ACL file name '%s'", ss)) + { +- log_write(0, LOG_MAIN|LOG_PANIC, +- "attempt to open tainted ACL file name \"%s\"", ss); + /* Avoid leaking info to an attacker */ + *log_msgptr = US"internal configuration error"; + return ERROR; + } + if ((fd = Uopen(ss, O_RDONLY, 0)) < 0) diff --git a/mail/exim/files/debian/75_05-parse.patch b/mail/exim/files/debian/75_05-parse.patch new file mode 100644 index 000000000000..f9dab900f88e --- /dev/null +++ b/mail/exim/files/debian/75_05-parse.patch @@ -0,0 +1,30 @@ +From 7eeeb6f26af05322814ecc77c87f09c72ab2216a Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Sun, 28 Mar 2021 10:58:46 +0200 +Subject: [PATCH 05/23] parse + +--- + src/parse.c | 6 +----- + 1 file changed, 1 insertion(+), 5 deletions(-) + +diff --git a/src/parse.c b/src/parse.c +index 3ea758ac9..d1bc79039 100644 +--- a/src/parse.c ++++ b/src/parse.c +@@ -1402,12 +1402,8 @@ for (;;) + return FF_ERROR; + } + +- if (is_tainted(filename)) +- { +- *error = string_sprintf("Tainted name '%s' for included file not permitted\n", +- filename); ++ if (*error = is_tainted2(filename, 0, "Tainted name '%s' for included file not permitted\n", filename)) + return FF_ERROR; +- } + + /* Check file name if required */ + +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_06-rda.patch b/mail/exim/files/debian/75_06-rda.patch new file mode 100644 index 000000000000..f4ca2afc13f1 --- /dev/null +++ b/mail/exim/files/debian/75_06-rda.patch @@ -0,0 +1,28 @@ +From a6da9c67acaee699616516be141d600cc178a633 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Sun, 28 Mar 2021 10:59:46 +0200 +Subject: [PATCH 06/23] rda + +--- + src/rda.c | 4 +--- + 1 file changed, 1 insertion(+), 3 deletions(-) + +diff --git a/src/rda.c b/src/rda.c +index aed8abc24..6ad7dd8bd 100644 +--- a/src/rda.c ++++ b/src/rda.c +@@ -179,10 +179,8 @@ struct stat statbuf; + /* Reading a file is a form of expansion; we wish to deny attackers the + capability to specify the file name. */ + +-if (is_tainted(filename)) ++if (*error = is_tainted2(filename, 0, "Tainted name '%s' for file read not permitted\n", filename)) + { +- *error = string_sprintf("Tainted name '%s' for file read not permitted\n", +- filename); + *yield = FF_ERROR; + return NULL; + } +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_07-appendfile.patch b/mail/exim/files/debian/75_07-appendfile.patch new file mode 100644 index 000000000000..5a9e37861d7f --- /dev/null +++ b/mail/exim/files/debian/75_07-appendfile.patch @@ -0,0 +1,34 @@ +From c29b50d2fe17cc108d751175ed4f4113c25c1768 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Sun, 28 Mar 2021 11:00:06 +0200 +Subject: [PATCH 07/23] appendfile + +--- + src/transports/appendfile.c | 8 +++++--- + 1 file changed, 5 insertions(+), 3 deletions(-) + +diff --git a/src/transports/appendfile.c b/src/transports/appendfile.c +index 8ab8b6016..7dbbaa2f9 100644 +--- a/src/transports/appendfile.c ++++ b/src/transports/appendfile.c +@@ -1286,12 +1286,14 @@ if (!(path = expand_string(fdname))) + expand_string_message); + goto ret_panic; + } +-if (is_tainted(path)) ++{ uschar *m; ++if (m = is_tainted2(path, 0, "Tainted '%s' (file or directory " ++ "name for %s transport) not permitted", path, tblock->name)) + { +- addr->message = string_sprintf("Tainted '%s' (file or directory " +- "name for %s transport) not permitted", path, tblock->name); ++ addr->message = m; + goto ret_panic; + } ++} + + if (path[0] != '/') + { +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_08-autoreply.patch b/mail/exim/files/debian/75_08-autoreply.patch new file mode 100644 index 000000000000..de5eb1dd3c20 --- /dev/null +++ b/mail/exim/files/debian/75_08-autoreply.patch @@ -0,0 +1,70 @@ +From 26de37d8960da80473866fb59b9dfd10a5761538 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Sun, 28 Mar 2021 11:06:27 +0200 +Subject: [PATCH 08/23] autoreply + +--- + src/transports/autoreply.c | 21 ++++++++++++--------- + 1 file changed, 12 insertions(+), 9 deletions(-) + +diff --git a/src/transports/autoreply.c b/src/transports/autoreply.c +index 865abbf4f..ed99de4c6 100644 +--- a/src/transports/autoreply.c ++++ b/src/transports/autoreply.c +@@ -404,14 +404,15 @@ recipient cache. */ + + if (oncelog && *oncelog && to) + { ++ uschar *m; + time_t then = 0; + +- if (is_tainted(oncelog)) ++ if (m = is_tainted2(oncelog, 0, "Tainted '%s' (once file for %s transport)" ++ " not permitted", oncelog, tblock->name)) + { + addr->transport_return = DEFER; + addr->basic_errno = EACCES; +- addr->message = string_sprintf("Tainted '%s' (once file for %s transport)" +- " not permitted", oncelog, tblock->name); ++ addr->message = m; + goto END_OFF; + } + +@@ -515,13 +516,14 @@ if (oncelog && *oncelog && to) + + if (then != 0 && (once_repeat_sec <= 0 || now - then < once_repeat_sec)) + { ++ uschar *m; + int log_fd; +- if (is_tainted(logfile)) ++ if (m = is_tainted2(logfile, 0, "Tainted '%s' (logfile for %s transport)" ++ " not permitted", logfile, tblock->name)) + { + addr->transport_return = DEFER; + addr->basic_errno = EACCES; +- addr->message = string_sprintf("Tainted '%s' (logfile for %s transport)" +- " not permitted", logfile, tblock->name); ++ addr->message = m; + goto END_OFF; + } + +@@ -548,12 +550,13 @@ if (oncelog && *oncelog && to) + /* We are going to send a message. Ensure any requested file is available. */ + if (file) + { +- if (is_tainted(file)) ++ uschar *m; ++ if (m = is_tainted2(file, 0, "Tainted '%s' (file for %s transport)" ++ " not permitted", file, tblock->name)) + { + addr->transport_return = DEFER; + addr->basic_errno = EACCES; +- addr->message = string_sprintf("Tainted '%s' (file for %s transport)" +- " not permitted", file, tblock->name); ++ addr->message = m; + return FALSE; + } + if (!(ff = Ufopen(file, "rb")) && !ob->file_optional) +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_09-pipe.patch b/mail/exim/files/debian/75_09-pipe.patch new file mode 100644 index 000000000000..0ec9bcfaed19 --- /dev/null +++ b/mail/exim/files/debian/75_09-pipe.patch @@ -0,0 +1,36 @@ +From f9628406706112be459adb3f121db8e6cf282c2d Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Fri, 2 Apr 2021 17:30:27 +0200 +Subject: [PATCH 09/23] pipe + +--- + src/transports/pipe.c | 9 ++++++--- + 1 file changed, 6 insertions(+), 3 deletions(-) + +diff --git a/src/transports/pipe.c b/src/transports/pipe.c +index 27422bd42..4c9e68beb 100644 +--- a/src/transports/pipe.c ++++ b/src/transports/pipe.c +@@ -599,13 +599,16 @@ if (!cmd || !*cmd) + tblock->name); + return FALSE; + } +-if (is_tainted(cmd)) ++ ++{ uschar *m; ++if (m = is_tainted2(cmd, 0, "Tainted '%s' (command " ++ "for %s transport) not permitted", cmd, tblock->name)) + { +- addr->message = string_sprintf("Tainted '%s' (command " +- "for %s transport) not permitted", cmd, tblock->name); + addr->transport_return = PANIC; ++ addr->message = m; + return FALSE; + } ++} + + /* When a pipe is set up by a filter file, there may be values for $thisaddress + and numerical the variables in existence. These are passed in +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_10-deliver.patch b/mail/exim/files/debian/75_10-deliver.patch new file mode 100644 index 000000000000..ea4a54239e31 --- /dev/null +++ b/mail/exim/files/debian/75_10-deliver.patch @@ -0,0 +1,49 @@ +From 2fee91ae42e974c21202e0b5e17185f6a87bf8af Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Wed, 31 Mar 2021 23:12:44 +0200 +Subject: [PATCH 10/23] deliver + +--- + src/deliver.c | 16 +++++++++------- + 1 file changed, 9 insertions(+), 7 deletions(-) + +diff --git a/src/deliver.c b/src/deliver.c +index d85edd70e..8b7998f37 100644 +--- a/src/deliver.c ++++ b/src/deliver.c +@@ -5538,10 +5538,11 @@ FILE * fp = NULL; + if (!s || !*s) + log_write(0, LOG_MAIN|LOG_PANIC, + "Failed to expand %s: '%s'\n", varname, filename); +-else if (*s != '/' || is_tainted(s)) +- log_write(0, LOG_MAIN|LOG_PANIC, +- "%s is not %s after expansion: '%s'\n", +- varname, *s == '/' ? "untainted" : "absolute", s); ++else if (*s != '/') ++ log_write(0, LOG_MAIN|LOG_PANIC, "%s is not absolute after expansion: '%s'\n", ++ varname, s); ++else if (is_tainted2(s, LOG_MAIN|LOG_PANIC, "Tainted %s after expansion: '%s'\n", varname, s)) ++ ; + else if (!(fp = Ufopen(s, "rb"))) + log_write(0, LOG_MAIN|LOG_PANIC, "Failed to open %s for %s " + "message texts: %s", s, reason, strerror(errno)); +@@ -6148,12 +6149,13 @@ else if (system_filter && process_recipients != RECIP_FAIL_TIMEOUT) + { + uschar *tmp = expand_string(tpname); + address_file = address_pipe = NULL; ++ uschar *m; + if (!tmp) + p->message = string_sprintf("failed to expand \"%s\" as a " + "system filter transport name", tpname); +- if (is_tainted(tmp)) +- p->message = string_sprintf("attempt to used tainted value '%s' for" +- "transport '%s' as a system filter", tmp, tpname); ++ if (is_tainted2(tmp, 0, m = string_sprintf("Tainted values '%s' " ++ "for transport '%s' as a system filter", tmp, tpname))) ++ p->message = m; + tpname = tmp; + } + else +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_11-directory.patch b/mail/exim/files/debian/75_11-directory.patch new file mode 100644 index 000000000000..4c3a68418c0b --- /dev/null +++ b/mail/exim/files/debian/75_11-directory.patch @@ -0,0 +1,26 @@ +From 5f41e800ce9cc7ad154047298914df955e905bf4 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Thu, 1 Apr 2021 21:28:59 +0200 +Subject: [PATCH 11/23] directory + +--- + src/directory.c | 3 +++ + 1 file changed, 3 insertions(+) + +diff --git a/src/directory.c b/src/directory.c +index 2d4d565f4..9f88f4141 100644 +--- a/src/directory.c ++++ b/src/directory.c +@@ -44,6 +44,9 @@ uschar c = 1; + struct stat statbuf; + uschar * path; + ++if (is_tainted2(name, LOG_MAIN|LOG_PANIC, "Tainted path '%s' for new directory", name)) ++ { p = US"create"; path = US name; errno = EACCES; goto bad; } ++ + if (parent) + { + path = string_sprintf("%s%s%s", parent, US"/", name); +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_12-expand.patch b/mail/exim/files/debian/75_12-expand.patch new file mode 100644 index 000000000000..ebb099d284f2 --- /dev/null +++ b/mail/exim/files/debian/75_12-expand.patch @@ -0,0 +1,34 @@ +From c02ea85f525ff256d78e084d6f76fe3032fd52e1 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Thu, 1 Apr 2021 21:33:50 +0200 +Subject: [PATCH 12/23] expand + +--- + src/expand.c | 8 ++++---- + 1 file changed, 4 insertions(+), 4 deletions(-) + +diff --git a/src/expand.c b/src/expand.c +index 05de94c49..21b86ebf5 100644 +--- a/src/expand.c ++++ b/src/expand.c +@@ -4383,13 +4383,13 @@ DEBUG(D_expand) + f.expand_string_forcedfail = FALSE; + expand_string_message = US""; + +-if (is_tainted(string)) ++{ uschar *m; ++if (m = is_tainted2(string, LOG_MAIN|LOG_PANIC, "Tainted string '%s' in expansion", s)) + { +- expand_string_message = +- string_sprintf("attempt to expand tainted string '%s'", s); +- log_write(0, LOG_MAIN|LOG_PANIC, "%s", expand_string_message); ++ expand_string_message = m; + goto EXPAND_FAILED; + } ++} + + while (*s != 0) + { +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_13-lf_sqlperform.patch b/mail/exim/files/debian/75_13-lf_sqlperform.patch new file mode 100644 index 000000000000..67283a02676e --- /dev/null +++ b/mail/exim/files/debian/75_13-lf_sqlperform.patch @@ -0,0 +1,49 @@ +From 9810dfc25d8b9687b46e57963a3ac30bf5c9b2c9 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Thu, 1 Apr 2021 21:36:12 +0200 +Subject: [PATCH 13/23] lf_sqlperform + +--- + src/lookups/lf_sqlperform.c | 14 +++++++++----- + 1 file changed, 9 insertions(+), 5 deletions(-) + +diff --git a/src/lookups/lf_sqlperform.c b/src/lookups/lf_sqlperform.c +index ad1df29d1..eda3089e2 100644 +--- a/src/lookups/lf_sqlperform.c ++++ b/src/lookups/lf_sqlperform.c +@@ -102,11 +102,13 @@ if (Ustrncmp(query, "servers", 7) == 0) + } + } + +- if (is_tainted(server)) +- { +- *errmsg = string_sprintf("%s server \"%s\" is tainted", name, server); ++ { uschar *m; ++ if (m = is_tainted2(server, 0, "Tainted %s server '%s'", name, server)) ++ { ++ *errmsg = m; + return DEFER; + } ++ } + + rc = (*fn)(ss+1, server, result, errmsg, &defer_break, do_cache, opts); + if (rc != DEFER || defer_break) return rc; +@@ -158,11 +160,13 @@ else + server = ele; + } + +- if (is_tainted(server)) ++ { uschar *m; ++ if (is_tainted2(server, 0, "Tainted %s server '%s'", name, server)) + { +- *errmsg = string_sprintf("%s server \"%s\" is tainted", name, server); ++ *errmsg = m; + return DEFER; + } ++ } + + rc = (*fn)(query, server, result, errmsg, &defer_break, do_cache, opts); + if (rc != DEFER || defer_break) return rc; +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_14-rf_get_transport.patch b/mail/exim/files/debian/75_14-rf_get_transport.patch new file mode 100644 index 000000000000..9e8b69d3ad6a --- /dev/null +++ b/mail/exim/files/debian/75_14-rf_get_transport.patch @@ -0,0 +1,28 @@ +From 015fff57c854184f8bce61476c46a2830a97daf8 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Fri, 2 Apr 2021 08:36:24 +0200 +Subject: [PATCH 14/23] rf_get_transport + +--- + src/routers/rf_get_transport.c | 4 +--- + 1 file changed, 1 insertion(+), 3 deletions(-) + +diff --git a/src/routers/rf_get_transport.c b/src/routers/rf_get_transport.c +index 4a43818ff..32bde9ec3 100644 +--- a/src/routers/rf_get_transport.c ++++ b/src/routers/rf_get_transport.c +@@ -66,10 +66,8 @@ if (expandable) + "\"%s\" in %s router: %s", tpname, router_name, expand_string_message); + return FALSE; + } +- if (is_tainted(ss)) ++ if (is_tainted2(ss, LOG_MAIN|LOG_PANIC, "Tainted tainted value '%s' from '%s' for transport", ss, tpname)) + { +- log_write(0, LOG_MAIN|LOG_PANIC, +- "attempt to use tainted value '%s' from '%s' for transport", ss, tpname); + addr->basic_errno = ERRNO_BADTRANSPORT; + /* Avoid leaking info to an attacker */ + addr->message = US"internal configuration error"; +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_15-deliver.patch b/mail/exim/files/debian/75_15-deliver.patch new file mode 100644 index 000000000000..0c2ca2772d10 --- /dev/null +++ b/mail/exim/files/debian/75_15-deliver.patch @@ -0,0 +1,31 @@ +From 2bafe3fc82cf62f0c21f939f5891b8d067f3abc7 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Sat, 3 Apr 2021 10:54:22 +0200 +Subject: [PATCH 15/23] deliver + +--- + src/deliver.c | 5 +++-- + test/paniclog/0622 | 2 +- + test/stderr/0622 | 2 +- + 3 files changed, 5 insertions(+), 4 deletions(-) + +diff --git a/src/deliver.c b/src/deliver.c +index 8b7998f37..87e944b03 100644 +--- a/src/deliver.c ++++ b/src/deliver.c +@@ -6153,9 +6153,10 @@ else if (system_filter && process_recipients != RECIP_FAIL_TIMEOUT) + if (!tmp) + p->message = string_sprintf("failed to expand \"%s\" as a " + "system filter transport name", tpname); +- if (is_tainted2(tmp, 0, m = string_sprintf("Tainted values '%s' " +- "for transport '%s' as a system filter", tmp, tpname))) ++ { uschar *m; ++ if (m = is_tainted2(tmp, 0, "Tainted values '%s' " "for transport '%s' as a system filter", tmp, tpname)) + p->message = m; ++ } + tpname = tmp; + } + else +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_16-smtp_out.patch b/mail/exim/files/debian/75_16-smtp_out.patch new file mode 100644 index 000000000000..a0280afd30a8 --- /dev/null +++ b/mail/exim/files/debian/75_16-smtp_out.patch @@ -0,0 +1,38 @@ +From b9b967cca71a4da51506f8ba596b9ae40cfcef57 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Thu, 1 Apr 2021 21:42:38 +0200 +Subject: [PATCH 16/23] smtp_out + +--- + src/smtp_out.c | 7 ++----- + 1 file changed, 2 insertions(+), 5 deletions(-) + +diff --git a/src/smtp_out.c b/src/smtp_out.c +index c4c409677..9c160e697 100644 +--- a/src/smtp_out.c ++++ b/src/smtp_out.c +@@ -53,11 +53,8 @@ if (!(expint = expand_string(istring))) + return FALSE; + } + +-if (is_tainted(expint)) ++if (is_tainted2(expint, LOG_MAIN|LOG_PANIC, "Tainted value '%s' from '%s' for interface", expint, istring)) + { +- log_write(0, LOG_MAIN|LOG_PANIC, +- "attempt to use tainted value '%s' from '%s' for interface", +- expint, istring); + addr->transport_return = PANIC; + addr->message = string_sprintf("failed to expand \"interface\" " + "option for %s: configuration error", msg); +@@ -425,7 +422,7 @@ if (ob->socks_proxy) + { + int sock = socks_sock_connect(sc->host, sc->host_af, port, sc->interface, + sc->tblock, ob->connect_timeout); +- ++ + if (sock >= 0) + { + if (early_data && early_data->data && early_data->len) +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_17-smtp.patch b/mail/exim/files/debian/75_17-smtp.patch new file mode 100644 index 000000000000..c77a284a9ff0 --- /dev/null +++ b/mail/exim/files/debian/75_17-smtp.patch @@ -0,0 +1,29 @@ +From 8b7d4ba8903ace7e3e3db70343798a5a0b7cea23 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Thu, 1 Apr 2021 22:02:27 +0200 +Subject: [PATCH 17/23] smtp + +--- + src/transports/smtp.c | 5 +---- + 1 file changed, 1 insertion(+), 4 deletions(-) + +diff --git a/src/transports/smtp.c b/src/transports/smtp.c +index 6540e4d2b..8fecf7eef 100644 +--- a/src/transports/smtp.c ++++ b/src/transports/smtp.c +@@ -4715,11 +4715,8 @@ if (!hostlist || (ob->hosts_override && ob->hosts)) + else + if (ob->hosts_randomize) s = expanded_hosts = string_copy(s); + +- if (is_tainted(s)) ++ if (is_tainted2(s, LOG_MAIN|LOG_PANIC, "Tainted host list '%s' from '%s' in transport %s", s, ob->hosts, tblock->name)) + { +- log_write(0, LOG_MAIN|LOG_PANIC, +- "attempt to use tainted host list '%s' from '%s' in transport %s", +- s, ob->hosts, tblock->name); + /* Avoid leaking info to an attacker */ + addrlist->message = US"internal configuration error"; + addrlist->transport_return = PANIC; +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_18-update-doc.patch b/mail/exim/files/debian/75_18-update-doc.patch new file mode 100644 index 000000000000..2edba6916744 --- /dev/null +++ b/mail/exim/files/debian/75_18-update-doc.patch @@ -0,0 +1,154 @@ +From 77cc1ad3058e4ef7ae82adb914ccff0be9fe2c8b Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Sat, 3 Apr 2021 09:29:13 +0200 +Subject: [PATCH 18/23] update doc + +--- + doc/doc-docbook/spec.xfpt | 45 ++++++++++++++++++++++++++++++++++++++- + doc/NewStuff | 45 +++++++++++++++++++++++++++++++++++++++ + 2 files changed, 89 insertions(+), 1 deletion(-) + +--- a/doc/NewStuff ++++ b/doc/NewStuff +@@ -4,10 +4,55 @@ + This file contains descriptions of new features that have been added to Exim. + Before a formal release, there may be quite a lot of detail so that people can + test from the snapshots or the Git before the documentation is updated. Once + the documentation is updated, this file is reduced to a short list. + ++Version 4.95 ++------------ ++ ++ 1. The fast-ramp two phase queue run support, previously experimental, is ++ now supported by default. ++ ++ 2. The native SRS support, previously experimental, is now supported. It is ++ not built unless specified in the Local/Makefile. ++ ++ 3. TLS resumption support, previously experimental, is now supported and ++ included in default builds. ++ ++ 4. Single-key LMDB lookups, previously experimental, are now supported. ++ The support is not built unless specified in the Local/Makefile. ++ ++ 5. Option "message_linelength_limit" on the smtp transport to enforce (by ++ default) the RFC 998 character limit. ++ ++ 6. An option to ignore the cache on a lookup. ++ ++ 7. Quota checking during reception (i.e. at SMTP time) for appendfile- ++ transport-managed quotas. ++ ++ 8. Sqlite lookups accept a "file=<path>" option to specify a per-operation ++ db file, replacing the previous prefix to the SQL string (which had ++ issues when the SQL used tainted values). ++ ++ 9. Lsearch lookups accept a "ret=full" option, to return both the portion ++ of the line matching the key, and the remainder. ++ ++10. A command-line option to have a daemon not create a notifier socket. ++ ++11. Faster TLS startup. When various configuration options contain no ++ expandable elements, the information can be preloaded and cached rather ++ than the provious behaviour of always loading at startup time for every ++ connection. This helps particularly for the CA bundle. ++ ++12. Proxy Protocol Timeout is configurable via "proxy_protocol_timeout" ++ main config option. ++ ++13. Option "smtp_accept_msx_per_connection" is now expanded. ++ ++13. A main config option "allow_insecure_tainted_data" allows to turn ++ taint errors into warnings. ++ + Version 4.94 + ------------ + + 1. EXPERIMENTAL_SRS_NATIVE optional build feature. See the experimental.spec + file. +--- a/doc/spec.txt ++++ b/doc/spec.txt +@@ -8650,12 +8650,20 @@ + Whether a string is expanded depends upon the context. Usually this is solely + dependent upon the option for which a value is sought; in this documentation, + options for which string expansion is performed are marked with * after the + data type. ACL rules always expand strings. A couple of expansion conditions do + not expand some of the brace-delimited branches, for security reasons, and +-expansion of data deriving from the sender ("tainted data") is not permitted. +- ++expansion of data deriving from the sender ("tainted data") is not permitted ++(including acessing a file using a tainted name). The main config ++option allow_insecure_tainted_data can be used as mitigation during ++uprades to more secure configurations. ++ ++Common ways of obtaining untainted equivalents of variables with tainted ++values come down to using the tainted value as a lookup key in a trusted ++database. This database could be the filesystem structure, or the ++password file, or accessed via a DBMS. Specific methods are indexed ++under "de-tainting". + + 11.1 Literal text in expanded strings + ------------------------------------- + + An uninterpreted dollar can be included in an expanded string by putting a +@@ -12946,10 +12954,12 @@ + + + 14.1 Miscellaneous + ------------------ + ++add_environment environment variables ++allow_insecure_tainted_data turn taint errors into warnings + bi_command to run for -bi command line option + debug_store do extra internal checks + disable_ipv6 do no IPv6 processing + keep_malformed for broken files - should not happen + localhost_number for unique message ids in clusters +@@ -13553,10 +13563,20 @@ + true, and also to add "@[]" to the list of local domains (defined in the named + domain list local_domains in the default configuration). This "magic string" + matches the domain literal form of all the local host's IP addresses. + + +-----------------------------------------------------+ ++|allow_insecure_tainted_data main boolean false | +++-----------------------------------------------------+ ++ ++The handling of tainted data may break older (pre 4.94) configurations. ++Setting this option to "true" turns taint errors (which result in a temporary ++message rejection) into warnings. This option is meant as mitigation only ++and deprecated already today. Future releases of Exim may ignore it. ++The taint log selector can be used to suppress even the warnings. ++ +++-----------------------------------------------------+ + |allow_mx_to_ip|Use: main|Type: boolean|Default: false| + +-----------------------------------------------------+ + + It appears that more and more DNS zone administrators are breaking the rules + and putting domain names that look like IP addresses on the right hand side of +@@ -35316,10 +35336,11 @@ + smtp_mailauth AUTH argument to MAIL commands + smtp_no_mail session with no MAIL commands + smtp_protocol_error SMTP protocol errors + smtp_syntax_error SMTP syntax errors + subject contents of Subject: on <= lines ++*taint taint errors or warnings + *tls_certificate_verified certificate verification status + *tls_cipher TLS cipher suite on <= and => lines + tls_peerdn TLS peer DN on <= and => lines + tls_sni TLS SNI on <= lines + unknown_in_list DNS lookup failed in list match +@@ -35604,11 +35625,13 @@ + + * tls_certificate_verified: An extra item is added to <= and => log lines + when TLS is in use. The item is "CV=yes" if the peer's certificate was + verified using a CA trust anchor, "CA=dane" if using a DNS trust anchor, + and "CV=no" if not. +- ++ * taint: Log warnings about tainted data. This selector can't be ++ turned of if allow_insecure_tainted_data is false (which is the ++ default). + * tls_cipher: When a message is sent or received over an encrypted + connection, the cipher suite used is added to the log line, preceded by X=. + + * tls_peerdn: When a message is sent or received over an encrypted + connection, and a certificate is supplied by the remote host, the peer DN diff --git a/mail/exim/files/debian/75_20-Set-mainlog_name-and-rejectlog_name-unconditionally.patch b/mail/exim/files/debian/75_20-Set-mainlog_name-and-rejectlog_name-unconditionally.patch new file mode 100644 index 000000000000..a660aeb3dd6e --- /dev/null +++ b/mail/exim/files/debian/75_20-Set-mainlog_name-and-rejectlog_name-unconditionally.patch @@ -0,0 +1,42 @@ +From 41c494e2465efadc2e82002a07430e8aec85bc9b Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Mon, 12 Apr 2021 08:41:44 +0200 +Subject: [PATCH 20/23] Set mainlog_name and rejectlog_name unconditionally. + +(cherry picked from commit 3f06b9b4c7244b169d50bce216c1f54b4dfe7efb) +--- + src/log.c | 10 ++++++---- + 1 file changed, 6 insertions(+), 4 deletions(-) + +diff --git a/src/log.c b/src/log.c +index 99eba5f90..011c4debc 100644 +--- a/src/log.c ++++ b/src/log.c +@@ -402,18 +402,20 @@ it gets statted to see if it has been cycled. With a datestamp, the datestamp + will be compared. The static slot for saving it is the same size as buffer, + and the text has been checked above to fit, so this use of strcpy() is OK. */ + +-if (type == lt_main && string_datestamp_offset >= 0) ++if (type == lt_main) + { + Ustrcpy(mainlog_name, buffer); +- mainlog_datestamp = mainlog_name + string_datestamp_offset; ++ if (string_datestamp_offset > 0) ++ mainlog_datestamp = mainlog_name + string_datestamp_offset; + } + + /* Ditto for the reject log */ + +-else if (type == lt_reject && string_datestamp_offset >= 0) ++else if (type == lt_reject) + { + Ustrcpy(rejectlog_name, buffer); +- rejectlog_datestamp = rejectlog_name + string_datestamp_offset; ++ if (string_datestamp_offset > 0) ++ rejectlog_datestamp = rejectlog_name + string_datestamp_offset; + } + + /* and deal with the debug log (which keeps the datestamp, but does not +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_21-tidy-log.c.patch b/mail/exim/files/debian/75_21-tidy-log.c.patch new file mode 100644 index 000000000000..b99f0c60988d --- /dev/null +++ b/mail/exim/files/debian/75_21-tidy-log.c.patch @@ -0,0 +1,124 @@ +From 8021b95c2e266861aba29c97b4bb90dc6f7637a2 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Mon, 12 Apr 2021 09:19:21 +0200 +Subject: [PATCH 21/23] tidy log.c + +(cherry picked from commit 0327b6460eec64da6b0c1543c7e9b3d0f8cb9294) +--- + src/log.c | 97 +++++++++++++++++++++++---------------------------- + 1 file changed, 44 insertions(+), 53 deletions(-) + +diff --git a/src/log.c b/src/log.c +index 011c4debc..7ef7074ec 100644 +--- a/src/log.c ++++ b/src/log.c +@@ -397,62 +397,53 @@ people want, I hope. */ + + ok = string_format(buffer, sizeof(buffer), CS file_path, log_names[type]); + +-/* Save the name of the mainlog for rollover processing. Without a datestamp, +-it gets statted to see if it has been cycled. With a datestamp, the datestamp +-will be compared. The static slot for saving it is the same size as buffer, +-and the text has been checked above to fit, so this use of strcpy() is OK. */ +- +-if (type == lt_main) ++switch (type) + { +- Ustrcpy(mainlog_name, buffer); +- if (string_datestamp_offset > 0) +- mainlog_datestamp = mainlog_name + string_datestamp_offset; +- } +- +-/* Ditto for the reject log */ +- +-else if (type == lt_reject) +- { +- Ustrcpy(rejectlog_name, buffer); +- if (string_datestamp_offset > 0) +- rejectlog_datestamp = rejectlog_name + string_datestamp_offset; +- } +- +-/* and deal with the debug log (which keeps the datestamp, but does not +-update it) */ +- +-else if (type == lt_debug) +- { +- Ustrcpy(debuglog_name, buffer); +- if (tag) +- { +- /* this won't change the offset of the datestamp */ +- ok2 = string_format(buffer, sizeof(buffer), "%s%s", +- debuglog_name, tag); +- if (ok2) +- Ustrcpy(debuglog_name, buffer); +- } +- } +- +-/* Remove any datestamp if this is the panic log. This is rare, so there's no +-need to optimize getting the datestamp length. We remove one non-alphanumeric +-char afterwards if at the start, otherwise one before. */ +- +-else if (string_datestamp_offset >= 0) +- { +- uschar * from = buffer + string_datestamp_offset; +- uschar * to = from + string_datestamp_length; ++ case lt_main: ++ /* Save the name of the mainlog for rollover processing. Without a datestamp, ++ it gets statted to see if it has been cycled. With a datestamp, the datestamp ++ will be compared. The static slot for saving it is the same size as buffer, ++ and the text has been checked above to fit, so this use of strcpy() is OK. */ ++ Ustrcpy(mainlog_name, buffer); ++ if (string_datestamp_offset > 0) ++ mainlog_datestamp = mainlog_name + string_datestamp_offset; ++ case lt_reject: ++ /* Ditto for the reject log */ ++ Ustrcpy(rejectlog_name, buffer); ++ if (string_datestamp_offset > 0) ++ rejectlog_datestamp = rejectlog_name + string_datestamp_offset; ++ case lt_debug: ++ /* and deal with the debug log (which keeps the datestamp, but does not ++ update it) */ ++ Ustrcpy(debuglog_name, buffer); ++ if (tag) ++ { ++ /* this won't change the offset of the datestamp */ ++ ok2 = string_format(buffer, sizeof(buffer), "%s%s", ++ debuglog_name, tag); ++ if (ok2) ++ Ustrcpy(debuglog_name, buffer); ++ } ++ default: ++ /* Remove any datestamp if this is the panic log. This is rare, so there's no ++ need to optimize getting the datestamp length. We remove one non-alphanumeric ++ char afterwards if at the start, otherwise one before. */ ++ if (string_datestamp_offset >= 0) ++ { ++ uschar * from = buffer + string_datestamp_offset; ++ uschar * to = from + string_datestamp_length; + +- if (from == buffer || from[-1] == '/') +- { +- if (!isalnum(*to)) to++; +- } +- else +- if (!isalnum(from[-1])) from--; ++ if (from == buffer || from[-1] == '/') ++ { ++ if (!isalnum(*to)) to++; ++ } ++ else ++ if (!isalnum(from[-1])) from--; + +- /* This copy is ok, because we know that to is a substring of from. But +- due to overlap we must use memmove() not Ustrcpy(). */ +- memmove(from, to, Ustrlen(to)+1); ++ /* This copy is ok, because we know that to is a substring of from. But ++ due to overlap we must use memmove() not Ustrcpy(). */ ++ memmove(from, to, Ustrlen(to)+1); ++ } + } + + /* If the file name is too long, it is an unrecoverable disaster */ +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_22-Silence-compiler.patch b/mail/exim/files/debian/75_22-Silence-compiler.patch new file mode 100644 index 000000000000..ce6e89894f9a --- /dev/null +++ b/mail/exim/files/debian/75_22-Silence-compiler.patch @@ -0,0 +1,222 @@ +From 2c9869d0622cc690b424cc74166d4a8393017ece Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Fri, 23 Apr 2021 17:40:40 +0200 +Subject: [PATCH 22/23] Silence compiler + +--- + src/acl.c | 2 +- + src/deliver.c | 3 +-- + src/expand.c | 6 +++++- + src/functions.h | 2 +- + src/lookups/lf_sqlperform.c | 4 ++-- + src/parse.c | 2 +- + src/rda.c | 2 +- + src/transports/appendfile.c | 4 ++-- + src/transports/autoreply.c | 12 ++++++------ + src/transports/pipe.c | 4 ++-- + 10 files changed, 22 insertions(+), 19 deletions(-) + +diff --git a/src/acl.c b/src/acl.c +index 81beab5f3..b62af5c65 100644 +--- a/src/acl.c ++++ b/src/acl.c +@@ -3600,7 +3600,7 @@ for (; cb; cb = cb->next) + case ACLC_QUEUE: + { + uschar *m; +- if (m = is_tainted2(arg, 0, "Tainted name '%s' for queue not permitted", arg)) ++ if ((m = is_tainted2(arg, 0, "Tainted name '%s' for queue not permitted", arg))) + { + *log_msgptr = m; + return ERROR; +diff --git a/src/deliver.c b/src/deliver.c +index 87e944b03..b40eed4f9 100644 +--- a/src/deliver.c ++++ b/src/deliver.c +@@ -6149,12 +6149,11 @@ else if (system_filter && process_recipients != RECIP_FAIL_TIMEOUT) + { + uschar *tmp = expand_string(tpname); + address_file = address_pipe = NULL; +- uschar *m; + if (!tmp) + p->message = string_sprintf("failed to expand \"%s\" as a " + "system filter transport name", tpname); + { uschar *m; +- if (m = is_tainted2(tmp, 0, "Tainted values '%s' " "for transport '%s' as a system filter", tmp, tpname)) ++ if ((m = is_tainted2(tmp, 0, "Tainted values '%s' " "for transport '%s' as a system filter", tmp, tpname))) + p->message = m; + } + tpname = tmp; +diff --git a/src/expand.c b/src/expand.c +index 21b86ebf5..dc4b4e102 100644 +--- a/src/expand.c ++++ b/src/expand.c +@@ -4384,7 +4384,7 @@ f.expand_string_forcedfail = FALSE; + expand_string_message = US""; + + { uschar *m; +-if (m = is_tainted2(string, LOG_MAIN|LOG_PANIC, "Tainted string '%s' in expansion", s)) ++if ((m = is_tainted2(string, LOG_MAIN|LOG_PANIC, "Tainted string '%s' in expansion", s))) + { + expand_string_message = m; + goto EXPAND_FAILED; +@@ -7629,10 +7629,12 @@ while (*s != 0) + /* Manually track tainting, as we deal in individual chars below */ + + if (is_tainted(sub)) ++ { + if (yield->s && yield->ptr) + gstring_rebuffer(yield); + else + yield->s = store_get(yield->size = Ustrlen(sub), TRUE); ++ } + + /* Check the UTF-8, byte-by-byte */ + +@@ -8193,6 +8195,7 @@ that is a bad idea, because expand_string_message is in dynamic store. */ + EXPAND_FAILED: + if (left) *left = s; + DEBUG(D_expand) ++ { + DEBUG(D_noutf8) + { + debug_printf_indent("|failed to expand: %s\n", string); +@@ -8212,6 +8215,7 @@ DEBUG(D_expand) + if (f.expand_string_forcedfail) + debug_printf_indent(UTF8_UP_RIGHT "failure was forced\n"); + } ++ } + if (resetok_p && !resetok) *resetok_p = FALSE; + expand_level--; + return NULL; +diff --git a/src/functions.h b/src/functions.h +index 1e8083673..b4d23c4bc 100644 +--- a/src/functions.h ++++ b/src/functions.h +@@ -1084,7 +1084,7 @@ if (f.running_in_test_harness && f.testsuite_delays) millisleep(millisec); + /******************************************************************************/ + /* Taint-checked file opens */ + static inline uschar * +-is_tainted2(const void *p, int lflags, const uschar* fmt, ...) ++is_tainted2(const void *p, int lflags, const char* fmt, ...) + { + va_list ap; + uschar *msg; +diff --git a/src/lookups/lf_sqlperform.c b/src/lookups/lf_sqlperform.c +index eda3089e2..38b7c2ad3 100644 +--- a/src/lookups/lf_sqlperform.c ++++ b/src/lookups/lf_sqlperform.c +@@ -103,7 +103,7 @@ if (Ustrncmp(query, "servers", 7) == 0) + } + + { uschar *m; +- if (m = is_tainted2(server, 0, "Tainted %s server '%s'", name, server)) ++ if ((m = is_tainted2(server, 0, "Tainted %s server '%s'", name, server))) + { + *errmsg = m; + return DEFER; +@@ -161,7 +161,7 @@ else + } + + { uschar *m; +- if (is_tainted2(server, 0, "Tainted %s server '%s'", name, server)) ++ if ((m = is_tainted2(server, 0, "Tainted %s server '%s'", name, server))) + { + *errmsg = m; + return DEFER; +diff --git a/src/parse.c b/src/parse.c +index d1bc79039..0622b3127 100644 +--- a/src/parse.c ++++ b/src/parse.c +@@ -1402,7 +1402,7 @@ for (;;) + return FF_ERROR; + } + +- if (*error = is_tainted2(filename, 0, "Tainted name '%s' for included file not permitted\n", filename)) ++ if ((*error = is_tainted2(filename, 0, "Tainted name '%s' for included file not permitted\n", filename))) + return FF_ERROR; + + /* Check file name if required */ +diff --git a/src/rda.c b/src/rda.c +index 6ad7dd8bd..bba0b719b 100644 +--- a/src/rda.c ++++ b/src/rda.c +@@ -179,7 +179,7 @@ struct stat statbuf; + /* Reading a file is a form of expansion; we wish to deny attackers the + capability to specify the file name. */ + +-if (*error = is_tainted2(filename, 0, "Tainted name '%s' for file read not permitted\n", filename)) ++if ((*error = is_tainted2(filename, 0, "Tainted name '%s' for file read not permitted\n", filename))) + { + *yield = FF_ERROR; + return NULL; +diff --git a/src/transports/appendfile.c b/src/transports/appendfile.c +index 7dbbaa2f9..6772b338b 100644 +--- a/src/transports/appendfile.c ++++ b/src/transports/appendfile.c +@@ -1287,8 +1287,8 @@ if (!(path = expand_string(fdname))) + goto ret_panic; + } + { uschar *m; +-if (m = is_tainted2(path, 0, "Tainted '%s' (file or directory " +- "name for %s transport) not permitted", path, tblock->name)) ++if ((m = is_tainted2(path, 0, "Tainted '%s' (file or directory " ++ "name for %s transport) not permitted", path, tblock->name))) + { + addr->message = m; + goto ret_panic; +diff --git a/src/transports/autoreply.c b/src/transports/autoreply.c +index ed99de4c6..80c7c0db0 100644 +--- a/src/transports/autoreply.c ++++ b/src/transports/autoreply.c +@@ -407,8 +407,8 @@ if (oncelog && *oncelog && to) + uschar *m; + time_t then = 0; + +- if (m = is_tainted2(oncelog, 0, "Tainted '%s' (once file for %s transport)" +- " not permitted", oncelog, tblock->name)) ++ if ((m = is_tainted2(oncelog, 0, "Tainted '%s' (once file for %s transport)" ++ " not permitted", oncelog, tblock->name))) + { + addr->transport_return = DEFER; + addr->basic_errno = EACCES; +@@ -518,8 +518,8 @@ if (oncelog && *oncelog && to) + { + uschar *m; + int log_fd; +- if (m = is_tainted2(logfile, 0, "Tainted '%s' (logfile for %s transport)" +- " not permitted", logfile, tblock->name)) ++ if ((m = is_tainted2(logfile, 0, "Tainted '%s' (logfile for %s transport)" ++ " not permitted", logfile, tblock->name))) + { + addr->transport_return = DEFER; + addr->basic_errno = EACCES; +@@ -551,8 +551,8 @@ if (oncelog && *oncelog && to) + if (file) + { + uschar *m; +- if (m = is_tainted2(file, 0, "Tainted '%s' (file for %s transport)" +- " not permitted", file, tblock->name)) ++ if ((m = is_tainted2(file, 0, "Tainted '%s' (file for %s transport)" ++ " not permitted", file, tblock->name))) + { + addr->transport_return = DEFER; + addr->basic_errno = EACCES; +diff --git a/src/transports/pipe.c b/src/transports/pipe.c +index 4c9e68beb..fc44fa585 100644 +--- a/src/transports/pipe.c ++++ b/src/transports/pipe.c +@@ -601,8 +601,8 @@ if (!cmd || !*cmd) + } + + { uschar *m; +-if (m = is_tainted2(cmd, 0, "Tainted '%s' (command " +- "for %s transport) not permitted", cmd, tblock->name)) ++if ((m = is_tainted2(cmd, 0, "Tainted '%s' (command " ++ "for %s transport) not permitted", cmd, tblock->name))) + { + addr->transport_return = PANIC; + addr->message = m; +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_23-Do-not-close-the-main-_log-if-we-do-not-see-a-chance.patch b/mail/exim/files/debian/75_23-Do-not-close-the-main-_log-if-we-do-not-see-a-chance.patch new file mode 100644 index 000000000000..12d91633c4bb --- /dev/null +++ b/mail/exim/files/debian/75_23-Do-not-close-the-main-_log-if-we-do-not-see-a-chance.patch @@ -0,0 +1,166 @@ +From 235c7030ee9ee1c1aad507786506a470b580bfe2 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Fri, 23 Apr 2021 22:41:57 +0200 +Subject: [PATCH 23/23] Do not close the (main)_log, if we do not see a chance + to open it again. + +The process doing local deliveries runs as an unprivileged user. If this +process needs to log failures or warnings (as caused by the +is_tainting2() function), it can't re-open the main_log and just exits. +--- + src/log.c | 84 ++++++++++++++++----------------- + src/transports/appendfile.c | 6 +++ + 2 files changed, 47 insertions(+), 43 deletions(-) + +diff --git a/src/log.c b/src/log.c +index 7ef7074ec..c2ef698e7 100644 +--- a/src/log.c ++++ b/src/log.c +@@ -646,18 +646,36 @@ return total_written; + } + + +- +-static void +-set_file_path(void) ++void ++set_file_path(BOOL *multiple) + { ++uschar *s; + int sep = ':'; /* Fixed separator - outside use */ +-uschar *t; +-const uschar *tt = US LOG_FILE_PATH; +-while ((t = string_nextinlist(&tt, &sep, log_buffer, LOG_BUFFER_SIZE))) ++uschar *ss = *log_file_path ? log_file_path : LOG_FILE_PATH; ++ ++logging_mode = 0; ++while ((s = string_nextinlist(&ss, &sep, log_buffer, LOG_BUFFER_SIZE))) + { +- if (Ustrcmp(t, "syslog") == 0 || t[0] == 0) continue; +- file_path = string_copy(t); +- break; ++ if (Ustrcmp(s, "syslog") == 0) ++ logging_mode |= LOG_MODE_SYSLOG; ++ else if (logging_mode & LOG_MODE_FILE) /* we know a file already */ ++ { ++ if (multiple) *multiple = TRUE; ++ } ++ else ++ { ++ logging_mode |= LOG_MODE_FILE; ++ ++ /* If a non-empty path is given, use it */ ++ ++ if (*s) ++ file_path = string_copy(s); ++ ++ /* If the path is empty, we want to use the first non-empty, non- ++ syslog item in LOG_FILE_PATH, if there is one, since the value of ++ log_file_path may have been set at runtime. If there is no such item, ++ use the ultimate default in the spool directory. */ ++ } + } + } + +@@ -665,7 +683,11 @@ while ((t = string_nextinlist(&tt, &sep, log_buffer, LOG_BUFFER_SIZE))) + void + mainlog_close(void) + { +-if (mainlogfd < 0) return; ++/* avoid closing it if it is closed already or if we do not see a chance ++to open the file mainlog later again */ ++if (mainlogfd < 0 /* already closed */ ++ || !(geteuid() == 0 || geteuid() == exim_uid)) ++ return; + (void)close(mainlogfd); + mainlogfd = -1; + mainlog_inode = 0; +@@ -780,38 +802,7 @@ if (!path_inspected) + /* If nothing has been set, don't waste effort... the default values for the + statics are file_path="" and logging_mode = LOG_MODE_FILE. */ + +- if (*log_file_path) +- { +- int sep = ':'; /* Fixed separator - outside use */ +- uschar *s; +- const uschar *ss = log_file_path; +- +- logging_mode = 0; +- while ((s = string_nextinlist(&ss, &sep, log_buffer, LOG_BUFFER_SIZE))) +- { +- if (Ustrcmp(s, "syslog") == 0) +- logging_mode |= LOG_MODE_SYSLOG; +- else if (logging_mode & LOG_MODE_FILE) +- multiple = TRUE; +- else +- { +- logging_mode |= LOG_MODE_FILE; +- +- /* If a non-empty path is given, use it */ +- +- if (*s) +- file_path = string_copy(s); +- +- /* If the path is empty, we want to use the first non-empty, non- +- syslog item in LOG_FILE_PATH, if there is one, since the value of +- log_file_path may have been set at runtime. If there is no such item, +- use the ultimate default in the spool directory. */ +- +- else +- set_file_path(); /* Empty item in log_file_path */ +- } /* First non-syslog item in log_file_path */ +- } /* Scan of log_file_path */ +- } ++ if (*log_file_path) set_file_path(&multiple); + + /* If no modes have been selected, it is a major disaster */ + +@@ -1431,7 +1422,7 @@ if (opts) + resulting in certain setup not having been done. Hack this for now so we + do not segfault; note that nondefault log locations will not work */ + +-if (!*file_path) set_file_path(); ++if (!*file_path) set_file_path(NULL); + + open_log(&fd, lt_debug, tag_name); + +@@ -1453,5 +1444,12 @@ debug_file = NULL; + unlink_log(lt_debug); + } + ++void ++open_logs(const char *m) ++{ ++set_file_path(NULL); ++open_log(&mainlogfd, lt_main, 0); ++open_log(&rejectlogfd, lt_reject, 0); ++} + + /* End of log.c */ +diff --git a/src/transports/appendfile.c b/src/transports/appendfile.c +index 6772b338b..706af6dde 100644 +--- a/src/transports/appendfile.c ++++ b/src/transports/appendfile.c +@@ -217,6 +217,9 @@ Arguments: + Returns: OK, FAIL, or DEFER + */ + ++void ++openlogs(); ++ + static int + appendfile_transport_setup(transport_instance *tblock, address_item *addrlist, + transport_feedback *dummy, uid_t uid, gid_t gid, uschar **errmsg) +@@ -231,6 +234,9 @@ dummy = dummy; + uid = uid; + gid = gid; + ++/* we can't wait until we're not privileged anymore */ ++open_logs("appendfile"); ++ + if (ob->expand_maildir_use_size_file) + ob->maildir_use_size_file = expand_check_condition(ob->expand_maildir_use_size_file, + US"`maildir_use_size_file` in transport", tblock->name); +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_24-Silence-the-compiler.patch b/mail/exim/files/debian/75_24-Silence-the-compiler.patch new file mode 100644 index 000000000000..14c3d5b433d2 --- /dev/null +++ b/mail/exim/files/debian/75_24-Silence-the-compiler.patch @@ -0,0 +1,57 @@ +From 33d5b8e8e4c2f23b4e834e3a095e3c9dd9f0686b Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Sun, 25 Apr 2021 18:58:35 +0200 +Subject: [PATCH 1/4] Silence the compiler + +--- + src/log.c | 4 ++-- + src/transports/appendfile.c | 4 ++-- + 2 files changed, 4 insertions(+), 4 deletions(-) + +diff --git a/src/log.c b/src/log.c +index c2ef698e7..11d259197 100644 +--- a/src/log.c ++++ b/src/log.c +@@ -651,7 +651,7 @@ set_file_path(BOOL *multiple) + { + uschar *s; + int sep = ':'; /* Fixed separator - outside use */ +-uschar *ss = *log_file_path ? log_file_path : LOG_FILE_PATH; ++const uschar *ss = *log_file_path ? log_file_path : US LOG_FILE_PATH; + + logging_mode = 0; + while ((s = string_nextinlist(&ss, &sep, log_buffer, LOG_BUFFER_SIZE))) +@@ -1445,7 +1445,7 @@ unlink_log(lt_debug); + } + + void +-open_logs(const char *m) ++open_logs(void) + { + set_file_path(NULL); + open_log(&mainlogfd, lt_main, 0); +diff --git a/src/transports/appendfile.c b/src/transports/appendfile.c +index 706af6dde..c0f4de4c8 100644 +--- a/src/transports/appendfile.c ++++ b/src/transports/appendfile.c +@@ -218,7 +218,7 @@ Returns: OK, FAIL, or DEFER + */ + + void +-openlogs(); ++open_logs(void); + + static int + appendfile_transport_setup(transport_instance *tblock, address_item *addrlist, +@@ -235,7 +235,7 @@ uid = uid; + gid = gid; + + /* we can't wait until we're not privileged anymore */ +-open_logs("appendfile"); ++open_logs(); + + if (ob->expand_maildir_use_size_file) + ob->maildir_use_size_file = expand_check_condition(ob->expand_maildir_use_size_file, +-- +2.30.2 + diff --git a/mail/exim/files/debian/75_26-Disable-taintchecks-for-mkdir-this-isn-t-part-of-4.9.patch b/mail/exim/files/debian/75_26-Disable-taintchecks-for-mkdir-this-isn-t-part-of-4.9.patch new file mode 100644 index 000000000000..cee6066f9200 --- /dev/null +++ b/mail/exim/files/debian/75_26-Disable-taintchecks-for-mkdir-this-isn-t-part-of-4.9.patch @@ -0,0 +1,27 @@ +From 1416743e923cacf42955392e92995f5fe7e1c680 Mon Sep 17 00:00:00 2001 +From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> +Date: Sun, 25 Apr 2021 10:19:32 +0200 +Subject: [PATCH 3/4] Disable taintchecks for mkdir, this isn't part of 4.94 + +--- + src/directory.c | 2 ++ + 1 file changed, 2 insertions(+) + +diff --git a/src/directory.c b/src/directory.c +index 9f88f4141..ece1ee8f3 100644 +--- a/src/directory.c ++++ b/src/directory.c +@@ -44,8 +44,10 @@ uschar c = 1; + struct stat statbuf; + uschar * path; + ++/* does not work with 4.94 + if (is_tainted2(name, LOG_MAIN|LOG_PANIC, "Tainted path '%s' for new directory", name)) + { p = US"create"; path = US name; errno = EACCES; goto bad; } ++*/ + + if (parent) + { +-- +2.30.2 + diff --git a/mail/exim/files/patch-z0002-Taint-fix-pam-expansion-condition.-Bug-2587 b/mail/exim/files/patch-z0002-Taint-fix-pam-expansion-condition.-Bug-2587 deleted file mode 100644 index cdc7ccda8ed5..000000000000 --- a/mail/exim/files/patch-z0002-Taint-fix-pam-expansion-condition.-Bug-2587 +++ /dev/null @@ -1,56 +0,0 @@ -From 173bd1c8f9cf83ad8c0e61a9e32678e7e371d41d Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Tue, 2 Jun 2020 14:50:31 +0100 -Subject: [PATCH 02/26] Taint: fix pam expansion condition. Bug 2587 - -(cherry picked from commit f7f933a199be8bb7362c715e0040545b514cddca) ---- - doc/ChangeLog | 9 +++++++++ - src/auths/call_pam.c | 5 ++--- - -diff --git doc/ChangeLog doc/ChangeLog -index 585deb042..dbdc22117 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -3,6 +3,15 @@ affect Exim's operation, with an unchanged configuration file. For new - options, and new features, see the NewStuff file next to this ChangeLog. - - -+Since Exim version 4.94 -+----------------------- -+ -+JH/02 Bug 2587: Fix pam expansion condition. Tainted values are commonly used -+ as arguments, so an implementation trying to copy these into a local -+ buffer was taking a taint-enformance trap. Fix by using dynamically -+ created buffers. -+ -+ - Exim version 4.94 - ----------------- - -diff --git src/auths/call_pam.c src/auths/call_pam.c -index 2959cbbf3..80bb23ec3 100644 ---- src/auths/call_pam.c -+++ src/auths/call_pam.c -@@ -83,8 +83,7 @@ for (int i = 0; i < num_msg; i++) - { - case PAM_PROMPT_ECHO_ON: - case PAM_PROMPT_ECHO_OFF: -- arg = string_nextinlist(&pam_args, &sep, big_buffer, big_buffer_size); -- if (!arg) -+ if (!(arg = string_nextinlist(&pam_args, &sep, NULL, 0))) - { - arg = US""; - pam_arg_ended = TRUE; -@@ -155,7 +154,7 @@ pam_arg_ended = FALSE; - fail. PAM doesn't support authentication with an empty user (it prompts for it, - causing a potential mis-interpretation). */ - --user = string_nextinlist(&pam_args, &sep, big_buffer, big_buffer_size); -+user = string_nextinlist(&pam_args, &sep, NULL, 0); - if (user == NULL || user[0] == 0) return FAIL; - - /* Start off PAM interaction */ --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0003-Taint-fix-listcount-expansion-operator.-Bug-2586 b/mail/exim/files/patch-z0003-Taint-fix-listcount-expansion-operator.-Bug-2586 deleted file mode 100644 index 42f01d070507..000000000000 --- a/mail/exim/files/patch-z0003-Taint-fix-listcount-expansion-operator.-Bug-2586 +++ /dev/null @@ -1,43 +0,0 @@ -From 63652bbaf66c4bdb388b08fdf3eb8ab1e4d91475 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Tue, 2 Jun 2020 15:03:36 +0100 -Subject: [PATCH 03/26] Taint: fix listcount expansion operator. Bug 2586 - -(cherry picked from commit 44644c2e404a3ea0191db0b0458e86924fb240bb) ---- - doc/ChangeLog | 4 ++++ - src/expand.c | 3 +-- - -diff --git doc/ChangeLog doc/ChangeLog -index dbdc22117..94bcea29b 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -11,6 +11,10 @@ JH/02 Bug 2587: Fix pam expansion condition. Tainted values are commonly used - buffer was taking a taint-enformance trap. Fix by using dynamically - created buffers. - -+JH/03 Bug 2586: Fix listcount expansion operator. Using tainted arguments is -+ reasonable, eg. to count headers. Fix by using dynamically created -+ buffers rather than a local, -+ - - Exim version 4.94 - ----------------- -diff --git src/expand.c src/expand.c -index 26f7f10ac..6ed22c14d 100644 ---- src/expand.c -+++ src/expand.c -@@ -7208,9 +7208,8 @@ while (*s != 0) - { - int cnt = 0; - int sep = 0; -- uschar buffer[256]; - -- while (string_nextinlist(CUSS &sub, &sep, buffer, sizeof(buffer))) cnt++; -+ while (string_nextinlist(CUSS &sub, &sep, NULL, 0)) cnt++; - yield = string_fmt_append(yield, "%d", cnt); - continue; - } --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0004-Docs-fix-mistaken-variable-name b/mail/exim/files/patch-z0004-Docs-fix-mistaken-variable-name deleted file mode 100644 index bcf4909ce0fb..000000000000 --- a/mail/exim/files/patch-z0004-Docs-fix-mistaken-variable-name +++ /dev/null @@ -1,28 +0,0 @@ -From aabe0ebe82297d7dec3abdfff9c3b1edc34fd8ab Mon Sep 17 00:00:00 2001 -From: Patrick Boutilier <boutilpj@ednet.ns.ca> -Date: Tue, 2 Jun 2020 15:16:10 +0100 -Subject: [PATCH 04/26] Docs: fix mistaken variable name - -(cherry picked from commit eb55cb1d2c5552209e24345e9d21f83ec1eaccf6) ---- - README.UPDATING | 4 ++-- - -diff --git README.UPDATING README.UPDATING -index a0afa8df0..708027f2c 100644 ---- README.UPDATING -+++ README.UPDATING -@@ -31,9 +31,9 @@ Exim version 4.94 - - Some Transports now refuse to use tainted data in constructing their delivery - location; this WILL BREAK configurations which are not updated accordingly. --In particular: any Transport use of $local_user which has been relying upon -+In particular: any Transport use of $local_part which has been relying upon - check_local_user far away in the Router to make it safe, should be updated to --replace $local_user with $local_part_data. -+replace $local_part with $local_part_data. - - Attempting to remove, in router or transport, a header name that ends with - an asterisk (which is a standards-legal name) will now result in all headers --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0006-Docs-typoes b/mail/exim/files/patch-z0006-Docs-typoes deleted file mode 100644 index 16ec41fe911f..000000000000 --- a/mail/exim/files/patch-z0006-Docs-typoes +++ /dev/null @@ -1,25 +0,0 @@ -From de498d230862bcc49acbc6d5e76c71b1e15596c3 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Tue, 2 Jun 2020 16:34:42 +0100 -Subject: [PATCH 06/26] Docs: typoes - -Cherry-picked from: 1195f8f2a4 ---- - doc/ChangeLog | 2 +- - -diff --git doc/ChangeLog doc/ChangeLog -index 94bcea29b..f858c9121 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -8,7 +8,7 @@ Since Exim version 4.94 - - JH/02 Bug 2587: Fix pam expansion condition. Tainted values are commonly used - as arguments, so an implementation trying to copy these into a local -- buffer was taking a taint-enformance trap. Fix by using dynamically -+ buffer was taking a taint-enforcement trap. Fix by using dynamically - created buffers. - - JH/03 Bug 2586: Fix listcount expansion operator. Using tainted arguments is --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0007-Taint-fix-multiple-ACL-actions-to-properly-manage-tainted- b/mail/exim/files/patch-z0007-Taint-fix-multiple-ACL-actions-to-properly-manage-tainted- deleted file mode 100644 index 44cc46634e77..000000000000 --- a/mail/exim/files/patch-z0007-Taint-fix-multiple-ACL-actions-to-properly-manage-tainted- +++ /dev/null @@ -1,79 +0,0 @@ -From 623f07cfdcaca96274ca765d0fcf0761bdf7151b Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Wed, 3 Jun 2020 11:40:17 +0100 -Subject: [PATCH 07/26] Taint: fix multiple ACL actions to properly manage - tainted argument data - -(cherry picked from commit 12b7f811de4a540d0724585aecfa33b5881e2a30) ---- - doc/ChangeLog | 4 +++- - src/acl.c | 12 ++++++------ - -diff --git doc/ChangeLog doc/ChangeLog -index f858c9121..015959cb6 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -13,7 +13,9 @@ JH/02 Bug 2587: Fix pam expansion condition. Tainted values are commonly used - - JH/03 Bug 2586: Fix listcount expansion operator. Using tainted arguments is - reasonable, eg. to count headers. Fix by using dynamically created -- buffers rather than a local, -+ buffers rather than a local. Do similar fixes for ACL actions "dcc", -+ "log_reject_target", "malware" and "spam"; the arguments are expanded -+ so could be handling tainted values. - - - Exim version 4.94 -diff --git src/acl.c src/acl.c -index c1d60bbd9..8619cd5ef 100644 ---- src/acl.c -+++ src/acl.c -@@ -3349,11 +3349,11 @@ for (; cb; cb = cb->next) - { - /* Separate the regular expression and any optional parameters. */ - const uschar * list = arg; -- uschar *ss = string_nextinlist(&list, &sep, big_buffer, big_buffer_size); -+ uschar *ss = string_nextinlist(&list, &sep, NULL, 0); - /* Run the dcc backend. */ - rc = dcc_process(&ss); - /* Modify return code based upon the existence of options. */ -- while ((ss = string_nextinlist(&list, &sep, big_buffer, big_buffer_size))) -+ while ((ss = string_nextinlist(&list, &sep, NULL, 0))) - if (strcmpic(ss, US"defer_ok") == 0 && rc == DEFER) - rc = FAIL; /* FAIL so that the message is passed to the next ACL */ - } -@@ -3514,7 +3514,7 @@ for (; cb; cb = cb->next) - int sep = 0; - const uschar *s = arg; - uschar * ss; -- while ((ss = string_nextinlist(&s, &sep, big_buffer, big_buffer_size))) -+ while ((ss = string_nextinlist(&s, &sep, NULL, 0))) - { - if (Ustrcmp(ss, "main") == 0) logbits |= LOG_MAIN; - else if (Ustrcmp(ss, "panic") == 0) logbits |= LOG_PANIC; -@@ -3567,7 +3567,7 @@ for (; cb; cb = cb->next) - { - /* Separate the regular expression and any optional parameters. */ - const uschar * list = arg; -- uschar * ss = string_nextinlist(&list, &sep, big_buffer, big_buffer_size); -+ uschar * ss = string_nextinlist(&list, &sep, NULL, 0); - uschar * opt; - BOOL defer_ok = FALSE; - int timeout = 0; -@@ -3672,11 +3672,11 @@ for (; cb; cb = cb->next) - { - /* Separate the regular expression and any optional parameters. */ - const uschar * list = arg; -- uschar *ss = string_nextinlist(&list, &sep, big_buffer, big_buffer_size); -+ uschar *ss = string_nextinlist(&list, &sep, NULL, 0); - - rc = spam(CUSS &ss); - /* Modify return code based upon the existence of options. */ -- while ((ss = string_nextinlist(&list, &sep, big_buffer, big_buffer_size))) -+ while ((ss = string_nextinlist(&list, &sep, NULL, 0))) - if (strcmpic(ss, US"defer_ok") == 0 && rc == DEFER) - rc = FAIL; /* FAIL so that the message is passed to the next ACL */ - } --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0008-Fix-bi.-Bug-2590 b/mail/exim/files/patch-z0008-Fix-bi.-Bug-2590 deleted file mode 100644 index 6c42ea45d7fc..000000000000 --- a/mail/exim/files/patch-z0008-Fix-bi.-Bug-2590 +++ /dev/null @@ -1,44 +0,0 @@ -From 0e8319c3edebfec2158fbaa4898af27cb3225c99 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Thu, 4 Jun 2020 15:28:15 +0100 -Subject: [PATCH 08/26] Fix -bi. Bug 2590 - - Actual fix from pierre.labastie@neuf.fr ; additional coding and testcase bu jgh - Broken-by: bdcc6f2bd5 - - (Cherry-picked from: 0e0e171628) ---- - doc/ChangeLog | 4 ++++ - src/exim.c | 2 +- - -diff --git doc/ChangeLog doc/ChangeLog -index 015959cb6..621d5b1b5 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -17,6 +17,10 @@ JH/03 Bug 2586: Fix listcount expansion operator. Using tainted arguments is - "log_reject_target", "malware" and "spam"; the arguments are expanded - so could be handling tainted values. - -+JH/04 Bug 2590: Fix -bi (newaliases). A previous code rearrangement had -+ broken the (no-op) support for this sendmail command. Restore it -+ to doing nothing, silently, and returning good status. -+ - - Exim version 4.94 - ----------------- -diff --git src/exim.c src/exim.c -index a60488e95..6143fe989 100644 ---- src/exim.c -+++ src/exim.c -@@ -2148,7 +2148,7 @@ on the second character (the one after '-'), to save some effort. */ - concept of *the* alias file, but since Sun's YP make script calls - sendmail this way, some support must be provided. */ - case 'i': -- if (!*++argrest) bi_option = TRUE; -+ if (!*argrest) bi_option = TRUE; - else badarg = TRUE; - break; - --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0009-Filters-fix-vacation-in-Exim-filter.-Bug-2593 b/mail/exim/files/patch-z0009-Filters-fix-vacation-in-Exim-filter.-Bug-2593 deleted file mode 100644 index cb3f2c113cd5..000000000000 --- a/mail/exim/files/patch-z0009-Filters-fix-vacation-in-Exim-filter.-Bug-2593 +++ /dev/null @@ -1,48 +0,0 @@ -From 701af1005a6effaac5ce249f1c2086dc6c0c2a7f Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Mon, 8 Jun 2020 13:00:55 +0100 -Subject: [PATCH 09/26] Filters: fix "vacation" in Exim filter. Bug 2593 - -Broken-by: cfb9cf20cb (4.90) -(cherry picked from commit 59eee1bc902f106d20f507ba16f37cb8ab5a5e8d) ---- - doc/ChangeLog | 5 ++ - src/transports/autoreply.c | 6 +-- - -diff --git doc/ChangeLog doc/ChangeLog -index 621d5b1b5..b9c1ec29e 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -21,6 +21,11 @@ JH/04 Bug 2590: Fix -bi (newaliases). A previous code rearrangement had - broken the (no-op) support for this sendmail command. Restore it - to doing nothing, silently, and returning good status. - -+JH/05 Bug 2593: Fix "vacation" in Exim filter. Previously, when a "once" -+ record path was given (or the default used) without a leading directory -+ path, an error occurred on trying to open it. Use the transport's working -+ directory. -+ - - Exim version 4.94 - ----------------- -diff --git src/transports/autoreply.c src/transports/autoreply.c -index 4c2c08b70..865abbf4f 100644 ---- src/transports/autoreply.c -+++ src/transports/autoreply.c -@@ -474,10 +474,10 @@ if (oncelog && *oncelog && to) - else - { - EXIM_DATUM key_datum, result_datum; -- uschar * dirname = string_copy(oncelog); -- uschar * s; -+ uschar * dirname, * s; - -- if ((s = Ustrrchr(dirname, '/'))) *s = '\0'; -+ dirname = (s = Ustrrchr(oncelog, '/')) -+ ? string_copyn(oncelog, s - oncelog) : NULL; - EXIM_DBOPEN(oncelog, dirname, O_RDWR|O_CREAT, ob->mode, &dbm_file); - if (!dbm_file) - { --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0010-TLS-use-RFC-6125-rules-for-certifucate-name-checks-when-CN b/mail/exim/files/patch-z0010-TLS-use-RFC-6125-rules-for-certifucate-name-checks-when-CN deleted file mode 100644 index 626d11609e1b..000000000000 --- a/mail/exim/files/patch-z0010-TLS-use-RFC-6125-rules-for-certifucate-name-checks-when-CN +++ /dev/null @@ -1,180 +0,0 @@ -From 3fe5ec41e81831028c992f77a15292872fbbac75 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Thu, 11 Jun 2020 20:45:05 +0100 -Subject: [PATCH 10/26] TLS: use RFC 6125 rules for certifucate name - checks when CNAMES are present. Bug 2594 - - (cherry picked from commit 0851a3bbf4667081d47f5d85b6b3a5cb33cbdba6) ---- - doc/ChangeLog | 7 ++- - src/host.c | 17 +++++++ - src/structs.h | 19 ++++---- - src/tls-gnu.c | 4 +- - src/tls-openssl.c | 20 ++++----- - -diff --git doc/ChangeLog doc/ChangeLog -index b9c1ec29e..612005803 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -26,6 +26,11 @@ JH/05 Bug 2593: Fix "vacation" in Exim filter. Previously, when a "once" - path, an error occurred on trying to open it. Use the transport's working - directory. - -+JH/06 Bug 2594: Change the name used for certificate name checks in the smtp -+ transport. Previously it was the name on the DNS A-record; use instead -+ the head of the CNAME chain leading there (if there is one). This seems -+ to align better with RFC 6125. -+ - - Exim version 4.94 - ----------------- -@@ -331,7 +336,7 @@ JH/20 Bug 2389: fix server advertising of usable certificates, under GnuTLS in - - JH/21 The smtp transport option "hosts_noproxy_tls" is now unset by default. - A single TCP connection by a client will now hold a TLS connection open -- for multiple message deliveries, by default. Previoud the default was to -+ for multiple message deliveries, by default. Previously the default was to - not do so. - - JH/22 The smtp transport option "hosts_try_dane" now enables all hosts by -diff --git src/host.c src/host.c -index 0e0e0130b..817d4446c 100644 ---- src/host.c -+++ src/host.c -@@ -1950,6 +1950,13 @@ BOOL temp_error = FALSE; - int af; - #endif - -+#ifndef DISABLE_TLS -+/* Copy the host name at this point to the value which is used for -+TLS certificate name checking, before anything modifies it. */ -+ -+host->certname = host->name; -+#endif -+ - /* Make sure DNS options are set as required. This appears to be necessary in - some circumstances when the get..byname() function actually calls the DNS. */ - -@@ -2117,6 +2124,9 @@ for (int i = 1; i <= times; - { - host_item *next = store_get(sizeof(host_item), FALSE); - next->name = host->name; -+#ifndef DISABLE_TLS -+ next->certname = host->certname; -+#endif - next->mx = host->mx; - next->address = text_address; - next->port = PORT_NONE; -@@ -2260,6 +2270,13 @@ BOOL v6_find_again = FALSE; - BOOL dnssec_fail = FALSE; - int i; - -+#ifndef DISABLE_TLS -+/* Copy the host name at this point to the value which is used for -+TLS certificate name checking, before any CNAME-following modifies it. */ -+ -+host->certname = host->name; -+#endif -+ - /* If allow_ip is set, a name which is an IP address returns that value - as its address. This is used for MX records when allow_mx_to_ip is set, for - those sites that feel they have to flaunt the RFC rules. */ -diff --git src/structs.h src/structs.h -index c6700d513..206237f04 100644 ---- src/structs.h -+++ src/structs.h -@@ -80,14 +80,17 @@ typedef enum {DS_UNK=-1, DS_NO, DS_YES} dnssec_status_t; - - typedef struct host_item { - struct host_item *next; -- const uschar *name; /* Host name */ -- const uschar *address; /* IP address in text form */ -- int port; /* port value in host order (if SRV lookup) */ -- int mx; /* MX value if found via MX records */ -- int sort_key; /* MX*1000 plus random "fraction" */ -- int status; /* Usable, unusable, or unknown */ -- int why; /* Why host is unusable */ -- int last_try; /* Time of last try if known */ -+ const uschar *name; /* Host name */ -+#ifndef DISABLE_TLS -+ const uschar *certname; /* Name used for certificate checks */ -+#endif -+ const uschar *address; /* IP address in text form */ -+ int port; /* port value in host order (if SRV lookup) */ -+ int mx; /* MX value if found via MX records */ -+ int sort_key; /* MX*1000 plus random "fraction" */ -+ int status; /* Usable, unusable, or unknown */ -+ int why; /* Why host is unusable */ -+ int last_try; /* Time of last try if known */ - dnssec_status_t dnssec; - } host_item; - -diff --git src/tls-gnu.c src/tls-gnu.c -index 24114f05e..875c82efa 100644 ---- src/tls-gnu.c -+++ src/tls-gnu.c -@@ -2601,9 +2601,9 @@ if (verify_check_given_host(CUSS &ob->tls_verify_cert_hostnames, host) == OK) - { - state->exp_tls_verify_cert_hostnames = - #ifdef SUPPORT_I18N -- string_domain_utf8_to_alabel(host->name, NULL); -+ string_domain_utf8_to_alabel(host->certname, NULL); - #else -- host->name; -+ host->certname; - #endif - DEBUG(D_tls) - debug_printf("TLS: server cert verification includes hostname: \"%s\".\n", -diff --git src/tls-openssl.c src/tls-openssl.c -index 8c9d8aa69..a62322928 100644 ---- src/tls-openssl.c -+++ src/tls-openssl.c -@@ -372,10 +372,10 @@ typedef struct ocsp_resp { - } ocsp_resplist; - - typedef struct tls_ext_ctx_cb { -- tls_support * tlsp; -- uschar *certificate; -- uschar *privatekey; -- BOOL is_server; -+ tls_support * tlsp; -+ uschar * certificate; -+ uschar * privatekey; -+ BOOL is_server; - #ifndef DISABLE_OCSP - STACK_OF(X509) *verify_stack; /* chain for verifying the proof */ - union { -@@ -390,14 +390,14 @@ typedef struct tls_ext_ctx_cb { - } client; - } u_ocsp; - #endif -- uschar *dhparam; -+ uschar * dhparam; - /* these are cached from first expand */ -- uschar *server_cipher_list; -+ uschar * server_cipher_list; - /* only passed down to tls_error: */ -- host_item *host; -+ host_item * host; - const uschar * verify_cert_hostnames; - #ifndef DISABLE_EVENT -- uschar * event_action; -+ uschar * event_action; - #endif - } tls_ext_ctx_cb; - -@@ -2915,9 +2915,9 @@ if (verify_check_given_host(CUSS &ob->tls_verify_cert_hostnames, host) == OK) - { - cbinfo->verify_cert_hostnames = - #ifdef SUPPORT_I18N -- string_domain_utf8_to_alabel(host->name, NULL); -+ string_domain_utf8_to_alabel(host->certname, NULL); - #else -- host->name; -+ host->certname; - #endif - DEBUG(D_tls) debug_printf("Cert hostname to check: \"%s\"\n", - cbinfo->verify_cert_hostnames); --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0011-Taint-fix-radius-expansion-condition b/mail/exim/files/patch-z0011-Taint-fix-radius-expansion-condition deleted file mode 100644 index 04cb3acd08a3..000000000000 --- a/mail/exim/files/patch-z0011-Taint-fix-radius-expansion-condition +++ /dev/null @@ -1,40 +0,0 @@ -From 94d719d803caf2c0c902dceeb787795eac11a63b Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Fri, 12 Jun 2020 00:46:34 +0100 -Subject: [PATCH 11/26] Taint: fix radius expansion condition - -(cherry picked from commit f91219c114a3d95792d052555664a5a7a3984a8d) ---- - doc/ChangeLog | 2 +- - src/auths/call_radius.c | 3 +-- - -diff --git doc/ChangeLog doc/ChangeLog -index 612005803..41d8c6276 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -9,7 +9,7 @@ Since Exim version 4.94 - JH/02 Bug 2587: Fix pam expansion condition. Tainted values are commonly used - as arguments, so an implementation trying to copy these into a local - buffer was taking a taint-enforcement trap. Fix by using dynamically -- created buffers. -+ created buffers. Similar fix for radius expansion condition. - - JH/03 Bug 2586: Fix listcount expansion operator. Using tainted arguments is - reasonable, eg. to count headers. Fix by using dynamically created -diff --git src/auths/call_radius.c src/auths/call_radius.c -index cc269dcd5..9d10b34c6 100644 ---- src/auths/call_radius.c -+++ src/auths/call_radius.c -@@ -96,8 +96,7 @@ int sep = 0; - #endif - - --user = string_nextinlist(&radius_args, &sep, big_buffer, big_buffer_size); --if (!user) user = US""; -+if (!(user = string_nextinlist(&radius_args, &sep, NULL, 0))) user = US""; - - DEBUG(D_auth) debug_printf("Running RADIUS authentication for user \"%s\" " - "and \"%s\"\n", user, radius_args); --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0012-smtp_accept_map_per_host-call-search_tidyup-in-fail-path.- b/mail/exim/files/patch-z0012-smtp_accept_map_per_host-call-search_tidyup-in-fail-path.- deleted file mode 100644 index 35d0e48879a1..000000000000 --- a/mail/exim/files/patch-z0012-smtp_accept_map_per_host-call-search_tidyup-in-fail-path.- +++ /dev/null @@ -1,42 +0,0 @@ -From c165e95889471bc1a644104dd9a6129c47c56c09 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Fri, 12 Jun 2020 20:43:43 +0100 -Subject: [PATCH 12/26] smtp_accept_map_per_host: call search_tidyup in fail - path. Bug 2597 - -(cherry-picked from: d3a538c8fe) ---- - doc/ChangeLog | 5 +++++ - src/daemon.c | 1 + - -diff --git doc/ChangeLog doc/ChangeLog -index 41d8c6276..92298e7fc 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -31,6 +31,11 @@ JH/06 Bug 2594: Change the name used for certificate name checks in the smtp - the head of the CNAME chain leading there (if there is one). This seems - to align better with RFC 6125. - -+JH/07 Bug 2597: Fix a resource leak. Using a lookup in obtaining a value for -+ smtp_accept_max_per_host allocated resources which were not released -+ when the limit was exceeded. This eventually crashed the daemon. Fix -+ by adding a relase action in that path. -+ - - Exim version 4.94 - ----------------- -diff --git src/daemon.c src/daemon.c -index 2bed143a1..9d491593f 100644 ---- src/daemon.c -+++ src/daemon.c -@@ -336,6 +336,7 @@ if ((max_for_this_host > 0) && - log_write(L_connection_reject, - LOG_MAIN, "Connection from %s refused: too many connections " - "from that IP address", whofrom->s); -+ search_tidyup(); - goto ERROR_RETURN; - } - } --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0013-Taint-fix-verify.-Bug-2598 b/mail/exim/files/patch-z0013-Taint-fix-verify.-Bug-2598 deleted file mode 100644 index de23801152f7..000000000000 --- a/mail/exim/files/patch-z0013-Taint-fix-verify.-Bug-2598 +++ /dev/null @@ -1,50 +0,0 @@ -From ecf1e77accda6355ebb745a0a03e97ba7eb298b2 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Sun, 14 Jun 2020 22:14:11 +0100 -Subject: [PATCH 13/26] Taint: fix verify. Bug 2598 - -(cherry-picked from 2b60ac1021 and 9eed571fd7) ---- - doc/ChangeLog | 4 +++ - src/acl.c | 4 +-- - -diff --git doc/ChangeLog doc/ChangeLog -index 92298e7fc..859e87b00 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -36,6 +36,10 @@ JH/07 Bug 2597: Fix a resource leak. Using a lookup in obtaining a value for - when the limit was exceeded. This eventually crashed the daemon. Fix - by adding a relase action in that path. - -+JH/08 Bug 2598: Fix verify ACL condition. The options for the condition are -+ expanded; previously using tainted values was rejected. Fix by using -+ dynamically-created buffers. -+ - - Exim version 4.94 - ----------------- -diff --git src/acl.c src/acl.c -index 8619cd5ef..11d1fd028 100644 ---- src/acl.c -+++ src/acl.c -@@ -1767,7 +1767,7 @@ switch(vp->value) - /* Remaining items are optional; they apply to sender and recipient - verification, including "header sender" verification. */ - --while ((ss = string_nextinlist(&list, &sep, big_buffer, big_buffer_size))) -+while ((ss = string_nextinlist(&list, &sep, NULL, 0))) - { - if (strcmpic(ss, US"defer_ok") == 0) defer_ok = TRUE; - else if (strcmpic(ss, US"no_details") == 0) no_details = TRUE; -@@ -1804,7 +1804,7 @@ while ((ss = string_nextinlist(&list, &sep, big_buffer, big_buffer_size))) - uschar * opt; - - while (isspace(*sublist)) sublist++; -- while ((opt = string_nextinlist(&sublist, &optsep, buffer, sizeof(buffer)))) -+ while ((opt = string_nextinlist(&sublist, &optsep, NULL, 0))) - { - callout_opt_t * op; - double period = 1.0F; --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0014-Fix-string_copy-macro-to-not-multiple-eval-args.-Bug-2603 b/mail/exim/files/patch-z0014-Fix-string_copy-macro-to-not-multiple-eval-args.-Bug-2603 deleted file mode 100644 index a8420ba00deb..000000000000 --- a/mail/exim/files/patch-z0014-Fix-string_copy-macro-to-not-multiple-eval-args.-Bug-2603 +++ /dev/null @@ -1,48 +0,0 @@ -From 5c608b75d5bd734ddca41e4468fb22544ef96265 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Sat, 20 Jun 2020 00:54:05 +0100 -Subject: [PATCH 14/26] Fix string_copy() macro to not multiple-eval args. Bug - 2603 - -Broken-by: a76d120aed -(cherry picked from commit 80c2ec2e47c556daff00c79ee068ce68f25fd264) ---- - doc/ChangeLog | 6 ++++++ - src/functions.h | 4 ++-- - -diff --git doc/ChangeLog doc/ChangeLog -index 859e87b00..1173b3651 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -40,6 +40,12 @@ JH/08 Bug 2598: Fix verify ACL condition. The options for the condition are - expanded; previously using tainted values was rejected. Fix by using - dynamically-created buffers. - -+JH/10 Bug 2603: Fix coding of string copying to only evaluate arguments once. -+ Previously a macro used one argument twice; when called with the -+ argument as an expression having side-effects, incorrect operation -+ resulted. Use an inlineable function. -+ -+ - - Exim version 4.94 - ----------------- -diff --git src/functions.h src/functions.h -index 0028deb0d..0050cdeeb 100644 ---- src/functions.h -+++ src/functions.h -@@ -767,9 +767,9 @@ string_copy_trc(const uschar * s, const char * func, int line) - /* Simple string-copy functions maintaining the taint */ - - #define string_copyn(s, len) \ -- string_copyn_taint_trc((s), (len), is_tainted(s), __FUNCTION__, __LINE__) -+ string_copyn_trc((s), (len), __FUNCTION__, __LINE__) - #define string_copy(s) \ -- string_copy_taint_trc((s), is_tainted(s), __FUNCTION__, __LINE__) -+ string_copy_trc((s), __FUNCTION__, __LINE__) - - - /************************************************* --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0015-Cutthrough-handle-request-when-a-callout-hold-is-active.-B b/mail/exim/files/patch-z0015-Cutthrough-handle-request-when-a-callout-hold-is-active.-B deleted file mode 100644 index 50e65bd87024..000000000000 --- a/mail/exim/files/patch-z0015-Cutthrough-handle-request-when-a-callout-hold-is-active.-B +++ /dev/null @@ -1,118 +0,0 @@ -From cdee8a5f76cc013de5622112cd04e42d0dcf333b Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Mon, 22 Jun 2020 17:27:18 +0100 -Subject: [PATCH 15/26] Cutthrough: handle request when a callout-hold is - active. Bug 2604 - -(cherry picked from commit 99bfcf2b678e7bd8125a7eb44409e46549bfc111) ---- - doc/ChangeLog | 4 +++ - src/acl.c | 50 +++++++++++++++++-------------- - src/verify.c | 4 +-- - -diff --git doc/ChangeLog doc/ChangeLog -index 1173b3651..de11b4f09 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -45,6 +45,10 @@ JH/10 Bug 2603: Fix coding of string copying to only evaluate arguments once. - argument as an expression having side-effects, incorrect operation - resulted. Use an inlineable function. - -+JH/11 Bug 2604: Fix request to cutthrough-deliver when a connection is already -+ held open for a verify callout. Previously this wan not accounted for -+ and a corrupt onward SMTP conversation resulted. -+ - - - Exim version 4.94 -diff --git src/acl.c src/acl.c -index 11d1fd028..62cb68561 100644 ---- src/acl.c -+++ src/acl.c -@@ -3264,37 +3264,41 @@ for (; cb; cb = cb->next) - the case where both sides handle prdr and this-node prdr acl - is "accept" */ - ignored = US"PRDR active"; -+ else if (f.deliver_freeze) -+ ignored = US"frozen"; -+ else if (f.queue_only_policy) -+ ignored = US"queue-only"; -+ else if (fake_response == FAIL) -+ ignored = US"fakereject"; -+ else if (rcpt_count != 1) -+ ignored = US"nonfirst rcpt"; -+ else if (cutthrough.delivery) -+ ignored = US"repeated"; -+ else if (cutthrough.callout_hold_only) -+ { -+ DEBUG(D_acl) -+ debug_printf_indent(" cutthrough request upgrades callout hold\n"); -+ cutthrough.callout_hold_only = FALSE; -+ cutthrough.delivery = TRUE; /* control accepted */ -+ } - else - { -- if (f.deliver_freeze) -- ignored = US"frozen"; -- else if (f.queue_only_policy) -- ignored = US"queue-only"; -- else if (fake_response == FAIL) -- ignored = US"fakereject"; -- else -+ cutthrough.delivery = TRUE; /* control accepted */ -+ while (*p == '/') - { -- if (rcpt_count == 1) -+ const uschar * pp = p+1; -+ if (Ustrncmp(pp, "defer=", 6) == 0) - { -- cutthrough.delivery = TRUE; /* control accepted */ -- while (*p == '/') -- { -- const uschar * pp = p+1; -- if (Ustrncmp(pp, "defer=", 6) == 0) -- { -- pp += 6; -- if (Ustrncmp(pp, "pass", 4) == 0) cutthrough.defer_pass = TRUE; -- /* else if (Ustrncmp(pp, "spool") == 0) ; default */ -- } -- else -- while (*pp && *pp != '/') pp++; -- p = pp; -- } -+ pp += 6; -+ if (Ustrncmp(pp, "pass", 4) == 0) cutthrough.defer_pass = TRUE; -+ /* else if (Ustrncmp(pp, "spool") == 0) ; default */ - } - else -- ignored = US"nonfirst rcpt"; -+ while (*pp && *pp != '/') pp++; -+ p = pp; - } - } -+ - DEBUG(D_acl) if (ignored) - debug_printf(" cutthrough request ignored on %s item\n", ignored); - } -diff --git src/verify.c src/verify.c -index fba1f6e9e..5f4181de9 100644 ---- src/verify.c -+++ src/verify.c -@@ -875,12 +875,12 @@ tls_retry_connection: - case PENDING_OK: done = TRUE; - new_address_record.result = ccache_accept; - break; -- case FAIL: done = TRUE; -+ case FAIL: done = TRUE; - yield = FAIL; - *failure_ptr = US"recipient"; - new_address_record.result = ccache_reject; - break; -- default: break; -+ default: break; - } - break; - --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0016-Lookups-Fix-subdir-filter-on-a-dsearch b/mail/exim/files/patch-z0016-Lookups-Fix-subdir-filter-on-a-dsearch deleted file mode 100644 index f2e46b49a370..000000000000 --- a/mail/exim/files/patch-z0016-Lookups-Fix-subdir-filter-on-a-dsearch +++ /dev/null @@ -1,53 +0,0 @@ -From 777ee8ae75277c05fb72cc94f568ba4d2bfe15a6 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Thu, 25 Jun 2020 11:16:54 +0100 -Subject: [PATCH 16/26] Lookups: Fix "subdir" filter on a dsearch. - -(cherry picked from commit e0e21929b7426b9b5bbf5e3747797043801b1151) ---- - doc/ChangeLog | 2 ++ - src/lookups/dsearch.c | 7 +++---- - -diff --git doc/ChangeLog doc/ChangeLog -index de11b4f09..bae9abb85 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -49,6 +49,8 @@ JH/11 Bug 2604: Fix request to cutthrough-deliver when a connection is already - held open for a verify callout. Previously this wan not accounted for - and a corrupt onward SMTP conversation resulted. - -+JH/13 Fix dsearch "subdir" filter to ignore ".". Previously only ".." was -+ excluded, not matching the documentation. - - - Exim version 4.94 -diff --git src/lookups/dsearch.c src/lookups/dsearch.c -index 455273fb1..501293ac0 100644 ---- src/lookups/dsearch.c -+++ src/lookups/dsearch.c -@@ -125,8 +125,7 @@ if ( Ulstat(filename, &statbuf) >= 0 - && S_ISDIR(statbuf.st_mode) - && ( flags & FILTER_DIR - || keystring[0] != '.' -- || keystring[1] != '.' -- || keystring[1] && keystring[2] -+ || keystring[1] && keystring[1] != '.' - ) ) ) ) - { - /* Since the filename exists in the filesystem, we can return a -@@ -135,10 +134,10 @@ if ( Ulstat(filename, &statbuf) >= 0 - return OK; - } - --if (errno == ENOENT) return FAIL; -+if (errno == ENOENT || errno == 0) return FAIL; - - save_errno = errno; --*errmsg = string_sprintf("%s: lstat failed", filename); -+*errmsg = string_sprintf("%s: lstat: %s", filename, strerror(errno)); - errno = save_errno; - return DEFER; - } --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0018-Sqlite-fix-segfault-on-bad-missing-sqlite_dbfile.-Bug-2606 b/mail/exim/files/patch-z0018-Sqlite-fix-segfault-on-bad-missing-sqlite_dbfile.-Bug-2606 deleted file mode 100644 index 61d4d4a6af65..000000000000 --- a/mail/exim/files/patch-z0018-Sqlite-fix-segfault-on-bad-missing-sqlite_dbfile.-Bug-2606 +++ /dev/null @@ -1,59 +0,0 @@ -From 2be77199fc9009ab796ad2d67eed20d8da4773c7 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Sun, 28 Jun 2020 15:24:21 +0100 -Subject: [PATCH 18/26] Sqlite: fix segfault on bad/missing sqlite_dbfile. - Bug 2606 - -(cherry picked from commit 3d0472791a0928963a3f8184fe28479e80d1a47d) ---- - doc/ChangeLog | 3 +++ - src/lookups/sqlite.c | 13 ++++++++++--- - -diff --git doc/ChangeLog doc/ChangeLog -index bae9abb85..8a13bda87 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -52,6 +52,9 @@ JH/11 Bug 2604: Fix request to cutthrough-deliver when a connection is already - JH/13 Fix dsearch "subdir" filter to ignore ".". Previously only ".." was - excluded, not matching the documentation. - -+JH/14 Bug 2606: Fix a segfault in sqlite lookups. When no, or a bad, filename -+ was given for the sqlite_dbfile a trap resulted. -+ - - Exim version 4.94 - ----------------- -diff --git src/lookups/sqlite.c src/lookups/sqlite.c -index dc4439153..1638ea401 100644 ---- src/lookups/sqlite.c -+++ src/lookups/sqlite.c -@@ -24,16 +24,23 @@ sqlite_open(const uschar * filename, uschar ** errmsg) - sqlite3 *db = NULL; - int ret; - --if (!filename || !*filename) filename = sqlite_dbfile; --if (*filename != '/') -+if (!filename || !*filename) -+ { -+ DEBUG(D_lookup) debug_printf_indent("Using sqlite_dbfile: %s\n", sqlite_dbfile); -+ filename = sqlite_dbfile; -+ } -+if (!filename || *filename != '/') - *errmsg = US"absolute file name expected for \"sqlite\" lookup"; - else if ((ret = sqlite3_open(CCS filename, &db)) != 0) - { - *errmsg = (void *)sqlite3_errmsg(db); -+ sqlite3_close(db); -+ db = NULL; - DEBUG(D_lookup) debug_printf_indent("Error opening database: %s\n", *errmsg); - } - --sqlite3_busy_timeout(db, 1000 * sqlite_lock_timeout); -+if (db) -+ sqlite3_busy_timeout(db, 1000 * sqlite_lock_timeout); - return db; - } - --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0019-Taint-fix-ACL-spam-condition-to-permit-tainted-name-argume b/mail/exim/files/patch-z0019-Taint-fix-ACL-spam-condition-to-permit-tainted-name-argume deleted file mode 100644 index e9b93e263ad8..000000000000 --- a/mail/exim/files/patch-z0019-Taint-fix-ACL-spam-condition-to-permit-tainted-name-argume +++ /dev/null @@ -1,52 +0,0 @@ -From 5f3e2ac9f39db5c8ef5a408929c8a5aba957b20f Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Mon, 29 Jun 2020 17:26:36 +0100 -Subject: [PATCH 19/26] Taint: fix ACL "spam" condition, to permit tainted - name arguments. - -Cherry-picked from: 62b2ccce05 ---- - doc/ChangeLog | 4 ++++ - src/spam.c | 5 +---- - -diff --git doc/ChangeLog doc/ChangeLog -index 8a13bda87..6a867c716 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -55,6 +55,10 @@ JH/13 Fix dsearch "subdir" filter to ignore ".". Previously only ".." was - JH/14 Bug 2606: Fix a segfault in sqlite lookups. When no, or a bad, filename - was given for the sqlite_dbfile a trap resulted. - -+JH/15 Fix "spam" ACL condition. Previously, tainted values for the "name" -+ argument resulted in a trap. There is no reason to disallow such; this -+ was a coding error. -+ - - Exim version 4.94 - ----------------- -diff --git src/spam.c src/spam.c -index 5eff1ad5c..63ced4f65 100644 ---- src/spam.c -+++ src/spam.c -@@ -190,7 +190,6 @@ spam(const uschar **listptr) - int sep = 0; - const uschar *list = *listptr; - uschar *user_name; --uschar user_name_buffer[128]; - unsigned long mbox_size; - FILE *mbox_file; - client_conn_ctx spamd_cctx = {.sock = -1}; -@@ -218,9 +217,7 @@ spamd_address_container * sd; - result = 0; - - /* find the username from the option list */ --if ((user_name = string_nextinlist(&list, &sep, -- user_name_buffer, -- sizeof(user_name_buffer))) == NULL) -+if (!(user_name = string_nextinlist(&list, &sep, NULL, 0))) - { - /* no username given, this means no scanning should be done */ - return FAIL; --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0020-Fix-message-reception-clock-usage.-Bug-2615 b/mail/exim/files/patch-z0020-Fix-message-reception-clock-usage.-Bug-2615 deleted file mode 100644 index 68dbd8d23d0d..000000000000 --- a/mail/exim/files/patch-z0020-Fix-message-reception-clock-usage.-Bug-2615 +++ /dev/null @@ -1,158 +0,0 @@ -From cafcab0848e35047a93a8920b5105baf55f8e702 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Tue, 30 Jun 2020 21:16:42 +0100 -Subject: [PATCH 20/26] Fix message-reception clock usage. Bug 2615 - -Broken-by: 6906c131d1 (4.94) -(cherry picked from commit c9bce82e3064126be34d85280d0a7fbf65b3abec) ---- - doc/ChangeLog | 8 ++++++ - src/exim.c | 60 +++++++++++++++++++++++++------------------ - src/functions.h | 1 + - src/receive.c | 2 +- - -diff --git doc/ChangeLog doc/ChangeLog -index 6a867c716..80277f979 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -59,6 +59,14 @@ JH/15 Fix "spam" ACL condition. Previously, tainted values for the "name" - argument resulted in a trap. There is no reason to disallow such; this - was a coding error. - -+JH/16 Bug 2615: Fix pause during message reception, on systems that have been -+ suspended/resumed. The Linux CLOCK_MONOTONIC does not account for time -+ spent suspended, ignoring the Posix definition. Previously we assumed -+ it did and a constant offset from real time could be used as a correction. -+ Change to using the same clock source for the start-of-message and the -+ post-message next-tick-wait. Also change to using CLOCK_BOOTTIME if it -+ exists, just to get a clock slightly more aligned to reality. -+ - - Exim version 4.94 - ----------------- -diff --git src/exim.c src/exim.c -index 6143fe989..dde991065 100644 ---- src/exim.c -+++ src/exim.c -@@ -384,14 +384,20 @@ return 0; - *************************************************/ - - #ifdef _POSIX_MONOTONIC_CLOCK --/* Amount CLOCK_MONOTONIC is behind realtime, at startup. */ -+# ifdef CLOCK_BOOTTIME -+# define EXIM_CLOCKTYPE CLOCK_BOOTTIME -+# else -+# define EXIM_CLOCKTYPE CLOCK_MONOTONIC -+# endif -+ -+/* Amount EXIM_CLOCK is behind realtime, at startup. */ - static struct timespec offset_ts; - - static void - exim_clock_init(void) - { - struct timeval tv; --if (clock_gettime(CLOCK_MONOTONIC, &offset_ts) != 0) return; -+if (clock_gettime(EXIM_CLOCKTYPE, &offset_ts) != 0) return; - (void)gettimeofday(&tv, NULL); - offset_ts.tv_sec = tv.tv_sec - offset_ts.tv_sec; - offset_ts.tv_nsec = tv.tv_usec * 1000 - offset_ts.tv_nsec; -@@ -402,6 +408,29 @@ offset_ts.tv_nsec += 1000*1000*1000; - #endif - - -+void -+exim_gettime(struct timeval * tv) -+{ -+#ifdef _POSIX_MONOTONIC_CLOCK -+struct timespec now_ts; -+ -+if (clock_gettime(EXIM_CLOCKTYPE, &now_ts) == 0) -+ { -+ now_ts.tv_sec += offset_ts.tv_sec; -+ if ((now_ts.tv_nsec += offset_ts.tv_nsec) >= 1000*1000*1000) -+ { -+ now_ts.tv_sec++; -+ now_ts.tv_nsec -= 1000*1000*1000; -+ } -+ tv->tv_sec = now_ts.tv_sec; -+ tv->tv_usec = now_ts.tv_nsec / 1000; -+ } -+else -+#endif -+ (void)gettimeofday(tv, NULL); -+} -+ -+ - /* Exim uses a time + a pid to generate a unique identifier in two places: its - message IDs, and in file names for maildir deliveries. Because some OS now - re-use pids within the same second, sub-second times are now being used. -@@ -428,28 +457,9 @@ exim_wait_tick(struct timeval * tgt_tv, int resolution) - struct timeval now_tv; - long int now_true_usec; - --#ifdef _POSIX_MONOTONIC_CLOCK --struct timespec now_ts; -- --if (clock_gettime(CLOCK_MONOTONIC, &now_ts) == 0) -- { -- now_ts.tv_sec += offset_ts.tv_sec; -- if ((now_ts.tv_nsec += offset_ts.tv_nsec) >= 1000*1000*1000) -- { -- now_ts.tv_sec++; -- now_ts.tv_nsec -= 1000*1000*1000; -- } -- now_tv.tv_sec = now_ts.tv_sec; -- now_true_usec = (now_ts.tv_nsec / (resolution * 1000)) * resolution; -- now_tv.tv_usec = now_true_usec; -- } --else --#endif -- { -- (void)gettimeofday(&now_tv, NULL); -- now_true_usec = now_tv.tv_usec; -- now_tv.tv_usec = (now_true_usec/resolution) * resolution; -- } -+exim_gettime(&now_tv); -+now_true_usec = now_tv.tv_usec; -+now_tv.tv_usec = (now_true_usec/resolution) * resolution; - - while (exim_tvcmp(&now_tv, tgt_tv) <= 0) - { -@@ -1728,7 +1738,7 @@ make quite sure. */ - - setlocale(LC_ALL, "C"); - --/* Get the offset between CLOCK_MONOTONIC and wallclock */ -+/* Get the offset between CLOCK_MONOTONIC/CLOCK_BOOTTIME and wallclock */ - - #ifdef _POSIX_MONOTONIC_CLOCK - exim_clock_init(); -diff --git src/functions.h src/functions.h -index 0050cdeeb..8b17531ed 100644 ---- src/functions.h -+++ src/functions.h -@@ -234,6 +234,7 @@ extern void msg_event_raise(const uschar *, const address_item *); - extern int exim_chown_failure(int, const uschar*, uid_t, gid_t); - extern const uschar * exim_errstr(int); - extern void exim_exit(int) NORETURN; -+extern void exim_gettimg(struct timeval *); - extern void exim_nullstd(void); - extern void exim_setugid(uid_t, gid_t, BOOL, uschar *); - extern void exim_underbar_exit(int) NORETURN; -diff --git src/receive.c src/receive.c -index 0fbd35f82..0db897e9e 100644 ---- src/receive.c -+++ src/receive.c -@@ -1784,7 +1784,7 @@ if (sender_host_address) dmarc_init(); /* initialize libopendmarc */ - ids, and fractions of a second are required. See the comments that precede the - message id creation below. */ - --(void)gettimeofday(&message_id_tv, NULL); -+exim_gettime(&message_id_tv); - - /* For other uses of the received time we can operate with granularity of one - second, and for that we use the global variable received_time. This is for --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0021-typoes b/mail/exim/files/patch-z0021-typoes deleted file mode 100644 index d7de1be5a89f..000000000000 --- a/mail/exim/files/patch-z0021-typoes +++ /dev/null @@ -1,24 +0,0 @@ -From 436c0d208b49421d3d126f7c284bc3130b50ff14 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Fri, 3 Jul 2020 20:35:58 +0100 -Subject: [PATCH 21/26] typoes - ---- - src/functions.h | 2 +- - -diff --git src/functions.h src/functions.h -index 8b17531ed..afe9f1bf4 100644 ---- src/functions.h -+++ src/functions.h -@@ -234,7 +234,7 @@ extern void msg_event_raise(const uschar *, const address_item *); - extern int exim_chown_failure(int, const uschar*, uid_t, gid_t); - extern const uschar * exim_errstr(int); - extern void exim_exit(int) NORETURN; --extern void exim_gettimg(struct timeval *); -+extern void exim_gettime(struct timeval *); - extern void exim_nullstd(void); - extern void exim_setugid(uid_t, gid_t, BOOL, uschar *); - extern void exim_underbar_exit(int) NORETURN; --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0022-Fix-DKIM-signing-to-always-terminate.-Bug-2295 b/mail/exim/files/patch-z0022-Fix-DKIM-signing-to-always-terminate.-Bug-2295 deleted file mode 100644 index 7525937433ae..000000000000 --- a/mail/exim/files/patch-z0022-Fix-DKIM-signing-to-always-terminate.-Bug-2295 +++ /dev/null @@ -1,193 +0,0 @@ -From de99158d2927863a6826c9f5f2c6fa4547326e75 Mon Sep 17 00:00:00 2001 -From: Guillaume Outters <guillaume-exim@outters.eu> -Date: Mon, 6 Jul 2020 22:31:51 +0100 -Subject: [PATCH 22/26] Fix DKIM signing to always ;-terminate. Bug 2295 - -(cherry picked from commit 65fe780259d0009354b5dfc9a4f1b48ad6513db2) ---- - doc/ChangeLog | 5 ++ - src/pdkim/pdkim.c | 116 ++++++++++++++++-------------------------- - -diff --git doc/ChangeLog doc/ChangeLog -index 80277f979..08c6638a9 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -67,6 +67,11 @@ JH/16 Bug 2615: Fix pause during message reception, on systems that have been - post-message next-tick-wait. Also change to using CLOCK_BOOTTIME if it - exists, just to get a clock slightly more aligned to reality. - -+JH/17 Bug 2295: Fix DKIM signing to always semicolon-terminate. Although the -+ RFC says it is optional some validators care. The missing char was not -+ intended but triggered by a line-wrap alignement. Discovery and fix by -+ Guillaume Outters, hacked on by JH. -+ - - Exim version 4.94 - ----------------- -diff --git src/pdkim/pdkim.c src/pdkim/pdkim.c -index 7712409b5..3a6ca4e91 100644 ---- src/pdkim/pdkim.c -+++ src/pdkim/pdkim.c -@@ -1111,14 +1111,14 @@ return string_catn(str, US"\r\n\t", 3); - - /* - * RFC 5322 specifies that header line length SHOULD be no more than 78 -- * lets make it so! - * pdkim_headcat - * -- * returns uschar * (not nul-terminated) -+ * Returns gstring (not nul-terminated) appending to one supplied - * - * col: this int holds and receives column number (octets since last '\n') - * str: partial string to append to -- * pad: padding, split line or space after before or after eg: ";" -+ * pad: padding, split line or space after before or after eg: ";". -+ * Only the initial charater is used. - * intro: - must join to payload eg "h=", usually the tag name - * payload: eg base64 data - long data can be split arbitrarily. - * -@@ -1127,7 +1127,7 @@ return string_catn(str, US"\r\n\t", 3); - * pairs and inside long values. it also always spaces or breaks after the - * "pad" - * -- * no guarantees are made for output given out-of range input. like tag -+ * No guarantees are made for output given out-of range input. like tag - * names longer than 78, or bogus col. Input is assumed to be free of line breaks. - */ - -@@ -1135,92 +1135,64 @@ static gstring * - pdkim_headcat(int * col, gstring * str, - const uschar * pad, const uschar * intro, const uschar * payload) - { --size_t l; -+int len, chomp, padded = 0; - --if (pad) -- { -- l = Ustrlen(pad); -- if (*col + l > 78) -- str = pdkim_hdr_cont(str, col); -- str = string_catn(str, pad, l); -- *col += l; -- } -- --l = (pad?1:0) + (intro?Ustrlen(intro):0); -+/* If we can fit at least the pad at the end of current line, do it now. -+Otherwise, wrap if there is a pad. */ - --if (*col + l > 78) -- { /*can't fit intro - start a new line to make room.*/ -- str = pdkim_hdr_cont(str, col); -- l = intro?Ustrlen(intro):0; -- } -- --l += payload ? Ustrlen(payload):0 ; -- --while (l>77) -- { /* this fragment will not fit on a single line */ -- if (pad) -- { -- str = string_catn(str, US" ", 1); -- *col += 1; -- pad = NULL; /* only want this once */ -- l--; -- } -- -- if (intro) -- { -- size_t sl = Ustrlen(intro); -- -- str = string_catn(str, intro, sl); -- *col += sl; -- l -= sl; -- intro = NULL; /* only want this once */ -- } -- -- if (payload) -+if (pad) -+ if (*col + 1 <= 78) - { -- size_t sl = Ustrlen(payload); -- size_t chomp = *col+sl < 77 ? sl : 78-*col; -- -- str = string_catn(str, payload, chomp); -- *col += chomp; -- payload += chomp; -- l -= chomp-1; -+ str = string_catn(str, pad, 1); -+ (*col)++; -+ pad = NULL; -+ padded = 1; - } -+ else -+ str = pdkim_hdr_cont(str, col); - -- /* the while precondition tells us it didn't fit. */ -- str = pdkim_hdr_cont(str, col); -- } -+/* Special case: if the whole addition does not fit at the end of the current -+line, but could fit on a new line, wrap to give it its full, dedicated line. */ - --if (*col + l > 78) -+len = (pad ? 2 : padded) -+ + (intro ? Ustrlen(intro) : 0) -+ + (payload ? Ustrlen(payload) : 0); -+if (len <= 77 && *col+len > 78) - { - str = pdkim_hdr_cont(str, col); -- pad = NULL; -+ padded = 0; - } - -+/* Either we already dealt with the pad or we know there is room */ -+ - if (pad) - { -+ str = string_catn(str, pad, 1); - str = string_catn(str, US" ", 1); -- *col += 1; -- pad = NULL; -+ *col += 2; - } -- --if (intro) -+else if (padded && *col < 78) - { -- size_t sl = Ustrlen(intro); -- -- str = string_catn(str, intro, sl); -- *col += sl; -- l -= sl; -- intro = NULL; -+ str = string_catn(str, US" ", 1); -+ (*col)++; - } - --if (payload) -- { -- size_t sl = Ustrlen(payload); -+/* Call recursively with intro as payload: it gets the same, special treatment -+(that is, not split if < 78). */ - -- str = string_catn(str, payload, sl); -- *col += sl; -- } -+if (intro) -+ str = pdkim_headcat(col, str, NULL, NULL, intro); -+ -+if (payload) -+ for (len = Ustrlen(payload); len; len -= chomp) -+ { -+ if (*col >= 78) -+ str = pdkim_hdr_cont(str, col); -+ chomp = *col+len > 78 ? 78 - *col : len; -+ str = string_catn(str, payload, chomp); -+ *col += chomp; -+ payload += chomp; -+ } - - return str; - } --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0023-Fix-taint-trap-in-parse_fix_phrase-.-Bug-2617 b/mail/exim/files/patch-z0023-Fix-taint-trap-in-parse_fix_phrase-.-Bug-2617 deleted file mode 100644 index ae3f4de35602..000000000000 --- a/mail/exim/files/patch-z0023-Fix-taint-trap-in-parse_fix_phrase-.-Bug-2617 +++ /dev/null @@ -1,366 +0,0 @@ -From 86ba540670517109809d93cd73716d320a6a0923 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Thu, 9 Jul 2020 15:30:55 +0100 -Subject: [PATCH 23/26] Fix taint trap in parse_fix_phrase(). Bug 2617 - -(cherry picked from commit 3c90bbcdc7cf73298156f7bcd5f5e750e7814e72) ---- - doc/ChangeLog | 6 +++ - src/acl.c | 3 +- - src/exim.c | 3 +- - src/expand.c | 5 +-- - src/functions.h | 4 +- - src/parse.c | 89 +++++++++++++++---------------------------- - src/rewrite.c | 9 +---- - src/sieve.c | 17 ++------- - -diff --git doc/ChangeLog doc/ChangeLog -index 08c6638a9..a1f39459e 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -72,6 +72,12 @@ JH/17 Bug 2295: Fix DKIM signing to always semicolon-terminate. Although the - intended but triggered by a line-wrap alignement. Discovery and fix by - Guillaume Outters, hacked on by JH. - -+JH/18 Bug 2617: Fix a taint trap in parse_fix_phrase(). Previously when the -+ name being quoted was tainted a trap would be taken. Fix by using -+ dynamicaly created buffers. The routine could have been called by a -+ rewrite with the "h" flag, by using the "-F" command-line option, or -+ by using a "name=" option on a control=submission ACL modifier. -+ - - Exim version 4.94 - ----------------- -diff --git src/acl.c src/acl.c -index 62cb68561..105b1b473 100644 ---- src/acl.c -+++ src/acl.c -@@ -3199,8 +3199,7 @@ for (; cb; cb = cb->next) - { - const uschar *pp = p + 6; - while (*pp) pp++; -- submission_name = string_copy(parse_fix_phrase(p+6, pp-p-6, -- big_buffer, big_buffer_size)); -+ submission_name = parse_fix_phrase(p+6, pp-p-6); - p = pp; - } - else break; -diff --git src/exim.c src/exim.c -index dde991065..ac0ff5523 100644 ---- src/exim.c -+++ src/exim.c -@@ -4769,8 +4769,7 @@ if (originator_login == NULL || f.running_in_test_harness) - /* Ensure that the user name is in a suitable form for use as a "phrase" in an - RFC822 address.*/ - --originator_name = string_copy(parse_fix_phrase(originator_name, -- Ustrlen(originator_name), big_buffer, big_buffer_size)); -+originator_name = parse_fix_phrase(originator_name, Ustrlen(originator_name)); - - /* If a message is created by this call of Exim, the uid/gid of its originator - are those of the caller. These values are overridden if an existing message is -diff --git src/expand.c src/expand.c -index 6ed22c14d..791222324 100644 ---- src/expand.c -+++ src/expand.c -@@ -7571,13 +7571,10 @@ while (*s != 0) - prescribed by the RFC, if there are characters that need to be encoded */ - - case EOP_RFC2047: -- { -- uschar buffer[2048]; - yield = string_cat(yield, - parse_quote_2047(sub, Ustrlen(sub), headers_charset, -- buffer, sizeof(buffer), FALSE)); -+ FALSE)); - continue; -- } - - /* RFC 2047 decode */ - -diff --git src/functions.h src/functions.h -index afe9f1bf4..f4d1622dc 100644 ---- src/functions.h -+++ src/functions.h -@@ -366,9 +366,9 @@ extern int parse_forward_list(uschar *, int, address_item **, uschar **, - const uschar *, uschar *, error_block **); - extern uschar *parse_find_address_end(uschar *, BOOL); - extern uschar *parse_find_at(uschar *); --extern const uschar *parse_fix_phrase(const uschar *, int, uschar *, int); -+extern const uschar *parse_fix_phrase(const uschar *, int); - extern uschar *parse_message_id(uschar *, uschar **, uschar **); --extern const uschar *parse_quote_2047(const uschar *, int, uschar *, uschar *, int, BOOL); -+extern const uschar *parse_quote_2047(const uschar *, int, uschar *, BOOL); - extern uschar *parse_date_time(uschar *str, time_t *t); - extern int vaguely_random_number(int); - #ifndef DISABLE_TLS -diff --git src/parse.c src/parse.c -index e3b471f1a..3ea758ac9 100644 ---- src/parse.c -+++ src/parse.c -@@ -843,8 +843,7 @@ return NULL; - - /* This function is used for quoting text in headers according to RFC 2047. - If the only characters that strictly need quoting are spaces, we return the --original string, unmodified. If a quoted string is too long for the buffer, it --is truncated. (This shouldn't happen: this is normally handling short strings.) -+original string, unmodified. - - Hmmph. As always, things get perverted for other uses. This function was - originally for the "phrase" part of addresses. Now it is being used for much -@@ -856,77 +855,57 @@ Arguments: - chars - len the length of the string - charset the name of the character set; NULL => iso-8859-1 -- buffer the buffer to put the answer in -- buffer_size the size of the buffer - fold if TRUE, a newline is inserted before the separating space when - more than one encoded-word is generated - - Returns: pointer to the original string, if no quoting needed, or -- pointer to buffer containing the quoted string, or -- a pointer to "String too long" if the buffer can't even hold -- the introduction -+ pointer to allocated memory containing the quoted string - */ - - const uschar * --parse_quote_2047(const uschar *string, int len, uschar *charset, uschar *buffer, -- int buffer_size, BOOL fold) -+parse_quote_2047(const uschar *string, int len, uschar *charset, BOOL fold) - { --const uschar *s = string; --uschar *p, *t; --int hlen; -+const uschar * s = string; -+int hlen, l; - BOOL coded = FALSE; - BOOL first_byte = FALSE; -+gstring * g = -+ string_fmt_append(NULL, "=?%s?Q?", charset ? charset : US"iso-8859-1"); - --if (!charset) charset = US"iso-8859-1"; -+hlen = l = g->ptr; - --/* We don't expect this to fail! */ -- --if (!string_format(buffer, buffer_size, "=?%s?Q?", charset)) -- return US"String too long"; -- --hlen = Ustrlen(buffer); --t = buffer + hlen; --p = buffer; -- --for (; len > 0; len--) -+for (s = string; len > 0; s++, len--) - { -- int ch = *s++; -- if (t > buffer + buffer_size - hlen - 8) break; -+ int ch = *s; - -- if ((t - p > 67) && !first_byte) -+ if (g->ptr - l > 67 && !first_byte) - { -- *t++ = '?'; -- *t++ = '='; -- if (fold) *t++ = '\n'; -- *t++ = ' '; -- p = t; -- Ustrncpy(p, buffer, hlen); -- t += hlen; -+ g = fold ? string_catn(g, US"?=\n ", 4) : string_catn(g, US"?= ", 3); -+ l = g->ptr; -+ g = string_catn(g, g->s, hlen); - } - -- if (ch < 33 || ch > 126 || -- Ustrchr("?=()<>@,;:\\\".[]_", ch) != NULL) -+ if ( ch < 33 || ch > 126 -+ || Ustrchr("?=()<>@,;:\\\".[]_", ch) != NULL) - { - if (ch == ' ') - { -- *t++ = '_'; -+ g = string_catn(g, US"_", 1); - first_byte = FALSE; - } - else - { -- t += sprintf(CS t, "=%02X", ch); -+ g = string_fmt_append(g, "=%02X", ch); - coded = TRUE; - first_byte = !first_byte; - } - } -- else { *t++ = ch; first_byte = FALSE; } -+ else -+ { g = string_catn(g, s, 1); first_byte = FALSE; } - } - --*t++ = '?'; --*t++ = '='; --*t = 0; -- --return coded ? buffer : string; -+g = string_catn(g, US"?=", 2); -+return coded ? string_from_gstring(g) : string; - } - - -@@ -969,32 +948,25 @@ August 2000: Additional code added: - We *could* use this for all cases, getting rid of the messy original code, - but leave it for now. It would complicate simple cases like "John Q. Smith". - --The result is passed back in the buffer; it is usually going to be added to --some other string. In order to be sure there is going to be no overflow, --restrict the length of the input to 1/4 of the buffer size - this allows for --every single character to be quoted or encoded without overflowing, and that --wouldn't happen because of amalgamation. If the phrase is too long, return a --fixed string. -+The result is passed back in allocated memory. - - Arguments: - phrase an RFC822 phrase - len the length of the phrase -- buffer a buffer to put the result in -- buffer_size the size of the buffer - - Returns: the fixed RFC822 phrase - */ - - const uschar * --parse_fix_phrase(const uschar *phrase, int len, uschar *buffer, int buffer_size) -+parse_fix_phrase(const uschar *phrase, int len) - { - int ch, i; - BOOL quoted = FALSE; - const uschar *s, *end; -+uschar * buffer; - uschar *t, *yield; - - while (len > 0 && isspace(*phrase)) { phrase++; len--; } --if (len > buffer_size/4) return US"Name too long"; - - /* See if there are any non-printing characters, and if so, use the RFC 2047 - encoding for the whole thing. */ -@@ -1002,11 +974,13 @@ encoding for the whole thing. */ - for (i = 0, s = phrase; i < len; i++, s++) - if ((*s < 32 && *s != '\t') || *s > 126) break; - --if (i < len) return parse_quote_2047(phrase, len, headers_charset, buffer, -- buffer_size, FALSE); -+if (i < len) -+ return parse_quote_2047(phrase, len, headers_charset, FALSE); - - /* No non-printers; use the RFC 822 quoting rules */ - -+buffer = store_get(len*4, is_tainted(phrase)); -+ - s = phrase; - end = s + len; - yield = t = buffer + 1; -@@ -1173,6 +1147,7 @@ while (s < end) - } - - *t = 0; -+store_release_above(t+1); - return yield; - } - -@@ -2102,7 +2077,6 @@ int main(void) - { - int start, end, domain; - uschar buffer[1024]; --uschar outbuff[1024]; - - big_buffer = store_malloc(big_buffer_size); - -@@ -2115,8 +2089,7 @@ while (Ufgets(buffer, sizeof(buffer), stdin) != NULL) - { - buffer[Ustrlen(buffer)-1] = 0; - if (buffer[0] == 0) break; -- printf("%s\n", CS parse_fix_phrase(buffer, Ustrlen(buffer), outbuff, -- sizeof(outbuff))); -+ printf("%s\n", CS parse_fix_phrase(buffer, Ustrlen(buffer))); - } - - printf("Testing parse_extract_address without group syntax and without UTF-8\n"); -diff --git src/rewrite.c src/rewrite.c -index f942bec05..7bff8a273 100644 ---- src/rewrite.c -+++ src/rewrite.c -@@ -292,16 +292,11 @@ for (rewrite_rule * rule = rewrite_rules; - uschar *p1 = new + start - 1; - uschar *p2 = new + end + 1; - const uschar *pf1, *pf2; -- uschar buff1[256], buff2[256]; - - while (p1 > new && p1[-1] == ' ') p1--; -- pf1 = parse_fix_phrase(new, p1 - new, buff1, sizeof(buff1)); -+ pf1 = parse_fix_phrase(new, p1 - new); - while (*p2 == ' ') p2++; -- pf2 = parse_fix_phrase(p2, Ustrlen(p2), buff2, sizeof(buff2)); -- -- /* Note that pf1 and pf2 are NOT necessarily buff1 and buff2. For -- a non-RFC 2047 phrase that does not need to be RFC 2822 quoted, they -- will be buff1+1 and buff2+1. */ -+ pf2 = parse_fix_phrase(p2, Ustrlen(p2)); - - start = Ustrlen(pf1) + start + new - p1; - end = start + Ustrlen(newparsed); -diff --git src/sieve.c src/sieve.c -index 18aa3e609..2038f336b 100644 ---- src/sieve.c -+++ src/sieve.c -@@ -3087,11 +3087,8 @@ while (*filter->pc) - if ((pid = child_open_exim2(&fd, envelope_from, envelope_from, - US"sieve-notify")) >= 1) - { -- FILE *f; -- uschar *buffer; -- int buffer_capacity; -+ FILE * f = fdopen(fd, "wb"); - -- f = fdopen(fd, "wb"); - fprintf(f,"From: %s\n", from.length == -1 - ? expand_string(US"$local_part_prefix$local_part$local_part_suffix@$domain") - : from.character); -@@ -3104,12 +3101,9 @@ while (*filter->pc) - message.character=US"Notification"; - message.length=Ustrlen(message.character); - } -- /* Allocation is larger than necessary, but enough even for split MIME words */ -- buffer_capacity = 32 + 4*message.length; -- buffer=store_get(buffer_capacity, TRUE); - if (message.length != -1) - fprintf(f, "Subject: %s\n", parse_quote_2047(message.character, -- message.length, US"utf-8", buffer, buffer_capacity, TRUE)); -+ message.length, US"utf-8", TRUE)); - fprintf(f,"\n"); - if (body.length>0) fprintf(f,"%s\n",body.character); - fflush(f); -@@ -3263,8 +3257,6 @@ while (*filter->pc) - if (exec) - { - address_item *addr; -- uschar *buffer; -- int buffer_capacity; - md5 base; - uschar digest[16]; - uschar hexdigest[33]; -@@ -3342,11 +3334,8 @@ while (*filter->pc) - addr->reply->from = expand_string(US"$local_part@$domain"); - else - addr->reply->from = from.character; -- /* Allocation is larger than necessary, but enough even for split MIME words */ -- buffer_capacity=32+4*subject.length; -- buffer = store_get(buffer_capacity, is_tainted(subject.character)); - /* deconst cast safe as we pass in a non-const item */ -- addr->reply->subject = US parse_quote_2047(subject.character, subject.length, US"utf-8", buffer, buffer_capacity, TRUE); -+ addr->reply->subject = US parse_quote_2047(subject.character, subject.length, US"utf-8", TRUE); - addr->reply->oncelog = string_from_gstring(once); - addr->reply->once_repeat=days*86400; - --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0024-Taint-fix-ACL-spam-condition-to-permit-tainted-name-argume b/mail/exim/files/patch-z0024-Taint-fix-ACL-spam-condition-to-permit-tainted-name-argume deleted file mode 100644 index 0c7e83bbb250..000000000000 --- a/mail/exim/files/patch-z0024-Taint-fix-ACL-spam-condition-to-permit-tainted-name-argume +++ /dev/null @@ -1,74 +0,0 @@ -From 9681a2140b43cfc028e61b4e7ffb13539cecffe5 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Mon, 13 Jul 2020 13:46:14 +0100 -Subject: [PATCH 24/26] Taint: fix ACL "spam" condition, to permit tainted - name arguments - -Follow-on from: 62b2ccce05 - -(cherry picked from commit 532800c8bf0e4bc2c27739477e70e0d7eef7df21) ---- - doc/ChangeLog | 6 +++--- - src/spam.c | 15 +++++++-------- - -diff --git doc/ChangeLog doc/ChangeLog -index a1f39459e..aaea04caf 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -55,9 +55,9 @@ JH/13 Fix dsearch "subdir" filter to ignore ".". Previously only ".." was - JH/14 Bug 2606: Fix a segfault in sqlite lookups. When no, or a bad, filename - was given for the sqlite_dbfile a trap resulted. - --JH/15 Fix "spam" ACL condition. Previously, tainted values for the "name" -- argument resulted in a trap. There is no reason to disallow such; this -- was a coding error. -+JH/15 Bug 2620: Fix "spam" ACL condition. Previously, tainted values for the -+ "name" argument resulted in a trap. There is no reason to disallow such; -+ this was a coding error. - - JH/16 Bug 2615: Fix pause during message reception, on systems that have been - suspended/resumed. The Linux CLOCK_MONOTONIC does not account for time -diff --git src/spam.c src/spam.c -index 63ced4f65..340f8b92f 100644 ---- src/spam.c -+++ src/spam.c -@@ -18,7 +18,7 @@ uschar spam_score_int_buffer[16]; - uschar spam_bar_buffer[128]; - uschar spam_action_buffer[32]; - uschar spam_report_buffer[32600]; --uschar prev_user_name[128] = ""; -+uschar * prev_user_name = NULL; - int spam_ok = 0; - int spam_rc = 0; - uschar *prev_spamd_address_work = NULL; -@@ -393,13 +393,12 @@ if (sd->is_rspamd) - } - else - { /* spamassassin variant */ -- (void)string_format(spamd_buffer, -- sizeof(spamd_buffer), -- "REPORT SPAMC/1.2\r\nUser: %s\r\nContent-length: %ld\r\n\r\n", -- user_name, -- mbox_size); -+ int n; -+ uschar * s = string_sprintf( -+ "REPORT SPAMC/1.2\r\nUser: %s\r\nContent-length: %ld\r\n\r\n%n", -+ user_name, mbox_size, &n); - /* send our request */ -- wrote = send(spamd_cctx.sock, spamd_buffer, Ustrlen(spamd_buffer), 0); -+ wrote = send(spamd_cctx.sock, s, n, 0); - } - - if (wrote == -1) -@@ -630,7 +629,7 @@ if (spamd_address_work != spamd_address) - prev_spamd_address_work = string_copy(spamd_address_work); - - /* remember user name and "been here" for it */ --Ustrcpy(prev_user_name, user_name); -+prev_user_name = user_name; - spam_ok = 1; - - return override --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0025-Fix-debug_print_socket b/mail/exim/files/patch-z0025-Fix-debug_print_socket deleted file mode 100644 index 5db4662f48cf..000000000000 --- a/mail/exim/files/patch-z0025-Fix-debug_print_socket +++ /dev/null @@ -1,79 +0,0 @@ -From 81cc39a7f5c17099f93b5c611bde5f58daaab71b Mon Sep 17 00:00:00 2001 -From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> -Date: Thu, 16 Jul 2020 23:45:55 +0200 -Subject: [PATCH 25/26] Fix debug_print_socket() - -debug_print_socket() crashed on AF_UNIX sockets ---- - src/debug.c | 34 +++++++++++++++++++--------------- - -diff --git src/debug.c src/debug.c -index 3a7d6a6f5..acc723a29 100644 ---- src/debug.c -+++ src/debug.c -@@ -328,20 +328,21 @@ if (fstat(fd, &s) == 0 && (s.st_mode & S_IFMT) == S_IFSOCK) - gstring * g = NULL; - int val; - socklen_t vlen = sizeof(val); -- struct sockaddr a; -+ struct sockaddr_storage a; - socklen_t alen = sizeof(a); - struct sockaddr_in * sinp = (struct sockaddr_in *)&a; - struct sockaddr_in6 * sin6p = (struct sockaddr_in6 *)&a; -- struct sockaddr_un * sa_unp ; (struct sockaddr_un *)&a; -+ struct sockaddr_un * sunp = (struct sockaddr_un *)&a; - -- if (getsockname(fd, &a, &alen) == 0) -- switch (sinp->sin_family) -+ if (getsockname(fd, (struct sockaddr*)&a, &alen) == 0) -+ switch (a.ss_family) - { - case AF_INET: - g = string_cat(g, US" domain AF_INET"); - g = string_fmt_append(g, " lcl [%s]:%u", - inet_ntoa(sinp->sin_addr), ntohs(sinp->sin_port)); -- if (getpeername(fd, &a, &alen) == 0) -+ alen = sizeof(*sinp); -+ if (getpeername(fd, sinp, &alen) == 0) - g = string_fmt_append(g, " rmt [%s]:%u", - inet_ntoa(sinp->sin_addr), ntohs(sinp->sin_port)); - break; -@@ -352,22 +353,25 @@ if (fstat(fd, &s) == 0 && (s.st_mode & S_IFMT) == S_IFSOCK) - g = string_fmt_append(g, " lcl [%s]:%u", - inet_ntop(AF_INET6, &sin6p->sin6_addr, CS buf, sizeof(buf)), - ntohs(sin6p->sin6_port)); -- if (getpeername(fd, &a, &alen) == 0) -+ alen = sizeof(*sin6p); -+ if (getpeername(fd, sin6p, &alen) == 0) - g = string_fmt_append(g, " rmt [%s]:%u", - inet_ntop(AF_INET6, &sin6p->sin6_addr, CS buf, sizeof(buf)), - ntohs(sin6p->sin6_port)); - break; - } - case AF_UNIX: -- g = string_cat(g, US" domain AF_UNIX"); -- g = string_fmt_append(g, " lcl %s%s", -- sa_unp->sun_path[0] ? US"" : US"@", -- sa_unp->sun_path[0] ? sa_unp->sun_path : sa_unp->sun_path+1); -- if (getpeername(fd, &a, &alen) == 0) -- g = string_fmt_append(g, " rmt %s%s", -- sa_unp->sun_path[0] ? US"" : US"@", -- sa_unp->sun_path[0] ? sa_unp->sun_path : sa_unp->sun_path+1); -- break; -+ g = string_cat(g, US"domain AF_UNIX"); -+ if (alen > sizeof(sa_family_t)) /* not unix(7) "unnamed socket" */ -+ g = string_fmt_append(g, " lcl %s%s", -+ sunp->sun_path[0] ? US"" : US"@", -+ sunp->sun_path[0] ? sunp->sun_path : sunp->sun_path+1); -+ alen = sizeof(*sunp); -+ if (getpeername(fd, sunp, &alen) == 0) -+ g = string_fmt_append(g, " rmt %s%s", -+ sunp->sun_path[0] ? US"" : US"@", -+ sunp->sun_path[0] ? sunp->sun_path : sunp->sun_path+1); -+ break; - default: - g = string_fmt_append(g, " domain %u", sinp->sin_family); - break; --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0026-debug_print_socket-output-formatting b/mail/exim/files/patch-z0026-debug_print_socket-output-formatting deleted file mode 100644 index d99b4c66a3ca..000000000000 --- a/mail/exim/files/patch-z0026-debug_print_socket-output-formatting +++ /dev/null @@ -1,51 +0,0 @@ -From 73b748711caf8a4b18dd1c0d7c662b5d57798dfe Mon Sep 17 00:00:00 2001 -From: "Heiko Schlittermann (HS12-RIPE)" <hs@schlittermann.de> -Date: Thu, 16 Jul 2020 23:53:27 +0200 -Subject: [PATCH 26/26] debug_print_socket(): output formatting - ---- - src/debug.c | 8 ++++---- - -diff --git src/debug.c src/debug.c -index acc723a29..6d6132e39 100644 ---- src/debug.c -+++ src/debug.c -@@ -338,7 +338,7 @@ if (fstat(fd, &s) == 0 && (s.st_mode & S_IFMT) == S_IFSOCK) - switch (a.ss_family) - { - case AF_INET: -- g = string_cat(g, US" domain AF_INET"); -+ g = string_cat(g, US"domain AF_INET"); - g = string_fmt_append(g, " lcl [%s]:%u", - inet_ntoa(sinp->sin_addr), ntohs(sinp->sin_port)); - alen = sizeof(*sinp); -@@ -349,7 +349,7 @@ if (fstat(fd, &s) == 0 && (s.st_mode & S_IFMT) == S_IFSOCK) - case AF_INET6: - { - uschar buf[46]; -- g = string_cat(g, US" domain AF_INET6"); -+ g = string_cat(g, US"domain AF_INET6"); - g = string_fmt_append(g, " lcl [%s]:%u", - inet_ntop(AF_INET6, &sin6p->sin6_addr, CS buf, sizeof(buf)), - ntohs(sin6p->sin6_port)); -@@ -373,7 +373,7 @@ if (fstat(fd, &s) == 0 && (s.st_mode & S_IFMT) == S_IFSOCK) - sunp->sun_path[0] ? sunp->sun_path : sunp->sun_path+1); - break; - default: -- g = string_fmt_append(g, " domain %u", sinp->sin_family); -+ g = string_fmt_append(g, "domain %u", sinp->sin_family); - break; - } - if (getsockopt(fd, SOL_SOCKET, SO_TYPE, &val, &vlen) == 0) -@@ -388,7 +388,7 @@ if (fstat(fd, &s) == 0 && (s.st_mode & S_IFMT) == S_IFSOCK) - { - struct protoent * p = getprotobynumber(val); - g = p -- ? string_fmt_append(g, " proto %s\n", p->p_name) -+ ? string_fmt_append(g, " proto %s", p->p_name) - : string_fmt_append(g, " proto %d", val); - } - #endif --- -2.24.3 (Apple Git-128) - diff --git a/mail/exim/files/patch-z0027-Fix-spelling-of-local_part_data-in-docs-and-debug-output b/mail/exim/files/patch-z0027-Fix-spelling-of-local_part_data-in-docs-and-debug-output deleted file mode 100644 index 40ef6ffc9eb5..000000000000 --- a/mail/exim/files/patch-z0027-Fix-spelling-of-local_part_data-in-docs-and-debug-output +++ /dev/null @@ -1,54 +0,0 @@ -From d08a4ba2c5216195c107b123842da17bc1b0559f Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Sun, 9 Aug 2020 01:38:00 +0100 -Subject: [PATCH 27/37] Fix spelling of local_part_data in docs and debug - output - -(cherry picked from commit ccec2d82e2fda6d764f6cd1a9dd21c4f6285b614) ---- - doc/ChangeLog | 2 +- - doc/NewStuff | 2 +- - src/routers/rf_queue_add.c | 2 +- - -diff --git doc/ChangeLog doc/ChangeLog -index aaea04caf..703f4b9ee 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -6700,7 +6700,7 @@ Exim version 4.31 - same list, then the first domain was re-checked, the value of $domain_data - after the final check could be wrong. In particular, if the second check - failed, it could be set empty. This bug probably also applied to -- $localpart_data. -+ $local_part_data. - - 41. The strip_trailing_dot option was not being applied to the address given - with the -f command-line option. -diff --git doc/NewStuff doc/NewStuff -index 43e170e11..16dec8808 100644 ---- doc/NewStuff -+++ doc/NewStuff -@@ -57,7 +57,7 @@ Version 4.94 - 16. An option on all single-key lookups, to return (on a hit) a de-tainted - version of the lookup key rather than the looked-up data. - --17. $domain_data and $localpart_data are now set by all list-match successes. -+17. $domain_data and $local_part_data are now set by all list-match successes. - Previously only list items that performed lookups did so. - Also, matching list items that are tail-match or RE-match now set the - numeric variables $0 (etc) in the same way os other RE matches. -diff --git src/routers/rf_queue_add.c src/routers/rf_queue_add.c -index 938eee30a..4dab60dfe 100644 ---- src/routers/rf_queue_add.c -+++ src/routers/rf_queue_add.c -@@ -98,7 +98,7 @@ DEBUG(D_route) - " errors_to=%s\n", - addr->transport ? addr->transport->name : US"<unset>", - addr->local_part, addr->domain, addr->prop.errors_address); -- debug_printf(" domain_data=%s localpart_data=%s\n", addr->prop.domain_data, -+ debug_printf(" domain_data=%s local_part_data=%s\n", addr->prop.domain_data, - addr->prop.localpart_data); - } - --- -2.28.0 - diff --git a/mail/exim/files/patch-z0028-Fix-readsocket-eol-replacement.-Bug-2630 b/mail/exim/files/patch-z0028-Fix-readsocket-eol-replacement.-Bug-2630 deleted file mode 100644 index d8c3e5b06bf0..000000000000 --- a/mail/exim/files/patch-z0028-Fix-readsocket-eol-replacement.-Bug-2630 +++ /dev/null @@ -1,216 +0,0 @@ -From 18a352ae8a799bb7be3a03b14bbf3ce9e0ba4945 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Fri, 14 Aug 2020 13:09:53 +0100 -Subject: [PATCH 28/37] Fix ${readsocket } eol-replacement. Bug 2630 - -(cherry picked from commit 7f83b348ccf4cd815e9758ab9ca1012e66324e9d) ---- - doc/ChangeLog | 4 ++++ - src/expand.c | 11 +++++++---- - src/functions.h | 2 +- - src/lookups/readsock.c | 6 ++++-- - src/macros.h | 6 ++++-- - src/readconf.c | 4 ++-- - src/string.c | 30 +++++++++++++++++----------- - -diff --git doc/ChangeLog doc/ChangeLog -index 703f4b9ee..2d2dc1f9f 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -78,6 +78,10 @@ JH/18 Bug 2617: Fix a taint trap in parse_fix_phrase(). Previously when the - rewrite with the "h" flag, by using the "-F" command-line option, or - by using a "name=" option on a control=submission ACL modifier. - -+JH/21 Bug 2630: Fix eol-replacement string for the ${readsocket } expansion. -+ Previously when a whitespace character was specified it was not inserted -+ after removing the newline. -+ - - Exim version 4.94 - ----------------- -diff --git src/expand.c src/expand.c -index 791222324..bb9fd79ef 100644 ---- src/expand.c -+++ src/expand.c -@@ -4920,7 +4920,7 @@ while (*s != 0) - { - expand_string_message = - string_sprintf("lookup of \"%s\" gave DEFER: %s", -- string_printing2(key, FALSE), search_error_message); -+ string_printing2(key, SP_TAB), search_error_message); - goto EXPAND_FAILED; - } - if (expand_setup > 0) expand_nmax = expand_setup; -@@ -5334,11 +5334,14 @@ while (*s != 0) - while ((item = string_nextinlist(&list, &sep, NULL, 0))) - g = string_append_listele(g, ',', item); - -- /* possibly plus an EOL string */ -+ /* possibly plus an EOL string. Process with escapes, to protect -+ from list-processing. The only current user of eol= in search -+ options is the readsock expansion. */ -+ - if (sub_arg[3] && *sub_arg[3]) - g = string_append_listele(g, ',', -- string_sprintf("eol=%s", sub_arg[3])); -- -+ string_sprintf("eol=%s", -+ string_printing2(sub_arg[3], SP_TAB|SP_SPACE))); - } - - /* Gat a (possibly cached) handle for the connection */ -diff --git src/functions.h src/functions.h -index f4d1622dc..51bb17a09 100644 ---- src/functions.h -+++ src/functions.h -@@ -529,7 +529,7 @@ extern int string_is_ip_address(const uschar *, int *); - #ifdef SUPPORT_I18N - extern BOOL string_is_utf8(const uschar *); - #endif --extern const uschar *string_printing2(const uschar *, BOOL); -+extern const uschar *string_printing2(const uschar *, int); - extern uschar *string_split_message(uschar *); - extern uschar *string_unprinting(uschar *); - #ifdef SUPPORT_I18N -diff --git src/lookups/readsock.c src/lookups/readsock.c -index c2088b7a5..cfc9b4ad8 100644 ---- src/lookups/readsock.c -+++ src/lookups/readsock.c -@@ -186,7 +186,9 @@ FILE * fp; - gstring * yield; - int ret = DEFER; - --DEBUG(D_lookup) debug_printf_indent("readsock: file=\"%s\" key=\"%s\" len=%d opts=\"%s\"\n", filename, keystring, length, opts); -+DEBUG(D_lookup) -+ debug_printf_indent("readsock: file=\"%s\" key=\"%s\" len=%d opts=\"%s\"\n", -+ filename, keystring, length, opts); - - /* Parse options */ - -@@ -200,7 +202,7 @@ if (opts) for (uschar * s; s = string_nextinlist(&opts, &sep, NULL, 0); ) - lf.do_tls = TRUE; - #endif - else if (Ustrncmp(s, "eol=", 4) == 0) -- eol = s + 4; -+ eol = string_unprinting(s + 4); - else if (Ustrcmp(s, "cache=yes") == 0) - lf.cache = TRUE; - else if (Ustrcmp(s, "send=no") == 0) -diff --git src/macros.h src/macros.h -index a507bbf83..2378773cb 100644 ---- src/macros.h -+++ src/macros.h -@@ -41,9 +41,11 @@ manipulate them. */ - - - /* For almost all calls to convert things to printing characters, we want to --allow tabs. A macro just makes life a bit easier. */ -+allow tabs & spaces. A macro just makes life a bit easier. */ - --#define string_printing(s) string_printing2((s), TRUE) -+#define string_printing(s) string_printing2((s), 0) -+#define SP_TAB BIT(0) -+#define SP_SPACE BIT(1) - - - /* We need a special return code for "no recipients and failed to send an error -diff --git src/readconf.c src/readconf.c -index 0d0769c88..948fa2403 100644 ---- src/readconf.c -+++ src/readconf.c -@@ -1546,7 +1546,7 @@ if (flags & opt_fn_print) - { - if (flags & opt_fn_print_label) printf("%s = ", name); - printf("%s\n", smtp_receive_timeout_s -- ? string_printing2(smtp_receive_timeout_s, FALSE) -+ ? string_printing2(smtp_receive_timeout_s, SP_TAB) - : readconf_printtime(smtp_receive_timeout)); - } - else if (*str == '$') -@@ -2463,7 +2463,7 @@ switch(ol->type & opt_mask) - case opt_rewrite: /* Show the text value */ - s = *(USS value); - if (!no_labels) printf("%s = ", name); -- printf("%s\n", s ? string_printing2(s, FALSE) : US""); -+ printf("%s\n", s ? string_printing2(s, SP_TAB) : US""); - break; - - case opt_int: -diff --git src/string.c src/string.c -index 5acee1b00..f91a6a428 100644 ---- src/string.c -+++ src/string.c -@@ -281,17 +281,17 @@ return ch; - /* This function is called for critical strings. It checks for any - non-printing characters, and if any are found, it makes a new copy - of the string with suitable escape sequences. It is most often called by the --macro string_printing(), which sets allow_tab TRUE. -+macro string_printing(), which sets flags to 0. - - Arguments: - s the input string -- allow_tab TRUE to allow tab as a printing character -+ flags Bit 0: convert tabs. Bit 1: convert spaces. - - Returns: string with non-printers encoded as printing sequences - */ - - const uschar * --string_printing2(const uschar *s, BOOL allow_tab) -+string_printing2(const uschar *s, int flags) - { - int nonprintcount = 0; - int length = 0; -@@ -301,7 +301,10 @@ uschar *ss, *tt; - while (*t != 0) - { - int c = *t++; -- if (!mac_isprint(c) || (!allow_tab && c == '\t')) nonprintcount++; -+ if ( !mac_isprint(c) -+ || flags & SP_TAB && c == '\t' -+ || flags & SP_SPACE && c == ' ' -+ ) nonprintcount++; - length++; - } - -@@ -310,17 +313,19 @@ if (nonprintcount == 0) return s; - /* Get a new block of store guaranteed big enough to hold the - expanded string. */ - --ss = store_get(length + nonprintcount * 3 + 1, is_tainted(s)); -+tt = ss = store_get(length + nonprintcount * 3 + 1, is_tainted(s)); - - /* Copy everything, escaping non printers. */ - --t = s; --tt = ss; -- --while (*t != 0) -+for (t = s; *t; ) - { - int c = *t; -- if (mac_isprint(c) && (allow_tab || c != '\t')) *tt++ = *t++; else -+ if ( mac_isprint(c) -+ && (!(flags & SP_TAB) || c != '\t') -+ && (!(flags & SP_SPACE) || c != ' ') -+ ) -+ *tt++ = *t++; -+ else - { - *tt++ = '\\'; - switch (*t) -@@ -947,7 +952,10 @@ else - s = ss; - if (!*s || *++s != sep || sep_is_special) break; - } -- while (g->ptr > 0 && isspace(g->s[g->ptr-1])) g->ptr--; -+ /* while (g->ptr > 0 && isspace(g->s[g->ptr-1])) g->ptr--; */ -+ while ( g->ptr > 0 && isspace(g->s[g->ptr-1]) -+ && (g->ptr == 1 || g->s[g->ptr-2] != '\\') ) -+ g->ptr--; - buffer = string_from_gstring(g); - gstring_release_unused(g); - } --- -2.28.0 - diff --git a/mail/exim/files/patch-z0029-Taint-fix-off-by-one-in-is_tainted-.-Bug-2634 b/mail/exim/files/patch-z0029-Taint-fix-off-by-one-in-is_tainted-.-Bug-2634 deleted file mode 100644 index 8af885bd35a1..000000000000 --- a/mail/exim/files/patch-z0029-Taint-fix-off-by-one-in-is_tainted-.-Bug-2634 +++ /dev/null @@ -1,51 +0,0 @@ -From d2671b04d025dee3b8311d2d83e0a0342c670f52 Mon Sep 17 00:00:00 2001 -From: Gavan <gavan@coolfactor.org> -Date: Fri, 21 Aug 2020 15:46:01 +0100 -Subject: [PATCH 29/37] Taint: fix off-by-one in is_tainted(). Bug 2634 - -(cherry picked from commit e0ae68c8ee6788508da4989ee0d6fcbaf40c7b97) ---- - doc/ChangeLog | 5 +++++ - src/store.c | 4 ++-- - 2 files changed, 7 insertions(+), 2 deletions(-) - -diff --git doc/ChangeLog doc/ChangeLog -index 2d2dc1f9f..6d944f204 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -82,6 +82,11 @@ JH/21 Bug 2630: Fix eol-replacement string for the ${readsocket } expansion. - Previously when a whitespace character was specified it was not inserted - after removing the newline. - -+JH/24 Bug 2634: Fix a taint trap seen on NetBSD: the testing coded for -+ is_tainted() had an off-by-one error in the overenthusiastic direction. -+ Find and fix by Gavan. Although NetBSD is not a supported platform for -+ 4.94 this bug could affect other platforms. -+ - - Exim version 4.94 - ----------------- -diff --git src/store.c src/store.c -index c460ba383..7d08c9804 100644 ---- src/store.c -+++ src/store.c -@@ -188,14 +188,14 @@ for (int pool = POOL_TAINT_BASE; pool < nelem(chainbase); pool++) - if ((b = current_block[pool])) - { - uschar * bc = US b + ALIGNED_SIZEOF_STOREBLOCK; -- if (US p >= bc && US p <= bc + b->length) return TRUE; -+ if (US p >= bc && US p < bc + b->length) return TRUE; - } - - for (int pool = POOL_TAINT_BASE; pool < nelem(chainbase); pool++) - for (b = chainbase[pool]; b; b = b->next) - { - uschar * bc = US b + ALIGNED_SIZEOF_STOREBLOCK; -- if (US p >= bc && US p <= bc + b->length) return TRUE; -+ if (US p >= bc && US p < bc + b->length) return TRUE; - } - return FALSE; - } --- -2.28.0 - diff --git a/mail/exim/files/patch-z0030-Build-ifdef-guard-for-EXPERIMENTAL_QUEUEFILE b/mail/exim/files/patch-z0030-Build-ifdef-guard-for-EXPERIMENTAL_QUEUEFILE deleted file mode 100644 index a8c5f8573def..000000000000 --- a/mail/exim/files/patch-z0030-Build-ifdef-guard-for-EXPERIMENTAL_QUEUEFILE +++ /dev/null @@ -1,32 +0,0 @@ -From 4970c58b394eb0778542c97e3f86b565f9e3daa7 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Mon, 24 Aug 2020 20:14:34 +0100 -Subject: [PATCH 30/37] Build: ifdef guard for EXPERIMENTAL_QUEUEFILE - -(cherry picked from commit 1f5d0a9551205febf6729c7ee36c27626a76b4a4) ---- - src/transports/queuefile.c | 4 ++++ - -diff --git src/transports/queuefile.c src/transports/queuefile.c -index 21ed3527f..97218548b 100644 ---- src/transports/queuefile.c -+++ src/transports/queuefile.c -@@ -8,7 +8,10 @@ - /* See the file NOTICE for conditions of use and distribution. */ - - -+ - #include "../exim.h" -+ -+#ifdef EXPERIMENTAL_QUEUEFILE /* whole file */ - #include "queuefile.h" - - /* Options specific to the appendfile transport. They must be in alphabetic -@@ -276,3 +279,4 @@ return FALSE; - } - - #endif /*!MACRO_PREDEF*/ -+#endif /*EXPERIMENTAL_QUEUEFILE*/ --- -2.28.0 - diff --git a/mail/exim/files/patch-z0031-Taint-fix-off-by-one-in-is_tainted-.-Bug-2634 b/mail/exim/files/patch-z0031-Taint-fix-off-by-one-in-is_tainted-.-Bug-2634 deleted file mode 100644 index ddcbf2da8520..000000000000 --- a/mail/exim/files/patch-z0031-Taint-fix-off-by-one-in-is_tainted-.-Bug-2634 +++ /dev/null @@ -1,28 +0,0 @@ -From 976ef0e5fa7896394fe045e824dfb3e7d7502a68 Mon Sep 17 00:00:00 2001 -From: Gavan <gavan@coolfactor.org> -Date: Fri, 21 Aug 2020 15:46:01 +0100 -Subject: [PATCH 31/37] Taint: fix off-by-one in is_tainted(). Bug 2634 - -(cherry picked from commit e0ae68c8ee6788508da4989ee0d6fcbaf40c7b97) ---- - doc/ChangeLog | 5 +++++ - -diff --git doc/ChangeLog doc/ChangeLog -index 6d944f204..ae4050322 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -87,6 +87,11 @@ JH/24 Bug 2634: Fix a taint trap seen on NetBSD: the testing coded for - Find and fix by Gavan. Although NetBSD is not a supported platform for - 4.94 this bug could affect other platforms. - -+JH/24 Bug 2634: Fix a taint trap seen on NetBSD: the testing coded for -+ is_tainted() had an off-by-one error in the overenthusiastic direction. -+ Find and fix by Gavan. Although NetBSD is not a supported platform for -+ 4.94 this bug could affect other platforms. -+ - - Exim version 4.94 - ----------------- --- -2.28.0 - diff --git a/mail/exim/files/patch-z0032-DANE-force-SNI-to-use-domain.-Bug-2265 b/mail/exim/files/patch-z0032-DANE-force-SNI-to-use-domain.-Bug-2265 deleted file mode 100644 index 3ca3f78622ef..000000000000 --- a/mail/exim/files/patch-z0032-DANE-force-SNI-to-use-domain.-Bug-2265 +++ /dev/null @@ -1,102 +0,0 @@ -From d8e99d6047e709b35eabb1395c2046100d1a1dda Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Wed, 19 Aug 2020 21:09:04 +0100 -Subject: [PATCH 32/37] DANE: force SNI to use $domain. Bug 2265 - -Note: this is not a complete fix for the issue -(cherry picked from commit 7044dd8fd62e215572ecf5a2c7f1bb9581cf6628) ---- - doc/ChangeLog | 10 ++++++++++ - src/receive.c | 2 +- - src/smtp_in.c | 2 +- - src/tls-gnu.c | 2 +- - src/tls-openssl.c | 1 + - src/transports/smtp.c | 1 + - -diff --git doc/ChangeLog doc/ChangeLog -index ae4050322..ec1b03304 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -91,6 +91,16 @@ JH/24 Bug 2634: Fix a taint trap seen on NetBSD: the testing coded for - is_tainted() had an off-by-one error in the overenthusiastic direction. - Find and fix by Gavan. Although NetBSD is not a supported platform for - 4.94 this bug could affect other platforms. -+JH/21 Bug 2630: Fix eol-replacement string for the ${readsocket } expansion. -+ Previously when a whitespace character was specified it was not inserted -+ after removing the newline. -+ -+JH/22 Bug 2265: Force SNI usage for smtp transport DANE'd connections, to be -+ the domain part of the recipient address. This overrides any tls_sni -+ option set, which was previously used. -+ -+JH/23 Logging: with the +tls_sni log_selector, do not wrap the received SNI -+ in quotes. - - - Exim version 4.94 -diff --git src/receive.c src/receive.c -index 0db897e9e..ec90e93cd 100644 ---- src/receive.c -+++ src/receive.c -@@ -4004,7 +4004,7 @@ if (LOGGING(tls_certificate_verified) && tls_in.cipher) - if (LOGGING(tls_peerdn) && tls_in.peerdn) - g = string_append(g, 3, US" DN=\"", string_printing(tls_in.peerdn), US"\""); - if (LOGGING(tls_sni) && tls_in.sni) -- g = string_append(g, 3, US" SNI=\"", string_printing(tls_in.sni), US"\""); -+ g = string_append(g, 2, US" SNI=", string_printing2(tls_in.sni, SP_TAB|SP_SPACE)); - #endif - - if (sender_host_authenticated) -diff --git src/smtp_in.c src/smtp_in.c -index 526164c46..a13f0ed63 100644 ---- src/smtp_in.c -+++ src/smtp_in.c -@@ -1811,7 +1811,7 @@ if (LOGGING(tls_certificate_verified) && tls_in.cipher) - if (LOGGING(tls_peerdn) && tls_in.peerdn) - g = string_append(g, 3, US" DN=\"", string_printing(tls_in.peerdn), US"\""); - if (LOGGING(tls_sni) && tls_in.sni) -- g = string_append(g, 3, US" SNI=\"", string_printing(tls_in.sni), US"\""); -+ g = string_append(g, 2, US" SNI=", string_printing2(tls_in.sni, SP_TAB|SP_SPACE)); - return g; - } - #endif -diff --git src/tls-gnu.c src/tls-gnu.c -index 875c82efa..a34633390 100644 ---- src/tls-gnu.c -+++ src/tls-gnu.c -@@ -2863,7 +2863,7 @@ DEBUG(D_tls) debug_printf("initialising GnuTLS as a client on fd %d\n", cctx->so - /* If dane is flagged, have either request or require dane for this host, and - a TLSA record found. Therefore, dane verify required. Which implies cert must - be requested and supplied, dane verify must pass, and cert verify irrelevant --(incl. hostnames), and (caller handled) require_tls */ -+(incl. hostnames), and (caller handled) require_tls and sni=$domain */ - - if (conn_args->dane && ob->dane_require_tls_ciphers) - { -diff --git src/tls-openssl.c src/tls-openssl.c -index a62322928..054b23d0c 100644 ---- src/tls-openssl.c -+++ src/tls-openssl.c -@@ -3197,6 +3197,7 @@ tlsp->tlsa_usage = 0; - #ifndef DISABLE_OCSP - { - # ifdef SUPPORT_DANE -+ /*XXX this should be moved to caller, to be common across gnutls/openssl */ - if ( conn_args->dane - && ob->hosts_request_ocsp[0] == '*' - && ob->hosts_request_ocsp[1] == '\0' -diff --git src/transports/smtp.c src/transports/smtp.c -index 8492a7f25..28dd8ff24 100644 ---- src/transports/smtp.c -+++ src/transports/smtp.c -@@ -2020,6 +2020,7 @@ if (!continue_hostname) - { - case OK: sx->conn_args.dane = TRUE; - ob->tls_tempfail_tryclear = FALSE; -+ ob->tls_sni = sx->addrlist->domain; - break; - case FAIL_FORCED: break; - default: set_errno_nohost(sx->addrlist, ERRNO_DNSDEFER, --- -2.28.0 - diff --git a/mail/exim/files/patch-z0033-DANE-Fix-2-rcpt-message-diff-domins-case.-Bug-2265 b/mail/exim/files/patch-z0033-DANE-Fix-2-rcpt-message-diff-domins-case.-Bug-2265 deleted file mode 100644 index 95b82c12e5cc..000000000000 --- a/mail/exim/files/patch-z0033-DANE-Fix-2-rcpt-message-diff-domins-case.-Bug-2265 +++ /dev/null @@ -1,217 +0,0 @@ -From a505cf777f90755bce69ab53a899b284a304127b Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Sun, 23 Aug 2020 15:32:48 +0100 -Subject: [PATCH 33/37] DANE: Fix 2-rcpt message, diff domins case. Bug 2265 - -(cherry picked from commit 99350dede64ad634300ddf15d0d97a81fd75d330) ---- - src/debug.c | 11 ++++- - src/deliver.c | 3 ++ - src/macros.h | 1 + - src/transports/smtp.c | 71 ++++++++++++++++++++++++---- - src/verify.c | 2 +- - -diff --git src/debug.c src/debug.c -index 6d6132e39..819e83331 100644 ---- src/debug.c -+++ src/debug.c -@@ -30,7 +30,16 @@ const uschar * rc_names[] = { /* Mostly for debug output */ - [UNEXPECTED] = US"UNEXPECTED", - [CANCELLED] = US"CANCELLED", - [FAIL_SEND] = US"FAIL_SEND", -- [FAIL_DROP] = US"FAIL_DROP" -+ [FAIL_DROP] = US"FAIL_DROP", -+ [DANE] = US"DANE", -+}; -+ -+const uschar * dns_rc_names[] = { -+ [DNS_SUCCEED] = US"DNS_SUCCEED", -+ [DNS_NOMATCH] = US"DNS_NOMATCH", -+ [DNS_NODATA] = US"DNS_NODATA", -+ [DNS_AGAIN] = US"DNS_AGAIN", -+ [DNS_FAIL] = US"DNS_FAIL", - }; - - -diff --git src/deliver.c src/deliver.c -index 40db50084..f5e28941f 100644 ---- src/deliver.c -+++ src/deliver.c -@@ -460,6 +460,9 @@ TRUE if the lists refer to the same hosts in the same order, except that - This enables Exim to use a single SMTP transaction for sending to two entirely - different domains that happen to end up pointing at the same hosts. - -+We do not try to batch up different A-record host names that refer to the -+same IP. -+ - Arguments: - one points to the first host list - two points to the second host list -diff --git src/macros.h src/macros.h -index 2378773cb..6fd5db94c 100644 ---- src/macros.h -+++ src/macros.h -@@ -304,6 +304,7 @@ Use rc_names[] for debug strings. */ - #define CANCELLED 13 /* Authentication cancelled */ - #define FAIL_SEND 14 /* send() failed in authenticator */ - #define FAIL_DROP 15 /* Fail and drop connection (used in ACL) */ -+#define DANE 16 /* Deferred for domain mismatch (used in transport) */ - - /* Returns from the deliver_message() function */ - -diff --git src/transports/smtp.c src/transports/smtp.c -index 28dd8ff24..6ca4552a6 100644 ---- src/transports/smtp.c -+++ src/transports/smtp.c -@@ -2019,11 +2019,12 @@ if (!continue_hostname) - switch (rc = tlsa_lookup(sx->conn_args.host, &sx->conn_args.tlsa_dnsa, sx->dane_required)) - { - case OK: sx->conn_args.dane = TRUE; -- ob->tls_tempfail_tryclear = FALSE; -- ob->tls_sni = sx->addrlist->domain; -+ ob->tls_tempfail_tryclear = FALSE; /* force TLS */ -+ ob->tls_sni = sx->first_addr->domain; /* force SNI */ - break; - case FAIL_FORCED: break; -- default: set_errno_nohost(sx->addrlist, ERRNO_DNSDEFER, -+ default: -+ set_errno_nohost(sx->addrlist, ERRNO_DNSDEFER, - string_sprintf("DANE error: tlsa lookup %s", - rc_to_string(rc)), - rc, FALSE, &sx->delivery_start); -@@ -3430,6 +3431,7 @@ BOOL pass_message = FALSE; - uschar *message = NULL; - uschar new_message_id[MESSAGE_ID_LENGTH + 1]; - smtp_context * sx = store_get(sizeof(*sx), TRUE); /* tainted, for the data buffers */ -+BOOL dane_held; - - suppress_tls = suppress_tls; /* stop compiler warning when no TLS support */ - *message_defer = FALSE; -@@ -3446,13 +3448,36 @@ sx->conn_args.tblock = tblock; - gettimeofday(&sx->delivery_start, NULL); - sx->sync_addr = sx->first_addr = addrlist; - --/* Get the channel set up ready for a message (MAIL FROM being the next --SMTP command to send */ -+DANE_DOMAINS: -+dane_held = FALSE; -+ -+/* Get the channel set up ready for a message, MAIL FROM being the next -+SMTP command to send. */ - - if ((rc = smtp_setup_conn(sx, suppress_tls)) != OK) - { - timesince(&addrlist->delivery_time, &sx->delivery_start); -- return rc; -+ yield = rc; -+ goto TIDYUP; -+ } -+ -+/*XXX*/ -+/* If the connection used DANE, ignore for now any addresses with incompatible -+domains. The SNI has to be the domain. Arrange a whole new TCP conn later, -+just in case only TLS isn't enough. */ -+ -+if (sx->conn_args.dane) -+ { -+ const uschar * dane_domain = sx->first_addr->domain; -+ -+ for (address_item * a = sx->first_addr->next; a; a = a->next) -+ if ( a->transport_return == PENDING_DEFER -+ && Ustrcmp(dane_domain, a->domain) != 0) -+ { -+ DEBUG(D_transport) debug_printf("DANE: holding %s for later\n", a->domain); -+ dane_held = TRUE; -+ a->transport_return = DANE; -+ } - } - - /* If there is a filter command specified for this transport, we can now -@@ -4203,7 +4228,7 @@ if (sx->completed_addr && sx->ok && sx->send_quit) - - - if (sx->first_addr != NULL) /* More addresses still to be sent */ -- { /* in this run of the transport */ -+ { /* on this connection */ - continue_sequence++; /* Causes * in logging */ - pipelining_active = sx->pipelining_used; /* was cleared at DATA */ - goto SEND_MESSAGE; -@@ -4235,7 +4260,7 @@ if (sx->completed_addr && sx->ok && sx->send_quit) - '2', ob->command_timeout); - - if (sx->ok && f.continue_more) -- return yield; /* More addresses for another run */ -+ goto TIDYUP; /* More addresses for another run */ - } - else - { -@@ -4255,7 +4280,7 @@ if (sx->completed_addr && sx->ok && sx->send_quit) - else - #endif - if (f.continue_more) -- return yield; /* More addresses for another run */ -+ goto TIDYUP; /* More addresses for another run */ - - /* If the socket is successfully passed, we mustn't send QUIT (or - indeed anything!) from here. */ -@@ -4295,7 +4320,7 @@ propagate it from the initial - sx->cctx.sock = -1; - continue_transport = NULL; - continue_hostname = NULL; -- return yield; -+ goto TIDYUP; - } - log_write(0, LOG_PANIC_DIE, "fork failed"); - } -@@ -4370,9 +4395,35 @@ if (sx->send_quit) - (void) event_raise(tblock->event_action, US"tcp:close", NULL); - #endif - -+/*XXX*/ -+if (dane_held) -+ { -+ sx->first_addr = NULL; -+ for (address_item * a = sx->addrlist->next; a; a = a->next) -+ if (a->transport_return == DANE) -+ { -+ a->transport_return = PENDING_DEFER; -+ if (!sx->first_addr) -+ { -+ /* Remember the new start-point in the addrlist, for smtp_setup_conn() -+ to get the domain string for SNI */ -+ -+ sx->first_addr = a; -+ DEBUG(D_transport) debug_printf("DANE: go-around for %s\n", a->domain); -+ } -+ } -+ goto DANE_DOMAINS; -+ } -+ - continue_transport = NULL; - continue_hostname = NULL; - return yield; -+ -+TIDYUP: -+if (dane_held) for (address_item * a = sx->addrlist->next; a; a = a->next) -+ if (a->transport_return == DANE) -+ a->transport_return = PENDING_DEFER; -+return yield; - } - - -diff --git src/verify.c src/verify.c -index 5f4181de9..43343a646 100644 ---- src/verify.c -+++ src/verify.c -@@ -674,7 +674,7 @@ coding means skipping this whole loop and doing the append separately. */ - if (!sx) sx = store_get(sizeof(*sx), TRUE); /* tainted buffers */ - memset(sx, 0, sizeof(*sx)); - -- sx->addrlist = addr; -+ sx->addrlist = sx->first_addr = addr; - sx->conn_args.host = host; - sx->conn_args.host_af = host_af, - sx->port = port; --- -2.28.0 - diff --git a/mail/exim/files/patch-z0034-Fix-non-DANE-build b/mail/exim/files/patch-z0034-Fix-non-DANE-build deleted file mode 100644 index c3b8c26a6131..000000000000 --- a/mail/exim/files/patch-z0034-Fix-non-DANE-build +++ /dev/null @@ -1,92 +0,0 @@ -From 7dad62cced33eebd10d13fd1f6cd59696175fa44 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Sun, 23 Aug 2020 17:27:30 +0100 -Subject: [PATCH 34/37] Fix non-DANE build - -(cherry picked from commit 79b19a30d9fc64a7b7f70928cdefe4f51064280b) ---- - src/transports/smtp.c | 15 +++++++++++---- - -diff --git src/transports/smtp.c src/transports/smtp.c -index 6ca4552a6..d63379e37 100644 ---- src/transports/smtp.c -+++ src/transports/smtp.c -@@ -2023,8 +2023,7 @@ if (!continue_hostname) - ob->tls_sni = sx->first_addr->domain; /* force SNI */ - break; - case FAIL_FORCED: break; -- default: -- set_errno_nohost(sx->addrlist, ERRNO_DNSDEFER, -+ default: set_errno_nohost(sx->addrlist, ERRNO_DNSDEFER, - string_sprintf("DANE error: tlsa lookup %s", - rc_to_string(rc)), - rc, FALSE, &sx->delivery_start); -@@ -3431,7 +3430,9 @@ BOOL pass_message = FALSE; - uschar *message = NULL; - uschar new_message_id[MESSAGE_ID_LENGTH + 1]; - smtp_context * sx = store_get(sizeof(*sx), TRUE); /* tainted, for the data buffers */ -+#if !defined(DISABLE_TLS) && defined(SUPPORT_DANE) - BOOL dane_held; -+#endif - - suppress_tls = suppress_tls; /* stop compiler warning when no TLS support */ - *message_defer = FALSE; -@@ -3448,8 +3449,10 @@ sx->conn_args.tblock = tblock; - gettimeofday(&sx->delivery_start, NULL); - sx->sync_addr = sx->first_addr = addrlist; - -+#if !defined(DISABLE_TLS) && defined(SUPPORT_DANE) - DANE_DOMAINS: - dane_held = FALSE; -+#endif - - /* Get the channel set up ready for a message, MAIL FROM being the next - SMTP command to send. */ -@@ -3461,7 +3464,7 @@ if ((rc = smtp_setup_conn(sx, suppress_tls)) != OK) - goto TIDYUP; - } - --/*XXX*/ -+#if !defined(DISABLE_TLS) && defined(SUPPORT_DANE) - /* If the connection used DANE, ignore for now any addresses with incompatible - domains. The SNI has to be the domain. Arrange a whole new TCP conn later, - just in case only TLS isn't enough. */ -@@ -3479,6 +3482,7 @@ if (sx->conn_args.dane) - a->transport_return = DANE; - } - } -+#endif - - /* If there is a filter command specified for this transport, we can now - set it up. This cannot be done until the identity of the host is known. */ -@@ -4395,7 +4399,7 @@ if (sx->send_quit) - (void) event_raise(tblock->event_action, US"tcp:close", NULL); - #endif - --/*XXX*/ -+#if !defined(DISABLE_TLS) && defined(SUPPORT_DANE) - if (dane_held) - { - sx->first_addr = NULL; -@@ -4414,15 +4418,18 @@ if (dane_held) - } - goto DANE_DOMAINS; - } -+#endif - - continue_transport = NULL; - continue_hostname = NULL; - return yield; - - TIDYUP: -+#if !defined(DISABLE_TLS) && defined(SUPPORT_DANE) - if (dane_held) for (address_item * a = sx->addrlist->next; a; a = a->next) - if (a->transport_return == DANE) - a->transport_return = PENDING_DEFER; -+#endif - return yield; - } - --- -2.28.0 - diff --git a/mail/exim/files/patch-z0035-DANE-Fix-2-messages-from-queue-case b/mail/exim/files/patch-z0035-DANE-Fix-2-messages-from-queue-case deleted file mode 100644 index 2837f707d29b..000000000000 --- a/mail/exim/files/patch-z0035-DANE-Fix-2-messages-from-queue-case +++ /dev/null @@ -1,525 +0,0 @@ -From 569be4bc51fd4806edcf6b3abcf550dbbba90df5 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Wed, 26 Aug 2020 23:43:54 +0100 -Subject: [PATCH 35/37] DANE: Fix 2 messages from queue case - -(cherry picked from commit b6054898ace169a0e5143117397a4f666a5e7283) ---- - src/deliver.c | 12 +++- - src/exim.c | 14 +++- - src/globals.c | 2 + - src/globals.h | 2 + - src/spool_in.c | 24 +++---- - src/tls-gnu.c | 6 +- - src/transport.c | 32 ++++++--- - src/transports/smtp.c | 89 ++++++++++++++++++++--- - src/transports/smtp.h | 2 +- - -diff --git src/deliver.c src/deliver.c -index f5e28941f..8f21c607e 100644 ---- src/deliver.c -+++ src/deliver.c -@@ -1195,7 +1195,7 @@ else - if (addr->host_used) - { - g = d_hostlog(g, addr); -- if (continue_sequence > 1) -+ if (continue_sequence > 1) /*XXX this is wrong for a dropped proxyconn. Would have to pass back from transport */ - g = string_catn(g, US"*", 1); - - #ifndef DISABLE_EVENT -@@ -4275,6 +4275,10 @@ for (int delivery_count = 0; addr_remote; delivery_count++) - } - } - -+/*XXX need to defeat this when DANE is used - but we don't know that yet. -+So look out for the place it gets used. -+*/ -+ - /* Get the flag which specifies whether the transport can handle different - domains that nevertheless resolve to the same set of hosts. If it needs - expanding, get variables set: $address_data, $domain_data, $localpart_data, -@@ -4353,6 +4357,11 @@ for (int delivery_count = 0; addr_remote; delivery_count++) - /************************************************************************/ - - -+/*XXX don't know yet if DANE will be used. So tpt will have to -+check at the point if gets next addr from list, and skip/defer any -+nonmatch domains -+*/ -+ - /* Pick off all addresses which have the same transport, errors address, - destination, and extra headers. In some cases they point to the same host - list, but we also need to check for identical host lists generated from -@@ -4499,6 +4508,7 @@ for (int delivery_count = 0; addr_remote; delivery_count++) - if (continue_transport) - { - BOOL ok = Ustrcmp(continue_transport, tp->name) == 0; -+/*XXX do we need to check for a DANEd conn vs. a change of domain? */ - - /* If the transport is about to override the host list do not check - it here but take the cost of running the transport process to discover -diff --git src/exim.c src/exim.c -index ac0ff5523..630ac4038 100644 ---- src/exim.c -+++ src/exim.c -@@ -2806,10 +2806,22 @@ on the second character (the one after '-'), to save some effort. */ - case 'S': smtp_peer_options |= OPTION_SIZE; break; - - #ifndef DISABLE_TLS -+ /* -MCs: used with -MCt; SNI was sent */ -+ /* -MCr: ditto, DANE */ -+ -+ case 'r': -+ case 's': if (++i < argc) -+ { -+ continue_proxy_sni = string_copy_taint(argv[i], TRUE); -+ if (argrest[1] == 'r') continue_proxy_dane = TRUE; -+ } -+ else badarg = TRUE; -+ break; -+ - /* -MCt: similar to -MCT below but the connection is still open - via a proxy process which handles the TLS context and coding. - Require three arguments for the proxied local address and port, -- and the TLS cipher. */ -+ and the TLS cipher. */ - - case 't': if (++i < argc) - sending_ip_address = string_copy_taint(argv[i], TRUE); -diff --git src/globals.c src/globals.c -index fc3086f72..c34ac9ddd 100644 ---- src/globals.c -+++ src/globals.c -@@ -729,6 +729,8 @@ uid_t config_uid = 0; - - int connection_max_messages= -1; - uschar *continue_proxy_cipher = NULL; -+BOOL continue_proxy_dane = FALSE; -+uschar *continue_proxy_sni = NULL; - uschar *continue_hostname = NULL; - uschar *continue_host_address = NULL; - int continue_sequence = 1; -diff --git src/globals.h src/globals.h -index c80c8532f..a4c1143b7 100644 ---- src/globals.h -+++ src/globals.h -@@ -425,6 +425,8 @@ extern uschar *config_main_filename; /* File name actually used */ - extern uschar *config_main_directory; /* Directory where the main config file was found */ - extern uid_t config_uid; /* Additional owner */ - extern uschar *continue_proxy_cipher; /* TLS cipher for proxied continued delivery */ -+extern BOOL continue_proxy_dane; /* proxied conn is DANE */ -+extern uschar *continue_proxy_sni; /* proxied conn SNI */ - extern uschar *continue_hostname; /* Host for continued delivery */ - extern uschar *continue_host_address; /* IP address for ditto */ - extern int continue_sequence; /* Sequence num for continued delivery */ -diff --git src/spool_in.c src/spool_in.c -index a0147d5ee..1b4cefdb2 100644 ---- src/spool_in.c -+++ src/spool_in.c -@@ -55,7 +55,7 @@ for (int i = 0; i < 2; i++) - - set_subdir_str(message_subdir, id, i); - fname = spool_fname(US"input", message_subdir, id, US"-D"); -- DEBUG(D_deliver) debug_printf("Trying spool file %s\n", fname); -+ DEBUG(D_deliver) debug_printf_indent("Trying spool file %s\n", fname); - - /* We protect against symlink attacks both in not propagating the - * file-descriptor to other processes as we exec, and also ensuring that we -@@ -367,7 +367,7 @@ for (int n = 0; n < 2; n++) - errno = 0; - - #ifndef COMPILE_UTILITY --DEBUG(D_deliver) debug_printf("reading spool file %s\n", name); -+DEBUG(D_deliver) debug_printf_indent("reading spool file %s\n", name); - #endif /* COMPILE_UTILITY */ - - /* The first line of a spool file contains the message id followed by -H (i.e. -@@ -430,7 +430,7 @@ if (f.running_in_test_harness) - #endif - - #ifndef COMPILE_UTILITY --DEBUG(D_deliver) debug_printf("user=%s uid=%ld gid=%ld sender=%s\n", -+DEBUG(D_deliver) debug_printf_indent("user=%s uid=%ld gid=%ld sender=%s\n", - originator_login, (long int)originator_uid, (long int)originator_gid, - sender_address); - #endif -@@ -715,7 +715,7 @@ host_build_sender_fullhost(); - - #ifndef COMPILE_UTILITY - DEBUG(D_deliver) -- debug_printf("sender_local=%d ident=%s\n", f.sender_local, -+ debug_printf_indent("sender_local=%d ident=%s\n", f.sender_local, - sender_ident ? sender_ident : US"unset"); - #endif /* COMPILE_UTILITY */ - -@@ -743,7 +743,7 @@ if (sscanf(CS big_buffer, "%d", &rcount) != 1 || rcount > 16384) - goto SPOOL_FORMAT_ERROR; - - #ifndef COMPILE_UTILITY --DEBUG(D_deliver) debug_printf("recipients_count=%d\n", rcount); -+DEBUG(D_deliver) debug_printf_indent("recipients_count=%d\n", rcount); - #endif /* COMPILE_UTILITY */ - - recipients_list_max = rcount; -@@ -814,7 +814,7 @@ for (recipients_count = 0; recipients_count < rcount; recipients_count++) - { - int dummy; - #if !defined (COMPILE_UTILITY) -- DEBUG(D_deliver) debug_printf("**** SPOOL_IN - Exim 3 spool file\n"); -+ DEBUG(D_deliver) debug_printf_indent("**** SPOOL_IN - Exim 3 spool file\n"); - #endif - while (isdigit(*(--p)) || *p == ','); - if (*p == ' ') -@@ -829,7 +829,7 @@ for (recipients_count = 0; recipients_count < rcount; recipients_count++) - else if (*p == ' ') - { - #if !defined (COMPILE_UTILITY) -- DEBUG(D_deliver) debug_printf("**** SPOOL_IN - early Exim 4 spool file\n"); -+ DEBUG(D_deliver) debug_printf_indent("**** SPOOL_IN - early Exim 4 spool file\n"); - #endif - *p++ = 0; - (void)sscanf(CS p, "%d", &pno); -@@ -842,7 +842,7 @@ for (recipients_count = 0; recipients_count < rcount; recipients_count++) - int flags; - - #if !defined (COMPILE_UTILITY) -- DEBUG(D_deliver) debug_printf("**** SPOOL_IN - Exim standard format spoolfile\n"); -+ DEBUG(D_deliver) debug_printf_indent("**** SPOOL_IN - Exim standard format spoolfile\n"); - #endif - - (void)sscanf(CS p+1, "%d", &flags); -@@ -878,13 +878,13 @@ for (recipients_count = 0; recipients_count < rcount; recipients_count++) - } - #if !defined(COMPILE_UTILITY) - else -- { DEBUG(D_deliver) debug_printf("**** SPOOL_IN - No additional fields\n"); } -+ { DEBUG(D_deliver) debug_printf_indent("**** SPOOL_IN - No additional fields\n"); } - - if (orcpt || dsn_flags) -- DEBUG(D_deliver) debug_printf("**** SPOOL_IN - address: <%s> orcpt: <%s> dsn_flags: 0x%x\n", -+ DEBUG(D_deliver) debug_printf_indent("**** SPOOL_IN - address: <%s> orcpt: <%s> dsn_flags: 0x%x\n", - big_buffer, orcpt, dsn_flags); - if (errors_to) -- DEBUG(D_deliver) debug_printf("**** SPOOL_IN - address: <%s> errorsto: <%s>\n", -+ DEBUG(D_deliver) debug_printf_indent("**** SPOOL_IN - address: <%s> errorsto: <%s>\n", - big_buffer, errors_to); - #endif - -@@ -956,7 +956,7 @@ line count by adding the body linecount to the header linecount. Close the file - and give a positive response. */ - - #ifndef COMPILE_UTILITY --DEBUG(D_deliver) debug_printf("body_linecount=%d message_linecount=%d\n", -+DEBUG(D_deliver) debug_printf_indent("body_linecount=%d message_linecount=%d\n", - body_linecount, message_linecount); - #endif /* COMPILE_UTILITY */ - -diff --git src/tls-gnu.c src/tls-gnu.c -index a34633390..dafe1be0c 100644 ---- src/tls-gnu.c -+++ src/tls-gnu.c -@@ -545,7 +545,10 @@ else - - /* peercert is set in peer_status() */ - tlsp->peerdn = state->peerdn; --tlsp->sni = state->received_sni; -+ -+/* do not corrupt sni sent by client; record sni rxd by server */ -+if (!state->host) -+ tlsp->sni = state->received_sni; - - /* record our certificate */ - { -@@ -2890,6 +2893,7 @@ if (!cipher_list) - cipher_list, &state, tlsp, errstr) != OK) - return FALSE; - -+ - #ifdef MEASURE_TIMING - report_time_since(&t0, US"client tls_init (delta)"); - #endif -diff --git src/transport.c src/transport.c -index 2d8426f29..b1cda55fd 100644 ---- src/transport.c -+++ src/transport.c -@@ -1661,6 +1661,7 @@ DEBUG(D_transport) - debug_printf("transport_check_waiting entered\n"); - debug_printf(" sequence=%d local_max=%d global_max=%d\n", - continue_sequence, local_message_max, connection_max_messages); -+ acl_level++; - } - - /* Do nothing if we have hit the maximum number that can be send down one -@@ -1670,23 +1671,23 @@ if (connection_max_messages >= 0) local_message_max = connection_max_messages; - if (local_message_max > 0 && continue_sequence >= local_message_max) - { - DEBUG(D_transport) -- debug_printf("max messages for one connection reached: returning\n"); -- return FALSE; -+ debug_printf_indent("max messages for one connection reached: returning\n"); -+ goto retfalse; - } - - /* Open the waiting information database. */ - - if (!(dbm_file = dbfn_open(string_sprintf("wait-%.200s", transport_name), - O_RDWR, &dbblock, TRUE, TRUE))) -- return FALSE; -+ goto retfalse; - - /* See if there is a record for this host; if not, there's nothing to do. */ - - if (!(host_record = dbfn_read(dbm_file, hostname))) - { - dbfn_close(dbm_file); -- DEBUG(D_transport) debug_printf("no messages waiting for %s\n", hostname); -- return FALSE; -+ DEBUG(D_transport) debug_printf_indent("no messages waiting for %s\n", hostname); -+ goto retfalse; - } - - /* If the data in the record looks corrupt, just log something and -@@ -1697,7 +1698,7 @@ if (host_record->count > WAIT_NAME_MAX) - dbfn_close(dbm_file); - log_write(0, LOG_MAIN|LOG_PANIC, "smtp-wait database entry for %s has bad " - "count=%d (max=%d)", hostname, host_record->count, WAIT_NAME_MAX); -- return FALSE; -+ goto retfalse; - } - - /* Scan the message ids in the record from the end towards the beginning, -@@ -1835,8 +1836,8 @@ while (1) - if (host_length <= 0) - { - dbfn_close(dbm_file); -- DEBUG(D_transport) debug_printf("waiting messages already delivered\n"); -- return FALSE; -+ DEBUG(D_transport) debug_printf_indent("waiting messages already delivered\n"); -+ goto retfalse; - } - - /* we were not able to find an acceptable message, nor was there a -@@ -1847,7 +1848,7 @@ while (1) - { - Ustrcpy(new_message_id, message_id); - dbfn_close(dbm_file); -- return FALSE; -+ goto retfalse; - } - } /* we need to process a continuation record */ - -@@ -1865,7 +1866,12 @@ if (host_length > 0) - } - - dbfn_close(dbm_file); -+DEBUG(D_transport) {acl_level--; debug_printf("transport_check_waiting: TRUE\n"); } - return TRUE; -+ -+retfalse: -+DEBUG(D_transport) {acl_level--; debug_printf("transport_check_waiting: FALSE\n"); } -+return FALSE; - } - - /************************************************* -@@ -1877,7 +1883,7 @@ void - transport_do_pass_socket(const uschar *transport_name, const uschar *hostname, - const uschar *hostaddress, uschar *id, int socket_fd) - { --int i = 20; -+int i = 22; - const uschar **argv; - - /* Set up the calling arguments; use the standard function for the basics, -@@ -1898,6 +1904,12 @@ if (smtp_peer_options & OPTION_TLS) - argv[i++] = sending_ip_address; - argv[i++] = string_sprintf("%d", sending_port); - argv[i++] = tls_out.active.sock >= 0 ? tls_out.cipher : continue_proxy_cipher; -+ -+ if (tls_out.sni) -+ { -+ argv[i++] = tls_out.dane_verified ? US"-MCr" : US"-MCs"; -+ argv[i++] = tls_out.sni; -+ } - } - else - argv[i++] = US"-MCT"; -diff --git src/transports/smtp.c src/transports/smtp.c -index d63379e37..7fc2a48bb 100644 ---- src/transports/smtp.c -+++ src/transports/smtp.c -@@ -1620,8 +1620,8 @@ return FALSE; - - typedef struct smtp_compare_s - { -- uschar *current_sender_address; -- struct transport_instance *tblock; -+ uschar * current_sender_address; -+ struct transport_instance * tblock; - } smtp_compare_t; - - -@@ -1991,6 +1991,74 @@ if (sx->smtps) - } - #endif - -+#ifdef SUPPORT_DANE -+/* If we have a proxied TLS connection, check usability for this message */ -+ -+if (continue_hostname && continue_proxy_cipher) -+ { -+ int rc; -+ const uschar * sni = US""; -+ -+ /* Check if the message will be DANE-verified; if so force its SNI */ -+ -+ smtp_port_for_connect(sx->conn_args.host, sx->port); -+ if ( sx->conn_args.host->dnssec == DS_YES -+ && ( sx->dane_required -+ || verify_check_given_host(CUSS &ob->hosts_try_dane, sx->conn_args.host) == OK -+ ) ) -+ switch (rc = tlsa_lookup(sx->conn_args.host, &sx->conn_args.tlsa_dnsa, sx->dane_required)) -+ { -+ case OK: sx->conn_args.dane = TRUE; -+ ob->tls_tempfail_tryclear = FALSE; /* force TLS */ -+ ob->tls_sni = sx->first_addr->domain; /* force SNI */ -+ break; -+ case FAIL_FORCED: break; -+ default: set_errno_nohost(sx->addrlist, ERRNO_DNSDEFER, -+ string_sprintf("DANE error: tlsa lookup %s", -+ rc_to_string(rc)), -+ rc, FALSE, &sx->delivery_start); -+# ifndef DISABLE_EVENT -+ (void) event_raise(sx->conn_args.tblock->event_action, -+ US"dane:fail", sx->dane_required -+ ? US"dane-required" : US"dnssec-invalid"); -+# endif -+ return rc; -+ } -+ -+ /* If the SNI required for the new message differs from the existing conn -+ drop the connection to force a new one. */ -+ -+ if (ob->tls_sni && !(sni = expand_cstring(ob->tls_sni))) -+ log_write(0, LOG_MAIN|LOG_PANIC, -+ "<%s>: failed to expand transport's tls_sni value: %s", -+ sx->addrlist->address, expand_string_message); -+ -+ if ( (continue_proxy_sni ? (Ustrcmp(continue_proxy_sni, sni) == 0) : !*sni) -+ && continue_proxy_dane == sx->conn_args.dane) -+ { -+ tls_out.sni = US sni; -+ if ((tls_out.dane_verified = continue_proxy_dane)) -+ sx->conn_args.host->dnssec = DS_YES; -+ } -+ else -+ { -+ DEBUG(D_transport) -+ debug_printf("Closing proxied-TLS connection due to SNI mismatch\n"); -+ -+ HDEBUG(D_transport|D_acl|D_v) debug_printf_indent(" SMTP>> QUIT\n"); -+ write(0, "QUIT\r\n", 6); -+ close(0); -+ tls_out.dane_verified = FALSE; -+ continue_hostname = continue_proxy_cipher = NULL; -+ f.continue_more = FALSE; -+ continue_sequence = 1; /* Unfortunately, this process cannot affect success log -+ which is done by delivery proc. Would have to pass this -+ back through reporting pipe. */ -+ } -+ } -+#endif -+ -+ - /* Make a connection to the host if this isn't a continued delivery, and handle - the initial interaction and HELO/EHLO/LHLO. Connect timeout errors are handled - specially so they can be identified for retries. */ -@@ -3430,7 +3498,7 @@ BOOL pass_message = FALSE; - uschar *message = NULL; - uschar new_message_id[MESSAGE_ID_LENGTH + 1]; - smtp_context * sx = store_get(sizeof(*sx), TRUE); /* tainted, for the data buffers */ --#if !defined(DISABLE_TLS) && defined(SUPPORT_DANE) -+#ifdef SUPPORT_DANE - BOOL dane_held; - #endif - -@@ -3449,7 +3517,7 @@ sx->conn_args.tblock = tblock; - gettimeofday(&sx->delivery_start, NULL); - sx->sync_addr = sx->first_addr = addrlist; - --#if !defined(DISABLE_TLS) && defined(SUPPORT_DANE) -+#ifdef SUPPORT_DANE - DANE_DOMAINS: - dane_held = FALSE; - #endif -@@ -3464,7 +3532,7 @@ if ((rc = smtp_setup_conn(sx, suppress_tls)) != OK) - goto TIDYUP; - } - --#if !defined(DISABLE_TLS) && defined(SUPPORT_DANE) -+#ifdef SUPPORT_DANE - /* If the connection used DANE, ignore for now any addresses with incompatible - domains. The SNI has to be the domain. Arrange a whole new TCP conn later, - just in case only TLS isn't enough. */ -@@ -4184,8 +4252,8 @@ if (sx->completed_addr && sx->ok && sx->send_quit) - t_compare.tblock = tblock; - t_compare.current_sender_address = sender_address; - -- if ( sx->first_addr != NULL -- || f.continue_more -+ if ( sx->first_addr != NULL /* more addrs for this message */ -+ || f.continue_more /* more addrs for coninued-host */ - || ( - #ifndef DISABLE_TLS - ( tls_out.active.sock < 0 && !continue_proxy_cipher -@@ -4232,7 +4300,7 @@ if (sx->completed_addr && sx->ok && sx->send_quit) - - - if (sx->first_addr != NULL) /* More addresses still to be sent */ -- { /* on this connection */ -+ { /* for this message */ - continue_sequence++; /* Causes * in logging */ - pipelining_active = sx->pipelining_used; /* was cleared at DATA */ - goto SEND_MESSAGE; -@@ -4256,6 +4324,7 @@ if (sx->completed_addr && sx->ok && sx->send_quit) - - tls_close(sx->cctx.tls_ctx, TLS_SHUTDOWN_WAIT); - sx->cctx.tls_ctx = NULL; -+ tls_out.active.sock = -1; - smtp_peer_options = smtp_peer_options_wrap; - sx->ok = !sx->smtps - && smtp_write_command(sx, SCMD_FLUSH, "EHLO %s\r\n", sx->helo_data) -@@ -4399,7 +4468,7 @@ if (sx->send_quit) - (void) event_raise(tblock->event_action, US"tcp:close", NULL); - #endif - --#if !defined(DISABLE_TLS) && defined(SUPPORT_DANE) -+#ifdef SUPPORT_DANE - if (dane_held) - { - sx->first_addr = NULL; -@@ -4425,7 +4494,7 @@ continue_hostname = NULL; - return yield; - - TIDYUP: --#if !defined(DISABLE_TLS) && defined(SUPPORT_DANE) -+#ifdef SUPPORT_DANE - if (dane_held) for (address_item * a = sx->addrlist->next; a; a = a->next) - if (a->transport_return == DANE) - a->transport_return = PENDING_DEFER; -diff --git src/transports/smtp.h src/transports/smtp.h -index 6e63a002d..213bca1a8 100644 ---- src/transports/smtp.h -+++ src/transports/smtp.h -@@ -87,7 +87,7 @@ typedef struct { - # ifdef EXPERIMENTAL_TLS_RESUME - uschar *tls_resumption_hosts; - # endif -- uschar *tls_sni; -+ const uschar *tls_sni; - uschar *tls_verify_certificates; - int tls_dh_min_bits; - BOOL tls_tempfail_tryclear; --- -2.28.0 - diff --git a/mail/exim/files/patch-z0036-Fix-non-DANE-build b/mail/exim/files/patch-z0036-Fix-non-DANE-build deleted file mode 100644 index 1139257b4226..000000000000 --- a/mail/exim/files/patch-z0036-Fix-non-DANE-build +++ /dev/null @@ -1,114 +0,0 @@ -From 6742503035564e057edc7d3eba88b108f7d3d74c Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Wed, 26 Aug 2020 23:59:28 +0100 -Subject: [PATCH 36/37] Fix non-DANE build - -(cherry picked from commit 651946cbf8e3849687332049730e5fa23d42b4b7) ---- - src/smtp_out.c | 2 +- - src/transport.c | 6 +++++- - src/transports/smtp.c | 15 ++++++++++----- - -diff --git src/smtp_out.c src/smtp_out.c -index 86c3e4127..c4c409677 100644 ---- src/smtp_out.c -+++ src/smtp_out.c -@@ -375,7 +375,7 @@ smtp_port_for_connect(host_item * host, int port) - { - if (host->port != PORT_NONE) - { -- HDEBUG(D_transport|D_acl|D_v) -+ HDEBUG(D_transport|D_acl|D_v) if (port != host->port) - debug_printf_indent("Transport port=%d replaced by host-specific port=%d\n", port, - host->port); - port = host->port; -diff --git src/transport.c src/transport.c -index b1cda55fd..609fd128c 100644 ---- src/transport.c -+++ src/transport.c -@@ -1907,7 +1907,11 @@ if (smtp_peer_options & OPTION_TLS) - - if (tls_out.sni) - { -- argv[i++] = tls_out.dane_verified ? US"-MCr" : US"-MCs"; -+ argv[i++] = -+#ifdef SUPPORT_DANE -+ tls_out.dane_verified ? US"-MCr" : -+#endif -+ US"-MCs"; - argv[i++] = tls_out.sni; - } - } -diff --git src/transports/smtp.c src/transports/smtp.c -index 7fc2a48bb..77335af09 100644 ---- src/transports/smtp.c -+++ src/transports/smtp.c -@@ -1991,7 +1991,6 @@ if (sx->smtps) - } - #endif - --#ifdef SUPPORT_DANE - /* If we have a proxied TLS connection, check usability for this message */ - - if (continue_hostname && continue_proxy_cipher) -@@ -1999,8 +1998,10 @@ if (continue_hostname && continue_proxy_cipher) - int rc; - const uschar * sni = US""; - -+#ifdef SUPPORT_DANE - /* Check if the message will be DANE-verified; if so force its SNI */ - -+ tls_out.dane_verified = FALSE; - smtp_port_for_connect(sx->conn_args.host, sx->port); - if ( sx->conn_args.host->dnssec == DS_YES - && ( sx->dane_required -@@ -2024,15 +2025,17 @@ if (continue_hostname && continue_proxy_cipher) - # endif - return rc; - } -+#endif - -- /* If the SNI required for the new message differs from the existing conn -- drop the connection to force a new one. */ -+ /* If the SNI or the DANE status required for the new message differs from the -+ existing conn drop the connection to force a new one. */ - - if (ob->tls_sni && !(sni = expand_cstring(ob->tls_sni))) - log_write(0, LOG_MAIN|LOG_PANIC, - "<%s>: failed to expand transport's tls_sni value: %s", - sx->addrlist->address, expand_string_message); - -+#ifdef SUPPORT_DANE - if ( (continue_proxy_sni ? (Ustrcmp(continue_proxy_sni, sni) == 0) : !*sni) - && continue_proxy_dane == sx->conn_args.dane) - { -@@ -2040,6 +2043,10 @@ if (continue_hostname && continue_proxy_cipher) - if ((tls_out.dane_verified = continue_proxy_dane)) - sx->conn_args.host->dnssec = DS_YES; - } -+#else -+ if ((continue_proxy_sni ? (Ustrcmp(continue_proxy_sni, sni) == 0) : !*sni)) -+ tls_out.sni = US sni; -+#endif - else - { - DEBUG(D_transport) -@@ -2048,7 +2055,6 @@ if (continue_hostname && continue_proxy_cipher) - HDEBUG(D_transport|D_acl|D_v) debug_printf_indent(" SMTP>> QUIT\n"); - write(0, "QUIT\r\n", 6); - close(0); -- tls_out.dane_verified = FALSE; - continue_hostname = continue_proxy_cipher = NULL; - f.continue_more = FALSE; - continue_sequence = 1; /* Unfortunately, this process cannot affect success log -@@ -2056,7 +2062,6 @@ if (continue_hostname && continue_proxy_cipher) - back through reporting pipe. */ - } - } --#endif - - - /* Make a connection to the host if this isn't a continued delivery, and handle --- -2.28.0 - diff --git a/mail/exim/files/patch-z0038-GnuTLS-clear-errno-before-any-data-i-o-op-so-error-logging b/mail/exim/files/patch-z0038-GnuTLS-clear-errno-before-any-data-i-o-op-so-error-logging deleted file mode 100644 index b3c9af46aee7..000000000000 --- a/mail/exim/files/patch-z0038-GnuTLS-clear-errno-before-any-data-i-o-op-so-error-logging +++ /dev/null @@ -1,41 +0,0 @@ -From 49d173f4e4c05bbc9e6f256f8914979dad85e9d3 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Sun, 6 Sep 2020 12:15:10 +0100 -Subject: [PATCH 38/42] GnuTLS: clear errno before any data i/o op, so error - logging does not see stale values - -(cherry picked from commit d52a8ce8499fbb88f4670623df9f52d3e790292b) ---- - src/tls-gnu.c | 3 +++ - -diff --git src/tls-gnu.c src/tls-gnu.c -index dafe1be0c..6ee603595 100644 ---- src/tls-gnu.c -+++ src/tls-gnu.c -@@ -3162,6 +3162,7 @@ DEBUG(D_tls) debug_printf("Calling gnutls_record_recv(session=%p, buffer=%p, buf - sigalrm_seen = FALSE; - if (smtp_receive_timeout > 0) ALARM(smtp_receive_timeout); - -+errno = 0; - do - inbytes = gnutls_record_recv(state->session, state->xfer_buffer, - MIN(ssl_xfer_buffer_size, lim)); -@@ -3322,6 +3323,7 @@ DEBUG(D_tls) - debug_printf("Calling gnutls_record_recv(session=%p, buffer=%p, len=" SIZE_T_FMT ")\n", - state->session, buff, len); - -+errno = 0; - do - inbytes = gnutls_record_recv(state->session, buff, len); - while (inbytes == GNUTLS_E_AGAIN); -@@ -3385,6 +3387,7 @@ while (left > 0) - DEBUG(D_tls) debug_printf("gnutls_record_send(session=%p, buffer=%p, left=" SIZE_T_FMT ")\n", - state->session, buff, left); - -+ errno = 0; - do - outbytes = gnutls_record_send(state->session, buff, left); - while (outbytes == GNUTLS_E_AGAIN); --- -2.29.2 - diff --git a/mail/exim/files/patch-z0039-Fix-non-TLS-build b/mail/exim/files/patch-z0039-Fix-non-TLS-build deleted file mode 100644 index ef9ef5c34095..000000000000 --- a/mail/exim/files/patch-z0039-Fix-non-TLS-build +++ /dev/null @@ -1,83 +0,0 @@ -From 7a534c812646a7a6f680827352d6209c6ff7be96 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Thu, 27 Aug 2020 21:15:19 +0100 -Subject: [PATCH 39/42] Fix non-TLS build - -(cherry picked from commit b38a477da0a5248ed1d2b7590922c89c6337ec3b) ---- - src/transports/smtp.c | 18 +++++++++--------- - -diff --git src/transports/smtp.c src/transports/smtp.c -index 77335af09..b0dedfa8c 100644 ---- src/transports/smtp.c -+++ src/transports/smtp.c -@@ -1989,7 +1989,7 @@ if (sx->smtps) - DEFER, FALSE, &sx->delivery_start); - return ERROR; - } --#endif -+#else - - /* If we have a proxied TLS connection, check usability for this message */ - -@@ -1998,7 +1998,7 @@ if (continue_hostname && continue_proxy_cipher) - int rc; - const uschar * sni = US""; - --#ifdef SUPPORT_DANE -+# ifdef SUPPORT_DANE - /* Check if the message will be DANE-verified; if so force its SNI */ - - tls_out.dane_verified = FALSE; -@@ -2018,14 +2018,14 @@ if (continue_hostname && continue_proxy_cipher) - string_sprintf("DANE error: tlsa lookup %s", - rc_to_string(rc)), - rc, FALSE, &sx->delivery_start); --# ifndef DISABLE_EVENT -+# ifndef DISABLE_EVENT - (void) event_raise(sx->conn_args.tblock->event_action, - US"dane:fail", sx->dane_required - ? US"dane-required" : US"dnssec-invalid"); --# endif -+# endif - return rc; - } --#endif -+# endif - - /* If the SNI or the DANE status required for the new message differs from the - existing conn drop the connection to force a new one. */ -@@ -2035,7 +2035,7 @@ if (continue_hostname && continue_proxy_cipher) - "<%s>: failed to expand transport's tls_sni value: %s", - sx->addrlist->address, expand_string_message); - --#ifdef SUPPORT_DANE -+# ifdef SUPPORT_DANE - if ( (continue_proxy_sni ? (Ustrcmp(continue_proxy_sni, sni) == 0) : !*sni) - && continue_proxy_dane == sx->conn_args.dane) - { -@@ -2043,10 +2043,10 @@ if (continue_hostname && continue_proxy_cipher) - if ((tls_out.dane_verified = continue_proxy_dane)) - sx->conn_args.host->dnssec = DS_YES; - } --#else -+# else - if ((continue_proxy_sni ? (Ustrcmp(continue_proxy_sni, sni) == 0) : !*sni)) - tls_out.sni = US sni; --#endif -+# endif - else - { - DEBUG(D_transport) -@@ -2062,7 +2062,7 @@ if (continue_hostname && continue_proxy_cipher) - back through reporting pipe. */ - } - } -- -+#endif /*!DISABLE_TLS*/ - - /* Make a connection to the host if this isn't a continued delivery, and handle - the initial interaction and HELO/EHLO/LHLO. Connect timeout errors are handled --- -2.29.2 - diff --git a/mail/exim/files/patch-z0040-eximon-fix-FreeBSD-build b/mail/exim/files/patch-z0040-eximon-fix-FreeBSD-build deleted file mode 100644 index 5486082bdd76..000000000000 --- a/mail/exim/files/patch-z0040-eximon-fix-FreeBSD-build +++ /dev/null @@ -1,25 +0,0 @@ -From f521f0d2120be2ccfb93306cc05790b9b0f162c1 Mon Sep 17 00:00:00 2001 -From: Richard Clayton <richard@highwayman.com> -Date: Sat, 12 Sep 2020 22:10:04 +0100 -Subject: [PATCH 40/42] eximon: fix FreeBSD build - -(cherry picked from commit ba00bdd4609501dd3ffe187074ff7f8197a9059f) ---- - exim_monitor/em_menu.c | 2 +- - -diff --git exim_monitor/em_menu.c exim_monitor/em_menu.c -index 33b3e0c94..2a70a1831 100644 ---- exim_monitor/em_menu.c -+++ exim_monitor/em_menu.c -@@ -670,7 +670,7 @@ if (spool_read_header(buffer, TRUE, FALSE) != spool_read_OK) - sprintf(CS big_buffer, "%s/input/%s", spool_directory, buffer); - if (Ustat(big_buffer, &statbuf) == 0) - text_showf(text, "Format error in spool file %s: size=%lu\n", buffer, -- (ulong)statbuf.st_size); -+ (unsigned long)statbuf.st_size); - else text_showf(text, "Format error in spool file %s\n", buffer); - } - else text_showf(text, "Read error for spool file %s\n", buffer); --- -2.29.2 - diff --git a/mail/exim/files/patch-z0041-LDAP-fix-taint-check-in-server-list-walk.-Bug-2646 b/mail/exim/files/patch-z0041-LDAP-fix-taint-check-in-server-list-walk.-Bug-2646 deleted file mode 100644 index 14a0a02fa090..000000000000 --- a/mail/exim/files/patch-z0041-LDAP-fix-taint-check-in-server-list-walk.-Bug-2646 +++ /dev/null @@ -1,51 +0,0 @@ -From e12d2e7bc2e9f0c30a1029602e57e5ae8df1b9db Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Fri, 30 Oct 2020 13:58:01 +0000 -Subject: [PATCH 41/42] LDAP: fix taint-check in server list walk. Bug - 2646 - - (cherry picked from commit 51b611aa81d7ee01243b196abc34a0e2eabd293c) ---- - doc/ChangeLog | 5 +++++ - src/lookups/ldap.c | 3 +-- - -diff --git doc/ChangeLog doc/ChangeLog -index ec1b03304..9924fca5c 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -102,6 +102,11 @@ JH/22 Bug 2265: Force SNI usage for smtp transport DANE'd connections, to be - JH/23 Logging: with the +tls_sni log_selector, do not wrap the received SNI - in quotes. - -+JH/26 Bug 2646: fix a memory usage issue in ldap lookups. Previously, when more -+ than one server was defined and depending on the platform memory layout -+ details, an internal consistency trap could be hit while walking the list -+ of servers. -+ - - Exim version 4.94 - ----------------- -diff --git src/lookups/ldap.c src/lookups/ldap.c -index ef550a08d..34908a351 100644 ---- src/lookups/ldap.c -+++ src/lookups/ldap.c -@@ -1093,7 +1093,6 @@ uschar *password = NULL; - uschar *local_servers = NULL; - uschar *server; - const uschar *list; --uschar buffer[512]; - - while (isspace(*url)) url++; - -@@ -1254,7 +1253,7 @@ if (!eldap_default_servers && !local_servers || p[3] != '/') - /* Loop through the default servers until OK or FAIL. Use local_servers list - * if defined in the lookup, otherwise use the global default list */ - list = !local_servers ? eldap_default_servers : local_servers; --while ((server = string_nextinlist(&list, &sep, buffer, sizeof(buffer)))) -+while ((server = string_nextinlist(&list, &sep, NULL, 0))) - { - int rc; - int port = 0; --- -2.29.2 - diff --git a/mail/exim/files/patch-z0042-Pass-authenticator-pubname-through-spool.-Bug-2648 b/mail/exim/files/patch-z0042-Pass-authenticator-pubname-through-spool.-Bug-2648 deleted file mode 100644 index 365d36034fd0..000000000000 --- a/mail/exim/files/patch-z0042-Pass-authenticator-pubname-through-spool.-Bug-2648 +++ /dev/null @@ -1,107 +0,0 @@ -From a3ab48f23ee4a83f796440ef67d7ac7b43aad4b5 Mon Sep 17 00:00:00 2001 -From: Jeremy Harris <jgh146exb@wizmail.org> -Date: Sat, 31 Oct 2020 23:58:11 +0000 -Subject: [PATCH 42/42] Pass authenticator pubname through spool. Bug 2648 - -(cherry picked from commit a75ebe0dcc5faeb915cacb0d9db66d2475789116) ---- - doc/ChangeLog | 4 ++++ - exim_monitor/em_globals.c | 1 + - src/smtp_in.c | 12 +++++++----- - src/spool_in.c | 4 +++- - src/spool_out.c | 6 ++++-- - -diff --git doc/ChangeLog doc/ChangeLog -index 9924fca5c..4759e018e 100644 ---- doc/ChangeLog -+++ doc/ChangeLog -@@ -107,6 +107,10 @@ JH/26 Bug 2646: fix a memory usage issue in ldap lookups. Previously, when more - details, an internal consistency trap could be hit while walking the list - of servers. - -+JH/27 Bug 2648: fix the passing of an authenticator public-name through spool -+ files. The value is used by the authresults expansion item. Previously -+ if this was used in a router or transport, a crash could result. -+ - - Exim version 4.94 - ----------------- -diff --git exim_monitor/em_globals.c exim_monitor/em_globals.c -index 925e88e05..30d22b5eb 100644 ---- exim_monitor/em_globals.c -+++ exim_monitor/em_globals.c -@@ -205,6 +205,7 @@ uschar *sender_address = NULL; - uschar *sender_fullhost = NULL; - uschar *sender_helo_name = NULL; - uschar *sender_host_address = NULL; -+uschar *sender_host_auth_pubname = NULL; - uschar *sender_host_authenticated = NULL; - uschar *sender_host_name = NULL; - int sender_host_port = 0; -diff --git src/smtp_in.c src/smtp_in.c -index a13f0ed63..f53c3cf65 100644 ---- src/smtp_in.c -+++ src/smtp_in.c -@@ -5935,12 +5935,14 @@ if (!sender_host_authenticated) - - g = string_append(g, 2, US";\n\tauth=pass (", sender_host_auth_pubname); - --if (Ustrcmp(sender_host_auth_pubname, "tls") != 0) -- g = string_append(g, 2, US") smtp.auth=", authenticated_id); --else if (authenticated_id) -- g = string_append(g, 2, US") x509.auth=", authenticated_id); -+if (Ustrcmp(sender_host_auth_pubname, "tls") == 0) -+ g = authenticated_id -+ ? string_append(g, 2, US") x509.auth=", authenticated_id) -+ : string_cat(g, US") reason=x509.auth"); - else -- g = string_catn(g, US") reason=x509.auth", 17); -+ g = authenticated_id -+ ? string_append(g, 2, US") smtp.auth=", authenticated_id) -+ : string_cat(g, US", no id saved)"); - - if (authenticated_sender) - g = string_append(g, 2, US" smtp.mailfrom=", authenticated_sender); -diff --git src/spool_in.c src/spool_in.c -index 1b4cefdb2..35e44df26 100644 ---- src/spool_in.c -+++ src/spool_in.c -@@ -253,7 +253,7 @@ sender_helo_name = NULL; - sender_host_address = NULL; - sender_host_name = NULL; - sender_host_port = 0; --sender_host_authenticated = NULL; -+sender_host_authenticated = sender_host_auth_pubname = NULL; - sender_ident = NULL; - f.sender_local = FALSE; - f.sender_set_untrusted = FALSE; -@@ -580,6 +580,8 @@ for (;;) - host_lookup_deferred = TRUE; - else if (Ustrcmp(p, "ost_lookup_failed") == 0) - host_lookup_failed = TRUE; -+ else if (Ustrncmp(p, "ost_auth_pubname", 16) == 0) -+ sender_host_auth_pubname = string_copy_taint(var + 18, tainted); - else if (Ustrncmp(p, "ost_auth", 8) == 0) - sender_host_authenticated = string_copy_taint(var + 10, tainted); - else if (Ustrncmp(p, "ost_name", 8) == 0) -diff --git src/spool_out.c src/spool_out.c -index 4b6539ecd..0851ce956 100644 ---- src/spool_out.c -+++ src/spool_out.c -@@ -174,9 +174,11 @@ if (sender_host_address) - fprintf(fp, "-host_address %s.%d\n", sender_host_address, sender_host_port); - if (sender_host_name) - spool_var_write(fp, US"host_name", sender_host_name); -- if (sender_host_authenticated) -- spool_var_write(fp, US"host_auth", sender_host_authenticated); - } -+if (sender_host_authenticated) -+ spool_var_write(fp, US"host_auth", sender_host_authenticated); -+if (sender_host_auth_pubname) -+ spool_var_write(fp, US"host_auth_pubname", sender_host_auth_pubname); - - /* Also about the interface a message came in on */ - --- -2.29.2 - diff --git a/mail/exim/options b/mail/exim/options index e00299182e54..56d828faa1c3 100644 --- a/mail/exim/options +++ b/mail/exim/options @@ -18,6 +18,7 @@ OPTIONS_DEFINE+= ALT_CONFIG_PREFIX \ PRDR \ READLINE \ SUID \ + TAINTWARN \ TCP_WRAPPERS \ WISHLIST \ EVENT \ @@ -125,6 +126,7 @@ SPF_DESC= Enable Sender Policy Framework checking SQLITE_DESC= Enable SQLite lookups SRS_DESC= Enable Sender Rewriting Scheme SUID_DESC= Install the exim binary suid root +TAINTWARN_DESC= Allow insecure tainted data (pre-4.93 config style, deprecated) TCP_WRAPPERS_DESC= Enable /etc/hosts.allow access control GNUTLS_DESC= Use GnuTLS instead of OpenSSL for TLS WISHLIST_DESC= Include the unsupported patches |