ZF-11921: Race condition in plugin loader include file cache

Issue Type: Bug Created: 2011-12-01T10:10:04.000+0000 Last Updated: 2012-11-21T00:46:58.000+0000 Status: Open Fix version(s): Reporter: Mikko Koppanen (mkoppanen) Assignee: Matthew Weier O'Phinney (matthew) Tags: - Zend_Loader

Related issues: Attachments:


There seems to be a race condition in Zend_Loader_PluginLoader. The symptoms are there is a missing '<?php' in the include file. I have analysed the code a bit and the following looks like a plausible explanation:

The code that appends the files to include file cache is not atomic and in some cases this can cause <?php to be omitted from the include file.

I think roughly the following happens:

a) Process 1 enters the routing, checks that file does not exist and adds '<php' to the string b) Process 1 starts file_put_contents c) At the same time process 2 enters the routine, checks that file does not exist and gets the file contents

If the C happens before file has been written the end results could end up being corrupted. This can be fixed by adding RW locking into the routine.

<pre class="highlight">
    protected static function _appendIncFile($incFile)
        if (!file_exists(self::$_includeFileCache)) {
            $file = '<?php';
        } else {
            $file = file_get_contents(self::$_includeFileCache);
        if (!strstr($file, $incFile)) {
            $file .= "\ninclude_once '$incFile';";
            file_put_contents(self::$_includeFileCache, $file);


Posted by Yosh de Vos (yosh) on 2012-08-23T10:37:43.000+0000

I have the same problem. All worked fine in our development environment, but as soon as I deployed it to production the contents of plugin loader cache file is returned to the webbrowser because of the missing <?php tag.

Multiple requests try to generate the file at the same time causing problems. Locking the file should solve this problem.

Posted by Lauri Elevant (clon) on 2012-11-21T00:46:58.000+0000

This bug seems to occur a few times a year, especially after new deployments. It is rather annoying as the site stays down until you delete the corrupted file.

We seem to have fixed the race condition with a simple locking mechanism - see the code below. Anyone with the paperwork done can perhaps commit this.

<pre class="highlight"> 
        if ($stream = fopen(self::$_includeFileCache, 'c+')) {
            flock($stream, LOCK_EX);
            $file = stream_get_contents($stream);
            if (empty($file)) {
                $file = '<?php';
            if (!strstr($file, $incFile)) {
                $file .= "\ninclude_once '$incFile';";
                fseek($stream, 0);
                fwrite($stream, $file);
            flock($stream, LOCK_UN);

Have you found an issue?

See the Overview section for more details.


© 2006-2018 by Zend, a Rogue Wave Company. Made with by awesome contributors.

This website is built using zend-expressive and it runs on PHP 7.