Jump to content
Donald Shimoda

Sample needed for Net.TSocket UDP cliente and server

Recommended Posts

7 hours ago, Fr0sT.Brutal said:

FWIW, with UDP packet loss is normal

In this case the device is connected with a direct cable and the response is ok. Synapse lost 0 data. Indy lost 20% of data.

Share this post


Link to post

I agree with @Fr0sT.Brutal. UDP is an unreliable connectionless transport, so some amount of packet loss is to be expected, even over a direct cable.  The most common cause of packet loss is when the receiver is reading packets slower than they are being sent and so it runs out of buffer space.  Until buffer space is freed up, new packets will get silently discarded by the OS.  So, check if your reading code is running too slow, or that your receive buffer is too small for your situation.  Of course, there can be other causes of packet loss, too (network congestion, outages, etc).

Edited by Remy Lebeau

Share this post


Link to post

UDP application have to be designed to work around data loss, that is not the fault of a low level UDP component.  If one loses packets and another does not, the first is probably less efficient. 

 

UDP is the basis of HTTP/3 and QUIC, which is reliable. 

 

Angus

 

Share this post


Link to post
On 12/14/2021 at 1:28 PM, Remy Lebeau said:

So, either your reading code is running too slow, or your receive buffer is too small for your situation.

The read is on a thread ,  nothing else interrupts. The same code, same test, using synapse work perfect. Problem in windows and Linux. Can send you the unit in private and maybe you can give your opinion?

I doubt the problem is buffer because comm is text and small amount of data. Just to be sure: how to get a faster response on indy reception? How to define a bigger buffer?

 

Thanks in advance

Edited by Donald Shimoda

Share this post


Link to post
On 12/15/2021 at 4:00 AM, Angus Robertson said:

If one loses packets and another does not, the first is probably less efficient

Correct, i believe the same and this, maybe and i hope, can be fixed with small adjustments

Share this post


Link to post
8 hours ago, Donald Shimoda said:

Correct, i believe the same and this, maybe and i hope, can be fixed with small adjustments

without any code, it is very difficult to help.
choosing udp as protocol has it's own consequency, ready to handle packet loss.

Share this post


Link to post
On 12/18/2021 at 11:09 AM, Donald Shimoda said:

The read is on a thread ,  nothing else interrupts.

Just because it runs is in a thread doesn't guarantee it is fast/efficient.  And actually, in your scenario, there is actually an interrupt, see below...

On 12/18/2021 at 11:09 AM, Donald Shimoda said:

The same code, same test, using synapse work perfect. Problem in windows and Linux. Can send you the unit in private and maybe you can give your opinion?

I just now gave it a quick look, and one major issue I see is that you are not using TIdUDPServer the way it is meant to be used,   You are creating it in your own thread that does its own reading of the UDP socket, rather than using TIdUDPServer's OnUDPRead event.  It seems you are not aware that TIdUDPServer is a multi-threaded component, its OnUDPRead event is fired in the context of internal reading threads, one per Binding.  The Synapse/Net.TSocket UDP sockets you are using don't work that same way.

 

So, it actually makes sense now why you are losing packets when using Indy - your code has multiple threads reading from the same UDP socket at the same time, so there are going to be times that you will receive packets in your own thread and be able to process them, and there are going to be times when TIdUDPServer will receive packets that you are ignoring.

 

If you want to do your own reading of an Indy UDP socket, don't use TIdUDPServer, use TIdUDPClient instead.  Despite their names, they are not truly client/server components, like with how TCP components work.  Since UDP is connection-less, you can actually mix TIdUDPClient and TIdUDPServer in various ways.  You can use TIdUDPServer as a client and TIdUDPClient as a server.  Or you can have two TIdUDPClients, or two TIdUDPServers, communicate with each other.  The difference between them is only in how they manage their respective sockets internally.  With TIdUDPClient, it just creates the socket, but you are responsible for all of the reading/writing.  With TIdUDPServer, it does all of the reading for you, and then you are responsible for writing.

 

That being said, I see a secondary issue in your code, not related to any particular socket library, that could also cause packet loss.  In your reading thread, when you do receive a packet, you lock a TCriticalSection before processing the packet.  But, you are using TCriticalSection.TryLock() for that lock, which is not a blocking function.  If, for some reason, the CS is already locked by another thread, TryLock() will exit immediate with a False return value, and you will then skip processing the packet, you are not caching/retrying the packet, you just throw it away.

On 12/18/2021 at 11:09 AM, Donald Shimoda said:

How to define a bigger buffer?

There is actually 2 buffers involved - the kernel buffer inside the socket itself, and the application buffer that TIdUDPServer reads into before giving you the data in the OnUDPRead event.  To set the size of the socket's buffer, you can use Indy's TIdSocketHandle.SetSockOpt() method to assign a value to the socket's SO_RCVBUF option.  To set the size of the OnUDPRead buffer, TIdUDPServer has a BufferSize property, which defaults to 8K.

Share this post


Link to post

In Indy's document, it is said that you can not do any time consuming method in TIdUDPServer.OnRead procedure.

 

to avoid TIdUDPServer loss package, I have added a buffer to receive data from TIdUDPServer.OnRead event. and then create  another thread to handle data in this buffer.

Share this post


Link to post

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now

×