@@ -36,12 +36,13 @@ static int verbose = 0;
36
36
static int compresslevel = 0 ;
37
37
static int noloop = 0 ;
38
38
static int standby_message_timeout = 10 * 1000 ; /* 10 sec = default */
39
- static volatile bool time_to_abort = false;
39
+ static volatile bool time_to_stop = false;
40
40
static bool do_create_slot = false;
41
41
static bool slot_exists_ok = false;
42
42
static bool do_drop_slot = false;
43
43
static bool synchronous = false;
44
44
static char * replication_slot = NULL ;
45
+ static XLogRecPtr endpos = InvalidXLogRecPtr ;
45
46
46
47
47
48
static void usage (void );
@@ -77,6 +78,7 @@ usage(void)
77
78
printf (_ (" %s [OPTION]...\n" ), progname );
78
79
printf (_ ("\nOptions:\n" ));
79
80
printf (_ (" -D, --directory=DIR receive write-ahead log files into this directory\n" ));
81
+ printf (_ (" -E, --endpos=LSN exit after receiving the specified LSN\n" ));
80
82
printf (_ (" --if-not-exists do not error if slot already exists when creating a slot\n" ));
81
83
printf (_ (" -n, --no-loop do not loop on connection lost\n" ));
82
84
printf (_ (" -s, --status-interval=SECS\n"
@@ -112,6 +114,16 @@ stop_streaming(XLogRecPtr xlogpos, uint32 timeline, bool segment_finished)
112
114
progname , (uint32 ) (xlogpos >> 32 ), (uint32 ) xlogpos ,
113
115
timeline );
114
116
117
+ if (!XLogRecPtrIsInvalid (endpos ) && endpos < xlogpos )
118
+ {
119
+ if (verbose )
120
+ fprintf (stderr , _ ("%s: stopped streaming at %X/%X (timeline %u)\n" ),
121
+ progname , (uint32 ) (xlogpos >> 32 ), (uint32 ) xlogpos ,
122
+ timeline );
123
+ time_to_stop = true;
124
+ return true;
125
+ }
126
+
115
127
/*
116
128
* Note that we report the previous, not current, position here. After a
117
129
* timeline switch, xlogpos points to the beginning of the segment because
@@ -128,7 +140,7 @@ stop_streaming(XLogRecPtr xlogpos, uint32 timeline, bool segment_finished)
128
140
prevtimeline = timeline ;
129
141
prevpos = xlogpos ;
130
142
131
- if (time_to_abort )
143
+ if (time_to_stop )
132
144
{
133
145
if (verbose )
134
146
fprintf (stderr , _ ("%s: received interrupt signal, exiting\n" ),
@@ -448,7 +460,7 @@ StreamLog(void)
448
460
static void
449
461
sigint_handler (int signum )
450
462
{
451
- time_to_abort = true;
463
+ time_to_stop = true;
452
464
}
453
465
#endif
454
466
@@ -460,6 +472,7 @@ main(int argc, char **argv)
460
472
{"version" , no_argument , NULL , 'V' },
461
473
{"directory" , required_argument , NULL , 'D' },
462
474
{"dbname" , required_argument , NULL , 'd' },
475
+ {"endpos" , required_argument , NULL , 'E' },
463
476
{"host" , required_argument , NULL , 'h' },
464
477
{"port" , required_argument , NULL , 'p' },
465
478
{"username" , required_argument , NULL , 'U' },
@@ -481,6 +494,7 @@ main(int argc, char **argv)
481
494
int c ;
482
495
int option_index ;
483
496
char * db_name ;
497
+ uint32 hi , lo ;
484
498
485
499
progname = get_progname (argv [0 ]);
486
500
set_pglocale_pgservice (argv [0 ], PG_TEXTDOMAIN ("pg_basebackup" ));
@@ -500,7 +514,7 @@ main(int argc, char **argv)
500
514
}
501
515
}
502
516
503
- while ((c = getopt_long (argc , argv , "D:d:h:p:U:s:S:nwWvZ:" ,
517
+ while ((c = getopt_long (argc , argv , "D:d:E: h:p:U:s:S:nwWvZ:" ,
504
518
long_options , & option_index )) != -1 )
505
519
{
506
520
switch (c )
@@ -544,6 +558,16 @@ main(int argc, char **argv)
544
558
case 'S' :
545
559
replication_slot = pg_strdup (optarg );
546
560
break ;
561
+ case 'E' :
562
+ if (sscanf (optarg , "%X/%X" , & hi , & lo ) != 2 )
563
+ {
564
+ fprintf (stderr ,
565
+ _ ("%s: could not parse end position \"%s\"\n" ),
566
+ progname , optarg );
567
+ exit (1 );
568
+ }
569
+ endpos = ((uint64 ) hi ) << 32 | lo ;
570
+ break ;
547
571
case 'n' :
548
572
noloop = 1 ;
549
573
break ;
@@ -714,11 +738,11 @@ main(int argc, char **argv)
714
738
while (true)
715
739
{
716
740
StreamLog ();
717
- if (time_to_abort )
741
+ if (time_to_stop )
718
742
{
719
743
/*
720
- * We've been Ctrl-C'ed. That's not an error, so exit without an
721
- * errorcode .
744
+ * We've been Ctrl-C'ed or end of streaming position has been
745
+ * willingly reached, so exit without an error code .
722
746
*/
723
747
exit (0 );
724
748
}
0 commit comments