private SocketConnection(Socket socket, PipeOptions sendPipeOptions, PipeOptions receivePipeOptions, SocketConnectionOptions socketConnectionOptions, string name, ILogger logger) { if (socket == null) { throw new ArgumentNullException(nameof(socket)); } if (string.IsNullOrWhiteSpace(name)) { Name = GetType().Name.Trim(); } if (sendPipeOptions == null) { sendPipeOptions = PipeOptions.Default; } if (receivePipeOptions == null) { receivePipeOptions = PipeOptions.Default; } Socket = socket; _logger = logger ?? NullLoggerFactory.Instance.CreateLogger("NetGear.Core.SocketConnection"); _trace = new TraceDebugger(_logger); var localEndPoint = (IPEndPoint)Socket.LocalEndPoint; var remoteEndPoint = (IPEndPoint)Socket.RemoteEndPoint; LocalAddress = localEndPoint.Address; LocalPort = localEndPoint.Port; RemoteAddress = remoteEndPoint.Address; RemotePort = remoteEndPoint.Port; SocketConnectionOptions = socketConnectionOptions; _sendOptions = sendPipeOptions; _receiveOptions = receivePipeOptions; _sendToSocket = new Pipe(_sendOptions); // read from this pipe and send to socket _receiveFromSocket = new Pipe(_receiveOptions); // recv from socket and push to this pipe _output = new WrappedWriter(_sendToSocket.Writer, this); _input = new WrappedReader(_receiveFromSocket.Reader, this); _sendOptions.ReaderScheduler.Schedule(s_DoSendAsync, this); _receiveOptions.WriterScheduler.Schedule(s_DoReceiveAsync, this); }
/// <summary> /// Open a new or existing socket as a client /// </summary> public static async Task <SocketConnection> ConnectAsync( EndPoint endpoint, PipeOptions sendPipeOptions, PipeOptions receivePipeOptions, SocketConnectionOptions connectionOptions = SocketConnectionOptions.None, Func <SocketConnection, Task> onConnected = null, Socket socket = null, string name = null) { var addressFamily = endpoint.AddressFamily == AddressFamily.Unspecified ? AddressFamily.InterNetwork : endpoint.AddressFamily; var protocolType = addressFamily == AddressFamily.Unix ? ProtocolType.Unspecified : ProtocolType.Tcp; if (socket == null) { socket = new Socket(addressFamily, SocketType.Stream, protocolType); } if (sendPipeOptions == null) { sendPipeOptions = PipeOptions.Default; } if (receivePipeOptions == null) { receivePipeOptions = PipeOptions.Default; } SetRecommendedClientOptions(socket); using (var args = CreateArgs(receivePipeOptions.ReaderScheduler, out _)) { Helpers.DebugLog(name, $"connecting to {endpoint}..."); await ConnectAsync(socket, args, endpoint); } Helpers.DebugLog(name, "connected"); var connection = Create(socket, sendPipeOptions, receivePipeOptions, connectionOptions, name); if (onConnected != null) { await onConnected(connection); } return(connection); }
private bool HasFlag(SocketConnectionOptions option) => (option & SocketConnectionOptions) != 0;
/// <summary> /// Create a SocketConnection instance over an existing socket; /// 进出两个方向都采用完全一样的设置。通常用于客户端,服务端不会也不应该这样子搞 /// </summary> public static SocketConnection Create(Socket socket, PipeOptions pipeOptions = null, SocketConnectionOptions socketConnectionOptions = SocketConnectionOptions.None, string name = null, ILogger logger = null) { return(new SocketConnection(socket, pipeOptions, pipeOptions, socketConnectionOptions, name, logger)); }