ext/intl: using a bit more modern c++ memory management features. (#19163)

not always possible (e.g. PHP objects) but when scoped we can manage
here to simplify memory managament starting with IntlDateFormat.
This commit is contained in:
David CARLIER 2025-07-18 14:10:40 +01:00 committed by GitHub
parent 419f6750c0
commit 063d795599
No known key found for this signature in database
GPG key ID: B5690EEEBB952194

View file

@ -70,10 +70,10 @@ U_CFUNC PHP_FUNCTION(datefmt_format_object)
size_t locale_len; size_t locale_len;
bool pattern = false; bool pattern = false;
UDate date; UDate date;
TimeZone *timeZone = NULL; std::unique_ptr<TimeZone> timeZone;
UErrorCode status = U_ZERO_ERROR; UErrorCode status = U_ZERO_ERROR;
DateFormat *df = NULL; std::unique_ptr<DateFormat> df;
Calendar *cal = NULL; std::unique_ptr<Calendar> cal;
DateFormat::EStyle dateStyle = DateFormat::kDefault, DateFormat::EStyle dateStyle = DateFormat::kDefault,
timeStyle = DateFormat::kDefault; timeStyle = DateFormat::kDefault;
@ -158,28 +158,28 @@ U_CFUNC PHP_FUNCTION(datefmt_format_object)
"not initialized properly", 0); "not initialized properly", 0);
RETURN_FALSE; RETURN_FALSE;
} }
timeZone = obj_cal->getTimeZone().clone(); timeZone = std::unique_ptr<TimeZone>(obj_cal->getTimeZone().clone());
date = obj_cal->getTime(status); date = obj_cal->getTime(status);
if (U_FAILURE(status)) { if (U_FAILURE(status)) {
intl_error_set(NULL, status, intl_error_set(NULL, status,
"datefmt_format_object: error obtaining instant from " "datefmt_format_object: error obtaining instant from "
"IntlCalendar", 0); "IntlCalendar", 0);
RETVAL_FALSE; RETURN_FALSE;
goto cleanup;
} }
cal = obj_cal->clone(); cal = std::unique_ptr<Calendar>(obj_cal->clone());
} else if (instanceof_function(instance_ce, php_date_get_interface_ce())) { } else if (instanceof_function(instance_ce, php_date_get_interface_ce())) {
if (intl_datetime_decompose(object, &date, &timeZone, NULL, TimeZone *tz;
if (intl_datetime_decompose(object, &date, &tz, NULL,
"datefmt_format_object") == FAILURE) { "datefmt_format_object") == FAILURE) {
RETURN_FALSE; RETURN_FALSE;
} }
cal = new GregorianCalendar(Locale::createFromName(locale_str), status); timeZone = std::unique_ptr<TimeZone>(tz);
cal = std::unique_ptr<Calendar>(new GregorianCalendar(Locale::createFromName(locale_str), status));
if (U_FAILURE(status)) { if (U_FAILURE(status)) {
intl_error_set(NULL, status, intl_error_set(NULL, status,
"datefmt_format_object: could not create GregorianCalendar", "datefmt_format_object: could not create GregorianCalendar",
0); 0);
RETVAL_FALSE; RETURN_FALSE;
goto cleanup;
} }
} else { } else {
intl_error_set(NULL, status, "datefmt_format_object: the passed object " intl_error_set(NULL, status, "datefmt_format_object: the passed object "
@ -190,36 +190,32 @@ U_CFUNC PHP_FUNCTION(datefmt_format_object)
if (pattern) { if (pattern) {
StringPiece sp(Z_STRVAL_P(format)); StringPiece sp(Z_STRVAL_P(format));
df = new SimpleDateFormat( df = std::unique_ptr<DateFormat>(new SimpleDateFormat(
UnicodeString::fromUTF8(sp), UnicodeString::fromUTF8(sp),
Locale::createFromName(locale_str), Locale::createFromName(locale_str),
status); status));
if (U_FAILURE(status)) { if (U_FAILURE(status)) {
intl_error_set(NULL, status, intl_error_set(NULL, status,
"datefmt_format_object: could not create SimpleDateFormat", "datefmt_format_object: could not create SimpleDateFormat",
0); 0);
RETVAL_FALSE; RETURN_FALSE;
goto cleanup;
} }
} else { } else {
df = DateFormat::createDateTimeInstance(dateStyle, timeStyle, df = std::unique_ptr<DateFormat>(DateFormat::createDateTimeInstance(dateStyle, timeStyle,
Locale::createFromName(locale_str)); Locale::createFromName(locale_str)));
if (df == NULL) { /* according to ICU sources, this should never happen */ if (df == NULL) { /* according to ICU sources, this should never happen */
intl_error_set(NULL, status, intl_error_set(NULL, status,
"datefmt_format_object: could not create DateFormat", "datefmt_format_object: could not create DateFormat",
0); 0);
RETVAL_FALSE; RETURN_FALSE;
goto cleanup;
} }
} }
//must be in this order (or have the cal adopt the tz) //must be in this order (or have the cal adopt the tz)
df->adoptCalendar(cal); df->adoptCalendar(cal.release());
cal = NULL; df->adoptTimeZone(timeZone.release());
df->adoptTimeZone(timeZone);
timeZone = NULL;
{ {
zend_string *u8str; zend_string *u8str;
@ -231,15 +227,8 @@ U_CFUNC PHP_FUNCTION(datefmt_format_object)
intl_error_set(NULL, status, intl_error_set(NULL, status,
"datefmt_format_object: error converting result to UTF-8", "datefmt_format_object: error converting result to UTF-8",
0); 0);
RETVAL_FALSE; RETURN_FALSE;
goto cleanup;
} }
RETVAL_STR(u8str); RETVAL_STR(u8str);
} }
cleanup:
delete df;
delete timeZone;
delete cal;
} }