Coverage Report

Created: 2026-10-28 08:13

next uncovered line (L), next uncovered region (R), next uncovered branch (B)
/src/libvpx/vpx_dsp/x86/highbd_sad4d_avx2.c
Line
Count
Source
1
/*
2
 *  Copyright (c) 2022 The WebM project authors. All Rights Reserved.
3
 *
4
 *  Use of this source code is governed by a BSD-style license
5
 *  that can be found in the LICENSE file in the root of the source
6
 *  tree. An additional intellectual property rights grant can be found
7
 *  in the file PATENTS.  All contributing project authors may
8
 *  be found in the AUTHORS file in the root of the source tree.
9
 */
10
#include <immintrin.h>  // AVX2
11
#include "./vpx_dsp_rtcd.h"
12
#include "vpx/vpx_integer.h"
13
14
static VPX_FORCE_INLINE void calc_final_4(const __m256i *const sums /*[4]*/,
15
595k
                                          uint32_t sad_array[4]) {
16
595k
  const __m256i t0 = _mm256_hadd_epi32(sums[0], sums[1]);
17
595k
  const __m256i t1 = _mm256_hadd_epi32(sums[2], sums[3]);
18
595k
  const __m256i t2 = _mm256_hadd_epi32(t0, t1);
19
595k
  const __m128i sum = _mm_add_epi32(_mm256_castsi256_si128(t2),
20
595k
                                    _mm256_extractf128_si256(t2, 1));
21
595k
  _mm_storeu_si128((__m128i *)sad_array, sum);
22
595k
}
23
24
static VPX_FORCE_INLINE void highbd_sad64xHx4d(__m256i *sums_16 /*[4]*/,
25
                                               const uint16_t *src,
26
                                               int src_stride,
27
                                               uint16_t *refs[4],
28
2.53M
                                               int ref_stride, int height) {
29
2.53M
  int i;
30
7.61M
  for (i = 0; i < height; ++i) {
31
    // load src and all ref[]
32
5.07M
    const __m256i s0 = _mm256_load_si256((const __m256i *)src);
33
5.07M
    const __m256i s1 = _mm256_load_si256((const __m256i *)(src + 16));
34
5.07M
    const __m256i s2 = _mm256_load_si256((const __m256i *)(src + 32));
35
5.07M
    const __m256i s3 = _mm256_load_si256((const __m256i *)(src + 48));
36
5.07M
    int x;
37
38
25.3M
    for (x = 0; x < 4; ++x) {
39
20.3M
      __m256i r[4];
40
20.3M
      r[0] = _mm256_loadu_si256((const __m256i *)refs[x]);
41
20.3M
      r[1] = _mm256_loadu_si256((const __m256i *)(refs[x] + 16));
42
20.3M
      r[2] = _mm256_loadu_si256((const __m256i *)(refs[x] + 32));
43
20.3M
      r[3] = _mm256_loadu_si256((const __m256i *)(refs[x] + 48));
44
45
      // absolute differences between every ref[] to src
46
20.3M
      r[0] = _mm256_abs_epi16(_mm256_sub_epi16(r[0], s0));
47
20.3M
      r[1] = _mm256_abs_epi16(_mm256_sub_epi16(r[1], s1));
48
20.3M
      r[2] = _mm256_abs_epi16(_mm256_sub_epi16(r[2], s2));
49
20.3M
      r[3] = _mm256_abs_epi16(_mm256_sub_epi16(r[3], s3));
50
51
      // sum every abs diff
52
20.3M
      sums_16[x] = _mm256_add_epi16(sums_16[x], _mm256_add_epi16(r[0], r[1]));
53
20.3M
      sums_16[x] = _mm256_add_epi16(sums_16[x], _mm256_add_epi16(r[2], r[3]));
54
20.3M
    }
55
56
5.07M
    src += src_stride;
57
5.07M
    refs[0] += ref_stride;
58
5.07M
    refs[1] += ref_stride;
59
5.07M
    refs[2] += ref_stride;
60
5.07M
    refs[3] += ref_stride;
61
5.07M
  }
62
2.53M
}
63
64
static VPX_FORCE_INLINE void highbd_sad64xNx4d_avx2(
65
    const uint8_t *src_ptr, int src_stride, const uint8_t *const ref_array[4],
66
104k
    int ref_stride, uint32_t sad_array[4], int n) {
67
104k
  const uint16_t *src = CONVERT_TO_SHORTPTR(src_ptr);
68
104k
  uint16_t *refs[4];
69
104k
  __m256i sums_16[4];
70
104k
  __m256i sums_32[4];
71
104k
  int i;
72
73
104k
  refs[0] = CONVERT_TO_SHORTPTR(ref_array[0]);
74
104k
  refs[1] = CONVERT_TO_SHORTPTR(ref_array[1]);
75
104k
  refs[2] = CONVERT_TO_SHORTPTR(ref_array[2]);
76
104k
  refs[3] = CONVERT_TO_SHORTPTR(ref_array[3]);
77
104k
  sums_32[0] = _mm256_setzero_si256();
78
104k
  sums_32[1] = _mm256_setzero_si256();
79
104k
  sums_32[2] = _mm256_setzero_si256();
80
104k
  sums_32[3] = _mm256_setzero_si256();
81
82
2.64M
  for (i = 0; i < (n / 2); ++i) {
83
2.53M
    sums_16[0] = _mm256_setzero_si256();
84
2.53M
    sums_16[1] = _mm256_setzero_si256();
85
2.53M
    sums_16[2] = _mm256_setzero_si256();
86
2.53M
    sums_16[3] = _mm256_setzero_si256();
87
88
2.53M
    highbd_sad64xHx4d(sums_16, src, src_stride, refs, ref_stride, 2);
89
90
    /* sums_16 will outrange after 2 rows, so add current sums_16 to
91
     * sums_32*/
92
2.53M
    sums_32[0] = _mm256_add_epi32(
93
2.53M
        sums_32[0],
94
2.53M
        _mm256_add_epi32(
95
2.53M
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[0])),
96
2.53M
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[0], 1))));
97
2.53M
    sums_32[1] = _mm256_add_epi32(
98
2.53M
        sums_32[1],
99
2.53M
        _mm256_add_epi32(
100
2.53M
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[1])),
101
2.53M
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[1], 1))));
102
2.53M
    sums_32[2] = _mm256_add_epi32(
103
2.53M
        sums_32[2],
104
2.53M
        _mm256_add_epi32(
105
2.53M
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[2])),
106
2.53M
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[2], 1))));
107
2.53M
    sums_32[3] = _mm256_add_epi32(
108
2.53M
        sums_32[3],
109
2.53M
        _mm256_add_epi32(
110
2.53M
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[3])),
111
2.53M
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[3], 1))));
112
113
2.53M
    src += src_stride << 1;
