Example #1
0
        private static IEnumerable <TypeSig> BaseTypes(TypeDef typeDef)
        {
            if (typeDef == null)
            {
                yield break;
            }
            if (typeDef.BaseType == null)
            {
                yield break;
            }

            TypeSig baseType = typeDef.ToTypeSig();

            do
            {
                var genericArgs = baseType is GenericInstSig ? ((GenericInstSig)baseType).GenericArguments : null;
                baseType = GenericArgumentResolver.Resolve(typeDef.BaseType.ToTypeSig(), genericArgs, null);
                yield return(baseType);

                typeDef = typeDef.BaseType.ResolveTypeDef();
                if (typeDef == null)
                {
                    break;
                }
            } while (typeDef.BaseType != null);
        }
Example #2
0
        static MethodSig ResolveGenericSignature(IMemberRef method, MethodSig overrideMethodSig)
        {
            if (method.DeclaringType is TypeSpec spec && spec.TypeSig is GenericInstSig genericInstSig)
            {
                overrideMethodSig = GenericArgumentResolver.Resolve(overrideMethodSig, genericInstSig.GenericArguments);
            }

            return(overrideMethodSig);
        }
Example #3
0
        public static VTableSignature FromMethod(IMethod method)
        {
            var sig      = method.MethodSig;
            var declType = method.DeclaringType.ToTypeSig();

            if (declType is GenericInstSig instSig)
            {
                sig = GenericArgumentResolver.Resolve(sig, instSig.GenericArguments);
            }
            return(new VTableSignature(sig, method.Name));
        }
Example #4
0
 static VTable ResolveGenericArgument(TypeDef openType, GenericInstSig genInst, VTable vTable)
 {
     Debug.Assert(new SigComparer().Equals(openType, vTable.Type));
     return(new VTable(genInst,
                       vTable.Slots.Select(slot => ResolveSlot(openType, (VTableSlot)slot, genInst.GenericArguments))
                       .ToList(),
                       vTable.InterfaceSlots.ToDictionary(
                           iface => GenericArgumentResolver.Resolve(iface.Key, genInst.GenericArguments),
                           iface => (IReadOnlyList <IVTableSlot>)iface.Value
                           .Select(slot => ResolveSlot(openType, (VTableSlot)slot, genInst.GenericArguments)).ToList())
                       ));
 }
Example #5
0
 internal static object ResolveGenericParams(List <TypeSig> typeParams, List <TypeSig> methodParams, object operand)
 {
     if (operand is MemberRef)
     {
         MemberRef memberRef = (MemberRef)operand;
         if (memberRef.IsFieldRef)
         {
             return new MemberRefUser(
                 memberRef.Module, memberRef.Name,
                 new FieldSig((TypeSig)ResolveGenericParams(typeParams, methodParams, memberRef.FieldSig.Type)),
                 (IMemberRefParent)ResolveGenericParams(typeParams, methodParams, memberRef.DeclaringType))
                    {
                        Rid = memberRef.Rid
                    }
         }
         ;
         else
         {
             return new MemberRefUser(
                 memberRef.Module, memberRef.Name,
                 GenericArgumentResolver.Resolve(memberRef.MethodSig, typeParams, methodParams),
                 (IMemberRefParent)ResolveGenericParams(typeParams, methodParams, memberRef.DeclaringType))
                    {
                        Rid = memberRef.Rid
                    }
         };
     }
     else if (operand is MethodSpec)
     {
         MethodSpec spec = (MethodSpec)operand;
         return(new MethodSpecUser(
                    (IMethodDefOrRef)ResolveGenericParams(typeParams, methodParams, spec.Method),
                    new GenericInstMethodSig(spec.GenericInstMethodSig.GenericArguments.Select(arg => (TypeSig)ResolveGenericParams(typeParams, methodParams, arg)).ToList())
                    )
         {
             Rid = spec.Rid
         });
     }
     else if (operand is TypeSpec)
     {
         TypeSpec spec = (TypeSpec)operand;
         return(new TypeSpecUser((TypeSig)ResolveGenericParams(typeParams, methodParams, spec.TypeSig))
         {
             Rid = spec.Rid
         });
     }
     else if (operand is TypeSig)
     {
         return(GenericArgumentResolver.Resolve((TypeSig)operand, typeParams, methodParams));
     }
     return(operand);
 }
        public static bool MatchInterfaceMethod(MethodDef candidate, MethodDef method, ITypeDefOrRef interfaceContextType)
        {
            var genericInstSig = interfaceContextType.TryGetGenericInstSig();

            if (genericInstSig != null)
            {
                return(MatchMethod(candidate, GenericArgumentResolver.Resolve(candidate.MethodSig, genericInstSig.GenericArguments, null), method));
            }
            else
            {
                return(MatchMethod(candidate, candidate.MethodSig, method));
            }
        }
