summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authortb <>2023-03-31 06:07:44 +0000
committertb <>2023-03-31 06:07:44 +0000
commit25a20dbee47e2778717afc53f5d438b40d543256 (patch)
treea362baf173cc7fea2ae5dd049cc308a5d976eed7
parent96e4788cde61058167082e95712348212c565bf9 (diff)
downloadopenbsd-25a20dbee47e2778717afc53f5d438b40d543256.tar.gz
openbsd-25a20dbee47e2778717afc53f5d438b40d543256.tar.bz2
openbsd-25a20dbee47e2778717afc53f5d438b40d543256.zip
Add a regress for the recent BIO_new_NDEF() write after free
This is a simple reproducer for a write after free that avoids all the mess with CMS, PKCS7 and SMIME. This now mostly allows ASAN to check that the memory handling in this marvellous function is correct.
-rw-r--r--src/regress/lib/libcrypto/bio/bio_asn1.c61
1 files changed, 59 insertions, 2 deletions
diff --git a/src/regress/lib/libcrypto/bio/bio_asn1.c b/src/regress/lib/libcrypto/bio/bio_asn1.c
index 9ee2bb5341..ac7f48ced8 100644
--- a/src/regress/lib/libcrypto/bio/bio_asn1.c
+++ b/src/regress/lib/libcrypto/bio/bio_asn1.c
@@ -1,4 +1,4 @@
1/* $OpenBSD: bio_asn1.c,v 1.1 2023/03/26 19:14:11 tb Exp $ */ 1/* $OpenBSD: bio_asn1.c,v 1.2 2023/03/31 06:07:44 tb Exp $ */
2 2
3/* 3/*
4 * Copyright (c) 2023 Theo Buehler <tb@openbsd.org> 4 * Copyright (c) 2023 Theo Buehler <tb@openbsd.org>
@@ -21,9 +21,65 @@
21#include <stdlib.h> 21#include <stdlib.h>
22 22
23#include <openssl/asn1.h> 23#include <openssl/asn1.h>
24#include <openssl/asn1t.h>
24#include <openssl/bio.h> 25#include <openssl/bio.h>
25#include <openssl/pkcs7.h> 26#include <openssl/evp.h>
26#include <openssl/objects.h> 27#include <openssl/objects.h>
28#include <openssl/pkcs7.h>
29
30/*
31 * Minimal reproducer for the BIO_new_NDEF() write after free fixed in
32 * bio_ndef.c r1.13.
33 */
34
35static int
36waf_cb(int op, ASN1_VALUE **pval, const ASN1_ITEM *it, void *exarg)
37{
38 return 0;
39}
40
41static const ASN1_AUX WAF_aux = {
42 .asn1_cb = waf_cb,
43};
44
45static const ASN1_ITEM WAF_it = {
46 .funcs = &WAF_aux,
47};
48
49static int
50test_bio_new_ndef_waf(void)
51{
52 BIO *out = NULL;
53 int failed = 1;
54
55 if ((out = BIO_new(BIO_s_mem())) == NULL)
56 goto err;
57
58 /*
59 * BIO_new_NDEF() pushes out onto asn_bio. The waf_cb() call fails.
60 * Prior to bio_ndef.c r1.13, asn_bio was freed and out->prev_bio
61 * still pointed to it.
62 */
63
64 if (BIO_new_NDEF(out, NULL, &WAF_it) != NULL) {
65 fprintf(stderr, "%s: BIO_new_NDEF succeeded\n", __func__);
66 goto err;
67 }
68
69 /*
70 * If out->prev_bio != NULL, this writes to out->prev_bio->next_bio.
71 * After bio_ndef.c r1.13, out is an isolated BIO, so this is a noop.
72 */
73
74 BIO_pop(out);
75
76 failed = 0;
77
78 err:
79 BIO_free(out);
80
81 return failed;
82}
27 83
28/* 84/*
29 * test_prefix_leak() leaks before asn/bio_asn1.c r1.19. 85 * test_prefix_leak() leaks before asn/bio_asn1.c r1.19.
@@ -167,6 +223,7 @@ main(void)
167{ 223{
168 int failed = 0; 224 int failed = 0;
169 225
226 failed |= test_bio_new_ndef_waf();
170 failed |= test_prefix_leak(); 227 failed |= test_prefix_leak();
171 failed |= test_infinite_loop(); 228 failed |= test_infinite_loop();
172 229