| 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 164 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 175 m_bridge->disconnect(); | 175 m_bridge->disconnect(); |
| 176 m_bridge.clear(); | 176 m_bridge.clear(); |
| 177 } | 177 } |
| 178 | 178 |
| 179 void WorkerWebSocketChannel::trace(Visitor* visitor) | 179 void WorkerWebSocketChannel::trace(Visitor* visitor) |
| 180 { | 180 { |
| 181 visitor->trace(m_bridge); | 181 visitor->trace(m_bridge); |
| 182 WebSocketChannel::trace(visitor); | 182 WebSocketChannel::trace(visitor); |
| 183 } | 183 } |
| 184 | 184 |
| 185 Peer::Peer(Bridge* bridge, WorkerLoaderProxy& loaderProxy, WebSocketChannelSyncH
elper* syncHelper) | 185 Peer::Peer(Bridge* bridge, PassRefPtr<WorkerLoaderProxy> loaderProxy, WebSocketC
hannelSyncHelper* syncHelper) |
| 186 : m_bridge(bridge) | 186 : m_bridge(bridge) |
| 187 , m_loaderProxy(loaderProxy) | 187 , m_loaderProxy(loaderProxy) |
| 188 , m_mainWebSocketChannel(nullptr) | 188 , m_mainWebSocketChannel(nullptr) |
| 189 , m_syncHelper(syncHelper) | 189 , m_syncHelper(syncHelper) |
| 190 { | 190 { |
| 191 ASSERT(!isMainThread()); | 191 ASSERT(!isMainThread()); |
| 192 } | 192 } |
| 193 | 193 |
| 194 Peer::~Peer() | 194 Peer::~Peer() |
| 195 { | 195 { |
| (...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 270 static void workerGlobalScopeDidConnect(ExecutionContext* context, Bridge* bridg
e, const String& subprotocol, const String& extensions) | 270 static void workerGlobalScopeDidConnect(ExecutionContext* context, Bridge* bridg
e, const String& subprotocol, const String& extensions) |
| 271 { | 271 { |
| 272 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 272 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 273 if (bridge->client()) | 273 if (bridge->client()) |
| 274 bridge->client()->didConnect(subprotocol, extensions); | 274 bridge->client()->didConnect(subprotocol, extensions); |
| 275 } | 275 } |
| 276 | 276 |
| 277 void Peer::didConnect(const String& subprotocol, const String& extensions) | 277 void Peer::didConnect(const String& subprotocol, const String& extensions) |
| 278 { | 278 { |
| 279 ASSERT(isMainThread()); | 279 ASSERT(isMainThread()); |
| 280 m_loaderProxy.postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGloba
lScopeDidConnect, m_bridge, subprotocol, extensions)); | 280 m_loaderProxy->postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGlob
alScopeDidConnect, m_bridge, subprotocol, extensions)); |
| 281 } | 281 } |
| 282 | 282 |
| 283 static void workerGlobalScopeDidReceiveTextMessage(ExecutionContext* context, Br
idge* bridge, const String& payload) | 283 static void workerGlobalScopeDidReceiveTextMessage(ExecutionContext* context, Br
idge* bridge, const String& payload) |
| 284 { | 284 { |
| 285 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 285 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 286 if (bridge->client()) | 286 if (bridge->client()) |
| 287 bridge->client()->didReceiveTextMessage(payload); | 287 bridge->client()->didReceiveTextMessage(payload); |
| 288 } | 288 } |
| 289 | 289 |
| 290 void Peer::didReceiveTextMessage(const String& payload) | 290 void Peer::didReceiveTextMessage(const String& payload) |
| 291 { | 291 { |
| 292 ASSERT(isMainThread()); | 292 ASSERT(isMainThread()); |
| 293 m_loaderProxy.postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGloba
lScopeDidReceiveTextMessage, m_bridge, payload)); | 293 m_loaderProxy->postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGlob
alScopeDidReceiveTextMessage, m_bridge, payload)); |
| 294 } | 294 } |
| 295 | 295 |
| 296 static void workerGlobalScopeDidReceiveBinaryMessage(ExecutionContext* context,
Bridge* bridge, PassOwnPtr<Vector<char>> payload) | 296 static void workerGlobalScopeDidReceiveBinaryMessage(ExecutionContext* context,
Bridge* bridge, PassOwnPtr<Vector<char>> payload) |
| 297 { | 297 { |
| 298 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 298 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 299 if (bridge->client()) | 299 if (bridge->client()) |
| 300 bridge->client()->didReceiveBinaryMessage(payload); | 300 bridge->client()->didReceiveBinaryMessage(payload); |
| 301 } | 301 } |
| 302 | 302 |
| 303 void Peer::didReceiveBinaryMessage(PassOwnPtr<Vector<char>> payload) | 303 void Peer::didReceiveBinaryMessage(PassOwnPtr<Vector<char>> payload) |
| 304 { | 304 { |
| 305 ASSERT(isMainThread()); | 305 ASSERT(isMainThread()); |
| 306 m_loaderProxy.postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGloba
lScopeDidReceiveBinaryMessage, m_bridge, payload)); | 306 m_loaderProxy->postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGlob
alScopeDidReceiveBinaryMessage, m_bridge, payload)); |
| 307 } | 307 } |
| 308 | 308 |
| 309 static void workerGlobalScopeDidConsumeBufferedAmount(ExecutionContext* context,
Bridge* bridge, uint64_t consumed) | 309 static void workerGlobalScopeDidConsumeBufferedAmount(ExecutionContext* context,
Bridge* bridge, uint64_t consumed) |
| 310 { | 310 { |
| 311 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 311 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 312 if (bridge->client()) | 312 if (bridge->client()) |
| 313 bridge->client()->didConsumeBufferedAmount(consumed); | 313 bridge->client()->didConsumeBufferedAmount(consumed); |
| 314 } | 314 } |
| 315 | 315 |
| 316 void Peer::didConsumeBufferedAmount(uint64_t consumed) | 316 void Peer::didConsumeBufferedAmount(uint64_t consumed) |
| 317 { | 317 { |
| 318 ASSERT(isMainThread()); | 318 ASSERT(isMainThread()); |
| 319 m_loaderProxy.postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGloba
lScopeDidConsumeBufferedAmount, m_bridge, consumed)); | 319 m_loaderProxy->postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGlob
alScopeDidConsumeBufferedAmount, m_bridge, consumed)); |
| 320 } | 320 } |
| 321 | 321 |
| 322 static void workerGlobalScopeDidStartClosingHandshake(ExecutionContext* context,
Bridge* bridge) | 322 static void workerGlobalScopeDidStartClosingHandshake(ExecutionContext* context,
Bridge* bridge) |
| 323 { | 323 { |
| 324 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 324 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 325 if (bridge->client()) | 325 if (bridge->client()) |
| 326 bridge->client()->didStartClosingHandshake(); | 326 bridge->client()->didStartClosingHandshake(); |
| 327 } | 327 } |
| 328 | 328 |
| 329 void Peer::didStartClosingHandshake() | 329 void Peer::didStartClosingHandshake() |
| 330 { | 330 { |
| 331 ASSERT(isMainThread()); | 331 ASSERT(isMainThread()); |
| 332 m_loaderProxy.postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGloba
lScopeDidStartClosingHandshake, m_bridge)); | 332 m_loaderProxy->postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGlob
alScopeDidStartClosingHandshake, m_bridge)); |
| 333 } | 333 } |
| 334 | 334 |
| 335 static void workerGlobalScopeDidClose(ExecutionContext* context, Bridge* bridge,
WebSocketChannelClient::ClosingHandshakeCompletionStatus closingHandshakeComple
tion, unsigned short code, const String& reason) | 335 static void workerGlobalScopeDidClose(ExecutionContext* context, Bridge* bridge,
WebSocketChannelClient::ClosingHandshakeCompletionStatus closingHandshakeComple
tion, unsigned short code, const String& reason) |
| 336 { | 336 { |
| 337 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 337 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 338 if (bridge->client()) | 338 if (bridge->client()) |
| 339 bridge->client()->didClose(closingHandshakeCompletion, code, reason); | 339 bridge->client()->didClose(closingHandshakeCompletion, code, reason); |
| 340 } | 340 } |
| 341 | 341 |
| 342 void Peer::didClose(ClosingHandshakeCompletionStatus closingHandshakeCompletion,
unsigned short code, const String& reason) | 342 void Peer::didClose(ClosingHandshakeCompletionStatus closingHandshakeCompletion,
unsigned short code, const String& reason) |
| 343 { | 343 { |
| 344 ASSERT(isMainThread()); | 344 ASSERT(isMainThread()); |
| 345 if (m_mainWebSocketChannel) { | 345 if (m_mainWebSocketChannel) { |
| 346 m_mainWebSocketChannel->disconnect(); | 346 m_mainWebSocketChannel->disconnect(); |
| 347 m_mainWebSocketChannel = nullptr; | 347 m_mainWebSocketChannel = nullptr; |
| 348 } | 348 } |
| 349 m_loaderProxy.postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGloba
lScopeDidClose, m_bridge, closingHandshakeCompletion, code, reason)); | 349 m_loaderProxy->postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGlob
alScopeDidClose, m_bridge, closingHandshakeCompletion, code, reason)); |
| 350 } | 350 } |
| 351 | 351 |
| 352 static void workerGlobalScopeDidError(ExecutionContext* context, Bridge* bridge) | 352 static void workerGlobalScopeDidError(ExecutionContext* context, Bridge* bridge) |
| 353 { | 353 { |
| 354 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); | 354 ASSERT_UNUSED(context, context->isWorkerGlobalScope()); |
| 355 if (bridge->client()) | 355 if (bridge->client()) |
| 356 bridge->client()->didError(); | 356 bridge->client()->didError(); |
| 357 } | 357 } |
| 358 | 358 |
| 359 void Peer::didError() | 359 void Peer::didError() |
| 360 { | 360 { |
| 361 ASSERT(isMainThread()); | 361 ASSERT(isMainThread()); |
| 362 m_loaderProxy.postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGloba
lScopeDidError, m_bridge)); | 362 m_loaderProxy->postTaskToWorkerGlobalScope(createCrossThreadTask(&workerGlob
alScopeDidError, m_bridge)); |
| 363 } | 363 } |
| 364 | 364 |
| 365 void Peer::trace(Visitor* visitor) | 365 void Peer::trace(Visitor* visitor) |
| 366 { | 366 { |
| 367 visitor->trace(m_bridge); | 367 visitor->trace(m_bridge); |
| 368 visitor->trace(m_mainWebSocketChannel); | 368 visitor->trace(m_mainWebSocketChannel); |
| 369 visitor->trace(m_syncHelper); | 369 visitor->trace(m_syncHelper); |
| 370 WebSocketChannelClient::trace(visitor); | 370 WebSocketChannelClient::trace(visitor); |
| 371 } | 371 } |
| 372 | 372 |
| (...skipping 26 matching lines...) Expand all Loading... |
| 399 | 399 |
| 400 if (!waitForMethodCompletion(createCrossThreadTask(&Peer::connect, m_peer.ge
t(), url, protocol))) | 400 if (!waitForMethodCompletion(createCrossThreadTask(&Peer::connect, m_peer.ge
t(), url, protocol))) |
| 401 return false; | 401 return false; |
| 402 | 402 |
| 403 return m_syncHelper->connectRequestResult(); | 403 return m_syncHelper->connectRequestResult(); |
| 404 } | 404 } |
| 405 | 405 |
| 406 void Bridge::send(const String& message) | 406 void Bridge::send(const String& message) |
| 407 { | 407 { |
| 408 ASSERT(m_peer); | 408 ASSERT(m_peer); |
| 409 m_loaderProxy.postTaskToLoader(createCrossThreadTask(&Peer::send, m_peer.get
(), message)); | 409 m_loaderProxy->postTaskToLoader(createCrossThreadTask(&Peer::send, m_peer.ge
t(), message)); |
| 410 } | 410 } |
| 411 | 411 |
| 412 void Bridge::send(const DOMArrayBuffer& binaryData, unsigned byteOffset, unsigne
d byteLength) | 412 void Bridge::send(const DOMArrayBuffer& binaryData, unsigned byteOffset, unsigne
d byteLength) |
| 413 { | 413 { |
| 414 ASSERT(m_peer); | 414 ASSERT(m_peer); |
| 415 // ArrayBuffer isn't thread-safe, hence the content of ArrayBuffer is copied
into Vector<char>. | 415 // ArrayBuffer isn't thread-safe, hence the content of ArrayBuffer is copied
into Vector<char>. |
| 416 OwnPtr<Vector<char>> data = adoptPtr(new Vector<char>(byteLength)); | 416 OwnPtr<Vector<char>> data = adoptPtr(new Vector<char>(byteLength)); |
| 417 if (binaryData.byteLength()) | 417 if (binaryData.byteLength()) |
| 418 memcpy(data->data(), static_cast<const char*>(binaryData.data()) + byteO
ffset, byteLength); | 418 memcpy(data->data(), static_cast<const char*>(binaryData.data()) + byteO
ffset, byteLength); |
| 419 | 419 |
| 420 m_loaderProxy.postTaskToLoader(createCrossThreadTask(&Peer::sendArrayBuffer,
m_peer.get(), data.release())); | 420 m_loaderProxy->postTaskToLoader(createCrossThreadTask(&Peer::sendArrayBuffer
, m_peer.get(), data.release())); |
| 421 } | 421 } |
| 422 | 422 |
| 423 void Bridge::send(PassRefPtr<BlobDataHandle> data) | 423 void Bridge::send(PassRefPtr<BlobDataHandle> data) |
| 424 { | 424 { |
| 425 ASSERT(m_peer); | 425 ASSERT(m_peer); |
| 426 m_loaderProxy.postTaskToLoader(createCrossThreadTask(&Peer::sendBlob, m_peer
.get(), data)); | 426 m_loaderProxy->postTaskToLoader(createCrossThreadTask(&Peer::sendBlob, m_pee
r.get(), data)); |
| 427 } | 427 } |
| 428 | 428 |
| 429 void Bridge::close(int code, const String& reason) | 429 void Bridge::close(int code, const String& reason) |
| 430 { | 430 { |
| 431 ASSERT(m_peer); | 431 ASSERT(m_peer); |
| 432 m_loaderProxy.postTaskToLoader(createCrossThreadTask(&Peer::close, m_peer.ge
t(), code, reason)); | 432 m_loaderProxy->postTaskToLoader(createCrossThreadTask(&Peer::close, m_peer.g
et(), code, reason)); |
| 433 } | 433 } |
| 434 | 434 |
| 435 void Bridge::fail(const String& reason, MessageLevel level, const String& source
URL, unsigned lineNumber) | 435 void Bridge::fail(const String& reason, MessageLevel level, const String& source
URL, unsigned lineNumber) |
| 436 { | 436 { |
| 437 ASSERT(m_peer); | 437 ASSERT(m_peer); |
| 438 m_loaderProxy.postTaskToLoader(createCrossThreadTask(&Peer::fail, m_peer.get
(), reason, level, sourceURL, lineNumber)); | 438 m_loaderProxy->postTaskToLoader(createCrossThreadTask(&Peer::fail, m_peer.ge
t(), reason, level, sourceURL, lineNumber)); |
| 439 } | 439 } |
| 440 | 440 |
| 441 void Bridge::disconnect() | 441 void Bridge::disconnect() |
| 442 { | 442 { |
| 443 if (!m_peer) | 443 if (!m_peer) |
| 444 return; | 444 return; |
| 445 | 445 |
| 446 waitForMethodCompletion(createCrossThreadTask(&Peer::disconnect, m_peer.get(
))); | 446 waitForMethodCompletion(createCrossThreadTask(&Peer::disconnect, m_peer.get(
))); |
| 447 // Here |m_peer| is detached from the main thread and we can delete it. | 447 // Here |m_peer| is detached from the main thread and we can delete it. |
| 448 | 448 |
| 449 m_client = nullptr; | 449 m_client = nullptr; |
| 450 m_peer = nullptr; | 450 m_peer = nullptr; |
| 451 m_syncHelper = nullptr; | 451 m_syncHelper = nullptr; |
| 452 // We won't use this any more. | 452 // We won't use this any more. |
| 453 m_workerGlobalScope.clear(); | 453 m_workerGlobalScope.clear(); |
| 454 } | 454 } |
| 455 | 455 |
| 456 // Caller of this function should hold a reference to the bridge, because this f
unction may call WebSocket::didClose() in the end, | 456 // Caller of this function should hold a reference to the bridge, because this f
unction may call WebSocket::didClose() in the end, |
| 457 // which causes the bridge to get disconnected from the WebSocket and deleted if
there is no other reference. | 457 // which causes the bridge to get disconnected from the WebSocket and deleted if
there is no other reference. |
| 458 bool Bridge::waitForMethodCompletion(PassOwnPtr<ExecutionContextTask> task) | 458 bool Bridge::waitForMethodCompletion(PassOwnPtr<ExecutionContextTask> task) |
| 459 { | 459 { |
| 460 ASSERT(m_workerGlobalScope); | 460 ASSERT(m_workerGlobalScope); |
| 461 ASSERT(m_syncHelper); | 461 ASSERT(m_syncHelper); |
| 462 | 462 |
| 463 m_loaderProxy.postTaskToLoader(task); | 463 m_loaderProxy->postTaskToLoader(task); |
| 464 | 464 |
| 465 // We wait for the syncHelper event even if a shutdown event is fired. | 465 // We wait for the syncHelper event even if a shutdown event is fired. |
| 466 // See https://codereview.chromium.org/267323004/#msg43 for why we need to w
ait this. | 466 // See https://codereview.chromium.org/267323004/#msg43 for why we need to w
ait this. |
| 467 ThreadState::SafePointScope scope(ThreadState::HeapPointersOnStack); | 467 ThreadState::SafePointScope scope(ThreadState::HeapPointersOnStack); |
| 468 m_syncHelper->wait(); | 468 m_syncHelper->wait(); |
| 469 // This is checking whether a shutdown event is fired or not. | 469 // This is checking whether a shutdown event is fired or not. |
| 470 return !m_workerGlobalScope->thread()->terminated(); | 470 return !m_workerGlobalScope->thread()->terminated(); |
| 471 } | 471 } |
| 472 | 472 |
| 473 void Bridge::trace(Visitor* visitor) | 473 void Bridge::trace(Visitor* visitor) |
| 474 { | 474 { |
| 475 visitor->trace(m_client); | 475 visitor->trace(m_client); |
| 476 visitor->trace(m_workerGlobalScope); | 476 visitor->trace(m_workerGlobalScope); |
| 477 visitor->trace(m_syncHelper); | 477 visitor->trace(m_syncHelper); |
| 478 visitor->trace(m_peer); | 478 visitor->trace(m_peer); |
| 479 } | 479 } |
| 480 | 480 |
| 481 } // namespace blink | 481 } // namespace blink |
| OLD | NEW |