1
0
mirror of https://github.com/postgrespro/pg_probackup.git synced 2025-02-10 14:37:03 +02:00

Compare system_identifier of PGDATA with system_identifier of backup_conn

This commit is contained in:
Artur Zakirov 2017-04-05 19:48:55 +03:00
parent e3f9d5997a
commit 5c7669757d
7 changed files with 65 additions and 36 deletions

View File

@ -44,6 +44,8 @@ static volatile uint32 total_copy_files_increment;
static uint32 total_files_num; static uint32 total_files_num;
static pthread_mutex_t check_stream_mut = PTHREAD_MUTEX_INITIALIZER; static pthread_mutex_t check_stream_mut = PTHREAD_MUTEX_INITIALIZER;
static int is_ptrack_enable = false;
/* Backup connection */ /* Backup connection */
static PGconn *backup_conn = NULL; static PGconn *backup_conn = NULL;
@ -87,6 +89,7 @@ static char *pg_ptrack_get_and_clear(Oid tablespace_oid,
/* Check functions */ /* Check functions */
static void check_server_version(void); static void check_server_version(void);
static void check_system_identifier(void);
static void confirm_block_size(const char *name, int blcksz); static void confirm_block_size(const char *name, int blcksz);
@ -114,7 +117,6 @@ do_backup_database(parray *backup_list, bool smooth_checkpoint)
pthread_t backup_threads[num_threads]; pthread_t backup_threads[num_threads];
pthread_t stream_thread; pthread_t stream_thread;
backup_files_args *backup_threads_args[num_threads]; backup_files_args *backup_threads_args[num_threads];
bool is_ptrack_support;
/* repack the options */ /* repack the options */
pgBackup *prev_backup = NULL; pgBackup *prev_backup = NULL;
@ -131,15 +133,6 @@ do_backup_database(parray *backup_list, bool smooth_checkpoint)
*/ */
current.tli = get_current_timeline(false); current.tli = get_current_timeline(false);
is_ptrack_support = pg_ptrack_support();
if (current.backup_mode == BACKUP_MODE_DIFF_PTRACK && !is_ptrack_support)
elog(ERROR, "Current Postgres instance does not support ptrack");
if(current.backup_mode == BACKUP_MODE_DIFF_PTRACK && !pg_ptrack_enable())
elog(ERROR, "ptrack is disabled");
if (is_ptrack_support)
is_ptrack_support = pg_ptrack_enable();
/* /*
* In differential backup mode, check if there is an already-validated * In differential backup mode, check if there is an already-validated
* full backup on current timeline. * full backup on current timeline.
@ -153,8 +146,8 @@ do_backup_database(parray *backup_list, bool smooth_checkpoint)
"Create new full backup before an incremental one."); "Create new full backup before an incremental one.");
} }
/* clear ptrack files for FULL and DIFF backup */ /* Clear ptrack files for FULL and DIFF backup */
if (current.backup_mode != BACKUP_MODE_DIFF_PTRACK && is_ptrack_support) if (current.backup_mode != BACKUP_MODE_DIFF_PTRACK && is_ptrack_enable)
pg_ptrack_clear(); pg_ptrack_clear();
/* notify start of backup to PostgreSQL server */ /* notify start of backup to PostgreSQL server */
@ -410,12 +403,12 @@ do_backup(bool smooth_checkpoint)
/* PGDATA and BACKUP_MODE are always required */ /* PGDATA and BACKUP_MODE are always required */
if (pgdata == NULL) if (pgdata == NULL)
elog(ERROR, "Required parameter not specified: PGDATA " elog(ERROR, "required parameter not specified: PGDATA "
"(-D, --pgdata)"); "(-D, --pgdata)");
/* A backup mode is needed */ /* A backup mode is needed */
if (current.backup_mode == BACKUP_MODE_INVALID) if (current.backup_mode == BACKUP_MODE_INVALID)
elog(ERROR, "Required parameter not specified: BACKUP_MODE " elog(ERROR, "required parameter not specified: BACKUP_MODE "
"(-b, --backup-mode)"); "(-b, --backup-mode)");
/* Create connection for PostgreSQL */ /* Create connection for PostgreSQL */
@ -433,7 +426,20 @@ do_backup(bool smooth_checkpoint)
if (pg_is_standby() && !from_replica) if (pg_is_standby() && !from_replica)
elog(ERROR, "backup is not allowed for standby"); elog(ERROR, "backup is not allowed for standby");
/* show configuration actually used */ /* ptrack backup checks */
if (current.backup_mode == BACKUP_MODE_DIFF_PTRACK && !pg_ptrack_support())
elog(ERROR, "current Postgres instance does not support ptrack");
is_ptrack_enable = pg_ptrack_enable();
if(current.backup_mode == BACKUP_MODE_DIFF_PTRACK && !is_ptrack_enable)
elog(ERROR, "ptrack is disabled");
/* Get exclusive lock of backup catalog */
catalog_lock(true);
check_system_identifier();
/* Show configuration actually used */
elog(LOG, "========================================"); elog(LOG, "========================================");
elog(LOG, "backup start"); elog(LOG, "backup start");
elog(LOG, "----------------------------------------"); elog(LOG, "----------------------------------------");
@ -441,10 +447,7 @@ do_backup(bool smooth_checkpoint)
pgBackupWriteConfigSection(stderr, &current); pgBackupWriteConfigSection(stderr, &current);
elog(LOG, "----------------------------------------"); elog(LOG, "----------------------------------------");
/* get exclusive lock of backup catalog */ /* Initialize backup result */
catalog_lock(true);
/* initialize backup result */
current.status = BACKUP_STATUS_RUNNING; current.status = BACKUP_STATUS_RUNNING;
current.tli = 0; /* get from result of pg_start_backup() */ current.tli = 0; /* get from result of pg_start_backup() */
current.start_lsn = 0; current.start_lsn = 0;
@ -459,7 +462,7 @@ do_backup(bool smooth_checkpoint)
current.checksum_version = get_data_checksum_version(true); current.checksum_version = get_data_checksum_version(true);
current.stream = stream_wal; current.stream = stream_wal;
/* create backup directory and backup.ini */ /* Create backup directory and backup.ini */
if (!check) if (!check)
{ {
if (pgBackupCreateDir(&current)) if (pgBackupCreateDir(&current))
@ -544,6 +547,30 @@ check_server_version(void)
confirm_block_size("wal_block_size", XLOG_BLCKSZ); confirm_block_size("wal_block_size", XLOG_BLCKSZ);
} }
/*
* Compare system_identifier of PGDATA with system_identifier of backup_conn.
*/
static void
check_system_identifier(void)
{
PGresult *res;
uint64 id;
char *val;
res = pgut_execute(backup_conn,
"SELECT system_identifier FROM pg_control_system()",
0, NULL);
val = PQgetvalue(res, 0, 0);
PQclear(res);
if (!parse_uint64(val, &id))
elog(ERROR, "%s is not system_identifier", val);
if (id != system_identifier)
elog(ERROR, "target data directory was initialized for system id %ld, but connected instance system id is %ld",
system_identifier, id);
}
static void static void
confirm_block_size(const char *name, int blcksz) confirm_block_size(const char *name, int blcksz)
{ {

View File

@ -215,9 +215,9 @@ catalog_lock(bool check_catalog)
Assert(pgdata); Assert(pgdata);
/* Check system-identifier */ /* Check system-identifier */
id = get_system_identifier(true); id = get_system_identifier(false);
if (id != system_identifier) if (id != system_identifier)
elog(ERROR, "Backup directory was initialized for system id = %ld, but target system id = %ld", elog(ERROR, "backup directory was initialized for system id %ld, but target system id is %ld",
system_identifier, id); system_identifier, id);
} }
} }

