Beispiel #1
0
        /// <summary>
        /// Creates an item for testing.
        /// </summary>
        /// <param name="id">The item id.</param>
        /// <param name="dirId">The directory id.</param>
        /// <param name="fileName">The item name.</param>
        /// <param name="dataOffset">Data offset.</param>
        /// <param name="extractedSize">Extracted size.</param>
        /// <param name="chunkSizes">Compressed chunks sizes.</param>
        /// <param name="type">The item type.</param>
        /// <returns>The new item.</returns>
        internal static NefsItem CreateItem(
            uint id,
            uint dirId,
            string fileName,
            UInt64 dataOffset,
            UInt32 extractedSize,
            IReadOnlyList <UInt32> chunkSizes,
            NefsItemType type)
        {
            var attributes = new NefsItemAttributes(
                isDirectory: type == NefsItemType.Directory,
                v16IsTransformed: true);

            var transform  = TestTransform;
            var chunks     = NefsDataChunk.CreateChunkList(chunkSizes, transform);
            var size       = new NefsItemSize(extractedSize, chunks);
            var dataSource = new NefsFileDataSource(@"C:\source.txt", dataOffset, size, extractedSize != chunkSizes.LastOrDefault());

            return(new NefsItem(
                       Guid.NewGuid(),
                       new NefsItemId(id),
                       fileName,
                       new NefsItemId(dirId),
                       dataSource,
                       transform,
                       attributes));
        }
Beispiel #2
0
        /// <inheritdoc/>
        public async Task <uint> DetransformChunkAsync(
            Stream input,
            Stream output,
            NefsDataChunk chunk,
            uint maxOutputSize,
            NefsProgress p)
        {
            using (var detransformedStream = new MemoryStream())
            {
                // Copy chunk to temp stream
                await input.CopyPartialAsync(detransformedStream, chunk.Size, p.CancellationToken);

                detransformedStream.Seek(0, SeekOrigin.Begin);

                // Decrypt
                if (chunk.Transform.IsAesEncrypted)
                {
                    using (var aesManager = this.CreateAesManager(chunk.Transform.Aes256Key))
                        using (var cryptoStream = new CryptoStream(detransformedStream, aesManager.CreateDecryptor(), CryptoStreamMode.Read, leaveOpen: true))
                            using (var tempStream = new MemoryStream())
                            {
                                await cryptoStream.CopyToAsync(tempStream, p.CancellationToken);

                                tempStream.Seek(0, SeekOrigin.Begin);

                                detransformedStream.Seek(0, SeekOrigin.Begin);
                                await tempStream.CopyToAsync(detransformedStream, p.CancellationToken);

                                detransformedStream.Seek(0, SeekOrigin.Begin);
                                detransformedStream.SetLength(tempStream.Length);
                            }
                }

                // Decompress
                if (chunk.Transform.IsZlibCompressed)
                {
                    using (var inflater = new DeflateStream(detransformedStream, CompressionMode.Decompress, leaveOpen: true))
                        using (var tempStream = new MemoryStream())
                        {
                            await inflater.CopyToAsync(tempStream, p.CancellationToken);

                            tempStream.Seek(0, SeekOrigin.Begin);

                            detransformedStream.Seek(0, SeekOrigin.Begin);
                            await tempStream.CopyToAsync(detransformedStream, p.CancellationToken);

                            detransformedStream.Seek(0, SeekOrigin.Begin);
                            detransformedStream.SetLength(tempStream.Length);
                        }
                }

                // Copy detransformed chunk to output stream
                var chunkSize = Math.Min(detransformedStream.Length, maxOutputSize);
                await detransformedStream.CopyPartialAsync(output, chunkSize, p.CancellationToken);

                return((uint)chunkSize);
            }
        }
        /// <summary>
        /// Initializes a new instance of the <see cref="NefsItemSize"/> class. This constructor can
        /// be used if the item is not compressed (i.e., extracted size == compressed size).
        /// </summary>
        /// <param name="extractedSize">The size of the item's data when extracted from the archive.</param>
        public NefsItemSize(UInt32 extractedSize)
        {
            this.ExtractedSize = extractedSize;
            var transform = new NefsDataTransform(extractedSize);
            var chunk     = new NefsDataChunk(extractedSize, extractedSize, transform);

            this.Chunks = new List <NefsDataChunk> {
                chunk
            };
        }