Example #7
0
        static IVTableSlot ResolveSlot(TypeDef openType, VTableSlot slot, IList <TypeSig> genArgs)
        {
            var newSig  = GenericArgumentResolver.Resolve(slot.Signature.MethodSig, genArgs);
            var newDecl = slot.MethodDefDeclType;

            if (new SigComparer().Equals(newDecl, openType))
            {
                newDecl = new GenericInstSig((ClassOrValueTypeSig)openType.ToTypeSig(), genArgs.ToArray());
            }
            else
            {
                newDecl = GenericArgumentResolver.Resolve(newDecl, genArgs);
            }
            return(new VTableSlot(newDecl, slot.MethodDef, slot.DeclaringType,
                                  new VTableSignature(newSig, slot.Signature.Name), (VTableSlot)slot.Parent));
        }
Example #8
0
        static MethodSig GetMethodSig(ITypeDefOrRef type, MethodSig msig, IList <TypeSig> methodGenArgs)
        {
            IList <TypeSig> typeGenArgs = null;
            var             ts          = type as TypeSpec;

            if (ts != null)
            {
                var genSig = ts.TypeSig.ToGenericInstSig();
                if (genSig != null)
                {
                    typeGenArgs = genSig.GenericArguments;
                }
            }
            if (typeGenArgs == null && methodGenArgs == null)
            {
                return(msig);
            }
            return(GenericArgumentResolver.Resolve(msig, typeGenArgs, methodGenArgs));
        }
        private static IEnumerable <TypeSig> BaseTypes(TypeSig type)
        {
            TypeDef typeDef = type.GetTypeDefOrRef().ResolveTypeDefThrow();

            if (typeDef.BaseType == null)
            {
                yield break;
            }

            TypeSig baseType = type;

            do
            {
                var genericArgs = baseType.IsGenericInstanceType ? ((GenericInstSig)baseType).GenericArguments : null;
                baseType = GenericArgumentResolver.Resolve(typeDef.BaseType.ToTypeSig(), genericArgs, null);
                yield return(baseType);

                typeDef = typeDef.BaseType.ResolveTypeDefThrow();
            } while (typeDef.BaseType != null);
        }
