From f787ba327a17805694b730da7c205dfe5493fdd0 Mon Sep 17 00:00:00 2001 From: Curtis McEnroe Date: Mon, 28 Oct 2019 23:43:04 -0400 Subject: Lock save file --- bounce.c | 49 +++++++++++++++++++++++++++++-------------------- 1 file changed, 29 insertions(+), 20 deletions(-) (limited to 'bounce.c') diff --git a/bounce.c b/bounce.c index 4e7458c..ff54c98 100644 --- a/bounce.c +++ b/bounce.c @@ -23,6 +23,7 @@ #include #include #include +#include #include #include #include @@ -67,6 +68,33 @@ static void eventRemove(size_t i) { event.clients[i] = event.clients[event.len]; } +static FILE *saveFile; + +static void saveExit(void) { + int error = ringSave(saveFile); + if (error) warn("fwrite"); + error = fclose(saveFile); + if (error) warn("fclose"); +} + +static void saveLoad(const char *path) { + umask(0066); + saveFile = fopen(path, "a+"); + if (!saveFile) err(EX_CANTCREAT, "%s", path); + + int error = flock(fileno(saveFile), LOCK_EX | LOCK_NB); + if (error && errno != EWOULDBLOCK) err(EX_OSERR, "flock"); + if (error) errx(EX_CANTCREAT, "%s: lock held by other process", path); + + rewind(saveFile); + ringLoad(saveFile); + + error = ftruncate(fileno(saveFile), 0); + if (error) err(EX_IOERR, "ftruncate"); + + atexit(saveExit); +} + static char *sensitive(char *arg) { char *value = NULL; if (arg[0] == '@') { @@ -89,14 +117,6 @@ static char *sensitive(char *arg) { return value; } -static FILE *saveFile; -static void exitSave(void) { - int error = ringSave(saveFile); - if (error) warn("fwrite"); - error = fclose(saveFile); - if (error) warn("fclose"); -} - int main(int argc, char *argv[]) { const char *localHost = "localhost"; const char *localPort = "6697"; @@ -158,18 +178,7 @@ int main(int argc, char *argv[]) { if (!user) user = nick; if (!real) real = nick; - if (save) { - umask(0066); - saveFile = fopen(save, "a+"); - if (!saveFile) err(EX_CANTCREAT, "%s", save); - - rewind(saveFile); - ringLoad(saveFile); - - int error = ftruncate(fileno(saveFile), 0); - if (error) err(EX_IOERR, "ftruncate"); - atexit(exitSave); - } + if (save) saveLoad(save); listenConfig(certPath, privPath); -- cgit 1.4.1