Пример #1
0
        public void TestParseMapPreviewIcons(string iconsFilePath)
        {
            using var original  = FileProvider.GetFile(iconsFilePath);
            using var recreated = new MemoryStream();

            MapPreviewIcons.Parse(original, true).SerializeTo(recreated, true);
            StreamAssert.AreEqual(original, recreated, true);
        }
Пример #2
0
        public void TestParseMapObjectData(string mapObjectDataFilePath)
        {
            using var original  = FileProvider.GetFile(mapObjectDataFilePath);
            using var recreated = new MemoryStream();

            MapObjectData.Parse(original, true).SerializeTo(recreated, true);
            StreamAssert.AreEqual(original, recreated, true, true);
        }
Пример #3
0
        private static void TestParseMapInfoInternal(string mapInfoFilePath)
        {
            using var original  = FileProvider.GetFile(mapInfoFilePath);
            using var recreated = new MemoryStream();

            MapInfo.Parse(original, true).SerializeTo(recreated, true);
            StreamAssert.AreEqual(original, recreated, true);
        }
Пример #4
0
        public void TestParseMapEnvironment(string environmentFilePath)
        {
            using var original  = FileProvider.GetFile(environmentFilePath);
            using var recreated = new MemoryStream();

            MapEnvironment.Parse(original, true).SerializeTo(recreated, true);
            StreamAssert.AreEqual(original, recreated, true);
        }
Пример #5
0
        public void TestParseMapInfo(string mapInfoFilePath)
        {
            using var recreated = new MemoryStream();
            using var original  = File.OpenRead(mapInfoFilePath);

            MapInfo.Parse(original, true).SerializeTo(recreated, true);
            StreamAssert.AreEqual(original, recreated, true);
        }
Пример #6
0
        public void TestParseCampaignDestructableObjectData(string campaignDestructableObjectDataFilePath)
        {
            using var original  = FileProvider.GetFile(campaignDestructableObjectDataFilePath);
            using var recreated = new MemoryStream();

            CampaignDestructableObjectData.Parse(original, true).SerializeTo(recreated, true);
            StreamAssert.AreEqual(original, recreated, true);
        }
Пример #7
0
        public void TestParsePathingMap(string pathingMapFile)
        {
            using var original  = FileProvider.GetFile(pathingMapFile);
            using var recreated = new MemoryStream();

            PathingMap.Parse(original, true).SerializeTo(recreated, true);
            StreamAssert.AreEqual(original, recreated, true);
        }
Пример #8
0
        public void TestPathingMap(string pathingMapFile)
        {
            using var fileStream = File.OpenRead(pathingMapFile);
            var pathingMap = PathingMap.Parse(fileStream, true);

            using var memoryStream = new MemoryStream();
            pathingMap.SerializeTo(memoryStream, true);

            StreamAssert.AreEqual(fileStream, memoryStream, true);
        }
Пример #9
0
        private void TestParseObjectDataInternal(string objectDataFilePath, bool fromCampaign)
        {
            using var original  = MpqFile.OpenRead(objectDataFilePath);
            using var recreated = new MemoryStream();

            using var objectDataReader = new BinaryReader(original);
            var objectData = objectDataReader.ReadObjectData(fromCampaign);

            using var objectDataWriter = new BinaryWriter(recreated);
            objectDataWriter.Write(objectData);

            StreamAssert.AreEqual(original, recreated, true, true);
        }
Пример #10
0
        public void TestParseMapUnits(string mapUnitsFilePath)
        {
            using var recreated = new MemoryStream();
            using var original  = File.OpenRead(mapUnitsFilePath);

            var data = MapUnits.Parse(original, true);

            Assert.AreEqual(original.Length, original.Position);

            data.SerializeTo(recreated, true);

            StreamAssert.AreEqual(original, recreated, true);
        }
Пример #11
0
        public void TestStoreThenRetrieveFile(string filename)
        {
            var fileStream = File.OpenRead(filename);
            var mpqFile    = MpqFile.New(fileStream, filename, true);
            var archive    = MpqArchive.Create(new MemoryStream(), new List <MpqFile>()
            {
                mpqFile
            });

            var openedArchive = MpqArchive.Open(archive.BaseStream);
            var openedStream  = openedArchive.OpenFile(filename);

            StreamAssert.AreEqual(fileStream, openedStream, true);
        }
Пример #12
0
        public void TestStoreThenRetrieveFile(string filename)
        {
            var fileStream = File.OpenRead(filename);
            // var mpqFile = new MpqKnownFile(filename, fileStream, MpqFileFlags.Exists, MpqLocale.Neutral, true);
            var mpqFile = MpqFile.New(fileStream, filename);
            var archive = MpqArchive.Create(new MemoryStream(), new List <MpqFile>()
            {
                mpqFile
            });

            var openedArchive = MpqArchive.Open(archive.BaseStream);
            var openedStream  = openedArchive.OpenFile(filename);

            fileStream.Position = 0;
            StreamAssert.AreEqual(fileStream, openedStream);
        }
