Windows 10-Absturz beim Aufrufen von LeaveCriticalSection

Ich habe ein Problem mit der Synchronisierung von Threads und kritischen Abschnitten unter Windows 10.

Application stürzt in diesem Fall ab:

Application hat zwei Threads.Thread 1 ruft EnterCriticalSection mit dem Objekt m_CS @ aThread 2 versucht dann, denselben kritischen Abschnitt einzugebenThread 1 beendet Thread 2 mit TerminateThreadThread 1 ruft LeaveCriticalSection @ a

In früheren Windows-Versionen, die ich testen konnte (7, 8, 8.1), funktioniert dies ordnungsgemäß. Thread 2 wird beendet und Thread 1 verlässt ausnahmslos den kritischen Bereich.

Unter Windows 10 stürzt die Anwendung mit Zugriffsverletzung ab, wenn Thread 1 den kritischen Abschnitt verlässt. Dies passiert nur, wenn ein anderer Thread beendet wurde, während auf EnterCriticalThread gewartet wurde.

Betrachtet man den Stack-Trace, sieht es so aus (letzter Frame oben):

RtlpWakeByAddress
RtlpUnWaitCriticalSection
RtlLeaveCriticalSection

Ich habe so viel Zeit mit dem Debuggen dieses Problems verbracht. In meinem Fall ist m_CS völlig in Ordnung, als LeaveCriticalSection aufgerufen wurde. Ich debuggte und verbrachte einige Zeit damit, den disassemblierten Code von ntdll.dll-Funktionen zu analysieren. Scheint, als ob das Objekt während der Ausführung von RtlpUnWaitCriticalSection beschädigt und dann bei einem Absturz an RtlpWakeByAddress übergeben wird. Grundsätzlich konnte ntdll.dll die Eigenschaften des CRITICAL_SECTION-Objekts ändern, z. B. die Anzahl der Sperren in RtlLeaveCriticalSection.

Aus dem Internet habe ich keine Antwort auf diese oder eine Aussage gefunden, was sich in Windows 10 geändert hat. Nur Thread-on-Reddit- und ~ 1800-Absturzberichte für Mozilla Firefox mit demselben Aufrufstapel im letzten Monat. Ich habe mich mit dem Autor des Beitrags über reddit in Verbindung gesetzt und er konnte dies bisher nicht beheben.

So hat sich jemand mit diesem Problem befasst und kann eine Lösung dafür oder Ratschläge haben? Als Lösung sehe ich im Moment nur vor, die Verwendung von WinAPI TerminateThread zu überdenken und es so weit wie möglich zu vermeiden. Eine andere Möglichkeit, wahrscheinlich ein Code-Refactoring durchzuführen und die Architektur der Anwendung zu überdenken.

Jede Antwort geschätzt. Danke im Vorau

Antworten auf die Frage(6)

Ihre Antwort auf die Frage