Revision: 15028
Author:   [email protected]
Date:     Mon Jun 10 02:26:18 2013
Log:      Generator object "next" method takes optional send value

Update the generators implementation to make "next" also do the job of
what was previously called "send" by taking an optional argument.
Remove send, and do a bunch of renamings.

[email protected]
BUG=v8:2355, v8:2715

Review URL: https://codereview.chromium.org/16136011
http://code.google.com/p/v8/source/detail?r=15028

Modified:
 /branches/bleeding_edge/src/arm/full-codegen-arm.cc
 /branches/bleeding_edge/src/full-codegen.cc
 /branches/bleeding_edge/src/generator.js
 /branches/bleeding_edge/src/heap.h
 /branches/bleeding_edge/src/hydrogen.cc
 /branches/bleeding_edge/src/ia32/full-codegen-ia32.cc
 /branches/bleeding_edge/src/objects.h
 /branches/bleeding_edge/src/runtime.cc
 /branches/bleeding_edge/src/runtime.h
 /branches/bleeding_edge/src/x64/full-codegen-x64.cc
 /branches/bleeding_edge/test/mjsunit/harmony/generators-iteration.js
 /branches/bleeding_edge/test/mjsunit/harmony/generators-objects.js
 /branches/bleeding_edge/test/mjsunit/harmony/generators-runtime.js

=======================================
--- /branches/bleeding_edge/src/arm/full-codegen-arm.cc Mon Jun 10 02:12:57 2013 +++ /branches/bleeding_edge/src/arm/full-codegen-arm.cc Mon Jun 10 02:26:18 2013
@@ -2029,10 +2029,10 @@
       // [sp + 1 * kPointerSize] iter
       // [sp + 0 * kPointerSize] g

-      Label l_catch, l_try, l_resume, l_send, l_call, l_loop;
+      Label l_catch, l_try, l_resume, l_next, l_call, l_loop;
       // Initial send value is undefined.
       __ LoadRoot(r0, Heap::kUndefinedValueRootIndex);
-      __ b(&l_send);
+      __ b(&l_next);

// catch (e) { receiver = iter; f = iter.throw; arg = e; goto l_call; }
       __ bind(&l_catch);
@@ -2063,15 +2063,15 @@
       __ bind(&l_resume);                                // received in r0
       __ PopTryHandler();

-      // receiver = iter; f = iter.send; arg = received;
-      __ bind(&l_send);
+      // receiver = iter; f = iter.next; arg = received;
+      __ bind(&l_next);
       __ ldr(r3, MemOperand(sp, 1 * kPointerSize));      // iter
       __ push(r3);                                       // iter
       __ push(r0);                                       // received
       __ mov(r0, r3);                                    // iter
-      __ LoadRoot(r2, Heap::ksend_stringRootIndex);      // "send"
-      Handle<Code> send_ic = isolate()->builtins()->LoadIC_Initialize();
-      CallIC(send_ic);                                   // iter.send in r0
+      __ LoadRoot(r2, Heap::knext_stringRootIndex);      // "next"
+      Handle<Code> next_ic = isolate()->builtins()->LoadIC_Initialize();
+      CallIC(next_ic);                                   // iter.next in r0

       // result = f.call(receiver, arg);
       __ bind(&l_call);
@@ -2174,7 +2174,7 @@

// If we are sending a value and there is no operand stack, we can jump back
   // in directly.
