diff --git a/pam-check-user-home-dir.patch b/pam-check-user-home-dir.patch new file mode 100644 index 0000000..e3a98e7 --- /dev/null +++ b/pam-check-user-home-dir.patch @@ -0,0 +1,72 @@ +From 27ded8954a1235bb65ffc9c730ae5a50b1dfed61 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Josef=20M=C3=B6llers?= +Date: Fri, 29 May 2020 14:35:43 +0000 +Subject: [PATCH] pam_setquota: skip mountpoints equal to the user's $HOME +MIME-Version: 1.0 +Content-Type: text/plain; charset=UTF-8 +Content-Transfer-Encoding: 8bit + +Matthias Gerstner found the following issue: + + +So this pam_setquota module iterates over all mounted file systems using +`setmntent()` and `getmntent()`. It tries to find the longest match of +a file system mounted on /home/$USER or above (except when the +fs=/some/path parameter is passed to the pam module). + +The thing is that /home/$USER is owned by the unprivileged user. And +there exist tools like fusermount from libfuse which is by default +installed setuid-root for everybody. fusermount allows to mount a FUSE +file system using an arbitrary "source device name" as the unprivileged +user. + +Thus considering the following use case: + +1) there is only the root file system (/) or a file system is mounted on + /home, but not on /home/$USER. +2) the attacker mounts a fake FUSE file system over its own home directory: + + ``` + user $ export _FUSE_COMMFD=0 + user $ fusermount $HOME -ononempty,fsname=/dev/sda1 + ``` + + This will result in a mount entry in /proc/mounts looking like this: + + ``` + /dev/sda1 on /home/$USER type fuse (rw,nosuid,nodev,relatime,user_id=1000,group_id=100) + ``` +3) when the attacker now logs in with pam_setquota configured then + pam_setquota will identify /dev/sda1 and the file system where + to apply the user's quota on. + +As a result an unprivileged user has full control over onto which block +device the quota is applied. + + +If the user's $HOME is on a separate partition, setting a quota on the +user's $HOME does not really make sense, so this patch skips mountpoints +equal to the user's $HOME, preventing the above mentioned bug as +a side-effect (or vice-versa). + +Reported-by: Matthias Gerstner +Co-authored-by: Tomáš Mráz +Co-authored-by: Dmitry V. Levin +Resolves: https://github.com/linux-pam/linux-pam/pull/230 +--- + modules/pam_setquota/pam_setquota.c | 2 +- + 1 file changed, 1 insertion(+), 1 deletion(-) + +diff --git a/modules/pam_setquota/pam_setquota.c b/modules/pam_setquota/pam_setquota.c +index 9c05862a..01b05e38 100644 +--- a/modules/pam_setquota/pam_setquota.c ++++ b/modules/pam_setquota/pam_setquota.c +@@ -275,7 +275,7 @@ pam_sm_open_session(pam_handle_t *pamh, int flags UNUSED, + */ + if ((mnt_len > match_size || (mnt_len == 0 && mnt->mnt_dir[0] == '/')) && + (s = pam_str_skip_prefix_len(pwd->pw_dir, mnt->mnt_dir, mnt_len)) != NULL && +- (s[0] == '\0' || s[0] == '/')) { ++ s[0] == '/') { + free(mntdevice); + if ((mntdevice = strdup(mnt->mnt_fsname)) == NULL) { + pam_syslog(pamh, LOG_CRIT, "Memory allocation error"); diff --git a/pam.changes b/pam.changes index ecbc36b..8085123 100644 --- a/pam.changes +++ b/pam.changes @@ -1,3 +1,11 @@ +------------------------------------------------------------------- +Thu May 28 12:36:33 UTC 2020 - Josef Möllers + +- pam_setquota.so: + When setting quota, don't apply any quota if the user's $HOME is + a mountpoint (ie the user has a partition of his/her own). + [bsc#1171721, pam-check-user-home-dir.patch] + ------------------------------------------------------------------- Wed May 27 09:27:32 UTC 2020 - Thorsten Kukuk diff --git a/pam.spec b/pam.spec index 82bb5fd..e95797a 100644 --- a/pam.spec +++ b/pam.spec @@ -48,6 +48,7 @@ Source12: pam-login_defs-check.sh Patch0: fix-man-links.dif Patch2: pam-limit-nproc.patch Patch4: pam-hostnames-in-access_conf.patch +Patch5: pam-check-user-home-dir.patch BuildRequires: audit-devel BuildRequires: bison BuildRequires: cracklib-devel @@ -141,6 +142,7 @@ cp -a %{SOURCE12} . %patch0 -p1 %patch2 -p1 %patch4 -p1 +%patch5 -p1 %build bash ./pam-login_defs-check.sh @@ -213,7 +215,6 @@ for i in pam_*/README; do done popd # XXX Remove until whitelisted -rm %{buildroot}/%{_lib}/security/pam_setquota.so rm %{buildroot}/%{_lib}/security/pam_faillock.so # Install unix2_chkpwd install -m 755 %{_builddir}/unix2_chkpwd %{buildroot}/sbin/ @@ -368,7 +369,7 @@ done /%{_lib}/security/pam_selinux.so /%{_lib}/security/pam_sepermit.so %endif -#/%{_lib}/security/pam_setquota.so +/%{_lib}/security/pam_setquota.so /%{_lib}/security/pam_shells.so /%{_lib}/security/pam_stress.so /%{_lib}/security/pam_succeed_if.so