diff --git a/Cargo.toml b/Cargo.toml index efe83af..50d3ae8 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -29,4 +29,5 @@ tracing-subscriber = { version = "0.3", default-features = false, features = ["e udev = "0.8" xdg = "2.5" zbus = { version = "4", default-features = false, features = ["tokio"] } +zbus_xml = "4" strum = { version = "0.26", features = ["derive"] } diff --git a/src/job.rs b/src/job.rs index 4e1ee07..d1521d9 100644 --- a/src/job.rs +++ b/src/job.rs @@ -12,11 +12,14 @@ use nix::sys::signal::Signal; use nix::unistd::Pid; use std::collections::HashMap; use std::ffi::OsStr; +use std::io::Cursor; use std::os::unix::process::ExitStatusExt; use std::process::ExitStatus; use tokio::process::{Child, Command}; use tracing::error; -use zbus::{fdo, interface, zvariant, Connection, Interface, InterfaceRef, SignalContext}; +use zbus::fdo::{self, IntrospectableProxy}; +use zbus::{interface, zvariant, Connection, Interface, InterfaceRef, SignalContext}; +use zbus_xml::Node; use crate::error::{to_zbus_fdo_error, zbus_to_zbus_fdo}; use crate::proxy::JobProxy; @@ -117,6 +120,24 @@ impl JobManager { self.mirrored_jobs.insert(name, object_path.to_owned()); Ok(object_path) } + + pub async fn mirror_connection(&mut self, connection: &Connection) -> fdo::Result<()> { + let proxy = IntrospectableProxy::builder(connection) + .destination("com.steampowered.SteamOSManager1")? + .path(JOB_PREFIX)? + .build() + .await?; + let introspection = proxy.introspect().await?; + let introspection = + Node::from_reader(Cursor::new(introspection)).map_err(to_zbus_fdo_error)?; + for node in introspection.nodes() { + if let Some(name) = node.name() { + self.mirror_job(connection, format!("{JOB_PREFIX}/{name}")) + .await?; + } + } + Ok(()) + } } #[interface(name = "com.steampowered.SteamOSManager1.JobManager")] diff --git a/src/manager/user.rs b/src/manager/user.rs index 7ebb516..dcfc22e 100644 --- a/src/manager/user.rs +++ b/src/manager/user.rs @@ -9,7 +9,7 @@ use anyhow::Result; use std::collections::HashMap; use tokio::sync::mpsc::Sender; -use tracing::error; +use tracing::{error, warn}; use zbus::proxy::Builder; use zbus::zvariant::{self, Fd}; use zbus::{fdo, interface, CacheProperties, Connection, Proxy, SignalContext}; @@ -90,8 +90,18 @@ impl SteamOSManager { system_conn: &Connection, channel: Sender, ) -> Result { + let hdmi_cec = HdmiCecControl::new(&connection).await?; + let mut job_manager = JobManager::new(connection).await?; + if let Err(e) = job_manager.mirror_connection(system_conn).await { + warn!("Could not mirror jobs: {e}"); + match e { + fdo::Error::ServiceUnknown(_) => (), + e => Err(e)?, + } + } + Ok(SteamOSManager { - hdmi_cec: HdmiCecControl::new(&connection).await?, + hdmi_cec, proxy: Builder::new(system_conn) .destination("com.steampowered.SteamOSManager1")? .path("/com/steampowered/SteamOSManager1")? @@ -99,7 +109,7 @@ impl SteamOSManager { .cache_properties(CacheProperties::No) .build() .await?, - job_manager: JobManager::new(connection).await?, + job_manager, channel, }) }