The branch stable/14 has been updated by kevans:

URL: 
https://cgit.FreeBSD.org/src/commit/?id=57b08d98db0a5bc16a6f0b47ade5b25021564d14

commit 57b08d98db0a5bc16a6f0b47ade5b25021564d14
Author:     Kyle Evans <[email protected]>
AuthorDate: 2025-10-29 02:37:21 +0000
Commit:     Kyle Evans <[email protected]>
CommitDate: 2026-01-20 04:05:44 +0000

    libutil: defer setting the MAC label until after the login class
    
    MAC policies, like mac_biba(4), may forbid changing the login class once
    a label has been applied.  For setting up the initial login context,
    this isn't really expected and in-fact may break some class-based
    configuration.
    
    Defer setting the MAC label until after the login class is set, and
    remove the requirement that we have a pwd entry since the label is
    pulled from the login class -- we only use pwd for syslog in this path.
    
    Patch is largely by Kevin Barry, with some modifications and this commit
    message by kevans@.
    
    PR:             177698
    Reviewed by:    des, olce
    Co-authored-by: Kevin Barry <ta0kira gmail com>
    
    (cherry picked from commit 98edcbcce0a4650084bd86e704cfa38bf590250c)
---
 lib/libutil/login_class.c | 55 ++++++++++++++++++++++++++---------------------
 1 file changed, 30 insertions(+), 25 deletions(-)

diff --git a/lib/libutil/login_class.c b/lib/libutil/login_class.c
index 172da78aaf17..db0218f94371 100644
--- a/lib/libutil/login_class.c
+++ b/lib/libutil/login_class.c
@@ -544,7 +544,7 @@ setusercontext(login_cap_t *lc, const struct passwd *pwd, 
uid_t uid, unsigned in
 
     /* we need a passwd entry to set these */
     if (pwd == NULL)
-       flags &= ~(LOGIN_SETGROUP | LOGIN_SETLOGIN | LOGIN_SETMAC);
+       flags &= ~(LOGIN_SETGROUP | LOGIN_SETLOGIN);
 
     /* Set the process priority */
     if (flags & LOGIN_SETPRIORITY)
@@ -565,6 +565,27 @@ setusercontext(login_cap_t *lc, const struct passwd *pwd, 
uid_t uid, unsigned in
        }
     }
 
+    /* Set the sessions login */
+    if ((flags & LOGIN_SETLOGIN) && setlogin(pwd->pw_name) != 0) {
+       syslog(LOG_ERR, "setlogin(%s): %m", pwd->pw_name);
+       login_close(llc);
+       return (-1);
+    }
+
+    /* Inform the kernel about current login class */
+    if (lc != NULL && lc->lc_class != NULL && (flags & LOGIN_SETLOGINCLASS)) {
+       error = setloginclass(lc->lc_class);
+       if (error != 0) {
+           syslog(LOG_ERR, "setloginclass(%s): %m", lc->lc_class);
+#ifdef notyet
+           login_close(llc);
+           return (-1);
+#endif
+       }
+    }
+
+    setlogincontext(lc, pwd, flags);
+
     /* Set up the user's MAC label. */
     if ((flags & LOGIN_SETMAC) && mac_is_present(NULL) == 1) {
        const char *label_string;
@@ -573,8 +594,10 @@ setusercontext(login_cap_t *lc, const struct passwd *pwd, 
uid_t uid, unsigned in
        label_string = login_getcapstr(lc, "label", NULL, NULL);
        if (label_string != NULL) {
            if (mac_from_text(&label, label_string) == -1) {
-               syslog(LOG_ERR, "mac_from_text('%s') for %s: %m",
-                   pwd->pw_name, label_string);
+               syslog(LOG_ERR, "mac_from_text('%s') for %s %s: %m",
+                   label_string, pwd != NULL ? "user" : "class",
+                   pwd != NULL ? pwd->pw_name : lc->lc_class);
+               login_close(llc);
                return (-1);
            }
            if (mac_set_proc(label) == -1)
@@ -583,33 +606,15 @@ setusercontext(login_cap_t *lc, const struct passwd *pwd, 
uid_t uid, unsigned in
                error = 0;
            mac_free(label);
            if (error != 0) {
-               syslog(LOG_ERR, "mac_set_proc('%s') for %s: %s",
-                   label_string, pwd->pw_name, strerror(error));
+               syslog(LOG_ERR, "mac_set_proc('%s') for %s %s: %s",
+                   label_string, pwd != NULL ? "user" : "class",
+                   pwd != NULL ? pwd->pw_name : lc->lc_class, strerror(error));
+               login_close(llc);
                return (-1);
            }
        }
     }
 
-    /* Set the sessions login */
-    if ((flags & LOGIN_SETLOGIN) && setlogin(pwd->pw_name) != 0) {
-       syslog(LOG_ERR, "setlogin(%s): %m", pwd->pw_name);
-       login_close(llc);
-       return (-1);
-    }
-
-    /* Inform the kernel about current login class */
-    if (lc != NULL && lc->lc_class != NULL && (flags & LOGIN_SETLOGINCLASS)) {
-       error = setloginclass(lc->lc_class);
-       if (error != 0) {
-           syslog(LOG_ERR, "setloginclass(%s): %m", lc->lc_class);
-#ifdef notyet
-           login_close(llc);
-           return (-1);
-#endif
-       }
-    }
-
-    setlogincontext(lc, pwd, flags);
     login_close(llc);
 
     /* This needs to be done after anything that needs root privs */

Reply via email to