Skip to content

Commit e69f9cf

Browse files
jamesarichclaude
andauthored
docs: overhaul for org best practices and dev/usage separation (#14)
Co-authored-by: Claude Sonnet 5 <noreply@anthropic.com>
1 parent 82d979e commit e69f9cf

7 files changed

Lines changed: 190 additions & 57 deletions

File tree

.github/ISSUE_TEMPLATE/bug_report.yml

Lines changed: 43 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -10,46 +10,77 @@ body:
1010
1111
- type: dropdown
1212
attributes:
13-
label: Operating System
13+
label: Board
1414
options:
15-
- Linux
16-
- MacOS
17-
- RaspberryPi OS
18-
- Windows 7
19-
- Windows 10
20-
- Windows 11
21-
- Others
15+
- Elecrow ThinkNode M1
16+
- Elecrow ThinkNode M3
17+
- Elecrow ThinkNode M6
18+
- Heltec Automation Mesh Node T114
19+
- LilyGO T-Echo
20+
- Minewsemi MX25LE01
21+
- Nologo ProMicro NRF52840 (SuperMini NRF52840)
22+
- RAK 4631
23+
- RAK WisMesh Tag
24+
- Seeed Studio SenseCAP Card Tracker T1000-E
25+
- Seeed SenseCAP Solar Node P1
26+
- Seeed Studio Wio Tracker L1
27+
- Seeed Studio XIAO nRF52840 BLE
28+
- Seeed Studio XIAO nRF52840 BLE SENSE
29+
- Other / not listed
2230
validations:
2331
required: true
2432

33+
- type: input
34+
attributes:
35+
label: How did you flash/update the bootloader?
36+
placeholder: e.g. Meshtastic Android app (USB), manual UF2 copy, adafruit-nrfutil, nRF Connect OTA
37+
validations:
38+
required: true
39+
40+
- type: dropdown
41+
attributes:
42+
label: Operating System (of the computer/phone used to flash, if applicable)
43+
options:
44+
- Linux
45+
- macOS
46+
- Windows 10
47+
- Windows 11
48+
- Android
49+
- iOS
50+
- Not applicable
51+
- Others
52+
validations:
53+
required: false
54+
2555
- type: textarea
2656
attributes:
2757
label: INFO_UF2.TXT
58+
description: Enter UF2 mode (double-press reset) and paste the contents of INFO_UF2.TXT from the mounted drive — it identifies the exact bootloader version and board.
2859
placeholder: Paste your INFO_UF2.TXT contents here
2960
validations:
3061
required: true
3162

3263
- type: textarea
3364
attributes:
34-
label: What happened ?
65+
label: What happened?
3566
placeholder: A clear and concise description of what the bug is.
3667
validations:
3768
required: true
3869

3970
- type: textarea
4071
attributes:
41-
label: How to reproduce ?
72+
label: How to reproduce?
4273
placeholder: |
4374
1. Go to '...'
4475
2. Click on '....'
45-
3. See error
76+
3. See error
4677
validations:
4778
required: true
4879

4980
- type: textarea
5081
attributes:
5182
label: Debug Log
52-
placeholder: Debug log attached txt file.
83+
placeholder: Debug log attached as a txt file.
5384
validations:
5485
required: false
5586

.github/ISSUE_TEMPLATE/config.yml

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
1-
contact_links:
2-
- name: Adafruit Support Forum
3-
url: https://forums.adafruit.com
4-
about: If you have other questions or need help, post it here.
1+
blank_issues_enabled: false
2+
contact_links:
3+
- name: Meshtastic Discussions
4+
url: https://github.com/orgs/meshtastic/discussions
5+
about: Questions, troubleshooting, and general discussion — ask here first.
6+
- name: Meshtastic Website
7+
url: https://meshtastic.org/
8+
about: Docs and other ways to reach us.

.github/PULL_REQUEST_TEMPLATE.md

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,16 @@
11
## Checklist
22

3-
*By completing this PR sufficiently, you help us to review this Pull Request quicker and also help improve the quality of Release Notes*
3+
*By completing this PR sufficiently, you help us to review this Pull Request quicker and also help improve the quality of Release Notes.*
4+
*See [`CONTRIBUTING.md`](../CONTRIBUTING.md) for the full dev setup and PR process.*
45

5-
- [ ] Please provide specific title of the PR describing the change
6-
- [ ] If you are adding an new boards, please make sure
7-
- [ ] Provide link to your allocated VID/PID if applicable
8-
- [ ] `UF2_BOARD_ID` in your board.h follow correct format from [uf2 specs](https://github.com/microsoft/uf2#files-exposed-by-bootloaders)
6+
- [ ] PR title specifically describes the change
7+
- [ ] `tools/build_all.py` (or CI's board matrix) passes
8+
- [ ] If adding a new board, see [Adding a new board](../CONTRIBUTING.md#adding-a-new-board):
9+
- [ ] Tested on real hardware, not just compiled
10+
- [ ] Link to allocated VID/PID provided, if applicable
11+
- [ ] `UF2_BOARD_ID` in `board.h` follows the [UF2 spec](https://github.com/microsoft/uf2#files-exposed-by-bootloaders) format
912

10-
*This checklist items that are not applicable to your PR can be deleted.*
13+
*Checklist items that don't apply to your PR can be deleted.*
1114

1215
-----------
1316

AGENTS.md

Lines changed: 10 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -7,9 +7,10 @@ Canonical guidance for AI coding agents and maintainers working in this repo.
77

88
1. `README.md` — boards supported, installation, the Meshtastic Android
99
in-app upgrade flow, troubleshooting.
10-
2. `changelog.md` — OTAFIX version history (2.1/2.2 at the top; everything
10+
2. `CONTRIBUTING.md` — dev setup, PR process, adding a new board.
11+
3. `changelog.md` — OTAFIX version history (2.1/2.2 at the top; everything
1112
below predates the OTAFIX fork).
12-
3. The design invariants and gotchas below — do not violate them.
13+
4. The design invariants and gotchas below — do not violate them.
1314

1415
## What this is
1516

@@ -29,9 +30,8 @@ This is C, built with a bare Makefile (the supported path) or `CMakeLists.txt`
2930

3031
## Build
3132

32-
In the workspace, `nix develop .#otafix` gives you the full toolchain and
33-
prints these same steps. Outside the workspace, you need `arm-none-eabi-gcc`
34-
(CI pins **12.3.Rel1** exactly — see the toolchain gotcha below) and Python 3.
33+
You need `arm-none-eabi-gcc` (CI pins **12.3.Rel1** exactly — see the
34+
toolchain gotcha below) and Python 3.
3535

3636
```sh
3737
git submodule update --init --recursive # lib/nrfx, lib/tinyusb, lib/uf2 — required, not vendored inline
@@ -109,21 +109,13 @@ itself; a human has to edit it too.
109109

110110
## Gotchas
111111

112-
- **ARM GCC version matters.** CI pins exactly `12.3.Rel1`. The nixpkgs
113-
default (`gcc-arm-embedded`, 15.2.rel1 as of 2026-08) fails with
114-
`-Werror=array-bounds` in
112+
- **ARM GCC version matters.** CI pins exactly `12.3.Rel1`. Much newer
113+
toolchains (verified: 15.2.Rel1) fail with `-Werror=array-bounds` in
115114
`lib/sdk11/components/libraries/bootloader_dfu/bootloader_settings.c`
116115
(a false positive from newer GCC's stricter analysis of a fixed
117-
MBR-address read) — verified by actually building with it.
118-
`gcc-arm-embedded-13` (13.3.rel1) compiles clean and is what the
119-
workspace's `.#otafix` shell uses, being the closest verified-working
120-
version nixpkgs currently carries.
121-
- **`uv pip install` ignores an activated venv if `UV_PYTHON` is set**
122-
it targets that interpreter directly and fails with "externally managed"
123-
against the read-only Nix store path. The workspace shell deliberately
124-
does not set `UV_PYTHON` here, unlike the main `.#python` shell (which
125-
has lock files that need a pinned interpreter for reproducibility; this
126-
repo has none).
116+
MBR-address read) — verified by actually building with it. 13.3.Rel1
117+
compiles clean and is the closest verified-working version if you can't
118+
get the exact CI-pinned one.
127119
- **MeshCore/Ripple content has been deliberately removed** from the docs
128120
(README, changelog) — this is Meshtastic's own branded fork now, not a
129121
place to re-add other companion-firmware documentation. If you're

CONTRIBUTING.md

Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
# Contributing
2+
3+
Thanks for considering a contribution. This is boot-critical firmware — a
4+
broken bootloader can leave a device needing a hardware programmer to
5+
recover — so a few things here are stricter than a typical repo.
6+
7+
## Before you start
8+
9+
- **Read [`AGENTS.md`](./AGENTS.md) first.** It covers the board abstraction,
10+
the build system split (`make` vs. the incomplete `CMakeLists.txt`), the
11+
vendored submodules, and a list of known gotchas. This file covers
12+
process; that one covers the code.
13+
- **New board support needs real hardware.** `UF2_BOARD_ID`, VID/PID, and
14+
pin definitions cannot be guessed from a datasheet alone — see
15+
[Adding a new board](#adding-a-new-board) below.
16+
- **This repo is [MIT-licensed](./LICENSE)** (originally Adafruit
17+
Industries). By contributing, you agree your changes are under the same
18+
license.
19+
20+
## Building locally
21+
22+
You need `arm-none-eabi-gcc` and Python 3 installed.
23+
24+
```sh
25+
git submodule update --init --recursive # lib/nrfx, lib/tinyusb, lib/uf2 — required, not vendored inline
26+
27+
python3 -m venv .venv && source .venv/bin/activate
28+
pip install adafruit-nrfutil uritemplate requests intelhex setuptools
29+
30+
# ARM GCC 12.3.Rel1 is what CI pins (.github/workflows/githubci.yml).
31+
# Newer versions (13.x verified working, 15.x does not) can hit a
32+
# -Werror=array-bounds false positive in bootloader_settings.c — see
33+
# AGENTS.md's Gotchas section before reaching for a newer toolchain.
34+
35+
make BOARD=wiscore_rak4631_board all
36+
make BOARD=wiscore_rak4631_board copy-artifact # writes _bin/<board>/
37+
```
38+
39+
Board names are the directory names under `src/boards/`. `tools/build_all.py`
40+
builds every board and prints a pass/fail + size table — run it before
41+
opening a PR; it's the same check CI's board matrix does per-PR, just local.
42+
43+
**Use `make`, not `cmake`.** `CMakeLists.txt` only has a `board.cmake` for 2
44+
of the 14 boards; `cmake -DBOARD=<anything else>` fails outright. Nobody
45+
uses the CMake path in practice.
46+
47+
There is no lint or test suite — for a bootloader, "does it compile for
48+
every board" (CI's job) and real hardware testing are the correctness
49+
signals that exist.
50+
51+
## Adding a new board
52+
53+
The [README's board list](./README.md#boards-supported) says to raise an
54+
issue for a board you'd like supported — that's still the right first step,
55+
and [#4](https://github.com/meshtastic/Adafruit_nRF52_Bootloader_OTAFIX/issues/4)
56+
and
57+
[#5](https://github.com/meshtastic/Adafruit_nRF52_Bootloader_OTAFIX/issues/5)
58+
are open examples. To actually submit the board yourself:
59+
60+
1. You need the physical hardware to test on — a bootloader that compiles
61+
but was never flashed is not a contribution, it's a liability.
62+
2. Add `src/boards/<your-board>/board.h` and `board.mk`, following an
63+
existing board (e.g. `src/boards/wiscore_rak4631_board`) as a template.
64+
3. `UF2_BOARD_ID` must follow the format in the
65+
[UF2 spec](https://github.com/microsoft/uf2#files-exposed-by-bootloaders).
66+
If your board has an allocated VID/PID, link to it in the PR.
67+
4. Confirm `make BOARD=<your-board> all` succeeds and the resulting UF2
68+
actually boots the board correctly — not just compiles.
69+
5. The PR template has a checklist for exactly this; fill it in.
70+
71+
## Pull requests
72+
73+
- CI (`.github/workflows/githubci.yml`) builds every board in the matrix on
74+
every PR. Branch protection on `master` requires all of those checks to
75+
pass before merge.
76+
- Recent commit history is
77+
[Conventional Commits](https://www.conventionalcommits.org/)-style
78+
(`docs:`, `ci:`, `chore:`, etc.); older history (pre-fork) is looser —
79+
match the newer style going forward.
80+
- Keep PRs scoped to one change. A board addition, a docs fix, and a CI
81+
tweak are three PRs, not one.
82+
83+
## Code of Conduct and security
84+
85+
This project follows the
86+
[Meshtastic Code of Conduct](./CODE_OF_CONDUCT.md). Report security
87+
vulnerabilities privately per [`SECURITY.md`](./SECURITY.md) — not as a
88+
public issue.

README.md

Lines changed: 29 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,25 @@
11
# Meshtastic OTAFIX Bootloader
22

33
[![Build](https://github.com/meshtastic/Adafruit_nRF52_Bootloader_OTAFIX/actions/workflows/githubci.yml/badge.svg)](https://github.com/meshtastic/Adafruit_nRF52_Bootloader_OTAFIX/actions/workflows/githubci.yml)
4+
[![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](./LICENSE)
45

5-
Adafruit nRF52 bootloader with enhanced OTA DFU, forked for [Meshtastic](https://meshtastic.org) from [oltaco's OTAFIX bootloader](https://github.com/oltaco/Adafruit_nRF52_Bootloader_OTAFIX). This is the bootloader several nRF52-based Meshtastic devices ship with, and the one the [Meshtastic Android app](https://github.com/meshtastic/Meshtastic-Android) can upgrade in-app (see [Bootloader upgrade from the Meshtastic Android app](#bootloader-upgrade-from-the-meshtastic-android-app) below).
6+
Adafruit nRF52 bootloader with enhanced OTA DFU, forked for [Meshtastic](https://meshtastic.org) from [oltaco's OTAFIX bootloader](https://github.com/oltaco/Adafruit_nRF52_Bootloader_OTAFIX). This is the bootloader several nRF52-based Meshtastic devices ship with, and the one the [Meshtastic Android app](https://github.com/meshtastic/Meshtastic-Android) can upgrade in-app.
67

78
Current release: **OTAFIX 2.2** — see [changelog.md](changelog.md) for version history.
89

10+
## Contents
11+
12+
- [Boards supported](#boards-supported)
13+
- [Installation](#installation)
14+
- [Bootloader upgrade from the Meshtastic Android app](#bootloader-upgrade-from-the-meshtastic-android-app)
15+
- [Troubleshooting](#troubleshooting)
16+
- [Recommended OTA DFU settings](#recommended-ota-dfu-settings)
17+
- [Notes on Xiao NRF52840 BLE](#notes-on-xiao-nrf52840-ble)
18+
- [Notes on RAK4631 bootloader](#notes-on-rak4631-bootloader)
19+
- [Contributing](#contributing)
20+
- [Getting help](#getting-help)
21+
- [License](#license)
22+
923
---
1024

1125
## Boards supported
@@ -24,14 +38,14 @@ Current release: **OTAFIX 2.2** — see [changelog.md](changelog.md) for version
2438
- Seeed Studio XIAO nRF52840 BLE ([See note](#notes-on-xiao-nrf52840-ble))
2539
- Seeed Studio XIAO nRF52840 BLE SENSE
2640

27-
If there is another nRF52840-based Meshtastic board you would like to see supported, please raise a GitHub issue.
41+
If there is another nRF52840-based Meshtastic board you would like to see supported, please [raise a GitHub issue](https://github.com/meshtastic/Adafruit_nRF52_Bootloader_OTAFIX/issues/new/choose) — or see [Adding a new board](./CONTRIBUTING.md#adding-a-new-board) in `CONTRIBUTING.md` if you want to submit it yourself.
2842

2943
---
3044

3145
## Installation
3246

3347
The recommended way to install the bootloader is using the UF2 file.
34-
Download the UF2 file for your board (they can be found in the releases with filenames beginning with `update-`), enter UF2 mode (usually by double pressing the reset button within 0.5s) and copy the UF2 file across.
48+
Download the UF2 file for your board (they can be found in the [releases](https://github.com/meshtastic/Adafruit_nRF52_Bootloader_OTAFIX/releases) with filenames beginning with `update-`), enter UF2 mode (usually by double pressing the reset button within 0.5s) and copy the UF2 file across.
3549

3650
If an incorrect bootloader has been flashed to the device, a full bootloader and SoftDevice zip package will need to be flashed using ``adafruit-nrfutil``.
3751

@@ -139,22 +153,20 @@ This version of the RAK4631 bootloader is based on a much newer version (0.9.2)
139153

140154
---
141155

142-
## Building locally
143-
144-
The build is `make`-based; the `CMakeLists.txt` in this repo is incomplete — only `heltec_t114` and `thinknode_m1` have a `board.cmake`, so `cmake -DBOARD=<other board>` will fail with `BOARD is not defined`-style errors. Use `make`.
156+
## Contributing
145157

146-
```sh
147-
git submodule update --init --recursive
158+
Want to build from source, add a board, or submit a fix? See
159+
[`CONTRIBUTING.md`](./CONTRIBUTING.md) for the development setup and PR
160+
process, and [`AGENTS.md`](./AGENTS.md) for how the codebase is put
161+
together.
148162

149-
python3 -m venv .venv && source .venv/bin/activate
150-
pip install adafruit-nrfutil uritemplate requests intelhex setuptools
163+
## Getting help
151164

152-
# ARM GCC 12.3.Rel1 is what CI pins (.github/workflows/githubci.yml).
153-
# Newer versions (13.x tested working, 15.x does not) can hit a
154-
# -Werror=array-bounds false positive in bootloader_settings.c.
165+
- **Questions or troubleshooting:** [Meshtastic Discussions](https://github.com/orgs/meshtastic/discussions)
166+
- **Bug reports and feature requests:** [open an issue](https://github.com/meshtastic/Adafruit_nRF52_Bootloader_OTAFIX/issues/new/choose)
167+
- **Security vulnerabilities:** see [`SECURITY.md`](./SECURITY.md) — please do not open a public issue
168+
- **General Meshtastic docs:** [meshtastic.org](https://meshtastic.org/)
155169

156-
make BOARD=wiscore_rak4631_board all
157-
make BOARD=wiscore_rak4631_board copy-artifact # writes _bin/<board>/
158-
```
170+
## License
159171

160-
Board names are the directory names under `src/boards/`. `tools/build_all.py` builds every board and prints a pass/fail + size table — useful for checking a change against the full matrix before pushing, the same thing CI's board matrix does per-PR.
172+
[MIT](./LICENSE), originally Copyright (c) 2016 Adafruit Industries.

changelog.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
# Adafruit nRF52 Bootloader Changelog
22

3+
OTAFIX 2.1 and 2.2 are Meshtastic's fork; everything from 0.6.2 down predates
4+
it and is upstream Adafruit history, kept for provenance.
5+
36
## OTAFIX 2.2
47

58
- Use maximum TX power for BLE: BLE TX power set to +8 for nRF52840.

0 commit comments

Comments
 (0)