All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 0/7] User/group creation at preinstall
@ 2011-05-31 19:53 ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 18:13 UTC (permalink / raw)
  To: poky

Hi Saul,

This pull request includes everything needed to add the ability to
create custom users and groups in our images/packages and the
corresponding ability to set custom ownership permissions. 

There is a useradd-example.bb file in meta-skeleton which provides
a heavily-commented example recipe to demonstrate how this feature
can be used.

I'd like to request that Mark Hatle and Richard do a code review of
this and offer their Acked-by: support if they are happy with things.

Once this gets into master, I'm happy to write up a short section for
the Poky Reference Manual to document it in a more visible way.

Scott

The following changes since commit 1169f1b066d0028bd2ef7915440450bd42ef165e:

  license.bbclass: Sane Parsing of licenses (2011-05-27 23:36:24 +0100)

are available in the git repository at:
  git://git.pokylinux.org/poky-contrib sgarman/user-group-creation
  http://git.pokylinux.org/cgit.cgi/poky-contrib/log/?h=sgarman/user-group-creation

Scott Garman (7):
  shadow: recipe and patch cleanup
  shadow: add a -native recipe with customized utilities
  base-passwd: add -cross recipe with default login.defs
  useradd.bbclass: new class for managing user/group permissions
  useradd-example: example recipe for using inherit useradd
  bitbake.conf: set PSEUDO_PASSWD within FAKEROOTENV
  package_rpm.bbclass: make RPM use on-disk permissions

 .../recipes-skeleton/useradd/useradd-example.bb    |   59 +
 meta/classes/package_rpm.bbclass                   |    2 +
 meta/classes/useradd.bbclass                       |  136 ++
 meta/conf/bitbake.conf                             |    2 +-
 .../base-passwd/base-passwd-3.5.22/login.defs      |  386 ++++++
 .../base-passwd/base-passwd-cross_3.5.22.bb        |   53 +
 .../shadow/files/add_root_cmd_options.patch        | 1293 ++++++++++++++++++++
 .../files/shadow-4.1.3-dots-in-usernames.patch     |    4 +
 .../shadow-4.1.4.2-env-reset-keep-locale.patch     |    4 +
 .../files/shadow-4.1.4.2-groupmod-pam-check.patch  |    4 +
 .../files/shadow-4.1.4.2-su_no_sanitize_env.patch  |    4 +
 .../shadow/files/shadow.automake-1.11.patch        |    4 +
 .../shadow/shadow-native_4.1.4.3.bb                |   66 +
 meta/recipes-extended/shadow/shadow.inc            |  121 --
 meta/recipes-extended/shadow/shadow_4.1.4.3.bb     |  141 ++-
 15 files changed, 2148 insertions(+), 131 deletions(-)
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
 create mode 100644 meta/classes/useradd.bbclass
 create mode 100644 meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
 create mode 100644 meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
 create mode 100644 meta/recipes-extended/shadow/files/add_root_cmd_options.patch
 create mode 100644 meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
 delete mode 100644 meta/recipes-extended/shadow/shadow.inc



^ permalink raw reply	[flat|nested] 51+ messages in thread

* [PATCH 1/7] shadow: recipe and patch cleanup
  2011-05-31 19:53 ` Scott Garman
@ 2011-05-31 19:53   ` Scott Garman
  -1 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 18:13 UTC (permalink / raw)
  To: poky

Taking over maintenance of the shadow recipe. Cleaning it up in
preparation of adding a -native version that will be used to add
users/groups during postinstall.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 .../files/shadow-4.1.3-dots-in-usernames.patch     |    4 +
 .../shadow-4.1.4.2-env-reset-keep-locale.patch     |    4 +
 .../files/shadow-4.1.4.2-groupmod-pam-check.patch  |    4 +
 .../files/shadow-4.1.4.2-su_no_sanitize_env.patch  |    4 +
 .../shadow/files/shadow.automake-1.11.patch        |    4 +
 meta/recipes-extended/shadow/shadow.inc            |  121 -----------------
 meta/recipes-extended/shadow/shadow_4.1.4.3.bb     |  141 ++++++++++++++++++--
 7 files changed, 152 insertions(+), 130 deletions(-)
 delete mode 100644 meta/recipes-extended/shadow/shadow.inc

diff --git a/meta/recipes-extended/shadow/files/shadow-4.1.3-dots-in-usernames.patch b/meta/recipes-extended/shadow/files/shadow-4.1.3-dots-in-usernames.patch
index 7a2ff2e..a7bb0a9 100644
--- a/meta/recipes-extended/shadow/files/shadow-4.1.3-dots-in-usernames.patch
+++ b/meta/recipes-extended/shadow/files/shadow-4.1.3-dots-in-usernames.patch
@@ -9,6 +9,10 @@
 #
 # comment added by Kevin Tian <kevin.tian@intel.com>, 2010-08-11
 
+Upstream-Status: Pending
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
 Index: shadow-4.1.4.2/libmisc/chkname.c
 ===================================================================
 --- shadow-4.1.4.2.orig/libmisc/chkname.c	2009-04-28 12:14:04.000000000 -0700
diff --git a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-env-reset-keep-locale.patch b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-env-reset-keep-locale.patch
index 124065c..6514746 100644
--- a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-env-reset-keep-locale.patch
+++ b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-env-reset-keep-locale.patch
@@ -12,6 +12,10 @@
 http://bugs.gentoo.org/283725
 https://alioth.debian.org/tracker/index.php?func=detail&aid=311740&group_id=30580&atid=411480
 
+Upstream-Status: Pending
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
 Index: shadow-4.1.4.2/libmisc/env.c
 ===================================================================
 --- shadow-4.1.4.2.orig/libmisc/env.c	2009-04-27 13:07:56.000000000 -0700
diff --git a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-groupmod-pam-check.patch b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-groupmod-pam-check.patch
index 6682fe8..640200b 100644
--- a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-groupmod-pam-check.patch
+++ b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-groupmod-pam-check.patch
@@ -17,6 +17,10 @@ http://lists.alioth.debian.org/pipermail/pkg-shadow-devel/2009-November/007850.h
 	* NEWS, src/groupmod.c: Fixed groupmod when configured with
 	--enable-account-tools-setuid.
 
+Upstream-Status: Pending
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
 Index: shadow-4.1.4.2/src/groupmod.c
 ===================================================================
 --- shadow-4.1.4.2.orig/src/groupmod.c	2009-06-05 15:16:58.000000000 -0700
diff --git a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-su_no_sanitize_env.patch b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-su_no_sanitize_env.patch
index f67251c..0dc4d75 100644
--- a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-su_no_sanitize_env.patch
+++ b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-su_no_sanitize_env.patch
@@ -12,6 +12,10 @@
 http://bugs.gentoo.org/show_bug.cgi?id=301957
 https://alioth.debian.org/scm/browser.php?group_id=30580
 
+Upstream-Status: Pending
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
 Index: shadow-4.1.4.2/src/su.c
 ===================================================================
 --- shadow-4.1.4.2.orig/src/su.c	2009-07-23 13:38:56.000000000 -0700
diff --git a/meta/recipes-extended/shadow/files/shadow.automake-1.11.patch b/meta/recipes-extended/shadow/files/shadow.automake-1.11.patch
index 36d7be6..a793f09 100644
--- a/meta/recipes-extended/shadow/files/shadow.automake-1.11.patch
+++ b/meta/recipes-extended/shadow/files/shadow.automake-1.11.patch
@@ -11,6 +11,10 @@
 
 man_nopan is for !USE_PAM already included in man_MANS and automake-1.11 hates to install some file twice
 
+Upstream-Status: Pending
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
 diff -uNr shadow-4.1.4.2.orig/man/Makefile.am shadow-4.1.4.2/man/Makefile.am
 --- shadow-4.1.4.2.orig/man/Makefile.am	2009-03-14 15:40:10.000000000 +0100
 +++ shadow-4.1.4.2/man/Makefile.am	2010-04-02 07:31:17.000000000 +0200
