Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.96) (envelope-from ) id 1wguph-006UfG-2M for pgsql-bugs@arkaria.postgresql.org; Tue, 07 Jul 2026 01:42:46 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.96) (envelope-from ) id 1wgupg-003zVT-05 for pgsql-bugs@arkaria.postgresql.org; Tue, 07 Jul 2026 01:42:44 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.96) (envelope-from ) id 1wgupf-003zVK-2M for pgsql-bugs@lists.postgresql.org; Tue, 07 Jul 2026 01:42:43 +0000 Received: from fout-b7-smtp.messagingengine.com ([202.12.124.150]) by magus.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.98.2) (envelope-from ) id 1wgupd-000000029xb-1fHY for pgsql-bugs@lists.postgresql.org; Tue, 07 Jul 2026 01:42:43 +0000 Received: from phl-compute-02.internal (phl-compute-02.internal [10.202.2.42]) by mailfout.stl.internal (Postfix) with ESMTP id 42A691D00185; Mon, 6 Jul 2026 21:42:39 -0400 (EDT) Received: from phl-frontend-03 ([10.202.2.162]) by phl-compute-02.internal (MEProxy); Mon, 06 Jul 2026 21:42:39 -0400 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=paquier.xyz; h= cc:cc:content-type:content-type:date:date:from:from:in-reply-to :in-reply-to:message-id:mime-version:references:reply-to:subject :subject:to:to; s=fm2; t=1783388559; x=1783474959; bh=FyliAXGkbC 2TlN4lUNY9nYTSDByUxup4dv0b6eYIz2M=; b=T6Xgx55ae045NIyIaXAA7QJvFj USbwebyTPAtfKrvUwBk019a69Eff/DmS1e1MtmkV/9HAw+CFAE1vPjrwxHXjN02T 7YK2hMD2NR5BI9xyySUs8eEWPJA+cyMf6qCa6jqFSa242TzWNbLDd28yIhAAGuOv uSvf1TLwlyDIytX18nZxux76Mxbhk2ZyTa0zmQEbxbMquwQkuFqhfbiz1EAP4qF6 N+133sBJXN9moS6GvxKY/kubDrtAvp0i07ciEe8qcMkjrknxTYN+QPTN2c2nN4ob 8fRYs+m57cvuB6tlzTPbI+goAG6GJjOwtKJGy/P/7rUPo6D06MWLCwacev8g== DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d= messagingengine.com; h=cc:cc:content-type:content-type:date:date :feedback-id:feedback-id:from:from:in-reply-to:in-reply-to :message-id:mime-version:references:reply-to:subject:subject:to :to:x-me-proxy:x-me-sender:x-me-sender:x-sasl-enc; s=fm2; t= 1783388559; x=1783474959; bh=FyliAXGkbC2TlN4lUNY9nYTSDByUxup4dv0 b6eYIz2M=; b=Yp6RLtGVAd5f7kTEyoQMYfSmXAJyAk6DsEPG3fjYL9pUvcg4BXX mElsHthB9AoOh0viqxm9PJK3vaItteP/k9136EUM/wg2cDT5JZ0tYa8ave+e4aFV 9VbVYw2rMTnwQQLtQVxnmVmE0PT3dfOHFei3u9EJAVKAtH7nUyne1E3+36nkpFa1 IPanudTYpatU+QDAEGtH0d01r0X5FlFlrVzZY4/TXKEHZ9Ek+qnU4GsnAc8nWb64 g3M9FPJpt8YeZ2OSLPbhBHCGsmaFvGRruXWos8sVNprjiiFOYvbg2Pg740CSoqbk CmV6rjsJAi6EQ5lMvZsb1ts99OtH1ouD9EQ== X-ME-Sender: X-ME-Received: X-ME-Proxy-Cause: dmFkZTESbMVN4jzatrlkf3BgLziXQ8eCoF56Qyg60DWv9EIRfqPt39CfDANZhZivY9rf1A /edPum2u5V1+G8rGUN15d2IJkCaparhKqAQWvthL9/2Op5d91fB1UYqabrHtpBPp5UA2D+ urewT191S7P9Kt7BeG3/wuJQQI04N911z4Y/Kbl6hdQcONo/xGfJ9b0QHrs2ohkprsckmX 7/l6VDSJHSTkiAeTgBRtW63Jytkp49AGe6yK62oXioQvbnoqzbkKTYvOZtGsEKkP/27Tm9 C+3JFNnCPhi7kZtGfbTsTWRJkYayNJ5O3BHWckm64RoE7kxf26KHhJdMsP2bYnmUtRsLkO HZF11yAf/x+0uAXMUzcfnJPW+VL6yqisO8SZ8ckCTADgZlVimpJcUaLVvMjeXYroIUJiwF JTNGXO0CVD9CuzJVdgFa9zF+9Sa3346JWKAMrJDNVw0vrsKwwY5QwMKCyOwzX5RI4M15Ea v9shhXo6IbUUmckyGaBl16YXWiNC+A7OwkjpHw68JcvCfUkJtbVyanAL4gJk2gyUGEm8El nHZ54zzJk9oAVhDEBA//wqg19EJbXBX8K3Q76WqDAwExD3DgsiWuHcVTJWlSzoPp3nTL1S jCzw9NeLXel4kgrR+gOrAj1UrWsUtH1qWX9KdVdDtr0NCFNeVdgtTmKW9ZBQ X-ME-Proxy: Feedback-ID: i0fe9450f:Fastmail Received: by mail.messagingengine.com (Postfix) with ESMTPA; Mon, 6 Jul 2026 21:42:37 -0400 (EDT) Date: Tue, 7 Jul 2026 10:42:33 +0900 From: Michael Paquier To: Matthias van de Meent Cc: Imran Zaheer , Srinath Reddy Sadipiralla , Alexander Lakhin , PostgreSQL mailing lists , Konstantin Knizhnik Subject: Re: BUG #19519: REPACK can fail due to missing chunk for toast value Message-ID: References: <19519-fe02d8ff679d834d@postgresql.org> MIME-Version: 1.0 Content-Type: multipart/signed; micalg=pgp-sha512; protocol="application/pgp-signature"; boundary="wmsZHvfWN2ByPVFF" Content-Disposition: inline In-Reply-To: List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Archived-At: Precedence: bulk --wmsZHvfWN2ByPVFF Content-Type: text/plain; charset=us-ascii Content-Disposition: inline Content-Transfer-Encoding: quoted-printable On Tue, Jul 07, 2026 at 01:51:32AM +0200, Matthias van de Meent wrote: > On Tue, 7 Jul 2026, 01:19 Michael Paquier, wrote: >=20 >> On Mon, Jul 06, 2026 at 08:21:41PM +0200, Matthias van de Meent wrote: >>> So, in effect, this is an issue that's quite similar to the CIC/RIC >>> bug of PG14<14.4, except that >>> >>> 1.) in this case it's SnapshotAny instead of a >>> registered-but-invisible MVCC snapshot; >>> 2.) the issue in this case only happens when toast pointers were >>> cleaned up and then are dereferenced, rather than HOT chains updated >>> and reclaimed since the scan started; and finally >>> 3.) this issue dates back a very long time, likely since TOAST, but >>> defininitely since PG14 introduced the GlobalVisTestFor apis. >> >> You mean 042b584c7f7d, revert of d9d076222f5b. That rings a bell. >> >=20 > Indeed >=20 >=20 >>> So I think the only way to fix this is either >>> 1.) we update every maintenance process that makes use of SnapshotAny >>> and could access TOAST tables to handle errors caused by missing TOAST >>> data when the base relation's tuple is RECENTLY_DEAD, and treat those >>> as "tuple cleanup has already started, we just weren't aware of it >>> yet, so ignore this tuple" (as I mentioned in [1]), or >> >> That seems like an option worth exploring to me, but I doubt that >> we'll be able to get something that can be backpatched due to how >> invasive it is. I strongly suspect that it would require at least one >> table AM change to cope with the fact that we want to let the callers >> be OK with TOAST chunks missing in some contexts when grabbing a toast >> slice. That's perhaps for the best if we think about potential >> regressions, this is scary and old enough that we may still be OK by >> living without a backpatch. >> >=20 > I suspect that for indexing we're lucky, in that we have full control > internally over which tuple data get fed into IndexBuildCallback. We can > make sure only fully detoasted attributes get passed on, and can be > implemented with some (a lot) of TRY/CATCH work in or around > FormIndexDatum. That said, I don't think that's very nice, and I'm also a > bit concerned about leaking things (memory, buffers, ...) in such an > approach. I've quickly thought about some try/catch blocks while detoasting, but I cannot really get how this would be entirely bullet-proof. It seems to me that we'll live better if we bite the bullet and go for the invasive change of passing a state across the stack to let detoasting know that we are dealing with a rewrite. > For REPACK/VACUUM FULL/CLUSTER, I think we can do something similar, given > that this code too has a central loop processing the tuple data, though I > suspect it'll need a bit more work than the reindex one. While looking at the whole stack, the handling of dead tuples seems to go through only index_build_range_scan() and relation_copy_for_cluster() for heapam. A re-check for TOAST values would be really bad if we have a lot of dead tuples. >> 2.) we set the xmin of the CI/R backend to the current OldestXmin for >>> the relation(s) we're currently processing, and so block all cleanup >>> of the relevant (toast) data for the duration of this statement or >>> whenever we check for a newer xmin for the relation (whilst ignoring >>> our current one). >> >> Err, I don't think that would be safe anyway? It's rather uncommon in >> practice in schemas, but we could trigger function calls, like index >> expressions, domains, whatever, that access data of other tables while >> processing one table with a SnapshotAny. The CIC revert of 14.4 was >> about such cases. >=20 > True, but in indexes that is forbidden: mislabeling of non-INMUTABLE > functions causes broken indexes every day, and we can't be expected to ma= ke > it work there. Similarly, for REPACK it shouldn't evaluate any > non-indexable expressions, right? Still I am pretty sure that the window would exist, users like fancy definitions. It seems at least worth looking if we could make something more stable across the board. Just playing with it now, and it does not seem that bad in practice, actually.. > Either way, if we can register a snapshot in the REPACK/INDEX backend who= se > xmin is (*correctly*) registered with the OldestNonRemovableTransactionId= () > of the relation, then concurrent cleanup won't happen for toast, and we'd > also avoid dereferencing those dangling toast pointers. We won't need to > actually use that snapshot for any scans; it'll avoid the issue as long as > our backend advertises an xmin <=3D the OldestXmin used in maintenance to > hold back pruning/vacuum on the relation. >=20 > (we can adjust that xmin every once in a while with a newer > OldestNonRemovableTransactionId (excl. our own backend) as long as we also > adjust the OldestXmin cutoff for the SnapshotAny visibility tests, but I > don't suggest to backpatch that even newer system, it'd add significant > complications to an already complicated system) I doubt that anything would be backpatchable, based on how the discussion is going. I'm OK to be proven wrong. > ps. sorry for the formatting, I'm writing this on my phone. No pb. Thanks. -- Michael --wmsZHvfWN2ByPVFF Content-Type: application/pgp-signature; name=signature.asc -----BEGIN PGP SIGNATURE----- iQIzBAEBCgAdFiEEG72nH6vTowiyblFKnvQgOdbyQH0FAmpMWYkACgkQnvQgOdby QH2NoRAAl3Ax9eILwNlIu1+7Ti69DvuPb03PQgwubZyAzAeGGMt71CaRmhI4tgqg gcp5XKEwQzKFjU8ZysSJVy7acKesnVAojk8Gq6j+Q/toemLL4stnrZ+RdoeJ9KHI tWZvqjwNJcLUEivet1zqdg+GdZN6Yd+K5ez8CK6UJG7egIMYWNJmW1pa9Iw3NwwX BOkuPs+/0OKC4GM8HFj4oDY1Q5yBSevtqte1ihEcFZJtv9F86Jga7Lt+kAF3tTKY TITAF59bHyNsgqSQ03OJiUEAnF8pjlIsvtKiWOqT4hFu9xPGckTY6ThF6PVsw0Zo lA/ZSxWePljLxCa3NHdumXQZgeo9HHitcIGNIOrvUmfD7NCWUhwLmP5PBwNIBvjC sFn9a0Y1GAzcsKdZMbzTGQ6yYXbmFfjNaH3N7jWK4tBZr48xt1Q1AmNFyjLGaHjw SCbNZDrjE+Fu1Nxy6uVklyNwMeyodpuGMRVHg5uzzu7+qUbHRFwGWSxNyruhta1z 0TeOp0kiEL6triCI3JRbiF/Zoh6b0v8+5P5id4xf1ApMijPnEwjCaD9jQsQaXfDJ vWapeIY2Yq7rjwzhcHDHtSvr9h9PJks1YODaYV2qhQ2G7/Rppnu9+mShY2t77Glt rk5pEjq+t5JdJqgI1Xw3adUrAyFljeodZD+GHXzhYvyon8Dv31Y= =te8/ -----END PGP SIGNATURE----- --wmsZHvfWN2ByPVFF--