Bug 127532 - [patch] install(1): install -S Not Safe in Jail with security.jail.chflags_allowed: 0
Summary: [patch] install(1): install -S Not Safe in Jail with security.jail.chflags_al...
Status: Open
Alias: None
Product: Base System
Classification: Unclassified
Component: bin (show other bugs)
Version: 6.2-RELEASE
Hardware: Any Any
: Normal Affects Only Me
Assignee: freebsd-bugs (Nobody)
URL:
Keywords: patch
Depends on:
Blocks:
 
Reported: 2008-09-22 04:00 UTC by Jason C. Wells
Modified: 2022-10-17 12:40 UTC (History)
0 users

See Also:


Attachments
xinstall-unsafe--S.diff (4.75 KB, patch)
2008-09-29 15:39 UTC, Jaakko Heinonen
no flags Details | Diff
install-S-safe.patch (4.53 KB, patch)
2009-05-29 22:16 UTC, Jilles Tjoelker
no flags Details | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description Jason C. Wells 2008-09-22 04:00:12 UTC
The install command deleted libc when it should not have.  Running the
install command with '-fschg -S' deletes the install target when
security.jail.chflags_allowed=0 inside a jail.  I observed this during
installworld.  The problem can be avoided by setting
security.jail.chflags_allowed=1 before running make installworld.

How-To-Repeat: (outside the jail)
~$ chflags noschg /usr/jails/cr/lib/libc.so.6

(inside the jail)
[root@s4cr /usr/src/lib/libc]# ls -lao /lib/libc.so.6
-rwxr-xr-x  1 root  wheel  - 981331 Sep 21 15:57 /lib/libc.so.6

[root@s4cr /usr/src/lib/libc]# sysctl -a | grep secur
kern.securelevel: -1
security.jail.chflags_allowed: 0

[root@s4cr /usr/src/lib/libc]#   make install
install -C -o root -g wheel -m 444   libc.a /usr/lib
install -C -o root -g wheel -m 444   libc_p.a /usr/lib
install -s -o root -g wheel -m 444   -fschg -S  libc.so.6 /lib
install: /lib/libc.so.6: chflags: Operation not permitted
*** Error code 71

Stop in /usr/src/lib/libc.

[root@s4cr /usr/src/lib/libc]# ls -lao /lib/libc.so.6
/libexec/ld-elf.so.1: Shared object "libc.so.6" not found, required by "ls"
[root@s4cr /usr/src/lib/libc]#
Comment 1 Jaakko Heinonen 2008-09-29 15:39:53 UTC
On 2008-09-22, Jason C. Wells wrote:
> The install command deleted libc when it should not have.  Running the
> install command with '-fschg -S' deletes the install target when
> security.jail.chflags_allowed=0 inside a jail.  I observed this during
> installworld.  The problem can be avoided by setting
> security.jail.chflags_allowed=1 before running make installworld.

This is a bug in install(1). Here's a stripped down way to reproduce it:

(in a jail)

# sysctl security.jail.jailed security.jail.chflags_allowed
security.jail.jailed: 1
security.jail.chflags_allowed: 0
# touch target
# ls -lo target
-rw-r--r--  1 root  wheel  - 0 Sep 29 09:54 target
# install -fschg -S /bin/cat target
install: target: chflags: Operation not permitted
# ls -lo target
ls: target: No such file or directory

The problem is that install(1) unlinks the target file if fchflags(2)
fails. This is not good especially with -S which is supposed to be safe.
There are also three more unsafe unlink(2) calls in install() function.
fstat(2) and fchown(2) and fchmod(2) are performed for the file after
rename. Failure on those calls causes the target to be unlinked. This is
how to reproduce the fchown(2) problem without jail:

(use a non-root user)

$ touch target
$ ls target
target
$ install -S -o root /bin/cat target
install: target: chown/chgrp: Operation not permitted
$ ls target
ls: target: No such file or directory


Attached patch does following changes:

* If safe copy is used perform fstat(2) and fchown(2) and fchmod(2)
  _before_ rename and on failure unlink the temporary copy instead of
  the target.
* On fchlags(2) failure don't unlink the target. We still exit with error
  status. fchflags(2) can't be performed before rename because
  immutable flags may prevent renaming.

-- 
Jaakko
Comment 2 Jilles Tjoelker freebsd_committer freebsd_triage 2009-05-29 22:16:27 UTC
The patch works but introduces a new problem: install -S -m 0 src dst
(installing to an unreadable destination, probably as non-root) no
longer works.

I have fixed this particular issue (attachment and
http://www.stack.nl/~jilles/unix/install-S-safe.patch ), but I think the
code is too hard to understand. The install() function was already
fairly twisted and the patch has not improved it.

-- 
Jilles Tjoelker
Comment 3 Eitan Adler freebsd_committer freebsd_triage 2017-12-31 08:01:07 UTC
For bugs matching the following criteria:

Status: In Progress Changed: (is less than) 2014-06-01

Reset to default assignee and clear in-progress tags.

Mail being skipped
Comment 4 Graham Perrin freebsd_committer freebsd_triage 2022-10-17 12:40:44 UTC
Keyword: 

    patch
or  patch-ready

– in lieu of summary line prefix: 

    [patch]

* bulk change for the keyword
* summary lines may be edited manually (not in bulk). 

Keyword descriptions and search interface: 

    <https://bugs.freebsd.org/bugzilla/describekeywords.cgi>