Skip to content

ext/gmp: Fix crash in gmp_pow with excessively large exponent#22352

Open
arshidkv12 wants to merge 3 commits into
php:masterfrom
arshidkv12:gmp-5
Open

ext/gmp: Fix crash in gmp_pow with excessively large exponent#22352
arshidkv12 wants to merge 3 commits into
php:masterfrom
arshidkv12:gmp-5

Conversation

@arshidkv12

Copy link
Copy Markdown
Contributor

@iliaal

iliaal commented Jun 17, 2026

Copy link
Copy Markdown
Contributor

Two concerns before this lands.

The 1000000 cap is arbitrary and rejects computable inputs, e.g. gmp_pow(2, 2000000) is a ~250 KB integer this now throws on. A fixed exponent limit was added once before and reverted as too restrictive (GH-16870, #16973), so a magic constant will likely draw the same objection.

It also caps only the exponent, not the result size. The GMP abort is driven by exp * bitlen(base), so a large enough base still reaches __gmp_exception under this cap, e.g. gmp_pow(gmp_init(str_repeat('9', 200000)), 1000000). Bounding against the projected size (exp * mpz_sizeinbase(base, 2) versus GMP's limit) would cover both cases and drop the magic number.

@arshidkv12

arshidkv12 commented Jun 18, 2026

Copy link
Copy Markdown
Contributor Author

The GMP abort is driven by exp * bitlen(base), so a large enough base still reaches __gmp_exception under this cap, e.g. gmp_pow(gmp_init(str_repeat('9', 200000)), 1000000). Bounding against the projected size (exp * mpz_sizeinbase(base, 2) versus GMP's limit) would cover both cases and drop the magic number.

Thank you. Good points — agreed, the 1,000,000 cap is arbitrary and can reject valid cases like gmp_pow(2, 2000000).

I think the issue is caused by this calculation: mpz/n_pow_ui.c:371

ralloc = (bsize * GMP_NUMB_BITS - cnt + GMP_NAIL_BITS) * e / GMP_NUMB_BITS + 5;

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.

2 participants