LCOV - code coverage report
Current view: top level - src/builtins - builtins-date.cc (source / functions) Hit Total Coverage
Test: app.info Lines: 380 385 98.7 %
Date: 2019-03-21 Functions: 70 100 70.0 %

          Line data    Source code
       1             : // Copyright 2016 the V8 project authors. All rights reserved.
       2             : // Use of this source code is governed by a BSD-style license that can be
       3             : // found in the LICENSE file.
       4             : 
       5             : #include "src/builtins/builtins-utils-inl.h"
       6             : #include "src/builtins/builtins.h"
       7             : #include "src/code-factory.h"
       8             : #include "src/conversions.h"
       9             : #include "src/counters.h"
      10             : #include "src/date.h"
      11             : #include "src/dateparser-inl.h"
      12             : #include "src/objects-inl.h"
      13             : #ifdef V8_INTL_SUPPORT
      14             : #include "src/objects/intl-objects.h"
      15             : #include "src/objects/js-date-time-format.h"
      16             : #endif
      17             : #include "src/string-stream.h"
      18             : 
      19             : namespace v8 {
      20             : namespace internal {
      21             : 
      22             : // -----------------------------------------------------------------------------
      23             : // ES6 section 20.3 Date Objects
      24             : 
      25             : namespace {
      26             : 
      27             : // ES6 section 20.3.1.1 Time Values and Time Range
      28             : const double kMinYear = -1000000.0;
      29             : const double kMaxYear = -kMinYear;
      30             : const double kMinMonth = -10000000.0;
      31             : const double kMaxMonth = -kMinMonth;
      32             : 
      33             : // 20.3.1.2 Day Number and Time within Day
      34             : const double kMsPerDay = 86400000.0;
      35             : 
      36             : // ES6 section 20.3.1.11 Hours, Minutes, Second, and Milliseconds
      37             : const double kMsPerSecond = 1000.0;
      38             : const double kMsPerMinute = 60000.0;
      39             : const double kMsPerHour = 3600000.0;
      40             : 
      41             : // ES6 section 20.3.1.14 MakeDate (day, time)
      42             : double MakeDate(double day, double time) {
      43      143564 :   if (std::isfinite(day) && std::isfinite(time)) {
      44       62377 :     return time + day * kMsPerDay;
      45             :   }
      46             :   return std::numeric_limits<double>::quiet_NaN();
      47             : }
      48             : 
      49             : // ES6 section 20.3.1.13 MakeDay (year, month, date)
      50       64321 : double MakeDay(double year, double month, double date) {
      51      127778 :   if ((kMinYear <= year && year <= kMaxYear) &&
      52      189390 :       (kMinMonth <= month && month <= kMaxMonth) && std::isfinite(date)) {
      53             :     int y = FastD2I(year);
      54             :     int m = FastD2I(month);
      55       62233 :     y += m / 12;
      56       62233 :     m %= 12;
      57       62233 :     if (m < 0) {
      58           9 :       m += 12;
      59           9 :       y -= 1;
      60             :     }
      61             :     DCHECK_LE(0, m);
      62             :     DCHECK_LT(m, 12);
      63             : 
      64             :     // kYearDelta is an arbitrary number such that:
      65             :     // a) kYearDelta = -1 (mod 400)
      66             :     // b) year + kYearDelta > 0 for years in the range defined by
      67             :     //    ECMA 262 - 15.9.1.1, i.e. upto 100,000,000 days on either side of
      68             :     //    Jan 1 1970. This is required so that we don't run into integer
      69             :     //    division of negative numbers.
      70             :     // c) there shouldn't be an overflow for 32-bit integers in the following
      71             :     //    operations.
      72             :     static const int kYearDelta = 399999;
      73             :     static const int kBaseDay =
      74             :         365 * (1970 + kYearDelta) + (1970 + kYearDelta) / 4 -
      75             :         (1970 + kYearDelta) / 100 + (1970 + kYearDelta) / 400;
      76      124466 :     int day_from_year = 365 * (y + kYearDelta) + (y + kYearDelta) / 4 -
      77      124466 :                         (y + kYearDelta) / 100 + (y + kYearDelta) / 400 -
      78       62233 :                         kBaseDay;
      79       62233 :     if ((y % 4 != 0) || (y % 100 == 0 && y % 400 != 0)) {
      80             :       static const int kDayFromMonth[] = {0,   31,  59,  90,  120, 151,
      81             :                                           181, 212, 243, 273, 304, 334};
      82       45218 :       day_from_year += kDayFromMonth[m];
      83             :     } else {
      84             :       static const int kDayFromMonth[] = {0,   31,  60,  91,  121, 152,
      85             :                                           182, 213, 244, 274, 305, 335};
      86       17015 :       day_from_year += kDayFromMonth[m];
      87             :     }
      88       62233 :     return static_cast<double>(day_from_year - 1) + DoubleToInteger(date);
      89             :   }
      90             :   return std::numeric_limits<double>::quiet_NaN();
      91             : }
      92             : 
      93             : // ES6 section 20.3.1.12 MakeTime (hour, min, sec, ms)
      94       70567 : double MakeTime(double hour, double min, double sec, double ms) {
      95      262819 :   if (std::isfinite(hour) && std::isfinite(min) && std::isfinite(sec) &&
      96             :       std::isfinite(ms)) {
      97       62206 :     double const h = DoubleToInteger(hour);
      98       62206 :     double const m = DoubleToInteger(min);
      99       62206 :     double const s = DoubleToInteger(sec);
     100       62206 :     double const milli = DoubleToInteger(ms);
     101       62206 :     return h * kMsPerHour + m * kMsPerMinute + s * kMsPerSecond + milli;
     102             :   }
     103             :   return std::numeric_limits<double>::quiet_NaN();
     104             : }
     105             : 
     106             : const char* kShortWeekDays[] = {"Sun", "Mon", "Tue", "Wed",
     107             :                                 "Thu", "Fri", "Sat"};
     108             : const char* kShortMonths[] = {"Jan", "Feb", "Mar", "Apr", "May", "Jun",
     109             :                               "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"};
     110             : 
     111             : // ES6 section 20.3.1.16 Date Time String Format
     112       58351 : double ParseDateTimeString(Isolate* isolate, Handle<String> str) {
     113       58351 :   str = String::Flatten(isolate, str);
     114             :   // TODO(bmeurer): Change DateParser to not use the FixedArray.
     115             :   Handle<FixedArray> tmp =
     116       58351 :       isolate->factory()->NewFixedArray(DateParser::OUTPUT_SIZE);
     117             :   DisallowHeapAllocation no_gc;
     118       58351 :   String::FlatContent str_content = str->GetFlatContent(no_gc);
     119             :   bool result;
     120       58351 :   if (str_content.IsOneByte()) {
     121       58351 :     result = DateParser::Parse(isolate, str_content.ToOneByteVector(), *tmp);
     122             :   } else {
     123           0 :     result = DateParser::Parse(isolate, str_content.ToUC16Vector(), *tmp);
     124             :   }
     125       58351 :   if (!result) return std::numeric_limits<double>::quiet_NaN();
     126             :   double const day = MakeDay(tmp->get(0)->Number(), tmp->get(1)->Number(),
     127       57837 :                              tmp->get(2)->Number());
     128             :   double const time = MakeTime(tmp->get(3)->Number(), tmp->get(4)->Number(),
     129       57837 :                                tmp->get(5)->Number(), tmp->get(6)->Number());
     130             :   double date = MakeDate(day, time);
     131       57837 :   if (tmp->get(7)->IsNull(isolate)) {
     132         529 :     if (date >= -DateCache::kMaxTimeBeforeUTCInMs &&
     133             :         date <= DateCache::kMaxTimeBeforeUTCInMs) {
     134        1022 :       date = isolate->date_cache()->ToUTC(static_cast<int64_t>(date));
     135             :     } else {
     136             :       return std::numeric_limits<double>::quiet_NaN();
     137             :     }
     138             :   } else {
     139       57308 :     date -= tmp->get(7)->Number() * 1000.0;
     140             :   }
     141       57819 :   return DateCache::TimeClip(date);
     142             : }
     143             : 
     144             : enum ToDateStringMode { kDateOnly, kTimeOnly, kDateAndTime };
     145             : 
     146             : typedef base::SmallVector<char, 128> DateBuffer;
     147             : 
     148             : template <class... Args>
     149       53469 : DateBuffer FormatDate(const char* format, Args... args) {
     150             :   DateBuffer buffer;
     151             :   SmallStringOptimizedAllocator<DateBuffer::kInlineSize> allocator(&buffer);
     152             :   StringStream sstream(&allocator);
     153       53469 :   sstream.Add(format, args...);
     154       53469 :   buffer.resize_no_init(sstream.length());
     155       53469 :   return buffer;
     156             : }
     157             : 
     158             : // ES6 section 20.3.4.41.1 ToDateString(tv)
     159       53469 : DateBuffer ToDateString(double time_val, DateCache* date_cache,
     160             :                         ToDateStringMode mode = kDateAndTime) {
     161       53469 :   if (std::isnan(time_val)) {
     162          63 :     return FormatDate("Invalid Date");
     163             :   }
     164       53406 :   int64_t time_ms = static_cast<int64_t>(time_val);
     165             :   int64_t local_time_ms = date_cache->ToLocal(time_ms);
     166             :   int year, month, day, weekday, hour, min, sec, ms;
     167             :   date_cache->BreakDownTime(local_time_ms, &year, &month, &day, &weekday, &hour,
     168       53406 :                             &min, &sec, &ms);
     169       53406 :   int timezone_offset = -date_cache->TimezoneOffset(time_ms);
     170       53406 :   int timezone_hour = std::abs(timezone_offset) / 60;
     171       53406 :   int timezone_min = std::abs(timezone_offset) % 60;
     172       53406 :   const char* local_timezone = date_cache->LocalTimezone(time_ms);
     173       53406 :   switch (mode) {
     174             :     case kDateOnly:
     175             :       return FormatDate("%s %s %02d %04d", kShortWeekDays[weekday],
     176          18 :                         kShortMonths[month], day, year);
     177             :     case kTimeOnly:
     178             :       return FormatDate("%02d:%02d:%02d GMT%c%02d%02d (%s)", hour, min, sec,
     179             :                         (timezone_offset < 0) ? '-' : '+', timezone_hour,
     180           9 :                         timezone_min, local_timezone);
     181             :     case kDateAndTime:
     182             :       return FormatDate("%s %s %02d %04d %02d:%02d:%02d GMT%c%02d%02d (%s)",
     183             :                         kShortWeekDays[weekday], kShortMonths[month], day, year,
     184             :                         hour, min, sec, (timezone_offset < 0) ? '-' : '+',
     185       53379 :                         timezone_hour, timezone_min, local_timezone);
     186             :   }
     187           0 :   UNREACHABLE();
     188             : }
     189             : 
     190        5814 : Object SetLocalDateValue(Isolate* isolate, Handle<JSDate> date,
     191             :                          double time_val) {
     192        5814 :   if (time_val >= -DateCache::kMaxTimeBeforeUTCInMs &&
     193             :       time_val <= DateCache::kMaxTimeBeforeUTCInMs) {
     194         684 :     time_val = isolate->date_cache()->ToUTC(static_cast<int64_t>(time_val));
     195             :   } else {
     196             :     time_val = std::numeric_limits<double>::quiet_NaN();
     197             :   }
     198       11628 :   return *JSDate::SetValue(date, DateCache::TimeClip(time_val));
     199             : }
     200             : 
     201             : }  // namespace
     202             : 
     203             : // ES #sec-date-constructor
     204      744665 : BUILTIN(DateConstructor) {
     205             :   HandleScope scope(isolate);
     206      148933 :   if (args.new_target()->IsUndefined(isolate)) {
     207          36 :     double const time_val = JSDate::CurrentTimeValue(isolate);
     208          36 :     DateBuffer buffer = ToDateString(time_val, isolate->date_cache());
     209          72 :     RETURN_RESULT_OR_FAILURE(
     210             :         isolate, isolate->factory()->NewStringFromUtf8(VectorOf(buffer)));
     211             :   }
     212             :   // [Construct]
     213      148897 :   int const argc = args.length() - 1;
     214      148897 :   Handle<JSFunction> target = args.target();
     215      148897 :   Handle<JSReceiver> new_target = Handle<JSReceiver>::cast(args.new_target());
     216             :   double time_val;
     217      148897 :   if (argc == 0) {
     218       91291 :     time_val = JSDate::CurrentTimeValue(isolate);
     219       57606 :   } else if (argc == 1) {
     220             :     Handle<Object> value = args.at(1);
     221       55227 :     if (value->IsJSDate()) {
     222             :       time_val = Handle<JSDate>::cast(value)->value()->Number();
     223             :     } else {
     224      110139 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, value,
     225             :                                          Object::ToPrimitive(value));
     226       55056 :       if (value->IsString()) {
     227         375 :         time_val = ParseDateTimeString(isolate, Handle<String>::cast(value));
     228             :       } else {
     229      109362 :         ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, value,
     230             :                                            Object::ToNumber(isolate, value));
     231             :         time_val = value->Number();
     232             :       }
     233             :     }
     234             :   } else {
     235             :     Handle<Object> year_object;
     236        4758 :     ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, year_object,
     237             :                                        Object::ToNumber(isolate, args.at(1)));
     238             :     Handle<Object> month_object;
     239        4758 :     ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, month_object,
     240             :                                        Object::ToNumber(isolate, args.at(2)));
     241             :     double year = year_object->Number();
     242             :     double month = month_object->Number();
     243             :     double date = 1.0, hours = 0.0, minutes = 0.0, seconds = 0.0, ms = 0.0;
     244        2379 :     if (argc >= 3) {
     245             :       Handle<Object> date_object;
     246        4578 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, date_object,
     247             :                                          Object::ToNumber(isolate, args.at(3)));
     248             :       date = date_object->Number();
     249        2289 :       if (argc >= 4) {
     250             :         Handle<Object> hours_object;
     251        4122 :         ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     252             :             isolate, hours_object, Object::ToNumber(isolate, args.at(4)));
     253             :         hours = hours_object->Number();
     254        2061 :         if (argc >= 5) {
     255             :           Handle<Object> minutes_object;
     256        2304 :           ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     257             :               isolate, minutes_object, Object::ToNumber(isolate, args.at(5)));
     258             :           minutes = minutes_object->Number();
     259        1152 :           if (argc >= 6) {
     260             :             Handle<Object> seconds_object;
     261         450 :             ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     262             :                 isolate, seconds_object, Object::ToNumber(isolate, args.at(6)));
     263             :             seconds = seconds_object->Number();
     264         225 :             if (argc >= 7) {
     265             :               Handle<Object> ms_object;
     266         378 :               ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     267             :                   isolate, ms_object, Object::ToNumber(isolate, args.at(7)));
     268             :               ms = ms_object->Number();
     269             :             }
     270             :           }
     271             :         }
     272             :       }
     273             :     }
     274        2379 :     if (!std::isnan(year)) {
     275        2361 :       double const y = DoubleToInteger(year);
     276        2361 :       if (0.0 <= y && y <= 99) year = 1900 + y;
     277             :     }
     278        2379 :     double const day = MakeDay(year, month, date);
     279        2379 :     double const time = MakeTime(hours, minutes, seconds, ms);
     280             :     time_val = MakeDate(day, time);
     281        2379 :     if (time_val >= -DateCache::kMaxTimeBeforeUTCInMs &&
     282             :         time_val <= DateCache::kMaxTimeBeforeUTCInMs) {
     283        4398 :       time_val = isolate->date_cache()->ToUTC(static_cast<int64_t>(time_val));
     284             :     } else {
     285             :       time_val = std::numeric_limits<double>::quiet_NaN();
     286             :     }
     287             :   }
     288      297776 :   RETURN_RESULT_OR_FAILURE(isolate, JSDate::New(target, new_target, time_val));
     289             : }
     290             : 
     291             : // ES6 section 20.3.3.1 Date.now ( )
     292     1780955 : BUILTIN(DateNow) {
     293             :   HandleScope scope(isolate);
     294     1068573 :   return *isolate->factory()->NewNumber(JSDate::CurrentTimeValue(isolate));
     295             : }
     296             : 
     297             : // ES6 section 20.3.3.2 Date.parse ( string )
     298      289880 : BUILTIN(DateParse) {
     299             :   HandleScope scope(isolate);
     300             :   Handle<String> string;
     301      115952 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     302             :       isolate, string,
     303             :       Object::ToString(isolate, args.atOrUndefined(isolate, 1)));
     304      115952 :   return *isolate->factory()->NewNumber(ParseDateTimeString(isolate, string));
     305             : }
     306             : 
     307             : // ES6 section 20.3.3.4 Date.UTC (year,month,date,hours,minutes,seconds,ms)
     308        9230 : BUILTIN(DateUTC) {
     309             :   HandleScope scope(isolate);
     310        1846 :   int const argc = args.length() - 1;
     311             :   double year = std::numeric_limits<double>::quiet_NaN();
     312             :   double month = 0.0, date = 1.0, hours = 0.0, minutes = 0.0, seconds = 0.0,
     313             :          ms = 0.0;
     314        1846 :   if (argc >= 1) {
     315             :     Handle<Object> year_object;
     316        3692 :     ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, year_object,
     317             :                                        Object::ToNumber(isolate, args.at(1)));
     318             :     year = year_object->Number();
     319        1846 :     if (argc >= 2) {
     320             :       Handle<Object> month_object;
     321        3692 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, month_object,
     322             :                                          Object::ToNumber(isolate, args.at(2)));
     323             :       month = month_object->Number();
     324        1846 :       if (argc >= 3) {
     325             :         Handle<Object> date_object;
     326        3692 :         ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     327             :             isolate, date_object, Object::ToNumber(isolate, args.at(3)));
     328             :         date = date_object->Number();
     329        1846 :         if (argc >= 4) {
     330             :           Handle<Object> hours_object;
     331        3546 :           ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     332             :               isolate, hours_object, Object::ToNumber(isolate, args.at(4)));
     333             :           hours = hours_object->Number();
     334        1773 :           if (argc >= 5) {
     335             :             Handle<Object> minutes_object;
     336        1872 :             ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     337             :                 isolate, minutes_object, Object::ToNumber(isolate, args.at(5)));
     338             :             minutes = minutes_object->Number();
     339         936 :             if (argc >= 6) {
     340             :               Handle<Object> seconds_object;
     341         234 :               ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     342             :                   isolate, seconds_object,
     343             :                   Object::ToNumber(isolate, args.at(6)));
     344             :               seconds = seconds_object->Number();
     345         117 :               if (argc >= 7) {
     346             :                 Handle<Object> ms_object;
     347         198 :                 ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     348             :                     isolate, ms_object, Object::ToNumber(isolate, args.at(7)));
     349             :                 ms = ms_object->Number();
     350             :               }
     351             :             }
     352             :           }
     353             :         }
     354             :       }
     355             :     }
     356             :   }
     357        1846 :   if (!std::isnan(year)) {
     358        1846 :     double const y = DoubleToInteger(year);
     359        1846 :     if (0.0 <= y && y <= 99) year = 1900 + y;
     360             :   }
     361        1846 :   double const day = MakeDay(year, month, date);
     362        1846 :   double const time = MakeTime(hours, minutes, seconds, ms);
     363        3692 :   return *isolate->factory()->NewNumber(
     364        1846 :       DateCache::TimeClip(MakeDate(day, time)));
     365             : }
     366             : 
     367             : // ES6 section 20.3.4.20 Date.prototype.setDate ( date )
     368        1350 : BUILTIN(DatePrototypeSetDate) {
     369             :   HandleScope scope(isolate);
     370         783 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setDate");
     371             :   Handle<Object> value = args.atOrUndefined(isolate, 1);
     372         198 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, value,
     373             :                                      Object::ToNumber(isolate, value));
     374             :   double time_val = date->value()->Number();
     375          99 :   if (!std::isnan(time_val)) {
     376          81 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     377             :     int64_t local_time_ms = isolate->date_cache()->ToLocal(time_ms);
     378             :     int const days = isolate->date_cache()->DaysFromTime(local_time_ms);
     379             :     int time_within_day = isolate->date_cache()->TimeInDay(local_time_ms, days);
     380             :     int year, month, day;
     381          81 :     isolate->date_cache()->YearMonthDayFromDays(days, &year, &month, &day);
     382         162 :     time_val = MakeDate(MakeDay(year, month, value->Number()), time_within_day);
     383             :   }
     384          99 :   return SetLocalDateValue(isolate, date, time_val);
     385             : }
     386             : 
     387             : // ES6 section 20.3.4.21 Date.prototype.setFullYear (year, month, date)
     388        4725 : BUILTIN(DatePrototypeSetFullYear) {
     389             :   HandleScope scope(isolate);
     390        1431 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setFullYear");
     391         783 :   int const argc = args.length() - 1;
     392             :   Handle<Object> year = args.atOrUndefined(isolate, 1);
     393        1566 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, year,
     394             :                                      Object::ToNumber(isolate, year));
     395             :   double y = year->Number(), m = 0.0, dt = 1.0;
     396             :   int time_within_day = 0;
     397         783 :   if (!std::isnan(date->value()->Number())) {
     398         765 :     int64_t const time_ms = static_cast<int64_t>(date->value()->Number());
     399             :     int64_t local_time_ms = isolate->date_cache()->ToLocal(time_ms);
     400             :     int const days = isolate->date_cache()->DaysFromTime(local_time_ms);
     401             :     time_within_day = isolate->date_cache()->TimeInDay(local_time_ms, days);
     402             :     int year, month, day;
     403         765 :     isolate->date_cache()->YearMonthDayFromDays(days, &year, &month, &day);
     404         765 :     m = month;
     405         765 :     dt = day;
     406             :   }
     407         783 :   if (argc >= 2) {
     408             :     Handle<Object> month = args.at(2);
     409        1422 :     ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, month,
     410             :                                        Object::ToNumber(isolate, month));
     411             :     m = month->Number();
     412         711 :     if (argc >= 3) {
     413             :       Handle<Object> date = args.at(3);
     414        1152 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, date,
     415             :                                          Object::ToNumber(isolate, date));
     416             :       dt = date->Number();
     417             :     }
     418             :   }
     419         783 :   double time_val = MakeDate(MakeDay(y, m, dt), time_within_day);
     420         783 :   return SetLocalDateValue(isolate, date, time_val);
     421             : }
     422             : 
     423             : // ES6 section 20.3.4.22 Date.prototype.setHours(hour, min, sec, ms)
     424       16515 : BUILTIN(DatePrototypeSetHours) {
     425             :   HandleScope scope(isolate);
     426        3816 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setHours");
     427        3132 :   int const argc = args.length() - 1;
     428             :   Handle<Object> hour = args.atOrUndefined(isolate, 1);
     429        6264 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, hour,
     430             :                                      Object::ToNumber(isolate, hour));
     431             :   double h = hour->Number();
     432             :   double time_val = date->value()->Number();
     433        3132 :   if (!std::isnan(time_val)) {
     434        3087 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     435             :     int64_t local_time_ms = isolate->date_cache()->ToLocal(time_ms);
     436             :     int day = isolate->date_cache()->DaysFromTime(local_time_ms);
     437             :     int time_within_day = isolate->date_cache()->TimeInDay(local_time_ms, day);
     438        3087 :     double m = (time_within_day / (60 * 1000)) % 60;
     439        3087 :     double s = (time_within_day / 1000) % 60;
     440        3087 :     double milli = time_within_day % 1000;
     441        3087 :     if (argc >= 2) {
     442             :       Handle<Object> min = args.at(2);
     443        6048 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, min,
     444             :                                          Object::ToNumber(isolate, min));
     445             :       m = min->Number();
     446        3024 :       if (argc >= 3) {
     447             :         Handle<Object> sec = args.at(3);
     448        5760 :         ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, sec,
     449             :                                            Object::ToNumber(isolate, sec));
     450             :         s = sec->Number();
     451        2880 :         if (argc >= 4) {
     452             :           Handle<Object> ms = args.at(4);
     453        4608 :           ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, ms,
     454             :                                              Object::ToNumber(isolate, ms));
     455             :           milli = ms->Number();
     456             :         }
     457             :       }
     458             :     }
     459        3087 :     time_val = MakeDate(day, MakeTime(h, m, s, milli));
     460             :   }
     461        3132 :   return SetLocalDateValue(isolate, date, time_val);
     462             : }
     463             : 
     464             : // ES6 section 20.3.4.23 Date.prototype.setMilliseconds(ms)
     465        2610 : BUILTIN(DatePrototypeSetMilliseconds) {
     466             :   HandleScope scope(isolate);
     467        1008 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setMilliseconds");
     468             :   Handle<Object> ms = args.atOrUndefined(isolate, 1);
     469         720 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, ms,
     470             :                                      Object::ToNumber(isolate, ms));
     471             :   double time_val = date->value()->Number();
     472         360 :   if (!std::isnan(time_val)) {
     473         342 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     474             :     int64_t local_time_ms = isolate->date_cache()->ToLocal(time_ms);
     475             :     int day = isolate->date_cache()->DaysFromTime(local_time_ms);
     476             :     int time_within_day = isolate->date_cache()->TimeInDay(local_time_ms, day);
     477         342 :     int h = time_within_day / (60 * 60 * 1000);
     478         342 :     int m = (time_within_day / (60 * 1000)) % 60;
     479         342 :     int s = (time_within_day / 1000) % 60;
     480         342 :     time_val = MakeDate(day, MakeTime(h, m, s, ms->Number()));
     481             :   }
     482         360 :   return SetLocalDateValue(isolate, date, time_val);
     483             : }
     484             : 
     485             : // ES6 section 20.3.4.24 Date.prototype.setMinutes ( min, sec, ms )
     486        4905 : BUILTIN(DatePrototypeSetMinutes) {
     487             :   HandleScope scope(isolate);
     488        1467 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setMinutes");
     489         819 :   int const argc = args.length() - 1;
     490             :   Handle<Object> min = args.atOrUndefined(isolate, 1);
     491        1638 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, min,
     492             :                                      Object::ToNumber(isolate, min));
     493             :   double time_val = date->value()->Number();
     494         819 :   if (!std::isnan(time_val)) {
     495         783 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     496             :     int64_t local_time_ms = isolate->date_cache()->ToLocal(time_ms);
     497             :     int day = isolate->date_cache()->DaysFromTime(local_time_ms);
     498             :     int time_within_day = isolate->date_cache()->TimeInDay(local_time_ms, day);
     499         783 :     int h = time_within_day / (60 * 60 * 1000);
     500             :     double m = min->Number();
     501         783 :     double s = (time_within_day / 1000) % 60;
     502         783 :     double milli = time_within_day % 1000;
     503         783 :     if (argc >= 2) {
     504             :       Handle<Object> sec = args.at(2);
     505        1440 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, sec,
     506             :                                          Object::ToNumber(isolate, sec));
     507             :       s = sec->Number();
     508         720 :       if (argc >= 3) {
     509             :         Handle<Object> ms = args.at(3);
     510        1152 :         ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, ms,
     511             :                                            Object::ToNumber(isolate, ms));
     512             :         milli = ms->Number();
     513             :       }
     514             :     }
     515         783 :     time_val = MakeDate(day, MakeTime(h, m, s, milli));
     516             :   }
     517         819 :   return SetLocalDateValue(isolate, date, time_val);
     518             : }
     519             : 
     520             : // ES6 section 20.3.4.25 Date.prototype.setMonth ( month, date )
     521        2025 : BUILTIN(DatePrototypeSetMonth) {
     522             :   HandleScope scope(isolate);
     523         891 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setMonth");
     524             :   int const argc = args.length() - 1;
     525             :   Handle<Object> month = args.atOrUndefined(isolate, 1);
     526         486 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, month,
     527             :                                      Object::ToNumber(isolate, month));
     528             :   double time_val = date->value()->Number();
     529         243 :   if (!std::isnan(time_val)) {
     530         216 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     531             :     int64_t local_time_ms = isolate->date_cache()->ToLocal(time_ms);
     532             :     int days = isolate->date_cache()->DaysFromTime(local_time_ms);
     533             :     int time_within_day = isolate->date_cache()->TimeInDay(local_time_ms, days);
     534             :     int year, unused, day;
     535         216 :     isolate->date_cache()->YearMonthDayFromDays(days, &year, &unused, &day);
     536             :     double m = month->Number();
     537         216 :     double dt = day;
     538         216 :     if (argc >= 2) {
     539             :       Handle<Object> date = args.at(2);
     540         288 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, date,
     541             :                                          Object::ToNumber(isolate, date));
     542             :       dt = date->Number();
     543             :     }
     544         216 :     time_val = MakeDate(MakeDay(year, m, dt), time_within_day);
     545             :   }
     546         243 :   return SetLocalDateValue(isolate, date, time_val);
     547             : }
     548             : 
     549             : // ES6 section 20.3.4.26 Date.prototype.setSeconds ( sec, ms )
     550        2025 : BUILTIN(DatePrototypeSetSeconds) {
     551             :   HandleScope scope(isolate);
     552         891 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setSeconds");
     553             :   int const argc = args.length() - 1;
     554             :   Handle<Object> sec = args.atOrUndefined(isolate, 1);
     555         486 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, sec,
     556             :                                      Object::ToNumber(isolate, sec));
     557             :   double time_val = date->value()->Number();
     558         243 :   if (!std::isnan(time_val)) {
     559         216 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     560             :     int64_t local_time_ms = isolate->date_cache()->ToLocal(time_ms);
     561             :     int day = isolate->date_cache()->DaysFromTime(local_time_ms);
     562             :     int time_within_day = isolate->date_cache()->TimeInDay(local_time_ms, day);
     563         216 :     int h = time_within_day / (60 * 60 * 1000);
     564         216 :     double m = (time_within_day / (60 * 1000)) % 60;
     565             :     double s = sec->Number();
     566         216 :     double milli = time_within_day % 1000;
     567         216 :     if (argc >= 2) {
     568             :       Handle<Object> ms = args.at(2);
     569         306 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, ms,
     570             :                                          Object::ToNumber(isolate, ms));
     571             :       milli = ms->Number();
     572             :     }
     573         216 :     time_val = MakeDate(day, MakeTime(h, m, s, milli));
     574             :   }
     575         243 :   return SetLocalDateValue(isolate, date, time_val);
     576             : }
     577             : 
     578             : // ES6 section 20.3.4.27 Date.prototype.setTime ( time )
     579        1170 : BUILTIN(DatePrototypeSetTime) {
     580             :   HandleScope scope(isolate);
     581         747 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setTime");
     582             :   Handle<Object> value = args.atOrUndefined(isolate, 1);
     583         126 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, value,
     584             :                                      Object::ToNumber(isolate, value));
     585         126 :   return *JSDate::SetValue(date, DateCache::TimeClip(value->Number()));
     586             : }
     587             : 
     588             : // ES6 section 20.3.4.28 Date.prototype.setUTCDate ( date )
     589        1215 : BUILTIN(DatePrototypeSetUTCDate) {
     590             :   HandleScope scope(isolate);
     591         729 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setUTCDate");
     592             :   Handle<Object> value = args.atOrUndefined(isolate, 1);
     593         162 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, value,
     594             :                                      Object::ToNumber(isolate, value));
     595          81 :   if (std::isnan(date->value()->Number())) return date->value();
     596          63 :   int64_t const time_ms = static_cast<int64_t>(date->value()->Number());
     597             :   int const days = isolate->date_cache()->DaysFromTime(time_ms);
     598             :   int const time_within_day = isolate->date_cache()->TimeInDay(time_ms, days);
     599             :   int year, month, day;
     600          63 :   isolate->date_cache()->YearMonthDayFromDays(days, &year, &month, &day);
     601             :   double const time_val =
     602         126 :       MakeDate(MakeDay(year, month, value->Number()), time_within_day);
     603         126 :   return *JSDate::SetValue(date, DateCache::TimeClip(time_val));
     604             : }
     605             : 
     606             : // ES6 section 20.3.4.29 Date.prototype.setUTCFullYear (year, month, date)
     607        4725 : BUILTIN(DatePrototypeSetUTCFullYear) {
     608             :   HandleScope scope(isolate);
     609        1431 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setUTCFullYear");
     610         783 :   int const argc = args.length() - 1;
     611             :   Handle<Object> year = args.atOrUndefined(isolate, 1);
     612        1566 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, year,
     613             :                                      Object::ToNumber(isolate, year));
     614             :   double y = year->Number(), m = 0.0, dt = 1.0;
     615             :   int time_within_day = 0;
     616         783 :   if (!std::isnan(date->value()->Number())) {
     617         765 :     int64_t const time_ms = static_cast<int64_t>(date->value()->Number());
     618             :     int const days = isolate->date_cache()->DaysFromTime(time_ms);
     619             :     time_within_day = isolate->date_cache()->TimeInDay(time_ms, days);
     620             :     int year, month, day;
     621         765 :     isolate->date_cache()->YearMonthDayFromDays(days, &year, &month, &day);
     622         765 :     m = month;
     623         765 :     dt = day;
     624             :   }
     625         783 :   if (argc >= 2) {
     626             :     Handle<Object> month = args.at(2);
     627        1422 :     ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, month,
     628             :                                        Object::ToNumber(isolate, month));
     629             :     m = month->Number();
     630         711 :     if (argc >= 3) {
     631             :       Handle<Object> date = args.at(3);
     632        1152 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, date,
     633             :                                          Object::ToNumber(isolate, date));
     634             :       dt = date->Number();
     635             :     }
     636             :   }
     637         783 :   double const time_val = MakeDate(MakeDay(y, m, dt), time_within_day);
     638        1566 :   return *JSDate::SetValue(date, DateCache::TimeClip(time_val));
     639             : }
     640             : 
     641             : // ES6 section 20.3.4.30 Date.prototype.setUTCHours(hour, min, sec, ms)
     642       16425 : BUILTIN(DatePrototypeSetUTCHours) {
     643             :   HandleScope scope(isolate);
     644        3771 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setUTCHours");
     645        3123 :   int const argc = args.length() - 1;
     646             :   Handle<Object> hour = args.atOrUndefined(isolate, 1);
     647        6246 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, hour,
     648             :                                      Object::ToNumber(isolate, hour));
     649             :   double h = hour->Number();
     650             :   double time_val = date->value()->Number();
     651        3123 :   if (!std::isnan(time_val)) {
     652        3069 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     653             :     int day = isolate->date_cache()->DaysFromTime(time_ms);
     654             :     int time_within_day = isolate->date_cache()->TimeInDay(time_ms, day);
     655        3069 :     double m = (time_within_day / (60 * 1000)) % 60;
     656        3069 :     double s = (time_within_day / 1000) % 60;
     657        3069 :     double milli = time_within_day % 1000;
     658        3069 :     if (argc >= 2) {
     659             :       Handle<Object> min = args.at(2);
     660        6012 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, min,
     661             :                                          Object::ToNumber(isolate, min));
     662             :       m = min->Number();
     663        3006 :       if (argc >= 3) {
     664             :         Handle<Object> sec = args.at(3);
     665        5742 :         ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, sec,
     666             :                                            Object::ToNumber(isolate, sec));
     667             :         s = sec->Number();
     668        2871 :         if (argc >= 4) {
     669             :           Handle<Object> ms = args.at(4);
     670        4608 :           ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, ms,
     671             :                                              Object::ToNumber(isolate, ms));
     672             :           milli = ms->Number();
     673             :         }
     674             :       }
     675             :     }
     676        3069 :     time_val = MakeDate(day, MakeTime(h, m, s, milli));
     677             :   }
     678        6246 :   return *JSDate::SetValue(date, DateCache::TimeClip(time_val));
     679             : }
     680             : 
     681             : // ES6 section 20.3.4.31 Date.prototype.setUTCMilliseconds(ms)
     682        1170 : BUILTIN(DatePrototypeSetUTCMilliseconds) {
     683             :   HandleScope scope(isolate);
     684         720 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setUTCMilliseconds");
     685             :   Handle<Object> ms = args.atOrUndefined(isolate, 1);
     686         144 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, ms,
     687             :                                      Object::ToNumber(isolate, ms));
     688             :   double time_val = date->value()->Number();
     689          72 :   if (!std::isnan(time_val)) {
     690          54 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     691             :     int day = isolate->date_cache()->DaysFromTime(time_ms);
     692             :     int time_within_day = isolate->date_cache()->TimeInDay(time_ms, day);
     693          54 :     int h = time_within_day / (60 * 60 * 1000);
     694          54 :     int m = (time_within_day / (60 * 1000)) % 60;
     695          54 :     int s = (time_within_day / 1000) % 60;
     696          54 :     time_val = MakeDate(day, MakeTime(h, m, s, ms->Number()));
     697             :   }
     698         144 :   return *JSDate::SetValue(date, DateCache::TimeClip(time_val));
     699             : }
     700             : 
     701             : // ES6 section 20.3.4.32 Date.prototype.setUTCMinutes ( min, sec, ms )
     702        4725 : BUILTIN(DatePrototypeSetUTCMinutes) {
     703             :   HandleScope scope(isolate);
     704        1431 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setUTCMinutes");
     705         783 :   int const argc = args.length() - 1;
     706             :   Handle<Object> min = args.atOrUndefined(isolate, 1);
     707        1566 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, min,
     708             :                                      Object::ToNumber(isolate, min));
     709             :   double time_val = date->value()->Number();
     710         783 :   if (!std::isnan(time_val)) {
     711         756 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     712             :     int day = isolate->date_cache()->DaysFromTime(time_ms);
     713             :     int time_within_day = isolate->date_cache()->TimeInDay(time_ms, day);
     714         756 :     int h = time_within_day / (60 * 60 * 1000);
     715             :     double m = min->Number();
     716         756 :     double s = (time_within_day / 1000) % 60;
     717         756 :     double milli = time_within_day % 1000;
     718         756 :     if (argc >= 2) {
     719             :       Handle<Object> sec = args.at(2);
     720        1422 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, sec,
     721             :                                          Object::ToNumber(isolate, sec));
     722             :       s = sec->Number();
     723         711 :       if (argc >= 3) {
     724             :         Handle<Object> ms = args.at(3);
     725        1152 :         ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, ms,
     726             :                                            Object::ToNumber(isolate, ms));
     727             :         milli = ms->Number();
     728             :       }
     729             :     }
     730         756 :     time_val = MakeDate(day, MakeTime(h, m, s, milli));
     731             :   }
     732        1566 :   return *JSDate::SetValue(date, DateCache::TimeClip(time_val));
     733             : }
     734             : 
     735             : // ES6 section 20.3.4.31 Date.prototype.setUTCMonth ( month, date )
     736        1935 : BUILTIN(DatePrototypeSetUTCMonth) {
     737             :   HandleScope scope(isolate);
     738         873 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setUTCMonth");
     739             :   int const argc = args.length() - 1;
     740             :   Handle<Object> month = args.atOrUndefined(isolate, 1);
     741         450 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, month,
     742             :                                      Object::ToNumber(isolate, month));
     743             :   double time_val = date->value()->Number();
     744         225 :   if (!std::isnan(time_val)) {
     745         198 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     746             :     int days = isolate->date_cache()->DaysFromTime(time_ms);
     747             :     int time_within_day = isolate->date_cache()->TimeInDay(time_ms, days);
     748             :     int year, unused, day;
     749         198 :     isolate->date_cache()->YearMonthDayFromDays(days, &year, &unused, &day);
     750             :     double m = month->Number();
     751         198 :     double dt = day;
     752         198 :     if (argc >= 2) {
     753             :       Handle<Object> date = args.at(2);
     754         288 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, date,
     755             :                                          Object::ToNumber(isolate, date));
     756             :       dt = date->Number();
     757             :     }
     758         198 :     time_val = MakeDate(MakeDay(year, m, dt), time_within_day);
     759             :   }
     760         450 :   return *JSDate::SetValue(date, DateCache::TimeClip(time_val));
     761             : }
     762             : 
     763             : // ES6 section 20.3.4.34 Date.prototype.setUTCSeconds ( sec, ms )
     764        1935 : BUILTIN(DatePrototypeSetUTCSeconds) {
     765             :   HandleScope scope(isolate);
     766         873 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setUTCSeconds");
     767             :   int const argc = args.length() - 1;
     768             :   Handle<Object> sec = args.atOrUndefined(isolate, 1);
     769         450 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, sec,
     770             :                                      Object::ToNumber(isolate, sec));
     771             :   double time_val = date->value()->Number();
     772         225 :   if (!std::isnan(time_val)) {
     773         198 :     int64_t const time_ms = static_cast<int64_t>(time_val);
     774             :     int day = isolate->date_cache()->DaysFromTime(time_ms);
     775             :     int time_within_day = isolate->date_cache()->TimeInDay(time_ms, day);
     776         198 :     int h = time_within_day / (60 * 60 * 1000);
     777         198 :     double m = (time_within_day / (60 * 1000)) % 60;
     778             :     double s = sec->Number();
     779         198 :     double milli = time_within_day % 1000;
     780         198 :     if (argc >= 2) {
     781             :       Handle<Object> ms = args.at(2);
     782         288 :       ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, ms,
     783             :                                          Object::ToNumber(isolate, ms));
     784             :       milli = ms->Number();
     785             :     }
     786         198 :     time_val = MakeDate(day, MakeTime(h, m, s, milli));
     787             :   }
     788         450 :   return *JSDate::SetValue(date, DateCache::TimeClip(time_val));
     789             : }
     790             : 
     791             : // ES6 section 20.3.4.35 Date.prototype.toDateString ( )
     792         900 : BUILTIN(DatePrototypeToDateString) {
     793             :   HandleScope scope(isolate);
     794         666 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.toDateString");
     795             :   DateBuffer buffer =
     796          18 :       ToDateString(date->value()->Number(), isolate->date_cache(), kDateOnly);
     797          36 :   RETURN_RESULT_OR_FAILURE(
     798             :       isolate, isolate->factory()->NewStringFromUtf8(VectorOf(buffer)));
     799             : }
     800             : 
     801             : // ES6 section 20.3.4.36 Date.prototype.toISOString ( )
     802        1495 : BUILTIN(DatePrototypeToISOString) {
     803             :   HandleScope scope(isolate);
     804         785 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.toISOString");
     805             :   double const time_val = date->value()->Number();
     806         137 :   if (std::isnan(time_val)) {
     807          36 :     THROW_NEW_ERROR_RETURN_FAILURE(
     808             :         isolate, NewRangeError(MessageTemplate::kInvalidTimeValue));
     809             :   }
     810         119 :   int64_t const time_ms = static_cast<int64_t>(time_val);
     811             :   int year, month, day, weekday, hour, min, sec, ms;
     812             :   isolate->date_cache()->BreakDownTime(time_ms, &year, &month, &day, &weekday,
     813         119 :                                        &hour, &min, &sec, &ms);
     814             :   char buffer[128];
     815         119 :   if (year >= 0 && year <= 9999) {
     816         110 :     SNPrintF(ArrayVector(buffer), "%04d-%02d-%02dT%02d:%02d:%02d.%03dZ", year,
     817         220 :              month + 1, day, hour, min, sec, ms);
     818           9 :   } else if (year < 0) {
     819           0 :     SNPrintF(ArrayVector(buffer), "-%06d-%02d-%02dT%02d:%02d:%02d.%03dZ", -year,
     820           0 :              month + 1, day, hour, min, sec, ms);
     821             :   } else {
     822           9 :     SNPrintF(ArrayVector(buffer), "+%06d-%02d-%02dT%02d:%02d:%02d.%03dZ", year,
     823          18 :              month + 1, day, hour, min, sec, ms);
     824             :   }
     825         238 :   return *isolate->factory()->NewStringFromAsciiChecked(buffer);
     826             : }
     827             : 
     828             : // ES6 section 20.3.4.41 Date.prototype.toString ( )
     829      267885 : BUILTIN(DatePrototypeToString) {
     830             :   HandleScope scope(isolate);
     831       54090 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.toString");
     832             :   DateBuffer buffer =
     833       53406 :       ToDateString(date->value()->Number(), isolate->date_cache());
     834      106812 :   RETURN_RESULT_OR_FAILURE(
     835             :       isolate, isolate->factory()->NewStringFromUtf8(VectorOf(buffer)));
     836             : }
     837             : 
     838             : // ES6 section 20.3.4.42 Date.prototype.toTimeString ( )
     839         855 : BUILTIN(DatePrototypeToTimeString) {
     840             :   HandleScope scope(isolate);
     841         657 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.toTimeString");
     842             :   DateBuffer buffer =
     843           9 :       ToDateString(date->value()->Number(), isolate->date_cache(), kTimeOnly);
     844          18 :   RETURN_RESULT_OR_FAILURE(
     845             :       isolate, isolate->factory()->NewStringFromUtf8(VectorOf(buffer)));
     846             : }
     847             : 
     848             : #ifdef V8_INTL_SUPPORT
     849             : // ecma402 #sup-date.prototype.tolocaledatestring
     850        1260 : BUILTIN(DatePrototypeToLocaleDateString) {
     851             :   HandleScope scope(isolate);
     852             : 
     853         252 :   isolate->CountUsage(v8::Isolate::UseCounterFeature::kDateToLocaleDateString);
     854             : 
     855         738 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.toLocaleDateString");
     856             : 
     857         189 :   RETURN_RESULT_OR_FAILURE(
     858             :       isolate, JSDateTimeFormat::ToLocaleDateTime(
     859             :                    isolate,
     860             :                    date,                                       // date
     861             :                    args.atOrUndefined(isolate, 1),             // locales
     862             :                    args.atOrUndefined(isolate, 2),             // options
     863             :                    JSDateTimeFormat::RequiredOption::kDate,    // required
     864             :                    JSDateTimeFormat::DefaultsOption::kDate));  // defaults
     865             : }
     866             : 
     867             : // ecma402 #sup-date.prototype.tolocalestring
     868        1125 : BUILTIN(DatePrototypeToLocaleString) {
     869             :   HandleScope scope(isolate);
     870             : 
     871         225 :   isolate->CountUsage(v8::Isolate::UseCounterFeature::kDateToLocaleString);
     872             : 
     873         711 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.toLocaleString");
     874             : 
     875         126 :   RETURN_RESULT_OR_FAILURE(
     876             :       isolate, JSDateTimeFormat::ToLocaleDateTime(
     877             :                    isolate,
     878             :                    date,                                      // date
     879             :                    args.atOrUndefined(isolate, 1),            // locales
     880             :                    args.atOrUndefined(isolate, 2),            // options
     881             :                    JSDateTimeFormat::RequiredOption::kAny,    // required
     882             :                    JSDateTimeFormat::DefaultsOption::kAll));  // defaults
     883             : }
     884             : 
     885             : // ecma402 #sup-date.prototype.tolocaletimestring
     886        1035 : BUILTIN(DatePrototypeToLocaleTimeString) {
     887             :   HandleScope scope(isolate);
     888             : 
     889         207 :   isolate->CountUsage(v8::Isolate::UseCounterFeature::kDateToLocaleTimeString);
     890             : 
     891         693 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.toLocaleTimeString");
     892             : 
     893          90 :   RETURN_RESULT_OR_FAILURE(
     894             :       isolate, JSDateTimeFormat::ToLocaleDateTime(
     895             :                    isolate,
     896             :                    date,                                       // date
     897             :                    args.atOrUndefined(isolate, 1),             // locales
     898             :                    args.atOrUndefined(isolate, 2),             // options
     899             :                    JSDateTimeFormat::RequiredOption::kTime,    // required
     900             :                    JSDateTimeFormat::DefaultsOption::kTime));  // defaults
     901             : }
     902             : #endif  // V8_INTL_SUPPORT
     903             : 
     904             : // ES6 section 20.3.4.43 Date.prototype.toUTCString ( )
     905         945 : BUILTIN(DatePrototypeToUTCString) {
     906             :   HandleScope scope(isolate);
     907         675 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.toUTCString");
     908             :   double const time_val = date->value()->Number();
     909          27 :   if (std::isnan(time_val)) {
     910           0 :     return *isolate->factory()->NewStringFromAsciiChecked("Invalid Date");
     911             :   }
     912             :   char buffer[128];
     913          27 :   int64_t time_ms = static_cast<int64_t>(time_val);
     914             :   int year, month, day, weekday, hour, min, sec, ms;
     915             :   isolate->date_cache()->BreakDownTime(time_ms, &year, &month, &day, &weekday,
     916          27 :                                        &hour, &min, &sec, &ms);
     917          54 :   SNPrintF(ArrayVector(buffer), "%s, %02d %s %04d %02d:%02d:%02d GMT",
     918             :            kShortWeekDays[weekday], day, kShortMonths[month], year, hour, min,
     919          81 :            sec);
     920          54 :   return *isolate->factory()->NewStringFromAsciiChecked(buffer);
     921             : }
     922             : 
     923             : // ES6 section B.2.4.1 Date.prototype.getYear ( )
     924         675 : BUILTIN(DatePrototypeGetYear) {
     925             :   HandleScope scope(isolate);
     926         189 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.getYear");
     927             :   double time_val = date->value()->Number();
     928         117 :   if (std::isnan(time_val)) return date->value();
     929          81 :   int64_t time_ms = static_cast<int64_t>(time_val);
     930             :   int64_t local_time_ms = isolate->date_cache()->ToLocal(time_ms);
     931             :   int days = isolate->date_cache()->DaysFromTime(local_time_ms);
     932             :   int year, month, day;
     933          81 :   isolate->date_cache()->YearMonthDayFromDays(days, &year, &month, &day);
     934         162 :   return Smi::FromInt(year - 1900);
     935             : }
     936             : 
     937             : // ES6 section B.2.4.2 Date.prototype.setYear ( year )
     938         720 : BUILTIN(DatePrototypeSetYear) {
     939             :   HandleScope scope(isolate);
     940         171 :   CHECK_RECEIVER(JSDate, date, "Date.prototype.setYear");
     941             :   Handle<Object> year = args.atOrUndefined(isolate, 1);
     942         270 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, year,
     943             :                                      Object::ToNumber(isolate, year));
     944             :   double m = 0.0, dt = 1.0, y = year->Number();
     945         135 :   if (!std::isnan(y)) {
     946         117 :     double y_int = DoubleToInteger(y);
     947         117 :     if (0.0 <= y_int && y_int <= 99.0) {
     948          27 :       y = 1900.0 + y_int;
     949             :     }
     950             :   }
     951             :   int time_within_day = 0;
     952         135 :   if (!std::isnan(date->value()->Number())) {
     953         117 :     int64_t const time_ms = static_cast<int64_t>(date->value()->Number());
     954             :     int64_t local_time_ms = isolate->date_cache()->ToLocal(time_ms);
     955             :     int const days = isolate->date_cache()->DaysFromTime(local_time_ms);
     956             :     time_within_day = isolate->date_cache()->TimeInDay(local_time_ms, days);
     957             :     int year, month, day;
     958         117 :     isolate->date_cache()->YearMonthDayFromDays(days, &year, &month, &day);
     959         117 :     m = month;
     960         117 :     dt = day;
     961             :   }
     962         135 :   double time_val = MakeDate(MakeDay(y, m, dt), time_within_day);
     963         135 :   return SetLocalDateValue(isolate, date, time_val);
     964             : }
     965             : 
     966             : // ES6 section 20.3.4.37 Date.prototype.toJSON ( key )
     967        1440 : BUILTIN(DatePrototypeToJson) {
     968             :   HandleScope scope(isolate);
     969         288 :   Handle<Object> receiver = args.atOrUndefined(isolate, 0);
     970             :   Handle<JSReceiver> receiver_obj;
     971         738 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(isolate, receiver_obj,
     972             :                                      Object::ToObject(isolate, receiver));
     973             :   Handle<Object> primitive;
     974         261 :   ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     975             :       isolate, primitive,
     976             :       Object::ToPrimitive(receiver_obj, ToPrimitiveHint::kNumber));
     977         198 :   if (primitive->IsNumber() && !std::isfinite(primitive->Number())) {
     978          18 :     return ReadOnlyRoots(isolate).null_value();
     979             :   } else {
     980             :     Handle<String> name =
     981          99 :         isolate->factory()->NewStringFromAsciiChecked("toISOString");
     982             :     Handle<Object> function;
     983         198 :     ASSIGN_RETURN_FAILURE_ON_EXCEPTION(
     984             :         isolate, function, Object::GetProperty(isolate, receiver_obj, name));
     985          99 :     if (!function->IsCallable()) {
     986          36 :       THROW_NEW_ERROR_RETURN_FAILURE(
     987             :           isolate, NewTypeError(MessageTemplate::kCalledNonCallable, name));
     988             :     }
     989         162 :     RETURN_RESULT_OR_FAILURE(
     990             :         isolate, Execution::Call(isolate, function, receiver_obj, 0, nullptr));
     991             :   }
     992             : }
     993             : 
     994             : }  // namespace internal
     995      120216 : }  // namespace v8

Generated by: LCOV version 1.10