Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Does BeginSend<IList<ArraySegment....) perform atomic send of all the ArraySegments?

Tags:

c#

.net

sockets

The Socket class in .NET exposes the following method:

Socket.BeginSend Method (IList<ArraySegment<Byte>>, SocketFlags, AsyncCallback, Object)

I have a BufferManager class that returns ArraySegment<byte> of a specified, constant size of 2kB. Now I have a message to be sent, let's say it is 10kB large, so I can use 5 preallocated buffers to store this message and call Socket.BeginSend(IList<ArraySegment>>...). Will this message be sent atomically, as it would be when I would just use just byte[] (ie. several parallel BeginSend operations wouldn't mix messages on the remote site)?

Edit: to clarify - I'm using TCP/IP socket and my program calls BeginSend from several threads simultaneously. Let's say we have two lists of array segments:
L1: a1 a2 a3
L2: b1 b2 b3
Now I call BeginSend(L1...) and BeginSend (L2...) from two threads at the same time. I want to know whether those two lists won't get mixed on the remote side and I won't read something like: a1 b1 b2 a2 b3 a3.

like image 477
paszczi Avatar asked Jul 04 '11 08:07

paszczi


1 Answers

All a BufferManager does is maintain a set of fixed blocks of memory for you to use. The BufferManager has no affect on the concurrency of the bytes, or how they are used in anyway at all what so ever. From the MSDN documentation:

You can use the BufferManager class to manage a buffer pool. The pool and its buffers are created when you instantiate this class and destroyed when the buffer pool is reclaimed by garbage collection. Every time you need to use a buffer, you take one from the pool, use it, and return it to the pool when done. This process is much faster than creating and destroying a buffer every time you need to use one.

The BufferManager is just a convenient way of avoiding calls to new[] and then waiting for the GC to destroy the blocks. When you are done sending these blocks, make sure you call BlockManager.ReturnBuffer, or those bytes will be unavailable for future messages, and will linger until your BufferManager itself is GC'd. If it's going to be along lived BufferManager, and you are sending a lot of messages using those buffers, you will likely leak huge amounts of memory.

like image 93
Armentage Avatar answered Oct 30 '22 16:10

Armentage