Index: test/unittests/compiler/mips64/instruction-selector-mips64-unittest.cc |
diff --git a/test/unittests/compiler/mips64/instruction-selector-mips64-unittest.cc b/test/unittests/compiler/mips64/instruction-selector-mips64-unittest.cc |
index 2ab6579c2a6b2e79a665d75af32122741c290773..5d33c26178d6185411a5d5ef4abe385af537cd23 100644 |
--- a/test/unittests/compiler/mips64/instruction-selector-mips64-unittest.cc |
+++ b/test/unittests/compiler/mips64/instruction-selector-mips64-unittest.cc |
@@ -1198,6 +1198,18 @@ std::ostream& operator<<(std::ostream& os, const MemoryAccessImm1& acc) { |
return os << acc.type; |
} |
+struct MemoryAccessImm2 { |
+ MachineType type; |
+ ArchOpcode store_opcode; |
+ ArchOpcode store_opcode_unaligned; |
+ bool (InstructionSelectorTest::Stream::*val_predicate)( |
+ const InstructionOperand*) const; |
+ const int32_t immediates[40]; |
+}; |
+ |
+std::ostream& operator<<(std::ostream& os, const MemoryAccessImm2& acc) { |
+ return os << acc.type; |
+} |
// ---------------------------------------------------------------------------- |
// Loads and stores immediate values |
@@ -1305,6 +1317,48 @@ const MemoryAccessImm1 kMemoryAccessImmMoreThan16bit[] = { |
&InstructionSelectorTest::Stream::IsInteger, |
{-65000, -55000, 32777, 55000, 65000}}}; |
+const MemoryAccessImm2 kMemoryAccessesImmUnaligned[] = { |
+ {MachineType::Int16(), |
+ kMips64Ush, |
+ kMips64Sh, |
+ &InstructionSelectorTest::Stream::IsInteger, |
+ {-4095, -3340, -3231, -3224, -3088, -1758, -1203, -123, -117, -91, |
+ -89, -87, -86, -82, -44, -23, -3, 0, 7, 10, |
+ 39, 52, 69, 71, 91, 92, 107, 109, 115, 124, |
+ 286, 655, 1362, 1569, 2587, 3067, 3096, 3462, 3510, 4095}}, |
+ {MachineType::Int32(), |
+ kMips64Usw, |
+ kMips64Sw, |
+ &InstructionSelectorTest::Stream::IsInteger, |
+ {-4095, -3340, -3231, -3224, -3088, -1758, -1203, -123, -117, -91, |
+ -89, -87, -86, -82, -44, -23, -3, 0, 7, 10, |
+ 39, 52, 69, 71, 91, 92, 107, 109, 115, 124, |
+ 286, 655, 1362, 1569, 2587, 3067, 3096, 3462, 3510, 4095}}, |
+ {MachineType::Int64(), |
+ kMips64Usd, |
+ kMips64Sd, |
+ &InstructionSelectorTest::Stream::IsInteger, |
+ {-4095, -3340, -3231, -3224, -3088, -1758, -1203, -123, -117, -91, |
+ -89, -87, -86, -82, -44, -23, -3, 0, 7, 10, |
+ 39, 52, 69, 71, 91, 92, 107, 109, 115, 124, |
+ 286, 655, 1362, 1569, 2587, 3067, 3096, 3462, 3510, 4095}}, |
+ {MachineType::Float32(), |
+ kMips64Uswc1, |
+ kMips64Swc1, |
+ &InstructionSelectorTest::Stream::IsDouble, |
+ {-4095, -3340, -3231, -3224, -3088, -1758, -1203, -123, -117, -91, |
+ -89, -87, -86, -82, -44, -23, -3, 0, 7, 10, |
+ 39, 52, 69, 71, 91, 92, 107, 109, 115, 124, |
+ 286, 655, 1362, 1569, 2587, 3067, 3096, 3462, 3510, 4095}}, |
+ {MachineType::Float64(), |
+ kMips64Usdc1, |
+ kMips64Sdc1, |
+ &InstructionSelectorTest::Stream::IsDouble, |
+ {-4095, -3340, -3231, -3224, -3088, -1758, -1203, -123, -117, -91, |
+ -89, -87, -86, -82, -44, -23, -3, 0, 7, 10, |
+ 39, 52, 69, 71, 91, 92, 107, 109, 115, 124, |
+ 286, 655, 1362, 1569, 2587, 3067, 3096, 3462, 3510, 4095}}}; |
+ |
} // namespace |
@@ -1391,10 +1445,60 @@ TEST_P(InstructionSelectorMemoryAccessImmTest, StoreWithImmediateIndex) { |
} |
} |
+TEST_P(InstructionSelectorMemoryAccessImmTest, StoreZero) { |
+ const MemoryAccessImm memacc = GetParam(); |
+ TRACED_FOREACH(int32_t, index, memacc.immediates) { |
+ StreamBuilder m(this, MachineType::Int32(), MachineType::Pointer()); |
+ m.Store(memacc.type.representation(), m.Parameter(0), |
+ m.Int32Constant(index), m.Int32Constant(0), kNoWriteBarrier); |
+ m.Return(m.Int32Constant(0)); |
+ Stream s = m.Build(); |
+ ASSERT_EQ(1U, s.size()); |
+ EXPECT_EQ(memacc.store_opcode, s[0]->arch_opcode()); |
+ EXPECT_EQ(kMode_MRI, s[0]->addressing_mode()); |
+ ASSERT_EQ(3U, s[0]->InputCount()); |
+ ASSERT_EQ(InstructionOperand::IMMEDIATE, s[0]->InputAt(1)->kind()); |
+ EXPECT_EQ(index, s.ToInt32(s[0]->InputAt(1))); |
+ ASSERT_EQ(InstructionOperand::IMMEDIATE, s[0]->InputAt(2)->kind()); |
+ EXPECT_EQ(0, s.ToInt64(s[0]->InputAt(2))); |
+ EXPECT_EQ(0U, s[0]->OutputCount()); |
+ } |
+} |
+ |
INSTANTIATE_TEST_CASE_P(InstructionSelectorTest, |
InstructionSelectorMemoryAccessImmTest, |
::testing::ValuesIn(kMemoryAccessesImm)); |
+typedef InstructionSelectorTestWithParam<MemoryAccessImm2> |
+ InstructionSelectorMemoryAccessUnalignedImmTest; |
+ |
+TEST_P(InstructionSelectorMemoryAccessUnalignedImmTest, StoreZero) { |
+ const MemoryAccessImm2 memacc = GetParam(); |
+ TRACED_FOREACH(int32_t, index, memacc.immediates) { |
+ StreamBuilder m(this, MachineType::Int32(), MachineType::Pointer()); |
+ bool unaligned_store_supported = m.machine()->UnalignedStoreSupported( |
+ MachineType::TypeForRepresentation(memacc.type.representation()), 1); |
+ m.UnalignedStore(memacc.type.representation(), m.Parameter(0), |
+ m.Int32Constant(index), m.Int32Constant(0)); |
+ m.Return(m.Int32Constant(0)); |
+ Stream s = m.Build(); |
+ ASSERT_EQ(1U, s.size()); |
+ EXPECT_EQ(unaligned_store_supported ? memacc.store_opcode_unaligned |
+ : memacc.store_opcode, |
+ s[0]->arch_opcode()); |
+ EXPECT_EQ(kMode_MRI, s[0]->addressing_mode()); |
+ ASSERT_EQ(3U, s[0]->InputCount()); |
+ ASSERT_EQ(InstructionOperand::IMMEDIATE, s[0]->InputAt(1)->kind()); |
+ EXPECT_EQ(index, s.ToInt32(s[0]->InputAt(1))); |
+ ASSERT_EQ(InstructionOperand::IMMEDIATE, s[0]->InputAt(2)->kind()); |
+ EXPECT_EQ(0, s.ToInt64(s[0]->InputAt(2))); |
+ EXPECT_EQ(0U, s[0]->OutputCount()); |
+ } |
+} |
+ |
+INSTANTIATE_TEST_CASE_P(InstructionSelectorTest, |
+ InstructionSelectorMemoryAccessUnalignedImmTest, |
+ ::testing::ValuesIn(kMemoryAccessesImmUnaligned)); |
// ---------------------------------------------------------------------------- |
// Load/store offsets more than 16 bits. |