Skip to content

Instantly share code, notes, and snippets.

@Muqsit
Created July 26, 2025 12:50
Show Gist options
  • Save Muqsit/aa7273e2c0b8c236b75e017b19374ec8 to your computer and use it in GitHub Desktop.
Save Muqsit/aa7273e2c0b8c236b75e017b19374ec8 to your computer and use it in GitHub Desktop.
Segfault? PHP / PocketMine-MP steps to generate a backtrace on linux

A ssegmentation fault in PHP is often the cause of a PHP extensions written in C, and more specifically one with a memory management error. However, I have encountered my share of segfaults during network programming, but I pair these with PHP's pthreads extension, so it would explain why. It is also possible to encounter segfaults from infinite recursion, but the root cause is still more or less the same - something weird in memory management.

Step 1: Compile PHP binary with debugging symbols

Below I compile with -g flag to enable PHP's GD extension, -t linux64 because I am running on a Ubuntu server, and -P5 to install PM5's dependencies and the right versions for those dependencies. YMMY. See PHP-Binaries for more flags and info.

git clone https://github.com/pmmp/PHP-Binaries.git
cd PHP-Binaries
./compile.sh -g -d -n -t linux64 -j4 -P5

Step 2: Run PocketMine inside GDB

Run gdb against the PHP executable from the above step. Then run PocketMine in GDB. If you are running PocketMine from source, you would run ./src/PocketMine.php instead.

gdb /path/to/PHP-Binaries/bin/php7/bin/php
(gdb) run ./PocketMine-MP.phar

Your PocketMine server should be running as normal. It may be a little slow because the debugger causes some noise, but it should still run at an acceptable CPU load.

Boring part. Now we wait for the segfault to happen. If you can cause the segfault at will, good for you - go ahead and do that right now.

DO NOT EXIT GDB once the segfault happens - there is still a step 3!

Step 3: Get a readable backtrace

source here loads the .gdbinit file that defines the command zbacktrace which generates a readable backtrace.

(gdb) source /path/to/PHP-Binaries/install_data/subdir/php/.gdbinit
(gdb) zbacktrace
[0x7f8809026350] Ds\Set->contains(object[0x7f88090263a0]) [internal function]
[0x7f86f3271b00] cosmicpe\item\enchantment\utils\EnchantmentUtils->getNearbyEntities(object[0x7f86f3271b50], 2025.000000, array(0)[0x7f86f3271b70], reference)
phar:///home/cosmicpe/void/plugins/CosmicPE_v0.0.2.phar/src/cosmicpe/item/enchantment/utils/EnchantmentUtils.php:143

In my case, the cause was the php-ds extension's Set implementation doing something unpleasant. Not only can I infer that from the backtrace, I also know the Set::contains() call responsible for it.

You may run exit inside GDB when you are done.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment