Revert^3 "Merge libart and libart-compiler into a single library"

This reverts commit 4617cc65933921f40b8dd09ad630850a984486c7.

Reason for revert: app startup regressions b/296703167 b/295363008

Change-Id: Ib31df00f80c57b9c86d6d0254e795b9ad6e22e00
diff --git a/Android.mk b/Android.mk
index f0a0abe..499c98d 100644
--- a/Android.mk
+++ b/Android.mk
@@ -446,6 +446,7 @@
   lib/libadbconnection.so \
   lib/libandroidio.so \
   lib/libartbase.so \
+  lib/libart-compiler.so \
   lib/libart-dexlayout.so \
   lib/libart-disassembler.so \
   lib/libartpalette.so \
@@ -473,6 +474,7 @@
   lib64/libadbconnection.so \
   lib64/libandroidio.so \
   lib64/libartbase.so \
+  lib64/libart-compiler.so \
   lib64/libart-dexlayout.so \
   lib64/libart-disassembler.so \
   lib64/libartpalette.so \
diff --git a/build/apex/Android.bp b/build/apex/Android.bp
index b898955..2dd8ec2 100644
--- a/build/apex/Android.bp
+++ b/build/apex/Android.bp
@@ -58,6 +58,7 @@
     "libadbconnection",
     // TODO(b/124476339): Clean up the following libraries once "required"
     // dependencies work with APEX libraries.
+    "libart-compiler",
     "libdt_fd_forward",
     "libdt_socket",
     "libjdwp",
@@ -106,6 +107,7 @@
 art_runtime_debug_native_shared_libs = [
     "libadbconnectiond",
     "libartd",
+    "libartd-compiler",
     "libdexfiled",
     "libopenjdkjvmd",
     "libopenjdkjvmtid",
diff --git a/build/apex/art_apex_test.py b/build/apex/art_apex_test.py
index 0de7f49..8eb5d13 100755
--- a/build/apex/art_apex_test.py
+++ b/build/apex/art_apex_test.py
@@ -475,6 +475,7 @@
     # Check internal libraries for ART.
     self._checker.check_native_library('libadbconnection')
     self._checker.check_native_library('libart')
+    self._checker.check_native_library('libart-compiler')
     self._checker.check_native_library('libart-dexlayout')
     self._checker.check_native_library('libart-disassembler')
     self._checker.check_native_library('libartbase')
@@ -620,6 +621,7 @@
     self._checker.check_native_library('libadbconnectiond')
     self._checker.check_native_library('libartbased')
     self._checker.check_native_library('libartd')
+    self._checker.check_native_library('libartd-compiler')
     self._checker.check_native_library('libartd-dexlayout')
     self._checker.check_native_library('libartd-disassembler')
     self._checker.check_native_library('libopenjdkjvmd')
diff --git a/compiler/Android.bp b/compiler/Android.bp
index a690898..6472613 100644
--- a/compiler/Android.bp
+++ b/compiler/Android.bp
@@ -37,7 +37,6 @@
         "libartpalette",
     ],
     header_libs: [
-        "libart_headers",
         "libart_generated_headers",
     ],
 }
@@ -66,23 +65,11 @@
             ],
         },
     },
-    // In order to save memory on device `art::HGraphVisualizerDisassembler` loads
-    // `libart-disassembler.so` dynamically. Host builds of `libart-compiler` depend on
-    // `libart-disassembler` directly with `shared_libs` or `static_libs`.
-    target: {
-        host: {
-            shared: {
-                shared_libs: [
-                    "libart-disassembler",
-                ],
-            },
-        },
-        android: {
-            runtime_libs: [
-                "libart-disassembler",
-            ],
-        },
-    },
+    runtime_libs: [
+        // `art::HGraphVisualizerDisassembler::HGraphVisualizerDisassembler` may dynamically load
+        // `libart-disassembler.so`.
+        "libart-disassembler",
+    ],
 }
 
 // Dependencies of libartd-compiler, used to propagate libartd-compiler deps when static linking.
@@ -109,23 +96,11 @@
             ],
         },
     },
-    // In order to save memory on device `art::HGraphVisualizerDisassembler` loads
-    // `libartd-disassembler.so` dynamically. Host builds of `libartd-compiler` depend on
-    // `libartd-disassembler` directly with `shared_libs` or `static_libs`.
-    target: {
-        host: {
-            shared: {
-                shared_libs: [
-                    "libartd-disassembler",
-                ],
-            },
-        },
-        android: {
-            runtime_libs: [
-                "libartd-disassembler",
-            ],
-        },
-    },
+    runtime_libs: [
+        // `art::HGraphVisualizerDisassembler::HGraphVisualizerDisassembler` may dynamically load
+        // `libartd-disassembler.so`.
+        "libartd-disassembler",
+    ],
 }
 
 art_cc_defaults {
@@ -269,7 +244,14 @@
             ],
         },
     },
+    static: {
+        cflags: ["-DART_STATIC_LIBART_COMPILER"],
+    },
     generated_sources: ["art_compiler_operator_srcs"],
+    shared_libs: [
+        "libbase",
+        "liblzma", // libelffile(d) dependency; must be repeated here since it's a static lib.
+    ],
     header_libs: [
         "art_cmdlineparser_headers", // For compiler_options.
         "art_disassembler_headers",
@@ -277,6 +259,8 @@
     ],
 
     export_include_dirs: ["."],
+    // Not using .map.txt because this is an internal API
+    version_script: "libart-compiler.map",
 }
 
 cc_defaults {
@@ -301,7 +285,7 @@
     output_extension: "operator_out.cc",
 }
 
