[Pkg-shadow-devel] Re: [Pkg-shadow-commits] r298 - trunk/debian/patches
Nicolas François
nicolas.francois@centraliens.net
Sun, 26 Jun 2005 23:05:29 +0200
--zhXaljGHf11kAtnf
Content-Type: text/plain; charset=us-ascii
Content-Disposition: inline
Hello,
On Sun, Jun 26, 2005 at 08:51:04PM +0300, Alexander Gattin wrote:
> OK. When we discussed the issue on IRC, I desided the
> way pwck works was "propagating passwd to shadow", i.e.
> master-to-shadow mirroring.
>
> This is policy aspect, I mean this takes one source of
> data (passwd) as primary and considers other as
> derived.
>
> Technically this has some problems. In case of
> passwd/shadow former has 7 fields while latter has 9.
>
> So technically it's impossible to get all the data for
> shadow from passwd, when there's an entry in latter
> which is missing from the former. At least, while some
> missing fields may have reasonable defaults, e.g.
> sp_min, sp_max, sp_warn, sp_inact, others are hardly
> re-creatable (sp_pwdp, sp_lstchg, sp_expire).
>
> I think the clash of pwck's policy against technical
> problems is the cause why pwck does nothing when
> "/etc/passwd contains an entry which is not in
> /etc/shadow". I.e. technical problems prevent pwck
> from passwd->shadow mirroring while _both_ ;) policy
> and technical problems prevent it from mirroring in
> reverse direction.
The more I dug into this, the more I was re-implementing pwconv/grpconv.
So my final implementation is quite a cut&past from {pw,grp}conv.
So maybe it is better to just issue a warning:
"This user/group does not have a shadowed entry. You should use
pwconv/grpconv to convert it to shadow."
Note: this warning will be issued only if the shadowed file exist (and
{pw,grp}ck is compiled with SHADOWPWD/SHADOWGRP.
I attach a update for 426_grpck_group-gshadow_members_consistency.
Tell me if you prefer a warning-only solution.
Also, Tomaz, as I will submit it to you later (after an update/reindent),
it would be nice to have your opinion.
Kind Regards,
--
Nekral
--zhXaljGHf11kAtnf
Content-Type: text/plain; charset=us-ascii
Content-Disposition: attachment; filename=426_grpck_group-gshadow_members_consistency
Goal: Warn when the members of a group differ in /etc/groups and /etc/gshadow.
Fixes: #75181
Status wrt upstream: It should be forwarded to upstream.
Note: With this patch, the user will be asked to add an entry to the shadowed
files (/etc/shadow for pwck or /etc/gshadow for grpck) when this entry is
present in non-shadowed file and not present in the shadowed file.
Index: shadow-4.0.3/src/grpck.c
===================================================================
--- shadow-4.0.3.orig/src/grpck.c 2005-06-24 00:02:49.000000000 +0200
+++ shadow-4.0.3/src/grpck.c 2005-06-26 22:05:06.668559000 +0200
@@ -144,7 +144,7 @@
{
int arg;
int errors = 0;
- int deleted = 0;
+ int changed = 0;
int i;
int prune = 0;
struct commonio_entry *gre, *tgre;
@@ -337,7 +337,7 @@
delete_gr:
SYSLOG ((LOG_INFO, "delete group line `%s'",
gre->line));
- deleted++;
+ changed++;
__gr_del_entry (gre);
continue;
@@ -432,11 +432,76 @@
SYSLOG ((LOG_INFO, "delete member `%s' group `%s'",
grp->gr_mem[i], grp->gr_name));
- deleted++;
+ changed++;
delete_member (grp->gr_mem, grp->gr_mem[i]);
gre->changed = 1;
__gr_set_changed ();
}
+
+#ifdef SHADOWGRP
+ /*
+ * Make sure this entry exists in the /etc/gshadow file.
+ */
+
+ if (is_shadow)
+ {
+ sgr = (struct sgrp *)sgr_locate (grp->gr_name);
+ if (sgr == NULL) {
+ printf (_("no matching group file entry in %s\n"), sgr_file);
+ printf (_("add group `%s' in %s? "),
+ grp->gr_name, sgr_file);
+ errors++;
+ if (yes_or_no ())
+ {
+ struct sgrp sg;
+ static char *empty = NULL;
+ sg.sg_name = grp->gr_name;
+ sg.sg_passwd = grp->gr_passwd;
+ sg.sg_adm = ∅
+ sg.sg_mem = grp->gr_mem;
+ SYSLOG ((LOG_INFO, "add group `%s' to `%s'",
+ grp->gr_name, sgr_file));
+ changed++;
+
+ if (!sgr_update(&sg))
+ {
+ fprintf (stderr,
+ _("%s: can't update shadow entry for %s\n"),
+ Prog, sg.sg_name);
+ exit (E_CANT_UPDATE);
+ }
+ /* remove password from /etc/group */
+ grp->gr_passwd = SHADOW_PASSWD_STRING; /* XXX warning: const */
+ if (!gr_update (grp)) {
+ fprintf (stderr,
+ _("%s: can't update entry for group %s\n"),
+ Prog, grp->gr_name);
+ exit (E_CANT_UPDATE);
+ }
+ }
+ } else {
+ /**
+ * Verify that the all members defined in /etc/group are also
+ * present in /etc/gshadow.
+ */
+ char **pgrp_mem,**psgr_mem;
+ for (pgrp_mem=grp->gr_mem; *pgrp_mem; pgrp_mem++)
+ {
+ for (psgr_mem=sgr->sg_mem; *psgr_mem; psgr_mem++)
+ {
+ if (strcmp(*pgrp_mem, *psgr_mem) == 0)
+ break;
+ }
+ if (*psgr_mem == NULL)
+ {
+ printf ("'%s' is a member of the '%s' group in %s but not in %s\n",
+ *pgrp_mem, sgr->sg_name, grp_file, sgr_file);
+ }
+ }
+ }
+ }
+#endif
+
}
#ifdef SHADOWGRP
@@ -483,7 +548,7 @@
delete_sg:
SYSLOG ((LOG_INFO, "delete shadow line `%s'",
sge->line));
- deleted++;
+ changed++;
__sgr_del_entry (sge);
continue;
@@ -541,12 +606,32 @@
* Make sure this entry exists in the /etc/group file.
*/
- if (!gr_locate (sgr->sg_name)) {
- puts (_("no matching group file entry\n"));
+ grp = (struct group *)gr_locate (sgr->sg_name);
+ if (grp == NULL) {
+ printf (_("no matching group file entry in %s\n"), grp_file);
printf (_("delete line `%s'? "), sge->line);
errors++;
if (yes_or_no ())
goto delete_sg;
+ } else {
+ /**
+ * Verify that the all members defined in /etc/gshadow are also
+ * present in /etc/group.
+ */
+ char **pgrp_mem,**psgr_mem;
+ for (psgr_mem=sgr->sg_mem; *psgr_mem; psgr_mem++)
+ {
+ for (pgrp_mem=grp->gr_mem; *pgrp_mem; pgrp_mem++)
+ {
+ if (strcmp(*pgrp_mem, *psgr_mem) == 0)
+ break;
+ }
+ if (*pgrp_mem == NULL)
+ {
+ printf ("'%s' is a member of the '%s' group in %s but not in %s\n",
+ *psgr_mem, sgr->sg_name, sgr_file, grp_file);
+ }
+ }
}
/*
@@ -574,7 +659,7 @@
SYSLOG ((LOG_INFO,
"delete admin `%s' from shadow group `%s'",
sgr->sg_adm[i], sgr->sg_name));
- deleted++;
+ changed++;
delete_member (sgr->sg_adm, sgr->sg_adm[i]);
sge->changed = 1;
__sgr_set_changed ();
@@ -603,7 +688,7 @@
SYSLOG ((LOG_INFO,
"delete member `%s' from shadow group `%s'",
sgr->sg_mem[i], sgr->sg_name));
- deleted++;
+ changed++;
delete_member (sgr->sg_mem, sgr->sg_mem[i]);
sge->changed = 1;
__sgr_set_changed ();
@@ -614,11 +699,11 @@
#endif /* SHADOWGRP */
/*
- * All done. If there were no deletions we can just abandon any
+ * All done. If there were no change we can just abandon any
* changes to the files.
*/
- if (deleted) {
+ if (changed) {
write_and_bye:
if (!gr_close ()) {
fprintf (stderr, _("%s: cannot update file %s\n"),
@@ -650,12 +735,12 @@
if (errors)
#ifdef NDBM
- printf (deleted ?
+ printf (changed ?
_
("%s: the files have been updated; run mkpasswd\n")
: _("%s: no changes\n"), Prog);
#else
- printf (deleted ?
+ printf (changed ?
_("%s: the files have been updated\n") :
_("%s: no changes\n"), Prog);
#endif
Index: shadow-4.0.3/src/pwck.c
===================================================================
--- shadow-4.0.3.orig/src/pwck.c 2002-01-10 14:01:28.000000000 +0100
+++ shadow-4.0.3/src/pwck.c 2005-06-26 21:51:43.068559000 +0200
@@ -45,6 +45,7 @@
#ifdef SHADOWPWD
#include "shadowio.h"
+#include "getdef.h"
extern void __spw_del_entry (const struct commonio_entry *);
extern struct commonio_entry *__spw_get_head (void);
#endif
@@ -421,6 +422,51 @@
pwd->pw_name, pwd->pw_shell);
errors++;
}
+#ifdef SHADOWPWD
+ /*
+ * Make sure this entry exists in the /etc/gshadow file.
+ */
+
+ if (is_shadow)
+ {
+ spw = (struct spwd *) spw_locate(pwd->pw_name);
+ if (spw == NULL) {
+ printf (_("no matching password file entry in %s\n"),
+ spw_file);
+ printf (_("add user `%s' in %s? "),
+ pwd->pw_name, spw_file);
+ errors++;
+ if (yes_or_no())
+ {
+ struct spwd sp;
+ sp.sp_namp = pwd->pw_name;
+ sp.sp_pwdp = pwd->pw_passwd;
+ sp.sp_min = getdef_num ("PASS_MIN_DAYS", -1);
+ sp.sp_max = getdef_num ("PASS_MAX_DAYS", -1);
+ sp.sp_warn = getdef_num ("PASS_WARN_AGE", -1);
+ sp.sp_inact = -1;
+ sp.sp_expire = -1;
+ sp.sp_flag = -1;
+ sp.sp_lstchg = time ((time_t *) 0) / (24L * 3600L);
+ if (!spw_update (&sp))
+ {
+ fprintf (stderr,
+ _("%s: can't update shadow entry for %s\n"),
+ Prog, sp.sp_namp);
+ exit (E_CANTUPDATE);
+ }
+ /* remove password from /etc/passwd */
+ pwd->pw_passwd = SHADOW_PASSWD_STRING;/* XXX warning: const */
+ if (!pw_update (pwd)) {
+ fprintf (stderr,
+ _("%s: can't update passwd entry for %s\n"),
+ Prog, pwd->pw_name);
+ exit (E_CANTUPDATE);
+ }
+ }
+ }
+ }
+#endif
}
#ifdef SHADOWPWD
@@ -539,7 +585,8 @@
* /etc/passwd entry and ask them to delete it.
*/
- puts (_("no matching password file entry\n"));
+ printf (_("no matching password file entry in %s\n"),
+ pwd_file);
printf (_("delete line `%s'? "), spe->line);
errors++;
--zhXaljGHf11kAtnf--