2
0
mirror of https://github.com/vdukhovni/postfix synced 2025-08-29 13:18:12 +00:00

postfix-3.5.18

This commit is contained in:
Wietse Venema 2023-01-21 00:00:00 -05:00 committed by Viktor Dukhovni
parent 265b67ac9e
commit cc9e59f707
15 changed files with 179 additions and 40 deletions

View File

@ -25156,3 +25156,62 @@ Apologies for any names omitted.
Cleanup: Postfix 3.5.16 introduced a missing msg_panic() Cleanup: Postfix 3.5.16 introduced a missing msg_panic()
argument (in code that never executes). File: argument (in code that never executes). File:
cleanup/cleanup_milter.c. cleanup/cleanup_milter.c.
20221128
Bugfix (introduced: Postfix 2.2): the smtpd_proxy_client
code mis-parsed the last XFORWARD attribute name in the
SMTP server's EHLO response. The result was that the
smtpd_proxy_client code failed to forward the IDENT attribute.
Fix by Andreas Weigel. File: smtpd/smtpd_proxy.c.
20221201
Portability: LINUX6 support. Files: makedefs, util/sys_defs.h.
20221207
Workaround: OpenSSL 3.x EVP_get_digestbyname() can return
lazily bound handles that may fail to work when one attempts
to use them, because no provider search happens until one
constructs an actual operation context. In sufficiently
hostile configurations, Postfix could mistakenly believe
that an algorithm is available, when in fact it is not. A
similar workaround may be needed for EVP_get_cipherbyname().
Fix by Viktor Dukhovni. Files: tls/tls.h, tls/tls_dane.c,
tls/tls_fprint.c, tls/tls_misc.c.
Bugfix (introduced: Postfix 2.11): the checkok() macro in
tls/tls_fprint.c evaluated its argument unconditionally;
it should evaluate the argument only if there was no prior
error. Found during code review. File: tls/tls_fprint.c.
20221215
Foolproofing: postscreen segfault with postscreen_dnsbl_threshold
< 1. It should reject such input with a fatal error instead.
Discovered by Benny Pedersen. File: postscreen/postscreen.c.
20230103
Bugfix (introduced: Postfix 2.7): the verify daemon logged
a garbled cache name when terminating a cache scan in
progress. Reported by Phil Biggs, fix by Viktor Dukhovni.
File: util/dict_cache.c.
Bitrot: fixes for linker warnings from newer Darwin (MacOS)
versions. Viktor Dukhovni. File: makedefs.
20230115
Workaround: STRREF() macro to shut up compiler warnings for
legitimate string comparison expressions. Back-ported from
Postfix 3.6 and later. Files: util/stringops.h, flush/flush.c.
Workaround for a breaking change in OpenSSL 3: always turn
on SSL_OP_IGNORE_UNEXPECTED_EOF, to avoid warning messages
and missed opportunities for TLS session reuse. This is
safe because the SMTP protocol implements application-level
framing, and is therefore not affected by TLS truncation
attacks. Fix by Viktor Dukhovni. Files: tls/tls.h, tls_client.c,
tls/tls_server.c.

View File

