hw/riscv: Move sifive_clint model to hw/intc
[qemu/ar7.git] / meson.build
blobbc869c676af6752d8662ff71d4891c6683bd4c72
1 project('qemu', ['c'], meson_version: '>=0.55.0',
2         default_options: ['warning_level=1', 'c_std=gnu99', 'cpp_std=gnu++11',
3                           'b_colorout=auto'],
4         version: run_command('head', meson.source_root() / 'VERSION').stdout().strip())
6 not_found = dependency('', required: false)
7 if meson.version().version_compare('>=0.56.0')
8   keyval = import('keyval')
9 else
10   keyval = import('unstable-keyval')
11 endif
12 ss = import('sourceset')
14 sh = find_program('sh')
15 cc = meson.get_compiler('c')
16 config_host = keyval.load(meson.current_build_dir() / 'config-host.mak')
17 enable_modules = 'CONFIG_MODULES' in config_host
18 enable_static = 'CONFIG_STATIC' in config_host
19 build_docs = 'BUILD_DOCS' in config_host
20 qemu_datadir = get_option('datadir') / get_option('qemu_suffix')
21 qemu_docdir = get_option('docdir') / get_option('qemu_suffix')
22 config_host_data = configuration_data()
23 genh = []
25 target_dirs = config_host['TARGET_DIRS'].split()
26 have_user = false
27 have_system = false
28 foreach target : target_dirs
29   have_user = have_user or target.endswith('-user')
30   have_system = have_system or target.endswith('-softmmu')
31 endforeach
32 have_tools = 'CONFIG_TOOLS' in config_host
33 have_block = have_system or have_tools
35 python = import('python').find_installation()
37 supported_oses = ['windows', 'freebsd', 'netbsd', 'openbsd', 'darwin', 'sunos', 'linux']
38 supported_cpus = ['ppc', 'ppc64', 's390x', 'sparc64', 'riscv32', 'riscv64', 'x86', 'x86_64',
39   'arm', 'aarch64', 'mips', 'mips64', 'sparc', 'sparc64']
41 cpu = host_machine.cpu_family()
42 targetos = host_machine.system()
44 configure_file(input: files('scripts/ninjatool.py'),
45                output: 'ninjatool',
46                configuration: config_host)
48 ##################
49 # Compiler flags #
50 ##################
52 add_project_arguments(config_host['QEMU_CFLAGS'].split(),
53                       native: false, language: ['c', 'objc'])
54 add_project_arguments(config_host['QEMU_CXXFLAGS'].split(),
55                       native: false, language: 'cpp')
56 add_project_link_arguments(config_host['QEMU_LDFLAGS'].split(),
57                            native: false, language: ['c', 'cpp', 'objc'])
58 add_project_arguments(config_host['QEMU_INCLUDES'].split(),
59                       language: ['c', 'cpp', 'objc'])
61 # Specify linker-script with add_project_link_arguments so that it is not placed
62 # within a linker --start-group/--end-group pair
63 if 'CONFIG_FUZZ' in config_host
64    add_project_link_arguments(['-Wl,-T,',
65                                (meson.current_source_dir() / 'tests/qtest/fuzz/fork_fuzz.ld')],
66                               native: false, language: ['c', 'cpp', 'objc'])
67 endif
69 link_language = meson.get_external_property('link_language', 'cpp')
70 if link_language == 'cpp'
71   add_languages('cpp', required: true, native: false)
72 endif
73 if host_machine.system() == 'darwin'
74   add_languages('objc', required: false, native: false)
75 endif
77 if 'SPARSE_CFLAGS' in config_host
78   run_target('sparse',
79              command: [find_program('scripts/check_sparse.py'),
80                        config_host['SPARSE_CFLAGS'].split(),
81                        'compile_commands.json'])
82 endif
84 m = cc.find_library('m', required: false)
85 util = cc.find_library('util', required: false)
86 winmm = []
87 socket = []
88 version_res = []
89 coref = []
90 iokit = []
91 cocoa = []
92 hvf = []
93 if targetos == 'windows'
94   socket = cc.find_library('ws2_32')
95   winmm = cc.find_library('winmm')
97   win = import('windows')
98   version_res = win.compile_resources('version.rc',
99                                       depend_files: files('pc-bios/qemu-nsis.ico'),
100                                       include_directories: include_directories('.'))
101 elif targetos == 'darwin'
102   coref = dependency('appleframeworks', modules: 'CoreFoundation')
103   iokit = dependency('appleframeworks', modules: 'IOKit')
104   cocoa = dependency('appleframeworks', modules: 'Cocoa')
105   hvf = dependency('appleframeworks', modules: 'Hypervisor')
106 elif targetos == 'sunos'
107   socket = [cc.find_library('socket'),
108             cc.find_library('nsl'),
109             cc.find_library('resolv')]
110 elif targetos == 'haiku'
111   socket = [cc.find_library('posix_error_mapper'),
112             cc.find_library('network'),
113             cc.find_library('bsd')]
114 endif
115 # The path to glib.h is added to all compilation commands.  This was
116 # grandfathered in from the QEMU Makefiles.
117 add_project_arguments(config_host['GLIB_CFLAGS'].split(),
118                       native: false, language: ['c', 'cpp', 'objc'])
119 glib = declare_dependency(link_args: config_host['GLIB_LIBS'].split())
120 gio = not_found
121 if 'CONFIG_GIO' in config_host
122   gio = declare_dependency(compile_args: config_host['GIO_CFLAGS'].split(),
123                            link_args: config_host['GIO_LIBS'].split())
124 endif
125 lttng = not_found
126 if 'CONFIG_TRACE_UST' in config_host
127   lttng = declare_dependency(link_args: config_host['LTTNG_UST_LIBS'].split())
128 endif
129 urcubp = not_found
130 if 'CONFIG_TRACE_UST' in config_host
131   urcubp = declare_dependency(link_args: config_host['URCU_BP_LIBS'].split())
132 endif
133 gcrypt = not_found
134 if 'CONFIG_GCRYPT' in config_host
135   gcrypt = declare_dependency(compile_args: config_host['GCRYPT_CFLAGS'].split(),
136                               link_args: config_host['GCRYPT_LIBS'].split())
137 endif
138 nettle = not_found
139 if 'CONFIG_NETTLE' in config_host
140   nettle = declare_dependency(compile_args: config_host['NETTLE_CFLAGS'].split(),
141                               link_args: config_host['NETTLE_LIBS'].split())
142 endif
143 gnutls = not_found
144 if 'CONFIG_GNUTLS' in config_host
145   gnutls = declare_dependency(compile_args: config_host['GNUTLS_CFLAGS'].split(),
146                               link_args: config_host['GNUTLS_LIBS'].split())
147 endif
148 pixman = not_found
149 if have_system or have_tools
150   pixman = dependency('pixman-1', required: have_system, version:'>=0.21.8',
151                       method: 'pkg-config', static: enable_static)
152 endif
153 pam = not_found
154 if 'CONFIG_AUTH_PAM' in config_host
155   pam = cc.find_library('pam')
156 endif
157 libaio = cc.find_library('aio', required: false)
158 zlib = dependency('zlib', required: true, static: enable_static)
159 linux_io_uring = not_found
160 if 'CONFIG_LINUX_IO_URING' in config_host
161   linux_io_uring = declare_dependency(compile_args: config_host['LINUX_IO_URING_CFLAGS'].split(),
162                                       link_args: config_host['LINUX_IO_URING_LIBS'].split())
163 endif
164 libxml2 = not_found
165 if 'CONFIG_LIBXML2' in config_host
166   libxml2 = declare_dependency(compile_args: config_host['LIBXML2_CFLAGS'].split(),
167                                link_args: config_host['LIBXML2_LIBS'].split())
168 endif
169 libnfs = not_found
170 if 'CONFIG_LIBNFS' in config_host
171   libnfs = declare_dependency(link_args: config_host['LIBNFS_LIBS'].split())
172 endif
173 libattr = not_found
174 if 'CONFIG_ATTR' in config_host
175   libattr = declare_dependency(link_args: config_host['LIBATTR_LIBS'].split())
176 endif
177 seccomp = not_found
178 if 'CONFIG_SECCOMP' in config_host
179   seccomp = declare_dependency(compile_args: config_host['SECCOMP_CFLAGS'].split(),
180                                link_args: config_host['SECCOMP_LIBS'].split())
181 endif
182 libcap_ng = not_found
183 if 'CONFIG_LIBCAP_NG' in config_host
184   libcap_ng = declare_dependency(link_args: config_host['LIBCAP_NG_LIBS'].split())
185 endif
186 if get_option('xkbcommon').auto() and not have_system and not have_tools
187   xkbcommon = not_found
188 else
189   xkbcommon = dependency('xkbcommon', required: get_option('xkbcommon'),
190                          method: 'pkg-config', static: enable_static)
191 endif
192 slirp = not_found
193 if config_host.has_key('CONFIG_SLIRP')
194   slirp = declare_dependency(compile_args: config_host['SLIRP_CFLAGS'].split(),
195                              link_args: config_host['SLIRP_LIBS'].split())
196 endif
197 vde = not_found
198 if config_host.has_key('CONFIG_VDE')
199   vde = declare_dependency(link_args: config_host['VDE_LIBS'].split())
200 endif
201 pulse = not_found
202 if 'CONFIG_LIBPULSE' in config_host
203   pulse = declare_dependency(compile_args: config_host['PULSE_CFLAGS'].split(),
204                              link_args: config_host['PULSE_LIBS'].split())
205 endif
206 alsa = not_found
207 if 'CONFIG_ALSA' in config_host
208   alsa = declare_dependency(compile_args: config_host['ALSA_CFLAGS'].split(),
209                             link_args: config_host['ALSA_LIBS'].split())
210 endif
211 jack = not_found
212 if 'CONFIG_LIBJACK' in config_host
213   jack = declare_dependency(link_args: config_host['JACK_LIBS'].split())
214 endif
215 spice = not_found
216 if 'CONFIG_SPICE' in config_host
217   spice = declare_dependency(compile_args: config_host['SPICE_CFLAGS'].split(),
218                              link_args: config_host['SPICE_LIBS'].split())
219 endif
220 rt = cc.find_library('rt', required: false)
221 libmpathpersist = not_found
222 if config_host.has_key('CONFIG_MPATH')
223   libmpathpersist = cc.find_library('mpathpersist')
224 endif
225 libdl = not_found
226 if 'CONFIG_PLUGIN' in config_host
227   libdl = cc.find_library('dl', required: true)
228 endif
229 libiscsi = not_found
230 if 'CONFIG_LIBISCSI' in config_host
231   libiscsi = declare_dependency(compile_args: config_host['LIBISCSI_CFLAGS'].split(),
232                                 link_args: config_host['LIBISCSI_LIBS'].split())
233 endif
234 zstd = not_found
235 if 'CONFIG_ZSTD' in config_host
236   zstd = declare_dependency(compile_args: config_host['ZSTD_CFLAGS'].split(),
237                             link_args: config_host['ZSTD_LIBS'].split())
238 endif
239 gbm = not_found
240 if 'CONFIG_GBM' in config_host
241   gbm = declare_dependency(compile_args: config_host['GBM_CFLAGS'].split(),
242                            link_args: config_host['GBM_LIBS'].split())
243 endif
244 virgl = not_found
245 if 'CONFIG_VIRGL' in config_host
246   virgl = declare_dependency(compile_args: config_host['VIRGL_CFLAGS'].split(),
247                              link_args: config_host['VIRGL_LIBS'].split())
248 endif
249 curl = not_found
250 if 'CONFIG_CURL' in config_host
251   curl = declare_dependency(compile_args: config_host['CURL_CFLAGS'].split(),
252                             link_args: config_host['CURL_LIBS'].split())
253 endif
254 libudev = not_found
255 if 'CONFIG_LIBUDEV' in config_host
256   libudev = declare_dependency(link_args: config_host['LIBUDEV_LIBS'].split())
257 endif
258 brlapi = not_found
259 if 'CONFIG_BRLAPI' in config_host
260   brlapi = declare_dependency(link_args: config_host['BRLAPI_LIBS'].split())
261 endif
263 sdl = not_found
264 if have_system
265   sdl = dependency('sdl2', required: get_option('sdl'), static: enable_static)
266   sdl_image = not_found
267 endif
268 if sdl.found()
269   # work around 2.0.8 bug
270   sdl = declare_dependency(compile_args: '-Wno-undef',
271                            dependencies: sdl)
272   sdl_image = dependency('SDL2_image', required: get_option('sdl_image'),
273                          method: 'pkg-config', static: enable_static)
274 else
275   if get_option('sdl_image').enabled()
276     error('sdl-image required, but SDL was @0@',
277           get_option('sdl').disabled() ? 'disabled' : 'not found')
278   endif
279   sdl_image = not_found
280 endif
282 rbd = not_found
283 if 'CONFIG_RBD' in config_host
284   rbd = declare_dependency(link_args: config_host['RBD_LIBS'].split())
285 endif
286 glusterfs = not_found
287 if 'CONFIG_GLUSTERFS' in config_host
288   glusterfs = declare_dependency(compile_args: config_host['GLUSTERFS_CFLAGS'].split(),
289                                  link_args: config_host['GLUSTERFS_LIBS'].split())
290 endif
291 libssh = not_found
292 if 'CONFIG_LIBSSH' in config_host
293   libssh = declare_dependency(compile_args: config_host['LIBSSH_CFLAGS'].split(),
294                               link_args: config_host['LIBSSH_LIBS'].split())
295 endif
296 libbzip2 = not_found
297 if 'CONFIG_BZIP2' in config_host
298   libbzip2 = declare_dependency(link_args: config_host['BZIP2_LIBS'].split())
299 endif
300 liblzfse = not_found
301 if 'CONFIG_LZFSE' in config_host
302   liblzfse = declare_dependency(link_args: config_host['LZFSE_LIBS'].split())
303 endif
304 oss = not_found
305 if 'CONFIG_AUDIO_OSS' in config_host
306   oss = declare_dependency(link_args: config_host['OSS_LIBS'].split())
307 endif
308 dsound = not_found
309 if 'CONFIG_AUDIO_DSOUND' in config_host
310   dsound = declare_dependency(link_args: config_host['DSOUND_LIBS'].split())
311 endif
312 coreaudio = not_found
313 if 'CONFIG_AUDIO_COREAUDIO' in config_host
314   coreaudio = declare_dependency(link_args: config_host['COREAUDIO_LIBS'].split())
315 endif
316 opengl = not_found
317 if 'CONFIG_OPENGL' in config_host
318   opengl = declare_dependency(compile_args: config_host['OPENGL_CFLAGS'].split(),
319                               link_args: config_host['OPENGL_LIBS'].split())
320 else
321 endif
322 gtk = not_found
323 if 'CONFIG_GTK' in config_host
324   gtk = declare_dependency(compile_args: config_host['GTK_CFLAGS'].split(),
325                               link_args: config_host['GTK_LIBS'].split())
326 endif
327 vte = not_found
328 if 'CONFIG_VTE' in config_host
329   vte = declare_dependency(compile_args: config_host['VTE_CFLAGS'].split(),
330                            link_args: config_host['VTE_LIBS'].split())
331 endif
332 x11 = not_found
333 if 'CONFIG_X11' in config_host
334   x11 = declare_dependency(compile_args: config_host['X11_CFLAGS'].split(),
335                            link_args: config_host['X11_LIBS'].split())
336 endif
337 curses = not_found
338 if 'CONFIG_CURSES' in config_host
339   curses = declare_dependency(compile_args: config_host['CURSES_CFLAGS'].split(),
340                               link_args: config_host['CURSES_LIBS'].split())
341 endif
342 iconv = not_found
343 if 'CONFIG_ICONV' in config_host
344   iconv = declare_dependency(compile_args: config_host['ICONV_CFLAGS'].split(),
345                              link_args: config_host['ICONV_LIBS'].split())
346 endif
347 gio = not_found
348 if 'CONFIG_GIO' in config_host
349   gio = declare_dependency(compile_args: config_host['GIO_CFLAGS'].split(),
350                            link_args: config_host['GIO_LIBS'].split())
351 endif
352 vnc = not_found
353 png = not_found
354 jpeg = not_found
355 sasl = not_found
356 if get_option('vnc').enabled()
357   vnc = declare_dependency() # dummy dependency
358   png = dependency('libpng', required: get_option('vnc_png'),
359                    method: 'pkg-config', static: enable_static)
360   jpeg = cc.find_library('jpeg', has_headers: ['jpeglib.h'],
361                          required: get_option('vnc_jpeg'),
362                          static: enable_static)
363   sasl = cc.find_library('sasl2', has_headers: ['sasl/sasl.h'],
364                          required: get_option('vnc_sasl'),
365                          static: enable_static)
366   if sasl.found()
367     sasl = declare_dependency(dependencies: sasl,
368                               compile_args: '-DSTRUCT_IOVEC_DEFINED')
369   endif
370 endif
371 fdt = not_found
372 if 'CONFIG_FDT' in config_host
373   fdt = declare_dependency(compile_args: config_host['FDT_CFLAGS'].split(),
374                            link_args: config_host['FDT_LIBS'].split())
375 endif
376 snappy = not_found
377 if 'CONFIG_SNAPPY' in config_host
378   snappy = declare_dependency(link_args: config_host['SNAPPY_LIBS'].split())
379 endif
380 lzo = not_found
381 if 'CONFIG_LZO' in config_host
382   lzo = declare_dependency(link_args: config_host['LZO_LIBS'].split())
383 endif
384 rdma = not_found
385 if 'CONFIG_RDMA' in config_host
386   rdma = declare_dependency(link_args: config_host['RDMA_LIBS'].split())
387 endif
388 numa = not_found
389 if 'CONFIG_NUMA' in config_host
390   numa = declare_dependency(link_args: config_host['NUMA_LIBS'].split())
391 endif
392 xen = not_found
393 if 'CONFIG_XEN_BACKEND' in config_host
394   xen = declare_dependency(compile_args: config_host['XEN_CFLAGS'].split(),
395                            link_args: config_host['XEN_LIBS'].split())
396 endif
397 cacard = not_found
398 if 'CONFIG_SMARTCARD' in config_host
399   cacard = declare_dependency(compile_args: config_host['SMARTCARD_CFLAGS'].split(),
400                               link_args: config_host['SMARTCARD_LIBS'].split())
401 endif
402 u2f = not_found
403 if have_system
404   u2f = dependency('u2f-emu', required: get_option('u2f'),
405                    method: 'pkg-config',
406                    static: enable_static)
407 endif
408 usbredir = not_found
409 if 'CONFIG_USB_REDIR' in config_host
410   usbredir = declare_dependency(compile_args: config_host['USB_REDIR_CFLAGS'].split(),
411                                 link_args: config_host['USB_REDIR_LIBS'].split())
412 endif
413 libusb = not_found
414 if 'CONFIG_USB_LIBUSB' in config_host
415   libusb = declare_dependency(compile_args: config_host['LIBUSB_CFLAGS'].split(),
416                               link_args: config_host['LIBUSB_LIBS'].split())
417 endif
418 capstone = not_found
419 if 'CONFIG_CAPSTONE' in config_host
420   capstone = declare_dependency(compile_args: config_host['CAPSTONE_CFLAGS'].split(),
421                                 link_args: config_host['CAPSTONE_LIBS'].split())
422 endif
423 libpmem = not_found
424 if 'CONFIG_LIBPMEM' in config_host
425   libpmem = declare_dependency(compile_args: config_host['LIBPMEM_CFLAGS'].split(),
426                                link_args: config_host['LIBPMEM_LIBS'].split())
427 endif
428 libdaxctl = not_found
429 if 'CONFIG_LIBDAXCTL' in config_host
430   libdaxctl = declare_dependency(link_args: config_host['LIBDAXCTL_LIBS'].split())
431 endif
432 tasn1 = not_found
433 if 'CONFIG_TASN1' in config_host
434   tasn1 = declare_dependency(compile_args: config_host['TASN1_CFLAGS'].split(),
435                              link_args: config_host['TASN1_LIBS'].split())
436 endif
437 keyutils = dependency('libkeyutils', required: false,
438                       method: 'pkg-config', static: enable_static)
440 has_gettid = cc.has_function('gettid')
442 # Create config-host.h
444 config_host_data.set('CONFIG_SDL', sdl.found())
445 config_host_data.set('CONFIG_SDL_IMAGE', sdl_image.found())
446 config_host_data.set('CONFIG_VNC', vnc.found())
447 config_host_data.set('CONFIG_VNC_JPEG', jpeg.found())
448 config_host_data.set('CONFIG_VNC_PNG', png.found())
449 config_host_data.set('CONFIG_VNC_SASL', sasl.found())
450 config_host_data.set('CONFIG_XKBCOMMON', xkbcommon.found())
451 config_host_data.set('CONFIG_KEYUTILS', keyutils.found())
452 config_host_data.set('CONFIG_GETTID', has_gettid)
453 config_host_data.set('QEMU_VERSION', '"@0@"'.format(meson.project_version()))
454 config_host_data.set('QEMU_VERSION_MAJOR', meson.project_version().split('.')[0])
455 config_host_data.set('QEMU_VERSION_MINOR', meson.project_version().split('.')[1])
456 config_host_data.set('QEMU_VERSION_MICRO', meson.project_version().split('.')[2])
458 arrays = ['CONFIG_AUDIO_DRIVERS', 'CONFIG_BDRV_RW_WHITELIST', 'CONFIG_BDRV_RO_WHITELIST']
459 strings = ['HOST_DSOSUF', 'CONFIG_IASL', 'qemu_confdir', 'qemu_datadir',
460            'qemu_moddir', 'qemu_localstatedir', 'qemu_helperdir', 'qemu_localedir',
461            'qemu_icondir', 'qemu_desktopdir', 'qemu_firmwarepath']
462 foreach k, v: config_host
463   if arrays.contains(k)
464     if v != ''
465       v = '"' + '", "'.join(v.split()) + '", '
466     endif
467     config_host_data.set(k, v)
468   elif k == 'ARCH'
469     config_host_data.set('HOST_' + v.to_upper(), 1)
470   elif strings.contains(k)
471     if not k.startswith('CONFIG_')
472       k = 'CONFIG_' + k.to_upper()
473     endif
474     config_host_data.set_quoted(k, v)
475   elif k.startswith('CONFIG_') or k.startswith('HAVE_') or k.startswith('HOST_')
476     config_host_data.set(k, v == 'y' ? 1 : v)
477   endif
478 endforeach
479 genh += configure_file(output: 'config-host.h', configuration: config_host_data)
481 minikconf = find_program('scripts/minikconf.py')
482 config_all_devices = {}
483 config_all_disas = {}
484 config_devices_mak_list = []
485 config_devices_h = {}
486 config_target_h = {}
487 config_target_mak = {}
489 disassemblers = {
490   'alpha' : ['CONFIG_ALPHA_DIS'],
491   'arm' : ['CONFIG_ARM_DIS'],
492   'avr' : ['CONFIG_AVR_DIS'],
493   'cris' : ['CONFIG_CRIS_DIS'],
494   'hppa' : ['CONFIG_HPPA_DIS'],
495   'i386' : ['CONFIG_I386_DIS'],
496   'x86_64' : ['CONFIG_I386_DIS'],
497   'x32' : ['CONFIG_I386_DIS'],
498   'lm32' : ['CONFIG_LM32_DIS'],
499   'm68k' : ['CONFIG_M68K_DIS'],
500   'microblaze' : ['CONFIG_MICROBLAZE_DIS'],
501   'mips' : ['CONFIG_MIPS_DIS'],
502   'moxie' : ['CONFIG_MOXIE_DIS'],
503   'nios2' : ['CONFIG_NIOS2_DIS'],
504   'or1k' : ['CONFIG_OPENRISC_DIS'],
505   'ppc' : ['CONFIG_PPC_DIS'],
506   'riscv' : ['CONFIG_RISCV_DIS'],
507   'rx' : ['CONFIG_RX_DIS'],
508   's390' : ['CONFIG_S390_DIS'],
509   'sh4' : ['CONFIG_SH4_DIS'],
510   'sparc' : ['CONFIG_SPARC_DIS'],
511   'xtensa' : ['CONFIG_XTENSA_DIS'],
513 if link_language == 'cpp'
514   disassemblers += {
515     'aarch64' : [ 'CONFIG_ARM_A64_DIS'],
516     'arm' : [ 'CONFIG_ARM_DIS', 'CONFIG_ARM_A64_DIS'],
517     'mips' : [ 'CONFIG_MIPS_DIS', 'CONFIG_NANOMIPS_DIS'],
518   }
519 endif
521 kconfig_external_symbols = [
522   'CONFIG_KVM',
523   'CONFIG_XEN',
524   'CONFIG_TPM',
525   'CONFIG_SPICE',
526   'CONFIG_IVSHMEM',
527   'CONFIG_OPENGL',
528   'CONFIG_X11',
529   'CONFIG_VHOST_USER',
530   'CONFIG_VHOST_KERNEL',
531   'CONFIG_VIRTFS',
532   'CONFIG_LINUX',
533   'CONFIG_PVRDMA',
535 ignored = ['TARGET_XML_FILES', 'TARGET_ABI_DIR', 'TARGET_DIRS']
537 foreach target : target_dirs
538   config_target = keyval.load(meson.current_build_dir() / target / 'config-target.mak')
540   foreach k, v: disassemblers
541     if config_host['ARCH'].startswith(k) or config_target['TARGET_BASE_ARCH'].startswith(k)
542       foreach sym: v
543         config_target += { sym: 'y' }
544         config_all_disas += { sym: 'y' }
545       endforeach
546     endif
547   endforeach
549   config_target_data = configuration_data()
550   foreach k, v: config_target
551     if not k.startswith('TARGET_') and not k.startswith('CONFIG_')
552       # do nothing
553     elif ignored.contains(k)
554       # do nothing
555     elif k == 'TARGET_BASE_ARCH'
556       config_target_data.set('TARGET_' + v.to_upper(), 1)
557     elif k == 'TARGET_NAME'
558       config_target_data.set_quoted(k, v)
559     elif v == 'y'
560       config_target_data.set(k, 1)
561     else
562       config_target_data.set(k, v)
563     endif
564   endforeach
565   config_target_h += {target: configure_file(output: target + '-config-target.h',
566                                                configuration: config_target_data)}
568   if target.endswith('-softmmu')
569     base_kconfig = []
570     foreach sym : kconfig_external_symbols
571       if sym in config_target or sym in config_host
572         base_kconfig += '@0@=y'.format(sym)
573       endif
574     endforeach
576     config_devices_mak = target + '-config-devices.mak'
577     config_devices_mak = configure_file(
578       input: ['default-configs' / target + '.mak', 'Kconfig'],
579       output: config_devices_mak,
580       depfile: config_devices_mak + '.d',
581       capture: true,
582       command: [minikconf, config_host['CONFIG_MINIKCONF_MODE'],
583                 config_devices_mak, '@DEPFILE@', '@INPUT@',
584                 base_kconfig])
586     config_devices_data = configuration_data()
587     config_devices = keyval.load(config_devices_mak)
588     foreach k, v: config_devices
589       config_devices_data.set(k, 1)
590     endforeach
591     config_devices_mak_list += config_devices_mak
592     config_devices_h += {target: configure_file(output: target + '-config-devices.h',
593                                                 configuration: config_devices_data)}
594     config_target += config_devices
595     config_all_devices += config_devices
596   endif
597   config_target_mak += {target: config_target}
598 endforeach
600 # This configuration is used to build files that are shared by
601 # multiple binaries, and then extracted out of the "common"
602 # static_library target.
604 # We do not use all_sources()/all_dependencies(), because it would
605 # build literally all source files, including devices only used by
606 # targets that are not built for this compilation.  The CONFIG_ALL
607 # pseudo symbol replaces it.
609 config_all = config_all_devices
610 config_all += config_host
611 config_all += config_all_disas
612 config_all += {
613   'CONFIG_XEN': config_host.has_key('CONFIG_XEN_BACKEND'),
614   'CONFIG_SOFTMMU': have_system,
615   'CONFIG_USER_ONLY': have_user,
616   'CONFIG_ALL': true,
619 # Generators
621 hxtool = find_program('scripts/hxtool')
622 shaderinclude = find_program('scripts/shaderinclude.pl')
623 qapi_gen = find_program('scripts/qapi-gen.py')
624 qapi_gen_depends = [ meson.source_root() / 'scripts/qapi/__init__.py',
625                      meson.source_root() / 'scripts/qapi/commands.py',
626                      meson.source_root() / 'scripts/qapi/common.py',
627                      meson.source_root() / 'scripts/qapi/doc.py',
628                      meson.source_root() / 'scripts/qapi/error.py',
629                      meson.source_root() / 'scripts/qapi/events.py',
630                      meson.source_root() / 'scripts/qapi/expr.py',
631                      meson.source_root() / 'scripts/qapi/gen.py',
632                      meson.source_root() / 'scripts/qapi/introspect.py',
633                      meson.source_root() / 'scripts/qapi/parser.py',
634                      meson.source_root() / 'scripts/qapi/schema.py',
635                      meson.source_root() / 'scripts/qapi/source.py',
636                      meson.source_root() / 'scripts/qapi/types.py',
637                      meson.source_root() / 'scripts/qapi/visit.py',
638                      meson.source_root() / 'scripts/qapi/common.py',
639                      meson.source_root() / 'scripts/qapi/doc.py',
640                      meson.source_root() / 'scripts/qapi-gen.py'
643 tracetool = [
644   python, files('scripts/tracetool.py'),
645    '--backend=' + config_host['TRACE_BACKENDS']
648 qemu_version_cmd = [find_program('scripts/qemu-version.sh'),
649                     meson.current_source_dir(),
650                     config_host['PKGVERSION'], meson.project_version()]
651 qemu_version = custom_target('qemu-version.h',
652                              output: 'qemu-version.h',
653                              command: qemu_version_cmd,
654                              capture: true,
655                              build_by_default: true,
656                              build_always_stale: true)
657 genh += qemu_version
659 hxdep = []
660 hx_headers = [
661   ['qemu-options.hx', 'qemu-options.def'],
662   ['qemu-img-cmds.hx', 'qemu-img-cmds.h'],
664 if have_system
665   hx_headers += [
666     ['hmp-commands.hx', 'hmp-commands.h'],
667     ['hmp-commands-info.hx', 'hmp-commands-info.h'],
668   ]
669 endif
670 foreach d : hx_headers
671   hxdep += custom_target(d[1],
672                 input: files(d[0]),
673                 output: d[1],
674                 capture: true,
675                 build_by_default: true, # to be removed when added to a target
676                 command: [hxtool, '-h', '@INPUT0@'])
677 endforeach
678 genh += hxdep
680 # Collect sourcesets.
682 util_ss = ss.source_set()
683 stub_ss = ss.source_set()
684 trace_ss = ss.source_set()
685 block_ss = ss.source_set()
686 blockdev_ss = ss.source_set()
687 qmp_ss = ss.source_set()
688 common_ss = ss.source_set()
689 softmmu_ss = ss.source_set()
690 user_ss = ss.source_set()
691 bsd_user_ss = ss.source_set()
692 linux_user_ss = ss.source_set()
693 specific_ss = ss.source_set()
694 specific_fuzz_ss = ss.source_set()
696 modules = {}
697 hw_arch = {}
698 target_arch = {}
699 target_softmmu_arch = {}
701 ###############
702 # Trace files #
703 ###############
705 # TODO: add each directory to the subdirs from its own meson.build, once
706 # we have those
707 trace_events_subdirs = [
708   'accel/kvm',
709   'accel/tcg',
710   'crypto',
711   'monitor',
713 if have_user
714   trace_events_subdirs += [ 'linux-user' ]
715 endif
716 if have_block
717   trace_events_subdirs += [
718     'authz',
719     'block',
720     'io',
721     'nbd',
722     'scsi',
723   ]
724 endif
725 if have_system
726   trace_events_subdirs += [
727     'audio',
728     'backends',
729     'backends/tpm',
730     'chardev',
731     'hw/9pfs',
732     'hw/acpi',
733     'hw/alpha',
734     'hw/arm',
735     'hw/audio',
736     'hw/block',
737     'hw/block/dataplane',
738     'hw/char',
739     'hw/display',
740     'hw/dma',
741     'hw/hppa',
742     'hw/hyperv',
743     'hw/i2c',
744     'hw/i386',
745     'hw/i386/xen',
746     'hw/ide',
747     'hw/input',
748     'hw/intc',
749     'hw/isa',
750     'hw/mem',
751     'hw/mips',
752     'hw/misc',
753     'hw/misc/macio',
754     'hw/net',
755     'hw/nvram',
756     'hw/pci',
757     'hw/pci-host',
758     'hw/ppc',
759     'hw/rdma',
760     'hw/rdma/vmw',
761     'hw/rtc',
762     'hw/s390x',
763     'hw/scsi',
764     'hw/sd',
765     'hw/sparc',
766     'hw/sparc64',
767     'hw/ssi',
768     'hw/timer',
769     'hw/tpm',
770     'hw/usb',
771     'hw/vfio',
772     'hw/virtio',
773     'hw/watchdog',
774     'hw/xen',
775     'hw/gpio',
776     'migration',
777     'net',
778     'ui',
779   ]
780 endif
781 trace_events_subdirs += [
782   'hw/core',
783   'qapi',
784   'qom',
785   'target/arm',
786   'target/hppa',
787   'target/i386',
788   'target/mips',
789   'target/ppc',
790   'target/riscv',
791   'target/s390x',
792   'target/sparc',
793   'util',
796 subdir('qapi')
797 subdir('qobject')
798 subdir('stubs')
799 subdir('trace')
800 subdir('util')
801 subdir('qom')
802 subdir('authz')
803 subdir('crypto')
804 subdir('ui')
807 if enable_modules
808   libmodulecommon = static_library('module-common', files('module-common.c') + genh, pic: true, c_args: '-DBUILD_DSO')
809   modulecommon = declare_dependency(link_whole: libmodulecommon, compile_args: '-DBUILD_DSO')
810 endif
812 # Build targets from sourcesets
814 stub_ss = stub_ss.apply(config_all, strict: false)
816 util_ss.add_all(trace_ss)
817 util_ss = util_ss.apply(config_all, strict: false)
818 libqemuutil = static_library('qemuutil',
819                              sources: util_ss.sources() + stub_ss.sources() + genh,
820                              dependencies: [util_ss.dependencies(), m, glib, socket])
821 qemuutil = declare_dependency(link_with: libqemuutil,
822                               sources: genh + version_res)
824 decodetree = generator(find_program('scripts/decodetree.py'),
825                        output: 'decode-@BASENAME@.c.inc',
826                        arguments: ['@INPUT@', '@EXTRA_ARGS@', '-o', '@OUTPUT@'])
828 subdir('audio')
829 subdir('io')
830 subdir('chardev')
831 subdir('fsdev')
832 subdir('libdecnumber')
833 subdir('target')
834 subdir('dump')
836 block_ss.add(files(
837   'block.c',
838   'blockjob.c',
839   'job.c',
840   'qemu-io-cmds.c',
842 block_ss.add(when: 'CONFIG_REPLICATION', if_true: files('replication.c'))
844 subdir('nbd')
845 subdir('scsi')
846 subdir('block')
848 blockdev_ss.add(files(
849   'blockdev.c',
850   'blockdev-nbd.c',
851   'iothread.c',
852   'job-qmp.c',
855 # os-posix.c contains POSIX-specific functions used by qemu-storage-daemon,
856 # os-win32.c does not
857 blockdev_ss.add(when: 'CONFIG_POSIX', if_true: files('os-posix.c'))
858 softmmu_ss.add(when: 'CONFIG_WIN32', if_true: [files('os-win32.c')])
860 softmmu_ss.add_all(blockdev_ss)
861 softmmu_ss.add(files(
862   'bootdevice.c',
863   'dma-helpers.c',
864   'qdev-monitor.c',
865 ), sdl)
867 softmmu_ss.add(when: 'CONFIG_TPM', if_true: files('tpm.c'))
868 softmmu_ss.add(when: 'CONFIG_SECCOMP', if_true: [files('qemu-seccomp.c'), seccomp])
869 softmmu_ss.add(when: ['CONFIG_FDT', fdt],  if_true: [files('device_tree.c')])
871 common_ss.add(files('cpus-common.c'))
873 subdir('softmmu')
875 specific_ss.add(files('disas.c', 'exec.c', 'gdbstub.c'), capstone, libpmem, libdaxctl)
876 specific_ss.add(files('exec-vary.c'))
877 specific_ss.add(when: 'CONFIG_TCG', if_true: files(
878   'fpu/softfloat.c',
879   'tcg/optimize.c',
880   'tcg/tcg-common.c',
881   'tcg/tcg-op-gvec.c',
882   'tcg/tcg-op-vec.c',
883   'tcg/tcg-op.c',
884   'tcg/tcg.c',
886 specific_ss.add(when: 'CONFIG_TCG_INTERPRETER', if_true: files('disas/tci.c', 'tcg/tci.c'))
888 subdir('backends')
889 subdir('disas')
890 subdir('migration')
891 subdir('monitor')
892 subdir('net')
893 subdir('replay')
894 subdir('hw')
895 subdir('accel')
896 subdir('plugins')
897 subdir('bsd-user')
898 subdir('linux-user')
900 bsd_user_ss.add(files('gdbstub.c'))
901 specific_ss.add_all(when: 'CONFIG_BSD_USER', if_true: bsd_user_ss)
903 linux_user_ss.add(files('gdbstub.c', 'thunk.c'))
904 specific_ss.add_all(when: 'CONFIG_LINUX_USER', if_true: linux_user_ss)
906 # needed for fuzzing binaries
907 subdir('tests/qtest/libqos')
908 subdir('tests/qtest/fuzz')
910 block_mods = []
911 softmmu_mods = []
912 foreach d, list : modules
913   foreach m, module_ss : list
914     if enable_modules and targetos != 'windows'
915       module_ss = module_ss.apply(config_host, strict: false)
916       sl = static_library(d + '-' + m, [genh, module_ss.sources()],
917                           dependencies: [modulecommon, module_ss.dependencies()], pic: true)
918       if d == 'block'
919         block_mods += sl
920       else
921         softmmu_mods += sl
922       endif
923     else
924       if d == 'block'
925         block_ss.add_all(module_ss)
926       else
927         softmmu_ss.add_all(module_ss)
928       endif
929     endif
930   endforeach
931 endforeach
933 nm = find_program('nm')
934 undefsym = find_program('scripts/undefsym.py')
935 block_syms = custom_target('block.syms', output: 'block.syms',
936                              input: [libqemuutil, block_mods],
937                              capture: true,
938                              command: [undefsym, nm, '@INPUT@'])
939 qemu_syms = custom_target('qemu.syms', output: 'qemu.syms',
940                              input: [libqemuutil, softmmu_mods],
941                              capture: true,
942                              command: [undefsym, nm, '@INPUT@'])
944 block_ss = block_ss.apply(config_host, strict: false)
945 libblock = static_library('block', block_ss.sources() + genh,
946                           dependencies: block_ss.dependencies(),
947                           link_depends: block_syms,
948                           name_suffix: 'fa',
949                           build_by_default: false)
951 block = declare_dependency(link_whole: [libblock],
952                            link_args: '@block.syms',
953                            dependencies: [crypto, io])
955 qmp_ss = qmp_ss.apply(config_host, strict: false)
956 libqmp = static_library('qmp', qmp_ss.sources() + genh,
957                         dependencies: qmp_ss.dependencies(),
958                         name_suffix: 'fa',
959                         build_by_default: false)
961 qmp = declare_dependency(link_whole: [libqmp])
963 foreach m : block_mods + softmmu_mods
964   shared_module(m.name(),
965                 name_prefix: '',
966                 link_whole: m,
967                 install: true,
968                 install_dir: config_host['qemu_moddir'])
969 endforeach
971 softmmu_ss.add(authz, block, chardev, crypto, io, qmp)
972 common_ss.add(qom, qemuutil)
974 common_ss.add_all(when: 'CONFIG_SOFTMMU', if_true: [softmmu_ss])
975 common_ss.add_all(when: 'CONFIG_USER_ONLY', if_true: user_ss)
977 common_all = common_ss.apply(config_all, strict: false)
978 common_all = static_library('common',
979                             build_by_default: false,
980                             sources: common_all.sources() + genh,
981                             dependencies: common_all.dependencies(),
982                             name_suffix: 'fa')
984 feature_to_c = find_program('scripts/feature_to_c.sh')
986 emulators = []
987 foreach target : target_dirs
988   config_target = config_target_mak[target]
989   target_name = config_target['TARGET_NAME']
990   arch = config_target['TARGET_BASE_ARCH']
991   arch_srcs = [config_target_h[target]]
992   arch_deps = []
993   c_args = ['-DNEED_CPU_H',
994             '-DCONFIG_TARGET="@0@-config-target.h"'.format(target),
995             '-DCONFIG_DEVICES="@0@-config-devices.h"'.format(target)]
996   link_args = []
998   config_target += config_host
999   target_inc = [include_directories('target' / config_target['TARGET_BASE_ARCH'])]
1000   if targetos == 'linux'
1001     target_inc += include_directories('linux-headers', is_system: true)
1002   endif
1003   if target.endswith('-softmmu')
1004     qemu_target_name = 'qemu-system-' + target_name
1005     target_type='system'
1006     t = target_softmmu_arch[arch].apply(config_target, strict: false)
1007     arch_srcs += t.sources()
1008     arch_deps += t.dependencies()
1010     hw_dir = target_name == 'sparc64' ? 'sparc64' : arch
1011     hw = hw_arch[hw_dir].apply(config_target, strict: false)
1012     arch_srcs += hw.sources()
1013     arch_deps += hw.dependencies()
1015     arch_srcs += config_devices_h[target]
1016     link_args += ['@block.syms', '@qemu.syms']
1017   else
1018     abi = config_target['TARGET_ABI_DIR']
1019     target_type='user'
1020     qemu_target_name = 'qemu-' + target_name
1021     if 'CONFIG_LINUX_USER' in config_target
1022       base_dir = 'linux-user'
1023       target_inc += include_directories('linux-user/host/' / config_host['ARCH'])
1024     else
1025       base_dir = 'bsd-user'
1026     endif
1027     target_inc += include_directories(
1028       base_dir,
1029       base_dir / abi,
1030     )
1031     if 'CONFIG_LINUX_USER' in config_target
1032       dir = base_dir / abi
1033       arch_srcs += files(dir / 'signal.c', dir / 'cpu_loop.c')
1034       if config_target.has_key('TARGET_SYSTBL_ABI')
1035         arch_srcs += \
1036           syscall_nr_generators[abi].process(base_dir / abi / config_target['TARGET_SYSTBL'],
1037                                              extra_args : config_target['TARGET_SYSTBL_ABI'])
1038       endif
1039     endif
1040   endif
1042   if 'TARGET_XML_FILES' in config_target
1043     gdbstub_xml = custom_target(target + '-gdbstub-xml.c',
1044                                 output: target + '-gdbstub-xml.c',
1045                                 input: files(config_target['TARGET_XML_FILES'].split()),
1046                                 command: [feature_to_c, '@INPUT@'],
1047                                 capture: true)
1048     arch_srcs += gdbstub_xml
1049   endif
1051   t = target_arch[arch].apply(config_target, strict: false)
1052   arch_srcs += t.sources()
1053   arch_deps += t.dependencies()
1055   target_common = common_ss.apply(config_target, strict: false)
1056   objects = common_all.extract_objects(target_common.sources())
1057   deps = target_common.dependencies()
1059   target_specific = specific_ss.apply(config_target, strict: false)
1060   arch_srcs += target_specific.sources()
1061   arch_deps += target_specific.dependencies()
1063   lib = static_library('qemu-' + target,
1064                  sources: arch_srcs + genh,
1065                  dependencies: arch_deps,
1066                  objects: objects,
1067                  include_directories: target_inc,
1068                  c_args: c_args,
1069                  build_by_default: false,
1070                  name_suffix: 'fa')
1072   if target.endswith('-softmmu')
1073     execs = [{
1074       'name': 'qemu-system-' + target_name,
1075       'gui': false,
1076       'sources': files('softmmu/main.c'),
1077       'dependencies': []
1078     }]
1079     if targetos == 'windows' and (sdl.found() or gtk.found())
1080       execs += [{
1081         'name': 'qemu-system-' + target_name + 'w',
1082         'gui': true,
1083         'sources': files('softmmu/main.c'),
1084         'dependencies': []
1085       }]
1086     endif
1087     if config_host.has_key('CONFIG_FUZZ')
1088       specific_fuzz = specific_fuzz_ss.apply(config_target, strict: false)
1089       execs += [{
1090         'name': 'qemu-fuzz-' + target_name,
1091         'gui': false,
1092         'sources': specific_fuzz.sources(),
1093         'dependencies': specific_fuzz.dependencies(),
1094       }]
1095     endif
1096   else
1097     execs = [{
1098       'name': 'qemu-' + target_name,
1099       'gui': false,
1100       'sources': [],
1101       'dependencies': []
1102     }]
1103   endif
1104   foreach exe: execs
1105     emulators += executable(exe['name'], exe['sources'],
1106                install: true,
1107                c_args: c_args,
1108                dependencies: arch_deps + deps + exe['dependencies'],
1109                objects: lib.extract_all_objects(recursive: true),
1110                link_language: link_language,
1111                link_depends: [block_syms, qemu_syms] + exe.get('link_depends', []),
1112                link_args: link_args,
1113                gui_app: exe['gui'])
1115     if 'CONFIG_TRACE_SYSTEMTAP' in config_host
1116       foreach stp: [
1117         {'ext': '.stp-build', 'fmt': 'stap', 'bin': meson.current_build_dir() / exe['name'], 'install': false},
1118         {'ext': '.stp', 'fmt': 'stap', 'bin': get_option('prefix') / get_option('bindir') / exe['name'], 'install': true},
1119         {'ext': '-simpletrace.stp', 'fmt': 'simpletrace-stap', 'bin': '', 'install': true},
1120         {'ext': '-log.stp', 'fmt': 'log-stap', 'bin': '', 'install': true},
1121       ]
1122         custom_target(exe['name'] + stp['ext'],
1123                       input: trace_events_all,
1124                       output: exe['name'] + stp['ext'],
1125                       capture: true,
1126                       install: stp['install'],
1127                       install_dir: qemu_datadir / '../systemtap/tapset',
1128                       command: [
1129                         tracetool, '--group=all', '--format=' + stp['fmt'],
1130                         '--binary=' + stp['bin'],
1131                         '--target-name=' + target_name,
1132                         '--target-type=' + target_type,
1133                         '--probe-prefix=qemu.' + target_type + '.' + target_name,
1134                         '@INPUT@',
1135                       ])
1136       endforeach
1137     endif
1138   endforeach
1139 endforeach
1141 # Other build targets
1143 if 'CONFIG_PLUGIN' in config_host
1144   install_headers('include/qemu/qemu-plugin.h')
1145 endif
1147 if 'CONFIG_GUEST_AGENT' in config_host
1148   subdir('qga')
1149 endif
1151 # Don't build qemu-keymap if xkbcommon is not explicitly enabled
1152 # when we don't build tools or system
1153 if xkbcommon.found()
1154   # used for the update-keymaps target, so include rules even if !have_tools
1155   qemu_keymap = executable('qemu-keymap', files('qemu-keymap.c', 'ui/input-keymap.c') + genh,
1156                            dependencies: [qemuutil, xkbcommon], install: have_tools)
1157 endif
1159 qemu_block_tools = []
1160 if have_tools
1161   qemu_img = executable('qemu-img', [files('qemu-img.c'), hxdep],
1162              dependencies: [authz, block, crypto, io, qom, qemuutil], install: true)
1163   qemu_io = executable('qemu-io', files('qemu-io.c'),
1164              dependencies: [block, qemuutil], install: true)
1165   qemu_nbd = executable('qemu-nbd', files('qemu-nbd.c'),
1166                dependencies: [block, qemuutil], install: true)
1168   subdir('storage-daemon')
1169   subdir('contrib/rdmacm-mux')
1170   subdir('contrib/elf2dmp')
1172   executable('qemu-edid', files('qemu-edid.c', 'hw/display/edid-generate.c'),
1173              dependencies: qemuutil,
1174              install: true)
1176   if 'CONFIG_VHOST_USER' in config_host
1177     subdir('contrib/libvhost-user')
1178     subdir('contrib/vhost-user-blk')
1179     subdir('contrib/vhost-user-gpu')
1180     subdir('contrib/vhost-user-input')
1181     subdir('contrib/vhost-user-scsi')
1182   endif
1184   if targetos == 'linux'
1185     executable('qemu-bridge-helper', files('qemu-bridge-helper.c'),
1186                dependencies: [qemuutil, libcap_ng],
1187                install: true,
1188                install_dir: get_option('libexecdir'))
1190     executable('qemu-pr-helper', files('scsi/qemu-pr-helper.c', 'scsi/utils.c'),
1191                dependencies: [authz, crypto, io, qom, qemuutil,
1192                               libcap_ng, libudev, libmpathpersist],
1193                install: true)
1194   endif
1196   if 'CONFIG_IVSHMEM' in config_host
1197     subdir('contrib/ivshmem-client')
1198     subdir('contrib/ivshmem-server')
1199   endif
1200 endif
1202 subdir('scripts')
1203 subdir('tools')
1204 subdir('pc-bios')
1205 subdir('tests')
1206 subdir('docs')
1207 if 'CONFIG_GTK' in config_host
1208   subdir('po')
1209 endif
1211 if build_docs
1212   makeinfo = find_program('makeinfo', required: build_docs)
1214   docs_inc = [
1215     '-I', meson.current_source_dir(),
1216     '-I', meson.current_build_dir() / 'docs',
1217     '-I', '@OUTDIR@',
1218   ]
1220   version_texi = configure_file(output: 'version.texi',
1221                               input: 'version.texi.in',
1222                               configuration: {'VERSION': meson.project_version(),
1223                                               'qemu_confdir': config_host['qemu_confdir']})
1225   texi = {
1226     'qemu-qmp-ref': ['docs/interop/qemu-qmp-ref.texi', qapi_doc_texi, version_texi],
1227   }
1228   if 'CONFIG_GUEST_AGENT' in config_host
1229     texi += {'qemu-ga-ref': ['docs/interop/qemu-ga-ref.texi', qga_qapi_doc_texi, version_texi]}
1230   endif
1232   if makeinfo.found()
1233     cmd = [
1234       'env', 'LC_ALL=C', makeinfo, '--no-split', '--number-sections', docs_inc,
1235       '@INPUT0@', '-o', '@OUTPUT@',
1236     ]
1237     foreach ext, args: {
1238         'info': [],
1239         'html': ['--no-headers', '--html'],
1240         'txt': ['--no-headers', '--plaintext'],
1241     }
1242       t = []
1243       foreach doc, input: texi
1244         output = doc + '.' + ext
1245         t += custom_target(output,
1246                       input: input,
1247                       output: output,
1248                       install: true,
1249                       install_dir: qemu_docdir / 'interop',
1250                       command: cmd + args)
1251       endforeach
1252       alias_target(ext, t)
1253     endforeach
1254   endif
1256   texi2pdf = find_program('texi2pdf', required: false)
1258   if texi2pdf.found()
1259     pdfs = []
1260     foreach doc, input: texi
1261       output = doc + '.pdf'
1262       pdfs += custom_target(output,
1263                     input: input,
1264                     output: output,
1265                     command: [texi2pdf, '-q', docs_inc, '@INPUT0@', '-o', '@OUTPUT@'],
1266                     build_by_default: false)
1267     endforeach
1268     alias_target('pdf', pdfs)
1269   endif
1271   texi2pod = find_program('scripts/texi2pod.pl')
1272   pod2man = find_program('pod2man', required: build_docs)
1274   if pod2man.found()
1275     foreach doc, input: texi
1276       man = doc + '.7'
1277       pod = custom_target(man + '.pod',
1278                           input: input,
1279                           output: man + '.pod',
1280                           command: [texi2pod,
1281                                     '-DVERSION="' + meson.project_version() + '"',
1282                                     '-DCONFDIR="' + config_host['qemu_confdir'] + '"',
1283                                     '@INPUT0@', '@OUTPUT@'])
1284       man = custom_target(man,
1285                           input: pod,
1286                           output: man,
1287                           capture: true,
1288                           install: true,
1289                           install_dir: get_option('mandir') / 'man7',
1290                           command: [pod2man, '--utf8', '--section=7', '--center=" "',
1291                                     '--release=" "', '@INPUT@'])
1292     endforeach
1293   endif
1294 endif
1296 if host_machine.system() == 'windows'
1297   nsis_cmd = [
1298     find_program('scripts/nsis.py'),
1299     '@OUTPUT@',
1300     get_option('prefix'),
1301     meson.current_source_dir(),
1302     host_machine.cpu_family(),
1303     '--',
1304     '-DDISPLAYVERSION=' + meson.project_version(),
1305   ]
1306   if build_docs
1307     nsis_cmd += '-DCONFIG_DOCUMENTATION=y'
1308   endif
1309   if 'CONFIG_GTK' in config_host
1310     nsis_cmd += '-DCONFIG_GTK=y'
1311   endif
1313   nsis = custom_target('nsis',
1314                        output: 'qemu-setup-' + meson.project_version() + '.exe',
1315                        input: files('qemu.nsi'),
1316                        build_always_stale: true,
1317                        command: nsis_cmd + ['@INPUT@'])
1318   alias_target('installer', nsis)
1319 endif
1321 summary_info = {}
1322 summary_info += {'Install prefix':    config_host['prefix']}
1323 summary_info += {'BIOS directory':    config_host['qemu_datadir']}
1324 summary_info += {'firmware path':     config_host['qemu_firmwarepath']}
1325 summary_info += {'binary directory':  config_host['bindir']}
1326 summary_info += {'library directory': config_host['libdir']}
1327 summary_info += {'module directory':  config_host['qemu_moddir']}
1328 summary_info += {'libexec directory': config_host['libexecdir']}
1329 summary_info += {'include directory': config_host['includedir']}
1330 summary_info += {'config directory':  config_host['sysconfdir']}
1331 if targetos != 'windows'
1332   summary_info += {'local state directory': config_host['qemu_localstatedir']}
1333   summary_info += {'Manual directory':      get_option('mandir')}
1334 else
1335   summary_info += {'local state directory': 'queried at runtime'}
1336 endif
1337 summary_info += {'Doc directory':     get_option('docdir')}
1338 summary_info += {'Build directory':   meson.current_build_dir()}
1339 summary_info += {'Source path':       meson.current_source_dir()}
1340 summary_info += {'GIT binary':        config_host['GIT']}
1341 summary_info += {'GIT submodules':    config_host['GIT_SUBMODULES']}
1342 summary_info += {'C compiler':        meson.get_compiler('c').cmd_array()[0]}
1343 summary_info += {'Host C compiler':   meson.get_compiler('c', native: true).cmd_array()[0]}
1344 if link_language == 'cpp'
1345   summary_info += {'C++ compiler':      meson.get_compiler('cpp').cmd_array()[0]}
1346 else
1347   summary_info += {'C++ compiler':      false}
1348 endif
1349 if targetos == 'darwin'
1350   summary_info += {'Objective-C compiler': meson.get_compiler('objc').cmd_array()[0]}
1351 endif
1352 summary_info += {'ARFLAGS':           config_host['ARFLAGS']}
1353 summary_info += {'CFLAGS':            config_host['CFLAGS']}
1354 summary_info += {'QEMU_CFLAGS':       config_host['QEMU_CFLAGS']}
1355 summary_info += {'QEMU_LDFLAGS':      config_host['QEMU_LDFLAGS']}
1356 summary_info += {'make':              config_host['MAKE']}
1357 summary_info += {'python':            '@0@ (version: @1@)'.format(python.full_path(), python.language_version())}
1358 summary_info += {'sphinx-build':      config_host['SPHINX_BUILD']}
1359 summary_info += {'genisoimage':       config_host['GENISOIMAGE']}
1360 # TODO: add back version
1361 summary_info += {'slirp support':     config_host.has_key('CONFIG_SLIRP')}
1362 if config_host.has_key('CONFIG_SLIRP')
1363   summary_info += {'smbd':            config_host['CONFIG_SMBD_COMMAND']}
1364 endif
1365 summary_info += {'module support':    config_host.has_key('CONFIG_MODULES')}
1366 if config_host.has_key('CONFIG_MODULES')
1367   summary_info += {'alternative module path': config_host.has_key('CONFIG_MODULE_UPGRADES')}
1368 endif
1369 summary_info += {'host CPU':          cpu}
1370 summary_info += {'host endianness':   build_machine.endian()}
1371 summary_info += {'target list':       config_host['TARGET_DIRS']}
1372 summary_info += {'gprof enabled':     config_host.has_key('CONFIG_GPROF')}
1373 summary_info += {'sparse enabled':    meson.get_compiler('c').cmd_array().contains('cgcc')}
1374 summary_info += {'strip binaries':    get_option('strip')}
1375 summary_info += {'profiler':          config_host.has_key('CONFIG_PROFILER')}
1376 summary_info += {'static build':      config_host.has_key('CONFIG_TOOLS')}
1377 if targetos == 'darwin'
1378   summary_info += {'Cocoa support': config_host.has_key('CONFIG_COCOA')}
1379 endif
1380 # TODO: add back version
1381 summary_info += {'SDL support':       sdl.found()}
1382 summary_info += {'SDL image support': sdl_image.found()}
1383 # TODO: add back version
1384 summary_info += {'GTK support':       config_host.has_key('CONFIG_GTK')}
1385 summary_info += {'GTK GL support':    config_host.has_key('CONFIG_GTK_GL')}
1386 summary_info += {'pixman':            pixman.found()}
1387 # TODO: add back version
1388 summary_info += {'VTE support':       config_host.has_key('CONFIG_VTE')}
1389 summary_info += {'TLS priority':      config_host['CONFIG_TLS_PRIORITY']}
1390 summary_info += {'GNUTLS support':    config_host.has_key('CONFIG_GNUTLS')}
1391 # TODO: add back version
1392 summary_info += {'libgcrypt':         config_host.has_key('CONFIG_GCRYPT')}
1393 if config_host.has_key('CONFIG_GCRYPT')
1394    summary_info += {'  hmac':            config_host.has_key('CONFIG_GCRYPT_HMAC')}
1395    summary_info += {'  XTS':             not config_host.has_key('CONFIG_QEMU_PRIVATE_XTS')}
1396 endif
1397 # TODO: add back version
1398 summary_info += {'nettle':            config_host.has_key('CONFIG_NETTLE')}
1399 if config_host.has_key('CONFIG_NETTLE')
1400    summary_info += {'  XTS':             not config_host.has_key('CONFIG_QEMU_PRIVATE_XTS')}
1401 endif
1402 summary_info += {'libtasn1':          config_host.has_key('CONFIG_TASN1')}
1403 summary_info += {'PAM':               config_host.has_key('CONFIG_AUTH_PAM')}
1404 summary_info += {'iconv support':     config_host.has_key('CONFIG_ICONV')}
1405 summary_info += {'curses support':    config_host.has_key('CONFIG_CURSES')}
1406 # TODO: add back version
1407 summary_info += {'virgl support':     config_host.has_key('CONFIG_VIRGL')}
1408 summary_info += {'curl support':      config_host.has_key('CONFIG_CURL')}
1409 summary_info += {'mingw32 support':   targetos == 'windows'}
1410 summary_info += {'Audio drivers':     config_host['CONFIG_AUDIO_DRIVERS']}
1411 summary_info += {'Block whitelist (rw)': config_host['CONFIG_BDRV_RW_WHITELIST']}
1412 summary_info += {'Block whitelist (ro)': config_host['CONFIG_BDRV_RO_WHITELIST']}
1413 summary_info += {'VirtFS support':    config_host.has_key('CONFIG_VIRTFS')}
1414 summary_info += {'Multipath support': config_host.has_key('CONFIG_MPATH')}
1415 summary_info += {'VNC support':       vnc.found()}
1416 if vnc.found()
1417   summary_info += {'VNC SASL support':  sasl.found()}
1418   summary_info += {'VNC JPEG support':  jpeg.found()}
1419   summary_info += {'VNC PNG support':   png.found()}
1420 endif
1421 summary_info += {'xen support':       config_host.has_key('CONFIG_XEN_BACKEND')}
1422 if config_host.has_key('CONFIG_XEN_BACKEND')
1423   summary_info += {'xen ctrl version':  config_host['CONFIG_XEN_CTRL_INTERFACE_VERSION']}
1424 endif
1425 summary_info += {'brlapi support':    config_host.has_key('CONFIG_BRLAPI')}
1426 summary_info += {'Documentation':     config_host.has_key('BUILD_DOCS')}
1427 summary_info += {'PIE':               get_option('b_pie')}
1428 summary_info += {'vde support':       config_host.has_key('CONFIG_VDE')}
1429 summary_info += {'netmap support':    config_host.has_key('CONFIG_NETMAP')}
1430 summary_info += {'Linux AIO support': config_host.has_key('CONFIG_LINUX_AIO')}
1431 summary_info += {'Linux io_uring support': config_host.has_key('CONFIG_LINUX_IO_URING')}
1432 summary_info += {'ATTR/XATTR support': config_host.has_key('CONFIG_ATTR')}
1433 summary_info += {'Install blobs':     config_host.has_key('INSTALL_BLOBS')}
1434 # TODO: add back KVM/HAX/HVF/WHPX/TCG
1435 #summary_info += {'KVM support':       have_kvm'}
1436 #summary_info += {'HAX support':       have_hax'}
1437 #summary_info += {'HVF support':       have_hvf'}
1438 #summary_info += {'WHPX support':      have_whpx'}
1439 #summary_info += {'TCG support':       have_tcg'}
1440 #if get_option('tcg')
1441 #  summary_info += {'TCG debug enabled': config_host.has_key('CONFIG_DEBUG_TCG')}
1442 #  summary_info += {'TCG interpreter':   config_host.has_key('CONFIG_TCG_INTERPRETER')}
1443 #endif
1444 summary_info += {'malloc trim support': config_host.has_key('CONFIG_MALLOC_TRIM')}
1445 summary_info += {'RDMA support':      config_host.has_key('CONFIG_RDMA')}
1446 summary_info += {'PVRDMA support':    config_host.has_key('CONFIG_PVRDMA')}
1447 summary_info += {'fdt support':       config_host.has_key('CONFIG_FDT')}
1448 summary_info += {'membarrier':        config_host.has_key('CONFIG_MEMBARRIER')}
1449 summary_info += {'preadv support':    config_host.has_key('CONFIG_PREADV')}
1450 summary_info += {'fdatasync':         config_host.has_key('CONFIG_FDATASYNC')}
1451 summary_info += {'madvise':           config_host.has_key('CONFIG_MADVISE')}
1452 summary_info += {'posix_madvise':     config_host.has_key('CONFIG_POSIX_MADVISE')}
1453 summary_info += {'posix_memalign':    config_host.has_key('CONFIG_POSIX_MEMALIGN')}
1454 summary_info += {'libcap-ng support': config_host.has_key('CONFIG_LIBCAP_NG')}
1455 summary_info += {'vhost-net support': config_host.has_key('CONFIG_VHOST_NET')}
1456 summary_info += {'vhost-crypto support': config_host.has_key('CONFIG_VHOST_CRYPTO')}
1457 summary_info += {'vhost-scsi support': config_host.has_key('CONFIG_VHOST_SCSI')}
1458 summary_info += {'vhost-vsock support': config_host.has_key('CONFIG_VHOST_VSOCK')}
1459 summary_info += {'vhost-user support': config_host.has_key('CONFIG_VHOST_KERNEL')}
1460 summary_info += {'vhost-user-fs support': config_host.has_key('CONFIG_VHOST_USER_FS')}
1461 summary_info += {'vhost-vdpa support': config_host.has_key('CONFIG_VHOST_VDPA')}
1462 summary_info += {'Trace backends':    config_host['TRACE_BACKENDS']}
1463 if config_host['TRACE_BACKENDS'].split().contains('simple')
1464   summary_info += {'Trace output file': config_host['CONFIG_TRACE_FILE'] + '-<pid>'}
1465 endif
1466 # TODO: add back protocol and server version
1467 summary_info += {'spice support':     config_host.has_key('CONFIG_SPICE')}
1468 summary_info += {'rbd support':       config_host.has_key('CONFIG_RBD')}
1469 summary_info += {'xfsctl support':    config_host.has_key('CONFIG_XFS')}
1470 summary_info += {'smartcard support': config_host.has_key('CONFIG_SMARTCARD')}
1471 summary_info += {'U2F support':       u2f.found()}
1472 summary_info += {'libusb':            config_host.has_key('CONFIG_USB_LIBUSB')}
1473 summary_info += {'usb net redir':     config_host.has_key('CONFIG_USB_REDIR')}
1474 summary_info += {'OpenGL support':    config_host.has_key('CONFIG_OPENGL')}
1475 summary_info += {'OpenGL dmabufs':    config_host.has_key('CONFIG_OPENGL_DMABUF')}
1476 summary_info += {'libiscsi support':  config_host.has_key('CONFIG_LIBISCSI')}
1477 summary_info += {'libnfs support':    config_host.has_key('CONFIG_LIBNFS')}
1478 summary_info += {'build guest agent': config_host.has_key('CONFIG_GUEST_AGENT')}
1479 if targetos == 'windows'
1480   if 'WIN_SDK' in config_host
1481     summary_info += {'Windows SDK':       config_host['WIN_SDK']}
1482   endif
1483   summary_info += {'QGA VSS support':   config_host.has_key('CONFIG_QGA_VSS')}
1484   summary_info += {'QGA w32 disk info': config_host.has_key('CONFIG_QGA_NTDDSCSI')}
1485   summary_info += {'QGA MSI support':   config_host.has_key('CONFIG_QGA_MSI_ENABLED')}
1486 endif
1487 summary_info += {'seccomp support':   config_host.has_key('CONFIG_SECCOMP')}
1488 summary_info += {'coroutine backend': config_host['CONFIG_COROUTINE_BACKEND']}
1489 summary_info += {'coroutine pool':    config_host['CONFIG_COROUTINE_POOL'] == '1'}
1490 summary_info += {'debug stack usage': config_host.has_key('CONFIG_DEBUG_STACK_USAGE')}
1491 summary_info += {'mutex debugging':   config_host.has_key('CONFIG_DEBUG_MUTEX')}
1492 summary_info += {'crypto afalg':      config_host.has_key('CONFIG_AF_ALG')}
1493 summary_info += {'GlusterFS support': config_host.has_key('CONFIG_GLUSTERFS')}
1494 summary_info += {'gcov':              get_option('b_coverage')}
1495 summary_info += {'TPM support':       config_host.has_key('CONFIG_TPM')}
1496 summary_info += {'libssh support':    config_host.has_key('CONFIG_LIBSSH')}
1497 summary_info += {'QOM debugging':     config_host.has_key('CONFIG_QOM_CAST_DEBUG')}
1498 summary_info += {'Live block migration': config_host.has_key('CONFIG_LIVE_BLOCK_MIGRATION')}
1499 summary_info += {'lzo support':       config_host.has_key('CONFIG_LZO')}
1500 summary_info += {'snappy support':    config_host.has_key('CONFIG_SNAPPY')}
1501 summary_info += {'bzip2 support':     config_host.has_key('CONFIG_BZIP2')}
1502 summary_info += {'lzfse support':     config_host.has_key('CONFIG_LZFSE')}
1503 summary_info += {'zstd support':      config_host.has_key('CONFIG_ZSTD')}
1504 summary_info += {'NUMA host support': config_host.has_key('CONFIG_NUMA')}
1505 summary_info += {'libxml2':           config_host.has_key('CONFIG_LIBXML2')}
1506 summary_info += {'tcmalloc support':  config_host.has_key('CONFIG_TCMALLOC')}
1507 summary_info += {'jemalloc support':  config_host.has_key('CONFIG_JEMALLOC')}
1508 summary_info += {'avx2 optimization': config_host.has_key('CONFIG_AVX2_OPT')}
1509 summary_info += {'avx512f optimization': config_host.has_key('CONFIG_AVX512F_OPT')}
1510 summary_info += {'replication support': config_host.has_key('CONFIG_REPLICATION')}
1511 summary_info += {'bochs support':     config_host.has_key('CONFIG_BOCHS')}
1512 summary_info += {'cloop support':     config_host.has_key('CONFIG_CLOOP')}
1513 summary_info += {'dmg support':       config_host.has_key('CONFIG_DMG')}
1514 summary_info += {'qcow v1 support':   config_host.has_key('CONFIG_QCOW1')}
1515 summary_info += {'vdi support':       config_host.has_key('CONFIG_VDI')}
1516 summary_info += {'vvfat support':     config_host.has_key('CONFIG_VVFAT')}
1517 summary_info += {'qed support':       config_host.has_key('CONFIG_QED')}
1518 summary_info += {'parallels support': config_host.has_key('CONFIG_PARALLELS')}
1519 summary_info += {'sheepdog support':  config_host.has_key('CONFIG_SHEEPDOG')}
1520 summary_info += {'capstone':          config_host.has_key('CONFIG_CAPSTONE')}
1521 summary_info += {'libpmem support':   config_host.has_key('CONFIG_LIBPMEM')}
1522 summary_info += {'libdaxctl support': config_host.has_key('CONFIG_LIBDAXCTL')}
1523 summary_info += {'libudev':           config_host.has_key('CONFIG_LIBUDEV')}
1524 summary_info += {'default devices':   config_host['CONFIG_MINIKCONF_MODE'] == '--defconfig'}
1525 summary_info += {'plugin support':    config_host.has_key('CONFIG_PLUGIN')}
1526 summary_info += {'fuzzing support':   config_host.has_key('CONFIG_FUZZ')}
1527 if config_host.has_key('HAVE_GDB_BIN')
1528   summary_info += {'gdb':             config_host['HAVE_GDB_BIN']}
1529 endif
1530 summary_info += {'thread sanitizer':  config_host.has_key('CONFIG_TSAN')}
1531 summary_info += {'rng-none':          config_host.has_key('CONFIG_RNG_NONE')}
1532 summary_info += {'Linux keyring':     config_host.has_key('CONFIG_SECRET_KEYRING')}
1533 summary(summary_info, bool_yn: true)
1535 if not supported_cpus.contains(cpu)
1536   message()
1537   warning('SUPPORT FOR THIS HOST CPU WILL GO AWAY IN FUTURE RELEASES!')
1538   message()
1539   message('CPU host architecture ' + cpu + ' support is not currently maintained.')
1540   message('The QEMU project intends to remove support for this host CPU in')
1541   message('a future release if nobody volunteers to maintain it and to')
1542   message('provide a build host for our continuous integration setup.')
1543   message('configure has succeeded and you can continue to build, but')
1544   message('if you care about QEMU on this platform you should contact')
1545   message('us upstream at qemu-devel@nongnu.org.')
1546 endif
1548 if not supported_oses.contains(targetos)
1549   message()
1550   warning('WARNING: SUPPORT FOR THIS HOST OS WILL GO AWAY IN FUTURE RELEASES!')
1551   message()
1552   message('Host OS ' + targetos + 'support is not currently maintained.')
1553   message('The QEMU project intends to remove support for this host OS in')
1554   message('a future release if nobody volunteers to maintain it and to')
1555   message('provide a build host for our continuous integration setup.')
1556   message('configure has succeeded and you can continue to build, but')
1557   message('if you care about QEMU on this platform you should contact')
1558   message('us upstream at qemu-devel@nongnu.org.')
1559 endif