1
0
mirror of https://github.com/php/php-src.git synced 2026-03-24 00:02:20 +01:00

Expose the source of exit points in zend_jit_dump_exit_info()

This adds a new flag: ZEND_JIT_DEBUG_TRACE_EXIT_INFO_SRC. When the flag is set,
zend_jit_dump_exit_info() exposes the source of exit points, in debug builds.

Closes GH-19700
This commit is contained in:
Arnaud Le Blanc
2025-09-04 12:04:50 +02:00
parent 5b8a5320df
commit 0d4ff662e6
5 changed files with 43 additions and 12 deletions

View File

@@ -59,6 +59,11 @@ PHP 8.6 UPGRADE NOTES
11. Changes to INI File Handling
========================================
- Opcache:
. opcache.jit_debug accepts a new flag: ZEND_JIT_DEBUG_TRACE_EXIT_INFO_SRC.
When used along with ZEND_JIT_DEBUG_TRACE_EXIT_INFO, the source of exit
points is printed in exit info output, in debug builds.
========================================
12. Windows Support
========================================

View File

@@ -106,7 +106,8 @@ static ZEND_OPCODE_HANDLER_RET ZEND_OPCODE_HANDLER_FUNC_CCONV zend_runtime_jit(Z
static int zend_jit_trace_op_len(const zend_op *opline);
static int zend_jit_trace_may_exit(const zend_op_array *op_array, const zend_op *opline);
static uint32_t zend_jit_trace_get_exit_point(const zend_op *to_opline, uint32_t flags);
static uint32_t _zend_jit_trace_get_exit_point(const zend_op *to_opline, uint32_t flags ZEND_FILE_LINE_DC);
#define zend_jit_trace_get_exit_point(to_opline, flags) _zend_jit_trace_get_exit_point(to_opline, flags ZEND_FILE_LINE_CC)
static const void *zend_jit_trace_get_exit_addr(uint32_t n);
static void zend_jit_trace_add_code(const void *start, uint32_t size);
static zend_string *zend_jit_func_name(const zend_op_array *op_array);

View File

@@ -64,15 +64,16 @@
#define ZEND_JIT_DEBUG_SIZE (1<<9)
#define ZEND_JIT_DEBUG_ASM_ADDR (1<<10)
#define ZEND_JIT_DEBUG_TRACE_START (1<<12)
#define ZEND_JIT_DEBUG_TRACE_STOP (1<<13)
#define ZEND_JIT_DEBUG_TRACE_COMPILED (1<<14)
#define ZEND_JIT_DEBUG_TRACE_EXIT (1<<15)
#define ZEND_JIT_DEBUG_TRACE_ABORT (1<<16)
#define ZEND_JIT_DEBUG_TRACE_BLACKLIST (1<<17)
#define ZEND_JIT_DEBUG_TRACE_BYTECODE (1<<18)
#define ZEND_JIT_DEBUG_TRACE_TSSA (1<<19)
#define ZEND_JIT_DEBUG_TRACE_EXIT_INFO (1<<20)
#define ZEND_JIT_DEBUG_TRACE_START (1<<12)
#define ZEND_JIT_DEBUG_TRACE_STOP (1<<13)
#define ZEND_JIT_DEBUG_TRACE_COMPILED (1<<14)
#define ZEND_JIT_DEBUG_TRACE_EXIT (1<<15)
#define ZEND_JIT_DEBUG_TRACE_ABORT (1<<16)
#define ZEND_JIT_DEBUG_TRACE_BLACKLIST (1<<17)
#define ZEND_JIT_DEBUG_TRACE_BYTECODE (1<<18)
#define ZEND_JIT_DEBUG_TRACE_TSSA (1<<19)
#define ZEND_JIT_DEBUG_TRACE_EXIT_INFO (1<<20)
#define ZEND_JIT_DEBUG_TRACE_EXIT_INFO_SRC (1<<21)
#define ZEND_JIT_DEBUG_IR_SRC (1<<24)
#define ZEND_JIT_DEBUG_IR_FINAL (1<<25)

View File

@@ -456,6 +456,10 @@ typedef struct _zend_jit_trace_exit_info {
uint32_t stack_offset;
zend_jit_ref_snapshot poly_func;
zend_jit_ref_snapshot poly_this;
#if ZEND_DEBUG
const char *filename;
int lineno;
#endif
} zend_jit_trace_exit_info;
typedef struct _zend_jit_trace_stack {

View File

@@ -132,7 +132,7 @@ static uint32_t zend_jit_exit_point_by_addr(const void *addr)
return (uint32_t)-1;
}
static uint32_t zend_jit_trace_get_exit_point(const zend_op *to_opline, uint32_t flags)
static uint32_t _zend_jit_trace_get_exit_point(const zend_op *to_opline, uint32_t flags ZEND_FILE_LINE_DC)
{
zend_jit_trace_info *t = &zend_jit_traces[ZEND_JIT_TRACE_NUM];
uint32_t exit_point;
@@ -178,7 +178,13 @@ static uint32_t zend_jit_trace_get_exit_point(const zend_op *to_opline, uint32_t
&& memcmp(t->stack_map + t->exit_info[i].stack_offset, stack, stack_size * sizeof(zend_jit_trace_stack)) == 0)) {
if (t->exit_info[i].opline == to_opline
&& t->exit_info[i].flags == flags
&& t->exit_info[i].stack_size == stack_size) {
&& t->exit_info[i].stack_size == stack_size
#if ZEND_DEBUG
&& (((JIT_G(debug) & ZEND_JIT_DEBUG_TRACE_EXIT_INFO_SRC) == 0)
|| (strcmp(t->exit_info[i].filename, __zend_filename) == 0
&& t->exit_info[i].lineno == __zend_lineno))
#endif
) {
return i;
}
}
@@ -202,6 +208,15 @@ static uint32_t zend_jit_trace_get_exit_point(const zend_op *to_opline, uint32_t
t->exit_info[exit_point].stack_offset = stack_offset;
t->exit_info[exit_point].poly_func = (zend_jit_ref_snapshot){.reg = ZREG_NONE};
t->exit_info[exit_point].poly_this = (zend_jit_ref_snapshot){.reg = ZREG_NONE};
#if ZEND_DEBUG
if ((JIT_G(debug) & ZEND_JIT_DEBUG_TRACE_EXIT_INFO_SRC) != 0) {
t->exit_info[exit_point].filename = __zend_filename;
t->exit_info[exit_point].lineno = __zend_lineno;
} else {
t->exit_info[exit_point].filename = NULL;
t->exit_info[exit_point].lineno = 0;
}
#endif
}
return exit_point;
@@ -8096,6 +8111,11 @@ static void zend_jit_dump_exit_info(zend_jit_trace_info *t)
fprintf(stderr, ":unknown(zval_copy(%s))", zend_reg_name(STACK_REG(stack, j)));
}
}
#if ZEND_DEBUG
if ((JIT_G(debug) & ZEND_JIT_DEBUG_TRACE_EXIT_INFO_SRC) != 0) {
fprintf(stderr, " %s:%d", t->exit_info[i].filename, t->exit_info[i].lineno);
}
#endif
fprintf(stderr, "\n");
}
}