[pacman-dev] [WIP 0/4] Dynamic Users
Packages with files owned by dynamically created users/groups have to create the user and chown the files in a post_install/post_upgrade install script. This makes pacman's database out of sync with the filesystem. See FS#43484. This patchset makes alpm/pacman aware of symbolic usernames and uses fakeuser (https://github.com/progandy/fakeuser) to provide a method for PKGBUILDs to add fake users. alpm will still fall back to the raw uid if it has not already been assigned, so packages that add users in post_install/post_upgrade will continue to work correctly, but should be changed to use pre_install/pre_upgrade instead. The makepkg portions should be complete, other than documentation. The alpm/pacman portions still need to be optimized to use a cache so that we don't have to consult /etc/{passwd,group} for every single file. *NOTE*: there is a bug in libarchive that prevents the symlink check from working with this patchset. This will be fixed in the next release. PKGBUILD ======== pkgname=dynamic-users-test pkgver=1 pkgrel=1 arch=(any) install=dynamic-users-test.install # entries are in passwd(5)/group(5) format, empty trailing fields can be omitted sysusers=('myuser') sysgroups=('mygroup') package() { touch "$pkgdir/testfile" chown myuser:mygroup "$pkgdir/testfile" } dynamic-users-test.install ========================== pre_install() { getent passwd myuser &>/dev/null || useradd --system myuser getent group mygroup &>/dev/null || groupadd --system mygroup } pre_upgrade() { pre_install } Andrew Gregory (4): use custom uid/gid lookup functions makepkg add sysusers during package() makepkg: store symbolic user/group names in mtree check_file_permissions: use symbolic user/group names if available lib/libalpm/add.c | 32 ++++++++++++++++++- scripts/Makefile.am | 2 ++ scripts/libmakepkg/.gitignore | 2 ++ scripts/libmakepkg/sysgroups.sh.in | 60 +++++++++++++++++++++++++++++++++++ scripts/libmakepkg/sysusers.sh.in | 65 ++++++++++++++++++++++++++++++++++++++ scripts/makepkg.sh.in | 6 ++-- src/pacman/check.c | 46 +++++++++++++++++++++------ 7 files changed, 200 insertions(+), 13 deletions(-) create mode 100644 scripts/libmakepkg/sysgroups.sh.in create mode 100644 scripts/libmakepkg/sysusers.sh.in -- 2.7.2
---
lib/libalpm/add.c | 32 +++++++++++++++++++++++++++++++-
1 file changed, 31 insertions(+), 1 deletion(-)
diff --git a/lib/libalpm/add.c b/lib/libalpm/add.c
index f5c9a95..e40ce27 100644
--- a/lib/libalpm/add.c
+++ b/lib/libalpm/add.c
@@ -106,6 +106,31 @@ int SYMEXPORT alpm_add_pkg(alpm_handle_t *handle, alpm_pkg_t *pkg)
return 0;
}
+#include
---
scripts/Makefile.am | 2 ++
scripts/libmakepkg/.gitignore | 2 ++
scripts/libmakepkg/sysgroups.sh.in | 60 +++++++++++++++++++++++++++++++++++
scripts/libmakepkg/sysusers.sh.in | 65 ++++++++++++++++++++++++++++++++++++++
scripts/makepkg.sh.in | 4 ++-
5 files changed, 132 insertions(+), 1 deletion(-)
create mode 100644 scripts/libmakepkg/sysgroups.sh.in
create mode 100644 scripts/libmakepkg/sysusers.sh.in
diff --git a/scripts/Makefile.am b/scripts/Makefile.am
index 6f9abb8..a3c1050 100644
--- a/scripts/Makefile.am
+++ b/scripts/Makefile.am
@@ -81,6 +81,8 @@ LIBMAKEPKG_IN = \
libmakepkg/source/hg.sh \
libmakepkg/source/local.sh \
libmakepkg/source/svn.sh \
+ libmakepkg/sysgroups.sh \
+ libmakepkg/sysusers.sh \
libmakepkg/tidy.sh \
libmakepkg/tidy/docs.sh \
libmakepkg/tidy/emptydirs.sh \
diff --git a/scripts/libmakepkg/.gitignore b/scripts/libmakepkg/.gitignore
index 2de91e7..7a784d0 100644
--- a/scripts/libmakepkg/.gitignore
+++ b/scripts/libmakepkg/.gitignore
@@ -4,6 +4,8 @@ lint_pkgbuild.sh
lint_pkgbuild/*.sh
source.sh
source/*.sh
+sysusers.sh
+sysgroups.sh
tidy.sh
tidy/*.sh
util.sh
diff --git a/scripts/libmakepkg/sysgroups.sh.in b/scripts/libmakepkg/sysgroups.sh.in
new file mode 100644
index 0000000..095d60e
--- /dev/null
+++ b/scripts/libmakepkg/sysgroups.sh.in
@@ -0,0 +1,60 @@
+#!/bin/bash
+#
+# source.sh - functions for downloading and extracting sources
+#
+# Copyright (c) 2016 Pacman Development Team
--- scripts/makepkg.sh.in | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/scripts/makepkg.sh.in b/scripts/makepkg.sh.in index a0134f6..1729782 100644 --- a/scripts/makepkg.sh.in +++ b/scripts/makepkg.sh.in @@ -1220,7 +1220,7 @@ create_package() { msg2 "$(gettext "Generating .MTREE file...")" LANG=C bsdtar -czf .MTREE --format=mtree \ - --options='!all,use-set,type,uid,gid,mode,time,size,md5,sha256,link' \ + --options='!all,use-set,type,uid,uname,gid,gname,mode,time,size,md5,sha256,link' \ "${comp_files[@]}" * comp_files+=(".MTREE") -- 2.7.2
Signed-off-by: Andrew Gregory
On 19/03/16 23:50, Andrew Gregory wrote:
Packages with files owned by dynamically created users/groups have to create the user and chown the files in a post_install/post_upgrade install script. This makes pacman's database out of sync with the filesystem. See FS#43484.
This patchset makes alpm/pacman aware of symbolic usernames and uses fakeuser (https://github.com/progandy/fakeuser) to provide a method for PKGBUILDs to add fake users.
alpm will still fall back to the raw uid if it has not already been assigned, so packages that add users in post_install/post_upgrade will continue to work correctly, but should be changed to use pre_install/pre_upgrade instead.
The makepkg portions should be complete, other than documentation. The alpm/pacman portions still need to be optimized to use a cache so that we don't have to consult /etc/{passwd,group} for every single file.
Great! I have no substantial comments from a brief look at the patchset. Minor comments to follow.
*NOTE*: there is a bug in libarchive that prevents the symlink check from working with this patchset. This will be fixed in the next release.
So we will need to add a configure check either for the latest libarchive or for this fix. A
On 19/03/16 23:50, Andrew Gregory wrote:
--- scripts/Makefile.am | 2 ++ scripts/libmakepkg/.gitignore | 2 ++ scripts/libmakepkg/sysgroups.sh.in | 60 +++++++++++++++++++++++++++++++++++ scripts/libmakepkg/sysusers.sh.in | 65 ++++++++++++++++++++++++++++++++++++++ scripts/makepkg.sh.in | 4 ++- 5 files changed, 132 insertions(+), 1 deletion(-) create mode 100644 scripts/libmakepkg/sysgroups.sh.in create mode 100644 scripts/libmakepkg/sysusers.sh.in
diff --git a/scripts/Makefile.am b/scripts/Makefile.am index 6f9abb8..a3c1050 100644 --- a/scripts/Makefile.am +++ b/scripts/Makefile.am @@ -81,6 +81,8 @@ LIBMAKEPKG_IN = \ libmakepkg/source/hg.sh \ libmakepkg/source/local.sh \ libmakepkg/source/svn.sh \ + libmakepkg/sysgroups.sh \ + libmakepkg/sysusers.sh \
libmakepkg/util/?
libmakepkg/tidy.sh \ libmakepkg/tidy/docs.sh \ libmakepkg/tidy/emptydirs.sh \ diff --git a/scripts/libmakepkg/.gitignore b/scripts/libmakepkg/.gitignore index 2de91e7..7a784d0 100644 --- a/scripts/libmakepkg/.gitignore +++ b/scripts/libmakepkg/.gitignore @@ -4,6 +4,8 @@ lint_pkgbuild.sh lint_pkgbuild/*.sh source.sh source/*.sh +sysusers.sh +sysgroups.sh tidy.sh tidy/*.sh util.sh diff --git a/scripts/libmakepkg/sysgroups.sh.in b/scripts/libmakepkg/sysgroups.sh.in new file mode 100644 index 0000000..095d60e --- /dev/null +++ b/scripts/libmakepkg/sysgroups.sh.in @@ -0,0 +1,60 @@ +#!/bin/bash +# +# source.sh - functions for downloading and extracting sources
Update
+# +# Copyright (c) 2016 Pacman Development Team
+# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see http://www.gnu.org/licenses/. +# + +[[ -n "$LIBMAKEPKG_SOURCE_SYSGROUPS" ]] && return
LIBMAKEPKG_SYSGROUPS or LIBMAKEPKG_UTIL_SYSGROUPS
+LIBMAKEPKG_SOURCE_SYSGROUPS=1 + +# field indices +gr_name=0 +gr_passwd=1 +gr_gid=2 +gr_users=3 + +dynamic_gid=101 + +gr_parse_ent() { + IFS=: read -a "$1" +} + +add_fake_group() { + local -a gr fakeuser_args + gr_parse_ent 'gr' <<< "$1" + + if [[ -n ${gr[$gr_gid]} ]]; then + fakeuser_args+=('-g' "${gr[$gr_gid]}") + else + fakeuser_args+=('-g' $(( dynamic_gid++ )) ) + fi + + [[ -n ${gr[$gr_name]} ]] && fakeuser_args+=('-n' "${gr[$gr_name]}") + [[ -n ${gr[$gr_passwd]} ]] && fakeuser_args+=('-p' "${gr[$gr_passwd]}") + [[ -n ${gr[$gr_gid]} ]] && fakeuser_args+=('-g' "${gr[$gr_gid]}") + [[ -n ${gr[$gr_users]} ]] && fakeuser_args+=('-m' "${gr[$gr_gecos]}") + + fakeadd -G "${fakeuser_args[@]}" +} + +add_fake_groups() { + for ent in "${sysgroups[@]}"; do + add_fake_group "$ent" + done +} + +# vim: set noet:
There are no other vim lines in libmakepkg... mostly because I don't use vim! I dislike them due to applying to a single editor. We need to discuss this separately!
diff --git a/scripts/libmakepkg/sysusers.sh.in b/scripts/libmakepkg/sysusers.sh.in new file mode 100644 index 0000000..fbb7328 --- /dev/null +++ b/scripts/libmakepkg/sysusers.sh.in @@ -0,0 +1,65 @@ +#!/bin/bash +# +# source.sh - functions for downloading and extracting sources +# +# Copyright (c) 2016 Pacman Development Team
+# +# This program is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 2 of the License, or +# (at your option) any later version. +# +# This program is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with this program. If not, see http://www.gnu.org/licenses/. +# + +[[ -n "$LIBMAKEPKG_SOURCE_SYSUSERS" ]] && return +LIBMAKEPKG_SOURCE_SYSUSERS=1 + +# field indices +pw_name=0 +pw_passwd=1 +pw_uid=2 +pw_gid=3 +pw_gecos=4 +pw_dir=5 +pw_shell=6 + +dynamic_uid=101 + +pw_parse_ent() { + IFS=: read -a "$1" +} + +add_fake_user() { + local -a pw fakeuser_args + pw_parse_ent 'pw' <<< "$1" + + if [[ -n ${pw[$pw_uid]} ]]; then + fakeuser_args+=('-u' "${pw[$pw_uid]}") + else + fakeuser_args+=('-u' $(( dynamic_uid++ )) ) + fi + + [[ -n ${pw[$pw_name]} ]] && fakeuser_args+=('-n' "${pw[$pw_name]}") + [[ -n ${pw[$pw_passwd]} ]] && fakeuser_args+=('-p' "${pw[$pw_passwd]}") + [[ -n ${pw[$pw_gid]} ]] && fakeuser_args+=('-g' "${pw[$pw_gid]}") + [[ -n ${pw[$pw_gecos]} ]] && fakeuser_args+=('-c' "${pw[$pw_gecos]}") + [[ -n ${pw[$pw_dir]} ]] && fakeuser_args+=('-d' "${pw[$pw_dir]}") + [[ -n ${pw[$pw_shell]} ]] && fakeuser_args+=('-s' "${pw[$pw_shell]}") + + fakeadd -U "${fakeuser_args[@]}" +} + +add_fake_users() { + for ent in "${sysusers[@]}"; do + add_fake_user "$ent" + done +} + +# vim: set noet: diff --git a/scripts/makepkg.sh.in b/scripts/makepkg.sh.in index 2efcc98..a0134f6 100644 --- a/scripts/makepkg.sh.in +++ b/scripts/makepkg.sh.in @@ -167,7 +167,7 @@ clean_up() { enter_fakeroot() { msg "$(gettext "Entering %s environment...")" "fakeroot" - fakeroot -- $0 -F "${ARGLIST[@]}" || exit $? + LD_PRELOAD=/usr/lib/libfakeuser.so fakeroot -- $0 -F "${ARGLIST[@]}" || exit $?
We should probably have a check that fakeuser is installed.
}
# Automatically update pkgver variable if a pkgver() function is provided @@ -2098,6 +2098,8 @@ if (( INFAKEROOT )); then fi
chmod 755 "$pkgdirbase" + add_fake_users + add_fake_groups if (( ! SPLITPKG )); then pkgdir="$pkgdirbase/$pkgname" mkdir "$pkgdir"
participants (2)
-
Allan McRae
-
Andrew Gregory