Benutzer mit den meisten Antworten
TcpClient Anwendung auf einem PC in VB simulieren

Frage
-
Hallo Forum,
ich versuche seit einigen Tagen in VB mit System.Net.Sockets (TcpClient, TcpListener, Pending, NetworkStream, ...) eine kleine Anwendung zusammen zu Stoppeln, die es mir erlaubt eine Client/Server-Verbindung zu simulieren. Das heist, a) alls Server auf Horchposition gehen und dann als Client eine Verbindung aufbauen und Text senden/empfangen. Das muß doch prinzipiell gehen.
Im folgenden Code-Beispiel bekomme ich (in der unterstrichenen Zeile) eine Fehlermeldung "Der Vorgang ist für nicht verbundene Sockets unzulässig." Versuche ich jedoch ein client.Connect davor, spricht er von "Sockets bereits verbunden". Jetzt weiß ich nicht mehr weiter, ich hoffe ihr könnt mir helfen,
lg heinz
Imports System.Net Imports System.Net.Sockets Module Module1 Sub Main() Try ' Set the TcpListener on port 13000. Dim port As Int32 = 13000 'Dim server As New TcpListener(IPAddress.Any, port) Dim server As New TcpListener(IPAddress.Parse("10.0.0.1"), port) ' Start listening for client requests. server.Start() ' Use the Pending method to poll the underlying socket instance for client connection requests. Dim s As Int16 = 0 While s = 0 If server.Pending() Then Exit While ' Hier wird der anrufende Client simuliert Connect("10.0.0.1", "Text vom Client") End While ' Buffer for reading data Dim bytes(1024) As [Byte] Dim data As [String] = Nothing ' Enter the listening loop. While True Console.Write("Waiting for a connection... ") ' Perform a blocking call to accept requests. ' You could also user server.AcceptSocket() here. Dim client As TcpClient = server.AcceptTcpClient() Console.WriteLine("Connected!") data = Nothing ' Get a stream object for reading and writing Dim stream As NetworkStream = client.GetStream() Dim i As Int32 ' Loop to receive all the data sent by the client. i = stream.Read(bytes, 0, bytes.Length) While (i <> 0) ' Translate data bytes to a ASCII string. data = System.Text.Encoding.ASCII.GetString(bytes, 0, i) Console.WriteLine([String].Format("Received: {0}", data)) ' Process the data sent by the client. data = data.ToUpper() Dim msg As [Byte]() = System.Text.Encoding.ASCII.GetBytes(data) ' Send back a response. stream.Write(msg, 0, msg.Length) Console.WriteLine([String].Format("Sent: {0}", data)) i = stream.Read(bytes, 0, bytes.Length) End While ' Shutdown and end connection client.Close() End While Catch e As SocketException Console.WriteLine("SocketException: {0}", e) End Try Console.WriteLine(ControlChars.Cr + "Hit enter to continue...") Console.Read() End Sub '------------------------------------------------------------------------ Private Sub Connect(ByVal server As [String], ByVal message As [String]) Try ' Create a TcpClient. ' Note, for this client to work you need to have a TcpServer ' connected to the same address as specified by the server, port ' combination. Dim port As Int32 = 13000 Dim tclient As New TcpClient(server, port) 'client.Connect(server, port) 'doppelter Connect ' Translate the passed message into ASCII and store it as a Byte array. Dim data As [Byte]() = System.Text.Encoding.ASCII.GetBytes(message) ' Get a client stream for reading and writing. ' Stream stream = client.GetStream(); Dim stream As NetworkStream = tclient.GetStream() ' Send the message to the connected TcpServer. stream.Write(data, 0, data.Length) Console.WriteLine("Sent: {0}", message) ' Receive the TcpServer.response. ' Buffer to store the response bytes. ''data = New [Byte](256) {} ' String to store the response ASCII representation. ''Dim responseData As [String] = [String].Empty ' Read the first batch of the TcpServer response bytes. ''Dim bytes As Int32 = stream.Read(data, 0, data.Length) ''responseData = System.Text.Encoding.ASCII.GetString(data, 0, bytes) ''Console.WriteLine("Received: {0}", responseData) ' Close everything. ''stream.Close() ''client.Close() Catch e As ArgumentNullException Console.WriteLine("ArgumentNullException: {0}", e) Catch e As SocketException Console.WriteLine("SocketException: {0}", e) End Try ''Console.WriteLine(ControlChars.Cr + " Press Enter to continue...") ''Console.Read() End Sub 'Connect '------------------------------------------------------------------------ Public Sub PendingTeil(ByVal ipNr As String, ByVal portNumber As Long) Try 'Dim ipAddress As IPAddress = Dns.Resolve("localhost").AddressList(0) 'ursprünglicher Code Dim ipAddress As IPAddress = Dns.GetHostEntry("localhost").AddressList(0) Dim tcpListener As New TcpListener(ipAddress, portNumber) tcpListener.Start() ' Use the Pending method to poll the underlying socket instance for client connection requests. If Not tcpListener.Pending() Then Console.WriteLine("Sorry, no connection requests have arrived") Else 'Accept the pending client connection and return a TcpClient object initialized for communication. Dim tcpClient As TcpClient = tcpListener.AcceptTcpClient() ' Using the RemoteEndPoint property. Console.Write("I am listening for connections on ") Console.WriteLine(ipAddress.Parse(CType(tcpListener.LocalEndpoint, IPEndPoint).Address.ToString())) Console.Write("on port number ") Console.Write(CType(tcpListener.LocalEndpoint, IPEndPoint).Port.ToString()) End If Catch End Try End Sub End Module
Antworten
-
Jetzt werde ich mich über die Analyse des Codes machen.
Herzlichen Dank für deine Hilfe - aber ich denke ich werde dein Wissen noch einige Male benötigen,
lg heinz
Hallo Heinz, super das freut mich.Der Code funktioniert übrigens auch über das Internet Dazu musst Du nur die öffentlichen IP Adressen der beiden Router eingeben und eine entsprechende Port Weiterleitung in den Routern haben.
Ach bitte mache eine NEUE Frage auf. Sonst wird das für die anderen, die ein Problem lösen müssen, zu unübersichtlich.
schöne Grüße Ellen
Ich benutze/ I'm using VB2008 & VB2010- Als Antwort markiert Heinz999 Montag, 21. Februar 2011 12:50
Alle Antworten
-
Hallo Heinz,
Dein Code geht. Ich habe folgende Änderungen vorgenommen:
Try ' Set the TcpListener on port 13000. Dim port As Int32 = 13000 Dim server As New TcpListener(IPAddress.Any, port) 'Dim server As New TcpListener(IPAddress.Parse("10.0.0.1"), port) ' Start listening for client requests. server.Start()
und diese hier:
While s = 0 If server.Pending() Then Exit While ' Hier wird der anrufende Client simuliert Connect("127.0.0.1", "Text vom Client") End While
Dein Fehler ist: Man kann nicht auf ein und demselben IP Endpunkt zwei sockets verbinden
Probier das mal so.
schöne Grüße Ellen
Ich benutze/ I'm using VB2008 & VB2010- Bearbeitet Ellen Ramcke Samstag, 19. Februar 2011 20:37 screenshot
-
Hallo Heinz,
meine Änderungen Deines Codes sind erst einmal die Lösung der Fehlermeldung oben. Ich habe mir Deinen Code noch einmal genau angesehen und ich muss sagen, der ist noch weit entfernt von einer lauffähigen Lösung.
Ich habe im Juli letzen Jahres hier ein unversielles TCP Chat Programm gepostet. Das folgende Programm ist eine Weiterentwicklung davon Dieses möchte ich Dir zur Verfügung stellen. Die Benutzung ist ohne copyright.
http://cid-c2d662ab4dd70d18.office.live.com/self.aspx/.Documents/TCP%5E_Chat.zip
Das interesante an diesem Projekt ist die class TCPChat. Diese verwende ich jetzt in vielen Forms Anwendungen zur TCP Kommunikation. Diese stellt einen asynchronen server bereit und arbeitet gleichzeitig als client
Viel Spaß und schöne Grüße Ellen
Ich benutze/ I'm using VB2008 & VB2010 -
Hallo Ellen,
danke für die rasche Antwort. Leider ändern deine Änderungen bei mir das Ergebnis nicht.
Prinzipiell geht es mir um das Verstehen und das Zusammenspiel der einzelnen Funktionen. Wenn ich deine Aussage "Man kann nicht auf ein und demselben IP Endpunkt zwei sockets verbinden" wörtlich nehme, ist eigentlich mein Vorhaben nicht möglich (was dein Testergebnis ja widerlegt). Die zweite Änderung auf "127.0.0.1" verstehe ich nicht ganz. Kannst du das etwas näher erläutern?
Ich habe mir dein "TCPChat" herunter geladen und werde nun versuchen anhand der Code-Verfolgung schlauer zu werden.
Nochmals Danke und schöne Grüße Heinz
-
Die zweite Änderung auf "127.0.0.1" verstehe ich nicht ganz. Kannst du das etwas näher erläutern?
Hallo Heinz,
nehmen wir mal an Dein Netzwerkadapter hat die IP Adresse 192.168.2.1.
Dann kann man einen TCPlistener verbinden mit 192.168.2.1:13000 auf port 13000. (Das nennt man Endpunkt) eine zweite Instanz auf demselben Rechner kann diesen Endpunkt nicht mehr verwenden. Das gilt für einen Client sowie einen server. Die Fehlermeldung: "Sockets bereits verbunden" ist ja eindeutig.
Was aber geht ist folgendes:
Einen listenener auf 0.0.0.0:13000 legen und einen client auf 192.168.2.1:13000. Dann unterhalten sich client und listener über den port 13000.
Die IP Adresse 127.0.0.1 hat eine Sonderfunktion. Diese Adresse ist das loop back device eines host. Lese bitte Seite 26 Einführung in TCP/IP
Ich stell Dir noch einen link ein. Einführung in TCP/IP. Muss ich noch suchen.
schöne Grüße Ellen
Hier die links. Hab ich alles mühevoll durchgearbeitet. An diesen Grundlagen kommt man nicht vorbei, trotz komfortabler NET Klassen
Einstiegsseite wiki:
http://de.wikipedia.org/wiki/TCP/IP-Referenzmodell#TCP.2FIP-Referenzmodell
und hier das pdf Dokument runterladen
http://www.rvs.uni-bielefeld.de/~heiko/tcpip/
Ich benutze/ I'm using VB2008 & VB2010- Bearbeitet Ellen Ramcke Sonntag, 20. Februar 2011 11:38 Nachtrag
-
Hallo Hellen,
danke für die Links. Ich bezog bisher mein Basiswissen aus "Internet intern" von Tischler/Jennrich, welches allerdings schon etwas älter ist. Im Prinzip ist mir die Sache verständlich, der Teufel liegt im Detail und in der Umsetzung.
Aber nun ein anderes Problem:
Ich habe nun TCPChat benutzt und die Fehlermeldung "sendData: Es konnte keine Verbindung hergestellt werden, da der Zielcomputer die Verbindung verweigert" bekommen. Ich habe nun versucht in der Windows-Firewall (ich fahre XP-Home) das Port 5000 zuzulassen, als Name habe ich "TCPChat" eingegeben - kein Erfolg.
Meine Frage dazu: Wie kann ich der Anwendung den Zugriff ermöglichen? Spielt der Router (Internet Gateway) hier auch eine Rolle und muß ich auch dort die Anwendung freigeben?
lg Heinz
-
Hallo Heinz,
ich habe hier PC Ferndiagnose. Ich möchte mir das mal ansehen. Pack das Programm aus und starte es. Doppelklicken auf "Hier doppelklicken" und ich bin in Deinem Computer drin. Eibverstanden?
Gruß Ellen
Ich benutze/ I'm using VB2008 & VB2010 -
Hallo Ellen,
TCPChat funktioniert nun. Mein Fehler war, dass ich es nicht installiert hatte sondern nur mit dem Debugger ausgeführt hatte.
Nach der Installation hat mich die Firewall gefragt ob ich es weiter blockieren will. Nachdem ich dies verneint habe, habe ich es auch in der Firewall eingetragen gefunden.
Jetzt werde ich mich über die Analyse des Codes machen.
Herzlichen Dank für deine Hilfe - aber ich denke ich werde dein Wissen noch einige Male benötigen,
lg heinz
-
Jetzt werde ich mich über die Analyse des Codes machen.
Herzlichen Dank für deine Hilfe - aber ich denke ich werde dein Wissen noch einige Male benötigen,
lg heinz
Hallo Heinz, super das freut mich.Der Code funktioniert übrigens auch über das Internet Dazu musst Du nur die öffentlichen IP Adressen der beiden Router eingeben und eine entsprechende Port Weiterleitung in den Routern haben.
Ach bitte mache eine NEUE Frage auf. Sonst wird das für die anderen, die ein Problem lösen müssen, zu unübersichtlich.
schöne Grüße Ellen
Ich benutze/ I'm using VB2008 & VB2010- Als Antwort markiert Heinz999 Montag, 21. Februar 2011 12:50