1 // Copyright (c) 2011 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.
5 #include "jingle/glue/fake_socket_factory.h"
8 #include "base/message_loop/message_loop.h"
9 #include "jingle/glue/utils.h"
10 #include "third_party/libjingle/source/talk/base/asyncsocket.h"
12 namespace jingle_glue
{
14 FakeUDPPacketSocket::FakeUDPPacketSocket(FakeSocketManager
* fake_socket_manager
,
15 const net::IPEndPoint
& address
)
16 : fake_socket_manager_(fake_socket_manager
),
17 endpoint_(address
), state_(IS_OPEN
), error_(0) {
18 CHECK(IPEndPointToSocketAddress(endpoint_
, &local_address_
));
19 fake_socket_manager_
->AddSocket(this);
22 FakeUDPPacketSocket::~FakeUDPPacketSocket() {
23 fake_socket_manager_
->RemoveSocket(this);
26 talk_base::SocketAddress
FakeUDPPacketSocket::GetLocalAddress() const {
27 DCHECK(CalledOnValidThread());
28 return local_address_
;
31 talk_base::SocketAddress
FakeUDPPacketSocket::GetRemoteAddress() const {
32 DCHECK(CalledOnValidThread());
33 return remote_address_
;
36 int FakeUDPPacketSocket::Send(const void *data
, size_t data_size
) {
37 DCHECK(CalledOnValidThread());
38 return SendTo(data
, data_size
, remote_address_
);
41 int FakeUDPPacketSocket::SendTo(const void *data
, size_t data_size
,
42 const talk_base::SocketAddress
& address
) {
43 DCHECK(CalledOnValidThread());
45 if (state_
== IS_CLOSED
) {
49 net::IPEndPoint destination
;
50 if (!SocketAddressToIPEndPoint(address
, &destination
)) {
54 const char* data_char
= reinterpret_cast<const char*>(data
);
55 std::vector
<char> data_vector(data_char
, data_char
+ data_size
);
57 fake_socket_manager_
->SendPacket(endpoint_
, destination
, data_vector
);
62 int FakeUDPPacketSocket::Close() {
63 DCHECK(CalledOnValidThread());
68 talk_base::AsyncPacketSocket::State
FakeUDPPacketSocket::GetState() const {
69 DCHECK(CalledOnValidThread());
82 int FakeUDPPacketSocket::GetOption(talk_base::Socket::Option opt
, int* value
) {
83 DCHECK(CalledOnValidThread());
87 int FakeUDPPacketSocket::SetOption(talk_base::Socket::Option opt
, int value
) {
88 DCHECK(CalledOnValidThread());
92 int FakeUDPPacketSocket::GetError() const {
93 DCHECK(CalledOnValidThread());
97 void FakeUDPPacketSocket::SetError(int error
) {
98 DCHECK(CalledOnValidThread());
102 void FakeUDPPacketSocket::DeliverPacket(const net::IPEndPoint
& from
,
103 const std::vector
<char>& data
) {
104 DCHECK(CalledOnValidThread());
106 talk_base::SocketAddress address
;
107 if (!jingle_glue::IPEndPointToSocketAddress(from
, &address
)) {
108 // We should always be able to convert address here because we
109 // don't expect IPv6 address on IPv4 connections.
114 SignalReadPacket(this, &data
[0], data
.size(), address
);
117 FakeSocketManager::FakeSocketManager()
118 : message_loop_(base::MessageLoop::current()) {}
120 FakeSocketManager::~FakeSocketManager() { }
122 void FakeSocketManager::SendPacket(const net::IPEndPoint
& from
,
123 const net::IPEndPoint
& to
,
124 const std::vector
<char>& data
) {
125 DCHECK_EQ(base::MessageLoop::current(), message_loop_
);
127 message_loop_
->PostTask(
129 base::Bind(&FakeSocketManager::DeliverPacket
, this, from
, to
, data
));
132 void FakeSocketManager::DeliverPacket(const net::IPEndPoint
& from
,
133 const net::IPEndPoint
& to
,
134 const std::vector
<char>& data
) {
135 DCHECK_EQ(base::MessageLoop::current(), message_loop_
);
137 std::map
<net::IPEndPoint
, FakeUDPPacketSocket
*>::iterator it
=
139 if (it
== endpoints_
.end()) {
140 LOG(WARNING
) << "Dropping packet with unknown destination: "
144 it
->second
->DeliverPacket(from
, data
);
147 void FakeSocketManager::AddSocket(FakeUDPPacketSocket
* socket_factory
) {
148 DCHECK_EQ(base::MessageLoop::current(), message_loop_
);
150 endpoints_
[socket_factory
->endpoint()] = socket_factory
;
153 void FakeSocketManager::RemoveSocket(FakeUDPPacketSocket
* socket_factory
) {
154 DCHECK_EQ(base::MessageLoop::current(), message_loop_
);
156 endpoints_
.erase(socket_factory
->endpoint());
159 FakeSocketFactory::FakeSocketFactory(FakeSocketManager
* socket_manager
,
160 const net::IPAddressNumber
& address
)
161 : socket_manager_(socket_manager
),
163 last_allocated_port_(0) {
166 FakeSocketFactory::~FakeSocketFactory() {
169 talk_base::AsyncPacketSocket
* FakeSocketFactory::CreateUdpSocket(
170 const talk_base::SocketAddress
& local_address
, int min_port
, int max_port
) {
171 CHECK_EQ(min_port
, 0);
172 CHECK_EQ(max_port
, 0);
173 return new FakeUDPPacketSocket(
174 socket_manager_
.get(), net::IPEndPoint(address_
, ++last_allocated_port_
));
177 talk_base::AsyncPacketSocket
* FakeSocketFactory::CreateServerTcpSocket(
178 const talk_base::SocketAddress
& local_address
, int min_port
, int max_port
,
180 // TODO(sergeyu): Implement fake TCP sockets.
185 talk_base::AsyncPacketSocket
* FakeSocketFactory::CreateClientTcpSocket(
186 const talk_base::SocketAddress
& local_address
,
187 const talk_base::SocketAddress
& remote_address
,
188 const talk_base::ProxyInfo
& proxy_info
, const std::string
& user_agent
,
190 // TODO(sergeyu): Implement fake TCP sockets.
195 } // namespace jingle_glue