static void avx2_test (void) { union256i_w s1, s2, res; short res_ref[16]; int i, j, sign = 1; int fail = 0; for (i = 0; i < 10; i++) { for (j = 0; j < 16; j++) { s1.a[j] = i * j * sign; s2.a[j] = (j + 20) * sign; sign = -sign; } res.x = _mm256_mulhi_epi16 (s1.x, s2.x); compute_pmulhw256 (s1.a, s2.a, res_ref); fail += check_union256i_w (res, res_ref); } if (fail != 0) abort (); }
// 32bpp optimized for 8-bit ARGB/RGBA. rmask should be 0x00FF,0x00FF,... etc static inline __m256i stretchblt_line_bilinear_pixel_blend_avx_argb8(const __m256i cur,const __m256i nxt,const __m256i mul,const __m256i rmask) { __m256i rc,gc; __m256i rn,gn; __m256i d,sum; rc = _mm256_and_si256( cur ,rmask); gc = _mm256_and_si256(_mm256_srli_epi16(cur,8),rmask); rn = _mm256_and_si256( nxt ,rmask); gn = _mm256_and_si256(_mm256_srli_epi16(nxt,8),rmask); d = _mm256_sub_epi16(rn,rc); sum = _mm256_add_epi16(rc,_mm256_mulhi_epi16(_mm256_add_epi16(d,d),mul)); d = _mm256_sub_epi16(gn,gc); sum = _mm256_add_epi16(_mm256_slli_epi16(_mm256_add_epi16(gc,_mm256_mulhi_epi16(_mm256_add_epi16(d,d),mul)),8),sum); return sum; }
void m16_256(int16_t *x, int16_t *y, int16_t *z, int N){ __m256i *x256, *y256, *z256; x256 = (__m256i *)x; y256 = (__m256i *)y; z256 = (__m256i *)z; int i; for(i=0; i<(N>>3); i++){ z256[i] = _mm256_mulhi_epi16(x256[i], y256[i]); } }
// 16bpp general R/G/B, usually 5/6/5 or 5/5/5 static inline __m256i stretchblt_line_bilinear_pixel_blend_avx_rgb16(const __m256i cur,const __m256i nxt,const __m256i mul,const __m256i rmask,const uint16_t rshift,const __m256i gmask,const uint16_t gshift,const __m256i bmask,const uint16_t bshift) { __m256i rc,gc,bc; __m256i rn,gn,bn; __m256i d,sum; rc = _mm256_and_si256(_mm256_srli_epi16(cur,rshift),rmask); gc = _mm256_and_si256(_mm256_srli_epi16(cur,gshift),gmask); bc = _mm256_and_si256(_mm256_srli_epi16(cur,bshift),bmask); rn = _mm256_and_si256(_mm256_srli_epi16(nxt,rshift),rmask); gn = _mm256_and_si256(_mm256_srli_epi16(nxt,gshift),gmask); bn = _mm256_and_si256(_mm256_srli_epi16(nxt,bshift),bmask); d = _mm256_sub_epi16(rn,rc); sum = _mm256_slli_epi16(_mm256_add_epi16(rc,_mm256_mulhi_epi16(_mm256_add_epi16(d,d),mul)),rshift); d = _mm256_sub_epi16(gn,gc); sum = _mm256_add_epi16(_mm256_slli_epi16(_mm256_add_epi16(gc,_mm256_mulhi_epi16(_mm256_add_epi16(d,d),mul)),gshift),sum); d = _mm256_sub_epi16(bn,bc); sum = _mm256_add_epi16(_mm256_slli_epi16(_mm256_add_epi16(bc,_mm256_mulhi_epi16(_mm256_add_epi16(d,d),mul)),bshift),sum); return sum; }
__m256i test_mm256_mulhi_epi16(__m256i a, __m256i b) { // CHECK: @llvm.x86.avx2.pmulh.w return _mm256_mulhi_epi16(a, b); }
__m256i test_mm256_mulhi_epi16(__m256i a, __m256i b) { // CHECK-LABEL: test_mm256_mulhi_epi16 // CHECK: call <16 x i16> @llvm.x86.avx2.pmulh.w(<16 x i16> %{{.*}}, <16 x i16> %{{.*}}) return _mm256_mulhi_epi16(a, b); }
void extern avx2_test (void) { x = _mm256_mulhi_epi16 (x, x); }