Ticket #3241: t3241_kick_wip_1.patch
File t3241_kick_wip_1.patch, 22.7 KB (added by , 9 years ago) |
---|
-
binaries/data/mods/public/gui/common/network.js
5 5 { 6 6 case 0: return translate("Unknown reason"); 7 7 case 1: return translate("Unexpected shutdown"); 8 8 case 2: return translate("Incorrect network protocol version"); 9 9 case 3: return translate("Game has already started"); 10 case 4: return translate("You have been kicked from the match"); 11 case 5: return translate("You have been banned from the match"); 10 12 default: return sprintf(translate("\\[Invalid value %(id)s]"), { id: id }); 11 13 } 12 14 } 13 15 14 16 function reportDisconnect(reason) -
binaries/data/mods/public/gui/gamesetup/gamesetup.js
1698 1698 1699 1699 var message = ""; 1700 1700 if ("text" in msg && msg.text) 1701 1701 message = escapeText(msg.text); 1702 1702 1703 // Kick / ban players 1704 if ("text" in msg) 1705 { 1706 var split = msg.text.split(/\s/); 1707 var kick = msg.text.indexOf("/kick") == 0; 1708 var ban = msg.text.indexOf("/ban") == 0; 1709 if (kick || ban) 1710 { 1711 if (!g_IsNetworked || !g_IsController) 1712 return; 1713 var trimmed = msg.text.substr(split[0].length + 1); 1714 var matched = ""; 1715 // Reject names which don't match or are a superset of the intended name. 1716 for each (var player in g_PlayerAssignments) 1717 if (trimmed.indexOf(player.name) == 0 && player.name.length > matched.length) 1718 matched = player.name; 1719 1720 if (matched.length && msg.guid == Engine.GetPlayerGUID()) 1721 Engine.KickPlayer(matched, ban); 1722 return; 1723 } 1724 } 1725 1703 1726 // TODO: Maybe host should have distinct font/color? 1704 1727 var color = "white"; 1705 1728 1706 1729 if (msg.guid && g_PlayerAssignments[msg.guid] && g_PlayerAssignments[msg.guid].player != -1) 1707 1730 { -
binaries/data/mods/public/gui/session/messages.js
325 325 function submitChatInput() 326 326 { 327 327 var input = Engine.GetGUIObjectByName("chatInput"); 328 328 var text = input.caption; 329 329 var isCheat = false; 330 330 331 if (text.length) 331 332 { 333 // Check cheats 332 334 if (!g_IsObserver && g_Players[Engine.GetPlayerID()].cheatsEnabled) 333 335 { 334 336 for each (var cheat in Object.keys(cheats)) 335 337 { 336 338 // Line must start with the cheat. … … 374 376 isCheat = true; 375 377 break; 376 378 } 377 379 } 378 380 379 // Observers should only send messages to "/all" 380 if (!isCheat && (!g_IsObserver || text.indexOf("/") == -1 || text.indexOf("/all ") == 0)) 381 if (!isCheat) 381 382 { 382 if (Engine.GetGUIObjectByName("toggleTeamChat").checked) 383 text = "/team " + text; 384 385 if (g_IsNetworked) 386 Engine.SendNetworkChat(text); 383 if (text.trim() == "/list") 384 addChatMessage({ "type": "clientlist", "guid": "local"}); 387 385 else 388 addChatMessage({ "type": "message", "guid": "local", "text": text }); 386 { 387 if (Engine.GetGUIObjectByName("toggleTeamChat").checked) 388 text = "/team " + text; 389 390 if (g_IsNetworked) 391 Engine.SendNetworkChat(text); 392 else 393 addChatMessage({ "type": "message", "guid": "local", "text": text }); 394 } 389 395 } 390 396 input.caption = ""; // Clear chat input 391 397 } 392 398 393 399 input.blur(); // Remove focus … … 453 459 if (!g_IsNetworked && msg.player == Engine.GetPlayerID()) 454 460 formatted = translate("You have been defeated."); 455 461 else 456 462 formatted = sprintf(translate("%(player)s has been defeated."), { player: "[color=\"" + playerColor + "\"]" + username + "[/color]" }); 457 463 break; 464 case "clientlist": 465 var userlist = Object.keys(playerAssignments).sort(function(a,b) 466 { 467 var playerA = playerAssignments[a].player; 468 var playerB = playerAssignments[b].player; 469 if (playerA == -1 || playerB == -1) 470 return 1; 471 else 472 return playerA - playerB; 473 }).map(guid => playerAssignments[guid].name).join(","); 474 formatted = sprintf(translate("Users: %(users)s."), { "users": userlist }); 475 break; 458 476 case "diplomacy": 459 477 var message; 460 478 if (msg.player == Engine.GetPlayerID()) 461 479 { 462 480 [username, playerColor] = getUsernameAndColor(msg.player1); … … 601 619 } 602 620 603 621 // Parses chat messages for commands. 604 622 function parseChatCommands(msg, playerAssignments) 605 623 { 624 var ban = false; 606 625 // Only interested in messages that start with '/'. 607 626 if (!msg.text || msg.text[0] != '/') 608 627 return; 609 628 610 629 var sender; … … 627 646 msg.hide = false; 628 647 recurse = true; 629 648 break; 630 649 case "/team": 631 650 // Check if we are in a team. 632 if ( g_Players[Engine.GetPlayerID()] && g_Players[Engine.GetPlayerID()].team != -1)651 if (!g_IsObserver && g_Players[Engine.GetPlayerID()] && g_Players[Engine.GetPlayerID()].team != -1) 633 652 { 634 653 if (g_Players[Engine.GetPlayerID()].team != g_Players[sender].team) 635 654 msg.hide = true; 636 655 else 637 656 msg.context = translate("Team"); … … 641 660 recurse = true; 642 661 break; 643 662 case "/ally": 644 663 case "/allies": 645 664 // Check if we sent the message, or are the sender's (mutual) ally 646 if ( Engine.GetPlayerID() == sender || (g_Players[sender] && g_Players[sender].isMutualAlly[Engine.GetPlayerID()]))665 if (!g_IsObserver && (Engine.GetPlayerID() == sender || (g_Players[sender] && g_Players[sender].isMutualAlly[Engine.GetPlayerID()]))) 647 666 msg.context = translate("Ally"); 648 667 else 649 668 msg.hide = true; 650 669 651 670 recurse = true; 652 671 break; 653 672 case "/enemy": 654 673 case "/enemies": 655 674 // Check if we sent the message, or are the sender's enemy 656 if ( Engine.GetPlayerID() == sender || (g_Players[sender] && g_Players[sender].isEnemy[Engine.GetPlayerID()]))675 if (!g_IsObserver && (Engine.GetPlayerID() == sender || (g_Players[sender] && g_Players[sender].isEnemy[Engine.GetPlayerID()]))) 657 676 msg.context = translate("Enemy"); 658 677 else 659 678 msg.hide = true; 660 679 661 680 recurse = true; 662 681 break; 663 682 case "/me": 664 683 msg.action = true; 665 684 break; 685 case "/ban": 686 ban = true; 687 case "/kick": 688 msg.hide = true; 689 if (!g_IsNetworked) 690 break; 691 var trimmed = msg.text.substr(split[0].length + 1); 692 var matched = ""; 693 // Reject names which don't match or are a superset of the intended name. 694 for each (var player in playerAssignments) 695 if (trimmed.indexOf(player.name) == 0 && player.name.length > matched.length) 696 matched = player.name; 697 698 if (matched.length) 699 { 700 // The text should be translated for each client individually (see #3304) 701 if (ban) 702 msg.text = "Banning " + matched + "."; 703 else 704 msg.text = "Kicking " + matched + "."; 705 msg.hide = false; 706 707 if (g_IsController) 708 Engine.KickPlayer(matched, ban); 709 } 710 return; 666 711 case "/msg": 667 712 var trimmed = msg.text.substr(split[0].length + 1); 668 713 var matched = ""; 669 714 715 // Don't show private messages from observers to players 716 if (g_PlayerAssignments[msg.guid].player == -1 && g_PlayerAssignments[Engine.GetPlayerGUID()].player != -1) 717 { 718 msg.hide = true; 719 return; 720 } 721 670 722 // Reject names which don't match or are a superset of the intended name. 671 723 for each (var player in playerAssignments) 672 724 if (trimmed.indexOf(player.name + " ") == 0 && player.name.length > matched.length) 673 725 matched = player.name; 674 726 675 727 // If the local player's name was the longest one matched, show the message. 676 var playerName = g_Players[Engine.GetPlayerID()].name;677 if (matched.length && (m atched == playerName || sender == Engine.GetPlayerID()))728 // Show the message only for sender and recipient. 729 if (matched.length && (msg.guid == Engine.GetPlayerGUID() || matched == g_PlayerAssignments[Engine.GetPlayerGUID()].name)) 678 730 { 679 731 msg.context = translate("Private"); 680 732 msg.text = trimmed.substr(matched.length + 1); 681 733 msg.hide = false; // Might override team message hiding. 682 734 return; -
source/gui/scripting/ScriptFunctions.cpp
186 186 if (g_Game) 187 187 return g_Game->GetPlayerID(); 188 188 return -1; 189 189 } 190 190 191 std::string GetPlayerGUID(ScriptInterface::CxPrivate* UNUSED(pCxPrivate)) 192 { 193 if (g_NetServer) 194 return g_NetServer->GetHostGUID(); 195 else if (g_NetClient) 196 return g_NetClient->GetGUID(); 197 else 198 return ""; 199 } 200 191 201 void SetPlayerID(ScriptInterface::CxPrivate* UNUSED(pCxPrivate), int id) 192 202 { 193 203 if (g_Game) 194 204 g_Game->SetPlayerID(id); 195 205 } … … 345 355 SAFE_DELETE(g_NetServer); 346 356 SAFE_DELETE(g_NetClient); 347 357 SAFE_DELETE(g_Game); 348 358 } 349 359 360 void KickPlayer(ScriptInterface::CxPrivate* UNUSED(pCxPrivate), std::wstring playerName, bool ban) 361 { 362 if (g_NetServer) 363 g_NetServer->KickPlayer(playerName, ban); 364 } 365 350 366 JS::Value PollNetworkClient(ScriptInterface::CxPrivate* pCxPrivate) 351 367 { 352 368 if (!g_NetClient) 353 369 return JS::UndefinedValue(); 354 370 … … 954 970 scriptInterface.RegisterFunction<void, JS::HandleValue, int, &StartGame>("StartGame"); 955 971 scriptInterface.RegisterFunction<void, &Script_EndGame>("EndGame"); 956 972 scriptInterface.RegisterFunction<void, std::wstring, &StartNetworkHost>("StartNetworkHost"); 957 973 scriptInterface.RegisterFunction<void, std::wstring, std::string, &StartNetworkJoin>("StartNetworkJoin"); 958 974 scriptInterface.RegisterFunction<void, &DisconnectNetworkGame>("DisconnectNetworkGame"); 975 scriptInterface.RegisterFunction<void, std::wstring, bool, &KickPlayer>("KickPlayer"); 959 976 scriptInterface.RegisterFunction<JS::Value, &PollNetworkClient>("PollNetworkClient"); 960 977 scriptInterface.RegisterFunction<void, JS::HandleValue, &SetNetworkGameAttributes>("SetNetworkGameAttributes"); 961 978 scriptInterface.RegisterFunction<void, int, std::string, &AssignNetworkPlayer>("AssignNetworkPlayer"); 962 979 scriptInterface.RegisterFunction<void, std::string, int, &SetNetworkPlayerStatus>("SetNetworkPlayerStatus"); 963 980 scriptInterface.RegisterFunction<void, &ClearAllPlayerReady>("ClearAllPlayerReady"); … … 977 994 scriptInterface.RegisterFunction<void, &QuickLoad>("QuickLoad"); 978 995 979 996 // Misc functions 980 997 scriptInterface.RegisterFunction<std::wstring, std::wstring, &SetCursor>("SetCursor"); 981 998 scriptInterface.RegisterFunction<int, &GetPlayerID>("GetPlayerID"); 999 scriptInterface.RegisterFunction<std::string, &GetPlayerGUID>("GetPlayerGUID"); 982 1000 scriptInterface.RegisterFunction<void, int, &SetPlayerID>("SetPlayerID"); 983 1001 scriptInterface.RegisterFunction<void, std::string, &OpenURL>("OpenURL"); 984 1002 scriptInterface.RegisterFunction<std::wstring, &GetMatchID>("GetMatchID"); 985 1003 scriptInterface.RegisterFunction<void, &RestartInAtlas>("RestartInAtlas"); 986 1004 scriptInterface.RegisterFunction<bool, &AtlasIsAvailable>("AtlasIsAvailable"); -
source/network/NetClient.cpp
139 139 ENSURE(!m_Session); // must be called before we start the connection 140 140 141 141 m_UserName = username; 142 142 } 143 143 144 CStr CNetClient::GetGUID() 145 { 146 return m_GUID; 147 } 148 144 149 bool CNetClient::SetupConnection(const CStr& server) 145 150 { 146 151 CNetClientSession* session = new CNetClientSession(*this); 147 152 bool ok = session->Connect(PS_DEFAULT_PORT, server); 148 153 SetAndOwnSession(session); -
source/network/NetClient.h
86 86 * Set the user's name that will be displayed to all players. 87 87 * This must not be called after the connection setup. 88 88 */ 89 89 void SetUserName(const CStrW& username); 90 90 91 /** Returns the GUID of the client. */ 92 CStr GetGUID(); 93 91 94 /** 92 95 * Set up a connection to the remote networked server. 93 96 * @param server IP address or host name to connect to 94 97 * @return true on success, false on connection failure 95 98 */ -
source/network/NetHost.h
1 /* Copyright (C) 201 1Wildfire Games.1 /* Copyright (C) 2015 Wildfire Games. 2 2 * This file is part of 0 A.D. 3 3 * 4 4 * 0 A.D. is free software: you can redistribute it and/or modify 5 5 * it under the terms of the GNU General Public License as published by 6 6 * the Free Software Foundation, either version 2 of the License, or … … 60 60 enum NetDisconnectReason 61 61 { 62 62 NDR_UNKNOWN = 0, 63 63 NDR_UNEXPECTED_SHUTDOWN, 64 64 NDR_INCORRECT_PROTOCOL_VERSION, 65 NDR_SERVER_ALREADY_IN_GAME 65 NDR_SERVER_ALREADY_IN_GAME, 66 NDR_KICKED, 67 NDR_BANNED 66 68 }; 67 69 68 70 class CNetHost 69 71 { 70 72 public: -
source/network/NetServer.cpp
127 127 128 128 m_ServerTurnManager = NULL; 129 129 130 130 m_ServerName = DEFAULT_SERVER_NAME; 131 131 m_WelcomeMessage = DEFAULT_WELCOME_MESSAGE; 132 m_HostGUID = std::string(""); 132 133 } 133 134 134 135 CNetServerWorker::~CNetServerWorker() 135 136 { 136 137 if (m_State != SERVER_STATE_UNCONNECTED) … … 604 605 session->SetFirstState(NSS_HANDSHAKE); 605 606 } 606 607 607 608 bool CNetServerWorker::HandleConnect(CNetServerSession* session) 608 609 { 610 CNetServerWorker& server = session->GetServer(); 611 612 // Disconnect banned IPs 613 std::string ipAddress = session -> GetIPAddress(); 614 if(std::find(server.m_BannedIPs.begin(), server.m_BannedIPs.end(), ipAddress) != server.m_BannedIPs.end()) 615 { 616 session->Disconnect(NDR_BANNED); 617 return false; 618 } 619 620 // Send handshake challenge 609 621 CSrvHandshakeMessage handshake; 610 622 handshake.m_Magic = PS_PROTOCOL_MAGIC; 611 623 handshake.m_ProtocolVersion = PS_PROTOCOL_VERSION; 612 624 handshake.m_SoftwareVersion = PS_PROTOCOL_VERSION; 613 625 return session->SendMessage(&handshake); … … 615 627 616 628 void CNetServerWorker::OnUserJoin(CNetServerSession* session) 617 629 { 618 630 AddPlayer(session->GetGUID(), session->GetUserName()); 619 631 632 if (m_HostGUID == "") 633 m_HostGUID = session->GetGUID(); 634 620 635 CGameSetupMessage gameSetupMessage(GetScriptInterface()); 621 636 gameSetupMessage.m_Data = m_GameAttributes.get(); 622 637 session->SendMessage(&gameSetupMessage); 623 638 624 639 CPlayerAssignmentMessage assignMessage; … … 630 645 { 631 646 RemovePlayer(session->GetGUID()); 632 647 633 648 if (m_ServerTurnManager && session->GetCurrState() != NSS_JOIN_SYNCING) 634 649 m_ServerTurnManager->UninitialiseClient(session->GetHostID()); // TODO: only for non-observers 635 636 // TODO: ought to switch the player controlled by that client637 // back to AI control, or something?638 650 } 639 651 640 652 void CNetServerWorker::AddPlayer(const CStr& guid, const CStrW& name) 641 653 { 642 654 // Find all player IDs in active use; we mustn't give them to a second player (excluding the unassigned ID: -1) … … 707 719 it->second.m_Status = 0; 708 720 709 721 SendPlayerAssignments(); 710 722 } 711 723 724 void CNetServerWorker::KickPlayer(const CStrW& playerName, bool ban) 725 { 726 if (ban) 727 { 728 // Add playername to blacklist 729 if (std::find(m_BannedPlayers.begin(), m_BannedPlayers.end(), playerName) == m_BannedPlayers.end()) 730 m_BannedPlayers.push_back(playerName); 731 732 // Add IP address to blacklist 733 std::string ipAddress = GetPlayerIPAddress(playerName); 734 if (std::find(m_BannedIPs.begin(), m_BannedIPs.end(), ipAddress) == m_BannedIPs.end()) 735 m_BannedIPs.push_back(ipAddress); 736 } 737 738 // Disconnect everyone with that nick except the host 739 for (auto session : m_Sessions) 740 { 741 if (session->GetUserName() == playerName && session->GetGUID() != m_HostGUID) 742 session->Disconnect(ban ? NDR_BANNED : NDR_KICKED); 743 } 744 } 745 746 std::string CNetServerWorker::GetPlayerIPAddress(const CStrW& playerName) 747 { 748 std::string ipAddress = "error"; 749 for (auto session : m_Sessions) 750 { 751 if (session->GetUserName() == playerName) 752 return session->GetIPAddress(); 753 } 754 return ipAddress; 755 } 756 757 std::string CNetServerWorker::GetHostGUID() 758 { 759 return m_HostGUID; 760 } 761 712 762 void CNetServerWorker::AssignPlayer(int playerID, const CStr& guid) 713 763 { 714 764 // Remove anyone who's already assigned to this player 715 765 for (PlayerAssignmentMap::iterator it = m_PlayerAssignments.begin(); it != m_PlayerAssignments.end(); ++it) 716 766 { … … 764 814 ENSURE(event->GetType() == (uint)NMT_CLIENT_HANDSHAKE); 765 815 766 816 CNetServerSession* session = (CNetServerSession*)context; 767 817 CNetServerWorker& server = session->GetServer(); 768 818 819 // Check protocol version 769 820 CCliHandshakeMessage* message = (CCliHandshakeMessage*)event->GetParamRef(); 770 821 if (message->m_ProtocolVersion != PS_PROTOCOL_VERSION) 771 822 { 772 823 session->Disconnect(NDR_INCORRECT_PROTOCOL_VERSION); 773 824 return false; 774 825 } 775 826 827 // Send handshake response 776 828 CSrvHandshakeResponseMessage handshakeResponse; 777 829 handshakeResponse.m_UseProtocolVersion = PS_PROTOCOL_VERSION; 778 830 handshakeResponse.m_Message = server.m_WelcomeMessage; 779 831 handshakeResponse.m_Flags = 0; 780 832 session->SendMessage(&handshakeResponse); … … 791 843 792 844 CAuthenticateMessage* message = (CAuthenticateMessage*)event->GetParamRef(); 793 845 794 846 CStrW username = server.DeduplicatePlayerName(SanitisePlayerName(message->m_Name)); 795 847 848 // Disconnect banned usernames 849 if(std::find(server.m_BannedPlayers.begin(), server.m_BannedPlayers.end(), username) != server.m_BannedPlayers.end()) 850 { 851 session->Disconnect(NDR_BANNED); 852 return true; 853 } 854 796 855 bool isRejoining = false; 797 856 798 857 if (server.m_State != SERVER_STATE_PREGAME) 799 858 { 800 859 // isRejoining = true; // uncomment this to test rejoining even if the player wasn't connected previously … … 1145 1204 { 1146 1205 CScopeLock lock(m_Worker->m_WorkerMutex); 1147 1206 m_Worker->m_PlayerReadyQueue.push_back(std::make_pair(guid, ready)); 1148 1207 } 1149 1208 1209 void CNetServer::KickPlayer(const CStrW& playerName, bool ban) 1210 { 1211 CScopeLock lock(m_Worker->m_WorkerMutex); 1212 m_Worker->KickPlayer(playerName, ban); 1213 } 1214 1215 std::string CNetServer::GetHostGUID() 1216 { 1217 CScopeLock lock(m_Worker->m_WorkerMutex); 1218 return m_Worker->GetHostGUID(); 1219 } 1220 1150 1221 void CNetServer::ClearAllPlayerReady() 1151 1222 { 1152 1223 CScopeLock lock(m_Worker->m_WorkerMutex); 1153 1224 m_Worker->m_PlayerResetReadyQueue.push_back(false); 1154 1225 } -
source/network/NetServer.h
134 134 * The changes will be asynchronously propagated to all clients. 135 135 */ 136 136 void ClearAllPlayerReady(); 137 137 138 138 /** 139 * Disconnects a player from the gamesetup / session. 140 */ 141 void KickPlayer(const CStrW& playerName, bool ban); 142 143 /** 144 * Returns the GUID of the host. 145 */ 146 std::string GetHostGUID(); 147 148 /** 139 149 * Call from the GUI to asynchronously notify all clients that they should start loading the game. 140 150 */ 141 151 void StartGame(); 142 152 143 153 /** … … 181 191 * Send a message to the given network peer. 182 192 */ 183 193 bool SendMessage(ENetPeer* peer, const CNetMessage* message); 184 194 185 195 /** 196 * Disconnected a player from the match / gamesetup and optionally prevents him/her from rejoining. 197 */ 198 void KickPlayer(const CStrW& playerName, bool ban); 199 200 /** 186 201 * Send a message to all clients who have completed the full connection process 187 202 * (i.e. are in the pre-game or in-game states). 188 203 */ 189 204 bool Broadcast(const CNetMessage* message); 190 205 206 /** 207 * Returns the IP address of the given connected player. 208 */ 209 std::string GetPlayerIPAddress(const CStrW& playerName); 210 191 211 private: 192 212 friend class CNetServer; 193 213 friend class CNetFileReceiveTask_ServerRejoin; 194 214 195 215 CNetServerWorker(int autostartPlayers); … … 244 264 void SetTurnLength(u32 msecs); 245 265 246 266 void AddPlayer(const CStr& guid, const CStrW& name); 247 267 void RemovePlayer(const CStr& guid); 248 268 void SetPlayerReady(const CStr& guid, const int ready); 269 std::string GetHostGUID(); 249 270 void SendPlayerAssignments(); 250 271 void ClearAllPlayerReady(); 251 272 252 273 void SetupSession(CNetServerSession* session); 253 274 bool HandleConnect(CNetServerSession* session); … … 269 290 270 291 void ConstructPlayerAssignmentMessage(CPlayerAssignmentMessage& message); 271 292 272 293 void HandleMessageReceive(const CNetMessage* message, CNetServerSession* session); 273 294 274 275 295 /** 276 296 * Internal script context for (de)serializing script messages, 277 297 * and for storing game attributes. 278 298 * (TODO: we shouldn't bother deserializing (except for debug printing of messages), 279 299 * we should just forward messages blindly and efficiently.) … … 285 305 /** 286 306 * Stores the most current game attributes. 287 307 */ 288 308 DefPersistentRooted<JS::Value> m_GameAttributes; 289 309 310 std::vector<std::string> m_BannedIPs; 311 std::vector<std::wstring> m_BannedPlayers; 312 290 313 int m_AutostartPlayers; 291 314 292 315 ENetHost* m_Host; 293 316 std::vector<CNetServerSession*> m_Sessions; 294 317 … … 301 324 302 325 u32 m_NextHostID; 303 326 304 327 CNetServerTurnManager* m_ServerTurnManager; 305 328 329 std::string m_HostGUID; 330 306 331 /** 307 332 * A copy of all simulation commands received so far, indexed by 308 333 * turn number, to simplify support for rejoining etc. 309 334 * TODO: verify this doesn't use too much RAM. 310 335 */ -
source/network/NetSession.cpp
1 /* Copyright (C) 201 1Wildfire Games.1 /* Copyright (C) 2015 Wildfire Games. 2 2 * This file is part of 0 A.D. 3 3 * 4 4 * 0 A.D. is free software: you can redistribute it and/or modify 5 5 * it under the terms of the GNU General Public License as published by 6 6 * the Free Software Foundation, either version 2 of the License, or … … 173 173 CNetServerSession::CNetServerSession(CNetServerWorker& server, ENetPeer* peer) : 174 174 m_Server(server), m_FileTransferer(this), m_Peer(peer) 175 175 { 176 176 } 177 177 178 std::string CNetServerSession::GetIPAddress() 179 { 180 char ipAddress[256] = "(error)"; 181 enet_address_get_host_ip(&(m_Peer->address), ipAddress, ARRAY_SIZE(ipAddress)); 182 return std::string(ipAddress); 183 } 184 178 185 void CNetServerSession::Disconnect(u32 reason) 179 186 { 180 187 Update((uint)NMT_CONNECTION_LOST, NULL); 181 188 182 189 enet_peer_disconnect(m_Peer, reason); -
source/network/NetSession.h
1 /* Copyright (C) 201 1Wildfire Games.1 /* Copyright (C) 2015 Wildfire Games. 2 2 * This file is part of 0 A.D. 3 3 * 4 4 * 0 A.D. is free software: you can redistribute it and/or modify 5 5 * it under the terms of the GNU General Public License as published by 6 6 * the Free Software Foundation, either version 2 of the License, or … … 121 121 122 122 u32 GetHostID() const { return m_HostID; } 123 123 void SetHostID(u32 id) { m_HostID = id; } 124 124 125 125 /** 126 * Returns the IP address of the client. 127 */ 128 std::string GetIPAddress(); 129 130 /** 126 131 * Sends a disconnection notification to the client, 127 132 * and sends a NMT_CONNECTION_LOST message to the session FSM. 128 133 * The server will receive a disconnection notification after a while. 129 134 * The server will not receive any further messages sent via this session. 130 135 */