Remove the link from dalvik instruction back to kMirOpCheck.
Free the MIR::meta for another use on PUT/GET instructions.
Change-Id: Ic5a5cc5026e2076031d7b8ce7f2b36c185bfc93a
diff --git a/compiler/dex/local_value_numbering.cc b/compiler/dex/local_value_numbering.cc
index 75883b7..9e83210 100644
--- a/compiler/dex/local_value_numbering.cc
+++ b/compiler/dex/local_value_numbering.cc
@@ -380,9 +380,6 @@
}
mir->optimization_flags |= MIR_IGNORE_RANGE_CHECK;
}
- if (mir->meta.throw_insn != NULL) {
- mir->meta.throw_insn->optimization_flags |= mir->optimization_flags;
- }
// Use side effect to note range check completed.
(void)LookupValue(ARRAY_REF, array, index, NO_VALUE);
// Establish value number for loaded register. Note use of memory version.
@@ -421,9 +418,6 @@
}
mir->optimization_flags |= MIR_IGNORE_RANGE_CHECK;
}
- if (mir->meta.throw_insn != NULL) {
- mir->meta.throw_insn->optimization_flags |= mir->optimization_flags;
- }
// Use side effect to note range check completed.
(void)LookupValue(ARRAY_REF, array, index, NO_VALUE);
// Rev the memory version
@@ -447,9 +441,6 @@
} else {
null_checked_.insert(base);
}
- if (mir->meta.throw_insn != NULL) {
- mir->meta.throw_insn->optimization_flags |= mir->optimization_flags;
- }
uint16_t field_ref = mir->dalvikInsn.vC;
uint16_t memory_version = GetMemoryVersion(base, field_ref);
if (opcode == Instruction::IGET_WIDE) {
@@ -479,9 +470,6 @@
} else {
null_checked_.insert(base);
}
- if (mir->meta.throw_insn != NULL) {
- mir->meta.throw_insn->optimization_flags |= mir->optimization_flags;
- }
uint16_t field_ref = mir->dalvikInsn.vC;
AdvanceMemoryVersion(base, field_ref);
}
diff --git a/compiler/dex/mir_graph.cc b/compiler/dex/mir_graph.cc
index f321cda..8c90edb 100644
--- a/compiler/dex/mir_graph.cc
+++ b/compiler/dex/mir_graph.cc
@@ -126,9 +126,6 @@
bottom_block->terminated_by_return = orig_block->terminated_by_return;
orig_block->terminated_by_return = false;
- /* Add it to the quick lookup cache */
- dex_pc_to_block_map_.Put(bottom_block->start_offset, bottom_block->id);
-
/* Handle the taken path */
bottom_block->taken = orig_block->taken;
if (bottom_block->taken != NullBasicBlockId) {
@@ -177,19 +174,29 @@
}
// Associate dex instructions in the bottom block with the new container.
- MIR* p = bottom_block->first_mir_insn;
- while (p != NULL) {
+ DCHECK(insn != nullptr);
+ DCHECK(insn != orig_block->first_mir_insn);
+ DCHECK(insn == bottom_block->first_mir_insn);
+ DCHECK_EQ(insn->offset, bottom_block->start_offset);
+ DCHECK(static_cast<int>(insn->dalvikInsn.opcode) == kMirOpCheck ||
+ !IsPseudoMirOp(insn->dalvikInsn.opcode));
+ DCHECK_EQ(dex_pc_to_block_map_.Get(insn->offset), orig_block->id);
+ MIR* p = insn;
+ dex_pc_to_block_map_.Put(p->offset, bottom_block->id);
+ while (p != bottom_block->last_mir_insn) {
+ p = p->next;
+ DCHECK(p != nullptr);
int opcode = p->dalvikInsn.opcode;
/*
* Some messiness here to ensure that we only enter real opcodes and only the
* first half of a potentially throwing instruction that has been split into
- * CHECK and work portions. The 2nd half of a split operation will have a non-null
- * throw_insn pointer that refers to the 1st half.
+ * CHECK and work portions. Since the 2nd half of a split operation is always
+ * the first in a BasicBlock, we can't hit it here.
*/
- if ((opcode == kMirOpCheck) || (!IsPseudoMirOp(opcode) && (p->meta.throw_insn == NULL))) {
+ if ((opcode == kMirOpCheck) || !IsPseudoMirOp(opcode)) {
+ DCHECK_EQ(dex_pc_to_block_map_.Get(p->offset), orig_block->id);
dex_pc_to_block_map_.Put(p->offset, bottom_block->id);
}
- p = (p == bottom_block->last_mir_insn) ? NULL : p->next;
}
return bottom_block;
@@ -508,7 +515,6 @@
static_cast<Instruction::Code>(kMirOpCheck);
// Associate the two halves
insn->meta.throw_insn = new_insn;
- new_insn->meta.throw_insn = insn;
AppendMIR(new_block, new_insn);
return new_block;
}
diff --git a/compiler/dex/mir_graph.h b/compiler/dex/mir_graph.h
index bbcea10..4666d1e 100644
--- a/compiler/dex/mir_graph.h
+++ b/compiler/dex/mir_graph.h
@@ -253,7 +253,7 @@
union {
// Incoming edges for phi node.
BasicBlockId* phi_incoming;
- // Establish link between two halves of throwing instructions.
+ // Establish link from check instruction (kMirOpCheck) to the actual throwing instruction.
MIR* throw_insn;
// Fused cmp branch condition.
ConditionCode ccode;
diff --git a/compiler/dex/quick/mir_to_lir.cc b/compiler/dex/quick/mir_to_lir.cc
index 6281eff..0a470a5 100644
--- a/compiler/dex/quick/mir_to_lir.cc
+++ b/compiler/dex/quick/mir_to_lir.cc
@@ -762,11 +762,13 @@
// Combine check and work halves of throwing instruction.
MIR* work_half = mir->meta.throw_insn;
mir->dalvikInsn.opcode = work_half->dalvikInsn.opcode;
+ mir->meta = work_half->meta; // Whatever the work_half had, we need to copy it.
opcode = work_half->dalvikInsn.opcode;
SSARepresentation* ssa_rep = work_half->ssa_rep;
work_half->ssa_rep = mir->ssa_rep;
mir->ssa_rep = ssa_rep;
work_half->dalvikInsn.opcode = static_cast<Instruction::Code>(kMirOpCheckPart2);
+ work_half->meta.throw_insn = mir;
}
if (opcode >= kMirOpFirst) {