Columnar: always disable parallel paths. (#4617)

Previously, if columnar.enable_custom_scan was false, parallel paths
could remain, leading to an unexpected error.

Also, ensure that cheapest_parameterized_paths is cleared if a custom
scan is used.

Co-authored-by: Jeff Davis <jefdavi@microsoft.com>
pull/4619/head
jeff-davis 2021-02-02 11:37:42 -08:00 committed by GitHub
parent 3ca0b6146b
commit e195af7e72
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 107 additions and 13 deletions

View File

@ -139,11 +139,12 @@ columnar_customscan_init()
static void
clear_paths(RelOptInfo *rel)
{
rel->pathlist = NULL;
rel->partial_pathlist = NULL;
rel->pathlist = NIL;
rel->partial_pathlist = NIL;
rel->cheapest_startup_path = NULL;
rel->cheapest_total_path = NULL;
rel->cheapest_unique_path = NULL;
rel->cheapest_parameterized_paths = NIL;
}
@ -157,12 +158,6 @@ ColumnarSetRelPathlistHook(PlannerInfo *root, RelOptInfo *rel, Index rti,
PreviousSetRelPathlistHook(root, rel, rti, rte);
}
if (!EnableColumnarCustomScan)
{
/* custon scans are disabled, use normal table access method api instead */
return;
}
if (!OidIsValid(rte->relid) || rte->rtekind != RTE_RELATION)
{
/* some calls to the pathlist hook don't have a valid relation set. Do nothing */
@ -183,13 +178,19 @@ ColumnarSetRelPathlistHook(PlannerInfo *root, RelOptInfo *rel, Index rti,
errmsg("sample scans not supported on columnar tables")));
}
Path *customPath = CreateColumnarScanPath(root, rel, rte);
/* columnar doesn't support parallel paths */
rel->partial_pathlist = NIL;
ereport(DEBUG1, (errmsg("pathlist hook for columnar table am")));
if (EnableColumnarCustomScan)
{
Path *customPath = CreateColumnarScanPath(root, rel, rte);
/* we propose a new path that will be the only path for scanning this relation */
clear_paths(rel);
add_path(rel, customPath);
ereport(DEBUG1, (errmsg("pathlist hook for columnar table am")));
/* we propose a new path that will be the only path for scanning this relation */
clear_paths(rel);
add_path(rel, customPath);
}
}
RelationClose(relation);
}

View File

@ -8,6 +8,7 @@ test: am_query
test: am_analyze
test: am_data_types
test: am_drop
test: columnar_fallback_scan
test: am_empty
test: am_insert
test: am_update_delete

View File

@ -0,0 +1,53 @@
--
-- columnar_fallback_scan.sql
--
-- Test columnar.enable_custom_scan = false, which will use an
-- ordinary sequential scan. It won't benefit from projection pushdown
-- or qual pushdown, but it should return the correct results.
--
set columnar.enable_custom_scan = false;
create table fallback_scan(i int) using columnar;
-- large enough to test parallel_workers > 1
select alter_columnar_table_set('fallback_scan', compression => 'none');
alter_columnar_table_set
---------------------------------------------------------------------
(1 row)
insert into fallback_scan select generate_series(1,150000);
vacuum analyze fallback_scan;
select count(*), min(i), max(i), avg(i) from fallback_scan;
count | min | max | avg
---------------------------------------------------------------------
150000 | 1 | 150000 | 75000.500000000000
(1 row)
--
-- Negative test: try to force a parallel plan with at least two
-- workers, but columnar should reject it and use a non-parallel scan.
--
set force_parallel_mode = regress;
set min_parallel_table_scan_size = 1;
set parallel_tuple_cost = 0;
set max_parallel_workers = 4;
set max_parallel_workers_per_gather = 4;
explain (costs off) select count(*), min(i), max(i), avg(i) from fallback_scan;
QUERY PLAN
---------------------------------------------------------------------
Aggregate
-> Seq Scan on fallback_scan
(2 rows)
select count(*), min(i), max(i), avg(i) from fallback_scan;
count | min | max | avg
---------------------------------------------------------------------
150000 | 1 | 150000 | 75000.500000000000
(1 row)
set force_parallel_mode to default;
set min_parallel_table_scan_size to default;
set parallel_tuple_cost to default;
set max_parallel_workers to default;
set max_parallel_workers_per_gather to default;
set columnar.enable_custom_scan to default;
drop table fallback_scan;

View File

@ -0,0 +1,39 @@
--
-- columnar_fallback_scan.sql
--
-- Test columnar.enable_custom_scan = false, which will use an
-- ordinary sequential scan. It won't benefit from projection pushdown
-- or qual pushdown, but it should return the correct results.
--
set columnar.enable_custom_scan = false;
create table fallback_scan(i int) using columnar;
-- large enough to test parallel_workers > 1
select alter_columnar_table_set('fallback_scan', compression => 'none');
insert into fallback_scan select generate_series(1,150000);
vacuum analyze fallback_scan;
select count(*), min(i), max(i), avg(i) from fallback_scan;
--
-- Negative test: try to force a parallel plan with at least two
-- workers, but columnar should reject it and use a non-parallel scan.
--
set force_parallel_mode = regress;
set min_parallel_table_scan_size = 1;
set parallel_tuple_cost = 0;
set max_parallel_workers = 4;
set max_parallel_workers_per_gather = 4;
explain (costs off) select count(*), min(i), max(i), avg(i) from fallback_scan;
select count(*), min(i), max(i), avg(i) from fallback_scan;
set force_parallel_mode to default;
set min_parallel_table_scan_size to default;
set parallel_tuple_cost to default;
set max_parallel_workers to default;
set max_parallel_workers_per_gather to default;
set columnar.enable_custom_scan to default;
drop table fallback_scan;