public static Socket Create(AddressFamily addressFamily, SocketType socketType, ProtocolType protocolType, bool blocking) { Socket socket; var result = SocketInterop.Socket(addressFamily, socketType, protocolType, blocking, out socket); result.ThrowOnError(); return(socket); }
private TSocket CreateAcceptSocket(IPEndPoint endPoint, SocketFlags flags) { int acceptSocketFd = -1; int port = endPoint.Port; try { bool ipv4 = endPoint.AddressFamily == System.Net.Sockets.AddressFamily.InterNetwork; SocketInterop.Socket(ipv4 ? AddressFamily.InterNetwork : AddressFamily.InterNetworkV6, SocketType.Stream, ProtocolType.Tcp, blocking: false, out acceptSocketFd).ThrowOnError(); TSocket acceptSocket = new TSocket(this, acceptSocketFd, flags); if (!ipv4) { // Kestrel does mapped ipv4 by default. acceptSocket.SetSocketOption(SocketOptionLevel.IPv6, SocketOptionName.IPv6Only, 0); } if (_transportOptions.ReceiveOnIncomingCpu) { if (_transportThread.CpuId != -1) { if (!acceptSocket.TrySetSocketOption(SocketOptionLevel.Socket, SocketOptionName.IncomingCpu, _transportThread.CpuId)) { _logger.LogWarning($"Cannot enable nameof{SocketOptionName.IncomingCpu} for {endPoint}"); } } } // Linux: allow bind during linger time acceptSocket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReuseAddress, 1); // Linux: allow concurrent binds and let the kernel do load-balancing acceptSocket.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReusePort, 1); if ((flags & SocketFlags.DeferAccept) != 0) { // Linux: wait up to 1 sec for data to arrive before accepting socket acceptSocket.SetSocketOption(SocketOptionLevel.Tcp, SocketOptionName.DeferAccept, 1); } acceptSocket.ZeroCopyThreshold = LinuxTransportOptions.NoZeroCopy; if (_transportOptions.ZeroCopy && _transportOptions.ZeroCopyThreshold != LinuxTransportOptions.NoZeroCopy) { if (acceptSocket.TrySetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ZeroCopy, 1)) { acceptSocket.ZeroCopyThreshold = _transportOptions.ZeroCopyThreshold; } } acceptSocket.Bind(endPoint); if (port == 0) { // When testing we want the OS to select a free port port = acceptSocket.GetLocalIPAddress().Port; } acceptSocket.Listen(ListenBacklog); endPoint.Port = port; return(acceptSocket); } catch { if (acceptSocketFd != -1) { IOInterop.Close(acceptSocketFd); } throw; } }