/* *SetmaskbasedonPGDATApermissions,neededforthecreationofthe *outputdirectorieswithcorrectpermissions.
*/ if (!GetDataDirectoryCreatePerm(new_cluster.pgdata))
pg_fatal("could not read permissions of directory \"%s\": %m",
new_cluster.pgdata);
log_opts.rootdir = (char *) pg_malloc0(MAXPGPATH);
len = snprintf(log_opts.rootdir, MAXPGPATH, "%s/%s", pgdata, BASE_OUTPUTDIR); if (len >= MAXPGPATH)
pg_fatal("directory path for new cluster is too long");
/* BASE_OUTPUTDIR/$timestamp/ */
gettimeofday(&time, NULL);
tt = (time_t) time.tv_sec;
strftime(timebuf, sizeof(timebuf), "%Y%m%dT%H%M%S", localtime(&tt)); /* append milliseconds */
snprintf(timebuf + strlen(timebuf), sizeof(timebuf) - strlen(timebuf), ".%03d", (int) (time.tv_usec / 1000));
log_opts.basedir = (char *) pg_malloc0(MAXPGPATH);
len = snprintf(log_opts.basedir, MAXPGPATH, "%s/%s", log_opts.rootdir,
timebuf); if (len >= MAXPGPATH)
pg_fatal("directory path for new cluster is too long");
/* BASE_OUTPUTDIR/$timestamp/dump/ */
log_opts.dumpdir = (char *) pg_malloc0(MAXPGPATH);
len = snprintf(log_opts.dumpdir, MAXPGPATH, "%s/%s/%s", log_opts.rootdir,
timebuf, DUMP_OUTPUTDIR); if (len >= MAXPGPATH)
pg_fatal("directory path for new cluster is too long");
/* BASE_OUTPUTDIR/$timestamp/log/ */
log_opts.logdir = (char *) pg_malloc0(MAXPGPATH);
len = snprintf(log_opts.logdir, MAXPGPATH, "%s/%s/%s", log_opts.rootdir,
timebuf, LOG_OUTPUTDIR); if (len >= MAXPGPATH)
pg_fatal("directory path for new cluster is too long");
/* *Ignoretheerrorcasewheretherootpathexists,asitiskeptthe *sameacrossruns.
*/ if (mkdir(log_opts.rootdir, pg_dir_create_mode) < 0 && errno != EEXIST)
pg_fatal("could not create directory \"%s\": %m", log_opts.rootdir); if (mkdir(log_opts.basedir, pg_dir_create_mode) < 0)
pg_fatal("could not create directory \"%s\": %m", log_opts.basedir); if (mkdir(log_opts.dumpdir, pg_dir_create_mode) < 0)
pg_fatal("could not create directory \"%s\": %m", log_opts.dumpdir); if (mkdir(log_opts.logdir, pg_dir_create_mode) < 0)
pg_fatal("could not create directory \"%s\": %m", log_opts.logdir);
len = snprintf(filename_path, sizeof(filename_path), "%s/%s",
log_opts.logdir, INTERNAL_LOG_FILE); if (len >= sizeof(filename_path))
pg_fatal("directory path for new cluster is too long");
if ((log_opts.internal = fopen_priv(filename_path, "a")) == NULL)
pg_fatal("could not open log file \"%s\": %m", filename_path);
/* label start of upgrade in logfiles */ for (filename = output_files; *filename != NULL; filename++)
{
len = snprintf(filename_path, sizeof(filename_path), "%s/%s",
log_opts.logdir, *filename); if (len >= sizeof(filename_path))
pg_fatal("directory path for new cluster is too long"); if ((fp = fopen_priv(filename_path, "a")) == NULL)
pg_fatal("could not write to log file \"%s\": %m", filename_path);
fprintf(fp, "-----------------------------------------------------------------\n" " pg_upgrade run on %s" "-----------------------------------------------------------------\n\n",
ctime(&run_time));
fclose(fp);
}
}
/* *Incasetheuserhasn'tspecifiedthedirectoryforthenewbinaries *with-B,defaulttousingthepathofthecurrentlyexecutedpg_upgrade *binary.
*/ if (!new_cluster.bindir)
{ char exec_path[MAXPGPATH];
if (find_my_exec(argv0, exec_path) < 0)
pg_fatal("%s: could not find own program executable", argv0); /* Trim off program name and keep just path */
*last_dir_separator(exec_path) = '\0';
canonicalize_path(exec_path);
new_cluster.bindir = pg_strdup(exec_path);
}
verify_directories();
/* no postmasters should be running, except for a live check */ if (pid_lock_file_exists(old_cluster.pgdata))
{ /* *Ifwehaveapostmaster.pidfile,trytostarttheserver.Ifit *starts,thepidfilewasstale,sostoptheserver.Ifitdoesn't *start,assumetheserverisrunning.Ifthepidfileisleftover *fromaservercrash,thisalsoallowsanycommittedtransactions *storedintheWALtobereplayedsotheyarenotlost,becauseWAL *filesarenottransferredfromoldtonewservers.Welatercheck *foracleanshutdown.
*/ if (start_postmaster(&old_cluster, false))
stop_postmaster(false); else
{ if (!user_opts.check)
pg_fatal("There seems to be a postmaster servicing the old cluster.\n" "Please shutdown that postmaster and try again."); else
user_opts.live_check = true;
}
}
/* same goes for the new postmaster */ if (pid_lock_file_exists(new_cluster.pgdata))
{ if (start_postmaster(&new_cluster, false))
stop_postmaster(false); else
pg_fatal("There seems to be a postmaster servicing the new cluster.\n" "Please shutdown that postmaster and try again.");
}
}
/* Change the char signedness of the new cluster, if necessary */ if (new_cluster.controldata.default_char_signedness != new_char_signedness)
{
prep_status("Setting the default char signedness for new cluster");
prep_status("Setting oldest XID for new cluster");
exec_prog(UTILITY_LOG_FILE, NULL, true, true, "\"%s/pg_resetwal\" -f -u %u \"%s\"",
new_cluster.bindir, old_cluster.controldata.chkpnt_oldstxid,
new_cluster.pgdata);
check_ok();
/* set the next transaction id and epoch of the new cluster */
prep_status("Setting next transaction ID and epoch for new cluster");
exec_prog(UTILITY_LOG_FILE, NULL, true, true, "\"%s/pg_resetwal\" -f -x %u \"%s\"",
new_cluster.bindir, old_cluster.controldata.chkpnt_nxtxid,
new_cluster.pgdata);
exec_prog(UTILITY_LOG_FILE, NULL, true, true, "\"%s/pg_resetwal\" -f -e %u \"%s\"",
new_cluster.bindir, old_cluster.controldata.chkpnt_nxtepoch,
new_cluster.pgdata); /* must reset commit timestamp limits also */
exec_prog(UTILITY_LOG_FILE, NULL, true, true, "\"%s/pg_resetwal\" -f -c %u,%u \"%s\"",
new_cluster.bindir,
old_cluster.controldata.chkpnt_nxtxid,
old_cluster.controldata.chkpnt_nxtxid,
new_cluster.pgdata);
check_ok();
/* now reset the wal archives in the new cluster */
prep_status("Resetting WAL archives");
exec_prog(UTILITY_LOG_FILE, NULL, true, true, /* use timeline 1 to match controldata and no WAL history file */ "\"%s/pg_resetwal\" -l 00000001%s \"%s\"", new_cluster.bindir,
old_cluster.controldata.nextxlogfile + 8,
new_cluster.pgdata);
check_ok();
}
/* *set_frozenxids() * *Thisiscalledonthenewclusterbeforewerestoreanything,with *minmxid_only=false.Itspurposeistoensurethatallinitdb-created *vacuumabletableshaverelfrozenxid/relminmxidmatchingtheoldcluster's *xid/mxidcounters.Wealsoinitializethedatfrozenxid/datminmxidofthe *built-indatabasestomatch. * *Aswecreateusertableslater,theirrelfrozenxid/relminmxidfieldswill *berestoredproperlybythebinary-upgraderestorescript.Likewisefor *user-databasedatfrozenxid/datminmxid.However,ifwe'reupgradingfroma *pre-9.3database,whichdoesnotstoreper-tableorper-DBminmxid,then *therelminmxid/datminmxidvaluesfilledinbytherestorescriptwilljust *bezeroes. * *Hence,withapre-9.3sourcedatabase,asecondcalloccursafter *everythingisrestored,withminmxid_only=true.Thispasswill *initializealltablesanddatabases,boththosemadebyinitdbanduser *objects,withthedesiredminmxidvalue.frozenxidvaluesareleftalone.
*/ staticvoid
set_frozenxids(bool minmxid_only)
{ int dbnum;
PGconn *conn,
*conn_template1;
PGresult *dbres; int ntups; int i_datname; int i_datallowconn;
if (!minmxid_only)
prep_status("Setting frozenxid and minmxid counters in new cluster"); else
prep_status("Setting minmxid counter in new cluster");
¤ Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.0.25Bemerkung:
(vorverarbeitet am 2026-08-08)
¤
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.