Fixing PHP Fatal error: Allowed memory size of (X) bytes exhausted.

This is a guide on how to fix one of PHP’s most common fatal errors: The memory exhausted error.

Here is an example of what this error might look like.

Fatal error: Allowed memory size of 134217728 bytes exhausted (tried to allocate 32 bytes) in your-script.php on line 4

PHP’s memory limit.

If you encounter this error, then it means that your PHP script has used up more memory than it is allowed to.

If you open the php.ini configuration file that your web server is using, you will come across the following directive.

; Maximum amount of memory a script may consume (128MB)
; http://php.net/memory-limit
memory_limit = 128M

The memory_limit directive defines the maximum amount of memory that a PHP script can consume. In the example above, you can see that the memory_limit directive is set to 128MB.

This means that if one of my PHP scripts consumes more than 128MB in memory, the memory exhausted error will be thrown and the script will die.

If you do not have access to your php.ini file, then you can check what your server’s memory limit is using PHP’s init_get function like so:

echo ini_get('memory_limit');

Recreating this fatal error.

Here is a sample PHP script that I wrote to recreate this error.

$arr = array();
foreach(range(1, 900000) as $i){
    $arr[] = md5($i);
}

In the code above, I looped through 900,000 times using PHP’s range function and then added the md5 hash of each value to an array. After running the script above, I immediately received a fatal error telling me that my script had consumed too much memory.

Common causes.

In my experience, the most common cause is a large PHP array. This is especially true in some of the earlier versions of PHP. However, it is worth pointing out that PHP 7 consumes far less memory and is far better-optimized.

A few cases where you might run into this memory exhausted error.

From my own personal experience, the most common cause is a large array or a database query that returns far too many rows.

For example, a badly-written JOIN query may return far more rows than you are expecting.

How NOT to fix this error.

On some of the various PHP help forums, you might across people offering solutions such as this.

ini_set('memory_limit', '1024M');

In the above piece of code, we are using PHP’s ini_set function to increase the memory limit.

This is a horrible solution because it does not attempt to fix the underlying problem. It can also cause your web server to run out of RAM.

This line of code attempts to paper over the cracks by giving the script 1GB of memory. In most cases, 1GB is far too much.

A more dangerous example.

ini_set('memory_limit', '-1');

This essentially tells the PHP script that there is no limit to the amount of memory it can use. In other words, it disables PHP’s memory limit.

Fixing memory exhausted errors the right way.

To fix this issue, a better approach is to.

  • Use a debugger such as Xdebug to profile your script and find out where the memory leak is coming from.
  • Make sure that your PHP arrays are not getting too large and that you are avoiding any unnecessary loops. In other words, if you have two loops for the same array, then you should combine them into one loop.
  • Be careful about the amount of data that you are returning from your database. Make sure that you are only selecting table columns that your script is going to use. In other words, specifically name the columns that you want to return. Do not be lazy. By doing a “SELECT * FROM”, you are returning every column.
  • Use PHP’s unset function to destroy variables that you are no longer using, as this can help free up memory. i.e. If you have just looped through a large array that you no longer intend on using, then you can destroy it by passing it into the unset function.