From 934c4183aad637e0ae739c8c66091cfa13dee8b7 Mon Sep 17 00:00:00 2001 From: "Alexander \"PapaTutuWawa" Date: Sun, 12 Jan 2025 00:21:59 +0100 Subject: [PATCH] Add udev stuff --- microkodi/config.py | 9 +++++++++ microkodi/main.py | 28 ++++++++++++++++++++++++++-- microkodi/udev.py | 27 +++++++++++++++++++++++++++ pyproject.toml | 3 ++- 4 files changed, 64 insertions(+), 3 deletions(-) create mode 100644 microkodi/udev.py diff --git a/microkodi/config.py b/microkodi/config.py index 7935107..bb7f48c 100644 --- a/microkodi/config.py +++ b/microkodi/config.py @@ -34,6 +34,13 @@ class Config: # URL scheme -> netloc (or '*' for fallback) -> fully-qualified player class players: dict[str, dict[str, str]] + card: str | None + connector: str | None + + @property + def watch_connector(self) -> bool: + return self.card is not None and self.connector is not None + def load_config(config_path: Path | None) -> Config: if config_path is None: config_data = {} @@ -59,4 +66,6 @@ def load_config(config_path: Path | None) -> Config: }, config_data.get("players", {}), ), + card=config_data.get("card"), + connector=config_data.get("connector"), ) diff --git a/microkodi/main.py b/microkodi/main.py index ee724d0..28345b7 100644 --- a/microkodi/main.py +++ b/microkodi/main.py @@ -5,6 +5,7 @@ import threading import argparse from pathlib import Path import importlib.util +import time from PySide6.QtGui import QGuiApplication from PySide6.QtQml import QQmlApplicationEngine @@ -13,12 +14,12 @@ from microkodi.jsonrpc import JsonRpcHandler, GlobalMethodHandler from microkodi.ui.bridge import DataBridge from microkodi.config import Config, load_config from microkodi.repository import I +from microkodi.udev import is_display_connected, block_until_display_connected def run_kodi_server(): config: Config = I.get("Config") - logging.basicConfig(level=logging.DEBUG) logger = logging.getLogger("JsonRPCServer") method_handler = GlobalMethodHandler() I.register("GlobalMethodHandler", method_handler) @@ -58,8 +59,12 @@ def run_kodi_server(): if __name__ == "__main__": parser = argparse.ArgumentParser() parser.add_argument("--config", "-c", type=Path, help="Location of the config file") + parser.add_argument("--debug", action="store_true", default=False) options = parser.parse_args() + logging.basicConfig(level=logging.DEBUG if options.debug else logging.INFO) + logger = logging.getLogger("ui") + # Load the config config = load_config(options.config) I.register("Config", config) @@ -87,6 +92,25 @@ if __name__ == "__main__": sys.exit(-1) engine.rootObjects()[0].setProperty("bridge", bridge) - exit_code = app.exec() + + if config.watch_connector: + logger.info("Will be watching display if it's gone") + + exit_code = 0 + while True: + exit_code = app.exec() + + if not config.watch_connector: + break + + # Exit if the display is still connected + if is_display_connected(config.card, config.connector): + break + + logger.info("Display is gone. Waiting until it's back") + block_until_display_connected(config.card, config.connector) + logger.info("Display is back. Waiting 500ms...") + time.sleep(0.5) + del engine sys.exit(exit_code) \ No newline at end of file diff --git a/microkodi/udev.py b/microkodi/udev.py new file mode 100644 index 0000000..daf3f8b --- /dev/null +++ b/microkodi/udev.py @@ -0,0 +1,27 @@ +import logging + +import pyudev + +def is_display_connected(card: str, connector: str) -> bool: + logger = logging.getLogger("udev") + status_file = f"/sys/class/drm/{card}-{connector}/status" + logger.debug("Reading file %s", status_file) + with open(status_file, "r") as f: + result = f.read().strip() + logger.debug("Result: '%s'", result) + return result == "connected" + +def block_until_display_connected(card: str, connector: str): + ctx = pyudev.Context() + monitor = pyudev.Monitor.from_netlink(ctx) + monitor.filter_by("drm") + for device in iter(monitor.poll, None): + if not "DEVNAME" in device: + continue + + if device.get("DEVNAME") != f"/dev/dri/{card}": + continue + + if not is_display_connected(card, connector): + continue + break \ No newline at end of file diff --git a/pyproject.toml b/pyproject.toml index b23d560..f7eccf3 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -4,7 +4,8 @@ version = "0.1.0" dependencies = [ "pyside6", "requests", - "yt-dlp" + "yt-dlp", + "pyudev" ] [tools.build]