Age Owner Branch data TLA Line data Source code
1 : : /*-------------------------------------------------------------------------
2 : : *
3 : : * nodeFuncs.h
4 : : * Various general-purpose manipulations of Node trees
5 : : *
6 : : * Portions Copyright (c) 1996-2024, PostgreSQL Global Development Group
7 : : * Portions Copyright (c) 1994, Regents of the University of California
8 : : *
9 : : * src/include/nodes/nodeFuncs.h
10 : : *
11 : : *-------------------------------------------------------------------------
12 : : */
13 : : #ifndef NODEFUNCS_H
14 : : #define NODEFUNCS_H
15 : :
16 : : #include "nodes/parsenodes.h"
17 : :
18 : : struct PlanState; /* avoid including execnodes.h too */
19 : :
20 : :
21 : : /* flags bits for query_tree_walker and query_tree_mutator */
22 : : #define QTW_IGNORE_RT_SUBQUERIES 0x01 /* subqueries in rtable */
23 : : #define QTW_IGNORE_CTE_SUBQUERIES 0x02 /* subqueries in cteList */
24 : : #define QTW_IGNORE_RC_SUBQUERIES 0x03 /* both of above */
25 : : #define QTW_IGNORE_JOINALIASES 0x04 /* JOIN alias var lists */
26 : : #define QTW_IGNORE_RANGE_TABLE 0x08 /* skip rangetable entirely */
27 : : #define QTW_EXAMINE_RTES_BEFORE 0x10 /* examine RTE nodes before their
28 : : * contents */
29 : : #define QTW_EXAMINE_RTES_AFTER 0x20 /* examine RTE nodes after their
30 : : * contents */
31 : : #define QTW_DONT_COPY_QUERY 0x40 /* do not copy top Query */
32 : : #define QTW_EXAMINE_SORTGROUP 0x80 /* include SortGroupClause lists */
33 : :
34 : : /* callback function for check_functions_in_node */
35 : : typedef bool (*check_function_callback) (Oid func_id, void *context);
36 : :
37 : : /* callback functions for tree walkers */
38 : : typedef bool (*tree_walker_callback) (Node *node, void *context);
39 : : typedef bool (*planstate_tree_walker_callback) (struct PlanState *planstate,
40 : : void *context);
41 : :
42 : : /* callback functions for tree mutators */
43 : : typedef Node *(*tree_mutator_callback) (Node *node, void *context);
44 : :
45 : :
46 : : extern Oid exprType(const Node *expr);
47 : : extern int32 exprTypmod(const Node *expr);
48 : : extern bool exprIsLengthCoercion(const Node *expr, int32 *coercedTypmod);
49 : : extern Node *applyRelabelType(Node *arg, Oid rtype, int32 rtypmod, Oid rcollid,
50 : : CoercionForm rformat, int rlocation,
51 : : bool overwrite_ok);
52 : : extern Node *relabel_to_typmod(Node *expr, int32 typmod);
53 : : extern Node *strip_implicit_coercions(Node *node);
54 : : extern bool expression_returns_set(Node *clause);
55 : :
56 : : extern Oid exprCollation(const Node *expr);
57 : : extern Oid exprInputCollation(const Node *expr);
58 : : extern void exprSetCollation(Node *expr, Oid collation);
59 : : extern void exprSetInputCollation(Node *expr, Oid inputcollation);
60 : :
61 : : extern int exprLocation(const Node *expr);
62 : :
63 : : extern void fix_opfuncids(Node *node);
64 : : extern void set_opfuncid(OpExpr *opexpr);
65 : : extern void set_sa_opfuncid(ScalarArrayOpExpr *opexpr);
66 : :
67 : : /* Is clause a FuncExpr clause? */
68 : : static inline bool
1902 tgl@sss.pgh.pa.us 69 :CBC 33003 : is_funcclause(const void *clause)
70 : : {
71 [ + - + + ]: 33003 : return clause != NULL && IsA(clause, FuncExpr);
72 : : }
73 : :
74 : : /* Is clause an OpExpr clause? */
75 : : static inline bool
76 : 2217603 : is_opclause(const void *clause)
77 : : {
78 [ + - + + ]: 2217603 : return clause != NULL && IsA(clause, OpExpr);
79 : : }
80 : :
81 : : /* Extract left arg of a binary opclause, or only arg of a unary opclause */
82 : : static inline Node *
83 : 733552 : get_leftop(const void *clause)
84 : : {
85 : 733552 : const OpExpr *expr = (const OpExpr *) clause;
86 : :
87 [ + - ]: 733552 : if (expr->args != NIL)
88 : 733552 : return (Node *) linitial(expr->args);
89 : : else
1902 tgl@sss.pgh.pa.us 90 :UBC 0 : return NULL;
91 : : }
92 : :
93 : : /* Extract right arg of a binary opclause (NULL if it's a unary opclause) */
94 : : static inline Node *
1902 tgl@sss.pgh.pa.us 95 :CBC 699181 : get_rightop(const void *clause)
96 : : {
97 : 699181 : const OpExpr *expr = (const OpExpr *) clause;
98 : :
99 [ + - ]: 699181 : if (list_length(expr->args) >= 2)
100 : 699181 : return (Node *) lsecond(expr->args);
101 : : else
1902 tgl@sss.pgh.pa.us 102 :UBC 0 : return NULL;
103 : : }
104 : :
105 : : /* Is clause an AND clause? */
106 : : static inline bool
1902 tgl@sss.pgh.pa.us 107 :CBC 2807416 : is_andclause(const void *clause)
108 : : {
109 : 2807416 : return (clause != NULL &&
110 [ + - + + ]: 3002540 : IsA(clause, BoolExpr) &&
111 [ + + ]: 195124 : ((const BoolExpr *) clause)->boolop == AND_EXPR);
112 : : }
113 : :
114 : : /* Is clause an OR clause? */
115 : : static inline bool
116 : 1863694 : is_orclause(const void *clause)
117 : : {
118 : 1863694 : return (clause != NULL &&
119 [ + - + + ]: 1989745 : IsA(clause, BoolExpr) &&
120 [ + + ]: 126051 : ((const BoolExpr *) clause)->boolop == OR_EXPR);
121 : : }
122 : :
123 : : /* Is clause a NOT clause? */
124 : : static inline bool
125 : 459588 : is_notclause(const void *clause)
126 : : {
127 : 459588 : return (clause != NULL &&
128 [ + - + + ]: 481822 : IsA(clause, BoolExpr) &&
129 [ + + ]: 22234 : ((const BoolExpr *) clause)->boolop == NOT_EXPR);
130 : : }
131 : :
132 : : /* Extract argument from a clause known to be a NOT clause */
133 : : static inline Expr *
134 : 6921 : get_notclausearg(const void *notclause)
135 : : {
136 : 6921 : return (Expr *) linitial(((const BoolExpr *) notclause)->args);
137 : : }
138 : :
139 : : extern bool check_functions_in_node(Node *node, check_function_callback checker,
140 : : void *context);
141 : :
142 : : /*
143 : : * The following functions are usually passed walker or mutator callbacks
144 : : * that are declared like "bool walker(Node *node, my_struct *context)"
145 : : * rather than "bool walker(Node *node, void *context)" as a strict reading
146 : : * of the C standard would require. Changing the callbacks' declarations
147 : : * to "void *" would create serious hazards of passing them the wrong context
148 : : * struct type, so we respectfully decline to support the standard's position
149 : : * that a pointer to struct is incompatible with "void *". Instead, silence
150 : : * related compiler warnings by inserting casts into these macro wrappers.
151 : : */
152 : :
153 : : #define expression_tree_walker(n, w, c) \
154 : : expression_tree_walker_impl(n, (tree_walker_callback) (w), c)
155 : : #define expression_tree_mutator(n, m, c) \
156 : : expression_tree_mutator_impl(n, (tree_mutator_callback) (m), c)
157 : :
158 : : #define query_tree_walker(q, w, c, f) \
159 : : query_tree_walker_impl(q, (tree_walker_callback) (w), c, f)
160 : : #define query_tree_mutator(q, m, c, f) \
161 : : query_tree_mutator_impl(q, (tree_mutator_callback) (m), c, f)
162 : :
163 : : #define range_table_walker(rt, w, c, f) \
164 : : range_table_walker_impl(rt, (tree_walker_callback) (w), c, f)
165 : : #define range_table_mutator(rt, m, c, f) \
166 : : range_table_mutator_impl(rt, (tree_mutator_callback) (m), c, f)
167 : :
168 : : #define range_table_entry_walker(r, w, c, f) \
169 : : range_table_entry_walker_impl(r, (tree_walker_callback) (w), c, f)
170 : :
171 : : #define query_or_expression_tree_walker(n, w, c, f) \
172 : : query_or_expression_tree_walker_impl(n, (tree_walker_callback) (w), c, f)
173 : : #define query_or_expression_tree_mutator(n, m, c, f) \
174 : : query_or_expression_tree_mutator_impl(n, (tree_mutator_callback) (m), c, f)
175 : :
176 : : #define raw_expression_tree_walker(n, w, c) \
177 : : raw_expression_tree_walker_impl(n, (tree_walker_callback) (w), c)
178 : :
179 : : #define planstate_tree_walker(ps, w, c) \
180 : : planstate_tree_walker_impl(ps, (planstate_tree_walker_callback) (w), c)
181 : :
182 : : extern bool expression_tree_walker_impl(Node *node,
183 : : tree_walker_callback walker,
184 : : void *context);
185 : : extern Node *expression_tree_mutator_impl(Node *node,
186 : : tree_mutator_callback mutator,
187 : : void *context);
188 : :
189 : : extern bool query_tree_walker_impl(Query *query,
190 : : tree_walker_callback walker,
191 : : void *context, int flags);
192 : : extern Query *query_tree_mutator_impl(Query *query,
193 : : tree_mutator_callback mutator,
194 : : void *context, int flags);
195 : :
196 : : extern bool range_table_walker_impl(List *rtable,
197 : : tree_walker_callback walker,
198 : : void *context, int flags);
199 : : extern List *range_table_mutator_impl(List *rtable,
200 : : tree_mutator_callback mutator,
201 : : void *context, int flags);
202 : :
203 : : extern bool range_table_entry_walker_impl(RangeTblEntry *rte,
204 : : tree_walker_callback walker,
205 : : void *context, int flags);
206 : :
207 : : extern bool query_or_expression_tree_walker_impl(Node *node,
208 : : tree_walker_callback walker,
209 : : void *context, int flags);
210 : : extern Node *query_or_expression_tree_mutator_impl(Node *node,
211 : : tree_mutator_callback mutator,
212 : : void *context, int flags);
213 : :
214 : : extern bool raw_expression_tree_walker_impl(Node *node,
215 : : tree_walker_callback walker,
216 : : void *context);
217 : :
218 : : extern bool planstate_tree_walker_impl(struct PlanState *planstate,
219 : : planstate_tree_walker_callback walker,
220 : : void *context);
221 : :
222 : : #endif /* NODEFUNCS_H */
|