diff options
author | Alvaro Herrera <alvherre@alvh.no-ip.org> | 2019-10-16 14:51:23 +0200 |
---|---|---|
committer | Alvaro Herrera <alvherre@alvh.no-ip.org> | 2019-10-16 14:51:23 +0200 |
commit | 1cd5bc3ccf92a511b087629b2c914dffa9151fce (patch) | |
tree | 2afcb196f62f38362ff6407d05041ed2e40f70f3 | |
parent | a8e49ae0c38172a288f26ae1590069ecc4a721cd (diff) | |
download | postgresql-1cd5bc3ccf92a511b087629b2c914dffa9151fce.tar.gz postgresql-1cd5bc3ccf92a511b087629b2c914dffa9151fce.zip |
Fix crash when reporting CREATE INDEX progress
A race condition can make us try to dereference a NULL pointer to the
PGPROC struct of a process that's already finished. That results in
crashes during REINDEX CONCURRENTLY and CREATE INDEX CONCURRENTLY.
This was introduced in ab0dfc961b6a, so backpatch to pg12.
Reported by: Justin Pryzby
Reviewed-by: Michaƫl Paquier
Discussion: https://postgr.es/m/20191012004446.GT10470@telsasoft.com
-rw-r--r-- | src/backend/commands/indexcmds.c | 6 | ||||
-rw-r--r-- | src/backend/storage/lmgr/lmgr.c | 10 |
2 files changed, 8 insertions, 8 deletions
diff --git a/src/backend/commands/indexcmds.c b/src/backend/commands/indexcmds.c index a5282411310..646b209b2cb 100644 --- a/src/backend/commands/indexcmds.c +++ b/src/backend/commands/indexcmds.c @@ -384,12 +384,14 @@ WaitForOlderSnapshots(TransactionId limitXmin, bool progress) if (VirtualTransactionIdIsValid(old_snapshots[i])) { + /* If requested, publish who we're going to wait for. */ if (progress) { PGPROC *holder = BackendIdGetProc(old_snapshots[i].backendId); - pgstat_progress_update_param(PROGRESS_WAITFOR_CURRENT_PID, - holder->pid); + if (holder) + pgstat_progress_update_param(PROGRESS_WAITFOR_CURRENT_PID, + holder->pid); } VirtualXactLock(old_snapshots[i], true); } diff --git a/src/backend/storage/lmgr/lmgr.c b/src/backend/storage/lmgr/lmgr.c index f838b0f758a..889841f4cc5 100644 --- a/src/backend/storage/lmgr/lmgr.c +++ b/src/backend/storage/lmgr/lmgr.c @@ -900,16 +900,14 @@ WaitForLockersMultiple(List *locktags, LOCKMODE lockmode, bool progress) while (VirtualTransactionIdIsValid(*lockholders)) { - /* - * If requested, publish who we're going to wait for. This is not - * 100% accurate if they're already gone, but we don't care. - */ + /* If requested, publish who we're going to wait for. */ if (progress) { PGPROC *holder = BackendIdGetProc(lockholders->backendId); - pgstat_progress_update_param(PROGRESS_WAITFOR_CURRENT_PID, - holder->pid); + if (holder) + pgstat_progress_update_param(PROGRESS_WAITFOR_CURRENT_PID, + holder->pid); } VirtualXactLock(*lockholders, true); lockholders++; |