Thread: ERROR: negative bitmapset member not allowed in SELECT
Hi everyone, the following statements results in an error "ERROR: negative bitmapset member not allowed", which is unexpected: CREATE TABLE t0(c0 serial, c1 boolean); CREATE STATISTICS s1 ON c0, c1 FROM t0; INSERT INTO t0(c1) VALUES(TRUE); ANALYZE; CREATE INDEX i0 ON t0(c0, (t0.c1 AND t0.c1)); SELECT * FROM (SELECT t0.c0 FROM t0 WHERE (((t0.c1) AND (t0.c1)) OR FALSE) IS TRUE) as result WHERE result.c0 IS NULL; -- unexpected: ERROR: negative bitmapset member not allowed When replacing serial by integer, I instead get "ERROR: type with OID 21938 does not exist". I'm using the following Postgres version: 12beta2 (Debian 12~beta2-1.pgdg90+1). Best, Manuel
On 2019-Jul-10, Manuel Rigger wrote: > CREATE TABLE t0(c0 serial, c1 boolean); > CREATE STATISTICS s1 ON c0, c1 FROM t0; > INSERT INTO t0(c1) VALUES(TRUE); > ANALYZE; > CREATE INDEX i0 ON t0(c0, (t0.c1 AND t0.c1)); > SELECT * FROM (SELECT t0.c0 FROM t0 WHERE (((t0.c1) AND (t0.c1)) OR > FALSE) IS TRUE) as result WHERE result.c0 IS NULL; -- unexpected: > ERROR: negative bitmapset member not allowed Backtrace: #0 errfinish (dummy=dummy@entry=0) at /pgsql/source/master/src/backend/utils/error/elog.c:411 #1 0x0000559f2b8ca430 in elog_finish (elevel=elevel@entry=20, fmt=fmt@entry=0x559f2ba6f538 "negative bitmapset member notallowed") at /pgsql/source/master/src/backend/utils/error/elog.c:1365 #2 0x0000559f2b6801f5 in bms_is_member (x=<optimized out>, a=<optimized out>) at /pgsql/source/master/src/backend/nodes/bitmapset.c:434 #3 0x0000559f2b68021d in bms_member_index (a=a@entry=0x559f2da39918, x=-30672) at /pgsql/source/master/src/backend/nodes/bitmapset.c:462 #4 0x0000559f2b758841 in mcv_get_match_bitmap (root=root@entry=0x559f2d9e2e78, clauses=clauses@entry=0x559f2da3a6f0, keys=0x559f2da39918,mcvlist=mcvlist@entry=0x559f2da3a938, is_or=is_or@entry=false) at /pgsql/source/master/src/backend/statistics/mcv.c:1597 #5 0x0000559f2b75b551 in mcv_clauselist_selectivity (root=root@entry=0x559f2d9e2e78, stat=stat@entry=0x559f2da398e0, clauses=clauses@entry=0x559f2da3a6f0,varRelid=varRelid@entry=2, jointype=jointype@entry=JOIN_INNER, sjinfo=sjinfo@entry=0x0,rel=0x559f2d9e1a10, basesel=0x7ffc17135958, totalsel=0x7ffc17135960) at /pgsql/source/master/src/backend/statistics/mcv.c:1876 #6 0x0000559f2b756dc4 in statext_mcv_clauselist_selectivity (estimatedclauses=0x7ffc171359f0, rel=<optimized out>, sjinfo=<optimizedout>, jointype=<optimized out>, varRelid=<optimized out>, clauses=<optimized out>, root=<optimized out>)at /pgsql/source/master/src/backend/statistics/extended_stats.c:1146 #7 statext_clauselist_selectivity (root=root@entry=0x559f2d9e2e78, clauses=clauses@entry=0x559f2da3a430, varRelid=varRelid@entry=2,jointype=jointype@entry=JOIN_INNER, sjinfo=sjinfo@entry=0x0, rel=<optimized out>, estimatedclauses=0x7ffc171359f0)at /pgsql/source/master/src/backend/statistics/extended_stats.c:1177 #8 0x0000559f2b6a98d1 in clauselist_selectivity (root=root@entry=0x559f2d9e2e78, clauses=0x559f2da3a430, varRelid=2, jointype=jointype@entry=JOIN_INNER,sjinfo=sjinfo@entry=0x0) at /pgsql/source/master/src/backend/optimizer/path/clausesel.c:94 #9 0x0000559f2b8767e6 in btcostestimate (root=0x559f2d9e2e78, path=0x559f2da38ef0, loop_count=1, indexStartupCost=0x7ffc17135c48,indexTotalCost=0x7ffc17135c50, indexSelectivity=0x7ffc17135c58, indexCorrelation=0x7ffc17135c60,indexPages=0x7ffc17135c78) at /pgsql/source/master/src/backend/utils/adt/selfuncs.c:5853 #10 0x0000559f2b6adc39 in cost_index (path=path@entry=0x559f2da38ef0, root=root@entry=0x559f2d9e2e78, loop_count=loop_count@entry=1,partial_path=partial_path@entry=false) at /pgsql/source/master/src/backend/optimizer/path/costsize.c:545 #11 0x0000559f2b6e9504 in create_index_path (root=root@entry=0x559f2d9e2e78, index=index@entry=0x559f2d9e1c28, indexclauses=indexclauses@entry=0x559f2da3a358,indexorderbys=indexorderbys@entry=0x0, indexorderbycols=indexorderbycols@entry=0x0,pathkeys=pathkeys@entry=0x0, indexscandir=ForwardScanDirection, indexonly=false,required_outer=0x0, loop_count=loop_count@entry=1, partial_path=false) at /pgsql/source/master/src/backend/optimizer/util/pathnode.c:1054 #12 0x0000559f2b6b67c5 in build_index_paths (root=root@entry=0x559f2d9e2e78, rel=rel@entry=0x559f2d9e1a10, index=index@entry=0x559f2d9e1c28,clauses=clauses@entry=0x7ffc17135f10, useful_predicate=<optimized out>, scantype=scantype@entry=ST_ANYSCAN,skip_nonnative_saop=<optimized out>, skip_lower_saop=<optimized out>) at /pgsql/source/master/src/backend/optimizer/path/indxpath.c:1039 #13 0x0000559f2b6b6ece in get_index_paths (root=root@entry=0x559f2d9e2e78, rel=rel@entry=0x559f2d9e1a10, index=index@entry=0x559f2d9e1c28,clauses=clauses@entry=0x7ffc17135f10, bitindexpaths=bitindexpaths@entry=0x7ffc17135ef0)at /pgsql/source/master/src/backend/optimizer/path/indxpath.c:754 -- Álvaro Herrera https://www.2ndQuadrant.com/ PostgreSQL Development, 24x7 Support, Remote DBA, Training & Services
Alvaro Herrera <alvherre@2ndquadrant.com> writes: > On 2019-Jul-10, Manuel Rigger wrote: >> CREATE TABLE t0(c0 serial, c1 boolean); >> CREATE STATISTICS s1 ON c0, c1 FROM t0; >> INSERT INTO t0(c1) VALUES(TRUE); >> ANALYZE; >> CREATE INDEX i0 ON t0(c0, (t0.c1 AND t0.c1)); >> SELECT * FROM (SELECT t0.c0 FROM t0 WHERE (((t0.c1) AND (t0.c1)) OR >> FALSE) IS TRUE) as result WHERE result.c0 IS NULL; -- unexpected: >> ERROR: negative bitmapset member not allowed > Backtrace: I'd say that mcv_get_match_bitmap has a completely misplaced level of faith that any OpExpr it's handed will have a plain Var on one side or the other. Not to mention an untenable assumption that the other side is a plain Const. regards, tom lane
I found another, maybe simpler statement sequence to reproduce the error "ERROR: negative bitmapset member not allowed": CREATE TABLE t0(c0 BOOLEAN, c1 BOOLEAN, UNIQUE(c1)); CREATE STATISTICS s1 ON c0, c1 FROM t0; INSERT INTO t0(c0) VALUES(TRUE); ANALYZE t0; SELECT * FROM t0 WHERE (t0.c0 AND t0.c1) >= TRUE; -- ERROR: negative bitmapset member not allowed I assume that the error is caused by the same underlying bug, right? Best, Manuel On Wed, Jul 10, 2019 at 10:18 PM Tom Lane <tgl@sss.pgh.pa.us> wrote: > > Alvaro Herrera <alvherre@2ndquadrant.com> writes: > > On 2019-Jul-10, Manuel Rigger wrote: > >> CREATE TABLE t0(c0 serial, c1 boolean); > >> CREATE STATISTICS s1 ON c0, c1 FROM t0; > >> INSERT INTO t0(c1) VALUES(TRUE); > >> ANALYZE; > >> CREATE INDEX i0 ON t0(c0, (t0.c1 AND t0.c1)); > >> SELECT * FROM (SELECT t0.c0 FROM t0 WHERE (((t0.c1) AND (t0.c1)) OR > >> FALSE) IS TRUE) as result WHERE result.c0 IS NULL; -- unexpected: > >> ERROR: negative bitmapset member not allowed > > > Backtrace: > > I'd say that mcv_get_match_bitmap has a completely misplaced level of > faith that any OpExpr it's handed will have a plain Var on one side > or the other. > > Not to mention an untenable assumption that the other side is a plain > Const. > > regards, tom lane
Hi everyone, I noticed that this bug was fixed in five recent commits by Tomas. Thanks a lot, Tomas! This really helps me continue testing Postgres. The five commits (e.g. [1]) reference a bug report by Andreas who reported a crash in an email with a timestamp 2019-07-10 20:37:51 [2]. However, it seems that I first reported what seems to be the same underlying bug, namely in the first email of this thread with a timestamp 2019-07-10 15:39:22 [3], where the bug results in the error "negative bitmapset member not allowed". Could it be that (some of) the five commits should actually have been attributed to me? I hope this does not appear too pedantic, but I'm developing a new DBMS testing tool, and it would be important for me to know which bug findings and associated commits can be attributed to it. By the way, I also reported two crashing bugs, which seem to expose the same underlying bug [4], but after Andreas. Best, Manuel [1] https://github.com/postgres/postgres/commit/e8b6ae2130e3a95bb776708a9a7c9cb21fe8ac87 [2] https://www.postgresql.org/message-id/8736jdhbhc.fsf%40ansel.ydns.eu [3] https://www.postgresql.org/message-id/CA+u7OA65+jEFb_TyV5g+Kq+onyJ2skMOPzgTgFH+qgLwszRqvw@mail.gmail.com [4] https://www.postgresql.org/message-id/CA+u7OA40Fe9=A3wQ2PHWy8VZg8=GpD6dxQXeXVDx6HAhRSPeRA@mail.gmail.com On Thu, Jul 11, 2019 at 1:56 PM Manuel Rigger <rigger.manuel@gmail.com> wrote: > > I found another, maybe simpler statement sequence to reproduce the > error "ERROR: negative bitmapset member not allowed": > > CREATE TABLE t0(c0 BOOLEAN, c1 BOOLEAN, UNIQUE(c1)); > CREATE STATISTICS s1 ON c0, c1 FROM t0; > INSERT INTO t0(c0) VALUES(TRUE); > ANALYZE t0; > SELECT * FROM t0 WHERE (t0.c0 AND t0.c1) >= TRUE; -- ERROR: negative > bitmapset member not allowed > > I assume that the error is caused by the same underlying bug, right? > > Best, > Manuel > > On Wed, Jul 10, 2019 at 10:18 PM Tom Lane <tgl@sss.pgh.pa.us> wrote: > > > > Alvaro Herrera <alvherre@2ndquadrant.com> writes: > > > On 2019-Jul-10, Manuel Rigger wrote: > > >> CREATE TABLE t0(c0 serial, c1 boolean); > > >> CREATE STATISTICS s1 ON c0, c1 FROM t0; > > >> INSERT INTO t0(c1) VALUES(TRUE); > > >> ANALYZE; > > >> CREATE INDEX i0 ON t0(c0, (t0.c1 AND t0.c1)); > > >> SELECT * FROM (SELECT t0.c0 FROM t0 WHERE (((t0.c1) AND (t0.c1)) OR > > >> FALSE) IS TRUE) as result WHERE result.c0 IS NULL; -- unexpected: > > >> ERROR: negative bitmapset member not allowed > > > > > Backtrace: > > > > I'd say that mcv_get_match_bitmap has a completely misplaced level of > > faith that any OpExpr it's handed will have a plain Var on one side > > or the other. > > > > Not to mention an untenable assumption that the other side is a plain > > Const. > > > > regards, tom lane