Booleans sind nicht threadsicher, vorallem da sie nichtmal atomar änderbar sind, da die CPU mir kompletten Registern arbeitet und dann nur die Bytes raus ANDed und SCHIFTet.
Die CPUs kennen da einen speziellen Befehl LOCK
z.B.
LOCK MOV [EAX], EDX
statt
MOV [EAX], EDX
.
Und die
WinAPI kennt die Interlocked-Behle, wie
InterlockedExchange.
Deine "innere" Änderung von ThreadString ist nicht abgesichert, denn da wird nicht geprüft, ob der String gerade von SetThreadString verändert wird.
Gut, man könnte jetzt beide Zeiten absichern und dann äußere und inner Änderungen nur über dieses SetThreadString ausführen,
Delphi-Quellcode:
Function SetThreadString(s:AnsiString):Boolean;
Var TimeOut:Integer;
Begin
TimeOut:=0;
Repeat
IF not(ThreadString_Locked) then
BEGIN
ThreadString_Locked:=True;
ThreadString:=s;
ThreadString_Locked:=False;
Result:=True;
END ELSE
Result:=False;
Inc(TimeOut);
Until TimeOut>1000;
End;
aber hier kann es immernoch vorkommen, daß mehrere Threads gleichzeitig durch das IF kommen und :=True setzen, da diese Beiden erst Recht nicht atomar sind.
Ich hatte letzens die CriticalSection über TryEnter und eine Schleife mit einem TimeOut versehn.
Schön ist das nicht unbedingt, aber es funktioniert wenigstens.