Ejemplo n.º 1
0
        public IReadOnlyCollection <String> ReadLines()
        {
            unsafe
            {
                Int32 headerOffset = Positive(_br.ReadInt32());
                Int32 headerCount  = Positive(_br.ReadInt32());
                Int32 headerSize   = checked (headerCount * sizeof(GVHeaderEntry));

                Int32 contentOffset = Positive(_br.ReadInt32());
                Int32 contentSize   = Positive(_br.ReadInt32());

                _stream.SetPosition(headerOffset);
                Byte[] header = _stream.ReadBytes(headerSize);

                _stream.SetPosition(contentOffset);
                Byte[] content = _stream.ReadBytes(contentSize);

                String[] result = new String[headerCount];

                fixed(Byte *headerBytes = header)
                fixed(Byte * contentBytes = content)
                {
                    GVHeaderEntry *entriesPtr = (GVHeaderEntry *)headerBytes;
                    SByte *        contentPtr = (SByte *)contentBytes;

                    for (Int32 i = 0; i < headerCount; i++)
                    {
                        if (IsEmpty(entriesPtr, i))
                        {
                            result[i] = $"{i:D4}|";
                            continue;
                        }

                        GVHeaderEntry entry = entriesPtr[i];

                        CheckEntry(i, ref entry, contentPtr);

                        Int32  offset = InRange(entry.Offset, minValue: 0, maxValue: contentSize - 1);
                        Int32  size   = InRange(entry.Size, minValue: 2, maxValue: contentSize - offset); // \0 terminated strings
                        UInt32 value  = entry.Value;
                        UInt32 mask   = entry.Mask;

                        String name = new String(contentPtr, offset, size - 1, Encoding.ASCII);

                        if ((value & mask) != value)
                        {
                            throw new InvalidDataException($"Value 0x[{value:X8}] of the variable [{i:D4}:{name}] is out of mask [{mask:X8}].");
                        }

                        FormatTypeAndValue(mask, value, out var formattedType, out var formattedValue);
                        result[i] = $"{i:D4}| {formattedType} {name} = {formattedValue}";
                    }
                }

                return(result);
            }
        }
Ejemplo n.º 2
0
        private static unsafe Boolean IsEmpty(GVHeaderEntry *entriesPtr, Int32 i)
        {
            Int64 *raw = (Int64 *)(entriesPtr + i);

            return(raw[0] == 0 && raw[1] == 0);
        }