Skip to content

Instantly share code, notes, and snippets.

@jacobslusser
Created November 14, 2023 22:26
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jacobslusser/55497df65d90db75a67a2f6ae693b8f9 to your computer and use it in GitHub Desktop.
Save jacobslusser/55497df65d90db75a67a2f6ae693b8f9 to your computer and use it in GitHub Desktop.
Proper DoSend pipeline loop
while (true)
{
// Get data from the send buffer
var result = await reader.ReadAsync().ConfigureAwait(false);
if (result.IsCanceled)
{
break;
}
// Write to the socket
var buffers = result.Buffer;
if (!buffers.IsEmpty)
{
int bytesSent;
if (buffers.IsSingleSegment)
{
bytesSent = await _socket!.SendAsync(buffers.First, SocketFlags.None).ConfigureAwait(false);
}
else
{
// HELP!!!
bytesSent = 0;
}
reader.AdvanceTo(buffers.GetPosition(bytesSent));
if (result.IsCompleted)
{
break;
}
}
}
@jacobslusser
Copy link
Author

@davidfowl if you have a moment, I'm trying to understand and replicate the DoSend and DoRecieve methods of the SocketConnection class in Kestrel. In that implementation there is a complicated SocketAsyncEventArgs derived class that I'm trying to avoid by using the standard Socket extension methods. However, there is not a good way or example I can find for sending a ReadOnlySequence<byte> instead of a simple ReadOnlyMemory<byte> -- noted by the HELP!!! comment above.

This question has been discussed in:

I'm not looking for a first-class implementation, just some guidance on the best way to send multiple buffers to avoid copies and loops (if possible).

Thx

@jacobslusser
Copy link
Author

I ended up following the SendMultiSegmentAsync approach used in SignalR. A little more basic than I expected, but I guess if it is good enough for SignalR....

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment