diff --git a/src/lib-config/write.c b/src/lib-config/write.c index 255d79c0..b8ef6156 100644 --- a/src/lib-config/write.c +++ b/src/lib-config/write.c @@ -302,6 +302,7 @@ int config_write(CONFIG_REC *rec, const char *fname, int create_mode) int ret; int fd; int save_errno; + const char *base_name; char *tmp_name = NULL; char *dest_name = NULL; @@ -309,12 +310,20 @@ int config_write(CONFIG_REC *rec, const char *fname, int create_mode) g_return_val_if_fail(fname != NULL || rec->fname != NULL, -1); g_return_val_if_fail(create_mode != -1 || rec->create_mode != -1, -1); + base_name = fname != NULL ? fname : rec->fname; + /* expand all symlinks; else we may replace a symlink with a regular file */ - dest_name = realpath(fname != NULL ? fname : rec->fname, NULL); + dest_name = realpath(base_name, NULL); + if (dest_name == NULL) { - config_error(rec, g_strerror(errno)); - ret = -1; - goto out; + if (errno == ENOENT) { + dest_name = g_strdup(base_name); + errno = 0; + } else { + config_error(rec, g_strerror(errno)); + ret = -1; + goto out; + } } tmp_name = g_strdup_printf("%s.XXXXXX", dest_name);