1 //
2 // Copyright (C) 2012 The Android Open Source Project
3 //
4 // Licensed under the Apache License, Version 2.0 (the "License");
5 // you may not use this file except in compliance with the License.
6 // You may obtain a copy of the License at
7 //
8 //      http://www.apache.org/licenses/LICENSE-2.0
9 //
10 // Unless required by applicable law or agreed to in writing, software
11 // distributed under the License is distributed on an "AS IS" BASIS,
12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 // See the License for the specific language governing permissions and
14 // limitations under the License.
15 //
16 
17 #include "shill/ipconfig.h"
18 
19 #include <sys/time.h>
20 
21 #include <limits>
22 
23 #if defined(__ANDROID__)
24 #include <dbus/service_constants.h>
25 #else
26 #include <chromeos/dbus/service_constants.h>
27 #endif  // __ANDROID__
28 
29 #include "shill/adaptor_interfaces.h"
30 #include "shill/control_interface.h"
31 #include "shill/error.h"
32 #include "shill/logging.h"
33 #include "shill/net/shill_time.h"
34 #include "shill/static_ip_parameters.h"
35 
36 using base::Callback;
37 using std::string;
38 
39 namespace shill {
40 
41 namespace Logging {
42 static auto kModuleLogScope = ScopeLogger::kInet;
ObjectID(IPConfig * i)43 static string ObjectID(IPConfig* i) { return i->GetRpcIdentifier(); }
44 }
45 
46 namespace {
47 
48 const time_t kDefaultLeaseExpirationTime = std::numeric_limits<long>::max();
49 
50 }  // namespace
51 
52 // static
53 const int IPConfig::kDefaultMTU = 1500;
54 const int IPConfig::kMinIPv4MTU = 576;
55 const int IPConfig::kMinIPv6MTU = 1280;
56 const int IPConfig::kUndefinedMTU = 0;
57 const char IPConfig::kType[] = "ip";
58 
59 // static
60 uint IPConfig::global_serial_ = 0;
61 
IPConfig(ControlInterface * control_interface,const std::string & device_name)62 IPConfig::IPConfig(ControlInterface* control_interface,
63                    const std::string& device_name)
64     : device_name_(device_name),
65       type_(kType),
66       serial_(global_serial_++),
67       adaptor_(control_interface->CreateIPConfigAdaptor(this)) {
68   Init();
69 }
70 
IPConfig(ControlInterface * control_interface,const std::string & device_name,const std::string & type)71 IPConfig::IPConfig(ControlInterface* control_interface,
72                    const std::string& device_name,
73                    const std::string& type)
74     : device_name_(device_name),
75       type_(type),
76       serial_(global_serial_++),
77       adaptor_(control_interface->CreateIPConfigAdaptor(this)) {
78   Init();
79 }
80 
Init()81 void IPConfig::Init() {
82   store_.RegisterConstString(kAddressProperty, &properties_.address);
83   store_.RegisterConstString(kBroadcastProperty,
84                              &properties_.broadcast_address);
85   store_.RegisterConstString(kDomainNameProperty, &properties_.domain_name);
86   store_.RegisterConstString(kAcceptedHostnameProperty,
87                              &properties_.accepted_hostname);
88   store_.RegisterConstString(kGatewayProperty, &properties_.gateway);
89   store_.RegisterConstString(kMethodProperty, &properties_.method);
90   store_.RegisterConstInt32(kMtuProperty, &properties_.mtu);
91   store_.RegisterConstStrings(kNameServersProperty, &properties_.dns_servers);
92   store_.RegisterConstString(kPeerAddressProperty, &properties_.peer_address);
93   store_.RegisterConstInt32(kPrefixlenProperty, &properties_.subnet_prefix);
94   store_.RegisterConstStrings(kSearchDomainsProperty,
95                               &properties_.domain_search);
96   store_.RegisterConstByteArray(kVendorEncapsulatedOptionsProperty,
97                                 &properties_.vendor_encapsulated_options);
98   store_.RegisterConstString(kWebProxyAutoDiscoveryUrlProperty,
99                              &properties_.web_proxy_auto_discovery);
100   store_.RegisterConstString(kDelegatedPrefixProperty,
101                              &properties_.delegated_prefix);
102   store_.RegisterConstInt32(kDelegatedPrefixLengthProperty,
103                             &properties_.delegated_prefix_length);
104   store_.RegisterConstUint32(kLeaseDurationSecondsProperty,
105                              &properties_.lease_duration_seconds);
106   time_ = Time::GetInstance();
107   current_lease_expiration_time_ = {kDefaultLeaseExpirationTime, 0};
108   SLOG(this, 2) << __func__ << " device: " << device_name();
109 }
110 
~IPConfig()111 IPConfig::~IPConfig() {
112   SLOG(this, 2) << __func__ << " device: " << device_name();
113 }
114 
GetRpcIdentifier()115 string IPConfig::GetRpcIdentifier() {
116   return adaptor_->GetRpcIdentifier();
117 }
118 
RequestIP()119 bool IPConfig::RequestIP() {
120   return false;
121 }
122 
RenewIP()123 bool IPConfig::RenewIP() {
124   return false;
125 }
126 
ReleaseIP(ReleaseReason reason)127 bool IPConfig::ReleaseIP(ReleaseReason reason) {
128   return false;
129 }
130 
Refresh(Error *)131 void IPConfig::Refresh(Error* /*error*/) {
132   if (!refresh_callback_.is_null()) {
133     refresh_callback_.Run(this);
134   }
135   RenewIP();
136 }
137 
ApplyStaticIPParameters(StaticIPParameters * static_ip_parameters)138 void IPConfig::ApplyStaticIPParameters(
139     StaticIPParameters* static_ip_parameters) {
140   static_ip_parameters->ApplyTo(&properties_);
141   EmitChanges();
142 }
143 
RestoreSavedIPParameters(StaticIPParameters * static_ip_parameters)144 void IPConfig::RestoreSavedIPParameters(
145     StaticIPParameters* static_ip_parameters) {
146   static_ip_parameters->RestoreTo(&properties_);
147   EmitChanges();
148 }
149 
UpdateLeaseExpirationTime(uint32_t new_lease_duration)150 void IPConfig::UpdateLeaseExpirationTime(uint32_t new_lease_duration) {
151   struct timeval new_expiration_time;
152   time_->GetTimeBoottime(&new_expiration_time);
153   new_expiration_time.tv_sec += new_lease_duration;
154   current_lease_expiration_time_ = new_expiration_time;
155 }
156 
ResetLeaseExpirationTime()157 void IPConfig::ResetLeaseExpirationTime() {
158   current_lease_expiration_time_ = {kDefaultLeaseExpirationTime, 0};
159 }
160 
TimeToLeaseExpiry(uint32_t * time_left)161 bool IPConfig::TimeToLeaseExpiry(uint32_t* time_left) {
162   if (current_lease_expiration_time_.tv_sec == kDefaultLeaseExpirationTime) {
163     SLOG(this, 2) << __func__ << ": No current DHCP lease";
164     return false;
165   }
166   struct timeval now;
167   time_->GetTimeBoottime(&now);
168   if (now.tv_sec > current_lease_expiration_time_.tv_sec) {
169     SLOG(this, 2) << __func__ << ": Current DHCP lease has already expired";
170     return false;
171   }
172   *time_left = current_lease_expiration_time_.tv_sec - now.tv_sec;
173   return true;
174 }
175 
UpdateProperties(const Properties & properties,bool new_lease_acquired)176 void IPConfig::UpdateProperties(const Properties& properties,
177                                 bool new_lease_acquired) {
178   // Take a reference of this instance to make sure we don't get destroyed in
179   // the middle of this call. (The |update_callback_| may cause a reference
180   // to be dropped. See, e.g., EthernetService::Disconnect and
181   // Ethernet::DropConnection.)
182   IPConfigRefPtr me = this;
183 
184   properties_ = properties;
185 
186   if (!update_callback_.is_null()) {
187     update_callback_.Run(this, new_lease_acquired);
188   }
189   EmitChanges();
190 }
191 
UpdateDNSServers(const std::vector<std::string> & dns_servers)192 void IPConfig::UpdateDNSServers(const std::vector<std::string>& dns_servers) {
193   properties_.dns_servers = dns_servers;
194   EmitChanges();
195 }
196 
NotifyFailure()197 void IPConfig::NotifyFailure() {
198   // Take a reference of this instance to make sure we don't get destroyed in
199   // the middle of this call. (The |update_callback_| may cause a reference
200   // to be dropped. See, e.g., EthernetService::Disconnect and
201   // Ethernet::DropConnection.)
202   IPConfigRefPtr me = this;
203 
204   if (!failure_callback_.is_null()) {
205     failure_callback_.Run(this);
206   }
207 }
208 
NotifyExpiry()209 void IPConfig::NotifyExpiry() {
210   if (!expire_callback_.is_null()) {
211     expire_callback_.Run(this);
212   }
213 }
214 
RegisterUpdateCallback(const UpdateCallback & callback)215 void IPConfig::RegisterUpdateCallback(const UpdateCallback& callback) {
216   update_callback_ = callback;
217 }
218 
RegisterFailureCallback(const Callback & callback)219 void IPConfig::RegisterFailureCallback(const Callback& callback) {
220   failure_callback_ = callback;
221 }
222 
RegisterRefreshCallback(const Callback & callback)223 void IPConfig::RegisterRefreshCallback(const Callback& callback) {
224   refresh_callback_ = callback;
225 }
226 
RegisterExpireCallback(const Callback & callback)227 void IPConfig::RegisterExpireCallback(const Callback& callback) {
228   expire_callback_ = callback;
229 }
230 
ResetProperties()231 void IPConfig::ResetProperties() {
232   properties_ = Properties();
233   EmitChanges();
234 }
235 
EmitChanges()236 void IPConfig::EmitChanges() {
237   adaptor_->EmitStringChanged(kAddressProperty, properties_.address);
238   adaptor_->EmitStringsChanged(kNameServersProperty, properties_.dns_servers);
239 }
240 
241 }  // namespace shill
242