Skip to content

PHP crashes with a use-after-free in -e mode on certain scripts #21504

@derickr

Description

@derickr

Description

The following code:

<?php

function test($t) {
    echo $t.PHP_EOL;
}

'1234' |> test(...);

When run with:

USE_ZEND_ALLOC=0 valgrind php -n -e test.php

This was reported to me in https://bugs.xdebug.org/view.php?id=2402, but it's not a bug in Xdebug, as:

  • The -n turns off all extensions, including Xdebug, so it's not active.
  • The -e turns on "extended instructions", which Xdebug does turn on so that it can do step debugging, however, it's also turn-on-able for other reasons.

Resulted in this output:

==3562624== Invalid read of size 4
==3562624==    at 0x4C40F1E: zend_gc_delref (zend_types.h:1383)
==3562624==    by 0x4C40FF9: zval_delref_p (zend_types.h:1419)
==3562624==    by 0x4C41557: zval_ptr_dtor_nogc (zend_variables.h:35)
==3562624==    by 0x4C4647E: zend_ast_destroy (zend_ast.c:1381)
==3562624==    by 0x4C464D6: zend_ast_destroy (zend_ast.c:1388)
==3562624==    by 0x4D74A52: zend_compile (zend_language_scanner.l:634)
==3562624==    by 0x4D74B2D: compile_file (zend_language_scanner.l:662)
==3562624==    by 0x4880BE5: phar_compile_file (phar.c:3305)
==3562624==    by 0x4DCD268: zend_execute_script (zend.c:1970)
==3562624==    by 0x4B80238: php_execute_script_ex (main.c:2641)
==3562624==    by 0x4B80369: php_execute_script (main.c:2681)
==3562624==    by 0x4DCF8C8: do_cli (php_cli.c:951)
==3562624==    by 0x4DD0836: main (php_cli.c:1362)
==3562624==  Address 0xc1a5a30 is 0 bytes inside a block of size 32 free'd
==3562624==    at 0x41E587F: free (vg_replace_malloc.c:989)
==3562624==    by 0x4C2D9D0: __zend_free (zend_alloc.c:3571)
==3562624==    by 0x4C2BC76: _efree (zend_alloc.c:2790)
==3562624==    by 0x4DBB52E: zend_string_release (zend_string.h:339)
==3562624==    by 0x4DBBFAA: zend_new_interned_string_request (zend_string.c:246)
==3562624==    by 0x4C6488B: zval_make_interned_string (zend_compile.c:566)
==3562624==    by 0x4C64906: zend_insert_literal (zend_compile.c:578)
==3562624==    by 0x4C64A0B: zend_add_literal (zend_compile.c:599)
==3562624==    by 0x4C69116: zend_emit_op (zend_compile.c:2291)
==3562624==    by 0x4C6CDEA: zend_compile_args (zend_compile.c:3897)
==3562624==    by 0x4C6D0C1: zend_compile_call_common (zend_compile.c:3972)
==3562624==    by 0x4C70C0E: zend_compile_call (zend_compile.c:5232)
==3562624==    by 0x4C8429B: zend_compile_var_inner (zend_compile.c:11980)
==3562624==    by 0x4C843B3: zend_compile_var (zend_compile.c:12011)
==3562624==    by 0x4C83D69: zend_compile_expr_inner (zend_compile.c:11830)
==3562624==    by 0x4C840D3: zend_compile_expr (zend_compile.c:11949)
==3562624==    by 0x4C7414B: zend_compile_pipe (zend_compile.c:6543)
==3562624==    by 0x4C8407A: zend_compile_expr_inner (zend_compile.c:11936)
==3562624==    by 0x4C840D3: zend_compile_expr (zend_compile.c:11949)
==3562624==    by 0x4C838EB: zend_compile_stmt (zend_compile.c:11791)
==3562624==    by 0x4C833C8: zend_compile_top_stmt (zend_compile.c:11675)
==3562624==    by 0x4C83329: zend_compile_top_stmt (zend_compile.c:11661)
==3562624==    by 0x4D749D9: zend_compile (zend_language_scanner.l:622)
==3562624==    by 0x4D74B2D: compile_file (zend_language_scanner.l:662)
==3562624==    by 0x4880BE5: phar_compile_file (phar.c:3305)
==3562624==    by 0x4DCD268: zend_execute_script (zend.c:1970)
==3562624==    by 0x4B80238: php_execute_script_ex (main.c:2641)
==3562624==    by 0x4B80369: php_execute_script (main.c:2681)
==3562624==    by 0x4DCF8C8: do_cli (php_cli.c:951)
==3562624==    by 0x4DD0836: main (php_cli.c:1362)
==3562624==  Block was alloc'd at
==3562624==    at 0x41E2818: malloc (vg_replace_malloc.c:446)
==3562624==    by 0x4C2D89E: __zend_malloc (zend_alloc.c:3543)
==3562624==    by 0x4C2BBF0: _emalloc (zend_alloc.c:2780)
==3562624==    by 0x4D72DB7: zend_string_alloc (zend_string.h:167)
==3562624==    by 0x4D72E2A: zend_string_init (zend_string.h:189)
==3562624==    by 0x4D77565: lex_scan (zend_language_scanner.l:2573)
==3562624==    by 0x4C68669: zendlex (zend_compile.c:2038)
==3562624==    by 0x4D69799: zendparse (zend_language_parser.c:5588)
==3562624==    by 0x4D74909: zend_compile (zend_language_scanner.l:603)
==3562624==    by 0x4D74B2D: compile_file (zend_language_scanner.l:662)
==3562624==    by 0x4880BE5: phar_compile_file (phar.c:3305)
==3562624==    by 0x4DCD268: zend_execute_script (zend.c:1970)
==3562624==    by 0x4B80238: php_execute_script_ex (main.c:2641)
==3562624==    by 0x4B80369: php_execute_script (main.c:2681)
==3562624==    by 0x4DCF8C8: do_cli (php_cli.c:951)
==3562624==    by 0x4DD0836: main (php_cli.c:1362)
==3562624== 
php: /home/derick/dev/php/php-src.git/Zend/zend_types.h:1383: zend_gc_delref: Assertion `p->refcount > 0' failed.
==3562624== 
==3562624== Process terminating with default action of signal 6 (SIGABRT)
==3562624==    at 0x81453BC: __pthread_kill_implementation (pthread_kill.c:44)
==3562624==    by 0x80EE941: raise (raise.c:26)
==3562624==    by 0x80D64AB: abort (abort.c:77)
==3562624==    by 0x80D641F: __assert_fail_base.cold (assert.c:118)
==3562624==    by 0x4C40F48: zend_gc_delref (zend_types.h:1383)
==3562624==    by 0x4C40FF9: zval_delref_p (zend_types.h:1419)
==3562624==    by 0x4C41557: zval_ptr_dtor_nogc (zend_variables.h:35)
==3562624==    by 0x4C4647E: zend_ast_destroy (zend_ast.c:1381)
==3562624==    by 0x4C464D6: zend_ast_destroy (zend_ast.c:1388)
==3562624==    by 0x4D74A52: zend_compile (zend_language_scanner.l:634)
==3562624==    by 0x4D74B2D: compile_file (zend_language_scanner.l:662)
==3562624==    by 0x4880BE5: phar_compile_file (phar.c:3305)
==3562624==    by 0x4DCD268: zend_execute_script (zend.c:1970)
==3562624==    by 0x4B80238: php_execute_script_ex (main.c:2641)
==3562624==    by 0x4B80369: php_execute_script (main.c:2681)
==3562624==    by 0x4DCF8C8: do_cli (php_cli.c:951)
==3562624==    by 0x4DD0836: main (php_cli.c:1362)
==3562624== 
==3562624== HEAP SUMMARY:
==3562624==     in use at exit: 5,218,545 bytes in 36,018 blocks
==3562624==   total heap usage: 41,131 allocs, 5,113 frees, 6,514,971 bytes allocated

But I expected this output instead:

1234

PHP Version

PHP 8.5.5-dev (cli) (built: Mar 23 2026 00:44:22) (NTS DEBUG)
Copyright (c) The PHP Group
Zend Engine v4.5.5-dev, Copyright (c) Zend Technologies
    with Zend OPcache v8.5.5-dev, Copyright (c), by Zend Technologies

Operating System

Debian forky/sid

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions