/// <summary>
        /// Writes header information into output stream (w/o CRC and table offsets/paddings).
        /// </summary>
        /// <param name="writer">Binary writer with correct endianness.</param>
        /// <param name="isPreAllocationCall">If true no assembly name will be written.</param>
        public void Write(
            TinyBinaryWriter writer,
            Boolean isPreAllocationCall)
        {
            writer.WriteString("MSSpot1");

            writer.WriteUInt32(0); // header CRC
            writer.WriteUInt32(0); // assembly CRC

            writer.WriteUInt32(writer.IsBigEndian ? FLAGS_BIG_ENDIAN : FLAGS_LITTLE_ENDIAN);

            // This CRC calculated only for BE assemblies!!!
            writer.WriteUInt32(writer.IsBigEndian ? _context.NativeMethodsCrc.Current : 0x00);
            writer.WriteUInt32(0xFFFFFFFF); // Native methods offset

            writer.WriteVersion(_context.AssemblyDefinition.Name.Version);

            writer.WriteUInt16(isPreAllocationCall
                ? (UInt16) 0x0000
                : _context.StringTable.GetOrCreateStringId(_context.AssemblyDefinition.Name.Name));
            writer.WriteUInt16(1); // String table version

            if (isPreAllocationCall)
            {
                _tablesOffset = writer.BaseStream.Position;
                for (var i = 0; i < 16; ++i)
                {
                    writer.WriteUInt32(0);
                }

                writer.WriteUInt32(0); // Number of patched methods

                _paddingsOffset = writer.BaseStream.Position;
                for (var i = 0; i < 16; ++i)
                {
                    writer.WriteByte(0);
                }
            }
            else
            {
                writer.BaseStream.Seek(12, SeekOrigin.Begin);

                var assemblyCrc32 = ComputeCrc32(writer.BaseStream,
                    _paddingsOffset, writer.BaseStream.Length - _paddingsOffset);
                writer.WriteUInt32(assemblyCrc32);

                writer.BaseStream.Seek(8, SeekOrigin.Begin);

                var headerCrc32 = ComputeCrc32(writer.BaseStream, 0, _paddingsOffset);
                writer.WriteUInt32(headerCrc32);
            }
        }
示例#2
0
        /// <inheritdoc/>
        protected override void WriteSingleItem(
            TinyBinaryWriter writer,
            MethodReference item)
        {
            UInt16 referenceId;

            _context.TypeReferencesTable.TryGetTypeReferenceId(item.DeclaringType, out referenceId);

            WriteStringReference(writer, item.Name);
            writer.WriteUInt16(referenceId);

            writer.WriteUInt16(_context.SignaturesTable.GetOrCreateSignatureId(item));
            writer.WriteUInt16(0); // padding
        }
示例#3
0
        private void WriteAttributes(
            TinyBinaryWriter writer,
            UInt16 tableNumber,
            IEnumerable <Tuple <CustomAttribute, UInt16> > attributes)
        {
            foreach (var item in attributes)
            {
                var attribute        = item.Item1;
                var targetIdentifier = item.Item2;

                writer.WriteUInt16(tableNumber);
                writer.WriteUInt16(targetIdentifier);

                writer.WriteUInt16(_context.GetMethodReferenceId(attribute.Constructor));
                writer.WriteUInt16(_context.SignaturesTable.GetOrCreateSignatureId(attribute));
            }
        }
示例#4
0
        private void WriteMethodBodies(
            Collection <MethodDefinition> methods,
            Collection <TypeReference> iInterfaces,
            TinyBinaryWriter writer)
        {
            UInt16 firstMethodId        = 0xFFFF;
            var    virtualMethodsNumber = 0;

            foreach (var method in methods.Where(item => item.IsVirtual))
            {
                firstMethodId = Math.Min(firstMethodId, _context.ByteCodeTable.GetMethodId(method));
                CreateMethodSignatures(method);
                ++virtualMethodsNumber;
            }

            var instanceMethodsNumber = 0;

            foreach (var method in methods.Where(item => !(item.IsVirtual || item.IsStatic)))
            {
                firstMethodId = Math.Min(firstMethodId, _context.ByteCodeTable.GetMethodId(method));
                CreateMethodSignatures(method);
                ++instanceMethodsNumber;
            }

            var staticMethodsNumber = 0;

            foreach (var method in methods.Where(item => item.IsStatic))
            {
                firstMethodId = Math.Min(firstMethodId, _context.ByteCodeTable.GetMethodId(method));
                CreateMethodSignatures(method);
                ++staticMethodsNumber;
            }

            if (virtualMethodsNumber + instanceMethodsNumber + staticMethodsNumber == 0)
            {
                firstMethodId = _context.ByteCodeTable.NextMethodId;
            }

            writer.WriteUInt16(_context.SignaturesTable.GetOrCreateSignatureId(iInterfaces));

            writer.WriteUInt16(firstMethodId);

            writer.WriteByte((Byte)virtualMethodsNumber);
            writer.WriteByte((Byte)instanceMethodsNumber);
            writer.WriteByte((Byte)staticMethodsNumber);
        }
        private void WriteAttributes(
            TinyBinaryWriter writer,
            UInt16 tableNumber,
            IEnumerable<Tuple<CustomAttribute, UInt16>> attributes)
        {
            foreach (var item in attributes)
            {
                var attribute = item.Item1;
                var targetIdentifier = item.Item2;

                writer.WriteUInt16(tableNumber);
                writer.WriteUInt16(targetIdentifier);

                writer.WriteUInt16(_context.GetMethodReferenceId(attribute.Constructor));
                writer.WriteUInt16(_context.SignaturesTable.GetOrCreateSignatureId(attribute));
            }
        }