8
init.c
View File

@ -30,7 +30,7 @@ do_init(void)
char path[MAXPGPATH]; char path[MAXPGPATH];
char arclog_path_dir[MAXPGPATH]; char arclog_path_dir[MAXPGPATH];
FILE *fp; FILE *fp;
uint64 _system_identifier; uint64 id;
struct dirent **dp; struct dirent **dp;
int results; int results;
@ -47,6 +47,9 @@ do_init(void)
elog(ERROR, "backup catalog already exist and it's not empty"); elog(ERROR, "backup catalog already exist and it's not empty");
} }
/* Read system_identifier from PGDATA */
id = get_system_identifier(false);
/* create backup catalog root directory */ /* create backup catalog root directory */
dir_create_dir(backup_path, DIR_PERMISSION); dir_create_dir(backup_path, DIR_PERMISSION);
@ -58,7 +61,6 @@ do_init(void)
join_path_components(arclog_path_dir, backup_path, "wal"); join_path_components(arclog_path_dir, backup_path, "wal");
dir_create_dir(arclog_path_dir, DIR_PERMISSION); dir_create_dir(arclog_path_dir, DIR_PERMISSION);
_system_identifier = get_system_identifier(false);
/* create pg_probackup.conf */ /* create pg_probackup.conf */
join_path_components(path, backup_path, BACKUP_CATALOG_CONF_FILE); join_path_components(path, backup_path, BACKUP_CATALOG_CONF_FILE);
fp = fopen(path, "wt"); fp = fopen(path, "wt");
@ -66,7 +68,7 @@ do_init(void)
elog(ERROR, "cannot create %s: %s", elog(ERROR, "cannot create %s: %s",
BACKUP_CATALOG_CONF_FILE, strerror(errno)); BACKUP_CATALOG_CONF_FILE, strerror(errno));
fprintf(fp, "system-identifier = %li\n", _system_identifier); fprintf(fp, "system-identifier = %li\n", id);
fprintf(fp, "\n"); fprintf(fp, "\n");
fclose(fp); fclose(fp);