@ -557,7 +557,7 @@ EOF
: ${SHLIB_ENV="LD_LIBRARY_PATH=`pwd`/lib"} : ${SHLIB_ENV="LD_LIBRARY_PATH=`pwd`/lib"}
: ${PLUGIN_LD="${CC-gcc} -shared"} : ${PLUGIN_LD="${CC-gcc} -shared"}
;; ;;
Linux.[345].*) SYSTYPE=LINUX$RELEASE_MAJOR Linux.[3456].*) SYSTYPE=LINUX$RELEASE_MAJOR
case "$CCARGS" in case "$CCARGS" in
*-DNO_DB*) ;; *-DNO_DB*) ;;
*-DHAS_DB*) ;; *-DHAS_DB*) ;;
@ -699,6 +699,12 @@ ReliantUNIX-?.5.43) SYSTYPE=ReliantUnix543
?.*|10.*) ;; ?.*|10.*) ;;
*) SYSLIBS="$SYSLIBS -lresolv";; *) SYSLIBS="$SYSLIBS -lresolv";;
esac esac
# Darwin 21 linker without additional coaxing complains about
# -Wl,-undefined,dynamic_lookup
case $RELEASE in
2[1-9].*|[3-9]?.*) NOFIXUP="-Wl,-no_fixup_chains ";;
*) NOFIXUP="";;
esac
# kqueue and/or poll are broken in MacOS X 10.5 (Darwin 9). # kqueue and/or poll are broken in MacOS X 10.5 (Darwin 9).
# kqueue works in Mac OS X 10.8 (Darwin 12). # kqueue works in Mac OS X 10.8 (Darwin 12).
case $RELEASE in case $RELEASE in
@ -706,12 +712,12 @@ ReliantUNIX-?.5.43) SYSTYPE=ReliantUnix543
esac esac
: ${SHLIB_CFLAGS=-fPIC} : ${SHLIB_CFLAGS=-fPIC}
: ${SHLIB_SUFFIX=.dylib} : ${SHLIB_SUFFIX=.dylib}
: ${SHLIB_LD='cc -shared -Wl,-flat_namespace -Wl,-undefined,dynamic_lookup -Wl,-install_name,@rpath/${LIB}'} : ${SHLIB_LD="cc -shared -Wl,-flat_namespace ${NOFIXUP}-Wl,-undefined,dynamic_lookup "'-Wl,-install_name,@rpath/${LIB}'}
: ${SHLIB_RPATH='-Wl,-rpath,${SHLIB_DIR}'} : ${SHLIB_RPATH='-Wl,-rpath,${SHLIB_DIR}'}
# In MacOS/X 10.11.x /bin/sh unsets DYLD_LIBRARY_PATH, so we # In MacOS/X 10.11.x /bin/sh unsets DYLD_LIBRARY_PATH, so we
# have export it into postfix-install indirectly! # have export it into postfix-install indirectly!
: ${SHLIB_ENV="DYLD_LIBRARY_PATH=`pwd`/lib SHLIB_ENV_VAR=DYLD_LIBRARY_PATH SHLIB_ENV_VAL=`pwd`/lib"} : ${SHLIB_ENV="DYLD_LIBRARY_PATH=`pwd`/lib SHLIB_ENV_VAR=DYLD_LIBRARY_PATH SHLIB_ENV_VAL=`pwd`/lib"}
: ${PLUGIN_LD='cc -shared -Wl,-flat_namespace -Wl,-undefined,dynamic_lookup'} : ${PLUGIN_LD="cc -shared -Wl,-flat_namespace ${NOFIXUP}-Wl,-undefined,dynamic_lookup"}
;; ;;
dcosx.1*) SYSTYPE=DCOSX1 dcosx.1*) SYSTYPE=DCOSX1
RANLIB=echo RANLIB=echo

View File

@ -229,7 +229,7 @@ static DOMAIN_LIST *flush_domains;
* Silly little macros. * Silly little macros.
*/ */
#define STR(x) vstring_str(x) #define STR(x) vstring_str(x)
#define STREQ(x,y) ((x) == (y) || strcmp(x,y) == 0) #define STREQ(x,y) (STRREF(x) == STRREF(y) || strcmp(x,y) == 0)
/* /*
* Forward declarations resulting from breaking up routines according to * Forward declarations resulting from breaking up routines according to

View File

@ -20,8 +20,8 @@
* Patches change both the patchlevel and the release date. Snapshots have no * Patches change both the patchlevel and the release date. Snapshots have no
* patchlevel; they change the release date only. * patchlevel; they change the release date only.
*/ */
#define MAIL_RELEASE_DATE "20221007" #define MAIL_RELEASE_DATE "20230121"
#define MAIL_VERSION_NUMBER "3.5.17" #define MAIL_VERSION_NUMBER "3.5.18"
#ifdef SNAPSHOT #ifdef SNAPSHOT
#define MAIL_VERSION_DATE "-" MAIL_RELEASE_DATE #define MAIL_VERSION_DATE "-" MAIL_RELEASE_DATE

View File