Пример #13
0
        public void TestParseMapDoodads(string mapDoodadsFilePath)
        {
            using var recreated = new MemoryStream();
            using var original  = File.OpenRead(mapDoodadsFilePath);

            var data = MapDoodads.Parse(original, true);

            Assert.AreEqual(original.Length, original.Position);

            data.SerializeTo(recreated, true);

            // TODO: skip header, since it's ignored in SerializeTo method (so always saves as TFT version)
            //if (data.)

            StreamAssert.AreEqual(original, recreated, true);
        }
Пример #14
0
        public void TestStoreThenRetrieveFileWithFlags(string fileName, MpqFileFlags flags)
        {
            using var fileStream = File.OpenRead(fileName);
            var mpqFile = MpqFile.New(fileStream, fileName, true);

            mpqFile.TargetFlags = flags;
            using var archive   = MpqArchive.Create(new MemoryStream(), new List <MpqFile>()
            {
                mpqFile
            }, new MpqArchiveCreateOptions { BlockSize = BlockSize });

            using var openedArchive = MpqArchive.Open(archive.BaseStream);
            var openedStream = openedArchive.OpenFile(fileName);

            StreamAssert.AreEqual(fileStream, openedStream, true);
        }
Пример #15
0
        internal static void RunBinaryRWTest(
            string filePath,
            Type type,
            string?readMethodName = null,
            object?[]?additionalReadParameters  = null,
            object?[]?additionalWriteParameters = null)
        {
            var expectedReadTypes = new[] { typeof(BinaryReader) };

            if (additionalReadParameters is not null)
            {
                expectedReadTypes = expectedReadTypes.Concat(additionalReadParameters.Select(p => p.GetType())).ToArray();
            }

            var readMethod = typeof(BinaryReaderExtensions).GetMethod(readMethodName ?? $"Read{type.Name}", expectedReadTypes);

            Assert.IsNotNull(readMethod, $"Could not find extension method to read {type.Name}.");

            var expectedWriteTypes = new[] { typeof(BinaryWriter), type };

            if (additionalWriteParameters is not null)
            {
                expectedWriteTypes = expectedWriteTypes.Concat(additionalWriteParameters.Select(p => p.GetType())).ToArray();
            }

            var writeMethod = typeof(BinaryWriterExtensions).GetMethod(nameof(BinaryWriter.Write), expectedWriteTypes);

            Assert.IsNotNull(writeMethod, $"Could not find extension method to write {type.Name}.");

            using var expectedStream = FileProvider.GetFile(filePath);
            using var reader         = new BinaryReader(expectedStream);
            var parsedFile = readMethod !.Invoke(null, new object?[] { reader }.Concat(additionalReadParameters ?? Array.Empty <object?[]>()).ToArray());

            Assert.AreEqual(type, parsedFile.GetType());

            using var actualStream = new MemoryStream();
            using var writer       = new BinaryWriter(actualStream);
            writeMethod !.Invoke(null, new object?[] { writer, parsedFile }.Concat(additionalWriteParameters ?? Array.Empty <object?[]>()).ToArray());
            writer.Flush();

            StreamAssert.AreEqual(expectedStream, actualStream, true);
        }
Пример #16
0
        public void TestRecreatePKCompressed()
        {
            var inputArchivePath = TestDataProvider.GetPath(@"Maps\PKCompressed.w3x");

            using var inputArchive     = MpqArchive.Open(inputArchivePath);
            using var recreatedArchive = MpqArchive.Create((Stream?)null, inputArchive.GetMpqFiles().ToArray(), new MpqArchiveCreateOptions { BlockSize = inputArchive.Header.BlockSize, HashTableSize = (ushort)inputArchive.Header.HashTableSize, ListFileCreateMode = MpqFileCreateMode.None, AttributesCreateMode = MpqFileCreateMode.None });

            for (var i = 0; i < inputArchive.Header.BlockTableSize; i++)
            {
                inputArchive.BaseStream.Position     = inputArchive[i].FilePosition;
                recreatedArchive.BaseStream.Position = recreatedArchive[i].FilePosition;

                // var size1 = inputArchive[i].CompressedSize;
                // var size2 = recreatedArchive[i].CompressedSize;
                // StreamAssert.AreEqual(inputArchive.BaseStream, recreatedArchive.BaseStream, size1 > size2 ? size1 : size2);
                StreamAssert.AreEqual(inputArchive.BaseStream, recreatedArchive.BaseStream);
            }

            inputArchive.BaseStream.Position     = 0;
            recreatedArchive.BaseStream.Position = 0;
            StreamAssert.AreEqual(inputArchive.BaseStream, recreatedArchive.BaseStream, MpqHeader.Size);
        }
