diff options
Diffstat (limited to 'lib/libpam')
83 files changed, 9192 insertions, 0 deletions
diff --git a/lib/libpam/Makefile b/lib/libpam/Makefile new file mode 100644 index 0000000..088e8a0 --- /dev/null +++ b/lib/libpam/Makefile @@ -0,0 +1,31 @@ +# Copyright 1998 Juniper Networks, Inc. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +# The modules must be built first, because they are built into the +# static version of libpam. +SUBDIR+= modules libpam + +.include <bsd.subdir.mk> diff --git a/lib/libpam/Makefile.inc b/lib/libpam/Makefile.inc new file mode 100644 index 0000000..ec21817 --- /dev/null +++ b/lib/libpam/Makefile.inc @@ -0,0 +1,32 @@ +# Copyright 1998 Juniper Networks, Inc. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +.ifdef PAM_DEBUG +DEBUG_FLAGS+= -DDEBUG +.endif + +SHLIB_MAJOR= 4 +PAM_MOD_DIR= ${LIBDIR} diff --git a/lib/libpam/libpam/Makefile b/lib/libpam/libpam/Makefile new file mode 100644 index 0000000..8b07458 --- /dev/null +++ b/lib/libpam/libpam/Makefile @@ -0,0 +1,169 @@ +#- +# Copyright (c) 1998 Juniper Networks, Inc. +# All rights reserved. +# Copyright (c) 2002 Networks Associates Technology, Inc. +# All rights reserved. +# +# Portions of this software was developed for the FreeBSD Project by +# ThinkSec AS and NAI Labs, the Security Research Division of Network +# Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +# ("CBOSS"), as part of the DARPA CHATS research program. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# 3. The name of the author may not be used to endorse or promote +# products derived from this software without specific prior written +# permission. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +OPENPAM= ${.CURDIR}/../../../contrib/openpam +.PATH: ${OPENPAM}/include ${OPENPAM}/lib ${OPENPAM}/doc/man + +LIB= pam +NO_PROFILE= + +SRCS= openpam_borrow_cred.c \ + openpam_configure.c \ + openpam_dispatch.c \ + openpam_dynamic.c \ + openpam_findenv.c \ + openpam_free_data.c \ + openpam_free_envlist.c \ + openpam_get_option.c \ + openpam_load.c \ + openpam_log.c \ + openpam_nullconv.c \ + openpam_readline.c \ + openpam_restore_cred.c \ + openpam_set_option.c \ + openpam_ttyconv.c \ + pam_acct_mgmt.c \ + pam_authenticate.c \ + pam_chauthtok.c \ + pam_close_session.c \ + pam_end.c \ + pam_error.c \ + pam_get_authtok.c \ + pam_get_data.c \ + pam_get_item.c \ + pam_get_user.c \ + pam_getenv.c \ + pam_getenvlist.c \ + pam_info.c \ + pam_open_session.c \ + pam_prompt.c \ + pam_putenv.c \ + pam_set_data.c \ + pam_set_item.c \ + pam_setcred.c \ + pam_setenv.c \ + pam_start.c \ + pam_strerror.c \ + pam_verror.c \ + pam_vinfo.c \ + pam_vprompt.c +# Local additions +SRCS+= pam_debug_log.c + +MAN= openpam.3 \ + openpam_borrow_cred.3 \ + openpam_free_data.3 \ + openpam_free_envlist.3 \ + openpam_get_option.3 \ + openpam_log.3 \ + openpam_nullconv.3 \ + openpam_readline.3 \ + openpam_restore_cred.3 \ + openpam_set_option.3 \ + openpam_ttyconv.3 \ + pam.3 \ + pam_acct_mgmt.3 \ + pam_authenticate.3 \ + pam_chauthtok.3 \ + pam_close_session.3 \ + pam_conv.3 \ + pam_end.3 \ + pam_error.3 \ + pam_get_authtok.3 \ + pam_get_data.3 \ + pam_get_item.3 \ + pam_get_user.3 \ + pam_getenv.3 \ + pam_getenvlist.3 \ + pam_info.3 \ + pam_open_session.3 \ + pam_prompt.3 \ + pam_putenv.3 \ + pam_set_data.3 \ + pam_set_item.3 \ + pam_setcred.3 \ + pam_setenv.3 \ + pam_sm_acct_mgmt.3 \ + pam_sm_authenticate.3 \ + pam_sm_chauthtok.3 \ + pam_sm_close_session.3 \ + pam_sm_open_session.3 \ + pam_sm_setcred.3 \ + pam_start.3 \ + pam_strerror.3 \ + pam_verror.3 \ + pam_vinfo.3 \ + pam_vprompt.3 \ + pam.conf.5 + +MLINKS= pam.conf.5 pam.d.5 + +CSTD?= c99 +WARNS?= 3 +CFLAGS+= -I${.CURDIR} -I${OPENPAM}/include +CFLAGS+= -DLIB_MAJ=${SHLIB_MAJOR} +CFLAGS+= -DOPENPAM_MODULES_DIR='"${PAM_MOD_DIR:C/\/*$//}/"' + +HEADERS= security/openpam.h \ + security/openpam_attr.h \ + security/openpam_version.h \ + security/pam_appl.h \ + security/pam_constants.h \ + security/pam_modules.h \ + security/pam_types.h \ + +ADD_HEADERS= security/pam_mod_misc.h + +# Static modules +MODULE_DIR= ../modules +.include "${.CURDIR}/${MODULE_DIR}/modules.inc" +STATIC_MODULES= ${MODULES:C/.*/${MODULE_DIR}\/&\/lib&.a/} +STATICOBJS+= openpam_static_modules.o +CLEANFILES+= openpam_static.o \ + openpam_static_modules.o + +openpam_static_modules.o: openpam_static.o ${STATIC_MODULES} + ${LD} -o ${.TARGET} -r --whole-archive ${.ALLSRC} + +# Can't put openpam_static.c in SRCS but want .o in .depend. +DPSRCS= openpam_static.c + +# Headers +INCS= ${HEADERS} ${ADD_HEADERS} +INCSDIR= ${INCLUDEDIR}/security + +.include <bsd.lib.mk> diff --git a/lib/libpam/libpam/pam_debug_log.c b/lib/libpam/libpam/pam_debug_log.c new file mode 100644 index 0000000..c3fe8e3 --- /dev/null +++ b/lib/libpam/libpam/pam_debug_log.c @@ -0,0 +1,62 @@ +/*- + * Copyright 2001 Mark R V Murray + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <libgen.h> +#include <stdarg.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#include <security/pam_appl.h> +#include <security/openpam.h> +#include <security/pam_mod_misc.h> + +/* Print a verbose error, including the function name and a + * cleaned up filename. + */ +void +_pam_verbose_error(pam_handle_t *pamh, int flags, + const char *file, const char *function, const char *format, ...) +{ + va_list ap; + char *fmtbuf, *modname, *period; + + if (!(flags & PAM_SILENT) && !openpam_get_option(pamh, "no_warn")) { + modname = basename(file); + period = strchr(modname, '.'); + if (period == NULL) + period = strchr(modname, '\0'); + va_start(ap, format); + asprintf(&fmtbuf, "%.*s: %s: %s\n", (int)(period - modname), + modname, function, format); + pam_verror(pamh, fmtbuf, ap); + free(fmtbuf); + va_end(ap); + } +} diff --git a/lib/libpam/libpam/pam_std_option.c b/lib/libpam/libpam/pam_std_option.c new file mode 100644 index 0000000..a9ddfba --- /dev/null +++ b/lib/libpam/libpam/pam_std_option.c @@ -0,0 +1,178 @@ +/*- + * Copyright 1998 Juniper Networks, Inc. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <stdio.h> +#include <string.h> +#include <syslog.h> + +#include <security/pam_appl.h> +#include <security/pam_mod_misc.h> + +/* Everyone has to have these options. It is not an error to + * specify them and then not use them. + */ +struct opttab std_options[PAM_MAX_OPTIONS] = { + { "debug", PAM_OPT_DEBUG }, + { "no_warn", PAM_OPT_NO_WARN }, + { "echo_pass", PAM_OPT_ECHO_PASS }, + { "use_first_pass", PAM_OPT_USE_FIRST_PASS }, + { "try_first_pass", PAM_OPT_TRY_FIRST_PASS }, + { "use_mapped_pass", PAM_OPT_USE_MAPPED_PASS }, + { "try_mapped_pass", PAM_OPT_TRY_MAPPED_PASS }, + { "expose_account", PAM_OPT_EXPOSE_ACCOUNT }, + { NULL, 0 } +}; + +/* Populate the options structure, syslogging all errors */ +void +pam_std_option(struct options *options, struct opttab other_options[], + int argc, const char *argv[]) +{ + struct opttab *oo; + int i, j, std, extra, arglen, found; + + std = 1; + extra = 1; + oo = other_options; + for (i = 0; i < PAM_MAX_OPTIONS; i++) { + if (std && std_options[i].name == NULL) + std = 0; + else if (extra && (oo == NULL || oo->name == NULL)) + extra = 0; + + if (std) + options->opt[i].name = std_options[i].name; + else if (extra) { + if (oo->value != i) + syslog(LOG_DEBUG, "Extra option fault: %d %d", + oo->value, i); + options->opt[i].name = oo->name; + oo++; + } + else + options->opt[i].name = NULL; + + options->opt[i].bool = 0; + options->opt[i].arg = NULL; + } + + for (j = 0; j < argc; j++) { +#ifdef DEBUG + syslog(LOG_DEBUG, "Doing arg %s", argv[j]); +#endif + found = 0; + for (i = 0; i < PAM_MAX_OPTIONS; i++) { + if (options->opt[i].name == NULL) + break; + arglen = strlen(options->opt[i].name); + if (strcmp(argv[j], options->opt[i].name) == 0) { + options->opt[i].bool = 1; + found = 1; + break; + } + else if (strncmp(argv[j], options->opt[i].name, arglen) + == 0 && argv[j][arglen] == '=') { + options->opt[i].bool = 1; + options->opt[i].arg + = strdup(&argv[j][arglen + 1]); + found = 1; + break; + } + } + if (!found) + syslog(LOG_WARNING, "PAM option: %s invalid", argv[j]); + } +} + +/* Test if option is set in options */ +int +pam_test_option(struct options *options, enum opt option, char **arg) +{ + if (arg != NULL) + *arg = options->opt[option].arg; + return options->opt[option].bool; +} + +/* Set option in options, errors to syslog */ +void +pam_set_option(struct options *options, enum opt option) +{ + if (option < PAM_OPT_STD_MAX) + options->opt[option].bool = 1; +#ifdef DEBUG + else + syslog(LOG_DEBUG, "PAM options: attempt to set option %d", + option); +#endif +} + +/* Clear option in options, errors to syslog */ +void +pam_clear_option(struct options *options, enum opt option) +{ + if (option < PAM_OPT_STD_MAX) + options->opt[option].bool = 0; +#ifdef DEBUG + else + syslog(LOG_DEBUG, "PAM options: attempt to clear option %d", + option); +#endif +} + +#ifdef DEBUG1 +enum { PAM_OPT_FOO=PAM_OPT_STD_MAX, PAM_OPT_BAR, PAM_OPT_BAZ, PAM_OPT_QUX }; + +struct opttab other_options[] = { + { "foo", PAM_OPT_FOO }, + { "bar", PAM_OPT_BAR }, + { "baz", PAM_OPT_BAZ }, + { "qux", PAM_OPT_QUX }, + { NULL, 0 } +}; + +int +main(int argc, const char *argv[]) +{ + struct options options; + int i, opt; + char *arg; + + pam_std_option(&options, other_options, argc, argv); + for (i = 0; i < PAM_MAX_OPTIONS; i++) { + opt = pam_test_option(&options, i, &arg); + if (opt) { + if (arg == NULL) + printf("%d []\n", i); + else + printf("%d [%s]\n", i, arg); + } + } + return 0; +} +#endif diff --git a/lib/libpam/libpam/security/pam_mod_misc.h b/lib/libpam/libpam/security/pam_mod_misc.h new file mode 100644 index 0000000..c9fc8d7 --- /dev/null +++ b/lib/libpam/libpam/security/pam_mod_misc.h @@ -0,0 +1,56 @@ +/*- + * Copyright 1998 Juniper Networks, Inc. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * $FreeBSD$ + */ + +#ifndef PAM_MOD_MISC_H +#define PAM_MOD_MISC_H + +#include <sys/cdefs.h> + +/* + * Common option names + */ +#define PAM_OPT_NULLOK "nullok" +#define PAM_OPT_AUTH_AS_SELF "auth_as_self" +#define PAM_OPT_ECHO_PASS "echo_pass" +#define PAM_OPT_DEBUG "debug" + +__BEGIN_DECLS +void _pam_verbose_error(pam_handle_t *, int, const char *, + const char *, const char *, ...); +__END_DECLS + +#define PAM_LOG(...) \ + openpam_log(PAM_LOG_DEBUG, __VA_ARGS__) + +#define PAM_RETURN(arg) \ + return (arg) + +#define PAM_VERBOSE_ERROR(...) \ + _pam_verbose_error(pamh, flags, __FILE__, __func__, __VA_ARGS__) + +#endif diff --git a/lib/libpam/modules/Makefile b/lib/libpam/modules/Makefile new file mode 100644 index 0000000..cacf011 --- /dev/null +++ b/lib/libpam/modules/Makefile @@ -0,0 +1,31 @@ +# Copyright 1998 Juniper Networks, Inc. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +.include "modules.inc" + +SUBDIR= ${MODULES} + +.include <bsd.subdir.mk> diff --git a/lib/libpam/modules/Makefile.inc b/lib/libpam/modules/Makefile.inc new file mode 100644 index 0000000..d4f2bb3 --- /dev/null +++ b/lib/libpam/modules/Makefile.inc @@ -0,0 +1,22 @@ +# $FreeBSD$ + +PAMDIR= ${.CURDIR}/../../../../contrib/openpam + +NO_INSTALLLIB= +NO_PROFILE= + +CFLAGS+= -I${PAMDIR}/include -I${.CURDIR}/../../libpam +WARNS?= 4 + +# This is nasty. +# For the static case, libpam.a depends on the modules. +# For the dynamic case, the modules depend on libpam.so.N +.if defined(_NO_LIBPAM_SO_YET) +NO_PIC= +.else +SHLIB_NAME?= ${LIB}.so.${SHLIB_MAJOR} +DPADD+= ${LIBPAM} +LDADD+= -lpam +.endif + +.include "../Makefile.inc" diff --git a/lib/libpam/modules/modules.inc b/lib/libpam/modules/modules.inc new file mode 100644 index 0000000..c570cfd --- /dev/null +++ b/lib/libpam/modules/modules.inc @@ -0,0 +1,33 @@ +# $FreeBSD$ + +.include <bsd.own.mk> + +MODULES = +MODULES += pam_chroot +MODULES += pam_deny +MODULES += pam_echo +MODULES += pam_exec +MODULES += pam_ftpusers +MODULES += pam_group +MODULES += pam_guest +.if ${MK_KERBEROS} != "no" +MODULES += pam_krb5 +MODULES += pam_ksu +.endif +MODULES += pam_lastlog +MODULES += pam_login_access +MODULES += pam_nologin +MODULES += pam_opie +MODULES += pam_opieaccess +MODULES += pam_passwdqc +MODULES += pam_permit +MODULES += pam_radius +MODULES += pam_rhosts +MODULES += pam_rootok +MODULES += pam_securetty +MODULES += pam_self +.if ${MK_OPENSSH} != "no" +MODULES += pam_ssh +.endif +MODULES += pam_tacplus +MODULES += pam_unix diff --git a/lib/libpam/modules/pam_chroot/Makefile b/lib/libpam/modules/pam_chroot/Makefile new file mode 100644 index 0000000..6d0fc0e --- /dev/null +++ b/lib/libpam/modules/pam_chroot/Makefile @@ -0,0 +1,7 @@ +# $FreeBSD$ + +LIB= pam_chroot +SRCS= pam_chroot.c +MAN= pam_chroot.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_chroot/pam_chroot.8 b/lib/libpam/modules/pam_chroot/pam_chroot.8 new file mode 100644 index 0000000..1bb4800 --- /dev/null +++ b/lib/libpam/modules/pam_chroot/pam_chroot.8 @@ -0,0 +1,94 @@ +.\" Copyright (c) 2003 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd February 10, 2003 +.Dt PAM_CHROOT 8 +.Os +.Sh NAME +.Nm pam_chroot +.Nd Chroot PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_chroot +.Op Ar arguments +.Sh DESCRIPTION +The chroot service module for PAM chroots users into either a +predetermined directory or one derived from their home directory. +If a user's home directory as specified in the +.Vt passwd +structure returned by +.Xr getpwnam 3 +contains the string +.Dq Li /./ , +the portion of the directory name to the left of that string is used +as the chroot directory, and the portion to the right will be the +current working directory inside the chroot tree. +Otherwise, the directories specified by the +.Cm dir +and +.Cm cwd +options (see below) are used. +.Bl -tag -width ".Cm also_root" +.It Cm also_root +Do not hold user ID 0 exempt from the chroot requirement. +.It Cm always +Report a failure if a chroot directory could not be derived from the +user's home directory, and the +.Cm dir +option was not specified. +.It Cm cwd Ns = Ns Ar directory +Specify the directory to +.Xr chdir 2 +into after a successful +.Xr chroot 2 +call. +.It Cm dir Ns = Ns Ar directory +Specify the chroot directory to use if one could not be derived from +the user's home directory. +.El +.Sh SEE ALSO +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module and this manual page were developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_chroot/pam_chroot.c b/lib/libpam/modules/pam_chroot/pam_chroot.c new file mode 100644 index 0000000..447e5f7 --- /dev/null +++ b/lib/libpam/modules/pam_chroot/pam_chroot.c @@ -0,0 +1,109 @@ +/*- + * Copyright (c) 2003 Networks Associates Technology, Inc. + * All rights reserved. + * + * This software was developed for the FreeBSD Project by ThinkSec AS and + * NAI Labs, the Security Research Division of Network Associates, Inc. + * under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the + * DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/param.h> + +#include <pwd.h> +#include <stdio.h> +#include <string.h> +#include <unistd.h> + +#define PAM_SM_SESSION + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/openpam.h> + +PAM_EXTERN int +pam_sm_open_session(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + const char *dir, *end, *cwd, *user; + struct passwd *pwd; + char buf[PATH_MAX]; + + if (pam_get_user(pamh, &user, NULL) != PAM_SUCCESS || + user == NULL || (pwd = getpwnam(user)) == NULL) + return (PAM_SESSION_ERR); + if (pwd->pw_uid == 0 && !openpam_get_option(pamh, "also_root")) + return (PAM_SUCCESS); + if (pwd->pw_dir == NULL) + return (PAM_SESSION_ERR); + if ((end = strstr(pwd->pw_dir, "/./")) != NULL) { + if (snprintf(buf, sizeof(buf), "%.*s", + (int)(end - pwd->pw_dir), pwd->pw_dir) > (int)sizeof(buf)) { + openpam_log(PAM_LOG_ERROR, + "%s's home directory is too long", user); + return (PAM_SESSION_ERR); + } + dir = buf; + cwd = end + 2; + } else if ((dir = openpam_get_option(pamh, "dir")) != NULL) { + if ((cwd = openpam_get_option(pamh, "cwd")) == NULL) + cwd = "/"; + } else { + if (openpam_get_option(pamh, "always")) { + openpam_log(PAM_LOG_ERROR, + "%s has no chroot directory", user); + return (PAM_SESSION_ERR); + } + return (PAM_SUCCESS); + } + + openpam_log(PAM_LOG_DEBUG, "chrooting %s to %s", dir, user); + + if (chroot(dir) == -1) { + openpam_log(PAM_LOG_ERROR, "chroot(): %m"); + return (PAM_SESSION_ERR); + } + if (chdir(cwd) == -1) { + openpam_log(PAM_LOG_ERROR, "chdir(): %m"); + return (PAM_SESSION_ERR); + } + pam_setenv(pamh, "HOME", cwd, 1); + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_close_session(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_chroot"); diff --git a/lib/libpam/modules/pam_deny/Makefile b/lib/libpam/modules/pam_deny/Makefile new file mode 100644 index 0000000..3bf8196 --- /dev/null +++ b/lib/libpam/modules/pam_deny/Makefile @@ -0,0 +1,31 @@ +# Copyright 1999 Max Khon. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_deny +SRCS= pam_deny.c +MAN= pam_deny.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_deny/pam_deny.8 b/lib/libpam/modules/pam_deny/pam_deny.8 new file mode 100644 index 0000000..d9544be --- /dev/null +++ b/lib/libpam/modules/pam_deny/pam_deny.8 @@ -0,0 +1,80 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd July 7, 2001 +.Dt PAM_DENY 8 +.Os +.Sh NAME +.Nm pam_deny +.Nd Deny PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_deny +.Op Ar options +.Sh DESCRIPTION +The Deny authentication service module for PAM, +.Nm +provides functionality for all the PAM categories: +authentication, +account management, +session management and +password management. +In terms of the +.Ar module-type +parameter, these are the +.Dq Li auth , +.Dq Li account , +.Dq Li session , +and +.Dq Li password +features. +.Pp +The Deny module +will universally deny all requests. +It is primarily of use during testing, +and to +.Dq null-out +unwanted functionality. +.Pp +The following options may be passed to the module: +.Bl -tag -width ".Cm no_warn" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +These messages include +reasons why the user's +authentication attempt was declined. +.El +.Sh SEE ALSO +.Xr syslog 3 , +.Xr pam.conf 5 , +.Xr pam 8 diff --git a/lib/libpam/modules/pam_deny/pam_deny.c b/lib/libpam/modules/pam_deny/pam_deny.c new file mode 100644 index 0000000..3d491b1 --- /dev/null +++ b/lib/libpam/modules/pam_deny/pam_deny.c @@ -0,0 +1,93 @@ +/*- + * Copyright 2001 Mark R V Murray + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <stddef.h> + +#define PAM_SM_AUTH +#define PAM_SM_ACCOUNT +#define PAM_SM_SESSION +#define PAM_SM_PASSWORD + +#include <security/pam_appl.h> +#include <security/pam_modules.h> + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + const char *user; + int r; + + if ((r = pam_get_user(pamh, &user, NULL)) != PAM_SUCCESS) + return (r); + + return (PAM_AUTH_ERR); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_CRED_ERR); +} + +PAM_EXTERN int +pam_sm_acct_mgmt(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_AUTH_ERR); +} + +PAM_EXTERN int +pam_sm_chauthtok(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_AUTHTOK_ERR); +} + +PAM_EXTERN int +pam_sm_open_session(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SESSION_ERR); +} + +PAM_EXTERN int +pam_sm_close_session(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SESSION_ERR); +} + +PAM_MODULE_ENTRY("pam_deny"); diff --git a/lib/libpam/modules/pam_echo/Makefile b/lib/libpam/modules/pam_echo/Makefile new file mode 100644 index 0000000..6f23946 --- /dev/null +++ b/lib/libpam/modules/pam_echo/Makefile @@ -0,0 +1,7 @@ +# $FreeBSD$ + +LIB= pam_echo +SRCS= pam_echo.c +MAN= pam_echo.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_echo/pam_echo.8 b/lib/libpam/modules/pam_echo/pam_echo.8 new file mode 100644 index 0000000..b162b5b --- /dev/null +++ b/lib/libpam/modules/pam_echo/pam_echo.8 @@ -0,0 +1,93 @@ +.\" Copyright (c) 2001,2003 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd February 6, 2003 +.Dt PAM_ECHO 8 +.Os +.Sh NAME +.Nm pam_echo +.Nd Echo PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_echo +.Op Ar arguments +.Sh DESCRIPTION +The echo service module for PAM displays its arguments to the user, +separated by spaces, using the current conversation function. +.Pp +If the +.Cm % +character occurs anywhere in the arguments to +.Nm , +it is assumed to introduce one of the following escape sequences: +.Bl -tag -width 4n +.It Cm %H +The name of the host on which the client runs +.Pq Dv PAM_RHOST . +.\".It Cm %h +.\"The name of the host on which the server runs. +.It Cm %s +The current service name +.Pq Dv PAM_SERVICE . +.It Cm %t +The name of the controlling tty +.Pq Dv PAM_TTY . +.It Cm %U +The applicant's user name +.Pq Dv PAM_RUSER . +.It Cm %u +The target account's user name +.Pq Dv PAM_USER . +.El +.Pp +Any other two-character sequence beginning with +.Cm % +expands to the character following the +.Cm % +character. +.Sh SEE ALSO +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module and this manual page were developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_echo/pam_echo.c b/lib/libpam/modules/pam_echo/pam_echo.c new file mode 100644 index 0000000..ff00859 --- /dev/null +++ b/lib/libpam/modules/pam_echo/pam_echo.c @@ -0,0 +1,156 @@ +/*- + * Copyright (c) 2001,2003 Networks Associates Technology, Inc. + * All rights reserved. + * + * This software was developed for the FreeBSD Project by ThinkSec AS and + * NAI Labs, the Security Research Division of Network Associates, Inc. + * under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the + * DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/openpam.h> + +static int +_pam_echo(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + char msg[PAM_MAX_MSG_SIZE]; + const void *str; + const char *p, *q; + int err, i, item; + size_t len; + + if (flags & PAM_SILENT) + return (PAM_SUCCESS); + for (i = 0, len = 0; i < argc && len < sizeof(msg) - 1; ++i) { + if (i > 0) + msg[len++] = ' '; + for (p = argv[i]; *p != '\0' && len < sizeof(msg) - 1; ++p) { + if (*p != '%' || p[1] == '\0') { + msg[len++] = *p; + continue; + } + switch (*++p) { + case 'H': + item = PAM_RHOST; + break; + case 'h': + /* not implemented */ + item = -1; + break; + case 's': + item = PAM_SERVICE; + break; + case 't': + item = PAM_TTY; + break; + case 'U': + item = PAM_RUSER; + break; + case 'u': + item = PAM_USER; + break; + default: + item = -1; + msg[len++] = *p; + break; + } + if (item == -1) + continue; + err = pam_get_item(pamh, item, &str); + if (err != PAM_SUCCESS) + return (err); + if (str == NULL) + str = "(null)"; + for (q = str; *q != '\0' && len < sizeof(msg) - 1; ++q) + msg[len++] = *q; + } + } + msg[len] = '\0'; + return (pam_info(pamh, "%s", msg)); +} + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + return (_pam_echo(pamh, flags, argc, argv)); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + return (_pam_echo(pamh, flags, argc, argv)); +} + +PAM_EXTERN int +pam_sm_open_session(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + return (_pam_echo(pamh, flags, argc, argv)); +} + +PAM_EXTERN int +pam_sm_close_session(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + return (_pam_echo(pamh, flags, argc, argv)); +} + +PAM_EXTERN int +pam_sm_chauthtok(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + if (flags & PAM_PRELIM_CHECK) + return (PAM_SUCCESS); + return (_pam_echo(pamh, flags, argc, argv)); +} + +PAM_MODULE_ENTRY("pam_echo"); diff --git a/lib/libpam/modules/pam_exec/Makefile b/lib/libpam/modules/pam_exec/Makefile new file mode 100644 index 0000000..0cf4268 --- /dev/null +++ b/lib/libpam/modules/pam_exec/Makefile @@ -0,0 +1,9 @@ +# $FreeBSD$ + +LIB= pam_exec +SRCS= pam_exec.c +MAN= pam_exec.8 + +WARNS?= 0 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_exec/pam_exec.8 b/lib/libpam/modules/pam_exec/pam_exec.8 new file mode 100644 index 0000000..311d64c --- /dev/null +++ b/lib/libpam/modules/pam_exec/pam_exec.8 @@ -0,0 +1,75 @@ +.\" Copyright (c) 2001,2003 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd February 1, 2005 +.Dt PAM_EXEC 8 +.Os +.Sh NAME +.Nm pam_exec +.Nd Exec PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_exec +.Op Ar arguments +.Sh DESCRIPTION +The exec service module for PAM executes the program designated by its +first argument, with its remaining arguments as command-line +arguments. +The child's environment is set to the current PAM environment list, +as returned by +.Xr pam_getenvlist 3 . +In addition, the following PAM items are exported as environment +variables: +.Ev PAM_RHOST , +.Ev PAM_RUSER , +.Ev PAM_SERVICE , +.Ev PAM_TTY , +and +.Ev PAM_USER . +.Sh SEE ALSO +.Xr pam_get_item 3 , +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module and this manual page were developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_exec/pam_exec.c b/lib/libpam/modules/pam_exec/pam_exec.c new file mode 100644 index 0000000..b27718f --- /dev/null +++ b/lib/libpam/modules/pam_exec/pam_exec.c @@ -0,0 +1,199 @@ +/*- + * Copyright (c) 2001,2003 Networks Associates Technology, Inc. + * All rights reserved. + * + * This software was developed for the FreeBSD Project by ThinkSec AS and + * NAI Labs, the Security Research Division of Network Associates, Inc. + * under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the + * DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/types.h> +#include <sys/wait.h> + +#include <errno.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/openpam.h> + +#define ENV_ITEM(n) { (n), #n } +static struct { + int item; + const char *name; +} env_items[] = { + ENV_ITEM(PAM_SERVICE), + ENV_ITEM(PAM_USER), + ENV_ITEM(PAM_TTY), + ENV_ITEM(PAM_RHOST), + ENV_ITEM(PAM_RUSER), +}; + +static int +_pam_exec(pam_handle_t *pamh __unused, int flags __unused, + int argc, const char *argv[]) +{ + int envlen, i, nitems, pam_err, status; + char *env, **envlist, **tmp; + volatile int childerr; + pid_t pid; + + if (argc < 1) + return (PAM_SERVICE_ERR); + + /* + * XXX For additional credit, divert child's stdin/stdout/stderr + * to the conversation function. + */ + + /* + * Set up the child's environment list. It consists of the PAM + * environment, plus a few hand-picked PAM items. + */ + envlist = pam_getenvlist(pamh); + for (envlen = 0; envlist[envlen] != NULL; ++envlen) + /* nothing */ ; + nitems = sizeof(env_items) / sizeof(*env_items); + tmp = realloc(envlist, (envlen + nitems + 1) * sizeof(*envlist)); + if (tmp == NULL) { + openpam_free_envlist(envlist); + return (PAM_BUF_ERR); + } + envlist = tmp; + for (i = 0; i < nitems; ++i) { + const void *item; + char *envstr; + + pam_err = pam_get_item(pamh, env_items[i].item, &item); + if (pam_err != PAM_SUCCESS || item == NULL) + continue; + asprintf(&envstr, "%s=%s", env_items[i].name, item); + if (envstr == NULL) { + openpam_free_envlist(envlist); + return (PAM_BUF_ERR); + } + envlist[envlen++] = envstr; + envlist[envlen] = NULL; + } + + /* + * Fork and run the command. By using vfork() instead of fork(), + * we can distinguish between an execve() failure and a non-zero + * exit code from the command. + */ + childerr = 0; + if ((pid = vfork()) == 0) { + execve(argv[0], (char * const *)argv, (char * const *)envlist); + childerr = errno; + _exit(1); + } + openpam_free_envlist(envlist); + if (pid == -1) { + openpam_log(PAM_LOG_ERROR, "vfork(): %m"); + return (PAM_SYSTEM_ERR); + } + if (waitpid(pid, &status, 0) == -1) { + openpam_log(PAM_LOG_ERROR, "waitpid(): %m"); + return (PAM_SYSTEM_ERR); + } + if (childerr != 0) { + openpam_log(PAM_LOG_ERROR, "execve(): %m"); + return (PAM_SYSTEM_ERR); + } + if (WIFSIGNALED(status)) { + openpam_log(PAM_LOG_ERROR, "%s caught signal %d%s", + argv[0], WTERMSIG(status), + WCOREDUMP(status) ? " (core dumped)" : ""); + return (PAM_SYSTEM_ERR); + } + if (!WIFEXITED(status)) { + openpam_log(PAM_LOG_ERROR, "unknown status 0x%x", status); + return (PAM_SYSTEM_ERR); + } + if (WEXITSTATUS(status) != 0) { + openpam_log(PAM_LOG_ERROR, "%s returned code %d", + argv[0], WEXITSTATUS(status)); + return (PAM_SYSTEM_ERR); + } + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + return (_pam_exec(pamh, flags, argc, argv)); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + return (_pam_exec(pamh, flags, argc, argv)); +} + +PAM_EXTERN int +pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + return (_pam_exec(pamh, flags, argc, argv)); +} + +PAM_EXTERN int +pam_sm_open_session(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + return (_pam_exec(pamh, flags, argc, argv)); +} + +PAM_EXTERN int +pam_sm_close_session(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + return (_pam_exec(pamh, flags, argc, argv)); +} + +PAM_EXTERN int +pam_sm_chauthtok(pam_handle_t *pamh, int flags, + int argc, const char *argv[]) +{ + + return (_pam_exec(pamh, flags, argc, argv)); +} + +PAM_MODULE_ENTRY("pam_exec"); diff --git a/lib/libpam/modules/pam_ftpusers/Makefile b/lib/libpam/modules/pam_ftpusers/Makefile new file mode 100644 index 0000000..8bca1aa --- /dev/null +++ b/lib/libpam/modules/pam_ftpusers/Makefile @@ -0,0 +1,7 @@ +# $FreeBSD$ + +LIB= pam_ftpusers +SRCS= pam_ftpusers.c +MAN= pam_ftpusers.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_ftpusers/pam_ftpusers.8 b/lib/libpam/modules/pam_ftpusers/pam_ftpusers.8 new file mode 100644 index 0000000..380e3b0 --- /dev/null +++ b/lib/libpam/modules/pam_ftpusers/pam_ftpusers.8 @@ -0,0 +1,99 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2002 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd April 17, 2002 +.Dt PAM_FTPUSERS 8 +.Os +.Sh NAME +.Nm pam_ftpusers +.Nd ftpusers PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_ftpusers +.Op Ar options +.Sh DESCRIPTION +The +.Pa ftpusers +service module for PAM, +.Nm +provides functionality for only one PAM category: +account management. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li account +feature. +.Ss Ftpusers Account Management Module +The +.Pa ftpusers +account management component +.Pq Fn pam_sm_acct_mgmt , +succeeds if and only if the user is listed in +.Pa /etc/ftpusers . +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm disallow" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +These messages include reasons why the user's authentication attempt +was declined. +.It Cm disallow +reverse the semantics; +.Nm +will succeed if and only if the user is not listed in +.Pa /etc/ftpusers . +.El +.Sh SEE ALSO +.Xr ftpusers 5 , +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module and this manual page were developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_ftpusers/pam_ftpusers.c b/lib/libpam/modules/pam_ftpusers/pam_ftpusers.c new file mode 100644 index 0000000..421955a --- /dev/null +++ b/lib/libpam/modules/pam_ftpusers/pam_ftpusers.c @@ -0,0 +1,115 @@ +/*- + * Copyright (c) 2001 Networks Associates Technology, Inc. + * All rights reserved. + * + * This software was developed for the FreeBSD Project by ThinkSec AS and + * NAI Labs, the Security Research Division of Network Associates, Inc. + * under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the + * DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <ctype.h> +#include <grp.h> +#include <paths.h> +#include <pwd.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#define PAM_SM_ACCOUNT + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> +#include <security/openpam.h> + +PAM_EXTERN int +pam_sm_acct_mgmt(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + struct passwd *pwd; + struct group *grp; + const char *user; + int pam_err, found, allow; + char *line, *name, **mem; + size_t len, ulen; + FILE *f; + + pam_err = pam_get_user(pamh, &user, NULL); + if (pam_err != PAM_SUCCESS) + return (pam_err); + if (user == NULL || (pwd = getpwnam(user)) == NULL) + return (PAM_SERVICE_ERR); + + found = 0; + ulen = strlen(user); + if ((f = fopen(_PATH_FTPUSERS, "r")) == NULL) { + PAM_LOG("%s: %m", _PATH_FTPUSERS); + goto done; + } + while (!found && (line = fgetln(f, &len)) != NULL) { + if (*line == '#') + continue; + while (len > 0 && isspace(line[len - 1])) + --len; + if (len == 0) + continue; + /* simple case first */ + if (*line != '@') { + if (len == ulen && strncmp(user, line, len) == 0) + found = 1; + continue; + } + /* member of specified group? */ + asprintf(&name, "%.*s", (int)len - 1, line + 1); + if (name == NULL) { + fclose(f); + return (PAM_BUF_ERR); + } + grp = getgrnam(name); + free(name); + if (grp == NULL) + continue; + for (mem = grp->gr_mem; mem && *mem && !found; ++mem) + if (strcmp(user, *mem) == 0) + found = 1; + } + done: + allow = (openpam_get_option(pamh, "disallow") == NULL); + if (found) + pam_err = allow ? PAM_SUCCESS : PAM_AUTH_ERR; + else + pam_err = allow ? PAM_AUTH_ERR : PAM_SUCCESS; + if (f != NULL) + fclose(f); + return (pam_err); +} + +PAM_MODULE_ENTRY("pam_ftpusers"); diff --git a/lib/libpam/modules/pam_group/Makefile b/lib/libpam/modules/pam_group/Makefile new file mode 100644 index 0000000..73b072a --- /dev/null +++ b/lib/libpam/modules/pam_group/Makefile @@ -0,0 +1,7 @@ +# $FreeBSD$ + +LIB= pam_group +SRCS= pam_group.c +MAN= pam_group.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_group/pam_group.8 b/lib/libpam/modules/pam_group/pam_group.8 new file mode 100644 index 0000000..832841b --- /dev/null +++ b/lib/libpam/modules/pam_group/pam_group.8 @@ -0,0 +1,83 @@ +.\" Copyright (c) 2003 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd February 6, 2003 +.Dt PAM_GROUP 8 +.Os +.Sh NAME +.Nm pam_group +.Nd Group PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_group +.Op Ar arguments +.Sh DESCRIPTION +The group service module for PAM accepts or rejects users based on +their membership in a particular file group. +.Pp +The following options may be passed to the +.Nm +module: +.Bl -tag -width ".Cm fail_safe" +.It Cm deny +Reverse the meaning of the test, i.e., reject the applicant if and only +if he or she is a member of the specified group. +This can be useful to exclude certain groups of users from certain +services. +.It Cm fail_safe +If the specified group does not exist, or has no members, act as if +it does exist and the applicant is a member. +.It Cm group Ns = Ns Ar groupname +Specify the name of the group to check. +The default is +.Dq Li wheel . +.It Cm root_only +Skip this module entirely if the target account is not the superuser +account. +.El +.Sh SEE ALSO +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module and this manual page were developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_group/pam_group.c b/lib/libpam/modules/pam_group/pam_group.c new file mode 100644 index 0000000..a9d5fc3 --- /dev/null +++ b/lib/libpam/modules/pam_group/pam_group.c @@ -0,0 +1,117 @@ +/*- + * Copyright (c) 2003 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/types.h> + +#include <grp.h> +#include <pwd.h> +#include <stdarg.h> +#include <stdio.h> +#include <string.h> +#include <syslog.h> +#include <unistd.h> + +#define PAM_SM_AUTH + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/openpam.h> + + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + const char *group, *user; + const void *ruser; + char *const *list; + struct passwd *pwd; + struct group *grp; + + /* get target account */ + if (pam_get_user(pamh, &user, NULL) != PAM_SUCCESS || + user == NULL || (pwd = getpwnam(user)) == NULL) + return (PAM_AUTH_ERR); + if (pwd->pw_uid != 0 && openpam_get_option(pamh, "root_only")) + return (PAM_IGNORE); + + /* get applicant */ + if (pam_get_item(pamh, PAM_RUSER, &ruser) != PAM_SUCCESS + || ruser == NULL || (pwd = getpwnam(ruser)) == NULL) + return (PAM_AUTH_ERR); + + /* get regulating group */ + if ((group = openpam_get_option(pamh, "group")) == NULL) + group = "wheel"; + if ((grp = getgrnam(group)) == NULL || grp->gr_mem == NULL) + goto failed; + + /* check if the group is empty */ + if (*grp->gr_mem == NULL) + goto failed; + + /* check membership */ + if (pwd->pw_gid == grp->gr_gid) + goto found; + for (list = grp->gr_mem; *list != NULL; ++list) + if (strcmp(*list, pwd->pw_name) == 0) + goto found; + + not_found: + if (openpam_get_option(pamh, "deny")) + return (PAM_SUCCESS); + return (PAM_AUTH_ERR); + found: + if (openpam_get_option(pamh, "deny")) + return (PAM_AUTH_ERR); + return (PAM_SUCCESS); + failed: + if (openpam_get_option(pamh, "fail_safe")) + goto found; + else + goto not_found; +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t * pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_group"); diff --git a/lib/libpam/modules/pam_guest/Makefile b/lib/libpam/modules/pam_guest/Makefile new file mode 100644 index 0000000..ccc192e --- /dev/null +++ b/lib/libpam/modules/pam_guest/Makefile @@ -0,0 +1,7 @@ +# $FreeBSD$ + +LIB= pam_guest +SRCS= pam_guest.c +MAN= pam_guest.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_guest/pam_guest.8 b/lib/libpam/modules/pam_guest/pam_guest.8 new file mode 100644 index 0000000..0bd1755 --- /dev/null +++ b/lib/libpam/modules/pam_guest/pam_guest.8 @@ -0,0 +1,98 @@ +.\" Copyright (c) 2003 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd May 26, 2003 +.Dt PAM_GUEST 8 +.Os +.Sh NAME +.Nm pam_guest +.Nd Guest PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_guest +.Op Ar arguments +.Sh DESCRIPTION +The guest service module for PAM allows guest logins. +If successful, the +.Nm +module sets the PAM environment variable +.Ev GUEST +to the login name. +The application can check this variable using +.Xr pam_getenv 3 +to differentiate guest logins from normal logins. +.Pp +The following options may be passed to the +.Nm +module: +.Bl -tag -width ".Cm pass_as_ruser" +.It Cm guests Ns = Ns Ar list +Comma-separated list of guest account names. +The default is +.Dq Li guest . +A typical value for +.Xr ftpd 8 +would be +.Dq Li anonymous,ftp . +.It Cm nopass +Omits the password prompt if the target account is on the list of +guest accounts. +.It Cm pass_as_ruser +The password typed in by the user is exported as the +.Dv PAM_RUSER +item. +This is useful for applications like +.Xr ftpd 8 +where guest users are encouraged to use their email address as +password. +.It Cm pass_is_user +Requires the guest user to type in the guest account name as password. +.El +.Sh SEE ALSO +.Xr pam_getenv 3 , +.Xr pam_get_item 3 , +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module and this manual page were developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_guest/pam_guest.c b/lib/libpam/modules/pam_guest/pam_guest.c new file mode 100644 index 0000000..110edce --- /dev/null +++ b/lib/libpam/modules/pam_guest/pam_guest.c @@ -0,0 +1,114 @@ +/*- + * Copyright (c) 2003 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <string.h> + +#define PAM_SM_AUTH + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/openpam.h> + +#define DEFAULT_GUESTS "guest" + +static int +lookup(const char *str, const char *list) +{ + const char *next; + size_t len; + + len = strlen(str); + while (*list != '\0') { + while (*list == ',') + ++list; + if ((next = strchr(list, ',')) == NULL) + next = strchr(list, '\0'); + if (next - list == (ptrdiff_t)len && + strncmp(list, str, len) == 0) + return (1); + list = next; + } + return (0); +} + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + const char *authtok, *guests, *user; + int err, is_guest; + + /* get target account */ + if (pam_get_user(pamh, &user, NULL) != PAM_SUCCESS || user == NULL) + return (PAM_AUTH_ERR); + + /* get list of guest logins */ + if ((guests = openpam_get_option(pamh, "guests")) == NULL) + guests = DEFAULT_GUESTS; + + /* check if the target account is on the list */ + is_guest = lookup(user, guests); + + /* check password */ + if (!openpam_get_option(pamh, "nopass")) { + err = pam_get_authtok(pamh, PAM_AUTHTOK, &authtok, NULL); + if (err != PAM_SUCCESS) + return (err); + if (openpam_get_option(pamh, "pass_is_user") && + strcmp(user, authtok) != 0) + return (PAM_AUTH_ERR); + if (openpam_get_option(pamh, "pass_as_ruser")) + pam_set_item(pamh, PAM_RUSER, authtok); + } + + /* done */ + if (is_guest) { + pam_setenv(pamh, "GUEST", user, 1); + return (PAM_SUCCESS); + } + return (PAM_AUTH_ERR); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t * pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_guest"); diff --git a/lib/libpam/modules/pam_krb5/Makefile b/lib/libpam/modules/pam_krb5/Makefile new file mode 100644 index 0000000..a90236c --- /dev/null +++ b/lib/libpam/modules/pam_krb5/Makefile @@ -0,0 +1,38 @@ +# Copyright 2001 FreeBSD, Inc. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_krb5 +SRCS= pam_krb5.c +MAN= pam_krb5.8 +.if defined(_FREEFALL_CONFIG) +CFLAGS+=-D_FREEFALL_CONFIG +WARNS= 0 +.endif + +DPADD= ${LIBKRB5} ${LIBASN1} ${LIBROKEN} ${LIBCOM_ERR} ${LIBCRYPT} ${LIBCRYPTO} +LDADD= -lkrb5 -lasn1 -lroken -lcom_err -lcrypt -lcrypto + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_krb5/pam_krb5.8 b/lib/libpam/modules/pam_krb5/pam_krb5.8 new file mode 100644 index 0000000..3e0db91 --- /dev/null +++ b/lib/libpam/modules/pam_krb5/pam_krb5.8 @@ -0,0 +1,217 @@ +.\" +.\" $Id: pam_krb5.5,v 1.5 2000/01/05 00:59:56 fcusack Exp $ +.\" $FreeBSD$ +.Dd January 15, 1999 +.Dt PAM_KRB5 8 +.Os +.Sh NAME +.Nm pam_krb5 +.Nd Kerberos 5 PAM module +.Sh SYNOPSIS +.Pa /usr/lib/pam_krb5.so +.Sh DESCRIPTION +The Kerberos 5 service module for PAM, typically +.Pa /usr/lib/pam_krb5.so , +provides functionality for three PAM categories: +authentication, +account management, +and password management. +It also provides null functions for session management. +The +.Pa pam_krb5.so +module is a shared object +that can be dynamically loaded to provide +the necessary functionality upon demand. +Its path is specified in the +PAM configuration file. +.Ss Kerberos 5 Authentication Module +The Kerberos 5 authentication component +provides functions to verify the identity of a user +.Pq Fn pam_sm_authenticate +and to set user specific credentials +.Pq Fn pam_sm_setcred . +.Fn pam_sm_authenticate +converts the supplied username into a Kerberos principal, +by appending the default local realm name. +It also supports usernames with explicit realm names. +If a realm name is supplied, then upon a successful return, it +changes the username by mapping the principal name into a local username +(calling +.Fn krb5_aname_to_localname ) . +This typically just means +the realm name is stripped. +.Pp +It prompts the user for a password and obtains a new Kerberos TGT for +the principal. +The TGT is verified by obtaining a service +ticket for the local host. +.Pp +When prompting for the current password, the authentication +module will use the prompt +.Dq Li "Password for <principal>:" . +.Pp +The +.Fn pam_sm_setcred +function stores the newly acquired credentials in a credentials cache, +and sets the environment variable +.Ev KRB5CCNAME +appropriately. +The credentials cache should be destroyed by the user at logout with +.Xr kdestroy 1 . +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm use_first_pass" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +These messages include +reasons why the user's +authentication attempt was declined. +.It Cm use_first_pass +If the authentication module is not the first in the stack, +and a previous module obtained the user's password, that password is +used to authenticate the user. +If this fails, the authentication +module returns failure without prompting the user for a password. +This option has no effect if the authentication module is +the first in the stack, or if no previous modules obtained the +user's password. +.It Cm try_first_pass +This option is similar to the +.Cm use_first_pass +option, except that if the previously obtained password fails, the +user is prompted for another password. +.It Cm forwardable +Obtain forwardable Kerberos credentials for the user. +.It Cm no_ccache +Do not save the obtained credentials in a credentials cache. +This is a +useful option if the authentication module is used for services such +as ftp or pop, where the user would not be able to destroy them. +[This +is not a recommendation to use the module for those services.] +.It Cm ccache Ns = Ns Ar name +Use +.Ar name +as the credentials cache. +.Ar name +must be in the form +.Ar type : Ns Ar residual . +The special tokens +.Ql %u , +to designate the decimal UID of the user; +and +.Ql %p , +to designate the current process ID; can be used in +.Ar name . +.El +.Ss Kerberos 5 Account Management Module +The Kerberos 5 account management component +provides a function to perform account management, +.Fn pam_sm_acct_mgmt . +The function verifies that the authenticated principal is allowed +to login to the local user account by calling +.Fn krb5_kuserok +(which checks the user's +.Pa .k5login +file). +.Ss Kerberos 5 Password Management Module +The Kerberos 5 password management component +provides a function to change passwords +.Pq Fn pam_sm_chauthtok . +The username supplied (the +user running the +.Xr passwd 1 +command, or the username given as an argument) is mapped into +a Kerberos principal name, using the same technique as in +the authentication module. +Note that if a realm name was +explicitly supplied during authentication, but not during +a password change, the mapping +done by the password management module may not result in the +same principal as was used for authentication. +.Pp +Unlike when +changing a +.Ux +password, the password management module will +allow any user to change any principal's password (if the user knows +the principal's old password, of course). +Also unlike +.Ux , +root +is always prompted for the principal's old password. +.Pp +The password management module uses the same heuristics as +.Xr kpasswd 1 +to determine how to contact the Kerberos password server. +.Pp +The following options may be passed to the password management +module: +.Bl -tag -width ".Cm use_first_pass" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm use_first_pass +If the password management module is not the first in the stack, +and a previous module obtained the user's old password, that password is +used to authenticate the user. +If this fails, the password +management +module returns failure without prompting the user for the old password. +If successful, the new password entered to the previous module is also +used as the new Kerberos password. +If the new password fails, +the password management module returns failure without +prompting the user for a new password. +.It Cm try_first_pass +This option is similar to the +.Cm use_first_pass +option, except that if the previously obtained old or new passwords fail, +the user is prompted for them. +.El +.Ss Kerberos 5 Session Management Module +The Kerberos 5 session management component +provides functions to initiate +.Pq Fn pam_sm_open_session +and terminate +.Pq Fn pam_sm_close_session +sessions. +Since session management is not defined under Kerberos 5, +both of these functions simply return success. +They are provided +only because of the naming conventions for PAM modules. +.Sh ENVIRONMENT +.Bl -tag -width "KRB5CCNAME" +.It Ev KRB5CCNAME +Location of the credentials cache. +.El +.Sh FILES +.Bl -tag -width ".Pa /tmp/krb5cc_ Ns Ar uid" -compact +.It Pa /tmp/krb5cc_ Ns Ar uid +default credentials cache +.Ar ( uid +is the decimal UID of the user). +.It Pa $HOME/.k5login +file containing Kerberos principals that are allowed access. +.El +.Sh SEE ALSO +.Xr kdestroy 1 , +.Xr passwd 1 , +.Xr syslog 3 , +.Xr pam.conf 5 , +.Xr pam 8 +.Sh NOTES +Applications should not call +.Fn pam_authenticate +more than once between calls to +.Fn pam_start +and +.Fn pam_end +when using the Kerberos 5 PAM module. diff --git a/lib/libpam/modules/pam_krb5/pam_krb5.c b/lib/libpam/modules/pam_krb5/pam_krb5.c new file mode 100644 index 0000000..b56e0a3 --- /dev/null +++ b/lib/libpam/modules/pam_krb5/pam_krb5.c @@ -0,0 +1,971 @@ +/*- + * This pam_krb5 module contains code that is: + * Copyright (c) Derrick J. Brashear, 1996. All rights reserved. + * Copyright (c) Frank Cusack, 1999-2001. All rights reserved. + * Copyright (c) Jacques A. Vidrine, 2000-2001. All rights reserved. + * Copyright (c) Nicolas Williams, 2001. All rights reserved. + * Copyright (c) Perot Systems Corporation, 2001. All rights reserved. + * Copyright (c) Mark R V Murray, 2001. All rights reserved. + * Copyright (c) Networks Associates Technology, Inc., 2002-2005. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notices, and the entire permission notice in its entirety, + * including the disclaimer of warranties. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior + * written permission. + * + * ALTERNATIVELY, this product may be distributed under the terms of + * the GNU Public License, in which case the provisions of the GPL are + * required INSTEAD OF the above restrictions. (This clause is + * necessary due to a potential bad interaction between the GPL and + * the restrictions contained in a BSD-style copyright.) + * + * THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED + * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES + * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, + * INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR + * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, + * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED + * OF THE POSSIBILITY OF SUCH DAMAGE. + * + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/types.h> +#include <sys/stat.h> +#include <errno.h> +#include <limits.h> +#include <pwd.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <syslog.h> +#include <unistd.h> + +#include <krb5.h> +#include <com_err.h> + +#define PAM_SM_AUTH +#define PAM_SM_ACCOUNT +#define PAM_SM_PASSWORD + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> +#include <security/openpam.h> + +#define COMPAT_HEIMDAL +/* #define COMPAT_MIT */ + +static int verify_krb_v5_tgt(krb5_context, krb5_ccache, char *, int); +static void cleanup_cache(pam_handle_t *, void *, int); +static const char *compat_princ_component(krb5_context, krb5_principal, int); +static void compat_free_data_contents(krb5_context, krb5_data *); + +#define USER_PROMPT "Username: " +#define PASSWORD_PROMPT "Password:" +#define NEW_PASSWORD_PROMPT "New Password:" + +#define PAM_OPT_CCACHE "ccache" +#define PAM_OPT_DEBUG "debug" +#define PAM_OPT_FORWARDABLE "forwardable" +#define PAM_OPT_NO_CCACHE "no_ccache" +#define PAM_OPT_REUSE_CCACHE "reuse_ccache" + +/* + * authentication management + */ +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + krb5_error_code krbret; + krb5_context pam_context; + krb5_creds creds; + krb5_principal princ; + krb5_ccache ccache; + krb5_get_init_creds_opt opts; + struct passwd *pwd; + int retval; + const void *ccache_data; + const char *user, *pass; + const void *sourceuser, *service; + char *principal, *princ_name, *ccache_name, luser[32], *srvdup; + + retval = pam_get_user(pamh, &user, USER_PROMPT); + if (retval != PAM_SUCCESS) + return (retval); + + PAM_LOG("Got user: %s", user); + + retval = pam_get_item(pamh, PAM_RUSER, &sourceuser); + if (retval != PAM_SUCCESS) + return (retval); + + PAM_LOG("Got ruser: %s", (const char *)sourceuser); + + service = NULL; + pam_get_item(pamh, PAM_SERVICE, &service); + if (service == NULL) + service = "unknown"; + + PAM_LOG("Got service: %s", (const char *)service); + + krbret = krb5_init_context(&pam_context); + if (krbret != 0) { + PAM_VERBOSE_ERROR("Kerberos 5 error"); + return (PAM_SERVICE_ERR); + } + + PAM_LOG("Context initialised"); + + krb5_get_init_creds_opt_init(&opts); + + if (openpam_get_option(pamh, PAM_OPT_FORWARDABLE)) + krb5_get_init_creds_opt_set_forwardable(&opts, 1); + + PAM_LOG("Credentials initialised"); + + krbret = krb5_cc_register(pam_context, &krb5_mcc_ops, FALSE); + if (krbret != 0 && krbret != KRB5_CC_TYPE_EXISTS) { + PAM_VERBOSE_ERROR("Kerberos 5 error"); + retval = PAM_SERVICE_ERR; + goto cleanup3; + } + + PAM_LOG("Done krb5_cc_register()"); + + /* Get principal name */ + if (openpam_get_option(pamh, PAM_OPT_AUTH_AS_SELF)) + asprintf(&principal, "%s/%s", (const char *)sourceuser, user); + else + principal = strdup(user); + + PAM_LOG("Created principal: %s", principal); + + krbret = krb5_parse_name(pam_context, principal, &princ); + free(principal); + if (krbret != 0) { + PAM_LOG("Error krb5_parse_name(): %s", + krb5_get_err_text(pam_context, krbret)); + PAM_VERBOSE_ERROR("Kerberos 5 error"); + retval = PAM_SERVICE_ERR; + goto cleanup3; + } + + PAM_LOG("Done krb5_parse_name()"); + + /* Now convert the principal name into something human readable */ + princ_name = NULL; + krbret = krb5_unparse_name(pam_context, princ, &princ_name); + if (krbret != 0) { + PAM_LOG("Error krb5_unparse_name(): %s", + krb5_get_err_text(pam_context, krbret)); + PAM_VERBOSE_ERROR("Kerberos 5 error"); + retval = PAM_SERVICE_ERR; + goto cleanup2; + } + + PAM_LOG("Got principal: %s", princ_name); + + /* Get password */ + retval = pam_get_authtok(pamh, PAM_AUTHTOK, &pass, PASSWORD_PROMPT); + if (retval != PAM_SUCCESS) + goto cleanup2; + + PAM_LOG("Got password"); + + /* Verify the local user exists (AFTER getting the password) */ + if (strchr(user, '@')) { + /* get a local account name for this principal */ + krbret = krb5_aname_to_localname(pam_context, princ, + sizeof(luser), luser); + if (krbret != 0) { + PAM_VERBOSE_ERROR("Kerberos 5 error"); + PAM_LOG("Error krb5_aname_to_localname(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_USER_UNKNOWN; + goto cleanup2; + } + + retval = pam_set_item(pamh, PAM_USER, luser); + if (retval != PAM_SUCCESS) + goto cleanup2; + + PAM_LOG("PAM_USER Redone"); + } + + pwd = getpwnam(user); + if (pwd == NULL) { + retval = PAM_USER_UNKNOWN; + goto cleanup2; + } + + PAM_LOG("Done getpwnam()"); + + /* Get a TGT */ + memset(&creds, 0, sizeof(krb5_creds)); + krbret = krb5_get_init_creds_password(pam_context, &creds, princ, + pass, NULL, pamh, 0, NULL, &opts); + if (krbret != 0) { + PAM_VERBOSE_ERROR("Kerberos 5 error"); + PAM_LOG("Error krb5_get_init_creds_password(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_AUTH_ERR; + goto cleanup2; + } + + PAM_LOG("Got TGT"); + + /* Generate a temporary cache */ + krbret = krb5_cc_gen_new(pam_context, &krb5_mcc_ops, &ccache); + if (krbret != 0) { + PAM_VERBOSE_ERROR("Kerberos 5 error"); + PAM_LOG("Error krb5_cc_gen_new(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_SERVICE_ERR; + goto cleanup; + } + krbret = krb5_cc_initialize(pam_context, ccache, princ); + if (krbret != 0) { + PAM_VERBOSE_ERROR("Kerberos 5 error"); + PAM_LOG("Error krb5_cc_initialize(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_SERVICE_ERR; + goto cleanup; + } + krbret = krb5_cc_store_cred(pam_context, ccache, &creds); + if (krbret != 0) { + PAM_VERBOSE_ERROR("Kerberos 5 error"); + PAM_LOG("Error krb5_cc_store_cred(): %s", + krb5_get_err_text(pam_context, krbret)); + krb5_cc_destroy(pam_context, ccache); + retval = PAM_SERVICE_ERR; + goto cleanup; + } + + PAM_LOG("Credentials stashed"); + + /* Verify them */ + if ((srvdup = strdup(service)) == NULL) { + retval = PAM_BUF_ERR; + goto cleanup; + } + krbret = verify_krb_v5_tgt(pam_context, ccache, srvdup, + openpam_get_option(pamh, PAM_OPT_DEBUG) ? 1 : 0); + free(srvdup); + if (krbret == -1) { + PAM_VERBOSE_ERROR("Kerberos 5 error"); + krb5_cc_destroy(pam_context, ccache); + retval = PAM_AUTH_ERR; + goto cleanup; + } + + PAM_LOG("Credentials stash verified"); + + retval = pam_get_data(pamh, "ccache", &ccache_data); + if (retval == PAM_SUCCESS) { + krb5_cc_destroy(pam_context, ccache); + PAM_VERBOSE_ERROR("Kerberos 5 error"); + retval = PAM_AUTH_ERR; + goto cleanup; + } + + PAM_LOG("Credentials stash not pre-existing"); + + asprintf(&ccache_name, "%s:%s", krb5_cc_get_type(pam_context, + ccache), krb5_cc_get_name(pam_context, ccache)); + if (ccache_name == NULL) { + PAM_VERBOSE_ERROR("Kerberos 5 error"); + retval = PAM_BUF_ERR; + goto cleanup; + } + retval = pam_set_data(pamh, "ccache", ccache_name, cleanup_cache); + if (retval != 0) { + krb5_cc_destroy(pam_context, ccache); + PAM_VERBOSE_ERROR("Kerberos 5 error"); + retval = PAM_SERVICE_ERR; + goto cleanup; + } + + PAM_LOG("Credentials stash saved"); + +cleanup: + krb5_free_cred_contents(pam_context, &creds); + PAM_LOG("Done cleanup"); +cleanup2: + krb5_free_principal(pam_context, princ); + PAM_LOG("Done cleanup2"); +cleanup3: + if (princ_name) + free(princ_name); + + krb5_free_context(pam_context); + + PAM_LOG("Done cleanup3"); + + if (retval != PAM_SUCCESS) + PAM_VERBOSE_ERROR("Kerberos 5 refuses you"); + + return (retval); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh, int flags, + int argc __unused, const char *argv[] __unused) +{ +#ifdef _FREEFALL_CONFIG + return (PAM_SUCCESS); +#else + + krb5_error_code krbret; + krb5_context pam_context; + krb5_principal princ; + krb5_creds creds; + krb5_ccache ccache_temp, ccache_perm; + krb5_cc_cursor cursor; + struct passwd *pwd = NULL; + int retval; + const char *cache_name, *q; + const void *user; + const void *cache_data; + char *cache_name_buf = NULL, *p; + + uid_t euid; + gid_t egid; + + if (flags & PAM_DELETE_CRED) + return (PAM_SUCCESS); + + if (flags & PAM_REFRESH_CRED) + return (PAM_SUCCESS); + + if (flags & PAM_REINITIALIZE_CRED) + return (PAM_SUCCESS); + + if (!(flags & PAM_ESTABLISH_CRED)) + return (PAM_SERVICE_ERR); + + /* If a persistent cache isn't desired, stop now. */ + if (openpam_get_option(pamh, PAM_OPT_NO_CCACHE)) + return (PAM_SUCCESS); + + PAM_LOG("Establishing credentials"); + + /* Get username */ + retval = pam_get_item(pamh, PAM_USER, &user); + if (retval != PAM_SUCCESS) + return (retval); + + PAM_LOG("Got user: %s", (const char *)user); + + krbret = krb5_init_context(&pam_context); + if (krbret != 0) { + PAM_LOG("Error krb5_init_context() failed"); + return (PAM_SERVICE_ERR); + } + + PAM_LOG("Context initialised"); + + euid = geteuid(); /* Usually 0 */ + egid = getegid(); + + PAM_LOG("Got euid, egid: %d %d", euid, egid); + + /* Retrieve the temporary cache */ + retval = pam_get_data(pamh, "ccache", &cache_data); + if (retval != PAM_SUCCESS) { + retval = PAM_CRED_UNAVAIL; + goto cleanup3; + } + krbret = krb5_cc_resolve(pam_context, cache_data, &ccache_temp); + if (krbret != 0) { + PAM_LOG("Error krb5_cc_resolve(\"%s\"): %s", (const char *)cache_data, + krb5_get_err_text(pam_context, krbret)); + retval = PAM_SERVICE_ERR; + goto cleanup3; + } + + /* Get the uid. This should exist. */ + pwd = getpwnam(user); + if (pwd == NULL) { + retval = PAM_USER_UNKNOWN; + goto cleanup3; + } + + PAM_LOG("Done getpwnam()"); + + /* Avoid following a symlink as root */ + if (setegid(pwd->pw_gid)) { + retval = PAM_SERVICE_ERR; + goto cleanup3; + } + if (seteuid(pwd->pw_uid)) { + retval = PAM_SERVICE_ERR; + goto cleanup3; + } + + PAM_LOG("Done setegid() & seteuid()"); + + /* Get the cache name */ + cache_name = openpam_get_option(pamh, PAM_OPT_CCACHE); + if (cache_name == NULL) { + asprintf(&cache_name_buf, "FILE:/tmp/krb5cc_%d", pwd->pw_uid); + cache_name = cache_name_buf; + } + + p = calloc(PATH_MAX + 16, sizeof(char)); + q = cache_name; + + if (p == NULL) { + PAM_LOG("Error malloc(): failure"); + retval = PAM_BUF_ERR; + goto cleanup3; + } + cache_name = p; + + /* convert %u and %p */ + while (*q) { + if (*q == '%') { + q++; + if (*q == 'u') { + sprintf(p, "%d", pwd->pw_uid); + p += strlen(p); + } + else if (*q == 'p') { + sprintf(p, "%d", getpid()); + p += strlen(p); + } + else { + /* Not a special token */ + *p++ = '%'; + q--; + } + q++; + } + else { + *p++ = *q++; + } + } + + PAM_LOG("Got cache_name: %s", cache_name); + + /* Initialize the new ccache */ + krbret = krb5_cc_get_principal(pam_context, ccache_temp, &princ); + if (krbret != 0) { + PAM_LOG("Error krb5_cc_get_principal(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_SERVICE_ERR; + goto cleanup3; + } + krbret = krb5_cc_resolve(pam_context, cache_name, &ccache_perm); + if (krbret != 0) { + PAM_LOG("Error krb5_cc_resolve(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_SERVICE_ERR; + goto cleanup2; + } + krbret = krb5_cc_initialize(pam_context, ccache_perm, princ); + if (krbret != 0) { + PAM_LOG("Error krb5_cc_initialize(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_SERVICE_ERR; + goto cleanup2; + } + + PAM_LOG("Cache initialised"); + + /* Prepare for iteration over creds */ + krbret = krb5_cc_start_seq_get(pam_context, ccache_temp, &cursor); + if (krbret != 0) { + PAM_LOG("Error krb5_cc_start_seq_get(): %s", + krb5_get_err_text(pam_context, krbret)); + krb5_cc_destroy(pam_context, ccache_perm); + retval = PAM_SERVICE_ERR; + goto cleanup2; + } + + PAM_LOG("Prepared for iteration"); + + /* Copy the creds (should be two of them) */ + while ((krbret = krb5_cc_next_cred(pam_context, ccache_temp, + &cursor, &creds) == 0)) { + krbret = krb5_cc_store_cred(pam_context, ccache_perm, &creds); + if (krbret != 0) { + PAM_LOG("Error krb5_cc_store_cred(): %s", + krb5_get_err_text(pam_context, krbret)); + krb5_cc_destroy(pam_context, ccache_perm); + krb5_free_cred_contents(pam_context, &creds); + retval = PAM_SERVICE_ERR; + goto cleanup2; + } + krb5_free_cred_contents(pam_context, &creds); + PAM_LOG("Iteration"); + } + krb5_cc_end_seq_get(pam_context, ccache_temp, &cursor); + + PAM_LOG("Done iterating"); + + if (strstr(cache_name, "FILE:") == cache_name) { + if (chown(&cache_name[5], pwd->pw_uid, pwd->pw_gid) == -1) { + PAM_LOG("Error chown(): %s", strerror(errno)); + krb5_cc_destroy(pam_context, ccache_perm); + retval = PAM_SERVICE_ERR; + goto cleanup2; + } + PAM_LOG("Done chown()"); + + if (chmod(&cache_name[5], (S_IRUSR | S_IWUSR)) == -1) { + PAM_LOG("Error chmod(): %s", strerror(errno)); + krb5_cc_destroy(pam_context, ccache_perm); + retval = PAM_SERVICE_ERR; + goto cleanup2; + } + PAM_LOG("Done chmod()"); + } + + krb5_cc_close(pam_context, ccache_perm); + + PAM_LOG("Cache closed"); + + retval = pam_setenv(pamh, "KRB5CCNAME", cache_name, 1); + if (retval != PAM_SUCCESS) { + PAM_LOG("Error pam_setenv(): %s", pam_strerror(pamh, retval)); + krb5_cc_destroy(pam_context, ccache_perm); + retval = PAM_SERVICE_ERR; + goto cleanup2; + } + + PAM_LOG("Environment done: KRB5CCNAME=%s", cache_name); + +cleanup2: + krb5_free_principal(pam_context, princ); + PAM_LOG("Done cleanup2"); +cleanup3: + krb5_free_context(pam_context); + PAM_LOG("Done cleanup3"); + + seteuid(euid); + setegid(egid); + + PAM_LOG("Done seteuid() & setegid()"); + + if (cache_name_buf != NULL) + free(cache_name_buf); + + return (retval); +#endif +} + +/* + * account management + */ +PAM_EXTERN int +pam_sm_acct_mgmt(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + krb5_error_code krbret; + krb5_context pam_context; + krb5_ccache ccache; + krb5_principal princ; + int retval; + const void *user; + const void *ccache_name; + + retval = pam_get_item(pamh, PAM_USER, &user); + if (retval != PAM_SUCCESS) + return (retval); + + PAM_LOG("Got user: %s", (const char *)user); + + retval = pam_get_data(pamh, "ccache", &ccache_name); + if (retval != PAM_SUCCESS) + return (PAM_SUCCESS); + + PAM_LOG("Got credentials"); + + krbret = krb5_init_context(&pam_context); + if (krbret != 0) { + PAM_LOG("Error krb5_init_context() failed"); + return (PAM_PERM_DENIED); + } + + PAM_LOG("Context initialised"); + + krbret = krb5_cc_resolve(pam_context, (const char *)ccache_name, &ccache); + if (krbret != 0) { + PAM_LOG("Error krb5_cc_resolve(\"%s\"): %s", (const char *)ccache_name, + krb5_get_err_text(pam_context, krbret)); + krb5_free_context(pam_context); + return (PAM_PERM_DENIED); + } + + PAM_LOG("Got ccache %s", (const char *)ccache_name); + + + krbret = krb5_cc_get_principal(pam_context, ccache, &princ); + if (krbret != 0) { + PAM_LOG("Error krb5_cc_get_principal(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_PERM_DENIED;; + goto cleanup; + } + + PAM_LOG("Got principal"); + + if (krb5_kuserok(pam_context, princ, (const char *)user)) + retval = PAM_SUCCESS; + else + retval = PAM_PERM_DENIED; + krb5_free_principal(pam_context, princ); + + PAM_LOG("Done kuserok()"); + +cleanup: + krb5_free_context(pam_context); + PAM_LOG("Done cleanup"); + + return (retval); + +} + +/* + * password management + */ +PAM_EXTERN int +pam_sm_chauthtok(pam_handle_t *pamh, int flags, + int argc __unused, const char *argv[] __unused) +{ + krb5_error_code krbret; + krb5_context pam_context; + krb5_creds creds; + krb5_principal princ; + krb5_get_init_creds_opt opts; + krb5_data result_code_string, result_string; + int result_code, retval; + const char *pass; + const void *user; + char *princ_name, *passdup; + + if (!(flags & PAM_UPDATE_AUTHTOK)) + return (PAM_AUTHTOK_ERR); + + retval = pam_get_item(pamh, PAM_USER, &user); + if (retval != PAM_SUCCESS) + return (retval); + + PAM_LOG("Got user: %s", (const char *)user); + + krbret = krb5_init_context(&pam_context); + if (krbret != 0) { + PAM_LOG("Error krb5_init_context() failed"); + return (PAM_SERVICE_ERR); + } + + PAM_LOG("Context initialised"); + + krb5_get_init_creds_opt_init(&opts); + + PAM_LOG("Credentials options initialised"); + + /* Get principal name */ + krbret = krb5_parse_name(pam_context, (const char *)user, &princ); + if (krbret != 0) { + PAM_LOG("Error krb5_parse_name(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_USER_UNKNOWN; + goto cleanup3; + } + + /* Now convert the principal name into something human readable */ + princ_name = NULL; + krbret = krb5_unparse_name(pam_context, princ, &princ_name); + if (krbret != 0) { + PAM_LOG("Error krb5_unparse_name(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_SERVICE_ERR; + goto cleanup2; + } + + PAM_LOG("Got principal: %s", princ_name); + + /* Get password */ + retval = pam_get_authtok(pamh, PAM_OLDAUTHTOK, &pass, PASSWORD_PROMPT); + if (retval != PAM_SUCCESS) + goto cleanup2; + + PAM_LOG("Got password"); + + memset(&creds, 0, sizeof(krb5_creds)); + krbret = krb5_get_init_creds_password(pam_context, &creds, princ, + pass, NULL, pamh, 0, "kadmin/changepw", &opts); + if (krbret != 0) { + PAM_LOG("Error krb5_get_init_creds_password(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_AUTH_ERR; + goto cleanup2; + } + + PAM_LOG("Credentials established"); + + /* Now get the new password */ + for (;;) { + retval = pam_get_authtok(pamh, + PAM_AUTHTOK, &pass, NEW_PASSWORD_PROMPT); + if (retval != PAM_TRY_AGAIN) + break; + pam_error(pamh, "Mismatch; try again, EOF to quit."); + } + if (retval != PAM_SUCCESS) + goto cleanup; + + PAM_LOG("Got new password"); + + /* Change it */ + if ((passdup = strdup(pass)) == NULL) { + retval = PAM_BUF_ERR; + goto cleanup; + } + krbret = krb5_change_password(pam_context, &creds, passdup, + &result_code, &result_code_string, &result_string); + free(passdup); + if (krbret != 0) { + PAM_LOG("Error krb5_change_password(): %s", + krb5_get_err_text(pam_context, krbret)); + retval = PAM_AUTHTOK_ERR; + goto cleanup; + } + if (result_code) { + PAM_LOG("Error krb5_change_password(): (result_code)"); + retval = PAM_AUTHTOK_ERR; + goto cleanup; + } + + PAM_LOG("Password changed"); + + if (result_string.data) + free(result_string.data); + if (result_code_string.data) + free(result_code_string.data); + +cleanup: + krb5_free_cred_contents(pam_context, &creds); + PAM_LOG("Done cleanup"); +cleanup2: + krb5_free_principal(pam_context, princ); + PAM_LOG("Done cleanup2"); +cleanup3: + if (princ_name) + free(princ_name); + + krb5_free_context(pam_context); + + PAM_LOG("Done cleanup3"); + + return (retval); +} + +PAM_MODULE_ENTRY("pam_krb5"); + +/* + * This routine with some modification is from the MIT V5B6 appl/bsd/login.c + * Modified by Sam Hartman <hartmans@mit.edu> to support PAM services + * for Debian. + * + * Verify the Kerberos ticket-granting ticket just retrieved for the + * user. If the Kerberos server doesn't respond, assume the user is + * trying to fake us out (since we DID just get a TGT from what is + * supposedly our KDC). If the host/<host> service is unknown (i.e., + * the local keytab doesn't have it), and we cannot find another + * service we do have, let her in. + * + * Returns 1 for confirmation, -1 for failure, 0 for uncertainty. + */ +/* ARGSUSED */ +static int +verify_krb_v5_tgt(krb5_context context, krb5_ccache ccache, + char *pam_service, int debug) +{ + krb5_error_code retval; + krb5_principal princ; + krb5_keyblock *keyblock; + krb5_data packet; + krb5_auth_context auth_context; + char phost[BUFSIZ]; + const char *services[3], **service; + + packet.data = 0; + + /* If possible we want to try and verify the ticket we have + * received against a keytab. We will try multiple service + * principals, including at least the host principal and the PAM + * service principal. The host principal is preferred because access + * to that key is generally sufficient to compromise root, while the + * service key for this PAM service may be less carefully guarded. + * It is important to check the keytab first before the KDC so we do + * not get spoofed by a fake KDC. + */ + services[0] = "host"; + services[1] = pam_service; + services[2] = NULL; + keyblock = 0; + retval = -1; + for (service = &services[0]; *service != NULL; service++) { + retval = krb5_sname_to_principal(context, NULL, *service, + KRB5_NT_SRV_HST, &princ); + if (retval != 0) { + if (debug) + syslog(LOG_DEBUG, + "pam_krb5: verify_krb_v5_tgt(): %s: %s", + "krb5_sname_to_principal()", + krb5_get_err_text(context, retval)); + return -1; + } + + /* Extract the name directly. */ + strncpy(phost, compat_princ_component(context, princ, 1), + BUFSIZ); + phost[BUFSIZ - 1] = '\0'; + + /* + * Do we have service/<host> keys? + * (use default/configured keytab, kvno IGNORE_VNO to get the + * first match, and ignore enctype.) + */ + retval = krb5_kt_read_service_key(context, NULL, princ, 0, 0, + &keyblock); + if (retval != 0) + continue; + break; + } + if (retval != 0) { /* failed to find key */ + /* Keytab or service key does not exist */ + if (debug) + syslog(LOG_DEBUG, + "pam_krb5: verify_krb_v5_tgt(): %s: %s", + "krb5_kt_read_service_key()", + krb5_get_err_text(context, retval)); + retval = 0; + goto cleanup; + } + if (keyblock) + krb5_free_keyblock(context, keyblock); + + /* Talk to the kdc and construct the ticket. */ + auth_context = NULL; + retval = krb5_mk_req(context, &auth_context, 0, *service, phost, + NULL, ccache, &packet); + if (auth_context) { + krb5_auth_con_free(context, auth_context); + auth_context = NULL; /* setup for rd_req */ + } + if (retval) { + if (debug) + syslog(LOG_DEBUG, + "pam_krb5: verify_krb_v5_tgt(): %s: %s", + "krb5_mk_req()", + krb5_get_err_text(context, retval)); + retval = -1; + goto cleanup; + } + + /* Try to use the ticket. */ + retval = krb5_rd_req(context, &auth_context, &packet, princ, NULL, + NULL, NULL); + if (retval) { + if (debug) + syslog(LOG_DEBUG, + "pam_krb5: verify_krb_v5_tgt(): %s: %s", + "krb5_rd_req()", + krb5_get_err_text(context, retval)); + retval = -1; + } + else + retval = 1; + +cleanup: + if (packet.data) + compat_free_data_contents(context, &packet); + krb5_free_principal(context, princ); + return retval; +} + +/* Free the memory for cache_name. Called by pam_end() */ +/* ARGSUSED */ +static void +cleanup_cache(pam_handle_t *pamh __unused, void *data, int pam_end_status __unused) +{ + krb5_context pam_context; + krb5_ccache ccache; + krb5_error_code krbret; + + if (krb5_init_context(&pam_context)) + return; + + krbret = krb5_cc_resolve(pam_context, data, &ccache); + if (krbret == 0) + krb5_cc_destroy(pam_context, ccache); + krb5_free_context(pam_context); + free(data); +} + +#ifdef COMPAT_HEIMDAL +#ifdef COMPAT_MIT +#error This cannot be MIT and Heimdal compatible! +#endif +#endif + +#ifndef COMPAT_HEIMDAL +#ifndef COMPAT_MIT +#error One of COMPAT_MIT and COMPAT_HEIMDAL must be specified! +#endif +#endif + +#ifdef COMPAT_HEIMDAL +/* ARGSUSED */ +static const char * +compat_princ_component(krb5_context context __unused, krb5_principal princ, int n) +{ + return princ->name.name_string.val[n]; +} + +/* ARGSUSED */ +static void +compat_free_data_contents(krb5_context context __unused, krb5_data * data) +{ + krb5_xfree(data->data); +} +#endif + +#ifdef COMPAT_MIT +static const char * +compat_princ_component(krb5_context context, krb5_principal princ, int n) +{ + return krb5_princ_component(context, princ, n)->data; +} + +static void +compat_free_data_contents(krb5_context context, krb5_data * data) +{ + krb5_free_data_contents(context, data); +} +#endif diff --git a/lib/libpam/modules/pam_ksu/Makefile b/lib/libpam/modules/pam_ksu/Makefile new file mode 100644 index 0000000..1cb1999 --- /dev/null +++ b/lib/libpam/modules/pam_ksu/Makefile @@ -0,0 +1,34 @@ +# Copyright 2002 FreeBSD, Inc. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_ksu +SRCS= pam_ksu.c +MAN= pam_ksu.8 + +DPADD= ${LIBKRB5} ${LIBASN1} ${LIBROKEN} ${LIBCOM_ERR} ${LIBCRYPT} ${LIBCRYPTO} +LDADD= -lkrb5 -lasn1 -lroken -lcom_err -lcrypt -lcrypto + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_ksu/pam_ksu.8 b/lib/libpam/modules/pam_ksu/pam_ksu.8 new file mode 100644 index 0000000..614dc9e --- /dev/null +++ b/lib/libpam/modules/pam_ksu/pam_ksu.8 @@ -0,0 +1,122 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2001 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" This software was developed for the FreeBSD Project by ThinkSec AS and +.\" NAI Labs, the Security Research Division of Network Associates, Inc. +.\" under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the +.\" DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd May 15, 2002 +.Dt PAM_KSU 8 +.Os +.Sh NAME +.Nm pam_ksu +.Nd Kerberos 5 SU PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_ksu +.Op Ar options +.Sh DESCRIPTION +The Kerberos 5 SU authentication service module for PAM, +.Nm +for only one PAM category: authentication. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li auth +feature. +The module is specifically designed to be used with the +.Xr su 1 +utility. +.\" It also provides a null function for session management. +.Ss Kerberos 5 SU Authentication Module +The Kerberos 5 SU authentication component provides functions to verify +the identity of a user +.Pq Fn pam_sm_authenticate , +and determine whether or not the user is authorized to obtain the +privileges of the target account. +If the target account is +.Dq root , +then the Kerberos 5 principal used +for authentication and authorization will be the +.Dq root +instance of +the current user, e.g.\& +.Dq Li user/root@REAL.M . +Otherwise, the principal will simply be the current user's default +principal, e.g.\& +.Dq Li user@REAL.M . +.Pp +The user is prompted for a password if necessary. +Authorization is performed +by comparing the Kerberos 5 principal with those listed in the +.Pa .k5login +file in the target account's home directory +(e.g.\& +.Pa /root/.k5login +for root). +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm use_first_pass" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm use_first_pass +If the authentication module +is not the first in the stack, +and a previous module +obtained the user's password, +that password is used +to authenticate the user. +If this fails, +the authentication module returns failure +without prompting the user for a password. +This option has no effect +if the authentication module +is the first in the stack, +or if no previous modules +obtained the user's password. +.It Cm try_first_pass +This option is similar to the +.Cm use_first_pass +option, +except that if the previously obtained password fails, +the user is prompted for another password. +.El +.Sh SEE ALSO +.Xr su 1 , +.Xr syslog 3 , +.Xr pam.conf 5 , +.Xr pam 8 diff --git a/lib/libpam/modules/pam_ksu/pam_ksu.c b/lib/libpam/modules/pam_ksu/pam_ksu.c new file mode 100644 index 0000000..80a395a --- /dev/null +++ b/lib/libpam/modules/pam_ksu/pam_ksu.c @@ -0,0 +1,256 @@ +/*- + * Copyright (c) 2002 Jacques A. Vidrine <nectar@FreeBSD.org> + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/param.h> +#include <errno.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +#include <krb5.h> + +#define PAM_SM_AUTH +#define PAM_SM_CRED +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +static const char superuser[] = "root"; + +static long get_su_principal(krb5_context, const char *, const char *, + char **, krb5_principal *); +static int auth_krb5(pam_handle_t *, krb5_context, const char *, + krb5_principal); + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + krb5_context context; + krb5_principal su_principal; + const char *user; + const void *ruser; + char *su_principal_name; + long rv; + int pamret; + + pamret = pam_get_user(pamh, &user, NULL); + if (pamret != PAM_SUCCESS) + return (pamret); + PAM_LOG("Got user: %s", user); + pamret = pam_get_item(pamh, PAM_RUSER, &ruser); + if (pamret != PAM_SUCCESS) + return (pamret); + PAM_LOG("Got ruser: %s", (const char *)ruser); + rv = krb5_init_context(&context); + if (rv != 0) { + PAM_LOG("krb5_init_context failed: %s", + krb5_get_err_text(context, rv)); + return (PAM_SERVICE_ERR); + } + rv = get_su_principal(context, user, ruser, &su_principal_name, &su_principal); + if (rv != 0) + return (PAM_AUTH_ERR); + PAM_LOG("kuserok: %s -> %s", su_principal_name, user); + rv = krb5_kuserok(context, su_principal, user); + pamret = rv ? auth_krb5(pamh, context, su_principal_name, su_principal) : PAM_AUTH_ERR; + free(su_principal_name); + krb5_free_principal(context, su_principal); + krb5_free_context(context); + return (pamret); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int ac __unused, const char *av[] __unused) +{ + + return (PAM_SUCCESS); +} + +/* Authenticate using Kerberos 5. + * pamh -- The PAM handle. + * context -- An initialized krb5_context. + * su_principal_name -- The target principal name, used only for password prompts. + * If NULL, the password prompts will not include a principal + * name. + * su_principal -- The target krb5_principal. + * Note that a valid keytab in the default location with a host entry + * must be available, and that the PAM application must have sufficient + * privileges to access it. + * Returns PAM_SUCCESS if authentication was successful, or an appropriate + * PAM error code if it was not. + */ +static int +auth_krb5(pam_handle_t *pamh, krb5_context context, const char *su_principal_name, + krb5_principal su_principal) +{ + krb5_creds creds; + krb5_get_init_creds_opt gic_opt; + krb5_verify_init_creds_opt vic_opt; + const char *pass; + char *prompt; + long rv; + int pamret; + + prompt = NULL; + krb5_get_init_creds_opt_init(&gic_opt); + krb5_verify_init_creds_opt_init(&vic_opt); + if (su_principal_name != NULL) + (void)asprintf(&prompt, "Password for %s:", su_principal_name); + else + (void)asprintf(&prompt, "Password:"); + if (prompt == NULL) + return (PAM_BUF_ERR); + pass = NULL; + pamret = pam_get_authtok(pamh, PAM_AUTHTOK, &pass, prompt); + free(prompt); + if (pamret != PAM_SUCCESS) + return (pamret); + rv = krb5_get_init_creds_password(context, &creds, su_principal, + pass, NULL, NULL, 0, NULL, &gic_opt); + if (rv != 0) { + PAM_LOG("krb5_get_init_creds_password: %s", + krb5_get_err_text(context, rv)); + return (PAM_AUTH_ERR); + } + krb5_verify_init_creds_opt_set_ap_req_nofail(&vic_opt, 1); + rv = krb5_verify_init_creds(context, &creds, NULL, NULL, NULL, + &vic_opt); + krb5_free_cred_contents(context, &creds); + if (rv != 0) { + PAM_LOG("krb5_verify_init_creds: %s", + krb5_get_err_text(context, rv)); + return (PAM_AUTH_ERR); + } + return (PAM_SUCCESS); +} + +/* Determine the target principal given the current user and the target user. + * context -- An initialized krb5_context. + * target_user -- The target username. + * current_user -- The current username. + * su_principal_name -- (out) The target principal name. + * su_principal -- (out) The target krb5_principal. + * When the target user is `root', the target principal will be a `root + * instance', e.g. `luser/root@REA.LM'. Otherwise, the target principal + * will simply be the current user's default principal name. Note that + * in any case, if KRB5CCNAME is set and a credentials cache exists, the + * principal name found there will be the `starting point', rather than + * the ruser parameter. + * + * Returns 0 for success, or a com_err error code on failure. + */ +static long +get_su_principal(krb5_context context, const char *target_user, const char *current_user, + char **su_principal_name, krb5_principal *su_principal) +{ + krb5_principal default_principal; + krb5_ccache ccache; + char *principal_name, *ccname, *p; + long rv; + uid_t euid, ruid; + + *su_principal = NULL; + default_principal = NULL; + /* Unless KRB5CCNAME was explicitly set, we won't really be able + * to look at the credentials cache since krb5_cc_default will + * look at getuid(). + */ + ruid = getuid(); + euid = geteuid(); + rv = seteuid(ruid); + if (rv != 0) + return (errno); + p = getenv("KRB5CCNAME"); + if (p != NULL) + ccname = strdup(p); + else + (void)asprintf(&ccname, "%s%lu", KRB5_DEFAULT_CCROOT, (unsigned long)ruid); + if (ccname == NULL) + return (errno); + rv = krb5_cc_resolve(context, ccname, &ccache); + free(ccname); + if (rv == 0) { + rv = krb5_cc_get_principal(context, ccache, &default_principal); + krb5_cc_close(context, ccache); + if (rv != 0) + default_principal = NULL; /* just to be safe */ + } + rv = seteuid(euid); + if (rv != 0) + return (errno); + if (default_principal == NULL) { + rv = krb5_make_principal(context, &default_principal, NULL, current_user, NULL); + if (rv != 0) { + PAM_LOG("Could not determine default principal name."); + return (rv); + } + } + /* Now that we have some principal, if the target account is + * `root', then transform it into a `root' instance, e.g. + * `user@REA.LM' -> `user/root@REA.LM'. + */ + rv = krb5_unparse_name(context, default_principal, &principal_name); + krb5_free_principal(context, default_principal); + if (rv != 0) { + PAM_LOG("krb5_unparse_name: %s", + krb5_get_err_text(context, rv)); + return (rv); + } + PAM_LOG("Default principal name: %s", principal_name); + if (strcmp(target_user, superuser) == 0) { + p = strrchr(principal_name, '@'); + if (p == NULL) { + PAM_LOG("malformed principal name `%s'", principal_name); + free(principal_name); + return (rv); + } + *p++ = '\0'; + *su_principal_name = NULL; + (void)asprintf(su_principal_name, "%s/%s@%s", principal_name, superuser, p); + free(principal_name); + } else + *su_principal_name = principal_name; + + if (*su_principal_name == NULL) + return (errno); + rv = krb5_parse_name(context, *su_principal_name, &default_principal); + if (rv != 0) { + PAM_LOG("krb5_parse_name `%s': %s", *su_principal_name, + krb5_get_err_text(context, rv)); + free(*su_principal_name); + return (rv); + } + PAM_LOG("Target principal name: %s", *su_principal_name); + *su_principal = default_principal; + return (0); +} + +PAM_MODULE_ENTRY("pam_ksu"); diff --git a/lib/libpam/modules/pam_lastlog/Makefile b/lib/libpam/modules/pam_lastlog/Makefile new file mode 100644 index 0000000..f0b96c4 --- /dev/null +++ b/lib/libpam/modules/pam_lastlog/Makefile @@ -0,0 +1,34 @@ +# Copyright 2001 Mark R V Murray +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_lastlog +SRCS= pam_lastlog.c +MAN= pam_lastlog.8 + +DPADD= ${LIBUTIL} +LDADD= -lutil + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_lastlog/pam_lastlog.8 b/lib/libpam/modules/pam_lastlog/pam_lastlog.8 new file mode 100644 index 0000000..9fc7e45 --- /dev/null +++ b/lib/libpam/modules/pam_lastlog/pam_lastlog.8 @@ -0,0 +1,106 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2001 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd January 24, 2002 +.Dt PAM_LASTLOG 8 +.Os +.Sh NAME +.Nm pam_lastlog +.Nd login accounting PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_lastlog +.Op Ar options +.Sh DESCRIPTION +The login accounting service module for PAM, +.Nm +provides functionality for only one PAM category: +session management. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li session +feature. +.Ss Login Accounting Session Management Module +The login accounting session management component provides functions +to initiate +.Pq Fn pam_sm_open_session +and terminate +.Pq Fn pam_sm_close_session +sessions. +The +.Fn pam_sm_open_session +function records the session in the +.Xr utmp 5 , +.Xr wtmp 5 +and +.Xr lastlog 5 +databases. +The +.Fn pam_sm_close_session +function does nothing. +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm no_warn" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +.It Cm no_fail +Ignore I/O failures. +.El +.Sh SEE ALSO +.Xr last 1 , +.Xr w 1 , +.Xr login 3 , +.Xr logout 3 , +.Xr pam.conf 5 , +.Xr utmp 5 , +.Xr lastlogin 8 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module and this manual page were developed for the FreeBSD Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_lastlog/pam_lastlog.c b/lib/libpam/modules/pam_lastlog/pam_lastlog.c new file mode 100644 index 0000000..817d1f3 --- /dev/null +++ b/lib/libpam/modules/pam_lastlog/pam_lastlog.c @@ -0,0 +1,202 @@ +/*- + * Copyright (c) 1980, 1987, 1988, 1991, 1993, 1994 + * The Regents of the University of California. All rights reserved. + * Copyright (c) 2001 Mark R V Murray + * All rights reserved. + * Copyright (c) 2001 Networks Associates Technology, Inc. + * All rights reserved. + * Copyright (c) 2004 Joe R. Doupnik + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * 4. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#define _BSD_SOURCE + +#include <sys/param.h> + +#include <fcntl.h> +#include <libutil.h> +#include <paths.h> +#include <pwd.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <syslog.h> +#include <time.h> +#include <unistd.h> +#include <utmp.h> + +#define PAM_SM_SESSION + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +PAM_EXTERN int +pam_sm_open_session(pam_handle_t *pamh, int flags, + int argc __unused, const char *argv[] __unused) +{ + struct passwd *pwd; + struct utmp utmp; + struct lastlog ll; + time_t t; + const char *user; + const void *rhost, *tty; + off_t llpos; + int fd, pam_err; + + pam_err = pam_get_user(pamh, &user, NULL); + if (pam_err != PAM_SUCCESS) + return (pam_err); + if (user == NULL || (pwd = getpwnam(user)) == NULL) + return (PAM_SERVICE_ERR); + PAM_LOG("Got user: %s", user); + + pam_err = pam_get_item(pamh, PAM_RHOST, &rhost); + if (pam_err != PAM_SUCCESS) { + PAM_LOG("No PAM_RHOST"); + goto err; + } + pam_err = pam_get_item(pamh, PAM_TTY, &tty); + if (pam_err != PAM_SUCCESS) { + PAM_LOG("No PAM_TTY"); + goto err; + } + if (tty == NULL) { + PAM_LOG("No PAM_TTY"); + pam_err = PAM_SERVICE_ERR; + goto err; + } + if (strncmp(tty, _PATH_DEV, strlen(_PATH_DEV)) == 0) + tty = (const char *)tty + strlen(_PATH_DEV); + if (*(const char *)tty == '\0') + return (PAM_SERVICE_ERR); + + fd = open(_PATH_LASTLOG, O_RDWR|O_CREAT, 0644); + if (fd == -1) { + PAM_LOG("Failed to open %s", _PATH_LASTLOG); + goto file_err; + } + + /* + * Record session in lastlog(5). + */ + llpos = (off_t)(pwd->pw_uid * sizeof(ll)); + if (lseek(fd, llpos, L_SET) != llpos) + goto file_err; + if ((flags & PAM_SILENT) == 0) { + if (read(fd, &ll, sizeof ll) == sizeof ll && ll.ll_time != 0) { + t = ll.ll_time; + if (*ll.ll_host != '\0') + pam_info(pamh, "Last login: %.*s from %.*s", + 24 - 5, ctime(&t), + (int)sizeof(ll.ll_host), ll.ll_host); + else + pam_info(pamh, "Last login: %.*s on %.*s", + 24 - 5, ctime(&t), + (int)sizeof(ll.ll_line), ll.ll_line); + } + if (lseek(fd, llpos, L_SET) != llpos) + goto file_err; + } + + bzero(&ll, sizeof(ll)); + ll.ll_time = time(NULL); + + /* note: does not need to be NUL-terminated */ + strncpy(ll.ll_line, tty, sizeof(ll.ll_line)); + if (rhost != NULL && *(const char *)rhost != '\0') + /* note: does not need to be NUL-terminated */ + strncpy(ll.ll_host, rhost, sizeof(ll.ll_host)); + + if (write(fd, (char *)&ll, sizeof(ll)) != sizeof(ll) || close(fd) != 0) + goto file_err; + + PAM_LOG("Login recorded in %s", _PATH_LASTLOG); + + /* + * Record session in utmp(5) and wtmp(5). + */ + bzero(&utmp, sizeof(utmp)); + utmp.ut_time = time(NULL); + /* note: does not need to be NUL-terminated */ + strncpy(utmp.ut_name, user, sizeof(utmp.ut_name)); + if (rhost != NULL && *(const char *)rhost != '\0') + strncpy(utmp.ut_host, rhost, sizeof(utmp.ut_host)); + (void)strncpy(utmp.ut_line, tty, sizeof(utmp.ut_line)); + login(&utmp); + + return (PAM_SUCCESS); + +file_err: + syslog(LOG_ERR, "%s: %m", _PATH_LASTLOG); + if (fd != -1) + close(fd); + pam_err = PAM_SYSTEM_ERR; +err: + if (openpam_get_option(pamh, "no_fail")) + return (PAM_SUCCESS); + return (pam_err); +} + +PAM_EXTERN int +pam_sm_close_session(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + const void *tty; + int pam_err; + + pam_err = pam_get_item(pamh, PAM_TTY, (const void **)&tty); + if (pam_err != PAM_SUCCESS) + goto err; + if (strncmp(tty, _PATH_DEV, strlen(_PATH_DEV)) == 0) + tty = (const char *)tty + strlen(_PATH_DEV); + if (*(const char *)tty == '\0') + return (PAM_SERVICE_ERR); + if (logout(tty) != 1) + syslog(LOG_ERR, "%s(): no utmp record for %s", + __func__, (const char *)tty); + logwtmp(tty, "", ""); + return (PAM_SUCCESS); + + err: + if (openpam_get_option(pamh, "no_fail")) + return (PAM_SUCCESS); + return (pam_err); +} + +PAM_MODULE_ENTRY("pam_lastlog"); diff --git a/lib/libpam/modules/pam_login_access/Makefile b/lib/libpam/modules/pam_login_access/Makefile new file mode 100644 index 0000000..5679a62 --- /dev/null +++ b/lib/libpam/modules/pam_login_access/Makefile @@ -0,0 +1,31 @@ +# Copyright 2001 Mark R V Murray +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_login_access +SRCS= pam_login_access.c login_access.c +MAN= login.access.5 pam_login_access.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_login_access/login.access.5 b/lib/libpam/modules/pam_login_access/login.access.5 new file mode 100644 index 0000000..034d8b7 --- /dev/null +++ b/lib/libpam/modules/pam_login_access/login.access.5 @@ -0,0 +1,57 @@ +.\" +.\" $FreeBSD$ +.\" +.Dd September 13, 2006 +.Dt LOGIN.ACCESS 5 +.Os +.Sh NAME +.Nm login.access +.Nd login access control table +.Sh DESCRIPTION +The +.Nm +file specifies (user, host) combinations and/or (user, tty) +combinations for which a login will be either accepted or refused. +.Pp +When someone logs in, the +.Nm +is scanned for the first entry that +matches the (user, host) combination, or, in case of non-networked +logins, the first entry that matches the (user, tty) combination. +The +permissions field of that table entry determines whether the login will +be accepted or refused. +.Pp +Each line of the login access control table has three fields separated by a +.Ql \&: +character: +.Ar permission : Ns Ar users : Ns Ar origins +.Pp +The first field should be a "+" (access granted) or "-" (access denied) +character. +The second field should be a list of one or more login names, +group names, or ALL (always matches). +The third field should be a list +of one or more tty names (for non-networked logins), host names, domain +names (begin with "."), host addresses, internet network numbers (end +with "."), ALL (always matches) or LOCAL (matches any string that does +not contain a "." character). +If you run NIS you can use @netgroupname +in host or user patterns. +.Pp +The EXCEPT operator makes it possible to write very compact rules. +.Pp +The group file is searched only when a name does not match that of the +logged-in user. +Only groups are matched in which users are explicitly +listed: the program does not look at a user's primary group id value. +.Sh FILES +.Bl -tag -width /etc/login.access -compact +.It Pa /etc/login.access +login access control table +.El +.Sh SEE ALSO +.Xr login 1 , +.Xr pam_login_access 8 +.Sh AUTHORS +.An Guido van Rooij diff --git a/lib/libpam/modules/pam_login_access/login_access.c b/lib/libpam/modules/pam_login_access/login_access.c new file mode 100644 index 0000000..dacb9d7 --- /dev/null +++ b/lib/libpam/modules/pam_login_access/login_access.c @@ -0,0 +1,249 @@ + /* + * This module implements a simple but effective form of login access + * control based on login names and on host (or domain) names, internet + * addresses (or network numbers), or on terminal line names in case of + * non-networked logins. Diagnostics are reported through syslog(3). + * + * Author: Wietse Venema, Eindhoven University of Technology, The Netherlands. + */ + +#if 0 +#ifndef lint +static char sccsid[] = "%Z% %M% %I% %E% %U%"; +#endif +#endif + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/types.h> +#include <ctype.h> +#include <errno.h> +#include <grp.h> +#include <netdb.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <syslog.h> +#include <unistd.h> + +#include "pam_login_access.h" + +#define _PATH_LOGACCESS "/etc/login.access" + + /* Delimiters for fields and for lists of users, ttys or hosts. */ + +static char fs[] = ":"; /* field separator */ +static char sep[] = ", \t"; /* list-element separator */ + + /* Constants to be used in assignments only, not in comparisons... */ + +#define YES 1 +#define NO 0 + +static int from_match(const char *, const char *); +static int list_match(char *, const char *, + int (*)(const char *, const char *)); +static int netgroup_match(const char *, const char *, const char *); +static int string_match(const char *, const char *); +static int user_match(const char *, const char *); + +/* login_access - match username/group and host/tty with access control file */ + +int +login_access(const char *user, const char *from) +{ + FILE *fp; + char line[BUFSIZ]; + char *perm; /* becomes permission field */ + char *users; /* becomes list of login names */ + char *froms; /* becomes list of terminals or hosts */ + int match = NO; + int end; + int lineno = 0; /* for diagnostics */ + + /* + * Process the table one line at a time and stop at the first match. + * Blank lines and lines that begin with a '#' character are ignored. + * Non-comment lines are broken at the ':' character. All fields are + * mandatory. The first field should be a "+" or "-" character. A + * non-existing table means no access control. + */ + + if ((fp = fopen(_PATH_LOGACCESS, "r")) != NULL) { + while (!match && fgets(line, sizeof(line), fp)) { + lineno++; + if (line[end = strlen(line) - 1] != '\n') { + syslog(LOG_ERR, "%s: line %d: missing newline or line too long", + _PATH_LOGACCESS, lineno); + continue; + } + if (line[0] == '#') + continue; /* comment line */ + while (end > 0 && isspace(line[end - 1])) + end--; + line[end] = 0; /* strip trailing whitespace */ + if (line[0] == 0) /* skip blank lines */ + continue; + if (!(perm = strtok(line, fs)) + || !(users = strtok((char *) 0, fs)) + || !(froms = strtok((char *) 0, fs)) + || strtok((char *) 0, fs)) { + syslog(LOG_ERR, "%s: line %d: bad field count", _PATH_LOGACCESS, + lineno); + continue; + } + if (perm[0] != '+' && perm[0] != '-') { + syslog(LOG_ERR, "%s: line %d: bad first field", _PATH_LOGACCESS, + lineno); + continue; + } + match = (list_match(froms, from, from_match) + && list_match(users, user, user_match)); + } + (void) fclose(fp); + } else if (errno != ENOENT) { + syslog(LOG_ERR, "cannot open %s: %m", _PATH_LOGACCESS); + } + return (match == 0 || (line[0] == '+')); +} + +/* list_match - match an item against a list of tokens with exceptions */ + +static int +list_match(char *list, const char *item, + int (*match_fn)(const char *, const char *)) +{ + char *tok; + int match = NO; + + /* + * Process tokens one at a time. We have exhausted all possible matches + * when we reach an "EXCEPT" token or the end of the list. If we do find + * a match, look for an "EXCEPT" list and recurse to determine whether + * the match is affected by any exceptions. + */ + + for (tok = strtok(list, sep); tok != 0; tok = strtok((char *) 0, sep)) { + if (strcasecmp(tok, "EXCEPT") == 0) /* EXCEPT: give up */ + break; + if ((match = (*match_fn)(tok, item)) != 0) /* YES */ + break; + } + /* Process exceptions to matches. */ + + if (match != NO) { + while ((tok = strtok((char *) 0, sep)) && strcasecmp(tok, "EXCEPT")) + /* VOID */ ; + if (tok == 0 || list_match((char *) 0, item, match_fn) == NO) + return (match); + } + return (NO); +} + +/* netgroup_match - match group against machine or user */ + +static int +netgroup_match(const char *group, const char *machine, const char *user) +{ + char domain[1024]; + unsigned int i; + + if (getdomainname(domain, sizeof(domain)) != 0 || *domain == '\0') { + syslog(LOG_ERR, "NIS netgroup support disabled: no NIS domain"); + return (NO); + } + + /* getdomainname() does not reliably terminate the string */ + for (i = 0; i < sizeof(domain); ++i) + if (domain[i] == '\0') + break; + if (i == sizeof(domain)) { + syslog(LOG_ERR, "NIS netgroup support disabled: invalid NIS domain"); + return (NO); + } + + if (innetgr(group, machine, user, domain) == 1) + return (YES); + return (NO); +} + +/* user_match - match a username against one token */ + +static int +user_match(const char *tok, const char *string) +{ + struct group *group; + int i; + + /* + * If a token has the magic value "ALL" the match always succeeds. + * Otherwise, return YES if the token fully matches the username, or if + * the token is a group that contains the username. + */ + + if (tok[0] == '@') { /* netgroup */ + return (netgroup_match(tok + 1, (char *) 0, string)); + } else if (string_match(tok, string)) { /* ALL or exact match */ + return (YES); + } else if ((group = getgrnam(tok)) != NULL) {/* try group membership */ + for (i = 0; group->gr_mem[i]; i++) + if (strcasecmp(string, group->gr_mem[i]) == 0) + return (YES); + } + return (NO); +} + +/* from_match - match a host or tty against a list of tokens */ + +static int +from_match(const char *tok, const char *string) +{ + int tok_len; + int str_len; + + /* + * If a token has the magic value "ALL" the match always succeeds. Return + * YES if the token fully matches the string. If the token is a domain + * name, return YES if it matches the last fields of the string. If the + * token has the magic value "LOCAL", return YES if the string does not + * contain a "." character. If the token is a network number, return YES + * if it matches the head of the string. + */ + + if (tok[0] == '@') { /* netgroup */ + return (netgroup_match(tok + 1, string, (char *) 0)); + } else if (string_match(tok, string)) { /* ALL or exact match */ + return (YES); + } else if (tok[0] == '.') { /* domain: match last fields */ + if ((str_len = strlen(string)) > (tok_len = strlen(tok)) + && strcasecmp(tok, string + str_len - tok_len) == 0) + return (YES); + } else if (strcasecmp(tok, "LOCAL") == 0) { /* local: no dots */ + if (strchr(string, '.') == 0) + return (YES); + } else if (tok[(tok_len = strlen(tok)) - 1] == '.' /* network */ + && strncmp(tok, string, tok_len) == 0) { + return (YES); + } + return (NO); +} + +/* string_match - match a string against one token */ + +static int +string_match(const char *tok, const char *string) +{ + + /* + * If the token has the magic value "ALL" the match always succeeds. + * Otherwise, return YES if the token fully matches the string. + */ + + if (strcasecmp(tok, "ALL") == 0) { /* all: always matches */ + return (YES); + } else if (strcasecmp(tok, string) == 0) { /* try exact match */ + return (YES); + } + return (NO); +} diff --git a/lib/libpam/modules/pam_login_access/pam_login_access.8 b/lib/libpam/modules/pam_login_access/pam_login_access.8 new file mode 100644 index 0000000..02f0d2d --- /dev/null +++ b/lib/libpam/modules/pam_login_access/pam_login_access.8 @@ -0,0 +1,89 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2001 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd January 24, 2002 +.Dt PAM_LOGIN_ACCESS 8 +.Os +.Sh NAME +.Nm pam_login_access +.Nd login.access PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_login_access +.Op Ar options +.Sh DESCRIPTION +The +.Pa login.access +service module for PAM, +.Nm +provides functionality for only one PAM category: +account management. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li account +feature. +.Ss Login.access Account Management Module +The +.Pa login.access +account management component +.Pq Fn pam_sm_acct_mgmt , +returns success if and only the user is allowed to log in on the +specified tty (in the case of a local login) or from the specified +remote host (in the case of a remote login), according to the +restrictions listed in +.Xr login.access 5 . +.Sh SEE ALSO +.Xr login.access 5 , +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Xr login.access 5 +access control scheme was designed and implemented by +.An Wietse Venema . +.Pp +The +.Nm +module and this manual page were developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_login_access/pam_login_access.c b/lib/libpam/modules/pam_login_access/pam_login_access.c new file mode 100644 index 0000000..945d5eb --- /dev/null +++ b/lib/libpam/modules/pam_login_access/pam_login_access.c @@ -0,0 +1,101 @@ +/*- + * Copyright (c) 2001 Mark R V Murray + * All rights reserved. + * Copyright (c) 2001 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#define _BSD_SOURCE + +#include <sys/param.h> + +#include <syslog.h> +#include <unistd.h> + +#define PAM_SM_ACCOUNT + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +#include "pam_login_access.h" + +PAM_EXTERN int +pam_sm_acct_mgmt(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + const void *rhost, *tty, *user; + char hostname[MAXHOSTNAMELEN]; + int pam_err; + + pam_err = pam_get_item(pamh, PAM_USER, &user); + if (pam_err != PAM_SUCCESS) + return (pam_err); + + if (user == NULL) + return (PAM_SERVICE_ERR); + + PAM_LOG("Got user: %s", (const char *)user); + + pam_err = pam_get_item(pamh, PAM_RHOST, &rhost); + if (pam_err != PAM_SUCCESS) + return (pam_err); + + pam_err = pam_get_item(pamh, PAM_TTY, &tty); + if (pam_err != PAM_SUCCESS) + return (pam_err); + + gethostname(hostname, sizeof hostname); + + if (rhost == NULL || *(const char *)rhost == '\0') { + PAM_LOG("Checking login.access for user %s on tty %s", + (const char *)user, (const char *)tty); + if (login_access(user, tty) != 0) + return (PAM_SUCCESS); + PAM_VERBOSE_ERROR("%s is not allowed to log in on %s", + user, tty); + } else { + PAM_LOG("Checking login.access for user %s from host %s", + (const char *)user, (const char *)rhost); + if (login_access(user, rhost) != 0) + return (PAM_SUCCESS); + PAM_VERBOSE_ERROR("%s is not allowed to log in from %s", + user, rhost); + } + + return (PAM_AUTH_ERR); +} + +PAM_MODULE_ENTRY("pam_login_access"); diff --git a/lib/libpam/modules/pam_login_access/pam_login_access.h b/lib/libpam/modules/pam_login_access/pam_login_access.h new file mode 100644 index 0000000..38c3049 --- /dev/null +++ b/lib/libpam/modules/pam_login_access/pam_login_access.h @@ -0,0 +1,39 @@ +/*- + * Copyright (c) 2001 Mark R V Murray + * All rights reserved. + * Copyright (c) 2001 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * $FreeBSD$ + */ + +extern int login_access(const char *, const char *); diff --git a/lib/libpam/modules/pam_nologin/Makefile b/lib/libpam/modules/pam_nologin/Makefile new file mode 100644 index 0000000..ba5a7d4 --- /dev/null +++ b/lib/libpam/modules/pam_nologin/Makefile @@ -0,0 +1,34 @@ +# Copyright 2001 Mark R V Murray +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_nologin +SRCS= pam_nologin.c +MAN= pam_nologin.8 + +DPADD= ${LIBUTIL} +LDADD= -lutil + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_nologin/pam_nologin.8 b/lib/libpam/modules/pam_nologin/pam_nologin.8 new file mode 100644 index 0000000..9448bf2 --- /dev/null +++ b/lib/libpam/modules/pam_nologin/pam_nologin.8 @@ -0,0 +1,90 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd June 10, 2007 +.Dt PAM_NOLOGIN 8 +.Os +.Sh NAME +.Nm pam_nologin +.Nd NoLogin PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_nologin +.Op Ar options +.Sh DESCRIPTION +The NoLogin service module for PAM, +.Nm +provides functionality for only one PAM category: +account management. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li account +feature. +.Ss NoLogin Account Management Module +The NoLogin account management component, +.Fn pam_sm_acct_mgmt , +verifies whether logins are administratively disabled via +.Xr nologin 5 . +It returns success if the user's login class has an "ignorenologin" +capability specified in +.Xr login.conf 5 +or the +.Xr nologin 5 +file does not exist. +If neither condition is met, +then the contents of +.Xr nologin 5 +are echoed +before failure is returned. +The location of +.Xr nologin 5 +is specified by a "nologin" capability in +.Xr login.conf 5 , +which defaults to +.Pa /var/run/nologin . +.Pp +The following options may be passed to the module: +.Bl -tag -width ".Cm no_warn" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +These messages include +reasons why the user's +login attempt was declined. +.El +.Sh SEE ALSO +.Xr syslog 3 , +.Xr login.conf 5 , +.Xr nologin 5 , +.Xr pam.conf 5 , +.Xr pam 8 diff --git a/lib/libpam/modules/pam_nologin/pam_nologin.c b/lib/libpam/modules/pam_nologin/pam_nologin.c new file mode 100644 index 0000000..1be63d2 --- /dev/null +++ b/lib/libpam/modules/pam_nologin/pam_nologin.c @@ -0,0 +1,127 @@ +/*- + * Copyright 2001 Mark R V Murray + * All rights reserved. + * Copyright (c) 2001 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/types.h> +#include <sys/stat.h> +#include <fcntl.h> +#include <login_cap.h> +#include <pwd.h> +#include <stdio.h> +#include <stdlib.h> +#include <unistd.h> + +#define PAM_SM_ACCOUNT + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +#define _PATH_NOLOGIN "/var/run/nologin" + +static char nologin_def[] = _PATH_NOLOGIN; + +PAM_EXTERN int +pam_sm_acct_mgmt(pam_handle_t *pamh, int flags, + int argc __unused, const char *argv[] __unused) +{ + login_cap_t *lc; + struct passwd *pwd; + struct stat st; + int retval, fd; + ssize_t ss; + const char *user, *nologin; + char *mtmp; + + retval = pam_get_user(pamh, &user, NULL); + if (retval != PAM_SUCCESS) + return (retval); + + PAM_LOG("Got user: %s", user); + + pwd = getpwnam(user); + if (pwd == NULL) + return (PAM_USER_UNKNOWN); + + /* + * login_getpwclass(3) will select the "root" class by default + * if pwd->pw_uid is 0. That class should have "ignorenologin" + * capability so that super-user can bypass nologin. + */ + lc = login_getpwclass(pwd); + if (lc == NULL) { + PAM_LOG("Unable to get login class for user %s", user); + return (PAM_SERVICE_ERR); + } + + if (login_getcapbool(lc, "ignorenologin", 0)) { + login_close(lc); + return (PAM_SUCCESS); + } + + nologin = login_getcapstr(lc, "nologin", nologin_def, nologin_def); + + fd = open(nologin, O_RDONLY, 0); + if (fd < 0) { + login_close(lc); + return (PAM_SUCCESS); + } + + PAM_LOG("Opened %s file", nologin); + + if (fstat(fd, &st) == 0) { + mtmp = malloc(st.st_size + 1); + if (mtmp != NULL) { + ss = read(fd, mtmp, st.st_size); + if (ss > 0) { + mtmp[ss] = '\0'; + pam_error(pamh, "%s", mtmp); + } + free(mtmp); + } + } + + PAM_VERBOSE_ERROR("Administrator refusing you: %s", nologin); + + close(fd); + login_close(lc); + + return (PAM_AUTH_ERR); +} + +PAM_MODULE_ENTRY("pam_nologin"); diff --git a/lib/libpam/modules/pam_opie/Makefile b/lib/libpam/modules/pam_opie/Makefile new file mode 100644 index 0000000..fbc1278 --- /dev/null +++ b/lib/libpam/modules/pam_opie/Makefile @@ -0,0 +1,35 @@ +# Copyright 2000 James Bloom +# All rights reserved. +# Based upon code Copyright 1998 Juniper Networks, Inc. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_opie +SRCS= pam_opie.c +MAN= pam_opie.8 + +DPADD= ${LIBOPIE} +LDADD= -lopie + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_opie/pam_opie.8 b/lib/libpam/modules/pam_opie/pam_opie.8 new file mode 100644 index 0000000..968985a --- /dev/null +++ b/lib/libpam/modules/pam_opie/pam_opie.8 @@ -0,0 +1,123 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2002 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd July 7, 2001 +.Dt PAM_OPIE 8 +.Os +.Sh NAME +.Nm pam_opie +.Nd OPIE PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_opie +.Op Ar options +.Sh DESCRIPTION +The OPIE authentication service module for PAM, +.Nm +provides functionality for only one PAM category: +that of authentication. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li auth +feature. +It also provides a null function for session management. +.Pp +Note that this module does not enforce +.Xr opieaccess 5 +checks. +There is a separate module, +.Xr pam_opieaccess 8 , +for this purpose. +.Ss OPIE Authentication Module +The OPIE authentication component +provides functions to verify the identity of a user +.Pq Fn pam_sm_authenticate , +which obtains the relevant +.Xr opie 4 +credentials. +It provides the user with an OPIE challenge, +and verifies that this is correct with +.Xr opiechallenge 3 . +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm auth_as_self" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm auth_as_self +This option will require the user +to authenticate himself as the user +given by +.Xr getlogin 2 , +not as the account they are attempting to access. +This is primarily for services like +.Xr su 1 , +where the user's ability to retype +their own password +might be deemed sufficient. +.It Cm no_fake_prompts +Do not generate fake challenges for users who do not have an OPIE key. +Note that this can leak information to a hypothetical attacker about +who uses OPIE and who does not, but it can be useful on systems where +some users want to use OPIE but most do not. +.El +.Pp +Note that +.Nm +ignores the standard options +.Cm try_first_pass +and +.Cm use_first_pass , +since a challenge must be generated before the user can submit a valid +response. +.Sh FILES +.Bl -tag -width ".Pa /etc/opiekeys" -compact +.It Pa /etc/opiekeys +default OPIE password database. +.El +.Sh SEE ALSO +.Xr passwd 1 , +.Xr getlogin 2 , +.Xr opiechallenge 3 , +.Xr syslog 3 , +.Xr opie 4 , +.Xr pam.conf 5 , +.Xr pam 8 diff --git a/lib/libpam/modules/pam_opie/pam_opie.c b/lib/libpam/modules/pam_opie/pam_opie.c new file mode 100644 index 0000000..bfb875f --- /dev/null +++ b/lib/libpam/modules/pam_opie/pam_opie.c @@ -0,0 +1,155 @@ +/*- + * Copyright 2000 James Bloom + * All rights reserved. + * Based upon code Copyright 1998 Juniper Networks, Inc. + * Copyright (c) 2001-2003 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/types.h> +#include <opie.h> +#include <pwd.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +#define PAM_SM_AUTH + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +#define PAM_OPT_NO_FAKE_PROMPTS "no_fake_prompts" + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + struct opie opie; + struct passwd *pwd; + int retval, i; + const char *(promptstr[]) = { "%s\nPassword: ", "%s\nPassword [echo on]: "}; + char challenge[OPIE_CHALLENGE_MAX]; + char principal[OPIE_PRINCIPAL_MAX]; + const char *user; + char *response; + int style; + + user = NULL; + if (openpam_get_option(pamh, PAM_OPT_AUTH_AS_SELF)) { + if ((pwd = getpwnam(getlogin())) == NULL) + return (PAM_AUTH_ERR); + user = pwd->pw_name; + } + else { + retval = pam_get_user(pamh, &user, NULL); + if (retval != PAM_SUCCESS) + return (retval); + } + + PAM_LOG("Got user: %s", user); + + /* + * Watch out: libopie feels entitled to truncate the user name + * passed to it if it's longer than OPIE_PRINCIPAL_MAX, which is + * not uncommon in Windows environments. + */ + if (strlen(user) >= sizeof(principal)) + return (PAM_AUTH_ERR); + strlcpy(principal, user, sizeof(principal)); + + /* + * Don't call the OPIE atexit() handler when our program exits, + * since the module has been unloaded and we will SEGV. + */ + opiedisableaeh(); + + /* + * If the no_fake_prompts option was given, and the user + * doesn't have an OPIE key, just fail rather than present the + * user with a bogus OPIE challenge. + */ + if (opiechallenge(&opie, principal, challenge) != 0 && + openpam_get_option(pamh, PAM_OPT_NO_FAKE_PROMPTS)) + return (PAM_AUTH_ERR); + + /* + * It doesn't make sense to use a password that has already been + * typed in, since we haven't presented the challenge to the user + * yet, so clear the stored password. + */ + pam_set_item(pamh, PAM_AUTHTOK, NULL); + + style = PAM_PROMPT_ECHO_OFF; + for (i = 0; i < 2; i++) { + retval = pam_prompt(pamh, style, &response, + promptstr[i], challenge); + if (retval != PAM_SUCCESS) { + opieunlock(); + return (retval); + } + + PAM_LOG("Completed challenge %d: %s", i, response); + + if (response[0] != '\0') + break; + + /* Second time round, echo the password */ + style = PAM_PROMPT_ECHO_ON; + } + + pam_set_item(pamh, PAM_AUTHTOK, response); + + /* + * Opieverify is supposed to return -1 only if an error occurs. + * But it returns -1 even if the response string isn't in the form + * it expects. Thus we can't log an error and can only check for + * success or lack thereof. + */ + retval = opieverify(&opie, response); + free(response); + return (retval == 0 ? PAM_SUCCESS : PAM_AUTH_ERR); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_opie"); diff --git a/lib/libpam/modules/pam_opieaccess/Makefile b/lib/libpam/modules/pam_opieaccess/Makefile new file mode 100644 index 0000000..1554a88 --- /dev/null +++ b/lib/libpam/modules/pam_opieaccess/Makefile @@ -0,0 +1,10 @@ +# $FreeBSD$ + +LIB= pam_opieaccess +SRCS= ${LIB}.c +MAN= pam_opieaccess.8 + +DPADD= ${LIBOPIE} +LDADD= -lopie + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_opieaccess/pam_opieaccess.8 b/lib/libpam/modules/pam_opieaccess/pam_opieaccess.8 new file mode 100644 index 0000000..5521a85 --- /dev/null +++ b/lib/libpam/modules/pam_opieaccess/pam_opieaccess.8 @@ -0,0 +1,142 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2002 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd October 26, 2007 +.Dt PAM_OPIEACCESS 8 +.Os +.Sh NAME +.Nm pam_opieaccess +.Nd OPIEAccess PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_opieaccess +.Op Ar options +.Sh DESCRIPTION +The +.Nm +module is used in conjunction with the +.Xr pam_opie 8 +PAM module to ascertain that authentication can proceed by other means +(such as the +.Xr pam_unix 8 +module) even if OPIE authentication failed. +To properly use this module, +.Xr pam_opie 8 +should be marked +.Dq Li sufficient , +and +.Nm +should be listed right below it and marked +.Dq Li requisite . +.Pp +The +.Nm +module provides functionality for only one PAM category: +authentication. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li auth +feature. +It also provides null functions for the remaining module types. +.Ss OPIEAccess Authentication Module +The authentication component +.Pq Fn pam_sm_authenticate , +returns +.Dv PAM_SUCCESS +in two cases: +.Bl -enum +.It +The user does not have OPIE enabled. +.It +The user has OPIE enabled, and the remote host is listed as a trusted +host in +.Pa /etc/opieaccess , +and the user does not have a file named +.Pa \&.opiealways +in his home directory. +.El +.Pp +Otherwise, it returns +.Dv PAM_AUTH_ERR . +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm allow_local" +.It Cm allow_local +Normally, local logins are subjected to the same restrictions as +remote logins from +.Dq localhost . +This option causes +.Nm +to always allow local logins. +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +These messages include reasons why the user's authentication attempt +was declined. +.El +.Sh FILES +.Bl -tag -width ".Pa $HOME/.opiealways" +.It Pa /etc/opieaccess +List of trusted hosts or networks. +See +.Xr opieaccess 5 +for a description of its syntax. +.It Pa $HOME/.opiealways +The presence of this file makes OPIE mandatory for the user. +.El +.Sh SEE ALSO +.Xr opie 4 , +.Xr opieaccess 5 , +.Xr pam.conf 5 , +.Xr pam 8 , +.Xr pam_opie 8 +.Sh AUTHORS +The +.Nm +module and this manual page were developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_opieaccess/pam_opieaccess.c b/lib/libpam/modules/pam_opieaccess/pam_opieaccess.c new file mode 100644 index 0000000..0351115 --- /dev/null +++ b/lib/libpam/modules/pam_opieaccess/pam_opieaccess.c @@ -0,0 +1,95 @@ +/*- + * Copyright (c) 2002 Networks Associates Technology, Inc. + * All rights reserved. + * + * This software was developed for the FreeBSD Project by ThinkSec AS and + * NAI Labs, the Security Research Division of Network Associates, Inc. + * under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the + * DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#define _BSD_SOURCE + +#include <sys/types.h> +#include <opie.h> +#include <pwd.h> +#include <unistd.h> +#include <syslog.h> + +#define PAM_SM_AUTH + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + struct opie opie; + struct passwd *pwent; + const void *luser, *rhost; + int r; + + r = pam_get_item(pamh, PAM_USER, &luser); + if (r != PAM_SUCCESS) + return (r); + if (luser == NULL) + return (PAM_SERVICE_ERR); + + pwent = getpwnam(luser); + if (pwent == NULL || opielookup(&opie, __DECONST(char *, luser)) != 0) + return (PAM_SUCCESS); + + r = pam_get_item(pamh, PAM_RHOST, &rhost); + if (r != PAM_SUCCESS) + return (r); + if (rhost == NULL || *(const char *)rhost == '\0') + rhost = openpam_get_option(pamh, "allow_local") ? + "" : "localhost"; + + if (opieaccessfile(__DECONST(char *, rhost)) != 0 && + opiealways(pwent->pw_dir) != 0) + return (PAM_SUCCESS); + + PAM_VERBOSE_ERROR("Refused; remote host is not in opieaccess"); + + return (PAM_AUTH_ERR); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_opieaccess"); diff --git a/lib/libpam/modules/pam_passwdqc/Makefile b/lib/libpam/modules/pam_passwdqc/Makefile new file mode 100644 index 0000000..905afe1 --- /dev/null +++ b/lib/libpam/modules/pam_passwdqc/Makefile @@ -0,0 +1,17 @@ +# $FreeBSD$ + +SRCDIR= ${.CURDIR}/../../../../contrib/pam_modules/pam_passwdqc +.PATH: ${SRCDIR} + +LIB= pam_passwdqc +SRCS= pam_passwdqc.c passwdqc_check.c passwdqc_random.c wordset_4k.c +MAN= pam_passwdqc.8 + +WARNS?= 0 +CFLAGS+= -I${SRCDIR} + +DPADD= ${LIBCRYPT} +LDADD= -lcrypt + +.include <bsd.lib.mk> + diff --git a/lib/libpam/modules/pam_passwdqc/pam_passwdqc.8 b/lib/libpam/modules/pam_passwdqc/pam_passwdqc.8 new file mode 100644 index 0000000..408f77d --- /dev/null +++ b/lib/libpam/modules/pam_passwdqc/pam_passwdqc.8 @@ -0,0 +1,268 @@ +.\" Copyright (c) 2000-2002 Solar Designer. +.\" All rights reserved. +.\" Copyright (c) 2001 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd April 15, 2002 +.Dt PAM_PASSWDQC 8 +.Os +.Sh NAME +.Nm pam_passwdqc +.Nd Password quality-control PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_passwdqc +.Op Ar options +.Sh DESCRIPTION +The +.Nm +module is a simple password strength checking module for +PAM. +In addition to checking regular passwords, it offers support for +passphrases and can provide randomly generated passwords. +.Pp +The +.Nm +module provides functionality for only one PAM category: +password changing. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li password +feature. +.Pp +The +.Fn pam_chauthtok +service function will ask the user for a new password, and verify that +it meets certain minimum standards. +If the chosen password is unsatisfactory, the service function returns +.Dv PAM_AUTHTOK_ERR . +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width indent +.It Xo +.Sm off +.Cm min No = Ar N0 , N1 , N2 , N3 , N4 +.Sm on +.Xc +.Sm off +.Pq Cm min No = Cm disabled , No 24 , 12 , 8 , 7 +.Sm on +The minimum allowed password lengths for different kinds of +passwords/passphrases. +The keyword +.Cm disabled +can be used to +disallow passwords of a given kind regardless of their length. +Each subsequent number is required to be no larger than the preceding +one. +.Pp +.Ar N0 +is used for passwords consisting of characters from one character +class only. +The character classes are: digits, lower-case letters, upper-case +letters, and other characters. +There is also a special class for +.No non- Ns Tn ASCII +characters which could not +be classified, but are assumed to be non-digits. +.Pp +.Ar N1 +is used for passwords consisting of characters from two character +classes, which do not meet the requirements for a passphrase. +.Pp +.Ar N2 +is used for passphrases. +A passphrase must consist of sufficient words (see the +.Cm passphrase +option below). +.Pp +.Ar N3 +and +.Ar N4 +are used for passwords consisting of characters from three +and four character classes, respectively. +.Pp +When calculating the number of character classes, upper-case letters +used as the first character and digits used as the last character of a +password are not counted. +.Pp +In addition to being sufficiently long, passwords are required to +contain enough different characters for the character classes and +the minimum length they have been checked against. +.Pp +.It Cm max Ns = Ns Ar N +.Pq Cm max Ns = Ns 40 +The maximum allowed password length. +This can be used to prevent users from setting passwords which may be +too long for some system services. +The value 8 is treated specially: if +.Cm max +is set to 8, passwords longer than 8 characters will not be rejected, +but will be truncated to 8 characters for the strength checks and the +user will be warned. +This is for compatibility with the traditional DES password hashes, +which truncate the password at 8 characters. +.Pp +It is important that you do set +.Cm max Ns = Ns 8 +if you are using the traditional +hashes, or some weak passwords will pass the checks. +.It Cm passphrase Ns = Ns Ar N +.Pq Cm passphrase Ns = Ns 3 +The number of words required for a passphrase, or 0 to disable +passphrase support. +.It Cm match Ns = Ns Ar N +.Pq Cm match Ns = Ns 4 +The length of common substring required to conclude that a password is +at least partially based on information found in a character string, +or 0 to disable the substring search. +Note that the password will not be rejected once a weak substring is +found; it will instead be subjected to the usual strength requirements +with the weak substring removed. +.Pp +The substring search is case-insensitive and is able to detect and +remove a common substring spelled backwards. +.It Xo +.Sm off +.Cm similar No = Cm permit | deny +.Sm on +.Xc +.Pq Cm similar Ns = Ns Cm deny +Whether a new password is allowed to be similar to the old one. +The passwords are considered to be similar when there is a sufficiently +long common substring and the new password with the substring removed +would be weak. +.It Xo +.Sm off +.Cm random No = Ar N Op , Cm only +.Sm on +.Xc +.Pq Cm random Ns = Ns 42 +The size of randomly-generated passwords in bits, or 0 to disable this +feature. +Passwords that contain the offered randomly-generated string will be +allowed regardless of other possible restrictions. +.Pp +The +.Cm only +modifier can be used to disallow user-chosen passwords. +.It Xo +.Sm off +.Cm enforce No = Cm none | users | everyone +.Sm on +.Xc +.Pq Cm enforce Ns = Ns Cm everyone +The module can be configured to warn of weak passwords only, but not +actually enforce strong passwords. +The +.Cm users +setting will enforce strong passwords for non-root users only. +.It Cm non-unix +Normally, +.Nm +uses +.Xr getpwnam 3 +to obtain the user's personal login information and use that during +the password strength checks. +This behavior can be disabled with the +.Cm non-unix +option. +.It Cm retry Ns = Ns Ar N +.Pq Cm retry Ns = Ns 3 +The number of times the module will ask for a new password if the user +fails to provide a sufficiently strong password and enter it twice the +first time. +.It Cm ask_oldauthtok Ns Op = Ns Cm update +Ask for the old password as well. +Normally, +.Nm +leaves this task for subsequent modules. +With no argument, the +.Cm ask_oldauthtok +option will cause +.Nm +to ask for the old password during the preliminary check phase. +If the +.Cm ask_oldauthtok +option is specified with the +.Cm update +argument, +.Nm +will do that during the update phase. +.It Cm check_oldauthtok +This tells +.Nm +to validate the old password before giving a +new password prompt. +Normally, this task is left for subsequent modules. +.Pp +The primary use for this option is when +.Cm ask_oldauthtok Ns = Ns Cm update +is also specified, in which case no other modules gets a chance to ask +for and validate the password. +Of course, this will only work with +.Ux +passwords. +.It Cm use_first_pass , use_authtok +Use the new password obtained by modules stacked before +.Nm . +This disables user interaction within +.Nm . +The only difference between +.Cm use_first_pass +and +.Cm use_authtok +is that the former is incompatible with +.Cm ask_oldauthtok . +.El +.Sh SEE ALSO +.Xr getpwnam 3 , +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module was written by +.An Solar Designer Aq solar@openwall.com . +This manual page, derived from the author's documentation, was written +for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_permit/Makefile b/lib/libpam/modules/pam_permit/Makefile new file mode 100644 index 0000000..dbbd5b5 --- /dev/null +++ b/lib/libpam/modules/pam_permit/Makefile @@ -0,0 +1,31 @@ +# Copyright 1999 Max Khon. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_permit +SRCS= pam_permit.c +MAN= pam_permit.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_permit/pam_permit.8 b/lib/libpam/modules/pam_permit/pam_permit.8 new file mode 100644 index 0000000..c7d98ab --- /dev/null +++ b/lib/libpam/modules/pam_permit/pam_permit.8 @@ -0,0 +1,75 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd July 7, 2001 +.Dt PAM_PERMIT 8 +.Os +.Sh NAME +.Nm pam_permit +.Nd Promiscuous PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_permit +.Op Ar options +.Sh DESCRIPTION +The Promiscuous authentication service module for PAM, +.Nm +provides functionality for all the PAM categories: +authentication, +account management, +session management and +password management. +In terms of the +.Ar module-type +parameter, these are the +.Dq Li auth , +.Dq Li account , +.Dq Li session , +and +.Dq Li password +features. +.Pp +The Promiscuous module +will universally allow all requests. +It is primarily of use during testing, +and to silence +.Dq noisy +PAM-enabled applications. +.Pp +The following options may be passed to the module: +.Bl -tag -width ".Cm debug" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.El +.Sh SEE ALSO +.Xr syslog 3 , +.Xr pam.conf 5 , +.Xr pam 8 diff --git a/lib/libpam/modules/pam_permit/pam_permit.c b/lib/libpam/modules/pam_permit/pam_permit.c new file mode 100644 index 0000000..fe0a4ed --- /dev/null +++ b/lib/libpam/modules/pam_permit/pam_permit.c @@ -0,0 +1,93 @@ +/*- + * Copyright 2001 Mark R V Murray + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <stddef.h> + +#define PAM_SM_AUTH +#define PAM_SM_ACCOUNT +#define PAM_SM_SESSION +#define PAM_SM_PASSWORD + +#include <security/pam_appl.h> +#include <security/pam_modules.h> + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + const char *user; + int r; + + if ((r = pam_get_user(pamh, &user, NULL)) != PAM_SUCCESS) + return (r); + + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_acct_mgmt(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_chauthtok(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_open_session(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_close_session(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_permit"); diff --git a/lib/libpam/modules/pam_radius/Makefile b/lib/libpam/modules/pam_radius/Makefile new file mode 100644 index 0000000..88e4357 --- /dev/null +++ b/lib/libpam/modules/pam_radius/Makefile @@ -0,0 +1,35 @@ +# Copyright 1998 Juniper Networks, Inc. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_radius +SRCS= pam_radius.c +MAN= pam_radius.8 +WARNS= 0 + +DPADD= ${LIBRADIUS} +LDADD= -lradius + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_radius/pam_radius.8 b/lib/libpam/modules/pam_radius/pam_radius.8 new file mode 100644 index 0000000..25e7312 --- /dev/null +++ b/lib/libpam/modules/pam_radius/pam_radius.8 @@ -0,0 +1,138 @@ +.\" Copyright (c) 1999 +.\" Andrzej Bialecki <abial@FreeBSD.org>. All rights reserved. +.\" +.\" Copyright (c) 1992, 1993, 1994 +.\" The Regents of the University of California. All rights reserved. +.\" All rights reserved. +.\" +.\" This code is derived from software donated to Berkeley by +.\" Jan-Simon Pendry. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. All advertising materials mentioning features or use of this software +.\" must display the following acknowledgement: +.\" This product includes software developed by the University of +.\" California, Berkeley and its contributors. +.\" 4. Neither the name of the University nor the names of its contributors +.\" may be used to endorse or promote products derived from this software +.\" without specific prior written permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd October 28, 2002 +.Dt PAM_RADIUS 8 +.Os +.Sh NAME +.Nm pam_radius +.Nd RADIUS authentication PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_radius +.Op Ar options +.Sh DESCRIPTION +The +.Nm +module provides authentication services based +upon the RADIUS (Remote Authentication Dial In User Service) protocol +for the PAM (Pluggable Authentication Module) framework. +.Pp +The +.Nm +module accepts these optional parameters: +.Bl -tag -width Fl +.It Cm use_first_pass +causes +.Nm +to use a previously entered password instead of prompting for a new one. +If no password has been entered then authentication fails. +.It Cm try_first_pass +causes +.Nm +to use a previously entered password, if one is available. +If no +password has been entered, +.Nm +prompts for one as usual. +.It Cm echo_pass +causes echoing to be left on if +.Nm +prompts for a password. +.It Cm conf Ns = Ns Ar pathname +specifies a non-standard location for the RADIUS client configuration file +(normally located in +.Pa /etc/radius.conf ) . +.It Cm nas_id Ns = Ns Ar identifier +specifies a NAS identifier to send instead of the hostname. +.It Cm template_user Ns = Ns Ar username +specifies a user whose +.Xr passwd 5 +entry will be used as a template to create the session environment +if the supplied username does not exist in local password database. +The user +will be authenticated with the supplied username and password, but his +credentials to the system will be presented as the ones for +.Ar username , +i.e., his login class, home directory, resource limits, etc.\& will be set to ones +defined for +.Ar username . +.Pp +If this option is omitted, and there is no username +in the system databases equal to the supplied one (as determined by call to +.Xr getpwnam 3 ) , +the authentication will fail. +.It Cm nas_ipaddr Ns Op No = Ns Ar address +specifies a NAS IP address to be sent. +If option is present, but there is no value provided then IP address +corresponding to the current hostname will be used. +.El +.Sh FILES +.Bl -tag -width /etc/radius.conf -compact +.It Pa /etc/radius.conf +The standard RADIUS client configuration file for +.Nm +.El +.Sh SEE ALSO +.Xr passwd 5 , +.Xr radius.conf 5 , +.Xr pam 8 +.Sh HISTORY +The +.Nm +module first appeared in +.Fx 3.1 . +The +.Nm +manual page first appeared in +.Fx 3.3 . +.Sh AUTHORS +.An -nosplit +The +.Nm +manual page was written by +.An Andrzej Bialecki Aq abial@FreeBSD.org . +.Pp +The +.Nm +module was written by +.An John D. Polstra Aq jdp@FreeBSD.org . diff --git a/lib/libpam/modules/pam_radius/pam_radius.c b/lib/libpam/modules/pam_radius/pam_radius.c new file mode 100644 index 0000000..306c4b7 --- /dev/null +++ b/lib/libpam/modules/pam_radius/pam_radius.c @@ -0,0 +1,366 @@ +/*- + * Copyright 1998 Juniper Networks, Inc. + * All rights reserved. + * Copyright (c) 2001-2003 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/param.h> +#include <sys/types.h> +#include <sys/socket.h> +#include <netdb.h> +#include <pwd.h> +#include <radlib.h> +#include <stdlib.h> +#include <string.h> +#include <syslog.h> +#include <unistd.h> + +#define PAM_SM_AUTH + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +#define PAM_OPT_CONF "conf" +#define PAM_OPT_TEMPLATE_USER "template_user" +#define PAM_OPT_NAS_ID "nas_id" +#define PAM_OPT_NAS_IPADDR "nas_ipaddr" + +#define MAX_CHALLENGE_MSGS 10 +#define PASSWORD_PROMPT "RADIUS Password:" + +static int build_access_request(struct rad_handle *, const char *, + const char *, const char *, const char *, const void *, + size_t); +static int do_accept(pam_handle_t *, struct rad_handle *); +static int do_challenge(pam_handle_t *, struct rad_handle *, + const char *, const char *, const char *); + +/* + * Construct an access request, but don't send it. Returns 0 on success, + * -1 on failure. + */ +static int +build_access_request(struct rad_handle *radh, const char *user, + const char *pass, const char *nas_id, const char *nas_ipaddr, + const void *state, size_t state_len) +{ + int error; + char host[MAXHOSTNAMELEN]; + struct sockaddr_in *haddr; + struct addrinfo hints; + struct addrinfo *res; + + if (rad_create_request(radh, RAD_ACCESS_REQUEST) == -1) { + syslog(LOG_CRIT, "rad_create_request: %s", rad_strerror(radh)); + return (-1); + } + if (nas_id == NULL || + (nas_ipaddr != NULL && strlen(nas_ipaddr) == 0)) { + if (gethostname(host, sizeof host) != -1) { + if (nas_id == NULL) + nas_id = host; + if (nas_ipaddr != NULL && strlen(nas_ipaddr) == 0) + nas_ipaddr = host; + } + } + if ((user != NULL && + rad_put_string(radh, RAD_USER_NAME, user) == -1) || + (pass != NULL && + rad_put_string(radh, RAD_USER_PASSWORD, pass) == -1) || + (nas_id != NULL && + rad_put_string(radh, RAD_NAS_IDENTIFIER, nas_id) == -1)) { + syslog(LOG_CRIT, "rad_put_string: %s", rad_strerror(radh)); + return (-1); + } + if (nas_ipaddr != NULL) { + memset(&hints, 0, sizeof(hints)); + hints.ai_family = AF_INET; + if (getaddrinfo(nas_ipaddr, NULL, &hints, &res) == 0 && + res != NULL && res->ai_family == AF_INET) { + haddr = (struct sockaddr_in *)res->ai_addr; + error = rad_put_addr(radh, RAD_NAS_IP_ADDRESS, + haddr->sin_addr); + freeaddrinfo(res); + if (error == -1) { + syslog(LOG_CRIT, "rad_put_addr: %s", + rad_strerror(radh)); + return (-1); + } + } + } + if (state != NULL && rad_put_attr(radh, RAD_STATE, state, + state_len) == -1) { + syslog(LOG_CRIT, "rad_put_attr: %s", rad_strerror(radh)); + return (-1); + } + if (rad_put_int(radh, RAD_SERVICE_TYPE, RAD_AUTHENTICATE_ONLY) == -1) { + syslog(LOG_CRIT, "rad_put_int: %s", rad_strerror(radh)); + return (-1); + } + return (0); +} + +static int +do_accept(pam_handle_t *pamh, struct rad_handle *radh) +{ + int attrtype; + const void *attrval; + size_t attrlen; + char *s; + + while ((attrtype = rad_get_attr(radh, &attrval, &attrlen)) > 0) { + if (attrtype == RAD_USER_NAME) { + s = rad_cvt_string(attrval, attrlen); + if (s == NULL) { + syslog(LOG_CRIT, + "rad_cvt_string: out of memory"); + return (-1); + } + pam_set_item(pamh, PAM_USER, s); + free(s); + } + } + if (attrtype == -1) { + syslog(LOG_CRIT, "rad_get_attr: %s", rad_strerror(radh)); + return (-1); + } + return (0); +} + +static int +do_challenge(pam_handle_t *pamh, struct rad_handle *radh, const char *user, + const char *nas_id, const char *nas_ipaddr) +{ + int retval; + int attrtype; + const void *attrval; + size_t attrlen; + const void *state; + size_t statelen; + struct pam_message msgs[MAX_CHALLENGE_MSGS]; + const struct pam_message *msg_ptrs[MAX_CHALLENGE_MSGS]; + struct pam_response *resp; + int num_msgs; + const void *item; + const struct pam_conv *conv; + + state = NULL; + statelen = 0; + num_msgs = 0; + while ((attrtype = rad_get_attr(radh, &attrval, &attrlen)) > 0) { + switch (attrtype) { + + case RAD_STATE: + state = attrval; + statelen = attrlen; + break; + + case RAD_REPLY_MESSAGE: + if (num_msgs >= MAX_CHALLENGE_MSGS) { + syslog(LOG_CRIT, + "Too many RADIUS challenge messages"); + return (PAM_SERVICE_ERR); + } + msgs[num_msgs].msg = rad_cvt_string(attrval, attrlen); + if (msgs[num_msgs].msg == NULL) { + syslog(LOG_CRIT, + "rad_cvt_string: out of memory"); + return (PAM_SERVICE_ERR); + } + msgs[num_msgs].msg_style = PAM_TEXT_INFO; + msg_ptrs[num_msgs] = &msgs[num_msgs]; + num_msgs++; + break; + } + } + if (attrtype == -1) { + syslog(LOG_CRIT, "rad_get_attr: %s", rad_strerror(radh)); + return (PAM_SERVICE_ERR); + } + if (num_msgs == 0) { + msgs[num_msgs].msg = strdup("(null RADIUS challenge): "); + if (msgs[num_msgs].msg == NULL) { + syslog(LOG_CRIT, "Out of memory"); + return (PAM_SERVICE_ERR); + } + msgs[num_msgs].msg_style = PAM_TEXT_INFO; + msg_ptrs[num_msgs] = &msgs[num_msgs]; + num_msgs++; + } + msgs[num_msgs-1].msg_style = PAM_PROMPT_ECHO_ON; + if ((retval = pam_get_item(pamh, PAM_CONV, &item)) != PAM_SUCCESS) { + syslog(LOG_CRIT, "do_challenge: cannot get PAM_CONV"); + return (retval); + } + conv = (const struct pam_conv *)item; + if ((retval = conv->conv(num_msgs, msg_ptrs, &resp, + conv->appdata_ptr)) != PAM_SUCCESS) + return (retval); + if (build_access_request(radh, user, resp[num_msgs-1].resp, nas_id, + nas_ipaddr, state, statelen) == -1) + return (PAM_SERVICE_ERR); + memset(resp[num_msgs-1].resp, 0, strlen(resp[num_msgs-1].resp)); + free(resp[num_msgs-1].resp); + free(resp); + while (num_msgs > 0) + free(msgs[--num_msgs].msg); + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + struct rad_handle *radh; + const char *user, *pass; + const void *tmpuser; + const char *conf_file, *template_user, *nas_id, *nas_ipaddr; + int retval; + int e; + + conf_file = openpam_get_option(pamh, PAM_OPT_CONF); + template_user = openpam_get_option(pamh, PAM_OPT_TEMPLATE_USER); + nas_id = openpam_get_option(pamh, PAM_OPT_NAS_ID); + nas_ipaddr = openpam_get_option(pamh, PAM_OPT_NAS_IPADDR); + + retval = pam_get_user(pamh, &user, NULL); + if (retval != PAM_SUCCESS) + return (retval); + + PAM_LOG("Got user: %s", user); + + retval = pam_get_authtok(pamh, PAM_AUTHTOK, &pass, PASSWORD_PROMPT); + if (retval != PAM_SUCCESS) + return (retval); + + PAM_LOG("Got password"); + + radh = rad_open(); + if (radh == NULL) { + syslog(LOG_CRIT, "rad_open failed"); + return (PAM_SERVICE_ERR); + } + + PAM_LOG("Radius opened"); + + if (rad_config(radh, conf_file) == -1) { + syslog(LOG_ALERT, "rad_config: %s", rad_strerror(radh)); + rad_close(radh); + return (PAM_SERVICE_ERR); + } + + PAM_LOG("Radius config file read"); + + if (build_access_request(radh, user, pass, nas_id, nas_ipaddr, NULL, + 0) == -1) { + rad_close(radh); + return (PAM_SERVICE_ERR); + } + + PAM_LOG("Radius build access done"); + + for (;;) { + switch (rad_send_request(radh)) { + + case RAD_ACCESS_ACCEPT: + e = do_accept(pamh, radh); + rad_close(radh); + if (e == -1) + return (PAM_SERVICE_ERR); + if (template_user != NULL) { + + PAM_LOG("Trying template user: %s", + template_user); + + /* + * If the given user name doesn't exist in + * the local password database, change it + * to the value given in the "template_user" + * option. + */ + retval = pam_get_item(pamh, PAM_USER, &tmpuser); + if (retval != PAM_SUCCESS) + return (retval); + if (getpwnam(tmpuser) == NULL) { + pam_set_item(pamh, PAM_USER, + template_user); + PAM_LOG("Using template user"); + } + + } + return (PAM_SUCCESS); + + case RAD_ACCESS_REJECT: + rad_close(radh); + PAM_VERBOSE_ERROR("Radius rejection"); + return (PAM_AUTH_ERR); + + case RAD_ACCESS_CHALLENGE: + retval = do_challenge(pamh, radh, user, nas_id, + nas_ipaddr); + if (retval != PAM_SUCCESS) { + rad_close(radh); + return (retval); + } + break; + + case -1: + syslog(LOG_CRIT, "rad_send_request: %s", + rad_strerror(radh)); + rad_close(radh); + PAM_VERBOSE_ERROR("Radius failure"); + return (PAM_AUTHINFO_UNAVAIL); + + default: + syslog(LOG_CRIT, + "rad_send_request: unexpected return value"); + rad_close(radh); + PAM_VERBOSE_ERROR("Radius error"); + return (PAM_SERVICE_ERR); + } + } +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_radius"); diff --git a/lib/libpam/modules/pam_rhosts/Makefile b/lib/libpam/modules/pam_rhosts/Makefile new file mode 100644 index 0000000..866267e --- /dev/null +++ b/lib/libpam/modules/pam_rhosts/Makefile @@ -0,0 +1,7 @@ +# $FreeBSD$ + +LIB= pam_rhosts +SRCS= pam_rhosts.c +MAN= pam_rhosts.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_rhosts/pam_rhosts.8 b/lib/libpam/modules/pam_rhosts/pam_rhosts.8 new file mode 100644 index 0000000..8adfcc6 --- /dev/null +++ b/lib/libpam/modules/pam_rhosts/pam_rhosts.8 @@ -0,0 +1,95 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2001 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd December 5, 2001 +.Dt PAM_RHOSTS 8 +.Os +.Sh NAME +.Nm pam_rhosts +.Nd Rhosts PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_rhosts +.Op Ar options +.Sh DESCRIPTION +The rhosts authentication service module for PAM, +.Nm +provides functionality for only one PAM category: +authentication. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li auth +feature. +.Ss Rhosts Authentication Module +The Rhosts authentication component +.Pq Fn pam_sm_authenticate , +returns success if and only if the target user's UID is not 0 and the +remote host and user are listed in +.Pa /etc/hosts.equiv +or in the target user's +.Pa ~/.rhosts . +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm allow_root" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +These messages include reasons why the user's authentication attempt +was declined. +.It Cm allow_root +do not automatically fail if the target user's UID is 0. +.El +.Sh SEE ALSO +.Xr hosts.equiv 5 , +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module and this manual page were developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_rhosts/pam_rhosts.c b/lib/libpam/modules/pam_rhosts/pam_rhosts.c new file mode 100644 index 0000000..4ba6ade --- /dev/null +++ b/lib/libpam/modules/pam_rhosts/pam_rhosts.c @@ -0,0 +1,95 @@ +/*- + * Copyright (c) 2002 Danny Braniss + * All rights reserved. + * Copyright (c) 2001,2002 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <pwd.h> +#include <stddef.h> +#include <string.h> +#include <unistd.h> + +#define PAM_SM_AUTH +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +#define OPT_ALLOW_ROOT "allow_root" + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + struct passwd *pw; + const char *user; + const void *ruser, *rhost; + int err, superuser; + + err = pam_get_user(pamh, &user, NULL); + if (err != PAM_SUCCESS) + return (err); + + if ((pw = getpwnam(user)) == NULL) + return (PAM_USER_UNKNOWN); + if (pw->pw_uid == 0 && + openpam_get_option(pamh, OPT_ALLOW_ROOT) == NULL) + return (PAM_AUTH_ERR); + + err = pam_get_item(pamh, PAM_RUSER, &ruser); + if (err != PAM_SUCCESS) + return (PAM_AUTH_ERR); + + err = pam_get_item(pamh, PAM_RHOST, &rhost); + if (err != PAM_SUCCESS) + return (PAM_AUTH_ERR); + + superuser = (strcmp(user, "root") == 0); + err = ruserok(rhost, superuser, ruser, user); + if (err != 0) + return (PAM_AUTH_ERR); + + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_rhosts"); diff --git a/lib/libpam/modules/pam_rootok/Makefile b/lib/libpam/modules/pam_rootok/Makefile new file mode 100644 index 0000000..8582daa --- /dev/null +++ b/lib/libpam/modules/pam_rootok/Makefile @@ -0,0 +1,31 @@ +# Copyright 2001 Mark R V Murray +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_rootok +SRCS= pam_rootok.c +MAN= pam_rootok.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_rootok/pam_rootok.8 b/lib/libpam/modules/pam_rootok/pam_rootok.8 new file mode 100644 index 0000000..4203fbd --- /dev/null +++ b/lib/libpam/modules/pam_rootok/pam_rootok.8 @@ -0,0 +1,75 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd July 8, 2001 +.Dt PAM_ROOTOK 8 +.Os +.Sh NAME +.Nm pam_rootok +.Nd RootOK PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_rootok +.Op Ar options +.Sh DESCRIPTION +The RootOK authentication service module for PAM, +.Nm +provides functionality for only one PAM category: +authentication. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li auth +feature. +It also provides a null function for session management. +.Ss RootOK Authentication Module +The RootOK authentication component +.Pq Fn pam_sm_authenticate , +always returns success for the superuser; +i.e., +if +.Xr getuid 2 +returns 0. +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm no_warn" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +These messages include +reasons why the user's +authentication attempt was declined. +.El +.Sh SEE ALSO +.Xr getuid 2 , +.Xr pam.conf 5 , +.Xr pam 8 diff --git a/lib/libpam/modules/pam_rootok/pam_rootok.c b/lib/libpam/modules/pam_rootok/pam_rootok.c new file mode 100644 index 0000000..16fab1f --- /dev/null +++ b/lib/libpam/modules/pam_rootok/pam_rootok.c @@ -0,0 +1,73 @@ +/*- + * Copyright (c) 2001 Mark R V Murray + * All rights reserved. + * Copyright (c) 2001 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#define _BSD_SOURCE + +#include <unistd.h> +#include <syslog.h> + +#define PAM_SM_AUTH + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + if (getuid() == 0) + return (PAM_SUCCESS); + + PAM_VERBOSE_ERROR("Refused; not superuser"); + PAM_LOG("User is not superuser"); + + return (PAM_AUTH_ERR); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_rootok"); diff --git a/lib/libpam/modules/pam_securetty/Makefile b/lib/libpam/modules/pam_securetty/Makefile new file mode 100644 index 0000000..8eb3e6e --- /dev/null +++ b/lib/libpam/modules/pam_securetty/Makefile @@ -0,0 +1,31 @@ +# Copyright 2001 Mark R V Murray +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_securetty +SRCS= pam_securetty.c +MAN= pam_securetty.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_securetty/pam_securetty.8 b/lib/libpam/modules/pam_securetty/pam_securetty.8 new file mode 100644 index 0000000..5825fb4 --- /dev/null +++ b/lib/libpam/modules/pam_securetty/pam_securetty.8 @@ -0,0 +1,92 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2002 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd July 8, 2001 +.Dt PAM_SECURETTY 8 +.Os +.Sh NAME +.Nm pam_securetty +.Nd SecureTTY PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_securetty +.Op Ar options +.Sh DESCRIPTION +The SecureTTY service module for PAM, +.Nm +provides functionality for only one PAM category: +account management. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li account +feature. +It also provides null functions for authentication and session +management. +.Ss SecureTTY Account Management Module +The SecureTTY account management component +.Pq Fn pam_sm_acct_mgmt , +returns failure if the user is attempting to authenticate as superuser, +and the process is attached to an insecure TTY. +In all other cases, the module returns success. +.Pp +A TTY is considered secure if it is listed in +.Pa /etc/ttys +and has the +.Dv TTY_SECURE +flag set. +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm no_warn" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +These messages include +reasons why the user's +authentication attempt was declined. +.El +.Sh SEE ALSO +.Xr getttynam 3 , +.Xr syslog 3 , +.Xr pam.conf 5 , +.Xr ttys 5 , +.Xr pam 8 diff --git a/lib/libpam/modules/pam_securetty/pam_securetty.c b/lib/libpam/modules/pam_securetty/pam_securetty.c new file mode 100644 index 0000000..f58274a --- /dev/null +++ b/lib/libpam/modules/pam_securetty/pam_securetty.c @@ -0,0 +1,96 @@ +/*- + * Copyright (c) 2001 Mark R V Murray + * All rights reserved. + * Copyright (c) 2001 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/types.h> +#include <sys/stat.h> +#include <pwd.h> +#include <ttyent.h> +#include <string.h> + +#define PAM_SM_ACCOUNT + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +#define TTY_PREFIX "/dev/" + +PAM_EXTERN int +pam_sm_acct_mgmt(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + struct passwd *pwd; + struct ttyent *ty; + const char *user; + const void *tty; + int pam_err; + + pam_err = pam_get_user(pamh, &user, NULL); + if (pam_err != PAM_SUCCESS) + return (pam_err); + if (user == NULL || (pwd = getpwnam(user)) == NULL) + return (PAM_SERVICE_ERR); + + PAM_LOG("Got user: %s", user); + + /* If the user is not root, secure ttys do not apply */ + if (pwd->pw_uid != 0) + return (PAM_SUCCESS); + + pam_err = pam_get_item(pamh, PAM_TTY, &tty); + if (pam_err != PAM_SUCCESS) + return (pam_err); + + PAM_LOG("Got TTY: %s", (const char *)tty); + + /* Ignore any "/dev/" on the PAM_TTY item */ + if (tty != NULL && strncmp(TTY_PREFIX, tty, sizeof(TTY_PREFIX)) == 0) { + PAM_LOG("WARNING: PAM_TTY starts with " TTY_PREFIX); + tty = (const char *)tty + sizeof(TTY_PREFIX) - 1; + } + + if (tty != NULL && (ty = getttynam(tty)) != NULL && + (ty->ty_status & TTY_SECURE) != 0) + return (PAM_SUCCESS); + + PAM_VERBOSE_ERROR("Not on secure TTY"); + return (PAM_AUTH_ERR); +} + +PAM_MODULE_ENTRY("pam_securetty"); diff --git a/lib/libpam/modules/pam_self/Makefile b/lib/libpam/modules/pam_self/Makefile new file mode 100644 index 0000000..50718e1 --- /dev/null +++ b/lib/libpam/modules/pam_self/Makefile @@ -0,0 +1,31 @@ +# Copyright 2001 Mark R V Murray +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_self +SRCS= pam_self.c +MAN= pam_self.8 + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_self/pam_self.8 b/lib/libpam/modules/pam_self/pam_self.8 new file mode 100644 index 0000000..d021434 --- /dev/null +++ b/lib/libpam/modules/pam_self/pam_self.8 @@ -0,0 +1,96 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2001 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" Portions of this software were developed for the FreeBSD Project by +.\" ThinkSec AS and NAI Labs, the Security Research Division of Network +.\" Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +.\" ("CBOSS"), as part of the DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd December 5, 2001 +.Dt PAM_SELF 8 +.Os +.Sh NAME +.Nm pam_self +.Nd Self PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_self +.Op Ar options +.Sh DESCRIPTION +The Self authentication service module for PAM, +.Nm +provides functionality for only one PAM category: +authentication. +In terms of the +.Ar module-type +parameter, this is the +.Dq Li auth +feature. +.Ss Self Authentication Module +The Self authentication component +.Pq Fn pam_sm_authenticate , +returns success if and only if the target user's user ID is identical +with the current real user ID. +If the current real user ID is zero, authentication will fail, +unless the +.Cm allow_root +option was specified. +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm allow_root" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +These messages include reasons why the user's authentication attempt +was declined. +.It Cm allow_root +do not automatically fail if the current real user ID is 0. +.El +.Sh SEE ALSO +.Xr getuid 2 , +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module and this manual page were developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. diff --git a/lib/libpam/modules/pam_self/pam_self.c b/lib/libpam/modules/pam_self/pam_self.c new file mode 100644 index 0000000..63df46c --- /dev/null +++ b/lib/libpam/modules/pam_self/pam_self.c @@ -0,0 +1,89 @@ +/*- + * Copyright (c) 2001 Mark R V Murray + * All rights reserved. + * Copyright (c) 2001,2002 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#define _BSD_SOURCE + +#include <pwd.h> +#include <unistd.h> +#include <syslog.h> + +#define PAM_SM_AUTH + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +#define OPT_ALLOW_ROOT "allow_root" + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + struct passwd *pwd; + const char *luser; + int pam_err; + uid_t uid; + + pam_err = pam_get_user(pamh, &luser, NULL); + if (pam_err != PAM_SUCCESS) + return (pam_err); + if (luser == NULL || (pwd = getpwnam(luser)) == NULL) + return (PAM_AUTH_ERR); + + uid = getuid(); + if (uid == 0 && !openpam_get_option(pamh, OPT_ALLOW_ROOT)) + return (PAM_AUTH_ERR); + + if (uid == (uid_t)pwd->pw_uid) + return (PAM_SUCCESS); + + PAM_VERBOSE_ERROR("Refused; source and target users differ"); + + return (PAM_AUTH_ERR); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_self"); diff --git a/lib/libpam/modules/pam_ssh/Makefile b/lib/libpam/modules/pam_ssh/Makefile new file mode 100644 index 0000000..f7dcd0c --- /dev/null +++ b/lib/libpam/modules/pam_ssh/Makefile @@ -0,0 +1,20 @@ +# PAM module for SSH +# $FreeBSD$ + +SSHDIR= ${.CURDIR}/../../../../crypto/openssh + +LIB= pam_ssh +MAN= pam_ssh.8 +SRCS= pam_ssh.c + +WARNS?= 0 +CFLAGS+= -I${SSHDIR} -include ssh_namespace.h + +DPADD= ${LIBSSH} ${LIBCRYPTO} ${LIBCRYPT} +LDADD= -lssh -lcrypto -lcrypt + +.include <bsd.lib.mk> + +.PATH: ${SSHDIR} + +${OBJS} ${POBJS} ${SOBJS}: ssh_namespace.h diff --git a/lib/libpam/modules/pam_ssh/pam_ssh.8 b/lib/libpam/modules/pam_ssh/pam_ssh.8 new file mode 100644 index 0000000..07e3176 --- /dev/null +++ b/lib/libpam/modules/pam_ssh/pam_ssh.8 @@ -0,0 +1,157 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2001-2003 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" This software was developed for the FreeBSD Project by ThinkSec AS and +.\" NAI Labs, the Security Research Division of Network Associates, Inc. +.\" under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the +.\" DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd November 26, 2001 +.Dt PAM_SSH 8 +.Os +.Sh NAME +.Nm pam_ssh +.Nd authentication and session management with SSH private keys +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_ssh +.Op Ar options +.Sh DESCRIPTION +The +SSH +authentication service module for PAM, +.Nm +provides functionality for two PAM categories: +authentication +and session management. +In terms of the +.Ar module-type +parameter, they are the +.Dq Li auth +and +.Dq Li session +features. +.Ss SSH Authentication Module +The +SSH +authentication component +provides a function to verify the identity of a user +.Pq Fn pam_sm_authenticate , +by prompting the user for a passphrase and verifying that it can +decrypt the target user's SSH key using that passphrase. +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm use_first_pass" +.It Cm use_first_pass +If the authentication module +is not the first in the stack, +and a previous module +obtained the user's password, +that password is used +to authenticate the user. +If this fails, +the authentication module returns failure +without prompting the user for a password. +This option has no effect +if the authentication module +is the first in the stack, +or if no previous modules +obtained the user's password. +.It Cm try_first_pass +This option is similar to the +.Cm use_first_pass +option, +except that if the previously obtained password fails, +the user is prompted for another password. +.It Cm nullok +Normally, keys with no passphrase are ignored for authentication +purposes. +If this option is set, keys with no passphrase will be taken into +consideration, allowing the user to log in with a blank password. +.El +.Ss SSH Session Management Module +The +SSH +session management component +provides functions to initiate +.Pq Fn pam_sm_open_session +and terminate +.Pq Fn pam_sm_close_session +sessions. +The +.Fn pam_sm_open_session +function starts an SSH agent, +passing it any private keys it decrypted +during the authentication phase, +and sets the environment variables +the agent specifies. +The +.Fn pam_sm_close_session +function kills the previously started SSH agent +by sending it a +.Dv SIGTERM . +.Pp +The following options may be passed to the session management module: +.Bl -tag -width ".Cm want_agent" +.It Cm want_agent +Start an agent even if no keys were decrypted during the +authentication phase. +.El +.Sh FILES +.Bl -tag -width ".Pa $HOME/.ssh/identity" -compact +.It Pa $HOME/.ssh/identity +SSH1 RSA key +.It Pa $HOME/.ssh/id_rsa +SSH2 RSA key +.It Pa $HOME/.ssh/id_dsa +SSH2 DSA key +.El +.Sh SEE ALSO +.Xr ssh-agent 1 , +.Xr pam.conf 5 , +.Xr pam 8 +.Sh AUTHORS +The +.Nm +module was originally written by +.An -nosplit +.An "Andrew J. Korty" Aq ajk@iu.edu . +The current implementation was developed for the +.Fx +Project by +ThinkSec AS and NAI Labs, the Security Research Division of Network +Associates, Inc.\& under DARPA/SPAWAR contract N66001-01-C-8035 +.Pq Dq CBOSS , +as part of the DARPA CHATS research program. +This manual page was written by +.An "Mark R V Murray" Aq markm@FreeBSD.org . diff --git a/lib/libpam/modules/pam_ssh/pam_ssh.c b/lib/libpam/modules/pam_ssh/pam_ssh.c new file mode 100644 index 0000000..25c63ca --- /dev/null +++ b/lib/libpam/modules/pam_ssh/pam_ssh.c @@ -0,0 +1,425 @@ +/*- + * Copyright (c) 2003 Networks Associates Technology, Inc. + * All rights reserved. + * + * This software was developed for the FreeBSD Project by ThinkSec AS and + * NAI Labs, the Security Research Division of Network Associates, Inc. + * under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the + * DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/param.h> +#include <sys/wait.h> + +#include <errno.h> +#include <fcntl.h> +#include <paths.h> +#include <pwd.h> +#include <signal.h> +#include <stdio.h> +#include <string.h> +#include <unistd.h> + +#define PAM_SM_AUTH +#define PAM_SM_SESSION + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/openpam.h> + +#include <openssl/evp.h> + +#include "key.h" +#include "buffer.h" +#include "authfd.h" +#include "authfile.h" + +extern char **environ; + +struct pam_ssh_key { + Key *key; + char *comment; +}; + +static const char *pam_ssh_prompt = "SSH passphrase: "; +static const char *pam_ssh_have_keys = "pam_ssh_have_keys"; + +static const char *pam_ssh_keyfiles[] = { + ".ssh/identity", /* SSH1 RSA key */ + ".ssh/id_rsa", /* SSH2 RSA key */ + ".ssh/id_dsa", /* SSH2 DSA key */ + NULL +}; + +static const char *pam_ssh_agent = "/usr/bin/ssh-agent"; +static char *const pam_ssh_agent_argv[] = { "ssh_agent", "-s", NULL }; +static char *const pam_ssh_agent_envp[] = { NULL }; + +/* + * Attempts to load a private key from the specified file in the specified + * directory, using the specified passphrase. If successful, returns a + * struct pam_ssh_key containing the key and its comment. + */ +static struct pam_ssh_key * +pam_ssh_load_key(const char *dir, const char *kfn, const char *passphrase) +{ + struct pam_ssh_key *psk; + char fn[PATH_MAX]; + char *comment; + Key *key; + + if (snprintf(fn, sizeof(fn), "%s/%s", dir, kfn) > (int)sizeof(fn)) + return (NULL); + comment = NULL; + key = key_load_private(fn, passphrase, &comment); + if (key == NULL) { + openpam_log(PAM_LOG_DEBUG, "failed to load key from %s\n", fn); + return (NULL); + } + + openpam_log(PAM_LOG_DEBUG, "loaded '%s' from %s\n", comment, fn); + if ((psk = malloc(sizeof(*psk))) == NULL) { + key_free(key); + free(comment); + return (NULL); + } + psk->key = key; + psk->comment = comment; + return (psk); +} + +/* + * Wipes a private key and frees the associated resources. + */ +static void +pam_ssh_free_key(pam_handle_t *pamh __unused, + void *data, int pam_err __unused) +{ + struct pam_ssh_key *psk; + + psk = data; + key_free(psk->key); + free(psk->comment); + free(psk); +} + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + const char **kfn, *passphrase, *user; + const void *item; + struct passwd *pwd; + struct pam_ssh_key *psk; + int nkeys, nullok, pam_err, pass; + + nullok = (openpam_get_option(pamh, "nullok") != NULL); + + /* PEM is not loaded by default */ + OpenSSL_add_all_algorithms(); + + /* get user name and home directory */ + pam_err = pam_get_user(pamh, &user, NULL); + if (pam_err != PAM_SUCCESS) + return (pam_err); + pwd = getpwnam(user); + if (pwd == NULL) + return (PAM_USER_UNKNOWN); + if (pwd->pw_dir == NULL) + return (PAM_AUTH_ERR); + + nkeys = 0; + pass = (pam_get_item(pamh, PAM_AUTHTOK, &item) == PAM_SUCCESS && + item != NULL); + load_keys: + /* get passphrase */ + pam_err = pam_get_authtok(pamh, PAM_AUTHTOK, + &passphrase, pam_ssh_prompt); + if (pam_err != PAM_SUCCESS) + return (pam_err); + + if (*passphrase == '\0' && !nullok) + goto skip_keys; + + /* switch to user credentials */ + pam_err = openpam_borrow_cred(pamh, pwd); + if (pam_err != PAM_SUCCESS) + return (pam_err); + + /* try to load keys from all keyfiles we know of */ + for (kfn = pam_ssh_keyfiles; *kfn != NULL; ++kfn) { + psk = pam_ssh_load_key(pwd->pw_dir, *kfn, passphrase); + if (psk != NULL) { + pam_set_data(pamh, *kfn, psk, pam_ssh_free_key); + ++nkeys; + } + } + + /* switch back to arbitrator credentials */ + openpam_restore_cred(pamh); + + skip_keys: + /* + * If we tried an old token and didn't get anything, and + * try_first_pass was specified, try again after prompting the + * user for a new passphrase. + */ + if (nkeys == 0 && pass == 1 && + openpam_get_option(pamh, "try_first_pass") != NULL) { + pam_set_item(pamh, PAM_AUTHTOK, NULL); + pass = 0; + goto load_keys; + } + + /* no keys? */ + if (nkeys == 0) + return (PAM_AUTH_ERR); + + pam_set_data(pamh, pam_ssh_have_keys, NULL, NULL); + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +/* + * Parses a line from ssh-agent's output. + */ +static void +pam_ssh_process_agent_output(pam_handle_t *pamh, FILE *f) +{ + char *line, *p, *key, *val; + size_t len; + + while ((line = fgetln(f, &len)) != NULL) { + if (len < 4 || strncmp(line, "SSH_", 4) != 0) + continue; + + /* find equal sign at end of key */ + for (p = key = line; p < line + len; ++p) + if (*p == '=') + break; + if (p == line + len || *p != '=') + continue; + *p = '\0'; + + /* find semicolon at end of value */ + for (val = ++p; p < line + len; ++p) + if (*p == ';') + break; + if (p == line + len || *p != ';') + continue; + *p = '\0'; + + /* store key-value pair in environment */ + openpam_log(PAM_LOG_DEBUG, "got %s: %s", key, val); + pam_setenv(pamh, key, val, 1); + } +} + +/* + * Starts an ssh agent and stores the environment variables derived from + * its output. + */ +static int +pam_ssh_start_agent(pam_handle_t *pamh) +{ + int agent_pipe[2]; + pid_t pid; + FILE *f; + + /* get a pipe which we will use to read the agent's output */ + if (pipe(agent_pipe) == -1) + return (PAM_SYSTEM_ERR); + + /* start the agent */ + openpam_log(PAM_LOG_DEBUG, "starting an ssh agent"); + pid = fork(); + if (pid == (pid_t)-1) { + /* failed */ + close(agent_pipe[0]); + close(agent_pipe[1]); + return (PAM_SYSTEM_ERR); + } + if (pid == 0) { + int fd; + + /* child: drop privs, close fds and start agent */ + setgid(getegid()); + setuid(geteuid()); + close(STDIN_FILENO); + open(_PATH_DEVNULL, O_RDONLY); + dup2(agent_pipe[1], STDOUT_FILENO); + dup2(agent_pipe[1], STDERR_FILENO); + for (fd = 3; fd < getdtablesize(); ++fd) + close(fd); + execve(pam_ssh_agent, pam_ssh_agent_argv, pam_ssh_agent_envp); + _exit(127); + } + + /* parent */ + close(agent_pipe[1]); + if ((f = fdopen(agent_pipe[0], "r")) == NULL) + return (PAM_SYSTEM_ERR); + pam_ssh_process_agent_output(pamh, f); + fclose(f); + + return (PAM_SUCCESS); +} + +/* + * Adds previously stored keys to a running agent. + */ +static int +pam_ssh_add_keys_to_agent(pam_handle_t *pamh) +{ + AuthenticationConnection *ac; + const struct pam_ssh_key *psk; + const char **kfn; + const void *item; + char **envlist, **env; + int pam_err; + + /* switch to PAM environment */ + envlist = environ; + if ((environ = pam_getenvlist(pamh)) == NULL) { + environ = envlist; + return (PAM_SYSTEM_ERR); + } + + /* get a connection to the agent */ + if ((ac = ssh_get_authentication_connection()) == NULL) { + pam_err = PAM_SYSTEM_ERR; + goto end; + } + + /* look for keys to add to it */ + for (kfn = pam_ssh_keyfiles; *kfn != NULL; ++kfn) { + pam_err = pam_get_data(pamh, *kfn, &item); + if (pam_err == PAM_SUCCESS && item != NULL) { + psk = item; + if (ssh_add_identity(ac, psk->key, psk->comment)) + openpam_log(PAM_LOG_DEBUG, + "added %s to ssh agent", psk->comment); + else + openpam_log(PAM_LOG_DEBUG, "failed " + "to add %s to ssh agent", psk->comment); + /* we won't need the key again, so wipe it */ + pam_set_data(pamh, *kfn, NULL, NULL); + } + } + pam_err = PAM_SUCCESS; + end: + /* disconnect from agent */ + if (ac != NULL) + ssh_close_authentication_connection(ac); + + /* switch back to original environment */ + for (env = environ; *env != NULL; ++env) + free(*env); + free(environ); + environ = envlist; + + return (pam_err); +} + +PAM_EXTERN int +pam_sm_open_session(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + struct passwd *pwd; + const char *user; + const void *data; + int pam_err; + + /* no keys, no work */ + if (pam_get_data(pamh, pam_ssh_have_keys, &data) != PAM_SUCCESS && + openpam_get_option(pamh, "want_agent") == NULL) + return (PAM_SUCCESS); + + /* switch to user credentials */ + pam_err = pam_get_user(pamh, &user, NULL); + if (pam_err != PAM_SUCCESS) + return (pam_err); + pwd = getpwnam(user); + if (pwd == NULL) + return (PAM_USER_UNKNOWN); + pam_err = openpam_borrow_cred(pamh, pwd); + if (pam_err != PAM_SUCCESS) + return (pam_err); + + /* start the agent */ + pam_err = pam_ssh_start_agent(pamh); + if (pam_err != PAM_SUCCESS) { + openpam_restore_cred(pamh); + return (pam_err); + } + + /* we have an agent, see if we can add any keys to it */ + pam_err = pam_ssh_add_keys_to_agent(pamh); + if (pam_err != PAM_SUCCESS) { + /* XXX ignore failures */ + } + + openpam_restore_cred(pamh); + return (PAM_SUCCESS); +} + +PAM_EXTERN int +pam_sm_close_session(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + const char *ssh_agent_pid; + char *end; + int status; + pid_t pid; + + if ((ssh_agent_pid = pam_getenv(pamh, "SSH_AGENT_PID")) == NULL) { + openpam_log(PAM_LOG_DEBUG, "no ssh agent"); + return (PAM_SUCCESS); + } + pid = (pid_t)strtol(ssh_agent_pid, &end, 10); + if (*ssh_agent_pid == '\0' || *end != '\0') { + openpam_log(PAM_LOG_DEBUG, "invalid ssh agent pid"); + return (PAM_SESSION_ERR); + } + openpam_log(PAM_LOG_DEBUG, "killing ssh agent %d", (int)pid); + if (kill(pid, SIGTERM) == -1 || + (waitpid(pid, &status, 0) == -1 && errno != ECHILD)) + return (PAM_SYSTEM_ERR); + return (PAM_SUCCESS); +} + +PAM_MODULE_ENTRY("pam_ssh"); diff --git a/lib/libpam/modules/pam_tacplus/Makefile b/lib/libpam/modules/pam_tacplus/Makefile new file mode 100644 index 0000000..053812a --- /dev/null +++ b/lib/libpam/modules/pam_tacplus/Makefile @@ -0,0 +1,34 @@ +# Copyright 1998 Juniper Networks, Inc. +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +LIB= pam_tacplus +SRCS= pam_tacplus.c +MAN= pam_tacplus.8 + +DPADD= ${LIBTACPLUS} +LDADD= -ltacplus + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_tacplus/pam_tacplus.8 b/lib/libpam/modules/pam_tacplus/pam_tacplus.8 new file mode 100644 index 0000000..03faf0c --- /dev/null +++ b/lib/libpam/modules/pam_tacplus/pam_tacplus.8 @@ -0,0 +1,130 @@ +.\" Copyright (c) 1999 +.\" Andrzej Bialecki <abial@FreeBSD.org>. All rights reserved. +.\" +.\" Copyright (c) 1992, 1993, 1994 +.\" The Regents of the University of California. All rights reserved. +.\" All rights reserved. +.\" +.\" This code is derived from software donated to Berkeley by +.\" Jan-Simon Pendry. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. All advertising materials mentioning features or use of this software +.\" must display the following acknowledgement: +.\" This product includes software developed by the University of +.\" California, Berkeley and its contributors. +.\" 4. Neither the name of the University nor the names of its contributors +.\" may be used to endorse or promote products derived from this software +.\" without specific prior written permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd August 2, 1999 +.Dt PAM_TACPLUS 8 +.Os +.Sh NAME +.Nm pam_tacplus +.Nd TACACS+ authentication PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_tacplus +.Op Ar options +.Sh DESCRIPTION +The +.Nm +module provides authentication services based +upon the TACACS+ protocol +for the PAM (Pluggable Authentication Module) framework. +.Pp +The +.Nm +module accepts these optional parameters: +.Bl -tag -width ".Cm use_first_pass" +.It Cm use_first_pass +causes +.Nm +to use a previously entered password instead of prompting for a new one. +If no password has been entered then authentication fails. +.It Cm try_first_pass +causes +.Nm +to use a previously entered password, if one is available. +If no +password has been entered, +.Nm +prompts for one as usual. +.It Cm echo_pass +causes echoing to be left on if +.Nm +prompts for a password. +.It Cm conf Ns = Ns Ar pathname +specifies a non-standard location for the TACACS+ client configuration file +(normally located in +.Pa /etc/tacplus.conf ) . +.It Cm template_user Ns = Ns Ar username +specifies a user whose +.Xr passwd 5 +entry will be used as a template to create the session environment +if the supplied username does not exist in local password database. +The user +will be authenticated with the supplied username and password, but his +credentials to the system will be presented as the ones for +.Ar username , +i.e., his login class, home directory, resource limits, etc.\& will be set to ones +defined for +.Ar username . +.Pp +If this option is omitted, and there is no username +in the system databases equal to the supplied one (as determined by call to +.Xr getpwnam 3 ) , +the authentication will fail. +.El +.Sh FILES +.Bl -tag -width /etc/tacplus.conf -compact +.It Pa /etc/tacplus.conf +The standard TACACS+ client configuration file for +.Nm +.El +.Sh SEE ALSO +.Xr passwd 5 , +.Xr tacplus.conf 5 , +.Xr pam 8 +.Sh HISTORY +The +.Nm +module first appeared in +.Fx 3.1 . +.Sh AUTHORS +.An -nosplit +The +.Nm +manual page was written by +.An Andrzej Bialecki Aq abial@FreeBSD.org +and adapted to TACACS+ from RADIUS by +.An Mark R V Murray Aq markm@FreeBSD.org . +.Pp +The +.Nm +module was written by +.An John D. Polstra Aq jdp@FreeBSD.org . diff --git a/lib/libpam/modules/pam_tacplus/pam_tacplus.c b/lib/libpam/modules/pam_tacplus/pam_tacplus.c new file mode 100644 index 0000000..7f860c3 --- /dev/null +++ b/lib/libpam/modules/pam_tacplus/pam_tacplus.c @@ -0,0 +1,281 @@ +/*- + * Copyright 1998 Juniper Networks, Inc. + * All rights reserved. + * Copyright (c) 2001-2003 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software were developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/param.h> + +#include <pwd.h> +#include <stdlib.h> +#include <string.h> +#include <syslog.h> +#include <taclib.h> +#include <unistd.h> + +#define PAM_SM_AUTH + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +#define PAM_OPT_CONF "conf" +#define PAM_OPT_TEMPLATE_USER "template_user" + +typedef int (*set_func)(struct tac_handle *, const char *); + +static int do_item(pam_handle_t *, struct tac_handle *, int, + set_func, const char *); +static char *get_msg(struct tac_handle *); +static int set_msg(struct tac_handle *, const char *); + +static int +do_item(pam_handle_t *pamh, struct tac_handle *tach, int item, + set_func func, const char *funcname) +{ + int retval; + const void *value; + + retval = pam_get_item(pamh, item, &value); + if (retval != PAM_SUCCESS) + return retval; + if (value != NULL && (*func)(tach, (const char *)value) == -1) { + syslog(LOG_CRIT, "%s: %s", funcname, tac_strerror(tach)); + tac_close(tach); + return PAM_SERVICE_ERR; + } + return PAM_SUCCESS; +} + +static char * +get_msg(struct tac_handle *tach) +{ + char *msg; + + msg = tac_get_msg(tach); + if (msg == NULL) { + syslog(LOG_CRIT, "tac_get_msg: %s", tac_strerror(tach)); + tac_close(tach); + return NULL; + } + return msg; +} + +static int +set_msg(struct tac_handle *tach, const char *msg) +{ + if (tac_set_msg(tach, msg) == -1) { + syslog(LOG_CRIT, "tac_set_msg: %s", tac_strerror(tach)); + tac_close(tach); + return -1; + } + return 0; +} + +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + int retval; + struct tac_handle *tach; + const char *conf_file, *template_user; + + conf_file = openpam_get_option(pamh, PAM_OPT_CONF); + template_user = openpam_get_option(pamh, PAM_OPT_TEMPLATE_USER); + + tach = tac_open(); + if (tach == NULL) { + syslog(LOG_CRIT, "tac_open failed"); + return (PAM_SERVICE_ERR); + } + if (tac_config(tach, conf_file) == -1) { + syslog(LOG_ALERT, "tac_config: %s", tac_strerror(tach)); + tac_close(tach); + return (PAM_SERVICE_ERR); + } + if (tac_create_authen(tach, TAC_AUTHEN_LOGIN, TAC_AUTHEN_TYPE_ASCII, + TAC_AUTHEN_SVC_LOGIN) == -1) { + syslog(LOG_CRIT, "tac_create_authen: %s", tac_strerror(tach)); + tac_close(tach); + return (PAM_SERVICE_ERR); + } + + PAM_LOG("Done tac_open() ... tac_close()"); + + retval = do_item(pamh, tach, PAM_USER, tac_set_user, "tac_set_user"); + if (retval != PAM_SUCCESS) + return (retval); + + PAM_LOG("Done user"); + + retval = do_item(pamh, tach, PAM_TTY, tac_set_port, "tac_set_port"); + if (retval != PAM_SUCCESS) + return (retval); + + PAM_LOG("Done tty"); + + retval = do_item(pamh, tach, PAM_RHOST, tac_set_rem_addr, + "tac_set_rem_addr"); + if (retval != PAM_SUCCESS) + return (retval); + + for (;;) { + char *srvr_msg; + size_t msg_len; + const char *user_msg; + char *data_msg; + int sflags; + int status; + + sflags = tac_send_authen(tach); + if (sflags == -1) { + syslog(LOG_CRIT, "tac_send_authen: %s", + tac_strerror(tach)); + tac_close(tach); + return (PAM_AUTHINFO_UNAVAIL); + } + status = TAC_AUTHEN_STATUS(sflags); + openpam_set_option(pamh, PAM_OPT_ECHO_PASS, + TAC_AUTHEN_NOECHO(sflags) ? NULL : ""); + switch (status) { + + case TAC_AUTHEN_STATUS_PASS: + tac_close(tach); + if (template_user != NULL) { + const void *item; + const char *user; + + PAM_LOG("Trying template user: %s", + template_user); + + /* + * If the given user name doesn't exist in + * the local password database, change it + * to the value given in the "template_user" + * option. + */ + retval = pam_get_item(pamh, PAM_USER, &item); + if (retval != PAM_SUCCESS) + return (retval); + user = (const char *)item; + if (getpwnam(user) == NULL) { + pam_set_item(pamh, PAM_USER, + template_user); + PAM_LOG("Using template user"); + } + } + return (PAM_SUCCESS); + + case TAC_AUTHEN_STATUS_FAIL: + tac_close(tach); + PAM_VERBOSE_ERROR("TACACS+ authentication failed"); + return (PAM_AUTH_ERR); + + case TAC_AUTHEN_STATUS_GETUSER: + case TAC_AUTHEN_STATUS_GETPASS: + if ((srvr_msg = get_msg(tach)) == NULL) + return (PAM_SERVICE_ERR); + if (status == TAC_AUTHEN_STATUS_GETUSER) + retval = pam_get_user(pamh, &user_msg, + *srvr_msg ? srvr_msg : NULL); + else if (status == TAC_AUTHEN_STATUS_GETPASS) + retval = pam_get_authtok(pamh, + PAM_AUTHTOK, &user_msg, + *srvr_msg ? srvr_msg : "Password:"); + free(srvr_msg); + if (retval != PAM_SUCCESS) { + /* XXX - send a TACACS+ abort packet */ + tac_close(tach); + return (retval); + } + if (set_msg(tach, user_msg) == -1) + return (PAM_SERVICE_ERR); + break; + + case TAC_AUTHEN_STATUS_GETDATA: + if ((srvr_msg = get_msg(tach)) == NULL) + return (PAM_SERVICE_ERR); + retval = pam_prompt(pamh, + openpam_get_option(pamh, PAM_OPT_ECHO_PASS) ? + PAM_PROMPT_ECHO_ON : PAM_PROMPT_ECHO_OFF, + &data_msg, "%s", *srvr_msg ? srvr_msg : "Data:"); + free(srvr_msg); + if (retval != PAM_SUCCESS) { + /* XXX - send a TACACS+ abort packet */ + tac_close(tach); + return (retval); + } + retval = set_msg(tach, data_msg); + memset(data_msg, 0, strlen(data_msg)); + free(data_msg); + if (retval == -1) + return (PAM_SERVICE_ERR); + break; + + case TAC_AUTHEN_STATUS_ERROR: + srvr_msg = (char *)tac_get_data(tach, &msg_len); + if (srvr_msg != NULL && msg_len != 0) { + syslog(LOG_CRIT, "tac_send_authen:" + " server detected error: %s", srvr_msg); + free(srvr_msg); + } + else + syslog(LOG_CRIT, + "tac_send_authen: server detected error"); + tac_close(tach); + return (PAM_AUTHINFO_UNAVAIL); + break; + + case TAC_AUTHEN_STATUS_RESTART: + case TAC_AUTHEN_STATUS_FOLLOW: + default: + syslog(LOG_CRIT, + "tac_send_authen: unexpected status %#x", status); + tac_close(tach); + return (PAM_AUTHINFO_UNAVAIL); + } + } +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_IGNORE); +} + +PAM_MODULE_ENTRY("pam_tacplus"); diff --git a/lib/libpam/modules/pam_unix/Makefile b/lib/libpam/modules/pam_unix/Makefile new file mode 100644 index 0000000..7235a51 --- /dev/null +++ b/lib/libpam/modules/pam_unix/Makefile @@ -0,0 +1,54 @@ +# Copyright 1998 Juniper Networks, Inc. +# All rights reserved. +# Copyright (c) 2002 Networks Associates Technology, Inc. +# All rights reserved. +# +# Portions of this software was developed for the FreeBSD Project by +# ThinkSec AS and NAI Labs, the Security Research Division of Network +# Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 +# ("CBOSS"), as part of the DARPA CHATS research program. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions +# are met: +# 1. Redistributions of source code must retain the above copyright +# notice, this list of conditions and the following disclaimer. +# 2. Redistributions in binary form must reproduce the above copyright +# notice, this list of conditions and the following disclaimer in the +# documentation and/or other materials provided with the distribution. +# 3. The name of the author may not be used to endorse or promote +# products derived from this software without specific prior written +# permission. +# +# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +# SUCH DAMAGE. +# +# $FreeBSD$ + +NO_PROFILE= +NO_INSTALLLIB= +.include <bsd.own.mk> + +LIB= pam_unix +SRCS= pam_unix.c +MAN= pam_unix.8 + +DPADD= ${LIBUTIL} ${LIBCRYPT} +LDADD= -lutil -lcrypt + +.if ${MK_NIS} != "no" +CFLAGS+= -DYP +DPADD+= ${LIBYPCLNT} +LDADD+= -lypclnt +.endif + +.include <bsd.lib.mk> diff --git a/lib/libpam/modules/pam_unix/pam_unix.8 b/lib/libpam/modules/pam_unix/pam_unix.8 new file mode 100644 index 0000000..60667e6 --- /dev/null +++ b/lib/libpam/modules/pam_unix/pam_unix.8 @@ -0,0 +1,215 @@ +.\" Copyright (c) 2001 Mark R V Murray +.\" All rights reserved. +.\" Copyright (c) 2001 Networks Associates Technology, Inc. +.\" All rights reserved. +.\" +.\" This software was developed for the FreeBSD Project by ThinkSec AS and +.\" NAI Labs, the Security Research Division of Network Associates, Inc. +.\" under DARPA/SPAWAR contract N66001-01-C-8035 ("CBOSS"), as part of the +.\" DARPA CHATS research program. +.\" +.\" Redistribution and use in source and binary forms, with or without +.\" modification, are permitted provided that the following conditions +.\" are met: +.\" 1. Redistributions of source code must retain the above copyright +.\" notice, this list of conditions and the following disclaimer. +.\" 2. Redistributions in binary form must reproduce the above copyright +.\" notice, this list of conditions and the following disclaimer in the +.\" documentation and/or other materials provided with the distribution. +.\" 3. The name of the author may not be used to endorse or promote +.\" products derived from this software without specific prior written +.\" permission. +.\" +.\" THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND +.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE +.\" ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE +.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS +.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) +.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT +.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY +.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF +.\" SUCH DAMAGE. +.\" +.\" $FreeBSD$ +.\" +.Dd March 27, 2007 +.Dt PAM_UNIX 8 +.Os +.Sh NAME +.Nm pam_unix +.Nd UNIX PAM module +.Sh SYNOPSIS +.Op Ar service-name +.Ar module-type +.Ar control-flag +.Pa pam_unix +.Op Ar options +.Sh DESCRIPTION +The +.Ux +authentication service module for PAM, +.Nm +provides functionality for three PAM categories: +authentication, +account management, and password management. +In terms of the +.Ar module-type +parameter, they are the +.Dq Li auth , +.Dq Li account , +and +.Dq Li password +features. +It also provides a null function for session management. +.Ss Ux Ss Authentication Module +The +.Ux +authentication component +provides functions to verify the identity of a user +.Pq Fn pam_sm_authenticate , +which obtains the relevant +.Xr passwd 5 +entry. +It prompts the user for a password +and verifies that this is correct with +.Xr crypt 3 . +.Pp +The following options may be passed to the authentication module: +.Bl -tag -width ".Cm use_first_pass" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm use_first_pass +If the authentication module +is not the first in the stack, +and a previous module +obtained the user's password, +that password is used +to authenticate the user. +If this fails, +the authentication module returns failure +without prompting the user for a password. +This option has no effect +if the authentication module +is the first in the stack, +or if no previous modules +obtained the user's password. +.It Cm try_first_pass +This option is similar to the +.Cm use_first_pass +option, +except that if the previously obtained password fails, +the user is prompted for another password. +.It Cm auth_as_self +This option will require the user +to authenticate himself as the user +given by +.Xr getlogin 2 , +not as the account they are attempting to access. +This is primarily for services like +.Xr su 1 , +where the user's ability to retype +their own password +might be deemed sufficient. +.It Cm nullok +If the password database +has no password +for the entity being authenticated, +then this option +will forgo password prompting, +and silently allow authentication to succeed. +.It Cm local_pass +Use only the local password database, +even if NIS is in use. +This will cause an authentication failure +if the system is configured +to only use NIS. +.It Cm nis_pass +Use only the NIS password database. +This will cause an authentication failure +if the system is not configured +to use NIS. +.El +.Ss Ux Ss Account Management Module +The +.Ux +account management component +provides a function to perform account management, +.Fn pam_sm_acct_mgmt . +The function verifies +that the authenticated user +is allowed to log into the local user account +by checking the following criteria: +.Bl -dash -offset indent +.It +locked status of the account compatible with +.Xr pw 8 +.Cm lock ; +.It +the password expiry date from +.Xr passwd 5 ; +.It +.Xr login.conf 5 +restrictions on the remote host, login time, and tty. +.El +.Pp +The following options may be passed to the management module: +.Bl -tag -width ".Cm use_first_pass" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.El +.Ss Ux Ss Password Management Module +The +.Ux +password management component +provides a function to perform password management, +.Fn pam_sm_chauthtok . +The function changes +the user's password. +.Pp +The following options may be passed to the password module: +.Bl -tag -width ".Cm use_first_pass" +.It Cm debug +.Xr syslog 3 +debugging information at +.Dv LOG_DEBUG +level. +.It Cm no_warn +suppress warning messages to the user. +These messages include +reasons why the user's +authentication attempt was declined. +.It Cm local_pass +forces the password module +to change a local password +in favour of a NIS one. +.It Cm nis_pass +forces the password module +to change a NIS password +in favour of a local one. +.El +.Sh FILES +.Bl -tag -width ".Pa /etc/master.passwd" -compact +.It Pa /etc/master.passwd +default +.Ux +password database. +.El +.Sh SEE ALSO +.Xr passwd 1 , +.Xr getlogin 2 , +.Xr crypt 3 , +.Xr getpwent 3 , +.Xr syslog 3 , +.Xr nsswitch.conf 5 , +.Xr passwd 5 , +.Xr pam 8 , +.Xr pw 8 , +.Xr yp 8 diff --git a/lib/libpam/modules/pam_unix/pam_unix.c b/lib/libpam/modules/pam_unix/pam_unix.c new file mode 100644 index 0000000..ce309a7 --- /dev/null +++ b/lib/libpam/modules/pam_unix/pam_unix.c @@ -0,0 +1,471 @@ +/*- + * Copyright 1998 Juniper Networks, Inc. + * All rights reserved. + * Copyright (c) 2002-2003 Networks Associates Technology, Inc. + * All rights reserved. + * + * Portions of this software was developed for the FreeBSD Project by + * ThinkSec AS and NAI Labs, the Security Research Division of Network + * Associates, Inc. under DARPA/SPAWAR contract N66001-01-C-8035 + * ("CBOSS"), as part of the DARPA CHATS research program. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. The name of the author may not be used to endorse or promote + * products derived from this software without specific prior written + * permission. + * + * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#include <sys/cdefs.h> +__FBSDID("$FreeBSD$"); + +#include <sys/param.h> +#include <sys/socket.h> +#include <sys/time.h> +#include <netinet/in.h> +#include <arpa/inet.h> + +#include <login_cap.h> +#include <netdb.h> +#include <pwd.h> +#include <stdlib.h> +#include <string.h> +#include <stdio.h> +#include <syslog.h> +#include <unistd.h> + +#include <libutil.h> + +#ifdef YP +#include <ypclnt.h> +#endif + +#define PAM_SM_AUTH +#define PAM_SM_ACCOUNT +#define PAM_SM_PASSWORD + +#include <security/pam_appl.h> +#include <security/pam_modules.h> +#include <security/pam_mod_misc.h> + +#define PASSWORD_HASH "md5" +#define DEFAULT_WARN (2L * 7L * 86400L) /* Two weeks */ +#define SALTSIZE 32 + +#define LOCKED_PREFIX "*LOCKED*" +#define LOCKED_PREFIX_LEN (sizeof(LOCKED_PREFIX) - 1) + +static void makesalt(char []); + +static char password_hash[] = PASSWORD_HASH; + +#define PAM_OPT_LOCAL_PASS "local_pass" +#define PAM_OPT_NIS_PASS "nis_pass" + +char *tempname = NULL; + +/* + * authentication management + */ +PAM_EXTERN int +pam_sm_authenticate(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + login_cap_t *lc; + struct passwd *pwd; + int retval; + const char *pass, *user, *realpw, *prompt; + + if (openpam_get_option(pamh, PAM_OPT_AUTH_AS_SELF)) { + pwd = getpwnam(getlogin()); + } else { + retval = pam_get_user(pamh, &user, NULL); + if (retval != PAM_SUCCESS) + return (retval); + pwd = getpwnam(user); + } + + PAM_LOG("Got user: %s", user); + + if (pwd != NULL) { + PAM_LOG("Doing real authentication"); + realpw = pwd->pw_passwd; + if (realpw[0] == '\0') { + if (!(flags & PAM_DISALLOW_NULL_AUTHTOK) && + openpam_get_option(pamh, PAM_OPT_NULLOK)) + return (PAM_SUCCESS); + realpw = "*"; + } + lc = login_getpwclass(pwd); + } else { + PAM_LOG("Doing dummy authentication"); + realpw = "*"; + lc = login_getclass(NULL); + } + prompt = login_getcapstr(lc, "passwd_prompt", NULL, NULL); + retval = pam_get_authtok(pamh, PAM_AUTHTOK, &pass, prompt); + login_close(lc); + if (retval != PAM_SUCCESS) + return (retval); + PAM_LOG("Got password"); + if (strcmp(crypt(pass, realpw), realpw) == 0) + return (PAM_SUCCESS); + + PAM_VERBOSE_ERROR("UNIX authentication refused"); + return (PAM_AUTH_ERR); +} + +PAM_EXTERN int +pam_sm_setcred(pam_handle_t *pamh __unused, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + + return (PAM_SUCCESS); +} + +/* + * account management + */ +PAM_EXTERN int +pam_sm_acct_mgmt(pam_handle_t *pamh, int flags __unused, + int argc __unused, const char *argv[] __unused) +{ + struct addrinfo hints, *res; + struct passwd *pwd; + struct timeval tp; + login_cap_t *lc; + time_t warntime; + int retval; + const char *user; + const void *rhost, *tty; + char rhostip[MAXHOSTNAMELEN] = ""; + + retval = pam_get_user(pamh, &user, NULL); + if (retval != PAM_SUCCESS) + return (retval); + + if (user == NULL || (pwd = getpwnam(user)) == NULL) + return (PAM_SERVICE_ERR); + + PAM_LOG("Got user: %s", user); + + retval = pam_get_item(pamh, PAM_RHOST, &rhost); + if (retval != PAM_SUCCESS) + return (retval); + + retval = pam_get_item(pamh, PAM_TTY, &tty); + if (retval != PAM_SUCCESS) + return (retval); + + if (*pwd->pw_passwd == '\0' && + (flags & PAM_DISALLOW_NULL_AUTHTOK) != 0) + return (PAM_NEW_AUTHTOK_REQD); + + if (strncmp(pwd->pw_passwd, LOCKED_PREFIX, LOCKED_PREFIX_LEN) == 0) + return (PAM_AUTH_ERR); + + lc = login_getpwclass(pwd); + if (lc == NULL) { + PAM_LOG("Unable to get login class for user %s", user); + return (PAM_SERVICE_ERR); + } + + PAM_LOG("Got login_cap"); + + if (pwd->pw_change || pwd->pw_expire) + gettimeofday(&tp, NULL); + + /* + * Check pw_expire before pw_change - no point in letting the + * user change the password on an expired account. + */ + + if (pwd->pw_expire) { + warntime = login_getcaptime(lc, "warnexpire", + DEFAULT_WARN, DEFAULT_WARN); + if (tp.tv_sec >= pwd->pw_expire) { + login_close(lc); + return (PAM_ACCT_EXPIRED); + } else if (pwd->pw_expire - tp.tv_sec < warntime && + (flags & PAM_SILENT) == 0) { + pam_error(pamh, "Warning: your account expires on %s", + ctime(&pwd->pw_expire)); + } + } + + retval = PAM_SUCCESS; + if (pwd->pw_change) { + warntime = login_getcaptime(lc, "warnpassword", + DEFAULT_WARN, DEFAULT_WARN); + if (tp.tv_sec >= pwd->pw_change) { + retval = PAM_NEW_AUTHTOK_REQD; + } else if (pwd->pw_change - tp.tv_sec < warntime && + (flags & PAM_SILENT) == 0) { + pam_error(pamh, "Warning: your password expires on %s", + ctime(&pwd->pw_change)); + } + } + + /* + * From here on, we must leave retval untouched (unless we + * know we're going to fail), because we need to remember + * whether we're supposed to return PAM_SUCCESS or + * PAM_NEW_AUTHTOK_REQD. + */ + + if (rhost && *(const char *)rhost != '\0') { + memset(&hints, 0, sizeof(hints)); + hints.ai_family = AF_UNSPEC; + if (getaddrinfo(rhost, NULL, &hints, &res) == 0) { + getnameinfo(res->ai_addr, res->ai_addrlen, + rhostip, sizeof(rhostip), NULL, 0, + NI_NUMERICHOST); + } + if (res != NULL) + freeaddrinfo(res); + } + + /* + * Check host / tty / time-of-day restrictions + */ + + if (!auth_hostok(lc, rhost, rhostip) || + !auth_ttyok(lc, tty) || + !auth_timeok(lc, time(NULL))) + retval = PAM_AUTH_ERR; + + login_close(lc); + + return (retval); +} + +/* + * password management + * + * standard Unix and NIS password changing + */ +PAM_EXTERN int +pam_sm_chauthtok(pam_handle_t *pamh, int flags, + int argc __unused, const char *argv[] __unused) +{ +#ifdef YP + struct ypclnt *ypclnt; + const void *yp_domain, *yp_server; +#endif + char salt[SALTSIZE + 1]; + login_cap_t * lc; + struct passwd *pwd, *old_pwd; + const char *user, *old_pass, *new_pass; + char *encrypted; + int pfd, tfd, retval; + + if (openpam_get_option(pamh, PAM_OPT_AUTH_AS_SELF)) + pwd = getpwnam(getlogin()); + else { + retval = pam_get_user(pamh, &user, NULL); + if (retval != PAM_SUCCESS) + return (retval); + pwd = getpwnam(user); + } + + if (pwd == NULL) + return (PAM_AUTHTOK_RECOVERY_ERR); + + PAM_LOG("Got user: %s", user); + + if (flags & PAM_PRELIM_CHECK) { + + PAM_LOG("PRELIM round"); + + if (getuid() == 0 && + (pwd->pw_fields & _PWF_SOURCE) == _PWF_FILES) + /* root doesn't need the old password */ + return (pam_set_item(pamh, PAM_OLDAUTHTOK, "")); +#ifdef YP + if (getuid() == 0 && + (pwd->pw_fields & _PWF_SOURCE) == _PWF_NIS) { + + yp_domain = yp_server = NULL; + (void)pam_get_data(pamh, "yp_domain", &yp_domain); + (void)pam_get_data(pamh, "yp_server", &yp_server); + + ypclnt = ypclnt_new(yp_domain, "passwd.byname", yp_server); + if (ypclnt == NULL) + return (PAM_BUF_ERR); + + if (ypclnt_connect(ypclnt) == -1) { + ypclnt_free(ypclnt); + return (PAM_SERVICE_ERR); + } + + retval = ypclnt_havepasswdd(ypclnt); + ypclnt_free(ypclnt); + if (retval == 1) + return (pam_set_item(pamh, PAM_OLDAUTHTOK, "")); + else if (retval == -1) + return (PAM_SERVICE_ERR); + } +#endif + if (pwd->pw_passwd[0] == '\0' + && openpam_get_option(pamh, PAM_OPT_NULLOK)) { + /* + * No password case. XXX Are we giving too much away + * by not prompting for a password? + * XXX check PAM_DISALLOW_NULL_AUTHTOK + */ + old_pass = ""; + } else { + retval = pam_get_authtok(pamh, + PAM_OLDAUTHTOK, &old_pass, NULL); + if (retval != PAM_SUCCESS) + return (retval); + } + PAM_LOG("Got old password"); + /* always encrypt first */ + encrypted = crypt(old_pass, pwd->pw_passwd); + if (old_pass[0] == '\0' && + !openpam_get_option(pamh, PAM_OPT_NULLOK)) + return (PAM_PERM_DENIED); + if (strcmp(encrypted, pwd->pw_passwd) != 0) + return (PAM_PERM_DENIED); + } + else if (flags & PAM_UPDATE_AUTHTOK) { + PAM_LOG("UPDATE round"); + + retval = pam_get_authtok(pamh, + PAM_OLDAUTHTOK, &old_pass, NULL); + if (retval != PAM_SUCCESS) + return (retval); + PAM_LOG("Got old password"); + + /* get new password */ + for (;;) { + retval = pam_get_authtok(pamh, + PAM_AUTHTOK, &new_pass, NULL); + if (retval != PAM_TRY_AGAIN) + break; + pam_error(pamh, "Mismatch; try again, EOF to quit."); + } + PAM_LOG("Got new password"); + if (retval != PAM_SUCCESS) { + PAM_VERBOSE_ERROR("Unable to get new password"); + return (retval); + } + + if (getuid() != 0 && new_pass[0] == '\0' && + !openpam_get_option(pamh, PAM_OPT_NULLOK)) + return (PAM_PERM_DENIED); + + if ((old_pwd = pw_dup(pwd)) == NULL) + return (PAM_BUF_ERR); + + pwd->pw_change = 0; + lc = login_getclass(pwd->pw_class); + if (login_setcryptfmt(lc, password_hash, NULL) == NULL) + openpam_log(PAM_LOG_ERROR, + "can't set password cipher, relying on default"); + login_close(lc); + makesalt(salt); + pwd->pw_passwd = crypt(new_pass, salt); +#ifdef YP + switch (old_pwd->pw_fields & _PWF_SOURCE) { + case _PWF_FILES: +#endif + retval = PAM_SERVICE_ERR; + if (pw_init(NULL, NULL)) + openpam_log(PAM_LOG_ERROR, "pw_init() failed"); + else if ((pfd = pw_lock()) == -1) + openpam_log(PAM_LOG_ERROR, "pw_lock() failed"); + else if ((tfd = pw_tmp(-1)) == -1) + openpam_log(PAM_LOG_ERROR, "pw_tmp() failed"); + else if (pw_copy(pfd, tfd, pwd, old_pwd) == -1) + openpam_log(PAM_LOG_ERROR, "pw_copy() failed"); + else if (pw_mkdb(pwd->pw_name) == -1) + openpam_log(PAM_LOG_ERROR, "pw_mkdb() failed"); + else + retval = PAM_SUCCESS; + pw_fini(); +#ifdef YP + break; + case _PWF_NIS: + yp_domain = yp_server = NULL; + (void)pam_get_data(pamh, "yp_domain", &yp_domain); + (void)pam_get_data(pamh, "yp_server", &yp_server); + ypclnt = ypclnt_new(yp_domain, + "passwd.byname", yp_server); + if (ypclnt == NULL) { + retval = PAM_BUF_ERR; + } else if (ypclnt_connect(ypclnt) == -1 || + ypclnt_passwd(ypclnt, pwd, old_pass) == -1) { + openpam_log(PAM_LOG_ERROR, "%s", ypclnt->error); + retval = PAM_SERVICE_ERR; + } else { + retval = PAM_SUCCESS; + } + ypclnt_free(ypclnt); + break; + default: + openpam_log(PAM_LOG_ERROR, "unsupported source 0x%x", + pwd->pw_fields & _PWF_SOURCE); + retval = PAM_SERVICE_ERR; + } +#endif + free(old_pwd); + } + else { + /* Very bad juju */ + retval = PAM_ABORT; + PAM_LOG("Illegal 'flags'"); + } + + return (retval); +} + +/* Mostly stolen from passwd(1)'s local_passwd.c - markm */ + +static unsigned char itoa64[] = /* 0 ... 63 => ascii - 64 */ + "./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz"; + +static void +to64(char *s, long v, int n) +{ + while (--n >= 0) { + *s++ = itoa64[v&0x3f]; + v >>= 6; + } +} + +/* Salt suitable for traditional DES and MD5 */ +void +makesalt(char salt[SALTSIZE]) +{ + int i; + + /* These are not really random numbers, they are just + * numbers that change to thwart construction of a + * dictionary. This is exposed to the public. + */ + for (i = 0; i < SALTSIZE; i += 4) + to64(&salt[i], arc4random(), 4); + salt[SALTSIZE] = '\0'; +} + +PAM_MODULE_ENTRY("pam_unix"); |