首页 文章

在.NET中指定UDP多播应该使用的网络接口

提问于
浏览
10

在具有活动无线卡和LAN端口的计算机上,交叉电缆连接到运行相同应用程序的另一台计算机,我们需要通过LAN线路将UDP多播发送到另一台计算机 . 使用C#套接字,Windows似乎每次尝试通过WLAN适配器路由消息 .

有没有办法指定发送UDP多播的网络接口?

3 回答

  • 5

    你可能正在寻找 SocketOptionName.MulticastInterface . Here是一篇关于MSDN的文章可能对你有所帮助 .

    除此之外,如果您更新本地路由表以获得与多播地址匹配的精确条目并指向正确的接口,那么它应该正常工作 .

  • 15

    就像尼古拉的补遗一样:KB318911的问题是一个肮脏的技巧,用户必须提供必要的适配器索引 . 在查看如何检索此适配器索引时,我想出了这样的配方:

    NetworkInterface[] nics = NetworkInterface.GetAllNetworkInterfaces();
    foreach (NetworkInterface adapter in nics)
    {
      IPInterfaceProperties ip_properties = adapter.GetIPProperties();
      if (!adapter.GetIPProperties().MulticastAddresses.Any())
        continue; // most of VPN adapters will be skipped
      if (!adapter.SupportsMulticast)
        continue; // multicast is meaningless for this type of connection
      if (OperationalStatus.Up != adapter.OperationalStatus)
        continue; // this adapter is off or not connected
      IPv4InterfaceProperties p = adapter.GetIPProperties().GetIPv4Properties();
      if (null == p)
        continue; // IPv4 is not configured on this adapter
    
      // now we have adapter index as p.Index, let put it to socket option
      my_sock.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.MulticastInterface, (int)IPAddress.HostToNetworkOrder(p.Index));
    }
    

    全文请注意http://windowsasusual.blogspot.ru/2013/01/socket-option-multicast-interface.html

  • 2

    根据您正在做的事情,有一个可能有用的Win32方法 . 它将返回给定IP地址的最佳接口 . 要获得默认值(0.0.0.0),这通常是您想要的多播,它非常简单:

    P / Invoke签名:

    [DllImport("iphlpapi.dll", CharSet = CharSet.Auto)]
    private static extern int GetBestInterface(UInt32 DestAddr, out UInt32 BestIfIndex);
    

    然后在其他地方:

    // There could be multiple adapters, get the default one
    uint index = 0;
    GetBestInterface(0, out index);
    var ifaceIndex = (int)index;
    
    var client = new UdpClient();
    client.Client.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.MulticastInterface, (int)IPAddress.HostToNetworkOrder(ifaceIndex));
    
    var localEndpoint = new IPEndPoint(IPAddress.Any, <port>);
    client.Client.Bind(localEndpoint);
    
    var multicastAddress = IPAddress.Parse("<group IP>");
    var multOpt = new MulticastOption(multicastAddress, ifaceIndex);
    client.Client.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.AddMembership, multOpt);
    
    var broadcastEndpoint = new IPEndPoint(IPAddress.Parse("<group IP>"), <port>);
    byte[] buffer = ...
    await client.SendAsync(buffer, buffer.Length, broadcastEp).ConfigureAwait(false);
    

相关问题