estructura - pilas en c++ codigo
Cambios en el valor del parĂ¡metro C++ entre marcos de pila en std:: vector (5)
Cada vez que un parámetro o una variable local cambia inesperadamente, hay una gran probabilidad de que se deba a la corrupción de la pila. Esto puede ocurrir siempre que use una variable local no inicializada o almacene datos más allá de la memoria asignada a una cadena o matriz local.
Una forma simple de depurar esto:
- Cargue su programa en un depurador.
- Inserte un punto de interrupción en la primera línea de código en la función ofensiva.
- Ejecute el programa hasta que llegue al punto de interrupción.
- Establezca un reloj en la variable que cambia inesperadamente.
- Paso a paso a través de la función hasta que ocurra el cambio inesperado.
El cambio se producirá cuando se escriba la memoria no asignada (o mal asignada). El objetivo de la escritura es la variable ofensiva.
Me encontré con un error realmente extraño, que espero que alguien pueda explicar. Tengo un std::vector<V3x>
simple, donde V3x
es un vector 3d (el tipo de álgebra lineal). El siguiente código hace que se produzca una excepción std::length_error
:
std::vector<V3x> vertices;
int vertexCount = computeVertexCount();
vertices.resize(vertexCount); // throws std::length_error
He verificado que computeVertexCount()
devuelve un valor de 35
, que está muy por debajo de vector::max_size()
por lo que no hay forma de que pida demasiada memoria.
Seguí la excepción hasta la definición de std::vector
, a las dos funciones siguientes.
void resize(size_type _Newsize, _Ty _Val)
{ // determine new length, padding with _Val elements as needed
if (size() < _Newsize)
// NOTE: here, _Newsize - size() = 35
_Insert_n(end(), _Newsize - size(), _Val);
else if (_Newsize < size())
erase(begin() + _Newsize, end());
}
void _Insert_n(const_iterator _Where,
size_type _Count, const _Ty& _Val)
{ // insert _Count * _Val at _Where
// NOTE: here, _Count = 3435973836
...
}
Entonces, cuando se _Count
parámetro _Count
entre _Insert_n()
resize()
y _Insert_n()
, el valor cambia de 35 a 3435973836. Supongo que la memoria se ha dañado de algún modo, pero no tengo idea de cómo podría ser eso.
Para un poco más de contexto en caso de que sea parte del problema, este código se encuentra en un plugin .dll que estoy cargando desde Softimage XSI.
¿Alguien sabe lo que podría causar que algo como esto suceda?
EDITAR: SOLUCIÓN
nobugz, podría besarte.
El tamaño de std :: vector estaba cambiando dentro de mi .dll, debido a _HAS_ITERATOR_DEBUGGING
en VS2008. La búsqueda me llevó a alguien con el mismo problema , y se solucionó agregando lo siguiente en la parte superior de mi proyecto:
// fix stack corruption errors caused by VS2008
#define _HAS_ITERATOR_DEBUGGING 0
#define _SECURE_SCL 0
El valor 3435973836 es significativo. En hex, eso es 0xcccccccc. Ese es el valor asignado a las variables locales en el modo de depuración por el código de inicialización del marco de la pila. Cuando lo veas de nuevo durante la depuración, dirías "ah, variable no inicializada". Tal vez eso te acerque un poco a resolver esto.
Mencionas DLL. Eso es relevante también. La depuración del iterador puede ocasionarle problemas, no puede mezclar el código que lo tiene desactivado con un código que no lo hace. Dado que el archivo DLL probablemente se haya compilado sin él, intente #define _HAS_ITERATOR_DEBUGGING 0.
Sugiero revisar las opciones de C ++ configuradas para los proyectos involucrados. Asegúrese de que todos comparten la misma alineación y la misma configuración de tiempo de ejecución. ¿Estás construyendo el .DLL involucrado?
el código publicado es correcto y puede suponer que std :: vector no tiene errores. replicar la excepción en el entorno más puro posible (nuevo proyecto en blanco). podría ser algo tonto como este en ComputeVertexCount ()?