-
-
Notifications
You must be signed in to change notification settings - Fork 17
/
build.sh
executable file
·636 lines (615 loc) · 28.6 KB
/
build.sh
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
609
610
611
612
613
614
615
616
617
618
619
620
621
622
623
624
625
626
627
628
629
630
631
632
633
634
635
636
#!/usr/bin/env bash
# SPDX-License-Identifier: Apache-2.0 OR MIT
set -eEuo pipefail
IFS=$'\n\t'
cd "$(dirname "$0")"/..
# shellcheck disable=SC2154
trap 's=$?; echo >&2 "$0: error on line "${LINENO}": ${BASH_COMMAND}"; exit ${s}' ERR
trap -- 'echo >&2 "$0: trapped SIGINT"; exit 1' SIGINT
# USAGE:
# ./tools/build.sh [+toolchain] [target]...
# TESTS=1 ./tools/build.sh [+toolchain] [target]...
# TARGET_GROUP=tier1/tier2 ./tools/build.sh [+toolchain]
# TARGET_GROUP=tier3 ./tools/build.sh [+toolchain]
# This is the list of targets to be built by the matrix in CI's "build" job that doesn't set target-group.
#
# Note that many of the targets listed here are those for which we have these target-specific codes
# in our codebase, which does NOT imply that targets not listed here are not supported.
# Almost all targets are checked at least once by the matrix in CI's "build" job that sets target-group.
# Some targets are also checked by calls to this script in CI's "test" or "no-std" job.
default_targets=(
# no atomic load/store (16-bit)
msp430-none-elf
msp430-unknown-none-elf # same as msp430-none-elf, but for checking custom target
# no atomic load/store (32-bit)
riscv32i-unknown-none-elf
mipsel-sony-psx
# no atomic load/store (64-bit)
riscv64i-unknown-none-elf # custom target
# no atomic CAS (16-bit)
avr-unknown-gnu-atmega2560 # custom target
avr-unknown-gnu-atmega328
# no atomic CAS (32-bit)
thumbv4t-none-eabi
thumbv6m-none-eabi
# no atomic CAS (64-bit)
bpfel-unknown-none
# no-std 32-bit with 32-bit atomic
thumbv7m-none-eabi
# no-std 64-bit with 64-bit atomic
x86_64-unknown-none
# no-std 64-bit with 128-bit atomic
aarch64-unknown-none
# x86_64
# rustc --print target-list | grep -E '^x86_64'
x86_64-unknown-linux-gnu
# x86_64 with CMPXCHG16B
x86_64-apple-darwin
# x86_64 X32 ABI
x86_64-unknown-linux-gnux32
# x86_64 without CPUID
x86_64-fortanix-unknown-sgx
# x86
i686-unknown-linux-gnu
i586-unknown-linux-gnu
# aarch64
# rustc --print target-list | grep -E '^(aarch64|arm64)'
# (for target in $(rustc --print target-list | grep -E '^(aarch64|arm64)'); do rustc --print target-spec-json -Z unstable-options --target "${target}" | jq -r '.os'; done) | LC_ALL=C sort -u
aarch64-linux-android
aarch64-pc-windows-msvc
aarch64-unknown-freebsd
aarch64-unknown-fuchsia
aarch64-unknown-linux-gnu
aarch64-unknown-linux-musl
aarch64-unknown-linux-uclibc # custom target
aarch64-unknown-netbsd
aarch64-unknown-openbsd
# aarch64 with FEAT_LSE & FEAT_LSE2
aarch64-apple-darwin
# aarch64 big endian
aarch64_be-unknown-linux-gnu
aarch64_be-unknown-netbsd
# aarch64 ILP32 ABI
aarch64-unknown-linux-gnu_ilp32
# aarch64 ILP32 ABI big endian
aarch64_be-unknown-linux-gnu_ilp32
# pre-v6 arm linux-like
armv4t-unknown-linux-gnueabi
armv5te-unknown-linux-gnueabi
arm-linux-androideabi
# riscv32 with atomic
riscv32imac-unknown-none-elf
riscv32imc-esp-espidf
# riscv64 with atomic
riscv64gc-unknown-linux-gnu
# powerpc64
# rustc --print target-list | grep -E '^powerpc64'
# (for target in $(rustc --print target-list | grep -E '^powerpc64'); do rustc --print target-spec-json -Z unstable-options --target "${target}" | jq -r '.os'; done) | LC_ALL=C sort -u
powerpc64-unknown-linux-gnu
powerpc64le-unknown-linux-gnu
powerpc64-unknown-linux-musl
powerpc64le-unknown-linux-musl
powerpc64-unknown-freebsd
powerpc64le-unknown-freebsd
# s390x
# rustc --print target-list | grep -E '^s390x'
s390x-unknown-linux-gnu
)
# List of known custom cfgs, excluding those that may be set from build script.
known_cfgs=(
portable_atomic_no_outline_atomics
portable_atomic_outline_atomics
# Not public APIs
portable_atomic_test_outline_atomics_detect_false
portable_atomic_doc_cfg
qemu
rustfmt
valgrind
)
# NB: sync with:
# - docs.rs metadata in Cargo.toml
# - env.TEST_FEATURES in .github/workflows/ci.yml.
# - test_features list in tools/test.sh.
test_features="float,std,serde,critical-section"
exclude_features="unsafe-assume-single-core,s-mode,force-amo,disable-fiq"
x() {
local cmd="$1"
shift
(
set -x
"${cmd}" "$@"
)
}
x_cargo() {
if [[ -n "${RUSTFLAGS:-}" ]]; then
echo "+ RUSTFLAGS='${RUSTFLAGS}' \\"
fi
RUSTFLAGS="${RUSTFLAGS:-} ${check_cfg:-}" \
x cargo ${pre_args[@]+"${pre_args[@]}"} "$@"
echo
}
bail() {
echo "error: $*" >&2
exit 1
}
is_no_std() {
case "$1" in
# https://github.com/rust-lang/rust/blob/1.70.0/library/std/build.rs#L41
# TODO: Mark ESP-IDF as no-std to work around upstream bug since nightly-2023-10-14: https://github.com/rust-lang/rust/pull/116723
# TODO: aarch64-unknown-linux-uclibc is a custom target and libc/std currently doesn't support it.
*-none* | *-uefi* | *-psp* | *-psx* | *-cuda* | avr-* | *-espidf | aarch64-unknown-linux-uclibc) return 0 ;;
*) return 1 ;;
esac
}
pre_args=()
is_custom_toolchain=''
if [[ "${1:-}" == "+"* ]]; then
if [[ "$1" == "+esp" ]]; then
is_custom_toolchain=1
fi
pre_args+=("$1")
shift
fi
if [[ -z "${is_custom_toolchain}" ]]; then
# shellcheck disable=SC2207
rustup_targets=($(rustup ${pre_args[@]+"${pre_args[@]}"} target list | sed 's/ .*//g'))
fi
# shellcheck disable=SC2207
all_targets=($(rustc ${pre_args[@]+"${pre_args[@]}"} --print target-list))
if [[ -n "${TARGET_GROUP:-}" ]] && [[ -n "${TESTS:-}" ]]; then
bail "when TARGET_GROUP is set, you cannot use TESTS"
fi
if [[ $# -gt 0 ]]; then
targets=("$@")
elif [[ -n "${TARGET_GROUP:-}" ]]; then
case "${TARGET_GROUP:-}" in
tier1/tier2) targets=("${rustup_targets[@]}") ;;
tier3)
targets=()
for target in "${all_targets[@]}"; do
for t in "${rustup_targets[@]}"; do
if [[ "${target}" == "${t}" ]]; then
target=""
break
fi
done
if [[ -n "${target}" ]]; then
targets+=("${target}")
fi
done
;;
*) bail "unrecognized target group '${TARGET_GROUP}'" ;;
esac
else
targets=("${default_targets[@]}")
fi
rustup_target_list=''
if [[ -z "${is_custom_toolchain}" ]]; then
rustup_target_list=$(rustup ${pre_args[@]+"${pre_args[@]}"} target list | sed 's/ .*//g')
fi
rustc_target_list=$(rustc ${pre_args[@]+"${pre_args[@]}"} --print target-list)
rustc_version=$(rustc ${pre_args[@]+"${pre_args[@]}"} -Vv | grep 'release: ' | sed 's/release: //')
rustc_minor_version="${rustc_version#*.}"
rustc_minor_version="${rustc_minor_version%%.*}"
llvm_version=$(rustc ${pre_args[@]+"${pre_args[@]}"} -Vv | (grep 'LLVM version: ' || true) | (sed 's/LLVM version: //' || true))
llvm_version="${llvm_version%%.*}"
host=$(rustc ${pre_args[@]+"${pre_args[@]}"} -Vv | grep 'host: ' | sed 's/host: //')
metadata=$(cargo metadata --format-version=1 --no-deps)
target_dir=$(jq <<<"${metadata}" -r '.target_directory')
# Do not use check here because it misses some errors such as invalid inline asm operands and LLVM codegen errors.
subcmd=build
if [[ -n "${TARGET_GROUP:-}" ]]; then
base_args=(hack --no-private "${subcmd}")
else
if [[ -n "${TESTS:-}" ]]; then
# TESTS=1 builds binaries, so cargo build requires toolchain and libraries.
subcmd=check
base_args=(hack "${subcmd}")
else
base_args=(hack "${subcmd}")
fi
fi
nightly=''
if [[ "${rustc_version}" == *"nightly"* ]] || [[ "${rustc_version}" == *"dev"* ]]; then
nightly=1
if [[ -z "${is_custom_toolchain}" ]]; then
rustup ${pre_args[@]+"${pre_args[@]}"} component add rust-src &>/dev/null
fi
# The latest syntax of -Z check-cfg requires 1.75.0-nightly.
# We only check this on the recent nightly to avoid old clippy bugs.
# shellcheck disable=SC2207
if [[ "${rustc_minor_version}" -ge 76 ]] && [[ -n "${TESTS:-}" ]] && [[ -z "${TARGET_GROUP:-}" ]]; then
build_scripts=(build.rs portable-atomic-util/build.rs)
check_cfg='-Z unstable-options --check-cfg=cfg(target_pointer_width,values("128")) --check-cfg=cfg(target_arch,values("xtensa")) --check-cfg=cfg(target_feature,values("lse2","lse128","rcpc3","quadword-atomics","fast-serialization","load-store-on-cond","distinct-ops","miscellaneous-extensions-3"))'
known_cfgs+=($(grep -E 'cargo:rustc-cfg=' "${build_scripts[@]}" | sed -E 's/^.*cargo:rustc-cfg=//; s/(=\\)?".*$//' | LC_ALL=C sort -u))
# TODO: handle multi-line target_feature_if
known_target_feature_values+=($(grep -E 'target_feature_if\("' "${build_scripts[@]}" | sed -E 's/^.*target_feature_if\(//; s/",.*$/"/' | LC_ALL=C sort -u))
check_cfg+=" --check-cfg=cfg(portable_atomic_target_feature,values($(IFS=',' && echo "${known_target_feature_values[*]}")))"
check_cfg+=" --check-cfg=cfg($(IFS=',' && echo "${known_cfgs[*]}"))"
subcmd=clippy
rustup ${pre_args[@]+"${pre_args[@]}"} component add clippy &>/dev/null
target_dir="${target_dir}/check-cfg"
if [[ -n "${TESTS:-}" ]]; then
base_args=(hack "${subcmd}" -Z check-cfg)
else
base_args=(hack "${subcmd}" -Z check-cfg)
fi
fi
fi
export CARGO_TARGET_DIR="${target_dir}"
has_asm=''
# asm! requires 1.59
# concat! in asm! requires 1.46.0-nightly (nightly-2020-06-21).
if [[ "${rustc_minor_version}" -ge 59 ]] || { [[ "${rustc_minor_version}" -ge 46 ]] && [[ -n "${nightly}" ]]; }; then
has_asm='1'
fi
build() {
local target="$1"
shift
local args=("${base_args[@]}")
local target_rustflags="${RUSTFLAGS:-}"
if ! grep <<<"${rustc_target_list}" -Eq "^${target}$" || [[ -f "target-specs/${target}.json" ]]; then
if [[ ! -f "target-specs/${target}.json" ]]; then
echo "target '${target}' not available on ${rustc_version} (skipped all checks)"
return 0
fi
if [[ "${rustc_minor_version}" -lt 47 ]]; then
echo "custom target ('${target}') is not work well with old rustc (${rustc_version}) (skipped all checks)"
return 0
fi
local target_flags=(--target "$(pwd)/target-specs/${target}.json")
else
local target_flags=(--target "${target}")
fi
args+=("${target_flags[@]}")
local cfgs
if grep <<<"${rustup_target_list}" -Eq "^${target}$"; then
cfgs=$(RUSTC_BOOTSTRAP=1 rustc ${pre_args[@]+"${pre_args[@]}"} --print cfg "${target_flags[@]}")
rustup ${pre_args[@]+"${pre_args[@]}"} target add "${target}" &>/dev/null
elif [[ -n "${nightly}" ]]; then
# -Z build-std requires 1.39.0-nightly: https://github.com/rust-lang/cargo/pull/7216
if [[ "${rustc_minor_version}" -lt 39 ]]; then
echo "-Z build-std not available on ${rustc_version} (skipped all checks for '${target}')"
return 0
fi
cfgs=$(RUSTC_BOOTSTRAP=1 rustc ${pre_args[@]+"${pre_args[@]}"} --print cfg "${target_flags[@]}")
if [[ -n "${TARGET_GROUP:-}" ]]; then
args+=(-Z build-std="core")
elif is_no_std "${target}"; then
args+=(-Z build-std="core,alloc")
elif [[ "${rustc_minor_version}" -lt 59 ]]; then
# On most targets, building std with the version before backtrace-sys was removed is painful.
# https://github.com/rust-lang/rust/commit/c058a8b8dc5dea0ed9b33e14da9e317e2749fcd7
# On musl, building std with pre-1.59 nightly requires musl toolchain.
args+=(-Z build-std="core,alloc")
args+=(--exclude-features "std")
elif grep <<<"${cfgs}" -q 'panic="abort"'; then
args+=(-Z build-std="panic_abort,std")
else
args+=(-Z build-std)
fi
else
echo "target '${target}' requires nightly compiler (skipped all checks)"
return 0
fi
has_atomic_cas='1'
# target_has_atomic changed in 1.40.0-nightly: https://github.com/rust-lang/rust/pull/65214
if [[ "${rustc_minor_version}" -ge 40 ]]; then
if ! grep <<<"${cfgs}" -q 'target_has_atomic='; then
has_atomic_cas=''
fi
else
if ! grep <<<"${cfgs}" -q 'target_has_atomic="cas"'; then
has_atomic_cas=''
fi
fi
if [[ "${target}" == "riscv"* ]] && [[ -z "${has_atomic_cas}" ]] && [[ -z "${has_asm}" ]]; then
# RISC-V without A-extension requires asm to implement atomics.
echo "target '${target}' requires asm to implement atomics (skipped all checks)"
return 0
fi
if [[ "${target}" == "avr"* ]]; then
if [[ "${llvm_version}" -eq 16 ]]; then
# https://github.com/rust-lang/compiler-builtins/issues/523
target_rustflags+=" -C linker-plugin-lto -C codegen-units=1"
elif [[ "${llvm_version}" -le 17 ]]; then
# https://github.com/rust-lang/rust/issues/88252
target_rustflags+=" -C opt-level=s"
fi
fi
if ! grep <<<"${rustup_target_list}" -Eq "^${target}$"; then
case "${target}" in
# TODO: LLVM bug: Undefined temporary symbol error when building std.
mips-*-linux-* | mipsel-*-linux-*) target_rustflags+=" -C opt-level=1" ;;
esac
fi
if [[ -n "${TESTS:-}" ]]; then
# We use std in main tests, so we cannot build them on no-std targets.
# Some no-std targets have target-specific test crates, so build public
# crates' library part and (if they exist) target-specific test crates.
if is_no_std "${target}"; then
local build_util_with_critical_section=''
if [[ -z "${has_atomic_cas}" ]]; then
case "${target}" in
thumbv[4-5]t* | armv[4-5]t* | thumbv6m* | riscv??i-*-none* | riscv??im-*-none* | riscv??imc-*-none*)
target_rustflags+=" --cfg portable_atomic_unsafe_assume_single_core"
;;
bpf* | mips*) build_util_with_critical_section='1' ;;
esac
fi
RUSTFLAGS="${target_rustflags}" \
x_cargo "${args[@]}" --features float --manifest-path Cargo.toml "$@"
if [[ -z "${build_util_with_critical_section}" ]]; then
RUSTFLAGS="${target_rustflags}" \
x_cargo "${args[@]}" --features alloc --manifest-path portable-atomic-util/Cargo.toml "$@"
else
RUSTFLAGS="${target_rustflags}" \
x_cargo "${args[@]}" --features alloc,portable-atomic/critical-section --manifest-path portable-atomic-util/Cargo.toml "$@"
fi
# target-specific test crates are nightly-only.
if [[ -n "${nightly}" ]]; then
local test_dir=''
# NB: sync with tools/no-std.sh
case "${target}" in
armv4t* | thumbv4t*) test_dir=tests/gba ;;
arm* | thumb* | riscv*) test_dir=tests/no-std-qemu ;;
avr-unknown-gnu-atmega2560) test_dir=tests/avr ;; # tests/avr is for atmega2560 not atmega328
esac
if [[ -n "${test_dir}" ]]; then
RUSTFLAGS="${target_rustflags}" \
x_cargo "${args[@]}" --all-features --manifest-path "${test_dir}"/Cargo.toml "$@"
fi
fi
return 0
fi
args+=(
--tests
--features "${test_features}"
--ignore-unknown-features
--workspace --exclude bench --exclude portable-atomic-internal-codegen
)
elif [[ -n "${TARGET_GROUP:-}" ]]; then
case "${target}" in
# TODO: LLVM bug: https://github.com/rust-lang/rust/issues/89498
m68k-unknown-linux-gnu) return 0 ;;
esac
RUSTFLAGS="${target_rustflags}" \
x_cargo "${args[@]}" --manifest-path Cargo.toml "$@"
return 0
else
# paste! on statements requires 1.45
if [[ "${rustc_minor_version}" -ge 45 ]]; then
if [[ -n "${has_atomic_cas}" ]]; then
RUSTFLAGS="${target_rustflags}" \
x_cargo "${args[@]}" --feature-powerset --manifest-path tests/api-test/Cargo.toml "$@"
else
# target without CAS requires asm to implement CAS.
if [[ -n "${has_asm}" ]]; then
# critical-section requires 1.54
if [[ "${rustc_minor_version}" -ge 54 ]]; then
RUSTFLAGS="${target_rustflags}" \
x_cargo "${args[@]}" --feature-powerset --features portable-atomic/critical-section --manifest-path tests/api-test/Cargo.toml "$@"
fi
case "${target}" in
avr-* | msp430-*) # always single-core
RUSTFLAGS="${target_rustflags}" \
x_cargo "${args[@]}" --feature-powerset --manifest-path tests/api-test/Cargo.toml "$@"
;;
bpf* | mips*) ;;
*)
CARGO_TARGET_DIR="${target_dir}/api-test-assume-single-core" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_unsafe_assume_single_core" \
x_cargo "${args[@]}" --feature-powerset --manifest-path tests/api-test/Cargo.toml "$@"
case "${target}" in
thumbv[4-5]t* | armv[4-5]t*)
CARGO_TARGET_DIR="${target_dir}/api-test-assume-single-core-disable-fiq" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_unsafe_assume_single_core --cfg portable_atomic_disable_fiq" \
x_cargo "${args[@]}" --feature-powerset --manifest-path tests/api-test/Cargo.toml "$@"
;;
riscv*)
CARGO_TARGET_DIR="${target_dir}/api-test-assume-single-core-s-mode" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_unsafe_assume_single_core --cfg portable_atomic_s_mode" \
x_cargo "${args[@]}" --feature-powerset --manifest-path tests/api-test/Cargo.toml "$@"
# .option arch requires 1.72
if [[ "${rustc_minor_version}" -ge 72 ]]; then
CARGO_TARGET_DIR="${target_dir}/api-test-assume-single-core-force-amo" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_unsafe_assume_single_core --cfg portable_atomic_force_amo" \
x_cargo "${args[@]}" --feature-powerset --manifest-path tests/api-test/Cargo.toml "$@"
fi
;;
esac
;;
esac
else
echo "target '${target}' requires asm to implement atomic CAS (skipped API check)"
fi
fi
fi
args+=(
--feature-powerset --depth 2 --optional-deps --no-dev-deps
${exclude_features+"--exclude-features=${exclude_features}"}
--workspace --no-private
)
# critical-section requires 1.54
if [[ "${rustc_minor_version}" -lt 54 ]]; then
args+=(--exclude-features "critical-section")
fi
if is_no_std "${target}"; then
args+=(--exclude-features "std")
if [[ -z "${has_atomic_cas}" ]]; then
if [[ -n "${has_asm}" ]]; then
case "${target}" in
avr-* | msp430-*) ;; # always single-core
bpf* | mips*) ;; # TODO, Arc can't be used here yet
*)
CARGO_TARGET_DIR="${target_dir}/assume-single-core" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_unsafe_assume_single_core" \
x_cargo "${args[@]}" --exclude-features "critical-section" "$@"
case "${target}" in
thumbv[4-5]t* | armv[4-5]t*)
CARGO_TARGET_DIR="${target_dir}/assume-single-core-disable-fiq" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_unsafe_assume_single_core --cfg portable_atomic_disable_fiq" \
x_cargo "${args[@]}" --exclude-features "critical-section" "$@"
;;
riscv*)
CARGO_TARGET_DIR="${target_dir}/assume-single-core-s-mode" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_unsafe_assume_single_core --cfg portable_atomic_s_mode" \
x_cargo "${args[@]}" --exclude-features "critical-section" "$@"
# .option arch requires 1.72
if [[ "${rustc_minor_version}" -ge 72 ]]; then
CARGO_TARGET_DIR="${target_dir}/assume-single-core-force-amo" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_unsafe_assume_single_core --cfg portable_atomic_force_amo" \
x_cargo "${args[@]}" --exclude-features "critical-section" "$@"
fi
;;
esac
;;
esac
else
echo "target '${target}' requires asm to implement atomic CAS (skipped build with --cfg portable_atomic_unsafe_assume_single_core)"
fi
case "${target}" in
avr-* | msp430-*) ;; # always single-core
*)
# portable-atomic-util crate and portable-atomic's require-cas feature require atomic CAS,
# so doesn't work on this target without portable_atomic_unsafe_assume_single_core cfg
# or critical-section feature.
args+=(
--exclude portable-atomic-util
--exclude-features require-cas
)
;;
esac
fi
fi
fi
RUSTFLAGS="${target_rustflags}" \
x_cargo "${args[@]}" "$@"
# Check {,no-}outline-atomics
case "${target}" in
# portable_atomic_no_outline_atomics only affects x86_64, aarch64, arm, and powerpc64.
# powerpc64 is skipped because outline-atomics is currently disabled by default on powerpc64.
x86_64* | aarch64* | arm*)
CARGO_TARGET_DIR="${target_dir}/no-outline-atomics" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_no_outline_atomics" \
x_cargo "${args[@]}" "$@"
;;
esac
case "${target}" in
# portable_atomic_outline_atomics only affects aarch64 Linux and powerpc64.
# powerpc64le- (little-endian) is skipped because it is pwr8 by default
aarch64*-linux-* | powerpc64-*)
CARGO_TARGET_DIR="${target_dir}/outline-atomics" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_outline_atomics" \
x_cargo "${args[@]}" "$@"
CARGO_TARGET_DIR="${target_dir}/outline-atomics-no-outline-atomics" \
RUSTFLAGS="${target_rustflags} --cfg portable_atomic_outline_atomics --cfg portable_atomic_no_outline_atomics" \
x_cargo "${args[@]}" "$@"
;;
esac
# Check target features
case "${target}" in
mips-*-linux-musl* | mipsel-*-linux-musl*) ;; # -crt-static by default
*-linux-musl*)
CARGO_TARGET_DIR="${target_dir}/no-crt-static" \
RUSTFLAGS="${target_rustflags} -C target_feature=-crt-static" \
x_cargo "${args[@]}" "$@"
case "${target}" in
# portable_atomic_no_outline_atomics only affects x86_64, aarch64, arm, and powerpc64.
# powerpc64 is skipped because outline-atomics is currently disabled by default on powerpc64.
x86_64* | aarch64* | arm*)
CARGO_TARGET_DIR="${target_dir}/no-crt-static-no-outline-atomics" \
RUSTFLAGS="${target_rustflags} -C target_feature=-crt-static --cfg portable_atomic_no_outline_atomics" \
x_cargo "${args[@]}" "$@"
;;
esac
;;
esac
case "${target}" in
x86_64*)
# Apple targets are skipped because they are +cmpxchg16b by default
case "${target}" in
*-apple-*) ;;
*)
CARGO_TARGET_DIR="${target_dir}/cmpxchg16b" \
RUSTFLAGS="${target_rustflags} -C target-feature=+cmpxchg16b" \
x_cargo "${args[@]}" "$@"
# Check no-outline-atomics
CARGO_TARGET_DIR="${target_dir}/cmpxchg16b-no-outline-atomics" \
RUSTFLAGS="${target_rustflags} -C target-feature=+cmpxchg16b --cfg portable_atomic_no_outline_atomics" \
x_cargo "${args[@]}" "$@"
;;
esac
;;
aarch64* | arm64*)
# macOS is skipped because it is +lse,+lse2 by default
case "${target}" in
*-darwin) ;;
*)
CARGO_TARGET_DIR="${target_dir}/lse" \
RUSTFLAGS="${target_rustflags} -C target-feature=+lse" \
x_cargo "${args[@]}" "$@"
# FEAT_LSE2 doesn't imply FEAT_LSE.
CARGO_TARGET_DIR="${target_dir}/lse2" \
RUSTFLAGS="${target_rustflags} -C target-feature=+lse,+lse2" \
x_cargo "${args[@]}" "$@"
;;
esac
# Support for FEAT_LRCPC3 and FEAT_LSE128 requires LLVM 16+.
if [[ "${llvm_version}" -ge 16 ]]; then
CARGO_TARGET_DIR="${target_dir}/rcpc3" \
RUSTFLAGS="${target_rustflags} -C target-feature=+lse,+lse2,+rcpc3" \
x_cargo "${args[@]}" "$@"
# FEAT_LSE128 implies FEAT_LSE but not FEAT_LSE2.
CARGO_TARGET_DIR="${target_dir}/lse128" \
RUSTFLAGS="${target_rustflags} -C target-feature=+lse2,+lse128" \
x_cargo "${args[@]}" "$@"
CARGO_TARGET_DIR="${target_dir}/lse128-rcpc3" \
RUSTFLAGS="${target_rustflags} -C target-feature=+lse2,+lse128,+rcpc3" \
x_cargo "${args[@]}" "$@"
fi
;;
powerpc64-*)
# powerpc64le- (little-endian) is skipped because it is pwr8 by default
CARGO_TARGET_DIR="${target_dir}/pwr8" \
RUSTFLAGS="${target_rustflags} -C target-cpu=pwr8" \
x_cargo "${args[@]}" "$@"
;;
powerpc64le-*)
# powerpc64- (big-endian) is skipped because it is pre-pwr8 by default
CARGO_TARGET_DIR="${target_dir}/pwr7" \
RUSTFLAGS="${target_rustflags} -C target-cpu=pwr7" \
x_cargo "${args[@]}" "$@"
;;
s390x*)
CARGO_TARGET_DIR="${target_dir}/z196" \
RUSTFLAGS="${target_rustflags} -C target-cpu=z196" \
x_cargo "${args[@]}" "$@"
CARGO_TARGET_DIR="${target_dir}/z15" \
RUSTFLAGS="${target_rustflags} -C target-cpu=z15" \
x_cargo "${args[@]}" "$@"
;;
esac
}
for target in "${targets[@]}"; do
case "${target}" in
host) target="${host}" ;;
esac
if [[ -n "${SKIP_DEFAULT_TARGET:-}" ]]; then
for default_target in "${default_targets[@]}"; do
if [[ "${target}" == "${default_target}" ]]; then
if [[ -n "${CI:-}" ]]; then
echo "target '${target}' is included in the default targets list and covered by other CI jobs or matrices (skipped all checks)"
else
echo "target '${target}' is included in the default targets list (skipped all checks because SKIP_DEFAULT_TARGET is set)"
fi
target=''
break
fi
done
if [[ -z "${target}" ]]; then
continue
fi
fi
build "${target}"
done