Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Started by Ranier Vilelaover 4 years ago24 messages
#1Ranier Vilela
ranier.vf@gmail.com
1 attachment(s)

Hi,

With the recent changes at procarray.c, I take a look in.
msvc compiler, has some warnings about signed vs unsigned.

So.

1. Size_t is weird, because all types are int.
2. Wouldn't it be better to initialize static variables?
3. There are some shadowing parameters.
4. Possible loop beyond numProcs?

- for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+ for (int pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)

I think no functional behavior changed.
Patch attached.

best regards,
Ranier Vilela

Attachments:

reduce_unmatechs_types_procarray.patchapplication/octet-stream; name=reduce_unmatechs_types_procarray.patchDownload
diff --git a/src/backend/storage/ipc/procarray.c b/src/backend/storage/ipc/procarray.c
index 085bd1e407..7ac0aa588f 100644
--- a/src/backend/storage/ipc/procarray.c
+++ b/src/backend/storage/ipc/procarray.c
@@ -263,7 +263,7 @@ static TransactionId latestObservedXid = InvalidTransactionId;
  * the highest xid that might still be running that we don't have in
  * KnownAssignedXids.
  */
-static TransactionId standbySnapshotPendingXmin;
+static TransactionId standbySnapshotPendingXmin = InvalidTransactionId;
 
 /*
  * State for visibility checks on different types of relations. See struct
@@ -280,7 +280,7 @@ static GlobalVisState GlobalVisTempRels;
  * recomputed, or InvalidTransactionId if it has not. Used to limit how many
  * times accurate horizons are recomputed. See GlobalVisTestShouldUpdate().
  */
-static TransactionId ComputeXidHorizonsResultLastXmin;
+static TransactionId ComputeXidHorizonsResultLastXmin = InvalidTransactionId;
 
 #ifdef XIDCACHE_DEBUG
 
@@ -703,7 +703,7 @@ ProcArrayEndTransaction(PGPROC *proc, TransactionId latestXid)
 static inline void
 ProcArrayEndTransactionInternal(PGPROC *proc, TransactionId latestXid)
 {
-	size_t		pgxactoff = proc->pgxactoff;
+	int		pgxactoff = proc->pgxactoff;
 
 	/*
 	 * Note: we need exclusive lock here because we're going to change other
@@ -829,12 +829,12 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	/* Walk the list and clear all XIDs. */
 	while (nextidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[nextidx];
+		PGPROC	   *nextproc = &allProcs[nextidx];
 
-		ProcArrayEndTransactionInternal(proc, proc->procArrayGroupMemberXid);
+		ProcArrayEndTransactionInternal(nextproc, nextproc->procArrayGroupMemberXid);
 
 		/* Move to next proc in list. */
-		nextidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
+		nextidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
 	}
 
 	/* We're done with the lock now. */
@@ -849,18 +849,18 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	 */
 	while (wakeidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[wakeidx];
+		PGPROC	   *nextproc = &allProcs[wakeidx];
 
-		wakeidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
-		pg_atomic_write_u32(&proc->procArrayGroupNext, INVALID_PGPROCNO);
+		wakeidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
+		pg_atomic_write_u32(&nextproc->procArrayGroupNext, INVALID_PGPROCNO);
 
 		/* ensure all previous writes are visible before follower continues. */
 		pg_write_barrier();
 
-		proc->procArrayGroupMember = false;
+		nextproc->procArrayGroupMember = false;
 
-		if (proc != MyProc)
-			PGSemaphoreUnlock(proc->sem);
+		if (nextproc != MyProc)
+			PGSemaphoreUnlock(nextproc->sem);
 	}
 }
 
