[builtins] Make Date toString functions conform to new spec

Previously, Date.toString() and friends were completely
implementation-defined. However, they actually seemed to match
each other's behavior with the exception of how years less than
1000 are formatted. The rough consensus among browsers seemed
to be %04d, so this was standardized at TC39 [1]. V8 previously
used %4d (it was the only one to do so); this patch adopts
the new standard.

[1] 5d4acf3377

Bug: v8:6076
Change-Id: I8c795a4e1b71187ad7c24a1aee8d7d66719a2586
Reviewed-on: https://chromium-review.googlesource.com/536733
Commit-Queue: Daniel Ehrenberg <littledan@chromium.org>
Reviewed-by: Jakob Gruber <jgruber@chromium.org>
Cr-Commit-Position: refs/heads/master@{#46037}
This commit is contained in:
Daniel Ehrenberg 2017-06-15 06:37:19 +02:00 committed by Commit Bot
parent f244f0c5ef
commit 2854ea7b77
2 changed files with 12 additions and 3 deletions

View File

@ -162,7 +162,7 @@ void ToDateString(double time_val, Vector<char> str, DateCache* date_cache,
const char* local_timezone = date_cache->LocalTimezone(time_ms);
switch (mode) {
case kDateOnly:
SNPrintF(str, "%s %s %02d %4d", kShortWeekDays[weekday],
SNPrintF(str, "%s %s %02d %04d", kShortWeekDays[weekday],
kShortMonths[month], day, year);
return;
case kTimeOnly:
@ -171,7 +171,7 @@ void ToDateString(double time_val, Vector<char> str, DateCache* date_cache,
local_timezone);
return;
case kDateAndTime:
SNPrintF(str, "%s %s %02d %4d %02d:%02d:%02d GMT%c%02d%02d (%s)",
SNPrintF(str, "%s %s %02d %04d %02d:%02d:%02d GMT%c%02d%02d (%s)",
kShortWeekDays[weekday], kShortMonths[month], day, year, hour,
min, sec, (timezone_offset < 0) ? '-' : '+', timezone_hour,
timezone_min, local_timezone);
@ -822,7 +822,7 @@ BUILTIN(DatePrototypeToUTCString) {
int year, month, day, weekday, hour, min, sec, ms;
isolate->date_cache()->BreakDownTime(time_ms, &year, &month, &day, &weekday,
&hour, &min, &sec, &ms);
SNPrintF(ArrayVector(buffer), "%s, %02d %s %4d %02d:%02d:%02d GMT",
SNPrintF(ArrayVector(buffer), "%s, %02d %s %04d %02d:%02d:%02d GMT",
kShortWeekDays[weekday], day, kShortMonths[month], year, hour, min,
sec);
return *isolate->factory()->NewStringFromAsciiChecked(buffer);

View File

@ -314,6 +314,15 @@ for (var i = 0; i < 24; i++) {
}
}
// Test padding with 0 rather than spaces
assertEquals('Wed, 01 Jan 0020 00:00:00 GMT', new Date('0020-01-01T00:00:00Z').toUTCString());
let dateRegExp = /^(Sun|Mon|Tue|Wed|Thu|Fri|Sat) (Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec) [0-9]{2} [0-9]{4}$/
match = dateRegExp.exec(new Date('0020-01-01T00:00:00Z').toDateString());
assertNotNull(match);
let stringRegExp = /^(Sun|Mon|Tue|Wed|Thu|Fri|Sat) (Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec) [0-9]{2} [0-9]{4} [0-9]{2}:[0-9]{2}:[0-9]{2} GMT[+-][0-9]{4}( \(.+\))?$/
match = stringRegExp.exec(new Date('0020-01-01T00:00:00Z').toString());
assertNotNull(match);
assertThrows('Date.prototype.setTime.call("", 1);', TypeError);
assertThrows('Date.prototype.setYear.call("", 1);', TypeError);
assertThrows('Date.prototype.setHours.call("", 1, 2, 3, 4);', TypeError);