mirror of
https://github.com/php/php-src.git
synced 2026-03-24 00:02:20 +01:00
Slightly improve error handling in DatePeriod::__construct()
This commit is contained in:
@@ -24,6 +24,7 @@
|
||||
#include "ext/standard/php_math.h"
|
||||
#include "php_date.h"
|
||||
#include "zend_interfaces.h"
|
||||
#include "zend_exceptions.h"
|
||||
#include "lib/timelib.h"
|
||||
#include "lib/timelib_private.h"
|
||||
#ifndef PHP_WIN32
|
||||
@@ -4117,13 +4118,11 @@ PHP_METHOD(DatePeriod, __construct)
|
||||
timelib_time *clone;
|
||||
zend_error_handling error_handling;
|
||||
|
||||
zend_replace_error_handling(EH_THROW, NULL, &error_handling);
|
||||
if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS(), "OOl|l", &start, date_ce_interface, &interval, date_ce_interval, &recurrences, &options) == FAILURE) {
|
||||
if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS(), "OOO|l", &start, date_ce_interface, &interval, date_ce_interval, &end, date_ce_interface, &options) == FAILURE) {
|
||||
if (zend_parse_parameters_ex(ZEND_PARSE_PARAMS_QUIET, ZEND_NUM_ARGS(), "s|l", &isostr, &isostr_len, &options) == FAILURE) {
|
||||
php_error_docref(NULL, E_WARNING, "This constructor accepts either (DateTimeInterface, DateInterval, int) OR (DateTimeInterface, DateInterval, DateTime) OR (string) as arguments.");
|
||||
zend_restore_error_handling(&error_handling);
|
||||
return;
|
||||
zend_type_error("DatePeriod::__construct() accepts (DateTimeInterface, DateInterval, int [, int]), or (DateTimeInterface, DateInterval, DateTime [, int]), or (string [, int]) as arguments");
|
||||
RETURN_THROWS();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -4132,15 +4131,30 @@ PHP_METHOD(DatePeriod, __construct)
|
||||
dpobj->current = NULL;
|
||||
|
||||
if (isostr) {
|
||||
zend_replace_error_handling(EH_THROW, NULL, &error_handling);
|
||||
date_period_initialize(&(dpobj->start), &(dpobj->end), &(dpobj->interval), &recurrences, isostr, isostr_len);
|
||||
zend_restore_error_handling(&error_handling);
|
||||
if (EG(exception)) {
|
||||
RETURN_THROWS();
|
||||
}
|
||||
|
||||
if (dpobj->start == NULL) {
|
||||
php_error_docref(NULL, E_WARNING, "The ISO interval '%s' did not contain a start date.", isostr);
|
||||
zend_string *func = get_active_function_or_method_name();
|
||||
zend_throw_error(zend_ce_exception, "%s(): ISO interval must contain a start date, \"%s\" given", ZSTR_VAL(func), isostr);
|
||||
zend_string_release(func);
|
||||
RETURN_THROWS();
|
||||
}
|
||||
if (dpobj->interval == NULL) {
|
||||
php_error_docref(NULL, E_WARNING, "The ISO interval '%s' did not contain an interval.", isostr);
|
||||
zend_string *func = get_active_function_or_method_name();
|
||||
zend_throw_error(zend_ce_exception, "%s(): ISO interval must contain an interval, \"%s\" given", ZSTR_VAL(func), isostr);
|
||||
zend_string_release(func);
|
||||
RETURN_THROWS();
|
||||
}
|
||||
if (dpobj->end == NULL && recurrences == 0) {
|
||||
php_error_docref(NULL, E_WARNING, "The ISO interval '%s' did not contain an end date or a recurrence count.", isostr);
|
||||
zend_string *func = get_active_function_or_method_name();
|
||||
zend_throw_error(zend_ce_exception, "%s(): ISO interval must contain an end date or a recurrence count, \"%s\" given", ZSTR_VAL(func), isostr);
|
||||
zend_string_release(func);
|
||||
RETURN_THROWS();
|
||||
}
|
||||
|
||||
if (dpobj->start) {
|
||||
@@ -4179,7 +4193,10 @@ PHP_METHOD(DatePeriod, __construct)
|
||||
}
|
||||
|
||||
if (dpobj->end == NULL && recurrences < 1) {
|
||||
php_error_docref(NULL, E_WARNING, "The recurrence count '%d' is invalid. Needs to be > 0", (int) recurrences);
|
||||
zend_string *func = get_active_function_or_method_name();
|
||||
zend_throw_error(zend_ce_exception, "%s(): Recurrence count must be greater than 0", ZSTR_VAL(func));
|
||||
zend_string_release(func);
|
||||
RETURN_THROWS();
|
||||
}
|
||||
|
||||
/* options */
|
||||
@@ -4189,8 +4206,6 @@ PHP_METHOD(DatePeriod, __construct)
|
||||
dpobj->recurrences = recurrences + dpobj->include_start_date;
|
||||
|
||||
dpobj->initialized = 1;
|
||||
|
||||
zend_restore_error_handling(&error_handling);
|
||||
}
|
||||
/* }}} */
|
||||
|
||||
|
||||
@@ -7,11 +7,12 @@ Havard Eide <nucleuz@gmail.com>
|
||||
date.timezone=UTC
|
||||
--FILE--
|
||||
<?php
|
||||
new DatePeriod();
|
||||
|
||||
try {
|
||||
new DatePeriod();
|
||||
} catch (TypeError $exception) {
|
||||
echo $exception->getMessage() . "\n";
|
||||
}
|
||||
?>
|
||||
--EXPECTF--
|
||||
Fatal error: Uncaught Exception: DatePeriod::__construct(): This constructor accepts either (DateTimeInterface, DateInterval, int) OR (DateTimeInterface, DateInterval, DateTime) OR (string) as arguments. in %s:%d
|
||||
Stack trace:
|
||||
#0 %s(%d): DatePeriod->__construct()
|
||||
#1 {main}
|
||||
thrown in %s on line %d
|
||||
--EXPECT--
|
||||
DatePeriod::__construct() accepts (DateTimeInterface, DateInterval, int [, int]), or (DateTimeInterface, DateInterval, DateTime [, int]), or (string [, int]) as arguments
|
||||
|
||||
@@ -9,11 +9,12 @@ try {
|
||||
}
|
||||
|
||||
try {
|
||||
new DatePeriod(new DateTime('yesterday'), new DateInterval('P1D'),-1);
|
||||
new DatePeriod(new DateTime('yesterday'), new DateInterval('P1D'), -1);
|
||||
} catch (Exception $exception) {
|
||||
echo $exception->getMessage(), "\n";
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECT--
|
||||
DatePeriod::__construct(): The recurrence count '0' is invalid. Needs to be > 0
|
||||
DatePeriod::__construct(): The recurrence count '-1' is invalid. Needs to be > 0
|
||||
DatePeriod::__construct(): Recurrence count must be greater than 0
|
||||
DatePeriod::__construct(): Recurrence count must be greater than 0
|
||||
|
||||
@@ -4,12 +4,9 @@ Bug #44562 (Creating instance of DatePeriod crashes)
|
||||
<?php
|
||||
date_default_timezone_set('Europe/Oslo');
|
||||
|
||||
try
|
||||
{
|
||||
try {
|
||||
$dp = new DatePeriod('2D');
|
||||
}
|
||||
catch ( Exception $e )
|
||||
{
|
||||
} catch (Exception $e) {
|
||||
echo $e->getMessage(), "\n";
|
||||
}
|
||||
|
||||
|
||||
@@ -4,13 +4,13 @@ DateInterval with bad format should not leak period
|
||||
<?php
|
||||
|
||||
try {
|
||||
$interval = new DateInterval('P3"D');
|
||||
new DateInterval('P3"D');
|
||||
} catch (Exception $e) {
|
||||
echo $e->getMessage(), "\n";
|
||||
}
|
||||
|
||||
try {
|
||||
$perid = new DatePeriod('P3"D');
|
||||
new DatePeriod('P3"D');
|
||||
} catch (Exception $e) {
|
||||
echo $e->getMessage(), "\n";
|
||||
}
|
||||
|
||||
29
ext/date/tests/date_period_bad_iso_format.phpt
Normal file
29
ext/date/tests/date_period_bad_iso_format.phpt
Normal file
@@ -0,0 +1,29 @@
|
||||
--TEST--
|
||||
Test bad ISO date formats passed to DatePeriod constructor
|
||||
--FILE--
|
||||
<?php
|
||||
|
||||
try {
|
||||
new DatePeriod("R4");
|
||||
} catch (Exception $e) {
|
||||
echo $e->getMessage(), "\n";
|
||||
}
|
||||
|
||||
try {
|
||||
new DatePeriod("R4/2012-07-01T00:00:00Z");
|
||||
} catch (Exception $e) {
|
||||
echo $e->getMessage(), "\n";
|
||||
}
|
||||
|
||||
|
||||
try {
|
||||
new DatePeriod("2012-07-01T00:00:00Z/P7D");
|
||||
} catch (Exception $e) {
|
||||
echo $e->getMessage(), "\n";
|
||||
}
|
||||
|
||||
?>
|
||||
--EXPECT--
|
||||
DatePeriod::__construct(): ISO interval must contain a start date, "R4" given
|
||||
DatePeriod::__construct(): ISO interval must contain an interval, "R4/2012-07-01T00:00:00Z" given
|
||||
DatePeriod::__construct(): ISO interval must contain an end date or a recurrence count, "2012-07-01T00:00:00Z/P7D" given
|
||||
Reference in New Issue
Block a user