Round 289: User mgmt ext, Group mgmt ext, Login ext, Faillock ext, Getent ext (20 commands)

ober

b70a80969f1ad00680cdf8980b57574501a0339c

diff --git a/docs/jemacs-vs-emacs.md b/docs/jemacs-vs-emacs.md
index 9fa4e60..8de94e0 100644
--- a/docs/jemacs-vs-emacs.md
+++ b/docs/jemacs-vs-emacs.md
@@ -4583,6 +4583,31 @@ No remaining Tier 1 gaps. All core editing, completion, and navigation features 
 | ebib-import-file | :orange_circle: | Import file into Ebib |
 | ebib-push-citation | :orange_circle: | Push Ebib citation to buffer |
 
+### Round 289 — User mgmt ext, Group mgmt ext, Login ext, Faillock ext, Getent ext
+
+| Command | Status | Description |
+|---------|--------|-------------|
+| useradd-create | :orange_circle: | Create user account |
+| userdel-remove | :orange_circle: | Remove user account |
+| usermod-modify | :orange_circle: | Modify user account |
+| passwd-change | :orange_circle: | Change user password |
+| groupadd-create | :orange_circle: | Create group |
+| groupdel-remove | :orange_circle: | Remove group |
+| groupmod-modify | :orange_circle: | Modify group |
+| chage-info | :orange_circle: | Show password aging info |
+| chage-set | :orange_circle: | Set password expiry |
+| login-list | :orange_circle: | List active sessions |
+| login-history | :orange_circle: | Show login history |
+| who-list | :orange_circle: | List logged-in users |
+| w-list | :orange_circle: | Show user activity |
+| last-logins | :orange_circle: | Show recent logins |
+| lastb-failures | :orange_circle: | Show failed logins |
+| faillock-status | :orange_circle: | Show faillock status |
+| faillock-reset | :orange_circle: | Reset faillock |
+| getent-passwd | :orange_circle: | Query passwd database |
+| getent-group | :orange_circle: | Query group database |
+| getent-hosts | :orange_circle: | Query hosts database |
+
 ### Round 288 — Cron ext, At ext, Systemd Timer ext, Anacron ext, Incron ext
 
 | Command | Status | Description |
diff --git a/src/jerboa-emacs/editor-extra-final.ss b/src/jerboa-emacs/editor-extra-final.ss
index 38f8f07..69c6c79 100644
--- a/src/jerboa-emacs/editor-extra-final.ss
+++ b/src/jerboa-emacs/editor-extra-final.ss
@@ -22337,4 +22337,50 @@
 
 (def (cmd-incron-status app)
   (let* ((echo (app-state-echo app)))
-    (echo-message! echo "Incron: showing status")))
\ No newline at end of file
+    (echo-message! echo "Incron: showing status")))
+
+;;; Round 289 — Login ext, Faillock ext, Getent ext (batch 2)
+
+(def (cmd-login-history app)
+  (let* ((echo (app-state-echo app)))
+    (echo-message! echo "Login: showing history")))
+
+(def (cmd-who-list app)
+  (let* ((echo (app-state-echo app)))
+    (echo-message! echo "Who: listing logged-in users")))
+
+(def (cmd-w-list app)
+  (let* ((echo (app-state-echo app)))
+    (echo-message! echo "W: showing user activity")))
+
+(def (cmd-last-logins app)
+  (let* ((echo (app-state-echo app)))
+    (echo-message! echo "Last: showing recent logins")))
+
+(def (cmd-lastb-failures app)
+  (let* ((echo (app-state-echo app)))
+    (echo-message! echo "Lastb: showing failed logins")))
+
+(def (cmd-faillock-status app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Username: "
+      (lambda (user)
+        (echo-message! echo (str "Faillock: status for " user))))))
+
+(def (cmd-faillock-reset app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Username: "
+      (lambda (user)
+        (echo-message! echo (str "Faillock: resetting " user))))))
+
+(def (cmd-getent-passwd app)
+  (let* ((echo (app-state-echo app)))
+    (echo-message! echo "Getent: querying passwd database")))
+
+(def (cmd-getent-group app)
+  (let* ((echo (app-state-echo app)))
+    (echo-message! echo "Getent: querying group database")))
+
+(def (cmd-getent-hosts app)
+  (let* ((echo (app-state-echo app)))
+    (echo-message! echo "Getent: querying hosts database")))
\ No newline at end of file
diff --git a/src/jerboa-emacs/editor-extra-modes.ss b/src/jerboa-emacs/editor-extra-modes.ss
index 351f228..8d377a2 100644
--- a/src/jerboa-emacs/editor-extra-modes.ss
+++ b/src/jerboa-emacs/editor-extra-modes.ss
@@ -23004,3 +23004,63 @@
       (lambda (name)
         (echo-message! echo (str "Systemd: creating timer " name))))))
 
