diff options
author | 2023-03-15 13:36:40 +0800 | |
---|---|---|
committer | 2023-05-11 16:08:45 +0000 | |
commit | 593fc2ed0b80bc2af4834f595cbb9fcc20edeb03 (patch) | |
tree | 18de608f51c3ae9f124a219d9c54d7aa0bac3b5d /compiler/utils/assembler_test.h | |
parent | ca3bf187748a26cfb33b53965e29086c5dc614de (diff) |
Add assembler for riscv64, part 2.
Test: m test-art-host-gtest
Bug: 271573990
Signed-off-by: Lifang Xia <lifang_xia@linux.alibaba.com>
Signed-off-by: Wendong Wang <wangwd@xcvmbyte.com>
Signed-off-by: Cao Xia <caoxia@eswincomputing.com>
Change-Id: I51a5c17f0d1d4e10d3b3b2f4e2ae88a75ca13bd1
Diffstat (limited to 'compiler/utils/assembler_test.h')
-rw-r--r-- | compiler/utils/assembler_test.h | 191 |
1 files changed, 183 insertions, 8 deletions
diff --git a/compiler/utils/assembler_test.h b/compiler/utils/assembler_test.h index f8a7f61f75..d375302d9d 100644 --- a/compiler/utils/assembler_test.h +++ b/compiler/utils/assembler_test.h @@ -411,6 +411,179 @@ class AssemblerTest : public AssemblerTestBase { return str; } + template <typename RegType, typename ImmType> + std::string RepeatTemplatedRegisterImmBitsShift( + void (Ass::*f)(RegType, ImmType), + int imm_bits, + int shift, + const std::vector<RegType*> registers, + std::string (AssemblerTest::*GetName)(const RegType&), + const std::string& fmt, + int bias) { + std::string str; + std::vector<int64_t> imms = CreateImmediateValuesBits(abs(imm_bits), (imm_bits > 0), shift); + + for (auto reg : registers) { + for (int64_t imm : imms) { + ImmType new_imm = CreateImmediate(imm); + if (f != nullptr) { + (assembler_.get()->*f)(*reg, new_imm + bias); + } + std::string base = fmt; + + std::string reg_string = (this->*GetName)(*reg); + size_t reg_index; + while ((reg_index = base.find(REG_TOKEN)) != std::string::npos) { + base.replace(reg_index, ConstexprStrLen(REG_TOKEN), reg_string); + } + + size_t imm_index = base.find(IMM_TOKEN); + if (imm_index != std::string::npos) { + std::ostringstream sreg; + sreg << imm + bias; + std::string imm_string = sreg.str(); + base.replace(imm_index, ConstexprStrLen(IMM_TOKEN), imm_string); + } + + if (str.size() > 0) { + str += "\n"; + } + str += base; + } + } + // Add a newline at the end. + str += "\n"; + return str; + } + + template <typename ImmType> + std::string RepeatTemplatedImmBitsShift( + void (Ass::*f)(ImmType), int imm_bits, int shift, const std::string& fmt, int bias = 0) { + std::vector<int64_t> imms = CreateImmediateValuesBits(abs(imm_bits), (imm_bits > 0), shift); + + WarnOnCombinations(imms.size()); + + std::string str; + + for (int64_t imm : imms) { + ImmType new_imm = CreateImmediate(imm); + if (f != nullptr) { + (assembler_.get()->*f)(new_imm + bias); + } + std::string base = fmt; + + size_t imm_index = base.find(IMM_TOKEN); + if (imm_index != std::string::npos) { + std::ostringstream sreg; + sreg << imm; + std::string imm_string = sreg.str(); + base.replace(imm_index, ConstexprStrLen(IMM_TOKEN), imm_string); + } + + if (str.size() > 0) { + str += "\n"; + } + str += base; + } + + // Add a newline at the end. + str += "\n"; + return str; + } + + template <typename Reg1, typename Reg2, typename ImmType> + std::string RepeatTemplatedRegistersImmBitsShift( + void (Ass::*f)(Reg1, Reg2, ImmType), + int imm_bits, + int shift, + const std::vector<Reg1*> reg1_registers, + const std::vector<Reg2*> reg2_registers, + std::string (AssemblerTest::*GetName1)(const Reg1&), + std::string (AssemblerTest::*GetName2)(const Reg2&), + const std::string& fmt, + int bias = 0, + int multiplier = 1) { + std::string str; + std::vector<int64_t> imms = CreateImmediateValuesBits(abs(imm_bits), (imm_bits > 0), shift); + + for (auto reg1 : reg1_registers) { + for (auto reg2 : reg2_registers) { + for (int64_t imm : imms) { + ImmType new_imm = CreateImmediate(imm); + if (f != nullptr) { + (assembler_.get()->*f)(*reg1, *reg2, new_imm * multiplier + bias); + } + std::string base = fmt; + + std::string reg1_string = (this->*GetName1)(*reg1); + size_t reg1_index; + while ((reg1_index = base.find(REG1_TOKEN)) != std::string::npos) { + base.replace(reg1_index, ConstexprStrLen(REG1_TOKEN), reg1_string); + } + + std::string reg2_string = (this->*GetName2)(*reg2); + size_t reg2_index; + while ((reg2_index = base.find(REG2_TOKEN)) != std::string::npos) { + base.replace(reg2_index, ConstexprStrLen(REG2_TOKEN), reg2_string); + } + + size_t imm_index = base.find(IMM_TOKEN); + if (imm_index != std::string::npos) { + std::ostringstream sreg; + sreg << imm * multiplier + bias; + std::string imm_string = sreg.str(); + base.replace(imm_index, ConstexprStrLen(IMM_TOKEN), imm_string); + } + + if (str.size() > 0) { + str += "\n"; + } + str += base; + } + } + } + // Add a newline at the end. + str += "\n"; + return str; + } + + template <typename ImmType> + std::string RepeatIbS( + void (Ass::*f)(ImmType), int imm_bits, int shift, const std::string& fmt, int bias = 0) { + return RepeatTemplatedImmBitsShift<ImmType>(f, imm_bits, shift, fmt, bias); + } + + template <typename ImmType> + std::string RepeatRIbS( + void (Ass::*f)(Reg, ImmType), int imm_bits, int shift, const std::string& fmt, int bias = 0) { + return RepeatTemplatedRegisterImmBitsShift<Reg, ImmType>( + f, + imm_bits, + shift, + GetRegisters(), + &AssemblerTest::GetRegName<RegisterView::kUsePrimaryName>, + fmt, + bias); + } + + template <typename ImmType> + std::string RepeatRRIbS(void (Ass::*f)(Reg, Reg, ImmType), + int imm_bits, + int shift, + const std::string& fmt, + int bias = 0) { + return RepeatTemplatedRegistersImmBitsShift<Reg, Reg, ImmType>( + f, + imm_bits, + shift, + GetRegisters(), + GetRegisters(), + &AssemblerTest::GetRegName<RegisterView::kUsePrimaryName>, + &AssemblerTest::GetRegName<RegisterView::kUsePrimaryName>, + fmt, + bias); + } + template <typename ImmType> std::string RepeatRRIb(void (Ass::*f)(Reg, Reg, ImmType), int imm_bits, @@ -857,7 +1030,9 @@ class AssemblerTest : public AssemblerTestBase { const int kMaxBitsExhaustiveTest = 8; // Create a couple of immediate values up to the number of bits given. - virtual std::vector<int64_t> CreateImmediateValuesBits(const int imm_bits, bool as_uint = false) { + virtual std::vector<int64_t> CreateImmediateValuesBits(const int imm_bits, + bool as_uint = false, + int shift = 0) { CHECK_GT(imm_bits, 0); CHECK_LE(imm_bits, 64); std::vector<int64_t> res; @@ -865,11 +1040,11 @@ class AssemblerTest : public AssemblerTestBase { if (imm_bits <= kMaxBitsExhaustiveTest) { if (as_uint) { for (uint64_t i = MinInt<uint64_t>(imm_bits); i <= MaxInt<uint64_t>(imm_bits); i++) { - res.push_back(static_cast<int64_t>(i)); + res.push_back(static_cast<int64_t>(i << shift)); } } else { for (int64_t i = MinInt<int64_t>(imm_bits); i <= MaxInt<int64_t>(imm_bits); i++) { - res.push_back(i); + res.push_back(i << shift); } } } else { @@ -877,14 +1052,14 @@ class AssemblerTest : public AssemblerTestBase { for (uint64_t i = MinInt<uint64_t>(kMaxBitsExhaustiveTest); i <= MaxInt<uint64_t>(kMaxBitsExhaustiveTest); i++) { - res.push_back(static_cast<int64_t>(i)); + res.push_back(static_cast<int64_t>(i << shift)); } for (int i = 0; i <= imm_bits; i++) { uint64_t j = (MaxInt<uint64_t>(kMaxBitsExhaustiveTest) + 1) + ((MaxInt<uint64_t>(imm_bits) - (MaxInt<uint64_t>(kMaxBitsExhaustiveTest) + 1)) * i / imm_bits); - res.push_back(static_cast<int64_t>(j)); + res.push_back(static_cast<int64_t>(j << shift)); } } else { for (int i = 0; i <= imm_bits; i++) { @@ -892,18 +1067,18 @@ class AssemblerTest : public AssemblerTestBase { ((((MinInt<int64_t>(kMaxBitsExhaustiveTest) - 1) - MinInt<int64_t>(imm_bits)) * i) / imm_bits); - res.push_back(static_cast<int64_t>(j)); + res.push_back(static_cast<int64_t>(j << shift)); } for (int64_t i = MinInt<int64_t>(kMaxBitsExhaustiveTest); i <= MaxInt<int64_t>(kMaxBitsExhaustiveTest); i++) { - res.push_back(static_cast<int64_t>(i)); + res.push_back(static_cast<int64_t>(i << shift)); } for (int i = 0; i <= imm_bits; i++) { int64_t j = (MaxInt<int64_t>(kMaxBitsExhaustiveTest) + 1) + ((MaxInt<int64_t>(imm_bits) - (MaxInt<int64_t>(kMaxBitsExhaustiveTest) + 1)) * i / imm_bits); - res.push_back(static_cast<int64_t>(j)); + res.push_back(static_cast<int64_t>(j << shift)); } } } |