astrid-runtime/astrid · error
WinFsp mountpoint did not become ready within
Error message
WinFsp mountpoint did not become ready within {} seconds: {} What it means
wait_for_mountpoint_ready loops (25 ms sleeps) until the mountpoint metadata shows a directory, bounded by MOUNTPOINT_READY_TIMEOUT. If the WinFsp mount never materializes as a browsable directory within the timeout, the function bails with the elapsed seconds and the path. It signals the mount failed to come up rather than hanging forever.
Solutions
- Verify WinFsp is installed and the version matches the crate's requirement (check C:\Program Files (x86)\WinFsp)
- Capture and inspect the daemon/service stderr for the earlier failure that prevented the mount
- Increase MOUNTPOINT_READY_TIMEOUT if the environment is slow (rebuild the crate)
- Test the same mount manually with winfsp-x.dll test tools or `net use` to isolate driver vs. app issues
Example fix
// before const MOUNTPOINT_READY_TIMEOUT: Duration = Duration::from_secs(5); // after const MOUNTPOINT_READY_TIMEOUT: Duration = Duration::from_secs(30);
Defensive patterns
Strategy: retry
Validate before calling
// verify WinFsp is present before mounting
if !Path::new("C:\\Program Files (x86)\\WinFsp\\bin\\winfsp-x64.dll").exists() {
return Err("WinFsp driver not installed".into());
} Type guard
fn mountpoint_became_dir(p: &Path, timeout: Duration) -> bool {
let start = std::time::Instant::now();
while start.elapsed() < timeout {
if std::fs::metadata(p).map(|m| m.is_dir()).unwrap_or(false) { return true; }
std::thread::sleep(Duration::from_millis(25));
}
false
} Try / catch
match mount_err {
Err(e) if e.to_string().contains("did not become ready") => {
// capture daemon stderr, check WinFsp install, then retry once with longer timeout
collect_daemon_logs()?;
retry_mount_with_timeout(Duration::from_secs(60))?;
}
other => other?,
} Prevention
- Install/verify the matching WinFsp release before mounting
- Propagate daemon stderr so earlier failures surface instead of a bare timeout
- Allow a generous timeout on slow or heavily loaded machines
- Smoke-test mounts at boot in CI
When it happens
Trigger: The WinFsp filesystem failed to start or register the junction (driver missing, service start failure, invalid filesystem parameters), so the poll sees only NotFound until the timeout elapses.
Common situations: WinFsp driver not installed or wrong version; the FSD/security descriptor rejected the mount; the daemon crashed after launching; slow system startup exceeding the configured timeout on heavily loaded machines.
Understand the failure class
Background: Request timed out: what client-side request timeouts mean across libraries (Request timed out, TIMED_OUT, APITimeoutError) — this error's family across 39 libraries.
Related errors
- no free Windows drive target is available; specify a…
- WinFsp control endpoint remained live after stop
- WinFsp failed to start mount with status
- WinFsp failed to start private mount
- WinFsp mountpoint is not a directory
AI-assisted analysis of astrid-runtime/astrid@affd8760f4 (2026-09-09).
Data as JSON: /api/errors/4e0554746602c5e7.
Report an issue: GitHub.
Appendix: source
Thrown at crates/astrid-storage-provider-winfsp/src/win.rs:123
// rather than inspecting the junction object itself.
match std::fs::metadata(mountpoint) {
Ok(metadata) if metadata.is_dir() => return Ok(()),
Ok(_) => bail!(
"WinFsp mountpoint is not a directory: {}",
mountpoint.display()
),
Err(error) if error.kind() == std::io::ErrorKind::NotFound => {},
Err(error) => {
return Err(error).with_context(|| {
format!(
"inspect WinFsp mountpoint readiness {}",
mountpoint.display()
)
});
},
}
if started.elapsed() >= MOUNTPOINT_READY_TIMEOUT {
bail!(
"WinFsp mountpoint did not become ready within {} seconds: {}",
MOUNTPOINT_READY_TIMEOUT.as_secs(),
mountpoint.display()
);
}
std::thread::sleep(Duration::from_millis(25));
}
}
#[derive(Debug, serde::Deserialize, serde::Serialize)]
#[serde(rename_all = "kebab-case", tag = "operation", deny_unknown_fields)]
enum ServiceControlRequest {
/// Probe service state with the broker bearer.
Status { token: String },
/// Stop and unmount the private service.
Stop { token: String },
}
View on GitHub (pinned to affd8760f4)