U_CFUNC PHP_FUNCTION(intlcal_roll) { zend_long field, value; zval args_a[3] = {0}, *args = args_a; zend_bool bool_variant_val = (zend_bool)-1; CALENDAR_METHOD_INIT_VARS; if (ZEND_NUM_ARGS() > (getThis() ? 2 :3) || zend_get_parameters_array_ex(ZEND_NUM_ARGS(), args) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlcal_set: too many arguments", 0 TSRMLS_CC); RETURN_FALSE; } if (!getThis()) { args++; } if (!Z_ISUNDEF(args[1]) && (Z_TYPE(args[1]) == IS_TRUE || Z_TYPE(args[1]) == IS_FALSE)) { if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Olb", &object, Calendar_ce_ptr, &field, &bool_variant_val) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlcal_roll: bad arguments", 0 TSRMLS_CC); RETURN_FALSE; } bool_variant_val = Z_TYPE(args[1]) == IS_TRUE? 1 : 0; } else if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Oll", &object, Calendar_ce_ptr, &field, &value) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlcal_roll: bad arguments", 0 TSRMLS_CC); RETURN_FALSE; } if (field < 0 || field >= UCAL_FIELD_COUNT) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlcal_roll: invalid field", 0 TSRMLS_CC); RETURN_FALSE; } if (bool_variant_val == (zend_bool)-1 && (value < INT32_MIN || value > INT32_MAX)) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlcal_roll: value out of bounds", 0 TSRMLS_CC); RETURN_FALSE; } CALENDAR_METHOD_FETCH_OBJECT; if (bool_variant_val != (zend_bool)-1) { co->ucal->roll((UCalendarDateFields)field, (UBool)bool_variant_val, CALENDAR_ERROR_CODE(co)); } else { co->ucal->roll((UCalendarDateFields)field, (int32_t)value, CALENDAR_ERROR_CODE(co)); } INTL_METHOD_CHECK_STATUS(co, "intlcal_roll: Error calling ICU Calendar::roll"); RETURN_TRUE; }
/* {{{ * Internal function which calls the udat_parseCalendar */ static void internal_parse_to_localtime(IntlDateFormatter_object *dfo, char* text_to_parse, int32_t text_len, int32_t *parse_pos, zval *return_value) { UCalendar *parsed_calendar = NULL; UChar* text_utf16 = NULL; int32_t text_utf16_len = 0; zend_long isInDST = 0; /* Convert timezone to UTF-16. */ intl_convert_utf8_to_utf16(&text_utf16, &text_utf16_len, text_to_parse, text_len, &INTL_DATA_ERROR_CODE(dfo)); INTL_METHOD_CHECK_STATUS(dfo, "Error converting timezone to UTF-16" ); parsed_calendar = (UCalendar *)udat_getCalendar(DATE_FORMAT_OBJECT(dfo)); udat_parseCalendar( DATE_FORMAT_OBJECT(dfo), parsed_calendar, text_utf16, text_utf16_len, parse_pos, &INTL_DATA_ERROR_CODE(dfo)); if (text_utf16) { efree(text_utf16); } INTL_METHOD_CHECK_STATUS( dfo, "Date parsing failed" ); array_init( return_value ); /* Add entries from various fields of the obtained parsed_calendar */ add_to_localtime_arr( dfo, return_value, parsed_calendar, UCAL_SECOND, CALENDAR_SEC); add_to_localtime_arr( dfo, return_value, parsed_calendar, UCAL_MINUTE, CALENDAR_MIN); add_to_localtime_arr( dfo, return_value, parsed_calendar, UCAL_HOUR_OF_DAY, CALENDAR_HOUR); add_to_localtime_arr( dfo, return_value, parsed_calendar, UCAL_YEAR, CALENDAR_YEAR); add_to_localtime_arr( dfo, return_value, parsed_calendar, UCAL_DAY_OF_MONTH, CALENDAR_MDAY); add_to_localtime_arr( dfo, return_value, parsed_calendar, UCAL_DAY_OF_WEEK, CALENDAR_WDAY); add_to_localtime_arr( dfo, return_value, parsed_calendar, UCAL_DAY_OF_YEAR, CALENDAR_YDAY); add_to_localtime_arr( dfo, return_value, parsed_calendar, UCAL_MONTH, CALENDAR_MON); /* Is in DST? */ isInDST = ucal_inDaylightTime(parsed_calendar , &INTL_DATA_ERROR_CODE(dfo)); INTL_METHOD_CHECK_STATUS( dfo, "Date parsing - localtime failed : while checking if currently in DST." ); add_assoc_long( return_value, CALENDAR_ISDST,(isInDST==1?1:0)); }
static void add_to_localtime_arr( IntlDateFormatter_object *dfo, zval* return_value, const UCalendar *parsed_calendar, zend_long calendar_field, char* key_name) { zend_long calendar_field_val = ucal_get( parsed_calendar, calendar_field, &INTL_DATA_ERROR_CODE(dfo)); INTL_METHOD_CHECK_STATUS( dfo, "Date parsing - localtime failed : could not get a field from calendar" ); if( strcmp(key_name, CALENDAR_YEAR )==0 ){ /* since tm_year is years from 1900 */ add_assoc_long( return_value, key_name,( calendar_field_val-1900) ); }else if( strcmp(key_name, CALENDAR_WDAY )==0 ){ /* since tm_wday starts from 0 whereas ICU WDAY start from 1 */ add_assoc_long( return_value, key_name,( calendar_field_val-1) ); }else{ add_assoc_long( return_value, key_name, calendar_field_val ); } }
U_CFUNC PHP_FUNCTION(intltz_get_display_name) { zend_bool daylight = 0; zend_long display_type = TimeZone::LONG; const char *locale_str = NULL; size_t dummy = 0; TIMEZONE_METHOD_INIT_VARS; if (zend_parse_method_parameters(ZEND_NUM_ARGS(), getThis(), "O|bls!", &object, TimeZone_ce_ptr, &daylight, &display_type, &locale_str, &dummy) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intltz_get_display_name: bad arguments", 0); RETURN_FALSE; } bool found = false; for (int i = 0; !found && i < sizeof(display_types)/sizeof(*display_types); i++) { if (display_types[i] == display_type) found = true; } if (!found) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intltz_get_display_name: wrong display type", 0); RETURN_FALSE; } if (!locale_str) { locale_str = intl_locale_get_default(); } TIMEZONE_METHOD_FETCH_OBJECT; UnicodeString result; to->utimezone->getDisplayName((UBool)daylight, (TimeZone::EDisplayType)display_type, Locale::createFromName(locale_str), result); char *str; int str_len; intl_convert_utf16_to_utf8(&str, &str_len, result.getBuffer(), result.length(), TIMEZONE_ERROR_CODE_P(to)); INTL_METHOD_CHECK_STATUS(to, "intltz_get_display_name: " "could not convert resulting time zone id to UTF-16"); RETVAL_STRINGL(str, str_len); //???? efree(str); }
U_CFUNC PHP_FUNCTION(intlcal_in_daylight_time) { CALENDAR_METHOD_INIT_VARS; if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O", &object, Calendar_ce_ptr) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlcal_in_daylight_time: bad arguments", 0 TSRMLS_CC); RETURN_FALSE; } CALENDAR_METHOD_FETCH_OBJECT; UBool ret = co->ucal->inDaylightTime(CALENDAR_ERROR_CODE(co)); INTL_METHOD_CHECK_STATUS(co, "intlcal_in_daylight_time: " "Error calling ICU method"); RETURN_BOOL((int)ret); }
U_CFUNC PHP_FUNCTION(intlcal_get_minimal_days_in_first_week) { CALENDAR_METHOD_INIT_VARS; if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O", &object, Calendar_ce_ptr) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlcal_get_minimal_days_in_first_week: bad arguments", 0 TSRMLS_CC); RETURN_FALSE; } CALENDAR_METHOD_FETCH_OBJECT; uint8_t result = co->ucal->getMinimalDaysInFirstWeek(); INTL_METHOD_CHECK_STATUS(co, "intlcal_get_first_day_of_week: Call to ICU method has failed"); RETURN_LONG((zend_long)result); }
U_CFUNC PHP_FUNCTION(intlcal_set_time) { double time_arg; CALENDAR_METHOD_INIT_VARS; if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Od", &object, Calendar_ce_ptr, &time_arg) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlcal_set_time: bad arguments", 0 TSRMLS_CC); RETURN_FALSE; } CALENDAR_METHOD_FETCH_OBJECT; co->ucal->setTime((UDate)time_arg, CALENDAR_ERROR_CODE(co)); INTL_METHOD_CHECK_STATUS(co, "Call to underlying method failed"); RETURN_TRUE; }
U_CFUNC PHP_FUNCTION(intlcal_get_time) { CALENDAR_METHOD_INIT_VARS; if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O", &object, Calendar_ce_ptr) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlcal_get_time: bad arguments", 0 TSRMLS_CC); RETURN_FALSE; } CALENDAR_METHOD_FETCH_OBJECT; UDate result = co->ucal->getTime(CALENDAR_ERROR_CODE(co)); INTL_METHOD_CHECK_STATUS(co, "intlcal_get_time: error calling ICU Calendar::getTime"); RETURN_DOUBLE((double)result); }
U_CFUNC PHP_FUNCTION(intlgregcal_set_gregorian_change) { double date; CALENDAR_METHOD_INIT_VARS; if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "Od", &object, GregorianCalendar_ce_ptr, &date) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlgregcal_set_gregorian_change: bad arguments", 0 TSRMLS_CC); RETURN_FALSE; } CALENDAR_METHOD_FETCH_OBJECT; fetch_greg(co)->setGregorianChange(date, CALENDAR_ERROR_CODE(co)); INTL_METHOD_CHECK_STATUS(co, "intlgregcal_set_gregorian_change: error " "calling ICU method"); RETURN_TRUE; }
/* {{{ proto string datefmt_get_timezone_id(IntlDateFormatter $mf) * Get formatter timezone_id. */ U_CFUNC PHP_FUNCTION(datefmt_get_timezone_id) { DATE_FORMAT_METHOD_INIT_VARS; if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O", &object, IntlDateFormatter_ce_ptr ) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "datefmt_get_timezone_" "id: unable to parse input params", 0 TSRMLS_CC); RETURN_FALSE; } DATE_FORMAT_METHOD_FETCH_OBJECT; UnicodeString res = UnicodeString(); fetch_datefmt(dfo)->getTimeZone().getID(res); intl_charFromString(res, &Z_STRVAL_P(return_value), &Z_STRLEN_P(return_value), &INTL_DATA_ERROR_CODE(dfo)); INTL_METHOD_CHECK_STATUS(dfo, "Could not convert time zone id to UTF-8"); Z_TYPE_P(return_value) = IS_STRING; }
/* {{{ * Internal function which calls the udat_format */ static void internal_format(IntlDateFormatter_object *dfo, UDate timestamp, zval *return_value) { UChar* formatted = NULL; int32_t resultlengthneeded =0 ; resultlengthneeded=udat_format( DATE_FORMAT_OBJECT(dfo), timestamp, NULL, resultlengthneeded, NULL, &INTL_DATA_ERROR_CODE(dfo)); if(INTL_DATA_ERROR_CODE(dfo)==U_BUFFER_OVERFLOW_ERROR) { INTL_DATA_ERROR_CODE(dfo)=U_ZERO_ERROR; formatted=(UChar*)emalloc(sizeof(UChar) * resultlengthneeded); udat_format( DATE_FORMAT_OBJECT(dfo), timestamp, formatted, resultlengthneeded, NULL, &INTL_DATA_ERROR_CODE(dfo)); } if (formatted && U_FAILURE( INTL_DATA_ERROR_CODE(dfo) ) ) { efree(formatted); } INTL_METHOD_CHECK_STATUS( dfo, "Date formatting failed" ); INTL_METHOD_RETVAL_UTF8( dfo, formatted, resultlengthneeded, 1 ); }
U_CFUNC PHP_FUNCTION(rbbi_get_rule_status_vec) { BREAKITER_METHOD_INIT_VARS; object = getThis(); if (zend_parse_parameters_none() == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "rbbi_get_rule_status_vec: bad arguments", 0 TSRMLS_CC); RETURN_FALSE; } BREAKITER_METHOD_FETCH_OBJECT; int32_t num_rules = fetch_rbbi(bio)->getRuleStatusVec(NULL, 0, BREAKITER_ERROR_CODE(bio)); if (BREAKITER_ERROR_CODE(bio) == U_BUFFER_OVERFLOW_ERROR) { BREAKITER_ERROR_CODE(bio) = U_ZERO_ERROR; } else { // should not happen INTL_METHOD_CHECK_STATUS(bio, "rbbi_get_rule_status_vec: failed " " determining the number of status values"); } int32_t *rules = new int32_t[num_rules]; num_rules = fetch_rbbi(bio)->getRuleStatusVec(rules, num_rules, BREAKITER_ERROR_CODE(bio)); if (U_FAILURE(BREAKITER_ERROR_CODE(bio))) { delete[] rules; intl_errors_set(BREAKITER_ERROR_P(bio), BREAKITER_ERROR_CODE(bio), "rbbi_get_rule_status_vec: failed obtaining the status values", 0 TSRMLS_CC); RETURN_FALSE; } array_init_size(return_value, num_rules); for (int32_t i = 0; i < num_rules; i++) { add_next_index_long(return_value, rules[i]); } delete[] rules; }
/* {{{ proto Spoofchecker::__construct() * Spoofchecker object constructor. */ PHP_METHOD(Spoofchecker, __construct) { #if U_ICU_VERSION_MAJOR_NUM < 58 int checks; #endif zend_error_handling error_handling; SPOOFCHECKER_METHOD_INIT_VARS; if (zend_parse_parameters_none_throw() == FAILURE) { return; } zend_replace_error_handling(EH_THROW, IntlException_ce_ptr, &error_handling); SPOOFCHECKER_METHOD_FETCH_OBJECT_NO_CHECK; co->uspoof = uspoof_open(SPOOFCHECKER_ERROR_CODE_P(co)); INTL_METHOD_CHECK_STATUS(co, "spoofchecker: unable to open ICU Spoof Checker"); #if U_ICU_VERSION_MAJOR_NUM >= 58 /* TODO save it into the object for further suspiction check comparison. */ /* ICU 58 removes WSC and MSC handling. However there are restriction levels as defined in http://www.unicode.org/reports/tr39/tr39-15.html#Restriction_Level_Detection and the default is high restrictive. In further, we might want to utilize uspoof_check2 APIs when it became stable, to use extended check result APIs. Subsequent changes in the unicode security algos are to be watched.*/ uspoof_setRestrictionLevel(co->uspoof, SPOOFCHECKER_DEFAULT_RESTRICTION_LEVEL); #else /* Single-script enforcement is on by default. This fails for languages like Japanese that legally use multiple scripts within a single word, so we turn it off. */ checks = uspoof_getChecks(co->uspoof, SPOOFCHECKER_ERROR_CODE_P(co)); uspoof_setChecks(co->uspoof, checks & ~USPOOF_SINGLE_SCRIPT, SPOOFCHECKER_ERROR_CODE_P(co)); #endif zend_restore_error_handling(&error_handling); }
U_CFUNC PHP_FUNCTION(intltz_get_id) { TIMEZONE_METHOD_INIT_VARS; if (zend_parse_method_parameters(ZEND_NUM_ARGS(), getThis(), "O", &object, TimeZone_ce_ptr) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intltz_get_id: bad arguments", 0); RETURN_FALSE; } TIMEZONE_METHOD_FETCH_OBJECT; UnicodeString id_us; to->utimezone->getID(id_us); zend_string *u8str; u8str = intl_convert_utf16_to_utf8( id_us.getBuffer(), id_us.length(), TIMEZONE_ERROR_CODE_P(to)); INTL_METHOD_CHECK_STATUS(to, "intltz_get_id: Could not convert id to UTF-8"); RETVAL_NEW_STR(u8str); }
/* {{{ proto string datefmt_get_timezone_id(IntlDateFormatter $mf) * Get formatter timezone_id. */ U_CFUNC PHP_FUNCTION(datefmt_get_timezone_id) { char *str; size_t str_len; DATE_FORMAT_METHOD_INIT_VARS; if (zend_parse_method_parameters(ZEND_NUM_ARGS(), getThis(), "O", &object, IntlDateFormatter_ce_ptr ) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "datefmt_get_timezone_" "id: unable to parse input params", 0); RETURN_FALSE; } DATE_FORMAT_METHOD_FETCH_OBJECT; UnicodeString res = UnicodeString(); fetch_datefmt(dfo)->getTimeZone().getID(res); intl_charFromString(res, &str, &str_len, &INTL_DATA_ERROR_CODE(dfo)); INTL_METHOD_CHECK_STATUS(dfo, "Could not convert time zone id to UTF-8"); RETVAL_STRINGL(str, str_len); //???? efree(str); }
U_CFUNC PHP_FUNCTION(intlcal_to_date_time) { zval retval; CALENDAR_METHOD_INIT_VARS; if (zend_parse_method_parameters(ZEND_NUM_ARGS() TSRMLS_CC, getThis(), "O", &object, Calendar_ce_ptr) == FAILURE) { intl_error_set(NULL, U_ILLEGAL_ARGUMENT_ERROR, "intlcal_to_date_time: bad arguments", 0 TSRMLS_CC); RETURN_FALSE; } CALENDAR_METHOD_FETCH_OBJECT; /* There are no exported functions in ext/date to this * in a more native fashion */ double date = co->ucal->getTime(CALENDAR_ERROR_CODE(co)) / 1000.; int64_t ts; char ts_str[sizeof("@-9223372036854775808")]; int ts_str_len; zval ts_tmp, ts_zval, tmp; INTL_METHOD_CHECK_STATUS(co, "Call to ICU method has failed"); if (date > (double)U_INT64_MAX || date < (double)U_INT64_MIN) { intl_errors_set(CALENDAR_ERROR_P(co), U_ILLEGAL_ARGUMENT_ERROR, "intlcal_to_date_time: The calendar date is out of the " "range for a 64-bit integer", 0 TSRMLS_CC); RETURN_FALSE; } ZVAL_UNDEF(&retval); ts = (int64_t)date; ts_str_len = slprintf(ts_str, sizeof(ts_str), "@%I64d", ts); ZVAL_STRINGL(&ts_zval, ts_str, ts_str_len); /* Now get the time zone */ const TimeZone& tz = co->ucal->getTimeZone(); zval *timezone_zval = timezone_convert_to_datetimezone( &tz, CALENDAR_ERROR_P(co), "intlcal_to_date_time", &tmp TSRMLS_CC); if (timezone_zval == NULL) { RETURN_FALSE; } /* resources allocated from now on */ /* Finally, instantiate object and call constructor */ object_init_ex(return_value, php_date_get_date_ce()); zend_call_method_with_2_params(return_value, NULL, NULL, "__construct", NULL, &ts_zval, timezone_zval); if (EG(exception)) { intl_errors_set(CALENDAR_ERROR_P(co), U_ILLEGAL_ARGUMENT_ERROR, "intlcal_to_date_time: DateTime constructor has thrown exception", 1 TSRMLS_CC); zend_object_store_ctor_failed(Z_OBJ_P(return_value) TSRMLS_CC); zval_ptr_dtor(return_value); zval_ptr_dtor(&ts_zval); RETVAL_FALSE; goto error; } zval_ptr_dtor(&ts_zval); /* due to bug #40743, we have to set the time zone again */ zend_call_method_with_1_params(return_value, NULL, NULL, "settimezone", &retval, timezone_zval); if (Z_ISUNDEF(retval) || Z_TYPE(retval) == IS_FALSE) { intl_errors_set(CALENDAR_ERROR_P(co), U_ILLEGAL_ARGUMENT_ERROR, "intlcal_to_date_time: call to DateTime::setTimeZone has failed", 1 TSRMLS_CC); zval_ptr_dtor(return_value); RETVAL_FALSE; goto error; } error: zval_ptr_dtor(timezone_zval); zval_ptr_dtor(&retval); }