Quick answer: Mark a known-good and known-bad commit, let git bisect binary-search the range while you test each midpoint, and automate the test so bisect runs unattended to land on the exact breaking commit.
When something used to work and now does not, the fastest path to the cause is not reading code, it is binary search over history. git bisect halves the suspect range with every test, so even hundreds of commits collapse to one in a handful of checks.
How to bisect it
1. Start bisect with good and bad markers
Run git bisect start, then git bisect bad on the broken commit and git bisect good <old-sha> on a version you know worked. Git checks out the midpoint for you to test.
2. Test each checkout and mark it
Build and reproduce at each midpoint, then run git bisect good or git bisect bad. Git narrows the range by half each time and finally names the first bad commit.
3. Automate with a test script
If the repro can be scripted, run git bisect run ./test.sh where the script exits 0 for good and nonzero for bad. Bisect then walks the whole history unattended.
4. Handle large game assets
Commits that change binary assets may need a clean reimport or LFS checkout at each step. Add that to your test script, or skip purely-asset commits with git bisect skip if they cannot build.
Catching the ones you can't reproduce
The hardest version of this to fix is the one you can't reproduce — it only happens on a player's hardware, OS, driver, or save state, under conditions that simply aren't present on your machine. A report that says “it crashed” or “it froze” gives you nothing to act on, so the bug survives release after release while quietly costing you players.
Automatic error capture closes that gap. Each failure arrives with its full stack trace, the device and OS, the build number, and a breadcrumb trail of what the player did right before it broke, so even a failure you have never seen becomes a specific, reproducible issue. Fold identical failures into one signature ranked by how many players each hits, and your worklist sorts itself worst-first instead of arriving as a stream of vague complaints.
This is where a tool like Bugnet earns its place. Its SDK captures every error automatically with the full stack trace plus device, OS, memory, build, and game-state context, folds duplicates into one grouped issue with an occurrence count, and ties each to the build it first appeared on — so you fix the problem that hurts the most players first and confirm it is gone when its signature disappears from the next release.
Most of the time the fix is small. Seeing the failure clearly is the part that actually costs you.