#!/bin/sh## configure [ <options> ]# usage## Prints usage.#usage(){cat << EOFUsage: $0 <options>options:--help Prints out this help.--update Re-runs last configure invocation [must be givenas first option!]--bootstrap <haikuporter> <HaikuPorts cross repo> <HaikuPorts repo>Prepare for a bootstrap build. No pre-builtpackages will be used, instead they will be builtfrom the sources (in several phases).<haikuporter> is the path to the haikuporter toolsuitable for the host platform.<HaikuPorts cross repo> is the path to a checkedout HaikuPorts cross-compilation repository.<HaikuPorts repo> is the path to a checked outHaikuPorts repository.--build-cross-tools <arch>Assume cross compilation.Toolchain will be compiled and placed in theoutput directory under "cross-tools". TheHAIKU_* tools variables will be set accordingly.<arch> specifies the target architecture, either"x86_gcc2", "x86", "x86_64", "ppc", "m68k","arm", "arm64", "riscv64", "sparc"This option and --cross-tools-prefix can bespecified multiple times. The first cross toolsspecify the primary tools, the subsequent ones thesecondary tools (for "hybrid" images).--cross-tools-prefix <prefix>Assume cross compilation. <prefix> should be apath to the directory where the crosscompilation tools are located, plus the platformprefix, e.g. "/path/to/tools/i586-pc-haiku-".This overrides the HAIKU_* tool variables.--cross-tools-source <buildtools dir>Toolchain sources for cross compilation.<buildtools dir> defines the location of thebuildtools sources.--distro-compatibility <level>The distribution's level of compatibility withthe official Haiku distribution. The generatedfiles will contain the respective trademarksaccordingly.official -- the official Haiku distribution.compatible -- a Haiku Compatible (tm) distro.default -- any other distro (default value).--host-only Configure for building tools for the build hostonly. Haiku cannot be built when configured likethis.--include-sources Includes the source code of projects that requireeither an offer of source code or a copy of thepatched sources. This is preferable whendistributing on physical mediums.--include-3rdparty Include 3rdparty/ in the build system.-j<n> Only relevant for --build-cross-tools. Is passedon to the make building the build tools.--no-downloads Do not download anything. Useful when trying tobootstrap and build Haiku from source only.--sysroot The location of the cross-compiler sysroot,primarily for CI environments or cross-compilersused outside of the Haiku build system.--target-arch <arch> Haiku only: Specify the target architecture tobuild for. Must be one of the architectures of thehost system. The installed build tools for thatarchitecture will be used.This option can be specified multiple times. Thefirst occurrence specifies the primaryarchitecture of the Haiku to build, subsequentones the secondary architectures.--use-clang <arch> Build with host Clang instead of GCC crosscompiler, targeting <arch>--use-gcc-pipe Build with GCC option -pipe. Speeds up the buildprocess, but uses more memory.--use-gcc-graphite Build with GCC Graphite engine for loopoptimizations. (Only for GCC 4+.)--use-32bit Use -m32 flag on 64bit host gcc compiler.--no-full-xattr Do not use Linux/*BSD/Darwin's native extended fileattributes as Haiku attributes. If they are stillavailable, they will be used to store hashes forthe attribute emulation layer.--no-xattr Do not use Linux/*BSD/Darwin's native extended fileattributes for Haiku extended attributes at all,even if they are available.--with-gdb <gdb sources dir>specify the path to a GDB source dir, to buildGDB for each arch we build the cross-tools for.--use-stack-protector Build with stack protection enabled--efi-signing-key Private keyfile to sign any EFI bootloadersenvironment variables:CC The host compiler. Defaults to "gcc".HAIKU_AR_<arch> The static library archiver for <arch>.Defaults to "ar".HAIKU_CC_<arch> The compiler for <arch>. Defaults to "gcc".HAIKU_LD_<arch> The <arch> linker. Defaults to "ld".HAIKU_OBJCOPY_<arch> The <arch> objcopy to be used. Defaults to"objcopy".HAIKU_RANLIB_<arch> The static library indexer for <arch>. Defaultsto "ranlib".HAIKU_STRIP_<arch> The <arch> strip command. Defaults to "strip".HAIKU_NASM The nasm assembler (x86 and x86_64 only).HAIKU_CPPFLAGS_<arch> The preprocessor flags for target architecture<arch>. Defaults to "".HAIKU_CCFLAGS_<arch> The C flags for target architecture <arch>.Defaults to "".HAIKU_CXXFLAGS_<arch> The C++ flags for target architecture <arch>.Defaults to "".HAIKU_LINKFLAGS_<arch> The flags passed to the compiler when linking fortarget architecture <arch>. Defaults to "".HAIKU_LDFLAGS_<arch> The linker flags for target architecture <arch>.Defaults to "".HAIKU_ARFLAGS_<arch> The flags passed to HAIKU_AR for targetarchitecture <arch> for archiving. Defaults to"cru".HAIKU_UNARFLAGS_<arch> The flags passed to HAIKU_AR for targetarchitecture <arch> for unarchiving. Defaults to"x".Non-default output directories:By default all objects, build configuration, and other related files arestored in /path/to/haiku_source/generated. To store objects in a non-defaultlocation, run "../../relative/path/to/haiku_source/configure <options>" fromwithin your non-default location. "jam [ options ] targets" can then be rundirectly inside your non-default location. Another option is to invoke "jam[ options ] targets" from within haiku_source. This can be accomplished byeither "export HAIKU_OUTPUT_DIR=your non-default location" before invokingjam or by creating a symlink of haiku_source/generated pointing to yournon-default location and running jam.EOF}# assertparam## Checks whether at least one parameter is left.#assertparam(){if [ $2 -lt 2 ]; thenecho $0: \`$1\': Parameter expected.exit 1fi}# assertparams## Checks whether at least a certain number of parameters is left.#assertparams(){if [ $3 -le $2 ]; thenecho $0: \`$1\': Not enough parameters.exit 1fi}# absolute_path## returns the absolute path of a given path.#absolute_path(){if [ "x$1" != "x${1#/}" ]; thenecho "$1"elseecho "`pwd`/$1"fi}# check_dir_exists## check if a directory exists or not#check_dir_exists(){if [ -d "$1" ]; thenreturn 0elsereturn 1fi}# check_file_exists## check if a file exists or not#check_file_exists(){if [ -f "$1" ]; thenreturn 0elsereturn 1fi}# real_path## returns the realpath of a symbolic link.#real_path(){perl -MCwd=realpath -e'print realpath($ARGV[0]), "\n"' "$1"}# relative_to## returns $1 relative to $2#relative_to(){perl -e 'use File::Spec; print File::Spec->abs2rel(@ARGV) . "\n"' \"$1" "$2"}# valid_toolchain## check if a toolchain is valid#valid_toolchain(){TRIPLET="$1"BASE="$2"SOURCE="$3"if [ ! -d "$BASE" ]; thenreturn 1fiif [ -f "$BASE/bin/$TRIPLET-gcc" ]; then[ "$BASE/bin/$TRIPLET-gcc" -nt "$SOURCE/legacy/gcc/configure" ] && \[ "$BASE/bin/$TRIPLET-gcc" -nt "$SOURCE/gcc/gcc/configure" ]return $?fireturn 1}# is_legacy_gcc## Determines if the specified GCC version is a "legacy" (i.e. GCC < 4) one.#is_legacy_gcc(){if [ `echo $1 | cut -d'.' -f1` -lt 4 ]; thenecho 1elseecho 0fi}# standard_gcc_settings## Sets the variables for a GCC platform.#standard_gcc_settings(){local gcc="$1"if command -v greadlink > /dev/null 2>&1; thenreadlink="greadlink -e"elif command -v realpath > /dev/null 2>&1; thenreadlink=realpathelif readlink -e / > /dev/null 2>&1; thenreadlink="readlink -e"elsereadlink=real_pathfi# PLATFORM_LINKLIBSlocal gcclib=`$gcc -print-libgcc-file-name`local gccdir=`dirname ${gcclib}`local gccRawVersion=`$gcc -dumpversion`local gccMachine=`$gcc -dumpmachine`# determine architecture from machine triplecase $gccMachine inarm-*) targetCpu=arm;;aarch64-*) targetCpu=arm64;;i?86-*) targetCpu=x86;;m68k-*) targetCpu=m68k;;powerpc-*) targetCpu=ppc;;riscv64-*) targetCpu=riscv64;;sparc64-*) targetCpu=sparc;;x86_64-*) targetCpu=x86_64;;*)echo "Unsupported gcc target machine: $gccMachine" >&2exit 1;;esaclocal targetArch=$targetCpucase $gccRawVersion in2.9*)# check for correct (most up-to-date) legacy compiler and complain# if an older one is installedif [ $gccRawVersion != $haikuRequiredLegacyGCCVersion ]; thenecho "GCC version $haikuRequiredLegacyGCCVersion is required!";echo "Please download it from www.haiku-os.org...";exit 1;fitargetArch=x86_gcc2;;esaclocal bootLibgcclocal bootLibSupCxxlocal bootCxxHeaderslocal boot32Libgcclocal boot32LibSupCxxlocal boot32CxxHeaderscase $gccMachine inx86_64-*)# Boot loader is 32-bit, need the 32-bit libs and c++ configboot32Libgcc=`$gcc -m32 -print-file-name=libgcc.a`boot32LibSupCxx=`$gcc -m32 -print-file-name=libsupc++.a`bootLibgcc=`$gcc -print-file-name=libgcc.a`bootLibSupCxx=`$gcc -print-file-name=libsupc++.a`local headersBase=$gccdir/../../../..local headers=$headersBase/$gccMachine/include/c++/$gccRawVersionif [ ! -d $headers ]; thenheaders=$headersBase/include/c++/$gccRawVersionfiboot32CxxHeaders="$headers/$gccMachine/32"bootCxxHeaders="$headers/$gccMachine";;esac# determine whether graphite loop optimization should/can be usedlocal useGraphite=`get_variable HAIKU_USE_GCC_GRAPHITE_$targetCpu`if [ -z "$useGraphite" ]; thenuseGraphite=$useGccGraphiteDefaultfiif [ "$useGraphite" != 0 ]; thenUNUSED=`echo "int main() {}" | $gcc -xc -c -floop-block - 2>&1`if [ $? != 0 ]; thenecho "GCC Graphite loop optimizations cannot be used on $targetArch"useGraphite=0fifiset_variable HAIKU_CPU_$targetArch $targetCpuget_build_tool_path CC_$targetArch "$gcc"set_variable HAIKU_CC_IS_LEGACY_GCC_$targetArch \`is_legacy_gcc $gccRawVersion`set_variable HAIKU_CC_IS_CLANG_$targetArch $useClangset_variable HAIKU_GCC_MACHINE_$targetArch $gccMachineset_variable HAIKU_GCC_LIB_DIR_$targetArch $gccdirset_variable HAIKU_BOOT_CXX_HEADERS_DIR_$targetArch "$bootCxxHeaders"set_variable HAIKU_BOOT_LIBSUPCXX_$targetArch "$bootLibSupCxx"set_variable HAIKU_BOOT_LIBGCC_$targetArch $bootLibgccset_variable HAIKU_BOOT_32_CXX_HEADERS_DIR_$targetArch "$boot32CxxHeaders"set_variable HAIKU_BOOT_32_LIBSUPCXX_$targetArch "$boot32LibSupCxx"set_variable HAIKU_BOOT_32_LIBGCC_$targetArch $boot32Libgccset_variable HAIKU_USE_GCC_GRAPHITE_$targetArch $useGraphitestandard_gcc_settings_targetArch=$targetArch}# set_variable## Set the value of a variable.#set_variable(){eval "$1=\"$2\""}# get_variable## Echo the value of a variable.#get_variable(){eval "echo \${$1}"}# set_default_value## Set the value for a variable, if no value is set yet.#set_default_value(){eval "$1=\${$1-$2}"}# get_build_tool_path## Gets a usable absolute path of a build tool.#get_build_tool_path(){local var="HAIKU_$1"local varval="`get_variable $var`"local cmd="$2"if [ ! -z "$varval" ]; then# this variable is already set (probably by user) so grab its contentscmd=$varvalfilocal path=${cmd%% *}if [ -f "$path" ]; then# get absolute path from relative pathlocal oldPwd="`pwd`"cd "`dirname "$path"`"path="`pwd`/`basename "$path"`"cd $oldPwdelsecommand -v "$path" > /dev/null 2>&1 || {echo "Build tool \"$path\" not found (maybe specify it in $var?)" >&2exit 1}fiif test "${cmd#* }" != "$cmd"; then# $cmd contains arguments, so preserve them (and only them)cmd=${cmd#* }else# $cmd does not contain arguments, so unset itcmd=fieval "$var=\"$path $cmd\""}# check_native_xattrs## Checks the host platform's support for extended attributes.# 0: no support, 1: only enough for xattr-ref, 2: full support#check_native_xattrs(){local xattr_set=local xattr_set_args=local xattr_get=local xattr_get_args=case $HOST_PLATFORM inhaiku_host)xattr_set="addattr"; xattr_set_args="\$NAME \"\$VALUE\""xattr_get="catattr"; xattr_get_args="\$NAME";;darwin)xattr_set="xattr"; xattr_set_args="-w \$NAME \"\$VALUE\""xattr_get="xattr"; xattr_get_args="-p \$NAME";;freebsd)xattr_set="setextattr"; xattr_set_args="user \$NAME \"\$VALUE\""xattr_get="getextattr"; xattr_get_args="user \$NAME";;linux)xattr_set="setfattr"; xattr_set_args="-n user.\$NAME -v \"\$VALUE\""xattr_get="getfattr"; xattr_get_args="-n user.\$NAME";;*)return 0;;esacif ! type $xattr_set >/dev/null 2>&1; thenecho "$0: could not find $xattr_set, assuming host has no extended attributes"return 0elif ! type $xattr_get >/dev/null 2>&1; thenecho "$0: could not find $xattr_get, assuming host has no extended attributes"return 0fimkdir -p "$outputDir"echo "xattr test file" >"$outputDir/xattrtest"local i=0# on round 0, we test if we can set 3 attrs of 1K each (enough for xattr-ref)# on round 1, we test if we can set 3 attrs of 45K each (enough for full xattr)while [ $i -lt 2 ]; dolocal j=0while [ $j -lt 3 ]; doNAME=attr$jVALUE=`printf '%*s' $((1024 + $i * 45056)) "" | tr ' ' x`if [ `echo -n $VALUE | wc -c` -lt $((1024 + $i * 45056)) ]; thenecho "$0: warning: could not generate test data for extended attributes"rm "$outputDir/xattrtest"return $ielif ! $xattr_set `eval echo \"$xattr_set_args\"` \"$outputDir/xattrtest" >/dev/null 2>&1 ; thenrm "$outputDir/xattrtest"return $ifij=$((j+1))donei=$((i+1))donerm "$outputDir/xattrtest"return 2}is_in_list(){local elementfor element in $2; doif [ "$1" = "$element" ]; thenreturn 0fidonereturn 1}# check for --help or -h and show usage immediatelyif [ "$1" = "--help" ] || [ "$1" = "-h" ]; thenusage; exit 0;fi# get cwd and the source directorycurrentDir=`pwd`cd `dirname "$0"`sourceDir=`pwd`cd "$currentDir"# determine output directoryif [ "$currentDir" = "$sourceDir" ]; thenoutputDir=$currentDir/generatedelseoutputDir=$currentDirfibuildOutputDir="$outputDir/build"HAIKU_BUILD_ATTRIBUTES_DIR="$outputDir/attributes"buildConfigFile="$buildOutputDir/BuildConfig"# check for update requestif [ "$1" = "--update" ]; thenif ! [ -e "$buildConfigFile" ]; thenecho $0 --update: \'$buildConfigFile\' not found - updating not possible.exit 1fi# get last configure invocation and flags from BuildConfig and call ourselves with itlastPwd=`grep "#d " "$buildConfigFile" | cut -c 4-`lastConfig=`grep "#c " "$buildConfigFile" | cut -c 4-`lastEnv=`grep "#e " "$buildConfigFile" | cut -c 4-`lastArgs=`grep "#a " "$buildConfigFile" | cut -c 4-`if [ -z "$lastConfig" ]; thenecho "$0 --update: The previous configure invocation was not properly" \"encoded into '$buildConfigFile' - updating not possible."exit 1ficd "$lastPwd"if [ -n "$lastEnv" ]; thenexport $lastEnvfi$lastConfig $lastArgsexit $?fi# backup the passed argumentsconfigureArgs="$@"configurePath=$0configureDir=`dirname $configurePath`# backup relevant environsconfigureEnvirons=for var in `env`; docase "$var" inCC\=*|HAIKU*\=*|JAMSHELL\=*|HOST_PYTHON\=*)configureEnvirons="$configureEnvirons $var";;esacdone# ensure umask is not too restrictiveif [ `umask` -gt 22 ]; thenecho Your umask is too restrictive "(should be <= 0022;" is actually `umask`")"echoecho Additionally, if the source tree was cloned with a too-restrictive umask,echo you will need to run \"git checkout\" again to fix this.exit 1fi# internal default parameter values#platform=`uname`platformMachine=`uname -m`targetArchs=buildCrossTools=buildCrossToolsScript="$sourceDir/build/scripts/build_cross_tools"buildCrossToolsJobs=useClang=0useGccGraphiteDefault=0unknownArchIndex=1haikuTargetArchs=gdbSources=if [ -z "$CC" ]; thenCC=gccfiif [ $(is_legacy_gcc $($CC -dumpversion)) -ne 0 ]; thenif [ $platform == "Haiku" ] && [ $platformMachine == "BePC" ]; thenCC=gcc-x86elseecho The host tools cannot be built with a legacy version of GCC.echo Please specify a more modern compiler in the "CC" environ.exit 1fifi# detect the build platformcase "${platform}" inDarwin) HOST_PLATFORM=darwin ;;FreeBSD) HOST_PLATFORM=freebsdif [ "$HAIKU_HOST_USE_32BIT" = 1 ] ; thenecho Unsupported platform: FreeBSD ${platformMachine}exit 1fi ;;Haiku) HOST_PLATFORM=haiku_host ;;Linux) HOST_PLATFORM=linux ;;OpenBSD) HOST_PLATFORM=openbsd ;;*) echo Unsupported platform: ${platform}exit 1 ;;esaccase $HOST_PLATFORM indarwin|freebsd|openbsd) statCmd='stat -f' ;;*) statCmd='stat -c' ;;esac# ensure git checkout was not done with a restrictive umaskif [ `$statCmd '%a' "$sourceDir/data/system/boot/SetupEnvironment"` -lt 644 ]; thenecho "The source tree was cloned with a umask > 0022. It seems you"echo have already corrected your umask, but not re-checked-out theecho source tree. Try running:echo " git checkout --force"echo to fix this problem.exit 1fi# exported (BuildSetup) default parameter values#GIT_DIR=`git -C "$configureDir" rev-parse --git-dir | sed 's/^gitdir: //'`HOST_GCC_MACHINE=`$CC -dumpmachine`HAIKU_INCLUDE_SOURCES=0HAIKU_INCLUDE_3RDPARTY=0HAIKU_DISTRO_COMPATIBILITY=defaultTARGET_PLATFORM=haikuHAIKU_USE_GCC_PIPE=0HAIKU_HOST_USE_32BIT=0HAIKU_HOST_USE_XATTR=HAIKU_HOST_USE_XATTR_REF=HAIKU_HOST_BUILD_ONLY=0HOST_EXTENDED_REGEX_SED="sed -r"HOST_GCC_LD=`$CC -print-prog-name=ld`HOST_GCC_OBJCOPY=`$CC -print-prog-name=objcopy`HOST_SHA256=HOST_HAIKU_PORTER=HAIKU_PORTS=HAIKU_PORTS_CROSS=HAIKU_IS_BOOTSTRAP=0HAIKU_NO_DOWNLOADS=0HAIKU_PACKAGING_ARCHS=set_default_value HAIKU_NASM nasmif sha256sum < /dev/null > /dev/null 2>&1; thenHOST_SHA256=sha256sumelif sha256 < /dev/null > /dev/null 2>&1; thenHOST_SHA256="sha256 -q"elif shasum < /dev/null > /dev/null 2>&1; thenHOST_SHA256="shasum -a 256"elseecho "Error: Neither sha256sum nor sha256 seem to be available!" >&2exit 1fihaikuRequiredLegacyGCCVersion="2.95.3-haiku-2017_07_20"export haikuRequiredLegacyGCCVersion# version of legacy gcc required to build haikusupportedTargetArchs="armarm64m68kppcriscv64sparcx86x86_64x86_gcc2"# parse parameters#while [ $# -gt 0 ] ; docase "$1" in--sysroot)assertparam "$1" $#crossToolsSysroot=$2shift 2;;--bootstrap)assertparams "$1" 3 $#HOST_HAIKU_PORTER="`absolute_path $2`"HAIKU_PORTS_CROSS="`absolute_path $3`"HAIKU_PORTS="`absolute_path $4`"HAIKU_IS_BOOTSTRAP=1HAIKU_NO_DOWNLOADS=1if ! check_file_exists "$HOST_HAIKU_PORTER"; thenecho "Invalid path to haikuporter: $HOST_HAIKU_PORTER" >&2exit 1fiif ! check_dir_exists "$HAIKU_PORTS"; thenecho "Non-existent directory $HAIKU_PORTS" >&2exit 1fiif ! check_dir_exists "$HAIKU_PORTS_CROSS"; thenecho "Non-existent directory $HAIKU_PORTS_CROSS" >&2exit 1fishift 4;;--cross-tools-source)assertparam "$1" $#buildCrossTools=$2shift 2;;--build-cross-tools)assertparam "$1" $#targetArch=$2shift 2case "$targetArch" inx86_gcc2) targetMachine=i586-pc-haiku;;x86) targetMachine=i586-pc-haiku;;x86_64) targetMachine=x86_64-unknown-haiku;;ppc) targetMachine=powerpc-apple-haiku;;m68k) targetMachine=m68k-unknown-haiku;;arm) targetMachine=arm-unknown-haiku;;arm64) targetMachine=aarch64-unknown-haiku;;riscv64) targetMachine=riscv64-unknown-haiku;;sparc) targetMachine=sparc64-unknown-haiku;;*)echo "Unsupported target architecture: $targetArch" >&2exit 1;;esacset_variable buildCrossToolsMachine_$targetArch $targetMachinetargetArchs="$targetArchs $targetArch";;--cross-tools-prefix)assertparam "$1" $#targetArch=unknown${unknownArchIndex}set_variable crossToolsPrefix_$targetArch "$2"targetArchs="$targetArchs $targetArch"unknownArchIndex=$(($unknownArchIndex + 1))shift 2;;--distro-compatibility)assertparam "$1" $#HAIKU_DISTRO_COMPATIBILITY=$2case "$HAIKU_DISTRO_COMPATIBILITY" inofficial) ;;compatible) ;;default) ;;*) echo "Invalid distro compatibility" \"level: $HAIKU_DISTRO_COMPATIBILITY"exit 1;;esacshift 2;;--host-only) HAIKU_HOST_BUILD_ONLY=1; shift 1;;--include-sources) HAIKU_INCLUDE_SOURCES=1; shift 1;;--include-3rdparty) HAIKU_INCLUDE_3RDPARTY=1; shift 1;;-j*) buildCrossToolsJobs="$1"; shift 1;;--no-downloads) HAIKU_NO_DOWNLOADS=1; shift 1;;--target-arch)assertparam "$1" $#targetArch=$2shift 2if [ ! "$platform" = Haiku ]; thenecho "--target-arch can only be specified on Haiku." >&2exit 1fiis_in_list "$targetArch" "$supportedTargetArchs" || (echo "Unsupported target architecture: \"$targetArch\"" >&2exit 1)haikuTargetArchs="$haikuTargetArchs $targetArch";;--use-clang)assertparam "$1" $#targetArch=$2useClang=1case "$targetArch" inx86) targetMachine=i586-pc-haiku;;x86_64) targetMachine=x86_64-unknown-haiku;;ppc) targetMachine=powerpc-apple-haiku;;arm) targetMachine=arm-unknown-haiku;;arm64) targetMachine=aarch64-unknown-haiku;;riscv64) targetMachine=riscv64-unknown-haiku;;sparc) targetMachine=sparc64-unknown-haiku;;*)echo "Unsupported target architecture: $2" >&2exit 1;;esacget_build_tool_path clang clangif [ -z `get_variable "crossToolsPrefix_$targetArch"` ] \&& [ -z `get_variable buildCrossToolsMachine_$targetArch` ]; thenset_variable crossToolsPrefix_$targetArch llvm-ficlangVersion=`$HAIKU_clang -v 2>&1 | head -1 | cut -d " " -f3`if [ `echo $clangVersion | cut -d'.' -f1` -lt 7 ]; thenecho "Haiku requires Clang 7 or better to build, but you have $clangVersion."echo "Please install a newer version."exit 1fitargetArchs="$targetArchs $targetArch"shift 2;;--use-gcc-pipe) HAIKU_USE_GCC_PIPE=1; shift 1;;--use-gcc-graphite) useGccGraphiteDefault=1; shift 1;;--use-32bit) HAIKU_HOST_USE_32BIT=1; shift 1;;--no-full-xattr)HAIKU_HOST_USE_XATTR=0; shift 1;;--no-xattr) HAIKU_HOST_USE_XATTR_REF=0; shift 1;;--with-gdb) gdbSources=$2; shift 2;;--use-stack-protector) HAIKU_USE_STACK_PROTECTOR=1; shift 1;;--efi-signing-key)assertparam "$1" $#HAIKU_EFI_SIGNING_KEY="$2"shift 2;;*) echo Invalid argument: \`$1\'; exit 1;;esacdone# check for case-sensitive filesystemmkdir haikuCaseTest 2>/dev/nullmkdir haikucasetest 2>/dev/nullcaseInsensitive=$?rmdir haikuCaseTest haikucasetest 2>/dev/nullif [ $caseInsensitive != 0 ]; thenecho "You need a case-sensitive file-system to build Haiku."if [ $HOST_PLATFORM = "darwin" ]; thenecho "You can create a case-sensitive disk image using Disk Utility."fiexit 1fi# check xattr supportif [ -z $HAIKU_HOST_USE_XATTR_REF ]; thencheck_native_xattrsattrSupport=$?if [ $attrSupport = 2 ] && [ -z $HAIKU_HOST_USE_XATTR ]; thenHAIKU_HOST_USE_XATTR=1elif [ $attrSupport = 1 ]; thenHAIKU_HOST_USE_XATTR_REF=1fifiif [ -z $HAIKU_HOST_USE_XATTR ]; then HAIKU_HOST_USE_XATTR=0; fiif [ -z $HAIKU_HOST_USE_XATTR_REF ]; then HAIKU_HOST_USE_XATTR_REF=0; fi# determine how to invoke sed with extended regexp support for non-GNU sedif [ $HOST_PLATFORM = "darwin" ]; thenHOST_EXTENDED_REGEX_SED="sed -E"fi# pick a JAMSHELLif [ "$JAMSHELL" = "" ]; thenif check_file_exists /bin/dash; thenJAMSHELL=/bin/dashelseJAMSHELL=/bin/shfifiif ! $JAMSHELL -c true; thenecho "$JAMSHELL does not work! Please specify a working JAMSHELL."exit 1fi# locate pythonif [ -z "$HOST_PYTHON" ]; thenif python3 --version < /dev/null > /dev/null 2>&1; thenHOST_PYTHON="python3"elif python --version < /dev/null > /dev/null 2>&1; thenHOST_PYTHON="python"elseecho "Python interpreter not found (maybe specify one in HOST_PYTHON?)"exit 1fifi# check is python is new enough# usage of python by HDS requires at least 3.9PYTHON_VERSION=$("$HOST_PYTHON" --version 2>&1 | sed -e 's/Python //')case $PYTHON_VERSION in2.* | 3.[1-8].*)echo "Python $PYTHON_VERSION is too old; need at least Python 3.9."echo "(maybe specify a newer one in HOST_PYTHON?)"exit 1;;*);;esac# check if wget supports --retry-on-host-errorif wget --retry-on-host-error --version > /dev/null 2>&1; thenHOST_WGET_RETRY_ON_HOST_ERROR=1fi# check if nasm can actually output ELF files# (the stock version in OSX can't)# XXX: should probably only test for x86* archif [ "$("$HAIKU_NASM" -hf | grep -c elf'[36][24] ')" -ne "2" ]; thenecho "$HAIKU_NASM cannot generate ELF files. Please install a working version."if [ $HOST_PLATFORM = "darwin" ]; thenecho "You can install it from Mac Ports."echo "Mac Ports is available at: http://www.macports.org/"fiexit 1fi# create output directorymkdir -p "$buildOutputDir" || exit 1if [ "$HAIKU_HOST_BUILD_ONLY" = 1 ]; theninvalidCommand=$sourceDir/build/scripts/host_build_onlyHAIKU_AR=$invalidCommandHAIKU_CC=$invalidCommandHAIKU_LD=$invalidCommandHAIKU_OBJCOPY=$invalidCommandHAIKU_RANLIB=$invalidCommandHAIKU_ELFEDIT=$invalidCommandHAIKU_NASM=$invalidCommandHAIKU_STRIP=$invalidCommandelse# On Haiku determine target architectures and tools automatically.if [ -z "$targetArchs" ]; thenif [ $HOST_PLATFORM != haiku_host ]; thenecho "Please specify the build tools to use or build (via" \"--cross-tools-prefix or --build-cross-tools) or specify a" \"host-only build (--host-only)." >&2echo "For more info, invoke $0 --help"exit 1fi# determine primary architecturetargetArch=`package list -i /system/packages/haiku-*.hpkg \| sed '/^\s*architecture:/!d; s,^\s*architecture:\s*,,'`is_in_list "$targetArch" "$supportedTargetArchs" || (echo "Unsupported target architecture: \"$targetArch\"" >&2exit 1)targetArchs=$targetArchset_default_value HAIKU_AR_$targetArch arset_default_value HAIKU_CC_$targetArch gccset_default_value HAIKU_LD_$targetArch ldset_default_value HAIKU_OBJCOPY_$targetArch objcopyset_default_value HAIKU_RANLIB_$targetArch ranlibset_default_value HAIKU_ELFEDIT_$targetArch elfeditset_default_value HAIKU_STRIP_$targetArch strip# determine secondary architecturesfor targetArch in $supportedTargetArchs; doif [ -e /system/packages/haiku_$targetArch-*.hpkg ]; thentargetArchs="$targetArchs $targetArch"set_default_value HAIKU_AR_$targetArch ar-$targetArchset_default_value HAIKU_CC_$targetArch gcc-$targetArchset_default_value HAIKU_LD_$targetArch ld-$targetArchset_default_value HAIKU_OBJCOPY_$targetArch objcopy-$targetArchset_default_value HAIKU_RANLIB_$targetArch ranlib-$targetArchset_default_value HAIKU_ELFEDIT_$targetArch elfedit-$targetArchset_default_value HAIKU_STRIP_$targetArch strip-$targetArchfidone# The target architectures might have been specified explicitly.if [ -n "$haikuTargetArchs" ]; thenfor targetArch in $haikuTargetArchs; dois_in_list "$targetArch" "$targetArchs" || (echo "Unsupported target architecture: \"$targetArch\"." \"Only native architectures of the host platform can" \"be specified." >&2exit 1)donetargetArchs="$haikuTargetArchs"fifiif [ "$targetArchs" = " x86_gcc2" ]; thenecho "Building a GCC2-only Haiku is no longer supported."echo "Please configure the secondary architecture."exit 1fiisPrimaryArch=1for targetArch in $targetArchs; do# Note: targetArch is "unknown<n>" at this point if a cross-tools# prefix was specified. The standard_gcc_settings call below will get# the actual architecture.for existingArch in $HAIKU_PACKAGING_ARCHS; doif [ $existingArch = $targetArch ]; then# somehow we wound up with a duplicate arch; skip this onetargetArch=breakfidoneif [ -z "$targetArch" ]; thencontinueficrossToolsPrefix=`get_variable crossToolsPrefix_$targetArch`# build cross tools from sourcesif [ -n "$buildCrossTools" -a -z "$crossToolsPrefix" ]; thencrossToolsDir="$outputDir/cross-tools-$targetArch"targetMachine=`get_variable buildCrossToolsMachine_$targetArch`script="$buildCrossToolsScript"scriptArgs=if [ $targetArch != x86_gcc2 ]; thenscript="${script}_gcc4"scriptArgs="$targetMachine"set_default_value HAIKU_USE_GCC_GRAPHITE_$targetArch \$useGccGraphiteDefaultfisecondaryArch=if [ -z "$isPrimaryArch" ]; thensecondaryArch=$targetArchficase $HOST_PLATFORM infreebsd|openbsd) MAKE=gmake;;*) MAKE=make;;esacif ! valid_toolchain "${targetMachine}" "${crossToolsDir}" "${buildCrossTools}"; thenMAKE=$MAKE \SECONDARY_ARCH=$secondaryArch \HAIKU_USE_GCC_GRAPHITE=`get_variable \HAIKU_USE_GCC_GRAPHITE_$targetArch` \HAIKU_USE_GCC_PIPE=$HAIKU_USE_GCC_PIPE \HAIKU_USE_GDB="$gdbSources" \HAIKU_USE_SYSROOT="$crossToolsSysroot" \"$script" $scriptArgs "$sourceDir" "$buildCrossTools" \"$crossToolsDir" $buildCrossToolsJobs || exit 1elseecho "$targetArch crosstools already exist in $crossToolsDir; skipping build"ficrossToolsPrefix="$crossToolsDir/bin/${targetMachine}-"fi# prepare gcc settings and get the actual target architectureif [ $useClang = 1 ]; thengcc="$HAIKU_clang -target ${targetMachine}"if [ ! -z "${crossToolsPrefix}" ]; thengcc="$gcc -B ${crossToolsPrefix}"fi# Clang's compiler intrinsics are not compatible with GCC's or even# across versions of Clang, so we must collect them for use in the build.mkdir -p "$outputDir/clang_headers" || exit 1clangHeadersDir=`$gcc -print-resource-dir`/include/case $targetArch inx86*) cp $clangHeadersDir/*intrin* $clangHeadersDir/mm3* "$outputDir/clang_headers" || exit 1 ;;ppc*) cp $clangHeadersDir/*altivec* "$outputDir/clang_headers" || exit 1 ;;arm*) cp $clangHeadersDir/*arm* "$outputDir/clang_headers" || exit 1 ;;esacelif [ -z "${crossToolsPrefix}" ]; thengcc=`get_variable HAIKU_CC_$targetArch`elsegcc="${crossToolsPrefix}gcc"fiif [ -z "$gcc" ]; thenecho "Please specify the build tools to use or build (via" \"--cross-tools-prefix or --build-cross-tools)." >&2echo "For more info, invoke $0 --help"exit 1fistandard_gcc_settings "$gcc"targetArch=$standard_gcc_settings_targetArch# set default values for flagsset_default_value HAIKU_CPPFLAGS_$targetArch ""set_default_value HAIKU_CCFLAGS_$targetArch ""set_default_value HAIKU_CXXFLAGS_$targetArch ""set_default_value HAIKU_LINKFLAGS_$targetArch ""set_default_value HAIKU_LDFLAGS_$targetArch ""set_default_value HAIKU_ARFLAGS_$targetArch cruset_default_value HAIKU_UNARFLAGS_$targetArch x# Override the cross tools variables, if the tools were built or a# prefix was specified.if [ -n "$crossToolsPrefix" ]; thenget_build_tool_path AR_$targetArch ${crossToolsPrefix}arget_build_tool_path OBJCOPY_$targetArch ${crossToolsPrefix}objcopyget_build_tool_path RANLIB_$targetArch ${crossToolsPrefix}ranlibget_build_tool_path STRIP_$targetArch ${crossToolsPrefix}stripget_build_tool_path LD_$targetArch ${crossToolsPrefix}ldif [ `get_variable HAIKU_CC_IS_LEGACY_GCC_$targetArch` -eq 0 ]; thenget_build_tool_path ELFEDIT_$targetArch ${crossToolsPrefix}elfeditfifi# check whether the Haiku compiler really targets HaikutargetMachine=`get_variable HAIKU_GCC_MACHINE_$targetArch`case "$targetMachine" in*-*-haiku) ;;*)echo The compiler specified as Haiku target compiler is not a \valid Haiku cross-compiler. Please see ReadMe.cross-compile. >&2echo compiler: $HAIKU_CCecho compiler is configured for target: $targetMachineexit 1 ;;esacHAIKU_PACKAGING_ARCHS="$HAIKU_PACKAGING_ARCHS $targetArch"isPrimaryArch=donefi# Generate BuildConfigcat << EOF > "$buildConfigFile"# -- WARNING --# This file was AUTOMATICALLY GENERATED by configure, and will be completely# overwritten the next time configure is run.##d ${currentDir}#c ${configurePath}#e ${configureEnvirons}#a ${configureArgs}GIT_DIR ?= "${GIT_DIR}" ;HOST_PLATFORM ?= "${HOST_PLATFORM}" ;TARGET_PLATFORM ?= "${TARGET_PLATFORM}" ;HAIKU_PACKAGING_ARCHS ?= ${HAIKU_PACKAGING_ARCHS} ;HAIKU_NO_DOWNLOADS ?= "${HAIKU_NO_DOWNLOADS}" ;HAIKU_INCLUDE_SOURCES ?= "${HAIKU_INCLUDE_SOURCES}" ;HAIKU_INCLUDE_3RDPARTY ?= "${HAIKU_INCLUDE_3RDPARTY}" ;HAIKU_DISTRO_COMPATIBILITY ?= "${HAIKU_DISTRO_COMPATIBILITY}" ;HAIKU_USE_GCC_PIPE ?= "${HAIKU_USE_GCC_PIPE}" ;HAIKU_HOST_USE_32BIT ?= "${HAIKU_HOST_USE_32BIT}" ;HAIKU_HOST_USE_XATTR ?= "${HAIKU_HOST_USE_XATTR}" ;HAIKU_HOST_USE_XATTR_REF ?= "${HAIKU_HOST_USE_XATTR_REF}" ;HAIKU_HOST_BUILD_ONLY ?= "${HAIKU_HOST_BUILD_ONLY}" ;JAMSHELL ?= ${JAMSHELL} -e -c ;HOST_CC ?= ${CC} ;HOST_GCC_MACHINE ?= ${HOST_GCC_MACHINE} ;HOST_LD ?= ${HOST_GCC_LD} ;HOST_OBJCOPY ?= ${HOST_GCC_OBJCOPY} ;HOST_EXTENDED_REGEX_SED ?= ${HOST_EXTENDED_REGEX_SED} ;HOST_SHA256 ?= ${HOST_SHA256} ;HOST_PYTHON ?= ${HOST_PYTHON} ;HOST_WGET_RETRY_ON_HOST_ERROR ?= ${HOST_WGET_RETRY_ON_HOST_ERROR} ;HAIKU_NASM ?= ${HAIKU_NASM} ;HAIKU_BUILD_ATTRIBUTES_DIR ?= "${HAIKU_BUILD_ATTRIBUTES_DIR}" ;HOST_HAIKU_PORTER ?= ${HOST_HAIKU_PORTER} ;HAIKU_PORTS ?= ${HAIKU_PORTS} ;HAIKU_PORTS_CROSS ?= ${HAIKU_PORTS_CROSS} ;HAIKU_IS_BOOTSTRAP ?= ${HAIKU_IS_BOOTSTRAP} ;HAIKU_BOOT_EFI_PRIVATE_KEYFILE ?= ${HAIKU_EFI_SIGNING_KEY} ;EOFfor targetArch in $HAIKU_PACKAGING_ARCHS; dovariables="HAIKU_CC HAIKU_CCHAIKU_CC_IS_LEGACY_GCC HAIKU_CC_IS_LEGACY_GCCHAIKU_CC_IS_CLANG HAIKU_CC_IS_CLANGHAIKU_USE_GCC_GRAPHITE HAIKU_USE_GCC_GRAPHITEHAIKU_CPU HAIKU_CPUHAIKU_GCC_MACHINE HAIKU_GCC_MACHINEHAIKU_GCC_LIB_DIR HAIKU_GCC_LIB_DIRHAIKU_BOOT_LIBGCC HAIKU_BOOT_LIBGCCHAIKU_BOOT_LIBSUPC++ HAIKU_BOOT_LIBSUPCXXHAIKU_BOOT_32_LIBGCC HAIKU_BOOT_32_LIBGCCHAIKU_BOOT_32_LIBSUPC++ HAIKU_BOOT_32_LIBSUPCXXHAIKU_AR HAIKU_ARHAIKU_LD HAIKU_LDHAIKU_OBJCOPY HAIKU_OBJCOPYHAIKU_RANLIB HAIKU_RANLIBHAIKU_ELFEDIT HAIKU_ELFEDITHAIKU_STRIP HAIKU_STRIPHAIKU_CPPFLAGS HAIKU_CPPFLAGSHAIKU_CCFLAGS HAIKU_CCFLAGSHAIKU_C++FLAGS HAIKU_CXXFLAGSHAIKU_LINKFLAGS HAIKU_LINKFLAGSHAIKU_LDFLAGS HAIKU_LDFLAGSHAIKU_ARFLAGS HAIKU_ARFLAGSHAIKU_UNARFLAGS HAIKU_UNARFLAGS"set -- $variableswhile [ $# -ge 2 ]; dovalue=`get_variable ${2}_$targetArch`echo "${1}_${targetArch} ?= $value ;" >> "$buildConfigFile"shift 2done# For variables that may have long values, distribute them over multiple# lines so that jam doesn't hit the maximum line length.variables="HAIKU_BOOT_C++_HEADERS_DIR HAIKU_BOOT_CXX_HEADERS_DIRHAIKU_BOOT_32_C++_HEADERS_DIR HAIKU_BOOT_32_CXX_HEADERS_DIR"set -- $variableswhile [ $# -ge 2 ]; doecho "${1}_${targetArch} ?= " >> "$buildConfigFile"get_variable ${2}_$targetArch | xargs -n 1 echo " " \>> "$buildConfigFile"echo " ;" >> "$buildConfigFile"shift 2donedone# Generate a Jamfile in the output directory.cat << EOF > $outputDir/Jamfile# -- WARNING --# This file was AUTOMATICALLY GENERATED by configure, and will be completely# overwritten the next time configure is run.HAIKU_TOP = $(relative_to "${sourceDir}" "${outputDir}") ;HAIKU_OUTPUT_DIR = . ;include [ FDirName \$(HAIKU_TOP) Jamfile ] ;EOFecho "Configured successfully!"