diff --git a/dexlib2/src/main/java/org/jf/dexlib2/writer/util/InstructionWriteUtil.java b/dexlib2/src/main/java/org/jf/dexlib2/writer/util/InstructionWriteUtil.java index f77f4192..9a9d417f 100644 --- a/dexlib2/src/main/java/org/jf/dexlib2/writer/util/InstructionWriteUtil.java +++ b/dexlib2/src/main/java/org/jf/dexlib2/writer/util/InstructionWriteUtil.java @@ -32,6 +32,7 @@ package org.jf.dexlib2.writer.util; import com.google.common.collect.Lists; +import com.google.common.collect.Maps; import org.jf.dexlib2.Format; import org.jf.dexlib2.Opcode; import org.jf.dexlib2.ReferenceType; @@ -148,17 +149,14 @@ public class InstructionWriteUtil 0xFFFF) { - if (codeOffsetShifts == null) { - codeOffsetShifts = new ArrayList(); - } - if (offsetToNewInstructionMap == null) { - offsetToNewInstructionMap = new HashMap(); - } codeOffsetShifts.add(currentCodeOffset+instruction.getCodeUnits()); offsetToNewInstructionMap.put(currentCodeOffset, Opcode.CONST_STRING_JUMBO.format); } @@ -166,10 +164,6 @@ public class InstructionWriteUtil { + public InsnWriteUtil(@Nonnull MethodImplementation implementation) { + super(implementation.getInstructions(), mockStringIndexProvider, ImmutableInstructionFactory.INSTANCE); + } + } + + @Before + public void setup() { + mockStringIndexProvider = new MockStringIndexProvider(); + } + + @Test + public void testArrayPayloadAlignment() { + ArrayList instructions = Lists.newArrayList(); + + // add misaligned array payload + instructions.add(new ImmutableInstruction10x(Opcode.NOP)); + instructions.add(new ImmutableArrayPayload(4, null)); + + ImmutableMethodImplementation methodImplementation = new ImmutableMethodImplementation(1, instructions, null, null); + InsnWriteUtil writeUtil = new InsnWriteUtil(methodImplementation); + + int codeOffset = 0; + for (Instruction instr: writeUtil.getInstructions()) { + if (instr.getOpcode().equals(Opcode.ARRAY_PAYLOAD)) { + Assert.assertEquals("array payload was not aligned properly", codeOffset%2, 0); + break; + } + codeOffset += instr.getCodeUnits(); + } + } + + @Test + public void testPackedSwitchAlignment() { + ArrayList instructions = Lists.newArrayList(); + // add misaligned packed switch payload + ArrayList switchElements = Lists.newArrayList(); + switchElements.add(new ImmutableSwitchElement(0, 5)); + instructions.add(new ImmutableInstruction10x(Opcode.NOP)); + instructions.add(new ImmutablePackedSwitchPayload(switchElements)); + + ImmutableMethodImplementation methodImplementation = new ImmutableMethodImplementation(1, instructions, null, null); + InsnWriteUtil writeUtil = new InsnWriteUtil(methodImplementation); + + int codeOffset = 0; + for (Instruction instr: writeUtil.getInstructions()) { + if (instr.getOpcode().equals(Opcode.PACKED_SWITCH_PAYLOAD)) { + Assert.assertEquals("packed switch payload was not aligned properly", codeOffset%2, 0); + break; + } + codeOffset += instr.getCodeUnits(); + } + } + + @Test + public void testSparseSwitchAlignment() { + ArrayList instructions = Lists.newArrayList(); + + // add misaligned sparse switch payload + ArrayList switchElements = Lists.newArrayList(); + switchElements.add(new ImmutableSwitchElement(0, 5)); + + instructions.add(new ImmutableInstruction10x(Opcode.NOP)); + instructions.add(new ImmutableSparseSwitchPayload(switchElements)); + + ImmutableMethodImplementation methodImplementation = new ImmutableMethodImplementation(1, instructions, null, null); + InsnWriteUtil writeUtil = new InsnWriteUtil(methodImplementation); + + int codeOffset = 0; + for (Instruction instr: writeUtil.getInstructions()) { + if (instr.getOpcode().equals(Opcode.SPARSE_SWITCH_PAYLOAD)) { + Assert.assertEquals("packed switch payload was not aligned properly", codeOffset%2, 0); + break; + } + codeOffset += instr.getCodeUnits(); + } + } +}