【问题标题】:Connecting to a Source game server in VB.NET连接到 VB.NET 中的源游戏服务器
【发布时间】:2010-12-14 20:53:04
【问题描述】:

我正在开发一个应用程序来检测在 LAN 上运行的基于源的游戏。跟进specifications provided by Valve,我将其缩小到我想要的范围:在端口 27015 上建立 UDP 连接,发送A2S_INFO 查询(0xFFFFFFFF 后跟“TSource 引擎查询”​​)并解析二进制回复。

这是我正在使用的代码:

Dim sIP As String = "192.168.0.154"
Dim nPort As Integer = 27015

Dim connectionMessage As String = "ÿÿÿÿTSource Engine Query" & Chr(0)

Dim endPoint As New IPEndPoint(IPAddress.Parse(sIP), nPort)

Dim client As Socket = New Socket(AddressFamily.InterNetwork, SocketType.Dgram, ProtocolType.Udp)
client.SetSocketOption(SocketOptionLevel.Socket, SocketOptionName.ReceiveTimeout, 6000)
client.SendTo(Encoding.ASCII.GetBytes(connectionMessage), endPoint)
Console.WriteLine("Message sent to " & sIP & ":" & nPort & vbCrLf & connectionMessage)
Dim sBuffer(1400) As Byte
Try
    client.ReceiveFrom(sBuffer, endPoint)
    MsgBox(System.Text.Encoding.Unicode.GetString(sBuffer))
Catch ex As SocketException
    MsgBox("Failed to receive response on " & sIP & ":" & nPort & ":" & vbCrLf & ex.Message)
End Try

我不断收到SocketError.TimedOut 异常,通知我:

未能在 192.168.0.154:27015 上接收响应: 连接尝试失败,因为连接方在一段时间后没有正确响应,或者连接失败,因为连接的主机没有响应

我相当肯定这非常接近答案,因为以下非常简单的 PHP 版本就像一个魅力:

$ip = "192.168.0.154";
$port = 27015;

$fp = fsockopen("udp://".$ip,$port, $errno, $errstr);
socket_set_timeout($fp, 6);

$prefix = "\xff\xff\xff\xff";
$command = "TSource Engine Query";
$msg = "$prefix$command";
fputs($fp, $msg, strlen($msg));

$response = "";
do {
    $response .= fgets($fp, 16);
    $status = socket_get_status($fp);
} while ($status['unread_bytes']);
fclose ($fp);

echo $response;

这为我提供了符合规范的回复。

我很接近,但我的 VB.NET 代码有问题。我做错了什么?

解决方案

编码类型对于传输二进制数据无效。我替换了以下内容:

Encoding.ASCII.GetBytes(connectionMessage)

与:

System.Text.Encoding.[Default].GetBytes(connectionMessage)

而且很快就解决了。

“pub”建议的更强大的解决方案可能是指定代码页(虽然我还没有测试过):

Encoding.GetEncoding("iso-8859-1").GetBytes(connectionMessage)

【问题讨论】:

    标签: php vb.net sockets udp


    【解决方案1】:

    对于世界各地没有在计算机上将 iso-8859-1 代码页设置为默认值的情侣,请使用:

    Encoding.GetEncoding("iso-8859-1").GetBytes(connectionMessage)

    【讨论】:

      【解决方案2】:

      您看过 CodeProject 上的这篇 Multi-Threaded Game Server Browser in VB.Net 文章了吗?如果您不想重复使用已经编写的代码,我相信您可以查看他们是如何做到的,看看您是否能找到您的问题。

      希望有帮助,和平。

      【讨论】:

      • 我找到并尝试了 Gameserver 查询库(在 C# 中,codeproject.com/KB/game/gameserverinfo.aspx),但不是这个。我试试看,谢谢!
      • 果然,他们的版本有效。我将拼凑代码中的问题并使用解决方案更新 OP。
      【解决方案3】:

      【讨论】:

      • 感谢您的建议。我立即尝试了一下,但我得到了完全相同的东西。查询已发送,但响应只是在 udpClient.Client.ReceiveTimeout 之后超时。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2017-07-11
      • 1970-01-01
      • 2016-07-08
      • 2017-06-13
      • 2017-06-20
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多