OSDN Git Service

af31a3da727f24b4fbe9a7df6bbd2982fca6221e
[android-x86/dalvik.git] / vm / mterp / cstubs / entry.c
1 /*
2  * Handler function table, one entry per opcode.
3  */
4 #undef H
5 #define H(_op) dvmMterp_##_op
6 DEFINE_GOTO_TABLE(gDvmMterpHandlers)
7
8 #undef H
9 #define H(_op) #_op
10 DEFINE_GOTO_TABLE(gDvmMterpHandlerNames)
11
12 #include <setjmp.h>
13
14 /*
15  * C mterp entry point.  This just calls the various C fallbacks, making
16  * this a slow but portable interpeter.
17  *
18  * This is only used for the "allstubs" variant.
19  */
20 bool dvmMterpStdRun(MterpGlue* glue)
21 {
22     jmp_buf jmpBuf;
23     int changeInterp;
24
25     glue->bailPtr = &jmpBuf;
26
27     /*
28      * We want to return "changeInterp" as a boolean, but we can't return
29      * zero through longjmp, so we return (boolean+1).
30      */
31     changeInterp = setjmp(jmpBuf) -1;
32     if (changeInterp >= 0) {
33         Thread* threadSelf = dvmThreadSelf();
34         LOGVV("mterp threadid=%d returning %d\n",
35             threadSelf->threadId, changeInterp);
36         return changeInterp;
37     }
38
39     /*
40      * We may not be starting at a point where we're executing instructions.
41      * We need to pick up where the other interpreter left off.
42      *
43      * In some cases we need to call into a throw/return handler which
44      * will do some processing and then either return to us (updating "glue")
45      * or longjmp back out.
46      */
47     switch (glue->entryPoint) {
48     case kInterpEntryInstr:
49         /* just start at the start */
50         break;
51     case kInterpEntryReturn:
52         dvmMterp_returnFromMethod(glue);
53         break;
54     case kInterpEntryThrow:
55         dvmMterp_exceptionThrown(glue);
56         break;
57     default:
58         dvmAbort();
59     }
60
61     /* run until somebody longjmp()s out */
62     while (true) {
63         typedef void (*Handler)(MterpGlue* glue);
64
65         u2 inst = /*glue->*/pc[0];
66         Handler handler = (Handler) gDvmMterpHandlers[inst & 0xff];
67         LOGVV("handler %p %s\n",
68             handler, (const char*) gDvmMterpHandlerNames[inst & 0xff]);
69         (*handler)(glue);
70     }
71 }
72
73 /*
74  * C mterp exit point.  Call here to bail out of the interpreter.
75  */
76 void dvmMterpStdBail(MterpGlue* glue, bool changeInterp)
77 {
78     jmp_buf* pJmpBuf = glue->bailPtr;
79     longjmp(*pJmpBuf, ((int)changeInterp)+1);
80 }