diff options
author | Heikki Linnakangas <heikki.linnakangas@iki.fi> | 2015-03-23 19:47:52 +0200 |
---|---|---|
committer | Heikki Linnakangas <heikki.linnakangas@iki.fi> | 2015-03-23 19:47:52 +0200 |
commit | 61081e75c6741024f7717ade0450090590e96c85 (patch) | |
tree | 9b4fde1d8bae566036df68eecdfd84b896e14b57 /src/bin/pg_rewind/logging.c | |
parent | 87cec51d3ad1107f6f224ed7d773e70c8896e4c0 (diff) | |
download | postgresql-61081e75c6741024f7717ade0450090590e96c85.tar.gz |
Add pg_rewind, for re-synchronizing a master server after failback.
Earlier versions of this tool were available (and still are) on github.
Thanks to Michael Paquier, Alvaro Herrera, Peter Eisentraut, Amit Kapila,
and Satoshi Nagayasu for review.
Diffstat (limited to 'src/bin/pg_rewind/logging.c')
-rw-r--r-- | src/bin/pg_rewind/logging.c | 140 |
1 files changed, 140 insertions, 0 deletions
diff --git a/src/bin/pg_rewind/logging.c b/src/bin/pg_rewind/logging.c new file mode 100644 index 0000000000..aba12d842e --- /dev/null +++ b/src/bin/pg_rewind/logging.c @@ -0,0 +1,140 @@ +/*------------------------------------------------------------------------- + * + * logging.c + * logging functions + * + * Copyright (c) 2010-2015, PostgreSQL Global Development Group + * + *------------------------------------------------------------------------- + */ +#include "postgres_fe.h" + +#include <unistd.h> +#include <time.h> + +#include "pg_rewind.h" +#include "logging.h" + +#include "pgtime.h" + +/* Progress counters */ +uint64 fetch_size; +uint64 fetch_done; + +static pg_time_t last_progress_report = 0; + +#define QUERY_ALLOC 8192 + +#define MESSAGE_WIDTH 60 + +static +pg_attribute_printf(2, 0) +void +pg_log_v(eLogType type, const char *fmt, va_list ap) +{ + char message[QUERY_ALLOC]; + + vsnprintf(message, sizeof(message), fmt, ap); + + switch (type) + { + case PG_DEBUG: + if (debug) + printf("%s", _(message)); + break; + + case PG_PROGRESS: + if (showprogress) + printf("%s", _(message)); + break; + + case PG_WARNING: + printf("%s", _(message)); + break; + + case PG_FATAL: + printf("\n%s", _(message)); + printf("%s", _("Failure, exiting\n")); + exit(1); + break; + + default: + break; + } + fflush(stdout); +} + + +void +pg_log(eLogType type, const char *fmt,...) +{ + va_list args; + + va_start(args, fmt); + pg_log_v(type, fmt, args); + va_end(args); +} + + +void +pg_fatal(const char *fmt,...) +{ + va_list args; + + va_start(args, fmt); + pg_log_v(PG_FATAL, fmt, args); + va_end(args); + /* should not get here, pg_log_v() exited already */ + exit(1); +} + + +/* + * Print a progress report based on the global variables. + * + * Progress report is written at maximum once per second, unless the + * force parameter is set to true. + */ +void +progress_report(bool force) +{ + int percent; + char fetch_done_str[32]; + char fetch_size_str[32]; + pg_time_t now; + + if (!showprogress) + return; + + now = time(NULL); + if (now == last_progress_report && !force) + return; /* Max once per second */ + + last_progress_report = now; + percent = fetch_size ? (int) ((fetch_done) * 100 / fetch_size) : 0; + + /* + * Avoid overflowing past 100% or the full size. This may make the total + * size number change as we approach the end of the backup (the estimate + * will always be wrong if WAL is included), but that's better than having + * the done column be bigger than the total. + */ + if (percent > 100) + percent = 100; + if (fetch_done > fetch_size) + fetch_size = fetch_done; + + /* + * Separate step to keep platform-dependent format code out of + * translatable strings. And we only test for INT64_FORMAT availability + * in snprintf, not fprintf. + */ + snprintf(fetch_done_str, sizeof(fetch_done_str), INT64_FORMAT, + fetch_done / 1024); + snprintf(fetch_size_str, sizeof(fetch_size_str), INT64_FORMAT, + fetch_size / 1024); + + pg_log(PG_PROGRESS, "%*s/%s kB (%d%%) copied\r", + (int) strlen(fetch_size_str), fetch_done_str, fetch_size_str, + percent); +} |