Merge pull request #21 from ZeruLight/feature/mercenaries

feature/mercenaries
This commit is contained in:
wish
2022-08-09 16:36:35 +10:00
committed by GitHub
6 changed files with 57 additions and 55 deletions

View File

@@ -1,17 +1,17 @@
package mhfpacket package mhfpacket
import ( import (
"errors" "errors"
"erupe-ce/network/clientctx"
"erupe-ce/network"
"erupe-ce/common/byteframe" "erupe-ce/common/byteframe"
"erupe-ce/network"
"erupe-ce/network/clientctx"
) )
// MsgMhfReadMercenaryW represents the MSG_MHF_READ_MERCENARY_W // MsgMhfReadMercenaryW represents the MSG_MHF_READ_MERCENARY_W
type MsgMhfReadMercenaryW struct { type MsgMhfReadMercenaryW struct {
AckHandle uint32 AckHandle uint32
Unk0 uint8 Unk0 bool
Unk1 uint8 Unk1 uint8
Unk2 uint16 // Hardcoded 0 in the binary Unk2 uint16 // Hardcoded 0 in the binary
} }
@@ -24,7 +24,7 @@ func (m *MsgMhfReadMercenaryW) Opcode() network.PacketID {
// Parse parses the packet from binary // Parse parses the packet from binary
func (m *MsgMhfReadMercenaryW) Parse(bf *byteframe.ByteFrame, ctx *clientctx.ClientContext) error { func (m *MsgMhfReadMercenaryW) Parse(bf *byteframe.ByteFrame, ctx *clientctx.ClientContext) error {
m.AckHandle = bf.ReadUint32() m.AckHandle = bf.ReadUint32()
m.Unk0 = bf.ReadUint8() m.Unk0 = bf.ReadBool()
m.Unk1 = bf.ReadUint8() m.Unk1 = bf.ReadUint8()
m.Unk2 = bf.ReadUint16() m.Unk2 = bf.ReadUint16()
return nil return nil

View File

@@ -1,18 +1,20 @@
package mhfpacket package mhfpacket
import ( import (
"errors" "errors"
"erupe-ce/network/clientctx"
"erupe-ce/network"
"erupe-ce/common/byteframe" "erupe-ce/common/byteframe"
"erupe-ce/network"
"erupe-ce/network/clientctx"
) )
// MsgMhfSaveMercenary represents the MSG_MHF_SAVE_MERCENARY // MsgMhfSaveMercenary represents the MSG_MHF_SAVE_MERCENARY
type MsgMhfSaveMercenary struct{ type MsgMhfSaveMercenary struct {
AckHandle uint32 AckHandle uint32
DataSize uint32 GCP uint32
RawDataPayload []byte Unk0 uint32
MercData []byte
Unk1 uint32
} }
// Opcode returns the ID associated with this packet type. // Opcode returns the ID associated with this packet type.
@@ -23,8 +25,11 @@ func (m *MsgMhfSaveMercenary) Opcode() network.PacketID {
// Parse parses the packet from binary // Parse parses the packet from binary
func (m *MsgMhfSaveMercenary) Parse(bf *byteframe.ByteFrame, ctx *clientctx.ClientContext) error { func (m *MsgMhfSaveMercenary) Parse(bf *byteframe.ByteFrame, ctx *clientctx.ClientContext) error {
m.AckHandle = bf.ReadUint32() m.AckHandle = bf.ReadUint32()
m.DataSize = bf.ReadUint32() bf.ReadUint32() // lenData
m.RawDataPayload = bf.ReadBytes(uint(m.DataSize)) m.GCP = bf.ReadUint32()
m.Unk0 = bf.ReadUint32()
m.MercData = bf.ReadBytes(uint(bf.ReadUint32()))
m.Unk1 = bf.ReadUint32()
return nil return nil
} }

View File

@@ -0,0 +1,5 @@
BEGIN;
CREATE SEQUENCE IF NOT EXISTS public.rasta_id_seq;
END;

View File

@@ -16,6 +16,7 @@ import (
const ( const (
BinaryMessageTypeState = 0 BinaryMessageTypeState = 0
BinaryMessageTypeChat = 1 BinaryMessageTypeChat = 1
BinaryMessageTypeData = 3
BinaryMessageTypeMailNotify = 4 BinaryMessageTypeMailNotify = 4
BinaryMessageTypeEmote = 6 BinaryMessageTypeEmote = 6
) )

View File

@@ -9,7 +9,6 @@ import (
"go.uber.org/zap" "go.uber.org/zap"
"io" "io"
"io/ioutil" "io/ioutil"
"math/rand"
"os" "os"
"path/filepath" "path/filepath"
) )
@@ -132,65 +131,57 @@ func handleMsgMhfCreateMercenary(s *Session, p mhfpacket.MHFPacket) {
bf := byteframe.NewByteFrame() bf := byteframe.NewByteFrame()
bf.WriteUint32(0x00) // Unk var nextID uint32
bf.WriteUint32(rand.Uint32()) // Partner ID? s.server.db.QueryRow("SELECT nextval('rasta_id_seq')").Scan(&nextID)
bf.WriteUint32(nextID) // New MercID
bf.WriteUint32(0xDEADBEEF) // Unk
doAckSimpleSucceed(s, pkt.AckHandle, bf.Data()) doAckSimpleSucceed(s, pkt.AckHandle, bf.Data())
} }
func handleMsgMhfSaveMercenary(s *Session, p mhfpacket.MHFPacket) { func handleMsgMhfSaveMercenary(s *Session, p mhfpacket.MHFPacket) {
pkt := p.(*mhfpacket.MsgMhfSaveMercenary) pkt := p.(*mhfpacket.MsgMhfSaveMercenary)
bf := byteframe.NewByteFrameFromBytes(pkt.RawDataPayload) if len(pkt.MercData) > 0 {
GCPValue := bf.ReadUint32() s.server.db.Exec("UPDATE characters SET savemercenary=$1 WHERE id=$2", pkt.MercData, s.charID)
_ = bf.ReadUint32() // unk
MercDataSize := bf.ReadUint32()
MercData := bf.ReadBytes(uint(MercDataSize))
_ = bf.ReadUint32() // unk
if MercDataSize > 0 {
// the save packet has an extra null byte after its size
_, err := s.server.db.Exec("UPDATE characters SET savemercenary=$1 WHERE id=$2", MercData[:MercDataSize], s.charID)
if err != nil {
s.logger.Fatal("Failed to update savemercenary and gcp in db", zap.Error(err))
}
}
// gcp value is always present regardless
_, err := s.server.db.Exec("UPDATE characters SET gcp=$1 WHERE id=$2", GCPValue, s.charID)
if err != nil {
s.logger.Fatal("Failed to update savemercenary and gcp in db", zap.Error(err))
} }
s.server.db.Exec("UPDATE characters SET gcp=$1 WHERE id=$2", pkt.GCP, s.charID)
doAckSimpleSucceed(s, pkt.AckHandle, []byte{0x00, 0x00, 0x00, 0x00}) doAckSimpleSucceed(s, pkt.AckHandle, []byte{0x00, 0x00, 0x00, 0x00})
} }
func handleMsgMhfReadMercenaryW(s *Session, p mhfpacket.MHFPacket) { func handleMsgMhfReadMercenaryW(s *Session, p mhfpacket.MHFPacket) {
pkt := p.(*mhfpacket.MsgMhfReadMercenaryW) pkt := p.(*mhfpacket.MsgMhfReadMercenaryW)
if pkt.Unk0 {
doAckBufSucceed(s, pkt.AckHandle, make([]byte, 2))
return
}
var data []byte var data []byte
var gcp uint32 var gcp uint32
// still has issues s.server.db.QueryRow("SELECT savemercenary FROM characters WHERE id = $1", s.charID).Scan(&data)
err := s.server.db.QueryRow("SELECT savemercenary FROM characters WHERE id = $1", s.charID).Scan(&data) s.server.db.QueryRow("SELECT COALESCE(gcp, 0) FROM characters WHERE id = $1", s.charID).Scan(&gcp)
if err != nil {
s.logger.Fatal("Failed to get savemercenary data from db", zap.Error(err))
}
err = s.server.db.QueryRow("SELECT COALESCE(gcp, 0) FROM characters WHERE id = $1", s.charID).Scan(&gcp)
if err != nil {
panic(err)
}
if len(data) == 0 {
data = []byte{0x00}
}
resp := byteframe.NewByteFrame() resp := byteframe.NewByteFrame()
resp.WriteBytes(data) if len(data) == 0 {
resp.WriteUint16(0) resp.WriteBytes(make([]byte, 3))
} else {
resp.WriteBytes(data[1:])
resp.WriteUint32(0) // Unk
}
resp.WriteUint32(gcp) resp.WriteUint32(gcp)
doAckBufSucceed(s, pkt.AckHandle, resp.Data()) doAckBufSucceed(s, pkt.AckHandle, resp.Data())
} }
func handleMsgMhfReadMercenaryM(s *Session, p mhfpacket.MHFPacket) { func handleMsgMhfReadMercenaryM(s *Session, p mhfpacket.MHFPacket) {
pkt := p.(*mhfpacket.MsgMhfReadMercenaryM) pkt := p.(*mhfpacket.MsgMhfReadMercenaryM)
// accessing actual rasta data of someone else still unsure of the formatting of this var data []byte
doAckBufSucceed(s, pkt.AckHandle, []byte{0x00, 0x00, 0x00, 0x00}) s.server.db.QueryRow("SELECT savemercenary FROM characters WHERE id = $1", pkt.CharID).Scan(&data)
resp := byteframe.NewByteFrame()
if len(data) == 0 {
resp.WriteBool(false)
} else {
resp.WriteBytes(data[4:])
}
doAckBufSucceed(s, pkt.AckHandle, resp.Data())
} }
func handleMsgMhfContractMercenary(s *Session, p mhfpacket.MHFPacket) {} func handleMsgMhfContractMercenary(s *Session, p mhfpacket.MHFPacket) {}

View File

@@ -119,7 +119,7 @@ func handleMsgSysCreateAcquireSemaphore(s *Session, p mhfpacket.MHFPacket) {
bf.WriteUint32(newSemaphore.id) bf.WriteUint32(newSemaphore.id)
doAckSimpleSucceed(s, pkt.AckHandle, bf.Data()) doAckSimpleSucceed(s, pkt.AckHandle, bf.Data())
} else { } else {
doAckSimpleFail(s, pkt.AckHandle, []byte{0x00, 0x00, 0x00, 0x00}) doAckSimpleSucceed(s, pkt.AckHandle, []byte{0x00, 0x00, 0x00, 0x00})
} }
} }