Example #10
0
        private static bool IsMatchingOverride(MethodOverride methodOverride, IMethodDefOrRef targetMethod)
        {
            SigComparer comparer = default;

            var targetDeclTypeDef   = targetMethod.DeclaringType.ResolveTypeDef();
            var overrideDeclTypeDef = methodOverride.MethodDeclaration.DeclaringType.ResolveTypeDef();

            if (!comparer.Equals(targetDeclTypeDef, overrideDeclTypeDef))
            {
                return(false);
            }

            var targetMethodSig   = targetMethod.MethodSig;
            var overrideMethodSig = methodOverride.MethodDeclaration.MethodSig;

            if (methodOverride.MethodDeclaration.DeclaringType is TypeSpec spec && spec.TypeSig is GenericInstSig genericInstSig)
            {
                overrideMethodSig = GenericArgumentResolver.Resolve(overrideMethodSig, genericInstSig.GenericArguments);
            }

            return(comparer.Equals(targetMethodSig, overrideMethodSig));
        }
        private void ResolveProperty(MosaProperty property)
        {
            GenericArgumentResolver resolver = new GenericArgumentResolver();

            if (property.DeclaringType.GenericArguments.Count > 0)
                resolver.PushTypeGenericArguments(property.DeclaringType.GenericArguments.GetGenericArguments());

            using (var mosaProperty = metadata.Controller.MutateProperty(property))
            {
                mosaProperty.PropertyType = metadata.Loader.GetType(resolver.Resolve(property.GetPropertySig().RetType));

                ResolveCustomAttributes(mosaProperty, property.GetUnderlyingObject<UnitDesc<PropertyDef, PropertySig>>().Definition);
            }
        }
        private void ResolveMethod(MosaMethod method)
        {
            GenericArgumentResolver resolver = new GenericArgumentResolver();
            bool hasOpening = method.DeclaringType.HasOpenGenericParams;

            if (method.DeclaringType.GenericArguments.Count > 0)
            {
                foreach (var i in method.DeclaringType.GenericArguments.GetGenericArguments())
                    hasOpening |= i.HasOpenGenericParameter();
                resolver.PushTypeGenericArguments(method.DeclaringType.GenericArguments.GetGenericArguments());
            }

            if (method.GenericArguments.Count > 0)
            {
                foreach (var i in method.GenericArguments.GetGenericArguments())
                    hasOpening |= i.HasOpenGenericParameter();
                resolver.PushMethodGenericArguments(method.GenericArguments.GetGenericArguments());
            }

            using (var mosaMethod = metadata.Controller.MutateMethod(method))
            {
                var desc = method.GetUnderlyingObject<UnitDesc<MethodDef, MethodSig>>();

                MosaType returnType = metadata.Loader.GetType(resolver.Resolve(desc.Signature.RetType));
                hasOpening |= returnType.HasOpenGenericParams;
                List<MosaParameter> pars = new List<MosaParameter>();

                Debug.Assert(desc.Signature.GetParamCount() + (desc.Signature.HasThis ? 1 : 0) == desc.Definition.Parameters.Count);
                foreach (var param in desc.Definition.Parameters)
                {
                    if (!param.IsNormalMethodParameter)
                        continue;
                    var paramType = metadata.Loader.GetType(resolver.Resolve(desc.Signature.Params[param.MethodSigIndex]));
                    var parameter = metadata.Controller.CreateParameter();

                    using (var mosaParameter = metadata.Controller.MutateParameter(parameter))
                    {
                        mosaParameter.Name = param.Name;
                        mosaParameter.ParameterAttributes = (MosaParameterAttributes)param.ParamDef.Attributes;
                        mosaParameter.ParameterType = paramType;
                        mosaParameter.DeclaringMethod = method;
                        ResolveCustomAttributes(mosaParameter, param.ParamDef);
                    }

                    pars.Add(parameter);
                    hasOpening |= paramType.HasOpenGenericParams;
                }

                mosaMethod.Signature = new MosaMethodSignature(returnType, pars);

                foreach (var methodImpl in desc.Definition.Overrides)
                {
                    Debug.Assert(methodImpl.MethodBody == desc.Definition);
                    mosaMethod.Overrides.Add(ResolveMethodOperand(methodImpl.MethodDeclaration, null));
                }

                if (desc.Definition.HasBody)
                    ResolveBody(desc.Definition, mosaMethod, desc.Definition.Body, resolver);

                mosaMethod.HasOpenGenericParams = hasOpening;

                ResolveCustomAttributes(mosaMethod, desc.Definition);
            }
        }
        private MosaMethod ResolveMethodOperand(IMethod operand, GenericArgumentResolver resolver)
        {
            if (operand is MethodSpec)
                return metadata.Loader.LoadGenericMethodInstance((MethodSpec)operand, resolver);
            else if (operand.DeclaringType.TryGetArraySig() != null || operand.DeclaringType.TryGetSZArraySig() != null)
                return ResolveArrayMethod(operand, resolver);

            TypeSig declType;
            MethodDef methodDef = operand as MethodDef;
            if (methodDef == null)
            {
                MemberRef memberRef = (MemberRef)operand;
                methodDef = memberRef.ResolveMethodThrow();
                declType = memberRef.DeclaringType.ToTypeSig();
            }
            else
                declType = methodDef.DeclaringType.ToTypeSig();

            if (resolver != null)
                declType = resolver.Resolve(declType);

            MDToken methodToken = methodDef.MDToken;

            MosaType type = metadata.Loader.GetType(declType);
            foreach (var method in type.Methods)
            {
                var desc = method.GetUnderlyingObject<UnitDesc<MethodDef, MethodSig>>();
                if (desc.Token.Token == methodToken)
                {
                    return method;
                }
            }

            throw new AssemblyLoadException();
        }
        private MosaField ResolveFieldOperand(IField operand, GenericArgumentResolver resolver)
        {
            TypeSig declType;
            FieldDef fieldDef = operand as FieldDef;
            if (fieldDef == null)
            {
                MemberRef memberRef = (MemberRef)operand;
                fieldDef = memberRef.ResolveFieldThrow();
                declType = memberRef.DeclaringType.ToTypeSig();
            }
            else
                declType = fieldDef.DeclaringType.ToTypeSig();

            MDToken fieldToken = fieldDef.MDToken;

            MosaType type = metadata.Loader.GetType(resolver.Resolve(declType));
            foreach (var field in type.Fields)
            {
                var desc = field.GetUnderlyingObject<UnitDesc<FieldDef, FieldSig>>();
                if (desc.Token.Token == fieldToken)
                {
                    return field;
                }
            }
            throw new AssemblyLoadException();
        }
        private MosaInstruction ResolveInstruction(MethodDef methodDef, CilBody body, int index, GenericArgumentResolver resolver)
        {
            Instruction instruction = body.Instructions[index];
            int? prev = index == 0 ? null : (int?)body.Instructions[index - 1].Offset;
            int? next = index == body.Instructions.Count - 1 ? null : (int?)body.Instructions[index + 1].Offset;

            object operand = instruction.Operand;

            // Special case: newarr instructions need to have their operand changed now so that the type is a SZArray
            if (instruction.OpCode == OpCodes.Newarr)
            {
                var typeSig = resolver.Resolve(((ITypeDefOrRef)instruction.Operand).ToTypeSig());
                var szArraySig = new SZArraySig(typeSig);
                operand = metadata.Loader.GetType(szArraySig);
            }
            else if (instruction.Operand is ITypeDefOrRef)
            {
                operand = ResolveTypeOperand((ITypeDefOrRef)instruction.Operand, resolver);
            }
            else if (instruction.Operand is MemberRef)
            {
                MemberRef memberRef = (MemberRef)instruction.Operand;
                if (memberRef.IsFieldRef)
                    operand = ResolveFieldOperand(memberRef, resolver);
                else
                    operand = ResolveMethodOperand(memberRef, resolver);
            }
            else if (instruction.Operand is IField)
            {
                operand = ResolveFieldOperand((IField)instruction.Operand, resolver);
            }
            else if (instruction.Operand is IMethod)
            {
                operand = ResolveMethodOperand((IMethod)instruction.Operand, resolver);
            }
            else if (instruction.Operand is Local)
            {
                operand = ((Local)instruction.Operand).Index;
            }
            else if (instruction.Operand is Parameter)
            {
                operand = ((Parameter)instruction.Operand).Index;
            }
            else if (instruction.Operand is Instruction)
            {
                operand = (int)((Instruction)instruction.Operand).Offset;
            }
            else if (instruction.Operand is Instruction[])
            {
                Instruction[] targets = (Instruction[])instruction.Operand;
                int[] offsets = new int[targets.Length];
                for (int i = 0; i < offsets.Length; i++)
                    offsets[i] = (int)targets[i].Offset;
                operand = offsets;
            }
            else if (instruction.Operand is string)
            {
                operand = metadata.Cache.GetStringId((string)instruction.Operand);
            }

            ushort code = (ushort)instruction.OpCode.Code;
            if (code > 0xff)    // To match compiler's opcode values
                code = (ushort)(0x100 + (code & 0xff));

            return new MosaInstruction((int)instruction.Offset, code, operand, prev, next);
        }
        private void ResolveBody(MethodDef methodDef, MosaMethod.Mutator method, CilBody body, GenericArgumentResolver resolver)
        {
            method.LocalVariables.Clear();
            int index = 0;
            foreach (var variable in body.Variables)
            {
                method.LocalVariables.Add(new MosaLocal(
                    variable.Name ?? "V_" + index,
                    metadata.Loader.GetType(resolver.Resolve(variable.Type)),
                    variable.Type.IsPinned));
                index++;
            }

            method.ExceptionBlocks.Clear();
            foreach (var eh in body.ExceptionHandlers)
            {
                method.ExceptionBlocks.Add(new MosaExceptionHandler(
                    (ExceptionHandlerType)eh.HandlerType,
                    ResolveOffset(body, eh.TryStart),
                    ResolveOffset(body, eh.TryEnd),
                    ResolveOffset(body, eh.HandlerStart),
                    ResolveOffset(body, eh.HandlerEnd),
                    eh.CatchType == null ? null : metadata.Loader.GetType(resolver.Resolve(eh.CatchType.ToTypeSig())),
                    eh.FilterStart == null ? null : (int?)eh.FilterStart.Offset
                ));
            }

            method.MaxStack = methodDef.Body.MaxStack;

            method.Code.Clear();
            for (int i = 0; i < body.Instructions.Count; i++)
            {
                method.Code.Add(ResolveInstruction(methodDef, body, i, resolver));
            }
        }
        private void ResolveField(MosaField field)
        {
            GenericArgumentResolver resolver = new GenericArgumentResolver();

            if (field.DeclaringType.GenericArguments.Count > 0)
                resolver.PushTypeGenericArguments(field.DeclaringType.GenericArguments.GetGenericArguments());

            using (var mosaField = metadata.Controller.MutateField(field))
            {
                mosaField.FieldType = metadata.Loader.GetType(resolver.Resolve(field.GetFieldSig().Type));

                mosaField.HasOpenGenericParams =
                    field.DeclaringType.HasOpenGenericParams ||
                    field.FieldType.GetTypeSig().HasOpenGenericParameter();

                ResolveCustomAttributes(mosaField, field.GetUnderlyingObject<UnitDesc<FieldDef, FieldSig>>().Definition);
            }
        }
        private static MethodSig Resolve(MethodBaseSig method, TypeSig typeContext)
        {
            var genericArgs = typeContext.IsGenericInstanceType ? ((GenericInstSig)typeContext).GenericArguments : null;

            return(GenericArgumentResolver.Resolve(method, genericArgs, null));
        }
 private MosaMethod ResolveArrayMethod(IMethod method, GenericArgumentResolver resolver)
 {
     MosaType type = metadata.Loader.GetType(resolver.Resolve(method.DeclaringType.ToTypeSig()));
     if (method.Name == "Get")
         return type.FindMethodByName("Get");
     else if (method.Name == "Set")
         return type.FindMethodByName("Set");
     else if (method.Name == "AddressOf")
         return type.FindMethodByName("AddressOf");
     else if (method.Name == ".ctor")
         return type.FindMethodByName(".ctor");
     else
         throw new AssemblyLoadException();
 }
