通过套接字实现最简单的广告/监听安排

本文关键字:监听 套接字 实现 最简单 | 更新日期: 2023-09-27 18:08:56

下面这个简单的安排有什么问题?我所做的就是创建一个UDP广播器,它播报一条消息,以及一个侦听器,它加入多播组来接收这条消息,两者都运行在同一台机器上。

string Port = "54153";
HostName Host = new HostName("224.3.0.5"); //a multicast range address
//listener
var L = new DatagramSocket();
L.MessageReceived += (sender2, args) => { /*something*/ };
await L.BindServiceNameAsync(Port);
L.JoinMulticastGroup(Host);
//advertiser
var AdvertiserSocket = new DatagramSocket();
AdvertiserSocket.Control.MulticastOnly = true;
Stream outStream = (await AdvertiserSocket.GetOutputStreamAsync(Host, Port)).AsStreamForWrite();
using (var writer = new StreamWriter(outStream))
{
  await writer.WriteLineAsync("MESSAGE");
  await writer.FlushAsync();
}

侦听器根本没有接收到任何内容(MessageReceived从未被调用)。我尝试了以下的变化,但没有成功:

  1. 在广告端调用和不调用BindServiceNameAsync()。
  2. 在广告人、听众或两者上使用MulticastOnly
  3. 在创建一个对象之前等待几秒钟。
  4. 使用255.255.255.255作为主机

通过套接字实现最简单的广告/监听安排

看起来广告人正在正确地播报数据(TCPView显示发送的数据包),但是接收端口没有得到任何东西。

谢谢你分享这个问题。我做了一个演示并做了一些测试。我发现侦听器套接字不会接收任何消息,直到它在组中发送了一条消息。

所以,目前的解决方法是在注册后立即发送一个空消息:

private async void btnListen_Click(object sender, RoutedEventArgs e)
{
        socket = new DatagramSocket();
        socket.MessageReceived += Socket_MessageReceived;
        socket.Control.MulticastOnly = true;
        await socket.BindServiceNameAsync(serverPort);
        socket.JoinMulticastGroup(serverHost);
        SendWithExistingSocket(socket, "");//send an empty message immediately
}
private async void SendWithExistingSocket(DatagramSocket socket, String text)
{
    if (socket != null)
    {
        Stream stream = (await socket.GetOutputStreamAsync(serverHost, serverPort)).AsStreamForWrite();
        using (var writer = new StreamWriter(stream))
        {
            writer.WriteLine(text);
            await writer.FlushAsync();
        }
    }
}

关于这个问题的根本原因,我将与相关团队协商,得到答复后立即通知您。