1 /* 2 * Copyright (C) 2008 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 /* 18 * Mterp entry point and support functions. 19 */ 20 #include "Dalvik.h" 21 #include "mterp/Mterp.h" 22 23 #include <stddef.h> 24 25 26 /* 27 * Verify some constants used by the mterp interpreter. 28 */ 29 bool dvmCheckAsmConstants() 30 { 31 bool failed = false; 32 33 #ifndef DVM_NO_ASM_INTERP 34 35 #ifndef DVM_JMP_TABLE_MTERP 36 extern void* dvmAsmInstructionStart[]; 37 extern void* dvmAsmInstructionEnd[]; 38 #endif 39 40 #define ASM_DEF_VERIFY 41 #include "mterp/common/asm-constants.h" 42 43 if (failed) { 44 ALOGE("Please correct the values in mterp/common/asm-constants.h"); 45 dvmAbort(); 46 } 47 48 #ifndef DVM_JMP_TABLE_MTERP 49 /* 50 * If we're using computed goto instruction transitions, make sure 51 * none of the handlers overflows the 64-byte limit. This won't tell 52 * which one did, but if any one is too big the total size will 53 * overflow. 54 */ 55 #if defined(__mips__) 56 const int width = 128; 57 #else 58 const int width = 64; 59 #endif 60 int interpSize = (uintptr_t) dvmAsmInstructionEnd - 61 (uintptr_t) dvmAsmInstructionStart; 62 if (interpSize != 0 && interpSize != kNumPackedOpcodes*width) { 63 ALOGE("ERROR: unexpected asm interp size %d", interpSize); 64 ALOGE("(did an instruction handler exceed %d bytes?)", width); 65 dvmAbort(); 66 } 67 #endif 68 69 #endif // ndef DVM_NO_ASM_INTERP 70 71 return !failed; 72 } 73 74 75 /* 76 * "Mterp entry point. 77 */ 78 void dvmMterpStd(Thread* self) 79 { 80 /* configure mterp items */ 81 self->interpSave.methodClassDex = self->interpSave.method->clazz->pDvmDex; 82 83 IF_LOGVV() { 84 char* desc = dexProtoCopyMethodDescriptor( 85 &self->interpSave.method->prototype); 86 LOGVV("mterp threadid=%d : %s.%s %s", 87 dvmThreadSelf()->threadId, 88 self->interpSave.method->clazz->descriptor, 89 self->interpSave.method->name, 90 desc); 91 free(desc); 92 } 93 //ALOGI("self is %p, pc=%p, fp=%p", self, self->interpSave.pc, 94 // self->interpSave.curFrame); 95 //ALOGI("first instruction is 0x%04x", self->interpSave.pc[0]); 96 97 /* 98 * Handle any ongoing profiling and prep for debugging 99 */ 100 if (self->interpBreak.ctl.subMode != 0) { 101 TRACE_METHOD_ENTER(self, self->interpSave.method); 102 self->debugIsMethodEntry = true; // Always true on startup 103 } 104 105 dvmMterpStdRun(self); 106 107 #ifdef LOG_INSTR 108 ALOGD("|-- Leaving interpreter loop"); 109 #endif 110 } 111