-  if (resume_mode == JSGeneratorObject::SEND) {
+  if (resume_mode == JSGeneratorObject::NEXT) {
     Label slow_resume;
     __ cmp(r3, Operand(0));
     __ b(ne, &slow_resume);
=======================================
--- /branches/bleeding_edge/src/full-codegen.cc Fri Jun  7 04:12:21 2013
+++ /branches/bleeding_edge/src/full-codegen.cc Mon Jun 10 02:26:18 2013
@@ -926,10 +926,10 @@
 }


-void FullCodeGenerator::EmitGeneratorSend(CallRuntime* expr) {
+void FullCodeGenerator::EmitGeneratorNext(CallRuntime* expr) {
   ZoneList<Expression*>* args = expr->arguments();
   ASSERT(args->length() == 2);
-  EmitGeneratorResume(args->at(0), args->at(1), JSGeneratorObject::SEND);
+  EmitGeneratorResume(args->at(0), args->at(1), JSGeneratorObject::NEXT);
 }


=======================================
--- /branches/bleeding_edge/src/generator.js    Wed May 15 08:57:58 2013
+++ /branches/bleeding_edge/src/generator.js    Mon Jun 10 02:26:18 2013
@@ -34,26 +34,16 @@
// ----------------------------------------------------------------------------


-// TODO(wingo): Give link to specification. For now, the following diagram is
-// the spec:
-// http://wiki.ecmascript.org/lib/exe/fetch.php?cache=cache&media=harmony:es6_generator_object_model_3-29-13.png +// Generator functions and objects are specified by ES6, sections 15.19.3 and
+// 15.19.4.

-function GeneratorObjectNext() {
+function GeneratorObjectNext(value) {
   if (!IS_GENERATOR(this)) {
     throw MakeTypeError('incompatible_method_receiver',
                         ['[Generator].prototype.next', this]);
   }

-  return %_GeneratorSend(this, void 0);
-}
-
-function GeneratorObjectSend(value) {
-  if (!IS_GENERATOR(this)) {
-    throw MakeTypeError('incompatible_method_receiver',
-                        ['[Generator].prototype.send', this]);
-  }
-
-  return %_GeneratorSend(this, value);
+  return %_GeneratorNext(this, value);
 }

 function GeneratorObjectThrow(exn) {
@@ -71,7 +61,6 @@
   InstallFunctions(GeneratorObjectPrototype,
                    DONT_ENUM | DONT_DELETE | READ_ONLY,
                    ["next", GeneratorObjectNext,
-                    "send", GeneratorObjectSend,
                     "throw", GeneratorObjectThrow]);
   %SetProperty(GeneratorObjectPrototype, "constructor",
GeneratorFunctionPrototype, DONT_ENUM | DONT_DELETE | READ_ONLY);
=======================================
--- /branches/bleeding_edge/src/heap.h  Fri Jun  7 04:12:21 2013
+++ /branches/bleeding_edge/src/heap.h  Mon Jun 10 02:26:18 2013
@@ -293,7 +293,6 @@
   V(hidden_stack_trace_string, "v8::hidden_stack_trace")                 \
   V(query_colon_string, "(?:)")                                          \
   V(Generator_string, "Generator")                                       \
-  V(send_string, "send")                                                 \
   V(throw_string, "throw")                                               \
   V(done_string, "done")                                                 \
   V(value_string, "value")                                               \
=======================================
--- /branches/bleeding_edge/src/hydrogen.cc     Fri Jun  7 10:28:46 2013
+++ /branches/bleeding_edge/src/hydrogen.cc     Mon Jun 10 02:26:18 2013
@@ -10917,8 +10917,8 @@


 // Support for generators.
-void HOptimizedGraphBuilder::GenerateGeneratorSend(CallRuntime* call) {
-  return Bailout("inlined runtime function: GeneratorSend");
+void HOptimizedGraphBuilder::GenerateGeneratorNext(CallRuntime* call) {
+  return Bailout("inlined runtime function: GeneratorNext");
 }


=======================================
--- /branches/bleeding_edge/src/ia32/full-codegen-ia32.cc Fri Jun 7 04:12:21 2013 +++ /branches/bleeding_edge/src/ia32/full-codegen-ia32.cc Mon Jun 10 02:26:18 2013
@@ -1988,10 +1988,10 @@
       // [sp + 1 * kPointerSize] iter
       // [sp + 0 * kPointerSize] g

-      Label l_catch, l_try, l_resume, l_send, l_call, l_loop;
+      Label l_catch, l_try, l_resume, l_next, l_call, l_loop;
       // Initial send value is undefined.
       __ mov(eax, isolate()->factory()->undefined_value());
-      __ jmp(&l_send);
+      __ jmp(&l_next);

// catch (e) { receiver = iter; f = iter.throw; arg = e; goto l_call; }
       __ bind(&l_catch);
@@ -2020,14 +2020,14 @@
       __ bind(&l_resume);                                // received in eax
       __ PopTryHandler();

-      // receiver = iter; f = iter.send; arg = received;
-      __ bind(&l_send);
+      // receiver = iter; f = iter.next; arg = received;
+      __ bind(&l_next);
       __ mov(edx, Operand(esp, 1 * kPointerSize));       // iter
       __ push(edx);                                      // iter
       __ push(eax);                                      // received
-      __ mov(ecx, isolate()->factory()->send_string());  // "send"
-      Handle<Code> send_ic = isolate()->builtins()->LoadIC_Initialize();
- CallIC(send_ic); // iter.send in eax
+      __ mov(ecx, isolate()->factory()->next_string());  // "next"
+      Handle<Code> next_ic = isolate()->builtins()->LoadIC_Initialize();
+ CallIC(next_ic); // iter.next in eax

       // result = f.call(receiver, arg);
       __ bind(&l_call);
@@ -2129,7 +2129,7 @@

// If we are sending a value and there is no operand stack, we can jump back
   // in directly.
-  if (resume_mode == JSGeneratorObject::SEND) {
+  if (resume_mode == JSGeneratorObject::NEXT) {
     Label slow_resume;
     __ cmp(edx, Immediate(0));
     __ j(not_zero, &slow_resume);
=======================================
--- /branches/bleeding_edge/src/objects.h       Fri Jun  7 08:02:20 2013
+++ /branches/bleeding_edge/src/objects.h       Mon Jun 10 02:26:18 2013
@@ -6529,7 +6529,7 @@
   static const int kSize = kStackHandlerIndexOffset + kPointerSize;

   // Resume mode, for use by runtime functions.
-  enum ResumeMode { SEND, THROW };
+  enum ResumeMode { NEXT, THROW };

// Yielding from a generator returns an object with the following inobject
   // properties.  See Context::generator_result_map() for the map.
=======================================
--- /branches/bleeding_edge/src/runtime.cc      Fri Jun  7 09:48:22 2013
+++ /branches/bleeding_edge/src/runtime.cc      Mon Jun 10 02:26:18 2013
@@ -2641,9 +2641,9 @@
// called if the suspended activation had operands on the stack, stack handlers // needing rewinding, or if the resume should throw an exception. The fast path // is handled directly in FullCodeGenerator::EmitGeneratorResume(), which is
-// inlined into GeneratorNext, GeneratorSend, and GeneratorThrow.
-// EmitGeneratorResumeResume is called in any case, as it needs to reconstruct
-// the stack frame and make space for arguments and operands.
+// inlined into GeneratorNext and GeneratorThrow. EmitGeneratorResumeResume is +// called in any case, as it needs to reconstruct the stack frame and make space
+// for arguments and operands.
 RUNTIME_FUNCTION(MaybeObject*, Runtime_ResumeJSGeneratorObject) {
   SealHandleScope shs(isolate);
   ASSERT(args.length() == 3);
@@ -2676,7 +2676,7 @@
   JSGeneratorObject::ResumeMode resume_mode =
       static_cast<JSGeneratorObject::ResumeMode>(resume_mode_int);
   switch (resume_mode) {
-    case JSGeneratorObject::SEND:
+    case JSGeneratorObject::NEXT:
       return value;
     case JSGeneratorObject::THROW:
       return isolate->Throw(value);
=======================================
--- /branches/bleeding_edge/src/runtime.h       Fri Jun  7 06:27:03 2013
+++ /branches/bleeding_edge/src/runtime.h       Mon Jun 10 02:26:18 2013
@@ -572,7 +572,7 @@
F(HasCachedArrayIndex, 1, 1) \ F(GetCachedArrayIndex, 1, 1) \ F(FastAsciiArrayJoin, 2, 1) \ - F(GeneratorSend, 2, 1) \ + F(GeneratorNext, 2, 1) \
   F(GeneratorThrow, 2, 1)


=======================================
--- /branches/bleeding_edge/src/x64/full-codegen-x64.cc Fri Jun 7 04:12:21 2013 +++ /branches/bleeding_edge/src/x64/full-codegen-x64.cc Mon Jun 10 02:26:18 2013
@@ -2012,10 +2012,10 @@
       // [sp + 1 * kPointerSize] iter
       // [sp + 0 * kPointerSize] g

-      Label l_catch, l_try, l_resume, l_send, l_call, l_loop;
+      Label l_catch, l_try, l_resume, l_next, l_call, l_loop;
       // Initial send value is undefined.
       __ LoadRoot(rax, Heap::kUndefinedValueRootIndex);
-      __ jmp(&l_send);
+      __ jmp(&l_next);

// catch (e) { receiver = iter; f = iter.throw; arg = e; goto l_call; }
       __ bind(&l_catch);
@@ -2045,15 +2045,15 @@
       __ bind(&l_resume);                                // received in rax
       __ PopTryHandler();

-      // receiver = iter; f = iter.send; arg = received;
-      __ bind(&l_send);
+      // receiver = iter; f = iter.next; arg = received;
+      __ bind(&l_next);
       __ movq(rcx, Operand(rsp, 1 * kPointerSize));      // iter
       __ push(rcx);                                      // iter
       __ push(rax);                                      // received
       __ movq(rax, rcx);                                 // iter
-      __ LoadRoot(rcx, Heap::ksend_stringRootIndex);     // "send"
-      Handle<Code> send_ic = isolate()->builtins()->LoadIC_Initialize();
- CallIC(send_ic); // iter.send in rax
+      __ LoadRoot(rcx, Heap::knext_stringRootIndex);     // "next"
+      Handle<Code> next_ic = isolate()->builtins()->LoadIC_Initialize();
+ CallIC(next_ic); // iter.next in rax

       // result = f.call(receiver, arg);
       __ bind(&l_call);
@@ -2155,7 +2155,7 @@

// If we are sending a value and there is no operand stack, we can jump back
   // in directly.
-  if (resume_mode == JSGeneratorObject::SEND) {
+  if (resume_mode == JSGeneratorObject::NEXT) {
     Label slow_resume;
     __ cmpq(rdx, Immediate(0));
     __ j(not_zero, &slow_resume);
=======================================
--- /branches/bleeding_edge/test/mjsunit/harmony/generators-iteration.js Wed May 15 08:57:58 2013 +++ /branches/bleeding_edge/test/mjsunit/harmony/generators-iteration.js Mon Jun 10 02:26:18 2013
@@ -64,9 +64,9 @@
     for (var i = 0; i < expected_values_for_send.length; i++) {
       assertIteratorResult(expected_values_for_send[i],
                            i == expected_values_for_send.length - 1,
-                           iter.send(send_val));
+                           iter.next(send_val));
     }
-    assertThrows(function() { iter.send(send_val); }, Error);
+    assertThrows(function() { iter.next(send_val); }, Error);
   }
   function testThrow(thunk) {
     for (var i = 0; i < expected_values_for_next.length; i++) {
@@ -572,7 +572,7 @@
     return iter.next();
   }
   function TestSendRecursion() {
-    function* g() { yield iter.send(42); }
+    function* g() { yield iter.next(42); }
     var iter = g();
     return iter.next();
   }
=======================================
--- /branches/bleeding_edge/test/mjsunit/harmony/generators-objects.js Wed Apr 17 08:01:25 2013 +++ /branches/bleeding_edge/test/mjsunit/harmony/generators-objects.js Mon Jun 10 02:26:18 2013
@@ -79,7 +79,7 @@

   function TestNonGenerator(non_generator) {
     assertThrows(function() { iter.next.call(non_generator); }, TypeError);
- assertThrows(function() { iter.send.call(non_generator, 1); }, TypeError); + assertThrows(function() { iter.next.call(non_generator, 1); }, TypeError); assertThrows(function() { iter.throw.call(non_generator, 1); }, TypeError); assertThrows(function() { iter.close.call(non_generator); }, TypeError);
   }
=======================================
--- /branches/bleeding_edge/test/mjsunit/harmony/generators-runtime.js Wed May 15 08:57:58 2013 +++ /branches/bleeding_edge/test/mjsunit/harmony/generators-runtime.js Mon Jun 10 02:26:18 2013
@@ -84,7 +84,7 @@
   assertSame(GeneratorObjectPrototype,
              Object.getPrototypeOf((function*(){yield 1}).prototype));

-  var expected_property_names = ["next", "send", "throw", "constructor"];
+  var expected_property_names = ["next", "throw", "constructor"];
   var found_property_names =
       Object.getOwnPropertyNames(GeneratorObjectPrototype);

--
--
v8-dev mailing list
[email protected]
http://groups.google.com/group/v8-dev
--- You received this message because you are subscribed to the Google Groups "v8-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to [email protected].
For more options, visit https://groups.google.com/groups/opt_out.


Reply via email to