@ -1141,7 +1141,7 @@ int main(int argc, char **argv)
0, 0,
}; };
static const CONFIG_INT_TABLE int_table[] = { static const CONFIG_INT_TABLE int_table[] = {
VAR_PSC_DNSBL_THRESH, DEF_PSC_DNSBL_THRESH, &var_psc_dnsbl_thresh, 0, 0, VAR_PSC_DNSBL_THRESH, DEF_PSC_DNSBL_THRESH, &var_psc_dnsbl_thresh, 1, 0,
VAR_PSC_DNSBL_WTHRESH, DEF_PSC_DNSBL_WTHRESH, &var_psc_dnsbl_wthresh, 0, 0, VAR_PSC_DNSBL_WTHRESH, DEF_PSC_DNSBL_WTHRESH, &var_psc_dnsbl_wthresh, 0, 0,
VAR_PSC_CMD_COUNT, DEF_PSC_CMD_COUNT, &var_psc_cmd_count, 1, 0, VAR_PSC_CMD_COUNT, DEF_PSC_CMD_COUNT, &var_psc_cmd_count, 1, 0,
VAR_SMTPD_CCONN_LIMIT, DEF_SMTPD_CCONN_LIMIT, &var_smtpd_cconn_limit, 0, 0, VAR_SMTPD_CCONN_LIMIT, DEF_SMTPD_CCONN_LIMIT, &var_smtpd_cconn_limit, 0, 0,

View File

@ -388,7 +388,7 @@ static int smtpd_proxy_connect(SMTPD_STATE *state)
*/ */
server_xforward_features = 0; server_xforward_features = 0;
lines = STR(proxy->reply); lines = STR(proxy->reply);
while ((words = mystrtok(&lines, "\n")) != 0) { while ((words = mystrtok(&lines, "\r\n")) != 0) {
if (mystrtok(&words, "- ") && (word = mystrtok(&words, " \t")) != 0) { if (mystrtok(&words, "- ") && (word = mystrtok(&words, " \t")) != 0) {
if (strcasecmp(word, XFORWARD_CMD) == 0) if (strcasecmp(word, XFORWARD_CMD) == 0)
while ((word = mystrtok(&words, " \t")) != 0) while ((word = mystrtok(&words, " \t")) != 0)

View File

@ -415,6 +415,13 @@ extern void tls_param_init(void);
#define SSL_OP_NO_TLSv1_3 0L /* Noop */ #define SSL_OP_NO_TLSv1_3 0L /* Noop */
#endif #endif
/*
* Always used when defined, SMTP has no truncation attacks.
*/
#ifndef SSL_OP_IGNORE_UNEXPECTED_EOF
#define SSL_OP_IGNORE_UNEXPECTED_EOF 0L
#endif
#define TLS_KNOWN_PROTOCOLS \ #define TLS_KNOWN_PROTOCOLS \
( TLS_PROTOCOL_SSLv2 | TLS_PROTOCOL_SSLv3 | TLS_PROTOCOL_TLSv1 \ ( TLS_PROTOCOL_SSLv2 | TLS_PROTOCOL_SSLv3 | TLS_PROTOCOL_TLSv1 \
| TLS_PROTOCOL_TLSv1_1 | TLS_PROTOCOL_TLSv1_2 | TLS_PROTOCOL_TLSv1_3 ) | TLS_PROTOCOL_TLSv1_1 | TLS_PROTOCOL_TLSv1_2 | TLS_PROTOCOL_TLSv1_3 )
@ -431,7 +438,8 @@ extern void tls_param_init(void);
* just exposed via hex codes or named elements of tls_ssl_options. * just exposed via hex codes or named elements of tls_ssl_options.
*/ */
#define TLS_SSL_OP_MANAGED_BITS \ #define TLS_SSL_OP_MANAGED_BITS \
(SSL_OP_CIPHER_SERVER_PREFERENCE | TLS_SSL_OP_PROTOMASK(~0)) (SSL_OP_CIPHER_SERVER_PREFERENCE | SSL_OP_IGNORE_UNEXPECTED_EOF | \
TLS_SSL_OP_PROTOMASK(~0))
extern int tls_protocol_mask(const char *); extern int tls_protocol_mask(const char *);
@ -679,6 +687,7 @@ extern void tls_dane_set_callback(SSL_CTX *, TLS_SESS_STATE *);
/* /*
* tls_fprint.c * tls_fprint.c
*/ */
extern const EVP_MD *tls_digest_byname(const char *, EVP_MD_CTX **);
extern char *tls_digest_encode(const unsigned char *, int); extern char *tls_digest_encode(const unsigned char *, int);
extern char *tls_data_fprint(const char *, int, const char *); extern char *tls_data_fprint(const char *, int, const char *);
extern char *tls_cert_fprint(X509 *, const char *); extern char *tls_cert_fprint(X509 *, const char *);

View File

@ -402,6 +402,15 @@ TLS_APPL_STATE *tls_client_init(const TLS_CLIENT_INIT_PROPS *props)
*/ */
SSL_CTX_set_verify_depth(client_ctx, props->verifydepth + 1); SSL_CTX_set_verify_depth(client_ctx, props->verifydepth + 1);
/*
* Presently we use TLS only with SMTP where truncation attacks are not
* possible as a result of application framing. If we ever use TLS in
* some other application protocol where truncation could be relevant,
* we'd need to disable truncation detection conditionally, or explicitly
* clear the option in that code path.
*/
off |= SSL_OP_IGNORE_UNEXPECTED_EOF;
/* /*
* Protocol selection is destination dependent, so we delay the protocol * Protocol selection is destination dependent, so we delay the protocol
* selection options to the per-session SSL object. * selection options to the per-session SSL object.

View File

@ -344,7 +344,7 @@ static dane_digest *add_digest(char *mdalg, int pref)
} }
if (*dane_mdalg if (*dane_mdalg
&& ((md = EVP_get_digestbyname(dane_mdalg)) == 0 && ((md = tls_digest_byname(dane_mdalg, NULL)) == 0
|| (mdlen = EVP_MD_size(md)) <= 0 || (mdlen = EVP_MD_size(md)) <= 0
|| mdlen > EVP_MAX_MD_SIZE)) { || mdlen > EVP_MAX_MD_SIZE)) {
msg_warn("Unimplemented digest algorithm in %s: %s%s%s", msg_warn("Unimplemented digest algorithm in %s: %s%s%s",

View File

@ -6,6 +6,10 @@
/* SYNOPSIS /* SYNOPSIS
/* #include <tls.h> /* #include <tls.h>
/* /*
/* EVP_MD *tls_digest_byname(const char *mdalg, EVP_MD_CTX **mdctxPtr)
/* const char *mdalg;
/* EVP_MD_CTX **mdctxPtr;
/*
/* char *tls_serverid_digest(props, protomask, ciphers) /* char *tls_serverid_digest(props, protomask, ciphers)
/* const TLS_CLIENT_START_PROPS *props; /* const TLS_CLIENT_START_PROPS *props;
/* long protomask; /* long protomask;
@ -28,6 +32,13 @@
/* X509 *peercert; /* X509 *peercert;
/* const char *mdalg; /* const char *mdalg;
/* DESCRIPTION /* DESCRIPTION
/* tls_digest_byname() constructs, and optionally returns, an EVP_MD_CTX
/* handle for performing digest operations with the algorithm named by the
/* mdalg parameter. The return value is non-null on success, and holds a
/* digest algorithm handle. If the mdctxPtr argument is non-null the
/* created context is returned to the caller, who is then responsible for
/* deleting it by calling EVP_MD_ctx_free() once it is no longer needed.
/*
/* tls_digest_encode() converts a binary message digest to a hex ASCII /* tls_digest_encode() converts a binary message digest to a hex ASCII
/* format with ':' separators between each pair of hex digits. /* format with ':' separators between each pair of hex digits.
/* The return value is dynamically allocated with mymalloc(), /* The return value is dynamically allocated with mymalloc(),
@ -61,6 +72,8 @@
/* and the caller must eventually free it with myfree(). /* and the caller must eventually free it with myfree().
/* /*
/* Arguments: /* Arguments:
/* .IP mdalg
/* A digest algorithm name, such as "sha256".
/* .IP peercert /* .IP peercert
/* Server or client X.509 certificate. /* Server or client X.509 certificate.
/* .IP md_buf /* .IP md_buf
@ -71,6 +84,9 @@
/* Name of a message digest algorithm suitable for computing secure /* Name of a message digest algorithm suitable for computing secure
/* (1st pre-image resistant) message digests of certificates. For now, /* (1st pre-image resistant) message digests of certificates. For now,
/* md5, sha1, or member of SHA-2 family if supported by OpenSSL. /* md5, sha1, or member of SHA-2 family if supported by OpenSSL.
/* .IP mdctxPtr
/* Pointer to an (EVP_MD_CTX *) handle, or NULL if only probing for
/* algorithm support without immediate use in mind.
/* .IP buf /* .IP buf
/* Input data for the message digest algorithm mdalg. /* Input data for the message digest algorithm mdalg.
/* .IP len /* .IP len
@ -125,7 +141,7 @@
static const char hexcodes[] = "0123456789ABCDEF"; static const char hexcodes[] = "0123456789ABCDEF";
#define checkok(ret) (ok &= ((ret) ? 1 : 0)) #define checkok(stillok) (ok = ok && (stillok))
#define digest_data(p, l) checkok(EVP_DigestUpdate(mdctx, (char *)(p), (l))) #define digest_data(p, l) checkok(EVP_DigestUpdate(mdctx, (char *)(p), (l)))
#define digest_object(p) digest_data((p), sizeof(*(p))) #define digest_object(p) digest_data((p), sizeof(*(p)))
#define digest_string(s) digest_data((s), strlen(s)+1) #define digest_string(s) digest_data((s), strlen(s)+1)
@ -159,13 +175,50 @@ static int digest_tlsa_usage(EVP_MD_CTX * mdctx, TLS_TLSA *tlsa,
return (ok); return (ok);
} }
/* tls_digest_byname - test availability or prepare to use digest */
const EVP_MD *tls_digest_byname(const char *mdalg, EVP_MD_CTX **mdctxPtr)
{
const EVP_MD *md;
EVP_MD_CTX *mdctx = NULL;
int ok = 1;
/*
* In OpenSSL 3.0, because of dynamically variable algorithm providers,
* there is a time-of-check/time-of-use issue that means that abstract
* algorithm handles returned by EVP_get_digestbyname() can (and not
* infrequently do) return ultimately unusable algorithms, to check for
* actual availability, one needs to use the new EVP_MD_fetch() API, or
* indirectly check usability by creating a concrete context. We take the
* latter approach here (works for 1.1.1 without #ifdef).
*
* Note that EVP_MD_CTX_{create,destroy} were renamed to, respectively,
* EVP_MD_CTX_{new,free} in OpenSSL 1.1.0.
*/
checkok(md = EVP_get_digestbyname(mdalg));
/*
* Sanity check: Newer shared libraries could (hypothetical ABI break)
* allow larger digests, we avoid such poison algorithms.
*/
checkok(EVP_MD_size(md) <= EVP_MAX_MD_SIZE);
checkok(mdctx = EVP_MD_CTX_new());
checkok(EVP_DigestInit_ex(mdctx, md, NULL));
if (ok && mdctxPtr != 0)
*mdctxPtr = mdctx;
else
EVP_MD_CTX_free(mdctx);
return (ok ? md : 0);
}
/* tls_serverid_digest - suffix props->serverid with parameter digest */ /* tls_serverid_digest - suffix props->serverid with parameter digest */
char *tls_serverid_digest(const TLS_CLIENT_START_PROPS *props, long protomask, char *tls_serverid_digest(const TLS_CLIENT_START_PROPS *props, long protomask,
const char *ciphers) const char *ciphers)
{ {
EVP_MD_CTX *mdctx; EVP_MD_CTX *mdctx;
const EVP_MD *md;
const char *mdalg; const char *mdalg;
unsigned char md_buf[EVP_MAX_MD_SIZE]; unsigned char md_buf[EVP_MAX_MD_SIZE];
unsigned int md_len; unsigned int md_len;
@ -181,17 +234,17 @@ char *tls_serverid_digest(const TLS_CLIENT_START_PROPS *props, long protomask,
* default digest, but DANE requires sha256 and sha512, so if we must * default digest, but DANE requires sha256 and sha512, so if we must
* fall back to our default digest, DANE support won't be available. We * fall back to our default digest, DANE support won't be available. We
* panic if the fallback algorithm is not available, as it was verified * panic if the fallback algorithm is not available, as it was verified
* available in tls_client_init() and must not simply vanish. * available in tls_client_init() and must not simply vanish. Our
* provider set is not expected to change once the OpenSSL library is
* initialized.
*/ */
if ((md = EVP_get_digestbyname(mdalg = "sha256")) == 0 if (tls_digest_byname(mdalg = LN_sha256, &mdctx) == 0
&& (md = EVP_get_digestbyname(mdalg = props->mdalg)) == 0) && tls_digest_byname(mdalg = props->mdalg, &mdctx) == 0)
msg_panic("digest algorithm \"%s\" not found", mdalg); msg_panic("digest algorithm \"%s\" not found", props->mdalg);
/* Salt the session lookup key with the OpenSSL runtime version. */ /* Salt the session lookup key with the OpenSSL runtime version. */
sslversion = OpenSSL_version_num(); sslversion = OpenSSL_version_num();
mdctx = EVP_MD_CTX_create();
checkok(EVP_DigestInit_ex(mdctx, md, NULL));
digest_string(props->helo ? props->helo : ""); digest_string(props->helo ? props->helo : "");
digest_object(&sslversion); digest_object(&sslversion);
digest_object(&protomask); digest_object(&protomask);
@ -284,18 +337,15 @@ char *tls_digest_encode(const unsigned char *md_buf, int md_len)
char *tls_data_fprint(const char *buf, int len, const char *mdalg) char *tls_data_fprint(const char *buf, int len, const char *mdalg)
{ {
EVP_MD_CTX *mdctx; EVP_MD_CTX *mdctx = NULL;
const EVP_MD *md;
unsigned char md_buf[EVP_MAX_MD_SIZE]; unsigned char md_buf[EVP_MAX_MD_SIZE];
unsigned int md_len; unsigned int md_len;
int ok = 1; int ok = 1;
/* Previously available in "init" routine. */ /* Previously available in "init" routine. */
if ((md = EVP_get_digestbyname(mdalg)) == 0) if (tls_digest_byname(mdalg, &mdctx) == 0)
msg_panic("digest algorithm \"%s\" not found", mdalg); msg_panic("digest algorithm \"%s\" not found", mdalg);
mdctx = EVP_MD_CTX_create();
checkok(EVP_DigestInit_ex(mdctx, md, NULL));
digest_data(buf, len); digest_data(buf, len);
checkok(EVP_DigestFinal_ex(mdctx, md_buf, &md_len)); checkok(EVP_DigestFinal_ex(mdctx, md_buf, &md_len));
EVP_MD_CTX_destroy(mdctx); EVP_MD_CTX_destroy(mdctx);

View File

@ -1515,7 +1515,6 @@ long tls_bio_dump_cb(BIO *bio, int cmd, const char *argp, int argi,
int tls_validate_digest(const char *dgst) int tls_validate_digest(const char *dgst)
{ {
const EVP_MD *md_alg; const EVP_MD *md_alg;
unsigned int md_len;
/* /*
* Register SHA-2 digests, if implemented and not already registered. * Register SHA-2 digests, if implemented and not already registered.
@ -1523,15 +1522,15 @@ int tls_validate_digest(const char *dgst)
* deploy SHA-2 certificates. Also facilitates DANE and TA support. * deploy SHA-2 certificates. Also facilitates DANE and TA support.
*/ */
#if defined(LN_sha256) && defined(NID_sha256) && !defined(OPENSSL_NO_SHA256) #if defined(LN_sha256) && defined(NID_sha256) && !defined(OPENSSL_NO_SHA256)
if (!EVP_get_digestbyname(LN_sha224)) if (!tls_digest_byname(LN_sha224, NULL))
EVP_add_digest(EVP_sha224()); EVP_add_digest(EVP_sha224());
if (!EVP_get_digestbyname(LN_sha256)) if (!tls_digest_byname(LN_sha256, NULL))
EVP_add_digest(EVP_sha256()); EVP_add_digest(EVP_sha256());
#endif #endif
#if defined(LN_sha512) && defined(NID_sha512) && !defined(OPENSSL_NO_SHA512) #if defined(LN_sha512) && defined(NID_sha512) && !defined(OPENSSL_NO_SHA512)
if (!EVP_get_digestbyname(LN_sha384)) if (!tls_digest_byname(LN_sha384, NULL))
EVP_add_digest(EVP_sha384()); EVP_add_digest(EVP_sha384());
if (!EVP_get_digestbyname(LN_sha512)) if (!tls_digest_byname(LN_sha512, NULL))
EVP_add_digest(EVP_sha512()); EVP_add_digest(EVP_sha512());
#endif #endif
@ -1539,19 +1538,10 @@ int tls_validate_digest(const char *dgst)
* If the administrator specifies an unsupported digest algorithm, fail * If the administrator specifies an unsupported digest algorithm, fail
* now, rather than in the middle of a TLS handshake. * now, rather than in the middle of a TLS handshake.
*/ */
if ((md_alg = EVP_get_digestbyname(dgst)) == 0) { if ((md_alg = tls_digest_byname(dgst, NULL)) == 0) {
msg_warn("Digest algorithm \"%s\" not found", dgst); msg_warn("Digest algorithm \"%s\" not found", dgst);
return (0); return (0);
} }
/*
* Sanity check: Newer shared libraries may use larger digests.
*/
if ((md_len = EVP_MD_size(md_alg)) > EVP_MAX_MD_SIZE) {
msg_warn("Digest algorithm \"%s\" output size %u too large",
dgst, md_len);
return (0);
}
return (1); return (1);
} }

View File

@ -477,6 +477,15 @@ TLS_APPL_STATE *tls_server_init(const TLS_SERVER_INIT_PROPS *props)
if (scache_timeout <= 0) if (scache_timeout <= 0)
cachable = 0; cachable = 0;
/*
* Presently we use TLS only with SMTP where truncation attacks are not
* possible as a result of application framing. If we ever use TLS in
* some other application protocol where truncation could be relevant,
* we'd need to disable truncation detection conditionally, or explicitly
* clear the option in that code path.
*/
off |= SSL_OP_IGNORE_UNEXPECTED_EOF;
/* /*
* Protocol work-arounds, OpenSSL version dependent. * Protocol work-arounds, OpenSSL version dependent.
*/ */

View File

@ -659,8 +659,8 @@ void dict_cache_close(DICT_CACHE *cp)
/* /*
* Destroy the DICT_CACHE object. * Destroy the DICT_CACHE object.
*/ */
myfree(cp->name);
dict_cache_control(cp, DICT_CACHE_CTL_INTERVAL, 0, DICT_CACHE_CTL_END); dict_cache_control(cp, DICT_CACHE_CTL_INTERVAL, 0, DICT_CACHE_CTL_END);
myfree(cp->name);
dict_close(cp->db); dict_close(cp->db);
if (cp->saved_curr_key) if (cp->saved_curr_key)
myfree(cp->saved_curr_key); myfree(cp->saved_curr_key);

View File

@ -80,6 +80,12 @@ extern int strncasecmp_utf8x(int, const char *, const char *, ssize_t);
#define strncasecmp_utf8(s1, s2, l) \ #define strncasecmp_utf8(s1, s2, l) \
strncasecmp_utf8x(util_utf8_enable ? CASEF_FLAG_UTF8 : 0, (s1), (s2), (l)) strncasecmp_utf8x(util_utf8_enable ? CASEF_FLAG_UTF8 : 0, (s1), (s2), (l))
/*
* Use STRREF(x) instead of x, to shut up compiler warnings when the operand
* is a string literal.
*/
#define STRREF(x) (&x[0])
/* LICENSE /* LICENSE
/* .ad /* .ad
/* .fi /* .fi

View File

@ -749,7 +749,8 @@ extern int initgroups(const char *, int);
/* /*
* LINUX. * LINUX.
*/ */
#if defined(LINUX2) || defined(LINUX3) || defined(LINUX4) || defined(LINUX5) #if defined(LINUX2) || defined(LINUX3) || defined(LINUX4) || defined(LINUX5) \
|| defined(LINUX6)
#define SUPPORTED #define SUPPORTED
#define UINT32_TYPE unsigned int #define UINT32_TYPE unsigned int
#define UINT16_TYPE unsigned short #define UINT16_TYPE unsigned short