SubtitleEdit/subtitleedit · error · IOException
MOSS-TTS (CrispASR) model {fileName} failed integrity check
Error message
MOSS-TTS (CrispASR) model {fileName} failed integrity check (expected SHA-256 {expected}, got {actual}). What it means
Thrown by MOSS-TTS CrispASR download service after a model file is downloaded and its SHA-256 hash does not match the expected pinned hash. It is an IOException raised by an integrity gate that runs over the freshly downloaded (or cached) file before it is allowed into the model registry.
Source
Thrown at src/ui/Logic/Download/MossTtsCrispAsrDownloadService.cs:145
{
return;
}
var expected = DownloadHashManager.GetLatestKnownHash(key);
if (string.IsNullOrEmpty(expected))
{
return;
}
string actual;
await using (var stream = File.OpenRead(filePath))
{
actual = await Sha256Util.ComputeSha256Async(stream, cancellationToken);
}
if (!string.Equals(expected, actual, StringComparison.OrdinalIgnoreCase))
{
throw new IOException(
$"MOSS-TTS (CrispASR) model {fileName} failed integrity check (expected SHA-256 {expected}, got {actual}).");
}
}
private static string GetUrl(string fileName)
{
if (!ModelUrls.TryGetValue(fileName, out var url))
{
throw new ArgumentException($"Unknown MOSS-TTS (CrispASR) model: {fileName}", nameof(fileName));
}
return url;
}
private static void TryDelete(string path)
{
try { File.Delete(path); } catch { /* best-effort cleanup */ }
}
View on GitHub (pinned to 17a9f07487)
Solutions
- Delete the cached file at the model path and re-run the download so it is fetched fresh.
- Confirm the pinned expected SHA-256 in the service matches the artifact the origin actually serves (the publisher may have republished the file).
- Verify network/disk health: a flaky connection or full disk can truncate the file and flip the hash.
- If the model was intentionally republished, update the pinned hash constant in MossTtsCrispAsrDownloadService and ship a new build.
Example fix
// before
if (!string.Equals(expected, actual, StringComparison.OrdinalIgnoreCase))
{
throw new IOException($"MOSS-TTS (CrispASR) model {fileName} failed integrity check ...");
}
// after - retry once after deleting the suspect cached file, then surface a clearer failure
if (!string.Equals(expected, actual, StringComparison.OrdinalIgnoreCase))
{
File.Delete(filePath);
throw new IOException(
$"MOSS-TTS (CrispASR) model {fileName} failed integrity check " +
$"(expected {expected}, got {actual}). The cached file was removed; retry the download.");
} Defensive patterns
Strategy: try-catch
Validate before calling
// Pre-check: if a cached file exists, verify its hash before offering it as ready.
var cached = Path.Combine(modelFolder, fileName);
if (File.Exists(cached))
{
using var s = File.OpenRead(cached);
var h = await Sha256Util.ComputeSha256Async(s, ct);
if (!string.Equals(expected, h, StringComparison.OrdinalIgnoreCase))
{
File.Delete(cached); // stale/corrupt; force re-download
}
} Try / catch
try { await downloadService.DownloadModelAsync(...); }
catch (IOException ex) when (ex.Message.Contains("failed integrity check"))
{
// delete suspect cache, retry once, then surface a clear user message
if (File.Exists(filePath)) File.Delete(filePath);
await downloadService.DownloadModelAsync(...);
} Prevention
- Always clear the model cache before re-downloading after a version bump.
- Keep the pinned expected hash and the origin artifact in lockstep when republishing.
- Wrap downloads in retry-with-backoff bounded to a small count to absorb transient corruption.
When it happens
Trigger: ComputeSha256Async runs over the downloaded file at filePath; expected is the pinned value from the service's hash table. The check is skipped (returns early) only when expected is empty, so a populated-but-wrong hash always throws this IOException.
Common situations: A truncated or partially written download (network drop, disk full), a CDN/origin that silently swapped the model artifact without bumping the pinned hash, a corrupt local cache from a previous interrupted run, or bit-rot on disk.
Related errors
- OmniVoice (CrispASR) model {fileName} failed integrity check
- OmniVoice {label} download failed integrity check (expected
- Qwen3 TTS {label} download failed integrity check (expected
- Qwen3 TTS (CrispASR) model {fileName} failed integrity check
- VibeVoice (CrispASR) model {fileName} failed integrity check
AI-assisted analysis of SubtitleEdit/subtitleedit@17a9f07487 (2026-08-13).
Data as JSON: /api/errors/7464408b2ebbeb83.
Report an issue: GitHub.