return fallback;
}
+static bool getenv_harder_bool(pam_handle_t *handle, const char *key, bool fallback) {
+ const char *v;
+ int r;
+
+ assert(handle);
+ assert(key);
+
+ v = getenv_harder(handle, key, NULL);
+ if (isempty(v))
+ return fallback;
+
+ r = parse_boolean(v);
+ if (r < 0) {
+ pam_syslog(handle, LOG_ERR, "Boolean environment variable value of '%s' is not valid: %s", key, v);
+ return fallback;
+ }
+
+ return r;
+}
+
static int update_environment(pam_handle_t *handle, const char *key, const char *value) {
int r;
_cleanup_(sd_bus_flush_close_unrefp) sd_bus *bus = NULL;
_cleanup_(user_record_unrefp) UserRecord *ur = NULL;
int session_fd = -EBADF, existing, r;
- bool debug = false, remote;
+ bool debug = false, remote, incomplete;
uint32_t vtnr = 0;
uid_t original_uid;
type = getenv_harder(handle, "XDG_SESSION_TYPE", type_pam);
class = getenv_harder(handle, "XDG_SESSION_CLASS", class_pam);
desktop = getenv_harder(handle, "XDG_SESSION_DESKTOP", desktop_pam);
+ incomplete = getenv_harder_bool(handle, "XDG_SESSION_INCOMPLETE", false);
if (streq_ptr(service, "systemd-user")) {
/* If we detect that we are running in the "systemd-user" PAM stack, then let's patch the class to
((IN_SET(user_record_disposition(ur), USER_INTRINSIC, USER_SYSTEM, USER_DYNAMIC) &&
streq(type, "tty")) ? "user-early" : "user");
+ if (incomplete) {
+ if (streq(class, "user"))
+ class = "user-incomplete";
+ else
+ pam_syslog_pam_error(handle, LOG_WARNING, 0, "PAM session of class '%s' is incomplete, which is not supported, ignoring.", class);
+ }
+
remote = !isempty(remote_host) && !is_localhost(remote_host);
r = pam_get_data(handle, "systemd.memory_max", (const void **)&memory_max);