| OLD | NEW |
| (Empty) |
| 1 // Copyright 2006-2008 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 var $createDate; | |
| 6 | |
| 7 // ------------------------------------------------------------------- | |
| 8 | |
| 9 (function(global, utils) { | |
| 10 | |
| 11 "use strict"; | |
| 12 | |
| 13 %CheckIsBootstrapping(); | |
| 14 | |
| 15 // ------------------------------------------------------------------- | |
| 16 // Imports | |
| 17 | |
| 18 var GlobalDate = global.Date; | |
| 19 var GlobalObject = global.Object; | |
| 20 var InternalArray = utils.InternalArray; | |
| 21 var IsFinite; | |
| 22 var MathAbs; | |
| 23 var MathFloor; | |
| 24 | |
| 25 utils.Import(function(from) { | |
| 26 IsFinite = from.IsFinite; | |
| 27 MathAbs = from.MathAbs; | |
| 28 MathFloor = from.MathFloor; | |
| 29 }); | |
| 30 | |
| 31 // ------------------------------------------------------------------- | |
| 32 | |
| 33 // This file contains date support implemented in JavaScript. | |
| 34 | |
| 35 var timezone_cache_time = NAN; | |
| 36 var timezone_cache_timezone; | |
| 37 | |
| 38 function LocalTimezone(t) { | |
| 39 if (NUMBER_IS_NAN(t)) return ""; | |
| 40 CheckDateCacheCurrent(); | |
| 41 if (t == timezone_cache_time) { | |
| 42 return timezone_cache_timezone; | |
| 43 } | |
| 44 var timezone = %DateLocalTimezone(t); | |
| 45 timezone_cache_time = t; | |
| 46 timezone_cache_timezone = timezone; | |
| 47 return timezone; | |
| 48 } | |
| 49 | |
| 50 | |
| 51 function UTC(time) { | |
| 52 if (NUMBER_IS_NAN(time)) return time; | |
| 53 // local_time_offset is needed before the call to DaylightSavingsOffset, | |
| 54 // so it may be uninitialized. | |
| 55 return %DateToUTC(time); | |
| 56 } | |
| 57 | |
| 58 | |
| 59 // ECMA 262 - 15.9.1.11 | |
| 60 function MakeTime(hour, min, sec, ms) { | |
| 61 if (!IsFinite(hour)) return NAN; | |
| 62 if (!IsFinite(min)) return NAN; | |
| 63 if (!IsFinite(sec)) return NAN; | |
| 64 if (!IsFinite(ms)) return NAN; | |
| 65 return TO_INTEGER(hour) * msPerHour | |
| 66 + TO_INTEGER(min) * msPerMinute | |
| 67 + TO_INTEGER(sec) * msPerSecond | |
| 68 + TO_INTEGER(ms); | |
| 69 } | |
| 70 | |
| 71 | |
| 72 // ECMA 262 - 15.9.1.12 | |
| 73 function TimeInYear(year) { | |
| 74 return DaysInYear(year) * msPerDay; | |
| 75 } | |
| 76 | |
| 77 | |
| 78 // Compute number of days given a year, month, date. | |
| 79 // Note that month and date can lie outside the normal range. | |
| 80 // For example: | |
| 81 // MakeDay(2007, -4, 20) --> MakeDay(2006, 8, 20) | |
| 82 // MakeDay(2007, -33, 1) --> MakeDay(2004, 3, 1) | |
| 83 // MakeDay(2007, 14, -50) --> MakeDay(2007, 8, 11) | |
| 84 function MakeDay(year, month, date) { | |
| 85 if (!IsFinite(year) || !IsFinite(month) || !IsFinite(date)) return NAN; | |
| 86 | |
| 87 // Convert to integer and map -0 to 0. | |
| 88 year = TO_INTEGER_MAP_MINUS_ZERO(year); | |
| 89 month = TO_INTEGER_MAP_MINUS_ZERO(month); | |
| 90 date = TO_INTEGER_MAP_MINUS_ZERO(date); | |
| 91 | |
| 92 if (year < kMinYear || year > kMaxYear || | |
| 93 month < kMinMonth || month > kMaxMonth) { | |
| 94 return NAN; | |
| 95 } | |
| 96 | |
| 97 // Now we rely on year and month being SMIs. | |
| 98 return %DateMakeDay(year | 0, month | 0) + date - 1; | |
| 99 } | |
| 100 | |
| 101 | |
| 102 // ECMA 262 - 15.9.1.13 | |
| 103 function MakeDate(day, time) { | |
| 104 var time = day * msPerDay + time; | |
| 105 // Some of our runtime funtions for computing UTC(time) rely on | |
| 106 // times not being significantly larger than MAX_TIME_MS. If there | |
| 107 // is no way that the time can be within range even after UTC | |
| 108 // conversion we return NaN immediately instead of relying on | |
| 109 // TimeClip to do it. | |
| 110 if (MathAbs(time) > MAX_TIME_BEFORE_UTC) return NAN; | |
| 111 return time; | |
| 112 } | |
| 113 | |
| 114 | |
| 115 // ECMA 262 - 15.9.1.14 | |
| 116 function TimeClip(time) { | |
| 117 if (!IsFinite(time)) return NAN; | |
| 118 if (MathAbs(time) > MAX_TIME_MS) return NAN; | |
| 119 return TO_INTEGER(time) + 0; | |
| 120 } | |
| 121 | |
| 122 | |
| 123 // The Date cache is used to limit the cost of parsing the same Date | |
| 124 // strings over and over again. | |
| 125 var Date_cache = { | |
| 126 // Cached time value. | |
| 127 time: 0, | |
| 128 // String input for which the cached time is valid. | |
| 129 string: null | |
| 130 }; | |
| 131 | |
| 132 | |
| 133 function DateConstructor(year, month, date, hours, minutes, seconds, ms) { | |
| 134 if (!%_IsConstructCall()) { | |
| 135 // ECMA 262 - 15.9.2 | |
| 136 return %_CallFunction(new GlobalDate(), DateToString); | |
| 137 } | |
| 138 | |
| 139 // ECMA 262 - 15.9.3 | |
| 140 var argc = %_ArgumentsLength(); | |
| 141 var value; | |
| 142 if (argc == 0) { | |
| 143 value = %DateCurrentTime(); | |
| 144 SET_UTC_DATE_VALUE(this, value); | |
| 145 } else if (argc == 1) { | |
| 146 if (IS_NUMBER(year)) { | |
| 147 value = TimeClip(year); | |
| 148 | |
| 149 } else if (IS_STRING(year)) { | |
| 150 // Probe the Date cache. If we already have a time value for the | |
| 151 // given time, we re-use that instead of parsing the string again. | |
| 152 CheckDateCacheCurrent(); | |
| 153 var cache = Date_cache; | |
| 154 if (cache.string === year) { | |
| 155 value = cache.time; | |
| 156 } else { | |
| 157 value = DateParse(year); | |
| 158 if (!NUMBER_IS_NAN(value)) { | |
| 159 cache.time = value; | |
| 160 cache.string = year; | |
| 161 } | |
| 162 } | |
| 163 | |
| 164 } else if (IS_DATE(year)) { | |
| 165 value = UTC_DATE_VALUE(year); | |
| 166 | |
| 167 } else { | |
| 168 var time = TO_PRIMITIVE(year); | |
| 169 value = IS_STRING(time) ? DateParse(time) : TO_NUMBER(time); | |
| 170 } | |
| 171 SET_UTC_DATE_VALUE(this, value); | |
| 172 } else { | |
| 173 year = TO_NUMBER(year); | |
| 174 month = TO_NUMBER(month); | |
| 175 date = argc > 2 ? TO_NUMBER(date) : 1; | |
| 176 hours = argc > 3 ? TO_NUMBER(hours) : 0; | |
| 177 minutes = argc > 4 ? TO_NUMBER(minutes) : 0; | |
| 178 seconds = argc > 5 ? TO_NUMBER(seconds) : 0; | |
| 179 ms = argc > 6 ? TO_NUMBER(ms) : 0; | |
| 180 year = (!NUMBER_IS_NAN(year) && | |
| 181 0 <= TO_INTEGER(year) && | |
| 182 TO_INTEGER(year) <= 99) ? 1900 + TO_INTEGER(year) : year; | |
| 183 var day = MakeDay(year, month, date); | |
| 184 var time = MakeTime(hours, minutes, seconds, ms); | |
| 185 value = MakeDate(day, time); | |
| 186 SET_LOCAL_DATE_VALUE(this, value); | |
| 187 } | |
| 188 } | |
| 189 | |
| 190 | |
| 191 var WeekDays = ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat']; | |
| 192 var Months = ['Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', | |
| 193 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec']; | |
| 194 | |
| 195 | |
| 196 function TwoDigitString(value) { | |
| 197 return value < 10 ? "0" + value : "" + value; | |
| 198 } | |
| 199 | |
| 200 | |
| 201 function DateString(date) { | |
| 202 CHECK_DATE(date); | |
| 203 return WeekDays[LOCAL_WEEKDAY(date)] + ' ' | |
| 204 + Months[LOCAL_MONTH(date)] + ' ' | |
| 205 + TwoDigitString(LOCAL_DAY(date)) + ' ' | |
| 206 + LOCAL_YEAR(date); | |
| 207 } | |
| 208 | |
| 209 | |
| 210 var LongWeekDays = ['Sunday', 'Monday', 'Tuesday', 'Wednesday', | |
| 211 'Thursday', 'Friday', 'Saturday']; | |
| 212 var LongMonths = ['January', 'February', 'March', 'April', 'May', 'June', | |
| 213 'July', 'August', 'September', 'October', 'November', 'December']; | |
| 214 | |
| 215 | |
| 216 function LongDateString(date) { | |
| 217 CHECK_DATE(date); | |
| 218 return LongWeekDays[LOCAL_WEEKDAY(date)] + ', ' | |
| 219 + LongMonths[LOCAL_MONTH(date)] + ' ' | |
| 220 + TwoDigitString(LOCAL_DAY(date)) + ', ' | |
| 221 + LOCAL_YEAR(date); | |
| 222 } | |
| 223 | |
| 224 | |
| 225 function TimeString(date) { | |
| 226 CHECK_DATE(date); | |
| 227 return TwoDigitString(LOCAL_HOUR(date)) + ':' | |
| 228 + TwoDigitString(LOCAL_MIN(date)) + ':' | |
| 229 + TwoDigitString(LOCAL_SEC(date)); | |
| 230 } | |
| 231 | |
| 232 | |
| 233 function TimeStringUTC(date) { | |
| 234 CHECK_DATE(date); | |
| 235 return TwoDigitString(UTC_HOUR(date)) + ':' | |
| 236 + TwoDigitString(UTC_MIN(date)) + ':' | |
| 237 + TwoDigitString(UTC_SEC(date)); | |
| 238 } | |
| 239 | |
| 240 | |
| 241 function LocalTimezoneString(date) { | |
| 242 CHECK_DATE(date); | |
| 243 var timezone = LocalTimezone(UTC_DATE_VALUE(date)); | |
| 244 | |
| 245 var timezoneOffset = -TIMEZONE_OFFSET(date); | |
| 246 var sign = (timezoneOffset >= 0) ? 1 : -1; | |
| 247 var hours = MathFloor((sign * timezoneOffset)/60); | |
| 248 var min = MathFloor((sign * timezoneOffset)%60); | |
| 249 var gmt = ' GMT' + ((sign == 1) ? '+' : '-') + | |
| 250 TwoDigitString(hours) + TwoDigitString(min); | |
| 251 return gmt + ' (' + timezone + ')'; | |
| 252 } | |
| 253 | |
| 254 | |
| 255 function DatePrintString(date) { | |
| 256 CHECK_DATE(date); | |
| 257 return DateString(date) + ' ' + TimeString(date); | |
| 258 } | |
| 259 | |
| 260 // ------------------------------------------------------------------- | |
| 261 | |
| 262 // Reused output buffer. Used when parsing date strings. | |
| 263 var parse_buffer = new InternalArray(8); | |
| 264 | |
| 265 // ECMA 262 - 15.9.4.2 | |
| 266 function DateParse(string) { | |
| 267 var arr = %DateParseString(string, parse_buffer); | |
| 268 if (IS_NULL(arr)) return NAN; | |
| 269 | |
| 270 var day = MakeDay(arr[0], arr[1], arr[2]); | |
| 271 var time = MakeTime(arr[3], arr[4], arr[5], arr[6]); | |
| 272 var date = MakeDate(day, time); | |
| 273 | |
| 274 if (IS_NULL(arr[7])) { | |
| 275 return TimeClip(UTC(date)); | |
| 276 } else { | |
| 277 return TimeClip(date - arr[7] * 1000); | |
| 278 } | |
| 279 } | |
| 280 | |
| 281 | |
| 282 // ECMA 262 - 15.9.4.3 | |
| 283 function DateUTC(year, month, date, hours, minutes, seconds, ms) { | |
| 284 year = TO_NUMBER(year); | |
| 285 month = TO_NUMBER(month); | |
| 286 var argc = %_ArgumentsLength(); | |
| 287 date = argc > 2 ? TO_NUMBER(date) : 1; | |
| 288 hours = argc > 3 ? TO_NUMBER(hours) : 0; | |
| 289 minutes = argc > 4 ? TO_NUMBER(minutes) : 0; | |
| 290 seconds = argc > 5 ? TO_NUMBER(seconds) : 0; | |
| 291 ms = argc > 6 ? TO_NUMBER(ms) : 0; | |
| 292 year = (!NUMBER_IS_NAN(year) && | |
| 293 0 <= TO_INTEGER(year) && | |
| 294 TO_INTEGER(year) <= 99) ? 1900 + TO_INTEGER(year) : year; | |
| 295 var day = MakeDay(year, month, date); | |
| 296 var time = MakeTime(hours, minutes, seconds, ms); | |
| 297 return TimeClip(MakeDate(day, time)); | |
| 298 } | |
| 299 | |
| 300 | |
| 301 // ECMA 262 - 15.9.4.4 | |
| 302 function DateNow() { | |
| 303 return %DateCurrentTime(); | |
| 304 } | |
| 305 | |
| 306 | |
| 307 // ECMA 262 - 15.9.5.2 | |
| 308 function DateToString() { | |
| 309 CHECK_DATE(this); | |
| 310 var t = UTC_DATE_VALUE(this) | |
| 311 if (NUMBER_IS_NAN(t)) return kInvalidDate; | |
| 312 var time_zone_string = LocalTimezoneString(this) | |
| 313 return DatePrintString(this) + time_zone_string; | |
| 314 } | |
| 315 | |
| 316 | |
| 317 // ECMA 262 - 15.9.5.3 | |
| 318 function DateToDateString() { | |
| 319 CHECK_DATE(this); | |
| 320 var t = UTC_DATE_VALUE(this); | |
| 321 if (NUMBER_IS_NAN(t)) return kInvalidDate; | |
| 322 return DateString(this); | |
| 323 } | |
| 324 | |
| 325 | |
| 326 // ECMA 262 - 15.9.5.4 | |
| 327 function DateToTimeString() { | |
| 328 CHECK_DATE(this); | |
| 329 var t = UTC_DATE_VALUE(this); | |
| 330 if (NUMBER_IS_NAN(t)) return kInvalidDate; | |
| 331 var time_zone_string = LocalTimezoneString(this); | |
| 332 return TimeString(this) + time_zone_string; | |
| 333 } | |
| 334 | |
| 335 | |
| 336 // ECMA 262 - 15.9.5.5 | |
| 337 function DateToLocaleString() { | |
| 338 CHECK_DATE(this); | |
| 339 return %_CallFunction(this, DateToString); | |
| 340 } | |
| 341 | |
| 342 | |
| 343 // ECMA 262 - 15.9.5.6 | |
| 344 function DateToLocaleDateString() { | |
| 345 CHECK_DATE(this); | |
| 346 var t = UTC_DATE_VALUE(this); | |
| 347 if (NUMBER_IS_NAN(t)) return kInvalidDate; | |
| 348 return LongDateString(this); | |
| 349 } | |
| 350 | |
| 351 | |
| 352 // ECMA 262 - 15.9.5.7 | |
| 353 function DateToLocaleTimeString() { | |
| 354 CHECK_DATE(this); | |
| 355 var t = UTC_DATE_VALUE(this); | |
| 356 if (NUMBER_IS_NAN(t)) return kInvalidDate; | |
| 357 return TimeString(this); | |
| 358 } | |
| 359 | |
| 360 | |
| 361 // ECMA 262 - 15.9.5.8 | |
| 362 function DateValueOf() { | |
| 363 CHECK_DATE(this); | |
| 364 return UTC_DATE_VALUE(this); | |
| 365 } | |
| 366 | |
| 367 | |
| 368 // ECMA 262 - 15.9.5.9 | |
| 369 function DateGetTime() { | |
| 370 CHECK_DATE(this); | |
| 371 return UTC_DATE_VALUE(this); | |
| 372 } | |
| 373 | |
| 374 | |
| 375 // ECMA 262 - 15.9.5.10 | |
| 376 function DateGetFullYear() { | |
| 377 CHECK_DATE(this); | |
| 378 return LOCAL_YEAR(this); | |
| 379 } | |
| 380 | |
| 381 | |
| 382 // ECMA 262 - 15.9.5.11 | |
| 383 function DateGetUTCFullYear() { | |
| 384 CHECK_DATE(this); | |
| 385 return UTC_YEAR(this); | |
| 386 } | |
| 387 | |
| 388 | |
| 389 // ECMA 262 - 15.9.5.12 | |
| 390 function DateGetMonth() { | |
| 391 CHECK_DATE(this); | |
| 392 return LOCAL_MONTH(this); | |
| 393 } | |
| 394 | |
| 395 | |
| 396 // ECMA 262 - 15.9.5.13 | |
| 397 function DateGetUTCMonth() { | |
| 398 CHECK_DATE(this); | |
| 399 return UTC_MONTH(this); | |
| 400 } | |
| 401 | |
| 402 | |
| 403 // ECMA 262 - 15.9.5.14 | |
| 404 function DateGetDate() { | |
| 405 CHECK_DATE(this); | |
| 406 return LOCAL_DAY(this); | |
| 407 } | |
| 408 | |
| 409 | |
| 410 // ECMA 262 - 15.9.5.15 | |
| 411 function DateGetUTCDate() { | |
| 412 CHECK_DATE(this); | |
| 413 return UTC_DAY(this); | |
| 414 } | |
| 415 | |
| 416 | |
| 417 // ECMA 262 - 15.9.5.16 | |
| 418 function DateGetDay() { | |
| 419 CHECK_DATE(this); | |
| 420 return LOCAL_WEEKDAY(this); | |
| 421 } | |
| 422 | |
| 423 | |
| 424 // ECMA 262 - 15.9.5.17 | |
| 425 function DateGetUTCDay() { | |
| 426 CHECK_DATE(this); | |
| 427 return UTC_WEEKDAY(this); | |
| 428 } | |
| 429 | |
| 430 | |
| 431 // ECMA 262 - 15.9.5.18 | |
| 432 function DateGetHours() { | |
| 433 CHECK_DATE(this); | |
| 434 return LOCAL_HOUR(this); | |
| 435 } | |
| 436 | |
| 437 | |
| 438 // ECMA 262 - 15.9.5.19 | |
| 439 function DateGetUTCHours() { | |
| 440 CHECK_DATE(this); | |
| 441 return UTC_HOUR(this); | |
| 442 } | |
| 443 | |
| 444 | |
| 445 // ECMA 262 - 15.9.5.20 | |
| 446 function DateGetMinutes() { | |
| 447 CHECK_DATE(this); | |
| 448 return LOCAL_MIN(this); | |
| 449 } | |
| 450 | |
| 451 | |
| 452 // ECMA 262 - 15.9.5.21 | |
| 453 function DateGetUTCMinutes() { | |
| 454 CHECK_DATE(this); | |
| 455 return UTC_MIN(this); | |
| 456 } | |
| 457 | |
| 458 | |
| 459 // ECMA 262 - 15.9.5.22 | |
| 460 function DateGetSeconds() { | |
| 461 CHECK_DATE(this); | |
| 462 return LOCAL_SEC(this); | |
| 463 } | |
| 464 | |
| 465 | |
| 466 // ECMA 262 - 15.9.5.23 | |
| 467 function DateGetUTCSeconds() { | |
| 468 CHECK_DATE(this); | |
| 469 return UTC_SEC(this) | |
| 470 } | |
| 471 | |
| 472 | |
| 473 // ECMA 262 - 15.9.5.24 | |
| 474 function DateGetMilliseconds() { | |
| 475 CHECK_DATE(this); | |
| 476 return LOCAL_MS(this); | |
| 477 } | |
| 478 | |
| 479 | |
| 480 // ECMA 262 - 15.9.5.25 | |
| 481 function DateGetUTCMilliseconds() { | |
| 482 CHECK_DATE(this); | |
| 483 return UTC_MS(this); | |
| 484 } | |
| 485 | |
| 486 | |
| 487 // ECMA 262 - 15.9.5.26 | |
| 488 function DateGetTimezoneOffset() { | |
| 489 CHECK_DATE(this); | |
| 490 return TIMEZONE_OFFSET(this); | |
| 491 } | |
| 492 | |
| 493 | |
| 494 // ECMA 262 - 15.9.5.27 | |
| 495 function DateSetTime(ms) { | |
| 496 CHECK_DATE(this); | |
| 497 SET_UTC_DATE_VALUE(this, TO_NUMBER(ms)); | |
| 498 return UTC_DATE_VALUE(this); | |
| 499 } | |
| 500 | |
| 501 | |
| 502 // ECMA 262 - 15.9.5.28 | |
| 503 function DateSetMilliseconds(ms) { | |
| 504 CHECK_DATE(this); | |
| 505 var t = LOCAL_DATE_VALUE(this); | |
| 506 ms = TO_NUMBER(ms); | |
| 507 var time = MakeTime(LOCAL_HOUR(this), LOCAL_MIN(this), LOCAL_SEC(this), ms); | |
| 508 return SET_LOCAL_DATE_VALUE(this, MakeDate(LOCAL_DAYS(this), time)); | |
| 509 } | |
| 510 | |
| 511 | |
| 512 // ECMA 262 - 15.9.5.29 | |
| 513 function DateSetUTCMilliseconds(ms) { | |
| 514 CHECK_DATE(this); | |
| 515 var t = UTC_DATE_VALUE(this); | |
| 516 ms = TO_NUMBER(ms); | |
| 517 var time = MakeTime(UTC_HOUR(this), | |
| 518 UTC_MIN(this), | |
| 519 UTC_SEC(this), | |
| 520 ms); | |
| 521 return SET_UTC_DATE_VALUE(this, MakeDate(UTC_DAYS(this), time)); | |
| 522 } | |
| 523 | |
| 524 | |
| 525 // ECMA 262 - 15.9.5.30 | |
| 526 function DateSetSeconds(sec, ms) { | |
| 527 CHECK_DATE(this); | |
| 528 var t = LOCAL_DATE_VALUE(this); | |
| 529 sec = TO_NUMBER(sec); | |
| 530 ms = %_ArgumentsLength() < 2 ? LOCAL_MS(this) : TO_NUMBER(ms); | |
| 531 var time = MakeTime(LOCAL_HOUR(this), LOCAL_MIN(this), sec, ms); | |
| 532 return SET_LOCAL_DATE_VALUE(this, MakeDate(LOCAL_DAYS(this), time)); | |
| 533 } | |
| 534 | |
| 535 | |
| 536 // ECMA 262 - 15.9.5.31 | |
| 537 function DateSetUTCSeconds(sec, ms) { | |
| 538 CHECK_DATE(this); | |
| 539 var t = UTC_DATE_VALUE(this); | |
| 540 sec = TO_NUMBER(sec); | |
| 541 ms = %_ArgumentsLength() < 2 ? UTC_MS(this) : TO_NUMBER(ms); | |
| 542 var time = MakeTime(UTC_HOUR(this), UTC_MIN(this), sec, ms); | |
| 543 return SET_UTC_DATE_VALUE(this, MakeDate(UTC_DAYS(this), time)); | |
| 544 } | |
| 545 | |
| 546 | |
| 547 // ECMA 262 - 15.9.5.33 | |
| 548 function DateSetMinutes(min, sec, ms) { | |
| 549 CHECK_DATE(this); | |
| 550 var t = LOCAL_DATE_VALUE(this); | |
| 551 min = TO_NUMBER(min); | |
| 552 var argc = %_ArgumentsLength(); | |
| 553 sec = argc < 2 ? LOCAL_SEC(this) : TO_NUMBER(sec); | |
| 554 ms = argc < 3 ? LOCAL_MS(this) : TO_NUMBER(ms); | |
| 555 var time = MakeTime(LOCAL_HOUR(this), min, sec, ms); | |
| 556 return SET_LOCAL_DATE_VALUE(this, MakeDate(LOCAL_DAYS(this), time)); | |
| 557 } | |
| 558 | |
| 559 | |
| 560 // ECMA 262 - 15.9.5.34 | |
| 561 function DateSetUTCMinutes(min, sec, ms) { | |
| 562 CHECK_DATE(this); | |
| 563 var t = UTC_DATE_VALUE(this); | |
| 564 min = TO_NUMBER(min); | |
| 565 var argc = %_ArgumentsLength(); | |
| 566 sec = argc < 2 ? UTC_SEC(this) : TO_NUMBER(sec); | |
| 567 ms = argc < 3 ? UTC_MS(this) : TO_NUMBER(ms); | |
| 568 var time = MakeTime(UTC_HOUR(this), min, sec, ms); | |
| 569 return SET_UTC_DATE_VALUE(this, MakeDate(UTC_DAYS(this), time)); | |
| 570 } | |
| 571 | |
| 572 | |
| 573 // ECMA 262 - 15.9.5.35 | |
| 574 function DateSetHours(hour, min, sec, ms) { | |
| 575 CHECK_DATE(this); | |
| 576 var t = LOCAL_DATE_VALUE(this); | |
| 577 hour = TO_NUMBER(hour); | |
| 578 var argc = %_ArgumentsLength(); | |
| 579 min = argc < 2 ? LOCAL_MIN(this) : TO_NUMBER(min); | |
| 580 sec = argc < 3 ? LOCAL_SEC(this) : TO_NUMBER(sec); | |
| 581 ms = argc < 4 ? LOCAL_MS(this) : TO_NUMBER(ms); | |
| 582 var time = MakeTime(hour, min, sec, ms); | |
| 583 return SET_LOCAL_DATE_VALUE(this, MakeDate(LOCAL_DAYS(this), time)); | |
| 584 } | |
| 585 | |
| 586 | |
| 587 // ECMA 262 - 15.9.5.34 | |
| 588 function DateSetUTCHours(hour, min, sec, ms) { | |
| 589 CHECK_DATE(this); | |
| 590 var t = UTC_DATE_VALUE(this); | |
| 591 hour = TO_NUMBER(hour); | |
| 592 var argc = %_ArgumentsLength(); | |
| 593 min = argc < 2 ? UTC_MIN(this) : TO_NUMBER(min); | |
| 594 sec = argc < 3 ? UTC_SEC(this) : TO_NUMBER(sec); | |
| 595 ms = argc < 4 ? UTC_MS(this) : TO_NUMBER(ms); | |
| 596 var time = MakeTime(hour, min, sec, ms); | |
| 597 return SET_UTC_DATE_VALUE(this, MakeDate(UTC_DAYS(this), time)); | |
| 598 } | |
| 599 | |
| 600 | |
| 601 // ECMA 262 - 15.9.5.36 | |
| 602 function DateSetDate(date) { | |
| 603 CHECK_DATE(this); | |
| 604 var t = LOCAL_DATE_VALUE(this); | |
| 605 date = TO_NUMBER(date); | |
| 606 var day = MakeDay(LOCAL_YEAR(this), LOCAL_MONTH(this), date); | |
| 607 return SET_LOCAL_DATE_VALUE(this, MakeDate(day, LOCAL_TIME_IN_DAY(this))); | |
| 608 } | |
| 609 | |
| 610 | |
| 611 // ECMA 262 - 15.9.5.37 | |
| 612 function DateSetUTCDate(date) { | |
| 613 CHECK_DATE(this); | |
| 614 var t = UTC_DATE_VALUE(this); | |
| 615 date = TO_NUMBER(date); | |
| 616 var day = MakeDay(UTC_YEAR(this), UTC_MONTH(this), date); | |
| 617 return SET_UTC_DATE_VALUE(this, MakeDate(day, UTC_TIME_IN_DAY(this))); | |
| 618 } | |
| 619 | |
| 620 | |
| 621 // ECMA 262 - 15.9.5.38 | |
| 622 function DateSetMonth(month, date) { | |
| 623 CHECK_DATE(this); | |
| 624 var t = LOCAL_DATE_VALUE(this); | |
| 625 month = TO_NUMBER(month); | |
| 626 date = %_ArgumentsLength() < 2 ? LOCAL_DAY(this) : TO_NUMBER(date); | |
| 627 var day = MakeDay(LOCAL_YEAR(this), month, date); | |
| 628 return SET_LOCAL_DATE_VALUE(this, MakeDate(day, LOCAL_TIME_IN_DAY(this))); | |
| 629 } | |
| 630 | |
| 631 | |
| 632 // ECMA 262 - 15.9.5.39 | |
| 633 function DateSetUTCMonth(month, date) { | |
| 634 CHECK_DATE(this); | |
| 635 var t = UTC_DATE_VALUE(this); | |
| 636 month = TO_NUMBER(month); | |
| 637 date = %_ArgumentsLength() < 2 ? UTC_DAY(this) : TO_NUMBER(date); | |
| 638 var day = MakeDay(UTC_YEAR(this), month, date); | |
| 639 return SET_UTC_DATE_VALUE(this, MakeDate(day, UTC_TIME_IN_DAY(this))); | |
| 640 } | |
| 641 | |
| 642 | |
| 643 // ECMA 262 - 15.9.5.40 | |
| 644 function DateSetFullYear(year, month, date) { | |
| 645 CHECK_DATE(this); | |
| 646 var t = LOCAL_DATE_VALUE(this); | |
| 647 year = TO_NUMBER(year); | |
| 648 var argc = %_ArgumentsLength(); | |
| 649 var time ; | |
| 650 if (NUMBER_IS_NAN(t)) { | |
| 651 month = argc < 2 ? 0 : TO_NUMBER(month); | |
| 652 date = argc < 3 ? 1 : TO_NUMBER(date); | |
| 653 time = 0; | |
| 654 } else { | |
| 655 month = argc < 2 ? LOCAL_MONTH(this) : TO_NUMBER(month); | |
| 656 date = argc < 3 ? LOCAL_DAY(this) : TO_NUMBER(date); | |
| 657 time = LOCAL_TIME_IN_DAY(this); | |
| 658 } | |
| 659 var day = MakeDay(year, month, date); | |
| 660 return SET_LOCAL_DATE_VALUE(this, MakeDate(day, time)); | |
| 661 } | |
| 662 | |
| 663 | |
| 664 // ECMA 262 - 15.9.5.41 | |
| 665 function DateSetUTCFullYear(year, month, date) { | |
| 666 CHECK_DATE(this); | |
| 667 var t = UTC_DATE_VALUE(this); | |
| 668 year = TO_NUMBER(year); | |
| 669 var argc = %_ArgumentsLength(); | |
| 670 var time ; | |
| 671 if (NUMBER_IS_NAN(t)) { | |
| 672 month = argc < 2 ? 0 : TO_NUMBER(month); | |
| 673 date = argc < 3 ? 1 : TO_NUMBER(date); | |
| 674 time = 0; | |
| 675 } else { | |
| 676 month = argc < 2 ? UTC_MONTH(this) : TO_NUMBER(month); | |
| 677 date = argc < 3 ? UTC_DAY(this) : TO_NUMBER(date); | |
| 678 time = UTC_TIME_IN_DAY(this); | |
| 679 } | |
| 680 var day = MakeDay(year, month, date); | |
| 681 return SET_UTC_DATE_VALUE(this, MakeDate(day, time)); | |
| 682 } | |
| 683 | |
| 684 | |
| 685 // ECMA 262 - 15.9.5.42 | |
| 686 function DateToUTCString() { | |
| 687 CHECK_DATE(this); | |
| 688 var t = UTC_DATE_VALUE(this); | |
| 689 if (NUMBER_IS_NAN(t)) return kInvalidDate; | |
| 690 // Return UTC string of the form: Sat, 31 Jan 1970 23:00:00 GMT | |
| 691 return WeekDays[UTC_WEEKDAY(this)] + ', ' | |
| 692 + TwoDigitString(UTC_DAY(this)) + ' ' | |
| 693 + Months[UTC_MONTH(this)] + ' ' | |
| 694 + UTC_YEAR(this) + ' ' | |
| 695 + TimeStringUTC(this) + ' GMT'; | |
| 696 } | |
| 697 | |
| 698 | |
| 699 // ECMA 262 - B.2.4 | |
| 700 function DateGetYear() { | |
| 701 CHECK_DATE(this); | |
| 702 return LOCAL_YEAR(this) - 1900; | |
| 703 } | |
| 704 | |
| 705 | |
| 706 // ECMA 262 - B.2.5 | |
| 707 function DateSetYear(year) { | |
| 708 CHECK_DATE(this); | |
| 709 year = TO_NUMBER(year); | |
| 710 if (NUMBER_IS_NAN(year)) return SET_UTC_DATE_VALUE(this, NAN); | |
| 711 year = (0 <= TO_INTEGER(year) && TO_INTEGER(year) <= 99) | |
| 712 ? 1900 + TO_INTEGER(year) : year; | |
| 713 var t = LOCAL_DATE_VALUE(this); | |
| 714 var month, date, time; | |
| 715 if (NUMBER_IS_NAN(t)) { | |
| 716 month = 0; | |
| 717 date = 1; | |
| 718 time = 0; | |
| 719 } else { | |
| 720 month = LOCAL_MONTH(this); | |
| 721 date = LOCAL_DAY(this); | |
| 722 time = LOCAL_TIME_IN_DAY(this); | |
| 723 } | |
| 724 var day = MakeDay(year, month, date); | |
| 725 return SET_LOCAL_DATE_VALUE(this, MakeDate(day, time)); | |
| 726 } | |
| 727 | |
| 728 | |
| 729 // ECMA 262 - B.2.6 | |
| 730 // | |
| 731 // Notice that this does not follow ECMA 262 completely. ECMA 262 | |
| 732 // says that toGMTString should be the same Function object as | |
| 733 // toUTCString. JSC does not do this, so for compatibility we do not | |
| 734 // do that either. Instead, we create a new function whose name | |
| 735 // property will return toGMTString. | |
| 736 function DateToGMTString() { | |
| 737 return %_CallFunction(this, DateToUTCString); | |
| 738 } | |
| 739 | |
| 740 | |
| 741 function PadInt(n, digits) { | |
| 742 if (digits == 1) return n; | |
| 743 return n < %_MathPow(10, digits - 1) ? '0' + PadInt(n, digits - 1) : n; | |
| 744 } | |
| 745 | |
| 746 | |
| 747 // ECMA 262 - 20.3.4.36 | |
| 748 function DateToISOString() { | |
| 749 CHECK_DATE(this); | |
| 750 var t = UTC_DATE_VALUE(this); | |
| 751 if (NUMBER_IS_NAN(t)) throw MakeRangeError(kInvalidTimeValue); | |
| 752 var year = UTC_YEAR(this); | |
| 753 var year_string; | |
| 754 if (year >= 0 && year <= 9999) { | |
| 755 year_string = PadInt(year, 4); | |
| 756 } else { | |
| 757 if (year < 0) { | |
| 758 year_string = "-" + PadInt(-year, 6); | |
| 759 } else { | |
| 760 year_string = "+" + PadInt(year, 6); | |
| 761 } | |
| 762 } | |
| 763 return year_string + | |
| 764 '-' + PadInt(UTC_MONTH(this) + 1, 2) + | |
| 765 '-' + PadInt(UTC_DAY(this), 2) + | |
| 766 'T' + PadInt(UTC_HOUR(this), 2) + | |
| 767 ':' + PadInt(UTC_MIN(this), 2) + | |
| 768 ':' + PadInt(UTC_SEC(this), 2) + | |
| 769 '.' + PadInt(UTC_MS(this), 3) + | |
| 770 'Z'; | |
| 771 } | |
| 772 | |
| 773 | |
| 774 // 20.3.4.37 Date.prototype.toJSON ( key ) | |
| 775 function DateToJSON(key) { | |
| 776 var o = TO_OBJECT(this); | |
| 777 var tv = TO_PRIMITIVE_NUMBER(o); | |
| 778 if (IS_NUMBER(tv) && !NUMBER_IS_FINITE(tv)) { | |
| 779 return null; | |
| 780 } | |
| 781 return o.toISOString(); | |
| 782 } | |
| 783 | |
| 784 | |
| 785 var date_cache_version_holder; | |
| 786 var date_cache_version = NAN; | |
| 787 | |
| 788 | |
| 789 function CheckDateCacheCurrent() { | |
| 790 if (!date_cache_version_holder) { | |
| 791 date_cache_version_holder = %DateCacheVersion(); | |
| 792 if (!date_cache_version_holder) return; | |
| 793 } | |
| 794 if (date_cache_version_holder[0] == date_cache_version) { | |
| 795 return; | |
| 796 } | |
| 797 date_cache_version = date_cache_version_holder[0]; | |
| 798 | |
| 799 // Reset the timezone cache: | |
| 800 timezone_cache_time = NAN; | |
| 801 timezone_cache_timezone = UNDEFINED; | |
| 802 | |
| 803 // Reset the date cache: | |
| 804 Date_cache.time = NAN; | |
| 805 Date_cache.string = null; | |
| 806 } | |
| 807 | |
| 808 | |
| 809 function CreateDate(time) { | |
| 810 var date = new GlobalDate(); | |
| 811 date.setTime(time); | |
| 812 return date; | |
| 813 } | |
| 814 | |
| 815 // ------------------------------------------------------------------- | |
| 816 | |
| 817 %SetCode(GlobalDate, DateConstructor); | |
| 818 %FunctionSetPrototype(GlobalDate, new GlobalObject()); | |
| 819 | |
| 820 // Set up non-enumerable properties of the Date object itself. | |
| 821 utils.InstallFunctions(GlobalDate, DONT_ENUM, [ | |
| 822 "UTC", DateUTC, | |
| 823 "parse", DateParse, | |
| 824 "now", DateNow | |
| 825 ]); | |
| 826 | |
| 827 // Set up non-enumerable constructor property of the Date prototype object. | |
| 828 %AddNamedProperty(GlobalDate.prototype, "constructor", GlobalDate, DONT_ENUM); | |
| 829 | |
| 830 // Set up non-enumerable functions of the Date prototype object and | |
| 831 // set their names. | |
| 832 utils.InstallFunctions(GlobalDate.prototype, DONT_ENUM, [ | |
| 833 "toString", DateToString, | |
| 834 "toDateString", DateToDateString, | |
| 835 "toTimeString", DateToTimeString, | |
| 836 "toLocaleString", DateToLocaleString, | |
| 837 "toLocaleDateString", DateToLocaleDateString, | |
| 838 "toLocaleTimeString", DateToLocaleTimeString, | |
| 839 "valueOf", DateValueOf, | |
| 840 "getTime", DateGetTime, | |
| 841 "getFullYear", DateGetFullYear, | |
| 842 "getUTCFullYear", DateGetUTCFullYear, | |
| 843 "getMonth", DateGetMonth, | |
| 844 "getUTCMonth", DateGetUTCMonth, | |
| 845 "getDate", DateGetDate, | |
| 846 "getUTCDate", DateGetUTCDate, | |
| 847 "getDay", DateGetDay, | |
| 848 "getUTCDay", DateGetUTCDay, | |
| 849 "getHours", DateGetHours, | |
| 850 "getUTCHours", DateGetUTCHours, | |
| 851 "getMinutes", DateGetMinutes, | |
| 852 "getUTCMinutes", DateGetUTCMinutes, | |
| 853 "getSeconds", DateGetSeconds, | |
| 854 "getUTCSeconds", DateGetUTCSeconds, | |
| 855 "getMilliseconds", DateGetMilliseconds, | |
| 856 "getUTCMilliseconds", DateGetUTCMilliseconds, | |
| 857 "getTimezoneOffset", DateGetTimezoneOffset, | |
| 858 "setTime", DateSetTime, | |
| 859 "setMilliseconds", DateSetMilliseconds, | |
| 860 "setUTCMilliseconds", DateSetUTCMilliseconds, | |
| 861 "setSeconds", DateSetSeconds, | |
| 862 "setUTCSeconds", DateSetUTCSeconds, | |
| 863 "setMinutes", DateSetMinutes, | |
| 864 "setUTCMinutes", DateSetUTCMinutes, | |
| 865 "setHours", DateSetHours, | |
| 866 "setUTCHours", DateSetUTCHours, | |
| 867 "setDate", DateSetDate, | |
| 868 "setUTCDate", DateSetUTCDate, | |
| 869 "setMonth", DateSetMonth, | |
| 870 "setUTCMonth", DateSetUTCMonth, | |
| 871 "setFullYear", DateSetFullYear, | |
| 872 "setUTCFullYear", DateSetUTCFullYear, | |
| 873 "toGMTString", DateToGMTString, | |
| 874 "toUTCString", DateToUTCString, | |
| 875 "getYear", DateGetYear, | |
| 876 "setYear", DateSetYear, | |
| 877 "toISOString", DateToISOString, | |
| 878 "toJSON", DateToJSON | |
| 879 ]); | |
| 880 | |
| 881 %InstallToContext(["create_date_fun", CreateDate]); | |
| 882 | |
| 883 }) | |
| OLD | NEW |