diff options
author | 2017-07-05 17:19:41 -0700 | |
---|---|---|
committer | 2017-07-06 11:58:20 -0700 | |
commit | a79f0b5deb932aa44e227c94c4ad09082b3ab4c7 (patch) | |
tree | 2d16c2876f6ccbc8ca1b9f6bf7fe43523a4132e3 /compiler/optimizing/nodes_vector.h | |
parent | 4c4d9df7c79747978d2f927994a7b3c11a079075 (diff) |
Added GVN related attributes to vector nodes.
Rationale: enables better GVNing of vector operations,
also pays off some technical debt by adding unit tests
for vector nodes.
Test: test-art-host, test-art-target
Change-Id: I2aa886b894bb6a0961823ae309cf8cf44984cf4a
Diffstat (limited to 'compiler/optimizing/nodes_vector.h')
-rw-r--r-- | compiler/optimizing/nodes_vector.h | 50 |
1 files changed, 46 insertions, 4 deletions
diff --git a/compiler/optimizing/nodes_vector.h b/compiler/optimizing/nodes_vector.h index 5dbe29b4fa..dc522a463e 100644 --- a/compiler/optimizing/nodes_vector.h +++ b/compiler/optimizing/nodes_vector.h @@ -46,6 +46,10 @@ class Alignment { return "ALIGN(" + std::to_string(base_) + "," + std::to_string(offset_) + ")"; } + bool operator==(const Alignment& other) const { + return base_ == other.base_ && offset_ == other.offset_; + } + private: size_t base_; size_t offset_; @@ -96,6 +100,13 @@ class HVecOperation : public HVariableInputSizeInstruction { return GetPackedField<TypeField>(); } + bool CanBeMoved() const OVERRIDE { return true; } + + bool InstructionDataEquals(const HInstruction* other) const OVERRIDE { + const HVecOperation* o = other->AsVecOperation(); + return GetVectorLength() == o->GetVectorLength() && GetPackedType() == o->GetPackedType(); + } + DECLARE_ABSTRACT_INSTRUCTION(VecOperation); protected: @@ -189,6 +200,11 @@ class HVecMemoryOperation : public HVecOperation { HInstruction* GetArray() const { return InputAt(0); } HInstruction* GetIndex() const { return InputAt(1); } + bool InstructionDataEquals(const HInstruction* other) const OVERRIDE { + const HVecMemoryOperation* o = other->AsVecMemoryOperation(); + return HVecOperation::InstructionDataEquals(o) && GetAlignment() == o->GetAlignment(); + } + DECLARE_ABSTRACT_INSTRUCTION(VecMemoryOperation); private: @@ -378,6 +394,13 @@ class HVecHalvingAdd FINAL : public HVecBinaryOperation { bool IsUnsigned() const { return GetPackedFlag<kFieldHAddIsUnsigned>(); } bool IsRounded() const { return GetPackedFlag<kFieldHAddIsRounded>(); } + bool InstructionDataEquals(const HInstruction* other) const OVERRIDE { + const HVecHalvingAdd* o = other->AsVecHalvingAdd(); + return HVecOperation::InstructionDataEquals(o) && + IsUnsigned() == o->IsUnsigned() && + IsRounded() == o->IsRounded(); + } + DECLARE_INSTRUCTION(VecHalvingAdd); private: @@ -466,6 +489,11 @@ class HVecMin FINAL : public HVecBinaryOperation { bool IsUnsigned() const { return GetPackedFlag<kFieldMinOpIsUnsigned>(); } + bool InstructionDataEquals(const HInstruction* other) const OVERRIDE { + const HVecMin* o = other->AsVecMin(); + return HVecOperation::InstructionDataEquals(o) && IsUnsigned() == o->IsUnsigned(); + } + DECLARE_INSTRUCTION(VecMin); private: @@ -496,6 +524,11 @@ class HVecMax FINAL : public HVecBinaryOperation { bool IsUnsigned() const { return GetPackedFlag<kFieldMaxOpIsUnsigned>(); } + bool InstructionDataEquals(const HInstruction* other) const OVERRIDE { + const HVecMax* o = other->AsVecMax(); + return HVecOperation::InstructionDataEquals(o) && IsUnsigned() == o->IsUnsigned(); + } + DECLARE_INSTRUCTION(VecMax); private: @@ -694,10 +727,9 @@ class HVecMultiplyAccumulate FINAL : public HVecOperation { static constexpr int kInputMulLeftIndex = 1; static constexpr int kInputMulRightIndex = 2; - bool CanBeMoved() const OVERRIDE { return true; } - bool InstructionDataEquals(const HInstruction* other) const OVERRIDE { - return op_kind_ == other->AsVecMultiplyAccumulate()->op_kind_; + const HVecMultiplyAccumulate* o = other->AsVecMultiplyAccumulate(); + return HVecOperation::InstructionDataEquals(o) && GetOpKind() == o->GetOpKind(); } InstructionKind GetOpKind() const { return op_kind_; } @@ -732,10 +764,16 @@ class HVecLoad FINAL : public HVecMemoryOperation { SetRawInputAt(1, index); SetPackedFlag<kFieldIsStringCharAt>(is_string_char_at); } - DECLARE_INSTRUCTION(VecLoad); bool IsStringCharAt() const { return GetPackedFlag<kFieldIsStringCharAt>(); } + bool InstructionDataEquals(const HInstruction* other) const OVERRIDE { + const HVecLoad* o = other->AsVecLoad(); + return HVecMemoryOperation::InstructionDataEquals(o) && IsStringCharAt() == o->IsStringCharAt(); + } + + DECLARE_INSTRUCTION(VecLoad); + private: // Additional packed bits. static constexpr size_t kFieldIsStringCharAt = HVecOperation::kNumberOfVectorOpPackedBits; @@ -767,7 +805,11 @@ class HVecStore FINAL : public HVecMemoryOperation { SetRawInputAt(1, index); SetRawInputAt(2, value); } + + bool CanBeMoved() const OVERRIDE { return false; } + DECLARE_INSTRUCTION(VecStore); + private: DISALLOW_COPY_AND_ASSIGN(HVecStore); }; |