blob: e2c0d49021832ab0ad99ace74874d411c6bbfe0f [file] [log] [blame]
Ben Chanfad4a0b2012-04-18 15:49:59 -07001// Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
Darin Petkov50308cd2011-06-01 18:25:07 -07002// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "shill/dhcpcd_proxy.h"
6
Paul Stewart3095c072012-12-14 08:05:07 -08007#include <dbus/dbus.h>
8#include <string.h>
9
Christopher Wileyb691efd2012-08-09 13:51:51 -070010#include <limits>
Darin Petkov50308cd2011-06-01 18:25:07 -070011
Darin Petkovd1b715b2011-06-02 21:21:22 -070012#include "shill/dhcp_provider.h"
Christopher Wileyb691efd2012-08-09 13:51:51 -070013#include "shill/logging.h"
Darin Petkovd1b715b2011-06-02 21:21:22 -070014
15using std::string;
Darin Petkove7cb7f82011-06-03 13:21:51 -070016using std::vector;
Darin Petkovd1b715b2011-06-02 21:21:22 -070017
Darin Petkov50308cd2011-06-01 18:25:07 -070018namespace shill {
19
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -070020namespace Logging {
21static auto kModuleLogScope = ScopeLogger::kDHCP;
22static string ObjectID(DHCPCDProxy *d) { return "(dhcpcd_proxy)"; }
23}
24
Darin Petkov50308cd2011-06-01 18:25:07 -070025const char DHCPCDProxy::kDBusInterfaceName[] = "org.chromium.dhcpcd";
26const char DHCPCDProxy::kDBusPath[] = "/org/chromium/dhcpcd";
27
Darin Petkovaceede32011-07-18 15:32:38 -070028DHCPCDListener::DHCPCDListener(DBus::Connection *connection,
29 DHCPProvider *provider)
30 : proxy_(connection, provider) {}
31
32DHCPCDListener::Proxy::Proxy(DBus::Connection *connection,
33 DHCPProvider *provider)
Darin Petkov50308cd2011-06-01 18:25:07 -070034 : DBus::InterfaceProxy(DHCPCDProxy::kDBusInterfaceName),
Darin Petkovd1b715b2011-06-02 21:21:22 -070035 DBus::ObjectProxy(*connection, DHCPCDProxy::kDBusPath),
36 provider_(provider) {
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -070037 SLOG(DHCP, nullptr, 2) << __func__;
Darin Petkovaceede32011-07-18 15:32:38 -070038 connect_signal(DHCPCDListener::Proxy, Event, EventSignal);
39 connect_signal(DHCPCDListener::Proxy, StatusChanged, StatusChangedSignal);
Darin Petkov50308cd2011-06-01 18:25:07 -070040}
41
Ben Chan5ea763b2014-08-13 11:07:54 -070042DHCPCDListener::Proxy::~Proxy() {}
43
Darin Petkovaceede32011-07-18 15:32:38 -070044void DHCPCDListener::Proxy::EventSignal(const DBus::SignalMessage &signal) {
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -070045 SLOG(DBus, nullptr, 2) << __func__;
Darin Petkov50308cd2011-06-01 18:25:07 -070046 DBus::MessageIter ri = signal.reader();
Christopher Wileyb691efd2012-08-09 13:51:51 -070047 unsigned int pid = std::numeric_limits<unsigned int>::max();
Gary Morain610977f2012-05-04 16:03:52 -070048 try {
49 ri >> pid;
50 } catch (const DBus::Error &e) {
51 LOG(FATAL) << "DBus exception: " << e.name() << ": " << e.what()
52 << " interface: " << signal.interface()
53 << " member: " << signal.member() << " path: " << signal.path();
54 }
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -070055 SLOG(DHCP, nullptr, 2) << "sender(" << signal.sender()
56 << ") pid(" << pid << ")";
Darin Petkovd1b715b2011-06-02 21:21:22 -070057
58 DHCPConfigRefPtr config = provider_->GetConfig(pid);
59 if (!config.get()) {
60 LOG(ERROR) << "Unknown DHCP client PID " << pid;
61 return;
62 }
Darin Petkovaceede32011-07-18 15:32:38 -070063 config->InitProxy(signal.sender());
Darin Petkove7cb7f82011-06-03 13:21:51 -070064
65 string reason;
Gary Morain610977f2012-05-04 16:03:52 -070066 try {
Darin Petkove7cb7f82011-06-03 13:21:51 -070067 ri >> reason;
Gary Morain610977f2012-05-04 16:03:52 -070068 } catch (const DBus::Error &e) {
69 LOG(FATAL) << "DBus exception: " << e.name() << ": " << e.what()
70 << " interface: " << signal.interface()
71 << " member: " << signal.member() << " path: " << signal.path();
72 }
Darin Petkove7cb7f82011-06-03 13:21:51 -070073 DHCPConfig::Configuration configuration;
Gary Morain610977f2012-05-04 16:03:52 -070074 try {
75 ri >> configuration;
76 } catch (const DBus::Error &e) {
77 LOG(FATAL) << "DBus exception: " << e.name() << ": " << e.what()
78 << " interface: " << signal.interface()
79 << " member: " << signal.member() << " path: " << signal.path();
80 }
Darin Petkove7cb7f82011-06-03 13:21:51 -070081 config->ProcessEventSignal(reason, configuration);
Darin Petkov50308cd2011-06-01 18:25:07 -070082}
83
Darin Petkovaceede32011-07-18 15:32:38 -070084void DHCPCDListener::Proxy::StatusChangedSignal(
85 const DBus::SignalMessage &signal) {
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -070086 SLOG(DBus, nullptr, 2) << __func__;
Darin Petkov50308cd2011-06-01 18:25:07 -070087 DBus::MessageIter ri = signal.reader();
Christopher Wileyb691efd2012-08-09 13:51:51 -070088 unsigned int pid = std::numeric_limits<unsigned int>::max();
Gary Morain610977f2012-05-04 16:03:52 -070089 try {
90 ri >> pid;
91 } catch (const DBus::Error &e) {
92 LOG(FATAL) << "DBus exception: " << e.name() << ": " << e.what()
93 << " interface: " << signal.interface()
94 << " member: " << signal.member() << " path: " << signal.path();
95 }
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -070096 SLOG(DHCP, nullptr, 2) << "sender(" << signal.sender()
97 << ") pid(" << pid << ")";
Darin Petkovd1b715b2011-06-02 21:21:22 -070098
99 // Accept StatusChanged signals just to get the sender address and create an
100 // appropriate proxy for the PID/sender pair.
101 DHCPConfigRefPtr config = provider_->GetConfig(pid);
102 if (!config.get()) {
103 LOG(ERROR) << "Unknown DHCP client PID " << pid;
104 return;
105 }
Darin Petkovaceede32011-07-18 15:32:38 -0700106 config->InitProxy(signal.sender());
Paul Stewart3bdf1ab2014-07-17 19:22:26 -0700107
108 string status;
109 try {
110 ri >> status;
111 } catch (const DBus::Error &e) {
112 LOG(FATAL) << "DBus exception: " << e.name() << ": " << e.what()
113 << " interface: " << signal.interface()
114 << " member: " << signal.member() << " path: " << signal.path();
115 }
116 config->ProcessStatusChangeSignal(status);
Darin Petkov50308cd2011-06-01 18:25:07 -0700117}
118
Darin Petkova7b89492011-07-27 12:48:17 -0700119DHCPCDProxy::DHCPCDProxy(DBus::Connection *connection, const string &service)
Darin Petkovaceede32011-07-18 15:32:38 -0700120 : proxy_(connection, service) {
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -0700121 SLOG(this, 2) << "DHCPCDProxy(service=" << service << ").";
Darin Petkovaceede32011-07-18 15:32:38 -0700122}
Darin Petkov50308cd2011-06-01 18:25:07 -0700123
Darin Petkovaceede32011-07-18 15:32:38 -0700124void DHCPCDProxy::Rebind(const string &interface) {
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -0700125 SLOG(DBus, nullptr, 2) << __func__;
Gary Morain610977f2012-05-04 16:03:52 -0700126 try {
127 proxy_.Rebind(interface);
128 } catch (const DBus::Error &e) {
129 LOG(FATAL) << "DBus exception: " << e.name() << ": " << e.what()
130 << " interface: " << interface;
131 }
Darin Petkovaceede32011-07-18 15:32:38 -0700132}
133
134void DHCPCDProxy::Release(const string &interface) {
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -0700135 SLOG(DBus, nullptr, 2) << __func__;
Gary Morain610977f2012-05-04 16:03:52 -0700136 try {
137 proxy_.Release(interface);
138 } catch (const DBus::Error &e) {
Paul Stewartf7f7ce72012-12-14 08:05:07 -0800139 if (!strcmp(e.name(), DBUS_ERROR_SERVICE_UNKNOWN) ||
140 !strcmp(e.name(), DBUS_ERROR_NO_REPLY)) {
Paul Stewart3095c072012-12-14 08:05:07 -0800141 LOG(ERROR) << "dhcpcd daemon appears to have already exited.";
142 } else {
143 LOG(FATAL) << "DBus exception: " << e.name() << ": " << e.what()
144 << " interface: " << interface;
145 }
Gary Morain610977f2012-05-04 16:03:52 -0700146 }
Darin Petkovaceede32011-07-18 15:32:38 -0700147}
148
149DHCPCDProxy::Proxy::Proxy(DBus::Connection *connection,
Darin Petkova7b89492011-07-27 12:48:17 -0700150 const string &service)
151 : DBus::ObjectProxy(*connection, kDBusPath, service.c_str()) {
Darin Petkov50308cd2011-06-01 18:25:07 -0700152 // Don't catch signals directly in this proxy because they will be dispatched
Darin Petkovaceede32011-07-18 15:32:38 -0700153 // to the client by the DHCPCD listener.
Darin Petkov50308cd2011-06-01 18:25:07 -0700154 _signals.erase("Event");
155 _signals.erase("StatusChanged");
156}
157
Darin Petkova7b89492011-07-27 12:48:17 -0700158DHCPCDProxy::Proxy::~Proxy() {}
159
mukesh agrawal1830fa12011-09-26 14:31:40 -0700160void DHCPCDProxy::Proxy::Event(
161 const uint32_t &/*pid*/,
162 const std::string &/*reason*/,
163 const DHCPConfig::Configuration &/*configuration*/) {
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -0700164 SLOG(DBus, nullptr, 2) << __func__;
Darin Petkovd1b715b2011-06-02 21:21:22 -0700165 NOTREACHED();
Darin Petkov50308cd2011-06-01 18:25:07 -0700166}
167
mukesh agrawal1830fa12011-09-26 14:31:40 -0700168void DHCPCDProxy::Proxy::StatusChanged(const uint32_t &/*pid*/,
169 const std::string &/*status*/) {
Rebecca Silbersteinc9c31d82014-10-21 15:01:00 -0700170 SLOG(DBus, nullptr, 2) << __func__;
Darin Petkovd1b715b2011-06-02 21:21:22 -0700171 NOTREACHED();
Darin Petkov50308cd2011-06-01 18:25:07 -0700172}
173
174} // namespace shill