"XDG_SESSION_CLASS",
"XDG_SESSION_TYPE",
"XDG_SESSION_DESKTOP",
+ "XDG_SESSION_EXTRA_DEVICE_ACCESS",
"XDG_SEAT",
"XDG_VTNR");
}
sd_event_get_exit_on_idle;
sd_varlink_is_connected;
} LIBSYSTEMD_258;
+
+LIBSYSTEMD_260 {
+global:
+ sd_session_has_extra_device_access;
+} LIBSYSTEMD_259;
return parse_boolean(s);
}
+_public_ int sd_session_has_extra_device_access(const char *session) {
+ _cleanup_free_ char *p = NULL, *s = NULL;
+ int r;
+
+ r = file_of_session(session, &p);
+ if (r < 0)
+ return r;
+
+ r = parse_env_file(/* f= */ NULL, p, "EXTRA_DEVICE_ACCESS", &s);
+ if (r == -ENOENT)
+ return -ENXIO;
+ if (r < 0)
+ return r;
+ if (isempty(s))
+ return -ENODATA;
+
+ return parse_boolean(s);
+}
+
_public_ int sd_session_get_state(const char *session, char **ret_state) {
_cleanup_free_ char *p = NULL, *s = NULL;
int r;
bool remote,
const char *remote_user,
const char *remote_host,
+ bool extra_device_access,
Session **ret_session) {
bool mangle_class = false;
session->original_type = session->type = type;
session->remote = remote;
+ session->extra_device_access = extra_device_access;
session->vtnr = vtnr;
session->class = class;
remote,
remote_user,
remote_host,
+ /* extra_device_access= */ false,
&session);
if (r == -EBUSY)
return sd_bus_error_set(error, BUS_ERROR_SESSION_BUSY, "Already running in a session or user slice");
bool remote,
const char *remote_user,
const char *remote_host,
+ bool extra_device_access,
Session **ret_session);
extern const BusObjectImplementation manager_object;
SD_BUS_PROPERTY("Remote", "b", bus_property_get_bool, offsetof(Session, remote), SD_BUS_VTABLE_PROPERTY_CONST),
SD_BUS_PROPERTY("RemoteHost", "s", NULL, offsetof(Session, remote_host), SD_BUS_VTABLE_PROPERTY_CONST),
SD_BUS_PROPERTY("RemoteUser", "s", NULL, offsetof(Session, remote_user), SD_BUS_VTABLE_PROPERTY_CONST),
+ SD_BUS_PROPERTY("ExtraDeviceAccess", "b", bus_property_get_bool, offsetof(Session, extra_device_access), SD_BUS_VTABLE_PROPERTY_CONST),
SD_BUS_PROPERTY("Service", "s", NULL, offsetof(Session, service), SD_BUS_VTABLE_PROPERTY_CONST),
SD_BUS_PROPERTY("Desktop", "s", NULL, offsetof(Session, desktop), SD_BUS_VTABLE_PROPERTY_CONST),
SD_BUS_PROPERTY("Scope", "s", NULL, offsetof(Session, scope), SD_BUS_VTABLE_PROPERTY_CONST),
"IS_DISPLAY=%s\n"
"STATE=%s\n"
"REMOTE=%s\n"
+ "EXTRA_DEVICE_ACCESS=%s\n"
"LEADER_FD_SAVED=%s\n",
s->user->user_record->uid,
one_zero(session_is_active(s)),
one_zero(s->user->display == s),
session_state_to_string(session_get_state(s)),
one_zero(s->remote),
+ one_zero(s->extra_device_access),
one_zero(s->leader_fd_saved));
env_file_fputs_assignment(f, "USER=", s->user->user_record->user_name);
int session_load(Session *s) {
_cleanup_free_ char *remote = NULL,
+ *extra_device_access = NULL,
*seat = NULL,
*tty_validity = NULL,
*vtnr = NULL,
assert(s);
r = parse_env_file(NULL, s->state_file,
- "REMOTE", &remote,
- "SCOPE", &s->scope,
- "SCOPE_JOB", &s->scope_job,
- "FIFO", &fifo_path,
- "SEAT", &seat,
- "TTY", &s->tty,
- "TTY_VALIDITY", &tty_validity,
- "DISPLAY", &s->display,
- "REMOTE_HOST", &s->remote_host,
- "REMOTE_USER", &s->remote_user,
- "SERVICE", &s->service,
- "DESKTOP", &s->desktop,
- "VTNR", &vtnr,
- "STATE", &state,
- "POSITION", &position,
- "LEADER", &leader_pid,
- "LEADER_FD_SAVED", &leader_fd_saved,
- "LEADER_PIDFDID", &leader_pidfdid,
- "TYPE", &type,
- "ORIGINAL_TYPE", &original_type,
- "CLASS", &class,
- "UID", &uid,
- "REALTIME", &realtime,
- "MONOTONIC", &monotonic,
- "CONTROLLER", &controller,
- "ACTIVE", &active,
- "DEVICES", &devices,
- "IS_DISPLAY", &is_display);
+ "REMOTE", &remote,
+ "EXTRA_DEVICE_ACCESS", &extra_device_access,
+ "SCOPE", &s->scope,
+ "SCOPE_JOB", &s->scope_job,
+ "FIFO", &fifo_path,
+ "SEAT", &seat,
+ "TTY", &s->tty,
+ "TTY_VALIDITY", &tty_validity,
+ "DISPLAY", &s->display,
+ "REMOTE_HOST", &s->remote_host,
+ "REMOTE_USER", &s->remote_user,
+ "SERVICE", &s->service,
+ "DESKTOP", &s->desktop,
+ "VTNR", &vtnr,
+ "STATE", &state,
+ "POSITION", &position,
+ "LEADER", &leader_pid,
+ "LEADER_FD_SAVED", &leader_fd_saved,
+ "LEADER_PIDFDID", &leader_pidfdid,
+ "TYPE", &type,
+ "ORIGINAL_TYPE", &original_type,
+ "CLASS", &class,
+ "UID", &uid,
+ "REALTIME", &realtime,
+ "MONOTONIC", &monotonic,
+ "CONTROLLER", &controller,
+ "ACTIVE", &active,
+ "DEVICES", &devices,
+ "IS_DISPLAY", &is_display);
if (r < 0)
return log_error_errno(r, "Failed to read %s: %m", s->state_file);
s->remote = k;
}
+ if (extra_device_access) {
+ k = parse_boolean(extra_device_access);
+ if (k >= 0)
+ s->extra_device_access = k;
+ }
+
if (vtnr)
(void) safe_atou(vtnr, &s->vtnr);
char *remote_host;
char *service;
char *desktop;
+ bool extra_device_access;
char *scope;
char *scope_job;
int remote;
const char *remote_user;
const char *remote_host;
+ bool extra_device_access;
} CreateSessionParameters;
static void create_session_parameters_done(CreateSessionParameters *p) {
int r;
static const sd_json_dispatch_field dispatch_table[] = {
- { "UID", _SD_JSON_VARIANT_TYPE_INVALID, sd_json_dispatch_uid_gid, offsetof(CreateSessionParameters, uid), SD_JSON_MANDATORY },
- { "PID", _SD_JSON_VARIANT_TYPE_INVALID, json_dispatch_pidref, offsetof(CreateSessionParameters, pid), SD_JSON_STRICT },
- { "Service", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, service), 0 },
- { "Type", SD_JSON_VARIANT_STRING, json_dispatch_session_type, offsetof(CreateSessionParameters, type), SD_JSON_MANDATORY },
- { "Class", SD_JSON_VARIANT_STRING, json_dispatch_session_class, offsetof(CreateSessionParameters, class), SD_JSON_MANDATORY },
- { "Desktop", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, desktop), SD_JSON_STRICT },
- { "Seat", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, seat), 0 },
- { "VTNr", _SD_JSON_VARIANT_TYPE_INVALID, sd_json_dispatch_uint, offsetof(CreateSessionParameters, vtnr), 0 },
- { "TTY", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, tty), 0 },
- { "Display", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, display), 0 },
- { "Remote", SD_JSON_VARIANT_BOOLEAN, sd_json_dispatch_tristate, offsetof(CreateSessionParameters, remote), 0 },
- { "RemoteUser", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, remote_user), 0 },
- { "RemoteHost", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, remote_host), 0 },
+ { "UID", _SD_JSON_VARIANT_TYPE_INVALID, sd_json_dispatch_uid_gid, offsetof(CreateSessionParameters, uid), SD_JSON_MANDATORY },
+ { "PID", _SD_JSON_VARIANT_TYPE_INVALID, json_dispatch_pidref, offsetof(CreateSessionParameters, pid), SD_JSON_STRICT },
+ { "Service", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, service), 0 },
+ { "Type", SD_JSON_VARIANT_STRING, json_dispatch_session_type, offsetof(CreateSessionParameters, type), SD_JSON_MANDATORY },
+ { "Class", SD_JSON_VARIANT_STRING, json_dispatch_session_class, offsetof(CreateSessionParameters, class), SD_JSON_MANDATORY },
+ { "Desktop", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, desktop), SD_JSON_STRICT },
+ { "Seat", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, seat), 0 },
+ { "VTNr", _SD_JSON_VARIANT_TYPE_INVALID, sd_json_dispatch_uint, offsetof(CreateSessionParameters, vtnr), 0 },
+ { "TTY", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, tty), 0 },
+ { "Display", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, display), 0 },
+ { "Remote", SD_JSON_VARIANT_BOOLEAN, sd_json_dispatch_tristate, offsetof(CreateSessionParameters, remote), 0 },
+ { "RemoteUser", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, remote_user), 0 },
+ { "RemoteHost", SD_JSON_VARIANT_STRING, sd_json_dispatch_const_string, offsetof(CreateSessionParameters, remote_host), 0 },
+ { "ExtraDeviceAccess", SD_JSON_VARIANT_BOOLEAN, sd_json_dispatch_stdbool, offsetof(CreateSessionParameters, extra_device_access), 0 },
{}
};
.class = _SESSION_CLASS_INVALID,
.type = _SESSION_TYPE_INVALID,
.remote = -1,
+ .extra_device_access = false,
};
r = sd_varlink_dispatch(link, parameters, dispatch_table, &p);
p.remote,
p.remote_user,
p.remote_host,
+ p.extra_device_access,
&session);
if (r == -EBUSY)
return sd_varlink_error(link, "io.systemd.Login.AlreadySessionMember", /* parameters= */ NULL);
uint32_t vtnr;
const char *tty;
const char *display;
+ bool extra_device_access;
bool remote;
const char *remote_user;
const char *remote_host;
JSON_BUILD_PAIR_STRING_NON_EMPTY("Display", c->display),
SD_JSON_BUILD_PAIR_BOOLEAN("Remote", c->remote),
JSON_BUILD_PAIR_STRING_NON_EMPTY("RemoteUser", c->remote_user),
- JSON_BUILD_PAIR_STRING_NON_EMPTY("RemoteHost", c->remote_host));
+ JSON_BUILD_PAIR_STRING_NON_EMPTY("RemoteHost", c->remote_host),
+ JSON_BUILD_PAIR_CONDITION_BOOLEAN(c->extra_device_access, "ExtraDeviceAccess", c->extra_device_access));
if (r < 0)
return pam_syslog_errno(pamh, LOG_ERR, r,
"Failed to issue io.systemd.Login.CreateSession varlink call: %m");
if (r != PAM_SUCCESS)
return r;
+ r = update_environment(pamh, "XDG_SESSION_EXTRA_DEVICE_ACCESS", one_zero(c->extra_device_access));
+ if (r != PAM_SUCCESS)
+ return r;
+
r = update_environment(pamh, "XDG_SEAT", real_seat);
if (r != PAM_SUCCESS)
return r;
c.desktop = getenv_harder(pamh, "XDG_SESSION_DESKTOP", desktop_pam);
c.area = getenv_harder(pamh, "XDG_AREA", area_pam);
c.incomplete = getenv_harder_bool(pamh, "XDG_SESSION_INCOMPLETE", false);
+ c.extra_device_access = getenv_harder_bool(pamh, "XDG_SESSION_EXTRA_DEVICE_ACCESS", false);
r = pam_get_data_many(
pamh,
SD_VARLINK_DEFINE_INPUT(RemoteUser, SD_VARLINK_STRING, SD_VARLINK_NULLABLE),
SD_VARLINK_FIELD_COMMENT("Host name of the remote host"),
SD_VARLINK_DEFINE_INPUT(RemoteHost, SD_VARLINK_STRING, SD_VARLINK_NULLABLE),
+ SD_VARLINK_FIELD_COMMENT("If true this session is granted access to additional hardware devices, "
+ "typically useful for remote, graphical sessions. "
+ "This adds access for all devices tagged with \"xaccess\" in udev."),
+ SD_VARLINK_DEFINE_INPUT(ExtraDeviceAccess, SD_VARLINK_BOOL, SD_VARLINK_NULLABLE),
SD_VARLINK_FIELD_COMMENT("The identifier string of the session of the user."),
SD_VARLINK_DEFINE_OUTPUT(Id, SD_VARLINK_STRING, 0),
SD_VARLINK_FIELD_COMMENT("The runtime path ($XDG_RUNTIME_DIR) of the user."),
/* Return 1 if the session is remote. */
int sd_session_is_remote(const char *session);
+/* Return 1 if the session is granted extra device access. */
+int sd_session_has_extra_device_access(const char *session);
+
/* Get state from session. Possible states: online, active, closing.
* This function is a more generic version of sd_session_is_active(). */
int sd_session_get_state(const char *session, char **ret_state);