Mterp.cpp revision 7a0bcd0de6c4da6499a088a18d1750e51204c2a6
1f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project/*
2f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * Copyright (C) 2008 The Android Open Source Project
3f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project *
4f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License");
5f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * you may not use this file except in compliance with the License.
6f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * You may obtain a copy of the License at
7f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project *
8f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project *      http://www.apache.org/licenses/LICENSE-2.0
9f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project *
10f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * Unless required by applicable law or agreed to in writing, software
11f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS,
12f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * See the License for the specific language governing permissions and
14f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * limitations under the License.
15f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project */
16f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
17f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project/*
18f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * Mterp entry point and support functions.
19f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project */
20f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project#include "mterp/Mterp.h"
21f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
22f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project#include <stddef.h>
23f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
24f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
25f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project/*
26f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * Verify some constants used by the mterp interpreter.
27f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project */
28f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Projectbool dvmCheckAsmConstants(void)
29f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project{
304212241f98a49adcb955aee67a302cea57f3d984Dan Bornstein    bool failed = false;
314212241f98a49adcb955aee67a302cea57f3d984Dan Bornstein
324212241f98a49adcb955aee67a302cea57f3d984Dan Bornstein#ifndef DVM_NO_ASM_INTERP
334212241f98a49adcb955aee67a302cea57f3d984Dan Bornstein
34f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    extern char dvmAsmInstructionStart[];
35f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    extern char dvmAsmInstructionEnd[];
36f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    extern char dvmAsmSisterStart[];
37f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    extern char dvmAsmSisterEnd[];
38f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
39f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project#define ASM_DEF_VERIFY
40f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project#include "mterp/common/asm-constants.h"
41f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
42f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    if (failed) {
43f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        LOGE("Please correct the values in mterp/common/asm-constants.h\n");
44f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        dvmAbort();
45f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    }
46f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
47f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    /*
48f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project     * If an instruction overflows the 64-byte handler size limit, it will
49f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project     * push everything up and alter the total size.  Check it here.
50f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project     */
51f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    const int width = 64;
52f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    int interpSize = dvmAsmInstructionEnd - dvmAsmInstructionStart;
53f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    if (interpSize != 0 && interpSize != 256*width) {
54f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        LOGE("ERROR: unexpected asm interp size %d\n", interpSize);
55f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        LOGE("(did an instruction handler exceed %d bytes?)\n", width);
56f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        dvmAbort();
57f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    }
58f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    int sisterSize = dvmAsmSisterEnd - dvmAsmSisterStart;
59f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    LOGV("mterp: interp is %d bytes, sisters are %d bytes\n",
60f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        interpSize, sisterSize);
61f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
624212241f98a49adcb955aee67a302cea57f3d984Dan Bornstein#endif // ndef DVM_NO_ASM_INTERP
634212241f98a49adcb955aee67a302cea57f3d984Dan Bornstein
64f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    return !failed;
65f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project}
66f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
67f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
68f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project/*
69f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * "Standard" mterp entry point.  This sets up a "glue" structure and then
70f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * calls into the assembly interpreter implementation.
71f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project *
72f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project * (There is presently no "debug" entry point.)
73f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project */
74f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Projectbool dvmMterpStd(Thread* self, InterpState* glue)
75f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project{
76f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    int changeInterp;
77f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
78f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    /* configure mterp items */
79f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    glue->self = self;
80f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    glue->methodClassDex = glue->method->clazz->pDvmDex;
81f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
82f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    glue->interpStackEnd = self->interpStackEnd;
83f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    glue->pSelfSuspendCount = &self->suspendCount;
84ba4fc8bfc1bccae048403bd1cea3b869dca61dd7Ben Cheng#if defined(WITH_JIT)
85ba4fc8bfc1bccae048403bd1cea3b869dca61dd7Ben Cheng    glue->pJitProfTable = gDvmJit.pProfTable;
86d726991ba52466cde88e37aba4de2395b62477faBill Buzbee    glue->jitThreshold = gDvmJit.threshold;
87ba4fc8bfc1bccae048403bd1cea3b869dca61dd7Ben Cheng#endif
88f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project#if defined(WITH_DEBUGGER)
89f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    glue->pDebuggerActive = &gDvm.debuggerActive;
90f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project#endif
91f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project#if defined(WITH_PROFILER)
92f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    glue->pActiveProfilers = &gDvm.activeProfilers;
93f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project#endif
94f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
95f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    IF_LOGVV() {
96f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        char* desc = dexProtoCopyMethodDescriptor(&glue->method->prototype);
97f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        LOGVV("mterp threadid=%d entry %d: %s.%s %s\n",
98f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project            dvmThreadSelf()->threadId,
99f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project            glue->entryPoint,
100f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project            glue->method->clazz->descriptor,
101f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project            glue->method->name,
102f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project            desc);
103f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        free(desc);
104f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    }
105f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    //LOGI("glue is %p, pc=%p, fp=%p\n", glue, glue->pc, glue->fp);
106f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    //LOGI("first instruction is 0x%04x\n", glue->pc[0]);
107f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project
108f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    changeInterp = dvmMterpStdRun(glue);
1097a0bcd0de6c4da6499a088a18d1750e51204c2a6Ben Cheng
1107a0bcd0de6c4da6499a088a18d1750e51204c2a6Ben Cheng#if defined(WITH_JIT)
1117a0bcd0de6c4da6499a088a18d1750e51204c2a6Ben Cheng    if (glue->jitState != kJitSingleStep) {
1127a0bcd0de6c4da6499a088a18d1750e51204c2a6Ben Cheng        glue->self->inJitCodeCache = NULL;
1137a0bcd0de6c4da6499a088a18d1750e51204c2a6Ben Cheng    }
1147a0bcd0de6c4da6499a088a18d1750e51204c2a6Ben Cheng#endif
1157a0bcd0de6c4da6499a088a18d1750e51204c2a6Ben Cheng
116f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    if (!changeInterp) {
117f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        /* this is a "normal" exit; we're not coming back */
118f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project#ifdef LOG_INSTR
119f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        LOGD("|-- Leaving interpreter loop");
120f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project#endif
121f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        return false;
122f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    } else {
123f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        /* we're "standard", so switch to "debug" */
124f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        LOGVV("  mterp returned, changeInterp=%d\n", changeInterp);
125f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        glue->nextMode = INTERP_DBG;
126f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project        return true;
127f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project    }
128f6c387128427e121477c1b32ad35cdcaa5101ba3The Android Open Source Project}
129