#include "catch2/catch.hpp" #include "../sources/SIMDHelpers.h" #include #include using namespace Catch::literals; constexpr int smallBufferSize { 3 }; constexpr int bigBufferSize { 4095 }; constexpr int medBufferSize { 127 }; constexpr double fillValue { 1.3 }; TEST_CASE("[Helpers] fill() - Manual buffer") { std::vector buffer (5); std::vector expected { fillValue, fillValue, fillValue, fillValue, fillValue }; fill(absl::MakeSpan(buffer), fillValue); REQUIRE(buffer == expected); } TEST_CASE("[Helpers] fill() - Small buffer") { std::vector buffer (smallBufferSize); std::vector expected (smallBufferSize); std::fill(expected.begin(), expected.end(), fillValue); fill(absl::MakeSpan(buffer), fillValue); REQUIRE(buffer == expected); } TEST_CASE("[Helpers] fill() - Big buffer") { std::vector buffer (bigBufferSize); std::vector expected (bigBufferSize); std::fill(expected.begin(), expected.end(), fillValue); fill(absl::MakeSpan(buffer), fillValue); REQUIRE(buffer == expected); } TEST_CASE("[Helpers] fill() - Small buffer -- SIMD") { std::vector buffer (smallBufferSize); std::vector expected (smallBufferSize); std::fill(expected.begin(), expected.end(), fillValue); fill(absl::MakeSpan(buffer), fillValue); REQUIRE(buffer == expected); } TEST_CASE("[Helpers] fill() - Big buffer -- SIMD") { std::vector buffer (bigBufferSize); std::vector expected (bigBufferSize); std::fill(expected.begin(), expected.end(), fillValue); fill(absl::MakeSpan(buffer), fillValue); REQUIRE(buffer == expected); } TEST_CASE("[Helpers] fill() - Small buffer -- doubles") { std::vector buffer (smallBufferSize); std::vector expected (smallBufferSize); std::fill(expected.begin(), expected.end(), fillValue); fill(absl::MakeSpan(buffer), fillValue); REQUIRE(buffer == expected); } TEST_CASE("[Helpers] fill() - Big buffer -- doubles") { std::vector buffer (bigBufferSize); std::vector expected (bigBufferSize); std::fill(expected.begin(), expected.end(), fillValue); fill(absl::MakeSpan(buffer), fillValue); REQUIRE(buffer == expected); } TEST_CASE("[Helpers] Interleaved read") { std::array input { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f, 3.0f, 13.0f, 4.0f, 14.0f, 5.0f, 15.0f, 6.0f, 16.0f, 7.0f, 17.0f}; std::array expected { 0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f, 6.0f, 7.0f, 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f, 16.0f, 17.0f }; std::array leftOutput; std::array rightOutput; readInterleaved(input, absl::MakeSpan(leftOutput), absl::MakeSpan(rightOutput)); std::array real; auto realIdx = 0; for (auto value: leftOutput) real[realIdx++] = value; for (auto value: rightOutput) real[realIdx++] = value; REQUIRE( real == expected ); } TEST_CASE("[Helpers] Interleaved read unaligned end") { std::array input { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f, 3.0f, 13.0f, 4.0f, 14.0f, 5.0f, 15.0f, 6.0f, 16.0f, 7.0f, 17.0f, 8.0f, 18.0f, 9.0f, 19.0f}; std::array expected { 0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f, 6.0f, 7.0f, 8.0f, 9.0f, 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f, 16.0f, 17.0f, 18.0f, 19.0f}; std::array leftOutput; std::array rightOutput; readInterleaved(input, absl::MakeSpan(leftOutput), absl::MakeSpan(rightOutput)); std::array real; auto realIdx = 0; for (auto value: leftOutput) real[realIdx++] = value; for (auto value: rightOutput) real[realIdx++] = value; REQUIRE( real == expected ); } TEST_CASE("[Helpers] Small interleaved read unaligned end") { std::array input { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f}; std::array expected { 0.0f, 1.0f, 2.0f, 10.0f, 11.0f, 12.0f}; std::array leftOutput; std::array rightOutput; readInterleaved(input, absl::MakeSpan(leftOutput), absl::MakeSpan(rightOutput)); std::array real; auto realIdx = 0; for (auto value: leftOutput) real[realIdx++] = value; for (auto value: rightOutput) real[realIdx++] = value; REQUIRE( real == expected ); } TEST_CASE("[Helpers] Interleaved read -- SIMD") { std::array input = { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f, 3.0f, 13.0f, 4.0f, 14.0f, 5.0f, 15.0f, 6.0f, 16.0f, 7.0f, 17.0f}; std::array expected = { 0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f, 6.0f, 7.0f, 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f, 16.0f, 17.0f }; std::array leftOutput; std::array rightOutput; readInterleaved(input, absl::MakeSpan(leftOutput), absl::MakeSpan(rightOutput)); std::array real; auto realIdx = 0; for (auto value: leftOutput) real[realIdx++] = value; for (auto value: rightOutput) real[realIdx++] = value; REQUIRE( real == expected ); } TEST_CASE("[Helpers] Interleaved read unaligned end -- SIMD") { std::array input = { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f, 3.0f, 13.0f, 4.0f, 14.0f, 5.0f, 15.0f, 6.0f, 16.0f, 7.0f, 17.0f, 8.0f, 18.0f, 9.0f, 19.0f}; std::array expected = { 0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f, 6.0f, 7.0f, 8.0f, 9.0f, 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f, 16.0f, 17.0f, 18.0f, 19.0f}; std::array leftOutput; std::array rightOutput; readInterleaved(input, absl::MakeSpan(leftOutput), absl::MakeSpan(rightOutput)); std::array real; auto realIdx = 0; for (auto value: leftOutput) real[realIdx++] = value; for (auto value: rightOutput) real[realIdx++] = value; REQUIRE( real == expected ); } TEST_CASE("[Helpers] Small interleaved read unaligned end -- SIMD") { std::array input { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f}; std::array expected { 0.0f, 1.0f, 2.0f, 10.0f, 11.0f, 12.0f}; std::array leftOutput; std::array rightOutput; readInterleaved(input, absl::MakeSpan(leftOutput), absl::MakeSpan(rightOutput)); std::array real; auto realIdx = 0; for (auto value: leftOutput) real[realIdx++] = value; for (auto value: rightOutput) real[realIdx++] = value; REQUIRE( real == expected ); } TEST_CASE("[Helpers] Interleaved read SIMD vs Scalar") { std::array input; std::array leftOutputScalar; std::array rightOutputScalar; std::array leftOutputSIMD; std::array rightOutputSIMD; std::iota(input.begin(), input.end(), 0.0f); readInterleaved(input, absl::MakeSpan(leftOutputScalar), absl::MakeSpan(rightOutputScalar)); readInterleaved(input, absl::MakeSpan(leftOutputSIMD), absl::MakeSpan(rightOutputSIMD)); REQUIRE( leftOutputScalar == leftOutputSIMD ); REQUIRE( rightOutputScalar == rightOutputSIMD ); } TEST_CASE("[Helpers] Interleaved write") { std::array leftInput { 0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f, 6.0f, 7.0f, }; std::array rightInput { 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f, 16.0f, 17.0f }; std::array output; std::array expected { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f, 3.0f, 13.0f, 4.0f, 14.0f, 5.0f, 15.0f, 6.0f, 16.0f, 7.0f, 17.0f}; writeInterleaved(leftInput, rightInput, absl::MakeSpan(output)); REQUIRE( output == expected ); } TEST_CASE("[Helpers] Interleaved write unaligned end") { std::array leftInput { 0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f, 6.0f, 7.0f, 8.0f, 9.0f}; std::array rightInput { 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f, 16.0f, 17.0f, 18.0f, 19.0f }; std::array output; std::array expected { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f, 3.0f, 13.0f, 4.0f, 14.0f, 5.0f, 15.0f, 6.0f, 16.0f, 7.0f, 17.0f, 8.0f, 18.0f, 9.0f, 19.0f}; writeInterleaved(leftInput, rightInput, absl::MakeSpan(output)); REQUIRE( output == expected ); } TEST_CASE("[Helpers] Small interleaved write unaligned end") { std::array leftInput { 0.0f, 1.0f, 2.0f}; std::array rightInput { 10.0f, 11.0f, 12.0f }; std::array output; std::array expected { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f}; writeInterleaved(leftInput, rightInput, absl::MakeSpan(output)); REQUIRE( output == expected ); } TEST_CASE("[Helpers] Interleaved write -- SIMD") { std::array leftInput { 0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f, 6.0f, 7.0f, }; std::array rightInput { 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f, 16.0f, 17.0f }; std::array output; std::array expected { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f, 3.0f, 13.0f, 4.0f, 14.0f, 5.0f, 15.0f, 6.0f, 16.0f, 7.0f, 17.0f}; writeInterleaved(leftInput, rightInput, absl::MakeSpan(output)); REQUIRE( output == expected ); } TEST_CASE("[Helpers] Interleaved write unaligned end -- SIMD") { std::array leftInput { 0.0f, 1.0f, 2.0f, 3.0f, 4.0f, 5.0f, 6.0f, 7.0f, 8.0f, 9.0f}; std::array rightInput { 10.0f, 11.0f, 12.0f, 13.0f, 14.0f, 15.0f, 16.0f, 17.0f, 18.0f, 19.0f }; std::array output; std::array expected = { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f, 3.0f, 13.0f, 4.0f, 14.0f, 5.0f, 15.0f, 6.0f, 16.0f, 7.0f, 17.0f, 8.0f, 18.0f, 9.0f, 19.0f}; writeInterleaved(leftInput, rightInput, absl::MakeSpan(output)); REQUIRE( output == expected ); } TEST_CASE("[Helpers] Small interleaved write unaligned end -- SIMD") { std::array leftInput { 0.0f, 1.0f, 2.0f}; std::array rightInput { 10.0f, 11.0f, 12.0f }; std::array output; std::array expected { 0.0f, 10.0f, 1.0f, 11.0f, 2.0f, 12.0f}; writeInterleaved(leftInput, rightInput, absl::MakeSpan(output)); REQUIRE( output == expected ); } TEST_CASE("[Helpers] Interleaved write SIMD vs Scalar") { std::array leftInput; std::array rightInput; std::array outputScalar; std::array outputSIMD; std::iota(leftInput.begin(), leftInput.end(), 0.0f); std::iota(rightInput.begin(), rightInput.end(), medBufferSize); writeInterleaved(leftInput, rightInput, absl::MakeSpan(outputScalar)); writeInterleaved(leftInput, rightInput, absl::MakeSpan(outputSIMD)); REQUIRE( outputScalar == outputSIMD ); } TEST_CASE("[Helpers] Gain, single") { std::array input { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f }; std::array output { 0.0f, 0.0f, 0.0f, 0.0f, 0.0f }; std::array expected { fillValue, fillValue, fillValue, fillValue, fillValue }; applyGain(fillValue, input, absl::MakeSpan(output)); REQUIRE( output == expected ); } TEST_CASE("[Helpers] Gain, single and inplace") { std::array buffer { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f }; std::array expected { fillValue, fillValue, fillValue, fillValue, fillValue }; applyGain(fillValue, buffer, absl::MakeSpan(buffer)); REQUIRE( buffer == expected ); } TEST_CASE("[Helpers] Gain, spans") { std::array input { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f }; std::array gain { 1.0f, 2.0f, 3.0f, 4.0f, 5.0f }; std::array output { 0.0f, 0.0f, 0.0f, 0.0f, 0.0f }; std::array expected { 1.0f, 2.0f, 3.0f, 4.0f, 5.0f }; applyGain(gain, input, absl::MakeSpan(output)); REQUIRE( output == expected ); } TEST_CASE("[Helpers] Gain, spans and inplace") { std::array buffer { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f }; std::array gain { 1.0f, 2.0f, 3.0f, 4.0f, 5.0f }; std::array expected { 1.0f, 2.0f, 3.0f, 4.0f, 5.0f }; applyGain(gain, buffer, absl::MakeSpan(buffer)); REQUIRE( buffer == expected ); } TEST_CASE("[Helpers] Gain, single (SIMD)") { std::array input { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f }; std::array output { 0.0f, 0.0f, 0.0f, 0.0f, 0.0f }; std::array expected { fillValue, fillValue, fillValue, fillValue, fillValue }; applyGain(fillValue, input, absl::MakeSpan(output)); REQUIRE( output == expected ); } TEST_CASE("[Helpers] Gain, single and inplace (SIMD)") { std::array buffer { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f }; std::array expected { fillValue, fillValue, fillValue, fillValue, fillValue }; applyGain(fillValue, buffer, absl::MakeSpan(buffer)); REQUIRE( buffer == expected ); } TEST_CASE("[Helpers] Gain, spans (SIMD)") { std::array input { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f }; std::array gain { 1.0f, 2.0f, 3.0f, 4.0f, 5.0f }; std::array output { 0.0f, 0.0f, 0.0f, 0.0f, 0.0f }; std::array expected { 1.0f, 2.0f, 3.0f, 4.0f, 5.0f }; applyGain(gain, input, absl::MakeSpan(output)); REQUIRE( output == expected ); } TEST_CASE("[Helpers] Gain, spans and inplace (SIMD)") { std::array buffer { 1.0f, 1.0f, 1.0f, 1.0f, 1.0f }; std::array gain { 1.0f, 2.0f, 3.0f, 4.0f, 5.0f }; std::array expected { 1.0f, 2.0f, 3.0f, 4.0f, 5.0f }; applyGain(gain, buffer, absl::MakeSpan(buffer)); REQUIRE( buffer == expected ); }