Home | History | Annotate | Download | only in local_discovery
      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 #ifndef CHROME_UTILITY_LOCAL_DISCOVERY_SERVICE_DISCOVERY_CLIENT_IMPL_H_
      6 #define CHROME_UTILITY_LOCAL_DISCOVERY_SERVICE_DISCOVERY_CLIENT_IMPL_H_
      7 
      8 #include <map>
      9 #include <string>
     10 #include <vector>
     11 
     12 #include "base/callback.h"
     13 #include "base/cancelable_callback.h"
     14 #include "base/memory/linked_ptr.h"
     15 #include "base/memory/weak_ptr.h"
     16 #include "base/message_loop/message_loop.h"
     17 #include "chrome/common/local_discovery/service_discovery_client.h"
     18 #include "net/dns/mdns_client.h"
     19 
     20 namespace local_discovery {
     21 
     22 class ServiceDiscoveryClientImpl : public ServiceDiscoveryClient {
     23  public:
     24   // |mdns_client| must outlive the Service Discovery Client.
     25   explicit ServiceDiscoveryClientImpl(net::MDnsClient* mdns_client);
     26   virtual ~ServiceDiscoveryClientImpl();
     27 
     28   // ServiceDiscoveryClient implementation:
     29   virtual scoped_ptr<ServiceWatcher> CreateServiceWatcher(
     30       const std::string& service_type,
     31       const ServiceWatcher::UpdatedCallback& callback) OVERRIDE;
     32 
     33   virtual scoped_ptr<ServiceResolver> CreateServiceResolver(
     34       const std::string& service_name,
     35       const ServiceResolver::ResolveCompleteCallback& callback) OVERRIDE;
     36 
     37   virtual scoped_ptr<LocalDomainResolver> CreateLocalDomainResolver(
     38       const std::string& domain,
     39       net::AddressFamily address_family,
     40       const LocalDomainResolver::IPAddressCallback& callback) OVERRIDE;
     41 
     42  private:
     43   net::MDnsClient* mdns_client_;
     44 
     45   DISALLOW_COPY_AND_ASSIGN(ServiceDiscoveryClientImpl);
     46 };
     47 
     48 class ServiceWatcherImpl : public ServiceWatcher,
     49                            public net::MDnsListener::Delegate,
     50                            public base::SupportsWeakPtr<ServiceWatcherImpl> {
     51  public:
     52   ServiceWatcherImpl(const std::string& service_type,
     53                      const ServiceWatcher::UpdatedCallback& callback,
     54                      net::MDnsClient* mdns_client);
     55   // Listening will automatically stop when the destructor is called.
     56   virtual ~ServiceWatcherImpl();
     57 
     58   // ServiceWatcher implementation:
     59   virtual void Start() OVERRIDE;
     60 
     61   virtual void DiscoverNewServices(bool force_update) OVERRIDE;
     62 
     63   virtual std::string GetServiceType() const OVERRIDE;
     64 
     65   virtual void OnRecordUpdate(net::MDnsListener::UpdateType update,
     66                               const net::RecordParsed* record) OVERRIDE;
     67 
     68   virtual void OnNsecRecord(const std::string& name, unsigned rrtype) OVERRIDE;
     69 
     70   virtual void OnCachePurged() OVERRIDE;
     71 
     72   virtual void OnTransactionResponse(
     73       scoped_ptr<net::MDnsTransaction>* transaction,
     74       net::MDnsTransaction::Result result,
     75       const net::RecordParsed* record);
     76 
     77  private:
     78   struct ServiceListeners {
     79     ServiceListeners(const std::string& service_name,
     80                      ServiceWatcherImpl* watcher,
     81                      net::MDnsClient* mdns_client);
     82     ~ServiceListeners();
     83     bool Start();
     84 
     85     void set_update_pending(bool update_pending) {
     86       update_pending_ = update_pending;
     87     }
     88 
     89     bool update_pending() { return update_pending_; }
     90    private:
     91     scoped_ptr<net::MDnsListener> srv_listener_;
     92     scoped_ptr<net::MDnsListener> txt_listener_;
     93     bool update_pending_;
     94   };
     95 
     96   typedef std::map<std::string, linked_ptr<ServiceListeners> >
     97       ServiceListenersMap;
     98 
     99   void ReadCachedServices();
    100   void AddService(const std::string& service);
    101   void RemoveService(const std::string& service);
    102   bool CreateTransaction(bool active, bool alert_existing_services,
    103                          bool force_refresh,
    104                          scoped_ptr<net::MDnsTransaction>* transaction);
    105 
    106   void DeferUpdate(ServiceWatcher::UpdateType update_type,
    107                    const std::string& service_name);
    108   void DeliverDeferredUpdate(ServiceWatcher::UpdateType update_type,
    109                              const std::string& service_name);
    110 
    111   void ScheduleQuery(int timeout_seconds);
    112 
    113   void SendQuery(int next_timeout_seconds, bool force_update);
    114 
    115   std::string service_type_;
    116   ServiceListenersMap services_;
    117   scoped_ptr<net::MDnsTransaction> transaction_network_;
    118   scoped_ptr<net::MDnsTransaction> transaction_cache_;
    119   scoped_ptr<net::MDnsListener> listener_;
    120 
    121   ServiceWatcher::UpdatedCallback callback_;
    122   bool started_;
    123 
    124   net::MDnsClient* mdns_client_;
    125 
    126   DISALLOW_COPY_AND_ASSIGN(ServiceWatcherImpl);
    127 };
    128 
    129 class ServiceResolverImpl
    130     : public ServiceResolver,
    131       public base::SupportsWeakPtr<ServiceResolverImpl> {
    132  public:
    133   ServiceResolverImpl(const std::string& service_name,
    134                       const ServiceResolver::ResolveCompleteCallback& callback,
    135                       net::MDnsClient* mdns_client);
    136 
    137   virtual ~ServiceResolverImpl();
    138 
    139   // ServiceResolver implementation:
    140   virtual void StartResolving() OVERRIDE;
    141 
    142   virtual std::string GetName() const OVERRIDE;
    143 
    144  private:
    145   // Respond to transaction finishing for SRV records.
    146   void SrvRecordTransactionResponse(net::MDnsTransaction::Result status,
    147                                     const net::RecordParsed* record);
    148 
    149   // Respond to transaction finishing for TXT records.
    150   void TxtRecordTransactionResponse(net::MDnsTransaction::Result status,
    151                                     const net::RecordParsed* record);
    152 
    153   // Respond to transaction finishing for A records.
    154   void ARecordTransactionResponse(net::MDnsTransaction::Result status,
    155                                   const net::RecordParsed* record);
    156 
    157   void AlertCallbackIfReady();
    158 
    159   void ServiceNotFound(RequestStatus status);
    160 
    161   // Convert a TXT record to a vector of strings (metadata).
    162   const std::vector<std::string>& RecordToMetadata(
    163       const net::RecordParsed* record) const;
    164 
    165   // Convert an SRV record to a host and port pair.
    166   net::HostPortPair RecordToAddress(
    167       const net::RecordParsed* record) const;
    168 
    169   // Convert an A record to an IP address.
    170   const net::IPAddressNumber& RecordToIPAddress(
    171       const net::RecordParsed* record) const;
    172 
    173   // Convert an MDns status to a service discovery status.
    174   RequestStatus MDnsStatusToRequestStatus(
    175       net::MDnsTransaction::Result status) const;
    176 
    177   bool CreateTxtTransaction();
    178   bool CreateSrvTransaction();
    179   void CreateATransaction();
    180 
    181   std::string service_name_;
    182   ResolveCompleteCallback callback_;
    183 
    184   bool has_resolved_;
    185 
    186   bool metadata_resolved_;
    187   bool address_resolved_;
    188 
    189   scoped_ptr<net::MDnsTransaction> txt_transaction_;
    190   scoped_ptr<net::MDnsTransaction> srv_transaction_;
    191   scoped_ptr<net::MDnsTransaction> a_transaction_;
    192 
    193   ServiceDescription service_staging_;
    194 
    195   net::MDnsClient* mdns_client_;
    196 
    197   DISALLOW_COPY_AND_ASSIGN(ServiceResolverImpl);
    198 };
    199 
    200 class LocalDomainResolverImpl : public LocalDomainResolver {
    201  public:
    202   LocalDomainResolverImpl(const std::string& domain,
    203                           net::AddressFamily address_family,
    204                           const IPAddressCallback& callback,
    205                           net::MDnsClient* mdns_client);
    206   virtual ~LocalDomainResolverImpl();
    207 
    208   virtual void Start() OVERRIDE;
    209 
    210   const std::string& domain() { return domain_; }
    211 
    212  private:
    213   void OnTransactionComplete(
    214       net::MDnsTransaction::Result result,
    215       const net::RecordParsed* record);
    216 
    217   scoped_ptr<net::MDnsTransaction> CreateTransaction(uint16 type);
    218 
    219   bool IsSuccess();
    220 
    221   void SendResolvedAddresses();
    222 
    223   std::string domain_;
    224   net::AddressFamily address_family_;
    225   IPAddressCallback callback_;
    226 
    227   scoped_ptr<net::MDnsTransaction> transaction_a_;
    228   scoped_ptr<net::MDnsTransaction> transaction_aaaa_;
    229 
    230   int transactions_finished_;
    231 
    232   net::MDnsClient* mdns_client_;
    233 
    234   net::IPAddressNumber address_ipv4_;
    235   net::IPAddressNumber address_ipv6_;
    236 
    237   base::CancelableCallback<void()> timeout_callback_;
    238 
    239   DISALLOW_COPY_AND_ASSIGN(LocalDomainResolverImpl);
    240 };
    241 
    242 
    243 }  // namespace local_discovery
    244 
    245 #endif  // CHROME_UTILITY_LOCAL_DISCOVERY_SERVICE_DISCOVERY_CLIENT_IMPL_H_
    246