unofficial mirror of guix-patches@gnu.org 
 help / color / mirror / code / Atom feed
From: Maxim Cournoyer <maxim.cournoyer@gmail.com>
To: Christopher Lemmer Webber <cwebber@dustycloud.org>
Cc: 44700@debbugs.gnu.org
Subject: [bug#44700] services: setuid: More configurable setuid support.
Date: Tue, 17 Nov 2020 11:29:23 -0500	[thread overview]
Message-ID: <875z64aqvw.fsf@gmail.com> (raw)
In-Reply-To: <874klog9tk.fsf@dustycloud.org> (Christopher Lemmer Webber's message of "Mon, 16 Nov 2020 18:29:11 -0500")

Hello Christopher,

Christopher Lemmer Webber <cwebber@dustycloud.org> writes:

> This patch allows for configuring the specific user, group, and whether
> to set the setuid and setgid bits.
>
> See also:
>   https://lists.gnu.org/archive/html/guix-devel/2020-11/msg00369.html
>
> But I thought I'd open this here so we could track changes since this is
> technically independent of the postfix stuff.  Anyway, patch attached.
> One change since the last email above is that I added support for
> string-based username/groups.
>
> This also needs documentation, I suppose, so that should be done.
> But it would be good to know if this patch looks like it's on the "right
> path" or not.
>
> From eadac673fb22132c555a4e1cee57a6308ecfdad4 Mon Sep 17 00:00:00 2001
> From: Christopher Lemmer Webber <cwebber@dustycloud.org>
> Date: Sun, 15 Nov 2020 16:58:52 -0500
> Subject: [PATCH] services: setuid: More configurable setuid support.
>
> New record <setuid-program> with fields for setting the specific user and
> group, as well as specifically selecting the setuid and setgid bits, for a
> program within the setuid-program-service.

Please make this a full sentence, e.g. "This adds a new record [...]".

>
> * gnu/services.scm (<setuid-program>): New record type.
>   (setuid-program, make-setuid-program, setuid-program?)
>   (setuid-program-program, stuid-program-setuid?, setuid-program-setgid?)
>   (setuid-program-user, setuid-program-group): New variables, export them.
>   (setuid-program-entry): New variable, a procedure used for the
>   service-extension of activation-service-type as set up by
>   setuid-program-service-type.  Unpacks the <setuid-program> record,
>   handing off within the gexp to activate-setuid-programs.
>   (setuid-program-service-type): Make use of setuid-program-entry.
> * gnu/build/activation.scm (activate-setuid-programs): Update to expect a
>   ftagged list for each program entry, pre-unpacked from the <setuid-program>
    ^tagged
>   record before being handed to this procedure.

The doc needs to be updated, as well as the current uses in the code
base.

> ---
>  gnu/build/activation.scm | 46 +++++++++++++++++++++----------------
>  gnu/services.scm         | 49 +++++++++++++++++++++++++++++++++++++---
>  2 files changed, 73 insertions(+), 22 deletions(-)
>
> diff --git a/gnu/build/activation.scm b/gnu/build/activation.scm
> index 4b67926e88..fd17ce0434 100644
> --- a/gnu/build/activation.scm
> +++ b/gnu/build/activation.scm
> @@ -229,13 +229,6 @@ they already exist."
>  (define (activate-setuid-programs programs)
>    "Turn PROGRAMS, a list of file names, into setuid programs stored under
>  %SETUID-DIRECTORY."
> -  (define (make-setuid-program prog)
> -    (let ((target (string-append %setuid-directory
> -                                 "/" (basename prog))))
> -      (copy-file prog target)
> -      (chown target 0 0)
> -      (chmod target #o6555)))
> -

I think it'd be nicer to keep that procedure here and extend it with the
logic added below, for readability.

>    (format #t "setting up setuid programs in '~a'...~%"
>            %setuid-directory)
>    (if (file-exists? %setuid-directory)
> @@ -247,18 +240,33 @@ they already exist."
>                           string<?))
>        (mkdir-p %setuid-directory))
>
> -  (for-each (lambda (program)
> -              (catch 'system-error
> -                (lambda ()
> -                  (make-setuid-program program))
> -                (lambda args
> -                  ;; If we fail to create a setuid program, better keep going
> -                  ;; so that we don't leave %SETUID-DIRECTORY empty or
> -                  ;; half-populated.  This can happen if PROGRAMS contains
> -                  ;; incorrect file names: <https://bugs.gnu.org/38800>.
> -                  (format (current-error-port)
> -                          "warning: failed to make '~a' setuid-root: ~a~%"
> -                          program (strerror (system-error-errno args))))))
> +  (for-each (match-lambda
> +              [('setuid-program src-path setuid? setgid? user group)
                 ^
There's a convention to not use square brackets in
the Guix code base, for uniformity.

> +               (let ((uid (match user
> +                            [(? string?) (passwd:uid (getpwnam user))]
> +                            [(? integer?) user]))
> +                     (gid (match group
> +                            [(? string?) (group:gid (getgrnam user))]
> +                            [(? integer?) group])))

The above code raise an un-handled exception, for example if the user or
group used doesn't exist.  It should be moved to the above
MAKE-SETUID-PROGRAM procedure and called inside the guard.

> +                 (catch 'system-error
> +                   (lambda ()
> +                     (let ((target (string-append %setuid-directory
> +                                                  "/" (basename src-path)))
> +                           (mode (+ #o0555                   ; base permissions
> +                                    (if setuid? #o4000 0)    ; setuid bit
> +                                    (if setgid? #o2000 0)))) ; setgid bit
> +                       (copy-file src-path target)
> +                       (chown target uid gid)
> +                       (chmod target mode)))
> +                   (lambda args
> +                     ;; If we fail to create a setuid program, better keep going
> +                     ;; so that we don't leave %SETUID-DIRECTORY empty or
> +                     ;; half-populated.  This can happen if PROGRAMS contains
> +                     ;; incorrect file names: <https://bugs.gnu.org/38800>.
> +                     (format (current-error-port)
> +                             "warning: failed to make '~a' setuid-root: ~a~%"

The above message should be adapted to say "failed to make ~s
setuid/setgid: ~a~%"

> +                             (setuid-program-program program)
> +                             (strerror (system-error-errno args))))))])
>              programs))
>
>  (define (activate-special-files special-files)
> diff --git a/gnu/services.scm b/gnu/services.scm
> index 4b30399adc..a5b4734152 100644
> --- a/gnu/services.scm
> +++ b/gnu/services.scm
> @@ -87,6 +87,14 @@
>              ambiguous-target-service-error-service
>              ambiguous-target-service-error-target-type
>
> +            setuid-program
> +            setuid-program?
> +            setuid-program-program
> +            setuid-program-setuid?
> +            setuid-program-setgid?
> +            setuid-program-user
> +            setuid-program-group
> +
>              system-service-type
>              provenance-service-type
>              sexp->system-provenance
> @@ -773,13 +781,48 @@ directory."
>  FILES must be a list of name/file-like object pairs."
>    (service etc-service-type files))
>
> +(define-record-type* <setuid-program> setuid-program make-setuid-program
> +  setuid-program?
> +  ;; Path to program to link with setuid permissions
> +  (program       setuid-program-program)          ;string
> +  ;; Whether to set user setuid bit
> +  (setuid?       setuid-program-setuid?           ;boolean
> +                 (default #t))
> +  ;; Whether to set user setgid bit
> +  (setgid?       setuid-program-setgid?           ;boolean
> +                 (default #t))

This departs from the previous default (not setgid was set).  It's
probably more explicit to be set to #f as default, since the service is
still named 'setuid-program-service-type', so having it do gid stuff by
default could come as a surprise.

> +  ;; The user this should be set to (defaults to root)
> +  (user          setuid-program-user              ;integer or string
> +                 (default 0))
> +  ;; Group we want to set this to (defaults to root)
> +  (group         setuid-program-group             ;integer or string
> +                 (default 0)))
> +(define (setuid-program-entry programs)
> +  #~(activate-setuid-programs
> +     ;; convert into a tagged list structure as expected by
> +     ;; activate-setuid-programs
> +     (list #$@(map (match-lambda
> +                     [(? setuid-program? sp)
> +                      #~(list 'setuid-program
> +                              #$(setuid-program-program sp)
> +                              #$(setuid-program-setuid? sp)
> +                              #$(setuid-program-setgid? sp)
> +                              #$(setuid-program-user sp)
> +                              #$(setuid-program-group sp))]
> +                     ;; legacy, non-<setuid-program> structure
> +                     [program
> +                      ;; TODO: Spit out a warning here?

A deprecation message should be printed, urging the users to use the new
interface, yes.

> +                      #~(list 'setuid-program
> +                              #$program
> +                              #t #t 0 0)])
> +                   programs))))
> +
>  (define setuid-program-service-type
>    (service-type (name 'setuid-program)
>                  (extensions
>                   (list (service-extension activation-service-type
> -                                          (lambda (programs)
> -                                            #~(activate-setuid-programs
> -                                               (list #$@programs))))))
> +                                          setuid-program-entry)))
>                  (compose concatenate)
>                  (extend append)
>                  (description

With the above comments, this looks like a good change to me!  I haven't
tested it yet, but intend to do so when I have a chance!

Thank you for working on it,

Maxim




      parent reply	other threads:[~2020-11-17 16:30 UTC|newest]

Thread overview: 19+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2020-11-16 23:29 [bug#44700] services: setuid: More configurable setuid support Christopher Lemmer Webber
2020-11-17  9:46 ` Ludovic Courtès
2020-11-17 16:31   ` Christopher Lemmer Webber
2020-11-17 20:48     ` Ludovic Courtès
2021-04-14 17:06       ` Christopher Lemmer Webber
2021-07-03 16:51         ` [bug#44700] [PATCH v2 0/2] " Brice Waegeneire
2021-07-03 16:51         ` [bug#44700] [PATCH v2 1/2] " Brice Waegeneire
2021-07-03 16:51         ` [bug#44700] [PATCH v2 2/2] services: Migrate to <setuid-program> Brice Waegeneire
2021-07-05 15:28           ` Chris Lemmer-Webber
2021-07-06 20:03             ` [bug#44700] [PATCH v3 0/2] More configurable setuid/setgid support Brice Waegeneire
2021-07-06 20:03             ` [bug#44700] [PATCH v3 1/2] services: setuid: More configurable setuid support Brice Waegeneire
2021-07-06 20:03             ` [bug#44700] [PATCH v3 2/2] services: Migrate to <setuid-program> Brice Waegeneire
2021-07-07 17:41               ` Chris Lemmer-Webber
2021-07-29 16:04                 ` Christine Lemmer-Webber
2021-07-29 16:16                   ` Christine Lemmer-Webber
2021-07-29 16:18                     ` bug#44700: " Christine Lemmer-Webber
2021-08-12 10:37                     ` [bug#44700] services: setuid: More configurable setuid support Ludovic Courtès
2021-08-12 16:06                       ` Christine Lemmer-Webber
2020-11-17 16:29 ` Maxim Cournoyer [this message]

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=875z64aqvw.fsf@gmail.com \
    --to=maxim.cournoyer@gmail.com \
    --cc=44700@debbugs.gnu.org \
    --cc=cwebber@dustycloud.org \
    /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).