Skip to content

Commit ebfa205

Browse files
committedOct 27, 2020
Return NULL early in context_preallocated_create if flags invalid
If the user passes invalid flags to _context_create, and the default illegal callback does not abort the program (which is possible), then we work with the result of malloc(0), which may be undefined behavior. This violates the promise that a library function won't crash after the illegal callback has been called. This commit fixes this issue by returning NULL early in _context_create in that case.
1 parent ac05f61 commit ebfa205

File tree

1 file changed

+9
-7
lines changed

1 file changed

+9
-7
lines changed
 

‎src/secp256k1.c

+9-7
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,8 @@ const secp256k1_context *secp256k1_context_no_precomp = &secp256k1_context_no_pr
8686

8787
size_t secp256k1_context_preallocated_size(unsigned int flags) {
8888
size_t ret = ROUND_TO_ALIGN(sizeof(secp256k1_context));
89+
/* A return value of 0 is reserved as an indicator for errors when we call this function internally. */
90+
VERIFY_CHECK(ret != 0);
8991

9092
if (EXPECT((flags & SECP256K1_FLAGS_TYPE_MASK) != SECP256K1_FLAGS_TYPE_CONTEXT, 0)) {
9193
secp256k1_callback_call(&default_illegal_callback,
@@ -122,21 +124,21 @@ secp256k1_context* secp256k1_context_preallocated_create(void* prealloc, unsigne
122124
if (!secp256k1_selftest()) {
123125
secp256k1_callback_call(&default_error_callback, "self test failed");
124126
}
125-
VERIFY_CHECK(prealloc != NULL);
127+
126128
prealloc_size = secp256k1_context_preallocated_size(flags);
129+
if (prealloc_size == 0) {
130+
return NULL;
131+
}
132+
VERIFY_CHECK(prealloc != NULL);
127133
ret = (secp256k1_context*)manual_alloc(&prealloc, sizeof(secp256k1_context), base, prealloc_size);
128134
ret->illegal_callback = default_illegal_callback;
129135
ret->error_callback = default_error_callback;
130136

131-
if (EXPECT((flags & SECP256K1_FLAGS_TYPE_MASK) != SECP256K1_FLAGS_TYPE_CONTEXT, 0)) {
132-
secp256k1_callback_call(&ret->illegal_callback,
133-
"Invalid flags");
134-
return NULL;
135-
}
136-
137137
secp256k1_ecmult_context_init(&ret->ecmult_ctx);
138138
secp256k1_ecmult_gen_context_init(&ret->ecmult_gen_ctx);
139139

140+
/* Flags have been checked by secp256k1_context_preallocated_size. */
141+
VERIFY_CHECK((flags & SECP256K1_FLAGS_TYPE_MASK) == SECP256K1_FLAGS_TYPE_CONTEXT);
140142
if (flags & SECP256K1_FLAGS_BIT_CONTEXT_SIGN) {
141143
secp256k1_ecmult_gen_context_build(&ret->ecmult_gen_ctx, &prealloc);
142144
}

0 commit comments

Comments
 (0)
Please sign in to comment.