]> git.proxmox.com Git - mirror_qemu.git/blame - meson.build
configure, meson: move pthread_setname_np checks to Meson
[mirror_qemu.git] / meson.build
CommitLineData
654d6b04
PB
1project('qemu', ['c'], meson_version: '>=0.58.2',
2 default_options: ['warning_level=1', 'c_std=gnu11', 'cpp_std=gnu++11', 'b_colorout=auto',
3 'b_staticpic=false'],
4 version: files('VERSION'))
a5665051
PB
5
6not_found = dependency('', required: false)
654d6b04 7keyval = import('keyval')
a81df1b6 8ss = import('sourceset')
8b18cdbf 9fs = import('fs')
a81df1b6 10
ce1c1e7a 11sh = find_program('sh')
a81df1b6 12cc = meson.get_compiler('c')
a5665051 13config_host = keyval.load(meson.current_build_dir() / 'config-host.mak')
3154fee4 14enable_modules = 'CONFIG_MODULES' in config_host
35be72ba 15enable_static = 'CONFIG_STATIC' in config_host
e3667660 16
d7dedf42
PB
17# Allow both shared and static libraries unless --enable-static
18static_kwargs = enable_static ? {'static': true} : {}
19
e3667660
YL
20# Temporary directory used for files created while
21# configure runs. Since it is in the build directory
22# we can safely blow away any previous version of it
23# (and we need not jump through hoops to try to delete
24# it when configure exits.)
25tmpdir = meson.current_build_dir() / 'meson-private/temp'
8fe11232
MAL
26
27if get_option('qemu_suffix').startswith('/')
28 error('qemu_suffix cannot start with a /')
29endif
30
16bf7a33 31qemu_confdir = get_option('sysconfdir') / get_option('qemu_suffix')
ab4c0996 32qemu_datadir = get_option('datadir') / get_option('qemu_suffix')
491e74c1 33qemu_docdir = get_option('docdir') / get_option('qemu_suffix')
16bf7a33
PB
34qemu_moddir = get_option('libdir') / get_option('qemu_suffix')
35
36qemu_desktopdir = get_option('datadir') / 'applications'
37qemu_icondir = get_option('datadir') / 'icons'
38
859aef02
PB
39config_host_data = configuration_data()
40genh = []
a5665051 41
760e4327
PB
42target_dirs = config_host['TARGET_DIRS'].split()
43have_user = false
44have_system = false
45foreach target : target_dirs
46 have_user = have_user or target.endswith('-user')
47 have_system = have_system or target.endswith('-softmmu')
48endforeach
49have_tools = 'CONFIG_TOOLS' in config_host
50have_block = have_system or have_tools
51
201e8ed7
PB
52python = import('python').find_installation()
53
54supported_oses = ['windows', 'freebsd', 'netbsd', 'openbsd', 'darwin', 'sunos', 'linux']
6125673e 55supported_cpus = ['ppc', 'ppc64', 's390x', 'riscv32', 'riscv64', 'x86', 'x86_64',
201e8ed7
PB
56 'arm', 'aarch64', 'mips', 'mips64', 'sparc', 'sparc64']
57
58cpu = host_machine.cpu_family()
59targetos = host_machine.system()
60
8a19980e
PB
61if cpu in ['x86', 'x86_64']
62 kvm_targets = ['i386-softmmu', 'x86_64-softmmu']
63elif cpu == 'aarch64'
64 kvm_targets = ['aarch64-softmmu']
65elif cpu == 's390x'
66 kvm_targets = ['s390x-softmmu']
67elif cpu in ['ppc', 'ppc64']
68 kvm_targets = ['ppc-softmmu', 'ppc64-softmmu']
fbc5884c
HC
69elif cpu in ['mips', 'mips64']
70 kvm_targets = ['mips-softmmu', 'mipsel-softmmu', 'mips64-softmmu', 'mips64el-softmmu']
8a19980e
PB
71else
72 kvm_targets = []
73endif
74
75accelerator_targets = { 'CONFIG_KVM': kvm_targets }
844a06bb
AG
76
77if cpu in ['aarch64']
78 accelerator_targets += {
79 'CONFIG_HVF': ['aarch64-softmmu']
80 }
81endif
82
0c3e41d4 83if cpu in ['x86', 'x86_64', 'arm', 'aarch64']
2a2d51bc 84 # i386 emulator provides xenpv machine type for multiple architectures
0c3e41d4
AB
85 accelerator_targets += {
86 'CONFIG_XEN': ['i386-softmmu', 'x86_64-softmmu'],
87 }
88endif
8a19980e
PB
89if cpu in ['x86', 'x86_64']
90 accelerator_targets += {
91 'CONFIG_HAX': ['i386-softmmu', 'x86_64-softmmu'],
8a19980e 92 'CONFIG_HVF': ['x86_64-softmmu'],
74a414a1 93 'CONFIG_NVMM': ['i386-softmmu', 'x86_64-softmmu'],
8a19980e
PB
94 'CONFIG_WHPX': ['i386-softmmu', 'x86_64-softmmu'],
95 }
96endif
97
a1b176f9
PB
98modular_tcg = []
99# Darwin does not support references to thread-local variables in modules
100if targetos != 'darwin'
101 modular_tcg = ['i386-softmmu', 'x86_64-softmmu']
102endif
dae0ec15 103
eae9a1d1 104edk2_targets = [ 'arm-softmmu', 'aarch64-softmmu', 'i386-softmmu', 'x86_64-softmmu' ]
e49c0ef6
PB
105unpack_edk2_blobs = false
106foreach target : edk2_targets
107 if target in target_dirs
108 bzip2 = find_program('bzip2', required: get_option('install_blobs'))
109 unpack_edk2_blobs = bzip2.found()
110 break
111 endif
112endforeach
45b545dd 113
9c29b741
PB
114dtrace = not_found
115stap = not_found
116if 'dtrace' in get_option('trace_backends')
117 dtrace = find_program('dtrace', required: true)
118 stap = find_program('stap', required: false)
119 if stap.found()
120 # Workaround to avoid dtrace(1) producing a file with 'hidden' symbol
121 # visibility. Define STAP_SDT_V2 to produce 'default' symbol visibility
122 # instead. QEMU --enable-modules depends on this because the SystemTap
123 # semaphores are linked into the main binary and not the module's shared
124 # object.
125 add_global_arguments('-DSTAP_SDT_V2',
126 native: false, language: ['c', 'cpp', 'objc'])
127 endif
128endif
129
201e8ed7
PB
130##################
131# Compiler flags #
132##################
133
ff9ed62b
AB
134# Specify linker-script with add_project_link_arguments so that it is not placed
135# within a linker --start-group/--end-group pair
537b7248
PB
136if get_option('fuzzing')
137 add_project_link_arguments(['-Wl,-T,',
138 (meson.current_source_dir() / 'tests/qtest/fuzz/fork_fuzz.ld')],
139 native: false, language: ['c', 'cpp', 'objc'])
140
141 # Specify a filter to only instrument code that is directly related to
142 # virtual-devices.
143 configure_file(output: 'instrumentation-filter',
144 input: 'scripts/oss-fuzz/instrumentation-filter-template',
145 copy: true)
146 add_global_arguments(
147 cc.get_supported_arguments('-fsanitize-coverage-allowlist=instrumentation-filter'),
148 native: false, language: ['c', 'cpp', 'objc'])
149
150 if get_option('fuzzing_engine') == ''
151 # Add CFLAGS to tell clang to add fuzzer-related instrumentation to all the
152 # compiled code. To build non-fuzzer binaries with --enable-fuzzing, link
153 # everything with fsanitize=fuzzer-no-link. Otherwise, the linker will be
154 # unable to bind the fuzzer-related callbacks added by instrumentation.
155 add_global_arguments('-fsanitize=fuzzer-no-link',
156 native: false, language: ['c', 'cpp', 'objc'])
157 add_global_link_arguments('-fsanitize=fuzzer-no-link',
ff9ed62b 158 native: false, language: ['c', 'cpp', 'objc'])
537b7248
PB
159 # For the actual fuzzer binaries, we need to link against the libfuzzer
160 # library. They need to be configurable, to support OSS-Fuzz
161 fuzz_exe_ldflags = ['-fsanitize=fuzzer']
162 else
163 # LIB_FUZZING_ENGINE was set; assume we are running on OSS-Fuzz, and
164 # the needed CFLAGS have already been provided
165 fuzz_exe_ldflags = get_option('fuzzing_engine').split()
166 endif
ff9ed62b
AB
167endif
168
5fc0617f
MAL
169add_global_arguments(config_host['QEMU_CFLAGS'].split(),
170 native: false, language: ['c', 'objc'])
171add_global_arguments(config_host['QEMU_CXXFLAGS'].split(),
172 native: false, language: 'cpp')
173add_global_link_arguments(config_host['QEMU_LDFLAGS'].split(),
174 native: false, language: ['c', 'cpp', 'objc'])
a5665051 175
1e6e616d
PB
176if targetos == 'linux'
177 add_project_arguments('-isystem', meson.current_source_dir() / 'linux-headers',
178 '-isystem', 'linux-headers',
179 language: ['c', 'cpp'])
180endif
181
23a77b2d 182add_project_arguments('-iquote', '.',
1e6e616d 183 '-iquote', meson.current_source_dir(),
1e6e616d
PB
184 '-iquote', meson.current_source_dir() / 'include',
185 '-iquote', meson.current_source_dir() / 'disas/libvixl',
186 language: ['c', 'cpp', 'objc'])
c46f76d1 187
fc929892
MAL
188link_language = meson.get_external_property('link_language', 'cpp')
189if link_language == 'cpp'
190 add_languages('cpp', required: true, native: false)
191endif
a5665051
PB
192if host_machine.system() == 'darwin'
193 add_languages('objc', required: false, native: false)
194endif
195
deb62371
PB
196sparse = find_program('cgcc', required: get_option('sparse'))
197if sparse.found()
968b4db3
PB
198 run_target('sparse',
199 command: [find_program('scripts/check_sparse.py'),
deb62371
PB
200 'compile_commands.json', sparse.full_path(), '-Wbitwise',
201 '-Wno-transparent-union', '-Wno-old-initializer',
202 '-Wno-non-pointer-null'])
968b4db3
PB
203endif
204
6ec0e15d
PB
205###########################################
206# Target-specific checks and dependencies #
207###########################################
208
537b7248
PB
209if get_option('fuzzing') and get_option('fuzzing_engine') == '' and \
210 not cc.links('''
211 #include <stdint.h>
212 #include <sys/types.h>
213 int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size);
214 int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size) { return 0; }
215 ''',
216 args: ['-Werror', '-fsanitize=fuzzer'])
217 error('Your compiler does not support -fsanitize=fuzzer')
218endif
219
9c29b741
PB
220if 'ftrace' in get_option('trace_backends') and targetos != 'linux'
221 error('ftrace is supported only on Linux')
222endif
223if 'syslog' in get_option('trace_backends') and not cc.compiles('''
224 #include <syslog.h>
225 int main(void) {
226 openlog("qemu", LOG_PID, LOG_DAEMON);
227 syslog(LOG_INFO, "configure");
228 return 0;
229 }''')
230 error('syslog is not supported on this system')
231endif
232
6ec0e15d
PB
233if targetos != 'linux' and get_option('mpath').enabled()
234 error('Multipath is supported only on Linux')
235endif
236
106ad1f9
PB
237if targetos != 'linux' and get_option('multiprocess').enabled()
238 error('Multiprocess QEMU is supported only on Linux')
239endif
240multiprocess_allowed = targetos == 'linux' and not get_option('multiprocess').disabled()
241
7fa1c635 242libm = cc.find_library('m', required: false)
6d7c7c2d 243threads = dependency('threads')
a81df1b6 244util = cc.find_library('util', required: false)
4a96337d 245winmm = []
a81df1b6 246socket = []
04c6f1e7 247version_res = []
d92989aa
MAL
248coref = []
249iokit = []
b6c7cfd4 250emulator_link_args = []
74a414a1 251nvmm =not_found
8a19980e 252hvf = not_found
a6305081 253host_dsosuf = '.so'
a81df1b6
PB
254if targetos == 'windows'
255 socket = cc.find_library('ws2_32')
4a96337d 256 winmm = cc.find_library('winmm')
04c6f1e7
MAL
257
258 win = import('windows')
259 version_res = win.compile_resources('version.rc',
260 depend_files: files('pc-bios/qemu-nsis.ico'),
261 include_directories: include_directories('.'))
a6305081 262 host_dsosuf = '.dll'
d92989aa
MAL
263elif targetos == 'darwin'
264 coref = dependency('appleframeworks', modules: 'CoreFoundation')
14176c8d 265 iokit = dependency('appleframeworks', modules: 'IOKit', required: false)
a6305081 266 host_dsosuf = '.dylib'
cfad62f1
PB
267elif targetos == 'sunos'
268 socket = [cc.find_library('socket'),
269 cc.find_library('nsl'),
270 cc.find_library('resolv')]
271elif targetos == 'haiku'
272 socket = [cc.find_library('posix_error_mapper'),
273 cc.find_library('network'),
274 cc.find_library('bsd')]
b6c7cfd4
PB
275elif targetos == 'openbsd'
276 if not get_option('tcg').disabled() and target_dirs.length() > 0
277 # Disable OpenBSD W^X if available
278 emulator_link_args = cc.get_supported_link_arguments('-Wl,-z,wxneeded')
279 endif
a81df1b6 280endif
6ec0e15d 281
8a19980e
PB
282accelerators = []
283if not get_option('kvm').disabled() and targetos == 'linux'
284 accelerators += 'CONFIG_KVM'
285endif
286if not get_option('xen').disabled() and 'CONFIG_XEN_BACKEND' in config_host
287 accelerators += 'CONFIG_XEN'
288 have_xen_pci_passthrough = not get_option('xen_pci_passthrough').disabled() and targetos == 'linux'
289else
290 have_xen_pci_passthrough = false
291endif
292if not get_option('whpx').disabled() and targetos == 'windows'
57e2a1f8 293 if get_option('whpx').enabled() and host_machine.cpu() != 'x86_64'
8a19980e
PB
294 error('WHPX requires 64-bit host')
295 elif cc.has_header('WinHvPlatform.h', required: get_option('whpx')) and \
296 cc.has_header('WinHvEmulation.h', required: get_option('whpx'))
297 accelerators += 'CONFIG_WHPX'
298 endif
299endif
300if not get_option('hvf').disabled()
301 hvf = dependency('appleframeworks', modules: 'Hypervisor',
302 required: get_option('hvf'))
303 if hvf.found()
304 accelerators += 'CONFIG_HVF'
305 endif
306endif
307if not get_option('hax').disabled()
308 if get_option('hax').enabled() or targetos in ['windows', 'darwin', 'netbsd']
309 accelerators += 'CONFIG_HAX'
310 endif
311endif
74a414a1
RZ
312if targetos == 'netbsd'
313 if cc.has_header_symbol('nvmm.h', 'nvmm_cpu_stop', required: get_option('nvmm'))
314 nvmm = cc.find_library('nvmm', required: get_option('nvmm'))
315 endif
316 if nvmm.found()
317 accelerators += 'CONFIG_NVMM'
318 endif
319endif
23a77b2d
PB
320
321tcg_arch = config_host['ARCH']
8a19980e
PB
322if not get_option('tcg').disabled()
323 if cpu not in supported_cpus
23a77b2d 324 if get_option('tcg_interpreter')
39687aca 325 warning('Unsupported CPU @0@, will use TCG with TCI (experimental and slow)'.format(cpu))
8a19980e
PB
326 else
327 error('Unsupported CPU @0@, try --enable-tcg-interpreter'.format(cpu))
328 endif
fa2f7b0b
PMD
329 elif get_option('tcg_interpreter')
330 warning('Use of the TCG interpretor is not recommended on this host')
331 warning('architecture. There is a native TCG execution backend available')
332 warning('which provides substantially better performance and reliability.')
333 warning('It is strongly recommended to remove the --enable-tcg-interpreter')
334 warning('configuration option on this architecture to use the native')
335 warning('backend.')
8a19980e 336 endif
23a77b2d
PB
337 if get_option('tcg_interpreter')
338 tcg_arch = 'tci'
339 elif config_host['ARCH'] == 'sparc64'
340 tcg_arch = 'sparc'
23a77b2d
PB
341 elif config_host['ARCH'] in ['x86_64', 'x32']
342 tcg_arch = 'i386'
343 elif config_host['ARCH'] == 'ppc64'
344 tcg_arch = 'ppc'
345 elif config_host['ARCH'] in ['riscv32', 'riscv64']
346 tcg_arch = 'riscv'
347 endif
348 add_project_arguments('-iquote', meson.current_source_dir() / 'tcg' / tcg_arch,
23a77b2d
PB
349 language: ['c', 'cpp', 'objc'])
350
8a19980e
PB
351 accelerators += 'CONFIG_TCG'
352 config_host += { 'CONFIG_TCG': 'y' }
353endif
354
355if 'CONFIG_KVM' not in accelerators and get_option('kvm').enabled()
356 error('KVM not available on this platform')
357endif
358if 'CONFIG_HVF' not in accelerators and get_option('hvf').enabled()
359 error('HVF not available on this platform')
360endif
74a414a1
RZ
361if 'CONFIG_NVMM' not in accelerators and get_option('nvmm').enabled()
362 error('NVMM not available on this platform')
363endif
8a19980e
PB
364if 'CONFIG_WHPX' not in accelerators and get_option('whpx').enabled()
365 error('WHPX not available on this platform')
366endif
367if not have_xen_pci_passthrough and get_option('xen_pci_passthrough').enabled()
368 if 'CONFIG_XEN' in accelerators
369 error('Xen PCI passthrough not available on this platform')
370 else
371 error('Xen PCI passthrough requested but Xen not enabled')
372 endif
373endif
b4e312e9 374
6ec0e15d
PB
375################
376# Dependencies #
377################
378
215b0c2f
PB
379# The path to glib.h is added to all compilation commands. This was
380# grandfathered in from the QEMU Makefiles.
381add_project_arguments(config_host['GLIB_CFLAGS'].split(),
382 native: false, language: ['c', 'cpp', 'objc'])
953d5a9e
MAL
383glib = declare_dependency(compile_args: config_host['GLIB_CFLAGS'].split(),
384 link_args: config_host['GLIB_LIBS'].split())
385# override glib dep with the configure results (for subprojects)
386meson.override_dependency('glib-2.0', glib)
387
a81df1b6
PB
388gio = not_found
389if 'CONFIG_GIO' in config_host
390 gio = declare_dependency(compile_args: config_host['GIO_CFLAGS'].split(),
391 link_args: config_host['GIO_LIBS'].split())
392endif
393lttng = not_found
9c29b741
PB
394if 'ust' in get_option('trace_backends')
395 lttng = dependency('lttng-ust', required: true, method: 'pkg-config',
396 kwargs: static_kwargs)
a81df1b6 397endif
b7612f45
PB
398pixman = not_found
399if have_system or have_tools
400 pixman = dependency('pixman-1', required: have_system, version:'>=0.21.8',
d7dedf42 401 method: 'pkg-config', kwargs: static_kwargs)
b7612f45 402endif
5e5733e5 403libaio = cc.find_library('aio', required: false)
d7dedf42 404zlib = dependency('zlib', required: true, kwargs: static_kwargs)
53c22b68 405
5e5733e5 406linux_io_uring = not_found
53c22b68
PB
407if not get_option('linux_io_uring').auto() or have_block
408 linux_io_uring = dependency('liburing', required: get_option('linux_io_uring'),
409 method: 'pkg-config', kwargs: static_kwargs)
5e5733e5
MAL
410endif
411libxml2 = not_found
c5b36c25
PB
412if not get_option('libxml2').auto() or have_block
413 libxml2 = dependency('libxml-2.0', required: get_option('libxml2'),
414 method: 'pkg-config', kwargs: static_kwargs)
5e5733e5
MAL
415endif
416libnfs = not_found
30045c05
PB
417if not get_option('libnfs').auto() or have_block
418 libnfs = dependency('libnfs', version: '>=1.9.3',
419 required: get_option('libnfs'),
d7dedf42 420 method: 'pkg-config', kwargs: static_kwargs)
5e5733e5 421endif
f7f2d651
PB
422
423libattr_test = '''
424 #include <stddef.h>
425 #include <sys/types.h>
426 #ifdef CONFIG_LIBATTR
427 #include <attr/xattr.h>
428 #else
429 #include <sys/xattr.h>
430 #endif
431 int main(void) { getxattr(NULL, NULL, NULL, 0); setxattr(NULL, NULL, NULL, 0, 0); return 0; }'''
432
ec0d5893 433libattr = not_found
f7f2d651
PB
434have_old_libattr = false
435if not get_option('attr').disabled()
436 if cc.links(libattr_test)
437 libattr = declare_dependency()
438 else
439 libattr = cc.find_library('attr', has_headers: ['attr/xattr.h'],
440 required: get_option('attr'),
d7dedf42 441 kwargs: static_kwargs)
f7f2d651
PB
442 if libattr.found() and not \
443 cc.links(libattr_test, dependencies: libattr, args: '-DCONFIG_LIBATTR')
444 libattr = not_found
445 if get_option('attr').enabled()
446 error('could not link libattr')
447 else
448 warning('could not link libattr, disabling')
449 endif
450 else
451 have_old_libattr = libattr.found()
452 endif
453 endif
ec0d5893 454endif
f7f2d651 455
c1ec4941
PB
456cocoa = dependency('appleframeworks', modules: 'Cocoa', required: get_option('cocoa'))
457if cocoa.found() and get_option('sdl').enabled()
458 error('Cocoa and SDL cannot be enabled at the same time')
459endif
460if cocoa.found() and get_option('gtk').enabled()
461 error('Cocoa and GTK+ cannot be enabled at the same time')
462endif
463
3f99cf57 464seccomp = not_found
90835c2b
PB
465if not get_option('seccomp').auto() or have_system or have_tools
466 seccomp = dependency('libseccomp', version: '>=2.3.0',
467 required: get_option('seccomp'),
d7dedf42 468 method: 'pkg-config', kwargs: static_kwargs)
3f99cf57 469endif
727c8bb8 470
3f99cf57 471libcap_ng = not_found
727c8bb8
PB
472if not get_option('cap_ng').auto() or have_system or have_tools
473 libcap_ng = cc.find_library('cap-ng', has_headers: ['cap-ng.h'],
474 required: get_option('cap_ng'),
d7dedf42 475 kwargs: static_kwargs)
727c8bb8
PB
476endif
477if libcap_ng.found() and not cc.links('''
478 #include <cap-ng.h>
479 int main(void)
480 {
481 capng_capability_to_name(CAPNG_EFFECTIVE);
482 return 0;
483 }''', dependencies: libcap_ng)
484 libcap_ng = not_found
485 if get_option('cap_ng').enabled()
486 error('could not link libcap-ng')
487 else
488 warning('could not link libcap-ng, disabling')
489 endif
3f99cf57 490endif
727c8bb8 491
1917ec6d
PB
492if get_option('xkbcommon').auto() and not have_system and not have_tools
493 xkbcommon = not_found
494else
495 xkbcommon = dependency('xkbcommon', required: get_option('xkbcommon'),
d7dedf42 496 method: 'pkg-config', kwargs: static_kwargs)
ade60d4f 497endif
cdaf0722
MAL
498vde = not_found
499if config_host.has_key('CONFIG_VDE')
500 vde = declare_dependency(link_args: config_host['VDE_LIBS'].split())
501endif
87430d5b 502
478e943f 503pulse = not_found
87430d5b
PB
504if not get_option('pa').auto() or (targetos == 'linux' and have_system)
505 pulse = dependency('libpulse', required: get_option('pa'),
506 method: 'pkg-config', kwargs: static_kwargs)
478e943f
PB
507endif
508alsa = not_found
87430d5b
PB
509if not get_option('alsa').auto() or (targetos == 'linux' and have_system)
510 alsa = dependency('alsa', required: get_option('alsa'),
511 method: 'pkg-config', kwargs: static_kwargs)
478e943f
PB
512endif
513jack = not_found
87430d5b
PB
514if not get_option('jack').auto() or have_system
515 jack = dependency('jack', required: get_option('jack'),
516 method: 'pkg-config', kwargs: static_kwargs)
478e943f 517endif
87430d5b 518
2634733c 519spice = not_found
d72c34cc 520spice_headers = not_found
58d3f3ff 521spice_protocol = not_found
2634733c
PB
522if 'CONFIG_SPICE' in config_host
523 spice = declare_dependency(compile_args: config_host['SPICE_CFLAGS'].split(),
524 link_args: config_host['SPICE_LIBS'].split())
d72c34cc 525 spice_headers = declare_dependency(compile_args: config_host['SPICE_CFLAGS'].split())
2634733c 526endif
58d3f3ff
GH
527if 'CONFIG_SPICE_PROTOCOL' in config_host
528 spice_protocol = declare_dependency(compile_args: config_host['SPICE_PROTOCOL_CFLAGS'].split())
529endif
5ee24e78 530rt = cc.find_library('rt', required: false)
ccf7afa5
PB
531libdl = not_found
532if 'CONFIG_PLUGIN' in config_host
e8575f25
AB
533 libdl = cc.find_library('dl', required: false)
534 if not cc.has_function('dlopen', dependencies: libdl)
535 error('dlopen not found')
536 endif
ccf7afa5 537endif
99650b62 538libiscsi = not_found
9db405a3
PB
539if not get_option('libiscsi').auto() or have_block
540 libiscsi = dependency('libiscsi', version: '>=1.9.0',
541 required: get_option('libiscsi'),
d7dedf42 542 method: 'pkg-config', kwargs: static_kwargs)
99650b62 543endif
5e5733e5 544zstd = not_found
b1def33d
PB
545if not get_option('zstd').auto() or have_block
546 zstd = dependency('libzstd', version: '>=1.4.0',
547 required: get_option('zstd'),
d7dedf42 548 method: 'pkg-config', kwargs: static_kwargs)
5e5733e5 549endif
ea458960 550virgl = not_found
587d59d6
PB
551if not get_option('virglrenderer').auto() or have_system
552 virgl = dependency('virglrenderer',
553 method: 'pkg-config',
554 required: get_option('virglrenderer'),
555 kwargs: static_kwargs)
ea458960 556endif
1d7bb6ab 557curl = not_found
f9cd86fe
PB
558if not get_option('curl').auto() or have_block
559 curl = dependency('libcurl', version: '>=7.29.0',
560 method: 'pkg-config',
561 required: get_option('curl'),
d7dedf42 562 kwargs: static_kwargs)
1d7bb6ab 563endif
f15bff25 564libudev = not_found
f01496a3 565if targetos == 'linux' and (have_system or have_tools)
6ec0e15d 566 libudev = dependency('libudev',
a0fbbb6e 567 method: 'pkg-config',
5c53015a 568 required: get_option('libudev'),
d7dedf42 569 kwargs: static_kwargs)
6ec0e15d
PB
570endif
571
5c53015a 572mpathlibs = [libudev]
6ec0e15d
PB
573mpathpersist = not_found
574mpathpersist_new_api = false
575if targetos == 'linux' and have_tools and not get_option('mpath').disabled()
576 mpath_test_source_new = '''
577 #include <libudev.h>
578 #include <mpath_persist.h>
579 unsigned mpath_mx_alloc_len = 1024;
580 int logsink;
581 static struct config *multipath_conf;
582 extern struct udev *udev;
583 extern struct config *get_multipath_config(void);
584 extern void put_multipath_config(struct config *conf);
585 struct udev *udev;
586 struct config *get_multipath_config(void) { return multipath_conf; }
587 void put_multipath_config(struct config *conf) { }
588 int main(void) {
589 udev = udev_new();
590 multipath_conf = mpath_lib_init();
591 return 0;
592 }'''
593 mpath_test_source_old = '''
594 #include <libudev.h>
595 #include <mpath_persist.h>
596 unsigned mpath_mx_alloc_len = 1024;
597 int logsink;
598 int main(void) {
599 struct udev *udev = udev_new();
600 mpath_lib_init(udev);
601 return 0;
602 }'''
5c53015a
PB
603 libmpathpersist = cc.find_library('mpathpersist',
604 required: get_option('mpath'),
d7dedf42 605 kwargs: static_kwargs)
5c53015a
PB
606 if libmpathpersist.found()
607 mpathlibs += libmpathpersist
608 if enable_static
609 mpathlibs += cc.find_library('devmapper',
610 required: get_option('mpath'),
d7dedf42 611 kwargs: static_kwargs)
43b43a40 612 endif
5c53015a
PB
613 mpathlibs += cc.find_library('multipath',
614 required: get_option('mpath'),
d7dedf42 615 kwargs: static_kwargs)
5c53015a
PB
616 foreach lib: mpathlibs
617 if not lib.found()
618 mpathlibs = []
619 break
620 endif
621 endforeach
622 if mpathlibs.length() == 0
623 msg = 'Dependencies missing for libmpathpersist'
624 elif cc.links(mpath_test_source_new, dependencies: mpathlibs)
6ec0e15d
PB
625 mpathpersist = declare_dependency(dependencies: mpathlibs)
626 mpathpersist_new_api = true
627 elif cc.links(mpath_test_source_old, dependencies: mpathlibs)
628 mpathpersist = declare_dependency(dependencies: mpathlibs)
629 else
5c53015a
PB
630 msg = 'Cannot detect libmpathpersist API'
631 endif
632 if not mpathpersist.found()
6ec0e15d 633 if get_option('mpath').enabled()
5c53015a 634 error(msg)
6ec0e15d 635 else
5c53015a 636 warning(msg + ', disabling')
6ec0e15d
PB
637 endif
638 endif
639 endif
f15bff25 640endif
6ec0e15d 641
5285e593 642iconv = not_found
5285e593 643curses = not_found
30fe76b1 644if have_system and not get_option('curses').disabled()
925a40df
PB
645 curses_test = '''
646 #include <locale.h>
647 #include <curses.h>
648 #include <wchar.h>
649 int main(void) {
650 wchar_t wch = L'w';
651 setlocale(LC_ALL, "");
652 resize_term(0, 0);
653 addwstr(L"wide chars\n");
654 addnwstr(&wch, 1);
655 add_wch(WACS_DEGREE);
656 return 0;
657 }'''
658
ca31e307
YL
659 curses_dep_list = targetos == 'windows' ? ['ncurses', 'ncursesw'] : ['ncursesw']
660 foreach curses_dep : curses_dep_list
661 if not curses.found()
662 curses = dependency(curses_dep,
663 required: false,
664 method: 'pkg-config',
d7dedf42 665 kwargs: static_kwargs)
ca31e307
YL
666 endif
667 endforeach
925a40df 668 msg = get_option('curses').enabled() ? 'curses library not found' : ''
0dbce6ef 669 curses_compile_args = ['-DNCURSES_WIDECHAR']
925a40df 670 if curses.found()
0dbce6ef
PB
671 if cc.links(curses_test, args: curses_compile_args, dependencies: [curses])
672 curses = declare_dependency(compile_args: curses_compile_args, dependencies: [curses])
925a40df
PB
673 else
674 msg = 'curses package not usable'
675 curses = not_found
5285e593
YL
676 endif
677 endif
925a40df 678 if not curses.found()
925a40df
PB
679 has_curses_h = cc.has_header('curses.h', args: curses_compile_args)
680 if targetos != 'windows' and not has_curses_h
681 message('Trying with /usr/include/ncursesw')
682 curses_compile_args += ['-I/usr/include/ncursesw']
683 has_curses_h = cc.has_header('curses.h', args: curses_compile_args)
684 endif
685 if has_curses_h
686 curses_libname_list = (targetos == 'windows' ? ['pdcurses'] : ['ncursesw', 'cursesw'])
687 foreach curses_libname : curses_libname_list
5285e593
YL
688 libcurses = cc.find_library(curses_libname,
689 required: false,
d7dedf42 690 kwargs: static_kwargs)
925a40df
PB
691 if libcurses.found()
692 if cc.links(curses_test, args: curses_compile_args, dependencies: libcurses)
693 curses = declare_dependency(compile_args: curses_compile_args,
694 dependencies: [libcurses])
695 break
696 else
697 msg = 'curses library not usable'
698 endif
5285e593 699 endif
925a40df
PB
700 endforeach
701 endif
702 endif
703 if not get_option('iconv').disabled()
704 foreach link_args : [ ['-liconv'], [] ]
705 # Programs will be linked with glib and this will bring in libiconv on FreeBSD.
706 # We need to use libiconv if available because mixing libiconv's headers with
707 # the system libc does not work.
708 # However, without adding glib to the dependencies -L/usr/local/lib will not be
709 # included in the command line and libiconv will not be found.
710 if cc.links('''
711 #include <iconv.h>
712 int main(void) {
713 iconv_t conv = iconv_open("WCHAR_T", "UCS-2");
714 return conv != (iconv_t) -1;
715 }''', args: config_host['GLIB_CFLAGS'].split() + config_host['GLIB_LIBS'].split() + link_args)
716 iconv = declare_dependency(link_args: link_args, dependencies: glib)
717 break
5285e593 718 endif
30fe76b1
PB
719 endforeach
720 endif
925a40df
PB
721 if curses.found() and not iconv.found()
722 if get_option('iconv').enabled()
723 error('iconv not available')
724 endif
725 msg = 'iconv required for curses UI but not available'
726 curses = not_found
727 endif
728 if not curses.found() and msg != ''
729 if get_option('curses').enabled()
730 error(msg)
30fe76b1 731 else
925a40df 732 warning(msg + ', disabling')
30fe76b1 733 endif
5285e593
YL
734 endif
735endif
736
2634733c 737brlapi = not_found
8c6d4ff4
PB
738if not get_option('brlapi').auto() or have_system
739 brlapi = cc.find_library('brlapi', has_headers: ['brlapi.h'],
740 required: get_option('brlapi'),
d7dedf42 741 kwargs: static_kwargs)
8c6d4ff4
PB
742 if brlapi.found() and not cc.links('''
743 #include <brlapi.h>
744 #include <stddef.h>
745 int main(void) { return brlapi__openConnection (NULL, NULL, NULL); }''', dependencies: brlapi)
746 brlapi = not_found
747 if get_option('brlapi').enabled()
748 error('could not link brlapi')
749 else
750 warning('could not link brlapi, disabling')
751 endif
752 endif
2634733c 753endif
35be72ba 754
760e4327 755sdl = not_found
c1ec4941 756if not get_option('sdl').auto() or (have_system and not cocoa.found())
d7dedf42 757 sdl = dependency('sdl2', required: get_option('sdl'), kwargs: static_kwargs)
760e4327
PB
758 sdl_image = not_found
759endif
35be72ba
PB
760if sdl.found()
761 # work around 2.0.8 bug
762 sdl = declare_dependency(compile_args: '-Wno-undef',
763 dependencies: sdl)
7161a433 764 sdl_image = dependency('SDL2_image', required: get_option('sdl_image'),
d7dedf42 765 method: 'pkg-config', kwargs: static_kwargs)
35be72ba
PB
766else
767 if get_option('sdl_image').enabled()
a8dc2ace
ST
768 error('sdl-image required, but SDL was @0@'.format(
769 get_option('sdl').disabled() ? 'disabled' : 'not found'))
35be72ba
PB
770 endif
771 sdl_image = not_found
2634733c 772endif
35be72ba 773
5e5733e5 774rbd = not_found
fabd1e93
PB
775if not get_option('rbd').auto() or have_block
776 librados = cc.find_library('rados', required: get_option('rbd'),
d7dedf42 777 kwargs: static_kwargs)
fabd1e93
PB
778 librbd = cc.find_library('rbd', has_headers: ['rbd/librbd.h'],
779 required: get_option('rbd'),
d7dedf42 780 kwargs: static_kwargs)
c518d6c2
PB
781 if librados.found() and librbd.found()
782 if cc.links('''
783 #include <stdio.h>
784 #include <rbd/librbd.h>
785 int main(void) {
786 rados_t cluster;
787 rados_create(&cluster, NULL);
48672ac0
PL
788 #if LIBRBD_VERSION_CODE < LIBRBD_VERSION(1, 12, 0)
789 #error
790 #endif
c518d6c2
PB
791 return 0;
792 }''', dependencies: [librbd, librados])
793 rbd = declare_dependency(dependencies: [librbd, librados])
794 elif get_option('rbd').enabled()
48672ac0 795 error('librbd >= 1.12.0 required')
c518d6c2 796 else
48672ac0 797 warning('librbd >= 1.12.0 not found, disabling')
c518d6c2 798 endif
fabd1e93 799 endif
5e5733e5 800endif
fabd1e93 801
5e5733e5 802glusterfs = not_found
08821ca2
PB
803glusterfs_ftruncate_has_stat = false
804glusterfs_iocb_has_stat = false
805if not get_option('glusterfs').auto() or have_block
806 glusterfs = dependency('glusterfs-api', version: '>=3',
807 required: get_option('glusterfs'),
d7dedf42 808 method: 'pkg-config', kwargs: static_kwargs)
08821ca2
PB
809 if glusterfs.found()
810 glusterfs_ftruncate_has_stat = cc.links('''
811 #include <glusterfs/api/glfs.h>
812
813 int
814 main(void)
815 {
816 /* new glfs_ftruncate() passes two additional args */
817 return glfs_ftruncate(NULL, 0, NULL, NULL);
818 }
819 ''', dependencies: glusterfs)
820 glusterfs_iocb_has_stat = cc.links('''
821 #include <glusterfs/api/glfs.h>
822
823 /* new glfs_io_cbk() passes two additional glfs_stat structs */
824 static void
825 glusterfs_iocb(glfs_fd_t *fd, ssize_t ret, struct glfs_stat *prestat, struct glfs_stat *poststat, void *data)
826 {}
827
828 int
829 main(void)
830 {
831 glfs_io_cbk iocb = &glusterfs_iocb;
832 iocb(NULL, 0 , NULL, NULL, NULL);
833 return 0;
834 }
835 ''', dependencies: glusterfs)
836 endif
5e5733e5
MAL
837endif
838libssh = not_found
839if 'CONFIG_LIBSSH' in config_host
840 libssh = declare_dependency(compile_args: config_host['LIBSSH_CFLAGS'].split(),
841 link_args: config_host['LIBSSH_LIBS'].split())
842endif
843libbzip2 = not_found
29ba6116
PB
844if not get_option('bzip2').auto() or have_block
845 libbzip2 = cc.find_library('bz2', has_headers: ['bzlib.h'],
846 required: get_option('bzip2'),
d7dedf42 847 kwargs: static_kwargs)
29ba6116
PB
848 if libbzip2.found() and not cc.links('''
849 #include <bzlib.h>
850 int main(void) { BZ2_bzlibVersion(); return 0; }''', dependencies: libbzip2)
851 libbzip2 = not_found
852 if get_option('bzip2').enabled()
853 error('could not link libbzip2')
854 else
855 warning('could not link libbzip2, disabling')
856 endif
857 endif
5e5733e5 858endif
ecea3696 859
5e5733e5 860liblzfse = not_found
ecea3696
PB
861if not get_option('lzfse').auto() or have_block
862 liblzfse = cc.find_library('lzfse', has_headers: ['lzfse.h'],
863 required: get_option('lzfse'),
d7dedf42 864 kwargs: static_kwargs)
ecea3696
PB
865endif
866if liblzfse.found() and not cc.links('''
867 #include <lzfse.h>
868 int main(void) { lzfse_decode_scratch_size(); return 0; }''', dependencies: liblzfse)
869 liblzfse = not_found
870 if get_option('lzfse').enabled()
871 error('could not link liblzfse')
872 else
873 warning('could not link liblzfse, disabling')
874 endif
5e5733e5 875endif
ecea3696 876
478e943f 877oss = not_found
87430d5b
PB
878if not get_option('oss').auto() or have_system
879 if not cc.has_header('sys/soundcard.h')
880 # not found
881 elif targetos == 'netbsd'
882 oss = cc.find_library('ossaudio', required: get_option('oss'),
883 kwargs: static_kwargs)
884 else
885 oss = declare_dependency()
886 endif
887
888 if not oss.found()
889 if get_option('oss').enabled()
890 error('OSS not found')
891 else
892 warning('OSS not found, disabling')
893 endif
894 endif
478e943f
PB
895endif
896dsound = not_found
87430d5b
PB
897if not get_option('dsound').auto() or (targetos == 'windows' and have_system)
898 if cc.has_header('dsound.h')
899 dsound = declare_dependency(link_args: ['-lole32', '-ldxguid'])
900 endif
901
902 if not dsound.found()
903 if get_option('dsound').enabled()
904 error('DirectSound not found')
905 else
906 warning('DirectSound not found, disabling')
907 endif
908 endif
478e943f 909endif
87430d5b 910
478e943f 911coreaudio = not_found
87430d5b
PB
912if not get_option('coreaudio').auto() or (targetos == 'darwin' and have_system)
913 coreaudio = dependency('appleframeworks', modules: 'CoreAudio',
914 required: get_option('coreaudio'))
915 if coreaudio.found() and not cc.links('''
916 #include <CoreAudio/CoreAudio.h>
917 int main(void)
918 {
919 return (int)AudioGetCurrentHostTime();
920 }''')
921 coreaudio = not_found
922 endif
923
924 if not coreaudio.found()
925 if get_option('coreaudio').enabled()
926 error('CoreAudio not found')
927 else
928 warning('CoreAudio not found, disabling')
929 endif
930 endif
2b1ccdf4 931endif
8bc5184d 932
2b1ccdf4
MAL
933opengl = not_found
934if 'CONFIG_OPENGL' in config_host
de2d3005
PB
935 opengl = declare_dependency(compile_args: config_host['OPENGL_CFLAGS'].split(),
936 link_args: config_host['OPENGL_LIBS'].split())
2b1ccdf4 937endif
8bc5184d
TH
938gbm = not_found
939if (have_system or have_tools) and (virgl.found() or opengl.found())
940 gbm = dependency('gbm', method: 'pkg-config', required: false,
941 kwargs: static_kwargs)
942endif
1b695471 943
57612511 944gnutls = not_found
cc4c7c73 945gnutls_crypto = not_found
abc14fd0 946if get_option('gnutls').enabled() or (get_option('gnutls').auto() and have_system)
cc4c7c73
DB
947 # For general TLS support our min gnutls matches
948 # that implied by our platform support matrix
949 #
950 # For the crypto backends, we look for a newer
951 # gnutls:
952 #
953 # Version 3.6.8 is needed to get XTS
954 # Version 3.6.13 is needed to get PBKDF
955 # Version 3.6.14 is needed to get HW accelerated XTS
956 #
957 # If newer enough gnutls isn't available, we can
958 # still use a different crypto backend to satisfy
959 # the platform support requirements
960 gnutls_crypto = dependency('gnutls', version: '>=3.6.14',
961 method: 'pkg-config',
962 required: false,
963 kwargs: static_kwargs)
964 if gnutls_crypto.found()
965 gnutls = gnutls_crypto
966 else
967 # Our min version if all we need is TLS
968 gnutls = dependency('gnutls', version: '>=3.5.18',
969 method: 'pkg-config',
970 required: get_option('gnutls'),
971 kwargs: static_kwargs)
972 endif
57612511
PB
973endif
974
8bd0931f
DB
975# We prefer use of gnutls for crypto, unless the options
976# explicitly asked for nettle or gcrypt.
977#
978# If gnutls isn't available for crypto, then we'll prefer
979# gcrypt over nettle for performance reasons.
57612511
PB
980gcrypt = not_found
981nettle = not_found
68014044 982xts = 'none'
8bd0931f 983
57612511
PB
984if get_option('nettle').enabled() and get_option('gcrypt').enabled()
985 error('Only one of gcrypt & nettle can be enabled')
57612511 986endif
8bd0931f
DB
987
988# Explicit nettle/gcrypt request, so ignore gnutls for crypto
989if get_option('nettle').enabled() or get_option('gcrypt').enabled()
cc4c7c73
DB
990 gnutls_crypto = not_found
991endif
57612511 992
8bd0931f
DB
993if not gnutls_crypto.found()
994 if (not get_option('gcrypt').auto() or have_system) and not get_option('nettle').enabled()
995 gcrypt = dependency('libgcrypt', version: '>=1.8',
996 method: 'config-tool',
997 required: get_option('gcrypt'),
998 kwargs: static_kwargs)
999 # Debian has removed -lgpg-error from libgcrypt-config
1000 # as it "spreads unnecessary dependencies" which in
1001 # turn breaks static builds...
1002 if gcrypt.found() and enable_static
1003 gcrypt = declare_dependency(dependencies: [
1004 gcrypt,
1005 cc.find_library('gpg-error', required: true, kwargs: static_kwargs)])
1006 endif
57612511 1007 endif
8bd0931f
DB
1008 if (not get_option('nettle').auto() or have_system) and not gcrypt.found()
1009 nettle = dependency('nettle', version: '>=3.4',
1010 method: 'pkg-config',
1011 required: get_option('nettle'),
1012 kwargs: static_kwargs)
1013 if nettle.found() and not cc.has_header('nettle/xts.h', dependencies: nettle)
1014 xts = 'private'
1015 endif
57612511
PB
1016 endif
1017endif
1018
2b1ccdf4 1019gtk = not_found
1b695471 1020gtkx11 = not_found
c23d7b4e 1021vte = not_found
c1ec4941 1022if not get_option('gtk').auto() or (have_system and not cocoa.found())
1b695471
PB
1023 gtk = dependency('gtk+-3.0', version: '>=3.22.0',
1024 method: 'pkg-config',
1025 required: get_option('gtk'),
d7dedf42 1026 kwargs: static_kwargs)
1b695471
PB
1027 if gtk.found()
1028 gtkx11 = dependency('gtk+-x11-3.0', version: '>=3.22.0',
1029 method: 'pkg-config',
1030 required: false,
d7dedf42 1031 kwargs: static_kwargs)
1b695471 1032 gtk = declare_dependency(dependencies: [gtk, gtkx11])
c23d7b4e
PB
1033
1034 if not get_option('vte').auto() or have_system
1035 vte = dependency('vte-2.91',
1036 method: 'pkg-config',
1037 required: get_option('vte'),
1038 kwargs: static_kwargs)
1039 endif
1b695471 1040 endif
2b1ccdf4 1041endif
1b695471 1042
2b1ccdf4 1043x11 = not_found
9d49bcf6 1044if gtkx11.found()
1b695471 1045 x11 = dependency('x11', method: 'pkg-config', required: gtkx11.found(),
d7dedf42 1046 kwargs: static_kwargs)
2b1ccdf4 1047endif
a0b93237 1048vnc = not_found
2b1ccdf4 1049png = not_found
2b1ccdf4 1050jpeg = not_found
2b1ccdf4 1051sasl = not_found
95e2289f 1052if have_system and not get_option('vnc').disabled()
a0b93237
PB
1053 vnc = declare_dependency() # dummy dependency
1054 png = dependency('libpng', required: get_option('vnc_png'),
d7dedf42 1055 method: 'pkg-config', kwargs: static_kwargs)
8e242b3c 1056 jpeg = dependency('libjpeg', required: get_option('vnc_jpeg'),
d7dedf42 1057 method: 'pkg-config', kwargs: static_kwargs)
a0b93237
PB
1058 sasl = cc.find_library('sasl2', has_headers: ['sasl/sasl.h'],
1059 required: get_option('vnc_sasl'),
d7dedf42 1060 kwargs: static_kwargs)
a0b93237
PB
1061 if sasl.found()
1062 sasl = declare_dependency(dependencies: sasl,
1063 compile_args: '-DSTRUCT_IOVEC_DEFINED')
1064 endif
478e943f 1065endif
241611ea 1066
05e391ae
PB
1067pam = not_found
1068if not get_option('auth_pam').auto() or have_system
1069 pam = cc.find_library('pam', has_headers: ['security/pam_appl.h'],
1070 required: get_option('auth_pam'),
1071 kwargs: static_kwargs)
1072endif
1073if pam.found() and not cc.links('''
1074 #include <stddef.h>
1075 #include <security/pam_appl.h>
1076 int main(void) {
1077 const char *service_name = "qemu";
1078 const char *user = "frank";
1079 const struct pam_conv pam_conv = { 0 };
1080 pam_handle_t *pamh = NULL;
1081 pam_start(service_name, user, &pam_conv, &pamh);
1082 return 0;
1083 }''', dependencies: pam)
1084 pam = not_found
1085 if get_option('auth_pam').enabled()
1086 error('could not link libpam')
1087 else
1088 warning('could not link libpam, disabling')
1089 endif
1090endif
1091
708eab42 1092snappy = not_found
241611ea
PB
1093if not get_option('snappy').auto() or have_system
1094 snappy = cc.find_library('snappy', has_headers: ['snappy-c.h'],
1095 required: get_option('snappy'),
d7dedf42 1096 kwargs: static_kwargs)
241611ea
PB
1097endif
1098if snappy.found() and not cc.links('''
1099 #include <snappy-c.h>
1100 int main(void) { snappy_max_compressed_length(4096); return 0; }''', dependencies: snappy)
1101 snappy = not_found
1102 if get_option('snappy').enabled()
1103 error('could not link libsnappy')
1104 else
1105 warning('could not link libsnappy, disabling')
1106 endif
708eab42 1107endif
0c32a0ae 1108
708eab42 1109lzo = not_found
0c32a0ae
PB
1110if not get_option('lzo').auto() or have_system
1111 lzo = cc.find_library('lzo2', has_headers: ['lzo/lzo1x.h'],
1112 required: get_option('lzo'),
d7dedf42 1113 kwargs: static_kwargs)
0c32a0ae
PB
1114endif
1115if lzo.found() and not cc.links('''
1116 #include <lzo/lzo1x.h>
1117 int main(void) { lzo_version(); return 0; }''', dependencies: lzo)
1118 lzo = not_found
1119 if get_option('lzo').enabled()
1120 error('could not link liblzo2')
1121 else
1122 warning('could not link liblzo2, disabling')
1123 endif
708eab42 1124endif
0c32a0ae 1125
55166230
MAL
1126rdma = not_found
1127if 'CONFIG_RDMA' in config_host
1128 rdma = declare_dependency(link_args: config_host['RDMA_LIBS'].split())
1129endif
ab318051
MAL
1130numa = not_found
1131if 'CONFIG_NUMA' in config_host
1132 numa = declare_dependency(link_args: config_host['NUMA_LIBS'].split())
1133endif
582ea95f
MAL
1134xen = not_found
1135if 'CONFIG_XEN_BACKEND' in config_host
1136 xen = declare_dependency(compile_args: config_host['XEN_CFLAGS'].split(),
1137 link_args: config_host['XEN_LIBS'].split())
1138endif
06677ce1 1139cacard = not_found
5f364c57
PB
1140if not get_option('smartcard').auto() or have_system
1141 cacard = dependency('libcacard', required: get_option('smartcard'),
1142 version: '>=2.5.1', method: 'pkg-config',
1143 kwargs: static_kwargs)
06677ce1 1144endif
0a40bcb7
CB
1145u2f = not_found
1146if have_system
1147 u2f = dependency('u2f-emu', required: get_option('u2f'),
1148 method: 'pkg-config',
d7dedf42 1149 kwargs: static_kwargs)
0a40bcb7 1150endif
06677ce1 1151usbredir = not_found
18f31e60
PB
1152if not get_option('usb_redir').auto() or have_system
1153 usbredir = dependency('libusbredirparser-0.5', required: get_option('usb_redir'),
1154 version: '>=0.6', method: 'pkg-config',
1155 kwargs: static_kwargs)
06677ce1
PB
1156endif
1157libusb = not_found
90540f32
PB
1158if not get_option('libusb').auto() or have_system
1159 libusb = dependency('libusb-1.0', required: get_option('libusb'),
1160 version: '>=1.0.13', method: 'pkg-config',
1161 kwargs: static_kwargs)
06677ce1 1162endif
90540f32 1163
c9322ab5 1164libpmem = not_found
e36e8c70
PB
1165if not get_option('libpmem').auto() or have_system
1166 libpmem = dependency('libpmem', required: get_option('libpmem'),
1167 method: 'pkg-config', kwargs: static_kwargs)
c9322ab5 1168endif
c7c91a74 1169libdaxctl = not_found
83ef1682
PB
1170if not get_option('libdaxctl').auto() or have_system
1171 libdaxctl = dependency('libdaxctl', required: get_option('libdaxctl'),
1172 version: '>=57', method: 'pkg-config',
1173 kwargs: static_kwargs)
c7c91a74 1174endif
8ce0a45f 1175tasn1 = not_found
ba7ed407
PB
1176if gnutls.found()
1177 tasn1 = dependency('libtasn1',
1178 method: 'pkg-config',
1179 kwargs: static_kwargs)
8ce0a45f 1180endif
af04e89d 1181keyutils = dependency('libkeyutils', required: false,
d7dedf42 1182 method: 'pkg-config', kwargs: static_kwargs)
a81df1b6 1183
3909def8
MAL
1184has_gettid = cc.has_function('gettid')
1185
aa087962
PB
1186# Malloc tests
1187
1188malloc = []
1189if get_option('malloc') == 'system'
1190 has_malloc_trim = \
1191 not get_option('malloc_trim').disabled() and \
1192 cc.links('''#include <malloc.h>
1193 int main(void) { malloc_trim(0); return 0; }''')
1194else
1195 has_malloc_trim = false
1196 malloc = cc.find_library(get_option('malloc'), required: true)
1197endif
1198if not has_malloc_trim and get_option('malloc_trim').enabled()
1199 if get_option('malloc') == 'system'
1200 error('malloc_trim not available on this platform.')
1201 else
1202 error('malloc_trim not available with non-libc memory allocator')
1203 endif
1204endif
1205
84e319a5
HR
1206# Check whether the glibc provides statx()
1207
e66420ac 1208gnu_source_prefix = '''
84e319a5
HR
1209 #ifndef _GNU_SOURCE
1210 #define _GNU_SOURCE
1211 #endif
e66420ac
PB
1212'''
1213statx_test = gnu_source_prefix + '''
84e319a5
HR
1214 #include <sys/stat.h>
1215 int main(void) {
1216 struct statx statxbuf;
1217 statx(0, "", 0, STATX_BASIC_STATS, &statxbuf);
1218 return 0;
1219 }'''
1220
1221has_statx = cc.links(statx_test)
1222
eb6a3886
SH
1223have_vhost_user_blk_server = (targetos == 'linux' and
1224 'CONFIG_VHOST_USER' in config_host)
e5e856c1
SH
1225
1226if get_option('vhost_user_blk_server').enabled()
1227 if targetos != 'linux'
1228 error('vhost_user_blk_server requires linux')
eb6a3886
SH
1229 elif 'CONFIG_VHOST_USER' not in config_host
1230 error('vhost_user_blk_server requires vhost-user support')
e5e856c1
SH
1231 endif
1232elif get_option('vhost_user_blk_server').disabled() or not have_system
1233 have_vhost_user_blk_server = false
1234endif
1235
9e62ba48 1236
df4ea709
HR
1237if get_option('fuse').disabled() and get_option('fuse_lseek').enabled()
1238 error('Cannot enable fuse-lseek while fuse is disabled')
1239endif
1240
a484a719
HR
1241fuse = dependency('fuse3', required: get_option('fuse'),
1242 version: '>=3.1', method: 'pkg-config',
d7dedf42 1243 kwargs: static_kwargs)
a484a719 1244
df4ea709
HR
1245fuse_lseek = not_found
1246if not get_option('fuse_lseek').disabled()
1247 if fuse.version().version_compare('>=3.8')
1248 # Dummy dependency
1249 fuse_lseek = declare_dependency()
1250 elif get_option('fuse_lseek').enabled()
1251 if fuse.found()
1252 error('fuse-lseek requires libfuse >=3.8, found ' + fuse.version())
1253 else
1254 error('fuse-lseek requires libfuse, which was not found')
1255 endif
1256 endif
1257endif
1258
46627f41
AM
1259# libbpf
1260libbpf = dependency('libbpf', required: get_option('bpf'), method: 'pkg-config')
1261if libbpf.found() and not cc.links('''
1262 #include <bpf/libbpf.h>
1263 int main(void)
1264 {
1265 bpf_object__destroy_skeleton(NULL);
1266 return 0;
1267 }''', dependencies: libbpf)
1268 libbpf = not_found
1269 if get_option('bpf').enabled()
1270 error('libbpf skeleton test failed')
1271 else
1272 warning('libbpf skeleton test failed, disabling')
1273 endif
1274endif
1275
87430d5b
PB
1276#################
1277# config-host.h #
1278#################
1279
1280audio_drivers_selected = []
1281if have_system
1282 audio_drivers_available = {
1283 'alsa': alsa.found(),
1284 'coreaudio': coreaudio.found(),
1285 'dsound': dsound.found(),
1286 'jack': jack.found(),
1287 'oss': oss.found(),
1288 'pa': pulse.found(),
1289 'sdl': sdl.found(),
1290 }
e5424a29
PB
1291 foreach k, v: audio_drivers_available
1292 config_host_data.set('CONFIG_AUDIO_' + k.to_upper(), v)
1293 endforeach
87430d5b
PB
1294
1295 # Default to native drivers first, OSS second, SDL third
1296 audio_drivers_priority = \
1297 [ 'pa', 'coreaudio', 'dsound', 'oss' ] + \
1298 (targetos == 'linux' ? [] : [ 'sdl' ])
1299 audio_drivers_default = []
1300 foreach k: audio_drivers_priority
1301 if audio_drivers_available[k]
1302 audio_drivers_default += k
1303 endif
1304 endforeach
1305
1306 foreach k: get_option('audio_drv_list')
1307 if k == 'default'
1308 audio_drivers_selected += audio_drivers_default
1309 elif not audio_drivers_available[k]
1310 error('Audio driver "@0@" not available.'.format(k))
1311 else
1312 audio_drivers_selected += k
1313 endif
1314 endforeach
1315endif
87430d5b
PB
1316config_host_data.set('CONFIG_AUDIO_DRIVERS',
1317 '"' + '", "'.join(audio_drivers_selected) + '", ')
1318
9e62ba48
DB
1319if get_option('cfi')
1320 cfi_flags=[]
1321 # Check for dependency on LTO
1322 if not get_option('b_lto')
1323 error('Selected Control-Flow Integrity but LTO is disabled')
1324 endif
1325 if config_host.has_key('CONFIG_MODULES')
1326 error('Selected Control-Flow Integrity is not compatible with modules')
1327 endif
1328 # Check for cfi flags. CFI requires LTO so we can't use
1329 # get_supported_arguments, but need a more complex "compiles" which allows
1330 # custom arguments
1331 if cc.compiles('int main () { return 0; }', name: '-fsanitize=cfi-icall',
1332 args: ['-flto', '-fsanitize=cfi-icall'] )
1333 cfi_flags += '-fsanitize=cfi-icall'
1334 else
1335 error('-fsanitize=cfi-icall is not supported by the compiler')
1336 endif
1337 if cc.compiles('int main () { return 0; }',
1338 name: '-fsanitize-cfi-icall-generalize-pointers',
1339 args: ['-flto', '-fsanitize=cfi-icall',
1340 '-fsanitize-cfi-icall-generalize-pointers'] )
1341 cfi_flags += '-fsanitize-cfi-icall-generalize-pointers'
1342 else
1343 error('-fsanitize-cfi-icall-generalize-pointers is not supported by the compiler')
1344 endif
1345 if get_option('cfi_debug')
1346 if cc.compiles('int main () { return 0; }',
1347 name: '-fno-sanitize-trap=cfi-icall',
1348 args: ['-flto', '-fsanitize=cfi-icall',
1349 '-fno-sanitize-trap=cfi-icall'] )
1350 cfi_flags += '-fno-sanitize-trap=cfi-icall'
1351 else
1352 error('-fno-sanitize-trap=cfi-icall is not supported by the compiler')
1353 endif
1354 endif
5fc0617f
MAL
1355 add_global_arguments(cfi_flags, native: false, language: ['c', 'cpp', 'objc'])
1356 add_global_link_arguments(cfi_flags, native: false, language: ['c', 'cpp', 'objc'])
9e62ba48
DB
1357endif
1358
14176c8d
JD
1359have_host_block_device = (targetos != 'darwin' or
1360 cc.has_header('IOKit/storage/IOMedia.h'))
1361
69202b40
PB
1362have_virtfs = (targetos == 'linux' and
1363 have_system and
1364 libattr.found() and
1365 libcap_ng.found())
1366
3a489d38
PMD
1367have_virtfs_proxy_helper = have_virtfs and have_tools
1368
69202b40
PB
1369if get_option('virtfs').enabled()
1370 if not have_virtfs
1371 if targetos != 'linux'
1372 error('virtio-9p (virtfs) requires Linux')
1373 elif not libcap_ng.found() or not libattr.found()
1374 error('virtio-9p (virtfs) requires libcap-ng-devel and libattr-devel')
1375 elif not have_system
1376 error('virtio-9p (virtfs) needs system emulation support')
1377 endif
1378 endif
1379elif get_option('virtfs').disabled()
1380 have_virtfs = false
1381endif
1382
9c29b741
PB
1383foreach k : get_option('trace_backends')
1384 config_host_data.set('CONFIG_TRACE_' + k.to_upper(), true)
1385endforeach
1386config_host_data.set_quoted('CONFIG_TRACE_FILE', get_option('trace_file'))
1387
16bf7a33
PB
1388config_host_data.set_quoted('CONFIG_BINDIR', get_option('prefix') / get_option('bindir'))
1389config_host_data.set_quoted('CONFIG_PREFIX', get_option('prefix'))
1390config_host_data.set_quoted('CONFIG_QEMU_CONFDIR', get_option('prefix') / qemu_confdir)
1391config_host_data.set_quoted('CONFIG_QEMU_DATADIR', get_option('prefix') / qemu_datadir)
1392config_host_data.set_quoted('CONFIG_QEMU_DESKTOPDIR', get_option('prefix') / qemu_desktopdir)
1393config_host_data.set_quoted('CONFIG_QEMU_FIRMWAREPATH', get_option('qemu_firmwarepath'))
1394config_host_data.set_quoted('CONFIG_QEMU_HELPERDIR', get_option('prefix') / get_option('libexecdir'))
1395config_host_data.set_quoted('CONFIG_QEMU_ICONDIR', get_option('prefix') / qemu_icondir)
1396config_host_data.set_quoted('CONFIG_QEMU_LOCALEDIR', get_option('prefix') / get_option('localedir'))
1397config_host_data.set_quoted('CONFIG_QEMU_LOCALSTATEDIR', get_option('prefix') / get_option('localstatedir'))
1398config_host_data.set_quoted('CONFIG_QEMU_MODDIR', get_option('prefix') / qemu_moddir)
1399config_host_data.set_quoted('CONFIG_SYSCONFDIR', get_option('prefix') / get_option('sysconfdir'))
1400
f7f2d651 1401config_host_data.set('CONFIG_ATTR', libattr.found())
8c6d4ff4 1402config_host_data.set('CONFIG_BRLAPI', brlapi.found())
b4e312e9 1403config_host_data.set('CONFIG_COCOA', cocoa.found())
537b7248 1404config_host_data.set('CONFIG_FUZZ', get_option('fuzzing'))
af2bb99b 1405config_host_data.set('CONFIG_GCOV', get_option('b_coverage'))
f01496a3 1406config_host_data.set('CONFIG_LIBUDEV', libudev.found())
0c32a0ae 1407config_host_data.set('CONFIG_LZO', lzo.found())
6ec0e15d
PB
1408config_host_data.set('CONFIG_MPATH', mpathpersist.found())
1409config_host_data.set('CONFIG_MPATH_NEW_API', mpathpersist_new_api)
f9cd86fe 1410config_host_data.set('CONFIG_CURL', curl.found())
5285e593 1411config_host_data.set('CONFIG_CURSES', curses.found())
8bc5184d 1412config_host_data.set('CONFIG_GBM', gbm.found())
08821ca2
PB
1413config_host_data.set('CONFIG_GLUSTERFS', glusterfs.found())
1414if glusterfs.found()
1415 config_host_data.set('CONFIG_GLUSTERFS_XLATOR_OPT', glusterfs.version().version_compare('>=4'))
1416 config_host_data.set('CONFIG_GLUSTERFS_DISCARD', glusterfs.version().version_compare('>=5'))
1417 config_host_data.set('CONFIG_GLUSTERFS_FALLOCATE', glusterfs.version().version_compare('>=6'))
1418 config_host_data.set('CONFIG_GLUSTERFS_ZEROFILL', glusterfs.version().version_compare('>=6'))
1419 config_host_data.set('CONFIG_GLUSTERFS_FTRUNCATE_HAS_STAT', glusterfs_ftruncate_has_stat)
1420 config_host_data.set('CONFIG_GLUSTERFS_IOCB_HAS_STAT', glusterfs_iocb_has_stat)
1421endif
1b695471 1422config_host_data.set('CONFIG_GTK', gtk.found())
c23d7b4e 1423config_host_data.set('CONFIG_VTE', vte.found())
f7f2d651 1424config_host_data.set('CONFIG_LIBATTR', have_old_libattr)
727c8bb8 1425config_host_data.set('CONFIG_LIBCAP_NG', libcap_ng.found())
46627f41 1426config_host_data.set('CONFIG_EBPF', libbpf.found())
63a7f853 1427config_host_data.set('CONFIG_LIBDAXCTL', libdaxctl.found())
9db405a3 1428config_host_data.set('CONFIG_LIBISCSI', libiscsi.found())
30045c05 1429config_host_data.set('CONFIG_LIBNFS', libnfs.found())
63a7f853
PB
1430config_host_data.set('CONFIG_LINUX_IO_URING', linux_io_uring.found())
1431config_host_data.set('CONFIG_LIBPMEM', libpmem.found())
fabd1e93 1432config_host_data.set('CONFIG_RBD', rbd.found())
35be72ba
PB
1433config_host_data.set('CONFIG_SDL', sdl.found())
1434config_host_data.set('CONFIG_SDL_IMAGE', sdl_image.found())
90835c2b 1435config_host_data.set('CONFIG_SECCOMP', seccomp.found())
241611ea 1436config_host_data.set('CONFIG_SNAPPY', snappy.found())
90540f32 1437config_host_data.set('CONFIG_USB_LIBUSB', libusb.found())
e5e856c1 1438config_host_data.set('CONFIG_VHOST_USER_BLK_SERVER', have_vhost_user_blk_server)
a0b93237
PB
1439config_host_data.set('CONFIG_VNC', vnc.found())
1440config_host_data.set('CONFIG_VNC_JPEG', jpeg.found())
1441config_host_data.set('CONFIG_VNC_PNG', png.found())
1442config_host_data.set('CONFIG_VNC_SASL', sasl.found())
69202b40 1443config_host_data.set('CONFIG_VIRTFS', have_virtfs)
63a7f853 1444config_host_data.set('CONFIG_VTE', vte.found())
4113f4cf 1445config_host_data.set('CONFIG_XKBCOMMON', xkbcommon.found())
af04e89d 1446config_host_data.set('CONFIG_KEYUTILS', keyutils.found())
3909def8 1447config_host_data.set('CONFIG_GETTID', has_gettid)
57612511 1448config_host_data.set('CONFIG_GNUTLS', gnutls.found())
cc4c7c73 1449config_host_data.set('CONFIG_GNUTLS_CRYPTO', gnutls_crypto.found())
57612511
PB
1450config_host_data.set('CONFIG_GCRYPT', gcrypt.found())
1451config_host_data.set('CONFIG_NETTLE', nettle.found())
1452config_host_data.set('CONFIG_QEMU_PRIVATE_XTS', xts == 'private')
aa087962 1453config_host_data.set('CONFIG_MALLOC_TRIM', has_malloc_trim)
84e319a5 1454config_host_data.set('CONFIG_STATX', has_statx)
b1def33d 1455config_host_data.set('CONFIG_ZSTD', zstd.found())
a484a719 1456config_host_data.set('CONFIG_FUSE', fuse.found())
df4ea709 1457config_host_data.set('CONFIG_FUSE_LSEEK', fuse_lseek.found())
9d71037f 1458config_host_data.set('CONFIG_X11', x11.found())
9e62ba48 1459config_host_data.set('CONFIG_CFI', get_option('cfi'))
859aef02
PB
1460config_host_data.set('QEMU_VERSION', '"@0@"'.format(meson.project_version()))
1461config_host_data.set('QEMU_VERSION_MAJOR', meson.project_version().split('.')[0])
1462config_host_data.set('QEMU_VERSION_MINOR', meson.project_version().split('.')[1])
1463config_host_data.set('QEMU_VERSION_MICRO', meson.project_version().split('.')[2])
1464
a6305081 1465config_host_data.set_quoted('CONFIG_HOST_DSOSUF', host_dsosuf)
69d8de7a 1466config_host_data.set('HAVE_HOST_BLOCK_DEVICE', have_host_block_device)
269506d2 1467config_host_data.set('HOST_WORDS_BIGENDIAN', host_machine.endian() == 'big')
69d8de7a
PB
1468
1469# has_header
e66420ac 1470config_host_data.set('CONFIG_EPOLL', cc.has_header('sys/epoll.h'))
d47a8b3b
PB
1471config_host_data.set('CONFIG_LINUX_MAGIC_H', cc.has_header('linux/magic.h'))
1472config_host_data.set('CONFIG_VALGRIND_H', cc.has_header('valgrind/valgrind.h'))
48f670ec 1473config_host_data.set('HAVE_BTRFS_H', cc.has_header('linux/btrfs.h'))
2964be52 1474config_host_data.set('HAVE_DRM_H', cc.has_header('libdrm/drm.h'))
2802d91d 1475config_host_data.set('HAVE_PTY_H', cc.has_header('pty.h'))
69d8de7a 1476config_host_data.set('HAVE_SYS_DISK_H', cc.has_header('sys/disk.h'))
ded5d78c 1477config_host_data.set('HAVE_SYS_IOCCOM_H', cc.has_header('sys/ioccom.h'))
4a9d5f89 1478config_host_data.set('HAVE_SYS_KCOV_H', cc.has_header('sys/kcov.h'))
ded5d78c 1479
69d8de7a 1480# has_function
a620fbe9 1481config_host_data.set('CONFIG_ACCEPT4', cc.has_function('accept4'))
e66420ac
PB
1482config_host_data.set('CONFIG_CLOCK_ADJTIME', cc.has_function('clock_adjtime'))
1483config_host_data.set('CONFIG_DUP3', cc.has_function('dup3'))
1484config_host_data.set('CONFIG_FALLOCATE', cc.has_function('fallocate'))
1485config_host_data.set('CONFIG_POSIX_FALLOCATE', cc.has_function('posix_fallocate'))
e1fbd2c4 1486config_host_data.set('CONFIG_POSIX_MEMALIGN', cc.has_function('posix_memalign'))
e66420ac 1487config_host_data.set('CONFIG_PPOLL', cc.has_function('ppoll'))
2b9f74ef 1488config_host_data.set('CONFIG_PREADV', cc.has_function('preadv', prefix: '#include <sys/uio.h>'))
ed3b3f17 1489config_host_data.set('CONFIG_SEM_TIMEDWAIT', cc.has_function('sem_timedwait', dependencies: threads))
e66420ac
PB
1490config_host_data.set('CONFIG_SENDFILE', cc.has_function('sendfile'))
1491config_host_data.set('CONFIG_SETNS', cc.has_function('setns') and cc.has_function('unshare'))
1492config_host_data.set('CONFIG_SYNCFS', cc.has_function('syncfs'))
1493config_host_data.set('CONFIG_SYNC_FILE_RANGE', cc.has_function('sync_file_range'))
1494config_host_data.set('CONFIG_TIMERFD', cc.has_function('timerfd_create'))
be7e89f6 1495config_host_data.set('HAVE_COPY_FILE_RANGE', cc.has_function('copy_file_range'))
e66420ac 1496config_host_data.set('HAVE_OPENPTY', cc.has_function('openpty', dependencies: util))
ed3b3f17 1497config_host_data.set('HAVE_STRCHRNUL', cc.has_function('strchrnul'))
69d8de7a 1498config_host_data.set('HAVE_SYSTEM_FUNCTION', cc.has_function('system', prefix: '#include <stdlib.h>'))
2b9f74ef 1499
e66420ac
PB
1500# has_header_symbol
1501config_host_data.set('CONFIG_BYTESWAP_H',
1502 cc.has_header_symbol('byteswap.h', 'bswap_32'))
1503config_host_data.set('CONFIG_EPOLL_CREATE1',
1504 cc.has_header_symbol('sys/epoll.h', 'epoll_create1'))
d47a8b3b
PB
1505config_host_data.set('CONFIG_HAS_ENVIRON',
1506 cc.has_header_symbol('unistd.h', 'environ', prefix: gnu_source_prefix))
e66420ac
PB
1507config_host_data.set('CONFIG_FALLOCATE_PUNCH_HOLE',
1508 cc.has_header_symbol('linux/falloc.h', 'FALLOC_FL_PUNCH_HOLE') and
1509 cc.has_header_symbol('linux/falloc.h', 'FALLOC_FL_KEEP_SIZE'))
1510config_host_data.set('CONFIG_FALLOCATE_ZERO_RANGE',
1511 cc.has_header_symbol('linux/falloc.h', 'FALLOC_FL_ZERO_RANGE'))
1512config_host_data.set('CONFIG_FIEMAP',
1513 cc.has_header('linux/fiemap.h') and
1514 cc.has_header_symbol('linux/fs.h', 'FS_IOC_FIEMAP'))
be7e89f6
PB
1515config_host_data.set('CONFIG_GETRANDOM',
1516 cc.has_function('getrandom') and
1517 cc.has_header_symbol('sys/random.h', 'GRND_NONBLOCK'))
a620fbe9
PB
1518config_host_data.set('CONFIG_INOTIFY',
1519 cc.has_header_symbol('sys/inotify.h', 'inotify_init'))
1520config_host_data.set('CONFIG_INOTIFY1',
1521 cc.has_header_symbol('sys/inotify.h', 'inotify_init1'))
e66420ac
PB
1522config_host_data.set('CONFIG_MACHINE_BSWAP_H',
1523 cc.has_header_symbol('machine/bswap.h', 'bswap32',
1524 prefix: '''#include <sys/endian.h>
1525 #include <sys/types.h>'''))
1526config_host_data.set('CONFIG_PRCTL_PR_SET_TIMERSLACK',
1527 cc.has_header_symbol('sys/prctl.h', 'PR_SET_TIMERSLACK'))
be7e89f6
PB
1528config_host_data.set('CONFIG_RTNETLINK',
1529 cc.has_header_symbol('linux/rtnetlink.h', 'IFLA_PROTO_DOWN'))
1530config_host_data.set('CONFIG_SYSMACROS',
1531 cc.has_header_symbol('sys/sysmacros.h', 'makedev'))
e1fbd2c4
PB
1532config_host_data.set('HAVE_OPTRESET',
1533 cc.has_header_symbol('getopt.h', 'optreset'))
be7e89f6
PB
1534config_host_data.set('HAVE_UTMPX',
1535 cc.has_header_symbol('utmpx.h', 'struct utmpx'))
653163fc
MAL
1536config_host_data.set('HAVE_IPPROTO_MPTCP',
1537 cc.has_header_symbol('netinet/in.h', 'IPPROTO_MPTCP'))
e66420ac
PB
1538
1539# has_member
1540config_host_data.set('HAVE_SIGEV_NOTIFY_THREAD_ID',
1541 cc.has_member('struct sigevent', 'sigev_notify_thread_id',
1542 prefix: '#include <signal.h>'))
ed3b3f17
PB
1543config_host_data.set('HAVE_STRUCT_STAT_ST_ATIM',
1544 cc.has_member('struct stat', 'st_atim',
1545 prefix: '#include <sys/stat.h>'))
e66420ac 1546
904ad5ec 1547config_host_data.set('CONFIG_EVENTFD', cc.links('''
e1fbd2c4
PB
1548 #include <sys/eventfd.h>
1549 int main(void) { return eventfd(0, EFD_NONBLOCK | EFD_CLOEXEC); }'''))
904ad5ec 1550config_host_data.set('CONFIG_FDATASYNC', cc.links(gnu_source_prefix + '''
e1fbd2c4
PB
1551 #include <unistd.h>
1552 int main(void) {
1553 #if defined(_POSIX_SYNCHRONIZED_IO) && _POSIX_SYNCHRONIZED_IO > 0
1554 return fdatasync(0);
1555 #else
1556 #error Not supported
1557 #endif
1558 }'''))
904ad5ec 1559config_host_data.set('CONFIG_MADVISE', cc.links(gnu_source_prefix + '''
e1fbd2c4
PB
1560 #include <sys/types.h>
1561 #include <sys/mman.h>
1562 #include <stddef.h>
1563 int main(void) { return madvise(NULL, 0, MADV_DONTNEED); }'''))
904ad5ec 1564config_host_data.set('CONFIG_MEMFD', cc.links(gnu_source_prefix + '''
e1fbd2c4
PB
1565 #include <sys/mman.h>
1566 int main(void) { return memfd_create("foo", MFD_ALLOW_SEALING); }'''))
904ad5ec 1567config_host_data.set('CONFIG_OPEN_BY_HANDLE', cc.links(gnu_source_prefix + '''
d47a8b3b
PB
1568 #include <fcntl.h>
1569 #if !defined(AT_EMPTY_PATH)
1570 # error missing definition
1571 #else
1572 int main(void) { struct file_handle fh; return open_by_handle_at(0, &fh, 0); }
1573 #endif'''))
904ad5ec 1574config_host_data.set('CONFIG_PIPE2', cc.links(gnu_source_prefix + '''
a620fbe9
PB
1575 #include <unistd.h>
1576 #include <fcntl.h>
1577
1578 int main(void)
1579 {
1580 int pipefd[2];
1581 return pipe2(pipefd, O_CLOEXEC);
1582 }'''))
904ad5ec 1583config_host_data.set('CONFIG_POSIX_MADVISE', cc.links(gnu_source_prefix + '''
e1fbd2c4
PB
1584 #include <sys/mman.h>
1585 #include <stddef.h>
1586 int main(void) { return posix_madvise(NULL, 0, POSIX_MADV_DONTNEED); }'''))
10f6b231
PB
1587
1588config_host_data.set('CONFIG_PTHREAD_SETNAME_NP_W_TID', cc.links('''
1589 #include <pthread.h>
1590
1591 static void *f(void *p) { return NULL; }
1592 int main(void)
1593 {
1594 pthread_t thread;
1595 pthread_create(&thread, 0, f, 0);
1596 pthread_setname_np(thread, "QEMU");
1597 return 0;
1598 }''', dependencies: threads))
1599config_host_data.set('CONFIG_PTHREAD_SETNAME_NP_WO_TID', cc.links('''
1600 #include <pthread.h>
1601
1602 static void *f(void *p) { pthread_setname_np("QEMU"); return NULL; }
1603 int main(void)
1604 {
1605 pthread_t thread;
1606 pthread_create(&thread, 0, f, 0);
1607 return 0;
1608 }''', dependencies: threads))
1609
904ad5ec 1610config_host_data.set('CONFIG_SIGNALFD', cc.links(gnu_source_prefix + '''
6bd17dcc
KS
1611 #include <sys/signalfd.h>
1612 #include <stddef.h>
1613 int main(void) { return signalfd(-1, NULL, SFD_CLOEXEC); }'''))
904ad5ec 1614config_host_data.set('CONFIG_SPLICE', cc.links(gnu_source_prefix + '''
a620fbe9
PB
1615 #include <unistd.h>
1616 #include <fcntl.h>
1617 #include <limits.h>
1618
1619 int main(void)
1620 {
1621 int len, fd = 0;
1622 len = tee(STDIN_FILENO, STDOUT_FILENO, INT_MAX, SPLICE_F_NONBLOCK);
1623 splice(STDIN_FILENO, NULL, fd, NULL, len, SPLICE_F_MOVE);
1624 return 0;
1625 }'''))
e1fbd2c4 1626
96a63aeb
PB
1627config_host_data.set('HAVE_MLOCKALL', cc.links(gnu_source_prefix + '''
1628 #include <sys/mman.h>
1629 int main(int argc, char *argv[]) {
1630 return mlockall(MCL_FUTURE);
1631 }'''))
1632
1633# Work around a system header bug with some kernel/XFS header
1634# versions where they both try to define 'struct fsxattr':
1635# xfs headers will not try to redefine structs from linux headers
1636# if this macro is set.
1637config_host_data.set('HAVE_FSXATTR', cc.links('''
1638 #include <linux/fs.h>'
1639 struct fsxattr foo;
1640 int main(void) {
1641 return 0;
1642 }'''))
1643
e46bd55d
PB
1644# Some versions of Mac OS X incorrectly define SIZE_MAX
1645config_host_data.set('HAVE_BROKEN_SIZE_MAX', not cc.compiles('''
1646 #include <stdint.h>
1647 #include <stdio.h>
1648 int main(int argc, char *argv[]) {
1649 return printf("%zu", SIZE_MAX);
1650 }''', args: ['-Werror']))
1651
a76a1f6b
PB
1652ignored = ['CONFIG_QEMU_INTERP_PREFIX', # actually per-target
1653 'HAVE_GDB_BIN']
87430d5b 1654arrays = ['CONFIG_BDRV_RW_WHITELIST', 'CONFIG_BDRV_RO_WHITELIST']
a6305081 1655strings = ['CONFIG_IASL']
859aef02 1656foreach k, v: config_host
765686d6
PB
1657 if ignored.contains(k)
1658 # do nothing
1659 elif arrays.contains(k)
859aef02
PB
1660 if v != ''
1661 v = '"' + '", "'.join(v.split()) + '", '
1662 endif
1663 config_host_data.set(k, v)
1664 elif k == 'ARCH'
1665 config_host_data.set('HOST_' + v.to_upper(), 1)
1666 elif strings.contains(k)
859aef02 1667 config_host_data.set_quoted(k, v)
96a63aeb 1668 elif k.startswith('CONFIG_')
859aef02
PB
1669 config_host_data.set(k, v == 'y' ? 1 : v)
1670 endif
1671endforeach
859aef02 1672
a0c9162c
PB
1673########################
1674# Target configuration #
1675########################
1676
2becc36a 1677minikconf = find_program('scripts/minikconf.py')
05512f55 1678config_all = {}
a98006bc 1679config_all_devices = {}
ca0fc784 1680config_all_disas = {}
2becc36a
PB
1681config_devices_mak_list = []
1682config_devices_h = {}
859aef02 1683config_target_h = {}
2becc36a 1684config_target_mak = {}
ca0fc784
PB
1685
1686disassemblers = {
1687 'alpha' : ['CONFIG_ALPHA_DIS'],
1688 'arm' : ['CONFIG_ARM_DIS'],
1689 'avr' : ['CONFIG_AVR_DIS'],
1690 'cris' : ['CONFIG_CRIS_DIS'],
3e7a84ee 1691 'hexagon' : ['CONFIG_HEXAGON_DIS'],
ca0fc784
PB
1692 'hppa' : ['CONFIG_HPPA_DIS'],
1693 'i386' : ['CONFIG_I386_DIS'],
1694 'x86_64' : ['CONFIG_I386_DIS'],
1695 'x32' : ['CONFIG_I386_DIS'],
ca0fc784
PB
1696 'm68k' : ['CONFIG_M68K_DIS'],
1697 'microblaze' : ['CONFIG_MICROBLAZE_DIS'],
1698 'mips' : ['CONFIG_MIPS_DIS'],
ca0fc784
PB
1699 'nios2' : ['CONFIG_NIOS2_DIS'],
1700 'or1k' : ['CONFIG_OPENRISC_DIS'],
1701 'ppc' : ['CONFIG_PPC_DIS'],
1702 'riscv' : ['CONFIG_RISCV_DIS'],
1703 'rx' : ['CONFIG_RX_DIS'],
1704 's390' : ['CONFIG_S390_DIS'],
1705 'sh4' : ['CONFIG_SH4_DIS'],
1706 'sparc' : ['CONFIG_SPARC_DIS'],
1707 'xtensa' : ['CONFIG_XTENSA_DIS'],
1708}
1709if link_language == 'cpp'
1710 disassemblers += {
1711 'aarch64' : [ 'CONFIG_ARM_A64_DIS'],
1712 'arm' : [ 'CONFIG_ARM_DIS', 'CONFIG_ARM_A64_DIS'],
1713 'mips' : [ 'CONFIG_MIPS_DIS', 'CONFIG_NANOMIPS_DIS'],
1714 }
1715endif
1716
e1fbd2c4 1717have_ivshmem = config_host_data.get('CONFIG_EVENTFD')
0a189110 1718host_kconfig = \
537b7248 1719 (get_option('fuzzing') ? ['CONFIG_FUZZ=y'] : []) + \
0a189110
PB
1720 ('CONFIG_TPM' in config_host ? ['CONFIG_TPM=y'] : []) + \
1721 ('CONFIG_SPICE' in config_host ? ['CONFIG_SPICE=y'] : []) + \
ccd250aa 1722 (have_ivshmem ? ['CONFIG_IVSHMEM=y'] : []) + \
0a189110 1723 ('CONFIG_OPENGL' in config_host ? ['CONFIG_OPENGL=y'] : []) + \
9d71037f 1724 (x11.found() ? ['CONFIG_X11=y'] : []) + \
0a189110
PB
1725 ('CONFIG_VHOST_USER' in config_host ? ['CONFIG_VHOST_USER=y'] : []) + \
1726 ('CONFIG_VHOST_VDPA' in config_host ? ['CONFIG_VHOST_VDPA=y'] : []) + \
1727 ('CONFIG_VHOST_KERNEL' in config_host ? ['CONFIG_VHOST_KERNEL=y'] : []) + \
69202b40 1728 (have_virtfs ? ['CONFIG_VIRTFS=y'] : []) + \
0a189110 1729 ('CONFIG_LINUX' in config_host ? ['CONFIG_LINUX=y'] : []) + \
3090de69 1730 ('CONFIG_PVRDMA' in config_host ? ['CONFIG_PVRDMA=y'] : []) + \
106ad1f9 1731 (multiprocess_allowed ? ['CONFIG_MULTIPROCESS_ALLOWED=y'] : [])
0a189110 1732
a9a74907 1733ignored = [ 'TARGET_XML_FILES', 'TARGET_ABI_DIR', 'TARGET_ARCH' ]
05512f55 1734
fdb75aef
PB
1735default_targets = 'CONFIG_DEFAULT_TARGETS' in config_host
1736actual_target_dirs = []
fbb4121d 1737fdt_required = []
a81df1b6 1738foreach target : target_dirs
765686d6
PB
1739 config_target = { 'TARGET_NAME': target.split('-')[0] }
1740 if target.endswith('linux-user')
fdb75aef
PB
1741 if targetos != 'linux'
1742 if default_targets
1743 continue
1744 endif
1745 error('Target @0@ is only available on a Linux host'.format(target))
1746 endif
765686d6
PB
1747 config_target += { 'CONFIG_LINUX_USER': 'y' }
1748 elif target.endswith('bsd-user')
fdb75aef
PB
1749 if 'CONFIG_BSD' not in config_host
1750 if default_targets
1751 continue
1752 endif
1753 error('Target @0@ is only available on a BSD host'.format(target))
1754 endif
765686d6
PB
1755 config_target += { 'CONFIG_BSD_USER': 'y' }
1756 elif target.endswith('softmmu')
1757 config_target += { 'CONFIG_SOFTMMU': 'y' }
1758 endif
1759 if target.endswith('-user')
1760 config_target += {
1761 'CONFIG_USER_ONLY': 'y',
1762 'CONFIG_QEMU_INTERP_PREFIX':
1763 config_host['CONFIG_QEMU_INTERP_PREFIX'].format(config_target['TARGET_NAME'])
1764 }
1765 endif
859aef02 1766
0a189110 1767 accel_kconfig = []
8a19980e
PB
1768 foreach sym: accelerators
1769 if sym == 'CONFIG_TCG' or target in accelerator_targets.get(sym, [])
1770 config_target += { sym: 'y' }
1771 config_all += { sym: 'y' }
23a77b2d
PB
1772 if sym == 'CONFIG_TCG' and tcg_arch == 'tci'
1773 config_target += { 'CONFIG_TCG_INTERPRETER': 'y' }
1774 elif sym == 'CONFIG_XEN' and have_xen_pci_passthrough
8a19980e
PB
1775 config_target += { 'CONFIG_XEN_PCI_PASSTHROUGH': 'y' }
1776 endif
dae0ec15
GH
1777 if target in modular_tcg
1778 config_target += { 'CONFIG_TCG_MODULAR': 'y' }
1779 else
1780 config_target += { 'CONFIG_TCG_BUILTIN': 'y' }
1781 endif
0a189110 1782 accel_kconfig += [ sym + '=y' ]
8a19980e
PB
1783 endif
1784 endforeach
0a189110 1785 if accel_kconfig.length() == 0
fdb75aef
PB
1786 if default_targets
1787 continue
1788 endif
1789 error('No accelerator available for target @0@'.format(target))
1790 endif
8a19980e 1791
fdb75aef 1792 actual_target_dirs += target
812b31d3 1793 config_target += keyval.load('configs/targets' / target + '.mak')
a9a74907 1794 config_target += { 'TARGET_' + config_target['TARGET_ARCH'].to_upper(): 'y' }
765686d6 1795
fbb4121d
PB
1796 if 'TARGET_NEED_FDT' in config_target
1797 fdt_required += target
1798 endif
1799
fa73168b
PB
1800 # Add default keys
1801 if 'TARGET_BASE_ARCH' not in config_target
1802 config_target += {'TARGET_BASE_ARCH': config_target['TARGET_ARCH']}
1803 endif
1804 if 'TARGET_ABI_DIR' not in config_target
1805 config_target += {'TARGET_ABI_DIR': config_target['TARGET_ARCH']}
1806 endif
859aef02 1807
ca0fc784
PB
1808 foreach k, v: disassemblers
1809 if config_host['ARCH'].startswith(k) or config_target['TARGET_BASE_ARCH'].startswith(k)
1810 foreach sym: v
1811 config_target += { sym: 'y' }
1812 config_all_disas += { sym: 'y' }
1813 endforeach
1814 endif
1815 endforeach
1816
859aef02
PB
1817 config_target_data = configuration_data()
1818 foreach k, v: config_target
1819 if not k.startswith('TARGET_') and not k.startswith('CONFIG_')
1820 # do nothing
1821 elif ignored.contains(k)
1822 # do nothing
1823 elif k == 'TARGET_BASE_ARCH'
a9a74907
PB
1824 # Note that TARGET_BASE_ARCH ends up in config-target.h but it is
1825 # not used to select files from sourcesets.
859aef02 1826 config_target_data.set('TARGET_' + v.to_upper(), 1)
765686d6 1827 elif k == 'TARGET_NAME' or k == 'CONFIG_QEMU_INTERP_PREFIX'
859aef02
PB
1828 config_target_data.set_quoted(k, v)
1829 elif v == 'y'
1830 config_target_data.set(k, 1)
1831 else
1832 config_target_data.set(k, v)
1833 endif
1834 endforeach
cb2c5531
PM
1835 config_target_data.set('QEMU_ARCH',
1836 'QEMU_ARCH_' + config_target['TARGET_BASE_ARCH'].to_upper())
859aef02
PB
1837 config_target_h += {target: configure_file(output: target + '-config-target.h',
1838 configuration: config_target_data)}
2becc36a
PB
1839
1840 if target.endswith('-softmmu')
d1d5e9ee 1841 config_input = meson.get_external_property(target, 'default')
2becc36a
PB
1842 config_devices_mak = target + '-config-devices.mak'
1843 config_devices_mak = configure_file(
d1d5e9ee 1844 input: ['configs/devices' / target / config_input + '.mak', 'Kconfig'],
2becc36a
PB
1845 output: config_devices_mak,
1846 depfile: config_devices_mak + '.d',
1847 capture: true,
7bc3ca7f
PB
1848 command: [minikconf,
1849 get_option('default_devices') ? '--defconfig' : '--allnoconfig',
2becc36a 1850 config_devices_mak, '@DEPFILE@', '@INPUT@',
f4063f9c
PMD
1851 host_kconfig, accel_kconfig,
1852 'CONFIG_' + config_target['TARGET_ARCH'].to_upper() + '=y'])
859aef02
PB
1853
1854 config_devices_data = configuration_data()
1855 config_devices = keyval.load(config_devices_mak)
1856 foreach k, v: config_devices
1857 config_devices_data.set(k, 1)
1858 endforeach
2becc36a 1859 config_devices_mak_list += config_devices_mak
859aef02
PB
1860 config_devices_h += {target: configure_file(output: target + '-config-devices.h',
1861 configuration: config_devices_data)}
1862 config_target += config_devices
a98006bc 1863 config_all_devices += config_devices
2becc36a
PB
1864 endif
1865 config_target_mak += {target: config_target}
a81df1b6 1866endforeach
fdb75aef 1867target_dirs = actual_target_dirs
a81df1b6 1868
2becc36a
PB
1869# This configuration is used to build files that are shared by
1870# multiple binaries, and then extracted out of the "common"
1871# static_library target.
1872#
1873# We do not use all_sources()/all_dependencies(), because it would
1874# build literally all source files, including devices only used by
1875# targets that are not built for this compilation. The CONFIG_ALL
1876# pseudo symbol replaces it.
1877
05512f55 1878config_all += config_all_devices
2becc36a
PB
1879config_all += config_host
1880config_all += config_all_disas
1881config_all += {
1882 'CONFIG_XEN': config_host.has_key('CONFIG_XEN_BACKEND'),
1883 'CONFIG_SOFTMMU': have_system,
1884 'CONFIG_USER_ONLY': have_user,
1885 'CONFIG_ALL': true,
1886}
1887
a0c9162c
PB
1888##############
1889# Submodules #
1890##############
8b18cdbf
RH
1891
1892capstone = not_found
1893capstone_opt = get_option('capstone')
1894if capstone_opt in ['enabled', 'auto', 'system']
1895 have_internal = fs.exists(meson.current_source_dir() / 'capstone/Makefile')
bcf36862 1896 capstone = dependency('capstone', version: '>=4.0',
d7dedf42 1897 kwargs: static_kwargs, method: 'pkg-config',
8b18cdbf
RH
1898 required: capstone_opt == 'system' or
1899 capstone_opt == 'enabled' and not have_internal)
8f4aea71
DB
1900
1901 # Some versions of capstone have broken pkg-config file
1902 # that reports a wrong -I path, causing the #include to
1903 # fail later. If the system has such a broken version
1904 # do not use it.
1905 if capstone.found() and not cc.compiles('#include <capstone.h>',
1906 dependencies: [capstone])
1907 capstone = not_found
1908 if capstone_opt == 'system'
1909 error('system capstone requested, it does not appear to work')
1910 endif
1911 endif
1912
8b18cdbf
RH
1913 if capstone.found()
1914 capstone_opt = 'system'
1915 elif have_internal
1916 capstone_opt = 'internal'
1917 else
1918 capstone_opt = 'disabled'
1919 endif
1920endif
1921if capstone_opt == 'internal'
1922 capstone_data = configuration_data()
1923 capstone_data.set('CAPSTONE_USE_SYS_DYN_MEM', '1')
1924
1925 capstone_files = files(
1926 'capstone/cs.c',
1927 'capstone/MCInst.c',
1928 'capstone/MCInstrDesc.c',
1929 'capstone/MCRegisterInfo.c',
1930 'capstone/SStream.c',
1931 'capstone/utils.c'
1932 )
1933
1934 if 'CONFIG_ARM_DIS' in config_all_disas
1935 capstone_data.set('CAPSTONE_HAS_ARM', '1')
1936 capstone_files += files(
1937 'capstone/arch/ARM/ARMDisassembler.c',
1938 'capstone/arch/ARM/ARMInstPrinter.c',
1939 'capstone/arch/ARM/ARMMapping.c',
1940 'capstone/arch/ARM/ARMModule.c'
1941 )
1942 endif
1943
1944 # FIXME: This config entry currently depends on a c++ compiler.
1945 # Which is needed for building libvixl, but not for capstone.
1946 if 'CONFIG_ARM_A64_DIS' in config_all_disas
1947 capstone_data.set('CAPSTONE_HAS_ARM64', '1')
1948 capstone_files += files(
1949 'capstone/arch/AArch64/AArch64BaseInfo.c',
1950 'capstone/arch/AArch64/AArch64Disassembler.c',
1951 'capstone/arch/AArch64/AArch64InstPrinter.c',
1952 'capstone/arch/AArch64/AArch64Mapping.c',
1953 'capstone/arch/AArch64/AArch64Module.c'
1954 )
1955 endif
1956
1957 if 'CONFIG_PPC_DIS' in config_all_disas
1958 capstone_data.set('CAPSTONE_HAS_POWERPC', '1')
1959 capstone_files += files(
1960 'capstone/arch/PowerPC/PPCDisassembler.c',
1961 'capstone/arch/PowerPC/PPCInstPrinter.c',
1962 'capstone/arch/PowerPC/PPCMapping.c',
1963 'capstone/arch/PowerPC/PPCModule.c'
1964 )
1965 endif
1966
3d562845
RH
1967 if 'CONFIG_S390_DIS' in config_all_disas
1968 capstone_data.set('CAPSTONE_HAS_SYSZ', '1')
1969 capstone_files += files(
1970 'capstone/arch/SystemZ/SystemZDisassembler.c',
1971 'capstone/arch/SystemZ/SystemZInstPrinter.c',
1972 'capstone/arch/SystemZ/SystemZMapping.c',
1973 'capstone/arch/SystemZ/SystemZModule.c',
1974 'capstone/arch/SystemZ/SystemZMCTargetDesc.c'
1975 )
1976 endif
1977
8b18cdbf
RH
1978 if 'CONFIG_I386_DIS' in config_all_disas
1979 capstone_data.set('CAPSTONE_HAS_X86', 1)
1980 capstone_files += files(
1981 'capstone/arch/X86/X86Disassembler.c',
1982 'capstone/arch/X86/X86DisassemblerDecoder.c',
1983 'capstone/arch/X86/X86ATTInstPrinter.c',
1984 'capstone/arch/X86/X86IntelInstPrinter.c',
eef20e40 1985 'capstone/arch/X86/X86InstPrinterCommon.c',
8b18cdbf
RH
1986 'capstone/arch/X86/X86Mapping.c',
1987 'capstone/arch/X86/X86Module.c'
1988 )
1989 endif
1990
1991 configure_file(output: 'capstone-defs.h', configuration: capstone_data)
1992
1993 capstone_cargs = [
1994 # FIXME: There does not seem to be a way to completely replace the c_args
1995 # that come from add_project_arguments() -- we can only add to them.
1996 # So: disable all warnings with a big hammer.
1997 '-Wno-error', '-w',
1998
1999 # Include all configuration defines via a header file, which will wind up
2000 # as a dependency on the object file, and thus changes here will result
2001 # in a rebuild.
2002 '-include', 'capstone-defs.h'
2003 ]
2004
2005 libcapstone = static_library('capstone',
610e7e0e 2006 build_by_default: false,
8b18cdbf
RH
2007 sources: capstone_files,
2008 c_args: capstone_cargs,
2009 include_directories: 'capstone/include')
2010 capstone = declare_dependency(link_with: libcapstone,
eef20e40 2011 include_directories: 'capstone/include/capstone')
8b18cdbf 2012endif
4d34a86b
PB
2013
2014slirp = not_found
2015slirp_opt = 'disabled'
2016if have_system
2017 slirp_opt = get_option('slirp')
2018 if slirp_opt in ['enabled', 'auto', 'system']
2019 have_internal = fs.exists(meson.current_source_dir() / 'slirp/meson.build')
d7dedf42 2020 slirp = dependency('slirp', kwargs: static_kwargs,
4d34a86b
PB
2021 method: 'pkg-config',
2022 required: slirp_opt == 'system' or
2023 slirp_opt == 'enabled' and not have_internal)
2024 if slirp.found()
2025 slirp_opt = 'system'
2026 elif have_internal
2027 slirp_opt = 'internal'
2028 else
2029 slirp_opt = 'disabled'
2030 endif
2031 endif
2032 if slirp_opt == 'internal'
2033 slirp_deps = []
2034 if targetos == 'windows'
2035 slirp_deps = cc.find_library('iphlpapi')
43f547b7
MAL
2036 elif targetos == 'darwin'
2037 slirp_deps = cc.find_library('resolv')
4d34a86b
PB
2038 endif
2039 slirp_conf = configuration_data()
2040 slirp_conf.set('SLIRP_MAJOR_VERSION', meson.project_version().split('.')[0])
2041 slirp_conf.set('SLIRP_MINOR_VERSION', meson.project_version().split('.')[1])
2042 slirp_conf.set('SLIRP_MICRO_VERSION', meson.project_version().split('.')[2])
2043 slirp_conf.set_quoted('SLIRP_VERSION_STRING', meson.project_version())
2044 slirp_cargs = ['-DG_LOG_DOMAIN="Slirp"']
2045 slirp_files = [
2046 'slirp/src/arp_table.c',
2047 'slirp/src/bootp.c',
2048 'slirp/src/cksum.c',
2049 'slirp/src/dhcpv6.c',
2050 'slirp/src/dnssearch.c',
2051 'slirp/src/if.c',
2052 'slirp/src/ip6_icmp.c',
2053 'slirp/src/ip6_input.c',
2054 'slirp/src/ip6_output.c',
2055 'slirp/src/ip_icmp.c',
2056 'slirp/src/ip_input.c',
2057 'slirp/src/ip_output.c',
2058 'slirp/src/mbuf.c',
2059 'slirp/src/misc.c',
2060 'slirp/src/ncsi.c',
2061 'slirp/src/ndp_table.c',
2062 'slirp/src/sbuf.c',
2063 'slirp/src/slirp.c',
2064 'slirp/src/socket.c',
2065 'slirp/src/state.c',
2066 'slirp/src/stream.c',
2067 'slirp/src/tcp_input.c',
2068 'slirp/src/tcp_output.c',
2069 'slirp/src/tcp_subr.c',
2070 'slirp/src/tcp_timer.c',
2071 'slirp/src/tftp.c',
2072 'slirp/src/udp.c',
2073 'slirp/src/udp6.c',
2074 'slirp/src/util.c',
2075 'slirp/src/version.c',
2076 'slirp/src/vmstate.c',
2077 ]
2078
2079 configure_file(
2080 input : 'slirp/src/libslirp-version.h.in',
2081 output : 'libslirp-version.h',
2082 configuration: slirp_conf)
2083
2084 slirp_inc = include_directories('slirp', 'slirp/src')
2085 libslirp = static_library('slirp',
610e7e0e 2086 build_by_default: false,
4d34a86b
PB
2087 sources: slirp_files,
2088 c_args: slirp_cargs,
2089 include_directories: slirp_inc)
2090 slirp = declare_dependency(link_with: libslirp,
2091 dependencies: slirp_deps,
2092 include_directories: slirp_inc)
2093 endif
2094endif
2095
c715343f
DB
2096# For CFI, we need to compile slirp as a static library together with qemu.
2097# This is because we register slirp functions as callbacks for QEMU Timers.
2098# When using a system-wide shared libslirp, the type information for the
2099# callback is missing and the timer call produces a false positive with CFI.
2100#
2101# Now that slirp_opt has been defined, check if the selected slirp is compatible
2102# with control-flow integrity.
2103if get_option('cfi') and slirp_opt == 'system'
2104 error('Control-Flow Integrity is not compatible with system-wide slirp.' \
2105 + ' Please configure with --enable-slirp=git')
2106endif
2107
fbb4121d
PB
2108fdt = not_found
2109fdt_opt = get_option('fdt')
2110if have_system
2111 if fdt_opt in ['enabled', 'auto', 'system']
2112 have_internal = fs.exists(meson.current_source_dir() / 'dtc/libfdt/Makefile.libfdt')
d7dedf42 2113 fdt = cc.find_library('fdt', kwargs: static_kwargs,
fbb4121d
PB
2114 required: fdt_opt == 'system' or
2115 fdt_opt == 'enabled' and not have_internal)
2116 if fdt.found() and cc.links('''
2117 #include <libfdt.h>
2118 #include <libfdt_env.h>
2119 int main(void) { fdt_check_full(NULL, 0); return 0; }''',
2120 dependencies: fdt)
2121 fdt_opt = 'system'
6c22853c
TH
2122 elif fdt_opt == 'system'
2123 error('system libfdt requested, but it is too old (1.5.1 or newer required)')
fbb4121d
PB
2124 elif have_internal
2125 fdt_opt = 'internal'
2126 else
2127 fdt_opt = 'disabled'
87daf898 2128 fdt = not_found
fbb4121d
PB
2129 endif
2130 endif
2131 if fdt_opt == 'internal'
2132 fdt_files = files(
2133 'dtc/libfdt/fdt.c',
2134 'dtc/libfdt/fdt_ro.c',
2135 'dtc/libfdt/fdt_wip.c',
2136 'dtc/libfdt/fdt_sw.c',
2137 'dtc/libfdt/fdt_rw.c',
2138 'dtc/libfdt/fdt_strerror.c',
2139 'dtc/libfdt/fdt_empty_tree.c',
2140 'dtc/libfdt/fdt_addresses.c',
2141 'dtc/libfdt/fdt_overlay.c',
2142 'dtc/libfdt/fdt_check.c',
2143 )
2144
2145 fdt_inc = include_directories('dtc/libfdt')
2146 libfdt = static_library('fdt',
610e7e0e 2147 build_by_default: false,
fbb4121d
PB
2148 sources: fdt_files,
2149 include_directories: fdt_inc)
2150 fdt = declare_dependency(link_with: libfdt,
2151 include_directories: fdt_inc)
2152 endif
2153endif
2154if not fdt.found() and fdt_required.length() > 0
2155 error('fdt not available but required by targets ' + ', '.join(fdt_required))
2156endif
2157
8b18cdbf 2158config_host_data.set('CONFIG_CAPSTONE', capstone.found())
fbb4121d 2159config_host_data.set('CONFIG_FDT', fdt.found())
4d34a86b 2160config_host_data.set('CONFIG_SLIRP', slirp.found())
8b18cdbf 2161
a0c9162c
PB
2162#####################
2163# Generated sources #
2164#####################
8b18cdbf 2165
a0c9162c 2166genh += configure_file(output: 'config-host.h', configuration: config_host_data)
a81df1b6 2167
3f885659 2168hxtool = find_program('scripts/hxtool')
650b5d54 2169shaderinclude = find_program('scripts/shaderinclude.pl')
a81df1b6 2170qapi_gen = find_program('scripts/qapi-gen.py')
654d6b04
PB
2171qapi_gen_depends = [ meson.current_source_dir() / 'scripts/qapi/__init__.py',
2172 meson.current_source_dir() / 'scripts/qapi/commands.py',
2173 meson.current_source_dir() / 'scripts/qapi/common.py',
2174 meson.current_source_dir() / 'scripts/qapi/error.py',
2175 meson.current_source_dir() / 'scripts/qapi/events.py',
2176 meson.current_source_dir() / 'scripts/qapi/expr.py',
2177 meson.current_source_dir() / 'scripts/qapi/gen.py',
2178 meson.current_source_dir() / 'scripts/qapi/introspect.py',
2179 meson.current_source_dir() / 'scripts/qapi/parser.py',
2180 meson.current_source_dir() / 'scripts/qapi/schema.py',
2181 meson.current_source_dir() / 'scripts/qapi/source.py',
2182 meson.current_source_dir() / 'scripts/qapi/types.py',
2183 meson.current_source_dir() / 'scripts/qapi/visit.py',
2184 meson.current_source_dir() / 'scripts/qapi/common.py',
2185 meson.current_source_dir() / 'scripts/qapi-gen.py'
a81df1b6
PB
2186]
2187
2188tracetool = [
2189 python, files('scripts/tracetool.py'),
9c29b741 2190 '--backend=' + ','.join(get_option('trace_backends'))
a81df1b6 2191]
0572d6cd
SH
2192tracetool_depends = files(
2193 'scripts/tracetool/backend/log.py',
2194 'scripts/tracetool/backend/__init__.py',
2195 'scripts/tracetool/backend/dtrace.py',
2196 'scripts/tracetool/backend/ftrace.py',
2197 'scripts/tracetool/backend/simple.py',
2198 'scripts/tracetool/backend/syslog.py',
2199 'scripts/tracetool/backend/ust.py',
2200 'scripts/tracetool/format/tcg_h.py',
2201 'scripts/tracetool/format/ust_events_c.py',
2202 'scripts/tracetool/format/ust_events_h.py',
2203 'scripts/tracetool/format/__init__.py',
2204 'scripts/tracetool/format/d.py',
2205 'scripts/tracetool/format/tcg_helper_c.py',
2206 'scripts/tracetool/format/simpletrace_stap.py',
2207 'scripts/tracetool/format/c.py',
2208 'scripts/tracetool/format/h.py',
2209 'scripts/tracetool/format/tcg_helper_h.py',
2210 'scripts/tracetool/format/log_stap.py',
2211 'scripts/tracetool/format/stap.py',
2212 'scripts/tracetool/format/tcg_helper_wrapper_h.py',
2213 'scripts/tracetool/__init__.py',
2214 'scripts/tracetool/transform.py',
2215 'scripts/tracetool/vcpu.py'
2216)
a81df1b6 2217
2c273f32
MAL
2218qemu_version_cmd = [find_program('scripts/qemu-version.sh'),
2219 meson.current_source_dir(),
859aef02 2220 config_host['PKGVERSION'], meson.project_version()]
2c273f32
MAL
2221qemu_version = custom_target('qemu-version.h',
2222 output: 'qemu-version.h',
2223 command: qemu_version_cmd,
2224 capture: true,
2225 build_by_default: true,
2226 build_always_stale: true)
2227genh += qemu_version
2228
3f885659
MAL
2229hxdep = []
2230hx_headers = [
2231 ['qemu-options.hx', 'qemu-options.def'],
2232 ['qemu-img-cmds.hx', 'qemu-img-cmds.h'],
2233]
2234if have_system
2235 hx_headers += [
2236 ['hmp-commands.hx', 'hmp-commands.h'],
2237 ['hmp-commands-info.hx', 'hmp-commands-info.h'],
2238 ]
2239endif
2240foreach d : hx_headers
b7c70bf2 2241 hxdep += custom_target(d[1],
3f885659
MAL
2242 input: files(d[0]),
2243 output: d[1],
2244 capture: true,
2245 build_by_default: true, # to be removed when added to a target
2246 command: [hxtool, '-h', '@INPUT0@'])
2247endforeach
2248genh += hxdep
2249
a0c9162c
PB
2250###################
2251# Collect sources #
2252###################
a81df1b6 2253
55567891 2254authz_ss = ss.source_set()
4a96337d 2255blockdev_ss = ss.source_set()
7e2b888f 2256block_ss = ss.source_set()
2becc36a 2257bsd_user_ss = ss.source_set()
c2306d71 2258chardev_ss = ss.source_set()
7e2b888f 2259common_ss = ss.source_set()
2389304a 2260crypto_ss = ss.source_set()
f78536b1 2261io_ss = ss.source_set()
2becc36a 2262linux_user_ss = ss.source_set()
7e2b888f 2263qmp_ss = ss.source_set()
da33fc09 2264qom_ss = ss.source_set()
7e2b888f 2265softmmu_ss = ss.source_set()
64ed6f92 2266specific_fuzz_ss = ss.source_set()
7e2b888f
PMD
2267specific_ss = ss.source_set()
2268stub_ss = ss.source_set()
2269trace_ss = ss.source_set()
2270user_ss = ss.source_set()
2271util_ss = ss.source_set()
2becc36a 2272
c94a7b88
GH
2273# accel modules
2274qtest_module_ss = ss.source_set()
dae0ec15 2275tcg_module_ss = ss.source_set()
c94a7b88 2276
3154fee4 2277modules = {}
db2e89df 2278target_modules = {}
2becc36a
PB
2279hw_arch = {}
2280target_arch = {}
2281target_softmmu_arch = {}
46369b50 2282target_user_arch = {}
a81df1b6
PB
2283
2284###############
2285# Trace files #
2286###############
2287
c9322ab5
MAL
2288# TODO: add each directory to the subdirs from its own meson.build, once
2289# we have those
a81df1b6 2290trace_events_subdirs = [
a81df1b6 2291 'crypto',
69ff4d0a
PMD
2292 'qapi',
2293 'qom',
a81df1b6 2294 'monitor',
69ff4d0a 2295 'util',
a81df1b6
PB
2296]
2297if have_user
2298 trace_events_subdirs += [ 'linux-user' ]
2299endif
2300if have_block
2301 trace_events_subdirs += [
2302 'authz',
2303 'block',
2304 'io',
2305 'nbd',
2306 'scsi',
2307 ]
2308endif
2309if have_system
2310 trace_events_subdirs += [
8985db26 2311 'accel/kvm',
a81df1b6
PB
2312 'audio',
2313 'backends',
2314 'backends/tpm',
2315 'chardev',
46627f41 2316 'ebpf',
a81df1b6
PB
2317 'hw/9pfs',
2318 'hw/acpi',
77c05b0b 2319 'hw/adc',
a81df1b6
PB
2320 'hw/alpha',
2321 'hw/arm',
2322 'hw/audio',
2323 'hw/block',
2324 'hw/block/dataplane',
2325 'hw/char',
2326 'hw/display',
2327 'hw/dma',
2328 'hw/hppa',
2329 'hw/hyperv',
2330 'hw/i2c',
2331 'hw/i386',
2332 'hw/i386/xen',
2333 'hw/ide',
2334 'hw/input',
2335 'hw/intc',
2336 'hw/isa',
2337 'hw/mem',
2338 'hw/mips',
2339 'hw/misc',
2340 'hw/misc/macio',
2341 'hw/net',
98e5d7a2 2342 'hw/net/can',
ce0e6a2c 2343 'hw/nubus',
88eea45c 2344 'hw/nvme',
a81df1b6
PB
2345 'hw/nvram',
2346 'hw/pci',
2347 'hw/pci-host',
2348 'hw/ppc',
2349 'hw/rdma',
2350 'hw/rdma/vmw',
2351 'hw/rtc',
2352 'hw/s390x',
2353 'hw/scsi',
2354 'hw/sd',
2355 'hw/sparc',
2356 'hw/sparc64',
2357 'hw/ssi',
2358 'hw/timer',
2359 'hw/tpm',
2360 'hw/usb',
2361 'hw/vfio',
2362 'hw/virtio',
2363 'hw/watchdog',
2364 'hw/xen',
2365 'hw/gpio',
a81df1b6
PB
2366 'migration',
2367 'net',
8b7a5507 2368 'softmmu',
a81df1b6 2369 'ui',
ad22c308 2370 'hw/remote',
a81df1b6
PB
2371 ]
2372endif
8985db26
PMD
2373if have_system or have_user
2374 trace_events_subdirs += [
2375 'accel/tcg',
2376 'hw/core',
2377 'target/arm',
a1477da3 2378 'target/arm/hvf',
8985db26
PMD
2379 'target/hppa',
2380 'target/i386',
2381 'target/i386/kvm',
34b8ff25 2382 'target/mips/tcg',
8985db26
PMD
2383 'target/ppc',
2384 'target/riscv',
2385 'target/s390x',
67043607 2386 'target/s390x/kvm',
8985db26
PMD
2387 'target/sparc',
2388 ]
2389endif
a81df1b6 2390
0df750e9
MAL
2391vhost_user = not_found
2392if 'CONFIG_VHOST_USER' in config_host
2393 libvhost_user = subproject('libvhost-user')
2394 vhost_user = libvhost_user.get_variable('vhost_user_dep')
2395endif
2396
a81df1b6
PB
2397subdir('qapi')
2398subdir('qobject')
2399subdir('stubs')
2400subdir('trace')
2401subdir('util')
5582c58f
MAL
2402subdir('qom')
2403subdir('authz')
a81df1b6 2404subdir('crypto')
2d78b56e 2405subdir('ui')
a81df1b6 2406
3154fee4
MAL
2407
2408if enable_modules
2409 libmodulecommon = static_library('module-common', files('module-common.c') + genh, pic: true, c_args: '-DBUILD_DSO')
2410 modulecommon = declare_dependency(link_whole: libmodulecommon, compile_args: '-DBUILD_DSO')
2411endif
2412
2becc36a 2413stub_ss = stub_ss.apply(config_all, strict: false)
a81df1b6
PB
2414
2415util_ss.add_all(trace_ss)
2becc36a 2416util_ss = util_ss.apply(config_all, strict: false)
a81df1b6
PB
2417libqemuutil = static_library('qemuutil',
2418 sources: util_ss.sources() + stub_ss.sources() + genh,
6d7c7c2d 2419 dependencies: [util_ss.dependencies(), libm, threads, glib, socket, malloc, pixman])
a81df1b6 2420qemuutil = declare_dependency(link_with: libqemuutil,
04c6f1e7 2421 sources: genh + version_res)
a81df1b6 2422
957b31f6
PMD
2423if have_system or have_user
2424 decodetree = generator(find_program('scripts/decodetree.py'),
2425 output: 'decode-@BASENAME@.c.inc',
2426 arguments: ['@INPUT@', '@EXTRA_ARGS@', '-o', '@OUTPUT@'])
2427 subdir('libdecnumber')
2428 subdir('target')
2429endif
abff1abf 2430
478e943f 2431subdir('audio')
7fcfd456 2432subdir('io')
848e8ff6 2433subdir('chardev')
ec0d5893 2434subdir('fsdev')
708eab42 2435subdir('dump')
ec0d5893 2436
f285bd3f
PMD
2437if have_block
2438 block_ss.add(files(
2439 'block.c',
2440 'blockjob.c',
2441 'job.c',
2442 'qemu-io-cmds.c',
2443 ))
2444 block_ss.add(when: 'CONFIG_REPLICATION', if_true: files('replication.c'))
2445
2446 subdir('nbd')
2447 subdir('scsi')
2448 subdir('block')
2449
2450 blockdev_ss.add(files(
2451 'blockdev.c',
2452 'blockdev-nbd.c',
2453 'iothread.c',
2454 'job-qmp.c',
2455 ), gnutls)
2456
2457 # os-posix.c contains POSIX-specific functions used by qemu-storage-daemon,
2458 # os-win32.c does not
2459 blockdev_ss.add(when: 'CONFIG_POSIX', if_true: files('os-posix.c'))
2460 softmmu_ss.add(when: 'CONFIG_WIN32', if_true: [files('os-win32.c')])
2461endif
4a96337d
PB
2462
2463common_ss.add(files('cpus-common.c'))
2464
5d3ea0e1 2465subdir('softmmu')
c9322ab5 2466
f343346b 2467common_ss.add(capstone)
d9f24bf5 2468specific_ss.add(files('cpu.c', 'disas.c', 'gdbstub.c'), capstone)
c9322ab5 2469
44b99a6d
RH
2470# Work around a gcc bug/misfeature wherein constant propagation looks
2471# through an alias:
2472# https://gcc.gnu.org/bugzilla/show_bug.cgi?id=99696
2473# to guess that a const variable is always zero. Without lto, this is
2474# impossible, as the alias is restricted to page-vary-common.c. Indeed,
2475# without lto, not even the alias is required -- we simply use different
2476# declarations in different compilation units.
2477pagevary = files('page-vary-common.c')
2478if get_option('b_lto')
2479 pagevary_flags = ['-fno-lto']
2480 if get_option('cfi')
2481 pagevary_flags += '-fno-sanitize=cfi-icall'
2482 endif
2483 pagevary = static_library('page-vary-common', sources: pagevary,
2484 c_args: pagevary_flags)
2485 pagevary = declare_dependency(link_with: pagevary)
2486endif
2487common_ss.add(pagevary)
6670d4d0
RH
2488specific_ss.add(files('page-vary.c'))
2489
ab318051 2490subdir('backends')
c574e161 2491subdir('disas')
55166230 2492subdir('migration')
ff219dca 2493subdir('monitor')
cdaf0722 2494subdir('net')
17ef2af6 2495subdir('replay')
8df9f0c3 2496subdir('semihosting')
582ea95f 2497subdir('hw')
104cc2c0 2498subdir('tcg')
c6347541 2499subdir('fpu')
1a82878a 2500subdir('accel')
f556b4a1 2501subdir('plugins')
b309c321 2502subdir('bsd-user')
3a30446a 2503subdir('linux-user')
46627f41
AM
2504subdir('ebpf')
2505
b309c321
MAL
2506bsd_user_ss.add(files('gdbstub.c'))
2507specific_ss.add_all(when: 'CONFIG_BSD_USER', if_true: bsd_user_ss)
2508
3a30446a
MAL
2509linux_user_ss.add(files('gdbstub.c', 'thunk.c'))
2510specific_ss.add_all(when: 'CONFIG_LINUX_USER', if_true: linux_user_ss)
5d3ea0e1 2511
a2ce7dbd
PB
2512# needed for fuzzing binaries
2513subdir('tests/qtest/libqos')
64ed6f92 2514subdir('tests/qtest/fuzz')
a2ce7dbd 2515
c94a7b88 2516# accel modules
dae0ec15
GH
2517tcg_real_module_ss = ss.source_set()
2518tcg_real_module_ss.add_all(when: 'CONFIG_TCG_MODULAR', if_true: tcg_module_ss)
2519specific_ss.add_all(when: 'CONFIG_TCG_BUILTIN', if_true: tcg_module_ss)
2520target_modules += { 'accel' : { 'qtest': qtest_module_ss,
2521 'tcg': tcg_real_module_ss }}
c94a7b88 2522
a0c9162c
PB
2523########################
2524# Library dependencies #
2525########################
2526
f5723ab6 2527modinfo_collect = find_program('scripts/modinfo-collect.py')
5ebbfecc 2528modinfo_generate = find_program('scripts/modinfo-generate.py')
f5723ab6
GH
2529modinfo_files = []
2530
3154fee4
MAL
2531block_mods = []
2532softmmu_mods = []
2533foreach d, list : modules
2534 foreach m, module_ss : list
2535 if enable_modules and targetos != 'windows'
3e292c51 2536 module_ss = module_ss.apply(config_all, strict: false)
3154fee4
MAL
2537 sl = static_library(d + '-' + m, [genh, module_ss.sources()],
2538 dependencies: [modulecommon, module_ss.dependencies()], pic: true)
2539 if d == 'block'
2540 block_mods += sl
2541 else
2542 softmmu_mods += sl
2543 endif
f5723ab6
GH
2544 if module_ss.sources() != []
2545 # FIXME: Should use sl.extract_all_objects(recursive: true) as
2546 # input. Sources can be used multiple times but objects are
2547 # unique when it comes to lookup in compile_commands.json.
2548 # Depnds on a mesion version with
2549 # https://github.com/mesonbuild/meson/pull/8900
2550 modinfo_files += custom_target(d + '-' + m + '.modinfo',
2551 output: d + '-' + m + '.modinfo',
ac347111 2552 input: module_ss.sources() + genh,
f5723ab6 2553 capture: true,
ac347111 2554 command: [modinfo_collect, module_ss.sources()])
f5723ab6 2555 endif
3154fee4
MAL
2556 else
2557 if d == 'block'
2558 block_ss.add_all(module_ss)
2559 else
2560 softmmu_ss.add_all(module_ss)
2561 endif
2562 endif
2563 endforeach
2564endforeach
2565
db2e89df
GH
2566foreach d, list : target_modules
2567 foreach m, module_ss : list
2568 if enable_modules and targetos != 'windows'
2569 foreach target : target_dirs
2570 if target.endswith('-softmmu')
2571 config_target = config_target_mak[target]
2572 config_target += config_host
2573 target_inc = [include_directories('target' / config_target['TARGET_BASE_ARCH'])]
2574 c_args = ['-DNEED_CPU_H',
2575 '-DCONFIG_TARGET="@0@-config-target.h"'.format(target),
2576 '-DCONFIG_DEVICES="@0@-config-devices.h"'.format(target)]
2577 target_module_ss = module_ss.apply(config_target, strict: false)
2578 if target_module_ss.sources() != []
2579 module_name = d + '-' + m + '-' + config_target['TARGET_NAME']
2580 sl = static_library(module_name,
2581 [genh, target_module_ss.sources()],
2582 dependencies: [modulecommon, target_module_ss.dependencies()],
2583 include_directories: target_inc,
2584 c_args: c_args,
2585 pic: true)
2586 softmmu_mods += sl
2587 # FIXME: Should use sl.extract_all_objects(recursive: true) too.
2588 modinfo_files += custom_target(module_name + '.modinfo',
2589 output: module_name + '.modinfo',
917ddc27 2590 input: target_module_ss.sources() + genh,
db2e89df 2591 capture: true,
917ddc27 2592 command: [modinfo_collect, '--target', target, target_module_ss.sources()])
db2e89df
GH
2593 endif
2594 endif
2595 endforeach
2596 else
2597 specific_ss.add_all(module_ss)
2598 endif
2599 endforeach
2600endforeach
2601
5ebbfecc
GH
2602if enable_modules
2603 modinfo_src = custom_target('modinfo.c',
2604 output: 'modinfo.c',
2605 input: modinfo_files,
2606 command: [modinfo_generate, '@INPUT@'],
2607 capture: true)
2608 modinfo_lib = static_library('modinfo', modinfo_src)
2609 modinfo_dep = declare_dependency(link_whole: modinfo_lib)
2610 softmmu_ss.add(modinfo_dep)
2611endif
2612
3154fee4 2613nm = find_program('nm')
604f3e4e 2614undefsym = find_program('scripts/undefsym.py')
3154fee4
MAL
2615block_syms = custom_target('block.syms', output: 'block.syms',
2616 input: [libqemuutil, block_mods],
2617 capture: true,
2618 command: [undefsym, nm, '@INPUT@'])
2619qemu_syms = custom_target('qemu.syms', output: 'qemu.syms',
2620 input: [libqemuutil, softmmu_mods],
2621 capture: true,
2622 command: [undefsym, nm, '@INPUT@'])
2623
da33fc09
PMD
2624qom_ss = qom_ss.apply(config_host, strict: false)
2625libqom = static_library('qom', qom_ss.sources() + genh,
2626 dependencies: [qom_ss.dependencies()],
2627 name_suffix: 'fa')
2628
2629qom = declare_dependency(link_whole: libqom)
2630
55567891
PMD
2631authz_ss = authz_ss.apply(config_host, strict: false)
2632libauthz = static_library('authz', authz_ss.sources() + genh,
2633 dependencies: [authz_ss.dependencies()],
2634 name_suffix: 'fa',
2635 build_by_default: false)
2636
2637authz = declare_dependency(link_whole: libauthz,
2638 dependencies: qom)
2639
2389304a
PMD
2640crypto_ss = crypto_ss.apply(config_host, strict: false)
2641libcrypto = static_library('crypto', crypto_ss.sources() + genh,
2642 dependencies: [crypto_ss.dependencies()],
2643 name_suffix: 'fa',
2644 build_by_default: false)
2645
2646crypto = declare_dependency(link_whole: libcrypto,
2647 dependencies: [authz, qom])
2648
f78536b1
PMD
2649io_ss = io_ss.apply(config_host, strict: false)
2650libio = static_library('io', io_ss.sources() + genh,
2651 dependencies: [io_ss.dependencies()],
2652 link_with: libqemuutil,
2653 name_suffix: 'fa',
2654 build_by_default: false)
2655
2656io = declare_dependency(link_whole: libio, dependencies: [crypto, qom])
2657
7e6edef3
PMD
2658libmigration = static_library('migration', sources: migration_files + genh,
2659 name_suffix: 'fa',
2660 build_by_default: false)
2661migration = declare_dependency(link_with: libmigration,
2662 dependencies: [zlib, qom, io])
2663softmmu_ss.add(migration)
2664
5e5733e5
MAL
2665block_ss = block_ss.apply(config_host, strict: false)
2666libblock = static_library('block', block_ss.sources() + genh,
2667 dependencies: block_ss.dependencies(),
2668 link_depends: block_syms,
2669 name_suffix: 'fa',
2670 build_by_default: false)
2671
2672block = declare_dependency(link_whole: [libblock],
b7c70bf2
MAL
2673 link_args: '@block.syms',
2674 dependencies: [crypto, io])
5e5733e5 2675
4fb9071f
SH
2676blockdev_ss = blockdev_ss.apply(config_host, strict: false)
2677libblockdev = static_library('blockdev', blockdev_ss.sources() + genh,
2678 dependencies: blockdev_ss.dependencies(),
2679 name_suffix: 'fa',
2680 build_by_default: false)
2681
2682blockdev = declare_dependency(link_whole: [libblockdev],
2683 dependencies: [block])
2684
ff219dca
PB
2685qmp_ss = qmp_ss.apply(config_host, strict: false)
2686libqmp = static_library('qmp', qmp_ss.sources() + genh,
2687 dependencies: qmp_ss.dependencies(),
2688 name_suffix: 'fa',
2689 build_by_default: false)
2690
2691qmp = declare_dependency(link_whole: [libqmp])
2692
c2306d71
PMD
2693libchardev = static_library('chardev', chardev_ss.sources() + genh,
2694 name_suffix: 'fa',
3eacf70b 2695 dependencies: [gnutls],
c2306d71
PMD
2696 build_by_default: false)
2697
2698chardev = declare_dependency(link_whole: libchardev)
2699
e28ab096
PMD
2700libhwcore = static_library('hwcore', sources: hwcore_files + genh,
2701 name_suffix: 'fa',
2702 build_by_default: false)
2703hwcore = declare_dependency(link_whole: libhwcore)
2704common_ss.add(hwcore)
2705
064f8ee7
PMD
2706###########
2707# Targets #
2708###########
2709
3154fee4
MAL
2710foreach m : block_mods + softmmu_mods
2711 shared_module(m.name(),
2712 name_prefix: '',
2713 link_whole: m,
2714 install: true,
16bf7a33 2715 install_dir: qemu_moddir)
3154fee4
MAL
2716endforeach
2717
4fb9071f 2718softmmu_ss.add(authz, blockdev, chardev, crypto, io, qmp)
64ed6f92
PB
2719common_ss.add(qom, qemuutil)
2720
2721common_ss.add_all(when: 'CONFIG_SOFTMMU', if_true: [softmmu_ss])
2becc36a
PB
2722common_ss.add_all(when: 'CONFIG_USER_ONLY', if_true: user_ss)
2723
2724common_all = common_ss.apply(config_all, strict: false)
2725common_all = static_library('common',
2726 build_by_default: false,
2727 sources: common_all.sources() + genh,
75eebe0b 2728 implicit_include_directories: false,
2becc36a
PB
2729 dependencies: common_all.dependencies(),
2730 name_suffix: 'fa')
2731
c9322ab5
MAL
2732feature_to_c = find_program('scripts/feature_to_c.sh')
2733
fd5eef85 2734emulators = {}
2becc36a
PB
2735foreach target : target_dirs
2736 config_target = config_target_mak[target]
2737 target_name = config_target['TARGET_NAME']
2738 arch = config_target['TARGET_BASE_ARCH']
859aef02 2739 arch_srcs = [config_target_h[target]]
64ed6f92
PB
2740 arch_deps = []
2741 c_args = ['-DNEED_CPU_H',
2742 '-DCONFIG_TARGET="@0@-config-target.h"'.format(target),
2743 '-DCONFIG_DEVICES="@0@-config-devices.h"'.format(target)]
b6c7cfd4 2744 link_args = emulator_link_args
2becc36a 2745
859aef02 2746 config_target += config_host
2becc36a
PB
2747 target_inc = [include_directories('target' / config_target['TARGET_BASE_ARCH'])]
2748 if targetos == 'linux'
2749 target_inc += include_directories('linux-headers', is_system: true)
2750 endif
2751 if target.endswith('-softmmu')
2752 qemu_target_name = 'qemu-system-' + target_name
2753 target_type='system'
abff1abf
PB
2754 t = target_softmmu_arch[arch].apply(config_target, strict: false)
2755 arch_srcs += t.sources()
64ed6f92 2756 arch_deps += t.dependencies()
abff1abf 2757
2c44220d
MAL
2758 hw_dir = target_name == 'sparc64' ? 'sparc64' : arch
2759 hw = hw_arch[hw_dir].apply(config_target, strict: false)
2760 arch_srcs += hw.sources()
64ed6f92 2761 arch_deps += hw.dependencies()
2c44220d 2762
2becc36a 2763 arch_srcs += config_devices_h[target]
64ed6f92 2764 link_args += ['@block.syms', '@qemu.syms']
2becc36a 2765 else
3a30446a 2766 abi = config_target['TARGET_ABI_DIR']
2becc36a
PB
2767 target_type='user'
2768 qemu_target_name = 'qemu-' + target_name
46369b50
PMD
2769 if arch in target_user_arch
2770 t = target_user_arch[arch].apply(config_target, strict: false)
2771 arch_srcs += t.sources()
2772 arch_deps += t.dependencies()
2773 endif
2becc36a
PB
2774 if 'CONFIG_LINUX_USER' in config_target
2775 base_dir = 'linux-user'
2776 target_inc += include_directories('linux-user/host/' / config_host['ARCH'])
e2a74729
WL
2777 endif
2778 if 'CONFIG_BSD_USER' in config_target
2becc36a 2779 base_dir = 'bsd-user'
e2a74729
WL
2780 target_inc += include_directories('bsd-user/' / targetos)
2781 dir = base_dir / abi
2782 arch_srcs += files(dir / 'target_arch_cpu.c')
2becc36a
PB
2783 endif
2784 target_inc += include_directories(
2785 base_dir,
3a30446a 2786 base_dir / abi,
2becc36a 2787 )
3a30446a
MAL
2788 if 'CONFIG_LINUX_USER' in config_target
2789 dir = base_dir / abi
2790 arch_srcs += files(dir / 'signal.c', dir / 'cpu_loop.c')
2791 if config_target.has_key('TARGET_SYSTBL_ABI')
2792 arch_srcs += \
2793 syscall_nr_generators[abi].process(base_dir / abi / config_target['TARGET_SYSTBL'],
2794 extra_args : config_target['TARGET_SYSTBL_ABI'])
2795 endif
2796 endif
2becc36a
PB
2797 endif
2798
c9322ab5
MAL
2799 if 'TARGET_XML_FILES' in config_target
2800 gdbstub_xml = custom_target(target + '-gdbstub-xml.c',
2801 output: target + '-gdbstub-xml.c',
2802 input: files(config_target['TARGET_XML_FILES'].split()),
2803 command: [feature_to_c, '@INPUT@'],
2804 capture: true)
2805 arch_srcs += gdbstub_xml
2806 endif
2807
abff1abf
PB
2808 t = target_arch[arch].apply(config_target, strict: false)
2809 arch_srcs += t.sources()
64ed6f92 2810 arch_deps += t.dependencies()
abff1abf 2811
2becc36a
PB
2812 target_common = common_ss.apply(config_target, strict: false)
2813 objects = common_all.extract_objects(target_common.sources())
64ed6f92 2814 deps = target_common.dependencies()
2becc36a 2815
2becc36a
PB
2816 target_specific = specific_ss.apply(config_target, strict: false)
2817 arch_srcs += target_specific.sources()
64ed6f92 2818 arch_deps += target_specific.dependencies()
2becc36a 2819
64ed6f92 2820 lib = static_library('qemu-' + target,
859aef02 2821 sources: arch_srcs + genh,
b7612f45 2822 dependencies: arch_deps,
2becc36a
PB
2823 objects: objects,
2824 include_directories: target_inc,
64ed6f92
PB
2825 c_args: c_args,
2826 build_by_default: false,
2becc36a 2827 name_suffix: 'fa')
64ed6f92
PB
2828
2829 if target.endswith('-softmmu')
2830 execs = [{
2831 'name': 'qemu-system-' + target_name,
654d6b04 2832 'win_subsystem': 'console',
64ed6f92
PB
2833 'sources': files('softmmu/main.c'),
2834 'dependencies': []
2835 }]
35be72ba 2836 if targetos == 'windows' and (sdl.found() or gtk.found())
64ed6f92
PB
2837 execs += [{
2838 'name': 'qemu-system-' + target_name + 'w',
654d6b04 2839 'win_subsystem': 'windows',
64ed6f92
PB
2840 'sources': files('softmmu/main.c'),
2841 'dependencies': []
2842 }]
2843 endif
537b7248 2844 if get_option('fuzzing')
64ed6f92
PB
2845 specific_fuzz = specific_fuzz_ss.apply(config_target, strict: false)
2846 execs += [{
2847 'name': 'qemu-fuzz-' + target_name,
654d6b04 2848 'win_subsystem': 'console',
64ed6f92
PB
2849 'sources': specific_fuzz.sources(),
2850 'dependencies': specific_fuzz.dependencies(),
64ed6f92
PB
2851 }]
2852 endif
2853 else
2854 execs = [{
2855 'name': 'qemu-' + target_name,
654d6b04 2856 'win_subsystem': 'console',
64ed6f92
PB
2857 'sources': [],
2858 'dependencies': []
2859 }]
2860 endif
2861 foreach exe: execs
8a74ce61 2862 exe_name = exe['name']
3983a767 2863 if targetos == 'darwin'
8a74ce61
AG
2864 exe_name += '-unsigned'
2865 endif
2866
2867 emulator = executable(exe_name, exe['sources'],
237377ac 2868 install: true,
64ed6f92
PB
2869 c_args: c_args,
2870 dependencies: arch_deps + deps + exe['dependencies'],
2871 objects: lib.extract_all_objects(recursive: true),
2872 link_language: link_language,
2873 link_depends: [block_syms, qemu_syms] + exe.get('link_depends', []),
2874 link_args: link_args,
654d6b04 2875 win_subsystem: exe['win_subsystem'])
8a74ce61 2876
3983a767 2877 if targetos == 'darwin'
411ad8dd
AO
2878 icon = 'pc-bios/qemu.rsrc'
2879 build_input = [emulator, files(icon)]
2880 install_input = [
2881 get_option('bindir') / exe_name,
2882 meson.current_source_dir() / icon
2883 ]
2884 if 'CONFIG_HVF' in config_target
2885 entitlements = 'accel/hvf/entitlements.plist'
2886 build_input += files(entitlements)
2887 install_input += meson.current_source_dir() / entitlements
2888 endif
2889
8a74ce61 2890 emulators += {exe['name'] : custom_target(exe['name'],
411ad8dd 2891 input: build_input,
8a74ce61
AG
2892 output: exe['name'],
2893 command: [
411ad8dd
AO
2894 files('scripts/entitlement.sh'),
2895 '@OUTPUT@',
2896 '@INPUT@'
8a74ce61
AG
2897 ])
2898 }
237377ac
AO
2899
2900 meson.add_install_script('scripts/entitlement.sh', '--install',
237377ac 2901 get_option('bindir') / exe['name'],
411ad8dd 2902 install_input)
8a74ce61
AG
2903 else
2904 emulators += {exe['name']: emulator}
2905 endif
10e1d263 2906
9c29b741 2907 if stap.found()
10e1d263 2908 foreach stp: [
bd5f973a
SH
2909 {'ext': '.stp-build', 'fmt': 'stap', 'bin': meson.current_build_dir() / exe['name'], 'install': false},
2910 {'ext': '.stp', 'fmt': 'stap', 'bin': get_option('prefix') / get_option('bindir') / exe['name'], 'install': true},
10e1d263
MAL
2911 {'ext': '-simpletrace.stp', 'fmt': 'simpletrace-stap', 'bin': '', 'install': true},
2912 {'ext': '-log.stp', 'fmt': 'log-stap', 'bin': '', 'install': true},
2913 ]
bd5f973a 2914 custom_target(exe['name'] + stp['ext'],
10e1d263 2915 input: trace_events_all,
bd5f973a 2916 output: exe['name'] + stp['ext'],
10e1d263 2917 install: stp['install'],
16bf7a33 2918 install_dir: get_option('datadir') / 'systemtap/tapset',
10e1d263
MAL
2919 command: [
2920 tracetool, '--group=all', '--format=' + stp['fmt'],
2921 '--binary=' + stp['bin'],
2922 '--target-name=' + target_name,
2923 '--target-type=' + target_type,
2924 '--probe-prefix=qemu.' + target_type + '.' + target_name,
c05012a3 2925 '@INPUT@', '@OUTPUT@'
0572d6cd
SH
2926 ],
2927 depend_files: tracetool_depends)
10e1d263
MAL
2928 endforeach
2929 endif
64ed6f92 2930 endforeach
2becc36a
PB
2931endforeach
2932
931049b4 2933# Other build targets
897b5afa 2934
f556b4a1
PB
2935if 'CONFIG_PLUGIN' in config_host
2936 install_headers('include/qemu/qemu-plugin.h')
2937endif
2938
f15bff25
PB
2939if 'CONFIG_GUEST_AGENT' in config_host
2940 subdir('qga')
b846ab7c
PB
2941elif get_option('guest_agent_msi').enabled()
2942 error('Guest agent MSI requested, but the guest agent is not being built')
f15bff25
PB
2943endif
2944
9755c94a
LV
2945# Don't build qemu-keymap if xkbcommon is not explicitly enabled
2946# when we don't build tools or system
4113f4cf 2947if xkbcommon.found()
28742467
MAL
2948 # used for the update-keymaps target, so include rules even if !have_tools
2949 qemu_keymap = executable('qemu-keymap', files('qemu-keymap.c', 'ui/input-keymap.c') + genh,
2950 dependencies: [qemuutil, xkbcommon], install: have_tools)
2951endif
2952
931049b4 2953if have_tools
b7c70bf2
MAL
2954 qemu_img = executable('qemu-img', [files('qemu-img.c'), hxdep],
2955 dependencies: [authz, block, crypto, io, qom, qemuutil], install: true)
2956 qemu_io = executable('qemu-io', files('qemu-io.c'),
2957 dependencies: [block, qemuutil], install: true)
eb705985 2958 qemu_nbd = executable('qemu-nbd', files('qemu-nbd.c'),
3eacf70b 2959 dependencies: [blockdev, qemuutil, gnutls], install: true)
b7c70bf2 2960
7c58bb76 2961 subdir('storage-daemon')
a9c9727c 2962 subdir('contrib/rdmacm-mux')
1d7bb6ab 2963 subdir('contrib/elf2dmp')
a9c9727c 2964
157e7b13
MAL
2965 executable('qemu-edid', files('qemu-edid.c', 'hw/display/edid-generate.c'),
2966 dependencies: qemuutil,
2967 install: true)
2968
931049b4 2969 if 'CONFIG_VHOST_USER' in config_host
2d7ac0af 2970 subdir('contrib/vhost-user-blk')
b7612f45 2971 subdir('contrib/vhost-user-gpu')
32fcc624 2972 subdir('contrib/vhost-user-input')
99650b62 2973 subdir('contrib/vhost-user-scsi')
931049b4 2974 endif
8f51e01c
MAL
2975
2976 if targetos == 'linux'
2977 executable('qemu-bridge-helper', files('qemu-bridge-helper.c'),
2978 dependencies: [qemuutil, libcap_ng],
2979 install: true,
2980 install_dir: get_option('libexecdir'))
897b5afa
MAL
2981
2982 executable('qemu-pr-helper', files('scsi/qemu-pr-helper.c', 'scsi/utils.c'),
2983 dependencies: [authz, crypto, io, qom, qemuutil,
6ec0e15d 2984 libcap_ng, mpathpersist],
897b5afa 2985 install: true)
8f51e01c
MAL
2986 endif
2987
ccd250aa 2988 if have_ivshmem
5ee24e78
MAL
2989 subdir('contrib/ivshmem-client')
2990 subdir('contrib/ivshmem-server')
2991 endif
931049b4
PB
2992endif
2993
f5aa6320 2994subdir('scripts')
3f99cf57 2995subdir('tools')
bdcbea7a 2996subdir('pc-bios')
f8aa24ea 2997subdir('docs')
e3667660 2998subdir('tests')
1b695471 2999if gtk.found()
e8f3bd71
MAL
3000 subdir('po')
3001endif
3f99cf57 3002
8adfeba9
MAL
3003if host_machine.system() == 'windows'
3004 nsis_cmd = [
3005 find_program('scripts/nsis.py'),
3006 '@OUTPUT@',
3007 get_option('prefix'),
3008 meson.current_source_dir(),
24bdcc96 3009 host_machine.cpu(),
8adfeba9
MAL
3010 '--',
3011 '-DDISPLAYVERSION=' + meson.project_version(),
3012 ]
3013 if build_docs
3014 nsis_cmd += '-DCONFIG_DOCUMENTATION=y'
3015 endif
1b695471 3016 if gtk.found()
8adfeba9
MAL
3017 nsis_cmd += '-DCONFIG_GTK=y'
3018 endif
3019
3020 nsis = custom_target('nsis',
3021 output: 'qemu-setup-' + meson.project_version() + '.exe',
3022 input: files('qemu.nsi'),
3023 build_always_stale: true,
3024 command: nsis_cmd + ['@INPUT@'])
3025 alias_target('installer', nsis)
3026endif
3027
a0c9162c
PB
3028#########################
3029# Configuration summary #
3030#########################
3031
983d0a75 3032# Directories
f9332757 3033summary_info = {}
16bf7a33
PB
3034summary_info += {'Install prefix': get_option('prefix')}
3035summary_info += {'BIOS directory': qemu_datadir}
3036summary_info += {'firmware path': get_option('qemu_firmwarepath')}
3037summary_info += {'binary directory': get_option('bindir')}
3038summary_info += {'library directory': get_option('libdir')}
3039summary_info += {'module directory': qemu_moddir}
3040summary_info += {'libexec directory': get_option('libexecdir')}
3041summary_info += {'include directory': get_option('includedir')}
3042summary_info += {'config directory': get_option('sysconfdir')}
f9332757 3043if targetos != 'windows'
16bf7a33 3044 summary_info += {'local state directory': get_option('localstatedir')}
b81efab7 3045 summary_info += {'Manual directory': get_option('mandir')}
f9332757
PB
3046else
3047 summary_info += {'local state directory': 'queried at runtime'}
3048endif
491e74c1 3049summary_info += {'Doc directory': get_option('docdir')}
f9332757
PB
3050summary_info += {'Build directory': meson.current_build_dir()}
3051summary_info += {'Source path': meson.current_source_dir()}
f9332757 3052summary_info += {'GIT submodules': config_host['GIT_SUBMODULES']}
983d0a75
PMD
3053summary(summary_info, bool_yn: true, section: 'Directories')
3054
e11a0e17
PMD
3055# Host binaries
3056summary_info = {}
3057summary_info += {'git': config_host['GIT']}
3058summary_info += {'make': config_host['MAKE']}
3059summary_info += {'python': '@0@ (version: @1@)'.format(python.full_path(), python.language_version())}
bb647c49 3060summary_info += {'sphinx-build': sphinx_build}
e11a0e17
PMD
3061if config_host.has_key('HAVE_GDB_BIN')
3062 summary_info += {'gdb': config_host['HAVE_GDB_BIN']}
3063endif
3064summary_info += {'genisoimage': config_host['GENISOIMAGE']}
3065if targetos == 'windows' and config_host.has_key('CONFIG_GUEST_AGENT')
bb647c49 3066 summary_info += {'wixl': wixl}
e11a0e17 3067endif
b8e0c493 3068if slirp_opt != 'disabled' and 'CONFIG_SLIRP_SMBD' in config_host
e11a0e17
PMD
3069 summary_info += {'smbd': config_host['CONFIG_SMBD_COMMAND']}
3070endif
3071summary(summary_info, bool_yn: true, section: 'Host binaries')
3072
1d718865
PMD
3073# Configurable features
3074summary_info = {}
3075summary_info += {'Documentation': build_docs}
aa3ca634
PMD
3076summary_info += {'system-mode emulation': have_system}
3077summary_info += {'user-mode emulation': have_user}
813803aa 3078summary_info += {'block layer': have_block}
1d718865
PMD
3079summary_info += {'Install blobs': get_option('install_blobs')}
3080summary_info += {'module support': config_host.has_key('CONFIG_MODULES')}
3081if config_host.has_key('CONFIG_MODULES')
3082 summary_info += {'alternative module path': config_host.has_key('CONFIG_MODULE_UPGRADES')}
3083endif
537b7248 3084summary_info += {'fuzzing support': get_option('fuzzing')}
1d718865 3085if have_system
87430d5b 3086 summary_info += {'Audio drivers': ' '.join(audio_drivers_selected)}
1d718865 3087endif
9c29b741
PB
3088summary_info += {'Trace backends': ','.join(get_option('trace_backends'))}
3089if 'simple' in get_option('trace_backends')
3090 summary_info += {'Trace output file': get_option('trace_file') + '-<pid>'}
1d718865
PMD
3091endif
3092summary_info += {'QOM debugging': config_host.has_key('CONFIG_QOM_CAST_DEBUG')}
3093summary_info += {'vhost-kernel support': config_host.has_key('CONFIG_VHOST_KERNEL')}
3094summary_info += {'vhost-net support': config_host.has_key('CONFIG_VHOST_NET')}
3095summary_info += {'vhost-crypto support': config_host.has_key('CONFIG_VHOST_CRYPTO')}
3096summary_info += {'vhost-scsi support': config_host.has_key('CONFIG_VHOST_SCSI')}
3097summary_info += {'vhost-vsock support': config_host.has_key('CONFIG_VHOST_VSOCK')}
3098summary_info += {'vhost-user support': config_host.has_key('CONFIG_VHOST_USER')}
3099summary_info += {'vhost-user-blk server support': have_vhost_user_blk_server}
3100summary_info += {'vhost-user-fs support': config_host.has_key('CONFIG_VHOST_USER_FS')}
3101summary_info += {'vhost-vdpa support': config_host.has_key('CONFIG_VHOST_VDPA')}
3102summary_info += {'build guest agent': config_host.has_key('CONFIG_GUEST_AGENT')}
3103summary(summary_info, bool_yn: true, section: 'Configurable features')
3104
2e864b8b 3105# Compilation information
983d0a75 3106summary_info = {}
2e864b8b
PMD
3107summary_info += {'host CPU': cpu}
3108summary_info += {'host endianness': build_machine.endian()}
63de9353
AB
3109summary_info += {'C compiler': ' '.join(meson.get_compiler('c').cmd_array())}
3110summary_info += {'Host C compiler': ' '.join(meson.get_compiler('c', native: true).cmd_array())}
f9332757 3111if link_language == 'cpp'
63de9353 3112 summary_info += {'C++ compiler': ' '.join(meson.get_compiler('cpp').cmd_array())}
f9332757
PB
3113else
3114 summary_info += {'C++ compiler': false}
3115endif
3116if targetos == 'darwin'
63de9353 3117 summary_info += {'Objective-C compiler': ' '.join(meson.get_compiler('objc').cmd_array())}
f9332757 3118endif
2e864b8b
PMD
3119if targetos == 'windows'
3120 if 'WIN_SDK' in config_host
3121 summary_info += {'Windows SDK': config_host['WIN_SDK']}
3122 endif
3123endif
47b30835
PB
3124summary_info += {'CFLAGS': ' '.join(get_option('c_args')
3125 + ['-O' + get_option('optimization')]
3126 + (get_option('debug') ? ['-g'] : []))}
3127if link_language == 'cpp'
3128 summary_info += {'CXXFLAGS': ' '.join(get_option('cpp_args')
3129 + ['-O' + get_option('optimization')]
3130 + (get_option('debug') ? ['-g'] : []))}
3131endif
3132link_args = get_option(link_language + '_link_args')
3133if link_args.length() > 0
3134 summary_info += {'LDFLAGS': ' '.join(link_args)}
3135endif
f9332757
PB
3136summary_info += {'QEMU_CFLAGS': config_host['QEMU_CFLAGS']}
3137summary_info += {'QEMU_LDFLAGS': config_host['QEMU_LDFLAGS']}
f9332757 3138summary_info += {'profiler': config_host.has_key('CONFIG_PROFILER')}
cdad781d 3139summary_info += {'link-time optimization (LTO)': get_option('b_lto')}
2e864b8b 3140summary_info += {'PIE': get_option('b_pie')}
3e8529dd 3141summary_info += {'static build': config_host.has_key('CONFIG_STATIC')}
2e864b8b
PMD
3142summary_info += {'malloc trim support': has_malloc_trim}
3143summary_info += {'membarrier': config_host.has_key('CONFIG_MEMBARRIER')}
2e864b8b
PMD
3144summary_info += {'debug stack usage': config_host.has_key('CONFIG_DEBUG_STACK_USAGE')}
3145summary_info += {'mutex debugging': config_host.has_key('CONFIG_DEBUG_MUTEX')}
3146summary_info += {'memory allocator': get_option('malloc')}
3147summary_info += {'avx2 optimization': config_host.has_key('CONFIG_AVX2_OPT')}
3148summary_info += {'avx512f optimization': config_host.has_key('CONFIG_AVX512F_OPT')}
3149summary_info += {'gprof enabled': config_host.has_key('CONFIG_GPROF')}
3150summary_info += {'gcov': get_option('b_coverage')}
3151summary_info += {'thread sanitizer': config_host.has_key('CONFIG_TSAN')}
3152summary_info += {'CFI support': get_option('cfi')}
3153if get_option('cfi')
3154 summary_info += {'CFI debug support': get_option('cfi_debug')}
3155endif
3156summary_info += {'strip binaries': get_option('strip')}
bb647c49 3157summary_info += {'sparse': sparse}
2e864b8b 3158summary_info += {'mingw32 support': targetos == 'windows'}
49e8565b
AB
3159
3160# snarf the cross-compilation information for tests
3161foreach target: target_dirs
3162 tcg_mak = meson.current_build_dir() / 'tests/tcg' / 'config-' + target + '.mak'
3163 if fs.exists(tcg_mak)
3164 config_cross_tcg = keyval.load(tcg_mak)
3165 target = config_cross_tcg['TARGET_NAME']
3166 compiler = ''
3167 if 'DOCKER_CROSS_CC_GUEST' in config_cross_tcg
3168 summary_info += {target + ' tests': config_cross_tcg['DOCKER_CROSS_CC_GUEST'] +
3169 ' via ' + config_cross_tcg['DOCKER_IMAGE']}
3170 elif 'CROSS_CC_GUEST' in config_cross_tcg
3171 summary_info += {target + ' tests'
3172 : config_cross_tcg['CROSS_CC_GUEST'] }
3173 endif
3174 endif
3175endforeach
3176
2e864b8b
PMD
3177summary(summary_info, bool_yn: true, section: 'Compilation')
3178
aa3ca634 3179# Targets and accelerators
2e864b8b 3180summary_info = {}
aa3ca634
PMD
3181if have_system
3182 summary_info += {'KVM support': config_all.has_key('CONFIG_KVM')}
3183 summary_info += {'HAX support': config_all.has_key('CONFIG_HAX')}
3184 summary_info += {'HVF support': config_all.has_key('CONFIG_HVF')}
3185 summary_info += {'WHPX support': config_all.has_key('CONFIG_WHPX')}
74a414a1 3186 summary_info += {'NVMM support': config_all.has_key('CONFIG_NVMM')}
aa3ca634
PMD
3187 summary_info += {'Xen support': config_host.has_key('CONFIG_XEN_BACKEND')}
3188 if config_host.has_key('CONFIG_XEN_BACKEND')
3189 summary_info += {'xen ctrl version': config_host['CONFIG_XEN_CTRL_INTERFACE_VERSION']}
3190 endif
3191endif
3192summary_info += {'TCG support': config_all.has_key('CONFIG_TCG')}
3193if config_all.has_key('CONFIG_TCG')
39687aca
PMD
3194 if get_option('tcg_interpreter')
3195 summary_info += {'TCG backend': 'TCI (TCG with bytecode interpreter, experimental and slow)'}
3196 else
3197 summary_info += {'TCG backend': 'native (@0@)'.format(cpu)}
3198 endif
029aa68f 3199 summary_info += {'TCG plugins': config_host.has_key('CONFIG_PLUGIN')}
aa3ca634 3200 summary_info += {'TCG debug enabled': config_host.has_key('CONFIG_DEBUG_TCG')}
aa3ca634 3201endif
2e864b8b 3202summary_info += {'target list': ' '.join(target_dirs)}
aa3ca634
PMD
3203if have_system
3204 summary_info += {'default devices': get_option('default_devices')}
106ad1f9 3205 summary_info += {'out of process emulation': multiprocess_allowed}
aa3ca634
PMD
3206endif
3207summary(summary_info, bool_yn: true, section: 'Targets and accelerators')
3208
813803aa
PMD
3209# Block layer
3210summary_info = {}
3211summary_info += {'coroutine backend': config_host['CONFIG_COROUTINE_BACKEND']}
3212summary_info += {'coroutine pool': config_host['CONFIG_COROUTINE_POOL'] == '1'}
3213if have_block
3214 summary_info += {'Block whitelist (rw)': config_host['CONFIG_BDRV_RW_WHITELIST']}
3215 summary_info += {'Block whitelist (ro)': config_host['CONFIG_BDRV_RO_WHITELIST']}
e5f05f8c 3216 summary_info += {'Use block whitelist in tools': config_host.has_key('CONFIG_BDRV_WHITELIST_TOOLS')}
813803aa
PMD
3217 summary_info += {'VirtFS support': have_virtfs}
3218 summary_info += {'build virtiofs daemon': have_virtiofsd}
3219 summary_info += {'Live block migration': config_host.has_key('CONFIG_LIVE_BLOCK_MIGRATION')}
3220 summary_info += {'replication support': config_host.has_key('CONFIG_REPLICATION')}
3221 summary_info += {'bochs support': config_host.has_key('CONFIG_BOCHS')}
3222 summary_info += {'cloop support': config_host.has_key('CONFIG_CLOOP')}
3223 summary_info += {'dmg support': config_host.has_key('CONFIG_DMG')}
3224 summary_info += {'qcow v1 support': config_host.has_key('CONFIG_QCOW1')}
3225 summary_info += {'vdi support': config_host.has_key('CONFIG_VDI')}
3226 summary_info += {'vvfat support': config_host.has_key('CONFIG_VVFAT')}
3227 summary_info += {'qed support': config_host.has_key('CONFIG_QED')}
3228 summary_info += {'parallels support': config_host.has_key('CONFIG_PARALLELS')}
bb647c49 3229 summary_info += {'FUSE exports': fuse}
813803aa
PMD
3230endif
3231summary(summary_info, bool_yn: true, section: 'Block layer support')
3232
aa58028a 3233# Crypto
aa3ca634 3234summary_info = {}
f9332757 3235summary_info += {'TLS priority': config_host['CONFIG_TLS_PRIORITY']}
bb647c49
PB
3236summary_info += {'GNUTLS support': gnutls}
3237if gnutls.found()
3238 summary_info += {' GNUTLS crypto': gnutls_crypto.found()}
3239endif
3240summary_info += {'libgcrypt': gcrypt}
3241summary_info += {'nettle': nettle}
57612511
PB
3242if nettle.found()
3243 summary_info += {' XTS': xts != 'private'}
f9332757 3244endif
aa58028a
PMD
3245summary_info += {'crypto afalg': config_host.has_key('CONFIG_AF_ALG')}
3246summary_info += {'rng-none': config_host.has_key('CONFIG_RNG_NONE')}
3247summary_info += {'Linux keyring': config_host.has_key('CONFIG_SECRET_KEYRING')}
3248summary(summary_info, bool_yn: true, section: 'Crypto')
3249
69a78cce 3250# Libraries
aa58028a
PMD
3251summary_info = {}
3252if targetos == 'darwin'
bb647c49
PB
3253 summary_info += {'Cocoa support': cocoa}
3254endif
3255summary_info += {'SDL support': sdl}
3256summary_info += {'SDL image support': sdl_image}
3257summary_info += {'GTK support': gtk}
3258summary_info += {'pixman': pixman}
3259summary_info += {'VTE support': vte}
3260summary_info += {'slirp support': slirp_opt == 'internal' ? slirp_opt : slirp}
3261summary_info += {'libtasn1': tasn1}
3262summary_info += {'PAM': pam}
3263summary_info += {'iconv support': iconv}
3264summary_info += {'curses support': curses}
3265summary_info += {'virgl support': virgl}
3266summary_info += {'curl support': curl}
3267summary_info += {'Multipath support': mpathpersist}
3268summary_info += {'VNC support': vnc}
a0b93237 3269if vnc.found()
bb647c49
PB
3270 summary_info += {'VNC SASL support': sasl}
3271 summary_info += {'VNC JPEG support': jpeg}
3272 summary_info += {'VNC PNG support': png}
f9332757 3273endif
87430d5b
PB
3274if targetos not in ['darwin', 'haiku', 'windows']
3275 summary_info += {'OSS support': oss}
3276elif targetos == 'darwin'
3277 summary_info += {'CoreAudio support': coreaudio}
3278elif targetos == 'windows'
3279 summary_info += {'DirectSound support': dsound}
3280endif
3281if targetos == 'linux'
3282 summary_info += {'ALSA support': alsa}
3283 summary_info += {'PulseAudio support': pulse}
3284endif
3285summary_info += {'JACK support': jack}
bb647c49 3286summary_info += {'brlapi support': brlapi}
f9332757
PB
3287summary_info += {'vde support': config_host.has_key('CONFIG_VDE')}
3288summary_info += {'netmap support': config_host.has_key('CONFIG_NETMAP')}
3289summary_info += {'Linux AIO support': config_host.has_key('CONFIG_LINUX_AIO')}
bb647c49
PB
3290summary_info += {'Linux io_uring support': linux_io_uring}
3291summary_info += {'ATTR/XATTR support': libattr}
f9332757
PB
3292summary_info += {'RDMA support': config_host.has_key('CONFIG_RDMA')}
3293summary_info += {'PVRDMA support': config_host.has_key('CONFIG_PVRDMA')}
fbb4121d 3294summary_info += {'fdt support': fdt_opt == 'disabled' ? false : fdt_opt}
bb647c49
PB
3295summary_info += {'libcap-ng support': libcap_ng}
3296summary_info += {'bpf support': libbpf}
f9332757
PB
3297# TODO: add back protocol and server version
3298summary_info += {'spice support': config_host.has_key('CONFIG_SPICE')}
bb647c49 3299summary_info += {'rbd support': rbd}
f9332757 3300summary_info += {'xfsctl support': config_host.has_key('CONFIG_XFS')}
bb647c49
PB
3301summary_info += {'smartcard support': cacard}
3302summary_info += {'U2F support': u2f}
3303summary_info += {'libusb': libusb}
3304summary_info += {'usb net redir': usbredir}
f9332757 3305summary_info += {'OpenGL support': config_host.has_key('CONFIG_OPENGL')}
bb647c49
PB
3306summary_info += {'GBM': gbm}
3307summary_info += {'libiscsi support': libiscsi}
3308summary_info += {'libnfs support': libnfs}
f9332757 3309if targetos == 'windows'
b846ab7c
PB
3310 if config_host.has_key('CONFIG_GUEST_AGENT')
3311 summary_info += {'QGA VSS support': config_host.has_key('CONFIG_QGA_VSS')}
3312 summary_info += {'QGA w32 disk info': config_host.has_key('CONFIG_QGA_NTDDSCSI')}
b846ab7c 3313 endif
f9332757 3314endif
bb647c49
PB
3315summary_info += {'seccomp support': seccomp}
3316summary_info += {'GlusterFS support': glusterfs}
f9332757
PB
3317summary_info += {'TPM support': config_host.has_key('CONFIG_TPM')}
3318summary_info += {'libssh support': config_host.has_key('CONFIG_LIBSSH')}
bb647c49
PB
3319summary_info += {'lzo support': lzo}
3320summary_info += {'snappy support': snappy}
3321summary_info += {'bzip2 support': libbzip2}
3322summary_info += {'lzfse support': liblzfse}
3323summary_info += {'zstd support': zstd}
f9332757 3324summary_info += {'NUMA host support': config_host.has_key('CONFIG_NUMA')}
bb647c49
PB
3325summary_info += {'libxml2': libxml2}
3326summary_info += {'capstone': capstone_opt == 'internal' ? capstone_opt : capstone}
3327summary_info += {'libpmem support': libpmem}
3328summary_info += {'libdaxctl support': libdaxctl}
3329summary_info += {'libudev': libudev}
3330# Dummy dependency, keep .found()
df4ea709 3331summary_info += {'FUSE lseek': fuse_lseek.found()}
69a78cce 3332summary(summary_info, bool_yn: true, section: 'Dependencies')
f9332757
PB
3333
3334if not supported_cpus.contains(cpu)
3335 message()
3336 warning('SUPPORT FOR THIS HOST CPU WILL GO AWAY IN FUTURE RELEASES!')
3337 message()
3338 message('CPU host architecture ' + cpu + ' support is not currently maintained.')
3339 message('The QEMU project intends to remove support for this host CPU in')
3340 message('a future release if nobody volunteers to maintain it and to')
3341 message('provide a build host for our continuous integration setup.')
3342 message('configure has succeeded and you can continue to build, but')
3343 message('if you care about QEMU on this platform you should contact')
3344 message('us upstream at qemu-devel@nongnu.org.')
3345endif
3346
3347if not supported_oses.contains(targetos)
3348 message()
3349 warning('WARNING: SUPPORT FOR THIS HOST OS WILL GO AWAY IN FUTURE RELEASES!')
3350 message()
3351 message('Host OS ' + targetos + 'support is not currently maintained.')
3352 message('The QEMU project intends to remove support for this host OS in')
3353 message('a future release if nobody volunteers to maintain it and to')
3354 message('provide a build host for our continuous integration setup.')
3355 message('configure has succeeded and you can continue to build, but')
3356 message('if you care about QEMU on this platform you should contact')
3357 message('us upstream at qemu-devel@nongnu.org.')
3358endif