X-Git-Url: https://deadsoftware.ru/gitweb?a=blobdiff_plain;f=src%2Fgame%2Fg_net.pas;h=4e2ed9a09f94f868abff12ccccba327c435a3b6d;hb=510ce208a83791aca610ab38198a9ebbb2ad2bfe;hp=95f96739e62eea4e74a3d662097d2421261c1a50;hpb=254041134b399e948e554ae99171174a7087ae40;p=d2df-sdl.git diff --git a/src/game/g_net.pas b/src/game/g_net.pas index 95f9673..4e2ed9a 100644 --- a/src/game/g_net.pas +++ b/src/game/g_net.pas @@ -1,4 +1,4 @@ -(* Copyright (C) DooM 2D:Forever Developers +(* Copyright (C) Doom 2D: Forever Developers * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -19,7 +19,7 @@ unit g_net; interface uses - e_log, e_msg, ENet, Classes; + e_log, e_msg, ENet, Classes, MAPDEF{$IFDEF USE_MINIUPNPC}, miniupnpc;{$ELSE};{$ENDIF} const NET_PROTOCOL_VER = 173; @@ -136,9 +136,17 @@ var NetForcePlayerUpdate: Boolean = False; NetPredictSelf: Boolean = True; - NetGotKeys: Boolean = False; + NetForwardPorts: Boolean = False; NetGotEverything: Boolean = False; + NetGotKeys: Boolean = False; + +{$IFDEF USE_MINIUPNPC} + NetPortForwarded: Word = 0; + NetPongForwarded: Boolean = False; + NetIGDControl: AnsiString; + NetIGDService: TURLStr; +{$ENDIF} NetDumpFile: TStream; @@ -181,6 +189,9 @@ procedure g_Net_DumpSendBuffer(); procedure g_Net_DumpRecvBuffer(Buf: penet_uint8; Len: LongWord); procedure g_Net_DumpEnd(); +function g_Net_ForwardPorts(ForwardPongPort: Boolean = True): Boolean; +procedure g_Net_UnforwardPorts(); + implementation uses @@ -305,6 +316,8 @@ begin NetMode := NET_NONE; + g_Net_UnforwardPorts(); + if NetDump then g_Net_DumpEnd(); end; @@ -348,6 +361,8 @@ begin NetAddr.host := IPAddr; NetAddr.port := Port; + if NetForwardPorts then g_Net_ForwardPorts(); + NetHost := enet_host_create(@NetAddr, NET_MAXCLIENTS, NET_CHANS, 0, 0); if (NetHost = nil) then @@ -414,7 +429,7 @@ begin NetMode := NET_NONE; g_Net_Cleanup; - e_WriteLog('NET: Server stopped', MSG_NOTIFY); + e_WriteLog('NET: Server stopped', TMsgType.Notify); end; @@ -582,7 +597,7 @@ begin TP.Lives := 0; TP.Kill(K_SIMPLEKILL, 0, HIT_DISCON); g_Console_Add(Format(_lc[I_PLAYER_LEAVE], [TP.Name]), True); - e_WriteLog('NET: Client ' + TP.Name + ' [' + IntToStr(ID) + '] disconnected.', MSG_NOTIFY); + e_WriteLog('NET: Client ' + TP.Name + ' [' + IntToStr(ID) + '] disconnected.', TMsgType.Notify); g_Player_Remove(TP.UID); end; @@ -636,7 +651,7 @@ begin end else begin - e_WriteLog('NET: Kicked from server: ' + IntToStr(NetEvent.data), MSG_NOTIFY); + e_WriteLog('NET: Kicked from server: ' + IntToStr(NetEvent.data), TMsgType.Notify); if (NetEvent.data <= NET_DISC_MAX) then g_Console_Add(_lc[I_NET_MSG] + _lc[I_NET_MSG_KICK] + _lc[TStrings_Locale(Cardinal(I_NET_DISC_NONE) + NetEvent.data)], True); @@ -650,7 +665,7 @@ begin g_Console_Add(_lc[I_NET_MSG] + _lc[I_NET_MSG_CLIENT_DISC]); g_Net_Cleanup; - e_WriteLog('NET: Disconnected', MSG_NOTIFY); + e_WriteLog('NET: Disconnected', TMsgType.Notify); end; procedure g_Net_Client_Send(Reliable: Boolean; Chan: Byte = NET_CHAN_GAME); @@ -789,8 +804,6 @@ begin ProcessLoading(true); - e_PollInput(); - if e_KeyPressed(IK_ESCAPE) or e_KeyPressed(IK_SPACE) then OuterLoop := False; end; @@ -954,8 +967,6 @@ begin ProcessLoading(true); - e_PollInput(); - if e_KeyPressed(IK_ESCAPE) or e_KeyPressed(IK_SPACE) then break; end; @@ -1101,6 +1112,141 @@ begin NetDumpFile := nil; end; +function g_Net_ForwardPorts(ForwardPongPort: Boolean = True): Boolean; +{$IFDEF USE_MINIUPNPC} +var + DevList: PUPNPDev; + Urls: TUPNPUrls; + Data: TIGDDatas; + LanAddr: array [0..255] of Char; + ExtAddr: array [0..40] of Char; + StrPort: AnsiString; + Err, I: Integer; +begin + Result := False; + + if NetPortForwarded = NetPort then + begin + Result := True; + exit; + end; + + conwriteln('trying to forward server ports...'); + + NetPongForwarded := False; + NetPortForwarded := 0; + + DevList := upnpDiscover(2000, nil, nil, 0, 0, Addr(Err)); + if DevList = nil then + begin + conwritefln(' upnpDiscover() failed: %d', [Err]); + exit; + end; + + I := UPNP_GetValidIGD(DevList, @Urls, @Data, Addr(LanAddr[0]), 256); + + if I = 0 then + begin + conwriteln(' could not find an IGD device on this LAN, aborting'); + FreeUPNPDevList(DevList); + FreeUPNPUrls(@Urls); + exit; + end + else if I = 1 then + conwritefln(' found IGD @ %s', [Urls.controlURL]) + else + conwritefln(' found some kind of UPNP device @ %s, maybe it''ll work', [Urls.controlURL]); + + UPNP_GetExternalIPAddress(Urls.controlURL, Addr(data.first.servicetype[1]), Addr(ExtAddr[0])); + if ExtAddr[0] <> #0 then + conwritefln(' external IP address: %s', [Addr(ExtAddr[0])]); + + StrPort := IntToStr(NetPort); + I := UPNP_AddPortMapping( + Urls.controlURL, Addr(data.first.servicetype[1]), + PChar(StrPort), PChar(StrPort), Addr(LanAddr[0]), PChar('D2DF'), + PChar('UDP'), nil, PChar('0') + ); + + if I <> 0 then + begin + conwritefln(' forwarding port %d failed: error %d', [NetPort, I]); + FreeUPNPDevList(DevList); + FreeUPNPUrls(@Urls); + exit; + end; + + if ForwardPongPort then + begin + StrPort := IntToStr(NetPort + 1); + I := UPNP_AddPortMapping( + Urls.controlURL, Addr(data.first.servicetype[1]), + PChar(StrPort), PChar(StrPort), Addr(LanAddr[0]), PChar('D2DF'), + PChar('UDP'), nil, PChar('0') + ); + + if I <> 0 then + begin + conwritefln(' forwarding port %d failed: error %d', [NetPort + 1, I]); + NetPongForwarded := False; + end + else + begin + conwritefln(' forwarded port %d successfully', [NetPort + 1]); + NetPongForwarded := True; + end; + end; + + conwritefln(' forwarded port %d successfully', [NetPort]); + NetIGDControl := AnsiString(Urls.controlURL); + NetIGDService := data.first.servicetype; + NetPortForwarded := NetPort; + + FreeUPNPDevList(DevList); + FreeUPNPUrls(@Urls); + Result := True; +end; +{$ELSE} +begin + Result := False; +end; +{$ENDIF} + +procedure g_Net_UnforwardPorts(); +{$IFDEF USE_MINIUPNPC} +var + I: Integer; + StrPort: AnsiString; +begin + if NetPortForwarded = 0 then Exit; + + conwriteln('unforwarding ports...'); + + StrPort := IntToStr(NetPortForwarded); + I := UPNP_DeletePortMapping( + PChar(NetIGDControl), Addr(NetIGDService[1]), + PChar(StrPort), PChar('UDP'), nil + ); + conwritefln(' port %d: %d', [NetPortForwarded, I]); + + if NetPongForwarded then + begin + NetPongForwarded := False; + StrPort := IntToStr(NetPortForwarded + 1); + I := UPNP_DeletePortMapping( + PChar(NetIGDControl), Addr(NetIGDService[1]), + PChar(StrPort), PChar('UDP'), nil + ); + conwritefln(' port %d: %d', [NetPortForwarded + 1, I]); + end; + + NetPortForwarded := 0; +end; +{$ELSE} +begin +end; +{$ENDIF} + initialization NetIn.Alloc(NET_BUFSIZE);