diff --git a/server/channelserver/handlers_achievement.go b/server/channelserver/handlers_achievement.go index d6ab68edb..ff909b99e 100644 --- a/server/channelserver/handlers_achievement.go +++ b/server/channelserver/handlers_achievement.go @@ -154,6 +154,9 @@ func handleMsgMhfResetAchievement(s *Session, p mhfpacket.MHFPacket) {} func handleMsgMhfAddAchievement(s *Session, p mhfpacket.MHFPacket) { pkt := p.(*mhfpacket.MsgMhfAddAchievement) + if pkt.AchievementID > 32 { + return + } var exists int err := s.server.db.QueryRow("SELECT id FROM achievements WHERE id=$1", s.charID).Scan(&exists) diff --git a/server/channelserver/handlers_goocoo.go b/server/channelserver/handlers_goocoo.go index 151ed88ca..9cef971b2 100644 --- a/server/channelserver/handlers_goocoo.go +++ b/server/channelserver/handlers_goocoo.go @@ -41,6 +41,9 @@ func handleMsgMhfEnumerateGuacot(s *Session, p mhfpacket.MHFPacket) { func handleMsgMhfUpdateGuacot(s *Session, p mhfpacket.MHFPacket) { pkt := p.(*mhfpacket.MsgMhfUpdateGuacot) for _, goocoo := range pkt.Goocoos { + if goocoo.Index > 4 { + continue + } if goocoo.Data1[0] == 0 { if _, err := s.server.db.Exec(fmt.Sprintf("UPDATE goocoo SET goocoo%d=NULL WHERE id=$1", goocoo.Index), s.charID); err != nil { s.logger.Error("Failed to clear goocoo slot", zap.Error(err)) diff --git a/server/channelserver/handlers_house.go b/server/channelserver/handlers_house.go index 74e5510c3..5d608a2c8 100644 --- a/server/channelserver/handlers_house.go +++ b/server/channelserver/handlers_house.go @@ -277,6 +277,10 @@ func handleMsgMhfLoadDecoMyset(s *Session, p mhfpacket.MHFPacket) { func handleMsgMhfSaveDecoMyset(s *Session, p mhfpacket.MHFPacket) { pkt := p.(*mhfpacket.MsgMhfSaveDecoMyset) + if len(pkt.RawDataPayload) < 3 { + doAckSimpleSucceed(s, pkt.AckHandle, make([]byte, 4)) + return + } var temp []byte err := s.server.db.QueryRow("SELECT decomyset FROM characters WHERE id = $1", s.charID).Scan(&temp) if err != nil { @@ -432,6 +436,9 @@ func handleMsgMhfOperateWarehouse(s *Session, p mhfpacket.MHFPacket) { case 1: bf.WriteUint8(0) case 2: + if pkt.BoxIndex > 9 { + break + } switch pkt.BoxType { case 0: if _, err := s.server.db.Exec(fmt.Sprintf("UPDATE warehouse SET item%dname=$1 WHERE character_id=$2", pkt.BoxIndex), pkt.Name, s.charID); err != nil { @@ -472,6 +479,9 @@ func warehouseGetItems(s *Session, index uint8) []mhfitem.MHFItemStack { initializeWarehouse(s) var data []byte var items []mhfitem.MHFItemStack + if index > 10 { + return items + } _ = s.server.db.QueryRow(fmt.Sprintf(`SELECT item%d FROM warehouse WHERE character_id=$1`, index), s.charID).Scan(&data) if len(data) > 0 { box := byteframe.NewByteFrameFromBytes(data) @@ -487,6 +497,9 @@ func warehouseGetItems(s *Session, index uint8) []mhfitem.MHFItemStack { func warehouseGetEquipment(s *Session, index uint8) []mhfitem.MHFEquipment { var data []byte var equipment []mhfitem.MHFEquipment + if index > 10 { + return equipment + } _ = s.server.db.QueryRow(fmt.Sprintf(`SELECT equip%d FROM warehouse WHERE character_id=$1`, index), s.charID).Scan(&data) if len(data) > 0 { box := byteframe.NewByteFrameFromBytes(data) @@ -519,6 +532,10 @@ func handleMsgMhfEnumerateWarehouse(s *Session, p mhfpacket.MHFPacket) { func handleMsgMhfUpdateWarehouse(s *Session, p mhfpacket.MHFPacket) { pkt := p.(*mhfpacket.MsgMhfUpdateWarehouse) + if pkt.BoxIndex > 10 { + doAckSimpleFail(s, pkt.AckHandle, make([]byte, 4)) + return + } saveStart := time.Now() var err error diff --git a/server/channelserver/handlers_items.go b/server/channelserver/handlers_items.go index 0bcd5bcd2..475111b42 100644 --- a/server/channelserver/handlers_items.go +++ b/server/channelserver/handlers_items.go @@ -225,6 +225,10 @@ func handleMsgMhfGetCogInfo(s *Session, p mhfpacket.MHFPacket) {} func handleMsgMhfCheckWeeklyStamp(s *Session, p mhfpacket.MHFPacket) { pkt := p.(*mhfpacket.MsgMhfCheckWeeklyStamp) + if pkt.StampType != "hl" && pkt.StampType != "ex" { + doAckBufSucceed(s, pkt.AckHandle, make([]byte, 14)) + return + } var total, redeemed, updated uint16 var lastCheck time.Time err := s.server.db.QueryRow(fmt.Sprintf("SELECT %s_checked FROM stamps WHERE character_id=$1", pkt.StampType), s.charID).Scan(&lastCheck) @@ -259,6 +263,10 @@ func handleMsgMhfCheckWeeklyStamp(s *Session, p mhfpacket.MHFPacket) { func handleMsgMhfExchangeWeeklyStamp(s *Session, p mhfpacket.MHFPacket) { pkt := p.(*mhfpacket.MsgMhfExchangeWeeklyStamp) + if pkt.StampType != "hl" && pkt.StampType != "ex" { + doAckBufSucceed(s, pkt.AckHandle, make([]byte, 12)) + return + } var total, redeemed uint16 var tktStack mhfitem.MHFItemStack if pkt.ExchangeType == 10 { // Yearly Sub Ex diff --git a/server/channelserver/handlers_mail.go b/server/channelserver/handlers_mail.go index d226ba6ea..77fadc33a 100644 --- a/server/channelserver/handlers_mail.go +++ b/server/channelserver/handlers_mail.go @@ -208,6 +208,10 @@ func getCharacterName(s *Session, charID uint32) string { func handleMsgMhfReadMail(s *Session, p mhfpacket.MHFPacket) { pkt := p.(*mhfpacket.MsgMhfReadMail) + if int(pkt.AccIndex) >= len(s.mailList) { + doAckBufSucceed(s, pkt.AckHandle, []byte{0}) + return + } mailId := s.mailList[pkt.AccIndex] if mailId == 0 { doAckBufSucceed(s, pkt.AckHandle, []byte{0}) @@ -301,6 +305,10 @@ func handleMsgMhfListMail(s *Session, p mhfpacket.MHFPacket) { func handleMsgMhfOprtMail(s *Session, p mhfpacket.MHFPacket) { pkt := p.(*mhfpacket.MsgMhfOprtMail) + if int(pkt.AccIndex) >= len(s.mailList) { + doAckSimpleSucceed(s, pkt.AckHandle, make([]byte, 4)) + return + } mail, err := GetMailByID(s, s.mailList[pkt.AccIndex]) if err != nil { doAckSimpleSucceed(s, pkt.AckHandle, make([]byte, 4)) diff --git a/server/channelserver/handlers_mercenary.go b/server/channelserver/handlers_mercenary.go index cc2d6102c..9ecc355de 100644 --- a/server/channelserver/handlers_mercenary.go +++ b/server/channelserver/handlers_mercenary.go @@ -307,6 +307,10 @@ func handleMsgMhfLoadOtomoAirou(s *Session, p mhfpacket.MHFPacket) { func handleMsgMhfSaveOtomoAirou(s *Session, p mhfpacket.MHFPacket) { pkt := p.(*mhfpacket.MsgMhfSaveOtomoAirou) + if len(pkt.RawDataPayload) < 2 { + doAckSimpleSucceed(s, pkt.AckHandle, make([]byte, 4)) + return + } dumpSaveData(s, pkt.RawDataPayload, "otomoairou") decomp, err := nullcomp.Decompress(pkt.RawDataPayload[1:]) if err != nil { diff --git a/server/channelserver/handlers_misc.go b/server/channelserver/handlers_misc.go index a74d1878a..970a2bab9 100644 --- a/server/channelserver/handlers_misc.go +++ b/server/channelserver/handlers_misc.go @@ -43,6 +43,9 @@ func handleMsgMhfUpdateEtcPoint(s *Session, p mhfpacket.MHFPacket) { column = "daily_quests" case 2: column = "promo_points" + default: + doAckSimpleSucceed(s, pkt.AckHandle, make([]byte, 4)) + return } var value int16 @@ -187,9 +190,17 @@ func handleMsgMhfUpdateEquipSkinHist(s *Session, p mhfpacket.MHFPacket) { return } + if pkt.ArmourID < 10000 || pkt.MogType > 4 { + doAckSimpleSucceed(s, pkt.AckHandle, make([]byte, 4)) + return + } bit := int(pkt.ArmourID) - 10000 - startByte := (size / 5) * int(pkt.MogType) - // psql set_bit could also work but I couldn't get it working + sectionSize := size / 5 + if bit/8 >= sectionSize { + doAckSimpleSucceed(s, pkt.AckHandle, make([]byte, 4)) + return + } + startByte := sectionSize * int(pkt.MogType) byteInd := bit / 8 bitInByte := bit % 8 data[startByte+byteInd] |= bits.Reverse8(1 << uint(bitInByte)) diff --git a/server/channelserver/handlers_register.go b/server/channelserver/handlers_register.go index 04df759c9..e7e870f1b 100644 --- a/server/channelserver/handlers_register.go +++ b/server/channelserver/handlers_register.go @@ -58,6 +58,10 @@ type RaviUpdate struct { func handleMsgSysOperateRegister(s *Session, p mhfpacket.MHFPacket) { pkt := p.(*mhfpacket.MsgSysOperateRegister) + if len(pkt.RawDataPayload) == 0 { + return + } + var raviUpdates []RaviUpdate var raviUpdate RaviUpdate // Strip null terminator diff --git a/server/channelserver/handlers_tower.go b/server/channelserver/handlers_tower.go index cb9a809b4..3114d8dfd 100644 --- a/server/channelserver/handlers_tower.go +++ b/server/channelserver/handlers_tower.go @@ -329,11 +329,8 @@ func handleMsgMhfGetTenrouirai(s *Session, p mhfpacket.MHFPacket) { data = append(data, bf) } case 5: - if pkt.MissionIndex > 3 { - pkt.MissionIndex %= 3 - if pkt.MissionIndex == 0 { - pkt.MissionIndex = 3 - } + if pkt.MissionIndex < 1 || pkt.MissionIndex > 3 { + pkt.MissionIndex = (pkt.MissionIndex % 3) + 1 } rows, err := s.server.db.Query(fmt.Sprintf(`SELECT name, tower_mission_%d FROM guild_characters gc INNER JOIN characters c ON gc.character_id = c.id WHERE guild_id=$1 AND tower_mission_%d IS NOT NULL ORDER BY tower_mission_%d DESC`, pkt.MissionIndex, pkt.MissionIndex, pkt.MissionIndex), pkt.GuildID) if err != nil {