diff options
author | mmc28a <78873583+mmc28a@users.noreply.github.com> | 2024-05-16 15:27:20 +0100 |
---|---|---|
committer | GitHub <noreply@github.com> | 2024-05-16 15:27:20 +0100 |
commit | 2cdba9ed4a1ee6872e513768311cc03ad68b315c (patch) | |
tree | c25f8813720bc573d8f9b9827a8df6456c7c6b0c | |
parent | 3134e2560de12dfebbd72ef4868b2a5c5d7b5da9 (diff) | |
download | vixl-upstream-main.tar.gz |
Fix zeroing part of SVE register for Neon INS (#95)upstream-main
The INS instruction inserts an element into an existing 128-bit vector, but for
systems with larger SVE registers, bits beyond the end of the vector must be
zeroed. Fix this and add a regression test.
-rw-r--r-- | src/aarch64/simulator-aarch64.cc | 2 | ||||
-rw-r--r-- | test/aarch64/test-assembler-sve-aarch64.cc | 20 | ||||
-rw-r--r-- | tools/code_coverage.log | 3 |
3 files changed, 24 insertions, 1 deletions
diff --git a/src/aarch64/simulator-aarch64.cc b/src/aarch64/simulator-aarch64.cc index 3624f257..52a9cb8b 100644 --- a/src/aarch64/simulator-aarch64.cc +++ b/src/aarch64/simulator-aarch64.cc @@ -8320,8 +8320,10 @@ void Simulator::VisitNEONCopy(const Instruction* instr) { if (instr->Mask(NEONCopyInsElementMask) == NEON_INS_ELEMENT) { int imm4 = instr->GetImmNEON4(); int rn_index = ExtractSignedBitfield32(31, tz, imm4); + mov(kFormat16B, rd, rd); // Zero bits beyond the MSB of a Q register. ins_element(vf, rd, reg_index, rn, rn_index); } else if (instr->Mask(NEONCopyInsGeneralMask) == NEON_INS_GENERAL) { + mov(kFormat16B, rd, rd); // Zero bits beyond the MSB of a Q register. ins_immediate(vf, rd, reg_index, ReadXRegister(instr->GetRn())); } else if (instr->Mask(NEONCopyUmovMask) == NEON_UMOV) { uint64_t value = LogicVRegister(rn).Uint(vf, reg_index); diff --git a/test/aarch64/test-assembler-sve-aarch64.cc b/test/aarch64/test-assembler-sve-aarch64.cc index f16ab336..fdbcdf99 100644 --- a/test/aarch64/test-assembler-sve-aarch64.cc +++ b/test/aarch64/test-assembler-sve-aarch64.cc @@ -19729,6 +19729,26 @@ TEST_SVE(sudot_usdot) { } } +TEST_SVE(neon_ins_zero_high_regression_test) { + SVE_SETUP_WITH_FEATURES(CPUFeatures::kNEON, CPUFeatures::kSVE); + + START(); + __ Movi(v0.V2D(), 0x0f0e0d0c0b0a0908, 0x0706050403020100); + + // Check that both forms of ins zero bits <VL-1:128> + __ Index(z1.VnB(), 0, 1); + __ Ins(v1.V16B(), 0, wzr); + __ Index(z2.VnB(), 0, 1); + __ Ins(v2.V16B(), 3, v2.V16B(), 3); + END(); + + if (CAN_RUN()) { + RUN(); + ASSERT_EQUAL_SVE(z0, z1); + ASSERT_EQUAL_SVE(z0, z2); + } +} + TEST_SVE(sve_load_store_sp_base_regression_test) { SVE_SETUP_WITH_FEATURES(CPUFeatures::kSVE); START(); diff --git a/tools/code_coverage.log b/tools/code_coverage.log index 3f459e44..0a5969b3 100644 --- a/tools/code_coverage.log +++ b/tools/code_coverage.log @@ -22,4 +22,5 @@ 1693487542 82.91% 97.57% 94.87% 1702052331 82.89% 97.59% 94.77% 1706691191 82.87% 97.59% 94.74% -1707395574 82.89% 97.59% 94.77%
\ No newline at end of file +1707395574 82.89% 97.59% 94.77% +1715261843 82.84% 97.60% 94.69% |