Cómo resolver composer install/update error: VirtualAlloc() failed: [0x00000008]

Errores basados en los métodos VirtualAlloc y VirtualFree durante la ejecución de un script en PHP, son causados por un simple hecho, PHP no tiene suficiente memoria disponible para ejecutar la tarea, es por eso que la excepción es lanzada y encontraras tambien el error de PHP "Out of memory (allocated xxxxxx) (tried to allocate xxxx bytes)". Por ejemplo, ultimamente con la ultima versión de Composer este tipo de excepción ocurre cuando se trata de actualizar paquetes con el comando composer update:

Loading composer repositories with package information

Updating dependencies (including require-dev)                                                           

VirtualAlloc() failed: [0x00000008] Not enough memory resources are available to process this command.  

VirtualFree() failed: [0x000001e7] Attempt to access invalid address.                                 

VirtualAlloc() failed: [0x00000008] Not enough memory resources are available to process this command.

VirtualFree() failed: [0x000001e7] Attempt to access invalid address.                                

PHP Fatal error:  Out of memory (allocated 1512046592) (tried to allocate 4096 bytes) in phar://C:/ProgramData/ComposerSetup/bin/composer.phar/src/Composer/DependencyResolver/Solver.php on line 220

Fatal error: Out of memory (allocated 1512046592) (tried to allocate 4096 bytes) in phar://C:/ProgramData/ComposerSetup/bin/composer.phar/src/Composer/DependencyResolver/Solver.php on line 220 

Con la anterior afirmación, estarás pensando como puede ser posible que la falla sea a causa de falta de memoria si tengo un equipo con más de 8GB de RAM? Bien, desafortunadamente, el problema no es siempre el mismo asi que de acuerdo a tu caso la solución puede variar.

Solución: incrementar memoria maxima permitida de PHP

Lo primero que tienes que saber es el limite de memoria actual de tu distribución de PHP. Puedes averiguarlo rápidamente desde la consola de comandos con el siguiente comando:

php -r "echo ini_get('memory_limit');"

En nuestro caso, sin modificar el archivo de configuración php.ini este comando nos genera 128M en la consola. Este valor es el limite de memoria que tiene PHP disponible para ejecutar scripts, con composer ese es basicamente el error así que necesitarás incrementar este limite en la configuración de PHP (php.ini).

Puedes averiguar que archivo de configuración se está usando para la versión de la consola con el siguiente comando:

php --ini

En nuestro caso, en windows el comando genera el siguiente texto:

Configuration File (php.ini) Path: C:\Windows
Loaded Configuration File:         C:\xampp72\php\php.ini
Scan for additional .ini files in: (none)    
Additional .ini files parsed:      (none)

Asi que abre el archivo de configuración php.ini con tu editor de texto favorito y modifica el monto de la propiedad memory_limit con un valor considerable, por ejemplo medio gigabyte 512M o 1GB:

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

Es obvio que el monto cambiará dependiendo de lo que necesite tu script, asi que lo mas probable es que tengas que cambiar e incrementar este valor de acuerdo a tus necesidades. Guarda el archivo, reinicia apache y prueba tus scripts. Si aun no funciona, incrementa el valor hasta que funcione (a menos que tengas una instalación de 32 bits de PHP, donde el maximo monto disponible es de 2G).

Si los valores que coloques no funcionan y tienes una distribución de PHP de 64 bits, prueba la solución de parche de mono que define un uso ilimitado de RAM para los scripts de PHP (absolutamente no recomendado en un entorno de producción, pero puede terminar util en entorno de desarrollo para saber que esta fallando).

Importante advertencia para usuarios de XAMPP en windows o distribuciones de PHP de 32 bits

Desafortunadamente, si tienes esta excepción cuando ejecutes algun script o composer cuando usas XAMPP y el monto máximo de memoria de 2GB no es suficiente, dejame decirte que estas en un gran problema pues necesitaras optimizar tu script si es posible o mover tu entorno de una distribución de 32 bits a una de 64 bits.

Este problema se basa en el hecho de que distribuciones de 32 bits (como el conocido XAMPP que solo ofrece esta arquitectura) no te dejarán acceder a un monto de memoria mayor a 2GB, incluso cuando tienes por ejemplo 16GB de ram disponibles en tu computadora. La arquitectura de 32 bits limitará cualquier valor mayor a su monto maximo p. ej. 1996MB  - 2056MB.

Tip de ultimo recurso para usuarios de XAMPP

Si estás trabajando con composer usando la versión de PHP disponible en XAMPP y la instrucción usada con composer, significa que el procesar el archivo de composer.json está necesitando mas de 2GB de memoria para ejecutarse, lo cual fallará en XAMPP. La solución desafortunadamente en este caso es el cambiar de Stack, por ejemplo usar Wampp en vez de xampp.

Este stack de desarrollo ofrece una versión de 64 bits que no debería tener ningun problema despues de incrementar el monto de memoria.

Solución parche de mono

Si has intentado la solución mencionada para la excepción con diferentes valores, pero no funcionó, puedes definir el uso ilimitado de memoria:

Advertencia

Normalmente no deberias hacer esto en producción, pues PHP tendrá acceso ilimitado a la memoria, lo que significa que en caso de que tus scripts produzcan una fuga de memoria, tu servidor puede llegar a ser inutilizable durante su ejecución, por lo cual tendrás que reiniciar el servidor. Intenta esto solamente en tu entorno de desarrollo local para probar si tu script funciona o no. 

; La cantidad máxima de memoria que una secuencia de comandos puede consumir (128MB)
; http://php.net/memory-limit
memory_limit=-1

Si estás usando composer cuando ves esta excepción, querrás ejecutar la instrucción p. ej. composer update con el ejecutable de PHP:

php -d memory_limit=-1 "C:\ProgramData\ComposerSetup\bin\composer.phar" update

Que te diviertas !

Esto podría ser de tu interes

Conviertete en un programador más sociable