Reputation: 1039
I succeded creating a UDP client-server connection and sending a large image over it.
I split and sent the image into packets of 1500 bytes each .I got at the other end 330025 bytes of 353723 (which I think is pretty good). But as you know UDP packets are not in order so I have to id every packet it's sent (I can't use tcp because I need speed for my project-game). Now I want to ask the 'server' for the missing packets.
This is the server's code:
Imports System
Imports System.IO
Imports System.Net
Imports System.Threading
Imports System.Net.Sockets
Imports System.Text.Encoding
Public Class Form1
Dim ep_client As New IPEndPoint(IPAddress.Parse("127.0.0.1"), 60000)
Dim ep_server As New IPEndPoint(IPAddress.Any, 60000)
Dim publisher As New UdpClient(ep_client)
Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
Form2.Show()
End Sub
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
Dim sendbytes() As Byte = ASCII.GetBytes(txt1.Text)
Dim img As Image, img_stream As MemoryStream, buffer As Byte()
Dim packet_size As Integer = 1024, sent_size As Long
Try
img_stream = imgToBytes(txt1.Text)
Debug.Print(img_stream.Length)
ReDim buffer(packet_size)
While Not img_stream.Position = img_stream.Length
sent_size += img_stream.Read(buffer, 0, packet_size)
publisher.Send(buffer, buffer.Length)
End While
Debug.Print(100 * sent_size / img_stream.Length & "%")
Catch ex As Exception
Debug.Print(ex.Message)
End Try
End Sub
Private Sub Button2_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button2.Click
''When I press this button it is supposed to 'listen'
Try
'Silence...Nothing here..
publisher.BeginReceive(New AsyncCallback(AddressOf receive), publisher)
Debug.Print("listening")
Catch ex As Exception
Debug.Print(ex.Message)
End Try
End Sub
Sub receive(ByVal ar As IAsyncResult)
''It should take the packets from coming from 'any' ip.
publisher.EndReceive(ar, ep_server)
Debug.Print("received")
publisher.BeginReceive(New AsyncCallback(AddressOf receive), publisher)
End Sub
Function imgToBytes(ByVal file_name As String) As MemoryStream
Dim img As Image = Image.FromFile(file_name)
Dim stream As New MemoryStream
img.Save(stream, Drawing.Imaging.ImageFormat.Jpeg)
stream.Position = 0
Return stream
End Function
End Class
This is the code for the client(which becomes a server...):
Imports System
Imports System.IO
Imports System.Net
Imports System.Threading
Imports System.Net.Sockets
Imports System.Text.Encoding
Public Class Form2
Dim ep_server As IPEndPoint = New IPEndPoint(IPAddress.Any, 60000)
Dim ep_client As New IPEndPoint(IPAddress.Parse("127.0.0.1"), 60000)
Dim client As New UdpClient(ep_client)
Dim stream As New MemoryStream
Private Sub Form2_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
Try
'I belive it's listening for packets comming from ep_client ->
'because I initialized the 'client' object with it
'How can I make it listen for ep_server?(from all ip's)
client.BeginReceive(New AsyncCallback(AddressOf receive), client)
Catch ex As Exception
Debug.Print(ex.Message)
End Try
End Sub
Public Sub receive(ByVal ar As IAsyncResult)
Dim buffer As Byte()
Try
'Now I use ep_server ->the proper way
buffer = client.EndReceive(ar, ep_server)
stream.Write(buffer, 0, buffer.Length)
client.BeginReceive(New AsyncCallback(AddressOf receive), client)
Catch ex As Exception
Debug.Print(ex.Message)
End Try
End Sub
Private Sub PictureBox1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles PictureBox1.Click
Dim img As Image = Image.FromStream(stream)
Debug.Print(stream.Length)
PictureBox1.Image = img ''Weird image because the packets are not arranged
End Sub
Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
Debug.Print("sent")
client.Send(ASCII.GetBytes("a"), 1, ep_client) ''Send something ->not working
End Sub
End Class
No error..nothing. I can send a picture from server to client but not the other way around. And there's another weird thing. I've put the client's code on another machine...It's gives an error when I write the ipv4(of the other machine) in ep_client like this Dim ep_client As New IPEndPoint(IPAddress.Parse("192.168.1.100"), 60000)
.
I get no error. And if I initialize both of the 'udp-clients' on server and client code like this : Dim client as new UdpClient(ep_client)
it gives an error :
Only one usage of each socket address (protocol/network address/port) is normally permitted
But if I write it like this (on the server side) Dim client as new UdpClient("127.0.0.1",60000)
it gives no error.What's the difference?
Where is the problem?
Upvotes: 1
Views: 1671
Reputation: 11426
Your immediate problem is you can only have one Socket bound to a port number on one machine at any given time - so there must already be something bound to port 60000 to give you the "Only one usage of each socket address..." Exception - perhaps another instance of your program is already running?
Aside, and I am a game developer and understand the need to use UDP, UDP is not a good choice here instead of TCP. UDP is good for small "real-time" data not large one-off data. If using UDP you have to worry about: reliability - the datagram may not get through at all, duplicates - the datagram may be duplicate, congestion control - sending too many datagrams in quick succession without checking previous ones are getting through will just result in them being dropped... Really sending a large file is much better suited to TCP.
Upvotes: 1