Skip to content

fix(tx16s): keep all code executed during USB sessions in flash bank 1 (PA12 errata)#7557

Open
AdsumSOK wants to merge 10 commits into
EdgeTX:mainfrom
AdsumSOK:pr/tx16s-code-bank1
Open

fix(tx16s): keep all code executed during USB sessions in flash bank 1 (PA12 errata)#7557
AdsumSOK wants to merge 10 commits into
EdgeTX:mainfrom
AdsumSOK:pr/tx16s-code-bank1

Conversation

@AdsumSOK

@AdsumSOK AdsumSOK commented Jul 14, 2026

Copy link
Copy Markdown

Fixes #5899, related to #7356. Supersedes #7554 (its two commits are included here), as discussed in the plan comment.

Problem

On early TX16S MK1 units (STM32F429, flash rev < 3), toggling PA12 (USB D+) during an active USB session couples noise into the flash read path when bank 2 (0x08100000+) is accessed simultaneously (ST errata ES0166 §2.4.6, "no fix planned"). Corrupted instruction fetches then fault or hang in random ISRs — the long-standing "radio crashes/reboots to DFU when USB is plugged" issue. Diagnosed independently with persistent fault capture (3 captured crashes, all faulting on fetches above 0x08100000) and by @ulph0's MPU-fence experiments on #5899; both analyses converge.

