From e7ce03017391f7472a9d30b039447d66f1d956c6 Mon Sep 17 00:00:00 2001 From: amit Date: Fri, 2 Nov 2018 16:48:25 +0900 Subject: [PATCH 2/2] Use permissions granted on parent to read stats on otherrel children Author: Dilip Kumar Reviewed by: Amit Langote --- src/backend/utils/adt/selfuncs.c | 58 +++++++++++++++++++++++++++++++++++++--- 1 file changed, 55 insertions(+), 3 deletions(-) diff --git a/src/backend/utils/adt/selfuncs.c b/src/backend/utils/adt/selfuncs.c index e0ece74bb9..698a4eca63 100644 --- a/src/backend/utils/adt/selfuncs.c +++ b/src/backend/utils/adt/selfuncs.c @@ -4924,8 +4924,18 @@ examine_variable(PlannerInfo *root, Node *node, int varRelid, { /* Get index's table for permission check */ RangeTblEntry *rte; + RelOptInfo *rel = index->rel; + + /* + * For a child table, check permissions using + * parent's RTE. + */ + if (rel->inh_root_parent) + rte = planner_rt_fetch(rel->inh_root_parent, + root); + else + rte = planner_rt_fetch(rel->relid, root); - rte = planner_rt_fetch(index->rel->relid, root); Assert(rte->rtekind == RTE_RELATION); /* @@ -4998,11 +5008,53 @@ examine_simple_variable(PlannerInfo *root, Var *var, if (HeapTupleIsValid(vardata->statsTuple)) { + RelOptInfo *rel; + Oid relid = rte->relid; + int varattno = var->varattno; + + rel = root->simple_rel_array[var->varno]; + + /* + * For an inheritance child table, check permissions using the + * root parent's RTE and columns. + */ + if (rel->inh_root_parent) + { + relid = planner_rt_fetch(rel->inh_root_parent, root)->relid; + + /* + * Must find out the column's attribute number per the root + * parent's schema. + */ + if (varattno > 0) + { + AppendRelInfo *appinfo = root->append_rel_array[rel->relid]; + ListCell *l; + bool found = false; + + Assert(appinfo != NULL); + varattno = 1; + foreach(l, appinfo->translated_vars) + { + if (equal(var, lfirst(l))) + { + found = true; + break; + } + varattno++; + } + /* + * The query can only select columns present in the parent + * table, so we must've found one in translated_vars. + */ + Assert(found); + } + } /* check if user has permission to read this column */ vardata->acl_ok = - (pg_class_aclcheck(rte->relid, GetUserId(), + (pg_class_aclcheck(relid, GetUserId(), ACL_SELECT) == ACLCHECK_OK) || - (pg_attribute_aclcheck(rte->relid, var->varattno, GetUserId(), + (pg_attribute_aclcheck(relid, varattno, GetUserId(), ACL_SELECT) == ACLCHECK_OK); } else -- 2.11.0