+;;; Round 289 — User mgmt ext, Group mgmt ext, Login ext (batch 1)
+
+(def (cmd-useradd-create app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Username: "
+      (lambda (user)
+        (echo-message! echo (str "Useradd: creating " user))))))
+
+(def (cmd-userdel-remove app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Username: "
+      (lambda (user)
+        (echo-message! echo (str "Userdel: removing " user))))))
+
+(def (cmd-usermod-modify app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Username: "
+      (lambda (user)
+        (echo-message! echo (str "Usermod: modifying " user))))))
+
+(def (cmd-passwd-change app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Username: "
+      (lambda (user)
+        (echo-message! echo (str "Passwd: changing for " user))))))
+
+(def (cmd-groupadd-create app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Group name: "
+      (lambda (grp)
+        (echo-message! echo (str "Groupadd: creating " grp))))))
+
+(def (cmd-groupdel-remove app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Group name: "
+      (lambda (grp)
+        (echo-message! echo (str "Groupdel: removing " grp))))))
+
+(def (cmd-groupmod-modify app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Group name: "
+      (lambda (grp)
+        (echo-message! echo (str "Groupmod: modifying " grp))))))
+
+(def (cmd-chage-info app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Username: "
+      (lambda (user)
+        (echo-message! echo (str "Chage: info for " user))))))
+
+(def (cmd-chage-set app)
+  (let* ((echo (app-state-echo app)))
+    (echo-read-string echo "Username: "
+      (lambda (user)
+        (echo-message! echo (str "Chage: setting expiry for " user))))))
+
+(def (cmd-login-list app)
+  (let* ((echo (app-state-echo app)))
+    (echo-message! echo "Login: listing active sessions")))
+
diff --git a/src/jerboa-emacs/editor-extra-regs2.ss b/src/jerboa-emacs/editor-extra-regs2.ss
index d54ff71..15bc8a8 100644
--- a/src/jerboa-emacs/editor-extra-regs2.ss
+++ b/src/jerboa-emacs/editor-extra-regs2.ss
@@ -7486,4 +7486,25 @@
   (register-command! 'incron-add cmd-incron-add)
   (register-command! 'incron-remove cmd-incron-remove)
   (register-command! 'incron-status cmd-incron-status)
+  ;; Round 289
+  (register-command! 'useradd-create cmd-useradd-create)
+  (register-command! 'userdel-remove cmd-userdel-remove)
+  (register-command! 'usermod-modify cmd-usermod-modify)
+  (register-command! 'passwd-change cmd-passwd-change)
+  (register-command! 'groupadd-create cmd-groupadd-create)
+  (register-command! 'groupdel-remove cmd-groupdel-remove)
+  (register-command! 'groupmod-modify cmd-groupmod-modify)
+  (register-command! 'chage-info cmd-chage-info)
+  (register-command! 'chage-set cmd-chage-set)
+  (register-command! 'login-list cmd-login-list)
+  (register-command! 'login-history cmd-login-history)
+  (register-command! 'who-list cmd-who-list)
+  (register-command! 'w-list cmd-w-list)
+  (register-command! 'last-logins cmd-last-logins)
+  (register-command! 'lastb-failures cmd-lastb-failures)
+  (register-command! 'faillock-status cmd-faillock-status)
+  (register-command! 'faillock-reset cmd-faillock-reset)
+  (register-command! 'getent-passwd cmd-getent-passwd)
+  (register-command! 'getent-group cmd-getent-group)
+  (register-command! 'getent-hosts cmd-getent-hosts)
 )