]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
sd-login: add sd_uid_get_login_time interface #26574
authorThorsten Kukuk <kukuk@suse.com>
Fri, 24 Feb 2023 08:47:52 +0000 (09:47 +0100)
committerThorsten Kukuk <kukuk@suse.com>
Sat, 25 Feb 2023 15:14:11 +0000 (16:14 +0100)
man/sd_uid_get_state.xml
src/libsystemd/libsystemd.sym
src/libsystemd/sd-login/sd-login.c
src/systemd/sd-login.h

index 087a2d539d0ada267b2625b3b2a22424e8b1014a..e6cf77ff6992a7dfa3431ec01d4bbe2a9cd92014 100644 (file)
@@ -22,6 +22,7 @@
     <refname>sd_uid_get_sessions</refname>
     <refname>sd_uid_get_seats</refname>
     <refname>sd_uid_get_display</refname>
+    <refname>sd_uid_get_login_time</refname>
     <refpurpose>Determine login state of a specific Unix user ID</refpurpose>
   </refnamediv>
 
         <paramdef>char **<parameter>session</parameter></paramdef>
       </funcprototype>
     </funcsynopsis>
+
+    <funcprototype>
+       <funcdef>int <function>sd_uid_get_login_time</function></funcdef>
+       <paramdef>uid_t <parameter>uid</parameter></paramdef>
+       <paramdef>uint64_t *<parameter>usec</parameter></paramdef>
+    </funcprototype>
   </refsynopsisdiv>
 
   <refsect1>
     of the "primary" session of a user. If the user has graphical
     sessions, it will be the oldest graphical session. Otherwise, it
     will be the oldest open session.</para>
+
+    <para><function>sd_uid_get_login_time()</function> may be used to
+    determine the time the user's service manager has been invoked,
+    which is the time when the user's first active session, since which
+    they stayed logged in continuously, began. The <parameter>usec</parameter>
+    is in microseconds since the epoch (<constant>CLOCK_REALTIME</constant>).
+    This call will fail with <constant>-ENXIO</constant> if the user is not
+    currently logged in.</para>
   </refsect1>
 
   <refsect1>
     <title>Return Value</title>
 
-    <para>On success, <function>sd_uid_get_state()</function> returns 0 or a positive integer. If the test
-    succeeds, <function>sd_uid_is_on_seat()</function> returns a positive integer; if it fails, 0.
-    <function>sd_uid_get_sessions()</function> and <function>sd_uid_get_seats()</function> return the number
-    of entries in the returned arrays. <function>sd_uid_get_display()</function> returns a non-negative code
-    on success. On failure, these calls return a negative errno-style error code.</para>
+    <para>On success, <function>sd_uid_get_state()</function> and
+    <function>sd_uid_get_login_time()</function> returns 0 or a positive
+    integer. If the test succeeds, <function>sd_uid_is_on_seat()</function>
+    returns a positive integer; if it fails, 0. <function>sd_uid_get_sessions()</function>
+    and <function>sd_uid_get_seats()</function> return the number of entries
+    in the returned arrays. <function>sd_uid_get_display()</function>
+    returns a non-negative code on success. On failure, these calls return
+    a negative errno-style error code.</para>
 
     <refsect2>
       <title>Errors</title>
index 8b5edabb75eb4749000381a89318cdb5bab4b3a5..b54417f3d112bf9d938324e8d0e0ac5e28126633 100644 (file)
@@ -817,4 +817,5 @@ LIBSYSTEMD_254 {
 global:
         sd_session_get_username;
         sd_session_get_start_time;
+        sd_uid_get_login_time;
 } LIBSYSTEMD_253;
index 12cb4e67922370bc3d1e4eb133580ad67f33b06a..a81b21062a733089429551f4a9bd5c85a0e0e37f 100644 (file)
@@ -503,6 +503,36 @@ _public_ int sd_uid_get_display(uid_t uid, char **session) {
         return 0;
 }
 
+_public_ int sd_uid_get_login_time(uid_t uid, uint64_t *usec) {
+        _cleanup_free_ char *p = NULL, *s = NULL, *rt = NULL;
+        usec_t t;
+        int r;
+
+        assert_return(usec, -EINVAL);
+
+        r = file_of_uid(uid, &p);
+        if (r < 0)
+                return r;
+
+        r = parse_env_file(NULL, p, "STATE", &s, "REALTIME", &rt);
+        if (r == -ENOENT)
+                return -ENXIO;
+        if (r < 0)
+                return r;
+        if (isempty(s) || isempty(rt))
+                return -EIO;
+
+        if (!STR_IN_SET(s, "active", "online"))
+                return -ENXIO;
+
+        r = safe_atou64(rt, &t);
+        if (r < 0)
+                return r;
+
+        *usec = t;
+        return 0;
+}
+
 static int file_of_seat(const char *seat, char **_p) {
         char *p;
         int r;
index 526af34d376dc2b2db377edb5f7bc6ef0d407bf4..7246d9f472a5c83f826e1b5b7827735809ca6134 100644 (file)
@@ -130,6 +130,9 @@ int sd_uid_get_state(uid_t uid, char **state);
 /* Return primary session of user, if there is any */
 int sd_uid_get_display(uid_t uid, char **session);
 
+/* Determine the login time of user */
+int sd_uid_get_login_time(uid_t uid, uint64_t *usec);
+
 /* Return 1 if UID has session on seat. If require_active is true, this will
  * look for active sessions only. */
 int sd_uid_is_on_seat(uid_t uid, int require_active, const char *seat);