diff --git a/dpnet/netserver.py b/dpnet/netserver.py index 4c588a7..064d51c 100644 --- a/dpnet/netserver.py +++ b/dpnet/netserver.py @@ -77,7 +77,7 @@ class Netserver: er.ApplicationReservedData += b'\x00\x04\x00' er.ApplicationReservedData += b'\xd9\x05' # game version er.ApplicationReservedData += b'\x02\x92\x05\x00\x01\x00\x00\x00\x00\x00' # Unknown - er.ApplicationReservedData += b'\x9c\x53\xf4\xdd' # Seems to be a checksum of current map + er.ApplicationReservedData += b'\x9c\x53\xf4\xde' # Seems to be a checksum of current map # \x00\x00\x00\x00: [None] # \x00\x00\x00\x01: # \x9c\x53\xf4\xdd: Three Way Island - Canyons @@ -148,7 +148,7 @@ class Netserver: session.send_cframe_sack() sack_sent = True - if not session.CFRAME_NRcv == cframe.NRecv: + if not session.next_send == cframe.NRecv: logger.error("Received CFRAME (%s) does not have same NRcv (%s). One sent packet might have been lost.", cframe.NRecv, session.CFRAME_NRcv) if not sack_sent: session.send_cframe_sack() @@ -199,6 +199,8 @@ class Netserver: # TODO: broadcast session has disconnected self.addrs.remove(session) return + if dframe.Control & DFrame.PACKET_CONTROL_KEEPALIVE_OR_CORRELATE: + session.send_dframe_keepalive() session.next_expected_seq += 1 if dframe.Payload: @@ -281,17 +283,34 @@ class Netserver: payload.write(b'\x01\x01\x00') #payload.write(b'\x00\x04\x00') payload.write(b'\xd9\x05') # game version - payload.write(b'\x02\x92\x05\x00\x01\x00\x00\x00\x00\x00') # Unknown - payload.write(b'\x9c\x53\xf4\xde') # Seems to be a checksum of current map + payload.write(b'\x02\x92') # unknown + payload.write(b'\x05\x00\x01\x00\x00\x00\x00\x00') # Unknown + payload.write(b'\x9c\x53\xf4\xdf') # Seems to be a checksum of current map OR linked to the number of chars in the map name payload.write(self.server.currentmap.mapname.encode("ascii")) - payload.putLong(0x00) # ?? + payload.write(b'\x00' * (32 - len(self.server.currentmap.mapname))) + #payload.putLong(0x00) # ?? payload.write((self.server.name + "\x00").encode("utf-16-le")) r.Payload = payload.getvalue() session.send(r) - if payload[0] == 0xc3: - self.server.broadcast_message(name + " is a dick.") + elif payload[0] == 0xc3: + player = self.get_player(session) + self.server.broadcast_message("%s: you should never have joined... Sorry bro." % player.name) + player.session.send_gamedata(b'\x3c\x56\xab\x31\x96\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') + player.session.send_gamedata(b'\x01\x02\x57\xab\xa1\x96\x56\xab\x31\x96\x0e\x01\x00\x00\x00') + player.session.send_gamedata(b'\x3d\x00\x5b\x53\x65\x72\x76\x65\x72\x5d') # [SERVER] + player.session.send_gamedata(b'\x3d\x01'+player.name.encode("ascii")+b"\x00") # playername + player.session.send_gamedata(b'\x0f\x56\xab\x31\x96\x06\x00\x00\x00\x00\x00\x00\x00\x00') # unknown + player.session.send_gamedata(b'\x10\x02\x56\xab\x31\x96\x00\x00\x00\x00\x00\x00\x00\x00') # unknown + player.session.send_gamedata(b'\x29\x28\x00\x00\x80\x32\x00\x00\x80\x05\x00\x00\x80\x00\x00\x00\x00\x00\x00\x00\x00\x00') # unknown + player.session.send_gamedata(b'\x39\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') # unknown + player.session.send_gamedata(b'\x39\x01\x02\x01\x02\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00') # unknown + player.session.send_gamedata(b'\x0f\x56\xab\x31\x96\x07\x00\x00\x00\x00\x00\x00\x00\x00') # unknown + + player.session.send_gamedata(b'\x0a\x12\x00\x00\x00\x00\x28\x10\x03\x10\x12\x00\x00\x00\xc1\xff\x41\xff\x00', acknow=True) # unknown + player.session.send_gamedata(b'\x0f\x56\xab\x31\x96\x08\x00\x00\x00\x00\x00\x00\x00\x00', acknow=True) # unknown + def send_packet(self, addr, packet): @@ -303,3 +322,11 @@ class Netserver: return next((x for x in self.addrs if x.ip == iporaddr[0] and x.port == iporaddr[1]), None) else: return next((x for x in self.addrs if x.ip == iporaddr and x.port == port), None) + + def get_player(self, iporaddr, port=None): + if type(iporaddr) == Session: + return next((x for x in self.server.players if x.session.ip == iporaddr.ip and x.session.port == iporaddr.port), None) + if not port: + return next((x for x in self.server.players if x.session.ip == iporaddr[0] and x.session.port == iporaddr[1]), None) + else: + return next((x for x in self.server.players if x.session.ip == iporaddr and x.session.port == port), None) \ No newline at end of file diff --git a/dpnet/session.py b/dpnet/session.py index af50e50..8fadc8c 100644 --- a/dpnet/session.py +++ b/dpnet/session.py @@ -49,9 +49,12 @@ class Session: self.send(response) self.connect_retry_timer = self.setup_Connect_Retry_Timer() - def send_gamedata(self, bPayload): + def send_gamedata(self, bPayload, **kwargs): + acknow = kwargs.get("acknow", False) dframe = DFrame() - dframe.Command = DFrame.PACKET_COMMAND_DATA | DFrame.PACKET_COMMAND_POLL | DFrame.PACKET_COMMAND_RELIABLE | DFrame.PACKET_COMMAND_SEQUENTIAL | DFrame.PACKET_COMMAND_NEW_MSG | DFrame.PACKET_COMMAND_END_MSG + dframe.Command = DFrame.PACKET_COMMAND_DATA | DFrame.PACKET_COMMAND_RELIABLE | DFrame.PACKET_COMMAND_SEQUENTIAL | DFrame.PACKET_COMMAND_NEW_MSG | DFrame.PACKET_COMMAND_END_MSG + if acknow: + dframe.Command = dframe.Command | DFrame.PACKET_COMMAND_POLL dframe.Control = 0x00 dframe.Seq = self.next_send dframe.NRcv = self.next_expected_seq diff --git a/server.py b/server.py index 9d9b052..2da8dcd 100644 --- a/server.py +++ b/server.py @@ -49,7 +49,7 @@ class Server: if __name__ == '__main__': - server = Server(name="giantsd", map=Map("MvMvMvM - Infinity7 - 4Teams"), maxplayers=10) + server = Server(name="giantsd", map=Map("expect crashes"), maxplayers=10) @server.on_new_player def new_player(player):