Re: rights(4) split? CAP_WRITE -> CAP_WRITE_DATA + CAP_WRITE_CTRL

Mariusz Zaborski <[email protected]> Wed, 3 Jun 2026 16:17:28 +0200
Newsgroups gmane.os.freebsd.devel.hackers,gmane.os.freebsd.architechture
Message-ID <CAGOYWV_663Jt1PngHsd61vUXMWLiLHU=dDKgiiGP=NVu5P-c7A@mail.gmail.com>
--000000000000290df906535a1745
Content-Type: text/plain; charset="UTF-8"

Actually I would feel safer with CAP_WRITE_LEGACY.

On Wed, 3 Jun 2026 at 16:15, Kyle Evans <[email protected]> wrote:

> On 6/3/26 03:04, Mariusz Zaborski wrote:
> > Hello,
> >
> > I think the idea of splitting CAP_WRITE into CAP_WRITE_DATA and
> CAP_WRITE_CTRL makes sense, especially for cases where a process should be
> able to exchange data but not transfer file descriptors.
> >
> >  From my perspective, the biggest concern is the capability change
> itself. While source compatibility can largely be preserved by making
> CAP_WRITE an alias for CAP_WRITE_DATA | CAP_WRITE_CTRL, there is still some
> potential for compatibility issues with existing applications and binaries
> that rely on the current semantics of CAP_WRITE.
> >
>
> My alternative proposal would be that we slice off two entirely new bits
> in index 1 and still make `CAP_WRITE` an alias, but rename the current
> assignment to `CAP_WRITE_COMPAT`.  We don't have any precedent for it, but
> I'd then handle translation at the cap_rights_*(2) border and unset the new
> `CAP_WRITE` if `CAP_WRITE_COMPAT` is unset when limiting, and unset
> `CAP_WRITE_LEGACY` if *either* of the new `CAP_WRITE_*` rights are missing.
>
> I don't know how I feel about it, but I bet it would work.
>
> > Other than that, the use case seems reasonable, and being able to
> explicitly prohibit SCM_RIGHTS on a socketpair could be a useful hardening
> measure
> >
> > Thanks,
> > Mariusz
> >
> >
> > On Tue, 2 Jun 2026 at 20:19, Kyle Evans <[email protected] <mailto:
> [email protected]>> wrote:
> >
> >     Hi,
> >
> >     I'm looking at an application where it would be useful to be able to
> construct a socketpair(2) that can't be used to send fds over, out of an
> abundance of caution.  The application in prison0 is effectively a broker
> between two jails that it hands each an end of the socketpair, then steps
> out of the way -- I don't see a reason to leave it capable of carrying
> SCM_RIGHTS.
> >
> >     I'd like to propose splitting CAP_WRITE into CAP_WRITE_DATA and
> CAP_WRITE_CTRL, with CAP_WRITE being an alias for DATA|CTRL.  The caveat is
> that I don't know if being able to revoke data but not control messages is
> really feasible or useful, off-hand.
> >
> >     In any event, my plan would be to use the last bit available in
> rights idx 0 for the CTRL right, rename the current CAP_WRITE to
> CAP_WRITE_DATA, and create a new CAP_WRITE name for the two combined.
>  There's some chance for breakage in applications that haven't been rebuilt
> with the new definition of CAP_WRITE, but I suspect most of them aren't
> attempting to send control messages.  The in-kernel users of CAP_WRITE look
> like they could mostly be scoped down to CAP_WRITE_DATA specifically,
> though maybe that gets a little awkward in `flags_to_rights` mapping of
> O_WRONLY/O_RDWR.
> >
> >     Thoughts? Terrible idea?
> >
> >     Thanks,
> >
> >     Kyle Evans
> >
>
>

--000000000000290df906535a1745
Content-Type: text/html; charset="UTF-8"
Content-Transfer-Encoding: quoted-printable

