| OLD | NEW |
| 1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 the V8 project authors. All rights reserved. |
| 2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
| 3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
| 4 // met: | 4 // met: |
| 5 // | 5 // |
| 6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
| 7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
| 8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
| 9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
| 10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
| (...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 72 %FunctionSetName(getter, name); | 72 %FunctionSetName(getter, name); |
| 73 %FunctionSetName(setter, name); | 73 %FunctionSetName(setter, name); |
| 74 %FunctionRemovePrototype(getter); | 74 %FunctionRemovePrototype(getter); |
| 75 %FunctionRemovePrototype(setter); | 75 %FunctionRemovePrototype(setter); |
| 76 %DefineOrRedefineAccessorProperty(object, name, getter, setter, DONT_ENUM); | 76 %DefineOrRedefineAccessorProperty(object, name, getter, setter, DONT_ENUM); |
| 77 %SetNativeFlag(getter); | 77 %SetNativeFlag(getter); |
| 78 %SetNativeFlag(setter); | 78 %SetNativeFlag(setter); |
| 79 } | 79 } |
| 80 | 80 |
| 81 | 81 |
| 82 // Helper function for installing constant properties on objects. |
| 83 function InstallConstants(object, constants) { |
| 84 if (constants.length >= 4) { |
| 85 %OptimizeObjectForAddingMultipleProperties(object, constants.length >> 1); |
| 86 } |
| 87 var attributes = DONT_ENUM | DONT_DELETE | READ_ONLY; |
| 88 for (var i = 0; i < constants.length; i += 2) { |
| 89 var name = constants[i]; |
| 90 var k = constants[i + 1]; |
| 91 %SetProperty(object, name, k, attributes); |
| 92 } |
| 93 %ToFastProperties(object); |
| 94 } |
| 95 |
| 96 |
| 82 // Prevents changes to the prototype of a built-in function. | 97 // Prevents changes to the prototype of a built-in function. |
| 83 // The "prototype" property of the function object is made non-configurable, | 98 // The "prototype" property of the function object is made non-configurable, |
| 84 // and the prototype object is made non-extensible. The latter prevents | 99 // and the prototype object is made non-extensible. The latter prevents |
| 85 // changing the __proto__ property. | 100 // changing the __proto__ property. |
| 86 function SetUpLockedPrototype(constructor, fields, methods) { | 101 function SetUpLockedPrototype(constructor, fields, methods) { |
| 87 %CheckIsBootstrapping(); | 102 %CheckIsBootstrapping(); |
| 88 var prototype = constructor.prototype; | 103 var prototype = constructor.prototype; |
| 89 // Install functions first, because this function is used to initialize | 104 // Install functions first, because this function is used to initialize |
| 90 // PropertyDescriptor itself. | 105 // PropertyDescriptor itself. |
| 91 var property_count = (methods.length >> 1) + (fields ? fields.length : 0); | 106 var property_count = (methods.length >> 1) + (fields ? fields.length : 0); |
| (...skipping 938 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1030 } | 1045 } |
| 1031 array[index] = s; | 1046 array[index] = s; |
| 1032 ++realLength; | 1047 ++realLength; |
| 1033 names[s] = 0; | 1048 names[s] = 0; |
| 1034 } | 1049 } |
| 1035 array.length = realLength; | 1050 array.length = realLength; |
| 1036 return array; | 1051 return array; |
| 1037 } | 1052 } |
| 1038 | 1053 |
| 1039 | 1054 |
| 1040 // ES5 section 15.2.3.4. | 1055 function ObjectGetOwnPropertyKeys(obj, symbolsOnly) { |
| 1041 function ObjectGetOwnPropertyNames(obj) { | |
| 1042 if (!IS_SPEC_OBJECT(obj)) { | |
| 1043 throw MakeTypeError("called_on_non_object", ["Object.getOwnPropertyNames"]); | |
| 1044 } | |
| 1045 // Special handling for proxies. | |
| 1046 if (%IsJSProxy(obj)) { | |
| 1047 var handler = %GetHandler(obj); | |
| 1048 var names = CallTrap0(handler, "getOwnPropertyNames", UNDEFINED); | |
| 1049 return ToNameArray(names, "getOwnPropertyNames", false); | |
| 1050 } | |
| 1051 | |
| 1052 var nameArrays = new InternalArray(); | 1056 var nameArrays = new InternalArray(); |
| 1057 var filter = symbolsOnly ? |
| 1058 PROPERTY_ATTRIBUTES_STRING | PROPERTY_ATTRIBUTES_PRIVATE_SYMBOL : |
| 1059 PROPERTY_ATTRIBUTES_SYMBOLIC; |
| 1053 | 1060 |
| 1054 // Find all the indexed properties. | 1061 // Find all the indexed properties. |
| 1055 | 1062 |
| 1056 // Get the local element names. | 1063 // Only get the local element names if we want to include string keys. |
| 1057 var localElementNames = %GetLocalElementNames(obj); | 1064 if (!symbolsOnly) { |
| 1058 for (var i = 0; i < localElementNames.length; ++i) { | 1065 var localElementNames = %GetLocalElementNames(obj); |
| 1059 localElementNames[i] = %_NumberToString(localElementNames[i]); | 1066 for (var i = 0; i < localElementNames.length; ++i) { |
| 1060 } | 1067 localElementNames[i] = %_NumberToString(localElementNames[i]); |
| 1061 nameArrays.push(localElementNames); | 1068 } |
| 1069 nameArrays.push(localElementNames); |
| 1062 | 1070 |
| 1063 // Get names for indexed interceptor properties. | 1071 // Get names for indexed interceptor properties. |
| 1064 var interceptorInfo = %GetInterceptorInfo(obj); | 1072 var interceptorInfo = %GetInterceptorInfo(obj); |
| 1065 if ((interceptorInfo & 1) != 0) { | 1073 if ((interceptorInfo & 1) != 0) { |
| 1066 var indexedInterceptorNames = %GetIndexedInterceptorElementNames(obj); | 1074 var indexedInterceptorNames = %GetIndexedInterceptorElementNames(obj); |
| 1067 if (!IS_UNDEFINED(indexedInterceptorNames)) { | 1075 if (!IS_UNDEFINED(indexedInterceptorNames)) { |
| 1068 nameArrays.push(indexedInterceptorNames); | 1076 nameArrays.push(indexedInterceptorNames); |
| 1077 } |
| 1069 } | 1078 } |
| 1070 } | 1079 } |
| 1071 | 1080 |
| 1072 // Find all the named properties. | 1081 // Find all the named properties. |
| 1073 | 1082 |
| 1074 // Get the local property names. | 1083 // Get the local property names. |
| 1075 nameArrays.push(%GetLocalPropertyNames(obj, false)); | 1084 nameArrays.push(%GetLocalPropertyNames(obj, filter)); |
| 1076 | 1085 |
| 1077 // Get names for named interceptor properties if any. | 1086 // Get names for named interceptor properties if any. |
| 1078 if ((interceptorInfo & 2) != 0) { | 1087 if ((interceptorInfo & 2) != 0) { |
| 1079 var namedInterceptorNames = %GetNamedInterceptorPropertyNames(obj); | 1088 var namedInterceptorNames = |
| 1089 %GetNamedInterceptorPropertyNames(obj); |
| 1080 if (!IS_UNDEFINED(namedInterceptorNames)) { | 1090 if (!IS_UNDEFINED(namedInterceptorNames)) { |
| 1081 nameArrays.push(namedInterceptorNames); | 1091 nameArrays.push(namedInterceptorNames); |
| 1082 } | 1092 } |
| 1083 } | 1093 } |
| 1084 | 1094 |
| 1085 var propertyNames = | 1095 var propertyNames = |
| 1086 %Apply(InternalArray.prototype.concat, | 1096 %Apply(InternalArray.prototype.concat, |
| 1087 nameArrays[0], nameArrays, 1, nameArrays.length - 1); | 1097 nameArrays[0], nameArrays, 1, nameArrays.length - 1); |
| 1088 | 1098 |
| 1089 // Property names are expected to be unique strings, | 1099 // Property names are expected to be unique strings, |
| 1090 // but interceptors can interfere with that assumption. | 1100 // but interceptors can interfere with that assumption. |
| 1091 if (interceptorInfo != 0) { | 1101 if (interceptorInfo != 0) { |
| 1092 var propertySet = { __proto__: null }; | 1102 var seenKeys = { __proto__: null }; |
| 1093 var j = 0; | 1103 var j = 0; |
| 1094 for (var i = 0; i < propertyNames.length; ++i) { | 1104 for (var i = 0; i < propertyNames.length; ++i) { |
| 1095 if (IS_SYMBOL(propertyNames[i])) continue; | 1105 var name = propertyNames[i]; |
| 1096 var name = ToString(propertyNames[i]); | 1106 if (symbolsOnly) { |
| 1097 // We need to check for the exact property value since for intrinsic | 1107 if (!IS_SYMBOL(name) || IS_PRIVATE(name)) continue; |
| 1098 // properties like toString if(propertySet["toString"]) will always | 1108 } else { |
| 1099 // succeed. | 1109 if (IS_SYMBOL(name)) continue; |
| 1100 if (propertySet[name] === true) { | 1110 name = ToString(name); |
| 1101 continue; | |
| 1102 } | 1111 } |
| 1103 propertySet[name] = true; | 1112 if (seenKeys[name]) continue; |
| 1113 seenKeys[name] = true; |
| 1104 propertyNames[j++] = name; | 1114 propertyNames[j++] = name; |
| 1105 } | 1115 } |
| 1106 propertyNames.length = j; | 1116 propertyNames.length = j; |
| 1107 } | 1117 } |
| 1108 | 1118 |
| 1109 return propertyNames; | 1119 return propertyNames; |
| 1110 } | 1120 } |
| 1111 | 1121 |
| 1112 | 1122 |
| 1123 // ES5 section 15.2.3.4. |
| 1124 function ObjectGetOwnPropertyNames(obj) { |
| 1125 if (!IS_SPEC_OBJECT(obj)) { |
| 1126 throw MakeTypeError("called_on_non_object", ["Object.getOwnPropertyNames"]); |
| 1127 } |
| 1128 // Special handling for proxies. |
| 1129 if (%IsJSProxy(obj)) { |
| 1130 var handler = %GetHandler(obj); |
| 1131 var names = CallTrap0(handler, "getOwnPropertyNames", UNDEFINED); |
| 1132 return ToNameArray(names, "getOwnPropertyNames", false); |
| 1133 } |
| 1134 |
| 1135 return ObjectGetOwnPropertyKeys(obj, false); |
| 1136 } |
| 1137 |
| 1138 |
| 1113 // ES5 section 15.2.3.5. | 1139 // ES5 section 15.2.3.5. |
| 1114 function ObjectCreate(proto, properties) { | 1140 function ObjectCreate(proto, properties) { |
| 1115 if (!IS_SPEC_OBJECT(proto) && proto !== null) { | 1141 if (!IS_SPEC_OBJECT(proto) && proto !== null) { |
| 1116 throw MakeTypeError("proto_object_or_null", [proto]); | 1142 throw MakeTypeError("proto_object_or_null", [proto]); |
| 1117 } | 1143 } |
| 1118 var obj = { __proto__: proto }; | 1144 var obj = { __proto__: proto }; |
| 1119 if (!IS_UNDEFINED(properties)) ObjectDefineProperties(obj, properties); | 1145 if (!IS_UNDEFINED(properties)) ObjectDefineProperties(obj, properties); |
| 1120 return obj; | 1146 return obj; |
| 1121 } | 1147 } |
| 1122 | 1148 |
| (...skipping 289 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1412 // Set up non-enumerable functions in the Object object. | 1438 // Set up non-enumerable functions in the Object object. |
| 1413 InstallFunctions($Object, DONT_ENUM, $Array( | 1439 InstallFunctions($Object, DONT_ENUM, $Array( |
| 1414 "keys", ObjectKeys, | 1440 "keys", ObjectKeys, |
| 1415 "create", ObjectCreate, | 1441 "create", ObjectCreate, |
| 1416 "defineProperty", ObjectDefineProperty, | 1442 "defineProperty", ObjectDefineProperty, |
| 1417 "defineProperties", ObjectDefineProperties, | 1443 "defineProperties", ObjectDefineProperties, |
| 1418 "freeze", ObjectFreeze, | 1444 "freeze", ObjectFreeze, |
| 1419 "getPrototypeOf", ObjectGetPrototypeOf, | 1445 "getPrototypeOf", ObjectGetPrototypeOf, |
| 1420 "getOwnPropertyDescriptor", ObjectGetOwnPropertyDescriptor, | 1446 "getOwnPropertyDescriptor", ObjectGetOwnPropertyDescriptor, |
| 1421 "getOwnPropertyNames", ObjectGetOwnPropertyNames, | 1447 "getOwnPropertyNames", ObjectGetOwnPropertyNames, |
| 1448 // getOwnPropertySymbols is added in symbol.js. |
| 1422 "is", ObjectIs, | 1449 "is", ObjectIs, |
| 1423 "isExtensible", ObjectIsExtensible, | 1450 "isExtensible", ObjectIsExtensible, |
| 1424 "isFrozen", ObjectIsFrozen, | 1451 "isFrozen", ObjectIsFrozen, |
| 1425 "isSealed", ObjectIsSealed, | 1452 "isSealed", ObjectIsSealed, |
| 1426 "preventExtensions", ObjectPreventExtension, | 1453 "preventExtensions", ObjectPreventExtension, |
| 1427 "seal", ObjectSeal | 1454 "seal", ObjectSeal |
| 1455 // deliverChangeRecords, getNotifier, observe and unobserve are added |
| 1456 // in object-observe.js. |
| 1428 )); | 1457 )); |
| 1429 } | 1458 } |
| 1430 | 1459 |
| 1431 SetUpObject(); | 1460 SetUpObject(); |
| 1432 | 1461 |
| 1433 | 1462 |
| 1434 // ---------------------------------------------------------------------------- | 1463 // ---------------------------------------------------------------------------- |
| 1435 // Boolean | 1464 // Boolean |
| 1436 | 1465 |
| 1437 function BooleanConstructor(x) { | 1466 function BooleanConstructor(x) { |
| (...skipping 179 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1617 return %NumberToPrecision(x, p); | 1646 return %NumberToPrecision(x, p); |
| 1618 } | 1647 } |
| 1619 | 1648 |
| 1620 | 1649 |
| 1621 // Harmony isFinite. | 1650 // Harmony isFinite. |
| 1622 function NumberIsFinite(number) { | 1651 function NumberIsFinite(number) { |
| 1623 return IS_NUMBER(number) && NUMBER_IS_FINITE(number); | 1652 return IS_NUMBER(number) && NUMBER_IS_FINITE(number); |
| 1624 } | 1653 } |
| 1625 | 1654 |
| 1626 | 1655 |
| 1656 // Harmony isInteger |
| 1657 function NumberIsInteger(number) { |
| 1658 return NumberIsFinite(number) && TO_INTEGER(number) == number; |
| 1659 } |
| 1660 |
| 1661 |
| 1627 // Harmony isNaN. | 1662 // Harmony isNaN. |
| 1628 function NumberIsNaN(number) { | 1663 function NumberIsNaN(number) { |
| 1629 return IS_NUMBER(number) && NUMBER_IS_NAN(number); | 1664 return IS_NUMBER(number) && NUMBER_IS_NAN(number); |
| 1630 } | 1665 } |
| 1631 | 1666 |
| 1632 | 1667 |
| 1668 // Harmony isSafeInteger |
| 1669 function NumberIsSafeInteger(number) { |
| 1670 if (NumberIsFinite(number)) { |
| 1671 var integral = TO_INTEGER(number); |
| 1672 if (integral == number) |
| 1673 return MathAbs(integral) <= $Number.MAX_SAFE_INTEGER; |
| 1674 } |
| 1675 return false; |
| 1676 } |
| 1677 |
| 1678 |
| 1633 // ---------------------------------------------------------------------------- | 1679 // ---------------------------------------------------------------------------- |
| 1634 | 1680 |
| 1635 function SetUpNumber() { | 1681 function SetUpNumber() { |
| 1636 %CheckIsBootstrapping(); | 1682 %CheckIsBootstrapping(); |
| 1637 | 1683 |
| 1638 %SetCode($Number, NumberConstructor); | 1684 %SetCode($Number, NumberConstructor); |
| 1639 %FunctionSetPrototype($Number, new $Number(0)); | 1685 %FunctionSetPrototype($Number, new $Number(0)); |
| 1640 | 1686 |
| 1641 %OptimizeObjectForAddingMultipleProperties($Number.prototype, 8); | 1687 %OptimizeObjectForAddingMultipleProperties($Number.prototype, 8); |
| 1642 // Set up the constructor property on the Number prototype object. | 1688 // Set up the constructor property on the Number prototype object. |
| 1643 %SetProperty($Number.prototype, "constructor", $Number, DONT_ENUM); | 1689 %SetProperty($Number.prototype, "constructor", $Number, DONT_ENUM); |
| 1644 | 1690 |
| 1645 %OptimizeObjectForAddingMultipleProperties($Number, 5); | 1691 InstallConstants($Number, $Array( |
| 1646 // ECMA-262 section 15.7.3.1. | 1692 // ECMA-262 section 15.7.3.1. |
| 1647 %SetProperty($Number, | 1693 "MAX_VALUE", 1.7976931348623157e+308, |
| 1648 "MAX_VALUE", | 1694 // ECMA-262 section 15.7.3.2. |
| 1649 1.7976931348623157e+308, | 1695 "MIN_VALUE", 5e-324, |
| 1650 DONT_ENUM | DONT_DELETE | READ_ONLY); | 1696 // ECMA-262 section 15.7.3.3. |
| 1697 "NaN", NAN, |
| 1698 // ECMA-262 section 15.7.3.4. |
| 1699 "NEGATIVE_INFINITY", -INFINITY, |
| 1700 // ECMA-262 section 15.7.3.5. |
| 1701 "POSITIVE_INFINITY", INFINITY, |
| 1651 | 1702 |
| 1652 // ECMA-262 section 15.7.3.2. | 1703 // --- Harmony constants (no spec refs until settled.) |
| 1653 %SetProperty($Number, "MIN_VALUE", 5e-324, | |
| 1654 DONT_ENUM | DONT_DELETE | READ_ONLY); | |
| 1655 | 1704 |
| 1656 // ECMA-262 section 15.7.3.3. | 1705 "MAX_SAFE_INTEGER", %_MathPow(2, 53) - 1, |
| 1657 %SetProperty($Number, "NaN", NAN, DONT_ENUM | DONT_DELETE | READ_ONLY); | 1706 "MIN_SAFE_INTEGER", -%_MathPow(2, 53) + 1, |
| 1658 | 1707 "EPSILON", %_MathPow(2, -52) |
| 1659 // ECMA-262 section 15.7.3.4. | 1708 )); |
| 1660 %SetProperty($Number, | |
| 1661 "NEGATIVE_INFINITY", | |
| 1662 -INFINITY, | |
| 1663 DONT_ENUM | DONT_DELETE | READ_ONLY); | |
| 1664 | |
| 1665 // ECMA-262 section 15.7.3.5. | |
| 1666 %SetProperty($Number, | |
| 1667 "POSITIVE_INFINITY", | |
| 1668 INFINITY, | |
| 1669 DONT_ENUM | DONT_DELETE | READ_ONLY); | |
| 1670 %ToFastProperties($Number); | |
| 1671 | 1709 |
| 1672 // Set up non-enumerable functions on the Number prototype object. | 1710 // Set up non-enumerable functions on the Number prototype object. |
| 1673 InstallFunctions($Number.prototype, DONT_ENUM, $Array( | 1711 InstallFunctions($Number.prototype, DONT_ENUM, $Array( |
| 1674 "toString", NumberToString, | 1712 "toString", NumberToString, |
| 1675 "toLocaleString", NumberToLocaleString, | 1713 "toLocaleString", NumberToLocaleString, |
| 1676 "valueOf", NumberValueOf, | 1714 "valueOf", NumberValueOf, |
| 1677 "toFixed", NumberToFixed, | 1715 "toFixed", NumberToFixed, |
| 1678 "toExponential", NumberToExponential, | 1716 "toExponential", NumberToExponential, |
| 1679 "toPrecision", NumberToPrecision | 1717 "toPrecision", NumberToPrecision |
| 1680 )); | 1718 )); |
| 1719 |
| 1720 // Harmony Number constructor additions |
| 1681 InstallFunctions($Number, DONT_ENUM, $Array( | 1721 InstallFunctions($Number, DONT_ENUM, $Array( |
| 1682 "isFinite", NumberIsFinite, | 1722 "isFinite", NumberIsFinite, |
| 1683 "isNaN", NumberIsNaN | 1723 "isInteger", NumberIsInteger, |
| 1724 "isNaN", NumberIsNaN, |
| 1725 "isSafeInteger", NumberIsSafeInteger, |
| 1726 "parseInt", GlobalParseInt, |
| 1727 "parseFloat", GlobalParseFloat |
| 1684 )); | 1728 )); |
| 1685 } | 1729 } |
| 1686 | 1730 |
| 1687 SetUpNumber(); | 1731 SetUpNumber(); |
| 1688 | 1732 |
| 1689 | 1733 |
| 1690 // ---------------------------------------------------------------------------- | 1734 // ---------------------------------------------------------------------------- |
| 1691 // Function | 1735 // Function |
| 1692 | 1736 |
| 1693 function FunctionSourceString(func) { | 1737 function FunctionSourceString(func) { |
| (...skipping 150 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1844 // Eventually, we should move to a real event queue that allows to maintain | 1888 // Eventually, we should move to a real event queue that allows to maintain |
| 1845 // relative ordering of different kinds of tasks. | 1889 // relative ordering of different kinds of tasks. |
| 1846 | 1890 |
| 1847 RunMicrotasks.runners = new InternalArray; | 1891 RunMicrotasks.runners = new InternalArray; |
| 1848 | 1892 |
| 1849 function RunMicrotasks() { | 1893 function RunMicrotasks() { |
| 1850 while (%SetMicrotaskPending(false)) { | 1894 while (%SetMicrotaskPending(false)) { |
| 1851 for (var i in RunMicrotasks.runners) RunMicrotasks.runners[i](); | 1895 for (var i in RunMicrotasks.runners) RunMicrotasks.runners[i](); |
| 1852 } | 1896 } |
| 1853 } | 1897 } |
| OLD | NEW |