diff --git a/.changes/mis-hashed-files.md b/.changes/mis-hashed-files.md new file mode 100644 index 00000000..5a17a93b --- /dev/null +++ b/.changes/mis-hashed-files.md @@ -0,0 +1,6 @@ +--- +"cargo-packager": "patch" +"@crabnebula/packager": "patch" +--- + +Check if required files/tools for packaging are outdated or mis-hashed and redownload them. diff --git a/Cargo.lock b/Cargo.lock index 61c8f7d2..41a0c661 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -89,13 +89,13 @@ dependencies = [ [[package]] name = "accesskit_unix" -version = "0.6.1" +version = "0.6.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6c8c9b4467d77cacfbc93cee9aa8e7822f6d527c774efdca5f8b3a5280c34847" +checksum = "09f46c18d99ba61ad7123dd13eeb0c104436ab6af1df6a1cd8c11054ed394a08" dependencies = [ "accesskit 0.12.1", "accesskit_consumer 0.16.1", - "async-channel 1.9.0", + "async-channel 2.1.1", "async-once-cell", "atspi 0.19.0", "futures-lite 1.13.0", @@ -153,7 +153,7 @@ checksum = "5284218aca17d9e150164428a0ebc7b955f70e3a9a78b4c20894513aabf98a67" dependencies = [ "accesskit 0.12.1", "accesskit_macos 0.10.1", - "accesskit_unix 0.6.1", + "accesskit_unix 0.6.2", "accesskit_windows 0.15.1", "winit 0.29.4", ] @@ -373,9 +373,9 @@ checksum = "96d30a06541fbafbc7f82ed10c06164cfbd2c401138f6addd8404629c4b16711" [[package]] name = "as-raw-xcb-connection" -version = "1.0.0" +version = "1.0.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2d5f312b0a56c5cdf967c0aeb67f6289603354951683bc97ddc595ab974ba9aa" +checksum = "175571dd1d178ced59193a6fc02dde1b972eb0bc56c892cde9beeceac5bf0f6b" [[package]] name = "ascii" @@ -556,9 +556,9 @@ dependencies = [ [[package]] name = "async-task" -version = "4.5.0" +version = "4.6.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "b4eb2cdb97421e01129ccb49169d8279ed21e829929144f4a22a6e54ac549ca1" +checksum = "e1d90cd0b264dfdd8eb5bad0a2c217c1f88fa96a8573f40e7b12de23fb468f46" [[package]] name = "async-trait" @@ -1604,9 +1604,9 @@ checksum = "7059fff8937831a9ae6f0fe4d658ffabf58f2ca96aa9dec1c889f936f705f216" [[package]] name = "crossbeam-channel" -version = "0.5.8" +version = "0.5.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "a33c2bf77f2df06183c3aa30d1e96c0695a313d4f9c453cc3762a6db39f99200" +checksum = "14c3242926edf34aec4ac3a77108ad4854bffaa2e4ddc1824124ce59231302d5" dependencies = [ "cfg-if", "crossbeam-utils", @@ -1614,9 +1614,9 @@ dependencies = [ [[package]] name = "crossbeam-deque" -version = "0.8.3" +version = "0.8.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ce6fd6f855243022dcecf8702fef0c297d4338e226845fe067f6341ad9fa0cef" +checksum = "fca89a0e215bab21874660c67903c5f143333cab1da83d041c7ded6053774751" dependencies = [ "cfg-if", "crossbeam-epoch", @@ -1625,22 +1625,21 @@ dependencies = [ [[package]] name = "crossbeam-epoch" -version = "0.9.15" +version = "0.9.16" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ae211234986c545741a7dc064309f67ee1e5ad243d0e48335adc0484d960bcc7" +checksum = "2d2fe95351b870527a5d09bf563ed3c97c0cffb87cf1c78a591bf48bb218d9aa" dependencies = [ "autocfg", "cfg-if", "crossbeam-utils", "memoffset 0.9.0", - "scopeguard", ] [[package]] name = "crossbeam-utils" -version = "0.8.16" +version = "0.8.17" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5a22b2d63d4d1dc0b7f1b6b2747dd0088008a9be28b6ddf0b1e7d335e3037294" +checksum = "c06d96137f14f244c37f989d9fff8f95e6c18b918e71f36638f8c49112e4c78f" dependencies = [ "cfg-if", ] @@ -2431,9 +2430,9 @@ dependencies = [ [[package]] name = "femtovg" -version = "0.8.0" +version = "0.8.1" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d900654f23fe7c254442e1902e22dff2c3facf61bc0fb6531cc103b66467864e" +checksum = "19df4b4c86231086212f22513ccfdbce94a1e1270d1cb09c030bd39fd73f3ee4" dependencies = [ "bitflags 2.4.1", "fnv", @@ -2874,8 +2873,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "fe9006bed769170c11f845cf00c7c1e9092aeb3f268e007c3e760ac68008070f" dependencies = [ "cfg-if", + "js-sys", "libc", "wasi 0.11.0+wasi-snapshot-preview1", + "wasm-bindgen", ] [[package]] @@ -3306,11 +3307,11 @@ dependencies = [ [[package]] name = "home" -version = "0.5.5" +version = "0.5.9" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "5444c27eef6923071f7ebcc33e3444508466a76f7a2b93da00ed6e19f30c1ddb" +checksum = "e3d1354bf6b7235cb4a0576c2619fd4ed18183f689b12b006a0ee7329eeff9a5" dependencies = [ - "windows-sys 0.48.0", + "windows-sys 0.52.0", ] [[package]] @@ -3369,9 +3370,9 @@ checksum = "df3b46402a9d5adb4c86a0cf463f42e19994e3ee891101b1841f30a545cb49a9" [[package]] name = "hyper" -version = "0.14.27" +version = "0.14.28" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ffb1cfd654a8219eaef89881fdb3bb3b1cdc5fa75ded05d6933b2b382e395468" +checksum = "bf96e135eb83a2a8ddf766e426a841d8ddd7449d5f00d34ea02b41d2f19eef80" dependencies = [ "bytes", "futures-channel", @@ -3384,7 +3385,7 @@ dependencies = [ "httpdate", "itoa 1.0.10", "pin-project-lite", - "socket2 0.4.10", + "socket2 0.5.5", "tokio", "tower-service", "tracing", @@ -4385,9 +4386,9 @@ dependencies = [ [[package]] name = "memmap2" -version = "0.9.0" +version = "0.9.2" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "deaba38d7abf1d4cca21cc89e932e542ba2b9258664d2a9ef0e61512039c9375" +checksum = "39a69c7c189ae418f83003da62820aca28d15a07725ce51fb924999335d622ff" dependencies = [ "libc", ] @@ -4448,9 +4449,9 @@ checksum = "68354c5c6bd36d73ff3feceb05efa59b6acb7626617f4962be322a825e61f79a" [[package]] name = "minisign" -version = "0.7.5" +version = "0.7.6" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "d2b6f58413c6cee060115673578e47271838f3c87cb9322c61a3bcd6d740b7d2" +checksum = "4225fad231f4cfb67990de1750bb53f10ff1d5b42b91beb2a49e6ebd36c9ab4a" dependencies = [ "getrandom 0.2.11", "rpassword", @@ -4507,23 +4508,23 @@ checksum = "d4b4532cf86bfef556348ac65e561e3123879f0e7566cca6d43a6ff5326f13df" [[package]] name = "napi-derive" -version = "2.14.3" +version = "2.14.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "2b0c0743f6a3f29c20851b8377f01d485a837e2bfa57dd56d519ab7ed98ae2af" +checksum = "9b5af262f1d8e660742eb722abc7113a5b3c3de4144d0ef23ede2518672ceff1" dependencies = [ "cfg-if", "convert_case 0.6.0", "napi-derive-backend", "proc-macro2", "quote", - "syn 1.0.109", + "syn 2.0.41", ] [[package]] name = "napi-derive-backend" -version = "1.0.56" +version = "1.0.57" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "4869e4d80615fdab57dffe38c36a5bc62fae37352a00a35ee7aca1cea41b1bb3" +checksum = "4ea236321b521d6926213a2021e407b0562e28a257c037a45919e414d2cdb4f8" dependencies = [ "convert_case 0.6.0", "once_cell", @@ -4531,7 +4532,7 @@ dependencies = [ "quote", "regex", "semver", - "syn 1.0.109", + "syn 2.0.41", ] [[package]] @@ -5732,9 +5733,9 @@ checksum = "c707298afce11da2efef2f600116fa93ffa7a032b5d7b628aa17711ec81383ca" [[package]] name = "reqwest" -version = "0.11.22" +version = "0.11.23" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "046cd98826c46c2ac8ddecae268eb5c2e58628688a5fc7a2643704a73faba95b" +checksum = "37b1ae8d9ac08420c66222fb9096fc5de435c3c48542bc5336c51892cffafb41" dependencies = [ "base64 0.21.5", "bytes", @@ -6128,7 +6129,7 @@ checksum = "1729a30a469de249c6effc17ec8d039b0aa29b3af79b819b7f51cb6ab8046a90" dependencies = [ "ab_glyph", "log", - "memmap2 0.9.0", + "memmap2 0.9.2", "smithay-client-toolkit 0.18.0", "tiny-skia 0.11.3", ] @@ -6550,7 +6551,7 @@ dependencies = [ "cursor-icon", "libc", "log", - "memmap2 0.9.0", + "memmap2 0.9.2", "rustix 0.38.28", "thiserror", "wayland-backend", @@ -6628,7 +6629,7 @@ dependencies = [ "foreign-types 0.5.0", "js-sys", "log", - "memmap2 0.9.0", + "memmap2 0.9.2", "objc", "raw-window-handle 0.5.2", "redox_syscall 0.4.1", @@ -7204,18 +7205,18 @@ checksum = "8eaa81235c7058867fa8c0e7314f33dcce9c215f535d1913822a2b3f5e289f3c" [[package]] name = "thiserror" -version = "1.0.50" +version = "1.0.51" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "f9a7210f5c9a7156bb50aa36aed4c95afb51df0df00713949448cf9e97d382d2" +checksum = "f11c217e1416d6f036b870f14e0413d480dbf28edbee1f877abaf0206af43bb7" dependencies = [ "thiserror-impl", ] [[package]] name = "thiserror-impl" -version = "1.0.50" +version = "1.0.51" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "266b2e40bc00e5a6c09c3584011e08b06f123c00362c92b975ba9843aaaa14b8" +checksum = "01742297787513b79cf8e29d1056ede1313e2420b7b3b15d0a768b4921f549df" dependencies = [ "proc-macro2", "quote", @@ -7619,10 +7620,11 @@ dependencies = [ [[package]] name = "uds_windows" -version = "1.0.2" +version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "ce65604324d3cce9b966701489fbd0cf318cb1f7bd9dd07ac9a4ee6fb791930d" +checksum = "89daebc3e6fd160ac4aa9fc8b3bf71e1f74fbf92367ae71fb83a037e8bf164b9" dependencies = [ + "memoffset 0.9.0", "tempfile", "winapi", ] @@ -8736,7 +8738,7 @@ dependencies = [ "js-sys", "libc", "log", - "memmap2 0.9.0", + "memmap2 0.9.2", "ndk 0.8.0", "ndk-sys 0.5.0+25.2.9519653", "objc2 0.4.1", @@ -8767,9 +8769,9 @@ dependencies = [ [[package]] name = "winnow" -version = "0.5.28" +version = "0.5.30" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "6c830786f7720c2fd27a1a0e27a709dbd3c4d009b56d098fc742d4f4eab91fe2" +checksum = "9b5c3db89721d50d0e2a673f5043fc4722f76dcc352d7b1ab8b8288bed4ed2c5" dependencies = [ "memchr", ] @@ -9058,18 +9060,18 @@ dependencies = [ [[package]] name = "zerocopy" -version = "0.7.30" +version = "0.7.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "306dca4455518f1f31635ec308b6b3e4eb1b11758cefafc782827d0aa7acb5c7" +checksum = "1c4061bedbb353041c12f413700357bec76df2c7e2ca8e4df8bac24c6bf68e3d" dependencies = [ "zerocopy-derive", ] [[package]] name = "zerocopy-derive" -version = "0.7.30" +version = "0.7.31" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "be912bf68235a88fbefd1b73415cb218405958d1655b2ece9035a19920bdf6ba" +checksum = "b3c129550b3e6de3fd0ba67ba5c81818f9805e58b8d7fee80a3a59d2c9fc601a" dependencies = [ "proc-macro2", "quote", diff --git a/crates/packager/src/package/nsis/mod.rs b/crates/packager/src/package/nsis/mod.rs index fa7e0c1d..c138889a 100644 --- a/crates/packager/src/package/nsis/mod.rs +++ b/crates/packager/src/package/nsis/mod.rs @@ -13,7 +13,10 @@ use std::{ use handlebars::{to_json, Handlebars}; use super::Context; -use crate::codesign::windows::{self as codesign, ConfigSignExt}; +use crate::{ + codesign::windows::{self as codesign, ConfigSignExt}, + util::verify_path_hash, +}; use crate::{ config::{Config, LogLevel, NSISInstallerMode, NsisCompression}, shell::CommandExt, @@ -27,7 +30,7 @@ const NSIS_URL: &str = #[cfg(target_os = "windows")] const NSIS_SHA1: &str = "586855a743a6e0ade203d8758af303a48ee0716b"; const NSIS_APPLICATIONID_URL: &str = "https://github.com/tauri-apps/binary-releases/releases/download/nsis-plugins-v0/NSIS-ApplicationID.zip"; -const NSIS_TAURI_UTILS: &str = +const NSIS_TAURI_UTILS_URL: &str = "https://github.com/tauri-apps/nsis-tauri-utils/releases/download/nsis_tauri_utils-v0.2.1/nsis_tauri_utils.dll"; const NSIS_TAURI_UTILS_SHA1: &str = "53A7CFAEB6A4A9653D6D5FBFF02A3C3B8720130A"; @@ -51,6 +54,13 @@ const NSIS_REQUIRED_FILES: &[&str] = &[ "Plugins/x86-unicode/nsis_tauri_utils.dll", ]; +const NSIS_REQUIRED_FILES_HASH: &[(&str, &str, &str, HashAlgorithm)] = &[( + "Plugins/x86-unicode/nsis_tauri_utils.dll", + NSIS_TAURI_UTILS_URL, + NSIS_TAURI_UTILS_SHA1, + HashAlgorithm::Sha1, +)]; + type DirectoriesSet = BTreeSet; type ResourcesMap = BTreeMap; @@ -278,7 +288,7 @@ fn get_and_extract_nsis( let data = download_and_verify( "nsis_tauri_utils.dll", - NSIS_TAURI_UTILS, + NSIS_TAURI_UTILS_URL, NSIS_TAURI_UTILS_SHA1, HashAlgorithm::Sha1, )?; @@ -572,6 +582,22 @@ pub(crate) fn package(ctx: &Context) -> crate::Result> { tracing::warn!("NSIS directory is missing some files. Recreating it..."); std::fs::remove_dir_all(&nsis_toolset_path)?; get_and_extract_nsis(ctx, &nsis_toolset_path)?; + } else { + let mismatched = NSIS_REQUIRED_FILES_HASH + .iter() + .filter(|(p, _, hash, hash_algorithm)| { + verify_path_hash(nsis_toolset_path.join(p), hash, *hash_algorithm).is_err() + }) + .collect::>(); + + if !mismatched.is_empty() { + tracing::warn!("NSIS directory contains mis-hashed files. Redownloading them."); + for (path, url, hash, hash_algorithim) in mismatched { + let path = nsis_toolset_path.join(path); + let data = download_and_verify(&path, url, hash, *hash_algorithim)?; + std::fs::write(path, data)?; + } + } } build_nsis_app_installer(ctx, &nsis_toolset_path) diff --git a/crates/packager/src/util.rs b/crates/packager/src/util.rs index 4d957526..35ae582d 100644 --- a/crates/packager/src/util.rs +++ b/crates/packager/src/util.rs @@ -148,6 +148,7 @@ pub(crate) fn download(url: &str) -> crate::Result> { Ok(bytes) } +#[derive(Clone, Copy)] pub(crate) enum HashAlgorithm { #[cfg(target_os = "windows")] Sha256, @@ -155,31 +156,37 @@ pub(crate) enum HashAlgorithm { } /// Function used to download a file and checks SHA256 to verify the download. -pub(crate) fn download_and_verify( - file: &str, +pub(crate) fn download_and_verify>( + path: P, url: &str, hash: &str, hash_algorithm: HashAlgorithm, ) -> crate::Result> { let data = download(url)?; - tracing::info!("Validating {file} hash"); + tracing::info!("Validating {} hash", path.as_ref().display()); + verify_hash(&data, hash, hash_algorithm)?; + Ok(data) +} +pub(crate) fn verify_hash( + data: &[u8], + hash: &str, + hash_algorithm: HashAlgorithm, +) -> crate::Result<()> { match hash_algorithm { #[cfg(target_os = "windows")] HashAlgorithm::Sha256 => { let hasher = sha2::Sha256::new(); - verify(&data, hash, hasher)?; + verify_data_with_hasher(data, hash, hasher) } HashAlgorithm::Sha1 => { let hasher = sha1::Sha1::new(); - verify(&data, hash, hasher)?; + verify_data_with_hasher(data, hash, hasher) } } - - Ok(data) } -fn verify(data: &Vec, hash: &str, mut hasher: impl Digest) -> crate::Result<()> { +fn verify_data_with_hasher(data: &[u8], hash: &str, mut hasher: impl Digest) -> crate::Result<()> { hasher.update(data); let url_hash = hasher.finalize().to_vec(); @@ -191,6 +198,15 @@ fn verify(data: &Vec, hash: &str, mut hasher: impl Digest) -> crate::Result< } } +pub(crate) fn verify_path_hash>( + path: P, + hash: &str, + hash_algorithm: HashAlgorithm, +) -> crate::Result<()> { + let data = std::fs::read(path)?; + verify_hash(&data, hash, hash_algorithm) +} + /// Extracts the zips from memory into a useable path. pub(crate) fn extract_zip(data: &[u8], path: &Path) -> crate::Result<()> { let cursor = Cursor::new(data);