mirror of
https://git.code.sf.net/p/quake/quakeforge
synced 2025-02-28 22:41:50 +00:00
at rxr's request, allow the master server to read in a static list of
servers (qw-master -f servers.txt). These servers can not be removed from the master server without editing the file and restarting the server. The format of the server list file is a simple line-by-line list of the servers' addresses and their port (optional: defaults to 27500): servername([ :]port)? one per line.
This commit is contained in:
parent
b5c2c0e14e
commit
6c6b8ca4c3
1 changed files with 73 additions and 15 deletions
|
@ -49,6 +49,9 @@ static const char rcsid[] =
|
||||||
#ifdef HAVE_WINSOCK_H
|
#ifdef HAVE_WINSOCK_H
|
||||||
# include <winsock.h>
|
# include <winsock.h>
|
||||||
#endif
|
#endif
|
||||||
|
#ifdef HAVE_NETDB_H
|
||||||
|
# include <netdb.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <time.h>
|
#include <time.h>
|
||||||
|
@ -76,7 +79,7 @@ typedef struct {
|
||||||
|
|
||||||
int
|
int
|
||||||
QW_AddHeartbeat (server_t **servers_p, int slen,
|
QW_AddHeartbeat (server_t **servers_p, int slen,
|
||||||
struct sockaddr_in *addr, char *buf)
|
struct sockaddr_in *addr, char *buf, qboolean notimeout)
|
||||||
{
|
{
|
||||||
server_t *servers = *servers_p;
|
server_t *servers = *servers_p;
|
||||||
int freeslot = -1;
|
int freeslot = -1;
|
||||||
|
@ -114,14 +117,15 @@ QW_AddHeartbeat (server_t **servers_p, int slen,
|
||||||
}
|
}
|
||||||
|
|
||||||
for (i = slen; i < slen + SLIST_MULTIPLE; i++)
|
for (i = slen; i < slen + SLIST_MULTIPLE; i++)
|
||||||
newservers[i].updated = 0;
|
memset (&newservers[i], 0, sizeof (newservers[i]));
|
||||||
|
|
||||||
freeslot = slen;
|
freeslot = slen;
|
||||||
slen += SLIST_MULTIPLE;
|
slen += SLIST_MULTIPLE;
|
||||||
*servers_p = newservers;
|
*servers_p = newservers;
|
||||||
|
servers = *servers_p;
|
||||||
}
|
}
|
||||||
servers[freeslot].addr = *addr;
|
servers[freeslot].addr = *addr;
|
||||||
servers[freeslot].notimeout = false;
|
servers[freeslot].notimeout = notimeout;
|
||||||
#if 1
|
#if 1
|
||||||
printf ("Added %s:%d (seq %d, players %d)\n",
|
printf ("Added %s:%d (seq %d, players %d)\n",
|
||||||
inet_ntoa (servers[freeslot].addr.sin_addr),
|
inet_ntoa (servers[freeslot].addr.sin_addr),
|
||||||
|
@ -221,27 +225,22 @@ QW_Pong (int sock, struct sockaddr_in *addr)
|
||||||
(struct sockaddr *) addr, sizeof (struct sockaddr_in));
|
(struct sockaddr *) addr, sizeof (struct sockaddr_in));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int serverlen = SLIST_MULTIPLE;
|
||||||
|
server_t *servers;
|
||||||
|
|
||||||
void
|
void
|
||||||
QW_Master (struct sockaddr_in *addr)
|
QW_Master (struct sockaddr_in *addr)
|
||||||
{
|
{
|
||||||
int sock;
|
int sock;
|
||||||
server_t *servers;
|
|
||||||
int serverlen = SLIST_MULTIPLE;
|
|
||||||
int i;
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
WSADATA winsockdata;
|
WSADATA winsockdata;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
servers = malloc (sizeof (server_t) * serverlen);
|
|
||||||
if (!servers) {
|
if (!servers) {
|
||||||
printf ("initial malloc failed\n");
|
printf ("initial malloc failed\n");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
for (i = 0; i < serverlen; i++)
|
|
||||||
servers[i].updated = 0;
|
|
||||||
|
|
||||||
#ifdef _WIN32
|
#ifdef _WIN32
|
||||||
i = WSAStartup (MAKEWORD (1, 1), &winsockdata);
|
i = WSAStartup (MAKEWORD (1, 1), &winsockdata);
|
||||||
if (i) {
|
if (i) {
|
||||||
|
@ -305,7 +304,7 @@ QW_Master (struct sockaddr_in *addr)
|
||||||
break;
|
break;
|
||||||
case S2M_HEARTBEAT:
|
case S2M_HEARTBEAT:
|
||||||
serverlen = QW_AddHeartbeat (&servers, serverlen,
|
serverlen = QW_AddHeartbeat (&servers, serverlen,
|
||||||
&recvaddr, buf);
|
&recvaddr, buf, false);
|
||||||
break;
|
break;
|
||||||
case S2M_SHUTDOWN:
|
case S2M_SHUTDOWN:
|
||||||
QW_HeartShutdown (&recvaddr, servers, serverlen);
|
QW_HeartShutdown (&recvaddr, servers, serverlen);
|
||||||
|
@ -321,6 +320,57 @@ QW_Master (struct sockaddr_in *addr)
|
||||||
free (servers);
|
free (servers);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
make_host_addr (const char *host, int port, struct sockaddr_in *host_addr)
|
||||||
|
{
|
||||||
|
struct hostent *host_ent;
|
||||||
|
|
||||||
|
host_ent = gethostbyname (host);
|
||||||
|
if (!host_ent)
|
||||||
|
return -1;
|
||||||
|
host_addr->sin_family = AF_INET;
|
||||||
|
memcpy (&host_addr->sin_addr, host_ent->h_addr_list[0],
|
||||||
|
sizeof (host_addr->sin_addr));
|
||||||
|
host_addr->sin_port = htons (port);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static void
|
||||||
|
read_hosts (const char *fname)
|
||||||
|
{
|
||||||
|
FILE *host_file;
|
||||||
|
int host_port;
|
||||||
|
char host_name[256];
|
||||||
|
static char *fake_heartbeat = " ";
|
||||||
|
char *buf;
|
||||||
|
struct sockaddr_in host_addr;
|
||||||
|
|
||||||
|
host_file = fopen (fname, "rt");
|
||||||
|
if (!host_file) {
|
||||||
|
fprintf (stderr, "could not open `%s'\n", fname);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
while (fgets (host_name, sizeof (host_name), host_file)) {
|
||||||
|
for (buf = host_name; *buf && !isspace ((byte)*buf) && *buf !=':';
|
||||||
|
buf++)
|
||||||
|
;
|
||||||
|
if (*buf)
|
||||||
|
*buf++ = 0;
|
||||||
|
if (*buf)
|
||||||
|
host_port = atoi (buf);
|
||||||
|
else
|
||||||
|
host_port = 27500; //FIXME: magic number (default server port)
|
||||||
|
if (make_host_addr (host_name, host_port, &host_addr) == -1) {
|
||||||
|
fprintf (stderr, "could not resolve `%s', skipping", host_name);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
serverlen = QW_AddHeartbeat (&servers, serverlen, &host_addr,
|
||||||
|
fake_heartbeat, true);
|
||||||
|
}
|
||||||
|
fclose (host_file);
|
||||||
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
main (int argc, char **argv)
|
main (int argc, char **argv)
|
||||||
{
|
{
|
||||||
|
@ -328,10 +378,18 @@ main (int argc, char **argv)
|
||||||
short port = htons (27000);
|
short port = htons (27000);
|
||||||
#ifndef WIN32 //FIXME
|
#ifndef WIN32 //FIXME
|
||||||
int c;
|
int c;
|
||||||
|
#endif
|
||||||
|
|
||||||
while ((c = getopt (argc, argv, "p:")) != -1) {
|
servers = calloc (sizeof (server_t), serverlen);
|
||||||
if (c == 'p') {
|
#ifndef WIN32 //FIXME
|
||||||
|
while ((c = getopt (argc, argv, "p:f:")) != -1) {
|
||||||
|
switch (c) {
|
||||||
|
case 'p':
|
||||||
port = htons (atoi (optarg));
|
port = htons (atoi (optarg));
|
||||||
|
break;
|
||||||
|
case 'f':
|
||||||
|
read_hosts (optarg);
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
Loading…
Reference in a new issue