User:Pizzahut/msqp.php
Jump to navigation
Jump to search
This is a code example for querying a Half-Life master server using the PHP language.
<?php
/*
Version history
1 Initial release.
2 Added option to retry same server if timeout occurs.
2.1 Added more master servers.
2.1.1 Fixed a bug, program didn't terminate if all master servers time out.
2.1.2 Removed a now redundant variable.
2.2 Seeding for long server lists.
*/
$master_servers = array("72.165.61.136", "68.142.72.250", "72.165.61.189",
"72.165.61.190", "69.28.151.162");
function query_timeout(&$socket, $seed)
{
// region=world, filter: game=Half-Life
if (!fwrite($socket, "1\xFF$seed\0\\gamedir\\valve\0"))
{
fclose($socket);
exit("fwrite error\n");
}
$s = bin2hex(fread($socket, 6));
$info = stream_get_meta_data($socket);
if ($info['timed_out'])
{
echo "Master server \"$seed\" timed out.\n";
fclose($socket);
}
else
{
if ($s !== "ffffffff660a")
{
fclose($socket);
exit("Expected ff ff ff ff 66 0a (hex) but got $s.");
}
}
return $info['timed_out'];
}
// Connect to master server, return timeout info.
// The socket is passed as reference and thus returned as well.
function master_server_timeout(&$socket, $ip)
{
$port = 27010;
$timeout = 1;
echo "Connecting to master server \"$ip\".\n";
$socket = fsockopen("udp://$ip", $port, $errno, $errstr, $timeout);
if (!$socket)
exit("Error $errno : $errstr \n");
stream_set_timeout($socket, $timeout);
return query_timeout($socket, "0.0.0.0:0");
}
// Try all master servers unless we find one that isn't timing out.
$abort = 1;
foreach ($master_servers as $ip)
{
if (!master_server_timeout($socket, $ip))
{
$abort = 0;
break;
}
}
if ($abort == 1)
exit("All master servers timed out, aborting.\n");
// Read list with server addresses (IP:port).
$count = 0;
do
{
$new_a1 = ord(fread($socket,1));
$info = stream_get_meta_data($socket);
if ($info['timed_out'])
{
if (query_timeout($socket, "$a1.$a2.$a3.$a4:$a5"))
break;
$a1 = ord(fread($socket,1));
$info = stream_get_meta_data($socket);
if ($info['timed_out'])
{
echo "Timeout occured.\n";
break;
}
echo "New seed, decreasing count.\n";
$count--;
}
else
$a1 = $new_a1;
if ($a1 != 0)
{
$a2 = ord(fread($socket,1));
$a3 = ord(fread($socket,1));
$a4 = ord(fread($socket,1));
$a5 = ord(fread($socket,1))*256 + ord(fread($socket,1));
$count++;
echo "$count $a1.$a2.$a3.$a4:$a5\n";
}
} while ($a1 != 0);
fclose($socket);
echo "Retrieved $count server addresses.\n";
?>