blob: bd53093646e4c48e0766af5bf090332dbfbb2171 [file] [log] [blame]
Elly Jonesa44d22d2012-01-05 18:05:56 -05001// Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
Elly Jones9aa5eca2011-11-04 14:48:13 -04002// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
Elly Jones9aa5eca2011-11-04 14:48:13 -04005#include <sys/mount.h>
Elly Jonesd31aee22012-07-02 11:09:10 -04006#include <sys/stat.h>
Elly Jones9aa5eca2011-11-04 14:48:13 -04007#include <unistd.h>
8
Elly Jonese7cb5b32011-12-01 14:18:32 -05009#include <base/command_line.h>
10#include <base/logging.h>
Eric Carusocc7106c2017-04-27 14:22:42 -070011#include <brillo/daemons/dbus_daemon.h>
Alex Vakulenkoe7696532015-10-16 16:27:29 -070012#include <brillo/syslog_logging.h>
Eric Carusocc7106c2017-04-27 14:22:42 -070013#include <chromeos/dbus/service_constants.h>
Elly Jones9aa5eca2011-11-04 14:48:13 -040014#include <chromeos/libminijail.h>
Luis Hector Chavezce837b82018-05-09 18:08:38 -070015#include <chromeos/scoped_minijail.h>
Elly Jones9aa5eca2011-11-04 14:48:13 -040016
Eric Caruso63c97432017-04-27 13:23:28 -070017#include "debugd/src/debugd_dbus_adaptor.h"
Elly Jones9aa5eca2011-11-04 14:48:13 -040018
Elly Jonese7cb5b32011-12-01 14:18:32 -050019namespace {
Elly Jones9aa5eca2011-11-04 14:48:13 -040020
Andrey Pronin0f029d82018-07-11 15:25:26 -070021// For TPM 1.2 only: Directory to mount for access to tcsd socket.
22constexpr char kTcsdDir[] = "/run/tcsd";
23
Elly Jonese7cb5b32011-12-01 14:18:32 -050024// @brief Enter a VFS namespace.
25//
26// We don't want anyone other than our descendants to see our tmpfs.
27void enter_vfs_namespace() {
Luis Hector Chavezce837b82018-05-09 18:08:38 -070028 ScopedMinijail j(minijail_new());
29
30 // Create a minimalistic mount namespace with just the bare minimum required.
31 minijail_namespace_vfs(j.get());
Allen Webb2b6e35d2019-02-21 10:06:31 -080032 if (minijail_enter_pivot_root(j.get(), "/mnt/empty"))
Luis Hector Chavezce837b82018-05-09 18:08:38 -070033 LOG(FATAL) << "minijail_enter_pivot_root() failed";
34 if (minijail_bind(j.get(), "/", "/", 0))
35 LOG(FATAL) << "minijail_bind(\"/\") failed";
36 if (minijail_mount_with_data(j.get(), "none", "/proc", "proc",
37 MS_NOSUID | MS_NOEXEC | MS_NODEV, nullptr)) {
38 LOG(FATAL) << "minijail_mount_with_data(\"/proc\") failed";
39 }
40 if (minijail_bind(j.get(), "/var", "/var", 1))
41 LOG(FATAL) << "minijail_bind(\"/var\") failed";
42
Mike Frysinger25cdbe72018-08-23 01:54:00 -040043 // Hack a path for vpd until it can migrate to /var.
44 // https://crbug.com/876838
45 if (minijail_mount_with_data(j.get(), "tmpfs", "/mnt", "tmpfs",
46 MS_NOSUID | MS_NOEXEC | MS_NODEV,
47 "mode=0755,size=10M")) {
48 LOG(FATAL) << "minijail_mount_with_data(\"/mnt\") failed";
49 }
50 const char kVpdPath[] = "/mnt/stateful_partition/unencrypted/cache/vpd";
51 if (minijail_bind(j.get(), kVpdPath, kVpdPath, 1))
52 LOG(FATAL) << "minijail_bind(\"" << kVpdPath << "\") failed";
53
Luis Hector Chavezce837b82018-05-09 18:08:38 -070054 // Mount /run/dbus to be able to communicate with D-Bus.
55 if (minijail_mount_with_data(j.get(), "tmpfs", "/run", "tmpfs",
56 MS_NOSUID | MS_NOEXEC | MS_NODEV, nullptr)) {
57 LOG(FATAL) << "minijail_mount_with_data(\"/run\") failed";
58 }
59 if (minijail_bind(j.get(), "/run/dbus", "/run/dbus", 0))
60 LOG(FATAL) << "minijail_bind(\"/run/dbus\") failed";
61
David Valleaue694deb2018-07-30 17:19:11 -070062 // Mount /tmp, /run/cups, and /run/ippusb to be able to communicate with CUPS.
Piotr Pawliczek39752f32018-10-16 14:42:28 -070063 minijail_mount_tmp(j.get());
Mike Frysinger97000d82018-06-05 11:36:12 -040064 // In case we start before cups, make sure the path exists.
65 mkdir("/run/cups", 0755);
Luis Hector Chavezce837b82018-05-09 18:08:38 -070066 if (minijail_bind(j.get(), "/run/cups", "/run/cups", 0))
67 LOG(FATAL) << "minijail_bind(\"/run/cups\") failed";
David Valleaue694deb2018-07-30 17:19:11 -070068 // In case we start before upstart-socket-bridge, make sure the path exists.
69 mkdir("/run/ippusb", 0755);
70 // Mount /run/ippusb to be able to communicate with CUPS.
71 if (minijail_bind(j.get(), "/run/ippusb", "/run/ippusb", 0))
72 LOG(FATAL) << "minijail_bind(\"/run/ippusb\") failed";
Luis Hector Chavezce837b82018-05-09 18:08:38 -070073
Mike Frysinger65884e62018-07-09 13:41:26 -040074 // Since shill provides network resolution settings, bind mount it.
75 // In case we start before shill, make sure the path exists.
76 mkdir("/run/shill", 0755);
77 if (minijail_bind(j.get(), "/run/shill", "/run/shill", 0))
78 LOG(FATAL) << "minijail_bind(\"/run/shill\") failed";
79
Luis Hector Chavez2a2dc1f2018-06-08 15:36:37 -070080 // Mount /run/arc/bugreport to be able to collect ARC bug reports.
81 // In case we start before ARC, make sure the path exists.
82 mkdir("/run/arc", 0755);
83 mkdir("/run/arc/bugreport", 0755);
84 if (minijail_bind(j.get(), "/run/arc/bugreport", "/run/arc/bugreport", 0))
85 LOG(FATAL) << "minijail_bind(\"/run/arc/bugreport\") failed";
86
Junichi Uekawaf8a0c9e2018-06-29 14:36:22 +090087 // Mount /run/containers to be able to collect container stats.
88 mkdir("/run/containers", 0755);
89 if (minijail_bind(j.get(), "/run/containers", "/run/containers", 0))
90 LOG(FATAL) << "minijail_bind(\"/run/containers\") failed";
91
Chris Morinb7a32eb2019-02-19 20:06:21 -080092 // Mount /run/systemd/journal to be able to log to journald.
93 mkdir("/run/systemd", 0755);
94 mkdir("/run/systemd/journal", 0755);
95 if (minijail_bind(j.get(), "/run/systemd/journal", "/run/systemd/journal", 0))
96 LOG(FATAL) << "minijail_bind(\"/run/systemd/journal\") failed";
97
Luis Hector Chavezce837b82018-05-09 18:08:38 -070098 // Mount /dev to be able to inspect devices.
99 if (minijail_mount_with_data(j.get(), "/dev", "/dev", "bind",
100 MS_BIND | MS_REC, nullptr)) {
101 LOG(FATAL) << "minijail_mount_with_data(\"/dev\") failed";
102 }
103
104 // Mount /sys to access some logs.
105 if (minijail_mount_with_data(j.get(), "/sys", "/sys", "bind",
106 MS_BIND | MS_REC, nullptr)) {
107 LOG(FATAL) << "minijail_mount_with_data(\"/sys\") failed";
108 }
109
Andrey Pronin0f029d82018-07-11 15:25:26 -0700110 if (USE_TPM) {
111 // For TPM 1.2 only: Enable utilities that communicate with TPM via tcsd -
112 // mount directory containing tcsd socket.
113 mkdir(kTcsdDir, 0755);
114 if (minijail_bind(j.get(), kTcsdDir, kTcsdDir, 0)) {
115 LOG(FATAL) << "minijail_bind(\"" << kTcsdDir << "\") failed";
116 }
117 }
118
Luis Hector Chavezce837b82018-05-09 18:08:38 -0700119 minijail_enter(j.get());
Elly Jones9aa5eca2011-11-04 14:48:13 -0400120}
121
Eric Carusocc7106c2017-04-27 14:22:42 -0700122class Daemon : public brillo::DBusServiceDaemon {
123 public:
Eric Caruso51535852017-07-11 14:13:20 -0700124 Daemon() : DBusServiceDaemon(debugd::kDebugdServiceName) {}
Eric Carusocc7106c2017-04-27 14:22:42 -0700125
126 protected:
127 void RegisterDBusObjectsAsync(
Eric Carusob298bb42017-05-09 10:53:30 -0700128 brillo::dbus_utils::AsyncEventSequencer* sequencer) override {
Eric Caruso51535852017-07-11 14:13:20 -0700129 adaptor_.reset(new debugd::DebugdDBusAdaptor(bus_));
Eric Carusocc7106c2017-04-27 14:22:42 -0700130 adaptor_->RegisterAsync(sequencer->GetHandler(
131 "RegisterAsync() failed.", true));
132 }
133
134 private:
135 std::unique_ptr<debugd::DebugdDBusAdaptor> adaptor_;
136
137 DISALLOW_COPY_AND_ASSIGN(Daemon);
138};
Ben Chanaf125862017-02-08 23:11:18 -0800139
140} // namespace
Elly Jones9aa5eca2011-11-04 14:48:13 -0400141
Ben Chanc572aff2018-04-10 09:20:27 -0700142int main(int argc, char* argv[]) {
Alex Vakulenko274c74a2015-04-02 14:31:10 -0700143 base::CommandLine::Init(argc, argv);
Mike Frysingerb2f7ac52018-05-17 02:36:23 -0400144 brillo::InitLog(brillo::kLogToSyslog | brillo::kLogToStderrIfTty);
Elly Jonese7cb5b32011-12-01 14:18:32 -0500145 enter_vfs_namespace();
Eric Carusocc7106c2017-04-27 14:22:42 -0700146 Daemon().Run();
Elly Jones9aa5eca2011-11-04 14:48:13 -0400147 return 0;
148}