Because any bank 2 read during USB is a potential crash vector (thread mode included), moving only the hot interrupt path to RAM (#7554) improved things (55 s → 24 min under MSC stress) but could not be a guarantee: every rebuild redistributes code across the bank boundary.

Fix: deterministic layout, enforced by the linker

  1. All code that may run during a USB session lives in bank 1. The FLASH region is restricted to bank 1 (1024K), so any overflow is a link error, not a lottery. UI code and its rodata (gui/colorlcd, lvgl, libopenui — ~613K) and cold assets (.flash, 165K) are placed in bank 2 through a new per-target pre_text_sections.ld (.uicode output section, claimed before the .text catch-all). Non-F429 targets get an empty file: zero layout change for them. Bank 1 sits at ~804K/1024K, bank 2 at ~778K/1024K.
  2. C++ comdats are pinned. Template instantiations shared by UI and core objects survive in a single copy whose home depends on link order; .text.shared claims the std:: comdats into bank 1 (with a dedicated startup copy, no-op on XIP targets), and .text.pinned pins individual symbols called from non-UI contexts, found by the call scan: lv_tick_inc (called from SysTick every 1 ms), the R9M inline helpers (pulses, every mixer cycle), the deferred-popup mailbox (telemetry/logs timers), setRequestedMainView (SET_SCREEN special function), cancelShutdownAnimation (see below).
  3. The UI is frozen while a USB session is active (colorlcd): a static USB screen naming the active mode is rendered before usbStart(), then perMain() returns early until unplug — for all three modes (mass storage used to keep LVGL running). Blocking popups are guarded, and a power long-press during USB now tears the session down first (usbSessionForceStop(), same cleanup as an unplug) so the bank 2 shutdown UI only runs once PA12 is quiet — trade-off: no confirmation dialog in that case.
  4. Kept from fix(tx16s): execute USB/SD interrupt-path code from RAM (USB->DFU crash on some MK1 units) #7554: hot USB/SD interrupt code executes from RAM (.fastcode). Plus a HID race fix (analysis by @ulph0): the joystick report buffer is no longer rewritten while the previous transfer is still in flight.

Verification

  • tools/check_bank1.sh runs after every build: no executable section in bank 2 except .uicode, USB handlers in RAM, and no direct call path into bank 2 from 56 USB-active roots (ISRs, mixer, audio, FreeRTOS timer callbacks, pwrCheck, head of perMain), with a per-edge whitelist for runtime-guarded paths.
  • tools/test_invariance.sh proves the guarantee is structural: two deliberately shifted builds (+8K core, +8K UI + swapped link order) must pass the same checks.
  • -DDIAG_BANK2_FENCE=ON (validation builds) arms an MPU no-access region over bank 2 for the whole USB session — any stray access, including through function pointers invisible to the static scan, traps deterministically; the fault handler stores the faulting address in RTC backup registers and the next boot appends it to /bank2fence.log on the SD card.

The fence proved itself immediately: the first on-radio test trapped pwrCheck()cancelShutdownAnimation()polled from menusTask every 50 ms during any USB session, a strong candidate for the historical randomness. After fixing it, on an affected early MK1:

Notes / open questions

  • The firmware image now spans both banks with a gap (bin ≈ 1.8 MB, gap filled); _firmware_length covers the full span for UF2/fw_desc consumers.
  • Should this be gated behind a build flag (e.g. EARLY_MK1_FLASH_ERRATA) instead of applying to all F429 targets? The bank 1 placement costs nothing on healthy units; the UI freeze during USB is the behavioral part worth discussing.
  • tools/check_bank1.sh could be wired into CI for the TX16S target to make the layout guarantee permanent.

🤖 Generated with Claude Code

Summary by CodeRabbit

  • Bug Fixes

    • Improved USB session handling, including cleaner shutdown behavior and a stable USB status screen.
    • Prevented UI popups and shutdown animations from interrupting active USB transfers.
    • Reduced redundant USB joystick reports when the host is not ready.
    • Improved firmware memory placement and startup reliability across supported STM32 hardware.
  • Diagnostics

    • Added optional safeguards and post-mortem reporting to help identify memory-access faults during USB use.

AdsumSOK and others added 10 commits July 14, 2026 13:24
On some TX16S MK1 units, instruction fetches from the upper flash
bank return corrupted data under heavy IRQ/DMA load. USB joystick or
mass-storage traffic then hard-faults inside the OTG/DMA interrupt
handlers (UNDEFINSTR/NOCP on provably valid instructions) and the
radio reboots into DFU. This is the long-standing "radio switches to
DFU when plugged into USB" issue (EdgeTX#5899, EdgeTX#7356, EdgeTX#6047, EdgeTX#6414): unit-
dependent (marginal flash), version-dependent (the linker moves the
hot handlers across the bank boundary as the firmware grows), and the
bootloader is immune (its code sits at the start of bank 1).

Fix: link the USB device stack, PCD/LL drivers, MSC storage glue and
SDIO diskio into a .fastcode section placed in RAM (copied at
startup, ~14KB), so the hot interrupt paths never fetch from flash.

Validated on an affected TX16S: continuous mass-storage stress-reads
crashed after ~1 min with the code in flash, and ran clean with the
code in RAM (same flash config otherwise).

Build with -DNO_LTO=ON (or drop -flto from the USB object libraries):
linker file-pattern matching cannot see through LTO partitions.
Linker-script file-pattern matching (used by the .fastcode RAM
section) cannot see through LTO partitions; without this the hot
interrupt code silently stays in flash.
On some STM32F42x units (flash rev < 3), USB D+ (PA12) switching
noise corrupts reads from flash bank 2 (ST errata ES0166 §2.4.6,
EdgeTX#5899). Restrict the FLASH region to bank 1 (overflow = link
error) and relegate UI code/rodata (.uicode: colorlcd, lvgl,
libopenui) and assets (.flash) to bank 2 via a per-target
pre_text_sections.ld, claimed before the .text catch-all.

Shared C++ comdats (std::) are pinned to bank 1 (.text.shared) with
their own startup copy (no-op on XIP targets), so link order can
never strand a template instantiation used by hot code in bank 2.
Symbols called from non-UI tasks but living in UI objects
(lv_tick_inc from SysTick, R9M inline helpers from the pulses path,
popup mailbox from telemetry/log timers, SET_SCREEN from the mixer)
are pinned individually (.text.pinned).

bench/check_bank1.sh verifies after every link: no executable
section in bank 2 except .uicode, USB handlers in RAM, and no direct
call path from USB-active contexts (ISRs, mixer, audio, timers,
perMain head) into bank 2.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
All UI code lives in flash bank 2 which must not be read during USB
traffic (PA12 errata). Draw a static USB screen before usbStart()
for every mode (mass storage included: LVGL used to keep running
during MSC), then return early from perMain() until unplug. The
blocking popup dialogs are also guarded so audio/telemetry callers
cannot start a nested UI loop while frozen.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
usbJoystickUpdate() used to rewrite the report buffer and re-arm the
IN endpoint at mixer rate even when the previous transfer was still
pending, corrupting the DMA buffer mid-transmit and hammering the
endpoint (analysis by ulph0, EdgeTX#5899). Skip the update until the
endpoint is idle; covers both the legacy and USBJ_EX paths.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Validation builds (-DDIAG_BANK2_FENCE=ON) arm an MPU no-access
region over flash bank 2 for the whole USB session: any stray access
— including through function pointers invisible to the static scan —
traps deterministically instead of corrupting reads probabilistically
(technique proven by ulph0's experiments, EdgeTX#5899). The
MemManage handler stores 0xB2FE0000|CFSR and the faulting address in
RTC backup registers BKP4R/BKP5R (survive the reset) and reboots.

Also adds bench/test_invariance.sh: two deliberately shifted builds
(core/UI padding, swapped UI link order) that must both pass
bench/check_bank1.sh, proving the layout guarantee is structural.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The stock HardFault handler returns into the fault without a
debugger; record fence traps escalated to HardFault (magic 0xB2FA)
like MemManage ones (0xB2FE) and reboot. On the next boot with
storage up, append the trap to /bank2fence.log and clear the marker
— the backup registers survive resets and power cycles (RTC cell).

Scan: root every FreeRTOS timer callback (the timer-task dispatch is
indirect, per10ms & co were unaudited) and reject roots living in
bank 2 (UI callbacks caught by a broad pattern are frozen contexts,
not hot ones).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
First on-radio fence trap (IACCVIOL @ cancelShutdownAnimation):
pwrCheck(), polled by menusTask every 50ms even while the UI is
frozen, fetched bank 2 code on every cycle of a USB session through
its button-released branch — a strong candidate for the historical
random crashes (EdgeTX#5899).

Power long-press during USB now tears the session down first
(usbSessionForceStop, same cleanup as an unplug — factored out of
handleUsbConnection): with PA12 quiet, the bank 2 shutdown UI is
safe again. The shutdown animation is skipped while frozen and
cancelShutdownAnimation is pinned to bank 1. Deliberate trade-off:
long-press during USB powers off without the confirmation dialog.

Scan: root menusTask/pwrCheck and every FreeRTOS timer callback,
add per-edge whitelist for runtime-guarded paths.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The same static screen serves all three USB modes; with only the
mass-storage icon, a joystick session reads as the wrong mode being
active (confused a tester into power-cycling the radio mid-session).

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
The emergency-mode screen is now drawn directly from menusTask at
boot (before any USB session can exist): whitelist that edge.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
@coderabbitai

coderabbitai Bot commented Jul 14, 2026

Copy link
Copy Markdown

Review Change Stack

📝 Walkthrough

Walkthrough

The PR adds STM32 linker sections and asset-bank mappings, relocates selected code at reset, freezes the COLORLCD UI during USB sessions, introduces optional bank-2 MPU diagnostics, improves HID readiness handling, and adds post-link bank-placement and invariance verification scripts.

Changes

STM32 linker layout and relocation

Layer / File(s) Summary
Linker sections, asset regions, and startup relocation
radio/src/boards/generic_stm32/linker/*, radio/src/targets/common/arm/stm32/system_init.c, radio/src/bootloader/CMakeLists.txt
Adds .fastcode and .text.shared, target asset-region aliases, F429 bank splitting and UI placement, default linker symbols, LTO exclusions, and reset-time section copying.

USB session and UI behavior

Layer / File(s) Summary
USB lifecycle, UI freezing, and HID readiness
radio/src/main.cpp, radio/src/edgetx.cpp, radio/src/gui/colorlcd/libui/popups.cpp, radio/src/targets/common/arm/stm32/usb_driver.cpp, radio/src/targets/common/arm/stm32/usbd_hid_joystick.c, radio/src/thirdparty/.../usbd_hid.h
Adds centralized USB cleanup, frozen USB screens, COLORLCD UI guards, shutdown handling, popup suppression, and HID endpoint readiness checks.

Bank-2 diagnostics

Layer / File(s) Summary
MPU fence and post-mortem capture
radio/src/targets/common/arm/stm32/bank2_fence.c, radio/src/targets/common/arm/stm32/cortex_m_isr.c, radio/src/targets/common/arm/stm32/usb_driver.cpp, radio/src/targets/horus/CMakeLists.txt
Adds optional bank-2 fencing during USB, fault capture through MemManage and HardFault paths, RTC marker storage, reboot-time logging, and build wiring.

Bank-1 verification

Layer / File(s) Summary
ELF placement and invariance checks
tools/check_bank1.sh, tools/test_invariance.sh
Validates executable placement, interrupt-handler RAM placement, direct-call reachability, and layout stability under padding and source-order perturbations.

Estimated code review effort: 5 (Critical) | ~120 minutes

Suggested labels: compilation, bug/regression ↩️

Suggested reviewers: raphaelcoeffic, philmoz

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 28.57% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly reflects the main change: keeping USB-session code in flash bank 1 for the TX16S PA12 errata.
Description check ✅ Passed The description is detailed and covers the problem, fix, verification, and issue links, though it doesn't use the template's exact Summary of changes heading.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
radio/src/edgetx.cpp (1)

1511-1520: 🩺 Stability & Availability | 🟠 Major | ⚡ Quick win

Move bank2FenceDumpPostMortem() out of the !UNEXPECTED_SHUTDOWN() guard
UNEXPECTED_SHUTDOWN() is the fault-reboot path, so this diagnostic is skipped on the very boot it is meant to report. Keep the SD init guarded if needed, but call the post-mortem dump independently.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@radio/src/edgetx.cpp` around lines 1511 - 1520, Move the
bank2FenceDumpPostMortem() call outside the !UNEXPECTED_SHUTDOWN() block so it
runs during fault-reboot boots as well. Keep sdMounted() and sdInit() within the
existing guard, and preserve the DIAG_BANK2_FENCE conditional compilation around
the diagnostic call.
🧹 Nitpick comments (5)
radio/src/targets/common/arm/stm32/bank2_fence.c (1)

112-130: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Enable PWR clock before reading from the Backup domain.

While read access to the RTC backup registers does not strictly require the Backup Domain write protection (DBP) to be cleared, reading them before ensuring the PWR clock is enabled can lead to subtle issues or bus faults on certain STM32 families if the initialization sequence is ever changed. It is safer to enable the PWR clock at the very beginning of the function.

🛠️ Proposed refactor
 void bank2FenceDumpPostMortem(void)
 {
+  __HAL_RCC_PWR_CLK_ENABLE();
   uint32_t r4 = RTC->BKP4R;
   uint32_t hi = r4 & 0xFFFF0000UL;
   if (hi != 0xB2FE0000UL && hi != 0xB2FA0000UL) return;
 
   FIL f;
   if (f_open(&f, "/bank2fence.log", FA_WRITE | FA_OPEN_APPEND) == FR_OK) {
     f_printf(&f, "%s cfsr=%04X addr=%08lX\n",
              (hi == 0xB2FE0000UL) ? "MEMMANAGE" : "HARDFAULT",
              (unsigned)(r4 & 0xFFFF), (unsigned long)RTC->BKP5R);
     f_close(&f);
   }
 
-  __HAL_RCC_PWR_CLK_ENABLE();
   SET_BIT(PWR->CR, PWR_CR_DBP);
   RTC->BKP4R = 0;
   RTC->BKP5R = 0;
 }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@radio/src/targets/common/arm/stm32/bank2_fence.c` around lines 112 - 130,
Move __HAL_RCC_PWR_CLK_ENABLE() to the beginning of bank2FenceDumpPostMortem,
before reading RTC->BKP4R. Keep the existing fault filtering, logging, and
backup-register clearing behavior unchanged.
radio/src/edgetx.cpp (1)

39-48: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Move usbSessionForceStop() declaration to a shared header.

It's declared manually here as a raw prototype but defined in main.cpp. Since hal/usb_driver.h already exports the related usbPlugged()/getSelectedUsbMode() primitives (used by popups.cpp), declaring this there too would avoid signature drift risk between the two TUs.

♻️ Suggested move
-#if defined(STM32) && !defined(SIMU)
-void usbSessionForceStop();
-#else
-inline void usbSessionForceStop() {}
-#endif
+#include "hal/usb_driver.h" // declares usbSessionForceStop()
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@radio/src/edgetx.cpp` around lines 39 - 48, Move the usbSessionForceStop()
declaration from edgetx.cpp into the shared hal/usb_driver.h header alongside
usbPlugged() and getSelectedUsbMode(), preserving the existing STM32/non-SIMU
availability behavior and removing the local raw prototype.
radio/src/gui/colorlcd/libui/popups.cpp (1)

44-66: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

The USB-session "UI frozen" predicate is duplicated raw across three files instead of sharing one helper. All three sites encode the same safety-critical PA12/bank-2 condition (usbPlugged() && getSelectedUsbMode() != USB_UNSELECTED_MODE, or its negation), risking silent drift if one site is updated without the others.

  • radio/src/gui/colorlcd/libui/popups.cpp#L44-L66: promote _usb_ui_frozen() out of static file scope (e.g. expose it as an inline function via hal/usb_driver.h) so it becomes the single source of truth.
  • radio/src/main.cpp#L592-L601: replace the raw usbPlugged() && getSelectedUsbMode() != USB_UNSELECTED_MODE check with the shared helper.
  • radio/src/edgetx.cpp#L1822-L1950: replace the repeated negated checks (usbConfirmed init, the shutdown-animation draw guard, and the release-branch cancelShutdownAnimation() guard) with calls to the shared helper.
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@radio/src/gui/colorlcd/libui/popups.cpp` around lines 44 - 66, Promote
_usb_ui_frozen() from popups.cpp file scope into the shared USB header,
preserving its platform-specific USB-session predicate and inline behavior. In
radio/src/gui/colorlcd/libui/popups.cpp lines 44-66, use the shared declaration
without redefining it; in radio/src/main.cpp lines 592-601, replace the raw USB
condition with _usb_ui_frozen(); and in radio/src/edgetx.cpp lines 1822-1950,
replace the repeated negated checks for usbConfirmed initialization,
shutdown-animation drawing, and cancelShutdownAnimation() with the shared
helper.
radio/src/boards/generic_stm32/linker/firmware.ld (1)

41-59: 🚀 Performance & Scalability | 🔵 Trivial

Confirm RAM budget on non-TX16S targets.

.fastcode (RAM-resident copy of ll_usb/hal_pcd/usb_driver/usbd_*/diskio_sdio code) is defined here in the shared firmware.ld, so it applies to every STM32 target that includes this script — not only the TX16S/F429 unit affected by the PA12/bank-2 erratum. On RAM-constrained targets (e.g. F20x with 128K total RAM), this permanently reserves extra RAM for code that didn't need relocation there. Worth confirming link/map-file RAM headroom on the smaller targets isn't eroded by this addition.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@radio/src/boards/generic_stm32/linker/firmware.ld` around lines 41 - 59,
Verify the .fastcode placement and size against linker map files for every
non-TX16S target using firmware.ld, especially RAM-constrained F20x devices.
Confirm REGION_BSS retains sufficient headroom after relocating the listed USB
and diskio_sdio sections; if not, limit this section to the affected target or
adjust the placement without impacting required TX16S behavior.
tools/test_invariance.sh (1)

33-33: 📐 Maintainability & Code Quality | 🔵 Trivial | 💤 Low value

Quote the command substitution to prevent word splitting.

It is recommended to double-quote the output of the command substitutions to prevent unintended word splitting and address the static analysis warnings.

♻️ Proposed refactor
-  docker run --rm -u $(id -u):$(id -g) -v "$(pwd)":/src -w /src \
+  docker run --rm -u "$(id -u):$(id -g)" -v "$(pwd)":/src -w /src \
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@tools/test_invariance.sh` at line 33, Update the docker run command in
test_invariance.sh to quote the id command substitutions for both user and group
values, preventing word splitting while preserving the existing volume and
working-directory behavior.

Source: Linters/SAST tools

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Outside diff comments:
In `@radio/src/edgetx.cpp`:
- Around line 1511-1520: Move the bank2FenceDumpPostMortem() call outside the
!UNEXPECTED_SHUTDOWN() block so it runs during fault-reboot boots as well. Keep
sdMounted() and sdInit() within the existing guard, and preserve the
DIAG_BANK2_FENCE conditional compilation around the diagnostic call.

---

Nitpick comments:
In `@radio/src/boards/generic_stm32/linker/firmware.ld`:
- Around line 41-59: Verify the .fastcode placement and size against linker map
files for every non-TX16S target using firmware.ld, especially RAM-constrained
F20x devices. Confirm REGION_BSS retains sufficient headroom after relocating
the listed USB and diskio_sdio sections; if not, limit this section to the
affected target or adjust the placement without impacting required TX16S
behavior.

In `@radio/src/edgetx.cpp`:
- Around line 39-48: Move the usbSessionForceStop() declaration from edgetx.cpp
into the shared hal/usb_driver.h header alongside usbPlugged() and
getSelectedUsbMode(), preserving the existing STM32/non-SIMU availability
behavior and removing the local raw prototype.

In `@radio/src/gui/colorlcd/libui/popups.cpp`:
- Around line 44-66: Promote _usb_ui_frozen() from popups.cpp file scope into
the shared USB header, preserving its platform-specific USB-session predicate
and inline behavior. In radio/src/gui/colorlcd/libui/popups.cpp lines 44-66, use
the shared declaration without redefining it; in radio/src/main.cpp lines
592-601, replace the raw USB condition with _usb_ui_frozen(); and in
radio/src/edgetx.cpp lines 1822-1950, replace the repeated negated checks for
usbConfirmed initialization, shutdown-animation drawing, and
cancelShutdownAnimation() with the shared helper.

In `@radio/src/targets/common/arm/stm32/bank2_fence.c`:
- Around line 112-130: Move __HAL_RCC_PWR_CLK_ENABLE() to the beginning of
bank2FenceDumpPostMortem, before reading RTC->BKP4R. Keep the existing fault
filtering, logging, and backup-register clearing behavior unchanged.

In `@tools/test_invariance.sh`:
- Line 33: Update the docker run command in test_invariance.sh to quote the id
command substitutions for both user and group values, preventing word splitting
while preserving the existing volume and working-directory behavior.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 96c52f6c-e7a0-4174-82e9-d67ce956438b

📥 Commits

Reviewing files that changed from the base of the PR and between f9abdcb and 30361bf.

📒 Files selected for processing (28)
  • radio/src/boards/generic_stm32/linker/definitions.ld
  • radio/src/boards/generic_stm32/linker/firmware.ld
  • radio/src/boards/generic_stm32/linker/stm32f20x/layout.ld
  • radio/src/boards/generic_stm32/linker/stm32f20x/pre_text_sections.ld
  • radio/src/boards/generic_stm32/linker/stm32f40x/layout.ld
  • radio/src/boards/generic_stm32/linker/stm32f40x/pre_text_sections.ld
  • radio/src/boards/generic_stm32/linker/stm32f413/layout.ld
  • radio/src/boards/generic_stm32/linker/stm32f413/pre_text_sections.ld
  • radio/src/boards/generic_stm32/linker/stm32f429_sdram/layout.ld
  • radio/src/boards/generic_stm32/linker/stm32f429_sdram/pre_text_sections.ld
  • radio/src/boards/generic_stm32/linker/stm32h750_sdram/layout.ld
  • radio/src/boards/generic_stm32/linker/stm32h750_sdram/pre_text_sections.ld
  • radio/src/boards/generic_stm32/linker/stm32h7rs_sdram/layout.ld
  • radio/src/boards/generic_stm32/linker/stm32h7rs_sdram/pre_text_sections.ld
  • radio/src/bootloader/CMakeLists.txt
  • radio/src/edgetx.cpp
  • radio/src/gui/colorlcd/libui/popups.cpp
  • radio/src/main.cpp
  • radio/src/targets/common/arm/stm32/bank2_fence.c
  • radio/src/targets/common/arm/stm32/cortex_m_isr.c
  • radio/src/targets/common/arm/stm32/f4/CMakeLists.txt
  • radio/src/targets/common/arm/stm32/system_init.c
  • radio/src/targets/common/arm/stm32/usb_driver.cpp
  • radio/src/targets/common/arm/stm32/usbd_hid_joystick.c
  • radio/src/targets/horus/CMakeLists.txt
  • radio/src/thirdparty/STM32_USB_Device_Library/Class/HID/Inc/usbd_hid.h
  • tools/check_bank1.sh
  • tools/test_invariance.sh

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Whilst powered on and inserting USB lead connected to pc, radio powers off every time 2.11.0 RC

1 participant