114
2.53M
  }
115
104k
  calc_final_4(sums_32, sad_array);
116
104k
}
117
118
#define HIGHBD_SAD64XNX4D(n)                                                   \
119
  void vpx_highbd_sad64x##n##x4d_avx2(const uint8_t *src, int src_stride,      \
120
                                      const uint8_t *const ref_array[4],       \
121
77.1k
                                      int ref_stride, uint32_t sad_array[4]) { \
122
77.1k
    highbd_sad64xNx4d_avx2(src, src_stride, ref_array, ref_stride, sad_array,  \
123
77.1k
                           n);                                                 \
124
77.1k
  }
vpx_highbd_sad64x64x4d_avx2
Line
Count
Source
121
54.8k
                                      int ref_stride, uint32_t sad_array[4]) { \
122
54.8k
    highbd_sad64xNx4d_avx2(src, src_stride, ref_array, ref_stride, sad_array,  \
123
54.8k
                           n);                                                 \
124
54.8k
  }
vpx_highbd_sad64x32x4d_avx2
Line
Count
Source
121
22.3k
                                      int ref_stride, uint32_t sad_array[4]) { \
122
22.3k
    highbd_sad64xNx4d_avx2(src, src_stride, ref_array, ref_stride, sad_array,  \
123
22.3k
                           n);                                                 \
124
22.3k
  }
125
126
#define HIGHBD_SADSKIP64XNx4D(n)                                             \
127
  void vpx_highbd_sad_skip_64x##n##x4d_avx2(                                 \
