From 50ce1cfbe836b044f03e067e857f6808ba31a086 Mon Sep 17 00:00:00 2001
From: amitlan <amitlangote09@gmail.com>
Date: Fri, 18 Nov 2022 20:45:06 +0900
Subject: [PATCH v27 3/5] ConcatRTEPermissionInfoLists() -> CombineRangeTable()

---
 src/backend/optimizer/plan/subselect.c    | 13 ++++-------
 src/backend/optimizer/prep/prepjointree.c | 28 ++++++++---------------
 src/backend/rewrite/rewriteHandler.c      | 17 +++++++-------
 src/backend/rewrite/rewriteManip.c        | 26 ++++++++++++---------
 src/include/rewrite/rewriteManip.h        |  6 ++---
 5 files changed, 41 insertions(+), 49 deletions(-)

diff --git a/src/backend/optimizer/plan/subselect.c b/src/backend/optimizer/plan/subselect.c
index cbeb0191fb..bc3f7519e4 100644
--- a/src/backend/optimizer/plan/subselect.c
+++ b/src/backend/optimizer/plan/subselect.c
@@ -1497,15 +1497,12 @@ convert_EXISTS_sublink_to_join(PlannerInfo *root, SubLink *sublink,
 		return NULL;
 
 	/*
-	 * Add subquery's RTEPermissionInfos into the upper query.  This also
-	 * updates the subquery's RTEs' perminfoindex.
+	 * Now we can attach the modified subquery rtable to the parent.
+	 * This also adds subquery's RTEPermissionInfos into the upper query.
 	 */
-	parse->rtepermlist = ConcatRTEPermissionInfoLists(parse->rtepermlist,
-													  subselect->rtepermlist,
-													  subselect->rtable);
-
-	/* Now we can attach the modified subquery rtable to the parent */
-	parse->rtable = list_concat(parse->rtable, subselect->rtable);
+	parse->rtable = CombineRangeTables(parse->rtable, subselect->rtable,
+									   subselect->rtepermlist,
+									   &parse->rtepermlist);
 
 	/*
 	 * And finally, build the JoinExpr node.
diff --git a/src/backend/optimizer/prep/prepjointree.c b/src/backend/optimizer/prep/prepjointree.c
index 8ac0a41d0e..9733323e3e 100644
--- a/src/backend/optimizer/prep/prepjointree.c
+++ b/src/backend/optimizer/prep/prepjointree.c
@@ -1198,21 +1198,16 @@ pull_up_simple_subquery(PlannerInfo *root, Node *jtnode, RangeTblEntry *rte,
 		}
 	}
 
-	/*
-	 * Add subquery's RTEPermissionInfos into the upper query.  This also
-	 * updates the subquery's RTEs' perminfoindex.
-	 */
-	parse->rtepermlist = ConcatRTEPermissionInfoLists(parse->rtepermlist,
-													  subquery->rtepermlist,
-													  subquery->rtable);
-
 	/*
 	 * Now append the adjusted rtable entries to upper query. (We hold off
 	 * until after fixing the upper rtable entries; no point in running that
 	 * code on the subquery ones too.)
+	 *
+	 * This also adds subquery's RTEPermissionInfos into the upper query.
 	 */
-	parse->rtable = list_concat(parse->rtable, subquery->rtable);
-
+	parse->rtable = CombineRangeTables(parse->rtable, subquery->rtable,
+									   subquery->rtepermlist,
+									   &parse->rtepermlist);
 	/*
 	 * Pull up any FOR UPDATE/SHARE markers, too.  (OffsetVarNodes already
 	 * adjusted the marker rtindexes, so just concat the lists.)
@@ -1346,17 +1341,14 @@ pull_up_simple_union_all(PlannerInfo *root, Node *jtnode, RangeTblEntry *rte)
 		}
 	}
 
-	/*
-	 * Add subquery's RTEPermissionInfos into the upper query.  This also
-	 * updates the subquery's RTEs' perminfoindex.
-	 */
-	root->parse->rtepermlist = ConcatRTEPermissionInfoLists(root->parse->rtepermlist,
-															subquery->rtepermlist,
-															rtable);
 	/*
 	 * Append child RTEs to parent rtable.
+	 *
+	 * This also adds subquery's RTEPermissionInfos into the upper query.
 	 */
-	root->parse->rtable = list_concat(root->parse->rtable, rtable);
+	root->parse->rtable = CombineRangeTables(root->parse->rtable, rtable,
+											 subquery->rtepermlist,
+											 &root->parse->rtepermlist);
 
 	/*
 	 * Recursively scan the subquery's setOperations tree and add
diff --git a/src/backend/rewrite/rewriteHandler.c b/src/backend/rewrite/rewriteHandler.c
index dde9788755..ac142da7b9 100644
--- a/src/backend/rewrite/rewriteHandler.c
+++ b/src/backend/rewrite/rewriteHandler.c
@@ -353,7 +353,7 @@ rewriteRuleAction(Query *parsetree,
 	Query	   *sub_action;
 	Query	  **sub_action_ptr;
 	acquireLocksOnSubLinks_context context;
-	List	   *query_rtable;
+	List	   *action_rtepermlist;
 
 	context.for_execute = true;
 
@@ -417,15 +417,14 @@ rewriteRuleAction(Query *parsetree,
 	 * NOTE: because planner will destructively alter rtable and rtepermlist,
 	 * we must ensure that rule action's lists are separate and shares no
 	 * substructure with the main query's lists.  Hence do a deep copy here
-	 * for both.  Copy rtable before calling ConcatRTEPermissionInfoLists(),
-	 * because perminfoindex of those RTEs will be updated there.
+	 * for both.
 	 */
-	query_rtable = copyObject(parsetree->rtable);
-	sub_action->rtepermlist =
-		ConcatRTEPermissionInfoLists(copyObject(sub_action->rtepermlist),
-									 parsetree->rtepermlist,
-									 query_rtable);
-	sub_action->rtable = list_concat(query_rtable, sub_action->rtable);
+	action_rtepermlist = sub_action->rtepermlist;
+	sub_action->rtepermlist = copyObject(parsetree->rtepermlist);
+	sub_action->rtable = CombineRangeTables(copyObject(parsetree->rtable),
+											sub_action->rtable,
+											action_rtepermlist,
+											&sub_action->rtepermlist);
 
 	/*
 	 * There could have been some SubLinks in parsetree's rtable, in which
diff --git a/src/backend/rewrite/rewriteManip.c b/src/backend/rewrite/rewriteManip.c
index 8f6446a435..1aa7346d9b 100644
--- a/src/backend/rewrite/rewriteManip.c
+++ b/src/backend/rewrite/rewriteManip.c
@@ -1533,24 +1533,26 @@ ReplaceVarsFromTargetList(Node *node,
 }
 
 /*
- * ConcatRTEPermissionInfoLists
- * 		Add RTEPermissionInfos found in src_rtepermlist into *dest_rtepermlist
+ * CombineRangeTables
+ * 		Adds the RTEs of 'rtable2' into 'rtable1'
  *
- * Also updates perminfoindex of the RTEs in src_rtable to point to the
- * "source" perminfos after they have been added into *dest_rtepermlist.
+ * This also adds the RTEPermissionInfos of 'rtepermlist2' (belonging to the
+ * RTEs in 'rtable2') into *rtepermlist1 and also updates perminfoindex of the
+ * RTEs in 'rtable2' to now point to the perminfos' indexes in *rtepermlist1.
+ *
+ * Note that this changes both 'rtable1' and 'rtepermlist1' destructively, so
+ * the caller should have better passed safe-to-modify copies.
  */
 List *
-ConcatRTEPermissionInfoLists(List *dest_rtepermlist, List *src_rtepermlist,
-							 List *src_rtable)
+CombineRangeTables(List *rtable1, List *rtable2,
+				   List *rtepermlist2, List **rtepermlist1)
 {
 	ListCell   *l;
-	int			offset = list_length(dest_rtepermlist);
-
-	dest_rtepermlist = list_concat(dest_rtepermlist, src_rtepermlist);
+	int			offset = list_length(*rtepermlist1);
 
 	if (offset > 0)
 	{
-		foreach(l, src_rtable)
+		foreach(l, rtable2)
 		{
 			RangeTblEntry  *rte = lfirst_node(RangeTblEntry, l);
 
@@ -1559,5 +1561,7 @@ ConcatRTEPermissionInfoLists(List *dest_rtepermlist, List *src_rtepermlist,
 		}
 	}
 
-	return dest_rtepermlist;
+	*rtepermlist1 = list_concat(*rtepermlist1, rtepermlist2);
+
+	return list_concat(rtable1, rtable2);
 }
diff --git a/src/include/rewrite/rewriteManip.h b/src/include/rewrite/rewriteManip.h
index 76699c8e13..90565a8e17 100644
--- a/src/include/rewrite/rewriteManip.h
+++ b/src/include/rewrite/rewriteManip.h
@@ -83,8 +83,8 @@ extern Node *ReplaceVarsFromTargetList(Node *node,
 									   ReplaceVarsNoMatchOption nomatch_option,
 									   int nomatch_varno,
 									   bool *outer_hasSubLinks);
-extern List *ConcatRTEPermissionInfoLists(List *dest_rtepermlist,
-							 List *src_rtepermlist,
-							 List *src_rtable);
+extern List *CombineRangeTables(List *rtable1, List *rtable2,
+				   List *rtepermlist2,
+				   List **rtepermlist1);
 
 #endif							/* REWRITEMANIP_H */
-- 
2.35.3

