Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings

Commit890a73b

Browse files
committed
Fix runtime partition pruning for HASH partitioned tables
This could only affect HASH partitioned tables with at least 2 partitionkey columns.If partition pruning was delayed until execution and the query containedan IS NULL qual on one of the partitioned keys, and some subsequentpartitioned key was being compared to a non-Const, then this could resultin a crash due to the incorrect keyno being used to calculate thestateidx for the expression evaluation code.Here we fix this by properly skipping partitioned keys which have anullkey set. Effectively, this must be the same as what's going oninside perform_pruning_base_step().Sergei Glukhov also provided a patch, but that's not what's being usedhere.Reported-by: Sergei GlukhovReviewed-by: tender wang, Sergei GlukhovDiscussion:https://postgr.es/m/d05b26fa-af54-27e1-f693-6c31590802fa@postgrespro.ruBackpatch-through: 11, where runtime partition pruning was added.
1 parentd6370a3 commit890a73b

File tree

3 files changed

+57
-15
lines changed

3 files changed

+57
-15
lines changed

‎src/backend/executor/execPartition.c

Lines changed: 17 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1878,7 +1878,7 @@ ExecInitPruningContext(PartitionPruneContext *context,
18781878
foreach(lc,pruning_steps)
18791879
{
18801880
PartitionPruneStepOp*step= (PartitionPruneStepOp*)lfirst(lc);
1881-
ListCell*lc2;
1881+
ListCell*lc2=list_head(step->exprs);
18821882
intkeyno;
18831883

18841884
/* not needed for other step kinds */
@@ -1887,22 +1887,27 @@ ExecInitPruningContext(PartitionPruneContext *context,
18871887

18881888
Assert(list_length(step->exprs) <=partnatts);
18891889

1890-
keyno=0;
1891-
foreach(lc2,step->exprs)
1890+
for (keyno=0;keyno<partnatts;keyno++)
18921891
{
1893-
Expr*expr= (Expr*)lfirst(lc2);
1892+
if (bms_is_member(keyno,step->nullkeys))
1893+
continue;
18941894

1895-
/* not needed for Consts */
1896-
if (!IsA(expr,Const))
1895+
if (lc2!=NULL)
18971896
{
1898-
intstateidx=PruneCxtStateIdx(partnatts,
1899-
step->step.step_id,
1900-
keyno);
1897+
Expr*expr=lfirst(lc2);
19011898

1902-
context->exprstates[stateidx]=
1903-
ExecInitExpr(expr,context->planstate);
1899+
/* not needed for Consts */
1900+
if (!IsA(expr,Const))
1901+
{
1902+
intstateidx=PruneCxtStateIdx(partnatts,
1903+
step->step.step_id,
1904+
keyno);
1905+
1906+
context->exprstates[stateidx]=
1907+
ExecInitExpr(expr,context->planstate);
1908+
}
1909+
lc2=lnext(step->exprs,lc2);
19041910
}
1905-
keyno++;
19061911
}
19071912
}
19081913
}

‎src/test/regress/expected/partition_prune.out

Lines changed: 21 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1948,7 +1948,6 @@ explain (costs off) select * from hp where a = 1 and b = 'abcde' and
19481948
One-Time Filter: false
19491949
(2 rows)
19501950

1951-
drop table hp;
19521951
--
19531952
-- Test runtime partition pruning
19541953
--
@@ -2070,6 +2069,27 @@ explain (analyze, costs off, summary off, timing off) execute ab_q3 (2, 2);
20702069
Filter: ((b >= $1) AND (b <= $2) AND (a < $0))
20712070
(10 rows)
20722071

2072+
--
2073+
-- Test runtime pruning with hash partitioned tables
2074+
--
2075+
-- recreate partitions dropped above
2076+
create table hp1 partition of hp for values with (modulus 4, remainder 1);
2077+
create table hp2 partition of hp for values with (modulus 4, remainder 2);
2078+
create table hp3 partition of hp for values with (modulus 4, remainder 3);
2079+
-- Ensure we correctly prune unneeded partitions when there is an IS NULL qual
2080+
prepare hp_q1 (text) as
2081+
select * from hp where a is null and b = $1;
2082+
explain (costs off) execute hp_q1('xxx');
2083+
QUERY PLAN
2084+
--------------------------------------------
2085+
Append
2086+
Subplans Removed: 3
2087+
-> Seq Scan on hp2 hp_1
2088+
Filter: ((a IS NULL) AND (b = $1))
2089+
(4 rows)
2090+
2091+
deallocate hp_q1;
2092+
drop table hp;
20732093
-- Test a backwards Append scan
20742094
create table list_part (a int) partition by list (a);
20752095
create table list_part1 partition of list_part for values in (1);

‎src/test/regress/sql/partition_prune.sql

Lines changed: 19 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -384,8 +384,6 @@ drop table hp2;
384384
explain (costs off)select*from hpwhere a=1and b='abcde'and
385385
(c=2or c=3);
386386

387-
droptable hp;
388-
389387
--
390388
-- Test runtime partition pruning
391389
--
@@ -436,6 +434,25 @@ select a from ab where b between $1 and $2 and a < (select 3);
436434

437435
explain (analyze, costs off, summary off, timing off) execute ab_q3 (2,2);
438436

437+
--
438+
-- Test runtime pruning with hash partitioned tables
439+
--
440+
441+
-- recreate partitions dropped above
442+
createtablehp1 partition of hp forvalues with (modulus4, remainder1);
443+
createtablehp2 partition of hp forvalues with (modulus4, remainder2);
444+
createtablehp3 partition of hp forvalues with (modulus4, remainder3);
445+
446+
-- Ensure we correctly prune unneeded partitions when there is an IS NULL qual
447+
prepare hp_q1 (text)as
448+
select*from hpwhere a isnulland b= $1;
449+
450+
explain (costs off) execute hp_q1('xxx');
451+
452+
deallocate hp_q1;
453+
454+
droptable hp;
455+
439456
-- Test a backwards Append scan
440457
createtablelist_part (aint) partition by list (a);
441458
createtablelist_part1 partition of list_part forvaluesin (1);

0 commit comments

Comments
 (0)

[8]ページ先頭

©2009-2025 Movatter.jp