• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download

HANDLE_OPCODE(OP_EXECUTE_INLINE)1 HANDLE_OPCODE(OP_EXECUTE_INLINE /*vB, {vD, vE, vF, vG}, inline@CCCC*/)
2     {
3         /*
4          * This has the same form as other method calls, but we ignore
5          * the 5th argument (vA).  This is chiefly because the first four
6          * arguments to a function on ARM are in registers.
7          *
8          * We only set the arguments that are actually used, leaving
9          * the rest uninitialized.  We're assuming that, if the method
10          * needs them, they'll be specified in the call.
11          *
12          * However, this annoys gcc when optimizations are enabled,
13          * causing a "may be used uninitialized" warning.  Quieting
14          * the warnings incurs a slight penalty (5%: 373ns vs. 393ns
15          * on empty method).  Note that valgrind is perfectly happy
16          * either way as the uninitialiezd values are never actually
17          * used.
18          */
19         u4 arg0, arg1, arg2, arg3;
20         arg0 = arg1 = arg2 = arg3 = 0;
21 
22         EXPORT_PC();
23 
24         vsrc1 = INST_B(inst);       /* #of args */
25         ref = FETCH(1);             /* inline call "ref" */
26         vdst = FETCH(2);            /* 0-4 register indices */
27         ILOGV("|execute-inline args=%d @%d {regs=0x%04x}",
28             vsrc1, ref, vdst);
29 
30         assert((vdst >> 16) == 0);  // 16-bit type -or- high 16 bits clear
31         assert(vsrc1 <= 4);
32 
33         switch (vsrc1) {
34         case 4:
35             arg3 = GET_REGISTER(vdst >> 12);
36             /* fall through */
37         case 3:
38             arg2 = GET_REGISTER((vdst & 0x0f00) >> 8);
39             /* fall through */
40         case 2:
41             arg1 = GET_REGISTER((vdst & 0x00f0) >> 4);
42             /* fall through */
43         case 1:
44             arg0 = GET_REGISTER(vdst & 0x0f);
45             /* fall through */
46         default:        // case 0
47             ;
48         }
49 
50         if (self->interpBreak.ctl.subMode & kSubModeDebugProfile) {
51             if (!dvmPerformInlineOp4Dbg(arg0, arg1, arg2, arg3, &retval, ref))
52                 GOTO_exceptionThrown();
53         } else {
54             if (!dvmPerformInlineOp4Std(arg0, arg1, arg2, arg3, &retval, ref))
55                 GOTO_exceptionThrown();
56         }
57     }
58     FINISH(3);
59 OP_END
60