Ben Ramsey

Contributing to PHP Core

I’ve been accepted to speak at ZendCon this year. One of the three talks I’ll be presenting is a new one: “Contributing to Core: My Journey to Add array_column() to the PHP Core.” While PHP conferences sometimes include talks or tutorials on creating PHP extensions or the intricacies of the PHP internals, I’ve never seen a talk about one’s personal experiences contributing to core, from start to finish, and how one would go about getting started. That’s what this talk is about.

The talk won’t include much code but will, rather, cover how to propose a new language feature from beginning to end. For some, this can be daunting. Even though I’ve been around the PHP community for many years, and I know many folks on the internals mailing list, I was still new to the process myself, especially since the process is new. So, I thought it fitting to introduce the process and share my experiences to demystify it and get others involved in improving and evolving the PHP language.

In preparing to contribute to the PHP core and maintain a good, clean environment for testing and updating patches, I needed to put together a virtual machine that I could build up and tear down quickly and often. I did this by using VirtualBox and Vagrant with a vanilla Ubuntu Vagrant box. The result is the vagrant-php-src-dev project, a collection of Puppet scripts that creates a basic environment to use for modifying, building, testing, and contributing to the PHP core. It is not full-featured on purpose. However, it does do some helpful initial system set-up, clones the php-src repository, and provides some helpful documentation and scripts for connecting to your own fork of the php-src repository.

I created this for my own development purposes, but I welcome pull requests and suggestions to turn this into a useful resource for the entire community. Here are a few pointers I learned along the way, provided here mainly so I’ll be able to find them later but also to help others.

The Build Cycle

Building PHP can take a while, depending on what you’re including in your configure command. I provide a basic configure command in this project in ~/src/config.nice-5.5. It’s pretty simple, but running make after configuring PHP with this command will still take several minutes.

To shave off some of the build time, after making changes to the C source, there’s no need to run configure again (unless you need to change configuration), and there’s no need to make clean. Simply run make and the compiler will figure out what parts of the source changed and will build only those objects before stitching everything together into the php binary. If you’re working on a single function or class, this can greatly increase your development speed.

Of course, if you need to switch branches to test things in PHP 5.4 or 5.3, for example, you’ll need to make clean or, possibly, make distclean to clean up all the compiled objects and rebuild them when you run make again.

If php-src is clean because it’s a fresh clone of the repository, then don’t forget to run buildconf. This is usually the source of some head-scratching for me, until I remember I need to run it. So, if trying to run configure and it can’t be found, run buildconf first.

Additionally, I found it difficult to sift through the compiler warning messages that dumped out onto my screen when running make. If working on a particular section of code (ext/standard/array.c, for example), it can be a pain to find any warnings applicable to the code you’re writing. Sometimes, I wasn’t even aware that my code was generating warnings. To clearly see those warnings, it’s best to dump them to a log file, like this:

make 2> tee ~/php55-make.log

Then, you can look in ~/php55-make.log to see if your code produced any compiler warnings.

Running Tests

Hacking the PHP core requires running tests to ensure nothing is broken, and new tests should always be written to cover changes made to the core. However, it’s not very fun to run make test after every change you make, since this runs all the tests. This can take a while.

Instead, you may use the run-tests.php script to run individual tests. For example:

sapi/cli/php run-tests.php ext/standard/tests/array/array_column_basic.phpt

Beware, though, you will first need to set the TEST_PHP_EXECUTABLE environment variable with the path to the php binary you wish to use for the tests.

export TEST_PHP_EXECUTABLE=/home/vagrant/src/php-src/sapi/cli/php

Please note: After running make, the built php binary will be in the sapi/ directory (see above). If you run make install, it will also be installed in the path of the configured prefix.

Puppet Cookbook

The Puppet Cookbook website, along with the standard Puppet documentation, was an invaluable resource for figuring out how to write Puppet scripts for scripting my development environment. I highly recommend it.

More to Come

I want to share more about my experience over the next few months, leading up to my talk at ZendCon and following it. If you’ll be at ZendCon, please consider attending my talk. I’ll be happy to answer any questions.

Stay tuned for more on this subject!