Beispiel #1
0
        internal static void FromSystemType(
            this SignatureTypeEncoder typeEncoder,
            Type type,
            AssemblyGenerator generator)
        {
            if (type.IsPrimitive)
            {
                typeEncoder.PrimitiveType(GetPrimitiveTypeCode(type));
            }
            else if (type == typeof(string))
            {
                typeEncoder.String();
            }
            else if (type == typeof(object))
            {
                typeEncoder.Object();
            }
            else if (type == typeof(void))
            {
                throw new ArgumentException(
                          "Void type is not allowed in SignatureTypeEncoder. Please, use FromSystemType from ReturnTypeEncoder.");
                //typeEncoder.VoidPointer();
            }
            else if (type.IsArray)
            {
                var elementType = type.GetElementType();
                var rank        = type.GetArrayRank();

                typeEncoder.Array(
                    x => x.FromSystemType(elementType, generator),
                    x => x.Shape(
                        type.GetArrayRank(),
                        ImmutableArray.Create <int>(),
                        ImmutableArray.Create <int>()));
            }
            else if (type.IsGenericType)
            {
                var genericTypeDef   = type.GetGenericTypeDefinition();
                var typeHandler      = generator.GetOrCreateType(genericTypeDef);
                var genericArguments = type.GetGenericArguments();

                var inst = typeEncoder.GenericInstantiation(typeHandler, genericArguments.Length, false);
                foreach (var ga in genericArguments)
                {
                    if (ga.IsGenericParameter)
                    {
                        inst.AddArgument().GenericTypeParameter(ga.GenericParameterPosition);
                    }
                    else
                    {
                        inst.AddArgument().FromSystemType(ga, generator);
                    }
                }
            }
            else
            {
                var typeHandler = generator.GetOrCreateType(type);
                typeEncoder.Type(typeHandler, type.IsValueType);
            }
        }
        public void SignatureTypeEncoder_Array()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            Assert.Same(b, e.Builder);

            SignatureTypeEncoder elementType;
            ArrayShapeEncoder    arrayShape;

            e.Array(out elementType, out arrayShape);
            AssertEx.Equal(new byte[] { 0x14 }, b.ToArray());
            Assert.Same(b, elementType.Builder);
            Assert.Same(b, arrayShape.Builder);
            b.Clear();

            e.Array(
                t => Assert.Same(b, t.Builder),
                s => Assert.Same(b, s.Builder));
            AssertEx.Equal(new byte[] { 0x14 }, b.ToArray());
            b.Clear();

            Assert.Throws <ArgumentNullException>(() => e.Array(null, n => { }));
            Assert.Throws <ArgumentNullException>(() => e.Array(n => { }, null));
        }
        public void SignatureTypeEncoder_GenericInstantiation()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            Assert.Same(b, e.Builder);

            var m = e.GenericInstantiation(MetadataTokens.TypeDefinitionHandle(1), 1, true);

            Assert.Same(b, m.Builder);
            AssertEx.Equal(new byte[] { 0x15, 0x11, 0x04, 0x01 }, b.ToArray());
            b.Clear();

            e.GenericInstantiation(MetadataTokens.TypeReferenceHandle(1), 1, true);
            AssertEx.Equal(new byte[] { 0x15, 0x11, 0x05, 0x01 }, b.ToArray());
            b.Clear();

            e.GenericInstantiation(MetadataTokens.TypeDefinitionHandle(1), 1000, false);
            AssertEx.Equal(new byte[] { 0x15, 0x12, 0x04, 0x83, 0xE8 }, b.ToArray());
            b.Clear();

            e.GenericInstantiation(MetadataTokens.TypeDefinitionHandle(1), ushort.MaxValue, false);
            AssertEx.Equal(new byte[] { 0x15, 0x12, 0x04, 0xC0, 0x00, 0xFF, 0xFF }, b.ToArray());
            b.Clear();

            AssertExtensions.Throws <ArgumentException>(null, () => e.GenericInstantiation(MetadataTokens.TypeSpecificationHandle(1), 1, isValueType: false));
            AssertExtensions.Throws <ArgumentException>(null, () => e.GenericInstantiation(default(EntityHandle), 1, isValueType: false));
            Assert.Throws <ArgumentOutOfRangeException>(() => e.GenericInstantiation(default(TypeDefinitionHandle), 0, true));
            Assert.Throws <ArgumentOutOfRangeException>(() => e.GenericInstantiation(default(TypeDefinitionHandle), -1, true));
            Assert.Throws <ArgumentOutOfRangeException>(() => e.GenericInstantiation(default(TypeDefinitionHandle), ushort.MaxValue + 1, true));
            Assert.Equal(0, b.Count);
        }
        public void SignatureTypeEncoder_FunctionPointer()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            Assert.Same(b, e.Builder);

            var m = e.FunctionPointer(
                SignatureCallingConvention.CDecl,
                FunctionPointerAttributes.HasThis,
                genericParameterCount: 1);

            Assert.Same(b, m.Builder);

            AssertEx.Equal(new byte[] { 0x1B, 0x21, 0x01 }, b.ToArray());
            b.Clear();

            e.FunctionPointer(
                SignatureCallingConvention.Default,
                FunctionPointerAttributes.HasExplicitThis,
                genericParameterCount: 0);

            AssertEx.Equal(new byte[] { 0x1B, 0x60 }, b.ToArray());
            b.Clear();

            e.FunctionPointer();

            AssertEx.Equal(new byte[] { 0x1B, 0x00 }, b.ToArray());
            b.Clear();

            AssertExtensions.Throws <ArgumentException>("attributes", () => e.FunctionPointer(0, (FunctionPointerAttributes)1000, genericParameterCount: 0));
            Assert.Throws <ArgumentOutOfRangeException>(() => e.FunctionPointer(0, 0, genericParameterCount: -1));
            Assert.Throws <ArgumentOutOfRangeException>(() => e.FunctionPointer(0, 0, genericParameterCount: ushort.MaxValue + 1));
            Assert.Equal(0, b.Count);
        }