示例#6
0
        private void WriteClassFields(
            IList <FieldDefinition> fieldsList,
            TinyBinaryWriter writer)
        {
            var firstStaticFieldId = _context.FieldsTable.MaxFieldId;
            var staticFieldsNumber = 0;

            foreach (var field in fieldsList.Where(item => item.IsStatic))
            {
                UInt16 fieldReferenceId;
                _context.FieldsTable.TryGetFieldReferenceId(field, true, out fieldReferenceId);
                firstStaticFieldId = Math.Min(firstStaticFieldId, fieldReferenceId);

                _context.SignaturesTable.GetOrCreateSignatureId(field);
                _context.StringTable.GetOrCreateStringId(field.Name);

                ++staticFieldsNumber;
            }

            var firstInstanseFieldId = _context.FieldsTable.MaxFieldId;
            var instanceFieldsNumber = 0;

            foreach (var field in fieldsList.Where(item => !item.IsStatic))
            {
                UInt16 fieldReferenceId;
                _context.FieldsTable.TryGetFieldReferenceId(field, true, out fieldReferenceId);
                firstInstanseFieldId = Math.Min(firstInstanseFieldId, fieldReferenceId);

                _context.SignaturesTable.GetOrCreateSignatureId(field);
                _context.StringTable.GetOrCreateStringId(field.Name);

                ++instanceFieldsNumber;
            }

            if (firstStaticFieldId > firstInstanseFieldId)
            {
                firstStaticFieldId = firstInstanseFieldId;
            }

            writer.WriteUInt16(firstStaticFieldId);
            writer.WriteUInt16(firstInstanseFieldId);

            writer.WriteByte((Byte)staticFieldsNumber);
            writer.WriteByte((Byte)instanceFieldsNumber);
        }
示例#7
0
        /// <inheritdoc/>
        protected override void WriteSingleItem(
            TinyBinaryWriter writer,
            AssemblyNameReference item)
        {
            WriteStringReference(writer, item.Name);
            writer.WriteUInt16(0); // padding

            writer.WriteVersion(item.Version);
        }
        /// <inheritdoc/>
        public void Write(
            TinyBinaryWriter writer)
        {
            var offset = 0U;
            foreach (var item in _resouces)
            {
                writer.WriteUInt32(0x02); // Version
                writer.WriteUInt32(0x04); // Size of header
                writer.WriteUInt32(0x08); // Size of resouce header

                writer.WriteUInt32(item.Item2);
                
                writer.WriteUInt16(item.Item1);
                writer.WriteUInt16(0x0); // paddding

                writer.WriteUInt32(offset);
                offset += 8; // Size of resource table record
            }

        }