Example #20
0
        public async Task Start(int maxRequests = 0, CancellationToken cancellationToken = default)
        {
            try
            {
                Logger.Debug("Creating named pipe security for {0}", WellKnownSidType.WorldSid);
                var ps  = new PipeSecurity();
                var sid = new SecurityIdentifier(WellKnownSidType.WorldSid, null);
                Logger.Debug("Security SID is {0}", sid.Value);
                ps.SetAccessRule(new PipeAccessRule(sid, PipeAccessRights.ReadWrite, System.Security.AccessControl.AccessControlType.Allow));

                var cnt = 0;
                while (maxRequests <= 0 || cnt < maxRequests)
                {
                    if (maxRequests > 0)
                    {
                        cnt++;
                    }

                    Logger.Debug("Creating named pipe {0}", "msixhero");
                    // ReSharper disable once StringLiteralTypo
                    using (var stream = NamedPipeNative.CreateNamedPipe("msixhero", ps))
                    {
                        Logger.Debug("Created stream " + stream.GetHashCode());

                        try
                        {
                            Logger.Debug("Waiting for a client connection...");
                            await stream.WaitForConnectionAsync(cancellationToken).ConfigureAwait(false);

                            // using var stream = client.GetStream();
                            var binaryWriter = new BinaryStreamProcessor(stream);
                            var binaryReader = new BinaryStreamProcessor(stream);

                            Logger.Debug("Reading command from stream...");
                            var command = await binaryReader.Read <IProxyObject>(cancellationToken).ConfigureAwait(false);

                            var commandType = command.GetType();
                            if (!this.receivers.TryGetValue(commandType, out var receiver))
                            {
                                throw new NotSupportedException("No receiver for type " + commandType.Name + " registered.");
                            }

                            string result = null;

                            var progress = new Progress <ProgressData>();
                            EventHandler <ProgressData> progressChanged = async(sender, data) =>
                            {
                                try
                                {
                                    this.autoResetEvent.WaitOne();
                                    await binaryWriter.Write((int)ResponseType.Progress, cancellationToken).ConfigureAwait(false);

                                    await binaryReader.Write(data, cancellationToken).ConfigureAwait(false);
                                }
                                finally
                                {
                                    this.autoResetEvent.Set();
                                }
                            };

                            try
                            {
                                progress.ProgressChanged += progressChanged;
                                var returnedType = GenericArgumentResolver.GetResultType(commandType, typeof(IProxyObjectWithOutput <>));

                                if (returnedType == null)
                                {
                                    Console.WriteLine($"Requested: {commandType.Name} with no returned value...");
                                    await receiver.Invoke(command, cancellationToken, progress).ConfigureAwait(false);
                                }
                                else
                                {
                                    Console.WriteLine($"Requested: {commandType.Name} with return value of type {returnedType.Name}...");
                                    var executionResult = await receiver.Get((IProxyObjectWithOutput <object>) command, cancellationToken, progress).ConfigureAwait(false);

                                    result = JsonConvert.SerializeObject(executionResult, Formatting.None, SerializerSettings);
                                }

                                try
                                {
                                    Logger.Trace("Beginning atomic scope with AutoResetEvent");
                                    this.autoResetEvent.WaitOne();

                                    Logger.Debug("Returning results via named pipe...");
                                    await binaryWriter.Write((int)ResponseType.Result, cancellationToken).ConfigureAwait(false);

                                    if (returnedType != null)
                                    {
                                        Console.WriteLine("Sending the results...");
                                        Logger.Debug("Returning actual results via named pipe...");
                                        await binaryWriter.Write(result, cancellationToken).ConfigureAwait(false);
                                    }

                                    Logger.Debug("Flushing the stream...");
                                    await stream.FlushAsync(cancellationToken).ConfigureAwait(false);

                                    Logger.Debug("Waiting for the pipe to drain...");
                                    stream.WaitForPipeDrain();
                                }
                                finally
                                {
                                    Logger.Trace("Finishing atomic scope with AutoResetEvent");
                                    this.autoResetEvent.Set();
                                }
                            }
                            catch (OperationCanceledException e)
                            {
                                Logger.Info(e);
                            }
                            catch (Exception e)
                            {
                                try
                                {
                                    Logger.Trace("Beginning atomic scope with AutoResetEvent");
                                    this.autoResetEvent.WaitOne();

                                    Logger.Error(e, "Reporting exception");
                                    Logger.Trace("Notifying about the response type ({0})...", ResponseType.Exception);
                                    await binaryWriter.Write((int)ResponseType.Exception, cancellationToken).ConfigureAwait(false);

                                    Logger.Trace("Notifying about the message {0}...", e.Message);
                                    await binaryWriter.Write(e.Message, cancellationToken).ConfigureAwait(false);

                                    Logger.Trace("Notifying about the callstack (0)...", e);
                                    await binaryWriter.Write(e.ToString(), cancellationToken).ConfigureAwait(false);

                                    Logger.Trace("Flushing....");
                                    await stream.FlushAsync(cancellationToken).ConfigureAwait(false);

                                    Logger.Trace("Waiting for the pipe to drain....");
                                    stream.WaitForPipeDrain();
                                }
                                finally
                                {
                                    Logger.Trace("Finishing atomic scope with AutoResetEvent");
                                    this.autoResetEvent.Set();
                                }
                            }
                            finally
                            {
                                progress.ProgressChanged -= progressChanged;
                            }
                        }
                        catch (Exception e)
                        {
                            Logger.Error(e);
                        }
                        finally
                        {
                            if (stream.IsConnected)
                            {
                                Logger.Debug("Disconnecting the stream " + stream.GetHashCode());
                                stream.Disconnect();
                            }
                        }
                    }

                    Logger.Debug("Finishing the main loop, repeating now...");
                }
            }
            catch (Exception e)
            {
                Logger.Fatal(e);
            }
        }
        private static TypeSig Resolve(TypeSig type, TypeSig typeContext)
        {
            var genericArgs = typeContext.IsGenericInstanceType ? ((GenericInstSig)typeContext).GenericArguments : null;

            return(GenericArgumentResolver.Resolve(type, genericArgs, null));
        }
        private void ResolveProperty(MosaProperty property)
        {
            GenericArgumentResolver resolver = new GenericArgumentResolver();

            if (property.DeclaringType.GenericArguments.Count > 0)
                resolver.PushTypeGenericArguments(property.DeclaringType.GenericArguments.GetGenericArguments());

            using (var mosaProperty = metadata.Controller.MutateProperty(property))
            {
                mosaProperty.PropertyType = metadata.Loader.GetType(resolver.Resolve(property.GetPropertySig().RetType));

                var propertyDesc = property.GetUnderlyingObject<UnitDesc<PropertyDef, PropertySig>>();

                if (propertyDesc.Definition.GetMethod != null)
                {
                    var getterDesc = new UnitDesc<MethodDef, MethodSig>(propertyDesc.Definition.GetMethod.Module, propertyDesc.Definition.GetMethod, propertyDesc.Definition.GetMethod.MethodSig);
                    mosaProperty.GetterMethod = metadata.Cache.GetMethodByToken(getterDesc.Token);
                }

                if (propertyDesc.Definition.SetMethod != null)
                {
                    var setterDesc = new UnitDesc<MethodDef, MethodSig>(propertyDesc.Definition.SetMethod.Module, propertyDesc.Definition.SetMethod, propertyDesc.Definition.SetMethod.MethodSig);
                    mosaProperty.SetterMethod = metadata.Cache.GetMethodByToken(setterDesc.Token);
                }

                ResolveCustomAttributes(mosaProperty, property.GetUnderlyingObject<UnitDesc<PropertyDef, PropertySig>>().Definition);
            }
        }
        private void ResolveType(MosaType type)
        {
            GenericArgumentResolver resolver = new GenericArgumentResolver();

            MosaType srcType = type;
            if (type.GenericArguments.Count > 0)
            {
                resolver.PushTypeGenericArguments(type.GenericArguments.GetGenericArguments());
                srcType = type.ElementType;
                Debug.Assert(srcType != null);
            }

            using (var mosaType = metadata.Controller.MutateType(type))
            {
                if (srcType.BaseType != null)
                    mosaType.BaseType = metadata.Loader.GetType(resolver.Resolve(srcType.BaseType.GetTypeSig()));

                if (srcType.DeclaringType != null)
                {
                    mosaType.DeclaringType = metadata.Loader.GetType(resolver.Resolve(srcType.DeclaringType.GetTypeSig()));
                    mosaType.Namespace = srcType.DeclaringType.Namespace;
                }

                var ifaces = new List<MosaType>(srcType.Interfaces);
                mosaType.Interfaces.Clear();
                for (int i = 0; i < ifaces.Count; i++)
                    mosaType.Interfaces.Add(metadata.Loader.GetType(resolver.Resolve(ifaces[i].GetTypeSig())));

                mosaType.HasOpenGenericParams = type.GetTypeSig().HasOpenGenericParameter();

                ResolveCustomAttributes(mosaType, srcType.GetUnderlyingObject<UnitDesc<TypeDef, TypeSig>>().Definition);
            }

            // Add type again to make it easier to find
            metadata.Controller.AddType(type);
        }
