Skip to content

Commit 719f2f5

Browse files
committed
add blank PartitionFilter node (replaces RuntimeInsert), move nodes' static initialization code to init_XXX_static_data()
1 parent e0b080f commit 719f2f5

11 files changed

+283
-104
lines changed

Makefile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
# contrib/pg_pathman/Makefile
22

33
MODULE_big = pg_pathman
4-
OBJS = src/init.o src/utils.o src/runtimeappend.o src/runtime_merge_append.o src/pg_pathman.o src/dsm_array.o \
4+
OBJS = src/init.o src/utils.o src/partition_filter.o src/runtimeappend.o src/runtime_merge_append.o src/pg_pathman.o src/dsm_array.o \
55
src/rangeset.o src/pl_funcs.o src/worker.o src/hooks.o src/nodes_common.o $(WIN32RES)
66

77
EXTENSION = pg_pathman

src/hooks.c

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
#include "pathman.h"
1616
#include "runtimeappend.h"
1717
#include "runtime_merge_append.h"
18+
#include "partition_filter.h"
1819
#include "utils.h"
1920

2021

@@ -346,14 +347,16 @@ void pg_pathman_enable_assign_hook(bool newval, void *extra)
346347
/* Return quickly if nothing has changed */
347348
if (newval == (pg_pathman_enable &&
348349
pg_pathman_enable_runtimeappend &&
349-
pg_pathman_enable_runtime_merge_append))
350+
pg_pathman_enable_runtime_merge_append &&
351+
pg_pathman_enable_partition_filter))
350352
return;
351353

352354
pg_pathman_enable_runtime_merge_append = newval;
353355
pg_pathman_enable_runtimeappend = newval;
356+
pg_pathman_enable_partition_filter = newval;
354357

355358
elog(NOTICE,
356-
"RuntimeAppend and RuntimeMergeAppend nodes have been %s",
359+
"RuntimeAppend, RuntimeMergeAppend and PartitionFilter nodes have been %s",
357360
newval ? "enabled" : "disabled");
358361
}
359362

src/partition_filter.c

