Skip to content

Fix buffer overflow in hash_pbkdf2() with a large output length - #23380

Open
lazerg wants to merge 1 commit into
php:PHP-8.4from
lazerg:fix/issue-23377-pbkdf2-length-overflow
Open

Fix buffer overflow in hash_pbkdf2() with a large output length#23380
lazerg wants to merge 1 commit into
php:PHP-8.4from
lazerg:fix/issue-23377-pbkdf2-length-overflow

Conversation

@lazerg

@lazerg lazerg commented Aug 19, 2026

Copy link
Copy Markdown
Contributor

hash_pbkdf2() sizes the digest buffer with ceil((float) length / 2.0) and the block count with ceil((float) digest_length / (float) ops->digest_size). A float carries 24 bits of mantissa, so past 2^24 the conversion rounds and both counts come out wrong: rounding up makes zend_bin2hex() write past the end of the return string, rounding down leaves the tail of the string uninitialized. hash_pbkdf2('md5', 'password', 'salt', 1, 268435473) writes 8 bytes out of bounds under ASAN.

Both counts are exact in integer arithmetic, so this replaces them with round-up divisions. <math.h> had no other user in the file.

This came out of #23377. The odd length case reported there is fine on its own, as Sjord noted before closing it: zend_string_alloc(length) reserves length + 1 bytes and 2 * ceil(length / 2) == length + 1, so the extra hexit lands on the terminator byte that gets overwritten a line later. The float conversion on those same two lines is a real overflow though.

@lazerg
lazerg force-pushed the fix/issue-23377-pbkdf2-length-overflow branch from 514c90e to 95e52bd Compare August 19, 2026 13:00
@lazerg lazerg changed the title Fix GH-23377: Buffer overflow in hash_pbkdf2() with a large output length Fix buffer overflow in hash_pbkdf2() with a large output length Aug 19, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant