summaryrefslogtreecommitdiff
path: root/compiler/optimizing
diff options
context:
space:
mode:
author Aart Bik <ajcbik@google.com> 2017-12-07 11:11:22 -0800
committer Aart Bik <ajcbik@google.com> 2017-12-07 15:43:33 -0800
commit2dd7b672ea0afd7ea4448b43d24829e9886de3af (patch)
treefd7e3c48f5ac17fc238bff68bf33e5868d1386dc /compiler/optimizing
parent718173b7705ebc7f4a15aaaa4c074f9e5d907b31 (diff)
Fixed spilling bug (visible on ARM64): missed SIMD type.
Test: test-art-host test-art-target Change-Id: I6f321446f54943e02f250732ec9da729f633c3a9
Diffstat (limited to 'compiler/optimizing')
-rw-r--r--compiler/optimizing/loop_optimization.cc3
-rw-r--r--compiler/optimizing/nodes_vector.h15
-rw-r--r--compiler/optimizing/ssa_liveness_analysis.cc7
3 files changed, 20 insertions, 5 deletions
diff --git a/compiler/optimizing/loop_optimization.cc b/compiler/optimizing/loop_optimization.cc
index 1ca096035e..3dc1ef7534 100644
--- a/compiler/optimizing/loop_optimization.cc
+++ b/compiler/optimizing/loop_optimization.cc
@@ -1749,7 +1749,8 @@ void HLoopOptimization::GenerateVecReductionPhiInputs(HPhi* phi, HInstruction* r
HInstruction* HLoopOptimization::ReduceAndExtractIfNeeded(HInstruction* instruction) {
if (instruction->IsPhi()) {
HInstruction* input = instruction->InputAt(1);
- if (input->IsVecOperation() && !input->IsVecExtractScalar()) {
+ if (HVecOperation::ReturnsSIMDValue(input)) {
+ DCHECK(!input->IsPhi());
HVecOperation* input_vector = input->AsVecOperation();
uint32_t vector_length = input_vector->GetVectorLength();
DataType::Type type = input_vector->GetPackedType();
diff --git a/compiler/optimizing/nodes_vector.h b/compiler/optimizing/nodes_vector.h
index 59d5b9f847..096349fd73 100644
--- a/compiler/optimizing/nodes_vector.h
+++ b/compiler/optimizing/nodes_vector.h
@@ -150,6 +150,19 @@ class HVecOperation : public HVariableInputSizeInstruction {
}
}
+ // Helper method to determine if an instruction returns a SIMD value.
+ // TODO: This method is needed until we introduce SIMD as proper type.
+ static bool ReturnsSIMDValue(HInstruction* instruction) {
+ if (instruction->IsVecOperation()) {
+ return !instruction->IsVecExtractScalar(); // only scalar returning vec op
+ } else if (instruction->IsPhi()) {
+ return
+ instruction->GetType() == kSIMDType &&
+ instruction->InputAt(1)->IsVecOperation(); // vectorizer does not go deeper
+ }
+ return false;
+ }
+
DECLARE_ABSTRACT_INSTRUCTION(VecOperation);
protected:
@@ -879,7 +892,7 @@ class HVecSetScalars FINAL : public HVecOperation {
vector_length,
dex_pc) {
for (size_t i = 0; i < number_of_scalars; i++) {
- DCHECK(!scalars[i]->IsVecOperation() || scalars[i]->IsVecExtractScalar());
+ DCHECK(!ReturnsSIMDValue(scalars[i]));
SetRawInputAt(0, scalars[i]);
}
}
diff --git a/compiler/optimizing/ssa_liveness_analysis.cc b/compiler/optimizing/ssa_liveness_analysis.cc
index 9ab7a89b33..f6bd05269e 100644
--- a/compiler/optimizing/ssa_liveness_analysis.cc
+++ b/compiler/optimizing/ssa_liveness_analysis.cc
@@ -474,9 +474,10 @@ size_t LiveInterval::NumberOfSpillSlotsNeeded() const {
// For a SIMD operation, compute the number of needed spill slots.
// TODO: do through vector type?
HInstruction* definition = GetParent()->GetDefinedBy();
- if (definition != nullptr &&
- definition->IsVecOperation() &&
- !definition->IsVecExtractScalar()) {
+ if (definition != nullptr && HVecOperation::ReturnsSIMDValue(definition)) {
+ if (definition->IsPhi()) {
+ definition = definition->InputAt(1); // SIMD always appears on back-edge
+ }
return definition->AsVecOperation()->GetVectorNumberOfBytes() / kVRegSize;
}
// Return number of needed spill slots based on type.