| From: | Paul A Jungwirth <pj(at)illuminatedcomputing(dot)com> |
|---|---|
| To: | Dean Rasheed <dean(dot)a(dot)rasheed(at)gmail(dot)com> |
| Cc: | Chao Li <li(dot)evan(dot)chao(at)gmail(dot)com>, Ayush Tiwari <ayushtiwari(dot)slg01(at)gmail(dot)com>, PostgreSQL-development <pgsql-hackers(at)postgresql(dot)org>, Peter Eisentraut <peter(at)eisentraut(dot)org> |
| Subject: | Re: Fix RLS checks for UPDATE/DELETE FOR PORTION OF leftover rows |
| Date: | 2026-07-16 00:26:27 |
| Message-ID: | CA+renyWqKvB86R2FBAUh=AWoyt40qMf7yHWzoHaBr15kyy+Tjw@mail.gmail.com |
| Views: | Whole Thread | Raw Message | Download mbox | Resend email |
| Thread: | |
| Lists: | pgsql-hackers |
On Wed, Jul 15, 2026 at 4:40 PM Dean Rasheed <dean(dot)a(dot)rasheed(at)gmail(dot)com> wrote:
>
> On Wed, 15 Jul 2026 at 22:02, Paul A Jungwirth
> <pj(at)illuminatedcomputing(dot)com> wrote:
> >
> > Thanks for taking a look! Here is a v4 with those additions.
> >
>
> + <entry><command>UPDATE ... FOR PORTION OF</command></entry>
> + <entry>
> + Filter existing row <footnoteref linkend="rls-select-priv"/> &
> + check new row <footnoteref linkend="rls-select-priv"/>
> + </entry>
> + <entry>
>
> The footnote "rls-select-priv" reads "If read access is required to
> either the existing or new row (for example, a WHERE or RETURNING
> clause that refers to columns from the relation)." However, FOR
> PORTION OF is guaranteed to require read access to the table, so as
> with a few other entries in that column, the link to this footnote is
> not needed -- it will unconditionally apply the SELECT policy to the
> existing and new rows. Similarly for DELETE ... FOR PORTION OF.
Just to confirm: you're saying that because FOR PORTION OF always
filters rows, the "if" in the footnote is misleading? I can see that
argument, so I removed the footnote after "filter existing row" and
"check new row" from the new entries. Do you think I should add a
different footnote explaining that it is unconditional?
> + /*
> + * As with regular INSERT/UPDATE above, if SELECT rights are needed
> + * for the statement, ensure the leftover row remains visible.
> + */
> + if (perminfo->requiredPerms & ACL_SELECT)
> + {
> + List *select_permissive_policies;
> + List *select_restrictive_policies;
> +
> + get_policies_for_relation(rel, CMD_SELECT, user_id,
> + &select_permissive_policies,
> + &select_restrictive_policies);
> + add_with_check_options(rel, rt_index,
> + WCO_RLS_INSERT_CHECK,
> + select_permissive_policies,
> + select_restrictive_policies,
> + withCheckOptions,
> + hasSubLinks,
> + true);
> + }
>
> Thinking some more about this, I'm not so sure it's right. For a plain
> INSERT, we apply SELECT policies if SELECT permissions are required,
> which only happens if there is a RETURNING clause. The reason is to
> ensure the user has rights to see the row returned by the RETURNING
> clause. However, for the auxiliary INSERTS for leftover portions in
> UPDATE/DELETE ... FOR PORTION OF, even if there is a RETURNING clause,
> it will only return the updated/deleted row, not the leftover rows.
> The command never reads the leftover rows, so why do we need the
> leftover rows to satisfy the SELECT policies?
I think you are right. I replaced that section with a comment.
v5 attached.
Yours,
--
Paul ~{:-)
pj(at)illuminatedcomputing(dot)com
| Attachment | Content-Type | Size |
|---|---|---|
| v5-0001-Fix-RLS-checks-for-FOR-PORTION-OF-leftover-rows.patch | text/x-patch | 15.6 KB |
| From | Date | Subject | |
|---|---|---|---|
| Next Message | Tom Lane | 2026-07-16 00:51:10 | Re: sequencesync worker race with REFRESH SEQUENCES |
| Previous Message | Michael Paquier | 2026-07-16 00:15:18 | Re: NULL pointer dereference in syslogger with load_libraries() and -DEXEC_BACKEND at startup |