Example #1
0
        public byte[] Export(string[] Content)
        {
            using (var Strm = new MemoryStream())
                using (StructWriter Writer = new StructWriter(Strm, Encoding: Encoding))
                {
                    var File = new TextDataFormat();
                    File.Content = Content;

                    File.Count   = Content.Length;
                    File.Offsets = new TextDataEntryOffset[File.Count];

                    var Offset = 16 + (16 * File.Count);

                    for (int i = 0; i < Content.Length; i++)
                    {
                        File.Offsets[i] = new TextDataEntryOffset()
                        {
                            Offset = Offset
                        };

                        Offset += Encoding.GetByteCount(Content[i] + '\x0');
                    }

                    Writer.WriteStruct(ref File);
                    Writer.Flush();

                    foreach (var String in Content)
                    {
                        Writer.WriteString(String, StringStyle.CString);
                    }


                    return(Strm.ToArray());
                }
        }
Example #2
0
        public byte[] Export(string[] Content)
        {
            var NewHeader = new HeaderFooter();

            Tools.CopyStruct(Header, ref NewHeader);

            using (MemoryStream OriScript = new MemoryStream(Script))
                using (MemoryStream Stream = new MemoryStream())
                    using (StructWriter Writer = new StructWriter(Stream, Header.Endian == 'B', Encoding)) {
                        NewHeader.StructOffset = 0;

                        OriScript.Position = Header.StructOffset;
                        byte[] StructData = new byte[Align(Header.StructCount * Header.StructSize)];
                        OriScript.Read(StructData, 0, StructData.Length);


                        NewHeader.TypesOffset = (uint)StructData.Length;

                        OriScript.Position = Header.TypesOffset;
                        byte[] TypeData = new byte[Align(Header.TypesCount * Tools.GetStructLength(new TypeDescriptor()))];
                        OriScript.Read(TypeData, 0, TypeData.Length);

                        NewHeader.StringOffset = (uint)(NewHeader.TypesOffset + TypeData.Length);

                        byte[] StrData;
                        using (MemoryStream StrStream = new MemoryStream())
                            using (StructWriter StrWriter = new StructWriter(StrStream, Writer.BigEndian, Encoding)) {
                                Dictionary <string, uint> OffsetMap = new Dictionary <string, uint>();
                                for (int i = 0; i < Content.Length; i++)
                                {
                                    if (OffsetMap.ContainsKey(Content[i]))
                                    {
                                        var Offset = OffsetMap[Content[i]];
                                        BitConverter.GetBytes(Offset).CopyTo(StructData, OffsetPos[i]);
                                    }
                                    else
                                    {
                                        BitConverter.GetBytes((uint)StrWriter.Position).CopyTo(StructData, OffsetPos[i]);
                                        OffsetMap[Content[i]] = (uint)StrWriter.Position;
                                        StrWriter.Write(Content[i], StringStyle.CString);
                                    }
                                }

                                StrWriter.Flush();

                                StrData = new byte[Align(StrStream.Length)];
                                StrStream.ToArray().CopyTo(StrData, 0);
                            }


                        Writer.Write(StructData);
                        Writer.Write(TypeData);
                        Writer.Write(StrData);
                        Writer.WriteStruct(ref NewHeader);
                        Writer.Flush();

                        return(Stream.ToArray());
                    }
        }
Example #3
0
        public static void Repack(File[] Files, Stream Output, bool CloseStreams = true)
        {
            if ((from x in Files where x.FileName == HeaderInfo select x).Count() != 1)
            {
                throw new Exception("Header Info Not Found");
            }

            byte[] HInfo = new byte[0x7F8];
            File   tmp   = (from x in Files where x.FileName == HeaderInfo select x).First();

            tmp.Content.Read(HInfo, 0, HInfo.Length);
            tmp.Content.Close();

            Files = (from x in Files where x.FileName != HeaderInfo select x).ToArray();

            StructWriter Writer = new StructWriter(Output, Encoding: Encoding.ASCII);
            PACHeader    Header = new PACHeader()
            {
                Signature = "PAC ",
                FileCount = (uint)Files.Length,
                Dummy     = HInfo
            };

            Writer.WriteStruct(ref Header);

            uint TotalHeaderLen = (uint)((Tools.GetStructLength(new File()) * Files.Length) + Tools.GetStructLength(Header));

            for (uint i = 0, x = 0; i < Files.Length; i++)
            {
                tmp = new File()
                {
                    FileName = Files[i].FileName,
                    Length   = (uint)Files[i].Content.Length,
                    Offset   = x + TotalHeaderLen
                };
                Writer.WriteStruct(ref tmp);

                x += tmp.Length;
            }


            for (uint i = 0; i < Files.Length; i++)
            {
                Files[i].Content.CopyTo(Writer.BaseStream);

                if (CloseStreams)
                {
                    Files[i].Content.Close();
                }
            }
            Writer.Flush();

            if (CloseStreams)
            {
                Writer.Close();
            }
        }
        public byte[] Export(string[] Strings)
        {
            if (Resource.Localizations.Length != Strings.Length)
            {
                throw new Exception("You can't add/remove strings from a locres file");
            }

            for (int i = 0; i < Resource.Localizations.Length; i++)
            {
                Resource.Localizations[i].Content = Strings[i];
            }

            using (var Stream = new MemoryStream())
                using (var Writer = new StructWriter(Stream, Encoding: Encoding.Unicode)) {
                    Writer.WriteStruct(ref Resource);
                    Writer.Flush();
                    return(Stream.ToArray());
                }
        }
