Commit fdde51c6 authored by Frank Tang's avatar Frank Tang Committed by V8 LUCI CQ

[Temporal] Add Instant.prototype.(add|subtract)

Spec Text:
https://tc39.es/proposal-temporal/#sec-temporal.instant.prototype.add
https://tc39.es/proposal-temporal/#sec-temporal.instant.prototype.subtract

Also fix bug in IsValidEpochNanoseconds

Bug: v8:11544
Change-Id: Ied605c9de4ee38a18e2356a89e3a69d534a004d1
Reviewed-on: https://chromium-review.googlesource.com/c/v8/v8/+/3617394
Commit-Queue: Frank Tang <ftang@chromium.org>
Reviewed-by: 's avatarAdam Klein <adamk@chromium.org>
Cr-Commit-Position: refs/heads/main@{#80983}
parent c8419529
...@@ -100,10 +100,6 @@ TO_BE_IMPLEMENTED(TemporalDurationPrototypeToLocaleString) ...@@ -100,10 +100,6 @@ TO_BE_IMPLEMENTED(TemporalDurationPrototypeToLocaleString)
TO_BE_IMPLEMENTED(TemporalDurationPrototypeToString) TO_BE_IMPLEMENTED(TemporalDurationPrototypeToString)
/* Temporal.Instant */ /* Temporal.Instant */
/* Temporal #sec-temporal.instant.prototype.add */
TO_BE_IMPLEMENTED(TemporalInstantPrototypeAdd)
/* Temporal #sec-temporal.instant.prototype.subtract */
TO_BE_IMPLEMENTED(TemporalInstantPrototypeSubtract)
/* Temporal #sec-temporal.instant.prototype.until */ /* Temporal #sec-temporal.instant.prototype.until */
TO_BE_IMPLEMENTED(TemporalInstantPrototypeUntil) TO_BE_IMPLEMENTED(TemporalInstantPrototypeUntil)
/* Temporal #sec-temporal.instant.prototype.since */ /* Temporal #sec-temporal.instant.prototype.since */
...@@ -660,6 +656,8 @@ TEMPORAL_GET_BIGINT_AFTER_DIVID(Instant, EpochMicroseconds, nanoseconds, 1000, ...@@ -660,6 +656,8 @@ TEMPORAL_GET_BIGINT_AFTER_DIVID(Instant, EpochMicroseconds, nanoseconds, 1000,
epochMicroseconds) epochMicroseconds)
TEMPORAL_PROTOTYPE_METHOD1(Instant, ToZonedDateTime, toZonedDateTime) TEMPORAL_PROTOTYPE_METHOD1(Instant, ToZonedDateTime, toZonedDateTime)
TEMPORAL_PROTOTYPE_METHOD1(Instant, ToZonedDateTimeISO, toZonedDateTimeISO) TEMPORAL_PROTOTYPE_METHOD1(Instant, ToZonedDateTimeISO, toZonedDateTimeISO)
TEMPORAL_PROTOTYPE_METHOD1(Instant, Add, add)
TEMPORAL_PROTOTYPE_METHOD1(Instant, Subtract, subtract)
// Calendar // Calendar
TEMPORAL_CONSTRUCTOR1(Calendar) TEMPORAL_CONSTRUCTOR1(Calendar)
......
...@@ -2525,7 +2525,7 @@ MaybeHandle<JSTemporalPlainTime> ToTemporalTime(Isolate* isolate, ...@@ -2525,7 +2525,7 @@ MaybeHandle<JSTemporalPlainTime> ToTemporalTime(Isolate* isolate,
// This function implement // This function implement
// "For each row of Table 8, except the header row, in table order, do" // "For each row of Table 8, except the header row, in table order, do"
// loop. It is designed to be used to implement the common part of // loop. It is designed to be used to implement the common part of
// ToPartialDuration, ToLimitedTemporalDuration, ToTemporalDurationRecord // ToPartialDuration, ToTemporalDurationRecord
Maybe<bool> IterateDurationRecordFieldsTable( Maybe<bool> IterateDurationRecordFieldsTable(
Isolate* isolate, Handle<JSReceiver> temporal_duration_like, Isolate* isolate, Handle<JSReceiver> temporal_duration_like,
Maybe<bool> (*RowFunction)(Isolate*, Maybe<bool> (*RowFunction)(Isolate*,
...@@ -5426,13 +5426,22 @@ MaybeHandle<BigInt> AddInstant(Isolate* isolate, ...@@ -5426,13 +5426,22 @@ MaybeHandle<BigInt> AddInstant(Isolate* isolate,
bool IsValidEpochNanoseconds(Isolate* isolate, bool IsValidEpochNanoseconds(Isolate* isolate,
Handle<BigInt> epoch_nanoseconds) { Handle<BigInt> epoch_nanoseconds) {
TEMPORAL_ENTER_FUNC(); TEMPORAL_ENTER_FUNC();
// nsMinInstant = -nsMaxInstant = -8.64 × 10^21
constexpr double kNsMinInstant = -8.64e21;
// nsMaxInstant = 10^8 × nsPerDay = 8.64 × 1021
constexpr double kNsMaxInstant = 8.64e21;
// 1. Assert: Type(epochNanoseconds) is BigInt. // 1. Assert: Type(epochNanoseconds) is BigInt.
// 2. If epochNanoseconds < −86400ℤ × 10^17ℤ or epochNanoseconds > 86400ℤ × // 2. If ℝ(epochNanoseconds) < nsMinInstant or ℝ(epochNanoseconds) >
// 10^17ℤ, then a. Return false. // nsMaxInstant, then
// 3. Return true. if (BigInt::CompareToDouble(epoch_nanoseconds, kNsMinInstant) ==
int64_t ns = epoch_nanoseconds->AsInt64(); ComparisonResult::kLessThan ||
return !(ns < -86400 * 1e17 || ns > 86400 * 1e17); BigInt::CompareToDouble(epoch_nanoseconds, kNsMaxInstant) ==
ComparisonResult::kGreaterThan) {
// a. Return false.
return false;
}
return true;
} }
Handle<BigInt> GetEpochFromISOParts(Isolate* isolate, Handle<BigInt> GetEpochFromISOParts(Isolate* isolate,
...@@ -7381,10 +7390,11 @@ MaybeHandle<JSTemporalPlainMonthDay> JSTemporalCalendar::MonthDayFromFields( ...@@ -7381,10 +7390,11 @@ MaybeHandle<JSTemporalPlainMonthDay> JSTemporalCalendar::MonthDayFromFields(
JSTemporalPlainMonthDay); JSTemporalPlainMonthDay);
// 6. Let result be ? ISOMonthDayFromFields(fields, options). // 6. Let result be ? ISOMonthDayFromFields(fields, options).
if (calendar->calendar_index() == 0) { if (calendar->calendar_index() == 0) {
Maybe<DateRecordCommon> maybe_result = DateRecordCommon result;
ISOMonthDayFromFields(isolate, fields, options, method_name); MAYBE_ASSIGN_RETURN_ON_EXCEPTION_VALUE(
MAYBE_RETURN(maybe_result, Handle<JSTemporalPlainMonthDay>()); isolate, result,
DateRecordCommon result = maybe_result.FromJust(); ISOMonthDayFromFields(isolate, fields, options, method_name),
Handle<JSTemporalPlainMonthDay>());
// 7. Return ? CreateTemporalMonthDay(result.[[Month]], result.[[Day]], // 7. Return ? CreateTemporalMonthDay(result.[[Month]], result.[[Day]],
// calendar, result.[[ReferenceISOYear]]). // calendar, result.[[ReferenceISOYear]]).
return CreateTemporalMonthDay(isolate, result.month, result.day, calendar, return CreateTemporalMonthDay(isolate, result.month, result.day, calendar,
...@@ -12133,6 +12143,73 @@ MaybeHandle<JSTemporalZonedDateTime> JSTemporalInstant::ToZonedDateTimeISO( ...@@ -12133,6 +12143,73 @@ MaybeHandle<JSTemporalZonedDateTime> JSTemporalInstant::ToZonedDateTimeISO(
calendar); calendar);
} }
namespace {
// #sec-temporal-adddurationtoorsubtractdurationfrominstant
MaybeHandle<JSTemporalInstant> AddDurationToOrSubtractDurationFromInstant(
Isolate* isolate, Arithmetic operation, Handle<JSTemporalInstant> handle,
Handle<Object> temporal_duration_like, const char* method_name) {
TEMPORAL_ENTER_FUNC();
// 1. If operation is subtract, let sign be -1. Otherwise, let sign be 1.
double sign = operation == Arithmetic::kSubtract ? -1.0 : 1.0;
// See https://github.com/tc39/proposal-temporal/pull/2253
// 2. Let duration be ? ToTemporalDurationRecord(temporalDurationLike).
DurationRecord duration;
MAYBE_ASSIGN_RETURN_ON_EXCEPTION_VALUE(
isolate, duration,
temporal::ToTemporalDurationRecord(isolate, temporal_duration_like,
method_name),
Handle<JSTemporalInstant>());
TimeDurationRecord& time_duration = duration.time_duration;
if (time_duration.days != 0 || duration.months != 0 || duration.weeks != 0 ||
duration.years != 0) {
THROW_NEW_ERROR_RETURN_VALUE(isolate,
NEW_TEMPORAL_INVALID_ARG_RANGE_ERROR(),
Handle<JSTemporalInstant>());
}
// 3. Let ns be ? AddInstant(instant.[[EpochNanoseconds]], sign x
// duration.[[Hours]], sign x duration.[[Minutes]], sign x
// duration.[[Seconds]], sign x duration.[[Milliseconds]], sign x
// duration.[[Microseconds]], sign x duration.[[Nanoseconds]]).
Handle<BigInt> ns;
ASSIGN_RETURN_ON_EXCEPTION(
isolate, ns,
AddInstant(
isolate, Handle<BigInt>(handle->nanoseconds(), isolate),
{0, sign * time_duration.hours, sign * time_duration.minutes,
sign * time_duration.seconds, sign * time_duration.milliseconds,
sign * time_duration.microseconds,
sign * time_duration.nanoseconds}),
JSTemporalInstant);
// 4. Return ! CreateTemporalInstant(ns).
return temporal::CreateTemporalInstant(isolate, ns);
}
} // namespace
// #sec-temporal.instant.prototype.add
MaybeHandle<JSTemporalInstant> JSTemporalInstant::Add(
Isolate* isolate, Handle<JSTemporalInstant> handle,
Handle<Object> temporal_duration_like) {
TEMPORAL_ENTER_FUNC();
return AddDurationToOrSubtractDurationFromInstant(
isolate, Arithmetic::kAdd, handle, temporal_duration_like,
"Temporal.Instant.prototype.add");
}
// #sec-temporal.instant.prototype.subtract
MaybeHandle<JSTemporalInstant> JSTemporalInstant::Subtract(
Isolate* isolate, Handle<JSTemporalInstant> handle,
Handle<Object> temporal_duration_like) {
TEMPORAL_ENTER_FUNC();
return AddDurationToOrSubtractDurationFromInstant(
isolate, Arithmetic::kSubtract, handle, temporal_duration_like,
"Temporal.Instant.prototype.subtract");
}
namespace temporal { namespace temporal {
// Step iii and iv of #sec-temporal.calendar.prototype.fields // Step iii and iv of #sec-temporal.calendar.prototype.fields
......
...@@ -256,6 +256,16 @@ class JSTemporalInstant ...@@ -256,6 +256,16 @@ class JSTemporalInstant
Isolate* isolate, Handle<JSTemporalInstant> instant, Isolate* isolate, Handle<JSTemporalInstant> instant,
Handle<Object> other); Handle<Object> other);
// #sec-temporal.instant.prototype.add
V8_WARN_UNUSED_RESULT static MaybeHandle<JSTemporalInstant> Add(
Isolate* isolate, Handle<JSTemporalInstant> instant,
Handle<Object> temporal_duration_like);
// #sec-temporal.instant.prototype.subtract
V8_WARN_UNUSED_RESULT static MaybeHandle<JSTemporalInstant> Subtract(
Isolate* isolate, Handle<JSTemporalInstant> instant,
Handle<Object> temporal_duration_like);
DECL_PRINTER(JSTemporalInstant) DECL_PRINTER(JSTemporalInstant)
TQ_OBJECT_CONSTRUCTORS(JSTemporalInstant) TQ_OBJECT_CONSTRUCTORS(JSTemporalInstant)
......
...@@ -48,13 +48,9 @@ ...@@ -48,13 +48,9 @@
'temporal/calendar-week-of-year': [FAIL], 'temporal/calendar-week-of-year': [FAIL],
'temporal/duration-add': [FAIL], 'temporal/duration-add': [FAIL],
'temporal/duration-to-json': [FAIL], 'temporal/duration-to-json': [FAIL],
'temporal/instant-add': [FAIL],
'temporal/instant-constructor': [FAIL], 'temporal/instant-constructor': [FAIL],
'temporal/instant-from-epoch-microseconds': [FAIL],
'temporal/instant-from-epoch-milliseconds': [FAIL], 'temporal/instant-from-epoch-milliseconds': [FAIL],
'temporal/instant-from-epoch-nanoseconds': [FAIL],
'temporal/instant-from-epoch-seconds': [FAIL], 'temporal/instant-from-epoch-seconds': [FAIL],
'temporal/instant-subtract': [FAIL],
'temporal/instant-to-json': [FAIL], 'temporal/instant-to-json': [FAIL],
'temporal/instant-toJSON': [FAIL], 'temporal/instant-toJSON': [FAIL],
'temporal/plain-date-time-add': [FAIL], 'temporal/plain-date-time-add': [FAIL],
......
...@@ -542,15 +542,6 @@ ...@@ -542,15 +542,6 @@
'built-ins/Temporal/Instant/compare/instant-string': [FAIL], 'built-ins/Temporal/Instant/compare/instant-string': [FAIL],
'built-ins/Temporal/Instant/from/instant-string': [FAIL], 'built-ins/Temporal/Instant/from/instant-string': [FAIL],
'built-ins/Temporal/Instant/from/timezone-custom': [FAIL], 'built-ins/Temporal/Instant/from/timezone-custom': [FAIL],
'built-ins/Temporal/Instant/prototype/add/argument-string': [FAIL],
'built-ins/Temporal/Instant/prototype/add/argument-string-negative-fractional-units': [FAIL],
'built-ins/Temporal/Instant/prototype/add/branding': [FAIL],
'built-ins/Temporal/Instant/prototype/add/infinity-throws-rangeerror': [FAIL],
'built-ins/Temporal/Instant/prototype/add/negative-infinity-throws-rangeerror': [FAIL],
'built-ins/Temporal/Instant/prototype/add/non-integer-throws-rangeerror': [FAIL],
'built-ins/Temporal/Instant/prototype/add/order-of-operations': [FAIL],
'built-ins/Temporal/Instant/prototype/add/result-out-of-range': [FAIL],
'built-ins/Temporal/Instant/prototype/add/subclassing-ignored': [FAIL],
'built-ins/Temporal/Instant/prototype/equals/argument-wrong-type': [FAIL], 'built-ins/Temporal/Instant/prototype/equals/argument-wrong-type': [FAIL],
'built-ins/Temporal/Instant/prototype/equals/instant-string': [FAIL], 'built-ins/Temporal/Instant/prototype/equals/instant-string': [FAIL],
'built-ins/Temporal/Instant/prototype/round/branding': [FAIL], 'built-ins/Temporal/Instant/prototype/round/branding': [FAIL],
...@@ -590,15 +581,6 @@ ...@@ -590,15 +581,6 @@
'built-ins/Temporal/Instant/prototype/since/smallestunit-plurals-accepted': [FAIL], 'built-ins/Temporal/Instant/prototype/since/smallestunit-plurals-accepted': [FAIL],
'built-ins/Temporal/Instant/prototype/since/smallestunit-undefined': [FAIL], 'built-ins/Temporal/Instant/prototype/since/smallestunit-undefined': [FAIL],
'built-ins/Temporal/Instant/prototype/since/smallestunit-wrong-type': [FAIL], 'built-ins/Temporal/Instant/prototype/since/smallestunit-wrong-type': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/argument-string': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/argument-string-negative-fractional-units': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/branding': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/infinity-throws-rangeerror': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/negative-infinity-throws-rangeerror': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/non-integer-throws-rangeerror': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/order-of-operations': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/result-out-of-range': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/subclassing-ignored': [FAIL],
'built-ins/Temporal/Instant/prototype/toJSON/basic': [FAIL], 'built-ins/Temporal/Instant/prototype/toJSON/basic': [FAIL],
'built-ins/Temporal/Instant/prototype/toJSON/branding': [FAIL], 'built-ins/Temporal/Instant/prototype/toJSON/branding': [FAIL],
'built-ins/Temporal/Instant/prototype/toJSON/negative-epochnanoseconds': [FAIL], 'built-ins/Temporal/Instant/prototype/toJSON/negative-epochnanoseconds': [FAIL],
...@@ -1437,10 +1419,8 @@ ...@@ -1437,10 +1419,8 @@
'built-ins/Temporal/Duration/prototype/toString/fractionalseconddigits-exact-number-of-digits': [FAIL], 'built-ins/Temporal/Duration/prototype/toString/fractionalseconddigits-exact-number-of-digits': [FAIL],
'built-ins/Temporal/Duration/prototype/total/calendar-possibly-required': [FAIL], 'built-ins/Temporal/Duration/prototype/total/calendar-possibly-required': [FAIL],
'built-ins/Temporal/Duration/prototype/total/year-zero': [FAIL], 'built-ins/Temporal/Duration/prototype/total/year-zero': [FAIL],
'built-ins/Temporal/Instant/prototype/add/argument-string-fractional-units-rounding-mode': [FAIL],
'built-ins/Temporal/Instant/prototype/since/largestunit-smallestunit-mismatch': [FAIL], 'built-ins/Temporal/Instant/prototype/since/largestunit-smallestunit-mismatch': [FAIL],
'built-ins/Temporal/Instant/prototype/since/year-zero': [FAIL], 'built-ins/Temporal/Instant/prototype/since/year-zero': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/argument-string-fractional-units-rounding-mode': [FAIL],
'built-ins/Temporal/Instant/prototype/until/largestunit-smallestunit-mismatch': [FAIL], 'built-ins/Temporal/Instant/prototype/until/largestunit-smallestunit-mismatch': [FAIL],
'built-ins/Temporal/Instant/prototype/until/year-zero': [FAIL], 'built-ins/Temporal/Instant/prototype/until/year-zero': [FAIL],
'built-ins/Temporal/PlainDate/prototype/since/days-in-month': [FAIL], 'built-ins/Temporal/PlainDate/prototype/since/days-in-month': [FAIL],
...@@ -1636,10 +1616,6 @@ ...@@ -1636,10 +1616,6 @@
'built-ins/Temporal/Duration/compare/twenty-five-hour-day': [FAIL], 'built-ins/Temporal/Duration/compare/twenty-five-hour-day': [FAIL],
'built-ins/Temporal/Duration/prototype/toJSON/basic': [FAIL], 'built-ins/Temporal/Duration/prototype/toJSON/basic': [FAIL],
'built-ins/Temporal/Duration/prototype/toString/balance': [FAIL], 'built-ins/Temporal/Duration/prototype/toString/balance': [FAIL],
'built-ins/Temporal/Instant/prototype/add/basic': [FAIL],
'built-ins/Temporal/Instant/prototype/add/disallowed-duration-units': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/basic': [FAIL],
'built-ins/Temporal/Instant/prototype/subtract/disallowed-duration-units': [FAIL],
'built-ins/Temporal/PlainDate/prototype/since/argument-string-invalid': [FAIL], 'built-ins/Temporal/PlainDate/prototype/since/argument-string-invalid': [FAIL],
'built-ins/Temporal/PlainDate/prototype/until/argument-string-invalid': [FAIL], 'built-ins/Temporal/PlainDate/prototype/until/argument-string-invalid': [FAIL],
'built-ins/Temporal/PlainDateTime/datetime-math': [FAIL], 'built-ins/Temporal/PlainDateTime/datetime-math': [FAIL],
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment