Repository navigation
Testing and QA
What a TrayIconGuard change has to pass before it ships. Every gate below is executed, not aspirational; the evidence quoted is from 8.6.3 (2026-10-16, Windows 11 build 26300 + CI).
| # | Gate | How it is executed | What it catches |
|---|---|---|---|
| 1 | Warning-free build |
./scripts/build.sh — GCC -Wall -Wextra; MSVC /W4 /permissive- in CI |
new diagnostics, implicit conversions |
| 2 | Manifest gate |
resources/app.manifest parses, supportedOS GUIDs unique, exactly one RT_MANIFEST(id 1) (checked with pefile) |
the Win11 "side-by-side configuration is incorrect" failure class |
| 3 | Dependency audit |
x86_64-w64-mingw32-objdump -p dist/TrayIconGuard.exe → only the OS allow-list |
accidental runtime dependencies (the product promise is a single exe) |
| 4 | Static analysis | cppcheck --enable=warning,performance,portability src |
shadowed members, missed initialisers |
| 5 | CLI matrix | every verb with its exit code — and with redirection: --status --json > state.json, --help > help.txt, --bogus → error: …, exit 1 |
output written to the console only, silently discarded when stdout was a pipe or a file. A console-only check cannot see it, and wine does not reproduce it |
| 6 | GUI smoke |
TrayIconGuard.exe --ui-test <page> writes %TEMP%\tig-uitest-<page>.png; all 7 pages × light/dark, plus both wizard variants |
layout and painting regressions (e.g. the 8.4.1 About z-order bug) |
| 7 | Updater end-to-end | loopback feed: download → SHA-256 → rename chain (.old) → relaunch, exit 0; live feed: --check-update → latest=<ver> newer=no
|
feed/asset drift, broken self-replacement |
| 8 | Publication check | release assets exist, and scripts/make_feed.py pins the feed from the served bytes |
a feed whose sha256 does not match the asset the client downloads |
| 9 | Guard event-driven E2E | run --watch with the default pollMs: 0, force IsPromoted = 0 on a real icon, expect it restored within a few seconds |
the 8.3.0–8.6.2 defect where the armed registry notification was never awaited and the loop never ran a pass |
- Real-Windows behaviours wine cannot model: tray menu interaction, notification balloons, MSIX registration, per-monitor DPI, SmartScreen reputation.
- Code signing and reputation: see Installation and Deployment.
.github/workflows/ci.yml runs on every push and every v* tag:
- Cross-build (ubuntu, mingw-w64, static): gates 1–3;
- Native build (windows-2022, MSVC): compile parity;
-
Release (tags only): normalize + upload the three assets, then run the feed job that
regenerates and commits
update/stable.jsonfrom those bytes.
-
--status --jsonpiped throughConvertFrom-Json(see the 8.6.2 fix). -
--check-updateafter an update printsnewer=no— no update loop. - Unknown argument exits 1 with a message.
-
--version,--status, About diagnostics and the PE resource all agree on the version. -
--watchwithpollMs: 0re-promotes an icon whoseIsPromotedwas forced to 0 (8.6.3+; on 8.6.2 and earlier the value simply stays 0 — see The Guard Watcher).
- Building from Source — the exact toolchain recipes
- Self-Updater Guide — the feed contract and its E2E test
- Independent-Audits — what was audited and what was not
The redirected-output defect survived one release because it was verified on the wrong kind of
build. TrayIconGuard.exe ships as a GUI-subsystem binary (add_executable(… WIN32 …) →
WINDOWS_GUI); a hand-rolled g++ build without -mwindows produces a console binary
(WINDOWS_CUI), where stdout is a real console/pipe handle and the defect simply does not
appear. The GUI binary attaches to the parent console with AttachConsole, which replaces
the process's standard handles — so a redirected stdout has to be saved before the call and
restored with SetStdHandle afterwards (8.6.2).
Check the subsystem before trusting a CLI test:
# Subsystem field of the PE optional header: 2 = WINDOWS_GUI, 3 = WINDOWS_CUI
$b=[IO.File]::ReadAllBytes('.\\dist\\TrayIconGuard.exe'); $pe=[BitConverter]::ToInt32($b,0x3C)
[BitConverter]::ToUInt16($b,$pe+24+68)TrayIconGuard · feed 8.6.3 / source tree 8.6.3 (see Changelog and Versioning) · PolyForm Noncommercial 1.0.0 · Repository · Report an issue · Home · Glossary · FAQ · Troubleshooting
Every claim in this wiki is traced to a source line at commit 124e849 or reproduced by
executing the program (build + Wine battery, 2026-10-16); measured discrepancies between
documentation, source and shipped binaries are documented, not smoothed over.
Home Getting Started Features Overview Comparison with Alternatives
Installation and Deployment Configuration Reference Command-Line Interface
How Tray Visibility Works Legacy Script Editions The Guard Watcher
GUI Pages Guide Backups and Snapshots Localization and Themes Self-Updater Guide Security and Privacy Troubleshooting
Architecture Roadmap and Ideas Independent-Audits Testing and QA Building from Source Changelog and Versioning FAQ Glossary
8.6.3 feed / 8.6.3 source · PolyForm Noncommercial 1.0.0