Example #5
0
        public byte[] Export(string[] Content)
        {
            if (Content.Length != Data.Count)
            {
                throw new Exception("You Can't Modify The Count of Strings.");
            }

            using (MemoryStream Buffer = new MemoryStream())
                using (StructWriter Writer = new StructWriter(Buffer, Encoding: Encoding)) {
                    for (int i = 0; i < Content.Length; i++)
                    {
                        Entry Entry = Data[i];
                        Entry.Content = Content[i];

                        Writer.WriteStruct(ref Entry);
                    }
                    Writer.Flush();

                    return(Encrypt(Buffer.ToArray()));
                }
        }
Example #6
0
        public byte[] Export(string[] Text)
        {
            MemoryStream Script   = new MemoryStream(Data);
            long         StrIndex = 0;
            long         LastPos  = 0;

            byte[] Buffer = new byte[0];
            using (MemoryStream Output = new MemoryStream())
                using (StructReader Reader = new StructReader(Script, Encoding: Encoding))
                    using (StructWriter Writer = new StructWriter(Output, Encoding: Encoding)) {
                        foreach (long BasePos in BlockPos)
                        {
                            Buffer = new byte[BasePos - LastPos];
                            Reader.Read(Buffer, 0, Buffer.Length);
                            Writer.Write(Buffer, 0, Buffer.Length);

                            BINv2Struct Struct = new BINv2Struct();
                            Reader.ReadStruct(ref Struct);
                            LastPos = Reader.BaseStream.Position;

                            for (uint i = 0; i < Struct.Strings.LongLength; i++)
                            {
                                Struct.Strings[i] = Text[i + StrIndex];
                            }

                            StrIndex += Struct.Strings.LongLength;
                            Writer.WriteStruct(ref Struct);
                        }

                        if (Reader.BaseStream.Position != Reader.BaseStream.Length)
                        {
                            Reader.BaseStream.CopyTo(Writer.BaseStream);
                        }

                        Writer.Flush();
                        return(Output.ToArray());
                    }
        }
Example #7
0
        public static void Save(Stream Output, Entry[] Content, bool BigEndian, bool SteamVer, bool CloseStreams = true)
        {
            uint HeaderSize = (SteamVer ? ExNameSize : NameSize) + 4;

            StructWriter Writer  = new StructWriter(Output, BigEndian);
            object       Section = SteamVer ? (object)new SteamSection() : new Section();

            ((dynamic)Section).Name  = SteamVer ? "Filename    " : "Filename";
            ((dynamic)Section).Event = new FieldInvoke(SectionEvent);

            long        BasePos      = (uint)(Content.LongLength * 4);
            List <byte> OffsetBuffer = new List <byte>((int)BasePos);
            List <byte> NameBuffer   = new List <byte>();

            foreach (Entry Entry in Content)
            {
                OffsetBuffer.Add((uint)(NameBuffer.Count + BasePos), BigEndian);
                NameBuffer.AddRange(Encoding.UTF8.GetBytes(Entry.Filename + "\x0"));
            }

            ((dynamic)Section).Data = OffsetBuffer.Concat(NameBuffer).ToArray();

            Writer.WriteStruct(SteamVer ? typeof(SteamSection) : typeof(Section), ref Section);

            while (Writer.BaseStream.Position % (SteamVer ? 8 : 4) != 0)
            {
                Writer.Write((byte)0x00);
            }

            long PackStart = Writer.BaseStream.Position;

            ((dynamic)Section).Name = SteamVer ? "Pack        " : "Pack    ";

            List <byte> OffsetTable = new List <byte>();

            OffsetTable.Add(Content.Length, BigEndian);

            BasePos = PackStart + HeaderSize + 4 + (Content.Length * 8);

            while (BasePos % (SteamVer ? 8 : 0x100) != 0)
            {
                BasePos++;
            }

            foreach (Entry Entry in Content)
            {
                OffsetTable.Add((uint)BasePos, BigEndian);
                OffsetTable.Add((uint)Entry.Content.Length, BigEndian);
                BasePos += Entry.Content.Length;

                while (!SteamVer && BasePos % 0x100 != 0)
                {
                    BasePos++;
                }
            }

            ((dynamic)Section).Data = OffsetTable.ToArray();
            Writer.WriteStruct(SteamVer ? typeof(SteamSection) : typeof(Section), ref Section);


            while (Writer.BaseStream.Position % (SteamVer ? 8 : 0x100) != 0)
            {
                Writer.Write((byte)0);
            }


            Writer.Flush();


            foreach (Entry Entry in Content)
            {
                Entry.Content.Position = 0;
                Entry.Content.CopyTo(Output);

                while (!SteamVer && Output.Position % 0x100 != 0)
                {
                    Output.WriteByte(0);
                }
            }

            while (SteamVer && Output.Position % 0x10 != 0)
            {
                Output.WriteByte(0);
            }

            Writer.Close();
            Output?.Close();
        }
Example #8
0
        public byte[] Export(string[] Strings)
        {
            uint[]   Offsets = new uint[Strings.LongLength];
            Database Header  = new Database();

            Tools.ReadStruct(Script, ref Header);
            byte[] Data;
            using (MemoryStream Output = new MemoryStream()) {
                Output.Write(Script, 0, (int)Header.StringTable);
                using (StructWriter Writer = new StructWriter(Output, Encoding: GetEncoding())) {
                    //Write Strings and Generate Offset Table
                    for (uint i = 0; i < Strings.LongLength; i++)
                    {
                        Offsets[i] = (uint)(Writer.BaseStream.Position) - Header.StringTable;
                        Writer.Write(Strings[i], GetStrEnd());
                        Writer.Flush();
                    }

                    //Update StrEnd Entry of the Header
                    uint StrEnd = 0;
                    while ((StrEnd = (uint)Output.Position) % 4 != Header.StringEnd % 4)
                    {
                        Output.WriteByte(0x00);
                    }


                    //Copy Content After the String Table
                    Output.Write(Script, (int)Header.StringEnd, (int)(Script.LongLength - Header.StringEnd));

                    Header.StringEnd = StrEnd;
                    Data             = Output.ToArray();

                    //Update Offsets
                    for (uint i = Header.ValueList, OID = 0, DFID = 0; i < Header.StringTable; i += 4)
                    {
                        if (DataFormat[(int)DFID])
                        {
                            BitConverter.GetBytes(Offsets[OID++]).CopyTo(Data, i);
                        }

                        DFID++;
                        if (DFID >= DataFormat.Count)
                        {
                            DFID = 0;
                        }
                    }
                }
            }

            Tools.BuildStruct(ref Header).CopyTo(Data, 0);

            Data = Encrypt(Data);
#if !MAX && !COMP1 && !COMP2 && !COMP3 && !COMP4 && !COMP5 && !COMP6 && !COMP7 && !COMP8
            FakeCompress(ref Data);
#else
            Compress(ref Data);
#endif

            XOR(ref Data, Begin: 1);

            return(Data);
        }
