diff --git a/doc/src/sgml/func.sgml b/doc/src/sgml/func.sgml
index 3631922..cdab9db 100644
--- a/doc/src/sgml/func.sgml
+++ b/doc/src/sgml/func.sgml
@@ -18597,7 +18597,17 @@ postgres=# select pg_start_backup('label_goes_here');
     WAL to be archived.  This behavior is only useful for backup
     software which independently monitors WAL archiving. Otherwise, WAL
     required to make the backup consistent might be missing and make the backup
-    useless.
+    useless. If the second parameter <parameter>wait_for_archive</> is true and
+    the backup is taken on a standby, <function>pg_stop_backup</> waits for WAL
+    to archived when <varname>archive_mode</> is <literal>always</>.  Enforcing
+    manually a WAL segment swtich to happen with for example
+    <function>pg_switch_wal</> may be necessary if the primary has low activity
+    to allow the backup to complete. Using <varname>statement_timeout</> to
+    limit the amount of time to wait or switching <parameter>wait_for_archive</>
+    to <literal>false</> will control the wait time, thought all the WAL segments
+    necessary to recover into a consistent state from the backup taken may not be
+    archived at the time <function>pg_stop_backup</> returns its status to the
+    caller.
    </para>
 
    <para>
diff --git a/src/backend/access/transam/xlog.c b/src/backend/access/transam/xlog.c
index 5b6cec8..4a47a6c 100644
--- a/src/backend/access/transam/xlog.c
+++ b/src/backend/access/transam/xlog.c
@@ -10875,10 +10875,10 @@ do_pg_stop_backup(char *labelfile, bool waitforarchive, TimeLineID *stoptli_p)
 	 * however.
 	 *
 	 * We don't force a switch to new WAL file and wait for all the required
-	 * files to be archived. This is okay if we use the backup to start the
-	 * standby. But, if it's for an archive recovery, to ensure all the
-	 * required files are available, a user should wait for them to be
-	 * archived, or include them into the backup.
+	 * files to be archived if waitforarchive is false. This is okay if we use
+	 * the backup to start the standby. But, if it's for an archive recovery,
+	 * to ensure all the required files are available, a user should set
+	 * waitforarchive true and wait for them to be archived.
 	 *
 	 * We return the current minimum recovery point as the backup end
 	 * location. Note that it can be greater than the exact backup end
@@ -10886,10 +10886,7 @@ do_pg_stop_backup(char *labelfile, bool waitforarchive, TimeLineID *stoptli_p)
 	 * pg_control. This is harmless for current uses.
 	 *
 	 * XXX currently a backup history file is for informational and debug
-	 * purposes only. It's not essential for an online backup. Furthermore,
-	 * even if it's created, it will not be archived during recovery because
-	 * an archiver is not invoked. So it doesn't seem worthwhile to write a
-	 * backup history file during recovery.
+	 * purposes only. It's not essential for an online backup.
 	 */
 	if (backup_started_in_recovery)
 	{
@@ -10918,28 +10915,26 @@ do_pg_stop_backup(char *labelfile, bool waitforarchive, TimeLineID *stoptli_p)
 		stoppoint = ControlFile->minRecoveryPoint;
 		stoptli = ControlFile->minRecoveryPointTLI;
 		LWLockRelease(ControlFileLock);
-
-		if (stoptli_p)
-			*stoptli_p = stoptli;
-		return stoppoint;
 	}
+	else
+	{
+		/*
+		 * Write the backup-end xlog record
+		 */
+		XLogBeginInsert();
+		XLogRegisterData((char *) (&startpoint), sizeof(startpoint));
+		stoppoint = XLogInsert(RM_XLOG_ID, XLOG_BACKUP_END);
+		stoptli = ThisTimeLineID;
 
-	/*
-	 * Write the backup-end xlog record
-	 */
-	XLogBeginInsert();
-	XLogRegisterData((char *) (&startpoint), sizeof(startpoint));
-	stoppoint = XLogInsert(RM_XLOG_ID, XLOG_BACKUP_END);
-	stoptli = ThisTimeLineID;
-
-	/*
-	 * Force a switch to a new xlog segment file, so that the backup is valid
-	 * as soon as archiver moves out the current segment file.
-	 */
-	RequestXLogSwitch(false);
+		/*
+		 * Force a switch to a new xlog segment file, so that the backup is valid
+		 * as soon as archiver moves out the current segment file.
+		 */
+		RequestXLogSwitch(false);
+	}
 
 	XLByteToPrevSeg(stoppoint, _logSegNo);
