Start the iptables and ip6tables processes in parallel.

This saves ~30ms on boot.

There should be no races between the threads that start the
and the main thread because pthread_join is documented to
synchronize memory with respect to other threads.

Bug: 28362720
Test: bullhead builds, boots
Test: netd_{unit,integration}_test pass
Change-Id: I24d83b880bd011bc801178f57f46d90f36621f9f
diff --git a/server/IptablesRestoreController.cpp b/server/IptablesRestoreController.cpp
index 406983a..e346b82 100644
--- a/server/IptablesRestoreController.cpp
+++ b/server/IptablesRestoreController.cpp
@@ -112,9 +112,12 @@
     static constexpr size_t STDERR_IDX = 1;
 };
 
-IptablesRestoreController::IptablesRestoreController() :
-    mIpRestore(nullptr),
-    mIp6Restore(nullptr) {
+IptablesRestoreController::IptablesRestoreController() {
+    // Start the IPv4 and IPv6 processes in parallel, since each one takes 20-30ms.
+    std::thread v4([this] () { mIpRestore.reset(forkAndExec(IPTABLES_PROCESS)); });
+    std::thread v6([this] () { mIp6Restore.reset(forkAndExec(IP6TABLES_PROCESS)); });
+    v4.join();
+    v6.join();
 }
 
 IptablesRestoreController::~IptablesRestoreController() {