diff --git a/common/rulesys.cpp b/common/rulesys.cpp index 0fbd2fa89..ea3d707cf 100644 --- a/common/rulesys.cpp +++ b/common/rulesys.cpp @@ -34,8 +34,8 @@ const char *RuleManager::s_categoryNames[_CatCount + 1] = { "InvalidCategory" }; -const RuleManager::RuleInfo RuleManager::s_RuleInfo[IntRuleCount + RealRuleCount + BoolRuleCount + 1] = { - /* this is done in three steps so we can reliably get to them by index*/ +const RuleManager::RuleInfo RuleManager::s_RuleInfo[IntRuleCount + RealRuleCount + BoolRuleCount + StringRuleCount + 1] = { + /* this is done in three steps, so we can reliably get to them by index*/ #define RULE_INT(category_name, rule_name, default_value, notes) \ { #category_name ":" #rule_name, Category__##category_name, IntRule, Int__##rule_name, notes }, #include "ruletypes.h" @@ -45,6 +45,9 @@ const RuleManager::RuleInfo RuleManager::s_RuleInfo[IntRuleCount + RealRuleCount #define RULE_BOOL(category_name, rule_name, default_value, notes) \ { #category_name ":" #rule_name, Category__##category_name, BoolRule, Bool__##rule_name, notes }, #include "ruletypes.h" + #define RULE_STRING(category_name, rule_name, default_value, notes) \ + { #category_name ":" #rule_name, Category__##category_name, StringRule, String__##rule_name, notes }, + #include "ruletypes.h" { "Invalid Rule", _CatCount, IntRule } }; @@ -114,6 +117,9 @@ bool RuleManager::GetRule(const std::string &rule_name, std::string &rule_value) case BoolRule: rule_value = m_RuleBoolValues[index] ? "true" : "false"; break; + case StringRule: + rule_value = m_RuleStringValues[index]; + break; } return true; @@ -152,6 +158,10 @@ bool RuleManager::SetRule(const std::string &rule_name, const std::string &rule_ m_RuleBoolValues[index] = static_cast(Strings::ToBool(rule_value)); LogRules("Set rule [{}] to value [{}]", rule_name, m_RuleBoolValues[index] == 1 ? "true" : "false"); break; + case StringRule: + m_RuleStringValues[index] = rule_value; + LogRules("Set rule [{}] to value [{}]", rule_name, rule_value); + break; } if (db_save) { @@ -215,11 +225,13 @@ std::string RuleManager::_GetRuleName(RuleType type, uint16 index) { return s_RuleInfo[index + IntRuleCount].name; case BoolRule: return s_RuleInfo[index + IntRuleCount + RealRuleCount].name; + case StringRule: + return s_RuleInfo[index + IntRuleCount + RealRuleCount + StringRuleCount].name; default: break; } - return s_RuleInfo[IntRuleCount + RealRuleCount + BoolRuleCount].name; + return s_RuleInfo[IntRuleCount + RealRuleCount + BoolRuleCount + StringRuleCount].name; } //assumes index is valid! @@ -231,11 +243,13 @@ const std::string &RuleManager::_GetRuleNotes(RuleType type, uint16 index) { return s_RuleInfo[index + IntRuleCount].notes; case BoolRule: return s_RuleInfo[index + IntRuleCount + RealRuleCount].notes; + case StringRule: + return s_RuleInfo[index + IntRuleCount + RealRuleCount + StringRuleCount].notes; default: break; } - return s_RuleInfo[IntRuleCount + RealRuleCount + BoolRuleCount].notes; + return s_RuleInfo[IntRuleCount + RealRuleCount + BoolRuleCount + StringRuleCount].notes; } bool RuleManager::LoadRules(Database *db, const std::string &rule_set_name, bool reload) { @@ -343,6 +357,10 @@ void RuleManager::SaveRules(Database *db, const std::string &rule_set_name) { for (i = 0; i < BoolRuleCount; i++) { _SaveRule(db, BoolRule, i); } + + for (i = 0; i < StringRuleCount; i++) { + _SaveRule(db, StringRule, i); + } } void RuleManager::_SaveRule(Database *db, RuleType type, uint16 index) { @@ -367,6 +385,9 @@ void RuleManager::_SaveRule(Database *db, RuleType type, uint16 index) { case BoolRule: rule_value = m_RuleBoolValues[index] ? "true" : "false"; break; + case StringRule: + rule_value = m_RuleStringValues[index]; + break; } const auto& rule_notes = _GetRuleNotes(type, index); @@ -446,6 +467,10 @@ bool RuleManager::UpdateInjectedRules(Database *db, const std::string &rule_set_ rule_data[r.name].first = fmt::format("{}", m_RuleBoolValues[r.rule_index] ? "true" : "false"); rule_data[r.name].second = &r.notes; break; + case StringRule: + rule_data[r.name].first = m_RuleStringValues[r.rule_index]; + rule_data[r.name].second = &r.notes; + break; default: break; } @@ -552,7 +577,7 @@ bool RuleManager::RestoreRuleNotes(Database *db) } } - return s_RuleInfo[IntRuleCount + RealRuleCount + BoolRuleCount]; + return s_RuleInfo[IntRuleCount + RealRuleCount + BoolRuleCount + StringRuleCount]; }(e.rule_name); if (Strings::Contains(rule.name, e.rule_name)) { @@ -617,3 +642,8 @@ bool RuleManager::GetBoolRule(RuleManager::BoolType t) const { return m_RuleBoolValues[t] == 1; } + +std::string RuleManager::GetStringRule(RuleManager::StringType t) const +{ + return m_RuleStringValues[t]; +} diff --git a/common/rulesys.h b/common/rulesys.h index 403f611e4..eab3af6b8 100644 --- a/common/rulesys.h +++ b/common/rulesys.h @@ -23,6 +23,7 @@ * - RuleI(category, rule) -> fetch an integer rule's value * - RuleR(category, rule) -> fetch a real (float) rule's value * - RuleB(category, rule) -> fetch a boolean/flag rule's value +* - RuleS(category, rule) -> fetch a string rule's value * */ @@ -35,6 +36,8 @@ RuleManager::Instance()->GetRealRule( RuleManager::Real__##rule_name ) #define RuleB(category_name, rule_name) \ RuleManager::Instance()->GetBoolRule( RuleManager::Bool__##rule_name ) +#define RuleS(category_name, rule_name) \ + RuleManager::Instance()->GetStringRule( RuleManager::String__##rule_name ) #include @@ -81,6 +84,17 @@ public: static const int BoolRuleCount = static_cast(_BoolRuleCount); + typedef enum { +#define RULE_STRING(category_name, rule_name, default_value, notes) \ + String__##rule_name, + +#include "ruletypes.h" + + _StringRuleCount + } StringType; + + static const int StringRuleCount = static_cast(_StringRuleCount); + typedef enum { #define RULE_CATEGORY(category_name) \ Category__##category_name, @@ -99,45 +113,49 @@ public: static const IntType InvalidInt = _IntRuleCount; static const RealType InvalidReal = _RealRuleCount; static const BoolType InvalidBool = _BoolRuleCount; + static const StringType InvalidString = _StringRuleCount; static const CategoryType InvalidCategory = _CatCount; - static const uint32 RulesCount = IntRuleCount + RealRuleCount + BoolRuleCount; + static const uint32 RulesCount = IntRuleCount + RealRuleCount + BoolRuleCount + StringRuleCount; //fetch routines, you should generally use the Rule* macros instead of this int GetIntRule(IntType t) const; float GetRealRule(RealType t) const; bool GetBoolRule(BoolType t) const; + std::string GetStringRule(StringType t) const; //management routines static std::string GetRuleName(IntType t) { return s_RuleInfo[static_cast(t)].name; } static std::string GetRuleName(RealType t) { return s_RuleInfo[static_cast(t) + IntRuleCount].name; } static std::string GetRuleName(BoolType t) { return s_RuleInfo[static_cast(t) + IntRuleCount + RealRuleCount].name; } - static const std::string &GetRuleNotes(IntType t) { return s_RuleInfo[static_cast(t)].notes; } - static const std::string &GetRuleNotes(RealType t) { return s_RuleInfo[static_cast(t) + IntRuleCount].notes; } - static const std::string &GetRuleNotes(BoolType t) { return s_RuleInfo[static_cast(t) + IntRuleCount + RealRuleCount].notes; } + static std::string GetRuleName(StringType t) { return s_RuleInfo[static_cast(t) + IntRuleCount + RealRuleCount + StringRuleCount].name; } + static const std::string& GetRuleNotes(IntType t) { return s_RuleInfo[static_cast(t)].notes; } + static const std::string& GetRuleNotes(RealType t) { return s_RuleInfo[static_cast(t) + IntRuleCount].notes; } + static const std::string& GetRuleNotes(BoolType t) { return s_RuleInfo[static_cast(t) + IntRuleCount + RealRuleCount].notes; } + static const std::string& GetRuleNotes(StringType t) { return s_RuleInfo[static_cast(t) + IntRuleCount + RealRuleCount + StringRuleCount].notes; } static uint32 CountRules() { return RulesCount; } - static CategoryType FindCategory(const std::string &category_name); - bool ListRules(const std::string &category_name, std::vector &l); - bool ListCategories(std::vector &l); - bool GetRule(const std::string &rule_name, std::string &rule_value); + static CategoryType FindCategory(const std::string& category_name); + bool ListRules(const std::string& category_name, std::vector& l); + bool ListCategories(std::vector& l); + bool GetRule(const std::string& rule_name, std::string& rule_value); bool SetRule( - const std::string &rule_name, - const std::string &rule_value, - Database *db = nullptr, + const std::string& rule_name, + const std::string& rule_value, + Database* db = nullptr, bool db_save = false, bool reload = false ); int GetActiveRulesetID() const { return m_activeRuleset; } std::string GetActiveRuleset() const { return m_activeName; } - static bool ListRulesets(Database *db, std::map &l); + static bool ListRulesets(Database* db, std::map& l); void ResetRules(bool reload = false); - bool LoadRules(Database *db, const std::string &rule_set_name, bool reload = false); - void SaveRules(Database *db, const std::string &rule_set_name); - bool UpdateInjectedRules(Database *db, const std::string &rule_set_name, bool quiet_update = false); - bool UpdateOrphanedRules(Database *db, bool quiet_update = false); - bool RestoreRuleNotes(Database *db); + bool LoadRules(Database* db, const std::string& rule_set_name, bool reload = false); + void SaveRules(Database* db, const std::string& rule_set_name); + bool UpdateInjectedRules(Database* db, const std::string& rule_set_name, bool quiet_update = false); + bool UpdateOrphanedRules(Database* db, bool quiet_update = false); + bool RestoreRuleNotes(Database* db); private: RuleManager(); @@ -147,21 +165,23 @@ private: int m_activeRuleset; std::string m_activeName; - int m_RuleIntValues[IntRuleCount]; - float m_RuleRealValues[RealRuleCount]; - uint32 m_RuleBoolValues[BoolRuleCount]; + int m_RuleIntValues[IntRuleCount]; + float m_RuleRealValues[RealRuleCount]; + uint32 m_RuleBoolValues[BoolRuleCount]; + std::string m_RuleStringValues[StringRuleCount]; typedef enum { IntRule, RealRule, - BoolRule + BoolRule, + StringRule } RuleType; - static bool _FindRule(const std::string &rule_name, RuleType &type_into, uint16 &index_into); + static bool _FindRule(const std::string& rule_name, RuleType& type_into, uint16& index_into); static std::string _GetRuleName(RuleType type, uint16 index); - static const std::string &_GetRuleNotes(RuleType type, uint16 index); - static int _FindOrCreateRuleset(Database *db, const std::string &rule_set_name); - void _SaveRule(Database *db, RuleType type, uint16 index); + static const std::string& _GetRuleNotes(RuleType type, uint16 index); + static int _FindOrCreateRuleset(Database* db, const std::string& rule_set_name); + void _SaveRule(Database* db, RuleType type, uint16 index); static const char* s_categoryNames[]; typedef struct { diff --git a/common/ruletypes.h b/common/ruletypes.h index 65ee545b9..68eb5cd35 100644 --- a/common/ruletypes.h +++ b/common/ruletypes.h @@ -28,6 +28,9 @@ #ifndef RULE_BOOL #define RULE_BOOL(cat, rule, default_value, notes) #endif +#ifndef RULE_STRING +#define RULE_STRING(cat, rule, default_value, notes) +#endif #ifndef RULE_CATEGORY_END #define RULE_CATEGORY_END() #endif @@ -324,6 +327,8 @@ RULE_INT(World, MaximumQuestErrors, 30, "Changes the maximum number of quest err RULE_INT(World, BootHour, 0, "Sets the in-game hour world will set when it first boots. 0-24 are valid options, where 0 disables this rule") RULE_BOOL(World, UseItemLinksForKeyRing, false, "Uses item links for Key Ring Listing instead of item name") RULE_BOOL(World, UseOldShadowKnightClassExport, true, "Disable to have Shadowknight show as Shadow Knight (live-like)") +RULE_STRING(World, IPExemptionZones, "", "Comma-delimited list of zones to exclude from IP-limit checks. Empty string to disable.") +RULE_STRING(World, MOTD, "", "Server MOTD sent on login, change from empty to have this be used instead of variables table 'motd' value") RULE_CATEGORY_END() RULE_CATEGORY(Zone) @@ -951,4 +956,5 @@ RULE_CATEGORY_END() #undef RULE_INT #undef RULE_REAL #undef RULE_BOOL +#undef RULE_STRING #undef RULE_CATEGORY_END diff --git a/world/client.cpp b/world/client.cpp index b39a00a89..30c0c266d 100644 --- a/world/client.cpp +++ b/world/client.cpp @@ -647,7 +647,7 @@ bool Client::HandleGenerateRandomNamePacket(const EQApplicationPacket *app) { if (database.CheckNameFilter(newName)) { std::string query = StringFormat("SELECT `name` FROM `character_data` WHERE `name` = '%s'", newName); auto res = database.QueryDatabase(query); - if (res.Success() && res.RowCount() == 0) { + if (res.Success() && res.RowCount() == 0) { unique = true; } } @@ -887,14 +887,19 @@ bool Client::HandleEnterWorldPacket(const EQApplicationPacket *app) { } auto outapp = new EQApplicationPacket(OP_MOTD); - std::string motd_message; - if (database.GetVariable("MOTD", motd_message)) { - outapp->size = motd_message.length() + 1; + std::string motd = RuleS(World, MOTD); + if (!motd.empty()) { + outapp->size = motd.length() + 1; outapp->pBuffer = new uchar[outapp->size]; memset(outapp->pBuffer, 0, outapp->size); - strcpy((char*)outapp->pBuffer, motd_message.c_str()); + strcpy((char*) outapp->pBuffer, motd.c_str()); + } else if (database.GetVariable("MOTD", motd)) { + outapp->size = motd.length() + 1; + outapp->pBuffer = new uchar[outapp->size]; + memset(outapp->pBuffer, 0, outapp->size); + strcpy((char*) outapp->pBuffer, motd.c_str()); } else { // Null Message of the Day. :) - outapp->size = 1; + outapp->size = 1; outapp->pBuffer = new uchar[outapp->size]; outapp->pBuffer[0] = 0; } diff --git a/world/clientlist.cpp b/world/clientlist.cpp index 58b8f558d..5936fc1fb 100644 --- a/world/clientlist.cpp +++ b/world/clientlist.cpp @@ -96,6 +96,15 @@ void ClientList::GetCLEIP(uint32 in_ip) { while (iterator.MoreElements()) { cle = iterator.GetData(); + + const auto zones = Strings::Split(RuleS(World, IPExemptionZones), ","); + for (const auto &z : zones) { + if (Strings::ToUnsignedInt(z) == cle->zone()) { + iterator.Advance(); + continue; + } + } + if ( cle->GetIP() == in_ip && ( diff --git a/world/zoneserver.cpp b/world/zoneserver.cpp index a3bfa2d4d..6ea739d3c 100644 --- a/world/zoneserver.cpp +++ b/world/zoneserver.cpp @@ -1100,7 +1100,7 @@ void ZoneServer::HandleMessage(uint16 opcode, const EQ::Net::Packet &p) { } auto smotd = (ServerMotd_Struct*) pack->pBuffer; - database.SetVariable("MOTD", smotd->motd); + RuleManager::Instance()->SetRule("MOTD", smotd->motd, &database, true, true); zoneserver_list.SendPacket(pack); break; } diff --git a/zone/lua_general.cpp b/zone/lua_general.cpp index e377fdb79..3ed23a411 100644 --- a/zone/lua_general.cpp +++ b/zone/lua_general.cpp @@ -5653,6 +5653,10 @@ bool get_ruleb(int rule) { return RuleManager::Instance()->GetBoolRule((RuleManager::BoolType)rule); } +std::string get_rules(int rule) { + return RuleManager::Instance()->GetStringRule((RuleManager::StringType)rule); +} + luabind::scope lua_register_general() { return luabind::namespace_("eq") [( @@ -7244,7 +7248,13 @@ luabind::scope lua_register_rules_const() { #define RULE_BOOL(cat, rule, default_value, notes) \ luabind::value(#rule, RuleManager::Bool__##rule), #include "../common/ruletypes.h" - luabind::value("_BoolRuleCount", RuleManager::_BoolRuleCount) + luabind::value("_BoolRuleCount", RuleManager::_BoolRuleCount), +#undef RULE_BOOL +#define RULE_STRING(cat, rule, default_value, notes) \ + luabind::value(#rule, RuleManager::String__##rule), +#include "../common/ruletypes.h" + luabind::value("_StringRuleCount", RuleManager::_StringRuleCount) +#undef RULE_STRING )]; } @@ -7269,6 +7279,13 @@ luabind::scope lua_register_ruleb() { ]; } +luabind::scope lua_register_rules() { + return luabind::namespace_("RuleS") + [ + luabind::def("Get", &get_rules) + ]; +} + luabind::scope lua_register_journal_speakmode() { return luabind::class_("SpeakMode") .enum_("constants")