Beispiel #4
0
        public void NefsHeaderPart7_MultipleItems_EntriesPopulated()
        {
            var items = new NefsItemList(@"C:\archive.nefs");

            var file1Id     = new NefsItemId(31);
            var file1Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                11, 12, 13
            }, TestHelpers.TestTransform);
            var file1DataSource = new NefsItemListDataSource(items, 123, new NefsItemSize(456, file1Chunks));
            var file1           = TestHelpers.CreateFile(file1Id.Value, file1Id.Value, "file1", file1DataSource);

            items.Add(file1);

            var file2Id     = new NefsItemId(41);
            var file2Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                14, 15, 16
            }, TestHelpers.TestTransform);
            var file2DataSource = new NefsItemListDataSource(items, 456, new NefsItemSize(789, file2Chunks));
            var file2           = TestHelpers.CreateFile(file2Id.Value, file2Id.Value, "file2", file2DataSource);

            items.Add(file2);

            var dir2Id = new NefsItemId(51);
            var dir1   = TestHelpers.CreateDirectory(dir2Id.Value, dir2Id.Value, "dir1");

            items.Add(dir1);

            var p7 = new NefsHeaderPart7(items);

            Assert.Equal(3, p7.EntriesByIndex.Count);

            // NOTES : Part 7 items are ordered in the same way that part 2 items are ordered (depth
            // first by name).

            /*
             * dir1
             */

            Assert.Equal(51U, p7.EntriesByIndex[0].Id.Value);
            Assert.Equal(51U, p7.EntriesByIndex[0].SiblingId.Value);

            /*
             * file1
             */

            Assert.Equal(31U, p7.EntriesByIndex[1].Id.Value);
            Assert.Equal(41U, p7.EntriesByIndex[1].SiblingId.Value);

            /*
             * file2
             */

            Assert.Equal(41U, p7.EntriesByIndex[2].Id.Value);
            Assert.Equal(51U, p7.EntriesByIndex[2].SiblingId.Value);
        }
        public void NefsHeaderPart3_MultipleItems_EntriesPopulated()
        {
            var items = new NefsItemList(@"C:\archive.nefs");

            var file1Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                11, 12, 13
            }, TestHelpers.TestTransform);
            var file1DataSource = new NefsItemListDataSource(items, 123, new NefsItemSize(456, file1Chunks));
            var file1           = TestHelpers.CreateFile(0, 0, "file1", file1DataSource);

            items.Add(file1);

            var file2Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                14, 15, 16
            }, TestHelpers.TestTransform);
            var file2DataSource = new NefsItemListDataSource(items, 456, new NefsItemSize(789, file2Chunks));
            var file2           = TestHelpers.CreateFile(1, 1, "file2", file2DataSource);

            items.Add(file2);

            var dir1 = TestHelpers.CreateDirectory(2, 2, "dir1");

            items.Add(dir1);

            var file3Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                22, 23, 24
            }, TestHelpers.TestTransform);
            var file3DataSource = new NefsItemListDataSource(items, 222, new NefsItemSize(333, file3Chunks));
            var file3           = TestHelpers.CreateFile(3, dir1.Id.Value, "file3", file3DataSource);

            items.Add(file3);

            var p3 = new NefsHeaderPart3(items);

            Assert.Equal(5, p3.OffsetsByFileName.Count);
            Assert.Equal(5, p3.FileNamesByOffset.Count);

            // Four file names plus a null terminal for each.
            Assert.Equal(36, (int)p3.Size);

            // Strings table is sorted alphabetically - and also contains data file name
            Assert.Equal("archive.nefs", p3.FileNamesByOffset[0]);
            Assert.Equal("dir1", p3.FileNamesByOffset[13]);
            Assert.Equal("file1", p3.FileNamesByOffset[18]);
            Assert.Equal("file2", p3.FileNamesByOffset[24]);
            Assert.Equal("file3", p3.FileNamesByOffset[30]);

            Assert.Equal(18, (int)p3.OffsetsByFileName[file1.FileName]);
            Assert.Equal(24, (int)p3.OffsetsByFileName[file2.FileName]);
            Assert.Equal(13, (int)p3.OffsetsByFileName[dir1.FileName]);
            Assert.Equal(30, (int)p3.OffsetsByFileName[file3.FileName]);
        }
