Hallo Leute,
ich habe mal eine Frage zum Thema Netzwerk.
In Delphi gibt es ja die Komponenten "TServerSocket" & "TClientSocket".
Mein Problem betrifft insbesondere den Client-Socket.
Das Ziel soll es sein, innerhalb einer Prozedur den Request an den Server zu schicken, und dann auch den Reply noch in der gleichen Prozedur auswerten zu können.
Da nützen Ereignisse OnClientRead usw. relativ wenig. Denn diese rufen sich ja als Extra-Threads außerhalb der Prozedur auf, sobald die Entsprechende Message den Socket erreicht.
Wie kann man also das Senden & den Empfang serialisieren???
Ich habe es schon mit abgeleiteten TThread-Klassen versucht, und dafür eine Prozedur zu schreiben, die auf den Wert einer Boolean-Variable wartet, die im Ereignis "OnClientRead" auf True gesetzt wird, wodurch dann die Thread-Prozedur merkt, dass sie sich beenden kann.
Im Hauptthread warte ich dann nach dem Senden des Requests auf die Beendigung des Threads, den ich vor dem Aufruf der Sendeprozedur startete. Aber dabei blockiert der Hauptthread anscheinend derartig, daß in ihm keine Ereignisse des Clients mehr ausgewertet werden können.
Dann habe ich auch noch -weils also überhaupt nicht ging-, versucht CriticalSections zu nutzen. Habe ich die richtig verstanden?
CriticalSections nützen, um kritische shared resources zwischen mehreren Threads nutzen zu können, indem man mit EnterCriticalSection(Section:TRTLCriticalSection) "Unit=>syncobjs" die Section betritt, sofern sie nicht vorher durch einen parallelen Thread betreten wurde. Wenn dem so ist, sollte EnterCriticalSection ja nicht fortfahren, und stattdessen solange mit der weiteren Ausführung warten, bis LeaveCriticalSection(Section) von dem Thread aufgerufen wird, der die EnterCS & LeaveCS eingebettete Resource bis dahin in Gebauch hatte.
Doch bei mir geht das irgendwie von Grund auch nicht.
Ich sage:
Delphi-Quelltext
1: 2: 3:
| InitializeCriticalSection(Section); EnterCriticalSection(Section); EnterCriticalSection(Section); |
Aber es lockt nicht dead.
Was ist falsch? Habe auch zum Testen des Sacherhaltes schon mal mit Timern gearbeitet. Diesen Timern habe ich dann einfach eine globale CriticalSection-Variable zu fressen gegeben.
Im einen Timer: Delay: 1000ms
Delphi-Quelltext
1: 2: 3: 4:
| Timer1.Enabled:=False; EnterCriticalSection(Section); ShowMessage('Test1'); LeaveCriticalSection(Section); |
Im anderen Timer: Delay: 5000ms
Delphi-Quelltext
1: 2: 3: 4:
| Timer2.Enabled:=False; EnterCriticalSection(Section); ShowMessage('Test2'); LeaveCriticalSection(Section); |
Das Problem:
Nichts geht, wie es soll.
Wenn ich jetzt beide Timer im Hauptthread der Anwendung auf Enabled setze, dann kommt zuerst die Ausgabe "Test1". -Soweit ganz supertollokay- Dann klicke ich aber in der Message nicht OK. Sondern warte noch 4 Sekunden. Der erste Thread steht also immer noch bei ShowMessage('Test1'); Doch dann poppt aufeinmal doch "Test2" auf.
Das dürfte doch gar nicht gehen!!! Denn die Section ist ja noch durch den ersten Timer-Thread belegt. Wieso geht das?
Wie serialisiert ihr den Empfang der Geschichte hier??
Dankeschön für eure Tipps.
Gruß TMTMTM
Delphi 5 Enterprise 1701-D
W2K
Moderiert von
matze: Delphi-Tags hinzugefügt