128
      const uint8_t *src, int src_stride, const uint8_t *const ref_array[4], \
129
26.9k
      int ref_stride, uint32_t sad_array[4]) {                               \
130
26.9k
    highbd_sad64xNx4d_avx2(src, 2 * src_stride, ref_array, 2 * ref_stride,   \
131
26.9k
                           sad_array, n / 2);                                \
132
26.9k
    sad_array[0] <<= 1;                                                      \
133
26.9k
    sad_array[1] <<= 1;                                                      \
134
26.9k
    sad_array[2] <<= 1;                                                      \
135
26.9k
    sad_array[3] <<= 1;                                                      \
136
26.9k
  }
vpx_highbd_sad_skip_64x64x4d_avx2
Line
Count
Source
129
26.2k
      int ref_stride, uint32_t sad_array[4]) {                               \
130
26.2k
    highbd_sad64xNx4d_avx2(src, 2 * src_stride, ref_array, 2 * ref_stride,   \
131
26.2k
                           sad_array, n / 2);                                \
132
26.2k
    sad_array[0] <<= 1;                                                      \
133
26.2k
    sad_array[1] <<= 1;                                                      \
134
26.2k
    sad_array[2] <<= 1;                                                      \
135
26.2k
    sad_array[3] <<= 1;                                                      \
136
26.2k
  }
vpx_highbd_sad_skip_64x32x4d_avx2
Line
Count
Source
129
681
      int ref_stride, uint32_t sad_array[4]) {                               \
130
681
    highbd_sad64xNx4d_avx2(src, 2 * src_stride, ref_array, 2 * ref_stride,   \
131
681
                           sad_array, n / 2);                                \
132
681
    sad_array[0] <<= 1;                                                      \
133
681
    sad_array[1] <<= 1;                                                      \
134
681
    sad_array[2] <<= 1;                                                      \
135
681
    sad_array[3] <<= 1;                                                      \
136
681
  }
