summaryrefslogtreecommitdiff
path: root/deps/v8/src/js/runtime.js
diff options
context:
space:
mode:
Diffstat (limited to 'deps/v8/src/js/runtime.js')
-rw-r--r--deps/v8/src/js/runtime.js283
1 files changed, 283 insertions, 0 deletions
diff --git a/deps/v8/src/js/runtime.js b/deps/v8/src/js/runtime.js
new file mode 100644
index 0000000000..b5e23671f4
--- /dev/null
+++ b/deps/v8/src/js/runtime.js
@@ -0,0 +1,283 @@
+// Copyright 2006-2008 the V8 project authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+// This files contains runtime support implemented in JavaScript.
+
+// CAUTION: Some of the functions specified in this file are called
+// directly from compiled code. These are the functions with names in
+// ALL CAPS. The compiled code passes the first argument in 'this'.
+
+
+// The following declarations are shared with other native JS files.
+// They are all declared at this one spot to avoid redeclaration errors.
+
+(function(global, utils) {
+
+%CheckIsBootstrapping();
+
+var GlobalArray = global.Array;
+var GlobalBoolean = global.Boolean;
+var GlobalString = global.String;
+var isConcatSpreadableSymbol =
+ utils.ImportNow("is_concat_spreadable_symbol");
+var MakeRangeError;
+
+utils.Import(function(from) {
+ MakeRangeError = from.MakeRangeError;
+});
+
+// ----------------------------------------------------------------------------
+
+/* -----------------------------
+ - - - H e l p e r s - - -
+ -----------------------------
+*/
+
+function APPLY_PREPARE(args) {
+ var length;
+
+ // First check that the receiver is callable.
+ if (!IS_CALLABLE(this)) {
+ throw %make_type_error(kApplyNonFunction, TO_STRING(this), typeof this);
+ }
+
+ // First check whether length is a positive Smi and args is an
+ // array. This is the fast case. If this fails, we do the slow case
+ // that takes care of more eventualities.
+ if (IS_ARRAY(args)) {
+ length = args.length;
+ if (%_IsSmi(length) && length >= 0 && length < kSafeArgumentsLength) {
+ return length;
+ }
+ }
+
+ length = (args == null) ? 0 : TO_UINT32(args.length);
+
+ // We can handle any number of apply arguments if the stack is
+ // big enough, but sanity check the value to avoid overflow when
+ // multiplying with pointer size.
+ if (length > kSafeArgumentsLength) throw %make_range_error(kStackOverflow);
+
+ // Make sure the arguments list has the right type.
+ if (args != null && !IS_SPEC_OBJECT(args)) {
+ throw %make_type_error(kWrongArgs, "Function.prototype.apply");
+ }
+
+ // Return the length which is the number of arguments to copy to the
+ // stack. It is guaranteed to be a small integer at this point.
+ return length;
+}
+
+
+function REFLECT_APPLY_PREPARE(args) {
+ var length;
+
+ // First check that the receiver is callable.
+ if (!IS_CALLABLE(this)) {
+ throw %make_type_error(kApplyNonFunction, TO_STRING(this), typeof this);
+ }
+
+ // First check whether length is a positive Smi and args is an
+ // array. This is the fast case. If this fails, we do the slow case
+ // that takes care of more eventualities.
+ if (IS_ARRAY(args)) {
+ length = args.length;
+ if (%_IsSmi(length) && length >= 0 && length < kSafeArgumentsLength) {
+ return length;
+ }
+ }
+
+ if (!IS_SPEC_OBJECT(args)) {
+ throw %make_type_error(kWrongArgs, "Reflect.apply");
+ }
+
+ length = TO_LENGTH(args.length);
+
+ // We can handle any number of apply arguments if the stack is
+ // big enough, but sanity check the value to avoid overflow when
+ // multiplying with pointer size.
+ if (length > kSafeArgumentsLength) throw %make_range_error(kStackOverflow);
+
+ // Return the length which is the number of arguments to copy to the
+ // stack. It is guaranteed to be a small integer at this point.
+ return length;
+}
+
+
+function REFLECT_CONSTRUCT_PREPARE(
+ args, newTarget) {
+ var length;
+ var ctorOk = IS_CALLABLE(this) && %IsConstructor(this);
+ var newTargetOk = IS_CALLABLE(newTarget) && %IsConstructor(newTarget);
+
+ // First check whether length is a positive Smi and args is an
+ // array. This is the fast case. If this fails, we do the slow case
+ // that takes care of more eventualities.
+ if (IS_ARRAY(args)) {
+ length = args.length;
+ if (%_IsSmi(length) && length >= 0 && length < kSafeArgumentsLength &&
+ ctorOk && newTargetOk) {
+ return length;
+ }
+ }
+
+ if (!ctorOk) {
+ if (!IS_CALLABLE(this)) {
+ throw %make_type_error(kCalledNonCallable, TO_STRING(this));
+ } else {
+ throw %make_type_error(kNotConstructor, TO_STRING(this));
+ }
+ }
+
+ if (!newTargetOk) {
+ if (!IS_CALLABLE(newTarget)) {
+ throw %make_type_error(kCalledNonCallable, TO_STRING(newTarget));
+ } else {
+ throw %make_type_error(kNotConstructor, TO_STRING(newTarget));
+ }
+ }
+
+ if (!IS_SPEC_OBJECT(args)) {
+ throw %make_type_error(kWrongArgs, "Reflect.construct");
+ }
+
+ length = TO_LENGTH(args.length);
+
+ // We can handle any number of apply arguments if the stack is
+ // big enough, but sanity check the value to avoid overflow when
+ // multiplying with pointer size.
+ if (length > kSafeArgumentsLength) throw %make_range_error(kStackOverflow);
+
+ // Return the length which is the number of arguments to copy to the
+ // stack. It is guaranteed to be a small integer at this point.
+ return length;
+}
+
+
+function CONCAT_ITERABLE_TO_ARRAY(iterable) {
+ return %concat_iterable_to_array(this, iterable);
+};
+
+
+/* -------------------------------------
+ - - - C o n v e r s i o n s - - -
+ -------------------------------------
+*/
+
+// ES5, section 9.12
+function SameValue(x, y) {
+ if (typeof x != typeof y) return false;
+ if (IS_NUMBER(x)) {
+ if (NUMBER_IS_NAN(x) && NUMBER_IS_NAN(y)) return true;
+ // x is +0 and y is -0 or vice versa.
+ if (x === 0 && y === 0 && %_IsMinusZero(x) != %_IsMinusZero(y)) {
+ return false;
+ }
+ }
+ if (IS_SIMD_VALUE(x)) return %SimdSameValue(x, y);
+ return x === y;
+}
+
+
+// ES6, section 7.2.4
+function SameValueZero(x, y) {
+ if (typeof x != typeof y) return false;
+ if (IS_NUMBER(x)) {
+ if (NUMBER_IS_NAN(x) && NUMBER_IS_NAN(y)) return true;
+ }
+ if (IS_SIMD_VALUE(x)) return %SimdSameValueZero(x, y);
+ return x === y;
+}
+
+
+function ConcatIterableToArray(target, iterable) {
+ var index = target.length;
+ for (var element of iterable) {
+ AddIndexedProperty(target, index++, element);
+ }
+ return target;
+}
+
+
+/* ---------------------------------
+ - - - U t i l i t i e s - - -
+ ---------------------------------
+*/
+
+
+// This function should be called rather than %AddElement in contexts where the
+// argument might not be less than 2**32-1. ES2015 ToLength semantics mean that
+// this is a concern at basically all callsites.
+function AddIndexedProperty(obj, index, value) {
+ if (index === TO_UINT32(index) && index !== kMaxUint32) {
+ %AddElement(obj, index, value);
+ } else {
+ %AddNamedProperty(obj, TO_STRING(index), value, NONE);
+ }
+}
+%SetForceInlineFlag(AddIndexedProperty);
+
+
+// ES6, draft 10-14-14, section 22.1.3.1.1
+function IsConcatSpreadable(O) {
+ if (!IS_SPEC_OBJECT(O)) return false;
+ var spreadable = O[isConcatSpreadableSymbol];
+ if (IS_UNDEFINED(spreadable)) return IS_ARRAY(O);
+ return TO_BOOLEAN(spreadable);
+}
+
+
+function ToPositiveInteger(x, rangeErrorIndex) {
+ var i = TO_INTEGER_MAP_MINUS_ZERO(x);
+ if (i < 0) throw MakeRangeError(rangeErrorIndex);
+ return i;
+}
+
+
+function MaxSimple(a, b) {
+ return a > b ? a : b;
+}
+
+
+function MinSimple(a, b) {
+ return a > b ? b : a;
+}
+
+
+%SetForceInlineFlag(MaxSimple);
+%SetForceInlineFlag(MinSimple);
+
+//----------------------------------------------------------------------------
+
+// NOTE: Setting the prototype for Array must take place as early as
+// possible due to code generation for array literals. When
+// generating code for a array literal a boilerplate array is created
+// that is cloned when running the code. It is essential that the
+// boilerplate gets the right prototype.
+%FunctionSetPrototype(GlobalArray, new GlobalArray(0));
+
+// ----------------------------------------------------------------------------
+// Exports
+
+utils.Export(function(to) {
+ to.AddIndexedProperty = AddIndexedProperty;
+ to.MaxSimple = MaxSimple;
+ to.MinSimple = MinSimple;
+ to.SameValue = SameValue;
+ to.SameValueZero = SameValueZero;
+ to.ToPositiveInteger = ToPositiveInteger;
+});
+
+%InstallToContext([
+ "apply_prepare_builtin", APPLY_PREPARE,
+ "concat_iterable_to_array_builtin", CONCAT_ITERABLE_TO_ARRAY,
+ "reflect_apply_prepare_builtin", REFLECT_APPLY_PREPARE,
+ "reflect_construct_prepare_builtin", REFLECT_CONSTRUCT_PREPARE,
+]);
+
+%InstallToContext([
+ "concat_iterable_to_array", ConcatIterableToArray,
+]);
+
+})