Skip to content

Library Injection

brkzlr edited this page Jun 18, 2026 · 4 revisions

Library Injection

Library injection lets you load your own code into a running process. This is useful for hooking functions, modifying behavior at a deeper level or adding custom functionality that can't be achieved with simple memory edits.

PINCE supports two types of library injection:

  • .so files (shared objects): works on any Linux process, including WINE/Proton
  • DLL files: only works on WINE/Proton processes

How to Access It

Open the Memory Viewer window and go to Tools menu:

  • Inject .so file: for any Linux process (native or WINE/Proton)
  • Inject DLL file: for WINE/Proton processes only

.so Injection

To inject a shared object file:

  1. Make sure you're attached to a process
  2. Go to Tools -> Inject .so file
  3. Select your .so file from the file dialog
  4. PINCE will call dlopen() in the target process to load your library

If the injection succeeds, you'll see a success message. Your library's constructor function (if you defined one with __attribute__((constructor))) will run automatically when loaded.

How It Works

PINCE uses GDB to call dlopen() or __libc_dlopen_mode() in the target process. If GDB can't resolve these symbols (like in stripped binaries), PINCE has a fallback mechanism that:

  • Scans the process's memory maps for libc or libdl
  • Parses the ELF symbol tables to find the dlopen address
  • Manually calls it with your library path

This works even in sandboxed environments like Flatpak or Steam Runtime and works on both native Linux and WINE/Proton processes.

DLL Injection (WINE/Proton Only)

To inject a Windows DLL:

  1. Make sure you're attached to a WINE or Proton process
  2. Go to Tools -> Inject DLL file
  3. Select your DLL file from the file dialog
  4. PINCE will convert the path to WINE format and call LoadLibraryW in the target process

If the injection succeeds, you'll see a message showing the module handle address (like "The DLL has been injected at 0x7f1234560000").

How It Works

DLL injection is more complex because WINE processes run Windows PE binaries:

  1. PINCE locates kernel32.dll and ntdll.dll in the process memory
  2. Parses the PE export tables to find LoadLibraryW
  3. Finds a clean execution context by waiting for a syscall
  4. Converts your Linux path to WINE format (Z:\path\to\file.dll)
  5. Allocates memory in the process, writes the path and calls LoadLibraryW

This handles both 32-bit and 64-bit WINE processes.

Limitations

  • DLL injection only works on WINE/Proton processes. If you try to inject a DLL into a native Linux process, you'll get an error message.
  • Your library must be compatible with the target process architecture (32-bit or 64-bit).
  • The library file must be accessible from the target process. For sandboxed environments, make sure the path is valid inside the sandbox.

Use Cases

Common reasons to use library injection:

  • Function hooking: Replace or wrap game functions with your own code
  • Custom allocators: Intercept memory allocation calls
  • Logging: Add debug output to specific functions
  • Patches: Apply complex multi-step modifications atomically

For simpler patches like NOPing instructions or basic code injection, you might want to check out Modifying Game Code or Libpince Engine instead, which don't require creating external library files.

Clone this wiki locally