1// Copyright 2013 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 <algorithm>
6
7#include "net/base/net_errors.h"
8#include "net/dns/mock_mdns_socket_factory.h"
9
10using testing::_;
11using testing::Invoke;
12
13namespace net {
14
15MockMDnsDatagramServerSocket::MockMDnsDatagramServerSocket(
16    AddressFamily address_family) {
17  local_address_ = GetMDnsIPEndPoint(address_family);
18}
19
20MockMDnsDatagramServerSocket::~MockMDnsDatagramServerSocket() {
21}
22
23int MockMDnsDatagramServerSocket::SendTo(IOBuffer* buf, int buf_len,
24                                         const IPEndPoint& address,
25                                         const CompletionCallback& callback) {
26  return SendToInternal(std::string(buf->data(), buf_len), address.ToString(),
27                        callback);
28}
29
30int MockMDnsDatagramServerSocket::GetLocalAddress(IPEndPoint* address) const {
31  *address = local_address_;
32  return OK;
33}
34
35void MockMDnsDatagramServerSocket::SetResponsePacket(
36    std::string response_packet) {
37  response_packet_ = response_packet;
38}
39
40int MockMDnsDatagramServerSocket::HandleRecvNow(
41    IOBuffer* buffer, int size, IPEndPoint* address,
42    const CompletionCallback& callback) {
43  int size_returned =
44      std::min(response_packet_.size(), static_cast<size_t>(size));
45  memcpy(buffer->data(), response_packet_.data(), size_returned);
46  return size_returned;
47}
48
49int MockMDnsDatagramServerSocket::HandleRecvLater(
50    IOBuffer* buffer, int size, IPEndPoint* address,
51    const CompletionCallback& callback) {
52  int rv = HandleRecvNow(buffer, size, address, callback);
53  base::MessageLoop::current()->PostTask(FROM_HERE, base::Bind(callback, rv));
54  return ERR_IO_PENDING;
55}
56
57MockMDnsSocketFactory::MockMDnsSocketFactory() {
58}
59
60MockMDnsSocketFactory::~MockMDnsSocketFactory() {
61}
62
63void MockMDnsSocketFactory::CreateSockets(
64    ScopedVector<DatagramServerSocket>* sockets) {
65  CreateSocket(ADDRESS_FAMILY_IPV4, sockets);
66  CreateSocket(ADDRESS_FAMILY_IPV6, sockets);
67}
68
69void MockMDnsSocketFactory::CreateSocket(
70    AddressFamily address_family,
71    ScopedVector<DatagramServerSocket>* sockets) {
72  scoped_ptr<testing::NiceMock<MockMDnsDatagramServerSocket> > new_socket(
73      new testing::NiceMock<MockMDnsDatagramServerSocket>(address_family));
74
75  ON_CALL(*new_socket, SendToInternal(_, _, _))
76      .WillByDefault(Invoke(
77          this,
78          &MockMDnsSocketFactory::SendToInternal));
79
80  ON_CALL(*new_socket, RecvFrom(_, _, _, _))
81      .WillByDefault(Invoke(
82          this,
83          &MockMDnsSocketFactory::RecvFromInternal));
84
85  sockets->push_back(new_socket.release());
86}
87
88void MockMDnsSocketFactory::SimulateReceive(const uint8* packet, int size) {
89  DCHECK(recv_buffer_size_ >= size);
90  DCHECK(recv_buffer_.get());
91  DCHECK(!recv_callback_.is_null());
92
93  memcpy(recv_buffer_->data(), packet, size);
94  CompletionCallback recv_callback = recv_callback_;
95  recv_callback_.Reset();
96  recv_callback.Run(size);
97}
98
99int MockMDnsSocketFactory::RecvFromInternal(
100    IOBuffer* buffer, int size,
101    IPEndPoint* address,
102    const CompletionCallback& callback) {
103    recv_buffer_ = buffer;
104    recv_buffer_size_ = size;
105    recv_callback_ = callback;
106    return ERR_IO_PENDING;
107}
108
109int MockMDnsSocketFactory::SendToInternal(
110    const std::string& packet, const std::string& address,
111    const CompletionCallback& callback) {
112  OnSendTo(packet);
113  return packet.size();
114}
115
116}  // namespace net
117