Introducing xdebug

Cal Evans   December 10, 2007   16 Comments on Introducing xdebug

Introducing xdebug

By: Stefan Priebsch

Other Articles in the Series

Part One: Introducing xdebug
Part Two: Tracing PHP Applications with xdebug
Part Three: Profiling PHP Applications With xdebug
Part Four: Debugging PHP applications with xdebug
Part Five: Creating Code Coverage Statistics with xdebug

This article is the first installment of a five-part series of articles covering xdebug, a free and open source
swiss army knife tool for PHP developers.
xdebug is a PHP extension created by Derick Rethans, one of the PHP core developers. This week, we will show you how to install xdebug and introduce you to some of the basic features.
In the subsequent parts of this article series, we will have a closer look at one of xdebug’s main features,
namely tracing, profiling, debugging, and code coverage.

Installing the xdebug extension

First of all, we need to install xdebug. As I write this article, the current version is 2.0.1.
Since the internal PHP APIs may change between different PHP releases, you must make sure
that the version of xdebug you are installing matches the PHP version you are using.

xdebug does not work with any PHP versions before 4.3, and will probably not yet work with PHP 6.
This is not a real problem, however, since PHP 4 will reach its end of life in 2008,
and PHP 6 will probably not be available before the end of 2008. This gives you enough
time to get used to xdebug so you can use it as a helpful tool when it comes to migrating your PHP code
to work with the next major or minor PHP release.

Installing on Unix

Before we dig into xdebug’s features, let us get the installation done.
On Unix, you can try installing xdebug through PECL, the PHP extension community library.
The PECL installation does not work on all systems, though. If the PECL installation does not
work out for you, you must compile xdebug from source. But first, try the PECL installation:

pecl install xdebug

If the PECL installation does not work for you, you need to compile xdebug from source.
In addition to a C compiler, you will need appropriate versions of the
usual build tools (Autoconf, Automake and Libtool). If they are not already installed
on your system, you can usually install them by running apt-get install build-essential
on Ubuntu or Debian.
When configuring xdebug, you will get an error when any required tool is missing. In this case,
just install the missing tool, then configure xdebug again.

Furthermore, two helper programs, phpize and php-config that are a part of PHP, are required.
If you have not compiled PHP from source, you will probably have to install
the developer packages using your distribution’s package manager.
On Ubuntu or Debian, you can install the PHP development tools using a command like
apt-get install php5-dev.

Please note that phpize and php-config must match the PHP version you are using,
so do not just copy them to your system from some other PHP installation. When your development tools are in place, you can download and compile xdebug:

tar -xzf xdebug-2.0.1.tgz
cd xdebug-2.0.1
./configure --enable-xdebug --with-php-config=/usr/bin/php-config
cp modules/ /usr/lib/apache2/modules/

The php-config path may be different on your system,
and depending on the your Apache installation directory,
you may need to copy to another directory.
Instead of copying the file, you can of course create a link as well.

Installing on Windows

If you are a Windows user, you can download a compiled DLL from
Select the PHP version you are using and click the appropriate link in the Windows modules section in the right column of the page.

You must use the non-debug version of PHP with xdebug. If you have downloaded PHP from,
debugging should not be enabled. When in doubt, check the Debug Build entry in the phpinfo() output.

I would recommend putting the downloaded DLL into PHP’s extension directory ext, which should be a subdirectory of your PHP directory. You can put the DLL to any directory, provided that you state the full path to the DLL in php.ini.

Activating the xdebug extension

Now you have the xdebug extension ready, either as a shared object on Unix or a DLL on Windows.
To activate xdebug, you must add an entry to php.ini. On Windows, use:


On Unix, use:


instead. The path to PHP’s extension directory or Apache’s module directory may differ on your system. Make
sure you specify the full absolute path, not a relative path.

Please note that on Windows, we use zend_extension_ts, which means that a
thread-safe extension is loaded, whereas on Unix, we a non-threadsafe extension is loaded.
Depending on your system setup,
you must decide for yourself wether you need a thread safe or non-thread-safe extension.
If you are not sure wether your PHP installation is thread-safe,
check the Thread Safety entry in the phpinfo() output.

You should not load any other Zend extensions while working with xdebug,
because they would probably use the same internal mechanisms in the Zend engine,
which usually calls for trouble. Not all Zend extensions work together with xdebug.
Since you will probably use xdebug on a development system rather than a live system, this is
no serious limitation. The most important rule is to not mix xdebug with other PHP debugger extensions.

Having restarted your web server because we changed php.ini, you can check
the output of phpinfo() or run php -m at the command line.
In each case, xdebug must be listed twice, once as a PHP extension, and as a Zend extension as well.

Take care when you are updating PHP with xdebug installed. If the internal APIs change between the PHP
versions (which does not happen on every new version, but will certainly happen when you are close to a project deadline), the new version of PHP will probably not start or at least give you funny errors.
If need be, you can always get away with disabling xdebug, at least temporarily, to get an updated
PHP version to work and re-enable xdebug as soon as a new version is released that works with the newer API version.

