-
Notifications
You must be signed in to change notification settings - Fork 193
Basic Usage
PINCE works a lot like Cheat Engine on purpose. If you already know CE, the main loop is basically the same: attach to something, scan for a value, narrow the results, add the useful address to the table, then edit or freeze it.
The Linux side changes some details though. PINCE uses GDB for debugging features, reads Linux process maps for scans and has Linux/WINE-specific pages for stuff like speedhack, signals, injection and Mono/IL2CPP.
If you prefer video, Guided Hacking made a good PINCE overview here (though it's pretty outdated now, good intro still): PINCE tutorial on YouTube.
If you prefer text, this page is the short version. It tries to explain where to start and where to go next, not every button in the program.
Click the monitor icon in the top-left of the main window. This opens the process selection window.
From there you can:
- type a process name or PID into the search box
- select a process and click
Open - double-click a process to attach
- press
Enterto open the selected process - click
Create Process[F1]to start an executable through PINCE
Create Process asks for:
- executable path
- optional arguments
- optional
LD_PRELOADpath
Use attach when the game/program is already running. Use create process when you want PINCE to launch it, especially if you need startup breakpoints, startup behavior or LD_PRELOAD.
Once attached, the scan controls unlock and the title area shows the process name and PID.
You can detach and reattach with Shift+F10. That is useful when you want to temporarily release the debugger without closing PINCE.
Most beginner usage is this loop:
- Attach to the target.
- Pick the value type, usually
Int32,Float32orInt(any)if you are not sure. - Enter the current value.
- Click
First Scan. - Change the value in-game.
- Enter the new value.
- Click
Next Scan. - Repeat until there are only a few results.
- Add likely results to the address table.
- Edit or freeze the value from the table.
Example with health:
- Health is
100, scan for100. - Take damage, health becomes
73. - Next scan for
73. - Heal to
90. - Next scan for
90. - Test the few remaining results by changing them.
If you do not know the exact value, use an unknown-value scan. Start with Unknown Value, then use scan types like Increased, Decreased, Changed or Unchanged as the value changes in-game.
The scan page covers the details: Scanning.
A quick starting point:
- health, money, ammo: try
Int32 - coordinates, speed, timers: try
Float32 - unknown integer size: try
Int(any) - mixed unknown value: try
Any(int, float) - text: use one of the string types
- bytes or signatures: use
ByteArray
Wrong type is one of the most common reasons a scan finds nothing. A value shown as 100 in the UI does not mean the game stores it as a normal 4 bytes integer. It could be float, double, encrypted, scaled, mirrored, server-side or only displayed text.
The default scan scope is meant to be useful without scanning the whole process.
If you get too many results, narrow normally with Next Scan first. If you get no results, then try changing value type, scan type, endianness or scan scope.
Common rough idea:
-
Basic: smaller and faster -
Normal: good default -
Read+Write: more writable memory -
Full: broadest, slowest and noisiest
For region details and Manage Scan Regions, see Scanning.
Scan results are temporary. The address table is where you keep values you care about.
After a scan, add interesting results to the table. From the table you can:
- edit the value
- freeze it
- change the displayed type or signed/hex representation
- add descriptions
- add manual addresses
- add pointer chains
- group entries
- save everything to a
.pctsession
Freezing is not magic. PINCE repeatedly writes the frozen value at the freeze interval. If the game writes the value again after PINCE does, you may still see it flicker or change. Some values need code modification, pointer work or a better address instead of a simple freeze.
For the full table docs, see Address Table & Sessions.
Use Ctrl+S or the disk icon to save a .pct session.
A session can save things like:
- address table entries
- groups
- scripts
- bookmarks
- structures
- notes
- process name
A session is not a save-state of the game. It does not save the target process memory. You still need to attach again later, and any plain dynamic addresses may be wrong on the next run.
If an address changes every restart, that is where pointers, pointer scanner results, module-relative addresses or scripts come in.
Useful pages:
PINCE can scan and edit many things while the target keeps running. You only need to stop it for debugger-style work, register editing, breakpoints, watchpoints, stepping or when you want the game frozen in place.
Default hotkeys:
-
F1: pause -
F2: break -
F3: continue
When the process is stopped, the process title turns red and shows [stopped].
The difference between pause and break is mostly the Memory Viewer behavior:
-
Pausestops the process without forcing the disassembly view to jump -
Breakstops the process and updates Memory Viewer to the current execution point
So use Pause if you do not want to lose your current disassembly location. Use Break if you want to see where the process currently is.
Memory View opens the advanced window.
It is where you go for:
- disassembly
- registers
- stack and stacktrace
- hex view
- breakpoints
- watchpoints
- finding what writes, reads or accesses an address
- patching instructions
- NOPing code
- bookmarks
- structures
- library injection
- Mono/IL2CPP tools
- the Libpince Engine
The layout is split into disassembly, registers, hex view and stack areas. Right-click menus matter a lot in this window.
For the full page, see Memory Viewer.
If freezing a value is not enough, the next step is usually finding the code that writes it.
Typical flow:
- Add the value to the address table.
- Right-click it.
- Use
Find out what writes this address. - Trigger the value change in-game.
- Look at the instruction that wrote it.
- Decide whether to patch the instruction, inspect registers or find the object base from the offset.
If the instruction looks like [rax+0x10], then rax is probably some object base and 0x10 is a field offset. That is where structures start becoming useful.
Relevant pages:
The main window has an Enable Speedhack checkbox and speed value.
Default hotkeys:
-
Ctrl+Shift+S: toggle speedhack -
Ctrl+Shift+Up: increase speed -
Ctrl+Shift+Down: decrease speed
Speedhack works by hooking time-related functions. Native Linux targets and WINE/Proton targets are handled differently. Some games use their own timing, server timing or anti-cheat checks, so speedhack is not guaranteed for every target.
Details are here: Speedhack.
Common defaults:
-
F1: pause process -
F2: break process -
F3: continue process -
Ctrl+S: save session -
Ctrl+O: open session -
Shift+F10: detach or reattach -
Delete: remove selected address table entries -
Space: toggle selected freeze checkbox -
Ctrl+Space: toggle children -
Ctrl+B: browse selected address in Memory Viewer -
Ctrl+D: disassemble selected address in Memory Viewer -
Ctrl+Shift+S: toggle speedhack -
Ctrl+Shift+Up: speedhack faster -
Ctrl+Shift+Down: speedhack slower
You can change hotkeys in Settings -> Hotkeys.
A decent reading order for new users:
- Scanning
- Address Table & Sessions
- Memory Viewer
- Search Opcodes & Watchpoints
- Pointers
- Pointer Scanner
For specific features, jump straight to the matching page from the sidebar. This page is only meant to get you oriented enough that the rest of the wiki makes sense.