Split JackWaitThreadedDriver's Execute method
[jack2.git] / wscript
blob7694738aede0261869cc26edc7cc21cb2a9d85af
1 #! /usr/bin/env python
2 # encoding: utf-8
3 from __future__ import print_function
5 import os
6 import Utils
7 import Options
8 import subprocess
9 g_maxlen = 40
10 import shutil
11 import Task
12 import re
13 import Logs
14 import sys
16 import waflib.Options
17 from waflib.Build import BuildContext, CleanContext, InstallContext, UninstallContext
19 VERSION='1.9.11'
20 APPNAME='jack'
21 JACK_API_VERSION = '0.1.0'
23 # these variables are mandatory ('/' are converted automatically)
24 top = '.'
25 out = 'build'
27 # lib32 variant name used when building in mixed mode
28 lib32 = 'lib32'
30 auto_options = []
32 def display_msg(msg, status = None, color = None):
33 sr = msg
34 global g_maxlen
35 g_maxlen = max(g_maxlen, len(msg))
36 if status:
37 Logs.pprint('NORMAL', "%s :" % msg.ljust(g_maxlen), sep=' ')
38 Logs.pprint(color, status)
39 else:
40 print("%s" % msg.ljust(g_maxlen))
42 def display_feature(msg, build):
43 if build:
44 display_msg(msg, "yes", 'GREEN')
45 else:
46 display_msg(msg, "no", 'YELLOW')
48 def print_error(msg):
49 """
50 This function prints an error without stopping waf. The reason waf should
51 not be stopped is to be able to list all missing dependencies in one chunk.
52 """
53 print(Logs.colors.RED + msg + Logs.colors.NORMAL)
55 def create_svnversion_task(bld, header='svnversion.h', define=None):
56 cmd = '../svnversion_regenerate.sh ${TGT}'
57 if define:
58 cmd += " " + define
60 def post_run(self):
61 sg = Utils.h_file(self.outputs[0].abspath(self.env))
62 #print sg.encode('hex')
63 Build.bld.node_sigs[self.env.variant()][self.outputs[0].id] = sg
65 bld(
66 rule = cmd,
67 name = 'svnversion',
68 runnable_status = Task.RUN_ME,
69 before = 'c',
70 color = 'BLUE',
71 post_run = post_run,
72 target = [bld.path.find_or_declare(header)]
75 class AutoOption:
76 """
77 This class is the foundation for the auto options. It adds an option
78 --foo=no|yes to the list of options and deals with all logic and checks for
79 these options.
81 Each option can have different dependencies that will be checked. If all
82 dependencies are available and the user has not done any request the option
83 will be enabled. If the user has requested to enable the option the class
84 ensures that all dependencies are available and prints an error message
85 otherwise. If the user disables the option, i.e. --foo=no, no checks are
86 made.
88 For each option it is possible to add packages that are required for the
89 option using the add_package function. For dependency programs add_program
90 should be used. For libraries (without pkg-config support) the add_library
91 function should be used. For headers the add_header function exists. If
92 there is another type of requirement or dependency the check hook (an
93 external function called when configuring) can be used.
95 When all checks have been made and the class has made a decision the result
96 is saved in conf.env['NAME'] where 'NAME' by default is the uppercase of the
97 name argument to __init__, but it can be changed with the conf_dest argument
98 to __init__.
100 The class will define a preprocessor symbol with the result. The default
101 name is HAVE_NAME, but it can be changed using the define argument to
102 __init__.
105 def __init__(self, opt, name, help, conf_dest=None, define=None):
106 # check hook to call upon configuration
107 self.check_hook = None
108 self.check_hook_error = None
109 self.check_hook_found = True
111 # required libraries
112 self.libs = [] # elements on the form [lib,uselib_store]
113 self.libs_not_found = [] # elements on the form lib
115 # required headers
116 self.headers = []
117 self.headers_not_found = []
119 # required packages (checked with pkg-config)
120 self.packages = [] # elements on the form [package,uselib_store,atleast_version]
121 self.packages_not_found = [] # elements on the form [package,atleast_version]
123 # required programs
124 self.programs = [] # elements on the form [program,var]
125 self.programs_not_found = [] # elements on the form program
127 # the result of the configuration (should the option be enabled or not?)
128 self.result = False
130 self.help = help
131 self.option = '--' + name
132 self.dest = 'auto_option_' + name
133 if conf_dest:
134 self.conf_dest = conf_dest
135 else:
136 self.conf_dest = name.upper()
137 if not define:
138 self.define = 'HAVE_' + name.upper()
139 else:
140 self.define = define
141 opt.add_option(self.option, type='string', default='auto', dest=self.dest, help=self.help+' (enabled by default if possible)', metavar='no|yes')
143 def add_library(self, library, uselib_store=None):
145 Add a required library that should be checked during configuration. The
146 library will be checked using the conf.check_cc function. If the
147 uselib_store arugment is not given it defaults to LIBRARY (the uppercase
148 of the library argument). The uselib_store argument will be passed to
149 check_cc which means LIB_LIBRARY, CFLAGS_LIBRARY and DEFINES_LIBRARY,
150 etc. will be defined if the option is enabled.
152 if not uselib_store:
153 uselib_store = library.upper().replace('-', '_')
154 self.libs.append([library, uselib_store])
156 def add_header(self, header):
158 Add a required header that should be checked during configuration. The
159 header will be checked using the conf.check_cc function which means
160 HAVE_HEADER_H will be defined if found.
162 self.headers.append(header)
164 def add_package(self, package, uselib_store=None, atleast_version=None):
166 Add a required package that should be checked using pkg-config during
167 configuration. The package will be checked using the conf.check_cfg
168 function and the uselib_store and atleast_version will be passed to
169 check_cfg. If uselib_store is None it defaults to PACKAGE (uppercase of
170 the package argument) with hyphens and dots replaced with underscores.
171 If atleast_version is None it defaults to '0'.
173 if not uselib_store:
174 uselib_store = package.upper().replace('-', '_').replace('.', '_')
175 if not atleast_version:
176 atleast_version = '0'
177 self.packages.append([package, uselib_store, atleast_version])
179 def add_program(self, program, var=None):
181 Add a required program that should be checked during configuration. If
182 var is not given it defaults to PROGRAM (the uppercase of the program
183 argument). If the option is enabled the program is saved in
184 conf.env.PROGRAM.
186 if not var:
187 var = program.upper().replace('-', '_')
188 self.programs.append([program, var])
190 def set_check_hook(self, check_hook, check_hook_error):
192 Set the check hook and the corresponding error printing function to the
193 configure step. The check_hook argument is a function that should return
194 True if the extra prerequisites were found and False if not. The
195 check_hook_error argument is an error printing function that should
196 print an error message telling the user that --foo was explicitly
197 requested but cannot be built since the extra prerequisites were not
198 found. Both function should take a single argument that is the waf
199 configuration context.
201 self.check_hook = check_hook
202 self.check_hook_error = check_hook_error
204 def _check(self, conf):
206 This is an internal function that runs all necessary configure checks.
207 It checks all dependencies (even if some dependency was not found) so
208 that the user can install all missing dependencies in one go, instead
209 of playing the infamous hit-configure-hit-configure game.
211 This function returns True if all dependencies were found and False if
212 not.
214 all_found = True
216 # check for libraries
217 for lib,uselib_store in self.libs:
218 try:
219 conf.check_cc(lib=lib, uselib_store=uselib_store)
220 except conf.errors.ConfigurationError:
221 all_found = False
222 self.libs_not_found.append(lib)
224 # check for headers
225 for header in self.headers:
226 try:
227 conf.check_cc(header_name=header)
228 except conf.errors.ConfigurationError:
229 all_found = False
230 self.headers_not_found.append(header)
232 # check for packages
233 for package,uselib_store,atleast_version in self.packages:
234 try:
235 conf.check_cfg(package=package, uselib_store=uselib_store, atleast_version=atleast_version, args='--cflags --libs')
236 except conf.errors.ConfigurationError:
237 all_found = False
238 self.packages_not_found.append([package,atleast_version])
240 # check for programs
241 for program,var in self.programs:
242 try:
243 conf.find_program(program, var=var)
244 except conf.errors.ConfigurationError:
245 all_found = False
246 self.programs_not_found.append(program)
248 # call hook (if specified)
249 if self.check_hook:
250 self.check_hook_found = self.check_hook(conf)
251 if not self.check_hook_found:
252 all_found = False
254 return all_found
256 def _configure_error(self, conf):
258 This is an internal function that prints errors for each missing
259 dependency. The error messages tell the user that this option required
260 some dependency, but it cannot be found.
263 for lib in self.libs_not_found:
264 print_error('%s requires the %s library, but it cannot be found.' % (self.option, lib))
266 for header in self.headers_not_found:
267 print_error('%s requires the %s header, but it cannot be found.' % (self.option, header))
269 for package,atleast_version in self.packages_not_found:
270 string = package
271 if atleast_version:
272 string += ' >= ' + atleast_version
273 print_error('%s requires the package %s, but it cannot be found.' % (self.option, string))
275 for program in self.programs_not_found:
276 print_error('%s requires the %s program, but it cannot be found.' % (self.option, program))
278 if not self.check_hook_found:
279 self.check_hook_error(conf)
281 def configure(self, conf):
283 This function configures the option examining the argument given too
284 --foo (where foo is this option). This function sets self.result to the
285 result of the configuration; True if the option should be enabled or
286 False if not. If not all dependencies were found self.result will shall
287 be False. conf.env['NAME'] will be set to the same value aswell as a
288 preprocessor symbol will be defined according to the result.
290 If --foo[=yes] was given, but some dependency was not found an error
291 message is printed (foreach missing dependency).
293 This function returns True on success and False on error.
295 argument = getattr(Options.options, self.dest)
296 if argument == 'no':
297 self.result = False
298 retvalue = True
299 elif argument == 'yes':
300 if self._check(conf):
301 self.result = True
302 retvalue = True
303 else:
304 self.result = False
305 retvalue = False
306 self._configure_error(conf)
307 elif argument == 'auto':
308 self.result = self._check(conf)
309 retvalue = True
310 else:
311 print_error('Invalid argument "' + argument + '" to ' + self.option)
312 self.result = False
313 retvalue = False
315 conf.env[self.conf_dest] = self.result
316 if self.result:
317 conf.define(self.define, 1)
318 else:
319 conf.define(self.define, 0)
320 return retvalue
322 def display_message(self):
324 This function displays a result message with the help text and the
325 result of the configuration.
327 display_feature(self.help, self.result)
329 def add_auto_option(opt, name, help, conf_dest=None, define=None):
331 Adds an option to the list of auto options and returns the newly created
332 option.
334 option = AutoOption(opt, name, help, conf_dest=conf_dest, define=define)
335 auto_options.append(option)
336 return option
338 def auto_options_argv_hack():
340 This function applies a hack that for each auto option --foo=no|yes replaces
341 any occurence --foo in argv with --foo=yes, in effect interpreting --foo as
342 --foo=yes. The function has to be called before waf issues the option
343 parser, i.e. before the configure phase.
345 for option in auto_options:
346 for x in range(1, len(sys.argv)):
347 if sys.argv[x] == option.option:
348 sys.argv[x] += '=yes'
350 def configure_auto_options(conf):
352 This function configures all auto options. It stops waf and prints an error
353 message if there were unsatisfied requirements.
355 ok = True
356 for option in auto_options:
357 if not option.configure(conf):
358 ok = False
359 if not ok:
360 conf.fatal('There were unsatisfied requirements.')
362 def display_auto_options_messages():
363 """This function displays all options and the configuration result."""
364 for option in auto_options:
365 option.display_message()
367 def check_for_celt(conf):
368 found = False
369 for version in ['11', '8', '7', '5']:
370 define = 'HAVE_CELT_API_0_' + version
371 if not found:
372 try:
373 conf.check_cfg(package='celt', atleast_version='0.' + version + '.0', args='--cflags --libs')
374 found = True
375 conf.define(define, 1)
376 continue
377 except conf.errors.ConfigurationError:
378 pass
379 conf.define(define, 0)
380 return found
382 def check_for_celt_error(conf):
383 print_error('--celt requires the package celt, but it could not be found.')
385 # The readline/readline.h header does not work if stdio.h is not included
386 # before. Thus a fragment with both stdio.h and readline/readline.h need to be
387 # test-compiled to find out whether readline is available.
388 def check_for_readline(conf):
389 try:
390 conf.check_cc(fragment='''
391 #include <stdio.h>
392 #include <readline/readline.h>
393 int main(void) { return 0; }''',
394 execute=False,
395 msg='Checking for header readline/readline.h')
396 return True
397 except conf.errors.ConfigurationError:
398 return False
400 def check_for_readline_error(conf):
401 print_error('--readline requires the readline/readline.h header, but it cannot be found.')
403 def check_for_mmsystem(conf):
404 try:
405 conf.check_cc(fragment='''
406 #include <windows.h>
407 #include <mmsystem.h>
408 int main(void) { return 0; }''',
409 execute=False,
410 msg='Checking for header mmsystem.h')
411 return True
412 except conf.errors.ConfigurationError:
413 return False
415 def check_for_mmsystem_error(conf):
416 print_error('--winmme requires the mmsystem.h header, but it cannot be found.')
418 def options(opt):
419 # options provided by the modules
420 opt.tool_options('compiler_cxx')
421 opt.tool_options('compiler_cc')
423 # install directories
424 opt.add_option('--htmldir', type='string', default=None, help="HTML documentation directory [Default: <prefix>/share/jack-audio-connection-kit/reference/html/")
425 opt.add_option('--libdir', type='string', help="Library directory [Default: <prefix>/lib]")
426 opt.add_option('--libdir32', type='string', help="32bit Library directory [Default: <prefix>/lib32]")
427 opt.add_option('--mandir', type='string', help="Manpage directory [Default: <prefix>/share/man/man1]")
429 # options affecting binaries
430 opt.add_option('--dist-target', type='string', default='auto', help='Specify the target for cross-compiling [auto,mingw]')
431 opt.add_option('--mixed', action='store_true', default=False, help='Build with 32/64 bits mixed mode')
432 opt.add_option('--debug', action='store_true', default=False, dest='debug', help='Build debuggable binaries')
434 # options affecting general jack functionality
435 opt.add_option('--classic', action='store_true', default=False, help='Force enable standard JACK (jackd) even if D-Bus JACK (jackdbus) is enabled too')
436 opt.add_option('--dbus', action='store_true', default=False, help='Enable D-Bus JACK (jackdbus)')
437 opt.add_option('--autostart', type='string', default="default", help='Autostart method. Possible values: "default", "classic", "dbus", "none"')
438 opt.add_option('--profile', action='store_true', default=False, help='Build with engine profiling')
439 opt.add_option('--clients', default=64, type="int", dest="clients", help='Maximum number of JACK clients')
440 opt.add_option('--ports-per-application', default=768, type="int", dest="application_ports", help='Maximum number of ports per application')
442 # options with third party dependencies
443 doxygen = add_auto_option(opt, 'doxygen', help='Build doxygen documentation', conf_dest='BUILD_DOXYGEN_DOCS')
444 doxygen.add_program('doxygen')
445 alsa = add_auto_option(opt, 'alsa', help='Enable ALSA driver', conf_dest='BUILD_DRIVER_ALSA')
446 alsa.add_package('alsa', atleast_version='1.0.18')
447 firewire = add_auto_option(opt, 'firewire', help='Enable FireWire driver (FFADO)', conf_dest='BUILD_DRIVER_FFADO')
448 firewire.add_package('libffado', atleast_version='1.999.17')
449 freebob = add_auto_option(opt, 'freebob', help='Enable FreeBob driver')
450 freebob.add_package('libfreebob', atleast_version='1.0.0')
451 iio = add_auto_option(opt, 'iio', help='Enable IIO driver', conf_dest='BUILD_DRIVER_IIO')
452 iio.add_package('gtkIOStream', atleast_version='1.4.0')
453 iio.add_package('eigen3', atleast_version='3.1.2')
454 portaudio = add_auto_option(opt, 'portaudio', help='Enable Portaudio driver', conf_dest='BUILD_DRIVER_PORTAUDIO')
455 portaudio.add_header('windows.h') # only build portaudio on windows
456 portaudio.add_package('portaudio-2.0', uselib_store='PORTAUDIO', atleast_version='19')
457 winmme = add_auto_option(opt, 'winmme', help='Enable WinMME driver', conf_dest='BUILD_DRIVER_WINMME')
458 winmme.set_check_hook(check_for_mmsystem, check_for_mmsystem_error)
460 celt = add_auto_option(opt, 'celt', help='Build with CELT')
461 celt.set_check_hook(check_for_celt, check_for_celt_error)
462 opus = add_auto_option(opt, 'opus', help='Build Opus netjack2')
463 opus.add_header('opus/opus_custom.h')
464 opus.add_package('opus', atleast_version='0.9.0')
465 samplerate = add_auto_option(opt, 'samplerate', help='Build with libsamplerate')
466 samplerate.add_package('samplerate')
467 sndfile = add_auto_option(opt, 'sndfile', help='Build with libsndfile')
468 sndfile.add_package('sndfile')
469 readline = add_auto_option(opt, 'readline', help='Build with readline')
470 readline.add_library('readline')
471 readline.set_check_hook(check_for_readline, check_for_readline_error)
473 # dbus options
474 opt.sub_options('dbus')
476 # this must be called before the configure phase
477 auto_options_argv_hack()
479 def configure(conf):
480 conf.load('compiler_cxx')
481 conf.load('compiler_cc')
482 if Options.options.dist_target == 'auto':
483 platform = sys.platform
484 conf.env['IS_MACOSX'] = platform == 'darwin'
485 conf.env['IS_LINUX'] = platform == 'linux' or platform == 'linux2' or platform == 'linux3' or platform == 'posix'
486 conf.env['IS_SUN'] = platform == 'sunos'
487 # GNU/kFreeBSD and GNU/Hurd are treated as Linux
488 if platform.startswith('gnu0') or platform.startswith('gnukfreebsd'):
489 conf.env['IS_LINUX'] = True
490 elif Options.options.dist_target == 'mingw':
491 conf.env['IS_WINDOWS'] = True
493 if conf.env['IS_LINUX']:
494 Logs.pprint('CYAN', "Linux detected")
496 if conf.env['IS_MACOSX']:
497 Logs.pprint('CYAN', "MacOS X detected")
499 if conf.env['IS_SUN']:
500 Logs.pprint('CYAN', "SunOS detected")
502 if conf.env['IS_WINDOWS']:
503 Logs.pprint('CYAN', "Windows detected")
505 if conf.env['IS_LINUX']:
506 conf.check_tool('compiler_cxx')
507 conf.check_tool('compiler_cc')
509 if conf.env['IS_MACOSX']:
510 conf.check_tool('compiler_cxx')
511 conf.check_tool('compiler_cc')
513 # waf 1.5 : check_tool('compiler_cxx') and check_tool('compiler_cc') do not work correctly, so explicit use of gcc and g++
514 if conf.env['IS_SUN']:
515 conf.check_tool('g++')
516 conf.check_tool('gcc')
518 #if conf.env['IS_SUN']:
519 # conf.check_tool('compiler_cxx')
520 # conf.check_tool('compiler_cc')
522 if conf.env['IS_WINDOWS']:
523 conf.check_tool('compiler_cxx')
524 conf.check_tool('compiler_cc')
525 conf.env.append_unique('CCDEFINES', '_POSIX')
526 conf.env.append_unique('CXXDEFINES', '_POSIX')
528 conf.env.append_unique('CXXFLAGS', '-Wall')
529 conf.env.append_unique('CFLAGS', '-Wall')
531 # configure all auto options
532 configure_auto_options(conf)
534 conf.sub_config('common')
535 if conf.env['IS_LINUX']:
536 conf.sub_config('linux')
537 if Options.options.dbus:
538 conf.sub_config('dbus')
539 if conf.env['BUILD_JACKDBUS'] != True:
540 conf.fatal('jackdbus was explicitly requested but cannot be built')
542 conf.sub_config('example-clients')
544 conf.env['LIB_PTHREAD'] = ['pthread']
545 conf.env['LIB_DL'] = ['dl']
546 conf.env['LIB_RT'] = ['rt']
547 conf.env['LIB_M'] = ['m']
548 conf.env['LIB_STDC++'] = ['stdc++']
549 conf.env['JACK_API_VERSION'] = JACK_API_VERSION
550 conf.env['JACK_VERSION'] = VERSION
552 conf.env['BUILD_WITH_PROFILE'] = Options.options.profile
553 conf.env['BUILD_WITH_32_64'] = Options.options.mixed
554 conf.env['BUILD_CLASSIC'] = Options.options.classic
555 conf.env['BUILD_DEBUG'] = Options.options.debug
557 if conf.env['BUILD_JACKDBUS']:
558 conf.env['BUILD_JACKD'] = conf.env['BUILD_CLASSIC']
559 else:
560 conf.env['BUILD_JACKD'] = True
562 conf.env['BINDIR'] = conf.env['PREFIX'] + '/bin'
564 if Options.options.htmldir:
565 conf.env['HTMLDIR'] = Options.options.htmldir
566 else:
567 # set to None here so that the doxygen code can find out the highest
568 # directory to remove upon install
569 conf.env['HTMLDIR'] = None
571 if Options.options.libdir:
572 conf.env['LIBDIR'] = Options.options.libdir
573 else:
574 conf.env['LIBDIR'] = conf.env['PREFIX'] + '/lib'
576 if Options.options.mandir:
577 conf.env['MANDIR'] = Options.options.mandir
578 else:
579 conf.env['MANDIR'] = conf.env['PREFIX'] + '/share/man/man1'
581 if conf.env['BUILD_DEBUG']:
582 conf.env.append_unique('CXXFLAGS', '-g')
583 conf.env.append_unique('CFLAGS', '-g')
584 conf.env.append_unique('LINKFLAGS', '-g')
586 if not Options.options.autostart in ["default", "classic", "dbus", "none"]:
587 conf.fatal("Invalid autostart value \"" + Options.options.autostart + "\"")
589 if Options.options.autostart == "default":
590 if conf.env['BUILD_JACKDBUS'] == True and conf.env['BUILD_JACKD'] == False:
591 conf.env['AUTOSTART_METHOD'] = "dbus"
592 else:
593 conf.env['AUTOSTART_METHOD'] = "classic"
594 else:
595 conf.env['AUTOSTART_METHOD'] = Options.options.autostart
597 if conf.env['AUTOSTART_METHOD'] == "dbus" and not conf.env['BUILD_JACKDBUS']:
598 conf.fatal("D-Bus autostart mode was specified but jackdbus will not be built")
599 if conf.env['AUTOSTART_METHOD'] == "classic" and not conf.env['BUILD_JACKD']:
600 conf.fatal("Classic autostart mode was specified but jackd will not be built")
602 if conf.env['AUTOSTART_METHOD'] == "dbus":
603 conf.define('USE_LIBDBUS_AUTOLAUNCH', 1)
604 elif conf.env['AUTOSTART_METHOD'] == "classic":
605 conf.define('USE_CLASSIC_AUTOLAUNCH', 1)
607 conf.define('CLIENT_NUM', Options.options.clients)
608 conf.define('PORT_NUM_FOR_CLIENT', Options.options.application_ports)
610 if conf.env['IS_WINDOWS']:
611 # we define this in the environment to maintain compatability with
612 # existing install paths that use ADDON_DIR rather than have to
613 # have special cases for windows each time.
614 conf.env['ADDON_DIR'] = conf.env['BINDIR'] + '/jack'
615 # don't define ADDON_DIR in config.h, use the default 'jack' defined in
616 # windows/JackPlatformPlug_os.h
617 else:
618 conf.env['ADDON_DIR'] = os.path.normpath(os.path.join(conf.env['LIBDIR'], 'jack'))
619 conf.define('ADDON_DIR', conf.env['ADDON_DIR'])
620 conf.define('JACK_LOCATION', os.path.normpath(os.path.join(conf.env['PREFIX'], 'bin')))
622 if not conf.env['IS_WINDOWS']:
623 conf.define('USE_POSIX_SHM', 1)
624 conf.define('JACKMP', 1)
625 if conf.env['BUILD_JACKDBUS'] == True:
626 conf.define('JACK_DBUS', 1)
627 if conf.env['BUILD_WITH_PROFILE'] == True:
628 conf.define('JACK_MONITOR', 1)
629 conf.write_config_header('config.h', remove=False)
631 svnrev = None
632 if os.access('svnversion.h', os.R_OK):
633 data = file('svnversion.h').read()
634 m = re.match(r'^#define SVN_VERSION "([^"]*)"$', data)
635 if m != None:
636 svnrev = m.group(1)
638 if Options.options.mixed == True:
639 conf.setenv(lib32, env=conf.env.derive())
640 conf.env.append_unique('CXXFLAGS', '-m32')
641 conf.env.append_unique('CFLAGS', '-m32')
642 conf.env.append_unique('LINKFLAGS', '-m32')
643 if Options.options.libdir32:
644 conf.env['LIBDIR'] = Options.options.libdir32
645 else:
646 conf.env['LIBDIR'] = conf.env['PREFIX'] + '/lib32'
647 conf.write_config_header('config.h')
649 print()
650 display_msg("==================")
651 version_msg = "JACK " + VERSION
652 if svnrev:
653 version_msg += " exported from r" + svnrev
654 else:
655 version_msg += " svn revision will checked and eventually updated during build"
656 print(version_msg)
658 print("Build with a maximum of %d JACK clients" % Options.options.clients)
659 print("Build with a maximum of %d ports per application" % Options.options.application_ports)
661 display_msg("Install prefix", conf.env['PREFIX'], 'CYAN')
662 display_msg("Library directory", conf.all_envs[""]['LIBDIR'], 'CYAN')
663 if conf.env['BUILD_WITH_32_64'] == True:
664 display_msg("32-bit library directory", conf.all_envs[lib32]['LIBDIR'], 'CYAN')
665 display_msg("Drivers directory", conf.env['ADDON_DIR'], 'CYAN')
666 display_feature('Build debuggable binaries', conf.env['BUILD_DEBUG'])
667 display_msg('C compiler flags', repr(conf.all_envs[""]['CFLAGS']))
668 display_msg('C++ compiler flags', repr(conf.all_envs[""]['CXXFLAGS']))
669 display_msg('Linker flags', repr(conf.all_envs[""]['LINKFLAGS']))
670 if conf.env['BUILD_WITH_32_64'] == True:
671 display_msg('32-bit C compiler flags', repr(conf.all_envs[lib32]['CFLAGS']))
672 display_msg('32-bit C++ compiler flags', repr(conf.all_envs[lib32]['CXXFLAGS']))
673 display_msg('32-bit linker flags', repr(conf.all_envs[lib32]['LINKFLAGS']))
674 display_feature('Build with engine profiling', conf.env['BUILD_WITH_PROFILE'])
675 display_feature('Build with 32/64 bits mixed mode', conf.env['BUILD_WITH_32_64'])
677 display_feature('Build standard JACK (jackd)', conf.env['BUILD_JACKD'])
678 display_feature('Build D-Bus JACK (jackdbus)', conf.env['BUILD_JACKDBUS'])
679 display_msg('Autostart method', conf.env['AUTOSTART_METHOD'])
681 if conf.env['BUILD_JACKDBUS'] and conf.env['BUILD_JACKD']:
682 print(Logs.colors.RED + 'WARNING !! mixing both jackd and jackdbus may cause issues:' + Logs.colors.NORMAL)
683 print(Logs.colors.RED + 'WARNING !! jackdbus does not use .jackdrc nor qjackctl settings' + Logs.colors.NORMAL)
685 # display configuration result messages for auto options
686 display_auto_options_messages()
688 if conf.env['BUILD_JACKDBUS'] == True:
689 display_msg('D-Bus service install directory', conf.env['DBUS_SERVICES_DIR'], 'CYAN')
690 #display_msg('Settings persistence', xxx)
692 if conf.env['DBUS_SERVICES_DIR'] != conf.env['DBUS_SERVICES_DIR_REAL']:
693 print()
694 print(Logs.colors.RED + "WARNING: D-Bus session services directory as reported by pkg-config is")
695 print(Logs.colors.RED + "WARNING:", end=' ')
696 print(Logs.colors.CYAN + conf.env['DBUS_SERVICES_DIR_REAL'])
697 print(Logs.colors.RED + 'WARNING: but service file will be installed in')
698 print(Logs.colors.RED + "WARNING:", end=' ')
699 print(Logs.colors.CYAN + conf.env['DBUS_SERVICES_DIR'])
700 print(Logs.colors.RED + 'WARNING: You may need to adjust your D-Bus configuration after installing jackdbus')
701 print('WARNING: You can override dbus service install directory')
702 print('WARNING: with --enable-pkg-config-dbus-service-dir option to this script')
703 print(Logs.colors.NORMAL, end=' ')
704 print()
706 def init(ctx):
707 for y in (BuildContext, CleanContext, InstallContext, UninstallContext):
708 name = y.__name__.replace('Context','').lower()
709 class tmp(y):
710 cmd = name + '_' + lib32
711 variant = lib32
713 def build(bld):
714 if not bld.variant:
715 out2 = out
716 else:
717 out2 = out + "/" + bld.variant
718 print("make[1]: Entering directory `" + os.getcwd() + "/" + out2 + "'")
720 if not bld.variant:
721 if not os.access('svnversion.h', os.R_OK):
722 create_svnversion_task(bld)
723 if bld.env['BUILD_WITH_32_64'] == True:
724 waflib.Options.commands.append(bld.cmd + '_' + lib32)
726 # process subfolders from here
727 bld.add_subdirs('common')
729 if bld.variant:
730 # only the wscript in common/ knows how to handle variants
731 return
733 if bld.env['IS_LINUX']:
734 bld.add_subdirs('linux')
735 bld.add_subdirs('example-clients')
736 bld.add_subdirs('tests')
737 bld.add_subdirs('man')
738 if bld.env['BUILD_JACKDBUS'] == True:
739 bld.add_subdirs('dbus')
741 if bld.env['IS_MACOSX']:
742 bld.add_subdirs('macosx')
743 bld.add_subdirs('example-clients')
744 bld.add_subdirs('tests')
745 if bld.env['BUILD_JACKDBUS'] == True:
746 bld.add_subdirs('dbus')
748 if bld.env['IS_SUN']:
749 bld.add_subdirs('solaris')
750 bld.add_subdirs('example-clients')
751 bld.add_subdirs('tests')
752 if bld.env['BUILD_JACKDBUS'] == True:
753 bld.add_subdirs('dbus')
755 if bld.env['IS_WINDOWS']:
756 bld.add_subdirs('windows')
757 bld.add_subdirs('example-clients')
758 #bld.add_subdirs('tests')
760 if bld.env['BUILD_DOXYGEN_DOCS'] == True:
761 html_build_dir = bld.path.find_or_declare('html').abspath()
763 bld(
764 features = 'subst',
765 source = 'doxyfile.in',
766 target = 'doxyfile',
767 HTML_BUILD_DIR = html_build_dir,
768 SRCDIR = bld.srcnode.abspath(),
769 VERSION = VERSION
772 # There are two reasons for logging to doxygen.log and using it as
773 # target in the build rule (rather than html_build_dir):
774 # (1) reduce the noise when running the build
775 # (2) waf has a regular file to check for a timestamp. If the directory
776 # is used instead waf will rebuild the doxygen target (even upon
777 # install).
778 def doxygen(task):
779 doxyfile = task.inputs[0].abspath()
780 logfile = task.outputs[0].abspath()
781 cmd = '%s %s &> %s' % (task.env.DOXYGEN, doxyfile, logfile)
782 return task.exec_command(cmd)
784 bld(
785 rule = doxygen,
786 source = 'doxyfile',
787 target = 'doxygen.log'
790 # Determine where to install HTML documentation. Since share_dir is the
791 # highest directory the uninstall routine should remove, there is no
792 # better candidate for share_dir, but the requested HTML directory if
793 # --htmldir is given.
794 if bld.env['HTMLDIR']:
795 html_install_dir = bld.options.destdir + bld.env['HTMLDIR']
796 share_dir = html_install_dir
797 else:
798 share_dir = bld.options.destdir + bld.env['PREFIX'] + '/share/jack-audio-connection-kit'
799 html_install_dir = share_dir + '/reference/html/'
801 if bld.cmd == 'install':
802 if os.path.isdir(html_install_dir):
803 Logs.pprint('CYAN', "Removing old doxygen documentation installation...")
804 shutil.rmtree(html_install_dir)
805 Logs.pprint('CYAN', "Removing old doxygen documentation installation done.")
806 Logs.pprint('CYAN', "Installing doxygen documentation...")
807 shutil.copytree(html_build_dir, html_install_dir)
808 Logs.pprint('CYAN', "Installing doxygen documentation done.")
809 elif bld.cmd =='uninstall':
810 Logs.pprint('CYAN', "Uninstalling doxygen documentation...")
811 if os.path.isdir(share_dir):
812 shutil.rmtree(share_dir)
813 Logs.pprint('CYAN', "Uninstalling doxygen documentation done.")
814 elif bld.cmd =='clean':
815 if os.access(html_build_dir, os.R_OK):
816 Logs.pprint('CYAN', "Removing doxygen generated documentation...")
817 shutil.rmtree(html_build_dir)
818 Logs.pprint('CYAN', "Removing doxygen generated documentation done.")
820 def dist_hook():
821 os.remove('svnversion_regenerate.sh')
822 os.system('../svnversion_regenerate.sh svnversion.h')