Beispiel #6
0
        public async Task DetransformAsync_ExtractedSizeSmallerThanTransformed_DataExtracted()
        {
            // There are situations in version 1.6 headers where the extracted size is smaller than
            // the compressed size, resulting in extra garbage data/padding at the end of an
            // extracted file. Need to make sure this extra garbage data is ignored.
            const string Data      = "Hello there!";
            var          dataBytes = Encoding.ASCII.GetBytes(Data);

            var aesStr      = "542E5211BD8A3AE494554DA4A18884B1C546258BCCA4B76D055D52602819525A";
            var aes         = StringHelper.FromHexString(aesStr);
            var chunkSize   = 0x10000U;
            var transform   = new NefsDataTransform(chunkSize, false, aes);
            var transformer = new NefsTransformer(this.fileSystem);

            using (var inputStream = new MemoryStream())
                using (var transformedStream = new MemoryStream())
                    using (var outputStream = new MemoryStream())
                    {
                        // Copy data to input stream
                        inputStream.Write(dataBytes, 0, dataBytes.Length);

                        // Add some garbage data to end of stream
                        await transformedStream.WriteAsync(Encoding.ASCII.GetBytes("HAHAHAHAHA"), 0, 10);

                        // Transform
                        await transformer.TransformAsync(inputStream, 0, (uint)dataBytes.Length, transformedStream, 0, transform, new NefsProgress());

                        transformedStream.Seek(0, SeekOrigin.Begin);

                        // Setup chunk info
                        var extractedSize   = Data.Length;
                        var transformedSize = transformedStream.Length;
                        var chunk           = new NefsDataChunk((uint)transformedSize, (uint)transformedSize, transform);
                        var chunks          = new List <NefsDataChunk> {
                            chunk
                        };

                        // Extract
                        await transformer.DetransformAsync(transformedStream, 0, outputStream, 0, (uint)extractedSize, chunks, new NefsProgress());

                        outputStream.Seek(0, SeekOrigin.Begin);

                        var outputBytes = new byte[Data.Length];
                        await outputStream.ReadAsync(outputBytes, 0, (int)outputStream.Length);

                        var outputStr = Encoding.ASCII.GetString(outputBytes);

                        // Verify
                        Assert.Equal(extractedSize, outputStream.Length);
                        Assert.Equal(Data, outputStr);
                    }
        }
