Merge "ueventd: don't double fork firmware handlers" am: 0f4fb5497a
am: e944b7e0a4

Change-Id: Ifc8c586aa3b06ecb42bf20284c461b4b7c159bc7
diff --git a/init/firmware_handler.cpp b/init/firmware_handler.cpp
index 8cd5cc5..860b30b 100644
--- a/init/firmware_handler.cpp
+++ b/init/firmware_handler.cpp
@@ -110,31 +110,16 @@
     if (uevent.subsystem != "firmware" || uevent.action != "add") return;
 
     // Loading the firmware in a child means we can do that in parallel...
-    // We double fork instead of waiting for these processes.
-    pid_t pid = fork();
+    auto pid = fork();
     if (pid == -1) {
         PLOG(ERROR) << "could not fork to process firmware event for " << uevent.firmware;
-        return;
     }
-
     if (pid == 0) {
-        pid = fork();
-        if (pid == -1) {
-            PLOG(ERROR) << "could not fork a sceond time to process firmware event for "
-                        << uevent.firmware;
-            _exit(EXIT_FAILURE);
-        }
-        if (pid == 0) {
-            Timer t;
-            ProcessFirmwareEvent(uevent);
-            LOG(INFO) << "loading " << uevent.path << " took " << t;
-            _exit(EXIT_SUCCESS);
-        }
-
+        Timer t;
+        ProcessFirmwareEvent(uevent);
+        LOG(INFO) << "loading " << uevent.path << " took " << t;
         _exit(EXIT_SUCCESS);
     }
-
-    waitpid(pid, nullptr, 0);
 }
 
 }  // namespace init
diff --git a/init/ueventd.cpp b/init/ueventd.cpp
index 81a0572..a713beb 100644
--- a/init/ueventd.cpp
+++ b/init/ueventd.cpp
@@ -268,6 +268,13 @@
         cold_boot.Run();
     }
 
+    // We use waitpid() in ColdBoot, so we can't ignore SIGCHLD until now.
+    signal(SIGCHLD, SIG_IGN);
+    // Reap and pending children that exited between the last call to waitpid() and setting SIG_IGN
+    // for SIGCHLD above.
+    while (waitpid(-1, nullptr, WNOHANG) > 0) {
+    }
+
     uevent_listener.Poll([&device_handler](const Uevent& uevent) {
         HandleFirmwareEvent(uevent);
         device_handler.HandleDeviceEvent(uevent);