1 /* 2 Minetest 3 Copyright (C) 2013 celeron55, Perttu Ahola <celeron55@gmail.com> 4 5 This program is free software; you can redistribute it and/or modify 6 it under the terms of the GNU Lesser General Public License as published by 7 the Free Software Foundation; either version 2.1 of the License, or 8 (at your option) any later version. 9 10 This program is distributed in the hope that it will be useful, 11 but WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 13 GNU Lesser General Public License for more details. 14 15 You should have received a copy of the GNU Lesser General Public License along 16 with this program; if not, write to the Free Software Foundation, Inc., 17 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 18 */ 19 20 #pragma once 21 22 #include "clientenvironment.h" 23 #include "irrlichttypes_extrabloated.h" 24 #include <ostream> 25 #include <map> 26 #include <set> 27 #include <vector> 28 #include <unordered_set> 29 #include "clientobject.h" 30 #include "gamedef.h" 31 #include "inventorymanager.h" 32 #include "localplayer.h" 33 #include "client/hud.h" 34 #include "particles.h" 35 #include "mapnode.h" 36 #include "tileanimation.h" 37 #include "mesh_generator_thread.h" 38 #include "network/address.h" 39 #include "network/peerhandler.h" 40 #include <fstream> 41 42 #define CLIENT_CHAT_MESSAGE_LIMIT_PER_10S 10.0f 43 44 struct ClientEvent; 45 struct MeshMakeData; 46 struct ChatMessage; 47 class MapBlockMesh; 48 class IWritableTextureSource; 49 class IWritableShaderSource; 50 class IWritableItemDefManager; 51 class ISoundManager; 52 class NodeDefManager; 53 //class IWritableCraftDefManager; 54 class ClientMediaDownloader; 55 struct MapDrawControl; 56 class ModChannelMgr; 57 class MtEventManager; 58 struct PointedThing; 59 class MapDatabase; 60 class Minimap; 61 struct MinimapMapblock; 62 class Camera; 63 class NetworkPacket; 64 namespace con { 65 class Connection; 66 } 67 68 enum LocalClientState { 69 LC_Created, 70 LC_Init, 71 LC_Ready 72 }; 73 74 /* 75 Packet counter 76 */ 77 78 class PacketCounter 79 { 80 public: 81 PacketCounter() = default; 82 add(u16 command)83 void add(u16 command) 84 { 85 auto n = m_packets.find(command); 86 if (n == m_packets.end()) 87 m_packets[command] = 1; 88 else 89 n->second++; 90 } 91 clear()92 void clear() 93 { 94 m_packets.clear(); 95 } 96 97 u32 sum() const; 98 void print(std::ostream &o) const; 99 100 private: 101 // command, count 102 std::map<u16, u32> m_packets; 103 }; 104 105 class ClientScripting; 106 class GameUI; 107 108 class Client : public con::PeerHandler, public InventoryManager, public IGameDef 109 { 110 public: 111 /* 112 NOTE: Nothing is thread-safe here. 113 */ 114 115 Client( 116 const char *playername, 117 const std::string &password, 118 const std::string &address_name, 119 MapDrawControl &control, 120 IWritableTextureSource *tsrc, 121 IWritableShaderSource *shsrc, 122 IWritableItemDefManager *itemdef, 123 NodeDefManager *nodedef, 124 ISoundManager *sound, 125 MtEventManager *event, 126 bool ipv6, 127 GameUI *game_ui 128 ); 129 130 ~Client(); 131 DISABLE_CLASS_COPY(Client); 132 133 // Load local mods into memory 134 void scanModSubfolder(const std::string &mod_name, const std::string &mod_path, 135 std::string mod_subpath); scanModIntoMemory(const std::string & mod_name,const std::string & mod_path)136 inline void scanModIntoMemory(const std::string &mod_name, const std::string &mod_path) 137 { 138 scanModSubfolder(mod_name, mod_path, ""); 139 } 140 141 /* 142 request all threads managed by client to be stopped 143 */ 144 void Stop(); 145 146 147 bool isShutdown(); 148 149 /* 150 The name of the local player should already be set when 151 calling this, as it is sent in the initialization. 152 */ 153 void connect(Address address, bool is_local_server); 154 155 /* 156 Stuff that references the environment is valid only as 157 long as this is not called. (eg. Players) 158 If this throws a PeerNotFoundException, the connection has 159 timed out. 160 */ 161 void step(float dtime); 162 163 /* 164 * Command Handlers 165 */ 166 167 void handleCommand(NetworkPacket* pkt); 168 handleCommand_Null(NetworkPacket * pkt)169 void handleCommand_Null(NetworkPacket* pkt) {}; 170 void handleCommand_Deprecated(NetworkPacket* pkt); 171 void handleCommand_Hello(NetworkPacket* pkt); 172 void handleCommand_AuthAccept(NetworkPacket* pkt); 173 void handleCommand_AcceptSudoMode(NetworkPacket* pkt); 174 void handleCommand_DenySudoMode(NetworkPacket* pkt); 175 void handleCommand_AccessDenied(NetworkPacket* pkt); 176 void handleCommand_RemoveNode(NetworkPacket* pkt); 177 void handleCommand_AddNode(NetworkPacket* pkt); 178 void handleCommand_NodemetaChanged(NetworkPacket *pkt); 179 void handleCommand_BlockData(NetworkPacket* pkt); 180 void handleCommand_Inventory(NetworkPacket* pkt); 181 void handleCommand_TimeOfDay(NetworkPacket* pkt); 182 void handleCommand_ChatMessage(NetworkPacket *pkt); 183 void handleCommand_ActiveObjectRemoveAdd(NetworkPacket* pkt); 184 void handleCommand_ActiveObjectMessages(NetworkPacket* pkt); 185 void handleCommand_Movement(NetworkPacket* pkt); 186 void handleCommand_Fov(NetworkPacket *pkt); 187 void handleCommand_HP(NetworkPacket* pkt); 188 void handleCommand_Breath(NetworkPacket* pkt); 189 void handleCommand_MovePlayer(NetworkPacket* pkt); 190 void handleCommand_DeathScreen(NetworkPacket* pkt); 191 void handleCommand_AnnounceMedia(NetworkPacket* pkt); 192 void handleCommand_Media(NetworkPacket* pkt); 193 void handleCommand_NodeDef(NetworkPacket* pkt); 194 void handleCommand_ItemDef(NetworkPacket* pkt); 195 void handleCommand_PlaySound(NetworkPacket* pkt); 196 void handleCommand_StopSound(NetworkPacket* pkt); 197 void handleCommand_FadeSound(NetworkPacket *pkt); 198 void handleCommand_Privileges(NetworkPacket* pkt); 199 void handleCommand_InventoryFormSpec(NetworkPacket* pkt); 200 void handleCommand_DetachedInventory(NetworkPacket* pkt); 201 void handleCommand_ShowFormSpec(NetworkPacket* pkt); 202 void handleCommand_SpawnParticle(NetworkPacket* pkt); 203 void handleCommand_AddParticleSpawner(NetworkPacket* pkt); 204 void handleCommand_DeleteParticleSpawner(NetworkPacket* pkt); 205 void handleCommand_HudAdd(NetworkPacket* pkt); 206 void handleCommand_HudRemove(NetworkPacket* pkt); 207 void handleCommand_HudChange(NetworkPacket* pkt); 208 void handleCommand_HudSetFlags(NetworkPacket* pkt); 209 void handleCommand_HudSetParam(NetworkPacket* pkt); 210 void handleCommand_HudSetSky(NetworkPacket* pkt); 211 void handleCommand_HudSetSun(NetworkPacket* pkt); 212 void handleCommand_HudSetMoon(NetworkPacket* pkt); 213 void handleCommand_HudSetStars(NetworkPacket* pkt); 214 void handleCommand_CloudParams(NetworkPacket* pkt); 215 void handleCommand_OverrideDayNightRatio(NetworkPacket* pkt); 216 void handleCommand_LocalPlayerAnimations(NetworkPacket* pkt); 217 void handleCommand_EyeOffset(NetworkPacket* pkt); 218 void handleCommand_UpdatePlayerList(NetworkPacket* pkt); 219 void handleCommand_ModChannelMsg(NetworkPacket *pkt); 220 void handleCommand_ModChannelSignal(NetworkPacket *pkt); 221 void handleCommand_SrpBytesSandB(NetworkPacket *pkt); 222 void handleCommand_FormspecPrepend(NetworkPacket *pkt); 223 void handleCommand_CSMRestrictionFlags(NetworkPacket *pkt); 224 void handleCommand_PlayerSpeed(NetworkPacket *pkt); 225 void handleCommand_MediaPush(NetworkPacket *pkt); 226 void handleCommand_MinimapModes(NetworkPacket *pkt); 227 228 void ProcessData(NetworkPacket *pkt); 229 230 void Send(NetworkPacket* pkt); 231 232 void interact(InteractAction action, const PointedThing &pointed); 233 234 void sendNodemetaFields(v3s16 p, const std::string &formname, 235 const StringMap &fields); 236 void sendInventoryFields(const std::string &formname, 237 const StringMap &fields); 238 void sendInventoryAction(InventoryAction *a); 239 void sendChatMessage(const std::wstring &message); 240 void clearOutChatQueue(); 241 void sendChangePassword(const std::string &oldpassword, 242 const std::string &newpassword); 243 void sendDamage(u16 damage); 244 void sendRespawn(); 245 void sendReady(); 246 getEnv()247 ClientEnvironment& getEnv() { return m_env; } tsrc()248 ITextureSource *tsrc() { return getTextureSource(); } sound()249 ISoundManager *sound() { return getSoundManager(); } 250 static const std::string &getBuiltinLuaPath(); 251 static const std::string &getClientModsLuaPath(); 252 253 const std::vector<ModSpec> &getMods() const override; 254 const ModSpec* getModSpec(const std::string &modname) const override; 255 256 // Causes urgent mesh updates (unlike Map::add/removeNodeWithEvent) 257 void removeNode(v3s16 p); 258 259 // helpers to enforce CSM restrictions 260 MapNode CSMGetNode(v3s16 p, bool *is_valid_position); 261 int CSMClampRadius(v3s16 pos, int radius); 262 v3s16 CSMClampPos(v3s16 pos); 263 264 void addNode(v3s16 p, MapNode n, bool remove_metadata = true); 265 266 void setPlayerControl(PlayerControl &control); 267 268 // Returns true if the inventory of the local player has been 269 // updated from the server. If it is true, it is set to false. 270 bool updateWieldedItem(); 271 272 /* InventoryManager interface */ 273 Inventory* getInventory(const InventoryLocation &loc) override; 274 void inventoryAction(InventoryAction *a) override; 275 276 // Send the item number 'item' as player item to the server 277 void setPlayerItem(u16 item); 278 getConnectedPlayerNames()279 const std::list<std::string> &getConnectedPlayerNames() 280 { 281 return m_env.getPlayerNames(); 282 } 283 284 float getAnimationTime(); 285 286 int getCrackLevel(); 287 v3s16 getCrackPos(); 288 void setCrack(int level, v3s16 pos); 289 290 u16 getHP(); 291 checkPrivilege(const std::string & priv)292 bool checkPrivilege(const std::string &priv) const 293 { return (m_privileges.count(priv) != 0); } 294 getPrivilegeList()295 const std::unordered_set<std::string> &getPrivilegeList() const 296 { return m_privileges; } 297 298 bool getChatMessage(std::wstring &message); 299 void typeChatMessage(const std::wstring& message); 300 getMapSeed()301 u64 getMapSeed(){ return m_map_seed; } 302 303 void addUpdateMeshTask(v3s16 blockpos, bool ack_to_server=false, bool urgent=false); 304 // Including blocks at appropriate edges 305 void addUpdateMeshTaskWithEdge(v3s16 blockpos, bool ack_to_server=false, bool urgent=false); 306 void addUpdateMeshTaskForNode(v3s16 nodepos, bool ack_to_server=false, bool urgent=false); 307 updateCameraOffset(v3s16 camera_offset)308 void updateCameraOffset(v3s16 camera_offset) 309 { m_mesh_update_thread.m_camera_offset = camera_offset; } 310 hasClientEvents()311 bool hasClientEvents() const { return !m_client_event_queue.empty(); } 312 // Get event from queue. If queue is empty, it triggers an assertion failure. 313 ClientEvent * getClientEvent(); 314 accessDenied()315 bool accessDenied() const { return m_access_denied; } 316 reconnectRequested()317 bool reconnectRequested() const { return m_access_denied_reconnect; } 318 setFatalError(const std::string & reason)319 void setFatalError(const std::string &reason) 320 { 321 m_access_denied = true; 322 m_access_denied_reason = reason; 323 } 324 325 // Renaming accessDeniedReason to better name could be good as it's used to 326 // disconnect client when CSM failed. accessDeniedReason()327 const std::string &accessDeniedReason() const { return m_access_denied_reason; } 328 itemdefReceived()329 const bool itemdefReceived() const 330 { return m_itemdef_received; } nodedefReceived()331 const bool nodedefReceived() const 332 { return m_nodedef_received; } mediaReceived()333 const bool mediaReceived() const 334 { return !m_media_downloader; } activeObjectsReceived()335 const bool activeObjectsReceived() const 336 { return m_activeobjects_received; } 337 getProtoVersion()338 u16 getProtoVersion() 339 { return m_proto_ver; } 340 341 void confirmRegistration(); 342 bool m_is_registration_confirmation_state = false; 343 bool m_simple_singleplayer_mode; 344 345 float mediaReceiveProgress(); 346 347 void afterContentReceived(); 348 349 float getRTT(); 350 float getCurRate(); 351 getMinimap()352 Minimap* getMinimap() { return m_minimap; } setCamera(Camera * camera)353 void setCamera(Camera* camera) { m_camera = camera; } 354 getCamera()355 Camera* getCamera () { return m_camera; } 356 357 bool shouldShowMinimap() const; 358 359 // IGameDef interface 360 IItemDefManager* getItemDefManager() override; 361 const NodeDefManager* getNodeDefManager() override; 362 ICraftDefManager* getCraftDefManager() override; 363 ITextureSource* getTextureSource(); 364 virtual IWritableShaderSource* getShaderSource(); 365 u16 allocateUnknownNodeId(const std::string &name) override; 366 virtual ISoundManager* getSoundManager(); 367 MtEventManager* getEventManager(); 368 virtual ParticleManager* getParticleManager(); checkLocalPrivilege(const std::string & priv)369 bool checkLocalPrivilege(const std::string &priv) 370 { return checkPrivilege(priv); } 371 virtual scene::IAnimatedMesh* getMesh(const std::string &filename, bool cache = false); 372 const std::string* getModFile(std::string filename); 373 374 std::string getModStoragePath() const override; 375 bool registerModStorage(ModMetadata *meta) override; 376 void unregisterModStorage(const std::string &name) override; 377 378 // The following set of functions is used by ClientMediaDownloader 379 // Insert a media file appropriately into the appropriate manager 380 bool loadMedia(const std::string &data, const std::string &filename, 381 bool from_media_push = false); 382 // Send a request for conventional media transfer 383 void request_media(const std::vector<std::string> &file_requests); 384 getState()385 LocalClientState getState() { return m_state; } 386 387 void makeScreenshot(); 388 pushToChatQueue(ChatMessage * cec)389 inline void pushToChatQueue(ChatMessage *cec) 390 { 391 m_chat_queue.push(cec); 392 } 393 getScript()394 ClientScripting *getScript() { return m_script; } modsLoaded()395 const bool modsLoaded() const { return m_mods_loaded; } 396 397 void pushToEventQueue(ClientEvent *event); 398 399 void showMinimap(bool show = true); 400 401 const Address getServerAddress(); 402 getAddressName()403 const std::string &getAddressName() const 404 { 405 return m_address_name; 406 } 407 getCSMRestrictionFlags()408 inline u64 getCSMRestrictionFlags() const 409 { 410 return m_csm_restriction_flags; 411 } 412 checkCSMRestrictionFlag(CSMRestrictionFlags flag)413 inline bool checkCSMRestrictionFlag(CSMRestrictionFlags flag) const 414 { 415 return m_csm_restriction_flags & flag; 416 } 417 418 bool joinModChannel(const std::string &channel) override; 419 bool leaveModChannel(const std::string &channel) override; 420 bool sendModChannelMessage(const std::string &channel, 421 const std::string &message) override; 422 ModChannel *getModChannel(const std::string &channel) override; 423 getFormspecPrepend()424 const std::string &getFormspecPrepend() const 425 { 426 return m_env.getLocalPlayer()->formspec_prepend; 427 } 428 private: 429 void loadMods(); 430 431 // Virtual methods from con::PeerHandler 432 void peerAdded(con::Peer *peer) override; 433 void deletingPeer(con::Peer *peer, bool timeout) override; 434 435 void initLocalMapSaving(const Address &address, 436 const std::string &hostname, 437 bool is_local_server); 438 439 void ReceiveAll(); 440 441 void sendPlayerPos(); 442 443 void deleteAuthData(); 444 // helper method shared with clientpackethandler 445 static AuthMechanism choseAuthMech(const u32 mechs); 446 447 void sendInit(const std::string &playerName); 448 void promptConfirmRegistration(AuthMechanism chosen_auth_mechanism); 449 void startAuth(AuthMechanism chosen_auth_mechanism); 450 void sendDeletedBlocks(std::vector<v3s16> &blocks); 451 void sendGotBlocks(const std::vector<v3s16> &blocks); 452 void sendRemovedSounds(std::vector<s32> &soundList); 453 454 // Helper function getPlayerName()455 inline std::string getPlayerName() 456 { return m_env.getLocalPlayer()->getName(); } 457 458 bool canSendChatMessage() const; 459 460 float m_packetcounter_timer = 0.0f; 461 float m_connection_reinit_timer = 0.1f; 462 float m_avg_rtt_timer = 0.0f; 463 float m_playerpos_send_timer = 0.0f; 464 IntervalLimiter m_map_timer_and_unload_interval; 465 466 IWritableTextureSource *m_tsrc; 467 IWritableShaderSource *m_shsrc; 468 IWritableItemDefManager *m_itemdef; 469 NodeDefManager *m_nodedef; 470 ISoundManager *m_sound; 471 MtEventManager *m_event; 472 473 474 MeshUpdateThread m_mesh_update_thread; 475 ClientEnvironment m_env; 476 ParticleManager m_particle_manager; 477 std::unique_ptr<con::Connection> m_con; 478 std::string m_address_name; 479 Camera *m_camera = nullptr; 480 Minimap *m_minimap = nullptr; 481 bool m_minimap_disabled_by_server = false; 482 483 // Server serialization version 484 u8 m_server_ser_ver; 485 486 // Used version of the protocol with server 487 // Values smaller than 25 only mean they are smaller than 25, 488 // and aren't accurate. We simply just don't know, because 489 // the server didn't send the version back then. 490 // If 0, server init hasn't been received yet. 491 u16 m_proto_ver = 0; 492 493 bool m_update_wielded_item = false; 494 Inventory *m_inventory_from_server = nullptr; 495 float m_inventory_from_server_age = 0.0f; 496 PacketCounter m_packetcounter; 497 // Block mesh animation parameters 498 float m_animation_time = 0.0f; 499 int m_crack_level = -1; 500 v3s16 m_crack_pos; 501 // 0 <= m_daynight_i < DAYNIGHT_CACHE_COUNT 502 //s32 m_daynight_i; 503 //u32 m_daynight_ratio; 504 std::queue<std::wstring> m_out_chat_queue; 505 u32 m_last_chat_message_sent; 506 float m_chat_message_allowance = 5.0f; 507 std::queue<ChatMessage *> m_chat_queue; 508 509 // The authentication methods we can use to enter sudo mode (=change password) 510 u32 m_sudo_auth_methods; 511 512 // The seed returned by the server in TOCLIENT_INIT is stored here 513 u64 m_map_seed = 0; 514 515 // Auth data 516 std::string m_playername; 517 std::string m_password; 518 // If set, this will be sent (and cleared) upon a TOCLIENT_ACCEPT_SUDO_MODE 519 std::string m_new_password; 520 // Usable by auth mechanisms. 521 AuthMechanism m_chosen_auth_mech; 522 void *m_auth_data = nullptr; 523 524 bool m_access_denied = false; 525 bool m_access_denied_reconnect = false; 526 std::string m_access_denied_reason = ""; 527 std::queue<ClientEvent *> m_client_event_queue; 528 bool m_itemdef_received = false; 529 bool m_nodedef_received = false; 530 bool m_activeobjects_received = false; 531 bool m_mods_loaded = false; 532 533 ClientMediaDownloader *m_media_downloader; 534 // Set of media filenames pushed by server at runtime 535 std::unordered_set<std::string> m_media_pushed_files; 536 537 // time_of_day speed approximation for old protocol 538 bool m_time_of_day_set = false; 539 float m_last_time_of_day_f = -1.0f; 540 float m_time_of_day_update_timer = 0.0f; 541 542 // An interval for generally sending object positions and stuff 543 float m_recommended_send_interval = 0.1f; 544 545 // Sounds 546 float m_removed_sounds_check_timer = 0.0f; 547 // Mapping from server sound ids to our sound ids 548 std::unordered_map<s32, int> m_sounds_server_to_client; 549 // And the other way! 550 std::unordered_map<int, s32> m_sounds_client_to_server; 551 // Relation of client id to object id 552 std::unordered_map<int, u16> m_sounds_to_objects; 553 554 // Privileges 555 std::unordered_set<std::string> m_privileges; 556 557 // Detached inventories 558 // key = name 559 std::unordered_map<std::string, Inventory*> m_detached_inventories; 560 561 // Storage for mesh data for creating multiple instances of the same mesh 562 StringMap m_mesh_data; 563 564 // own state 565 LocalClientState m_state; 566 567 GameUI *m_game_ui; 568 569 // Used for saving server map to disk client-side 570 MapDatabase *m_localdb = nullptr; 571 IntervalLimiter m_localdb_save_interval; 572 u16 m_cache_save_interval; 573 574 // Client modding 575 ClientScripting *m_script = nullptr; 576 std::unordered_map<std::string, ModMetadata *> m_mod_storages; 577 float m_mod_storage_save_timer = 10.0f; 578 std::vector<ModSpec> m_mods; 579 StringMap m_mod_vfs; 580 581 bool m_shutdown = false; 582 583 // CSM restrictions byteflag 584 u64 m_csm_restriction_flags = CSMRestrictionFlags::CSM_RF_NONE; 585 u32 m_csm_restriction_noderange = 8; 586 587 std::unique_ptr<ModChannelMgr> m_modchannel_mgr; 588 }; 589