PostgreSQL Source Code  git master
timeline.c File Reference
#include "postgres_fe.h"
#include "access/timeline.h"
#include "pg_rewind.h"
Include dependency graph for timeline.c:

Go to the source code of this file.

Functions

TimeLineHistoryEntryrewind_parseTimeLineHistory (char *buffer, TimeLineID targetTLI, int *nentries)
 

Function Documentation

◆ rewind_parseTimeLineHistory()

TimeLineHistoryEntry* rewind_parseTimeLineHistory ( char *  buffer,
TimeLineID  targetTLI,
int *  nentries 
)

Definition at line 28 of file timeline.c.

29 {
30  char *fline;
31  TimeLineHistoryEntry *entry;
32  TimeLineHistoryEntry *entries = NULL;
33  int nlines = 0;
34  TimeLineID lasttli = 0;
35  XLogRecPtr prevend;
36  char *bufptr;
37  bool lastline = false;
38 
39  /*
40  * Parse the file...
41  */
42  prevend = InvalidXLogRecPtr;
43  bufptr = buffer;
44  while (!lastline)
45  {
46  char *ptr;
47  TimeLineID tli;
48  uint32 switchpoint_hi;
49  uint32 switchpoint_lo;
50  int nfields;
51 
52  fline = bufptr;
53  while (*bufptr && *bufptr != '\n')
54  bufptr++;
55  if (!(*bufptr))
56  lastline = true;
57  else
58  *bufptr++ = '\0';
59 
60  /* skip leading whitespace and check for # comment */
61  for (ptr = fline; *ptr; ptr++)
62  {
63  if (!isspace((unsigned char) *ptr))
64  break;
65  }
66  if (*ptr == '\0' || *ptr == '#')
67  continue;
68 
69  nfields = sscanf(fline, "%u\t%X/%X", &tli, &switchpoint_hi, &switchpoint_lo);
70 
71  if (nfields < 1)
72  {
73  /* expect a numeric timeline ID as first field of line */
74  pg_log_error("syntax error in history file: %s", fline);
75  pg_log_error_detail("Expected a numeric timeline ID.");
76  exit(1);
77  }
78  if (nfields != 3)
79  {
80  pg_log_error("syntax error in history file: %s", fline);
81  pg_log_error_detail("Expected a write-ahead log switchpoint location.");
82  exit(1);
83  }
84  if (entries && tli <= lasttli)
85  {
86  pg_log_error("invalid data in history file: %s", fline);
87  pg_log_error_detail("Timeline IDs must be in increasing sequence.");
88  exit(1);
89  }
90 
91  lasttli = tli;
92 
93  nlines++;
94  entries = pg_realloc(entries, nlines * sizeof(TimeLineHistoryEntry));
95 
96  entry = &entries[nlines - 1];
97  entry->tli = tli;
98  entry->begin = prevend;
99  entry->end = ((uint64) (switchpoint_hi)) << 32 | (uint64) switchpoint_lo;
100  prevend = entry->end;
101 
102  /* we ignore the remainder of each line */
103  }
104 
105  if (entries && targetTLI <= lasttli)
106  {
107  pg_log_error("invalid data in history file");
108  pg_log_error_detail("Timeline IDs must be less than child timeline's ID.");
109  exit(1);
110  }
111 
112  /*
113  * Create one more entry for the "tip" of the timeline, which has no entry
114  * in the history file.
115  */
116  nlines++;
117  if (entries)
118  entries = pg_realloc(entries, nlines * sizeof(TimeLineHistoryEntry));
119  else
120  entries = pg_malloc(1 * sizeof(TimeLineHistoryEntry));
121 
122  entry = &entries[nlines - 1];
123  entry->tli = targetTLI;
124  entry->begin = prevend;
125  entry->end = InvalidXLogRecPtr;
126 
127  *nentries = nlines;
128  return entries;
129 }
uint64_t uint64
Definition: c.h:486
uint32_t uint32
Definition: c.h:485
void * pg_realloc(void *ptr, size_t size)
Definition: fe_memutils.c:65
void * pg_malloc(size_t size)
Definition: fe_memutils.c:47
exit(1)
#define pg_log_error(...)
Definition: logging.h:106
#define pg_log_error_detail(...)
Definition: logging.h:109
XLogRecPtr begin
Definition: timeline.h:28
TimeLineID tli
Definition: timeline.h:27
XLogRecPtr end
Definition: timeline.h:29
uint64 XLogRecPtr
Definition: xlogdefs.h:21
#define InvalidXLogRecPtr
Definition: xlogdefs.h:28
uint32 TimeLineID
Definition: xlogdefs.h:59

References TimeLineHistoryEntry::begin, TimeLineHistoryEntry::end, exit(), InvalidXLogRecPtr, pg_log_error, pg_log_error_detail, pg_malloc(), pg_realloc(), and TimeLineHistoryEntry::tli.

Referenced by getTimelineHistory().