Beispiel #7
0
        /// <inheritdoc/>
        public async Task <NefsItemSize> TransformAsync(
            Stream input,
            Int64 inputOffset,
            UInt32 inputLength,
            Stream output,
            Int64 outputOffset,
            NefsDataTransform transform,
            NefsProgress p)
        {
            var chunks       = new List <NefsDataChunk>();
            var rawChunkSize = transform.ChunkSize;

            input.Seek(inputOffset, SeekOrigin.Begin);
            output.Seek(outputOffset, SeekOrigin.Begin);

            // Split file into chunks and transform them
            using (var t = p.BeginTask(1.0f, $"Transforming stream"))
            {
                var cumulativeChunkSize = 0U;
                var bytesRemaining      = (int)inputLength;

                // Determine how many chunks to split file into
                var numChunks = (int)Math.Ceiling(inputLength / (double)rawChunkSize);

                for (var i = 0; i < numChunks; ++i)
                {
                    using (var st = p.BeginSubTask(1.0f / numChunks, $"Transforming chunk {i + 1}/{numChunks}"))
                    {
                        // The last chunk may not be exactly equal to the raw chunk size
                        var nextChunkSize = (int)Math.Min(rawChunkSize, bytesRemaining);
                        bytesRemaining -= nextChunkSize;

                        // Transform chunk and write to output stream
                        var chunkSize = await this.TransformChunkAsync(input, (uint)nextChunkSize, output, transform, p);

                        cumulativeChunkSize += chunkSize;

                        // Record chunk info
                        var chunk = new NefsDataChunk(chunkSize, cumulativeChunkSize, transform);
                        chunks.Add(chunk);
                    }
                }
            }

            // Return item size
            return(new NefsItemSize(inputLength, chunks));
        }
        /// <summary>
        /// Creates a test archive. Does not write an archive to disk. Just creates a <see
        /// cref="NefsArchive"/> object.
        /// </summary>
        /// <param name="filePath">The file path to use for the archive.</param>
        /// <returns>A <see cref="NefsArchive"/>.</returns>
        public static NefsArchive Create(string filePath)
        {
            var items     = new NefsItemList(filePath);
            var aesString = "44927647059D3D73CDCC8D4C6E808538CAD7622D076A507E16C43A8DD8E3B5AB";

            var file1Attributes = new NefsItemAttributes(v20IsZlib: true);
            var file1Chunks     = NefsDataChunk.CreateChunkList(File1ChunkSizes, TestHelpers.TestTransform);
            var file1DataSource = new NefsItemListDataSource(items, File1Offset, new NefsItemSize(File1ExtractedSize, file1Chunks));
            var file1           = new NefsItem(File1Guid, new NefsItemId(File1ItemId), File1Name, new NefsItemId(File1DirectoryId), file1DataSource, TestHelpers.TestTransform, file1Attributes);

            items.Add(file1);

            var dir1Attributes = new NefsItemAttributes(isDirectory: true);
            var dir1DataSource = new NefsEmptyDataSource();
            var dir1           = new NefsItem(Dir1Guid, new NefsItemId(Dir1ItemId), Dir1Name, new NefsItemId(Dir1DirectoryId), dir1DataSource, null, dir1Attributes);

            items.Add(dir1);

            var file2Attributes = new NefsItemAttributes(v20IsZlib: true);
            var file2Chunks     = NefsDataChunk.CreateChunkList(File2ChunkSizes, TestHelpers.TestTransform);
            var file2DataSource = new NefsItemListDataSource(items, File2Offset, new NefsItemSize(File2ExtractedSize, file2Chunks));
            var file2           = new NefsItem(File2Guid, new NefsItemId(File2ItemId), File2Name, new NefsItemId(File2DirectoryId), file2DataSource, TestHelpers.TestTransform, file2Attributes);

            items.Add(file2);

            var file3Attributes = new NefsItemAttributes(v20IsZlib: true);
            var file3Transform  = new NefsDataTransform(File3ExtractedSize);
            var file3Chunks     = NefsDataChunk.CreateChunkList(File3ChunkSizes, file3Transform);
            var file3DataSource = new NefsItemListDataSource(items, File3Offset, new NefsItemSize(File3ExtractedSize, file3Chunks));
            var file3           = new NefsItem(File3Guid, new NefsItemId(File3ItemId), File3Name, new NefsItemId(File3DirectoryId), file3DataSource, file3Transform, file3Attributes);

            items.Add(file3);

            Assert.Equal((int)NumItems, items.Count);

            var intro = new NefsHeaderIntro();

            intro.Data0x6c_NumberOfItems.Value   = (uint)items.Count;
            intro.Data0x24_AesKeyHexString.Value = Encoding.ASCII.GetBytes(aesString);

            var toc = new Nefs20HeaderIntroToc();

            var header = new Nefs20Header(intro, toc, items);

            return(new NefsArchive(header, items));
        }
        /// <summary>
        /// Creates a list of chunk metadata for an item.
        /// </summary>
        /// <param name="index">The part 4 index where the chunk list starts at.</param>
        /// <param name="numChunks">The number of chunks.</param>
        /// <param name="chunkSize">The raw chunk size used in the transform.</param>
        /// <param name="aes256key">The AES 256 key to use if chunk is encrypted.</param>
        /// <returns>A list of chunk data.</returns>
        public List <NefsDataChunk> CreateChunksList(uint index, uint numChunks, uint chunkSize, byte[] aes256key)
        {
            var chunks = new List <NefsDataChunk>();

            for (var i = index; i < index + numChunks; ++i)
            {
                var entry          = this.entriesByIndex[(int)i];
                var cumulativeSize = entry.CumulativeBlockSize;
                var size           = cumulativeSize;

                if (i > index)
                {
                    size -= this.entriesByIndex[(int)i - 1].CumulativeBlockSize;
                }

                // Determine transform -- need to clean this up
                NefsDataTransform transform;
                var transformVal = entry.Data0x04_TransformType.Value;

                switch (transformVal)
                {
                case (int)Nefs16HeaderPart4TransformType.Zlib:
                    transform = new NefsDataTransform(chunkSize, true);
                    break;

                case (int)Nefs16HeaderPart4TransformType.Aes:
                    transform = new NefsDataTransform(chunkSize, false, aes256key);
                    break;

                case (int)Nefs16HeaderPart4TransformType.None:
                    transform = new NefsDataTransform(chunkSize, false);
                    break;

                default:
                    Log.LogError("Found v1.6 data chunk with unknown transform; aborting.");
                    return(new List <NefsDataChunk>());
                }

                // Create data chunk info
                var chunk = new NefsDataChunk(size, cumulativeSize, transform);
                chunks.Add(chunk);
            }

            return(chunks);
        }
        /// <summary>
        /// Creates a test archive. Does not write an archive to disk. Just creates a <see
        /// cref="NefsArchive"/> object.
        /// </summary>
        /// <param name="filePath">The file path to use for the archive.</param>
        /// <returns>A <see cref="NefsArchive"/>.</returns>
        public static NefsArchive Create(string filePath)
        {
            var items = new NefsItemList(filePath);

            var file1Attributes = new NefsItemAttributes(v20IsZlib: true);
            var file1Chunks     = NefsDataChunk.CreateChunkList(File1ChunkSizes, TestHelpers.TestTransform);
            var file1DataSource = new NefsItemListDataSource(items, File1Offset, new NefsItemSize(File1ExtractedSize, file1Chunks));
            var file1           = new NefsItem(File1Guid, new NefsItemId(File1ItemId), File1Name, new NefsItemId(File1DirectoryId), file1DataSource, TestHelpers.TestTransform, file1Attributes);

            items.Add(file1);

            var dir1Attributes = new NefsItemAttributes(isDirectory: true);
            var dir1DataSource = new NefsEmptyDataSource();
            var dir1           = new NefsItem(Dir1Guid, new NefsItemId(Dir1ItemId), Dir1Name, new NefsItemId(Dir1DirectoryId), dir1DataSource, null, dir1Attributes);

            items.Add(dir1);

            var file2Attributes = new NefsItemAttributes(v20IsZlib: true);
            var file2Chunks     = NefsDataChunk.CreateChunkList(File2ChunkSizes, TestHelpers.TestTransform);
            var file2DataSource = new NefsItemListDataSource(items, File2Offset, new NefsItemSize(File2ExtractedSize, file2Chunks));
            var file2           = new NefsItem(File2Guid, new NefsItemId(File2ItemId), File2Name, new NefsItemId(File2DirectoryId), file2DataSource, TestHelpers.TestTransform, file2Attributes);

            items.Add(file2);

            var file3Attributes = new NefsItemAttributes(v20IsZlib: true);
            var file3Chunks     = NefsDataChunk.CreateChunkList(File3ChunkSizes, TestHelpers.TestTransform);
            var file3DataSource = new NefsItemListDataSource(items, File3Offset, new NefsItemSize(File3ExtractedSize, file3Chunks));
            var file3           = new NefsItem(File3Guid, new NefsItemId(File3ItemId), File3Name, new NefsItemId(File3DirectoryId), file3DataSource, TestHelpers.TestTransform, file3Attributes);

            items.Add(file3);

            Assert.Equal((int)NumItems, items.Count);

            var intro = new NefsHeaderIntro();

            intro.Data0x6c_NumberOfItems.Value = (uint)items.Count;

            var toc = new Nefs20HeaderIntroToc();

            var header = new Nefs20Header(intro, toc, items);

            return(new NefsArchive(header, items));
        }
        /// <summary>
        /// Creates a list of chunk metadata for an item.
        /// </summary>
        /// <param name="index">The part 4 index where the chunk list starts at.</param>
        /// <param name="numChunks">The number of chunks.</param>
        /// <param name="transform">The transform used for data chunks.</param>
        /// <returns>A list of chunk data.</returns>
        public List <NefsDataChunk> CreateChunksList(uint index, uint numChunks, NefsDataTransform transform)
        {
            var chunks = new List <NefsDataChunk>();

            for (var i = index; i < index + numChunks; ++i)
            {
                var cumulativeSize = this.entriesByIndex[(int)i].CumulativeChunkSize;
                var size           = cumulativeSize;

                if (i > index)
                {
                    size -= this.entriesByIndex[(int)i - 1].CumulativeChunkSize;
                }

                var chunk = new NefsDataChunk(size, cumulativeSize, transform);
                chunks.Add(chunk);
            }

            return(chunks);
        }
        public NefsHeaderPart4Tests()
        {
            var items = new NefsItemList(@"C:\archive.nefs");

            var file1Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                1, 11, 21
            }, TestHelpers.TestTransform);
            var file1DataSource = new NefsItemListDataSource(items, 123, new NefsItemSize(456, file1Chunks));

            this.file1 = TestHelpers.CreateFile(0, 0, "file1", file1DataSource);
            items.Add(this.file1);

            var file2Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                2, 22, 52
            }, TestHelpers.TestTransform);
            var file2DataSource = new NefsItemListDataSource(items, 456, new NefsItemSize(789, file2Chunks));

            this.file2 = TestHelpers.CreateFile(1, 1, "file2", file2DataSource);
            items.Add(this.file2);

            this.dir1 = TestHelpers.CreateDirectory(2, 2, "dir1");
            items.Add(this.dir1);

            var file3Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                3, 13, 23
            }, TestHelpers.TestTransform);
            var file3DataSource = new NefsItemListDataSource(items, 222, new NefsItemSize(333, file3Chunks));

            this.file3 = TestHelpers.CreateFile(3, this.dir1.Id.Value, "file3", file3DataSource);
            items.Add(this.file3);

            var file4DataSource = new NefsItemListDataSource(items, 777, new NefsItemSize(444));

            this.file4NotCompressed = TestHelpers.CreateFile(4, this.dir1.Id.Value, "file4", file4DataSource);
            items.Add(this.file4NotCompressed);

            this.testItems = items;
        }
