用户数据报协议 (UDP,User Datagram Protocol) 是一种简单协议,非常适合用于将数据传递到远程主机。由于 UDP 协议是一种无连接协议,因此发送到远程主机的 UDP 数据不一定能到达,也无法保证能以相同顺序到达。使用 UDP 的应用程序必须做好处理丢失、重复和乱序的数据报的准备。
using System;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading;
namespace SyncServer
{
public class Program
{
static void Main(string[] args)
{
Thread thread = new Thread(new ThreadStart(BroadcastIPAddress));
thread.IsBackground = true;
thread.Name = "#BroadcastIPAddress";
thread.Priority = ThreadPriority.Lowest;
thread.Start();
Console.WriteLine("Start Broadcast");
Console.Read();
}
private static void BroadcastIPAddress()
{
Socket s = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
try
{
IPEndPoint ip = new IPEndPoint(IPAddress.Broadcast, 12593);
string machineName = Environment.MachineName;
s.MulticastLoopback = true;
s.EnableBroadcast = true;
var broadCastMessage = Encoding.ASCII.GetBytes(string.Format("{0}:{1}:{2}", machineName, "8080", "SyncServer"));
while (true)
{
s.SendTo(broadCastMessage, ip);
Thread.Sleep(1000);
}
}
catch (Exception ex)
{
}
finally
{
s.Close();
}
}
}
}
using System;
using System.Collections.Generic;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading;
using System.Windows;
namespace Client
{
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
Loaded += MainWindow_Loaded;
}
private void MainWindow_Loaded(object sender, RoutedEventArgs e)
{
Thread thread = new Thread(new ThreadStart(RefreshServers));
thread.IsBackground = true;
thread.Name = "#RefreshPosServers";
thread.Start();
}
private void RefreshServers()
{
Socket s = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
EndPoint rip = null;
try
{
s.Bind(new IPEndPoint(IPAddress.Any, 12593));
rip = (EndPoint)(new IPEndPoint(IPAddress.Any, 0));
}
catch (Exception ex)
{
return;
}
try
{
byte[] buf = new byte[100];
int r = 0;
while (true)
{
r = s.ReceiveFrom(buf,ref rip);
var ip = ((IPEndPoint)rip).Address.ToString();
var message = Encoding.Default.GetString(buf, 0, r);
if (Dispatcher.CheckAccess())
{
ReloadData(message);
}
else
{
Dispatcher.BeginInvoke(new Action<string>(ReloadData), message);
}
Thread.Sleep(2000);
}
}
catch (Exception ex)/*Timeout exception*/
{
System.Diagnostics.Debug.Print(ex.ToString());
}
}
public void ReloadData(object message)
{
txtMessage.Text += message + "\r\n";
}
}
}
下图为演示效果: