47 List *pushed_down_joins,
61 List *new_restrictlist);
119 root->simple_rte_array[rti++] = rte;
125 root->append_rel_array = NULL;
146 if (root->append_rel_array[child_relid])
147 elog(
ERROR,
"child relation already exists");
149 root->append_rel_array[child_relid] = appinfo;
171 root->simple_rel_array =
174 root->simple_rte_array =
177 if (root->append_rel_array)
178 root->append_rel_array =
181 root->append_rel_array =
198 Assert(relid > 0 && relid < root->simple_rel_array_size);
199 if (root->simple_rel_array[relid] != NULL)
200 elog(
ERROR,
"rel %d already exists", relid);
203 rte = root->simple_rte_array[relid];
268 rel->fdwroutine = NULL;
269 rel->fdw_private = NULL;
279 rel->part_scheme = NULL;
281 rel->boundinfo = NULL;
284 rel->part_rels = NULL;
287 rel->partexprs = NULL;
288 rel->nullable_partexprs = NULL;
296 rel->parent = parent;
297 rel->top_parent = parent->top_parent ? parent->top_parent : parent;
327 rel->top_parent = NULL;
357 rel->attr_needed = (
Relids *)
359 rel->attr_widths = (
int32 *)
366 rel->attr_needed = NULL;
367 rel->attr_widths = NULL;
397 root->simple_rel_array[relid] = rel;
414 rel = root->simple_rel_array[relid];
419 elog(
ERROR,
"no relation entry for relid %d", relid);
433 return root->simple_rel_array[relid];
455 rel = root->simple_rel_array[relid];
464 rte = root->simple_rte_array[relid];
469 elog(
ERROR,
"no relation entry for relid %d", relid);
511 root->join_rel_hash = hashtab;
537 if (root->join_rel_hash)
593 joinrel->fdwroutine = outer_rel->fdwroutine;
601 joinrel->fdwroutine = outer_rel->fdwroutine;
609 joinrel->fdwroutine = outer_rel->fdwroutine;
626 if (root->join_rel_hash)
663 List *pushed_down_joins,
664 List **restrictlist_ptr)
683 if (restrictlist_ptr)
716 outer_rel, inner_rel);
721 joinrel->attr_needed = NULL;
722 joinrel->attr_widths = NULL;
740 joinrel->fdwroutine = NULL;
741 joinrel->fdw_private = NULL;
751 joinrel->parent = NULL;
752 joinrel->top_parent = NULL;
754 joinrel->part_scheme = NULL;
756 joinrel->boundinfo = NULL;
759 joinrel->part_rels = NULL;
762 joinrel->partexprs = NULL;
763 joinrel->nullable_partexprs = NULL;
799 outer_rel, inner_rel,
801 if (restrictlist_ptr)
802 *restrictlist_ptr = restrictlist;
819 sjinfo, restrictlist);
849 if (root->join_rel_level)
900 nappinfos, appinfos);
920 joinrel->attr_needed = NULL;
921 joinrel->attr_widths = NULL;
937 joinrel->fdwroutine = NULL;
938 joinrel->fdw_private = NULL;
945 joinrel->parent = parent_joinrel;
946 joinrel->top_parent = parent_joinrel->top_parent ? parent_joinrel->top_parent : parent_joinrel;
948 joinrel->part_scheme = NULL;
950 joinrel->boundinfo = NULL;
953 joinrel->part_rels = NULL;
956 joinrel->partexprs = NULL;
957 joinrel->nullable_partexprs = NULL;
964 nappinfos, appinfos);
994 sjinfo, restrictlist);
1010 nappinfos, appinfos,
1011 parent_joinrel, joinrel);
1108 List *pushed_down_joins,
1147 foreach(lc, pushed_down_joins)
1176 elog(
ERROR,
"unexpected node type in rel targetlist: %d",
1202 tuple_width += baserel->attr_widths[ndx];
1222 foreach(lc, pushed_down_joins)
1231 var->varnullingrels =
1297 Relids both_input_relids;
1307 both_input_relids,
NIL);
1309 both_input_relids, result);
1348 Relids both_input_relids,
1349 List *new_restrictlist)
1387 both_input_relids));
1407 return new_restrictlist;
1412 List *joininfo_list,
1420 foreach(l, joininfo_list)
1445 return new_joininfo;
1476 foreach(lc, root->upper_rels[kind])
1499 root->upper_rels[kind] =
lappend(root->upper_rels[kind], upperrel);
1586 pclauses =
lappend(pclauses, rinfo);
1602 foreach(lc, pclauses)
1657 List **restrict_clauses)
1688 if (outer_path->param_info)
1689 outer_and_req =
bms_union(outer_path->parent->relids,
1692 outer_and_req = NULL;
1693 if (inner_path->param_info)
1694 inner_and_req =
bms_union(inner_path->parent->relids,
1697 inner_and_req = NULL;
1708 outer_path->parent->relids,
1711 inner_path->parent->relids,
1713 pclauses =
lappend(pclauses, rinfo);
1724 foreach(lc, eclauses)
1732 outer_path->parent->relids,
1736 inner_path->parent->relids,
1740 Assert(rinfo->left_ec == rinfo->right_ec);
1741 dropped_ecs =
lappend(dropped_ecs, rinfo->left_ec);
1744 pclauses =
lappend(pclauses, rinfo);
1779 Relids real_outer_and_req;
1781 real_outer_and_req =
bms_union(outer_path->parent->relids,
1788 outer_path->parent);
1789 foreach(lc, eclauses)
1794 outer_path->parent->relids,
1795 real_outer_and_req));
1797 outer_path->parent->relids,
1799 pclauses =
lappend(pclauses, rinfo);
1808 *restrict_clauses =
list_concat(pclauses, *restrict_clauses);
1905 if (path->param_info == NULL)
1987 return path->param_info->ppi_serials;
2023 if (outer_rel->part_scheme == NULL || inner_rel->part_scheme == NULL ||
2026 outer_rel->part_scheme != inner_rel->part_scheme ||
2034 part_scheme = outer_rel->part_scheme;
2040 Assert(!joinrel->part_scheme && !joinrel->partexprs &&
2041 !joinrel->nullable_partexprs && !joinrel->part_rels &&
2042 !joinrel->boundinfo);
2051 joinrel->part_scheme = part_scheme;
2085 Assert(rel1->part_scheme == rel2->part_scheme);
2088 memset(pk_has_clause, 0,
sizeof(pk_has_clause));
2089 foreach(lc, restrictlist)
2104 if (!rinfo->can_join)
2108 if (!rinfo->mergeopfamilies && !
OidIsValid(rinfo->hashjoinoperator))
2188 pk_has_clause[ipk1] =
true;
2192 for (cnt_pks = 0; cnt_pks < part_scheme->
partnatts; cnt_pks++)
2194 if (!pk_has_clause[cnt_pks])
2218 Assert(rel->part_scheme);
2220 Assert(rel->nullable_partexprs);
2226 for (cnt = 0; cnt < rel->part_scheme->partnatts; cnt++)
2231 foreach(lc, rel->partexprs[cnt])
2247 foreach(lc, rel->nullable_partexprs[cnt])
2270 joinrel->nullable_partexprs =
2279 for (
int cnt = 0; cnt < partnatts; cnt++)
2282 const List *outer_expr = outer_rel->partexprs[cnt];
2283 const List *outer_null_expr = outer_rel->nullable_partexprs[cnt];
2284 const List *inner_expr = inner_rel->partexprs[cnt];
2285 const List *inner_null_expr = inner_rel->nullable_partexprs[cnt];
2287 List *nullable_partexpr =
NIL;
2317 nullable_partexpr =
list_copy(outer_null_expr);
2331 nullable_partexpr =
list_concat(nullable_partexpr,
2344 nullable_partexpr =
list_concat(nullable_partexpr,
2346 nullable_partexpr =
list_concat(nullable_partexpr,
2387 nullable_partexpr =
lappend(nullable_partexpr,
c);
2393 elog(
ERROR,
"unrecognized join type: %d", (
int) jointype);
2396 joinrel->partexprs[cnt] = partexpr;
2397 joinrel->nullable_partexprs[cnt] = nullable_partexpr;
2416 nappinfos, appinfos);
AppendRelInfo ** find_appinfos_by_relids(PlannerInfo *root, Relids relids, int *nappinfos)
Node * adjust_appendrel_attrs(PlannerInfo *root, Node *node, int nappinfos, AppendRelInfo **appinfos)
Relids adjust_child_relids(Relids relids, int nappinfos, AppendRelInfo **appinfos)
uint32 bitmap_hash(const void *key, Size keysize)
Bitmapset * bms_join(Bitmapset *a, Bitmapset *b)
bool bms_equal(const Bitmapset *a, const Bitmapset *b)
bool bms_is_subset(const Bitmapset *a, const Bitmapset *b)
int bms_num_members(const Bitmapset *a)
bool bms_is_member(int x, const Bitmapset *a)
Bitmapset * bms_make_singleton(int x)
Bitmapset * bms_add_member(Bitmapset *a, int x)
Bitmapset * bms_union(const Bitmapset *a, const Bitmapset *b)
Bitmapset * bms_intersect(const Bitmapset *a, const Bitmapset *b)
Bitmapset * bms_add_members(Bitmapset *a, const Bitmapset *b)
Bitmapset * bms_del_members(Bitmapset *a, const Bitmapset *b)
Bitmapset * bms_int_members(Bitmapset *a, const Bitmapset *b)
int bitmap_match(const void *key1, const void *key2, Size keysize)
bool bms_overlap(const Bitmapset *a, const Bitmapset *b)
Bitmapset * bms_copy(const Bitmapset *a)
bool bms_nonempty_difference(const Bitmapset *a, const Bitmapset *b)
#define OidIsValid(objectId)
bool is_parallel_safe(PlannerInfo *root, Node *node)
double get_parameterized_baserel_size(PlannerInfo *root, RelOptInfo *rel, List *param_clauses)
double get_parameterized_joinrel_size(PlannerInfo *root, RelOptInfo *rel, Path *outer_path, Path *inner_path, SpecialJoinInfo *sjinfo, List *restrict_clauses)
void set_joinrel_size_estimates(PlannerInfo *root, RelOptInfo *rel, RelOptInfo *outer_rel, RelOptInfo *inner_rel, SpecialJoinInfo *sjinfo, List *restrictlist)
bool enable_partitionwise_join
int32 clamp_width_est(int64 tuple_width)
void * hash_search(HTAB *hashp, const void *keyPtr, HASHACTION action, bool *foundPtr)
HTAB * hash_create(const char *tabname, long nelem, const HASHCTL *info, int flags)
bool equal(const void *a, const void *b)
List * generate_join_implied_equalities_for_ecs(PlannerInfo *root, List *eclasses, Relids join_relids, Relids outer_relids, RelOptInfo *inner_rel)
List * generate_join_implied_equalities(PlannerInfo *root, Relids join_relids, Relids outer_relids, RelOptInfo *inner_rel, SpecialJoinInfo *sjinfo)
void add_child_join_rel_equivalences(PlannerInfo *root, int nappinfos, AppendRelInfo **appinfos, RelOptInfo *parent_joinrel, RelOptInfo *child_joinrel)
bool has_relevant_eclass_joinclause(PlannerInfo *root, RelOptInfo *rel1)
#define palloc0_array(type, count)
bool apply_child_basequals(PlannerInfo *root, RelOptInfo *parentrel, RelOptInfo *childrel, RangeTblEntry *childRTE, AppendRelInfo *appinfo)
void mark_dummy_rel(RelOptInfo *rel)
Assert(fmt[strlen(fmt) - 1] !='\n')
List * lappend(List *list, void *datum)
List * list_copy(const List *oldlist)
bool list_member_oid(const List *list, Oid datum)
List * list_concat(List *list1, const List *list2)
List * list_append_unique_ptr(List *list, void *datum)
List * list_concat_copy(const List *list1, const List *list2)
bool op_in_opfamily(Oid opno, Oid opfamily)
Datum subpath(PG_FUNCTION_ARGS)
void pfree(void *pointer)
void * palloc0(Size size)
MemoryContext CurrentMemoryContext
Oid exprType(const Node *expr)
Oid exprCollation(const Node *expr)
#define IsA(nodeptr, _type_)
#define IS_OUTER_JOIN(jointype)
#define castNode(_type_, nodeptr)
#define repalloc0_array(pointer, type, oldcount, count)
RTEPermissionInfo * getRTEPermissionInfo(List *rteperminfos, RangeTblEntry *rte)
@ PARTITION_STRATEGY_HASH
bool has_useful_pathkeys(PlannerInfo *root, RelOptInfo *rel)
#define RINFO_IS_PUSHED_DOWN(rinfo, joinrelids)
#define IS_PARTITIONED_REL(rel)
#define PATH_REQ_OUTER(path)
@ RELOPT_OTHER_MEMBER_REL
#define IS_OTHER_REL(rel)
#define PARTITION_MAX_KEYS
#define lfirst_node(type, lc)
static int list_length(const List *l)
static ListCell * list_head(const List *l)
static void * list_nth(const List *list, int n)
#define list_make2(x1, x2)
PlaceHolderInfo * find_placeholder_info(PlannerInfo *root, PlaceHolderVar *phv)
void add_placeholders_to_joinrel(PlannerInfo *root, RelOptInfo *joinrel, RelOptInfo *outer_rel, RelOptInfo *inner_rel, SpecialJoinInfo *sjinfo)
void get_relation_info(PlannerInfo *root, Oid relationObjectId, bool inhparent, RelOptInfo *rel)
static void build_joinrel_partition_info(PlannerInfo *root, RelOptInfo *joinrel, RelOptInfo *outer_rel, RelOptInfo *inner_rel, SpecialJoinInfo *sjinfo, List *restrictlist)
void setup_simple_rel_arrays(PlannerInfo *root)
static void set_joinrel_partition_key_exprs(RelOptInfo *joinrel, RelOptInfo *outer_rel, RelOptInfo *inner_rel, JoinType jointype)
static void build_joinrel_tlist(PlannerInfo *root, RelOptInfo *joinrel, RelOptInfo *input_rel, SpecialJoinInfo *sjinfo, List *pushed_down_joins, bool can_null)
ParamPathInfo * get_baserel_parampathinfo(PlannerInfo *root, RelOptInfo *baserel, Relids required_outer)
RelOptInfo * build_join_rel(PlannerInfo *root, Relids joinrelids, RelOptInfo *outer_rel, RelOptInfo *inner_rel, SpecialJoinInfo *sjinfo, List *pushed_down_joins, List **restrictlist_ptr)
static bool have_partkey_equi_join(PlannerInfo *root, RelOptInfo *joinrel, RelOptInfo *rel1, RelOptInfo *rel2, JoinType jointype, List *restrictlist)
Relids min_join_parameterization(PlannerInfo *root, Relids joinrelids, RelOptInfo *outer_rel, RelOptInfo *inner_rel)
static void build_join_rel_hash(PlannerInfo *root)
RelOptInfo * find_base_rel(PlannerInfo *root, int relid)
ParamPathInfo * get_appendrel_parampathinfo(RelOptInfo *appendrel, Relids required_outer)
RelOptInfo * build_simple_rel(PlannerInfo *root, int relid, RelOptInfo *parent)
Relids find_childrel_parents(PlannerInfo *root, RelOptInfo *rel)
void expand_planner_arrays(PlannerInfo *root, int add_size)
RelOptInfo * find_join_rel(PlannerInfo *root, Relids relids)
ParamPathInfo * get_joinrel_parampathinfo(PlannerInfo *root, RelOptInfo *joinrel, Path *outer_path, Path *inner_path, SpecialJoinInfo *sjinfo, Relids required_outer, List **restrict_clauses)
RelOptInfo * find_base_rel_ignore_join(PlannerInfo *root, int relid)
static void build_child_join_reltarget(PlannerInfo *root, RelOptInfo *parentrel, RelOptInfo *childrel, int nappinfos, AppendRelInfo **appinfos)
RelOptInfo * find_base_rel_noerr(PlannerInfo *root, int relid)
static List * build_joinrel_restrictlist(PlannerInfo *root, RelOptInfo *joinrel, RelOptInfo *outer_rel, RelOptInfo *inner_rel, SpecialJoinInfo *sjinfo)
static int match_expr_to_partition_keys(Expr *expr, RelOptInfo *rel, bool strict_op)
static void set_foreign_rel_properties(RelOptInfo *joinrel, RelOptInfo *outer_rel, RelOptInfo *inner_rel)
RelOptInfo * build_child_join_rel(PlannerInfo *root, RelOptInfo *outer_rel, RelOptInfo *inner_rel, RelOptInfo *parent_joinrel, List *restrictlist, SpecialJoinInfo *sjinfo)
struct JoinHashEntry JoinHashEntry
static void build_joinrel_joinlist(RelOptInfo *joinrel, RelOptInfo *outer_rel, RelOptInfo *inner_rel)
ParamPathInfo * find_param_path_info(RelOptInfo *rel, Relids required_outer)
RelOptInfo * fetch_upper_rel(PlannerInfo *root, UpperRelationKind kind, Relids relids)
static void add_join_rel(PlannerInfo *root, RelOptInfo *joinrel)
static List * subbuild_joinrel_joinlist(RelOptInfo *joinrel, List *joininfo_list, List *new_joininfo)
static List * subbuild_joinrel_restrictlist(PlannerInfo *root, RelOptInfo *joinrel, RelOptInfo *input_rel, Relids both_input_relids, List *new_restrictlist)
Bitmapset * get_param_path_clause_serials(Path *path)
bool join_clause_is_movable_into(RestrictInfo *rinfo, Relids currentrelids, Relids current_and_outer)
Node * remove_nulling_relids(Node *node, const Bitmapset *removable_relids, const Bitmapset *except_relids)
Size add_size(Size s1, Size s2)
static pg_noinline void Size size
int simple_rel_array_size
Selectivity tuple_fraction
bool consider_param_startup
Bitmapset * notnullattnums
struct PathTarget * reltarget
List * cheapest_parameterized_paths
struct Path * cheapest_unique_path
Relids lateral_referencers
struct Path * cheapest_startup_path
QualCost baserestrictcost
struct Path * cheapest_total_path
List * non_unique_for_rels
Bitmapset * eclass_indexes
Relids direct_lateral_relids
bool consider_partitionwise_join
Index baserestrict_min_security
Relids incompatible_relids
PathTarget * create_empty_pathtarget(void)