#define HEADER_SIZE sizeof(netint2[2])
#define HEADER_SIZE3 sizeof(netint4[3])
-static MyEventType NetGenFunc(EventGenRec *gen, MyEvent *event);
+ExtFunc MyEventType NetGenFunc(EventGenRec *gen, MyEvent *event);
-static int sock = -1;
-static EventGenRec netGen = { NULL, 0, FT_read, -1, NetGenFunc, EM_net };
+EventGenRec netGen[MAX_SCREENS] = {
+ { NULL, 0, FT_read, -1, NetGenFunc, EM_net, 0, "\0", 0, HEADER_SIZE3 } };
-static char netBuf[64];
-static int netBufSize, netBufGoal = HEADER_SIZE3;
-static int isServer, lostConn, gotEndConn;
+//static char netBuf[64];
+//static int netBufSize, netBufGoal = HEADER_SIZE3;
-ExtFunc void InitNet(void)
+ExtFunc void make_netGen(void)
{
- AtExit(CloseNet);
-}
+ int i;
-ExtFunc int WaitForConnection(char *portStr)
-{
- struct sockaddr_in addr;
- struct hostent *host;
- int sockListen;
- int addrLen;
- short port;
- int val1;
- struct linger val2;
+ for (i = 1; i <= MAX_SCREENS; i++)
+ memcpy(netGen+i, &netGen[0], sizeof(EventGenRec));
+} //Make_netGen
- if (portStr)
- port = atoi(portStr); /* XXX Error checking */
- else
- port = DEFAULT_PORT;
- memset(&addr, 0, sizeof(addr));
- addr.sin_family = AF_INET;
- addr.sin_addr.s_addr = htonl(INADDR_ANY);
- addr.sin_port = htons(port);
- sockListen = socket(AF_INET, SOCK_STREAM, 0);
- if (sockListen < 0)
- die("socket");
- val1 = 1;
- setsockopt(sockListen, SOL_SOCKET, SO_REUSEADDR,
- (void *)&val1, sizeof(val1));
- if (bind(sockListen, (struct sockaddr *)&addr, sizeof(addr)) < 0)
- die("bind");
- if (listen(sockListen, 1) < 0)
- die("listen");
-
- // while(1) {
- addrLen = sizeof(addr);
- if ((sock = accept(sockListen, (struct sockaddr *)&addr, &addrLen)) < 0)
- die("accept");
- fprintf(stderr, "Connection: %s\n", inet_ntoa(addr.sin_addr));
- // if (!fork()) {
- close(sockListen);
- val2.l_onoff = 1;
- val2.l_linger = 0;
- setsockopt(sock, SOL_SOCKET, SO_LINGER,
- (void *)&val2, sizeof(val2));
- netGen.fd = sock;
- strcpy(opponentHost, "???");
- if (addr.sin_family == AF_INET) {
- host = gethostbyaddr((void *)&addr.sin_addr,
- sizeof(struct in_addr), AF_INET);
- if (host) {
- strncpy(opponentHost, host->h_name, sizeof(opponentHost)-1);
- opponentHost[sizeof(opponentHost)-1] = 0;
- }
- }
- AddEventGen(&netGen);
-// close(sock);
- // exit(0);
- // }
-// close(sock);
- // }
- isServer = 1;
- return 0;
-}
ExtFunc int InitiateConnection(char *hostStr, char *portStr)
-{
+{ //connect to host
struct sockaddr_in addr;
struct hostent *host;
short port;
- int mySock;
+// make_netGen();
+ AtExit(CloseNet);
if (portStr)
port = atoi(portStr); /* XXX Error checking */
else
if (!host)
die("gethostbyname");
assert(host->h_addrtype == AF_INET);
- strncpy(opponentHost, host->h_name, sizeof(opponentHost)-1);
- opponentHost[sizeof(opponentHost)-1] = 0;
again:
memset(&addr, 0, sizeof(addr));
addr.sin_family = host->h_addrtype;
memcpy(&addr.sin_addr, host->h_addr, host->h_length);
addr.sin_port = htons(port);
- mySock = socket(AF_INET, SOCK_STREAM, 0);
- if (mySock < 0)
+ if ((netGen[0].fd = socket(AF_INET, SOCK_STREAM, 0)) < 0)
die("socket");
- if (connect(mySock, (struct sockaddr *)&addr, sizeof(addr)) < 0) {
+ if (connect(netGen[0].fd, (struct sockaddr *)&addr, sizeof(addr)) < 0) {
if (errno != ECONNREFUSED)
die("connect");
- close(mySock);
+ close(netGen[0].fd);
sleep(1);
goto again;
}
- netGen.fd = sock = mySock;
- AddEventGen(&netGen);
+ AddEventGen(&netGen[0]);
+ totalPlayers = 0;
return 0;
+} //InitiateConnection
+
+ExtFunc void HandShake(void)
+{ //talk to your host
+ MyEvent event;
+
+ {
+ netint4 versiondata[2];
+ versiondata[0] = hton4(MAJOR_VERSION);
+ versiondata[1] = hton4(PROTOCOL_VERSION);
+ SendPacket(0, NP_hello, sizeof(versiondata), versiondata);
+ }
+
+ do {
+ if (WaitMyEvent(&event, EM_net) == E_net)
+ switch (event.u.net.type) {
+ case NP_hello:
+ {
+ me = event.u.net.uid;
+ memcpy(&Players[me], &Players[0], sizeof(Player));
+ fprintf(stderr, "Accepted (%s) as #%d (%s)\n",
+ event.u.net.data, me, Players[me].name);
+ SendPacket(0, NP_newPlayer,
+ sizeof(Player) - sizeof(Players[me].host) - sizeof(Players[me].spy),
+ &Players[me]);
+ break;
+ }
+ case NP_gamedata:
+ {
+ fprintf(stderr, ": %d\n", event.type);
+ break;
+ }
+ case NP_newPlayer:
+ {
+ totalPlayers++;
+ memcpy(&Players[event.u.net.uid],
+ event.u.net.data, event.u.net.size);
+ fprintf(stderr, "Receiving player #%d (%s)\n",
+ event.u.net.uid, Players[event.u.net.uid].name);
+ break;
+ }
+ case NP_error:
+ {
+ fprintf(stderr, "Rejected by server: %s\n", event.u.net.data);
+ exit(1);
+ }
+ default:
+ break;
+ }
+ else
+ fatal("Hm, the party apparantly ended prematurely.");
+ }
+ while (event.u.net.type != NP_goAhead);
+
+ // send Players[0]
+ // receive seed, initspeed
+ // receive #players
+ // receive Players[*]
+
+ /*
+ {
+ netint4 data[3];
+ int len;
+ int seed;
+
+ if (protocolVersion >= 3)
+ len = sizeof(data);
+ else
+ len = sizeof(netint4[2]);
+ if ((Players[0].flags & SCF_setSeed))
+ seed = Game.seed;
+ else
+ seed = time(0);
+ if (waitConn)
+ SRandom(seed);
+ data[0] = hton4(Players[0].flags);
+ data[1] = hton4(seed);
+ data[2] = hton4(Game.initspeed);
+ SendPackets(0, NP_startConn, len, data);
+ if (WaitMyEvent(&event, EM_net) != E_net ||
+ event.u.net.type != NP_startConn)
+ fatal("Network negotiation failed");
+ memcpy(data, event.u.net.data, len);
+ Players[1].flags = ntoh4(data[0]);
+ seed = ntoh4(data[1]);
+ if (initConn) {
+ if ((Players[0].flags & SCF_setSeed) != (Players[1].flags & SCF_setSeed))
+ fatal("If one player sets the random number seed, "
+ "both must.");
+ if ((Players[0].flags & SCF_setSeed) && seed != Game.seed)
+ fatal("Both players have set the random number seed, "
+ "and they are unequal.");
+ if (protocolVersion >= 3 && Game.initspeed != ntoh4(data[2]))
+ fatal("Your opponent is using a different step-down "
+ "interval (-i).\nYou must both use the same one.");
+ SRandom(seed);
+ }
+ }
+ */
+// SendPackets(0, NP_initData, strlen(Players[0].name) + 1, Players[0].name);
+
+/*
+ if (WaitMyEvent(&event, EM_net) != E_net ||
+ event.u.net.type != NP_userName)
+ fatal("Network negotiation failed");
+ strncpy(Players[1].name, event.u.net.data,
+ sizeof(Players[1].name) - 1);
+ Players[1].name[sizeof(Players[1].name)-1] = 0;
+ for (i = 0; Players[1].name[i]; ++i)
+ if (!isprint(Players[1].name[i]))
+ Players[1].name[i] = '?';
+ for (i = 0; Players[1].host[i]; ++i)
+ if (!isprint(Players[1].host[i]))
+ Players[1].host[i] = '?';
+*/
+} //HandShake
+
+ExtFunc void CheckNetConn(void)
+{ //am I necessary?
}
-static MyEventType NetGenFunc(EventGenRec *gen, MyEvent *event)
-{
+
+ExtFunc MyEventType NetGenFunc(EventGenRec *gen, MyEvent *event)
+{ //receive
int result;
short uid, type, size;
- netint4 data[3];
+ netint4 *data = (netint4*)&(gen->buf);
- result = MyRead(sock, netBuf + netBufSize, netBufGoal - netBufSize);
+ result = MyRead(gen->fd, gen->buf + gen->bufSize,
+ gen->bufGoal - gen->bufSize);
if (result < 0) {
- lostConn = 1;
+ close(gen->fd);
+ gen->fd = -1;
return E_lostConn;
}
- netBufSize += result;
- if (netBufSize < netBufGoal)
+ gen->bufSize += result;
+ if (gen->bufSize < gen->bufGoal)
return E_none;
- memcpy(data, netBuf, sizeof(data));
+ // *ugly* memcpy(data, gen->buf, sizeof(data));
uid = ntoh4(data[0]);
type = ntoh4(data[1]);
size = ntoh4(data[2]);
- netBufGoal = size;
- if (netBufSize < netBufGoal)
+ gen->bufGoal = size;
+ if (gen->bufSize < gen->bufGoal)
return E_none;
- netBufSize = 0;
- netBufGoal = HEADER_SIZE3;
+ gen->bufSize = 0;
+ gen->bufGoal = HEADER_SIZE3;
+ event->u.net.sender = gen->player;
+ event->u.net.uid = uid;
event->u.net.type = type;
event->u.net.size = size - HEADER_SIZE3;
- event->u.net.data = netBuf + HEADER_SIZE3;
+ event->u.net.data = gen->buf + HEADER_SIZE3;
if (type == NP_endConn) {
- gotEndConn = 1;
- return E_lostConn;
- }
- else if (type == NP_byeBye) {
- lostConn = 1;
+ fprintf(stderr, "Close connection\n");
return E_lostConn;
}
return E_net;
-}
-
-ExtFunc void CheckNetConn(void)
-{
-}
+} //NetGenFunc
ExtFunc void SendPacket(short uid, NetPacketType type, int size, void *data)
-{
+{ //send shit to server
netint4 header[3];
header[0] = hton4(uid);
header[1] = hton4(type);
header[2] = hton4(size + HEADER_SIZE3);
- if (MyWrite(sock, header, HEADER_SIZE3) != HEADER_SIZE3)
+ if (MyWrite(netGen[0].fd, header, HEADER_SIZE3) != HEADER_SIZE3)
+ die("write (header)");
+ if (size > 0 && data && MyWrite(netGen[0].fd, data, size) != size)
die("write");
- if (size > 0 && data && MyWrite(sock, data, size) != size)
- die("write");
-}
+} //SendPacket
ExtFunc void CloseNet(void)
-{
+{ //kick some connection's ass!
MyEvent event;
- if (sock >= 0) {
- if (!lostConn) {
- SendPacket(0, NP_endConn, 0, NULL);
- if (isServer) {
- while (!lostConn)
- WaitMyEvent(&event, EM_net);
- }
- else {
- while (!gotEndConn)
- WaitMyEvent(&event, EM_net);
- SendPacket(0, NP_byeBye, 0, NULL);
- }
- }
- close(sock);
- sock = -1;
+ if (netGen[0].fd >= 0) {
+ SendPacket(0, NP_endConn, 0, NULL);
+ close(netGen[0].fd);
+ netGen[0].fd = -1;
}
- if (netGen.next)
- RemoveEventGen(&netGen);
-}
+ if (netGen[0].next)
+ RemoveEventGen(&netGen[0]);
+} //CloseNet
/*
* vi: ts=4 ai