summaryrefslogtreecommitdiff
path: root/Linux-PAM/modules/pam_exec
diff options
context:
space:
mode:
Diffstat (limited to 'Linux-PAM/modules/pam_exec')
-rw-r--r--Linux-PAM/modules/pam_exec/README10
-rw-r--r--Linux-PAM/modules/pam_exec/pam_exec.884
-rw-r--r--Linux-PAM/modules/pam_exec/pam_exec.8.xml28
-rw-r--r--Linux-PAM/modules/pam_exec/pam_exec.c65
4 files changed, 155 insertions, 32 deletions
diff --git a/Linux-PAM/modules/pam_exec/README b/Linux-PAM/modules/pam_exec/README
index 8ff9a742..f0845205 100644
--- a/Linux-PAM/modules/pam_exec/README
+++ b/Linux-PAM/modules/pam_exec/README
@@ -6,6 +6,11 @@ DESCRIPTION
pam_exec is a PAM module that can be used to run an external command.
+The child's environment is set to the current PAM environment list, as returned
+by pam_getenvlist(3) In addition, the following PAM items are exported as
+environment variables: PAM_RHOST, PAM_RUSER, PAM_SERVICE, PAM_TTY, and PAM_USER
+.
+
OPTIONS
debug
@@ -16,6 +21,11 @@ log=file
The output of the command is appended to file
+quiet
+
+ Per default pam_exec.so will echo the exit status of the external command
+ if it fails. Specifying this option will suppress the message.
+
seteuid
Per default pam_exec.so will execute the external command with the real
diff --git a/Linux-PAM/modules/pam_exec/pam_exec.8 b/Linux-PAM/modules/pam_exec/pam_exec.8
index ae8f8a46..9ac2ccbb 100644
--- a/Linux-PAM/modules/pam_exec/pam_exec.8
+++ b/Linux-PAM/modules/pam_exec/pam_exec.8
@@ -1,35 +1,55 @@
.\" Title: pam_exec
.\" Author:
-.\" Generator: DocBook XSL Stylesheets v1.70.1 <http://docbook.sf.net/>
-.\" Date: 06/09/2006
-.\" Manual: Linux\-PAM Manual
-.\" Source: Linux\-PAM Manual
+.\" Generator: DocBook XSL Stylesheets v1.73.1 <http://docbook.sf.net/>
+.\" Date: 02/04/2008
+.\" Manual: Linux-PAM Manual
+.\" Source: Linux-PAM Manual
.\"
-.TH "PAM_EXEC" "8" "06/09/2006" "Linux\-PAM Manual" "Linux\-PAM Manual"
+.TH "PAM_EXEC" "8" "02/04/2008" "Linux-PAM Manual" "Linux\-PAM Manual"
.\" disable hyphenation
.nh
.\" disable justification (adjust text to left margin only)
.ad l
.SH "NAME"
-pam_exec \- PAM module which calls an external command
+pam_exec - PAM module which calls an external command
.SH "SYNOPSIS"
.HP 12
-\fBpam_exec.so\fR [debug] [seteuid] [log=\fIfile\fR] \fIcommand\fR [\fI...\fR]
+\fBpam_exec\.so\fR [debug] [seteuid] [quiet] [log=\fIfile\fR] \fIcommand\fR [\fI\.\.\.\fR]
.SH "DESCRIPTION"
.PP
-pam_exec is a PAM module that can be used to run an external command.
+pam_exec is a PAM module that can be used to run an external command\.
+.PP
+The child\'s environment is set to the current PAM environment list, as returned by
+\fBpam_getenvlist\fR(3)
+In addition, the following PAM items are exported as environment variables:
+\fIPAM_RHOST\fR,
+\fIPAM_RUSER\fR,
+\fIPAM_SERVICE\fR,
+\fIPAM_TTY\fR, and
+\fIPAM_USER\fR\.
.SH "OPTIONS"
.PP
-.TP 3n
+.PP
\fBdebug\fR
-Print debug information.
-.TP 3n
+.RS 4
+Print debug information\.
+.RE
+.PP
\fBlog=\fR\fB\fIfile\fR\fR
+.RS 4
The output of the command is appended to
\fIfile\fR
-.TP 3n
+.RE
+.PP
+\fBquiet\fR
+.RS 4
+Per default pam_exec\.so will echo the exit status of the external command if it fails\. Specifying this option will suppress the message\.
+.RE
+.PP
\fBseteuid\fR
-Per default pam_exec.so will execute the external command with the real user ID of the calling process. Specifying this option means the command is run with the effective user ID.
+.RS 4
+Per default pam_exec\.so will execute the external command with the real user ID of the calling process\. Specifying this option means the command is run with the effective user ID\.
+.RE
.SH "MODULE SERVICES PROVIDED"
.PP
The services
@@ -38,45 +58,53 @@ The services
\fBpassword\fR
and
\fBsession\fR
-are supported.
+are supported\.
.SH "RETURN VALUES"
.PP
-.TP 3n
+.PP
PAM_SUCCESS
-The external command runs successfull.
-.TP 3n
+.RS 4
+The external command runs successfull\.
+.RE
+.PP
PAM_SERVICE_ERR
-No argument or a wrong number of arguments were given.
-.TP 3n
+.RS 4
+No argument or a wrong number of arguments were given\.
+.RE
+.PP
PAM_SYSTEM_ERR
-A system error occured or the command to execute failed.
-.TP 3n
+.RS 4
+A system error occured or the command to execute failed\.
+.RE
+.PP
PAM_IGNORE
+.RS 4
\fBpam_setcred\fR
-was called, which does not execute the command.
+was called, which does not execute the command\.
+.RE
.SH "EXAMPLES"
.PP
Add the following line to
-\fI/etc/pam.d/passwd\fR
+\fI/etc/pam\.d/passwd\fR
to rebuild the NIS database after each local password change:
.sp
-.RS 3n
+.RS 4
.nf
- passwd optional pam_exec.so seteuid make \-C /var/yp
+ passwd optional pam_exec\.so seteuid make \-C /var/yp
.fi
.RE
.sp
This will execute the command
.sp
-.RS 3n
+.RS 4
.nf
make \-C /var/yp
.fi
.RE
.sp
-with effective user ID.
+with effective user ID\.
.SH "SEE ALSO"
.PP
@@ -85,4 +113,4 @@ with effective user ID.
\fBpam\fR(8)
.SH "AUTHOR"
.PP
-pam_exec was written by Thorsten Kukuk <kukuk@thkukuk.de>.
+pam_exec was written by Thorsten Kukuk <kukuk@thkukuk\.de>\.
diff --git a/Linux-PAM/modules/pam_exec/pam_exec.8.xml b/Linux-PAM/modules/pam_exec/pam_exec.8.xml
index 1e8bb0ba..f4dc1e15 100644
--- a/Linux-PAM/modules/pam_exec/pam_exec.8.xml
+++ b/Linux-PAM/modules/pam_exec/pam_exec.8.xml
@@ -25,6 +25,9 @@
seteuid
</arg>
<arg choice="opt">
+ quiet
+ </arg>
+ <arg choice="opt">
log=<replaceable>file</replaceable>
</arg>
<arg choice="plain">
@@ -45,6 +48,18 @@
an external command.
</para>
+ <para>
+ The child's environment is set to the current PAM environment list, as
+ returned by
+ <citerefentry>
+ <refentrytitle>pam_getenvlist</refentrytitle><manvolnum>3</manvolnum>
+ </citerefentry>
+ In addition, the following PAM items are
+ exported as environment variables: <emphasis>PAM_RHOST</emphasis>,
+ <emphasis>PAM_RUSER</emphasis>, <emphasis>PAM_SERVICE</emphasis>,
+ <emphasis>PAM_TTY</emphasis>, and <emphasis>PAM_USER</emphasis>.
+ </para>
+
</refsect1>
<refsect1 id="pam_exec-options">
@@ -78,6 +93,19 @@
<varlistentry>
<term>
+ <option>quiet</option>
+ </term>
+ <listitem>
+ <para>
+ Per default pam_exec.so will echo the exit status of the
+ external command if it fails.
+ Specifying this option will suppress the message.
+ </para>
+ </listitem>
+ </varlistentry>
+
+ <varlistentry>
+ <term>
<option>seteuid</option>
</term>
<listitem>
diff --git a/Linux-PAM/modules/pam_exec/pam_exec.c b/Linux-PAM/modules/pam_exec/pam_exec.c
index 34ba7404..766c0a06 100644
--- a/Linux-PAM/modules/pam_exec/pam_exec.c
+++ b/Linux-PAM/modules/pam_exec/pam_exec.c
@@ -59,11 +59,24 @@
#include <security/pam_modutil.h>
#include <security/pam_ext.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
call_exec (pam_handle_t *pamh, int argc, const char **argv)
{
int debug = 0;
int call_setuid = 0;
+ int quiet = 0;
int optargc;
const char *logfile = NULL;
pid_t pid;
@@ -85,6 +98,8 @@ call_exec (pam_handle_t *pamh, int argc, const char **argv)
logfile = &argv[optargc][4];
else if (strcasecmp (argv[optargc], "seteuid") == 0)
call_setuid = 1;
+ else if (strcasecmp (argv[optargc], "quiet") == 0)
+ quiet = 1;
else
break; /* Unknown option, assume program to execute. */
}
@@ -115,6 +130,7 @@ call_exec (pam_handle_t *pamh, int argc, const char **argv)
{
pam_syslog (pamh, LOG_ERR, "%s failed: exit code %d",
argv[optargc], WEXITSTATUS(status));
+ if (!quiet)
pam_error (pamh, _("%s failed: exit code %d"),
argv[optargc], WEXITSTATUS(status));
}
@@ -123,6 +139,7 @@ call_exec (pam_handle_t *pamh, int argc, const char **argv)
pam_syslog (pamh, LOG_ERR, "%s failed: caught signal %d%s",
argv[optargc], WTERMSIG(status),
WCOREDUMP(status) ? " (core dumped)" : "");
+ if (!quiet)
pam_error (pamh, _("%s failed: caught signal %d%s"),
argv[optargc], WTERMSIG(status),
WCOREDUMP(status) ? " (core dumped)" : "");
@@ -131,6 +148,7 @@ call_exec (pam_handle_t *pamh, int argc, const char **argv)
{
pam_syslog (pamh, LOG_ERR, "%s failed: unknown status 0x%x",
argv[optargc], status);
+ if (!quiet)
pam_error (pamh, _("%s failed: unknown status 0x%x"),
argv[optargc], status);
}
@@ -208,22 +226,61 @@ call_exec (pam_handle_t *pamh, int argc, const char **argv)
exit (ENOMEM);
for (i = 0; i < (argc - optargc); i++)
- arggv[i] = argv[i+optargc];
+ arggv[i] = strdup(argv[i+optargc]);
arggv[i] = NULL;
+ char **envlist, **tmp;
+ int envlen, nitems;
+
+ /*
+ * 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)
+ {
+ free(envlist);
+ pam_syslog (pamh, LOG_ERR, "realloc environment failed : %m");
+ exit (ENOMEM);
+ }
+ envlist = tmp;
+ for (i = 0; i < nitems; ++i)
+ {
+ const void *item;
+ char *envstr;
+
+ if (pam_get_item(pamh, env_items[i].item, &item) != PAM_SUCCESS || item == NULL)
+ continue;
+ asprintf(&envstr, "%s=%s", env_items[i].name, (const char *)item);
+ if (envstr == NULL)
+ {
+ free(envlist);
+ pam_syslog (pamh, LOG_ERR, "prepare environment failed : %m");
+ exit (ENOMEM);
+ }
+ envlist[envlen++] = envstr;
+ envlist[envlen] = NULL;
+ }
+
if (debug)
pam_syslog (pamh, LOG_DEBUG, "Calling %s ...", arggv[0]);
- if (execv (arggv[0], arggv) == -1)
+ if (execve (arggv[0], arggv, envlist) == -1)
{
int err = errno;
- pam_syslog (pamh, LOG_ERR, "execv(%s,...) failed: %m",
+ pam_syslog (pamh, LOG_ERR, "execve(%s,...) failed: %m",
arggv[0]);
+ free(envlist);
exit (err);
}
+ free(envlist);
exit (1); /* should never be reached. */
}
- return PAM_SYSTEM_ERR;
+ return PAM_SYSTEM_ERR; /* will never be reached. */
}
PAM_EXTERN int