*** a/doc/src/sgml/high-availability.sgml
--- b/doc/src/sgml/high-availability.sgml
***************
*** 620,626 **** protocol to make nodes agree on a serializable transactional order.
      when <command>pg_ctl promote</> is run or a trigger file is found
      (<varname>trigger_file</>). Before failover,
      any WAL immediately available in the archive or in <filename>pg_xlog</> will be
!     restored, but no attempt is made to connect to the master.
     </para>
    </sect2>
  
--- 620,636 ----
      when <command>pg_ctl promote</> is run or a trigger file is found
      (<varname>trigger_file</>). Before failover,
      any WAL immediately available in the archive or in <filename>pg_xlog</> will be
!     restored by default, but no attempt is made to connect to the master.
!     If <literal>--immediate</> option is specified, <command>pg_ctl promote</>
!     makes recovery ignore any WAL that have not been replayed yet
!     and exit immediately. This promotion is faster but can cause data loss.
!     So it's useful if you want to switch the server to normal operation
!     as soon as possible at the expense of durability.
!     While recovery is being delayed (by a time-delayed standby) or paused,
!     you may find that subsequent WAL data can cause a disaster to happen
!     (for example, WAL data indicating an unexpected deletion of important
!     database). In this case, <literal>--immediate</> option can be used to
!     ignore such problematic WAL data.
     </para>
    </sect2>
  
*** a/doc/src/sgml/ref/pg_ctl-ref.sgml
--- b/doc/src/sgml/ref/pg_ctl-ref.sgml
***************
*** 93,98 **** PostgreSQL documentation
--- 93,99 ----
     <arg choice="plain"><option>promote</option></arg>
     <arg choice="opt"><option>-s</option></arg>
     <arg choice="opt"><option>-D</option> <replaceable>datadir</replaceable></arg>
+    <arg choice="opt"><option>--immediate</option></arg>
    </cmdsynopsis>
  
    <cmdsynopsis>
***************
*** 404,409 **** PostgreSQL documentation
--- 405,419 ----
       </varlistentry>
  
       <varlistentry>
+       <term><option>--immediate</option></term>
+       <listitem>
+        <para>
+         Exit recovery immediately in promote mode.
+        </para>
+       </listitem>
+      </varlistentry>
+ 
+      <varlistentry>
        <term><option>-?</></term>
        <term><option>--help</></term>
        <listitem>
*** a/src/backend/access/transam/xlog.c
--- b/src/backend/access/transam/xlog.c
***************
*** 74,79 **** extern uint32 bootstrap_data_checksum_version;
--- 74,80 ----
  #define RECOVERY_COMMAND_DONE	"recovery.done"
  #define PROMOTE_SIGNAL_FILE		"promote"
  #define FALLBACK_PROMOTE_SIGNAL_FILE "fallback_promote"
+ #define IMMEDIATE_PROMOTE_SIGNAL_FILE	"immediate_promote"
  
  
  /* User-settable parameters */
***************
*** 240,245 **** bool		StandbyMode = false;
--- 241,249 ----
  /* whether request for fast promotion has been made yet */
  static bool fast_promote = false;
  
+ /* whether request for immediate promotion has been made yet */
+ static bool immediate_promote = false;
+ 
  /*
   * if recoveryStopsBefore/After returns true, it saves information of the stop
   * point here
***************
*** 6761,6766 **** StartupXLOG(void)
--- 6765,6777 ----
  						recoveryPausesHere();
  				}
  
+ 				/*
+ 				 * In immediate promotion, we ignore WAL data that have not
+ 				 * been replayed yet and exit recovery immediately.
+ 				 */
+ 				if (immediate_promote)
+ 					break;
+ 
  				/* Setup error traceback support for ereport() */
  				errcallback.callback = rm_redo_error_callback;
  				errcallback.arg = (void *) record;
***************
*** 11299,11315 **** CheckForStandbyTrigger(void)
--- 11310,11341 ----
  		 * Startup process do the unlink. This allows Startup to know whether
  		 * it should create a full checkpoint before starting up (fallback
  		 * mode). Fast promotion takes precedence.
+ 		 *
+ 		 * Also the promote file allows Startup to know whether it should
+ 		 * exit recovery immediately without replaying the remaining WAL
+ 		 * data. Since immediate promotion has a risk of data loss, it's
+ 		 * treated as lowest-priority mode.
  		 */
  		if (stat(PROMOTE_SIGNAL_FILE, &stat_buf) == 0)
  		{
  			unlink(PROMOTE_SIGNAL_FILE);
  			unlink(FALLBACK_PROMOTE_SIGNAL_FILE);
+ 			unlink(IMMEDIATE_PROMOTE_SIGNAL_FILE);
  			fast_promote = true;
+ 			immediate_promote = false;
  		}
  		else if (stat(FALLBACK_PROMOTE_SIGNAL_FILE, &stat_buf) == 0)
  		{
  			unlink(FALLBACK_PROMOTE_SIGNAL_FILE);
+ 			unlink(IMMEDIATE_PROMOTE_SIGNAL_FILE);
  			fast_promote = false;
+ 			immediate_promote = false;
+ 		}
+ 		else if(stat(IMMEDIATE_PROMOTE_SIGNAL_FILE, &stat_buf) == 0)
+ 		{
+ 			unlink(IMMEDIATE_PROMOTE_SIGNAL_FILE);
+ 			fast_promote = true;
+ 			immediate_promote = true;
  		}
  
  		ereport(LOG, (errmsg("received promote request")));
