Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1jLKnw-0005iv-Go for pgsql-bugs@arkaria.postgresql.org; Mon, 06 Apr 2020 06:00:16 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.92) (envelope-from ) id 1jLKnv-0000yq-9T for pgsql-bugs@arkaria.postgresql.org; Mon, 06 Apr 2020 06:00:15 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.3:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1jLKnv-0000yj-19 for pgsql-bugs@lists.postgresql.org; Mon, 06 Apr 2020 06:00:15 +0000 Received: from mail-lf1-x141.google.com ([2a00:1450:4864:20::141]) by magus.postgresql.org with esmtps (TLS1.3:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.92) (envelope-from ) id 1jLKnp-0006CV-ER for pgsql-bugs@lists.postgresql.org; Mon, 06 Apr 2020 06:00:14 +0000 Received: by mail-lf1-x141.google.com with SMTP id j17so10769653lfe.7 for ; Sun, 05 Apr 2020 23:00:08 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=subject:from:to:references:message-id:date:user-agent:mime-version :in-reply-to:content-language; bh=fkrdy2fEFhHeuPImixZc/r5uRJVZgBBYp062VgXPKBg=; b=VtqXP5pAqUp++m2lFkpnv24tnQlbMq6hMMbZmq0gLcFerAYrEzzMN5QkTJDSTsWLC6 H3PH3pyy/7+fAKSWevIvAQM9q/MTvYK+tTJvH3pyckASrAuJpIE4nTSAAn4stYH0qE82 e/3yJsFEovoc3x5b+ucSyjLRoNeSMcmt/jHBh5m6wGj6jQ9lloVThmos+oT/qXNjkZL4 8/dC6lB3w+8+SXf8ik5Rp+qv6YIWKkChkYmKe6QepeGQ4qe6UldCLrrpWLWL//u+PSzO M+AV06w4scjdCghi5WaQKzYf3U+meBO73Lj8bZsc3SUV+DcgDz9/Iif+dtBz914hLpVi 4L8w== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:subject:from:to:references:message-id:date :user-agent:mime-version:in-reply-to:content-language; bh=fkrdy2fEFhHeuPImixZc/r5uRJVZgBBYp062VgXPKBg=; b=mga3ySH8QGYm6CWKh0bgP90qXk4u5L6AO7OKmlKS7bh91nqx4Aj2vRKkIvtJnREShK tCeAKP7EGypLve1rapI4pOwX8n6XJ5H+UthlvSSyX6q9F/yakBZ1Q3oHSaWcZZJKrMDe 11PP+rs4UyOhQdND1b31OAZ9X1k1KfhVey++r9CPJZi/AmeL4pu/pUIXedmNgi7sDYZS gc1rJlBJ6ow9MidHeWHRISXqiPRs3iiQAIK8Okn1UookhDWtyt0OfFdgUaEj5ClAYRkc NYHE0jFM6Bzt5jZb4ej2sNxY3eOxboaWldFDfKjhhmagkQoYbUMTAXcJy7OY5PfqYutm 3LuA== X-Gm-Message-State: AGi0Pubw0Vd4Laqd2UPQAHMCiKomL0oFd4T81wUt7jjCHFinhIxNEgE8 uRip+dtcz99505X1u789IinXVw84 X-Google-Smtp-Source: APiQypIZDqbyq3rIWeOCSUV1Unvak1yR8uuXGvThrLopfjYaRVZYMQA9bDHBU0bIY+rtm2+aGPSMIg== X-Received: by 2002:a19:86c3:: with SMTP id i186mr12200566lfd.209.1586152807398; Sun, 05 Apr 2020 23:00:07 -0700 (PDT) Received: from [1.0.0.7] ([178.155.6.128]) by smtp.gmail.com with ESMTPSA id x28sm9292892ljd.24.2020.04.05.23.00.06 for (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Sun, 05 Apr 2020 23:00:06 -0700 (PDT) Subject: Re: BUG #16329: Valgrind detects an invalid read when building a gist index with buffering From: Alexander Lakhin To: pgsql-bugs@lists.postgresql.org References: <16329-7a6aa9b6fa1118a1@postgresql.org> Message-ID: Date: Mon, 6 Apr 2020 09:00:00 +0300 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:68.0) Gecko/20100101 Thunderbird/68.4.1 MIME-Version: 1.0 In-Reply-To: Content-Type: multipart/mixed; boundary="------------A66D539AE50A59F872972C48" Content-Language: en-US List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Precedence: bulk This is a multi-part message in MIME format. --------------A66D539AE50A59F872972C48 Content-Type: text/plain; charset=utf-8 Content-Transfer-Encoding: 7bit Hello hackers, 30.03.2020 08:00, Alexander Lakhin wrote: > 30.03.2020 00:00, PG Bug reporting form wrote: >> The following bug has been logged on the website: >> >> Bug reference: 16329 >> Logged by: Alexander Lakhin >> Email address: exclusion@gmail.com >> PostgreSQL version: 12.2 >> Operating system: Ubuntu 18.04 >> Description: >> >> Running the following query under valgrind: >> create table gist_point_tbl(id int4, p point); >> insert into gist_point_tbl (id, p) >> select g, point(g*10+1, g*10+1) from generate_series(1, 30000) g; >> create index gist_pointidx2 on gist_point_tbl using gist(p) with (buffering >> = on, fillfactor=50); >> >> leads to a memory access error: >> ==00:00:00:08.755 18585== Invalid read of size 2 >> ==00:00:00:08.756 18585== at 0x1F94CA: gistBuildCallback >> (gistbuild.c:495) >> Please look at the patch that modifies the gist regression test to make the issue visible and fixes it by avoiding access to the memory context that can be reset in gistProcessEmptyingQueue(). Best regards, Alexander --------------A66D539AE50A59F872972C48 Content-Type: text/x-patch; charset=UTF-8; name="fix-gistbuild.patch" Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename="fix-gistbuild.patch" diff --git a/src/backend/access/gist/gistbuild.c b/src/backend/access/gist/gistbuild.c index 671b5e9186..cee81d58ad 100644 --- a/src/backend/access/gist/gistbuild.c +++ b/src/backend/access/gist/gistbuild.c @@ -456,6 +456,10 @@ gistBuildCallback(Relation index, itup = gistFormTuple(buildstate->giststate, index, values, isnull, true); itup->t_tid = *tid; + /* Update tuple count and total size. */ + buildstate->indtuples += 1; + buildstate->indtuplesSize += IndexTupleSize(itup); + if (buildstate->bufferingMode == GIST_BUFFERING_ACTIVE) { /* We have buffers, so use them. */ @@ -471,10 +475,6 @@ gistBuildCallback(Relation index, buildstate->giststate, buildstate->heaprel, true); } - /* Update tuple count and total size. */ - buildstate->indtuples += 1; - buildstate->indtuplesSize += IndexTupleSize(itup); - MemoryContextSwitchTo(oldCtx); MemoryContextReset(buildstate->giststate->tempCxt); diff --git a/src/test/regress/expected/gist.out b/src/test/regress/expected/gist.out index 90edb4061d..8515a63c07 100644 --- a/src/test/regress/expected/gist.out +++ b/src/test/regress/expected/gist.out @@ -22,9 +22,12 @@ ERROR: value 101 out of bounds for option "fillfactor" DETAIL: Valid values are between "10" and "100". -- Insert enough data to create a tree that's a couple of levels deep. insert into gist_point_tbl (id, p) -select g, point(g*10, g*10) from generate_series(1, 10000) g; +select g, point(g*10, g*10) from generate_series(1, 20000) g; insert into gist_point_tbl (id, p) select g+100000, point(g*10+1, g*10+1) from generate_series(1, 10000) g; +-- Test buffering index build with data +create index gist_pointidx6 on gist_point_tbl using gist(p) with (buffering = on, fillfactor=50); +drop index gist_pointidx6; -- To test vacuum, delete some entries from all over the index. delete from gist_point_tbl where id % 2 = 1; -- And also delete some concentration of values. diff --git a/src/test/regress/sql/gist.sql b/src/test/regress/sql/gist.sql index b9d398ea94..0efb265ec3 100644 --- a/src/test/regress/sql/gist.sql +++ b/src/test/regress/sql/gist.sql @@ -20,11 +20,15 @@ create index gist_pointidx5 on gist_point_tbl using gist(p) with (fillfactor=101 -- Insert enough data to create a tree that's a couple of levels deep. insert into gist_point_tbl (id, p) -select g, point(g*10, g*10) from generate_series(1, 10000) g; +select g, point(g*10, g*10) from generate_series(1, 20000) g; insert into gist_point_tbl (id, p) select g+100000, point(g*10+1, g*10+1) from generate_series(1, 10000) g; +-- Test buffering index build with data +create index gist_pointidx6 on gist_point_tbl using gist(p) with (buffering = on, fillfactor=50); +drop index gist_pointidx6; + -- To test vacuum, delete some entries from all over the index. delete from gist_point_tbl where id % 2 = 1; --------------A66D539AE50A59F872972C48--