]> git.ipfire.org Git - thirdparty/systemd.git/commitdiff
homed: don't block logins into accounts with future change time
authorLennart Poettering <lennart@poettering.net>
Wed, 2 Sep 2020 14:35:22 +0000 (16:35 +0200)
committerLennart Poettering <lennart@poettering.net>
Mon, 21 Sep 2020 16:02:31 +0000 (18:02 +0200)
This might happen if the system clock is wrong, and we should allow
access in this case (though certainly log about it).

src/home/pam_systemd_home.c
src/shared/user-record-show.c
src/shared/user-record.c

index 13b164ecfc07ebabc23bef7d8515ff27f9af6108..db182dc999786801c86643d8f9c01872ea4cef21 100644 (file)
@@ -846,8 +846,8 @@ _public_ PAM_EXTERN int pam_sm_acct_mgmt(
         switch (r) {
 
         case -ESTALE:
-                (void) pam_prompt(handle, PAM_ERROR_MSG, NULL, "User record is newer than current system time, prohibiting access.");
-                return PAM_ACCT_EXPIRED;
+                pam_syslog(handle, LOG_WARNING, "User record for '%s' is newer than current system time, assuming incorrect system clock, allowing access.", ur->user_name);
+                break;
 
         case -ENOLCK:
                 (void) pam_prompt(handle, PAM_ERROR_MSG, NULL, "User record is blocked, prohibiting access.");
index 33787c083f571f0d1448733008d1ad2fe73d08b4..7839f6c2b8f738c59ad5144f5e3c77bd1debad1d 100644 (file)
@@ -45,6 +45,10 @@ void user_record_show(UserRecord *hr, bool show_full_group_info) {
         if (hr->last_change_usec != USEC_INFINITY) {
                 char buf[FORMAT_TIMESTAMP_MAX];
                 printf(" Last Change: %s\n", format_timestamp(buf, sizeof(buf), hr->last_change_usec));
+
+                if (hr->last_change_usec > now(CLOCK_REALTIME))
+                        printf("              %sModification time lies in the future, system clock wrong?%s\n",
+                               ansi_highlight_yellow(), ansi_normal());
         }
 
         if (hr->last_password_change_usec != USEC_INFINITY &&
@@ -56,10 +60,6 @@ void user_record_show(UserRecord *hr, bool show_full_group_info) {
         r = user_record_test_blocked(hr);
         switch (r) {
 
-        case -ESTALE:
-                printf("    Login OK: %sno%s (last change time is in the future)\n", ansi_highlight_red(), ansi_normal());
-                break;
-
         case -ENOLCK:
                 printf("    Login OK: %sno%s (record is locked)\n", ansi_highlight_red(), ansi_normal());
                 break;
@@ -72,10 +72,11 @@ void user_record_show(UserRecord *hr, bool show_full_group_info) {
                 printf("    Login OK: %sno%s (record not valid anymore))\n", ansi_highlight_red(), ansi_normal());
                 break;
 
+        case -ESTALE:
         default: {
                 usec_t y;
 
-                if (r < 0) {
+                if (r < 0 && r != -ESTALE) {
                         errno = -r;
                         printf("    Login OK: %sno%s (%m)\n", ansi_highlight_red(), ansi_normal());
                         break;
index e04df4d78b41f52af7187a2800785c0081dfb445..a80c4932d153c51c7634425c3ec56a908b39c91e 100644 (file)
@@ -2025,19 +2025,20 @@ int user_record_test_blocked(UserRecord *h) {
 
         assert(h);
 
-        n = now(CLOCK_REALTIME);
-        if (h->last_change_usec != UINT64_MAX &&
-            h->last_change_usec > n) /* Don't allow log ins when the record is from the future */
-                return -ESTALE;
-
         if (h->locked > 0)
                 return -ENOLCK;
 
+        n = now(CLOCK_REALTIME);
+
         if (h->not_before_usec != UINT64_MAX && n < h->not_before_usec)
                 return -EL2HLT;
         if (h->not_after_usec != UINT64_MAX && n > h->not_after_usec)
                 return -EL3HLT;
 
+        if (h->last_change_usec != UINT64_MAX &&
+            h->last_change_usec > n) /* Complain during log-ins when the record is from the future */
+                return -ESTALE;
+
         return 0;
 }