***************
*** 11350,11356 **** CheckPromoteSignal(void)
  	struct stat stat_buf;
  
  	if (stat(PROMOTE_SIGNAL_FILE, &stat_buf) == 0 ||
! 		stat(FALLBACK_PROMOTE_SIGNAL_FILE, &stat_buf) == 0)
  		return true;
  
  	return false;
--- 11376,11383 ----
  	struct stat stat_buf;
  
  	if (stat(PROMOTE_SIGNAL_FILE, &stat_buf) == 0 ||
! 		stat(FALLBACK_PROMOTE_SIGNAL_FILE, &stat_buf) == 0 ||
! 		stat(IMMEDIATE_PROMOTE_SIGNAL_FILE, &stat_buf) == 0)
  		return true;
  
  	return false;
*** a/src/bin/pg_ctl/pg_ctl.c
--- b/src/bin/pg_ctl/pg_ctl.c
***************
*** 80,85 **** static bool wait_set = false;
--- 80,86 ----
  static int	wait_seconds = DEFAULT_WAIT;
  static bool silent_mode = false;
  static ShutdownMode shutdown_mode = SMART_MODE;
+ static int	immediate_promote = 0;
  static int	sig = SIGTERM;		/* default */
  static CtlCommand ctl_command = NO_COMMAND;
  static char *pg_data = NULL;
***************
*** 1165,1175 **** do_promote(void)
  	}
  
  	/*
! 	 * For 9.3 onwards, "fast" promotion is performed. Promotion with a full
! 	 * checkpoint is still possible by writing a file called
! 	 * "fallback_promote" instead of "promote"
  	 */
! 	snprintf(promote_file, MAXPGPATH, "%s/promote", pg_data);
  
  	if ((prmfile = fopen(promote_file, "w")) == NULL)
  	{
--- 1166,1182 ----
  	}
  
  	/*
! 	 * Create a promote file according to the specified mode.
! 	 *
! 	 * For 9.3 onwards, "fast" promotion is performed (i.e., end-of-recovery
! 	 * checkpoint is skipped) by default. Promotion with a full checkpoint
! 	 * is still possible by writing a file called "fallback_promote" instead
! 	 * of "promote" and "immediate_promote"
  	 */
! 	if (immediate_promote)
! 		snprintf(promote_file, MAXPGPATH, "%s/immediate_promote", pg_data);
! 	else
! 		snprintf(promote_file, MAXPGPATH, "%s/promote", pg_data);
  
  	if ((prmfile = fopen(promote_file, "w")) == NULL)
  	{
***************
*** 1872,1878 **** do_help(void)
  			 "                 [-o \"OPTIONS\"]\n"), progname);
  	printf(_("  %s reload  [-D DATADIR] [-s]\n"), progname);
  	printf(_("  %s status  [-D DATADIR]\n"), progname);
! 	printf(_("  %s promote [-D DATADIR] [-s]\n"), progname);
  	printf(_("  %s kill    SIGNALNAME PID\n"), progname);
  #if defined(WIN32) || defined(__CYGWIN__)
  	printf(_("  %s register   [-N SERVICENAME] [-U USERNAME] [-P PASSWORD] [-D DATADIR]\n"
--- 1879,1885 ----
  			 "                 [-o \"OPTIONS\"]\n"), progname);
  	printf(_("  %s reload  [-D DATADIR] [-s]\n"), progname);
  	printf(_("  %s status  [-D DATADIR]\n"), progname);
! 	printf(_("  %s promote [-D DATADIR] [-s] [--immediate]\n"), progname);
  	printf(_("  %s kill    SIGNALNAME PID\n"), progname);
  #if defined(WIN32) || defined(__CYGWIN__)
  	printf(_("  %s register   [-N SERVICENAME] [-U USERNAME] [-P PASSWORD] [-D DATADIR]\n"
***************
*** 1913,1918 **** do_help(void)
--- 1920,1928 ----
  	printf(_("  fast        quit directly, with proper shutdown\n"));
  	printf(_("  immediate   quit without complete shutdown; will lead to recovery on restart\n"));
  
+ 	printf(_("\nOptions for promote:\n"));
+ 	printf(_("      --immediate        exit recovery immediately; unreplayed logs are ignored\n"));
+ 
  	printf(_("\nAllowed signal names for kill:\n"));
  	printf("  ABRT HUP INT QUIT TERM USR1 USR2\n");
  
***************
*** 2085,2090 **** main(int argc, char **argv)
--- 2095,2101 ----
  		{"silent", no_argument, NULL, 's'},
  		{"timeout", required_argument, NULL, 't'},
  		{"core-files", no_argument, NULL, 'c'},
+ 		{"immediate", no_argument, &immediate_promote, 1},
  		{NULL, 0, NULL, 0}
  	};
  
***************
*** 2225,2230 **** main(int argc, char **argv)
--- 2236,2243 ----
  				case 'c':
  					allow_core_files = true;
  					break;
+ 			case 0:
+ 					break;
  				default:
  					/* getopt_long already issued a suitable error message */
  					do_advice();
