From 850d2d82c293e52cf0ef57e6cc762617fcc09979 Mon Sep 17 00:00:00 2001 From: Derick Rethans Date: Mon, 10 Oct 2022 16:47:13 +0100 Subject: [PATCH 1/5] Fixed crash with CATCH on PHP 8.2 with 32-bit --- branchinfo.c | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/branchinfo.c b/branchinfo.c index 3547c1b..bddd9ff 100644 --- a/branchinfo.c +++ b/branchinfo.c @@ -113,7 +113,11 @@ void vld_branch_post_process(zend_op_array *opa, vld_branch_info *branch_info) if (vld_set_in(branch_info->entry_points, i) && opa->opcodes[i].opcode == ZEND_CATCH) { #if PHP_VERSION_ID >= 70300 # if ZEND_USE_ABS_JMP_ADDR +# if PHP_VERSION_ID >= 80200 + if (opa->opcodes[i].op2.jmp_addr != -1) { +# else if (opa->opcodes[i].op2.jmp_addr != NULL) { +# endif # else if (opa->opcodes[i].op2.jmp_offset != 0) { # endif @@ -264,9 +268,9 @@ void vld_branch_info_dump(zend_op_array *opa, vld_branch_info *branch_info) for (i = 0; i < branch_info->starts->size; i++) { if (vld_set_in(branch_info->starts, i)) { fprintf( - VLD_G(path_dump_file), - "\t\"%s_%d\" [ label = \"{ op #%d-%d | line %d-%d }\" ];\n", - fname, i, i, + VLD_G(path_dump_file), + "\t\"%s_%d\" [ label = \"{ op #%d-%d | line %d-%d }\" ];\n", + fname, i, i, branch_info->branches[i].end_op, branch_info->branches[i].start_lineno, branch_info->branches[i].end_lineno -- 2.45.2 From 298cea2f3880cdc775fddbdb4fcb334e1f19bfc5 Mon Sep 17 00:00:00 2001 From: Derick Rethans Date: Fri, 16 Dec 2022 10:27:40 +0000 Subject: [PATCH 2/5] Fixed showing the JMP for the 'default' (or error) case in MATCH instructions --- srm_oparray.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/srm_oparray.c b/srm_oparray.c index 9fc75d4..54661c3 100644 --- a/srm_oparray.c +++ b/srm_oparray.c @@ -341,7 +341,7 @@ static const op_usage opcodes[] = { # if PHP_VERSION_ID >= 70400 /* 194 */ { "ARRAY_KEY_EXISTS", ALL_USED }, # if PHP_VERSION_ID >= 80000 - /* 195 */ { "MATCH", ALL_USED | OP2_JMP_ARRAY }, + /* 195 */ { "MATCH", ALL_USED | OP2_JMP_ARRAY | EXT_VAL_JMP_REL }, /* 196 */ { "CASE_STRICT", ALL_USED }, /* 197 */ { "MATCH_ERROR", ALL_USED }, /* 198 */ { "JMP_NULL", ALL_USED }, -- 2.45.2 From 7d25f1e5949935aa153b37d6bdaf19cf8079772a Mon Sep 17 00:00:00 2001 From: Derick Rethans Date: Tue, 28 May 2024 15:09:58 +0100 Subject: [PATCH 3/5] RECV uses OP2_OPNUM too --- srm_oparray.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/srm_oparray.c b/srm_oparray.c index 54661c3..1df6f06 100644 --- a/srm_oparray.c +++ b/srm_oparray.c @@ -145,7 +145,7 @@ static const op_usage opcodes[] = { /* 60 */ { "DO_FCALL", SPECIAL }, /* 61 */ { "INIT_FCALL", ALL_USED }, /* 62 */ { "RETURN", OP1_USED }, - /* 63 */ { "RECV", RES_USED | OP1_USED }, + /* 63 */ { "RECV", RES_USED | OP1_USED | OP2_OPNUM }, /* 64 */ { "RECV_INIT", ALL_USED }, /* 65 */ { "SEND_VAL", OP1_USED }, /* 66 */ { "SEND_VAR_EX", ALL_USED }, @@ -649,6 +649,9 @@ static unsigned int vld_get_special_flags(const zend_op *op, unsigned int base_a } #endif break; + case ZEND_RECV: + flags = OP1_USED|OP2_USED|OP2_OPNUM; + break; } return flags; } -- 2.45.2 From d7abb0c5ebda8277cda4be37a92d55e29ab5b503 Mon Sep 17 00:00:00 2001 From: Derick Rethans Date: Tue, 28 May 2024 15:11:24 +0100 Subject: [PATCH 4/5] PHP_CHECK_GCC_ARG is now AX_CHECK_COMPILE_FLAG --- config.m4 | 72 +++++++++++++++++++++++++++---------------------------- 1 file changed, 36 insertions(+), 36 deletions(-) diff --git a/config.m4 b/config.m4 index 54b914d..18cfa7d 100644 --- a/config.m4 +++ b/config.m4 @@ -20,42 +20,42 @@ if test "$PHP_VLD" != "no"; then CPPFLAGS=$old_CPPFLAGS if test "$PHP_VLD_DEV" = "yes"; then - PHP_CHECK_GCC_ARG(-Wbool-conversion, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wbool-conversion") - PHP_CHECK_GCC_ARG(-Wdeclaration-after-statement, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wdeclaration-after-statement") - PHP_CHECK_GCC_ARG(-Wdiscarded-qualifiers, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wdiscarded-qualifiers") - PHP_CHECK_GCC_ARG(-Wduplicate-enum, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wduplicate-enum") - PHP_CHECK_GCC_ARG(-Wempty-body, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wempty-body") - PHP_CHECK_GCC_ARG(-Wenum-compare, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wenum-compare") - PHP_CHECK_GCC_ARG(-Werror, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Werror") - PHP_CHECK_GCC_ARG(-Wextra, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wextra") - PHP_CHECK_GCC_ARG(-Wformat-nonliteral, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wformat-nonliteral") - PHP_CHECK_GCC_ARG(-Wformat-security, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wformat-security") - PHP_CHECK_GCC_ARG(-Wheader-guard, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wheader-guard") - PHP_CHECK_GCC_ARG(-Wincompatible-pointer-types-discards-qualifiers, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wincompatible-pointer-types-discards-qualifiers") - PHP_CHECK_GCC_ARG(-Wimplicit-fallthrough, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wimplicit-fallthrough") - PHP_CHECK_GCC_ARG(-Winit-self, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Winit-self") - PHP_CHECK_GCC_ARG(-Wlogical-not-parentheses, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wlogical-not-parentheses") - PHP_CHECK_GCC_ARG(-Wlogical-op, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wlogical-op") - PHP_CHECK_GCC_ARG(-Wlogical-op-parentheses, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wlogical-op-parentheses") - PHP_CHECK_GCC_ARG(-Wloop-analysis, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wloop-analysis") - PHP_CHECK_GCC_ARG(-Wmaybe-uninitialized, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wmaybe-uninitialized") - PHP_CHECK_GCC_ARG(-Wmissing-format-attribute, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wmissing-format-attribute") - PHP_CHECK_GCC_ARG(-Wno-missing-field-initializers, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wno-missing-field-initializers") - PHP_CHECK_GCC_ARG(-Wno-sign-compare, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wno-sign-compare") - PHP_CHECK_GCC_ARG(-Wno-unused-but-set-variable, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wno-unused-but-set-variable") - PHP_CHECK_GCC_ARG(-Wno-unused-parameter, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wno-unused-parameter") - PHP_CHECK_GCC_ARG(-Wno-variadic-macros, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wno-variadic-macros") - PHP_CHECK_GCC_ARG(-Wparentheses, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wparentheses") - PHP_CHECK_GCC_ARG(-Wpointer-bool-conversion, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wpointer-bool-conversion") - PHP_CHECK_GCC_ARG(-Wsizeof-array-argument, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wsizeof-array-argument") - PHP_CHECK_GCC_ARG(-Wstring-conversion, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wstring-conversion") - PHP_CHECK_GCC_ARG(-Wwrite-strings, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wwrite-strings") - PHP_CHECK_GCC_ARG(-fdiagnostics-show-option, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fdiagnostics-show-option") - PHP_CHECK_GCC_ARG(-fno-exceptions, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fno-exceptions") - PHP_CHECK_GCC_ARG(-fno-omit-frame-pointer, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fno-omit-frame-pointer") - PHP_CHECK_GCC_ARG(-fno-optimize-sibling-calls, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fno-optimize-sibling-calls") - PHP_CHECK_GCC_ARG(-fsanitize-address, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fsanitize-address") - PHP_CHECK_GCC_ARG(-fstack-protector, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fstack-protector") + AX_CHECK_COMPILE_FLAG(-Wbool-conversion, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wbool-conversion") + AX_CHECK_COMPILE_FLAG(-Wdeclaration-after-statement, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wdeclaration-after-statement") + AX_CHECK_COMPILE_FLAG(-Wdiscarded-qualifiers, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wdiscarded-qualifiers") + AX_CHECK_COMPILE_FLAG(-Wduplicate-enum, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wduplicate-enum") + AX_CHECK_COMPILE_FLAG(-Wempty-body, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wempty-body") + AX_CHECK_COMPILE_FLAG(-Wenum-compare, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wenum-compare") + AX_CHECK_COMPILE_FLAG(-Werror, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Werror") + AX_CHECK_COMPILE_FLAG(-Wextra, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wextra") + AX_CHECK_COMPILE_FLAG(-Wformat-nonliteral, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wformat-nonliteral") + AX_CHECK_COMPILE_FLAG(-Wformat-security, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wformat-security") + AX_CHECK_COMPILE_FLAG(-Wheader-guard, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wheader-guard") + AX_CHECK_COMPILE_FLAG(-Wincompatible-pointer-types-discards-qualifiers, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wincompatible-pointer-types-discards-qualifiers") + AX_CHECK_COMPILE_FLAG(-Wimplicit-fallthrough, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wimplicit-fallthrough") + AX_CHECK_COMPILE_FLAG(-Winit-self, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Winit-self") + AX_CHECK_COMPILE_FLAG(-Wlogical-not-parentheses, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wlogical-not-parentheses") + AX_CHECK_COMPILE_FLAG(-Wlogical-op, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wlogical-op") + AX_CHECK_COMPILE_FLAG(-Wlogical-op-parentheses, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wlogical-op-parentheses") + AX_CHECK_COMPILE_FLAG(-Wloop-analysis, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wloop-analysis") + AX_CHECK_COMPILE_FLAG(-Wmaybe-uninitialized, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wmaybe-uninitialized") + AX_CHECK_COMPILE_FLAG(-Wmissing-format-attribute, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wmissing-format-attribute") + AX_CHECK_COMPILE_FLAG(-Wno-missing-field-initializers, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wno-missing-field-initializers") + AX_CHECK_COMPILE_FLAG(-Wno-sign-compare, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wno-sign-compare") + AX_CHECK_COMPILE_FLAG(-Wno-unused-but-set-variable, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wno-unused-but-set-variable") + AX_CHECK_COMPILE_FLAG(-Wno-unused-parameter, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wno-unused-parameter") + AX_CHECK_COMPILE_FLAG(-Wno-variadic-macros, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wno-variadic-macros") + AX_CHECK_COMPILE_FLAG(-Wparentheses, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wparentheses") + AX_CHECK_COMPILE_FLAG(-Wpointer-bool-conversion, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wpointer-bool-conversion") + AX_CHECK_COMPILE_FLAG(-Wsizeof-array-argument, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wsizeof-array-argument") + AX_CHECK_COMPILE_FLAG(-Wstring-conversion, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wstring-conversion") + AX_CHECK_COMPILE_FLAG(-Wwrite-strings, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -Wwrite-strings") + AX_CHECK_COMPILE_FLAG(-fdiagnostics-show-option, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fdiagnostics-show-option") + AX_CHECK_COMPILE_FLAG(-fno-exceptions, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fno-exceptions") + AX_CHECK_COMPILE_FLAG(-fno-omit-frame-pointer, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fno-omit-frame-pointer") + AX_CHECK_COMPILE_FLAG(-fno-optimize-sibling-calls, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fno-optimize-sibling-calls") + AX_CHECK_COMPILE_FLAG(-fsanitize-address, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fsanitize-address") + AX_CHECK_COMPILE_FLAG(-fstack-protector, _MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS -fstack-protector") MAINTAINER_CFLAGS="$_MAINTAINER_CFLAGS" STD_CFLAGS="-g -O0 -Wall" -- 2.45.2 From df1c52c4cb62e5ff31e1b72e3f11df9a45ee567a Mon Sep 17 00:00:00 2001 From: Derick Rethans Date: Wed, 26 Jun 2024 16:58:42 +0100 Subject: [PATCH 5/5] Add support for PHP 8.4 opcodes ZEND_JMP_FRAMELESS and ZEND_FRAMELESS_ICALL_[0-3] --- srm_oparray.c | 29 +++++++++++++++++++++++++++++ srm_oparray.h | 2 ++ tests/jmp_frameless.inc | 6 ++++++ 3 files changed, 37 insertions(+) create mode 100644 tests/jmp_frameless.inc diff --git a/srm_oparray.c b/srm_oparray.c index 1df6f06..3bd6dce 100644 --- a/srm_oparray.c +++ b/srm_oparray.c @@ -350,6 +350,16 @@ static const op_usage opcodes[] = { /* 200 */ { "FETCH_GLOBALS", ALL_USED }, /* 201 */ { "VERIFY_NEVER_TYPE", ALL_USED }, /* 202 */ { "ZEND_CALLABLE_CONVERT", ALL_USED }, +# if PHP_VERSION_ID >= 80300 + /* 203 */ { "ZEND_BIND_INIT_STATIC_OR_JMP", ALL_USED }, +# if PHP_VERSION_ID >= 80400 + /* 204 */ { "ZEND_FRAMELESS_ICALL_0", ALL_USED | EXT_VAL_FLF }, + /* 205 */ { "ZEND_FRAMELESS_ICALL_1", ALL_USED | EXT_VAL_FLF }, + /* 206 */ { "ZEND_FRAMELESS_ICALL_2", ALL_USED | EXT_VAL_FLF }, + /* 207 */ { "ZEND_FRAMELESS_ICALL_3", ALL_USED | EXT_VAL_FLF }, + /* 208 */ { "ZEND_JMP_FRAMELESS", ALL_USED | EXT_CACHED_PTR | OP2_OPNUM }, +# endif +# endif # endif # endif # else @@ -814,6 +824,12 @@ void vld_dump_op(int nr, zend_op * op_ptr, unsigned int base_address, int notdea last_lineno = op.lineno; } +#if PHP_VERSION_ID >= 80400 + if (flags & EXT_VAL_FLF) { + fetch_type = (char*) ZEND_FLF_FUNC(&op)->common.function_name->val; + } +#endif + if (op.opcode >= NUM_KNOWN_OPCODES) { if (VLD_G(format)) { vld_printf(stderr, "%5d %s %c %c %c %c %s <%03d>%-23s %s %-14s ", nr, VLD_G(col_sep), notdead ? ' ' : '*', entry ? 'E' : ' ', start ? '>' : ' ', end ? '>' : ' ', VLD_G(col_sep), op.opcode, VLD_G(col_sep), fetch_type); @@ -834,6 +850,11 @@ void vld_dump_op(int nr, zend_op * op_ptr, unsigned int base_address, int notdea } } +#if PHP_VERSION_ID >= 80400 + if (flags & EXT_CACHED_PTR) { + vld_printf(stderr, "s%-3d ", op.extended_value); + } else +#endif if (flags & EXT_VAL) { #if PHP_VERSION_ID >= 70300 if (op.opcode == ZEND_CATCH) { @@ -1085,6 +1106,14 @@ int vld_find_jumps(zend_op_array *opa, unsigned int position, size_t *jump_count *jump_count = 1; return 1; +#if PHP_VERSION_ID >= 80400 + } else if (opcode.opcode == ZEND_JMP_FRAMELESS) { + jumps[0] = VLD_ZNODE_JMP_LINE(opcode.op2, position, base_address); + jumps[1] = position + 1; + *jump_count = 2; + return 1; +#endif + } else if ( opcode.opcode == ZEND_GENERATOR_RETURN || opcode.opcode == ZEND_EXIT || diff --git a/srm_oparray.h b/srm_oparray.h index 7cc0803..ee65c25 100644 --- a/srm_oparray.h +++ b/srm_oparray.h @@ -57,6 +57,8 @@ #define EXT_VAL_JMP_ABS 1<<25 #define VLD_IS_JMP_ARRAY 1<<26 #define VLD_IS_INDEX 1<<27 +#define EXT_VAL_FLF 1<<28 +#define EXT_CACHED_PTR 1<<29 typedef struct _op_usage { const char *name; diff --git a/tests/jmp_frameless.inc b/tests/jmp_frameless.inc new file mode 100644 index 0000000..f693565 --- /dev/null +++ b/tests/jmp_frameless.inc @@ -0,0 +1,6 @@ +