A launcher can exit while its long-lived close/hide helper remains. The next
run then starts another watcher, so several copies watch the same prefix.
Add an opt-in RCLOL_CLEAN_STALE_HELPERS=1 preflight that removes only helper
processes of this prefix reparented to init/systemd. Helpers of a live
launcher, other prefixes, the game, Riot/League/CEF, darlingserver and the
runtime are preserved. Unreadable or relative process data leaves a process
alone.
Validated across repeated launcher starts: the cleanup removed four, then one,
then one orphaned watcher; a subsequent dry run reported no orphaned helpers.
Zombie reaping after partial recovery is tracked separately in #124.
Darlingserver normally stays alive after the Riot Client or game is closed.
If the client window disappears but Riot/League/CEF processes remain,
restarting via run.sh reuses a half-dead runtime and can fail to open a
window.
Add an opt-in RCLOL_RECOVER_STALE_CLIENT=1 preflight. When a darlingserver is
alive, no game is running, no managed client window is visible and stale
client processes belong to this prefix, stop only that client/CEF tree.
Preserve darlingserver, launchd/mldr, sockets and .init.pid, then continue
with the normal product launch.
The helper fails closed when X11 is unavailable, never touches a running game
or a visible client window, and does not patch client binaries, CEF or assets.
It saves the Darling bootstrap, but not Riot Client/CEF startup; a full runtime
restart remains the fallback if no window appears.
Use a project-owned identity for the visible desktop entry while keeping the existing binary, package and window-matching identifiers working. The helper now copies the project's original icon instead of extracting one from the client, and the old game-named entry and icons it created are removed. Extend the packaging check to assert the neutral fields.
Add docs/COMPLIANCE.md with the project's compatibility scope: no DRM/anti-cheat circumvention, no third-party game assets, and neutral terminology for issues and PRs. Link it from README and NOTICE.
The patch comments and the Mach-O strings filter named an anti-cheat product. Use neutral wording; the patches still differ only in comments. The platform-identity document now says the overrides are for compatibility, not a bypass of anti-cheat, telemetry, licensing or platform controls.
Consolidate the non-affiliation note into a dedicated Trademarks section, replace the embedded gameplay video with a pointer to the status document, and reword the takedown note as a continuity statement. Describe the compatibility tools as referring to public API names and constants.
The bundled darling-lol.svg/png are the League of Legends logo, a Riot Games trademark, used as the project icon. The README already states that the project is not affiliated with or endorsed by Riot Games, so the icon should not be someone else's mark.
Replace both files with an original D monogram. Same file names, so flake.nix and the desktop entry keep working. The mark is provisional and easy to swap for a final one. No functional changes.
Mesa derives its shader disk cache from $HOME. Inside the guest that is
/Users/<user>, which does not exist on the host filesystem, so Mesa could not
create the cache and disabled it, once per process:
Failed to create /Users/<user> for shader cache (Permission denied)---disabling
One launcher log contained 212 of those lines, and no shader compiled by one
process was reused by another process or by the next start: the client and the
game recompiled every shader on every launch, spending CPU at startup for no
gain.
Mesa is host code loaded into the guest and reads MESA_SHADER_CACHE_DIR verbatim,
so point it at a host directory; Mesa creates mesa_shader_cache/ (client and game
shaders) and radv_builtin_shaders/ below it. A non-empty value from the caller is
preserved, and a directory that cannot be created leaves the previous behaviour
instead of ending the launch.
Observed on a Radeon RX 550 with radv: no shader-cache failure after the change,
and 434 files / 5.6 MB written during one client start, still growing while the
client ran. The cache is reused from the second start on, which lowers the
client's CPU use while it starts; the startup-time gain itself has not been
measured separately.
The client does not come back properly after a match when its own "Close client
during game" option is enabled. The UI (LeagueClientUx and its helpers) is a
Chromium/CEF instance and, under Darling, the pre-match instance keeps running:
the client the backend starts when the match ends is a second CEF instance on the
same --user-data-dir, and its window never paints. Its DOM and audio work and the
window stays black; closing the client by hand during a match leaves the same
state for the same reason.
RCLOL_CLOSE_CLIENT_IN_GAME=1 opts in to closing that UI from the host, and only
while a match runs, so the client that appears afterwards is the only instance.
The UI also competes with the game for CPU: on a four-core host with a Radeon
RX 550 a practice match reported roughly 120 FPS with the UI running and roughly
180 FPS with it closed. This is not the helper-killing memory optimization the
RAM section warns against, and the Riot client, the League backend and the game
are never touched.
The helper fails closed. It attributes the game and the client to the launcher's
prefix through the loader's __mldr_sockpath, since guest processes do not carry
DPREFIX (checked on a live session). It never closes a client younger than 60
seconds (the one the backend starts after a match), preserves a process of
another installation or owner, acts only when the environment and the stat fields
can be read, gives up after three closes in one match, and leaves after ten
minutes without a client or a match. It is off by default.
Tests use fake /proc entries and mock every signal.