diff --git a/Zend/tests/stack_limit/stack_limit_001.phpt b/Zend/tests/stack_limit/stack_limit_001.phpt index ca185635c39c8..a24bf47eb4e11 100644 --- a/Zend/tests/stack_limit/stack_limit_001.phpt +++ b/Zend/tests/stack_limit/stack_limit_001.phpt @@ -3,7 +3,6 @@ Stack limit 001 - Stack limit checks with max_allowed_stack_size detection --SKIPIF-- --EXTENSIONS-- zend_test diff --git a/Zend/tests/stack_limit/stack_limit_002.phpt b/Zend/tests/stack_limit/stack_limit_002.phpt index 309de9bf6a2a3..f4fa6ae521714 100644 --- a/Zend/tests/stack_limit/stack_limit_002.phpt +++ b/Zend/tests/stack_limit/stack_limit_002.phpt @@ -3,7 +3,6 @@ Stack limit 002 - Stack limit checks with max_allowed_stack_size detection (fibe --SKIPIF-- --EXTENSIONS-- zend_test diff --git a/Zend/tests/stack_limit/stack_limit_003.phpt b/Zend/tests/stack_limit/stack_limit_003.phpt index 9eb94a971636f..4dd0851f1d6f1 100644 --- a/Zend/tests/stack_limit/stack_limit_003.phpt +++ b/Zend/tests/stack_limit/stack_limit_003.phpt @@ -7,7 +7,7 @@ if (!function_exists('zend_test_zend_call_stack_get')) die("skip zend_test_zend_ --EXTENSIONS-- zend_test --INI-- -zend.max_allowed_stack_size=128K +zend.max_allowed_stack_size=512K --FILE-- start(); $depth1 = $fiber->getReturn(); -ini_set('fiber.stack_size', '200K'); +ini_set('fiber.stack_size', '512K'); $fiber = new Fiber($callback); $fiber->start(); $depth2 = $fiber->getReturn(); diff --git a/Zend/tests/stack_limit/stack_limit_006.phpt b/Zend/tests/stack_limit/stack_limit_006.phpt index 0b51fabb4babd..725372059c22b 100644 --- a/Zend/tests/stack_limit/stack_limit_006.phpt +++ b/Zend/tests/stack_limit/stack_limit_006.phpt @@ -3,7 +3,6 @@ Stack limit 006 - env size affects __libc_stack_end --SKIPIF-- --EXTENSIONS-- zend_test diff --git a/Zend/tests/stack_limit/stack_limit_007.phpt b/Zend/tests/stack_limit/stack_limit_007.phpt index 411af1d2c6894..cb2953f6ac37e 100644 --- a/Zend/tests/stack_limit/stack_limit_007.phpt +++ b/Zend/tests/stack_limit/stack_limit_007.phpt @@ -7,7 +7,7 @@ if (!function_exists('zend_test_zend_call_stack_get')) die("skip zend_test_zend_ --EXTENSIONS-- zend_test --INI-- -zend.max_allowed_stack_size=128K +zend.max_allowed_stack_size=512K --FILE-- --EXTENSIONS-- zend_test diff --git a/Zend/tests/stack_limit/stack_limit_011.phpt b/Zend/tests/stack_limit/stack_limit_011.phpt index 6155525675c32..c9345bb13d5a0 100644 --- a/Zend/tests/stack_limit/stack_limit_011.phpt +++ b/Zend/tests/stack_limit/stack_limit_011.phpt @@ -7,24 +7,27 @@ if (!function_exists('zend_test_zend_call_stack_get')) die("skip zend_test_zend_ --EXTENSIONS-- zend_test --INI-- -zend.max_allowed_stack_size=128K +zend.max_allowed_stack_size=512K --FILE-- +--EXTENSIONS-- +zend_test +--INI-- +; The test may use a large amount of memory on systems with a large stack limit +memory_limit=1G +--FILE-- +getMessage(), "\n"; +} + +?> +--EXPECTF-- +%S%rMaximum call stack size of [0-9]+ bytes reached|Allowed memory size of [0-9]+ bytes exhausted%r%s diff --git a/Zend/zend.c b/Zend/zend.c index ee3f5272c9640..f4ef074e167eb 100644 --- a/Zend/zend.c +++ b/Zend/zend.c @@ -206,6 +206,12 @@ static ZEND_INI_MH(OnUpdateReservedStackSize) /* {{{ */ zend_ulong min = 32*1024; #endif +#if defined(__SANITIZE_ADDRESS__) || __has_feature(memory_sanitizer) + /* AddressSanitizer and MemorySanitizer use more stack due to + * instrumentation */ + min *= 10; +#endif + if (size == 0) { size = min; } else if (size < min) { diff --git a/Zend/zend_compile.c b/Zend/zend_compile.c index 68cd9403f1efb..ca83f9b22ae3b 100644 --- a/Zend/zend_compile.c +++ b/Zend/zend_compile.c @@ -102,9 +102,14 @@ static void zend_compile_assign(znode *result, zend_ast *ast); #ifdef ZEND_CHECK_STACK_LIMIT zend_never_inline static void zend_stack_limit_error(void) { + size_t max_stack_size = 0; + if ((uintptr_t) EG(stack_base) > (uintptr_t) EG(stack_limit)) { + max_stack_size = (size_t) ((uintptr_t) EG(stack_base) - (uintptr_t) EG(stack_limit)); + } + zend_error_noreturn(E_COMPILE_ERROR, "Maximum call stack size of %zu bytes reached during compilation. Try splitting expression", - (size_t) ((uintptr_t) EG(stack_base) - (uintptr_t) EG(stack_limit))); + max_stack_size); } static void zend_check_stack_limit(void) diff --git a/Zend/zend_execute.c b/Zend/zend_execute.c index 29631504d5f90..8a2731fb3a497 100644 --- a/Zend/zend_execute.c +++ b/Zend/zend_execute.c @@ -2308,8 +2308,13 @@ static zend_never_inline ZEND_COLD void ZEND_FASTCALL zend_use_new_element_for_s #ifdef ZEND_CHECK_STACK_LIMIT static zend_never_inline ZEND_COLD void ZEND_FASTCALL zend_call_stack_size_error(void) { - zend_throw_error(NULL, "Maximum call stack size of %zu bytes reached. Infinite recursion?", - (size_t) ((uintptr_t) EG(stack_base) - (uintptr_t) EG(stack_limit))); + size_t max_stack_size = 0; + if ((uintptr_t) EG(stack_base) > (uintptr_t) EG(stack_limit)) { + max_stack_size = (size_t) ((uintptr_t) EG(stack_base) - (uintptr_t) EG(stack_limit)); + } + zend_throw_error(NULL, + "Maximum call stack size of %zu bytes reached. Infinite recursion?", + max_stack_size); } #endif /* ZEND_CHECK_STACK_LIMIT */