diff --git a/meta/recipes-extended/shadow/shadow.inc b/meta/recipes-extended/shadow/shadow.inc
deleted file mode 100644
index 42f92a7..0000000
--- a/meta/recipes-extended/shadow/shadow.inc
+++ /dev/null
@@ -1,121 +0,0 @@
-DESCRIPTION = "Tools to change and administer password and group data."
-HOMEPAGE = "http://pkg-shadow.alioth.debian.org/"
-BUGTRACKER = "https://alioth.debian.org/tracker/?group_id=30580"
-SECTION = "base utils"
-LICENSE = "BSD | Artistic"
-LIC_FILES_CHKSUM = "file://COPYING;md5=08c553a87d4e51bbed50b20e0adcaede \
-                    file://src/passwd.c;firstline=8;endline=30;md5=2899a045e90511d0e043b85a7db7e2fe"
-
-PAM_PLUGINS = "  libpam-runtime \
-                 pam-plugin-faildelay \
-                 pam-plugin-securetty \
-                 pam-plugin-nologin \
-                 pam-plugin-env \
-                 pam-plugin-group \
-                 pam-plugin-limits \
-                 pam-plugin-lastlog \
-                 pam-plugin-motd \
-                 pam-plugin-mail \
-                 pam-plugin-shells \
-                 pam-plugin-rootok"
-                 
-DEPENDS = "${@base_contains('DISTRO_FEATURES', 'pam', 'libpam', '', d)}"
-RDEPENDS_${PN} = "${@base_contains('DISTRO_FEATURES', 'pam', '${PAM_PLUGINS}', '', d)}"
-
-# since we deduce from ${SERIAL_CONSOLE}
-PACKAGE_ARCH = "${MACHINE_ARCH}"
-
-# Additional Policy files for PAM
-PAM_SRC_URI = "file://pam.d/chfn \
-               file://pam.d/chpasswd \
-               file://pam.d/chsh \
-               file://pam.d/login \
-               file://pam.d/newusers \
-               file://pam.d/passwd \
-               file://pam.d/su"
-
-SRC_URI = "ftp://pkg-shadow.alioth.debian.org/pub/pkg-shadow/shadow-${PV}.tar.bz2 \
-           file://login_defs_pam.sed \
-           ${@base_contains('DISTRO_FEATURES', 'pam', '${PAM_SRC_URI}', '', d)} \
-           file://securetty"
-
-inherit autotools gettext
-
-EXTRA_OECONF += "--without-audit \
-                 --without-libcrack \
-                 ${@base_contains('DISTRO_FEATURES', 'pam', '--with-libpam', '--without-libpam', d)} \
-                 --without-selinux"
-
-do_install_append() {
-	# Ensure that the image has as /var/spool/mail dir so shadow can put mailboxes there if the user
-	# reconfigures Shadow to default (see sed below).
-	install -d ${D}${localstatedir}/spool/mail
-
-	if [ -e ${WORKDIR}/pam.d ]; then
-		install -d ${D}${sysconfdir}/pam.d/
-		install -m 0644 ${WORKDIR}/pam.d/* ${D}${sysconfdir}/pam.d/
-		# Remove defaults that are not used when supporting PAM
-		sed -i -f ${WORKDIR}/login_defs_pam.sed ${D}${sysconfdir}/login.defs
-	fi
-
-	# Enable CREATE_HOME by default.
-	sed -i 's/#CREATE_HOME/CREATE_HOME/g' ${D}${sysconfdir}/login.defs
-
-	# As we are on an embedded system ensure the users mailbox is in ~/ not
-	# /var/spool/mail by default as who knows where or how big /var is.
-	# The system MDA will set this later anyway.
-	sed -i 's/MAIL_DIR/#MAIL_DIR/g' ${D}${sysconfdir}/login.defs
-	sed -i 's/#MAIL_FILE/MAIL_FILE/g' ${D}${sysconfdir}/login.defs
-
-	# disable checking emails at all
-	sed -i 's/MAIL_CHECK_ENAB/#MAIL_CHECK_ENAB/g' ${D}${sysconfdir}/login.defs
-
-	# now we don't have a mail system. disable mail creation for now
-	sed -i 's:/bin/bash:/bin/sh:g' ${D}${sysconfdir}/default/useradd
-	sed -i '/^CREATE_MAIL_SPOOL/ s:^:#:' ${D}${sysconfdir}/default/useradd
-
-	install -d ${D}${sbindir} ${D}${base_sbindir} ${D}${base_bindir} 
-	for i in passwd chfn newgrp chsh ; do
-		mv ${D}${bindir}/$i ${D}${bindir}/$i.${PN}
-	done
-
-	mv ${D}${sbindir}/chpasswd ${D}${sbindir}/chpasswd.${PN}
-	mv ${D}${sbindir}/vigr ${D}${base_sbindir}/vigr.${PN}
-	mv ${D}${sbindir}/vipw ${D}${base_sbindir}/vipw.${PN}
-	mv ${D}${bindir}/login ${D}${base_bindir}/login.${PN}
-
-	# Ensure we add a suitable securetty file to the package that has most common embedded TTYs defined.
-	if [ ! -z "${SERIAL_CONSOLE}" ]; then
-	# our SERIAL_CONSOLE contains baud rate too and sometime -L option as well.
-	# the following pearl :) takes that and converts it into newline sepated tty's and appends
-	# them into securetty. So if a machine has a weird looking console device node (e.g. ttyAMA0) that securetty
-	# does not know then it will get appended to securetty and root login will be allowed on
-	# that console.
-		echo "${SERIAL_CONSOLE}" | sed -e 's/[0-9][0-9]\|\-L//g'|tr "[ ]" "[\n]"  >> ${WORKDIR}/securetty
-	fi
-	install -m 0400 ${WORKDIR}/securetty ${D}${sysconfdir}/securetty 
-}
-
-pkg_postinst_${PN} () {
-	update-alternatives --install ${bindir}/passwd passwd passwd.${PN} 200
-	update-alternatives --install ${sbindir}/chpasswd chpasswd chpasswd.${PN} 200
-	update-alternatives --install ${bindir}/chfn chfn chfn.${PN} 200
-	update-alternatives --install ${bindir}/newgrp newgrp newgrp.${PN} 200
-	update-alternatives --install ${bindir}/chsh chsh chsh.${PN} 200
-	update-alternatives --install ${base_bindir}/login login login.${PN} 200
-	update-alternatives --install ${base_sbindir}/vipw vipw vipw.${PN} 200
-	update-alternatives --install ${base_sbindir}/vigr vigr vigr.${PN} 200
-
-	if [ "x$D" != "x" ]; then
-		exit 1
-	fi  
-
-	pwconv
-	grpconv
-}
-
-pkg_prerm_${PN} () {
-	for i in passwd chpasswd chfn newgrp chsh login vipw vigr ; do
-		update-alternatives --remove $i $i.${PN}
-	done
-}
diff --git a/meta/recipes-extended/shadow/shadow_4.1.4.3.bb b/meta/recipes-extended/shadow/shadow_4.1.4.3.bb
index c8aa223..25b7bca 100644
--- a/meta/recipes-extended/shadow/shadow_4.1.4.3.bb
+++ b/meta/recipes-extended/shadow/shadow_4.1.4.3.bb
@@ -1,14 +1,137 @@
-require shadow.inc
+SUMMARY = "Tools to change and administer password and group data"
+DESCRIPTION = "Tools to change and administer password and group data"
+HOMEPAGE = "http://pkg-shadow.alioth.debian.org"
+BUGTRACKER = "https://alioth.debian.org/tracker/?group_id=30580"
+SECTION = "base utils"
+PRIORITY = "optional"
+LICENSE = "BSD | Artistic"
+LIC_FILES_CHKSUM = "file://COPYING;md5=08c553a87d4e51bbed50b20e0adcaede \
+                    file://src/passwd.c;firstline=8;endline=30;md5=2899a045e90511d0e043b85a7db7e2fe"
 
-PR = "r1"
+DEPENDS = "${@base_contains('DISTRO_FEATURES', 'pam', 'libpam', '', d)}"
+RDEPENDS_${PN} = "${@base_contains('DISTRO_FEATURES', 'pam', '${PAM_PLUGINS}', '', d)}"
+PR = "r2"
 
-SRC_URI += "file://shadow.automake-1.11.patch \
-	    file://shadow-4.1.3-dots-in-usernames.patch \
-	    file://shadow-4.1.4.2-env-reset-keep-locale.patch \
-	    file://shadow-4.1.4.2-groupmod-pam-check.patch \
-	    file://shadow-4.1.4.2-su_no_sanitize_env.patch"
+SRC_URI = "ftp://pkg-shadow.alioth.debian.org/pub/pkg-shadow/shadow-${PV}.tar.bz2 \
+           file://login_defs_pam.sed \
+           ${@base_contains('DISTRO_FEATURES', 'pam', '${PAM_SRC_URI}', '', d)} \
+           file://securetty \
+           file://shadow.automake-1.11.patch \
+           file://shadow-4.1.3-dots-in-usernames.patch \
+           file://shadow-4.1.4.2-env-reset-keep-locale.patch \
+           file://shadow-4.1.4.2-groupmod-pam-check.patch \
+           file://shadow-4.1.4.2-su_no_sanitize_env.patch"
 
 SRC_URI[md5sum] = "b8608d8294ac88974f27b20f991c0e79"
-SRC_URI[sha256sum] = "633f5bb4ea0c88c55f3642c97f9d25cbef74f82e0b4cf8d54e7ad6f9f9caa778"
+SRC_URI[sha256sum] = "633f5bb4ea0c88c55f3642c97f9d25cbef74f82e0b4cf8d54e7ad6f9f9caa778" 
 
-EXTRA_OECONF_libc-uclibc += " --with-nscd=no "
+inherit autotools gettext
+
+# Since we deduce our arch from ${SERIAL_CONSOLE}
+PACKAGE_ARCH = "${MACHINE_ARCH}"
+
+EXTRA_OECONF += "--without-audit \
+                 --without-libcrack \
+                 ${@base_contains('DISTRO_FEATURES', 'pam', '--with-libpam', '--without-libpam', d)} \
+                 --without-selinux"
+EXTRA_OECONF_libc-uclibc += "--with-nscd=no"
+
+PAM_PLUGINS = "libpam-runtime \
+               pam-plugin-faildelay \
+               pam-plugin-securetty \
+               pam-plugin-nologin \
+               pam-plugin-env \
+               pam-plugin-group \
+               pam-plugin-limits \
+               pam-plugin-lastlog \
+               pam-plugin-motd \
+               pam-plugin-mail \
+               pam-plugin-shells \
+               pam-plugin-rootok"
+                 
+# Additional Policy files for PAM
+PAM_SRC_URI = "file://pam.d/chfn \
+               file://pam.d/chpasswd \
+               file://pam.d/chsh \
+               file://pam.d/login \
+               file://pam.d/newusers \
+               file://pam.d/passwd \
+               file://pam.d/su"
+
+do_install_append() {
+	# Ensure that the image has as a /var/spool/mail dir so shadow can
+	# put mailboxes there if the user reconfigures shadow to its
+	# defaults (see sed below).
+	install -d ${D}${localstatedir}/spool/mail
+
+	if [ -e ${WORKDIR}/pam.d ]; then
+		install -d ${D}${sysconfdir}/pam.d/
+		install -m 0644 ${WORKDIR}/pam.d/* ${D}${sysconfdir}/pam.d/
+		# Remove defaults that are not used when supporting PAM.
+		sed -i -f ${WORKDIR}/login_defs_pam.sed ${D}${sysconfdir}/login.defs
+	fi
+
+	# Enable CREATE_HOME by default.
+	sed -i 's/#CREATE_HOME/CREATE_HOME/g' ${D}${sysconfdir}/login.defs
+
+	# As we are on an embedded system, ensure the users mailbox is in
+	# ~/ not /var/spool/mail by default, as who knows where or how big
+	# /var is. The system MDA will set this later anyway.
+	sed -i 's/MAIL_DIR/#MAIL_DIR/g' ${D}${sysconfdir}/login.defs
+	sed -i 's/#MAIL_FILE/MAIL_FILE/g' ${D}${sysconfdir}/login.defs
+
+	# Disable checking emails.
+	sed -i 's/MAIL_CHECK_ENAB/#MAIL_CHECK_ENAB/g' ${D}${sysconfdir}/login.defs
+
+	# Now we don't have a mail system. Disable mail creation for now.
+	sed -i 's:/bin/bash:/bin/sh:g' ${D}${sysconfdir}/default/useradd
+	sed -i '/^CREATE_MAIL_SPOOL/ s:^:#:' ${D}${sysconfdir}/default/useradd
+
+	install -d ${D}${sbindir} ${D}${base_sbindir} ${D}${base_bindir} 
+	for i in passwd chfn newgrp chsh ; do
+		mv ${D}${bindir}/$i ${D}${bindir}/$i.${PN}
+	done
+
+	mv ${D}${sbindir}/chpasswd ${D}${sbindir}/chpasswd.${PN}
+	mv ${D}${sbindir}/vigr ${D}${base_sbindir}/vigr.${PN}
+	mv ${D}${sbindir}/vipw ${D}${base_sbindir}/vipw.${PN}
+	mv ${D}${bindir}/login ${D}${base_bindir}/login.${PN}
+
+	# Ensure we add a suitable securetty file to the package that has
+	# most common embedded TTYs defined.
+	if [ ! -z "${SERIAL_CONSOLE}" ]; then
+		# Our SERIAL_CONSOLE contains a baud rate and sometimes a -L
+		# option as well. The following pearl :) takes that and converts
+		# it into newline-separated tty's and appends them into
+		# securetty. So if a machine has a weird looking console device
+		# node (e.g. ttyAMA0) that securetty does not know, it will get
+		# appended to securetty and root logins will be allowed on that
+		# console.
+		echo "${SERIAL_CONSOLE}" | sed -e 's/[0-9][0-9]\|\-L//g'|tr "[ ]" "[\n]"  >> ${WORKDIR}/securetty
+	fi
+	install -m 0400 ${WORKDIR}/securetty ${D}${sysconfdir}/securetty 
+}
+
+pkg_postinst_${PN} () {
+	update-alternatives --install ${bindir}/passwd passwd passwd.${PN} 200
+	update-alternatives --install ${sbindir}/chpasswd chpasswd chpasswd.${PN} 200
+	update-alternatives --install ${bindir}/chfn chfn chfn.${PN} 200
+	update-alternatives --install ${bindir}/newgrp newgrp newgrp.${PN} 200
+	update-alternatives --install ${bindir}/chsh chsh chsh.${PN} 200
+	update-alternatives --install ${base_bindir}/login login login.${PN} 200
+	update-alternatives --install ${base_sbindir}/vipw vipw vipw.${PN} 200
+	update-alternatives --install ${base_sbindir}/vigr vigr vigr.${PN} 200
+
+	if [ "x$D" != "x" ]; then
+		exit 1
+	fi  
+
+	pwconv
+	grpconv
+}
+
+pkg_prerm_${PN} () {
+	for i in passwd chpasswd chfn newgrp chsh login vipw vigr ; do
+		update-alternatives --remove $i $i.${PN}
+	done
+}
-- 
1.7.1



^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-05-31 19:53 ` Scott Garman
@ 2011-05-31 19:53   ` Scott Garman
  -1 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 18:13 UTC (permalink / raw)
  To: poky

This adds a -native recipe for the shadow utilities.

The custom --root option allows the the following utilities to be
run within a chroot when invoked under pseudo:

* useradd
* groupadd
* usermod
* groupmod
* userdel
* groupdel
* passwd
* gpasswd
* pwconv
* pwunconv
* grpconv
* grpunconv

They can then be used to manipulate user and group account information
in target sysroots.

useradd was also modified to create home directories recursively when
necessary.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 .../shadow/files/add_root_cmd_options.patch        | 1293 ++++++++++++++++++++
 .../shadow/shadow-native_4.1.4.3.bb                |   66 +
 2 files changed, 1359 insertions(+), 0 deletions(-)
 create mode 100644 meta/recipes-extended/shadow/files/add_root_cmd_options.patch
 create mode 100644 meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb

diff --git a/meta/recipes-extended/shadow/files/add_root_cmd_options.patch b/meta/recipes-extended/shadow/files/add_root_cmd_options.patch
new file mode 100644
index 0000000..3511ebb
--- /dev/null
+++ b/meta/recipes-extended/shadow/files/add_root_cmd_options.patch
@@ -0,0 +1,1293 @@
+Add a --root command option to the following utilties:
+
+* useradd
+* groupadd
+* usermod
+* groupmod
+* userdel
+* groupdel
+* passwd
+* gpasswd
+* pwconv
+* pwunconv
+* grpconv
+* grpunconv
+
+This option allows the utilities to be chrooted when run under pseudo.
+They can then be used to manipulate user and group account information
+in target sysroots.
+
+Upstream-Status: Inappropriate [Other]
+Workaround is specific to our build system.
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
+diff -urN shadow-4.1.4.3.orig//src/gpasswd.c shadow-4.1.4.3//src/gpasswd.c
+--- shadow-4.1.4.3.orig//src/gpasswd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/gpasswd.c	2011-05-28 17:09:52.346013331 -0700
+@@ -63,6 +63,7 @@
+  * (/etc/gshadow present) */
+ static bool is_shadowgrp;
+ #endif
++static const char *newroot = "";
+ 
+ /* Flags set by options */
+ static bool aflg = false;
+@@ -97,6 +98,7 @@
+ static void usage (void);
+ static RETSIGTYPE catch_signals (int killed);
+ static bool is_valid_user_list (const char *users);
++static void process_root_flag (int argc, char **argv);
+ static void process_flags (int argc, char **argv);
+ static void check_flags (int argc, int opt_index);
+ static void open_files (void);
+@@ -136,6 +138,7 @@
+ 	           "Options:\n"
+ 	           "  -a, --add USER                add USER to GROUP\n"
+ 	           "  -d, --delete USER             remove USER from GROUP\n"
++	           "  -Q  --root CHROOT_DIR         directory to chroot into\n"
+ 	           "  -r, --remove-password         remove the GROUP's password\n"
+ 	           "  -R, --restrict                restrict access to GROUP to its members\n"
+ 	           "  -M, --members USER,...        set the list of members of GROUP\n"
+@@ -226,6 +229,55 @@
+ }
+ 
+ /*
++ * process_root_flag - chroot if given the --root option
++ *
++ * We do this outside of process_flags() because
++ * the is_shadow_pwd boolean needs to be set before
++ * process_flags(), and if we do need to chroot() we
++ * must do so before is_shadow_pwd gets set.
++ */
++static void process_root_flag (int argc, char **argv)
++{
++	/*
++	 * Parse the command line options.
++	 */
++	int flag;
++	int option_index = 0;
++	static struct option long_options[] = {
++		{"root", required_argument, NULL, 'Q'},
++		{NULL, 0, NULL, '\0'}
++	};
++
++	while ((flag = getopt_long (argc, argv, "a:A:d:gM:Q:rR", long_options, &option_index)) != -1) {
++		switch (flag) {
++		case 'Q':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
++		/* no-op on everything else - they will be hanled by process_flags() */
++		}
++	}
++}
++
++/*
+  * process_flags - process the command line options and arguments
+  */
+ static void process_flags (int argc, char **argv)
+@@ -235,6 +287,7 @@
+ 	static struct option long_options[] = {
+ 		{"add", required_argument, NULL, 'a'},
+ 		{"delete", required_argument, NULL, 'd'},
++		{"root", required_argument, NULL, 'Q'},
+ 		{"remove-password", no_argument, NULL, 'r'},
+ 		{"restrict", no_argument, NULL, 'R'},
+ 		{"administrators", required_argument, NULL, 'A'},
+@@ -242,7 +295,7 @@
+ 		{NULL, 0, NULL, '\0'}
+ 		};
+ 
+-	while ((flag = getopt_long (argc, argv, "a:A:d:gM:rR", long_options, &option_index)) != -1) {
++	while ((flag = getopt_long (argc, argv, "a:A:d:gM:Q:rR", long_options, &option_index)) != -1) {
+ 		switch (flag) {
+ 		case 'a':	/* add a user */
+ 			aflg = true;
+@@ -283,6 +336,9 @@
+ 			}
+ 			Mflg = true;
+ 			break;
++		case 'Q':
++			/* no-op since we handled this in process_root_flag() earlier */
++			break;
+ 		case 'r':	/* remove group password */
+ 			rflg = true;
+ 			break;
+@@ -995,6 +1051,8 @@
+ 	setbuf (stdout, NULL);
+ 	setbuf (stderr, NULL);
+ 
++	process_root_flag (argc, argv);
++
+ #ifdef SHADOWGRP
+ 	is_shadowgrp = sgr_file_present ();
+ #endif
+diff -urN shadow-4.1.4.3.orig//src/groupadd.c shadow-4.1.4.3//src/groupadd.c
+--- shadow-4.1.4.3.orig//src/groupadd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/groupadd.c	2011-05-28 17:09:52.346013331 -0700
+@@ -76,6 +76,7 @@
+ static gid_t group_id;
+ static /*@null@*/char *group_passwd;
+ static /*@null@*/char *empty_list = NULL;
++static const char *newroot = "";
+ 
+ static bool oflg = false;	/* permit non-unique group ID to be specified with -g */
+ static bool gflg = false;	/* ID value for the new group */
+@@ -120,6 +121,7 @@
+ 	(void) fputs (_("  -o, --non-unique              allow to create groups with duplicate\n"
+ 	                "                                (non-unique) GID\n"), stderr);
+ 	(void) fputs (_("  -p, --password PASSWORD       use this encrypted password for the new group\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
+ 	(void) fputs (_("  -r, --system                  create a system account\n"), stderr);
+ 	(void) fputs ("\n", stderr);
+ 	exit (E_USAGE);
+@@ -383,12 +385,13 @@
+ 		{"key", required_argument, NULL, 'K'},
+ 		{"non-unique", no_argument, NULL, 'o'},
+ 		{"password", required_argument, NULL, 'p'},
++		{"root", required_argument, NULL, 'R'},
+ 		{"system", no_argument, NULL, 'r'},
+ 		{NULL, 0, NULL, '\0'}
+ 	};
+ 
+ 	while ((c =
+-		getopt_long (argc, argv, "fg:hK:op:r", long_options,
++		getopt_long (argc, argv, "fg:hK:op:R:r", long_options,
+ 		             &option_index)) != -1) {
+ 		switch (c) {
+ 		case 'f':
+@@ -440,6 +443,28 @@
+ 			pflg = true;
+ 			group_passwd = optarg;
+ 			break;
++		case 'R':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
+ 		case 'r':
+ 			rflg = true;
+ 			break;
+diff -urN shadow-4.1.4.3.orig//src/groupdel.c shadow-4.1.4.3//src/groupdel.c
+--- shadow-4.1.4.3.orig//src/groupdel.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/groupdel.c	2011-05-28 17:09:52.346013331 -0700
+@@ -36,6 +36,7 @@
+ 
+ #include <ctype.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <grp.h>
+ #include <pwd.h>
+ #ifdef ACCT_TOOLS_SETUID
+@@ -59,6 +60,7 @@
+ 
+ static char *group_name;
+ static gid_t group_id = -1;
++static const char *newroot = "";
+ 
+ #ifdef	SHADOWGRP
+ static bool is_shadow_grp;
+@@ -70,12 +72,14 @@
+ /*@-exitarg@*/
+ #define E_SUCCESS	0	/* success */
+ #define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
+ #define E_NOTFOUND	6	/* specified group doesn't exist */
+ #define E_GROUP_BUSY	8	/* can't remove user's primary group */
+ #define E_GRP_UPDATE	10	/* can't update group file */
+ 
+ /* local function prototypes */
+ static void usage (void);
++static void process_flags (int argc, char **argv);
+ static void grp_update (void);
+ static void close_files (void);
+ static void open_files (void);
+@@ -86,11 +90,78 @@
+  */
+ static void usage (void)
+ {
+-	fputs (_("Usage: groupdel group\n"), stderr);
++	(void) fprintf (stderr,
++					_("Usage: groupdel [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -g, --group GROUP            group name to delete\n"), stderr);
++	(void) fputs (_("  -h, --help                   display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR        directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
+ 	exit (E_USAGE);
+ }
+ 
+ /*
++ * process_flags - perform command line argument setting
++ *
++ *	process_flags() interprets the command line arguments and sets
++ *	the values that the user will be created with accordingly. The
++ *	values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"group", required_argument, NULL, 'g'},
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "g:R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'g':
++				group_name = optarg;
++				break;
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++							_("%s: invalid chroot path '%s'\n"),
++							Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++							_("%s: chroot directory %s does not exist\n"),
++							Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++							_("%s: unable to chroot to directory %s\n"),
++							Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
++/*
+  * grp_update - update group file entries
+  *
+  *	grp_update() writes the new records to the group files.
+@@ -328,14 +399,14 @@
+ 	(void) bindtextdomain (PACKAGE, LOCALEDIR);
+ 	(void) textdomain (PACKAGE);
+ 
+-	if (argc != 2) {
++   if (argc == 1) {
+ 		usage ();
+ 	}
+ 
+-	group_name = argv[1];
+-
+ 	OPENLOG ("groupdel");
+ 
++	process_flags (argc, argv);
++
+ #ifdef ACCT_TOOLS_SETUID
+ #ifdef USE_PAM
+ 	{
+diff -urN shadow-4.1.4.3.orig//src/groupmod.c shadow-4.1.4.3//src/groupmod.c
+--- shadow-4.1.4.3.orig//src/groupmod.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/groupmod.c	2011-05-28 17:09:52.346013331 -0700
+@@ -79,6 +79,7 @@
+ static char *group_passwd;
+ static gid_t group_id;
+ static gid_t group_newid;
++static char *newroot = "";
+ 
+ struct cleanup_info_mod info_passwd;
+ struct cleanup_info_mod info_group;
+@@ -126,6 +127,7 @@
+ 	(void) fputs (_("  -o, --non-unique              allow to use a duplicate (non-unique) GID\n"), stderr);
+ 	(void) fputs (_("  -p, --password PASSWORD       change the password to this (encrypted)\n"
+ 	                "                                PASSWORD\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
+ 	(void) fputs ("\n", stderr);
+ 	exit (E_USAGE);
+ }
+@@ -346,10 +348,11 @@
+ 		{"new-name", required_argument, NULL, 'n'},
+ 		{"non-unique", no_argument, NULL, 'o'},
+ 		{"password", required_argument, NULL, 'p'},
++		{"root", required_argument, NULL, 'R'},
+ 		{NULL, 0, NULL, '\0'}
+ 	};
+ 	while ((c =
+-		getopt_long (argc, argv, "g:hn:op:",
++		getopt_long (argc, argv, "g:hn:op:R:",
+ 		             long_options, &option_index)) != -1) {
+ 		switch (c) {
+ 		case 'g':
+@@ -373,6 +376,28 @@
+ 			group_passwd = optarg;
+ 			pflg = true;
+ 			break;
++		case 'R':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
+ 		default:
+ 			usage ();
+ 		}
+diff -urN shadow-4.1.4.3.orig//src/grpconv.c shadow-4.1.4.3//src/grpconv.c
+--- shadow-4.1.4.3.orig//src/grpconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/grpconv.c	2011-05-28 17:09:52.346013331 -0700
+@@ -39,6 +39,7 @@
+ 
+ #include <errno.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <grp.h>
+ #include <stdio.h>
+ #include <stdlib.h>
+@@ -50,6 +51,14 @@
+ #ifdef SHADOWGRP
+ #include "groupio.h"
+ #include "sgroupio.h"
++
++/*
++ * exit status values
++ */
++/*@-exitarg@*/
++#define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
++
+ /*
+  * Global variables
+  */
+@@ -57,9 +66,12 @@
+ 
+ static bool gr_locked  = false;
+ static bool sgr_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -82,6 +94,77 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: grpconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ *	process_flags() interprets the command line arguments and sets
++ *	the values that the user will be created with accordingly. The
++ *	values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
+ int main (int argc, char **argv)
+ {
+ 	const struct group *gr;
+@@ -100,6 +183,8 @@
+ 
+ 	OPENLOG ("grpconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (gr_lock () == 0) {
+ 		fprintf (stderr,
+ 		         _("%s: cannot lock %s; try again later.\n"),
+diff -urN shadow-4.1.4.3.orig//src/grpunconv.c shadow-4.1.4.3//src/grpunconv.c
+--- shadow-4.1.4.3.orig//src/grpunconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/grpunconv.c	2011-05-28 17:09:52.346013331 -0700
+@@ -43,6 +43,7 @@
+ #include <stdlib.h>
+ #include <string.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <time.h>
+ #include <unistd.h>
+ #include <grp.h>
+@@ -51,6 +52,14 @@
+ #ifdef SHADOWGRP
+ #include "groupio.h"
+ #include "sgroupio.h"
++
++/*
++ * exit status values
++ */
++/*@-exitarg@*/
++#define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
++
+ /*
+  * Global variables
+  */
+@@ -58,9 +67,12 @@
+ 
+ static bool gr_locked  = false;
+ static bool sgr_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -83,6 +95,77 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: grpunconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ * process_flags() interprets the command line arguments and sets
++ * the values that the user will be created with accordingly. The
++ * values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
+ int main (int argc, char **argv)
+ {
+ 	const struct group *gr;
+@@ -100,6 +183,8 @@
+ 
+ 	OPENLOG ("grpunconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (sgr_file_present () == 0) {
+ 		exit (0);	/* no /etc/gshadow, nothing to do */
+ 	}
+diff -urN shadow-4.1.4.3.orig//src/passwd.c shadow-4.1.4.3//src/passwd.c
+--- shadow-4.1.4.3.orig//src/passwd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/passwd.c	2011-05-28 17:09:52.346013331 -0700
+@@ -75,6 +75,7 @@
+ static char *name;		/* The name of user whose password is being changed */
+ static char *myname;		/* The current user's name */
+ static bool amroot;		/* The caller's real UID was 0 */
++static const char *newroot = "";
+ 
+ static bool
+     aflg = false,			/* -a - show status for all users */
+@@ -174,6 +175,7 @@
+ 	         "  -n, --mindays MIN_DAYS        set minimum number of days before password\n"
+ 	         "                                change to MIN_DAYS\n"
+ 	         "  -q, --quiet                   quiet mode\n"
++	         "  -R, --root CHROOT_DIR         directory to chroot into\n"
+ 	         "  -r, --repository REPOSITORY   change password in REPOSITORY repository\n"
+ 	         "  -S, --status                  report password status on the named account\n"
+ 	         "  -u, --unlock                  unlock the password of the named account\n"
+@@ -803,6 +805,7 @@
+ 			{"lock", no_argument, NULL, 'l'},
+ 			{"mindays", required_argument, NULL, 'n'},
+ 			{"quiet", no_argument, NULL, 'q'},
++			{"root", required_argument, NULL, 'R'},
+ 			{"repository", required_argument, NULL, 'r'},
+ 			{"status", no_argument, NULL, 'S'},
+ 			{"unlock", no_argument, NULL, 'u'},
+@@ -811,7 +814,7 @@
+ 			{NULL, 0, NULL, '\0'}
+ 		};
+ 
+-		while ((c = getopt_long (argc, argv, "adei:kln:qr:Suw:x:",
++		while ((c = getopt_long (argc, argv, "adei:kln:qR:r:Suw:x:",
+ 		                         long_options, &option_index)) != -1) {
+ 			switch (c) {
+ 			case 'a':
+@@ -858,6 +861,28 @@
+ 			case 'q':
+ 				qflg = true;	/* ok for users */
+ 				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++				            _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
+ 			case 'r':
+ 				/* -r repository (files|nis|nisplus) */
+ 				/* only "files" supported for now */
+diff -urN shadow-4.1.4.3.orig//src/pwconv.c shadow-4.1.4.3//src/pwconv.c
+--- shadow-4.1.4.3.orig//src/pwconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/pwconv.c	2011-05-28 17:09:52.346013331 -0700
+@@ -59,6 +59,7 @@
+ 
+ #include <errno.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <pwd.h>
+ #include <stdio.h>
+ #include <stdlib.h>
+@@ -79,6 +80,7 @@
+ #define E_SUCCESS	0	/* success */
+ #define E_NOPERM	1	/* permission denied */
+ #define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
+ #define E_FAILURE	3	/* unexpected failure, nothing done */
+ #define E_MISSING	4	/* unexpected failure, passwd file missing */
+ #define E_PWDBUSY	5	/* passwd file(s) busy */
+@@ -90,9 +92,12 @@
+ 
+ static bool spw_locked = false;
+ static bool pw_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -115,6 +120,77 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: pwconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ *	process_flags() interprets the command line arguments and sets
++ *	the values that the user will be created with accordingly. The
++ *	values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
+ int main (int argc, char **argv)
+ {
+ 	const struct passwd *pw;
+@@ -122,9 +198,6 @@
+ 	const struct spwd *sp;
+ 	struct spwd spent;
+ 
+-	if (1 != argc) {
+-		(void) fputs (_("Usage: pwconv\n"), stderr);
+-	}
+ 	Prog = Basename (argv[0]);
+ 
+ 	(void) setlocale (LC_ALL, "");
+@@ -133,6 +206,8 @@
+ 
+ 	OPENLOG ("pwconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (pw_lock () == 0) {
+ 		fprintf (stderr,
+ 		         _("%s: cannot lock %s; try again later.\n"),
+diff -urN shadow-4.1.4.3.orig//src/pwunconv.c shadow-4.1.4.3//src/pwunconv.c
+--- shadow-4.1.4.3.orig//src/pwunconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/pwunconv.c	2011-05-28 17:09:52.356013600 -0700
+@@ -35,6 +35,7 @@
+ #ident "$Id: pwunconv.c 2852 2009-04-30 21:44:35Z nekral-guest $"
+ 
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <pwd.h>
+ #include <stdio.h>
+ #include <sys/types.h>
+@@ -46,15 +47,24 @@
+ #include "shadowio.h"
+ 
+ /*
++ * exit status values
++ */
++/*@-exitarg@*/
++#define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
++/*
+  * Global variables
+  */
+ char *Prog;
+ 
+ static bool spw_locked = false;
+ static bool pw_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -75,6 +85,76 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: pwunconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ * process_flags() interprets the command line arguments and sets
++ * the values that the user will be created with accordingly. The
++ * values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
+ 
+ int main (int argc, char **argv)
+ {
+@@ -93,6 +173,8 @@
+ 
+ 	OPENLOG ("pwunconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (!spw_file_present ()) {
+ 		/* shadow not installed, do nothing */
+ 		exit (0);
+diff -urN shadow-4.1.4.3.orig//src/useradd.c shadow-4.1.4.3//src/useradd.c
+--- shadow-4.1.4.3.orig//src/useradd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/useradd.c	2011-05-28 17:10:25.446909971 -0700
+@@ -112,6 +112,7 @@
+ #ifdef WITH_SELINUX
+ static const char *user_selinux = "";
+ #endif
++static const char *newroot = "";
+ 
+ static long user_expire = -1;
+ static bool is_shadow_pwd;
+@@ -189,6 +190,7 @@
+ static void new_spent (struct spwd *);
+ static void grp_update (void);
+ 
++static void process_root_flag (int argc, char **argv);
+ static void process_flags (int argc, char **argv);
+ static void close_files (void);
+ static void open_files (void);
+@@ -711,6 +713,7 @@
+ 	(void) fputs (_("  -o, --non-unique              allow to create users with duplicate\n"
+ 	                "                                (non-unique) UID\n"), stderr);
+ 	(void) fputs (_("  -p, --password PASSWORD       encrypted password of the new account\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
+ 	(void) fputs (_("  -r, --system                  create a system account\n"), stderr);
+ 	(void) fputs (_("  -s, --shell SHELL             login shell of the new account\n"), stderr);
+ 	(void) fputs (_("  -u, --uid UID                 user ID of the new account\n"), stderr);
+@@ -943,6 +946,59 @@
+ }
+ 
+ /*
++ * process_root_flag - chroot if given the --root option
++ *
++ * We do this outside of process_flags() because
++ * the is_shadow_pwd boolean needs to be set before
++ * process_flags(), and if we do need to chroot() we
++ * must do so before is_shadow_pwd gets set.
++ */
++static void process_root_flag (int argc, char **argv)
++{
++	/*
++	 * Parse the command line options.
++	 */
++	int c;
++	static struct option long_options[] = {
++		{"root", required_argument, NULL, 'R'},
++		{NULL, 0, NULL, '\0'}
++	};
++	while ((c = getopt_long (argc, argv,
++#ifdef WITH_SELINUX
++	                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:UZ:",
++#else
++	                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:U",
++#endif
++	                         long_options, NULL)) != -1) {
++		switch (c) {
++		case 'R':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
++		/* no-op on everything else - they will be hanled by process_flags() */
++		}
++	}
++}
++
++/*
+  * process_flags - perform command line argument setting
+  *
+  *	process_flags() interprets the command line arguments and sets
+@@ -978,6 +1034,7 @@
+ 			{"no-user-group", no_argument, NULL, 'N'},
+ 			{"non-unique", no_argument, NULL, 'o'},
+ 			{"password", required_argument, NULL, 'p'},
++			{"root", required_argument, NULL, 'R'},
+ 			{"system", no_argument, NULL, 'r'},
+ 			{"shell", required_argument, NULL, 's'},
+ #ifdef WITH_SELINUX
+@@ -989,9 +1046,9 @@
+ 		};
+ 		while ((c = getopt_long (argc, argv,
+ #ifdef WITH_SELINUX
+-		                         "b:c:d:De:f:g:G:k:K:lmMNop:rs:u:UZ:",
++		                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:UZ:",
+ #else
+-		                         "b:c:d:De:f:g:G:k:K:lmMNop:rs:u:U",
++		                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:U",
+ #endif
+ 		                         long_options, NULL)) != -1) {
+ 			switch (c) {
+@@ -1156,6 +1213,9 @@
+ 				}
+ 				user_pass = optarg;
+ 				break;
++			case 'R':
++				/* no-op since we handled this in process_root_flag() earlier */
++				break;
+ 			case 'r':
+ 				rflg = true;
+ 				break;
+@@ -1748,8 +1808,16 @@
+ #ifdef WITH_SELINUX
+ 		selinux_file_context (user_home);
+ #endif
+-		/* XXX - create missing parent directories.  --marekm */
+-		if (mkdir (user_home, 0) != 0) {
++		/* shell out to invoke mkdir -p 
++		 * creating a subshell under pseudo's chroot() breaks the jail
++		 * (bug in pseudo), so make sure we include the full host path
++		 * to the sysroot when the --root option is in use.
++		 */
++		int sysroot_path_len = strlen(newroot);
++		int home_path_len = strlen(user_home);
++		char cmd[sysroot_path_len + home_path_len + 10];
++		sprintf(cmd, "mkdir -p %s%s", newroot, user_home);
++		if (system (cmd) != 0) {
+ 			fprintf (stderr,
+ 			         _("%s: cannot create directory %s\n"),
+ 			         Prog, user_home);
+@@ -1861,6 +1929,7 @@
+ 	 */
+ 	user_groups[0] = (char *) 0;
+ 
++	process_root_flag (argc, argv);
+ 
+ 	is_shadow_pwd = spw_file_present ();
+ #ifdef SHADOWGRP
+diff -urN shadow-4.1.4.3.orig//src/userdel.c shadow-4.1.4.3//src/userdel.c
+--- shadow-4.1.4.3.orig//src/userdel.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/userdel.c	2011-05-28 17:09:52.356013600 -0700
+@@ -79,6 +79,7 @@
+ static char *user_name;
+ static uid_t user_id;
+ static char *user_home;
++static const char *newroot = "";
+ 
+ static bool fflg = false;
+ static bool rflg = false;
+@@ -119,6 +120,7 @@
+ 	         "  -f, --force                   force removal of files,\n"
+ 	         "                                even if not owned by user\n"
+ 	         "  -h, --help                    display this help message and exit\n"
++	         "  -R, --root CHROOT_DIR         directory to chroot into\n"
+ 	         "  -r, --remove                  remove home directory and mail spool\n"
+ 	         "\n"), stderr);
+ 	exit (E_USAGE);
+@@ -768,12 +770,34 @@
+ 			{"remove", no_argument, NULL, 'r'},
+ 			{NULL, 0, NULL, '\0'}
+ 		};
+-		while ((c = getopt_long (argc, argv, "fhr",
++		while ((c = getopt_long (argc, argv, "fhR:r",
+ 		                         long_options, NULL)) != -1) {
+ 			switch (c) {
+ 			case 'f':	/* force remove even if not owned by user */
+ 				fflg = true;
+ 				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
+ 			case 'r':	/* remove home dir and mailbox */
+ 				rflg = true;
+ 				break;
+diff -urN shadow-4.1.4.3.orig//src/usermod.c shadow-4.1.4.3//src/usermod.c
+--- shadow-4.1.4.3.orig//src/usermod.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/usermod.c	2011-05-28 17:09:52.356013600 -0700
+@@ -110,6 +110,7 @@
+ static long user_newinactive;
+ static long sys_ngroups;
+ static char **user_groups;	/* NULL-terminated list */
++static const char *newroot = "";
+ 
+ static bool
+     aflg = false,		/* append to existing secondary group set */
+@@ -164,6 +165,7 @@
+ #endif
+ static void grp_update (void);
+ 
++static void process_root_flag (int, char **);
+ static void process_flags (int, char **);
+ static void close_files (void);
+ static void open_files (void);
+@@ -323,6 +325,7 @@
+ 	         "                                new location (use only with -d)\n"
+ 	         "  -o, --non-unique              allow using duplicate (non-unique) UID\n"
+ 	         "  -p, --password PASSWORD       use encrypted password for the new password\n"
++	         "  -R  --root CHROOT_DIR         directory to chroot into\n"
+ 	         "  -s, --shell SHELL             new login shell for the user account\n"
+ 	         "  -u, --uid UID                 new UID for the user account\n"
+ 	         "  -U, --unlock                  unlock the user account\n"
+@@ -802,6 +805,60 @@
+ }
+ 
+ /*
++ * process_root_flag - chroot if given the --root option
++ *
++ * We do this outside of process_flags() because
++ * the is_shadow_pwd boolean needs to be set before
++ * process_flags(), and if we do need to chroot() we
++ * must do so before is_shadow_pwd gets set.
++ */
++static void process_root_flag (int argc, char **argv)
++{
++	/*
++	 * Parse the command line options.
++	 */
++	int c;
++	static struct option long_options[] = {
++		{"root", required_argument, NULL, 'R'},
++		{NULL, 0, NULL, '\0'}
++	};
++	while ((c = getopt_long (argc, argv,
++#ifdef WITH_SELINUX
++                             "ac:d:e:f:g:G:hl:Lmop:R:s:u:UZ:",
++#else
++	                         "ac:d:e:f:g:G:hl:Lmop:R:s:u:U",
++#endif
++	                         long_options, NULL)) != -1) {
++		switch (c) {
++		case 'R':
++			if (    (!VALID (optarg) ) 
++				|| (   ('/' != optarg[0]) ) ) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
++		/* no-op on everything else - they will be hanled by process_flags() */
++		}
++	}
++}
++
++/*
+  * process_flags - perform command line argument setting
+  *
+  *	process_flags() interprets the command line arguments and sets the
+@@ -895,6 +952,7 @@
+ 			{"move-home", no_argument, NULL, 'm'},
+ 			{"non-unique", no_argument, NULL, 'o'},
+ 			{"password", required_argument, NULL, 'p'},
++			{"root", required_argument, NULL, 'R'},
+ #ifdef WITH_SELINUX
+ 			{"selinux-user", required_argument, NULL, 'Z'},
+ #endif
+@@ -905,9 +963,9 @@
+ 		};
+ 		while ((c = getopt_long (argc, argv,
+ #ifdef WITH_SELINUX
+-			                 "ac:d:e:f:g:G:hl:Lmop:s:u:UZ:",
++			                 "ac:d:e:f:g:G:hl:Lmop:R:s:u:UZ:",
+ #else
+-			                 "ac:d:e:f:g:G:hl:Lmop:s:u:U",
++			                 "ac:d:e:f:g:G:hl:Lmop:R:s:u:U",
+ #endif
+ 			                 long_options, NULL)) != -1) {
+ 			switch (c) {
+@@ -999,6 +1057,9 @@
+ 				user_pass = optarg;
+ 				pflg = true;
+ 				break;
++			case 'R':
++				/* no-op since we handled this in process_root_flag() earlier */
++				break;
+ 			case 's':
+ 				if (!VALID (optarg)) {
+ 					fprintf (stderr,
+@@ -1715,6 +1776,8 @@
+ 
+ 	OPENLOG ("usermod");
+ 
++	process_root_flag (argc, argv);
++
+ 	is_shadow_pwd = spw_file_present ();
+ #ifdef SHADOWGRP
+ 	is_shadow_grp = sgr_file_present ();
diff --git a/meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb b/meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
new file mode 100644
index 0000000..2f93e05
--- /dev/null
+++ b/meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
@@ -0,0 +1,66 @@
+SUMMARY = "Tools to change and administer password and group data"
+DESCRIPTION = "Tools to change and administer password and group data"
+HOMEPAGE = "http://pkg-shadow.alioth.debian.org"
+BUGTRACKER = "https://alioth.debian.org/tracker/?group_id=30580"
+SECTION = "base utils"
+PRIORITY = "optional"
+LICENSE = "BSD | Artistic"
+LIC_FILES_CHKSUM = "file://COPYING;md5=08c553a87d4e51bbed50b20e0adcaede \
+                    file://src/passwd.c;firstline=8;endline=30;md5=2899a045e90511d0e043b85a7db7e2fe"
+
+PR = "r0"
+
+SRC_URI = "ftp://pkg-shadow.alioth.debian.org/pub/pkg-shadow/shadow-${PV}.tar.bz2 \
+           file://shadow.automake-1.11.patch \
+           file://shadow-4.1.3-dots-in-usernames.patch \
+           file://shadow-4.1.4.2-env-reset-keep-locale.patch \
+           file://add_root_cmd_options.patch"
+
+SRC_URI[md5sum] = "b8608d8294ac88974f27b20f991c0e79"
+SRC_URI[sha256sum] = "633f5bb4ea0c88c55f3642c97f9d25cbef74f82e0b4cf8d54e7ad6f9f9caa778" 
+
+inherit autotools gettext native
+
+EXTRA_OECONF += "--without-audit \
+                 --without-libcrack \
+                 --without-libpam \
+                 --without-selinux"
+
+do_install_append() {
+	# Enable CREATE_HOME by default.
+	sed -i 's/#CREATE_HOME/CREATE_HOME/g' ${D}${sysconfdir}/login.defs
+
+	# As we are on an embedded system, ensure the users mailbox is in
+	# ~/ not /var/spool/mail by default, as who knows where or how big
+	# /var is. The system MDA will set this later anyway.
+	sed -i 's/MAIL_DIR/#MAIL_DIR/g' ${D}${sysconfdir}/login.defs
+	sed -i 's/#MAIL_FILE/MAIL_FILE/g' ${D}${sysconfdir}/login.defs
+
+	# Disable checking emails.
+	sed -i 's/MAIL_CHECK_ENAB/#MAIL_CHECK_ENAB/g' ${D}${sysconfdir}/login.defs
+
+	# Now we don't have a mail system. Disable mail creation for now.
+	sed -i 's:/bin/bash:/bin/sh:g' ${D}${sysconfdir}/default/useradd
+	sed -i '/^CREATE_MAIL_SPOOL/ s:^:#:' ${D}${sysconfdir}/default/useradd
+
+	install -d ${D}${sbindir} ${D}${base_sbindir} ${D}${base_bindir} 
+	for i in passwd chfn newgrp chsh ; do
+		mv ${D}${bindir}/$i ${D}${bindir}/$i.${PN}
+	done
+
+	mv ${D}${sbindir}/chpasswd ${D}${sbindir}/chpasswd.${PN}
+}
+
+pkg_postinst_${PN} () {
+	update-alternatives --install ${bindir}/passwd passwd passwd.${PN} 200
+	update-alternatives --install ${sbindir}/chpasswd chpasswd chpasswd.${PN} 200
+	update-alternatives --install ${bindir}/chfn chfn chfn.${PN} 200
+	update-alternatives --install ${bindir}/newgrp newgrp newgrp.${PN} 200
+	update-alternatives --install ${bindir}/chsh chsh chsh.${PN} 200
+}
+
+pkg_prerm_${PN} () {
+	for i in passwd chpasswd chfn newgrp chsh ; do
+		update-alternatives --remove $i $i.${PN}
+	done
+}
-- 
1.7.1



^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 3/7] base-passwd: add -cross recipe with default login.defs
  2011-05-31 19:53 ` Scott Garman
@ 2011-05-31 19:53   ` Scott Garman
  -1 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 18:13 UTC (permalink / raw)
  To: poky

The -cross version of the recipe is needed in order to set up
user and group account information in the target machine sysroot.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 .../base-passwd/base-passwd-3.5.22/login.defs      |  386 ++++++++++++++++++++
 .../base-passwd/base-passwd-cross_3.5.22.bb        |   53 +++
 2 files changed, 439 insertions(+), 0 deletions(-)
 create mode 100644 meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
 create mode 100644 meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb

diff --git a/meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs b/meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
new file mode 100644
index 0000000..1d392ac
--- /dev/null
+++ b/meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
@@ -0,0 +1,386 @@
+#
+# /etc/login.defs - Configuration control definitions for the shadow package.
+#
+#	$Id: login.defs 3038 2009-07-23 20:41:35Z nekral-guest $
+#
+
+#
+# Delay in seconds before being allowed another attempt after a login failure
+# Note: When PAM is used, some modules may enfore a minimal delay (e.g.
+#       pam_unix enforces a 2s delay)
+#
+FAIL_DELAY		3
+
+#
+# Enable logging and display of /var/log/faillog login failure info.
+#
+FAILLOG_ENAB		yes
+
+#
+# Enable display of unknown usernames when login failures are recorded.
+#
+LOG_UNKFAIL_ENAB	no
+
+#
+# Enable logging of successful logins
+#
+LOG_OK_LOGINS		no
+
+#
+# Enable logging and display of /var/log/lastlog login time info.
+#
+LASTLOG_ENAB		yes
+
+#
+# Enable checking and display of mailbox status upon login.
+#
+# Disable if the shell startup files already check for mail
+# ("mailx -e" or equivalent).
+#
+#MAIL_CHECK_ENAB		yes
+
+#
+# Enable additional checks upon password changes.
+#
+OBSCURE_CHECKS_ENAB	yes
+
+#
+# Enable checking of time restrictions specified in /etc/porttime.
+#
+PORTTIME_CHECKS_ENAB	yes
+
+#
+# Enable setting of ulimit, umask, and niceness from passwd gecos field.
+#
+QUOTAS_ENAB		yes
+
+#
+# Enable "syslog" logging of su activity - in addition to sulog file logging.
+# SYSLOG_SG_ENAB does the same for newgrp and sg.
+#
+SYSLOG_SU_ENAB		yes
+SYSLOG_SG_ENAB		yes
+
+#
+# If defined, either full pathname of a file containing device names or
+# a ":" delimited list of device names.  Root logins will be allowed only
+# upon these devices.
+#
+CONSOLE		/etc/securetty
+#CONSOLE	console:tty01:tty02:tty03:tty04
+
+#
+# If defined, all su activity is logged to this file.
+#
+#SULOG_FILE	/var/log/sulog
+
+#
+# If defined, ":" delimited list of "message of the day" files to
+# be displayed upon login.
+#
+MOTD_FILE	/etc/motd
+#MOTD_FILE	/etc/motd:/usr/lib/news/news-motd
+
+#
+# If defined, this file will be output before each login prompt.
+#
+#ISSUE_FILE	/etc/issue
+
+#
+# If defined, file which maps tty line to TERM environment parameter.
+# Each line of the file is in a format something like "vt100  tty01".
+#
+#TTYTYPE_FILE	/etc/ttytype
+
+#
+# If defined, login failures will be logged here in a utmp format.
+# last, when invoked as lastb, will read /var/log/btmp, so...
+#
+FTMP_FILE	/var/log/btmp
+
+#
+# If defined, name of file whose presence which will inhibit non-root
+# logins.  The contents of this file should be a message indicating
+# why logins are inhibited.
+#
+NOLOGINS_FILE	/etc/nologin
+
+#
+# If defined, the command name to display when running "su -".  For
+# example, if this is defined as "su" then a "ps" will display the
+# command is "-su".  If not defined, then "ps" would display the
+# name of the shell actually being run, e.g. something like "-sh".
+#
+SU_NAME		su
+
+#
+# *REQUIRED*
+#   Directory where mailboxes reside, _or_ name of file, relative to the
+#   home directory.  If you _do_ define both, #MAIL_DIR takes precedence.
+#
+#MAIL_DIR	/var/spool/mail
+MAIL_FILE	.mail
+
+#
+# If defined, file which inhibits all the usual chatter during the login
+# sequence.  If a full pathname, then hushed mode will be enabled if the
+# user's name or shell are found in the file.  If not a full pathname, then
+# hushed mode will be enabled if the file exists in the user's home directory.
+#
+HUSHLOGIN_FILE	.hushlogin
+#HUSHLOGIN_FILE	/etc/hushlogins
+
+#
+# If defined, either a TZ environment parameter spec or the
+# fully-rooted pathname of a file containing such a spec.
+#
+#ENV_TZ		TZ=CST6CDT
+#ENV_TZ		/etc/tzname
+
+#
+# If defined, an HZ environment parameter spec.
+#
+# for Linux/x86
+ENV_HZ		HZ=100
+# For Linux/Alpha...
+#ENV_HZ		HZ=1024
+
+#
+# *REQUIRED*  The default PATH settings, for superuser and normal users.
+#
+# (they are minimal, add the rest in the shell startup files)
+ENV_SUPATH	PATH=/sbin:/bin:/usr/sbin:/usr/bin
+ENV_PATH	PATH=/bin:/usr/bin
+
+#
+# Terminal permissions
+#
+#	TTYGROUP	Login tty will be assigned this group ownership.
+#	TTYPERM		Login tty will be set to this permission.
+#
+# If you have a "write" program which is "setgid" to a special group
+# which owns the terminals, define TTYGROUP to the group number and
+# TTYPERM to 0620.  Otherwise leave TTYGROUP commented out and assign
+# TTYPERM to either 622 or 600.
+#
+TTYGROUP	tty
+TTYPERM		0600
+
+#
+# Login configuration initializations:
+#
+#	ERASECHAR	Terminal ERASE character ('\010' = backspace).
+#	KILLCHAR	Terminal KILL character ('\025' = CTRL/U).
+#	ULIMIT		Default "ulimit" value.
+#
+# The ERASECHAR and KILLCHAR are used only on System V machines.
+# The ULIMIT is used only if the system supports it.
+# (now it works with setrlimit too; ulimit is in 512-byte units)
+#
+# Prefix these values with "0" to get octal, "0x" to get hexadecimal.
+#
+ERASECHAR	0177
+KILLCHAR	025
+#ULIMIT		2097152
+
+# Default initial "umask" value for non-PAM enabled systems.
+# UMASK is also used by useradd and newusers to set the mode of new home
+# directories.
+# 022 is the default value, but 027, or even 077, could be considered
+# better for privacy. There is no One True Answer here: each sysadmin
+# must make up her mind.
+UMASK		022
+
+#
+# Password aging controls:
+#
+#	PASS_MAX_DAYS	Maximum number of days a password may be used.
+#	PASS_MIN_DAYS	Minimum number of days allowed between password changes.
+#	PASS_MIN_LEN	Minimum acceptable password length.
+#	PASS_WARN_AGE	Number of days warning given before a password expires.
+#
+PASS_MAX_DAYS	99999
+PASS_MIN_DAYS	0
+PASS_MIN_LEN	5
+PASS_WARN_AGE	7
+
+#
+# If "yes", the user must be listed as a member of the first gid 0 group
+# in /etc/group (called "root" on most Linux systems) to be able to "su"
+# to uid 0 accounts.  If the group doesn't exist or is empty, no one
+# will be able to "su" to uid 0.
+#
+SU_WHEEL_ONLY	no
+
+#
+# If compiled with cracklib support, where are the dictionaries
+#
+CRACKLIB_DICTPATH	/var/cache/cracklib/cracklib_dict
+
+#
+# Min/max values for automatic uid selection in useradd
+#
+UID_MIN			 1000
+UID_MAX			60000
+# System accounts
+SYS_UID_MIN		  101
+SYS_UID_MAX		  999
+
+#
+# Min/max values for automatic gid selection in groupadd
+#
+GID_MIN			 1000
+GID_MAX			60000
+# System accounts
+SYS_GID_MIN		  101
+SYS_GID_MAX		  999
+
+#
+# Max number of login retries if password is bad
+#
+LOGIN_RETRIES		5
+
+#
+# Max time in seconds for login
+#
+LOGIN_TIMEOUT		60
+
+#
+# Maximum number of attempts to change password if rejected (too easy)
+#
+PASS_CHANGE_TRIES	5
+
+#
+# Warn about weak passwords (but still allow them) if you are root.
+#
+PASS_ALWAYS_WARN	yes
+
+#
+# Number of significant characters in the password for crypt().
+# Default is 8, don't change unless your crypt() is better.
+# Ignored if MD5_CRYPT_ENAB set to "yes".
+#
+#PASS_MAX_LEN		8
+
+#
+# Require password before chfn/chsh can make any changes.
+#
+CHFN_AUTH		yes
+
+#
+# Which fields may be changed by regular users using chfn - use
+# any combination of letters "frwh" (full name, room number, work
+# phone, home phone).  If not defined, no changes are allowed.
+# For backward compatibility, "yes" = "rwh" and "no" = "frwh".
+# 
+CHFN_RESTRICT		rwh
+
+#
+# Password prompt (%s will be replaced by user name).
+#
+# XXX - it doesn't work correctly yet, for now leave it commented out
+# to use the default which is just "Password: ".
+#LOGIN_STRING		"%s's Password: "
+
+#
+# Only works if compiled with MD5_CRYPT defined:
+# If set to "yes", new passwords will be encrypted using the MD5-based
+# algorithm compatible with the one used by recent releases of FreeBSD.
+# It supports passwords of unlimited length and longer salt strings.
+# Set to "no" if you need to copy encrypted passwords to other systems
+# which don't understand the new algorithm.  Default is "no".
+#
+# Note: If you use PAM, it is recommended to use a value consistent with
+# the PAM modules configuration.
+#
+# This variable is deprecated. You should use ENCRYPT_METHOD.
+#
+#MD5_CRYPT_ENAB	no
+
+#
+# Only works if compiled with ENCRYPTMETHOD_SELECT defined:
+# If set to MD5 , MD5-based algorithm will be used for encrypting password
+# If set to SHA256, SHA256-based algorithm will be used for encrypting password
+# If set to SHA512, SHA512-based algorithm will be used for encrypting password
+# If set to DES, DES-based algorithm will be used for encrypting password (default)
+# Overrides the MD5_CRYPT_ENAB option
+#
+# Note: If you use PAM, it is recommended to use a value consistent with
+# the PAM modules configuration.
+#
+#ENCRYPT_METHOD DES
+
+#
+# Only works if ENCRYPT_METHOD is set to SHA256 or SHA512.
+#
+# Define the number of SHA rounds.
+# With a lot of rounds, it is more difficult to brute forcing the password.
+# But note also that it more CPU resources will be needed to authenticate
+# users.
+#
+# If not specified, the libc will choose the default number of rounds (5000).
+# The values must be inside the 1000-999999999 range.
+# If only one of the MIN or MAX values is set, then this value will be used.
+# If MIN > MAX, the highest value will be used.
+#
+# SHA_CRYPT_MIN_ROUNDS 5000
+# SHA_CRYPT_MAX_ROUNDS 5000
+
+#
+# List of groups to add to the user's supplementary group set
+# when logging in on the console (as determined by the CONSOLE
+# setting).  Default is none.
+#
+# Use with caution - it is possible for users to gain permanent
+# access to these groups, even when not logged in on the console.
+# How to do it is left as an exercise for the reader...
+#
+#CONSOLE_GROUPS		floppy:audio:cdrom
+
+#
+# Should login be allowed if we can't cd to the home directory?
+# Default in no.
+#
+DEFAULT_HOME	yes
+
+#
+# If this file exists and is readable, login environment will be
+# read from it.  Every line should be in the form name=value.
+#
+ENVIRON_FILE	/etc/environment
+
+#
+# If defined, this command is run when removing a user.
+# It should remove any at/cron/print jobs etc. owned by
+# the user to be removed (passed as the first argument).
+#
+#USERDEL_CMD	/usr/sbin/userdel_local
+
+#
+# Enable setting of the umask group bits to be the same as owner bits
+# (examples: 022 -> 002, 077 -> 007) for non-root users, if the uid is
+# the same as gid, and username is the same as the primary group name.
+#
+# This also enables userdel to remove user groups if no members exist.
+#
+USERGROUPS_ENAB yes
+
+#
+# If set to a non-nul number, the shadow utilities will make sure that
+# groups never have more than this number of users on one line.
+# This permit to support split groups (groups split into multiple lines,
+# with the same group ID, to avoid limitation of the line length in the
+# group file).
+#
+# 0 is the default value and disables this feature.
+#
+#MAX_MEMBERS_PER_GROUP	0
+
+#
+# If useradd should create home directories for users by default (non
+# system users only)
+# This option is overridden with the -M or -m flags on the useradd command
+# line.
+#
+CREATE_HOME     yes
+
diff --git a/meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb b/meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
new file mode 100644
index 0000000..ab88a65
--- /dev/null
+++ b/meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
@@ -0,0 +1,53 @@
+SUMMARY = "Base system master password/group files."
+DESCRIPTION = "The master copies of the user database files (/etc/passwd and /etc/group).  The update-passwd tool is also provided to keep the system databases synchronized with these master files."
+SECTION = "base"
+DEPENDS = "shadow-native"
+PR = "r0"
+LICENSE = "GPLv2+"
+LIC_FILES_CHKSUM = "file://COPYING;md5=eb723b61539feef013de476e68b5c50a"
+
+SRC_URI = "${DEBIAN_MIRROR}/main/b/base-passwd/base-passwd_${PV}.tar.gz \
+           file://nobash.patch \
+           file://root-home.patch \
+           file://login.defs"
+
+SRC_URI[md5sum] = "47f22ab6b572d0133409ff6ad1fab402"
+SRC_URI[sha256sum] = "d34acb35a9f9f221e7e4f642b9ef4b22083dd77bb2fc7216756f445316d842fc"
+
+S = "${WORKDIR}/base-passwd"
+
+inherit autotools
+
+SSTATEPOSTINSTFUNCS += "base_passwd_cross_sstate_postinst"
+
+do_install () {
+	install -d -m 755 ${D}${sbindir}
+	install -p -m 755 update-passwd ${D}${sbindir}/
+	install -d -m 755 ${D}${mandir}/man8 ${D}${mandir}/pl/man8
+	install -p -m 644 man/update-passwd.8 ${D}${mandir}/man8/
+	install -p -m 644 man/update-passwd.pl.8 \
+		${D}${mandir}/pl/man8/update-passwd.8
+	gzip -9 ${D}${mandir}/man8/* ${D}${mandir}/pl/man8/*
+	install -d -m 755 ${D}${datadir}/base-passwd
+	install -p -m 644 passwd.master ${D}${datadir}/base-passwd/
+	install -p -m 644 group.master ${D}${datadir}/base-passwd/
+    install -p -m 644 ${S}/../login.defs ${D}${datadir}/base-passwd/login.defs
+
+	install -d -m 755 ${D}${docdir}/${PN}
+	install -p -m 644 debian/changelog ${D}${docdir}/${PN}/
+	gzip -9 ${D}${docdir}/${PN}/*
+	install -p -m 644 README ${D}${docdir}/${PN}/
+	install -p -m 644 debian/copyright ${D}${docdir}/${PN}/
+}
+
+base_passwd_cross_sstate_postinst() {
+	if [ "${BB_CURRENTTASK}" = "populate_sysroot" -o "${BB_CURRENTTASK}" = "populate_sysroot_setscene" ]
+	then
+		# Staging does not copy ${sysconfdir} files into the
+		# target sysroot, so we need to do so manually.
+		install -d -m 755 ${STAGING_DIR_TARGET}${sysconfdir}
+		install -p -m 644 ${STAGING_DIR_TARGET}${datadir}/base-passwd/passwd.master ${STAGING_DIR_TARGET}${sysconfdir}/passwd
+		install -p -m 644 ${STAGING_DIR_TARGET}${datadir}/base-passwd/group.master ${STAGING_DIR_TARGET}${sysconfdir}/group
+		install -p -m 644 ${STAGING_DIR_TARGET}${datadir}/base-passwd/login.defs ${STAGING_DIR_TARGET}/${sysconfdir}/login.defs
+	fi
+}
-- 
1.7.1



^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 4/7] useradd.bbclass: new class for managing user/group permissions
  2011-05-31 19:53 ` Scott Garman
@ 2011-05-31 19:53   ` Scott Garman
  -1 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 18:13 UTC (permalink / raw)
  To: poky

This class is to be used by recipes that need to set up specific
user/group accounts and set custom file/directory permissions.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 meta/classes/useradd.bbclass |  136 ++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 136 insertions(+), 0 deletions(-)
 create mode 100644 meta/classes/useradd.bbclass

diff --git a/meta/classes/useradd.bbclass b/meta/classes/useradd.bbclass
new file mode 100644
index 0000000..ac6f8f6
--- /dev/null
+++ b/meta/classes/useradd.bbclass
@@ -0,0 +1,136 @@
+USERADDPN ?= "${PN}"
+
+# base-passwd-cross provides the default passwd and group files in the
+# target sysroot, and shadow-native provides the utilities needed to
+# add and modify user and group accounts
+DEPENDS_append = " base-passwd-cross shadow-native"
+RDEPENDS_${USERADDPN}_append = " base-passwd shadow"
+
+PSEUDO="${STAGING_DIR_NATIVE}/usr/bin/pseudo"
+export PSEUDO
+PSEUDO_LOCALSTATEDIR="${STAGING_DIR_TARGET}/var/pseudo"
+export PSEUDO_LOCALSTATEDIR
+PSEUDO_PASSWD = "${STAGING_DIR_TARGET}"
+export PSEUDO_PASSWD
+
+useradd_sysroot () {
+	# Explicitly set $D since it isn't set to anything
+	# before do_install
+	D=${D}
+	useradd_preinst
+}
+
+useradd_sysroot_sstate () {
+	if [ "${BB_CURRENTTASK}" = "populate_sysroot_setscene" ]
+	then
+		# Explicitly set $D since it isn't set to anything
+		# before do_install
+		D=${D}
+		useradd_preinst
+	fi
+}
+
+useradd_preinst () {
+OPT=""
+SYSROOT=""
+
+if test "x$D" != "x"; then
+	# Installing into a sysroot
+	SYSROOT="${STAGING_DIR_TARGET}"
+	OPT="--root ${STAGING_DIR_TARGET}"
+else
+	# Installing onto a target
+	PSEUDO=""
+fi
+
+# Perform group additions first, since user additions may depend
+# on these groups existing
+if test "x${GROUPADD_PARAM_${PN}}" != "x"; then
+	echo "Running groupadd commands..."
+	# Invoke multiple instances of groupadd for parameter lists
+	# separated by ';'
+	opts=`echo "${GROUPADD_PARAM_${PN}}" | cut -d ';' -f 1`
+	remaining=`echo "${GROUPADD_PARAM_${PN}}" | cut -d ';' -f 2-`
+	while test "x$opts" != "x"; do
+		eval $PSEUDO groupadd -f $OPT $opts
+
+		if test "x$opts" = "x$remaining"; then
+			break
+		fi
+		opts=`echo "$remaining" | cut -d ';' -f 1`
+		remaining=`echo "$remaining" | cut -d ';' -f 2-`
+	done
+fi 
+
+if test "x${USERADD_PARAM_${PN}}" != "x"; then
+	echo "Running useradd commands..."
+	# Invoke multiple instances of useradd for parameter lists
+	# separated by ';'
+	opts=`echo "${USERADD_PARAM_${PN}}" | cut -d ';' -f 1`
+	remaining=`echo "${USERADD_PARAM_${PN}}" | cut -d ';' -f 2-`
+	while test "x$opts" != "x"; do
+		# useradd does not have a -f option, so we have to check if the
+		# username already exists manually
+		username=`echo "$opts" | awk '{ print $NF }'`
+		user_exists=`grep "^$username:" $SYSROOT/etc/passwd || true`
+		if test "x$user_exists" = "x"; then
+			eval $PSEUDO useradd $OPT $opts
+		else
+			echo "Note: username $username already exists, not re-creating it"
+		fi
+
+		if test "x$opts" = "x$remaining"; then
+			break
+		fi
+		opts=`echo "$remaining" | cut -d ';' -f 1`
+		remaining=`echo "$remaining" | cut -d ';' -f 2-`
+	done
+fi
+}
+
+do_install[prefuncs] += "useradd_sysroot"
+SSTATEPOSTINSTFUNCS += "useradd_sysroot_sstate"
+
+# Recipe parse-time sanity checks
+def update_useradd_after_parse(d):
+	if bb.data.getVar('USERADD_PACKAGES', d) == None:
+		if bb.data.getVar('USERADD_PARAM', d) == None and bb.data.getVar('GROUPADD_PARAM', d) == None:
+			raise bb.build.FuncFailed, "%s inherits useradd but doesn't set USERADD_PARAM or GROUPADD_PARAM" % bb.data.getVar('FILE', d)
+
+python __anonymous() {
+	update_useradd_after_parse(d)
+}
+
+# Adds the preinst script into generated packages
+fakeroot python populate_packages_prepend () {
+	def update_useradd_package(pkg):
+		bb.debug(1, 'adding user/group calls to preinst for %s' % pkg)
+		localdata = bb.data.createCopy(d)
+		overrides = bb.data.getVar("OVERRIDES", localdata, 1)
+		bb.data.setVar("OVERRIDES", "%s:%s" % (pkg, overrides), localdata)
+		bb.data.update_data(localdata)
+
+		"""
+		useradd preinst is appended here because pkg_preinst may be
+		required to execute on the target. Not doing so may cause
+		useradd preinst to be invoked twice, causing unwanted warnings.
+		"""
+		preinst = bb.data.getVar('pkg_preinst', localdata, 1)
+		if not preinst:
+			preinst = '#!/bin/sh\n'
+		preinst += bb.data.getVar('useradd_preinst', localdata, 1)
+		bb.data.setVar('pkg_preinst_%s' % pkg, preinst, d)
+
+	# We add the user/group calls to all packages to allow any package
+	# to contain files owned by the users/groups defined in the recipe.
+	# The user/group addition code is careful not to create duplicate
+	# entries, so this is safe.
+	pkgs = bb.data.getVar('USERADD_PACKAGES', d, 1)
+	if pkgs == None:
+		pkgs = bb.data.getVar('USERADDPN', d, 1)
+		packages = (bb.data.getVar('PACKAGES', d, 1) or "").split()
+		if not pkgs in packages and packages != []:
+			pkgs = packages[0]
+	for pkg in pkgs.split():
+		update_useradd_package(pkg)
+}
-- 
1.7.1



^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 5/7] useradd-example: example recipe for using inherit useradd
  2011-05-31 19:53 ` Scott Garman
@ 2011-05-31 19:53   ` Scott Garman
  -1 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 18:13 UTC (permalink / raw)
  To: poky

An example recipe for demonstrating/documenting how user and
group manipulation is done with 'inherit useradd'

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 .../recipes-skeleton/useradd/useradd-example.bb    |   59 ++++++++++++++++++++
 1 files changed, 59 insertions(+), 0 deletions(-)
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file4

diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example.bb b/meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
new file mode 100644
index 0000000..1e6ae87
--- /dev/null
+++ b/meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
@@ -0,0 +1,59 @@
+SUMMARY = "Example recipe for using inherit useradd"
+DESCRIPTION = "This recipe serves as an example for using features from useradd.bbclass"
+SECTION = "examples"
+PR = "r0"
+LICENSE = "MIT"
+LIC_FILES_CHKSUM = "file://${COREBASE}/LICENSE;md5=3f40d7994397109285ec7b81fdeb3b58 \
+                    file://${COREBASE}/meta/COPYING.MIT;md5=3da9cfbcb788c80a0384361b4de20420"
+
+SRC_URI = "file://file1 \
+           file://file2 \
+           file://file3 \
+           file://file4"
+
+S = "${WORKDIR}"
+
+inherit useradd
+
+# Specify which package(s) should include the user/group code.
+# Make sure that any packages which install files owned by custom
+# users/groups are included here. The code which adds users and
+# groups is idempotent.
+USERADD_PACKAGES = "useradd-example"
+
+# You *must* set USERADD_PARAM and/or GROUPADD_PARAM when
+# you inherit useradd.
+
+# USERADD_PARAM specifies command line options to pass to the
+# useradd command. Multiple users can be created by separating
+# the commands with a semicolon. Here we'll create two users,
+# user1 and user3:
+USERADD_PARAM_useradd-example = "-u 1200 -d /home/user1 -r -s /bin/bash user1; -u 1201 -d /home/user3 -r -s /bin/bash user3"
+
+# GROUPADD_PARAM works the same way, which you set to the options
+# you'd normally pass to the groupadd command. This will create
+# groups group1, group2, and group3:
+GROUPADD_PARAM_useradd-example = "-g 880 group1; -g 890 group2; -g 900 group3"
+
+do_install () {
+	install -d -m 755 ${D}/usr/share/user1
+	install -d -m 755 ${D}/usr/share/user3
+	install -p -m 644 file1 ${D}/usr/share/user1/
+	install -p -m 644 file2 ${D}/usr/share/user1/
+	install -p -m 644 file3 ${D}/usr/share/user3/
+	install -p -m 644 file4 ${D}/usr/share/user3/
+
+	# The new users and groups are created before the do_install
+	# step, so you are now free to make use of them:
+	chown -R user1 ${D}/usr/share/user1
+	chown -R user3 ${D}/usr/share/user3
+	chgrp group1 ${D}/usr/share/user1/file1
+	chgrp group3 ${D}/usr/share/user1/file2
+	chgrp group1 ${D}/usr/share/user3/file3
+	chgrp group3 ${D}/usr/share/user3/file4
+}
+
+PACKAGES =+ "${PN}-user3"
+
+FILES_${PN} = "/usr/share/user1/*"
+FILES_${PN}-user3 = "/usr/share/user3/*"
diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file1 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
new file mode 100644
index 0000000..e69de29
diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file2 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
new file mode 100644
index 0000000..e69de29
diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file3 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
new file mode 100644
index 0000000..e69de29
diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file4 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
new file mode 100644
index 0000000..e69de29
-- 
1.7.1



^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 6/7] bitbake.conf: set PSEUDO_PASSWD within FAKEROOTENV
  2011-05-31 19:53 ` Scott Garman
@ 2011-05-31 19:53   ` Scott Garman
  -1 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 18:13 UTC (permalink / raw)
  To: poky

PSEUDO_PASSWD needs to point to the directory where passwd and group
files are kept. This will allow pseudo to use those users and groups
to change file ownership.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 meta/conf/bitbake.conf |    2 +-
 1 files changed, 1 insertions(+), 1 deletions(-)

diff --git a/meta/conf/bitbake.conf b/meta/conf/bitbake.conf
index d307385..6f16a65 100644
--- a/meta/conf/bitbake.conf
+++ b/meta/conf/bitbake.conf
@@ -535,7 +535,7 @@ SRC_URI = "file://${FILE}"
 
 # Use pseudo as the fakeroot implementation
 PSEUDO_LOCALSTATEDIR ?= "${WORKDIR}/pseudo/"
-FAKEROOTENV = "PSEUDO_PREFIX=${STAGING_DIR_NATIVE}${prefix_native} PSEUDO_LOCALSTATEDIR=${PSEUDO_LOCALSTATEDIR} PSEUDO_NOSYMLINKEXP=1 PSEUDO_DISABLED=0"
+FAKEROOTENV = "PSEUDO_PREFIX=${STAGING_DIR_NATIVE}${prefix_native} PSEUDO_LOCALSTATEDIR=${PSEUDO_LOCALSTATEDIR} PSEUDO_PASSWD=${STAGING_DIR_TARGET}/etc PSEUDO_NOSYMLINKEXP=1 PSEUDO_DISABLED=0"
 FAKEROOTDIRS = "${PSEUDO_LOCALSTATEDIR}"
 PREFERRED_PROVIDER_virtual/fakeroot-native ?= "pseudo-native"
 
-- 
1.7.1



^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 7/7] package_rpm.bbclass: make RPM use on-disk permissions
  2011-05-31 19:53 ` Scott Garman
@ 2011-05-31 19:53   ` Scott Garman
  -1 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 18:13 UTC (permalink / raw)
  To: poky

Instruct RPM to use the on-disk permissions, owners, groups,
and directory permissions, instead of defaulting to root:root

Code changes suggested by Mark Hatle.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 meta/classes/package_rpm.bbclass |    2 ++
 1 files changed, 2 insertions(+), 0 deletions(-)

diff --git a/meta/classes/package_rpm.bbclass b/meta/classes/package_rpm.bbclass
index 1d8c686..d124c01 100644
--- a/meta/classes/package_rpm.bbclass
+++ b/meta/classes/package_rpm.bbclass
@@ -484,6 +484,7 @@ python write_specfile () {
 			else:
 				bb.note("Creating RPM package for %s" % splitname)
 				spec_files_top.append('%files')
+				spec_files_top.append('%defattr(-,-,-,-)')
 				if file_list:
 					spec_files_top.extend(file_list)
 				spec_files_top.append('')
@@ -570,6 +571,7 @@ python write_specfile () {
 		else:
 			bb.note("Creating RPM package for %s" % splitname)
 			spec_files_bottom.append('%%files -n %s' % splitname)
+			spec_files_bottom.append('%defattr(-,-,-,-)')
 			if file_list:
 				spec_files_bottom.extend(file_list)
 			spec_files_bottom.append('')
-- 
1.7.1



^ permalink raw reply related	[flat|nested] 51+ messages in thread

* Re: [poky] [PATCH 0/7] User/group creation at preinstall
  2011-05-31 19:53 ` Scott Garman
@ 2011-05-31 18:45   ` Koen Kooi
  -1 siblings, 0 replies; 51+ messages in thread
From: Koen Kooi @ 2011-05-31 18:45 UTC (permalink / raw)
  To: Scott Garman
  Cc: poky@yoctoproject.org Project,
	Patches and discussions about the oe-core layer

Shouldn't patches like this be sent to the oe-core list? It wouldn't have saved me from the selinux bug in shadow, though :)

Op 31 mei 2011, om 20:13 heeft Scott Garman het volgende geschreven:

> Hi Saul,
> 
> This pull request includes everything needed to add the ability to
> create custom users and groups in our images/packages and the
> corresponding ability to set custom ownership permissions. 
> 
> There is a useradd-example.bb file in meta-skeleton which provides
> a heavily-commented example recipe to demonstrate how this feature
> can be used.
> 
> I'd like to request that Mark Hatle and Richard do a code review of
> this and offer their Acked-by: support if they are happy with things.
> 
> Once this gets into master, I'm happy to write up a short section for
> the Poky Reference Manual to document it in a more visible way.
> 
> Scott
> 
> The following changes since commit 1169f1b066d0028bd2ef7915440450bd42ef165e:
> 
>  license.bbclass: Sane Parsing of licenses (2011-05-27 23:36:24 +0100)
> 
> are available in the git repository at:
>  git://git.pokylinux.org/poky-contrib sgarman/user-group-creation
>  http://git.pokylinux.org/cgit.cgi/poky-contrib/log/?h=sgarman/user-group-creation
> 
> Scott Garman (7):
>  shadow: recipe and patch cleanup
>  shadow: add a -native recipe with customized utilities
>  base-passwd: add -cross recipe with default login.defs
>  useradd.bbclass: new class for managing user/group permissions
>  useradd-example: example recipe for using inherit useradd
>  bitbake.conf: set PSEUDO_PASSWD within FAKEROOTENV
>  package_rpm.bbclass: make RPM use on-disk permissions
> 
> .../recipes-skeleton/useradd/useradd-example.bb    |   59 +
> meta/classes/package_rpm.bbclass                   |    2 +
> meta/classes/useradd.bbclass                       |  136 ++
> meta/conf/bitbake.conf                             |    2 +-
> .../base-passwd/base-passwd-3.5.22/login.defs      |  386 ++++++
> .../base-passwd/base-passwd-cross_3.5.22.bb        |   53 +
> .../shadow/files/add_root_cmd_options.patch        | 1293 ++++++++++++++++++++
> .../files/shadow-4.1.3-dots-in-usernames.patch     |    4 +
> .../shadow-4.1.4.2-env-reset-keep-locale.patch     |    4 +
> .../files/shadow-4.1.4.2-groupmod-pam-check.patch  |    4 +
> .../files/shadow-4.1.4.2-su_no_sanitize_env.patch  |    4 +
> .../shadow/files/shadow.automake-1.11.patch        |    4 +
> .../shadow/shadow-native_4.1.4.3.bb                |   66 +
> meta/recipes-extended/shadow/shadow.inc            |  121 --
> meta/recipes-extended/shadow/shadow_4.1.4.3.bb     |  141 ++-
> 15 files changed, 2148 insertions(+), 131 deletions(-)
> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
> create mode 100644 meta/classes/useradd.bbclass
> create mode 100644 meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
> create mode 100644 meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
> create mode 100644 meta/recipes-extended/shadow/files/add_root_cmd_options.patch
> create mode 100644 meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
> delete mode 100644 meta/recipes-extended/shadow/shadow.inc
> 
> _______________________________________________
> poky mailing list
> poky@yoctoproject.org
> https://lists.yoctoproject.org/listinfo/poky




^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 0/7] User/group creation at preinstall
@ 2011-05-31 18:45   ` Koen Kooi
  0 siblings, 0 replies; 51+ messages in thread
From: Koen Kooi @ 2011-05-31 18:45 UTC (permalink / raw)
  To: Scott Garman
  Cc: poky@yoctoproject.org Project,
	Patches and discussions about the oe-core layer

Shouldn't patches like this be sent to the oe-core list? It wouldn't have saved me from the selinux bug in shadow, though :)

Op 31 mei 2011, om 20:13 heeft Scott Garman het volgende geschreven:

> Hi Saul,
> 
> This pull request includes everything needed to add the ability to
> create custom users and groups in our images/packages and the
> corresponding ability to set custom ownership permissions. 
> 
> There is a useradd-example.bb file in meta-skeleton which provides
> a heavily-commented example recipe to demonstrate how this feature
> can be used.
> 
> I'd like to request that Mark Hatle and Richard do a code review of
> this and offer their Acked-by: support if they are happy with things.
> 
> Once this gets into master, I'm happy to write up a short section for
> the Poky Reference Manual to document it in a more visible way.
> 
> Scott
> 
> The following changes since commit 1169f1b066d0028bd2ef7915440450bd42ef165e:
> 
>  license.bbclass: Sane Parsing of licenses (2011-05-27 23:36:24 +0100)
> 
> are available in the git repository at:
>  git://git.pokylinux.org/poky-contrib sgarman/user-group-creation
>  http://git.pokylinux.org/cgit.cgi/poky-contrib/log/?h=sgarman/user-group-creation
> 
> Scott Garman (7):
>  shadow: recipe and patch cleanup
>  shadow: add a -native recipe with customized utilities
>  base-passwd: add -cross recipe with default login.defs
>  useradd.bbclass: new class for managing user/group permissions
>  useradd-example: example recipe for using inherit useradd
>  bitbake.conf: set PSEUDO_PASSWD within FAKEROOTENV
>  package_rpm.bbclass: make RPM use on-disk permissions
> 
> .../recipes-skeleton/useradd/useradd-example.bb    |   59 +
> meta/classes/package_rpm.bbclass                   |    2 +
> meta/classes/useradd.bbclass                       |  136 ++
> meta/conf/bitbake.conf                             |    2 +-
> .../base-passwd/base-passwd-3.5.22/login.defs      |  386 ++++++
> .../base-passwd/base-passwd-cross_3.5.22.bb        |   53 +
> .../shadow/files/add_root_cmd_options.patch        | 1293 ++++++++++++++++++++
> .../files/shadow-4.1.3-dots-in-usernames.patch     |    4 +
> .../shadow-4.1.4.2-env-reset-keep-locale.patch     |    4 +
> .../files/shadow-4.1.4.2-groupmod-pam-check.patch  |    4 +
> .../files/shadow-4.1.4.2-su_no_sanitize_env.patch  |    4 +
> .../shadow/files/shadow.automake-1.11.patch        |    4 +
> .../shadow/shadow-native_4.1.4.3.bb                |   66 +
> meta/recipes-extended/shadow/shadow.inc            |  121 --
> meta/recipes-extended/shadow/shadow_4.1.4.3.bb     |  141 ++-
> 15 files changed, 2148 insertions(+), 131 deletions(-)
> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
> create mode 100644 meta/classes/useradd.bbclass
> create mode 100644 meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
> create mode 100644 meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
> create mode 100644 meta/recipes-extended/shadow/files/add_root_cmd_options.patch
> create mode 100644 meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
> delete mode 100644 meta/recipes-extended/shadow/shadow.inc
> 
> _______________________________________________
> poky mailing list
> poky@yoctoproject.org
> https://lists.yoctoproject.org/listinfo/poky



^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [poky] [PATCH 0/7] User/group creation at preinstall
  2011-05-31 18:45   ` Koen Kooi
@ 2011-05-31 19:06     ` Saul Wold
  -1 siblings, 0 replies; 51+ messages in thread
From: Saul Wold @ 2011-05-31 19:06 UTC (permalink / raw)
  To: Koen Kooi
  Cc: Patches and discussions about the oe-core layer,
	poky@yoctoproject.org Project

On 05/31/2011 11:45 AM, Koen Kooi wrote:
> Shouldn't patches like this be sent to the oe-core list? It wouldn't have saved me from the selinux bug in shadow, though :)
>
Scott,

I would agree with Koen, this is a oe-core change, not a Poky only 
change, please resend this request to the oe-core list.

Thanks
	Sau!


> Op 31 mei 2011, om 20:13 heeft Scott Garman het volgende geschreven:
>
>> Hi Saul,
>>
>> This pull request includes everything needed to add the ability to
>> create custom users and groups in our images/packages and the
>> corresponding ability to set custom ownership permissions.
>>
>> There is a useradd-example.bb file in meta-skeleton which provides
>> a heavily-commented example recipe to demonstrate how this feature
>> can be used.
>>
>> I'd like to request that Mark Hatle and Richard do a code review of
>> this and offer their Acked-by: support if they are happy with things.
>>
>> Once this gets into master, I'm happy to write up a short section for
>> the Poky Reference Manual to document it in a more visible way.
>>
>> Scott
>>
>> The following changes since commit 1169f1b066d0028bd2ef7915440450bd42ef165e:
>>
>>   license.bbclass: Sane Parsing of licenses (2011-05-27 23:36:24 +0100)
>>
>> are available in the git repository at:
>>   git://git.pokylinux.org/poky-contrib sgarman/user-group-creation
>>   http://git.pokylinux.org/cgit.cgi/poky-contrib/log/?h=sgarman/user-group-creation
>>
>> Scott Garman (7):
>>   shadow: recipe and patch cleanup
>>   shadow: add a -native recipe with customized utilities
>>   base-passwd: add -cross recipe with default login.defs
>>   useradd.bbclass: new class for managing user/group permissions
>>   useradd-example: example recipe for using inherit useradd
>>   bitbake.conf: set PSEUDO_PASSWD within FAKEROOTENV
>>   package_rpm.bbclass: make RPM use on-disk permissions
>>
>> .../recipes-skeleton/useradd/useradd-example.bb    |   59 +
>> meta/classes/package_rpm.bbclass                   |    2 +
>> meta/classes/useradd.bbclass                       |  136 ++
>> meta/conf/bitbake.conf                             |    2 +-
>> .../base-passwd/base-passwd-3.5.22/login.defs      |  386 ++++++
>> .../base-passwd/base-passwd-cross_3.5.22.bb        |   53 +
>> .../shadow/files/add_root_cmd_options.patch        | 1293 ++++++++++++++++++++
>> .../files/shadow-4.1.3-dots-in-usernames.patch     |    4 +
>> .../shadow-4.1.4.2-env-reset-keep-locale.patch     |    4 +
>> .../files/shadow-4.1.4.2-groupmod-pam-check.patch  |    4 +
>> .../files/shadow-4.1.4.2-su_no_sanitize_env.patch  |    4 +
>> .../shadow/files/shadow.automake-1.11.patch        |    4 +
>> .../shadow/shadow-native_4.1.4.3.bb                |   66 +
>> meta/recipes-extended/shadow/shadow.inc            |  121 --
>> meta/recipes-extended/shadow/shadow_4.1.4.3.bb     |  141 ++-
>> 15 files changed, 2148 insertions(+), 131 deletions(-)
>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
>> create mode 100644 meta/classes/useradd.bbclass
>> create mode 100644 meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
>> create mode 100644 meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
>> create mode 100644 meta/recipes-extended/shadow/files/add_root_cmd_options.patch
>> create mode 100644 meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
>> delete mode 100644 meta/recipes-extended/shadow/shadow.inc
>>
>> _______________________________________________
>> poky mailing list
>> poky@yoctoproject.org
>> https://lists.yoctoproject.org/listinfo/poky
>
> _______________________________________________
> poky mailing list
> poky@yoctoproject.org
> https://lists.yoctoproject.org/listinfo/poky
>



^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 0/7] User/group creation at preinstall
@ 2011-05-31 19:06     ` Saul Wold
  0 siblings, 0 replies; 51+ messages in thread
From: Saul Wold @ 2011-05-31 19:06 UTC (permalink / raw)
  To: Koen Kooi
  Cc: Patches and discussions about the oe-core layer,
	poky@yoctoproject.org Project

On 05/31/2011 11:45 AM, Koen Kooi wrote:
> Shouldn't patches like this be sent to the oe-core list? It wouldn't have saved me from the selinux bug in shadow, though :)
>
Scott,

I would agree with Koen, this is a oe-core change, not a Poky only 
change, please resend this request to the oe-core list.

Thanks
	Sau!


> Op 31 mei 2011, om 20:13 heeft Scott Garman het volgende geschreven:
>
>> Hi Saul,
>>
>> This pull request includes everything needed to add the ability to
>> create custom users and groups in our images/packages and the
>> corresponding ability to set custom ownership permissions.
>>
>> There is a useradd-example.bb file in meta-skeleton which provides
>> a heavily-commented example recipe to demonstrate how this feature
>> can be used.
>>
>> I'd like to request that Mark Hatle and Richard do a code review of
>> this and offer their Acked-by: support if they are happy with things.
>>
>> Once this gets into master, I'm happy to write up a short section for
>> the Poky Reference Manual to document it in a more visible way.
>>
>> Scott
>>
>> The following changes since commit 1169f1b066d0028bd2ef7915440450bd42ef165e:
>>
>>   license.bbclass: Sane Parsing of licenses (2011-05-27 23:36:24 +0100)
>>
>> are available in the git repository at:
>>   git://git.pokylinux.org/poky-contrib sgarman/user-group-creation
>>   http://git.pokylinux.org/cgit.cgi/poky-contrib/log/?h=sgarman/user-group-creation
>>
>> Scott Garman (7):
>>   shadow: recipe and patch cleanup
>>   shadow: add a -native recipe with customized utilities
>>   base-passwd: add -cross recipe with default login.defs
>>   useradd.bbclass: new class for managing user/group permissions
>>   useradd-example: example recipe for using inherit useradd
>>   bitbake.conf: set PSEUDO_PASSWD within FAKEROOTENV
>>   package_rpm.bbclass: make RPM use on-disk permissions
>>
>> .../recipes-skeleton/useradd/useradd-example.bb    |   59 +
>> meta/classes/package_rpm.bbclass                   |    2 +
>> meta/classes/useradd.bbclass                       |  136 ++
>> meta/conf/bitbake.conf                             |    2 +-
>> .../base-passwd/base-passwd-3.5.22/login.defs      |  386 ++++++
>> .../base-passwd/base-passwd-cross_3.5.22.bb        |   53 +
>> .../shadow/files/add_root_cmd_options.patch        | 1293 ++++++++++++++++++++
>> .../files/shadow-4.1.3-dots-in-usernames.patch     |    4 +
>> .../shadow-4.1.4.2-env-reset-keep-locale.patch     |    4 +
>> .../files/shadow-4.1.4.2-groupmod-pam-check.patch  |    4 +
>> .../files/shadow-4.1.4.2-su_no_sanitize_env.patch  |    4 +
>> .../shadow/files/shadow.automake-1.11.patch        |    4 +
>> .../shadow/shadow-native_4.1.4.3.bb                |   66 +
>> meta/recipes-extended/shadow/shadow.inc            |  121 --
>> meta/recipes-extended/shadow/shadow_4.1.4.3.bb     |  141 ++-
>> 15 files changed, 2148 insertions(+), 131 deletions(-)
>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
>> create mode 100644 meta/classes/useradd.bbclass
>> create mode 100644 meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
>> create mode 100644 meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
>> create mode 100644 meta/recipes-extended/shadow/files/add_root_cmd_options.patch
>> create mode 100644 meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
>> delete mode 100644 meta/recipes-extended/shadow/shadow.inc
>>
>> _______________________________________________
>> poky mailing list
>> poky@yoctoproject.org
>> https://lists.yoctoproject.org/listinfo/poky
>
> _______________________________________________
> poky mailing list
> poky@yoctoproject.org
> https://lists.yoctoproject.org/listinfo/poky
>


^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 5/7] useradd-example: example recipe for using inherit useradd
  2011-05-31 19:53   ` Scott Garman
  (?)
@ 2011-05-31 19:09   ` Mark Hatle
  -1 siblings, 0 replies; 51+ messages in thread
From: Mark Hatle @ 2011-05-31 19:09 UTC (permalink / raw)
  To: poky

A few suggestions below to expand the example a bit.

On 5/31/11 1:13 PM, Scott Garman wrote:
> An example recipe for demonstrating/documenting how user and
> group manipulation is done with 'inherit useradd'
> 
> Signed-off-by: Scott Garman <scott.a.garman@intel.com>
> ---
>  .../recipes-skeleton/useradd/useradd-example.bb    |   59 ++++++++++++++++++++
>  1 files changed, 59 insertions(+), 0 deletions(-)
>  create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
>  create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
>  create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
>  create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
>  create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
> 
> diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example.bb b/meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
> new file mode 100644
> index 0000000..1e6ae87
> --- /dev/null
> +++ b/meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
> @@ -0,0 +1,59 @@
> +SUMMARY = "Example recipe for using inherit useradd"
> +DESCRIPTION = "This recipe serves as an example for using features from useradd.bbclass"
> +SECTION = "examples"
> +PR = "r0"
> +LICENSE = "MIT"
> +LIC_FILES_CHKSUM = "file://${COREBASE}/LICENSE;md5=3f40d7994397109285ec7b81fdeb3b58 \
> +                    file://${COREBASE}/meta/COPYING.MIT;md5=3da9cfbcb788c80a0384361b4de20420"
> +
> +SRC_URI = "file://file1 \
> +           file://file2 \
> +           file://file3 \
> +           file://file4"
> +
> +S = "${WORKDIR}"
> +

Move the package's up here to be clearer what we're doing:

PACKAGES =+ "${PN}-user3"

> +inherit useradd
> +
> +# Specify which package(s) should include the user/group code.
> +# Make sure that any packages which install files owned by custom
> +# users/groups are included here. The code which adds users and
> +# groups is idempotent.
> +USERADD_PACKAGES = "useradd-example"

List two packages above:

USERADD_PACKAGES = "useradd-example ${PN}-user3"

> +
> +# You *must* set USERADD_PARAM and/or GROUPADD_PARAM when
> +# you inherit useradd.
> +
> +# USERADD_PARAM specifies command line options to pass to the
> +# useradd command. Multiple users can be created by separating
> +# the commands with a semicolon. Here we'll create two users,
> +# user1 and user3:
> +USERADD_PARAM_useradd-example = "-u 1200 -d /home/user1 -r -s /bin/bash user1; -u 1201 -d /home/user3 -r -s /bin/bash user3"

Break the above apart into:

USERADD_PARAM_useradd-example = "-u 1200 -d /home/user1 -r -s /bin/bash user1;
-u 1201 -d /home/user2 -r -s /bin/bash user2"

USERADD_PARAM_${PN}-user3 = "-u 1202 -d /home/user3 -r -s /bin/bash user3"

> +
> +# GROUPADD_PARAM works the same way, which you set to the options
> +# you'd normally pass to the groupadd command. This will create
> +# groups group1, group2, and group3:
> +GROUPADD_PARAM_useradd-example = "-g 880 group1; -g 890 group2; -g 900 group3"

GROUPADD_PARAM_useradd-example = "-g 880 group1; -g 890 group2"

GROUPADD_PARAM_${PN}-user3 = "-g 900 group3"

> +
> +do_install () {
> +	install -d -m 755 ${D}/usr/share/user1
> +	install -d -m 755 ${D}/usr/share/user3
> +	install -p -m 644 file1 ${D}/usr/share/user1/
> +	install -p -m 644 file2 ${D}/usr/share/user1/
> +	install -p -m 644 file3 ${D}/usr/share/user3/
> +	install -p -m 644 file4 ${D}/usr/share/user3/
> +
> +	# The new users and groups are created before the do_install
> +	# step, so you are now free to make use of them:

To match the above split:

> +	chown -R user1 ${D}/usr/share/user1
> +	chown -R user3 ${D}/usr/share/user3
> +	chgrp group1 ${D}/usr/share/user1/file1
> +	chgrp group3 ${D}/usr/share/user1/file2
> +	chgrp group1 ${D}/usr/share/user3/file3
> +	chgrp group3 ${D}/usr/share/user3/file4

	chown -R user1 ${D}/usr/share/user1
	chown -R user3 ${D}/usr/share/user3
	chgrp group1 ${D}/usr/share/user1/file1
	chgrp group2 ${D}/usr/share/user1/file2
	chgrp group3 ${D}/usr/share/user3/file3
	chgrp group3 ${D}/usr/share/user3/file4

Since the user1 added groups 1 and 2..  while user3 only has group 3....

> +}
> +
> +PACKAGES =+ "${PN}-user3"

Moved the above line, so remove it here.

> +
> +FILES_${PN} = "/usr/share/user1/*"
> +FILES_${PN}-user3 = "/usr/share/user3/*"

This should now produce two split packages.  Each having different users and
groups being added.

> diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file1 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
> new file mode 100644
> index 0000000..e69de29
> diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file2 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
> new file mode 100644
> index 0000000..e69de29
> diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file3 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
> new file mode 100644
> index 0000000..e69de29
> diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file4 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
> new file mode 100644
> index 0000000..e69de29



^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 0/7] User/group creation at preinstall
  2011-05-31 19:06     ` Saul Wold
  (?)
@ 2011-05-31 19:09     ` Mark Hatle
  -1 siblings, 0 replies; 51+ messages in thread
From: Mark Hatle @ 2011-05-31 19:09 UTC (permalink / raw)
  To: poky

Other then the suggested changes to the example commit.  This looks good to me.

But I agree, it needs to go over oe-core for inclusion.

--Mark

On 5/31/11 2:06 PM, Saul Wold wrote:
> On 05/31/2011 11:45 AM, Koen Kooi wrote:
>> Shouldn't patches like this be sent to the oe-core list? It wouldn't have saved me from the selinux bug in shadow, though :)
>>
> Scott,
> 
> I would agree with Koen, this is a oe-core change, not a Poky only 
> change, please resend this request to the oe-core list.
> 
> Thanks
> 	Sau!
> 
> 
>> Op 31 mei 2011, om 20:13 heeft Scott Garman het volgende geschreven:
>>
>>> Hi Saul,
>>>
>>> This pull request includes everything needed to add the ability to
>>> create custom users and groups in our images/packages and the
>>> corresponding ability to set custom ownership permissions.
>>>
>>> There is a useradd-example.bb file in meta-skeleton which provides
>>> a heavily-commented example recipe to demonstrate how this feature
>>> can be used.
>>>
>>> I'd like to request that Mark Hatle and Richard do a code review of
>>> this and offer their Acked-by: support if they are happy with things.
>>>
>>> Once this gets into master, I'm happy to write up a short section for
>>> the Poky Reference Manual to document it in a more visible way.
>>>
>>> Scott
>>>
>>> The following changes since commit 1169f1b066d0028bd2ef7915440450bd42ef165e:
>>>
>>>   license.bbclass: Sane Parsing of licenses (2011-05-27 23:36:24 +0100)
>>>
>>> are available in the git repository at:
>>>   git://git.pokylinux.org/poky-contrib sgarman/user-group-creation
>>>   http://git.pokylinux.org/cgit.cgi/poky-contrib/log/?h=sgarman/user-group-creation
>>>
>>> Scott Garman (7):
>>>   shadow: recipe and patch cleanup
>>>   shadow: add a -native recipe with customized utilities
>>>   base-passwd: add -cross recipe with default login.defs
>>>   useradd.bbclass: new class for managing user/group permissions
>>>   useradd-example: example recipe for using inherit useradd
>>>   bitbake.conf: set PSEUDO_PASSWD within FAKEROOTENV
>>>   package_rpm.bbclass: make RPM use on-disk permissions
>>>
>>> .../recipes-skeleton/useradd/useradd-example.bb    |   59 +
>>> meta/classes/package_rpm.bbclass                   |    2 +
>>> meta/classes/useradd.bbclass                       |  136 ++
>>> meta/conf/bitbake.conf                             |    2 +-
>>> .../base-passwd/base-passwd-3.5.22/login.defs      |  386 ++++++
>>> .../base-passwd/base-passwd-cross_3.5.22.bb        |   53 +
>>> .../shadow/files/add_root_cmd_options.patch        | 1293 ++++++++++++++++++++
>>> .../files/shadow-4.1.3-dots-in-usernames.patch     |    4 +
>>> .../shadow-4.1.4.2-env-reset-keep-locale.patch     |    4 +
>>> .../files/shadow-4.1.4.2-groupmod-pam-check.patch  |    4 +
>>> .../files/shadow-4.1.4.2-su_no_sanitize_env.patch  |    4 +
>>> .../shadow/files/shadow.automake-1.11.patch        |    4 +
>>> .../shadow/shadow-native_4.1.4.3.bb                |   66 +
>>> meta/recipes-extended/shadow/shadow.inc            |  121 --
>>> meta/recipes-extended/shadow/shadow_4.1.4.3.bb     |  141 ++-
>>> 15 files changed, 2148 insertions(+), 131 deletions(-)
>>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
>>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
>>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
>>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
>>> create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
>>> create mode 100644 meta/classes/useradd.bbclass
>>> create mode 100644 meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
>>> create mode 100644 meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
>>> create mode 100644 meta/recipes-extended/shadow/files/add_root_cmd_options.patch
>>> create mode 100644 meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
>>> delete mode 100644 meta/recipes-extended/shadow/shadow.inc
>>>
>>> _______________________________________________
>>> poky mailing list
>>> poky@yoctoproject.org
>>> https://lists.yoctoproject.org/listinfo/poky
>>
>> _______________________________________________
>> poky mailing list
>> poky@yoctoproject.org
>> https://lists.yoctoproject.org/listinfo/poky
>>
> _______________________________________________
> poky mailing list
> poky@yoctoproject.org
> https://lists.yoctoproject.org/listinfo/poky



^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [poky] [PATCH 0/7] User/group creation at preinstall
  2011-05-31 19:06     ` Saul Wold
@ 2011-05-31 19:51       ` Scott Garman
  -1 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 19:51 UTC (permalink / raw)
  To: Saul Wold
  Cc: Koen Kooi, poky@yoctoproject.org Project,
	Patches and discussions about the oe-core layer

On 05/31/2011 12:06 PM, Saul Wold wrote:
> On 05/31/2011 11:45 AM, Koen Kooi wrote:
>> Shouldn't patches like this be sent to the oe-core list? It wouldn't
>> have saved me from the selinux bug in shadow, though :)
>>
> Scott,
>
> I would agree with Koen, this is a oe-core change, not a Poky only
> change, please resend this request to the oe-core list.

Sure, I'll resend it to oe-core.

That said, I have no idea what criteria should be used to determine 
which list to send things to, and I'm sure I'm not the only one. Is this 
documented anywhere?

Scott

-- 
Scott Garman
Embedded Linux Engineer - Yocto Project
Intel Open Source Technology Center



^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 0/7] User/group creation at preinstall
@ 2011-05-31 19:51       ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 19:51 UTC (permalink / raw)
  To: Saul Wold
  Cc: poky@yoctoproject.org Project,
	Patches and discussions about the oe-core layer

On 05/31/2011 12:06 PM, Saul Wold wrote:
> On 05/31/2011 11:45 AM, Koen Kooi wrote:
>> Shouldn't patches like this be sent to the oe-core list? It wouldn't
>> have saved me from the selinux bug in shadow, though :)
>>
> Scott,
>
> I would agree with Koen, this is a oe-core change, not a Poky only
> change, please resend this request to the oe-core list.

Sure, I'll resend it to oe-core.

That said, I have no idea what criteria should be used to determine 
which list to send things to, and I'm sure I'm not the only one. Is this 
documented anywhere?

Scott

-- 
Scott Garman
Embedded Linux Engineer - Yocto Project
Intel Open Source Technology Center


^ permalink raw reply	[flat|nested] 51+ messages in thread

* [PATCH 0/7] User/group creation at preinstall
@ 2011-05-31 19:53 ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 19:53 UTC (permalink / raw)
  To: openembedded-core

Hi Saul,

This pull request includes everything needed to add the ability to
create custom users and groups in our images/packages and the
corresponding ability to set custom ownership permissions. 

There is a useradd-example.bb file in meta-skeleton which provides
a heavily-commented example recipe to demonstrate how this feature
can be used.

I'd like to request that Mark Hatle and Richard do a code review of
this and offer their Acked-by: support if they are happy with things.

Once this gets into master, I'm happy to write up a short section for
the Poky Reference Manual to document it in a more visible way.

Scott

The following changes since commit 1169f1b066d0028bd2ef7915440450bd42ef165e:

  license.bbclass: Sane Parsing of licenses (2011-05-27 23:36:24 +0100)

are available in the git repository at:
  git://git.pokylinux.org/poky-contrib sgarman/user-group-creation
  http://git.pokylinux.org/cgit.cgi/poky-contrib/log/?h=sgarman/user-group-creation

Scott Garman (7):
  shadow: recipe and patch cleanup
  shadow: add a -native recipe with customized utilities
  base-passwd: add -cross recipe with default login.defs
  useradd.bbclass: new class for managing user/group permissions
  useradd-example: example recipe for using inherit useradd
  bitbake.conf: set PSEUDO_PASSWD within FAKEROOTENV
  package_rpm.bbclass: make RPM use on-disk permissions

 .../recipes-skeleton/useradd/useradd-example.bb    |   59 +
 meta/classes/package_rpm.bbclass                   |    2 +
 meta/classes/useradd.bbclass                       |  136 ++
 meta/conf/bitbake.conf                             |    2 +-
 .../base-passwd/base-passwd-3.5.22/login.defs      |  386 ++++++
 .../base-passwd/base-passwd-cross_3.5.22.bb        |   53 +
 .../shadow/files/add_root_cmd_options.patch        | 1293 ++++++++++++++++++++
 .../files/shadow-4.1.3-dots-in-usernames.patch     |    4 +
 .../shadow-4.1.4.2-env-reset-keep-locale.patch     |    4 +
 .../files/shadow-4.1.4.2-groupmod-pam-check.patch  |    4 +
 .../files/shadow-4.1.4.2-su_no_sanitize_env.patch  |    4 +
 .../shadow/files/shadow.automake-1.11.patch        |    4 +
 .../shadow/shadow-native_4.1.4.3.bb                |   66 +
 meta/recipes-extended/shadow/shadow.inc            |  121 --
 meta/recipes-extended/shadow/shadow_4.1.4.3.bb     |  141 ++-
 15 files changed, 2148 insertions(+), 131 deletions(-)
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
 create mode 100644 meta/classes/useradd.bbclass
 create mode 100644 meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
 create mode 100644 meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
 create mode 100644 meta/recipes-extended/shadow/files/add_root_cmd_options.patch
 create mode 100644 meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
 delete mode 100644 meta/recipes-extended/shadow/shadow.inc




^ permalink raw reply	[flat|nested] 51+ messages in thread

* [PATCH 1/7] shadow: recipe and patch cleanup
@ 2011-05-31 19:53   ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 19:53 UTC (permalink / raw)
  To: openembedded-core

Taking over maintenance of the shadow recipe. Cleaning it up in
preparation of adding a -native version that will be used to add
users/groups during postinstall.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 .../files/shadow-4.1.3-dots-in-usernames.patch     |    4 +
 .../shadow-4.1.4.2-env-reset-keep-locale.patch     |    4 +
 .../files/shadow-4.1.4.2-groupmod-pam-check.patch  |    4 +
 .../files/shadow-4.1.4.2-su_no_sanitize_env.patch  |    4 +
 .../shadow/files/shadow.automake-1.11.patch        |    4 +
 meta/recipes-extended/shadow/shadow.inc            |  121 -----------------
 meta/recipes-extended/shadow/shadow_4.1.4.3.bb     |  141 ++++++++++++++++++--
 7 files changed, 152 insertions(+), 130 deletions(-)
 delete mode 100644 meta/recipes-extended/shadow/shadow.inc

diff --git a/meta/recipes-extended/shadow/files/shadow-4.1.3-dots-in-usernames.patch b/meta/recipes-extended/shadow/files/shadow-4.1.3-dots-in-usernames.patch
index 7a2ff2e..a7bb0a9 100644
--- a/meta/recipes-extended/shadow/files/shadow-4.1.3-dots-in-usernames.patch
+++ b/meta/recipes-extended/shadow/files/shadow-4.1.3-dots-in-usernames.patch
@@ -9,6 +9,10 @@
 #
 # comment added by Kevin Tian <kevin.tian@intel.com>, 2010-08-11
 
+Upstream-Status: Pending
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
 Index: shadow-4.1.4.2/libmisc/chkname.c
 ===================================================================
 --- shadow-4.1.4.2.orig/libmisc/chkname.c	2009-04-28 12:14:04.000000000 -0700
diff --git a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-env-reset-keep-locale.patch b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-env-reset-keep-locale.patch
index 124065c..6514746 100644
--- a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-env-reset-keep-locale.patch
+++ b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-env-reset-keep-locale.patch
@@ -12,6 +12,10 @@
 http://bugs.gentoo.org/283725
 https://alioth.debian.org/tracker/index.php?func=detail&aid=311740&group_id=30580&atid=411480
 
+Upstream-Status: Pending
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
 Index: shadow-4.1.4.2/libmisc/env.c
 ===================================================================
 --- shadow-4.1.4.2.orig/libmisc/env.c	2009-04-27 13:07:56.000000000 -0700
diff --git a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-groupmod-pam-check.patch b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-groupmod-pam-check.patch
index 6682fe8..640200b 100644
--- a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-groupmod-pam-check.patch
+++ b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-groupmod-pam-check.patch
@@ -17,6 +17,10 @@ http://lists.alioth.debian.org/pipermail/pkg-shadow-devel/2009-November/007850.h
 	* NEWS, src/groupmod.c: Fixed groupmod when configured with
 	--enable-account-tools-setuid.
 
+Upstream-Status: Pending
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
 Index: shadow-4.1.4.2/src/groupmod.c
 ===================================================================
 --- shadow-4.1.4.2.orig/src/groupmod.c	2009-06-05 15:16:58.000000000 -0700
diff --git a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-su_no_sanitize_env.patch b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-su_no_sanitize_env.patch
index f67251c..0dc4d75 100644
--- a/meta/recipes-extended/shadow/files/shadow-4.1.4.2-su_no_sanitize_env.patch
+++ b/meta/recipes-extended/shadow/files/shadow-4.1.4.2-su_no_sanitize_env.patch
@@ -12,6 +12,10 @@
 http://bugs.gentoo.org/show_bug.cgi?id=301957
 https://alioth.debian.org/scm/browser.php?group_id=30580
 
+Upstream-Status: Pending
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
 Index: shadow-4.1.4.2/src/su.c
 ===================================================================
 --- shadow-4.1.4.2.orig/src/su.c	2009-07-23 13:38:56.000000000 -0700
diff --git a/meta/recipes-extended/shadow/files/shadow.automake-1.11.patch b/meta/recipes-extended/shadow/files/shadow.automake-1.11.patch
index 36d7be6..a793f09 100644
--- a/meta/recipes-extended/shadow/files/shadow.automake-1.11.patch
+++ b/meta/recipes-extended/shadow/files/shadow.automake-1.11.patch
@@ -11,6 +11,10 @@
 
 man_nopan is for !USE_PAM already included in man_MANS and automake-1.11 hates to install some file twice
 
+Upstream-Status: Pending
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
 diff -uNr shadow-4.1.4.2.orig/man/Makefile.am shadow-4.1.4.2/man/Makefile.am
 --- shadow-4.1.4.2.orig/man/Makefile.am	2009-03-14 15:40:10.000000000 +0100
 +++ shadow-4.1.4.2/man/Makefile.am	2010-04-02 07:31:17.000000000 +0200
diff --git a/meta/recipes-extended/shadow/shadow.inc b/meta/recipes-extended/shadow/shadow.inc
deleted file mode 100644
index 42f92a7..0000000
--- a/meta/recipes-extended/shadow/shadow.inc
+++ /dev/null
@@ -1,121 +0,0 @@
-DESCRIPTION = "Tools to change and administer password and group data."
-HOMEPAGE = "http://pkg-shadow.alioth.debian.org/"
-BUGTRACKER = "https://alioth.debian.org/tracker/?group_id=30580"
-SECTION = "base utils"
-LICENSE = "BSD | Artistic"
-LIC_FILES_CHKSUM = "file://COPYING;md5=08c553a87d4e51bbed50b20e0adcaede \
-                    file://src/passwd.c;firstline=8;endline=30;md5=2899a045e90511d0e043b85a7db7e2fe"
-
-PAM_PLUGINS = "  libpam-runtime \
-                 pam-plugin-faildelay \
-                 pam-plugin-securetty \
-                 pam-plugin-nologin \
-                 pam-plugin-env \
-                 pam-plugin-group \
-                 pam-plugin-limits \
-                 pam-plugin-lastlog \
-                 pam-plugin-motd \
-                 pam-plugin-mail \
-                 pam-plugin-shells \
-                 pam-plugin-rootok"
-                 
-DEPENDS = "${@base_contains('DISTRO_FEATURES', 'pam', 'libpam', '', d)}"
-RDEPENDS_${PN} = "${@base_contains('DISTRO_FEATURES', 'pam', '${PAM_PLUGINS}', '', d)}"
-
-# since we deduce from ${SERIAL_CONSOLE}
-PACKAGE_ARCH = "${MACHINE_ARCH}"
-
-# Additional Policy files for PAM
-PAM_SRC_URI = "file://pam.d/chfn \
-               file://pam.d/chpasswd \
-               file://pam.d/chsh \
-               file://pam.d/login \
-               file://pam.d/newusers \
-               file://pam.d/passwd \
-               file://pam.d/su"
-
-SRC_URI = "ftp://pkg-shadow.alioth.debian.org/pub/pkg-shadow/shadow-${PV}.tar.bz2 \
-           file://login_defs_pam.sed \
-           ${@base_contains('DISTRO_FEATURES', 'pam', '${PAM_SRC_URI}', '', d)} \
-           file://securetty"
-
-inherit autotools gettext
-
-EXTRA_OECONF += "--without-audit \
-                 --without-libcrack \
-                 ${@base_contains('DISTRO_FEATURES', 'pam', '--with-libpam', '--without-libpam', d)} \
-                 --without-selinux"
-
-do_install_append() {
-	# Ensure that the image has as /var/spool/mail dir so shadow can put mailboxes there if the user
-	# reconfigures Shadow to default (see sed below).
-	install -d ${D}${localstatedir}/spool/mail
-
-	if [ -e ${WORKDIR}/pam.d ]; then
-		install -d ${D}${sysconfdir}/pam.d/
-		install -m 0644 ${WORKDIR}/pam.d/* ${D}${sysconfdir}/pam.d/
-		# Remove defaults that are not used when supporting PAM
-		sed -i -f ${WORKDIR}/login_defs_pam.sed ${D}${sysconfdir}/login.defs
-	fi
-
-	# Enable CREATE_HOME by default.
-	sed -i 's/#CREATE_HOME/CREATE_HOME/g' ${D}${sysconfdir}/login.defs
-
-	# As we are on an embedded system ensure the users mailbox is in ~/ not
-	# /var/spool/mail by default as who knows where or how big /var is.
-	# The system MDA will set this later anyway.
-	sed -i 's/MAIL_DIR/#MAIL_DIR/g' ${D}${sysconfdir}/login.defs
-	sed -i 's/#MAIL_FILE/MAIL_FILE/g' ${D}${sysconfdir}/login.defs
-
-	# disable checking emails at all
-	sed -i 's/MAIL_CHECK_ENAB/#MAIL_CHECK_ENAB/g' ${D}${sysconfdir}/login.defs
-
-	# now we don't have a mail system. disable mail creation for now
-	sed -i 's:/bin/bash:/bin/sh:g' ${D}${sysconfdir}/default/useradd
-	sed -i '/^CREATE_MAIL_SPOOL/ s:^:#:' ${D}${sysconfdir}/default/useradd
-
-	install -d ${D}${sbindir} ${D}${base_sbindir} ${D}${base_bindir} 
-	for i in passwd chfn newgrp chsh ; do
-		mv ${D}${bindir}/$i ${D}${bindir}/$i.${PN}
-	done
-
-	mv ${D}${sbindir}/chpasswd ${D}${sbindir}/chpasswd.${PN}
-	mv ${D}${sbindir}/vigr ${D}${base_sbindir}/vigr.${PN}
-	mv ${D}${sbindir}/vipw ${D}${base_sbindir}/vipw.${PN}
-	mv ${D}${bindir}/login ${D}${base_bindir}/login.${PN}
-
-	# Ensure we add a suitable securetty file to the package that has most common embedded TTYs defined.
-	if [ ! -z "${SERIAL_CONSOLE}" ]; then
-	# our SERIAL_CONSOLE contains baud rate too and sometime -L option as well.
-	# the following pearl :) takes that and converts it into newline sepated tty's and appends
-	# them into securetty. So if a machine has a weird looking console device node (e.g. ttyAMA0) that securetty
-	# does not know then it will get appended to securetty and root login will be allowed on
-	# that console.
-		echo "${SERIAL_CONSOLE}" | sed -e 's/[0-9][0-9]\|\-L//g'|tr "[ ]" "[\n]"  >> ${WORKDIR}/securetty
-	fi
-	install -m 0400 ${WORKDIR}/securetty ${D}${sysconfdir}/securetty 
-}
-
-pkg_postinst_${PN} () {
-	update-alternatives --install ${bindir}/passwd passwd passwd.${PN} 200
-	update-alternatives --install ${sbindir}/chpasswd chpasswd chpasswd.${PN} 200
-	update-alternatives --install ${bindir}/chfn chfn chfn.${PN} 200
-	update-alternatives --install ${bindir}/newgrp newgrp newgrp.${PN} 200
-	update-alternatives --install ${bindir}/chsh chsh chsh.${PN} 200
-	update-alternatives --install ${base_bindir}/login login login.${PN} 200
-	update-alternatives --install ${base_sbindir}/vipw vipw vipw.${PN} 200
-	update-alternatives --install ${base_sbindir}/vigr vigr vigr.${PN} 200
-
-	if [ "x$D" != "x" ]; then
-		exit 1
-	fi  
-
-	pwconv
-	grpconv
-}
-
-pkg_prerm_${PN} () {
-	for i in passwd chpasswd chfn newgrp chsh login vipw vigr ; do
-		update-alternatives --remove $i $i.${PN}
-	done
-}
diff --git a/meta/recipes-extended/shadow/shadow_4.1.4.3.bb b/meta/recipes-extended/shadow/shadow_4.1.4.3.bb
index c8aa223..25b7bca 100644
--- a/meta/recipes-extended/shadow/shadow_4.1.4.3.bb
+++ b/meta/recipes-extended/shadow/shadow_4.1.4.3.bb
@@ -1,14 +1,137 @@
-require shadow.inc
+SUMMARY = "Tools to change and administer password and group data"
+DESCRIPTION = "Tools to change and administer password and group data"
+HOMEPAGE = "http://pkg-shadow.alioth.debian.org"
+BUGTRACKER = "https://alioth.debian.org/tracker/?group_id=30580"
+SECTION = "base utils"
+PRIORITY = "optional"
+LICENSE = "BSD | Artistic"
+LIC_FILES_CHKSUM = "file://COPYING;md5=08c553a87d4e51bbed50b20e0adcaede \
+                    file://src/passwd.c;firstline=8;endline=30;md5=2899a045e90511d0e043b85a7db7e2fe"
 
-PR = "r1"
+DEPENDS = "${@base_contains('DISTRO_FEATURES', 'pam', 'libpam', '', d)}"
+RDEPENDS_${PN} = "${@base_contains('DISTRO_FEATURES', 'pam', '${PAM_PLUGINS}', '', d)}"
+PR = "r2"
 
-SRC_URI += "file://shadow.automake-1.11.patch \
-	    file://shadow-4.1.3-dots-in-usernames.patch \
-	    file://shadow-4.1.4.2-env-reset-keep-locale.patch \
-	    file://shadow-4.1.4.2-groupmod-pam-check.patch \
-	    file://shadow-4.1.4.2-su_no_sanitize_env.patch"
+SRC_URI = "ftp://pkg-shadow.alioth.debian.org/pub/pkg-shadow/shadow-${PV}.tar.bz2 \
+           file://login_defs_pam.sed \
+           ${@base_contains('DISTRO_FEATURES', 'pam', '${PAM_SRC_URI}', '', d)} \
+           file://securetty \
+           file://shadow.automake-1.11.patch \
+           file://shadow-4.1.3-dots-in-usernames.patch \
+           file://shadow-4.1.4.2-env-reset-keep-locale.patch \
+           file://shadow-4.1.4.2-groupmod-pam-check.patch \
+           file://shadow-4.1.4.2-su_no_sanitize_env.patch"
 
 SRC_URI[md5sum] = "b8608d8294ac88974f27b20f991c0e79"
-SRC_URI[sha256sum] = "633f5bb4ea0c88c55f3642c97f9d25cbef74f82e0b4cf8d54e7ad6f9f9caa778"
+SRC_URI[sha256sum] = "633f5bb4ea0c88c55f3642c97f9d25cbef74f82e0b4cf8d54e7ad6f9f9caa778" 
 
-EXTRA_OECONF_libc-uclibc += " --with-nscd=no "
+inherit autotools gettext
+
+# Since we deduce our arch from ${SERIAL_CONSOLE}
+PACKAGE_ARCH = "${MACHINE_ARCH}"
+
+EXTRA_OECONF += "--without-audit \
+                 --without-libcrack \
+                 ${@base_contains('DISTRO_FEATURES', 'pam', '--with-libpam', '--without-libpam', d)} \
+                 --without-selinux"
+EXTRA_OECONF_libc-uclibc += "--with-nscd=no"
+
+PAM_PLUGINS = "libpam-runtime \
+               pam-plugin-faildelay \
+               pam-plugin-securetty \
+               pam-plugin-nologin \
+               pam-plugin-env \
+               pam-plugin-group \
+               pam-plugin-limits \
+               pam-plugin-lastlog \
+               pam-plugin-motd \
+               pam-plugin-mail \
+               pam-plugin-shells \
+               pam-plugin-rootok"
+                 
+# Additional Policy files for PAM
+PAM_SRC_URI = "file://pam.d/chfn \
+               file://pam.d/chpasswd \
+               file://pam.d/chsh \
+               file://pam.d/login \
+               file://pam.d/newusers \
+               file://pam.d/passwd \
+               file://pam.d/su"
+
+do_install_append() {
+	# Ensure that the image has as a /var/spool/mail dir so shadow can
+	# put mailboxes there if the user reconfigures shadow to its
+	# defaults (see sed below).
+	install -d ${D}${localstatedir}/spool/mail
+
+	if [ -e ${WORKDIR}/pam.d ]; then
+		install -d ${D}${sysconfdir}/pam.d/
+		install -m 0644 ${WORKDIR}/pam.d/* ${D}${sysconfdir}/pam.d/
+		# Remove defaults that are not used when supporting PAM.
+		sed -i -f ${WORKDIR}/login_defs_pam.sed ${D}${sysconfdir}/login.defs
+	fi
+
+	# Enable CREATE_HOME by default.
+	sed -i 's/#CREATE_HOME/CREATE_HOME/g' ${D}${sysconfdir}/login.defs
+
+	# As we are on an embedded system, ensure the users mailbox is in
+	# ~/ not /var/spool/mail by default, as who knows where or how big
+	# /var is. The system MDA will set this later anyway.
+	sed -i 's/MAIL_DIR/#MAIL_DIR/g' ${D}${sysconfdir}/login.defs
+	sed -i 's/#MAIL_FILE/MAIL_FILE/g' ${D}${sysconfdir}/login.defs
+
+	# Disable checking emails.
+	sed -i 's/MAIL_CHECK_ENAB/#MAIL_CHECK_ENAB/g' ${D}${sysconfdir}/login.defs
+
+	# Now we don't have a mail system. Disable mail creation for now.
+	sed -i 's:/bin/bash:/bin/sh:g' ${D}${sysconfdir}/default/useradd
+	sed -i '/^CREATE_MAIL_SPOOL/ s:^:#:' ${D}${sysconfdir}/default/useradd
+
+	install -d ${D}${sbindir} ${D}${base_sbindir} ${D}${base_bindir} 
+	for i in passwd chfn newgrp chsh ; do
+		mv ${D}${bindir}/$i ${D}${bindir}/$i.${PN}
+	done
+
+	mv ${D}${sbindir}/chpasswd ${D}${sbindir}/chpasswd.${PN}
+	mv ${D}${sbindir}/vigr ${D}${base_sbindir}/vigr.${PN}
+	mv ${D}${sbindir}/vipw ${D}${base_sbindir}/vipw.${PN}
+	mv ${D}${bindir}/login ${D}${base_bindir}/login.${PN}
+
+	# Ensure we add a suitable securetty file to the package that has
+	# most common embedded TTYs defined.
+	if [ ! -z "${SERIAL_CONSOLE}" ]; then
+		# Our SERIAL_CONSOLE contains a baud rate and sometimes a -L
+		# option as well. The following pearl :) takes that and converts
+		# it into newline-separated tty's and appends them into
+		# securetty. So if a machine has a weird looking console device
+		# node (e.g. ttyAMA0) that securetty does not know, it will get
+		# appended to securetty and root logins will be allowed on that
+		# console.
+		echo "${SERIAL_CONSOLE}" | sed -e 's/[0-9][0-9]\|\-L//g'|tr "[ ]" "[\n]"  >> ${WORKDIR}/securetty
+	fi
+	install -m 0400 ${WORKDIR}/securetty ${D}${sysconfdir}/securetty 
+}
+
+pkg_postinst_${PN} () {
+	update-alternatives --install ${bindir}/passwd passwd passwd.${PN} 200
+	update-alternatives --install ${sbindir}/chpasswd chpasswd chpasswd.${PN} 200
+	update-alternatives --install ${bindir}/chfn chfn chfn.${PN} 200
+	update-alternatives --install ${bindir}/newgrp newgrp newgrp.${PN} 200
+	update-alternatives --install ${bindir}/chsh chsh chsh.${PN} 200
+	update-alternatives --install ${base_bindir}/login login login.${PN} 200
+	update-alternatives --install ${base_sbindir}/vipw vipw vipw.${PN} 200
+	update-alternatives --install ${base_sbindir}/vigr vigr vigr.${PN} 200
+
+	if [ "x$D" != "x" ]; then
+		exit 1
+	fi  
+
+	pwconv
+	grpconv
+}
+
+pkg_prerm_${PN} () {
+	for i in passwd chpasswd chfn newgrp chsh login vipw vigr ; do
+		update-alternatives --remove $i $i.${PN}
+	done
+}
-- 
1.7.1




^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 2/7] shadow: add a -native recipe with customized utilities
@ 2011-05-31 19:53   ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 19:53 UTC (permalink / raw)
  To: openembedded-core

This adds a -native recipe for the shadow utilities.

The custom --root option allows the the following utilities to be
run within a chroot when invoked under pseudo:

* useradd
* groupadd
* usermod
* groupmod
* userdel
* groupdel
* passwd
* gpasswd
* pwconv
* pwunconv
* grpconv
* grpunconv

They can then be used to manipulate user and group account information
in target sysroots.

useradd was also modified to create home directories recursively when
necessary.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 .../shadow/files/add_root_cmd_options.patch        | 1293 ++++++++++++++++++++
 .../shadow/shadow-native_4.1.4.3.bb                |   66 +
 2 files changed, 1359 insertions(+), 0 deletions(-)
 create mode 100644 meta/recipes-extended/shadow/files/add_root_cmd_options.patch
 create mode 100644 meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb

diff --git a/meta/recipes-extended/shadow/files/add_root_cmd_options.patch b/meta/recipes-extended/shadow/files/add_root_cmd_options.patch
new file mode 100644
index 0000000..3511ebb
--- /dev/null
+++ b/meta/recipes-extended/shadow/files/add_root_cmd_options.patch
@@ -0,0 +1,1293 @@
+Add a --root command option to the following utilties:
+
+* useradd
+* groupadd
+* usermod
+* groupmod
+* userdel
+* groupdel
+* passwd
+* gpasswd
+* pwconv
+* pwunconv
+* grpconv
+* grpunconv
+
+This option allows the utilities to be chrooted when run under pseudo.
+They can then be used to manipulate user and group account information
+in target sysroots.
+
+Upstream-Status: Inappropriate [Other]
+Workaround is specific to our build system.
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
+diff -urN shadow-4.1.4.3.orig//src/gpasswd.c shadow-4.1.4.3//src/gpasswd.c
+--- shadow-4.1.4.3.orig//src/gpasswd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/gpasswd.c	2011-05-28 17:09:52.346013331 -0700
+@@ -63,6 +63,7 @@
+  * (/etc/gshadow present) */
+ static bool is_shadowgrp;
+ #endif
++static const char *newroot = "";
+ 
+ /* Flags set by options */
+ static bool aflg = false;
+@@ -97,6 +98,7 @@
+ static void usage (void);
+ static RETSIGTYPE catch_signals (int killed);
+ static bool is_valid_user_list (const char *users);
++static void process_root_flag (int argc, char **argv);
+ static void process_flags (int argc, char **argv);
+ static void check_flags (int argc, int opt_index);
+ static void open_files (void);
+@@ -136,6 +138,7 @@
+ 	           "Options:\n"
+ 	           "  -a, --add USER                add USER to GROUP\n"
+ 	           "  -d, --delete USER             remove USER from GROUP\n"
++	           "  -Q  --root CHROOT_DIR         directory to chroot into\n"
+ 	           "  -r, --remove-password         remove the GROUP's password\n"
+ 	           "  -R, --restrict                restrict access to GROUP to its members\n"
+ 	           "  -M, --members USER,...        set the list of members of GROUP\n"
+@@ -226,6 +229,55 @@
+ }
+ 
+ /*
++ * process_root_flag - chroot if given the --root option
++ *
++ * We do this outside of process_flags() because
++ * the is_shadow_pwd boolean needs to be set before
++ * process_flags(), and if we do need to chroot() we
++ * must do so before is_shadow_pwd gets set.
++ */
++static void process_root_flag (int argc, char **argv)
++{
++	/*
++	 * Parse the command line options.
++	 */
++	int flag;
++	int option_index = 0;
++	static struct option long_options[] = {
++		{"root", required_argument, NULL, 'Q'},
++		{NULL, 0, NULL, '\0'}
++	};
++
++	while ((flag = getopt_long (argc, argv, "a:A:d:gM:Q:rR", long_options, &option_index)) != -1) {
++		switch (flag) {
++		case 'Q':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
++		/* no-op on everything else - they will be hanled by process_flags() */
++		}
++	}
++}
++
++/*
+  * process_flags - process the command line options and arguments
+  */
+ static void process_flags (int argc, char **argv)
+@@ -235,6 +287,7 @@
+ 	static struct option long_options[] = {
+ 		{"add", required_argument, NULL, 'a'},
+ 		{"delete", required_argument, NULL, 'd'},
++		{"root", required_argument, NULL, 'Q'},
+ 		{"remove-password", no_argument, NULL, 'r'},
+ 		{"restrict", no_argument, NULL, 'R'},
+ 		{"administrators", required_argument, NULL, 'A'},
+@@ -242,7 +295,7 @@
+ 		{NULL, 0, NULL, '\0'}
+ 		};
+ 
+-	while ((flag = getopt_long (argc, argv, "a:A:d:gM:rR", long_options, &option_index)) != -1) {
++	while ((flag = getopt_long (argc, argv, "a:A:d:gM:Q:rR", long_options, &option_index)) != -1) {
+ 		switch (flag) {
+ 		case 'a':	/* add a user */
+ 			aflg = true;
+@@ -283,6 +336,9 @@
+ 			}
+ 			Mflg = true;
+ 			break;
++		case 'Q':
++			/* no-op since we handled this in process_root_flag() earlier */
++			break;
+ 		case 'r':	/* remove group password */
+ 			rflg = true;
+ 			break;
+@@ -995,6 +1051,8 @@
+ 	setbuf (stdout, NULL);
+ 	setbuf (stderr, NULL);
+ 
++	process_root_flag (argc, argv);
++
+ #ifdef SHADOWGRP
+ 	is_shadowgrp = sgr_file_present ();
+ #endif
+diff -urN shadow-4.1.4.3.orig//src/groupadd.c shadow-4.1.4.3//src/groupadd.c
+--- shadow-4.1.4.3.orig//src/groupadd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/groupadd.c	2011-05-28 17:09:52.346013331 -0700
+@@ -76,6 +76,7 @@
+ static gid_t group_id;
+ static /*@null@*/char *group_passwd;
+ static /*@null@*/char *empty_list = NULL;
++static const char *newroot = "";
+ 
+ static bool oflg = false;	/* permit non-unique group ID to be specified with -g */
+ static bool gflg = false;	/* ID value for the new group */
+@@ -120,6 +121,7 @@
+ 	(void) fputs (_("  -o, --non-unique              allow to create groups with duplicate\n"
+ 	                "                                (non-unique) GID\n"), stderr);
+ 	(void) fputs (_("  -p, --password PASSWORD       use this encrypted password for the new group\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
+ 	(void) fputs (_("  -r, --system                  create a system account\n"), stderr);
+ 	(void) fputs ("\n", stderr);
+ 	exit (E_USAGE);
+@@ -383,12 +385,13 @@
+ 		{"key", required_argument, NULL, 'K'},
+ 		{"non-unique", no_argument, NULL, 'o'},
+ 		{"password", required_argument, NULL, 'p'},
++		{"root", required_argument, NULL, 'R'},
+ 		{"system", no_argument, NULL, 'r'},
+ 		{NULL, 0, NULL, '\0'}
+ 	};
+ 
+ 	while ((c =
+-		getopt_long (argc, argv, "fg:hK:op:r", long_options,
++		getopt_long (argc, argv, "fg:hK:op:R:r", long_options,
+ 		             &option_index)) != -1) {
+ 		switch (c) {
+ 		case 'f':
+@@ -440,6 +443,28 @@
+ 			pflg = true;
+ 			group_passwd = optarg;
+ 			break;
++		case 'R':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
+ 		case 'r':
+ 			rflg = true;
+ 			break;
+diff -urN shadow-4.1.4.3.orig//src/groupdel.c shadow-4.1.4.3//src/groupdel.c
+--- shadow-4.1.4.3.orig//src/groupdel.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/groupdel.c	2011-05-28 17:09:52.346013331 -0700
+@@ -36,6 +36,7 @@
+ 
+ #include <ctype.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <grp.h>
+ #include <pwd.h>
+ #ifdef ACCT_TOOLS_SETUID
+@@ -59,6 +60,7 @@
+ 
+ static char *group_name;
+ static gid_t group_id = -1;
++static const char *newroot = "";
+ 
+ #ifdef	SHADOWGRP
+ static bool is_shadow_grp;
+@@ -70,12 +72,14 @@
+ /*@-exitarg@*/
+ #define E_SUCCESS	0	/* success */
+ #define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
+ #define E_NOTFOUND	6	/* specified group doesn't exist */
+ #define E_GROUP_BUSY	8	/* can't remove user's primary group */
+ #define E_GRP_UPDATE	10	/* can't update group file */
+ 
+ /* local function prototypes */
+ static void usage (void);
++static void process_flags (int argc, char **argv);
+ static void grp_update (void);
+ static void close_files (void);
+ static void open_files (void);
+@@ -86,11 +90,78 @@
+  */
+ static void usage (void)
+ {
+-	fputs (_("Usage: groupdel group\n"), stderr);
++	(void) fprintf (stderr,
++					_("Usage: groupdel [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -g, --group GROUP            group name to delete\n"), stderr);
++	(void) fputs (_("  -h, --help                   display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR        directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
+ 	exit (E_USAGE);
+ }
+ 
+ /*
++ * process_flags - perform command line argument setting
++ *
++ *	process_flags() interprets the command line arguments and sets
++ *	the values that the user will be created with accordingly. The
++ *	values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"group", required_argument, NULL, 'g'},
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "g:R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'g':
++				group_name = optarg;
++				break;
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++							_("%s: invalid chroot path '%s'\n"),
++							Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++							_("%s: chroot directory %s does not exist\n"),
++							Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++							_("%s: unable to chroot to directory %s\n"),
++							Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
++/*
+  * grp_update - update group file entries
+  *
+  *	grp_update() writes the new records to the group files.
+@@ -328,14 +399,14 @@
+ 	(void) bindtextdomain (PACKAGE, LOCALEDIR);
+ 	(void) textdomain (PACKAGE);
+ 
+-	if (argc != 2) {
++   if (argc == 1) {
+ 		usage ();
+ 	}
+ 
+-	group_name = argv[1];
+-
+ 	OPENLOG ("groupdel");
+ 
++	process_flags (argc, argv);
++
+ #ifdef ACCT_TOOLS_SETUID
+ #ifdef USE_PAM
+ 	{
+diff -urN shadow-4.1.4.3.orig//src/groupmod.c shadow-4.1.4.3//src/groupmod.c
+--- shadow-4.1.4.3.orig//src/groupmod.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/groupmod.c	2011-05-28 17:09:52.346013331 -0700
+@@ -79,6 +79,7 @@
+ static char *group_passwd;
+ static gid_t group_id;
+ static gid_t group_newid;
++static char *newroot = "";
+ 
+ struct cleanup_info_mod info_passwd;
+ struct cleanup_info_mod info_group;
+@@ -126,6 +127,7 @@
+ 	(void) fputs (_("  -o, --non-unique              allow to use a duplicate (non-unique) GID\n"), stderr);
+ 	(void) fputs (_("  -p, --password PASSWORD       change the password to this (encrypted)\n"
+ 	                "                                PASSWORD\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
+ 	(void) fputs ("\n", stderr);
+ 	exit (E_USAGE);
+ }
+@@ -346,10 +348,11 @@
+ 		{"new-name", required_argument, NULL, 'n'},
+ 		{"non-unique", no_argument, NULL, 'o'},
+ 		{"password", required_argument, NULL, 'p'},
++		{"root", required_argument, NULL, 'R'},
+ 		{NULL, 0, NULL, '\0'}
+ 	};
+ 	while ((c =
+-		getopt_long (argc, argv, "g:hn:op:",
++		getopt_long (argc, argv, "g:hn:op:R:",
+ 		             long_options, &option_index)) != -1) {
+ 		switch (c) {
+ 		case 'g':
+@@ -373,6 +376,28 @@
+ 			group_passwd = optarg;
+ 			pflg = true;
+ 			break;
++		case 'R':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
+ 		default:
+ 			usage ();
+ 		}
+diff -urN shadow-4.1.4.3.orig//src/grpconv.c shadow-4.1.4.3//src/grpconv.c
+--- shadow-4.1.4.3.orig//src/grpconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/grpconv.c	2011-05-28 17:09:52.346013331 -0700
+@@ -39,6 +39,7 @@
+ 
+ #include <errno.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <grp.h>
+ #include <stdio.h>
+ #include <stdlib.h>
+@@ -50,6 +51,14 @@
+ #ifdef SHADOWGRP
+ #include "groupio.h"
+ #include "sgroupio.h"
++
++/*
++ * exit status values
++ */
++/*@-exitarg@*/
++#define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
++
+ /*
+  * Global variables
+  */
+@@ -57,9 +66,12 @@
+ 
+ static bool gr_locked  = false;
+ static bool sgr_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -82,6 +94,77 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: grpconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ *	process_flags() interprets the command line arguments and sets
++ *	the values that the user will be created with accordingly. The
++ *	values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
+ int main (int argc, char **argv)
+ {
+ 	const struct group *gr;
+@@ -100,6 +183,8 @@
+ 
+ 	OPENLOG ("grpconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (gr_lock () == 0) {
+ 		fprintf (stderr,
+ 		         _("%s: cannot lock %s; try again later.\n"),
+diff -urN shadow-4.1.4.3.orig//src/grpunconv.c shadow-4.1.4.3//src/grpunconv.c
+--- shadow-4.1.4.3.orig//src/grpunconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/grpunconv.c	2011-05-28 17:09:52.346013331 -0700
+@@ -43,6 +43,7 @@
+ #include <stdlib.h>
+ #include <string.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <time.h>
+ #include <unistd.h>
+ #include <grp.h>
+@@ -51,6 +52,14 @@
+ #ifdef SHADOWGRP
+ #include "groupio.h"
+ #include "sgroupio.h"
++
++/*
++ * exit status values
++ */
++/*@-exitarg@*/
++#define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
++
+ /*
+  * Global variables
+  */
+@@ -58,9 +67,12 @@
+ 
+ static bool gr_locked  = false;
+ static bool sgr_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -83,6 +95,77 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: grpunconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ * process_flags() interprets the command line arguments and sets
++ * the values that the user will be created with accordingly. The
++ * values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
+ int main (int argc, char **argv)
+ {
+ 	const struct group *gr;
+@@ -100,6 +183,8 @@
+ 
+ 	OPENLOG ("grpunconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (sgr_file_present () == 0) {
+ 		exit (0);	/* no /etc/gshadow, nothing to do */
+ 	}
+diff -urN shadow-4.1.4.3.orig//src/passwd.c shadow-4.1.4.3//src/passwd.c
+--- shadow-4.1.4.3.orig//src/passwd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/passwd.c	2011-05-28 17:09:52.346013331 -0700
+@@ -75,6 +75,7 @@
+ static char *name;		/* The name of user whose password is being changed */
+ static char *myname;		/* The current user's name */
+ static bool amroot;		/* The caller's real UID was 0 */
++static const char *newroot = "";
+ 
+ static bool
+     aflg = false,			/* -a - show status for all users */
+@@ -174,6 +175,7 @@
+ 	         "  -n, --mindays MIN_DAYS        set minimum number of days before password\n"
+ 	         "                                change to MIN_DAYS\n"
+ 	         "  -q, --quiet                   quiet mode\n"
++	         "  -R, --root CHROOT_DIR         directory to chroot into\n"
+ 	         "  -r, --repository REPOSITORY   change password in REPOSITORY repository\n"
+ 	         "  -S, --status                  report password status on the named account\n"
+ 	         "  -u, --unlock                  unlock the password of the named account\n"
+@@ -803,6 +805,7 @@
+ 			{"lock", no_argument, NULL, 'l'},
+ 			{"mindays", required_argument, NULL, 'n'},
+ 			{"quiet", no_argument, NULL, 'q'},
++			{"root", required_argument, NULL, 'R'},
+ 			{"repository", required_argument, NULL, 'r'},
+ 			{"status", no_argument, NULL, 'S'},
+ 			{"unlock", no_argument, NULL, 'u'},
+@@ -811,7 +814,7 @@
+ 			{NULL, 0, NULL, '\0'}
+ 		};
+ 
+-		while ((c = getopt_long (argc, argv, "adei:kln:qr:Suw:x:",
++		while ((c = getopt_long (argc, argv, "adei:kln:qR:r:Suw:x:",
+ 		                         long_options, &option_index)) != -1) {
+ 			switch (c) {
+ 			case 'a':
+@@ -858,6 +861,28 @@
+ 			case 'q':
+ 				qflg = true;	/* ok for users */
+ 				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++				            _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
+ 			case 'r':
+ 				/* -r repository (files|nis|nisplus) */
+ 				/* only "files" supported for now */
+diff -urN shadow-4.1.4.3.orig//src/pwconv.c shadow-4.1.4.3//src/pwconv.c
+--- shadow-4.1.4.3.orig//src/pwconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/pwconv.c	2011-05-28 17:09:52.346013331 -0700
+@@ -59,6 +59,7 @@
+ 
+ #include <errno.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <pwd.h>
+ #include <stdio.h>
+ #include <stdlib.h>
+@@ -79,6 +80,7 @@
+ #define E_SUCCESS	0	/* success */
+ #define E_NOPERM	1	/* permission denied */
+ #define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
+ #define E_FAILURE	3	/* unexpected failure, nothing done */
+ #define E_MISSING	4	/* unexpected failure, passwd file missing */
+ #define E_PWDBUSY	5	/* passwd file(s) busy */
+@@ -90,9 +92,12 @@
+ 
+ static bool spw_locked = false;
+ static bool pw_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -115,6 +120,77 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: pwconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ *	process_flags() interprets the command line arguments and sets
++ *	the values that the user will be created with accordingly. The
++ *	values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
+ int main (int argc, char **argv)
+ {
+ 	const struct passwd *pw;
+@@ -122,9 +198,6 @@
+ 	const struct spwd *sp;
+ 	struct spwd spent;
+ 
+-	if (1 != argc) {
+-		(void) fputs (_("Usage: pwconv\n"), stderr);
+-	}
+ 	Prog = Basename (argv[0]);
+ 
+ 	(void) setlocale (LC_ALL, "");
+@@ -133,6 +206,8 @@
+ 
+ 	OPENLOG ("pwconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (pw_lock () == 0) {
+ 		fprintf (stderr,
+ 		         _("%s: cannot lock %s; try again later.\n"),
+diff -urN shadow-4.1.4.3.orig//src/pwunconv.c shadow-4.1.4.3//src/pwunconv.c
+--- shadow-4.1.4.3.orig//src/pwunconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/pwunconv.c	2011-05-28 17:09:52.356013600 -0700
+@@ -35,6 +35,7 @@
+ #ident "$Id: pwunconv.c 2852 2009-04-30 21:44:35Z nekral-guest $"
+ 
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <pwd.h>
+ #include <stdio.h>
+ #include <sys/types.h>
+@@ -46,15 +47,24 @@
+ #include "shadowio.h"
+ 
+ /*
++ * exit status values
++ */
++/*@-exitarg@*/
++#define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
++/*
+  * Global variables
+  */
+ char *Prog;
+ 
+ static bool spw_locked = false;
+ static bool pw_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -75,6 +85,76 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: pwunconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ * process_flags() interprets the command line arguments and sets
++ * the values that the user will be created with accordingly. The
++ * values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
+ 
+ int main (int argc, char **argv)
+ {
+@@ -93,6 +173,8 @@
+ 
+ 	OPENLOG ("pwunconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (!spw_file_present ()) {
+ 		/* shadow not installed, do nothing */
+ 		exit (0);
+diff -urN shadow-4.1.4.3.orig//src/useradd.c shadow-4.1.4.3//src/useradd.c
+--- shadow-4.1.4.3.orig//src/useradd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/useradd.c	2011-05-28 17:10:25.446909971 -0700
+@@ -112,6 +112,7 @@
+ #ifdef WITH_SELINUX
+ static const char *user_selinux = "";
+ #endif
++static const char *newroot = "";
+ 
+ static long user_expire = -1;
+ static bool is_shadow_pwd;
+@@ -189,6 +190,7 @@
+ static void new_spent (struct spwd *);
+ static void grp_update (void);
+ 
++static void process_root_flag (int argc, char **argv);
+ static void process_flags (int argc, char **argv);
+ static void close_files (void);
+ static void open_files (void);
+@@ -711,6 +713,7 @@
+ 	(void) fputs (_("  -o, --non-unique              allow to create users with duplicate\n"
+ 	                "                                (non-unique) UID\n"), stderr);
+ 	(void) fputs (_("  -p, --password PASSWORD       encrypted password of the new account\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
+ 	(void) fputs (_("  -r, --system                  create a system account\n"), stderr);
+ 	(void) fputs (_("  -s, --shell SHELL             login shell of the new account\n"), stderr);
+ 	(void) fputs (_("  -u, --uid UID                 user ID of the new account\n"), stderr);
+@@ -943,6 +946,59 @@
+ }
+ 
+ /*
++ * process_root_flag - chroot if given the --root option
++ *
++ * We do this outside of process_flags() because
++ * the is_shadow_pwd boolean needs to be set before
++ * process_flags(), and if we do need to chroot() we
++ * must do so before is_shadow_pwd gets set.
++ */
++static void process_root_flag (int argc, char **argv)
++{
++	/*
++	 * Parse the command line options.
++	 */
++	int c;
++	static struct option long_options[] = {
++		{"root", required_argument, NULL, 'R'},
++		{NULL, 0, NULL, '\0'}
++	};
++	while ((c = getopt_long (argc, argv,
++#ifdef WITH_SELINUX
++	                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:UZ:",
++#else
++	                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:U",
++#endif
++	                         long_options, NULL)) != -1) {
++		switch (c) {
++		case 'R':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
++		/* no-op on everything else - they will be hanled by process_flags() */
++		}
++	}
++}
++
++/*
+  * process_flags - perform command line argument setting
+  *
+  *	process_flags() interprets the command line arguments and sets
+@@ -978,6 +1034,7 @@
+ 			{"no-user-group", no_argument, NULL, 'N'},
+ 			{"non-unique", no_argument, NULL, 'o'},
+ 			{"password", required_argument, NULL, 'p'},
++			{"root", required_argument, NULL, 'R'},
+ 			{"system", no_argument, NULL, 'r'},
+ 			{"shell", required_argument, NULL, 's'},
+ #ifdef WITH_SELINUX
+@@ -989,9 +1046,9 @@
+ 		};
+ 		while ((c = getopt_long (argc, argv,
+ #ifdef WITH_SELINUX
+-		                         "b:c:d:De:f:g:G:k:K:lmMNop:rs:u:UZ:",
++		                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:UZ:",
+ #else
+-		                         "b:c:d:De:f:g:G:k:K:lmMNop:rs:u:U",
++		                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:U",
+ #endif
+ 		                         long_options, NULL)) != -1) {
+ 			switch (c) {
+@@ -1156,6 +1213,9 @@
+ 				}
+ 				user_pass = optarg;
+ 				break;
++			case 'R':
++				/* no-op since we handled this in process_root_flag() earlier */
++				break;
+ 			case 'r':
+ 				rflg = true;
+ 				break;
+@@ -1748,8 +1808,16 @@
+ #ifdef WITH_SELINUX
+ 		selinux_file_context (user_home);
+ #endif
+-		/* XXX - create missing parent directories.  --marekm */
+-		if (mkdir (user_home, 0) != 0) {
++		/* shell out to invoke mkdir -p 
++		 * creating a subshell under pseudo's chroot() breaks the jail
++		 * (bug in pseudo), so make sure we include the full host path
++		 * to the sysroot when the --root option is in use.
++		 */
++		int sysroot_path_len = strlen(newroot);
++		int home_path_len = strlen(user_home);
++		char cmd[sysroot_path_len + home_path_len + 10];
++		sprintf(cmd, "mkdir -p %s%s", newroot, user_home);
++		if (system (cmd) != 0) {
+ 			fprintf (stderr,
+ 			         _("%s: cannot create directory %s\n"),
+ 			         Prog, user_home);
+@@ -1861,6 +1929,7 @@
+ 	 */
+ 	user_groups[0] = (char *) 0;
+ 
++	process_root_flag (argc, argv);
+ 
+ 	is_shadow_pwd = spw_file_present ();
+ #ifdef SHADOWGRP
+diff -urN shadow-4.1.4.3.orig//src/userdel.c shadow-4.1.4.3//src/userdel.c
+--- shadow-4.1.4.3.orig//src/userdel.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/userdel.c	2011-05-28 17:09:52.356013600 -0700
+@@ -79,6 +79,7 @@
+ static char *user_name;
+ static uid_t user_id;
+ static char *user_home;
++static const char *newroot = "";
+ 
+ static bool fflg = false;
+ static bool rflg = false;
+@@ -119,6 +120,7 @@
+ 	         "  -f, --force                   force removal of files,\n"
+ 	         "                                even if not owned by user\n"
+ 	         "  -h, --help                    display this help message and exit\n"
++	         "  -R, --root CHROOT_DIR         directory to chroot into\n"
+ 	         "  -r, --remove                  remove home directory and mail spool\n"
+ 	         "\n"), stderr);
+ 	exit (E_USAGE);
+@@ -768,12 +770,34 @@
+ 			{"remove", no_argument, NULL, 'r'},
+ 			{NULL, 0, NULL, '\0'}
+ 		};
+-		while ((c = getopt_long (argc, argv, "fhr",
++		while ((c = getopt_long (argc, argv, "fhR:r",
+ 		                         long_options, NULL)) != -1) {
+ 			switch (c) {
+ 			case 'f':	/* force remove even if not owned by user */
+ 				fflg = true;
+ 				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
+ 			case 'r':	/* remove home dir and mailbox */
+ 				rflg = true;
+ 				break;
+diff -urN shadow-4.1.4.3.orig//src/usermod.c shadow-4.1.4.3//src/usermod.c
+--- shadow-4.1.4.3.orig//src/usermod.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/usermod.c	2011-05-28 17:09:52.356013600 -0700
+@@ -110,6 +110,7 @@
+ static long user_newinactive;
+ static long sys_ngroups;
+ static char **user_groups;	/* NULL-terminated list */
++static const char *newroot = "";
+ 
+ static bool
+     aflg = false,		/* append to existing secondary group set */
+@@ -164,6 +165,7 @@
+ #endif
+ static void grp_update (void);
+ 
++static void process_root_flag (int, char **);
+ static void process_flags (int, char **);
+ static void close_files (void);
+ static void open_files (void);
+@@ -323,6 +325,7 @@
+ 	         "                                new location (use only with -d)\n"
+ 	         "  -o, --non-unique              allow using duplicate (non-unique) UID\n"
+ 	         "  -p, --password PASSWORD       use encrypted password for the new password\n"
++	         "  -R  --root CHROOT_DIR         directory to chroot into\n"
+ 	         "  -s, --shell SHELL             new login shell for the user account\n"
+ 	         "  -u, --uid UID                 new UID for the user account\n"
+ 	         "  -U, --unlock                  unlock the user account\n"
+@@ -802,6 +805,60 @@
+ }
+ 
+ /*
++ * process_root_flag - chroot if given the --root option
++ *
++ * We do this outside of process_flags() because
++ * the is_shadow_pwd boolean needs to be set before
++ * process_flags(), and if we do need to chroot() we
++ * must do so before is_shadow_pwd gets set.
++ */
++static void process_root_flag (int argc, char **argv)
++{
++	/*
++	 * Parse the command line options.
++	 */
++	int c;
++	static struct option long_options[] = {
++		{"root", required_argument, NULL, 'R'},
++		{NULL, 0, NULL, '\0'}
++	};
++	while ((c = getopt_long (argc, argv,
++#ifdef WITH_SELINUX
++                             "ac:d:e:f:g:G:hl:Lmop:R:s:u:UZ:",
++#else
++	                         "ac:d:e:f:g:G:hl:Lmop:R:s:u:U",
++#endif
++	                         long_options, NULL)) != -1) {
++		switch (c) {
++		case 'R':
++			if (    (!VALID (optarg) ) 
++				|| (   ('/' != optarg[0]) ) ) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
++		/* no-op on everything else - they will be hanled by process_flags() */
++		}
++	}
++}
++
++/*
+  * process_flags - perform command line argument setting
+  *
+  *	process_flags() interprets the command line arguments and sets the
+@@ -895,6 +952,7 @@
+ 			{"move-home", no_argument, NULL, 'm'},
+ 			{"non-unique", no_argument, NULL, 'o'},
+ 			{"password", required_argument, NULL, 'p'},
++			{"root", required_argument, NULL, 'R'},
+ #ifdef WITH_SELINUX
+ 			{"selinux-user", required_argument, NULL, 'Z'},
+ #endif
+@@ -905,9 +963,9 @@
+ 		};
+ 		while ((c = getopt_long (argc, argv,
+ #ifdef WITH_SELINUX
+-			                 "ac:d:e:f:g:G:hl:Lmop:s:u:UZ:",
++			                 "ac:d:e:f:g:G:hl:Lmop:R:s:u:UZ:",
+ #else
+-			                 "ac:d:e:f:g:G:hl:Lmop:s:u:U",
++			                 "ac:d:e:f:g:G:hl:Lmop:R:s:u:U",
+ #endif
+ 			                 long_options, NULL)) != -1) {
+ 			switch (c) {
+@@ -999,6 +1057,9 @@
+ 				user_pass = optarg;
+ 				pflg = true;
+ 				break;
++			case 'R':
++				/* no-op since we handled this in process_root_flag() earlier */
++				break;
+ 			case 's':
+ 				if (!VALID (optarg)) {
+ 					fprintf (stderr,
+@@ -1715,6 +1776,8 @@
+ 
+ 	OPENLOG ("usermod");
+ 
++	process_root_flag (argc, argv);
++
+ 	is_shadow_pwd = spw_file_present ();
+ #ifdef SHADOWGRP
+ 	is_shadow_grp = sgr_file_present ();
diff --git a/meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb b/meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
new file mode 100644
index 0000000..2f93e05
--- /dev/null
+++ b/meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
@@ -0,0 +1,66 @@
+SUMMARY = "Tools to change and administer password and group data"
+DESCRIPTION = "Tools to change and administer password and group data"
+HOMEPAGE = "http://pkg-shadow.alioth.debian.org"
+BUGTRACKER = "https://alioth.debian.org/tracker/?group_id=30580"
+SECTION = "base utils"
+PRIORITY = "optional"
+LICENSE = "BSD | Artistic"
+LIC_FILES_CHKSUM = "file://COPYING;md5=08c553a87d4e51bbed50b20e0adcaede \
+                    file://src/passwd.c;firstline=8;endline=30;md5=2899a045e90511d0e043b85a7db7e2fe"
+
+PR = "r0"
+
+SRC_URI = "ftp://pkg-shadow.alioth.debian.org/pub/pkg-shadow/shadow-${PV}.tar.bz2 \
+           file://shadow.automake-1.11.patch \
+           file://shadow-4.1.3-dots-in-usernames.patch \
+           file://shadow-4.1.4.2-env-reset-keep-locale.patch \
+           file://add_root_cmd_options.patch"
+
+SRC_URI[md5sum] = "b8608d8294ac88974f27b20f991c0e79"
+SRC_URI[sha256sum] = "633f5bb4ea0c88c55f3642c97f9d25cbef74f82e0b4cf8d54e7ad6f9f9caa778" 
+
+inherit autotools gettext native
+
+EXTRA_OECONF += "--without-audit \
+                 --without-libcrack \
+                 --without-libpam \
+                 --without-selinux"
+
+do_install_append() {
+	# Enable CREATE_HOME by default.
+	sed -i 's/#CREATE_HOME/CREATE_HOME/g' ${D}${sysconfdir}/login.defs
+
+	# As we are on an embedded system, ensure the users mailbox is in
+	# ~/ not /var/spool/mail by default, as who knows where or how big
+	# /var is. The system MDA will set this later anyway.
+	sed -i 's/MAIL_DIR/#MAIL_DIR/g' ${D}${sysconfdir}/login.defs
+	sed -i 's/#MAIL_FILE/MAIL_FILE/g' ${D}${sysconfdir}/login.defs
+
+	# Disable checking emails.
+	sed -i 's/MAIL_CHECK_ENAB/#MAIL_CHECK_ENAB/g' ${D}${sysconfdir}/login.defs
+
+	# Now we don't have a mail system. Disable mail creation for now.
+	sed -i 's:/bin/bash:/bin/sh:g' ${D}${sysconfdir}/default/useradd
+	sed -i '/^CREATE_MAIL_SPOOL/ s:^:#:' ${D}${sysconfdir}/default/useradd
+
+	install -d ${D}${sbindir} ${D}${base_sbindir} ${D}${base_bindir} 
+	for i in passwd chfn newgrp chsh ; do
+		mv ${D}${bindir}/$i ${D}${bindir}/$i.${PN}
+	done
+
+	mv ${D}${sbindir}/chpasswd ${D}${sbindir}/chpasswd.${PN}
+}
+
+pkg_postinst_${PN} () {
+	update-alternatives --install ${bindir}/passwd passwd passwd.${PN} 200
+	update-alternatives --install ${sbindir}/chpasswd chpasswd chpasswd.${PN} 200
+	update-alternatives --install ${bindir}/chfn chfn chfn.${PN} 200
+	update-alternatives --install ${bindir}/newgrp newgrp newgrp.${PN} 200
+	update-alternatives --install ${bindir}/chsh chsh chsh.${PN} 200
+}
+
+pkg_prerm_${PN} () {
+	for i in passwd chpasswd chfn newgrp chsh ; do
+		update-alternatives --remove $i $i.${PN}
+	done
+}
-- 
1.7.1




^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 3/7] base-passwd: add -cross recipe with default login.defs
@ 2011-05-31 19:53   ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 19:53 UTC (permalink / raw)
  To: openembedded-core

The -cross version of the recipe is needed in order to set up
user and group account information in the target machine sysroot.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 .../base-passwd/base-passwd-3.5.22/login.defs      |  386 ++++++++++++++++++++
 .../base-passwd/base-passwd-cross_3.5.22.bb        |   53 +++
 2 files changed, 439 insertions(+), 0 deletions(-)
 create mode 100644 meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
 create mode 100644 meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb

diff --git a/meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs b/meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
new file mode 100644
index 0000000..1d392ac
--- /dev/null
+++ b/meta/recipes-core/base-passwd/base-passwd-3.5.22/login.defs
@@ -0,0 +1,386 @@
+#
+# /etc/login.defs - Configuration control definitions for the shadow package.
+#
+#	$Id: login.defs 3038 2009-07-23 20:41:35Z nekral-guest $
+#
+
+#
+# Delay in seconds before being allowed another attempt after a login failure
+# Note: When PAM is used, some modules may enfore a minimal delay (e.g.
+#       pam_unix enforces a 2s delay)
+#
+FAIL_DELAY		3
+
+#
+# Enable logging and display of /var/log/faillog login failure info.
+#
+FAILLOG_ENAB		yes
+
+#
+# Enable display of unknown usernames when login failures are recorded.
+#
+LOG_UNKFAIL_ENAB	no
+
+#
+# Enable logging of successful logins
+#
+LOG_OK_LOGINS		no
+
+#
+# Enable logging and display of /var/log/lastlog login time info.
+#
+LASTLOG_ENAB		yes
+
+#
+# Enable checking and display of mailbox status upon login.
+#
+# Disable if the shell startup files already check for mail
+# ("mailx -e" or equivalent).
+#
+#MAIL_CHECK_ENAB		yes
+
+#
+# Enable additional checks upon password changes.
+#
+OBSCURE_CHECKS_ENAB	yes
+
+#
+# Enable checking of time restrictions specified in /etc/porttime.
+#
+PORTTIME_CHECKS_ENAB	yes
+
+#
+# Enable setting of ulimit, umask, and niceness from passwd gecos field.
+#
+QUOTAS_ENAB		yes
+
+#
+# Enable "syslog" logging of su activity - in addition to sulog file logging.
+# SYSLOG_SG_ENAB does the same for newgrp and sg.
+#
+SYSLOG_SU_ENAB		yes
+SYSLOG_SG_ENAB		yes
+
+#
+# If defined, either full pathname of a file containing device names or
+# a ":" delimited list of device names.  Root logins will be allowed only
+# upon these devices.
+#
+CONSOLE		/etc/securetty
+#CONSOLE	console:tty01:tty02:tty03:tty04
+
+#
+# If defined, all su activity is logged to this file.
+#
+#SULOG_FILE	/var/log/sulog
+
+#
+# If defined, ":" delimited list of "message of the day" files to
+# be displayed upon login.
+#
+MOTD_FILE	/etc/motd
+#MOTD_FILE	/etc/motd:/usr/lib/news/news-motd
+
+#
+# If defined, this file will be output before each login prompt.
+#
+#ISSUE_FILE	/etc/issue
+
+#
+# If defined, file which maps tty line to TERM environment parameter.
+# Each line of the file is in a format something like "vt100  tty01".
+#
+#TTYTYPE_FILE	/etc/ttytype
+
+#
+# If defined, login failures will be logged here in a utmp format.
+# last, when invoked as lastb, will read /var/log/btmp, so...
+#
+FTMP_FILE	/var/log/btmp
+
+#
+# If defined, name of file whose presence which will inhibit non-root
+# logins.  The contents of this file should be a message indicating
+# why logins are inhibited.
+#
+NOLOGINS_FILE	/etc/nologin
+
+#
+# If defined, the command name to display when running "su -".  For
+# example, if this is defined as "su" then a "ps" will display the
+# command is "-su".  If not defined, then "ps" would display the
+# name of the shell actually being run, e.g. something like "-sh".
+#
+SU_NAME		su
+
+#
+# *REQUIRED*
+#   Directory where mailboxes reside, _or_ name of file, relative to the
+#   home directory.  If you _do_ define both, #MAIL_DIR takes precedence.
+#
+#MAIL_DIR	/var/spool/mail
+MAIL_FILE	.mail
+
+#
+# If defined, file which inhibits all the usual chatter during the login
+# sequence.  If a full pathname, then hushed mode will be enabled if the
+# user's name or shell are found in the file.  If not a full pathname, then
+# hushed mode will be enabled if the file exists in the user's home directory.
+#
+HUSHLOGIN_FILE	.hushlogin
+#HUSHLOGIN_FILE	/etc/hushlogins
+
+#
+# If defined, either a TZ environment parameter spec or the
+# fully-rooted pathname of a file containing such a spec.
+#
+#ENV_TZ		TZ=CST6CDT
+#ENV_TZ		/etc/tzname
+
+#
+# If defined, an HZ environment parameter spec.
+#
+# for Linux/x86
+ENV_HZ		HZ=100
+# For Linux/Alpha...
+#ENV_HZ		HZ=1024
+
+#
+# *REQUIRED*  The default PATH settings, for superuser and normal users.
+#
+# (they are minimal, add the rest in the shell startup files)
+ENV_SUPATH	PATH=/sbin:/bin:/usr/sbin:/usr/bin
+ENV_PATH	PATH=/bin:/usr/bin
+
+#
+# Terminal permissions
+#
+#	TTYGROUP	Login tty will be assigned this group ownership.
+#	TTYPERM		Login tty will be set to this permission.
+#
+# If you have a "write" program which is "setgid" to a special group
+# which owns the terminals, define TTYGROUP to the group number and
+# TTYPERM to 0620.  Otherwise leave TTYGROUP commented out and assign
+# TTYPERM to either 622 or 600.
+#
+TTYGROUP	tty
+TTYPERM		0600
+
+#
+# Login configuration initializations:
+#
+#	ERASECHAR	Terminal ERASE character ('\010' = backspace).
+#	KILLCHAR	Terminal KILL character ('\025' = CTRL/U).
+#	ULIMIT		Default "ulimit" value.
+#
+# The ERASECHAR and KILLCHAR are used only on System V machines.
+# The ULIMIT is used only if the system supports it.
+# (now it works with setrlimit too; ulimit is in 512-byte units)
+#
+# Prefix these values with "0" to get octal, "0x" to get hexadecimal.
+#
+ERASECHAR	0177
+KILLCHAR	025
+#ULIMIT		2097152
+
+# Default initial "umask" value for non-PAM enabled systems.
+# UMASK is also used by useradd and newusers to set the mode of new home
+# directories.
+# 022 is the default value, but 027, or even 077, could be considered
+# better for privacy. There is no One True Answer here: each sysadmin
+# must make up her mind.
+UMASK		022
+
+#
+# Password aging controls:
+#
+#	PASS_MAX_DAYS	Maximum number of days a password may be used.
+#	PASS_MIN_DAYS	Minimum number of days allowed between password changes.
+#	PASS_MIN_LEN	Minimum acceptable password length.
+#	PASS_WARN_AGE	Number of days warning given before a password expires.
+#
+PASS_MAX_DAYS	99999
+PASS_MIN_DAYS	0
+PASS_MIN_LEN	5
+PASS_WARN_AGE	7
+
+#
+# If "yes", the user must be listed as a member of the first gid 0 group
+# in /etc/group (called "root" on most Linux systems) to be able to "su"
+# to uid 0 accounts.  If the group doesn't exist or is empty, no one
+# will be able to "su" to uid 0.
+#
+SU_WHEEL_ONLY	no
+
+#
+# If compiled with cracklib support, where are the dictionaries
+#
+CRACKLIB_DICTPATH	/var/cache/cracklib/cracklib_dict
+
+#
+# Min/max values for automatic uid selection in useradd
+#
+UID_MIN			 1000
+UID_MAX			60000
+# System accounts
+SYS_UID_MIN		  101
+SYS_UID_MAX		  999
+
+#
+# Min/max values for automatic gid selection in groupadd
+#
+GID_MIN			 1000
+GID_MAX			60000
+# System accounts
+SYS_GID_MIN		  101
+SYS_GID_MAX		  999
+
+#
+# Max number of login retries if password is bad
+#
+LOGIN_RETRIES		5
+
+#
+# Max time in seconds for login
+#
+LOGIN_TIMEOUT		60
+
+#
+# Maximum number of attempts to change password if rejected (too easy)
+#
+PASS_CHANGE_TRIES	5
+
+#
+# Warn about weak passwords (but still allow them) if you are root.
+#
+PASS_ALWAYS_WARN	yes
+
+#
+# Number of significant characters in the password for crypt().
+# Default is 8, don't change unless your crypt() is better.
+# Ignored if MD5_CRYPT_ENAB set to "yes".
+#
+#PASS_MAX_LEN		8
+
+#
+# Require password before chfn/chsh can make any changes.
+#
+CHFN_AUTH		yes
+
+#
+# Which fields may be changed by regular users using chfn - use
+# any combination of letters "frwh" (full name, room number, work
+# phone, home phone).  If not defined, no changes are allowed.
+# For backward compatibility, "yes" = "rwh" and "no" = "frwh".
+# 
+CHFN_RESTRICT		rwh
+
+#
+# Password prompt (%s will be replaced by user name).
+#
+# XXX - it doesn't work correctly yet, for now leave it commented out
+# to use the default which is just "Password: ".
+#LOGIN_STRING		"%s's Password: "
+
+#
+# Only works if compiled with MD5_CRYPT defined:
+# If set to "yes", new passwords will be encrypted using the MD5-based
+# algorithm compatible with the one used by recent releases of FreeBSD.
+# It supports passwords of unlimited length and longer salt strings.
+# Set to "no" if you need to copy encrypted passwords to other systems
+# which don't understand the new algorithm.  Default is "no".
+#
+# Note: If you use PAM, it is recommended to use a value consistent with
+# the PAM modules configuration.
+#
+# This variable is deprecated. You should use ENCRYPT_METHOD.
+#
+#MD5_CRYPT_ENAB	no
+
+#
+# Only works if compiled with ENCRYPTMETHOD_SELECT defined:
+# If set to MD5 , MD5-based algorithm will be used for encrypting password
+# If set to SHA256, SHA256-based algorithm will be used for encrypting password
+# If set to SHA512, SHA512-based algorithm will be used for encrypting password
+# If set to DES, DES-based algorithm will be used for encrypting password (default)
+# Overrides the MD5_CRYPT_ENAB option
+#
+# Note: If you use PAM, it is recommended to use a value consistent with
+# the PAM modules configuration.
+#
+#ENCRYPT_METHOD DES
+
+#
+# Only works if ENCRYPT_METHOD is set to SHA256 or SHA512.
+#
+# Define the number of SHA rounds.
+# With a lot of rounds, it is more difficult to brute forcing the password.
+# But note also that it more CPU resources will be needed to authenticate
+# users.
+#
+# If not specified, the libc will choose the default number of rounds (5000).
+# The values must be inside the 1000-999999999 range.
+# If only one of the MIN or MAX values is set, then this value will be used.
+# If MIN > MAX, the highest value will be used.
+#
+# SHA_CRYPT_MIN_ROUNDS 5000
+# SHA_CRYPT_MAX_ROUNDS 5000
+
+#
+# List of groups to add to the user's supplementary group set
+# when logging in on the console (as determined by the CONSOLE
+# setting).  Default is none.
+#
+# Use with caution - it is possible for users to gain permanent
+# access to these groups, even when not logged in on the console.
+# How to do it is left as an exercise for the reader...
+#
+#CONSOLE_GROUPS		floppy:audio:cdrom
+
+#
+# Should login be allowed if we can't cd to the home directory?
+# Default in no.
+#
+DEFAULT_HOME	yes
+
+#
+# If this file exists and is readable, login environment will be
+# read from it.  Every line should be in the form name=value.
+#
+ENVIRON_FILE	/etc/environment
+
+#
+# If defined, this command is run when removing a user.
+# It should remove any at/cron/print jobs etc. owned by
+# the user to be removed (passed as the first argument).
+#
+#USERDEL_CMD	/usr/sbin/userdel_local
+
+#
+# Enable setting of the umask group bits to be the same as owner bits
+# (examples: 022 -> 002, 077 -> 007) for non-root users, if the uid is
+# the same as gid, and username is the same as the primary group name.
+#
+# This also enables userdel to remove user groups if no members exist.
+#
+USERGROUPS_ENAB yes
+
+#
+# If set to a non-nul number, the shadow utilities will make sure that
+# groups never have more than this number of users on one line.
+# This permit to support split groups (groups split into multiple lines,
+# with the same group ID, to avoid limitation of the line length in the
+# group file).
+#
+# 0 is the default value and disables this feature.
+#
+#MAX_MEMBERS_PER_GROUP	0
+
+#
+# If useradd should create home directories for users by default (non
+# system users only)
+# This option is overridden with the -M or -m flags on the useradd command
+# line.
+#
+CREATE_HOME     yes
+
diff --git a/meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb b/meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
new file mode 100644
index 0000000..ab88a65
--- /dev/null
+++ b/meta/recipes-core/base-passwd/base-passwd-cross_3.5.22.bb
@@ -0,0 +1,53 @@
+SUMMARY = "Base system master password/group files."
+DESCRIPTION = "The master copies of the user database files (/etc/passwd and /etc/group).  The update-passwd tool is also provided to keep the system databases synchronized with these master files."
+SECTION = "base"
+DEPENDS = "shadow-native"
+PR = "r0"
+LICENSE = "GPLv2+"
+LIC_FILES_CHKSUM = "file://COPYING;md5=eb723b61539feef013de476e68b5c50a"
+
+SRC_URI = "${DEBIAN_MIRROR}/main/b/base-passwd/base-passwd_${PV}.tar.gz \
+           file://nobash.patch \
+           file://root-home.patch \
+           file://login.defs"
+
+SRC_URI[md5sum] = "47f22ab6b572d0133409ff6ad1fab402"
+SRC_URI[sha256sum] = "d34acb35a9f9f221e7e4f642b9ef4b22083dd77bb2fc7216756f445316d842fc"
+
+S = "${WORKDIR}/base-passwd"
+
+inherit autotools
+
+SSTATEPOSTINSTFUNCS += "base_passwd_cross_sstate_postinst"
+
+do_install () {
+	install -d -m 755 ${D}${sbindir}
+	install -p -m 755 update-passwd ${D}${sbindir}/
+	install -d -m 755 ${D}${mandir}/man8 ${D}${mandir}/pl/man8
+	install -p -m 644 man/update-passwd.8 ${D}${mandir}/man8/
+	install -p -m 644 man/update-passwd.pl.8 \
+		${D}${mandir}/pl/man8/update-passwd.8
+	gzip -9 ${D}${mandir}/man8/* ${D}${mandir}/pl/man8/*
+	install -d -m 755 ${D}${datadir}/base-passwd
+	install -p -m 644 passwd.master ${D}${datadir}/base-passwd/
+	install -p -m 644 group.master ${D}${datadir}/base-passwd/
+    install -p -m 644 ${S}/../login.defs ${D}${datadir}/base-passwd/login.defs
+
+	install -d -m 755 ${D}${docdir}/${PN}
+	install -p -m 644 debian/changelog ${D}${docdir}/${PN}/
+	gzip -9 ${D}${docdir}/${PN}/*
+	install -p -m 644 README ${D}${docdir}/${PN}/
+	install -p -m 644 debian/copyright ${D}${docdir}/${PN}/
+}
+
+base_passwd_cross_sstate_postinst() {
+	if [ "${BB_CURRENTTASK}" = "populate_sysroot" -o "${BB_CURRENTTASK}" = "populate_sysroot_setscene" ]
+	then
+		# Staging does not copy ${sysconfdir} files into the
+		# target sysroot, so we need to do so manually.
+		install -d -m 755 ${STAGING_DIR_TARGET}${sysconfdir}
+		install -p -m 644 ${STAGING_DIR_TARGET}${datadir}/base-passwd/passwd.master ${STAGING_DIR_TARGET}${sysconfdir}/passwd
+		install -p -m 644 ${STAGING_DIR_TARGET}${datadir}/base-passwd/group.master ${STAGING_DIR_TARGET}${sysconfdir}/group
+		install -p -m 644 ${STAGING_DIR_TARGET}${datadir}/base-passwd/login.defs ${STAGING_DIR_TARGET}/${sysconfdir}/login.defs
+	fi
+}
-- 
1.7.1




^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 4/7] useradd.bbclass: new class for managing user/group permissions
@ 2011-05-31 19:53   ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 19:53 UTC (permalink / raw)
  To: openembedded-core

This class is to be used by recipes that need to set up specific
user/group accounts and set custom file/directory permissions.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 meta/classes/useradd.bbclass |  136 ++++++++++++++++++++++++++++++++++++++++++
 1 files changed, 136 insertions(+), 0 deletions(-)
 create mode 100644 meta/classes/useradd.bbclass

diff --git a/meta/classes/useradd.bbclass b/meta/classes/useradd.bbclass
new file mode 100644
index 0000000..ac6f8f6
--- /dev/null
+++ b/meta/classes/useradd.bbclass
@@ -0,0 +1,136 @@
+USERADDPN ?= "${PN}"
+
+# base-passwd-cross provides the default passwd and group files in the
+# target sysroot, and shadow-native provides the utilities needed to
+# add and modify user and group accounts
+DEPENDS_append = " base-passwd-cross shadow-native"
+RDEPENDS_${USERADDPN}_append = " base-passwd shadow"
+
+PSEUDO="${STAGING_DIR_NATIVE}/usr/bin/pseudo"
+export PSEUDO
+PSEUDO_LOCALSTATEDIR="${STAGING_DIR_TARGET}/var/pseudo"
+export PSEUDO_LOCALSTATEDIR
+PSEUDO_PASSWD = "${STAGING_DIR_TARGET}"
+export PSEUDO_PASSWD
+
+useradd_sysroot () {
+	# Explicitly set $D since it isn't set to anything
+	# before do_install
+	D=${D}
+	useradd_preinst
+}
+
+useradd_sysroot_sstate () {
+	if [ "${BB_CURRENTTASK}" = "populate_sysroot_setscene" ]
+	then
+		# Explicitly set $D since it isn't set to anything
+		# before do_install
+		D=${D}
+		useradd_preinst
+	fi
+}
+
+useradd_preinst () {
+OPT=""
+SYSROOT=""
+
+if test "x$D" != "x"; then
+	# Installing into a sysroot
+	SYSROOT="${STAGING_DIR_TARGET}"
+	OPT="--root ${STAGING_DIR_TARGET}"
+else
+	# Installing onto a target
+	PSEUDO=""
+fi
+
+# Perform group additions first, since user additions may depend
+# on these groups existing
+if test "x${GROUPADD_PARAM_${PN}}" != "x"; then
+	echo "Running groupadd commands..."
+	# Invoke multiple instances of groupadd for parameter lists
+	# separated by ';'
+	opts=`echo "${GROUPADD_PARAM_${PN}}" | cut -d ';' -f 1`
+	remaining=`echo "${GROUPADD_PARAM_${PN}}" | cut -d ';' -f 2-`
+	while test "x$opts" != "x"; do
+		eval $PSEUDO groupadd -f $OPT $opts
+
+		if test "x$opts" = "x$remaining"; then
+			break
+		fi
+		opts=`echo "$remaining" | cut -d ';' -f 1`
+		remaining=`echo "$remaining" | cut -d ';' -f 2-`
+	done
+fi 
+
+if test "x${USERADD_PARAM_${PN}}" != "x"; then
+	echo "Running useradd commands..."
+	# Invoke multiple instances of useradd for parameter lists
+	# separated by ';'
+	opts=`echo "${USERADD_PARAM_${PN}}" | cut -d ';' -f 1`
+	remaining=`echo "${USERADD_PARAM_${PN}}" | cut -d ';' -f 2-`
+	while test "x$opts" != "x"; do
+		# useradd does not have a -f option, so we have to check if the
+		# username already exists manually
+		username=`echo "$opts" | awk '{ print $NF }'`
+		user_exists=`grep "^$username:" $SYSROOT/etc/passwd || true`
+		if test "x$user_exists" = "x"; then
+			eval $PSEUDO useradd $OPT $opts
+		else
+			echo "Note: username $username already exists, not re-creating it"
+		fi
+
+		if test "x$opts" = "x$remaining"; then
+			break
+		fi
+		opts=`echo "$remaining" | cut -d ';' -f 1`
+		remaining=`echo "$remaining" | cut -d ';' -f 2-`
+	done
+fi
+}
+
+do_install[prefuncs] += "useradd_sysroot"
+SSTATEPOSTINSTFUNCS += "useradd_sysroot_sstate"
+
+# Recipe parse-time sanity checks
+def update_useradd_after_parse(d):
+	if bb.data.getVar('USERADD_PACKAGES', d) == None:
+		if bb.data.getVar('USERADD_PARAM', d) == None and bb.data.getVar('GROUPADD_PARAM', d) == None:
+			raise bb.build.FuncFailed, "%s inherits useradd but doesn't set USERADD_PARAM or GROUPADD_PARAM" % bb.data.getVar('FILE', d)
+
+python __anonymous() {
+	update_useradd_after_parse(d)
+}
+
+# Adds the preinst script into generated packages
+fakeroot python populate_packages_prepend () {
+	def update_useradd_package(pkg):
+		bb.debug(1, 'adding user/group calls to preinst for %s' % pkg)
+		localdata = bb.data.createCopy(d)
+		overrides = bb.data.getVar("OVERRIDES", localdata, 1)
+		bb.data.setVar("OVERRIDES", "%s:%s" % (pkg, overrides), localdata)
+		bb.data.update_data(localdata)
+
+		"""
+		useradd preinst is appended here because pkg_preinst may be
+		required to execute on the target. Not doing so may cause
+		useradd preinst to be invoked twice, causing unwanted warnings.
+		"""
+		preinst = bb.data.getVar('pkg_preinst', localdata, 1)
+		if not preinst:
+			preinst = '#!/bin/sh\n'
+		preinst += bb.data.getVar('useradd_preinst', localdata, 1)
+		bb.data.setVar('pkg_preinst_%s' % pkg, preinst, d)
+
+	# We add the user/group calls to all packages to allow any package
+	# to contain files owned by the users/groups defined in the recipe.
+	# The user/group addition code is careful not to create duplicate
+	# entries, so this is safe.
+	pkgs = bb.data.getVar('USERADD_PACKAGES', d, 1)
+	if pkgs == None:
+		pkgs = bb.data.getVar('USERADDPN', d, 1)
+		packages = (bb.data.getVar('PACKAGES', d, 1) or "").split()
+		if not pkgs in packages and packages != []:
+			pkgs = packages[0]
+	for pkg in pkgs.split():
+		update_useradd_package(pkg)
+}
-- 
1.7.1




^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 5/7] useradd-example: example recipe for using inherit useradd
@ 2011-05-31 19:53   ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 19:53 UTC (permalink / raw)
  To: openembedded-core

An example recipe for demonstrating/documenting how user and
group manipulation is done with 'inherit useradd'

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 .../recipes-skeleton/useradd/useradd-example.bb    |   59 ++++++++++++++++++++
 1 files changed, 59 insertions(+), 0 deletions(-)
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
 create mode 100644 meta-skeleton/recipes-skeleton/useradd/useradd-example/file4

diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example.bb b/meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
new file mode 100644
index 0000000..1e6ae87
--- /dev/null
+++ b/meta-skeleton/recipes-skeleton/useradd/useradd-example.bb
@@ -0,0 +1,59 @@
+SUMMARY = "Example recipe for using inherit useradd"
+DESCRIPTION = "This recipe serves as an example for using features from useradd.bbclass"
+SECTION = "examples"
+PR = "r0"
+LICENSE = "MIT"
+LIC_FILES_CHKSUM = "file://${COREBASE}/LICENSE;md5=3f40d7994397109285ec7b81fdeb3b58 \
+                    file://${COREBASE}/meta/COPYING.MIT;md5=3da9cfbcb788c80a0384361b4de20420"
+
+SRC_URI = "file://file1 \
+           file://file2 \
+           file://file3 \
+           file://file4"
+
+S = "${WORKDIR}"
+
+inherit useradd
+
+# Specify which package(s) should include the user/group code.
+# Make sure that any packages which install files owned by custom
+# users/groups are included here. The code which adds users and
+# groups is idempotent.
+USERADD_PACKAGES = "useradd-example"
+
+# You *must* set USERADD_PARAM and/or GROUPADD_PARAM when
+# you inherit useradd.
+
+# USERADD_PARAM specifies command line options to pass to the
+# useradd command. Multiple users can be created by separating
+# the commands with a semicolon. Here we'll create two users,
+# user1 and user3:
+USERADD_PARAM_useradd-example = "-u 1200 -d /home/user1 -r -s /bin/bash user1; -u 1201 -d /home/user3 -r -s /bin/bash user3"
+
+# GROUPADD_PARAM works the same way, which you set to the options
+# you'd normally pass to the groupadd command. This will create
+# groups group1, group2, and group3:
+GROUPADD_PARAM_useradd-example = "-g 880 group1; -g 890 group2; -g 900 group3"
+
+do_install () {
+	install -d -m 755 ${D}/usr/share/user1
+	install -d -m 755 ${D}/usr/share/user3
+	install -p -m 644 file1 ${D}/usr/share/user1/
+	install -p -m 644 file2 ${D}/usr/share/user1/
+	install -p -m 644 file3 ${D}/usr/share/user3/
+	install -p -m 644 file4 ${D}/usr/share/user3/
+
+	# The new users and groups are created before the do_install
+	# step, so you are now free to make use of them:
+	chown -R user1 ${D}/usr/share/user1
+	chown -R user3 ${D}/usr/share/user3
+	chgrp group1 ${D}/usr/share/user1/file1
+	chgrp group3 ${D}/usr/share/user1/file2
+	chgrp group1 ${D}/usr/share/user3/file3
+	chgrp group3 ${D}/usr/share/user3/file4
+}
+
+PACKAGES =+ "${PN}-user3"
+
+FILES_${PN} = "/usr/share/user1/*"
+FILES_${PN}-user3 = "/usr/share/user3/*"
diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file1 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file1
new file mode 100644
index 0000000..e69de29
diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file2 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file2
new file mode 100644
index 0000000..e69de29
diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file3 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file3
new file mode 100644
index 0000000..e69de29
diff --git a/meta-skeleton/recipes-skeleton/useradd/useradd-example/file4 b/meta-skeleton/recipes-skeleton/useradd/useradd-example/file4
new file mode 100644
index 0000000..e69de29
-- 
1.7.1




^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 6/7] bitbake.conf: set PSEUDO_PASSWD within FAKEROOTENV
@ 2011-05-31 19:53   ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 19:53 UTC (permalink / raw)
  To: openembedded-core

PSEUDO_PASSWD needs to point to the directory where passwd and group
files are kept. This will allow pseudo to use those users and groups
to change file ownership.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 meta/conf/bitbake.conf |    2 +-
 1 files changed, 1 insertions(+), 1 deletions(-)

diff --git a/meta/conf/bitbake.conf b/meta/conf/bitbake.conf
index d307385..6f16a65 100644
--- a/meta/conf/bitbake.conf
+++ b/meta/conf/bitbake.conf
@@ -535,7 +535,7 @@ SRC_URI = "file://${FILE}"
 
 # Use pseudo as the fakeroot implementation
 PSEUDO_LOCALSTATEDIR ?= "${WORKDIR}/pseudo/"
-FAKEROOTENV = "PSEUDO_PREFIX=${STAGING_DIR_NATIVE}${prefix_native} PSEUDO_LOCALSTATEDIR=${PSEUDO_LOCALSTATEDIR} PSEUDO_NOSYMLINKEXP=1 PSEUDO_DISABLED=0"
+FAKEROOTENV = "PSEUDO_PREFIX=${STAGING_DIR_NATIVE}${prefix_native} PSEUDO_LOCALSTATEDIR=${PSEUDO_LOCALSTATEDIR} PSEUDO_PASSWD=${STAGING_DIR_TARGET}/etc PSEUDO_NOSYMLINKEXP=1 PSEUDO_DISABLED=0"
 FAKEROOTDIRS = "${PSEUDO_LOCALSTATEDIR}"
 PREFERRED_PROVIDER_virtual/fakeroot-native ?= "pseudo-native"
 
-- 
1.7.1




^ permalink raw reply related	[flat|nested] 51+ messages in thread

* [PATCH 7/7] package_rpm.bbclass: make RPM use on-disk permissions
@ 2011-05-31 19:53   ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-05-31 19:53 UTC (permalink / raw)
  To: openembedded-core

Instruct RPM to use the on-disk permissions, owners, groups,
and directory permissions, instead of defaulting to root:root

Code changes suggested by Mark Hatle.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 meta/classes/package_rpm.bbclass |    2 ++
 1 files changed, 2 insertions(+), 0 deletions(-)

diff --git a/meta/classes/package_rpm.bbclass b/meta/classes/package_rpm.bbclass
index 1d8c686..d124c01 100644
--- a/meta/classes/package_rpm.bbclass
+++ b/meta/classes/package_rpm.bbclass
@@ -484,6 +484,7 @@ python write_specfile () {
 			else:
 				bb.note("Creating RPM package for %s" % splitname)
 				spec_files_top.append('%files')
+				spec_files_top.append('%defattr(-,-,-,-)')
 				if file_list:
 					spec_files_top.extend(file_list)
 				spec_files_top.append('')
@@ -570,6 +571,7 @@ python write_specfile () {
 		else:
 			bb.note("Creating RPM package for %s" % splitname)
 			spec_files_bottom.append('%%files -n %s' % splitname)
+			spec_files_bottom.append('%defattr(-,-,-,-)')
 			if file_list:
 				spec_files_bottom.extend(file_list)
 			spec_files_bottom.append('')
-- 
1.7.1




^ permalink raw reply related	[flat|nested] 51+ messages in thread

* Re: [poky] [PATCH 0/7] User/group creation at preinstall
  2011-05-31 19:51       ` Scott Garman
  (?)
@ 2011-05-31 19:57       ` Otavio Salvador
  2011-05-31 21:16           ` [OE-core] " Mark Hatle
  -1 siblings, 1 reply; 51+ messages in thread
From: Otavio Salvador @ 2011-05-31 19:57 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer
  Cc: Koen Kooi, poky@yoctoproject.org Project

On Tue, May 31, 2011 at 19:51, Scott Garman <scott.a.garman@intel.com> wrote:
> That said, I have no idea what criteria should be used to determine which
> list to send things to, and I'm sure I'm not the only one. Is this
> documented anywhere?

It seems to me that poky list ought to be not used anymore and patches
to be send to oe-core as AFAIK Yocto will base on it. Am I missing
anything?

This is really confusing. This is not just regarding mailing lists but
also IRC channels :-/

-- 
Otavio Salvador                             O.S. Systems
E-mail: otavio@ossystems.com.br  http://www.ossystems.com.br
Mobile: +55 53 9981-7854              http://projetos.ossystems.com.br



^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [poky] [PATCH 0/7] User/group creation at preinstall
  2011-05-31 19:57       ` [poky] " Otavio Salvador
@ 2011-05-31 21:16           ` Mark Hatle
  0 siblings, 0 replies; 51+ messages in thread
From: Mark Hatle @ 2011-05-31 21:16 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer
  Cc: Koen Kooi, poky@yoctoproject.org Project

On 5/31/11 2:57 PM, Otavio Salvador wrote:
> On Tue, May 31, 2011 at 19:51, Scott Garman <scott.a.garman@intel.com> wrote:
>> That said, I have no idea what criteria should be used to determine which
>> list to send things to, and I'm sure I'm not the only one. Is this
>> documented anywhere?
> 
> It seems to me that poky list ought to be not used anymore and patches
> to be send to oe-core as AFAIK Yocto will base on it. Am I missing
> anything?
> 
> This is really confusing. This is not just regarding mailing lists but
> also IRC channels :-/
> 

As I understand it, the intention is the Poky list is used for Poky specific
items or to discuss (from a Poky specific point of view) oe-core items.. I.e.
problems, issues, etc from the usage of oe-core within the Poky use.

The confusion currently comes from many of the oe-core items used to live in the
Poky domain, and no longer due.  Unfortunately this will take a bit of education
for folks who don't contribute daily so that they know which mailing list to use.

(In otherwords the Poky list still has it's place, but only for Poky specific
discussions.)

--Mark



^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [OE-core] [PATCH 0/7] User/group creation at preinstall
@ 2011-05-31 21:16           ` Mark Hatle
  0 siblings, 0 replies; 51+ messages in thread
From: Mark Hatle @ 2011-05-31 21:16 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer
  Cc: poky@yoctoproject.org Project, Otavio Salvador

On 5/31/11 2:57 PM, Otavio Salvador wrote:
> On Tue, May 31, 2011 at 19:51, Scott Garman <scott.a.garman@intel.com> wrote:
>> That said, I have no idea what criteria should be used to determine which
>> list to send things to, and I'm sure I'm not the only one. Is this
>> documented anywhere?
> 
> It seems to me that poky list ought to be not used anymore and patches
> to be send to oe-core as AFAIK Yocto will base on it. Am I missing
> anything?
> 
> This is really confusing. This is not just regarding mailing lists but
> also IRC channels :-/
> 

As I understand it, the intention is the Poky list is used for Poky specific
items or to discuss (from a Poky specific point of view) oe-core items.. I.e.
problems, issues, etc from the usage of oe-core within the Poky use.

The confusion currently comes from many of the oe-core items used to live in the
Poky domain, and no longer due.  Unfortunately this will take a bit of education
for folks who don't contribute daily so that they know which mailing list to use.

(In otherwords the Poky list still has it's place, but only for Poky specific
discussions.)

--Mark


^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [poky] [PATCH 0/7] User/group creation at preinstall
  2011-05-31 19:51       ` Scott Garman
@ 2011-05-31 21:25         ` Richard Purdie
  -1 siblings, 0 replies; 51+ messages in thread
From: Richard Purdie @ 2011-05-31 21:25 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer
  Cc: Koen Kooi, poky@yoctoproject.org Project

On Tue, 2011-05-31 at 12:51 -0700, Scott Garman wrote:
> On 05/31/2011 12:06 PM, Saul Wold wrote:
> > On 05/31/2011 11:45 AM, Koen Kooi wrote:
> >> Shouldn't patches like this be sent to the oe-core list? It wouldn't
> >> have saved me from the selinux bug in shadow, though :)
> >>
> > Scott,
> >
> > I would agree with Koen, this is a oe-core change, not a Poky only
> > change, please resend this request to the oe-core list.
> 
> Sure, I'll resend it to oe-core.
> 
> That said, I have no idea what criteria should be used to determine 
> which list to send things to, and I'm sure I'm not the only one. Is this 
> documented anywhere?

We're trying to make this simpler over time:

bitbake changes -> bitbake-devel
Any code in oe-core -> oe-core list
Anything in poky not in oe-core/bitbake -> poky list

Cheers,

Richard





^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [OE-core] [PATCH 0/7] User/group creation at preinstall
@ 2011-05-31 21:25         ` Richard Purdie
  0 siblings, 0 replies; 51+ messages in thread
From: Richard Purdie @ 2011-05-31 21:25 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer
  Cc: poky@yoctoproject.org Project

On Tue, 2011-05-31 at 12:51 -0700, Scott Garman wrote:
> On 05/31/2011 12:06 PM, Saul Wold wrote:
> > On 05/31/2011 11:45 AM, Koen Kooi wrote:
> >> Shouldn't patches like this be sent to the oe-core list? It wouldn't
> >> have saved me from the selinux bug in shadow, though :)
> >>
> > Scott,
> >
> > I would agree with Koen, this is a oe-core change, not a Poky only
> > change, please resend this request to the oe-core list.
> 
> Sure, I'll resend it to oe-core.
> 
> That said, I have no idea what criteria should be used to determine 
> which list to send things to, and I'm sure I'm not the only one. Is this 
> documented anywhere?

We're trying to make this simpler over time:

bitbake changes -> bitbake-devel
Any code in oe-core -> oe-core list
Anything in poky not in oe-core/bitbake -> poky list

Cheers,

Richard




^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [poky] [PATCH 0/7] User/group creation at preinstall
  2011-05-31 21:16           ` [OE-core] " Mark Hatle
  (?)
@ 2011-05-31 21:27           ` Scott Garman
  2011-05-31 21:51             ` Richard Purdie
  -1 siblings, 1 reply; 51+ messages in thread
From: Scott Garman @ 2011-05-31 21:27 UTC (permalink / raw)
  To: openembedded-core

On 05/31/2011 02:16 PM, Mark Hatle wrote:
> On 5/31/11 2:57 PM, Otavio Salvador wrote:
>> On Tue, May 31, 2011 at 19:51, Scott Garman<scott.a.garman@intel.com>  wrote:
>>> That said, I have no idea what criteria should be used to determine which
>>> list to send things to, and I'm sure I'm not the only one. Is this
>>> documented anywhere?
>>
>> It seems to me that poky list ought to be not used anymore and patches
>> to be send to oe-core as AFAIK Yocto will base on it. Am I missing
>> anything?
>>
>> This is really confusing. This is not just regarding mailing lists but
>> also IRC channels :-/
>>
>
> As I understand it, the intention is the Poky list is used for Poky specific
> items or to discuss (from a Poky specific point of view) oe-core items.. I.e.
> problems, issues, etc from the usage of oe-core within the Poky use.
>
> The confusion currently comes from many of the oe-core items used to live in the
> Poky domain, and no longer due.  Unfortunately this will take a bit of education
> for folks who don't contribute daily so that they know which mailing list to use.
>
> (In otherwords the Poky list still has it's place, but only for Poky specific
> discussions.)

So presumably this would mean: if it's about a recipe that is not in 
OE-core, it's Poky-specific?

Which would also mean that discussion about anything in the bitbake 
classes belongs on OE-core as well, yes?

Scott

-- 
Scott Garman
Embedded Linux Engineer - Yocto Project
Intel Open Source Technology Center



^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [poky] [PATCH 0/7] User/group creation at preinstall
  2011-05-31 21:27           ` [poky] " Scott Garman
@ 2011-05-31 21:51             ` Richard Purdie
  0 siblings, 0 replies; 51+ messages in thread
From: Richard Purdie @ 2011-05-31 21:51 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On Tue, 2011-05-31 at 14:27 -0700, Scott Garman wrote:
> So presumably this would mean: if it's about a recipe that is not in 
> OE-core, it's Poky-specific?

If its not bitbake and its not on OE-Core its poky specific.

> Which would also mean that discussion about anything in the bitbake 
> classes belongs on OE-core as well, yes?

Correct.

Cheers,

Richard




^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-05-31 19:53   ` Scott Garman
  (?)
@ 2011-06-01  9:47   ` Phil Blundell
  2011-06-01 12:34     ` Martyn Welch
  2011-06-01 17:43     ` Scott Garman
  -1 siblings, 2 replies; 51+ messages in thread
From: Phil Blundell @ 2011-06-01  9:47 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On Tue, 2011-05-31 at 12:53 -0700, Scott Garman wrote:
> This adds a -native recipe for the shadow utilities.
> 
> The custom --root option allows the the following utilities to be
> run within a chroot when invoked under pseudo:

Rather than patching the code for all these utilities, can't you just
wrap them in a call to chroot(8)?  That is, make useradd.bbclass do:

eval $PSEUDO chroot ${STAGING_DIR_TARGET} useradd ...

rather than the existing

eval $PSEUDO useradd --root ${STAGING_DIR_TARGET} ...

?

p.





^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-06-01  9:47   ` Phil Blundell
@ 2011-06-01 12:34     ` Martyn Welch
  2011-06-01 13:42       ` Phil Blundell
  2011-06-01 17:43     ` Scott Garman
  1 sibling, 1 reply; 51+ messages in thread
From: Martyn Welch @ 2011-06-01 12:34 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On 01/06/11 10:47, Phil Blundell wrote:
> On Tue, 2011-05-31 at 12:53 -0700, Scott Garman wrote:
>> This adds a -native recipe for the shadow utilities.
>>
>> The custom --root option allows the the following utilities to be
>> run within a chroot when invoked under pseudo:
> 
> Rather than patching the code for all these utilities, can't you just
> wrap them in a call to chroot(8)?  That is, make useradd.bbclass do:
> 
> eval $PSEUDO chroot ${STAGING_DIR_TARGET} useradd ...
> 
> rather than the existing
> 
> eval $PSEUDO useradd --root ${STAGING_DIR_TARGET} ...
> 
> ?
> 

You'd need root privileges to use chroot wouldn't you? I'm assuming you
wouldn't with the existing.

Martyn

-- 
Martyn Welch (Principal Software Engineer) | Registered in England and
GE Intelligent Platforms                   | Wales (3828642) at 100
T +44(0)127322748                          | Barbirolli Square, Manchester,
E martyn.welch@ge.com                      | M2 3AB  VAT:GB 927559189



^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-06-01 12:34     ` Martyn Welch
@ 2011-06-01 13:42       ` Phil Blundell
  0 siblings, 0 replies; 51+ messages in thread
From: Phil Blundell @ 2011-06-01 13:42 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On Wed, 2011-06-01 at 13:34 +0100, Martyn Welch wrote:
> On 01/06/11 10:47, Phil Blundell wrote:
> > On Tue, 2011-05-31 at 12:53 -0700, Scott Garman wrote:
> >> This adds a -native recipe for the shadow utilities.
> >>
> >> The custom --root option allows the the following utilities to be
> >> run within a chroot when invoked under pseudo:
> > 
> > Rather than patching the code for all these utilities, can't you just
> > wrap them in a call to chroot(8)?  That is, make useradd.bbclass do:
> > 
> > eval $PSEUDO chroot ${STAGING_DIR_TARGET} useradd ...
> > 
> > rather than the existing
> > 
> > eval $PSEUDO useradd --root ${STAGING_DIR_TARGET} ...
> > 
> > ?
> > 
> 
> You'd need root privileges to use chroot wouldn't you? I'm assuming you
> wouldn't with the existing.

Doesn't $PSEUDO sort that out?  The --root option that Scott has patched
into all the utilities seems to just end up calling chroot(2) anyway so
you would need root privileges at that point.  That said, I'm not
entirely au fait with pseudo so I might well be misunderstanding how it
works.

p.





^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-06-01  9:47   ` Phil Blundell
  2011-06-01 12:34     ` Martyn Welch
@ 2011-06-01 17:43     ` Scott Garman
  2011-06-01 21:05       ` Mark Hatle
  1 sibling, 1 reply; 51+ messages in thread
From: Scott Garman @ 2011-06-01 17:43 UTC (permalink / raw)
  To: openembedded-core

On 06/01/2011 02:47 AM, Phil Blundell wrote:
> On Tue, 2011-05-31 at 12:53 -0700, Scott Garman wrote:
>> This adds a -native recipe for the shadow utilities.
>>
>> The custom --root option allows the the following utilities to be
>> run within a chroot when invoked under pseudo:
>
> Rather than patching the code for all these utilities, can't you just
> wrap them in a call to chroot(8)?  That is, make useradd.bbclass do:
>
> eval $PSEUDO chroot ${STAGING_DIR_TARGET} useradd ...
>
> rather than the existing
>
> eval $PSEUDO useradd --root ${STAGING_DIR_TARGET} ...

That's a reasonable suggestion. I haven't tried it yet, but I have found 
that pseudo's chroot(2) implementation is not complete. One of the cases 
where it does not work is when forking child processes, which breaks the 
jail and the child processes are no longer chroot'ed.

My guess is that chroot(8) is going to call chroot(2) and then fork a 
child process to run its additional arguments.

cc'ing Mark directly in case he has additional comments or needs to 
correct me.

Scott

-- 
Scott Garman
Embedded Linux Engineer - Yocto Project
Intel Open Source Technology Center



^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-06-01 17:43     ` Scott Garman
@ 2011-06-01 21:05       ` Mark Hatle
  2011-06-02 11:19         ` Phil Blundell
  0 siblings, 1 reply; 51+ messages in thread
From: Mark Hatle @ 2011-06-01 21:05 UTC (permalink / raw)
  To: Scott Garman; +Cc: openembedded-core

On 6/1/11 12:43 PM, Scott Garman wrote:
> On 06/01/2011 02:47 AM, Phil Blundell wrote:
>> On Tue, 2011-05-31 at 12:53 -0700, Scott Garman wrote:
>>> This adds a -native recipe for the shadow utilities.
>>>
>>> The custom --root option allows the the following utilities to be
>>> run within a chroot when invoked under pseudo:
>>
>> Rather than patching the code for all these utilities, can't you just
>> wrap them in a call to chroot(8)?  That is, make useradd.bbclass do:
>>
>> eval $PSEUDO chroot ${STAGING_DIR_TARGET} useradd ...
>>
>> rather than the existing
>>
>> eval $PSEUDO useradd --root ${STAGING_DIR_TARGET} ...
> 
> That's a reasonable suggestion. I haven't tried it yet, but I have found 
> that pseudo's chroot(2) implementation is not complete. One of the cases 
> where it does not work is when forking child processes, which breaks the 
> jail and the child processes are no longer chroot'ed.
> 
> My guess is that chroot(8) is going to call chroot(2) and then fork a 
> child process to run its additional arguments.

chroot should be complete in pseudo, if you can reproduce any failures we should
pass them upstream.

The reason I suggested the --root option was primarily for the ease of people
who are NOT using the automated scripting, i.e. someone manually adding a
preinst (or similar) to their recipes.

The --root option is easier (to me at least) to understand that having to if-def
stuff around a chroot..  (but that is personal preference...)

--Mark

> cc'ing Mark directly in case he has additional comments or needs to 
> correct me.
> 
> Scott
> 




^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-06-01 21:05       ` Mark Hatle
@ 2011-06-02 11:19         ` Phil Blundell
  0 siblings, 0 replies; 51+ messages in thread
From: Phil Blundell @ 2011-06-02 11:19 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On Wed, 2011-06-01 at 16:05 -0500, Mark Hatle wrote:
> The reason I suggested the --root option was primarily for the ease of people
> who are NOT using the automated scripting, i.e. someone manually adding a
> preinst (or similar) to their recipes.

I was thinking about this stuff the other day for update-rc.d.  Really,
it sucks that all the manually-written postinsts have to include all of
this garbage about checking for $D.  It also sucks a bit that this same
code (for both manually-written and auto-generated postinsts) ends up
getting deployed into the packages and onto the target system, where it
is at best a waste of space.

I think maybe a better way of dealing with that whole thing would be for
update-rc.d-native and similar tools to provide a set of wrapper scripts
which would take care of all the machinations required to support
offline root mode, be that adding "--root $D" or doing stuff with chroot
or whatever.  If those were installed into some appropriate place in the
sysroot then we could arrange for the right directory to be prepended to
$PATH during rootfs construction and then everything ought to "just
work" without the postinst scripts needing to take any special measures.

p.






^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-05-31 19:53   ` Scott Garman
  (?)
  (?)
@ 2011-09-01 14:46   ` Phil Blundell
  -1 siblings, 0 replies; 51+ messages in thread
From: Phil Blundell @ 2011-09-01 14:46 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

I just tried using useradd.bbclass for the first time (in an effort to
make dbus installable on a readonly-rootfs) and it doesn't seem to be
working very well for me.

The root of my problem seems to be the code below.  As far as I can
tell, what's happening is that process_root_flag() consumes all the
command line arguments to useradd, which means that the subsequent call
to getopt() in process_flags() just returns immediately because there is
nothing left for it to do.  The upshot of all this is that the switches
on the command line are simply ignored and useradd doesn't do what I
wanted.

Is anybody else using this code successfully in oe-core with a
nontrivial USERADD_PARAM?

p.

On Tue, 2011-05-31 at 12:53 -0700, Scott Garman wrote:
> + /*
> ++ * process_root_flag - chroot if given the --root option
> ++ *
> ++ * We do this outside of process_flags() because
> ++ * the is_shadow_pwd boolean needs to be set before
> ++ * process_flags(), and if we do need to chroot() we
> ++ * must do so before is_shadow_pwd gets set.
> ++ */
> ++static void process_root_flag (int argc, char **argv)
> ++{
> ++	/*
> ++	 * Parse the command line options.
> ++	 */
> ++	int flag;
> ++	int option_index = 0;
> ++	static struct option long_options[] = {
> ++		{"root", required_argument, NULL, 'Q'},
> ++		{NULL, 0, NULL, '\0'}
> ++	};
> ++
> ++	while ((flag = getopt_long (argc, argv, "a:A:d:gM:Q:rR", long_options, &option_index)) != -1) {
> ++		switch (flag) {
> ++		case 'Q':
> ++			if ('/' != optarg[0]) {
> ++				fprintf (stderr,
> ++				         _("%s: invalid chroot path '%s'\n"),
> ++				         Prog, optarg);
> ++				exit (E_BAD_ARG);
> ++			}
> ++			newroot = optarg;
> ++
> ++			if (access (newroot, F_OK) != 0) {
> ++				fprintf(stderr,
> ++				        _("%s: chroot directory %s does not exist\n"),
> ++				        Prog, newroot);
> ++				exit (E_BAD_ARG);
> ++			}
> ++			if ( chroot(newroot) != 0 ) {
> ++				fprintf(stderr,
> ++				        _("%s: unable to chroot to directory %s\n"),
> ++				        Prog, newroot);
> ++				exit (E_BAD_ARG);
> ++			}
> ++			break;
> ++		/* no-op on everything else - they will be hanled by process_flags() */
> ++		}
> ++	}
> ++}





^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-05-31 19:53   ` Scott Garman
                     ` (2 preceding siblings ...)
  (?)
@ 2011-09-01 16:41   ` Phil Blundell
  2011-09-01 16:54     ` Mark Hatle
  -1 siblings, 1 reply; 51+ messages in thread
From: Phil Blundell @ 2011-09-01 16:41 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

[-- Attachment #1: Type: text/plain, Size: 1846 bytes --]

On Thu, 2011-09-01 at 15:46 +0100, Phil Blundell wrote:
> I just tried using useradd.bbclass for the first time (in an effort to
> make dbus installable on a readonly-rootfs) and it doesn't seem to be
> working very well for me.
> 
> The root of my problem seems to be the code below.  As far as I can
> tell, what's happening is that process_root_flag() consumes all the
> command line arguments to useradd, which means that the subsequent call
> to getopt() in process_flags() just returns immediately because there is
> nothing left for it to do.  The upshot of all this is that the switches
> on the command line are simply ignored and useradd doesn't do what I
> wanted.
> 
> Is anybody else using this code successfully in oe-core with a
> nontrivial USERADD_PARAM?

So, I added a strategic "optind = 1" to useradd.c and the situation
seems to have improved a bit.  However, I've encountered a couple of
other issues which are slightly annoying:

a) with the attached patch, dbus itself no longer requires a postinst to
be run at boot time.  Which is cool.  Unfortunately, inheriting useradd
causes it to now depend on shadow (which wasn't previously in my image)
and shadow itself isn't currently amenable to read-only-rootfs either so
my image build still fails.  I guess the answer to this is to have
shadow excluded (by some or other mechanism) during rootfs construction
for non-package-management-enabled images.

b) the useradd.bbclass stuff seems to try to apply itself to
virtclass-native packages as well, which was causing an error during
do_install() for dbus-native.  I worked around this by adding

USERADD_PARAM_${PN}_virtclass-native = ""
GROUPADD_PARAM_${PN}_virtclass-native = ""

to the recipe, but it seems as though the class should probably be
sorting this out for itself.

p.


[-- Attachment #2: dbus.diff --]
[-- Type: text/x-patch, Size: 3403 bytes --]

diff --git a/meta/recipes-core/dbus/dbus.inc b/meta/recipes-core/dbus/dbus.inc
index a8ecda8..7010002 100644
--- a/meta/recipes-core/dbus/dbus.inc
+++ b/meta/recipes-core/dbus/dbus.inc
@@ -14,11 +14,21 @@ SRC_URI = "http://dbus.freedesktop.org/releases/dbus/dbus-${PV}.tar.gz \
            file://tmpdir.patch; \
            file://dbus-1.init"
 
-inherit autotools pkgconfig gettext update-rc.d
+inherit autotools pkgconfig gettext update-rc.d useradd
+
+USERADD_PACKAGES = "${PN}"
+USERADD_PARAM_${PN} = "-d ${MESSAGEHOME} -g ${MESSAGEUSER} -r -N ${MESSAGEUSER}"
+GROUPADD_PARAM_${PN} = "${MESSAGEUSER}; netdev"
+USERADD_PARAM_${PN}_virtclass-native = ""
+GROUPADD_PARAM_${PN}_virtclass-native = ""
 
 INITSCRIPT_NAME = "dbus-1"
 INITSCRIPT_PARAMS = "start 02 5 3 2 . stop 20 0 1 6 ."
 
+MESSAGEUSER=messagebus
+MESSAGEHOME="${localstatedir}/run/dbus"
+UUIDDIR="${localstatedir}/lib/dbus"
+
 CONFFILES_${PN} = "${sysconfdir}/dbus-1/system.conf ${sysconfdir}/dbus-1/session.conf"
 
 DEBIANNAME_${PN} = "dbus-1"
@@ -38,38 +48,22 @@ FILES_${PN} = "${bindir}/dbus-daemon* \
                ${libexecdir}/dbus* \
                ${sysconfdir} \
                ${datadir}/dbus-1/services \
-               ${datadir}/dbus-1/system-services"
+               ${datadir}/dbus-1/system-services \
+	       ${MESSAGEHOME} \
+	       ${UUIDDIR}"
 FILES_${PN}-lib = "${libdir}/lib*.so.*"
 RRECOMMENDS_${PN}-lib = "${PN}"
 FILES_${PN}-dev += "${libdir}/dbus-1.0/include ${bindir}/dbus-glib-tool"
 
-pkg_postinst_dbus() {
-	# can't do adduser stuff offline
-	if [ "x$D" != "x" ]; then
-		exit 1
-	fi
-
-	MESSAGEUSER=messagebus
-	MESSAGEHOME=/var/run/dbus
-	UUIDDIR=/var/lib/dbus
-
-	mkdir -p $MESSAGEHOME
-	mkdir -p $UUIDDIR
-	chgrp "$MESSAGEUSER" "$MESSAGEHOME" 2>/dev/null || addgroup "$MESSAGEUSER"
-	chown "$MESSAGEUSER":"$MESSAGEUSER" "$MESSAGEHOME" 2>/dev/null || \
-		adduser --system --home "$MESSAGEHOME" --no-create-home --disabled-password \
-			--ingroup "$MESSAGEUSER" "$MESSAGEUSER"
+pkg_postinst_${PN}() {
+	chgrp "${MESSAGEUSER}" "${MESSAGEHOME}"
+	chown "${MESSAGEUSER}":"${MESSAGEUSER}" "${MESSAGEHOME}"
+	chown "${MESSAGEUSER}":"${MESSAGEUSER}" "${UUIDDIR}"
 
-	chown "$MESSAGEUSER":"$MESSAGEUSER" "$UUIDDIR"
+	chown root:"${MESSAGEUSER}" $D${libexecdir}/dbus-daemon-launch-helper
+	chmod 4754 $D${libexecdir}/dbus-daemon-launch-helper
 
-	grep -q netdev: /etc/group || addgroup netdev
-
-	chown root:"$MESSAGEUSER" /usr/libexec/dbus-daemon-launch-helper
-	chmod 4754 /usr/libexec/dbus-daemon-launch-helper
-
-	# add volatile after new user/grp are created
-	echo "d messagebus messagebus 0755 /var/run/dbus none" > /etc/default/volatiles/99_dbus
-	if [ -e /etc/init.d/populate-volatile.sh ] ; then
+	if [ -z "$D" ] && [ -e /etc/init.d/populate-volatile.sh ] ; then
 		/etc/init.d/populate-volatile.sh update
 	fi
 }
@@ -95,6 +89,12 @@ do_install() {
 	# disable dbus-1 sysv script on systemd installs
 	# nearly all distros call the initscript plain 'dbus', but OE-core is different
 	ln -sf /dev/null ${D}/${base_libdir}/systemd/system/dbus-1.service
+
+	install -d ${D}${UUIDDIR}
+	install -d ${D}${MESSAGEHOME}
+
+	install -d ${D}${sysconfdir}/default/volatiles
+	echo "d messagebus messagebus 0755 /var/run/dbus none" > ${D}${sysconfdir}/default/volatiles/99_dbus
 }
 
 do_install_virtclass-native() {

^ permalink raw reply related	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-01 16:41   ` Phil Blundell
@ 2011-09-01 16:54     ` Mark Hatle
  2011-09-01 16:58       ` Phil Blundell
  0 siblings, 1 reply; 51+ messages in thread
From: Mark Hatle @ 2011-09-01 16:54 UTC (permalink / raw)
  To: openembedded-core

On 9/1/11 11:41 AM, Phil Blundell wrote:
> On Thu, 2011-09-01 at 15:46 +0100, Phil Blundell wrote:
>> I just tried using useradd.bbclass for the first time (in an effort to
>> make dbus installable on a readonly-rootfs) and it doesn't seem to be
>> working very well for me.
>>
>> The root of my problem seems to be the code below.  As far as I can
>> tell, what's happening is that process_root_flag() consumes all the
>> command line arguments to useradd, which means that the subsequent call
>> to getopt() in process_flags() just returns immediately because there is
>> nothing left for it to do.  The upshot of all this is that the switches
>> on the command line are simply ignored and useradd doesn't do what I
>> wanted.
>>
>> Is anybody else using this code successfully in oe-core with a
>> nontrivial USERADD_PARAM?
> 
> So, I added a strategic "optind = 1" to useradd.c and the situation
> seems to have improved a bit.  However, I've encountered a couple of
> other issues which are slightly annoying:
> 
> a) with the attached patch, dbus itself no longer requires a postinst to
> be run at boot time.  Which is cool.  Unfortunately, inheriting useradd
> causes it to now depend on shadow (which wasn't previously in my image)
> and shadow itself isn't currently amenable to read-only-rootfs either so
> my image build still fails.  I guess the answer to this is to have
> shadow excluded (by some or other mechanism) during rootfs construction
> for non-package-management-enabled images.

What is it depending on for the target?  Is the shadow-utils or something now
required?  That doesn't seem to make sense to me -- other then we need a
passwd/group/shadow/gshadow file to work with.  As long as something can provide
those, we should be ok.

> b) the useradd.bbclass stuff seems to try to apply itself to
> virtclass-native packages as well, which was causing an error during
> do_install() for dbus-native.  I worked around this by adding
> 
> USERADD_PARAM_${PN}_virtclass-native = ""
> GROUPADD_PARAM_${PN}_virtclass-native = ""

Yup, definitely a bug and should be fixed.  native and cross cases should not do
anything with useradd.

--Mark

> to the recipe, but it seems as though the class should probably be
> sorting this out for itself.
> 
> p.
> 
> 
> 
> 
> _______________________________________________
> Openembedded-core mailing list
> Openembedded-core@lists.openembedded.org
> http://lists.linuxtogo.org/cgi-bin/mailman/listinfo/openembedded-core




^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-01 16:54     ` Mark Hatle
@ 2011-09-01 16:58       ` Phil Blundell
  2011-09-01 17:25         ` Mark Hatle
  0 siblings, 1 reply; 51+ messages in thread
From: Phil Blundell @ 2011-09-01 16:58 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On Thu, 2011-09-01 at 11:54 -0500, Mark Hatle wrote:
> What is it depending on for the target?  Is the shadow-utils or something now
> required?  That doesn't seem to make sense to me -- other then we need a
> passwd/group/shadow/gshadow file to work with.  As long as something can provide
> those, we should be ok.

I haven't investigated in detail, but the code from useradd.bbclass
says:

# base-passwd-cross provides the default passwd and group files in the
# target sysroot, and shadow -native and -sysroot provide the utilities
# and support files needed to add and modify user and group accounts
DEPENDS_append = " base-passwd shadow-native shadow-sysroot"
RDEPENDS_${USERADDPN}_append = " base-passwd shadow"

And, I guess, if you want to support online package management then it
does make some sense to have the shadow utils there.  But I don't
need/want that in my configuration.

p.





^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-01 16:58       ` Phil Blundell
@ 2011-09-01 17:25         ` Mark Hatle
  2011-09-01 19:44           ` Phil Blundell
  0 siblings, 1 reply; 51+ messages in thread
From: Mark Hatle @ 2011-09-01 17:25 UTC (permalink / raw)
  To: openembedded-core

On 9/1/11 11:58 AM, Phil Blundell wrote:
> On Thu, 2011-09-01 at 11:54 -0500, Mark Hatle wrote:
>> What is it depending on for the target?  Is the shadow-utils or something now
>> required?  That doesn't seem to make sense to me -- other then we need a
>> passwd/group/shadow/gshadow file to work with.  As long as something can provide
>> those, we should be ok.
> 
> I haven't investigated in detail, but the code from useradd.bbclass
> says:
> 
> # base-passwd-cross provides the default passwd and group files in the
> # target sysroot, and shadow -native and -sysroot provide the utilities
> # and support files needed to add and modify user and group accounts
> DEPENDS_append = " base-passwd shadow-native shadow-sysroot"
> RDEPENDS_${USERADDPN}_append = " base-passwd shadow"

Hmm, good point... I'd forgotten about that.

> And, I guess, if you want to support online package management then it
> does make some sense to have the shadow utils there.  But I don't
> need/want that in my configuration.

Does busybox or something else provide a compatible adduser?  If so maybe a
virtual RDEPENDS is more reasonable in this case.

I think we're caught in the case of we build packages.. as such we need to cover
what the package needs at runtime, this includes install time.  At least w/ a
virtual depend, we can likely fake it by providing it by something else.. but
I'm not sure..

--Mark

> p.
> 
> 
> 
> _______________________________________________
> Openembedded-core mailing list
> Openembedded-core@lists.openembedded.org
> http://lists.linuxtogo.org/cgi-bin/mailman/listinfo/openembedded-core




^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-01 17:25         ` Mark Hatle
@ 2011-09-01 19:44           ` Phil Blundell
  2011-09-01 21:59             ` Richard Purdie
  0 siblings, 1 reply; 51+ messages in thread
From: Phil Blundell @ 2011-09-01 19:44 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On Thu, 2011-09-01 at 12:25 -0500, Mark Hatle wrote:
> On 9/1/11 11:58 AM, Phil Blundell wrote:
> > And, I guess, if you want to support online package management then it
> > does make some sense to have the shadow utils there.  But I don't
> > need/want that in my configuration.
> 
> Does busybox or something else provide a compatible adduser?  If so maybe a
> virtual RDEPENDS is more reasonable in this case.

I'm not sure offhand (it's actually useradd, not adduser, for what
that's worth) but, even if busybox does provide those applets, that
probably isn't quite the point.  The issue here is that I don't really
want to have any implementation of useradd at all on the target system;
using one from busybox would be a bit less bad than requiring standalone
shadow, but still not really ideal.

One workaround would be to weaken the RDEPENDS to an RRECOMMENDS, which
would allow me to declare it as a BAD_RECOMMENDATION.  Or I guess we
could make it be a virtual and I could then provide a dummy-useradd
package which satisfies the dependency but doesn't actually install any
files.  

The approach we take with update-rc.d is to let it be installed and then
have rootfs_ipk rip it back out again after image construction is done,
but this won't work with shadow as it stands due to the postinst issue
in that package.  So a third option would be to find a way to finesse
the postinst thing somehow and then use the same rootfs_ipk logic with
shadow too.

None of those really sound very appealing.  Anybody have a better idea?

p.





^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-01 19:44           ` Phil Blundell
@ 2011-09-01 21:59             ` Richard Purdie
  2011-09-02  0:02               ` Mark Hatle
                                 ` (2 more replies)
  0 siblings, 3 replies; 51+ messages in thread
From: Richard Purdie @ 2011-09-01 21:59 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On Thu, 2011-09-01 at 20:44 +0100, Phil Blundell wrote:
> On Thu, 2011-09-01 at 12:25 -0500, Mark Hatle wrote:
> > On 9/1/11 11:58 AM, Phil Blundell wrote:
> > > And, I guess, if you want to support online package management then it
> > > does make some sense to have the shadow utils there.  But I don't
> > > need/want that in my configuration.
> > 
> > Does busybox or something else provide a compatible adduser?  If so maybe a
> > virtual RDEPENDS is more reasonable in this case.
> 
> I'm not sure offhand (it's actually useradd, not adduser, for what
> that's worth) but, even if busybox does provide those applets, that
> probably isn't quite the point.  The issue here is that I don't really
> want to have any implementation of useradd at all on the target system;
> using one from busybox would be a bit less bad than requiring standalone
> shadow, but still not really ideal.
> 
> One workaround would be to weaken the RDEPENDS to an RRECOMMENDS, which
> would allow me to declare it as a BAD_RECOMMENDATION.  Or I guess we
> could make it be a virtual and I could then provide a dummy-useradd
> package which satisfies the dependency but doesn't actually install any
> files.  
> 
> The approach we take with update-rc.d is to let it be installed and then
> have rootfs_ipk rip it back out again after image construction is done,
> but this won't work with shadow as it stands due to the postinst issue
> in that package.  So a third option would be to find a way to finesse
> the postinst thing somehow and then use the same rootfs_ipk logic with
> shadow too.

The latter sounds like what we'll need to do. I haven't looked at shadow
to see what kind of finessing is required though...

Does opkg have any notion of bitbake's ASSUME_PROVIDED?

Cheers,

Richard




^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-01 21:59             ` Richard Purdie
@ 2011-09-02  0:02               ` Mark Hatle
  2011-09-02  7:15               ` Phil Blundell
  2011-09-02  9:50               ` Phil Blundell
  2 siblings, 0 replies; 51+ messages in thread
From: Mark Hatle @ 2011-09-02  0:02 UTC (permalink / raw)
  To: openembedded-core

On 9/1/11 4:59 PM, Richard Purdie wrote:
> On Thu, 2011-09-01 at 20:44 +0100, Phil Blundell wrote:
>> On Thu, 2011-09-01 at 12:25 -0500, Mark Hatle wrote:
>>> On 9/1/11 11:58 AM, Phil Blundell wrote:
>>>> And, I guess, if you want to support online package management then it
>>>> does make some sense to have the shadow utils there.  But I don't
>>>> need/want that in my configuration.
>>>
>>> Does busybox or something else provide a compatible adduser?  If so maybe a
>>> virtual RDEPENDS is more reasonable in this case.
>>
>> I'm not sure offhand (it's actually useradd, not adduser, for what
>> that's worth) but, even if busybox does provide those applets, that
>> probably isn't quite the point.  The issue here is that I don't really
>> want to have any implementation of useradd at all on the target system;
>> using one from busybox would be a bit less bad than requiring standalone
>> shadow, but still not really ideal.
>>
>> One workaround would be to weaken the RDEPENDS to an RRECOMMENDS, which
>> would allow me to declare it as a BAD_RECOMMENDATION.  Or I guess we
>> could make it be a virtual and I could then provide a dummy-useradd
>> package which satisfies the dependency but doesn't actually install any
>> files.  
>>
>> The approach we take with update-rc.d is to let it be installed and then
>> have rootfs_ipk rip it back out again after image construction is done,
>> but this won't work with shadow as it stands due to the postinst issue
>> in that package.  So a third option would be to find a way to finesse
>> the postinst thing somehow and then use the same rootfs_ipk logic with
>> shadow too.
> 
> The latter sounds like what we'll need to do. I haven't looked at shadow
> to see what kind of finessing is required though...
> 
> Does opkg have any notion of bitbake's ASSUME_PROVIDED?

RPM has a mechanism to provide a list of "provided" items.  But there is not
currently any logic to seed that data.  If there is a standard list, it's
something we can add easily enough.

--Mark

> Cheers,
> 
> Richard
> 
> 
> _______________________________________________
> Openembedded-core mailing list
> Openembedded-core@lists.openembedded.org
> http://lists.linuxtogo.org/cgi-bin/mailman/listinfo/openembedded-core




^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-01 21:59             ` Richard Purdie
  2011-09-02  0:02               ` Mark Hatle
@ 2011-09-02  7:15               ` Phil Blundell
  2011-09-02  9:50               ` Phil Blundell
  2 siblings, 0 replies; 51+ messages in thread
From: Phil Blundell @ 2011-09-02  7:15 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On Thu, 2011-09-01 at 22:59 +0100, Richard Purdie wrote:
> The latter sounds like what we'll need to do. I haven't looked at shadow
> to see what kind of finessing is required though...
> 
> Does opkg have any notion of bitbake's ASSUME_PROVIDED?

Not explicitly, but the same mechanism that we use for
BAD_RECOMMENDATIONS could be bent to do it; that wouldn't be very
hard.  

OTOH, I don't think this would buy much compared to just removing it
after installation (as we do with base-passwd already) so I'm not sure
that any extra mechanics are justified.  We'd have to address the
postinst issue either way around, so that's probably the thing to look
at first.

p.





^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-01 21:59             ` Richard Purdie
  2011-09-02  0:02               ` Mark Hatle
  2011-09-02  7:15               ` Phil Blundell
@ 2011-09-02  9:50               ` Phil Blundell
  2011-09-02 14:03                 ` Richard Purdie
  2 siblings, 1 reply; 51+ messages in thread
From: Phil Blundell @ 2011-09-02  9:50 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

[-- Attachment #1: Type: text/plain, Size: 2130 bytes --]

On Thu, 2011-09-01 at 22:59 +0100, Richard Purdie wrote:
> The latter sounds like what we'll need to do. I haven't looked at shadow
> to see what kind of finessing is required though...

Fixing the immediate problem with shadow turned out to be rather
straightforward, see attached.  However, with this done, I now encounter
two new issues.

1. the logic around $D in useradd.bbclass seems to be backwards to me
(and, empirically, isn't working because the supposedly-created users
are not showing up in my rootfs).  Specifically, it does:

        useradd_preinst () {
        OPT=""
        SYSROOT=""
        
        if test "x$D" != "x"; then
        	# Installing into a sysroot
        	SYSROOT="${STAGING_DIR_TARGET}"
        	OPT="--root ${STAGING_DIR_TARGET}"
        
        [...]
        
        useradd_sysroot () {
        	export PSEUDO="${STAGING_DIR_NATIVE}/usr/bin/pseudo"
        	export PSEUDO_LOCALSTATEDIR="${STAGING_DIR_TARGET}/var/pseudo"
        
        	# Explicitly set $D since it isn't set to anything
        	# before do_install
        	D=${D}
        	useradd_preinst
        }

It looks to me as though the code in useradd_preinst() should be using
SYSROOT="$D" (and likewise for OPT), and useradd_sysroot() should be
setting D=${STAGING_DIR_TARGET}.  But maybe there is some clever thing
going on here that I'm not properly understanding.

2. during rootfs construction, the script ordering is wrong.  All the
preinsts run before all the postinsts, which has always been a bit wrong
but hasn't caused too much of a problem in the past.  However,
crucially, this means that the useradd_preinst() runs before
base-passwd's postinst and hence /etc/passwd doesn't exist at the point
where useradd tries to modify it.

I can't think of any reasonable fix for (2) other than to teach
rootfs_ipk how to track package dependencies and run the scripts in the
right order.  I guess that wouldn't be impossible by any means but
trying to do it in a shell script is not a prospect that fills me with a
lot of enthusiasm.  Any better suggestions?

p.


[-- Attachment #2: shadow.diff --]
[-- Type: text/x-patch, Size: 1053 bytes --]

diff --git a/meta/recipes-extended/shadow/shadow_4.1.4.3.bb b/meta/recipes-extended/shadow/shadow_4.1.4.3.bb
index 728b8e5..c5a6848 100644
--- a/meta/recipes-extended/shadow/shadow_4.1.4.3.bb
+++ b/meta/recipes-extended/shadow/shadow_4.1.4.3.bb
@@ -9,7 +9,7 @@ LIC_FILES_CHKSUM = "file://COPYING;md5=08c553a87d4e51bbed50b20e0adcaede \
 
 DEPENDS = "${@base_contains('DISTRO_FEATURES', 'pam', 'libpam', '', d)}"
 RDEPENDS_${PN} = "${@base_contains('DISTRO_FEATURES', 'pam', '${PAM_PLUGINS}', '', d)}"
-PR = "r3"
+PR = "r4"
 
 SRC_URI = "http://pkg-shadow.alioth.debian.org/releases/${BPN}-${PV}.tar.bz2 \
            file://login_defs_pam.sed \
@@ -122,12 +122,13 @@ pkg_postinst_${PN} () {
 	update-alternatives --install ${base_sbindir}/vipw vipw vipw.${PN} 200
 	update-alternatives --install ${base_sbindir}/vigr vigr vigr.${PN} 200
 
-	if [ "x$D" != "x" ]; then
-		exit 1
-	fi  
-
-	pwconv
-	grpconv
+	if [ -n "$D" ]; then
+		pwconv -R $D
+		grpconv -R $D
+	else
+		pwconv
+		grpconv
+	fi
 }
 
 pkg_prerm_${PN} () {

^ permalink raw reply related	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-02  9:50               ` Phil Blundell
@ 2011-09-02 14:03                 ` Richard Purdie
  2011-09-02 18:43                   ` Phil Blundell
  0 siblings, 1 reply; 51+ messages in thread
From: Richard Purdie @ 2011-09-02 14:03 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On Fri, 2011-09-02 at 10:50 +0100, Phil Blundell wrote:
> On Thu, 2011-09-01 at 22:59 +0100, Richard Purdie wrote:
> > The latter sounds like what we'll need to do. I haven't looked at shadow
> > to see what kind of finessing is required though...
> 
> Fixing the immediate problem with shadow turned out to be rather
> straightforward, see attached.  However, with this done, I now encounter
> two new issues.
> 
> 1. the logic around $D in useradd.bbclass seems to be backwards to me
> (and, empirically, isn't working because the supposedly-created users
> are not showing up in my rootfs).  Specifically, it does:
> 
>         useradd_preinst () {
>         OPT=""
>         SYSROOT=""
>         
>         if test "x$D" != "x"; then
>         	# Installing into a sysroot
>         	SYSROOT="${STAGING_DIR_TARGET}"
>         	OPT="--root ${STAGING_DIR_TARGET}"
>         
>         [...]
>         
>         useradd_sysroot () {
>         	export PSEUDO="${STAGING_DIR_NATIVE}/usr/bin/pseudo"
>         	export PSEUDO_LOCALSTATEDIR="${STAGING_DIR_TARGET}/var/pseudo"
>         
>         	# Explicitly set $D since it isn't set to anything
>         	# before do_install
>         	D=${D}
>         	useradd_preinst
>         }
> 
> It looks to me as though the code in useradd_preinst() should be using
> SYSROOT="$D" (and likewise for OPT), and useradd_sysroot() should be
> setting D=${STAGING_DIR_TARGET}.  But maybe there is some clever thing
> going on here that I'm not properly understanding.

It looks like the useradd_sysroot code will work since D is set to
'something' and then is set correctly in the preinst. What won't work
correctly is the rootfs user creation as you point out.

So I'd agree with your change.

> 2. during rootfs construction, the script ordering is wrong.  All the
> preinsts run before all the postinsts, which has always been a bit wrong
> but hasn't caused too much of a problem in the past.  However,
> crucially, this means that the useradd_preinst() runs before
> base-passwd's postinst and hence /etc/passwd doesn't exist at the point
> where useradd tries to modify it.
> 
> I can't think of any reasonable fix for (2) other than to teach
> rootfs_ipk how to track package dependencies and run the scripts in the
> right order.  I guess that wouldn't be impossible by any means but
> trying to do it in a shell script is not a prospect that fills me with a
> lot of enthusiasm.  Any better suggestions?

Write it in python? ;-)

Seriously, does opkg have the logic in it to run this stuff? If so
perhaps we need to teach opkg about offline postinstalls since it should
already know about dependencies?

Cheers,

Richard





^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-02 14:03                 ` Richard Purdie
@ 2011-09-02 18:43                   ` Phil Blundell
  2011-09-02 19:17                     ` Mark Hatle
  0 siblings, 1 reply; 51+ messages in thread
From: Phil Blundell @ 2011-09-02 18:43 UTC (permalink / raw)
  To: Patches and discussions about the oe-core layer

On Fri, 2011-09-02 at 15:03 +0100, Richard Purdie wrote:
> Seriously, does opkg have the logic in it to run this stuff? If so
> perhaps we need to teach opkg about offline postinstalls since it should
> already know about dependencies?

Yeah, that might be a sensible plan.  I'm not entirely sure that opkg
even gets the maintainer script ordering right itself during normal
circumstances, but at least it does have a dependency graph so one could
imagine how it might be made to work correctly.  I'll have a poke at
opkg when I get a moment and see if I can figure out how much work would
be involved in that.

How do the RPM-using folks deal with this; does rpm handle everything
automatically?

p.





^ permalink raw reply	[flat|nested] 51+ messages in thread

* Re: [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-09-02 18:43                   ` Phil Blundell
@ 2011-09-02 19:17                     ` Mark Hatle
  0 siblings, 0 replies; 51+ messages in thread
From: Mark Hatle @ 2011-09-02 19:17 UTC (permalink / raw)
  To: openembedded-core

On 9/2/11 1:43 PM, Phil Blundell wrote:
> On Fri, 2011-09-02 at 15:03 +0100, Richard Purdie wrote:
>> Seriously, does opkg have the logic in it to run this stuff? If so
>> perhaps we need to teach opkg about offline postinstalls since it should
>> already know about dependencies?
> 
> Yeah, that might be a sensible plan.  I'm not entirely sure that opkg
> even gets the maintainer script ordering right itself during normal
> circumstances, but at least it does have a dependency graph so one could
> imagine how it might be made to work correctly.  I'll have a poke at
> opkg when I get a moment and see if I can figure out how much work would
> be involved in that.
> 
> How do the RPM-using folks deal with this; does rpm handle everything
> automatically?

RPM uses the dependency mappings that have the pre and post tags on them..
(Note, these are tags that we do not presently use in OE, as OE has no
equivalent to them.)  Without the pre/post dependency tags it assumes the
dependencies are met and can run through the scripts in an arbitrary order.

(For package_rpm.bbclass, we install w/o scripts and then post-process
everything to ensure the dependencies are there.. ordering is not guaranteed.)

--Mark

> p.
> 
> 
> 
> _______________________________________________
> Openembedded-core mailing list
> Openembedded-core@lists.openembedded.org
> http://lists.linuxtogo.org/cgi-bin/mailman/listinfo/openembedded-core




^ permalink raw reply	[flat|nested] 51+ messages in thread

* [PATCH 2/7] shadow: add a -native recipe with customized utilities
  2011-06-02 23:50 [PATCH 0/7] User/group creation at preinstall v2 Scott Garman
@ 2011-06-02 23:50 ` Scott Garman
  0 siblings, 0 replies; 51+ messages in thread
From: Scott Garman @ 2011-06-02 23:50 UTC (permalink / raw)
  To: openembedded-core

This adds a -native recipe for the shadow utilities.

The custom --root option allows the the following utilities to be
run within a chroot when invoked under pseudo:

* useradd
* groupadd
* usermod
* groupmod
* userdel
* groupdel
* passwd
* gpasswd
* pwconv
* pwunconv
* grpconv
* grpunconv

They can then be used to manipulate user and group account information
in target sysroots.

useradd was also modified to create home directories recursively when
necessary.

Signed-off-by: Scott Garman <scott.a.garman@intel.com>
---
 .../shadow/files/add_root_cmd_options.patch        | 1296 ++++++++++++++++++++
 .../shadow/shadow-native_4.1.4.3.bb                |   66 +
 2 files changed, 1362 insertions(+), 0 deletions(-)
 create mode 100644 meta/recipes-extended/shadow/files/add_root_cmd_options.patch
 create mode 100644 meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb

diff --git a/meta/recipes-extended/shadow/files/add_root_cmd_options.patch b/meta/recipes-extended/shadow/files/add_root_cmd_options.patch
new file mode 100644
index 0000000..db969bb
--- /dev/null
+++ b/meta/recipes-extended/shadow/files/add_root_cmd_options.patch
@@ -0,0 +1,1296 @@
+Add a --root command option to the following utilties:
+
+* useradd
+* groupadd
+* usermod
+* groupmod
+* userdel
+* groupdel
+* passwd
+* gpasswd
+* pwconv
+* pwunconv
+* grpconv
+* grpunconv
+
+This option allows the utilities to be chrooted when run under pseudo.
+They can then be used to manipulate user and group account information
+in target sysroots.
+
+The useradd utility was also modified to create home directories
+recursively when necessary.
+
+Upstream-Status: Inappropriate [Other]
+Workaround is specific to our build system.
+
+Signed-off-by: Scott Garman <scott.a.garman@intel.com>
+
+diff -urN shadow-4.1.4.3.orig//src/gpasswd.c shadow-4.1.4.3//src/gpasswd.c
+--- shadow-4.1.4.3.orig//src/gpasswd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/gpasswd.c	2011-05-28 17:09:52.346013331 -0700
+@@ -63,6 +63,7 @@
+  * (/etc/gshadow present) */
+ static bool is_shadowgrp;
+ #endif
++static const char *newroot = "";
+ 
+ /* Flags set by options */
+ static bool aflg = false;
+@@ -97,6 +98,7 @@
+ static void usage (void);
+ static RETSIGTYPE catch_signals (int killed);
+ static bool is_valid_user_list (const char *users);
++static void process_root_flag (int argc, char **argv);
+ static void process_flags (int argc, char **argv);
+ static void check_flags (int argc, int opt_index);
+ static void open_files (void);
+@@ -136,6 +138,7 @@
+ 	           "Options:\n"
+ 	           "  -a, --add USER                add USER to GROUP\n"
+ 	           "  -d, --delete USER             remove USER from GROUP\n"
++	           "  -Q  --root CHROOT_DIR         directory to chroot into\n"
+ 	           "  -r, --remove-password         remove the GROUP's password\n"
+ 	           "  -R, --restrict                restrict access to GROUP to its members\n"
+ 	           "  -M, --members USER,...        set the list of members of GROUP\n"
+@@ -226,6 +229,55 @@
+ }
+ 
+ /*
++ * process_root_flag - chroot if given the --root option
++ *
++ * We do this outside of process_flags() because
++ * the is_shadow_pwd boolean needs to be set before
++ * process_flags(), and if we do need to chroot() we
++ * must do so before is_shadow_pwd gets set.
++ */
++static void process_root_flag (int argc, char **argv)
++{
++	/*
++	 * Parse the command line options.
++	 */
++	int flag;
++	int option_index = 0;
++	static struct option long_options[] = {
++		{"root", required_argument, NULL, 'Q'},
++		{NULL, 0, NULL, '\0'}
++	};
++
++	while ((flag = getopt_long (argc, argv, "a:A:d:gM:Q:rR", long_options, &option_index)) != -1) {
++		switch (flag) {
++		case 'Q':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
++		/* no-op on everything else - they will be hanled by process_flags() */
++		}
++	}
++}
++
++/*
+  * process_flags - process the command line options and arguments
+  */
+ static void process_flags (int argc, char **argv)
+@@ -235,6 +287,7 @@
+ 	static struct option long_options[] = {
+ 		{"add", required_argument, NULL, 'a'},
+ 		{"delete", required_argument, NULL, 'd'},
++		{"root", required_argument, NULL, 'Q'},
+ 		{"remove-password", no_argument, NULL, 'r'},
+ 		{"restrict", no_argument, NULL, 'R'},
+ 		{"administrators", required_argument, NULL, 'A'},
+@@ -242,7 +295,7 @@
+ 		{NULL, 0, NULL, '\0'}
+ 		};
+ 
+-	while ((flag = getopt_long (argc, argv, "a:A:d:gM:rR", long_options, &option_index)) != -1) {
++	while ((flag = getopt_long (argc, argv, "a:A:d:gM:Q:rR", long_options, &option_index)) != -1) {
+ 		switch (flag) {
+ 		case 'a':	/* add a user */
+ 			aflg = true;
+@@ -283,6 +336,9 @@
+ 			}
+ 			Mflg = true;
+ 			break;
++		case 'Q':
++			/* no-op since we handled this in process_root_flag() earlier */
++			break;
+ 		case 'r':	/* remove group password */
+ 			rflg = true;
+ 			break;
+@@ -995,6 +1051,8 @@
+ 	setbuf (stdout, NULL);
+ 	setbuf (stderr, NULL);
+ 
++	process_root_flag (argc, argv);
++
+ #ifdef SHADOWGRP
+ 	is_shadowgrp = sgr_file_present ();
+ #endif
+diff -urN shadow-4.1.4.3.orig//src/groupadd.c shadow-4.1.4.3//src/groupadd.c
+--- shadow-4.1.4.3.orig//src/groupadd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/groupadd.c	2011-05-28 17:09:52.346013331 -0700
+@@ -76,6 +76,7 @@
+ static gid_t group_id;
+ static /*@null@*/char *group_passwd;
+ static /*@null@*/char *empty_list = NULL;
++static const char *newroot = "";
+ 
+ static bool oflg = false;	/* permit non-unique group ID to be specified with -g */
+ static bool gflg = false;	/* ID value for the new group */
+@@ -120,6 +121,7 @@
+ 	(void) fputs (_("  -o, --non-unique              allow to create groups with duplicate\n"
+ 	                "                                (non-unique) GID\n"), stderr);
+ 	(void) fputs (_("  -p, --password PASSWORD       use this encrypted password for the new group\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
+ 	(void) fputs (_("  -r, --system                  create a system account\n"), stderr);
+ 	(void) fputs ("\n", stderr);
+ 	exit (E_USAGE);
+@@ -383,12 +385,13 @@
+ 		{"key", required_argument, NULL, 'K'},
+ 		{"non-unique", no_argument, NULL, 'o'},
+ 		{"password", required_argument, NULL, 'p'},
++		{"root", required_argument, NULL, 'R'},
+ 		{"system", no_argument, NULL, 'r'},
+ 		{NULL, 0, NULL, '\0'}
+ 	};
+ 
+ 	while ((c =
+-		getopt_long (argc, argv, "fg:hK:op:r", long_options,
++		getopt_long (argc, argv, "fg:hK:op:R:r", long_options,
+ 		             &option_index)) != -1) {
+ 		switch (c) {
+ 		case 'f':
+@@ -440,6 +443,28 @@
+ 			pflg = true;
+ 			group_passwd = optarg;
+ 			break;
++		case 'R':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
+ 		case 'r':
+ 			rflg = true;
+ 			break;
+diff -urN shadow-4.1.4.3.orig//src/groupdel.c shadow-4.1.4.3//src/groupdel.c
+--- shadow-4.1.4.3.orig//src/groupdel.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/groupdel.c	2011-05-28 17:09:52.346013331 -0700
+@@ -36,6 +36,7 @@
+ 
+ #include <ctype.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <grp.h>
+ #include <pwd.h>
+ #ifdef ACCT_TOOLS_SETUID
+@@ -59,6 +60,7 @@
+ 
+ static char *group_name;
+ static gid_t group_id = -1;
++static const char *newroot = "";
+ 
+ #ifdef	SHADOWGRP
+ static bool is_shadow_grp;
+@@ -70,12 +72,14 @@
+ /*@-exitarg@*/
+ #define E_SUCCESS	0	/* success */
+ #define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
+ #define E_NOTFOUND	6	/* specified group doesn't exist */
+ #define E_GROUP_BUSY	8	/* can't remove user's primary group */
+ #define E_GRP_UPDATE	10	/* can't update group file */
+ 
+ /* local function prototypes */
+ static void usage (void);
++static void process_flags (int argc, char **argv);
+ static void grp_update (void);
+ static void close_files (void);
+ static void open_files (void);
+@@ -86,11 +90,78 @@
+  */
+ static void usage (void)
+ {
+-	fputs (_("Usage: groupdel group\n"), stderr);
++	(void) fprintf (stderr,
++					_("Usage: groupdel [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -g, --group GROUP            group name to delete\n"), stderr);
++	(void) fputs (_("  -h, --help                   display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR        directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
+ 	exit (E_USAGE);
+ }
+ 
+ /*
++ * process_flags - perform command line argument setting
++ *
++ *	process_flags() interprets the command line arguments and sets
++ *	the values that the user will be created with accordingly. The
++ *	values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"group", required_argument, NULL, 'g'},
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "g:R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'g':
++				group_name = optarg;
++				break;
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++							_("%s: invalid chroot path '%s'\n"),
++							Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++							_("%s: chroot directory %s does not exist\n"),
++							Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++							_("%s: unable to chroot to directory %s\n"),
++							Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
++/*
+  * grp_update - update group file entries
+  *
+  *	grp_update() writes the new records to the group files.
+@@ -328,14 +399,14 @@
+ 	(void) bindtextdomain (PACKAGE, LOCALEDIR);
+ 	(void) textdomain (PACKAGE);
+ 
+-	if (argc != 2) {
++   if (argc == 1) {
+ 		usage ();
+ 	}
+ 
+-	group_name = argv[1];
+-
+ 	OPENLOG ("groupdel");
+ 
++	process_flags (argc, argv);
++
+ #ifdef ACCT_TOOLS_SETUID
+ #ifdef USE_PAM
+ 	{
+diff -urN shadow-4.1.4.3.orig//src/groupmod.c shadow-4.1.4.3//src/groupmod.c
+--- shadow-4.1.4.3.orig//src/groupmod.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/groupmod.c	2011-05-28 17:09:52.346013331 -0700
+@@ -79,6 +79,7 @@
+ static char *group_passwd;
+ static gid_t group_id;
+ static gid_t group_newid;
++static char *newroot = "";
+ 
+ struct cleanup_info_mod info_passwd;
+ struct cleanup_info_mod info_group;
+@@ -126,6 +127,7 @@
+ 	(void) fputs (_("  -o, --non-unique              allow to use a duplicate (non-unique) GID\n"), stderr);
+ 	(void) fputs (_("  -p, --password PASSWORD       change the password to this (encrypted)\n"
+ 	                "                                PASSWORD\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
+ 	(void) fputs ("\n", stderr);
+ 	exit (E_USAGE);
+ }
+@@ -346,10 +348,11 @@
+ 		{"new-name", required_argument, NULL, 'n'},
+ 		{"non-unique", no_argument, NULL, 'o'},
+ 		{"password", required_argument, NULL, 'p'},
++		{"root", required_argument, NULL, 'R'},
+ 		{NULL, 0, NULL, '\0'}
+ 	};
+ 	while ((c =
+-		getopt_long (argc, argv, "g:hn:op:",
++		getopt_long (argc, argv, "g:hn:op:R:",
+ 		             long_options, &option_index)) != -1) {
+ 		switch (c) {
+ 		case 'g':
+@@ -373,6 +376,28 @@
+ 			group_passwd = optarg;
+ 			pflg = true;
+ 			break;
++		case 'R':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
+ 		default:
+ 			usage ();
+ 		}
+diff -urN shadow-4.1.4.3.orig//src/grpconv.c shadow-4.1.4.3//src/grpconv.c
+--- shadow-4.1.4.3.orig//src/grpconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/grpconv.c	2011-05-28 17:09:52.346013331 -0700
+@@ -39,6 +39,7 @@
+ 
+ #include <errno.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <grp.h>
+ #include <stdio.h>
+ #include <stdlib.h>
+@@ -50,6 +51,14 @@
+ #ifdef SHADOWGRP
+ #include "groupio.h"
+ #include "sgroupio.h"
++
++/*
++ * exit status values
++ */
++/*@-exitarg@*/
++#define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
++
+ /*
+  * Global variables
+  */
+@@ -57,9 +66,12 @@
+ 
+ static bool gr_locked  = false;
+ static bool sgr_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -82,6 +94,77 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: grpconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ *	process_flags() interprets the command line arguments and sets
++ *	the values that the user will be created with accordingly. The
++ *	values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
+ int main (int argc, char **argv)
+ {
+ 	const struct group *gr;
+@@ -100,6 +183,8 @@
+ 
+ 	OPENLOG ("grpconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (gr_lock () == 0) {
+ 		fprintf (stderr,
+ 		         _("%s: cannot lock %s; try again later.\n"),
+diff -urN shadow-4.1.4.3.orig//src/grpunconv.c shadow-4.1.4.3//src/grpunconv.c
+--- shadow-4.1.4.3.orig//src/grpunconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/grpunconv.c	2011-05-28 17:09:52.346013331 -0700
+@@ -43,6 +43,7 @@
+ #include <stdlib.h>
+ #include <string.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <time.h>
+ #include <unistd.h>
+ #include <grp.h>
+@@ -51,6 +52,14 @@
+ #ifdef SHADOWGRP
+ #include "groupio.h"
+ #include "sgroupio.h"
++
++/*
++ * exit status values
++ */
++/*@-exitarg@*/
++#define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
++
+ /*
+  * Global variables
+  */
+@@ -58,9 +67,12 @@
+ 
+ static bool gr_locked  = false;
+ static bool sgr_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -83,6 +95,77 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: grpunconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ * process_flags() interprets the command line arguments and sets
++ * the values that the user will be created with accordingly. The
++ * values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
+ int main (int argc, char **argv)
+ {
+ 	const struct group *gr;
+@@ -100,6 +183,8 @@
+ 
+ 	OPENLOG ("grpunconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (sgr_file_present () == 0) {
+ 		exit (0);	/* no /etc/gshadow, nothing to do */
+ 	}
+diff -urN shadow-4.1.4.3.orig//src/passwd.c shadow-4.1.4.3//src/passwd.c
+--- shadow-4.1.4.3.orig//src/passwd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/passwd.c	2011-05-28 17:09:52.346013331 -0700
+@@ -75,6 +75,7 @@
+ static char *name;		/* The name of user whose password is being changed */
+ static char *myname;		/* The current user's name */
+ static bool amroot;		/* The caller's real UID was 0 */
++static const char *newroot = "";
+ 
+ static bool
+     aflg = false,			/* -a - show status for all users */
+@@ -174,6 +175,7 @@
+ 	         "  -n, --mindays MIN_DAYS        set minimum number of days before password\n"
+ 	         "                                change to MIN_DAYS\n"
+ 	         "  -q, --quiet                   quiet mode\n"
++	         "  -R, --root CHROOT_DIR         directory to chroot into\n"
+ 	         "  -r, --repository REPOSITORY   change password in REPOSITORY repository\n"
+ 	         "  -S, --status                  report password status on the named account\n"
+ 	         "  -u, --unlock                  unlock the password of the named account\n"
+@@ -803,6 +805,7 @@
+ 			{"lock", no_argument, NULL, 'l'},
+ 			{"mindays", required_argument, NULL, 'n'},
+ 			{"quiet", no_argument, NULL, 'q'},
++			{"root", required_argument, NULL, 'R'},
+ 			{"repository", required_argument, NULL, 'r'},
+ 			{"status", no_argument, NULL, 'S'},
+ 			{"unlock", no_argument, NULL, 'u'},
+@@ -811,7 +814,7 @@
+ 			{NULL, 0, NULL, '\0'}
+ 		};
+ 
+-		while ((c = getopt_long (argc, argv, "adei:kln:qr:Suw:x:",
++		while ((c = getopt_long (argc, argv, "adei:kln:qR:r:Suw:x:",
+ 		                         long_options, &option_index)) != -1) {
+ 			switch (c) {
+ 			case 'a':
+@@ -858,6 +861,28 @@
+ 			case 'q':
+ 				qflg = true;	/* ok for users */
+ 				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++				            _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
+ 			case 'r':
+ 				/* -r repository (files|nis|nisplus) */
+ 				/* only "files" supported for now */
+diff -urN shadow-4.1.4.3.orig//src/pwconv.c shadow-4.1.4.3//src/pwconv.c
+--- shadow-4.1.4.3.orig//src/pwconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/pwconv.c	2011-05-28 17:09:52.346013331 -0700
+@@ -59,6 +59,7 @@
+ 
+ #include <errno.h>
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <pwd.h>
+ #include <stdio.h>
+ #include <stdlib.h>
+@@ -79,6 +80,7 @@
+ #define E_SUCCESS	0	/* success */
+ #define E_NOPERM	1	/* permission denied */
+ #define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
+ #define E_FAILURE	3	/* unexpected failure, nothing done */
+ #define E_MISSING	4	/* unexpected failure, passwd file missing */
+ #define E_PWDBUSY	5	/* passwd file(s) busy */
+@@ -90,9 +92,12 @@
+ 
+ static bool spw_locked = false;
+ static bool pw_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -115,6 +120,77 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: pwconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ *	process_flags() interprets the command line arguments and sets
++ *	the values that the user will be created with accordingly. The
++ *	values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
++
+ int main (int argc, char **argv)
+ {
+ 	const struct passwd *pw;
+@@ -122,9 +198,6 @@
+ 	const struct spwd *sp;
+ 	struct spwd spent;
+ 
+-	if (1 != argc) {
+-		(void) fputs (_("Usage: pwconv\n"), stderr);
+-	}
+ 	Prog = Basename (argv[0]);
+ 
+ 	(void) setlocale (LC_ALL, "");
+@@ -133,6 +206,8 @@
+ 
+ 	OPENLOG ("pwconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (pw_lock () == 0) {
+ 		fprintf (stderr,
+ 		         _("%s: cannot lock %s; try again later.\n"),
+diff -urN shadow-4.1.4.3.orig//src/pwunconv.c shadow-4.1.4.3//src/pwunconv.c
+--- shadow-4.1.4.3.orig//src/pwunconv.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/pwunconv.c	2011-05-28 17:09:52.356013600 -0700
+@@ -35,6 +35,7 @@
+ #ident "$Id: pwunconv.c 2852 2009-04-30 21:44:35Z nekral-guest $"
+ 
+ #include <fcntl.h>
++#include <getopt.h>
+ #include <pwd.h>
+ #include <stdio.h>
+ #include <sys/types.h>
+@@ -46,15 +47,24 @@
+ #include "shadowio.h"
+ 
+ /*
++ * exit status values
++ */
++/*@-exitarg@*/
++#define E_USAGE		2	/* invalid command syntax */
++#define E_BAD_ARG	3	/* invalid argument to option */
++/*
+  * Global variables
+  */
+ char *Prog;
+ 
+ static bool spw_locked = false;
+ static bool pw_locked = false;
++static const char *newroot = "";
+ 
+ /* local function prototypes */
+ static void fail_exit (int status);
++static void usage (void);
++static void process_flags (int argc, char **argv);
+ 
+ static void fail_exit (int status)
+ {
+@@ -75,6 +85,76 @@
+ 	exit (status);
+ }
+ 
++/*
++ * usage - display usage message and exit
++ */
++static void usage (void)
++{
++	(void) fprintf (stderr,
++					_("Usage: pwunconv [options]\n"
++					  "\n"
++					  "Options:\n"),
++					Prog);
++	(void) fputs (_("  -h, --help                    display this help message and exit\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
++	(void) fputs ("\n", stderr);
++	exit (E_USAGE);
++}
++
++/*
++ * process_flags - perform command line argument setting
++ *
++ * process_flags() interprets the command line arguments and sets
++ * the values that the user will be created with accordingly. The
++ * values are checked for sanity.
++ */
++static void process_flags (int argc, char **argv)
++{
++	{
++		/*
++		 * Parse the command line options.
++		 */
++		int c;
++		static struct option long_options[] = {
++			{"help", no_argument, NULL, 'h'},
++			{"root", required_argument, NULL, 'R'},
++			{NULL, 0, NULL, '\0'}
++		};
++		while ((c = getopt_long (argc, argv,
++								 "R:",
++								 long_options, NULL)) != -1) {
++			switch (c) {
++			case 'h':
++				usage ();
++				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
++			default:
++				usage ();
++			}
++		}
++	}
++}
+ 
+ int main (int argc, char **argv)
+ {
+@@ -93,6 +173,8 @@
+ 
+ 	OPENLOG ("pwunconv");
+ 
++	process_flags (argc, argv);
++
+ 	if (!spw_file_present ()) {
+ 		/* shadow not installed, do nothing */
+ 		exit (0);
+diff -urN shadow-4.1.4.3.orig//src/useradd.c shadow-4.1.4.3//src/useradd.c
+--- shadow-4.1.4.3.orig//src/useradd.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/useradd.c	2011-05-28 17:10:25.446909971 -0700
+@@ -112,6 +112,7 @@
+ #ifdef WITH_SELINUX
+ static const char *user_selinux = "";
+ #endif
++static const char *newroot = "";
+ 
+ static long user_expire = -1;
+ static bool is_shadow_pwd;
+@@ -189,6 +190,7 @@
+ static void new_spent (struct spwd *);
+ static void grp_update (void);
+ 
++static void process_root_flag (int argc, char **argv);
+ static void process_flags (int argc, char **argv);
+ static void close_files (void);
+ static void open_files (void);
+@@ -711,6 +713,7 @@
+ 	(void) fputs (_("  -o, --non-unique              allow to create users with duplicate\n"
+ 	                "                                (non-unique) UID\n"), stderr);
+ 	(void) fputs (_("  -p, --password PASSWORD       encrypted password of the new account\n"), stderr);
++	(void) fputs (_("  -R, --root CHROOT_DIR         directory to chroot into\n"), stderr);
+ 	(void) fputs (_("  -r, --system                  create a system account\n"), stderr);
+ 	(void) fputs (_("  -s, --shell SHELL             login shell of the new account\n"), stderr);
+ 	(void) fputs (_("  -u, --uid UID                 user ID of the new account\n"), stderr);
+@@ -943,6 +946,59 @@
+ }
+ 
+ /*
++ * process_root_flag - chroot if given the --root option
++ *
++ * We do this outside of process_flags() because
++ * the is_shadow_pwd boolean needs to be set before
++ * process_flags(), and if we do need to chroot() we
++ * must do so before is_shadow_pwd gets set.
++ */
++static void process_root_flag (int argc, char **argv)
++{
++	/*
++	 * Parse the command line options.
++	 */
++	int c;
++	static struct option long_options[] = {
++		{"root", required_argument, NULL, 'R'},
++		{NULL, 0, NULL, '\0'}
++	};
++	while ((c = getopt_long (argc, argv,
++#ifdef WITH_SELINUX
++	                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:UZ:",
++#else
++	                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:U",
++#endif
++	                         long_options, NULL)) != -1) {
++		switch (c) {
++		case 'R':
++			if ('/' != optarg[0]) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
++		/* no-op on everything else - they will be hanled by process_flags() */
++		}
++	}
++}
++
++/*
+  * process_flags - perform command line argument setting
+  *
+  *	process_flags() interprets the command line arguments and sets
+@@ -978,6 +1034,7 @@
+ 			{"no-user-group", no_argument, NULL, 'N'},
+ 			{"non-unique", no_argument, NULL, 'o'},
+ 			{"password", required_argument, NULL, 'p'},
++			{"root", required_argument, NULL, 'R'},
+ 			{"system", no_argument, NULL, 'r'},
+ 			{"shell", required_argument, NULL, 's'},
+ #ifdef WITH_SELINUX
+@@ -989,9 +1046,9 @@
+ 		};
+ 		while ((c = getopt_long (argc, argv,
+ #ifdef WITH_SELINUX
+-		                         "b:c:d:De:f:g:G:k:K:lmMNop:rs:u:UZ:",
++		                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:UZ:",
+ #else
+-		                         "b:c:d:De:f:g:G:k:K:lmMNop:rs:u:U",
++		                         "b:c:d:De:f:g:G:k:K:lmMNop:R:rs:u:U",
+ #endif
+ 		                         long_options, NULL)) != -1) {
+ 			switch (c) {
+@@ -1156,6 +1213,9 @@
+ 				}
+ 				user_pass = optarg;
+ 				break;
++			case 'R':
++				/* no-op since we handled this in process_root_flag() earlier */
++				break;
+ 			case 'r':
+ 				rflg = true;
+ 				break;
+@@ -1748,8 +1808,16 @@
+ #ifdef WITH_SELINUX
+ 		selinux_file_context (user_home);
+ #endif
+-		/* XXX - create missing parent directories.  --marekm */
+-		if (mkdir (user_home, 0) != 0) {
++		/* shell out to invoke mkdir -p 
++		 * creating a subshell under pseudo's chroot() breaks the jail
++		 * (bug in pseudo), so make sure we include the full host path
++		 * to the sysroot when the --root option is in use.
++		 */
++		int sysroot_path_len = strlen(newroot);
++		int home_path_len = strlen(user_home);
++		char cmd[sysroot_path_len + home_path_len + 10];
++		sprintf(cmd, "mkdir -p %s%s", newroot, user_home);
++		if (system (cmd) != 0) {
+ 			fprintf (stderr,
+ 			         _("%s: cannot create directory %s\n"),
+ 			         Prog, user_home);
+@@ -1861,6 +1929,7 @@
+ 	 */
+ 	user_groups[0] = (char *) 0;
+ 
++	process_root_flag (argc, argv);
+ 
+ 	is_shadow_pwd = spw_file_present ();
+ #ifdef SHADOWGRP
+diff -urN shadow-4.1.4.3.orig//src/userdel.c shadow-4.1.4.3//src/userdel.c
+--- shadow-4.1.4.3.orig//src/userdel.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/userdel.c	2011-05-28 17:09:52.356013600 -0700
+@@ -79,6 +79,7 @@
+ static char *user_name;
+ static uid_t user_id;
+ static char *user_home;
++static const char *newroot = "";
+ 
+ static bool fflg = false;
+ static bool rflg = false;
+@@ -119,6 +120,7 @@
+ 	         "  -f, --force                   force removal of files,\n"
+ 	         "                                even if not owned by user\n"
+ 	         "  -h, --help                    display this help message and exit\n"
++	         "  -R, --root CHROOT_DIR         directory to chroot into\n"
+ 	         "  -r, --remove                  remove home directory and mail spool\n"
+ 	         "\n"), stderr);
+ 	exit (E_USAGE);
+@@ -768,12 +770,34 @@
+ 			{"remove", no_argument, NULL, 'r'},
+ 			{NULL, 0, NULL, '\0'}
+ 		};
+-		while ((c = getopt_long (argc, argv, "fhr",
++		while ((c = getopt_long (argc, argv, "fhR:r",
+ 		                         long_options, NULL)) != -1) {
+ 			switch (c) {
+ 			case 'f':	/* force remove even if not owned by user */
+ 				fflg = true;
+ 				break;
++			case 'R':
++				if ('/' != optarg[0]) {
++					fprintf (stderr,
++					         _("%s: invalid chroot path '%s'\n"),
++					         Prog, optarg);
++					exit (E_BAD_ARG);
++				}
++				newroot = optarg;
++
++				if (access (newroot, F_OK) != 0) {
++					fprintf(stderr,
++					        _("%s: chroot directory %s does not exist\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				if ( chroot(newroot) != 0 ) {
++					fprintf(stderr,
++					        _("%s: unable to chroot to directory %s\n"),
++					        Prog, newroot);
++					exit (E_BAD_ARG);
++				}
++				break;
+ 			case 'r':	/* remove home dir and mailbox */
+ 				rflg = true;
+ 				break;
+diff -urN shadow-4.1.4.3.orig//src/usermod.c shadow-4.1.4.3//src/usermod.c
+--- shadow-4.1.4.3.orig//src/usermod.c	2011-02-13 09:58:16.000000000 -0800
++++ shadow-4.1.4.3//src/usermod.c	2011-05-28 17:09:52.356013600 -0700
+@@ -110,6 +110,7 @@
+ static long user_newinactive;
+ static long sys_ngroups;
+ static char **user_groups;	/* NULL-terminated list */
++static const char *newroot = "";
+ 
+ static bool
+     aflg = false,		/* append to existing secondary group set */
+@@ -164,6 +165,7 @@
+ #endif
+ static void grp_update (void);
+ 
++static void process_root_flag (int, char **);
+ static void process_flags (int, char **);
+ static void close_files (void);
+ static void open_files (void);
+@@ -323,6 +325,7 @@
+ 	         "                                new location (use only with -d)\n"
+ 	         "  -o, --non-unique              allow using duplicate (non-unique) UID\n"
+ 	         "  -p, --password PASSWORD       use encrypted password for the new password\n"
++	         "  -R  --root CHROOT_DIR         directory to chroot into\n"
+ 	         "  -s, --shell SHELL             new login shell for the user account\n"
+ 	         "  -u, --uid UID                 new UID for the user account\n"
+ 	         "  -U, --unlock                  unlock the user account\n"
+@@ -802,6 +805,60 @@
+ }
+ 
+ /*
++ * process_root_flag - chroot if given the --root option
++ *
++ * We do this outside of process_flags() because
++ * the is_shadow_pwd boolean needs to be set before
++ * process_flags(), and if we do need to chroot() we
++ * must do so before is_shadow_pwd gets set.
++ */
++static void process_root_flag (int argc, char **argv)
++{
++	/*
++	 * Parse the command line options.
++	 */
++	int c;
++	static struct option long_options[] = {
++		{"root", required_argument, NULL, 'R'},
++		{NULL, 0, NULL, '\0'}
++	};
++	while ((c = getopt_long (argc, argv,
++#ifdef WITH_SELINUX
++                             "ac:d:e:f:g:G:hl:Lmop:R:s:u:UZ:",
++#else
++	                         "ac:d:e:f:g:G:hl:Lmop:R:s:u:U",
++#endif
++	                         long_options, NULL)) != -1) {
++		switch (c) {
++		case 'R':
++			if (    (!VALID (optarg) ) 
++				|| (   ('/' != optarg[0]) ) ) {
++				fprintf (stderr,
++				         _("%s: invalid chroot path '%s'\n"),
++				         Prog, optarg);
++				exit (E_BAD_ARG);
++			}
++			newroot = optarg;
++
++			if (access (newroot, F_OK) != 0) {
++				fprintf(stderr,
++				        _("%s: chroot directory %s does not exist\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			if ( chroot(newroot) != 0 ) {
++				fprintf(stderr,
++				        _("%s: unable to chroot to directory %s\n"),
++				        Prog, newroot);
++				exit (E_BAD_ARG);
++			}
++			break;
++		/* no-op on everything else - they will be hanled by process_flags() */
++		}
++	}
++}
++
++/*
+  * process_flags - perform command line argument setting
+  *
+  *	process_flags() interprets the command line arguments and sets the
+@@ -895,6 +952,7 @@
+ 			{"move-home", no_argument, NULL, 'm'},
+ 			{"non-unique", no_argument, NULL, 'o'},
+ 			{"password", required_argument, NULL, 'p'},
++			{"root", required_argument, NULL, 'R'},
+ #ifdef WITH_SELINUX
+ 			{"selinux-user", required_argument, NULL, 'Z'},
+ #endif
+@@ -905,9 +963,9 @@
+ 		};
+ 		while ((c = getopt_long (argc, argv,
+ #ifdef WITH_SELINUX
+-			                 "ac:d:e:f:g:G:hl:Lmop:s:u:UZ:",
++			                 "ac:d:e:f:g:G:hl:Lmop:R:s:u:UZ:",
+ #else
+-			                 "ac:d:e:f:g:G:hl:Lmop:s:u:U",
++			                 "ac:d:e:f:g:G:hl:Lmop:R:s:u:U",
+ #endif
+ 			                 long_options, NULL)) != -1) {
+ 			switch (c) {
+@@ -999,6 +1057,9 @@
+ 				user_pass = optarg;
+ 				pflg = true;
+ 				break;
++			case 'R':
++				/* no-op since we handled this in process_root_flag() earlier */
++				break;
+ 			case 's':
+ 				if (!VALID (optarg)) {
+ 					fprintf (stderr,
+@@ -1715,6 +1776,8 @@
+ 
+ 	OPENLOG ("usermod");
+ 
++	process_root_flag (argc, argv);
++
+ 	is_shadow_pwd = spw_file_present ();
+ #ifdef SHADOWGRP
+ 	is_shadow_grp = sgr_file_present ();
diff --git a/meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb b/meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
new file mode 100644
index 0000000..2f93e05
--- /dev/null
+++ b/meta/recipes-extended/shadow/shadow-native_4.1.4.3.bb
@@ -0,0 +1,66 @@
+SUMMARY = "Tools to change and administer password and group data"
+DESCRIPTION = "Tools to change and administer password and group data"
+HOMEPAGE = "http://pkg-shadow.alioth.debian.org"
+BUGTRACKER = "https://alioth.debian.org/tracker/?group_id=30580"
+SECTION = "base utils"
+PRIORITY = "optional"
+LICENSE = "BSD | Artistic"
+LIC_FILES_CHKSUM = "file://COPYING;md5=08c553a87d4e51bbed50b20e0adcaede \
+                    file://src/passwd.c;firstline=8;endline=30;md5=2899a045e90511d0e043b85a7db7e2fe"
+
+PR = "r0"
+
+SRC_URI = "ftp://pkg-shadow.alioth.debian.org/pub/pkg-shadow/shadow-${PV}.tar.bz2 \
+           file://shadow.automake-1.11.patch \
+           file://shadow-4.1.3-dots-in-usernames.patch \
+           file://shadow-4.1.4.2-env-reset-keep-locale.patch \
+           file://add_root_cmd_options.patch"
+
+SRC_URI[md5sum] = "b8608d8294ac88974f27b20f991c0e79"
+SRC_URI[sha256sum] = "633f5bb4ea0c88c55f3642c97f9d25cbef74f82e0b4cf8d54e7ad6f9f9caa778" 
+
+inherit autotools gettext native
+
+EXTRA_OECONF += "--without-audit \
+                 --without-libcrack \
+                 --without-libpam \
+                 --without-selinux"
+
+do_install_append() {
+	# Enable CREATE_HOME by default.
+	sed -i 's/#CREATE_HOME/CREATE_HOME/g' ${D}${sysconfdir}/login.defs
+
+	# As we are on an embedded system, ensure the users mailbox is in
+	# ~/ not /var/spool/mail by default, as who knows where or how big
+	# /var is. The system MDA will set this later anyway.
+	sed -i 's/MAIL_DIR/#MAIL_DIR/g' ${D}${sysconfdir}/login.defs
+	sed -i 's/#MAIL_FILE/MAIL_FILE/g' ${D}${sysconfdir}/login.defs
+
+	# Disable checking emails.
+	sed -i 's/MAIL_CHECK_ENAB/#MAIL_CHECK_ENAB/g' ${D}${sysconfdir}/login.defs
+
+	# Now we don't have a mail system. Disable mail creation for now.
+	sed -i 's:/bin/bash:/bin/sh:g' ${D}${sysconfdir}/default/useradd
+	sed -i '/^CREATE_MAIL_SPOOL/ s:^:#:' ${D}${sysconfdir}/default/useradd
+
+	install -d ${D}${sbindir} ${D}${base_sbindir} ${D}${base_bindir} 
+	for i in passwd chfn newgrp chsh ; do
+		mv ${D}${bindir}/$i ${D}${bindir}/$i.${PN}
+	done
+
+	mv ${D}${sbindir}/chpasswd ${D}${sbindir}/chpasswd.${PN}
+}
+
+pkg_postinst_${PN} () {
+	update-alternatives --install ${bindir}/passwd passwd passwd.${PN} 200
+	update-alternatives --install ${sbindir}/chpasswd chpasswd chpasswd.${PN} 200
+	update-alternatives --install ${bindir}/chfn chfn chfn.${PN} 200
+	update-alternatives --install ${bindir}/newgrp newgrp newgrp.${PN} 200
+	update-alternatives --install ${bindir}/chsh chsh chsh.${PN} 200
+}
+
+pkg_prerm_${PN} () {
+	for i in passwd chpasswd chfn newgrp chsh ; do
+		update-alternatives --remove $i $i.${PN}
+	done
+}
-- 
1.7.1




^ permalink raw reply related	[flat|nested] 51+ messages in thread

end of thread, other threads:[~2011-09-02 19:22 UTC | newest]

Thread overview: 51+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2011-05-31 18:13 [PATCH 0/7] User/group creation at preinstall Scott Garman
2011-05-31 19:53 ` Scott Garman
2011-05-31 18:13 ` [PATCH 1/7] shadow: recipe and patch cleanup Scott Garman
2011-05-31 19:53   ` Scott Garman
2011-05-31 18:13 ` [PATCH 2/7] shadow: add a -native recipe with customized utilities Scott Garman
2011-05-31 19:53   ` Scott Garman
2011-06-01  9:47   ` Phil Blundell
2011-06-01 12:34     ` Martyn Welch
2011-06-01 13:42       ` Phil Blundell
2011-06-01 17:43     ` Scott Garman
2011-06-01 21:05       ` Mark Hatle
2011-06-02 11:19         ` Phil Blundell
2011-09-01 14:46   ` Phil Blundell
2011-09-01 16:41   ` Phil Blundell
2011-09-01 16:54     ` Mark Hatle
2011-09-01 16:58       ` Phil Blundell
2011-09-01 17:25         ` Mark Hatle
2011-09-01 19:44           ` Phil Blundell
2011-09-01 21:59             ` Richard Purdie
2011-09-02  0:02               ` Mark Hatle
2011-09-02  7:15               ` Phil Blundell
2011-09-02  9:50               ` Phil Blundell
2011-09-02 14:03                 ` Richard Purdie
2011-09-02 18:43                   ` Phil Blundell
2011-09-02 19:17                     ` Mark Hatle
2011-05-31 18:13 ` [PATCH 3/7] base-passwd: add -cross recipe with default login.defs Scott Garman
2011-05-31 19:53   ` Scott Garman
2011-05-31 18:13 ` [PATCH 4/7] useradd.bbclass: new class for managing user/group permissions Scott Garman
2011-05-31 19:53   ` Scott Garman
2011-05-31 18:13 ` [PATCH 5/7] useradd-example: example recipe for using inherit useradd Scott Garman
2011-05-31 19:53   ` Scott Garman
2011-05-31 19:09   ` Mark Hatle
2011-05-31 18:13 ` [PATCH 6/7] bitbake.conf: set PSEUDO_PASSWD within FAKEROOTENV Scott Garman
2011-05-31 19:53   ` Scott Garman
2011-05-31 18:13 ` [PATCH 7/7] package_rpm.bbclass: make RPM use on-disk permissions Scott Garman
2011-05-31 19:53   ` Scott Garman
2011-05-31 18:45 ` [poky] [PATCH 0/7] User/group creation at preinstall Koen Kooi
2011-05-31 18:45   ` Koen Kooi
2011-05-31 19:06   ` [poky] " Saul Wold
2011-05-31 19:06     ` Saul Wold
2011-05-31 19:09     ` Mark Hatle
2011-05-31 19:51     ` [poky] " Scott Garman
2011-05-31 19:51       ` Scott Garman
2011-05-31 19:57       ` [poky] " Otavio Salvador
2011-05-31 21:16         ` Mark Hatle
2011-05-31 21:16           ` [OE-core] " Mark Hatle
2011-05-31 21:27           ` [poky] " Scott Garman
2011-05-31 21:51             ` Richard Purdie
2011-05-31 21:25       ` Richard Purdie
2011-05-31 21:25         ` [OE-core] " Richard Purdie
2011-06-02 23:50 [PATCH 0/7] User/group creation at preinstall v2 Scott Garman
2011-06-02 23:50 ` [PATCH 2/7] shadow: add a -native recipe with customized utilities Scott Garman

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.