protected override IList <IStructuralNode> CreateChildNodes()
        {
            const int IsDirectoryFlag = unchecked ((int)0x80000000);

            var id        = _provider.Data.Read <int>(_offset + 4);
            var rvaTarget = _resourceBase + (id & ~IsDirectoryFlag);

            var keyNode = new TemplatedStructuralNode(_provider.Data, this, _named ? "Name RVA" : "ID", StandardTemplates.Int32, _offset);

            if ((id & IsDirectoryFlag) != 0)
            {
                return(new IStructuralNode[]
                {
                    keyNode,
                    new TemplatedStructuralNode(_provider.Data, this, "Subdirectory RVA", StandardTemplates.Int32, _offset + 4),
                    new ResourceDirectoryNode(_provider, this, _resourceBase, rvaTarget, _depth + 1),
                });
            }
            else
            {
                var dataRVA  = _provider.Data.Read <int>(rvaTarget);
                var dataSize = _provider.Data.Read <int>(rvaTarget + 4);

                var dataFilePos = _provider.MapRVAtoFile(dataRVA);

                return(new IStructuralNode[]
                {
                    keyNode,
                    new TemplatedStructuralNode(_provider.Data, this, "Data Entry RVA", StandardTemplates.Int32, _offset + 4),
                    new TemplatedStructuralNode(_provider.Data, this, "Data Entry", PETemplates.ResourceDataEntry, rvaTarget),
                    new TemplatedStructuralNode(_provider.Data, this, "Data", StandardTemplates.Blob(dataSize), dataFilePos),
                });
            }
        }
        public void Children()
        {
            var mockData = new Mock <IDataSource>(MockBehavior.Strict);

            var mockChildTemplate = new Mock <IStructuralNodeTemplate>(MockBehavior.Strict);

            mockChildTemplate.Setup(x => x.Width).Returns(4);

            var mockTemplate = new Mock <IStructuralNodeTemplate>(MockBehavior.Strict);

            mockTemplate.Setup(x => x.Width).Returns(12);
            mockTemplate.Setup(x => x.Components).Returns(new[]
            {
                new Component("A", mockChildTemplate.Object, 0),
                new Component("B", mockChildTemplate.Object, 4),
                new Component("C", mockChildTemplate.Object, 8),
            });

            var node = new TemplatedStructuralNode(mockData.Object, null, "root", mockTemplate.Object, 100);

            Assert.That(node.Children.Select(x => x.Name), Is.EqualTo(new[] { "A", "B", "C" }));
            Assert.That(node.Children.Select(x => x.ByteRange !.Offset), Is.EqualTo(new[] { 100, 104, 108 }));
            Assert.That(node.Children.Select(x => x.ByteRange !.Length), Has.All.EqualTo(4));
            Assert.That(node.Children.Select(x => x.Parent), Has.All.EqualTo(node));
        }
        protected override IList <IStructuralNode> CreateChildNodes()
        {
            var nameEntryCount = _provider.Data.Read <ushort>(_offset + 12);
            var idEntryCount   = _provider.Data.Read <ushort>(_offset + 14);

            var result = new IStructuralNode[nameEntryCount + idEntryCount + 1];

            result[0] = new TemplatedStructuralNode(_provider.Data, this, "Header", PETemplates.ResourceDirectoryHeader, _offset);

            var offset = _offset + PETemplates.ResourceDirectoryHeader.Width;
            var index  = 1;

            for (var i = 0; i < nameEntryCount; i++)
            {
                result[index++] = new ResourceDirectoryEntryNode(_provider, this, _resourceBase, offset, true, _depth);
                offset         += 8;
            }

            for (var i = 0; i < idEntryCount; i++)
            {
                result[index++] = new ResourceDirectoryEntryNode(_provider, this, _resourceBase, offset, false, _depth);
                offset         += 8;
            }

            return(result);
        }
        public void Value()
        {
            var mockData = new Mock <IDataSource>(MockBehavior.Strict);

            var mockTemplate = new Mock <IStructuralNodeTemplate>(MockBehavior.Strict);

            mockTemplate.Setup(x => x.Width).Returns(10);
            mockTemplate.Setup(x => x.GetValue(mockData.Object, 100)).Returns(42);

            var node = new TemplatedStructuralNode(
                mockData.Object,
                null,
                "<name>",
                mockTemplate.Object,
                100);

            Assert.That(node.Value, Is.EqualTo(42));
        }
        public void ChildrenEmpty()
        {
            var mockData = new Mock <IDataSource>(MockBehavior.Strict);

            var mockTemplate = new Mock <IStructuralNodeTemplate>(MockBehavior.Strict);

            mockTemplate.Setup(x => x.Width).Returns(10);
            mockTemplate.Setup(x => x.Components).Returns(Array.Empty <Component>());

            var node = new TemplatedStructuralNode(
                mockData.Object,
                null,
                "<name>",
                mockTemplate.Object,
                100);

            Assert.That(node.ByteRange.Offset, Is.EqualTo(100));
            Assert.That(node.ByteRange.Length, Is.EqualTo(10));
            Assert.That(node.Children.Count, Is.EqualTo(0));
        }