Hmbown/CodeWhale · error
The running executable path changed during the update; no…
Error message
The running executable path changed during the update; no further files were replaced. Run the intended executable again by its full path.
What it means
Before replacing files, the updater re-reads its own executable path and compares the SHA-256 of the bytes on disk to the hash recorded at update start. A mismatch means the file at the recorded path changed underneath the running process (it was replaced, edited, or a different binary now sits there), so the updater aborts having replaced nothing and tells the user to relaunch by full path.
Solutions
- Run the intended executable again by its full path (as the message says) so the identity is recomputed against the bytes actually on disk, then retry the update.
- Verify with `sha256sum <path>` which binary now occupies the path and reinstall the expected version if it is wrong.
- Prevent concurrent writers: do not run two updaters or installers against the same install directory at once.
- If it happens repeatedly, check antivirus/sync tools replacing the binary and exclude the install directory.
Defensive patterns
Strategy: try-catch
Validate before calling
let bytes = std::fs::read(&running_path)?;
let current = sha256_hex(&bytes);
if current != recorded_hash {
eprintln!("binary at {running_path:?} changed since start; restart by full path before updating");
} Try / catch
match run_update() {
Err(e) if e.to_string().contains("running executable path changed") => {
// no files were replaced; safely restart the intended binary by full path and retry
}
other => other?,
} Prevention
- Never run two updaters against the same install directory concurrently.
- Re-run the updater by its full path after any external modification of the binary.
- Exclude install directories from sync/antivirus tools.
- Record and compare the binary hash before launching an update session.
When it happens
Trigger: validate_primary_update_identity, called at the start of run_update's swap phase, when sha256_hex(std::fs::read(identity.path)) differs from identity.file_hash.
Common situations: Another update/install overwrote the binary while this one ran; the user or a tool edited or replaced the executable mid-update; running from a copy that was subsequently overwritten; a previous aborted swap left a different binary at the path.
Understand the failure class
Background: Checksum mismatch errors: "checksum verification failed", "digest mismatch", "expected vs actual checksum" — what they mean and how to fix them — this error's family across 41 libraries.
Related errors
- Android loaded-image identity changed: /proc/self/maps has…
- Android loaded-image proof changed from
- SHA256 mismatch for from ! expected: actual
- Android identifies runtime linker ` `; refusing to use the…
- Android reported deleted loaded image
AI-assisted analysis of Hmbown/CodeWhale@73e0f67d83 (2026-09-22).
Data as JSON: /api/errors/9c58a0942daf71b9.
Report an issue: GitHub.
Appendix: source
Thrown at crates/cli/src/update.rs:556
let minor = ((device & 0xff) | ((device >> 12) & 0xfff00)) as u32;
(major, minor)
}
fn validate_primary_update_identity(identity: &UpdateExecutableIdentity) -> Result<()> {
#[cfg(target_os = "android")]
{
let fresh = android_loaded_executable_proof()?;
if fresh != identity.android_proof {
bail!(
"Android loaded-image proof changed from {:?} to {:?}; refusing to replace the update target",
identity.android_proof,
fresh
);
}
}
let bytes = std::fs::read(&identity.path).context("failed to recheck updater binary")?;
if sha256_hex(&bytes) != identity.file_hash {
bail!(
"The running executable path changed during the update; no further files were replaced. Run the intended executable again by its full path."
);
}
Ok(())
}
/// Only the running binary and copies of those exact bytes are ours to update.
/// Command names alone do not establish ownership of an existing sibling.
fn validate_update_target(target: &Path, identity: &UpdateExecutableIdentity) -> Result<()> {
if !InstallMethod::from_path(target).supports_self_update() || protected_update_path(target) {
bail!(
"Refusing to replace managed/system path {}.\n\n{GITHUB_MIGRATION_HELP}",
target.display()
);
}
let metadata = match std::fs::symlink_metadata(target) {
Ok(metadata) => metadata,
Err(error) if error.kind() == std::io::ErrorKind::NotFound && target != identity.path => {View on GitHub (pinned to 73e0f67d83)