@@ -68,9 +68,7 @@ prompt_text() {
6868# --- help ---
6969
7070print_help () {
71- echo " moonshine-install.sh — install moonshine via systemd-sysext"
72- echo " "
73- echo " curl -fsSL https://github.com/hgaiser/moonshine/releases/latest/download/moonshine-install.sh | bash"
71+ echo " moonshine-install.sh — install moonshine"
7472 echo " "
7573 echo " Options:"
7674 echo " --uninstall Remove moonshine completely"
@@ -103,14 +101,6 @@ if [[ "$(uname -m)" != "x86_64" ]]; then
103101 die " moonshine only supports x86_64"
104102fi
105103
106- if ! command -v systemd-sysext & > /dev/null; then
107- die " systemd-sysext not found (systemd >= 248 required)"
108- fi
109-
110- if systemd-detect-virt --container --quiet 2> /dev/null; then
111- die " cannot run inside a container (sysext uses overlayfs)"
112- fi
113-
114104if ! command -v sudo & > /dev/null; then
115105 die " sudo not found"
116106fi
@@ -155,39 +145,22 @@ if [[ "$UNINSTALL" == "true" ]]; then
155145 sudo systemctl disable " moonshine@${USER} " || true
156146 fi
157147
158- if systemd-sysext list 2> /dev/null | grep -q moonshine; then
159- step " Unmerging sysext..."
160- sudo systemd-sysext unmerge moonshine.raw || true
161- fi
162-
163- if [[ -f /var/lib/extensions/moonshine.raw ]]; then
164- step " Removing extension image..."
165- sudo rm -f /var/lib/extensions/moonshine.raw
166- fi
167-
168- if [[ -f /etc/systemd/system/moonshine@.service ]]; then
169- step " Removing copied service unit..."
170- sudo rm -f /etc/systemd/system/moonshine@.service
171- sudo systemctl daemon-reload || true
172- fi
173-
148+ step " Removing files..."
149+ sudo rm -rf /opt/moonshine
150+ sudo rm -f /etc/systemd/system/moonshine@.service
151+ sudo rm -f /etc/udev/rules.d/60-moonshine.rules
152+ sudo rm -f /etc/modules-load.d/moonshine.conf
153+ sudo rm -f /etc/sysusers.d/moonshine.conf
154+ sudo rm -f /etc/vulkan/implicit_layer.d/VkLayer_moonshine_wsi.json
155+ sudo rm -f /etc/polkit-1/rules.d/50-moonshine-inhibit-sleep.rules
156+ sudo rm -f /etc/profile.d/moonshine.sh
157+ sudo systemctl daemon-reload || true
174158 sudo udevadm control --reload || true
175159
176160 ok " moonshine uninstalled"
177161 exit 0
178162fi
179163
180- # --- check if sysext is already enabled ---
181-
182- if ! systemctl is-enabled systemd-sysext.service & > /dev/null; then
183- die " systemd-sysext.service is not enabled.
184- Moonshine requires sysext to be active at boot to merge the extension.
185- Enable it first (this makes /usr read-only, breaking package managers
186- like pacman/apt/dnf while the sysext is active — understand the risk):
187- sudo systemctl enable --now systemd-sysext.service
188- Then run this installer again."
189- fi
190-
191164# --- download ---
192165
193166VERSION=" __VERSION__"
202175
203176info " Installing moonshine ${VERSION} "
204177
205- URL=" https://github.com/hgaiser/moonshine/releases/download/${VERSION} /moonshine-${VERSION} -x86_64.raw "
178+ URL=" https://github.com/hgaiser/moonshine/releases/download/${VERSION} /moonshine-${VERSION} -linux-amd64.tar.zst "
206179step " Downloading ${DIM}${URL}${RESET} "
207180TMPFILE=" $( mktemp) "
208181curl -fsSL --retry 3 -o " $TMPFILE " " $URL "
209182
210183SIZE=$( du -h " $TMPFILE " | cut -f1)
211184step " Downloaded (${SIZE} )"
185+
186+ step " Extracting..."
187+ TMPDIR=" $( mktemp -d) "
188+ tar --zstd -xf " $TMPFILE " -C " $TMPDIR "
189+ S=" $TMPDIR /moonshine"
190+
212191echo " "
213192
214193# --- prompts ---
@@ -251,25 +230,73 @@ if [[ -z "$HEALTHCHECK" ]]; then
251230fi
252231
253232# --- build and run privileged commands ---
254- # start-moonshine.sh and moonshine@.service are not in the sysext — they're
255- # deployed directly to /etc/systemd/system/ so they persist on the real
256- # filesystem regardless of the sysext overlay. This ensures the service unit
257- # is available at boot before systemd-sysext merges extensions, and avoids
258- # permission issues with overlayfs on distros like Bazzite.
233+
234+ MOONSHINE_HOME=" /opt/moonshine"
259235
260236CMDS=(
237+ # Stop existing service
261238 " systemctl stop 'moonshine@${USER} ' 2>/dev/null || true"
262- " mkdir -p /var/lib/extensions"
263- " mv '${TMPFILE} ' /var/lib/extensions/moonshine.raw"
264- " systemd-sysext refresh"
265- " curl -fsSL --retry 3 -o /etc/systemd/system/start-moonshine.sh https://raw.githubusercontent.com/hgaiser/moonshine/${VERSION} /dist/start-moonshine.sh"
266- " chmod +x /etc/systemd/system/start-moonshine.sh"
267- " curl -fsSL --retry 3 https://raw.githubusercontent.com/hgaiser/moonshine/${VERSION} /dist/moonshine@.service | sed 's|/usr/bin/start-moonshine.sh|/etc/systemd/system/start-moonshine.sh|' > /etc/systemd/system/moonshine@.service"
239+
240+ # Create directories
241+ " mkdir -p '${MOONSHINE_HOME} /bin'"
242+ " mkdir -p /etc/udev/rules.d"
243+ " mkdir -p /etc/modules-load.d"
244+ " mkdir -p /etc/sysusers.d"
245+ " mkdir -p /etc/vulkan/implicit_layer.d"
246+ " mkdir -p /etc/polkit-1/rules.d"
247+ # Deploy moonshine binary
248+ " cp '${S} /bin/moonshine' '${MOONSHINE_HOME} /bin/moonshine'"
249+ " chmod 755 '${MOONSHINE_HOME} /bin/moonshine'"
250+
251+ # Deploy Vulkan WSI layer
252+ " mkdir -p '${MOONSHINE_HOME} /lib'"
253+ " cp '${S} /lib/moonshine/vulkan-layers/libmoonshine_wsi.so' '${MOONSHINE_HOME} /lib/libmoonshine_wsi.so'"
254+ " chmod 755 '${MOONSHINE_HOME} /lib/libmoonshine_wsi.so'"
255+
256+ # Deploy the install script itself for future upgrades/uninstall
257+ " cp '${S} /bin/moonshine-install.sh' '${MOONSHINE_HOME} /bin/moonshine-install.sh'"
258+ " chmod 755 '${MOONSHINE_HOME} /bin/moonshine-install.sh'"
259+
260+ # Deploy start script with path patched
261+ " sed 's|/usr/bin/moonshine|${MOONSHINE_HOME} /bin/moonshine|g' '${S} /share/moonshine/start-moonshine.sh' > '${MOONSHINE_HOME} /start-moonshine.sh'"
262+ " chmod 755 '${MOONSHINE_HOME} /start-moonshine.sh'"
263+
264+ # Deploy service unit with path patched
265+ " sed 's|/usr/bin/start-moonshine.sh|${MOONSHINE_HOME} /start-moonshine.sh|' '${S} /share/moonshine/moonshine@.service' > /etc/systemd/system/moonshine@.service"
266+
267+ # Deploy udev rules
268+ " cp '${S} /share/moonshine/60-moonshine.rules' /etc/udev/rules.d/60-moonshine.rules"
269+
270+ # Deploy modules-load config
271+ " cp '${S} /share/moonshine/moonshine-modules.conf' /etc/modules-load.d/moonshine.conf"
272+
273+ # Deploy sysusers config
274+ " cp '${S} /share/moonshine/moonshine-sysusers.conf' /etc/sysusers.d/moonshine.conf"
275+
276+ # Deploy Vulkan layer manifest with library_path patched
277+ " sed 's|/usr/lib/moonshine/vulkan-layers/libmoonshine_wsi.so|${MOONSHINE_HOME} /lib/libmoonshine_wsi.so|' '${S} /share/moonshine/VkLayer_moonshine_wsi.json' > /etc/vulkan/implicit_layer.d/VkLayer_moonshine_wsi.json"
278+
279+ # Deploy polkit sleep-inhibit rules
280+ " cp '${S} /share/moonshine/50-moonshine-inhibit-sleep.rules' /etc/polkit-1/rules.d/50-moonshine-inhibit-sleep.rules"
281+
282+ # Create profile.d for PATH
283+ " echo 'export PATH=\"\$ {PATH}:${MOONSHINE_HOME} /bin\" ' > /etc/profile.d/moonshine.sh"
284+
285+ # Reload systemd
286+ " systemctl daemon-reload"
287+
288+ # Apply sysusers (creates moonshine group)
268289 " systemd-sysusers || true"
290+
291+ # Reload udev rules
269292 " udevadm control --reload || true"
270293 " udevadm trigger || true"
294+
295+ # Load kernel modules
271296 " modprobe uinput || true"
272297 " modprobe uhid || true"
298+
299+ # Reload polkit
273300 " systemctl reload-or-restart polkit.service || true"
274301)
275302
280307if [[ " $HEALTHCHECK " == " true" ]]; then
281308 CMDS+=(" echo ''" )
282309 CMDS+=(" echo ':: Running health check'" )
283- CMDS+=(" systemd-run --quiet --wait --pipe -p 'User=${USER} ' -p 'SupplementaryGroups=input' -p 'SupplementaryGroups=moonshine' -p 'DeviceAllow=/dev/uinput rw' -p 'DeviceAllow=/dev/uhid rw' -p 'DeviceAllow=char-drm rw' -p 'DeviceAllow=char-nvidia rw' -p 'DeviceAllow=char-nvidia-uvm rw' /etc/systemd/system/ start-moonshine.sh healthcheck || true" )
310+ CMDS+=(" systemd-run --quiet --wait --pipe -p 'User=${USER} ' -p 'SupplementaryGroups=input' -p 'SupplementaryGroups=moonshine' -p 'DeviceAllow=/dev/uinput rw' -p 'DeviceAllow=/dev/uhid rw' -p 'DeviceAllow=char-drm rw' -p 'DeviceAllow=char-nvidia rw' -p 'DeviceAllow=char-nvidia-uvm rw' ' ${MOONSHINE_HOME} / start-moonshine.sh' healthcheck || true" )
284311fi
285312
286313if [[ " $ENABLE_ON_BOOT " == " true" ]] || [[ " $START_NOW " == " true" ]]; then
287- CMDS+=(" systemctl daemon-reload" )
288314 if [[ " $ENABLE_ON_BOOT " == " true" ]] && [[ " $START_NOW " == " true" ]]; then
289315 CMDS+=(" systemctl enable --now 'moonshine@${USER} '" )
290316 elif [[ " $ENABLE_ON_BOOT " == " true" ]]; then
@@ -304,6 +330,9 @@ echo ""
304330
305331sudo bash -c " $( printf ' %s\n' " ${CMDS[@]} " ) "
306332
333+ # Cleanup temp files
334+ rm -rf " $TMPDIR " " $TMPFILE "
335+
307336ok " moonshine ${VERSION} installed"
308337
309338if [[ " $ENABLE_ON_BOOT " != " true" ]] && [[ " $START_NOW " != " true" ]]; then
@@ -320,7 +349,5 @@ echo ""
320349echo -e " ${DIM} status${RESET} ${BOLD} systemctl status moonshine@${USER}${RESET} "
321350echo -e " ${DIM} config${RESET} ${BOLD} /home/${USER} /.config/moonshine/config.toml${RESET} "
322351echo " "
323- step " This installer is at /usr/bin/moonshine-install.sh for future upgrades or uninstall"
324- echo " "
325352
326353ok " Done"
0 commit comments