137
138
static VPX_FORCE_INLINE void highbd_sad32xHx4d(__m256i *sums_16 /*[4]*/,
139
                                               const uint16_t *src,
140
                                               int src_stride,
141
                                               uint16_t *refs[4],
142
622k
                                               int ref_stride, int height) {
143
622k
  int i;
144
5.60M
  for (i = 0; i < height; i++) {
145
4.98M
    __m256i r[8];
146
147
    // load src and all ref[]
148
4.98M
    const __m256i s = _mm256_load_si256((const __m256i *)src);
149
4.98M
    const __m256i s2 = _mm256_load_si256((const __m256i *)(src + 16));
150
4.98M
    r[0] = _mm256_loadu_si256((const __m256i *)refs[0]);
151
4.98M
    r[1] = _mm256_loadu_si256((const __m256i *)(refs[0] + 16));
152
4.98M
    r[2] = _mm256_loadu_si256((const __m256i *)refs[1]);
153
4.98M
    r[3] = _mm256_loadu_si256((const __m256i *)(refs[1] + 16));
154
4.98M
    r[4] = _mm256_loadu_si256((const __m256i *)refs[2]);
155
4.98M
    r[5] = _mm256_loadu_si256((const __m256i *)(refs[2] + 16));
156
4.98M
    r[6] = _mm256_loadu_si256((const __m256i *)refs[3]);
157
4.98M
    r[7] = _mm256_loadu_si256((const __m256i *)(refs[3] + 16));
158
159
    // absolute differences between every ref[] to src
160
4.98M
    r[0] = _mm256_abs_epi16(_mm256_sub_epi16(r[0], s));
161
4.98M
    r[1] = _mm256_abs_epi16(_mm256_sub_epi16(r[1], s2));
162
4.98M
    r[2] = _mm256_abs_epi16(_mm256_sub_epi16(r[2], s));
163
4.98M
    r[3] = _mm256_abs_epi16(_mm256_sub_epi16(r[3], s2));
164
4.98M
    r[4] = _mm256_abs_epi16(_mm256_sub_epi16(r[4], s));
165
4.98M
    r[5] = _mm256_abs_epi16(_mm256_sub_epi16(r[5], s2));
166
4.98M
    r[6] = _mm256_abs_epi16(_mm256_sub_epi16(r[6], s));
167
4.98M
    r[7] = _mm256_abs_epi16(_mm256_sub_epi16(r[7], s2));
168
169
    // sum every abs diff
170
4.98M
    sums_16[0] = _mm256_add_epi16(sums_16[0], _mm256_add_epi16(r[0], r[1]));
171
4.98M
    sums_16[1] = _mm256_add_epi16(sums_16[1], _mm256_add_epi16(r[2], r[3]));
172
4.98M
    sums_16[2] = _mm256_add_epi16(sums_16[2], _mm256_add_epi16(r[4], r[5]));
173
4.98M
    sums_16[3] = _mm256_add_epi16(sums_16[3], _mm256_add_epi16(r[6], r[7]));
174
175
4.98M
    src += src_stride;
176
4.98M
    refs[0] += ref_stride;
177
4.98M
    refs[1] += ref_stride;
178
4.98M
    refs[2] += ref_stride;
179
4.98M
    refs[3] += ref_stride;
180
4.98M
  }
181
622k
}
182
183
static VPX_FORCE_INLINE void highbd_sad32xNx4d_avx2(
184
    const uint8_t *src_ptr, int src_stride, const uint8_t *const ref_array[4],
185
179k
    int ref_stride, uint32_t sad_array[4], int n) {
186
179k
  const uint16_t *src = CONVERT_TO_SHORTPTR(src_ptr);
187
179k
  uint16_t *refs[4];
188
179k
  __m256i sums_16[4];
189
179k
  __m256i sums_32[4];
190
179k
  int i;
191
192
179k
  refs[0] = CONVERT_TO_SHORTPTR(ref_array[0]);
193
179k
  refs[1] = CONVERT_TO_SHORTPTR(ref_array[1]);
194
179k
  refs[2] = CONVERT_TO_SHORTPTR(ref_array[2]);
195
179k
  refs[3] = CONVERT_TO_SHORTPTR(ref_array[3]);
196
179k
  sums_32[0] = _mm256_setzero_si256();
197
179k
  sums_32[1] = _mm256_setzero_si256();
198
179k
  sums_32[2] = _mm256_setzero_si256();
199
179k
  sums_32[3] = _mm256_setzero_si256();
200
201
802k
  for (i = 0; i < (n / 8); ++i) {
202
622k
    sums_16[0] = _mm256_setzero_si256();
203
622k
    sums_16[1] = _mm256_setzero_si256();
204
622k
    sums_16[2] = _mm256_setzero_si256();
205
622k
    sums_16[3] = _mm256_setzero_si256();
206
207
622k
    highbd_sad32xHx4d(sums_16, src, src_stride, refs, ref_stride, 8);
208
209
    /* sums_16 will outrange after 8 rows, so add current sums_16 to
210
     * sums_32*/
211
622k
    sums_32[0] = _mm256_add_epi32(
212
622k
        sums_32[0],
213
622k
        _mm256_add_epi32(
214
622k
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[0])),
215
622k
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[0], 1))));
216
622k
    sums_32[1] = _mm256_add_epi32(
217
622k
        sums_32[1],
218
622k
        _mm256_add_epi32(
219
622k
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[1])),
220
622k
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[1], 1))));
221
622k
    sums_32[2] = _mm256_add_epi32(
222
622k
        sums_32[2],
223
622k
        _mm256_add_epi32(
224
622k
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[2])),
225
622k
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[2], 1))));
226
622k
    sums_32[3] = _mm256_add_epi32(
227
622k
        sums_32[3],
228
622k
        _mm256_add_epi32(
229
622k
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[3])),
230
622k
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[3], 1))));
231
232
622k
    src += src_stride << 3;
233
622k
  }
234
179k
  calc_final_4(sums_32, sad_array);
235
179k
}
236
237
#define HIGHBD_SAD32XNX4D(n)                                                   \
238
  void vpx_highbd_sad32x##n##x4d_avx2(const uint8_t *src, int src_stride,      \
239
                                      const uint8_t *const ref_array[4],       \
240
130k
                                      int ref_stride, uint32_t sad_array[4]) { \
241
130k
    highbd_sad32xNx4d_avx2(src, src_stride, ref_array, ref_stride, sad_array,  \
242
130k
                           n);                                                 \
243
130k
  }
