Skip to content

Commit 1624b54

Browse files
Add initial version of web configurator and web flasher tool for RS41ng firmware (#126)
* Add initial version of web configurator and web flasher tool for RS41ng firmware. Requires WebUSB support for flashing. MCU lock/unlock currently not working reliably. * Add note about WebUSB requirements and indicate WebUSB support on the first page of the web configurator * Test publishing GitHub Pages from branch * Add missing Node types to web configurator deps * Add screenshot of the web configurator in README * Fix web configurator docs
1 parent fd08aa1 commit 1624b54

132 files changed

Lines changed: 17086 additions & 181 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.github/workflows/deploy-web.yml

Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
# Builds the web configurator (web/) and deploys it to GitHub Pages.
2+
#
3+
# One-time repo setup:
4+
# Settings → Pages → Build and deployment → Source = "GitHub Actions".
5+
# The site is served at https://<owner>.github.io/<repo>/ — vite.config.ts uses
6+
# base "./" (relative paths) so it works from that subpath without further config.
7+
8+
name: Deploy web configurator
9+
10+
on:
11+
push:
12+
# TEMPORARY: web-configurator is included so Pages can be tested from the branch
13+
# before merge. Revert to `branches: [main]` once verified.
14+
branches: [main, web-configurator]
15+
paths:
16+
- "web/**"
17+
- ".github/workflows/deploy-web.yml"
18+
# Allow manual runs from the Actions tab.
19+
workflow_dispatch:
20+
21+
permissions:
22+
contents: read
23+
pages: write
24+
id-token: write
25+
26+
# Allow only one concurrent deployment; let an in-progress run finish.
27+
concurrency:
28+
group: pages
29+
cancel-in-progress: false
30+
31+
jobs:
32+
build:
33+
runs-on: ubuntu-24.04
34+
defaults:
35+
run:
36+
working-directory: web
37+
steps:
38+
- uses: actions/checkout@v4
39+
40+
# Keep this version in sync with the Dockerfile's Bun install.
41+
- uses: oven-sh/setup-bun@v2
42+
with:
43+
bun-version: 1.3.14
44+
45+
- name: Install dependencies
46+
run: bun install --frozen-lockfile
47+
48+
- name: Run tests
49+
run: bun run test
50+
51+
# `bun run build` runs vue-tsc --noEmit then vite build, so this also typechecks.
52+
- name: Build
53+
run: bun run build
54+
55+
- uses: actions/configure-pages@v5
56+
57+
- uses: actions/upload-pages-artifact@v3
58+
with:
59+
path: web/dist
60+
61+
deploy:
62+
needs: build
63+
runs-on: ubuntu-24.04
64+
environment:
65+
name: github-pages
66+
url: ${{ steps.deployment.outputs.page_url }}
67+
steps:
68+
- id: deployment
69+
uses: actions/deploy-pages@v4

.gitignore

Lines changed: 24 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,30 @@
11
/.idea
2+
/.cursor/
23
/cmake-build-debug
4+
/cmake-build-debug-arm-none-eabi
35
/build
46
/samples
57
*~
68
.vscode/
7-
.DS_Store
9+
.DS_Store
10+
11+
# Local scratch: personal configs and firmware binaries copied out of build/
12+
/temp/
13+
/*.bin
14+
15+
# User firmware config (generated from web configurator - do not commit personal config)
16+
# config.yaml.example is intentionally NOT ignored (it is the committed template).
17+
/config.yaml
18+
/config-*.yaml
19+
20+
# Local-only planning/scratch notes (not part of the repo)
21+
/tasks/
22+
23+
# Ephemeral outputs from scripts/generate_config.ts (removed after firmware POST_BUILD when used)
24+
/src/config_generated.c
25+
/src/config_generated.h
26+
27+
# Node/Bun dependencies (bun.lock files are committed — Bun is the canonical package manager)
28+
/node_modules/
29+
/web/node_modules/
30+
/web/dist/

Dockerfile

Lines changed: 12 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,25 +1,28 @@
1-
FROM fedora:36
1+
FROM fedora:43
22

33
RUN dnf install -y \
44
gcc-c++ \
55
arm-none-eabi-gcc-cs \
66
arm-none-eabi-gcc-cs-c++ \
77
arm-none-eabi-binutils-cs \
88
arm-none-eabi-newlib \
9-
cmake
9+
cmake \
10+
curl \
11+
unzip
1012

11-
COPY docker_build.sh /build.sh
12-
RUN chmod +x /build.sh
13+
# Install Bun (TypeScript runtime for config generator), pinned to match CI (deploy-web.yml)
14+
RUN curl -fsSL https://bun.sh/install | bash -s "bun-v1.3.14"
15+
ENV PATH="/root/.bun/bin:${PATH}"
1316

14-
ENTRYPOINT ["/bin/bash", "/build.sh"]
17+
# Run the build script from the mounted source tree (not a baked-in copy) so that
18+
# edits to docker_build.sh take effect without rebuilding the image. The source is
19+
# mounted at /usr/local/src/RS41ng by the build-firmware.sh / build-firmware.bat wrappers.
20+
ENTRYPOINT ["/bin/bash", "/usr/local/src/RS41ng/docker_build.sh"]
1521

1622
# FROM debian:bookworm-slim
1723

1824
# RUN apt-get -y update && \
1925
# apt-get -y install \
2026
# build-essential cmake gcc-arm-none-eabi
2127

22-
# COPY docker_build.sh /build.sh
23-
# RUN chmod +x /build.sh
24-
25-
# ENTRYPOINT ["/bin/bash", "/build.sh"]
28+
# ENTRYPOINT ["/bin/bash", "/usr/local/src/RS41ng/docker_build.sh"]

README.md

Lines changed: 235 additions & 158 deletions
Large diffs are not rendered by default.

build-firmware.bat

Lines changed: 64 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,64 @@
1+
@echo off
2+
REM Build the RS41ng firmware using the Docker build environment.
3+
REM
4+
REM Usage:
5+
REM build-firmware.bat [config-file.yaml] [extra cmake flags...]
6+
REM
7+
REM Examples:
8+
REM build-firmware.bat - use config.yaml (default)
9+
REM build-firmware.bat my-tracker.yaml - use a different config file
10+
REM build-firmware.bat -DRS41=1 - no config file; pass target flag for the built-in config
11+
REM build-firmware.bat my-tracker.yaml -DRS41=1
12+
REM
13+
REM The first argument, if it does not start with "-", selects the configuration
14+
REM YAML file (relative to this script's directory). When that file exists, the
15+
REM hardware target is derived from its hardware.type field, so no -D flag is needed.
16+
REM Any remaining arguments are forwarded to cmake. Requires the rs41ng_compiler
17+
REM Docker image (build it once with: docker build -t rs41ng_compiler .).
18+
19+
setlocal enabledelayedexpansion
20+
21+
REM Run from the repository root (where this script lives).
22+
cd /d "%~dp0"
23+
24+
set "CONFIG_FILE=config.yaml"
25+
set "CONFIG_EXPLICIT=0"
26+
27+
set "FIRST=%~1"
28+
if defined FIRST (
29+
set "LEAD=!FIRST:~0,1!"
30+
if not "!LEAD!"=="-" (
31+
set "CONFIG_FILE=%~1"
32+
set "CONFIG_EXPLICIT=1"
33+
shift
34+
)
35+
)
36+
37+
REM Collect any remaining arguments to forward to cmake.
38+
set "EXTRA_ARGS="
39+
:collect
40+
if not "%~1"=="" (
41+
set "EXTRA_ARGS=!EXTRA_ARGS! %~1"
42+
shift
43+
goto collect
44+
)
45+
46+
docker image inspect rs41ng_compiler >nul 2>&1
47+
if errorlevel 1 (
48+
echo ERROR: Docker image "rs41ng_compiler" not found. 1>&2
49+
echo Build it once with: docker build -t rs41ng_compiler . 1>&2
50+
exit /b 1
51+
)
52+
53+
if not exist "%CONFIG_FILE%" (
54+
if "%CONFIG_EXPLICIT%"=="1" (
55+
echo ERROR: config file "%CONFIG_FILE%" not found in %cd% 1>&2
56+
exit /b 1
57+
)
58+
echo No "%CONFIG_FILE%" found - building with the built-in manual configuration ^(config.h / config.c^).
59+
echo You must pass a target flag, e.g.: build-firmware.bat -DRS41=1
60+
) else (
61+
echo Using configuration file: %CONFIG_FILE%
62+
)
63+
64+
docker run --rm -it -v "%cd%:/usr/local/src/RS41ng" -e "CONFIG_FILE=%CONFIG_FILE%" rs41ng_compiler%EXTRA_ARGS%

build-firmware.sh

Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
#!/bin/bash
2+
3+
# Build the RS41ng firmware using the Docker build environment.
4+
#
5+
# Usage:
6+
# ./build-firmware.sh [config-file.yaml] [extra cmake flags...]
7+
#
8+
# Examples:
9+
# ./build-firmware.sh # use config.yaml (default)
10+
# ./build-firmware.sh my-tracker.yaml # use a different config file
11+
# ./build-firmware.sh -DRS41=1 # no config file; pass target flag for the built-in config
12+
# ./build-firmware.sh my-tracker.yaml -DRS41=1
13+
#
14+
# The first argument, if it does not start with "-", selects the configuration
15+
# YAML file (relative to this script's directory). When that file exists, the
16+
# hardware target is derived from its hardware.type field, so no -D flag is needed.
17+
# Any remaining arguments are forwarded to cmake (e.g. a -DRS41=1 target flag when
18+
# building without a config file). Requires the rs41ng_compiler Docker image
19+
# (build it once with: docker build -t rs41ng_compiler .).
20+
21+
set -e
22+
23+
# Run from the repository root (where this script lives) so the volume mount and
24+
# the config file path are resolved consistently regardless of the caller's cwd.
25+
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
26+
cd "$SCRIPT_DIR"
27+
28+
CONFIG_FILE="config.yaml"
29+
CONFIG_EXPLICIT=0
30+
if [ -n "$1" ] && [ "${1#-}" = "$1" ]; then
31+
CONFIG_FILE="$1"
32+
CONFIG_EXPLICIT=1
33+
shift
34+
fi
35+
36+
if ! docker image inspect rs41ng_compiler >/dev/null 2>&1; then
37+
echo "ERROR: Docker image 'rs41ng_compiler' not found." >&2
38+
echo "Build it once with: docker build -t rs41ng_compiler ." >&2
39+
exit 1
40+
fi
41+
42+
if [ ! -f "$CONFIG_FILE" ]; then
43+
if [ "$CONFIG_EXPLICIT" = "1" ]; then
44+
echo "ERROR: config file '$CONFIG_FILE' not found in $SCRIPT_DIR" >&2
45+
exit 1
46+
fi
47+
echo "No '$CONFIG_FILE' found - building with the built-in manual configuration (config.h / config.c)."
48+
echo "You must pass a target flag, e.g.: ./build-firmware.sh -DRS41=1"
49+
else
50+
echo "Using configuration file: $CONFIG_FILE"
51+
fi
52+
53+
docker run --rm -it \
54+
-v "$(pwd)":/usr/local/src/RS41ng \
55+
-e CONFIG_FILE="$CONFIG_FILE" \
56+
rs41ng_compiler "$@"

bun.lock

Lines changed: 31 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)