pg.ddx.io  pgsql-hackers@postgresql.org mailing list archive  
help / color / mirror / Atom feed
[sqlsmith] Crash in tsquery_rewrite/QTNBinary
3+ messages / 3 participants
[nested] [flat]

Commits from this thread:
  2016-12-11 0eaaaf00e2 c8bfe055be c6caa52000 6f5cb982e7 79e1a9efa8 f4ccee408d  Prevent crash when ts_rewrite() replaces a non-top-level subtree with null.
* [sqlsmith] Crash in tsquery_rewrite/QTNBinary
@ 2016-12-07 06:06 Andreas Seltenreich <seltenreich@gmx.de>
  2016-12-10 21:07 ` Re: [sqlsmith] Crash in tsquery_rewrite/QTNBinary Artur Zakirov <a.zakirov@postgrespro.ru>
  0 siblings, 1 reply; 3+ messages in thread

From: Andreas Seltenreich @ 2016-12-07 06:06 UTC (permalink / raw)
  To: pgsql-hackers

Hi,

the following query crashes master as of 4212cb7.

select ts_rewrite(
          tsquery_phrase(
             tsquery $$'sanct' & 'peter'$$,
             tsquery $$'5' <-> '6'$$,
	     42),
          tsquery $$'5' <-> '6'$$,
          plainto_tsquery('I') );

Backtrace below.

regards,
Andreas

Program terminated with signal SIGSEGV, Segmentation fault.
#0  QTNBinary (in=0x0) at tsquery_util.c:256
#1  0x0000559debd68643 in QTNBinary (in=0x559ded7cc998) at tsquery_util.c:260
#2  0x0000559debd68643 in QTNBinary (in=in@entry=0x559ded7cd068) at tsquery_util.c:260
#3  0x0000559debd67df5 in tsquery_rewrite (fcinfo=0x559ded72c040) at tsquery_rewrite.c:453
#4  0x0000559debb754f4 in ExecMakeFunctionResultNoSets (fcache=0x559ded72bfd0, econtext=0x559ded72bda8, isNull=0x559ded72d350 "", isDone=<optimized out>) at execQual.c:2046
#5  0x0000559debb7ba1e in ExecTargetList (tupdesc=<optimized out>, isDone=0x7ffce180da6c, itemIsDone=0x559ded72d490, isnull=0x559ded72d350 "", values=0x559ded72d330, econtext=0x559ded72bda8, targetlist=0x559ded72d458) at execQual.c:5486
#6  ExecProject (projInfo=<optimized out>, isDone=isDone@entry=0x7ffce180da6c) at execQual.c:5710
#7  0x0000559debb92c79 in ExecResult (node=node@entry=0x559ded72bc90) at nodeResult.c:155
#8  0x0000559debb74478 in ExecProcNode (node=node@entry=0x559ded72bc90) at execProcnode.c:392
#9  0x0000559debb702fe in ExecutePlan (dest=0x559ded7c8b98, direction=<optimized out>, numberTuples=0, sendTuples=<optimized out>, operation=CMD_SELECT, use_parallel_mode=<optimized out>, planstate=0x559ded72bc90, estate=0x559ded72bb78) at execMain.c:1568
#10 standard_ExecutorRun (queryDesc=0x559ded727a18, direction=<optimized out>, count=0) at execMain.c:338
#11 0x0000559debc9c238 in PortalRunSelect (portal=portal@entry=0x559ded71f958, forward=forward@entry=1 '\001', count=0, count@entry=9223372036854775807, dest=dest@entry=0x559ded7c8b98) at pquery.c:946
#12 0x0000559debc9d89e in PortalRun (portal=portal@entry=0x559ded71f958, count=count@entry=9223372036854775807, isTopLevel=isTopLevel@entry=1 '\001', dest=dest@entry=0x559ded7c8b98, altdest=altdest@entry=0x559ded7c8b98, completionTag=completionTag@entry=0x7ffce180dee0 "") at pquery.c:787
#13 0x0000559debc9af42 in exec_simple_query (query_string=0x559ded795048 "...") at postgres.c:1094
#14 PostgresMain (argc=<optimized out>, argv=argv@entry=0x559ded7390b0, dbname=<optimized out>, username=<optimized out>) at postgres.c:4069
#15 0x0000559deb9ee2f8 in BackendRun (port=0x559ded726ef0) at postmaster.c:4274
#16 BackendStartup (port=0x559ded726ef0) at postmaster.c:3946
#17 ServerLoop () at postmaster.c:1704
#18 0x0000559debc2ebb4 in PostmasterMain (argc=3, argv=0x559ded7004a0) at postmaster.c:1312
#19 0x0000559deb9ef68d in main (argc=3, argv=0x559ded7004a0) at main.c:228


-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers



^ permalink  raw  reply  [nested|flat] 3+ messages in thread

* Re: [sqlsmith] Crash in tsquery_rewrite/QTNBinary
  2016-12-07 06:06 [sqlsmith] Crash in tsquery_rewrite/QTNBinary Andreas Seltenreich <seltenreich@gmx.de>
@ 2016-12-10 21:07 ` Artur Zakirov <a.zakirov@postgrespro.ru>
  2016-12-11 18:12   ` Re: [sqlsmith] Crash in tsquery_rewrite/QTNBinary Tom Lane <tgl@sss.pgh.pa.us>
  0 siblings, 1 reply; 3+ messages in thread

From: Artur Zakirov @ 2016-12-10 21:07 UTC (permalink / raw)
  To: Andreas Seltenreich <seltenreich@gmx.de>; +Cc: pgsql-hackers

Hi,

2016-12-07 9:06 GMT+03:00 Andreas Seltenreich <seltenreich@gmx.de>:
> Hi,
>
> the following query crashes master as of 4212cb7.
>
> select ts_rewrite(
>           tsquery_phrase(
>              tsquery $$'sanct' & 'peter'$$,
>              tsquery $$'5' <-> '6'$$,
>              42),
>           tsquery $$'5' <-> '6'$$,
>           plainto_tsquery('I') );
>

This happens also for queries:

select ts_rewrite(
          to_tsquery('5 & (6 | 5)'),
          to_tsquery('5'),
          to_tsquery('I'));

select ts_rewrite(
          to_tsquery('5 & 6 <-> 5'),
          to_tsquery('5'),
          to_tsquery('I'));

It happens because 'I' is stop word and substitute query becomes
empty. And for queries above we need recursive dropvoidsubtree()
function. Without this patch this function cleans only first level of
tree. And query above becomes: '6 | void'.

Firstly I made recursive dropvoidsubtree(). But attached patch cleans
query tree in dofindsubquery() to avoid extra tree scan.

-- 
Artur Zakirov
Postgres Professional: http://www.postgrespro.com
Russian Postgres Company

-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

Attachments:

0001-dofindsubquery-with-drop.diff (text/plain, 3.3K) download diff --git a/src/backend/utils/adt/tsquery_rewrite.c b/src/backend/utils/adt/tsquery_rewrite.c index e5bed6e..00174bd 100644 --- a/src/backend/utils/adt/tsquery_rewrite.c +++ b/src/backend/utils/adt/tsquery_rewrite.c @@ -186,6 +186,15 @@ findeq(QTNode *node, QTNode *ex, QTNode *subs, bool *isfind) * Recursive guts of findsubquery(): attempt to replace "ex" with "subs" * at the root node, and if we failed to do so, recursively match against * child nodes. + * + * Delete any void subtrees. In the following example '5' is replaced by empty + * operand: + * + * AND -> 6 + * / \ + * 5 PHRASE + * / \ + * 6 5 */ static QTNode * dofindsubquery(QTNode *root, QTNode *ex, QTNode *subs, bool *isfind) @@ -200,39 +209,20 @@ dofindsubquery(QTNode *root, QTNode *ex, QTNode *subs, bool *isfind) if (root && (root->flags & QTN_NOCHANGE) == 0 && root->valnode->type == QI_OPR) { - int i; - - for (i = 0; i < root->nchild; i++) - root->child[i] = dofindsubquery(root->child[i], ex, subs, isfind); - } - - return root; -} - -/* - * Delete any void subtrees that may have been inserted when the replacement - * subtree is void. - */ -static QTNode * -dropvoidsubtree(QTNode *root) -{ - if (!root) - return NULL; - - if (root->valnode->type == QI_OPR) - { int i, j = 0; for (i = 0; i < root->nchild; i++) { - if (root->child[i]) - { - root->child[j] = root->child[i]; + root->child[j] = dofindsubquery(root->child[i], ex, subs, isfind); + if (root->child[j]) j++; - } } + /* + * Delete any void subtrees that may have been inserted when the replacement + * subtree is void. + */ root->nchild = j; if (root->nchild == 0) @@ -267,9 +257,6 @@ findsubquery(QTNode *root, QTNode *ex, QTNode *subs, bool *isfind) root = dofindsubquery(root, ex, subs, &DidFind); - if (!subs && DidFind) - root = dropvoidsubtree(root); - if (isfind) *isfind = DidFind; diff --git a/src/test/regress/expected/tsearch.out b/src/test/regress/expected/tsearch.out index 55d6a85..9c20aaf 100644 --- a/src/test/regress/expected/tsearch.out +++ b/src/test/regress/expected/tsearch.out @@ -1251,6 +1251,14 @@ SELECT ts_rewrite('5 <-> (6 | 8)', 'SELECT keyword, sample FROM test_tsquery'::t '5' <-> '7' | '5' <-> '8' (1 row) +-- Check empty substitute +SELECT ts_rewrite(to_tsquery('5 & 6 <-> 5'), to_tsquery('5'), to_tsquery('I')); +NOTICE: text-search query contains only stop words or doesn't contain lexemes, ignored + ts_rewrite +------------ + '6' +(1 row) + SELECT keyword FROM test_tsquery WHERE keyword @> 'new'; keyword ---------------- diff --git a/src/test/regress/sql/tsearch.sql b/src/test/regress/sql/tsearch.sql index afd990e..8752344 100644 --- a/src/test/regress/sql/tsearch.sql +++ b/src/test/regress/sql/tsearch.sql @@ -418,6 +418,8 @@ SELECT ts_rewrite('1 & (2 <2> 3)', 'SELECT keyword, sample FROM test_tsquery'::t SELECT ts_rewrite('5 <-> (1 & (2 <-> 3))', 'SELECT keyword, sample FROM test_tsquery'::text ); SELECT ts_rewrite('5 <-> (6 | 8)', 'SELECT keyword, sample FROM test_tsquery'::text ); +-- Check empty substitute +SELECT ts_rewrite(to_tsquery('5 & 6 <-> 5'), to_tsquery('5'), to_tsquery('I')); SELECT keyword FROM test_tsquery WHERE keyword @> 'new'; SELECT keyword FROM test_tsquery WHERE keyword @> 'moscow';
^ permalink raw reply [nested|flat] 3+ messages in thread

* Re: [sqlsmith] Crash in tsquery_rewrite/QTNBinary
  2016-12-07 06:06 [sqlsmith] Crash in tsquery_rewrite/QTNBinary Andreas Seltenreich <seltenreich@gmx.de>
  2016-12-10 21:07 ` Re: [sqlsmith] Crash in tsquery_rewrite/QTNBinary Artur Zakirov <a.zakirov@postgrespro.ru>