-	XLogFileName(stopxlogfilename, ThisTimeLineID, _logSegNo);
+	XLogFileName(stopxlogfilename, stoptli, _logSegNo);
 
 	/* Use the log timezone here, not the session timezone */
 	stamp_time = (pg_time_t) time(NULL);
@@ -10951,7 +10946,7 @@ do_pg_stop_backup(char *labelfile, bool waitforarchive, TimeLineID *stoptli_p)
 	 * Write the backup history file
 	 */
 	XLByteToSeg(startpoint, _logSegNo);
-	BackupHistoryFilePath(histfilepath, ThisTimeLineID, _logSegNo,
+	BackupHistoryFilePath(histfilepath, stoptli, _logSegNo,
 						  (uint32) (startpoint % XLogSegSize));
 	fp = AllocateFile(histfilepath, "w");
 	if (!fp)
@@ -10979,6 +10974,9 @@ do_pg_stop_backup(char *labelfile, bool waitforarchive, TimeLineID *stoptli_p)
 	 */
 	CleanupBackupHistory();
 
+	if (stoptli_p)
+		*stoptli_p = stoptli;
+
 	/*
 	 * If archiving is enabled, wait for all the required WAL files to be
 	 * archived before returning. If archiving isn't enabled, the required WAL
@@ -11001,11 +10999,15 @@ do_pg_stop_backup(char *labelfile, bool waitforarchive, TimeLineID *stoptli_p)
 	 */
 	if (waitforarchive && XLogArchivingActive())
 	{
+		/* Don't wait if WAL archiving not enabled always in recovery */
+		if (backup_started_in_recovery && !XLogArchivingAlways())
+			return stoppoint;
+
 		XLByteToPrevSeg(stoppoint, _logSegNo);
-		XLogFileName(lastxlogfilename, ThisTimeLineID, _logSegNo);
+		XLogFileName(lastxlogfilename, stoptli, _logSegNo);
 
 		XLByteToSeg(startpoint, _logSegNo);
-		BackupHistoryFileName(histfilename, ThisTimeLineID, _logSegNo,
+		BackupHistoryFileName(histfilename, stoptli, _logSegNo,
 							  (uint32) (startpoint % XLogSegSize));
 
 		seconds_before_warning = 60;
@@ -11028,12 +11030,24 @@ do_pg_stop_backup(char *labelfile, bool waitforarchive, TimeLineID *stoptli_p)
 			if (++waits >= seconds_before_warning)
 			{
 				seconds_before_warning *= 2;	/* This wraps in >10 years... */
-				ereport(WARNING,
-						(errmsg("pg_stop_backup still waiting for all required WAL segments to be archived (%d seconds elapsed)",
-								waits),
-						 errhint("Check that your archive_command is executing properly.  "
-								 "pg_stop_backup can be canceled safely, "
-								 "but the database backup will not be usable without all the WAL segments.")));
+				if (!backup_started_in_recovery)
+					ereport(WARNING,
+							(errmsg("pg_stop_backup still waiting for all required WAL segments to be archived (%d seconds elapsed)",
+									waits),
+							 errhint("Check that your archive_command is executing properly.  "
+									 "pg_stop_backup can be canceled safely, "
+									 "but the database backup will not be usable without all the WAL segments.")));
+				else
+					ereport(WARNING,
+							(errmsg("pg_stop_backup still waiting for all required WAL segments to be archived (%d seconds elapsed)",
+									waits),
+							 errhint("Backup has been taken from a standby, check if the WAL segment "
+									 "needed for this backup have been completed, in which case a "
+									 "foreced segment switch may can be needed on the primary. "
+									 "If a segment swtich has already happend check that your "
+									 "archive_command is executing properly."
+									 "pg_stop_backup can be canceled safely, but the database backup "
+									 "will not be usable without all the WAL segments.")));
 			}
 		}
 
@@ -11047,8 +11061,6 @@ do_pg_stop_backup(char *labelfile, bool waitforarchive, TimeLineID *stoptli_p)
 	/*
 	 * We're done.  As a convenience, return the ending WAL location.
 	 */
-	if (stoptli_p)
-		*stoptli_p = stoptli;
 	return stoppoint;
 }
 
