On Mon, Sep 14, 2026 at 12:32:18AM -0400, Tom Lane wrote: > Kyotaro Horiguchi <[email protected]> writes: > > Commit cb298616463 changed the following line: > > > - printf(_("Latest checkpoint's NextOID: %u\n"), > > + printf(_("Latest checkpoint's NextOID: " OID8_FORMAT "\n"),
Oops, sorry about that. I can see the breakage with some update-po. >> It appears that xgettext does not recognize PostgreSQL's OID8_FORMAT >> macro and therefore extracts only the preceding string literal as the >> msgid. In contrast, PRIu64, which is used in the same file, is >> correctly extracted as %<PRIu64>. Therefore, shouldn't we use "%" >> PRIu64 instead of OID8_FORMAT here as well? Yes, it's not the first time that 64-bit values show this problem with translatable strings. > That would be fairly sad, because it means hard-wiring the fact that > Oid8 is the same as uint64 in a bunch of non-obvious places. > Admittedly, we've lived with formatting Oid as %u for a long time. > But can we fix this some other way? The proposed patch to use the Pri markers would work with gettext(). Just note that, I have.. cough.. also broken pg_resetwal in two places. The other places switched recently (amcheck, backend) only relate to internal errors and places without po files, so they're out of the picture, fine with the OID8_FORMAT markers. Anyway, I really want to keep this code greppable with the Oid8 markers, so I don't think that the proposed patch is what I would do. The magic solution I can think of is to remove the markers from the translatable strings, and replace them with a set of %s, as of the attached patch, then use a pre-built string that itself uses OID8_FORMAT. I am pretty sure we have used this method in other places of the tree, but I cannot pinpoint where, on top of my mind. The idea of documenting this trick or equivalent in c.h is interesting in the long term, for sure. Any suggestions how to word this requirement close to the OID8_FORMAT declaration? Thoughts? -- Michael
From 00a59f976130a1bb569dce94a9f2ab32692a9c76 Mon Sep 17 00:00:00 2001 From: Michael Paquier <[email protected]> Date: Mon, 14 Sep 2026 14:47:48 +0900 Subject: [PATCH] Fix translation of pg_resetwal and pg_controldata's NextOID output xgettext() drops OID8_FORMAT and therefore extracts an incomplete message. Let's use %s in these translatable strings, with a pre-built buffer that relies on OID8_FORMAT. Reported-by: Kyotaro Horiguchi <[email protected]> --- src/bin/pg_controldata/pg_controldata.c | 6 ++++-- src/bin/pg_resetwal/pg_resetwal.c | 13 +++++++++---- 2 files changed, 13 insertions(+), 6 deletions(-) diff --git a/src/bin/pg_controldata/pg_controldata.c b/src/bin/pg_controldata/pg_controldata.c index b785f7f40701..31dba74f5996 100644 --- a/src/bin/pg_controldata/pg_controldata.c +++ b/src/bin/pg_controldata/pg_controldata.c @@ -101,6 +101,7 @@ main(int argc, char *argv[]) char pgctime_str[128]; char ckpttime_str[128]; char mock_auth_nonce_str[MOCK_AUTH_NONCE_LEN * 2 + 1]; + char nextoid_str[32]; const char *strftime_fmt = "%c"; const char *progname; char xlogfilename[MAXFNAMELEN]; @@ -269,8 +270,9 @@ main(int argc, char *argv[]) printf(_("Latest checkpoint's NextXID: %u:%u\n"), EpochFromFullTransactionId(ControlFile->checkPointCopy.nextXid), XidFromFullTransactionId(ControlFile->checkPointCopy.nextXid)); - printf(_("Latest checkpoint's NextOID: " OID8_FORMAT "\n"), - ControlFile->checkPointCopy.nextOid); + snprintf(nextoid_str, sizeof(nextoid_str), OID8_FORMAT, + ControlFile->checkPointCopy.nextOid); + printf(_("Latest checkpoint's NextOID: %s\n"), nextoid_str); printf(_("Latest checkpoint's NextMultiXactId: %u\n"), ControlFile->checkPointCopy.nextMulti); printf(_("Latest checkpoint's NextMultiOffset: %" PRIu64 "\n"), diff --git a/src/bin/pg_resetwal/pg_resetwal.c b/src/bin/pg_resetwal/pg_resetwal.c index 63e4381e03f0..45146df30a56 100644 --- a/src/bin/pg_resetwal/pg_resetwal.c +++ b/src/bin/pg_resetwal/pg_resetwal.c @@ -757,6 +757,8 @@ GuessControlValues(void) static void PrintControlValues(bool guessed) { + char nextoid_str[32]; + if (guessed) printf(_("Guessed pg_control values:\n\n")); else @@ -775,8 +777,9 @@ PrintControlValues(bool guessed) printf(_("Latest checkpoint's NextXID: %u:%u\n"), EpochFromFullTransactionId(ControlFile.checkPointCopy.nextXid), XidFromFullTransactionId(ControlFile.checkPointCopy.nextXid)); - printf(_("Latest checkpoint's NextOID: " OID8_FORMAT "\n"), - ControlFile.checkPointCopy.nextOid); + snprintf(nextoid_str, sizeof(nextoid_str), OID8_FORMAT, + ControlFile.checkPointCopy.nextOid); + printf(_("Latest checkpoint's NextOID: %s\n"), nextoid_str); printf(_("Latest checkpoint's NextMultiXactId: %u\n"), ControlFile.checkPointCopy.nextMulti); printf(_("Latest checkpoint's NextMultiOffset: %" PRIu64 "\n"), @@ -835,6 +838,7 @@ static void PrintNewControlValues(void) { char fname[MAXFNAMELEN]; + char nextoid_str[32]; /* This will be always printed in order to keep format same. */ printf(_("\n\nValues to be changed:\n\n")); @@ -861,8 +865,9 @@ PrintNewControlValues(void) if (next_oid_given) { - printf(_("NextOID: " OID8_FORMAT "\n"), - ControlFile.checkPointCopy.nextOid); + snprintf(nextoid_str, sizeof(nextoid_str), OID8_FORMAT, + ControlFile.checkPointCopy.nextOid); + printf(_("NextOID: %s\n"), nextoid_str); } if (next_xid_given) -- 2.55.0
signature.asc
Description: PGP signature