View File

@ -457,7 +457,7 @@ restore_directories(const char *pg_data_dir, const char *backup_dir)
* it again. * it again.
*/ */
if (!dir_is_empty(linked_path)) if (!dir_is_empty(linked_path))
elog(ERROR, "restore destination is not empty: \"%s\"", elog(ERROR, "restore tablespace destination is not empty: \"%s\"",
linked_path); linked_path);
if (link_sep) if (link_sep)
@ -560,7 +560,7 @@ check_tablespace_mapping(pgBackup *backup)
linked_path); linked_path);
if (!dir_is_empty(linked_path)) if (!dir_is_empty(linked_path))
elog(ERROR, "restore destination is not empty: \"%s\"", elog(ERROR, "restore tablespace destination is not empty: \"%s\"",
linked_path); linked_path);
} }
@ -1071,7 +1071,7 @@ get_tablespace_mapping(const char *dir)
/* /*
* Save create directory path into memory. We can use it in next page restore to * Save create directory path into memory. We can use it in next page restore to
* not raise the error "restore destination is not empty" in * not raise the error "restore tablespace destination is not empty" in
* restore_directories(). * restore_directories().
*/ */
static void static void

View File

@ -48,7 +48,7 @@ class OptionTest(ProbackupTest, unittest.TestCase):
# backup command failure without backup mode option # backup command failure without backup mode option
self.assertEqual( self.assertEqual(
self.run_pb(["backup", "-B", self.backup_dir(node), "-D", node.data_dir]), self.run_pb(["backup", "-B", self.backup_dir(node), "-D", node.data_dir]),
six.b("ERROR: Required parameter not specified: BACKUP_MODE (-b, --backup-mode)\n") six.b("ERROR: required parameter not specified: BACKUP_MODE (-b, --backup-mode)\n")
) )
# backup command failure with invalid backup mode option # backup command failure with invalid backup mode option

View File

@ -524,7 +524,7 @@ class RestoreTest(ProbackupTest, unittest.TestCase):
# 2 - Try to restore to existing tablespace directory # 2 - Try to restore to existing tablespace directory
node.cleanup() node.cleanup()
self.assertIn(six.b("ERROR: restore destination is not empty"), self.assertIn(six.b("ERROR: restore tablespace destination is not empty"),
self.restore_pb(node)) self.restore_pb(node))
# 3 - Restore using tablespace-mapping # 3 - Restore using tablespace-mapping