vpx_highbd_sad32x64x4d_avx2
Line
Count
Source
240
17.6k
                                      int ref_stride, uint32_t sad_array[4]) { \
241
17.6k
    highbd_sad32xNx4d_avx2(src, src_stride, ref_array, ref_stride, sad_array,  \
242
17.6k
                           n);                                                 \
243
17.6k
  }
vpx_highbd_sad32x32x4d_avx2
Line
Count
Source
240
80.6k
                                      int ref_stride, uint32_t sad_array[4]) { \
241
80.6k
    highbd_sad32xNx4d_avx2(src, src_stride, ref_array, ref_stride, sad_array,  \
242
80.6k
                           n);                                                 \
243
80.6k
  }
vpx_highbd_sad32x16x4d_avx2
Line
Count
Source
240
31.7k
                                      int ref_stride, uint32_t sad_array[4]) { \
241
31.7k
    highbd_sad32xNx4d_avx2(src, src_stride, ref_array, ref_stride, sad_array,  \
242
31.7k
                           n);                                                 \
243
31.7k
  }
244
245
#define HIGHBD_SADSKIP32XNx4D(n)                                             \
246
  void vpx_highbd_sad_skip_32x##n##x4d_avx2(                                 \
247
      const uint8_t *src, int src_stride, const uint8_t *const ref_array[4], \
248
49.8k
      int ref_stride, uint32_t sad_array[4]) {                               \
249
49.8k
    highbd_sad32xNx4d_avx2(src, 2 * src_stride, ref_array, 2 * ref_stride,   \
250
49.8k
                           sad_array, n / 2);                                \
251
49.8k
    sad_array[0] <<= 1;                                                      \
252
49.8k
    sad_array[1] <<= 1;                                                      \
253
49.8k
    sad_array[2] <<= 1;                                                      \
254
49.8k
    sad_array[3] <<= 1;                                                      \
255
49.8k
  }
Unexecuted instantiation: vpx_highbd_sad_skip_32x64x4d_avx2
vpx_highbd_sad_skip_32x32x4d_avx2
Line
Count
Source
248
45.3k
      int ref_stride, uint32_t sad_array[4]) {                               \
249
45.3k
    highbd_sad32xNx4d_avx2(src, 2 * src_stride, ref_array, 2 * ref_stride,   \
250
45.3k
                           sad_array, n / 2);                                \
251
45.3k
    sad_array[0] <<= 1;                                                      \
252
45.3k
    sad_array[1] <<= 1;                                                      \
253
45.3k
    sad_array[2] <<= 1;                                                      \
254
45.3k
    sad_array[3] <<= 1;                                                      \
255
45.3k
  }
vpx_highbd_sad_skip_32x16x4d_avx2
Line
Count
Source
248
4.42k
      int ref_stride, uint32_t sad_array[4]) {                               \
249
4.42k
    highbd_sad32xNx4d_avx2(src, 2 * src_stride, ref_array, 2 * ref_stride,   \
250
4.42k
                           sad_array, n / 2);                                \
251
4.42k
    sad_array[0] <<= 1;                                                      \
252
4.42k
    sad_array[1] <<= 1;                                                      \
253
4.42k
    sad_array[2] <<= 1;                                                      \
254
4.42k
    sad_array[3] <<= 1;                                                      \
255
4.42k
  }
