media: Specify WebRTC owners in media OWNERS file.
[chromium-blink-merge.git] / net / dns / mdns_client_impl.h
blob4ed85f24ac7404b1dafc7411a12ef171f0e49090
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.
5 #ifndef NET_DNS_MDNS_CLIENT_IMPL_H_
6 #define NET_DNS_MDNS_CLIENT_IMPL_H_
8 #include <map>
9 #include <string>
10 #include <utility>
11 #include <vector>
13 #include "base/cancelable_callback.h"
14 #include "base/memory/scoped_vector.h"
15 #include "base/observer_list.h"
16 #include "net/base/io_buffer.h"
17 #include "net/base/ip_endpoint.h"
18 #include "net/dns/mdns_cache.h"
19 #include "net/dns/mdns_client.h"
20 #include "net/udp/datagram_server_socket.h"
21 #include "net/udp/udp_server_socket.h"
22 #include "net/udp/udp_socket.h"
24 namespace net {
26 class MDnsSocketFactoryImpl : public MDnsSocketFactory {
27 public:
28 MDnsSocketFactoryImpl() {};
29 ~MDnsSocketFactoryImpl() override{};
31 void CreateSockets(ScopedVector<DatagramServerSocket>* sockets) override;
33 private:
34 DISALLOW_COPY_AND_ASSIGN(MDnsSocketFactoryImpl);
37 // A connection to the network for multicast DNS clients. It reads data into
38 // DnsResponse objects and alerts the delegate that a packet has been received.
39 class NET_EXPORT_PRIVATE MDnsConnection {
40 public:
41 class Delegate {
42 public:
43 // Handle an mDNS packet buffered in |response| with a size of |bytes_read|.
44 virtual void HandlePacket(DnsResponse* response, int bytes_read) = 0;
45 virtual void OnConnectionError(int error) = 0;
46 virtual ~Delegate() {}
49 explicit MDnsConnection(MDnsConnection::Delegate* delegate);
50 virtual ~MDnsConnection();
52 // Both methods return true if at least one of the socket handlers succeeded.
53 bool Init(MDnsSocketFactory* socket_factory);
54 void Send(const scoped_refptr<IOBuffer>& buffer, unsigned size);
56 private:
57 class SocketHandler {
58 public:
59 SocketHandler(scoped_ptr<DatagramServerSocket> socket,
60 MDnsConnection* connection);
61 ~SocketHandler();
63 int Start();
64 void Send(const scoped_refptr<IOBuffer>& buffer, unsigned size);
66 private:
67 int DoLoop(int rv);
68 void OnDatagramReceived(int rv);
70 // Callback for when sending a query has finished.
71 void SendDone(int rv);
73 scoped_ptr<DatagramServerSocket> socket_;
74 MDnsConnection* connection_;
75 IPEndPoint recv_addr_;
76 DnsResponse response_;
77 IPEndPoint multicast_addr_;
78 bool send_in_progress_;
79 std::queue<std::pair<scoped_refptr<IOBuffer>, unsigned> > send_queue_;
81 DISALLOW_COPY_AND_ASSIGN(SocketHandler);
84 // Callback for handling a datagram being received on either ipv4 or ipv6.
85 void OnDatagramReceived(DnsResponse* response,
86 const IPEndPoint& recv_addr,
87 int bytes_read);
89 void PostOnError(SocketHandler* loop, int rv);
90 void OnError(int rv);
92 // Only socket handlers which successfully bound and started are kept.
93 ScopedVector<SocketHandler> socket_handlers_;
95 Delegate* delegate_;
97 base::WeakPtrFactory<MDnsConnection> weak_ptr_factory_;
99 DISALLOW_COPY_AND_ASSIGN(MDnsConnection);
102 class MDnsListenerImpl;
104 class NET_EXPORT_PRIVATE MDnsClientImpl : public MDnsClient {
105 public:
106 // The core object exists while the MDnsClient is listening, and is deleted
107 // whenever the number of listeners reaches zero. The deletion happens
108 // asychronously, so destroying the last listener does not immediately
109 // invalidate the core.
110 class Core : public base::SupportsWeakPtr<Core>, MDnsConnection::Delegate {
111 public:
112 Core();
113 ~Core() override;
115 // Initialize the core. Returns true on success.
116 bool Init(MDnsSocketFactory* socket_factory);
118 // Send a query with a specific rrtype and name. Returns true on success.
119 bool SendQuery(uint16 rrtype, std::string name);
121 // Add/remove a listener to the list of listeners.
122 void AddListener(MDnsListenerImpl* listener);
123 void RemoveListener(MDnsListenerImpl* listener);
125 // Query the cache for records of a specific type and name.
126 void QueryCache(uint16 rrtype, const std::string& name,
127 std::vector<const RecordParsed*>* records) const;
129 // Parse the response and alert relevant listeners.
130 void HandlePacket(DnsResponse* response, int bytes_read) override;
132 void OnConnectionError(int error) override;
134 private:
135 typedef std::pair<std::string, uint16> ListenerKey;
136 typedef std::map<ListenerKey, ObserverList<MDnsListenerImpl>* >
137 ListenerMap;
139 // Alert listeners of an update to the cache.
140 void AlertListeners(MDnsCache::UpdateType update_type,
141 const ListenerKey& key, const RecordParsed* record);
143 // Schedule a cache cleanup to a specific time, cancelling other cleanups.
144 void ScheduleCleanup(base::Time cleanup);
146 // Clean up the cache and schedule a new cleanup.
147 void DoCleanup();
149 // Callback for when a record is removed from the cache.
150 void OnRecordRemoved(const RecordParsed* record);
152 void NotifyNsecRecord(const RecordParsed* record);
154 // Delete and erase the observer list for |key|. Only deletes the observer
155 // list if is empty.
156 void CleanupObserverList(const ListenerKey& key);
158 ListenerMap listeners_;
160 MDnsCache cache_;
162 base::CancelableClosure cleanup_callback_;
163 base::Time scheduled_cleanup_;
165 scoped_ptr<MDnsConnection> connection_;
167 DISALLOW_COPY_AND_ASSIGN(Core);
170 MDnsClientImpl();
171 ~MDnsClientImpl() override;
173 // MDnsClient implementation:
174 scoped_ptr<MDnsListener> CreateListener(
175 uint16 rrtype,
176 const std::string& name,
177 MDnsListener::Delegate* delegate) override;
179 scoped_ptr<MDnsTransaction> CreateTransaction(
180 uint16 rrtype,
181 const std::string& name,
182 int flags,
183 const MDnsTransaction::ResultCallback& callback) override;
185 bool StartListening(MDnsSocketFactory* socket_factory) override;
186 void StopListening() override;
187 bool IsListening() const override;
189 Core* core() { return core_.get(); }
191 private:
192 scoped_ptr<Core> core_;
194 DISALLOW_COPY_AND_ASSIGN(MDnsClientImpl);
197 class MDnsListenerImpl : public MDnsListener,
198 public base::SupportsWeakPtr<MDnsListenerImpl> {
199 public:
200 MDnsListenerImpl(uint16 rrtype,
201 const std::string& name,
202 MDnsListener::Delegate* delegate,
203 MDnsClientImpl* client);
205 ~MDnsListenerImpl() override;
207 // MDnsListener implementation:
208 bool Start() override;
210 // Actively refresh any received records.
211 void SetActiveRefresh(bool active_refresh) override;
213 const std::string& GetName() const override;
215 uint16 GetType() const override;
217 MDnsListener::Delegate* delegate() { return delegate_; }
219 // Alert the delegate of a record update.
220 void HandleRecordUpdate(MDnsCache::UpdateType update_type,
221 const RecordParsed* record_parsed);
223 // Alert the delegate of the existence of an Nsec record.
224 void AlertNsecRecord();
226 private:
227 void ScheduleNextRefresh();
228 void DoRefresh();
230 uint16 rrtype_;
231 std::string name_;
232 MDnsClientImpl* client_;
233 MDnsListener::Delegate* delegate_;
235 base::Time last_update_;
236 uint32 ttl_;
237 bool started_;
238 bool active_refresh_;
240 base::CancelableClosure next_refresh_;
241 DISALLOW_COPY_AND_ASSIGN(MDnsListenerImpl);
244 class MDnsTransactionImpl : public base::SupportsWeakPtr<MDnsTransactionImpl>,
245 public MDnsTransaction,
246 public MDnsListener::Delegate {
247 public:
248 MDnsTransactionImpl(uint16 rrtype,
249 const std::string& name,
250 int flags,
251 const MDnsTransaction::ResultCallback& callback,
252 MDnsClientImpl* client);
253 ~MDnsTransactionImpl() override;
255 // MDnsTransaction implementation:
256 bool Start() override;
258 const std::string& GetName() const override;
259 uint16 GetType() const override;
261 // MDnsListener::Delegate implementation:
262 void OnRecordUpdate(MDnsListener::UpdateType update,
263 const RecordParsed* record) override;
264 void OnNsecRecord(const std::string& name, unsigned type) override;
266 void OnCachePurged() override;
268 private:
269 bool is_active() { return !callback_.is_null(); }
271 void Reset();
273 // Trigger the callback and reset all related variables.
274 void TriggerCallback(MDnsTransaction::Result result,
275 const RecordParsed* record);
277 // Internal callback for when a cache record is found.
278 void CacheRecordFound(const RecordParsed* record);
280 // Signal the transactionis over and release all related resources.
281 void SignalTransactionOver();
283 // Reads records from the cache and calls the callback for every
284 // record read.
285 void ServeRecordsFromCache();
287 // Send a query to the network and set up a timeout to time out the
288 // transaction. Returns false if it fails to start listening on the network
289 // or if it fails to send a query.
290 bool QueryAndListen();
292 uint16 rrtype_;
293 std::string name_;
294 MDnsTransaction::ResultCallback callback_;
296 scoped_ptr<MDnsListener> listener_;
297 base::CancelableCallback<void()> timeout_;
299 MDnsClientImpl* client_;
301 bool started_;
302 int flags_;
304 DISALLOW_COPY_AND_ASSIGN(MDnsTransactionImpl);
307 } // namespace net
308 #endif // NET_DNS_MDNS_CLIENT_IMPL_H_