summaryrefslogtreecommitdiff
path: root/modules/pammodutil
diff options
context:
space:
mode:
authorAndrew G. Morgan <morgan@kernel.org>2001-12-09 22:15:11 +0000
committerAndrew G. Morgan <morgan@kernel.org>2001-12-09 22:15:11 +0000
commitda67a7d6126846939fd43b1ddb5aa8c06ee09301 (patch)
treee9df9e69023b0e8584ee85cd8a44daf210bee75d /modules/pammodutil
parentcb7734d4080f3673a34594ee4c6e7b02dcd89f33 (diff)
Relevant BUGIDs: 490938
Purpose of commit: new feature Commit summary: --------------- Added libpammodutil and link it with every module as its built. The issue here is that there is a lot of code that the various modules use in common, and this staic library can be used to help make this code more maintainable. I do not intend to make this library dynamic. Especially right now, as I want to be free to chop and change the API and don't want to deal with revision control and third party modules. This checkin makes the pam_rhost_auth module make some use of this new library. I don't intend to add support for any other module prior to releasing 0.76.
Diffstat (limited to 'modules/pammodutil')
-rw-r--r--modules/pammodutil/Makefile53
-rw-r--r--modules/pammodutil/README15
-rw-r--r--modules/pammodutil/include/security/_pam_modutil.h33
-rw-r--r--modules/pammodutil/modutil_cleanup.c16
-rw-r--r--modules/pammodutil/modutil_getpwnam.c80
-rw-r--r--modules/pammodutil/modutil_getpwuid.c80
-rw-r--r--modules/pammodutil/pammodutil.h22
7 files changed, 299 insertions, 0 deletions
diff --git a/modules/pammodutil/Makefile b/modules/pammodutil/Makefile
new file mode 100644
index 00000000..a97388ef
--- /dev/null
+++ b/modules/pammodutil/Makefile
@@ -0,0 +1,53 @@
+#
+# $Id$
+#
+#
+
+include ../../Make.Rules
+
+LIBNAME=libpammodutil
+
+# ---------------------------------------------
+
+dummy: all
+
+# ---------------------------------------------
+
+CFLAGS += $(PIC) $(STATIC) $(MOREFLAGS) \
+ -DLIBPAM_VERSION_MAJOR=$(MAJOR_REL) \
+ -DLIBPAM_VERSION_MINOR=$(MINOR_REL)
+
+# all the object files we care about
+LIBOBJECTS = modutil_cleanup.o modutil_getpwnam.o modutil_getpwuid.o
+
+# static library name
+LIBSTATIC = $(LIBNAME).a
+
+SLIBOBJECTS = $(addprefix static/,$(LIBOBJECTS) $(STATICOBJ))
+
+# ---------------------------------------------
+## rules
+
+all: dirs $(LIBSTATIC) ../../Make.Rules
+
+dirs:
+ $(MKDIR) static
+
+static/%.o : %.c
+ $(CC) $(CFLAGS) $(CPPFLAGS) $(TARGET_ARCH) -c $< -o $@
+
+$(LIBSTATIC): $(SLIBOBJECTS)
+ ar cr $@ $(SLIBOBJECTS)
+ $(RANLIB) $@
+
+install:
+ @echo "at this time, we're not installing $(LIBSTATIC)"
+
+remove:
+ @echo "at this time, there is nothing to remove"
+
+clean:
+ rm -f a.out core *~ static/*.o
+ rm -f *.a *.o
+ if [ -d dynamic ]; then rmdir dynamic ; fi
+ if [ -d static ]; then rmdir static ; fi
diff --git a/modules/pammodutil/README b/modules/pammodutil/README
new file mode 100644
index 00000000..241f83a7
--- /dev/null
+++ b/modules/pammodutil/README
@@ -0,0 +1,15 @@
+$Id$
+
+This is a libarary of routines for use by modules. The routines seem
+to have a common use for modules, but are not part of libpam and never
+will be. They are also a convenient layer of abstraction for providing
+thread-safe functions that may require use of pam_handle_t 'data'
+items to make their thread-safeness tied to the use of a single
+pam_handle_t per thread.
+
+Functions provided so far are all listed in
+
+ include/security/_pam_modutil.h
+
+.
+
diff --git a/modules/pammodutil/include/security/_pam_modutil.h b/modules/pammodutil/include/security/_pam_modutil.h
new file mode 100644
index 00000000..af8a7ae1
--- /dev/null
+++ b/modules/pammodutil/include/security/_pam_modutil.h
@@ -0,0 +1,33 @@
+#ifndef _PAM_MODUTIL_H
+#define _PAM_MODUTIL_H
+
+/*
+ * $Id$
+ *
+ * This file is a list of handy libc wrappers that attempt to provide some
+ * thread-safe and other convenient functionality to modules in a form that
+ * is common, but not dynamically linked with yet another dynamic pam
+ * library extension.
+ *
+ * A number of these functions reserve space in a pam_[sg]et_data item.
+ * In all cases, the name of the item is prefixed with "_pammodutil_*".
+ *
+ * On systems that simply can't support thread safe programming, these
+ * functions don't support it either - sorry.
+ *
+ * Copyright (c) 2001 Andrew Morgan <morgan@kernel.org>
+ */
+
+#include <pwd.h>
+#include <sys/types.h>
+
+extern struct passwd *_pammodutil_getpwnam(pam_handle_t *pamh,
+ const char *user);
+
+extern struct passwd *_pammodutil_getpwuid(pam_handle_t *pamh,
+ uid_t uid);
+
+extern void _pammodutil_cleanup(pam_handle_t *pamh, void *data,
+ int error_status);
+
+#endif /* _PAM_MODUTIL_H */
diff --git a/modules/pammodutil/modutil_cleanup.c b/modules/pammodutil/modutil_cleanup.c
new file mode 100644
index 00000000..e95d6100
--- /dev/null
+++ b/modules/pammodutil/modutil_cleanup.c
@@ -0,0 +1,16 @@
+/*
+ * $Id$
+ *
+ * This function provides a common pam_set_data() friendly version of free().
+ */
+
+#include "pammodutil.h"
+
+void _pammodutil_cleanup(pam_handle_t *pamh, void *data, int error_status)
+{
+ if (data) {
+ /* junk it */
+ (void) free(data);
+ }
+}
+
diff --git a/modules/pammodutil/modutil_getpwnam.c b/modules/pammodutil/modutil_getpwnam.c
new file mode 100644
index 00000000..287dc065
--- /dev/null
+++ b/modules/pammodutil/modutil_getpwnam.c
@@ -0,0 +1,80 @@
+/*
+ * $Id$
+ *
+ * This function provides a thread safer version of getpwnam() for use
+ * with PAM modules that care about this sort of thing.
+ *
+ * XXX - or at least it should provide a thread-safe alternative.
+ */
+
+#include "pammodutil.h"
+
+#include <pwd.h>
+#include <stdlib.h>
+
+struct passwd *_pammodutil_getpwnam(pam_handle_t *pamh, const char *user)
+{
+#ifdef HAVE_GETPWNAM_R
+
+ void *buffer=NULL;
+ size_t length = PWD_INITIAL_LENGTH;
+
+ do {
+ int status;
+ void *new_buffer;
+ struct passwd *result = NULL;
+
+ new_buffer = realloc(buffer, sizeof(struct passwd) + length);
+ if (new_buffer == NULL) {
+
+ D(("out of memory"));
+
+ /* no memory for the user - so delete the memory */
+ if (buffer) {
+ free(buffer);
+ }
+ return NULL;
+ }
+ buffer = new_buffer;
+
+ /* make the re-entrant call to get the pwd structure */
+ status = getpwnam_r(user, buffer,
+ sizeof(struct passwd) + (char *) buffer,
+ length, &result);
+ if (!status && result) {
+ status = pam_set_data(pamh, "_pammodutil_getpwnam", result,
+ _pammodutil_cleanup);
+ if (status == PAM_SUCCESS) {
+ D(("success"));
+ return result;
+ }
+
+ D(("was unable to register the data item [%s]",
+ pam_strerror(pamh, status)));
+
+ free(buffer);
+ return NULL;
+
+ }
+
+ length <<= 1;
+
+ } while (length < PWD_ABSURD_PWD_LENGTH);
+
+ D(("pwd structure took %u bytes or so of memory",
+ length+sizeof(struct passwd)));
+
+ free(buffer);
+ return NULL;
+
+#else /* ie. ifndef HAVE_GETPWNAM_R */
+
+ /*
+ * Sorry, there does not appear to be a reentrant version of
+ * getpwnam(). So, we use the standard libc function.
+ */
+
+ return getpwnam(user);
+
+#endif /* def HAVE_GETPWNAM_R */
+}
diff --git a/modules/pammodutil/modutil_getpwuid.c b/modules/pammodutil/modutil_getpwuid.c
new file mode 100644
index 00000000..e200dd1e
--- /dev/null
+++ b/modules/pammodutil/modutil_getpwuid.c
@@ -0,0 +1,80 @@
+/*
+ * $Id$
+ *
+ * This function provides a thread safer version of getpwuid() for use
+ * with PAM modules that care about this sort of thing.
+ *
+ * XXX - or at least it should provide a thread-safe alternative.
+ */
+
+#include "pammodutil.h"
+
+#include <pwd.h>
+#include <stdlib.h>
+
+struct passwd *_pammodutil_getpwuid(pam_handle_t *pamh, uid_t uid)
+{
+#ifdef HAVE_GETPWNAM_R
+
+ void *buffer=NULL;
+ size_t length = PWD_INITIAL_LENGTH;
+
+ do {
+ int status;
+ void *new_buffer;
+ struct passwd *result = NULL;
+
+ new_buffer = realloc(buffer, sizeof(struct passwd) + length);
+ if (new_buffer == NULL) {
+
+ D(("out of memory"));
+
+ /* no memory for the user - so delete the memory */
+ if (buffer) {
+ free(buffer);
+ }
+ return NULL;
+ }
+ buffer = new_buffer;
+
+ /* make the re-entrant call to get the pwd structure */
+ status = getpwuid_r(uid, buffer,
+ sizeof(struct passwd) + (char *) buffer,
+ length, &result);
+ if (!status && result) {
+ status = pam_set_data(pamh, "_pammodutil_getpwuid", result,
+ _pammodutil_cleanup);
+ if (status == PAM_SUCCESS) {
+ D(("success"));
+ return result;
+ }
+
+ D(("was unable to register the data item [%s]",
+ pam_strerror(pamh, status)));
+
+ free(buffer);
+ return NULL;
+
+ }
+
+ length <<= 1;
+
+ } while (length < PWD_ABSURD_PWD_LENGTH);
+
+ D(("pwd structure took %u bytes or so of memory",
+ length+sizeof(struct passwd)));
+
+ free(buffer);
+ return NULL;
+
+#else /* ie. ifndef HAVE_GETPWNAM_R */
+
+ /*
+ * Sorry, there does not appear to be a reentrant version of
+ * getpwnam(). So, we use the standard libc function.
+ */
+
+ return getpwuid(uid);
+
+#endif /* def HAVE_GETPWNAM_R */
+}
diff --git a/modules/pammodutil/pammodutil.h b/modules/pammodutil/pammodutil.h
new file mode 100644
index 00000000..efcc98e1
--- /dev/null
+++ b/modules/pammodutil/pammodutil.h
@@ -0,0 +1,22 @@
+#ifndef PAMMODUTIL_H
+#define PAMMODUTIL_H
+
+/*
+ * $Id$
+ *
+ * Copyright (c) 2001 Andrew Morgan <morgan@kernel.org>
+ */
+
+#include <security/_pam_aconf.h>
+#include <security/_pam_macros.h>
+#include <security/pam_modules.h>
+#include <security/_pam_modutil.h>
+
+#define PWD_INITIAL_LENGTH 0x100
+#define PWD_ABSURD_PWD_LENGTH 0x1000
+
+/* This is a simple cleanup, it just free()s the 'data' memory */
+extern void _pammodutil_cleanup(pam_handle_t *pamh, void *data,
+ int error_status);
+
+#endif /* PAMMODUTIL_H */