CCharEntity* CZoneEntities::GetCharByName(int8* name) { if (!m_charList.empty()) { for (EntityList_t::const_iterator it = m_charList.begin(); it != m_charList.end(); ++it) { CCharEntity* PCurrentChar = (CCharEntity*)it->second; if (stricmp(PCurrentChar->GetName(), name) == 0) { return PCurrentChar; } } } return nullptr; }
void CParty::AssignPartyRole(int8* MemberName, uint8 role) { DSP_DEBUG_BREAK_IF (m_PartyType != PARTY_PCS); for (uint32 i = 0; i < members.size(); ++i) { CCharEntity* PChar = (CCharEntity*)members.at(i); if (strcmp(MemberName, PChar->GetName()) == 0) { switch(role) { case 0: SetLeader(PChar); break; case 4: SetQuaterMaster(PChar); break; case 5: SetQuaterMaster(NULL); break; case 6: SetSyncTarget(PChar); break; } ReloadParty(); return; } } ShowError(CL_RED"The character with name <%s> isn't found in party\n" CL_RESET, MemberName); }
int32 map_cleanup(uint32 tick, CTaskMgr::CTask* PTask) { map_session_list_t::iterator it = map_session_list.begin(); while (it != map_session_list.end()) { map_session_data_t* map_session_data = it->second; CCharEntity* PChar = map_session_data->PChar; if ((time(nullptr) - map_session_data->last_update) > 5) { if (PChar != nullptr && !(PChar->nameflags.flags & FLAG_DC)) { PChar->nameflags.flags |= FLAG_DC; PChar->updatemask |= UPDATE_HP; if (PChar->status == STATUS_NORMAL) { PChar->loc.zone->SpawnPCs(PChar); } } if ((time(nullptr) - map_session_data->last_update) > map_config.max_time_lastupdate) { if (PChar != nullptr) { if (map_session_data->shuttingDown == 0) { //[Alliance] fix to stop server crashing: //if a party within an alliance only has 1 char (that char will be party leader) //if char then disconnects we need to tell the server about the alliance change if (PChar->PParty != nullptr && PChar->PParty->m_PAlliance != nullptr && PChar->PParty->GetLeader() == PChar) { if (PChar->PParty->members.size() == 1) { if (PChar->PParty->m_PAlliance->partyList.size() == 1) { PChar->PParty->m_PAlliance->dissolveAlliance(); } else { PChar->PParty->m_PAlliance->removeParty(PChar->PParty); } } } // uncharm pet if player d/c if (PChar->PPet != nullptr && PChar->PPet->objtype == TYPE_MOB) { petutils::DespawnPet(PChar); } PChar->StatusEffectContainer->SaveStatusEffects(true); ShowDebug(CL_CYAN"map_cleanup: %s timed out, closing session\n" CL_RESET, PChar->GetName()); PChar->status = STATUS_SHUTDOWN; PacketParser[0x00D](map_session_data, PChar, 0); } else { map_session_data->PChar->StatusEffectContainer->SaveStatusEffects(true); Sql_Query(SqlHandle, "DELETE FROM accounts_sessions WHERE charid = %u;", map_session_data->PChar->id); aFree(map_session_data->server_packet_data); delete map_session_data->PChar; delete map_session_data; map_session_data = nullptr; map_session_list.erase(it++); continue; } } else if (map_session_data->shuttingDown == 0) { ShowWarning(CL_YELLOW"map_cleanup: WHITHOUT CHAR timed out, session closed\n" CL_RESET); const int8* Query = "DELETE FROM accounts_sessions WHERE client_addr = %u AND client_port = %u"; Sql_Query(SqlHandle, Query, map_session_data->client_addr, map_session_data->client_port); aFree(map_session_data->server_packet_data); map_session_list.erase(it++); delete map_session_data; continue; } } } else if (PChar != nullptr && (PChar->nameflags.flags & FLAG_DC)) { PChar->nameflags.flags &= ~FLAG_DC; PChar->updatemask |= UPDATE_HP; PChar->pushPacket(new CCharUpdatePacket(PChar)); if (PChar->status == STATUS_NORMAL) { PChar->loc.zone->SpawnPCs(PChar); } charutils::SaveCharStats(PChar); } ++it; } return 0; }
int32 parse(int8* buff, size_t* buffsize, sockaddr_in* from, map_session_data_t* map_session_data) { // начало обработки входящего пакета int8* PacketData_Begin = &buff[FFXI_HEADER_SIZE]; int8* PacketData_End = &buff[*buffsize]; CCharEntity *PChar = map_session_data->PChar; uint16 SmallPD_Size = 0; uint16 SmallPD_Type = 0; uint16 SmallPD_Code = RBUFW(buff, 0); for (int8* SmallPD_ptr = PacketData_Begin; SmallPD_ptr + (RBUFB(SmallPD_ptr, 1) & 0xFE) * 2 <= PacketData_End && (RBUFB(SmallPD_ptr, 1) & 0xFE); SmallPD_ptr = SmallPD_ptr + SmallPD_Size * 2) { SmallPD_Size = (RBUFB(SmallPD_ptr, 1) & 0x0FE); SmallPD_Type = (RBUFW(SmallPD_ptr, 0) & 0x1FF); if (PacketSize[SmallPD_Type] == SmallPD_Size || PacketSize[SmallPD_Type] == 0) // Tests incoming packets for the correct size prior to processing { // если код текущего пакета меньше либо равен последнему полученному // или больше глобального то игнорируем пакет if ((RBUFW(SmallPD_ptr, 2) <= map_session_data->client_packet_id) || (RBUFW(SmallPD_ptr, 2) > SmallPD_Code)) { continue; } if (SmallPD_Type != 0x15) { ShowInfo("parse: %03hX | %04hX %04hX %02hX from user: %s\n", SmallPD_Type, RBUFW(SmallPD_ptr, 2), RBUFW(buff, 2), SmallPD_Size, PChar->GetName()); } if (PChar->loc.zone == nullptr && SmallPD_Type != 0x0A) { ShowWarning("This packet is unexpected from %s - Received %03hX earlier without matching 0x0A\n", PChar->GetName(), SmallPD_Type); } else { PacketParser[SmallPD_Type](map_session_data, PChar, CBasicPacket(reinterpret_cast<uint8*>(SmallPD_ptr))); } } else { ShowWarning("Bad packet size %03hX | %04hX %04hX %02hX from user: %s\n", SmallPD_Type, RBUFW(SmallPD_ptr, 2), RBUFW(buff, 2), SmallPD_Size, PChar->GetName()); } } ((CAICharNormal*)PChar->PBattleAI)->CheckActionAfterReceive(gettick()); map_session_data->client_packet_id = SmallPD_Code; // здесь мы проверяем, получил ли клиент предыдущий пакет // если не получил, то мы не создаем новый, а отправляем предыдущий if (RBUFW(buff, 2) != map_session_data->server_packet_id) { WBUFW(map_session_data->server_packet_data, 2) = SmallPD_Code; WBUFW(map_session_data->server_packet_data, 8) = (uint32)time(nullptr); g_PBuff = map_session_data->server_packet_data; *buffsize = map_session_data->server_packet_size; map_session_data->server_packet_data = buff; return -1; } // увеличиваем номер отправленного пакета только в случае отправки новых данных map_session_data->server_packet_id += 1; return 0; }
int32 parse(int8* buff, size_t* buffsize, sockaddr_in* from, map_session_data_t* map_session_data) { // начало обработки входящего пакета int8* PacketData_Begin = &buff[FFXI_HEADER_SIZE]; int8* PacketData_End = &buff[*buffsize]; CCharEntity *PChar = map_session_data->PChar; uint16 SmallPD_Size = 0; uint16 SmallPD_Type = 0; uint16 SmallPD_Code = RBUFW(buff,0); for(int8* SmallPD_ptr = PacketData_Begin; SmallPD_ptr + (RBUFB(SmallPD_ptr,1) & 0xFE)*2 <= PacketData_End && (RBUFB(SmallPD_ptr,1) & 0xFE); SmallPD_ptr = SmallPD_ptr + SmallPD_Size*2) { SmallPD_Size = (RBUFB(SmallPD_ptr,1) & 0x0FE); SmallPD_Type = (RBUFW(SmallPD_ptr,0) & 0x1FF); if(PacketSize[SmallPD_Type] == SmallPD_Size || PacketSize[SmallPD_Type] == 0) // Tests incoming packets for the correct size prior to processing { // если код текущего пакета меньше либо равен последнему полученному // или больше глобального то игнорируем пакет if ((RBUFW(SmallPD_ptr,2) <= map_session_data->client_packet_id) || (RBUFW(SmallPD_ptr,2) > SmallPD_Code)) { continue; } if (SmallPD_Type != 0x15) { ShowInfo("parse: %03hX | %04hX %04hX %02hX from user: %s\n", SmallPD_Type, RBUFW(SmallPD_ptr,2), RBUFW(buff,2), SmallPD_Size, PChar->GetName()); } if (PChar->loc.zone == NULL && SmallPD_Type != 0x0A) { ShowWarning("This packet is unexpected from %s - Received %03hX earlier without matching 0x0A\n", PChar->GetName(), SmallPD_Type); } else { PacketParser[SmallPD_Type](map_session_data, PChar, SmallPD_ptr); } } else { ShowWarning("Bad packet size %03hX | %04hX %04hX %02hX from user: %s\n", SmallPD_Type, RBUFW(SmallPD_ptr,2), RBUFW(buff,2), SmallPD_Size, PChar->GetName()); } } map_session_data->client_packet_id = SmallPD_Code; // здесь мы проверяем, получил ли клиент предыдущий пакет // если не получил, то мы не создаем новый, а отправляем предыдущий if (RBUFW(buff,2) != map_session_data->server_packet_id) { WBUFW(map_session_data->server_packet_data,2) = SmallPD_Code; WBUFW(map_session_data->server_packet_data,8) = (uint32)time(NULL); g_PBuff = map_session_data->server_packet_data; *buffsize = map_session_data->server_packet_size; map_session_data->server_packet_data = buff; return -1; } // увеличиваем номер отправленного пакета только в случае отправки новых данных map_session_data->server_packet_id += 1; // собираем большой пакет, состоящий из нескольких маленьких CBasicPacket* PSmallPacket; *buffsize = FFXI_HEADER_SIZE; while(!PChar->isPacketListEmpty() && *buffsize + PChar->firstPacketSize()*2 < map_config.buffer_size ) { PSmallPacket = PChar->popPacket(); PSmallPacket->setCode(map_session_data->server_packet_id); memcpy(buff+*buffsize, PSmallPacket, PSmallPacket->getSize()*2); *buffsize += PSmallPacket->getSize()*2; delete PSmallPacket; } return 0; }