about summary refs log tree commit diff
path: root/login
diff options
context:
space:
mode:
authorFlorian Weimer <fweimer@redhat.com>2019-08-05 15:54:10 +0200
committerFlorian Weimer <fweimer@redhat.com>2019-08-05 15:55:05 +0200
commit1a7fe2ebe52b3c8bf465d1756e69452d05c1c103 (patch)
tree1d32b2e5a5c55d660354cefb1b02918b62127300 /login
parenta6c1ce778e5c05a2e6925883b410157ef47654fd (diff)
downloadglibc-1a7fe2ebe52b3c8bf465d1756e69452d05c1c103.tar.gz
glibc-1a7fe2ebe52b3c8bf465d1756e69452d05c1c103.tar.xz
glibc-1a7fe2ebe52b3c8bf465d1756e69452d05c1c103.zip
login: Remove utmp backend jump tables [BZ #23518]
There is just one file-based implementation, so this dispatch
mechanism is unnecessary.  Instead of the vtable pointer
__libc_utmp_jump_table, use a non-negative file_fd as the indicator
that the backend is initialized.
Diffstat (limited to 'login')
-rw-r--r--login/getutent_r.c108
-rw-r--r--login/getutid_r.c2
-rw-r--r--login/getutline_r.c2
-rw-r--r--login/updwtmp.c2
-rw-r--r--login/utmp-private.h29
-rw-r--r--login/utmp_file.c89
-rw-r--r--login/utmpname.c3
7 files changed, 52 insertions, 183 deletions
diff --git a/login/getutent_r.c b/login/getutent_r.c
index 98ffc5d1c6..fd13be8a1e 100644
--- a/login/getutent_r.c
+++ b/login/getutent_r.c
@@ -23,115 +23,16 @@
 
 #include "utmp-private.h"
 
-
-/* Functions defined here.  */
-static int setutent_unknown (void);
-static int getutent_r_unknown (struct utmp *buffer, struct utmp **result);
-static int getutid_r_unknown (const struct utmp *line, struct utmp *buffer,
-			      struct utmp **result);
-static int getutline_r_unknown (const struct utmp *id, struct utmp *buffer,
-				struct utmp **result);
-static struct utmp *pututline_unknown (const struct utmp *data);
-static void endutent_unknown (void);
-
-/* Initial Jump table.  */
-const struct utfuncs __libc_utmp_unknown_functions =
-{
-  setutent_unknown,
-  getutent_r_unknown,
-  getutid_r_unknown,
-  getutline_r_unknown,
-  pututline_unknown,
-  endutent_unknown,
-  NULL
-};
-
-/* Currently selected backend.  */
-const struct utfuncs *__libc_utmp_jump_table = &__libc_utmp_unknown_functions;
-
 /* We need to protect the opening of the file.  */
 __libc_lock_define_initialized (, __libc_utmp_lock attribute_hidden)
 
 
-static int
-setutent_unknown (void)
-{
-  int result;
-
-  result = (*__libc_utmp_file_functions.setutent) ();
-  if (result)
-    __libc_utmp_jump_table = &__libc_utmp_file_functions;
-
-  return result;
-}
-
-
-static int
-getutent_r_unknown (struct utmp *buffer, struct utmp **result)
-{
-  /* The backend was not yet initialized.  */
-  if (setutent_unknown ())
-    return (*__libc_utmp_jump_table->getutent_r) (buffer, result);
-
-  /* Not available.  */
-  *result = NULL;
-  return -1;
-}
-
-
-static int
-getutid_r_unknown (const struct utmp *id, struct utmp *buffer,
-		   struct utmp **result)
-{
-  /* The backend was not yet initialized.  */
-  if (setutent_unknown ())
-    return (*__libc_utmp_jump_table->getutid_r) (id, buffer, result);
-
-  /* Not available.  */
-  *result = NULL;
-  return -1;
-}
-
-
-static int
-getutline_r_unknown (const struct utmp *line, struct utmp *buffer,
-		     struct utmp **result)
-{
-  /* The backend was not yet initialized.  */
-  if (setutent_unknown ())
-    return (*__libc_utmp_jump_table->getutline_r) (line, buffer, result);
-
-  /* Not available.  */
-  *result = NULL;
-  return -1;
-}
-
-
-static struct utmp *
-pututline_unknown (const struct utmp *data)
-{
-  /* The backend was not yet initialized.  */
-  if (setutent_unknown ())
-    return (*__libc_utmp_jump_table->pututline) (data);
-
-  /* Not available.  */
-  return NULL;
-}
-
-
-static void
-endutent_unknown (void)
-{
-  /* Nothing to do.  */
-}
-
-
 void
 __setutent (void)
 {
   __libc_lock_lock (__libc_utmp_lock);
 
-  (*__libc_utmp_jump_table->setutent) ();
+  __libc_setutent ();
 
   __libc_lock_unlock (__libc_utmp_lock);
 }
@@ -145,7 +46,7 @@ __getutent_r (struct utmp *buffer, struct utmp **result)
 
   __libc_lock_lock (__libc_utmp_lock);
 
-  retval = (*__libc_utmp_jump_table->getutent_r) (buffer, result);
+  retval = __libc_getutent_r (buffer, result);
 
   __libc_lock_unlock (__libc_utmp_lock);
 
@@ -162,7 +63,7 @@ __pututline (const struct utmp *data)
 
   __libc_lock_lock (__libc_utmp_lock);
 
-  buffer = (*__libc_utmp_jump_table->pututline) (data);
+  buffer = __libc_pututline (data);
 
   __libc_lock_unlock (__libc_utmp_lock);
 
@@ -177,8 +78,7 @@ __endutent (void)
 {
   __libc_lock_lock (__libc_utmp_lock);
 
-  (*__libc_utmp_jump_table->endutent) ();
-  __libc_utmp_jump_table = &__libc_utmp_unknown_functions;
+  __libc_endutent ();
 
   __libc_lock_unlock (__libc_utmp_lock);
 }
diff --git a/login/getutid_r.c b/login/getutid_r.c
index 34ea61d8f4..86ffc85b01 100644
--- a/login/getutid_r.c
+++ b/login/getutid_r.c
@@ -49,7 +49,7 @@ __getutid_r (const struct utmp *id, struct utmp *buffer, struct utmp **result)
 
   __libc_lock_lock (__libc_utmp_lock);
 
-  retval = (*__libc_utmp_jump_table->getutid_r) (id, buffer, result);
+  retval = __libc_getutid_r (id, buffer, result);
 
   __libc_lock_unlock (__libc_utmp_lock);
 
diff --git a/login/getutline_r.c b/login/getutline_r.c
index 110b89e438..f03255dbbd 100644
--- a/login/getutline_r.c
+++ b/login/getutline_r.c
@@ -36,7 +36,7 @@ __getutline_r (const struct utmp *line, struct utmp *buffer,
 
   __libc_lock_lock (__libc_utmp_lock);
 
-  retval = (*__libc_utmp_jump_table->getutline_r) (line, buffer, result);
+  retval = __libc_getutline_r (line, buffer, result);
 
   __libc_lock_unlock (__libc_utmp_lock);
 
diff --git a/login/updwtmp.c b/login/updwtmp.c
index b9bccd9b67..387e580828 100644
--- a/login/updwtmp.c
+++ b/login/updwtmp.c
@@ -29,7 +29,7 @@ __updwtmp (const char *wtmp_file, const struct utmp *utmp)
 {
   const char *file_name = TRANSFORM_UTMP_FILE_NAME (wtmp_file);
 
-  (*__libc_utmp_file_functions.updwtmp) (file_name, utmp);
+  __libc_updwtmp (file_name, utmp);
 }
 libc_hidden_def (__updwtmp)
 weak_alias (__updwtmp, updwtmp)
diff --git a/login/utmp-private.h b/login/utmp-private.h
index a82a923657..d60461d644 100644
--- a/login/utmp-private.h
+++ b/login/utmp-private.h
@@ -24,24 +24,17 @@
 #include <utmp.h>
 #include <libc-lock.h>
 
-/* The structure describing the functions in a backend.  */
-struct utfuncs
-{
-  int (*setutent) (void);
-  int (*getutent_r) (struct utmp *, struct utmp **);
-  int (*getutid_r) (const struct utmp *, struct utmp *, struct utmp **);
-  int (*getutline_r) (const struct utmp *, struct utmp *, struct utmp **);
-  struct utmp *(*pututline) (const struct utmp *);
-  void (*endutent) (void);
-  int (*updwtmp) (const char *, const struct utmp *);
-};
-
-/* The tables from the services.  */
-extern const struct utfuncs __libc_utmp_file_functions attribute_hidden;
-extern const struct utfuncs __libc_utmp_unknown_functions attribute_hidden;
-
-/* Currently selected backend.  */
-extern const struct utfuncs *__libc_utmp_jump_table attribute_hidden;
+/* These functions check for initialization, but not perform any
+   locking.  */
+int __libc_setutent (void) attribute_hidden;
+int __libc_getutent_r (struct utmp *, struct utmp **) attribute_hidden;
+int __libc_getutid_r (const struct utmp *, struct utmp *, struct utmp **)
+  attribute_hidden;
+int __libc_getutline_r (const struct utmp *, struct utmp *, struct utmp **)
+  attribute_hidden;
+struct utmp *__libc_pututline (const struct utmp *) attribute_hidden;
+void __libc_endutent (void) attribute_hidden;
+int __libc_updwtmp (const char *, const struct utmp *) attribute_hidden;
 
 /* Current file name.  */
 extern const char *__libc_utmp_file_name attribute_hidden;
diff --git a/login/utmp_file.c b/login/utmp_file.c
index b19d3caf0d..cb8a02825c 100644
--- a/login/utmp_file.c
+++ b/login/utmp_file.c
@@ -105,37 +105,12 @@ static void timeout_handler (int signum) {};
     alarm (old_timeout);						      \
 } while (0)
 
-
-/* Functions defined here.  */
-static int setutent_file (void);
-static int getutent_r_file (struct utmp *buffer, struct utmp **result);
-static int getutid_r_file (const struct utmp *key, struct utmp *buffer,
-			   struct utmp **result);
-static int getutline_r_file (const struct utmp *key, struct utmp *buffer,
-			     struct utmp **result);
-static struct utmp *pututline_file (const struct utmp *data);
-static void endutent_file (void);
-static int updwtmp_file (const char *file, const struct utmp *utmp);
-
-/* Jump table for file functions.  */
-const struct utfuncs __libc_utmp_file_functions =
-{
-  setutent_file,
-  getutent_r_file,
-  getutid_r_file,
-  getutline_r_file,
-  pututline_file,
-  endutent_file,
-  updwtmp_file
-};
-
-
 #ifndef TRANSFORM_UTMP_FILE_NAME
 # define TRANSFORM_UTMP_FILE_NAME(file_name) (file_name)
 #endif
 
-static int
-setutent_file (void)
+int
+__libc_setutent (void)
 {
   if (file_fd < 0)
     {
@@ -166,15 +141,19 @@ setutent_file (void)
   return 1;
 }
 
+/* Preform initialization if necessary.  */
+static bool
+maybe_setutent (void)
+{
+  return file_fd >= 0 || __libc_setutent ();
+}
 
-static int
-getutent_r_file (struct utmp *buffer, struct utmp **result)
+int
+__libc_getutent_r (struct utmp *buffer, struct utmp **result)
 {
   ssize_t nbytes;
 
-  assert (file_fd >= 0);
-
-  if (file_offset == -1l)
+  if (!maybe_setutent () || file_offset == -1l)
     {
       /* Not available.  */
       *result = NULL;
@@ -279,13 +258,11 @@ unlock_return:
 
 /* For implementing this function we don't use the getutent_r function
    because we can avoid the reposition on every new entry this way.  */
-static int
-getutid_r_file (const struct utmp *id, struct utmp *buffer,
-		struct utmp **result)
+int
+__libc_getutid_r (const struct utmp *id, struct utmp *buffer,
+		  struct utmp **result)
 {
-  assert (file_fd >= 0);
-
-  if (file_offset == -1l)
+  if (!maybe_setutent () || file_offset == -1l)
     {
       *result = NULL;
       return -1;
@@ -309,13 +286,11 @@ getutid_r_file (const struct utmp *id, struct utmp *buffer,
 
 /* For implementing this function we don't use the getutent_r function
    because we can avoid the reposition on every new entry this way.  */
-static int
-getutline_r_file (const struct utmp *line, struct utmp *buffer,
-		  struct utmp **result)
+int
+__libc_getutline_r (const struct utmp *line, struct utmp *buffer,
+		    struct utmp **result)
 {
-  assert (file_fd >= 0);
-
-  if (file_offset == -1l)
+  if (!maybe_setutent () || file_offset == -1l)
     {
       *result = NULL;
       return -1;
@@ -361,15 +336,16 @@ unlock_return:
 }
 
 
-static struct utmp *
-pututline_file (const struct utmp *data)
+struct utmp *
+__libc_pututline (const struct utmp *data)
 {
+  if (!maybe_setutent ())
+    return NULL;
+
   struct utmp buffer;
   struct utmp *pbuf;
   int found;
 
-  assert (file_fd >= 0);
-
   if (! file_writable)
     {
       /* We must make the file descriptor writable before going on.  */
@@ -467,18 +443,19 @@ pututline_file (const struct utmp *data)
 }
 
 
-static void
-endutent_file (void)
+void
+__libc_endutent (void)
 {
-  assert (file_fd >= 0);
-
-  __close_nocancel_nostatus (file_fd);
-  file_fd = -1;
+  if (file_fd >= 0)
+    {
+      __close_nocancel_nostatus (file_fd);
+      file_fd = -1;
+    }
 }
 
 
-static int
-updwtmp_file (const char *file, const struct utmp *utmp)
+int
+__libc_updwtmp (const char *file, const struct utmp *utmp)
 {
   int result = -1;
   off64_t offset;
diff --git a/login/utmpname.c b/login/utmpname.c
index c3da183d5b..8f94b19caf 100644
--- a/login/utmpname.c
+++ b/login/utmpname.c
@@ -42,8 +42,7 @@ __utmpname (const char *file)
   __libc_lock_lock (__libc_utmp_lock);
 
   /* Close the old file.  */
-  (*__libc_utmp_jump_table->endutent) ();
-  __libc_utmp_jump_table = &__libc_utmp_unknown_functions;
+  __libc_endutent ();
 
   if (strcmp (file, __libc_utmp_file_name) != 0)
     {