Skip to content

Commit 761c4b2

Browse files
committed
Add GitHub Actions CI to build and test via QEMU
This commit introduces a GitHub Actions workflow to build the Linmo kernel using the GNU RISC-V toolchain and run selected applications (e.g., cpubench) using QEMU. Test output is extracted from QEMU logs and automatically posted as a comment to pull requests. Toolchain setup, kernel build, and QEMU test execution have been modularized into reusable scripts under the `.ci/` directory. Features: - CI supports running multiple apps in a single job - All QEMU runs are time-limited to prevent hangs - Results are reported directly to GitHub PRs Limitations: - Only GNU toolchain is supported (LLVM is a work in progress) - Some test apps (e.g., cpubench) do not exit cleanly due to entering preemptive scheduler mode Fixes: #2 Supersedes: #11
1 parent 9679c50 commit 761c4b2

File tree

3 files changed

+119
-0
lines changed

3 files changed

+119
-0
lines changed

.ci/run-qemu-tests.sh

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
#!/bin/bash
2+
set -e
3+
export CROSS_COMPILE=${CROSS_COMPILE:-riscv32-unknown-elf-}
4+
5+
# Check if at least one app is provided
6+
if [ $# -eq 0 ]; then
7+
echo "Usage: $0 <app1> [app2] [app3] ..."
8+
echo "Example: $0 hello echo cpubench"
9+
exit 1
10+
fi
11+
12+
APPS="$@"
13+
TIMEOUT=10
14+
15+
echo "[+] Will run apps: $APPS"
16+
echo ""
17+
18+
# Loop through each app
19+
for app in $APPS; do
20+
echo "=== Running $app ==="
21+
22+
# Build the app
23+
echo "[+] Building $app..."
24+
make clean >/dev/null 2>&1
25+
if ! make "$app" >/dev/null 2>&1; then
26+
echo "[!] Failed to build $app"
27+
echo ""
28+
continue
29+
fi
30+
31+
# Run in QEMU with timeout
32+
echo "[+] Running $app in QEMU (timeout: ${TIMEOUT}s)..."
33+
set +e
34+
timeout ${TIMEOUT}s qemu-system-riscv32 -nographic -machine virt -bios none -kernel build/image.elf
35+
exit_code=$?
36+
set -e
37+
38+
# Print result
39+
if [ $exit_code -eq 124 ]; then
40+
echo "[!] $app timed out"
41+
elif [ $exit_code -eq 0 ]; then
42+
echo "[✓] $app completed successfully"
43+
else
44+
echo "[!] $app failed with exit code $exit_code"
45+
fi
46+
echo ""
47+
done
48+
49+
echo "[+] All apps tested"

.ci/setup-toolchain.sh

Lines changed: 11 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,11 @@
1+
#!/bin/bash
2+
set -e
3+
4+
URL="https://github.com/riscv-collab/riscv-gnu-toolchain/releases/download/2025.06.13/riscv32-elf-ubuntu-22.04-gcc-nightly-2025.06.13-nightly.tar.xz"
5+
6+
echo "[+] Downloading RISC-V GNU toolchain..."
7+
wget "$URL"
8+
tar -xf "$(basename "$URL")"
9+
10+
echo "[+] Exporting toolchain path..."
11+
echo "$PWD/riscv/bin" >> "$GITHUB_PATH"

.github/workflows/ci.yml

Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
name: Linmo CI
2+
3+
on:
4+
push:
5+
branches: [main, ci]
6+
pull_request:
7+
branches: [main, ci]
8+
9+
jobs:
10+
basic-tests:
11+
runs-on: ubuntu-24.04
12+
name: Basic Tests
13+
14+
steps:
15+
- name: Checkout
16+
uses: actions/checkout@v4
17+
18+
- name: Install dependencies
19+
run: |
20+
sudo apt-get update
21+
sudo apt-get install -y build-essential qemu-system-riscv32 wget
22+
23+
- name: Setup RISC-V Toolchain
24+
run: .ci/setup-toolchain.sh
25+
26+
- name: Verify toolchain installation
27+
run: |
28+
riscv32-unknown-elf-gcc --version
29+
qemu-system-riscv32 --version
30+
env:
31+
CROSS_COMPILE: riscv32-unknown-elf-
32+
33+
- name: Build Kernel
34+
run: |
35+
make clean
36+
make
37+
env:
38+
CROSS_COMPILE: riscv32-unknown-elf-
39+
40+
- name: Run Basic Apps
41+
id: test
42+
run: |
43+
output=$(.ci/run-qemu-tests.sh cpubench test64)
44+
echo "TEST_OUTPUT<<EOF" >> $GITHUB_OUTPUT
45+
echo "$output" >> $GITHUB_OUTPUT
46+
echo "EOF" >> $GITHUB_OUTPUT
47+
48+
- name: Comment PR with results
49+
if: github.event_name == 'pull_request'
50+
uses: actions/github-script@v7
51+
with:
52+
script: |
53+
const output = `${{ steps.test.outputs.TEST_OUTPUT }}`;
54+
github.rest.issues.createComment({
55+
issue_number: context.issue.number,
56+
owner: context.repo.owner,
57+
repo: context.repo.repo,
58+
body: `## Linmo QEMU App Test Result\n\n\`\`\`\n${output}\n\`\`\`\n\n_This is an automated report from CI._`
59+
});

0 commit comments

Comments
 (0)