1 // Copyright (c) 2012 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include "ppapi/cpp/private/tcp_socket_private.h"
6 
7 #include "ppapi/c/pp_bool.h"
8 #include "ppapi/c/pp_errors.h"
9 #include "ppapi/cpp/completion_callback.h"
10 #include "ppapi/cpp/instance_handle.h"
11 #include "ppapi/cpp/module.h"
12 #include "ppapi/cpp/module_impl.h"
13 
14 namespace pp {
15 
16 namespace {
17 
interface_name()18 template <> const char* interface_name<PPB_TCPSocket_Private_0_5>() {
19   return PPB_TCPSOCKET_PRIVATE_INTERFACE_0_5;
20 }
21 
interface_name()22 template <> const char* interface_name<PPB_TCPSocket_Private_0_4>() {
23   return PPB_TCPSOCKET_PRIVATE_INTERFACE_0_4;
24 }
25 
interface_name()26 template <> const char* interface_name<PPB_TCPSocket_Private_0_3>() {
27   return PPB_TCPSOCKET_PRIVATE_INTERFACE_0_3;
28 }
29 
30 }  // namespace
31 
TCPSocketPrivate(const InstanceHandle & instance)32 TCPSocketPrivate::TCPSocketPrivate(const InstanceHandle& instance) {
33   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
34     PassRefFromConstructor(get_interface<PPB_TCPSocket_Private_0_5>()->Create(
35         instance.pp_instance()));
36   } else if (has_interface<PPB_TCPSocket_Private_0_4>()) {
37     PassRefFromConstructor(get_interface<PPB_TCPSocket_Private_0_4>()->Create(
38         instance.pp_instance()));
39   } else if (has_interface<PPB_TCPSocket_Private_0_3>()) {
40     PassRefFromConstructor(get_interface<PPB_TCPSocket_Private_0_3>()->Create(
41         instance.pp_instance()));
42   }
43 }
44 
TCPSocketPrivate(PassRef,PP_Resource resource)45 TCPSocketPrivate::TCPSocketPrivate(PassRef, PP_Resource resource)
46     : Resource(PASS_REF, resource) {
47 }
48 
49 // static
IsAvailable()50 bool TCPSocketPrivate::IsAvailable() {
51   return has_interface<PPB_TCPSocket_Private_0_5>() ||
52       has_interface<PPB_TCPSocket_Private_0_4>() ||
53       has_interface<PPB_TCPSocket_Private_0_3>();
54 }
55 
Connect(const char * host,uint16_t port,const CompletionCallback & callback)56 int32_t TCPSocketPrivate::Connect(const char* host,
57                                   uint16_t port,
58                                   const CompletionCallback& callback) {
59   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
60     return get_interface<PPB_TCPSocket_Private_0_5>()->Connect(
61         pp_resource(), host, port, callback.pp_completion_callback());
62   }
63   if (has_interface<PPB_TCPSocket_Private_0_4>()) {
64     return get_interface<PPB_TCPSocket_Private_0_4>()->Connect(
65         pp_resource(), host, port, callback.pp_completion_callback());
66   }
67   if (has_interface<PPB_TCPSocket_Private_0_3>()) {
68     return get_interface<PPB_TCPSocket_Private_0_3>()->Connect(
69         pp_resource(), host, port, callback.pp_completion_callback());
70   }
71   return callback.MayForce(PP_ERROR_NOINTERFACE);
72 }
73 
ConnectWithNetAddress(const PP_NetAddress_Private * addr,const CompletionCallback & callback)74 int32_t TCPSocketPrivate::ConnectWithNetAddress(
75     const PP_NetAddress_Private* addr,
76     const CompletionCallback& callback) {
77   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
78     return get_interface<PPB_TCPSocket_Private_0_5>()->ConnectWithNetAddress(
79         pp_resource(), addr, callback.pp_completion_callback());
80   }
81   if (has_interface<PPB_TCPSocket_Private_0_4>()) {
82     return get_interface<PPB_TCPSocket_Private_0_4>()->ConnectWithNetAddress(
83         pp_resource(), addr, callback.pp_completion_callback());
84   }
85   if (has_interface<PPB_TCPSocket_Private_0_3>()) {
86     return get_interface<PPB_TCPSocket_Private_0_3>()->ConnectWithNetAddress(
87         pp_resource(), addr, callback.pp_completion_callback());
88   }
89   return callback.MayForce(PP_ERROR_NOINTERFACE);
90 }
91 
GetLocalAddress(PP_NetAddress_Private * local_addr)92 bool TCPSocketPrivate::GetLocalAddress(PP_NetAddress_Private* local_addr) {
93   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
94     PP_Bool result = get_interface<PPB_TCPSocket_Private_0_5>()->
95         GetLocalAddress(pp_resource(), local_addr);
96     return PP_ToBool(result);
97   }
98   if (has_interface<PPB_TCPSocket_Private_0_4>()) {
99     PP_Bool result = get_interface<PPB_TCPSocket_Private_0_4>()->
100         GetLocalAddress(pp_resource(), local_addr);
101     return PP_ToBool(result);
102   }
103   if (has_interface<PPB_TCPSocket_Private_0_3>()) {
104     PP_Bool result = get_interface<PPB_TCPSocket_Private_0_3>()->
105         GetLocalAddress(pp_resource(), local_addr);
106     return PP_ToBool(result);
107   }
108   return false;
109 }
110 
GetRemoteAddress(PP_NetAddress_Private * remote_addr)111 bool TCPSocketPrivate::GetRemoteAddress(PP_NetAddress_Private* remote_addr) {
112   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
113     PP_Bool result = get_interface<PPB_TCPSocket_Private_0_5>()->
114         GetRemoteAddress(pp_resource(), remote_addr);
115     return PP_ToBool(result);
116   }
117   if (has_interface<PPB_TCPSocket_Private_0_4>()) {
118     PP_Bool result = get_interface<PPB_TCPSocket_Private_0_4>()->
119         GetRemoteAddress(pp_resource(), remote_addr);
120     return PP_ToBool(result);
121   }
122   if (has_interface<PPB_TCPSocket_Private_0_3>()) {
123     PP_Bool result = get_interface<PPB_TCPSocket_Private_0_3>()->
124         GetRemoteAddress(pp_resource(), remote_addr);
125     return PP_ToBool(result);
126   }
127   return false;
128 }
129 
SSLHandshake(const char * server_name,uint16_t server_port,const CompletionCallback & callback)130 int32_t TCPSocketPrivate::SSLHandshake(const char* server_name,
131                                        uint16_t server_port,
132                                        const CompletionCallback& callback) {
133   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
134     return get_interface<PPB_TCPSocket_Private_0_5>()->SSLHandshake(
135         pp_resource(), server_name, server_port,
136         callback.pp_completion_callback());
137   }
138   if (has_interface<PPB_TCPSocket_Private_0_4>()) {
139     return get_interface<PPB_TCPSocket_Private_0_4>()->SSLHandshake(
140         pp_resource(), server_name, server_port,
141         callback.pp_completion_callback());
142   }
143   if (has_interface<PPB_TCPSocket_Private_0_3>()) {
144     return get_interface<PPB_TCPSocket_Private_0_3>()->SSLHandshake(
145         pp_resource(), server_name, server_port,
146         callback.pp_completion_callback());
147   }
148   return callback.MayForce(PP_ERROR_NOINTERFACE);
149 }
150 
GetServerCertificate()151 X509CertificatePrivate TCPSocketPrivate::GetServerCertificate() {
152   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
153     return X509CertificatePrivate(PASS_REF,
154         get_interface<PPB_TCPSocket_Private_0_5>()->GetServerCertificate(
155             pp_resource()));
156   }
157   if (has_interface<PPB_TCPSocket_Private_0_4>()) {
158     return X509CertificatePrivate(PASS_REF,
159         get_interface<PPB_TCPSocket_Private_0_4>()->GetServerCertificate(
160             pp_resource()));
161   }
162   return X509CertificatePrivate();
163 }
164 
AddChainBuildingCertificate(const X509CertificatePrivate & cert,bool trusted)165 bool TCPSocketPrivate::AddChainBuildingCertificate(
166     const X509CertificatePrivate& cert,
167     bool trusted) {
168   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
169     return PP_ToBool(get_interface<PPB_TCPSocket_Private_0_5>()->
170         AddChainBuildingCertificate(pp_resource(), cert.pp_resource(),
171                                     PP_FromBool(trusted)));
172   }
173   if (has_interface<PPB_TCPSocket_Private_0_4>()) {
174     return PP_ToBool(get_interface<PPB_TCPSocket_Private_0_4>()->
175         AddChainBuildingCertificate(pp_resource(), cert.pp_resource(),
176                                     PP_FromBool(trusted)));
177   }
178   return false;
179 }
180 
Read(char * buffer,int32_t bytes_to_read,const CompletionCallback & callback)181 int32_t TCPSocketPrivate::Read(char* buffer,
182                                int32_t bytes_to_read,
183                                const CompletionCallback& callback) {
184   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
185     return get_interface<PPB_TCPSocket_Private_0_5>()->Read(
186         pp_resource(), buffer, bytes_to_read,
187         callback.pp_completion_callback());
188   }
189   if (has_interface<PPB_TCPSocket_Private_0_4>()) {
190     return get_interface<PPB_TCPSocket_Private_0_4>()->Read(
191         pp_resource(), buffer, bytes_to_read,
192         callback.pp_completion_callback());
193   }
194   if (has_interface<PPB_TCPSocket_Private_0_3>()) {
195     return get_interface<PPB_TCPSocket_Private_0_3>()->Read(
196         pp_resource(), buffer, bytes_to_read,
197         callback.pp_completion_callback());
198   }
199   return callback.MayForce(PP_ERROR_NOINTERFACE);
200 }
201 
Write(const char * buffer,int32_t bytes_to_write,const CompletionCallback & callback)202 int32_t TCPSocketPrivate::Write(const char* buffer,
203                                 int32_t bytes_to_write,
204                                 const CompletionCallback& callback) {
205   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
206     return get_interface<PPB_TCPSocket_Private_0_5>()->Write(
207         pp_resource(), buffer, bytes_to_write,
208         callback.pp_completion_callback());
209   }
210   if (has_interface<PPB_TCPSocket_Private_0_4>()) {
211     return get_interface<PPB_TCPSocket_Private_0_4>()->Write(
212         pp_resource(), buffer, bytes_to_write,
213         callback.pp_completion_callback());
214   }
215   if (has_interface<PPB_TCPSocket_Private_0_3>()) {
216     return get_interface<PPB_TCPSocket_Private_0_3>()->Write(
217         pp_resource(), buffer, bytes_to_write,
218         callback.pp_completion_callback());
219   }
220   return callback.MayForce(PP_ERROR_NOINTERFACE);
221 }
222 
Disconnect()223 void TCPSocketPrivate::Disconnect() {
224   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
225     return get_interface<PPB_TCPSocket_Private_0_5>()->Disconnect(
226         pp_resource());
227   }
228   if (has_interface<PPB_TCPSocket_Private_0_4>()) {
229     return get_interface<PPB_TCPSocket_Private_0_4>()->Disconnect(
230         pp_resource());
231   }
232   if (has_interface<PPB_TCPSocket_Private_0_3>()) {
233     return get_interface<PPB_TCPSocket_Private_0_3>()->Disconnect(
234         pp_resource());
235   }
236 }
237 
SetOption(PP_TCPSocketOption_Private name,const Var & value,const CompletionCallback & callback)238 int32_t TCPSocketPrivate::SetOption(PP_TCPSocketOption_Private name,
239                                     const Var& value,
240                                     const CompletionCallback& callback) {
241   if (has_interface<PPB_TCPSocket_Private_0_5>()) {
242     return get_interface<PPB_TCPSocket_Private_0_5>()->SetOption(
243         pp_resource(), name, value.pp_var(), callback.pp_completion_callback());
244   }
245   return callback.MayForce(PP_ERROR_NOINTERFACE);
246 }
247 
248 }  // namespace pp
249