Beispiel #5
0
        public void SignatureTypeEncoder_VoidPointer()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            e.VoidPointer();
            AssertEx.Equal(new byte[] { 0x0F, 0x01 }, b.ToArray());
        }
Beispiel #6
0
        public void SignatureTypeEncoder_CustomModifiers()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            var a = e.CustomModifiers();

            AssertEx.Equal(new byte[0], b.ToArray());
            Assert.Same(b, a.Builder);
        }
Beispiel #7
0
        public void SignatureTypeEncoder_SZArray()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            var a = e.SZArray();

            AssertEx.Equal(new byte[] { 0x1D }, b.ToArray());
            Assert.Same(b, a.Builder);
        }
Beispiel #8
0
        public void SignatureTypeEncoder_Pointer()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            var p = e.Pointer();

            AssertEx.Equal(new byte[] { 0x0F }, b.ToArray());
            Assert.Same(b, p.Builder);
        }
Beispiel #9
0
        public void SignatureTypeEncoder_GenericTypeParameter()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            e.GenericTypeParameter(0);
            AssertEx.Equal(new byte[] { 0x13, 0x00 }, b.ToArray());
            b.Clear();

            e.GenericTypeParameter(ushort.MaxValue);
            AssertEx.Equal(new byte[] { 0x13, 0xC0, 0x00, 0xFF, 0xFF }, b.ToArray());
            b.Clear();

            Assert.Throws <ArgumentOutOfRangeException>(() => e.GenericTypeParameter(-1));
            Assert.Throws <ArgumentOutOfRangeException>(() => e.GenericTypeParameter(ushort.MaxValue + 1));
            Assert.Equal(0, b.Count);
        }
        internal static void FromSystemType(
            this SignatureTypeEncoder typeEncoder,
            Type type,
            AssemblyGenerator generator)
        {
            if (type.IsPrimitive)
            {
                typeEncoder.PrimitiveType(GetPrimitiveTypeCode(type));
            }
            else if (type == typeof(String))
            {
                typeEncoder.String();
            }
            else if (type == typeof(Object))
            {
                typeEncoder.Object();
            }
            else if (type == typeof(void))
            {
                throw new ArgumentException("Void type is not allowed in SignatureTypeEncoder. Please, use FromSystemType from ReturnTypeEncoder.");
                //typeEncoder.VoidPointer();
            }
            else if (type.IsArray)
            {
                var elementType = type.GetElementType();
                var rank        = type.GetArrayRank();

                typeEncoder.Array(
                    x => x.FromSystemType(elementType, generator),
                    x => x.Shape(
                        type.GetArrayRank(),
                        ImmutableArray.Create <int>(),
                        ImmutableArray.Create <int>()));
            }
            else if (type.IsGenericType)
            {
                throw new ArgumentException("Generic types not supported for now!");
            }
            else
            {
                var typeHandler = generator.GetOrCreateType(type);
                typeEncoder.Type(typeHandler, type.IsValueType);
            }
        }
Beispiel #11
0
        public void SignatureTypeEncoder_Type()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            e.Type(MetadataTokens.TypeDefinitionHandle(1), isValueType: true);
            AssertEx.Equal(new byte[] { 0x11, 0x04 }, b.ToArray());
            b.Clear();

            e.Type(MetadataTokens.TypeDefinitionHandle(1), isValueType: false);
            AssertEx.Equal(new byte[] { 0x12, 0x04 }, b.ToArray());
            b.Clear();

            e.Type(MetadataTokens.TypeReferenceHandle(1), isValueType: false);
            AssertEx.Equal(new byte[] { 0x12, 0x05 }, b.ToArray());
            b.Clear();

            Assert.Throws <ArgumentException>(() => e.Type(MetadataTokens.TypeSpecificationHandle(1), isValueType: false));
            Assert.Throws <ArgumentException>(() => e.Type(default(EntityHandle), isValueType: false));
            Assert.Equal(0, b.Count);
        }