256
257
static VPX_FORCE_INLINE void highbd_sad16xHx4d(__m256i *sums_16 /*[4]*/,
258
                                               const uint16_t *src,
259
                                               int src_stride,
260
                                               uint16_t *refs[4],
261
333k
                                               int ref_stride, int height) {
262
333k
  int i;
263
4.78M
  for (i = 0; i < height; i++) {
264
4.44M
    __m256i r[4];
265
266
    // load src and all ref[]
267
4.44M
    const __m256i s = _mm256_load_si256((const __m256i *)src);
268
4.44M
    r[0] = _mm256_loadu_si256((const __m256i *)refs[0]);
269
4.44M
    r[1] = _mm256_loadu_si256((const __m256i *)refs[1]);
270
4.44M
    r[2] = _mm256_loadu_si256((const __m256i *)refs[2]);
271
4.44M
    r[3] = _mm256_loadu_si256((const __m256i *)refs[3]);
272
273
    // absolute differences between every ref[] to src
274
4.44M
    r[0] = _mm256_abs_epi16(_mm256_sub_epi16(r[0], s));
275
4.44M
    r[1] = _mm256_abs_epi16(_mm256_sub_epi16(r[1], s));
276
4.44M
    r[2] = _mm256_abs_epi16(_mm256_sub_epi16(r[2], s));
277
4.44M
    r[3] = _mm256_abs_epi16(_mm256_sub_epi16(r[3], s));
278
279
    // sum every abs diff
280
4.44M
    sums_16[0] = _mm256_add_epi16(sums_16[0], r[0]);
281
4.44M
    sums_16[1] = _mm256_add_epi16(sums_16[1], r[1]);
282
4.44M
    sums_16[2] = _mm256_add_epi16(sums_16[2], r[2]);
283
4.44M
    sums_16[3] = _mm256_add_epi16(sums_16[3], r[3]);
284
285
4.44M
    src += src_stride;
286
4.44M
    refs[0] += ref_stride;
287
4.44M
    refs[1] += ref_stride;
288
4.44M
    refs[2] += ref_stride;
289
4.44M
    refs[3] += ref_stride;
290
4.44M
  }
291
333k
}
292
293
static VPX_FORCE_INLINE void highbd_sad16xNx4d_avx2(
294
    const uint8_t *src_ptr, int src_stride, const uint8_t *const ref_array[4],
295
80.6k
    int ref_stride, uint32_t sad_array[4], int n) {
296
80.6k
  const uint16_t *src = CONVERT_TO_SHORTPTR(src_ptr);
297
80.6k
  uint16_t *refs[4];
298
80.6k
  __m256i sums_16[4];
299
80.6k
  __m256i sums_32[4];
300
80.6k
  const int height = VPXMIN(16, n);
301
80.6k
  const int num_iters = n / height;
302
80.6k
  int i;
303
304
80.6k
  refs[0] = CONVERT_TO_SHORTPTR(ref_array[0]);
305
80.6k
  refs[1] = CONVERT_TO_SHORTPTR(ref_array[1]);
306
80.6k
  refs[2] = CONVERT_TO_SHORTPTR(ref_array[2]);
307
80.6k
  refs[3] = CONVERT_TO_SHORTPTR(ref_array[3]);
308
80.6k
  sums_32[0] = _mm256_setzero_si256();
309
80.6k
  sums_32[1] = _mm256_setzero_si256();
310
80.6k
  sums_32[2] = _mm256_setzero_si256();
311
80.6k
  sums_32[3] = _mm256_setzero_si256();
312
313
183k
  for (i = 0; i < num_iters; ++i) {
314
103k
    sums_16[0] = _mm256_setzero_si256();
315
103k
    sums_16[1] = _mm256_setzero_si256();
316
103k
    sums_16[2] = _mm256_setzero_si256();
317
103k
    sums_16[3] = _mm256_setzero_si256();
318
319
103k
    highbd_sad16xHx4d(sums_16, src, src_stride, refs, ref_stride, height);
320
321
    // sums_16 will outrange after 16 rows, so add current sums_16 to sums_32
322
103k
    sums_32[0] = _mm256_add_epi32(
323
103k
        sums_32[0],
324
103k
        _mm256_add_epi32(
325
103k
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[0])),
326
103k
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[0], 1))));
327
103k
    sums_32[1] = _mm256_add_epi32(
328
103k
        sums_32[1],
329
103k
        _mm256_add_epi32(
330
103k
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[1])),
331
103k
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[1], 1))));
332
103k
    sums_32[2] = _mm256_add_epi32(
333
103k
        sums_32[2],
334
103k
        _mm256_add_epi32(
335
103k
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[2])),
336
103k
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[2], 1))));
337
103k
    sums_32[3] = _mm256_add_epi32(
338
103k
        sums_32[3],
339
103k
        _mm256_add_epi32(
340
103k
            _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[3])),
341
103k
            _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[3], 1))));
342
343
103k
    src += src_stride << 4;
344
103k
  }
345
80.6k
  calc_final_4(sums_32, sad_array);
