Skip to content

fix(mgt,opus): zwei kopflose Formate waren ueber die Erkennung unerre… #870

fix(mgt,opus): zwei kopflose Formate waren ueber die Erkennung unerre…

fix(mgt,opus): zwei kopflose Formate waren ueber die Erkennung unerre… #870

Workflow file for this run

# ============================================================================
# UnifiedFloppyTool - Sanitizer Checks
#
# Runs ASan and UBSan builds to catch memory errors and undefined behaviour.
# Uses the CMake build path (library targets + test suite).
#
# Fixes applied:
# FAILURE-007: removed --target all, use default CMake target
# Added: ctest --build-config for multi-config generators
# ============================================================================
name: Sanitizer Checks
on:
push:
branches: [main, develop]
pull_request:
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true
permissions:
contents: read
env:
QT_VERSION: '6.10.1'
jobs:
asan:
# MF-432: without this GitHub's default is 360 min. On 2026-08-19
# five Linux jobs hung in the Qt/apt download and would have burned
# six hours each. A hang now dies here instead.
timeout-minutes: 60
runs-on: ubuntu-22.04
steps:
- uses: actions/checkout@v7
- name: Install Qt
uses: jurplel/install-qt-action@v4
with:
version: ${{ env.QT_VERSION }}
host: linux
target: desktop
modules: 'qtserialport'
cache: true
- name: Install dependencies
run: |
sudo apt-get update -q
sudo apt-get install -y libusb-1.0-0-dev libgl1-mesa-dev
- name: Build with ASan (CMake)
# FIX-007: no --target all
run: |
cmake -B build \
-DCMAKE_BUILD_TYPE=Debug \
-DUFT_BUILD_TESTS=ON \
-DCMAKE_C_FLAGS="-fsanitize=address -fno-omit-frame-pointer" \
-DCMAKE_CXX_FLAGS="-fsanitize=address -fno-omit-frame-pointer" \
-DCMAKE_EXE_LINKER_FLAGS="-fsanitize=address"
cmake --build build --parallel $(nproc) 2>&1 || true
# GUI may fail (missing headers) — tests are what matters
# ─────────────────────────────────────────────────────────────────
# SCHARF (MF-517). Dieser Schritt hat KEIN `|| true`.
#
# Er faehrt genau die Tests, die den Weg gehen, den ein Benutzer
# geht: eine Datei oeffnen. Dort lagen fuenf Speicherfehler, die
# 241 gruene Tests nicht gefunden haben (KNOWN_ISSUES FUZZ-1/FUZZ-2)
# — Heap-Ueberlauf 44830 B, Stapel-Ueberlauf 1800 B, ein doppeltes
# free bei jeder abgeschnittenen DSK-Datei, ein Lesen 29 KB hinter
# ein Feld, und zwoelf read_track, die durch NULL schrieben.
#
# detect_leaks=0 mit Absicht: geleckt wird in diesem Baum an vielen
# Stellen, und ein ungemessener Rueckstand darf kein Tor bewachen.
# Speicher-FEHLER sind etwas anderes als Speicher-Verlust; die
# ersten werden hier scharf geprueft, die zweiten weiter unten
# gemeldet.
- name: Memory-safety gate — open path (ARMED)
run: |
cd build
ctest --output-on-failure --timeout 300 --no-tests=error \
--tests-regex "test_convert_roundtrip_measured|test_convert_identity_lossless|test_track_add_sector_owns_copies|test_convert_fuzz|test_convert_roundtrip_lossless|test_disk_open_fuzz|test_disk_write_fuzz|test_dsk_open_bounds|test_format_probe_fuzz"
env:
# halt_on_error=0: EIN Lauf meldet ALLE Funde statt beim ersten
# abzubrechen. Sonst kostet jeder einzelne Fehler eine eigene
# CI-Runde — beim ersten scharfen Lauf (MF-520) war genau das
# der Fall, und hinter dem gemeldeten koennen weitere stehen.
# ASan setzt den Exit-Code trotzdem, das Tor bleibt scharf.
ASAN_OPTIONS: detect_leaks=0:halt_on_error=0:exitcode=1:print_stacktrace=1
# ─────────────────────────────────────────────────────────────────
# BERICHTEND, nicht scharf.
#
# Bis MF-517 lief hier eine Liste von NEUN Testnamen, und das mit
# `|| true`. Damit sah der Baum 232 seiner 241 Tests nie unter ASan,
# und die neun, die er sah, konnten nichts roeten. Als "ASan-
# Workflow" gefuehrt zu werden und beides zu sein, ist genau die
# Sorte Zusage, gegen die DESIGN_PRINCIPLES geschrieben ist.
#
# Jetzt laeuft die ganze Suite, damit der Rueckstand GEMESSEN im Log
# steht statt geschaetzt zu werden. `|| true` bleibt hier bewusst:
# den Rueckstand scharf zu schalten, ohne ihn vorher zu kennen, waere
# derselbe Fehler in die andere Richtung.
- name: Full suite under ASan (reporting only, incl. leaks)
# MF-530: `if: always()`, weil GitHub den Auftrag sonst
# abbricht, sobald das scharfe Tor darueber rot wird — und
# dann faellt genau die Messung aus, die den Rueckstand
# sichtbar haelt. Beim d80-Fund (MF-529) ist das passiert:
# ein Befund im Tor, und der Leck-Bericht des ganzen Laufs
# war weg. Ein Tor, das die Messung mitreisst, misst nicht
# mehr.
if: always()
run: |
cd build
ctest --output-on-failure --timeout 300 || true
env:
ASAN_OPTIONS: detect_leaks=1:abort_on_error=1:print_stacktrace=1
- name: Upload ASan findings
if: failure()
uses: actions/upload-artifact@v4
with:
name: asan-findings-${{ github.sha }}
path: |
build/Testing/Temporary/
build/**/*.log
retention-days: 7
ubsan:
# MF-432: without this GitHub's default is 360 min. On 2026-08-19
# five Linux jobs hung in the Qt/apt download and would have burned
# six hours each. A hang now dies here instead.
timeout-minutes: 60
runs-on: ubuntu-22.04
steps:
- uses: actions/checkout@v7
- name: Install Qt
uses: jurplel/install-qt-action@v4
with:
version: ${{ env.QT_VERSION }}
host: linux
target: desktop
modules: 'qtserialport'
cache: true
- name: Install dependencies
run: |
sudo apt-get update -q
sudo apt-get install -y libusb-1.0-0-dev libgl1-mesa-dev
- name: Build with UBSan (CMake)
run: |
cmake -B build \
-DCMAKE_BUILD_TYPE=Debug \
-DUFT_BUILD_TESTS=ON \
-DCMAKE_C_FLAGS="-fsanitize=undefined -fno-omit-frame-pointer" \
-DCMAKE_CXX_FLAGS="-fsanitize=undefined -fno-omit-frame-pointer" \
-DCMAKE_EXE_LINKER_FLAGS="-fsanitize=undefined"
cmake --build build --parallel $(nproc) 2>&1 || true
# GUI may fail (missing headers) — tests are what matters
# SCHARF (MF-517) — siehe die Begruendung im ASan-Auftrag oben.
- name: UB gate — open path (ARMED)
run: |
cd build
ctest --output-on-failure --timeout 300 --no-tests=error \
--tests-regex "test_convert_roundtrip_measured|test_convert_identity_lossless|test_track_add_sector_owns_copies|test_convert_fuzz|test_convert_roundtrip_lossless|test_disk_open_fuzz|test_disk_write_fuzz|test_dsk_open_bounds|test_format_probe_fuzz"
env:
# Wie beim ASan-Tor: ein Lauf, alle Funde.
UBSAN_OPTIONS: print_stacktrace=1:halt_on_error=0:exitcode=1
# BERICHTEND. Vorher liefen hier neun Testnamen mit `|| true`; die
# restlichen 232 sah niemand unter UBSan.
- name: Full suite under UBSan (reporting only)
# MF-530: `if: always()`, weil GitHub den Auftrag sonst
# abbricht, sobald das scharfe Tor darueber rot wird — und
# dann faellt genau die Messung aus, die den Rueckstand
# sichtbar haelt. Beim d80-Fund (MF-529) ist das passiert:
# ein Befund im Tor, und der Leck-Bericht des ganzen Laufs
# war weg. Ein Tor, das die Messung mitreisst, misst nicht
# mehr.
if: always()
run: |
cd build
ctest --output-on-failure --timeout 300 || true
env:
UBSAN_OPTIONS: print_stacktrace=1:halt_on_error=1
- name: Upload UBSan findings
if: failure()
uses: actions/upload-artifact@v4
with:
name: ubsan-findings-${{ github.sha }}
path: |
build/Testing/Temporary/
build/**/*.log
retention-days: 7