Beispiel #12
0
        private EntityHandle MakeMemberReferenceHandle(TypeSystemEntity methodOrField)
        {
            EntityHandle handle;

            if (!_memberRefOrSpecHandles.TryGetValue(methodOrField, out handle))
            {
                MethodDesc method     = methodOrField as MethodDesc;
                FieldDesc  field      = methodOrField as FieldDesc;
                TypeDesc   owningType = (method != null ? method.OwningType : field.OwningType);
                string     name       = (method != null ? method.Name : field.Name);

                BlobHandle signature = method != null?
                                       MakeSignatureHandle(method.GetTypicalMethodDefinition()) :
                                           MakeSignatureHandle(field);

                handle = _metadataBuilder.AddMemberReference(
                    MakeTypeRefOrSpecHandle(owningType),
                    _metadataBuilder.GetOrAddString(name),
                    signature);

                if (method != null && method.HasInstantiation && !method.IsTypicalMethodDefinition)
                {
                    BlobEncoder methodSpecEncoder = new BlobEncoder(new BlobBuilder());

                    GenericTypeArgumentsEncoder argEncoder = methodSpecEncoder.MethodSpecificationSignature(method.Instantiation.Length);
                    for (int i = 0; i < method.Instantiation.Length; i++)
                    {
                        SignatureTypeEncoder argTypeEncoder = argEncoder.AddArgument();
                        _signatureEmitter.EncodeTypeSignature(argTypeEncoder, method.Instantiation[i]);
                    }

                    handle = _metadataBuilder.AddMethodSpecification(handle, _metadataBuilder.GetOrAddBlob(methodSpecEncoder.Builder));
                }

                _memberRefOrSpecHandles[methodOrField] = handle;
            }

            return(handle);
        }
Beispiel #13
0
        private EntityHandle MakeTypeRefOrSpecHandle(TypeDesc type)
        {
            EntityHandle handle;

            if (!_typeRefOrSpecHandles.TryGetValue(type, out handle))
            {
                if (!type.IsDefType || !type.IsTypeDefinition || type is RuntimeDeterminedType)
                {
                    SignatureTypeEncoder sigEncoder = new SignatureTypeEncoder(new BlobBuilder());
                    _signatureEmitter.EncodeTypeSignature(sigEncoder, type);
                    handle = _metadataBuilder.AddTypeSpecification(_metadataBuilder.GetOrAddBlob(sigEncoder.Builder));
                }
                else
                {
                    handle = MakeTypeRefHandle(type);
                }

                _typeRefOrSpecHandles[type] = handle;
            }

            return(handle);
        }
Beispiel #14
0
        public void SignatureTypeEncoder_Array()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            Assert.Same(b, e.Builder);

            var parts = e.Array();

            AssertEx.Equal(new byte[] { 0x14 }, b.ToArray());
            Assert.Same(b, parts.Item1.Builder);
            Assert.Same(b, parts.Item2.Builder);
            b.Clear();

            e.Array(
                part => Assert.Same(b, part.Builder),
                part => Assert.Same(b, part.Builder));
            AssertEx.Equal(new byte[] { 0x14 }, b.ToArray());
            b.Clear();

            Assert.Throws <ArgumentNullException>(() => e.Array(null, _ => { }));
            Assert.Throws <ArgumentNullException>(() => e.Array(_ => { }, null));
        }
        public void SignatureTypeEncoder_Primitives()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            Assert.Same(b, e.Builder);

            e.Boolean();
            AssertEx.Equal(new byte[] { 0x02 }, b.ToArray());
            b.Clear();

            e.Char();
            AssertEx.Equal(new byte[] { 0x03 }, b.ToArray());
            b.Clear();

            e.SByte();
            AssertEx.Equal(new byte[] { 0x04 }, b.ToArray());
            b.Clear();

            e.Byte();
            AssertEx.Equal(new byte[] { 0x05 }, b.ToArray());
            b.Clear();

            e.Int16();
            AssertEx.Equal(new byte[] { 0x06 }, b.ToArray());
            b.Clear();

            e.UInt16();
            AssertEx.Equal(new byte[] { 0x07 }, b.ToArray());
            b.Clear();

            e.Int32();
            AssertEx.Equal(new byte[] { 0x08 }, b.ToArray());
            b.Clear();

            e.UInt32();
            AssertEx.Equal(new byte[] { 0x09 }, b.ToArray());
            b.Clear();

            e.Int64();
            AssertEx.Equal(new byte[] { 0x0A }, b.ToArray());
            b.Clear();

            e.UInt64();
            AssertEx.Equal(new byte[] { 0x0B }, b.ToArray());
            b.Clear();

            e.Single();
            AssertEx.Equal(new byte[] { 0x0C }, b.ToArray());
            b.Clear();

            e.Double();
            AssertEx.Equal(new byte[] { 0x0D }, b.ToArray());
            b.Clear();

            e.String();
            AssertEx.Equal(new byte[] { 0x0E }, b.ToArray());
            b.Clear();

            e.IntPtr();
            AssertEx.Equal(new byte[] { 0x18 }, b.ToArray());
            b.Clear();

            e.UIntPtr();
            AssertEx.Equal(new byte[] { 0x19 }, b.ToArray());
            b.Clear();

            e.Object();
            AssertEx.Equal(new byte[] { 0x1C }, b.ToArray());
            b.Clear();
        }
