UDP 客户端收不到任何数据
UDP Client can't receive any data
我已经开始学习 System.Net,并编写了一个简单的 UDP 客户端-服务器聊天应用程序。
为了简单起见,客户端和服务器都位于我的机器上(通过本地)。
我可以从客户端向服务器发送一条消息并将其写在那里,但在那之后,客户端也应该收到一条硬编码消息(你好!),这是我的问题。
Screenshot of application (server and client)
客户代码:
public class UDPClient
{
private Socket clientSocket;
private EndPoint epSend, epRecieve;
private byte[] dataBuffer;
private ArraySegment<byte> dataBufferSegments;
/// <summary>
/// initializing client with buffer, end points of server and client (for sending and listening)
/// </summary>
/// <param name="address"></param>
/// <param name="port">for future port-forwarding</param>
public void Initialize(IPAddress address, int port = 0)
{
dataBuffer = new byte[4096];
dataBufferSegments = new ArraySegment<byte>(dataBuffer);
epRecieve = new IPEndPoint(address, clientListenOn);
epSend = new IPEndPoint(address, serverListenOn);
Console.WriteLine(epRecieve.Serialize());
Console.WriteLine(epSend.Serialize());
clientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
clientSocket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.PacketInformation, true);
}
/// <summary>
/// async task for listening on packets
/// </summary>
public void Listen()
{
_ = Task.Run(async () =>
{
SocketReceiveMessageFromResult res;
while (true)
{
res = await clientSocket.ReceiveMessageFromAsync(dataBufferSegments, SocketFlags.None, epRecieve);
Console.WriteLine(Encoding.UTF8.GetString(dataBuffer, 0, bufferSize));
}
});
}
/// <summary>
/// async task for sending data back to server
/// </summary>
/// <param name="data"></param>
/// <returns></returns>
public async Task Send(byte[] data)
{
var s = new ArraySegment<byte>(data);
await clientSocket.SendToAsync(s, SocketFlags.None, epSend);
}
}
服务器代码:
/// <summary>
/// UDP Server
/// </summary>
public class UDPServer
{
private Socket serverSocket;
private EndPoint epRecieve, epSend;
private byte[] dataBuffer;
private ArraySegment<byte> dataBufferSegments;
public void Initialize()
{
dataBuffer = new byte[4096];
dataBufferSegments = new ArraySegment<byte>(dataBuffer);
epRecieve = new IPEndPoint(IPAddress.Loopback, serverListenOn);
Console.WriteLine(epRecieve.Serialize());
serverSocket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
serverSocket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.PacketInformation, true);
serverSocket.Bind(epRecieve);
}
public void Listen()
{
_ = Task.Run(async () =>
{
SocketReceiveMessageFromResult res;
while (true)
{
res = await serverSocket.ReceiveMessageFromAsync(dataBufferSegments, SocketFlags.None, epRecieve);
Console.WriteLine(Encoding.UTF8.GetString(dataBuffer, 0, bufferSize));
Console.WriteLine(res.RemoteEndPoint);
Console.WriteLine(res.ReceivedBytes.ConvertToString());
Console.WriteLine(res.PacketInformation.Address);
epSend = new IPEndPoint(res.PacketInformation.Address, clientListenOn);
Console.WriteLine(epSend.Serialize());
//this doesn't seem to work...
await SendTo(epSend, Encoding.UTF8.GetBytes("Hello back!"));
}
});
}
public async Task SendTo(EndPoint recipient, byte[] data)
{
var s = new ArraySegment<byte>(data);
await serverSocket.SendToAsync(s, SocketFlags.None, recipient);
}
}
服务器主代码:
static void Main(string[] args)
{
Network.UDPServer server = new Network.UDPServer();
server.Initialize();
server.Listen();
Console.ReadLine();
}
客户端主要代码:
static async Task Main(string[] args)
{
Network.UDPClient client = new Network.UDPClient();
IPAddress ip = IPAddress.Loopback;
Console.WriteLine(ip.ToString());
client.Initialize(ip);
client.Listen();
await client.Send(Encoding.UTF8.GetBytes(Console.ReadLine()));
Console.ReadLine();
}
因此我希望任何人都能指出我的系统出了什么问题。
非常感谢!
我将您的代码粘贴到 Visual Studio 上并进行了一些小修改(缺少一些字段等),我遇到的问题如下:
在您的 UDP 客户端上,此行抛出类型为 InvalidOperationException
的异常。
System.InvalidOperationException: 'You must call the Bind method before performing this operation.'
res = await clientSocket.ReceiveMessageFromAsync(dataBufferSegments, SocketFlags.None, epRecieve);
您需要将套接字绑定到本地端点,特别是您的接收端点。这样做是为了将该套接字与该特定端点相关联并从中接收数据。
public void Initialize(IPAddress address, int port = 0)
{
dataBuffer = new byte[4096];
dataBufferSegments = new ArraySegment<byte>(dataBuffer);
epRecieve = new IPEndPoint(address, clientListenOn);
epSend = new IPEndPoint(address, serverListenOn);
Console.WriteLine(epRecieve.Serialize());
Console.WriteLine(epSend.Serialize());
clientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
clientSocket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.PacketInformation, true);
_clientSocket.Bind(_epRecieve);
}
您可以在这里阅读更多内容:
MSDN - Socket.Bind(EndPoint) Method
我已经开始学习 System.Net,并编写了一个简单的 UDP 客户端-服务器聊天应用程序。
为了简单起见,客户端和服务器都位于我的机器上(通过本地)。
我可以从客户端向服务器发送一条消息并将其写在那里,但在那之后,客户端也应该收到一条硬编码消息(你好!),这是我的问题。
Screenshot of application (server and client)
客户代码:
public class UDPClient
{
private Socket clientSocket;
private EndPoint epSend, epRecieve;
private byte[] dataBuffer;
private ArraySegment<byte> dataBufferSegments;
/// <summary>
/// initializing client with buffer, end points of server and client (for sending and listening)
/// </summary>
/// <param name="address"></param>
/// <param name="port">for future port-forwarding</param>
public void Initialize(IPAddress address, int port = 0)
{
dataBuffer = new byte[4096];
dataBufferSegments = new ArraySegment<byte>(dataBuffer);
epRecieve = new IPEndPoint(address, clientListenOn);
epSend = new IPEndPoint(address, serverListenOn);
Console.WriteLine(epRecieve.Serialize());
Console.WriteLine(epSend.Serialize());
clientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
clientSocket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.PacketInformation, true);
}
/// <summary>
/// async task for listening on packets
/// </summary>
public void Listen()
{
_ = Task.Run(async () =>
{
SocketReceiveMessageFromResult res;
while (true)
{
res = await clientSocket.ReceiveMessageFromAsync(dataBufferSegments, SocketFlags.None, epRecieve);
Console.WriteLine(Encoding.UTF8.GetString(dataBuffer, 0, bufferSize));
}
});
}
/// <summary>
/// async task for sending data back to server
/// </summary>
/// <param name="data"></param>
/// <returns></returns>
public async Task Send(byte[] data)
{
var s = new ArraySegment<byte>(data);
await clientSocket.SendToAsync(s, SocketFlags.None, epSend);
}
}
服务器代码:
/// <summary>
/// UDP Server
/// </summary>
public class UDPServer
{
private Socket serverSocket;
private EndPoint epRecieve, epSend;
private byte[] dataBuffer;
private ArraySegment<byte> dataBufferSegments;
public void Initialize()
{
dataBuffer = new byte[4096];
dataBufferSegments = new ArraySegment<byte>(dataBuffer);
epRecieve = new IPEndPoint(IPAddress.Loopback, serverListenOn);
Console.WriteLine(epRecieve.Serialize());
serverSocket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
serverSocket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.PacketInformation, true);
serverSocket.Bind(epRecieve);
}
public void Listen()
{
_ = Task.Run(async () =>
{
SocketReceiveMessageFromResult res;
while (true)
{
res = await serverSocket.ReceiveMessageFromAsync(dataBufferSegments, SocketFlags.None, epRecieve);
Console.WriteLine(Encoding.UTF8.GetString(dataBuffer, 0, bufferSize));
Console.WriteLine(res.RemoteEndPoint);
Console.WriteLine(res.ReceivedBytes.ConvertToString());
Console.WriteLine(res.PacketInformation.Address);
epSend = new IPEndPoint(res.PacketInformation.Address, clientListenOn);
Console.WriteLine(epSend.Serialize());
//this doesn't seem to work...
await SendTo(epSend, Encoding.UTF8.GetBytes("Hello back!"));
}
});
}
public async Task SendTo(EndPoint recipient, byte[] data)
{
var s = new ArraySegment<byte>(data);
await serverSocket.SendToAsync(s, SocketFlags.None, recipient);
}
}
服务器主代码:
static void Main(string[] args)
{
Network.UDPServer server = new Network.UDPServer();
server.Initialize();
server.Listen();
Console.ReadLine();
}
客户端主要代码:
static async Task Main(string[] args)
{
Network.UDPClient client = new Network.UDPClient();
IPAddress ip = IPAddress.Loopback;
Console.WriteLine(ip.ToString());
client.Initialize(ip);
client.Listen();
await client.Send(Encoding.UTF8.GetBytes(Console.ReadLine()));
Console.ReadLine();
}
因此我希望任何人都能指出我的系统出了什么问题。
非常感谢!
我将您的代码粘贴到 Visual Studio 上并进行了一些小修改(缺少一些字段等),我遇到的问题如下:
在您的 UDP 客户端上,此行抛出类型为 InvalidOperationException
的异常。
System.InvalidOperationException: 'You must call the Bind method before performing this operation.'
res = await clientSocket.ReceiveMessageFromAsync(dataBufferSegments, SocketFlags.None, epRecieve);
您需要将套接字绑定到本地端点,特别是您的接收端点。这样做是为了将该套接字与该特定端点相关联并从中接收数据。
public void Initialize(IPAddress address, int port = 0)
{
dataBuffer = new byte[4096];
dataBufferSegments = new ArraySegment<byte>(dataBuffer);
epRecieve = new IPEndPoint(address, clientListenOn);
epSend = new IPEndPoint(address, serverListenOn);
Console.WriteLine(epRecieve.Serialize());
Console.WriteLine(epSend.Serialize());
clientSocket = new Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp);
clientSocket.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.PacketInformation, true);
_clientSocket.Bind(_epRecieve);
}
您可以在这里阅读更多内容: MSDN - Socket.Bind(EndPoint) Method