CVE-2014-0185: PHP-FPM sockets unavailable after updating PHP

Want to help support this blog? Try out Oh Dear, the best all-in-one monitoring tool for your entire website, co-founded by me (the guy that wrote this blogpost). Start with a 10-day trial, no strings attached.

We offer uptime monitoring, SSL checks, broken links checking, performance & cronjob monitoring, branded status pages & so much more. Try us out today!

Profile image of Mattias Geniar

Mattias Geniar, May 13, 2014

Follow me on Twitter as @mattiasgeniar

Reference: CVE-2014-0185

A few days ago, a security update to PHP was released that corrected the default permissions on the listening socket that PHP-FPM would create. If your PHP-FPM pool had a configuration like the one below, without an explicit owner/group/mode, it would default to user root, group root and mode 0666 (the snippet below is the default content of the php-fpm pool configuration).

;listen.owner = nobody
;listen.group = nobody
;listen.mode = 0666

The example above is in comments (note the lines starting with a semicolon), so wasn’t active. That means the defaults of root/root/0666 were active. Sockets were created with the following permissions (read- and writable by all).

~# stat /var/run/php-fpm/pool.sock
...
Access: (0666/srw-rw-rw-)  Uid: (    0/    root)   Gid: (    0/    root)

The recent update to PHP (as of 5.3.38, 5.4.28 and 5.5.11) changes those default permissions, if not explicitly defined, to 0660. Meaning the socket is now only readable/writable by user root and group root. If your configuration depended on the “other” privileges being correct (meaning anyone can write to the socket and have it execute as the user php-fpm was executing as), your config will now break. These are the new default permissions.

~# stat /var/run/php-fpm/pool.sock
...
Access: (0660/srw-rw----)  Uid: (    0/    root)   Gid: (    0/    root)

So a more safe 0660 for everyone. Your Apache or Nginx logs can however trigger an error like this after the update, because the socket is unavailable to them.

HTTP/1.1 500 Internal Server Error
...

[error] [client 127.0.0.1] (13)Permission denied: FastCGI: failed to connect to server "/var/www/cgi-bin/http-socket.fcgi": connect() failed
[error] [client 127.0.0.1] FastCGI: incomplete headers (0 bytes) received from server "/var/www/cgi-bin/http-socket.fcgi"
...
127.0.0.1 - - [x/x/2014:00:00:00 +0200] "HEAD / HTTP/1.1" 500 - "-"

There’s no reason to change your Apache configurations or FastCGI configs. The fix is in applying the correct permissions in your PHP-FPM pool configuration. Uncomment the listen.* parameters and set them explicitly.

listen.owner = httpd
listen.group = httpd
listen.mode = 0660

Remember: it’s the webserver that is passing the request on to PHP-FPM, so the user that is running as the webserver needs read/write permissions on the Socket. In the case of Apache, that may be the ‘httpd’ or ‘www-data’ user, in the case of Nginx that’ll be the ‘nginx’ user.

If you’re struggling with permissions and need a quick resolution, you can change your PHP-FPM pool configuration (temporarily!!) back to the default permissions of earlier:

...
listen.mode = 0666

The new permissions and owner/group are only applied once you restart your PHP-FPM daemon.

If you’re struggling with a PHP configuration no longer working after an PHP update, triggering HTTP 500 errors and throwing messages in your error logs about “failed to connect to server” (FastCGI), keep this in mind.

More info can be found on the PHP Sec Bug #67060: sapi/fpm: possible privilege escalation due to insecure default configuration page.



Want to subscribe to the cron.weekly newsletter?

I write a weekly-ish newsletter on Linux, open source & webdevelopment called cron.weekly.

It features the latest news, guides & tutorials and new open source projects. You can sign up via email below.

No spam. Just some good, practical Linux & open source content.