<div dir=3D"ltr">Actually I would feel safer with=C2=A0CAP_WRITE_LEGACY.</d=
iv><br><div class=3D"gmail_quote gmail_quote_container"><div dir=3D"ltr" cl=
ass=3D"gmail_attr">On Wed, 3 Jun 2026 at 16:15, Kyle Evans &lt;<a href=3D"m=
ailto:[email protected]">[email protected]</a>&gt; wrote:<br></div><block=
quote class=3D"gmail_quote" style=3D"margin:0px 0px 0px 0.8ex;border-left:1=
px solid rgb(204,204,204);padding-left:1ex">On 6/3/26 03:04, Mariusz Zabors=
ki wrote:<br>
&gt; Hello,<br>
&gt; <br>
&gt; I think the idea of splitting CAP_WRITE into CAP_WRITE_DATA and CAP_WR=
ITE_CTRL makes sense, especially for cases where a process should be able t=
o exchange data but not transfer file descriptors.<br>
&gt; <br>
&gt;=C2=A0 From my perspective, the biggest concern is the capability chang=
e itself. While source compatibility can largely be preserved by making CAP=
_WRITE an alias for CAP_WRITE_DATA | CAP_WRITE_CTRL, there is still some po=
tential for compatibility issues with existing applications and binaries th=
at rely on the current semantics of CAP_WRITE.<br>
&gt; <br>
<br>
My alternative proposal would be that we slice off two entirely new bits in=
 index 1 and still make `CAP_WRITE` an alias, but rename the current assign=
ment to `CAP_WRITE_COMPAT`.=C2=A0 We don&#39;t have any precedent for it, b=
ut I&#39;d then handle translation at the cap_rights_*(2) border and unset =
the new `CAP_WRITE` if `CAP_WRITE_COMPAT` is unset when limiting, and unset=
 `CAP_WRITE_LEGACY` if *either* of the new `CAP_WRITE_*` rights are missing=
.<br>
<br>
I don&#39;t know how I feel about it, but I bet it would work.<br>
<br>
&gt; Other than that, the use case seems reasonable, and being able to expl=
icitly prohibit SCM_RIGHTS on a socketpair could be a useful hardening meas=
ure<br>
&gt; <br>
&gt; Thanks,<br>
&gt; Mariusz<br>
&gt; <br>
&gt; <br>
&gt; On Tue, 2 Jun 2026 at 20:19, Kyle Evans &lt;<a href=3D"mailto:kevans@f=
reebsd.org" target=3D"_blank">[email protected]</a> &lt;mailto:<a href=3D"=
mailto:[email protected]" target=3D"_blank">[email protected]</a>&gt;&gt;=
 wrote:<br>
&gt; <br>
&gt;=C2=A0 =C2=A0 =C2=A0Hi,<br>
&gt; <br>
&gt;=C2=A0 =C2=A0 =C2=A0I&#39;m looking at an application where it would be=
 useful to be able to construct a socketpair(2) that can&#39;t be used to s=
end fds over, out of an abundance of caution.=C2=A0 The application in pris=
on0 is effectively a broker between two jails that it hands each an end of =
the socketpair, then steps out of the way -- I don&#39;t see a reason to le=
ave it capable of carrying SCM_RIGHTS.<br>
&gt; <br>
&gt;=C2=A0 =C2=A0 =C2=A0I&#39;d like to propose splitting CAP_WRITE into CA=
P_WRITE_DATA and CAP_WRITE_CTRL, with CAP_WRITE being an alias for DATA|CTR=
L.=C2=A0 The caveat is that I don&#39;t know if being able to revoke data b=
ut not control messages is really feasible or useful, off-hand.<br>
&gt; <br>
&gt;=C2=A0 =C2=A0 =C2=A0In any event, my plan would be to use the last bit =
available in rights idx 0 for the CTRL right, rename the current CAP_WRITE =
to CAP_WRITE_DATA, and create a new CAP_WRITE name for the two combined.=C2=
=A0 =C2=A0There&#39;s some chance for breakage in applications that haven&#=
39;t been rebuilt with the new definition of CAP_WRITE, but I suspect most =
of them aren&#39;t attempting to send control messages.=C2=A0 The in-kernel=
 users of CAP_WRITE look like they could mostly be scoped down to CAP_WRITE=
_DATA specifically, though maybe that gets a little awkward in `flags_to_ri=
ghts` mapping of O_WRONLY/O_RDWR.<br>
&gt; <br>
&gt;=C2=A0 =C2=A0 =C2=A0Thoughts? Terrible idea?<br>
&gt; <br>
&gt;=C2=A0 =C2=A0 =C2=A0Thanks,<br>
&gt; <br>
&gt;=C2=A0 =C2=A0 =C2=A0Kyle Evans<br>
&gt; <br>
<br>
</blockquote></div>

--000000000000290df906535a1745--