($INBOX_DIR/description missing)help / color / mirror / Atom feed
[PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState 21+ messages / 2 participants [nested] [flat]
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState @ 2020-05-08 20:40 Alvaro Herrera <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Alvaro Herrera @ 2020-05-08 20:40 UTC (permalink / raw) --- src/backend/access/transam/xlogreader.c | 31 +++++++++++-------------- src/backend/access/transam/xlogutils.c | 1 - src/backend/replication/walsender.c | 6 ++--- src/bin/pg_waldump/pg_waldump.c | 1 - src/include/access/xlogreader.h | 4 +--- 5 files changed, 17 insertions(+), 26 deletions(-) diff --git a/src/backend/access/transam/xlogreader.c b/src/backend/access/transam/xlogreader.c index 7cee8b92c9..f42dee2640 100644 --- a/src/backend/access/transam/xlogreader.c +++ b/src/backend/access/transam/xlogreader.c @@ -1050,8 +1050,6 @@ err: * Read 'count' bytes into 'buf', starting at location 'startptr', from WAL * fetched from timeline 'tli'. * - * 'seg/segcxt' identify the last segment used. - * * Returns true if succeeded, false if an error occurs, in which case * 'errinfo' receives error details. * @@ -1061,7 +1059,6 @@ err: bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, TimeLineID tli, - WALOpenSegment *seg, WALSegmentContext *segcxt, WALReadError *errinfo) { char *p; @@ -1078,34 +1075,34 @@ WALRead(XLogReaderState *state, int segbytes; int readbytes; - startoff = XLogSegmentOffset(recptr, segcxt->ws_segsize); + startoff = XLogSegmentOffset(recptr, state->segcxt.ws_segsize); /* * If the data we want is not in a segment we have open, close what we * have (if anything) and open the next one, using the caller's * provided openSegment callback. */ - if (seg->ws_file < 0 || - !XLByteInSeg(recptr, seg->ws_segno, segcxt->ws_segsize) || - tli != seg->ws_tli) + if (state->seg.ws_file < 0 || + !XLByteInSeg(recptr, state->seg.ws_segno, state->segcxt.ws_segsize) || + tli != state->seg.ws_tli) { XLogSegNo nextSegNo; - if (seg->ws_file >= 0) + if (state->seg.ws_file >= 0) state->routine.segment_close(state); - XLByteToSeg(recptr, nextSegNo, segcxt->ws_segsize); - seg->ws_file = state->routine.segment_open(state, nextSegNo, - segcxt, &tli); + XLByteToSeg(recptr, nextSegNo, state->segcxt.ws_segsize); + state->seg.ws_file = state->routine.segment_open(state, nextSegNo, + &state->segcxt, &tli); /* Update the current segment info. */ - seg->ws_tli = tli; - seg->ws_segno = nextSegNo; + state->seg.ws_tli = tli; + state->seg.ws_segno = nextSegNo; } /* How many bytes are within this segment? */ - if (nbytes > (segcxt->ws_segsize - startoff)) - segbytes = segcxt->ws_segsize - startoff; + if (nbytes > (state->segcxt.ws_segsize - startoff)) + segbytes = state->segcxt.ws_segsize - startoff; else segbytes = nbytes; @@ -1115,7 +1112,7 @@ WALRead(XLogReaderState *state, /* Reset errno first; eases reporting non-errno-affecting errors */ errno = 0; - readbytes = pg_pread(seg->ws_file, p, segbytes, (off_t) startoff); + readbytes = pg_pread(state->seg.ws_file, p, segbytes, (off_t) startoff); #ifndef FRONTEND pgstat_report_wait_end(); @@ -1127,7 +1124,7 @@ WALRead(XLogReaderState *state, errinfo->wre_req = segbytes; errinfo->wre_read = readbytes; errinfo->wre_off = startoff; - errinfo->wre_seg = *seg; + errinfo->wre_seg = state->seg; return false; } diff --git a/src/backend/access/transam/xlogutils.c b/src/backend/access/transam/xlogutils.c index bbd801513a..fc0bb7d059 100644 --- a/src/backend/access/transam/xlogutils.c +++ b/src/backend/access/transam/xlogutils.c @@ -947,7 +947,6 @@ read_local_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, * zero-padded up to the page boundary if it's incomplete. */ if (!WALRead(state, cur_page, targetPagePtr, XLOG_BLCKSZ, tli, - &state->seg, &state->segcxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/backend/replication/walsender.c b/src/backend/replication/walsender.c index d18475b854..ed8c08cb6a 100644 --- a/src/backend/replication/walsender.c +++ b/src/backend/replication/walsender.c @@ -840,8 +840,6 @@ logical_read_xlog_page(XLogReaderState *state, XLogRecPtr targetPagePtr, int req sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); @@ -2760,6 +2758,8 @@ XLogSendPhysical(void) enlargeStringInfo(&output_message, nbytes); retry: + fake_xlogreader.seg = *sendSeg; + fake_xlogreader.segcxt = *sendCxt; if (!WALRead(&fake_xlogreader, &output_message.data[output_message.len], startptr, @@ -2767,8 +2767,6 @@ retry: sendSeg->ws_tli, /* Pass the current TLI because only * WalSndSegmentOpen controls whether new * TLI is needed. */ - sendSeg, - sendCxt, &errinfo)) WALReadRaiseError(&errinfo); diff --git a/src/bin/pg_waldump/pg_waldump.c b/src/bin/pg_waldump/pg_waldump.c index e29f65500f..46734914b7 100644 --- a/src/bin/pg_waldump/pg_waldump.c +++ b/src/bin/pg_waldump/pg_waldump.c @@ -356,7 +356,6 @@ WALDumpReadPage(XLogReaderState *state, XLogRecPtr targetPagePtr, int reqLen, } if (!WALRead(state, readBuff, targetPagePtr, count, private->timeline, - &state->seg, &state->segcxt, &errinfo)) { WALOpenSegment *seg = &errinfo.wre_seg; diff --git a/src/include/access/xlogreader.h b/src/include/access/xlogreader.h index 81af200f5e..e77f478d68 100644 --- a/src/include/access/xlogreader.h +++ b/src/include/access/xlogreader.h @@ -301,9 +301,7 @@ typedef struct WALReadError extern bool WALRead(XLogReaderState *state, char *buf, XLogRecPtr startptr, Size count, - TimeLineID tli, WALOpenSegment *seg, - WALSegmentContext *segcxt, - WALReadError *errinfo); + TimeLineID tli, WALReadError *errinfo); /* Functions for decoding an XLogRecord */ -- 2.20.1 --/04w6evG8XlLl3ft Content-Type: text/x-diff; charset=us-ascii Content-Disposition: attachment; filename="0002-Simplify-XLogReader-s-open_segment-API.patch" ^ permalink raw reply [nested|flat] 21+ messages in thread
* Re: Adding support for SSLKEYLOGFILE in the frontend @ 2025-04-01 20:22 Daniel Gustafsson <[email protected]> 0 siblings, 0 replies; 21+ messages in thread From: Daniel Gustafsson @ 2025-04-01 20:22 UTC (permalink / raw) To: pgsql-hackers; +Cc: Tom Lane <[email protected]>; Jacob Champion <[email protected]>; Abhishek Chanda <[email protected]>; Álvaro Herrera <[email protected]> I took another pass at this one and did a few small tweaks, so I would to take it for another spin across CI before looking at committing it. There are no functionality changes, only polish. -- Daniel Gustafsson Attachments: [application/octet-stream] v11-0001-libpq-Add-support-for-dumping-SSL-keylog-to-file.patch (9.9K, ../../[email protected]/2-v11-0001-libpq-Add-support-for-dumping-SSL-keylog-to-file.patch) download | inline diff: From 6f5af1cd5dd3ab6047f4781bdc79d4053022cad9 Mon Sep 17 00:00:00 2001 From: Daniel Gustafsson <[email protected]> Date: Thu, 13 Mar 2025 22:55:35 +0100 Subject: [PATCH v11] libpq: Add support for dumping SSL keylog to file This adds a new connection parameter which instructs libpq to write out keymaterial clientside into a file in order to make connection debugging with Wireshark and similar tools possible. The file format used is the standardized NSS format. Author: Abhishek Chanda <[email protected]> Co-authored-by: Daniel Gustafsson <[email protected]> Reviewed-by: Jacob Champion <[email protected]> Discussion: https://postgr.es/m/CAKiP-K85C8uQbzXKWf5wHQPkuygGUGcufke713iHmYWOe9q2dA@mail.gmail.com --- configure | 2 +- configure.ac | 2 +- doc/src/sgml/libpq.sgml | 24 ++++++++++ meson.build | 1 + src/include/pg_config.h.in | 3 ++ src/interfaces/libpq/fe-connect.c | 4 ++ src/interfaces/libpq/fe-secure-openssl.c | 58 ++++++++++++++++++++++++ src/interfaces/libpq/libpq-int.h | 1 + src/test/ssl/t/001_ssltests.pl | 27 +++++++++++ 9 files changed, 120 insertions(+), 2 deletions(-) diff --git a/configure b/configure index 30d949c3c46..ac343659c24 100755 --- a/configure +++ b/configure @@ -12931,7 +12931,7 @@ fi done # Function introduced in OpenSSL 1.1.1, not in LibreSSL. - for ac_func in X509_get_signature_info SSL_CTX_set_num_tickets + for ac_func in X509_get_signature_info SSL_CTX_set_num_tickets SSL_CTX_set_keylog_callback do : as_ac_var=`$as_echo "ac_cv_func_$ac_func" | $as_tr_sh` ac_fn_c_check_func "$LINENO" "$ac_func" "$as_ac_var" diff --git a/configure.ac b/configure.ac index 25cdfcf65af..1f48ed3f116 100644 --- a/configure.ac +++ b/configure.ac @@ -1382,7 +1382,7 @@ if test "$with_ssl" = openssl ; then # Function introduced in OpenSSL 1.0.2, not in LibreSSL. AC_CHECK_FUNCS([SSL_CTX_set_cert_cb]) # Function introduced in OpenSSL 1.1.1, not in LibreSSL. - AC_CHECK_FUNCS([X509_get_signature_info SSL_CTX_set_num_tickets]) + AC_CHECK_FUNCS([X509_get_signature_info SSL_CTX_set_num_tickets SSL_CTX_set_keylog_callback]) AC_DEFINE([USE_OPENSSL], 1, [Define to 1 to build with OpenSSL support. (--with-ssl=openssl)]) elif test "$with_ssl" != no ; then AC_MSG_ERROR([--with-ssl must specify openssl]) diff --git a/doc/src/sgml/libpq.sgml b/doc/src/sgml/libpq.sgml index b359fbff295..c49605c4879 100644 --- a/doc/src/sgml/libpq.sgml +++ b/doc/src/sgml/libpq.sgml @@ -1918,6 +1918,30 @@ postgresql://%2Fvar%2Flib%2Fpostgresql/dbname </listitem> </varlistentry> + <varlistentry id="libpq-connect-sslkeylogfile" xreflabel="sslkeylogfile"> + <term><literal>sslkeylogfile</literal></term> + <listitem> + <para> + This parameter specifies the location where <literal>libpq</literal> + will log keys used in this SSL context. This is useful for debugging + <productname>PostgreSQL</productname> protocol interactions or client + connections using network inspection tools like + <productname>Wireshark</productname>. This parameter is ignored if an + SSL connection is not made, or if <productname>LibreSSL</productname> + is used (<productname>LibreSSL</productname> does not support key + logging). Keys are logged using the <productname>NSS</productname> + format. + <warning> + <para> + Key logging will expose potentially sensitive information in the + keylog file. Keylog files should be handled with the same care as + <xref linkend="libpq-connect-sslkey" /> files. + </para> + </warning> + </para> + </listitem> + </varlistentry> + <varlistentry id="libpq-connect-sslpassword" xreflabel="sslpassword"> <term><literal>sslpassword</literal></term> <listitem> diff --git a/meson.build b/meson.build index b8da4966297..7d5e3348a73 100644 --- a/meson.build +++ b/meson.build @@ -1479,6 +1479,7 @@ if sslopt in ['auto', 'openssl'] # Function introduced in OpenSSL 1.1.1, not in LibreSSL. ['X509_get_signature_info'], ['SSL_CTX_set_num_tickets'], + ['SSL_CTX_set_keylog_callback'], ] are_openssl_funcs_complete = true diff --git a/src/include/pg_config.h.in b/src/include/pg_config.h.in index 92f0616c400..8e35c02e208 100644 --- a/src/include/pg_config.h.in +++ b/src/include/pg_config.h.in @@ -364,6 +364,9 @@ /* Define to 1 if you have the `SSL_CTX_set_ciphersuites' function. */ #undef HAVE_SSL_CTX_SET_CIPHERSUITES +/* Define to 1 if you have the `SSL_CTX_set_keylog_callback' function. */ +#undef HAVE_SSL_CTX_SET_KEYLOG_CALLBACK + /* Define to 1 if you have the `SSL_CTX_set_num_tickets' function. */ #undef HAVE_SSL_CTX_SET_NUM_TICKETS diff --git a/src/interfaces/libpq/fe-connect.c b/src/interfaces/libpq/fe-connect.c index d5051f5e820..ead446b4eef 100644 --- a/src/interfaces/libpq/fe-connect.c +++ b/src/interfaces/libpq/fe-connect.c @@ -391,6 +391,10 @@ static const internalPQconninfoOption PQconninfoOptions[] = { "OAuth-Scope", "", 15, offsetof(struct pg_conn, oauth_scope)}, + {"sslkeylogfile", NULL, NULL, NULL, + "SSL-Key-Log-File", "", 0, /* sizeof("") = 0 */ + offsetof(struct pg_conn, sslkeylogfile)}, + /* Terminating entry --- MUST BE LAST */ {NULL, NULL, NULL, NULL, NULL, NULL, 0} diff --git a/src/interfaces/libpq/fe-secure-openssl.c b/src/interfaces/libpq/fe-secure-openssl.c index 5bb9d9779d8..4bfd8e0447c 100644 --- a/src/interfaces/libpq/fe-secure-openssl.c +++ b/src/interfaces/libpq/fe-secure-openssl.c @@ -57,6 +57,7 @@ * include <wincrypt.h>, but some other Windows headers do.) */ #include "common/openssl.h" +#include <openssl/ssl.h> #include <openssl/conf.h> #ifdef USE_SSL_ENGINE #include <openssl/engine.h> @@ -684,6 +685,49 @@ pgtls_verify_peer_name_matches_certificate_guts(PGconn *conn, /* See pqcomm.h comments on OpenSSL implementation of ALPN (RFC 7301) */ static unsigned char alpn_protos[] = PG_ALPN_PROTOCOL_VECTOR; +#ifdef HAVE_SSL_CTX_SET_KEYLOG_CALLBACK +/* + * SSL Key Logging callback + * + * This callback lets the user store all key material to a file for debugging + * purposes. The file will be written using the NSS keylog format. LibreSSL + * 3.5 introduced stub function to set the callback for OpenSSL compatibility + * but the callback is never invoked. + */ +static void +SSL_CTX_keylog_cb(const SSL *ssl, const char *line) +{ + int fd; + mode_t old_umask; + ssize_t rc; + PGconn *conn = SSL_get_app_data(ssl); + + if (conn == NULL) + return; + + old_umask = umask(077); + fd = open(conn->sslkeylogfile, O_WRONLY | O_APPEND | O_CREAT, 0600); + umask(old_umask); + + if (fd == -1) + { + libpq_append_conn_error(conn, "could not open ssl keylog file %s: %s", + conn->sslkeylogfile, pg_strerror(errno)); + return; + } + + /* line is guaranteed by OpenSSL to be NUL terminated */ + rc = write(fd, line, strlen(line)); + if (rc < 0) + libpq_append_conn_error(conn, "could not write to ssl keylog file %s: %s", + conn->sslkeylogfile, pg_strerror(errno)); + else + rc = write(fd, "\n", 1); + (void) rc; /* silence compiler warnings */ + close(fd); +} +#endif + /* * Create per-connection SSL object, and load the client certificate, * private key, and trusted CA certs. @@ -1000,6 +1044,20 @@ initialize_SSL(PGconn *conn) } conn->ssl_in_use = true; + if (conn->sslkeylogfile && strlen(conn->sslkeylogfile) > 0) + { +#ifdef HAVE_SSL_CTX_SET_KEYLOG_CALLBACK + SSL_CTX_set_keylog_callback(SSL_context, SSL_CTX_keylog_cb); +#else +#ifdef LIBRESSL_VERSION_NUMBER + fprintf(stderr, libpq_gettext("WARNING: sslkeylogfile support requires OpenSSL\n")); +#else + fprintf(stderr, libpq_gettext("WARNING: libpq was not built with sslkeylogfile support\n")); +#endif +#endif + } + + /* * SSL contexts are reference counted by OpenSSL. We can free it as soon * as we have created the SSL object, and it will stick around for as long diff --git a/src/interfaces/libpq/libpq-int.h b/src/interfaces/libpq/libpq-int.h index ade5ad82f07..ac148fe8c32 100644 --- a/src/interfaces/libpq/libpq-int.h +++ b/src/interfaces/libpq/libpq-int.h @@ -424,6 +424,7 @@ struct pg_conn char *load_balance_hosts; /* load balance over hosts */ char *scram_client_key; /* base64-encoded SCRAM client key */ char *scram_server_key; /* base64-encoded SCRAM server key */ + char *sslkeylogfile; /* where should the client write ssl keylogs */ bool cancelRequest; /* true if this connection is used to send a * cancel request, instead of being a normal diff --git a/src/test/ssl/t/001_ssltests.pl b/src/test/ssl/t/001_ssltests.pl index 5422511d4ab..086abf3b8b3 100644 --- a/src/test/ssl/t/001_ssltests.pl +++ b/src/test/ssl/t/001_ssltests.pl @@ -147,6 +147,33 @@ my $default_ssl_connstr = $common_connstr = "$default_ssl_connstr user=ssltestuser dbname=trustdb hostaddr=$SERVERHOSTADDR host=common-name.pg-ssltest.test"; +SKIP: +{ + skip "Keylogging is not supported with LibreSSL", 5 if $libressl; + + my $tempdir = PostgreSQL::Test::Utils::tempdir; + my @status; + + # Properly escape backslashes in the path + $tempdir =~ s/\\/\\\\/g; + + # Connect should work with a given sslkeylogfile + $node->connect_ok( + "$common_connstr sslrootcert=ssl/root+server_ca.crt sslkeylogfile=$tempdir/key.txt sslmode=require", + "connect with server root cert and sslkeylogfile=$tempdir/key.txt"); + + # Verify the key file exists + ok(-f "$tempdir/key.txt", "keylog file exists at: $tempdir/key.txt"); + + # Skip permission checks on Windows/Cygwin + skip "Permissions check not enforced on Windows", 2 + if ($windows_os || $Config::Config{osname} eq 'cygwin'); + + ok( (@status = stat("$tempdir/key.txt")), + "keylog file exists and returned status"); + ok(@status && !($status[2] & 0006), "keylog file is not world readable"); +} + # The server should not accept non-SSL connections. $node->connect_fails( "$common_connstr sslmode=disable", -- 2.39.3 (Apple Git-146) ^ permalink raw reply [nested|flat] 21+ messages in thread
end of thread, other threads:[~2025-04-01 20:22 UTC | newest] Thread overview: 21+ messages (download: mbox mbox.gz follow: Atom feed) -- links below jump to the message on this page -- 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2020-05-08 20:40 [PATCH 1/2] fix WALRead API to take seg/segcxt from XLogReaderState Alvaro Herrera <[email protected]> 2025-04-01 20:22 Re: Adding support for SSLKEYLOGFILE in the frontend Daniel Gustafsson <[email protected]>
This inbox is served by agora; see mirroring instructions for how to clone and mirror all data and code used for this inbox