From 6f8125a947503ed0e35a42b2b2898caccd4615ba Mon Sep 17 00:00:00 2001 From: Filip Maj Date: Sun, 13 Dec 2015 22:16:40 -0500 Subject: [PATCH] Redid haschocobo packet and added hasgoobbue packet. Redid the GC Info packet to work properly. I've begun adding the list packets. --- .../packets/send/list/ListBeginPacket.cs | 36 ++++ .../packets/send/list/ListEndPacket.cs | 21 ++ .../packets/send/list/ListEntriesEndPacket.cs | 44 +++++ .../packets/send/list/ListStartPacket.cs | 62 ++++++ .../send/list/SetListPropertyPacket.cs | 184 ++++++++++++++++++ .../packets/send/player/SetGCInfoPacket.cs | 12 -- .../send/player/SetGrandCompanyPacket.cs | 35 ++++ .../send/player/SetHasChocoboPacket.cs | 22 +++ .../send/player/SetHasGoobbuePacket.cs | 22 +++ 9 files changed, 426 insertions(+), 12 deletions(-) create mode 100644 FFXIVClassic Map Server/packets/send/list/ListBeginPacket.cs create mode 100644 FFXIVClassic Map Server/packets/send/list/ListEndPacket.cs create mode 100644 FFXIVClassic Map Server/packets/send/list/ListEntriesEndPacket.cs create mode 100644 FFXIVClassic Map Server/packets/send/list/ListStartPacket.cs create mode 100644 FFXIVClassic Map Server/packets/send/list/SetListPropertyPacket.cs delete mode 100644 FFXIVClassic Map Server/packets/send/player/SetGCInfoPacket.cs create mode 100644 FFXIVClassic Map Server/packets/send/player/SetGrandCompanyPacket.cs create mode 100644 FFXIVClassic Map Server/packets/send/player/SetHasChocoboPacket.cs create mode 100644 FFXIVClassic Map Server/packets/send/player/SetHasGoobbuePacket.cs diff --git a/FFXIVClassic Map Server/packets/send/list/ListBeginPacket.cs b/FFXIVClassic Map Server/packets/send/list/ListBeginPacket.cs new file mode 100644 index 00000000..971ef01a --- /dev/null +++ b/FFXIVClassic Map Server/packets/send/list/ListBeginPacket.cs @@ -0,0 +1,36 @@ +using FFXIVClassic_Lobby_Server.packets; +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace FFXIVClassic_Map_Server.packets.send.list +{ + class ListBeginPacket + { + public const ushort OPCODE = 0x017D; + public const uint PACKET_SIZE = 0x40; + + public static SubPacket buildPacket(uint playerActorID, uint locationCode, ulong id, ulong listId, uint numEntries) + { + byte[] data = new byte[PACKET_SIZE - 0x20]; + + using (MemoryStream mem = new MemoryStream(data)) + { + using (BinaryWriter binWriter = new BinaryWriter(mem)) + { + //Write List Header + binWriter.Write((UInt64)locationCode); + binWriter.Write((UInt64)id); + //Write List Info + binWriter.Write((UInt64)listId); + binWriter.Write((UInt32)numEntries); + } + } + + return new SubPacket(OPCODE, playerActorID, playerActorID, data); + } + } +} diff --git a/FFXIVClassic Map Server/packets/send/list/ListEndPacket.cs b/FFXIVClassic Map Server/packets/send/list/ListEndPacket.cs new file mode 100644 index 00000000..e429271a --- /dev/null +++ b/FFXIVClassic Map Server/packets/send/list/ListEndPacket.cs @@ -0,0 +1,21 @@ +using FFXIVClassic_Lobby_Server.packets; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace FFXIVClassic_Map_Server.packets.send.list +{ + class ListEndPacket + { + public const ushort OPCODE = 0x017E; + public const uint PACKET_SIZE = 0x28; + + public static SubPacket buildPacket(uint playerActorID, ulong listId) + { + return new SubPacket(OPCODE, 0, playerActorID, BitConverter.GetBytes(listId)); + } + + } +} diff --git a/FFXIVClassic Map Server/packets/send/list/ListEntriesEndPacket.cs b/FFXIVClassic Map Server/packets/send/list/ListEntriesEndPacket.cs new file mode 100644 index 00000000..9334d223 --- /dev/null +++ b/FFXIVClassic Map Server/packets/send/list/ListEntriesEndPacket.cs @@ -0,0 +1,44 @@ +using FFXIVClassic_Lobby_Server.packets; +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace FFXIVClassic_Map_Server.packets.send.list +{ + class ListEntriesEndPacket + { + public const ushort OPCODE = 0x017F; + public const uint PACKET_SIZE = 0x1B8; + + public static SubPacket buildPacket(uint playerActorID, uint locationCode, uint id, uint numInPacket) + { + byte[] data = new byte[PACKET_SIZE - 0x20]; + + using (MemoryStream mem = new MemoryStream(data)) + { + using (BinaryWriter binWriter = new BinaryWriter(mem)) + { + //Write List Header + binWriter.Write((UInt64)locationCode); + binWriter.Write((UInt64)id); + //Write Entries + uint max = 8; + if (numInPacket < 8) + max = numInPacket; + for (int i = 0; i < max; i++) + { + + } + //Write Count + binWriter.Seek(0x30 * 8, SeekOrigin.Begin); + binWriter.Write(max); + } + } + + return new SubPacket(OPCODE, playerActorID, playerActorID, data); + } + } +} diff --git a/FFXIVClassic Map Server/packets/send/list/ListStartPacket.cs b/FFXIVClassic Map Server/packets/send/list/ListStartPacket.cs new file mode 100644 index 00000000..53c21806 --- /dev/null +++ b/FFXIVClassic Map Server/packets/send/list/ListStartPacket.cs @@ -0,0 +1,62 @@ +using FFXIVClassic_Lobby_Server.packets; +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace FFXIVClassic_Map_Server.packets.send.list +{ + class ListStartPacket + { + public const uint TYPEID_RETAINER = 0x13881; + public const uint TYPEID_PARTY = 0x2711; + public const uint TYPEID_LINKSHELL = 0x4E22; + + public const ushort OPCODE = 0x017C; + public const uint PACKET_SIZE = 0x98; + + public static SubPacket buildPacket(uint playerActorID, uint locationCode, ulong id, ulong listId, uint numEntries) + { + byte[] data = new byte[PACKET_SIZE - 0x20]; + + using (MemoryStream mem = new MemoryStream(data)) + { + using (BinaryWriter binWriter = new BinaryWriter(mem)) + { + //Temp stuff + string name = ""; + uint listTypeId = 0x4E22; + + //Write list header + binWriter.Write((UInt64)locationCode); + binWriter.Write((UInt64)id); + + //Write list id + binWriter.Write((UInt64)3); + binWriter.Write((UInt64)listId); + binWriter.Write((UInt64)0); + binWriter.Write((UInt64)listId); + + //This seems to change depending on what the list is for + binWriter.Write((UInt32)listTypeId); + binWriter.Seek(0x40, SeekOrigin.Begin); + + //This is for Linkshell + binWriter.Write((UInt32)0xFFFFFFFF); + binWriter.Write(Encoding.ASCII.GetBytes(name), 0, Encoding.ASCII.GetByteCount(name) >= 0x20 ? 0x20 : Encoding.ASCII.GetByteCount(name)); + + binWriter.Write((UInt32)0x6D); + binWriter.Write((UInt32)0x6D); + binWriter.Write((UInt32)0x6D); + binWriter.Write((UInt32)0x6D); + + binWriter.Write((UInt32)numEntries); + } + } + + return new SubPacket(OPCODE, playerActorID, playerActorID, data); + } + } +} diff --git a/FFXIVClassic Map Server/packets/send/list/SetListPropertyPacket.cs b/FFXIVClassic Map Server/packets/send/list/SetListPropertyPacket.cs new file mode 100644 index 00000000..59e812f5 --- /dev/null +++ b/FFXIVClassic Map Server/packets/send/list/SetListPropertyPacket.cs @@ -0,0 +1,184 @@ +using FFXIVClassic_Lobby_Server.common; +using FFXIVClassic_Lobby_Server.packets; +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Reflection; +using System.Text; +using System.Threading.Tasks; + +namespace FFXIVClassic_Map_Server.packets.send.actor +{ + class SetListPropetyPacket + { + public const ushort OPCODE = 0x017A; + public const uint PACKET_SIZE = 0xB0; + + private const ushort MAXBYTES = 0x98; + + private ushort runningByteTotal = 0; + private byte[] data = new byte[PACKET_SIZE - 0x20]; + private bool isMore = false; + + private MemoryStream mem; + private BinaryWriter binWriter; + + public SetListPropetyPacket(ulong listId) + { + mem = new MemoryStream(data); + binWriter = new BinaryWriter(mem); + binWriter.Write((UInt64)listId); + binWriter.Seek(1, SeekOrigin.Current); + } + + public void closeStreams() + { + binWriter.Dispose(); + mem.Dispose(); + } + + public bool addByte(uint id, byte value) + { + if (runningByteTotal + 6 > MAXBYTES) + return false; + + binWriter.Write((byte)1); + binWriter.Write((UInt32)id); + binWriter.Write((byte)value); + runningByteTotal+=6; + + return true; + } + + public bool addShort(uint id, ushort value) + { + if (runningByteTotal + 7 > MAXBYTES) + return false; + + binWriter.Write((byte)2); + binWriter.Write((UInt32)id); + binWriter.Write((UInt16)value); + runningByteTotal+=7; + + return true; + } + + public bool addInt(uint id, uint value) + { + if (runningByteTotal + 9 > MAXBYTES) + return false; + + binWriter.Write((byte)4); + binWriter.Write((UInt32)id); + binWriter.Write((UInt32)value); + runningByteTotal+=9; + + return true; + } + + public bool addBuffer(uint id, byte[] buffer) + { + if (runningByteTotal + 5 + buffer.Length > MAXBYTES) + return false; + + binWriter.Write((byte)buffer.Length); + binWriter.Write((UInt32)id); + binWriter.Write(buffer); + runningByteTotal += (ushort)(5 + buffer.Length); + + return true; + } + + public void addProperty(FFXIVClassic_Map_Server.dataobjects.Actor actor, string name) + { + string[] split = name.Split('.'); + int arrayIndex = 0; + + if (!(split[0].Equals("work") || split[0].Equals("charaWork") || split[0].Equals("playerWork") || split[0].Equals("npcWork"))) + return; + + Object curObj = actor; + for (int i = 0; i < split.Length; i++) + { + //For arrays + if (split[i].Contains('[')) + { + if (split[i].LastIndexOf(']') - split[i].IndexOf('[') <= 0) + return; + + arrayIndex = Convert.ToInt32(split[i].Substring(split[i].IndexOf('[') + 1, split[i].Length - split[i].LastIndexOf(']'))); + split[i] = split[i].Substring(0, split[i].IndexOf('[')); + } + + FieldInfo field = curObj.GetType().GetField(split[i]); + if (field == null) + return; + + curObj = field.GetValue(curObj); + if (curObj == null) + return; + } + + if (curObj == null) + return; + else + { + //Array, we actually care whats inside + if (curObj.GetType().IsArray) + { + if (((Array)curObj).Length <= arrayIndex) + return; + curObj = ((Array)curObj).GetValue(arrayIndex); + } + + if (curObj == null) + return; + + //Cast to the proper object and add to packet + uint id = Utils.MurmurHash2(name, 0); + if (curObj is bool) + addByte(id, (byte)(((bool)curObj) ? 1 : 0)); + else if (curObj is byte) + addByte(id, (byte)curObj); + else if (curObj is ushort) + addShort(id, (ushort)curObj); + else if (curObj is short) + addShort(id, (ushort)(short)curObj); + else if (curObj is uint) + addInt(id, (uint)curObj); + else if (curObj is int) + addInt(id, (uint)(int)curObj); + else if (curObj is float) + addBuffer(id, BitConverter.GetBytes((float)curObj)); + else + return; + } + } + + public void setIsMore(bool flag) + { + isMore = flag; + } + + public void setTarget(string target) + { + binWriter.Write((byte)(isMore ? 0x62 + target.Length : 0x82 + target.Length)); + binWriter.Write(Encoding.ASCII.GetBytes(target)); + runningByteTotal += (ushort)(1 + Encoding.ASCII.GetByteCount(target)); + + } + + public SubPacket buildPacket(uint playerActorID, uint actorID) + { + binWriter.Seek(0x8, SeekOrigin.Begin); + binWriter.Write((byte)runningByteTotal); + + closeStreams(); + + SubPacket packet = new SubPacket(OPCODE, playerActorID, actorID, data); + return packet; + } + + } +} diff --git a/FFXIVClassic Map Server/packets/send/player/SetGCInfoPacket.cs b/FFXIVClassic Map Server/packets/send/player/SetGCInfoPacket.cs deleted file mode 100644 index 62d2c294..00000000 --- a/FFXIVClassic Map Server/packets/send/player/SetGCInfoPacket.cs +++ /dev/null @@ -1,12 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Text; -using System.Threading.Tasks; - -namespace FFXIVClassic_Map_Server.packets.send.player -{ - class SetGCInfoPacket - { - } -} diff --git a/FFXIVClassic Map Server/packets/send/player/SetGrandCompanyPacket.cs b/FFXIVClassic Map Server/packets/send/player/SetGrandCompanyPacket.cs new file mode 100644 index 00000000..1593fde6 --- /dev/null +++ b/FFXIVClassic Map Server/packets/send/player/SetGrandCompanyPacket.cs @@ -0,0 +1,35 @@ +using FFXIVClassic_Lobby_Server.packets; +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace FFXIVClassic_Map_Server.packets.send.actor +{ + class SetGrandCompanyPacket + { + public const ushort OPCODE = 0x0194; + public const uint PACKET_SIZE = 0x28; + + public static SubPacket buildPacket(uint sourceActorID, uint targetActorID, ushort currentAllegiance, ushort rankLimsa, ushort rankGridania, ushort rankUldah) + { + byte[] data = new byte[PACKET_SIZE - 0x20]; + + using (MemoryStream mem = new MemoryStream(data)) + { + using (BinaryWriter binWriter = new BinaryWriter(mem)) + { + binWriter.Write((UInt16)currentAllegiance); + binWriter.Write((UInt16)rankLimsa); + binWriter.Write((UInt16)rankGridania); + binWriter.Write((UInt16)rankUldah); + } + } + + return new SubPacket(OPCODE, sourceActorID, targetActorID, data); + } + + } +} diff --git a/FFXIVClassic Map Server/packets/send/player/SetHasChocoboPacket.cs b/FFXIVClassic Map Server/packets/send/player/SetHasChocoboPacket.cs new file mode 100644 index 00000000..0c63324f --- /dev/null +++ b/FFXIVClassic Map Server/packets/send/player/SetHasChocoboPacket.cs @@ -0,0 +1,22 @@ +using FFXIVClassic_Lobby_Server.packets; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace FFXIVClassic_Map_Server.packets.send.player +{ + class SetHasChocoboPacket + { + public const ushort OPCODE = 0x0199; + public const uint PACKET_SIZE = 0x28; + + public static SubPacket buildPacket(uint playerActorID, bool hasChocobo) + { + byte[] data = new byte[PACKET_SIZE - 0x20]; + data[0] = (byte)(hasChocobo ? 1 : 0); + return new SubPacket(OPCODE, playerActorID, playerActorID, data); + } + } +} diff --git a/FFXIVClassic Map Server/packets/send/player/SetHasGoobbuePacket.cs b/FFXIVClassic Map Server/packets/send/player/SetHasGoobbuePacket.cs new file mode 100644 index 00000000..f798fc5f --- /dev/null +++ b/FFXIVClassic Map Server/packets/send/player/SetHasGoobbuePacket.cs @@ -0,0 +1,22 @@ +using FFXIVClassic_Lobby_Server.packets; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; + +namespace FFXIVClassic_Map_Server.packets.send.player +{ + class SetHasGoobbuePacket + { + public const ushort OPCODE = 0x01A1; + public const uint PACKET_SIZE = 0x28; + + public static SubPacket buildPacket(uint playerActorID, bool hasGoobbue) + { + byte[] data = new byte[PACKET_SIZE - 0x20]; + data[0] = (byte)(hasGoobbue ? 1 : 0); + return new SubPacket(OPCODE, playerActorID, playerActorID, data); + } + } +}