• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  *  Copyright 2004 The WebRTC Project Authors. All rights reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 #ifndef WEBRTC_BASE_NETWORK_H_
12 #define WEBRTC_BASE_NETWORK_H_
13 
14 #include <deque>
15 #include <map>
16 #include <string>
17 #include <vector>
18 
19 #include "webrtc/base/basictypes.h"
20 #include "webrtc/base/ipaddress.h"
21 #include "webrtc/base/messagehandler.h"
22 #include "webrtc/base/sigslot.h"
23 
24 #if defined(WEBRTC_POSIX)
25 struct ifaddrs;
26 #endif  // defined(WEBRTC_POSIX)
27 
28 namespace rtc {
29 
30 class Network;
31 class Thread;
32 
33 enum AdapterType {
34   // This enum resembles the one in Chromium net::ConnectionType.
35   ADAPTER_TYPE_UNKNOWN = 0,
36   ADAPTER_TYPE_ETHERNET = 1,
37   ADAPTER_TYPE_WIFI = 2,
38   ADAPTER_TYPE_CELLULAR = 3,
39   ADAPTER_TYPE_VPN = 4
40 };
41 
42 // Makes a string key for this network. Used in the network manager's maps.
43 // Network objects are keyed on interface name, network prefix and the
44 // length of that prefix.
45 std::string MakeNetworkKey(const std::string& name, const IPAddress& prefix,
46                            int prefix_length);
47 
48 // Generic network manager interface. It provides list of local
49 // networks.
50 class NetworkManager {
51  public:
52   typedef std::vector<Network*> NetworkList;
53 
54   NetworkManager();
55   virtual ~NetworkManager();
56 
57   // Called when network list is updated.
58   sigslot::signal0<> SignalNetworksChanged;
59 
60   // Indicates a failure when getting list of network interfaces.
61   sigslot::signal0<> SignalError;
62 
63   // Start/Stop monitoring of network interfaces
64   // list. SignalNetworksChanged or SignalError is emitted immidiately
65   // after StartUpdating() is called. After that SignalNetworksChanged
66   // is emitted wheneven list of networks changes.
67   virtual void StartUpdating() = 0;
68   virtual void StopUpdating() = 0;
69 
70   // Returns the current list of networks available on this machine.
71   // UpdateNetworks() must be called before this method is called.
72   // It makes sure that repeated calls return the same object for a
73   // given network, so that quality is tracked appropriately. Does not
74   // include ignored networks.
75   virtual void GetNetworks(NetworkList* networks) const = 0;
76 
77   // Dumps a list of networks available to LS_INFO.
DumpNetworks(bool include_ignored)78   virtual void DumpNetworks(bool include_ignored) {}
79 };
80 
81 // Base class for NetworkManager implementations.
82 class NetworkManagerBase : public NetworkManager {
83  public:
84   NetworkManagerBase();
85   virtual ~NetworkManagerBase();
86 
87   virtual void GetNetworks(std::vector<Network*>* networks) const;
ipv6_enabled()88   bool ipv6_enabled() const { return ipv6_enabled_; }
set_ipv6_enabled(bool enabled)89   void set_ipv6_enabled(bool enabled) { ipv6_enabled_ = enabled; }
90 
91  protected:
92   typedef std::map<std::string, Network*> NetworkMap;
93   // Updates |networks_| with the networks listed in |list|. If
94   // |network_map_| already has a Network object for a network listed
95   // in the |list| then it is reused. Accept ownership of the Network
96   // objects in the |list|. |changed| will be set to true if there is
97   // any change in the network list.
98   void MergeNetworkList(const NetworkList& list, bool* changed);
99 
100  private:
101   friend class NetworkTest;
102   void DoUpdateNetworks();
103 
104   NetworkList networks_;
105   NetworkMap networks_map_;
106   bool ipv6_enabled_;
107 };
108 
109 // Basic implementation of the NetworkManager interface that gets list
110 // of networks using OS APIs.
111 class BasicNetworkManager : public NetworkManagerBase,
112                             public MessageHandler {
113  public:
114   BasicNetworkManager();
115   virtual ~BasicNetworkManager();
116 
117   virtual void StartUpdating();
118   virtual void StopUpdating();
119 
120   // Logs the available networks.
121   virtual void DumpNetworks(bool include_ignored);
122 
123   // MessageHandler interface.
124   virtual void OnMessage(Message* msg);
started()125   bool started() { return start_count_ > 0; }
126 
127   // Sets the network ignore list, which is empty by default. Any network on
128   // the ignore list will be filtered from network enumeration results.
set_network_ignore_list(const std::vector<std::string> & list)129   void set_network_ignore_list(const std::vector<std::string>& list) {
130     network_ignore_list_ = list;
131   }
132 #if defined(WEBRTC_LINUX)
133   // Sets the flag for ignoring non-default routes.
set_ignore_non_default_routes(bool value)134   void set_ignore_non_default_routes(bool value) {
135     ignore_non_default_routes_ = true;
136   }
137 #endif
138 
139  protected:
140 #if defined(WEBRTC_POSIX)
141   // Separated from CreateNetworks for tests.
142   void ConvertIfAddrs(ifaddrs* interfaces,
143                       bool include_ignored,
144                       NetworkList* networks) const;
145 #endif  // defined(WEBRTC_POSIX)
146 
147   // Creates a network object for each network available on the machine.
148   bool CreateNetworks(bool include_ignored, NetworkList* networks) const;
149 
150   // Determines if a network should be ignored.
151   bool IsIgnoredNetwork(const Network& network) const;
152 
153  private:
154   friend class NetworkTest;
155 
156   void DoUpdateNetworks();
157 
158   Thread* thread_;
159   bool sent_first_update_;
160   int start_count_;
161   std::vector<std::string> network_ignore_list_;
162   bool ignore_non_default_routes_;
163 };
164 
165 // Represents a Unix-type network interface, with a name and single address.
166 class Network {
167  public:
168   Network(const std::string& name, const std::string& description,
169           const IPAddress& prefix, int prefix_length);
170 
171   Network(const std::string& name, const std::string& description,
172           const IPAddress& prefix, int prefix_length, AdapterType type);
173 
174   // Returns the name of the interface this network is associated wtih.
name()175   const std::string& name() const { return name_; }
176 
177   // Returns the OS-assigned name for this network. This is useful for
178   // debugging but should not be sent over the wire (for privacy reasons).
description()179   const std::string& description() const { return description_; }
180 
181   // Returns the prefix for this network.
prefix()182   const IPAddress& prefix() const { return prefix_; }
183   // Returns the length, in bits, of this network's prefix.
prefix_length()184   int prefix_length() const { return prefix_length_; }
185 
186   // |key_| has unique value per network interface. Used in sorting network
187   // interfaces. Key is derived from interface name and it's prefix.
key()188   std::string key() const { return key_; }
189 
190   // Returns the Network's current idea of the 'best' IP it has.
191   // Or return an unset IP if this network has no active addresses.
192   // Here is the rule on how we mark the IPv6 address as ignorable for WebRTC.
193   // 1) return all global temporary dynamic and non-deprecrated ones.
194   // 2) if #1 not available, return global ones.
195   // 3) if #2 not available, use ULA ipv6 as last resort. (ULA stands
196   // for unique local address, which is not route-able in open
197   // internet but might be useful for a close WebRTC deployment.
198 
199   // TODO(guoweis): rule #3 actually won't happen at current
200   // implementation. The reason being that ULA address starting with
201   // 0xfc 0r 0xfd will be grouped into its own Network. The result of
202   // that is WebRTC will have one extra Network to generate candidates
203   // but the lack of rule #3 shouldn't prevent turning on IPv6 since
204   // ULA should only be tried in a close deployment anyway.
205 
206   // Note that when not specifying any flag, it's treated as case global
207   // IPv6 address
208   IPAddress GetBestIP() const;
209 
210   // Keep the original function here for now.
211   // TODO(guoweis): Remove this when all callers are migrated to GetBestIP().
ip()212   IPAddress ip() const { return GetBestIP(); }
213 
214   // Adds an active IP address to this network. Does not check for duplicates.
AddIP(const InterfaceAddress & ip)215   void AddIP(const InterfaceAddress& ip) { ips_.push_back(ip); }
216 
217   // Sets the network's IP address list. Returns true if new IP addresses were
218   // detected. Passing true to already_changed skips this check.
219   bool SetIPs(const std::vector<InterfaceAddress>& ips, bool already_changed);
220   // Get the list of IP Addresses associated with this network.
GetIPs()221   const std::vector<InterfaceAddress>& GetIPs() const { return ips_;}
222   // Clear the network's list of addresses.
ClearIPs()223   void ClearIPs() { ips_.clear(); }
224 
225   // Returns the scope-id of the network's address.
226   // Should only be relevant for link-local IPv6 addresses.
scope_id()227   int scope_id() const { return scope_id_; }
set_scope_id(int id)228   void set_scope_id(int id) { scope_id_ = id; }
229 
230   // Indicates whether this network should be ignored, perhaps because
231   // the IP is 0, or the interface is one we know is invalid.
ignored()232   bool ignored() const { return ignored_; }
set_ignored(bool ignored)233   void set_ignored(bool ignored) { ignored_ = ignored; }
234 
type()235   AdapterType type() const { return type_; }
preference()236   int preference() const { return preference_; }
set_preference(int preference)237   void set_preference(int preference) { preference_ = preference; }
238 
239   // Debugging description of this network
240   std::string ToString() const;
241 
242  private:
243   std::string name_;
244   std::string description_;
245   IPAddress prefix_;
246   int prefix_length_;
247   std::string key_;
248   std::vector<InterfaceAddress> ips_;
249   int scope_id_;
250   bool ignored_;
251   AdapterType type_;
252   int preference_;
253 
254   friend class NetworkManager;
255 };
256 
257 }  // namespace rtc
258 
259 #endif  // WEBRTC_BASE_NETWORK_H_
260