ART: Refactor try/catch block info, store exception type
This patch replaces HBasicBlock fields storing try/catch info with a
single TryCatchInformation data structure, saving memory for the
majority of non-try/catch blocks. It also changes builder to store
the exception type for catch blocks.
Change-Id: Ib3e43f7db247e6915d67c267fc62410420e230c9
diff --git a/compiler/optimizing/nodes.cc b/compiler/optimizing/nodes.cc
index f2b63ae..64c680c 100644
--- a/compiler/optimizing/nodes.cc
+++ b/compiler/optimizing/nodes.cc
@@ -339,7 +339,10 @@
// been visited already and had its try membership set.
HBasicBlock* first_predecessor = block->GetPredecessors().Get(0);
DCHECK(!block->IsLoopHeader() || !block->GetLoopInformation()->IsBackEdge(*first_predecessor));
- block->SetTryEntry(first_predecessor->ComputeTryEntryOfSuccessors());
+ const HTryBoundary* try_entry = first_predecessor->ComputeTryEntryOfSuccessors();
+ if (try_entry != nullptr) {
+ block->SetTryCatchInformation(new (arena_) TryCatchInformation(*try_entry));
+ }
}
}
@@ -1164,19 +1167,21 @@
return new_block;
}
-HTryBoundary* HBasicBlock::ComputeTryEntryOfSuccessors() const {
+const HTryBoundary* HBasicBlock::ComputeTryEntryOfSuccessors() const {
if (EndsWithTryBoundary()) {
HTryBoundary* try_boundary = GetLastInstruction()->AsTryBoundary();
if (try_boundary->IsEntry()) {
- DCHECK(try_entry_ == nullptr);
+ DCHECK(!IsTryBlock());
return try_boundary;
} else {
- DCHECK(try_entry_ != nullptr);
- DCHECK(try_entry_->HasSameExceptionHandlersAs(*try_boundary));
+ DCHECK(IsTryBlock());
+ DCHECK(try_catch_information_->GetTryEntry().HasSameExceptionHandlersAs(*try_boundary));
return nullptr;
}
+ } else if (IsTryBlock()) {
+ return &try_catch_information_->GetTryEntry();
} else {
- return try_entry_;
+ return nullptr;
}
}