From d9dd7073cf723ff4388163e1af7024aea205de07 Mon Sep 17 00:00:00 2001 From: David Cernat Date: Sat, 13 Oct 2018 15:36:13 +0300 Subject: [PATCH] [General] Send certain packets only when logged in Previously, client mods adding packet-sending scripts to the spawn area made clients send the associated packets as soon as they inputted their character name when joining a server using those mods. This made the clients either get disconnected for not replying to a handshake first, or it made them get kicked for sending object packets that are disallowed for players who are not logged in. To fix this, LocalPlayer's hasFinishedCharGen() has been replaced with isLoggedIn(), because the former was already returning true when players inputted their names. --- apps/openmw/mwgui/quickkeysmenu.cpp | 4 +- apps/openmw/mwinput/inputmanagerimp.cpp | 4 +- apps/openmw/mwmp/LocalPlayer.cpp | 10 +++- apps/openmw/mwmp/LocalPlayer.hpp | 3 +- apps/openmw/mwscript/containerextensions.cpp | 6 ++- apps/openmw/mwscript/dialogueextensions.cpp | 8 +-- apps/openmw/mwscript/interpretercontext.cpp | 8 +-- apps/openmw/mwscript/miscextensions.cpp | 53 ++++++++++++------- .../mwscript/transformationextensions.cpp | 30 ++++++----- apps/openmw/mwworld/scene.cpp | 8 +-- 10 files changed, 80 insertions(+), 54 deletions(-) diff --git a/apps/openmw/mwgui/quickkeysmenu.cpp b/apps/openmw/mwgui/quickkeysmenu.cpp index d5fc1b70d..8bcf45ded 100644 --- a/apps/openmw/mwgui/quickkeysmenu.cpp +++ b/apps/openmw/mwgui/quickkeysmenu.cpp @@ -164,10 +164,10 @@ namespace MWGui Start of tes3mp addition Send a PLAYER_QUICKKEYS packet whenever a key is unassigned, but only if the player - has finished character generation, so as to avoid doing anything doing startup when all + is logged in on the server, so as to avoid doing anything doing at startup when all quick keys get unassigned by default */ - if (mwmp::Main::get().getLocalPlayer()->hasFinishedCharGen() && !mwmp::Main::get().getLocalPlayer()->isReceivingQuickKeys) + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn() && !mwmp::Main::get().getLocalPlayer()->isReceivingQuickKeys) { mwmp::Main::get().getLocalPlayer()->sendQuickKey(key->index, Type_Unassigned); } diff --git a/apps/openmw/mwinput/inputmanagerimp.cpp b/apps/openmw/mwinput/inputmanagerimp.cpp index fc5216dfe..9aaf34908 100644 --- a/apps/openmw/mwinput/inputmanagerimp.cpp +++ b/apps/openmw/mwinput/inputmanagerimp.cpp @@ -1070,9 +1070,9 @@ namespace MWInput /* Start of tes3mp addition - Ignore attempts to rest if the player has not finished character generation yet + Ignore attempts to rest if the player has not logged in on the server yet */ - if (!mwmp::Main::get().getLocalPlayer()->hasFinishedCharGen()) + if (!mwmp::Main::get().getLocalPlayer()->isLoggedIn()) return; /* End of tes3mp addition diff --git a/apps/openmw/mwmp/LocalPlayer.cpp b/apps/openmw/mwmp/LocalPlayer.cpp index 6568e4d80..547657bee 100644 --- a/apps/openmw/mwmp/LocalPlayer.cpp +++ b/apps/openmw/mwmp/LocalPlayer.cpp @@ -46,6 +46,7 @@ using namespace std; LocalPlayer::LocalPlayer() { deathTime = time(0); + receivedCharacter = false; charGenState.currentStage = 0; charGenState.endStage = 1; @@ -193,9 +194,12 @@ bool LocalPlayer::processCharGen() return true; } -bool LocalPlayer::hasFinishedCharGen() +bool LocalPlayer::isLoggedIn() { - return charGenState.isFinished; + if (charGenState.isFinished && (charGenState.endStage > 1 || receivedCharacter)) + return true; + + return false; } void LocalPlayer::updateStatsDynamic(bool forceUpdate) @@ -855,6 +859,8 @@ void LocalPlayer::closeInventoryWindows() void LocalPlayer::setCharacter() { + receivedCharacter = true; + MWBase::World *world = MWBase::Environment::get().getWorld(); // Ignore invalid races diff --git a/apps/openmw/mwmp/LocalPlayer.hpp b/apps/openmw/mwmp/LocalPlayer.hpp index faa59a394..5e8d242a4 100644 --- a/apps/openmw/mwmp/LocalPlayer.hpp +++ b/apps/openmw/mwmp/LocalPlayer.hpp @@ -16,6 +16,7 @@ namespace mwmp virtual ~LocalPlayer(); time_t deathTime; + bool receivedCharacter; bool isReceivingInventory; bool isReceivingQuickKeys; @@ -25,7 +26,7 @@ namespace mwmp void update(); bool processCharGen(); - bool hasFinishedCharGen(); + bool isLoggedIn(); void updateStatsDynamic(bool forceUpdate = false); void updateAttributes(bool forceUpdate = false); diff --git a/apps/openmw/mwscript/containerextensions.cpp b/apps/openmw/mwscript/containerextensions.cpp index ae33e9457..ac58b77cb 100644 --- a/apps/openmw/mwscript/containerextensions.cpp +++ b/apps/openmw/mwscript/containerextensions.cpp @@ -113,7 +113,8 @@ namespace MWScript Send an ID_CONTAINER packet every time an item is added to a Ptr that doesn't belong to a DedicatedPlayer */ - else if (!ptr.getClass().isActor() || !mwmp::PlayerList::isDedicatedPlayer(ptr)) + else if (mwmp::Main::get().getLocalPlayer()->isLoggedIn() && + (!ptr.getClass().isActor() || !mwmp::PlayerList::isDedicatedPlayer(ptr))) { mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); objectList->reset(); @@ -240,7 +241,8 @@ namespace MWScript Send an ID_CONTAINER packet every time an item is removed from a Ptr that doesn't belong to a DedicatedPlayer */ - else if (!ptr.getClass().isActor() || !mwmp::PlayerList::isDedicatedPlayer(ptr)) + else if (mwmp::Main::get().getLocalPlayer()->isLoggedIn() && + (!ptr.getClass().isActor() || !mwmp::PlayerList::isDedicatedPlayer(ptr))) { mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); objectList->reset(); diff --git a/apps/openmw/mwscript/dialogueextensions.cpp b/apps/openmw/mwscript/dialogueextensions.cpp index 24da3136b..8b4374538 100644 --- a/apps/openmw/mwscript/dialogueextensions.cpp +++ b/apps/openmw/mwscript/dialogueextensions.cpp @@ -63,7 +63,7 @@ namespace MWScript Send an ID_PLAYER_JOURNAL packet every time a new journal entry is added through a script */ - if (!MWBase::Environment::get().getJournal()->hasEntry(quest, index)) + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn() && !MWBase::Environment::get().getJournal()->hasEntry(quest, index)) mwmp::Main::get().getLocalPlayer()->sendJournalEntry(quest, index, ptr); /* End of tes3mp addition @@ -99,7 +99,8 @@ namespace MWScript Send an ID_PLAYER_JOURNAL packet every time a journal index is set through a script */ - mwmp::Main::get().getLocalPlayer()->sendJournalIndex(quest, index); + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn()) + mwmp::Main::get().getLocalPlayer()->sendJournalIndex(quest, index); /* End of tes3mp addition */ @@ -137,7 +138,8 @@ namespace MWScript Send an ID_PLAYER_TOPIC packet every time a new topic is added through a script */ - if (MWBase::Environment::get().getDialogueManager()->isNewTopic(Misc::StringUtils::lowerCase(topic))) + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn() && + MWBase::Environment::get().getDialogueManager()->isNewTopic(Misc::StringUtils::lowerCase(topic))) mwmp::Main::get().getLocalPlayer()->sendTopic(Misc::StringUtils::lowerCase(topic)); /* End of tes3mp addition diff --git a/apps/openmw/mwscript/interpretercontext.cpp b/apps/openmw/mwscript/interpretercontext.cpp index fd0fdbb60..b0049e1b7 100644 --- a/apps/openmw/mwscript/interpretercontext.cpp +++ b/apps/openmw/mwscript/interpretercontext.cpp @@ -613,10 +613,10 @@ namespace MWScript Start of tes3mp addition Send an ID_OBJECT_STATE packet whenever an object is enabled, as long as - the player has finished character generation and the object wasn't already + the player is logged in on the server and the object wasn't already enabled previously */ - if (mwmp::Main::get().getLocalPlayer()->hasFinishedCharGen()) + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn()) { if (ref.isInCell() && !ref.getRefData().isEnabled()) { @@ -651,10 +651,10 @@ namespace MWScript Start of tes3mp addition Send an ID_OBJECT_STATE packet whenever an object is disabled, as long as - the player has finished character generation and the object wasn't already + the player is logged in on the server and the object wasn't already disabled previously */ - if (mwmp::Main::get().getLocalPlayer()->hasFinishedCharGen()) + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn()) { if (ref.isInCell() && ref.getRefData().isEnabled()) { diff --git a/apps/openmw/mwscript/miscextensions.cpp b/apps/openmw/mwscript/miscextensions.cpp index adb25a5a2..43fd4343c 100644 --- a/apps/openmw/mwscript/miscextensions.cpp +++ b/apps/openmw/mwscript/miscextensions.cpp @@ -9,6 +9,7 @@ */ #include "../mwmp/Main.hpp" #include "../mwmp/Networking.hpp" +#include "../mwmp/LocalPlayer.hpp" #include "../mwmp/ObjectList.hpp" #include "../mwmp/ScriptController.hpp" /* @@ -105,11 +106,14 @@ namespace MWScript Send an ID_VIDEO_PLAY packet every time a video is played through a script */ - mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); - objectList->reset(); - objectList->packetOrigin = ScriptController::getPacketOriginFromContextType(runtime.getContext().getContextType()); - objectList->addVideoPlay(name, allowSkipping); - objectList->sendVideoPlay(); + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn()) + { + mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); + objectList->reset(); + objectList->packetOrigin = ScriptController::getPacketOriginFromContextType(runtime.getContext().getContextType()); + objectList->addVideoPlay(name, allowSkipping); + objectList->sendVideoPlay(); + } /* End of tes3mp addition */ @@ -216,11 +220,14 @@ namespace MWScript Send an ID_OBJECT_LOCK packet every time an object is locked through a script */ - mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); - objectList->reset(); - objectList->packetOrigin = ScriptController::getPacketOriginFromContextType(runtime.getContext().getContextType()); - objectList->addObjectLock(ptr, lockLevel); - objectList->sendObjectLock(); + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn()) + { + mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); + objectList->reset(); + objectList->packetOrigin = ScriptController::getPacketOriginFromContextType(runtime.getContext().getContextType()); + objectList->addObjectLock(ptr, lockLevel); + objectList->sendObjectLock(); + } /* End of tes3mp addition */ @@ -266,11 +273,14 @@ namespace MWScript Send an ID_OBJECT_LOCK packet every time an object is unlocked through a script */ - mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); - objectList->reset(); - objectList->packetOrigin = ScriptController::getPacketOriginFromContextType(runtime.getContext().getContextType()); - objectList->addObjectLock(ptr, 0); - objectList->sendObjectLock(); + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn()) + { + mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); + objectList->reset(); + objectList->packetOrigin = ScriptController::getPacketOriginFromContextType(runtime.getContext().getContextType()); + objectList->addObjectLock(ptr, 0); + objectList->sendObjectLock(); + } /* End of tes3mp addition */ @@ -770,11 +780,14 @@ namespace MWScript Send an ID_OBJECT_DELETE packet every time an object is deleted through a script */ - mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); - objectList->reset(); - objectList->packetOrigin = ScriptController::getPacketOriginFromContextType(runtime.getContext().getContextType()); - objectList->addObjectDelete(ptr); - objectList->sendObjectDelete(); + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn()) + { + mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); + objectList->reset(); + objectList->packetOrigin = ScriptController::getPacketOriginFromContextType(runtime.getContext().getContextType()); + objectList->addObjectDelete(ptr); + objectList->sendObjectDelete(); + } /* End of tes3mp addition */ diff --git a/apps/openmw/mwscript/transformationextensions.cpp b/apps/openmw/mwscript/transformationextensions.cpp index 8f3dca009..8594b6fc2 100644 --- a/apps/openmw/mwscript/transformationextensions.cpp +++ b/apps/openmw/mwscript/transformationextensions.cpp @@ -63,8 +63,7 @@ namespace MWScript Prevent players from changing their own scale - Send an ID_OBJECT_SCALE every time an object's - scale is changed through a script + Send an ID_OBJECT_SCALE every time an object's scale is changed through a script */ if (ptr == MWMechanics::getPlayer()) { @@ -599,19 +598,22 @@ namespace MWScript Send an ID_OBJECT_PLACE or ID_OBJECT_SPAWN packet every time an object is placed in the world through a script */ - mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); - objectList->reset(); - objectList->packetOrigin = ScriptController::getPacketOriginFromContextType(runtime.getContext().getContextType()); - - if (ptr.getClass().isActor()) - { - objectList->addObjectSpawn(ptr); - objectList->sendObjectSpawn(); - } - else + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn()) { - objectList->addObjectPlace(ptr); - objectList->sendObjectPlace(); + mwmp::ObjectList *objectList = mwmp::Main::get().getNetworking()->getObjectList(); + objectList->reset(); + objectList->packetOrigin = ScriptController::getPacketOriginFromContextType(runtime.getContext().getContextType()); + + if (ptr.getClass().isActor()) + { + objectList->addObjectSpawn(ptr); + objectList->sendObjectSpawn(); + } + else + { + objectList->addObjectPlace(ptr); + objectList->sendObjectPlace(); + } } /* End of tes3mp addition diff --git a/apps/openmw/mwworld/scene.cpp b/apps/openmw/mwworld/scene.cpp index b93753fc5..ef0ef4031 100644 --- a/apps/openmw/mwworld/scene.cpp +++ b/apps/openmw/mwworld/scene.cpp @@ -489,9 +489,9 @@ namespace MWWorld Start of tes3mp addition Send an ID_PLAYER_CELL_STATE packet with all cell states stored in LocalPlayer - and then clear them, but only if the player has finished character generation + and then clear them, but only if the player is logged in on the server */ - if (mwmp::Main::get().getLocalPlayer()->hasFinishedCharGen()) + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn()) { mwmp::Main::get().getLocalPlayer()->sendCellStates(); mwmp::Main::get().getLocalPlayer()->clearCellStates(); @@ -631,9 +631,9 @@ namespace MWWorld Start of tes3mp addition Send an ID_PLAYER_CELL_STATE packet with all cell states stored in LocalPlayer - and then clear them, but only if the player has finished character generation + and then clear them, but only if the player is logged in on the server */ - if (mwmp::Main::get().getLocalPlayer()->hasFinishedCharGen()) + if (mwmp::Main::get().getLocalPlayer()->isLoggedIn()) { mwmp::Main::get().getLocalPlayer()->sendCellStates(); mwmp::Main::get().getLocalPlayer()->clearCellStates();