Commit cd5574617f8 for php.net

commit cd5574617f8f27a56ba33f2ebbbc78ddb5039e4d
Merge: e22ba55be19 946d687d8d5
Author: David Carlier <devnexen@gmail.com>
Date:   Sun May 24 07:35:29 2026 +0100

    Merge branch 'PHP-8.5'

    * PHP-8.5:
      ext/intl: fix IntlListFormatter object error state after format() failures

diff --cc ext/intl/listformatter/listformatter_class.cpp
index 817b3d74369,e4f8b18d7dd..950eb81b7e1
--- a/ext/intl/listformatter/listformatter_class.cpp
+++ b/ext/intl/listformatter/listformatter_class.cpp
@@@ -142,41 -138,76 +144,41 @@@ PHP_METHOD(IntlListFormatter, format

      ZEND_HASH_FOREACH_VAL(ht, val) {
          zend_string *str_val, *tmp_str;
 -
 -        str_val = zval_get_tmp_string(val, &tmp_str);
 -
 -        // Convert PHP string to UTF-16
 -        UChar *ustr = NULL;
 -        int32_t ustr_len = 0;
 -        UErrorCode status = U_ZERO_ERROR;
 -
 -        intl_convert_utf8_to_utf16(&ustr, &ustr_len, ZSTR_VAL(str_val), ZSTR_LEN(str_val), &status);
 +        UErrorCode conv_status = U_ZERO_ERROR;
 +
 +        str_val = zval_try_get_tmp_string(val, &tmp_str);
 +        if (UNEXPECTED(!str_val)) {
 +            RETURN_THROWS();
 +        }
 +        intl_stringFromChar(items[i], ZSTR_VAL(str_val), ZSTR_LEN(str_val), &conv_status);
          zend_tmp_string_release(tmp_str);

 -        if (U_FAILURE(status)) {
 -            // We can't use goto cleanup because items and itemLengths are incompletely allocated
 -            for (uint32_t j = 0; j < i; j++) {
 -                efree((void *)items[j]);
 -            }
 -            efree(items);
 -            efree(itemLengths);
 -            intl_errors_set(LISTFORMATTER_ERROR_P(obj), status, "Failed to convert string to UTF-16");
 +        if (U_FAILURE(conv_status)) {
-             intl_error_set(nullptr, conv_status, "Failed to convert string to UTF-16");
++            intl_errors_set(LISTFORMATTER_ERROR_P(obj), conv_status, "Failed to convert string to UTF-16");
              RETURN_FALSE;
          }
 -
 -        items[i] = ustr;
 -        itemLengths[i] = ustr_len;
 +
          i++;
      } ZEND_HASH_FOREACH_END();

      UErrorCode status = U_ZERO_ERROR;
 -    int32_t resultLength;
 -    UChar *result = NULL;
 -
 -    resultLength = ulistfmt_format(LISTFORMATTER_OBJECT(obj), items, itemLengths, count, NULL, 0, &status);
 -
 -    if (U_FAILURE(status) && status != U_BUFFER_OVERFLOW_ERROR) {
 -        intl_errors_set(LISTFORMATTER_ERROR_P(obj), status, "Failed to format list");
 -        RETVAL_FALSE;
 -        goto cleanup;
 -    }
 +    UnicodeString result;

 -    // Allocate buffer and try again
 -    status = U_ZERO_ERROR;
 -    result = (UChar *)safe_emalloc(resultLength + 1, sizeof(UChar), 0);
 -    ulistfmt_format(LISTFORMATTER_OBJECT(obj), items, itemLengths, count, result, resultLength, &status);
 +    LISTFORMATTER_OBJECT(obj)->format(items.get(), count, result, status);

      if (U_FAILURE(status)) {
-         intl_error_set(nullptr, status, "Failed to format list");
 -        if (result) {
 -            efree(result);
 -        }
+         intl_errors_set(LISTFORMATTER_ERROR_P(obj), status, "Failed to format list");
 -        RETVAL_FALSE;
 -        goto cleanup;
 +        RETURN_FALSE;
      }

 -    // Convert result back to UTF-8
 -    zend_string *ret = intl_convert_utf16_to_utf8(result, resultLength, &status);
 -    efree(result);
 -
 +    zend_string *ret = intl_charFromString(result, &status);
 +
      if (!ret) {
-         intl_error_set(nullptr, status, "Failed to convert result to UTF-8");
+         intl_errors_set(LISTFORMATTER_ERROR_P(obj), status, "Failed to convert result to UTF-8");
 -        RETVAL_FALSE;
 -    } else {
 -        RETVAL_NEW_STR(ret);
 +        RETURN_FALSE;
      }

 -cleanup:
 -    for (i = 0; i < count; i++) {
 -        efree((void *)items[i]);
 -    }
 -    efree(items);
 -    efree(itemLengths);
 +    RETVAL_STR(ret);
  }

  PHP_METHOD(IntlListFormatter, getErrorCode)