Double gBn/sConstructorMap

The new getBn/sConstructorMap() functions ensure that the
map is initialized before usage. For ABI compatibility (to prebuilt
HAL definition libs), the old global map is kept and checked as well.

Test: boots
Bug: 69122224
Change-Id: I32b1a612f8e841d1e7dca5335230a3dc7d589da5
diff --git a/transport/HidlPassthroughSupport.cpp b/transport/HidlPassthroughSupport.cpp
index e101e27..b79d21c 100644
--- a/transport/HidlPassthroughSupport.cpp
+++ b/transport/HidlPassthroughSupport.cpp
@@ -35,9 +35,12 @@
         // interfaceDescriptor fails
         return nullptr;
     }
-    auto func = gBsConstructorMap.get(myDescriptor, nullptr);
+    auto func = getBsConstructorMap().get(myDescriptor, nullptr);
     if (!func) {
-        return nullptr;
+        func = gBsConstructorMap.get(myDescriptor, nullptr);
+        if (!func) {
+            return nullptr;
+        }
     }
 
     sp<IBase> base = func(static_cast<void*>(iface.get()));
@@ -51,4 +54,4 @@
 
 }  // namespace details
 }  // namespace hardware
-}  // namespace android
\ No newline at end of file
+}  // namespace android
diff --git a/transport/Static.cpp b/transport/Static.cpp
index 784b835..cbe6add 100644
--- a/transport/Static.cpp
+++ b/transport/Static.cpp
@@ -29,16 +29,28 @@
 Mutex gDefaultServiceManagerLock;
 sp<android::hidl::manager::V1_0::IServiceManager> gDefaultServiceManager;
 
-ConcurrentMap<std::string, std::function<sp<IBinder>(void *)>>
-        gBnConstructorMap{};
+// Deprecated; kept for ABI compatibility. Use getBnConstructorMap.
+BnConstructorMap gBnConstructorMap{};
 
 ConcurrentMap<const ::android::hidl::base::V1_0::IBase*, wp<::android::hardware::BHwBinder>>
     gBnMap{};
 
 ConcurrentMap<wp<::android::hidl::base::V1_0::IBase>, SchedPrio> gServicePrioMap{};
 
-ConcurrentMap<std::string, std::function<sp<::android::hidl::base::V1_0::IBase>(void *)>>
-        gBsConstructorMap;
+// Deprecated; kept for ABI compatibility. Use getBsConstructorMap.
+BsConstructorMap gBsConstructorMap{};
+
+// For static executables, it is not guaranteed that gBnConstructorMap are initialized before
+// used in HAL definition libraries.
+BnConstructorMap& getBnConstructorMap() {
+    static BnConstructorMap map{};
+    return map;
+}
+
+BsConstructorMap& getBsConstructorMap() {
+    static BsConstructorMap map{};
+    return map;
+}
 
 }  // namespace details
 }  // namespace hardware
diff --git a/transport/include/hidl/HidlBinderSupport.h b/transport/include/hidl/HidlBinderSupport.h
index fc834b9..09111f4 100644
--- a/transport/include/hidl/HidlBinderSupport.h
+++ b/transport/include/hidl/HidlBinderSupport.h
@@ -330,9 +330,12 @@
         sp<IBinder> sBnObj = wBnObj.promote();
 
         if (sBnObj == nullptr) {
-            auto func = details::gBnConstructorMap.get(myDescriptor, nullptr);
+            auto func = details::getBnConstructorMap().get(myDescriptor, nullptr);
             if (!func) {
-                return nullptr;
+                func = details::gBnConstructorMap.get(myDescriptor, nullptr);
+                if (!func) {
+                    return nullptr;
+                }
             }
 
             sBnObj = sp<IBinder>(func(static_cast<void*>(ifacePtr)));
diff --git a/transport/include/hidl/Static.h b/transport/include/hidl/Static.h
index 63b06fe..0522e44 100644
--- a/transport/include/hidl/Static.h
+++ b/transport/include/hidl/Static.h
@@ -40,18 +40,22 @@
 extern ConcurrentMap<const ::android::hidl::base::V1_0::IBase*, wp<::android::hardware::BHwBinder>>
     gBnMap;
 
+using BnConstructorMap = ConcurrentMap<std::string, std::function<sp<IBinder>(void*)>>;
 // For HidlBinderSupport and autogenerated code
 // value function receives reinterpret_cast<void *>(static_cast<IFoo *>(foo)),
 // returns sp<IBinder>
-extern ConcurrentMap<std::string,
-        std::function<sp<IBinder>(void *)>> gBnConstructorMap;
+// deprecated; use getBnConstructorMap instead.
+extern BnConstructorMap gBnConstructorMap;
+BnConstructorMap& getBnConstructorMap();
 
+using BsConstructorMap = ConcurrentMap<std::string,
+        std::function<sp<::android::hidl::base::V1_0::IBase>(void*)>>;
 // For HidlPassthroughSupport and autogenerated code
 // value function receives reinterpret_cast<void *>(static_cast<IFoo *>(foo)),
 // returns sp<IBase>
-extern ConcurrentMap<std::string,
-        std::function<sp<::android::hidl::base::V1_0::IBase>(void *)>> gBsConstructorMap;
-
+// deprecated; use getBsConstructorMap instead.
+extern BsConstructorMap gBsConstructorMap;
+BsConstructorMap& getBsConstructorMap();
 }  // namespace details
 }  // namespace hardware
 }  // namespace android