Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Programmieren allgemein (https://www.delphipraxis.net/40-programmieren-allgemein/)
-   -   Exception EAccessViolation (https://www.delphipraxis.net/172710-exception-eaccessviolation.html)

Cruentus 18. Jan 2013 14:05

Exception EAccessViolation
 
Hallo allerseits,

kurz worum es geht: Ich habe ein Spielbrett programmiert mit Ereignisfeldern. Betritt man ein Ereignisfeld wird eins von mehreren möglichen Minispielen in einem neuen Formblatt geöffnet, das Spielfeld bleibt in der Ebene dahinter aber geöffnet. Hat man gewonnen oder verloren wird das Minispielformblatt geschlossen und das Ergebnis an das Spielfeld übermittelt, welches dann entsprechend reagiert. Programmiert habe ich die Minispiele alle einzeln für sich, erst am Ende habe ich alles in einem Projekt zusammengeführt und mit dem Spielfeld "verbunden".

Nun tritt selten (hab nicht gezählt, aber ich habe bistimmt 20 Ereignisfelder ohne Fehler gehabt) folgender Fehler auf: "Im Projekt name.exe ist eine Exception der EAccessViolation mit der Meldung 'Zugriffsverletzung bei Adresse 0040391C in Modul 'name.exe'. Lesen von Adresse 00000031' aufgetreten".

Die Fehlermeldung trat bisher nur dann auf, wenn man gewonnen/verloren hatte und man nun zum Spielfeld zurückkehrt (Fehler tritt also nur am Ende eines Ereignisses auf). Klicke ich auf Anhalten, zeigt er mir aber keine Stelle im Quelltext, wo der Fehler aufgetreten sein soll, es wird keine Zeile gehighlighted. Klicke ich auf Fortsetzen kommt nochmal eine Windowsfehlermeldung mit ähnlichem Inhalt, ich kann aber normal weiterspielen. Sobald ich aber wieder ein Ereignisfeld betrete, kommt nun jedesmal die gleiche Fehlermeldung.

Bis auf die Tatsache, dass der Fehler nur nach Ereignissen auftritt (setze ich Spielfiguren auf ein normales Feld, gibt es keine Fehlermeldung), habe ich bisher keine Gemeinsamkeiten erkennen können, ich kann den Fehler beim ersten Mal nicht gezielt reproduzieren (nach dem ersten Auftreten tritt er dann ja immer auf).

Die Adresse der Zugrifssverletzung bleibt auch nach einem Neustart immer die gleiche(entspricht diese einer Zeile im Quelltext?), die Leseadresse variiert je nach Minispiel.

Ich bin ein wenig verzweifelt, da ich nun doch schon sehr lange an diesem Projekt sitze und es nun eigentlich auch spielfertig ist, die Fehlermeldung stört bisher auch nur in kosmetischer Hinsicht...aber sie stört eben.

Ich danke schonmal für eure Mühe und freue mich über Antworten.
Gruß
Cruentus

DeddyH 18. Jan 2013 14:08

AW: Exception EAccessViolation
 
Eine derartig kleine Adresse lässt auf einen Nil-Pointer-Zugriff schließen. Du scheinst also auf etwas zuzugreifen, was (noch) nicht oder nicht mehr da ist.

Medium 18. Jan 2013 14:09

AW: Exception EAccessViolation
 
Adressen unter... öhm, war das 400h oder 800h(?) sind nil. Du greifst dort also auf eine Referenz zu, der keine Instanz zugewiesen wurde. Mehr lässt sich ohne etwas Code aber auch nicht sagen.

Cruentus 18. Jan 2013 14:22

AW: Exception EAccessViolation
 
Hmm, Zugriff auf einen Nullpointer. Okay. Aber eigentlich kommt der Fehler ja erst im laufenden Spielbetrieb, da sollte es ja eigentlich keine nicht initialisierten Variablen geben (dann müsste er ja auch reproduzierbar sein). Und der Fehlzugriff müsste sich doch auch irgendwie bemerkbar machen (falsch gesetzte Figuren, falsche Spielergebnisse, Spiele nicht erneut aufrufen können, etc.). Aber ich kann ja nochmal nachschauen.

Ich würde gerne Quelltext posten, allerdings hat die zentrale Klasse über 3000 Zeilen, da kämen dann noch die Spielcodezeilen hinzu. Und da ich beim "Anhalten" nicht angezeigt bekomme, wo der Fehler auftritt... Ich habe auch schon überlegt, im Einzelschrittmodus durchzugehen. Aber da ich im normalen Spielbetrieb ca. 15 Minuten gebraucht habe, bis der Fehler das erste Mal auftrat, wäre ich damit ja noch im nächsten Leben beschäftigt (zudem laufen bei manchen Spielen noch parallel Timer mit).

Auch wenn das jetzt vielleicht total grottiger Programmierstil wäre, aber gibt es vielleicht eine Möglichkeit die Compiler- und Windowsexceptionmeldung zu unterdrücken? Immerhin konnte ich immer ohne Einschränkungen weiterspielen.

DeddyH 18. Jan 2013 14:27

AW: Exception EAccessViolation
 
Die Möglichkeit zum Unterdrücken gibt es zwar, aber davon möchte ich ausdrücklich abraten. Mach Dir lieber die Mühe und untersuche, wo die Fehler herkommen. Anschließend beseitigst Du die Ursache und hast gar keine Notwendigkeit mehr, irgendetwas unter den Teppich kehren zu müssen ;)

CarlAshnikov 18. Jan 2013 14:30

AW: Exception EAccessViolation
 
Zitat:

Und da ich beim "Anhalten" nicht angezeigt bekomme, wo der Fehler auftritt...
Ich weiß nicht wie das bei anderen Delphi-Versionen ist, aber bei mir gibt's die Debugger-Option "Bei Delphi Exceptions stoppen". Damit sollte man schon sehen wo der Fehler auftritt.

Cruentus 18. Jan 2013 17:56

AW: Exception EAccessViolation
 
Ich benutze den Turbodelphi-Explorer. Sonst hat der mir bei den Exceptions auch immer die entsprechende Zeile rot markiert, nur diesesmal nicht.

Ich habe den Quelltext mal überflogen und verstärkt auf Möglichkeiten einer Null-Pointer-Exception geachtet. Ich habe jetzt eine TStringList im Verdacht, die ich nicht immer initialisiert aber nach jedem Spiel immer wieder mit .free; freigegeben habe. Da könnte doch der Knackpunkt sein, oder?

Ich habe das jetzt geändert und werde das morgen mal ausgiebig testen, ob die Exception irgendwann wieder auftritt oder nicht. Gibt mir dann zwar keine Gewissheit, ist aber besser als gar nichts^^

Danke schonmal
Gruß
Cruentus

Edit: So, ich habe das Spiel heute mal einige Stunden laufen lassen, der Fehler ist nicht wieder aufgetreten. Das ist zwar keine Garantie, aber scheinbar lag es an der .free Geschichte. Somit ist das Problem gelöst. Danke für eure Hilfe, sie hat mir den entscheidenden Hinweis gegeben!


Alle Zeitangaben in WEZ +1. Es ist jetzt 10:57 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz