From 7f4ed7e121fa4bbc10773f5c9682644e3ad9a692 Mon Sep 17 00:00:00 2001 From: Weilin Du Date: Mon, 21 Sep 2026 20:19:22 +0800 Subject: [PATCH 1/2] Reuse zend_bin2hex in random, SOAP, LDAP and syslog --- ext/ldap/ldap.c | 5 ++--- ext/random/random.c | 16 ++++++---------- ext/soap/php_encoding.c | 4 ++-- main/php_syslog.c | 7 +++---- 4 files changed, 13 insertions(+), 19 deletions(-) diff --git a/ext/ldap/ldap.c b/ext/ldap/ldap.c index 3e03df4c3375..35512d9061ba 100644 --- a/ext/ldap/ldap.c +++ b/ext/ldap/ldap.c @@ -3884,7 +3884,6 @@ PHP_FUNCTION(ldap_set_rebind_proc) static zend_string* php_ldap_do_escape(const bool *map, const char *value, size_t valuelen, zend_long flags) { - char hex[] = "0123456789abcdef"; size_t i, p = 0; size_t len = 0; zend_string *ret; @@ -3917,8 +3916,8 @@ static zend_string* php_ldap_do_escape(const bool *map, const char *value, size_ if (map[v] || ((flags & PHP_LDAP_ESCAPE_DN) && ((i == 0) || (i + 1 == valuelen)) && (v == ' '))) { ZSTR_VAL(ret)[p++] = '\\'; - ZSTR_VAL(ret)[p++] = hex[v >> 4]; - ZSTR_VAL(ret)[p++] = hex[v & 0x0f]; + zend_bin2hex(ZSTR_VAL(ret) + p, &v, 1); + p += 2; } else { ZSTR_VAL(ret)[p++] = v; } diff --git a/ext/random/random.c b/ext/random/random.c index fe4176418e41..f423a10f9a7b 100644 --- a/ext/random/random.c +++ b/ext/random/random.c @@ -315,32 +315,28 @@ PHPAPI void *php_random_default_status(void) } /* }}} */ -/* this is read-only, so it's ok */ -ZEND_SET_ALIGNED(16, static const char hexconvtab[]) = "0123456789abcdef"; - /* {{{ php_random_bin2hex_le */ -/* stolen from standard/string.c */ PHPAPI zend_string *php_random_bin2hex_le(const void *ptr, const size_t len) { +#ifdef WORDS_BIGENDIAN zend_string *str; size_t i; str = zend_string_safe_alloc(len, 2 * sizeof(char), 0, 0); i = 0; -#ifdef WORDS_BIGENDIAN /* force little endian */ for (size_t h = len; 0 < h; h--) { size_t j = h-1; -#else - for (size_t j = 0; j < len; j++) { -#endif - ZSTR_VAL(str)[i++] = hexconvtab[((unsigned char *) ptr)[j] >> 4]; - ZSTR_VAL(str)[i++] = hexconvtab[((unsigned char *) ptr)[j] & 15]; + zend_bin2hex(ZSTR_VAL(str) + i, (const unsigned char *) ptr + j, 1); + i += 2; } ZSTR_VAL(str)[i] = '\0'; return str; +#else + return zend_bin2hex_str(ptr, len); +#endif } /* }}} */ diff --git a/ext/soap/php_encoding.c b/ext/soap/php_encoding.c index 044d2058ec09..7ae65c313087 100644 --- a/ext/soap/php_encoding.c +++ b/ext/soap/php_encoding.c @@ -920,8 +920,8 @@ static xmlNodePtr to_xml_string(encodeTypePtr type, zval *data, int style, xmlNo if (c) { err[i-1] = '\\'; err[i++] = 'x'; - err[i++] = ((unsigned char)c >> 4) + ((((unsigned char)c >> 4) > 9) ? ('a' - 10) : '0'); - err[i++] = (c & 15) + (((c & 15) > 9) ? ('a' - 10) : '0'); + zend_bin2hex(err + i, (const unsigned char *) &c, 1); + i += 2; err[i++] = '.'; err[i++] = '.'; err[i++] = '.'; diff --git a/main/php_syslog.c b/main/php_syslog.c index a92b2518caab..bb1e366ae0e8 100644 --- a/main/php_syslog.c +++ b/main/php_syslog.c @@ -56,11 +56,10 @@ PHPAPI void php_syslog_str(int priority, const zend_string* message) } else if ((c < 0x20) && (PG(syslog_filter) == PHP_SYSLOG_FILTER_ALL)) { smart_string_appendc(&sbuf, c); } else { - static const char xdigits[] = "0123456789abcdef"; + char escaped[4] = "\\x"; - smart_string_appendl(&sbuf, "\\x", 2); - smart_string_appendc(&sbuf, xdigits[c >> 4]); - smart_string_appendc(&sbuf, xdigits[c & 0xf]); + zend_bin2hex(escaped + 2, &c, 1); + smart_string_appendl(&sbuf, escaped, sizeof(escaped)); } } From 1f2d1092eb62ae98e19258221f9e4c295297064e Mon Sep 17 00:00:00 2001 From: Weilin Du Date: Mon, 21 Sep 2026 21:42:29 +0800 Subject: [PATCH 2/2] ext/random: Use zend_bin2hex_str for little-endian random state serialization --- ext/ldap/ldap.c | 5 +++-- ext/random/random.c | 5 +++-- ext/soap/php_encoding.c | 4 ++-- main/php_syslog.c | 7 ++++--- 4 files changed, 12 insertions(+), 9 deletions(-) diff --git a/ext/ldap/ldap.c b/ext/ldap/ldap.c index 35512d9061ba..3e03df4c3375 100644 --- a/ext/ldap/ldap.c +++ b/ext/ldap/ldap.c @@ -3884,6 +3884,7 @@ PHP_FUNCTION(ldap_set_rebind_proc) static zend_string* php_ldap_do_escape(const bool *map, const char *value, size_t valuelen, zend_long flags) { + char hex[] = "0123456789abcdef"; size_t i, p = 0; size_t len = 0; zend_string *ret; @@ -3916,8 +3917,8 @@ static zend_string* php_ldap_do_escape(const bool *map, const char *value, size_ if (map[v] || ((flags & PHP_LDAP_ESCAPE_DN) && ((i == 0) || (i + 1 == valuelen)) && (v == ' '))) { ZSTR_VAL(ret)[p++] = '\\'; - zend_bin2hex(ZSTR_VAL(ret) + p, &v, 1); - p += 2; + ZSTR_VAL(ret)[p++] = hex[v >> 4]; + ZSTR_VAL(ret)[p++] = hex[v & 0x0f]; } else { ZSTR_VAL(ret)[p++] = v; } diff --git a/ext/random/random.c b/ext/random/random.c index f423a10f9a7b..15a2ddef9075 100644 --- a/ext/random/random.c +++ b/ext/random/random.c @@ -319,6 +319,7 @@ PHPAPI void *php_random_default_status(void) PHPAPI zend_string *php_random_bin2hex_le(const void *ptr, const size_t len) { #ifdef WORDS_BIGENDIAN + ZEND_SET_ALIGNED(16, static const char hexconvtab[]) = "0123456789abcdef"; zend_string *str; size_t i; @@ -328,8 +329,8 @@ PHPAPI zend_string *php_random_bin2hex_le(const void *ptr, const size_t len) /* force little endian */ for (size_t h = len; 0 < h; h--) { size_t j = h-1; - zend_bin2hex(ZSTR_VAL(str) + i, (const unsigned char *) ptr + j, 1); - i += 2; + ZSTR_VAL(str)[i++] = hexconvtab[((const unsigned char *) ptr)[j] >> 4]; + ZSTR_VAL(str)[i++] = hexconvtab[((const unsigned char *) ptr)[j] & 15]; } ZSTR_VAL(str)[i] = '\0'; diff --git a/ext/soap/php_encoding.c b/ext/soap/php_encoding.c index 7ae65c313087..044d2058ec09 100644 --- a/ext/soap/php_encoding.c +++ b/ext/soap/php_encoding.c @@ -920,8 +920,8 @@ static xmlNodePtr to_xml_string(encodeTypePtr type, zval *data, int style, xmlNo if (c) { err[i-1] = '\\'; err[i++] = 'x'; - zend_bin2hex(err + i, (const unsigned char *) &c, 1); - i += 2; + err[i++] = ((unsigned char)c >> 4) + ((((unsigned char)c >> 4) > 9) ? ('a' - 10) : '0'); + err[i++] = (c & 15) + (((c & 15) > 9) ? ('a' - 10) : '0'); err[i++] = '.'; err[i++] = '.'; err[i++] = '.'; diff --git a/main/php_syslog.c b/main/php_syslog.c index bb1e366ae0e8..a92b2518caab 100644 --- a/main/php_syslog.c +++ b/main/php_syslog.c @@ -56,10 +56,11 @@ PHPAPI void php_syslog_str(int priority, const zend_string* message) } else if ((c < 0x20) && (PG(syslog_filter) == PHP_SYSLOG_FILTER_ALL)) { smart_string_appendc(&sbuf, c); } else { - char escaped[4] = "\\x"; + static const char xdigits[] = "0123456789abcdef"; - zend_bin2hex(escaped + 2, &c, 1); - smart_string_appendl(&sbuf, escaped, sizeof(escaped)); + smart_string_appendl(&sbuf, "\\x", 2); + smart_string_appendc(&sbuf, xdigits[c >> 4]); + smart_string_appendc(&sbuf, xdigits[c & 0xf]); } }