Beispiel #13
0
        /// <summary>
        /// Creates a <see cref="NefsArchive"/> to be used for testing.
        /// </summary>
        /// <param name="filePath">The file path to associate with the archive.</param>
        /// <returns>An archive object.</returns>
        /// <remarks><![CDATA[ Test archive items: /file1 /dir1 /dir1/file2 ]]></remarks>
        internal static NefsArchive CreateTestArchive(string filePath)
        {
            var items = new NefsItemList(filePath);

            var transform = new NefsDataTransform(50, true);

            var file1Attributes = new NefsItemAttributes(v20IsZlib: true);
            var file1Chunks     = NefsDataChunk.CreateChunkList(new List <UInt32> {
                2, 3, 4
            }, transform);
            var file1DataSource = new NefsItemListDataSource(items, 100, new NefsItemSize(20, file1Chunks));
            var file1           = new NefsItem(Guid.NewGuid(), new NefsItemId(0), "file1", new NefsItemId(0), file1DataSource, transform, file1Attributes);

            items.Add(file1);

            var dir1Attributes = new NefsItemAttributes(isDirectory: true);
            var dir1DataSource = new NefsEmptyDataSource();
            var dir1           = new NefsItem(Guid.NewGuid(), new NefsItemId(1), "dir1", new NefsItemId(1), dir1DataSource, null, dir1Attributes);

            items.Add(dir1);

            var file2Attributes = new NefsItemAttributes(v20IsZlib: true);
            var file2Chunks     = NefsDataChunk.CreateChunkList(new List <UInt32> {
                5, 6, 7
            }, transform);
            var file2DataSource = new NefsItemListDataSource(items, 104, new NefsItemSize(15, file2Chunks));
            var file2           = new NefsItem(Guid.NewGuid(), new NefsItemId(2), "file2", dir1.Id, file2DataSource, transform, file2Attributes);

            items.Add(file2);

            var intro  = new NefsHeaderIntro();
            var toc    = new Nefs20HeaderIntroToc();
            var header = new Nefs20Header(intro, toc, items);

            return(new NefsArchive(header, items));
        }
