diff --git a/lib/libcrypto/asn1/p5_pbev2.c b/lib/libcrypto/asn1/p5_pbev2.c index ebb20c296..76872a8de 100644 --- a/lib/libcrypto/asn1/p5_pbev2.c +++ b/lib/libcrypto/asn1/p5_pbev2.c @@ -1,4 +1,4 @@ -/* $OpenBSD: p5_pbev2.c,v 1.32 2024/03/02 10:17:37 tb Exp $ */ +/* $OpenBSD: p5_pbev2.c,v 1.35 2024/03/26 07:03:10 tb Exp $ */ /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL * project 1999-2004. */ @@ -177,17 +177,17 @@ PBKDF2PARAM_free(PBKDF2PARAM *a) ASN1_item_free((ASN1_VALUE *)a, &PBKDF2PARAM_it); } -/* Return an algorithm identifier for a PKCS#5 v2.0 PBE algorithm: +/* + * Return an algorithm identifier for a PKCS#5 v2.0 PBE algorithm: * yes I know this is horrible! - * - * Extended version to allow application supplied PRF NID and IV. */ X509_ALGOR * -PKCS5_pbe2_set_iv(const EVP_CIPHER *cipher, int iter, unsigned char *salt, - int saltlen, unsigned char *aiv, int prf_nid) +PKCS5_pbe2_set(const EVP_CIPHER *cipher, int iter, unsigned char *salt, + int saltlen) { X509_ALGOR *scheme = NULL, *kalg = NULL, *ret = NULL; + int prf_nid = NID_hmacWithSHA1; int alg_nid, keylen; EVP_CIPHER_CTX ctx; unsigned char iv[EVP_MAX_IV_LENGTH]; @@ -212,12 +212,8 @@ PKCS5_pbe2_set_iv(const EVP_CIPHER *cipher, int iter, unsigned char *salt, goto merr; /* Create random IV */ - if (EVP_CIPHER_iv_length(cipher)) { - if (aiv) - memcpy(iv, aiv, EVP_CIPHER_iv_length(cipher)); - else - arc4random_buf(iv, EVP_CIPHER_iv_length(cipher)); - } + if (EVP_CIPHER_iv_length(cipher) > 0) + arc4random_buf(iv, EVP_CIPHER_iv_length(cipher)); EVP_CIPHER_CTX_legacy_clear(&ctx); @@ -229,14 +225,6 @@ PKCS5_pbe2_set_iv(const EVP_CIPHER *cipher, int iter, unsigned char *salt, EVP_CIPHER_CTX_cleanup(&ctx); goto err; } - /* If prf NID unspecified see if cipher has a preference. - * An error is OK here: just means use default PRF. - */ - if ((prf_nid == -1) && - EVP_CIPHER_CTX_ctrl(&ctx, EVP_CTRL_PBE_PRF_NID, 0, &prf_nid) <= 0) { - ERR_clear_error(); - prf_nid = NID_hmacWithSHA1; - } EVP_CIPHER_CTX_cleanup(&ctx); /* If its RC2 then we'd better setup the key length */ @@ -287,13 +275,6 @@ PKCS5_pbe2_set_iv(const EVP_CIPHER *cipher, int iter, unsigned char *salt, return NULL; } -X509_ALGOR * -PKCS5_pbe2_set(const EVP_CIPHER *cipher, int iter, unsigned char *salt, - int saltlen) -{ - return PKCS5_pbe2_set_iv(cipher, iter, salt, saltlen, NULL, -1); -} - X509_ALGOR * PKCS5_pbkdf2_set(int iter, unsigned char *salt, int saltlen, int prf_nid, int keylen) diff --git a/lib/libcrypto/bio/bio_lib.c b/lib/libcrypto/bio/bio_lib.c index 2f490a42f..ba7153922 100644 --- a/lib/libcrypto/bio/bio_lib.c +++ b/lib/libcrypto/bio/bio_lib.c @@ -1,4 +1,4 @@ -/* $OpenBSD: bio_lib.c,v 1.52 2024/03/02 09:22:41 tb Exp $ */ +/* $OpenBSD: bio_lib.c,v 1.53 2024/03/27 01:22:30 tb Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -198,8 +198,7 @@ LCRYPTO_ALIAS(BIO_vfree); int BIO_up_ref(BIO *bio) { - int refs = CRYPTO_add(&bio->references, 1, CRYPTO_LOCK_BIO); - return (refs > 1) ? 1 : 0; + return CRYPTO_add(&bio->references, 1, CRYPTO_LOCK_BIO) > 1; } LCRYPTO_ALIAS(BIO_up_ref); diff --git a/lib/libcrypto/bn/arch/amd64/bn_arch.h b/lib/libcrypto/bn/arch/amd64/bn_arch.h index f3653bcc4..927cd7520 100644 --- a/lib/libcrypto/bn/arch/amd64/bn_arch.h +++ b/lib/libcrypto/bn/arch/amd64/bn_arch.h @@ -1,4 +1,4 @@ -/* $OpenBSD: bn_arch.h,v 1.13 2023/02/16 11:13:05 jsing Exp $ */ +/* $OpenBSD: bn_arch.h,v 1.14 2024/03/26 06:09:25 jsing Exp $ */ /* * Copyright (c) 2023 Joel Sing * @@ -42,6 +42,7 @@ #define HAVE_BN_WORD_CLZ #if defined(__GNUC__) + #define HAVE_BN_DIV_REM_WORDS_INLINE static inline void @@ -62,9 +63,7 @@ bn_div_rem_words_inline(BN_ULONG h, BN_ULONG l, BN_ULONG d, BN_ULONG *out_q, *out_q = q; *out_r = r; } -#endif /* __GNUC__ */ -#if defined(__GNUC__) #define HAVE_BN_MULW static inline void @@ -84,6 +83,26 @@ bn_mulw(BN_ULONG a, BN_ULONG b, BN_ULONG *out_r1, BN_ULONG *out_r0) *out_r1 = r1; *out_r0 = r0; } + +#define HAVE_BN_SUBW + +static inline void +bn_subw(BN_ULONG a, BN_ULONG b, BN_ULONG *out_borrow, BN_ULONG *out_r0) +{ + BN_ULONG borrow, r0; + + __asm__ ( + "subq %3, %1 \n" + "setb %b0 \n" + "and $1, %0 \n" + : "=r"(borrow), "=r"(r0) + : "1"(a), "rm"(b) + : "cc"); + + *out_borrow = borrow; + *out_r0 = r0; +} + #endif /* __GNUC__ */ #endif diff --git a/lib/libcrypto/bn/bn_mont.c b/lib/libcrypto/bn/bn_mont.c index 12fea44c5..c7e2eefb5 100644 --- a/lib/libcrypto/bn/bn_mont.c +++ b/lib/libcrypto/bn/bn_mont.c @@ -1,4 +1,4 @@ -/* $OpenBSD: bn_mont.c,v 1.61 2023/07/08 12:21:58 beck Exp $ */ +/* $OpenBSD: bn_mont.c,v 1.63 2024/03/26 04:23:04 jsing Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -299,219 +299,6 @@ BN_MONT_CTX_set_locked(BN_MONT_CTX **pmctx, int lock, const BIGNUM *mod, } LCRYPTO_ALIAS(BN_MONT_CTX_set_locked); -static int bn_montgomery_reduce(BIGNUM *ret, BIGNUM *r, BN_MONT_CTX *mctx); - -static int -bn_mod_mul_montgomery_simple(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, - BN_MONT_CTX *mctx, BN_CTX *ctx) -{ - BIGNUM *tmp; - int ret = 0; - - BN_CTX_start(ctx); - - if ((tmp = BN_CTX_get(ctx)) == NULL) - goto err; - - if (a == b) { - if (!BN_sqr(tmp, a, ctx)) - goto err; - } else { - if (!BN_mul(tmp, a, b, ctx)) - goto err; - } - - /* Reduce from aRR to aR. */ - if (!bn_montgomery_reduce(r, tmp, mctx)) - goto err; - - ret = 1; - err: - BN_CTX_end(ctx); - - return ret; -} - -static void -bn_montgomery_multiply_word(const BN_ULONG *ap, BN_ULONG b, const BN_ULONG *np, - BN_ULONG *tp, BN_ULONG w, BN_ULONG *carry_a, BN_ULONG *carry_n, int n_len) -{ - BN_ULONG x3, x2, x1, x0; - - *carry_a = *carry_n = 0; - - while (n_len & ~3) { - bn_qwmulw_addqw_addw(ap[3], ap[2], ap[1], ap[0], b, - tp[3], tp[2], tp[1], tp[0], *carry_a, carry_a, - &x3, &x2, &x1, &x0); - bn_qwmulw_addqw_addw(np[3], np[2], np[1], np[0], w, - x3, x2, x1, x0, *carry_n, carry_n, - &tp[3], &tp[2], &tp[1], &tp[0]); - ap += 4; - np += 4; - tp += 4; - n_len -= 4; - } - while (n_len > 0) { - bn_mulw_addw_addw(ap[0], b, tp[0], *carry_a, carry_a, &x0); - bn_mulw_addw_addw(np[0], w, x0, *carry_n, carry_n, &tp[0]); - ap++; - np++; - tp++; - n_len--; - } -} - -/* - * bn_montgomery_multiply_words() computes r = aR * bR * R^-1 = abR for the - * given word arrays. The caller must ensure that rp, ap, bp and np are all - * n_len words in length, while tp must be n_len * 2 + 2 words in length. - */ -void -bn_montgomery_multiply_words(BN_ULONG *rp, const BN_ULONG *ap, const BN_ULONG *bp, - const BN_ULONG *np, BN_ULONG *tp, BN_ULONG n0, int n_len) -{ - BN_ULONG a0, b, carry_a, carry_n, carry, mask, w; - int i; - - carry = 0; - - for (i = 0; i < n_len; i++) - tp[i] = 0; - - a0 = ap[0]; - - for (i = 0; i < n_len; i++) { - b = bp[i]; - - /* Compute new t[0] * n0, as we need it for this iteration. */ - w = (a0 * b + tp[0]) * n0; - - bn_montgomery_multiply_word(ap, b, np, tp, w, &carry_a, - &carry_n, n_len); - bn_addw_addw(carry_a, carry_n, carry, &carry, &tp[n_len]); - - tp++; - } - tp[n_len] = carry; - - /* - * The output is now in the range of [0, 2N). Attempt to reduce once by - * subtracting the modulus. If the reduction was necessary then the - * result is already in r, otherwise copy the value prior to reduction - * from tp. - */ - mask = bn_ct_ne_zero(tp[n_len]) - bn_sub_words(rp, tp, np, n_len); - - for (i = 0; i < n_len; i++) { - *rp = (*rp & ~mask) | (*tp & mask); - rp++; - tp++; - } -} - -/* - * bn_montgomery_multiply() computes r = aR * bR * R^-1 = abR for the given - * BIGNUMs. The caller must ensure that the modulus is two or more words in - * length and that a and b have the same number of words as the modulus. - */ -int -bn_montgomery_multiply(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, - BN_MONT_CTX *mctx, BN_CTX *ctx) -{ - BIGNUM *t; - int ret = 0; - - BN_CTX_start(ctx); - - if (mctx->N.top <= 1 || a->top != mctx->N.top || b->top != mctx->N.top) - goto err; - if (!bn_wexpand(r, mctx->N.top)) - goto err; - - if ((t = BN_CTX_get(ctx)) == NULL) - goto err; - if (!bn_wexpand(t, mctx->N.top * 2 + 2)) - goto err; - - bn_montgomery_multiply_words(r->d, a->d, b->d, mctx->N.d, t->d, - mctx->n0[0], mctx->N.top); - - r->top = mctx->N.top; - bn_correct_top(r); - - BN_set_negative(r, a->neg ^ b->neg); - - ret = 1; - err: - BN_CTX_end(ctx); - - return ret; -} - -#ifndef OPENSSL_BN_ASM_MONT -int -bn_mod_mul_montgomery(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, - BN_MONT_CTX *mctx, BN_CTX *ctx) -{ - if (mctx->N.top <= 1 || a->top != mctx->N.top || b->top != mctx->N.top) - return bn_mod_mul_montgomery_simple(r, a, b, mctx, ctx); - - return bn_montgomery_multiply(r, a, b, mctx, ctx); -} -#else - -int -bn_mod_mul_montgomery(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, - BN_MONT_CTX *mctx, BN_CTX *ctx) -{ - if (mctx->N.top <= 1 || a->top != mctx->N.top || b->top != mctx->N.top) - return bn_mod_mul_montgomery_simple(r, a, b, mctx, ctx); - - /* - * Legacy bn_mul_mont() performs stack based allocation, without - * size limitation. Allowing a large size results in the stack - * being blown. - */ - if (mctx->N.top > (8 * 1024 / sizeof(BN_ULONG))) - return bn_montgomery_multiply(r, a, b, mctx, ctx); - - if (!bn_wexpand(r, mctx->N.top)) - return 0; - - /* - * Legacy bn_mul_mont() can indicate that we should "fallback" to - * another implementation. - */ - if (!bn_mul_mont(r->d, a->d, b->d, mctx->N.d, mctx->n0, mctx->N.top)) - return bn_montgomery_multiply(r, a, b, mctx, ctx); - - r->top = mctx->N.top; - bn_correct_top(r); - - BN_set_negative(r, a->neg ^ b->neg); - - return (1); -} -#endif - -int -BN_mod_mul_montgomery(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, - BN_MONT_CTX *mctx, BN_CTX *ctx) -{ - /* Compute r = aR * bR * R^-1 mod N = abR mod N */ - return bn_mod_mul_montgomery(r, a, b, mctx, ctx); -} -LCRYPTO_ALIAS(BN_mod_mul_montgomery); - -int -BN_to_montgomery(BIGNUM *r, const BIGNUM *a, BN_MONT_CTX *mctx, BN_CTX *ctx) -{ - /* Compute r = a * R * R * R^-1 mod N = aR mod N */ - return bn_mod_mul_montgomery(r, a, &mctx->RR, mctx, ctx); -} -LCRYPTO_ALIAS(BN_to_montgomery); - /* * bn_montgomery_reduce() performs Montgomery reduction, reducing the input * from its Montgomery form aR to a, returning the result in r. Note that the @@ -583,6 +370,217 @@ bn_montgomery_reduce(BIGNUM *r, BIGNUM *a, BN_MONT_CTX *mctx) return 1; } +static int +bn_mod_mul_montgomery_simple(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, + BN_MONT_CTX *mctx, BN_CTX *ctx) +{ + BIGNUM *tmp; + int ret = 0; + + BN_CTX_start(ctx); + + if ((tmp = BN_CTX_get(ctx)) == NULL) + goto err; + + if (a == b) { + if (!BN_sqr(tmp, a, ctx)) + goto err; + } else { + if (!BN_mul(tmp, a, b, ctx)) + goto err; + } + + /* Reduce from aRR to aR. */ + if (!bn_montgomery_reduce(r, tmp, mctx)) + goto err; + + ret = 1; + err: + BN_CTX_end(ctx); + + return ret; +} + +static void +bn_montgomery_multiply_word(const BN_ULONG *ap, BN_ULONG b, const BN_ULONG *np, + BN_ULONG *tp, BN_ULONG w, BN_ULONG *carry_a, BN_ULONG *carry_n, int n_len) +{ + BN_ULONG x3, x2, x1, x0; + + *carry_a = *carry_n = 0; + + while (n_len & ~3) { + bn_qwmulw_addqw_addw(ap[3], ap[2], ap[1], ap[0], b, + tp[3], tp[2], tp[1], tp[0], *carry_a, carry_a, + &x3, &x2, &x1, &x0); + bn_qwmulw_addqw_addw(np[3], np[2], np[1], np[0], w, + x3, x2, x1, x0, *carry_n, carry_n, + &tp[3], &tp[2], &tp[1], &tp[0]); + ap += 4; + np += 4; + tp += 4; + n_len -= 4; + } + while (n_len > 0) { + bn_mulw_addw_addw(ap[0], b, tp[0], *carry_a, carry_a, &x0); + bn_mulw_addw_addw(np[0], w, x0, *carry_n, carry_n, &tp[0]); + ap++; + np++; + tp++; + n_len--; + } +} + +/* + * bn_montgomery_multiply_words() computes r = aR * bR * R^-1 = abR for the + * given word arrays. The caller must ensure that rp, ap, bp and np are all + * n_len words in length, while tp must be n_len * 2 + 2 words in length. + */ +static void +bn_montgomery_multiply_words(BN_ULONG *rp, const BN_ULONG *ap, const BN_ULONG *bp, + const BN_ULONG *np, BN_ULONG *tp, BN_ULONG n0, int n_len) +{ + BN_ULONG a0, b, carry_a, carry_n, carry, mask, w; + int i; + + carry = 0; + + for (i = 0; i < n_len; i++) + tp[i] = 0; + + a0 = ap[0]; + + for (i = 0; i < n_len; i++) { + b = bp[i]; + + /* Compute new t[0] * n0, as we need it for this iteration. */ + w = (a0 * b + tp[0]) * n0; + + bn_montgomery_multiply_word(ap, b, np, tp, w, &carry_a, + &carry_n, n_len); + bn_addw_addw(carry_a, carry_n, carry, &carry, &tp[n_len]); + + tp++; + } + tp[n_len] = carry; + + /* + * The output is now in the range of [0, 2N). Attempt to reduce once by + * subtracting the modulus. If the reduction was necessary then the + * result is already in r, otherwise copy the value prior to reduction + * from tp. + */ + mask = bn_ct_ne_zero(tp[n_len]) - bn_sub_words(rp, tp, np, n_len); + + for (i = 0; i < n_len; i++) { + *rp = (*rp & ~mask) | (*tp & mask); + rp++; + tp++; + } +} + +/* + * bn_montgomery_multiply() computes r = aR * bR * R^-1 = abR for the given + * BIGNUMs. The caller must ensure that the modulus is two or more words in + * length and that a and b have the same number of words as the modulus. + */ +static int +bn_montgomery_multiply(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, + BN_MONT_CTX *mctx, BN_CTX *ctx) +{ + BIGNUM *t; + int ret = 0; + + BN_CTX_start(ctx); + + if (mctx->N.top <= 1 || a->top != mctx->N.top || b->top != mctx->N.top) + goto err; + if (!bn_wexpand(r, mctx->N.top)) + goto err; + + if ((t = BN_CTX_get(ctx)) == NULL) + goto err; + if (!bn_wexpand(t, mctx->N.top * 2 + 2)) + goto err; + + bn_montgomery_multiply_words(r->d, a->d, b->d, mctx->N.d, t->d, + mctx->n0[0], mctx->N.top); + + r->top = mctx->N.top; + bn_correct_top(r); + + BN_set_negative(r, a->neg ^ b->neg); + + ret = 1; + err: + BN_CTX_end(ctx); + + return ret; +} + +#ifndef OPENSSL_BN_ASM_MONT +static int +bn_mod_mul_montgomery(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, + BN_MONT_CTX *mctx, BN_CTX *ctx) +{ + if (mctx->N.top <= 1 || a->top != mctx->N.top || b->top != mctx->N.top) + return bn_mod_mul_montgomery_simple(r, a, b, mctx, ctx); + + return bn_montgomery_multiply(r, a, b, mctx, ctx); +} +#else + +static int +bn_mod_mul_montgomery(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, + BN_MONT_CTX *mctx, BN_CTX *ctx) +{ + if (mctx->N.top <= 1 || a->top != mctx->N.top || b->top != mctx->N.top) + return bn_mod_mul_montgomery_simple(r, a, b, mctx, ctx); + + /* + * Legacy bn_mul_mont() performs stack based allocation, without + * size limitation. Allowing a large size results in the stack + * being blown. + */ + if (mctx->N.top > (8 * 1024 / sizeof(BN_ULONG))) + return bn_montgomery_multiply(r, a, b, mctx, ctx); + + if (!bn_wexpand(r, mctx->N.top)) + return 0; + + /* + * Legacy bn_mul_mont() can indicate that we should "fallback" to + * another implementation. + */ + if (!bn_mul_mont(r->d, a->d, b->d, mctx->N.d, mctx->n0, mctx->N.top)) + return bn_montgomery_multiply(r, a, b, mctx, ctx); + + r->top = mctx->N.top; + bn_correct_top(r); + + BN_set_negative(r, a->neg ^ b->neg); + + return (1); +} +#endif + +int +BN_mod_mul_montgomery(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, + BN_MONT_CTX *mctx, BN_CTX *ctx) +{ + /* Compute r = aR * bR * R^-1 mod N = abR mod N */ + return bn_mod_mul_montgomery(r, a, b, mctx, ctx); +} +LCRYPTO_ALIAS(BN_mod_mul_montgomery); + +int +BN_to_montgomery(BIGNUM *r, const BIGNUM *a, BN_MONT_CTX *mctx, BN_CTX *ctx) +{ + /* Compute r = a * R * R * R^-1 mod N = aR mod N */ + return bn_mod_mul_montgomery(r, a, &mctx->RR, mctx, ctx); +} +LCRYPTO_ALIAS(BN_to_montgomery); + int BN_from_montgomery(BIGNUM *r, const BIGNUM *a, BN_MONT_CTX *mctx, BN_CTX *ctx) { diff --git a/lib/libcrypto/crypto_internal.h b/lib/libcrypto/crypto_internal.h index e5742657d..5e21535f3 100644 --- a/lib/libcrypto/crypto_internal.h +++ b/lib/libcrypto/crypto_internal.h @@ -1,4 +1,4 @@ -/* $OpenBSD: crypto_internal.h,v 1.7 2023/08/15 08:39:27 jsing Exp $ */ +/* $OpenBSD: crypto_internal.h,v 1.8 2024/03/26 04:11:42 jsing Exp $ */ /* * Copyright (c) 2023 Joel Sing * @@ -92,7 +92,7 @@ crypto_store_htobe64(uint8_t *dst, uint64_t v) * unsigned host endian value, from the specified address in memory. The memory * address may have any alignment. */ -#ifndef HAVE_CRYPTO_LOAD_BE32TOH +#ifndef HAVE_CRYPTO_LOAD_LE32TOH static inline uint32_t crypto_load_le32toh(const uint8_t *src) { @@ -109,7 +109,7 @@ crypto_load_le32toh(const uint8_t *src) * unsigned little endian value, at the specified address in memory. The memory * address may have any alignment. */ -#ifndef HAVE_CRYPTO_STORE_HTOBE32 +#ifndef HAVE_CRYPTO_STORE_HTOLE32 static inline void crypto_store_htole32(uint8_t *dst, uint32_t v) { diff --git a/lib/libcrypto/dh/dh_lib.c b/lib/libcrypto/dh/dh_lib.c index d8698859f..86503bc4e 100644 --- a/lib/libcrypto/dh/dh_lib.c +++ b/lib/libcrypto/dh/dh_lib.c @@ -1,4 +1,4 @@ -/* $OpenBSD: dh_lib.c,v 1.43 2023/11/29 21:35:57 tb Exp $ */ +/* $OpenBSD: dh_lib.c,v 1.45 2024/03/27 01:26:30 tb Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -140,39 +140,35 @@ DH_new_method(ENGINE *engine) LCRYPTO_ALIAS(DH_new_method); void -DH_free(DH *r) +DH_free(DH *dh) { - int i; - - if (r == NULL) - return; - i = CRYPTO_add(&r->references, -1, CRYPTO_LOCK_DH); - if (i > 0) + if (dh == NULL) return; - if (r->meth != NULL && r->meth->finish != NULL) - r->meth->finish(r); + if (CRYPTO_add(&dh->references, -1, CRYPTO_LOCK_DH) > 0) + return; - CRYPTO_free_ex_data(CRYPTO_EX_INDEX_DH, r, &r->ex_data); + if (dh->meth != NULL && dh->meth->finish != NULL) + dh->meth->finish(dh); - BN_free(r->p); - BN_free(r->g); - BN_free(r->q); - BN_free(r->j); - free(r->seed); - BN_free(r->counter); - BN_free(r->pub_key); - BN_free(r->priv_key); - free(r); + CRYPTO_free_ex_data(CRYPTO_EX_INDEX_DH, dh, &dh->ex_data); + + BN_free(dh->p); + BN_free(dh->g); + BN_free(dh->q); + BN_free(dh->j); + free(dh->seed); + BN_free(dh->counter); + BN_free(dh->pub_key); + BN_free(dh->priv_key); + free(dh); } LCRYPTO_ALIAS(DH_free); int -DH_up_ref(DH *r) +DH_up_ref(DH *dh) { - int i = CRYPTO_add(&r->references, 1, CRYPTO_LOCK_DH); - - return i > 1 ? 1 : 0; + return CRYPTO_add(&dh->references, 1, CRYPTO_LOCK_DH) > 1; } LCRYPTO_ALIAS(DH_up_ref); @@ -186,16 +182,16 @@ DH_get_ex_new_index(long argl, void *argp, CRYPTO_EX_new *new_func, LCRYPTO_ALIAS(DH_get_ex_new_index); int -DH_set_ex_data(DH *d, int idx, void *arg) +DH_set_ex_data(DH *dh, int idx, void *arg) { - return CRYPTO_set_ex_data(&d->ex_data, idx, arg); + return CRYPTO_set_ex_data(&dh->ex_data, idx, arg); } LCRYPTO_ALIAS(DH_set_ex_data); void * -DH_get_ex_data(DH *d, int idx) +DH_get_ex_data(DH *dh, int idx) { - return CRYPTO_get_ex_data(&d->ex_data, idx); + return CRYPTO_get_ex_data(&dh->ex_data, idx); } LCRYPTO_ALIAS(DH_get_ex_data); diff --git a/lib/libcrypto/dsa/dsa_lib.c b/lib/libcrypto/dsa/dsa_lib.c index 65eb65288..daf2fa135 100644 --- a/lib/libcrypto/dsa/dsa_lib.c +++ b/lib/libcrypto/dsa/dsa_lib.c @@ -1,4 +1,4 @@ -/* $OpenBSD: dsa_lib.c,v 1.46 2023/11/29 21:35:57 tb Exp $ */ +/* $OpenBSD: dsa_lib.c,v 1.48 2024/03/27 01:49:31 tb Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -146,49 +146,45 @@ DSA_new_method(ENGINE *engine) LCRYPTO_ALIAS(DSA_new_method); void -DSA_free(DSA *r) +DSA_free(DSA *dsa) { - int i; - - if (r == NULL) + if (dsa == NULL) return; - i = CRYPTO_add(&r->references, -1, CRYPTO_LOCK_DSA); - if (i > 0) + if (CRYPTO_add(&dsa->references, -1, CRYPTO_LOCK_DSA) > 0) return; - if (r->meth != NULL && r->meth->finish != NULL) - r->meth->finish(r); + if (dsa->meth != NULL && dsa->meth->finish != NULL) + dsa->meth->finish(dsa); - CRYPTO_free_ex_data(CRYPTO_EX_INDEX_DSA, r, &r->ex_data); + CRYPTO_free_ex_data(CRYPTO_EX_INDEX_DSA, dsa, &dsa->ex_data); - BN_free(r->p); - BN_free(r->q); - BN_free(r->g); - BN_free(r->pub_key); - BN_free(r->priv_key); - BN_free(r->kinv); - BN_free(r->r); - free(r); + BN_free(dsa->p); + BN_free(dsa->q); + BN_free(dsa->g); + BN_free(dsa->pub_key); + BN_free(dsa->priv_key); + BN_free(dsa->kinv); + BN_free(dsa->r); + free(dsa); } LCRYPTO_ALIAS(DSA_free); int -DSA_up_ref(DSA *r) +DSA_up_ref(DSA *dsa) { - int i = CRYPTO_add(&r->references, 1, CRYPTO_LOCK_DSA); - return i > 1 ? 1 : 0; + return CRYPTO_add(&dsa->references, 1, CRYPTO_LOCK_DSA) > 1; } LCRYPTO_ALIAS(DSA_up_ref); int -DSA_size(const DSA *r) +DSA_size(const DSA *dsa) { DSA_SIG signature; int ret = 0; - signature.r = r->q; - signature.s = r->q; + signature.r = dsa->q; + signature.s = dsa->q; if ((ret = i2d_DSA_SIG(&signature, NULL)) < 0) ret = 0; @@ -207,102 +203,107 @@ DSA_get_ex_new_index(long argl, void *argp, CRYPTO_EX_new *new_func, LCRYPTO_ALIAS(DSA_get_ex_new_index); int -DSA_set_ex_data(DSA *d, int idx, void *arg) +DSA_set_ex_data(DSA *dsa, int idx, void *arg) { - return CRYPTO_set_ex_data(&d->ex_data, idx, arg); + return CRYPTO_set_ex_data(&dsa->ex_data, idx, arg); } LCRYPTO_ALIAS(DSA_set_ex_data); void * -DSA_get_ex_data(DSA *d, int idx) +DSA_get_ex_data(DSA *dsa, int idx) { - return CRYPTO_get_ex_data(&d->ex_data, idx); + return CRYPTO_get_ex_data(&dsa->ex_data, idx); } LCRYPTO_ALIAS(DSA_get_ex_data); int -DSA_security_bits(const DSA *d) +DSA_security_bits(const DSA *dsa) { - if (d->p == NULL || d->q == NULL) + if (dsa->p == NULL || dsa->q == NULL) return -1; - return BN_security_bits(BN_num_bits(d->p), BN_num_bits(d->q)); + return BN_security_bits(BN_num_bits(dsa->p), BN_num_bits(dsa->q)); } LCRYPTO_ALIAS(DSA_security_bits); #ifndef OPENSSL_NO_DH DH * -DSA_dup_DH(const DSA *r) +DSA_dup_DH(const DSA *dsa) { /* * DSA has p, q, g, optional pub_key, optional priv_key. * DH has p, optional length, g, optional pub_key, optional priv_key, * optional q. */ - DH *ret = NULL; + DH *dh = NULL; - if (r == NULL) + if (dsa == NULL) goto err; - ret = DH_new(); - if (ret == NULL) + + if ((dh = DH_new()) == NULL) goto err; - if (r->p != NULL) - if ((ret->p = BN_dup(r->p)) == NULL) - goto err; - if (r->q != NULL) { - ret->length = BN_num_bits(r->q); - if ((ret->q = BN_dup(r->q)) == NULL) + + if (dsa->p != NULL) { + if ((dh->p = BN_dup(dsa->p)) == NULL) goto err; } - if (r->g != NULL) - if ((ret->g = BN_dup(r->g)) == NULL) + if (dsa->q != NULL) { + dh->length = BN_num_bits(dsa->q); + if ((dh->q = BN_dup(dsa->q)) == NULL) goto err; - if (r->pub_key != NULL) - if ((ret->pub_key = BN_dup(r->pub_key)) == NULL) + } + if (dsa->g != NULL) { + if ((dh->g = BN_dup(dsa->g)) == NULL) goto err; - if (r->priv_key != NULL) - if ((ret->priv_key = BN_dup(r->priv_key)) == NULL) + } + if (dsa->pub_key != NULL) { + if ((dh->pub_key = BN_dup(dsa->pub_key)) == NULL) goto err; + } + if (dsa->priv_key != NULL) { + if ((dh->priv_key = BN_dup(dsa->priv_key)) == NULL) + goto err; + } - return ret; + return dh; -err: - DH_free(ret); + err: + DH_free(dh); return NULL; } LCRYPTO_ALIAS(DSA_dup_DH); #endif void -DSA_get0_pqg(const DSA *d, const BIGNUM **p, const BIGNUM **q, const BIGNUM **g) +DSA_get0_pqg(const DSA *dsa, const BIGNUM **p, const BIGNUM **q, const BIGNUM **g) { if (p != NULL) - *p = d->p; + *p = dsa->p; if (q != NULL) - *q = d->q; + *q = dsa->q; if (g != NULL) - *g = d->g; + *g = dsa->g; } LCRYPTO_ALIAS(DSA_get0_pqg); int -DSA_set0_pqg(DSA *d, BIGNUM *p, BIGNUM *q, BIGNUM *g) +DSA_set0_pqg(DSA *dsa, BIGNUM *p, BIGNUM *q, BIGNUM *g) { - if ((d->p == NULL && p == NULL) || (d->q == NULL && q == NULL) || - (d->g == NULL && g == NULL)) + if ((dsa->p == NULL && p == NULL) || (dsa->q == NULL && q == NULL) || + (dsa->g == NULL && g == NULL)) return 0; if (p != NULL) { - BN_free(d->p); - d->p = p; + BN_free(dsa->p); + dsa->p = p; } if (q != NULL) { - BN_free(d->q); - d->q = q; + BN_free(dsa->q); + dsa->q = q; } if (g != NULL) { - BN_free(d->g); - d->g = g; + BN_free(dsa->g); + dsa->g = g; } return 1; @@ -310,28 +311,28 @@ DSA_set0_pqg(DSA *d, BIGNUM *p, BIGNUM *q, BIGNUM *g) LCRYPTO_ALIAS(DSA_set0_pqg); void -DSA_get0_key(const DSA *d, const BIGNUM **pub_key, const BIGNUM **priv_key) +DSA_get0_key(const DSA *dsa, const BIGNUM **pub_key, const BIGNUM **priv_key) { if (pub_key != NULL) - *pub_key = d->pub_key; + *pub_key = dsa->pub_key; if (priv_key != NULL) - *priv_key = d->priv_key; + *priv_key = dsa->priv_key; } LCRYPTO_ALIAS(DSA_get0_key); int -DSA_set0_key(DSA *d, BIGNUM *pub_key, BIGNUM *priv_key) +DSA_set0_key(DSA *dsa, BIGNUM *pub_key, BIGNUM *priv_key) { - if (d->pub_key == NULL && pub_key == NULL) + if (dsa->pub_key == NULL && pub_key == NULL) return 0; if (pub_key != NULL) { - BN_free(d->pub_key); - d->pub_key = pub_key; + BN_free(dsa->pub_key); + dsa->pub_key = pub_key; } if (priv_key != NULL) { - BN_free(d->priv_key); - d->priv_key = priv_key; + BN_free(dsa->priv_key); + dsa->priv_key = priv_key; } return 1; @@ -339,63 +340,63 @@ DSA_set0_key(DSA *d, BIGNUM *pub_key, BIGNUM *priv_key) LCRYPTO_ALIAS(DSA_set0_key); const BIGNUM * -DSA_get0_p(const DSA *d) +DSA_get0_p(const DSA *dsa) { - return d->p; + return dsa->p; } LCRYPTO_ALIAS(DSA_get0_p); const BIGNUM * -DSA_get0_q(const DSA *d) +DSA_get0_q(const DSA *dsa) { - return d->q; + return dsa->q; } LCRYPTO_ALIAS(DSA_get0_q); const BIGNUM * -DSA_get0_g(const DSA *d) +DSA_get0_g(const DSA *dsa) { - return d->g; + return dsa->g; } LCRYPTO_ALIAS(DSA_get0_g); const BIGNUM * -DSA_get0_pub_key(const DSA *d) +DSA_get0_pub_key(const DSA *dsa) { - return d->pub_key; + return dsa->pub_key; } LCRYPTO_ALIAS(DSA_get0_pub_key); const BIGNUM * -DSA_get0_priv_key(const DSA *d) +DSA_get0_priv_key(const DSA *dsa) { - return d->priv_key; + return dsa->priv_key; } LCRYPTO_ALIAS(DSA_get0_priv_key); void -DSA_clear_flags(DSA *d, int flags) +DSA_clear_flags(DSA *dsa, int flags) { - d->flags &= ~flags; + dsa->flags &= ~flags; } LCRYPTO_ALIAS(DSA_clear_flags); int -DSA_test_flags(const DSA *d, int flags) +DSA_test_flags(const DSA *dsa, int flags) { - return d->flags & flags; + return dsa->flags & flags; } LCRYPTO_ALIAS(DSA_test_flags); void -DSA_set_flags(DSA *d, int flags) +DSA_set_flags(DSA *dsa, int flags) { - d->flags |= flags; + dsa->flags |= flags; } LCRYPTO_ALIAS(DSA_set_flags); ENGINE * -DSA_get0_engine(DSA *d) +DSA_get0_engine(DSA *dsa) { return NULL; } diff --git a/lib/libcrypto/ec/ec_key.c b/lib/libcrypto/ec/ec_key.c index dd976898a..e95982947 100644 --- a/lib/libcrypto/ec/ec_key.c +++ b/lib/libcrypto/ec/ec_key.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ec_key.c,v 1.39 2023/11/29 21:35:57 tb Exp $ */ +/* $OpenBSD: ec_key.c,v 1.40 2024/03/27 01:22:30 tb Exp $ */ /* * Written by Nils Larsch for the OpenSSL project. */ @@ -204,8 +204,7 @@ LCRYPTO_ALIAS(EC_KEY_dup); int EC_KEY_up_ref(EC_KEY *r) { - int i = CRYPTO_add(&r->references, 1, CRYPTO_LOCK_EC); - return ((i > 1) ? 1 : 0); + return CRYPTO_add(&r->references, 1, CRYPTO_LOCK_EC) > 1; } LCRYPTO_ALIAS(EC_KEY_up_ref); diff --git a/lib/libcrypto/evp/e_rc2.c b/lib/libcrypto/evp/e_rc2.c index 0a1955110..25caef6e3 100644 --- a/lib/libcrypto/evp/e_rc2.c +++ b/lib/libcrypto/evp/e_rc2.c @@ -1,4 +1,4 @@ -/* $OpenBSD: e_rc2.c,v 1.27 2024/01/07 15:42:57 tb Exp $ */ +/* $OpenBSD: e_rc2.c,v 1.28 2024/03/26 06:58:21 tb Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -397,12 +397,6 @@ rc2_ctrl(EVP_CIPHER_CTX *c, int type, int arg, void *ptr) } return 0; -#ifdef PBE_PRF_TEST - case EVP_CTRL_PBE_PRF_NID: - *(int *)ptr = NID_hmacWithMD5; - return 1; -#endif - default: return -1; } diff --git a/lib/libcrypto/evp/evp_local.h b/lib/libcrypto/evp/evp_local.h index d0335931e..b1c0c9b14 100644 --- a/lib/libcrypto/evp/evp_local.h +++ b/lib/libcrypto/evp/evp_local.h @@ -1,4 +1,4 @@ -/* $OpenBSD: evp_local.h,v 1.20 2024/03/24 06:05:41 tb Exp $ */ +/* $OpenBSD: evp_local.h,v 1.21 2024/03/26 01:41:06 tb Exp $ */ /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL * project 2000. */ @@ -307,10 +307,6 @@ struct evp_pkey_method_st { int (*signctx)(EVP_PKEY_CTX *ctx, unsigned char *sig, size_t *siglen, EVP_MD_CTX *mctx); - int (*verifyctx_init)(EVP_PKEY_CTX *ctx, EVP_MD_CTX *mctx); - int (*verifyctx)(EVP_PKEY_CTX *ctx, const unsigned char *sig, - int siglen, EVP_MD_CTX *mctx); - int (*encrypt_init)(EVP_PKEY_CTX *ctx); int (*encrypt)(EVP_PKEY_CTX *ctx, unsigned char *out, size_t *outlen, const unsigned char *in, size_t inlen); diff --git a/lib/libcrypto/evp/m_sigver.c b/lib/libcrypto/evp/m_sigver.c index f89f6034b..eea2de49e 100644 --- a/lib/libcrypto/evp/m_sigver.c +++ b/lib/libcrypto/evp/m_sigver.c @@ -1,4 +1,4 @@ -/* $OpenBSD: m_sigver.c,v 1.18 2024/03/25 11:41:40 joshua Exp $ */ +/* $OpenBSD: m_sigver.c,v 1.21 2024/03/27 01:55:40 joshua Exp $ */ /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL * project 2006. */ @@ -95,12 +95,7 @@ do_sigver_init(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, const EVP_MD *type, } if (ver) { - if (ctx->pctx->pmeth->verifyctx_init) { - if (ctx->pctx->pmeth->verifyctx_init(ctx->pctx, - ctx) <=0) - return 0; - ctx->pctx->operation = EVP_PKEY_OP_VERIFYCTX; - } else if (ctx->pctx->pmeth->digestverify != NULL) { + if (ctx->pctx->pmeth->digestverify != NULL) { ctx->pctx->operation = EVP_PKEY_OP_VERIFY; ctx->update = update_oneshot_only; } else if (EVP_PKEY_verify_init(ctx->pctx) <= 0) @@ -171,43 +166,52 @@ int EVP_DigestSignFinal(EVP_MD_CTX *ctx, unsigned char *sigret, size_t *siglen) { EVP_PKEY_CTX *pctx = ctx->pctx; - int r = 0; + EVP_MD_CTX *md_ctx = NULL; + unsigned char md[EVP_MAX_MD_SIZE]; + unsigned int mdlen = 0; + int s; + int ret = 0; if (pctx->pmeth->flags & EVP_PKEY_FLAG_SIGCTX_CUSTOM) return evp_digestsignfinal_sigctx_custom(ctx, sigret, siglen); - if (sigret) { - EVP_MD_CTX tmp_ctx; - unsigned char md[EVP_MAX_MD_SIZE]; - unsigned int mdlen = 0; - EVP_MD_CTX_legacy_clear(&tmp_ctx); - if (!EVP_MD_CTX_copy_ex(&tmp_ctx, ctx)) - return 0; + if (sigret == NULL) { if (ctx->pctx->pmeth->signctx != NULL) { - r = tmp_ctx.pctx->pmeth->signctx(tmp_ctx.pctx, - sigret, siglen, &tmp_ctx); - EVP_MD_CTX_cleanup(&tmp_ctx); - return r; - } - r = EVP_DigestFinal_ex(&tmp_ctx, md, &mdlen); - EVP_MD_CTX_cleanup(&tmp_ctx); - if (!r) - return r; - if (EVP_PKEY_sign(ctx->pctx, sigret, siglen, md, mdlen) <= 0) - return 0; - } else { - if (ctx->pctx->pmeth->signctx != NULL) { - if (ctx->pctx->pmeth->signctx(ctx->pctx, sigret, + if (ctx->pctx->pmeth->signctx(ctx->pctx, NULL, siglen, ctx) <= 0) return 0; - } else { - int s = EVP_MD_size(ctx->digest); - if (s < 0 || EVP_PKEY_sign(ctx->pctx, sigret, siglen, - NULL, s) <= 0) - return 0; + return 1; } + + if ((s = EVP_MD_size(ctx->digest)) < 0) + return 0; + if (EVP_PKEY_sign(ctx->pctx, NULL, siglen, NULL, s) <= 0) + return 0; + + return 1; } - return 1; + + + if ((md_ctx = EVP_MD_CTX_new()) == NULL) + goto err; + if (!EVP_MD_CTX_copy_ex(md_ctx, ctx)) + goto err; + if (md_ctx->pctx->pmeth->signctx != NULL) { + if(md_ctx->pctx->pmeth->signctx(md_ctx->pctx, + sigret, siglen, md_ctx) <= 0) + goto err; + } + if (!EVP_DigestFinal_ex(md_ctx, md, &mdlen)) + goto err; + if (EVP_PKEY_sign(ctx->pctx, sigret, siglen, md, mdlen) <= 0) + goto err; + + ret = 1; + + err: + EVP_MD_CTX_free(md_ctx); + + return ret; } int @@ -233,22 +237,13 @@ EVP_DigestVerifyFinal(EVP_MD_CTX *ctx, const unsigned char *sig, size_t siglen) unsigned char md[EVP_MAX_MD_SIZE]; int r; unsigned int mdlen = 0; - int vctx; - if (ctx->pctx->pmeth->verifyctx) - vctx = 1; - else - vctx = 0; EVP_MD_CTX_legacy_clear(&tmp_ctx); if (!EVP_MD_CTX_copy_ex(&tmp_ctx, ctx)) return -1; - if (vctx) { - r = tmp_ctx.pctx->pmeth->verifyctx(tmp_ctx.pctx, sig, - siglen, &tmp_ctx); - } else - r = EVP_DigestFinal_ex(&tmp_ctx, md, &mdlen); + r = EVP_DigestFinal_ex(&tmp_ctx, md, &mdlen); EVP_MD_CTX_cleanup(&tmp_ctx); - if (vctx || !r) + if (!r) return r; return EVP_PKEY_verify(ctx->pctx, sig, siglen, md, mdlen); } diff --git a/lib/libcrypto/evp/p_legacy.c b/lib/libcrypto/evp/p_legacy.c index 2036258dc..a444309f1 100644 --- a/lib/libcrypto/evp/p_legacy.c +++ b/lib/libcrypto/evp/p_legacy.c @@ -1,4 +1,4 @@ -/* $OpenBSD: p_legacy.c,v 1.3 2024/02/18 15:44:10 tb Exp $ */ +/* $OpenBSD: p_legacy.c,v 1.4 2024/03/26 05:22:50 joshua Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -99,7 +99,7 @@ EVP_OpenInit(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *type, int i, size = 0, ret = 0; if (type) { - EVP_CIPHER_CTX_legacy_clear(ctx); + EVP_CIPHER_CTX_reset(ctx); if (!EVP_DecryptInit_ex(ctx, type, NULL, NULL, NULL)) return 0; } @@ -154,7 +154,7 @@ EVP_SealInit(EVP_CIPHER_CTX *ctx, const EVP_CIPHER *type, unsigned char **ek, int i, iv_len; if (type) { - EVP_CIPHER_CTX_legacy_clear(ctx); + EVP_CIPHER_CTX_reset(ctx); if (!EVP_EncryptInit_ex(ctx, type, NULL, NULL, NULL)) return 0; } diff --git a/lib/libcrypto/evp/p_sign.c b/lib/libcrypto/evp/p_sign.c index f6d6e12a3..70290ed21 100644 --- a/lib/libcrypto/evp/p_sign.c +++ b/lib/libcrypto/evp/p_sign.c @@ -1,4 +1,4 @@ -/* $OpenBSD: p_sign.c,v 1.20 2024/02/18 15:45:42 tb Exp $ */ +/* $OpenBSD: p_sign.c,v 1.21 2024/03/26 06:08:51 joshua Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -71,18 +71,19 @@ EVP_SignFinal(EVP_MD_CTX *ctx, unsigned char *sigret, unsigned int *siglen, { unsigned char m[EVP_MAX_MD_SIZE]; unsigned int m_len; - EVP_MD_CTX tmp_ctx; + EVP_MD_CTX *md_ctx; EVP_PKEY_CTX *pkctx = NULL; size_t sltmp; int ret = 0; *siglen = 0; - EVP_MD_CTX_legacy_clear(&tmp_ctx); - if (!EVP_MD_CTX_copy_ex(&tmp_ctx, ctx)) + + if ((md_ctx = EVP_MD_CTX_new()) == NULL) goto err; - if (!EVP_DigestFinal_ex(&tmp_ctx, &(m[0]), &m_len)) + if (!EVP_MD_CTX_copy_ex(md_ctx, ctx)) + goto err; + if (!EVP_DigestFinal_ex(md_ctx, &(m[0]), &m_len)) goto err; - EVP_MD_CTX_cleanup(&tmp_ctx); sltmp = (size_t)EVP_PKEY_size(pkey); @@ -99,6 +100,7 @@ EVP_SignFinal(EVP_MD_CTX *ctx, unsigned char *sigret, unsigned int *siglen, ret = 1; err: + EVP_MD_CTX_free(md_ctx); EVP_PKEY_CTX_free(pkctx); return ret; } diff --git a/lib/libcrypto/evp/p_verify.c b/lib/libcrypto/evp/p_verify.c index ed9b3700f..04b7c39c6 100644 --- a/lib/libcrypto/evp/p_verify.c +++ b/lib/libcrypto/evp/p_verify.c @@ -1,4 +1,4 @@ -/* $OpenBSD: p_verify.c,v 1.19 2024/02/18 15:45:42 tb Exp $ */ +/* $OpenBSD: p_verify.c,v 1.20 2024/03/26 05:50:49 joshua Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -71,16 +71,16 @@ EVP_VerifyFinal(EVP_MD_CTX *ctx, const unsigned char *sigbuf, { unsigned char m[EVP_MAX_MD_SIZE]; unsigned int m_len; - EVP_MD_CTX tmp_ctx; + EVP_MD_CTX *md_ctx; EVP_PKEY_CTX *pkctx = NULL; int ret = 0; - EVP_MD_CTX_legacy_clear(&tmp_ctx); - if (!EVP_MD_CTX_copy_ex(&tmp_ctx, ctx)) + if ((md_ctx = EVP_MD_CTX_new()) == NULL) goto err; - if (!EVP_DigestFinal_ex(&tmp_ctx, &(m[0]), &m_len)) + if (!EVP_MD_CTX_copy_ex(md_ctx, ctx)) + goto err; + if (!EVP_DigestFinal_ex(md_ctx, &(m[0]), &m_len)) goto err; - EVP_MD_CTX_cleanup(&tmp_ctx); ret = -1; if ((pkctx = EVP_PKEY_CTX_new(pkey, NULL)) == NULL) @@ -92,6 +92,7 @@ EVP_VerifyFinal(EVP_MD_CTX *ctx, const unsigned char *sigbuf, ret = EVP_PKEY_verify(pkctx, sigbuf, siglen, m, m_len); err: + EVP_MD_CTX_free(md_ctx); EVP_PKEY_CTX_free(pkctx); return ret; } diff --git a/lib/libcrypto/hmac/hmac.c b/lib/libcrypto/hmac/hmac.c index 32d75154d..d80b45de5 100644 --- a/lib/libcrypto/hmac/hmac.c +++ b/lib/libcrypto/hmac/hmac.c @@ -1,4 +1,4 @@ -/* $OpenBSD: hmac.c,v 1.32 2024/02/18 15:45:42 tb Exp $ */ +/* $OpenBSD: hmac.c,v 1.33 2024/03/26 12:10:50 joshua Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -180,14 +180,7 @@ LCRYPTO_ALIAS(HMAC_Final); HMAC_CTX * HMAC_CTX_new(void) { - HMAC_CTX *ctx; - - if ((ctx = calloc(1, sizeof(*ctx))) == NULL) - return NULL; - - HMAC_CTX_init(ctx); - - return ctx; + return calloc(1, sizeof(HMAC_CTX)); } LCRYPTO_ALIAS(HMAC_CTX_new); diff --git a/lib/libcrypto/md4/md4.c b/lib/libcrypto/md4/md4.c index 12e3ac71d..1889c6fac 100644 --- a/lib/libcrypto/md4/md4.c +++ b/lib/libcrypto/md4/md4.c @@ -1,4 +1,4 @@ -/* $OpenBSD: md4.c,v 1.7 2023/08/10 13:41:56 jsing Exp $ */ +/* $OpenBSD: md4.c,v 1.15 2024/03/26 12:23:02 jsing Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -61,8 +61,14 @@ #include #include + #include +#include "crypto_internal.h" + +/* Ensure that MD4_LONG and uint32_t are equivalent size. */ +CTASSERT(sizeof(MD4_LONG) == sizeof(uint32_t)); + __BEGIN_HIDDEN_DECLS void md4_block_data_order (MD4_CTX *c, const void *p, size_t num); @@ -77,19 +83,13 @@ __END_HIDDEN_DECLS #define HASH_UPDATE MD4_Update #define HASH_TRANSFORM MD4_Transform #define HASH_FINAL MD4_Final -#define HASH_MAKE_STRING(c,s) do { \ - unsigned long ll; \ - ll=(c)->A; HOST_l2c(ll,(s)); \ - ll=(c)->B; HOST_l2c(ll,(s)); \ - ll=(c)->C; HOST_l2c(ll,(s)); \ - ll=(c)->D; HOST_l2c(ll,(s)); \ - } while (0) #define HASH_BLOCK_DATA_ORDER md4_block_data_order +#define HASH_NO_UPDATE +#define HASH_NO_TRANSFORM +#define HASH_NO_FINAL + #include "md32_common.h" -LCRYPTO_ALIAS(MD4_Update); -LCRYPTO_ALIAS(MD4_Final); -LCRYPTO_ALIAS(MD4_Transform); /* #define F(x,y,z) (((x) & (y)) | ((~(x)) & (z))) @@ -119,32 +119,16 @@ LCRYPTO_ALIAS(MD4_Transform); /* Implemented from RFC1186 The MD4 Message-Digest Algorithm */ -#define INIT_DATA_A (unsigned long)0x67452301L -#define INIT_DATA_B (unsigned long)0xefcdab89L -#define INIT_DATA_C (unsigned long)0x98badcfeL -#define INIT_DATA_D (unsigned long)0x10325476L - -int -MD4_Init(MD4_CTX *c) -{ - memset (c, 0, sizeof(*c)); - c->A = INIT_DATA_A; - c->B = INIT_DATA_B; - c->C = INIT_DATA_C; - c->D = INIT_DATA_D; - return 1; -} -LCRYPTO_ALIAS(MD4_Init); - #ifndef md4_block_data_order #ifdef X #undef X #endif void -md4_block_data_order(MD4_CTX *c, const void *data_, size_t num) +md4_block_data_order(MD4_CTX *c, const void *_in, size_t num) { - const unsigned char *data = data_; - unsigned int A, B, C, D, l; + const uint8_t *in = _in; + const MD4_LONG *in32; + unsigned int A, B, C, D; unsigned int X0, X1, X2, X3, X4, X5, X6, X7, X8, X9, X10, X11, X12, X13, X14, X15; @@ -153,56 +137,65 @@ md4_block_data_order(MD4_CTX *c, const void *data_, size_t num) C = c->C; D = c->D; - for (; num--; ) { - HOST_c2l(data, l); - X0 = l; - HOST_c2l(data, l); - X1 = l; + while (num-- > 0) { + if ((uintptr_t)in % 4 == 0) { + /* Input is 32 bit aligned. */ + in32 = (const MD4_LONG *)in; + X0 = le32toh(in32[0]); + X1 = le32toh(in32[1]); + X2 = le32toh(in32[2]); + X3 = le32toh(in32[3]); + X4 = le32toh(in32[4]); + X5 = le32toh(in32[5]); + X6 = le32toh(in32[6]); + X7 = le32toh(in32[7]); + X8 = le32toh(in32[8]); + X9 = le32toh(in32[9]); + X10 = le32toh(in32[10]); + X11 = le32toh(in32[11]); + X12 = le32toh(in32[12]); + X13 = le32toh(in32[13]); + X14 = le32toh(in32[14]); + X15 = le32toh(in32[15]); + } else { + /* Input is not 32 bit aligned. */ + X0 = crypto_load_le32toh(&in[0 * 4]); + X1 = crypto_load_le32toh(&in[1 * 4]); + X2 = crypto_load_le32toh(&in[2 * 4]); + X3 = crypto_load_le32toh(&in[3 * 4]); + X4 = crypto_load_le32toh(&in[4 * 4]); + X5 = crypto_load_le32toh(&in[5 * 4]); + X6 = crypto_load_le32toh(&in[6 * 4]); + X7 = crypto_load_le32toh(&in[7 * 4]); + X8 = crypto_load_le32toh(&in[8 * 4]); + X9 = crypto_load_le32toh(&in[9 * 4]); + X10 = crypto_load_le32toh(&in[10 * 4]); + X11 = crypto_load_le32toh(&in[11 * 4]); + X12 = crypto_load_le32toh(&in[12 * 4]); + X13 = crypto_load_le32toh(&in[13 * 4]); + X14 = crypto_load_le32toh(&in[14 * 4]); + X15 = crypto_load_le32toh(&in[15 * 4]); + } + in += MD4_CBLOCK; + /* Round 0 */ R0(A, B, C, D, X0, 3, 0); - HOST_c2l(data, l); - X2 = l; R0(D, A, B, C, X1, 7, 0); - HOST_c2l(data, l); - X3 = l; R0(C, D, A, B, X2, 11, 0); - HOST_c2l(data, l); - X4 = l; R0(B, C, D, A, X3, 19, 0); - HOST_c2l(data, l); - X5 = l; R0(A, B, C, D, X4, 3, 0); - HOST_c2l(data, l); - X6 = l; R0(D, A, B, C, X5, 7, 0); - HOST_c2l(data, l); - X7 = l; R0(C, D, A, B, X6, 11, 0); - HOST_c2l(data, l); - X8 = l; R0(B, C, D, A, X7, 19, 0); - HOST_c2l(data, l); - X9 = l; R0(A, B, C, D, X8, 3, 0); - HOST_c2l(data, l); - X10 = l; R0(D, A,B, C,X9, 7, 0); - HOST_c2l(data, l); - X11 = l; R0(C, D,A, B,X10, 11, 0); - HOST_c2l(data, l); - X12 = l; R0(B, C,D, A,X11, 19, 0); - HOST_c2l(data, l); - X13 = l; R0(A, B,C, D,X12, 3, 0); - HOST_c2l(data, l); - X14 = l; R0(D, A,B, C,X13, 7, 0); - HOST_c2l(data, l); - X15 = l; R0(C, D,A, B,X14, 11, 0); R0(B, C,D, A,X15, 19, 0); + /* Round 1 */ R1(A, B, C, D, X0, 3, 0x5A827999L); R1(D, A, B, C, X4, 5, 0x5A827999L); @@ -220,6 +213,7 @@ md4_block_data_order(MD4_CTX *c, const void *data_, size_t num) R1(D, A, B, C, X7, 5, 0x5A827999L); R1(C, D, A, B, X11, 9, 0x5A827999L); R1(B, C, D, A, X15, 13, 0x5A827999L); + /* Round 2 */ R2(A, B, C, D, X0, 3, 0x6ED9EBA1L); R2(D, A, B, C, X8, 9, 0x6ED9EBA1L); @@ -246,6 +240,114 @@ md4_block_data_order(MD4_CTX *c, const void *data_, size_t num) } #endif +int +MD4_Init(MD4_CTX *c) +{ + memset(c, 0, sizeof(*c)); + + c->A = 0x67452301UL; + c->B = 0xefcdab89UL; + c->C = 0x98badcfeUL; + c->D = 0x10325476UL; + + return 1; +} +LCRYPTO_ALIAS(MD4_Init); + +int +MD4_Update(MD4_CTX *c, const void *data_, size_t len) +{ + const unsigned char *data = data_; + unsigned char *p; + MD4_LONG l; + size_t n; + + if (len == 0) + return 1; + + l = (c->Nl + (((MD4_LONG)len) << 3))&0xffffffffUL; + /* 95-05-24 eay Fixed a bug with the overflow handling, thanks to + * Wei Dai for pointing it out. */ + if (l < c->Nl) /* overflow */ + c->Nh++; + c->Nh+=(MD4_LONG)(len>>29); /* might cause compiler warning on 16-bit */ + c->Nl = l; + + n = c->num; + if (n != 0) { + p = (unsigned char *)c->data; + + if (len >= MD4_CBLOCK || len + n >= MD4_CBLOCK) { + memcpy (p + n, data, MD4_CBLOCK - n); + md4_block_data_order (c, p, 1); + n = MD4_CBLOCK - n; + data += n; + len -= n; + c->num = 0; + memset(p, 0, MD4_CBLOCK); /* keep it zeroed */ + } else { + memcpy(p + n, data, len); + c->num += (unsigned int)len; + return 1; + } + } + + n = len / MD4_CBLOCK; + if (n > 0) { + md4_block_data_order(c, data, n); + n *= MD4_CBLOCK; + data += n; + len -= n; + } + + if (len != 0) { + p = (unsigned char *)c->data; + c->num = (unsigned int)len; + memcpy(p, data, len); + } + return 1; +} +LCRYPTO_ALIAS(MD4_Update); + +void +MD4_Transform(MD4_CTX *c, const unsigned char *data) +{ + md4_block_data_order(c, data, 1); +} +LCRYPTO_ALIAS(MD4_Transform); + +int +MD4_Final(unsigned char *md, MD4_CTX *c) +{ + unsigned char *p = (unsigned char *)c->data; + size_t n = c->num; + + p[n] = 0x80; /* there is always room for one */ + n++; + + if (n > (MD4_CBLOCK - 8)) { + memset(p + n, 0, MD4_CBLOCK - n); + n = 0; + md4_block_data_order(c, p, 1); + } + + memset(p + n, 0, MD4_CBLOCK - 8 - n); + c->data[MD4_LBLOCK - 2] = htole32(c->Nl); + c->data[MD4_LBLOCK - 1] = htole32(c->Nh); + + md4_block_data_order(c, p, 1); + c->num = 0; + memset(p, 0, MD4_CBLOCK); + + crypto_store_htole32(&md[0 * 4], c->A); + crypto_store_htole32(&md[1 * 4], c->B); + crypto_store_htole32(&md[2 * 4], c->C); + crypto_store_htole32(&md[3 * 4], c->D); + + return 1; +} +LCRYPTO_ALIAS(MD4_Final); + unsigned char * MD4(const unsigned char *d, size_t n, unsigned char *md) { diff --git a/lib/libcrypto/md5/md5.c b/lib/libcrypto/md5/md5.c index c2ee2958d..6b1afb444 100644 --- a/lib/libcrypto/md5/md5.c +++ b/lib/libcrypto/md5/md5.c @@ -1,4 +1,4 @@ -/* $OpenBSD: md5.c,v 1.18 2023/08/15 08:39:27 jsing Exp $ */ +/* $OpenBSD: md5.c,v 1.21 2024/03/26 05:55:15 jsing Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -57,6 +57,7 @@ */ #include +#include #include #include @@ -74,63 +75,64 @@ void md5_block_asm_data_order(MD5_CTX *c, const void *p, size_t num); #define md5_block_data_order md5_block_asm_data_order #endif -#define DATA_ORDER_IS_LITTLE_ENDIAN - -#define HASH_LONG MD5_LONG -#define HASH_CTX MD5_CTX -#define HASH_CBLOCK MD5_CBLOCK -#define HASH_UPDATE MD5_Update -#define HASH_TRANSFORM MD5_Transform -#define HASH_FINAL MD5_Final -#define HASH_BLOCK_DATA_ORDER md5_block_data_order - -#define HASH_NO_UPDATE -#define HASH_NO_TRANSFORM -#define HASH_NO_FINAL - -#include "md32_common.h" - -/* -#define F(x,y,z) (((x) & (y)) | ((~(x)) & (z))) -#define G(x,y,z) (((x) & (z)) | ((y) & (~(z)))) -*/ - -/* As pointed out by Wei Dai , the above can be - * simplified to the code below. Wei attributes these optimizations - * to Peter Gutmann's SHS code, and he attributes it to Rich Schroeppel. - */ -#define F(b,c,d) ((((c) ^ (d)) & (b)) ^ (d)) -#define G(b,c,d) ((((b) ^ (c)) & (d)) ^ (c)) -#define H(b,c,d) ((b) ^ (c) ^ (d)) -#define I(b,c,d) (((~(d)) | (b)) ^ (c)) - -#define R0(a,b,c,d,k,s,t) { \ - a+=((k)+(t)+F((b),(c),(d))); \ - a=ROTATE(a,s); \ - a+=b; };\ - -#define R1(a,b,c,d,k,s,t) { \ - a+=((k)+(t)+G((b),(c),(d))); \ - a=ROTATE(a,s); \ - a+=b; }; - -#define R2(a,b,c,d,k,s,t) { \ - a+=((k)+(t)+H((b),(c),(d))); \ - a=ROTATE(a,s); \ - a+=b; }; - -#define R3(a,b,c,d,k,s,t) { \ - a+=((k)+(t)+I((b),(c),(d))); \ - a=ROTATE(a,s); \ - a+=b; }; - -/* Implemented from RFC1321 The MD5 Message-Digest Algorithm. */ - #ifndef MD5_ASM +static inline uint32_t +md5_F(uint32_t x, uint32_t y, uint32_t z) +{ + return (x & y) | (~x & z); +} + +static inline uint32_t +md5_G(uint32_t x, uint32_t y, uint32_t z) +{ + return (x & z) | (y & ~z); +} + +static inline uint32_t +md5_H(uint32_t x, uint32_t y, uint32_t z) +{ + return x ^ y ^ z; +} + +static inline uint32_t +md5_I(uint32_t x, uint32_t y, uint32_t z) +{ + return y ^ (x | ~z); +} + +static inline void +md5_round1(uint32_t *a, uint32_t b, uint32_t c, uint32_t d, uint32_t x, + uint32_t t, uint32_t s) +{ + *a = b + crypto_rol_u32(*a + md5_F(b, c, d) + x + t, s); +} + +static inline void +md5_round2(uint32_t *a, uint32_t b, uint32_t c, uint32_t d, uint32_t x, + uint32_t t, uint32_t s) +{ + *a = b + crypto_rol_u32(*a + md5_G(b, c, d) + x + t, s); +} + +static inline void +md5_round3(uint32_t *a, uint32_t b, uint32_t c, uint32_t d, uint32_t x, + uint32_t t, uint32_t s) +{ + *a = b + crypto_rol_u32(*a + md5_H(b, c, d) + x + t, s); +} + +static inline void +md5_round4(uint32_t *a, uint32_t b, uint32_t c, uint32_t d, uint32_t x, + uint32_t t, uint32_t s) +{ + *a = b + crypto_rol_u32(*a + md5_I(b, c, d) + x + t, s); +} + static void md5_block_data_order(MD5_CTX *c, const void *_in, size_t num) { const uint8_t *in = _in; + const MD5_LONG *in32; MD5_LONG A, B, C, D; MD5_LONG X0, X1, X2, X3, X4, X5, X6, X7, X8, X9, X10, X11, X12, X13, X14, X15; @@ -140,93 +142,114 @@ md5_block_data_order(MD5_CTX *c, const void *_in, size_t num) C = c->C; D = c->D; - for (; num--; ) { - X0 = crypto_load_le32toh(&in[0 * 4]); - X1 = crypto_load_le32toh(&in[1 * 4]); - X2 = crypto_load_le32toh(&in[2 * 4]); - X3 = crypto_load_le32toh(&in[3 * 4]); - X4 = crypto_load_le32toh(&in[4 * 4]); - X5 = crypto_load_le32toh(&in[5 * 4]); - X6 = crypto_load_le32toh(&in[6 * 4]); - X7 = crypto_load_le32toh(&in[7 * 4]); - X8 = crypto_load_le32toh(&in[8 * 4]); - X9 = crypto_load_le32toh(&in[9 * 4]); - X10 = crypto_load_le32toh(&in[10 * 4]); - X11 = crypto_load_le32toh(&in[11 * 4]); - X12 = crypto_load_le32toh(&in[12 * 4]); - X13 = crypto_load_le32toh(&in[13 * 4]); - X14 = crypto_load_le32toh(&in[14 * 4]); - X15 = crypto_load_le32toh(&in[15 * 4]); + while (num-- > 0) { + if ((uintptr_t)in % 4 == 0) { + /* Input is 32 bit aligned. */ + in32 = (const MD5_LONG *)in; + X0 = le32toh(in32[0]); + X1 = le32toh(in32[1]); + X2 = le32toh(in32[2]); + X3 = le32toh(in32[3]); + X4 = le32toh(in32[4]); + X5 = le32toh(in32[5]); + X6 = le32toh(in32[6]); + X7 = le32toh(in32[7]); + X8 = le32toh(in32[8]); + X9 = le32toh(in32[9]); + X10 = le32toh(in32[10]); + X11 = le32toh(in32[11]); + X12 = le32toh(in32[12]); + X13 = le32toh(in32[13]); + X14 = le32toh(in32[14]); + X15 = le32toh(in32[15]); + } else { + /* Input is not 32 bit aligned. */ + X0 = crypto_load_le32toh(&in[0 * 4]); + X1 = crypto_load_le32toh(&in[1 * 4]); + X2 = crypto_load_le32toh(&in[2 * 4]); + X3 = crypto_load_le32toh(&in[3 * 4]); + X4 = crypto_load_le32toh(&in[4 * 4]); + X5 = crypto_load_le32toh(&in[5 * 4]); + X6 = crypto_load_le32toh(&in[6 * 4]); + X7 = crypto_load_le32toh(&in[7 * 4]); + X8 = crypto_load_le32toh(&in[8 * 4]); + X9 = crypto_load_le32toh(&in[9 * 4]); + X10 = crypto_load_le32toh(&in[10 * 4]); + X11 = crypto_load_le32toh(&in[11 * 4]); + X12 = crypto_load_le32toh(&in[12 * 4]); + X13 = crypto_load_le32toh(&in[13 * 4]); + X14 = crypto_load_le32toh(&in[14 * 4]); + X15 = crypto_load_le32toh(&in[15 * 4]); + } in += MD5_CBLOCK; - /* Round 0 */ - R0(A, B, C, D, X0, 7, 0xd76aa478L); - R0(D, A, B, C, X1, 12, 0xe8c7b756L); - R0(C, D, A, B, X2, 17, 0x242070dbL); - R0(B, C, D, A, X3, 22, 0xc1bdceeeL); - R0(A, B, C, D, X4, 7, 0xf57c0fafL); - R0(D, A, B, C, X5, 12, 0x4787c62aL); - R0(C, D, A, B, X6, 17, 0xa8304613L); - R0(B, C, D, A, X7, 22, 0xfd469501L); - R0(A, B, C, D, X8, 7, 0x698098d8L); - R0(D, A, B, C, X9, 12, 0x8b44f7afL); - R0(C, D, A, B, X10, 17, 0xffff5bb1L); - R0(B, C, D, A, X11, 22, 0x895cd7beL); - R0(A, B, C, D, X12, 7, 0x6b901122L); - R0(D, A, B, C, X13, 12, 0xfd987193L); - R0(C, D, A, B, X14, 17, 0xa679438eL); - R0(B, C, D, A, X15, 22, 0x49b40821L); - /* Round 1 */ - R1(A, B, C, D, X1, 5, 0xf61e2562L); - R1(D, A, B, C, X6, 9, 0xc040b340L); - R1(C, D, A, B, X11, 14, 0x265e5a51L); - R1(B, C, D, A, X0, 20, 0xe9b6c7aaL); - R1(A, B, C, D, X5, 5, 0xd62f105dL); - R1(D, A, B, C, X10, 9, 0x02441453L); - R1(C, D, A, B, X15, 14, 0xd8a1e681L); - R1(B, C, D, A, X4, 20, 0xe7d3fbc8L); - R1(A, B, C, D, X9, 5, 0x21e1cde6L); - R1(D, A, B, C, X14, 9, 0xc33707d6L); - R1(C, D, A, B, X3, 14, 0xf4d50d87L); - R1(B, C, D, A, X8, 20, 0x455a14edL); - R1(A, B, C, D, X13, 5, 0xa9e3e905L); - R1(D, A, B, C, X2, 9, 0xfcefa3f8L); - R1(C, D, A, B, X7, 14, 0x676f02d9L); - R1(B, C, D, A, X12, 20, 0x8d2a4c8aL); - /* Round 2 */ - R2(A, B, C, D, X5, 4, 0xfffa3942L); - R2(D, A, B, C, X8, 11, 0x8771f681L); - R2(C, D, A, B, X11, 16, 0x6d9d6122L); - R2(B, C, D, A, X14, 23, 0xfde5380cL); - R2(A, B, C, D, X1, 4, 0xa4beea44L); - R2(D, A, B, C, X4, 11, 0x4bdecfa9L); - R2(C, D, A, B, X7, 16, 0xf6bb4b60L); - R2(B, C, D, A, X10, 23, 0xbebfbc70L); - R2(A, B, C, D, X13, 4, 0x289b7ec6L); - R2(D, A, B, C, X0, 11, 0xeaa127faL); - R2(C, D, A, B, X3, 16, 0xd4ef3085L); - R2(B, C, D, A, X6, 23, 0x04881d05L); - R2(A, B, C, D, X9, 4, 0xd9d4d039L); - R2(D, A, B, C, X12, 11, 0xe6db99e5L); - R2(C, D, A, B, X15, 16, 0x1fa27cf8L); - R2(B, C, D, A, X2, 23, 0xc4ac5665L); - /* Round 3 */ - R3(A, B, C, D, X0, 6, 0xf4292244L); - R3(D, A, B, C, X7, 10, 0x432aff97L); - R3(C, D, A, B, X14, 15, 0xab9423a7L); - R3(B, C, D, A, X5, 21, 0xfc93a039L); - R3(A, B, C, D, X12, 6, 0x655b59c3L); - R3(D, A, B, C, X3, 10, 0x8f0ccc92L); - R3(C, D, A, B, X10, 15, 0xffeff47dL); - R3(B, C, D, A, X1, 21, 0x85845dd1L); - R3(A, B, C, D, X8, 6, 0x6fa87e4fL); - R3(D, A, B, C, X15, 10, 0xfe2ce6e0L); - R3(C, D, A, B, X6, 15, 0xa3014314L); - R3(B, C, D, A, X13, 21, 0x4e0811a1L); - R3(A, B, C, D, X4, 6, 0xf7537e82L); - R3(D, A, B, C, X11, 10, 0xbd3af235L); - R3(C, D, A, B, X2, 15, 0x2ad7d2bbL); - R3(B, C, D, A, X9, 21, 0xeb86d391L); + md5_round1(&A, B, C, D, X0, 0xd76aa478L, 7); + md5_round1(&D, A, B, C, X1, 0xe8c7b756L, 12); + md5_round1(&C, D, A, B, X2, 0x242070dbL, 17); + md5_round1(&B, C, D, A, X3, 0xc1bdceeeL, 22); + md5_round1(&A, B, C, D, X4, 0xf57c0fafL, 7); + md5_round1(&D, A, B, C, X5, 0x4787c62aL, 12); + md5_round1(&C, D, A, B, X6, 0xa8304613L, 17); + md5_round1(&B, C, D, A, X7, 0xfd469501L, 22); + md5_round1(&A, B, C, D, X8, 0x698098d8L, 7); + md5_round1(&D, A, B, C, X9, 0x8b44f7afL, 12); + md5_round1(&C, D, A, B, X10, 0xffff5bb1L, 17); + md5_round1(&B, C, D, A, X11, 0x895cd7beL, 22); + md5_round1(&A, B, C, D, X12, 0x6b901122L, 7); + md5_round1(&D, A, B, C, X13, 0xfd987193L, 12); + md5_round1(&C, D, A, B, X14, 0xa679438eL, 17); + md5_round1(&B, C, D, A, X15, 0x49b40821L, 22); + + md5_round2(&A, B, C, D, X1, 0xf61e2562L, 5); + md5_round2(&D, A, B, C, X6, 0xc040b340L, 9); + md5_round2(&C, D, A, B, X11, 0x265e5a51L, 14); + md5_round2(&B, C, D, A, X0, 0xe9b6c7aaL, 20); + md5_round2(&A, B, C, D, X5, 0xd62f105dL, 5); + md5_round2(&D, A, B, C, X10, 0x02441453L, 9); + md5_round2(&C, D, A, B, X15, 0xd8a1e681L, 14); + md5_round2(&B, C, D, A, X4, 0xe7d3fbc8L, 20); + md5_round2(&A, B, C, D, X9, 0x21e1cde6L, 5); + md5_round2(&D, A, B, C, X14, 0xc33707d6L, 9); + md5_round2(&C, D, A, B, X3, 0xf4d50d87L, 14); + md5_round2(&B, C, D, A, X8, 0x455a14edL, 20); + md5_round2(&A, B, C, D, X13, 0xa9e3e905L, 5); + md5_round2(&D, A, B, C, X2, 0xfcefa3f8L, 9); + md5_round2(&C, D, A, B, X7, 0x676f02d9L, 14); + md5_round2(&B, C, D, A, X12, 0x8d2a4c8aL, 20); + + md5_round3(&A, B, C, D, X5, 0xfffa3942L, 4); + md5_round3(&D, A, B, C, X8, 0x8771f681L, 11); + md5_round3(&C, D, A, B, X11, 0x6d9d6122L, 16); + md5_round3(&B, C, D, A, X14, 0xfde5380cL, 23); + md5_round3(&A, B, C, D, X1, 0xa4beea44L, 4); + md5_round3(&D, A, B, C, X4, 0x4bdecfa9L, 11); + md5_round3(&C, D, A, B, X7, 0xf6bb4b60L, 16); + md5_round3(&B, C, D, A, X10, 0xbebfbc70L, 23); + md5_round3(&A, B, C, D, X13, 0x289b7ec6L, 4); + md5_round3(&D, A, B, C, X0, 0xeaa127faL, 11); + md5_round3(&C, D, A, B, X3, 0xd4ef3085L, 16); + md5_round3(&B, C, D, A, X6, 0x04881d05L, 23); + md5_round3(&A, B, C, D, X9, 0xd9d4d039L, 4); + md5_round3(&D, A, B, C, X12, 0xe6db99e5L, 11); + md5_round3(&C, D, A, B, X15, 0x1fa27cf8L, 16); + md5_round3(&B, C, D, A, X2, 0xc4ac5665L, 23); + + md5_round4(&A, B, C, D, X0, 0xf4292244L, 6); + md5_round4(&D, A, B, C, X7, 0x432aff97L, 10); + md5_round4(&C, D, A, B, X14, 0xab9423a7L, 15); + md5_round4(&B, C, D, A, X5, 0xfc93a039L, 21); + md5_round4(&A, B, C, D, X12, 0x655b59c3L, 6); + md5_round4(&D, A, B, C, X3, 0x8f0ccc92L, 10); + md5_round4(&C, D, A, B, X10, 0xffeff47dL, 15); + md5_round4(&B, C, D, A, X1, 0x85845dd1L, 21); + md5_round4(&A, B, C, D, X8, 0x6fa87e4fL, 6); + md5_round4(&D, A, B, C, X15, 0xfe2ce6e0L, 10); + md5_round4(&C, D, A, B, X6, 0xa3014314L, 15); + md5_round4(&B, C, D, A, X13, 0x4e0811a1L, 21); + md5_round4(&A, B, C, D, X4, 0xf7537e82L, 6); + md5_round4(&D, A, B, C, X11, 0xbd3af235L, 10); + md5_round4(&C, D, A, B, X2, 0x2ad7d2bbL, 15); + md5_round4(&B, C, D, A, X9, 0xeb86d391L, 21); A = c->A += A; B = c->B += B; diff --git a/lib/libcrypto/rsa/rsa_lib.c b/lib/libcrypto/rsa/rsa_lib.c index b379cddc0..91f4938ec 100644 --- a/lib/libcrypto/rsa/rsa_lib.c +++ b/lib/libcrypto/rsa/rsa_lib.c @@ -1,4 +1,4 @@ -/* $OpenBSD: rsa_lib.c,v 1.49 2023/11/19 15:46:10 tb Exp $ */ +/* $OpenBSD: rsa_lib.c,v 1.50 2024/03/27 01:22:30 tb Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -192,8 +192,7 @@ LCRYPTO_ALIAS(RSA_free); int RSA_up_ref(RSA *r) { - int i = CRYPTO_add(&r->references, 1, CRYPTO_LOCK_RSA); - return i > 1 ? 1 : 0; + return CRYPTO_add(&r->references, 1, CRYPTO_LOCK_RSA) > 1; } LCRYPTO_ALIAS(RSA_up_ref); diff --git a/lib/libcrypto/rsa/rsa_oaep.c b/lib/libcrypto/rsa/rsa_oaep.c index 38c9b478e..b2f1da003 100644 --- a/lib/libcrypto/rsa/rsa_oaep.c +++ b/lib/libcrypto/rsa/rsa_oaep.c @@ -1,4 +1,4 @@ -/* $OpenBSD: rsa_oaep.c,v 1.38 2024/02/18 15:45:42 tb Exp $ */ +/* $OpenBSD: rsa_oaep.c,v 1.39 2024/03/26 05:37:28 joshua Exp $ */ /* * Copyright 1999-2018 The OpenSSL Project Authors. All Rights Reserved. * @@ -326,12 +326,14 @@ PKCS1_MGF1(unsigned char *mask, long len, const unsigned char *seed, { long i, outlen = 0; unsigned char cnt[4]; - EVP_MD_CTX c; + EVP_MD_CTX *md_ctx; unsigned char md[EVP_MAX_MD_SIZE]; int mdlen; int rv = -1; - EVP_MD_CTX_legacy_clear(&c); + if ((md_ctx = EVP_MD_CTX_new()) == NULL) + goto err; + mdlen = EVP_MD_size(dgst); if (mdlen < 0) goto err; @@ -340,24 +342,27 @@ PKCS1_MGF1(unsigned char *mask, long len, const unsigned char *seed, cnt[1] = (unsigned char)((i >> 16) & 255); cnt[2] = (unsigned char)((i >> 8)) & 255; cnt[3] = (unsigned char)(i & 255); - if (!EVP_DigestInit_ex(&c, dgst, NULL) || - !EVP_DigestUpdate(&c, seed, seedlen) || - !EVP_DigestUpdate(&c, cnt, 4)) + if (!EVP_DigestInit_ex(md_ctx, dgst, NULL) || + !EVP_DigestUpdate(md_ctx, seed, seedlen) || + !EVP_DigestUpdate(md_ctx, cnt, 4)) goto err; if (outlen + mdlen <= len) { - if (!EVP_DigestFinal_ex(&c, mask + outlen, NULL)) + if (!EVP_DigestFinal_ex(md_ctx, mask + outlen, NULL)) goto err; outlen += mdlen; } else { - if (!EVP_DigestFinal_ex(&c, md, NULL)) + if (!EVP_DigestFinal_ex(md_ctx, md, NULL)) goto err; memcpy(mask + outlen, md, len - outlen); outlen = len; } } + rv = 0; + err: - EVP_MD_CTX_cleanup(&c); + EVP_MD_CTX_free(md_ctx); + return rv; } LCRYPTO_ALIAS(PKCS1_MGF1); diff --git a/lib/libcrypto/rsa/rsa_pss.c b/lib/libcrypto/rsa/rsa_pss.c index 6670866ff..610ae7c92 100644 --- a/lib/libcrypto/rsa/rsa_pss.c +++ b/lib/libcrypto/rsa/rsa_pss.c @@ -1,4 +1,4 @@ -/* $OpenBSD: rsa_pss.c,v 1.18 2024/02/18 15:45:42 tb Exp $ */ +/* $OpenBSD: rsa_pss.c,v 1.19 2024/03/26 05:26:27 joshua Exp $ */ /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL * project 2005. */ @@ -89,10 +89,11 @@ RSA_verify_PKCS1_PSS_mgf1(RSA *rsa, const unsigned char *mHash, int hLen, maskedDBLen, MSBits, emLen; const unsigned char *H; unsigned char *DB = NULL; - EVP_MD_CTX ctx; + EVP_MD_CTX *md_ctx; unsigned char H_[EVP_MAX_MD_SIZE]; - EVP_MD_CTX_legacy_clear(&ctx); + if ((md_ctx = EVP_MD_CTX_new()) == NULL) + goto err; if (mgf1Hash == NULL) mgf1Hash = Hash; @@ -157,25 +158,26 @@ RSA_verify_PKCS1_PSS_mgf1(RSA *rsa, const unsigned char *mHash, RSAerror(RSA_R_SLEN_CHECK_FAILED); goto err; } - if (!EVP_DigestInit_ex(&ctx, Hash, NULL) || - !EVP_DigestUpdate(&ctx, zeroes, sizeof zeroes) || - !EVP_DigestUpdate(&ctx, mHash, hLen)) + if (!EVP_DigestInit_ex(md_ctx, Hash, NULL) || + !EVP_DigestUpdate(md_ctx, zeroes, sizeof zeroes) || + !EVP_DigestUpdate(md_ctx, mHash, hLen)) goto err; if (maskedDBLen - i) { - if (!EVP_DigestUpdate(&ctx, DB + i, maskedDBLen - i)) + if (!EVP_DigestUpdate(md_ctx, DB + i, maskedDBLen - i)) goto err; } - if (!EVP_DigestFinal_ex(&ctx, H_, NULL)) + if (!EVP_DigestFinal_ex(md_ctx, H_, NULL)) goto err; if (timingsafe_bcmp(H_, H, hLen)) { RSAerror(RSA_R_BAD_SIGNATURE); ret = 0; - } else + } else { ret = 1; + } -err: + err: free(DB); - EVP_MD_CTX_cleanup(&ctx); + EVP_MD_CTX_free(md_ctx); return ret; } @@ -198,9 +200,10 @@ RSA_padding_add_PKCS1_PSS_mgf1(RSA *rsa, unsigned char *EM, int ret = 0; int hLen, maskedDBLen, MSBits, emLen; unsigned char *H, *salt = NULL, *p; - EVP_MD_CTX ctx; + EVP_MD_CTX *md_ctx; - EVP_MD_CTX_legacy_clear(&ctx); + if ((md_ctx = EVP_MD_CTX_new()) == NULL) + goto err; if (mgf1Hash == NULL) mgf1Hash = Hash; @@ -245,13 +248,13 @@ RSA_padding_add_PKCS1_PSS_mgf1(RSA *rsa, unsigned char *EM, } maskedDBLen = emLen - hLen - 1; H = EM + maskedDBLen; - if (!EVP_DigestInit_ex(&ctx, Hash, NULL) || - !EVP_DigestUpdate(&ctx, zeroes, sizeof zeroes) || - !EVP_DigestUpdate(&ctx, mHash, hLen)) + if (!EVP_DigestInit_ex(md_ctx, Hash, NULL) || + !EVP_DigestUpdate(md_ctx, zeroes, sizeof zeroes) || + !EVP_DigestUpdate(md_ctx, mHash, hLen)) goto err; - if (sLen && !EVP_DigestUpdate(&ctx, salt, sLen)) + if (sLen && !EVP_DigestUpdate(md_ctx, salt, sLen)) goto err; - if (!EVP_DigestFinal_ex(&ctx, H, NULL)) + if (!EVP_DigestFinal_ex(md_ctx, H, NULL)) goto err; /* Generate dbMask in place then perform XOR on it */ @@ -281,7 +284,7 @@ RSA_padding_add_PKCS1_PSS_mgf1(RSA *rsa, unsigned char *EM, err: free(salt); - EVP_MD_CTX_cleanup(&ctx); + EVP_MD_CTX_free(md_ctx); return ret; } diff --git a/lib/libcrypto/sha/sha1.c b/lib/libcrypto/sha/sha1.c index 4b48653bd..8bcc5e043 100644 --- a/lib/libcrypto/sha/sha1.c +++ b/lib/libcrypto/sha/sha1.c @@ -1,4 +1,4 @@ -/* $OpenBSD: sha1.c,v 1.12 2023/08/10 07:15:23 jsing Exp $ */ +/* $OpenBSD: sha1.c,v 1.13 2024/03/26 12:54:22 jsing Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -64,8 +64,13 @@ #include #include +#include "crypto_internal.h" + #if !defined(OPENSSL_NO_SHA1) && !defined(OPENSSL_NO_SHA) +/* Ensure that SHA_LONG and uint32_t are equivalent sizes. */ +CTASSERT(sizeof(SHA_LONG) == sizeof(uint32_t)); + #define DATA_ORDER_IS_BIG_ENDIAN #define HASH_LONG SHA_LONG @@ -138,109 +143,77 @@ void sha1_block_data_order(SHA_CTX *c, const void *p, size_t num); #if !defined(SHA1_ASM) #include static void -sha1_block_data_order(SHA_CTX *c, const void *p, size_t num) +sha1_block_data_order(SHA_CTX *c, const void *_in, size_t num) { - const unsigned char *data = p; - unsigned int A, B, C, D, E, T, l; + const uint8_t *in = _in; + const SHA_LONG *in32; + unsigned int A, B, C, D, E, T; unsigned int X0, X1, X2, X3, X4, X5, X6, X7, X8, X9, X10, X11, X12, X13, X14, X15; - A = c->h0; - B = c->h1; - C = c->h2; - D = c->h3; - E = c->h4; + while (num--) { + A = c->h0; + B = c->h1; + C = c->h2; + D = c->h3; + E = c->h4; - for (;;) { - - if (BYTE_ORDER != LITTLE_ENDIAN && - sizeof(SHA_LONG) == 4 && ((size_t)p % 4) == 0) { - const SHA_LONG *W = (const SHA_LONG *)data; - - X0 = W[0]; - X1 = W[1]; - BODY_00_15( 0, A, B, C, D, E, T, X0); - X2 = W[2]; - BODY_00_15( 1, T, A, B, C, D, E, X1); - X3 = W[3]; - BODY_00_15( 2, E, T, A, B, C, D, X2); - X4 = W[4]; - BODY_00_15( 3, D, E, T, A, B, C, X3); - X5 = W[5]; - BODY_00_15( 4, C, D, E, T, A, B, X4); - X6 = W[6]; - BODY_00_15( 5, B, C, D, E, T, A, X5); - X7 = W[7]; - BODY_00_15( 6, A, B, C, D, E, T, X6); - X8 = W[8]; - BODY_00_15( 7, T, A, B, C, D, E, X7); - X9 = W[9]; - BODY_00_15( 8, E, T, A, B, C, D, X8); - X10 = W[10]; - BODY_00_15( 9, D, E, T, A, B, C, X9); - X11 = W[11]; - BODY_00_15(10, C, D, E, T, A, B, X10); - X12 = W[12]; - BODY_00_15(11, B, C, D, E, T, A, X11); - X13 = W[13]; - BODY_00_15(12, A, B, C, D, E, T, X12); - X14 = W[14]; - BODY_00_15(13, T, A, B, C, D, E, X13); - X15 = W[15]; - BODY_00_15(14, E, T, A, B, C, D, X14); - BODY_00_15(15, D, E, T, A, B, C, X15); - - data += SHA_CBLOCK; + if ((size_t)in % 4 == 0) { + /* Input is 32 bit aligned. */ + in32 = (const SHA_LONG *)in; + X0 = be32toh(in32[0]); + X1 = be32toh(in32[1]); + X2 = be32toh(in32[2]); + X3 = be32toh(in32[3]); + X4 = be32toh(in32[4]); + X5 = be32toh(in32[5]); + X6 = be32toh(in32[6]); + X7 = be32toh(in32[7]); + X8 = be32toh(in32[8]); + X9 = be32toh(in32[9]); + X10 = be32toh(in32[10]); + X11 = be32toh(in32[11]); + X12 = be32toh(in32[12]); + X13 = be32toh(in32[13]); + X14 = be32toh(in32[14]); + X15 = be32toh(in32[15]); } else { - HOST_c2l(data, l); - X0 = l; - HOST_c2l(data, l); - X1 = l; - BODY_00_15( 0, A, B, C, D, E, T, X0); - HOST_c2l(data, l); - X2 = l; - BODY_00_15( 1, T, A, B, C, D, E, X1); - HOST_c2l(data, l); - X3 = l; - BODY_00_15( 2, E, T, A, B, C, D, X2); - HOST_c2l(data, l); - X4 = l; - BODY_00_15( 3, D, E, T, A, B, C, X3); - HOST_c2l(data, l); - X5 = l; - BODY_00_15( 4, C, D, E, T, A, B, X4); - HOST_c2l(data, l); - X6 = l; - BODY_00_15( 5, B, C, D, E, T, A, X5); - HOST_c2l(data, l); - X7 = l; - BODY_00_15( 6, A, B, C, D, E, T, X6); - HOST_c2l(data, l); - X8 = l; - BODY_00_15( 7, T, A, B, C, D, E, X7); - HOST_c2l(data, l); - X9 = l; - BODY_00_15( 8, E, T, A, B, C, D, X8); - HOST_c2l(data, l); - X10 = l; - BODY_00_15( 9, D, E, T, A, B, C, X9); - HOST_c2l(data, l); - X11 = l; - BODY_00_15(10, C, D, E, T, A, B, X10); - HOST_c2l(data, l); - X12 = l; - BODY_00_15(11, B, C, D, E, T, A, X11); - HOST_c2l(data, l); - X13 = l; - BODY_00_15(12, A, B, C, D, E, T, X12); - HOST_c2l(data, l); - X14 = l; - BODY_00_15(13, T, A, B, C, D, E, X13); - HOST_c2l(data, l); - X15 = l; - BODY_00_15(14, E, T, A, B, C, D, X14); - BODY_00_15(15, D, E, T, A, B, C, X15); + /* Input is not 32 bit aligned. */ + X0 = crypto_load_be32toh(&in[0 * 4]); + X1 = crypto_load_be32toh(&in[1 * 4]); + X2 = crypto_load_be32toh(&in[2 * 4]); + X3 = crypto_load_be32toh(&in[3 * 4]); + X4 = crypto_load_be32toh(&in[4 * 4]); + X5 = crypto_load_be32toh(&in[5 * 4]); + X6 = crypto_load_be32toh(&in[6 * 4]); + X7 = crypto_load_be32toh(&in[7 * 4]); + X8 = crypto_load_be32toh(&in[8 * 4]); + X9 = crypto_load_be32toh(&in[9 * 4]); + X10 = crypto_load_be32toh(&in[10 * 4]); + X11 = crypto_load_be32toh(&in[11 * 4]); + X12 = crypto_load_be32toh(&in[12 * 4]); + X13 = crypto_load_be32toh(&in[13 * 4]); + X14 = crypto_load_be32toh(&in[14 * 4]); + X15 = crypto_load_be32toh(&in[15 * 4]); } + in += SHA_CBLOCK; + + BODY_00_15( 0, A, B, C, D, E, T, X0); + BODY_00_15( 1, T, A, B, C, D, E, X1); + BODY_00_15( 2, E, T, A, B, C, D, X2); + BODY_00_15( 3, D, E, T, A, B, C, X3); + BODY_00_15( 4, C, D, E, T, A, B, X4); + BODY_00_15( 5, B, C, D, E, T, A, X5); + BODY_00_15( 6, A, B, C, D, E, T, X6); + BODY_00_15( 7, T, A, B, C, D, E, X7); + BODY_00_15( 8, E, T, A, B, C, D, X8); + BODY_00_15( 9, D, E, T, A, B, C, X9); + BODY_00_15(10, C, D, E, T, A, B, X10); + BODY_00_15(11, B, C, D, E, T, A, X11); + BODY_00_15(12, A, B, C, D, E, T, X12); + BODY_00_15(13, T, A, B, C, D, E, X13); + BODY_00_15(14, E, T, A, B, C, D, X14); + BODY_00_15(15, D, E, T, A, B, C, X15); BODY_16_19(16, C, D, E, T, A, B, X0, X0, X2, X8, X13); BODY_16_19(17, B, C, D, E, T, A, X1, X1, X3, X9, X14); @@ -316,16 +289,6 @@ sha1_block_data_order(SHA_CTX *c, const void *p, size_t num) c->h2 = (c->h2 + A)&0xffffffffL; c->h3 = (c->h3 + B)&0xffffffffL; c->h4 = (c->h4 + C)&0xffffffffL; - - if (--num == 0) - break; - - A = c->h0; - B = c->h1; - C = c->h2; - D = c->h3; - E = c->h4; - } } #endif @@ -412,7 +375,6 @@ int SHA1_Final(unsigned char *md, SHA_CTX *c) { unsigned char *p = (unsigned char *)c->data; - unsigned long ll; size_t n = c->num; p[n] = 0x80; /* there is always room for one */ @@ -423,31 +385,20 @@ SHA1_Final(unsigned char *md, SHA_CTX *c) n = 0; sha1_block_data_order(c, p, 1); } - memset(p + n, 0, SHA_CBLOCK - 8 - n); - p += SHA_CBLOCK - 8; -#if defined(DATA_ORDER_IS_BIG_ENDIAN) - HOST_l2c(c->Nh, p); - HOST_l2c(c->Nl, p); -#elif defined(DATA_ORDER_IS_LITTLE_ENDIAN) - HOST_l2c(c->Nl, p); - HOST_l2c(c->Nh, p); -#endif - p -= SHA_CBLOCK; + memset(p + n, 0, SHA_CBLOCK - 8 - n); + c->data[SHA_LBLOCK - 2] = htobe32(c->Nh); + c->data[SHA_LBLOCK - 1] = htobe32(c->Nl); + sha1_block_data_order(c, p, 1); c->num = 0; memset(p, 0, SHA_CBLOCK); - ll = c->h0; - HOST_l2c(ll, md); - ll = c->h1; - HOST_l2c(ll, md); - ll = c->h2; - HOST_l2c(ll, md); - ll = c->h3; - HOST_l2c(ll, md); - ll = c->h4; - HOST_l2c(ll, md); + crypto_store_htobe32(&md[0 * 4], c->h0); + crypto_store_htobe32(&md[1 * 4], c->h1); + crypto_store_htobe32(&md[2 * 4], c->h2); + crypto_store_htobe32(&md[3 * 4], c->h3); + crypto_store_htobe32(&md[4 * 4], c->h4); return 1; } diff --git a/lib/libcrypto/x509/x509_local.h b/lib/libcrypto/x509/x509_local.h index 83b57403d..73cc582d7 100644 --- a/lib/libcrypto/x509/x509_local.h +++ b/lib/libcrypto/x509/x509_local.h @@ -1,4 +1,4 @@ -/* $OpenBSD: x509_local.h,v 1.22 2024/03/02 10:52:24 tb Exp $ */ +/* $OpenBSD: x509_local.h,v 1.23 2024/03/26 05:39:47 tb Exp $ */ /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL * project 2013. */ @@ -404,8 +404,6 @@ int PKCS5_pbe_set0_algor(X509_ALGOR *algor, int alg, int iter, const unsigned char *salt, int saltlen); X509_ALGOR *PKCS5_pbe2_set(const EVP_CIPHER *cipher, int iter, unsigned char *salt, int saltlen); -X509_ALGOR *PKCS5_pbe2_set_iv(const EVP_CIPHER *cipher, int iter, - unsigned char *salt, int saltlen, unsigned char *aiv, int prf_nid); X509_ALGOR *PKCS5_pbe_set(int alg, int iter, const unsigned char *salt, int saltlen); X509_ALGOR *PKCS5_pbkdf2_set(int iter, unsigned char *salt, int saltlen, diff --git a/lib/libcrypto/x509/x509_set.c b/lib/libcrypto/x509/x509_set.c index b56d30aec..442bc1282 100644 --- a/lib/libcrypto/x509/x509_set.c +++ b/lib/libcrypto/x509/x509_set.c @@ -1,4 +1,4 @@ -/* $OpenBSD: x509_set.c,v 1.26 2023/06/23 08:00:28 tb Exp $ */ +/* $OpenBSD: x509_set.c,v 1.29 2024/03/26 23:21:36 tb Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -83,13 +83,19 @@ int X509_set_version(X509 *x, long version) { if (x == NULL) - return (0); + return 0; + /* + * RFC 5280, 4.1: versions 1 - 3 are specified as follows. + * Version ::= INTEGER { v1(0), v2(1), v3(2) } + */ + if (version < 0 || version > 2) + return 0; if (x->cert_info->version == NULL) { if ((x->cert_info->version = ASN1_INTEGER_new()) == NULL) - return (0); + return 0; } x->cert_info->enc.modified = 1; - return (ASN1_INTEGER_set(x->cert_info->version, version)); + return ASN1_INTEGER_set(x->cert_info->version, version); } LCRYPTO_ALIAS(X509_set_version); @@ -251,12 +257,12 @@ X509_get_X509_PUBKEY(const X509 *x) LCRYPTO_ALIAS(X509_get_X509_PUBKEY); void -X509_get0_uids(const X509 *x, const ASN1_BIT_STRING **piuid, - const ASN1_BIT_STRING **psuid) +X509_get0_uids(const X509 *x, const ASN1_BIT_STRING **issuerUID, + const ASN1_BIT_STRING **subjectUID) { - if (piuid != NULL) - *piuid = x->cert_info->issuerUID; - if (psuid != NULL) - *psuid = x->cert_info->subjectUID; + if (issuerUID != NULL) + *issuerUID = x->cert_info->issuerUID; + if (subjectUID != NULL) + *subjectUID = x->cert_info->subjectUID; } LCRYPTO_ALIAS(X509_get0_uids); diff --git a/lib/libcrypto/x509/x509_trs.c b/lib/libcrypto/x509/x509_trs.c index 18eb8b86c..f0f4eefb6 100644 --- a/lib/libcrypto/x509/x509_trs.c +++ b/lib/libcrypto/x509/x509_trs.c @@ -1,4 +1,4 @@ -/* $OpenBSD: x509_trs.c,v 1.54 2024/03/25 04:03:26 tb Exp $ */ +/* $OpenBSD: x509_trs.c,v 1.55 2024/03/26 22:43:42 tb Exp $ */ /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL * project 1999. */ @@ -59,12 +59,10 @@ #include #include -#include #include #include #include -#include "crypto_internal.h" #include "x509_internal.h" #include "x509_local.h" diff --git a/lib/libcrypto/x509/x509cset.c b/lib/libcrypto/x509/x509cset.c index 7904a7d67..468831266 100644 --- a/lib/libcrypto/x509/x509cset.c +++ b/lib/libcrypto/x509/x509cset.c @@ -1,4 +1,4 @@ -/* $OpenBSD: x509cset.c,v 1.19 2023/02/16 08:38:17 tb Exp $ */ +/* $OpenBSD: x509cset.c,v 1.22 2024/03/26 23:41:45 tb Exp $ */ /* Written by Dr Stephen N Henson (steve@openssl.org) for the OpenSSL * project 2001. */ @@ -68,8 +68,7 @@ int X509_CRL_up_ref(X509_CRL *x) { - int refs = CRYPTO_add(&x->references, 1, CRYPTO_LOCK_X509_CRL); - return (refs > 1) ? 1 : 0; + return CRYPTO_add(&x->references, 1, CRYPTO_LOCK_X509_CRL) > 1; } LCRYPTO_ALIAS(X509_CRL_up_ref); @@ -77,21 +76,28 @@ int X509_CRL_set_version(X509_CRL *x, long version) { if (x == NULL) - return (0); + return 0; + /* + * RFC 5280, 4.1: versions 1 - 3 are specified as follows. + * Version ::= INTEGER { v1(0), v2(1), v3(2) } + * The only specified versions for CRLs are 1 and 2. + */ + if (version < 0 || version > 1) + return 0; if (x->crl->version == NULL) { if ((x->crl->version = ASN1_INTEGER_new()) == NULL) - return (0); + return 0; } - return (ASN1_INTEGER_set(x->crl->version, version)); + return ASN1_INTEGER_set(x->crl->version, version); } LCRYPTO_ALIAS(X509_CRL_set_version); int X509_CRL_set_issuer_name(X509_CRL *x, X509_NAME *name) { - if ((x == NULL) || (x->crl == NULL)) - return (0); - return (X509_NAME_set(&x->crl->issuer, name)); + if (x == NULL || x->crl == NULL) + return 0; + return X509_NAME_set(&x->crl->issuer, name); } LCRYPTO_ALIAS(X509_CRL_set_issuer_name); @@ -101,7 +107,7 @@ X509_CRL_set_lastUpdate(X509_CRL *x, const ASN1_TIME *tm) ASN1_TIME *in; if (x == NULL) - return (0); + return 0; in = x->crl->lastUpdate; if (in != tm) { in = ASN1_STRING_dup(tm); @@ -110,7 +116,7 @@ X509_CRL_set_lastUpdate(X509_CRL *x, const ASN1_TIME *tm) x->crl->lastUpdate = in; } } - return (in != NULL); + return in != NULL; } LCRYPTO_ALIAS(X509_CRL_set_lastUpdate); @@ -127,7 +133,7 @@ X509_CRL_set_nextUpdate(X509_CRL *x, const ASN1_TIME *tm) ASN1_TIME *in; if (x == NULL) - return (0); + return 0; in = x->crl->nextUpdate; if (in != tm) { in = ASN1_STRING_dup(tm); @@ -136,7 +142,7 @@ X509_CRL_set_nextUpdate(X509_CRL *x, const ASN1_TIME *tm) x->crl->nextUpdate = in; } } - return (in != NULL); + return in != NULL; } LCRYPTO_ALIAS(X509_CRL_set_nextUpdate); @@ -150,11 +156,10 @@ LCRYPTO_ALIAS(X509_CRL_set1_nextUpdate); int X509_CRL_sort(X509_CRL *c) { - int i; X509_REVOKED *r; + int i; - /* sort the data so it will be written in serial - * number order */ + /* Sort the data so it will be written in serial number order */ sk_X509_REVOKED_sort(c->crl->revoked); for (i = 0; i < sk_X509_REVOKED_num(c->crl->revoked); i++) { r = sk_X509_REVOKED_value(c->crl->revoked, i); @@ -192,7 +197,7 @@ X509_REVOKED_set_revocationDate(X509_REVOKED *x, ASN1_TIME *tm) ASN1_TIME *in; if (x == NULL) - return (0); + return 0; in = x->revocationDate; if (in != tm) { in = ASN1_STRING_dup(tm); @@ -201,7 +206,7 @@ X509_REVOKED_set_revocationDate(X509_REVOKED *x, ASN1_TIME *tm) x->revocationDate = in; } } - return (in != NULL); + return in != NULL; } LCRYPTO_ALIAS(X509_REVOKED_set_revocationDate); @@ -211,7 +216,7 @@ X509_REVOKED_set_serialNumber(X509_REVOKED *x, ASN1_INTEGER *serial) ASN1_INTEGER *in; if (x == NULL) - return (0); + return 0; in = x->serialNumber; if (in != serial) { in = ASN1_INTEGER_dup(serial); @@ -220,7 +225,7 @@ X509_REVOKED_set_serialNumber(X509_REVOKED *x, ASN1_INTEGER *serial) x->serialNumber = in; } } - return (in != NULL); + return in != NULL; } LCRYPTO_ALIAS(X509_REVOKED_set_serialNumber); diff --git a/lib/libcrypto/x509/x509rset.c b/lib/libcrypto/x509/x509rset.c index b05b2a1c9..2e2d4abd0 100644 --- a/lib/libcrypto/x509/x509rset.c +++ b/lib/libcrypto/x509/x509rset.c @@ -1,4 +1,4 @@ -/* $OpenBSD: x509rset.c,v 1.14 2024/03/25 12:10:57 jsing Exp $ */ +/* $OpenBSD: x509rset.c,v 1.16 2024/03/26 23:45:05 tb Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -69,9 +69,12 @@ int X509_REQ_set_version(X509_REQ *x, long version) { if (x == NULL) - return (0); + return 0; + /* RFC 2986 section 4.1 only specifies version 1, encoded as a 0. */ + if (version != 0) + return 0; x->req_info->enc.modified = 1; - return (ASN1_INTEGER_set(x->req_info->version, version)); + return ASN1_INTEGER_set(x->req_info->version, version); } LCRYPTO_ALIAS(X509_REQ_set_version); @@ -85,10 +88,10 @@ LCRYPTO_ALIAS(X509_REQ_get_version); int X509_REQ_set_subject_name(X509_REQ *x, X509_NAME *name) { - if ((x == NULL) || (x->req_info == NULL)) - return (0); + if (x == NULL || x->req_info == NULL) + return 0; x->req_info->enc.modified = 1; - return (X509_NAME_set(&x->req_info->subject, name)); + return X509_NAME_set(&x->req_info->subject, name); } LCRYPTO_ALIAS(X509_REQ_set_subject_name); @@ -102,9 +105,9 @@ LCRYPTO_ALIAS(X509_REQ_get_subject_name); int X509_REQ_set_pubkey(X509_REQ *x, EVP_PKEY *pkey) { - if ((x == NULL) || (x->req_info == NULL)) - return (0); + if (x == NULL || x->req_info == NULL) + return 0; x->req_info->enc.modified = 1; - return (X509_PUBKEY_set(&x->req_info->pubkey, pkey)); + return X509_PUBKEY_set(&x->req_info->pubkey, pkey); } LCRYPTO_ALIAS(X509_REQ_set_pubkey); diff --git a/lib/libcrypto/x509/x_all.c b/lib/libcrypto/x509/x_all.c index cd6da9f40..45c527b41 100644 --- a/lib/libcrypto/x509/x_all.c +++ b/lib/libcrypto/x509/x_all.c @@ -1,4 +1,4 @@ -/* $OpenBSD: x_all.c,v 1.30 2023/02/16 08:38:17 tb Exp $ */ +/* $OpenBSD: x_all.c,v 1.31 2024/03/27 01:22:30 tb Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -535,7 +535,6 @@ LCRYPTO_ALIAS(X509_NAME_digest); int X509_up_ref(X509 *x) { - int i = CRYPTO_add(&x->references, 1, CRYPTO_LOCK_X509); - return i > 1 ? 1 : 0; + return CRYPTO_add(&x->references, 1, CRYPTO_LOCK_X509) > 1; } LCRYPTO_ALIAS(X509_up_ref); diff --git a/lib/libssl/ssl_local.h b/lib/libssl/ssl_local.h index b4d093b22..2266d5e3c 100644 --- a/lib/libssl/ssl_local.h +++ b/lib/libssl/ssl_local.h @@ -1,4 +1,4 @@ -/* $OpenBSD: ssl_local.h,v 1.13 2024/02/03 15:58:34 beck Exp $ */ +/* $OpenBSD: ssl_local.h,v 1.14 2024/03/26 03:44:11 beck Exp $ */ /* Copyright (C) 1995-1998 Eric Young (eay@cryptsoft.com) * All rights reserved. * @@ -599,6 +599,9 @@ typedef struct ssl_handshake_st { /* Extensions seen in this handshake. */ uint32_t extensions_seen; + /* Extensions processed in this handshake. */ + uint32_t extensions_processed; + /* Signature algorithms selected for use (static pointers). */ const struct ssl_sigalg *our_sigalg; const struct ssl_sigalg *peer_sigalg; diff --git a/lib/libssl/ssl_tlsext.c b/lib/libssl/ssl_tlsext.c index 3883aa6ce..e1506e5d6 100644 --- a/lib/libssl/ssl_tlsext.c +++ b/lib/libssl/ssl_tlsext.c @@ -1,4 +1,4 @@ -/* $OpenBSD: ssl_tlsext.c,v 1.142 2024/03/26 01:21:34 beck Exp $ */ +/* $OpenBSD: ssl_tlsext.c,v 1.143 2024/03/26 03:44:11 beck Exp $ */ /* * Copyright (c) 2016, 2017, 2019 Joel Sing * Copyright (c) 2017 Doug Hogan @@ -2253,6 +2253,16 @@ tlsext_extension_seen(SSL *s, uint16_t type) return ((s->s3->hs.extensions_seen & (1 << idx)) != 0); } +int +tlsext_extension_processed(SSL *s, uint16_t type) +{ + size_t idx; + + if (tls_extension_find(type, &idx) == NULL) + return 0; + return ((s->s3->hs.extensions_processed & (1 << idx)) != 0); +} + const struct tls_extension_funcs * tlsext_funcs(const struct tls_extension *tlsext, int is_server) { @@ -2490,6 +2500,8 @@ tlsext_process(SSL *s, struct tlsext_data *td, int is_server, uint16_t msg_type, alert_desc = SSL_AD_DECODE_ERROR; + s->s3->hs.extensions_processed = 0; + /* Run processing for present TLS extensions, in a defined order. */ for (idx = 0; idx < N_TLS_EXTENSIONS; idx++) { tlsext = &tls_extensions[idx]; @@ -2503,6 +2515,8 @@ tlsext_process(SSL *s, struct tlsext_data *td, int is_server, uint16_t msg_type, if (CBS_len(&td->extensions[idx]) != 0) goto err; + + s->s3->hs.extensions_processed |= (1 << idx); } return 1; diff --git a/lib/libssl/ssl_tlsext.h b/lib/libssl/ssl_tlsext.h index da14f7fa9..4fd2ec05a 100644 --- a/lib/libssl/ssl_tlsext.h +++ b/lib/libssl/ssl_tlsext.h @@ -1,4 +1,4 @@ -/* $OpenBSD: ssl_tlsext.h,v 1.33 2023/04/23 18:51:53 tb Exp $ */ +/* $OpenBSD: ssl_tlsext.h,v 1.34 2024/03/26 03:44:11 beck Exp $ */ /* * Copyright (c) 2016, 2017 Joel Sing * Copyright (c) 2017 Doug Hogan @@ -41,6 +41,7 @@ int tlsext_server_build(SSL *s, uint16_t msg_type, CBB *cbb); int tlsext_server_parse(SSL *s, uint16_t msg_type, CBS *cbs, int *alert); int tlsext_extension_seen(SSL *s, uint16_t); +int tlsext_extension_processed(SSL *s, uint16_t); int tlsext_randomize_build_order(SSL *s); __END_HIDDEN_DECLS diff --git a/lib/libtls/tls.c b/lib/libtls/tls.c index 58245009d..a8b03f0d4 100644 --- a/lib/libtls/tls.c +++ b/lib/libtls/tls.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tls.c,v 1.100 2024/03/26 01:15:57 joshua Exp $ */ +/* $OpenBSD: tls.c,v 1.102 2024/03/26 08:54:48 joshua Exp $ */ /* * Copyright (c) 2014 Joel Sing * @@ -72,23 +72,32 @@ tls_error(struct tls *ctx) return ctx->error.msg; } +int +tls_error_code(struct tls *ctx) +{ + return ctx->error.code; +} + void tls_error_clear(struct tls_error *error) { free(error->msg); error->msg = NULL; + error->code = TLS_ERROR_UNKNOWN; error->errno_value = 0; error->tls = 0; } static int -tls_error_vset(struct tls_error *error, int errno_value, const char *fmt, va_list ap) +tls_error_vset(struct tls_error *error, int code, int errno_value, + const char *fmt, va_list ap) { char *errmsg = NULL; int rv = -1; tls_error_clear(error); + error->code = code; error->errno_value = errno_value; error->tls = 1; @@ -115,7 +124,7 @@ tls_error_vset(struct tls_error *error, int errno_value, const char *fmt, va_lis } int -tls_error_set(struct tls_error *error, const char *fmt, ...) +tls_error_set(struct tls_error *error, int code, const char *fmt, ...) { va_list ap; int errno_value, rv; @@ -123,27 +132,27 @@ tls_error_set(struct tls_error *error, const char *fmt, ...) errno_value = errno; va_start(ap, fmt); - rv = tls_error_vset(error, errno_value, fmt, ap); + rv = tls_error_vset(error, code, errno_value, fmt, ap); va_end(ap); return (rv); } int -tls_error_setx(struct tls_error *error, const char *fmt, ...) +tls_error_setx(struct tls_error *error, int code, const char *fmt, ...) { va_list ap; int rv; va_start(ap, fmt); - rv = tls_error_vset(error, -1, fmt, ap); + rv = tls_error_vset(error, code, -1, fmt, ap); va_end(ap); return (rv); } int -tls_config_set_error(struct tls_config *config, const char *fmt, ...) +tls_config_set_error(struct tls_config *config, int code, const char *fmt, ...) { va_list ap; int errno_value, rv; @@ -151,27 +160,27 @@ tls_config_set_error(struct tls_config *config, const char *fmt, ...) errno_value = errno; va_start(ap, fmt); - rv = tls_error_vset(&config->error, errno_value, fmt, ap); + rv = tls_error_vset(&config->error, code, errno_value, fmt, ap); va_end(ap); return (rv); } int -tls_config_set_errorx(struct tls_config *config, const char *fmt, ...) +tls_config_set_errorx(struct tls_config *config, int code, const char *fmt, ...) { va_list ap; int rv; va_start(ap, fmt); - rv = tls_error_vset(&config->error, -1, fmt, ap); + rv = tls_error_vset(&config->error, code, -1, fmt, ap); va_end(ap); return (rv); } int -tls_set_error(struct tls *ctx, const char *fmt, ...) +tls_set_error(struct tls *ctx, int code, const char *fmt, ...) { va_list ap; int errno_value, rv; @@ -179,27 +188,27 @@ tls_set_error(struct tls *ctx, const char *fmt, ...) errno_value = errno; va_start(ap, fmt); - rv = tls_error_vset(&ctx->error, errno_value, fmt, ap); + rv = tls_error_vset(&ctx->error, code, errno_value, fmt, ap); va_end(ap); return (rv); } int -tls_set_errorx(struct tls *ctx, const char *fmt, ...) +tls_set_errorx(struct tls *ctx, int code, const char *fmt, ...) { va_list ap; int rv; va_start(ap, fmt); - rv = tls_error_vset(&ctx->error, -1, fmt, ap); + rv = tls_error_vset(&ctx->error, code, -1, fmt, ap); va_end(ap); return (rv); } int -tls_set_ssl_errorx(struct tls *ctx, const char *fmt, ...) +tls_set_ssl_errorx(struct tls *ctx, int code, const char *fmt, ...) { va_list ap; int rv; @@ -209,7 +218,7 @@ tls_set_ssl_errorx(struct tls *ctx, const char *fmt, ...) return (0); va_start(ap, fmt); - rv = tls_error_vset(&ctx->error, -1, fmt, ap); + rv = tls_error_vset(&ctx->error, code, -1, fmt, ap); va_end(ap); return (rv); @@ -350,31 +359,35 @@ tls_keypair_to_pkey(struct tls *ctx, struct tls_keypair *keypair, EVP_PKEY **pke return (0); if (len > INT_MAX) { - tls_set_errorx(ctx, ctx->config->use_fake_private_key ? + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + ctx->config->use_fake_private_key ? "cert too long" : "key too long"); goto err; } if ((bio = BIO_new_mem_buf(mem, len)) == NULL) { - tls_set_errorx(ctx, "failed to create buffer"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "failed to create buffer"); goto err; } if (ctx->config->use_fake_private_key) { if ((x509 = PEM_read_bio_X509(bio, NULL, tls_password_cb, NULL)) == NULL) { - tls_set_errorx(ctx, "failed to read X509 certificate"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to read X509 certificate"); goto err; } if ((*pkey = X509_get_pubkey(x509)) == NULL) { - tls_set_errorx(ctx, "failed to retrieve pubkey"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to retrieve pubkey"); goto err; } } else { if ((*pkey = PEM_read_bio_PrivateKey(bio, NULL, tls_password_cb, NULL)) == NULL) { - tls_set_errorx(ctx, "failed to read private key"); - goto err; + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to read private key"); + goto err; } } @@ -399,7 +412,7 @@ tls_keypair_setup_pkey(struct tls *ctx, struct tls_keypair *keypair, EVP_PKEY *p return (0); if (keypair->pubkey_hash == NULL) { - tls_set_errorx(ctx, "public key hash not set"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "public key hash not set"); goto err; } @@ -407,7 +420,8 @@ tls_keypair_setup_pkey(struct tls *ctx, struct tls_keypair *keypair, EVP_PKEY *p case EVP_PKEY_RSA: if ((rsa = EVP_PKEY_get1_RSA(pkey)) == NULL || RSA_set_ex_data(rsa, 0, keypair->pubkey_hash) == 0) { - tls_set_errorx(ctx, "RSA key setup failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "RSA key setup failure"); goto err; } if (ctx->config->sign_cb != NULL) { @@ -415,20 +429,23 @@ tls_keypair_setup_pkey(struct tls *ctx, struct tls_keypair *keypair, EVP_PKEY *p if (rsa_method == NULL || RSA_set_ex_data(rsa, 1, ctx->config) == 0 || RSA_set_method(rsa, rsa_method) == 0) { - tls_set_errorx(ctx, "failed to setup RSA key"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to setup RSA key"); goto err; } } /* Reset the key to work around caching in OpenSSL 3. */ if (EVP_PKEY_set1_RSA(pkey, rsa) == 0) { - tls_set_errorx(ctx, "failed to set RSA key"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to set RSA key"); goto err; } break; case EVP_PKEY_EC: if ((eckey = EVP_PKEY_get1_EC_KEY(pkey)) == NULL || EC_KEY_set_ex_data(eckey, 0, keypair->pubkey_hash) == 0) { - tls_set_errorx(ctx, "EC key setup failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "EC key setup failure"); goto err; } if (ctx->config->sign_cb != NULL) { @@ -436,18 +453,20 @@ tls_keypair_setup_pkey(struct tls *ctx, struct tls_keypair *keypair, EVP_PKEY *p if (ecdsa_method == NULL || EC_KEY_set_ex_data(eckey, 1, ctx->config) == 0 || EC_KEY_set_method(eckey, ecdsa_method) == 0) { - tls_set_errorx(ctx, "failed to setup EC key"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to setup EC key"); goto err; } } /* Reset the key to work around caching in OpenSSL 3. */ if (EVP_PKEY_set1_EC_KEY(pkey, eckey) == 0) { - tls_set_errorx(ctx, "failed to set EC key"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to set EC key"); goto err; } break; default: - tls_set_errorx(ctx, "incorrect key type"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "incorrect key type"); goto err; } @@ -472,13 +491,15 @@ tls_configure_ssl_keypair(struct tls *ctx, SSL_CTX *ssl_ctx, if (keypair->cert_mem != NULL) { if (keypair->cert_len > INT_MAX) { - tls_set_errorx(ctx, "certificate too long"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "certificate too long"); goto err; } if (SSL_CTX_use_certificate_chain_mem(ssl_ctx, keypair->cert_mem, keypair->cert_len) != 1) { - tls_set_errorx(ctx, "failed to load certificate"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to load certificate"); goto err; } } @@ -489,7 +510,8 @@ tls_configure_ssl_keypair(struct tls *ctx, SSL_CTX *ssl_ctx, if (tls_keypair_setup_pkey(ctx, keypair, pkey) == -1) goto err; if (SSL_CTX_use_PrivateKey(ssl_ctx, pkey) != 1) { - tls_set_errorx(ctx, "failed to load private key"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to load private key"); goto err; } EVP_PKEY_free(pkey); @@ -498,7 +520,8 @@ tls_configure_ssl_keypair(struct tls *ctx, SSL_CTX *ssl_ctx, if (!ctx->config->skip_private_key_check && SSL_CTX_check_private_key(ssl_ctx) != 1) { - tls_set_errorx(ctx, "private/public key mismatch"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "private/public key mismatch"); goto err; } @@ -534,7 +557,8 @@ tls_configure_ssl(struct tls *ctx, SSL_CTX *ssl_ctx) if (ctx->config->alpn != NULL) { if (SSL_CTX_set_alpn_protos(ssl_ctx, ctx->config->alpn, ctx->config->alpn_len) != 0) { - tls_set_errorx(ctx, "failed to set alpn"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to set alpn"); goto err; } } @@ -542,7 +566,8 @@ tls_configure_ssl(struct tls *ctx, SSL_CTX *ssl_ctx) if (ctx->config->ciphers != NULL) { if (SSL_CTX_set_cipher_list(ssl_ctx, ctx->config->ciphers) != 1) { - tls_set_errorx(ctx, "failed to set ciphers"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to set ciphers"); goto err; } } @@ -572,7 +597,8 @@ tls_ssl_cert_verify_cb(X509_STORE_CTX *x509_ctx, void *arg) return (1); if ((X509_verify_cert(x509_ctx)) < 0) { - tls_set_errorx(ctx, "X509 verify cert failed"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "X509 verify cert failed"); return (0); } @@ -580,7 +606,8 @@ tls_ssl_cert_verify_cb(X509_STORE_CTX *x509_ctx, void *arg) if (x509_err == X509_V_OK) return (1); - tls_set_errorx(ctx, "certificate verification failed: %s", + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "certificate verification failed: %s", X509_verify_cert_error_string(x509_err)); return (0); @@ -620,31 +647,35 @@ tls_configure_ssl_verify(struct tls *ctx, SSL_CTX *ssl_ctx, int verify) if (ca_mem != NULL) { if (ca_len > INT_MAX) { - tls_set_errorx(ctx, "ca too long"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "ca too long"); goto err; } if (SSL_CTX_load_verify_mem(ssl_ctx, ca_mem, ca_len) != 1) { - tls_set_errorx(ctx, "ssl verify memory setup failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ssl verify memory setup failure"); goto err; } } else if (SSL_CTX_load_verify_locations(ssl_ctx, NULL, ctx->config->ca_path) != 1) { - tls_set_errorx(ctx, "ssl verify locations failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ssl verify locations failure"); goto err; } if (crl_mem != NULL) { if (crl_len > INT_MAX) { - tls_set_errorx(ctx, "crl too long"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "crl too long"); goto err; } if ((bio = BIO_new_mem_buf(crl_mem, crl_len)) == NULL) { - tls_set_errorx(ctx, "failed to create buffer"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to create buffer"); goto err; } if ((xis = PEM_X509_INFO_read_bio(bio, NULL, tls_password_cb, NULL)) == NULL) { - tls_set_errorx(ctx, "failed to parse crl"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to parse crl"); goto err; } store = SSL_CTX_get_cert_store(ssl_ctx); @@ -653,7 +684,8 @@ tls_configure_ssl_verify(struct tls *ctx, SSL_CTX *ssl_ctx, int verify) if (xi->crl == NULL) continue; if (!X509_STORE_add_crl(store, xi->crl)) { - tls_set_error(ctx, "failed to add crl"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "failed to add crl"); goto err; } } @@ -759,21 +791,24 @@ tls_ssl_error(struct tls *ctx, SSL *ssl_conn, int ssl_ret, const char *prefix) } else if (ssl_ret == -1) { errstr = strerror(errno); } - tls_set_ssl_errorx(ctx, "%s failed: %s", prefix, errstr); + tls_set_ssl_errorx(ctx, TLS_ERROR_UNKNOWN, + "%s failed: %s", prefix, errstr); return (-1); case SSL_ERROR_SSL: if ((err = ERR_peek_error()) != 0) { errstr = ERR_error_string(err, NULL); } - tls_set_ssl_errorx(ctx, "%s failed: %s", prefix, errstr); + tls_set_ssl_errorx(ctx, TLS_ERROR_UNKNOWN, + "%s failed: %s", prefix, errstr); return (-1); case SSL_ERROR_WANT_CONNECT: case SSL_ERROR_WANT_ACCEPT: case SSL_ERROR_WANT_X509_LOOKUP: default: - tls_set_ssl_errorx(ctx, "%s failed (%d)", prefix, ssl_err); + tls_set_ssl_errorx(ctx, TLS_ERROR_UNKNOWN, + "%s failed (%d)", prefix, ssl_err); return (-1); } } @@ -786,12 +821,14 @@ tls_handshake(struct tls *ctx) tls_error_clear(&ctx->error); if ((ctx->flags & (TLS_CLIENT | TLS_SERVER_CONN)) == 0) { - tls_set_errorx(ctx, "invalid operation for context"); + tls_set_errorx(ctx, TLS_ERROR_INVALID_CONTEXT, + "invalid operation for context"); goto out; } if ((ctx->state & TLS_HANDSHAKE_COMPLETE) != 0) { - tls_set_errorx(ctx, "handshake already completed"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "handshake already completed"); goto out; } @@ -828,7 +865,8 @@ tls_read(struct tls *ctx, void *buf, size_t buflen) } if (buflen > INT_MAX) { - tls_set_errorx(ctx, "buflen too long"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "buflen too long"); goto out; } @@ -859,7 +897,8 @@ tls_write(struct tls *ctx, const void *buf, size_t buflen) } if (buflen > INT_MAX) { - tls_set_errorx(ctx, "buflen too long"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "buflen too long"); goto out; } @@ -885,7 +924,8 @@ tls_close(struct tls *ctx) tls_error_clear(&ctx->error); if ((ctx->flags & (TLS_CLIENT | TLS_SERVER_CONN)) == 0) { - tls_set_errorx(ctx, "invalid operation for context"); + tls_set_errorx(ctx, TLS_ERROR_INVALID_CONTEXT, + "invalid operation for context"); rv = -1; goto out; } @@ -906,13 +946,13 @@ tls_close(struct tls *ctx) if (shutdown(ctx->socket, SHUT_RDWR) != 0) { if (rv == 0 && errno != ENOTCONN && errno != ECONNRESET) { - tls_set_error(ctx, "shutdown"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, "shutdown"); rv = -1; } } if (close(ctx->socket) != 0) { if (rv == 0) { - tls_set_error(ctx, "close"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, "close"); rv = -1; } } @@ -920,7 +960,7 @@ tls_close(struct tls *ctx) } if ((ctx->state & TLS_EOF_NO_CLOSE_NOTIFY) != 0) { - tls_set_errorx(ctx, "EOF without close notify"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "EOF without close notify"); rv = -1; } diff --git a/lib/libtls/tls.h b/lib/libtls/tls.h index 34183745e..b69c4af58 100644 --- a/lib/libtls/tls.h +++ b/lib/libtls/tls.h @@ -1,4 +1,4 @@ -/* $OpenBSD: tls.h,v 1.63 2023/07/02 06:37:27 beck Exp $ */ +/* $OpenBSD: tls.h,v 1.65 2024/03/26 08:54:48 joshua Exp $ */ /* * Copyright (c) 2014 Joel Sing * @@ -76,6 +76,13 @@ extern "C" { #define TLS_MAX_SESSION_ID_LENGTH 32 #define TLS_TICKET_KEY_SIZE 48 +/* Error codes */ +#if defined(LIBRESSL_NEXT_API) || defined(LIBRESSL_INTERNAL) +#define TLS_ERROR_UNKNOWN 0x0000 +#define TLS_ERROR_OUT_OF_MEMORY 0x1000 +#define TLS_ERROR_INVALID_CONTEXT 0x2000 +#endif + struct tls; struct tls_config; @@ -88,6 +95,10 @@ int tls_init(void); const char *tls_config_error(struct tls_config *_config); const char *tls_error(struct tls *_ctx); +#if defined(LIBRESSL_NEXT_API) || defined(LIBRESSL_INTERNAL) +int tls_config_error_code(struct tls_config *_config); +int tls_error_code(struct tls *_ctx); +#endif struct tls_config *tls_config_new(void); void tls_config_free(struct tls_config *_config); diff --git a/lib/libtls/tls_bio_cb.c b/lib/libtls/tls_bio_cb.c index 8a1edfd5e..56b9e12a7 100644 --- a/lib/libtls/tls_bio_cb.c +++ b/lib/libtls/tls_bio_cb.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tls_bio_cb.c,v 1.21 2023/05/14 07:26:25 op Exp $ */ +/* $OpenBSD: tls_bio_cb.c,v 1.22 2024/03/26 06:24:52 joshua Exp $ */ /* * Copyright (c) 2016 Tobias Pape * @@ -143,7 +143,7 @@ tls_set_cbs(struct tls *ctx, tls_read_cb read_cb, tls_write_cb write_cb, int rv = -1; if (read_cb == NULL || write_cb == NULL) { - tls_set_errorx(ctx, "no callbacks provided"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "no callbacks provided"); goto err; } @@ -152,11 +152,13 @@ tls_set_cbs(struct tls *ctx, tls_read_cb read_cb, tls_write_cb write_cb, ctx->cb_arg = cb_arg; if ((bio_cb = bio_s_cb()) == NULL) { - tls_set_errorx(ctx, "failed to create callback method"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to create callback method"); goto err; } if ((bio = BIO_new(bio_cb)) == NULL) { - tls_set_errorx(ctx, "failed to create callback i/o"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to create callback i/o"); goto err; } BIO_set_data(bio, ctx); diff --git a/lib/libtls/tls_client.c b/lib/libtls/tls_client.c index deb24ebc2..97e1d4021 100644 --- a/lib/libtls/tls_client.c +++ b/lib/libtls/tls_client.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tls_client.c,v 1.49 2023/05/14 07:26:25 op Exp $ */ +/* $OpenBSD: tls_client.c,v 1.51 2024/03/26 08:54:48 joshua Exp $ */ /* * Copyright (c) 2014 Joel Sing * @@ -66,12 +66,13 @@ tls_connect_servername(struct tls *ctx, const char *host, const char *port, int rv = -1, s = -1, ret; if ((ctx->flags & TLS_CLIENT) == 0) { - tls_set_errorx(ctx, "not a client context"); + tls_set_errorx(ctx, TLS_ERROR_INVALID_CONTEXT, + "not a client context"); goto err; } if (host == NULL) { - tls_set_errorx(ctx, "host not specified"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "host not specified"); goto err; } @@ -79,11 +80,11 @@ tls_connect_servername(struct tls *ctx, const char *host, const char *port, if (port == NULL) { ret = tls_host_port(host, &hs, &ps); if (ret == -1) { - tls_set_errorx(ctx, "memory allocation failure"); + tls_set_errorx(ctx, TLS_ERROR_OUT_OF_MEMORY, "out of memory"); goto err; } if (ret != 0) { - tls_set_errorx(ctx, "no port provided"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "no port provided"); goto err; } } @@ -114,7 +115,8 @@ tls_connect_servername(struct tls *ctx, const char *host, const char *port, hints.ai_family = AF_UNSPEC; hints.ai_flags = AI_ADDRCONFIG; if ((s = getaddrinfo(h, p, &hints, &res0)) != 0) { - tls_set_error(ctx, "%s", gai_strerror(s)); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "%s", gai_strerror(s)); goto err; } } @@ -125,11 +127,13 @@ tls_connect_servername(struct tls *ctx, const char *host, const char *port, for (res = res0; res; res = res->ai_next) { s = socket(res->ai_family, res->ai_socktype, res->ai_protocol); if (s == -1) { - tls_set_error(ctx, "socket"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "socket"); continue; } if (connect(s, res->ai_addr, res->ai_addrlen) == -1) { - tls_set_error(ctx, "connect"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "connect"); close(s); s = -1; continue; @@ -174,11 +178,13 @@ tls_client_read_session(struct tls *ctx) int rv = -1; if (fstat(sfd, &sb) == -1) { - tls_set_error(ctx, "failed to stat session file"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "failed to stat session file"); goto err; } if (sb.st_size < 0 || sb.st_size > INT_MAX) { - tls_set_errorx(ctx, "invalid session file size"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "invalid session file size"); goto err; } session_len = (size_t)sb.st_size; @@ -192,19 +198,22 @@ tls_client_read_session(struct tls *ctx) n = pread(sfd, session, session_len, 0); if (n < 0 || (size_t)n != session_len) { - tls_set_error(ctx, "failed to read session file"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "failed to read session file"); goto err; } if ((bio = BIO_new_mem_buf(session, session_len)) == NULL) goto err; if ((ss = PEM_read_bio_SSL_SESSION(bio, NULL, tls_password_cb, NULL)) == NULL) { - tls_set_errorx(ctx, "failed to parse session"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to parse session"); goto err; } if (SSL_set_session(ctx->ssl_conn, ss) != 1) { - tls_set_errorx(ctx, "failed to set session"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to set session"); goto err; } @@ -234,7 +243,8 @@ tls_client_write_session(struct tls *ctx) if ((ss = SSL_get1_session(ctx->ssl_conn)) == NULL) { if (ftruncate(sfd, 0) == -1) { - tls_set_error(ctx, "failed to truncate session file"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "failed to truncate session file"); goto err; } goto done; @@ -251,12 +261,14 @@ tls_client_write_session(struct tls *ctx) offset = 0; if (ftruncate(sfd, len) == -1) { - tls_set_error(ctx, "failed to truncate session file"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "failed to truncate session file"); goto err; } while (len > 0) { if ((n = pwrite(sfd, data + offset, len, offset)) == -1) { - tls_set_error(ctx, "failed to write session file"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "failed to write session file"); goto err; } offset += n; @@ -281,13 +293,15 @@ tls_connect_common(struct tls *ctx, const char *servername) int rv = -1; if ((ctx->flags & TLS_CLIENT) == 0) { - tls_set_errorx(ctx, "not a client context"); + tls_set_errorx(ctx, TLS_ERROR_INVALID_CONTEXT, + "not a client context"); goto err; } if (servername != NULL) { if ((ctx->servername = strdup(servername)) == NULL) { - tls_set_errorx(ctx, "out of memory"); + tls_set_errorx(ctx, TLS_ERROR_OUT_OF_MEMORY, + "out of memory"); goto err; } @@ -304,7 +318,7 @@ tls_connect_common(struct tls *ctx, const char *servername) } if ((ctx->ssl_ctx = SSL_CTX_new(SSLv23_client_method())) == NULL) { - tls_set_errorx(ctx, "ssl context failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "ssl context failure"); goto err; } @@ -317,7 +331,8 @@ tls_connect_common(struct tls *ctx, const char *servername) if (ctx->config->verify_name) { if (ctx->servername == NULL) { - tls_set_errorx(ctx, "server name not specified"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "server name not specified"); goto err; } } @@ -328,23 +343,26 @@ tls_connect_common(struct tls *ctx, const char *servername) if (ctx->config->ecdhecurves != NULL) { if (SSL_CTX_set1_groups(ctx->ssl_ctx, ctx->config->ecdhecurves, ctx->config->ecdhecurves_len) != 1) { - tls_set_errorx(ctx, "failed to set ecdhe curves"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to set ecdhe curves"); goto err; } } if (SSL_CTX_set_tlsext_status_cb(ctx->ssl_ctx, tls_ocsp_verify_cb) != 1) { - tls_set_errorx(ctx, "ssl OCSP verification setup failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ssl OCSP verification setup failure"); goto err; } if ((ctx->ssl_conn = SSL_new(ctx->ssl_ctx)) == NULL) { - tls_set_errorx(ctx, "ssl connection failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "ssl connection failure"); goto err; } if (SSL_set_app_data(ctx->ssl_conn, ctx) != 1) { - tls_set_errorx(ctx, "ssl application data failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ssl application data failure"); goto err; } @@ -355,7 +373,8 @@ tls_connect_common(struct tls *ctx, const char *servername) } if (SSL_set_tlsext_status_type(ctx->ssl_conn, TLSEXT_STATUSTYPE_ocsp) != 1) { - tls_set_errorx(ctx, "ssl OCSP extension setup failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ssl OCSP extension setup failure"); goto err; } @@ -368,7 +387,8 @@ tls_connect_common(struct tls *ctx, const char *servername) inet_pton(AF_INET6, ctx->servername, &addrbuf) != 1) { if (SSL_set_tlsext_host_name(ctx->ssl_conn, ctx->servername) == 0) { - tls_set_errorx(ctx, "server name indication failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "server name indication failure"); goto err; } } @@ -393,7 +413,7 @@ tls_connect_fds(struct tls *ctx, int fd_read, int fd_write, int rv = -1; if (fd_read < 0 || fd_write < 0) { - tls_set_errorx(ctx, "invalid file descriptors"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "invalid file descriptors"); goto err; } @@ -402,7 +422,8 @@ tls_connect_fds(struct tls *ctx, int fd_read, int fd_write, if (SSL_set_rfd(ctx->ssl_conn, fd_read) != 1 || SSL_set_wfd(ctx->ssl_conn, fd_write) != 1) { - tls_set_errorx(ctx, "ssl file descriptor failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ssl file descriptor failure"); goto err; } @@ -437,12 +458,13 @@ tls_handshake_client(struct tls *ctx) int rv = -1; if ((ctx->flags & TLS_CLIENT) == 0) { - tls_set_errorx(ctx, "not a client context"); + tls_set_errorx(ctx, TLS_ERROR_INVALID_CONTEXT, + "not a client context"); goto err; } if ((ctx->state & TLS_CONNECTED) == 0) { - tls_set_errorx(ctx, "context not connected"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "context not connected"); goto err; } @@ -457,14 +479,16 @@ tls_handshake_client(struct tls *ctx) if (ctx->config->verify_name) { cert = SSL_get_peer_certificate(ctx->ssl_conn); if (cert == NULL) { - tls_set_errorx(ctx, "no server certificate"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "no server certificate"); goto err; } if (tls_check_name(ctx, cert, ctx->servername, &match) == -1) goto err; if (!match) { - tls_set_errorx(ctx, "name `%s' not present in" - " server certificate", ctx->servername); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "name `%s' not present in server certificate", + ctx->servername); goto err; } } diff --git a/lib/libtls/tls_config.c b/lib/libtls/tls_config.c index 5eb5b69ac..449071641 100644 --- a/lib/libtls/tls_config.c +++ b/lib/libtls/tls_config.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tls_config.c,v 1.67 2023/07/02 06:37:27 beck Exp $ */ +/* $OpenBSD: tls_config.c,v 1.68 2024/03/26 06:24:52 joshua Exp $ */ /* * Copyright (c) 2014 Joel Sing * @@ -50,12 +50,14 @@ tls_config_load_file(struct tls_error *error, const char *filetype, *len = 0; if ((fd = open(filename, O_RDONLY)) == -1) { - tls_error_set(error, "failed to open %s file '%s'", + tls_error_set(error, TLS_ERROR_UNKNOWN, + "failed to open %s file '%s'", filetype, filename); goto err; } if (fstat(fd, &st) != 0) { - tls_error_set(error, "failed to stat %s file '%s'", + tls_error_set(error, TLS_ERROR_UNKNOWN, + "failed to stat %s file '%s'", filetype, filename); goto err; } @@ -63,13 +65,15 @@ tls_config_load_file(struct tls_error *error, const char *filetype, goto err; *len = (size_t)st.st_size; if ((*buf = malloc(*len)) == NULL) { - tls_error_set(error, "failed to allocate buffer for " - "%s file", filetype); + tls_error_set(error, TLS_ERROR_UNKNOWN, + "failed to allocate buffer for %s file", + filetype); goto err; } n = read(fd, *buf, *len); if (n < 0 || (size_t)n != *len) { - tls_error_set(error, "failed to read %s file '%s'", + tls_error_set(error, TLS_ERROR_UNKNOWN, + "failed to read %s file '%s'", filetype, filename); goto err; } @@ -203,6 +207,12 @@ tls_config_error(struct tls_config *config) return config->error.msg; } +int +tls_config_error_code(struct tls_config *config) +{ + return config->error.code; +} + void tls_config_clear_keys(struct tls_config *config) { @@ -291,17 +301,19 @@ tls_config_parse_alpn(struct tls_config *config, const char *alpn, *alpn_len = 0; if ((buf_len = strlen(alpn) + 1) > 65535) { - tls_config_set_errorx(config, "alpn too large"); + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, "alpn too large"); goto err; } if ((buf = malloc(buf_len)) == NULL) { - tls_config_set_errorx(config, "out of memory"); + tls_config_set_errorx(config, TLS_ERROR_OUT_OF_MEMORY, + "out of memory"); goto err; } if ((s = strdup(alpn)) == NULL) { - tls_config_set_errorx(config, "out of memory"); + tls_config_set_errorx(config, TLS_ERROR_OUT_OF_MEMORY, + "out of memory"); goto err; } @@ -309,12 +321,12 @@ tls_config_parse_alpn(struct tls_config *config, const char *alpn, q = s; while ((p = strsep(&q, ",")) != NULL) { if ((len = strlen(p)) == 0) { - tls_config_set_errorx(config, + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, "alpn protocol with zero length"); goto err; } if (len > 255) { - tls_config_set_errorx(config, + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, "alpn protocol too long"); goto err; } @@ -484,11 +496,13 @@ tls_config_set_ciphers(struct tls_config *config, const char *ciphers) ciphers = TLS_CIPHERS_ALL; if ((ssl_ctx = SSL_CTX_new(SSLv23_method())) == NULL) { - tls_config_set_errorx(config, "out of memory"); + tls_config_set_errorx(config, TLS_ERROR_OUT_OF_MEMORY, + "out of memory"); goto err; } if (SSL_CTX_set_cipher_list(ssl_ctx, ciphers) != 1) { - tls_config_set_errorx(config, "no ciphers for '%s'", ciphers); + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, + "no ciphers for '%s'", ciphers); goto err; } @@ -526,7 +540,8 @@ tls_config_set_dheparams(struct tls_config *config, const char *params) else if (strcasecmp(params, "legacy") == 0) keylen = 1024; else { - tls_config_set_errorx(config, "invalid dhe param '%s'", params); + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, + "invalid dhe param '%s'", params); return (-1); } @@ -543,8 +558,8 @@ tls_config_set_ecdhecurve(struct tls_config *config, const char *curve) strcasecmp(curve, "auto") == 0) { curve = TLS_ECDHE_CURVES; } else if (strchr(curve, ',') != NULL || strchr(curve, ':') != NULL) { - tls_config_set_errorx(config, "invalid ecdhe curve '%s'", - curve); + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, + "invalid ecdhe curve '%s'", curve); return (-1); } @@ -569,7 +584,8 @@ tls_config_set_ecdhecurves(struct tls_config *config, const char *curves) curves = TLS_ECDHE_CURVES; if ((cs = strdup(curves)) == NULL) { - tls_config_set_errorx(config, "out of memory"); + tls_config_set_errorx(config, TLS_ERROR_OUT_OF_MEMORY, + "out of memory"); goto err; } @@ -584,14 +600,15 @@ tls_config_set_ecdhecurves(struct tls_config *config, const char *curves) if (nid == NID_undef) nid = EC_curve_nist2nid(p); if (nid == NID_undef) { - tls_config_set_errorx(config, + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, "invalid ecdhe curve '%s'", p); goto err; } if ((curves_new = reallocarray(curves_list, curves_num + 1, sizeof(int))) == NULL) { - tls_config_set_errorx(config, "out of memory"); + tls_config_set_errorx(config, TLS_ERROR_OUT_OF_MEMORY, + "out of memory"); goto err; } curves_list = curves_new; @@ -712,24 +729,26 @@ tls_config_set_session_fd(struct tls_config *config, int session_fd) } if (fstat(session_fd, &sb) == -1) { - tls_config_set_error(config, "failed to stat session file"); + tls_config_set_error(config, TLS_ERROR_UNKNOWN, + "failed to stat session file"); return (-1); } if (!S_ISREG(sb.st_mode)) { - tls_config_set_errorx(config, + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, "session file is not a regular file"); return (-1); } if (sb.st_uid != getuid()) { - tls_config_set_errorx(config, "session file has incorrect " - "owner (uid %u != %u)", sb.st_uid, getuid()); + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, + "session file has incorrect owner (uid %u != %u)", + sb.st_uid, getuid()); return (-1); } mugo = sb.st_mode & (S_IRWXU|S_IRWXG|S_IRWXO); if (mugo != (S_IRUSR|S_IWUSR)) { - tls_config_set_errorx(config, "session file has incorrect " - "permissions (%o != 600)", mugo); + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, + "session file has incorrect permissions (%o != 600)", mugo); return (-1); } @@ -846,7 +865,8 @@ tls_config_set_session_id(struct tls_config *config, const unsigned char *session_id, size_t len) { if (len > TLS_MAX_SESSION_ID_LENGTH) { - tls_config_set_errorx(config, "session ID too large"); + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, + "session ID too large"); return (-1); } memset(config->session_id, 0, sizeof(config->session_id)); @@ -858,11 +878,13 @@ int tls_config_set_session_lifetime(struct tls_config *config, int lifetime) { if (lifetime > TLS_MAX_SESSION_TIMEOUT) { - tls_config_set_errorx(config, "session lifetime too large"); + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, + "session lifetime too large"); return (-1); } if (lifetime != 0 && lifetime < TLS_MIN_SESSION_TIMEOUT) { - tls_config_set_errorx(config, "session lifetime too small"); + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, + "session lifetime too small"); return (-1); } @@ -879,7 +901,7 @@ tls_config_add_ticket_key(struct tls_config *config, uint32_t keyrev, if (TLS_TICKET_KEY_SIZE != keylen || sizeof(newkey.aes_key) + sizeof(newkey.hmac_key) > keylen) { - tls_config_set_errorx(config, + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, "wrong amount of ticket key data"); return (-1); } @@ -903,7 +925,8 @@ tls_config_add_ticket_key(struct tls_config *config, uint32_t keyrev, sizeof(tk->aes_key)) == 0 && memcmp(newkey.hmac_key, tk->hmac_key, sizeof(tk->hmac_key)) == 0) return (0); - tls_config_set_errorx(config, "ticket key already present"); + tls_config_set_errorx(config, TLS_ERROR_UNKNOWN, + "ticket key already present"); return (-1); } diff --git a/lib/libtls/tls_conninfo.c b/lib/libtls/tls_conninfo.c index 08f8714ec..bf525170f 100644 --- a/lib/libtls/tls_conninfo.c +++ b/lib/libtls/tls_conninfo.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tls_conninfo.c,v 1.25 2024/03/24 11:30:12 beck Exp $ */ +/* $OpenBSD: tls_conninfo.c,v 1.27 2024/03/26 06:31:22 jsing Exp $ */ /* * Copyright (c) 2015 Joel Sing * Copyright (c) 2015 Bob Beck @@ -79,7 +79,7 @@ tls_get_peer_cert_hash(struct tls *ctx, char **hash) return (0); if (tls_cert_hash(ctx->ssl_peer_cert, hash) == -1) { - tls_set_errorx(ctx, "unable to compute peer certificate hash - out of memory"); + tls_set_errorx(ctx, TLS_ERROR_OUT_OF_MEMORY, "out of memory"); *hash = NULL; return -1; } @@ -245,7 +245,7 @@ tls_conninfo_populate(struct tls *ctx) tls_conninfo_free(ctx->conninfo); if ((ctx->conninfo = calloc(1, sizeof(struct tls_conninfo))) == NULL) { - tls_set_errorx(ctx, "out of memory"); + tls_set_errorx(ctx, TLS_ERROR_OUT_OF_MEMORY, "out of memory"); goto err; } diff --git a/lib/libtls/tls_internal.h b/lib/libtls/tls_internal.h index c06e8218f..5ff48ed7c 100644 --- a/lib/libtls/tls_internal.h +++ b/lib/libtls/tls_internal.h @@ -1,4 +1,4 @@ -/* $OpenBSD: tls_internal.h,v 1.84 2024/03/26 00:50:22 joshua Exp $ */ +/* $OpenBSD: tls_internal.h,v 1.85 2024/03/26 06:24:52 joshua Exp $ */ /* * Copyright (c) 2014 Jeremie Courreges-Anglas * Copyright (c) 2014 Joel Sing @@ -46,6 +46,7 @@ union tls_addr { struct tls_error { char *msg; + int code; int errno_value; int tls; }; @@ -258,27 +259,27 @@ int tls_set_cbs(struct tls *ctx, tls_read_cb read_cb, tls_write_cb write_cb, void *cb_arg); void tls_error_clear(struct tls_error *error); -int tls_error_set(struct tls_error *error, const char *fmt, ...) - __attribute__((__format__ (printf, 2, 3))) - __attribute__((__nonnull__ (2))); -int tls_error_setx(struct tls_error *error, const char *fmt, ...) - __attribute__((__format__ (printf, 2, 3))) - __attribute__((__nonnull__ (2))); -int tls_config_set_error(struct tls_config *cfg, const char *fmt, ...) - __attribute__((__format__ (printf, 2, 3))) - __attribute__((__nonnull__ (2))); -int tls_config_set_errorx(struct tls_config *cfg, const char *fmt, ...) - __attribute__((__format__ (printf, 2, 3))) - __attribute__((__nonnull__ (2))); -int tls_set_error(struct tls *ctx, const char *fmt, ...) - __attribute__((__format__ (printf, 2, 3))) - __attribute__((__nonnull__ (2))); -int tls_set_errorx(struct tls *ctx, const char *fmt, ...) - __attribute__((__format__ (printf, 2, 3))) - __attribute__((__nonnull__ (2))); -int tls_set_ssl_errorx(struct tls *ctx, const char *fmt, ...) - __attribute__((__format__ (printf, 2, 3))) - __attribute__((__nonnull__ (2))); +int tls_error_set(struct tls_error *error, int code, const char *fmt, ...) + __attribute__((__format__ (printf, 3, 4))) + __attribute__((__nonnull__ (3))); +int tls_error_setx(struct tls_error *error, int code, const char *fmt, ...) + __attribute__((__format__ (printf, 3, 4))) + __attribute__((__nonnull__ (3))); +int tls_config_set_error(struct tls_config *cfg, int code, const char *fmt, ...) + __attribute__((__format__ (printf, 3, 4))) + __attribute__((__nonnull__ (3))); +int tls_config_set_errorx(struct tls_config *cfg, int code, const char *fmt, ...) + __attribute__((__format__ (printf, 3, 4))) + __attribute__((__nonnull__ (3))); +int tls_set_error(struct tls *ctx, int code, const char *fmt, ...) + __attribute__((__format__ (printf, 3, 4))) + __attribute__((__nonnull__ (3))); +int tls_set_errorx(struct tls *ctx, int code, const char *fmt, ...) + __attribute__((__format__ (printf, 3, 4))) + __attribute__((__nonnull__ (3))); +int tls_set_ssl_errorx(struct tls *ctx, int code, const char *fmt, ...) + __attribute__((__format__ (printf, 3, 4))) + __attribute__((__nonnull__ (3))); int tls_ssl_error(struct tls *ctx, SSL *ssl_conn, int ssl_ret, const char *prefix); diff --git a/lib/libtls/tls_keypair.c b/lib/libtls/tls_keypair.c index a12d21d0d..ffda91df8 100644 --- a/lib/libtls/tls_keypair.c +++ b/lib/libtls/tls_keypair.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tls_keypair.c,v 1.8 2021/01/05 17:37:12 jsing Exp $ */ +/* $OpenBSD: tls_keypair.c,v 1.9 2024/03/26 06:24:52 joshua Exp $ */ /* * Copyright (c) 2014 Joel Sing * @@ -144,19 +144,22 @@ tls_keypair_load_cert(struct tls_keypair *keypair, struct tls_error *error, *cert = NULL; if (keypair->cert_mem == NULL) { - tls_error_set(error, "keypair has no certificate"); + tls_error_set(error, TLS_ERROR_UNKNOWN, + "keypair has no certificate"); goto err; } if ((cert_bio = BIO_new_mem_buf(keypair->cert_mem, keypair->cert_len)) == NULL) { - tls_error_set(error, "failed to create certificate bio"); + tls_error_set(error, TLS_ERROR_UNKNOWN, + "failed to create certificate bio"); goto err; } if ((*cert = PEM_read_bio_X509(cert_bio, NULL, tls_password_cb, NULL)) == NULL) { if ((ssl_err = ERR_peek_error()) != 0) errstr = ERR_error_string(ssl_err, NULL); - tls_error_set(error, "failed to load certificate: %s", errstr); + tls_error_set(error, TLS_ERROR_UNKNOWN, + "failed to load certificate: %s", errstr); goto err; } diff --git a/lib/libtls/tls_ocsp.c b/lib/libtls/tls_ocsp.c index f7d7ba919..bfd06e3c6 100644 --- a/lib/libtls/tls_ocsp.c +++ b/lib/libtls/tls_ocsp.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tls_ocsp.c,v 1.25 2024/03/24 11:30:12 beck Exp $ */ +/* $OpenBSD: tls_ocsp.c,v 1.26 2024/03/26 06:24:52 joshua Exp $ */ /* * Copyright (c) 2015 Marko Kreen * Copyright (c) 2016 Bob Beck @@ -85,7 +85,7 @@ tls_ocsp_fill_info(struct tls *ctx, int response_status, int cert_status, ctx->ocsp->ocsp_result = NULL; if ((info = calloc(1, sizeof (struct tls_ocsp_result))) == NULL) { - tls_set_error(ctx, "calloc"); + tls_set_error(ctx, TLS_ERROR_OUT_OF_MEMORY, "out of memory"); return -1; } info->response_status = response_status; @@ -102,19 +102,19 @@ tls_ocsp_fill_info(struct tls *ctx, int response_status, int cert_status, info->revocation_time = info->this_update = info->next_update = -1; if (revtime != NULL && tls_ocsp_asn1_parse_time(ctx, revtime, &info->revocation_time) != 0) { - tls_set_error(ctx, + tls_set_error(ctx, TLS_ERROR_UNKNOWN, "unable to parse revocation time in OCSP reply"); goto err; } if (thisupd != NULL && tls_ocsp_asn1_parse_time(ctx, thisupd, &info->this_update) != 0) { - tls_set_error(ctx, + tls_set_error(ctx, TLS_ERROR_UNKNOWN, "unable to parse this update time in OCSP reply"); goto err; } if (nextupd != NULL && tls_ocsp_asn1_parse_time(ctx, nextupd, &info->next_update) != 0) { - tls_set_error(ctx, + tls_set_error(ctx, TLS_ERROR_UNKNOWN, "unable to parse next update time in OCSP reply"); goto err; } @@ -180,19 +180,21 @@ tls_ocsp_setup_from_peer(struct tls *ctx) ocsp->main_cert = SSL_get_peer_certificate(ctx->ssl_conn); ocsp->extra_certs = SSL_get_peer_cert_chain(ctx->ssl_conn); if (ocsp->main_cert == NULL) { - tls_set_errorx(ctx, "no peer certificate for OCSP"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "no peer certificate for OCSP"); goto err; } ocsp_urls = X509_get1_ocsp(ocsp->main_cert); if (ocsp_urls == NULL) { - tls_set_errorx(ctx, "no OCSP URLs in peer certificate"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "no OCSP URLs in peer certificate"); goto err; } ocsp->ocsp_url = strdup(sk_OPENSSL_STRING_value(ocsp_urls, 0)); if (ocsp->ocsp_url == NULL) { - tls_set_errorx(ctx, "out of memory"); + tls_set_errorx(ctx, TLS_ERROR_OUT_OF_MEMORY, "out of memory"); goto err; } @@ -217,7 +219,7 @@ tls_ocsp_verify_response(struct tls *ctx, OCSP_RESPONSE *resp) unsigned long flags; if ((br = OCSP_response_get1_basic(resp)) == NULL) { - tls_set_errorx(ctx, "cannot load ocsp reply"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "cannot load ocsp reply"); goto err; } @@ -230,14 +232,15 @@ tls_ocsp_verify_response(struct tls *ctx, OCSP_RESPONSE *resp) /* now verify */ if (OCSP_basic_verify(br, ctx->ocsp->extra_certs, SSL_CTX_get_cert_store(ctx->ssl_ctx), flags) != 1) { - tls_set_errorx(ctx, "ocsp verify failed"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "ocsp verify failed"); goto err; } /* signature OK, look inside */ response_status = OCSP_response_status(resp); if (response_status != OCSP_RESPONSE_STATUS_SUCCESSFUL) { - tls_set_errorx(ctx, "ocsp verify failed: response - %s", + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ocsp verify failed: response - %s", OCSP_response_status_str(response_status)); goto err; } @@ -245,19 +248,21 @@ tls_ocsp_verify_response(struct tls *ctx, OCSP_RESPONSE *resp) cid = tls_ocsp_get_certid(ctx->ocsp->main_cert, ctx->ocsp->extra_certs, ctx->ssl_ctx); if (cid == NULL) { - tls_set_errorx(ctx, "ocsp verify failed: no issuer cert"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ocsp verify failed: no issuer cert"); goto err; } if (OCSP_resp_find_status(br, cid, &cert_status, &crl_reason, &revtime, &thisupd, &nextupd) != 1) { - tls_set_errorx(ctx, "ocsp verify failed: no result for cert"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ocsp verify failed: no result for cert"); goto err; } if (OCSP_check_validity(thisupd, nextupd, JITTER_SEC, MAXAGE_SEC) != 1) { - tls_set_errorx(ctx, + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "ocsp verify failed: ocsp response not current"); goto err; } @@ -269,8 +274,9 @@ tls_ocsp_verify_response(struct tls *ctx, OCSP_RESPONSE *resp) /* finally can look at status */ if (cert_status != V_OCSP_CERTSTATUS_GOOD && cert_status != V_OCSP_CERTSTATUS_UNKNOWN) { - tls_set_errorx(ctx, "ocsp verify failed: revoked cert - %s", - OCSP_crl_reason_str(crl_reason)); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ocsp verify failed: revoked cert - %s", + OCSP_crl_reason_str(crl_reason)); goto err; } ret = 0; @@ -298,7 +304,8 @@ tls_ocsp_process_response_internal(struct tls *ctx, const unsigned char *respons if (resp == NULL) { tls_ocsp_free(ctx->ocsp); ctx->ocsp = NULL; - tls_set_error(ctx, "unable to parse OCSP response"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "unable to parse OCSP response"); return -1; } ret = tls_ocsp_verify_response(ctx, resp); @@ -320,7 +327,8 @@ tls_ocsp_verify_cb(SSL *ssl, void *arg) size = SSL_get_tlsext_status_ocsp_resp(ssl, &raw); if (size <= 0) { if (ctx->config->ocsp_require_stapling) { - tls_set_errorx(ctx, "no stapled OCSP response provided"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "no stapled OCSP response provided"); return 0; } return 1; diff --git a/lib/libtls/tls_server.c b/lib/libtls/tls_server.c index 5f93c7a03..a94b4221e 100644 --- a/lib/libtls/tls_server.c +++ b/lib/libtls/tls_server.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tls_server.c,v 1.49 2023/05/14 07:26:25 op Exp $ */ +/* $OpenBSD: tls_server.c,v 1.51 2024/03/26 08:54:48 joshua Exp $ */ /* * Copyright (c) 2014 Joel Sing * @@ -181,7 +181,8 @@ tls_server_ticket_cb(SSL *ssl, unsigned char *keyname, unsigned char *iv, /* create new session */ key = tls_server_ticket_key(tls_ctx->config, NULL); if (key == NULL) { - tls_set_errorx(tls_ctx, "no valid ticket key found"); + tls_set_errorx(tls_ctx, TLS_ERROR_UNKNOWN, + "no valid ticket key found"); return (-1); } @@ -189,12 +190,14 @@ tls_server_ticket_cb(SSL *ssl, unsigned char *keyname, unsigned char *iv, arc4random_buf(iv, EVP_MAX_IV_LENGTH); if (!EVP_EncryptInit_ex(ctx, EVP_aes_256_cbc(), NULL, key->aes_key, iv)) { - tls_set_errorx(tls_ctx, "failed to init encrypt"); + tls_set_errorx(tls_ctx, TLS_ERROR_UNKNOWN, + "failed to init encrypt"); return (-1); } if (!HMAC_Init_ex(hctx, key->hmac_key, sizeof(key->hmac_key), EVP_sha256(), NULL)) { - tls_set_errorx(tls_ctx, "failed to init hmac"); + tls_set_errorx(tls_ctx, TLS_ERROR_UNKNOWN, + "failed to init hmac"); return (-1); } return (0); @@ -206,12 +209,14 @@ tls_server_ticket_cb(SSL *ssl, unsigned char *keyname, unsigned char *iv, if (!EVP_DecryptInit_ex(ctx, EVP_aes_256_cbc(), NULL, key->aes_key, iv)) { - tls_set_errorx(tls_ctx, "failed to init decrypt"); + tls_set_errorx(tls_ctx, TLS_ERROR_UNKNOWN, + "failed to init decrypt"); return (-1); } if (!HMAC_Init_ex(hctx, key->hmac_key, sizeof(key->hmac_key), EVP_sha256(), NULL)) { - tls_set_errorx(tls_ctx, "failed to init hmac"); + tls_set_errorx(tls_ctx, TLS_ERROR_UNKNOWN, + "failed to init hmac"); return (-1); } @@ -229,7 +234,7 @@ tls_configure_server_ssl(struct tls *ctx, SSL_CTX **ssl_ctx, SSL_CTX_free(*ssl_ctx); if ((*ssl_ctx = SSL_CTX_new(SSLv23_server_method())) == NULL) { - tls_set_errorx(ctx, "ssl context failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "ssl context failure"); goto err; } @@ -237,11 +242,13 @@ tls_configure_server_ssl(struct tls *ctx, SSL_CTX **ssl_ctx, if (SSL_CTX_set_tlsext_servername_callback(*ssl_ctx, tls_servername_cb) != 1) { - tls_set_error(ctx, "failed to set servername callback"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "failed to set servername callback"); goto err; } if (SSL_CTX_set_tlsext_servername_arg(*ssl_ctx, ctx) != 1) { - tls_set_error(ctx, "failed to set servername callback arg"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "failed to set servername callback arg"); goto err; } @@ -270,7 +277,8 @@ tls_configure_server_ssl(struct tls *ctx, SSL_CTX **ssl_ctx, SSL_CTX_set_ecdh_auto(*ssl_ctx, 1); if (SSL_CTX_set1_groups(*ssl_ctx, ctx->config->ecdhecurves, ctx->config->ecdhecurves_len) != 1) { - tls_set_errorx(ctx, "failed to set ecdhe curves"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to set ecdhe curves"); goto err; } } @@ -279,7 +287,8 @@ tls_configure_server_ssl(struct tls *ctx, SSL_CTX **ssl_ctx, SSL_CTX_set_options(*ssl_ctx, SSL_OP_CIPHER_SERVER_PREFERENCE); if (SSL_CTX_set_tlsext_status_cb(*ssl_ctx, tls_ocsp_stapling_cb) != 1) { - tls_set_errorx(ctx, "failed to add OCSP stapling callback"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "failed to add OCSP stapling callback"); goto err; } @@ -289,7 +298,7 @@ tls_configure_server_ssl(struct tls *ctx, SSL_CTX **ssl_ctx, SSL_CTX_clear_options(*ssl_ctx, SSL_OP_NO_TICKET); if (!SSL_CTX_set_tlsext_ticket_key_cb(*ssl_ctx, tls_server_ticket_cb)) { - tls_set_error(ctx, + tls_set_error(ctx, TLS_ERROR_UNKNOWN, "failed to set the TLS ticket callback"); goto err; } @@ -297,7 +306,8 @@ tls_configure_server_ssl(struct tls *ctx, SSL_CTX **ssl_ctx, if (SSL_CTX_set_session_id_context(*ssl_ctx, ctx->config->session_id, sizeof(ctx->config->session_id)) != 1) { - tls_set_error(ctx, "failed to set session id context"); + tls_set_error(ctx, TLS_ERROR_UNKNOWN, + "failed to set session id context"); goto err; } @@ -323,7 +333,7 @@ tls_configure_server_sni(struct tls *ctx) sni_ctx = &ctx->sni_ctx; for (kp = ctx->config->keypair->next; kp != NULL; kp = kp->next) { if ((*sni_ctx = tls_sni_ctx_new()) == NULL) { - tls_set_errorx(ctx, "out of memory"); + tls_set_errorx(ctx, TLS_ERROR_OUT_OF_MEMORY, "out of memory"); goto err; } (*sni_ctx)->keypair = kp; @@ -362,22 +372,25 @@ tls_accept_common(struct tls *ctx) struct tls *conn_ctx = NULL; if ((ctx->flags & TLS_SERVER) == 0) { - tls_set_errorx(ctx, "not a server context"); + tls_set_errorx(ctx, TLS_ERROR_INVALID_CONTEXT, + "not a server context"); goto err; } if ((conn_ctx = tls_server_conn(ctx)) == NULL) { - tls_set_errorx(ctx, "connection context failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "connection context failure"); goto err; } if ((conn_ctx->ssl_conn = SSL_new(ctx->ssl_ctx)) == NULL) { - tls_set_errorx(ctx, "ssl failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "ssl failure"); goto err; } if (SSL_set_app_data(conn_ctx->ssl_conn, conn_ctx) != 1) { - tls_set_errorx(ctx, "ssl application data failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ssl application data failure"); goto err; } @@ -405,7 +418,8 @@ tls_accept_fds(struct tls *ctx, struct tls **cctx, int fd_read, int fd_write) if (SSL_set_rfd(conn_ctx->ssl_conn, fd_read) != 1 || SSL_set_wfd(conn_ctx->ssl_conn, fd_write) != 1) { - tls_set_errorx(ctx, "ssl file descriptor failure"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "ssl file descriptor failure"); goto err; } @@ -448,7 +462,8 @@ tls_handshake_server(struct tls *ctx) int rv = -1; if ((ctx->flags & TLS_SERVER_CONN) == 0) { - tls_set_errorx(ctx, "not a server connection context"); + tls_set_errorx(ctx, TLS_ERROR_INVALID_CONTEXT, + "not a server connection context"); goto err; } diff --git a/lib/libtls/tls_signer.c b/lib/libtls/tls_signer.c index 177c9d07a..5eb370745 100644 --- a/lib/libtls/tls_signer.c +++ b/lib/libtls/tls_signer.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tls_signer.c,v 1.9 2023/06/18 19:12:58 tb Exp $ */ +/* $OpenBSD: tls_signer.c,v 1.10 2024/03/26 06:24:52 joshua Exp $ */ /* * Copyright (c) 2021 Eric Faurot * @@ -91,7 +91,7 @@ tls_signer_add_keypair_mem(struct tls_signer *signer, const uint8_t *cert, /* Compute certificate hash */ if ((bio = BIO_new_mem_buf(cert, cert_len)) == NULL) { - tls_error_setx(&signer->error, + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, "failed to create certificate bio"); goto err; } @@ -99,12 +99,12 @@ tls_signer_add_keypair_mem(struct tls_signer *signer, const uint8_t *cert, NULL)) == NULL) { if ((ssl_err = ERR_peek_error()) != 0) errstr = ERR_error_string(ssl_err, NULL); - tls_error_setx(&signer->error, "failed to load certificate: %s", - errstr); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "failed to load certificate: %s", errstr); goto err; } if (tls_cert_pubkey_hash(x509, &hash) == -1) { - tls_error_setx(&signer->error, + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, "failed to get certificate hash"); goto err; } @@ -116,23 +116,27 @@ tls_signer_add_keypair_mem(struct tls_signer *signer, const uint8_t *cert, /* Read private key */ if ((bio = BIO_new_mem_buf(key, key_len)) == NULL) { - tls_error_setx(&signer->error, "failed to create key bio"); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "failed to create key bio"); goto err; } if ((pkey = PEM_read_bio_PrivateKey(bio, NULL, tls_password_cb, NULL)) == NULL) { - tls_error_setx(&signer->error, "failed to read private key"); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "failed to read private key"); goto err; } if ((skey = calloc(1, sizeof(*skey))) == NULL) { - tls_error_set(&signer->error, "failed to create key entry"); + tls_error_set(&signer->error, TLS_ERROR_UNKNOWN, + "failed to create key entry"); goto err; } skey->hash = hash; if ((skey->rsa = EVP_PKEY_get1_RSA(pkey)) == NULL && (skey->ecdsa = EVP_PKEY_get1_EC_KEY(pkey)) == NULL) { - tls_error_setx(&signer->error, "unknown key type"); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "unknown key type"); goto err; } @@ -194,29 +198,31 @@ tls_sign_rsa(struct tls_signer *signer, struct tls_signer_key *skey, } else if (padding_type == TLS_PADDING_RSA_PKCS1) { rsa_padding = RSA_PKCS1_PADDING; } else { - tls_error_setx(&signer->error, "invalid RSA padding type (%d)", - padding_type); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "invalid RSA padding type (%d)", padding_type); return (-1); } if (input_len > INT_MAX) { - tls_error_setx(&signer->error, "input too large"); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "input too large"); return (-1); } if ((rsa_size = RSA_size(skey->rsa)) <= 0) { - tls_error_setx(&signer->error, "invalid RSA size: %d", - rsa_size); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "invalid RSA size: %d", rsa_size); return (-1); } if ((signature = calloc(1, rsa_size)) == NULL) { - tls_error_set(&signer->error, "RSA signature"); + tls_error_set(&signer->error, TLS_ERROR_UNKNOWN, "RSA signature"); return (-1); } if ((signature_len = RSA_private_encrypt((int)input_len, input, signature, skey->rsa, rsa_padding)) <= 0) { /* XXX - include further details from libcrypto. */ - tls_error_setx(&signer->error, "RSA signing failed"); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "RSA signing failed"); free(signature); return (-1); } @@ -239,28 +245,32 @@ tls_sign_ecdsa(struct tls_signer *signer, struct tls_signer_key *skey, *out_signature_len = 0; if (padding_type != TLS_PADDING_NONE) { - tls_error_setx(&signer->error, "invalid ECDSA padding"); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "invalid ECDSA padding"); return (-1); } if (input_len > INT_MAX) { - tls_error_setx(&signer->error, "digest too large"); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "digest too large"); return (-1); } if ((signature_len = ECDSA_size(skey->ecdsa)) <= 0) { - tls_error_setx(&signer->error, "invalid ECDSA size: %d", - signature_len); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "invalid ECDSA size: %d", signature_len); return (-1); } if ((signature = calloc(1, signature_len)) == NULL) { - tls_error_set(&signer->error, "ECDSA signature"); + tls_error_set(&signer->error, TLS_ERROR_UNKNOWN, + "ECDSA signature"); return (-1); } if (!ECDSA_sign(0, input, input_len, signature, &signature_len, skey->ecdsa)) { /* XXX - include further details from libcrypto. */ - tls_error_setx(&signer->error, "ECDSA signing failed"); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, + "ECDSA signing failed"); free(signature); return (-1); } @@ -286,7 +296,7 @@ tls_signer_sign(struct tls_signer *signer, const char *pubkey_hash, break; if (skey == NULL) { - tls_error_setx(&signer->error, "key not found"); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, "key not found"); return (-1); } @@ -298,7 +308,7 @@ tls_signer_sign(struct tls_signer *signer, const char *pubkey_hash, return tls_sign_ecdsa(signer, skey, input, input_len, padding_type, out_signature, out_signature_len); - tls_error_setx(&signer->error, "unknown key type"); + tls_error_setx(&signer->error, TLS_ERROR_UNKNOWN, "unknown key type"); return (-1); } diff --git a/lib/libtls/tls_verify.c b/lib/libtls/tls_verify.c index a35ebe025..78f6c249c 100644 --- a/lib/libtls/tls_verify.c +++ b/lib/libtls/tls_verify.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tls_verify.c,v 1.29 2023/11/22 18:23:09 op Exp $ */ +/* $OpenBSD: tls_verify.c,v 1.30 2024/03/26 06:24:52 joshua Exp $ */ /* * Copyright (c) 2014 Jeremie Courreges-Anglas * @@ -102,7 +102,8 @@ tls_check_subject_altname(struct tls *ctx, X509 *cert, const char *name, NULL); if (altname_stack == NULL) { if (critical != -1) { - tls_set_errorx(ctx, "error decoding subjectAltName"); + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "error decoding subjectAltName"); goto err; } goto done; @@ -141,7 +142,7 @@ tls_check_subject_altname(struct tls *ctx, X509 *cert, const char *name, len = ASN1_STRING_length(altname->d.dNSName); if (len < 0 || (size_t)len != strlen(data)) { - tls_set_errorx(ctx, + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "error verifying name '%s': " "NUL byte in subjectAltName, " "probably a malicious certificate", @@ -155,7 +156,7 @@ tls_check_subject_altname(struct tls *ctx, X509 *cert, const char *name, * dNSName must be rejected. */ if (strcmp(data, " ") == 0) { - tls_set_errorx(ctx, + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "error verifying name '%s': " "a dNSName of \" \" must not be " "used", name); @@ -182,7 +183,7 @@ tls_check_subject_altname(struct tls *ctx, X509 *cert, const char *name, data = ASN1_STRING_get0_data(altname->d.iPAddress); if (datalen < 0) { - tls_set_errorx(ctx, + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, "Unexpected negative length for an " "IP address: %d", datalen); goto err; @@ -243,7 +244,8 @@ tls_check_common_name(struct tls *ctx, X509 *cert, const char *name, * more than one CN fed to us in the subject, treating the * certificate as hostile. */ - tls_set_errorx(ctx, "error verifying name '%s': " + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "error verifying name '%s': " "Certificate subject contains multiple Common Name fields, " "probably a malicious or malformed certificate", name); goto err; @@ -255,7 +257,8 @@ tls_check_common_name(struct tls *ctx, X509 *cert, const char *name, * Fail if we cannot encode the CN bytes as UTF-8. */ if ((common_name_len = ASN1_STRING_to_UTF8(&utf8_bytes, data)) < 0) { - tls_set_errorx(ctx, "error verifying name '%s': " + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "error verifying name '%s': " "Common Name field cannot be encoded as a UTF-8 string, " "probably a malicious certificate", name); goto err; @@ -265,7 +268,8 @@ tls_check_common_name(struct tls *ctx, X509 *cert, const char *name, * must be between 1 and 64 bytes long. */ if (common_name_len < 1 || common_name_len > 64) { - tls_set_errorx(ctx, "error verifying name '%s': " + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "error verifying name '%s': " "Common Name field has invalid length, " "probably a malicious certificate", name); goto err; @@ -274,7 +278,8 @@ tls_check_common_name(struct tls *ctx, X509 *cert, const char *name, * Fail if the resulting text contains a NUL byte. */ if (memchr(utf8_bytes, 0, common_name_len) != NULL) { - tls_set_errorx(ctx, "error verifying name '%s': " + tls_set_errorx(ctx, TLS_ERROR_UNKNOWN, + "error verifying name '%s': " "NUL byte in Common Name field, " "probably a malicious certificate", name); goto err; @@ -282,7 +287,8 @@ tls_check_common_name(struct tls *ctx, X509 *cert, const char *name, common_name = strndup(utf8_bytes, common_name_len); if (common_name == NULL) { - tls_set_error(ctx, "out of memory"); + tls_set_error(ctx, TLS_ERROR_OUT_OF_MEMORY, + "out of memory"); goto err; } diff --git a/regress/lib/libssl/tlsext/tlsexttest.c b/regress/lib/libssl/tlsext/tlsexttest.c index 3888cb7de..c7983833d 100644 --- a/regress/lib/libssl/tlsext/tlsexttest.c +++ b/regress/lib/libssl/tlsext/tlsexttest.c @@ -1,4 +1,4 @@ -/* $OpenBSD: tlsexttest.c,v 1.85 2024/03/25 10:19:14 jsing Exp $ */ +/* $OpenBSD: tlsexttest.c,v 1.86 2024/03/26 02:43:56 beck Exp $ */ /* * Copyright (c) 2017 Joel Sing * Copyright (c) 2017 Doug Hogan @@ -3189,9 +3189,9 @@ test_tlsext_srtp_server(void) #endif /* OPENSSL_NO_SRTP */ static const unsigned char tlsext_clienthello_default[] = { - 0x00, 0x34, 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, - 0x00, 0x0a, 0x00, 0x0a, 0x00, 0x08, 0x00, 0x1d, - 0x00, 0x17, 0x00, 0x18, 0x00, 0x19, 0x00, 0x23, + 0x00, 0x34, 0x00, 0x0a, 0x00, 0x0a, 0x00, 0x08, + 0x00, 0x1d, 0x00, 0x17, 0x00, 0x18, 0x00, 0x19, + 0x00, 0x0b, 0x00, 0x02, 0x01, 0x00, 0x00, 0x23, 0x00, 0x00, 0x00, 0x0d, 0x00, 0x18, 0x00, 0x16, 0x08, 0x06, 0x06, 0x01, 0x06, 0x03, 0x08, 0x05, 0x05, 0x01, 0x05, 0x03, 0x08, 0x04, 0x04, 0x01, diff --git a/regress/sys/kern/noexec/testfly.S b/regress/sys/kern/noexec/testfly.S index 50ffbc575..afe29e6ac 100644 --- a/regress/sys/kern/noexec/testfly.S +++ b/regress/sys/kern/noexec/testfly.S @@ -1,4 +1,4 @@ -/* $OpenBSD: testfly.S,v 1.12 2023/01/22 16:38:36 anton Exp $ */ +/* $OpenBSD: testfly.S,v 1.13 2024/03/26 19:12:34 miod Exp $ */ /* * Copyright (c) 2002,2003 Michael Shalayeff @@ -36,11 +36,22 @@ .space 16384 -#if defined(__aarch64__) || defined(__amd64__) +#if defined(__aarch64__) .section .rodata .globl testfly .type testfly,_ASM_TYPE_FUNCTION testfly: + bti c + ret +END(testfly) +#endif + +#if defined(__amd64__) + .section .rodata + .globl testfly + .type testfly,_ASM_TYPE_FUNCTION +testfly: + endbr64 ret END(testfly) #endif diff --git a/regress/usr.bin/ssh/sftp-cmds.sh b/regress/usr.bin/ssh/sftp-cmds.sh index a7594bfc0..78b3c3ca5 100644 --- a/regress/usr.bin/ssh/sftp-cmds.sh +++ b/regress/usr.bin/ssh/sftp-cmds.sh @@ -1,4 +1,4 @@ -# $OpenBSD: sftp-cmds.sh,v 1.17 2024/03/25 06:05:42 dtucker Exp $ +# $OpenBSD: sftp-cmds.sh,v 1.18 2024/03/26 08:09:16 dtucker Exp $ # Placed in the Public Domain. # XXX - TODO: @@ -188,7 +188,7 @@ cmp ${COPY}.1 ${COPY}.2 || fail "created file is not equal after ln" verbose "$tid: ln -s" rm -f ${COPY}.2 echo "ln -s ${COPY}.1 ${COPY}.2" | ${SFTP} -D ${SFTPSERVER} >/dev/null 2>&1 || fail "ln -s failed" -test -L ${COPY}.2 || fail "missing file after ln -s" +test -h ${COPY}.2 || fail "missing file after ln -s" verbose "$tid: cp" rm -f ${COPY}.2 diff --git a/sys/dev/pci/drm/amd/amdgpu/amdgpu_drv.c b/sys/dev/pci/drm/amd/amdgpu/amdgpu_drv.c index 469cb3f17..cbee3cc31 100644 --- a/sys/dev/pci/drm/amd/amdgpu/amdgpu_drv.c +++ b/sys/dev/pci/drm/amd/amdgpu/amdgpu_drv.c @@ -3448,22 +3448,34 @@ amdgpu_init_backlight(struct amdgpu_device *adev) struct backlight_device *bd = adev->dm.backlight_dev[0]; struct drm_connector_list_iter conn_iter; struct drm_connector *connector; + struct amdgpu_dm_connector *aconnector; if (bd == NULL) return; drm_connector_list_iter_begin(dev, &conn_iter); drm_for_each_connector_iter(connector, &conn_iter) { - if (connector->connector_type != DRM_MODE_CONNECTOR_LVDS && - connector->connector_type != DRM_MODE_CONNECTOR_eDP && - connector->connector_type != DRM_MODE_CONNECTOR_DSI) + aconnector = to_amdgpu_dm_connector(connector); + + if (connector->registration_state != DRM_CONNECTOR_REGISTERED) continue; + if (aconnector->bl_idx == -1) + continue; + + dev->registered = false; + connector->registration_state = DRM_CONNECTOR_UNREGISTERED; + connector->backlight_device = bd; connector->backlight_property = drm_property_create_range(dev, 0, "Backlight", 0, bd->props.max_brightness); drm_object_attach_property(&connector->base, connector->backlight_property, bd->props.brightness); + + connector->registration_state = DRM_CONNECTOR_REGISTERED; + dev->registered = true; + + break; } drm_connector_list_iter_end(&conn_iter); } diff --git a/sys/dev/pci/drm/i915/gem/i915_gem_mman.c b/sys/dev/pci/drm/i915/gem/i915_gem_mman.c index 344229ec2..a5585e4c8 100644 --- a/sys/dev/pci/drm/i915/gem/i915_gem_mman.c +++ b/sys/dev/pci/drm/i915/gem/i915_gem_mman.c @@ -1449,8 +1449,18 @@ i915_gem_mmap(struct file *filp, vm_prot_t accessprot, * destroyed and will be invalid when the vma manager lock * is released. */ - mmo = container_of(node, struct i915_mmap_offset, vma_node); - obj = i915_gem_object_get_rcu(mmo->obj); + if (!node->driver_private) { + mmo = container_of(node, struct i915_mmap_offset, vma_node); + obj = i915_gem_object_get_rcu(mmo->obj); + + GEM_BUG_ON(obj && obj->ops->mmap_ops); + } else { + obj = i915_gem_object_get_rcu + (container_of(node, struct drm_i915_gem_object, + base.vma_node)); + + GEM_BUG_ON(obj && !obj->ops->mmap_ops); + } } drm_vma_offset_unlock_lookup(dev->vma_offset_manager); rcu_read_unlock(); @@ -1464,6 +1474,9 @@ i915_gem_mmap(struct file *filp, vm_prot_t accessprot, } } + if (obj->ops->mmap_ops) + uvm_obj_init(&obj->base.uobj, obj->ops->mmap_ops, 1); + return &obj->base.uobj; } diff --git a/sys/dev/pci/drm/i915/gem/i915_gem_object_types.h b/sys/dev/pci/drm/i915/gem/i915_gem_object_types.h index 46bdb138b..525b0b7d1 100644 --- a/sys/dev/pci/drm/i915/gem/i915_gem_object_types.h +++ b/sys/dev/pci/drm/i915/gem/i915_gem_object_types.h @@ -114,7 +114,11 @@ struct drm_i915_gem_object_ops { void (*release)(struct drm_i915_gem_object *obj); +#ifdef __linux__ const struct vm_operations_struct *mmap_ops; +#else + const struct uvm_pagerops *mmap_ops; +#endif const char *name; /* friendly name for debug, e.g. lockdep classes */ }; diff --git a/sys/dev/pci/drm/i915/gem/i915_gem_ttm.c b/sys/dev/pci/drm/i915/gem/i915_gem_ttm.c index e02791026..fc99a31b4 100644 --- a/sys/dev/pci/drm/i915/gem/i915_gem_ttm.c +++ b/sys/dev/pci/drm/i915/gem/i915_gem_ttm.c @@ -1067,7 +1067,8 @@ static void i915_ttm_delayed_free(struct drm_i915_gem_object *obj) ttm_bo_put(i915_gem_to_ttm(obj)); } -#ifdef notyet +#ifdef __linux__ + static vm_fault_t vm_fault_ttm(struct vm_fault *vmf) { struct vm_area_struct *area = vmf->vma; @@ -1219,6 +1220,187 @@ static const struct vm_operations_struct vm_ops_ttm = { .close = ttm_vm_close, }; +#else /* !__linux__ */ + +static int + +vm_fault_ttm(struct uvm_faultinfo *ufi, vaddr_t vaddr, vm_page_t *pps, + int npages, int centeridx, vm_fault_t fault_type, + vm_prot_t access_type, int flags) +{ + struct uvm_object *uobj = ufi->entry->object.uvm_obj; + struct ttm_buffer_object *bo = (struct ttm_buffer_object *)uobj; + struct drm_device *dev = bo->base.dev; + struct drm_i915_gem_object *obj = i915_ttm_to_gem(bo); + intel_wakeref_t wakeref = 0; + vm_fault_t ret; + int idx; + int write = !!(access_type & PROT_WRITE); + + /* Sanity check that we allow writing into this object */ + if (unlikely(i915_gem_object_is_readonly(obj) && write)) { + uvmfault_unlockall(ufi, NULL, &obj->base.uobj); + return VM_PAGER_BAD; + } + + ret = ttm_bo_vm_reserve(bo); + if (ret) { + switch (ret) { + case VM_FAULT_NOPAGE: + ret = VM_PAGER_OK; + break; + case VM_FAULT_RETRY: + ret = VM_PAGER_REFAULT; + break; + default: + ret = VM_PAGER_BAD; + break; + } + uvmfault_unlockall(ufi, NULL, &obj->base.uobj); + return ret; + } + + if (obj->mm.madv != I915_MADV_WILLNEED) { + dma_resv_unlock(bo->base.resv); + uvmfault_unlockall(ufi, NULL, &obj->base.uobj); + return VM_PAGER_BAD; + } + + /* + * This must be swapped out with shmem ttm_tt (pipeline-gutting). + * Calling ttm_bo_validate() here with TTM_PL_SYSTEM should only go as + * far as far doing a ttm_bo_move_null(), which should skip all the + * other junk. + */ + if (!bo->resource) { + struct ttm_operation_ctx ctx = { + .interruptible = true, + .no_wait_gpu = true, /* should be idle already */ + }; + int err; + + GEM_BUG_ON(!bo->ttm || !(bo->ttm->page_flags & TTM_TT_FLAG_SWAPPED)); + + err = ttm_bo_validate(bo, i915_ttm_sys_placement(), &ctx); + if (err) { + dma_resv_unlock(bo->base.resv); + uvmfault_unlockall(ufi, NULL, &obj->base.uobj); + return VM_PAGER_BAD; + } + } else if (!i915_ttm_resource_mappable(bo->resource)) { + int err = -ENODEV; + int i; + + for (i = 0; i < obj->mm.n_placements; i++) { + struct intel_memory_region *mr = obj->mm.placements[i]; + unsigned int flags; + + if (!mr->io_size && mr->type != INTEL_MEMORY_SYSTEM) + continue; + + flags = obj->flags; + flags &= ~I915_BO_ALLOC_GPU_ONLY; + err = __i915_ttm_migrate(obj, mr, flags); + if (!err) + break; + } + + if (err) { + drm_dbg(dev, "Unable to make resource CPU accessible(err = %pe)\n", + ERR_PTR(err)); + dma_resv_unlock(bo->base.resv); + ret = VM_FAULT_SIGBUS; + goto out_rpm; + } + } + + if (i915_ttm_cpu_maps_iomem(bo->resource)) + wakeref = intel_runtime_pm_get(&to_i915(obj->base.dev)->runtime_pm); + + if (drm_dev_enter(dev, &idx)) { + ret = ttm_bo_vm_fault_reserved(ufi, vaddr, + TTM_BO_VM_NUM_PREFAULT, 1); + drm_dev_exit(idx); + } else { + STUB(); +#ifdef notyet + ret = ttm_bo_vm_dummy_page(vmf, vmf->vma->vm_page_prot); +#else + STUB(); + ret = VM_FAULT_NOPAGE; +#endif + } +#ifdef __linux__ + if (ret == VM_FAULT_RETRY && !(vmf->flags & FAULT_FLAG_RETRY_NOWAIT)) + goto out_rpm; +#endif + + /* + * ttm_bo_vm_reserve() already has dma_resv_lock. + * userfault_count is protected by dma_resv lock and rpm wakeref. + */ + if (ret == VM_FAULT_NOPAGE && wakeref && !obj->userfault_count) { + obj->userfault_count = 1; + spin_lock(&to_i915(obj->base.dev)->runtime_pm.lmem_userfault_lock); + list_add(&obj->userfault_link, &to_i915(obj->base.dev)->runtime_pm.lmem_userfault_list); + spin_unlock(&to_i915(obj->base.dev)->runtime_pm.lmem_userfault_lock); + + GEM_WARN_ON(!i915_ttm_cpu_maps_iomem(bo->resource)); + } + + if (wakeref & CONFIG_DRM_I915_USERFAULT_AUTOSUSPEND) + intel_wakeref_auto(&to_i915(obj->base.dev)->runtime_pm.userfault_wakeref, + msecs_to_jiffies_timeout(CONFIG_DRM_I915_USERFAULT_AUTOSUSPEND)); + + i915_ttm_adjust_lru(obj); + + dma_resv_unlock(bo->base.resv); + +out_rpm: + switch (ret) { + case VM_FAULT_NOPAGE: + ret = VM_PAGER_OK; + break; + case VM_FAULT_RETRY: + ret = VM_PAGER_REFAULT; + break; + default: + ret = VM_PAGER_BAD; + break; + } + + if (wakeref) + intel_runtime_pm_put(&to_i915(obj->base.dev)->runtime_pm, wakeref); + + uvmfault_unlockall(ufi, NULL, &obj->base.uobj); + + return ret; +} + +static void +ttm_vm_reference(struct uvm_object *uobj) +{ + struct drm_i915_gem_object *obj = + i915_ttm_to_gem((struct ttm_buffer_object *)uobj); + + i915_gem_object_get(obj); +} + +static void +ttm_vm_detach(struct uvm_object *uobj) +{ + struct drm_i915_gem_object *obj = + i915_ttm_to_gem((struct ttm_buffer_object *)uobj); + + i915_gem_object_put(obj); +} + +const struct uvm_pagerops vm_ops_ttm = { + .pgo_fault = vm_fault_ttm, + .pgo_reference = ttm_vm_reference, + .pgo_detach = ttm_vm_detach, +}; + #endif static u64 i915_ttm_mmap_offset(struct drm_i915_gem_object *obj) @@ -1272,9 +1454,7 @@ static const struct drm_i915_gem_object_ops i915_gem_ttm_obj_ops = { .mmap_offset = i915_ttm_mmap_offset, .unmap_virtual = i915_ttm_unmap_virtual, -#ifdef notyet .mmap_ops = &vm_ops_ttm, -#endif }; void i915_ttm_bo_destroy(struct ttm_buffer_object *bo) diff --git a/sys/kern/kern_lock.c b/sys/kern/kern_lock.c index b21e1aa55..19f441bd5 100644 --- a/sys/kern/kern_lock.c +++ b/sys/kern/kern_lock.c @@ -1,4 +1,4 @@ -/* $OpenBSD: kern_lock.c,v 1.72 2022/04/26 15:31:14 dv Exp $ */ +/* $OpenBSD: kern_lock.c,v 1.73 2024/03/26 18:18:30 bluhm Exp $ */ /* * Copyright (c) 2017 Visa Hankala @@ -264,15 +264,17 @@ mtx_enter(struct mutex *mtx) spc->spc_spinning++; while (mtx_enter_try(mtx) == 0) { - CPU_BUSY_CYCLE(); - + do { + CPU_BUSY_CYCLE(); #ifdef MP_LOCKDEBUG - if (--nticks == 0) { - db_printf("%s: %p lock spun out\n", __func__, mtx); - db_enter(); - nticks = __mp_lock_spinout; - } + if (--nticks == 0) { + db_printf("%s: %p lock spun out\n", + __func__, mtx); + db_enter(); + nticks = __mp_lock_spinout; + } #endif + } while (mtx->mtx_owner != NULL); } spc->spc_spinning--; } diff --git a/sys/kern/sys_socket.c b/sys/kern/sys_socket.c index 8a0c8ed0e..bba512b43 100644 --- a/sys/kern/sys_socket.c +++ b/sys/kern/sys_socket.c @@ -1,4 +1,4 @@ -/* $OpenBSD: sys_socket.c,v 1.61 2023/04/15 13:18:28 kn Exp $ */ +/* $OpenBSD: sys_socket.c,v 1.62 2024/03/26 09:46:47 mvs Exp $ */ /* $NetBSD: sys_socket.c,v 1.13 1995/08/12 23:59:09 mycroft Exp $ */ /* @@ -144,9 +144,11 @@ soo_stat(struct file *fp, struct stat *ub, struct proc *p) memset(ub, 0, sizeof (*ub)); ub->st_mode = S_IFSOCK; solock(so); + mtx_enter(&so->so_rcv.sb_mtx); if ((so->so_rcv.sb_state & SS_CANTRCVMORE) == 0 || so->so_rcv.sb_cc != 0) ub->st_mode |= S_IRUSR | S_IRGRP | S_IROTH; + mtx_leave(&so->so_rcv.sb_mtx); if ((so->so_snd.sb_state & SS_CANTSENDMORE) == 0) ub->st_mode |= S_IWUSR | S_IWGRP | S_IWOTH; ub->st_uid = so->so_euid; diff --git a/sys/kern/uipc_socket.c b/sys/kern/uipc_socket.c index 7b04935ef..06313d40c 100644 --- a/sys/kern/uipc_socket.c +++ b/sys/kern/uipc_socket.c @@ -1,4 +1,4 @@ -/* $OpenBSD: uipc_socket.c,v 1.321 2024/03/22 17:34:11 mvs Exp $ */ +/* $OpenBSD: uipc_socket.c,v 1.322 2024/03/26 09:46:47 mvs Exp $ */ /* $NetBSD: uipc_socket.c,v 1.21 1996/02/04 02:17:52 christos Exp $ */ /* @@ -160,6 +160,9 @@ soalloc(const struct protosw *prp, int wait) break; } break; + case AF_UNIX: + so->so_rcv.sb_flags |= SB_MTXLOCK; + break; } return (so); @@ -987,8 +990,11 @@ dontblock: * Dispose of any SCM_RIGHTS message that went * through the read path rather than recv. */ - if (pr->pr_domain->dom_dispose) + if (pr->pr_domain->dom_dispose) { + sb_mtx_unlock(&so->so_rcv); pr->pr_domain->dom_dispose(cm); + sb_mtx_lock(&so->so_rcv); + } m_free(cm); } } @@ -1173,8 +1179,11 @@ dontblock: } SBLASTRECORDCHK(&so->so_rcv, "soreceive 4"); SBLASTMBUFCHK(&so->so_rcv, "soreceive 4"); - if (pr->pr_flags & PR_WANTRCVD) + if (pr->pr_flags & PR_WANTRCVD) { + sb_mtx_unlock(&so->so_rcv); pru_rcvd(so); + sb_mtx_lock(&so->so_rcv); + } } if (orig_resid == uio->uio_resid && orig_resid && (flags & MSG_EOR) == 0 && @@ -1233,10 +1242,10 @@ sorflush(struct socket *so) /* with SBL_WAIT and SLB_NOINTR sblock() must not fail */ KASSERT(error == 0); socantrcvmore(so); + mtx_enter(&sb->sb_mtx); m = sb->sb_mb; memset(&sb->sb_startzero, 0, (caddr_t)&sb->sb_endzero - (caddr_t)&sb->sb_startzero); - mtx_enter(&sb->sb_mtx); sb->sb_timeo_nsecs = INFSLP; mtx_leave(&sb->sb_mtx); sbunlock(so, sb); @@ -1757,7 +1766,8 @@ somove(struct socket *so, int wait) void sorwakeup(struct socket *so) { - soassertlocked_readonly(so); + if ((so->so_rcv.sb_flags & SB_MTXLOCK) == 0) + soassertlocked_readonly(so); #ifdef SOCKET_SPLICE if (so->so_rcv.sb_flags & SB_SPLICE) { @@ -1877,6 +1887,8 @@ sosetopt(struct socket *so, int level, int optname, struct mbuf *m) cnt = 1; solock(so); + mtx_enter(&sb->sb_mtx); + switch (optname) { case SO_SNDBUF: case SO_RCVBUF: @@ -1898,7 +1910,10 @@ sosetopt(struct socket *so, int level, int optname, struct mbuf *m) sb->sb_hiwat : cnt; break; } + + mtx_leave(&sb->sb_mtx); sounlock(so); + break; } @@ -2169,13 +2184,6 @@ sofilt_unlock(struct socket *so, struct sockbuf *sb) } } -static inline void -sofilt_assert_locked(struct socket *so, struct sockbuf *sb) -{ - MUTEX_ASSERT_LOCKED(&sb->sb_mtx); - soassertlocked_readonly(so); -} - int soo_kqfilter(struct file *fp, struct knote *kn) { @@ -2218,9 +2226,14 @@ filt_soread(struct knote *kn, long hint) struct socket *so = kn->kn_fp->f_data; int rv = 0; - sofilt_assert_locked(so, &so->so_rcv); + MUTEX_ASSERT_LOCKED(&so->so_rcv.sb_mtx); + if ((so->so_rcv.sb_flags & SB_MTXLOCK) == 0) + soassertlocked_readonly(so); if (so->so_options & SO_ACCEPTCONN) { + if (so->so_rcv.sb_flags & SB_MTXLOCK) + soassertlocked_readonly(so); + kn->kn_data = so->so_qlen; rv = (kn->kn_data != 0); @@ -2275,7 +2288,8 @@ filt_sowrite(struct knote *kn, long hint) struct socket *so = kn->kn_fp->f_data; int rv; - sofilt_assert_locked(so, &so->so_snd); + MUTEX_ASSERT_LOCKED(&so->so_snd.sb_mtx); + soassertlocked_readonly(so); kn->kn_data = sbspace(so, &so->so_snd); if (so->so_snd.sb_state & SS_CANTSENDMORE) { @@ -2306,7 +2320,9 @@ filt_soexcept(struct knote *kn, long hint) struct socket *so = kn->kn_fp->f_data; int rv = 0; - sofilt_assert_locked(so, &so->so_rcv); + MUTEX_ASSERT_LOCKED(&so->so_rcv.sb_mtx); + if ((so->so_rcv.sb_flags & SB_MTXLOCK) == 0) + soassertlocked_readonly(so); #ifdef SOCKET_SPLICE if (isspliced(so)) { diff --git a/sys/kern/uipc_socket2.c b/sys/kern/uipc_socket2.c index 70f7c150f..153010a59 100644 --- a/sys/kern/uipc_socket2.c +++ b/sys/kern/uipc_socket2.c @@ -1,4 +1,4 @@ -/* $OpenBSD: uipc_socket2.c,v 1.144 2024/02/12 22:48:27 mvs Exp $ */ +/* $OpenBSD: uipc_socket2.c,v 1.145 2024/03/26 09:46:47 mvs Exp $ */ /* $NetBSD: uipc_socket2.c,v 1.11 1996/02/04 02:17:55 christos Exp $ */ /* @@ -142,7 +142,9 @@ soisdisconnecting(struct socket *so) soassertlocked(so); so->so_state &= ~SS_ISCONNECTING; so->so_state |= SS_ISDISCONNECTING; + mtx_enter(&so->so_rcv.sb_mtx); so->so_rcv.sb_state |= SS_CANTRCVMORE; + mtx_leave(&so->so_rcv.sb_mtx); so->so_snd.sb_state |= SS_CANTSENDMORE; wakeup(&so->so_timeo); sowwakeup(so); @@ -155,7 +157,9 @@ soisdisconnected(struct socket *so) soassertlocked(so); so->so_state &= ~(SS_ISCONNECTING|SS_ISCONNECTED|SS_ISDISCONNECTING); so->so_state |= SS_ISDISCONNECTED; + mtx_enter(&so->so_rcv.sb_mtx); so->so_rcv.sb_state |= SS_CANTRCVMORE; + mtx_leave(&so->so_rcv.sb_mtx); so->so_snd.sb_state |= SS_CANTSENDMORE; wakeup(&so->so_timeo); sowwakeup(so); @@ -219,9 +223,10 @@ sonewconn(struct socket *head, int connstatus, int wait) mtx_enter(&head->so_snd.sb_mtx); so->so_snd.sb_timeo_nsecs = head->so_snd.sb_timeo_nsecs; mtx_leave(&head->so_snd.sb_mtx); + + mtx_enter(&head->so_rcv.sb_mtx); so->so_rcv.sb_wat = head->so_rcv.sb_wat; so->so_rcv.sb_lowat = head->so_rcv.sb_lowat; - mtx_enter(&head->so_rcv.sb_mtx); so->so_rcv.sb_timeo_nsecs = head->so_rcv.sb_timeo_nsecs; mtx_leave(&head->so_rcv.sb_mtx); @@ -651,16 +656,22 @@ soreserve(struct socket *so, u_long sndcc, u_long rcvcc) if (sbreserve(so, &so->so_snd, sndcc)) goto bad; - if (sbreserve(so, &so->so_rcv, rcvcc)) - goto bad2; so->so_snd.sb_wat = sndcc; - so->so_rcv.sb_wat = rcvcc; - if (so->so_rcv.sb_lowat == 0) - so->so_rcv.sb_lowat = 1; if (so->so_snd.sb_lowat == 0) so->so_snd.sb_lowat = MCLBYTES; if (so->so_snd.sb_lowat > so->so_snd.sb_hiwat) so->so_snd.sb_lowat = so->so_snd.sb_hiwat; + + mtx_enter(&so->so_rcv.sb_mtx); + if (sbreserve(so, &so->so_rcv, rcvcc)) { + mtx_leave(&so->so_rcv.sb_mtx); + goto bad2; + } + so->so_rcv.sb_wat = rcvcc; + if (so->so_rcv.sb_lowat == 0) + so->so_rcv.sb_lowat = 1; + mtx_leave(&so->so_rcv.sb_mtx); + return (0); bad2: sbrelease(so, &so->so_snd); @@ -676,8 +687,7 @@ bad: int sbreserve(struct socket *so, struct sockbuf *sb, u_long cc) { - KASSERT(sb == &so->so_rcv || sb == &so->so_snd); - soassertlocked(so); + sbmtxassertlocked(so, sb); if (cc == 0 || cc > sb_max) return (1); @@ -818,7 +828,7 @@ sbappend(struct socket *so, struct sockbuf *sb, struct mbuf *m) if (m == NULL) return; - soassertlocked(so); + sbmtxassertlocked(so, sb); SBLASTRECORDCHK(sb, "sbappend 1"); if ((n = sb->sb_lastrecord) != NULL) { @@ -899,8 +909,7 @@ sbappendrecord(struct socket *so, struct sockbuf *sb, struct mbuf *m0) { struct mbuf *m; - KASSERT(sb == &so->so_rcv || sb == &so->so_snd); - soassertlocked(so); + sbmtxassertlocked(so, sb); if (m0 == NULL) return; @@ -984,6 +993,8 @@ sbappendcontrol(struct socket *so, struct sockbuf *sb, struct mbuf *m0, struct mbuf *m, *mlast, *n; int eor = 0, space = 0; + sbmtxassertlocked(so, sb); + if (control == NULL) panic("sbappendcontrol"); for (m = control; ; m = m->m_next) { @@ -1109,8 +1120,7 @@ sbdrop(struct socket *so, struct sockbuf *sb, int len) struct mbuf *m, *mn; struct mbuf *next; - KASSERT(sb == &so->so_rcv || sb == &so->so_snd); - soassertlocked(so); + sbmtxassertlocked(so, sb); next = (m = sb->sb_mb) ? m->m_nextpkt : NULL; while (len > 0) { diff --git a/sys/kern/uipc_usrreq.c b/sys/kern/uipc_usrreq.c index 6a480c517..d11b30f96 100644 --- a/sys/kern/uipc_usrreq.c +++ b/sys/kern/uipc_usrreq.c @@ -1,4 +1,4 @@ -/* $OpenBSD: uipc_usrreq.c,v 1.202 2024/03/22 17:34:11 mvs Exp $ */ +/* $OpenBSD: uipc_usrreq.c,v 1.203 2024/03/26 09:46:47 mvs Exp $ */ /* $NetBSD: uipc_usrreq.c,v 1.18 1996/02/09 19:00:50 christos Exp $ */ /* @@ -489,8 +489,10 @@ uipc_rcvd(struct socket *so) * Adjust backpressure on sender * and wakeup any waiting to write. */ + mtx_enter(&so->so_rcv.sb_mtx); so2->so_snd.sb_mbcnt = so->so_rcv.sb_mbcnt; so2->so_snd.sb_cc = so->so_rcv.sb_cc; + mtx_leave(&so->so_rcv.sb_mtx); sowwakeup(so2); sounlock(so2); } @@ -499,8 +501,9 @@ int uipc_send(struct socket *so, struct mbuf *m, struct mbuf *nam, struct mbuf *control) { + struct unpcb *unp = sotounpcb(so); struct socket *so2; - int error = 0; + int error = 0, dowakeup = 0; if (control) { sounlock(so); @@ -514,21 +517,24 @@ uipc_send(struct socket *so, struct mbuf *m, struct mbuf *nam, error = EPIPE; goto dispose; } - if ((so2 = unp_solock_peer(so)) == NULL) { + if (unp->unp_conn == NULL) { error = ENOTCONN; goto dispose; } + so2 = unp->unp_conn->unp_socket; + /* * Send to paired receive port, and then raise * send buffer counts to maintain backpressure. * Wake up readers. */ + mtx_enter(&so2->so_rcv.sb_mtx); if (control) { if (sbappendcontrol(so2, &so2->so_rcv, m, control)) { control = NULL; } else { - sounlock(so2); + mtx_leave(&so2->so_rcv.sb_mtx); error = ENOBUFS; goto dispose; } @@ -539,9 +545,12 @@ uipc_send(struct socket *so, struct mbuf *m, struct mbuf *nam, so->so_snd.sb_mbcnt = so2->so_rcv.sb_mbcnt; so->so_snd.sb_cc = so2->so_rcv.sb_cc; if (so2->so_rcv.sb_cc > 0) + dowakeup = 1; + mtx_leave(&so2->so_rcv.sb_mtx); + + if (dowakeup) sorwakeup(so2); - sounlock(so2); m = NULL; dispose: @@ -563,7 +572,7 @@ uipc_dgram_send(struct socket *so, struct mbuf *m, struct mbuf *nam, struct unpcb *unp = sotounpcb(so); struct socket *so2; const struct sockaddr *from; - int error = 0; + int error = 0, dowakeup = 0; if (control) { sounlock(so); @@ -583,7 +592,7 @@ uipc_dgram_send(struct socket *so, struct mbuf *m, struct mbuf *nam, goto dispose; } - if ((so2 = unp_solock_peer(so)) == NULL) { + if (unp->unp_conn == NULL) { if (nam != NULL) error = ECONNREFUSED; else @@ -591,20 +600,24 @@ uipc_dgram_send(struct socket *so, struct mbuf *m, struct mbuf *nam, goto dispose; } + so2 = unp->unp_conn->unp_socket; + if (unp->unp_addr) from = mtod(unp->unp_addr, struct sockaddr *); else from = &sun_noname; + + mtx_enter(&so2->so_rcv.sb_mtx); if (sbappendaddr(so2, &so2->so_rcv, from, m, control)) { - sorwakeup(so2); + dowakeup = 1; m = NULL; control = NULL; } else error = ENOBUFS; + mtx_leave(&so2->so_rcv.sb_mtx); - if (so2 != so) - sounlock(so2); - + if (dowakeup) + sorwakeup(so2); if (nam) unp_disconnect(unp); @@ -1390,9 +1403,9 @@ unp_gc(void *arg __unused) if ((unp->unp_gcflags & UNP_GCDEAD) == 0) continue; so = unp->unp_socket; - solock(so); + mtx_enter(&so->so_rcv.sb_mtx); unp_scan(so->so_rcv.sb_mb, unp_remove_gcrefs); - sounlock(so); + mtx_leave(&so->so_rcv.sb_mtx); } /* @@ -1414,9 +1427,9 @@ unp_gc(void *arg __unused) unp->unp_gcflags &= ~UNP_GCDEAD; so = unp->unp_socket; - solock(so); + mtx_enter(&so->so_rcv.sb_mtx); unp_scan(so->so_rcv.sb_mb, unp_restore_gcrefs); - sounlock(so); + mtx_leave(&so->so_rcv.sb_mtx); KASSERT(nunref > 0); nunref--; diff --git a/sys/miscfs/fifofs/fifo_vnops.c b/sys/miscfs/fifofs/fifo_vnops.c index 545837282..81175a674 100644 --- a/sys/miscfs/fifofs/fifo_vnops.c +++ b/sys/miscfs/fifofs/fifo_vnops.c @@ -1,4 +1,4 @@ -/* $OpenBSD: fifo_vnops.c,v 1.103 2024/02/03 22:50:09 mvs Exp $ */ +/* $OpenBSD: fifo_vnops.c,v 1.104 2024/03/26 09:46:47 mvs Exp $ */ /* $NetBSD: fifo_vnops.c,v 1.18 1996/03/16 23:52:42 christos Exp $ */ /* @@ -201,7 +201,9 @@ fifo_open(void *v) if (fip->fi_writers == 1) { solock(rso); rso->so_state &= ~SS_ISDISCONNECTED; + mtx_enter(&rso->so_rcv.sb_mtx); rso->so_rcv.sb_state &= ~SS_CANTRCVMORE; + mtx_leave(&rso->so_rcv.sb_mtx); sounlock(rso); if (fip->fi_readers > 0) wakeup(&fip->fi_readers); @@ -518,7 +520,6 @@ filt_fiforead(struct knote *kn, long hint) struct socket *so = kn->kn_hook; int rv; - soassertlocked(so); MUTEX_ASSERT_LOCKED(&so->so_rcv.sb_mtx); kn->kn_data = so->so_rcv.sb_cc; @@ -574,7 +575,6 @@ filt_fifoexcept(struct knote *kn, long hint) struct socket *so = kn->kn_hook; int rv = 0; - soassertlocked(so); MUTEX_ASSERT_LOCKED(&so->so_rcv.sb_mtx); if (kn->kn_flags & __EV_POLL) { diff --git a/sys/net/rtable.c b/sys/net/rtable.c index 38282ebd7..48108ce02 100644 --- a/sys/net/rtable.c +++ b/sys/net/rtable.c @@ -1,4 +1,4 @@ -/* $OpenBSD: rtable.c,v 1.85 2023/11/12 17:51:40 bluhm Exp $ */ +/* $OpenBSD: rtable.c,v 1.86 2024/03/26 10:01:57 bluhm Exp $ */ /* * Copyright (c) 2014-2016 Martin Pieuchot @@ -875,7 +875,7 @@ an_match(struct art_node *an, const struct sockaddr *dst, int plen) return (0); rt = SRPL_FIRST(&sr, &an->an_rtlist); - match = (memcmp(rt->rt_dest, dst, dst->sa_len) == 0); + match = (rt != NULL && memcmp(rt->rt_dest, dst, dst->sa_len) == 0); SRPL_LEAVE(&sr); return (match); diff --git a/sys/netinet6/frag6.c b/sys/netinet6/frag6.c index 5ecb11f1c..1b528b30b 100644 --- a/sys/netinet6/frag6.c +++ b/sys/netinet6/frag6.c @@ -1,4 +1,4 @@ -/* $OpenBSD: frag6.c,v 1.87 2022/02/22 01:15:02 guenther Exp $ */ +/* $OpenBSD: frag6.c,v 1.88 2024/03/26 23:48:49 bluhm Exp $ */ /* $KAME: frag6.c,v 1.40 2002/05/27 21:40:31 itojun Exp $ */ /* @@ -404,8 +404,17 @@ frag6_input(struct mbuf **mp, int *offp, int proto, int af) /* adjust offset to point where the original next header starts */ offset = ip6af->ip6af_offset - sizeof(struct ip6_frag); pool_put(&ip6af_pool, ip6af); + next += offset - sizeof(struct ip6_hdr); + if ((u_int)next > IPV6_MAXPACKET) { + TAILQ_REMOVE(&frag6_queue, q6, ip6q_queue); + frag6_nfrags -= q6->ip6q_nfrag; + frag6_nfragpackets--; + mtx_leave(&frag6_mutex); + pool_put(&ip6q_pool, q6); + goto dropfrag; + } ip6 = mtod(m, struct ip6_hdr *); - ip6->ip6_plen = htons((u_short)next + offset - sizeof(struct ip6_hdr)); + ip6->ip6_plen = htons(next); ip6->ip6_src = q6->ip6q_src; ip6->ip6_dst = q6->ip6q_dst; if (q6->ip6q_ecn == IPTOS_ECN_CE) diff --git a/sys/sys/mutex.h b/sys/sys/mutex.h index a90714c82..cff33404c 100644 --- a/sys/sys/mutex.h +++ b/sys/sys/mutex.h @@ -1,4 +1,4 @@ -/* $OpenBSD: mutex.h,v 1.20 2024/02/03 22:50:09 mvs Exp $ */ +/* $OpenBSD: mutex.h,v 1.21 2024/03/26 18:18:30 bluhm Exp $ */ /* * Copyright (c) 2004 Artur Grabowski @@ -40,7 +40,7 @@ #include struct mutex { - volatile void *mtx_owner; + void *volatile mtx_owner; int mtx_wantipl; int mtx_oldipl; #ifdef WITNESS diff --git a/sys/sys/socketvar.h b/sys/sys/socketvar.h index dc34b1c5c..782ebce75 100644 --- a/sys/sys/socketvar.h +++ b/sys/sys/socketvar.h @@ -1,4 +1,4 @@ -/* $OpenBSD: socketvar.h,v 1.125 2024/03/22 17:34:11 mvs Exp $ */ +/* $OpenBSD: socketvar.h,v 1.126 2024/03/26 09:46:47 mvs Exp $ */ /* $NetBSD: socketvar.h,v 1.18 1996/02/09 18:25:38 christos Exp $ */ /*- @@ -242,7 +242,10 @@ sb_notify(struct socket *so, struct sockbuf *sb) static inline long sbspace(struct socket *so, struct sockbuf *sb) { - soassertlocked_readonly(so); + if (sb->sb_flags & SB_MTXLOCK) + sbmtxassertlocked(so, sb); + else + soassertlocked_readonly(so); return lmin(sb->sb_hiwat - sb->sb_cc, sb->sb_mbmax - sb->sb_mbcnt); } diff --git a/usr.bin/tmux/window-copy.c b/usr.bin/tmux/window-copy.c index 913f35103..3ae46cdc9 100644 --- a/usr.bin/tmux/window-copy.c +++ b/usr.bin/tmux/window-copy.c @@ -1,4 +1,4 @@ -/* $OpenBSD: window-copy.c,v 1.346 2024/03/21 11:26:28 nicm Exp $ */ +/* $OpenBSD: window-copy.c,v 1.347 2024/03/26 10:20:20 nicm Exp $ */ /* * Copyright (c) 2007 Nicholas Marriott @@ -805,7 +805,7 @@ window_copy_formats(struct window_mode_entry *wme, struct format_tree *ft) format_add(ft, "selection_active", "1"); else format_add(ft, "selection_active", "0"); - if (data->endselx != data->selx && data->endsely != data->sely) + if (data->endselx != data->selx || data->endsely != data->sely) format_add(ft, "selection_present", "1"); else format_add(ft, "selection_present", "0"); diff --git a/usr.sbin/bgpd/session.c b/usr.sbin/bgpd/session.c index da3d0311c..a5ce33808 100644 --- a/usr.sbin/bgpd/session.c +++ b/usr.sbin/bgpd/session.c @@ -1,4 +1,4 @@ -/* $OpenBSD: session.c,v 1.466 2024/03/22 15:41:34 claudio Exp $ */ +/* $OpenBSD: session.c,v 1.467 2024/03/26 12:45:29 claudio Exp $ */ /* * Copyright (c) 2003, 2004, 2005 Henning Brauer @@ -58,6 +58,7 @@ void session_sighdlr(int); int setup_listeners(u_int *); void init_peer(struct peer *); void start_timer_holdtime(struct peer *); +void start_timer_sendholdtime(struct peer *); void start_timer_keepalive(struct peer *); void session_close_connection(struct peer *); void change_state(struct peer *, enum session_state, enum session_events); @@ -835,6 +836,20 @@ start_timer_holdtime(struct peer *peer) timer_stop(&peer->timers, Timer_Hold); } +void +start_timer_sendholdtime(struct peer *peer) +{ + uint16_t holdtime = INTERVAL_HOLD; + + if (peer->holdtime > INTERVAL_HOLD) + holdtime = peer->holdtime; + + if (peer->holdtime > 0) + timer_set(&peer->timers, Timer_SendHold, holdtime); + else + timer_stop(&peer->timers, Timer_SendHold); +} + void start_timer_keepalive(struct peer *peer) { @@ -1929,10 +1944,7 @@ session_dispatch_msg(struct pollfd *pfd, struct peer *p) return (1); } p->stats.last_write = getmonotime(); - if (p->holdtime > 0) - timer_set(&p->timers, Timer_SendHold, - p->holdtime < INTERVAL_HOLD ? INTERVAL_HOLD : - p->holdtime); + start_timer_sendholdtime(p); if (p->throttled && p->wbuf.queued < SESS_MSG_LOW_MARK) { if (imsg_rde(IMSG_XON, p->conf.id, NULL, 0) == -1) log_peer_warn(&p->conf, "imsg_compose XON");