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

Side by Side Diff: Source/bindings/v8/custom/V8PromiseCustom.cpp

Issue 131823003: DevTools: Implement async call stacks for Promises. (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Created 6 years, 11 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 unified diff | Download patch | Annotate | Revision Log
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2013 Google Inc. All rights reserved. 2 * Copyright (C) 2013 Google Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions are 5 * modification, are permitted provided that the following conditions are
6 * met: 6 * met:
7 * 7 *
8 * * Redistributions of source code must retain the above copyright 8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer. 9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above 10 * * Redistributions in binary form must reproduce the above
(...skipping 27 matching lines...) Expand all
38 #include "bindings/v8/ScriptFunctionCall.h" 38 #include "bindings/v8/ScriptFunctionCall.h"
39 #include "bindings/v8/ScriptState.h" 39 #include "bindings/v8/ScriptState.h"
40 #include "bindings/v8/V8Binding.h" 40 #include "bindings/v8/V8Binding.h"
41 #include "bindings/v8/V8HiddenPropertyName.h" 41 #include "bindings/v8/V8HiddenPropertyName.h"
42 #include "bindings/v8/V8PerIsolateData.h" 42 #include "bindings/v8/V8PerIsolateData.h"
43 #include "bindings/v8/V8ScriptRunner.h" 43 #include "bindings/v8/V8ScriptRunner.h"
44 #include "bindings/v8/WrapperTypeInfo.h" 44 #include "bindings/v8/WrapperTypeInfo.h"
45 #include "core/dom/Document.h" 45 #include "core/dom/Document.h"
46 #include "core/dom/ExecutionContextTask.h" 46 #include "core/dom/ExecutionContextTask.h"
47 #include "core/frame/DOMWindow.h" 47 #include "core/frame/DOMWindow.h"
48 #include "core/inspector/InspectorInstrumentation.h"
48 #include "core/workers/WorkerGlobalScope.h" 49 #include "core/workers/WorkerGlobalScope.h"
49 #include "platform/Task.h" 50 #include "platform/Task.h"
50 #include "wtf/Deque.h" 51 #include "wtf/Deque.h"
51 #include "wtf/Functional.h" 52 #include "wtf/Functional.h"
52 #include "wtf/Noncopyable.h" 53 #include "wtf/Noncopyable.h"
53 #include "wtf/PassOwnPtr.h" 54 #include "wtf/PassOwnPtr.h"
54 55
55 namespace WebCore { 56 namespace WebCore {
56 57
57 namespace { 58 namespace {
(...skipping 125 matching lines...) Expand 10 before | Expand all | Expand 10 after
183 } 184 }
184 185
185 ASSERT(!derivedPromise.IsEmpty()); 186 ASSERT(!derivedPromise.IsEmpty());
186 derivedPromises->Set(derivedPromises->Length(), derivedPromise); 187 derivedPromises->Set(derivedPromises->Length(), derivedPromise);
187 188
188 // Since they are treated as a tuple, 189 // Since they are treated as a tuple,
189 // we need to guaranteed that the length of these arrays are same. 190 // we need to guaranteed that the length of these arrays are same.
190 ASSERT(fulfillCallbacks->Length() == rejectCallbacks->Length() && rejectCall backs->Length() == derivedPromises->Length()); 191 ASSERT(fulfillCallbacks->Length() == rejectCallbacks->Length() && rejectCall backs->Length() == derivedPromises->Length());
191 } 192 }
192 193
194 class TaskPerformScopeForInstrumentation {
195 public:
196 TaskPerformScopeForInstrumentation(ExecutionContext* context, ExecutionConte xtTask* task)
197 : m_cookie(InspectorInstrumentation::willPerformPromiseTask(context, tas k))
198 {
199 }
200
201 ~TaskPerformScopeForInstrumentation()
202 {
203 InspectorInstrumentation::didPerformPromiseTask(m_cookie);
204 }
205
206 private:
207 InspectorInstrumentationCookie m_cookie;
208 };
209
193 class CallHandlerTask FINAL : public ExecutionContextTask { 210 class CallHandlerTask FINAL : public ExecutionContextTask {
194 public: 211 public:
195 CallHandlerTask(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> han dler, v8::Handle<v8::Value> argument, v8::Isolate* isolate, ExecutionContext* co ntext) 212 CallHandlerTask(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> han dler, v8::Handle<v8::Value> argument, V8PromiseCustom::PromiseState originatorSt ate, v8::Isolate* isolate, ExecutionContext* context)
196 : m_promise(isolate, promise) 213 : m_promise(isolate, promise)
197 , m_handler(isolate, handler) 214 , m_handler(isolate, handler)
198 , m_argument(isolate, argument) 215 , m_argument(isolate, argument)
199 , m_requestState(context) 216 , m_requestState(context)
200 { 217 {
201 ASSERT(!m_promise.isEmpty()); 218 ASSERT(!m_promise.isEmpty());
202 ASSERT(!m_handler.isEmpty()); 219 ASSERT(!m_handler.isEmpty());
203 ASSERT(!m_argument.isEmpty()); 220 ASSERT(!m_argument.isEmpty());
221 InspectorInstrumentation::didPostPromiseTask(context, this, originatorSt ate == V8PromiseCustom::Fulfilled);
204 } 222 }
205 virtual ~CallHandlerTask() { } 223 virtual ~CallHandlerTask() { }
206 224
207 virtual void performTask(ExecutionContext*) OVERRIDE; 225 virtual void performTask(ExecutionContext*) OVERRIDE;
208 226
209 private: 227 private:
210 ScopedPersistent<v8::Object> m_promise; 228 ScopedPersistent<v8::Object> m_promise;
211 ScopedPersistent<v8::Function> m_handler; 229 ScopedPersistent<v8::Function> m_handler;
212 ScopedPersistent<v8::Value> m_argument; 230 ScopedPersistent<v8::Value> m_argument;
213 DOMRequestState m_requestState; 231 DOMRequestState m_requestState;
214 }; 232 };
215 233
216 void CallHandlerTask::performTask(ExecutionContext* context) 234 void CallHandlerTask::performTask(ExecutionContext* context)
217 { 235 {
236 TaskPerformScopeForInstrumentation performTaskScope(context, this);
yhirano 2014/01/15 13:28:55 Can you place this statement after L240? It is goo
aandrey 2014/01/15 14:49:53 Will be memory leak, as we need to clean up our in
237
218 ASSERT(context); 238 ASSERT(context);
219 if (context->activeDOMObjectsAreStopped()) 239 if (context->activeDOMObjectsAreStopped())
220 return; 240 return;
221 241
222 DOMRequestState::Scope scope(m_requestState); 242 DOMRequestState::Scope scope(m_requestState);
223 v8::Isolate* isolate = m_requestState.isolate(); 243 v8::Isolate* isolate = m_requestState.isolate();
224 v8::Handle<v8::Value> info[] = { m_argument.newLocal(isolate) }; 244 v8::Handle<v8::Value> info[] = { m_argument.newLocal(isolate) };
225 v8::TryCatch trycatch; 245 v8::TryCatch trycatch;
226 v8::Local<v8::Value> value = V8ScriptRunner::callFunction(m_handler.newLocal (isolate), context, v8::Undefined(isolate), WTF_ARRAY_LENGTH(info), info, isolat e); 246 v8::Local<v8::Value> value = V8ScriptRunner::callFunction(m_handler.newLocal (isolate), context, v8::Undefined(isolate), WTF_ARRAY_LENGTH(info), info, isolat e);
227 if (value.IsEmpty()) { 247 if (value.IsEmpty()) {
228 V8PromiseCustom::reject(m_promise.newLocal(isolate), trycatch.Exception( ), isolate); 248 V8PromiseCustom::reject(m_promise.newLocal(isolate), trycatch.Exception( ), isolate);
229 } else { 249 } else {
230 V8PromiseCustom::resolve(m_promise.newLocal(isolate), value, isolate); 250 V8PromiseCustom::resolve(m_promise.newLocal(isolate), value, isolate);
231 } 251 }
232 } 252 }
233 253
234 class UpdateDerivedTask FINAL : public ExecutionContextTask { 254 class UpdateDerivedTask FINAL : public ExecutionContextTask {
235 public: 255 public:
236 UpdateDerivedTask(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> o nFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> originat orValueObject, v8::Isolate* isolate, ExecutionContext* context) 256 UpdateDerivedTask(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> o nFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> originat orValueObject, v8::Isolate* isolate, ExecutionContext* context)
237 : m_promise(isolate, promise) 257 : m_promise(isolate, promise)
238 , m_onFulfilled(isolate, onFulfilled) 258 , m_onFulfilled(isolate, onFulfilled)
239 , m_onRejected(isolate, onRejected) 259 , m_onRejected(isolate, onRejected)
240 , m_originatorValueObject(isolate, originatorValueObject) 260 , m_originatorValueObject(isolate, originatorValueObject)
241 , m_requestState(context) 261 , m_requestState(context)
242 { 262 {
243 ASSERT(!m_promise.isEmpty()); 263 ASSERT(!m_promise.isEmpty());
244 ASSERT(!m_originatorValueObject.isEmpty()); 264 ASSERT(!m_originatorValueObject.isEmpty());
265 InspectorInstrumentation::didPostPromiseTask(context, this, true);
yhirano 2014/01/14 04:54:38 Why is the third parameter always true?
aandrey 2014/01/14 05:35:53 This indicates that the Promise originatorState is
245 } 266 }
246 virtual ~UpdateDerivedTask() { } 267 virtual ~UpdateDerivedTask() { }
247 268
248 virtual void performTask(ExecutionContext*) OVERRIDE; 269 virtual void performTask(ExecutionContext*) OVERRIDE;
249 270
250 private: 271 private:
251 ScopedPersistent<v8::Object> m_promise; 272 ScopedPersistent<v8::Object> m_promise;
252 ScopedPersistent<v8::Function> m_onFulfilled; 273 ScopedPersistent<v8::Function> m_onFulfilled;
253 ScopedPersistent<v8::Function> m_onRejected; 274 ScopedPersistent<v8::Function> m_onRejected;
254 ScopedPersistent<v8::Object> m_originatorValueObject; 275 ScopedPersistent<v8::Object> m_originatorValueObject;
255 DOMRequestState m_requestState; 276 DOMRequestState m_requestState;
256 }; 277 };
257 278
258 void UpdateDerivedTask::performTask(ExecutionContext* context) 279 void UpdateDerivedTask::performTask(ExecutionContext* context)
259 { 280 {
281 TaskPerformScopeForInstrumentation performTaskScope(context, this);
yhirano 2014/01/15 13:28:55 ditto as L236
282
260 ASSERT(context); 283 ASSERT(context);
261 if (context->activeDOMObjectsAreStopped()) 284 if (context->activeDOMObjectsAreStopped())
262 return; 285 return;
263 286
264 DOMRequestState::Scope scope(m_requestState); 287 DOMRequestState::Scope scope(m_requestState);
265 v8::Isolate* isolate = m_requestState.isolate(); 288 v8::Isolate* isolate = m_requestState.isolate();
266 v8::Local<v8::Object> originatorValueObject = m_originatorValueObject.newLoc al(isolate); 289 v8::Local<v8::Object> originatorValueObject = m_originatorValueObject.newLoc al(isolate);
267 v8::Local<v8::Value> coercedAlready = originatorValueObject->GetHiddenValue( V8HiddenPropertyName::thenableHiddenPromise(isolate)); 290 v8::Local<v8::Value> coercedAlready = originatorValueObject->GetHiddenValue( V8HiddenPropertyName::thenableHiddenPromise(isolate));
268 if (!coercedAlready.IsEmpty() && coercedAlready->IsObject()) { 291 if (!coercedAlready.IsEmpty() && coercedAlready->IsObject()) {
269 ASSERT(V8PromiseCustom::isPromise(coercedAlready.As<v8::Object>(), isola te)); 292 ASSERT(V8PromiseCustom::isPromise(coercedAlready.As<v8::Object>(), isola te));
(...skipping 136 matching lines...) Expand 10 before | Expand all | Expand 10 after
406 } 429 }
407 430
408 m_derivedStack.append(Derived::create(derivedPromise, onFulfilled, onRej ected, promise, isolate)); 431 m_derivedStack.append(Derived::create(derivedPromise, onFulfilled, onRej ected, promise, isolate));
409 } 432 }
410 clearDerived(internal, isolate); 433 clearDerived(internal, isolate);
411 } 434 }
412 435
413 void PromisePropagator::updateDerivedFromValue(v8::Handle<v8::Object> derivedPro mise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Value> value, v8::Iso late* isolate) 436 void PromisePropagator::updateDerivedFromValue(v8::Handle<v8::Object> derivedPro mise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Value> value, v8::Iso late* isolate)
414 { 437 {
415 if (!onFulfilled.IsEmpty()) { 438 if (!onFulfilled.IsEmpty()) {
416 V8PromiseCustom::callHandler(derivedPromise, onFulfilled, value, isolate ); 439 V8PromiseCustom::callHandler(derivedPromise, onFulfilled, value, V8Promi seCustom::Fulfilled, isolate);
417 } else { 440 } else {
418 setValue(derivedPromise, value, isolate); 441 setValue(derivedPromise, value, isolate);
419 } 442 }
420 } 443 }
421 444
422 void PromisePropagator::updateDerivedFromReason(v8::Handle<v8::Object> derivedPr omise, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Value> reason, v8::Is olate* isolate) 445 void PromisePropagator::updateDerivedFromReason(v8::Handle<v8::Object> derivedPr omise, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Value> reason, v8::Is olate* isolate)
423 { 446 {
424 if (!onRejected.IsEmpty()) { 447 if (!onRejected.IsEmpty()) {
425 V8PromiseCustom::callHandler(derivedPromise, onRejected, reason, isolate ); 448 V8PromiseCustom::callHandler(derivedPromise, onRejected, reason, V8Promi seCustom::Rejected, isolate);
426 } else { 449 } else {
427 setReason(derivedPromise, reason, isolate); 450 setReason(derivedPromise, reason, isolate);
428 } 451 }
429 } 452 }
430 453
431 void PromisePropagator::updateDerived(v8::Handle<v8::Object> derivedPromise, v8: :Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Hand le<v8::Object> originator, v8::Isolate* isolate) 454 void PromisePropagator::updateDerived(v8::Handle<v8::Object> derivedPromise, v8: :Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Hand le<v8::Object> originator, v8::Isolate* isolate)
432 { 455 {
433 v8::Local<v8::Object> originatorInternal = V8PromiseCustom::getInternal(orig inator); 456 v8::Local<v8::Object> originatorInternal = V8PromiseCustom::getInternal(orig inator);
434 V8PromiseCustom::PromiseState originatorState = V8PromiseCustom::getState(or iginatorInternal); 457 V8PromiseCustom::PromiseState originatorState = V8PromiseCustom::getState(or iginatorInternal);
435 ASSERT(originatorState == V8PromiseCustom::Fulfilled || originatorState == V 8PromiseCustom::Rejected); 458 ASSERT(originatorState == V8PromiseCustom::Fulfilled || originatorState == V 8PromiseCustom::Rejected);
(...skipping 340 matching lines...) Expand 10 before | Expand all | Expand 10 after
776 createClosure(promiseRejectCallback, promise, isolate) 799 createClosure(promiseRejectCallback, promise, isolate)
777 }; 800 };
778 v8::TryCatch trycatch; 801 v8::TryCatch trycatch;
779 if (V8ScriptRunner::callFunction(then, getExecutionContext(), thenable, WTF_ ARRAY_LENGTH(argv), argv, isolate).IsEmpty()) { 802 if (V8ScriptRunner::callFunction(then, getExecutionContext(), thenable, WTF_ ARRAY_LENGTH(argv), argv, isolate).IsEmpty()) {
780 reject(promise, trycatch.Exception(), isolate); 803 reject(promise, trycatch.Exception(), isolate);
781 } 804 }
782 thenable->SetHiddenValue(V8HiddenPropertyName::thenableHiddenPromise(isolate ), promise); 805 thenable->SetHiddenValue(V8HiddenPropertyName::thenableHiddenPromise(isolate ), promise);
783 return promise; 806 return promise;
784 } 807 }
785 808
786 void V8PromiseCustom::callHandler(v8::Handle<v8::Object> promise, v8::Handle<v8: :Function> handler, v8::Handle<v8::Value> argument, v8::Isolate* isolate) 809 void V8PromiseCustom::callHandler(v8::Handle<v8::Object> promise, v8::Handle<v8: :Function> handler, v8::Handle<v8::Value> argument, PromiseState originatorState , v8::Isolate* isolate)
787 { 810 {
811 ASSERT(originatorState == Fulfilled || originatorState == Rejected);
788 ExecutionContext* executionContext = getExecutionContext(); 812 ExecutionContext* executionContext = getExecutionContext();
789 ASSERT(executionContext && executionContext->isContextThread()); 813 ASSERT(executionContext && executionContext->isContextThread());
790 executionContext->postTask(adoptPtr(new CallHandlerTask(promise, handler, ar gument, isolate, executionContext))); 814 executionContext->postTask(adoptPtr(new CallHandlerTask(promise, handler, ar gument, originatorState, isolate, executionContext)));
791 } 815 }
792 816
793 } // namespace WebCore 817 } // namespace WebCore
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698