Beispiel #16
0
        public void SignatureTypeEncoder_Array()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            var parts = e.Array();
            AssertEx.Equal(new byte[] { 0x14 }, b.ToArray());
            Assert.Same(b, parts.Item1.Builder);
            Assert.Same(b, parts.Item2.Builder);
            b.Clear();

            e.Array(
                part => Assert.Same(b, part.Builder),
                part => Assert.Same(b, part.Builder));
            AssertEx.Equal(new byte[] { 0x14 }, b.ToArray());
            b.Clear();

            Assert.Throws<ArgumentNullException>(() => e.Array(null, _ => { }));
            Assert.Throws<ArgumentNullException>(() => e.Array(_ => { }, null));
        }
Beispiel #17
0
        public void SignatureTypeEncoder_Array()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            SignatureTypeEncoder elementType;
            ArrayShapeEncoder arrayShape;
            e.Array(out elementType, out arrayShape);
            AssertEx.Equal(new byte[] { 0x14 }, b.ToArray());
            Assert.Same(b, elementType.Builder);
            Assert.Same(b, arrayShape.Builder);
            b.Clear();

            e.Array(
                t => Assert.Same(b, t.Builder),
                s => Assert.Same(b, s.Builder));
            AssertEx.Equal(new byte[] { 0x14 }, b.ToArray());
            b.Clear();

            Assert.Throws<ArgumentNullException>(() => e.Array(null, n => { }));
            Assert.Throws<ArgumentNullException>(() => e.Array(n => { }, null));
        }
Beispiel #18
0
        public void SignatureTypeEncoder_GenericInstantiation()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            var m = e.GenericInstantiation(MetadataTokens.TypeDefinitionHandle(1), 1, true);
            Assert.Same(b, m.Builder);
            AssertEx.Equal(new byte[] { 0x15, 0x11, 0x04, 0x01 }, b.ToArray());
            b.Clear();

            e.GenericInstantiation(MetadataTokens.TypeReferenceHandle(1), 1, true);
            AssertEx.Equal(new byte[] { 0x15, 0x11, 0x05, 0x01 }, b.ToArray());
            b.Clear();

            e.GenericInstantiation(MetadataTokens.TypeDefinitionHandle(1), 1000, false);
            AssertEx.Equal(new byte[] { 0x15, 0x12, 0x04, 0x83, 0xE8 }, b.ToArray());
            b.Clear();

            e.GenericInstantiation(MetadataTokens.TypeDefinitionHandle(1), ushort.MaxValue, false);
            AssertEx.Equal(new byte[] { 0x15, 0x12, 0x04, 0xC0, 0x00, 0xFF, 0xFF }, b.ToArray());
            b.Clear();

            Assert.Throws<ArgumentException>(() => e.GenericInstantiation(MetadataTokens.TypeSpecificationHandle(1), 1, isValueType: false));
            Assert.Throws<ArgumentException>(() => e.GenericInstantiation(default(EntityHandle), 1, isValueType: false));
            Assert.Throws<ArgumentOutOfRangeException>(() => e.GenericInstantiation(default(TypeDefinitionHandle), 0, true));
            Assert.Throws<ArgumentOutOfRangeException>(() => e.GenericInstantiation(default(TypeDefinitionHandle), -1, true));
            Assert.Throws<ArgumentOutOfRangeException>(() => e.GenericInstantiation(default(TypeDefinitionHandle), ushort.MaxValue + 1, true));
            Assert.Equal(0, b.Count);
        }
