kit

kit
git clone https://git.ryansepassi.com/git/kit.git
Log | Files | Refs | README

common.sh (30743B)


      1 #!/bin/sh
      2 
      3 set -eu
      4 
      5 PATH=${PATH:-/usr/bin:/bin:/usr/sbin:/sbin}
      6 export PATH
      7 
      8 : "${KIT:=./build/kit}"
      9 
     10 c_rules=$("$KIT" build source rules/c/common.sh)
     11 . "$c_rules"
     12 
     13 bk_source() {
     14     "$KIT" build source "$1"
     15 }
     16 
     17 bk_config() {
     18     key=$1
     19     def=$2
     20     "$KIT" build config-get --default "$def" "$key"
     21 }
     22 
     23 bk_glob() {
     24     "$KIT" build glob "$1"
     25 }
     26 
     27 bk_depfile() {
     28     if [ -s "$1" ]; then
     29         norm="$1.norm"
     30         sed -e 's@driver/cmd/\.\./\.\./@@g' \
     31             -e 's@driver/env/\.\./@driver/@g' \
     32             -e 's@src/build/\.\./@src/@g' \
     33             "$1" > "$norm"
     34         "$KIT" build depfile "$norm" >/dev/null
     35         rm -f "$1" "$norm"
     36     fi
     37 }
     38 
     39 c_depfile_filter() {
     40     sed -e 's@driver/cmd/\.\./\.\./@@g' \
     41         -e 's@driver/env/\.\./@driver/@g' \
     42         -e 's@src/build/\.\./@src/@g' \
     43         "$1"
     44 }
     45 
     46 bk_host_detect() {
     47     uname_s=$(uname -s)
     48     uname_m=$(uname -m)
     49     case "$uname_s" in
     50         Darwin) BK_HOST_OS=darwin ;;
     51         Linux) BK_HOST_OS=linux ;;
     52         FreeBSD) BK_HOST_OS=freebsd ;;
     53         MINGW*|MSYS*|CYGWIN*) BK_HOST_OS=windows ;;
     54         *) echo "unsupported host OS: $uname_s" >&2; exit 1 ;;
     55     esac
     56     case "$uname_m" in
     57         x86_64|amd64) BK_HOST_ARCH=x86_64 ;;
     58         aarch64|arm64) BK_HOST_ARCH=aarch64 ;;
     59         riscv64) BK_HOST_ARCH=rv64 ;;
     60         *) echo "unsupported host arch: $uname_m" >&2; exit 1 ;;
     61     esac
     62 
     63     BK_HOST_OS=$(bk_config host.os "$BK_HOST_OS")
     64     BK_HOST_ARCH=$(bk_config host.arch "$BK_HOST_ARCH")
     65 }
     66 
     67 bk_cfg_file=${BK_CFG_FILE:-}
     68 bk_cfg_init() {
     69     if [ -z "$bk_cfg_file" ]; then
     70         bk_cfg_file=$(bk_source include/kit/config.h)
     71     fi
     72 }
     73 
     74 bk_cfg() {
     75     bk_cfg_init
     76     awk -v k="$1" '$1 == "#define" && $2 == k { print $3; found = 1 }
     77                    END { if (!found) print "" }' "$bk_cfg_file"
     78 }
     79 
     80 bk_enabled() {
     81     [ "$(bk_cfg "$1")" = "1" ]
     82 }
     83 
     84 bk_filter_out() {
     85     pat=$1
     86     shift
     87     for x in "$@"; do
     88         case "$x" in
     89             $pat) ;;
     90             *) printf '%s\n' "$x" ;;
     91         esac
     92     done
     93 }
     94 
     95 bk_find_sources() {
     96     pat=$1
     97     case "$pat" in
     98         *'/**/*.c')
     99             dir=$(dirname "$(dirname "$pat")")
    100             find "$dir" -type f -name '*.c' 2>/dev/null | sort
    101             ;;
    102         *'/*.c')
    103             dir=$(dirname "$pat")
    104             find "$dir" -type f -name '*.c' 2>/dev/null |
    105                 awk -v p="$dir/" 'index($0, p) == 1 {
    106                     rest = substr($0, length(p) + 1)
    107                     if (rest !~ /\//) print
    108                 }' | sort
    109             ;;
    110         *)
    111             find . -type f -path "./$pat" 2>/dev/null | sed 's@^\./@@' | sort
    112             ;;
    113     esac
    114 }
    115 
    116 bk_cc_supports() {
    117     flag=$1
    118     if "$BK_CC" "$flag" -x c -E /dev/null >/dev/null 2>&1; then
    119         printf '%s' "$flag"
    120     fi
    121 }
    122 
    123 bk_flags_init() {
    124     bk_host_detect
    125 
    126     BK_CC=$(bk_config cc "${CC:-clang}")
    127     BK_AR=$(bk_config ar "${AR:-ar}")
    128     BK_MODE=$(bk_config mode "${RELEASE:-debug}")
    129     BK_PROFILE=$(bk_config profile "${PROFILE:-0}")
    130 
    131     case "$BK_MODE" in
    132         1|release)
    133             BK_HOST_OPTFLAGS=$(bk_config host.optflags "-O2")
    134             BK_HOST_MODE_CPPFLAGS="-DNDEBUG"
    135             BK_HOST_MODE_CFLAGS="-ffunction-sections -fdata-sections"
    136             if [ "$BK_PROFILE" = "1" ]; then
    137                 BK_HOST_MODE_CFLAGS="$BK_HOST_MODE_CFLAGS -g -fno-omit-frame-pointer"
    138             fi
    139             case "$BK_HOST_OS" in
    140                 darwin) BK_HOST_MODE_LDFLAGS="-Wl,-dead_strip" ;;
    141                 *) BK_HOST_MODE_LDFLAGS="-Wl,--gc-sections" ;;
    142             esac
    143             if [ "$BK_PROFILE" != "1" ]; then
    144                 BK_HOST_MODE_LDFLAGS="$BK_HOST_MODE_LDFLAGS -Wl,-S"
    145             fi
    146             ;;
    147         *)
    148             BK_HOST_OPTFLAGS=$(bk_config host.optflags "-O0")
    149             BK_HOST_MODE_CPPFLAGS=""
    150             BK_HOST_MODE_CFLAGS="-g3 -fno-omit-frame-pointer -fno-optimize-sibling-calls -fsanitize=address,undefined -fno-sanitize-recover=address,undefined -fsanitize-address-use-after-scope"
    151             BK_HOST_MODE_LDFLAGS="-fsanitize=address,undefined"
    152             ;;
    153     esac
    154 
    155     BK_HOST_SYSROOT_CFLAGS=""
    156     BK_HOST_SYSROOT_LDFLAGS=""
    157     if [ "$BK_HOST_OS" = darwin ]; then
    158         sdk=$(xcrun --show-sdk-path 2>/dev/null || true)
    159         sdk=$(bk_config host.sysroot "$sdk")
    160         if [ -n "$sdk" ]; then
    161             BK_HOST_SYSROOT_CFLAGS="-isysroot $sdk"
    162             BK_HOST_SYSROOT_LDFLAGS="-isysroot $sdk"
    163         fi
    164     fi
    165 
    166     auto_init=$(bk_cc_supports -ftrivial-auto-var-init=zero)
    167     no_default_config=$(bk_cc_supports --no-default-config)
    168     BK_AUTO_INIT_CFLAGS=$(bk_config cflags.auto-init "$auto_init")
    169     BK_FREESTANDING_CONFIG_CFLAGS=$(bk_config cflags.freestanding-config "$no_default_config")
    170 
    171     BK_CFLAGS_COMMON="$BK_HOST_OPTFLAGS $BK_HOST_MODE_CPPFLAGS $BK_HOST_MODE_CFLAGS $BK_AUTO_INIT_CFLAGS -std=c11 -Wpedantic -Wall -Wextra -Werror"
    172     BK_HOST_CFLAGS="$BK_CFLAGS_COMMON $BK_HOST_SYSROOT_CFLAGS"
    173     BK_HOST_LDFLAGS="$BK_HOST_SYSROOT_LDFLAGS $BK_HOST_MODE_LDFLAGS"
    174     BK_FREESTANDING_CFLAGS="$BK_CFLAGS_COMMON $BK_FREESTANDING_CONFIG_CFLAGS -ffreestanding -nostdinc -Irt/include"
    175     BK_LIB_VISIBILITY_CFLAGS="-fvisibility=hidden"
    176     BK_LIB_CFLAGS="$BK_FREESTANDING_CFLAGS $BK_LIB_VISIBILITY_CFLAGS -Iinclude -Isrc -Ivendor"
    177     BK_DRIVER_CFLAGS="$BK_FREESTANDING_CFLAGS -Iinclude -Ilang -Idriver -Idriver/lib"
    178     BK_DRIVER_ENV_CFLAGS="$BK_HOST_CFLAGS -Iinclude -Ilang -Idriver -Idriver/lib"
    179     BK_HOST_LDLIBS=""
    180     BK_DRIVER_ENV_OS_CFLAGS=""
    181 
    182     case "$BK_HOST_OS" in
    183         darwin)
    184             BK_DRIVER_ENV_OS_CFLAGS="-D_XOPEN_SOURCE=600 -D_DARWIN_C_SOURCE=1"
    185             ;;
    186         linux)
    187             BK_DRIVER_ENV_OS_CFLAGS="-D_GNU_SOURCE=1"
    188             ;;
    189         freebsd)
    190             BK_HOST_LDLIBS="-lpthread"
    191             BK_HOST_LDFLAGS="$BK_HOST_LDFLAGS -rdynamic"
    192             ;;
    193         windows)
    194             BK_DRIVER_ENV_OS_CFLAGS="-D_WIN32_WINNT=0x0601"
    195             BK_HOST_LDLIBS="-lpsapi"
    196             ;;
    197     esac
    198 }
    199 
    200 bk_list_to_args() {
    201     file=$1
    202     shift
    203     : > "$file"
    204     for x in "$@"; do
    205         [ -n "$x" ] && printf '%s\n' "$x" >> "$file"
    206     done
    207 }
    208 
    209 bk_compile() {
    210     src=$1
    211     obj=$2
    212     flags=$3
    213     mkdir -p "$(dirname "$obj")"
    214     dep="$obj.d"
    215     "$BK_CC" $flags -MMD -MP -MF "$dep" -c "$src" -o "$obj"
    216     bk_depfile "$dep"
    217 }
    218 
    219 bk_flat_obj() {
    220     src=$1
    221     root=$2
    222     dest=$3
    223     rel=${src#"$root"/}
    224     dir=$(dirname "$rel")
    225     base=${rel%.c}
    226     flat=$(printf '%s' "$base" | tr '/' '_').o
    227     printf '%s/%s/%s/%s\n' "$KIT_BUILD_OUT" "$dest" "$dir" "$flat"
    228 }
    229 
    230 bk_flat_obj_rel() {
    231     src=$1
    232     root=$2
    233     dest=$3
    234     rel=${src#"$root"/}
    235     dir=$(dirname "$rel")
    236     base=${rel%.c}
    237     flat=$(printf '%s' "$base" | tr '/' '_').o
    238     if [ "$dir" = "." ]; then
    239         printf '%s/%s\n' "$dest" "$flat"
    240     else
    241         printf '%s/%s/%s\n' "$dest" "$dir" "$flat"
    242     fi
    243 }
    244 
    245 bk_driver_obj() {
    246     src=$1
    247     rel=${src#driver/}
    248     printf '%s/driver/%s.o\n' "$KIT_BUILD_OUT" "${rel%.c}"
    249 }
    250 
    251 bk_driver_obj_rel() {
    252     src=$1
    253     rel=${src#driver/}
    254     printf 'driver/%s.o\n' "${rel%.c}"
    255 }
    256 
    257 bk_target_local() {
    258     printf '%s\n' "${KIT_BUILD_TARGET##*:}"
    259 }
    260 
    261 bk_obj_target() {
    262     printf '%s\n' "$1" | sed 's@/@_@g; s@[.]c$@.o@'
    263 }
    264 
    265 bk_sort_words() {
    266     printf '%s\n' "$@" | awk 'NF' | sort -u
    267 }
    268 
    269 bk_lib_sources() {
    270     bk_cfg_init
    271     src_api=$(bk_find_sources 'src/api/*.c')
    272     src_arch=$(bk_find_sources 'src/arch/*.c')
    273     src_asm=$(bk_find_sources 'src/asm/*.c')
    274     src_cg=$(bk_find_sources 'src/cg/*.c')
    275     src_core=$(bk_find_sources 'src/core/*.c')
    276     src_obj=$(bk_find_sources 'src/obj/*.c')
    277 
    278     lib_srcs="
    279 src/abi/abi.c
    280 src/abi/registry.c
    281 $(printf '%s\n' $src_api | awk '$0!="src/api/archive.c" && $0!="src/api/disasm.c" && $0!="src/api/link.c" && $0!="src/api/build.c" && $0!="src/api/cas.c" && $0!="src/api/build_coord.c" && $0!="src/api/package.c" && $0!="src/api/compress.c" && $0!="src/api/image.c" && $0!="src/api/stubs.c"')
    282 $(printf '%s\n' $src_arch | awk '$0 !~ /_stubs[.]c$/')
    283 $src_asm
    284 $src_cg
    285 $src_core
    286 $(printf '%s\n' $src_obj | awk '$0 !~ /_stubs[.]c$/ && $0!="src/obj/image.c"')
    287 src/os/registry.c
    288 "
    289 
    290     aa64=$(bk_find_sources 'src/arch/aa64/**/*.c')
    291     x64=$(bk_find_sources 'src/arch/x64/**/*.c')
    292     arm32=$(bk_find_sources 'src/arch/arm32/**/*.c')
    293     riscv=$(bk_find_sources 'src/arch/riscv/**/*.c')
    294     wasm_arch=$(bk_find_sources 'src/arch/wasm/**/*.c')
    295     c_target=$(bk_find_sources 'src/arch/c_target/**/*.c')
    296 
    297     if ! bk_enabled KIT_OPT_ENABLED; then
    298         aa64=$(printf '%s\n' $aa64 | awk '$0 !~ /\/opt_coord[.]c$/')
    299         x64=$(printf '%s\n' $x64 | awk '$0 !~ /\/opt_coord[.]c$/')
    300         arm32=$(printf '%s\n' $arm32 | awk '$0 !~ /\/opt_coord[.]c$/')
    301         riscv=$(printf '%s\n' $riscv | awk '$0 !~ /\/opt_coord[.]c$/')
    302     fi
    303     if ! bk_enabled KIT_DISASM_ENABLED; then
    304         aa64=$(printf '%s\n' $aa64 | awk '$0 !~ /\/disasm[.]c$/')
    305         x64=$(printf '%s\n' $x64 | awk '$0 !~ /\/disasm[.]c$/')
    306         arm32=$(printf '%s\n' $arm32 | awk '$0 !~ /\/disasm[.]c$/')
    307         riscv=$(printf '%s\n' $riscv | awk '$0 !~ /\/disasm[.]c$/')
    308         lib_srcs="$lib_srcs
    309 src/arch/disasm_stubs.c"
    310     fi
    311     if ! bk_enabled KIT_LINK_ENABLED; then
    312         aa64=$(printf '%s\n' $aa64 | awk '$0 !~ /\/link[.]c$/')
    313         x64=$(printf '%s\n' $x64 | awk '$0 !~ /\/link[.]c$/')
    314         arm32=$(printf '%s\n' $arm32 | awk '$0 !~ /\/link[.]c$/')
    315         riscv=$(printf '%s\n' $riscv | awk '$0 !~ /\/link[.]c$/')
    316         lib_srcs="$lib_srcs
    317 src/arch/link_stubs.c"
    318     fi
    319     if ! bk_enabled KIT_DBG_ENABLED; then
    320         aa64=$(printf '%s\n' $aa64 | awk '$0 !~ /\/dbg[.]c$/')
    321         x64=$(printf '%s\n' $x64 | awk '$0 !~ /\/dbg[.]c$/')
    322         arm32=$(printf '%s\n' $arm32 | awk '$0 !~ /\/dbg[.]c$/')
    323         riscv=$(printf '%s\n' $riscv | awk '$0 !~ /\/dbg[.]c$/')
    324         lib_srcs="$lib_srcs
    325 src/arch/dbg_stubs.c"
    326     fi
    327     if ! bk_enabled KIT_EMU_ENABLED; then
    328         riscv=$(printf '%s\n' $riscv | awk '$0 !~ /\/emu[.]c$/')
    329         lib_srcs="$lib_srcs
    330 src/arch/emu_stubs.c"
    331     fi
    332     if ! bk_enabled KIT_INTERP_ENABLED; then
    333         lib_srcs="$lib_srcs
    334 src/interp/interp_stubs.c"
    335     fi
    336 
    337     obj_elf=$(bk_find_sources 'src/obj/elf/**/*.c')
    338     obj_macho=$(bk_find_sources 'src/obj/macho/**/*.c')
    339     obj_coff=$(bk_find_sources 'src/obj/coff/**/*.c')
    340     obj_wasm=$(bk_find_sources 'src/obj/wasm/**/*.c')
    341 
    342     bk_enabled KIT_ARCH_AA64_ENABLED || {
    343         obj_elf=$(printf '%s\n' $obj_elf | awk '$0 !~ /\/reloc_aarch64[.]c$/')
    344         obj_macho=$(printf '%s\n' $obj_macho | awk '$0 !~ /\/reloc_aarch64[.]c$/')
    345         obj_coff=$(printf '%s\n' $obj_coff | awk '$0 !~ /\/reloc_aarch64[.]c$/')
    346     }
    347     bk_enabled KIT_ARCH_X64_ENABLED || {
    348         obj_elf=$(printf '%s\n' $obj_elf | awk '$0 !~ /\/reloc_x86_64[.]c$/')
    349         obj_macho=$(printf '%s\n' $obj_macho | awk '$0 !~ /\/reloc_x86_64[.]c$/')
    350         obj_coff=$(printf '%s\n' $obj_coff | awk '$0 !~ /\/reloc_x86_64[.]c$/')
    351     }
    352     if ! bk_enabled KIT_ARCH_RV32_ENABLED && ! bk_enabled KIT_ARCH_RV64_ENABLED; then
    353         obj_elf=$(printf '%s\n' $obj_elf | awk '$0 !~ /\/reloc_riscv(32|64)[.]c$/')
    354     fi
    355     bk_enabled KIT_ARCH_ARM32_ENABLED || {
    356         obj_elf=$(printf '%s\n' $obj_elf | awk '$0 !~ /\/reloc_arm[.]c$/')
    357     }
    358     if ! bk_enabled KIT_LINK_ENABLED; then
    359         obj_elf=$(printf '%s\n' $obj_elf | awk '$0 !~ /\/link(_dyn)?[.]c$/')
    360         obj_macho=$(printf '%s\n' $obj_macho | awk '$0 !~ /\/link[.]c$/')
    361         obj_coff=$(printf '%s\n' $obj_coff | awk '$0 !~ /\/link[.]c$/')
    362         lib_srcs="$lib_srcs
    363 src/obj/link_stubs.c"
    364     fi
    365     if ! bk_enabled KIT_EMU_ENABLED; then
    366         obj_elf=$(printf '%s\n' $obj_elf | awk '$0 !~ /\/emu_load[.]c$/')
    367         lib_srcs="$lib_srcs
    368 src/obj/emu_stubs.c"
    369     fi
    370     if ! bk_enabled KIT_AR_ENABLED; then
    371         obj_coff=$(printf '%s\n' $obj_coff | awk '$0 !~ /\/archive[.]c$/')
    372         lib_srcs="$lib_srcs
    373 src/obj/archive_stubs.c"
    374     fi
    375 
    376     bk_enabled KIT_OPT_ENABLED && lib_srcs="$lib_srcs
    377 $(bk_find_sources 'src/opt/**/*.c' | awk '$0!="src/opt/pass_o2.c"')"
    378     bk_enabled KIT_INTERP_ENABLED && lib_srcs="$lib_srcs
    379 $(bk_find_sources 'src/interp/**/*.c' | awk '$0 !~ /\/interp_stubs[.]c$/')"
    380     bk_enabled KIT_AR_ENABLED && lib_srcs="$lib_srcs
    381 src/api/archive.c"
    382     bk_enabled KIT_DISASM_ENABLED && lib_srcs="$lib_srcs
    383 src/api/disasm.c"
    384     bk_enabled KIT_DWARF_ENABLED && lib_srcs="$lib_srcs
    385 $(bk_find_sources 'src/debug/**/*.c')"
    386     bk_enabled KIT_LINK_ENABLED && lib_srcs="$lib_srcs
    387 src/api/link.c
    388 src/api/build.c
    389 $(bk_find_sources 'src/link/**/*.c')"
    390     if ! bk_enabled KIT_JIT_ENABLED; then
    391         lib_srcs=$(printf '%s\n' $lib_srcs | awk '$0 !~ /\/link_jit[.]c$/')
    392     fi
    393     bk_enabled KIT_BUILD_ENABLED && lib_srcs="$lib_srcs
    394 $(bk_find_sources 'src/build/**/*.c')
    395 src/api/build_coord.c"
    396     bk_enabled KIT_IMAGE_ENABLED && lib_srcs="$lib_srcs
    397 src/api/image.c
    398 src/obj/image.c"
    399     bk_enabled KIT_DBG_ENABLED && lib_srcs="$lib_srcs
    400 $(bk_find_sources 'src/dbg/**/*.c')"
    401     bk_enabled KIT_EMU_ENABLED && lib_srcs="$lib_srcs
    402 $(bk_find_sources 'src/emu/**/*.c')
    403 src/os/linux/linux.c"
    404     bk_enabled KIT_GRAM_ENABLED && lib_srcs="$lib_srcs
    405 $(bk_find_sources 'src/gram/**/*.c')"
    406     bk_enabled KIT_CAS_ENABLED && lib_srcs="$lib_srcs
    407 src/api/cas.c
    408 src/dist/dist.c
    409 src/dist/blake2b.c
    410 src/dist/blob.c
    411 src/dist/tree.c
    412 src/dist/cas.c
    413 vendor/monocypher/monocypher.c"
    414     need_codec=0
    415     if bk_enabled KIT_COMPRESS_ENABLED; then
    416         lib_srcs="$lib_srcs
    417 src/api/compress.c
    418 src/dist/lz4frame.c"
    419         need_codec=1
    420     fi
    421     if bk_enabled KIT_PKG_ENABLED; then
    422         lib_srcs="$lib_srcs
    423 src/api/package.c
    424 src/dist/b64.c
    425 src/dist/ed25519.c
    426 src/dist/minisig.c
    427 src/dist/tar.c
    428 src/dist/kpkg.c
    429 src/dist/manifest.c
    430 src/dist/release.c
    431 src/dist/trust.c
    432 vendor/monocypher/monocypher-ed25519.c"
    433         need_codec=1
    434     fi
    435     [ "$need_codec" = 1 ] && lib_srcs="$lib_srcs
    436 src/dist/deflate.c
    437 src/dist/lz4.c"
    438 
    439     bk_enabled KIT_ARCH_AA64_ENABLED && lib_srcs="$lib_srcs
    440 $aa64"
    441     bk_enabled KIT_ARCH_X64_ENABLED && lib_srcs="$lib_srcs
    442 $x64"
    443     bk_enabled KIT_ARCH_ARM32_ENABLED && lib_srcs="$lib_srcs
    444 $arm32"
    445     if bk_enabled KIT_ARCH_RV32_ENABLED || bk_enabled KIT_ARCH_RV64_ENABLED; then
    446         lib_srcs="$lib_srcs
    447 $riscv"
    448     fi
    449     bk_enabled KIT_ARCH_WASM_ENABLED && lib_srcs="$lib_srcs
    450 $wasm_arch"
    451     bk_enabled KIT_ARCH_C_TARGET_ENABLED && lib_srcs="$lib_srcs
    452 $c_target"
    453     if bk_enabled KIT_ARCH_WASM_ENABLED || bk_enabled KIT_OBJ_WASM_ENABLED || bk_enabled KIT_LANG_WASM_ENABLED; then
    454         lib_srcs="$lib_srcs
    455 $(bk_find_sources 'src/wasm/**/*.c')
    456 $obj_wasm"
    457     fi
    458     bk_enabled KIT_OBJ_ELF_ENABLED && lib_srcs="$lib_srcs
    459 $obj_elf"
    460     bk_enabled KIT_OBJ_MACHO_ENABLED && lib_srcs="$lib_srcs
    461 $obj_macho"
    462     bk_enabled KIT_OBJ_COFF_ENABLED && lib_srcs="$lib_srcs
    463 $obj_coff"
    464     if bk_enabled KIT_OBJ_ELF_ENABLED || bk_enabled KIT_OBJ_MACHO_ENABLED || bk_enabled KIT_OBJ_COFF_ENABLED; then
    465         lib_srcs="$lib_srcs
    466 src/os/hosted.c"
    467     fi
    468     if bk_enabled KIT_OBJ_ELF_ENABLED || bk_enabled KIT_EMU_ENABLED; then
    469         lib_srcs="$lib_srcs
    470 src/os/linux/os.c"
    471     fi
    472     bk_enabled KIT_OBJ_ELF_ENABLED && lib_srcs="$lib_srcs
    473 src/os/linux/hosted.c
    474 src/os/freebsd/os.c
    475 src/os/freebsd/hosted.c
    476 src/os/android/os.c
    477 src/os/android/hosted.c"
    478     bk_enabled KIT_OBJ_MACHO_ENABLED && lib_srcs="$lib_srcs
    479 src/os/macos/os.c
    480 src/os/macos/hosted.c"
    481     bk_enabled KIT_OBJ_COFF_ENABLED && lib_srcs="$lib_srcs
    482 src/os/windows/os.c
    483 src/os/windows/hosted.c"
    484 
    485     if bk_enabled KIT_ARCH_AA64_ENABLED || bk_enabled KIT_ARCH_C_TARGET_ENABLED; then
    486         if bk_enabled KIT_OBJ_ELF_ENABLED || bk_enabled KIT_OBJ_MACHO_ENABLED || bk_enabled KIT_OBJ_COFF_ENABLED; then
    487             lib_srcs="$lib_srcs
    488 src/abi/abi_aapcs64.c"
    489         fi
    490         bk_enabled KIT_OBJ_MACHO_ENABLED && lib_srcs="$lib_srcs
    491 src/abi/abi_apple_arm64.c"
    492         bk_enabled KIT_OBJ_COFF_ENABLED && lib_srcs="$lib_srcs
    493 src/abi/abi_aapcs64_windows.c"
    494     fi
    495     if bk_enabled KIT_ARCH_X64_ENABLED || bk_enabled KIT_ARCH_C_TARGET_ENABLED; then
    496         if bk_enabled KIT_OBJ_ELF_ENABLED || bk_enabled KIT_OBJ_MACHO_ENABLED; then
    497             lib_srcs="$lib_srcs
    498 src/abi/abi_sysv_x64.c"
    499         fi
    500         bk_enabled KIT_OBJ_MACHO_ENABLED && lib_srcs="$lib_srcs
    501 src/abi/abi_apple_x64.c"
    502         bk_enabled KIT_OBJ_COFF_ENABLED && lib_srcs="$lib_srcs
    503 src/abi/abi_win64_x64.c"
    504     fi
    505     if bk_enabled KIT_ARCH_RV32_ENABLED || bk_enabled KIT_ARCH_RV64_ENABLED || bk_enabled KIT_ARCH_C_TARGET_ENABLED; then
    506         bk_enabled KIT_OBJ_ELF_ENABLED && lib_srcs="$lib_srcs
    507 src/abi/abi_rv64.c"
    508     fi
    509     if bk_enabled KIT_ARCH_ARM32_ENABLED || bk_enabled KIT_ARCH_C_TARGET_ENABLED; then
    510         bk_enabled KIT_OBJ_ELF_ENABLED && lib_srcs="$lib_srcs
    511 src/abi/abi_aapcs32.c"
    512     fi
    513 
    514     bk_enabled KIT_LANG_CPP_ENABLED && lib_srcs="$lib_srcs
    515 $(bk_find_sources 'lang/cpp/**/*.c')"
    516     bk_enabled KIT_LANG_C_ENABLED && lib_srcs="$lib_srcs
    517 $(bk_find_sources 'lang/c/**/*.c')"
    518     bk_enabled KIT_LANG_WASM_ENABLED && lib_srcs="$lib_srcs
    519 $(bk_find_sources 'lang/wasm/**/*.c')"
    520     bk_enabled KIT_LANG_TOY_ENABLED && lib_srcs="$lib_srcs
    521 $(bk_find_sources 'lang/toy/*.c')"
    522 
    523     printf '%s\n' $lib_srcs | awk 'NF && $0 != "src/opt/pass_o2.c"' | sort -u
    524 }
    525 
    526 bk_driver_sources() {
    527     bk_cfg_init
    528     env_srcs="driver/env/common.c"
    529     case "$BK_HOST_OS" in
    530         windows)
    531             env_srcs="$env_srcs
    532 driver/env/windows.c"
    533             ;;
    534         darwin)
    535             env_srcs="$env_srcs
    536 driver/env/posix.c
    537 driver/env/posix_dbg.c
    538 driver/env/macos.c"
    539             case "$BK_HOST_ARCH" in
    540                 aarch64) env_srcs="$env_srcs
    541 driver/env/icache_arm.c
    542 driver/env/uctx_aarch64_macos.c" ;;
    543                 x86_64) env_srcs="$env_srcs
    544 driver/env/icache_x86.c
    545 driver/env/uctx_x86_64_macos.c" ;;
    546                 *) echo "no Darwin ucontext for $BK_HOST_ARCH" >&2; exit 1 ;;
    547             esac
    548             ;;
    549         linux)
    550             env_srcs="$env_srcs
    551 driver/env/posix.c
    552 driver/env/posix_dbg.c
    553 driver/env/linux.c"
    554             case "$BK_HOST_ARCH" in
    555                 x86_64) env_srcs="$env_srcs
    556 driver/env/linux_exec_hint_x86_64.c
    557 driver/env/icache_x86.c
    558 driver/env/uctx_x86_64_linux.c" ;;
    559                 aarch64) env_srcs="$env_srcs
    560 driver/env/linux_exec_hint_default.c
    561 driver/env/icache_arm.c
    562 driver/env/uctx_aarch64_linux.c" ;;
    563                 rv64) env_srcs="$env_srcs
    564 driver/env/linux_exec_hint_default.c
    565 driver/env/icache_riscv.c
    566 driver/env/uctx_rv64_linux.c" ;;
    567                 *) echo "no Linux ucontext for $BK_HOST_ARCH" >&2; exit 1 ;;
    568             esac
    569             ;;
    570         freebsd)
    571             env_srcs="$env_srcs
    572 driver/env/posix.c
    573 driver/env/posix_dbg.c
    574 driver/env/freebsd.c"
    575             case "$BK_HOST_ARCH" in
    576                 x86_64) env_srcs="$env_srcs
    577 driver/env/icache_x86.c
    578 driver/env/uctx_x86_64_freebsd.c" ;;
    579                 aarch64) env_srcs="$env_srcs
    580 driver/env/icache_arm.c
    581 driver/env/uctx_aarch64_freebsd.c" ;;
    582                 rv64) env_srcs="$env_srcs
    583 driver/env/icache_riscv.c
    584 driver/env/uctx_rv64_freebsd.c" ;;
    585                 *) echo "no FreeBSD ucontext for $BK_HOST_ARCH" >&2; exit 1 ;;
    586             esac
    587             ;;
    588     esac
    589 
    590     tool_srcs=""
    591     bk_enabled KIT_TOOL_CC_ENABLED && tool_srcs="$tool_srcs driver/cmd/cc.c"
    592     bk_enabled KIT_TOOL_CHECK_ENABLED && tool_srcs="$tool_srcs driver/cmd/cc.c"
    593     bk_enabled KIT_TOOL_BUILD_EXE_ENABLED && tool_srcs="$tool_srcs driver/cmd/build.c"
    594     bk_enabled KIT_TOOL_BUILD_LIB_ENABLED && tool_srcs="$tool_srcs driver/cmd/build.c"
    595     bk_enabled KIT_TOOL_BUILD_OBJ_ENABLED && tool_srcs="$tool_srcs driver/cmd/build.c"
    596     bk_enabled KIT_TOOL_BUILD_ENABLED && tool_srcs="$tool_srcs driver/cmd/build_coord.c"
    597     bk_enabled KIT_TOOL_INSTALL_ENABLED && tool_srcs="$tool_srcs driver/cmd/install.c"
    598     bk_enabled KIT_TOOL_CPP_ENABLED && tool_srcs="$tool_srcs driver/cmd/cpp.c"
    599     bk_enabled KIT_TOOL_AS_ENABLED && tool_srcs="$tool_srcs driver/cmd/as.c"
    600     bk_enabled KIT_TOOL_LD_ENABLED && tool_srcs="$tool_srcs driver/cmd/ld.c"
    601     bk_enabled KIT_TOOL_AR_ENABLED && tool_srcs="$tool_srcs driver/cmd/ar.c"
    602     bk_enabled KIT_TOOL_CPIO_ENABLED && tool_srcs="$tool_srcs driver/cmd/cpio.c"
    603     bk_enabled KIT_TOOL_RANLIB_ENABLED && tool_srcs="$tool_srcs driver/cmd/ranlib.c"
    604     bk_enabled KIT_TOOL_STRIP_ENABLED && tool_srcs="$tool_srcs driver/cmd/strip.c"
    605     bk_enabled KIT_TOOL_OBJCOPY_ENABLED && tool_srcs="$tool_srcs driver/cmd/objcopy.c"
    606     bk_enabled KIT_TOOL_IMAGE_ENABLED && tool_srcs="$tool_srcs driver/cmd/image.c"
    607     bk_enabled KIT_TOOL_OBJDUMP_ENABLED && tool_srcs="$tool_srcs driver/cmd/objdump.c"
    608     bk_enabled KIT_TOOL_DBG_ENABLED && tool_srcs="$tool_srcs driver/cmd/dbg.c"
    609     bk_enabled KIT_TOOL_RUN_ENABLED && tool_srcs="$tool_srcs driver/cmd/run.c"
    610     bk_enabled KIT_TOOL_EMU_ENABLED && tool_srcs="$tool_srcs driver/cmd/emu.c"
    611     bk_enabled KIT_TOOL_NM_ENABLED && tool_srcs="$tool_srcs driver/cmd/nm.c"
    612     bk_enabled KIT_TOOL_SIZE_ENABLED && tool_srcs="$tool_srcs driver/cmd/size.c"
    613     bk_enabled KIT_TOOL_ADDR2LINE_ENABLED && tool_srcs="$tool_srcs driver/cmd/addr2line.c"
    614     bk_enabled KIT_TOOL_SYMBOLIZE_ENABLED && tool_srcs="$tool_srcs driver/cmd/symbolize.c"
    615     bk_enabled KIT_TOOL_STRINGS_ENABLED && tool_srcs="$tool_srcs driver/cmd/strings.c"
    616     bk_enabled KIT_TOOL_CAS_ENABLED && tool_srcs="$tool_srcs driver/cmd/cas.c"
    617     bk_enabled KIT_TOOL_PKG_ENABLED && tool_srcs="$tool_srcs driver/cmd/pkg.c"
    618     bk_enabled KIT_TOOL_XXD_ENABLED && tool_srcs="$tool_srcs driver/cmd/xxd.c"
    619     bk_enabled KIT_TOOL_CMP_ENABLED && tool_srcs="$tool_srcs driver/cmd/cmp.c"
    620     bk_enabled KIT_TOOL_HASH_ENABLED && tool_srcs="$tool_srcs driver/cmd/hash.c"
    621     bk_enabled KIT_TOOL_COMPRESS_ENABLED && tool_srcs="$tool_srcs driver/cmd/compress.c"
    622     bk_enabled KIT_TOOL_DISAS_ENABLED && tool_srcs="$tool_srcs driver/cmd/disas.c"
    623     bk_enabled KIT_TOOL_MC_ENABLED && tool_srcs="$tool_srcs driver/cmd/mc.c"
    624     bk_enabled KIT_TOOL_GRAM_ENABLED && tool_srcs="$tool_srcs driver/cmd/gram.c"
    625     bk_enabled KIT_TOOL_TARGETS_ENABLED && tool_srcs="$tool_srcs driver/cmd/targets.c"
    626     bk_enabled KIT_TOOL_UPDATE_ENABLED && tool_srcs="$tool_srcs driver/cmd/update.c"
    627 
    628     shared=""
    629     if bk_enabled KIT_TOOL_CC_ENABLED || bk_enabled KIT_TOOL_CHECK_ENABLED || bk_enabled KIT_TOOL_BUILD_EXE_ENABLED || bk_enabled KIT_TOOL_BUILD_LIB_ENABLED || bk_enabled KIT_TOOL_BUILD_OBJ_ENABLED || bk_enabled KIT_TOOL_CPP_ENABLED || bk_enabled KIT_TOOL_AS_ENABLED || bk_enabled KIT_TOOL_DBG_ENABLED || bk_enabled KIT_TOOL_RUN_ENABLED; then
    630         shared="$shared driver/lib/cflags.c"
    631     fi
    632     if bk_enabled KIT_TOOL_CC_ENABLED || bk_enabled KIT_TOOL_CHECK_ENABLED || bk_enabled KIT_TOOL_BUILD_EXE_ENABLED || bk_enabled KIT_TOOL_BUILD_LIB_ENABLED || bk_enabled KIT_TOOL_BUILD_OBJ_ENABLED || bk_enabled KIT_TOOL_LD_ENABLED || bk_enabled KIT_TOOL_RUN_ENABLED; then
    633         shared="$shared driver/lib/lib_resolve.c"
    634     fi
    635     if bk_enabled KIT_TOOL_CC_ENABLED || bk_enabled KIT_TOOL_CHECK_ENABLED || bk_enabled KIT_TOOL_BUILD_EXE_ENABLED || bk_enabled KIT_TOOL_BUILD_LIB_ENABLED || bk_enabled KIT_TOOL_BUILD_OBJ_ENABLED || bk_enabled KIT_TOOL_RUN_ENABLED; then
    636         shared="$shared driver/lib/hosted.c"
    637     fi
    638     if bk_enabled KIT_TOOL_CC_ENABLED || bk_enabled KIT_TOOL_CHECK_ENABLED || bk_enabled KIT_TOOL_BUILD_EXE_ENABLED || bk_enabled KIT_TOOL_BUILD_LIB_ENABLED || bk_enabled KIT_TOOL_BUILD_OBJ_ENABLED || bk_enabled KIT_TOOL_LD_ENABLED; then
    639         shared="$shared driver/lib/runtime.c"
    640     fi
    641     if bk_enabled KIT_TOOL_CC_ENABLED || bk_enabled KIT_TOOL_CHECK_ENABLED || bk_enabled KIT_TOOL_BUILD_EXE_ENABLED || bk_enabled KIT_TOOL_BUILD_LIB_ENABLED || bk_enabled KIT_TOOL_BUILD_OBJ_ENABLED; then
    642         shared="$shared driver/lib/link_flags.c driver/lib/link_inputs.c"
    643     fi
    644     if bk_enabled KIT_TOOL_BUILD_EXE_ENABLED || bk_enabled KIT_TOOL_BUILD_LIB_ENABLED || bk_enabled KIT_TOOL_BUILD_OBJ_ENABLED; then
    645         shared="$shared driver/lib/archive_engine.c"
    646     fi
    647     if bk_enabled KIT_TOOL_CC_ENABLED || bk_enabled KIT_TOOL_CHECK_ENABLED || bk_enabled KIT_TOOL_AR_ENABLED || bk_enabled KIT_TOOL_RANLIB_ENABLED || bk_enabled KIT_TOOL_STRIP_ENABLED || bk_enabled KIT_TOOL_DBG_ENABLED || bk_enabled KIT_TOOL_RUN_ENABLED || bk_enabled KIT_TOOL_BUILD_EXE_ENABLED || bk_enabled KIT_TOOL_BUILD_LIB_ENABLED || bk_enabled KIT_TOOL_BUILD_OBJ_ENABLED; then
    648         shared="$shared driver/lib/inputs.c"
    649     fi
    650     if bk_enabled KIT_TOOL_STRIP_ENABLED || bk_enabled KIT_TOOL_OBJCOPY_ENABLED; then
    651         shared="$shared driver/lib/objedit.c"
    652     fi
    653     bk_enabled KIT_TOOL_RUN_ENABLED && shared="$shared driver/lib/wasm_run.c"
    654     if bk_enabled KIT_TOOL_CAS_ENABLED || bk_enabled KIT_TOOL_PKG_ENABLED || bk_enabled KIT_TOOL_BUILD_ENABLED || bk_enabled KIT_TOOL_UPDATE_ENABLED; then
    655         shared="$shared driver/lib/dist_host.c"
    656     fi
    657     if bk_enabled KIT_TOOL_BUILD_ENABLED; then
    658         case "$BK_HOST_OS" in
    659             windows) shared="$shared driver/env/build_host_windows.c" ;;
    660             *) shared="$shared driver/env/build_host_posix.c" ;;
    661         esac
    662     fi
    663     if bk_enabled KIT_TOOL_INSTALL_ENABLED || bk_enabled KIT_TOOL_UPDATE_ENABLED; then
    664         shared="$shared driver/lib/install_links.c"
    665     fi
    666     bk_enabled KIT_TOOL_UPDATE_ENABLED && shared="$shared driver/release_key.c"
    667     if bk_enabled KIT_TOOL_ADDR2LINE_ENABLED || bk_enabled KIT_TOOL_SYMBOLIZE_ENABLED; then
    668         shared="$shared driver/lib/dwarfsym.c"
    669     fi
    670     if bk_enabled KIT_TOOL_DBG_ENABLED || bk_enabled KIT_TOOL_RUN_ENABLED; then
    671         shared="$shared driver/lib/backtrace.c"
    672     fi
    673 
    674     printf '%s\n' driver/main.c driver/version.c driver/lib/target.c $env_srcs $tool_srcs $shared |
    675         awk 'NF' | sort -u
    676 }
    677 
    678 bk_version_defs() {
    679     version_file=$(bk_source VERSION)
    680     version=$(sed -n '1p' "$version_file")
    681     [ -n "$version" ] || version=0.0.0
    682     build_id=$(bk_config build.id buildcoord)
    683     case "$BK_HOST_ARCH" in
    684         rv64) triple_arch=riscv64 ;;
    685         *) triple_arch=$BK_HOST_ARCH ;;
    686     esac
    687     case "$BK_HOST_OS" in
    688         darwin) triple_os=macos ;;
    689         linux) triple_os=linux-gnu ;;
    690         *) triple_os=$BK_HOST_OS ;;
    691     esac
    692     host_triple=$(bk_config host.triple "$triple_arch-$triple_os")
    693     printf '%s\n' "-DKIT_VERSION_STR=\"$version\" -DKIT_BUILD_ID=\"$build_id\" -DKIT_HOST_TRIPLE=\"$host_triple\""
    694 }
    695 
    696 bk_libkit_object_plan() {
    697     for src in $(bk_lib_sources); do
    698         flags=$BK_LIB_CFLAGS
    699         root=src
    700         dest=lib
    701         case "$src" in
    702             src/api/lang_registry.c)
    703                 flags="$BK_FREESTANDING_CFLAGS $BK_LIB_VISIBILITY_CFLAGS -Iinclude -Ilang -Isrc"
    704                 ;;
    705             lang/cpp/*)
    706                 flags="$BK_FREESTANDING_CFLAGS $BK_LIB_VISIBILITY_CFLAGS -Iinclude -Ilang/cpp"
    707                 root=lang
    708                 dest=lang
    709                 ;;
    710             lang/c/*)
    711                 flags="$BK_FREESTANDING_CFLAGS $BK_LIB_VISIBILITY_CFLAGS -Iinclude -Ilang/cpp -Ilang/c"
    712                 root=lang
    713                 dest=lang
    714                 ;;
    715             lang/wasm/*)
    716                 flags="$BK_FREESTANDING_CFLAGS $BK_LIB_VISIBILITY_CFLAGS -Iinclude -Isrc -Ilang/wasm"
    717                 root=lang
    718                 dest=lang
    719                 ;;
    720             lang/toy/*)
    721                 flags="$BK_FREESTANDING_CFLAGS $BK_LIB_VISIBILITY_CFLAGS -Iinclude -Ilang/toy"
    722                 root=lang
    723                 dest=lang
    724                 ;;
    725             vendor/*)
    726                 root=vendor
    727                 dest=vendor
    728                 ;;
    729         esac
    730         printf '%s|%s|%s|%s\n' \
    731             "$(bk_obj_target "$src")" "$src" \
    732             "$(bk_flat_obj_rel "$src" "$root" "$dest")" "$flags"
    733     done
    734 }
    735 
    736 bk_driver_object_plan() {
    737     version_defs=$(bk_version_defs)
    738     for src in $(bk_driver_sources); do
    739         flags=$BK_DRIVER_CFLAGS
    740         case "$src" in
    741             driver/env/*)
    742                 flags="$BK_DRIVER_ENV_CFLAGS $BK_DRIVER_ENV_OS_CFLAGS"
    743                 ;;
    744         esac
    745         case "$src" in
    746             driver/version.c)
    747                 flags="$flags $version_defs"
    748                 ;;
    749         esac
    750         printf '%s|%s|%s|%s\n' \
    751             "$(bk_obj_target "$src")" "$src" "$(bk_driver_obj_rel "$src")" \
    752             "$flags"
    753     done
    754 }
    755 
    756 bk_object_plan() {
    757     case "$1" in
    758         driver) bk_driver_object_plan ;;
    759         libkit) bk_libkit_object_plan ;;
    760         libkit-*.objs)
    761             set_id=${1#libkit-}
    762             set_id=${set_id%.objs}
    763             bk_libkit_object_plan | awk -F '|' -v set_id="$set_id" '
    764                 BEGIN { limit = 60; first = set_id * limit + 1; last = first + limit - 1 }
    765                 NR >= first && NR <= last { print }
    766             '
    767             ;;
    768         *)
    769             echo "unknown object plan: $1" >&2
    770             return 1
    771             ;;
    772     esac
    773 }
    774 
    775 bk_libkit_object_sets() {
    776     bk_libkit_object_plan | awk '
    777         BEGIN { limit = 60 }
    778         (NR - 1) % limit == 0 { printf "libkit-%u.objs\n", int((NR - 1) / limit) }
    779     '
    780 }
    781 
    782 bk_object_plan_find() {
    783     if bk_libkit_object_plan | awk -F '|' -v target="$1" '
    784             $1 == target { print; found = 1; exit }
    785             END { if (!found) exit 1 }
    786         '; then
    787         return 0
    788     fi
    789     bk_driver_object_plan | awk -F '|' -v target="$1" '
    790         $1 == target { print; found = 1; exit }
    791         END { if (!found) exit 1 }
    792     '
    793 }
    794 
    795 bk_copy_runtime_support() {
    796     find rt -type f | sort | while IFS= read -r rt_file; do
    797         src=$(bk_source "$rt_file")
    798         dst="$KIT_BUILD_OUT/support/rt/$rt_file"
    799         mkdir -p "$(dirname "$dst")"
    800         cp "$src" "$dst"
    801     done
    802 }
    803 
    804 c_flags_init() {
    805     bk_flags_init
    806     C_CC=$BK_CC
    807     C_AR=$BK_AR
    808     C_CFLAGS=""
    809     C_LDFLAGS=$BK_HOST_LDFLAGS
    810     C_LDLIBS=$BK_HOST_LDLIBS
    811 }
    812 
    813 c_object_plan() {
    814     bk_object_plan "$1"
    815 }
    816 
    817 c_object_plan_find() {
    818     bk_object_plan_find "$1"
    819 }
    820 
    821 c_archive_output() {
    822     case "$1" in
    823         libkit) printf '%s\n' libkit.a ;;
    824         *)
    825             echo "no static-library plan for target: $KIT_BUILD_TARGET" >&2
    826             return 1
    827             ;;
    828     esac
    829 }
    830 
    831 c_archive_object_sets() {
    832     case "$1" in
    833         libkit) bk_libkit_object_sets ;;
    834         *)
    835             echo "no static-library object sets for target: $KIT_BUILD_TARGET" >&2
    836             return 1
    837             ;;
    838     esac
    839 }
    840 
    841 c_executable_output() {
    842     case "$1" in
    843         kit) printf '%s\n' kit ;;
    844         *)
    845             echo "no executable plan for target: $KIT_BUILD_TARGET" >&2
    846             return 1
    847             ;;
    848     esac
    849 }
    850 
    851 c_executable_object_sets() {
    852     case "$1" in
    853         kit) printf '%s\n' //:driver ;;
    854     esac
    855 }
    856 
    857 c_executable_libraries() {
    858     case "$1" in
    859         kit) printf '%s\n' '//:libkit|libkit.a' ;;
    860     esac
    861 }
    862 
    863 c_executable_after_link() {
    864     case "$1" in
    865         kit)
    866             lib_dir=$("$KIT" build need //:libkit)
    867             cp "$lib_dir/libkit.a" "$KIT_BUILD_OUT/libkit.a"
    868             bk_copy_runtime_support
    869             ;;
    870     esac
    871 }