sddm/sddm-0.17.0.20180408git-fix-pam-group.patch

90 lines
3.5 KiB
Diff
Raw Normal View History

From bd14b3a8a9731e644a50c1c350b7f76038c22bbb Mon Sep 17 00:00:00 2001
From: "J. Konrad Tegtmeier-Rottach" <jktr@0x16.de>
Date: Mon, 19 Jun 2017 23:13:34 +0200
Subject: [PATCH] Honor PAM's ambient supplemental groups.
When compiled with USE_PAM, prefer a combination of
getgroups(3) and getgrouplist(3) for ambient and user
groups, respectively, to initgroups(3).
This way, groups injected into the PAM environment
by means of pam_groups.so aren't ignored.
Signed-off-by: J. Konrad Tegtmeier-Rottach <jktr@0x16.de>
---
src/helper/UserSession.cpp | 57 ++++++++++++++++++++++++++++++++++++++++++++++
1 file changed, 57 insertions(+)
diff --git a/src/helper/UserSession.cpp b/src/helper/UserSession.cpp
index 587888d7..4b5b8553 100644
--- a/src/helper/UserSession.cpp
+++ b/src/helper/UserSession.cpp
@@ -116,10 +116,67 @@ namespace SDDM {
qCritical() << "setgid(" << pw->pw_gid << ") failed for user: " << username;
exit(Auth::HELPER_OTHER_ERROR);
}
+
+#ifdef USE_PAM
+
+ // fetch ambient groups from PAM's environment;
+ // these are set by modules such as pam_groups.so
+ int n_pam_groups = getgroups(0, NULL);
+ gid_t *pam_groups = NULL;
+ if (n_pam_groups > 0) {
+ pam_groups = new gid_t[n_pam_groups];
+ if ((n_pam_groups = getgroups(n_pam_groups, pam_groups)) == -1) {
+ qCritical() << "getgroups() failed to fetch supplemental"
+ << "PAM groups for user:" << username;
+ exit(Auth::HELPER_OTHER_ERROR);
+ }
+ } else {
+ n_pam_groups = 0;
+ }
+
+ // fetch session's user's groups
+ int n_user_groups = 0;
+ gid_t *user_groups = NULL;
+ if (-1 == getgrouplist(username.constData(), pw->pw_gid,
+ NULL, &n_user_groups)) {
+ user_groups = new gid_t[n_user_groups];
+ if ((n_user_groups = getgrouplist(username.constData(),
+ pw->pw_gid, user_groups,
+ &n_user_groups)) == -1 ) {
+ qCritical() << "getgrouplist(" << username << ", " << pw->pw_gid
+ << ") failed";
+ exit(Auth::HELPER_OTHER_ERROR);
+ }
+ }
+
+ // set groups to concatenation of PAM's ambient
+ // groups and the session's user's groups
+ int n_groups = n_pam_groups + n_user_groups;
+ if (n_groups > 0) {
+ gid_t *groups = new gid_t[n_groups];
+ memcpy(groups, pam_groups, (n_pam_groups * sizeof(gid_t)));
+ memcpy((groups + n_pam_groups), user_groups,
+ (n_user_groups * sizeof(gid_t)));
+
+ // setgroups(2) handles duplicate groups
+ if (setgroups(n_groups, groups) != 0) {
+ qCritical() << "setgroups() failed for user: " << username;
+ exit (Auth::HELPER_OTHER_ERROR);
+ }
+ delete[] groups;
+ }
+ delete[] pam_groups;
+ delete[] user_groups;
+
+#else
+
if (initgroups(pw->pw_name, pw->pw_gid) != 0) {
qCritical() << "initgroups(" << pw->pw_name << ", " << pw->pw_gid << ") failed for user: " << username;
exit(Auth::HELPER_OTHER_ERROR);
}
+
+#endif /* USE_PAM */
+
if (setuid(pw->pw_uid) != 0) {
qCritical() << "setuid(" << pw->pw_uid << ") failed for user: " << username;
exit(Auth::HELPER_OTHER_ERROR);