diff --git a/.cargo/audit.toml b/.cargo/audit.toml index 9cf5437..c1cd0d0 100644 --- a/.cargo/audit.toml +++ b/.cargo/audit.toml @@ -29,26 +29,14 @@ # Empty output on both targets means the entry is still justified. Any output # means it is not: drop the entry and fix the advisory for real. +# The quick-xml pair (RUSTSEC-2026-0194 / -0195) used to live here and was +# removed on 2026-07-27 by #312: plist 1.10.0 ships quick-xml 0.41.0, which +# carries the fix, so the advisories were resolved rather than accepted. That is +# the intended lifecycle of an entry in this file — it leaves when a fix becomes +# reachable, not when someone remembers to look. + [advisories] ignore = [ - # quick-xml 0.38.4 — RUSTSEC-2026-0194 (quadratic run time when checking a - # start tag for duplicate attribute names) and RUSTSEC-2026-0195 (unbounded - # namespace-declaration allocation enabling memory-exhaustion DoS), 7.5 - # high each. - # - # Not compiled on either shipped target. quick-xml is pulled by `plist`, - # which tauri only depends on for Apple bundling: both per-target trees are - # empty, and it appears solely under x86_64-apple-darwin, which we do not - # ship. - # - # An override is not an option either — both advisories are patched only in - # >= 0.41.0 while plist requires ^0.38, a semver-incompatible boundary that - # `[patch.crates-io]` cannot cross. - # - # Removal trigger: plist (or tauri) shipping quick-xml >= 0.41.0 — see #312. - "RUSTSEC-2026-0194", - "RUSTSEC-2026-0195", - # rsa 0.9.10 — RUSTSEC-2023-0071 (Marvin attack: potential key recovery # through timing side channels), 5.9 medium. # diff --git a/.forgejo/workflows/check-rust.yml b/.forgejo/workflows/check-rust.yml index 4617060..9a66f85 100644 --- a/.forgejo/workflows/check-rust.yml +++ b/.forgejo/workflows/check-rust.yml @@ -75,11 +75,13 @@ jobs: # Anti-rot guard for the suppressions in .cargo/audit.toml (#310). Each # entry there is justified by its crate being absent from every shipped # target's graph — a property of today's resolved graph, not a permanent - # one. If a tauri/plist bump ever makes quick-xml unconditional, the - # suppression would silently hide a live advisory and the daily audit - # would stay green: the inverse of the permanent red #310 exists to kill. + # one. rsa is currently reachable from nothing: its only parent in the + # lockfile is sqlx-mysql, which this SQLite project never compiles. If a + # dependency change ever pulls it into a shipped target, the suppression + # would silently hide a live advisory and the daily audit would stay + # green: the inverse of the permanent red #310 exists to kill. # - # That bump would itself be a src-tauri change, which is exactly what + # Such a change would itself touch src-tauri, which is exactly what # triggers this workflow. Runs after cargo check so the registry index is # already warm, and --locked so cargo tree cannot rewrite the lockfile the # audit was taken against. @@ -94,7 +96,7 @@ jobs: - name: Verify suppressed advisories are still unreachable run: | set -u - CRATES="quick-xml rsa" + CRATES="rsa" TARGETS="x86_64-unknown-linux-gnu x86_64-pc-windows-msvc" rc=0 checks=0 diff --git a/CHANGELOG.fr.md b/CHANGELOG.fr.md index 48b3bc7..8f20764 100644 --- a/CHANGELOG.fr.md +++ b/CHANGELOG.fr.md @@ -12,7 +12,7 @@ ### Sécurité -- Mise à jour de deux dépendances Rust situées sur le chemin de la mise à jour automatique, corrigeant six advisories RustSec : `rustls-webpki` 0.103.9 → 0.103.13 (traitement des contraintes de nom de certificat et analyse des listes de révocation, dont une panique atteignable) et `tar` 0.4.44 → 0.4.46 (`chmod` de répertoires arbitraires en suivant des liens symboliques pendant l'extraction, et en-têtes de taille PAX mal pris en compte). Les deux sont tirées par `tauri-plugin-updater`, qui télécharge et décompresse les mises à jour de l'application : ce sont donc de vrais chemins de code du produit livré. Aucun changement de comportement. Trois autres advisories restent signalées sur le fichier de verrouillage mais ne s'appliquent pas au produit livré — `quick-xml` n'est compilé que pour des cibles Apple que nous ne livrons pas, et `rsa` n'est jamais compilé — elles sont désormais consignées comme acceptées, avec leur justification et les conditions de leur retrait, plutôt que de laisser l'audit de sécurité quotidien rouge en permanence (#310). +- Mise à jour de deux dépendances Rust situées sur le chemin de la mise à jour automatique, corrigeant six advisories RustSec : `rustls-webpki` 0.103.9 → 0.103.13 (traitement des contraintes de nom de certificat et analyse des listes de révocation, dont une panique atteignable) et `tar` 0.4.44 → 0.4.46 (`chmod` de répertoires arbitraires en suivant des liens symboliques pendant l'extraction, et en-têtes de taille PAX mal pris en compte). Les deux sont tirées par `tauri-plugin-updater` : celle qui gère TLS travaille à chaque vérification et à chaque téléchargement de mise à jour, tandis que celle qui décompresse n'est atteinte que par des formats d'installeur que cette application ne livre pas — elle a été mise à jour quand même, plutôt que contournée par un raisonnement. Aucun changement de comportement. Une autre advisory reste signalée sur le fichier de verrouillage et ne s'applique pas au produit livré : `rsa` n'est jamais compilé, son seul parent étant un pilote MySQL qu'une application SQLite ne construit jamais. Elle est consignée comme acceptée, avec sa justification et les conditions de son retrait, plutôt que de laisser l'audit de sécurité quotidien rouge en permanence. Les deux advisories visant `quick-xml` ont été acceptées de la même façon pendant quelques heures, puis résolues pour de bon : `plist` 1.10.0 livrait déjà le `quick-xml` 0.41.0 corrigé (#310, #312). - Mise à jour de la dépendance de build `postcss` (8.5.13 → 8.5.23), corrigeant GHSA-r28c-9q8g-f849 (traversée de chemin lors du chargement automatique d'une source map précédente depuis un commentaire `sourceMappingURL`, menant à la divulgation de fichiers `.map` arbitraires). Outillage de build uniquement, aucun changement runtime ni de comportement — le CSS généré est identique octet pour octet. Une advisory reste signalée sur `react-router` et est volontairement laissée en l'état : elle vise le mode React Server Components, qu'une application de bureau locale n'exécute jamais, et aucun correctif n'existe vers lequel avancer puisque `react-router-dom` est figé en 7.18.1 (sortir de la plage concernée demanderait une migration vers react-router v8, pas un changement de version) (#311). ## [0.14.0] - 2026-07-18 diff --git a/CHANGELOG.md b/CHANGELOG.md index 34b06af..d35ef9b 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,7 +12,7 @@ ### Security -- Updated two Rust dependencies sitting on the automatic-update path, clearing six RustSec advisories: `rustls-webpki` 0.103.9 → 0.103.13 (certificate name-constraint handling and certificate-revocation-list parsing, including a reachable panic) and `tar` 0.4.44 → 0.4.46 (arbitrary directory `chmod` by following symlinks during extraction, and mishandled PAX size headers). Both are pulled in by `tauri-plugin-updater`, which downloads and unpacks application updates, so these are real code paths in the shipped app. No behaviour change. Three further advisories are still reported against the lockfile but do not apply to the shipped product — `quick-xml` is only compiled for Apple targets we do not ship, and `rsa` is never compiled at all — so they are now recorded as accepted, together with their justification and the conditions for removing them, instead of leaving the daily security audit permanently red (#310). +- Updated two Rust dependencies sitting on the automatic-update path, clearing six RustSec advisories: `rustls-webpki` 0.103.9 → 0.103.13 (certificate name-constraint handling and certificate-revocation-list parsing, including a reachable panic) and `tar` 0.4.44 → 0.4.46 (arbitrary directory `chmod` by following symlinks during extraction, and mishandled PAX size headers). Both are pulled in by `tauri-plugin-updater`: the TLS one runs on every update check and download, while the archive one is only reached by installer formats this app does not ship — it was updated anyway rather than reasoned around. No behaviour change. One further advisory is still reported against the lockfile and does not apply to the shipped product: `rsa` is never compiled at all, its only parent being a MySQL driver that a SQLite application never builds. It is recorded as accepted, with its justification and the conditions for removing it, instead of leaving the daily security audit permanently red. The two advisories against `quick-xml` were accepted the same way for a few hours, then resolved outright: `plist` 1.10.0 turned out to ship the fixed `quick-xml` 0.41.0 (#310, #312). - Updated the build-time dependency `postcss` (8.5.13 → 8.5.23), clearing GHSA-r28c-9q8g-f849 (path traversal while auto-loading a previous source map from a `sourceMappingURL` comment, leading to arbitrary `.map` file disclosure). Build tooling only, no runtime or behaviour change — the generated CSS is byte-for-byte identical. One advisory remains reported against `react-router`, and is deliberately left as is: it targets the React Server Components mode, which a local desktop app never runs, and no fix exists to move forward to since `react-router-dom` is frozen at 7.18.1 (leaving the affected range would mean migrating to react-router v8, not bumping a version) (#311). ## [0.14.0] - 2026-07-18 diff --git a/docs/adr/0018-suppression-advisories-non-atteignables.md b/docs/adr/0018-suppression-advisories-non-atteignables.md index e4a7643..af5c7b4 100644 --- a/docs/adr/0018-suppression-advisories-non-atteignables.md +++ b/docs/adr/0018-suppression-advisories-non-atteignables.md @@ -5,6 +5,10 @@ - Issues: #310 (les 9 advisories découvertes, cette décision), #312 (déclencheur de retrait des entrées `quick-xml`), #314 (le cron de `audit.yml` n'a jamais démarré) - S'appuie sur #232 (split de `check.yml`, création de `audit.yml`, retrait du `|| true` qui masquait la sortie de `cargo audit`) +> **Amendement du 2026-07-27 (#312/#313)** — la décision et ses trois règles sont inchangées ; seules les entrées ont bougé. Les deux advisories `quick-xml` ont **quitté la liste le jour même** : `plist` 1.10.0 tire `quick-xml` 0.41.0, qui porte le correctif, dans la borne existante de `tauri`. Elles sont donc **résolues, pas acceptées**, et le mécanisme a fonctionné comme prévu — la vérification par cible a montré qu'un correctif était devenu atteignable, et l'entrée est partie. Il ne reste que `RUSTSEC-2023-0071` (`rsa`), et le garde-fou ne boucle plus que sur ce crate. +> +> Trois passages ci-dessous sont **datés du 2026-07-27 avant ce bump** et à lire comme historiques : `quick-xml` comme exemple de l'insuffisance de `--target all` (règle 1), l'entrée `quick-xml` du tableau de contexte, et l'alternative « override / `[patch.crates-io]` » — cette dernière **n'est plus vraie**, `plist` 1.10.0 déclarant désormais `quick-xml ^0.41.0`. L'argument de fond qu'elle illustre (`[patch.crates-io]` ne franchit pas une frontière semver-incompatible) reste correct, seul le cas d'espèce a disparu. + ## Contexte #232 a retiré le `|| true` qui avalait la sortie de `cargo audit` et créé `audit.yml`, un job quotidien (06:00 UTC) **volontairement bloquant** : il *est* le canal de notification pour les advisories publiées entre deux PR Rust, `check-rust.yml` ne tournant que sur ~1 PR sur 40. @@ -51,7 +55,7 @@ Trois détails la rendent fiable plutôt que décorative : - un **canari** (`tar`, dépendance réellement présente) doit être trouvé à chaque exécution, faute de quoi le silence de la boucle ne prouve rien ; - `.cargo/**` est ajouté aux `paths` de `check-rust.yml` pour qu'une PR ne touchant que la liste déclenche bien la vérification. -Le pendant — une entrée devenue *inutile*, que rien ne signale — est couvert par une issue de suivi portant la condition de retrait (#312 pour `quick-xml`). +Le pendant — une entrée devenue *inutile*, que rien ne signale — est couvert par une issue de suivi portant la condition de retrait : #312 l'a joué pour `quick-xml` (et a servi : le déclencheur avait sauté sans que personne le remarque), #319 le fait pour `rsa`. **Toute entrée de la liste doit en avoir une**, sinon le garde-fou ne couvre qu'une moitié du risque. ## Alternatives considérées @@ -59,7 +63,7 @@ Le pendant — une entrée devenue *inutile*, que rien ne signale — est couver - **Remettre `continue-on-error` ou `|| true` sur le job quotidien.** Rejeté pour la même raison, en pire : cela supprime le signal pour *toutes* les advisories, pas seulement pour les trois inévitables. - **Dupliquer des `--ignore` dans `audit.yml` et `check-rust.yml`.** Rejeté : deux listes à maintenir en phase, sans endroit naturel où écrire la justification. Le fichier `.cargo/audit.toml` est lu par les deux workflows sans qu'aucun n'ait à le savoir, et il porte les preuves à côté des entrées. - **Ignorer au niveau du crate plutôt que de l'advisory.** Rejeté — voir la règle 2. -- **Un override / `[patch.crates-io]` pour `quick-xml`.** Impossible : le correctif est en `0.41.0` et `plist` exige `^0.38`. `[patch.crates-io]` ne franchit pas une frontière semver-incompatible. +- **Un override / `[patch.crates-io]` pour `quick-xml`.** Impossible : le correctif est en `0.41.0` et `plist` exige `^0.38`. `[patch.crates-io]` ne franchit pas une frontière semver-incompatible. *(Périmé le jour même — `plist` 1.10.0 déclare `quick-xml ^0.41.0`, et un simple `cargo update -p plist` a suffi ; voir l'amendement en tête. Le principe reste, le cas d'espèce a disparu.)* - **Retirer `sqlx-mysql` du graphe pour éliminer `rsa`.** Écarté : `rsa` n'étant compilé sur aucune cible, l'opération serait un contorsionnement du manifeste pour un gain nul. ## Conséquences @@ -87,4 +91,4 @@ Le pendant — une entrée devenue *inutile*, que rien ne signale — est couver - [`.forgejo/workflows/check-rust.yml`](../../.forgejo/workflows/check-rust.yml) — étape « Verify suppressed advisories are still unreachable » - [`.forgejo/workflows/audit.yml`](../../.forgejo/workflows/audit.yml) — le gate quotidien bloquant - [ADR 0009](0009-proxy-price-fetching-via-maximus-api.md) — récupération de cours via `reqwest`, l'un des deux chemins qui rendent `rustls-webpki` atteignable -- Issues #310 (cette décision), #312 (retrait `quick-xml`), #313 (`tauri-plugin-deep-link` yanked), #314 (cron jamais déclenché), #315 (smoke-test du cycle de mise à jour) +- Issues #310 (cette décision), #312 (retrait `quick-xml`, **fait le 2026-07-27**), #313 (`tauri-plugin-deep-link` yanked, fait), #314 (cron jamais déclenché), #315 (smoke-test du cycle de mise à jour), #319 (déclencheur de retrait `rsa`, la dernière entrée restante) diff --git a/src-tauri/Cargo.lock b/src-tauri/Cargo.lock index c3167de..c4319f8 100644 --- a/src-tauri/Cargo.lock +++ b/src-tauri/Cargo.lock @@ -589,7 +589,7 @@ version = "3.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "faf9468729b8cbcea668e36183cb69d317348c2e08e994829fb56ebfdfbaac34" dependencies = [ - "windows-sys 0.48.0", + "windows-sys 0.61.2", ] [[package]] @@ -989,7 +989,7 @@ dependencies = [ "libc", "option-ext", "redox_users", - "windows-sys 0.59.0", + "windows-sys 0.61.2", ] [[package]] @@ -1209,7 +1209,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "39cab71617ae0d63f51a36d69f866391735b51691dbda63cf6f96d042b63efeb" dependencies = [ "libc", - "windows-sys 0.52.0", + "windows-sys 0.61.2", ] [[package]] @@ -3498,9 +3498,9 @@ checksum = "7edddbd0b52d732b21ad9a5fab5c704c14cd949e5e9a1ec5929a24fded1b904c" [[package]] name = "plist" -version = "1.8.0" +version = "1.10.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "740ebea15c5d1428f910cd1a5f52cebf8d25006245ed8ade92702f4943d91e07" +checksum = "7da1d65da6dd5d1e44199ac0f58712d241c0f439f80adea8924d832384087f85" dependencies = [ "base64 0.22.1", "indexmap 2.13.0", @@ -3648,9 +3648,9 @@ dependencies = [ [[package]] name = "quick-xml" -version = "0.38.4" +version = "0.41.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b66c2058c55a409d601666cffe35f04333cf1013010882cec174a7467cd4e21c" +checksum = "e660451e55124f798a69a5af3f49ccfbefbd41910eefd25caf2393e1f3473ec1" dependencies = [ "memchr", ] @@ -4044,7 +4044,7 @@ dependencies = [ "errno", "libc", "linux-raw-sys", - "windows-sys 0.52.0", + "windows-sys 0.61.2", ] [[package]] @@ -4100,7 +4100,7 @@ dependencies = [ "security-framework", "security-framework-sys", "webpki-root-certs", - "windows-sys 0.52.0", + "windows-sys 0.61.2", ] [[package]] @@ -4645,9 +4645,9 @@ dependencies = [ [[package]] name = "spin" -version = "0.9.8" +version = "0.9.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6980e8d7511241f8acf4aebddbb1ff938df5eebe98691418c4468d0b72a96a67" +checksum = "3763264f6b73151db08c50ff20d7d8a0b8796e021cdea7ceedad07b80155fa0e" dependencies = [ "lock_api", ] @@ -5206,9 +5206,9 @@ dependencies = [ [[package]] name = "tauri-plugin-deep-link" -version = "2.4.8" +version = "2.4.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "3db49816aee496a9b200d55b55ab6ae73fd50847c79f2fabc7ee20871fa75c95" +checksum = "70ee75bc5627f77bfdf40c913255ebc258117b10ebe2b2239a1a1cf40b0b58aa" dependencies = [ "dunce", "plist", @@ -5477,7 +5477,7 @@ dependencies = [ "getrandom 0.3.4", "once_cell", "rustix", - "windows-sys 0.52.0", + "windows-sys 0.61.2", ] [[package]] @@ -6323,7 +6323,7 @@ version = "0.1.11" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c2a7b1c03c876122aa43f3020e6c3c3ee5c05081c9a00739faf7503aeba10d22" dependencies = [ - "windows-sys 0.48.0", + "windows-sys 0.61.2", ] [[package]]