From 4de2d31e9175105324526f010b831c2ec9ca9b9e Mon Sep 17 00:00:00 2001 From: Gregor Lohaus Date: Fri, 29 May 2026 12:51:45 +0200 Subject: [PATCH] clear env, dont inherit nix wrapper env --- flake.nix | 1 + .../com/gregor/jprototerm/ShellSession.java | 25 +++++++++++++++++++ 2 files changed, 26 insertions(+) diff --git a/flake.nix b/flake.nix index 33e182c..45ba01e 100644 --- a/flake.nix +++ b/flake.nix @@ -108,6 +108,7 @@ done makeWrapper "${pkgs.jdk25}/bin/java" "$out/bin/jprototerm" \ + --run 'export JPROTOTERM_HOST_LD_LIBRARY_PATH="''${LD_LIBRARY_PATH:-}"' \ --add-flags "--enable-native-access=ALL-UNNAMED,javafx.graphics" \ --add-flags "--module-path $out/share/jprototerm/javafx" \ --add-flags "--add-modules javafx.controls,javafx.fxml" \ diff --git a/src/main/java/com/gregor/jprototerm/ShellSession.java b/src/main/java/com/gregor/jprototerm/ShellSession.java index d787383..5ee7514 100644 --- a/src/main/java/com/gregor/jprototerm/ShellSession.java +++ b/src/main/java/com/gregor/jprototerm/ShellSession.java @@ -27,6 +27,7 @@ public final class ShellSession implements AutoCloseable { Map environment = new HashMap<>(System.getenv()); environment.put("TERM", "xterm-kitty"); environment.put("COLORTERM", "truecolor"); + sanitizeWrapperEnvironment(environment); environment.putAll(envOverride); LinuxPty pty = LinuxPty.spawn( @@ -42,6 +43,30 @@ public final class ShellSession implements AutoCloseable { } } + /** + * Strips the variables injected by the Nix launcher wrapper from the shell's + * environment so they do not leak into terminal subprocesses. + * + *

jprototerm is launched from a Nix wrapper that prepends Nix store paths to + * {@code LD_LIBRARY_PATH} (and adds a GL shim) so the bundled JavaFX/ghostty natives + * resolve. If the shell inherited that path, host programs run inside the terminal + * (e.g. {@code flatpak}, {@code pdftoppm}) would load the Nix copies of libraries such + * as freetype/fontconfig/glib, which in turn drag in the Nix glibc through their + * RUNPATHs and clash with the host {@code libc.so.6}. We restore the user's original + * {@code LD_LIBRARY_PATH}, captured by the wrapper before it prepended anything. + */ + private static void sanitizeWrapperEnvironment(Map environment) { + String hostLibraryPath = environment.remove("JPROTOTERM_HOST_LD_LIBRARY_PATH"); + if (hostLibraryPath == null || hostLibraryPath.isEmpty()) { + environment.remove("LD_LIBRARY_PATH"); + } else { + environment.put("LD_LIBRARY_PATH", hostLibraryPath); + } + // These are jprototerm's own runtime settings, not the user's shell environment. + environment.remove("GDK_BACKEND"); + environment.remove("JLIBGHOSTTY_LIBRARY"); + } + public void startReading(TerminalPane pane) { reader.submit(() -> readOutput(pane)); }