Merge "init: remove Parser singleton and related cleanup"
diff --git a/adb/adbd_auth.cpp b/adb/adbd_auth.cpp
index b5f87be..3488ad1 100644
--- a/adb/adbd_auth.cpp
+++ b/adb/adbd_auth.cpp
@@ -217,8 +217,8 @@
     send_packet(p, t);
 }
 
-void adbd_auth_verified(atransport *t)
-{
+void adbd_auth_verified(atransport* t) {
+    LOG(INFO) << "adb client authorized";
     handle_online(t);
     send_connect(t);
 }
diff --git a/adb/daemon/usb.cpp b/adb/daemon/usb.cpp
index d3b2f3d..0f92282 100644
--- a/adb/daemon/usb.cpp
+++ b/adb/daemon/usb.cpp
@@ -235,6 +235,8 @@
 };
 
 bool init_functionfs(struct usb_handle* h) {
+    LOG(INFO) << "initializing functionfs";
+
     ssize_t ret;
     struct desc_v1 v1_descriptor;
     struct desc_v2 v2_descriptor;
@@ -255,10 +257,10 @@
     v2_descriptor.os_desc = os_desc_compat;
 
     if (h->control < 0) { // might have already done this before
-        D("OPENING %s", USB_FFS_ADB_EP0);
+        LOG(INFO) << "opening control endpoint " << USB_FFS_ADB_EP0;
         h->control = adb_open(USB_FFS_ADB_EP0, O_RDWR);
         if (h->control < 0) {
-            D("[ %s: cannot open control endpoint: errno=%d]", USB_FFS_ADB_EP0, errno);
+            PLOG(ERROR) << "cannot open control endpoint " << USB_FFS_ADB_EP0;
             goto err;
         }
 
@@ -289,13 +291,13 @@
 
     h->bulk_out = adb_open(USB_FFS_ADB_OUT, O_RDWR);
     if (h->bulk_out < 0) {
-        D("[ %s: cannot open bulk-out ep: errno=%d ]", USB_FFS_ADB_OUT, errno);
+        PLOG(ERROR) << "cannot open bulk-out endpoint " << USB_FFS_ADB_OUT;
         goto err;
     }
 
     h->bulk_in = adb_open(USB_FFS_ADB_IN, O_RDWR);
     if (h->bulk_in < 0) {
-        D("[ %s: cannot open bulk-in ep: errno=%d ]", USB_FFS_ADB_IN, errno);
+        PLOG(ERROR) << "cannot open bulk-in endpoint " << USB_FFS_ADB_IN;
         goto err;
     }
 
@@ -356,12 +358,13 @@
 
         while (true) {
             if (init_functionfs(usb)) {
+                LOG(INFO) << "functionfs successfully initialized";
                 break;
             }
             std::this_thread::sleep_for(1s);
         }
 
-        D("[ usb_thread - registering device ]");
+        LOG(INFO) << "registering usb transport";
         register_usb_transport(usb, 0, 0, 1);
     }
 
@@ -430,6 +433,8 @@
 }
 
 static void usb_ffs_close(usb_handle* h) {
+    LOG(INFO) << "closing functionfs transport";
+
     h->kicked = false;
     adb_close(h->bulk_out);
     adb_close(h->bulk_in);
diff --git a/adb/transport_usb.cpp b/adb/transport_usb.cpp
index 2f46920..7e8ae67 100644
--- a/adb/transport_usb.cpp
+++ b/adb/transport_usb.cpp
@@ -120,24 +120,24 @@
 static int remote_read(apacket *p, atransport *t)
 {
     if (usb_read(t->usb, &p->msg, sizeof(amessage))) {
-        D("remote usb: read terminated (message)");
+        PLOG(ERROR) << "remote usb: read terminated (message)";
         return -1;
     }
 
     if (!check_header(p, t)) {
-        D("remote usb: check_header failed");
+        LOG(ERROR) << "remote usb: check_header failed";
         return -1;
     }
 
     if (p->msg.data_length) {
         if (usb_read(t->usb, p->data, p->msg.data_length)) {
-            D("remote usb: terminated (data)");
+            PLOG(ERROR) << "remote usb: terminated (data)";
             return -1;
         }
     }
 
     if (!check_data(p)) {
-        D("remote usb: check_data failed");
+        LOG(ERROR) << "remote usb: check_data failed";
         return -1;
     }
 
@@ -150,12 +150,12 @@
     unsigned size = p->msg.data_length;
 
     if (usb_write(t->usb, &p->msg, sizeof(amessage))) {
-        D("remote usb: 1 - write terminated");
+        PLOG(ERROR) << "remote usb: 1 - write terminated";
         return -1;
     }
-    if(p->msg.data_length == 0) return 0;
+    if (p->msg.data_length == 0) return 0;
     if (usb_write(t->usb, &p->data, size)) {
-        D("remote usb: 2 - write terminated");
+        PLOG(ERROR) << "remote usb: 2 - write terminated";
         return -1;
     }
 
diff --git a/init/Android.bp b/init/Android.bp
index 6e95baa..0d7240e 100644
--- a/init/Android.bp
+++ b/init/Android.bp
@@ -18,7 +18,7 @@
     name: "init_defaults",
     cpp_std: "experimental",
     sanitize: {
-        misc_undefined: ["integer"],
+        misc_undefined: ["signed-integer-overflow"],
     },
     cppflags: [
         "-DLOG_UEVENTS=0",
diff --git a/init/Android.mk b/init/Android.mk
index ad17f79..f30c2a4 100644
--- a/init/Android.mk
+++ b/init/Android.mk
@@ -99,5 +99,5 @@
     ln -sf ../init $(TARGET_ROOT_OUT)/sbin/ueventd; \
     ln -sf ../init $(TARGET_ROOT_OUT)/sbin/watchdogd
 
-LOCAL_SANITIZE := integer
+LOCAL_SANITIZE := signed-integer-overflow
 include $(BUILD_EXECUTABLE)
diff --git a/init/reboot.cpp b/init/reboot.cpp
index 17e3576..ce81483 100644
--- a/init/reboot.cpp
+++ b/init/reboot.cpp
@@ -398,7 +398,7 @@
         LOG(INFO) << "terminating init services";
 
         // Ask all services to terminate except shutdown critical ones.
-        ServiceManager::GetInstance().ForEachService([](Service* s) {
+        ServiceManager::GetInstance().ForEachServiceShutdownOrder([](Service* s) {
             if (!s->IsShutdownCritical()) s->Terminate();
         });
 
@@ -434,7 +434,7 @@
 
     // minimum safety steps before restarting
     // 2. kill all services except ones that are necessary for the shutdown sequence.
-    ServiceManager::GetInstance().ForEachService([](Service* s) {
+    ServiceManager::GetInstance().ForEachServiceShutdownOrder([](Service* s) {
         if (!s->IsShutdownCritical()) s->Stop();
     });
     ServiceManager::GetInstance().ReapAnyOutstandingChildren();
@@ -448,7 +448,7 @@
         LOG(INFO) << "vold not running, skipping vold shutdown";
     }
     // logcat stopped here
-    ServiceManager::GetInstance().ForEachService([&kill_after_apps](Service* s) {
+    ServiceManager::GetInstance().ForEachServiceShutdownOrder([&kill_after_apps](Service* s) {
         if (kill_after_apps.count(s->name())) s->Stop();
     });
     // 4. sync, try umount, and optionally run fsck for user shutdown
diff --git a/init/service.cpp b/init/service.cpp
index fc64db6..d0a0751 100644
--- a/init/service.cpp
+++ b/init/service.cpp
@@ -155,6 +155,8 @@
     : name(name), value(value) {
 }
 
+unsigned long Service::next_start_order_ = 1;
+
 Service::Service(const std::string& name, const std::vector<std::string>& args)
     : Service(name, 0, 0, 0, {}, 0, 0, "", args) {}
 
@@ -182,6 +184,7 @@
       swappiness_(-1),
       soft_limit_in_bytes_(-1),
       limit_in_bytes_(-1),
+      start_order_(0),
       args_(args) {
     onrestart_.InitSingleTrigger("onrestart");
 }
@@ -225,8 +228,8 @@
     if (capabilities_.any() && uid_) {
         // If Android is running in a container, some securebits might already
         // be locked, so don't change those.
-        int64_t securebits = prctl(PR_GET_SECUREBITS);
-        if (securebits == -1) {
+        unsigned long securebits = prctl(PR_GET_SECUREBITS);
+        if (securebits == -1UL) {
             PLOG(FATAL) << "prctl(PR_GET_SECUREBITS) failed for " << name_;
         }
         securebits |= SECBIT_KEEP_CAPS | SECBIT_KEEP_CAPS_LOCKED;
@@ -283,6 +286,7 @@
 
     pid_ = 0;
     flags_ &= (~SVC_RUNNING);
+    start_order_ = 0;
 
     // Oneshot processes go into the disabled state on exit,
     // except when manually restarted.
@@ -805,6 +809,7 @@
     time_started_ = boot_clock::now();
     pid_ = pid;
     flags_ |= SVC_RUNNING;
+    start_order_ = next_start_order_++;
     process_cgroup_empty_ = false;
 
     errno = -createProcessGroup(uid_, pid_);
@@ -1096,6 +1101,19 @@
     }
 }
 
+// Shutdown services in the opposite order that they were started.
+void ServiceManager::ForEachServiceShutdownOrder(const std::function<void(Service*)>& callback) const {
+    std::vector<Service*> shutdown_services;
+    for (const auto& service : services_) {
+        if (service->start_order() > 0) shutdown_services.emplace_back(service.get());
+    }
+    std::sort(shutdown_services.begin(), shutdown_services.end(),
+              [](const auto& a, const auto& b) { return a->start_order() > b->start_order(); });
+    for (const auto& service : shutdown_services) {
+        callback(service);
+    }
+}
+
 void ServiceManager::ForEachServiceInClass(const std::string& classname,
                                            void (*func)(Service* svc)) const {
     for (const auto& s : services_) {
diff --git a/init/service.h b/init/service.h
index 10e19d9..976f431 100644
--- a/init/service.h
+++ b/init/service.h
@@ -108,6 +108,7 @@
     int priority() const { return priority_; }
     int oom_score_adjust() const { return oom_score_adjust_; }
     bool process_cgroup_empty() const { return process_cgroup_empty_; }
+    unsigned long start_order() const { return start_order_; }
     const std::vector<std::string>& args() const { return args_; }
 
   private:
@@ -149,6 +150,8 @@
     template <typename T>
     bool AddDescriptor(const std::vector<std::string>& args, std::string* err);
 
+    static unsigned long next_start_order_;
+
     std::string name_;
     std::set<std::string> classnames_;
     std::string console_;
@@ -190,6 +193,8 @@
 
     bool process_cgroup_empty_ = false;
 
+    unsigned long start_order_;
+
     std::vector<std::string> args_;
 };
 
@@ -209,6 +214,7 @@
     Service* FindServiceByPid(pid_t pid) const;
     Service* FindServiceByKeychord(int keychord_id) const;
     void ForEachService(const std::function<void(Service*)>& callback) const;
+    void ForEachServiceShutdownOrder(const std::function<void(Service*)>& callback) const;
     void ForEachServiceInClass(const std::string& classname,
                                void (*func)(Service* svc)) const;
     void ForEachServiceWithFlags(unsigned matchflags,
diff --git a/rootdir/init.rc b/rootdir/init.rc
index 9301743..7644d28 100644
--- a/rootdir/init.rc
+++ b/rootdir/init.rc
@@ -314,7 +314,6 @@
     # Make sure /sys/kernel/debug (if present) is labeled properly
     # Note that tracefs may be mounted under debug, so we need to cross filesystems
     restorecon --recursive --cross-filesystems /sys/kernel/debug
-    chmod 0755 /sys/kernel/debug/tracing
 
     # We chown/chmod /cache again so because mount is run as root + defaults
     chown system cache /cache
@@ -352,6 +351,10 @@
     mkdir /cache/lost+found 0770 root root
 
 on late-fs
+    # Ensure that tracefs has the correct permissions.
+    # This does not work correctly if it is called in post-fs.
+    chmod 0755 /sys/kernel/debug/tracing
+
     # HALs required before storage encryption can get unlocked (FBE/FDE)
     class_start early_hal
 
@@ -377,12 +380,12 @@
     # create basic filesystem structure
     mkdir /data/misc 01771 system misc
     mkdir /data/misc/recovery 0770 system log
-    copy /data/misc/recovery/default.prop /data/misc/recovery/default.prop.1
-    chmod 0440 /data/misc/recovery/default.prop.1
-    chown system log /data/misc/recovery/default.prop.1
-    copy /default.prop /data/misc/recovery/default.prop
-    chmod 0440 /data/misc/recovery/default.prop
-    chown system log /data/misc/recovery/default.prop
+    copy /data/misc/recovery/ro.build.fingerprint /data/misc/recovery/ro.build.fingerprint.1
+    chmod 0440 /data/misc/recovery/ro.build.fingerprint.1
+    chown system log /data/misc/recovery/ro.build.fingerprint.1
+    write /data/misc/recovery/ro.build.fingerprint ${ro.build.fingerprint}
+    chmod 0440 /data/misc/recovery/ro.build.fingerprint
+    chown system log /data/misc/recovery/ro.build.fingerprint
     mkdir /data/misc/recovery/proc 0770 system log
     copy /data/misc/recovery/proc/version /data/misc/recovery/proc/version.1
     chmod 0440 /data/misc/recovery/proc/version.1