提交 0c383155 编写于 作者: T Tom Lane

Update for new pg_control format.

上级 4d14fe00
# #
# $Header: /cvsroot/pgsql/contrib/pg_controldata/Attic/Makefile,v 1.2 2001/02/25 15:57:45 petere Exp $ # $Header: /cvsroot/pgsql/contrib/pg_controldata/Attic/Makefile,v 1.3 2001/03/13 01:17:40 tgl Exp $
# #
subdir = contrib/pg_controldata subdir = contrib/pg_controldata
top_builddir = ../.. top_builddir = ../..
include $(top_builddir)/src/Makefile.global include $(top_builddir)/src/Makefile.global
override CPPFLAGS := -I$(libpq_srcdir) $(CPPFLAGS) OBJS = pg_controldata.o pg_crc.o
OBJS = pg_controldata.o
all: pg_controldata all: pg_controldata
pg_controldata: $(OBJS) pg_controldata: $(OBJS)
$(CC) $(CFLAGS) $(OBJS) $(LDFLAGS) $(LIBS) -o $@ $(CC) $(CFLAGS) $(OBJS) $(LDFLAGS) $(LIBS) -o $@
pg_crc.c: $(top_builddir)/src/backend/utils/hash/pg_crc.c
rm -f $@ && $(LN_S) $< .
install: all installdirs install: all installdirs
$(INSTALL_PROGRAM) pg_controldata$(X) $(bindir) $(INSTALL_PROGRAM) pg_controldata$(X) $(bindir)
$(INSTALL_DATA) README.pg_controldata $(docdir)/contrib $(INSTALL_DATA) README.pg_controldata $(docdir)/contrib
...@@ -26,7 +27,7 @@ uninstall: ...@@ -26,7 +27,7 @@ uninstall:
rm -f $(bindir)/pg_controldata$(X) $(docdir)/contrib/README.pg_controldata rm -f $(bindir)/pg_controldata$(X) $(docdir)/contrib/README.pg_controldata
clean distclean maintainer-clean: clean distclean maintainer-clean:
rm -f pg_controldata$(X) $(OBJS) rm -f pg_controldata$(X) $(OBJS) pg_crc.c
depend dep: depend dep:
$(CC) -MM -MG $(CFLAGS) *.c > depend $(CC) -MM -MG $(CFLAGS) *.c > depend
......
...@@ -2,18 +2,31 @@ I had a need to read such things as the backend locale and the catalog ...@@ -2,18 +2,31 @@ I had a need to read such things as the backend locale and the catalog
version number from the current database, and couldn't find any existing version number from the current database, and couldn't find any existing
program to do that. program to do that.
The attached utility produces this output: The attached utility produces output like this:
linda:~$ pg_controldata $ pg_controldata
Log file id: 0 pg_control version number: 71
Log file segment: 5 Catalog version number: 200101061
Last modified: Wed Feb 7 19:35:47 2001 Database state: IN_PRODUCTION
pg_control last modified: Sat Mar 10 00:07:55 2001
Current log file id: 0
Next log file segment: 9
Latest checkpoint location: 0/88CAA20
Prior checkpoint location: 0/70A5D48
Latest checkpoint's REDO location: 0/88CAA20
Latest checkpoint's UNDO location: 0/0
Latest checkpoint's StartUpID: 22
Latest checkpoint's NextXID: 4711
Latest checkpoint's NextOID: 444704
Time of latest checkpoint: Sat Mar 10 00:07:52 2001
Database block size: 8192 Database block size: 8192
Blocks per segment of large relation: 131072 Blocks per segment of large relation: 131072
Catalog version number: 200101061 LC_COLLATE: C
LC_COLLATE: en_GB LC_CTYPE: C
LC_CTYPE: en_GB
Log archive directory:
To access the pg_control file, the program must be run as the Postgres user,
and PGDATA must be set correctly in its environment.
-- --
Oliver Elphick <olly@lfix.co.uk> Oliver Elphick <olly@lfix.co.uk>
/* pg_controldata /*
* pg_controldata
* *
* reads the data from $PGDATA/global/pg_control * reads the data from $PGDATA/global/pg_control
* *
* copyright (c) Oliver Elphick <olly@lfix.co.uk>, 2001; * copyright (c) Oliver Elphick <olly@lfix.co.uk>, 2001;
* licence: BSD * licence: BSD
* *
*/ * $Header: /cvsroot/pgsql/contrib/pg_controldata/Attic/pg_controldata.c,v 1.2 2001/03/13 01:17:40 tgl Exp $
*/
#include "postgres.h"
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h> #include <unistd.h>
#include <time.h> #include <time.h>
#include <sys/types.h> #include <sys/types.h>
#include <sys/stat.h> #include <sys/stat.h>
#include <fcntl.h> #include <fcntl.h>
#include "catalog/pg_control.h"
typedef unsigned int uint32;
#include "config.h" static const char *
#include "access/xlogdefs.h" dbState(DBState state)
/*
* #include "access/xlog.h"
* #include "c.h"
*/
/* The following definitions are extracted from access/xlog.h and its
* recursive includes. There is too much initialisation needed if
* they are included direct. Perhaps someone more knowledgeable can
* fix that.
*/
typedef struct crc64
{ {
uint32 crc1; switch (state)
uint32 crc2; {
} crc64; case DB_STARTUP:
return "STARTUP";
#define LOCALE_NAME_BUFLEN 128 case DB_SHUTDOWNED:
return "SHUTDOWNED";
typedef enum DBState case DB_SHUTDOWNING:
{ return "SHUTDOWNING";
DB_STARTUP = 0, case DB_IN_RECOVERY:
DB_SHUTDOWNED, return "IN_RECOVERY";
DB_SHUTDOWNING, case DB_IN_PRODUCTION:
DB_IN_RECOVERY, return "IN_PRODUCTION";
DB_IN_PRODUCTION }
} DBState; return "unrecognized status code";
}
typedef struct ControlFileData int
main()
{ {
crc64 crc;
uint32 logId; /* current log file id */
uint32 logSeg; /* current log file segment (1-based) */
struct
XLogRecPtr checkPoint; /* last check point record ptr */
time_t time; /* time stamp of last modification */
DBState state; /* see enum above */
/*
* this data is used to make sure that configuration of this DB is
* compatible with the backend executable
*/
uint32 blcksz; /* block size for this DB */
uint32 relseg_size; /* blocks per segment of large relation */
uint32 catalog_version_no; /* internal version number */
/* active locales --- "C" if compiled without USE_LOCALE: */
char lc_collate[LOCALE_NAME_BUFLEN];
char lc_ctype[LOCALE_NAME_BUFLEN];
/*
* important directory locations
*/
char archdir[MAXPGPATH]; /* where to move offline log files */
} ControlFileData;
int main() {
ControlFileData ControlFile; ControlFileData ControlFile;
int fd; int fd;
char ControlFilePath[MAXPGPATH]; char ControlFilePath[MAXPGPATH];
char *DataDir; char *DataDir;
char tmdt[32]; crc64 crc;
char pgctime_str[32];
char ckpttime_str[32];
DataDir = getenv("PGDATA"); DataDir = getenv("PGDATA");
if ( DataDir == NULL ) { if ( DataDir == NULL ) {
...@@ -91,33 +58,77 @@ int main() { ...@@ -91,33 +58,77 @@ int main() {
snprintf(ControlFilePath, MAXPGPATH, "%s/global/pg_control", DataDir); snprintf(ControlFilePath, MAXPGPATH, "%s/global/pg_control", DataDir);
if ((fd = open(ControlFilePath, O_RDONLY)) == -1) { if ((fd = open(ControlFilePath, O_RDONLY)) == -1)
{
perror("Failed to open $PGDATA/global/pg_control for reading"); perror("Failed to open $PGDATA/global/pg_control for reading");
exit(2); exit(2);
} }
read(fd, &ControlFile, sizeof(ControlFileData)); if (read(fd, &ControlFile, sizeof(ControlFileData)) != sizeof(ControlFileData))
strftime(tmdt, 32, "%c", localtime(&(ControlFile.time))); {
perror("Failed to read $PGDATA/global/pg_control");
printf("Log file id: %u\n" exit(2);
"Log file segment: %u\n" }
"Last modified: %s\n" close(fd);
/* Check the CRC. */
INIT_CRC64(crc);
COMP_CRC64(crc,
(char*) &ControlFile + sizeof(crc64),
sizeof(ControlFileData) - sizeof(crc64));
FIN_CRC64(crc);
if (!EQ_CRC64(crc, ControlFile.crc))
printf("WARNING: Calculated CRC checksum does not match value stored in file.\n"
"Either the file is corrupt, or it has a different layout than this program\n"
"is expecting. The results below are untrustworthy.\n\n");
strftime(pgctime_str, 32, "%c",
localtime(&(ControlFile.time)));
strftime(ckpttime_str, 32, "%c",
localtime(&(ControlFile.checkPointCopy.time)));
printf("pg_control version number: %u\n"
"Catalog version number: %u\n"
"Database state: %s\n"
"pg_control last modified: %s\n"
"Current log file id: %u\n"
"Next log file segment: %u\n"
"Latest checkpoint location: %X/%X\n"
"Prior checkpoint location: %X/%X\n"
"Latest checkpoint's REDO location: %X/%X\n"
"Latest checkpoint's UNDO location: %X/%X\n"
"Latest checkpoint's StartUpID: %u\n"
"Latest checkpoint's NextXID: %u\n"
"Latest checkpoint's NextOID: %u\n"
"Time of latest checkpoint: %s\n"
"Database block size: %u\n" "Database block size: %u\n"
"Blocks per segment of large relation: %u\n" "Blocks per segment of large relation: %u\n"
"Catalog version number: %u\n"
"LC_COLLATE: %s\n" "LC_COLLATE: %s\n"
"LC_CTYPE: %s\n" "LC_CTYPE: %s\n",
"Log archive directory: %s\n",
ControlFile.pg_control_version,
ControlFile.catalog_version_no,
dbState(ControlFile.state),
pgctime_str,
ControlFile.logId, ControlFile.logId,
ControlFile.logSeg, ControlFile.logSeg,
tmdt, ControlFile.checkPoint.xlogid,
ControlFile.checkPoint.xrecoff,
ControlFile.prevCheckPoint.xlogid,
ControlFile.prevCheckPoint.xrecoff,
ControlFile.checkPointCopy.redo.xlogid,
ControlFile.checkPointCopy.redo.xrecoff,
ControlFile.checkPointCopy.undo.xlogid,
ControlFile.checkPointCopy.undo.xrecoff,
ControlFile.checkPointCopy.ThisStartUpID,
ControlFile.checkPointCopy.nextXid,
ControlFile.checkPointCopy.nextOid,
ckpttime_str,
ControlFile.blcksz, ControlFile.blcksz,
ControlFile.relseg_size, ControlFile.relseg_size,
ControlFile.catalog_version_no,
ControlFile.lc_collate, ControlFile.lc_collate,
ControlFile.lc_ctype, ControlFile.lc_ctype);
ControlFile.archdir);
return (0); return (0);
} }
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册