From b4fb7e187a3db0bf79d6d0a10b71bbcd1ae7e538 Mon Sep 17 00:00:00 2001 From: VladimirMangos Date: Thu, 23 Oct 2008 06:07:03 +0400 Subject: [PATCH] [sql/updates/2008_10_23_01_mangos_command.sql sql/updates/2008_10_23_02_mangos_mangos_string.sql] Better 'pdump' commands args checking and related error output. --- sql/mangos.sql | 2 + sql/updates/2008_10_23_01_mangos_command.sql | 5 + sql/updates/2008_10_23_02_mangos_mangos_string.sql | 9 ++ sql/updates/Makefile.am | 4 + src/game/AccountMgr.h | 1 - src/game/Language.h | 8 +- src/game/Level3.cpp | 101 ++++++++++++++--- src/game/PlayerDump.cpp | 124 ++++++++++++--------- src/game/PlayerDump.h | 15 ++- 9 files changed, 201 insertions(+), 68 deletions(-) create mode 100644 sql/updates/2008_10_23_01_mangos_command.sql create mode 100644 sql/updates/2008_10_23_02_mangos_mangos_string.sql diff --git a/sql/mangos.sql b/sql/mangos.sql index da6ae59..85fdb13 100644 --- a/sql/mangos.sql +++ b/sql/mangos.sql @@ -342,6 +342,8 @@ INSERT INTO `command` VALUES ('npc textemote',3,'Syntax: .npc textemote #emoteid\r\n\r\nMake the selected creature to do textemote with an emote of id #emoteid.'), ('npc whisper',1,'Syntax: .npc whisper #playerguid #text\r\nMake the selected npc whisper #text to #playerguid.'), ('password',0,'Syntax: .password $old_password $new_password $new_password\r\n\r\nChange your account password.'), +('pdump write',3,'Syntax is: pdump write $filename $playerNameOrGUID\r\nWrite character dump with name/guid $playerNameOrGUID to file $filename.'), +('pdump load',3,'Syntax is: pdump load $filename $account [$newname] [$newguid]\r\nLoad character dump from dump file into character list of $account with saved or $newname, with saved (or first free) or $newguid guid.'), ('pinfo',2,'Syntax: .pinfo [$player_name] [rep]\r\n\r\nOutput account information for selected player or player find by $player_name. If \"rep\" parameter provided show reputation information for player.'), ('plimit',3,'Syntax: .plimit [#num|-1|-2|-3|reset|player|moderator|gamemaster|administrator]\r\n\r\nWithout arg show current player amount and security level limitations for login to server, with arg set player linit ($num > 0) or securiti limitation ($num < 0 or security leme name. With `reset` sets player limit to the one in the config file'), ('quest add',3,'Syntax: .quest add #quest_id\r\n\r\nAdd to character quest log quest #quest_id. Quest started from item can\'t be added by this command but correct .additem call provided in command output.'), diff --git a/sql/updates/2008_10_23_01_mangos_command.sql b/sql/updates/2008_10_23_01_mangos_command.sql new file mode 100644 index 0000000..8e2efdd --- /dev/null +++ b/sql/updates/2008_10_23_01_mangos_command.sql @@ -0,0 +1,5 @@ +DELETE FROM command WHERE name IN ('pdump write','pdump load'); + +INSERT INTO command VALUES +('pdump write',3,'Syntax is: pdump write $filename $playerNameOrGUID\r\nWrite character dump with name/guid $playerNameOrGUID to file $filename.'), +('pdump load',3,'Syntax is: pdump load $filename $account [$newname] [$newguid]\r\nLoad character dump from dump file into character list of $account with saved or $newname, with saved (or first free) or $newguid guid.'); diff --git a/sql/updates/2008_10_23_02_mangos_mangos_string.sql b/sql/updates/2008_10_23_02_mangos_mangos_string.sql new file mode 100644 index 0000000..ddf29e2 --- /dev/null +++ b/sql/updates/2008_10_23_02_mangos_mangos_string.sql @@ -0,0 +1,9 @@ +DELETE FROM mangos_string WHERE entry IN (1112,1113,1114,1115,1116,1117); + +INSERT INTO mangos_string VALUES +(1112,'Failed to open file: %s',NULL,NULL,NULL,NULL,NULL,NULL,NULL,NULL), +(1113,'Account %s (%u) have max amount allowed characters (client limit)',NULL,NULL,NULL,NULL,NULL,NULL,NULL,NULL), +(1114,'Dump file have broken data!',NULL,NULL,NULL,NULL,NULL,NULL,NULL,NULL), +(1115,'Invalid character name!',NULL,NULL,NULL,NULL,NULL,NULL,NULL,NULL), +(1116,'Invalid character guid!',NULL,NULL,NULL,NULL,NULL,NULL,NULL,NULL), +(1117,'Character guid %u in use!',NULL,NULL,NULL,NULL,NULL,NULL,NULL,NULL); diff --git a/sql/updates/Makefile.am b/sql/updates/Makefile.am index db3e7f5..b66f32d 100644 --- a/sql/updates/Makefile.am +++ b/sql/updates/Makefile.am @@ -101,6 +101,8 @@ pkgdata_DATA = \ 2008_10_21_03_mangos_command.sql \ 2008_10_22_01_mangos_quest_template.sql \ 2008_10_22_02_mangos_mangos_string.sql \ + 2008_10_23_01_mangos_command.sql \ + 2008_10_23_02_mangos_mangos_string.sql \ README ## Additional files to include when running 'make dist' @@ -183,4 +185,6 @@ EXTRA_DIST = \ 2008_10_21_03_mangos_command.sql \ 2008_10_22_01_mangos_quest_template.sql \ 2008_10_22_02_mangos_mangos_string.sql \ + 2008_10_23_01_mangos_command.sql \ + 2008_10_23_02_mangos_mangos_string.sql \ README diff --git a/src/game/AccountMgr.h b/src/game/AccountMgr.h index b54f863..1b74c71 100644 --- a/src/game/AccountMgr.h +++ b/src/game/AccountMgr.h @@ -48,7 +48,6 @@ class AccountMgr bool CheckPassword(uint32 accid, std::string passwd); uint32 GetId(std::string username); - uint32 GetIdByGUID(const uint64 &guid) const; uint32 GetSecurity(uint32 acc_id); bool GetName(uint32 acc_id, std::string &name); diff --git a/src/game/Language.h b/src/game/Language.h index 910f513..cd48754 100644 --- a/src/game/Language.h +++ b/src/game/Language.h @@ -676,7 +676,13 @@ enum MangosStrings LANG_SKILL_LIST_CONSOLE = 1109, LANG_CREATURE_LIST_CONSOLE = 1110, LANG_GO_LIST_CONSOLE = 1111, - // Room for more level 3 1112-1199 not used + LANG_FILE_OPEN_FAIL = 1112, + LANG_ACCOUNT_CHARACTER_LIST_FULL = 1113, + LANG_DUMP_BROKEN = 1114, + LANG_INVALID_CHARACTER_NAME = 1115, + LANG_INVALID_CHARACTER_GUID = 1116, + LANG_CHARACTER_GUID_IN_USE = 1117, + // Room for more level 3 1118-1199 not used // FREE IDS 1200-9999 diff --git a/src/game/Level3.cpp b/src/game/Level3.cpp index 57888f5..de6a100 100644 --- a/src/game/Level3.cpp +++ b/src/game/Level3.cpp @@ -5346,24 +5346,82 @@ bool ChatHandler::HandleLoadPDumpCommand(const char *args) SetSentErrorMessage(true); return false; } + } + + if(!accmgr.GetName(account_id,account_name)) + { + PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str()); + SetSentErrorMessage(true); + return false; + } - if(!accmgr.GetName(account_id,account_name)) + char* guid_str = NULL; + char* name_str = strtok(NULL, " "); + + std::string name; + if(name_str) + { + name = name_str; + // normalize the name if specified and check if it exists + if(!normalizePlayerName(name)) { - PSendSysMessage(LANG_ACCOUNT_NOT_EXIST,account_name.c_str()); + PSendSysMessage(LANG_INVALID_CHARACTER_NAME); + SetSentErrorMessage(true); + return false; + } + + if(!ObjectMgr::IsValidName(name,true)) + { + PSendSysMessage(LANG_INVALID_CHARACTER_NAME); SetSentErrorMessage(true); return false; } + + guid_str = strtok(NULL, " "); } - char * name = strtok(NULL, " "); - char * guid_str = name ? strtok(NULL, " ") : NULL; + uint32 guid = 0; - uint32 guid = guid_str ? atoi(guid_str) : 0; + if(guid_str) + { + guid = atoi(guid_str); + if(!guid) + { + PSendSysMessage(LANG_INVALID_CHARACTER_GUID); + SetSentErrorMessage(true); + return false; + } - if(PlayerDumpReader().LoadDump(file, account_id, name ? name : "", guid)) - PSendSysMessage(LANG_COMMAND_IMPORT_SUCCESS); - else - PSendSysMessage(LANG_COMMAND_IMPORT_FAILED); + if(objmgr.GetPlayerAccountIdByGUID(guid)) + { + PSendSysMessage(LANG_CHARACTER_GUID_IN_USE,guid); + SetSentErrorMessage(true); + return false; + } + } + + switch(PlayerDumpReader().LoadDump(file, account_id, name, guid)) + { + case DUMP_SUCCESS: + PSendSysMessage(LANG_COMMAND_IMPORT_SUCCESS); + break; + case DUMP_FILE_OPEN_ERROR: + PSendSysMessage(LANG_FILE_OPEN_FAIL,file); + SetSentErrorMessage(true); + return false; + case DUMP_FILE_BROKEN: + PSendSysMessage(LANG_DUMP_BROKEN,file); + SetSentErrorMessage(true); + return false; + case DUMP_TOO_MANY_CHARS: + PSendSysMessage(LANG_ACCOUNT_CHARACTER_LIST_FULL,account_name,account_id); + SetSentErrorMessage(true); + return false; + default: + PSendSysMessage(LANG_COMMAND_IMPORT_FAILED); + SetSentErrorMessage(true); + return false; + } return true; } @@ -5407,10 +5465,27 @@ bool ChatHandler::HandleWritePDumpCommand(const char *args) if(!guid) guid = atoi(p2); - if (PlayerDumpWriter().WriteDump(file, guid)) - PSendSysMessage(LANG_COMMAND_EXPORT_SUCCESS); - else - PSendSysMessage(LANG_COMMAND_EXPORT_FAILED); + if(!objmgr.GetPlayerAccountIdByGUID(guid)) + { + PSendSysMessage(LANG_PLAYER_NOT_FOUND); + SetSentErrorMessage(true); + return false; + } + + switch(PlayerDumpWriter().WriteDump(file, guid)) + { + case DUMP_SUCCESS: + PSendSysMessage(LANG_COMMAND_EXPORT_SUCCESS); + break; + case DUMP_FILE_OPEN_ERROR: + PSendSysMessage(LANG_FILE_OPEN_FAIL,file); + SetSentErrorMessage(true); + return false; + default: + PSendSysMessage(LANG_COMMAND_EXPORT_FAILED); + SetSentErrorMessage(true); + return false; + } return true; } diff --git a/src/game/PlayerDump.cpp b/src/game/PlayerDump.cpp index 03c7f62..33577d5 100644 --- a/src/game/PlayerDump.cpp +++ b/src/game/PlayerDump.cpp @@ -24,7 +24,7 @@ #include "ObjectMgr.h" // Character Dump tables -#define DUMP_TABLE_COUNT 20 +#define DUMP_TABLE_COUNT 19 struct DumpTable { @@ -256,11 +256,8 @@ void StoreGUID(QueryResult *result,uint32 data,uint32 field, std::set& g } // Writing - High-level functions -bool PlayerDumpWriter::DumpTable(std::string& dump, uint32 guid, char const*tableFrom, char const*tableTo, DumpTableType type) +void PlayerDumpWriter::DumpTable(std::string& dump, uint32 guid, char const*tableFrom, char const*tableTo, DumpTableType type) { - if (!tableFrom || !tableTo) - return false; - GUIDs const* guids = NULL; char const* fieldname = NULL; @@ -278,7 +275,7 @@ bool PlayerDumpWriter::DumpTable(std::string& dump, uint32 guid, char const*tabl // for guid set stop if set is empty if(guids && guids->empty()) - return true; // nothing to do + return; // nothing to do // setup for guids case start position GUIDs::const_iterator guids_itr; @@ -296,7 +293,7 @@ bool PlayerDumpWriter::DumpTable(std::string& dump, uint32 guid, char const*tabl QueryResult *result = CharacterDatabase.PQuery("SELECT * FROM %s WHERE %s", tableFrom, wherestr.c_str()); if(!result) - return false; + return; do { @@ -326,8 +323,6 @@ bool PlayerDumpWriter::DumpTable(std::string& dump, uint32 guid, char const*tabl delete result; } while(guids && guids_itr != guids->end()); // not set case iterate single time, set case iterate for all guids - - return true; } std::string PlayerDumpWriter::GetDump(uint32 guid) @@ -336,28 +331,29 @@ std::string PlayerDumpWriter::GetDump(uint32 guid) for(int i = 0; i < DUMP_TABLE_COUNT; i++) DumpTable(dump, guid, dumpTables[i].name, dumpTables[i].name, dumpTables[i].type); - // TODO: Add instance/group/gifts.. + // TODO: Add instance/group.. // TODO: Add a dump level option to skip some non-important tables return dump; } -bool PlayerDumpWriter::WriteDump(std::string file, uint32 guid) +DumpReturn PlayerDumpWriter::WriteDump(std::string file, uint32 guid) { FILE *fout = fopen(file.c_str(), "w"); - if (!fout) { sLog.outError("Failed to open file!\r\n"); return false; } + if (!fout) + return DUMP_FILE_OPEN_ERROR; std::string dump = GetDump(guid); fprintf(fout,"%s\n",dump.c_str()); fclose(fout); - return true; + return DUMP_SUCCESS; } // Reading - High-level functions -#define ROLLBACK {CharacterDatabase.RollbackTransaction(); fclose(fin); return false;} +#define ROLLBACK(DR) {CharacterDatabase.RollbackTransaction(); fclose(fin); return (DR);} -bool PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string name, uint32 guid) +DumpReturn PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string name, uint32 guid) { // check character count { @@ -370,12 +366,13 @@ bool PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string na delete result; if (charcount >= 10) - return false; + return DUMP_TOO_MANY_CHARS; } } + FILE *fin = fopen(file.c_str(), "r"); if(!fin) - return false; + return DUMP_FILE_OPEN_ERROR; QueryResult * result = NULL; char newguid[20], chraccount[20], newpetid[20], currpetid[20], lastpetid[20]; @@ -431,8 +428,7 @@ bool PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string na if(!fgets(buf, 32000, fin)) { if(feof(fin)) break; - sLog.outError("LoadPlayerDump: File read error!"); - ROLLBACK; + ROLLBACK(DUMP_FILE_BROKEN); } std::string line; line.assign(buf); @@ -446,7 +442,7 @@ bool PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string na if(tn.empty()) { sLog.outError("LoadPlayerDump: Can't extract table name from line: '%s'!", line.c_str()); - ROLLBACK; + ROLLBACK(DUMP_FILE_BROKEN); } DumpTableType type; @@ -463,27 +459,33 @@ bool PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string na if (i == DUMP_TABLE_COUNT) { sLog.outError("LoadPlayerDump: Unknown table: '%s'!", tn.c_str()); - ROLLBACK; + ROLLBACK(DUMP_FILE_BROKEN); } // change the data to server values switch(type) { case DTT_CHAR_TABLE: - if(!changenth(line, 1, newguid)) ROLLBACK; + if(!changenth(line, 1, newguid)) + ROLLBACK(DUMP_FILE_BROKEN); break; case DTT_CHARACTER: // character t. { - if(!changenth(line, 1, newguid)) ROLLBACK; + if(!changenth(line, 1, newguid)) + ROLLBACK(DUMP_FILE_BROKEN); // guid, data field:guid, items - if(!changenth(line, 2, chraccount)) ROLLBACK; + if(!changenth(line, 2, chraccount)) + ROLLBACK(DUMP_FILE_BROKEN); std::string vals = getnth(line, 3); - if(!changetoknth(vals, OBJECT_FIELD_GUID+1, newguid)) ROLLBACK; + if(!changetoknth(vals, OBJECT_FIELD_GUID+1, newguid)) + ROLLBACK(DUMP_FILE_BROKEN); for(uint16 field = PLAYER_FIELD_INV_SLOT_HEAD; field < PLAYER_FARSIGHT; field++) - if(!changetokGuid(vals, field+1, items, objmgr.m_hiItemGuid, true)) ROLLBACK; - if(!changenth(line, 3, vals.c_str())) ROLLBACK; + if(!changetokGuid(vals, field+1, items, objmgr.m_hiItemGuid, true)) + ROLLBACK(DUMP_FILE_BROKEN); + if(!changenth(line, 3, vals.c_str())) + ROLLBACK(DUMP_FILE_BROKEN); if (name == "") { // check if the original name already exists @@ -495,38 +497,50 @@ bool PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string na { delete result; // rename on login: `at_login` field 30 in raw field list - if(!changenth(line, 30, "1")) ROLLBACK; + if(!changenth(line, 30, "1")) + ROLLBACK(DUMP_FILE_BROKEN); } } - else if(!changenth(line, 4, name.c_str())) ROLLBACK; + else if(!changenth(line, 4, name.c_str())) + ROLLBACK(DUMP_FILE_BROKEN); break; } case DTT_INVENTORY: // character_inventory t. { - if(!changenth(line, 1, newguid)) ROLLBACK; + if(!changenth(line, 1, newguid)) + ROLLBACK(DUMP_FILE_BROKEN); // bag, item - if(!changeGuid(line, 2, items, objmgr.m_hiItemGuid, true)) ROLLBACK; - if(!changeGuid(line, 4, items, objmgr.m_hiItemGuid)) ROLLBACK; + if(!changeGuid(line, 2, items, objmgr.m_hiItemGuid, true)) + ROLLBACK(DUMP_FILE_BROKEN); + if(!changeGuid(line, 4, items, objmgr.m_hiItemGuid)) + ROLLBACK(DUMP_FILE_BROKEN); break; } case DTT_ITEM: // item_instance t. { // item, owner, data field:item, owner guid - if(!changeGuid(line, 1, items, objmgr.m_hiItemGuid)) ROLLBACK; - if(!changenth(line, 2, newguid)) ROLLBACK; + if(!changeGuid(line, 1, items, objmgr.m_hiItemGuid)) + ROLLBACK(DUMP_FILE_BROKEN); + if(!changenth(line, 2, newguid)) + ROLLBACK(DUMP_FILE_BROKEN); std::string vals = getnth(line,3); - if(!changetokGuid(vals, OBJECT_FIELD_GUID+1, items, objmgr.m_hiItemGuid)) ROLLBACK; - if(!changetoknth(vals, ITEM_FIELD_OWNER+1, newguid)) ROLLBACK; - if(!changenth(line, 3, vals.c_str())) ROLLBACK; + if(!changetokGuid(vals, OBJECT_FIELD_GUID+1, items, objmgr.m_hiItemGuid)) + ROLLBACK(DUMP_FILE_BROKEN); + if(!changetoknth(vals, ITEM_FIELD_OWNER+1, newguid)) + ROLLBACK(DUMP_FILE_BROKEN); + if(!changenth(line, 3, vals.c_str())) + ROLLBACK(DUMP_FILE_BROKEN); break; } case DTT_ITEM_GIFT: // character_gift { // guid,item_guid, - if(!changenth(line, 1, newguid)) ROLLBACK; - if(!changeGuid(line, 2, items, objmgr.m_hiItemGuid)) ROLLBACK; + if(!changenth(line, 1, newguid)) + ROLLBACK(DUMP_FILE_BROKEN); + if(!changeGuid(line, 2, items, objmgr.m_hiItemGuid)) + ROLLBACK(DUMP_FILE_BROKEN); break; } case DTT_PET: // character_pet t @@ -548,8 +562,10 @@ bool PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string na } // item, entry, owner, ... - if(!changenth(line, 1, newpetid)) ROLLBACK; - if(!changenth(line, 3, newguid)) ROLLBACK; + if(!changenth(line, 1, newpetid)) + ROLLBACK(DUMP_FILE_BROKEN); + if(!changenth(line, 3, newguid)) + ROLLBACK(DUMP_FILE_BROKEN); break; } @@ -559,27 +575,34 @@ bool PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string na // lookup currpetid and match to new inserted pet id std::map :: const_iterator petids_iter = petids.find(atoi(currpetid)); - if(petids_iter == petids.end()) ROLLBACK; // couldn't find new inserted id + if(petids_iter == petids.end()) // couldn't find new inserted id + ROLLBACK(DUMP_FILE_BROKEN); snprintf(newpetid, 20, "%d", petids_iter->second); - if(!changenth(line, 1, newpetid)) ROLLBACK; + if(!changenth(line, 1, newpetid)) + ROLLBACK(DUMP_FILE_BROKEN); break; } case DTT_MAIL: // mail { // id,messageType,stationery,sender,receiver - if(!changeGuid(line, 1, mails, objmgr.m_mailid)) ROLLBACK; - if(!changenth(line, 5, newguid)) ROLLBACK; + if(!changeGuid(line, 1, mails, objmgr.m_mailid)) + ROLLBACK(DUMP_FILE_BROKEN); + if(!changenth(line, 5, newguid)) + ROLLBACK(DUMP_FILE_BROKEN); break; } case DTT_MAIL_ITEM: // mail_items { // mail_id,item_guid,item_template,receiver - if(!changeGuid(line, 1, mails, objmgr.m_mailid)) ROLLBACK; - if(!changeGuid(line, 2, items, objmgr.m_hiItemGuid)) ROLLBACK; - if(!changenth(line, 4, newguid)) ROLLBACK; + if(!changeGuid(line, 1, mails, objmgr.m_mailid)) + ROLLBACK(DUMP_FILE_BROKEN); + if(!changeGuid(line, 2, items, objmgr.m_hiItemGuid)) + ROLLBACK(DUMP_FILE_BROKEN); + if(!changenth(line, 4, newguid)) + ROLLBACK(DUMP_FILE_BROKEN); break; } default: @@ -587,7 +610,8 @@ bool PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string na break; } - if(!CharacterDatabase.Execute(line.c_str())) ROLLBACK; + if(!CharacterDatabase.Execute(line.c_str())) + ROLLBACK(DUMP_FILE_BROKEN); } CharacterDatabase.CommitTransaction(); @@ -600,5 +624,5 @@ bool PlayerDumpReader::LoadDump(std::string file, uint32 account, std::string na fclose(fin); - return true; + return DUMP_SUCCESS; } diff --git a/src/game/PlayerDump.h b/src/game/PlayerDump.h index 0df90b8..2e83102 100644 --- a/src/game/PlayerDump.h +++ b/src/game/PlayerDump.h @@ -71,6 +71,15 @@ enum DumpTableType DTT_ITEM_TEXT, // <- item_text // item_text }; +enum DumpReturn +{ + DUMP_SUCCESS, + DUMP_FILE_OPEN_ERROR, + DUMP_TOO_MANY_CHARS, + DUMP_UNEXPECTED_END, + DUMP_FILE_BROKEN, +}; + class PlayerDump { protected: @@ -83,11 +92,11 @@ class PlayerDumpWriter : public PlayerDump PlayerDumpWriter() {} std::string GetDump(uint32 guid); - bool WriteDump(std::string file, uint32 guid); + DumpReturn WriteDump(std::string file, uint32 guid); private: typedef std::set GUIDs; - bool DumpTable(std::string& dump, uint32 guid, char const*tableFrom, char const*tableTo, DumpTableType type); + void DumpTable(std::string& dump, uint32 guid, char const*tableFrom, char const*tableTo, DumpTableType type); std::string GenerateWhereStr(char const* field, GUIDs const& guids, GUIDs::const_iterator& itr); std::string GenerateWhereStr(char const* field, uint32 guid); @@ -102,7 +111,7 @@ class PlayerDumpReader : public PlayerDump public: PlayerDumpReader() {} - bool LoadDump(std::string file, uint32 account, std::string name, uint32 guid); + DumpReturn LoadDump(std::string file, uint32 account, std::string name, uint32 guid); }; #endif -- 2.11.4.GIT