Ejemplo n.º 1
0
        /// <summary>
        /// Add the given method to its declaring class.
        /// </summary>
        protected override void SetAccessFlags(DexLib.MethodDefinition dmethod, MethodDefinition method)
        {
            dmethod.IsStatic = true;
            dmethod.IsPublic = true;


            if (method.IsAbstract || method.IsVirtual)
            {
                // generate a warning, since these methods will never be called
                // as virtual. Do not generate a warning if we know the compiler
                // will handle the call.

                if (method.DeclaringType.FullName == "System.Array")
                {
                    // all array methods should be redirected by the compiler.
                    return;
                }
                if (method.DeclaringType.FullName == "System.String" && method.Name.EndsWith("GetEnumerator"))
                {
                    // IEnumerable.GetEnumerator will actually never be called by the compiler
                    // in foreach loops. Nevertheless Roslyn requires its existence.
                    return;
                }
                var intfMethod = method.GetBaseInterfaceMethod();
                if (intfMethod != null && intfMethod.DeclaringType.FullName == "System.IFormattable")
                {
                    // this is handled by the compiler.
                    return;
                }

                DLog.Warning(DContext.CompilerCodeGenerator, "Abstract or virtual .NET method '{0}' in DexImport class '{1}'. Unless specially handled by the compiler, this will never be called virtually.", method.Name, method.DeclaringType.FullName);
            }
        }
Ejemplo n.º 2
0
        /// <summary>
        /// Add the given method to its declaring class.
        /// </summary>
        protected virtual void SetAccessFlags(DexLib.MethodDefinition dmethod, MethodDefinition method)
        {
            // subclass accesses have already been fixed on an actual use basis.
            if (method.IsPrivate)
            {
                dmethod.IsPrivate = true;
            }
            else if (method.IsFamily || method.IsFamilyOrAssembly)
            {
                dmethod.IsProtected = true;
            }
            else
            {
                dmethod.IsPublic = true;
            }

            if (method.DeclaringType.IsInterface)
            {
                dmethod.IsAbstract = true;
                //dmethod.
            }
            else
            {
                if (method.IsConstructor)
                {
                    dmethod.IsConstructor = true;
                    dmethod.IsStatic      = method.IsStatic;
                    if (method.IsStatic)
                    {
                        // reset access modifiers for static constructors.
                        dmethod.IsPrivate   = false;
                        dmethod.IsProtected = false;
                    }
                }
                else if (method.IsAbstract)
                {
                    dmethod.IsAbstract = true;
                }
                else if (method.IsVirtual)
                {
                    dmethod.IsVirtual = true;
                }
                else if (method.IsStatic)
                {
                    dmethod.IsStatic = true;
                }
                else
                {
                    dmethod.IsFinal = true;
                }
                //if (method.IsInitOnly) dmethod.IsFinal = true;
            }

            if (method.IsCompilerGenerated())
            {
                dmethod.IsSynthetic = true;
            }
        }
Ejemplo n.º 3
0
        /// <summary>
        /// Add the given method to its declaring class.
        /// </summary>
        protected virtual void SetAccessFlags(DexLib.MethodDefinition dmethod, MethodDefinition method)
        {
            if (method.IsPrivate)
            {
                if (method.DeclaringType.HasNestedTypes)
                {
                    dmethod.IsProtected = true;
                }
                else
                {
                    dmethod.IsPrivate = true;
                }
            }
            else if (method.IsFamily)
            {
                dmethod.IsProtected = true;
            }
            else
            {
                dmethod.IsPublic = true;
            }

            if (method.DeclaringType.IsInterface)
            {
                dmethod.IsAbstract = true;
                //dmethod.
            }
            else
            {
                if (method.IsConstructor)
                {
                    dmethod.IsConstructor = true;
                }
                else if (method.IsAbstract)
                {
                    dmethod.IsAbstract = true;
                }
                else if (method.IsVirtual)
                {
                    dmethod.IsVirtual = true;
                }
                else if (method.IsStatic)
                {
                    dmethod.IsStatic = true;
                }
                else
                {
                    dmethod.IsFinal = true;
                }
                //if (method.IsInitOnly) dmethod.IsFinal = true;
            }
        }
