tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

non_temporal_memcpy_test.cc (3032B)


      1 // Copyright 2022 The Abseil Authors
      2 //
      3 // Licensed under the Apache License, Version 2.0 (the "License");
      4 // you may not use this file except in compliance with the License.
      5 // You may obtain a copy of the License at
      6 //
      7 //     https://www.apache.org/licenses/LICENSE-2.0
      8 //
      9 // Unless required by applicable law or agreed to in writing, software
     10 // distributed under the License is distributed on an "AS IS" BASIS,
     11 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     12 // See the License for the specific language governing permissions and
     13 // limitations under the License.
     14 
     15 #include "absl/crc/internal/non_temporal_memcpy.h"
     16 
     17 #include <algorithm>
     18 #include <cstdint>
     19 #include <iostream>
     20 #include <vector>
     21 
     22 #include "gtest/gtest.h"
     23 
     24 namespace {
     25 
     26 struct TestParam {
     27  size_t copy_size;
     28  uint32_t src_offset;
     29  uint32_t dst_offset;
     30 };
     31 
     32 class NonTemporalMemcpyTest : public testing::TestWithParam<TestParam> {
     33 protected:
     34  void SetUp() override {
     35    // Make buf_size multiple of 16 bytes.
     36    size_t buf_size = ((std::max(GetParam().src_offset, GetParam().dst_offset) +
     37                        GetParam().copy_size) +
     38                       15) /
     39                      16 * 16;
     40    a_.resize(buf_size);
     41    b_.resize(buf_size);
     42    for (size_t i = 0; i < buf_size; i++) {
     43      a_[i] = static_cast<uint8_t>(i % 256);
     44      b_[i] = ~a_[i];
     45    }
     46  }
     47 
     48  std::vector<uint8_t> a_, b_;
     49 };
     50 
     51 TEST_P(NonTemporalMemcpyTest, SSEEquality) {
     52  uint8_t *src = a_.data() + GetParam().src_offset;
     53  uint8_t *dst = b_.data() + GetParam().dst_offset;
     54  absl::crc_internal::non_temporal_store_memcpy(dst, src, GetParam().copy_size);
     55  for (size_t i = 0; i < GetParam().copy_size; i++) {
     56    EXPECT_EQ(src[i], dst[i]);
     57  }
     58 }
     59 
     60 #ifdef __AVX__
     61 TEST_P(NonTemporalMemcpyTest, AVXEquality) {
     62  uint8_t* src = a_.data() + GetParam().src_offset;
     63  uint8_t* dst = b_.data() + GetParam().dst_offset;
     64 
     65  absl::crc_internal::non_temporal_store_memcpy_avx(dst, src,
     66                                                    GetParam().copy_size);
     67  for (size_t i = 0; i < GetParam().copy_size; i++) {
     68    EXPECT_EQ(src[i], dst[i]);
     69  }
     70 }
     71 #endif
     72 
     73 // 63B is smaller than one cacheline operation thus the non-temporal routine
     74 // will not be called.
     75 // 4352B is sufficient for testing 4092B data copy with room for offsets.
     76 constexpr TestParam params[] = {
     77    {63, 0, 0},       {58, 5, 5},    {61, 2, 0},    {61, 0, 2},
     78    {58, 5, 2},       {4096, 0, 0},  {4096, 0, 1},  {4096, 0, 2},
     79    {4096, 0, 3},     {4096, 0, 4},  {4096, 0, 5},  {4096, 0, 6},
     80    {4096, 0, 7},     {4096, 0, 8},  {4096, 0, 9},  {4096, 0, 10},
     81    {4096, 0, 11},    {4096, 0, 12}, {4096, 0, 13}, {4096, 0, 14},
     82    {4096, 0, 15},    {4096, 7, 7},  {4096, 3, 0},  {4096, 1, 0},
     83    {4096, 9, 3},     {4096, 9, 11}, {8192, 0, 0},  {8192, 5, 2},
     84    {1024768, 7, 11}, {1, 0, 0},     {1, 0, 1},     {1, 1, 0},
     85    {1, 1, 1}};
     86 
     87 INSTANTIATE_TEST_SUITE_P(ParameterizedNonTemporalMemcpyTest,
     88                         NonTemporalMemcpyTest, testing::ValuesIn(params));
     89 
     90 }  // namespace