Beispiel #14
0
        public void NefsHeaderPart1_MultipleItems_EntriesPopulated()
        {
            var items = new NefsItemList(@"C:\archive.nefs");

            var file1Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                11, 12, 13
            }, TestHelpers.TestTransform);
            var file1DataSource = new NefsItemListDataSource(items, 123, new NefsItemSize(456, file1Chunks));
            var file1           = TestHelpers.CreateFile(0, 0, "file1", file1DataSource);

            items.Add(file1);

            var file2Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                14, 15, 16
            }, TestHelpers.TestTransform);
            var file2DataSource = new NefsItemListDataSource(items, 456, new NefsItemSize(789, file2Chunks));
            var file2           = TestHelpers.CreateFile(1, 1, "file2", file2DataSource);

            items.Add(file2);

            var dir1 = TestHelpers.CreateDirectory(2, 2, "dir1");

            items.Add(dir1);

            var p4 = new Nefs20HeaderPart4(items);
            var p1 = new NefsHeaderPart1(items, p4);

            Assert.Equal(3, p1.EntriesByGuid.Count);
            Assert.Equal(3, p1.EntriesByIndex.Count);

            /*
             * dir1
             */

            // Offset to data and index to p4 are both 0 since this is a directory
            Assert.Equal(2, (int)p1.EntriesByGuid[dir1.Guid].Id.Value);
            Assert.Equal(0, (int)p1.EntriesByGuid[dir1.Guid].OffsetToData);
            Assert.Equal(0, (int)p1.EntriesByGuid[dir1.Guid].IndexPart2);
            Assert.Equal(0, (int)p1.EntriesByGuid[dir1.Guid].IndexPart4);

            /*
             * file1
             */

            Assert.Equal(0, (int)p1.EntriesByGuid[file1.Guid].Id.Value);
            Assert.Equal(123, (int)p1.EntriesByGuid[file1.Guid].OffsetToData);
            Assert.Equal(1, (int)p1.EntriesByGuid[file1.Guid].IndexPart2);
            Assert.Equal(0, (int)p1.EntriesByGuid[file1.Guid].IndexPart4);

            /*
             * file2
             */

            Assert.Equal(1, (int)p1.EntriesByGuid[file2.Guid].Id.Value);
            Assert.Equal(456, (int)p1.EntriesByGuid[file2.Guid].OffsetToData);
            Assert.Equal(2, (int)p1.EntriesByGuid[file2.Guid].IndexPart2);

            // There are 3 chunks for file1, so file2's chunks start right after that (hence p4
            // index == 3)
            Assert.Equal(3, (int)p1.EntriesByGuid[file2.Guid].IndexPart4);
        }