There are quite some php.ini switches to configure xdebug,
but most of them have sensible deafult values,
so we can start using xdebug without worrying about configuration settings right now.
We will take a look at the most important configuration settings as we need to.

Improved var_dump() output

Let’s face it: the most widely used PHP debugger is var_dump().
Given the dynamic nature of PHP, and the fact that PHP is a scripting language, there is nothing wrong
in using var_dump() – I do it all the time. The drawback is that you have to modify your
program to debug it. The more var_dump() statements you put into your code, the more likely
it is that you’ll forget to remove them all once you have found and fixed your bug.

xdebug offers interesting alternatives to the extensive use of var_dump() statements
for debugging your code, which we will get to know in the next and last article of this series. But for now,
you’ll be glad to hear that xdebug even improves our beloved var_dump() debugger.

When the xdebug extension is loaded, the output of PHP’s var_dump() function is automatically
beautified for better readability, as the following screenshot shows:

You can configure the way xdebug formats the var_dump() output by various php.ini settings.
First of all, you can change the length of strings that xdebug displays. The default
value is 512; longer strings are automatcally truncated.

Wether you want xdebug to display the full string depends on the situation, and the size of data you work with. If you work with big strings, the var_dump() output can get long and hard to read, thus is is a good idea truncate strings for better overview. On the contrary, if you are looking for a specific value in the output, you will probably want the strings to be displayed in full length.

To change the string length xdebug displays, add

xdebug.var_display_max_data=<your preferred value>

to php.ini and restart your web server so that this setting takes effect.
Alternatively, just like you can change various php.ini settings of the PHP core at script
runtime by ini_set, you can add

ini_set('xdebug.var_display_max_data', <your preferred value>);

on top of your script to make sure the ini_set-command is executed before your first var_dump() is encountered, otherwise your runtime setting will not take effect.
Configuring xdebug at runtime with ini_set saves you from restarting your web server every time you want to modify the xdebug configuration and makes you much more flexible.

You can also control the number of array elements or object properties that xdebug displays. This is done by modifying the xdebug.var_display_max_children setting, which defaults to 128. This value should be sufficient to display all properties of your objects, but if you work with large arrays, you might still need to increase this value.

If you work with nested objects and arrays, you may want to modify the xdebug.var_display_max_depth setting. This setting has a default value of 3, which means that three nested levels of array elements and object relations are displayed.

You can also dump the values of the superglobal variables using the xdebug function xdebug_dump_superglobals(). As the superglobals, especially $_SERVER,
are arrays that contain many values, you must explicitly tell xdebug which array keys you would like to see.
To do this, set xdebug.dump.<superglobal name> where <superglobal name> is one of
Use the array key(s) that you want xdebug to display as argument, using a comma-separated list if you
want to display more than one key per superglobal variable. You can use * as a wildcard
to display all keys, which can be useful for $_GET and $_POST.


ini_set('xdebug.dump.SERVER', 'HTTP_HOST, SERVER_NAME');

in your PHP script or setting


in php.ini will display the value of $_SERVER['HTTP_HOST'] and $_SERVER['SERVER_NAME']. To display all GET parameters that were passed to the script, use


By default, xdebug does not dump undefined values, but just skips the respective array keys.
To force display of undefined values, set xdebug.dump_undefined to On. I would
recomment turning xdebug.dump_undefined on, because it can be quite confusing if you.

You may wonder why xdebug supports configuring displaying select items of superglobal variables, when the
same effect could be achieved with a number of var_dump() statements.
First of all, you can have values of different superglobals displayed in one spot in a very readable way.
Second, and more imporant, xdebug does not only show these superglobals when you call
xdebug_dump_superglobals(), but also when any error occurs in your script, as
we will see in the next section.

Better error messages

xdebug also improves the way PHP displays error messages by automatically displaying a stack trace along with
every PHP error message, warning and notice.
This stack trace lists the history of function calls that lead to
an error. As PHP programs become more and more object-oriented,
sometimes errors tend to show up deep inside libraries or helper
objects. The stack trace allows you to quickly find out where the
code piece that caused an error was originally called from.

Since version 5.0, PHP also has a native function debug_print_backtrace()
that displays the stack trace, but you’d have to call this function explicitly each time
an error occurs, which means that you would have to create a custom error handler just
to display stack traces along with error messages. Also, the stack trace created by
xdebug is easier to read than the output of the native PHP function.

Like PHP itself, xdebug only displays error messages when display_erorrs is set to On in php.ini. On a development system, this should be the case. If not, add

ini_set('display_errors', 'Off');

to your script to change the setting at runtime.

Looking at this stack trace, you can see that the function foo() was called, which
called bar(), which in turn called baz(). In addition to the name of the calling
functions and where they are located in the source code, xdebug displays a timestamp and the amount of
memory used by the script when the function was called.