346
80.6k
}
347
348
#define HIGHBD_SAD16XNX4D(n)                                                   \
349
  void vpx_highbd_sad16x##n##x4d_avx2(const uint8_t *src, int src_stride,      \
350
                                      const uint8_t *const ref_array[4],       \
351
22.3k
                                      int ref_stride, uint32_t sad_array[4]) { \
352
22.3k
    highbd_sad16xNx4d_avx2(src, src_stride, ref_array, ref_stride, sad_array,  \
353
22.3k
                           n);                                                 \
354
22.3k
  }
355
356
#define HIGHBD_SADSKIP16XNx4D(n)                                             \
357
  void vpx_highbd_sad_skip_16x##n##x4d_avx2(                                 \
358
      const uint8_t *src, int src_stride, const uint8_t *const ref_array[4], \
359
58.3k
      int ref_stride, uint32_t sad_array[4]) {                               \
360
58.3k
    highbd_sad16xNx4d_avx2(src, 2 * src_stride, ref_array, 2 * ref_stride,   \
361
58.3k
                           sad_array, n / 2);                                \
362
58.3k
    sad_array[0] <<= 1;                                                      \
363
58.3k
    sad_array[1] <<= 1;                                                      \
364
58.3k
    sad_array[2] <<= 1;                                                      \
365
58.3k
    sad_array[3] <<= 1;                                                      \
366
58.3k
  }
vpx_highbd_sad_skip_16x32x4d_avx2
Line
Count
Source
359
287
      int ref_stride, uint32_t sad_array[4]) {                               \
360
287
    highbd_sad16xNx4d_avx2(src, 2 * src_stride, ref_array, 2 * ref_stride,   \
361
287
                           sad_array, n / 2);                                \
362
287
    sad_array[0] <<= 1;                                                      \
363
287
    sad_array[1] <<= 1;                                                      \
364
287
    sad_array[2] <<= 1;                                                      \
365
287
    sad_array[3] <<= 1;                                                      \
366
287
  }
vpx_highbd_sad_skip_16x16x4d_avx2
Line
Count
Source
359
53.7k
      int ref_stride, uint32_t sad_array[4]) {                               \
360
53.7k
    highbd_sad16xNx4d_avx2(src, 2 * src_stride, ref_array, 2 * ref_stride,   \
361
53.7k
                           sad_array, n / 2);                                \
362
53.7k
    sad_array[0] <<= 1;                                                      \
363
53.7k
    sad_array[1] <<= 1;                                                      \
364
53.7k
    sad_array[2] <<= 1;                                                      \
365
53.7k
    sad_array[3] <<= 1;                                                      \
366
53.7k
  }
vpx_highbd_sad_skip_16x8x4d_avx2
Line
Count
Source
359
4.32k
      int ref_stride, uint32_t sad_array[4]) {                               \
360
4.32k
    highbd_sad16xNx4d_avx2(src, 2 * src_stride, ref_array, 2 * ref_stride,   \
361
4.32k
                           sad_array, n / 2);                                \
362
4.32k
    sad_array[0] <<= 1;                                                      \
363
4.32k
    sad_array[1] <<= 1;                                                      \
364
4.32k
    sad_array[2] <<= 1;                                                      \
365
4.32k
    sad_array[3] <<= 1;                                                      \
366
4.32k
  }
367
368
void vpx_highbd_sad16x16x4d_avx2(const uint8_t *src_ptr, int src_stride,
369
                                 const uint8_t *const ref_array[4],
370
179k
                                 int ref_stride, uint32_t sad_array[4]) {
371
179k
  const uint16_t *src = CONVERT_TO_SHORTPTR(src_ptr);
372
179k
  uint16_t *refs[4];
373
179k
  __m256i sums_16[4];
374
375
179k
  refs[0] = CONVERT_TO_SHORTPTR(ref_array[0]);
376
179k
  refs[1] = CONVERT_TO_SHORTPTR(ref_array[1]);
377
179k
  refs[2] = CONVERT_TO_SHORTPTR(ref_array[2]);
378
179k
  refs[3] = CONVERT_TO_SHORTPTR(ref_array[3]);
379
179k
  sums_16[0] = _mm256_setzero_si256();
380
179k
  sums_16[1] = _mm256_setzero_si256();
381
179k
  sums_16[2] = _mm256_setzero_si256();
382
179k
  sums_16[3] = _mm256_setzero_si256();
383
384
179k
  highbd_sad16xHx4d(sums_16, src, src_stride, refs, ref_stride, 16);
385
386
179k
  {
387
179k
    __m256i sums_32[4];
388
179k
    sums_32[0] = _mm256_add_epi32(
389
179k
        _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[0])),
390
179k
        _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[0], 1)));
