Add a timeout for all installd operations.

Bug: 216514270
Test: atest installd_utils_test
Test: atest installd_dexopt_test
Change-Id: I6c25e1df756ca486de1c8611185dbedf60d7cd7d
Merged-In: I6c25e1df756ca486de1c8611185dbedf60d7cd7d
(cherry picked from commit 495142ac75cdb2595a61755d7ab42a748e651728)
diff --git a/cmds/installd/view_compiler.cpp b/cmds/installd/view_compiler.cpp
index 60d6492..8c000a1 100644
--- a/cmds/installd/view_compiler.cpp
+++ b/cmds/installd/view_compiler.cpp
@@ -33,7 +33,13 @@
 namespace android {
 namespace installd {
 
-using base::unique_fd;
+namespace {
+
+using ::android::base::unique_fd;
+
+constexpr int kTimeoutMs = 300000;
+
+} // namespace
 
 bool view_compiler(const char* apk_path, const char* package_name, const char* out_dex_file,
                    int uid) {
@@ -88,7 +94,17 @@
         _exit(1);
     }
 
-    return wait_child(pid) == 0;
+    int return_code = wait_child_with_timeout(pid, kTimeoutMs);
+    if (!WIFEXITED(return_code)) {
+        LOG(WARNING) << "viewcompiler failed for " << package_name << ":" << apk_path;
+        if (WTERMSIG(return_code) == SIGKILL) {
+            // If the subprocess is killed while it's writing to the file, the file is likely
+            // corrupted, so we should remove it.
+            remove_file_at_fd(outfd.get());
+        }
+        return false;
+    }
+    return WEXITSTATUS(return_code) == 0;
 }
 
 } // namespace installd