On 31/01/2023 12:26, Ashutosh Bapat wrote:
On Mon, Jan 30, 2023 at 9:35 PM Sébastien Lardière
<sebast...@lardiere.net> wrote:
On 27/01/2023 15:55, Peter Eisentraut wrote:
On 27.01.23 14:52, Sébastien Lardière wrote:
The attached patch proposes to change the format of timelineid from
%u to %X.
I think your complaint has merit.  But note that if we did a change
like this, then log files or reports from different versions would
have different meaning without a visual difference, which is kind of
what you complained about in the first place.  At least we should do
something like 0x%X.

Hi,

Here's the patch with the suggested format ; plus, I add some note in
the documentation about recovery_target_timeline, because I don't get
how strtoul(), with the special 0 base parameter can work without 0x
prefix ; I suppose that nobody use it.

I also change pg_controldata and the usage of this output by pg_upgrade.
I let internal usages unchanded : content of backup manifest and content
of history file.
The patch seems to have some special/unprintable characters in it. I
see a lot ^[[ in there. I can't read the patch because of that.

Sorry for that, it was the --color from git diff, it's fixed, I hope, thank you

regards,

--
Sébastien
diff --git a/doc/src/sgml/backup.sgml b/doc/src/sgml/backup.sgml
index be05a33205..7e26b51031 100644
--- a/doc/src/sgml/backup.sgml
+++ b/doc/src/sgml/backup.sgml
@@ -1332,7 +1332,8 @@ restore_command = 'cp /mnt/server/archivedir/%f %p'
     you like, add comments to a history file to record your own notes about
     how and why this particular timeline was created.  Such comments will be
     especially valuable when you have a thicket of different timelines as
-    a result of experimentation.
+    a result of experimentation. In both WAL segment file names and history files,
+    the timeline ID number is expressed in hexadecimal.
    </para>
 
    <para>
diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml
index 1cf53c74ea..508774cfee 100644
--- a/doc/src/sgml/config.sgml
+++ b/doc/src/sgml/config.sgml
@@ -4110,7 +4110,9 @@ restore_command = 'copy "C:\\server\\archivedir\\%f" "%p"'  # Windows
         current when the base backup was taken.  The
         value <literal>latest</literal> recovers
         to the latest timeline found in the archive, which is useful in
-        a standby server.  <literal>latest</literal> is the default.
+        a standby server. A numerical value expressed in hexadecimal must be
+        prefixed with <literal>0x</literal>, for example <literal>0x11</literal>.
+        <literal>latest</literal> is the default.
        </para>
 
        <para>
diff --git a/src/backend/access/rmgrdesc/xlogdesc.c b/src/backend/access/rmgrdesc/xlogdesc.c
index f390c177e4..bdbe993877 100644
--- a/src/backend/access/rmgrdesc/xlogdesc.c
+++ b/src/backend/access/rmgrdesc/xlogdesc.c
@@ -45,7 +45,7 @@ xlog_desc(StringInfo buf, XLogReaderState *record)
 		CheckPoint *checkpoint = (CheckPoint *) rec;
 
 		appendStringInfo(buf, "redo %X/%X; "
-						 "tli %u; prev tli %u; fpw %s; xid %u:%u; oid %u; multi %u; offset %u; "
+						 "tli 0x%X; prev tli 0x%X; fpw %s; xid %u:%u; oid %u; multi %u; offset %u; "
 						 "oldest xid %u in DB %u; oldest multi %u in DB %u; "
 						 "oldest/newest commit timestamp xid: %u/%u; "
 						 "oldest running xid %u; %s",
@@ -135,7 +135,7 @@ xlog_desc(StringInfo buf, XLogReaderState *record)
 		xl_end_of_recovery xlrec;
 
 		memcpy(&xlrec, rec, sizeof(xl_end_of_recovery));
-		appendStringInfo(buf, "tli %u; prev tli %u; time %s",
+		appendStringInfo(buf, "tli 0x%X; prev tli 0x%X; time %s",
 						 xlrec.ThisTimeLineID, xlrec.PrevTimeLineID,
 						 timestamptz_to_str(xlrec.end_time));
 	}
diff --git a/src/backend/access/transam/xlog.c b/src/backend/access/transam/xlog.c
index fb4c860bde..c22cf4b2a1 100644
--- a/src/backend/access/transam/xlog.c
+++ b/src/backend/access/transam/xlog.c
@@ -7819,7 +7819,7 @@ xlog_redo(XLogReaderState *record)
 		(void) GetCurrentReplayRecPtr(&replayTLI);
 		if (checkPoint.ThisTimeLineID != replayTLI)
 			ereport(PANIC,
-					(errmsg("unexpected timeline ID %u (should be %u) in shutdown checkpoint record",
+					(errmsg("unexpected timeline ID 0x%X (should be 0x%X) in shutdown checkpoint record",
 							checkPoint.ThisTimeLineID, replayTLI)));
 
 		RecoveryRestartPoint(&checkPoint, record);
@@ -7906,7 +7906,7 @@ xlog_redo(XLogReaderState *record)
 		(void) GetCurrentReplayRecPtr(&replayTLI);
 		if (xlrec.ThisTimeLineID != replayTLI)
 			ereport(PANIC,
-					(errmsg("unexpected timeline ID %u (should be %u) in end-of-recovery record",
+					(errmsg("unexpected timeline ID 0x%X (should be 0x%X) in end-of-recovery record",
 							xlrec.ThisTimeLineID, replayTLI)));
 	}
 	else if (info == XLOG_NOOP)
diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c
index aa6c929477..1643d0d98c 100644
--- a/src/backend/access/transam/xlogreader.c
+++ b/src/backend/access/transam/xlogreader.c
@@ -1329,7 +1329,7 @@ XLogReaderValidatePageHeader(XLogReaderState *state, XLogRecPtr recptr,
 			XLogFileName(fname, state->seg.ws_tli, segno, state->segcxt.ws_segsize);
 
 			report_invalid_record(state,
-								  "out-of-sequence timeline ID %u (after %u) in WAL segment %s, LSN %X/%X, offset %u",
+								  "out-of-sequence timeline ID 0x%X (after 0x%X) in WAL segment %s, LSN %X/%X, offset %u",
 								  hdr->xlp_tli,
 								  state->latestPageTLI,
 								  fname,
diff --git a/src/backend/access/transam/xlogrecovery.c b/src/backend/access/transam/xlogrecovery.c
index 2a5352f879..72087b4cf9 100644
--- a/src/backend/access/transam/xlogrecovery.c
+++ b/src/backend/access/transam/xlogrecovery.c
@@ -1108,7 +1108,7 @@ validateRecoveryParameters(void)
 		if (rtli != 1 && !existsTimeLineHistory(rtli))
 			ereport(FATAL,
 					(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
-					 errmsg("recovery target timeline %u does not exist",
+					 errmsg("recovery target timeline 0x%X does not exist",
 							rtli)));
 		recoveryTargetTLI = rtli;
 	}
@@ -3080,7 +3080,7 @@ ReadRecord(XLogPrefetcher *xlogprefetcher, int emode,
 			XLogFileName(fname, xlogreader->seg.ws_tli, segno,
 						 wal_segment_size);
 			ereport(emode_for_corrupt_record(emode, xlogreader->EndRecPtr),
-					(errmsg("unexpected timeline ID %u in WAL segment %s, LSN %X/%X, offset %u",
+					(errmsg("unexpected timeline ID 0x%X in WAL segment %s, LSN %X/%X, offset %u",
 							xlogreader->latestPageTLI,
 							fname,
 							LSN_FORMAT_ARGS(xlogreader->latestPagePtr),
@@ -3719,7 +3719,7 @@ WaitForWALToBecomeAvailable(XLogRecPtr RecPtr, bool randAccess,
 							tli = tliOfPointInHistory(tliRecPtr, expectedTLEs);
 
 							if (curFileTLI > 0 && tli < curFileTLI)
-								elog(ERROR, "according to history file, WAL location %X/%X belongs to timeline %u, but previous recovered WAL file came from timeline %u",
+								elog(ERROR, "according to history file, WAL location %X/%X belongs to timeline 0x%X, but previous recovered WAL file came from timeline 0x%X",
 									 LSN_FORMAT_ARGS(tliRecPtr),
 									 tli, curFileTLI);
 						}
@@ -4019,7 +4019,7 @@ rescanLatestTimeLine(TimeLineID replayTLI, XLogRecPtr replayLSN)
 	if (!found)
 	{
 		ereport(LOG,
-				(errmsg("new timeline %u is not a child of database system timeline %u",
+				(errmsg("new timeline 0x%X is not a child of database system timeline 0x%X",
 						newtarget,
 						replayTLI)));
 		return false;
@@ -4033,7 +4033,7 @@ rescanLatestTimeLine(TimeLineID replayTLI, XLogRecPtr replayLSN)
 	if (currentTle->end < replayLSN)
 	{
 		ereport(LOG,
-				(errmsg("new timeline %u forked off current database system timeline %u before current recovery point %X/%X",
+				(errmsg("new timeline 0x%X forked off current database system timeline 0x%X before current recovery point %X/%X",
 						newtarget,
 						replayTLI,
 						LSN_FORMAT_ARGS(replayLSN))));
@@ -4052,7 +4052,7 @@ rescanLatestTimeLine(TimeLineID replayTLI, XLogRecPtr replayLSN)
 	restoreTimeLineHistoryFiles(oldtarget + 1, newtarget);
 
 	ereport(LOG,
-			(errmsg("new target timeline is %u",
+			(errmsg("new target timeline is 0x%X",
 					recoveryTargetTLI)));
 
 	return true;
diff --git a/src/backend/backup/backup_manifest.c b/src/backend/backup/backup_manifest.c
index fabd2ca299..a405dad984 100644
--- a/src/backend/backup/backup_manifest.c
+++ b/src/backend/backup/backup_manifest.c
@@ -250,7 +250,7 @@ AddWALInfoToBackupManifest(backup_manifest_info *manifest, XLogRecPtr startptr,
 		 */
 		if (first_wal_range && endtli != entry->tli)
 			ereport(ERROR,
-					errmsg("expected end timeline %u but found timeline %u",
+					errmsg("expected end timeline 0x%X but found timeline 0x%X",
 						   starttli, entry->tli));
 
 		/*
@@ -274,7 +274,7 @@ AddWALInfoToBackupManifest(backup_manifest_info *manifest, XLogRecPtr startptr,
 			 */
 			if (XLogRecPtrIsInvalid(entry->begin))
 				ereport(ERROR,
-						errmsg("expected start timeline %u but found timeline %u",
+						errmsg("expected start timeline 0x%X but found timeline 0x%X",
 							   starttli, entry->tli));
 		}
 
@@ -301,7 +301,7 @@ AddWALInfoToBackupManifest(backup_manifest_info *manifest, XLogRecPtr startptr,
 	 */
 	if (!found_start_timeline)
 		ereport(ERROR,
-				errmsg("start timeline %u not found in history of timeline %u",
+				errmsg("start timeline 0x%X not found in history of timeline 0x%X",
 					   starttli, endtli));
 
 	/* Terminate the list of WAL ranges. */
diff --git a/src/backend/replication/walreceiver.c b/src/backend/replication/walreceiver.c
index b0cfddd548..f6ef5f75ed 100644
--- a/src/backend/replication/walreceiver.c
+++ b/src/backend/replication/walreceiver.c
@@ -361,7 +361,7 @@ WalReceiverMain(void)
 		if (primaryTLI < startpointTLI)
 			ereport(ERROR,
 					(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
-					 errmsg("highest timeline %u of the primary is behind recovery timeline %u",
+					 errmsg("highest timeline 0x%X of the primary is behind recovery timeline 0x%X",
 							primaryTLI, startpointTLI)));
 
 		/*
@@ -414,11 +414,11 @@ WalReceiverMain(void)
 		{
 			if (first_stream)
 				ereport(LOG,
-						(errmsg("started streaming WAL from primary at %X/%X on timeline %u",
+						(errmsg("started streaming WAL from primary at %X/%X on timeline 0x%X",
 								LSN_FORMAT_ARGS(startpoint), startpointTLI)));
 			else
 				ereport(LOG,
-						(errmsg("restarted WAL streaming at %X/%X on timeline %u",
+						(errmsg("restarted WAL streaming at %X/%X on timeline 0x%X",
 								LSN_FORMAT_ARGS(startpoint), startpointTLI)));
 			first_stream = false;
 
@@ -499,7 +499,7 @@ WalReceiverMain(void)
 						{
 							ereport(LOG,
 									(errmsg("replication terminated by primary server"),
-									 errdetail("End of WAL reached on timeline %u at %X/%X.",
+									 errdetail("End of WAL reached on timeline 0x%X at %X/%X.",
 											   startpointTLI,
 											   LSN_FORMAT_ARGS(LogstreamResult.Write))));
 							endofwal = true;
@@ -621,7 +621,7 @@ WalReceiverMain(void)
 		}
 		else
 			ereport(LOG,
-					(errmsg("primary server contains no more WAL on requested timeline %u",
+					(errmsg("primary server contains no more WAL on requested timeline 0x%X",
 							startpointTLI)));
 
 		/*
@@ -756,7 +756,7 @@ WalRcvFetchTimeLineHistoryFiles(TimeLineID first, TimeLineID last)
 			char		expectedfname[MAXFNAMELEN];
 
 			ereport(LOG,
-					(errmsg("fetching timeline history file for timeline %u from primary server",
+					(errmsg("fetching timeline history file for timeline 0x%X from primary server",
 							tli)));
 
 			walrcv_readtimelinehistoryfile(wrconn, tli, &fname, &content, &len);
@@ -770,7 +770,7 @@ WalRcvFetchTimeLineHistoryFiles(TimeLineID first, TimeLineID last)
 			if (strcmp(fname, expectedfname) != 0)
 				ereport(ERROR,
 						(errcode(ERRCODE_PROTOCOL_VIOLATION),
-						 errmsg_internal("primary reported unexpected file name for timeline history file of timeline %u",
+						 errmsg_internal("primary reported unexpected file name for timeline history file of timeline 0x%X",
 										 tli)));
 
 			/*
diff --git a/src/bin/pg_basebackup/pg_basebackup.c b/src/bin/pg_basebackup/pg_basebackup.c
index 1d3ef2c694..c9491de0df 100644
--- a/src/bin/pg_basebackup/pg_basebackup.c
+++ b/src/bin/pg_basebackup/pg_basebackup.c
@@ -1921,7 +1921,7 @@ BaseBackup(char *compression_algorithm, char *compression_detail,
 	PQclear(res);
 
 	if (verbose && includewal != NO_WAL)
-		pg_log_info("write-ahead log start point: %s on timeline %u",
+		pg_log_info("write-ahead log start point: %s on timeline 0x%X",
 					xlogstart, starttli);
 
 	/*
diff --git a/src/bin/pg_controldata/pg_controldata.c b/src/bin/pg_controldata/pg_controldata.c
index c390ec51ce..436435c737 100644
--- a/src/bin/pg_controldata/pg_controldata.c
+++ b/src/bin/pg_controldata/pg_controldata.c
@@ -241,9 +241,9 @@ main(int argc, char *argv[])
 		   LSN_FORMAT_ARGS(ControlFile->checkPointCopy.redo));
 	printf(_("Latest checkpoint's REDO WAL file:    %s\n"),
 		   xlogfilename);
-	printf(_("Latest checkpoint's TimeLineID:       %u\n"),
+	printf(_("Latest checkpoint's TimeLineID:       0x%X\n"),
 		   ControlFile->checkPointCopy.ThisTimeLineID);
-	printf(_("Latest checkpoint's PrevTimeLineID:   %u\n"),
+	printf(_("Latest checkpoint's PrevTimeLineID:   0x%X\n"),
 		   ControlFile->checkPointCopy.PrevTimeLineID);
 	printf(_("Latest checkpoint's full_page_writes: %s\n"),
 		   ControlFile->checkPointCopy.fullPageWrites ? _("on") : _("off"));
diff --git a/src/bin/pg_rewind/pg_rewind.c b/src/bin/pg_rewind/pg_rewind.c
index 858d8d9f2f..7f9b7b663d 100644
--- a/src/bin/pg_rewind/pg_rewind.c
+++ b/src/bin/pg_rewind/pg_rewind.c
@@ -350,7 +350,7 @@ main(int argc, char **argv)
 		XLogRecPtr	chkptendrec;
 
 		findCommonAncestorTimeline(&divergerec, &lastcommontliIndex);
-		pg_log_info("servers diverged at WAL location %X/%X on timeline %u",
+		pg_log_info("servers diverged at WAL location %X/%X on timeline 0x%X",
 					LSN_FORMAT_ARGS(divergerec),
 					targetHistory[lastcommontliIndex].tli);
 
@@ -856,7 +856,7 @@ getTimelineHistory(ControlFileData *controlFile, int *nentries)
 			TimeLineHistoryEntry *entry;
 
 			entry = &history[i];
-			pg_log_debug("%u: %X/%X - %X/%X", entry->tli,
+			pg_log_debug("0x%X: %X/%X - %X/%X", entry->tli,
 						 LSN_FORMAT_ARGS(entry->begin),
 						 LSN_FORMAT_ARGS(entry->end));
 		}
diff --git a/src/bin/pg_upgrade/controldata.c b/src/bin/pg_upgrade/controldata.c
index 9071a6fd45..b04347d801 100644
--- a/src/bin/pg_upgrade/controldata.c
+++ b/src/bin/pg_upgrade/controldata.c
@@ -241,7 +241,7 @@ get_control_data(ClusterInfo *cluster, bool live_check)
 				pg_fatal("%d: controldata retrieval problem", __LINE__);
 
 			p++;				/* remove ':' char */
-			tli = str2uint(p);
+			tli = strtoul(p, NULL, 0);
 			got_tli = true;
 		}
 		else if ((p = strstr(bufin, "First log file ID after reset:")) != NULL)
diff --git a/src/bin/pg_verifybackup/pg_verifybackup.c b/src/bin/pg_verifybackup/pg_verifybackup.c
index 7634dfc285..2a54d7ab52 100644
--- a/src/bin/pg_verifybackup/pg_verifybackup.c
+++ b/src/bin/pg_verifybackup/pg_verifybackup.c
@@ -807,14 +807,14 @@ parse_required_wal(verifier_context *context, char *pg_waldump_path,
 	{
 		char	   *pg_waldump_cmd;
 
-		pg_waldump_cmd = psprintf("\"%s\" --quiet --path=\"%s\" --timeline=%u --start=%X/%X --end=%X/%X\n",
+		pg_waldump_cmd = psprintf("\"%s\" --quiet --path=\"%s\" --timeline=%X --start=%X/%X --end=%X/%X\n",
 								  pg_waldump_path, wal_directory, this_wal_range->tli,
 								  LSN_FORMAT_ARGS(this_wal_range->start_lsn),
 								  LSN_FORMAT_ARGS(this_wal_range->end_lsn));
 		fflush(NULL);
 		if (system(pg_waldump_cmd) != 0)
 			report_backup_error(context,
-								"WAL parsing failed for timeline %u",
+								"WAL parsing failed for timeline %X",
 								this_wal_range->tli);
 
 		this_wal_range = this_wal_range->next;
diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c
index 44b5c8726e..23dc7354ba 100644
--- a/src/bin/pg_waldump/pg_waldump.c
+++ b/src/bin/pg_waldump/pg_waldump.c
@@ -1007,7 +1007,7 @@ main(int argc, char **argv)
 					private.startptr = (uint64) xlogid << 32 | xrecoff;
 				break;
 			case 't':
-				if (sscanf(optarg, "%u", &private.timeline) != 1)
+				if (sscanf(optarg, "%X", &private.timeline) != 1)
 				{
 					pg_log_error("invalid timeline specification: \"%s\"", optarg);
 					goto bad_argument;

Reply via email to