Commit 3560d9bd authored by neis's avatar neis Committed by Commit bot

[runtime] Fix effect of setting .prototype on generator functions.

When setting a generator function's  "prototype" property to a non-object, the
prototype of new generator instances should be %GeneratorPrototype%, not
%ObjectPrototype%.

R=verwaest@chromium.org
BUG=v8:5011

Review-Url: https://codereview.chromium.org/1982203003
Cr-Commit-Position: refs/heads/master@{#36313}
parent 75140f39
......@@ -749,6 +749,8 @@ void Genesis::CreateIteratorMaps(Handle<JSFunction> empty) {
factory()->NewJSObject(isolate()->object_function(), TENURED);
Handle<JSObject> generator_object_prototype =
factory()->NewJSObject(isolate()->object_function(), TENURED);
native_context()->set_initial_generator_prototype(
*generator_object_prototype);
SetObjectPrototype(generator_object_prototype, iterator_prototype);
Handle<JSObject> generator_function_prototype =
factory()->NewJSObject(isolate()->object_function(), TENURED);
......
......@@ -181,6 +181,7 @@ enum BindingFlags {
generator_function_function) \
V(GENERATOR_OBJECT_PROTOTYPE_MAP_INDEX, Map, generator_object_prototype_map) \
V(INITIAL_ARRAY_PROTOTYPE_INDEX, JSObject, initial_array_prototype) \
V(INITIAL_GENERATOR_PROTOTYPE_INDEX, JSObject, initial_generator_prototype) \
V(INITIAL_OBJECT_PROTOTYPE_INDEX, JSObject, initial_object_prototype) \
V(INT16_ARRAY_FUN_INDEX, JSFunction, int16_array_fun) \
V(INT16X8_FUNCTION_INDEX, JSFunction, int16x8_function) \
......
......@@ -11907,8 +11907,13 @@ void JSFunction::SetPrototype(Handle<JSFunction> function,
new_map->SetConstructor(*value);
new_map->set_non_instance_prototype(true);
Isolate* isolate = new_map->GetIsolate();
construct_prototype = handle(
function->context()->native_context()->initial_object_prototype(),
IsGeneratorFunction(function->shared()->kind())
? function->context()
->native_context()
->initial_generator_prototype()
: function->context()->native_context()->initial_object_prototype(),
isolate);
} else {
function->map()->set_non_instance_prototype(false);
......
......@@ -83,7 +83,7 @@ bytecodes: [
B(Star), R(0),
B(CreateArrayLiteral), U8(0), U8(0), U8(3),
B(Star), R(1),
B(CallJSRuntime), U8(121), R(0), U8(2),
B(CallJSRuntime), U8(122), R(0), U8(2),
/* 44 S> */ B(Return),
]
constant pool: [
......
......@@ -87,3 +87,29 @@ function TestGeneratorObjectMethods() {
TestNonGenerator(g.prototype);
}
TestGeneratorObjectMethods();
function TestPrototype() {
function* g() { }
let g_prototype = g.prototype;
assertEquals([], Reflect.ownKeys(g_prototype));
let generator_prototype = Object.getPrototypeOf(g_prototype);
assertSame(generator_prototype, Object.getPrototypeOf(g).prototype);
// Unchanged .prototype
assertSame(g_prototype, Object.getPrototypeOf(g()));
// Custom object as .prototype
{
let proto = {};
g.prototype = proto;
assertSame(proto, Object.getPrototypeOf(g()));
}
// Custom non-object as .prototype
g.prototype = null;
assertSame(generator_prototype, Object.getPrototypeOf(g()));
}
TestPrototype();
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment