Example #1
0
    /// <inheritdoc />
    public void Unserialize(UndertaleReader reader)
    {
        uint len = reader.ReadUInt32();

        Data = reader.ReadBytes((int)len);
        Util.DebugUtil.Assert(Data.Length == len);
    }
            public void ReadData(UndertaleReader reader, int length)
            {
                if (_Length != 0 && _Length != length)
                    throw new UndertaleSerializationException("Failed to compute length of shader data");

                _Length = (uint)length;
                Data = reader.ReadBytes(length);
            }
Example #3
0
 public void Unserialize(UndertaleReader reader)
 {
     DisableDebugger          = reader.ReadByte() != 0 ? true : false;
     BytecodeVersion          = reader.ReadByte();
     Unknown                  = reader.ReadUInt16();
     Filename                 = reader.ReadUndertaleString();
     Config                   = reader.ReadUndertaleString();
     LastObj                  = reader.ReadUInt32();
     LastTile                 = reader.ReadUInt32();
     GameID                   = reader.ReadUInt32();
     Unknown1                 = reader.ReadUInt32();
     Unknown2                 = reader.ReadUInt32();
     Unknown3                 = reader.ReadUInt32();
     Unknown4                 = reader.ReadUInt32();
     Name                     = reader.ReadUndertaleString();
     Major                    = reader.ReadUInt32();
     Minor                    = reader.ReadUInt32();
     Release                  = reader.ReadUInt32();
     Build                    = reader.ReadUInt32();
     DefaultWindowWidth       = reader.ReadUInt32();
     DefaultWindowHeight      = reader.ReadUInt32();
     Info                     = (InfoFlags)reader.ReadUInt32();
     LicenseMD5               = reader.ReadBytes(16);
     LicenseCRC32             = reader.ReadUInt32();
     Timestamp                = reader.ReadUInt64();
     DisplayName              = reader.ReadUndertaleString();
     ActiveTargets1           = reader.ReadUInt32();
     ActiveTargets2           = reader.ReadUInt32();
     FunctionClassifications1 = reader.ReadUInt32();
     FunctionClassifications2 = reader.ReadUInt32();
     SteamAppID               = reader.ReadInt32();
     DebuggerPort             = reader.ReadUInt32();
     RoomOrder                = reader.ReadUndertaleObject <UndertaleSimpleResourcesList <UndertaleRoom, UndertaleChunkROOM> >();
     if (Major >= 2)
     {
         GMS2RandomUID       = reader.ReadBytes(40);
         GMS2FPS             = reader.ReadSingle();
         GMS2AllowStatistics = reader.ReadBoolean();
         GMS2GameGUID        = reader.ReadBytes(16);
     }
     reader.undertaleData.UnsupportedBytecodeVersion = BytecodeVersion < 14 || BytecodeVersion > 17;
     reader.Bytecode14OrLower = BytecodeVersion <= 14;
 }
        internal override void UnserializeChunk(UndertaleReader reader)
        {
            if (reader.undertaleData.GeneralInfo?.BytecodeVersion >= 17)
            {
                /* This code performs four checks to identify GM2022.2.
                 * First, as you've seen, is the bytecode version.
                 * Second, we assume it is. If there are no Glyphs, we are vindicated by the impossibility of null values there.
                 * Third, we check that the Glyph Length is less than the chunk length. If it's going outside the chunk, that means
                 * that the length was misinterpreted.
                 * Fourth, in case of a terrible fluke causing this to appear valid erroneously, we verify that each pointer leads into the next.
                 * And if someone builds their game so the first pointer is absolutely valid length data and the next font is valid glyph data-
                 * screw it, call Jacky720 when someone constructs that and you want to mod it.
                 * Maybe try..catch on the whole shebang?
                 */
                uint positionToReturn = reader.Position;
                if (reader.ReadUInt32() > 0) // Font count
                {
                    uint firstFontPointer = reader.ReadUInt32();
                    reader.Position = firstFontPointer + 48; // There are 48 bytes of existing metadata.
                    uint glyphsLength = reader.ReadUInt32();
                    reader.undertaleData.GMS2022_2 = true;
                    if ((glyphsLength * 4) > this.Length)
                    {
                        reader.undertaleData.GMS2022_2 = false;
                    }
                    else if (glyphsLength != 0)
                    {
                        List <uint> glyphPointers = new List <uint>();
                        for (uint i = 0; i < glyphsLength; i++)
                        {
                            glyphPointers.Add(reader.ReadUInt32());
                        }
                        foreach (uint pointer in glyphPointers)
                        {
                            if (reader.Position != pointer)
                            {
                                reader.undertaleData.GMS2022_2 = false;
                                break;
                            }

                            reader.Position += 14;
                            ushort kerningLength = reader.ReadUInt16();
                            reader.Position += (uint)4 * kerningLength;  // combining read/write would apparently break
                        }
                    }
                }
                reader.Position = positionToReturn;
            }

            base.UnserializeChunk(reader);

            Padding = reader.ReadBytes(512);
        }
Example #5
0
        internal override void UnserializeChunk(UndertaleReader reader)
        {
            base.UnserializeChunk(reader);

            // Strange data for each extension, some kind of unique identifier based on
            // the product ID for each of them
            productIdData = new List <byte[]>();
            for (int i = 0; i < List.Count; i++)
            {
                productIdData.Add(reader.ReadBytes(16));
            }
        }