示例#9
0
        /// <inheritdoc/>
        public void Write(
            TinyBinaryWriter writer)
        {
            var offset = 0U;

            foreach (var item in _resouces)
            {
                writer.WriteUInt32(0x02); // Version
                writer.WriteUInt32(0x04); // Size of header
                writer.WriteUInt32(0x08); // Size of resouce header

                writer.WriteUInt32(item.Item2);

                writer.WriteUInt16(item.Item1);
                writer.WriteUInt16(0x0); // paddding

                writer.WriteUInt32(offset);
                offset += 8; // Size of resource table record
            }
        }
        public void Process(
            TinyBinaryWriter writer)
        {
            writer.WriteUInt32((UInt32)_bitmap.Width);
            writer.WriteUInt32((UInt32)_bitmap.Height);

            writer.WriteUInt16(0x00);   // flags

            var tinyImageFormat = GetTinytImageFormat(_bitmap.RawFormat);

            if (tinyImageFormat != 0)
            {
                writer.WriteByte(0x01);     // bpp
                writer.WriteByte(tinyImageFormat);
                _bitmap.Save(writer.BaseStream, _bitmap.RawFormat);
            }
            else
            {
                writer.WriteByte(0x10);     // bpp
                writer.WriteByte(tinyImageFormat);

                var rect = new Rectangle(Point.Empty, _bitmap.Size);
                using (var convertedBitmap =
                           _bitmap.Clone(new Rectangle(Point.Empty, _bitmap.Size),
                                         PixelFormat.Format16bppRgb565))
                {
                    var bitmapData = convertedBitmap.LockBits(
                        rect, ImageLockMode.ReadOnly, convertedBitmap.PixelFormat);

                    var buffer = new Int16[bitmapData.Stride * convertedBitmap.Height / sizeof(Int16)];
                    System.Runtime.InteropServices.Marshal.Copy(
                        bitmapData.Scan0, buffer, 0, buffer.Length);

                    convertedBitmap.UnlockBits(bitmapData);
                    foreach (var item in buffer)
                    {
                        writer.WriteInt16(item);
                    }
                }
            }
        }
        public void Process(
            TinyBinaryWriter writer)
        {
            writer.WriteUInt32((UInt32)_bitmap.Width);
            writer.WriteUInt32((UInt32)_bitmap.Height);

            writer.WriteUInt16(0x00);   // flags

            var tinyImageFormat = GetTinytImageFormat(_bitmap.RawFormat);

            if (tinyImageFormat != 0)
            {
                writer.WriteByte(0x01);     // bpp
                writer.WriteByte(tinyImageFormat);
                _bitmap.Save(writer.BaseStream, _bitmap.RawFormat);
            }
            else
            {
                writer.WriteByte(0x10);     // bpp
                writer.WriteByte(tinyImageFormat);

                var rect = new Rectangle(Point.Empty, _bitmap.Size);
                using (var convertedBitmap =
                    _bitmap.Clone(new Rectangle(Point.Empty, _bitmap.Size),
                        PixelFormat.Format16bppRgb565))
                {
                    var bitmapData = convertedBitmap.LockBits(
                        rect, ImageLockMode.ReadOnly, convertedBitmap.PixelFormat);

                    var buffer = new Int16[bitmapData.Stride * convertedBitmap.Height / sizeof(Int16)];
                    System.Runtime.InteropServices.Marshal.Copy(
                        bitmapData.Scan0, buffer, 0, buffer.Length);

                    convertedBitmap.UnlockBits(bitmapData);
                    foreach (var item in buffer)
                    {
                        writer.WriteInt16(item);
                    }
                }
            }
        }
        /// <summary>
        /// Processes original data and writes processed data into output writer.
        /// </summary>
        /// <param name="writer">Endianness-aware binary writer.</param>
        public void Process(
            TinyBinaryWriter writer)
        {
            using (var stream = new MemoryStream(_fontResouce, false))
            using (var reader = new BinaryReader(stream))
            {
                // CLR_GFX_FontDescription

                {
                    // CLR_GFX_FontMetrics

                    writer.WriteUInt16(reader.ReadUInt16()); // CLR_GFX_FontMetrics.m_height
                    writer.WriteInt16(reader.ReadInt16()); // CLR_GFX_FontMetrics.m_offset

                    writer.WriteInt16(reader.ReadInt16()); // CLR_GFX_FontMetrics.m_ascent
                    writer.WriteInt16(reader.ReadInt16()); // CLR_GFX_FontMetrics.m_descent

                    writer.WriteInt16(reader.ReadInt16()); // CLR_GFX_FontMetrics.m_internalLeading
                    writer.WriteInt16(reader.ReadInt16()); // CLR_GFX_FontMetrics.m_externalLeading

                    writer.WriteInt16(reader.ReadInt16()); // CLR_GFX_FontMetrics.m_aveCharWidth
                    writer.WriteInt16(reader.ReadInt16()); // CLR_GFX_FontMetrics.m_aveCharWidth
                }

                var rangesCount = reader.ReadInt16();
                writer.WriteInt16(rangesCount); // CLR_GFX_FontDescription.m_ranges
                var charactersCount = reader.ReadInt16();
                writer.WriteInt16(charactersCount); // CLR_GFX_FontDescription.m_characters

                var flags = reader.ReadInt16();
                writer.WriteInt16(flags); // CLR_GFX_FontDescription.m_flags
                writer.WriteInt16(reader.ReadInt16()); // CLR_GFX_FontDescription.m_pad

                // CLR_GFX_BitmapDescription

                var width = reader.ReadUInt32();
                writer.WriteUInt32(width); // CLR_GFX_BitmapDescription.m_width
                var height = reader.ReadUInt32();
                writer.WriteUInt32(height); // CLR_GFX_BitmapDescription.m_height

                writer.WriteUInt16(reader.ReadUInt16()); // CLR_GFX_BitmapDescription.m_flags

                var bitsPerPixel = reader.ReadByte();
                writer.WriteByte(bitsPerPixel); // CLR_GFX_BitmapDescription.m_bitsPerPixel
                writer.WriteByte(reader.ReadByte()); // CLR_GFX_BitmapDescription.m_type

                for (var i = 0; i <= rangesCount; ++i) // Including sentinel range
                {
                    // CLR_GFX_FontCharacterRange

                    writer.WriteUInt32(reader.ReadUInt32()); // CLR_GFX_FontCharacterRange.m_indexOfFirstFontCharacter

                    writer.WriteUInt16(reader.ReadUInt16()); // CLR_GFX_FontCharacterRange.m_firstChar
                    writer.WriteUInt16(reader.ReadUInt16()); // CLR_GFX_FontCharacterRange.m_lastChar

                    writer.WriteUInt32(reader.ReadUInt32()); // CLR_GFX_FontCharacterRange.m_rangeOffset
                }

                for (var i = 0; i <= charactersCount; ++i) // Including sentinel character
                {
                    // CLR_GFX_FontCharacter

                    writer.WriteUInt16(reader.ReadUInt16()); // CLR_GFX_FontCharacter.m_offset

                    writer.WriteByte(reader.ReadByte()); // CLR_GFX_FontCharacter.m_marginLeft
                    writer.WriteByte(reader.ReadByte()); // CLR_GFX_FontCharacter.m_marginRight
                }

                if (bitsPerPixel == 0)
                {
                    bitsPerPixel = 16; // Native value, rest calculations are same
                }
                var totalSizeInWords = ((width * bitsPerPixel + 31) / 32) * height;
                for (var i = 0; i < totalSizeInWords; ++i)
                {
                    writer.WriteUInt32(reader.ReadUInt32());
                }

                if ((flags & FLAG_FONT_EX) == FLAG_FONT_EX)
                {
                    // TODO: implement it according original idea if needed
                }

                while (stream.Position < stream.Length)
                {
                    writer.WriteByte(reader.ReadByte());
                }
            }
        }
