baldurk / renderdoc

RenderDoc is a stand-alone graphics debugging tool.
https://renderdoc.org
MIT License
8.92k stars 1.34k forks source link

Linux `dlopen()` hook doesn’t respect `RUNPATH`s #3403

Closed OrichalcumCosmonaut closed 2 months ago

OrichalcumCosmonaut commented 2 months ago

Description

I’m developing a game with SDL3 (specifically libsdl-org/SDL#9312) while running NixOS, and RenderDoc’s dlopen() hook is causing SDL3 to not be able to find its dependencies.

Some background: Nix (and thus NixOS also) uses RUNPATHs extensively to try to solve the “dependency hell” problem: every executable and library has its RUNPATH set so it finds the specific version it was compiled with, and the /lib and /lib64 directories are empty (except for a “stub” dynamic linker that prints a message and exits: https://github.com/NixOS/nixpkgs/blob/3c02efecddd1a55dbf797f038aa97405973e47f8/nixos/modules/config/stub-ld.nix).

$ patchelf --print-rpath "$(which cat)"
/nix/store/jrwzc846rmzv74axmzyn0j6hagz23sna-acl-2.3.2/lib:/nix/store/6dm3hpmqmskkb024bz130fv5h29w8k2g-attr-2.5.2/lib:/nix/store/h676f70iisfd9chl08v3745gr3650s1p-gmp-with-cxx-6.3.0/lib:/nix/store/0wydilnf1c9vznywsvxqnaing4wraaxp-glibc-2.39-52/lib

For shared libraries linked with the executable/library, this works fine, because they are resolved before RenderDoc has the opportunity to hook dlopen(). SDL3, however, loads most of its dependencies at runtime with dlopen().

When I run the game normally, it works fine (e.g. finding libdbus, output from LD_DEBUG=all):

   1275066: file=libdbus-1.so.3 [0];  dynamically loaded by /nix/store/s8ghhgv2ycqh5rmqij0180qc50gzli44-SDL3-3.1.2+d22cf05bb5202dd65c28d96f73ee65b481e1207a/lib/libSDL3.so.0 [0]
   1275066: find library=libdbus-1.so.3 [0]; searching
   1275066:  search path=/nix/store/fr89g4mi5zsplmjfl56y0ckl7pzzdskq-vulkan-loader-1.3.283.0/lib        (LD_LIBRARY_PATH)
   1275066:   trying file=/nix/store/fr89g4mi5zsplmjfl56y0ckl7pzzdskq-vulkan-loader-1.3.283.0/lib/libdbus-1.so.3
   1275066:  search path=/nix/store/0wydilnf1c9vznywsvxqnaing4wraaxp-glibc-2.39-52/lib      (system search path)
   1275066:   trying file=/nix/store/0wydilnf1c9vznywsvxqnaing4wraaxp-glibc-2.39-52/lib/libdbus-1.so.3
   1275066:  search path=/nix/store/3drzwzpbhpi3s7ddw67p8ip9z182a1ak-alsa-lib-1.2.11/lib/glibc-hwcaps/x86-64-v3:/nix/store/3drzwzpbhpi3s7ddw67p8ip9z182a1ak-alsa-lib-1.2.11/lib/glibc-hwcaps/x86-64-v2:/nix/store/3drzwzpbhpi3s7ddw67p8ip9z182a1ak-alsa-lib-1.2.11/lib:/nix/store/fs6fjxv9ls9r3xqk3ms76zxilkqlpvwv-dbus-1.14.10-lib/lib/glibc-hwcaps/x86-64-v3:/nix/store/fs6fjxv9ls9r3xqk3ms76zxilkqlpvwv-dbus-1.14.10-lib/lib/glibc-hwcaps/x86-64-v2:/nix/store/fs6fjxv9ls9r3xqk3ms76zxilkqlpvwv-dbus-1.14.10-lib/lib:/nix/store/3lc70x3rsx2dmbwwrpk877kaa4b7d333-systemd-minimal-libs-256.2/lib/glibc-hwcaps/x86-64-v3:/nix/store/3lc70x3rsx2dmbwwrpk877kaa4b7d333-systemd-minimal-libs-256.2/lib/glibc-hwcaps/x86-64-v2:/nix/store/3lc70x3rsx2dmbwwrpk877kaa4b7d333-systemd-minimal-libs-256.2/lib:/nix/store/5mlcqyhcnv3nqn76kyakqcwac7g8qbxz-libdecor-0.2.2/lib/glibc-hwcaps/x86-64-v3:/nix/store/5mlcqyhcnv3nqn76kyakqcwac7g8qbxz-libdecor-0.2.2/lib/glibc-hwcaps/x86-64-v2:/nix/store/5mlcqyhcnv3nqn76kyakqcwac7g8qbxz-libdecor-0.2.2/lib:/nix/store/dhn51w2km4fyf9ivi00rz03qs8q4mpng-pipewire-1.2.1/lib/glibc-hwcaps/x86-64-v3:/nix/store/dhn51w2km4fyf9ivi00rz03qs8q4mpng-pipewire-1.2.1/lib/glibc-hwcaps/x86-64-v2:/nix/store/dhn51w2km4fyf9ivi00rz03qs8q4mpng-pipewire-1.2.1/lib:/nix/store/kqxqiyhflq7f72z4ldbhd0b8mf9h9ick-libpulseaudio-17.0/lib/glibc-hwcaps/x86-64-v3:/nix/store/kqxqiyhflq7f72z4ldbhd0b8mf9h9ick-libpulseaudio-17.0/lib/glibc-hwcaps/x86-64-v2:/nix/store/kqxqiyhflq7f72z4ldbhd0b8mf9h9ick-libpulseaudio-17.0/lib:/nix/store/hgvky83ijhl0fl625g4hwllwzmpdnksl-wayland-1.23.0/lib/glibc-hwcaps/x86-64-v3:/nix/store/hgvky83ijhl0fl625g4hwllwzmpdnksl-wayland-1.23.0/lib/glibc-hwcaps/x86-64-v2:/nix/store/hgvky83ijhl0fl625g4hwllwzmpdnksl-wayland-1.23.0/lib:/nix/store/gkhma9q8dm7vgjzqhjg1p34pflmpz6jz-libusb-1.0.27/lib/glibc-hwcaps/x86-64-v3:/nix/store/gkhma9q8dm7vgjzqhjg1p34pflmpz6jz-libusb-1.0.27/lib/glibc-hwcaps/x86-64-v2:/nix/store/gkhma9q8dm7vgjzqhjg1p34pflmpz6jz-libusb-1.0.27/lib:/nix/store/jszyncc1s8hkg9qw17nmi0lfrckhas2n-libxkbcommon-1.7.0/lib/glibc-hwcaps/x86-64-v3:/nix/store/jszyncc1s8hkg9qw17nmi0lfrckhas2n-libxkbcommon-1.7.0/lib/glibc-hwcaps/x86-64-v2:/nix/store/jszyncc1s8hkg9qw17nmi0lfrckhas2n-libxkbcommon-1.7.0/lib:/nix/store/rcvwvfgk5dkwc3a8sza5q0351h8axbkh-libglvnd-1.7.0/lib/glibc-hwcaps/x86-64-v3:/nix/store/rcvwvfgk5dkwc3a8sza5q0351h8axbkh-libglvnd-1.7.0/lib/glibc-hwcaps/x86-64-v2:/nix/store/rcvwvfgk5dkwc3a8sza5q0351h8axbkh-libglvnd-1.7.0/lib:/nix/store/94sinl3kmf4byyjgfpy4mmm9crwj8imc-libX11-1.8.9/lib/glibc-hwcaps/x86-64-v3:/nix/store/94sinl3kmf4byyjgfpy4mmm9crwj8imc-libX11-1.8.9/lib/glibc-hwcaps/x86-64-v2:/nix/store/94sinl3kmf4byyjgfpy4mmm9crwj8imc-libX11-1.8.9/lib:/nix/store/053wlpj13qsrvq01fmky8gjj4amz2wbj-libXext-1.3.6/lib/glibc-hwcaps/x86-64-v3:/nix/store/053wlpj13qsrvq01fmky8gjj4amz2wbj-libXext-1.3.6/lib/glibc-hwcaps/x86-64-v2:/nix/store/053wlpj13qsrvq01fmky8gjj4amz2wbj-libXext-1.3.6/lib:/nix/store/0awsl91layljahrj5lpbdrx5xbll4m1f-libXcursor-1.2.2/lib/glibc-hwcaps/x86-64-v3:/nix/store/0awsl91layljahrj5lpbdrx5xbll4m1f-libXcursor-1.2.2/lib/glibc-hwcaps/x86-64-v2:/nix/store/0awsl91layljahrj5lpbdrx5xbll4m1f-libXcursor-1.2.2/lib:/nix/store/99k9431pk5m5zr0n1hvqby398785j43s-libXfixes-6.0.1/lib/glibc-hwcaps/x86-64-v3:/nix/store/99k9431pk5m5zr0n1hvqby398785j43s-libXfixes-6.0.1/lib/glibc-hwcaps/x86-64-v2:/nix/store/99k9431pk5m5zr0n1hvqby398785j43s-libXfixes-6.0.1/lib:/nix/store/zj91xq030vl12ixm62kpwfsib56ifcnj-libXi-1.8.1/lib/glibc-hwcaps/x86-64-v3:/nix/store/zj91xq030vl12ixm62kpwfsib56ifcnj-libXi-1.8.1/lib/glibc-hwcaps/x86-64-v2:/nix/store/zj91xq030vl12ixm62kpwfsib56ifcnj-libXi-1.8.1/lib:/nix/store/dkdpymarl3qjjx16bxdc5qnm6mvw2cck-libXrandr-1.5.4/lib/glibc-hwcaps/x86-64-v3:/nix/store/dkdpymarl3qjjx16bxdc5qnm6mvw2cck-libXrandr-1.5.4/lib/glibc-hwcaps/x86-64-v2:/nix/store/dkdpymarl3qjjx16bxdc5qnm6mvw2cck-libXrandr-1.5.4/lib:/nix/store/vphcxrp0528cbzbrhhxs3ky0wv5xiyg9-libXScrnSaver-1.2.4/lib/glibc-hwcaps/x86-64-v3:/nix/store/vphcxrp0528cbzbrhhxs3ky0wv5xiyg9-libXScrnSaver-1.2.4/lib/glibc-hwcaps/x86-64-v2:/nix/store/vphcxrp0528cbzbrhhxs3ky0wv5xiyg9-libXScrnSaver-1.2.4/lib      (RUNPATH from file /nix/store/s8ghhgv2ycqh5rmqij0180qc50gzli44-SDL3-3.1.2+d22cf05bb5202dd65c28d96f73ee65b481e1207a/lib/libSDL3.so.0)
   1275066:   trying file=/nix/store/3drzwzpbhpi3s7ddw67p8ip9z182a1ak-alsa-lib-1.2.11/lib/glibc-hwcaps/x86-64-v3/libdbus-1.so.3
   1275066:   trying file=/nix/store/3drzwzpbhpi3s7ddw67p8ip9z182a1ak-alsa-lib-1.2.11/lib/glibc-hwcaps/x86-64-v2/libdbus-1.so.3
   1275066:   trying file=/nix/store/3drzwzpbhpi3s7ddw67p8ip9z182a1ak-alsa-lib-1.2.11/lib/libdbus-1.so.3
   1275066:   trying file=/nix/store/fs6fjxv9ls9r3xqk3ms76zxilkqlpvwv-dbus-1.14.10-lib/lib/glibc-hwcaps/x86-64-v3/libdbus-1.so.3
   1275066:   trying file=/nix/store/fs6fjxv9ls9r3xqk3ms76zxilkqlpvwv-dbus-1.14.10-lib/lib/glibc-hwcaps/x86-64-v2/libdbus-1.so.3
   1275066:   trying file=/nix/store/fs6fjxv9ls9r3xqk3ms76zxilkqlpvwv-dbus-1.14.10-lib/lib/libdbus-1.so.3
   1275066: 
   1275066: file=libdbus-1.so.3 [0];  generating link map
   1275066:   dynamic: 0x00007f7411b61e28  base: 0x00007f7411b0b000   size: 0x00000000000582d0
   1275066:     entry: 0x00007f7411b0b000  phdr: 0x00007f7411b0b040  phnum:                 11

However, if I run the game using RenderDoc, it doesn’t:

   1275120: file=libdbus-1.so.3 [0];  dynamically loaded by /nix/store/xfdsqkw504aci9pwdf8h621q6cqybj7y-renderdoc-1.33/lib/librenderdoc.so [0]
   1275120: find library=libdbus-1.so.3 [0]; searching
   1275120:  search path=/nix/store/fr89g4mi5zsplmjfl56y0ckl7pzzdskq-vulkan-loader-1.3.283.0/lib:/nix/store/xfdsqkw504aci9pwdf8h621q6cqybj7y-renderdoc-1.33/lib:/nix/store/rcvwvfgk5dkwc3a8sza5q0351h8axbkh-libglvnd-1.7.0/lib:/nix/store/xfdsqkw504aci9pwdf8h621q6cqybj7y-renderdoc-1.33/bin:/nix/store/xfdsqkw504aci9pwdf8h621q6cqybj7y-renderdoc-1.33/bin/../lib     (LD_LIBRARY_PATH)
   1275120:   trying file=/nix/store/fr89g4mi5zsplmjfl56y0ckl7pzzdskq-vulkan-loader-1.3.283.0/lib/libdbus-1.so.3
   1275120:   trying file=/nix/store/xfdsqkw504aci9pwdf8h621q6cqybj7y-renderdoc-1.33/lib/libdbus-1.so.3
   1275120:   trying file=/nix/store/rcvwvfgk5dkwc3a8sza5q0351h8axbkh-libglvnd-1.7.0/lib/libdbus-1.so.3
   1275120:   trying file=/nix/store/xfdsqkw504aci9pwdf8h621q6cqybj7y-renderdoc-1.33/bin/libdbus-1.so.3
   1275120:   trying file=/nix/store/xfdsqkw504aci9pwdf8h621q6cqybj7y-renderdoc-1.33/bin/../lib/libdbus-1.so.3
   1275120:  search path=/run/opengl-driver/lib:/nix/store/cp4bas285jiglfch3nxbmzv44cyq53ap-libxcb-1.17.0/lib:/nix/store/94sinl3kmf4byyjgfpy4mmm9crwj8imc-libX11-1.8.9/lib:/nix/store/l7wi654ndpw5yyanchg27frdjjpvxz5j-xcb-util-keysyms-0.4.1/lib       (RUNPATH from file /nix/store/xfdsqkw504aci9pwdf8h621q6cqybj7y-renderdoc-1.33/lib/librenderdoc.so)
   1275120:   trying file=/run/opengl-driver/lib/libdbus-1.so.3
   1275120:   trying file=/nix/store/cp4bas285jiglfch3nxbmzv44cyq53ap-libxcb-1.17.0/lib/libdbus-1.so.3
   1275120:   trying file=/nix/store/94sinl3kmf4byyjgfpy4mmm9crwj8imc-libX11-1.8.9/lib/libdbus-1.so.3
   1275120:   trying file=/nix/store/l7wi654ndpw5yyanchg27frdjjpvxz5j-xcb-util-keysyms-0.4.1/lib/libdbus-1.so.3
   1275120:  search path=/nix/store/0wydilnf1c9vznywsvxqnaing4wraaxp-glibc-2.39-52/lib      (system search path)
   1275120:   trying file=/nix/store/0wydilnf1c9vznywsvxqnaing4wraaxp-glibc-2.39-52/lib/libdbus-1.so.3
   1275120:  search path=/nix/store/kgmfgzb90h658xg0i7mxh9wgyx0nrqac-gcc-13.3.0-lib/lib     (RUNPATH from file /nix/store/xfdsqkw504aci9pwdf8h621q6cqybj7y-renderdoc-1.33/lib/librenderdoc.so)
   1275120:   trying file=/nix/store/kgmfgzb90h658xg0i7mxh9wgyx0nrqac-gcc-13.3.0-lib/lib/libdbus-1.so.3
   1275120:  search cache=/nix/store/0wydilnf1c9vznywsvxqnaing4wraaxp-glibc-2.39-52/etc/ld.so.cache
   1275120:  search path=/nix/store/0wydilnf1c9vznywsvxqnaing4wraaxp-glibc-2.39-52/lib:/nix/store/dffyikn59cy7fff2qd60gs9jl63szqnh-xgcc-13.3.0-libgcc/lib       (system search path)
   1275120:   trying file=/nix/store/0wydilnf1c9vznywsvxqnaing4wraaxp-glibc-2.39-52/lib/libdbus-1.so.3
   1275120:   trying file=/nix/store/dffyikn59cy7fff2qd60gs9jl63szqnh-xgcc-13.3.0-libgcc/lib/libdbus-1.so.3

As can be seen in the logs from the dynamic linker (specifically the RUNPATH from file… parts), it’s looking in librenderdoc’s search path and not libSDL3’s, because the call to the real dlopen() happens in librenderdoc.

I’ve been able to work around this by having RenderDoc instead launch a wrapper script that adds SDL3’s RUNPATH to LD_LIBRARY_PATH before starting the game, but it would be nice to not need this (especially because I have to use “capture child processes”, which makes me need to open the capture manually from /tmp/RenderDoc instead of listing them. Sometimes it doesn’t, though? Maybe that’s a bug too?):

#!/usr/bin/env bash
set -euo pipefail
GAME='zig-out/bin/x86_64-linux-gnu/game'
IFS=':' read -ra GAME_RPATH <<< "$(patchelf --print-rpath "$GAME")"
for path in "${GAME_RPATH[@]}"; do
    if [[ $path == *"SDL3"* ]]; then
        SDL3_LIBS="$path"
        break
    fi
done
LD_LIBRARY_PATH="$(patchelf --print-rpath "$SDL3_LIBS/libSDL3.so"):$LD_LIBRARY_PATH" \
    exec "$GAME"

Steps to reproduce

// foobar.c
int foobar_doImportantTask(void) {
    return 42;
}
// main.c
#include <stdlib.h>
#include <stdio.h>
#include <dlfcn.h>

typedef int (*FoobarProc)(void);

int main(void) {
    void *foobar_handle = dlopen("libfoobar.so", RTLD_NOW);
    if (foobar_handle == NULL) {
        fprintf(stderr, "Couldn't load libfoobar.so!\n");
        return EXIT_FAILURE;
    }
    FoobarProc foobar_doImportantTask = (FoobarProc)dlsym(foobar_handle, "foobar_doImportantTask");
    printf("Important task result: %d\n", foobar_doImportantTask());
    dlclose(foobar_handle);
    return EXIT_SUCCESS;
}
$ cc -shared -o libfoobar.so foobar.c
$ cc '-Wl,-rpath,$ORIGIN' -ldl -o main main.c
$ ./main
Important task result: 42
$ renderdoccmd capture -w ./main
Launching './main'
Couldn't load libfoobar.so!
'./main' finished executing.

Environment

baldurk commented 2 months ago

I'll need to investigate this, but my initial reaction is that this looks like it may not be feasible to fix especially seeing as when googling I found a bug that address sanitiser has the same issue with the same cause and the same LD_LIBRARY_PATH workaround (28164 on llvm-project github, not linking to avoid the annoying auto-backlink github does).

Can you give more details about this please?

especially because I have to use “capture child processes”, which makes me need to open the capture manually from /tmp/RenderDoc instead of listing them. Sometimes it doesn’t, though? Maybe that’s a bug too?

There is no circumstance where you should have to load a capture from manually - if you have enabled child process capturing then when you launch e.g. bash it should display a list of child processes and you can select your program to connect to it. Does your shell script exit early after launching your program? Normally I'd expect the script's lifetime to be a superset of the program but as long as it lives at least long enough to notify the UI of the child process you should follow this UI flow naturally. If the script exits immediately after launching the process then the parent-child link may be lost, though in that situation you could use File -> Attach to running instance.

Please also note, renderdoccmd is not a user-facing tool and should not be used or relied on, it is for internal use only and you should launch programs for capture from the UI instead.

OrichalcumCosmonaut commented 2 months ago

I'll need to investigate this, but my initial reaction is that this looks like it may not be feasible to fix […]

Ah, that’s unfortunate. Since this is only a development tool, continuing to use the workaround should be fine either way.

I was looking through the man pages of things libdl provides, and it seems like there could be a solution involving dlmopen()… although if the ASAN developers were unable to find one, then maybe not.

There is no circumstance where you should have to load a capture from manually […]

Most of the time, when capturing a frame with F12 with that script, it doesn’t get added to the list of captures in the GUI, and it doesn’t open it automatically if there was only one. The tab that appears when a process is connected to also seems to briefly appear (on the order of a frame or a few) and then closes. The script doesn’t seem to be exiting early, if I remove exec and add an echo afterwards it still does this.

[…] it is for internal use only and you should launch programs for capture from the UI instead.

The same issue also occurs when using the GUI.

baldurk commented 2 months ago

If the process tab is only appearing for a frame or two that sounds like the bash script is exiting very quickly.

Can you do this:

  1. Add something to the start and end of the script that prints its PID to a file so that you know its PID and when it starts and exits.
  2. Launch the script with child process capturing, let it launch your program, and then pause while your program is running.
  3. Verify that both the bash script and your program are both alive and that the bash script has not exited yet.
  4. Go into File -> Attach to running instance in the UI and see which processes are listed.
OrichalcumCosmonaut commented 2 months ago

The bash script and the game both remain alive, and Attach to Running Instance shows the bash script and the game.

OrichalcumCosmonaut commented 2 months ago

Ah, I think the issue is that env exits too quickly. Not really sure how to avoid that.

If I replace the shebang with #!/nix/store/i1x9sidnvhhbbha2zhgpxkhpysw6ajmr-bash-5.2p26/bin/bash it works.

baldurk commented 2 months ago

Oh I see so env is running as an extra process as an immediate parent of bash that runs and exits instantly.

I don't know anything about NixOS but do you have a normal PATH that can find programs? What happens if instead of running the script directly you put just bash as the executable to run, allow it to be found in PATH, and pass the script as a command line argument. Presumably running via bash directly will omit the invocation of env.

OrichalcumCosmonaut commented 2 months ago

NixOS does have a normal $PATH, it’s definitely longer than other distributions but it does work:

$ echo $PATH
/nix/store/n49v63dcj6058jrwazjaqqycv2bl50jx-harfbuzz-9.0.0-dev/bin /nix/store/wv2j9r10cq7xhkwrwf8rqhnzpg1bprsx-graphite2-1.3.14/bin /nix/store/65lhpq7pbc6nnngfp030ddglb71xixg9-pkg-config-wrapper-0.29.2/bin /nix/store/mi8ylnwvsvsjmnh85x33pi74xivpgcwi-qoi-unstable-2023-08-10/bin /nix/store/q27x7z1drmhk6yc518fv65sr0rszxjy0-shaderc-2024.0-bin/bin /nix/store/ws9fz232czsmrvl8hhzqsqfhwj73g260-msdf-atlas-gen-1.3/bin /nix/store/xhgs2p5dn42jhiaiwr4ryvnf0qg2f3rk-zig-0.13.0/bin /nix/store/0av1a7ya0y4p30qgay933f31prb2m1xk-zls/bin /nix/store/dv5vgsw8naxnkcc88x78vprbnn1pp44y-patchelf-0.15.0/bin /nix/store/62zpnw69ylcfhcpy1di8152zlzmbls91-gcc-wrapper-13.3.0/bin /nix/store/zw4dkm2hl72kfz7j2ci4qbc0avgxzz75-gcc-13.3.0/bin /nix/store/xfk033jdxdc5758wrpb0h2w462zlsb73-glibc-2.39-52-bin/bin /nix/store/cnknp3yxfibxjhila0sjd1v3yglqssng-coreutils-9.5/bin /nix/store/pg90p34kys2famxnq7925sbgj4jrnsi8-binutils-wrapper-2.42/bin /nix/store/qsx2xqqm0lp6d8hi86r4y0rz5v9m62wn-binutils-2.42/bin /nix/store/cnknp3yxfibxjhila0sjd1v3yglqssng-coreutils-9.5/bin /nix/store/5my5b6mw7h9hxqknvggjla1ci165ly21-findutils-4.10.0/bin /nix/store/fy6s9lk05yjl1cz2dl8gs0sjrd6h9w5f-diffutils-3.10/bin /nix/store/9zsm74npdqq2lgjzavlzaqrz8x44mq9d-gnused-4.9/bin /nix/store/k8zpadqbwqwalggnhqi74gdgrlf3if9l-gnugrep-3.11/bin /nix/store/2ywpssz17pj0vr4vj7by6aqx2gk01593-gawk-5.2.2/bin /nix/store/nzzl7dnay9jzgfv9fbwg1zza6ji7bjvr-gnutar-1.35/bin /nix/store/7m0l19yg0cb1c29wl54y24bbxsd85f4s-gzip-1.13/bin /nix/store/cx1220ll0pgq6svfq7bmhpdzp0avs09w-bzip2-1.0.8-bin/bin /nix/store/70anjdzz5rj9lcamll62lvp5ib3yqzzr-gnumake-4.4.1/bin /nix/store/i1x9sidnvhhbbha2zhgpxkhpysw6ajmr-bash-5.2p26/bin /nix/store/6rv8ckk0hg6s6q2zay2aaxgirrdy4l6v-patch-2.7.6/bin /nix/store/xzdawyw3njki7gx2yx4bkmhdzymgjawm-xz-5.6.2-bin/bin /nix/store/rnndls2fiid1sic81i06dkqjhh24lpvr-file-5.45/bin /home/quinn/Documents/game/.direnv/bin /run/wrappers/bin /home/quinn/.local/share/flatpak/exports/bin /var/lib/flatpak/exports/bin /home/quinn/.nix-profile/bin /nix/profile/bin /home/quinn/.local/state/nix/profile/bin /etc/profiles/per-user/quinn/bin /nix/var/nix/profiles/default/bin /run/current-system/sw/bin
$ bash --version
GNU bash, version 5.2.26(1)-release (x86_64-pc-linux-gnu)
Copyright (C) 2022 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>

This is free software; you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.

If I put bash in the “Executable Path” field and click Launch, RenderDoc shows an error popup that says “Invalid application executable: bash”.

OrichalcumCosmonaut commented 2 months ago

Putting /nix/store/i1x9sidnvhhbbha2zhgpxkhpysw6ajmr-bash-5.2p26/bin/bash in the executable field, correcting the working directory, launching, double-clicking on the child process and then doing a capture with F12 or the GUI does work as expected, maybe except for the fact that RenderDoc names the capture starting with bash.

baldurk commented 2 months ago

OK yep I can see that the launch process isn't allowing non-absolute paths to search PATH for the executable. I don't think there's a strong reason for that, so I can fix that at least so that a plain bash will work.

That's probably the only thing I can do about the issues you're hitting though.

baldurk commented 2 months ago

That commit should allow you to run just plain bash as an executable, as long as it's in PATH it will run, and you can run the script from there. I looked at the options for addressing the original issue and none of them I feel are merited for the marginal benefit but potentially high costs.