2011-02-18 7 views
7

Me encuentro con un problema muy extraño con una aplicación grande. Hago un uso intensivo de TObjectList almacenando un objeto personalizado en ellos. En listas grandes, estoy experimentando bloqueos extraños con "Infracción de acceso en la dirección ... lectura de la dirección ..." "instrucción privilegiada" y otros, cuando uso el método BORRAR. He seguido esto exactamente cuando intento eliminar el último elemento de la lista. Lo he comprobado registrando la eliminación de objetos contenidos de su proceso de destrucción, y también tratando de eliminarlos por mi cuenta (para a: = olist.count-1 downto 0 do .. debugmsg ('deleting' + inttostr (a)) .. olist.delete (a)), en ambos sentidos obtengo la violación de acceso correcta al eliminar el ÚLTIMO elemento restante en la lista.TObjectList.Clear access violation

Esto no sucede siempre, porque uso claro en otras áreas, y también en algunas listas diferentes (más pequeñas), pero esto ocurre en un punto muy específico de mi aplicación.

No tengo ni idea de lo que podría estar mal, no hay nada que intente acceder a la lista durante el borrado, y los objetos corespondidos no tienen acceso a su lista de objetos principal, tiene que haber algo atornillado en TObjectList.delete/métodos claros cuando se trata de borrar el último elemento.

¿Alguna sugerencia? Usando Delphi XE.

+1

Parece una corrupción de memoria que ocurre en otro lugar y solo ve el eco. –

+2

TObjectList tiene una propiedad 'OwnsObjects'. ¿Es verdadero o falso? ¿Cómo se ve el código que está usando TObjectList? –

+0

@Remy: a partir del comentario sobre "también trato de eliminarlos por mi cuenta", está bastante claro que 'OwnsObjects' está establecido en' true'. –

Respuesta

18

Me parece que estás liberando objetos que ya han sido liberados. Para rastrear esto, download the full version of FastMM, agregue FullDebugMode a la línea Definiciones condicionales en Opciones de proyecto-> Compilador de Delphi y la opción Archivo de mapa en Vincular establecer en detallado y reconstruir. (Build, not Compile). Luego, copie el DLL de FullDebugMode en la misma carpeta que su EXE y ejecútelo. Vigilará su memoria a medida que distribuye y liberará, y cuando intente liberar el mismo objeto por segunda vez, lo detectará y le dará datos de depuración muy detallados sobre el origen del problema.

+4

+1 Esta es la causa más probable del problema y la mejor manera de intentar una solución. Hay otras causas posibles, pero intente esto primero. –

+0

oh wow eso está bien, ya veo algunos problemas "FastMM ha detectado un intento de invocar un mecanismo virtual en un objeto liberado. Ahora se generará una infracción de acceso para abortar la operación actual". Voy a tomar un poco para analizar todo esto, pero esto es de gran ayuda. Informará pronto. Gracias :) – hikari

+0

@Hikari: Sí, esa es la única. Solo asegúrate de cuando hagas una versión de lanzamiento que desactives FullDebugMode * * –

1

¿Estás seguro de que el último objeto es válido y aún no se ha eliminado? Podría estar en la lista dos veces, por ej. debido a otros errores.