Example #24
0
        private MosaInstruction ResolveInstruction(MethodDef methodDef, CilBody body, int index, GenericArgumentResolver resolver)
        {
            Instruction instruction = body.Instructions[index];
            int? prev = index == 0 ? null : (int?)body.Instructions[index - 1].Offset;
            int? next = index == body.Instructions.Count - 1 ? null : (int?)body.Instructions[index + 1].Offset;

            object operand = instruction.Operand;

            if (instruction.Operand is ITypeDefOrRef)
            {
                operand = ResolveTypeOperand((ITypeDefOrRef)instruction.Operand, resolver);
            }
            else if (instruction.Operand is MemberRef)
            {
                MemberRef memberRef = (MemberRef)instruction.Operand;
                if (memberRef.IsFieldRef)
                    operand = ResolveFieldOperand(memberRef, resolver);
                else
                    operand = ResolveMethodOperand(memberRef, resolver);
            }
            else if (instruction.Operand is IField)
            {
                operand = ResolveFieldOperand((IField)instruction.Operand, resolver);
            }
            else if (instruction.Operand is IMethod)
            {
                operand = ResolveMethodOperand((IMethod)instruction.Operand, resolver);
            }
            else if (instruction.Operand is Local)
            {
                operand = ((Local)instruction.Operand).Index;
            }
            else if (instruction.Operand is Parameter)
            {
                operand = ((Parameter)instruction.Operand).Index;
            }
            else if (instruction.Operand is Instruction)
            {
                operand = (int)((Instruction)instruction.Operand).Offset;
            }
            else if (instruction.Operand is Instruction[])
            {
                Instruction[] targets = (Instruction[])instruction.Operand;
                int[] offsets = new int[targets.Length];
                for (int i = 0; i < offsets.Length; i++)
                    offsets[i] = (int)targets[i].Offset;
                operand = offsets;
            }
            else if (instruction.Operand is string)
            {
                operand = metadata.Cache.GetStringId((string)instruction.Operand);
            }

            ushort code = (ushort)instruction.OpCode.Code;
            if (code > 0xff)    // To match compiler's opcode values
                code = (ushort)(0x100 + (code & 0xff));

            return new MosaInstruction((int)instruction.Offset, code, operand, prev, next);
        }