Lines changed: 155 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,155 @@
1+
#include "partition_filter.h"
2+
#include "utils/guc.h"
3+
4+
5+
bool pg_pathman_enable_partition_filter = true;
6+
7+
CustomScanMethods partition_filter_plan_methods;
8+
CustomExecMethods partition_filter_exec_methods;
9+
10+
11+
12+
void
13+
init_partition_filter_static_data(void)
14+
{
15+
partition_filter_plan_methods.CustomName = "PartitionFilter";
16+
partition_filter_plan_methods.CreateCustomScanState = partition_filter_create_scan_state;
17+
18+
partition_filter_exec_methods.CustomName = "PartitionFilter";
19+
partition_filter_exec_methods.BeginCustomScan = partition_filter_begin;
20+
partition_filter_exec_methods.ExecCustomScan = partition_filter_exec;
21+
partition_filter_exec_methods.EndCustomScan = partition_filter_end;
22+
partition_filter_exec_methods.ReScanCustomScan = partition_filter_rescan;
23+
partition_filter_exec_methods.MarkPosCustomScan = NULL;
24+
partition_filter_exec_methods.RestrPosCustomScan = NULL;
25+
partition_filter_exec_methods.ExplainCustomScan = partition_filter_explain;
26+
27+
DefineCustomBoolVariable("pg_pathman.enable_partitionfilter",
28+
"Enables the planner's use of PartitionFilter custom node.",
29+
NULL,
30+
&pg_pathman_enable_partition_filter,
31+
true,
32+
PGC_USERSET,
33+
0,
34+
NULL,
35+
NULL,
36+
NULL);
37+
}
38+
39+
Plan *
40+
create_partition_filter_plan(Plan *subplan, PartRelationInfo *prel)
41+
{
42+
CustomScan *cscan = makeNode(CustomScan);
43+
44+
cscan->scan.plan.startup_cost = subplan->startup_cost;
45+
cscan->scan.plan.total_cost = subplan->total_cost;
46+
cscan->scan.plan.plan_rows = subplan->plan_rows;
47+
cscan->scan.plan.plan_width = subplan->plan_width;
48+
49+
cscan->scan.plan.qual = NIL;
50+
51+
cscan->custom_plans = list_make1(subplan);
52+
53+
cscan->scan.plan.targetlist = subplan->targetlist;
54+
55+
/* No relation will be scanned */
56+
cscan->scan.scanrelid = 0;
57+
cscan->custom_scan_tlist = subplan->targetlist;
58+
59+
cscan->methods = &partition_filter_plan_methods;
60+
61+
return &cscan->scan.plan;
62+
}
63+
64+
Node *
65+
partition_filter_create_scan_state(CustomScan *node)
66+
{
67+
PartitionFilterState *state = palloc0(sizeof(PartitionFilterState));
68+
69+
NodeSetTag(state, T_CustomScanState);
70+
71+
state->css.flags = node->flags;
72+
state->css.methods = &partition_filter_exec_methods;
73+
74+
state->subplan = (Plan *) linitial(node->custom_plans);
75+
76+
return (Node *) state;
77+
}
78+
79+
void
80+
partition_filter_begin(CustomScanState *node, EState *estate, int eflags)
81+
{
82+
PartitionFilterState *state = (PartitionFilterState *) node;
83+
84+
node->custom_ps = list_make1(ExecInitNode(state->subplan, estate, eflags));
85+
86+
state->firstStart = true;
87+
}
88+
89+
TupleTableSlot *
90+
partition_filter_exec(CustomScanState *node)
91+
{
92+
PartitionFilterState *state = (PartitionFilterState *) node;
93+
94+
EState *estate = node->ss.ps.state;
95+
PlanState *child_ps = (PlanState *) linitial(node->custom_ps);
96+
TupleTableSlot *slot;
97+
98+
if (state->firstStart)
99+
state->savedRelInfo = estate->es_result_relation_info;
100+
101+
slot = ExecProcNode(child_ps);
102+
103+
if (!TupIsNull(slot))
104+
{
105+
/* estate->es_result_relation_info = NULL; */
106+
107+
return slot;
108+
}
109+
110+
return NULL;
111+
}
112+
113+
void
114+
partition_filter_end(CustomScanState *node)
115+
{
116+
Assert(list_length(node->custom_ps) == 1);
117+
118+
ExecEndNode((PlanState *) linitial(node->custom_ps));
119+
}
120+
121+
void
122+
partition_filter_rescan(CustomScanState *node)
123+
{
124+
Assert(list_length(node->custom_ps) == 1);
125+
126+
ExecReScan((PlanState *) linitial(node->custom_ps));
127+
}
128+
129+
void
130+
partition_filter_explain(CustomScanState *node, List *ancestors, ExplainState *es)
131+
{
132+
/* Nothing to do here now */
133+
}
134+
135+
/* Add proxy PartitionFilter nodes to subplans of ModifyTable node */
136+
void
137+
add_partition_filters(List *rtable, ModifyTable *modify_table)
138+
{
139+
ListCell *lc1,
140+
*lc2;
141+
142+
Assert(IsA(modify_table, ModifyTable));
143+
144+
if (!pg_pathman_enable_partition_filter)
145+
return;
146+
147+
forboth (lc1, modify_table->plans, lc2, modify_table->resultRelations)
148+
{
149+
Index rindex = lfirst_int(lc2);
150+
PartRelationInfo *prel = get_pathman_relation_info(getrelid(rindex, rtable),
151+
NULL);
152+
if (prel)
153+
lfirst(lc1) = create_partition_filter_plan((Plan *) lfirst(lc1), prel);
154+
}
155+
}

src/partition_filter.h

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
#ifndef RUNTIME_INSERT_H
2+
#define RUNTIME_INSERT_H
3+
4+
#include "postgres.h"
5+
#include "optimizer/paths.h"
6+
#include "optimizer/pathnode.h"
7+
8+
#include "pathman.h"
9+
#include "nodes_common.h"
10+
11+
12+
typedef struct
13+
{
14+
CustomScanState css;
15+
bool firstStart;
16+
ResultRelInfo *savedRelInfo;
17+
Plan *subplan;
18+
} PartitionFilterState;
19+
20+
21+
extern bool pg_pathman_enable_partition_filter;
22+
23+
extern CustomScanMethods partition_filter_plan_methods;
24+
extern CustomExecMethods partition_filter_exec_methods;
25+
26+
27+
void add_partition_filters(List *rtable, ModifyTable *modify_table);
28+
29+
void init_partition_filter_static_data(void);
30+
31+
Plan * create_partition_filter_plan(Plan *subplan, PartRelationInfo *prel);
32+
33+
Node * partition_filter_create_scan_state(CustomScan *node);
34+
35+
void partition_filter_begin(CustomScanState *node, EState *estate, int eflags);
36+
37+
TupleTableSlot * partition_filter_exec(CustomScanState *node);
38+
39+
void partition_filter_end(CustomScanState *node);
40+
41+
void partition_filter_rescan(CustomScanState *node);
42+
43+
void partition_filter_explain(CustomScanState *node, List *ancestors, ExplainState *es);
44+
45+
#endif

src/pg_pathman.c

Lines changed: 9 additions & 53 deletions
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@
4242
#include "hooks.h"
4343
#include "runtimeappend.h"
4444
#include "runtime_merge_append.h"
45+
#include "partition_filter.h"
4546

4647
PG_MODULE_MAGIC;
4748

