| OLD | NEW |
| 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 325 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 336 | 336 |
| 337 static void workerGlobalScopeDidConnect(ExecutionContext* context, PassRefPtrWil
lBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWrapper, const St
ring& subprotocol, const String& extensions) | 337 static void workerGlobalScopeDidConnect(ExecutionContext* context, PassRefPtrWil
lBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWrapper, const St
ring& subprotocol, const String& extensions) |
| 338 { | 338 { |
| 339 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 339 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 340 workerClientWrapper->didConnect(subprotocol, extensions); | 340 workerClientWrapper->didConnect(subprotocol, extensions); |
| 341 } | 341 } |
| 342 | 342 |
| 343 void WorkerThreadableWebSocketChannel::Peer::didConnect(const String& subprotoco
l, const String& extensions) | 343 void WorkerThreadableWebSocketChannel::Peer::didConnect(const String& subprotoco
l, const String& extensions) |
| 344 { | 344 { |
| 345 ASSERT(isMainThread()); | 345 ASSERT(isMainThread()); |
| 346 m_loaderProxy.postTaskToWorkerGlobalScope(createCallbackTask(&workerGlobalSc
opeDidConnect, m_workerClientWrapper.get(), subprotocol, extensions)); | 346 // It is important to seprate task creation from posting |
| 347 // the task. See the above comment. |
| 348 OwnPtr<ExecutionContextTask> task = createCallbackTask(&workerGlobalScopeDid
Connect, m_workerClientWrapper.get(), subprotocol, extensions); |
| 349 m_loaderProxy.postTaskToWorkerGlobalScope(task.release()); |
| 347 } | 350 } |
| 348 | 351 |
| 349 static void workerGlobalScopeDidReceiveMessage(ExecutionContext* context, PassRe
fPtrWillBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWrapper, c
onst String& message) | 352 static void workerGlobalScopeDidReceiveMessage(ExecutionContext* context, PassRe
fPtrWillBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWrapper, c
onst String& message) |
| 350 { | 353 { |
| 351 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 354 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 352 workerClientWrapper->didReceiveMessage(message); | 355 workerClientWrapper->didReceiveMessage(message); |
| 353 } | 356 } |
| 354 | 357 |
| 355 void WorkerThreadableWebSocketChannel::Peer::didReceiveMessage(const String& mes
sage) | 358 void WorkerThreadableWebSocketChannel::Peer::didReceiveMessage(const String& mes
sage) |
| 356 { | 359 { |
| 357 ASSERT(isMainThread()); | 360 ASSERT(isMainThread()); |
| 358 m_loaderProxy.postTaskToWorkerGlobalScope(createCallbackTask(&workerGlobalSc
opeDidReceiveMessage, m_workerClientWrapper.get(), message)); | 361 // It is important to seprate task creation from posting |
| 362 // the task. See the above comment. |
| 363 OwnPtr<ExecutionContextTask> task = createCallbackTask(&workerGlobalScopeDid
ReceiveMessage, m_workerClientWrapper.get(), message); |
| 364 m_loaderProxy.postTaskToWorkerGlobalScope(task.release()); |
| 359 } | 365 } |
| 360 | 366 |
| 361 static void workerGlobalScopeDidReceiveBinaryData(ExecutionContext* context, Pas
sRefPtrWillBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWrapper
, PassOwnPtr<Vector<char> > binaryData) | 367 static void workerGlobalScopeDidReceiveBinaryData(ExecutionContext* context, Pas
sRefPtrWillBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWrapper
, PassOwnPtr<Vector<char> > binaryData) |
| 362 { | 368 { |
| 363 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 369 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 364 workerClientWrapper->didReceiveBinaryData(binaryData); | 370 workerClientWrapper->didReceiveBinaryData(binaryData); |
| 365 } | 371 } |
| 366 | 372 |
| 367 void WorkerThreadableWebSocketChannel::Peer::didReceiveBinaryData(PassOwnPtr<Vec
tor<char> > binaryData) | 373 void WorkerThreadableWebSocketChannel::Peer::didReceiveBinaryData(PassOwnPtr<Vec
tor<char> > binaryData) |
| 368 { | 374 { |
| 369 ASSERT(isMainThread()); | 375 ASSERT(isMainThread()); |
| 370 m_loaderProxy.postTaskToWorkerGlobalScope(createCallbackTask(&workerGlobalSc
opeDidReceiveBinaryData, m_workerClientWrapper.get(), binaryData)); | 376 // It is important to seprate task creation from posting |
| 377 // the task. See the above comment. |
| 378 OwnPtr<ExecutionContextTask> task = createCallbackTask(&workerGlobalScopeDid
ReceiveBinaryData, m_workerClientWrapper.get(), binaryData); |
| 379 m_loaderProxy.postTaskToWorkerGlobalScope(task.release()); |
| 371 } | 380 } |
| 372 | 381 |
| 373 static void workerGlobalScopeDidConsumeBufferedAmount(ExecutionContext* context,
PassRefPtrWillBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWra
pper, unsigned long consumed) | 382 static void workerGlobalScopeDidConsumeBufferedAmount(ExecutionContext* context,
PassRefPtrWillBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWra
pper, unsigned long consumed) |
| 374 { | 383 { |
| 375 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 384 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 376 workerClientWrapper->didConsumeBufferedAmount(consumed); | 385 workerClientWrapper->didConsumeBufferedAmount(consumed); |
| 377 } | 386 } |
| 378 | 387 |
| 379 void WorkerThreadableWebSocketChannel::Peer::didConsumeBufferedAmount(unsigned l
ong consumed) | 388 void WorkerThreadableWebSocketChannel::Peer::didConsumeBufferedAmount(unsigned l
ong consumed) |
| 380 { | 389 { |
| 381 ASSERT(isMainThread()); | 390 ASSERT(isMainThread()); |
| 382 m_loaderProxy.postTaskToWorkerGlobalScope(createCallbackTask(&workerGlobalSc
opeDidConsumeBufferedAmount, m_workerClientWrapper.get(), consumed)); | 391 // It is important to seprate task creation from posting |
| 392 // the task. See the above comment. |
| 393 OwnPtr<ExecutionContextTask> task = createCallbackTask(&workerGlobalScopeDid
ConsumeBufferedAmount, m_workerClientWrapper.get(), consumed); |
| 394 m_loaderProxy.postTaskToWorkerGlobalScope(task.release()); |
| 383 } | 395 } |
| 384 | 396 |
| 385 static void workerGlobalScopeDidStartClosingHandshake(ExecutionContext* context,
PassRefPtrWillBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWra
pper) | 397 static void workerGlobalScopeDidStartClosingHandshake(ExecutionContext* context,
PassRefPtrWillBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWra
pper) |
| 386 { | 398 { |
| 387 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 399 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 388 workerClientWrapper->didStartClosingHandshake(); | 400 workerClientWrapper->didStartClosingHandshake(); |
| 389 } | 401 } |
| 390 | 402 |
| 391 void WorkerThreadableWebSocketChannel::Peer::didStartClosingHandshake() | 403 void WorkerThreadableWebSocketChannel::Peer::didStartClosingHandshake() |
| 392 { | 404 { |
| 393 ASSERT(isMainThread()); | 405 ASSERT(isMainThread()); |
| 394 m_loaderProxy.postTaskToWorkerGlobalScope(createCallbackTask(&workerGlobalSc
opeDidStartClosingHandshake, m_workerClientWrapper.get())); | 406 // It is important to seprate task creation from posting |
| 407 // the task. See the above comment. |
| 408 OwnPtr<ExecutionContextTask> task = createCallbackTask(&workerGlobalScopeDid
StartClosingHandshake, m_workerClientWrapper.get()); |
| 409 m_loaderProxy.postTaskToWorkerGlobalScope(task.release()); |
| 395 } | 410 } |
| 396 | 411 |
| 397 static void workerGlobalScopeDidClose(ExecutionContext* context, PassRefPtrWillB
eRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWrapper, WebSocketC
hannelClient::ClosingHandshakeCompletionStatus closingHandshakeCompletion, unsig
ned short code, const String& reason) | 412 static void workerGlobalScopeDidClose(ExecutionContext* context, PassRefPtrWillB
eRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWrapper, WebSocketC
hannelClient::ClosingHandshakeCompletionStatus closingHandshakeCompletion, unsig
ned short code, const String& reason) |
| 398 { | 413 { |
| 399 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 414 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 400 workerClientWrapper->didClose(closingHandshakeCompletion, code, reason); | 415 workerClientWrapper->didClose(closingHandshakeCompletion, code, reason); |
| 401 } | 416 } |
| 402 | 417 |
| 403 void WorkerThreadableWebSocketChannel::Peer::didClose(ClosingHandshakeCompletion
Status closingHandshakeCompletion, unsigned short code, const String& reason) | 418 void WorkerThreadableWebSocketChannel::Peer::didClose(ClosingHandshakeCompletion
Status closingHandshakeCompletion, unsigned short code, const String& reason) |
| 404 { | 419 { |
| 405 ASSERT(isMainThread()); | 420 ASSERT(isMainThread()); |
| 406 m_mainWebSocketChannel = nullptr; | 421 m_mainWebSocketChannel = nullptr; |
| 407 m_loaderProxy.postTaskToWorkerGlobalScope(createCallbackTask(&workerGlobalSc
opeDidClose, m_workerClientWrapper.get(), closingHandshakeCompletion, code, reas
on)); | 422 // It is important to seprate task creation from posting |
| 423 // the task. See the above comment. |
| 424 OwnPtr<ExecutionContextTask> task = createCallbackTask(&workerGlobalScopeDid
Close, m_workerClientWrapper.get(), closingHandshakeCompletion, code, reason); |
| 425 m_loaderProxy.postTaskToWorkerGlobalScope(task.release()); |
| 408 } | 426 } |
| 409 | 427 |
| 410 static void workerGlobalScopeDidReceiveMessageError(ExecutionContext* context, P
assRefPtrWillBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWrapp
er) | 428 static void workerGlobalScopeDidReceiveMessageError(ExecutionContext* context, P
assRefPtrWillBeRawPtr<ThreadableWebSocketChannelClientWrapper> workerClientWrapp
er) |
| 411 { | 429 { |
| 412 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 430 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 413 workerClientWrapper->didReceiveMessageError(); | 431 workerClientWrapper->didReceiveMessageError(); |
| 414 } | 432 } |
| 415 | 433 |
| 416 void WorkerThreadableWebSocketChannel::Peer::didReceiveMessageError() | 434 void WorkerThreadableWebSocketChannel::Peer::didReceiveMessageError() |
| 417 { | 435 { |
| 418 ASSERT(isMainThread()); | 436 ASSERT(isMainThread()); |
| 419 m_loaderProxy.postTaskToWorkerGlobalScope(createCallbackTask(&workerGlobalSc
opeDidReceiveMessageError, m_workerClientWrapper.get())); | 437 // It is important to seprate task creation from posting |
| 438 // the task. See the above comment. |
| 439 OwnPtr<ExecutionContextTask> task = createCallbackTask(&workerGlobalScopeDid
ReceiveMessageError, m_workerClientWrapper.get()); |
| 440 m_loaderProxy.postTaskToWorkerGlobalScope(task.release()); |
| 420 } | 441 } |
| 421 | 442 |
| 422 void WorkerThreadableWebSocketChannel::Peer::trace(Visitor* visitor) | 443 void WorkerThreadableWebSocketChannel::Peer::trace(Visitor* visitor) |
| 423 { | 444 { |
| 424 visitor->trace(m_workerClientWrapper); | 445 visitor->trace(m_workerClientWrapper); |
| 425 visitor->trace(m_mainWebSocketChannel); | 446 visitor->trace(m_mainWebSocketChannel); |
| 426 visitor->trace(m_syncHelper); | 447 visitor->trace(m_syncHelper); |
| 427 WebSocketChannelClient::trace(visitor); | 448 WebSocketChannelClient::trace(visitor); |
| 428 } | 449 } |
| 429 | 450 |
| (...skipping 18 matching lines...) Expand all Loading... |
| 448 RefPtr<WeakReference<Peer> > reference = WeakReference<Peer>::createUnbound(
); | 469 RefPtr<WeakReference<Peer> > reference = WeakReference<Peer>::createUnbound(
); |
| 449 m_peer = WeakPtr<Peer>(reference); | 470 m_peer = WeakPtr<Peer>(reference); |
| 450 #endif | 471 #endif |
| 451 | 472 |
| 452 RefPtrWillBeRawPtr<ThreadableWebSocketChannelSyncHelper> syncHelper = Thread
ableWebSocketChannelSyncHelper::create(adoptPtr(blink::Platform::current()->crea
teWaitableEvent())); | 473 RefPtrWillBeRawPtr<ThreadableWebSocketChannelSyncHelper> syncHelper = Thread
ableWebSocketChannelSyncHelper::create(adoptPtr(blink::Platform::current()->crea
teWaitableEvent())); |
| 453 // This pointer is guaranteed to be valid until we call terminatePeer. | 474 // This pointer is guaranteed to be valid until we call terminatePeer. |
| 454 m_syncHelper = syncHelper.get(); | 475 m_syncHelper = syncHelper.get(); |
| 455 | 476 |
| 456 RefPtrWillBeRawPtr<Bridge> protect(this); | 477 RefPtrWillBeRawPtr<Bridge> protect(this); |
| 457 #if ENABLE(OILPAN) | 478 #if ENABLE(OILPAN) |
| 458 if (!waitForMethodCompletion(createCallbackTask(&Peer::initialize, &m_peer,
AllowCrossThreadAccess(&m_loaderProxy), m_workerClientWrapper.get(), sourceURL,
lineNumber, syncHelper.get()))) { | 479 // In order to assure all temporary objects to be destroyed before |
| 480 // posting the task, we separate task creation and posting. |
| 481 // In other words, it is dangerous to have a complicated expression |
| 482 // as a waitForMethodCompletion argument. |
| 483 OwnPtr<ExecutionContextTask> task = createCallbackTask(&Peer::initialize, &m
_peer, AllowCrossThreadAccess(&m_loaderProxy), m_workerClientWrapper.get(), sour
ceURL, lineNumber, syncHelper.get()); |
| 459 #else | 484 #else |
| 460 if (!waitForMethodCompletion(createCallbackTask(&Peer::initialize, reference
, AllowCrossThreadAccess(&m_loaderProxy), m_workerClientWrapper.get(), sourceURL
, lineNumber, syncHelper.get()))) { | 485 // See the above comment. |
| 486 OwnPtr<ExecutionContextTask> task = createCallbackTask(&Peer::initialize, re
ference, AllowCrossThreadAccess(&m_loaderProxy), m_workerClientWrapper.get(), so
urceURL, lineNumber, syncHelper.get()); |
| 461 #endif | 487 #endif |
| 488 if (!waitForMethodCompletion(task.release())) { |
| 462 // The worker thread has been signalled to shutdown before method comple
tion. | 489 // The worker thread has been signalled to shutdown before method comple
tion. |
| 463 disconnect(); | 490 disconnect(); |
| 464 } | 491 } |
| 465 } | 492 } |
| 466 | 493 |
| 467 bool WorkerThreadableWebSocketChannel::Bridge::connect(const KURL& url, const St
ring& protocol) | 494 bool WorkerThreadableWebSocketChannel::Bridge::connect(const KURL& url, const St
ring& protocol) |
| 468 { | 495 { |
| 469 if (hasTerminatedPeer()) | 496 if (hasTerminatedPeer()) |
| 470 return false; | 497 return false; |
| 471 | 498 |
| 472 RefPtrWillBeRawPtr<Bridge> protect(this); | 499 RefPtrWillBeRawPtr<Bridge> protect(this); |
| 473 if (!waitForMethodCompletion(CallClosureTask::create(bind(&Peer::connect, m_
peer, url.copy(), protocol.isolatedCopy())))) | 500 // It is important to seprate task creation from calling |
| 501 // waitForMethodCompletion. See the above comment. |
| 502 OwnPtr<ExecutionContextTask> task = CallClosureTask::create(bind(&Peer::conn
ect, m_peer, url.copy(), protocol.isolatedCopy())); |
| 503 if (!waitForMethodCompletion(task.release())) |
| 474 return false; | 504 return false; |
| 475 | 505 |
| 476 return m_syncHelper->connectRequestResult(); | 506 return m_syncHelper->connectRequestResult(); |
| 477 } | 507 } |
| 478 | 508 |
| 479 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(cons
t String& message) | 509 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(cons
t String& message) |
| 480 { | 510 { |
| 481 if (hasTerminatedPeer()) | 511 if (hasTerminatedPeer()) |
| 482 return WebSocketChannel::SendFail; | 512 return WebSocketChannel::SendFail; |
| 483 | 513 |
| 484 RefPtrWillBeRawPtr<Bridge> protect(this); | 514 RefPtrWillBeRawPtr<Bridge> protect(this); |
| 485 if (!waitForMethodCompletion(CallClosureTask::create(bind(&Peer::send, m_pee
r, message.isolatedCopy())))) | 515 // It is important to seprate task creation from calling |
| 516 // waitForMethodCompletion. See the above comment. |
| 517 OwnPtr<ExecutionContextTask> task = CallClosureTask::create(bind(&Peer::send
, m_peer, message.isolatedCopy())); |
| 518 if (!waitForMethodCompletion(task.release())) |
| 486 return WebSocketChannel::SendFail; | 519 return WebSocketChannel::SendFail; |
| 487 | 520 |
| 488 return m_syncHelper->sendRequestResult(); | 521 return m_syncHelper->sendRequestResult(); |
| 489 } | 522 } |
| 490 | 523 |
| 491 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(cons
t ArrayBuffer& binaryData, unsigned byteOffset, unsigned byteLength) | 524 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(cons
t ArrayBuffer& binaryData, unsigned byteOffset, unsigned byteLength) |
| 492 { | 525 { |
| 493 if (hasTerminatedPeer()) | 526 if (hasTerminatedPeer()) |
| 494 return WebSocketChannel::SendFail; | 527 return WebSocketChannel::SendFail; |
| 495 | 528 |
| 496 // ArrayBuffer isn't thread-safe, hence the content of ArrayBuffer is copied
into Vector<char>. | 529 // ArrayBuffer isn't thread-safe, hence the content of ArrayBuffer is copied
into Vector<char>. |
| 497 OwnPtr<Vector<char> > data = adoptPtr(new Vector<char>(byteLength)); | 530 OwnPtr<Vector<char> > data = adoptPtr(new Vector<char>(byteLength)); |
| 498 if (binaryData.byteLength()) | 531 if (binaryData.byteLength()) |
| 499 memcpy(data->data(), static_cast<const char*>(binaryData.data()) + byteO
ffset, byteLength); | 532 memcpy(data->data(), static_cast<const char*>(binaryData.data()) + byteO
ffset, byteLength); |
| 500 | 533 |
| 501 RefPtrWillBeRawPtr<Bridge> protect(this); | 534 RefPtrWillBeRawPtr<Bridge> protect(this); |
| 502 if (!waitForMethodCompletion(CallClosureTask::create(bind(&Peer::sendArrayBu
ffer, m_peer, data.release())))) | 535 // It is important to seprate task creation from calling |
| 536 // waitForMethodCompletion. See the above comment. |
| 537 OwnPtr<ExecutionContextTask> task = CallClosureTask::create(bind(&Peer::send
ArrayBuffer, m_peer, data.release())); |
| 538 if (!waitForMethodCompletion(task.release())) |
| 503 return WebSocketChannel::SendFail; | 539 return WebSocketChannel::SendFail; |
| 504 | 540 |
| 505 return m_syncHelper->sendRequestResult(); | 541 return m_syncHelper->sendRequestResult(); |
| 506 } | 542 } |
| 507 | 543 |
| 508 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(Pass
RefPtr<BlobDataHandle> data) | 544 WebSocketChannel::SendResult WorkerThreadableWebSocketChannel::Bridge::send(Pass
RefPtr<BlobDataHandle> data) |
| 509 { | 545 { |
| 510 if (hasTerminatedPeer()) | 546 if (hasTerminatedPeer()) |
| 511 return WebSocketChannel::SendFail; | 547 return WebSocketChannel::SendFail; |
| 512 | 548 |
| 513 RefPtrWillBeRawPtr<Bridge> protect(this); | 549 RefPtrWillBeRawPtr<Bridge> protect(this); |
| 514 if (!waitForMethodCompletion(CallClosureTask::create(bind(&Peer::sendBlob, m
_peer, data)))) | 550 // It is important to seprate task creation from calling |
| 551 // waitForMethodCompletion. See the above comment. |
| 552 OwnPtr<ExecutionContextTask> task = CallClosureTask::create(bind(&Peer::send
Blob, m_peer, data)); |
| 553 if (!waitForMethodCompletion(task.release())) |
| 515 return WebSocketChannel::SendFail; | 554 return WebSocketChannel::SendFail; |
| 516 | 555 |
| 517 return m_syncHelper->sendRequestResult(); | 556 return m_syncHelper->sendRequestResult(); |
| 518 } | 557 } |
| 519 | 558 |
| 520 void WorkerThreadableWebSocketChannel::Bridge::close(int code, const String& rea
son) | 559 void WorkerThreadableWebSocketChannel::Bridge::close(int code, const String& rea
son) |
| 521 { | 560 { |
| 522 if (hasTerminatedPeer()) | 561 if (hasTerminatedPeer()) |
| 523 return; | 562 return; |
| 524 | 563 |
| 525 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::close, m_
peer, code, reason.isolatedCopy()))); | 564 // It is important to seprate task creation from calling |
| 565 // waitForMethodCompletion. See the above comment. |
| 566 OwnPtr<ExecutionContextTask> task = CallClosureTask::create(bind(&Peer::clos
e, m_peer, code, reason.isolatedCopy())); |
| 567 m_loaderProxy.postTaskToLoader(task.release()); |
| 526 } | 568 } |
| 527 | 569 |
| 528 void WorkerThreadableWebSocketChannel::Bridge::fail(const String& reason, Messag
eLevel level, const String& sourceURL, unsigned lineNumber) | 570 void WorkerThreadableWebSocketChannel::Bridge::fail(const String& reason, Messag
eLevel level, const String& sourceURL, unsigned lineNumber) |
| 529 { | 571 { |
| 530 if (hasTerminatedPeer()) | 572 if (hasTerminatedPeer()) |
| 531 return; | 573 return; |
| 532 | 574 |
| 533 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::fail, m_p
eer, reason.isolatedCopy(), level, sourceURL.isolatedCopy(), lineNumber))); | 575 // It is important to seprate task creation from calling |
| 576 // waitForMethodCompletion. See the above comment. |
| 577 OwnPtr<ExecutionContextTask> task = CallClosureTask::create(bind(&Peer::fail
, m_peer, reason.isolatedCopy(), level, sourceURL.isolatedCopy(), lineNumber)); |
| 578 m_loaderProxy.postTaskToLoader(task.release()); |
| 534 } | 579 } |
| 535 | 580 |
| 536 void WorkerThreadableWebSocketChannel::Bridge::disconnect() | 581 void WorkerThreadableWebSocketChannel::Bridge::disconnect() |
| 537 { | 582 { |
| 538 if (hasTerminatedPeer()) | 583 if (hasTerminatedPeer()) |
| 539 return; | 584 return; |
| 540 | 585 |
| 541 clearClientWrapper(); | 586 clearClientWrapper(); |
| 542 terminatePeer(); | 587 terminatePeer(); |
| 543 } | 588 } |
| (...skipping 18 matching lines...) Expand all Loading... |
| 562 events.append(m_syncHelper->event()); | 607 events.append(m_syncHelper->event()); |
| 563 ThreadState::SafePointScope scope(ThreadState::HeapPointersOnStack); | 608 ThreadState::SafePointScope scope(ThreadState::HeapPointersOnStack); |
| 564 blink::Platform::current()->waitMultipleEvents(events); | 609 blink::Platform::current()->waitMultipleEvents(events); |
| 565 // This is checking whether a shutdown event is fired or not. | 610 // This is checking whether a shutdown event is fired or not. |
| 566 return !m_workerGlobalScope->thread()->runLoop().terminated(); | 611 return !m_workerGlobalScope->thread()->runLoop().terminated(); |
| 567 } | 612 } |
| 568 | 613 |
| 569 void WorkerThreadableWebSocketChannel::Bridge::terminatePeer() | 614 void WorkerThreadableWebSocketChannel::Bridge::terminatePeer() |
| 570 { | 615 { |
| 571 ASSERT(!hasTerminatedPeer()); | 616 ASSERT(!hasTerminatedPeer()); |
| 617 |
| 618 // It is important to seprate task creation from calling |
| 619 // waitForMethodCompletion. See the above comment. |
| 620 OwnPtr<ExecutionContextTask> task = CallClosureTask::create(bind(&Peer::dest
roy, m_peer)); |
| 572 #if ENABLE(OILPAN) | 621 #if ENABLE(OILPAN) |
| 573 // The worker thread has to wait for the main thread to complete Peer::destr
oy, | 622 // The worker thread has to wait for the main thread to complete Peer::destr
oy, |
| 574 // because the worker thread has to make sure that the main thread does not
have any | 623 // because the worker thread has to make sure that the main thread does not
have any |
| 575 // references to on-heap objects allocated in the thread heap of the worker
thread | 624 // references to on-heap objects allocated in the thread heap of the worker
thread |
| 576 // before the worker thread shuts down. | 625 // before the worker thread shuts down. |
| 577 waitForMethodCompletion(CallClosureTask::create(bind(&Peer::destroy, m_peer)
)); | 626 waitForMethodCompletion(task.release()); |
| 578 #else | 627 #else |
| 579 m_loaderProxy.postTaskToLoader(CallClosureTask::create(bind(&Peer::destroy,
m_peer))); | 628 m_loaderProxy.postTaskToLoader(task.release()); |
| 580 #endif | 629 #endif |
| 581 | 630 |
| 582 // Peer::destroy() deletes m_peer and then m_syncHelper will be released. | 631 // Peer::destroy() deletes m_peer and then m_syncHelper will be released. |
| 583 // We must not touch m_syncHelper any more. | 632 // We must not touch m_syncHelper any more. |
| 584 m_syncHelper = nullptr; | 633 m_syncHelper = nullptr; |
| 585 | 634 |
| 586 // We won't use this any more. | 635 // We won't use this any more. |
| 587 m_workerGlobalScope = nullptr; | 636 m_workerGlobalScope = nullptr; |
| 588 } | 637 } |
| 589 | 638 |
| 590 void WorkerThreadableWebSocketChannel::Bridge::trace(Visitor* visitor) | 639 void WorkerThreadableWebSocketChannel::Bridge::trace(Visitor* visitor) |
| 591 { | 640 { |
| 592 visitor->trace(m_workerClientWrapper); | 641 visitor->trace(m_workerClientWrapper); |
| 593 visitor->trace(m_workerGlobalScope); | 642 visitor->trace(m_workerGlobalScope); |
| 594 visitor->trace(m_syncHelper); | 643 visitor->trace(m_syncHelper); |
| 595 visitor->trace(m_peer); | 644 visitor->trace(m_peer); |
| 596 } | 645 } |
| 597 | 646 |
| 598 } // namespace WebCore | 647 } // namespace WebCore |
| OLD | NEW |