Example #25
0
        private void ResolveMethod(MosaMethod method)
        {
            GenericArgumentResolver resolver = new GenericArgumentResolver();
            bool hasOpening = method.DeclaringType.HasOpenGenericParams;

            if (method.DeclaringType.GenericArguments.Count > 0)
            {
                foreach (var i in method.DeclaringType.GenericArguments.GetGenericArguments())
                    hasOpening |= i.HasOpenGenericParameter();
                resolver.PushTypeGenericArguments(method.DeclaringType.GenericArguments.GetGenericArguments());
            }

            if (method.GenericArguments.Count > 0)
            {
                foreach (var i in method.GenericArguments.GetGenericArguments())
                    hasOpening |= i.HasOpenGenericParameter();
                resolver.PushMethodGenericArguments(method.GenericArguments.GetGenericArguments());
            }
            else
                hasOpening |= method.GetMethodSig().HasOpenGenericParameter();

            using (var mosaMethod = metadata.Controller.MutateMethod(method))
            {
                var desc = method.GetUnderlyingObject<UnitDesc<MethodDef, MethodSig>>();

                MosaType returnType = metadata.Loader.GetType(resolver.Resolve(desc.Signature.RetType));
                List<MosaParameter> pars = new List<MosaParameter>();

                Debug.Assert(desc.Signature.GetParamCount() == desc.Definition.ParamDefs.Count);
                for (int i = 0; i < desc.Definition.ParamDefs.Count; i++)
                {
                    pars.Add(new MosaParameter(desc.Definition.ParamDefs[i].FullName, metadata.Loader.GetType(resolver.Resolve(desc.Signature.Params[i]))));
                }

                mosaMethod.Signature = new MosaMethodSignature(returnType, pars);

                if (desc.Definition.HasBody)
                    ResolveBody(desc.Definition, mosaMethod, desc.Definition.Body, resolver);

                mosaMethod.HasOpenGenericParams = hasOpening;

                ResolveCustomAttributes(mosaMethod, desc.Definition);
            }
        }
