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

Side by Side Diff: Source/modules/websockets/WorkerThreadableWebSocketChannel.cpp

Issue 265713004: Cleanup WorkerThreadableWebSocketChannel's logic to wait for the main thread (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Created 6 years, 7 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
« no previous file with comments | « Source/modules/websockets/WorkerThreadableWebSocketChannel.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2011, 2012 Google Inc. All rights reserved. 2 * Copyright (C) 2011, 2012 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 102 matching lines...) Expand 10 before | Expand all | Expand 10 after
113 , m_bufferedAmount(0) 113 , m_bufferedAmount(0)
114 { 114 {
115 } 115 }
116 116
117 OwnPtr<blink::WebWaitableEvent> m_event; 117 OwnPtr<blink::WebWaitableEvent> m_event;
118 bool m_connectRequestResult; 118 bool m_connectRequestResult;
119 WebSocketChannel::SendResult m_sendRequestResult; 119 WebSocketChannel::SendResult m_sendRequestResult;
120 unsigned long m_bufferedAmount; 120 unsigned long m_bufferedAmount;
121 }; 121 };
122 122
123 WorkerThreadableWebSocketChannel::WorkerThreadableWebSocketChannel(WorkerGlobalS cope& context, WebSocketChannelClient* client, const String& sourceURL, unsigned lineNumber) 123 WorkerThreadableWebSocketChannel::WorkerThreadableWebSocketChannel(WorkerGlobalS cope& workerGlobalScope, WebSocketChannelClient* client, const String& sourceURL , unsigned lineNumber)
124 : m_workerGlobalScope(context) 124 : m_workerClientWrapper(ThreadableWebSocketChannelClientWrapper::create(clie nt))
125 , m_workerClientWrapper(ThreadableWebSocketChannelClientWrapper::create(clie nt)) 125 , m_bridge(Bridge::create(m_workerClientWrapper, workerGlobalScope))
126 , m_bridge(Bridge::create(m_workerClientWrapper, m_workerGlobalScope))
127 , m_sourceURLAtConnection(sourceURL) 126 , m_sourceURLAtConnection(sourceURL)
128 , m_lineNumberAtConnection(lineNumber) 127 , m_lineNumberAtConnection(lineNumber)
129 { 128 {
130 ASSERT(m_workerClientWrapper.get()); 129 ASSERT(m_workerClientWrapper.get());
131 m_bridge->initialize(sourceURL, lineNumber); 130 m_bridge->initialize(sourceURL, lineNumber);
132 } 131 }
133 132
134 WorkerThreadableWebSocketChannel::~WorkerThreadableWebSocketChannel() 133 WorkerThreadableWebSocketChannel::~WorkerThreadableWebSocketChannel()
135 { 134 {
136 if (m_bridge) 135 if (m_bridge)
(...skipping 313 matching lines...) Expand 10 before | Expand all | Expand 10 after
450 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); 449 ASSERT_UNUSED(context, context->isWorkerGlobalScope());
451 workerClientWrapper->didReceiveMessageError(); 450 workerClientWrapper->didReceiveMessageError();
452 } 451 }
453 452
454 void WorkerThreadableWebSocketChannel::Peer::didReceiveMessageError() 453 void WorkerThreadableWebSocketChannel::Peer::didReceiveMessageError()
455 { 454 {
456 ASSERT(isMainThread()); 455 ASSERT(isMainThread());
457 m_loaderProxy.postTaskToWorkerGlobalScope(createCallbackTask(&workerGlobalSc opeDidReceiveMessageError, m_workerClientWrapper)); 456 m_loaderProxy.postTaskToWorkerGlobalScope(createCallbackTask(&workerGlobalSc opeDidReceiveMessageError, m_workerClientWrapper));
458 } 457 }
459 458
460 WorkerThreadableWebSocketChannel::Bridge::Bridge(PassRefPtr<ThreadableWebSocketC hannelClientWrapper> workerClientWrapper, PassRefPtrWillBeRawPtr<WorkerGlobalSco pe> workerGlobalScope) 459 WorkerThreadableWebSocketChannel::Bridge::Bridge(PassRefPtr<ThreadableWebSocketC hannelClientWrapper> workerClientWrapper, WorkerGlobalScope& workerGlobalScope)
461 : m_workerClientWrapper(workerClientWrapper) 460 : m_workerClientWrapper(workerClientWrapper)
462 , m_workerGlobalScope(workerGlobalScope) 461 , m_workerGlobalScope(workerGlobalScope)
463 , m_loaderProxy(m_workerGlobalScope->thread()->workerLoaderProxy()) 462 , m_loaderProxy(m_workerGlobalScope->thread()->workerLoaderProxy())
464 , m_syncHelper(0) 463 , m_syncHelper(0)
465 { 464 {
466 ASSERT(m_workerClientWrapper.get()); 465 ASSERT(m_workerClientWrapper.get());
467 } 466 }
468 467
469 WorkerThreadableWebSocketChannel::Bridge::~Bridge() 468 WorkerThreadableWebSocketChannel::Bridge::~Bridge()
470 { 469 {
(...skipping 12 matching lines...) Expand all
483 RefPtr<Bridge> protect(this); 482 RefPtr<Bridge> protect(this);
484 m_loaderProxy.postTaskToLoader(createCallbackTask(&Peer::initialize, referen ce.release(), AllowCrossThreadAccess(&m_loaderProxy), m_workerClientWrapper, sou rceURL, lineNumber, syncHelper.release())); 483 m_loaderProxy.postTaskToLoader(createCallbackTask(&Peer::initialize, referen ce.release(), AllowCrossThreadAccess(&m_loaderProxy), m_workerClientWrapper, sou rceURL, lineNumber, syncHelper.release()));
485 if (!waitForMethodCompletion()) { 484 if (!waitForMethodCompletion()) {
486 // The worker thread has been signalled to shutdown before method comple tion. 485 // The worker thread has been signalled to shutdown before method comple tion.
487 terminatePeer(); 486 terminatePeer();
488 } 487 }
489 } 488 }
490 489
491 bool WorkerThreadableWebSocketChannel::Bridge::connect(const KURL& url, const St ring& protocol) 490 bool WorkerThreadableWebSocketChannel::Bridge::connect(const KURL& url, const St ring& protocol)
492 { 491 {
493 if (!m_workerGlobalScope) 492 if (hasTerminatedPeer())
494 return false; 493 return false;
495 ASSERT(m_syncHelper); 494
495 RefPtr<Bridge> protect(this);
yhirano 2014/05/07 08:05:18 Can you tell me why this move is needed? I think p
tyoshino (SeeGerritForStatus) 2014/05/08 05:03:00 As discussed offline, it looks we no longer need t
496 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::connect, m_peer, url.copy(), protocol.isolatedCopy()))); 496 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::connect, m_peer, url.copy(), protocol.isolatedCopy())));
497 RefPtr<Bridge> protect(this); 497 if (!waitForMethodCompletion())
yhirano 2014/05/07 08:05:18 [optional] We could have postTaskAndWait for this
tyoshino (SeeGerritForStatus) 2014/05/08 05:03:00 Done.
498 waitForMethodCompletion(); 498 return false;
499
499 return m_syncHelper->connectRequestResult(); 500 return m_syncHelper->connectRequestResult();
500 } 501 }
501 502
502 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(cons t String& message) 503 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(cons t String& message)
503 { 504 {
504 if (!m_workerGlobalScope) 505 if (hasTerminatedPeer())
505 return WebSocketChannel::SendFail; 506 return WebSocketChannel::SendFail;
506 ASSERT(m_syncHelper); 507
508 RefPtr<Bridge> protect(this);
507 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::send, m_p eer, message.isolatedCopy()))); 509 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::send, m_p eer, message.isolatedCopy())));
508 RefPtr<Bridge> protect(this); 510 if (!waitForMethodCompletion())
509 waitForMethodCompletion(); 511 return WebSocketChannel::SendFail;
512
510 return m_syncHelper->sendRequestResult(); 513 return m_syncHelper->sendRequestResult();
511 } 514 }
512 515
513 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(cons t ArrayBuffer& binaryData, unsigned byteOffset, unsigned byteLength) 516 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(cons t ArrayBuffer& binaryData, unsigned byteOffset, unsigned byteLength)
514 { 517 {
515 if (!m_workerGlobalScope) 518 if (hasTerminatedPeer())
516 return WebSocketChannel::SendFail; 519 return WebSocketChannel::SendFail;
517 ASSERT(m_syncHelper); 520
518 // ArrayBuffer isn't thread-safe, hence the content of ArrayBuffer is copied into Vector<char>. 521 // ArrayBuffer isn't thread-safe, hence the content of ArrayBuffer is copied into Vector<char>.
519 OwnPtr<Vector<char> > data = adoptPtr(new Vector<char>(byteLength)); 522 OwnPtr<Vector<char> > data = adoptPtr(new Vector<char>(byteLength));
520 if (binaryData.byteLength()) 523 if (binaryData.byteLength())
521 memcpy(data->data(), static_cast<const char*>(binaryData.data()) + byteO ffset, byteLength); 524 memcpy(data->data(), static_cast<const char*>(binaryData.data()) + byteO ffset, byteLength);
522 525
526 RefPtr<Bridge> protect(this);
523 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::sendArray Buffer, m_peer, data.release()))); 527 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::sendArray Buffer, m_peer, data.release())));
524 RefPtr<Bridge> protect(this); 528 if (!waitForMethodCompletion())
525 waitForMethodCompletion(); 529 return WebSocketChannel::SendFail;
530
526 return m_syncHelper->sendRequestResult(); 531 return m_syncHelper->sendRequestResult();
527 } 532 }
528 533
529 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(Pass RefPtr<BlobDataHandle> data) 534 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(Pass RefPtr<BlobDataHandle> data)
530 { 535 {
531 if (!m_workerGlobalScope) 536 if (hasTerminatedPeer())
532 return WebSocketChannel::SendFail; 537 return WebSocketChannel::SendFail;
533 ASSERT(m_syncHelper); 538
539 RefPtr<Bridge> protect(this);
534 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::sendBlob, m_peer, data))); 540 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::sendBlob, m_peer, data)));
535 RefPtr<Bridge> protect(this); 541 if (!waitForMethodCompletion())
536 waitForMethodCompletion(); 542 return WebSocketChannel::SendFail;
543
537 return m_syncHelper->sendRequestResult(); 544 return m_syncHelper->sendRequestResult();
538 } 545 }
539 546
540 unsigned long WorkerThreadableWebSocketChannel::Bridge::bufferedAmount() 547 unsigned long WorkerThreadableWebSocketChannel::Bridge::bufferedAmount()
541 { 548 {
542 if (!m_workerGlobalScope) 549 if (hasTerminatedPeer())
543 return 0; 550 return 0;
544 ASSERT(m_syncHelper); 551
552 RefPtr<Bridge> protect(this);
545 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::bufferedA mount, m_peer))); 553 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::bufferedA mount, m_peer)));
546 RefPtr<Bridge> protect(this); 554 if (!waitForMethodCompletion())
547 waitForMethodCompletion(); 555 return 0;
556
548 return m_syncHelper->bufferedAmount(); 557 return m_syncHelper->bufferedAmount();
549 } 558 }
550 559
551 void WorkerThreadableWebSocketChannel::Bridge::close(int code, const String& rea son) 560 void WorkerThreadableWebSocketChannel::Bridge::close(int code, const String& rea son)
552 { 561 {
562 if (hasTerminatedPeer())
563 return;
564
553 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::close, m_ peer, code, reason.isolatedCopy()))); 565 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::close, m_ peer, code, reason.isolatedCopy())));
554 } 566 }
555 567
556 void WorkerThreadableWebSocketChannel::Bridge::fail(const String& reason, Messag eLevel level, const String& sourceURL, unsigned lineNumber) 568 void WorkerThreadableWebSocketChannel::Bridge::fail(const String& reason, Messag eLevel level, const String& sourceURL, unsigned lineNumber)
557 { 569 {
570 if (hasTerminatedPeer())
571 return;
572
558 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::fail, m_p eer, reason.isolatedCopy(), level, sourceURL.isolatedCopy(), lineNumber))); 573 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::fail, m_p eer, reason.isolatedCopy(), level, sourceURL.isolatedCopy(), lineNumber)));
559 } 574 }
560 575
561 void WorkerThreadableWebSocketChannel::Bridge::disconnect() 576 void WorkerThreadableWebSocketChannel::Bridge::disconnect()
562 { 577 {
563 clearClientWrapper(); 578 clearClientWrapper();
564 terminatePeer(); 579 terminatePeer();
565 } 580 }
566 581
567 void WorkerThreadableWebSocketChannel::Bridge::suspend() 582 void WorkerThreadableWebSocketChannel::Bridge::suspend()
568 { 583 {
584 if (hasTerminatedPeer())
585 return;
586
569 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::suspend, m_peer))); 587 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::suspend, m_peer)));
570 } 588 }
571 589
572 void WorkerThreadableWebSocketChannel::Bridge::resume() 590 void WorkerThreadableWebSocketChannel::Bridge::resume()
573 { 591 {
592 if (hasTerminatedPeer())
593 return;
594
574 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::resume, m _peer))); 595 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::resume, m _peer)));
575 } 596 }
576 597
577 void WorkerThreadableWebSocketChannel::Bridge::clearClientWrapper() 598 void WorkerThreadableWebSocketChannel::Bridge::clearClientWrapper()
578 { 599 {
579 m_workerClientWrapper->clearClient(); 600 m_workerClientWrapper->clearClient();
580 } 601 }
581 602
582 // Caller of this function should hold a reference to the bridge, because this f unction may call WebSocket::didClose() in the end, 603 // Caller of this function should hold a reference to the bridge, because this f unction may call WebSocket::didClose() in the end,
583 // which causes the bridge to get disconnected from the WebSocket and deleted if there is no other reference. 604 // which causes the bridge to get disconnected from the WebSocket and deleted if there is no other reference.
584 bool WorkerThreadableWebSocketChannel::Bridge::waitForMethodCompletion() 605 bool WorkerThreadableWebSocketChannel::Bridge::waitForMethodCompletion()
585 { 606 {
586 if (!m_syncHelper) 607 ASSERT(m_workerGlobalScope);
587 return true; 608 ASSERT(m_syncHelper);
588 609
589 blink::WebWaitableEvent* shutdownEvent = m_workerGlobalScope->thread()->shut downEvent(); 610 blink::WebWaitableEvent* shutdownEvent = m_workerGlobalScope->thread()->shut downEvent();
590 Vector<blink::WebWaitableEvent*> events; 611 Vector<blink::WebWaitableEvent*> events;
591 events.append(shutdownEvent); 612 events.append(shutdownEvent);
592 events.append(m_syncHelper->event()); 613 events.append(m_syncHelper->event());
593 614
594 ThreadState::SafePointScope scope(ThreadState::HeapPointersOnStack); 615 ThreadState::SafePointScope scope(ThreadState::HeapPointersOnStack);
595 blink::WebWaitableEvent* signalled = blink::Platform::current()->waitMultipl eEvents(events); 616 blink::WebWaitableEvent* signalled = blink::Platform::current()->waitMultipl eEvents(events);
596 return signalled != shutdownEvent; 617 return signalled != shutdownEvent;
597 } 618 }
598 619
599 void WorkerThreadableWebSocketChannel::Bridge::terminatePeer() 620 void WorkerThreadableWebSocketChannel::Bridge::terminatePeer()
600 { 621 {
601 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::destroy, m_peer))); 622 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::destroy, m_peer)));
623 // Peer::destroy() deletes m_peer and then m_syncHelper will be released.
624 // We must not touch m_syncHelper any more.
625 m_syncHelper = 0;
626
627 // We won't use this any more.
602 m_workerGlobalScope = nullptr; 628 m_workerGlobalScope = nullptr;
603 m_syncHelper = 0;
604 } 629 }
605 630
606 } // namespace WebCore 631 } // namespace WebCore
OLDNEW
« no previous file with comments | « Source/modules/websockets/WorkerThreadableWebSocketChannel.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698