Autor Beitrag
Black Rider
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 21



BeitragVerfasst: So 15.09.13 03:07 
Hallo zusammen

Ich bin eigentlich der Meinung die Funktionsweise von LOCK() verstanden zu haben. Aber anscheinend ist das nicht der Fall.

Ich habe eine Form in welcher ein neuer Thread gestartet wird um eine Arbeit auszuführen.
Damit das Form den aktuellen Fortschritt weiss, habe ich eine Variable erstellt wodrauf beide Threads (Arbeiterthread und Formthread) zugreiffen sollten.

Deklaration:
ausblenden C#-Quelltext
1:
2:
private static Int32 tsm_tries = 0;
private static Object lockvar_tsm_tries = "";

Steht in einer speziellen Klasse dafür. Habe ich auch schon mit ca 25 anderen Variablen auch in dieser Klasse so gemacht, funktionierte immer.

Zudem habe ich, bis jetzt, nur EINE Methode erstellt welche diese 2 Variablen aufruft oder sonst in irgend einer Weise verwendet.
ausblenden C#-Quelltext
1:
2:
3:
4:
5:
6:
7:
public static void ConnectionTries_AddOne()
{
     lock (lockvar_tsm_tries)
     {
           tsm_tries++;
     }
}


Zudem mache ich vor dem Ausführen eine Haltemarke bei der lock Zeilte und bei der ++ Zeile.
Ich starte mein Programm. Der neue Thread wird gestartet, dieser hält bei der lock an. Wenn ich dann auf weiter drücke, kommt dieser aber nie bei der tsm_tries++; Zeile an. Er kommt auch nicht nochmal bei der lock Zeile an. Also ist er eindeutig bei der lock Zeile hängen geblieben. Wie wenn der Code durch den Lock schon gesperrt wäre, da ich da aber einen Haltepunkt habe, weiss ich das er zu 100% das erste mal darauf zugreifft und somit auch in den Code rein kommen müsste.

Kann mir da jemand helfen? :(

Freundliche Grüsse

Black Rider

Moderiert von user profile iconTh69: C#-Tags hinzugefügt
jaenicke
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19336
Erhaltene Danke: 1751

W11 x64 (Chrome, Edge)
Delphi 12 Pro, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: So 15.09.13 06:16 
Hast du das ganze mal unabhängig von deinem ganzen Projekt getestet? Einfach in einem kleinen Testprojekt?
Erstens macht das das ganze einfacher zu debuggen, zweitens siehst du, ob es an dem Quelltext liegt und drittens könntest du das Testprojekt dann hier einfach posten. Denn der von dir gepostete Quelltext sieht eigentlich korrekt aus.
Th69
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Moderator
Beiträge: 4803
Erhaltene Danke: 1060

Win10
C#, C++ (VS 2017/19/22)
BeitragVerfasst: So 15.09.13 09:49 
Hallo Black Rider,

hast du noch andere lock-Objekte genau so deklariert? Deine zweite Zeile kommt mir komisch vor - nimm besser
ausblenden C#-Quelltext
1:
private static Object lockvar_tsm_tries = new Object();					

Bei "" bin ich mir nicht sicher, ob der Compiler die nicht intern so optimiert, daß alle Referenzen dann auf die gleiche Instanz zeigen (und das wäre für den lock dann eben ein Deadlock ;-)).

P.S: Bitte demnächst den Code selber hier im Forum als C# kennzeichnen, danke.
jaenicke
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starofftopic star
Beiträge: 19336
Erhaltene Danke: 1751

W11 x64 (Chrome, Edge)
Delphi 12 Pro, C# (VS 2022), JS/HTML, Java (NB), PHP, Lazarus
BeitragVerfasst: So 15.09.13 10:58 
user profile iconTh69 hat folgendes geschrieben Zum zitierten Posting springen:
Bei "" bin ich mir nicht sicher, ob der Compiler die nicht intern so optimiert, daß alle Referenzen dann auf die gleiche Instanz zeigen (und das wäre für den lock dann eben ein Deadlock ;-)).
Darauf bin ich nicht gekommen, aber in Visual C# 2010 passiert das jedenfalls nicht.
jfheins
ontopic starontopic starontopic starontopic starontopic starontopic starofftopic starofftopic star
Beiträge: 918
Erhaltene Danke: 158