Example #6
0
        internal override void UnserializeChunk(UndertaleReader reader)
        {
            base.UnserializeChunk(reader);

            // Strange data for each extension, some kind of unique identifier based on
            // the product ID for each of them
            productIdData = new List <byte[]>();
            if (reader.undertaleData.GeneralInfo?.Major >= 2 || (reader.undertaleData.GeneralInfo?.Major == 1 && reader.undertaleData.GeneralInfo?.Build >= 9999))
            {
                for (int i = 0; i < List.Count; i++)
                {
                    productIdData.Add(reader.ReadBytes(16));
                }
            }
        }
        internal override void UnserializeChunk(UndertaleReader reader)
        {
            base.UnserializeChunk(reader);

            // Strange data for each extension, some kind of unique identifier based on
            // the product ID for each of them
            productIdData = new List <byte[]>();
            // NOTE: I do not know if 1773 is the earliest version which contains product IDs.
            if (reader.undertaleData.GeneralInfo?.Major >= 2 || (reader.undertaleData.GeneralInfo?.Major == 1 && reader.undertaleData.GeneralInfo?.Build >= 1773) || (reader.undertaleData.GeneralInfo?.Major == 1 && reader.undertaleData.GeneralInfo?.Build == 1539))
            {
                for (int i = 0; i < List.Count; i++)
                {
                    productIdData.Add(reader.ReadBytes(16));
                }
            }
        }
Example #8
0
 public void Unserialize(UndertaleReader reader)
 {
     DisableDebugger = reader.ReadByte() != 0 ? true : false;
     BytecodeVersion = reader.ReadByte();
     Unknown         = reader.ReadUInt16();
     Filename        = reader.ReadUndertaleString();
     Config          = reader.ReadUndertaleString();
     LastObj         = reader.ReadUInt32();
     LastTile        = reader.ReadUInt32();
     GameID          = reader.ReadUInt32();
     byte[] GuidData = reader.ReadBytes(16);
     DirectPlayGuid          = new Guid(GuidData);
     Name                    = reader.ReadUndertaleString();
     Major                   = reader.ReadUInt32();
     Minor                   = reader.ReadUInt32();
     Release                 = reader.ReadUInt32();
     Build                   = reader.ReadUInt32();
     DefaultWindowWidth      = reader.ReadUInt32();
     DefaultWindowHeight     = reader.ReadUInt32();
     Info                    = (InfoFlags)reader.ReadUInt32();
     LicenseMD5              = reader.ReadBytes(16);
     LicenseCRC32            = reader.ReadUInt32();
     Timestamp               = reader.ReadUInt64();
     DisplayName             = reader.ReadUndertaleString();
     ActiveTargets           = reader.ReadUInt64();
     FunctionClassifications = (FunctionClassification)reader.ReadUInt64();
     SteamAppID              = reader.ReadInt32();
     DebuggerPort            = reader.ReadUInt32();
     RoomOrder               = reader.ReadUndertaleObject <UndertaleSimpleResourcesList <UndertaleRoom, UndertaleChunkROOM> >();
     if (Major >= 2)
     {
         // Begin parsing random UID, and verify it based on original algorithm
         GMS2RandomUID = new List <long>();
         Random random      = new Random((int)(Timestamp & 4294967295L));
         long   firstRandom = (long)random.Next() << 32 | (long)random.Next();
         if (reader.ReadInt64() != firstRandom)
         {
             //throw new IOException("Unexpected random UID");
         }
         long  infoNumber = (long)(Timestamp - 1000);
         ulong temp       = (ulong)infoNumber;
         temp = ((temp << 56 & 18374686479671623680UL) | (temp >> 8 & 71776119061217280UL) |
                 (temp << 32 & 280375465082880UL) | (temp >> 16 & 1095216660480UL) | (temp << 8 & 4278190080UL) |
                 (temp >> 24 & 16711680UL) | (temp >> 16 & 65280UL) | (temp >> 32 & 255UL));
         infoNumber  = (long)temp;
         infoNumber ^= firstRandom;
         infoNumber  = ~infoNumber;
         infoNumber ^= ((long)GameID << 32 | (long)GameID);
         infoNumber ^= ((long)(DefaultWindowWidth + (int)Info) << 48 |
                        (long)(DefaultWindowHeight + (int)Info) << 32 |
                        (long)(DefaultWindowHeight + (int)Info) << 16 |
                        (long)(DefaultWindowWidth + (int)Info));
         infoNumber ^= BytecodeVersion;
         int infoLocation = (int)(Math.Abs((int)(Timestamp & 65535L) / 7 + (GameID - DefaultWindowWidth) + RoomOrder.Count) % 4);
         for (int i = 0; i < 4; i++)
         {
             if (i == infoLocation)
             {
                 long curr = reader.ReadInt64();
                 curr = infoNumber;
                 GMS2RandomUID.Add(curr);
             }
             else
             {
                 int first  = reader.ReadInt32();
                 int second = reader.ReadInt32();
                 first  = random.Next();
                 second = random.Next();
                 GMS2RandomUID.Add(((long)first << 32) | (long)second);
             }
         }
         GMS2FPS             = reader.ReadSingle();
         GMS2AllowStatistics = reader.ReadBoolean();
         GMS2GameGUID        = reader.ReadBytes(16);
     }
     reader.undertaleData.UnsupportedBytecodeVersion = BytecodeVersion < 14 || BytecodeVersion > 17;
     reader.Bytecode14OrLower = BytecodeVersion <= 14;
 }
        internal override void UnserializeChunk(UndertaleReader reader)
        {
            base.UnserializeChunk(reader);

            Padding = reader.ReadBytes(512);
        }