#!/bin/bash # omarchy:summary=Send a fire-and-forget IPC call to a running omarchy-shell # omarchy:hidden=true OMARCHY_PATH=${OMARCHY_PATH:-$HOME/.local/share/omarchy} SHELL_QML="$OMARCHY_PATH/default/quickshell/omarchy-shell/shell.qml" if (( $# < 2 )); then echo "Usage: omarchy-shell-ipc-fast [args...]" >&2 exit 1 fi perl -MCwd=abs_path -MEncode=encode,decode -MSocket \ -e ' sub read_qstring { my ($data, $offset) = @_; return ("", $offset) if $offset + 4 > length($data); my $length = unpack("N", substr($data, $offset, 4)); $offset += 4; return ("", $offset) if $length == 0xffffffff || $offset + $length > length($data); return (decode("UTF-16BE", substr($data, $offset, $length)), $offset + $length); } sub qstring { my $encoded = encode("UTF-16BE", $_[0] // ""); return pack("N", length($encoded)) . $encoded; } my $shell_qml = abs_path(shift @ARGV); my $target = shift @ARGV; my $function = shift @ARGV; my @args = @ARGV; my $runtime_dir = $ENV{"XDG_RUNTIME_DIR"} || "/run/user/$<"; my $payload = chr(3) . qstring($target) . qstring($function) . pack("N", scalar @args) . join("", map { qstring($_) } @args); my @candidates; for my $lock_path (glob("$runtime_dir/quickshell/by-id/*/instance.lock")) { my $data; next unless open(my $lock, "<:raw", $lock_path); { local $/; $data = <$lock>; } close($lock); my (undef, $offset) = read_qstring($data, 0); my ($path) = read_qstring($data, $offset); next unless $path && abs_path($path) eq $shell_qml; (my $socket_path = $lock_path) =~ s{/instance\.lock$}{/ipc.sock}; push @candidates, [(stat($lock_path))[9] || 0, $socket_path]; } for my $candidate (sort { $b->[0] <=> $a->[0] } @candidates) { socket(my $client, AF_UNIX, SOCK_STREAM, 0) || next; if (connect($client, sockaddr_un($candidate->[1]))) { syswrite($client, $payload); close($client); exit 0; } close($client); } exit 1; ' "$SHELL_QML" "$@"