From 3576879c54f6641790fd7376cef3674d6e21a191 Mon Sep 17 00:00:00 2001
From: Maxime Schoemans <maxime.schoemans@enterprisedb.com>
Date: Thu, 14 May 2026 19:31:08 +0200
Subject: [PATCH] numeric.c: set calcSumX2 in deserialize fns for sumX2
 aggregates

numeric_poly_deserialize and numeric_deserialize describe themselves as
the deserializers for aggregate functions that require sumX2 (var_pop,
var_samp, stddev_pop, stddev_samp, regr_*), but construct their result
with calcSumX2 = false. This is harmless in-tree because the only
follow-up call (numeric_(poly_)combine) doesn't read the flag. It
breaks any caller that runs a transition function on a deserialized
state: do_int128_accum / do_numeric_accum gate sumX2 += value * value
on state->calcSumX2, so deserialized var/stddev state silently stops
accumulating sumX2 while N and sumX continue to update.

Pass true to match the documented purpose, consistent with numeric_combine
which already sets the flag this way on its fresh state.
---
 src/backend/utils/adt/numeric.c | 4 ++--
 1 file changed, 2 insertions(+), 2 deletions(-)

diff --git a/src/backend/utils/adt/numeric.c b/src/backend/utils/adt/numeric.c
index cb23dfe9b95..4c83aa8e43f 100644
--- a/src/backend/utils/adt/numeric.c
+++ b/src/backend/utils/adt/numeric.c
@@ -5346,7 +5346,7 @@ numeric_deserialize(PG_FUNCTION_ARGS)
 	initReadOnlyStringInfo(&buf, VARDATA_ANY(sstate),
 						   VARSIZE_ANY_EXHDR(sstate));
 
-	result = makeNumericAggStateCurrentContext(false);
+	result = makeNumericAggStateCurrentContext(true);
 
 	/* N */
 	result->N = pq_getmsgint64(&buf);
@@ -5671,7 +5671,7 @@ numeric_poly_deserialize(PG_FUNCTION_ARGS)
 	initReadOnlyStringInfo(&buf, VARDATA_ANY(sstate),
 						   VARSIZE_ANY_EXHDR(sstate));
 
-	result = makeInt128AggStateCurrentContext(false);
+	result = makeInt128AggStateCurrentContext(true);
 
 	/* N */
 	result->N = pq_getmsgint64(&buf);
-- 
2.50.1 (Apple Git-155)

