| Lists: | pgsql-bugspgsql-hackers | 
|---|
| From: | Vallimaharajan G <vallimaharajan(dot)gs(at)zohocorp(dot)com> | 
|---|---|
| To: | "pgsql-hackers" <pgsql-hackers(at)postgresql(dot)org> | 
| Cc: | "zlabs-cstore(at)zohocorp(dot)com" <zlabs-cstore(at)zohocorp(dot)com>, "pgsql-hackers" <pgsql-hackers(at)lists(dot)postgresql(dot)org>, "pgsql-bugs" <pgsql-bugs(at)lists(dot)postgresql(dot)org> | 
| Subject: | [Bug] Heap Use After Free in parallel_vacuum_reset_dead_items Function | 
| Date: | 2024-11-25 18:27:07 | 
| Message-ID: | 1936493cc38.68cb2ef27266.7456585136086197135@zohocorp.com | 
| Views: | Whole Thread | Raw Message | Download mbox | Resend email | 
| Lists: | pgsql-bugs pgsql-hackers | 
Hi Developers,
     We have discovered a bug in the parallel_vacuum_reset_dead_items function in PG v17.2. Specifically:
TidStoreDestroy(dead_items) frees the dead_items pointer.
The pointer is reinitialized using TidStoreCreateShared().
However, the code later accesses the freed pointer instead of the newly reinitialized pvs->dead_items, as seen in these lines:
pvs->shared->dead_items_dsa_handle = dsa_get_handle(TidStoreGetDSA(dead_items));
pvs->shared->dead_items_handle = TidStoreGetHandle(dead_items);
This can lead to undefined behaviour or crashes due to the use of invalid memory.
Caught this issue while running the existing regression tests from vacuum_parallel.sql with our custom malloc allocator implementation.
For your reference, we have previously shared our custom malloc allocator implementation in a separate bug fix. (message ID: ).
Failed regression:
SET max_parallel_maintenance_workers TO 4;
SET min_parallel_index_scan_size TO '128kB';
CREATE TABLE parallel_vacuum_table (a int) WITH (autovacuum_enabled = off);
INSERT INTO parallel_vacuum_table SELECT i from generate_series(1, 10000) i;
CREATE INDEX regular_sized_index ON parallel_vacuum_table(a);
CREATE INDEX typically_sized_index ON parallel_vacuum_table(a);
CREATE INDEX vacuum_in_leader_small_index ON parallel_vacuum_table((1));
DELETE FROM parallel_vacuum_table;
VACUUM (PARALLEL 4, INDEX_CLEANUP ON) parallel_vacuum_table;
Please let me know if you have any questions or would like further details.
Thanks & Regards,
Vallimaharajan G
Member Technical Staff
ZOHO Corporation
| Attachment | Content-Type | Size | 
|---|---|---|
| parallel_vacuum_fix.patch | application/octet-stream | 1.1 KB | 
| From: | John Naylor <johncnaylorls(at)gmail(dot)com> | 
|---|---|
| To: | Vallimaharajan G <vallimaharajan(dot)gs(at)zohocorp(dot)com> | 
| Cc: | pgsql-hackers <pgsql-hackers(at)postgresql(dot)org>, "zlabs-cstore(at)zohocorp(dot)com" <zlabs-cstore(at)zohocorp(dot)com>, pgsql-hackers <pgsql-hackers(at)lists(dot)postgresql(dot)org>, pgsql-bugs <pgsql-bugs(at)lists(dot)postgresql(dot)org> | 
| Subject: | Re: [Bug] Heap Use After Free in parallel_vacuum_reset_dead_items Function | 
| Date: | 2024-11-26 09:53:45 | 
| Message-ID: | CANWCAZYJe4vya4taNFdqK2dx6q3VmyxyL7V+8DBy62YnaQUeiA@mail.gmail.com | 
| Views: | Whole Thread | Raw Message | Download mbox | Resend email | 
| Lists: | pgsql-bugs pgsql-hackers | 
On Tue, Nov 26, 2024 at 1:58โฏAM Vallimaharajan G <
vallimaharajan(dot)gs(at)zohocorp(dot)com> wrote:
>
> Hi Developers,
>      We have discovered a bug in the parallel_vacuum_reset_dead_items
function in PG v17.2. Specifically:
>
> TidStoreDestroy(dead_items) frees the dead_items pointer.
> The pointer is reinitialized using TidStoreCreateShared().
> However, the code later accesses the freed pointer instead of the newly
reinitialized pvs->dead_items, as seen in these lines:
>
>            pvs->shared->dead_items_dsa_handle =
dsa_get_handle(TidStoreGetDSA(dead_items));
>            pvs->shared->dead_items_handle = TidStoreGetHandle(dead_items);
Thanks for the report! I don't see any immediate evidence of deleterious
effects, but it's still sloppy. To reduce risk going forward, I think we
should always access this pointer via the struct rather than a separate
copy, quick attempt attached.
(BTW, it's normally discouraged to cross-post to different lists. Either
one is fine in this case.)
--
John Naylor
Amazon Web Services
| Attachment | Content-Type | Size | 
|---|---|---|
| v2-fix-parallel-vacuum.patch | text/x-patch | 3.2 KB | 
| From: | John Naylor <johncnaylorls(at)gmail(dot)com> | 
|---|---|
| To: | Vallimaharajan G <vallimaharajan(dot)gs(at)zohocorp(dot)com> | 
| Cc: | "zlabs-cstore(at)zohocorp(dot)com" <zlabs-cstore(at)zohocorp(dot)com>, pgsql-hackers <pgsql-hackers(at)lists(dot)postgresql(dot)org> | 
| Subject: | Re: [Bug] Heap Use After Free in parallel_vacuum_reset_dead_items Function | 
| Date: | 2024-12-05 01:46:33 | 
| Message-ID: | CANWCAZZgVMvByZA1r9mpPsHYnGrvX=HJR20H+5rbs3AnwvbfFA@mail.gmail.com | 
| Views: | Whole Thread | Raw Message | Download mbox | Resend email | 
| Lists: | pgsql-bugs pgsql-hackers | 
On Tue, Nov 26, 2024 at 4:53โฏPM John Naylor <johncnaylorls(at)gmail(dot)com> wrote:
> Thanks for the report! I don't see any immediate evidence of deleterious effects, but it's still sloppy. To reduce risk going forward, I think we should always access this pointer via the struct rather than a separate copy, quick attempt attached.
[removing -bugs]
I looked again and changed a few more places for consistency, and committed.
-- 
John Naylor
Amazon Web Services