In the previous section, we have already learned how to configure xdebug to display values of superglobal variables.
In addition, you can configure xdebug to display the current values of local variables as well.
To display local variables along with every error message, you need to add


to php.ini. You can use ini_set as well, which we won’t repeat mentioning from now on.
Just keep in mind that you can do a lot of configuration at runtime, but you can obviously not
change settings that affect work that is done before your script actually starts.

By the way, the php.ini settings xdebug.var_display_max_data, debug.var_display_max_children, and xdebug.var_display_max_depth that we used above to control the formatting of the var_dump() output also affect the format of variables that xdebug outputs in error messages. The same holds true for display of superglobals.

There is even more. With xdebug.collect_params, you can configure xdebug to display information about the parameters that were passed to a function. xdebug.collect_params takes a numeric parameter, with 0 meaning no additional information, and 4 meaning to display the variable name and always the full contents of each function parameter. A value of 3 will display name and parameter, but honoring the configuration settings mentioned above and thus truncating long variable content. A value of 1 will display the type and number of elements only, whereas 2 will in addition display the full information in a tooltip. Using a tooltip is very convenient for online viewing, but not really suitable for printing the information.

Here is the xdebug configuration used to create the following screenshot:


This screenshot was taken using the following xdebug configuration:

Please note that the more information you ask xdebug to collect during script execution, the more memory and computing time it will use, thus slowing the execution of your script. Make sure to only enable xdebug on development systems, and never on production systems. It is not a wise idea to display error messages as part of the HTML result on production systems, and it is even less of a good idea to enrich this information with stack traces and potentially variable values. Imagine your web site displaying your database username and password to everybody just because you use an uninitialized variable!

Since superglobal variables should not change at runtime,
xdebug by default displays them only on the first error message, not in every error message.
If you want xdebug to repeat dumping the global variables on every error, use


Please note that the extended error
display of xdebug does not work if you define a custom error handler
using register_error_handler(). This is because xdebug
internally uses the same mechanism. Should your scripts use a custom
error handler, you can still use the function
to output the stack trace in your custom error handler.

Object-oriented code uses exceptions when something goes wrong. Since an exception is not an error,
xdebug will not display a stack trace when an exception is thrown, but only if that exception is uncaught.
That is because an uncaught exception is a fatal error.
To can configure xdebug to display a stack trace whenever an execption is thrown, use


Recursion Limit

Another very useful feature is the fact that xdebug limits recursion depth,
thus preventing endless recursion, which usually makes PHP segfault on Unix.
On Windows, PHP even locks up the whole system when it falls into endless recursion, which
is usually far worse than having PHP segfault.

xdebug prevents endless recursion by stopping the script once a pre-defined nesting depth is reached.
This is, in effect, a limit of the stack size. Every recursive function call will increase the stack size,
but also nested regular function calls increase the stack size.
The default value is 100 and this feature is enabled by default.
You can modify this limit, which might be necessary if you
work with a script that works on deeply nested recursive data structures.

xdebug.max_nesting_level=<your preferred value>

Bear in mind, however, that xdebug does not prevent endless loops with for, while or similar, since they do not increase the stack size. You can easily put an additional counter into such loops, however, that just kills the script after a ridiculously high number of repetitions. I would not recommend doing this in production code, though, since a program can can never tell wether a loop is endless.


xdebug is a small, but very useful tool in PHP development.
It should be installed and activated on every PHP installation that is used for development.
You should not run xdebug on a production system, though, because most features degrade
performance. Personally, I would never want to miss xdebug a single day on my development system,
and if it is just for the better formatting of the var_dump() output.

Today, we have just scratched the surface of what xdebug
can do to make your every day’s life as a developer much easier.
Next week, we will explore the tracing features of xdebug.
Tracing helps you better understand your applications, and can be a replacement
for putting loads of var_dump() statements into your code.

Make sure you check back here next week for the second part of this series of xdebug articles.
Until then: Happy coding – with xdebug enabled.

About the author:

Stefan Priebsch has been solving IT problems for over 25 years.
He is founder and CEO of e-novative GmbH, one of the first German IT
consultancies offering PHP-based solutions.
Stefan holds a university degree in computer science,
is an internationally recognized PHP expert, book author, trainer and consultant.
You can reach him at

About Cal Evans

Many moons ago, at the tender age of 14, Cal touched his first computer. (We're using the term "computer" loosely here, it was a TRS-80 Model 1) Since then his life has never been the same. He graduated from TRS-80s to Commodores and eventually to IBM PC's. For the past 10 years Cal has worked with PHP and MySQL on Linux OSX, and when necessary, Windows. He has built on a variety of projects ranging in size from simple web pages to multi-million dollar web applications. When not banging his head on his monitor, attempting a blood sacrifice to get a particular piece of code working, he enjoys building and managing development teams using his widely imitated but never patented management style of "management by wandering around". Cal is happily married to wife 1.31, the lovely and talented Kathy. Together they have 2 kids who were both bright enough not to pursue a career in IT. Cal blogs at and is the founder and host of Nomad PHP