Ich habe eine WS-Wrapper Klasse geschrieben, die mir Packete empfangen und weiterverarbeiten soll.
dazu diese Function:
PacketStruktur ist:
Word:Länge der Daten (ohne Header) in Byte
Word:OpCode
Word:CRC (not used here)
dann die Daten
Delphi-Quelltext
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23:
| class procedure TClient.HandlePacket; var size,curSize,bfSize,curPos:Integer; encrypted:boolean; begin curSize:=Length(Buffer); SetLength(Buffer,curSize+8193); Winsockread(sockClient,@buffer[curSize],size); if(size<=0) then begin SetLength(Buffer,curSize); exit; end; curSize:=curSize+size; SetLength(Buffer,curSize); curPos:=0; while(curPos+6<=curSize) do begin size:=PWord(@Buffer[curPos])^; if(curPos+6+size>curSize) then break; DispatchPacket(PWord(@buffer[curPos+2])^,Word(size),Cardinal(@buffer[curPos+6])); InjectPacket(@buffer[curPos]); Inc(curPos,size+6); end; SetLength(Buffer,curSize-curPos); end; |
Buffer ist eine Klassenvariable mit "Array of Byte"
sollte so korrekt sein, oder?
will damit praktisch unvollständig packete und mehrere packete im buffer managen
2. teil:
Der Message Handler ist ein class(TForm) mit:
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37:
| procedure MessageHandler(var Msg:TMessage);Message MSG_ASYNC; procedure TWS.MessageHandler(var msg:Tmessage); begin case WSAGetSelectEvent(MSG.LParam) of FD_READ: TClient.HandlePacket;
FD_CLOSE: FD_ACCEPT: end; end; procedure TWS.Initialize(port:integer); begin if not WSInitialized then Exit;
LsockClient:=WinsockBind(port); if not(WinsockListen(LsockSRClient)) then Exit; TieSocket(WS.Handle,LsockClient,MSG_ASYNC); end; class procedure TWS.TieSocket(handle:hwnd;Sock:TSocket;Msg:Integer); begin dwError:=WSAAsyncSelect(Sock, handle, Msg, FD_CLOSE or FD_READ or FD_ACCEPT); if dwError <> ERROR_SUCCESS then begin dwError:=WSAGetLastError; CloseSocket(Sock); Exit; end; end; |
Könne hier Probleme auftreten?
Meine Probleme derzeit:
Das Programm hat eine Gui, die gelegendlich mal einfriert (vermutlich beim Warten auf eine Verbindung).
Muss ich also das Form TWS in einem ExtraThread erzeugen?
Außerdem habe ich das Problem, dass wenn ich in der HandlePacket function eine showmessage() zeige, läuft die Funktion erneut an.
Soll heißen: Die funktion wird nochmal aufgerufen, obwohl noch die MessageBox offen ist!
Wie geht das?
die nachrichtenschleife wird doch erst weiterlaufen, wenn die Funktion beendet ist, oder?
Zusätzlich: Eigendlich brauche ich das Form TWS ja gar nicht
ich könnte ja einfach ein "Fenster" ohne Fenster machen, um ein Handle zu haben, und das dann in einer Nachrichtenschleife abfragen.
Aber wie geht das? Hat da jemand ein bischen Code oder nen Link?