-
Notifications
You must be signed in to change notification settings - Fork 1
Expand file tree
/
Copy pathdev
More file actions
executable file
·106 lines (100 loc) · 4.75 KB
/
Copy pathdev
File metadata and controls
executable file
·106 lines (100 loc) · 4.75 KB
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
#!/usr/bin/env bash
# Wrapper for invoking cargo / qemu inside the pinned dev container.
set -euo pipefail
IMAGE_TAG="cyphera-kernel-container:latest"
PROJECT_ROOT="$(cd "$(dirname "$0")" && pwd)"
ensure_image() {
if ! docker image inspect "$IMAGE_TAG" >/dev/null 2>&1; then
echo "==> Building dev image (${IMAGE_TAG})..."
docker build -t "$IMAGE_TAG" "$PROJECT_ROOT/tools/dev"
fi
}
run_in_container() {
ensure_image
local args=(--rm)
# With a controlling terminal, run interactively and let the container
# share our stdin (so `./dev shell` / `./dev run` are usable). Without
# one (CI, or any non-interactive runner), feed the container stdin from
# /dev/null: the QEMU integration tests attach the kernel console with
# `-serial stdio`, so QEMU reads the runner's stdin. Handing it the
# parent's (already-consumed or watched) stdin makes QEMU block / the
# run get torn down; a clean EOF lets the battery run headless and
# report pass/fail through the exit code.
local stdin_src=/dev/null
if [[ -t 0 && -t 1 ]]; then
args+=(-it)
stdin_src=/dev/stdin
fi
# Hardware-accelerate the QEMU integration tests when the host exposes
# KVM; without it QEMU falls back to software emulation, under which the
# heavier tests can exceed their timeout.
if [[ -e /dev/kvm ]]; then
args+=(--device /dev/kvm --group-add "$(stat -c '%g' /dev/kvm)")
fi
# Forward the QEMU-runner knobs (run-qemu.sh reads these) so e.g.
# CYPHERA_MEM=4096M ./dev test exercises the >1 GiB direct-map path.
for var in CYPHERA_MEM CYPHERA_GRAPHICAL CYPHERA_AUDIO CYPHERA_AUDIO_BACKEND \
CYPHERA_TEST_TIMEOUT CYPHERA_GDB CYPHERA_DISK_IMG CYPHERA_ACCEL CYPHERA_SMP; do
[[ -n "${!var:-}" ]] && args+=(-e "$var=${!var}")
done
# The container runs as root and bind-mounts the source tree at
# /workspace. Every directory the build writes to is shadowed by a
# named volume so build artifacts land in Docker-managed storage, not
# as root-owned droppings in the host checkout. The bind mount is then
# source-only (edited on the host as the unprivileged user, read in the
# container). Test results come back over stdout / the process exit
# code, never as files on the host. The shadowed write paths:
# /workspace/target — root + kernel cargo target
# /workspace/selftests/target — selftests workspace cargo target
# /workspace/bundles — staged userland ELFs (build-userland.sh)
# /workspace/demo/.build — initrd/rootfs staged by demo/run.sh
docker run "${args[@]}" \
-v "$PROJECT_ROOT:/workspace" \
-v cyphera-kernel-cargo-registry:/usr/local/cargo/registry \
-v cyphera-kernel-cargo-git:/usr/local/cargo/git \
-v cyphera-kernel-target:/workspace/target \
-v cyphera-kernel-selftests-target:/workspace/selftests/target \
-v cyphera-kernel-bundles:/workspace/bundles \
-v cyphera-kernel-demo-build:/workspace/demo/.build \
"$IMAGE_TAG" \
"$@" < "$stdin_src"
}
usage() {
cat <<EOF
Usage: ./dev <command> [args...]
Commands:
build cargo build (debug)
build-release cargo build --release
run cargo run; boots the kernel in QEMU (Ctrl-A x to exit)
run-release cargo run --release
demo boot the kernel running a hello-world userland (see demo/)
demo-alpine boot the kernel into an interactive Alpine shell (needs network; see demo/)
build-userland build + stage the userland test-driver ELFs (bundles/userland/)
test [kind] QEMU integration battery: smoke | subsystem | all (default all)
fmt cargo fmt
clippy cargo clippy -- -D warnings
shell interactive bash inside the dev container
rebuild-image force rebuild of the dev image
clean cargo clean
EOF
}
case "${1:-}" in
build) run_in_container cargo build ;;
build-release) run_in_container cargo build --release ;;
run) run_in_container cargo run ;;
run-release) run_in_container cargo run --release ;;
demo) run_in_container ./demo/run.sh ;;
demo-alpine) run_in_container ./demo/run-alpine.sh ;;
build-userland) run_in_container ./tools/build-userland.sh ;;
test) run_in_container ./tools/test.sh "${2:-all}" ;;
fmt) run_in_container cargo fmt --all ;;
clippy) run_in_container cargo clippy -- -D warnings ;;
shell) run_in_container bash ;;
clean) run_in_container cargo clean ;;
rebuild-image)
docker rmi -f "$IMAGE_TAG" 2>/dev/null || true
ensure_image
;;
-h|--help|"") usage ;;
*) usage; exit 1 ;;
esac