[PATCH v2 13/13] meson: build single binary

Yonggang Luo <[email protected]>
Newsgroups org.nongnu.qemu-riscv,org.nongnu.qemu-arm,org.nongnu.qemu-devel
Message-ID <[email protected]>
- Add -Dsingle_binary / --enable-single-binary (default true) and
  --disable-single-binary to gate the combined qemu-system binary.
- Map each base arch to a primary softmmu target (arm ->
  aarch64-softmmu, riscv -> riscv64-softmmu) that supplies arch_srcs.
  Sibling targets contribute target-info-def.c only.
- Apply common_ss and system_ss once against the union of those
  base-arch configs so constructors and Kconfig stubs are not
  duplicated.
- Build qemu-system only, including on Windows. Do not add
  qemu-systemw: a GUI twin would keep QEMU exporting data from the
  .exe into DLLs, and those data exports cannot be delay-loaded
  (qdev_prop_array and other qdev_prop_*). That would block enabling
  modules globally on Windows.

Signed-off-by: Pierrick Bouvier <[email protected]>
Signed-off-by: Yonggang Luo <[email protected]>
---
 meson.build                   | 69 +++++++++++++++++++++++++++++++++--
 meson_options.txt             |  2 +
 scripts/meson-buildoptions.sh |  3 ++
 3 files changed, 71 insertions(+), 3 deletions(-)

diff --git a/meson.build b/meson.build
index 449d50f2983..eea54fd0ba3 100644
--- a/meson.build
+++ b/meson.build
@@ -4249,6 +4249,18 @@ if host_os == 'darwin'
 endif
 
 traceable = []
+single_binary_arch_objects = []
+single_binary_bases_config = {}
+single_binary_deps = []
+single_binary_crates = []
+# base arch -> softmmu target that supplies arch_srcs
+single_binary_primary = {
+  'arm': 'aarch64-softmmu',
+  'riscv': 'riscv64-softmmu',
+}
+if not get_option('single_binary')
+  single_binary_primary = {}
+endif
 emulators = {}
 foreach target : target_dirs
   config_target = config_target_mak[target]
@@ -4321,8 +4333,6 @@ foreach target : target_dirs
     endif
   endif
 
-  arch_srcs += files('target-info-def.c')
-
   if target_base_arch in target_arch
     t = target_arch[target_base_arch].apply(config_target, strict: false)
     arch_srcs += t.sources()
@@ -4391,8 +4401,9 @@ foreach target : target_dirs
     lib_deps += dep.partial_dependency(compile_args: true, includes: true)
   endforeach
 
+  target_info_src = files('target-info-def.c')
   lib = static_library('qemu-' + target,
-                 sources: arch_srcs + genh,
+                 sources: target_info_src + arch_srcs + genh,
                  dependencies: lib_deps,
                  objects: objects,
                  include_directories: target_inc,
@@ -4400,6 +4411,16 @@ foreach target : target_dirs
                  build_by_default: false)
 
   if target.endswith('-softmmu')