-art_cc_library_static {
+art_cc_library {
     name: "libart-compiler",
     defaults: [
         "libart-compiler-defaults",
@@ -309,6 +293,11 @@
         "art_hugepage_defaults",
         "libart-compiler_deps",
     ],
+    shared_libs: [
+        // libart is not included in libart-compiler_deps to allow libart-compiler(-for-test)
+        // select suitable libart library (either with or without LTO).
+        "libart",
+    ],
     target: {
         android: {
             lto: {
@@ -334,6 +323,9 @@
         "art_hugepage_defaults",
         "libart-compiler_deps",
     ],
+    header_libs: [
+        "libart_headers",
+    ],
 }
 
 cc_defaults {
@@ -341,6 +333,7 @@
     defaults: [
         "libart-compiler_static_base_defaults",
         "libart-disassembler_static_defaults",
+        "libart_static_defaults",
         "libartbase_static_defaults",
         "libdexfile_static_defaults",
         "libprofile_static_defaults",
@@ -356,6 +349,7 @@
     defaults: [
         "libart-compiler_static_base_defaults",
         "libart-disassembler_static_defaults",
+        "libart-for-test_static_defaults",
         "libartbase_static_defaults",
         "libdexfile_static_defaults",
         "libprofile_static_defaults",
@@ -363,13 +357,16 @@
     whole_static_libs: ["libart-compiler-for-test"],
 }
 
-art_cc_library_static {
+art_cc_library {
     name: "libartd-compiler",
     defaults: [
         "art_debug_defaults",
         "libart-compiler-defaults",
         "libartd-compiler_deps",
     ],
+    shared_libs: [
+        "libartd",
+    ],
     apex_available: [
         "com.android.art.debug",
         // TODO(b/183882457): This lib doesn't go into com.android.art, but
@@ -385,6 +382,7 @@
         "libart-compiler_static_base_defaults",
         "libartbased_static_defaults",
         "libartd-disassembler_static_defaults",
+        "libartd_static_defaults",
         "libdexfiled_static_defaults",
         "libprofiled_static_defaults",
     ],
@@ -401,34 +399,19 @@
         "libart-compiler_static_base_defaults",
         "libartbased_static_defaults",
         "libartd-disassembler_static_defaults",
+        "libartd-for-test_static_defaults",
         "libdexfiled_static_defaults",
         "libprofiled_static_defaults",
     ],
     whole_static_libs: ["libartd-compiler"],
 }
 
-// Export headers required by `libart-runtime` to use JIT from `libart-compiler`.
-cc_library_headers {
-    name: "libart-compiler_jit_headers",
-    defaults: ["art_defaults"],
-    host_supported: true,
-    export_include_dirs: ["export"],
-    apex_available: [
-        "com.android.art",
-        "com.android.art.debug",
-        "test_broken_com.android.art",
-    ],
-}
-
 // Properties common to `libart-compiler-gtest` and `libartd-compiler-gtest`.
 art_cc_defaults {
     name: "libart-compiler-gtest-common",
     srcs: [
         "common_compiler_test.cc",
     ],
-    header_libs: [
-        "libart_headers",
-    ],
 }
 
 art_cc_library_static {
diff --git a/compiler/export/jit_create.h b/compiler/export/jit_create.h
deleted file mode 100644
index 53dd45e..0000000
--- a/compiler/export/jit_create.h
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * Copyright (C) 2023 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- *      http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef ART_COMPILER_EXPORT_JIT_CREATE_H_
-#define ART_COMPILER_EXPORT_JIT_CREATE_H_
-
-#include "base/macros.h"
-
-namespace art HIDDEN {
-namespace jit {
-
-class JitCompilerInterface;
-
-// Used in `libart-runtime` to create `libart-compiler` JIT.
-JitCompilerInterface* jit_create();
-
-}  // namespace jit
-}  // namespace art
-
-#endif  // ART_COMPILER_EXPORT_JIT_CREATE_H_
diff --git a/compiler/jit/jit_compiler.cc b/compiler/jit/jit_compiler.cc
index 86c0f80..e672367 100644
--- a/compiler/jit/jit_compiler.cc
+++ b/compiler/jit/jit_compiler.cc
@@ -17,6 +17,7 @@
 #include "jit_compiler.h"
 
 #include "android-base/stringprintf.h"
+
 #include "arch/instruction_set.h"
 #include "arch/instruction_set_features.h"
 #include "art_method-inl.h"
@@ -28,7 +29,6 @@
 #include "compiler.h"
 #include "debug/elf_debug_writer.h"
 #include "driver/compiler_options.h"
-#include "export/jit_create.h"
 #include "jit/debugger_interface.h"
 #include "jit/jit.h"
 #include "jit/jit_code_cache.h"
@@ -125,7 +125,7 @@
   }
 }
 
-JitCompilerInterface* jit_create() {
+EXPORT extern "C" JitCompilerInterface* jit_load() {
   VLOG(jit) << "Create jit compiler";
   auto* const jit_compiler = JitCompiler::Create();
   CHECK(jit_compiler != nullptr);
diff --git a/compiler/libart-compiler.map b/compiler/libart-compiler.map
new file mode 100644
index 0000000..f66052a
--- /dev/null
+++ b/compiler/libart-compiler.map
@@ -0,0 +1,34 @@
+#
+# Copyright (C) 2022 The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+#      http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+#
+
+ART_COMPILER {
+  global:
+    extern "C++" {
+      art::debug::MakeMiniDebugInfo*;
+      *art::debug::WriteDebugInfo*;
+      art::Compiler::Create*;
+      art::CompilerOptions::*;
+      art::CreateTrampoline*;
+      art::IntrinsicObjects::*;
+      art::linker::operator*art::linker::LinkerPatch::Type*;
+      art::operator*art::Whence*;
+    };
+
+    jit_load;
+
+  local:
+    *;
+};
diff --git a/compiler/optimizing/graph_visualizer.cc b/compiler/optimizing/graph_visualizer.cc
index c2c0953..bd33fde 100644
--- a/compiler/optimizing/graph_visualizer.cc
+++ b/compiler/optimizing/graph_visualizer.cc
@@ -115,9 +115,7 @@
   }
 }
 
-// On target: load `libart-disassembler` only when required (to save on memory).
-// On host: `libart-disassembler` should be linked directly (either as a static or dynamic lib)
-#ifdef ART_TARGET
+#ifndef ART_STATIC_LIBART_COMPILER
 using create_disasm_prototype = Disassembler*(InstructionSet, DisassemblerOptions*);
 #endif
 
@@ -127,7 +125,7 @@
                                const uint8_t* base_address,
                                const uint8_t* end_address)
       : instruction_set_(instruction_set), disassembler_(nullptr) {
-#ifdef ART_TARGET
+#ifndef ART_STATIC_LIBART_COMPILER
     constexpr const char* libart_disassembler_so_name =
         kIsDebugBuild ? "libartd-disassembler.so" : "libart-disassembler.so";
     libart_disassembler_handle_ = dlopen(libart_disassembler_so_name, RTLD_NOW);
@@ -161,7 +159,7 @@
   ~HGraphVisualizerDisassembler() {
     // We need to call ~Disassembler() before we close the library.
     disassembler_.reset();
-#ifdef ART_TARGET
+#ifndef ART_STATIC_LIBART_COMPILER
     if (libart_disassembler_handle_ != nullptr) {
       dlclose(libart_disassembler_handle_);
     }
@@ -186,7 +184,7 @@
   InstructionSet instruction_set_;
   std::unique_ptr<Disassembler> disassembler_;
 
-#ifdef ART_TARGET
+#ifndef ART_STATIC_LIBART_COMPILER
   void* libart_disassembler_handle_;
 #endif
 };
diff --git a/dex2oat/Android.bp b/dex2oat/Android.bp
index 1807ed5..761b073 100644
--- a/dex2oat/Android.bp
+++ b/dex2oat/Android.bp
@@ -104,6 +104,7 @@
     name: "libart-dex2oat",
     defaults: ["libart-dex2oat-defaults"],
     shared_libs: [
+        "libart-compiler",
         "libart-dexlayout",
         "libart",
         "libartpalette",
@@ -126,6 +127,7 @@
         "libprofile_static_defaults",
     ],
     whole_static_libs: [
+        "libart-compiler",
         "libart-dexlayout",
         "libart-dex2oat",
     ],
@@ -139,6 +141,7 @@
     host_supported: true,
     defaults: [
         "art_defaults",
+        "libart-compiler_static_defaults",
         "libart-dex2oat_static_defaults",
         "libart-dexlayout_static_defaults",
         "libart_static_defaults",
@@ -155,6 +158,7 @@
         "libart-dex2oat-defaults",
     ],
     shared_libs: [
+        "libartd-compiler",
         "libartd-dexlayout",
         "libartd",
         "libartpalette",
@@ -176,6 +180,7 @@
         "libprofiled_static_defaults",
     ],
     whole_static_libs: [
+        "libartd-compiler",
         "libartd-dexlayout",
         "libartd-dex2oat",
     ],
@@ -188,6 +193,7 @@
     defaults: [
         "art_debug_defaults",
         "libartbased_static_defaults",
+        "libartd-compiler_static_defaults",
         "libartd-dex2oat_static_defaults",
         "libartd-dexlayout_static_defaults",
         "libartd_static_defaults",
@@ -298,6 +304,7 @@
         android: {
             shared_libs: [
                 "libart",
+                "libart-compiler",
                 "libart-dexlayout",
                 "libartbase",
                 "libdexfile",
@@ -359,6 +366,7 @@
             shared_libs: [
                 "libartbased",
                 "libartd",
+                "libartd-compiler",
                 "libartd-dexlayout",
                 "libdexfiled",
                 "libprofiled",
diff --git a/imgdiag/Android.bp b/imgdiag/Android.bp
index 7d1869f..573fea5 100644
--- a/imgdiag/Android.bp
+++ b/imgdiag/Android.bp
@@ -69,6 +69,7 @@
     shared_libs: [
         "libart",
         "libartbase",
+        "libart-compiler",
     ],
     apex_available: [
         "com.android.art",
@@ -85,6 +86,7 @@
     shared_libs: [
         "libartd",
         "libartbased",
+        "libartd-compiler",
         "libdexfiled",
     ],
     apex_available: [
diff --git a/oatdump/Android.bp b/oatdump/Android.bp
index 9c749a6..dacd647 100644
--- a/oatdump/Android.bp
+++ b/oatdump/Android.bp
@@ -40,6 +40,7 @@
     device_supported: false,
     host_supported: true,
     defaults: [
+        "libart-compiler_static_defaults",
         "libart-dexlayout_static_defaults",
         "libart-disassembler_static_defaults",
         "libart_static_defaults",
@@ -61,6 +62,7 @@
         android: {
             shared_libs: [
                 "libart",
+                "libart-compiler",
                 "libart-dexlayout",
                 "libart-disassembler",
                 "libartbase",
@@ -93,6 +95,7 @@
     device_supported: false,
     host_supported: true,
     defaults: [
+        "libartd-compiler_static_defaults",
         "libartd-dexlayout_static_defaults",
         "libartd-disassembler_static_defaults",
         "libartd_static_defaults",
@@ -118,6 +121,7 @@
             shared_libs: [
                 "libartbased",
                 "libartd",
+                "libartd-compiler",
                 "libartd-dexlayout",
                 "libartd-disassembler",
                 "libbase",
@@ -170,6 +174,7 @@
         "libartbase_static_defaults",
         "libdexfile_static_defaults",
         "libprofile_static_defaults",
+        "libart-compiler_static_defaults",
         "libart-dexlayout_static_defaults",
         "oatdumps-defaults",
     ],
@@ -187,6 +192,7 @@
         "libartbased_static_defaults",
         "libdexfiled_static_defaults",
         "libprofiled_static_defaults",
+        "libartd-compiler_static_defaults",
         "libartd-dexlayout_static_defaults",
         "oatdumps-defaults",
     ],
diff --git a/openjdkjvmti/Android.bp b/openjdkjvmti/Android.bp
index 2e2ce19..87dd681 100644
--- a/openjdkjvmti/Android.bp
+++ b/openjdkjvmti/Android.bp
@@ -114,6 +114,7 @@
     defaults: ["libopenjdkjvmti_defaults"],
     shared_libs: [
         "libart",
+        "libart-compiler",
         "libdexfile",
         "libartbase",
     ],
@@ -132,6 +133,7 @@
     ],
     shared_libs: [
         "libartd",
+        "libartd-compiler",
         "libdexfiled",
         "libartbased",
     ],
diff --git a/runtime/Android.bp b/runtime/Android.bp
index 840d173..9b67dd9 100644
--- a/runtime/Android.bp
+++ b/runtime/Android.bp
@@ -101,134 +101,10 @@
     ],
 }
 
-// Common dependencies for `libart-runtime_deps` and `libartd-runtime_deps`.
 cc_defaults {
-    name: "libart-runtime_common_deps",
+    name: "libart_defaults",
     defaults: ["art_defaults"],
     host_supported: true,
-    target: {
-        android: {
-            header_libs: [
-                "libnativeloader-headers", // For dlext_namespaces.h
-            ],
-            shared_libs: [
-                "libdl_android",
-                "libstatssocket",
-                "libz", // For adler32.
-                "heapprofd_client_api",
-            ],
-            static_libs: [
-                "libstatslog_art",
-            ],
-        },
-        host: {
-            shared_libs: [
-                "libz", // For adler32.
-            ],
-        },
-    },
-    header_libs: [
-        "art_cmdlineparser_headers",
-        "cpp-define-generator-definitions",
-        "jni_platform_headers",
-        "libart_headers",
-        "libnativehelper_header_only",
-        "libart_generated_headers",
-        // `libart-runtime` doesn't depend on all `libart-compiler` headers, it only requires
-        // `jit_create` to initialize the JIT compiler.
-        "libart-compiler_jit_headers",
-    ],
-    export_header_lib_headers: [
-        "libart_headers",
-        "libart_generated_headers",
-    ],
-    shared_libs: [
-        "libartpalette",
-        "libbase", // For common macros.
-        "liblog",
-        "liblz4",
-        "liblzma", // libelffile(d) dependency; must be repeated here since it's a static lib.
-        "libnativebridge",
-        "libnativeloader",
-        "libsigchain",
-        "libunwindstack",
-    ],
-    static_libs: ["libodrstatslog"],
-}
-
-cc_defaults {
-    name: "libart-runtime_deps",
-    defaults: ["libart-runtime_common_deps"],
-    static_libs: [
-        "libelffile",
-    ],
-    shared_libs: [
-        "libartbase",
-        "libdexfile",
-        "libprofile",
-    ],
-    export_shared_lib_headers: [
-        "libdexfile",
-    ],
-}
-
-cc_defaults {
-    name: "libartd-runtime_deps",
-    defaults: ["libart-runtime_common_deps"],
-    static_libs: [
-        "libelffiled",
-    ],
-    shared_libs: [
-        "libartbased",
-        "libdexfiled",
-        "libprofiled",
-    ],
-    export_shared_lib_headers: [
-        "libdexfiled",
-    ],
-}
-
-// Common defaults for `libart_defaults`, `libartd_defaults` and `libart-runtime_common_defaults`.
-cc_defaults {
-    name: "libart_common_defaults",
-    defaults: [
-        "art_defaults",
-        "libart_nativeunwind_defaults",
-        "art_hugepage_defaults",
-    ],
-    host_supported: true,
-    target: {
-        android_arm: {
-            ldflags: JIT_DEBUG_REGISTER_CODE_LDFLAGS,
-        },
-        android_arm64: {
-            ldflags: JIT_DEBUG_REGISTER_CODE_LDFLAGS,
-        },
-        android_x86: {
-            ldflags: JIT_DEBUG_REGISTER_CODE_LDFLAGS,
-        },
-        android_x86_64: {
-            ldflags: JIT_DEBUG_REGISTER_CODE_LDFLAGS,
-        },
-    },
-    runtime_libs: [
-        // Libraries loaded at runtime. Exceptions:
-        // - libart(d)-compiler.so and libopenjdk(d).so cannot be listed here
-        //   due to cyclic dependency.
-        // - libicu_jni.so is only loaded to handle dependency order in VM
-        //   startup (see Runtime::InitNativeMethods), but its API is internal
-        //   to com.android.i18n and not used by ART/libcore. Therefore it's not
-        //   listed here to avoid visibility issues. Instead it's linked from
-        //   the ART module namespace through an entry in requireNativeLibs in
-        //   manifest-art.json.
-        "libjavacore",
-    ],
-}
-
-// Common defaults for `libart-runtime_defaults` and `libartd-runtime_defaults`.
-cc_defaults {
-    name: "libart-runtime_common_defaults",
-    defaults: ["libart_common_defaults"],
     srcs: [
         "app_info.cc",
         "aot_class_linker.cc",
@@ -550,12 +426,36 @@
                 "thread_android.cc",
                 "metrics/statsd.cc",
             ],
+            header_libs: [
+                "libnativeloader-headers", // For dlext_namespaces.h
+            ],
+            shared_libs: [
+                "libdl_android",
+                "libstatssocket",
+                "libz", // For adler32.
+                "heapprofd_client_api",
+            ],
+            static_libs: [
+                "libstatslog_art",
+            ],
             generated_sources: [
                 "apex-info-list-tinyxml",
                 "art-apex-cache-info",
             ],
             tidy_disabled_srcs: [":art-apex-cache-info"],
         },
+        android_arm: {
+            ldflags: JIT_DEBUG_REGISTER_CODE_LDFLAGS,
+        },
+        android_arm64: {
+            ldflags: JIT_DEBUG_REGISTER_CODE_LDFLAGS,
+        },
+        android_x86: {
+            ldflags: JIT_DEBUG_REGISTER_CODE_LDFLAGS,
+        },
+        android_x86_64: {
+            ldflags: JIT_DEBUG_REGISTER_CODE_LDFLAGS,
+        },
         host: {
             srcs: [
                 "monitor_linux.cc",
@@ -566,49 +466,56 @@
                 "-fsanitize-address-use-after-return=never",
                 "-Wno-unused-command-line-argument",
             ],
+            shared_libs: [
+                "libz", // For adler32.
+            ],
         },
     },
+    static: {
+        cflags: ["-DART_STATIC_LIBART"],
+    },
     generated_sources: [
         "art_operator_srcs",
     ],
+    header_libs: [
+        "art_cmdlineparser_headers",
+        "cpp-define-generator-definitions",
+        "jni_platform_headers",
+        "libart_headers",
+        "libnativehelper_header_only",
+        "libart_generated_headers",
+    ],
+    export_header_lib_headers: [
+        "libart_headers",
+        "libart_generated_headers",
+    ],
     whole_static_libs: [
         "libcpu_features",
     ],
-}
-
-cc_defaults {
-    name: "libart-runtime_defaults",
-    defaults: [
-        "libart-runtime_common_defaults",
-        "libart-runtime_deps",
+    shared_libs: [
+        "libartpalette",
+        "libbase", // For common macros.
+        "liblog",
+        "liblz4",
+        "liblzma", // libelffile(d) dependency; must be repeated here since it's a static lib.
+        "libnativebridge",
+        "libnativeloader",
+        "libsigchain",
+        "libunwindstack",
     ],
-}
+    static_libs: ["libodrstatslog"],
 
-cc_defaults {
-    name: "libartd-runtime_defaults",
-    defaults: [
-        "art_debug_defaults",
-        "libart-runtime_common_defaults",
-        "libartd-runtime_deps",
-    ],
-}
-
-cc_defaults {
-    name: "libart_defaults",
-    defaults: [
-        "libart_common_defaults",
-        "libart-runtime_deps",
-        "libart-compiler_deps",
-    ],
-}
-
-cc_defaults {
-    name: "libartd_defaults",
-    defaults: [
-        "art_debug_defaults",
-        "libart_common_defaults",
-        "libartd-runtime_deps",
-        "libartd-compiler_deps",
+    runtime_libs: [
+        // Libraries loaded at runtime. Exceptions:
+        // - libart(d)-compiler.so and libopenjdk(d).so cannot be listed here
+        //   due to cyclic dependency.
+        // - libicu_jni.so is only loaded to handle dependency order in VM
+        //   startup (see Runtime::InitNativeMethods), but its API is internal
+        //   to com.android.i18n and not used by ART/libcore. Therefore it's not
+        //   listed here to avoid visibility issues. Instead it's linked from
+        //   the ART module namespace through an entry in requireNativeLibs in
+        //   manifest-art.json.
+        "libjavacore",
     ],
 }
 
@@ -648,10 +555,9 @@
         "libdexfile_static_defaults",
         "libdexfile_support_static_defaults",
         "libprofile_static_defaults",
-        "libart-compiler_static_defaults",
     ],
     whole_static_libs: [
-        "libart-runtime",
+        "libart",
         "libelffile",
         "libsigchain_fake",
         "libnativeloader",
@@ -666,10 +572,9 @@
         "libdexfiled_static_defaults",
         "libdexfiled_support_static_defaults",
         "libprofiled_static_defaults",
-        "libartd-compiler_static_defaults",
     ],
     whole_static_libs: [
-        "libartd-runtime",
+        "libartd",
         "libelffiled",
         "libsigchain_fake",
         "libnativeloader",
@@ -678,7 +583,7 @@
 
 // libart_static_defaults for standalone gtests.
 // Doesn't link libsigchain_fake.
-// Uses libart-(runtime/compiler)-for-test instead of libart-runtime/compiler.
+// Uses libart-for-test instead of libart.
 cc_defaults {
     name: "libart-for-test_static_defaults",
     defaults: [
@@ -687,18 +592,16 @@
         "libdexfile_static_defaults",
         "libdexfile_support_static_defaults",
         "libprofile_static_defaults",
-        "libart-compiler-for-test_static_defaults",
     ],
     whole_static_libs: [
-        "libart-runtime-for-test",
+        "libart-for-test",
         "libelffile",
     ],
 }
 
 // libartd_static_defaults for gtests.
 // Doesn't link libsigchain_fake.
-// Note that `libartd-runtime-for-test` is not required here, because `libartd-runtime`
-// doesn't use LTO.
+// Note that `libartd-for-test` is not required here, because `libartd` doesn't use LTO.
 cc_defaults {
     name: "libartd-for-test_static_defaults",
     defaults: [
@@ -707,10 +610,9 @@
         "libdexfiled_static_defaults",
         "libdexfiled_support_static_defaults",
         "libprofiled_static_defaults",
-        "libartd-compiler-for-test_static_defaults",
     ],
     whole_static_libs: [
-        "libartd-runtime",
+        "libartd",
         "libelffiled",
     ],
 }
@@ -757,14 +659,37 @@
 // We always build dex2oat and dependencies, even if the host build is otherwise disabled, since
 // they are used to cross compile for the target.
 
+// Properties common to `libart` and `libart-broken`.
+art_cc_defaults {
+    name: "libart_common_defaults",
+    defaults: [
+        "libart_defaults",
+        "libart_nativeunwind_defaults",
+        "art_hugepage_defaults",
+    ],
+    whole_static_libs: [
+    ],
+    static_libs: [
+        "libelffile",
+    ],
+    shared_libs: [
+        "libartbase",
+        "libdexfile",
+        "libprofile",
+    ],
+    export_shared_lib_headers: [
+        "libdexfile",
+    ],
+}
+
 // Release version of the ART runtime library.
-art_cc_library_static {
-    name: "libart-runtime",
-    defaults: ["libart-runtime_defaults"],
+art_cc_library {
+    name: "libart",
+    defaults: ["libart_common_defaults"],
     apex_available: [
         "com.android.art",
         "com.android.art.debug",
-        // This lib doesn't go into test_broken_com.android.art, but the libart-broken
+        // libart doesn't go into test_broken_com.android.art, but the libart-broken
         // needs to have the same apex_available list as its dependencies in order
         // to compile against their sources. Then that change comes back up to affect
         // libart as well, because it also needs to have the same apex_available as its
@@ -781,67 +706,13 @@
     },
 }
 
-// For static linking with gtests. Same as `libart-runtime`, but without LTO.
-// When gtests static link a library with LTO enabled, they are also built with LTO.
-// This makes the build process use a lot of memory. b/277207452
-art_cc_library_static {
-    name: "libart-runtime-for-test",
-    defaults: ["libart-runtime_defaults"],
-}
-
-// Debug version of the ART runtime library.
-art_cc_library_static {
-    name: "libartd-runtime",
-    defaults: ["libartd-runtime_defaults"],
-    apex_available: [
-        "com.android.art.debug",
-        // TODO(b/183882457): This lib doesn't go into com.android.art, but
-        // apex_available lists need to be the same for internal libs to avoid
-        // stubs, and this depends on libsigchain.
-        "com.android.art",
-    ],
-}
-
-// Release version of the ART runtime library, bundled with `libart-compiler` for JIT support.
-art_cc_library {
-    name: "libart",
-    defaults: ["libart_defaults"],
-    // `libart-runtime` and `libart-compiler` are built separately because they use different
-    // optimization profiles (AFDO and PGO respectively), which can't be combined: b/255683875
-    whole_static_libs: [
-        "libart-compiler",
-        "libart-runtime",
-    ],
-    apex_available: [
-        "com.android.art.debug",
-        "com.android.art",
-        // This lib doesn't go into test_broken_com.android.art, but the libart-broken
-        // needs to have the same apex_available list as its dependencies in order
-        // to compile against their sources. Then that change comes back up to affect
-        // libart as well, because it also needs to have the same apex_available as its
-        // dependencies.
-        "test_broken_com.android.art",
-    ],
-    target: {
-        android: {
-            lto: {
-                thin: true,
-            },
-        },
-    },
-}
-
 art_cc_library {
     name: "libart-unstripped",
-    defaults: ["libart_defaults"],
-    whole_static_libs: [
-        "libart-compiler",
-        "libart-runtime",
-    ],
+    defaults: ["libart_common_defaults"],
     apex_available: [
         "com.android.art",
         "com.android.art.debug",
-        // This lib doesn't go into test_broken_com.android.art, but the libart-broken
+        // libart doesn't go into test_broken_com.android.art, but the libart-broken
         // needs to have the same apex_available list as its dependencies in order
         // to compile against their sources. Then that change comes back up to affect
         // libart as well, because it also needs to have the same apex_available as its
@@ -853,19 +724,13 @@
     },
 }
 
-// "Broken" version of the libart, used only for testing.
+// "Broken" version of the ART runtime library, used only for testing.
 art_cc_test_library {
     name: "libart-broken",
-    defaults: [
-        "libart-runtime_defaults",
-        "libart_defaults",
-    ],
-    cflags: ["-DART_CRASH_RUNTIME_DELIBERATELY"],
+    defaults: ["libart_common_defaults"],
     stem: "libart",
     gtest: false,
-    whole_static_libs: [
-        "libart-compiler",
-    ],
+    cflags: ["-DART_CRASH_RUNTIME_DELIBERATELY"],
     apex_available: [
         // libart-broken only goes into test_broken_com.android.art, but the libart-broken
         // needs to have the same apex_available list as its dependencies in order
@@ -876,13 +741,38 @@
     ],
 }
 
-// Debug version of the ART runtime library, bundled with `libartd-compiler` for JIT support.
+// For static linking with gtests. Same as `libart`, but without LTO.
+// When gtests static link a library with LTO enabled, they are also built with LTO.
+// This makes the build process use a lot of memory. b/277207452
+art_cc_library_static {
+    name: "libart-for-test",
+    defaults: ["libart_common_defaults"],
+    shared_libs: [
+        "libartbase",
+        "libdexfile",
+        "libprofile",
+    ],
+}
+
+// Debug version of the ART runtime library.
 art_cc_library {
     name: "libartd",
-    defaults: ["libartd_defaults"],
+    defaults: [
+        "art_debug_defaults",
+        "libart_defaults",
+    ],
     whole_static_libs: [
-        "libartd-compiler",
-        "libartd-runtime",
+    ],
+    static_libs: [
+        "libelffiled",
+    ],
+    shared_libs: [
+        "libartbased",
+        "libdexfiled",
+        "libprofiled",
+    ],
+    export_shared_lib_headers: [
+        "libdexfiled",
     ],
     apex_available: [
         "com.android.art.debug",
@@ -1054,6 +944,7 @@
         "intern_table_test.cc",
         "interpreter/safe_math_test.cc",
         "interpreter/unstarted_runtime_test.cc",
+        "jit/jit_load_test.cc",
         "jit/jit_memory_region_test.cc",
         "jit/profile_saver_test.cc",
         "jit/profiling_info_test.cc",
diff --git a/runtime/jit/jit.cc b/runtime/jit/jit.cc
index d4acf69..2b1850f 100644
--- a/runtime/jit/jit.cc
+++ b/runtime/jit/jit.cc
@@ -31,14 +31,13 @@
 #include "compilation_kind.h"
 #include "debugger.h"
 #include "dex/type_lookup_table.h"
+#include "gc/space/image_space.h"
 #include "entrypoints/entrypoint_utils-inl.h"
 #include "entrypoints/runtime_asm_entrypoints.h"
-#include "gc/space/image_space.h"
 #include "image-inl.h"
 #include "interpreter/interpreter.h"
 #include "jit-inl.h"
 #include "jit_code_cache.h"
-#include "jit_create.h"
 #include "jni/java_vm_ext.h"
 #include "mirror/method_handle_impl.h"
 #include "mirror/var_handle.h"
@@ -82,7 +81,9 @@
 DEFINE_RUNTIME_DEBUG_FLAG(Jit, kSlowMode);
 
 // JIT compiler
+void* Jit::jit_library_handle_ = nullptr;
 JitCompilerInterface* Jit::jit_compiler_ = nullptr;
+JitCompilerInterface* (*Jit::jit_load_)(void) = nullptr;
 
 JitOptions* JitOptions::CreateFromRuntimeArguments(const RuntimeArgumentMap& options) {
   auto* jit_options = new JitOptions;
@@ -186,8 +187,16 @@
       fd_methods_(-1),
       fd_methods_size_(0) {}
 
-std::unique_ptr<Jit> Jit::Create(JitCodeCache* code_cache, JitOptions* options) {
-  jit_compiler_ = jit_create();
+Jit* Jit::Create(JitCodeCache* code_cache, JitOptions* options) {
+  if (jit_load_ == nullptr) {
+    LOG(WARNING) << "Not creating JIT: library not loaded";
+    return nullptr;
+  }
+  jit_compiler_ = (jit_load_)();
+  if (jit_compiler_ == nullptr) {
+    LOG(WARNING) << "Not creating JIT: failed to allocate a compiler";
+    return nullptr;
+  }
   std::unique_ptr<Jit> jit(new Jit(code_cache, options));
 
   // If the code collector is enabled, check if that still holds:
@@ -220,8 +229,42 @@
 
   // Notify native debugger about the classes already loaded before the creation of the jit.
   jit->DumpTypeInfoForLoadedTypes(Runtime::Current()->GetClassLinker());
+  return jit.release();
+}
 
-  return jit;
+template <typename T>
+bool Jit::LoadSymbol(T* address, const char* name, std::string* error_msg) {
+  *address = reinterpret_cast<T>(dlsym(jit_library_handle_, name));
+  if (*address == nullptr) {
+    *error_msg = std::string("JIT couldn't find ") + name + std::string(" entry point");
+    return false;
+  }
+  return true;
+}
+
+#ifdef ART_STATIC_LIBART
+extern "C" JitCompilerInterface* jit_load();
+#endif
+
+bool Jit::LoadCompilerLibrary([[maybe_unused]] /*out*/ std::string* error_msg) {
+#ifdef ART_STATIC_LIBART
+  jit_load_ = &jit_load;
+  return true;
+#else
+  jit_library_handle_ = dlopen(
+      kIsDebugBuild ? "libartd-compiler.so" : "libart-compiler.so", RTLD_NOW);
+  if (jit_library_handle_ == nullptr) {
+    std::ostringstream oss;
+    oss << "JIT could not load libart-compiler.so: " << dlerror();
+    *error_msg = oss.str();
+    return false;
+  }
+  if (!LoadSymbol(&jit_load_, "jit_load", error_msg)) {
+    dlclose(jit_library_handle_);
+    return false;
+  }
+  return true;
+#endif
 }
 
 bool Jit::CompileMethodInternal(ArtMethod* method,
@@ -375,6 +418,10 @@
     delete jit_compiler_;
     jit_compiler_ = nullptr;
   }
+  if (jit_library_handle_ != nullptr) {
+    dlclose(jit_library_handle_);
+    jit_library_handle_ = nullptr;
+  }
 }
 
 void Jit::NewTypeLoadedIfUsingJit(mirror::Class* type) {
diff --git a/runtime/jit/jit.h b/runtime/jit/jit.h
index d5fcd35..c95fd9d 100644
--- a/runtime/jit/jit.h
+++ b/runtime/jit/jit.h
@@ -240,7 +240,7 @@
   virtual ~Jit();
 
   // Create JIT itself.
-  static std::unique_ptr<Jit> Create(JitCodeCache* code_cache, JitOptions* options);
+  static Jit* Create(JitCodeCache* code_cache, JitOptions* options);
 
   bool CompileMethod(ArtMethod* method, Thread* self, CompilationKind compilation_kind, bool prejit)
       REQUIRES_SHARED(Locks::mutator_lock_);
@@ -364,6 +364,9 @@
                                         JValue* result)
       REQUIRES_SHARED(Locks::mutator_lock_);
 
+  // Load the compiler library.
+  static bool LoadCompilerLibrary(std::string* error_msg);
+
   ThreadPool* GetThreadPool() const {
     return thread_pool_.get();
   }
@@ -472,7 +475,10 @@
       REQUIRES_SHARED(Locks::mutator_lock_);
 
   // JIT compiler
+  static void* jit_library_handle_;
   static JitCompilerInterface* jit_compiler_;
+  static JitCompilerInterface* (*jit_load_)(void);
+  template <typename T> static bool LoadSymbol(T*, const char* symbol, std::string* error_msg);
 
   // JIT resources owned by runtime.
   jit::JitCodeCache* const code_cache_;
diff --git a/runtime/jit/jit_load_test.cc b/runtime/jit/jit_load_test.cc
new file mode 100644
index 0000000..4b080a5
--- /dev/null
+++ b/runtime/jit/jit_load_test.cc
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "common_runtime_test.h"
+#include "compiler_callbacks.h"
+
+namespace art {
+
+class JitLoadTest : public CommonRuntimeTest {
+ protected:
+  void SetUpRuntimeOptions(RuntimeOptions *options) override {
+    callbacks_.reset();
+    CommonRuntimeTest::SetUpRuntimeOptions(options);
+    options->push_back(std::make_pair("-Xusejit:true", nullptr));
+  }
+};
+
+
+TEST_F(JitLoadTest, JitLoad) {
+  Thread::Current()->TransitionFromSuspendedToRunnable();
+  runtime_->Start();
+  ASSERT_NE(runtime_->GetJit(), nullptr);
+}
+
+}  // namespace art
diff --git a/runtime/runtime.cc b/runtime/runtime.cc
index 074260e..38e3c0d 100644
--- a/runtime/runtime.cc
+++ b/runtime/runtime.cc
@@ -988,6 +988,11 @@
   // recoding profiles. Maybe we should consider changing the name to be more clear it's
   // not only about compiling. b/28295073.
   if (jit_options_->UseJitCompilation() || jit_options_->GetSaveProfilingInfo()) {
+    // Try to load compiler pre zygote to reduce PSS. b/27744947
+    std::string error_msg;
+    if (!jit::Jit::LoadCompilerLibrary(&error_msg)) {
+      LOG(WARNING) << "Failed to load JIT compiler with error " << error_msg;
+    }
     CreateJit();
 #ifdef ADDRESS_SANITIZER
     // (b/238730394): In older implementations of sanitizer + glibc there is a race between
@@ -3063,8 +3068,15 @@
     return;
   }
 
-  jit_ = jit::Jit::Create(jit_code_cache_.get(), jit_options_.get());
-  jit_->CreateThreadPool();
+  jit::Jit* jit = jit::Jit::Create(jit_code_cache_.get(), jit_options_.get());
+  jit_.reset(jit);
+  if (jit == nullptr) {
+    LOG(WARNING) << "Failed to allocate JIT";
+    // Release JIT code cache resources (several MB of memory).
+    jit_code_cache_.reset();
+  } else {
+    jit->CreateThreadPool();
+  }
 }
 
 bool Runtime::CanRelocate() const {
diff --git a/tools/art_verifier/Android.bp b/tools/art_verifier/Android.bp
index 5d19215..19498e0 100644
--- a/tools/art_verifier/Android.bp
+++ b/tools/art_verifier/Android.bp
@@ -59,6 +59,8 @@
     defaults: [
         "art_verifier-defaults",
         "libart_static_defaults",
+        // TODO(b/186902856): remove once libart-compiler is merged into libart
+        "libart-compiler_static_defaults",
     ],
 }
 
@@ -68,5 +70,7 @@
         "art_debug_defaults",
         "art_verifier-defaults",
         "libartd_static_defaults",
+        // TODO(b/186902856): remove once libart-compiler is merged into libart
+        "libartd-compiler_static_defaults",
     ],
 }
diff --git a/tools/fuzzer/Android.bp b/tools/fuzzer/Android.bp
index 8ac2086..c3f35d2 100644
--- a/tools/fuzzer/Android.bp
+++ b/tools/fuzzer/Android.bp
@@ -30,6 +30,8 @@
     defaults: [
         // Run in release mode since debug is too slow.
         "libart_static_defaults",
+        // TODO(b/186902856): remove once libart-compiler is merged into libart
+        "libart-compiler_static_defaults",
         // To allow the ART module to build correctly.
         "art_module_source_build_defaults",
     ],