C# 通过同一个开放套接字进行异步多向服务器-客户端通信?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/1241/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-07-31 12:11:33  来源:igfitidea点击:

Asynchronous multi-direction server-client communication over the same open socket?

提问by Adam Haile

I have a client-server app where the client is on a Windows Mobile 6 device, written in C++ and the server is on full Windows and written in C#.

我有一个客户端 - 服务器应用程序,其中客户端在 Windows Mobile 6 设备上,用 C++ 编写,服务器在完整的 Windows 上,用 C# 编写。

Originally, I only needed it to send messages from the client to the server, with the server only ever sending back an acknowledgement that it received the message. Now, I would like to update it so that the server can actually send a message to the client to request data. As I currently have it set up so the client is only in receive mode after it sends data to the server, this doesn't allow for the server to send a request at any time. I would have to wait for client data. My first thought would be to create another thread on the client with a separate open socket, listening for server requests...just like the server already has in respect the client. Is there a way, within the same thread and using the same socket, to all the server to send requests at any time?

最初,我只需要它从客户端向服务器发送消息,服务器只发回它收到消息的确认。现在,我想更新它,以便服务器可以实际向客户端发送消息以请求数据。由于我目前设置了它,因此客户端仅在向服务器发送数据后才处于接收模式,这不允许服务器随时发送请求。我将不得不等待客户数据。我的第一个想法是在客户端上创建另一个具有单独打开套接字的线程,侦听服务器请求……就像服务器已经对客户端进行了处理一样。有没有办法,在同一个线程内,使用同一个套接字,随时向所有服务器发送请求?

Can you use something to the effect of WaitForMultipleObjects()and pass it a receive buffer and an event that tells it there is data to be sent?

你能用一些东西来WaitForMultipleObjects()传递一个接收缓冲区和一个告诉它有数据要发送的事件吗?

采纳答案by sven

When I needed to write an application with a client-server model where the clients could leave and enter whenever they want, (I assume that's also the case for your application as you use mobile devices) I made sure that the clients send an onlinemessage to the server, indicating they were connected and ready to do whatever they needed doing.

当我需要使用客户端 - 服务器模型编写一个应用程序时,客户端可以随时离开和进入(我假设您的应用程序也是如此,因为您使用移动设备)我确保客户端发送在线消息到服务器,表明他们已连接并准备好做任何他们需要做的事情。

at that time the server could send messages back to the client trough the same open connection.

那时服务器可以通过相同的开放连接将消息发送回客户端。

Also, but I don't know if that is applicable for you, I had some sort of heartbeatthe clients sent to the server, letting it know it was still online. That way the server knows when a client was forcibly disconnected from the network and it could mark that client back as offline.

另外,但我不知道这是否适用于您,我将客户端发送到服务器的某种心跳,让它知道它仍然在线。这样服务器就知道客户端何时被强行与网络断开连接,并且可以将该客户端标记为离线。

回答by fastcall

I'm not clear on whether or not you're wanting to add the asynchronous bits to the server in C# or the client in C++.

我不清楚您是否想将异步位添加到 C# 中的服务器或 C++ 中的客户端。

If you're talking about doing this in C++, desktop Windows platforms can do socket I/O asynchronously through the API's that use overlapped I/O. For sockets, WSASend, WSARecv both allow async I/O (read the documentation on their LPOVERLAPPED parameters, which you can populate with events that get set when the I/O completes).

如果您正在谈论在 C++ 中执行此操作,桌面 Windows 平台可以通过使用重叠 I/O 的 API 异步执行套接字 I/O。对于套接字,WSASend、WSARecv 都允许异步 I/O(阅读有关其 LPOVERLAPPED 参数的文档,您可以使用 I/O 完成时设置的事件填充这些参数)。

I don't know if Windows Mobile platforms support these functions, so you might have to do some additional digging.

我不知道 Windows Mobile 平台是否支持这些功能,所以你可能需要做一些额外的挖掘。

回答by roo

Check out asio. It is a cross compatable c++ library for asyncronous IO. I am not sure if this would be useful for the server ( I have never tried to link a standard c++ DLL to a c# project) but for the client it would be useful.

查看asio。它是一个用于异步 IO 的交叉兼容 C++ 库。我不确定这对服务器是否有用(我从未尝试将标准的 c++ DLL 链接到 ac# 项目),但对于客户端它会很有用。

We use it with our application, and it solved most of our IO concurrency problems.

我们将它与我们的应用程序一起使用,它解决了我们的大部分 IO 并发问题。

回答by Steve Gury

Using asynchronous communication is totally possible in single thread!

在单线程中使用异步通信是完全可能的!

There is a common design pattern in network software development called the reactor pattern (look at this book). Some well known network library provides an implementation of this pattern (look at ACE).

网络软件开发中有一种常见的设计模式称为反应器模式(参阅本书)。一些著名的网络库提供了这种模式的实现(看看 ACE)。

Briefly, the reactor is an object, you register all your sockets inside, and you wait for something. If something happened (new data arrived, connection close...) the reactor will notify you. And of course, you can use only one socket to send and received data asynchronously.

简而言之,反应器是一个对象,你在里面注册所有的套接字,然后等待一些东西。如果发生了某些事情(新数据到达、连接关闭...),反应器会通知您。当然,您可以只使用一个套接字异步发送和接收数据。