commaai/openpilot · error
failed to create Cabana settings directory
Error message
failed to create Cabana settings directory %s: %s
What it means
Emitted by ensureSettingsDirectory() in tools/cabana/settings.cc when std::filesystem::create_directories on the parent of the settings file (utils::configPath()) reports an error via the std::error_code overload. This means Cabana cannot even create the directory that would hold cabana.json, so settings persistence will fail. The function returns false so callers know saving is unavailable.
Solutions
- Inspect the printed path and errno message; usually fix with `mkdir -p <configPath>` as the right user or `rm` the regular file blocking the directory.
- Ensure HOME is set and writable for the user running cabana (the message text names the exact parent path).
- Check permissions/ownership: `chown -R $USER <configPath parent>` or chmod u+w.
- If intentional (read-only rootfs), ignore — Cabana runs with default settings, it just cannot persist them.
Example fix
# before: message says e.g. 'failed to create Cabana settings directory /home/user/.comma: Not a directory' ls -la /home/user/.comma # a regular file is squatting on the path rm /home/user/.comma # after: directory is created on next start, message gone
Defensive patterns
Strategy: validation
Validate before calling
// Pre-check directory creatability before cabana tries to save settings:
bool configDirUsable(const std::filesystem::path &dir) {
std::error_code ec;
std::filesystem::create_directories(dir, ec);
if (ec) return false;
auto probe = dir / ".write-probe";
std::ofstream t(probe);
bool ok = t.good();
t.close();
std::filesystem::remove(probe);
return ok;
} Prevention
- Run cabana under the user that owns the config directory (~/.comma).
- In containers/CI, set HOME to a writable path or mount a writable volume at the config dir.
- Don't place regular files where the config directory path is expected.
When it happens
Trigger: Calling ensureSettingsDirectory() (directly or via saveSettings) when the config directory path cannot be created: a component of utils::configPath() exists as a regular file, the user lacks write permission on the parent, the path is on a read-only mount, or (rarely) the path exceeds NAME_MAX/PATH_MAX. The error_code out-param is non-zero after create_directories(path.parent_path(), error).
Common situations: Running Cabana as a different user than the one owning ~/.comma; HOME unset or pointing somewhere non-writable (CI containers, root shells); a stale regular file sitting where the directory should be; read-only NFS/container mounts.
Related errors
- failed to create temporary Cabana settings
- failed to lock Cabana settings
- failed to preserve corrupt Cabana settings
- failed to read Cabana settings
- failed to save Cabana settings to
AI-assisted analysis of commaai/openpilot@516ec1e682 (2026-08-15).
Data as JSON: /api/errors/d01a53d0d66f72b9.
Report an issue: GitHub.
Appendix: source
Thrown at openpilot/tools/cabana/settings.cc:92
std::ifstream input(settingsFile());
if (!input) return {};
const std::string contents{std::istreambuf_iterator<char>(input), std::istreambuf_iterator<char>()};
std::string error;
auto settings_json = json11::Json::parse(contents, error);
if (!error.empty() || !settings_json.is_object()) {
fprintf(stderr, "failed to read Cabana settings %s%s%s\n", settingsFile().c_str(), error.empty() ? "" : ": ", error.c_str());
return {.exists = true, .valid = false};
}
return {.values = settings_json.object_items(), .exists = true};
}
bool ensureSettingsDirectory() {
const auto path = settingsFile();
std::error_code error;
std::filesystem::create_directories(path.parent_path(), error);
if (error) {
fprintf(stderr, "failed to create Cabana settings directory %s: %s\n", path.parent_path().c_str(), error.message().c_str());
return false;
}
return true;
}
bool writeAll(int fd, const std::string &data) {
size_t written = 0;
while (written < data.size()) {
ssize_t result = write(fd, data.data() + written, data.size() - written);
if (result < 0 && errno == EINTR) continue;
if (result <= 0) return false;
written += result;
}
return true;
}
bool saveSettings(const json11::Json::object &settings_json) {
const auto path = settingsFile();View on GitHub (pinned to 516ec1e682)