![]() |
Indy: mehrere UDP-Server auf einem Port
Hallo!
Wie man ![]() Dabei erfuhr ich im verlinkten Thread (danke Basilikum), daß ein Port auch von mehreren Servern gleichzeitig benutzt werden kann. Da ich Indy 9 verwende, ergibt sich ein Problem: Beim TCP-Server findet sich auch eine entsprechende Einstellmöglichkeit (Property ReuseSocket). Beim UDP-Server ist das nicht implementiert. Natürlich könnte ich mich nun in die Tiefen der (etwas chaotischen) Indy-Sources begeben, die Verfahrensweise bei TCP ergründen und auf UDP übertragen. Nur - warum das Rad zweimal erfinden? Vielleicht hat ja jemand das schon mal implementiert. Wie kann ich also bei Indy 9 einstellen, daß mehrere UDP-Server auf einem Port arbeiten? Für Eure Mithilfe bedanke ich mich im Voraus. Gruß Dietmar Brüggendiek |
Re: Indy: mehrere UDP-Server auf einem Port
leider bietet tidudpserver keine Möglichkeit, um die Option SO_REUSEADDR zum richtigen Zeitpunkt (vor Bind) zu setzen (bei TIdUDPServer.Active:=true wird das vorhandene Binding zerstört, und ein neues initialisiert, wonach natürlich die Option wieder auf dem Default-Value ist).
aber "von Hand" geht's trotzdem:
Delphi-Quellcode:
Gruss Basilikum
Uses
idstack, idstackwindows, idsockethandle; [...] Var sh : TIdSocketHandle; B : Bool; Buf : Array[0..127] Of Byte; begin GStack:=TIdStackWindows.CreateStack(); sh:=TIdSocketHandle.Create(Nil); sh.AllocateSocket(SOCK_DGRAM); sh.Port:=4444; B:=True; sh.SetSockOpt(SOL_SOCKET,SO_REUSEADDR,@B,SizeOf(Bool)); sh.Bind(); sh.Recv(Buf,SizeOf(Buf),0); // in einen Thread verpacken end; |
Re: Indy: mehrere UDP-Server auf einem Port
Hallo Basilikum!
Erst einmal vielen Dank für die schnelle Antwort. Verstehe ich das richtig, daß ich mit TidUDPServer nicht arbeiten kann, sondern mir das Ganze mit den Sockets selber erstellen muß? Falls dem so ist, wearte ich erst mal auf die offizielle Freigabe von Indy 10. Sollte das da auch noch nicht implementiert sein, versuche ich es einzubauen. Gruß Dietmar Brüggendiek |
Re: Indy: mehrere UDP-Server auf einem Port
Hallo Dietmar
ich habe soeben bemerkt, dass die Methode GetBinding() von TIdUDPServer virtual definiert ist. Dies ermöglicht es, trotzdem die Klasse TIdUDPServer zu verwenden:
Delphi-Quellcode:
Gruss Basilikum
unit Unit1;
interface uses Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms, Dialogs, IdUDPServer, IdStackConsts, IdSocketHandle, StdCtrls; type TUDPServer = Class(TIdUDPServer) Protected function GetBinding: TIdSocketHandle; override; end; TForm1 = class(TForm) Button1: TButton; Button2: TButton; procedure Button1Click(Sender: TObject); procedure Button2Click(Sender: TObject); private _UDPServer : TUDPServer; { Private declarations } public { Public declarations } procedure UDPRead(Sender: TObject; AData: TStream; ABinding: TIdSocketHandle); end; var Form1: TForm1; implementation {$R *.dfm} function TUDPServer.GetBinding: TIdSocketHandle; var i: integer; begin if not Assigned(FCurrentBinding) then begin if Bindings.Count < 1 then begin Bindings.Add; end; for i := 0 to Bindings.Count - 1 do begin Bindings[i].AllocateSocket(Id_SOCK_DGRAM); Bindings[i].SetSockOpt(Id_SOL_SOCKET,Id_SO_REUSEADDR,@Id_SO_True,SizeOf(Bool)); // Bis auf diese Zeile ist alles kopiert von TIdUDPServer Bindings[i].Bind; end; FCurrentBinding := Bindings[0]; FListenerThread := TIdUDPListenerThread.Create(BufferSize, Self); FListenerThread.Start; BroadcastEnabledChanged; end; Result := FCurrentBinding; end; procedure TForm1.Button1Click(Sender: TObject); begin // Dies ist nur notwendig, da ich die Indy-Palette nicht installiert habe.... ansonsten per OI _UDPServer:=TUDPServer.Create(Self); _UDPServer.DefaultPort:=4444; _UDPServer.Active:=True; _UDPServer.OnUDPRead:=UDPRead; end; procedure TForm1.UDPRead(Sender: TObject; AData: TStream; ABinding: TIdSocketHandle); Var S : String; Begin SetLength(S,4); AData.Read(S[1],4); Caption:=S; end; procedure TForm1.Button2Click(Sender: TObject); begin _UDPServer.Broadcast('test',4444); end; end. |
Re: Indy: mehrere UDP-Server auf einem Port
Hallo Basilikum!
Herzlichen Dank für den Code. Damit funktioniert das so, wie ich mir das vorgestellt hatte. Es ist mir allerdings unverständlich, wieso das bei den Indys nicht vorgesehen ist. Da werde ich mal nachfragen müssen. Gruß Dietmar Brüggendiek |
Alle Zeitangaben in WEZ +1. Es ist jetzt 15:27 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz