aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--uid.c38
1 files changed, 28 insertions, 10 deletions
diff --git a/uid.c b/uid.c
index b98019b9..dc88f0cd 100644
--- a/uid.c
+++ b/uid.c
@@ -134,7 +134,7 @@ void initialize_saved_lists(struct query *hostlist, const char *idfile)
if (lstat(idfile, &statbuf) < 0) {
if (errno == ENOTDIR)
{
- report(stderr, GT_("lstat: %s: %s\n"), idfile, strerror(errno));
+ report(stderr, "lstat: %s: %s\n", idfile, strerror(errno));
exit(PS_IOERR);
}
}
@@ -292,8 +292,7 @@ void initialize_saved_lists(struct query *hostlist, const char *idfile)
/* return the end list element for direct modification */
struct idlist *save_str(struct idlist **idl, const char *str, flag st)
{
- return *save_str_quick(idl, str ? xstrdup(str) : NULL,
- st);
+ return *save_str_quick(idl, str ? xstrdup(str) : NULL, st);
}
void free_str_list(struct idlist **idl)
@@ -538,11 +537,12 @@ void uid_swap_lists(struct query *ctl)
if (ctl->newsaved)
{
/* old state of mailbox may now be irrelevant */
+ struct idlist **temp = &ctl->oldsaved;
if (outlevel >= O_DEBUG)
report(stdout, GT_("swapping UID lists\n"));
- free_str_list(&ctl->oldsaved);
ctl->oldsaved = ctl->newsaved;
ctl->newsaved = (struct idlist *) NULL;
+ free_str_list(temp);
}
/* in fast uidl, there is no need to swap lists: the old state of
* mailbox cannot be discarded! */
@@ -608,14 +608,17 @@ void write_saved_lists(struct query *hostlist, const char *idfile)
{
if (outlevel >= O_DEBUG)
report(stdout, GT_("Deleting fetchids file.\n"));
- unlink(idfile);
- }
- else
- {
+ if (unlink(idfile))
+ report(stderr, GT_("Error deleting %s: %s\n"), strerror(errno));
+ } else {
+ char *newnam = xmalloc(strlen(idfile) + 2);
+ strcpy(newnam, idfile);
+ strcat(newnam, "_");
if (outlevel >= O_DEBUG)
report(stdout, GT_("Writing fetchids file.\n"));
- /* FIXME: do not overwrite the old idfile */
- if ((tmpfp = fopen(idfile, "w")) != (FILE *)NULL) {
+ (void)unlink(newnam); /* remove file/link first */
+ if ((tmpfp = fopen(newnam, "w")) != (FILE *)NULL) {
+ int errflg;
for (ctl = hostlist; ctl; ctl = ctl->next) {
for (idp = ctl->oldsaved; idp; idp = idp->next)
if (idp->val.status.mark == UID_SEEN
@@ -625,8 +628,23 @@ void write_saved_lists(struct query *hostlist, const char *idfile)
}
for (idp = scratchlist; idp; idp = idp->next)
fputs(idp->id, tmpfp);
+ fflush(tmpfp);
+ errflg = ferror(tmpfp);
fclose(tmpfp);
+ /* if we could write successfully, move into place;
+ * otherwise, drop */
+ if (errflg) {
+ report(stderr, GT_("Error writing to fetchids file %s, old file left in place.\n"), newnam);
+ unlink(newnam);
+ } else {
+ if (rename(newnam, idfile)) {
+ report(stderr, GT_("Cannot rename fetchids file %s to %s: %s\n"), newnam, idfile, strerror(errno));
+ }
+ }
+ } else {
+ report(stderr, GT_("Cannot open fetchids file %s for writing: %s\n"), newnam, strerror(errno));
}
+ free(newnam);
}
}
#endif /* POP3_ENABLE */