Пример #17
0
        public void TestParseMapUnits(string mapUnitsFilePath)
        {
            using var recreated = new MemoryStream();
            using var original  = File.OpenRead(mapUnitsFilePath);

            var data = MapUnits.Parse(original, true);

            Assert.AreEqual(original.Length, original.Position);

            data.SerializeTo(recreated, true);

            original.Position = 4;
            using (var reader = new BinaryReader(original, new UTF8Encoding(false, true), true))
            {
                var version = (MapWidgetsVersion)reader.ReadUInt32();
                if (version != MapWidgetsVersion.TFT)
                {
                    // Can't compare streams, because serialize always saves as TFT, which sets header version to 8 and has additional data per unit.
                    return;
                }
            }

            StreamAssert.AreEqual(original, recreated, true);
        }
Пример #18
0
        public void TestRecreateArchive(string inputArchivePath, bool loadListFile)
        {
            using var inputArchive = MpqArchive.Open(inputArchivePath, loadListFile);
            if (loadListFile && !inputArchive.FileExists(ListFile.FileName))
            {
                return;
            }

            var mpqFiles = inputArchive.GetMpqFiles().ToArray();

            using var recreatedArchive = MpqArchive.Create((Stream?)null, mpqFiles, new MpqArchiveCreateOptions { BlockSize = inputArchive.Header.BlockSize, ListFileCreateMode = MpqFileCreateMode.None, AttributesCreateMode = MpqFileCreateMode.None });

            // TODO: fix assumption that recreated archive's hashtable cannot be smaller than original
            // TODO: fix assumption of how recreated blocktable's entries are laid out relative to input mpqFiles array? (aka: replace the 'offset' variable)
            var offsetPerUnknownFile  = (recreatedArchive.HashTable.Size / inputArchive.HashTable.Size) - 1;
            var mpqEncryptedFileCount = mpqFiles.Where(mpqFile => mpqFile.IsFilePositionFixed).Count();
            var offset = mpqEncryptedFileCount * (offsetPerUnknownFile + 1);

            mpqEncryptedFileCount = 0;
            for (var index = 0; index < mpqFiles.Length; index++)
            {
                var      mpqFile = mpqFiles[index];
                MpqEntry?inputEntry;
                if (mpqFile is MpqKnownFile knownFile)
                {
                    inputEntry = inputArchive.GetMpqEntries(knownFile.FileName).FirstOrDefault();
                }
                else if (mpqFile is MpqUnknownFile unknownFile)
                {
                    inputArchive.TryGetEntryFromHashTable(mpqFile.HashIndex & inputArchive.HashTable.Mask, out inputEntry);
                }
                else if (mpqFile is MpqOrphanedFile orphanedFile)
                {
                    // TODO
                    throw new NotSupportedException("found orphaned mpqfile");
                }
                else
                {
                    throw new NotImplementedException();
                }

                var blockIndex = index + (int)offset;
                if (mpqFile.IsFilePositionFixed)
                {
                    blockIndex = mpqEncryptedFileCount * ((int)offsetPerUnknownFile + 1);
                    mpqEncryptedFileCount++;
                }

                var recreatedEntry = recreatedArchive[blockIndex];

                if (inputEntry is not null)
                {
                    if (!mpqFile.MpqStream.CanBeDecrypted)
                    {
                        // Check if both files have the same encryption seed.
                        Assert.IsTrue(!mpqFile.TargetFlags.HasFlag(MpqFileFlags.BlockOffsetAdjustedKey) || inputEntry.FileOffset == recreatedEntry.FileOffset);

                        inputArchive.BaseStream.Position     = inputEntry.FilePosition;
                        recreatedArchive.BaseStream.Position = recreatedEntry.FilePosition;

                        var size1 = inputEntry.CompressedSize;
                        var size2 = recreatedEntry.CompressedSize;
                        StreamAssert.AreEqual(inputArchive.BaseStream, recreatedArchive.BaseStream, size1 > size2 ? size1 : size2);
                    }
                    else
                    {
                        using var inputStream     = inputArchive.OpenFile(inputEntry);
                        using var recreatedStream = recreatedArchive.OpenFile(recreatedEntry);

                        StreamAssert.AreEqual(inputStream, recreatedStream, mpqFile is MpqKnownFile known ? known.FileName : "<unknown file>");
                    }
                }
                else
                {
                    Assert.IsFalse(recreatedEntry.Flags.HasFlag(MpqFileFlags.Exists));
                }

                if (mpqFile is MpqUnknownFile && !mpqFile.IsFilePositionFixed)
                {
                    offset += offsetPerUnknownFile;
                }
            }
        }