+    if target_base_arch in single_binary_primary
+      single_binary_bases_config += config_target
+      single_binary_arch_objects += lib.extract_objects(target_info_src)
+      if target == single_binary_primary[target_base_arch]
+        single_binary_arch_objects += lib.extract_objects(arch_srcs)
+        single_binary_deps += arch_deps
+        single_binary_deps += target_stubs
+        single_binary_crates += main_rs
+      endif
+    endif
     execs = [{
       'name': 'qemu-system-' + target_name,
       'win_subsystem': 'console',
@@ -4481,6 +4502,47 @@ foreach target : target_dirs
   endforeach
 endforeach
 
+if single_binary_arch_objects.length() != 0
+  single_binary_objects = []
+  foreach spec: [[common_ss, common_all], [system_ss, libsystem]]
+    src = spec[0].apply(single_binary_bases_config, strict: false)
+    single_binary_objects += spec[1].extract_objects(src.sources())
+    single_binary_deps += src.dependencies()
+  endforeach
+  foreach base, tgt: single_binary_primary
+    if base in target_common_arch_libs
+      src = target_common_arch[base].apply(single_binary_bases_config,
+                                           strict: false)
+      single_binary_objects += target_common_arch_libs[base].extract_objects(
+        src.sources())
+      single_binary_deps += src.dependencies()
+    endif
+    if base in target_common_system_arch_libs
+      src = target_common_system_arch[base].apply(single_binary_bases_config,
+                                                  strict: false)
+      single_binary_objects += target_common_system_arch_libs[base].extract_objects(
+        src.sources())
+      single_binary_deps += src.dependencies()
+    endif
+  endforeach
+  single_binary_objects += single_binary_arch_objects
+
+  single_binary_link_args = emulator_link_args
+  single_binary_link_args += enable_modules ? ['@block.syms', '@qemu.syms'] : []
+  emulator = executable('qemu-system',
+             sources: [single_binary_crates, files('system/main.c')],
+             dependencies: single_binary_deps + [sdl],
+             objects: single_binary_objects,
+             link_depends: [block_syms, qemu_syms],
+             link_args: single_binary_link_args,
+             install: true)
+  emulators += {'qemu-system': emulator}
+  traceable += [{
+    'exe': 'qemu-system',
+    'probe-prefix': 'qemu.system.multi',
+  }]
+endif
+
 # Other build targets
 
 if get_option('plugins')
@@ -4833,6 +4895,7 @@ if config_all_accel.has_key('CONFIG_TCG')
   endif
 endif
 summary_info += {'target list':       ' '.join(target_dirs)}
+summary_info += {'single binary':     get_option('single_binary')}
 if have_system
   summary_info += {'default devices':   get_option('default_devices')}
   summary_info += {'out of process emulation': multiprocess_allowed}
diff --git a/meson_options.txt b/meson_options.txt
index a07cb47d35e..9d86a46fba7 100644
--- a/meson_options.txt
+++ b/meson_options.txt
@@ -91,6 +91,8 @@ option('tcg', type: 'feature', value: 'enabled',
        description: 'TCG support')
 option('plugins', type: 'boolean', value: false,
        description: 'TCG plugins via shared library loading')
+option('single_binary', type: 'boolean', value: true,
+       description: 'combined qemu-system binary')
 option('debug_tcg', type: 'boolean', value: false,
        description: 'TCG debugging')
 option('debug_remap', type: 'boolean', value: false,
diff --git a/scripts/meson-buildoptions.sh b/scripts/meson-buildoptions.sh
index c003985047c..d8e49111ac7 100644
--- a/scripts/meson-buildoptions.sh
+++ b/scripts/meson-buildoptions.sh
@@ -19,6 +19,7 @@ meson_options_help() {
   printf "%s\n" '  --disable-install-blobs  install provided firmware blobs'
   printf "%s\n" '  --disable-qom-cast-debug cast debugging support'
   printf "%s\n" '  --disable-relocatable    toggle relocatable install'
+  printf "%s\n" '  --disable-single-binary  combined qemu-system binary'
   printf "%s\n" '  --docdir=VALUE           Base directory for documentation installation'
   printf "%s\n" '                           (can be empty) [share/doc]'
   printf "%s\n" '  --enable-asan            enable address sanitizer'
@@ -486,6 +487,8 @@ _meson_option_parse() {
     --disable-seccomp) printf "%s" -Dseccomp=disabled ;;
     --enable-selinux) printf "%s" -Dselinux=enabled ;;
     --disable-selinux) printf "%s" -Dselinux=disabled ;;
+    --enable-single-binary) printf "%s" -Dsingle_binary=true ;;
+    --disable-single-binary) printf "%s" -Dsingle_binary=false ;;
     --enable-slirp) printf "%s" -Dslirp=enabled ;;
     --disable-slirp) printf "%s" -Dslirp=disabled ;;
     --enable-slirp-smbd) printf "%s" -Dslirp_smbd=enabled ;;
-- 
2.52.0.windows.1
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.