Beispiel #19
0
        public void SignatureTypeEncoder_PrimitiveType()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            e.PrimitiveType(PrimitiveTypeCode.Boolean);
            AssertEx.Equal(new byte[] { 0x02 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Char);
            AssertEx.Equal(new byte[] { 0x03 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.SByte);
            AssertEx.Equal(new byte[] { 0x04 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Byte);
            AssertEx.Equal(new byte[] { 0x05 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Int16);
            AssertEx.Equal(new byte[] { 0x06 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.UInt16);
            AssertEx.Equal(new byte[] { 0x07 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Int32);
            AssertEx.Equal(new byte[] { 0x08 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.UInt32);
            AssertEx.Equal(new byte[] { 0x09 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Int64);
            AssertEx.Equal(new byte[] { 0x0A }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.UInt64);
            AssertEx.Equal(new byte[] { 0x0B }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Single);
            AssertEx.Equal(new byte[] { 0x0C }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Double);
            AssertEx.Equal(new byte[] { 0x0D }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.String);
            AssertEx.Equal(new byte[] { 0x0E }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.IntPtr);
            AssertEx.Equal(new byte[] { 0x18 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.UIntPtr);
            AssertEx.Equal(new byte[] { 0x19 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Object);
            AssertEx.Equal(new byte[] { 0x1C }, b.ToArray());
            b.Clear();

            Assert.Throws<ArgumentOutOfRangeException>(() => e.PrimitiveType(PrimitiveTypeCode.Void));
            Assert.Throws<ArgumentOutOfRangeException>(() => e.PrimitiveType(PrimitiveTypeCode.TypedReference));
            Assert.Throws<ArgumentOutOfRangeException>(() => e.PrimitiveType((PrimitiveTypeCode)255));
        }
Beispiel #20
0
 public void Array(out SignatureTypeEncoder elementType, out ArrayShapeEncoder arrayShape)
 {
     Builder.WriteByte((byte)SignatureTypeCode.Array);
     elementType = this;
     arrayShape  = new ArrayShapeEncoder(Builder);
 }
Beispiel #21
0
        public void SignatureTypeEncoder_CustomModifiers()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            var a = e.CustomModifiers();
            AssertEx.Equal(new byte[0], b.ToArray());
            Assert.Same(b, a.Builder);
        }
Beispiel #22
0
        public void SignatureTypeEncoder_Primitives()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            e.Boolean();
            AssertEx.Equal(new byte[] { 0x02 }, b.ToArray());
            b.Clear();

            e.Char();
            AssertEx.Equal(new byte[] { 0x03 }, b.ToArray());
            b.Clear();

            e.SByte();
            AssertEx.Equal(new byte[] { 0x04 }, b.ToArray());
            b.Clear();

            e.Byte();
            AssertEx.Equal(new byte[] { 0x05 }, b.ToArray());
            b.Clear();

            e.Int16();
            AssertEx.Equal(new byte[] { 0x06 }, b.ToArray());
            b.Clear();

            e.UInt16();
            AssertEx.Equal(new byte[] { 0x07 }, b.ToArray());
            b.Clear();

            e.Int32();
            AssertEx.Equal(new byte[] { 0x08 }, b.ToArray());
            b.Clear();

            e.UInt32();
            AssertEx.Equal(new byte[] { 0x09 }, b.ToArray());
            b.Clear();

            e.Int64();
            AssertEx.Equal(new byte[] { 0x0A }, b.ToArray());
            b.Clear();

            e.UInt64();
            AssertEx.Equal(new byte[] { 0x0B }, b.ToArray());
            b.Clear();

            e.Single();
            AssertEx.Equal(new byte[] { 0x0C }, b.ToArray());
            b.Clear();

            e.Double();
            AssertEx.Equal(new byte[] { 0x0D }, b.ToArray());
            b.Clear();

            e.String();
            AssertEx.Equal(new byte[] { 0x0E }, b.ToArray());
            b.Clear();

            e.IntPtr();
            AssertEx.Equal(new byte[] { 0x18 }, b.ToArray());
            b.Clear();

            e.UIntPtr();
            AssertEx.Equal(new byte[] { 0x19 }, b.ToArray());
            b.Clear();

            e.Object();
            AssertEx.Equal(new byte[] { 0x1C }, b.ToArray());
            b.Clear();
        }
Beispiel #23
0
        public void SignatureTypeEncoder_Type()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            e.Type(MetadataTokens.TypeDefinitionHandle(1), isValueType: true);
            AssertEx.Equal(new byte[] { 0x11, 0x04 }, b.ToArray());
            b.Clear();

            e.Type(MetadataTokens.TypeDefinitionHandle(1), isValueType: false);
            AssertEx.Equal(new byte[] { 0x12, 0x04 }, b.ToArray());
            b.Clear();

            e.Type(MetadataTokens.TypeReferenceHandle(1), isValueType: false);
            AssertEx.Equal(new byte[] { 0x12, 0x05 }, b.ToArray());
            b.Clear();

            Assert.Throws<ArgumentException>(() => e.Type(MetadataTokens.TypeSpecificationHandle(1), isValueType: false));
            Assert.Throws<ArgumentException>(() => e.Type(default(EntityHandle), isValueType: false));
            Assert.Equal(0, b.Count);
        }
Beispiel #24
0
        public void SignatureTypeEncoder_VoidPointer()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            e.VoidPointer();
            AssertEx.Equal(new byte[] { 0x0F, 0x01 }, b.ToArray());
        }
Beispiel #25
0
        public void SignatureTypeEncoder_GenericTypeParameter()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            e.GenericTypeParameter(0);
            AssertEx.Equal(new byte[] { 0x13, 0x00 }, b.ToArray());
            b.Clear();

            e.GenericTypeParameter(ushort.MaxValue);
            AssertEx.Equal(new byte[] { 0x13, 0xC0, 0x00, 0xFF, 0xFF }, b.ToArray());
            b.Clear();

            Assert.Throws<ArgumentOutOfRangeException>(() => e.GenericTypeParameter(-1));
            Assert.Throws<ArgumentOutOfRangeException>(() => e.GenericTypeParameter(ushort.MaxValue + 1));
            Assert.Equal(0, b.Count);
        }
Beispiel #26
0
        private void EncodeTypeSignature(SignatureTypeEncoder encoder, TypeDesc type)
        {
            if (type is RuntimeDeterminedType)
            {
                EncodeTypeSignature(encoder, ((RuntimeDeterminedType)type).RuntimeDeterminedDetailsType);
                return;
            }

            switch (type.Category)
            {
            case TypeFlags.Boolean:
                encoder.Boolean(); break;

            case TypeFlags.Byte:
                encoder.Byte(); break;

            case TypeFlags.SByte:
                encoder.SByte(); break;

            case TypeFlags.Char:
                encoder.Char(); break;

            case TypeFlags.Int16:
                encoder.Int16(); break;

            case TypeFlags.UInt16:
                encoder.UInt16(); break;

            case TypeFlags.Int32:
                encoder.Int32(); break;

            case TypeFlags.UInt32:
                encoder.UInt32(); break;

            case TypeFlags.Int64:
                encoder.Int64(); break;

            case TypeFlags.UInt64:
                encoder.UInt64(); break;

            case TypeFlags.Single:
                encoder.Single(); break;

            case TypeFlags.Double:
                encoder.Double(); break;

            case TypeFlags.IntPtr:
                encoder.IntPtr(); break;

            case TypeFlags.UIntPtr:
                encoder.UIntPtr(); break;

            case TypeFlags.Void:
                encoder.Builder.WriteByte((byte)PrimitiveTypeCode.Void);
                break;

            case TypeFlags.SignatureTypeVariable:
                encoder.GenericTypeParameter(((SignatureVariable)type).Index);
                break;

            case TypeFlags.SignatureMethodVariable:
                encoder.GenericMethodTypeParameter(((SignatureMethodVariable)type).Index);
                break;

            case TypeFlags.GenericParameter:
            {
                var genericTypeDesc = (GenericParameterDesc)type;
                if (genericTypeDesc.Kind == GenericParameterKind.Type)
                {
                    encoder.GenericTypeParameter(genericTypeDesc.Index);
                }
                else
                {
                    encoder.GenericMethodTypeParameter(genericTypeDesc.Index);
                }
            }
            break;

            case TypeFlags.FunctionPointer:
            {
                FunctionPointerType fptrType = (FunctionPointerType)type;
                encoder.FunctionPointer(
                    SignatureCallingConvention.Default,
                    fptrType.Signature.IsStatic ? default(FunctionPointerAttributes) : FunctionPointerAttributes.HasThis,
                    fptrType.Signature.GenericParameterCount);

                // Return Type Sig
                EncodeTypeSignature(encoder, fptrType.Signature.ReturnType);

                // Parameter Types Sig
                for (int i = 0; i < fptrType.Signature.Length; i++)
                {
                    EncodeTypeSignature(encoder, fptrType.Signature[i]);
                }
            }
            break;

            case TypeFlags.Array:
            {
                // Skip bounds and lobounds (TODO)
                ImmutableArray <int> bounds      = ImmutableArray.Create <int>();
                ImmutableArray <int> lowerBounds = ImmutableArray.Create <int>();
                encoder.Array(
                    elementType => EncodeTypeSignature(elementType, ((ArrayType)type).ElementType),
                    arrayShape => arrayShape.Shape(((ArrayType)type).Rank, bounds, lowerBounds));
            }
            break;

            case TypeFlags.SzArray:
                encoder.SZArray();
                EncodeTypeSignature(encoder, ((ParameterizedType)type).ParameterType);
                break;

            case TypeFlags.ByRef:
                encoder.Builder.WriteByte((byte)SignatureTypeCode.ByReference);
                EncodeTypeSignature(encoder, ((ParameterizedType)type).ParameterType);
                break;

            case TypeFlags.Pointer:
                encoder.Builder.WriteByte((byte)SignatureTypeCode.Pointer);
                EncodeTypeSignature(encoder, ((ParameterizedType)type).ParameterType);
                break;

            case TypeFlags.Enum:
            case TypeFlags.Class:
            case TypeFlags.ValueType:
            case TypeFlags.Interface:
            case TypeFlags.Nullable:
            {
                if (type == _typeSystemContext.GetWellKnownType(WellKnownType.TypedReference))
                {
                    encoder.Builder.WriteByte((byte)PrimitiveTypeCode.TypedReference);
                }
                else if (type == _typeSystemContext.GetWellKnownType(WellKnownType.Object))
                {
                    encoder.PrimitiveType(PrimitiveTypeCode.Object);
                }
                else if (type == _typeSystemContext.GetWellKnownType(WellKnownType.String))
                {
                    encoder.PrimitiveType(PrimitiveTypeCode.String);
                }
                else if (type.HasInstantiation && !type.IsGenericDefinition)
                {
                    encoder.GenericInstantiation(MakeTypeRefOrSpecHandle(type.GetTypeDefinition()), type.Instantiation.Length, type.IsValueType);

                    for (int i = 0; i < type.Instantiation.Length; i++)
                    {
                        EncodeTypeSignature(encoder, type.Instantiation[i]);
                    }
                }
                else
                {
                    encoder.Type(MakeTypeRefHandle(type), type.IsValueType);
                }
            }
            break;

            default:
                throw new InvalidOperationException("Attempting to encode an invalid type signature.");
            }
        }
Beispiel #27
0
        internal static void FromSystemType(this SignatureTypeEncoder typeEncoder, Type type,
                                            IAssemblyMetadata metadata)
        {
            if (type.IsByRef)
            {
                throw new ArgumentException("ByRef types should be handled by parameter encoder or return type encoder");
            }
            else if (type.IsPointer)
            {
                typeEncoder.Pointer().FromSystemType(type.GetElementType(), metadata);
            }
            else if (type.IsPrimitive)
            {
                typeEncoder.PrimitiveType(GetPrimitiveTypeCode(type));
            }
            else if (type == typeof(string))
            {
                typeEncoder.String();
            }
            else if (type == typeof(object))
            {
                typeEncoder.Object();
            }
            else if (type == typeof(void))
            {
                throw new ArgumentException(
                          "Void type is not allowed in SignatureTypeEncoder. Please, use FromSystemType from ReturnTypeEncoder.",
                          nameof(type));
            }
            else if (type.IsArray)
            {
                var elementType = type.GetElementType();

                if (type.GetArrayRank() == 1)
                {
                    typeEncoder.SZArray().FromSystemType(elementType, metadata);
                }
                else
                {
                    typeEncoder.Array(
                        x => x.FromSystemType(elementType, metadata),
                        x => x.Shape(
                            type.GetArrayRank(),
                            ImmutableArray.Create <int>(),
                            ImmutableArray.CreateRange <int>(Enumerable.Repeat(0, type.GetArrayRank())) // better matches metadata from C#
                            ));
                }
            }
            else if (type.IsGenericType)
            {
                var genericTypeDef   = type.GetGenericTypeDefinition();
                var typeHandler      = metadata.GetTypeHandle(genericTypeDef);
                var genericArguments = type.GetGenericArguments();

                var inst = typeEncoder.GenericInstantiation(typeHandler, genericArguments.Length, type.IsValueType);
                foreach (var ga in genericArguments)
                {
                    if (ga.IsGenericParameter)
                    {
                        inst.AddArgument().GenericTypeParameter(ga.GenericParameterPosition);
                    }
                    else
                    {
                        inst.AddArgument().FromSystemType(ga, metadata);
                    }
                }
            }
            else if (type.IsGenericMethodParameter())
            {
                typeEncoder.GenericMethodTypeParameter(type.GenericParameterPosition);
            }
            else if (type.IsGenericParameter)
            {
                typeEncoder.GenericTypeParameter(type.GenericParameterPosition);
            }
            else
            {
                var typeHandler = metadata.GetTypeHandle(type);
                typeEncoder.Type(typeHandler, type.IsValueType);
            }
        }
Beispiel #28
0
        public static void EncodeSpecialType(this SignatureTypeEncoder typeEncoder, SpecialType specialType)
        {
            switch (specialType)
            {
            case SpecialType.System_Boolean:
                typeEncoder.Boolean();
                break;

            case SpecialType.System_SByte:
                typeEncoder.SByte();
                break;

            case SpecialType.System_Byte:
                typeEncoder.Byte();
                break;

            case SpecialType.System_Int16:
                typeEncoder.Int16();
                break;

            case SpecialType.System_Int32:
                typeEncoder.Int32();
                break;

            case SpecialType.System_Int64:
                typeEncoder.Int64();
                break;

            case SpecialType.System_UInt16:
                typeEncoder.UInt16();
                break;

            case SpecialType.System_UInt32:
                typeEncoder.UInt32();
                break;

            case SpecialType.System_UInt64:
                typeEncoder.UInt64();
                break;

            case SpecialType.System_Single:
                typeEncoder.Single();
                break;

            case SpecialType.System_Double:
                typeEncoder.Double();
                break;

            case SpecialType.System_Char:
                typeEncoder.Char();
                break;

            case SpecialType.System_String:
                typeEncoder.String();
                break;

            case SpecialType.System_Object:
                typeEncoder.Object();
                break;

            case SpecialType.System_IntPtr:
                typeEncoder.IntPtr();
                break;

            case SpecialType.System_UIntPtr:
                typeEncoder.UIntPtr();
                break;

            default:
                throw new NotImplementedException();
            }

            // TODO: handle C# interface mappings for special types
        }
Beispiel #29
0
 public void Array(out SignatureTypeEncoder elementType, out ArrayShapeEncoder arrayShape)
 {
     Builder.WriteByte((byte)SignatureTypeCode.Array);
     elementType = this;
     arrayShape = new ArrayShapeEncoder(Builder);
 }
Beispiel #30
0
        /// <summary>
        /// Encode a type signature into a specified blob.
        /// </summary>
        /// <param name="blobBuilder">Blob to encode type signature into. Must not be null</param>
        public void EncodeSignatureForType(TypeDesc type, BlobBuilder blobBuilder)
        {
            SignatureTypeEncoder sigEncoder = new SignatureTypeEncoder(blobBuilder);

            _signatureEmitter.EncodeTypeSignature(sigEncoder, type);
        }
        public void SignatureTypeEncoder_PrimitiveType()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);

            Assert.Same(b, e.Builder);

            e.PrimitiveType(PrimitiveTypeCode.Boolean);
            AssertEx.Equal(new byte[] { 0x02 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Char);
            AssertEx.Equal(new byte[] { 0x03 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.SByte);
            AssertEx.Equal(new byte[] { 0x04 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Byte);
            AssertEx.Equal(new byte[] { 0x05 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Int16);
            AssertEx.Equal(new byte[] { 0x06 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.UInt16);
            AssertEx.Equal(new byte[] { 0x07 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Int32);
            AssertEx.Equal(new byte[] { 0x08 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.UInt32);
            AssertEx.Equal(new byte[] { 0x09 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Int64);
            AssertEx.Equal(new byte[] { 0x0A }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.UInt64);
            AssertEx.Equal(new byte[] { 0x0B }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Single);
            AssertEx.Equal(new byte[] { 0x0C }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Double);
            AssertEx.Equal(new byte[] { 0x0D }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.String);
            AssertEx.Equal(new byte[] { 0x0E }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.IntPtr);
            AssertEx.Equal(new byte[] { 0x18 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.UIntPtr);
            AssertEx.Equal(new byte[] { 0x19 }, b.ToArray());
            b.Clear();

            e.PrimitiveType(PrimitiveTypeCode.Object);
            AssertEx.Equal(new byte[] { 0x1C }, b.ToArray());
            b.Clear();

            Assert.Throws <ArgumentOutOfRangeException>(() => e.PrimitiveType(PrimitiveTypeCode.Void));
            Assert.Throws <ArgumentOutOfRangeException>(() => e.PrimitiveType(PrimitiveTypeCode.TypedReference));
            Assert.Throws <ArgumentOutOfRangeException>(() => e.PrimitiveType((PrimitiveTypeCode)255));
        }
Beispiel #32
0
        public void SignatureTypeEncoder_SZArray()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            var a = e.SZArray();
            AssertEx.Equal(new byte[] { 0x1D }, b.ToArray());
            Assert.Same(b, a.Builder);
        }
Beispiel #33
0
        public void SignatureTypeEncoder_FunctionPointer()
        {
            var b = new BlobBuilder();
            var e = new SignatureTypeEncoder(b);
            Assert.Same(b, e.Builder);

            var m = e.FunctionPointer(
                SignatureCallingConvention.CDecl,
                FunctionPointerAttributes.HasThis,
                genericParameterCount: 1);

            Assert.Same(b, m.Builder);

            AssertEx.Equal(new byte[] { 0x1B, 0x21, 0x01 }, b.ToArray());
            b.Clear();

            e.FunctionPointer(
                SignatureCallingConvention.Default,
                FunctionPointerAttributes.HasExplicitThis,
                genericParameterCount: 0);

            AssertEx.Equal(new byte[] { 0x1B, 0x60 }, b.ToArray());
            b.Clear();

            e.FunctionPointer();

            AssertEx.Equal(new byte[] { 0x1B, 0x00 }, b.ToArray());
            b.Clear();

            Assert.Throws<ArgumentException>(() => e.FunctionPointer(0, (FunctionPointerAttributes)1000, genericParameterCount: 0));
            Assert.Throws<ArgumentOutOfRangeException>(() => e.FunctionPointer(0, 0, genericParameterCount: -1));
            Assert.Throws<ArgumentOutOfRangeException>(() => e.FunctionPointer(0, 0, genericParameterCount: ushort.MaxValue + 1));
            Assert.Equal(0, b.Count);
        }