Skip to content

Read the chip's IrqMask-suppressed count from native radio stats - #745

Merged
A13xB0 merged 2 commits into
MeshBench:mainfrom
NomDeTom:node-stats-irq-suppressed
Oct 13, 2026
Merged

A13xB0 merged 2 commits into
MeshBench:mainfrom
NomDeTom:node-stats-irq-suppressed

Conversation

@NomDeTom

@NomDeTom NomDeTom commented Oct 13, 2026 •

Copy link
Copy Markdown
Contributor

What this changes, and why

  • firmware.RadioStats gains IRQSuppressed and SuppressedReported, read from bytes 43-46 of a radio stats record (kindRadioStats) that is at least 47 bytes long. A shorter record leaves SuppressedReported false.
  • node.stats answers irq_suppressed for each node: the count, or null where the node's chip did not report one.
  • The Python client's NodeStat gains irq_suppressed: int | None.

The count is the number of IRQ events the chip raised that the firmware's IrqMask kept out of the status register. virtual-sx1262 keeps it from MeshBench/virtual-sx1262#2 onward (irq_suppressed in vsx_counters). The native bridge sends it in MeshBench/meshcore-native#26. Until a node sends a 47-byte record, the field is null.

Without it, a node whose firmware did not enable an interrupt and a node whose chip never raised that interrupt report the same irq_reads, busy_reads and busy_ms.

Manual: MeshBench/docs#40 (regenerated Python and control references).

Verification

  • gofmt -l .: empty.
  • go vet on internal/firmware, internal/app/session, internal/app/state: clean.
  • go test on internal/firmware, internal/app/state, internal/app/session, internal (layers and layout map): pass. The full go test ./... was not run.
  • golangci-lint v2.12.2 on the same packages: no findings in changed lines. The pre-existing findings in build.go, native.go, prefs.go and bridge.go (net.Listen) are unchanged.
  • tools/verbdoc/verbdoc.py --check: current.
  • New tests: internal/firmware/radiostats_test.go (a 47-byte record sets the count and SuppressedReported; a 43-byte record does not). Python: test_a_suppressed_count_is_none_unless_the_chip_kept_one, and an assertion in test_node_stats_carry_the_rows that a stopped node answers None.
  • Python client: ruff check and ruff format --check are clean. pytest tests/ against a binary built from this branch: 51 passed, 3 failed (test_pytest_plugin.py: test_the_meshbench_fixture_is_discovered, test_the_scenario_is_cleared_between_tests, test_a_failure_carries_the_provenance). The same three fail with this change stashed; they need the client installed as a package, and it was run from source.
  • End to end: native MeshCore 1.16.0 and 1.17.0 builds with bridge: report what the chip's IrqMask kept out meshcore-native#26 against virtual-sx1262 8fb9623, in headless runs on fife-strict (three nodes) and scotland-strict. The parsed counts reached the experiment export through the follow-up PR (Record each node's radio counters in every experiment cell #746): 1.16 nodes (IrqMask 0x0272) reported 24 and 1.17 nodes (0x0276) 12 on the three-node link.

Checklist

  • One independent change. If it is two, it is two pull requests.
  • A new package updates the layout map in CLAUDE.md in this commit. (No new package.)
  • A new dependency is justified here, in one line. (None.)
  • Files under 500 lines; new panels and widgets are one type per file.
  • A new panel joins auditTargets; a new state is reachable by flag. (No panel.)
  • docs/shortcomings.md still tells the truth after this change.
  • Every claim here is verified, not assumed — no invented verb, flag, path or result.
  • A behaviour change is covered by a test that fails without it.
  • Nothing staged that was not written or asked for — no build artifacts, nothing under security-audit/.

A chip that applies the firmware's IrqMask counts the events it had to raise
and was not allowed to. A native node can append that count to its radio
stats record as bytes 43-46; the bridge reads it when the record is at least
47 bytes long. node.stats answers it as irq_suppressed, and the Python
client's NodeStat carries it.

A record shorter than 47 bytes comes from a chip that does not count, and
irq_suppressed is then absent (None in the Python client) rather than zero.
@A13xB0

A13xB0 commented Oct 13, 2026

Copy link
Copy Markdown
Collaborator

keeping an eye

@A13xB0

A13xB0 commented Oct 13, 2026

Copy link
Copy Markdown
Collaborator

apologies for pipeline breaking... I'll fix this tomorrow at some point, its just missing tih

      - name: Headers cgo needs
        run: |
          sudo apt-get update
          sudo apt-get install -y --no-install-recommends \
            gcc pkg-config libgl1-mesa-dev xorg-dev \
            libwayland-dev libxkbcommon-dev libxkbcommon-x11-dev \
            libx11-xcb-dev libegl1-mesa-dev libvulkan-dev libffi-dev

feel free to add it if you wish to this PR or I can do it in a seperate one tomorrow

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.

2 participants