Example #1
0
        /// <summary>
        /// Record the given method mapping
        /// </summary>
        internal CompiledMethod Record(MethodSource source, RL.MethodBody rlBody, InvocationFrame frame)
        {
            var compiledMethod = GetOrCreateCompileMethod(source);

            compiledMethod.RLBody          = rlBody;
            compiledMethod.InvocationFrame = frame;
            return(compiledMethod);
        }
Example #2
0
        /// <summary>
        /// Default ctor
        /// </summary>
        public RegisterMapper(MethodBody body, InvocationFrame frame)
        {
            this.frame = frame;
            // Select all non-argument registers that are in use.
            Dictionary <Register, RegisterFlags> used;
            int  maxOutgoingRegisters;
            bool largeInvokeInsFound;

            GetUsedArgumentRegisters(body, out used, out maxOutgoingRegisters, out largeInvokeInsFound);
            //var used = body.Registers.Where(x => (x.Category != RCategory.Argument) && body.Instructions.Uses(x)).ToList();
            var sorted = used.OrderBy(x => x.Value).ThenBy(x => x.Key.Index).Select(x => x.Key).ToList();

            AddKeepWithNext(sorted, body);
            // Collect argument registers
            var arguments = body.Registers.Where(x => x.Category == RCategory.Argument).ToList();

            // Prepare various decisions
            //var maxOutgoingRegisters = body.Instructions.Max(x => x.Code.IsInvoke() ? x.Registers.Count : 0);
            var required = sorted.Count + arguments.Count;
            //var largeInvokeInsFound = body.Instructions.Any(x => x.Code.IsInvoke() && x.Registers.Count > 5);

            // Allocate Dex registers for each
            var index = 0;

            // Allocate spill registers (if needed)
            if ((required >= 16) || (largeInvokeInsFound && (required + maxOutgoingRegisters >= 16)))
            {
                spillRangeRegisters = new DexLib.Instructions.Register[MaxSpillRegisters];
                for (var i = 0; i < MaxSpillRegisters; i++)
                {
                    spillRangeRegisters[i] = new DexLib.Instructions.Register(index++);
                }
            }

            // Allocate Dex registers for each temp register.
            foreach (var r in sorted)
            {
                var dreg = new DexLib.Instructions.Register(index++);
                map[r] = dreg;
                dRegisterTypes[dreg] = r.Type;
            }

            // Allocate outgoing invocation frame (if needed)
            if ((required >= 16) || largeInvokeInsFound)
            {
                invokeRangeRegisters = new DexLib.Instructions.Register[maxOutgoingRegisters];
                for (var i = 0; i < maxOutgoingRegisters; i++)
                {
                    invokeRangeRegisters[i] = new DexLib.Instructions.Register(index++);
                }
            }

            // Allocate Dex registers for each argument
            foreach (var r in arguments)
            {
                var dreg = new DexLib.Instructions.Register(index++);
                map[r] = dreg;
                dRegisterTypes[dreg] = r.Type;
            }
            ArgumentCount = arguments.Count;
        }
Example #3
0
 /// <summary>
 /// Default ctor
 /// </summary>
 public DexCompiler(RL.MethodBody rlBody, MethodBody dexBody, InvocationFrame frame)
 {
     this.rlBody  = rlBody;
     this.dexBody = dexBody;
     this.frame   = frame;
 }