@@ -875,7 +875,7 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 void
 ProcArrayClearTransaction(PGPROC *proc)
 {
-	size_t		pgxactoff;
+	int		pgxactoff;
 
 	/*
 	 * Currently we need to lock ProcArrayLock exclusively here, as we
@@ -1355,7 +1355,7 @@ TransactionIdIsInProgress(TransactionId xid)
 	TransactionId topxid;
 	TransactionId latestCompletedXid;
 	int			mypgxactoff;
-	size_t		numProcs;
+	int			numProcs;
 	int			j;
 
 	/*
@@ -1432,7 +1432,7 @@ TransactionIdIsInProgress(TransactionId xid)
 	/* No shortcuts, gotta grovel through the array */
 	mypgxactoff = MyProc->pgxactoff;
 	numProcs = arrayP->numProcs;
-	for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+	for (int pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
 	{
 		int			pgprocno;
 		PGPROC	   *proc;
@@ -2166,7 +2166,7 @@ GetSnapshotData(Snapshot snapshot)
 	TransactionId *other_xids = ProcGlobal->xids;
 	TransactionId xmin;
 	TransactionId xmax;
-	size_t		count = 0;
+	TransactionId count = 0;
 	int			subcount = 0;
 	bool		suboverflowed = false;
 	FullTransactionId latest_completed;
@@ -2248,7 +2248,7 @@ GetSnapshotData(Snapshot snapshot)
 
 	if (!snapshot->takenDuringRecovery)
 	{
-		size_t		numProcs = arrayP->numProcs;
+		int			numProcs = arrayP->numProcs;
 		TransactionId *xip = snapshot->xip;
 		int		   *pgprocnos = arrayP->pgprocnos;
 		XidCacheStatus *subxidStates = ProcGlobal->subxidStates;
@@ -2258,7 +2258,7 @@ GetSnapshotData(Snapshot snapshot)
 		 * First collect set of pgxactoff/xids that need to be included in the
 		 * snapshot.
 		 */
-		for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+		for (int pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
 		{
 			/* Fetch xid just once - see GetNewTransactionId */
 			TransactionId xid = UINT32_ACCESS_ONCE(other_xids[pgxactoff]);
#2Andres Freund
andres@anarazel.de
In reply to: Ranier Vilela (#1)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Hi,

On 2021-06-12 10:55:22 -0300, Ranier Vilela wrote:

With the recent changes at procarray.c, I take a look in.
msvc compiler, has some warnings about signed vs unsigned.

1. Size_t is weird, because all types are int.

Not sure why I ended up using size_t here. There are cases where using a
natively sized integer can lead to better code being generated, so I'd
want to see some evaluation of the code generation effects.

2. Wouldn't it be better to initialize static variables?

No, explicit initialization needs additional space in the binary, and
static variables are always zero initialized.

3. There are some shadowing parameters.

Hm, yea, that's not great. Those are from

commit 0e141c0fbb211bdd23783afa731e3eef95c9ad7a
Author: Robert Haas <rhaas@postgresql.org>
Date: 2015-08-06 11:52:51 -0400

Reduce ProcArrayLock contention by removing backends in batches.

Amit, Robert, I assume you don't mind changing this?

4. Possible loop beyond numProcs?

What are you referring to here?

Greetings,

Andres Freund

#3Ranier Vilela
ranier.vf@gmail.com
In reply to: Andres Freund (#2)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Hi Andres, thanks for taking a look.

Em sáb., 12 de jun. de 2021 às 16:27, Andres Freund <andres@anarazel.de>
escreveu:

Hi,

On 2021-06-12 10:55:22 -0300, Ranier Vilela wrote:

With the recent changes at procarray.c, I take a look in.
msvc compiler, has some warnings about signed vs unsigned.

1. Size_t is weird, because all types are int.

Not sure why I ended up using size_t here. There are cases where using a
natively sized integer can lead to better code being generated, so I'd
want to see some evaluation of the code generation effects.

Yes, sure.

2. Wouldn't it be better to initialize static variables?

No, explicit initialization needs additional space in the binary, and
static variables are always zero initialized.

Yes, I missed this part.
But I was worried about this line:

/* hasn't been updated yet */
if (!TransactionIdIsValid(ComputeXidHorizonsResultLastXmin))

The first run with ComputeXidHorizonsResultLastXmin = 0, is ok?

3. There are some shadowing parameters.

Hm, yea, that's not great. Those are from

commit 0e141c0fbb211bdd23783afa731e3eef95c9ad7a
Author: Robert Haas <rhaas@postgresql.org>
Date: 2015-08-06 11:52:51 -0400

Reduce ProcArrayLock contention by removing backends in batches.

Amit, Robert, I assume you don't mind changing this?

4. Possible loop beyond numProcs?

What are you referring to here?

My mistake.

best regards,
Ranier Vilela

#4Ranier Vilela
ranier.vf@gmail.com
In reply to: Ranier Vilela (#3)
1 attachment(s)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em dom., 13 de jun. de 2021 às 09:43, Ranier Vilela <ranier.vf@gmail.com>
escreveu:

Hi Andres, thanks for taking a look.

Em sáb., 12 de jun. de 2021 às 16:27, Andres Freund <andres@anarazel.de>
escreveu:

Hi,

On 2021-06-12 10:55:22 -0300, Ranier Vilela wrote:

With the recent changes at procarray.c, I take a look in.
msvc compiler, has some warnings about signed vs unsigned.

1. Size_t is weird, because all types are int.

Not sure why I ended up using size_t here. There are cases where using a
natively sized integer can lead to better code being generated, so I'd
want to see some evaluation of the code generation effects.

Yes, sure.

I'm a little confused by the msvc compiler, but here's the difference in
code generation.
Apart from the noise caused by unnecessary changes regarding the names.

Microsoft (R) C/C++ Optimizing Compiler Versão 19.28.29915 para x64

diff attached.

regards,
Ranier Vilela

Attachments:

procarray_asm.diffapplication/octet-stream; name=procarray_asm.diffDownload
--- procarray_b.asm	2021-06-13 21:59:19.572424200 -0300
+++ procarray.asm	2021-06-13 22:11:15.102819700 -0300
@@ -277,21 +277,21 @@
 $pdata$ExpireOldKnownAssignedTransactionIds DD imagerel $LN4
 	DD	imagerel $LN4+60
 	DD	imagerel $unwind$ExpireOldKnownAssignedTransactionIds
-$pdata$GetSnapshotData DD imagerel $LN138
-	DD	imagerel $LN138+432
+$pdata$GetSnapshotData DD imagerel $LN141
+	DD	imagerel $LN141+455
 	DD	imagerel $unwind$GetSnapshotData
-$pdata$0$GetSnapshotData DD imagerel $LN138+432
-	DD	imagerel $LN138+437
+$pdata$0$GetSnapshotData DD imagerel $LN141+455
+	DD	imagerel $LN141+460
 	DD	imagerel $chain$0$GetSnapshotData
-$pdata$2$GetSnapshotData DD imagerel $LN138+437
-	DD	imagerel $LN138+1120
+$pdata$1$GetSnapshotData DD imagerel $LN141+460
+	DD	imagerel $LN141+1118
+	DD	imagerel $chain$1$GetSnapshotData
+$pdata$2$GetSnapshotData DD imagerel $LN141+1118
+	DD	imagerel $LN141+1504
 	DD	imagerel $chain$2$GetSnapshotData
-$pdata$3$GetSnapshotData DD imagerel $LN138+1120
-	DD	imagerel $LN138+1514
+$pdata$3$GetSnapshotData DD imagerel $LN141+1504
+	DD	imagerel $LN141+1575
 	DD	imagerel $chain$3$GetSnapshotData
-$pdata$4$GetSnapshotData DD imagerel $LN138+1514
-	DD	imagerel $LN138+1571
-	DD	imagerel $chain$4$GetSnapshotData
 $pdata$ProcArrayInstallImportedXmin DD imagerel $LN22
 	DD	imagerel $LN22+94
 	DD	imagerel $unwind$ProcArrayInstallImportedXmin
@@ -1273,28 +1273,28 @@
 	DD	030023206H
 $unwind$ExpireOldKnownAssignedTransactionIds DD 020601H
 	DD	030023206H
-$unwind$GetSnapshotData DD 060f01H
-	DD	0f008f20fH
-	DD	07004d006H
-	DD	030026003H
+$unwind$GetSnapshotData DD 070e01H
+	DD	0e00ae20eH
+	DD	0c006d008H
+	DD	060037004H
+	DD	03002H
 $chain$0$GetSnapshotData DD 020521H
-	DD	0f5405H
-	DD	imagerel $LN138
-	DD	imagerel $LN138+432
+	DD	0e5405H
+	DD	imagerel $LN141
+	DD	imagerel $LN141+455
 	DD	imagerel $unwind$GetSnapshotData
-$chain$2$GetSnapshotData DD 040a21H
-	DD	0de40aH
-	DD	0ec405H
-	DD	imagerel $LN138+432
-	DD	imagerel $LN138+437
+$chain$1$GetSnapshotData DD 020521H
+	DD	0df405H
+	DD	imagerel $LN141+455
+	DD	imagerel $LN141+460
 	DD	imagerel $chain$0$GetSnapshotData
-$chain$3$GetSnapshotData DD 021H
-	DD	imagerel $LN138+432
-	DD	imagerel $LN138+437
+$chain$2$GetSnapshotData DD 021H
+	DD	imagerel $LN141+455
+	DD	imagerel $LN141+460
 	DD	imagerel $chain$0$GetSnapshotData
-$chain$4$GetSnapshotData DD 021H
-	DD	imagerel $LN138
-	DD	imagerel $LN138+432
+$chain$3$GetSnapshotData DD 021H
+	DD	imagerel $LN141
+	DD	imagerel $LN141+455
 	DD	imagerel $unwind$GetSnapshotData
 $unwind$ProcArrayInstallImportedXmin DD 084e01H
 	DD	08344eH
@@ -6005,9 +6005,9 @@
 ; Function compile flags: /Ogtpy
 _TEXT	SEGMENT
 xid$ = 96
-tv803 = 104
-xtmp$1 = 104
-tv793 = 112
+$T1 = 104
+xtmp$2 = 104
+tv800 = 112
 TransactionIdIsInProgress PROC
 ; File C:\dll\postgres\postgres\src\backend\storage\ipc\procarray.c
 ; Line 1349
@@ -6104,20 +6104,19 @@
 	mov	al, 1
 	jmp	$LN1@Transactio
 $LN21@Transactio:
-; Line 1434
-	movsxd	r12, DWORD PTR [rbp]
 ; Line 1435
-	mov	rdi, rsi
-	mov	rax, QWORD PTR MyProc
+	movsxd	r12, DWORD PTR [rbp]
 	test	r12, r12
-	je	$LN90@Transactio
-	movsxd	rax, DWORD PTR [rax+80]
+	jle	$LN90@Transactio
+; Line 1443
+	mov	rax, QWORD PTR MyProc
 	lea	rcx, QWORD PTR [rbp+40]
-	mov	QWORD PTR tv803[rsp], rax
+	mov	rdi, rsi
+	mov	QWORD PTR tv800[rsp], rcx
 	mov	r14, rsi
-	mov	QWORD PTR tv793[rsp], rcx
+	movsxd	rax, DWORD PTR [rax+80]
+	mov	QWORD PTR $T1[rsp], rax
 $LL7@Transactio:
-; Line 1443
 	cmp	rdi, rax
 	je	$LN5@Transactio
 ; Line 1447
@@ -6140,7 +6139,7 @@
 ; Line 1473
 	lock or	DWORD PTR [rsp], esi
 ; Line 1475
-	mov	rax, QWORD PTR tv793[rsp]
+	mov	rax, QWORD PTR tv800[rsp]
 	movsxd	rax, DWORD PTR [rax+rdi*4]
 	imul	r8, rax, 896				; 00000380H
 	add	r8, QWORD PTR allProcs
@@ -6171,11 +6170,11 @@
 	add	r14, 4
 $LN93@Transactio:
 ; Line 1435
-	mov	rax, QWORD PTR tv803[rsp]
+	mov	rax, QWORD PTR $T1[rsp]
 $LN5@Transactio:
 	inc	rdi
 	cmp	rdi, r12
-	jb	$LL7@Transactio
+	jl	$LL7@Transactio
 $LN90@Transactio:
 ; Line 1504
 	call	RecoveryInProgress
@@ -6253,9 +6252,9 @@
 	je	SHORT $LN30@Transactio
 ; Line 4951
 	mov	rcx, QWORD PTR ?xids@?1??TransactionIdIsInProgress@@9@9
-	lea	rdx, QWORD PTR xtmp$1[rsp]
+	lea	rdx, QWORD PTR xtmp$2[rsp]
 	mov	r8d, ebx
-	mov	DWORD PTR xtmp$1[rsp], esi
+	mov	DWORD PTR xtmp$2[rsp], esi
 	call	KnownAssignedXidsGetAndSetXmin
 	mov	r15d, eax
 $LN30@Transactio:
@@ -6671,47 +6670,48 @@
 _TEXT	ENDS
 ; Function compile flags: /Ogtpy
 _TEXT	SEGMENT
-oldestxid$1$ = 32
-myxid$1$ = 36
-count$1$ = 40
-tv1165 = 48
-allStatusFlags$1$ = 56
-xip$1$ = 64
-numProcs$1$ = 72
+$T1 = 32
+xmax$2$ = 40
+oldestxid$1$ = 44
+myxid$1$ = 48
+other_xids$1$ = 56
+tv1217 = 64
+allStatusFlags$1$ = 72
 latest_completed$1$ = 80
 curXactCompletionCount$1$ = 88
 xmin$ = 176
 snapshot$ = 176
-subcount$1$ = 184
-tv1269 = 192
-xmax$2$ = 200
+tv1309 = 184
+subcount$1$ = 192
+count$1$ = 200
 GetSnapshotData PROC
 ; File C:\dll\postgres\postgres\src\backend\storage\ipc\procarray.c
 ; Line 2164
-$LN138:
+$LN141:
 	push	rbx
 	push	rsi
 	push	rdi
+	push	r12
 	push	r13
-	push	r15
-	sub	rsp, 128				; 00000080H
+	push	r14
+	sub	rsp, 120				; 00000078H
 ; Line 2166
 	mov	rax, QWORD PTR ProcGlobal
 ; Line 2169
 	xor	edi, edi
-	mov	r15, QWORD PTR procArray
+	mov	rbx, QWORD PTR procArray
 ; Line 2171
-	xor	bl, bl
+	xor	r13b, r13b
 	mov	rsi, rcx
-	mov	QWORD PTR count$1$[rsp], rdi
+	mov	DWORD PTR count$1$[rsp], edi
 	mov	DWORD PTR subcount$1$[rsp], edi
-	mov	r13, QWORD PTR [rax+8]
-	mov	DWORD PTR tv1269[rsp], ebx
+	mov	r14, QWORD PTR [rax+8]
+	mov	DWORD PTR tv1309[rsp], r13d
 ; Line 2194
 	cmp	QWORD PTR [rcx+16], rdi
 	jne	$LN6@GetSnapsho
 ; Line 2200
-	movsxd	rcx, DWORD PTR [r15+4]
+	movsxd	rcx, DWORD PTR [rbx+4]
 	shl	rcx, 2
 	call	QWORD PTR __imp_malloc
 	mov	QWORD PTR [rsi+16], rax
@@ -6762,8 +6762,9 @@
 $LN6@GetSnapsho:
 ; Line 2219
 	mov	rcx, QWORD PTR MainLWLockArray
-	mov	edx, 1
+	mov	r12d, 1
 	add	rcx, 512				; 00000200H
+	mov	edx, r12d
 	call	LWLockAcquire
 ; Line 2086
 	mov	rax, QWORD PTR [rsi+112]
@@ -6772,7 +6773,7 @@
 	je	$LN21@GetSnapsho
 ; Line 2090
 	cmp	QWORD PTR [rcx+56], rax
-	jne	SHORT $LN21@GetSnapsho
+	jne	$LN21@GetSnapsho
 ; Line 2113
 	mov	rcx, QWORD PTR MyProc
 	cmp	DWORD PTR [rcx+68], edi
@@ -6821,39 +6822,46 @@
 	mov	rcx, QWORD PTR MainLWLockArray
 	add	rcx, 512				; 00000200H
 	call	LWLockRelease
-; Line 2224
-	jmp	$LN114@GetSnapsho
+; Line 2513
+	mov	rax, rsi
+	add	rsp, 120				; 00000078H
+	pop	r14
+	pop	r13
+	pop	r12
+	pop	rdi
+	pop	rsi
+	pop	rbx
+	ret	0
 $LN21@GetSnapsho:
-; Line 2228
-	mov	rax, QWORD PTR MyProc
+; Line 2227
 	mov	rdi, QWORD PTR [rcx+48]
-	mov	QWORD PTR [rsp+120], rbp
-	mov	QWORD PTR [rsp+112], r12
-	mov	QWORD PTR [rsp+104], r14
 ; Line 2229
-	movsxd	r14, DWORD PTR [rax+80]
+	mov	rax, QWORD PTR MyProc
+	mov	QWORD PTR [rsp+112], rbp
+	mov	QWORD PTR [rsp+104], r15
 ; Line 2233
-	lea	r12d, DWORD PTR [rdi+1]
+	lea	r15d, DWORD PTR [rdi+1]
+	mov	QWORD PTR latest_completed$1$[rsp], rdi
+	movsxd	rax, DWORD PTR [rax+80]
+	mov	QWORD PTR tv1217[rsp], rax
+	mov	edx, DWORD PTR [r14+rax*4]
 	mov	eax, DWORD PTR [rcx+16]
 	mov	DWORD PTR oldestxid$1$[rsp], eax
 	mov	rax, QWORD PTR [rcx+56]
-	mov	edx, DWORD PTR [r13+r14*4]
 	mov	QWORD PTR curXactCompletionCount$1$[rsp], rax
 ; Line 2237
 	mov	eax, 3
-	cmp	r12d, eax
-	mov	QWORD PTR latest_completed$1$[rsp], rdi
-	mov	QWORD PTR tv1165[rsp], r14
-	cmovb	r12d, eax
+	cmp	r15d, eax
 	mov	DWORD PTR myxid$1$[rsp], edx
-	mov	DWORD PTR xmax$2$[rsp], r12d
+	cmovb	r15d, eax
+	mov	DWORD PTR xmax$2$[rsp], r15d
 ; Line 2241
-	mov	ebp, r12d
-	mov	DWORD PTR xmin$[rsp], r12d
+	mov	ebp, r15d
+	mov	DWORD PTR xmin$[rsp], r15d
 ; Line 2244
 	cmp	edx, eax
 	jb	SHORT $LN23@GetSnapsho
-	cmp	edx, r12d
+	cmp	edx, r15d
 	cmovs	ebp, edx
 	mov	DWORD PTR xmin$[rsp], ebp
 $LN23@GetSnapsho:
@@ -6863,60 +6871,59 @@
 ; Line 2249
 	test	al, al
 	jne	$LN24@GetSnapsho
-; Line 2251
-	movsxd	rcx, DWORD PTR [r15]
-; Line 2261
-	xor	ebx, ebx
+; Line 2254
 	mov	rax, QWORD PTR ProcGlobal
-	add	r15, 40					; 00000028H
-	mov	r8, QWORD PTR [rsi+16]
-	mov	QWORD PTR numProcs$1$[rsp], rcx
-	mov	QWORD PTR xip$1$[rsp], r8
+	lea	r15, QWORD PTR [rbx+40]
+	mov	r12, QWORD PTR [rsi+16]
+; Line 2255
 	mov	rdx, QWORD PTR [rax+24]
-	mov	r12, QWORD PTR [rax+16]
+	mov	r13, QWORD PTR [rax+16]
+; Line 2261
+	movsxd	rax, DWORD PTR [rbx]
 	mov	QWORD PTR allStatusFlags$1$[rsp], rdx
-	test	rcx, rcx
-	je	$LN134@GetSnapsho
-; Line 2251
-	mov	edi, DWORD PTR tv1269[rsp]
-	sub	r13, r15
-	npad	8
+	mov	QWORD PTR $T1[rsp], rax
+	test	rax, rax
+	jle	$LN137@GetSnapsho
+; Line 2281
+	mov	rdi, QWORD PTR tv1217[rsp]
+	xor	ebx, ebx
+	sub	r14, r15
+	mov	QWORD PTR other_xids$1$[rsp], r14
 $LL13@GetSnapsho:
-; Line 2264
-	mov	ecx, DWORD PTR [r15+r13]
 ; Line 2273
+	mov	ecx, DWORD PTR [r14+r15]
 	test	ecx, ecx
 	je	$LN132@GetSnapsho
 ; Line 2281
-	cmp	rbx, r14
+	cmp	rbx, rdi
 	je	$LN132@GetSnapsho
 ; Line 2297
 	cmp	ecx, DWORD PTR xmax$2$[rsp]
-	jns	$LN132@GetSnapsho
+	jns	$LN136@GetSnapsho
 ; Line 2305
 	test	BYTE PTR [rbx+rdx], 18
-	jne	$LN132@GetSnapsho
-; Line 2312
-	mov	rax, QWORD PTR count$1$[rsp]
+	jne	$LN136@GetSnapsho
+; Line 2308
 	mov	ebp, DWORD PTR xmin$[rsp]
 	cmp	ecx, ebp
+; Line 2312
+	mov	DWORD PTR [r12], ecx
 	cmovs	ebp, ecx
-	mov	DWORD PTR [r8+rax*4], ecx
-	inc	rax
+	inc	DWORD PTR count$1$[rsp]
+	add	r12, 4
 	mov	DWORD PTR xmin$[rsp], ebp
-	mov	QWORD PTR count$1$[rsp], rax
 ; Line 2329
-	test	dil, dil
-	jne	SHORT $LN11@GetSnapsho
+	cmp	BYTE PTR tv1309[rsp], 0
+	jne	SHORT $LN134@GetSnapsho
 ; Line 2332
-	cmp	BYTE PTR [r12+rbx*2+1], dil
+	cmp	BYTE PTR [r13+rbx*2+1], 0
 	je	SHORT $LN32@GetSnapsho
 ; Line 2333
-	mov	dil, 1
-	jmp	SHORT $LN11@GetSnapsho
+	mov	BYTE PTR tv1309[rsp], 1
+	jmp	SHORT $LN134@GetSnapsho
 $LN32@GetSnapsho:
 ; Line 2336
-	movzx	r14d, BYTE PTR [r12+rbx*2]
+	movzx	r14d, BYTE PTR [r13+rbx*2]
 ; Line 2338
 	test	r14d, r14d
 	je	SHORT $LN133@GetSnapsho
@@ -6937,51 +6944,24 @@
 	mov	rdx, QWORD PTR allStatusFlags$1$[rsp]
 ; Line 2348
 	add	ebp, r14d
-	mov	r8, QWORD PTR xip$1$[rsp]
 	mov	DWORD PTR subcount$1$[rsp], ebp
 	mov	ebp, DWORD PTR xmin$[rsp]
 $LN133@GetSnapsho:
 ; Line 2261
-	mov	r14, QWORD PTR tv1165[rsp]
+	mov	r14, QWORD PTR other_xids$1$[rsp]
+$LN134@GetSnapsho:
+	mov	rax, QWORD PTR $T1[rsp]
 $LN11@GetSnapsho:
 	inc	rbx
 	add	r15, 4
-	cmp	rbx, QWORD PTR numProcs$1$[rsp]
-	jb	$LL13@GetSnapsho
+	cmp	rbx, rax
+	jl	$LL13@GetSnapsho
 ; Line 2353
-	mov	r13d, DWORD PTR subcount$1$[rsp]
-	mov	DWORD PTR tv1269[rsp], edi
 	mov	rdi, QWORD PTR latest_completed$1$[rsp]
-	jmp	SHORT $LN35@GetSnapsho
-$LN132@GetSnapsho:
-; Line 2273
-	mov	ebp, DWORD PTR xmin$[rsp]
-; Line 2338
-	jmp	SHORT $LN11@GetSnapsho
-$LN24@GetSnapsho:
-; Line 2385
-	mov	rcx, QWORD PTR [rsi+32]
-	lea	rdx, QWORD PTR xmin$[rsp]
-	mov	r8d, r12d
-	call	KnownAssignedXidsGetAndSetXmin
-; Line 2388
-	mov	rcx, QWORD PTR procArray
-	mov	r13d, eax
-	mov	ebp, DWORD PTR xmin$[rsp]
-	mov	edx, DWORD PTR [rcx+28]
-	mov	ecx, ebp
-	call	TransactionIdPrecedesOrEquals
-	test	al, al
-	movzx	ebx, bl
-	mov	eax, 1
-	cmovne	ebx, eax
-	mov	DWORD PTR tv1269[rsp], ebx
-	jmp	SHORT $LN35@GetSnapsho
-$LN134@GetSnapsho:
-; Line 2261
-	mov	r13d, ebx
-$LN35@GetSnapsho:
+$LN137@GetSnapsho:
 ; Line 2398
+	mov	r13d, DWORD PTR tv1309[rsp]
+$LN35@GetSnapsho:
 	mov	rcx, QWORD PTR procArray
 ; Line 2401
 	mov	rax, QWORD PTR MyProc
@@ -7012,7 +6992,7 @@
 ; Line 321
 	cmp	ecx, 3
 	jae	SHORT $LN57@GetSnapsho
-	npad	2
+	npad	3
 $LL56@GetSnapsho:
 ; Line 322
 	dec	ecx
@@ -7042,7 +7022,33 @@
 ; Line 335
 	mov	r15d, r12d
 	jmp	SHORT $LN67@GetSnapsho
+$LN136@GetSnapsho:
+; File C:\dll\postgres\postgres\src\backend\storage\ipc\procarray.c
+; Line 2273
+	mov	rax, QWORD PTR $T1[rsp]
+$LN132@GetSnapsho:
+	mov	ebp, DWORD PTR xmin$[rsp]
+; Line 2338
+	jmp	$LN11@GetSnapsho
+$LN24@GetSnapsho:
+; Line 2385
+	mov	rcx, QWORD PTR [rsi+32]
+	lea	rdx, QWORD PTR xmin$[rsp]
+	mov	r8d, r15d
+	call	KnownAssignedXidsGetAndSetXmin
+; Line 2388
+	mov	rcx, QWORD PTR procArray
+	mov	ebp, DWORD PTR xmin$[rsp]
+	mov	DWORD PTR subcount$1$[rsp], eax
+	mov	edx, DWORD PTR [rcx+28]
+	mov	ecx, ebp
+	call	TransactionIdPrecedesOrEquals
+	test	al, al
+	movzx	r13d, r13b
+	cmovne	r13d, r12d
+	jmp	$LN35@GetSnapsho
 $LN66@GetSnapsho:
+; File C:\dll\postgres\postgres\src\include\access\transam.h
 ; Line 337
 	mov	edx, r14d
 	mov	ecx, r12d
@@ -7052,14 +7058,13 @@
 $LN67@GetSnapsho:
 ; File C:\dll\postgres\postgres\src\backend\storage\ipc\procarray.c
 ; Line 4251
-	mov	r12, QWORD PTR [rsp+112]
-	sub	r14d, edi
 	sub	r15d, edi
-	movsxd	rcx, r14d
-	mov	r14, QWORD PTR [rsp+104]
-	add	rcx, rdi
+	sub	r14d, edi
 	movsxd	rax, r15d
+	mov	r15, QWORD PTR [rsp+104]
 	add	rax, rdi
+	movsxd	rcx, r14d
+	add	rcx, rdi
 ; Line 2443
 	test	eax, eax
 ; File C:\dll\postgres\postgres\src\include\access\transam.h
@@ -7076,13 +7081,13 @@
 	mov	rdx, QWORD PTR GlobalVisSharedRels
 	mov	QWORD PTR GlobalVisSharedRels, rax
 	test	edx, edx
-	je	SHORT $LN135@GetSnapsho
+	je	SHORT $LN138@GetSnapsho
 ; Line 363
 	cmp	rax, rdx
-	ja	SHORT $LN135@GetSnapsho
+	ja	SHORT $LN138@GetSnapsho
 ; Line 365
 	mov	QWORD PTR GlobalVisSharedRels, rdx
-$LN135@GetSnapsho:
+$LN138@GetSnapsho:
 ; Line 360
 	mov	rdx, QWORD PTR GlobalVisCatalogRels
 	mov	r8d, ecx
@@ -7124,7 +7129,7 @@
 	cdqe
 	add	rax, rdi
 ; Line 2461
-	jmp	SHORT $LN136@GetSnapsho
+	jmp	SHORT $LN139@GetSnapsho
 $LN37@GetSnapsho:
 ; File C:\dll\postgres\postgres\src\include\access\transam.h
 ; Line 130
@@ -7136,13 +7141,12 @@
 ; Line 136
 	cmp	eax, 3
 	jae	SHORT $LN92@GetSnapsho
-	npad	7
 $LL91@GetSnapsho:
 ; Line 137
 	inc	rax
 	cmp	eax, 3
 	jb	SHORT $LL91@GetSnapsho
-$LN136@GetSnapsho:
+$LN139@GetSnapsho:
 ; Line 357
 	mov	QWORD PTR GlobalVisTempRels, rax
 $LN92@GetSnapsho:
@@ -7213,17 +7217,17 @@
 	mov	QWORD PTR GlobalVisDataRels+8, rbx
 	mov	DWORD PTR RecentXmin, ebp
 	mov	DWORD PTR [rsi+8], eax
-	mov	rax, QWORD PTR count$1$[rsp]
+	mov	eax, DWORD PTR count$1$[rsp]
 	mov	DWORD PTR [rsi+24], eax
-	mov	eax, DWORD PTR tv1269[rsp]
-	mov	BYTE PTR [rsi+44], al
+	mov	eax, DWORD PTR subcount$1$[rsp]
+	mov	DWORD PTR [rsi+40], eax
 	mov	rax, QWORD PTR curXactCompletionCount$1$[rsp]
 	mov	QWORD PTR [rsi+112], rax
 	mov	DWORD PTR [rsi+4], ebp
-	mov	DWORD PTR [rsi+40], r13d
+	mov	BYTE PTR [rsi+44], r13b
 	call	GetCurrentCommandId
 ; Line 2508
-	mov	rbp, QWORD PTR [rsp+120]
+	mov	rbp, QWORD PTR [rsp+112]
 	mov	DWORD PTR [rsi+48], eax
 	xor	eax, eax
 	mov	QWORD PTR [rsi+64], rax
@@ -7238,8 +7242,16 @@
 	mov	QWORD PTR [rsi+104], rax
 ; Line 2055
 	mov	QWORD PTR [rsi+96], rax
-; Line 2056
-	jmp	SHORT $LN114@GetSnapsho
+; Line 2513
+	mov	rax, rsi
+	add	rsp, 120				; 00000078H
+	pop	r14
+	pop	r13
+	pop	r12
+	pop	rdi
+	pop	rsi
+	pop	rbx
+	ret	0
 $LN113@GetSnapsho:
 ; Line 2064
 	call	GetXLogInsertRecPtr
@@ -7251,12 +7263,12 @@
 	mov	rcx, rax
 	mov	QWORD PTR [rsi+96], rax
 	call	MaintainOldSnapshotTimeMapping
-$LN114@GetSnapsho:
 ; Line 2513
 	mov	rax, rsi
-	add	rsp, 128				; 00000080H
-	pop	r15
+	add	rsp, 120				; 00000078H
+	pop	r14
 	pop	r13
+	pop	r12
 	pop	rdi
 	pop	rsi
 	pop	rbx
#5Ranier Vilela
ranier.vf@gmail.com
In reply to: Ranier Vilela (#4)
1 attachment(s)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

I took it a step further.

Transactions

HEAD patched
10002207 10586781
10146167 10388685
10048919 10333359
10065764,3333333 10436275 3,55021946687555

TPS
HEAD patched
33469,016009 35399,010472
33950,624679 34733,252336
33639,8429 34578,495043
33686,4945293333 34903,5859503333 3,48700968070122

3,55% Is it worth touch procarray.c for real?

With msvc 64 bits, the asm generated:
HEAD
213.731 bytes procarray.asm
patched
212.035 bytes procarray.asm

Patch attached.

regards,
Ranier Vilela

Attachments:

improve_procarray.patchapplication/octet-stream; name=improve_procarray.patchDownload
diff --git a/src/backend/access/heap/heapam_handler.c b/src/backend/access/heap/heapam_handler.c
index 1b8b640012..5b6f3d65f2 100644
--- a/src/backend/access/heap/heapam_handler.c
+++ b/src/backend/access/heap/heapam_handler.c
@@ -2460,14 +2460,15 @@ reform_and_rewrite_tuple(HeapTuple tuple,
 	TupleDesc	oldTupDesc = RelationGetDescr(OldHeap);
 	TupleDesc	newTupDesc = RelationGetDescr(NewHeap);
 	HeapTuple	copiedTuple;
+	int			natts = newTupDesc->natts;
 	int			i;
 
 	heap_deform_tuple(tuple, oldTupDesc, values, isnull);
 
 	/* Be sure to null out any dropped columns */
-	for (i = 0; i < newTupDesc->natts; i++)
+	for (i = 0; i < natts; i++)
 	{
-		if (TupleDescAttr(newTupDesc, i)->attisdropped)
+		if (!isnull[i] && TupleDescAttr(newTupDesc, i)->attisdropped)
 			isnull[i] = true;
 	}
 
diff --git a/src/backend/storage/ipc/procarray.c b/src/backend/storage/ipc/procarray.c
index 085bd1e407..0f0c5032c4 100644
--- a/src/backend/storage/ipc/procarray.c
+++ b/src/backend/storage/ipc/procarray.c
@@ -445,6 +445,7 @@ void
 ProcArrayAdd(PGPROC *proc)
 {
 	ProcArrayStruct *arrayP = procArray;
+	int        numProcs;
 	int			index;
 	int			movecount;
 
@@ -473,7 +474,8 @@ ProcArrayAdd(PGPROC *proc)
 	 * Since the occurrence of adding/removing a proc is much lower than the
 	 * access to the ProcArray itself, the overhead should be marginal
 	 */
-	for (index = 0; index < arrayP->numProcs; index++)
+	numProcs = arrayP->numProcs;
+	for (index = 0; index < numProcs; index++)
 	{
 		int			procno PG_USED_FOR_ASSERTS_ONLY = arrayP->pgprocnos[index];
 
@@ -485,7 +487,7 @@ ProcArrayAdd(PGPROC *proc)
 			break;
 	}
 
-	movecount = arrayP->numProcs - index;
+	movecount = numProcs - index;
 	memmove(&arrayP->pgprocnos[index + 1],
 			&arrayP->pgprocnos[index],
 			movecount * sizeof(*arrayP->pgprocnos));
@@ -509,9 +511,10 @@ ProcArrayAdd(PGPROC *proc)
 
 	/* adjust pgxactoff for all following PGPROCs */
 	index++;
-	for (; index < arrayP->numProcs; index++)
+	numProcs = arrayP->numProcs;
+	for (; index < numProcs; index++)
 	{
-		int			procno = arrayP->pgprocnos[index];
+		int		procno = arrayP->pgprocnos[index];
 
 		Assert(procno >= 0 && procno < (arrayP->maxProcs + NUM_AUXILIARY_PROCS));
 		Assert(allProcs[procno].pgxactoff == index - 1);
@@ -541,8 +544,10 @@ void
 ProcArrayRemove(PGPROC *proc, TransactionId latestXid)
 {
 	ProcArrayStruct *arrayP = procArray;
+	int        numProcs;
 	int			myoff;
 	int			movecount;
+	int        index;
 
 #ifdef XIDCACHE_DEBUG
 	/* dump stats at backend shutdown, but not prepared-xact end */
@@ -607,7 +612,8 @@ ProcArrayRemove(PGPROC *proc, TransactionId latestXid)
 	 * Adjust pgxactoff of following procs for removed PGPROC (note that
 	 * numProcs already has been decremented).
 	 */
-	for (int index = myoff; index < arrayP->numProcs; index++)
+	numProcs = arrayP->numProcs;
+	for (index = myoff; index < numProcs; index++)
 	{
 		int			procno = arrayP->pgprocnos[index];
 
@@ -703,7 +709,7 @@ ProcArrayEndTransaction(PGPROC *proc, TransactionId latestXid)
 static inline void
 ProcArrayEndTransactionInternal(PGPROC *proc, TransactionId latestXid)
 {
-	size_t		pgxactoff = proc->pgxactoff;
+	int			pgxactoff = proc->pgxactoff;
 
 	/*
 	 * Note: we need exclusive lock here because we're going to change other
@@ -761,7 +767,7 @@ ProcArrayEndTransactionInternal(PGPROC *proc, TransactionId latestXid)
 static void
 ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 {
-	PROC_HDR   *procglobal = ProcGlobal;
+	const PROC_HDR   *procglobal = ProcGlobal;
 	uint32		nextidx;
 	uint32		wakeidx;
 
@@ -829,12 +835,12 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	/* Walk the list and clear all XIDs. */
 	while (nextidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[nextidx];
+		PGPROC	   *nextproc = &allProcs[nextidx];
 
-		ProcArrayEndTransactionInternal(proc, proc->procArrayGroupMemberXid);
+		ProcArrayEndTransactionInternal(nextproc, nextproc->procArrayGroupMemberXid);
 
 		/* Move to next proc in list. */
-		nextidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
+		nextidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
 	}
 
 	/* We're done with the lock now. */
@@ -849,18 +855,18 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	 */
 	while (wakeidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[wakeidx];
+		PGPROC	   *nextproc = &allProcs[wakeidx];
 
-		wakeidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
-		pg_atomic_write_u32(&proc->procArrayGroupNext, INVALID_PGPROCNO);
+		wakeidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
+		pg_atomic_write_u32(&nextproc->procArrayGroupNext, INVALID_PGPROCNO);
 
 		/* ensure all previous writes are visible before follower continues. */
 		pg_write_barrier();
 
-		proc->procArrayGroupMember = false;
+		nextproc->procArrayGroupMember = false;
 
-		if (proc != MyProc)
-			PGSemaphoreUnlock(proc->sem);
+		if (nextproc != MyProc)
+			PGSemaphoreUnlock(nextproc->sem);
 	}
 }
 
@@ -875,7 +881,7 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 void
 ProcArrayClearTransaction(PGPROC *proc)
 {
-	size_t		pgxactoff;
+	int			pgxactoff;
 
 	/*
 	 * Currently we need to lock ProcArrayLock exclusively here, as we
@@ -1024,6 +1030,7 @@ ProcArrayApplyRecoveryInfo(RunningTransactions running)
 {
 	TransactionId *xids;
 	int			nxids;
+	int        cnts;
 	int			i;
 
 	Assert(standbyState >= STANDBY_INITIALIZED);
@@ -1126,9 +1133,10 @@ ProcArrayApplyRecoveryInfo(RunningTransactions running)
 	 * Add to the temp array any xids which have not already completed.
 	 */
 	nxids = 0;
-	for (i = 0; i < running->xcnt + running->subxcnt; i++)
+	cnts = running->xcnt + running->subxcnt;
+	for (i = 0; i < cnts; i++)
 	{
-		TransactionId xid = running->xids[i];
+		const TransactionId xid = running->xids[i];
 
 		/*
 		 * The running-xacts snapshot can contain xids that were still visible
@@ -1349,14 +1357,14 @@ TransactionIdIsInProgress(TransactionId xid)
 {
 	static TransactionId *xids = NULL;
 	static TransactionId *other_xids;
-	XidCacheStatus *other_subxidstates;
-	int			nxids = 0;
-	ProcArrayStruct *arrayP = procArray;
+	const XidCacheStatus *other_subxidstates;
+	const ProcArrayStruct *arrayP = procArray;
 	TransactionId topxid;
 	TransactionId latestCompletedXid;
+	int			nxids = 0;
+	int 		pgxactoff;
 	int			mypgxactoff;
-	size_t		numProcs;
-	int			j;
+	int			numProcs;
 
 	/*
 	 * Don't bother checking a transaction older than RecentXmin; it could not
@@ -1432,12 +1440,13 @@ TransactionIdIsInProgress(TransactionId xid)
 	/* No shortcuts, gotta grovel through the array */
 	mypgxactoff = MyProc->pgxactoff;
 	numProcs = arrayP->numProcs;
-	for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+	for (pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
 	{
-		int			pgprocno;
-		PGPROC	   *proc;
+		const PGPROC	*proc;
 		TransactionId pxid;
-		int			pxids;
+		int				pxids;
+		int				pgprocno;
+		int				j;
 
 		/* Ignore ourselves --- dealt with it above */
 		if (pgxactoff == mypgxactoff)
@@ -1558,7 +1567,9 @@ TransactionIdIsInProgress(TransactionId xid)
 	Assert(TransactionIdIsValid(topxid));
 	if (!TransactionIdEquals(topxid, xid))
 	{
-		for (int i = 0; i < nxids; i++)
+		int 	i;
+
+		for (i = 0; i < nxids; i++)
 		{
 			if (TransactionIdEquals(xids[i], topxid))
 				return true;
@@ -1579,10 +1590,11 @@ TransactionIdIsInProgress(TransactionId xid)
 bool
 TransactionIdIsActive(TransactionId xid)
 {
-	bool		result = false;
-	ProcArrayStruct *arrayP = procArray;
-	TransactionId *other_xids = ProcGlobal->xids;
+	const ProcArrayStruct *arrayP;
+	const TransactionId *other_xids;
+	int 		numProcs;
 	int			i;
+	bool		result;
 
 	/*
 	 * Don't bother checking a transaction older than RecentXmin; it could not
@@ -1591,12 +1603,17 @@ TransactionIdIsActive(TransactionId xid)
 	if (TransactionIdPrecedes(xid, RecentXmin))
 		return false;
 
+	arrayP = procArray;
+	other_xids = ProcGlobal->xids;
+	numProcs = arrayP->numProcs;
+	result = false;
+
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (i = 0; i < arrayP->numProcs; i++)
+	for (i = 0; i < numProcs; i++)
 	{
-		int			pgprocno = arrayP->pgprocnos[i];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		int		 pgprocno = arrayP->pgprocnos[i];
+		const PGPROC	*proc = &allProcs[pgprocno];
 		TransactionId pxid;
 
 		/* Fetch xid just once - see GetNewTransactionId */
@@ -1689,10 +1706,12 @@ TransactionIdIsActive(TransactionId xid)
 static void
 ComputeXidHorizons(ComputeXidHorizonsResult *h)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
 	TransactionId kaxmin;
+	const TransactionId *other_xids = ProcGlobal->xids;
+	int 		numProcs = arrayP->numProcs;
+	int			index;
 	bool		in_recovery = RecoveryInProgress();
-	TransactionId *other_xids = ProcGlobal->xids;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
@@ -1742,11 +1761,11 @@ ComputeXidHorizons(ComputeXidHorizonsResult *h)
 	h->slot_xmin = procArray->replication_slot_xmin;
 	h->slot_catalog_xmin = procArray->replication_slot_catalog_xmin;
 
-	for (int index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
-		int8		statusFlags = ProcGlobal->statusFlags[index];
+		int				pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	*proc = &allProcs[pgprocno];
+		int8			statusFlags = ProcGlobal->statusFlags[index];
 		TransactionId xid;
 		TransactionId xmin;
 
@@ -2162,21 +2181,20 @@ GetSnapshotDataReuse(Snapshot snapshot)
 Snapshot
 GetSnapshotData(Snapshot snapshot)
 {
-	ProcArrayStruct *arrayP = procArray;
-	TransactionId *other_xids = ProcGlobal->xids;
+	const ProcArrayStruct *arrayP = procArray;
+	const TransactionId *other_xids = ProcGlobal->xids;
+	FullTransactionId latest_completed;
 	TransactionId xmin;
 	TransactionId xmax;
-	size_t		count = 0;
-	int			subcount = 0;
-	bool		suboverflowed = false;
-	FullTransactionId latest_completed;
 	TransactionId oldestxid;
-	int			mypgxactoff;
 	TransactionId myxid;
-	uint64		curXactCompletionCount;
-
 	TransactionId replication_slot_xmin = InvalidTransactionId;
 	TransactionId replication_slot_catalog_xmin = InvalidTransactionId;
+	uint64		curXactCompletionCount;
+	int			mypgxactoff;
+	int			count = 0;
+	int			subcount = 0;
+	bool		suboverflowed = false;
 
 	Assert(snapshot != NULL);
 
@@ -2248,17 +2266,18 @@ GetSnapshotData(Snapshot snapshot)
 
 	if (!snapshot->takenDuringRecovery)
 	{
-		size_t		numProcs = arrayP->numProcs;
 		TransactionId *xip = snapshot->xip;
-		int		   *pgprocnos = arrayP->pgprocnos;
-		XidCacheStatus *subxidStates = ProcGlobal->subxidStates;
-		uint8	   *allStatusFlags = ProcGlobal->statusFlags;
+		const XidCacheStatus *subxidStates = ProcGlobal->subxidStates;
+		const uint8	   *allStatusFlags = ProcGlobal->statusFlags;
+		const int		   *pgprocnos = arrayP->pgprocnos;
+		int					numProcs = arrayP->numProcs;
+		int 				pgxactoff;
 
 		/*
 		 * First collect set of pgxactoff/xids that need to be included in the
 		 * snapshot.
 		 */
-		for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+		for (pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
 		{
 			/* Fetch xid just once - see GetNewTransactionId */
 			TransactionId xid = UINT32_ACCESS_ONCE(other_xids[pgxactoff]);
@@ -2328,7 +2347,6 @@ GetSnapshotData(Snapshot snapshot)
 			 */
 			if (!suboverflowed)
 			{
-
 				if (subxidStates[pgxactoff].overflowed)
 					suboverflowed = true;
 				else
@@ -2337,8 +2355,8 @@ GetSnapshotData(Snapshot snapshot)
 
 					if (nsubxids > 0)
 					{
-						int			pgprocno = pgprocnos[pgxactoff];
-						PGPROC	   *proc = &allProcs[pgprocno];
+						int				pgprocno = pgprocnos[pgxactoff];
+						const PGPROC	*proc = &allProcs[pgprocno];
 
 						pg_read_barrier();	/* pairs with GetNewTransactionId */
 
@@ -2526,22 +2544,27 @@ bool
 ProcArrayInstallImportedXmin(TransactionId xmin,
 							 VirtualTransactionId *sourcevxid)
 {
-	bool		result = false;
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP;
+	int 		numProcs;
 	int			index;
+	bool		result;
 
 	Assert(TransactionIdIsNormal(xmin));
 	if (!sourcevxid)
 		return false;
 
+	arrayP = procArray;
+	numProcs = arrayP->numProcs;
+	result = false;
+
 	/* Get lock so source xact can't end while we're doing this */
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
-		int			statusFlags = ProcGlobal->statusFlags[index];
+		int				pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	*proc = &allProcs[pgprocno];
+		int				statusFlags = ProcGlobal->statusFlags[index];
 		TransactionId xid;
 
 		/* Ignore procs running LAZY VACUUM */
@@ -2600,8 +2623,8 @@ ProcArrayInstallImportedXmin(TransactionId xmin,
 bool
 ProcArrayInstallRestoredXmin(TransactionId xmin, PGPROC *proc)
 {
-	bool		result = false;
 	TransactionId xid;
+	bool		result = false;
 
 	Assert(TransactionIdIsNormal(xmin));
 	Assert(proc != NULL);
@@ -2672,6 +2695,7 @@ GetRunningTransactionData(void)
 	TransactionId latestCompletedXid;
 	TransactionId oldestRunningXid;
 	TransactionId *xids;
+	int			numProcs = arrayP->numProcs;
 	int			index;
 	int			count;
 	int			subcount;
@@ -2721,7 +2745,7 @@ GetRunningTransactionData(void)
 	/*
 	 * Spin over procArray collecting all xids
 	 */
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		TransactionId xid;
 
@@ -2765,11 +2789,11 @@ GetRunningTransactionData(void)
 	{
 		XidCacheStatus *other_subxidstates = ProcGlobal->subxidStates;
 
-		for (index = 0; index < arrayP->numProcs; index++)
+		for (index = 0; index < numProcs; index++)
 		{
-			int			pgprocno = arrayP->pgprocnos[index];
-			PGPROC	   *proc = &allProcs[pgprocno];
-			int			nsubxids;
+			int				pgprocno = arrayP->pgprocnos[index];
+			const PGPROC	*proc = &allProcs[pgprocno];
+			int				nsubxids;
 
 			/*
 			 * Save subtransaction XIDs. Other backends can't add or remove
@@ -2838,9 +2862,10 @@ GetRunningTransactionData(void)
 TransactionId
 GetOldestActiveTransactionId(void)
 {
-	ProcArrayStruct *arrayP = procArray;
-	TransactionId *other_xids = ProcGlobal->xids;
+	const ProcArrayStruct *arrayP = procArray;
+	const TransactionId *other_xids = ProcGlobal->xids;
 	TransactionId oldestRunningXid;
+	int			numProcs = arrayP->numProcs;
 	int			index;
 
 	Assert(!RecoveryInProgress());
@@ -2860,7 +2885,7 @@ GetOldestActiveTransactionId(void)
 	 * Spin over procArray collecting all xids and subxids.
 	 */
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		TransactionId xid;
 
@@ -2903,9 +2928,8 @@ GetOldestActiveTransactionId(void)
 TransactionId
 GetOldestSafeDecodingTransactionId(bool catalogOnly)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
 	TransactionId oldestSafeXid;
-	int			index;
 	bool		recovery_in_progress = RecoveryInProgress();
 
 	Assert(LWLockHeldByMe(ProcArrayLock));
@@ -2928,16 +2952,16 @@ GetOldestSafeDecodingTransactionId(bool catalogOnly)
 	 * slot's general xmin horizon, but the catalog horizon is only usable
 	 * when only catalog data is going to be looked at.
 	 */
-	if (TransactionIdIsValid(procArray->replication_slot_xmin) &&
-		TransactionIdPrecedes(procArray->replication_slot_xmin,
+	if (TransactionIdIsValid(arrayP->replication_slot_xmin) &&
+		TransactionIdPrecedes(arrayP->replication_slot_xmin,
 							  oldestSafeXid))
-		oldestSafeXid = procArray->replication_slot_xmin;
+		oldestSafeXid = arrayP->replication_slot_xmin;
 
 	if (catalogOnly &&
-		TransactionIdIsValid(procArray->replication_slot_catalog_xmin) &&
-		TransactionIdPrecedes(procArray->replication_slot_catalog_xmin,
+		TransactionIdIsValid(arrayP->replication_slot_catalog_xmin) &&
+		TransactionIdPrecedes(arrayP->replication_slot_catalog_xmin,
 							  oldestSafeXid))
-		oldestSafeXid = procArray->replication_slot_catalog_xmin;
+		oldestSafeXid = arrayP->replication_slot_catalog_xmin;
 
 	/*
 	 * If we're not in recovery, we walk over the procarray and collect the
@@ -2953,12 +2977,14 @@ GetOldestSafeDecodingTransactionId(bool catalogOnly)
 	 */
 	if (!recovery_in_progress)
 	{
-		TransactionId *other_xids = ProcGlobal->xids;
+		const TransactionId *other_xids = ProcGlobal->xids;
+		int 		numProcs = arrayP->numProcs;
+		int 		index;
 
 		/*
 		 * Spin over procArray collecting min(ProcGlobal->xids[i])
 		 */
-		for (index = 0; index < arrayP->numProcs; index++)
+		for (index = 0; index < numProcs; index++)
 		{
 			TransactionId xid;
 
@@ -2999,8 +3025,9 @@ GetOldestSafeDecodingTransactionId(bool catalogOnly)
 VirtualTransactionId *
 GetVirtualXIDsDelayingChkpt(int *nvxids)
 {
+	const ProcArrayStruct *arrayP = procArray;
 	VirtualTransactionId *vxids;
-	ProcArrayStruct *arrayP = procArray;
+	int 		numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
@@ -3010,10 +3037,10 @@ GetVirtualXIDsDelayingChkpt(int *nvxids)
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		int				pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	*proc = &allProcs[pgprocno];
 
 		if (proc->delayChkpt)
 		{
@@ -3043,16 +3070,17 @@ GetVirtualXIDsDelayingChkpt(int *nvxids)
 bool
 HaveVirtualXIDsDelayingChkpt(VirtualTransactionId *vxids, int nvxids)
 {
-	bool		result = false;
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int 		numProcs = arrayP->numProcs;
 	int			index;
+	bool		result = false;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		int					pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	   *proc = &allProcs[pgprocno];
 		VirtualTransactionId vxid;
 
 		GET_VXID_FROM_PGPROC(vxid, *proc);
@@ -3089,7 +3117,7 @@ HaveVirtualXIDsDelayingChkpt(VirtualTransactionId *vxids, int nvxids)
 PGPROC *
 BackendPidGetProc(int pid)
 {
-	PGPROC	   *result;
+	const PGPROC	   *result;
 
 	if (pid == 0)				/* never match dummy PGPROCs */
 		return NULL;
@@ -3112,25 +3140,26 @@ BackendPidGetProc(int pid)
 PGPROC *
 BackendPidGetProcWithLock(int pid)
 {
-	PGPROC	   *result = NULL;
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP;
+	int 		numProcs;
 	int			index;
 
 	if (pid == 0)				/* never match dummy PGPROCs */
 		return NULL;
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	arrayP = procArray;
+	numProcs = arrayP->numProcs;
+	for (index = 0; index < numProcs; index++)
 	{
-		PGPROC	   *proc = &allProcs[arrayP->pgprocnos[index]];
+		const PGPROC		*proc = &allProcs[arrayP->pgprocnos[index]];
 
 		if (proc->pid == pid)
 		{
-			result = proc;
-			break;
+			return proc;
 		}
 	}
 
-	return result;
+	return NULL;
 }
 
 /*
@@ -3149,31 +3178,29 @@ BackendPidGetProcWithLock(int pid)
 int
 BackendXidGetPid(TransactionId xid)
 {
-	int			result = 0;
-	ProcArrayStruct *arrayP = procArray;
-	TransactionId *other_xids = ProcGlobal->xids;
+	const ProcArrayStruct *arrayP;
+	const TransactionId *other_xids;
+	int 		numProcs;
 	int			index;
 
 	if (xid == InvalidTransactionId)	/* never match invalid xid */
 		return 0;
 
-	LWLockAcquire(ProcArrayLock, LW_SHARED);
-
-	for (index = 0; index < arrayP->numProcs; index++)
+	arrayP = procArray;
+	other_xids = ProcGlobal->xids;
+	numProcs = arrayP->numProcs;
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		int					pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	   *proc = &allProcs[pgprocno];
 
 		if (other_xids[index] == xid)
 		{
-			result = proc->pid;
-			break;
+			return proc->pid;
 		}
 	}
 
-	LWLockRelease(ProcArrayLock);
-
-	return result;
+	return 0;
 }
 
 /*
@@ -3220,7 +3247,8 @@ GetCurrentVirtualXIDs(TransactionId limitXmin, bool excludeXmin0,
 					  int *nvxids)
 {
 	VirtualTransactionId *vxids;
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int 		numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
@@ -3230,11 +3258,11 @@ GetCurrentVirtualXIDs(TransactionId limitXmin, bool excludeXmin0,
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
-		uint8		statusFlags = ProcGlobal->statusFlags[index];
+		int				pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	*proc = &allProcs[pgprocno];
+		uint8			statusFlags = ProcGlobal->statusFlags[index];
 
 		if (proc == MyProc)
 			continue;
@@ -3245,7 +3273,7 @@ GetCurrentVirtualXIDs(TransactionId limitXmin, bool excludeXmin0,
 		if (allDbs || proc->databaseId == MyDatabaseId)
 		{
 			/* Fetch xmin just once - might change on us */
-			TransactionId pxmin = UINT32_ACCESS_ONCE(proc->xmin);
+			const TransactionId pxmin = UINT32_ACCESS_ONCE(proc->xmin);
 
 			if (excludeXmin0 && !TransactionIdIsValid(pxmin))
 				continue;
@@ -3306,7 +3334,8 @@ VirtualTransactionId *
 GetConflictingVirtualXIDs(TransactionId limitXmin, Oid dbOid)
 {
 	static VirtualTransactionId *vxids;
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int 		numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
@@ -3327,10 +3356,10 @@ GetConflictingVirtualXIDs(TransactionId limitXmin, Oid dbOid)
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		int				pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	*proc = &allProcs[pgprocno];
 
 		/* Exclude prepared transactions */
 		if (proc->pid == 0)
@@ -3340,7 +3369,7 @@ GetConflictingVirtualXIDs(TransactionId limitXmin, Oid dbOid)
 			proc->databaseId == dbOid)
 		{
 			/* Fetch xmin just once - can't change on us, but good coding */
-			TransactionId pxmin = UINT32_ACCESS_ONCE(proc->xmin);
+			const TransactionId pxmin = UINT32_ACCESS_ONCE(proc->xmin);
 
 			/*
 			 * We ignore an invalid pxmin because this means that backend has
@@ -3386,16 +3415,17 @@ pid_t
 SignalVirtualTransaction(VirtualTransactionId vxid, ProcSignalReason sigmode,
 						 bool conflictPending)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int 		numProcs = arrayP->numProcs;
 	int			index;
 	pid_t		pid = 0;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		PGPROC	   	*proc = &allProcs[pgprocno];
 		VirtualTransactionId procvxid;
 
 		GET_VXID_FROM_PGPROC(procvxid, *proc);
@@ -3434,8 +3464,9 @@ SignalVirtualTransaction(VirtualTransactionId vxid, ProcSignalReason sigmode,
 bool
 MinimumActiveBackends(int min)
 {
-	ProcArrayStruct *arrayP = procArray;
-	int			count = 0;
+	ProcArrayStruct *arrayP;
+	int			count;
+	int  		numProcs;
 	int			index;
 
 	/* Quick short-circuit if no minimum is specified */
@@ -3447,10 +3478,13 @@ MinimumActiveBackends(int min)
 	 * bogus, but since we are only testing fields for zero or nonzero, it
 	 * should be OK.  The result is only used for heuristic purposes anyway...
 	 */
-	for (index = 0; index < arrayP->numProcs; index++)
+	count = 0;
+	arrayP = procArray;
+	numProcs = arrayP->numProcs;
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		int					pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	   *proc = &allProcs[pgprocno];
 
 		/*
 		 * Since we're not holding a lock, need to be prepared to deal with
@@ -3487,16 +3521,17 @@ MinimumActiveBackends(int min)
 int
 CountDBBackends(Oid databaseid)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		int				pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	*proc = &allProcs[pgprocno];
 
 		if (proc->pid == 0)
 			continue;			/* do not count prepared xacts */
@@ -3517,16 +3552,17 @@ CountDBBackends(Oid databaseid)
 int
 CountDBConnections(Oid databaseid)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int 		numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		int					pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	   *proc = &allProcs[pgprocno];
 
 		if (proc->pid == 0)
 			continue;			/* do not count prepared xacts */
@@ -3548,16 +3584,17 @@ CountDBConnections(Oid databaseid)
 void
 CancelDBBackends(Oid databaseid, ProcSignalReason sigmode, bool conflictPending)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			index;
 
 	/* tell all backends to die */
 	LWLockAcquire(ProcArrayLock, LW_EXCLUSIVE);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const int	pgprocno = arrayP->pgprocnos[index];
+		PGPROC	   	*proc = &allProcs[pgprocno];
 
 		if (databaseid == InvalidOid || proc->databaseId == databaseid)
 		{
@@ -3588,16 +3625,17 @@ CancelDBBackends(Oid databaseid, ProcSignalReason sigmode, bool conflictPending)
 int
 CountUserBackends(Oid roleid)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int 		numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		int					pgprocno = arrayP->pgprocnos[index];
+		const PGPROC	   *proc = &allProcs[pgprocno];
 
 		if (proc->pid == 0)
 			continue;			/* do not count prepared xacts */
@@ -3638,7 +3676,7 @@ CountUserBackends(Oid roleid)
 bool
 CountOtherDBBackends(Oid databaseId, int *nbackends, int *nprepared)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
 
 #define MAXAUTOVACPIDS	10		/* max autovacs to SIGTERM per iteration */
 	int			autovac_pids[MAXAUTOVACPIDS];
@@ -3647,9 +3685,10 @@ CountOtherDBBackends(Oid databaseId, int *nbackends, int *nprepared)
 	/* 50 tries with 100ms sleep between tries makes 5 sec total wait */
 	for (tries = 0; tries < 50; tries++)
 	{
+		int 		numProcs = arrayP->numProcs;
+		int			index;
 		int			nautovacs = 0;
 		bool		found = false;
-		int			index;
 
 		CHECK_FOR_INTERRUPTS();
 
@@ -3657,11 +3696,11 @@ CountOtherDBBackends(Oid databaseId, int *nbackends, int *nprepared)
 
 		LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-		for (index = 0; index < arrayP->numProcs; index++)
+		for (index = 0; index < numProcs; index++)
 		{
-			int			pgprocno = arrayP->pgprocnos[index];
-			PGPROC	   *proc = &allProcs[pgprocno];
-			uint8		statusFlags = ProcGlobal->statusFlags[index];
+			int					pgprocno = arrayP->pgprocnos[index];
+			const PGPROC	   *proc = &allProcs[pgprocno];
+			uint8				statusFlags = ProcGlobal->statusFlags[index];
 
 			if (proc->databaseId != databaseId)
 				continue;
@@ -3716,17 +3755,18 @@ CountOtherDBBackends(Oid databaseId, int *nbackends, int *nprepared)
 void
 TerminateOtherDBBackends(Oid databaseId)
 {
-	ProcArrayStruct *arrayP = procArray;
-	List	   *pids = NIL;
+	const ProcArrayStruct *arrayP = procArray;
+	const List *pids = NIL;
+	int 		numProcs = procArray->numProcs;
 	int			nprepared = 0;
 	int			i;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (i = 0; i < procArray->numProcs; i++)
+	for (i = 0; i < numProcs; i++)
 	{
-		int			pgprocno = arrayP->pgprocnos[i];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		int					pgprocno = arrayP->pgprocnos[i];
+		const PGPROC	   *proc = &allProcs[pgprocno];
 
 		if (proc->databaseId != databaseId)
 			continue;
@@ -3767,8 +3807,8 @@ TerminateOtherDBBackends(Oid databaseId)
 		 */
 		foreach(lc, pids)
 		{
-			int			pid = lfirst_int(lc);
-			PGPROC	   *proc = BackendPidGetProc(pid);
+			int					pid = lfirst_int(lc);
+			const PGPROC	   *proc = BackendPidGetProc(pid);
 
 			if (proc != NULL)
 			{
@@ -3795,8 +3835,8 @@ TerminateOtherDBBackends(Oid databaseId)
 		 */
 		foreach(lc, pids)
 		{
-			int			pid = lfirst_int(lc);
-			PGPROC	   *proc = BackendPidGetProc(pid);
+			int					pid = lfirst_int(lc);
+			const PGPROC	   *proc = BackendPidGetProc(pid);
 
 			if (proc != NULL)
 			{
#6Ranier Vilela
ranier.vf@gmail.com
In reply to: Ranier Vilela (#5)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em seg., 14 de jun. de 2021 às 21:01, Ranier Vilela <ranier.vf@gmail.com>
escreveu:

I took it a step further.

Transactions

HEAD patched
10002207 10586781
10146167 10388685
10048919 10333359
10065764,3333333 10436275 3,55021946687555

TPS
HEAD patched
33469,016009 35399,010472
33950,624679 34733,252336
33639,8429 34578,495043
33686,4945293333 34903,5859503333 3,48700968070122

3,55% Is it worth touch procarray.c for real?

With msvc 64 bits, the asm generated:
HEAD
213.731 bytes procarray.asm
patched
212.035 bytes procarray.asm

Patch attached.

Added to next CF (https://commitfest.postgresql.org/33/3169/)

regards,
Ranier Vilela

#7Aleksander Alekseev
aleksander@timescale.com
In reply to: Ranier Vilela (#6)
1 attachment(s)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Hi hackers,

Patch attached.

Added to next CF (https://commitfest.postgresql.org/33/3169/)

The proposed code casts `const` variables to non-`const`. I'm surprised
MSVC misses it. Also, there were some issues with the code formatting. The
corrected patch is attached.

The patch is listed under the "Performance" topic on CF. However, I can't
verify any changes in the performance because there were no benchmarks
attached that I could reproduce. By looking at the code and the first
message in the thread, I assume this is in fact a refactoring.

Personally I don't believe that changes like:

-               for (int i = 0; i < nxids; i++)
+               int     i;
+               for (i = 0; i < nxids; i++)

.. or:

-       for (int index = myoff; index < arrayP->numProcs; index++)
+       numProcs = arrayP->numProcs;
+       for (index = myoff; index < numProcs; index++)

... are of any value, but other changes may be. I choose to keep the patch
as-is except for the named defects and let the committer decide which
changes, if any, are worth committing.

I'm updating the status to "Ready for Committer".

--
Best regards,
Aleksander Alekseev

Attachments:

v3-0001-procarray-refactoring.patchapplication/octet-stream; name=v3-0001-procarray-refactoring.patchDownload
diff --git a/src/backend/access/heap/heapam_handler.c b/src/backend/access/heap/heapam_handler.c
index beb8f20708..61460fce60 100644
--- a/src/backend/access/heap/heapam_handler.c
+++ b/src/backend/access/heap/heapam_handler.c
@@ -2459,14 +2459,15 @@ reform_and_rewrite_tuple(HeapTuple tuple,
 	TupleDesc	oldTupDesc = RelationGetDescr(OldHeap);
 	TupleDesc	newTupDesc = RelationGetDescr(NewHeap);
 	HeapTuple	copiedTuple;
+	int			natts = newTupDesc->natts;
 	int			i;
 
 	heap_deform_tuple(tuple, oldTupDesc, values, isnull);
 
 	/* Be sure to null out any dropped columns */
-	for (i = 0; i < newTupDesc->natts; i++)
+	for (i = 0; i < natts; i++)
 	{
-		if (TupleDescAttr(newTupDesc, i)->attisdropped)
+		if (!isnull[i] && TupleDescAttr(newTupDesc, i)->attisdropped)
 			isnull[i] = true;
 	}
 
diff --git a/src/backend/storage/ipc/procarray.c b/src/backend/storage/ipc/procarray.c
index 4c91e721d0..6261946196 100644
--- a/src/backend/storage/ipc/procarray.c
+++ b/src/backend/storage/ipc/procarray.c
@@ -445,6 +445,7 @@ void
 ProcArrayAdd(PGPROC *proc)
 {
 	ProcArrayStruct *arrayP = procArray;
+	int			numProcs;
 	int			index;
 	int			movecount;
 
@@ -473,7 +474,8 @@ ProcArrayAdd(PGPROC *proc)
 	 * Since the occurrence of adding/removing a proc is much lower than the
 	 * access to the ProcArray itself, the overhead should be marginal
 	 */
-	for (index = 0; index < arrayP->numProcs; index++)
+	numProcs = arrayP->numProcs;
+	for (index = 0; index < numProcs; index++)
 	{
 		int			procno PG_USED_FOR_ASSERTS_ONLY = arrayP->pgprocnos[index];
 
@@ -485,7 +487,7 @@ ProcArrayAdd(PGPROC *proc)
 			break;
 	}
 
-	movecount = arrayP->numProcs - index;
+	movecount = numProcs - index;
 	memmove(&arrayP->pgprocnos[index + 1],
 			&arrayP->pgprocnos[index],
 			movecount * sizeof(*arrayP->pgprocnos));
@@ -509,7 +511,8 @@ ProcArrayAdd(PGPROC *proc)
 
 	/* adjust pgxactoff for all following PGPROCs */
 	index++;
-	for (; index < arrayP->numProcs; index++)
+	numProcs = arrayP->numProcs;
+	for (; index < numProcs; index++)
 	{
 		int			procno = arrayP->pgprocnos[index];
 
@@ -541,8 +544,10 @@ void
 ProcArrayRemove(PGPROC *proc, TransactionId latestXid)
 {
 	ProcArrayStruct *arrayP = procArray;
+	int			numProcs;
 	int			myoff;
 	int			movecount;
+	int			index;
 
 #ifdef XIDCACHE_DEBUG
 	/* dump stats at backend shutdown, but not prepared-xact end */
@@ -607,7 +612,8 @@ ProcArrayRemove(PGPROC *proc, TransactionId latestXid)
 	 * Adjust pgxactoff of following procs for removed PGPROC (note that
 	 * numProcs already has been decremented).
 	 */
-	for (int index = myoff; index < arrayP->numProcs; index++)
+	numProcs = arrayP->numProcs;
+	for (index = myoff; index < numProcs; index++)
 	{
 		int			procno = arrayP->pgprocnos[index];
 
@@ -703,7 +709,7 @@ ProcArrayEndTransaction(PGPROC *proc, TransactionId latestXid)
 static inline void
 ProcArrayEndTransactionInternal(PGPROC *proc, TransactionId latestXid)
 {
-	size_t		pgxactoff = proc->pgxactoff;
+	int			pgxactoff = proc->pgxactoff;
 
 	/*
 	 * Note: we need exclusive lock here because we're going to change other
@@ -829,12 +835,12 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	/* Walk the list and clear all XIDs. */
 	while (nextidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[nextidx];
+		PGPROC	   *nextproc = &allProcs[nextidx];
 
-		ProcArrayEndTransactionInternal(proc, proc->procArrayGroupMemberXid);
+		ProcArrayEndTransactionInternal(nextproc, nextproc->procArrayGroupMemberXid);
 
 		/* Move to next proc in list. */
-		nextidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
+		nextidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
 	}
 
 	/* We're done with the lock now. */
@@ -849,18 +855,18 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	 */
 	while (wakeidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[wakeidx];
+		PGPROC	   *nextproc = &allProcs[wakeidx];
 
-		wakeidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
-		pg_atomic_write_u32(&proc->procArrayGroupNext, INVALID_PGPROCNO);
+		wakeidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
+		pg_atomic_write_u32(&nextproc->procArrayGroupNext, INVALID_PGPROCNO);
 
 		/* ensure all previous writes are visible before follower continues. */
 		pg_write_barrier();
 
-		proc->procArrayGroupMember = false;
+		nextproc->procArrayGroupMember = false;
 
-		if (proc != MyProc)
-			PGSemaphoreUnlock(proc->sem);
+		if (nextproc != MyProc)
+			PGSemaphoreUnlock(nextproc->sem);
 	}
 }
 
@@ -875,7 +881,7 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 void
 ProcArrayClearTransaction(PGPROC *proc)
 {
-	size_t		pgxactoff;
+	int			pgxactoff;
 
 	/*
 	 * Currently we need to lock ProcArrayLock exclusively here, as we
@@ -1024,6 +1030,7 @@ ProcArrayApplyRecoveryInfo(RunningTransactions running)
 {
 	TransactionId *xids;
 	int			nxids;
+	int			cnts;
 	int			i;
 
 	Assert(standbyState >= STANDBY_INITIALIZED);
@@ -1126,9 +1133,10 @@ ProcArrayApplyRecoveryInfo(RunningTransactions running)
 	 * Add to the temp array any xids which have not already completed.
 	 */
 	nxids = 0;
-	for (i = 0; i < running->xcnt + running->subxcnt; i++)
+	cnts = running->xcnt + running->subxcnt;
+	for (i = 0; i < cnts; i++)
 	{
-		TransactionId xid = running->xids[i];
+		const TransactionId xid = running->xids[i];
 
 		/*
 		 * The running-xacts snapshot can contain xids that were still visible
@@ -1349,14 +1357,14 @@ TransactionIdIsInProgress(TransactionId xid)
 {
 	static TransactionId *xids = NULL;
 	static TransactionId *other_xids;
-	XidCacheStatus *other_subxidstates;
-	int			nxids = 0;
-	ProcArrayStruct *arrayP = procArray;
+	const XidCacheStatus *other_subxidstates;
+	const ProcArrayStruct *arrayP = procArray;
 	TransactionId topxid;
 	TransactionId latestCompletedXid;
+	int			nxids = 0;
+	int			pgxactoff;
 	int			mypgxactoff;
-	size_t		numProcs;
-	int			j;
+	int			numProcs;
 
 	/*
 	 * Don't bother checking a transaction older than RecentXmin; it could not
@@ -1432,12 +1440,13 @@ TransactionIdIsInProgress(TransactionId xid)
 	/* No shortcuts, gotta grovel through the array */
 	mypgxactoff = MyProc->pgxactoff;
 	numProcs = arrayP->numProcs;
-	for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+	for (pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
 	{
-		int			pgprocno;
-		PGPROC	   *proc;
+		const PGPROC *proc;
 		TransactionId pxid;
 		int			pxids;
+		int			pgprocno;
+		int			j;
 
 		/* Ignore ourselves --- dealt with it above */
 		if (pgxactoff == mypgxactoff)
@@ -1558,7 +1567,9 @@ TransactionIdIsInProgress(TransactionId xid)
 	Assert(TransactionIdIsValid(topxid));
 	if (!TransactionIdEquals(topxid, xid))
 	{
-		for (int i = 0; i < nxids; i++)
+		int			i;
+
+		for (i = 0; i < nxids; i++)
 		{
 			if (TransactionIdEquals(xids[i], topxid))
 				return true;
@@ -1579,10 +1590,11 @@ TransactionIdIsInProgress(TransactionId xid)
 bool
 TransactionIdIsActive(TransactionId xid)
 {
-	bool		result = false;
-	ProcArrayStruct *arrayP = procArray;
-	TransactionId *other_xids = ProcGlobal->xids;
+	const ProcArrayStruct *arrayP;
+	const TransactionId *other_xids;
+	int			numProcs;
 	int			i;
+	bool		result;
 
 	/*
 	 * Don't bother checking a transaction older than RecentXmin; it could not
@@ -1591,12 +1603,17 @@ TransactionIdIsActive(TransactionId xid)
 	if (TransactionIdPrecedes(xid, RecentXmin))
 		return false;
 
+	arrayP = procArray;
+	other_xids = ProcGlobal->xids;
+	numProcs = arrayP->numProcs;
+	result = false;
+
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (i = 0; i < arrayP->numProcs; i++)
+	for (i = 0; i < numProcs; i++)
 	{
 		int			pgprocno = arrayP->pgprocnos[i];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 		TransactionId pxid;
 
 		/* Fetch xid just once - see GetNewTransactionId */
@@ -1689,10 +1706,12 @@ TransactionIdIsActive(TransactionId xid)
 static void
 ComputeXidHorizons(ComputeXidHorizonsResult *h)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
 	TransactionId kaxmin;
+	const TransactionId *other_xids = ProcGlobal->xids;
+	int			numProcs = arrayP->numProcs;
+	int			index;
 	bool		in_recovery = RecoveryInProgress();
-	TransactionId *other_xids = ProcGlobal->xids;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
@@ -1742,10 +1761,10 @@ ComputeXidHorizons(ComputeXidHorizonsResult *h)
 	h->slot_xmin = procArray->replication_slot_xmin;
 	h->slot_catalog_xmin = procArray->replication_slot_catalog_xmin;
 
-	for (int index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 		int8		statusFlags = ProcGlobal->statusFlags[index];
 		TransactionId xid;
 		TransactionId xmin;
@@ -2163,21 +2182,20 @@ GetSnapshotDataReuse(Snapshot snapshot)
 Snapshot
 GetSnapshotData(Snapshot snapshot)
 {
-	ProcArrayStruct *arrayP = procArray;
-	TransactionId *other_xids = ProcGlobal->xids;
+	const ProcArrayStruct *arrayP = procArray;
+	const TransactionId *other_xids = ProcGlobal->xids;
+	FullTransactionId latest_completed;
 	TransactionId xmin;
 	TransactionId xmax;
-	size_t		count = 0;
-	int			subcount = 0;
-	bool		suboverflowed = false;
-	FullTransactionId latest_completed;
 	TransactionId oldestxid;
-	int			mypgxactoff;
 	TransactionId myxid;
-	uint64		curXactCompletionCount;
-
 	TransactionId replication_slot_xmin = InvalidTransactionId;
 	TransactionId replication_slot_catalog_xmin = InvalidTransactionId;
+	uint64		curXactCompletionCount;
+	int			mypgxactoff;
+	int			count = 0;
+	int			subcount = 0;
+	bool		suboverflowed = false;
 
 	Assert(snapshot != NULL);
 
@@ -2249,17 +2267,18 @@ GetSnapshotData(Snapshot snapshot)
 
 	if (!snapshot->takenDuringRecovery)
 	{
-		size_t		numProcs = arrayP->numProcs;
 		TransactionId *xip = snapshot->xip;
-		int		   *pgprocnos = arrayP->pgprocnos;
-		XidCacheStatus *subxidStates = ProcGlobal->subxidStates;
-		uint8	   *allStatusFlags = ProcGlobal->statusFlags;
+		const XidCacheStatus *subxidStates = ProcGlobal->subxidStates;
+		const uint8 *allStatusFlags = ProcGlobal->statusFlags;
+		const int  *pgprocnos = arrayP->pgprocnos;
+		int			numProcs = arrayP->numProcs;
+		int			pgxactoff;
 
 		/*
 		 * First collect set of pgxactoff/xids that need to be included in the
 		 * snapshot.
 		 */
-		for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+		for (pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
 		{
 			/* Fetch xid just once - see GetNewTransactionId */
 			TransactionId xid = UINT32_ACCESS_ONCE(other_xids[pgxactoff]);
@@ -2339,7 +2358,7 @@ GetSnapshotData(Snapshot snapshot)
 					if (nsubxids > 0)
 					{
 						int			pgprocno = pgprocnos[pgxactoff];
-						PGPROC	   *proc = &allProcs[pgprocno];
+						const PGPROC *proc = &allProcs[pgprocno];
 
 						pg_read_barrier();	/* pairs with GetNewTransactionId */
 
@@ -2527,21 +2546,26 @@ bool
 ProcArrayInstallImportedXmin(TransactionId xmin,
 							 VirtualTransactionId *sourcevxid)
 {
-	bool		result = false;
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP;
+	int			numProcs;
 	int			index;
+	bool		result;
 
 	Assert(TransactionIdIsNormal(xmin));
 	if (!sourcevxid)
 		return false;
 
+	arrayP = procArray;
+	numProcs = arrayP->numProcs;
+	result = false;
+
 	/* Get lock so source xact can't end while we're doing this */
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 		int			statusFlags = ProcGlobal->statusFlags[index];
 		TransactionId xid;
 
@@ -2673,6 +2697,7 @@ GetRunningTransactionData(void)
 	TransactionId latestCompletedXid;
 	TransactionId oldestRunningXid;
 	TransactionId *xids;
+	int			numProcs = arrayP->numProcs;
 	int			index;
 	int			count;
 	int			subcount;
@@ -2722,7 +2747,7 @@ GetRunningTransactionData(void)
 	/*
 	 * Spin over procArray collecting all xids
 	 */
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		TransactionId xid;
 
@@ -2766,10 +2791,10 @@ GetRunningTransactionData(void)
 	{
 		XidCacheStatus *other_subxidstates = ProcGlobal->subxidStates;
 
-		for (index = 0; index < arrayP->numProcs; index++)
+		for (index = 0; index < numProcs; index++)
 		{
 			int			pgprocno = arrayP->pgprocnos[index];
-			PGPROC	   *proc = &allProcs[pgprocno];
+			const PGPROC *proc = &allProcs[pgprocno];
 			int			nsubxids;
 
 			/*
@@ -2839,9 +2864,10 @@ GetRunningTransactionData(void)
 TransactionId
 GetOldestActiveTransactionId(void)
 {
-	ProcArrayStruct *arrayP = procArray;
-	TransactionId *other_xids = ProcGlobal->xids;
+	const ProcArrayStruct *arrayP = procArray;
+	const TransactionId *other_xids = ProcGlobal->xids;
 	TransactionId oldestRunningXid;
+	int			numProcs = arrayP->numProcs;
 	int			index;
 
 	Assert(!RecoveryInProgress());
@@ -2861,7 +2887,7 @@ GetOldestActiveTransactionId(void)
 	 * Spin over procArray collecting all xids and subxids.
 	 */
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		TransactionId xid;
 
@@ -2904,9 +2930,8 @@ GetOldestActiveTransactionId(void)
 TransactionId
 GetOldestSafeDecodingTransactionId(bool catalogOnly)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
 	TransactionId oldestSafeXid;
-	int			index;
 	bool		recovery_in_progress = RecoveryInProgress();
 
 	Assert(LWLockHeldByMe(ProcArrayLock));
@@ -2929,16 +2954,16 @@ GetOldestSafeDecodingTransactionId(bool catalogOnly)
 	 * slot's general xmin horizon, but the catalog horizon is only usable
 	 * when only catalog data is going to be looked at.
 	 */
-	if (TransactionIdIsValid(procArray->replication_slot_xmin) &&
-		TransactionIdPrecedes(procArray->replication_slot_xmin,
+	if (TransactionIdIsValid(arrayP->replication_slot_xmin) &&
+		TransactionIdPrecedes(arrayP->replication_slot_xmin,
 							  oldestSafeXid))
-		oldestSafeXid = procArray->replication_slot_xmin;
+		oldestSafeXid = arrayP->replication_slot_xmin;
 
 	if (catalogOnly &&
-		TransactionIdIsValid(procArray->replication_slot_catalog_xmin) &&
-		TransactionIdPrecedes(procArray->replication_slot_catalog_xmin,
+		TransactionIdIsValid(arrayP->replication_slot_catalog_xmin) &&
+		TransactionIdPrecedes(arrayP->replication_slot_catalog_xmin,
 							  oldestSafeXid))
-		oldestSafeXid = procArray->replication_slot_catalog_xmin;
+		oldestSafeXid = arrayP->replication_slot_catalog_xmin;
 
 	/*
 	 * If we're not in recovery, we walk over the procarray and collect the
@@ -2954,12 +2979,14 @@ GetOldestSafeDecodingTransactionId(bool catalogOnly)
 	 */
 	if (!recovery_in_progress)
 	{
-		TransactionId *other_xids = ProcGlobal->xids;
+		const TransactionId *other_xids = ProcGlobal->xids;
+		int			numProcs = arrayP->numProcs;
+		int			index;
 
 		/*
 		 * Spin over procArray collecting min(ProcGlobal->xids[i])
 		 */
-		for (index = 0; index < arrayP->numProcs; index++)
+		for (index = 0; index < numProcs; index++)
 		{
 			TransactionId xid;
 
@@ -3000,8 +3027,9 @@ GetOldestSafeDecodingTransactionId(bool catalogOnly)
 VirtualTransactionId *
 GetVirtualXIDsDelayingChkpt(int *nvxids)
 {
+	const ProcArrayStruct *arrayP = procArray;
 	VirtualTransactionId *vxids;
-	ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
@@ -3011,10 +3039,10 @@ GetVirtualXIDsDelayingChkpt(int *nvxids)
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 
 		if (proc->delayChkpt)
 		{
@@ -3044,16 +3072,17 @@ GetVirtualXIDsDelayingChkpt(int *nvxids)
 bool
 HaveVirtualXIDsDelayingChkpt(VirtualTransactionId *vxids, int nvxids)
 {
-	bool		result = false;
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			index;
+	bool		result = false;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 		VirtualTransactionId vxid;
 
 		GET_VXID_FROM_PGPROC(vxid, *proc);
@@ -3113,25 +3142,26 @@ BackendPidGetProc(int pid)
 PGPROC *
 BackendPidGetProcWithLock(int pid)
 {
-	PGPROC	   *result = NULL;
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP;
+	int			numProcs;
 	int			index;
 
 	if (pid == 0)				/* never match dummy PGPROCs */
 		return NULL;
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	arrayP = procArray;
+	numProcs = arrayP->numProcs;
+	for (index = 0; index < numProcs; index++)
 	{
-		PGPROC	   *proc = &allProcs[arrayP->pgprocnos[index]];
+		const PGPROC *proc = &allProcs[arrayP->pgprocnos[index]];
 
 		if (proc->pid == pid)
 		{
-			result = proc;
-			break;
+			return proc;
 		}
 	}
 
-	return result;
+	return NULL;
 }
 
 /*
@@ -3150,31 +3180,29 @@ BackendPidGetProcWithLock(int pid)
 int
 BackendXidGetPid(TransactionId xid)
 {
-	int			result = 0;
-	ProcArrayStruct *arrayP = procArray;
-	TransactionId *other_xids = ProcGlobal->xids;
+	const ProcArrayStruct *arrayP;
+	const TransactionId *other_xids;
+	int			numProcs;
 	int			index;
 
 	if (xid == InvalidTransactionId)	/* never match invalid xid */
 		return 0;
 
-	LWLockAcquire(ProcArrayLock, LW_SHARED);
-
-	for (index = 0; index < arrayP->numProcs; index++)
+	arrayP = procArray;
+	other_xids = ProcGlobal->xids;
+	numProcs = arrayP->numProcs;
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 
 		if (other_xids[index] == xid)
 		{
-			result = proc->pid;
-			break;
+			return proc->pid;
 		}
 	}
 
-	LWLockRelease(ProcArrayLock);
-
-	return result;
+	return 0;
 }
 
 /*
@@ -3221,7 +3249,8 @@ GetCurrentVirtualXIDs(TransactionId limitXmin, bool excludeXmin0,
 					  int *nvxids)
 {
 	VirtualTransactionId *vxids;
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
@@ -3231,10 +3260,10 @@ GetCurrentVirtualXIDs(TransactionId limitXmin, bool excludeXmin0,
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 		uint8		statusFlags = ProcGlobal->statusFlags[index];
 
 		if (proc == MyProc)
@@ -3246,7 +3275,7 @@ GetCurrentVirtualXIDs(TransactionId limitXmin, bool excludeXmin0,
 		if (allDbs || proc->databaseId == MyDatabaseId)
 		{
 			/* Fetch xmin just once - might change on us */
-			TransactionId pxmin = UINT32_ACCESS_ONCE(proc->xmin);
+			const TransactionId pxmin = UINT32_ACCESS_ONCE(proc->xmin);
 
 			if (excludeXmin0 && !TransactionIdIsValid(pxmin))
 				continue;
@@ -3307,7 +3336,8 @@ VirtualTransactionId *
 GetConflictingVirtualXIDs(TransactionId limitXmin, Oid dbOid)
 {
 	static VirtualTransactionId *vxids;
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
@@ -3328,10 +3358,10 @@ GetConflictingVirtualXIDs(TransactionId limitXmin, Oid dbOid)
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 
 		/* Exclude prepared transactions */
 		if (proc->pid == 0)
@@ -3341,7 +3371,7 @@ GetConflictingVirtualXIDs(TransactionId limitXmin, Oid dbOid)
 			proc->databaseId == dbOid)
 		{
 			/* Fetch xmin just once - can't change on us, but good coding */
-			TransactionId pxmin = UINT32_ACCESS_ONCE(proc->xmin);
+			const TransactionId pxmin = UINT32_ACCESS_ONCE(proc->xmin);
 
 			/*
 			 * We ignore an invalid pxmin because this means that backend has
@@ -3387,13 +3417,14 @@ pid_t
 SignalVirtualTransaction(VirtualTransactionId vxid, ProcSignalReason sigmode,
 						 bool conflictPending)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			index;
 	pid_t		pid = 0;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
 		PGPROC	   *proc = &allProcs[pgprocno];
@@ -3435,8 +3466,9 @@ SignalVirtualTransaction(VirtualTransactionId vxid, ProcSignalReason sigmode,
 bool
 MinimumActiveBackends(int min)
 {
-	ProcArrayStruct *arrayP = procArray;
-	int			count = 0;
+	ProcArrayStruct *arrayP;
+	int			count;
+	int			numProcs;
 	int			index;
 
 	/* Quick short-circuit if no minimum is specified */
@@ -3448,10 +3480,13 @@ MinimumActiveBackends(int min)
 	 * bogus, but since we are only testing fields for zero or nonzero, it
 	 * should be OK.  The result is only used for heuristic purposes anyway...
 	 */
-	for (index = 0; index < arrayP->numProcs; index++)
+	count = 0;
+	arrayP = procArray;
+	numProcs = arrayP->numProcs;
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 
 		/*
 		 * Since we're not holding a lock, need to be prepared to deal with
@@ -3488,16 +3523,17 @@ MinimumActiveBackends(int min)
 int
 CountDBBackends(Oid databaseid)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 
 		if (proc->pid == 0)
 			continue;			/* do not count prepared xacts */
@@ -3518,16 +3554,17 @@ CountDBBackends(Oid databaseid)
 int
 CountDBConnections(Oid databaseid)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 
 		if (proc->pid == 0)
 			continue;			/* do not count prepared xacts */
@@ -3549,15 +3586,16 @@ CountDBConnections(Oid databaseid)
 void
 CancelDBBackends(Oid databaseid, ProcSignalReason sigmode, bool conflictPending)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			index;
 
 	/* tell all backends to die */
 	LWLockAcquire(ProcArrayLock, LW_EXCLUSIVE);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
-		int			pgprocno = arrayP->pgprocnos[index];
+		const int	pgprocno = arrayP->pgprocnos[index];
 		PGPROC	   *proc = &allProcs[pgprocno];
 
 		if (databaseid == InvalidOid || proc->databaseId == databaseid)
@@ -3589,16 +3627,17 @@ CancelDBBackends(Oid databaseid, ProcSignalReason sigmode, bool conflictPending)
 int
 CountUserBackends(Oid roleid)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
+	int			numProcs = arrayP->numProcs;
 	int			count = 0;
 	int			index;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (index = 0; index < arrayP->numProcs; index++)
+	for (index = 0; index < numProcs; index++)
 	{
 		int			pgprocno = arrayP->pgprocnos[index];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 
 		if (proc->pid == 0)
 			continue;			/* do not count prepared xacts */
@@ -3639,7 +3678,7 @@ CountUserBackends(Oid roleid)
 bool
 CountOtherDBBackends(Oid databaseId, int *nbackends, int *nprepared)
 {
-	ProcArrayStruct *arrayP = procArray;
+	const ProcArrayStruct *arrayP = procArray;
 
 #define MAXAUTOVACPIDS	10		/* max autovacs to SIGTERM per iteration */
 	int			autovac_pids[MAXAUTOVACPIDS];
@@ -3648,9 +3687,10 @@ CountOtherDBBackends(Oid databaseId, int *nbackends, int *nprepared)
 	/* 50 tries with 100ms sleep between tries makes 5 sec total wait */
 	for (tries = 0; tries < 50; tries++)
 	{
+		int			numProcs = arrayP->numProcs;
+		int			index;
 		int			nautovacs = 0;
 		bool		found = false;
-		int			index;
 
 		CHECK_FOR_INTERRUPTS();
 
@@ -3658,10 +3698,10 @@ CountOtherDBBackends(Oid databaseId, int *nbackends, int *nprepared)
 
 		LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-		for (index = 0; index < arrayP->numProcs; index++)
+		for (index = 0; index < numProcs; index++)
 		{
 			int			pgprocno = arrayP->pgprocnos[index];
-			PGPROC	   *proc = &allProcs[pgprocno];
+			const PGPROC *proc = &allProcs[pgprocno];
 			uint8		statusFlags = ProcGlobal->statusFlags[index];
 
 			if (proc->databaseId != databaseId)
@@ -3718,16 +3758,17 @@ void
 TerminateOtherDBBackends(Oid databaseId)
 {
 	ProcArrayStruct *arrayP = procArray;
-	List	   *pids = NIL;
+	const List *pids = NIL;
+	int			numProcs = procArray->numProcs;
 	int			nprepared = 0;
 	int			i;
 
 	LWLockAcquire(ProcArrayLock, LW_SHARED);
 
-	for (i = 0; i < procArray->numProcs; i++)
+	for (i = 0; i < numProcs; i++)
 	{
 		int			pgprocno = arrayP->pgprocnos[i];
-		PGPROC	   *proc = &allProcs[pgprocno];
+		const PGPROC *proc = &allProcs[pgprocno];
 
 		if (proc->databaseId != databaseId)
 			continue;
@@ -3769,7 +3810,7 @@ TerminateOtherDBBackends(Oid databaseId)
 		foreach(lc, pids)
 		{
 			int			pid = lfirst_int(lc);
-			PGPROC	   *proc = BackendPidGetProc(pid);
+			const PGPROC *proc = BackendPidGetProc(pid);
 
 			if (proc != NULL)
 			{
@@ -3797,7 +3838,7 @@ TerminateOtherDBBackends(Oid databaseId)
 		foreach(lc, pids)
 		{
 			int			pid = lfirst_int(lc);
-			PGPROC	   *proc = BackendPidGetProc(pid);
+			const PGPROC *proc = BackendPidGetProc(pid);
 
 			if (proc != NULL)
 			{
#8Ranier Vilela
ranier.vf@gmail.com
In reply to: Aleksander Alekseev (#7)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em qui., 15 de jul. de 2021 às 08:38, Aleksander Alekseev <
aleksander@timescale.com> escreveu:

Hi hackers,

Patch attached.

Added to next CF (https://commitfest.postgresql.org/33/3169/)

Hi Aleksander, thanks for taking a look at this.

The proposed code casts `const` variables to non-`const`. I'm surprised
MSVC misses it.

I lost where. Can you show me?

Also, there were some issues with the code formatting. The corrected patch
is attached.

Sorry, thanks for correcting.

The patch is listed under the "Performance" topic on CF. However, I can't
verify any changes in the performance because there were no benchmarks
attached that I could reproduce. By looking at the code and the first
message in the thread, I assume this is in fact a refactoring.

My mistake, a serious fault.
But the benchmark came from:
pgbench -i -p 5432 -d postgres
pgbench -c 50 -T 300 -S -n

Personally I don't believe that changes like:

-               for (int i = 0; i < nxids; i++)
+               int     i;
+               for (i = 0; i < nxids; i++)

Yeah, it seems to me that this style will be consolidated in Postgres 'for
(int i = 0;'.

.. or:

-       for (int index = myoff; index < arrayP->numProcs; index++)
+       numProcs = arrayP->numProcs;
+       for (index = myoff; index < numProcs; index++)

The rationale here is to cache arrayP->numProcs to local variable, which
improves performance.

... are of any value, but other changes may be. I choose to keep the patch
as-is except for the named defects and let the committer decide which
changes, if any, are worth committing.

I'm updating the status to "Ready for Committer".

Thank you.

regards,
Ranier Vilela

#9David Rowley
dgrowleyml@gmail.com
In reply to: Aleksander Alekseev (#7)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

On Thu, 15 Jul 2021 at 23:38, Aleksander Alekseev
<aleksander@timescale.com> wrote:

I'm updating the status to "Ready for Committer".

I think that might be a bit premature. I can't quite see how changing
the pids List to a const List makes any sense, especially when the
code goes and calls lappend_int() on it to assign it some different
value.

There are also problems in BackendPidGetProcWithLock around consts.

Much of this patch kinda feels like another one of those "I've got a
fancy new static analyzer" patches. Unfortunately, it just introduces
a bunch of compiler warnings as a result of the changes it makes.

I'd suggest splitting each portion of the patch out into parts related
to what it aims to achieve. For example, it looks like there's some
renaming going on to remove a local variable from shadowing a function
parameter. Yet the patch is claiming performance improvements. I
don't see how that part relates to performance. The changes to
ProcArrayClearTransaction() seem also unrelated to performance.

I'm not sure what the point of changing things like for (int i =0...
to move the variable declaration somewhere else is about. That just
seems like needless stylistic changes that achieve nothing but more
headaches for committers doing backpatching work.

I'd say if this patch wants to be taken seriously it better decide
what it's purpose is, because to me it looks just like a jumble of
random changes that have no clear purpose.

I'm going to set this back to waiting on author.

David

#10Ranier Vilela
ranier.vf@gmail.com
In reply to: David Rowley (#9)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em qui., 15 de jul. de 2021 às 09:45, David Rowley <dgrowleyml@gmail.com>
escreveu:

On Thu, 15 Jul 2021 at 23:38, Aleksander Alekseev
<aleksander@timescale.com> wrote:

I'm updating the status to "Ready for Committer".

I think that might be a bit premature. I can't quite see how changing
the pids List to a const List makes any sense, especially when the
code goes and calls lappend_int() on it to assign it some different
value.

There are also problems in BackendPidGetProcWithLock around consts.

Much of this patch kinda feels like another one of those "I've got a
fancy new static analyzer" patches. Unfortunately, it just introduces
a bunch of compiler warnings as a result of the changes it makes.

I'd suggest splitting each portion of the patch out into parts related
to what it aims to achieve. For example, it looks like there's some
renaming going on to remove a local variable from shadowing a function
parameter. Yet the patch is claiming performance improvements. I
don't see how that part relates to performance. The changes to
ProcArrayClearTransaction() seem also unrelated to performance.

I'm not sure what the point of changing things like for (int i =0...
to move the variable declaration somewhere else is about. That just
seems like needless stylistic changes that achieve nothing but more
headaches for committers doing backpatching work.

I'd say if this patch wants to be taken seriously it better decide
what it's purpose is, because to me it looks just like a jumble of
random changes that have no clear purpose.

I'm going to set this back to waiting on author.

I understood.
I will try to address all concerns in the new version.

regards,
Ranier Vilela

#11Aleksander Alekseev
aleksander@timescale.com
In reply to: David Rowley (#9)
1 attachment(s)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Thanks, David.

I lost where. Can you show me?

See the attached warnings.txt.

But the benchmark came from:
pgbench -i -p 5432 -d postgres
pgbench -c 50 -T 300 -S -n

I'm afraid this tells nothing unless you also provide the
configuration files and the hardware description, and also some
information on how you checked that there is no performance
degradation on all the other supported platforms and possible
configurations. Benchmarking is a very complicated topic - trust me,
been there!

It would be better to submit two separate patches, the one that
addresses Size_t and another that addresses shadowing. Refactorings
only, nothing else.

Regarding the code formatting, please see src/tools/pgindent.

--
Best regards,
Aleksander Alekseev

Attachments:

warnings.txttext/plain; charset=US-ASCII; name=warnings.txtDownload
#12Ranier Vilela
ranier.vf@gmail.com
In reply to: Aleksander Alekseev (#11)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em qui., 15 de jul. de 2021 às 10:01, Aleksander Alekseev <
aleksander@timescale.com> escreveu:

Thanks, David.

I lost where. Can you show me?

See the attached warnings.txt.

Thank you.

But the benchmark came from:
pgbench -i -p 5432 -d postgres
pgbench -c 50 -T 300 -S -n

I'm afraid this tells nothing unless you also provide the
configuration files and the hardware description, and also some
information on how you checked that there is no performance
degradation on all the other supported platforms and possible
configurations.

Benchmarking is a very complicated topic - trust me,
been there!

Absolutely.

It would be better to submit two separate patches, the one that
addresses Size_t and another that addresses shadowing. Refactorings
only, nothing else.

Regarding the code formatting, please see src/tools/pgindent.

I will try.

regards,
Ranier Vilela

#13Ranier Vilela
ranier.vf@gmail.com
In reply to: Ranier Vilela (#12)
2 attachment(s)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em qui., 15 de jul. de 2021 às 10:04, Ranier Vilela <ranier.vf@gmail.com>
escreveu:

Em qui., 15 de jul. de 2021 às 10:01, Aleksander Alekseev <
aleksander@timescale.com> escreveu:

Thanks, David.

I lost where. Can you show me?

See the attached warnings.txt.

Thank you.

But the benchmark came from:
pgbench -i -p 5432 -d postgres
pgbench -c 50 -T 300 -S -n

I'm afraid this tells nothing unless you also provide the
configuration files and the hardware description, and also some
information on how you checked that there is no performance
degradation on all the other supported platforms and possible
configurations.

Benchmarking is a very complicated topic - trust me,
been there!

Absolutely.

It would be better to submit two separate patches, the one that
addresses Size_t and another that addresses shadowing. Refactorings
only, nothing else.

Regarding the code formatting, please see src/tools/pgindent.

I will try.

Here are the two patches.
As suggested, reclassified as refactoring only.

regards,
Ranier Vilela

Attachments:

0001-Promove-unshadowing-of-two-variables-PGPROC-type.patchtext/x-patch; charset=US-ASCII; name=0001-Promove-unshadowing-of-two-variables-PGPROC-type.patchDownload
From 57eaa5fa92489b217239ec44e2ccf83556a1da4f Mon Sep 17 00:00:00 2001
From: Ranier Vilela <ranier.vf@gmail.com>
Date: Thu, 15 Jul 2021 21:36:21 -0300
Subject: [PATCH] Promove unshadowing of two variables PGPROC type.

ProcArrayGroupClearXid function has a parameter already named *proc*,
When declaring a local variable with the same name, people may get confused when using them.
Better to rename local variables to nextproc and maintain readability.

No need to backpatch, this patch is classified as refactoring only.
---
 src/backend/storage/ipc/procarray.c | 18 +++++++++---------
 1 file changed, 9 insertions(+), 9 deletions(-)

diff --git a/src/backend/storage/ipc/procarray.c b/src/backend/storage/ipc/procarray.c
index 4c91e721d0..286132c696 100644
--- a/src/backend/storage/ipc/procarray.c
+++ b/src/backend/storage/ipc/procarray.c
@@ -829,12 +829,12 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	/* Walk the list and clear all XIDs. */
 	while (nextidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[nextidx];
+		PGPROC	   *nextproc = &allProcs[nextidx];
 
-		ProcArrayEndTransactionInternal(proc, proc->procArrayGroupMemberXid);
+		ProcArrayEndTransactionInternal(nextproc, proc->procArrayGroupMemberXid);
 
 		/* Move to next proc in list. */
-		nextidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
+		nextidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
 	}
 
 	/* We're done with the lock now. */
@@ -849,18 +849,18 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	 */
 	while (wakeidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[wakeidx];
+		PGPROC	   *nextproc = &allProcs[wakeidx];
 
-		wakeidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
-		pg_atomic_write_u32(&proc->procArrayGroupNext, INVALID_PGPROCNO);
+		wakeidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
+		pg_atomic_write_u32(&nextproc->procArrayGroupNext, INVALID_PGPROCNO);
 
 		/* ensure all previous writes are visible before follower continues. */
 		pg_write_barrier();
 
-		proc->procArrayGroupMember = false;
+		nextproc->procArrayGroupMember = false;
 
-		if (proc != MyProc)
-			PGSemaphoreUnlock(proc->sem);
+		if (nextproc != MyProc)
+			PGSemaphoreUnlock(nextproc->sem);
 	}
 }
 
-- 
2.25.1

0001-Reduce-Wsign-compare-warnings-from-clang-12-compiler.patchtext/x-patch; charset=US-ASCII; name=0001-Reduce-Wsign-compare-warnings-from-clang-12-compiler.patchDownload
From fafb23a62835f7d35bd3f4642b06253cf16cbfca Mon Sep 17 00:00:00 2001
From: Ranier Vilela <ranier.vf@gmail.com>
Date: Thu, 15 Jul 2021 21:40:20 -0300
Subject: [PATCH] Reduce Wsign-compare warnings from clang-12 compiler.

All size_t variables declared in procarray.c, are true ints.
Lets promove a changes for int, reducing warnings like
"comparison of integers of different signs".

No need to backpatch, why this patch is classified as
refactoring only.
---
 src/backend/storage/ipc/procarray.c | 14 +++++++-------
 1 file changed, 7 insertions(+), 7 deletions(-)

diff --git a/src/backend/storage/ipc/procarray.c b/src/backend/storage/ipc/procarray.c
index 286132c696..efb489bc5d 100644
--- a/src/backend/storage/ipc/procarray.c
+++ b/src/backend/storage/ipc/procarray.c
@@ -703,7 +703,7 @@ ProcArrayEndTransaction(PGPROC *proc, TransactionId latestXid)
 static inline void
 ProcArrayEndTransactionInternal(PGPROC *proc, TransactionId latestXid)
 {
-	size_t		pgxactoff = proc->pgxactoff;
+	int			pgxactoff = proc->pgxactoff;
 
 	/*
 	 * Note: we need exclusive lock here because we're going to change other
@@ -875,7 +875,7 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 void
 ProcArrayClearTransaction(PGPROC *proc)
 {
-	size_t		pgxactoff;
+	int			pgxactoff;
 
 	/*
 	 * Currently we need to lock ProcArrayLock exclusively here, as we
@@ -1355,7 +1355,7 @@ TransactionIdIsInProgress(TransactionId xid)
 	TransactionId topxid;
 	TransactionId latestCompletedXid;
 	int			mypgxactoff;
-	size_t		numProcs;
+	int			numProcs;
 	int			j;
 
 	/*
@@ -1432,7 +1432,7 @@ TransactionIdIsInProgress(TransactionId xid)
 	/* No shortcuts, gotta grovel through the array */
 	mypgxactoff = MyProc->pgxactoff;
 	numProcs = arrayP->numProcs;
-	for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+	for (int pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
 	{
 		int			pgprocno;
 		PGPROC	   *proc;
@@ -2167,7 +2167,7 @@ GetSnapshotData(Snapshot snapshot)
 	TransactionId *other_xids = ProcGlobal->xids;
 	TransactionId xmin;
 	TransactionId xmax;
-	size_t		count = 0;
+	int			count = 0;
 	int			subcount = 0;
 	bool		suboverflowed = false;
 	FullTransactionId latest_completed;
@@ -2249,7 +2249,7 @@ GetSnapshotData(Snapshot snapshot)
 
 	if (!snapshot->takenDuringRecovery)
 	{
-		size_t		numProcs = arrayP->numProcs;
+		int			numProcs = arrayP->numProcs;
 		TransactionId *xip = snapshot->xip;
 		int		   *pgprocnos = arrayP->pgprocnos;
 		XidCacheStatus *subxidStates = ProcGlobal->subxidStates;
@@ -2259,7 +2259,7 @@ GetSnapshotData(Snapshot snapshot)
 		 * First collect set of pgxactoff/xids that need to be included in the
 		 * snapshot.
 		 */
-		for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+		for (int pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
 		{
 			/* Fetch xid just once - see GetNewTransactionId */
 			TransactionId xid = UINT32_ACCESS_ONCE(other_xids[pgxactoff]);
-- 
2.25.1

#14Aleksander Alekseev
aleksander@timescale.com
In reply to: Ranier Vilela (#13)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Hi Rainer,

Here are the two patches.
As suggested, reclassified as refactoring only.

Please don't change the status of the patch on CF application before
it was reviewed. It will only slow things down.

Your patch seems to have some problems on FreeBSD. Please see
http://commitfest.cputube.org/

--
Best regards,
Aleksander Alekseev

#15Ranier Vilela
ranier.vf@gmail.com
In reply to: Aleksander Alekseev (#14)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em sex., 16 de jul. de 2021 às 09:05, Aleksander Alekseev <
aleksander@timescale.com> escreveu:

Hi Rainer,

Here are the two patches.
As suggested, reclassified as refactoring only.

Please don't change the status of the patch on CF application before
it was reviewed. It will only slow things down.

Hi Aleksander,
Sorry, lack of practice.

Your patch seems to have some problems on FreeBSD. Please see
http://commitfest.cputube.org/

I saw.
Very strange, in all other architectures, it went well.
I will have to install a FreeBSD to be able to debug.

Thanks for your review.

best regards,
Ranier Vilela

#16Ranier Vilela
ranier.vf@gmail.com
In reply to: Ranier Vilela (#15)
1 attachment(s)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em sex., 16 de jul. de 2021 às 09:41, Ranier Vilela <ranier.vf@gmail.com>
escreveu:

Em sex., 16 de jul. de 2021 às 09:05, Aleksander Alekseev <
aleksander@timescale.com> escreveu:

Hi Rainer,

Here are the two patches.
As suggested, reclassified as refactoring only.

Please don't change the status of the patch on CF application before
it was reviewed. It will only slow things down.

Hi Aleksander,
Sorry, lack of practice.

Your patch seems to have some problems on FreeBSD. Please see
http://commitfest.cputube.org/

I saw.
Very strange, in all other architectures, it went well.
I will have to install a FreeBSD to be able to debug.

There are a typo in
0001-Promove-unshadowing-of-two-variables-PGPROC-type.patch

- ProcArrayEndTransactionInternal(proc, proc->procArrayGroupMemberXid);
+ ProcArrayEndTransactionInternal(nextproc,
nextproc->procArrayGroupMemberXid);

Attached new version v1, with fix.
Now pass check-world at FreeBSD 13 with clang 11.

regards,
Ranier Vilela

Attachments:

v1-0001-Promove-unshadowing-of-two-variables-PGPROC-type.patchapplication/octet-stream; name=v1-0001-Promove-unshadowing-of-two-variables-PGPROC-type.patchDownload
From 57eaa5fa92489b217239ec44e2ccf83556a1da4f Mon Sep 17 00:00:00 2001
From: Ranier Vilela <ranier.vf@gmail.com>
Date: Thu, 20 Jul 2021 18:56:11 -0300
Subject: [PATCH v1] Promove unshadowing of two variables PGPROC type.

ProcArrayGroupClearXid function has a parameter already named *proc*,
When declaring a local variable with the same name, people may get confused when using them.
Better to rename local variables to nextproc and maintain readability.

No need to backpatch, this patch is classified as refactoring only.
---
 src/backend/storage/ipc/procarray.c | 18 +++++++++---------
 1 file changed, 9 insertions(+), 9 deletions(-)

diff --git a/src/backend/storage/ipc/procarray.c b/src/backend/storage/ipc/procarray.c
index 4c91e721d0..286132c696 100644
--- a/src/backend/storage/ipc/procarray.c
+++ b/src/backend/storage/ipc/procarray.c
@@ -829,12 +829,12 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	/* Walk the list and clear all XIDs. */
 	while (nextidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[nextidx];
+		PGPROC	   *nextproc = &allProcs[nextidx];
 
-		ProcArrayEndTransactionInternal(proc, proc->procArrayGroupMemberXid);
+		ProcArrayEndTransactionInternal(nextproc, nextproc->procArrayGroupMemberXid);
 
 		/* Move to next proc in list. */
-		nextidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
+		nextidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
 	}
 
 	/* We're done with the lock now. */
@@ -849,18 +849,18 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	 */
 	while (wakeidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[wakeidx];
+		PGPROC	   *nextproc = &allProcs[wakeidx];
 
-		wakeidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
-		pg_atomic_write_u32(&proc->procArrayGroupNext, INVALID_PGPROCNO);
+		wakeidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
+		pg_atomic_write_u32(&nextproc->procArrayGroupNext, INVALID_PGPROCNO);
 
 		/* ensure all previous writes are visible before follower continues. */
 		pg_write_barrier();
 
-		proc->procArrayGroupMember = false;
+		nextproc->procArrayGroupMember = false;
 
-		if (proc != MyProc)
-			PGSemaphoreUnlock(proc->sem);
+		if (nextproc != MyProc)
+			PGSemaphoreUnlock(nextproc->sem);
 	}
 }
 
-- 
2.25.1

#17Aleksander Alekseev
aleksander@timescale.com
In reply to: Ranier Vilela (#16)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

The following review has been posted through the commitfest application:
make installcheck-world: tested, passed
Implements feature: tested, passed
Spec compliant: tested, passed
Documentation: tested, passed

The patch was tested on MacOS against master `80ba4bb3`.

The new status of this patch is: Ready for Committer

#18Aleksander Alekseev
aleksander@timescale.com
In reply to: Aleksander Alekseev (#17)
2 attachment(s)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Hi hackers,

The following review has been posted through the commitfest application:

make installcheck-world: tested, passed
Implements feature: tested, passed
Spec compliant: tested, passed
Documentation: tested, passed

The patch was tested on MacOS against master `80ba4bb3`.

The new status of this patch is: Ready for Committer

The second patch seems fine too. I'm attaching both patches to trigger
cfbot and to double-check them.

--
Best regards,
Aleksander Alekseev

Attachments:

0002-Promove-unshadowing-of-two-variables-PGPROC-type.patchapplication/octet-stream; name=0002-Promove-unshadowing-of-two-variables-PGPROC-type.patchDownload
From 57eaa5fa92489b217239ec44e2ccf83556a1da4f Mon Sep 17 00:00:00 2001
From: Ranier Vilela <ranier.vf@gmail.com>
Date: Thu, 20 Jul 2021 18:56:11 -0300
Subject: [PATCH v1] Promove unshadowing of two variables PGPROC type.

ProcArrayGroupClearXid function has a parameter already named *proc*,
When declaring a local variable with the same name, people may get confused when using them.
Better to rename local variables to nextproc and maintain readability.

No need to backpatch, this patch is classified as refactoring only.
---
 src/backend/storage/ipc/procarray.c | 18 +++++++++---------
 1 file changed, 9 insertions(+), 9 deletions(-)

diff --git a/src/backend/storage/ipc/procarray.c b/src/backend/storage/ipc/procarray.c
index 4c91e721d0..286132c696 100644
--- a/src/backend/storage/ipc/procarray.c
+++ b/src/backend/storage/ipc/procarray.c
@@ -829,12 +829,12 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	/* Walk the list and clear all XIDs. */
 	while (nextidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[nextidx];
+		PGPROC	   *nextproc = &allProcs[nextidx];
 
-		ProcArrayEndTransactionInternal(proc, proc->procArrayGroupMemberXid);
+		ProcArrayEndTransactionInternal(nextproc, nextproc->procArrayGroupMemberXid);
 
 		/* Move to next proc in list. */
-		nextidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
+		nextidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
 	}
 
 	/* We're done with the lock now. */
@@ -849,18 +849,18 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 	 */
 	while (wakeidx != INVALID_PGPROCNO)
 	{
-		PGPROC	   *proc = &allProcs[wakeidx];
+		PGPROC	   *nextproc = &allProcs[wakeidx];
 
-		wakeidx = pg_atomic_read_u32(&proc->procArrayGroupNext);
-		pg_atomic_write_u32(&proc->procArrayGroupNext, INVALID_PGPROCNO);
+		wakeidx = pg_atomic_read_u32(&nextproc->procArrayGroupNext);
+		pg_atomic_write_u32(&nextproc->procArrayGroupNext, INVALID_PGPROCNO);
 
 		/* ensure all previous writes are visible before follower continues. */
 		pg_write_barrier();
 
-		proc->procArrayGroupMember = false;
+		nextproc->procArrayGroupMember = false;
 
-		if (proc != MyProc)
-			PGSemaphoreUnlock(proc->sem);
+		if (nextproc != MyProc)
+			PGSemaphoreUnlock(nextproc->sem);
 	}
 }
 
-- 
2.25.1

0001-Reduce-Wsign-compare-warnings-from-clang-12-compiler.patchapplication/octet-stream; name=0001-Reduce-Wsign-compare-warnings-from-clang-12-compiler.patchDownload
From fafb23a62835f7d35bd3f4642b06253cf16cbfca Mon Sep 17 00:00:00 2001
From: Ranier Vilela <ranier.vf@gmail.com>
Date: Thu, 15 Jul 2021 21:40:20 -0300
Subject: [PATCH] Reduce Wsign-compare warnings from clang-12 compiler.

All size_t variables declared in procarray.c, are true ints.
Lets promove a changes for int, reducing warnings like
"comparison of integers of different signs".

No need to backpatch, why this patch is classified as
refactoring only.
---
 src/backend/storage/ipc/procarray.c | 14 +++++++-------
 1 file changed, 7 insertions(+), 7 deletions(-)

diff --git a/src/backend/storage/ipc/procarray.c b/src/backend/storage/ipc/procarray.c
index 286132c696..efb489bc5d 100644
--- a/src/backend/storage/ipc/procarray.c
+++ b/src/backend/storage/ipc/procarray.c
@@ -703,7 +703,7 @@ ProcArrayEndTransaction(PGPROC *proc, TransactionId latestXid)
 static inline void
 ProcArrayEndTransactionInternal(PGPROC *proc, TransactionId latestXid)
 {
-	size_t		pgxactoff = proc->pgxactoff;
+	int			pgxactoff = proc->pgxactoff;
 
 	/*
 	 * Note: we need exclusive lock here because we're going to change other
@@ -875,7 +875,7 @@ ProcArrayGroupClearXid(PGPROC *proc, TransactionId latestXid)
 void
 ProcArrayClearTransaction(PGPROC *proc)
 {
-	size_t		pgxactoff;
+	int			pgxactoff;
 
 	/*
 	 * Currently we need to lock ProcArrayLock exclusively here, as we
@@ -1355,7 +1355,7 @@ TransactionIdIsInProgress(TransactionId xid)
 	TransactionId topxid;
 	TransactionId latestCompletedXid;
 	int			mypgxactoff;
-	size_t		numProcs;
+	int			numProcs;
 	int			j;
 
 	/*
@@ -1432,7 +1432,7 @@ TransactionIdIsInProgress(TransactionId xid)
 	/* No shortcuts, gotta grovel through the array */
 	mypgxactoff = MyProc->pgxactoff;
 	numProcs = arrayP->numProcs;
-	for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+	for (int pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
 	{
 		int			pgprocno;
 		PGPROC	   *proc;
@@ -2167,7 +2167,7 @@ GetSnapshotData(Snapshot snapshot)
 	TransactionId *other_xids = ProcGlobal->xids;
 	TransactionId xmin;
 	TransactionId xmax;
-	size_t		count = 0;
+	int			count = 0;
 	int			subcount = 0;
 	bool		suboverflowed = false;
 	FullTransactionId latest_completed;
@@ -2249,7 +2249,7 @@ GetSnapshotData(Snapshot snapshot)
 
 	if (!snapshot->takenDuringRecovery)
 	{
-		size_t		numProcs = arrayP->numProcs;
+		int			numProcs = arrayP->numProcs;
 		TransactionId *xip = snapshot->xip;
 		int		   *pgprocnos = arrayP->pgprocnos;
 		XidCacheStatus *subxidStates = ProcGlobal->subxidStates;
@@ -2259,7 +2259,7 @@ GetSnapshotData(Snapshot snapshot)
 		 * First collect set of pgxactoff/xids that need to be included in the
 		 * snapshot.
 		 */
-		for (size_t pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
+		for (int pgxactoff = 0; pgxactoff < numProcs; pgxactoff++)
 		{
 			/* Fetch xid just once - see GetNewTransactionId */
 			TransactionId xid = UINT32_ACCESS_ONCE(other_xids[pgxactoff]);
-- 
2.25.1

#19Ranier Vilela
ranier.vf@gmail.com
In reply to: Aleksander Alekseev (#18)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em sex., 23 de jul. de 2021 às 07:02, Aleksander Alekseev <
aleksander@timescale.com> escreveu:

Hi hackers,

The following review has been posted through the commitfest application:

make installcheck-world: tested, passed
Implements feature: tested, passed
Spec compliant: tested, passed
Documentation: tested, passed

The patch was tested on MacOS against master `80ba4bb3`.

The new status of this patch is: Ready for Committer

The second patch seems fine too. I'm attaching both patches to trigger
cfbot and to double-check them.

Thanks Aleksander, for reviewing this.

regards,
Ranier Vilela

#20Fujii Masao
masao.fujii@oss.nttdata.com
In reply to: Ranier Vilela (#19)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

On 2021/07/23 20:07, Ranier Vilela wrote:

Em sex., 23 de jul. de 2021 às 07:02, Aleksander Alekseev <aleksander@timescale.com <mailto:aleksander@timescale.com>> escreveu:

Hi hackers,

The following review has been posted through the commitfest application:
make installcheck-world:  tested, passed
Implements feature:       tested, passed
Spec compliant:           tested, passed
Documentation:            tested, passed

The patch was tested on MacOS against master `80ba4bb3`.

The new status of this patch is: Ready for Committer

The second patch seems fine too. I'm attaching both patches to trigger cfbot and to double-check them.

Thanks Aleksander, for reviewing this.

I looked at these patches because they are marked as ready for committer.
They don't change any actual behavior, but look valid to me in term of coding.
Barring any objection, I will commit them.

Regards,

--
Fujii Masao
Advanced Computing Technology Center
Research and Development Headquarters
NTT DATA CORPORATION

#21Fujii Masao
masao.fujii@oss.nttdata.com
In reply to: Fujii Masao (#20)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

On 2021/09/11 12:21, Fujii Masao wrote:

On 2021/07/23 20:07, Ranier Vilela wrote:

Em sex., 23 de jul. de 2021 às 07:02, Aleksander Alekseev <aleksander@timescale.com <mailto:aleksander@timescale.com>> escreveu:

    Hi hackers,

        The following review has been posted through the commitfest application:
        make installcheck-world:  tested, passed
        Implements feature:       tested, passed
        Spec compliant:           tested, passed
        Documentation:            tested, passed

        The patch was tested on MacOS against master `80ba4bb3`.

        The new status of this patch is: Ready for Committer

    The second patch seems fine too. I'm attaching both patches to trigger cfbot and to double-check them.

Thanks Aleksander, for reviewing this.

I looked at these patches because they are marked as ready for committer.
They don't change any actual behavior, but look valid to me in term of coding.
Barring any objection, I will commit them.

No need to backpatch, why this patch is classified as
refactoring only.

I found this in the commit log in the patch. I agree that these patches
are refactoring ones. But I'm thinking that it's worth doing back-patch,
to make future back-patching easy. Thought?

Regards,

--
Fujii Masao
Advanced Computing Technology Center
Research and Development Headquarters
NTT DATA CORPORATION

#22Ranier Vilela
ranier.vf@gmail.com
In reply to: Fujii Masao (#21)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em qua., 15 de set. de 2021 às 01:08, Fujii Masao <
masao.fujii@oss.nttdata.com> escreveu:

On 2021/09/11 12:21, Fujii Masao wrote:

On 2021/07/23 20:07, Ranier Vilela wrote:

Em sex., 23 de jul. de 2021 às 07:02, Aleksander Alekseev <

aleksander@timescale.com <mailto:aleksander@timescale.com>> escreveu:

Hi hackers,

The following review has been posted through the commitfest

application:

make installcheck-world: tested, passed
Implements feature: tested, passed
Spec compliant: tested, passed
Documentation: tested, passed

The patch was tested on MacOS against master `80ba4bb3`.

The new status of this patch is: Ready for Committer

The second patch seems fine too. I'm attaching both patches to

trigger cfbot and to double-check them.

Thanks Aleksander, for reviewing this.

I looked at these patches because they are marked as ready for committer.
They don't change any actual behavior, but look valid to me in term of

coding.

Barring any objection, I will commit them.

No need to backpatch, why this patch is classified as
refactoring only.

I found this in the commit log in the patch. I agree that these patches
are refactoring ones. But I'm thinking that it's worth doing back-patch,
to make future back-patching easy. Thought?

Thanks for picking this.

I don't see anything against it being more work for the committer.

regards,
Ranier Vilela

#23Fujii Masao
masao.fujii@oss.nttdata.com
In reply to: Ranier Vilela (#22)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

On 2021/09/15 21:27, Ranier Vilela wrote:

I found this in the commit log in the patch. I agree that these patches
are refactoring ones. But I'm thinking that it's worth doing back-patch,
to make future back-patching easy. Thought?

Thanks for picking this.

Pushed. Thanks!

Regards,

--
Fujii Masao
Advanced Computing Technology Center
Research and Development Headquarters
NTT DATA CORPORATION

#24Ranier Vilela
ranier.vf@gmail.com
In reply to: Fujii Masao (#23)
Re: Signed vs Unsigned (take 2) (src/backend/storage/ipc/procarray.c)

Em qui., 16 de set. de 2021 às 01:13, Fujii Masao <
masao.fujii@oss.nttdata.com> escreveu:

On 2021/09/15 21:27, Ranier Vilela wrote:

I found this in the commit log in the patch. I agree that these

patches

are refactoring ones. But I'm thinking that it's worth doing

back-patch,

to make future back-patching easy. Thought?

Thanks for picking this.

Pushed. Thanks!

Thank you.

I will close this item if it is not already closed.

regards,
Ranier Vilela