From 69b276a7124936b090a646e679fda93e412379e6 Mon Sep 17 00:00:00 2001 From: nekral-guest Date: Sat, 9 Aug 2008 23:25:18 +0000 Subject: [PATCH] * src/chpasswd.c: Added fail_exit(). * src/chpasswd.c: Added support for syslog. * src/chpasswd.c: Report failure to unlock files to stderr and syslog. * src/chpasswd.c: Simplify the PAM error handling. * src/chpasswd.c: Report failure during *_close() to syslog. * src/chpasswd.c: Ignore the return value or pam_end(). --- ChangeLog | 10 ++++++ src/chpasswd.c | 97 ++++++++++++++++++++++++++++++++------------------ 2 files changed, 73 insertions(+), 34 deletions(-) diff --git a/ChangeLog b/ChangeLog index f76ca87a..a0ec5f63 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,13 @@ +2008-08-07 Nicolas François + + * src/chpasswd.c: Added fail_exit(). + * src/chpasswd.c: Added support for syslog. + * src/chpasswd.c: Report failure to unlock files to stderr and + syslog. + * src/chpasswd.c: Simplify the PAM error handling. + * src/chpasswd.c: Report failure during *_close() to syslog. + * src/chpasswd.c: Ignore the return value or pam_end(). + 2008-08-07 Nicolas François * src/chgpasswd.c: Added fail_exit(). diff --git a/src/chpasswd.c b/src/chpasswd.c index ac8ba50b..ace0ea60 100644 --- a/src/chpasswd.c +++ b/src/chpasswd.c @@ -52,21 +52,24 @@ * Global variables */ static char *Prog; -static bool cflg = false; -static bool eflg = false; +static bool cflg = false; +static bool eflg = false; static bool md5flg = false; -static bool sflg = false; +static bool sflg = false; static const char *crypt_method = NULL; static long sha_rounds = 5000; static bool is_shadow_pwd; +static bool passwd_locked = false; +static bool shadow_locked = false; #ifdef USE_PAM static pam_handle_t *pamh = NULL; #endif /* local function prototypes */ +static void fail_exit (int code); static void usage (void); static void process_flags (int argc, char **argv); static void check_flags (void); @@ -74,6 +77,30 @@ static void check_perms (void); static void open_files (void); static void close_files (void); +/* + * fail_exit - exit with a failure code after unlocking the files + */ +static void fail_exit (int code) +{ + if (passwd_locked) { + if (pw_unlock () == 0) { + fprintf (stderr, _("%s: failed to unlock %s\n"), Prog, pw_dbname ()); + SYSLOG ((LOG_ERR, "failed to unlock %s", pw_dbname ())); + /* continue */ + } + } + + if (shadow_locked) { + if (spw_unlock () == 0) { + fprintf (stderr, _("%s: failed to unlock %s\n"), Prog, spw_dbname ()); + SYSLOG ((LOG_ERR, "failed to unlock %s", spw_dbname ())); + /* continue */ + } + } + + exit (code); +} + /* * usage - display usage message and exit */ @@ -219,32 +246,27 @@ static void check_perms (void) { #ifdef USE_PAM int retval = PAM_SUCCESS; - struct passwd *pampw; + pampw = getpwuid (getuid ()); /* local, no need for xgetpwuid */ - if (pampw == NULL) { + if (NULL == pampw) { retval = PAM_USER_UNKNOWN; } - if (retval == PAM_SUCCESS) { + if (PAM_SUCCESS == retval) { retval = pam_start ("chpasswd", pampw->pw_name, &conv, &pamh); } - if (retval == PAM_SUCCESS) { + if (PAM_SUCCESS == retval) { retval = pam_authenticate (pamh, 0); - if (retval != PAM_SUCCESS) { - pam_end (pamh, retval); - } } - if (retval == PAM_SUCCESS) { + if (PAM_SUCCESS == retval) { retval = pam_acct_mgmt (pamh, 0); - if (retval != PAM_SUCCESS) { - pam_end (pamh, retval); - } } - if (retval != PAM_SUCCESS) { + if (PAM_SUCCESS != retval) { + (void) pam_end (pamh, retval); fprintf (stderr, _("%s: PAM authentication failed\n"), Prog); exit (1); } @@ -263,13 +285,13 @@ static void open_files (void) if (pw_lock () == 0) { fprintf (stderr, _("%s: cannot lock %s\n"), Prog, pw_dbname ()); - exit (1); + fail_exit (1); } + passwd_locked = true; if (pw_open (O_RDWR) == 0) { fprintf (stderr, _("%s: cannot open %s\n"), Prog, pw_dbname ()); - pw_unlock (); - exit (1); + fail_exit (1); } /* Do the same for the shadowed database, if it exist */ @@ -278,16 +300,14 @@ static void open_files (void) fprintf (stderr, _("%s: cannot lock %s\n"), Prog, spw_dbname ()); - pw_unlock (); - exit (1); + fail_exit (1); } + shadow_locked = true; if (spw_open (O_RDWR) == 0) { fprintf (stderr, _("%s: cannot open %s\n"), Prog, spw_dbname ()); - pw_unlock (); - spw_unlock (); - exit (1); + fail_exit (1); } } } @@ -302,19 +322,30 @@ static void close_files (void) fprintf (stderr, _("%s: failure while writing changes to %s\n"), Prog, spw_dbname ()); - pw_unlock (); - exit (1); + SYSLOG ((LOG_ERR, "failure while writing changes to %s", spw_dbname ())); + fail_exit (1); } - spw_unlock (); + if (spw_unlock () == 0) { + fprintf (stderr, _("%s: failed to unlock %s\n"), Prog, spw_dbname ()); + SYSLOG ((LOG_ERR, "failed to unlock %s", spw_dbname ())); + /* continue */ + } + shadow_locked = false; } if (pw_close () == 0) { fprintf (stderr, _("%s: failure while writing changes to %s\n"), Prog, pw_dbname ()); - exit (1); + SYSLOG ((LOG_ERR, "failure while writing changes to %s", pw_dbname ())); + fail_exit (1); } - pw_unlock (); + if (pw_unlock () == 0) { + fprintf (stderr, _("%s: failed to unlock %s\n"), Prog, pw_dbname ()); + SYSLOG ((LOG_ERR, "failed to unlock %s", pw_dbname ())); + /* continue */ + } + passwd_locked = false; } int main (int argc, char **argv) @@ -342,6 +373,8 @@ int main (int argc, char **argv) process_flags (argc, argv); + OPENLOG ("chpasswd"); + check_perms (); is_shadow_pwd = spw_file_present (); @@ -469,11 +502,7 @@ int main (int argc, char **argv) if (0 != errors) { fprintf (stderr, _("%s: error detected, changes ignored\n"), Prog); - if (is_shadow_pwd) { - spw_unlock (); - } - pw_unlock (); - exit (1); + fail_exit (1); } close_files (); @@ -481,7 +510,7 @@ int main (int argc, char **argv) nscd_flush_cache ("passwd"); #ifdef USE_PAM - pam_end (pamh, PAM_SUCCESS); + (void) pam_end (pamh, PAM_SUCCESS); #endif /* USE_PAM */ return (0);