391
179k
    sums_32[1] = _mm256_add_epi32(
392
179k
        _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[1])),
393
179k
        _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[1], 1)));
394
179k
    sums_32[2] = _mm256_add_epi32(
395
179k
        _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[2])),
396
179k
        _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[2], 1)));
397
179k
    sums_32[3] = _mm256_add_epi32(
398
179k
        _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[3])),
399
179k
        _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[3], 1)));
400
179k
    calc_final_4(sums_32, sad_array);
401
179k
  }
402
179k
}
403
404
void vpx_highbd_sad16x8x4d_avx2(const uint8_t *src_ptr, int src_stride,
405
                                const uint8_t *const ref_array[4],
406
50.7k
                                int ref_stride, uint32_t sad_array[4]) {
407
50.7k
  const uint16_t *src = CONVERT_TO_SHORTPTR(src_ptr);
408
50.7k
  uint16_t *refs[4];
409
50.7k
  __m256i sums_16[4];
410
411
50.7k
  refs[0] = CONVERT_TO_SHORTPTR(ref_array[0]);
412
50.7k
  refs[1] = CONVERT_TO_SHORTPTR(ref_array[1]);
413
50.7k
  refs[2] = CONVERT_TO_SHORTPTR(ref_array[2]);
414
50.7k
  refs[3] = CONVERT_TO_SHORTPTR(ref_array[3]);
415
50.7k
  sums_16[0] = _mm256_setzero_si256();
416
50.7k
  sums_16[1] = _mm256_setzero_si256();
417
50.7k
  sums_16[2] = _mm256_setzero_si256();
418
50.7k
  sums_16[3] = _mm256_setzero_si256();
419
420
50.7k
  highbd_sad16xHx4d(sums_16, src, src_stride, refs, ref_stride, 8);
421
422
50.7k
  {
423
50.7k
    __m256i sums_32[4];
424
50.7k
    sums_32[0] = _mm256_add_epi32(
425
50.7k
        _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[0])),
426
50.7k
        _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[0], 1)));
427
50.7k
    sums_32[1] = _mm256_add_epi32(
428
50.7k
        _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[1])),
429
50.7k
        _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[1], 1)));
430
50.7k
    sums_32[2] = _mm256_add_epi32(
431
50.7k
        _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[2])),
432
50.7k
        _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[2], 1)));
433
50.7k
    sums_32[3] = _mm256_add_epi32(
434
50.7k
        _mm256_cvtepu16_epi32(_mm256_castsi256_si128(sums_16[3])),
435
        _mm256_cvtepu16_epi32(_mm256_extractf128_si256(sums_16[3], 1)));
436
50.7k
    calc_final_4(sums_32, sad_array);
437
50.7k
  }
438
50.7k
}
439
440
// clang-format off
441
HIGHBD_SAD64XNX4D(64)
442
HIGHBD_SADSKIP64XNx4D(64)
443
444
HIGHBD_SAD64XNX4D(32)
445
HIGHBD_SADSKIP64XNx4D(32)
446
447
HIGHBD_SAD32XNX4D(64)
448
HIGHBD_SADSKIP32XNx4D(64)
449
450
HIGHBD_SAD32XNX4D(32)
451
HIGHBD_SADSKIP32XNx4D(32)
452
453
HIGHBD_SAD32XNX4D(16)
454
HIGHBD_SADSKIP32XNx4D(16)
455
456
HIGHBD_SAD16XNX4D(32)
457
HIGHBD_SADSKIP16XNx4D(32)
458
459
HIGHBD_SADSKIP16XNx4D(16)
460
461
HIGHBD_SADSKIP16XNx4D(8)
462
    // clang-format on