Beispiel #15
0
        public void NefsHeaderPart2_MultipleItems_EntriesPopulated()
        {
            var items = new NefsItemList(@"C:\archive.nefs");

            var file1Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                11, 12, 13
            }, TestHelpers.TestTransform);
            var file1DataSource = new NefsItemListDataSource(items, 123, new NefsItemSize(456, file1Chunks));
            var file1           = TestHelpers.CreateFile(0, 0, "file1", file1DataSource);

            items.Add(file1);

            var file2Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                14, 15, 16
            }, TestHelpers.TestTransform);
            var file2DataSource = new NefsItemListDataSource(items, 456, new NefsItemSize(789, file2Chunks));
            var file2           = TestHelpers.CreateFile(1, 1, "file2", file2DataSource);

            items.Add(file2);

            var dir1 = TestHelpers.CreateDirectory(2, 2, "dir1");

            items.Add(dir1);

            var file3Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                22, 23, 24
            }, TestHelpers.TestTransform);
            var file3DataSource = new NefsItemListDataSource(items, 222, new NefsItemSize(333, file3Chunks));
            var file3           = TestHelpers.CreateFile(3, dir1.Id.Value, "file3", file3DataSource);

            items.Add(file3);

            var p3 = new NefsHeaderPart3(items);
            var p2 = new NefsHeaderPart2(items, p3);

            Assert.Equal(4, p2.EntriesByIndex.Count);

            // NOTE: Part 3 is the strings table. So offset into p3 must take into account null
            // terminated file/dir names. Also note strings table is alphabetized. Also note the
            // data file name is added to the strings table.

            // NOTE: The order of part 2 is generated by depth first traversal of the file tree,
            // with items sorted by filename.

            /*
             * dir1
             */

            Assert.Equal(2, (int)p2.EntriesByIndex[0].Id.Value);
            Assert.Equal(2, (int)p2.EntriesByIndex[0].Data0x00_DirectoryId.Value);
            Assert.Equal(3, (int)p2.EntriesByIndex[0].Data0x04_FirstChildId.Value);
            Assert.Equal(0, (int)p2.EntriesByIndex[0].Data0x0c_ExtractedSize.Value);
            Assert.Equal(13, (int)p2.EntriesByIndex[0].Data0x08_OffsetIntoPart3.Value);

            /*
             * file3
             */

            Assert.Equal(3, (int)p2.EntriesByIndex[1].Id.Value);
            Assert.Equal(2, (int)p2.EntriesByIndex[1].Data0x00_DirectoryId.Value);
            Assert.Equal(3, (int)p2.EntriesByIndex[1].Data0x04_FirstChildId.Value);
            Assert.Equal(333, (int)p2.EntriesByIndex[1].Data0x0c_ExtractedSize.Value);
            Assert.Equal(30, (int)p2.EntriesByIndex[1].Data0x08_OffsetIntoPart3.Value);

            /*
             * file1
             */

            Assert.Equal(0, (int)p2.EntriesByIndex[2].Id.Value);
            Assert.Equal(0, (int)p2.EntriesByIndex[2].DirectoryId.Value);
            Assert.Equal(0, (int)p2.EntriesByIndex[2].FirstChildId.Value);
            Assert.Equal(456, (int)p2.EntriesByIndex[2].ExtractedSize);
            Assert.Equal(18, (int)p2.EntriesByIndex[2].OffsetIntoPart3);

            /*
             * file2
             */

            Assert.Equal(1, (int)p2.EntriesByIndex[3].Id.Value);
            Assert.Equal(1, (int)p2.EntriesByIndex[3].DirectoryId.Value);
            Assert.Equal(1, (int)p2.EntriesByIndex[3].FirstChildId.Value);
            Assert.Equal(789, (int)p2.EntriesByIndex[3].ExtractedSize);
            Assert.Equal(24, (int)p2.EntriesByIndex[3].OffsetIntoPart3);
        }
