我有一个TCP客户端/服务器应用程序通过ActiveSync连接与Windows CE设备通信。客户端和服务器都使用异步套接字(即Socket.Begin*
和Socket.End*
函数)。当客户端和服务器都在我的桌面上运行时,一切都按照预期运行,但是当客户端在通过ActiveSync连接的Windows CE设备上运行时,我总是在调用Socket.Shutdown
后在ReceiveCallback上获得SocketException
(当设备启动断开连接时)。完整的例外是:
System.Net.Sockets.SocketException: An error message cannot be displayed because an optional resource assembly containing it cannot be found
at System.Net.Sockets.Socket.ReceiveNoCheck()
at ReceiveAsyncRequest.doRequest()
at AsyncRequest.handleRequest()
at WorkerThread.doWork()
at WorkerThread.doWorkI()
at WorkItem.doWork()
at System.Threading.Timer.ring()
如果服务器(在桌面上运行)启动断开连接,一切似乎也正常工作。我有一些关于如何避免这种情况的想法,包括不允许设备启动断开连接,并在启动断开连接后忽略所有异常。但是,我想知道为什么会发生这种情况,是否有更好的处理方法。
Disconnect和ReceiveCallbacks(在服务器和客户端上操作相同)是:
public bool Disconnect(StateObject state)
{
try{
if(state.isDisconnecting) return false;
state.isDisconnecting = true;
state.sock.Shutdown(SocketShutdown.Both);
//Wait for sending and receiving to complete, but don't wait more than 10 seconds
for(int i=0; i<100 && (state.isSending || state.isReceiving); i++){
System.Threading.Thread.Sleep(100);
}
/* Log the disconnect */
state.sock.Close();
return true;
} catch (Exception e){
/* Log the exception */
return false;
}
}
private void ReceiveCallback(IAsyncResult iar)
{
StateObject state = (StateObject)iar.AsyncState;
try{
//handle the new bytes in the buffer.
int recv = state.sock.EndReceive(iar);
//Handle the buffer, storing it somewhere and verifying complete messages.
if(recv > 0){
//start listening for the next message
state.sock.BeginReceive(state.recvBuffer, 0, StateObject.BUFFER_SIZE, SocketFlags.None, new AsyncCallback(ReceiveCallback), state);
} else {
state.isReceiving = false;
Disconnect(state);
}
} catch (Exception e){
/* Log the exception */
}
}
//For reference, A StateObject looks kinda like this:
public class StateObject
{
public const int BUFFER_SIZE = 1024;
public Socket sock = null;
public bool isSending = false;
public bool isReceiving = false;
public bool isDisconnecting = false;
public byte[] recvBuffer = new byte[BUFFER_SIZE];
public byte[] sendBuffer = new byte[BUFFER_SIZE];
//Other stuff that helps handle the buffers and ensure complete messages,
// even when TCP breaks up packets.
}
为了得到实际的异常,也许试着找出它需要哪个库并部署它?
如果消息不能在您的设备上显示,因为该消息没有安装在您的设备上。您必须安装netcf.messages.cab。你可以在这里找到它:
C:Program Files (x86)Microsoft.NETSDKCompactFrameworkv3.5WindowsCEDiagnostics
安装此CAB-File后,再次运行您的应用程序并发布您得到的新错误。