@ 2016-12-11 18:12   ` Tom Lane <tgl@sss.pgh.pa.us>
  0 siblings, 0 replies; 3+ messages in thread

From: Tom Lane @ 2016-12-11 18:12 UTC (permalink / raw)
  To: Artur Zakirov <a.zakirov@postgrespro.ru>; +Cc: Andreas Seltenreich <seltenreich@gmx.de>; pgsql-hackers

Artur Zakirov <a.zakirov@postgrespro.ru> writes:
> 2016-12-07 9:06 GMT+03:00 Andreas Seltenreich <seltenreich@gmx.de>:
>> the following query crashes master as of 4212cb7.

> It happens because 'I' is stop word and substitute query becomes
> empty. And for queries above we need recursive dropvoidsubtree()
> function. Without this patch this function cleans only first level of
> tree. And query above becomes: '6 | void'.

> Firstly I made recursive dropvoidsubtree(). But attached patch cleans
> query tree in dofindsubquery() to avoid extra tree scan.

This patch looks good to me.  I have to admit that I'd been suspicious
of dropvoidsubtree() the last time I looked at this code, but I didn't
have adequate reason to touch it.  Pushed with some minor comment
adjustments.

			regards, tom lane


-- 
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers



^ permalink  raw  reply  [nested|flat] 3+ messages in thread


end of thread, other threads:[~2016-12-11 18:12 UTC | newest]

Thread overview: 3+ messages (download: mbox mbox.gz follow: Atom feed)
-- links below jump to the message on this page --
2016-12-07 06:06 [sqlsmith] Crash in tsquery_rewrite/QTNBinary Andreas Seltenreich <seltenreich@gmx.de>
2016-12-10 21:07 ` Artur Zakirov <a.zakirov@postgrespro.ru>
2016-12-11 18:12   ` Tom Lane <tgl@sss.pgh.pa.us>

This inbox is served by DDX for PostgreSQL; see mirroring instructions
for how to clone and mirror all data and code used for this inbox