diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/backend/optimizer/path/joinpath.c | 21 | ||||
| -rw-r--r-- | src/test/regress/expected/join.out | 27 | ||||
| -rw-r--r-- | src/test/regress/sql/join.sql | 20 |
3 files changed, 62 insertions, 6 deletions
diff --git a/src/backend/optimizer/path/joinpath.c b/src/backend/optimizer/path/joinpath.c index 3b9407eb2eb..ea5b6415186 100644 --- a/src/backend/optimizer/path/joinpath.c +++ b/src/backend/optimizer/path/joinpath.c @@ -2260,10 +2260,20 @@ hash_inner_and_outer(PlannerInfo *root, /* * If the joinrel is parallel-safe, we may be able to consider a - * partial hash join. However, the resulting path must not be - * parameterized. + * partial hash join. + * + * However, we can't handle JOIN_RIGHT_SEMI, because the hash table is + * either a shared hash table or a private hash table per backend. In + * the shared case, there is no concurrency protection for the match + * flags, so multiple workers could inspect and set the flags + * concurrently, potentially producing incorrect results. In the + * private case, each worker has its own copy of the hash table, so no + * single process has all the match flags. + * + * Also, the resulting path must not be parameterized. */ if (joinrel->consider_parallel && + jointype != JOIN_RIGHT_SEMI && outerrel->partial_pathlist != NIL && bms_is_empty(joinrel->lateral_relids)) { @@ -2294,13 +2304,12 @@ hash_inner_and_outer(PlannerInfo *root, * Normally, given that the joinrel is parallel-safe, the cheapest * total inner path will also be parallel-safe, but if not, we'll * have to search for the cheapest safe, unparameterized inner - * path. If full, right, right-semi or right-anti join, we can't - * use parallelism (building the hash table in each backend) - * because no one process has all the match bits. + * path. If full, right, or right-anti join, we can't use + * parallelism (building the hash table in each backend) because + * no one process has all the match bits. */ if (jointype == JOIN_FULL || jointype == JOIN_RIGHT || - jointype == JOIN_RIGHT_SEMI || jointype == JOIN_RIGHT_ANTI) cheapest_safe_inner = NULL; else if (cheapest_total_inner->parallel_safe) diff --git a/src/test/regress/expected/join.out b/src/test/regress/expected/join.out index d10095de70f..0e82ca1867a 100644 --- a/src/test/regress/expected/join.out +++ b/src/test/regress/expected/join.out @@ -3081,6 +3081,33 @@ select * from tbl_rs t1 join (6 rows) -- +-- regression test for bug with parallel-hash-right-semi join +-- +begin; +-- encourage use of parallel plans +set local parallel_setup_cost=0; +set local parallel_tuple_cost=0; +set local min_parallel_table_scan_size=0; +set local max_parallel_workers_per_gather=4; +-- ensure we don't get parallel hash right semi join +explain (costs off) +select * from tenk1 t1 +where exists (select 1 from tenk1 t2 where fivethous = t1.fivethous) +and t1.fivethous < 5; + QUERY PLAN +-------------------------------------------------- + Gather + Workers Planned: 4 + -> Parallel Hash Semi Join + Hash Cond: (t1.fivethous = t2.fivethous) + -> Parallel Seq Scan on tenk1 t1 + Filter: (fivethous < 5) + -> Parallel Hash + -> Parallel Seq Scan on tenk1 t2 +(8 rows) + +rollback; +-- -- regression test for bug #13908 (hash join with skew tuples & nbatch increase) -- set work_mem to '64kB'; diff --git a/src/test/regress/sql/join.sql b/src/test/regress/sql/join.sql index b1732453e8d..c6b8b09a381 100644 --- a/src/test/regress/sql/join.sql +++ b/src/test/regress/sql/join.sql @@ -760,6 +760,26 @@ select * from tbl_rs t1 join on true; -- +-- regression test for bug with parallel-hash-right-semi join +-- + +begin; + +-- encourage use of parallel plans +set local parallel_setup_cost=0; +set local parallel_tuple_cost=0; +set local min_parallel_table_scan_size=0; +set local max_parallel_workers_per_gather=4; + +-- ensure we don't get parallel hash right semi join +explain (costs off) +select * from tenk1 t1 +where exists (select 1 from tenk1 t2 where fivethous = t1.fivethous) +and t1.fivethous < 5; + +rollback; + +-- -- regression test for bug #13908 (hash join with skew tuples & nbatch increase) -- |