Example #9
0
        public void Encode(Bitmap Texture, Stream Output, bool CloseStreams = true)
        {
            StructWriter Writer = new StructWriter(Output, (bool)IsBigEnddian);

            Writer.Write(0x2065727574786554);

            if (SteamVersion.Value)
            {
                Writer.Write(0x20202020);

                Writer.Write(0); //0xC, section length
                Writer.WriteRawType(Const.UINT64, SteamUnk);
                Writer.Write(0); //0x18, pnglen
                Writer.WriteRawType(Const.UINT16, (ushort)TexSize.Width);
                Writer.WriteRawType(Const.UINT16, (ushort)TexSize.Height);
            }
            else
            {
                Writer.Write(0); //0x8, blocklen
                Writer.WriteRawType(Const.UINT32, Flags);
                Writer.Write(0); //0x10, pnglen
                Writer.WriteRawType(Const.UINT32, (uint)TexSize.Width);
                Writer.WriteRawType(Const.UINT32, (uint)TexSize.Height);
            }

            if (Tiled)
            {
                Texture = Retile(Texture);
            }
            uint SectionLength;

            if (SteamVersion.Value)
            {
                byte[] Buffer = new byte[Texture.Width * Texture.Height * 4];
                fixed(void *pBuff = &Buffer[0])
                {
                    int   Stride = Texture.Width;
                    uint *pPixel = (uint *)pBuff;

                    unchecked
                    {
                        for (int i = 0; i < Buffer.Length / 4; i++)
                        {
                            int X = i % Stride;
                            int Y = i / Stride;

                            uint ARGB = (uint)Texture.GetPixel(X, Y).ToArgb();

                            //ARGB => ABGR
                            *pPixel++ = (ARGB & 0xFF00FF00) | ((ARGB & 0x00FF0000) >> 8 * 2) | ((ARGB & 0x000000FF) << 8 * 2);
                        }
                    }
                }

                if (Compressed)
                {
                    Buffer = LZSSCompress(Buffer);
                }

                Writer.Write(Buffer);

                SectionLength = (uint)Writer.BaseStream.Position;
                uint TexLen = SectionLength - 0x20;
                Writer.Seek(0xC, 0);
                Writer.WriteRawType(Const.UINT32, SectionLength);
                Writer.Seek(0x18, 0);
                Writer.WriteRawType(Const.UINT32, TexLen);
            }
            else
            {
                Texture.Save(Writer.BaseStream, ImageFormat.Png);
                SectionLength = (uint)Writer.BaseStream.Position;
                uint PngLen = SectionLength - 0x1C;
                Writer.Seek(0x8, 0);
                Writer.WriteRawType(Const.UINT32, SectionLength);
                Writer.Seek(0x10, 0);
                Writer.WriteRawType(Const.UINT32, PngLen);
            }

            Writer.Seek(SectionLength, 0);
            while (Writer.BaseStream.Position % (SteamVersion.Value ? 8 : 4) != 0)
            {
                Writer.Write((byte)0x0);
            }

            StructReader Reader = new StructReader(this.Texture, (bool)IsBigEnddian);

            Reader.Seek(SteamVersion.Value ? 0x0C : 0x08, 0);
            Reader.Seek(Reader.ReadRawType(Const.UINT32), 0);

            while (Reader.BaseStream.Position % (SteamVersion.Value ? 8 : 4) != 0)
            {
                Reader.ReadByte();
            }

            Reader.BaseStream.CopyTo(Writer.BaseStream);
            Writer.Flush();

            if (CloseStreams)
            {
                Writer.Close();
                Output?.Close();
            }
        }
Example #10
0
        public void Save(Entry[] Entries, Stream Output)
        {
            if (this.Entries == null)
            {
                Open();
            }

            if (this.Entries.LongLength != Entries.LongLength)
            {
                throw new Exception("You can't add or remove files from the packget.");
            }

            Packget.BaseStream.Position = 0x00;
            byte[] Buffer = new byte[DataBegin];
            if (Packget.Read(Buffer, 0, Buffer.Length) != Buffer.Length)
            {
                throw new Exception("Failed to Copy the Static Header Data.");
            }

            StructWriter Writer = new StructWriter(Output, false, Encoding);

            Writer.Write(Buffer, 0, Buffer.Length);

            //Recovery File Order
            if (PackgetHeader.Flags != 0x3)
            {
                Entries = Entries.OrderBy(x => Convert.ToUInt32(Path.GetFileNameWithoutExtension(x.FileName).Trim(), 16)).ToArray();
            }

            uint ContentBegin = Header.Offsets.First() + PackgetHeader.HeaderLen;
            uint BufferPos    = ContentBegin;

            for (uint i = 0; i < Header.Offsets.Length; i++)
            {
                uint Length = (uint)Entries[i].Content.Length;
                Header.Offsets[i] = BufferPos - PackgetHeader.HeaderLen;
                Header.Lengths[i] = Length;
                BufferPos        += Length + (uint)AsserionRequired(Length);

                if (PackgetHeader.Flags == 0x3)
                {
                    Header.NamesOffset[i] = BufferPos - PackgetHeader.HeaderLen;

                    uint StrLen = (uint)Encoding.GetByteCount(Entries[i].FileName + "\x0");
                    StrLen += (uint)AsserionRequired(StrLen);

                    BufferPos += StrLen;
                }
            }

            Writer.WriteStruct(ref Header);

            if (Writer.BaseStream.Position < ContentBegin)
            {
                Buffer = new byte[ContentBegin - Writer.BaseStream.Position];
                Packget.BaseStream.Position = Writer.BaseStream.Position;
                if (Packget.Read(Buffer, 0, Buffer.Length) != Buffer.Length)
                {
                    throw new Exception("Failed to copy unk data");
                }

                Writer.Write(Buffer, 0, Buffer.Length);
            }

            Writer.BaseStream.Position = ContentBegin;

            for (uint i = 0; i < Header.Offsets.Length; i++)
            {
                Entries[i].Content.CopyTo(Writer.BaseStream);
                byte[] Assertion = new byte[AsserionRequired(Writer.BaseStream.Position)];
                Writer.Write(Assertion);


                if (PackgetHeader.Flags == 0x3)
                {
                    byte[] Data = Encoding.GetBytes(Entries[i].FileName + "\x0");
                    Assertion = new byte[AsserionRequired(Data.Length)];
                    Writer.Write(Data);
                    Writer.Write(Assertion);
                }
            }

            Writer.Flush();
        }