From e09a54e23101d28acb5355f3cca11bd0e46ce13b Mon Sep 17 00:00:00 2001 From: Tyson Andre Date: Mon, 17 Oct 2022 20:02:31 -0400 Subject: [PATCH] Add alternative to zend_string_dup for persistent strings And add a ZEND_ASSERT statement so that misuse of zend_string_dup can be detected. See comments in 9eb295fc4ca970dfeed0709cb3c16885acfb03b4 --- Zend/zend_string.h | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/Zend/zend_string.h b/Zend/zend_string.h index ed59ef82a14fe..9f5b4fb7ef7b3 100644 --- a/Zend/zend_string.h +++ b/Zend/zend_string.h @@ -195,9 +195,22 @@ static zend_always_inline zend_string *zend_string_copy(zend_string *s) return s; } +static zend_always_inline zend_string *zend_string_dup_safe(zend_string *s, bool persistent) +{ + if (ZSTR_IS_INTERNED(s) && (!persistent || (GC_FLAGS(s) & IS_STR_PERSISTENT))) { + return s; + } else { + return zend_string_init(ZSTR_VAL(s), ZSTR_LEN(s), persistent); + } +} + +/* Callers should use PHP 8.2's definition of zend_string_dup_safe instead, + if they need a temporary or interned persistent string + and aren't sure if it might be a temporary (allocated with emalloc) interned string. */ static zend_always_inline zend_string *zend_string_dup(zend_string *s, bool persistent) { if (ZSTR_IS_INTERNED(s)) { + ZEND_ASSERT(!persistent || (GC_FLAGS(s) & (IS_STR_PERSISTENT|IS_STR_PERMANENT))); return s; } else { return zend_string_init(ZSTR_VAL(s), ZSTR_LEN(s), persistent);