Skip to content
Snippets Groups Projects
moz.configure 17.4 KiB
Newer Older
  • Learn to ignore specific revisions
  • # -*- Mode: python; indent-tabs-mode: nil; tab-width: 40 -*-
    
    # vim: set filetype=python:
    # This Source Code Form is subject to the terms of the Mozilla Public
    # License, v. 2.0. If a copy of the MPL was not distributed with this
    # file, You can obtain one at http://mozilla.org/MPL/2.0/.
    
    include('build/moz.configure/init.configure')
    
    
    # Note:
    # - Gecko-specific options and rules should go in toolkit/moz.configure.
    # - Firefox-specific options and rules should go in browser/moz.configure.
    # - Fennec-specific options and rules should go in
    #   mobile/android/moz.configure.
    # - Spidermonkey-specific options and rules should go in js/moz.configure.
    # - etc.
    
    # Multiprocess Firefox Testing UI - Nightly and Aurora
    # To be removed in Bug 1003313
    @depends(milestone)
    def e10s_testing_only(milestone):
    
            return True
    
    set_config('E10S_TESTING_ONLY', e10s_testing_only)
    
    set_define('E10S_TESTING_ONLY', e10s_testing_only)
    
    option('--enable-artifact-builds', env='MOZ_ARTIFACT_BUILDS',
           help='Download and use prebuilt binary artifacts.')
    
    @depends('--enable-artifact-builds')
    def artifact_builds(value):
        if value:
    
            return True
    
    set_config('MOZ_ARTIFACT_BUILDS', artifact_builds)
    
    imply_option('--enable-artifact-build-symbols',
                 depends(artifact_builds)(lambda v: False if v is None else None),
                 reason='--disable-artifact-builds')
    
    option('--enable-artifact-build-symbols',
           help='Download symbols when artifact builds are enabled.')
    
    set_config('MOZ_ARTIFACT_BUILD_SYMBOLS',
               depends_if('--enable-artifact-build-symbols')(lambda _: True))
    
    
    @depends('--enable-artifact-builds')
    def imply_disable_compile_environment(value):
        if value:
            return False
    
    imply_option('--enable-compile-environment', imply_disable_compile_environment)
    
    
    option('--disable-compile-environment',
           help='Disable compiler/library checks')
    
    @depends('--disable-compile-environment')
    
    def compile_environment(compile_env):
        if compile_env:
    
            return True
    
    set_config('COMPILE_ENVIRONMENT', compile_environment)
    
    add_old_configure_assignment('COMPILE_ENVIRONMENT', compile_environment)
    
    js_option('--disable-tests',
              help='Do not build test libraries & programs')
    
    @depends('--disable-tests')
    def enable_tests(value):
        if value:
            return True
    
    set_config('ENABLE_TESTS', enable_tests)
    set_define('ENABLE_TESTS', enable_tests)
    
    
    js_option(env='MOZILLA_OFFICIAL',
              help='Build an official release')
    
    @depends('MOZILLA_OFFICIAL')
    def mozilla_official(official):
        if official:
            return True
    
    set_config('MOZILLA_OFFICIAL', mozilla_official)
    set_define('MOZILLA_OFFICIAL', mozilla_official)
    add_old_configure_assignment('MOZILLA_OFFICIAL', mozilla_official)
    
    
    @depends(enable_tests)
    def gtest_has_rtti(value):
        if value:
            return '0'
    
    set_define('GTEST_HAS_RTTI', gtest_has_rtti)
    
    @depends(target, enable_tests)
    def linux_gtest_defines(target, enable_tests):
        if enable_tests and target.os == 'Android':
            return namespace(os_linux_android=True,
                             use_own_tr1_tuple=True,
                             has_clone='0')
    
    set_define('GTEST_OS_LINUX_ANDROID',
    
    set_define('GTEST_USE_OWN_TR1_TUPLE',
    
    js_option('--enable-debug',
              nargs='?',
              help='Enable building with developer debug info '
                   '(using the given compiler flags).')
    
    
    add_old_configure_assignment('MOZ_DEBUG',
                                 depends('--enable-debug')(lambda v: bool(v)))
    
    js_option('--enable-rust-debug',
              help='Build Rust code with debug assertions turned on.')
    
    
    @depends('--enable-rust-debug', '--enable-debug')
    def debug_rust(value, debug):
        if value.origin == 'default':
            return bool(debug) or None
        elif bool(value):
    
            return True
    
    set_config('MOZ_DEBUG_RUST', debug_rust)
    set_define('MOZ_DEBUG_RUST', debug_rust)
    
    
    include('build/moz.configure/pkg.configure')
    # Make this assignment here rather than in pkg.configure to avoid
    # requiring this file in unit tests.
    add_old_configure_assignment('PKG_CONFIG', pkg_config)
    
    
    include('build/moz.configure/toolchain.configure',
            when='--enable-compile-environment')
    include('build/moz.configure/memory.configure',
            when='--enable-compile-environment')
    include('build/moz.configure/headers.configure',
            when='--enable-compile-environment')
    include('build/moz.configure/warnings.configure',
            when='--enable-compile-environment')
    
    
    @depends(target, host)
    def is_openbsd(target, host):
        return target.kernel == 'OpenBSD' or host.kernel == 'OpenBSD'
    
    option(env='SO_VERSION', nargs=1, default='1.0', when=is_openbsd,
           help='Shared library version for OpenBSD systems')
    
    @depends('SO_VERSION', when=is_openbsd)
    def so_version(value):
        return value
    
    
    @template
    def library_name_info_template(host_or_target):
        assert host_or_target in (host, target)
        compiler = {
            host: host_c_compiler,
            target: c_compiler,
        }[host_or_target]
    
        @depends(host_or_target, compiler, so_version)
        def library_name_info_impl(host_or_target, compiler, so_version):
            if host_or_target.kernel == 'WINNT':
                # There aren't artifacts for mingw builds, so it's OK that the
                # results are inaccurate in that case.
                if compiler and compiler.type not in ('msvc', 'clang-cl'):
                    return namespace(
                        dll=namespace(prefix='', suffix='.dll'),
                        lib=namespace(prefix='lib', suffix='a'),
                        import_lib=namespace(prefix='lib', suffix='a'),
                        rust_lib=namespace(prefix='', suffix='lib'),
                        obj=namespace(prefix='', suffix='o'),
                    )
    
    
                return namespace(
                    dll=namespace(prefix='', suffix='.dll'),
    
                    lib=namespace(prefix='', suffix='lib'),
                    import_lib=namespace(prefix='', suffix='lib'),
    
                    rust_lib=namespace(prefix='', suffix='lib'),
    
            elif host_or_target.kernel == 'Darwin':
                return namespace(
                    dll=namespace(prefix='lib', suffix='.dylib'),
                    lib=namespace(prefix='lib', suffix='a'),
                    import_lib=namespace(prefix=None, suffix=''),
                    rust_lib=namespace(prefix='lib', suffix='a'),
                    obj=namespace(prefix='', suffix='o'),
                )
            elif so_version:
                so = '.so.%s' % so_version
            else:
                so = '.so'
    
                lib=namespace(prefix='lib', suffix='a'),
                import_lib=namespace(prefix=None, suffix=''),
                rust_lib=namespace(prefix='lib', suffix='a'),
                obj=namespace(prefix='', suffix='o'),
            )
    
    
        return library_name_info_impl
    
    host_library_name_info = library_name_info_template(host)
    library_name_info = library_name_info_template(target)
    
    set_config('DLL_PREFIX', library_name_info.dll.prefix)
    set_config('DLL_SUFFIX', library_name_info.dll.suffix)
    set_config('LIB_PREFIX', library_name_info.lib.prefix)
    set_config('LIB_SUFFIX', library_name_info.lib.suffix)
    set_config('RUST_LIB_PREFIX', library_name_info.rust_lib.prefix)
    set_config('RUST_LIB_SUFFIX', library_name_info.rust_lib.suffix)
    set_config('OBJ_SUFFIX', library_name_info.obj.suffix)
    
    # Lots of compilation tests depend on this variable being present.
    
    add_old_configure_assignment('OBJ_SUFFIX', library_name_info.obj.suffix)
    set_config('IMPORT_LIB_SUFFIX', library_name_info.import_lib.suffix)
    set_define('MOZ_DLL_SUFFIX', depends(library_name_info.dll.suffix)(lambda s: '"%s"' % s))
    
    @imports(_from='mozbuild.backend', _import='backends')
    
    @deprecated_option('--enable-build-backend', nargs='+',
                       choices=build_backends_choices)
    def build_backend(backends):
        if backends:
            return tuple('+%s' % b for b in backends)
    
    imply_option('--build-backends', build_backend)
    
    
    @depends('--enable-artifact-builds', '--disable-compile-environment', '--help')
    @imports('sys')
    def build_backend_defaults(artifact_builds, compile_environment, _):
    
        if artifact_builds:
            all_backends = ['FasterMake+RecursiveMake']
        else:
            all_backends = ['RecursiveMake', 'FasterMake']
    
        # Normally, we'd use target.os == 'WINNT', but a dependency on target
        # would require target to depend on --help, as well as host and shell,
        # and this is not a can of worms we can open at the moment.
        if sys.platform == 'win32' and compile_environment:
    
        return tuple(all_backends)
    
    option('--build-backends', nargs='+', default=build_backend_defaults,
           choices=build_backends_choices, help='Build backends to generate')
    
    @depends('--build-backends')
    def build_backends(backends):
        return backends
    
    set_config('BUILD_BACKENDS', build_backends)
    
    option('--disable-gtest-in-build',
           help='Force disable building the gtest libxul during the build.',
           when='--enable-compile-environment')
    
    
    # Determine whether to build the gtest xul. This happens in automation
    # on Desktop platforms with the exception of Windows PGO, where linking
    # xul-gtest.dll takes too long.
    
    @depends('MOZ_PGO', build_project, target, 'MOZ_AUTOMATION', '--disable-gtest-in-build',
    
             enable_tests, when='--enable-compile-environment')
    def build_gtest(pgo, build_project, target, automation, enabled, enable_tests):
        if not enable_tests or not enabled:
    
        if (automation and build_project == 'browser' and
            not (pgo and target.os == 'WINNT')):
            return True
    
    set_config('LINK_GTEST_DURING_COMPILE', build_gtest)
    
    # Awk detection
    # ==============================================================
    awk = check_prog('AWK', ('gawk', 'mawk', 'nawk', 'awk'))
    
    # Until the AWK variable is not necessary in old-configure
    @depends(awk)
    def awk_for_old_configure(value):
    
        return value
    
    add_old_configure_assignment('AWK', awk_for_old_configure)
    
    # Perl detection
    # ==============================================================
    perl = check_prog('PERL', ('perl5', 'perl'))
    
    # Until the PERL variable is not necessary in old-configure
    @depends(perl)
    def perl_for_old_configure(value):
    
        return value
    
    add_old_configure_assignment('PERL', perl_for_old_configure)
    
    
    @template
    def perl_version_check(min_version):
        @depends(perl)
        @checking('for minimum required perl version >= %s' % min_version)
        def get_perl_version(perl):
    
            return Version(check_cmd_output(
                perl, '-e', 'print $]',
                onerror=lambda: die('Failed to get perl version.')
            ))
    
    
        @depends(get_perl_version)
        def check_perl_version(version):
            if version < min_version:
    
                die('Perl %s or higher is required.', min_version)
    
    
        @depends(perl)
        @checking('for full perl installation')
    
        def has_full_perl_installation(perl):
            ret = subprocess.call(
                [perl, '-e', 'use Config; exit(!-d $Config{archlib})'])
            return ret == 0
    
        @depends(has_full_perl_installation)
        def require_full_perl_installation(has_full_perl_installation):
            if not has_full_perl_installation:
    
                die('Cannot find Config.pm or $Config{archlib}. '
                    'A full perl installation is required.')
    
    # GNU make detection
    # ==============================================================
    option(env='MAKE', nargs=1, help='Path to GNU make')
    
    @depends('MAKE', host)
    def possible_makes(make, host):
        candidates = []
        if host.kernel == 'WINNT':
            candidates.append('mingw32-make')
        if make:
            candidates.append(make[0])
        if host.kernel == 'WINNT':
            candidates.extend(('make', 'gmake'))
        else:
            candidates.extend(('gmake', 'make'))
        return candidates
    
    check_prog('GMAKE', possible_makes)
    
    
    # tup detection
    # ==============================================================
    @depends(build_backends)
    def tup_progs(build_backends):
        for backend in build_backends:
            if 'Tup' in backend:
                return ['tup']
        return None
    
    tup = check_prog('TUP', tup_progs)
    
    
    # watchman detection
    # ==============================================================
    
    
    option(env='WATCHMAN', nargs=1, help='Path to the watchman program')
    
    @checking('for watchman', callback=lambda w: w.path if w else 'not found')
    def watchman(prog):
    
        if not prog:
            prog = find_program('watchman')
    
        if not prog:
            return
    
    
        # `watchman version` will talk to the Watchman daemon service.
        # This can hang due to permissions problems. e.g.
        # https://github.com/facebook/watchman/issues/376. So use
        # `watchman --version` to prevent a class of failures.
        out = check_cmd_output(prog, '--version', onerror=lambda: None)
    
        return namespace(path=prog, version=Version(out.strip()))
    
    @checking('for watchman version')
    def watchman_version(w):
        return w.version
    
    
    @depends_all(hg_version, hg_config, watchman)
    @checking('for watchman Mercurial integration')
    @imports('os')
    def watchman_hg(hg_version, hg_config, watchman):
        if hg_version < Version('3.8'):
            return 'no (Mercurial 3.8+ required)'
    
        ext_enabled = False
        mode_disabled = False
    
        for k in ('extensions.fsmonitor', 'extensions.hgext.fsmonitor'):
            if k in hg_config and hg_config[k] != '!':
                ext_enabled = True
    
        mode_disabled = hg_config.get('fsmonitor.mode') == 'off'
    
        if not ext_enabled:
            return 'no (fsmonitor extension not enabled)'
        if mode_disabled:
            return 'no (fsmonitor.mode=off disables fsmonitor)'
    
        return True
    
    
    # Miscellaneous programs
    # ==============================================================
    check_prog('DOXYGEN', ('doxygen',), allow_missing=True)
    check_prog('XARGS', ('xargs',))
    
    
            return namespace(
                DSYMUTIL=('dsymutil', 'llvm-dsymutil'),
    
                MKFSHFS=('newfs_hfs', 'mkfs.hfsplus'),
                HFS_TOOL=('hfsplus',)
    
        if target.os == 'GNU' and target.kernel == 'Linux':
    
    check_prog('DSYMUTIL', extra_programs.DSYMUTIL,
    
    check_prog('MKFSHFS', extra_programs.MKFSHFS,
    
    check_prog('HFS_TOOL', extra_programs.HFS_TOOL,
    
    check_prog('RPMBUILD', extra_programs.RPMBUILD,
    
    option('--enable-system-hunspell',
           help="Use system hunspell (located with pkgconfig)")
    
    @depends('--enable-system-hunspell', compile_environment)
    def check_for_hunspell(value, compile_env):
        return value and compile_env
    
    system_hunspell = pkg_check_modules('MOZ_HUNSPELL', 'hunspell',
    
    set_config('MOZ_SYSTEM_HUNSPELL', depends_if(system_hunspell)(lambda _: True))
    
        if target.kernel != 'WINNT':
            return
    
        candidates = [
    
            'makensis-3.01',
            'makensis-3.0b3',
            'makensis-3.0b1',
    
            'makensis',
        ]
    
        # Look for nsis installed by msys environment. But only the 32-bit version.
        # We use an absolute path and insert as the first entry so it is preferred
        # over a 64-bit exe that may be in PATH.
        if 'MSYSTEM_PREFIX' in os.environ:
            prefix = os.path.dirname(os.environ['MSYSTEM_PREFIX'])
            candidates.insert(0, os.path.join(prefix, 'mingw32', 'bin', 'makensis.exe'))
    
        return tuple(candidates)
    
    nsis = check_prog('MAKENSISU', makensis_progs, allow_missing=True)
    
    
    # Make sure the version of makensis is up to date.
    @depends_if(nsis)
    @checking('for NSIS version')
    @imports('re')
    def nsis_version(nsis):
        nsis_min_version = '3.0b1'
        out = check_cmd_output(nsis, '-version',
                               onerror=lambda: die('Failed to get nsis version.'))
        m = re.search(r'(?<=v)[0-9]+\.[0-9]+((a|b|rc)[0-9]+)?', out)
    
        if not m:
            raise FatalCheckError('Unknown version of makensis')
        ver = Version(m.group(0))
    
    
        # Versions comparisons don't quite work well with beta versions, so ensure
        # it works for the non-beta version.
        if ver < nsis_min_version and (ver >= '3.0a' or ver < '3'):
    
            raise FatalCheckError('To build the installer you must have NSIS'
                                  ' version %s or greater in your path'
                                  % nsis_min_version)
    
        return ver
    
    
    # And that makensis is 32-bit (but only on Windows).
    @depends_if(nsis, when=depends(host)(lambda h: h.kernel == 'WINNT'))
    
    @checking('for 32-bit NSIS')
    def nsis_binary_type(nsis):
        bin_type = windows_binary_type(nsis)
        if bin_type != 'win32':
            raise FatalCheckError('%s is not a 32-bit Windows application' % nsis)
    
        return 'yes'
    
    
    # And any flags we have to give to makensis
    @depends(host)
    def nsis_flags(host):
        if host.kernel != 'WINNT':
            return '-nocd'
        return ''
    
    set_config('MAKENSISU_FLAGS', nsis_flags)
    
    # Fallthrough to autoconf-based configure
    include('build/moz.configure/old.configure')
    
    
    @imports('__sandbox__')
    def all_paths():
        return __sandbox__._all_paths
    
    set_config('ALL_CONFIGURE_PATHS', all_paths())
    # Please do not add anything after setting ALL_CONFIGURE_PATHS.