#include "postgres.h"#include "access/htup_details.h"#include "access/xlog.h"#include "access/xlog_fn.h"#include "access/xlog_internal.h"#include "access/xlogutils.h"#include "catalog/catalog.h"#include "catalog/pg_type.h"#include "funcapi.h"#include "miscadmin.h"#include "replication/walreceiver.h"#include "storage/smgr.h"#include "utils/builtins.h"#include "utils/numeric.h"#include "utils/guc.h"#include "utils/timestamp.h"#include "storage/fd.h"
Go to the source code of this file.
Defines | |
| #define | MAXLSNCOMPONENT 8 |
Functions | |
| static void | validate_xlog_location (char *str) |
| Datum | pg_start_backup (PG_FUNCTION_ARGS) |
| Datum | pg_stop_backup (PG_FUNCTION_ARGS) |
| Datum | pg_switch_xlog (PG_FUNCTION_ARGS) |
| Datum | pg_create_restore_point (PG_FUNCTION_ARGS) |
| Datum | pg_current_xlog_location (PG_FUNCTION_ARGS) |
| Datum | pg_current_xlog_insert_location (PG_FUNCTION_ARGS) |
| Datum | pg_last_xlog_receive_location (PG_FUNCTION_ARGS) |
| Datum | pg_last_xlog_replay_location (PG_FUNCTION_ARGS) |
| Datum | pg_xlogfile_name_offset (PG_FUNCTION_ARGS) |
| Datum | pg_xlogfile_name (PG_FUNCTION_ARGS) |
| Datum | pg_xlog_replay_pause (PG_FUNCTION_ARGS) |
| Datum | pg_xlog_replay_resume (PG_FUNCTION_ARGS) |
| Datum | pg_is_xlog_replay_paused (PG_FUNCTION_ARGS) |
| Datum | pg_last_xact_replay_timestamp (PG_FUNCTION_ARGS) |
| Datum | pg_is_in_recovery (PG_FUNCTION_ARGS) |
| Datum | pg_xlog_location_diff (PG_FUNCTION_ARGS) |
| Datum | pg_is_in_backup (PG_FUNCTION_ARGS) |
| Datum | pg_backup_start_time (PG_FUNCTION_ARGS) |
| #define MAXLSNCOMPONENT 8 |
Referenced by validate_xlog_location().
| Datum pg_backup_start_time | ( | PG_FUNCTION_ARGS | ) |
Definition at line 570 of file xlogfuncs.c.
References AllocateFile(), BACKUP_LABEL_FILE, CStringGetDatum, DirectFunctionCall3, ereport, errcode(), errcode_for_file_access(), errmsg(), ERROR, FreeFile(), Int32GetDatum, InvalidOid, NULL, ObjectIdGetDatum, PG_RETURN_DATUM, PG_RETURN_NULL, and timestamptz_in().
{
Datum xtime;
FILE *lfp;
char fline[MAXPGPATH];
char backup_start_time[30];
/*
* See if label file is present
*/
lfp = AllocateFile(BACKUP_LABEL_FILE, "r");
if (lfp == NULL)
{
if (errno != ENOENT)
ereport(ERROR,
(errcode_for_file_access(),
errmsg("could not read file \"%s\": %m",
BACKUP_LABEL_FILE)));
PG_RETURN_NULL();
}
/*
* Parse the file to find the the START TIME line.
*/
backup_start_time[0] = '\0';
while (fgets(fline, sizeof(fline), lfp) != NULL)
{
if (sscanf(fline, "START TIME: %25[^\n]\n", backup_start_time) == 1)
break;
}
/* Check for a read error. */
if (ferror(lfp))
ereport(ERROR,
(errcode_for_file_access(),
errmsg("could not read file \"%s\": %m", BACKUP_LABEL_FILE)));
/* Close the backup label file. */
if (FreeFile(lfp))
ereport(ERROR,
(errcode_for_file_access(),
errmsg("could not close file \"%s\": %m", BACKUP_LABEL_FILE)));
if (strlen(backup_start_time) == 0)
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("invalid data in file \"%s\"", BACKUP_LABEL_FILE)));
/*
* Convert the time string read from file to TimestampTz form.
*/
xtime = DirectFunctionCall3(timestamptz_in,
CStringGetDatum(backup_start_time),
ObjectIdGetDatum(InvalidOid),
Int32GetDatum(-1));
PG_RETURN_DATUM(xtime);
}
| Datum pg_create_restore_point | ( | PG_FUNCTION_ARGS | ) |
Definition at line 126 of file xlogfuncs.c.
References cstring_to_text(), ereport, errcode(), errhint(), errmsg(), ERROR, MAXFNAMELEN, PG_GETARG_TEXT_P, PG_RETURN_TEXT_P, RecoveryInProgress(), snprintf(), superuser(), text_to_cstring(), XLogIsNeeded, and XLogRestorePoint().
{
text *restore_name = PG_GETARG_TEXT_P(0);
char *restore_name_str;
XLogRecPtr restorepoint;
char location[MAXFNAMELEN];
if (!superuser())
ereport(ERROR,
(errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
(errmsg("must be superuser to create a restore point"))));
if (RecoveryInProgress())
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
(errmsg("recovery is in progress"),
errhint("WAL control functions cannot be executed during recovery."))));
if (!XLogIsNeeded())
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("WAL level not sufficient for creating a restore point"),
errhint("wal_level must be set to \"archive\" or \"hot_standby\" at server start.")));
restore_name_str = text_to_cstring(restore_name);
if (strlen(restore_name_str) >= MAXFNAMELEN)
ereport(ERROR,
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
errmsg("value too long for restore point (maximum %d characters)", MAXFNAMELEN - 1)));
restorepoint = XLogRestorePoint(restore_name_str);
/*
* As a convenience, return the WAL location of the restore point record
*/
snprintf(location, sizeof(location), "%X/%X",
(uint32) (restorepoint >> 32), (uint32) restorepoint);
PG_RETURN_TEXT_P(cstring_to_text(location));
}
| Datum pg_current_xlog_insert_location | ( | PG_FUNCTION_ARGS | ) |
Definition at line 199 of file xlogfuncs.c.
References cstring_to_text(), ereport, errcode(), errhint(), errmsg(), ERROR, GetXLogInsertRecPtr(), PG_RETURN_TEXT_P, RecoveryInProgress(), and snprintf().
{
XLogRecPtr current_recptr;
char location[MAXFNAMELEN];
if (RecoveryInProgress())
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("recovery is in progress"),
errhint("WAL control functions cannot be executed during recovery.")));
current_recptr = GetXLogInsertRecPtr();
snprintf(location, sizeof(location), "%X/%X",
(uint32) (current_recptr >> 32), (uint32) current_recptr);
PG_RETURN_TEXT_P(cstring_to_text(location));
}
| Datum pg_current_xlog_location | ( | PG_FUNCTION_ARGS | ) |
Definition at line 175 of file xlogfuncs.c.
References cstring_to_text(), ereport, errcode(), errhint(), errmsg(), ERROR, GetXLogWriteRecPtr(), PG_RETURN_TEXT_P, RecoveryInProgress(), and snprintf().
{
XLogRecPtr current_recptr;
char location[MAXFNAMELEN];
if (RecoveryInProgress())
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("recovery is in progress"),
errhint("WAL control functions cannot be executed during recovery.")));
current_recptr = GetXLogWriteRecPtr();
snprintf(location, sizeof(location), "%X/%X",
(uint32) (current_recptr >> 32), (uint32) current_recptr);
PG_RETURN_TEXT_P(cstring_to_text(location));
}
| Datum pg_is_in_backup | ( | PG_FUNCTION_ARGS | ) |
Definition at line 558 of file xlogfuncs.c.
References BackupInProgress(), and PG_RETURN_BOOL.
{
PG_RETURN_BOOL(BackupInProgress());
}
| Datum pg_is_in_recovery | ( | PG_FUNCTION_ARGS | ) |
Definition at line 469 of file xlogfuncs.c.
References PG_RETURN_BOOL, and RecoveryInProgress().
{
PG_RETURN_BOOL(RecoveryInProgress());
}
| Datum pg_is_xlog_replay_paused | ( | PG_FUNCTION_ARGS | ) |
Definition at line 431 of file xlogfuncs.c.
References ereport, errcode(), errhint(), errmsg(), ERROR, PG_RETURN_BOOL, RecoveryInProgress(), RecoveryIsPaused(), and superuser().
{
if (!superuser())
ereport(ERROR,
(errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
(errmsg("must be superuser to control recovery"))));
if (!RecoveryInProgress())
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("recovery is not in progress"),
errhint("Recovery control functions can only be executed during recovery.")));
PG_RETURN_BOOL(RecoveryIsPaused());
}
| Datum pg_last_xact_replay_timestamp | ( | PG_FUNCTION_ARGS | ) |
Definition at line 454 of file xlogfuncs.c.
References GetLatestXTime(), PG_RETURN_NULL, and PG_RETURN_TIMESTAMPTZ.
{
TimestampTz xtime;
xtime = GetLatestXTime();
if (xtime == 0)
PG_RETURN_NULL();
PG_RETURN_TIMESTAMPTZ(xtime);
}
| Datum pg_last_xlog_receive_location | ( | PG_FUNCTION_ARGS | ) |
Definition at line 224 of file xlogfuncs.c.
References cstring_to_text(), GetWalRcvWriteRecPtr(), NULL, PG_RETURN_NULL, PG_RETURN_TEXT_P, and snprintf().
{
XLogRecPtr recptr;
char location[MAXFNAMELEN];
recptr = GetWalRcvWriteRecPtr(NULL, NULL);
if (recptr == 0)
PG_RETURN_NULL();
snprintf(location, sizeof(location), "%X/%X",
(uint32) (recptr >> 32), (uint32) recptr);
PG_RETURN_TEXT_P(cstring_to_text(location));
}
| Datum pg_last_xlog_replay_location | ( | PG_FUNCTION_ARGS | ) |
Definition at line 246 of file xlogfuncs.c.
References cstring_to_text(), GetXLogReplayRecPtr(), NULL, PG_RETURN_NULL, PG_RETURN_TEXT_P, and snprintf().
{
XLogRecPtr recptr;
char location[MAXFNAMELEN];
recptr = GetXLogReplayRecPtr(NULL);
if (recptr == 0)
PG_RETURN_NULL();
snprintf(location, sizeof(location), "%X/%X",
(uint32) (recptr >> 32), (uint32) recptr);
PG_RETURN_TEXT_P(cstring_to_text(location));
}
| Datum pg_start_backup | ( | PG_FUNCTION_ARGS | ) |
Definition at line 49 of file xlogfuncs.c.
References cstring_to_text(), do_pg_start_backup(), NULL, PG_GETARG_BOOL, PG_GETARG_TEXT_P, PG_RETURN_TEXT_P, snprintf(), and text_to_cstring().
{
text *backupid = PG_GETARG_TEXT_P(0);
bool fast = PG_GETARG_BOOL(1);
char *backupidstr;
XLogRecPtr startpoint;
char startxlogstr[MAXFNAMELEN];
backupidstr = text_to_cstring(backupid);
startpoint = do_pg_start_backup(backupidstr, fast, NULL, NULL);
snprintf(startxlogstr, sizeof(startxlogstr), "%X/%X",
(uint32) (startpoint >> 32), (uint32) startpoint);
PG_RETURN_TEXT_P(cstring_to_text(startxlogstr));
}
| Datum pg_stop_backup | ( | PG_FUNCTION_ARGS | ) |
Definition at line 80 of file xlogfuncs.c.
References cstring_to_text(), do_pg_stop_backup(), NULL, PG_RETURN_TEXT_P, and snprintf().
{
XLogRecPtr stoppoint;
char stopxlogstr[MAXFNAMELEN];
stoppoint = do_pg_stop_backup(NULL, true, NULL);
snprintf(stopxlogstr, sizeof(stopxlogstr), "%X/%X",
(uint32) (stoppoint >> 32), (uint32) stoppoint);
PG_RETURN_TEXT_P(cstring_to_text(stopxlogstr));
}
| Datum pg_switch_xlog | ( | PG_FUNCTION_ARGS | ) |
Definition at line 96 of file xlogfuncs.c.
References cstring_to_text(), ereport, errcode(), errhint(), errmsg(), ERROR, PG_RETURN_TEXT_P, RecoveryInProgress(), RequestXLogSwitch(), snprintf(), and superuser().
{
XLogRecPtr switchpoint;
char location[MAXFNAMELEN];
if (!superuser())
ereport(ERROR,
(errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
(errmsg("must be superuser to switch transaction log files"))));
if (RecoveryInProgress())
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("recovery is in progress"),
errhint("WAL control functions cannot be executed during recovery.")));
switchpoint = RequestXLogSwitch();
/*
* As a convenience, return the WAL location of the switch record
*/
snprintf(location, sizeof(location), "%X/%X",
(uint32) (switchpoint >> 32), (uint32) switchpoint);
PG_RETURN_TEXT_P(cstring_to_text(location));
}
| Datum pg_xlog_location_diff | ( | PG_FUNCTION_ARGS | ) |
Definition at line 504 of file xlogfuncs.c.
References DatumGetNumeric, DirectFunctionCall1, DirectFunctionCall2, ereport, errcode(), errmsg(), ERROR, Int64GetDatum(), int8_numeric(), numeric_sub(), PG_GETARG_TEXT_P, PG_RETURN_NUMERIC, text_to_cstring(), and validate_xlog_location().
{
text *location1 = PG_GETARG_TEXT_P(0);
text *location2 = PG_GETARG_TEXT_P(1);
char *str1,
*str2;
XLogRecPtr loc1,
loc2;
Numeric result;
uint64 bytes1,
bytes2;
uint32 hi,
lo;
/*
* Read and parse input
*/
str1 = text_to_cstring(location1);
str2 = text_to_cstring(location2);
validate_xlog_location(str1);
validate_xlog_location(str2);
if (sscanf(str1, "%X/%X", &hi, &lo) != 2)
ereport(ERROR,
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
errmsg("could not parse transaction log location \"%s\"", str1)));
loc1 = ((uint64) hi) << 32 | lo;
if (sscanf(str2, "%X/%X", &hi, &lo) != 2)
ereport(ERROR,
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
errmsg("could not parse transaction log location \"%s\"", str2)));
loc2 = ((uint64) hi) << 32 | lo;
bytes1 = (uint64) loc1;
bytes2 = (uint64) loc2;
/*
* result = bytes1 - bytes2.
*
* XXX: this won't handle values higher than 2^63 correctly.
*/
result = DatumGetNumeric(DirectFunctionCall2(numeric_sub,
DirectFunctionCall1(int8_numeric, Int64GetDatum((int64) bytes1)),
DirectFunctionCall1(int8_numeric, Int64GetDatum((int64) bytes2))));
PG_RETURN_NUMERIC(result);
}
| Datum pg_xlog_replay_pause | ( | PG_FUNCTION_ARGS | ) |
Definition at line 387 of file xlogfuncs.c.
References ereport, errcode(), errhint(), errmsg(), ERROR, PG_RETURN_VOID, RecoveryInProgress(), SetRecoveryPause(), and superuser().
{
if (!superuser())
ereport(ERROR,
(errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
(errmsg("must be superuser to control recovery"))));
if (!RecoveryInProgress())
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("recovery is not in progress"),
errhint("Recovery control functions can only be executed during recovery.")));
SetRecoveryPause(true);
PG_RETURN_VOID();
}
| Datum pg_xlog_replay_resume | ( | PG_FUNCTION_ARGS | ) |
Definition at line 409 of file xlogfuncs.c.
References ereport, errcode(), errhint(), errmsg(), ERROR, PG_RETURN_VOID, RecoveryInProgress(), SetRecoveryPause(), and superuser().
{
if (!superuser())
ereport(ERROR,
(errcode(ERRCODE_INSUFFICIENT_PRIVILEGE),
(errmsg("must be superuser to control recovery"))));
if (!RecoveryInProgress())
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("recovery is not in progress"),
errhint("Recovery control functions can only be executed during recovery.")));
SetRecoveryPause(false);
PG_RETURN_VOID();
}
| Datum pg_xlogfile_name | ( | PG_FUNCTION_ARGS | ) |
Definition at line 350 of file xlogfuncs.c.
References cstring_to_text(), ereport, errcode(), errhint(), errmsg(), ERROR, PG_GETARG_TEXT_P, PG_RETURN_TEXT_P, RecoveryInProgress(), text_to_cstring(), ThisTimeLineID, validate_xlog_location(), XLByteToPrevSeg, and XLogFileName.
{
text *location = PG_GETARG_TEXT_P(0);
char *locationstr;
uint32 hi,
lo;
XLogSegNo xlogsegno;
XLogRecPtr locationpoint;
char xlogfilename[MAXFNAMELEN];
if (RecoveryInProgress())
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("recovery is in progress"),
errhint("pg_xlogfile_name() cannot be executed during recovery.")));
locationstr = text_to_cstring(location);
validate_xlog_location(locationstr);
if (sscanf(locationstr, "%X/%X", &hi, &lo) != 2)
ereport(ERROR,
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
errmsg("could not parse transaction log location \"%s\"",
locationstr)));
locationpoint = ((uint64) hi) << 32 | lo;
XLByteToPrevSeg(locationpoint, xlogsegno);
XLogFileName(xlogfilename, ThisTimeLineID, xlogsegno);
PG_RETURN_TEXT_P(cstring_to_text(xlogfilename));
}
| Datum pg_xlogfile_name_offset | ( | PG_FUNCTION_ARGS | ) |
Definition at line 270 of file xlogfuncs.c.
References BlessTupleDesc(), CreateTemplateTupleDesc(), CStringGetTextDatum, ereport, errcode(), errhint(), errmsg(), ERROR, heap_form_tuple(), HeapTupleGetDatum, INT4OID, PG_GETARG_TEXT_P, PG_RETURN_DATUM, RecoveryInProgress(), text_to_cstring(), TEXTOID, ThisTimeLineID, TupleDescInitEntry(), UInt32GetDatum, validate_xlog_location(), values, XLByteToPrevSeg, and XLogFileName.
{
text *location = PG_GETARG_TEXT_P(0);
char *locationstr;
uint32 hi,
lo;
XLogSegNo xlogsegno;
uint32 xrecoff;
XLogRecPtr locationpoint;
char xlogfilename[MAXFNAMELEN];
Datum values[2];
bool isnull[2];
TupleDesc resultTupleDesc;
HeapTuple resultHeapTuple;
Datum result;
if (RecoveryInProgress())
ereport(ERROR,
(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
errmsg("recovery is in progress"),
errhint("pg_xlogfile_name_offset() cannot be executed during recovery.")));
/*
* Read input and parse
*/
locationstr = text_to_cstring(location);
validate_xlog_location(locationstr);
if (sscanf(locationstr, "%X/%X", &hi, &lo) != 2)
ereport(ERROR,
(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
errmsg("could not parse transaction log location \"%s\"",
locationstr)));
locationpoint = ((uint64) hi) << 32 | lo;
/*
* Construct a tuple descriptor for the result row. This must match this
* function's pg_proc entry!
*/
resultTupleDesc = CreateTemplateTupleDesc(2, false);
TupleDescInitEntry(resultTupleDesc, (AttrNumber) 1, "file_name",
TEXTOID, -1, 0);
TupleDescInitEntry(resultTupleDesc, (AttrNumber) 2, "file_offset",
INT4OID, -1, 0);
resultTupleDesc = BlessTupleDesc(resultTupleDesc);
/*
* xlogfilename
*/
XLByteToPrevSeg(locationpoint, xlogsegno);
XLogFileName(xlogfilename, ThisTimeLineID, xlogsegno);
values[0] = CStringGetTextDatum(xlogfilename);
isnull[0] = false;
/*
* offset
*/
xrecoff = locationpoint % XLogSegSize;
values[1] = UInt32GetDatum(xrecoff);
isnull[1] = false;
/*
* Tuple jam: Having first prepared your Datums, then squash together
*/
resultHeapTuple = heap_form_tuple(resultTupleDesc, values, isnull);
result = HeapTupleGetDatum(resultHeapTuple);
PG_RETURN_DATUM(result);
}
| static void validate_xlog_location | ( | char * | str | ) | [static] |
Definition at line 480 of file xlogfuncs.c.
References ereport, errcode(), errmsg(), ERROR, and MAXLSNCOMPONENT.
Referenced by pg_xlog_location_diff(), pg_xlogfile_name(), and pg_xlogfile_name_offset().
{
#define MAXLSNCOMPONENT 8
int len1,
len2;
len1 = strspn(str, "0123456789abcdefABCDEF");
if (len1 < 1 || len1 > MAXLSNCOMPONENT || str[len1] != '/')
ereport(ERROR,
(errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
errmsg("invalid input syntax for transaction log location: \"%s\"", str)));
len2 = strspn(str + len1 + 1, "0123456789abcdefABCDEF");
if (len2 < 1 || len2 > MAXLSNCOMPONENT || str[len1 + 1 + len2] != '\0')
ereport(ERROR,
(errcode(ERRCODE_INVALID_TEXT_REPRESENTATION),
errmsg("invalid input syntax for transaction log location: \"%s\"", str)));
}
1.7.1