- power::run_command: .stdout(Stdio::null()) — the pipe was never drained,
structurally fragile even if no current caller hits it.
- config: replace to_string_lossy() on relative wallpaper paths with
to_str() + log::warn, so non-UTF-8 paths are dropped cleanly instead
of being mangled into unopenable U+FFFD strings.
- main: require MOONGREET_DEBUG=1 to raise verbosity. Mere presence of
the var must not leak socket paths, usernames, and auth round counts
into the journal.
- sessions: parse Hidden= and NoDisplay= keys, skip entries marked true.
Keeps disabled or stub .desktop files out of the session dropdown.
- i18n test: assert four previously-missing string fields so future locales
cannot ship empty strings unnoticed.
- greeter: atomic check-and-set fingerprint_probe_initializing to keep a
fast user switch from spawning two parallel fprintd D-Bus inits.
- greeter: set_avatar_from_file decodes via gio::File::read_future +
Pixbuf::from_stream_at_scale_future inside glib::spawn_future_local;
shows default icon first, swaps on completion.
- greeter: cap MAX_WALLPAPER_FILE_SIZE at 10 MB and MAX_AVATAR_FILE_SIZE
at 5 MB to bound worst-case decode latency.
- config: apply the same symlink-rejection check to the Moonarch
wallpaper fallback that the user-configured path already uses.
- greeter: after login_worker returns, drop the cloned greetd socket
held in shared state so repeated failed logins do not leak FDs.
- attempt_login takes Zeroizing<String> by value, eliminating the redundant
Zeroizing::new(password.to_string()) that doubled the Rust-owned copy.
- Clear password_entry's internal buffer immediately after extracting the
password, shortening the window during which the GTK GString persists in
non-zeroizable libc memory.
The rule that grants the greeter user authorization for
org.freedesktop.login1.{reboot,power-off} lived only in the moonarch
repo and was never installed by any PKGBUILD. On a fresh install the
reboot/shutdown buttons silently failed because greetd's greeter
session is inactive in logind and polkit denies inactive sessions by
default.
Move the rule into the moongreet source tree where it belongs and
ship it via moongreet-git.
Greeter windows were only created at startup. Hotplugged monitors (e.g.
HDMI reconnect) would show no UI. Connect to the monitor ListModel's
items-changed signal to create greeter windows for newly added monitors.
Aligned with moonlock's hotplug fix using the same pattern adapted for
gtk4-layer-shell (ListModel) instead of session-lock (connect_monitor).
Wayland surfaces belong to exactly one output — mirroring is not an option.
Create one full greeter window per monitor via set_monitor(), with only the
first receiving KeyboardMode::Exclusive. Removes the old wallpaper-only
secondary windows. Matches moonlock's per-monitor pattern.
Layer-shell keyboard grab is only confirmed by the compositor at map
time. The previous realize-time grab_focus() could fire before the
compositor assigned keyboard input, causing intermittent input loss.
GTK4 does not reliably read /etc/xdg/gtk-4.0/settings.ini under greetd
without a settings daemon, falling back to default blue accent instead
of Colloid-Grey-Dark-Catppuccin.
Greeter used hardcoded colors (#1a1a2e, white, #ff6b6b) instead of
GTK theme variables, breaking theme consistency across the ecosystem.
Now uses @theme_bg_color, @theme_fg_color, @error_color etc. —
matching moonlock and moonset.
- Add 30s timeout with SIGKILL to power actions (adapted from moonset)
- Add 500ms minimum login response time against timing enumeration
- Cache GREETD_SOCK in GreeterState at startup
- Add [profile.release] with LTO, codegen-units=1, strip
- Add compressed="true" to GResource CSS/SVG entries
- Add SYNC comments to duplicated blur/background functions
- Add nix dependency for signal handling in power timeout
- Add zeroize dependency, wrap password in Zeroizing<String> from entry extraction
through to login_worker (prevents heap-resident plaintext)
- Add MAX_BLUR_DIMENSION (1920px) downscale before GPU blur to reduce 4K workload
- Wallpaper: use symlink_metadata + is_symlink rejection in greeter.rs and config.rs
- Avatar: add is_file() check, swap lookup order to ~/.face first (consistent with
moonlock/moonset)
- greetd errors: show generic fallback in UI, log raw PAM details at debug level only
- fprintd: validate device path prefix before creating D-Bus proxy
- Locale: cache detected locale via OnceLock (avoid repeated env/file reads)
Colloid-Catppuccin theme loaded via ~/.config/gtk-4.0/gtk.css at
PRIORITY_USER (800) was overriding moongreet's PRIORITY_APPLICATION (600),
causing avatar to lose its circular border-radius.
- Use STYLE_PROVIDER_PRIORITY_USER for app CSS provider
- Replace border-radius: 50% with 9999px (GTK4 CSS percentage quirk)
- Include missed Cargo.lock and PKGBUILD updates from v0.6.0
Fingerprint auth was missing because moongreet rejected multi-stage
auth_message sequences from greetd. With pam_fprintd.so in the PAM
stack, greetd sends non-secret prompts for fingerprint and secret
prompts for password — moongreet now handles both in a loop.
- Replace single-pass auth with multi-stage auth_message loop
- fprintd D-Bus probe (gio::DBusProxy) for UI feedback only
- Fingerprint label shown when device available and fingers enrolled
- 60s socket timeout when fingerprint available (pam_fprintd scan time)
- Config option: [appearance] fingerprint-enabled (default: true)
- Fix: password entry focus loss after auth error (grab_focus while
widget was insensitive — now re-enable before grab_focus)
GskBlurNode samples pixels outside texture bounds as transparent,
causing visible darkening at wallpaper edges. Fix renders the texture
with 3x-sigma padding before blur, then clips back to original size.
Symmetric fix with moonset v0.7.1.
Wallpaper is installed by moonarch to /usr/share/moonarch/wallpaper.jpg.
Embedding a 374K JPEG in the binary was redundant. Without a wallpaper
file, GTK background color (Catppuccin Mocha base) shows through and
wallpaper-only windows on secondary monitors are skipped.
Replace unwrap() calls with match-based error handling that falls back
to eprintln — prevents panic when running outside a systemd session.
Consistent with moonlock's logging init pattern.
Address all findings from quality, performance, and security audits:
- Filter greetd error descriptions consistently (security)
- Re-enable power buttons after failed action (UX bug)
- Narrow TOCTOU window in avatar loading via symlink_metadata (security)
- Allow @ in usernames for LDAP compatibility
- Eliminate unnecessary Vec allocation in passwd parsing
- Remove dead i18n field, annotate retained-for-future struct fields
- Fix if/if→if/else and noisy test output in power.rs
Replace CPU blur (image crate + disk cache + async orchestration) with
GPU blur via GskBlurNode — symmetric with moonlock and moonset.
Removes ~15 transitive dependencies and ~200 lines of caching code.
Gaussian blur applied at texture load time when `background-blur` is
set in the [appearance] section of moongreet.toml. Blur runs once,
result is shared across monitors.
- Rework load_background_texture(): use resources_lookup_data()/from_bytes()
for GResource path (no abort on missing resource), add 50 MB file size limit,
handle non-UTF-8 paths gracefully
- Filter error details to debug level only — warn! logs without internal details
to prevent system info leaking into journal
- Make debug logging opt-in via MOONGREET_DEBUG env var (default: Info)
- Truncate greetd error description in stale-session retry path using
MAX_GREETD_ERROR_LENGTH (matching show_greetd_error())
- Add 3 unit tests for load_background_texture edge cases
Replace env_logger file-based logging with systemd-journal-logger for
consistency with moonlock and native journalctl integration. Add debug-level
logging at all decision points: config loading, user/session detection,
avatar resolution, locale detection, IPC messages, login flow, and
persistence. No credentials are ever logged.
display_name() now returns only the first GECOS subfield (before comma)
instead of the full GECOS string with room numbers and phone extensions.
split_shell_words() returns None for trailing backslashes instead of
silently ignoring them.
Complete rewrite of the greetd greeter from Python/PyGObject to Rust/gtk4-rs
for consistency with moonset, single binary without Python runtime, and
improved security through Rust memory safety.
Modules: main, greeter, ipc, config, i18n, users, sessions, power
86 unit tests covering all modules including login_worker IPC flow.
Security hardening: shell-word splitting for exec_cmd, absolute path
validation for session binaries, session-name sanitization, absolute
loginctl path, atomic IPC writes.