From: Edouard Klein <edou@rdklein.fr>
To: 63904@debbugs.gnu.org
Cc: dev@jpoiret.xyz, me@tobias.gr, zimon.toutoune@gmail.com,
othacehe@gnu.org, ludo@gnu.org, mail@cbaines.net,
rekado@elephly.net
Subject: bug#63904: Can't setuid programs to anybody but root
Date: Tue, 06 Jun 2023 09:21:43 +0200 [thread overview]
Message-ID: <878rcxt4jt.fsf@rdklein.fr> (raw)
In-Reply-To: <87h6rmtdzk.fsf@rdklein.fr>
Dear Guix, CCing the core team,
I tried tracking down the bug.
The fatidic call to getpw was easy enough to find:
The make-setuid-program procedure is given a numeric uid argument. This
numeric uid is found from the user name string by
activate-setuid-program which calls getpwnam
(gnu/build/activation.scm:317).
Now this gave me an idea to sidestep the bug: See below the modified
part of the minimal reproductible example: I just force-assign a uid to
the user I want to setuid to, and give this uid instead of the username
to the setuid record.
This is cumbersome, but it does the job: the call to getpw is averted
and I get a system in which I can setuid to somebody other than root.
However, I'm lost as to how to solve the bug for good. I tried to
understand the call stack, but I can't figure out how in the folding
service machinery the services are ordered. My intuition is that I need
to make it so the folding of non-root setuids happen after the folding
of user and groups (I also have the intuition that root-setuids must
happen before, because folding users and group may require that root
setuid binaries are there, but I have not been able to verify that).
Here is what I was able to find.
getpw is called by activate-setuid-program
activate-setuid-program is called in setuid-program->activation-gexp
setuid-program->activation-gexp is the activation procedure for setuid-program-service-type
setuid-program-service-type is itself an extension of activation-service-type
I'm trying to follow how the service DAG is constructed, and then
walked, from there, but I don't think I have a very clear model of how
it works in my head.
I think the devil may be in:
(define (compute-boot-script _ gexps)
;; Reverse GEXPS so that extensions appear in the boot script in the right
;; order. That is, user extensions would come first, and extensions added
;; by 'essential-services' (e.g., running shepherd) are guaranteed to come
;; last.
(gexp->file "boot"
;; Clean up and activate the system, then spawn shepherd.
#~(begin #$@(reverse gexps))))
Any help there would be greatly appreciated.
Thanks in advance,
Cheers,
Edouard.
(operating-system
(host-name "minimal-container")
(timezone "UTC")
(locale "en_US.utf8")
(bootloader (bootloader-configuration
(bootloader grub-bootloader)))
(file-systems %base-file-systems)
(users (cons
(user-account
(name "suc")
(group "users")
(uid 1042))
%base-user-accounts))
(setuid-programs
(cons (setuid-program (program (file-append coreutils "/bin/true"))
;; (user "suc")
(user 1042)
)
%setuid-programs))
(packages %base-packages)
(services %base-services))
edk@beaver-labs.com writes:
> Dear Guix developers,
>
> At the end of the email is the code for a minimal container, which tries
> to setuid =true=, the simplest binary of all, to user suc.
>
> When line 26 is commented, and the container is built and run with:
> sudo $(guix system container mwe.scm)
>
> One can login to the container and run:
> ls -l /run/setuid-programs/true
>
> which yields:
> -r-sr-xr-x 1 root root 39488 Jun 5 09:59 /run/setuid-programs/true
> as it should.
>
> Also, one can fire up guile and run (getpw "suc") and get in return:
> $1 = #("suc" "x" 1000 998 "" "/home/suc" "/gnu/store/m6c5hgqg569mbcjjbp8l8m7q82ascpdl-bash-5.1.16/bin/bash")
>
> However, when line 26 is uncommented, the container can be built, but
> when run fails with the error below.
> My hunch is that things are done out of order, with setuid binaries
> being set up before user creation, but I have no way of checking that.
>
> Please do not hesitate to ping me if I can be of help.
>
> Cheers,
>
> Edouard.
>
> The error:
> system container is running as PID 9825
> WARNING: (guile-user): imported module (guix build utils) overrides core binding `delete'
> Run 'sudo guix container exec 9825 /run/current-system/profile/bin/bash --login'
> or run 'sudo nsenter -a -t 9825' to get a shell into it.
>
> WARNING: (guile-user): imported module (guix build utils) overrides core binding `delete'
> making '/gnu/store/mnc9lfpn01frmffqa31jy3c381dkgrwl-system' the current system...
> WARNING: (guile-user): imported module (guix build utils) overrides core binding `delete'
> setting up setuid programs in '/run/setuid-programs'...
> Backtrace:
> 12 (primitive-load "/gnu/store/bygckv7p4091xqykjnkay4qnazn…")
> In gnu/build/linux-container.scm:
> 300:8 11 (call-with-temporary-directory #<procedure 7fb026898d70…>)
> 397:16 10 (_ "/tmp/guix-directory.B9dmTN")
> 62:6 9 (call-with-clean-exit #<procedure 7fb0268a5380 at gnu/b…>)
> In unknown file:
> 8 (primitive-load "/gnu/store/mnc9lfpn01frmffqa31jy3c381d…")
> In ice-9/eval.scm:
> 619:8 7 (_ #f)
> In unknown file:
> 6 (primitive-load "/gnu/store/dib6wfh2r52dfaydz78n33267qx…")
> In srfi/srfi-1.scm:
> 634:9 5 (for-each #<procedure primitive-load (_)> ("/gnu/sto…" …))
> In unknown file:
> 4 (primitive-load "/gnu/store/ypwqsx11k2qmxkscmzan6srq87q…")
> In srfi/srfi-1.scm:
> 634:9 3 (for-each #<procedure 7fb026380538 at gnu/build/activa…> …)
> In ice-9/boot-9.scm:
> 1747:15 2 (with-exception-handler #<procedure 7fb02683c6f0 at ic…> …)
> In gnu/build/activation.scm:
> 317:57 1 (_)
> In unknown file:
> 0 (getpw "suc")
>
> ERROR: In procedure getpw:
> In procedure getpw: entry not found
>
>
>
> The code
>
> (use-modules
> (guix gexp)
> (gnu system)
> (gnu bootloader)
> (gnu bootloader grub)
> (gnu system file-systems)
> (gnu services)
> (gnu services base)
> (gnu system setuid)
> (gnu packages base))
>
> (operating-system
> (host-name "minimal-container")
> (timezone "UTC")
> (locale "en_US.utf8")
> (bootloader (bootloader-configuration
> (bootloader grub-bootloader)))
> (file-systems %base-file-systems)
> (users (cons
> (user-account
> (name "suc")
> (group "users"))
> %base-user-accounts))
> (setuid-programs
> (cons (setuid-program (program (file-append coreutils "/bin/true"))
> (user "suc")
> )
> %setuid-programs))
> (packages %base-packages)
> (services %base-services))
next prev parent reply other threads:[~2023-06-06 7:49 UTC|newest]
Thread overview: 4+ messages / expand[flat|nested] mbox.gz Atom feed top
2023-06-05 10:00 bug#63904: Can't setuid programs to anybody but root edk
2023-06-06 7:21 ` Edouard Klein [this message]
2023-06-08 7:19 ` Josselin Poiret via Bug reports for GNU Guix
2023-07-06 12:04 ` Edouard Klein
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
List information: https://guix.gnu.org/
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=878rcxt4jt.fsf@rdklein.fr \
--to=edou@rdklein.fr \
--cc=63904@debbugs.gnu.org \
--cc=dev@jpoiret.xyz \
--cc=ludo@gnu.org \
--cc=mail@cbaines.net \
--cc=me@tobias.gr \
--cc=othacehe@gnu.org \
--cc=rekado@elephly.net \
--cc=zimon.toutoune@gmail.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
Code repositories for project(s) associated with this public inbox
https://git.savannah.gnu.org/cgit/guix.git
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).