fix: verify() resource leaks and dead cleanup code (OpenSSL 3.x)#81
Conversation
timlegge
left a comment
There was a problem hiding this comment.
I would probably try to avoid the switch code duplication.
I have also give thought to re-enabling the oaep. The last time I tested it I think the newer openssl versions seem to protect against the martian attach now. I would wonder whether the changes might affect that
|
@Koan-Bot rebase |
Rebase: fix: verify() resource leaks and dead cleanup code (OpenSSL 3.x)Branch Diff: 1 file changed, 30 insertions(+), 19 deletions(-) Review feedback was analyzed and applied. Actions
Automated by Kōan |
83c386f to
e9d7ab4
Compare
|
@timlegge ready for a second round of review |
| } | ||
|
|
||
| CHECK_OPEN_SSL(digest = get_message_digest(text_SV, p_rsa->hashMode)); | ||
| { |
There was a problem hiding this comment.
Why is the { here? where is the matching one and why is it needed?
There was a problem hiding this comment.
The { opens a block scope (matching } is at line 1112, replacing the old #if/EVP_MD_free/EVP_PKEY_CTX_free/#endif block).
It's needed for C89 compatibility: verify_result must be declared at the top of a block since it's used by both the OpenSSL 3.x and pre-3.x code paths — it has to be declared before the #if/#else fork so the shared switch(verify_result) after #endif can see it.
Without this block, we'd need to either:
- Use
PREINIT:for all declarations (buterror,ctx,mdare only meaningful in the 3.x path — pollutingPREINIT:with them feels wrong) - Declare
verify_resultinPREINIT:and drop the block — that would work too, and would be simpler
Happy to go with option 2 if you prefer — move int verify_result; to PREINIT: and remove the {/} wrapper entirely.
There was a problem hiding this comment.
Declare verify_result in PREINIT:
|
@timlegge — Regarding your review comment about re-enabling OAEP and the Marvin attack: The switch duplication is fixed in the rebase (see inline reply). As for the PKCS#1 v1.5 / Marvin attack question — that's addressed separately in PR #92. The key insight: the Marvin attack (CVE-2024-2467) only affects PKCS#1 v1.5 decryption (the padding oracle in RSA_private_decrypt). It does NOT affect signatures — RSA_sign()/RSA_verify() with PKCS#1 v1.5 are not vulnerable because signatures don't involve padding-dependent branching on secret data. PR #92 re-enables PKCS#1 v1.5 for sign/verify while keeping it disabled for encrypt/decrypt (where the Marvin attack is relevant). That's orthogonal to this PR, which is purely about resource cleanup. Re: modern OpenSSL protecting against Marvin on the decryption side — OpenSSL 3.2+ added implicit Marvin mitigation ( |
|
The PR to re-enable will need some testing against the Marvin tool kit to be sure. |
Rebase: fix: verify() resource leaks and dead cleanup code (OpenSSL 3.x)Branch Diff: 1 file changed, 30 insertions(+), 19 deletions(-) Review feedback was analyzed and applied. Actions
Automated by Kōan |
e9d7ab4 to
0c95b9a
Compare
|
@Koan-Bot rebase |
|
❌ Permission denied. Only users with write access can trigger bot commands. |
|
@atoomic this looks fine but does need it be rebased |
|
@Koan-Bot rebase |
|
@timlegge I've added you to the list of authorized users, just need a reboot ( in a few min ) before it takes action |
… 3.x) Two issues in the OpenSSL 3.x verify path: 1. Error-path leaks: CHECK_OPEN_SSL during setup croaks immediately, leaking the EVP_PKEY_CTX and EVP_MD objects. 2. Dead cleanup code: EVP_MD_free and EVP_PKEY_CTX_free after the switch block were unreachable because XSRETURN_NO/XSRETURN_YES are longjmps that skip all subsequent code. Fix: use THROW/goto err pattern for setup errors, and free resources before the switch statement on the success path. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
0c95b9a to
e69c9b0
Compare
Rebase: fix: verify() resource leaks and dead cleanup code (OpenSSL 3.x)Branch Diff: 1 file changed, 28 insertions(+), 31 deletions(-) Review feedback was analyzed and applied. Actions
Automated by Kōan |
| } | ||
|
|
||
| CHECK_OPEN_SSL(digest = get_message_digest(text_SV, p_rsa->hashMode)); | ||
| { |
There was a problem hiding this comment.
Declare verify_result in PREINIT:
|
@atoomic let's merge and see if any of the other PRs need to be rebased |
Summary
Two issues in the OpenSSL 3.x verify path:
Error-path leaks: If any
CHECK_OPEN_SSLfires duringEVP_PKEY_CTXorEVP_MDsetup, both objects leak becausecroak()is called immediatelyDead cleanup code:
EVP_MD_free(md)andEVP_PKEY_CTX_free(ctx)placed after the switch statement are unreachable —XSRETURN_NOandXSRETURN_YESare longjmps that skip all subsequent codeFix
CHECK_OPEN_SSLwithTHROW()/goto errpattern for proper cleanup during setupEVP_MD_free,EVP_PKEY_CTX_free) to before theswitch(verify_result)statement, so resources are freed regardless of whichXSRETURN_*path is takenTest plan
🤖 Generated with Claude Code