示例#13
0
        private void WriteExceptionsTable()
        {
            if (!_body.HasExceptionHandlers)
            {
                return;
            }

            foreach (var handler in _body.ExceptionHandlers
                     .OrderBy(item => item.HandlerStart.Offset))
            {
                switch (handler.HandlerType)
                {
                case ExceptionHandlerType.Catch:
                    _writer.WriteUInt16(0x0000);
                    _writer.WriteUInt16(GetTypeReferenceId(handler.CatchType, 0x8000));
                    break;

                case ExceptionHandlerType.Fault:
                    _writer.WriteUInt16(0x0001);
                    _writer.WriteUInt16(0x0000);
                    break;

                case ExceptionHandlerType.Finally:
                    _writer.WriteUInt16(0x0002);
                    _writer.WriteUInt16(0x0000);
                    break;

                case ExceptionHandlerType.Filter:
                    _writer.WriteUInt16(0x0003);
                    _writer.WriteUInt16((UInt16)handler.FilterStart.Offset);
                    break;
                }

                _writer.WriteUInt16((UInt16)handler.TryStart.Offset);
                _writer.WriteUInt16((UInt16)handler.TryEnd.Offset);
                _writer.WriteUInt16((UInt16)handler.HandlerStart.Offset);
                if (handler.HandlerEnd == null)
                {
                    _writer.WriteUInt16((UInt16)_body.Instructions.Last().Offset);
                }
                else
                {
                    _writer.WriteUInt16((UInt16)handler.HandlerEnd.Offset);
                }
            }

            _writer.WriteByte((Byte)_body.ExceptionHandlers.Count);
        }
