Skip to content

[API Proposal]: add overloads with SocketAddress to Socket's SendTo and ReceiveFrom #87397

Closed
@wfurt

Description

@wfurt

Background and motivation

This is subset from #30797. There is long discussion about how to make sending and receiving UDP more efficient. Current overloads allocate a lot for each packet and that kills performance and it puts lot of pressure on GC. Garbage collection has significant impact on scenarios that are sensitive to timing - like multiplayer Unity games.

API Proposal

namespace System.Net.Sockets;

public class Socket
{
+  public int ReceiveFrom(Span<byte> buffer, SocketFlags socketFlags, SocketAddress socketAddress);
+  public ValueTask<int> ReceiveFromAsync(Memory<byte> buffer, SocketFlags socketFlags, SocketAddress socketAddress, CancellationToken cancellationToken = default);

+. public int SendTo(ReadOnlySpan<byte> buffer, SocketFlags socketFlags, SocketAddress socketAddress);
+. public ValueTask<int> SendToAsync(ReadOnlyMemory<byte> buffer, SocketFlags socketFlags, SocketAddress socketAddress, CancellationToken cancellationToken = default);
}

Instead of allocating and returning EndPoint, we can reuse SocketAddress and we would update it in place. Ideally using API proposed in #86872 but in worst case the SocketAddress is already writable and we can play some internal tricks.

API Usage

example of simple server that would process request - inspired by DNS server linked in #30797

  SocketAddress sa = new SocketAddress(AddressFamily.InterNetworkV6);
  while (doWork)
  {
      int receivedLength = s.ReceiveFrom(buffer, SocketFlags.None, sa);
      response = processRequest(buffer.Slice(0, receivedLength);
      s.SendTo(response, SocketFlags.None, sa);
  }

The async version would be basically same with addition of CancellationToken. Unlike ReceiveFromAsync that used EndPoint and returns SocketReceiveFromResult we would return ValueTask<int> just like the synchronous version and we would update socketAddress in-place.

Alternative Designs

No response

Risks

This is low-level API intended for experienced users. While there is nothing particularly dangerous one should be very careful about life cycle of the socketAddress as it can be overwritten on subsequent use.

Metadata

Metadata

Assignees

Labels

api-approvedAPI was approved in API review, it can be implementedarea-System.Net.SocketsblockingMarks issues that we want to fast track in order to unblock other important work

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions