OLD | NEW |
1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include "src/bootstrapper.h" | 5 #include "src/bootstrapper.h" |
6 | 6 |
7 #include "src/accessors.h" | 7 #include "src/accessors.h" |
8 #include "src/api-natives.h" | 8 #include "src/api-natives.h" |
9 #include "src/code-stubs.h" | 9 #include "src/code-stubs.h" |
10 #include "src/extensions/externalize-string-extension.h" | 10 #include "src/extensions/externalize-string-extension.h" |
(...skipping 251 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
262 // 'from'. | 262 // 'from'. |
263 void TransferObject(Handle<JSObject> from, Handle<JSObject> to); | 263 void TransferObject(Handle<JSObject> from, Handle<JSObject> to); |
264 void TransferNamedProperties(Handle<JSObject> from, Handle<JSObject> to); | 264 void TransferNamedProperties(Handle<JSObject> from, Handle<JSObject> to); |
265 void TransferIndexedProperties(Handle<JSObject> from, Handle<JSObject> to); | 265 void TransferIndexedProperties(Handle<JSObject> from, Handle<JSObject> to); |
266 | 266 |
267 enum FunctionMode { | 267 enum FunctionMode { |
268 // With prototype. | 268 // With prototype. |
269 FUNCTION_WITH_WRITEABLE_PROTOTYPE, | 269 FUNCTION_WITH_WRITEABLE_PROTOTYPE, |
270 FUNCTION_WITH_READONLY_PROTOTYPE, | 270 FUNCTION_WITH_READONLY_PROTOTYPE, |
271 // Without prototype. | 271 // Without prototype. |
272 FUNCTION_WITHOUT_PROTOTYPE, | 272 FUNCTION_WITHOUT_PROTOTYPE |
273 BOUND_FUNCTION | |
274 }; | 273 }; |
275 | 274 |
276 static bool IsFunctionModeWithPrototype(FunctionMode function_mode) { | 275 static bool IsFunctionModeWithPrototype(FunctionMode function_mode) { |
277 return (function_mode == FUNCTION_WITH_WRITEABLE_PROTOTYPE || | 276 return (function_mode == FUNCTION_WITH_WRITEABLE_PROTOTYPE || |
278 function_mode == FUNCTION_WITH_READONLY_PROTOTYPE); | 277 function_mode == FUNCTION_WITH_READONLY_PROTOTYPE); |
279 } | 278 } |
280 | 279 |
281 Handle<Map> CreateSloppyFunctionMap(FunctionMode function_mode); | 280 Handle<Map> CreateSloppyFunctionMap(FunctionMode function_mode); |
282 | 281 |
283 void SetFunctionInstanceDescriptor(Handle<Map> map, | 282 void SetFunctionInstanceDescriptor(Handle<Map> map, |
(...skipping 195 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
479 AccessorConstantDescriptor d(Handle<Name>(Name::cast(prototype->name())), | 478 AccessorConstantDescriptor d(Handle<Name>(Name::cast(prototype->name())), |
480 prototype, ro_attribs); | 479 prototype, ro_attribs); |
481 map->AppendDescriptor(&d); | 480 map->AppendDescriptor(&d); |
482 } | 481 } |
483 } | 482 } |
484 | 483 |
485 | 484 |
486 Handle<Map> Genesis::CreateSloppyFunctionMap(FunctionMode function_mode) { | 485 Handle<Map> Genesis::CreateSloppyFunctionMap(FunctionMode function_mode) { |
487 Handle<Map> map = factory()->NewMap(JS_FUNCTION_TYPE, JSFunction::kSize); | 486 Handle<Map> map = factory()->NewMap(JS_FUNCTION_TYPE, JSFunction::kSize); |
488 SetFunctionInstanceDescriptor(map, function_mode); | 487 SetFunctionInstanceDescriptor(map, function_mode); |
489 map->set_is_constructor(IsFunctionModeWithPrototype(function_mode)); | 488 if (IsFunctionModeWithPrototype(function_mode)) map->set_is_constructor(); |
490 map->set_is_callable(); | 489 map->set_is_callable(); |
491 return map; | 490 return map; |
492 } | 491 } |
493 | 492 |
494 | 493 |
495 Handle<JSFunction> Genesis::CreateEmptyFunction(Isolate* isolate) { | 494 Handle<JSFunction> Genesis::CreateEmptyFunction(Isolate* isolate) { |
496 // Allocate the map for function instances. Maps are allocated first and their | 495 // Allocate the map for function instances. Maps are allocated first and their |
497 // prototypes patched later, once empty function is created. | 496 // prototypes patched later, once empty function is created. |
498 | 497 |
499 // Functions with this map will not have a 'prototype' property, and | 498 // Functions with this map will not have a 'prototype' property, and |
(...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
602 int size = IsFunctionModeWithPrototype(function_mode) ? 3 : 2; | 601 int size = IsFunctionModeWithPrototype(function_mode) ? 3 : 2; |
603 Map::EnsureDescriptorSlack(map, size); | 602 Map::EnsureDescriptorSlack(map, size); |
604 | 603 |
605 PropertyAttributes rw_attribs = | 604 PropertyAttributes rw_attribs = |
606 static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE); | 605 static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE); |
607 PropertyAttributes ro_attribs = | 606 PropertyAttributes ro_attribs = |
608 static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY); | 607 static_cast<PropertyAttributes>(DONT_ENUM | DONT_DELETE | READ_ONLY); |
609 PropertyAttributes roc_attribs = | 608 PropertyAttributes roc_attribs = |
610 static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY); | 609 static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY); |
611 | 610 |
612 if (function_mode == BOUND_FUNCTION) { | 611 DCHECK(function_mode == FUNCTION_WITH_WRITEABLE_PROTOTYPE || |
613 { // Add length. | 612 function_mode == FUNCTION_WITH_READONLY_PROTOTYPE || |
614 Handle<String> length_string = isolate()->factory()->length_string(); | 613 function_mode == FUNCTION_WITHOUT_PROTOTYPE); |
615 DataDescriptor d(length_string, 0, roc_attribs, Representation::Tagged()); | 614 { // Add length. |
616 map->AppendDescriptor(&d); | 615 Handle<AccessorInfo> length = |
617 } | 616 Accessors::FunctionLengthInfo(isolate(), roc_attribs); |
618 { // Add name. | 617 AccessorConstantDescriptor d(Handle<Name>(Name::cast(length->name())), |
619 Handle<String> name_string = isolate()->factory()->name_string(); | 618 length, roc_attribs); |
620 DataDescriptor d(name_string, 1, roc_attribs, Representation::Tagged()); | 619 map->AppendDescriptor(&d); |
621 map->AppendDescriptor(&d); | 620 } |
622 } | 621 { // Add name. |
623 } else { | 622 Handle<AccessorInfo> name = |
624 DCHECK(function_mode == FUNCTION_WITH_WRITEABLE_PROTOTYPE || | 623 Accessors::FunctionNameInfo(isolate(), roc_attribs); |
625 function_mode == FUNCTION_WITH_READONLY_PROTOTYPE || | 624 AccessorConstantDescriptor d(Handle<Name>(Name::cast(name->name())), name, |
626 function_mode == FUNCTION_WITHOUT_PROTOTYPE); | 625 roc_attribs); |
627 { // Add length. | 626 map->AppendDescriptor(&d); |
628 Handle<AccessorInfo> length = | |
629 Accessors::FunctionLengthInfo(isolate(), roc_attribs); | |
630 AccessorConstantDescriptor d(Handle<Name>(Name::cast(length->name())), | |
631 length, roc_attribs); | |
632 map->AppendDescriptor(&d); | |
633 } | |
634 { // Add name. | |
635 Handle<AccessorInfo> name = | |
636 Accessors::FunctionNameInfo(isolate(), roc_attribs); | |
637 AccessorConstantDescriptor d(Handle<Name>(Name::cast(name->name())), name, | |
638 roc_attribs); | |
639 map->AppendDescriptor(&d); | |
640 } | |
641 } | 627 } |
642 if (IsFunctionModeWithPrototype(function_mode)) { | 628 if (IsFunctionModeWithPrototype(function_mode)) { |
643 // Add prototype. | 629 // Add prototype. |
644 PropertyAttributes attribs = | 630 PropertyAttributes attribs = |
645 function_mode == FUNCTION_WITH_WRITEABLE_PROTOTYPE ? rw_attribs | 631 function_mode == FUNCTION_WITH_WRITEABLE_PROTOTYPE ? rw_attribs |
646 : ro_attribs; | 632 : ro_attribs; |
647 Handle<AccessorInfo> prototype = | 633 Handle<AccessorInfo> prototype = |
648 Accessors::FunctionPrototypeInfo(isolate(), attribs); | 634 Accessors::FunctionPrototypeInfo(isolate(), attribs); |
649 AccessorConstantDescriptor d(Handle<Name>(Name::cast(prototype->name())), | 635 AccessorConstantDescriptor d(Handle<Name>(Name::cast(prototype->name())), |
650 prototype, attribs); | 636 prototype, attribs); |
(...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
725 Builtins::kRestrictedStrictArgumentsPropertiesThrower); | 711 Builtins::kRestrictedStrictArgumentsPropertiesThrower); |
726 } | 712 } |
727 return strict_poison_function_; | 713 return strict_poison_function_; |
728 } | 714 } |
729 | 715 |
730 | 716 |
731 Handle<Map> Genesis::CreateStrictFunctionMap( | 717 Handle<Map> Genesis::CreateStrictFunctionMap( |
732 FunctionMode function_mode, Handle<JSFunction> empty_function) { | 718 FunctionMode function_mode, Handle<JSFunction> empty_function) { |
733 Handle<Map> map = factory()->NewMap(JS_FUNCTION_TYPE, JSFunction::kSize); | 719 Handle<Map> map = factory()->NewMap(JS_FUNCTION_TYPE, JSFunction::kSize); |
734 SetStrictFunctionInstanceDescriptor(map, function_mode); | 720 SetStrictFunctionInstanceDescriptor(map, function_mode); |
735 map->set_is_constructor(IsFunctionModeWithPrototype(function_mode)); | 721 if (IsFunctionModeWithPrototype(function_mode)) map->set_is_constructor(); |
736 map->set_is_callable(); | 722 map->set_is_callable(); |
737 Map::SetPrototype(map, empty_function); | 723 Map::SetPrototype(map, empty_function); |
738 return map; | 724 return map; |
739 } | 725 } |
740 | 726 |
741 | 727 |
742 Handle<Map> Genesis::CreateStrongFunctionMap( | 728 Handle<Map> Genesis::CreateStrongFunctionMap( |
743 Handle<JSFunction> empty_function, bool is_constructor) { | 729 Handle<JSFunction> empty_function, bool is_constructor) { |
744 Handle<Map> map = factory()->NewMap(JS_FUNCTION_TYPE, JSFunction::kSize); | 730 Handle<Map> map = factory()->NewMap(JS_FUNCTION_TYPE, JSFunction::kSize); |
745 SetStrongFunctionInstanceDescriptor(map); | 731 SetStrongFunctionInstanceDescriptor(map); |
746 map->set_is_constructor(is_constructor); | 732 if (is_constructor) map->set_is_constructor(); |
747 Map::SetPrototype(map, empty_function); | 733 Map::SetPrototype(map, empty_function); |
748 map->set_is_callable(); | 734 map->set_is_callable(); |
749 map->set_is_extensible(is_constructor); | 735 map->set_is_extensible(is_constructor); |
750 map->set_is_strong(); | 736 map->set_is_strong(); |
751 return map; | 737 return map; |
752 } | 738 } |
753 | 739 |
754 | 740 |
755 void Genesis::CreateStrictModeFunctionMaps(Handle<JSFunction> empty) { | 741 void Genesis::CreateStrictModeFunctionMaps(Handle<JSFunction> empty) { |
756 // Allocate map for the prototype-less strict mode instances. | 742 // Allocate map for the prototype-less strict mode instances. |
757 Handle<Map> strict_function_without_prototype_map = | 743 Handle<Map> strict_function_without_prototype_map = |
758 CreateStrictFunctionMap(FUNCTION_WITHOUT_PROTOTYPE, empty); | 744 CreateStrictFunctionMap(FUNCTION_WITHOUT_PROTOTYPE, empty); |
759 native_context()->set_strict_function_without_prototype_map( | 745 native_context()->set_strict_function_without_prototype_map( |
760 *strict_function_without_prototype_map); | 746 *strict_function_without_prototype_map); |
761 | 747 |
762 // Allocate map for the strict mode functions. This map is temporary, used | 748 // Allocate map for the strict mode functions. This map is temporary, used |
763 // only for processing of builtins. | 749 // only for processing of builtins. |
764 // Later the map is replaced with writable prototype map, allocated below. | 750 // Later the map is replaced with writable prototype map, allocated below. |
765 Handle<Map> strict_function_map = | 751 Handle<Map> strict_function_map = |
766 CreateStrictFunctionMap(FUNCTION_WITH_READONLY_PROTOTYPE, empty); | 752 CreateStrictFunctionMap(FUNCTION_WITH_READONLY_PROTOTYPE, empty); |
767 native_context()->set_strict_function_map(*strict_function_map); | 753 native_context()->set_strict_function_map(*strict_function_map); |
768 | 754 |
769 // The final map for the strict mode functions. Writeable prototype. | 755 // The final map for the strict mode functions. Writeable prototype. |
770 // This map is installed in MakeFunctionInstancePrototypeWritable. | 756 // This map is installed in MakeFunctionInstancePrototypeWritable. |
771 strict_function_map_writable_prototype_ = | 757 strict_function_map_writable_prototype_ = |
772 CreateStrictFunctionMap(FUNCTION_WITH_WRITEABLE_PROTOTYPE, empty); | 758 CreateStrictFunctionMap(FUNCTION_WITH_WRITEABLE_PROTOTYPE, empty); |
773 | |
774 // Special map for non-constructor bound functions. | |
775 // TODO(bmeurer): Bound functions should not be represented as JSFunctions. | |
776 Handle<Map> bound_function_without_constructor_map = | |
777 CreateStrictFunctionMap(BOUND_FUNCTION, empty); | |
778 native_context()->set_bound_function_without_constructor_map( | |
779 *bound_function_without_constructor_map); | |
780 | |
781 // Special map for constructor bound functions. | |
782 // TODO(bmeurer): Bound functions should not be represented as JSFunctions. | |
783 Handle<Map> bound_function_with_constructor_map = | |
784 Map::Copy(bound_function_without_constructor_map, "IsConstructor"); | |
785 bound_function_with_constructor_map->set_is_constructor(true); | |
786 native_context()->set_bound_function_with_constructor_map( | |
787 *bound_function_with_constructor_map); | |
788 } | 759 } |
789 | 760 |
790 | 761 |
791 void Genesis::CreateStrongModeFunctionMaps(Handle<JSFunction> empty) { | 762 void Genesis::CreateStrongModeFunctionMaps(Handle<JSFunction> empty) { |
792 // Allocate map for strong mode instances, which never have prototypes. | 763 // Allocate map for strong mode instances, which never have prototypes. |
793 Handle<Map> strong_function_map = CreateStrongFunctionMap(empty, false); | 764 Handle<Map> strong_function_map = CreateStrongFunctionMap(empty, false); |
794 native_context()->set_strong_function_map(*strong_function_map); | 765 native_context()->set_strong_function_map(*strong_function_map); |
795 // Constructors do, though. | 766 // Constructors do, though. |
796 Handle<Map> strong_constructor_map = CreateStrongFunctionMap(empty, true); | 767 Handle<Map> strong_constructor_map = CreateStrongFunctionMap(empty, true); |
797 native_context()->set_strong_constructor_map(*strong_constructor_map); | 768 native_context()->set_strong_constructor_map(*strong_constructor_map); |
(...skipping 654 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1452 } | 1423 } |
1453 | 1424 |
1454 { // -- W e a k S e t | 1425 { // -- W e a k S e t |
1455 Handle<JSFunction> js_weak_set_fun = InstallFunction( | 1426 Handle<JSFunction> js_weak_set_fun = InstallFunction( |
1456 global, "WeakSet", JS_WEAK_SET_TYPE, JSWeakSet::kSize, | 1427 global, "WeakSet", JS_WEAK_SET_TYPE, JSWeakSet::kSize, |
1457 isolate->initial_object_prototype(), Builtins::kIllegal); | 1428 isolate->initial_object_prototype(), Builtins::kIllegal); |
1458 InstallWithIntrinsicDefaultProto(isolate, js_weak_set_fun, | 1429 InstallWithIntrinsicDefaultProto(isolate, js_weak_set_fun, |
1459 Context::JS_WEAK_SET_FUN_INDEX); | 1430 Context::JS_WEAK_SET_FUN_INDEX); |
1460 } | 1431 } |
1461 | 1432 |
| 1433 { // --- B o u n d F u n c t i o n |
| 1434 Handle<Map> map = |
| 1435 factory->NewMap(JS_BOUND_FUNCTION_TYPE, JSBoundFunction::kSize); |
| 1436 map->set_is_callable(); |
| 1437 Map::SetPrototype(map, empty_function); |
| 1438 |
| 1439 PropertyAttributes roc_attribs = |
| 1440 static_cast<PropertyAttributes>(DONT_ENUM | READ_ONLY); |
| 1441 Map::EnsureDescriptorSlack(map, 2); |
| 1442 |
| 1443 { // length |
| 1444 DataDescriptor d(factory->length_string(), JSBoundFunction::kLengthIndex, |
| 1445 roc_attribs, Representation::Tagged()); |
| 1446 map->AppendDescriptor(&d); |
| 1447 } |
| 1448 { // name |
| 1449 DataDescriptor d(factory->name_string(), JSBoundFunction::kNameIndex, |
| 1450 roc_attribs, Representation::Tagged()); |
| 1451 map->AppendDescriptor(&d); |
| 1452 } |
| 1453 |
| 1454 map->SetInObjectProperties(2); |
| 1455 native_context()->set_bound_function_without_constructor_map(*map); |
| 1456 |
| 1457 map = Map::Copy(map, "IsConstructor"); |
| 1458 map->set_is_constructor(); |
| 1459 native_context()->set_bound_function_with_constructor_map(*map); |
| 1460 } |
| 1461 |
1462 { // --- sloppy arguments map | 1462 { // --- sloppy arguments map |
1463 // Make sure we can recognize argument objects at runtime. | 1463 // Make sure we can recognize argument objects at runtime. |
1464 // This is done by introducing an anonymous function with | 1464 // This is done by introducing an anonymous function with |
1465 // class_name equals 'Arguments'. | 1465 // class_name equals 'Arguments'. |
1466 Handle<String> arguments_string = factory->Arguments_string(); | 1466 Handle<String> arguments_string = factory->Arguments_string(); |
1467 Handle<Code> code = isolate->builtins()->Illegal(); | 1467 Handle<Code> code = isolate->builtins()->Illegal(); |
1468 Handle<JSFunction> function = factory->NewFunctionWithoutPrototype( | 1468 Handle<JSFunction> function = factory->NewFunctionWithoutPrototype( |
1469 arguments_string, code); | 1469 arguments_string, code); |
1470 function->shared()->set_instance_class_name(*arguments_string); | 1470 function->shared()->set_instance_class_name(*arguments_string); |
1471 | 1471 |
(...skipping 806 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2278 } | 2278 } |
2279 | 2279 |
2280 | 2280 |
2281 void Genesis::InstallJSProxyMaps() { | 2281 void Genesis::InstallJSProxyMaps() { |
2282 // Allocate the different maps for all Proxy types. | 2282 // Allocate the different maps for all Proxy types. |
2283 // Next to the default proxy, we need maps indicating callable and | 2283 // Next to the default proxy, we need maps indicating callable and |
2284 // constructable proxies. | 2284 // constructable proxies. |
2285 | 2285 |
2286 Handle<Map> proxy_function_map = | 2286 Handle<Map> proxy_function_map = |
2287 Map::Copy(isolate()->sloppy_function_without_prototype_map(), "Proxy"); | 2287 Map::Copy(isolate()->sloppy_function_without_prototype_map(), "Proxy"); |
2288 proxy_function_map->set_is_constructor(true); | 2288 proxy_function_map->set_is_constructor(); |
2289 native_context()->set_proxy_function_map(*proxy_function_map); | 2289 native_context()->set_proxy_function_map(*proxy_function_map); |
2290 | 2290 |
2291 Handle<Map> proxy_map = | 2291 Handle<Map> proxy_map = |
2292 factory()->NewMap(JS_PROXY_TYPE, JSProxy::kSize, FAST_ELEMENTS); | 2292 factory()->NewMap(JS_PROXY_TYPE, JSProxy::kSize, FAST_ELEMENTS); |
2293 native_context()->set_proxy_map(*proxy_map); | 2293 native_context()->set_proxy_map(*proxy_map); |
2294 | 2294 |
2295 Handle<Map> proxy_callable_map = Map::Copy(proxy_map, "callable Proxy"); | 2295 Handle<Map> proxy_callable_map = Map::Copy(proxy_map, "callable Proxy"); |
2296 proxy_callable_map->set_is_callable(); | 2296 proxy_callable_map->set_is_callable(); |
2297 native_context()->set_proxy_callable_map(*proxy_callable_map); | 2297 native_context()->set_proxy_callable_map(*proxy_callable_map); |
2298 proxy_callable_map->SetConstructor(native_context()->function_function()); | 2298 proxy_callable_map->SetConstructor(native_context()->function_function()); |
2299 | 2299 |
2300 Handle<Map> proxy_constructor_map = | 2300 Handle<Map> proxy_constructor_map = |
2301 Map::Copy(proxy_callable_map, "constructor Proxy"); | 2301 Map::Copy(proxy_callable_map, "constructor Proxy"); |
2302 proxy_constructor_map->set_is_constructor(true); | 2302 proxy_constructor_map->set_is_constructor(); |
2303 native_context()->set_proxy_constructor_map(*proxy_constructor_map); | 2303 native_context()->set_proxy_constructor_map(*proxy_constructor_map); |
2304 } | 2304 } |
2305 | 2305 |
2306 | 2306 |
2307 void Genesis::InitializeGlobal_harmony_proxies() { | 2307 void Genesis::InitializeGlobal_harmony_proxies() { |
2308 if (!FLAG_harmony_proxies) return; | 2308 if (!FLAG_harmony_proxies) return; |
2309 Handle<JSGlobalObject> global( | 2309 Handle<JSGlobalObject> global( |
2310 JSGlobalObject::cast(native_context()->global_object())); | 2310 JSGlobalObject::cast(native_context()->global_object())); |
2311 Isolate* isolate = global->GetIsolate(); | 2311 Isolate* isolate = global->GetIsolate(); |
2312 Factory* factory = isolate->factory(); | 2312 Factory* factory = isolate->factory(); |
(...skipping 205 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2518 MaybeHandle<JSObject>(), Builtins::kArrayConcat); | 2518 MaybeHandle<JSObject>(), Builtins::kArrayConcat); |
2519 | 2519 |
2520 // Make sure that InternalArray.prototype.concat appears to be compiled. | 2520 // Make sure that InternalArray.prototype.concat appears to be compiled. |
2521 // The code will never be called, but inline caching for call will | 2521 // The code will never be called, but inline caching for call will |
2522 // only work if it appears to be compiled. | 2522 // only work if it appears to be compiled. |
2523 concat->shared()->DontAdaptArguments(); | 2523 concat->shared()->DontAdaptArguments(); |
2524 DCHECK(concat->is_compiled()); | 2524 DCHECK(concat->is_compiled()); |
2525 // Set the lengths for the functions to satisfy ECMA-262. | 2525 // Set the lengths for the functions to satisfy ECMA-262. |
2526 concat->shared()->set_length(1); | 2526 concat->shared()->set_length(1); |
2527 } | 2527 } |
2528 // Install Function.prototype.apply, call, and toString. | 2528 |
| 2529 // Install Function.prototype.apply, bind, call, and toString. |
2529 { | 2530 { |
2530 Handle<String> key = factory()->Function_string(); | 2531 Handle<String> key = factory()->Function_string(); |
2531 Handle<JSFunction> function = | 2532 Handle<JSFunction> function = |
2532 Handle<JSFunction>::cast(Object::GetProperty( | 2533 Handle<JSFunction>::cast(Object::GetProperty( |
2533 handle(native_context()->global_object()), key).ToHandleChecked()); | 2534 handle(native_context()->global_object()), key).ToHandleChecked()); |
2534 Handle<JSObject> proto = | 2535 Handle<JSObject> proto = |
2535 Handle<JSObject>(JSObject::cast(function->instance_prototype())); | 2536 Handle<JSObject>(JSObject::cast(function->instance_prototype())); |
2536 | 2537 |
2537 // Install the apply, call and toString functions. | 2538 // Install the apply, bind, call and toString functions. |
2538 SimpleInstallFunction(proto, factory()->apply_string(), | 2539 SimpleInstallFunction(proto, factory()->apply_string(), |
2539 Builtins::kFunctionPrototypeApply, 2, false); | 2540 Builtins::kFunctionPrototypeApply, 2, false); |
| 2541 SimpleInstallFunction(proto, factory()->bind_string(), |
| 2542 Builtins::kFunctionPrototypeBind, 1, false); |
2540 SimpleInstallFunction(proto, factory()->call_string(), | 2543 SimpleInstallFunction(proto, factory()->call_string(), |
2541 Builtins::kFunctionPrototypeCall, 1, false); | 2544 Builtins::kFunctionPrototypeCall, 1, false); |
2542 SimpleInstallFunction(proto, factory()->toString_string(), | 2545 SimpleInstallFunction(proto, factory()->toString_string(), |
2543 Builtins::kFunctionPrototypeToString, 0, false); | 2546 Builtins::kFunctionPrototypeToString, 0, false); |
2544 } | 2547 } |
2545 | 2548 |
2546 // Set up the Promise constructor. | 2549 // Set up the Promise constructor. |
2547 { | 2550 { |
2548 Handle<String> key = factory()->Promise_string(); | 2551 Handle<String> key = factory()->Promise_string(); |
2549 Handle<JSFunction> function = Handle<JSFunction>::cast( | 2552 Handle<JSFunction> function = Handle<JSFunction>::cast( |
(...skipping 803 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3353 } | 3356 } |
3354 | 3357 |
3355 | 3358 |
3356 // Called when the top-level V8 mutex is destroyed. | 3359 // Called when the top-level V8 mutex is destroyed. |
3357 void Bootstrapper::FreeThreadResources() { | 3360 void Bootstrapper::FreeThreadResources() { |
3358 DCHECK(!IsActive()); | 3361 DCHECK(!IsActive()); |
3359 } | 3362 } |
3360 | 3363 |
3361 } // namespace internal | 3364 } // namespace internal |
3362 } // namespace v8 | 3365 } // namespace v8 |
OLD | NEW |