summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorThorsten Kukuk <kukuk@suse.com>2024-11-19 10:53:28 +0100
committerDamien Miller <djm@mindrot.org>2024-12-02 16:55:36 +0100
commit96b64056c812620014b65371a9e3ac86bfcd08d5 (patch)
tree0469d398c8ff4589f8440ae9f92dc0e2e91c9166
parentupstream: unbreak (diff)
downloadopenssh-96b64056c812620014b65371a9e3ac86bfcd08d5.tar.xz
openssh-96b64056c812620014b65371a9e3ac86bfcd08d5.zip
Add wtmpdb support as Y2038 safe wtmp replacement
-rw-r--r--Makefile.in5
-rw-r--r--configure.ac42
-rw-r--r--loginrec.c74
-rw-r--r--loginrec.h3
4 files changed, 119 insertions, 5 deletions
diff --git a/Makefile.in b/Makefile.in
index 389e5d9cb..2fcd8aa1f 100644
--- a/Makefile.in
+++ b/Makefile.in
@@ -60,6 +60,7 @@ GSSLIBS=@GSSLIBS@
SSHDLIBS=@SSHDLIBS@
LIBEDIT=@LIBEDIT@
LIBFIDO2=@LIBFIDO2@
+LIBWTMPDB=@LIBWTMPDB@
AR=@AR@
AWK=@AWK@
RANLIB=@RANLIB@
@@ -234,10 +235,10 @@ sshd$(EXEEXT): libssh.a $(LIBCOMPAT) $(SSHDOBJS)
$(LD) -o $@ $(SSHDOBJS) $(LDFLAGS) -lssh -lopenbsd-compat $(SSHDLIBS) $(LIBS) $(CHANNELLIBS)
sshd-session$(EXEEXT): libssh.a $(LIBCOMPAT) $(SSHD_SESSION_OBJS)
- $(LD) -o $@ $(SSHD_SESSION_OBJS) $(LDFLAGS) -lssh -lopenbsd-compat $(SSHDLIBS) $(LIBS) $(GSSLIBS) $(K5LIBS) $(CHANNELLIBS)
+ $(LD) -o $@ $(SSHD_SESSION_OBJS) $(LDFLAGS) -lssh -lopenbsd-compat $(SSHDLIBS) $(LIBS) $(GSSLIBS) $(K5LIBS) $(CHANNELLIBS) $(LIBWTMPDB)
sshd-auth$(EXEEXT): libssh.a $(LIBCOMPAT) $(SSHD_AUTH_OBJS)
- $(LD) -o $@ $(SSHD_AUTH_OBJS) $(LDFLAGS) -lssh -lopenbsd-compat $(SSHDLIBS) $(LIBS) $(GSSLIBS) $(K5LIBS) $(CHANNELLIBS)
+ $(LD) -o $@ $(SSHD_AUTH_OBJS) $(LDFLAGS) -lssh -lopenbsd-compat $(SSHDLIBS) $(LIBS) $(GSSLIBS) $(K5LIBS) $(CHANNELLIBS) $(LIBWTMPDB)
scp$(EXEEXT): $(LIBCOMPAT) libssh.a $(SCP_OBJS)
$(LD) -o $@ $(SCP_OBJS) $(LDFLAGS) -lssh -lopenbsd-compat $(LIBS)
diff --git a/configure.ac b/configure.ac
index 3728187c4..018277287 100644
--- a/configure.ac
+++ b/configure.ac
@@ -1772,6 +1772,48 @@ AC_ARG_WITH([libedit],
fi ]
)
+# Check whether user wants wtmpdb support
+WTMPDB_MSG="no"
+AC_ARG_WITH([wtmpdb],
+ [ --with-wtmpdb[[=PATH]] Enable wtmpdb support for sshd],
+ [ if test "x$withval" != "xno" ; then
+ if test "x$withval" = "xyes" ; then
+ if test "x$PKGCONFIG" != "xno"; then
+ AC_MSG_CHECKING([if $PKGCONFIG knows about wtmpdb])
+ if "$PKGCONFIG" libwtmpdb; then
+ AC_MSG_RESULT([yes])
+ use_pkgconfig_for_libwtmpdb=yes
+ else
+ AC_MSG_RESULT([no])
+ fi
+ fi
+ else
+ CPPFLAGS="$CPPFLAGS -I${withval}/include"
+ if test -n "${rpath_opt}"; then
+ LDFLAGS="-L${withval}/lib ${rpath_opt}${withval}/lib ${LDFLAGS}"
+ else
+ LDFLAGS="-L${withval}/lib ${LDFLAGS}"
+ fi
+ fi
+ if test "x$use_pkgconfig_for_libwtmpdb" = "xyes"; then
+ LIBWTMPDB=`$PKGCONFIG --libs libwtmpdb`
+ CPPFLAGS="$CPPFLAGS `$PKGCONFIG --cflags libwtmpdb`"
+ else
+ LIBWTMPDB="-lwtmpdb"
+ fi
+ OTHERLIBS=`echo $LIBWTMPDB | sed 's/-lwtmpdb//'`
+ AC_CHECK_LIB([wtmpdb], [wtmpdb_login],
+ [ AC_DEFINE([USE_WTMPDB], [1], [Use libwtmpdb for sshd])
+ WTMPDB_MSG="yes"
+ AC_SUBST([LIBWTMPDB])
+ ],
+ [ AC_MSG_ERROR([libwtmpdb not found]) ],
+ [ $OTHERLIBS ]
+ )
+ fi ]
+)
+
+
AUDIT_MODULE=none
AC_ARG_WITH([audit],
[ --with-audit=module Enable audit support (modules=debug,bsm,linux)],
diff --git a/loginrec.c b/loginrec.c
index 4afe136f4..c4a9bd485 100644
--- a/loginrec.c
+++ b/loginrec.c
@@ -166,6 +166,10 @@
# include <util.h>
#endif
+#ifdef USE_WTMPDB
+# include <wtmpdb.h>
+#endif
+
/**
** prototypes for helper functions in this file
**/
@@ -186,6 +190,9 @@ int wtmp_write_entry(struct logininfo *li);
int wtmpx_write_entry(struct logininfo *li);
int lastlog_write_entry(struct logininfo *li);
int syslogin_write_entry(struct logininfo *li);
+#ifdef USE_WTMPDB
+int wtmpdb_write_entry(struct logininfo *li);
+#endif
int getlast_entry(struct logininfo *li);
int lastlog_get_entry(struct logininfo *li);
@@ -446,6 +453,9 @@ login_write(struct logininfo *li)
#ifdef USE_WTMPX
wtmpx_write_entry(li);
#endif
+#ifdef USE_WTMPDB
+ wtmpdb_write_entry(li);
+#endif
#ifdef CUSTOM_SYS_AUTH_RECORD_LOGIN
if (li->type == LTYPE_LOGIN &&
!sys_auth_record_login(li->username,li->hostname,li->line,
@@ -1391,6 +1401,64 @@ wtmpx_get_entry(struct logininfo *li)
}
#endif /* USE_WTMPX */
+#ifdef USE_WTMPDB
+static int
+wtmpdb_perform_login(struct logininfo *li)
+{
+ uint64_t login_time = li->tv_sec * ((uint64_t) 1000000ULL) +
+ li->tv_usec;
+ const char *tty;
+
+ if (strncmp(li->line, "/dev/", 5) == 0)
+ tty = &(li->line[5]);
+ else
+ tty = li->line;
+
+ li->wtmpdb_id = wtmpdb_login(NULL, USER_PROCESS, li->username,
+ login_time, tty, li->hostname, 0, 0);
+
+ if (li->wtmpdb_id < 0)
+ return (0);
+
+ return (1);
+}
+
+static int
+wtmpdb_perform_logout(struct logininfo *li)
+{
+ uint64_t logout_time = li->tv_sec * ((uint64_t) 1000000ULL) +
+ li->tv_usec;
+
+ if (li->wtmpdb_id == 0) {
+ const char *tty;
+
+ if (strncmp(li->line, "/dev/", 5) == 0)
+ tty = &(li->line[5]);
+ else
+ tty = li->line;
+
+ li->wtmpdb_id = wtmpdb_get_id(NULL, tty, NULL);
+ }
+ wtmpdb_logout(NULL, li->wtmpdb_id, logout_time, NULL);
+
+ return (1);
+}
+
+int
+wtmpdb_write_entry(struct logininfo *li)
+{
+ switch(li->type) {
+ case LTYPE_LOGIN:
+ return (wtmpdb_perform_login(li));
+ case LTYPE_LOGOUT:
+ return (wtmpdb_perform_logout(li));
+ default:
+ logit("%s: invalid type field", __func__);
+ return (0);
+ }
+}
+#endif
+
/**
** Low-level libutil login() functions
**/
@@ -1529,10 +1597,10 @@ lastlog_write_entry(struct logininfo *li)
strlcpy(last.ll_host, li->hostname,
MIN_SIZEOF(last.ll_host, li->hostname));
last.ll_time = li->tv_sec;
-
+
if (!lastlog_openseek(li, &fd, O_RDWR|O_CREAT))
return (0);
-
+
/* write the entry */
if (atomicio(vwrite, fd, &last, sizeof(last)) != sizeof(last)) {
close(fd);
@@ -1540,7 +1608,7 @@ lastlog_write_entry(struct logininfo *li)
LASTLOG_FILE, strerror(errno));
return (0);
}
-
+
close(fd);
return (1);
default:
diff --git a/loginrec.h b/loginrec.h
index 02bceb604..62ddd01d5 100644
--- a/loginrec.h
+++ b/loginrec.h
@@ -79,6 +79,9 @@ struct logininfo {
unsigned int tv_sec;
unsigned int tv_usec;
union login_netinfo hostaddr; /* caller's host address(es) */
+#ifdef USE_WTMPDB
+ int64_t wtmpdb_id; /* ID for wtmpdb_logout */
+#endif
}; /* struct logininfo */
/*