Beispiel #16
0
        public void NefsHeaderPart6_MultipleItems_EntriesPopulated()
        {
            var items = new NefsItemList(@"C:\archive.nefs");

            var file1Attributes = new NefsItemAttributes(
                part6Volume: 12,
                part6Unknown0x3: 14);
            var file1Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                11, 12, 13
            }, TestHelpers.TestTransform);
            var file1DataSource = new NefsItemListDataSource(items, 123, new NefsItemSize(456, file1Chunks));
            var file1           = new NefsItem(Guid.NewGuid(), new NefsItemId(0), "file1", new NefsItemId(0), file1DataSource, TestHelpers.TestTransform, file1Attributes);

            items.Add(file1);

            var file2Attributes = new NefsItemAttributes(
                part6Volume: 6,
                part6Unknown0x3: 7);
            var file2Chunks = NefsDataChunk.CreateChunkList(new List <UInt32> {
                14, 15, 16
            }, TestHelpers.TestTransform);
            var file2DataSource = new NefsItemListDataSource(items, 456, new NefsItemSize(789, file2Chunks));
            var file2           = new NefsItem(Guid.NewGuid(), new NefsItemId(1), "file2", new NefsItemId(1), file2DataSource, TestHelpers.TestTransform, file2Attributes);

            items.Add(file2);

            var dir1Attributes = new NefsItemAttributes(
                isDirectory: true,
                part6Volume: 1,
                part6Unknown0x3: 2);
            var dir1DataSource = new NefsEmptyDataSource();
            var dir1           = new NefsItem(Guid.NewGuid(), new NefsItemId(2), "dir1", new NefsItemId(2), dir1DataSource, null, dir1Attributes);

            items.Add(dir1);

            var p6 = new Nefs20HeaderPart6(items);

            Assert.Equal(3, p6.EntriesByGuid.Count);
            Assert.Equal(3, p6.EntriesByIndex.Count);

            /*
             * file1
             */

            Assert.Equal(file1Attributes.Part6Volume, p6.EntriesByGuid[file1.Guid].Volume);
            Assert.Equal(file1Attributes.Part6Unknown0x3, p6.EntriesByGuid[file1.Guid].Unknown0x3);

            /*
             * file2
             */

            Assert.Equal(file2Attributes.Part6Volume, p6.EntriesByGuid[file2.Guid].Volume);
            Assert.Equal(file2Attributes.Part6Unknown0x3, p6.EntriesByGuid[file2.Guid].Unknown0x3);

            /*
             * dir1
             */

            var attributes = p6.EntriesByGuid[dir1.Guid].CreateAttributes();

            Assert.Equal(dir1Attributes.Part6Volume, p6.EntriesByGuid[dir1.Guid].Volume);
            Assert.Equal(dir1Attributes.Part6Unknown0x3, p6.EntriesByGuid[dir1.Guid].Unknown0x3);
            Assert.True(attributes.IsDirectory);
        }