示例#14
0
        /// <summary>
        /// Processes original data and writes processed data into output writer.
        /// </summary>
        /// <param name="writer">Endianness-aware binary writer.</param>
        public void Process(
            TinyBinaryWriter writer)
        {
            using (var stream = new MemoryStream(_fontResouce, false))
                using (var reader = new BinaryReader(stream))
                {
                    // CLR_GFX_FontDescription

                    {
                        // CLR_GFX_FontMetrics

                        writer.WriteUInt16(reader.ReadUInt16()); // CLR_GFX_FontMetrics.m_height
                        writer.WriteInt16(reader.ReadInt16());   // CLR_GFX_FontMetrics.m_offset

                        writer.WriteInt16(reader.ReadInt16());   // CLR_GFX_FontMetrics.m_ascent
                        writer.WriteInt16(reader.ReadInt16());   // CLR_GFX_FontMetrics.m_descent

                        writer.WriteInt16(reader.ReadInt16());   // CLR_GFX_FontMetrics.m_internalLeading
                        writer.WriteInt16(reader.ReadInt16());   // CLR_GFX_FontMetrics.m_externalLeading

                        writer.WriteInt16(reader.ReadInt16());   // CLR_GFX_FontMetrics.m_aveCharWidth
                        writer.WriteInt16(reader.ReadInt16());   // CLR_GFX_FontMetrics.m_aveCharWidth
                    }

                    var rangesCount = reader.ReadInt16();
                    writer.WriteInt16(rangesCount);     // CLR_GFX_FontDescription.m_ranges
                    var charactersCount = reader.ReadInt16();
                    writer.WriteInt16(charactersCount); // CLR_GFX_FontDescription.m_characters

                    var flags = reader.ReadInt16();
                    writer.WriteInt16(flags);              // CLR_GFX_FontDescription.m_flags
                    writer.WriteInt16(reader.ReadInt16()); // CLR_GFX_FontDescription.m_pad

                    // CLR_GFX_BitmapDescription

                    var width = reader.ReadUInt32();
                    writer.WriteUInt32(width);               // CLR_GFX_BitmapDescription.m_width
                    var height = reader.ReadUInt32();
                    writer.WriteUInt32(height);              // CLR_GFX_BitmapDescription.m_height

                    writer.WriteUInt16(reader.ReadUInt16()); // CLR_GFX_BitmapDescription.m_flags

                    var bitsPerPixel = reader.ReadByte();
                    writer.WriteByte(bitsPerPixel);        // CLR_GFX_BitmapDescription.m_bitsPerPixel
                    writer.WriteByte(reader.ReadByte());   // CLR_GFX_BitmapDescription.m_type

                    for (var i = 0; i <= rangesCount; ++i) // Including sentinel range
                    {
                        // CLR_GFX_FontCharacterRange

                        writer.WriteUInt32(reader.ReadUInt32()); // CLR_GFX_FontCharacterRange.m_indexOfFirstFontCharacter

                        writer.WriteUInt16(reader.ReadUInt16()); // CLR_GFX_FontCharacterRange.m_firstChar
                        writer.WriteUInt16(reader.ReadUInt16()); // CLR_GFX_FontCharacterRange.m_lastChar

                        writer.WriteUInt32(reader.ReadUInt32()); // CLR_GFX_FontCharacterRange.m_rangeOffset
                    }

                    for (var i = 0; i <= charactersCount; ++i) // Including sentinel character
                    {
                        // CLR_GFX_FontCharacter

                        writer.WriteUInt16(reader.ReadUInt16()); // CLR_GFX_FontCharacter.m_offset

                        writer.WriteByte(reader.ReadByte());     // CLR_GFX_FontCharacter.m_marginLeft
                        writer.WriteByte(reader.ReadByte());     // CLR_GFX_FontCharacter.m_marginRight
                    }

                    if (bitsPerPixel == 0)
                    {
                        bitsPerPixel = 16; // Native value, rest calculations are same
                    }
                    var totalSizeInWords = ((width * bitsPerPixel + 31) / 32) * height;
                    for (var i = 0; i < totalSizeInWords; ++i)
                    {
                        writer.WriteUInt32(reader.ReadUInt32());
                    }

                    if ((flags & FLAG_FONT_EX) == FLAG_FONT_EX)
                    {
                        // TODO: implement it according original idea if needed
                    }

                    while (stream.Position < stream.Length)
                    {
                        writer.WriteByte(reader.ReadByte());
                    }
                }
        }
示例#15
0
 /// <summary>
 /// Writes string reference ID related to passed string value into output stream.
 /// </summary>
 /// <param name="writer">Target binary writer for writing reference ID.</param>
 /// <param name="value">String value for obtaining reference and writing.</param>
 protected void WriteStringReference(
     TinyBinaryWriter writer,
     String value)
 {
     writer.WriteUInt16(GetOrCreateStringId(value));
 }