REVISIÓN: Liberar memoria varias veces puede causar un error de aplicación en Visual C++

Síntomas

Memoria que se libera varias veces puede provocar un error de aplicación.

Nota: Esto es cierto si utiliza malloc y varios libre o nueva y eliminar múltiples.

Causa

Estructuras de control del montón se modifican después de la primera llamada a free() y ya no está en un estado donde las llamadas subsiguientes a free() funcionará.

Solución

Evite llamar a múltiples libre o eliminar varias en el mismo puntero. Es una forma de evitar esto asignando el puntero null después de llamar a libre o eliminar. La eliminación y funciones libres devuelven sin hacer nada si se pasa un puntero null como argumento. Esto no funciona en casos donde libre o llamar a delete en varios punteros apuntando a la misma ubicación de memoria.

Para ayudar a los clientes que experimenten este problema en las aplicaciones de terceros, Microsoft ha lanzado una nueva DLL de biblioteca de tiempo de ejecución de C, Msvcrt.dll, que implementa dos administradores del montón, el Administrador de pila compatible con Visual C++ 5 y el Administrador de pila compatible con Visual C++ 6. Detecta con qué versión de Visual C++, la aplicación se genera y utiliza el administrador del montón apropiado para esa aplicación. Si esta versión es 6.0 o posterior, se utiliza el Administrador de pila compatible con Visual C++ 6 y si es anterior a la versión 6.0, se utiliza el montón compatible con Visual C++ 5.

Usuarios de Visual Studio 6.0 pueden obtener este nuevo msvcrt.dll instalando el último Microsoft Visual Studio Service Pack. Los usuarios de Visual Studio de no deberían instalar la actualización de las bibliotecas de Microsoft.

Estado

Microsoft ha confirmado que se trata de un error en los productos de Microsoft que se enumeran al principio de este artículo.

Este error se corrigió en Visual Studio 6.0 Service Pack 3.
Para obtener más información acerca de los service Pack de Visual Studio, consulte los artículos siguientes en Microsoft Knowledge Base:

194022 Visual Studio 6.0 service Pack, qué son, dónde, por qué

194295 cómo saber que está instalado un service pack de Visual Studio

Más información

Liberar memoria varias veces, produce un comportamiento indefinido.


Versiones de lanzamiento del código de ejemplo siguiente causa un error de aplicación cuando crea con Visual C++ 6.0; el código no provoca un error de aplicación cuando crea con Visual C++ 5.0.

Versiones de depuración con Visual C++ 6.0 o Visual C++ 5.0 problema una aserción:
   Debug Assertion Failed!

Es importante destacar que el estado del montón de bloques pequeños (SBH) está constantemente en un flujo. Debido a esto, hay situaciones donde es posible que no hay aserción se emitirá en la versión de depuración, pero se producirá un error de aplicación en la versión de lanzamiento.

Las versiones de lanzamiento en Visual C++ 6.0 son más sensibles a liberar memoria varias veces que en Visual C++ 5.0. Si se compila con Visual C++ 5.0, el siguiente caso es uno donde la llamada incorrecta a libre es inocua. Si la llamada a free() se hicieron más distante de la original, es posible provocar un error de aplicación. Hay una gran probabilidad de que la memoria se dañará.

Código de ejemplo

   // Compile options for Release builds /c   // Compile options for Debug builds /c /Zi
#include <malloc.h>
int main(int argc, char* argv[])
{
char *pChar1 = (char *)malloc(10*sizeof(char));
char *pChar2 = (char *)malloc(10*sizeof(char));
free(pChar1);
free(pChar1);
return 0;
}

Propiedades

Id. de artículo: 194550 - Última revisión: 23 ene. 2017 - Revisión: 1

Comentarios