@@ -159,37 +160,9 @@ _PG_init(void)
159160
planner_hook_original = planner_hook;
160161
planner_hook = pathman_planner_hook;
161162

162-
/* RuntimeAppend */
163-
runtimeappend_path_methods.CustomName = "RuntimeAppend";
164-
runtimeappend_path_methods.PlanCustomPath = create_runtimeappend_plan;
165-
166-
runtimeappend_plan_methods.CustomName = "RuntimeAppend";
167-
runtimeappend_plan_methods.CreateCustomScanState = runtimeappend_create_scan_state;
168-
169-
runtimeappend_exec_methods.CustomName = "RuntimeAppend";
170-
runtimeappend_exec_methods.BeginCustomScan = runtimeappend_begin;
171-
runtimeappend_exec_methods.ExecCustomScan = runtimeappend_exec;
172-
runtimeappend_exec_methods.EndCustomScan = runtimeappend_end;
173-
runtimeappend_exec_methods.ReScanCustomScan = runtimeappend_rescan;
174-
runtimeappend_exec_methods.MarkPosCustomScan = NULL;
175-
runtimeappend_exec_methods.RestrPosCustomScan = NULL;
176-
runtimeappend_exec_methods.ExplainCustomScan = runtimeappend_explain;
177-
178-
/* RuntimeMergeAppend */
179-
runtime_merge_append_path_methods.CustomName = "RuntimeMergeAppend";
180-
runtime_merge_append_path_methods.PlanCustomPath = create_runtimemergeappend_plan;
181-
182-
runtime_merge_append_plan_methods.CustomName = "RuntimeMergeAppend";
183-
runtime_merge_append_plan_methods.CreateCustomScanState = runtimemergeappend_create_scan_state;
184-
185-
runtime_merge_append_exec_methods.CustomName = "RuntimeMergeAppend";
186-
runtime_merge_append_exec_methods.BeginCustomScan = runtimemergeappend_begin;
187-
runtime_merge_append_exec_methods.ExecCustomScan = runtimemergeappend_exec;
188-
runtime_merge_append_exec_methods.EndCustomScan = runtimemergeappend_end;
189-
runtime_merge_append_exec_methods.ReScanCustomScan = runtimemergeappend_rescan;
190-
runtime_merge_append_exec_methods.MarkPosCustomScan = NULL;
191-
runtime_merge_append_exec_methods.RestrPosCustomScan = NULL;
192-
runtime_merge_append_exec_methods.ExplainCustomScan = runtimemergeappend_explain;
163+
init_runtimeappend_static_data();
164+
init_runtime_merge_append_static_data();
165+
init_partition_filter_static_data();
193166

194167
DefineCustomBoolVariable("pg_pathman.enable",
195168
"Enables pg_pathman's optimizations during the planner stage",
@@ -201,28 +174,6 @@ _PG_init(void)
201174
NULL,
202175
pg_pathman_enable_assign_hook,
203176
NULL);
204-
205-
DefineCustomBoolVariable("pg_pathman.enable_runtimeappend",
206-
"Enables the planner's use of RuntimeAppend custom node.",
207-
NULL,
208-
&pg_pathman_enable_runtimeappend,
209-
true,
210-
PGC_USERSET,
211-
0,
212-
NULL,
213-
NULL,
214-
NULL);
215-
216-
DefineCustomBoolVariable("pg_pathman.enable_runtimemergeappend",
217-
"Enables the planner's use of RuntimeMergeAppend custom node.",
218-
NULL,
219-
&pg_pathman_enable_runtime_merge_append,
220-
true,
221-
PGC_USERSET,
222-
0,
223-
NULL,
224-
NULL,
225-
NULL);
226177
}
227178

228179
PartRelationInfo *
@@ -301,6 +252,11 @@ pathman_planner_hook(Query *parse, int cursorOptions, ParamListInfo boundParams)
301252
disable_inheritance_subselect(parse);
302253
handle_modification_query(parse);
303254
break;
255+
case CMD_INSERT:
256+
result = standard_planner(parse, cursorOptions, boundParams);
257+
add_partition_filters(result->rtable,
258+
(ModifyTable *) result->planTree);
259+
return result;
304260
default:
305261
break;
306262
}

src/runtime_insert.c

Lines changed: 0 additions & 1 deletion
This file was deleted.

src/runtime_insert.h

Lines changed: 0 additions & 47 deletions
This file was deleted.

0 commit comments

Comments
 (0)
pFad - Phonifier reborn

Pfad - The Proxy pFad of © 2024 Garber Painting. All rights reserved.

Note: This service is not intended for secure transactions such as banking, social media, email, or purchasing. Use at your own risk. We assume no liability whatsoever for broken pages.


Alternative Proxies:

Alternative Proxy

pFad Proxy

pFad v3 Proxy

pFad v4 Proxy