Ejemplo n.º 4
0
        /// <summary>
        /// Create the current type as class definition.
        /// </summary>
        public void Create(ClassDefinition declaringClass, DexTargetPackage targetPackage)
        {
            // Find xMethod
            xMethod = XBuilder.AsMethodDefinition(compiler.Module, method);

            // Create method definition
            dmethod           = new DexLib.MethodDefinition();
            dmethod.Name      = GetMethodName(method, targetPackage);
            dmethod.MapFileId = compiler.GetNextMapFileId();
            AddMethodToDeclaringClass(declaringClass, dmethod, targetPackage);
            targetPackage.Record(xMethod, dmethod);

            // Set access flags
            SetAccessFlags(dmethod, method);

            // Create prototype
            dmethod.Prototype = PrototypeBuilder.BuildPrototype(compiler, targetPackage, declaringClass, xMethod);
        }
Ejemplo n.º 5
0
        /// <summary>
        /// Create the current type as class definition.
        /// </summary>
        public void Create(ClassDefinition declaringClass, DexTargetPackage targetPackage)
        {
            // Find xMethod
            xMethod = XBuilder.AsMethodDefinition(compiler.Module, method);

            // Create method definition
            dmethod = new DexLib.MethodDefinition();
            dmethod.Name = GetMethodName(method, targetPackage);
            dmethod.MapFileId = compiler.GetNextMapFileId();
            AddMethodToDeclaringClass(declaringClass, dmethod, targetPackage);
            targetPackage.Record(xMethod, dmethod);

            // Set access flags
            SetAccessFlags(dmethod, method);

            // Create prototype
            dmethod.Prototype = PrototypeBuilder.BuildPrototype(compiler, targetPackage, declaringClass, xMethod);
        }
Ejemplo n.º 6
0
        /// <summary>
        /// Ensure that the name of the method is unique.
        /// </summary>
        private static void UpdateName(DexLib.MethodDefinition method, ClassDefinition declaringClass)
        {
            var baseName = method.Name;

            if (baseName == "<init>")
            {
                baseName = "NetCtor";
            }
            var name    = baseName;
            var postfix = 0;

            while (true)
            {
                if (declaringClass.Methods.All(x => x.Name != name))
                {
                    method.Name = name;
                    return;
                }
                name = baseName + ++postfix;
            }
        }
Ejemplo n.º 7
0
 /// <summary>
 /// Add the given method to its declaring class.
 /// </summary>
 protected override void SetAccessFlags(DexLib.MethodDefinition dmethod, MethodDefinition method)
 {
     base.SetAccessFlags(dmethod, method);
     dmethod.IsNative = true;
 }
Ejemplo n.º 8
0
 /// <summary>
 /// Add the given method to its declaring class.
 /// </summary>
 protected virtual void AddMethodToDeclaringClass(ClassDefinition declaringClass, DexLib.MethodDefinition dmethod, DexTargetPackage targetPackage)
 {
     dmethod.Owner = declaringClass;
     declaringClass.Methods.Add(dmethod);
 }
Ejemplo n.º 9
0
        public static MethodEntry RecordMapping(TypeEntry typeEntry, XMethodDefinition xMethod, MethodDefinition method, DexLib.MethodDefinition dmethod, CompiledMethod compiledMethod)
        {
            var scopeId = xMethod.ScopeId;

            StringBuilder netSignature = new StringBuilder();

            method.MethodSignatureFullName(netSignature);

            var entry = new MethodEntry(method.OriginalName, netSignature.ToString(), dmethod.Name, dmethod.Prototype.ToSignature(), dmethod.MapFileId,
                                        scopeId);

            typeEntry.Methods.Add(entry);

            if (compiledMethod != null)
            {
                compiledMethod.RecordMapping(entry);
            }

            return(entry);
        }
Ejemplo n.º 10
0
        /// <summary>
        /// Add the given method to its declaring class.
        /// </summary>
        protected override void AddMethodToDeclaringClass(ClassDefinition declaringClass, DexLib.MethodDefinition dmethod, DexTargetPackage targetPackage)
        {
            var generatedCodeClass = targetPackage.GetOrCreateGeneratedCodeClass();

            UpdateName(dmethod, generatedCodeClass);
            dmethod.Owner = generatedCodeClass;
            generatedCodeClass.Methods.Add(dmethod);
        }
Ejemplo n.º 11
0
 /// <summary>
 /// Add the given method to its declaring class.
 /// </summary>
 protected override void SetAccessFlags(DexLib.MethodDefinition dmethod, MethodDefinition method)
 {
     dmethod.IsStatic = true;
     dmethod.IsPublic = true;
 }