Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(240)

Unified Diff: src/runtime.cc

Issue 14066016: Generators can resume (Closed) Base URL: git://github.com/v8/v8.git@master
Patch Set: Use Abort() instead of int3() Created 7 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/runtime.h ('k') | src/x64/full-codegen-x64.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/runtime.cc
diff --git a/src/runtime.cc b/src/runtime.cc
index 1df5653acfc5a772fc96ce4cde3bceac9ddaea12..63f1edb2602ab344be90b0f88e8a460b4a95d022 100644
--- a/src/runtime.cc
+++ b/src/runtime.cc
@@ -2475,6 +2475,65 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_SuspendJSGeneratorObject) {
}
+// Note that this function is the slow path for resuming generators. It is only
+// 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.
+RUNTIME_FUNCTION(MaybeObject*, Runtime_ResumeJSGeneratorObject) {
+ HandleScope scope(isolate);
+ ASSERT(args.length() == 3);
+ CONVERT_ARG_HANDLE_CHECKED(JSGeneratorObject, generator_object, 0);
+ CONVERT_ARG_HANDLE_CHECKED(Object, value, 1);
+ CONVERT_SMI_ARG_CHECKED(resume_mode_int, 2);
+ JavaScriptFrameIterator stack_iterator(isolate);
+ JavaScriptFrame *frame = stack_iterator.frame();
+
+ ASSERT_EQ(frame->function(), generator_object->function());
+
+ STATIC_ASSERT(JSGeneratorObject::kGeneratorExecuting <= 0);
+ STATIC_ASSERT(JSGeneratorObject::kGeneratorClosed <= 0);
+
+ Address pc = generator_object->function()->code()->instruction_start();
+ int offset = generator_object->continuation();
+ ASSERT(offset > 0);
+ frame->set_pc(pc + offset);
+ generator_object->set_continuation(JSGeneratorObject::kGeneratorExecuting);
+
+ if (generator_object->operand_stack()->length() != 0) {
+ // TODO(wingo): Copy operand stack. Rewind handlers.
+ UNIMPLEMENTED();
+ }
+
+ JSGeneratorObject::ResumeMode resume_mode =
+ static_cast<JSGeneratorObject::ResumeMode>(resume_mode_int);
+ switch (resume_mode) {
+ case JSGeneratorObject::SEND:
+ return *value;
+ case JSGeneratorObject::THROW:
+ return isolate->Throw(*value);
+ }
+
+ UNREACHABLE();
+ return isolate->ThrowIllegalOperation();
+}
+
+
+RUNTIME_FUNCTION(MaybeObject*, Runtime_ThrowGeneratorStateError) {
+ HandleScope scope(isolate);
+ ASSERT(args.length() == 1);
+ CONVERT_ARG_HANDLE_CHECKED(JSGeneratorObject, generator, 0);
+ int continuation = generator->continuation();
+ const char *message = continuation == JSGeneratorObject::kGeneratorClosed ?
+ "generator_finished" : "generator_running";
+ Vector< Handle<Object> > argv = HandleVector<Object>(NULL, 0);
+ Handle<Object> error = isolate->factory()->NewError(message, argv);
+ return isolate->Throw(*error);
+}
+
+
MUST_USE_RESULT static MaybeObject* CharFromCode(Isolate* isolate,
Object* char_code) {
if (char_code->IsNumber()) {
« no previous file with comments | « src/runtime.h ('k') | src/x64/full-codegen-x64.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698