diff options
| -rw-r--r-- | dx/src/com/android/dx/command/dexer/Main.java | 4 | ||||
| -rw-r--r-- | dx/src/com/android/dx/dex/DexOptions.java | 8 | ||||
| -rw-r--r-- | dx/src/com/android/dx/dex/code/Dops.java | 26 | ||||
| -rw-r--r-- | dx/src/com/android/dx/io/Opcodes.java | 17 | ||||
| -rw-r--r-- | vm/Exception.cpp | 2 | ||||
| -rw-r--r-- | vm/alloc/HeapSource.cpp | 2 | ||||
| -rw-r--r-- | vm/analysis/DexPrepare.cpp | 2 | ||||
| -rw-r--r-- | vm/compiler/Frontend.cpp | 8 | ||||
| -rw-r--r-- | vm/compiler/codegen/arm/CodegenDriver.cpp | 5 | ||||
| -rw-r--r-- | vm/reflect/Annotation.cpp | 6 |
10 files changed, 66 insertions, 14 deletions
diff --git a/dx/src/com/android/dx/command/dexer/Main.java b/dx/src/com/android/dx/command/dexer/Main.java index 947bd4178..653b9bce4 100644 --- a/dx/src/com/android/dx/command/dexer/Main.java +++ b/dx/src/com/android/dx/command/dexer/Main.java @@ -1192,6 +1192,9 @@ public class Main { */ public boolean keepClassesInJar = false; + /** what API level to target */ + public int targetApiLevel = DexFormat.API_NO_EXTENDED_OPCODES; + /** how much source position info to preserve */ public int positionInfo = PositionList.LINES; @@ -1513,6 +1516,7 @@ public class Main { cfOptions.warn = DxConsole.err; dexOptions = new DexOptions(); + dexOptions.targetApiLevel = targetApiLevel; dexOptions.forceJumbo = forceJumbo; } } diff --git a/dx/src/com/android/dx/dex/DexOptions.java b/dx/src/com/android/dx/dex/DexOptions.java index 60d83a84e..db0c7a2c5 100644 --- a/dx/src/com/android/dx/dex/DexOptions.java +++ b/dx/src/com/android/dx/dex/DexOptions.java @@ -34,4 +34,12 @@ public class DexOptions { public String getMagic() { return DexFormat.apiToMagic(targetApiLevel); } + + /** + * Returns whether extended opcodes are allowed. This became + * allowed as of Ice Cream Sandwich. + */ + public boolean canUseExtendedOpcodes() { + return targetApiLevel >= DexFormat.API_CURRENT; + } } diff --git a/dx/src/com/android/dx/dex/code/Dops.java b/dx/src/com/android/dx/dex/code/Dops.java index a84ddc098..cc5c173ed 100644 --- a/dx/src/com/android/dx/dex/code/Dops.java +++ b/dx/src/com/android/dx/dex/code/Dops.java @@ -1206,15 +1206,29 @@ public final class Dops { * the last in its chain */ public static Dop getNextOrNull(Dop opcode, DexOptions options) { - int nextOpcode = opcode.getNextOpcode(); + boolean suppressExtendedOpcodes = !options.canUseExtendedOpcodes(); - if (nextOpcode == Opcodes.NO_NEXT) { - return null; - } + for (;;) { + int nextOpcode = opcode.getNextOpcode(); - opcode = get(nextOpcode); + if (nextOpcode == Opcodes.NO_NEXT) { + return null; + } + + opcode = get(nextOpcode); - return opcode; + if (suppressExtendedOpcodes && Opcodes.isExtended(nextOpcode)) { + /* + * Continuing rather than just returning null here + * protects against the possibility that an + * instruction fitting chain might list non-extended + * opcodes after extended ones. + */ + continue; + } + + return opcode; + } } /** diff --git a/dx/src/com/android/dx/io/Opcodes.java b/dx/src/com/android/dx/io/Opcodes.java index 611dbda43..6dba49d9e 100644 --- a/dx/src/com/android/dx/io/Opcodes.java +++ b/dx/src/com/android/dx/io/Opcodes.java @@ -327,6 +327,23 @@ public final class Opcodes { } /** + * Gets whether ({@code true}) or not ({@code false}) the given + * opcode value is an "extended" opcode (not counting the nop-like + * payload opcodes). Extended opcodes require a full 16-bit code + * unit to represent, without leaving space for an argument byte. + * + * @param opcode the opcode value + * @return {@code true} iff the opcode is an "extended" opcode + */ + public static boolean isExtended(int opcode) { + /* + * Note: Extended opcodes all have the form ((byteValue << 8) + * | 0xff). + */ + return (opcode >= 0x00ff); + } + + /** * Gets the opcode out of an opcode unit, the latter of which may also * include one or more argument values. * diff --git a/vm/Exception.cpp b/vm/Exception.cpp index 36f2d20c0..ca7614096 100644 --- a/vm/Exception.cpp +++ b/vm/Exception.cpp @@ -1225,7 +1225,7 @@ void dvmThrowArrayStoreExceptionNotArray(ClassObject* actual, const char* label) void dvmThrowArrayStoreExceptionIncompatibleArrays(ClassObject* source, ClassObject* destination) { throwTypeError(gDvm.exArrayStoreException, - "Incompatible types: src=%s, dst=%s", + "%s and %s are incompatible array types", source, destination); } diff --git a/vm/alloc/HeapSource.cpp b/vm/alloc/HeapSource.cpp index caf30af02..56d392ab3 100644 --- a/vm/alloc/HeapSource.cpp +++ b/vm/alloc/HeapSource.cpp @@ -414,7 +414,7 @@ static bool remapNewHeap(HeapSource* hs, Heap* newHeap) ALOGE("Unable to create an ashmem region for the new heap"); return false; } - void* addr = mmap(newHeapBase, rem_size, PROT_READ | PROT_WRITE, MAP_PRIVATE, fd, 0); + void* addr = mmap(newHeapBase, rem_size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_FIXED, fd, 0); int ret = close(fd); if (addr == MAP_FAILED) { ALOGE("Unable to map an ashmem region for the new heap"); diff --git a/vm/analysis/DexPrepare.cpp b/vm/analysis/DexPrepare.cpp index 707ac90e1..38954030a 100644 --- a/vm/analysis/DexPrepare.cpp +++ b/vm/analysis/DexPrepare.cpp @@ -1153,7 +1153,7 @@ static const u1* getSignature(const ClassPathEntry* cpe) * If this changes, update DEX_OPT_MAGIC_VERS. */ static const size_t kMinDepSize = 4 * 4; -static const size_t kMaxDepSize = 4 * 4 + 2544; // sanity check +static const size_t kMaxDepSize = 4 * 4 + 2643; // sanity check /* * Read the "opt" header, verify it, then read the dependencies section diff --git a/vm/compiler/Frontend.cpp b/vm/compiler/Frontend.cpp index 65ef1ebd9..3cebe8238 100644 --- a/vm/compiler/Frontend.cpp +++ b/vm/compiler/Frontend.cpp @@ -1484,6 +1484,11 @@ static bool exhaustTrace(CompilationUnit *cUnit, BasicBlock *curBlock) return true; } +/* placeholder of future passes */ +__attribute__((weak)) void dvmExtraPass(CompilationUnit *cUnit) +{ +} + /* Compile a loop */ static bool compileLoop(CompilationUnit *cUnit, unsigned int startOffset, JitTraceDescription *desc, int numMaxInsts, @@ -1574,12 +1579,15 @@ static bool compileLoop(CompilationUnit *cUnit, unsigned int startOffset, dvmCompilerLoopOpt(cUnit); + /* * Change the backward branch to the backward chaining cell after dataflow * analsys/optimizations are done. */ dvmCompilerInsertBackwardChaining(cUnit); + dvmExtraPass(cUnit); + #if defined(ARCH_IA32) /* Convert MIR to LIR, etc. */ dvmCompilerMIR2LIR(cUnit, info); diff --git a/vm/compiler/codegen/arm/CodegenDriver.cpp b/vm/compiler/codegen/arm/CodegenDriver.cpp index 93ea6133a..d9da0cd69 100644 --- a/vm/compiler/codegen/arm/CodegenDriver.cpp +++ b/vm/compiler/codegen/arm/CodegenDriver.cpp @@ -824,7 +824,7 @@ static bool genArithOpInt(CompilationUnit *cUnit, MIR *mir, bool checkZero = false; bool unary = false; int retReg = r0; - int (*callTgt)(int, int) = NULL; + int (*callTgt)(int, int); RegLocation rlResult; bool shiftOp = false; @@ -4417,7 +4417,8 @@ void dvmCompilerMIR2LIR(CompilationUnit *cUnit) * Append the label pseudo LIR first. Chaining cells will be handled * separately afterwards. */ - dvmCompilerAppendLIR(cUnit, (LIR *) &labelList[i]); + if(bb->blockType != kDalvikByteCode || !bb->hidden) + dvmCompilerAppendLIR(cUnit, (LIR *) &labelList[i]); } if (bb->blockType == kEntryBlock) { diff --git a/vm/reflect/Annotation.cpp b/vm/reflect/Annotation.cpp index bbd58e953..942027c7b 100644 --- a/vm/reflect/Annotation.cpp +++ b/vm/reflect/Annotation.cpp @@ -1288,7 +1288,7 @@ bool dvmIsClassAnnotationPresent(const ClassObject* clazz, { const DexAnnotationSetItem* pAnnoSet = findAnnotationSetForClass(clazz); if (pAnnoSet == NULL) { - return false; + return NULL; } const DexAnnotationItem* pAnnoItem = getAnnotationItemFromAnnotationSet( clazz, pAnnoSet, kDexVisibilityRuntime, annotationClazz); @@ -1743,7 +1743,7 @@ bool dvmIsMethodAnnotationPresent(const ClassObject* clazz, { const DexAnnotationSetItem* pAnnoSet = findAnnotationSetForMethod(method); if (pAnnoSet == NULL) { - return false; + return NULL; } const DexAnnotationItem* pAnnoItem = getAnnotationItemFromAnnotationSet( clazz, pAnnoSet, kDexVisibilityRuntime, annotationClazz); @@ -2053,7 +2053,7 @@ bool dvmIsFieldAnnotationPresent(const ClassObject* clazz, { const DexAnnotationSetItem* pAnnoSet = findAnnotationSetForField(field); if (pAnnoSet == NULL) { - return false; + return NULL; } const DexAnnotationItem* pAnnoItem = getAnnotationItemFromAnnotationSet( clazz, pAnnoSet, kDexVisibilityRuntime, annotationClazz); |
