Chromium Code Reviews| Index: ppapi/proxy/tcp_socket_resource_base.cc |
| diff --git a/ppapi/shared_impl/tcp_socket_shared.cc b/ppapi/proxy/tcp_socket_resource_base.cc |
| similarity index 58% |
| rename from ppapi/shared_impl/tcp_socket_shared.cc |
| rename to ppapi/proxy/tcp_socket_resource_base.cc |
| index ae23b28f4261fe0a5de62bb7f6700cf6b6ab35fc..d3e1cdcbad2f05106458213a634ae1c7f5e374c5 100644 |
| --- a/ppapi/shared_impl/tcp_socket_shared.cc |
| +++ b/ppapi/proxy/tcp_socket_resource_base.cc |
| @@ -2,149 +2,67 @@ |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| -#include "ppapi/shared_impl/tcp_socket_shared.h" |
| +#include "ppapi/proxy/tcp_socket_resource_base.h" |
| -#include <string.h> |
| +#include <cstring> |
| -#include <algorithm> |
| - |
| -#include "base/basictypes.h" |
| -#include "base/bind.h" |
|
yzshen1
2013/08/16 20:40:42
Things like bind, logging are still needed, right?
ygorshenin1
2013/08/19 14:33:35
Done.
|
| -#include "base/logging.h" |
| -#include "ppapi/c/pp_bool.h" |
| -#include "ppapi/c/pp_completion_callback.h" |
| #include "ppapi/c/pp_errors.h" |
| -#include "ppapi/shared_impl/ppapi_globals.h" |
| +#include "ppapi/proxy/pp_utils.h" |
| +#include "ppapi/proxy/ppapi_messages.h" |
| #include "ppapi/shared_impl/private/ppb_x509_certificate_private_shared.h" |
| #include "ppapi/shared_impl/socket_option_data.h" |
| -#include "ppapi/shared_impl/var_tracker.h" |
| #include "ppapi/shared_impl/var.h" |
| +#include "ppapi/shared_impl/var_tracker.h" |
| #include "ppapi/thunk/enter.h" |
| -#include "ppapi/thunk/ppb_x509_certificate_private_api.h" |
| namespace ppapi { |
| - |
| -const int32_t TCPSocketShared::kMaxReadSize = 1024 * 1024; |
| -const int32_t TCPSocketShared::kMaxWriteSize = 1024 * 1024; |
| -const int32_t TCPSocketShared::kMaxSendBufferSize = |
| - 1024 * TCPSocketShared::kMaxWriteSize; |
| -const int32_t TCPSocketShared::kMaxReceiveBufferSize = |
| - 1024 * TCPSocketShared::kMaxReadSize; |
| - |
| -TCPSocketShared::TCPSocketShared(ResourceObjectType resource_type, |
| - uint32 socket_id) |
| - : resource_type_(resource_type) { |
| - Init(socket_id); |
| -} |
| - |
| -TCPSocketShared::~TCPSocketShared() { |
| +namespace proxy { |
| + |
| +const int32_t TCPSocketResourceBase::kMaxReadSize = 1024 * 1024; |
| +const int32_t TCPSocketResourceBase::kMaxWriteSize = 1024 * 1024; |
| +const int32_t TCPSocketResourceBase::kMaxSendBufferSize = |
| + 1024 * TCPSocketResourceBase::kMaxWriteSize; |
| +const int32_t TCPSocketResourceBase::kMaxReceiveBufferSize = |
| + 1024 * TCPSocketResourceBase::kMaxReadSize; |
| + |
| +TCPSocketResourceBase::TCPSocketResourceBase(Connection connection, |
| + PP_Instance instance, |
| + bool private_api) |
| + : PluginResource(connection, instance), |
| + connection_state_(BEFORE_CONNECT), |
| + read_buffer_(NULL), |
| + bytes_to_read_(-1), |
| + private_api_(private_api) { |
| + local_addr_.size = 0; |
| + memset(local_addr_.data, 0, |
| + arraysize(local_addr_.data) * sizeof(*local_addr_.data)); |
| + remote_addr_.size = 0; |
| + memset(remote_addr_.data, 0, |
| + arraysize(remote_addr_.data) * sizeof(*remote_addr_.data)); |
| } |
| -void TCPSocketShared::OnConnectCompleted( |
| - int32_t result, |
| +TCPSocketResourceBase::TCPSocketResourceBase( |
| + Connection connection, |
| + PP_Instance instance, |
| + bool private_api, |
| const PP_NetAddress_Private& local_addr, |
| - const PP_NetAddress_Private& remote_addr) { |
| - // It is possible that |connect_callback_| is pending while |
| - // |connection_state_| is not BEFORE_CONNECT: DisconnectImpl() has been |
| - // called, but a ConnectCompleted notification came earlier than the task to |
| - // abort |connect_callback_|. We don't want to update |connection_state_| or |
| - // other members in that case. |
| - if (connection_state_ != BEFORE_CONNECT || |
| - !TrackedCallback::IsPending(connect_callback_)) { |
| - return; |
| - } |
| - |
| - result = OverridePPError(result); |
| - if (result == PP_OK) { |
| - local_addr_ = local_addr; |
| - remote_addr_ = remote_addr; |
| - connection_state_ = CONNECTED; |
| - } |
| - connect_callback_->Run(result); |
| + const PP_NetAddress_Private& remote_addr) |
| + : PluginResource(connection, instance), |
| + connection_state_(CONNECTED), |
| + read_buffer_(NULL), |
| + bytes_to_read_(-1), |
| + private_api_(private_api) { |
| + local_addr_ = local_addr_; |
|
yzshen1
2013/08/16 20:40:42
You used the wrong variable name. Besides, you cou
ygorshenin1
2013/08/19 14:33:35
Done. Tests for TCPServerSocket handle this now.
|
| + remote_addr_ = remote_addr_; |
|
yzshen1
2013/08/16 20:40:42
You used the wrong variable name.
ygorshenin1
2013/08/19 14:33:35
Done.
|
| } |
| -void TCPSocketShared::OnSSLHandshakeCompleted( |
| - bool succeeded, |
| - const PPB_X509Certificate_Fields& certificate_fields) { |
| - // It is possible that |ssl_handshake_callback_| is pending while |
| - // |connection_state_| is not CONNECT: DisconnectImpl() has been |
| - // called, but a SSLHandshakeCompleted notification came earlier than the task |
| - // to abort |ssl_handshake_callback_|. We don't want to update |
| - // |connection_state_| or other members in that case. |
| - if (connection_state_ != CONNECTED || |
| - !TrackedCallback::IsPending(ssl_handshake_callback_)) { |
| - return; |
| - } |
| - |
| - if (succeeded) { |
| - connection_state_ = SSL_CONNECTED; |
| - server_certificate_ = new PPB_X509Certificate_Private_Shared( |
| - resource_type_, |
| - GetOwnerResource()->pp_instance(), |
| - certificate_fields); |
| - ssl_handshake_callback_->Run(PP_OK); |
| - } else { |
| - // The resource might be released in the callback so we need to hold |
| - // a reference so we can Disconnect() first. |
| - GetOwnerResource()->AddRef(); |
| - ssl_handshake_callback_->Run(PP_ERROR_FAILED); |
| - DisconnectImpl(); |
| - GetOwnerResource()->Release(); |
| - } |
| -} |
| - |
| -void TCPSocketShared::OnReadCompleted(int32_t result, |
| - const std::string& data) { |
| - // It is possible that |read_callback_| is pending while |read_buffer_| is |
| - // NULL: DisconnectImpl() has been called, but a ReadCompleted notification |
| - // came earlier than the task to abort |read_callback_|. We shouldn't access |
| - // the buffer in that case. The user may have released it. |
| - if (!TrackedCallback::IsPending(read_callback_) || !read_buffer_) |
| - return; |
| - |
| - result = OverridePPError(result); |
| - bool succeeded = result == PP_OK; |
| - if (succeeded) { |
| - CHECK_LE(static_cast<int32_t>(data.size()), bytes_to_read_); |
| - if (!data.empty()) |
| - memcpy(read_buffer_, data.c_str(), data.size()); |
| - } |
| - read_buffer_ = NULL; |
| - bytes_to_read_ = -1; |
| - |
| - read_callback_->Run( |
| - succeeded ? static_cast<int32_t>(data.size()) : result); |
| -} |
| - |
| -void TCPSocketShared::OnWriteCompleted(int32_t result) { |
| - if (!TrackedCallback::IsPending(write_callback_)) |
| - return; |
| - |
| - result = OverridePPError(result); |
| - write_callback_->Run(result); |
| +TCPSocketResourceBase::~TCPSocketResourceBase() { |
| } |
| -void TCPSocketShared::OnSetOptionCompleted(int32_t result) { |
| - if (set_option_callbacks_.empty()) { |
| - NOTREACHED(); |
| - return; |
| - } |
| - |
| - result = OverridePPError(result); |
| - scoped_refptr<TrackedCallback> callback = set_option_callbacks_.front(); |
| - set_option_callbacks_.pop(); |
| - |
| - if (TrackedCallback::IsPending(callback)) |
| - callback->Run(result); |
| -} |
| - |
| -int32_t TCPSocketShared::OverridePPError(int32_t pp_error) { |
| - return pp_error; |
| -} |
| - |
| -int32_t TCPSocketShared::ConnectImpl(const char* host, |
| - uint16_t port, |
| - scoped_refptr<TrackedCallback> callback) { |
| +int32_t TCPSocketResourceBase::ConnectImpl( |
| + const char* host, |
| + uint16_t port, |
| + scoped_refptr<TrackedCallback> callback) { |
| if (!host) |
| return PP_ERROR_BADARGUMENT; |
| if (connection_state_ != BEFORE_CONNECT) |
| @@ -153,12 +71,16 @@ int32_t TCPSocketShared::ConnectImpl(const char* host, |
| return PP_ERROR_INPROGRESS; // Can only have one pending request. |
| connect_callback_ = callback; |
| - // Send the request, the browser will call us back via ConnectACK. |
| - SendConnect(host, port); |
| + |
| + Call<PpapiPluginMsg_TCPSocket_ConnectReply>( |
| + BROWSER, |
| + PpapiHostMsg_TCPSocket_Connect(host, port), |
| + base::Bind(&TCPSocketResourceBase::OnPluginMsgConnectReply, |
| + base::Unretained(this))); |
| return PP_OK_COMPLETIONPENDING; |
| } |
| -int32_t TCPSocketShared::ConnectWithNetAddressImpl( |
| +int32_t TCPSocketResourceBase::ConnectWithNetAddressImpl( |
| const PP_NetAddress_Private* addr, |
| scoped_refptr<TrackedCallback> callback) { |
| if (!addr) |
| @@ -169,30 +91,32 @@ int32_t TCPSocketShared::ConnectWithNetAddressImpl( |
| return PP_ERROR_INPROGRESS; // Can only have one pending request. |
| connect_callback_ = callback; |
| - // Send the request, the browser will call us back via ConnectACK. |
| - SendConnectWithNetAddress(*addr); |
| + |
| + Call<PpapiPluginMsg_TCPSocket_ConnectReply>( |
| + BROWSER, |
| + PpapiHostMsg_TCPSocket_ConnectWithNetAddress(*addr), |
| + base::Bind(&TCPSocketResourceBase::OnPluginMsgConnectReply, |
| + base::Unretained(this))); |
| return PP_OK_COMPLETIONPENDING; |
| } |
| -PP_Bool TCPSocketShared::GetLocalAddressImpl( |
| +PP_Bool TCPSocketResourceBase::GetLocalAddressImpl( |
| PP_NetAddress_Private* local_addr) { |
| if (!IsConnected() || !local_addr) |
| return PP_FALSE; |
| - |
| *local_addr = local_addr_; |
| return PP_TRUE; |
| } |
| -PP_Bool TCPSocketShared::GetRemoteAddressImpl( |
| +PP_Bool TCPSocketResourceBase::GetRemoteAddressImpl( |
| PP_NetAddress_Private* remote_addr) { |
| if (!IsConnected() || !remote_addr) |
| return PP_FALSE; |
| - |
| *remote_addr = remote_addr_; |
| return PP_TRUE; |
| } |
| -int32_t TCPSocketShared::SSLHandshakeImpl( |
| +int32_t TCPSocketResourceBase::SSLHandshakeImpl( |
| const char* server_name, |
| uint16_t server_port, |
| scoped_refptr<TrackedCallback> callback) { |
| @@ -203,24 +127,30 @@ int32_t TCPSocketShared::SSLHandshakeImpl( |
| return PP_ERROR_FAILED; |
| if (TrackedCallback::IsPending(ssl_handshake_callback_) || |
| TrackedCallback::IsPending(read_callback_) || |
| - TrackedCallback::IsPending(write_callback_)) |
| + TrackedCallback::IsPending(write_callback_)) { |
| return PP_ERROR_INPROGRESS; |
| + } |
| ssl_handshake_callback_ = callback; |
| - // Send the request, the browser will call us back via SSLHandshakeACK. |
| - SendSSLHandshake(server_name, server_port, trusted_certificates_, |
| - untrusted_certificates_); |
| + Call<PpapiPluginMsg_TCPSocket_SSLHandshakeReply>( |
| + BROWSER, |
| + PpapiHostMsg_TCPSocket_SSLHandshake(server_name, |
| + server_port, |
| + trusted_certificates_, |
| + untrusted_certificates_), |
| + base::Bind(&TCPSocketResourceBase::OnPluginMsgSSLHandshakeReply, |
| + base::Unretained(this))); |
| return PP_OK_COMPLETIONPENDING; |
| } |
| -PP_Resource TCPSocketShared::GetServerCertificateImpl() { |
| +PP_Resource TCPSocketResourceBase::GetServerCertificateImpl() { |
| if (!server_certificate_.get()) |
| return 0; |
| return server_certificate_->GetReference(); |
| } |
| -PP_Bool TCPSocketShared::AddChainBuildingCertificateImpl( |
| +PP_Bool TCPSocketResourceBase::AddChainBuildingCertificateImpl( |
| PP_Resource certificate, |
| PP_Bool trusted) { |
| // TODO(raymes): The plumbing for this functionality is implemented but the |
| @@ -251,9 +181,10 @@ PP_Bool TCPSocketShared::AddChainBuildingCertificateImpl( |
| return success; |
| } |
| -int32_t TCPSocketShared::ReadImpl(char* buffer, |
| - int32_t bytes_to_read, |
| - scoped_refptr<TrackedCallback> callback) { |
| +int32_t TCPSocketResourceBase::ReadImpl( |
| + char* buffer, |
| + int32_t bytes_to_read, |
| + scoped_refptr<TrackedCallback> callback) { |
| if (!buffer || bytes_to_read <= 0) |
| return PP_ERROR_BADARGUMENT; |
| @@ -266,14 +197,18 @@ int32_t TCPSocketShared::ReadImpl(char* buffer, |
| bytes_to_read_ = std::min(bytes_to_read, kMaxReadSize); |
| read_callback_ = callback; |
| - // Send the request, the browser will call us back via ReadACK. |
| - SendRead(bytes_to_read_); |
| + Call<PpapiPluginMsg_TCPSocket_ReadReply>( |
| + BROWSER, |
| + PpapiHostMsg_TCPSocket_Read(bytes_to_read), |
|
yzshen1
2013/08/16 20:40:42
you used the wrong variable name.
ygorshenin1
2013/08/19 14:33:35
Done, now test for TCPSocketPrivate handles this.
|
| + base::Bind(&TCPSocketResourceBase::OnPluginMsgReadReply, |
| + base::Unretained(this))); |
| return PP_OK_COMPLETIONPENDING; |
| } |
| -int32_t TCPSocketShared::WriteImpl(const char* buffer, |
| - int32_t bytes_to_write, |
| - scoped_refptr<TrackedCallback> callback) { |
| +int32_t TCPSocketResourceBase::WriteImpl( |
| + const char* buffer, |
| + int32_t bytes_to_write, |
| + scoped_refptr<TrackedCallback> callback) { |
| if (!buffer || bytes_to_write <= 0) |
| return PP_ERROR_BADARGUMENT; |
| @@ -288,19 +223,21 @@ int32_t TCPSocketShared::WriteImpl(const char* buffer, |
| write_callback_ = callback; |
| - // Send the request, the browser will call us back via WriteACK. |
| - SendWrite(std::string(buffer, bytes_to_write)); |
| + Call<PpapiPluginMsg_TCPSocket_WriteReply>( |
| + BROWSER, |
| + PpapiHostMsg_TCPSocket_Write(std::string(buffer, bytes_to_write)), |
| + base::Bind(&TCPSocketResourceBase::OnPluginMsgWriteReply, |
| + base::Unretained(this))); |
| return PP_OK_COMPLETIONPENDING; |
| } |
| -void TCPSocketShared::DisconnectImpl() { |
| +void TCPSocketResourceBase::DisconnectImpl() { |
| if (connection_state_ == DISCONNECTED) |
| return; |
| connection_state_ = DISCONNECTED; |
| - SendDisconnect(); |
| - socket_id_ = 0; |
| + Post(BROWSER, PpapiHostMsg_TCPSocket_Disconnect()); |
| PostAbortIfNecessary(&connect_callback_); |
| PostAbortIfNecessary(&ssl_handshake_callback_); |
| @@ -311,7 +248,7 @@ void TCPSocketShared::DisconnectImpl() { |
| server_certificate_ = NULL; |
| } |
| -int32_t TCPSocketShared::SetOptionImpl( |
| +int32_t TCPSocketResourceBase::SetOptionImpl( |
| PP_TCPSocket_Option name, |
| const PP_Var& value, |
| scoped_refptr<TrackedCallback> callback) { |
| @@ -340,33 +277,125 @@ int32_t TCPSocketShared::SetOptionImpl( |
| } |
| set_option_callbacks_.push(callback); |
| - SendSetOption(name, option_data); |
| + |
| + Call<PpapiPluginMsg_TCPSocket_SetOptionReply>( |
| + BROWSER, |
| + PpapiHostMsg_TCPSocket_SetOption(name, option_data), |
| + base::Bind(&TCPSocketResourceBase::OnPluginMsgSetOptionReply, |
| + base::Unretained(this))); |
| return PP_OK_COMPLETIONPENDING; |
| } |
| -void TCPSocketShared::Init(uint32 socket_id) { |
| - DCHECK(socket_id != 0); |
| - socket_id_ = socket_id; |
| - connection_state_ = BEFORE_CONNECT; |
| +bool TCPSocketResourceBase::IsConnected() const { |
| + return connection_state_ == CONNECTED || connection_state_ == SSL_CONNECTED; |
| +} |
| + |
| +void TCPSocketResourceBase::PostAbortIfNecessary( |
| + scoped_refptr<TrackedCallback>* callback) { |
| + if (TrackedCallback::IsPending(*callback)) |
| + (*callback)->PostAbort(); |
| +} |
| + |
| +void TCPSocketResourceBase::OnPluginMsgConnectReply( |
| + const ResourceMessageReplyParams& params, |
| + const PP_NetAddress_Private& local_addr, |
| + const PP_NetAddress_Private& remote_addr) { |
| + // It is possible that |connect_callback_| is pending while |
| + // |connection_state_| is not BEFORE_CONNECT: DisconnectImpl() has been |
| + // called, but a ConnectCompleted notification came earlier than the task to |
| + // abort |connect_callback_|. We don't want to update |connection_state_| or |
| + // other members in that case. |
| + if (connection_state_ != BEFORE_CONNECT || |
| + !TrackedCallback::IsPending(connect_callback_)) { |
| + return; |
| + } |
| + |
| + if (params.result() == PP_OK) { |
| + local_addr_ = local_addr; |
| + remote_addr_ = remote_addr; |
| + connection_state_ = CONNECTED; |
| + } |
| + RunCallback(connect_callback_, params.result()); |
| +} |
| + |
| +void TCPSocketResourceBase::OnPluginMsgSSLHandshakeReply( |
| + const ResourceMessageReplyParams& params, |
| + const PPB_X509Certificate_Fields& certificate_fields) { |
| + // It is possible that |ssl_handshake_callback_| is pending while |
|
yzshen1
2013/08/16 20:40:42
wrong indent.
ygorshenin1
2013/08/19 14:33:35
Done.
|
| + // |connection_state_| is not CONNECT: DisconnectImpl() has been |
| + // called, but a SSLHandshakeCompleted notification came earlier than the task |
| + // to abort |ssl_handshake_callback_|. We don't want to update |
| + // |connection_state_| or other members in that case. |
| + if (connection_state_ != CONNECTED || |
| + !TrackedCallback::IsPending(ssl_handshake_callback_)) { |
| + return; |
| + } |
| + |
| + if (params.result() == PP_OK) { |
| + connection_state_ = SSL_CONNECTED; |
| + server_certificate_ = new PPB_X509Certificate_Private_Shared( |
| + OBJECT_IS_PROXY, |
| + pp_instance(), |
| + certificate_fields); |
| + RunCallback(ssl_handshake_callback_, params.result()); |
| + } else { |
| + // The resource might be released in the callback so we need to hold |
| + // a reference so we can Disconnect() first. |
| + AddRef(); |
| + RunCallback(ssl_handshake_callback_, params.result()); |
| + DisconnectImpl(); |
| + Release(); |
| + } |
| +} |
| + |
| +void TCPSocketResourceBase::OnPluginMsgReadReply( |
| + const ResourceMessageReplyParams& params, |
| + const std::string& data) { |
| + // It is possible that |read_callback_| is pending while |read_buffer_| is |
| + // NULL: DisconnectImpl() has been called, but a ReadCompleted notification |
| + // came earlier than the task to abort |read_callback_|. We shouldn't access |
| + // the buffer in that case. The user may have released it. |
| + if (!TrackedCallback::IsPending(read_callback_) || !read_buffer_) |
| + return; |
| + |
| + const bool succeeded = params.result() == PP_OK; |
| + if (succeeded) { |
| + CHECK_LE(static_cast<int32_t>(data.size()), bytes_to_read_); |
| + if (!data.empty()) |
| + memcpy(read_buffer_, data.c_str(), data.size()); |
| + } |
| read_buffer_ = NULL; |
| bytes_to_read_ = -1; |
| - local_addr_.size = 0; |
| - memset(local_addr_.data, 0, |
| - arraysize(local_addr_.data) * sizeof(*local_addr_.data)); |
| - remote_addr_.size = 0; |
| - memset(remote_addr_.data, 0, |
| - arraysize(remote_addr_.data) * sizeof(*remote_addr_.data)); |
| + read_callback_->Run( |
| + succeeded ? |
| + static_cast<int32_t>(data.size()) : |
|
yzshen1
2013/08/16 20:40:42
four more spaces of indent, please.
ygorshenin1
2013/08/19 14:33:35
Done.
|
| + pp_utils::ConvertPPError(params.result(), private_api_)); |
| } |
| -bool TCPSocketShared::IsConnected() const { |
| - return connection_state_ == CONNECTED || connection_state_ == SSL_CONNECTED; |
| +void TCPSocketResourceBase::OnPluginMsgWriteReply( |
| + const ResourceMessageReplyParams& params) { |
| + if (!TrackedCallback::IsPending(write_callback_)) |
| + return; |
| + RunCallback(write_callback_, params.result()); |
| } |
| -void TCPSocketShared::PostAbortIfNecessary( |
| - scoped_refptr<TrackedCallback>* callback) { |
| - if (TrackedCallback::IsPending(*callback)) |
| - (*callback)->PostAbort(); |
| +void TCPSocketResourceBase::OnPluginMsgSetOptionReply( |
| + const ResourceMessageReplyParams& params) { |
| + if (set_option_callbacks_.empty()) { |
| + NOTREACHED(); |
| + return; |
| + } |
| + scoped_refptr<TrackedCallback> callback = set_option_callbacks_.front(); |
| + set_option_callbacks_.pop(); |
| + if (TrackedCallback::IsPending(callback)) |
| + RunCallback(callback, params.result()); |
| +} |
| + |
| +void TCPSocketResourceBase::RunCallback(scoped_refptr<TrackedCallback> callback, |
| + int32_t pp_result) { |
| + callback->Run(pp_utils::ConvertPPError(pp_result, private_api_)); |
| } |
| } // namespace ppapi |
| +} // namespace proxy |