Modularize password changing mechanisms, as proposed in
<20000130122641.A8134@xanadu.kublai.com>: Subject: PROPOSAL: making passwd pluggable (sort of) Date: Sun, 30 Jan 2000 12:26:41 -0500
This commit is contained in:
parent
492312b9ed
commit
919f6272de
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: extern.h,v 1.6 2000/01/26 01:18:48 aidan Exp $ */
|
||||
/* $NetBSD: extern.h,v 1.7 2000/02/14 04:36:20 aidan Exp $ */
|
||||
|
||||
/*
|
||||
* Copyright (c) 1994
|
||||
@ -35,10 +35,39 @@
|
||||
* @(#)extern.h 8.1 (Berkeley) 4/2/94
|
||||
*/
|
||||
|
||||
int kadm_passwd __P((char *, char *, char *, char *));
|
||||
int kadm5_passwd __P((char *));
|
||||
int krb_check __P((void));
|
||||
int krb_passwd __P((void));
|
||||
int local_passwd __P((char *));
|
||||
void to64 __P((char *, long, int));
|
||||
int yp_passwd __P((char *));
|
||||
/* return values from pw_init() and pw_arg_end() */
|
||||
enum {
|
||||
PW_USE_FORCE,
|
||||
PW_USE,
|
||||
PW_DONT_USE
|
||||
};
|
||||
|
||||
void to64(char *, long, int);
|
||||
|
||||
#ifdef KERBEROS5
|
||||
int krb5_init __P((const char *));
|
||||
int krb5_arg __P((char, const char *));
|
||||
int krb5_arg_end __P((void));
|
||||
void krb5_end __P((void));
|
||||
int krb5_chpw __P((const char *));
|
||||
#endif
|
||||
#ifdef KERBEROS
|
||||
int krb4_init __P((const char *));
|
||||
int krb4_arg __P((char, const char *));
|
||||
int krb4_arg_end __P((void));
|
||||
void krb4_end __P((void));
|
||||
int krb4_chpw __P((const char *));
|
||||
#endif
|
||||
#ifdef YP
|
||||
int yp_init __P((const char *));
|
||||
int yp_arg __P((char, const char *));
|
||||
int yp_arg_end __P((void));
|
||||
void yp_end __P((void));
|
||||
int yp_chpw __P((const char *));
|
||||
#endif
|
||||
/* local */
|
||||
int local_init __P((const char *));
|
||||
int local_arg __P((char, const char *));
|
||||
int local_arg_end __P((void));
|
||||
void local_end __P((void));
|
||||
int local_chpw __P((const char *));
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: local_passwd.c,v 1.18 2000/01/12 05:13:32 mjl Exp $ */
|
||||
/* $NetBSD: local_passwd.c,v 1.19 2000/02/14 04:36:21 aidan Exp $ */
|
||||
|
||||
/*-
|
||||
* Copyright (c) 1990, 1993, 1994
|
||||
@ -38,7 +38,7 @@
|
||||
#if 0
|
||||
static char sccsid[] = "from: @(#)local_passwd.c 8.3 (Berkeley) 4/2/94";
|
||||
#else
|
||||
__RCSID("$NetBSD: local_passwd.c,v 1.18 2000/01/12 05:13:32 mjl Exp $");
|
||||
__RCSID("$NetBSD: local_passwd.c,v 1.19 2000/02/14 04:36:21 aidan Exp $");
|
||||
#endif
|
||||
#endif /* not lint */
|
||||
|
||||
@ -62,6 +62,7 @@ __RCSID("$NetBSD: local_passwd.c,v 1.18 2000/01/12 05:13:32 mjl Exp $");
|
||||
static char *getnewpasswd __P((struct passwd *, int));
|
||||
|
||||
static uid_t uid;
|
||||
static int force_local;
|
||||
|
||||
char *tempname;
|
||||
|
||||
@ -139,8 +140,43 @@ getnewpasswd(pw, min_pw_len)
|
||||
}
|
||||
|
||||
int
|
||||
local_passwd(uname)
|
||||
char *uname;
|
||||
local_init(progname)
|
||||
const char *progname;
|
||||
{
|
||||
force_local = 0;
|
||||
return (0);
|
||||
}
|
||||
|
||||
int
|
||||
local_arg(char arg, const char *optarg)
|
||||
{
|
||||
switch (arg) {
|
||||
case 'l':
|
||||
force_local = 1;
|
||||
break;
|
||||
default:
|
||||
return(0);
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
int
|
||||
local_arg_end()
|
||||
{
|
||||
if (force_local)
|
||||
return(PW_USE_FORCE);
|
||||
return(PW_USE);
|
||||
}
|
||||
|
||||
void
|
||||
local_end()
|
||||
{
|
||||
/* NOOP */
|
||||
}
|
||||
|
||||
int
|
||||
local_chpw(uname)
|
||||
const char *uname;
|
||||
{
|
||||
struct passwd *pw;
|
||||
struct passwd old_pw;
|
||||
|
@ -1,4 +1,4 @@
|
||||
.\" $NetBSD: passwd.1,v 1.12 1999/03/22 18:16:41 garbled Exp $
|
||||
.\" $NetBSD: passwd.1,v 1.13 2000/02/14 04:36:21 aidan Exp $
|
||||
.\"
|
||||
.\" Copyright (c) 1990, 1993
|
||||
.\" The Regents of the University of California. All rights reserved.
|
||||
@ -38,19 +38,46 @@
|
||||
.Os
|
||||
.Sh NAME
|
||||
.Nm passwd ,
|
||||
.Nm yppasswd
|
||||
.Nm yppasswd ,
|
||||
.Nm kpasswd
|
||||
.Nd modify a user's password
|
||||
.Sh SYNOPSIS
|
||||
.Nm
|
||||
.Nm passwd
|
||||
.Op Fl l
|
||||
.Op Ar user
|
||||
.Nm passwd
|
||||
.Op Fl y
|
||||
.Op Ar user
|
||||
.Nm passwd
|
||||
.Op Fl 4
|
||||
.Op Fl k
|
||||
.Op Fl i Ar instance
|
||||
.Op Fl r Ar realm
|
||||
.Op Fl u Ar fullname
|
||||
.Op Ar user
|
||||
.Nm passwd
|
||||
.Op Fl 5
|
||||
.Op Fl k
|
||||
.Op Fl u Ar fullname
|
||||
.Op Ar user
|
||||
.Nm kpasswd
|
||||
.Op Fl 4
|
||||
.Op Fl k
|
||||
.Op Fl i Ar instance
|
||||
.Op Fl r Ar realm
|
||||
.Op Fl u Ar fullname
|
||||
.Op Ar user
|
||||
.Nm kpasswd
|
||||
.Op Fl 5
|
||||
.Op Fl k
|
||||
.Op Fl u Ar fullname
|
||||
.Op Ar user
|
||||
.Nm yppasswd
|
||||
.Op Ar user
|
||||
.Sh DESCRIPTION
|
||||
.Nm
|
||||
changes the user's local or YP password. First, the user is prompted
|
||||
for their current password.
|
||||
changes the user's local, YP, or kerberos password. First, the user is
|
||||
prompted for their current password.
|
||||
If the current password is correctly typed, a new password is
|
||||
requested.
|
||||
The new password must be entered twice to avoid typing errors.
|
||||
@ -62,6 +89,8 @@ Its total length must be less than
|
||||
(currently 128 characters).
|
||||
Numbers, upper case letters and meta characters
|
||||
are encouraged.
|
||||
.Pp
|
||||
All options may not be available on all systems.
|
||||
.Bl -tag -width flag
|
||||
.It Fl l
|
||||
This option causes the password to be updated only in the local
|
||||
@ -79,11 +108,45 @@ is the equivalent of
|
||||
with the
|
||||
.Fl y
|
||||
flag.
|
||||
.It Fl 4
|
||||
This option causes passwd to change the user's kerberos password,
|
||||
using the kerberos 4 admin protocol.
|
||||
.It Fl 5
|
||||
This option causes passwd to change the user's kerberos password,
|
||||
using the kerberos 5 admin protocol.
|
||||
.It Fl k
|
||||
This option causes passwd to change the user's kerberos password,
|
||||
using either the kerberos 4 or kerberos 5 admin protocol.
|
||||
If both kerberos 4 and kerberos 5 libraries and config files are
|
||||
installed on the host, kerberos 5 will be used to change the password.
|
||||
.Nm kpasswd
|
||||
is the equivalent of
|
||||
.Nm
|
||||
with the
|
||||
.Fl k
|
||||
flag.
|
||||
.It Fl i Ar instance
|
||||
This option selects a non-default Kerberos 4 instance for the
|
||||
Kerberos password to be changed.
|
||||
.It Fl r Ar realm
|
||||
This option selects a non-default Kerberos 4 realm for the Kerberos
|
||||
password to be changed.
|
||||
.It Fl u Ar fullname
|
||||
This option specifies the entire principal.instance@realm (for Kerberos
|
||||
4) or principal/instance@realm (for Kerberos 5) for the Kerberos
|
||||
password to be changed.
|
||||
.El
|
||||
.Pp
|
||||
This is the behavior if no flags are specified:
|
||||
If Kerberos is active then
|
||||
.Nm
|
||||
will talk to the Kerberos server, attempting to use Kerberos 5, then
|
||||
Kerberos 4 protocols to change the password (even if the user has an
|
||||
entry in the local database.)
|
||||
If Kerberos is unavailable, an attempt is made to use the YP database.
|
||||
If the password is not in the YP database, then
|
||||
an attempt is made to use the local password database.
|
||||
.Pp
|
||||
The super-user is not required to provide a user's current password
|
||||
if only the local password is modified.
|
||||
.Sh FILES
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: passwd.c,v 1.15 2000/01/26 01:18:48 aidan Exp $ */
|
||||
/* $NetBSD: passwd.c,v 1.16 2000/02/14 04:36:21 aidan Exp $ */
|
||||
|
||||
/*
|
||||
* Copyright (c) 1988, 1993, 1994
|
||||
@ -43,7 +43,7 @@ __COPYRIGHT("@(#) Copyright (c) 1988, 1993, 1994\n\
|
||||
#if 0
|
||||
static char sccsid[] = "from: @(#)passwd.c 8.3 (Berkeley) 4/2/94";
|
||||
#else
|
||||
__RCSID("$NetBSD: passwd.c,v 1.15 2000/01/26 01:18:48 aidan Exp $");
|
||||
__RCSID("$NetBSD: passwd.c,v 1.16 2000/02/14 04:36:21 aidan Exp $");
|
||||
#endif
|
||||
#endif /* not lint */
|
||||
|
||||
@ -53,28 +53,54 @@ __RCSID("$NetBSD: passwd.c,v 1.15 2000/01/26 01:18:48 aidan Exp $");
|
||||
#include <unistd.h>
|
||||
|
||||
#include "extern.h"
|
||||
|
||||
static struct pw_module_s {
|
||||
const char *argv0;
|
||||
const char *args;
|
||||
const char *usage;
|
||||
int (*pw_init) __P((const char *));
|
||||
int (*pw_arg) __P((char, const char *));
|
||||
int (*pw_arg_end) __P((void));
|
||||
void (*pw_end) __P((void));
|
||||
|
||||
int (*pw_chpw) __P((const char*));
|
||||
int invalid;
|
||||
#define INIT_INVALID 1
|
||||
#define ARG_INVALID 2
|
||||
int use_class;
|
||||
} pw_modules[] = {
|
||||
#ifdef KERBEROS5
|
||||
{ NULL, "5ku:", "[-5] [-k] [-u principal]",
|
||||
krb5_init, krb5_arg, krb5_arg_end, krb5_end, krb5_chpw, 0, 0 },
|
||||
{ "kpasswd", "5ku:", "[-5] [-k] [-u principal]",
|
||||
krb5_init, krb5_arg, krb5_arg_end, krb5_end, krb5_chpw, 0, 0 },
|
||||
#endif
|
||||
#ifdef KERBEROS
|
||||
{ NULL, "4ku:i:r:", "[-4] [-k] [-u user] [-i instance] [-r realm]",
|
||||
krb4_init, krb4_arg, krb4_arg_end, krb4_end, krb4_chpw, 0, 0 },
|
||||
{ "kpasswd", "4ku:i:r:", "[-4] [-k] [-u user] [-i instance] [-r realm]",
|
||||
krb4_init, krb4_arg, krb4_arg_end, krb4_end, krb4_chpw, 0, 0 },
|
||||
#endif
|
||||
#ifdef YP
|
||||
{ NULL, "y", "[-y]",
|
||||
yp_init, yp_arg, yp_arg_end, yp_end, yp_chpw, 0, 0 },
|
||||
{ "yppasswd", "", "[-y]",
|
||||
yp_init, yp_arg, yp_arg_end, yp_end, yp_chpw, 0, 0 },
|
||||
#endif
|
||||
/* local */
|
||||
{ NULL, "l", "[-l]",
|
||||
local_init, local_arg, local_arg_end, local_end, local_chpw, 0, 0 },
|
||||
|
||||
/* terminator */
|
||||
{ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }
|
||||
};
|
||||
|
||||
void usage __P((void));
|
||||
|
||||
/*
|
||||
* Note on configuration:
|
||||
* Generally one would not use both Kerberos and YP
|
||||
* to maintain passwords.
|
||||
*/
|
||||
|
||||
int use_kerberos;
|
||||
int use_yp;
|
||||
int yppwd;
|
||||
int yflag;
|
||||
|
||||
extern char *__progname; /* from crt0.o */
|
||||
|
||||
int main __P((int, char **));
|
||||
|
||||
#ifdef YP
|
||||
extern int _yp_check __P((char **)); /* buried deep inside libc */
|
||||
#endif
|
||||
|
||||
int
|
||||
main(argc, argv)
|
||||
int argc;
|
||||
@ -83,87 +109,123 @@ main(argc, argv)
|
||||
extern int optind;
|
||||
int ch;
|
||||
char *username;
|
||||
#if defined(KERBEROS)
|
||||
char *iflag = 0, *rflag = 0;
|
||||
#endif
|
||||
#if defined(KERBEROS) || defined(KERBEROS5)
|
||||
char *uflag = 0;
|
||||
#endif
|
||||
char optstring[64]; /* if we ever get more than 64 args, shoot me. */
|
||||
const char *curopt, *optopt;
|
||||
int i, j;
|
||||
int valid;
|
||||
int use_always;
|
||||
|
||||
#if defined(KERBEROS) || defined(KERBEROS5)
|
||||
if (strcmp(__progname, "kpasswd") == 0)
|
||||
use_kerberos = 1;
|
||||
else
|
||||
use_kerberos = krb_check();
|
||||
#endif
|
||||
#ifdef YP
|
||||
use_yp = _yp_check(NULL);
|
||||
#endif
|
||||
/* allow passwd modules to do argv[0] specific processing */
|
||||
use_always = 0;
|
||||
valid = 0;
|
||||
for (i = 0; pw_modules[i].pw_init != NULL; i++) {
|
||||
pw_modules[i].invalid = 0;
|
||||
if (pw_modules[i].argv0) {
|
||||
/*
|
||||
* If we have a module that matches this progname, be
|
||||
* sure that no modules but those that match this
|
||||
* progname can be used. If we have a module that
|
||||
* matches against a particular progname, but does NOT
|
||||
* match this one, don't use that module.
|
||||
*/
|
||||
if ((strcmp(__progname, pw_modules[i].argv0) == 0) &&
|
||||
use_always == 0) {
|
||||
for (j = 0; j < i; j++) {
|
||||
pw_modules[j].invalid |= INIT_INVALID;
|
||||
(*pw_modules[j].pw_end)();
|
||||
}
|
||||
use_always = 1;
|
||||
} else if (use_always == 0)
|
||||
pw_modules[i].invalid |= INIT_INVALID;
|
||||
} else if (use_always)
|
||||
pw_modules[i].invalid |= INIT_INVALID;
|
||||
|
||||
if (strcmp(__progname, "yppasswd") == 0) {
|
||||
#ifdef YP
|
||||
if (!use_yp)
|
||||
errx(1, "YP not in use.");
|
||||
use_kerberos = 0;
|
||||
yppwd = 1;
|
||||
#else
|
||||
errx(1, "YP support not compiled in.");
|
||||
#endif
|
||||
if (pw_modules[i].invalid)
|
||||
continue;
|
||||
|
||||
pw_modules[i].invalid |= (*pw_modules[i].pw_init)(__progname) ?
|
||||
/* zero on success, non-zero on error */
|
||||
INIT_INVALID : 0;
|
||||
|
||||
if (! pw_modules[i].invalid)
|
||||
valid = 1;
|
||||
}
|
||||
|
||||
while ((ch = getopt(argc, argv, "lkyi:r:u:")) != -1)
|
||||
switch (ch) {
|
||||
case 'l': /* change local password file */
|
||||
if (yppwd)
|
||||
usage();
|
||||
use_kerberos = 0;
|
||||
use_yp = 0;
|
||||
break;
|
||||
#ifdef KERBEROS
|
||||
case 'i':
|
||||
iflag = optarg;
|
||||
break;
|
||||
case 'r':
|
||||
rflag = optarg;
|
||||
break;
|
||||
#endif
|
||||
#if defined(KERBEROS) || defined(KERBEROS5)
|
||||
case 'u':
|
||||
uflag = optarg;
|
||||
break;
|
||||
#endif
|
||||
case 'k': /* change Kerberos password */
|
||||
#if defined(KERBEROS) || defined(KERBEROS5)
|
||||
if (yppwd)
|
||||
usage();
|
||||
use_kerberos = 1;
|
||||
use_yp = 0;
|
||||
break;
|
||||
#endif
|
||||
#ifndef KERBEROS
|
||||
case 'i':
|
||||
case 'r':
|
||||
errx(1, "Kerberos4 support not compiled in.");
|
||||
#endif
|
||||
#if !defined(KERBEROS) && !defined(KERBEROS5)
|
||||
case 'u':
|
||||
errx(1, "Kerberos support not compiled in.");
|
||||
#endif
|
||||
case 'y': /* change YP password */
|
||||
#ifdef YP
|
||||
if (yppwd)
|
||||
usage();
|
||||
if (!use_yp)
|
||||
errx(1, "YP not in use.");
|
||||
use_kerberos = 0;
|
||||
yflag = 1;
|
||||
break;
|
||||
#else
|
||||
errx(1, "YP support not compiled in.");
|
||||
#endif
|
||||
default:
|
||||
usage();
|
||||
if (valid == 0)
|
||||
errx(1, "Can't change password.");
|
||||
|
||||
/* Build the option string from the individual modules' option
|
||||
* strings. Note that two modules can share a single option
|
||||
* letter. */
|
||||
optstring[0] = '\0';
|
||||
j = 0;
|
||||
for (i = 0; pw_modules[i].pw_init != NULL; i++) {
|
||||
if (pw_modules[i].invalid)
|
||||
continue;
|
||||
|
||||
curopt = pw_modules[i].args;
|
||||
while (*curopt != '\0') {
|
||||
if ((optopt = strchr(optstring, *curopt)) == (char *) 0) {
|
||||
optstring[j++] = *curopt;
|
||||
if (curopt[1] == ':') {
|
||||
curopt++;
|
||||
optstring[j++] = *curopt;
|
||||
}
|
||||
optstring[j] = '\0';
|
||||
} else if ((optopt[1] == ':' && curopt[1] != ':') ||
|
||||
(optopt[1] != ':' && curopt[1] == ':')) {
|
||||
errx(1, "NetBSD ERROR! Different password "
|
||||
"modules have two different ideas about "
|
||||
"%c argument format.", curopt[0]);
|
||||
}
|
||||
curopt++;
|
||||
}
|
||||
}
|
||||
|
||||
while ((ch = getopt(argc, argv, optstring)) != -1)
|
||||
{
|
||||
valid = 0;
|
||||
for (i = 0; pw_modules[i].pw_init != NULL; i++) {
|
||||
if (pw_modules[i].invalid)
|
||||
continue;
|
||||
if ((optopt = strchr(pw_modules[i].args, ch)) != (char *) 0) {
|
||||
j = (optopt[1] == ':') ?
|
||||
! (*pw_modules[i].pw_arg)(ch, optarg) :
|
||||
! (*pw_modules[i].pw_arg)(ch, (char *) 0);
|
||||
if (j != 0)
|
||||
pw_modules[i].invalid |= ARG_INVALID;
|
||||
if (pw_modules[i].invalid)
|
||||
(*pw_modules[i].pw_end)();
|
||||
} else {
|
||||
/* arg doesn't match this module */
|
||||
pw_modules[i].invalid |= ARG_INVALID;
|
||||
(*pw_modules[i].pw_end)();
|
||||
}
|
||||
if (! pw_modules[i].invalid)
|
||||
valid = 1;
|
||||
}
|
||||
if (! valid) {
|
||||
usage();
|
||||
exit(1);
|
||||
}
|
||||
}
|
||||
|
||||
/* select which module to use to actually change the password. */
|
||||
use_always = 0;
|
||||
valid = 0;
|
||||
for (i = 0; pw_modules[i].pw_init != NULL; i++)
|
||||
if (! pw_modules[i].invalid) {
|
||||
pw_modules[i].use_class = (*pw_modules[i].pw_arg_end)();
|
||||
if (pw_modules[i].use_class != PW_DONT_USE)
|
||||
valid = 1;
|
||||
if (pw_modules[i].use_class == PW_USE_FORCE)
|
||||
use_always = 1;
|
||||
}
|
||||
|
||||
|
||||
if (! valid)
|
||||
/* hang the DJ */
|
||||
errx(1, "No valid password module specified.");
|
||||
|
||||
argc -= optind;
|
||||
argv += optind;
|
||||
@ -176,15 +238,6 @@ main(argc, argv)
|
||||
case 0:
|
||||
break;
|
||||
case 1:
|
||||
#ifdef KERBEROS5
|
||||
if (use_kerberos && strcmp(argv[0], username)) {
|
||||
errx(1, "%s\n\t%s\n%s\n",
|
||||
"to change another user's Kerberos password, do",
|
||||
"\"kinit <user>; passwd; kdestroy\";",
|
||||
"to change a user's local passwd, use\
|
||||
\"passwd -l <user>\"");
|
||||
}
|
||||
#endif
|
||||
username = argv[0];
|
||||
break;
|
||||
default:
|
||||
@ -192,30 +245,31 @@ main(argc, argv)
|
||||
exit(1);
|
||||
}
|
||||
|
||||
#if defined(KERBEROS5)
|
||||
if (use_kerberos)
|
||||
exit(kadm5_passwd(username));
|
||||
#elif defined(KERBEROS)
|
||||
if (uflag && (iflag || rflag))
|
||||
errx(1, "-u cannot be used with -r or -i");
|
||||
|
||||
if (use_kerberos)
|
||||
exit(kadm_passwd(username, iflag, rflag, uflag));
|
||||
#endif
|
||||
#ifdef YP
|
||||
if (use_yp)
|
||||
exit(yp_passwd(username));
|
||||
#endif
|
||||
exit(local_passwd(username));
|
||||
/* allow for fallback to other chpw() methods. */
|
||||
for (i = 0; pw_modules[i].pw_init != NULL; i++) {
|
||||
if (pw_modules[i].invalid)
|
||||
continue;
|
||||
if ((use_always && pw_modules[i].use_class == PW_USE_FORCE) ||
|
||||
(!use_always && pw_modules[i].use_class == PW_USE)) {
|
||||
valid = (*pw_modules[i].pw_chpw)(username);
|
||||
(*pw_modules[i].pw_end)();
|
||||
if (valid >= 0)
|
||||
exit(valid);
|
||||
/* return value < 0 indicates continuation. */
|
||||
}
|
||||
}
|
||||
exit(1);
|
||||
}
|
||||
|
||||
void
|
||||
usage()
|
||||
{
|
||||
int i;
|
||||
|
||||
if (yppwd)
|
||||
fprintf(stderr, "usage: %s user\n", __progname);
|
||||
else
|
||||
fprintf(stderr, "usage: %s [-l] [-k] [-y] [-i instance] [-r realm] [-u fullname] user\n", __progname);
|
||||
fprintf(stderr, "usage:\n");
|
||||
for (i = 0; pw_modules[i].pw_init != NULL; i++)
|
||||
if (! (pw_modules[i].invalid & INIT_INVALID))
|
||||
fprintf(stderr, "\t%s %s [user]\n", __progname,
|
||||
pw_modules[i].usage);
|
||||
exit(1);
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $NetBSD: yp_passwd.c,v 1.21 1999/12/23 01:02:52 mjl Exp $ */
|
||||
/* $NetBSD: yp_passwd.c,v 1.22 2000/02/14 04:36:21 aidan Exp $ */
|
||||
|
||||
/*
|
||||
* Copyright (c) 1988, 1990, 1993, 1994
|
||||
@ -38,7 +38,7 @@
|
||||
#if 0
|
||||
static char sccsid[] = "from: @(#)local_passwd.c 8.3 (Berkeley) 4/2/94";
|
||||
#else
|
||||
__RCSID("$NetBSD: yp_passwd.c,v 1.21 1999/12/23 01:02:52 mjl Exp $");
|
||||
__RCSID("$NetBSD: yp_passwd.c,v 1.22 2000/02/14 04:36:21 aidan Exp $");
|
||||
#endif
|
||||
#endif /* not lint */
|
||||
|
||||
@ -71,12 +71,11 @@ __RCSID("$NetBSD: yp_passwd.c,v 1.21 1999/12/23 01:02:52 mjl Exp $");
|
||||
|
||||
extern char *__progname; /* from crt0.o */
|
||||
|
||||
extern int yflag, yppwd;
|
||||
static int yflag;
|
||||
|
||||
static char *getnewpasswd __P((struct passwd *, char **));
|
||||
static int ypgetpwnam __P((char *));
|
||||
static int ypgetpwnam __P((const char *));
|
||||
static void pw_error __P((char *, int, int));
|
||||
static void test_local __P((char *));
|
||||
|
||||
static uid_t uid;
|
||||
char *domain;
|
||||
@ -92,25 +91,58 @@ pw_error(name, err, eval)
|
||||
errx(eval, "YP passwd database unchanged");
|
||||
}
|
||||
|
||||
static void
|
||||
test_local(username)
|
||||
char *username;
|
||||
int
|
||||
yp_init(progname)
|
||||
const char *progname;
|
||||
{
|
||||
int yppwd;
|
||||
|
||||
/*
|
||||
* Something failed recoverably stating that the YP system couldn't
|
||||
* find this user. Look for a local passwd entry, and change that
|
||||
* if and only if we weren't run as yppasswd or with the -y option.
|
||||
* This function does not return if a local entry is found.
|
||||
*/
|
||||
if (yppwd == 0 && yflag == 0)
|
||||
if ((getpwnam(username) != NULL) && !local_passwd(username))
|
||||
exit(0);
|
||||
if (strcmp(progname, "yppasswd") == 0) {
|
||||
yppwd = 1;
|
||||
} else
|
||||
yppwd = 0;
|
||||
yflag = 0;
|
||||
if (_yp_check(NULL) == 0) {
|
||||
/* can't use YP. */
|
||||
if (yppwd)
|
||||
errx(1, "YP not in use.");
|
||||
return(-1);
|
||||
}
|
||||
return (0);
|
||||
}
|
||||
|
||||
int
|
||||
yp_passwd(username)
|
||||
char *username;
|
||||
yp_arg(ch, arg)
|
||||
char ch;
|
||||
const char *arg;
|
||||
{
|
||||
switch (ch) {
|
||||
case 'y':
|
||||
yflag = 1;
|
||||
break;
|
||||
default:
|
||||
return(0);
|
||||
}
|
||||
return(1);
|
||||
}
|
||||
|
||||
int
|
||||
yp_arg_end()
|
||||
{
|
||||
if (yflag)
|
||||
return (PW_USE_FORCE);
|
||||
return (PW_USE);
|
||||
}
|
||||
|
||||
void
|
||||
yp_end()
|
||||
{
|
||||
/* NOOP */
|
||||
}
|
||||
|
||||
int
|
||||
yp_chpw(username)
|
||||
const char *username;
|
||||
{
|
||||
char *master;
|
||||
int r, rpcport, status;
|
||||
@ -124,7 +156,7 @@ yp_passwd(username)
|
||||
/*
|
||||
* Get local domain
|
||||
*/
|
||||
if ((r = yp_get_default_domain(&domain)) != NULL)
|
||||
if ((r = yp_get_default_domain(&domain)) != 0)
|
||||
errx(1, "can't get local YP domain. Reason: %s",
|
||||
yperr_string(r));
|
||||
|
||||
@ -133,9 +165,10 @@ yp_passwd(username)
|
||||
* the daemon.
|
||||
*/
|
||||
if ((r = yp_master(domain, "passwd.byname", &master)) != 0) {
|
||||
test_local(username);
|
||||
errx(1, "can't find the master YP server. Reason: %s",
|
||||
warnx("can't find the master YP server. Reason: %s",
|
||||
yperr_string(r));
|
||||
/* continuation */
|
||||
return(-1);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -143,9 +176,10 @@ yp_passwd(username)
|
||||
*/
|
||||
if ((rpcport = getrpcport(master, YPPASSWDPROG,
|
||||
YPPASSWDPROC_UPDATE, IPPROTO_UDP)) == 0) {
|
||||
test_local(username);
|
||||
errx(1, "master YP server not running yppasswd daemon.\n\t%s\n",
|
||||
"Can't change password.");
|
||||
warnx("master YP server not running yppasswd daemon.\n\t%s\n",
|
||||
"Can't change YP password.");
|
||||
/* continuation */
|
||||
return(-1);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -158,8 +192,9 @@ yp_passwd(username)
|
||||
/* then get user's login identity */
|
||||
if (!ypgetpwnam(username) ||
|
||||
!(pw = getpwnam(username))) {
|
||||
test_local(username);
|
||||
errx(1, "unknown user %s", username);
|
||||
warnx("YP unknown user %s", username);
|
||||
/* continuation */
|
||||
return(-1);
|
||||
}
|
||||
|
||||
if (uid && uid != pw->pw_uid)
|
||||
@ -196,7 +231,7 @@ yp_passwd(username)
|
||||
else
|
||||
printf("The YP password has been changed on %s, %s\n",
|
||||
master, "the master YP passwd server.");
|
||||
exit(0);
|
||||
return(0);
|
||||
}
|
||||
|
||||
static char *
|
||||
@ -263,7 +298,7 @@ getnewpasswd(pw, old_pass)
|
||||
|
||||
static int
|
||||
ypgetpwnam(nam)
|
||||
char *nam;
|
||||
const char *nam;
|
||||
{
|
||||
char *val;
|
||||
int reason, vallen;
|
||||
|
Loading…
Reference in New Issue
Block a user