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.94.2) (envelope-from ) id 1tvatS-0069KI-1b for pgsql-hackers@arkaria.postgresql.org; Fri, 21 Mar 2025 11:50:30 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.94.2) (envelope-from ) id 1tvatQ-005GOu-0o for pgsql-hackers@arkaria.postgresql.org; Fri, 21 Mar 2025 11:50:28 +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.94.2) (envelope-from ) id 1tvatP-005GOm-ID for pgsql-hackers@lists.postgresql.org; Fri, 21 Mar 2025 11:50:27 +0000 Received: from mail.postgrespro.ru ([93.174.132.70]) by magus.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.96) (envelope-from ) id 1tvatM-000JSn-2R for pgsql-hackers@lists.postgresql.org; Fri, 21 Mar 2025 11:50:26 +0000 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=postgrespro.ru; s=mx2023; t=1742557823; bh=flZdqwQOfYaovS7j2fBsxF6tYlBUYh8odpRuIpcXvWI=; h=Message-ID:Date:User-Agent:Subject:From:To:Cc:References: In-Reply-To:From; b=EIUNFaeWigrmWZtUem+mY3ragmUHlcNxMviAR/fpnOt2dlSE/gYsdH7OOB9G2OlhM w3ENzy975Ok8oz9d4tyJKSTKVG+jLswIm0Ay6p42wKjyNMGj4ATL8FMMKZbrwUxgGq zleXFlBE3JMreHocI/yuTNf4qc83PW3Bcv75XrJP06qOkq2BTzNURPnMxnIMk6yPs5 5W8lqp7NUCtGbOkYF/5cdwlC7PsNftHKv8VdAYtYqpFXj7tgcvhFSktRbI1df/GEjG E9o1wHCnBZGS43277dBurIgoDA8/qTVl5tLYL6nn27MSOwvNWBnlE+6BR5UZZujKF8 oSFuMppFoCb5w== Received: from [172.30.51.154] (unknown [93.174.131.138]) (using TLSv1.3 with cipher TLS_AES_128_GCM_SHA256 (128/128 bits) key-exchange X25519 server-signature RSA-PSS (2048 bits) server-digest SHA256) (Client did not present a certificate) (Authenticated sender: y.sokolov@postgrespro.ru) by mail.postgrespro.ru (Postfix/465) with ESMTPSA id 7066660B9B; Fri, 21 Mar 2025 14:50:23 +0300 (MSK) Message-ID: Date: Fri, 21 Mar 2025 14:50:22 +0300 MIME-Version: 1.0 User-Agent: Mozilla Thunderbird Subject: Re: Optimize truncation logic to reduce AccessExclusive lock impact From: Yura Sokolov To: David Rowley , Stepan Neretin Cc: PostgreSQL Hackers References: <0be607a5-20f6-4894-bb22-412e3c784bc2@postgrespro.ru> Content-Language: en-US In-Reply-To: <0be607a5-20f6-4894-bb22-412e3c784bc2@postgrespro.ru> Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 7bit X-KSMG-AntiPhishing: NotDetected X-KSMG-AntiSpam-Interceptor-Info: not scanned X-KSMG-AntiSpam-Status: not scanned, disabled by settings X-KSMG-AntiVirus: Kaspersky Secure Mail Gateway, version 2.1.0.7854, bases: 2025/03/21 10:39:00 #27808689 X-KSMG-AntiVirus-Status: NotDetected, skipped X-KSMG-LinksScanning: not scanned, disabled by settings X-KSMG-Message-Action: skipped X-KSMG-Rule-ID: 1 List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Archived-At: Precedence: bulk 19.03.2025 19:05, Yura Sokolov wrote: > 19.03.2025 05:09, David Rowley wrote: >> On Tue, 18 Mar 2025 at 19:04, Stepan Neretin wrote: >>> We propose modifying the truncation condition in should_attempt_truncation to avoid unnecessary full buffer scans. >> I'm just following this code through. Looking at >> DropRelationBuffers(), d6ad34f34 added an optimisation so that we can >> skip scanning all of shared buffers while in recovery (where >> smgrnblocks_cached() can return a non-InvalidBlockNumber value), which >> the following code might decide to lookup the buffers one-by-one >> rather than scanning the entire buffer pool: >> >> if (BlockNumberIsValid(nBlocksToInvalidate) && >> nBlocksToInvalidate < BUF_DROP_FULL_SCAN_THRESHOLD) >> { >> for (j = 0; j < nforks; j++) >> FindAndDropRelationBuffers(rlocator.locator, forkNum[j], >> nForkBlock[j], firstDelBlock[j]); >> return; >> } >> >> While I don't know this code too well, from a quick look, it seem to >> me that since DropRelationBuffers() is being called from >> smgrtruncate() in this case, smgrtruncate() has access to old_nblocks >> so it knows the old size of the relation. Couldn't we do something >> like have another version of DropRelationBuffers() which accepts a >> parameter for the old number of blocks and uses that instead of >> calling smgrnblocks_cached()? That would allow the >> FindAndDropRelationBuffers() optimisation to be used in cases where >> the buffers to truncate is small or shared buffers is large. > > Yes, it will work for smaller relations. > But it doesn't fix issue with large relations: > - imho, there is no big need to truncate 2TB table to release every 8MB of > free space, but it happens now. After thinking a bit, I realized I was not quite right: if large table is truncated on small number of pages, and we know old size and new one, we can precisely remove them from shared buffers. Exactly as you've described, excuse me for not understanding you clearly for the first time. But the question still remains: should we use this possibility with huge tables, or we should just truncate them rarely? -- regards Yura Sokolov aka funny-falcon