Example #26
0
        private void ResolveType(MosaType type)
        {
            GenericArgumentResolver resolver = new GenericArgumentResolver();

            if (type.GenericArguments.Count > 0)
                resolver.PushTypeGenericArguments(type.GenericArguments.GetGenericArguments());

            using (var mosaType = metadata.Controller.MutateType(type))
            {
                if (type.BaseType != null)
                    mosaType.BaseType = metadata.Loader.GetType(resolver.Resolve(type.BaseType.GetTypeSig()));

                if (type.DeclaringType != null)
                    mosaType.DeclaringType = metadata.Loader.GetType(resolver.Resolve(type.DeclaringType.GetTypeSig()));

                for (int i = 0; i < type.Interfaces.Count; i++)
                    mosaType.Interfaces[i] = metadata.Loader.GetType(resolver.Resolve(type.Interfaces[i].GetTypeSig()));

                mosaType.HasOpenGenericParams = type.GetTypeSig().HasOpenGenericParameter();

                ResolveCustomAttributes(mosaType, type.GetUnderlyingObject<UnitDesc<TypeDef, TypeSig>>().Definition);
            }
        }
 private MosaType ResolveTypeOperand(ITypeDefOrRef operand, GenericArgumentResolver resolver)
 {
     return metadata.Loader.GetType(resolver.Resolve(operand.ToTypeSig()));
 }
Example #28
0
 static IEnumerable <Type> Resolve(string methodName, object[] parameters)
 {
     return(GenericArgumentResolver.ResolveTypeArguments(typeof(Generic).GetInstanceMethod(methodName), parameters));
 }