Win 10
VS 2013, VS2015
BeitragVerfasst: So 15.09.13 11:51 
Die Optimierung wird ziemlich sicher durchgeführt.

Mir erschließt sich nur nicht, warum das dann ein Deadlock sein sollte. Das passiert soch eigentlich nur, wenn in dem lock {} Statement noch auf den anderen Thread wartet, und dieser dann versucht auf den Ursprungsthread zu warten. Da ich hier nirgendwo etwas sehe was mit Warten zu tun hat, sehe ich auch keine Möglichkeit für ein Deadlock.
Th69
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Moderator
Beiträge: 4803
Erhaltene Danke: 1060

Win10
C#, C++ (VS 2017/19/22)
BeitragVerfasst: So 15.09.13 12:35 
Hallo,

ich meinte, wenn er noch anderen Code hat, der genau so aufgebaut ist und in diesem er evtl. wartet (denn wenn beide dann intern den selben Lock benutzen würden, dann könnte dies ein Deadlock sein - denn so liest sich ja die Beschreibung von user profile iconBlack Rider).
Aber das beste ist wohl, wir warten auf ein Testprojekt (anstatt darüber zu spekulieren).
Black Rider Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 21



BeitragVerfasst: So 15.09.13 15:13 
Hallo zusammen

Vielen Dank für die Antworten.

Auf die lock variable wird ansonsten von nirgend's zugegriffen. Ein Deadlock ist also auszuschliessen.
Ich habe daraufhin ein Testobjekt gemacht. Wie sollte es auch anders sein, da hat es ohne Probleme funktioniert.
Ich habe dann wieder weiter ausprobiert, Thread als Klassenmember deklariert etc. War nix.

Des Rätsels Lösung war die von Th69
ausblenden C#-Quelltext
1:
private static Object lockvar_tsm_tries = new Object();					


Ich habe es mehrmals getestet. Wenn ich new Objekt verwende, geht er in den gesicherten Code rein. Wenn ich "" verwende, geht er in den gesicherten Code nicht rein.
Ehrlich gesagt, ich verstehe es nicht. Meine Anwendung umfasst atm 25000 Zeilen. Ich habe wie schon erwähnt in einer anderen Klasse ca. 25 andere Variablen auch so gesichert. Da Software läuft schon seit 8 Monaten täglich in der Firma.

Aber bei diesem Beispiel scheint es wirklich nur mit new Object zu klappen :/

So, Sonntagnachmittag auch verbraten. Wenigstens haben wir den Fehler nun gefunden :)

Nochmal Danke und einen schönen Abend noch.

Gruss

Black Rider
Th69
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Moderator
Beiträge: 4803
Erhaltene Danke: 1060

Win10
C#, C++ (VS 2017/19/22)
BeitragVerfasst: Mo 16.09.13 08:58 
Hallo Black Rider,

du solltest deshalb auch alle lock Variablen auf "new Object()" umstellen.
Ich verstehe auch nicht, wie ihr bei eurem Projekt auf die Zuweisung "" gekommen seid? Es sollte doch jedem klar sein, daß
ausblenden C#-Quelltext
1:
2:
string s = "";
string s2 = "";

intern vom Compiler optimiert werden könnte (und nichts anderes ist ja euer bisheriger Code).
Black Rider Threadstarter
ontopic starontopic starontopic starontopic starontopic starontopic starontopic starontopic star
Beiträge: 21



BeitragVerfasst: Mo 16.09.13 11:35 
Da ich mir C# selber beigebracht habe, muss ich diesen Fehler wohl von irgend einem Bsp. aus dem Internet übernommen haben.

Gruss Black Rider