pgsql: Fix deletion of speculatively inserted TOAST on conflict

From: Andres Freund <andres(at)anarazel(dot)de>
To: pgsql-committers(at)postgresql(dot)org
Subject: pgsql: Fix deletion of speculatively inserted TOAST on conflict
Date: 2016-08-18 00:06:33
Message-ID: E1baAqv-0001LO-RX@gemulon.postgresql.org
Views: Raw Message | Whole Thread | Download mbox | Resend email
Thread:
Lists: pgsql-committers pgsql-hackers

Fix deletion of speculatively inserted TOAST on conflict

INSERT .. ON CONFLICT runs a pre-check of the possible conflicting
constraints before performing the actual speculative insertion. In case
the inserted tuple included TOASTed columns the ON CONFLICT condition
would be handled correctly in case the conflict was caught by the
pre-check, but if two transactions entered the speculative insertion
phase at the same time, one would have to re-try, and the code for
aborting a speculative insertion did not handle deleting the
speculatively inserted TOAST datums correctly.

TOAST deletion would fail with "ERROR: attempted to delete invisible
tuple" as we attempted to remove the TOAST tuples using
simple_heap_delete which reasoned that the given tuples should not be
visible to the command that wrote them.

This commit updates the heap_abort_speculative() function which aborts
the conflicting tuple to use itself, via toast_delete, for deleting
associated TOAST datums. Like before, the inserted toast rows are not
marked as being speculative.

This commit also adds a isolationtester spec test, exercising the
relevant code path. Unfortunately 9.5 cannot handle two waiting
sessions, and thus cannot execute this test.

Reported-By: Viren Negi, Oskari Saarenmaa
Author: Oskari Saarenmaa, edited a bit by me
Bug: #14150
Discussion: <20160519123338(dot)12513(dot)20271(at)wrigleys(dot)postgresql(dot)org>
Backpatch: 9.5, where ON CONFLICT was introduced

Branch
------
master

Details
-------
http://git.postgresql.org/pg/commitdiff/07ef035129586ca26a713c4cd15e550dfe35e643

Modified Files
--------------
src/backend/access/heap/heapam.c | 12 +++--
src/backend/access/heap/tuptoaster.c | 15 ++++---
src/backend/utils/time/tqual.c | 4 +-
src/include/access/tuptoaster.h | 2 +-
.../isolation/expected/insert-conflict-toast.out | 15 +++++++
src/test/isolation/isolation_schedule | 1 +
.../isolation/specs/insert-conflict-toast.spec | 51 ++++++++++++++++++++++
7 files changed, 87 insertions(+), 13 deletions(-)

Responses

Browse pgsql-committers by date

  From Date Subject
Next Message Andres Freund 2016-08-18 00:06:34 pgsql: Fix deletion of speculatively inserted TOAST on conflict
Previous Message Tom Lane 2016-08-17 22:33:13 pgsql: Implement regexp_match(), a simplified alternative to regexp_mat

Browse pgsql-hackers by date

  From Date Subject
Next Message Andres Freund 2016-08-18 00:06:36 pgsql: Fix deletion of speculatively inserted TOAST on conflict
Previous Message Peter Geoghegan 2016-08-17 23:58:49 Re: CLUSTER, reform_and_rewrite_tuple(), and parallelism