shadow1ng/fscan · error
Unable to create persistence directory
Error message
Unable to create persistence directory
What it means
copyToPersistPath tries a list of candidate persistence directories (via os.MkdirAll) and, if it could not create or use any of them (targetDir stays empty), returns this error. It typically means every candidate path was unwritable or failed to be created due to permissions or a full filesystem.
Source
Thrown at plugins/local/crontask.go:169
// 获取用户目录
if usr, err := user.Current(); err == nil {
userDirs := []string{
filepath.Join(usr.HomeDir, ".local", "bin"),
filepath.Join(usr.HomeDir, ".cache"),
}
persistDirs = append(userDirs, persistDirs...)
}
var targetDir string
for _, dir := range persistDirs {
if err := os.MkdirAll(dir, 0755); err == nil {
targetDir = dir
break
}
}
if targetDir == "" {
return "", fmt.Errorf("%s", i18n.GetText("persistence_dir_create_failed"))
}
// 生成隐藏文件名
basename := filepath.Base(p.targetFile)
hiddenName := "." + strings.TrimSuffix(basename, filepath.Ext(basename))
if p.isScriptFile() {
hiddenName += ".sh"
}
targetPath := filepath.Join(targetDir, hiddenName)
// 复制文件
err := p.copyFile(p.targetFile, targetPath)
if err != nil {
return "", err
}
// 设置执行权限View on GitHub (pinned to 95cc12e753)
Solutions
- Re-run as root (or with CAP_DAC_OVERRIDE) so the persistence directories can be created.
- Pre-create one of the candidate directories and grant the current user write permission.
- Point the persistence location at a user-writable path (e.g. user crontab area) if root is unavailable.
- Check disk space / mount flags (ro) if permissions look correct.
Example fix
// before $ ./agent --plugin crontask # running as low-priv user // after $ sudo ./agent --plugin crontask # or, pre-provision: $ sudo mkdir -p /var/spool/cron && sudo chown agent /var/spool/cron
Defensive patterns
Strategy: try-catch
Validate before calling
for _, dir := range candidateDirs {
if info, err := os.Stat(dir); err == nil && info.IsDir() {
if f, err := os.CreateTemp(dir, ".w"); err == nil { f.Close(); os.Remove(f.Name()); break }
}
} Try / catch
res := plugin.Scan(ctx, cfg)
if !res.Success && strings.Contains(res.Error.Error(), "persistence directory") {
return fmt.Errorf("needs root or writable persistence dir: %w", res.Error)
} Prevention
- Run persistence plugins with the privileges they require (root).
- Pre-create the persistence directory with correct ownership in provisioning.
- Avoid read-only root filesystems when persistence plugins are enabled.
When it happens
Trigger: Running the crontask plugin as a non-root user when all candidate persistence directories require root; read-only root filesystem (containers); MkdirAll failing on every candidate due to permission or disk errors.
Common situations: Persistence attempted on a hardened/minimal container without write access to standard cron locations; running the agent under a restricted service account; immutable or read-only /etc, /var, or $HOME.
Understand the failure class
Background: mkdir permission denied (EACCES): failed to create directory errors explained — this error's family across 32 libraries.
Related errors
- Unable to create any system cron task
- service_dir_create_failed
- failed to create TXT file: %w
- Unsupported platform: {{.Arg1}}
- Target file not specified
AI-assisted analysis of shadow1ng/fscan@95cc12e753 (2026-09-06).
Data as JSON: /api/errors/47f745677d99811c.
Report an issue: GitHub.