Index: ppapi/proxy/tcp_server_socket_private_resource.cc |
diff --git a/ppapi/proxy/tcp_server_socket_private_resource.cc b/ppapi/proxy/tcp_server_socket_private_resource.cc |
new file mode 100644 |
index 0000000000000000000000000000000000000000..2456eb1baaf3025c63d1ce7fe73a50399f37bbaf |
--- /dev/null |
+++ b/ppapi/proxy/tcp_server_socket_private_resource.cc |
@@ -0,0 +1,140 @@ |
+// Copyright (c) 2013 The Chromium Authors. All rights reserved. |
+// Use of this source code is governed by a BSD-style license that can be |
+// found in the LICENSE file. |
+ |
+#include "ppapi/proxy/tcp_server_socket_private_resource.h" |
+ |
+#include "ppapi/proxy/plugin_dispatcher.h" |
+#include "ppapi/proxy/ppapi_messages.h" |
+#include "ppapi/proxy/ppb_tcp_socket_private_proxy.h" |
+ |
+namespace ppapi { |
+namespace proxy { |
+ |
+TCPServerSocketPrivateResource::TCPServerSocketPrivateResource( |
+ Connection connection, |
+ PP_Instance instance) |
+ : PluginResource(connection, instance), |
+ state_(STATE_BEFORE_LISTENING), |
+ local_addr_(), |
+ plugin_dispatcher_id_(0) { |
+ SendCreate(BROWSER, PpapiHostMsg_TCPServerSocket_CreatePrivate()); |
+ |
+ PluginDispatcher* dispatcher = PluginDispatcher::GetForInstance(instance); |
+ if (dispatcher) |
+ plugin_dispatcher_id_ = dispatcher->plugin_dispatcher_id(); |
+ else |
+ NOTREACHED(); |
+} |
+ |
+TCPServerSocketPrivateResource::~TCPServerSocketPrivateResource() { |
+} |
+ |
+thunk::PPB_TCPServerSocket_Private_API* |
+TCPServerSocketPrivateResource::AsPPB_TCPServerSocket_Private_API() { |
+ return this; |
+} |
+ |
+int32_t TCPServerSocketPrivateResource::Listen( |
+ const PP_NetAddress_Private* addr, |
+ int32_t backlog, |
+ scoped_refptr<TrackedCallback> callback) { |
+ if (!addr) |
+ return PP_ERROR_BADARGUMENT; |
+ if (state_ != STATE_BEFORE_LISTENING) |
+ return PP_ERROR_FAILED; |
+ if (TrackedCallback::IsPending(listen_callback_)) |
+ return PP_ERROR_INPROGRESS; |
+ |
+ listen_callback_ = callback; |
+ |
+ // Send the request, the browser will call us back via ListenACK |
+ Call<PpapiPluginMsg_TCPServerSocket_ListenReply>( |
+ BROWSER, |
+ PpapiHostMsg_TCPServerSocket_Listen(*addr, backlog), |
+ base::Bind(&TCPServerSocketPrivateResource::OnPluginMsgListenReply, |
+ base::Unretained(this))); |
+ return PP_OK_COMPLETIONPENDING; |
+} |
+ |
+int32_t TCPServerSocketPrivateResource::Accept( |
+ PP_Resource* tcp_socket, |
+ scoped_refptr<TrackedCallback> callback) { |
+ if (!tcp_socket) |
+ return PP_ERROR_BADARGUMENT; |
+ if (state_ != STATE_LISTENING) |
+ return PP_ERROR_FAILED; |
+ if (TrackedCallback::IsPending(accept_callback_)) |
+ return PP_ERROR_INPROGRESS; |
+ |
+ accept_callback_ = callback; |
+ |
+ Call<PpapiPluginMsg_TCPServerSocket_AcceptReply>( |
+ BROWSER, |
+ PpapiHostMsg_TCPServerSocket_Accept(plugin_dispatcher_id_), |
+ base::Bind(&TCPServerSocketPrivateResource::OnPluginMsgAcceptReply, |
+ base::Unretained(this), tcp_socket)); |
+ return PP_OK_COMPLETIONPENDING; |
+} |
+ |
+int32_t TCPServerSocketPrivateResource::GetLocalAddress( |
+ PP_NetAddress_Private* addr) { |
+ if (!addr) |
+ return PP_ERROR_BADARGUMENT; |
+ if (state_ != STATE_LISTENING) |
+ return PP_ERROR_FAILED; |
+ *addr = local_addr_; |
+ return PP_OK; |
+} |
+ |
+void TCPServerSocketPrivateResource::StopListening() { |
+ if (state_ == STATE_CLOSED) |
+ return; |
+ state_ = STATE_CLOSED; |
+ Post(BROWSER, PpapiHostMsg_TCPServerSocket_StopListening()); |
+ if (TrackedCallback::IsPending(listen_callback_)) |
+ listen_callback_->PostAbort(); |
+ if (TrackedCallback::IsPending(accept_callback_)) |
+ accept_callback_->PostAbort(); |
+} |
+ |
+void TCPServerSocketPrivateResource::OnPluginMsgListenReply( |
+ const ResourceMessageReplyParams& params, |
+ const PP_NetAddress_Private& local_addr) { |
+ if (state_ == STATE_CLOSED) |
yzshen1
2013/07/30 17:56:49
Nit: it seems to following is more robust:
if (sta
ygorshenin1
2013/07/31 11:09:30
Done.
|
+ return; |
+ DCHECK(state_ == STATE_BEFORE_LISTENING); |
+ DCHECK(TrackedCallback::IsPending(listen_callback_)); |
+ if (params.result() == PP_OK) { |
+ local_addr_ = local_addr; |
+ state_ = STATE_LISTENING; |
+ } else { |
+ state_ = STATE_BEFORE_LISTENING; |
+ } |
+ listen_callback_->Run(params.result()); |
+} |
+ |
+void TCPServerSocketPrivateResource::OnPluginMsgAcceptReply( |
+ PP_Resource* tcp_socket, |
+ const ResourceMessageReplyParams& params, |
+ uint32 accepted_socket_id, |
+ const PP_NetAddress_Private& local_addr, |
+ const PP_NetAddress_Private& remote_addr) { |
+ DCHECK(tcp_socket); |
+ if (state_ == STATE_CLOSED) |
yzshen1
2013/07/30 17:56:49
Nit: it seems to following is more robust:
if (sta
ygorshenin1
2013/07/31 11:09:30
Done.
|
+ return; |
+ DCHECK(state_ == STATE_LISTENING); |
+ DCHECK(TrackedCallback::IsPending(accept_callback_)); |
+ if (params.result() == PP_OK) { |
+ *tcp_socket = |
+ PPB_TCPSocket_Private_Proxy::CreateProxyResourceForConnectedSocket( |
+ pp_instance(), |
+ accepted_socket_id, |
+ local_addr, |
+ remote_addr); |
+ } |
+ accept_callback_->Run(params.result()); |
+} |
+ |
+} // namespace proxy |
+} // namespace ppapi |