循环直到使用 BeginConnect(C# 套接字)连接到服务器
Posted
技术标签:
【中文标题】循环直到使用 BeginConnect(C# 套接字)连接到服务器【英文标题】:Loop until connected to server with BeginConnect (C# sockets) 【发布时间】:2019-01-14 06:56:30 【问题描述】:我需要一种方法来尝试连接到服务器,直到它成功连接。我已经使用 Socket.Connect 成功地完成了,但我无法让它与 Socket.BeginConnect 一起使用。
这是方法:
public void Start()
while (clientSocket == null || !clientSocket.Connected)
try
clientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Stream, ProtocolType.Tcp);
clientSocket.BeginConnect(serverEndPoint, new AsyncCallback(ConnectCallback), null);
catch (SocketException)
clientSocket.Close();
Start();
catch (Exception) throw;
private void ConnectCallback(IAsyncResult ar)
try
clientSocket.EndConnect(ar);
clientSocket.BeginReceive(buffer, 0, buffer.Length, SocketFlags.None, new AsyncCallback(ReceiveCallback), null);
catch (Exception) throw;
但我收到此错误(多次):
System.ArgumentException:未返回 IAsyncResult 对象 来自此类的相应异步方法。范围 名称:异步结果在 System.Net.Sockets.Socket.InternalEndConnect(IAsyncResult asyncResult) 在 System.Net.Sockets.Socket.EndConnect(IAsyncResult asyncResult) 在 SocketLibrary.Client.TCPClient.ConnectCallback(IAsyncResult ar) 在 System.Net.LazyAsyncResult.Complete(IntPtr userToken) 在 System.Net.ContextAwareResult.CompleteCallback(对象状态)在 System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext、ContextCallback 回调、对象状态、布尔值 preserveSyncCtx) 在 System.Threading.ExecutionContext.Run(ExecutionContext executionContext、ContextCallback 回调、对象状态、布尔值 preserveSyncCtx) 在 System.Threading.ExecutionContext.Run(ExecutionContext executionContext、ContextCallback 回调、对象状态)在 System.Net.ContextAwareResult.Complete(IntPtr userToken) 在 System.Net.LazyAsyncResult.ProtectedInvokeCallback(对象结果, IntPtr userToken) 在 System.Net.Sockets.Socket.ConnectCallback() 在 System.Net.Sockets.Socket.RegisteredWaitCallback(对象状态,布尔值 超时)在 System.Threading._ThreadPoolWaitOrTimerCallback.PerformWaitOrTimerCallback(对象 状态,布尔超时)
我尝试捕获 ArgumentException,但随后出现此错误(再次多次)
未处理的异常:System.NullReferenceException:对象引用 未设置为对象的实例。在 SocketLibrary.Client.TCPClient.ConnectCallback(IAsyncResult ar) 在 System.Net.LazyAsyncResult.Complete(IntPtr userToken) 在 System.Net.ContextAwareResult.CompleteCallback(对象状态)在 System.Threading.ExecutionContext.RunInternal(ExecutionContext executionContext、ContextCallback 回调、对象状态、布尔值 preserveSyncCtx) 在 System.Threading.ExecutionContext.Run(ExecutionContext executionContext、ContextCallback 回调、对象状态、布尔值 preserveSyncCtx) 在 System.Threading.ExecutionContext.Run(ExecutionContext executionContext、ContextCallback 回调、对象状态)在 System.Net.ContextAwareResult.Complete(IntPtr userToken) 在 System.Net.LazyAsyncResult.ProtectedInvokeCallback(对象结果, IntPtr userToken) 在 System.Net.Sockets.Socket.ConnectCallback() 在 System.Net.Sockets.Socket.RegisteredWaitCallback(对象状态,布尔值 超时)在 System.Threading._ThreadPoolWaitOrTimerCallback.PerformWaitOrTimerCallback(对象 状态,布尔超时)
我对使用套接字还很陌生(而且我只编程了几个月)所以我确定我完全错误地解决了这个问题,所以我很感激任何帮助/建议。
【问题讨论】:
这很可能与服务器连接有关。尝试 ping 它或使用 telnet 看看您是否可以访问它。很可能clientSocket
通过套接字发送请求并等待响应,但从未得到响应,因此抛出异常
服务器在所有其他测试中都运行良好,只有当我尝试以这种方式连接时才会发生这种情况。但是,服务器确实说客户端连接了 10 次,然后立即断开连接。编辑:此外,它适用于 telnet。
【参考方案1】:
由于您尚未发布完整代码,我假设您正在尝试使用全局 client
对象。在ConnectCallback
中,您需要先检索client
对象并将其类型转换为Socket
。所以在你的情况下,它会是:
private static void ConnectCallback(IAsyncResult ar)
try
// Retrieve the socket from the state object.
client = (Socket) ar.AsyncState;
//In case, you are using local client object
//Socket client = (Socket) ar.AsyncState;
// Complete the connection.
client.EndConnect(ar);
Console.WriteLine("Socket connected to 0",
client.RemoteEndPoint.ToString());
// Signal that the connection has been made.
connectDone.Set();
catch (Exception e)
Console.WriteLine(e.ToString());
以上代码取自this MSDN例子,看看吧。如果你修复了,这是你方法的第一步,它应该可以工作。
【讨论】:
以上是关于循环直到使用 BeginConnect(C# 套接字)连接到服务器的主要内容,如果未能解决你的问题,请参考以下文章
win 10 UAP/UWP(通用应用程序)的异步套接字库?
C# TcpClient的Connect超时处理(Timeout)
在 do while 循环内部,我想在 c# 中每 1 分钟执行一次特定代码,直到条件满足