Rumah >pembangunan bahagian belakang >C++ >Bagaimana untuk Melaksanakan log2(__m256d) dengan Cekap dalam AVX2?

Bagaimana untuk Melaksanakan log2(__m256d) dengan Cekap dalam AVX2?

DDD
DDDasal
2024-12-04 14:06:11195semak imbas

How to Efficiently Implement log2(__m256d) in AVX2?

Pelaksanaan log2(__m256d) yang Cekap dalam AVX2

Pengenalan

__mm256d log intrinsik (__m256d a) tidak disokong melebihi penyusun Intel dan prestasinya terjejas pada pemproses AMD. Artikel ini bertujuan untuk menyediakan penyelesaian berprestasi dan pengkompil silang untuk mengira log2() bagi vektor beregu menggunakan set arahan AVX2.

Pendekatan

Kaedah biasa melibatkan membahagikan log(a*b) kepada log(a) log(b) dan melaraskan pincang eksponen. Untuk kes log2, hasilnya bersamaan dengan log eksponen2(mantissa). Memandangkan julat mantissa (1.0 hingga 2.0) adalah terhad, anggaran polinomial untuk log2(mantissa) boleh digunakan.

Pertimbangan Ketepatan

Ketepatan anggaran mempengaruhi ralat relatif. Untuk meminimumkan ralat mutlak atau relatif maksimum, pekali harus ditala melalui pemasangan minimax dan bukannya hanya menggunakan pengembangan siri Taylor.

Vectorization

Untuk memanfaatkan arahan AVX2 ditetapkan untuk pemprosesan vektor, langkah berikut dilaksanakan:

  1. Ekstrak bit eksponen dan tukar mereka terapung selepas pelarasan pincang.
  2. Ekstrak mantissa dan ubah suainya untuk julat [0.5, 1.0) dengan pelarasan eksponen.
  3. Gunakan anggaran polinomial untuk log(x) tepat di sekitar x =1.0 menggunakan arahan AVX2 dengan FMA.
  4. Kira hasil log2 akhir dengan menambahkan eksponen dan penghampiran polinomial.
  5. Sertakan pengendalian khas untuk kes bawah, limpahan dan denormal.

Peningkatan Prestasi

Untuk meningkatkan prestasi:

  • Gunakan tertib lebih tinggi polinomial atau nisbah polinomial untuk ketepatan yang lebih tinggi.
  • Gunakan arahan AVX512 untuk keupayaan lanjutan, seperti mengekstrak eksponen dan mantissa dengan lebih cekap.
  • Alih keluar atau laraskan penyemakan kes khas jika nilai diketahui menjadi terhingga dan positif.

Pelaksanaan

Pelaksanaan di bawah menggunakan intrinsik untuk vektorisasi dan arahan FMA untuk pendaraban dan penambahan yang cekap:

__m256d Log2(__m256d x) {
  // Extract exponent and adjust bias
  const __m256i exps64 = _mm256_srli_epi64(_mm256_and_si256(gDoubleExpMask, _mm256_castpd_si256(x)), 52);
  const __m256i exps32_avx = _mm256_permutevar8x32_epi32(exps64, gTo32bitExp);
  const __m128i exps32_sse = _mm256_castsi256_si128(exps32_avx);
  const __m128i normExps = _mm_sub_epi32(exps32_sse, gExpNormalizer);
  const __m256d expsPD = _mm256_cvtepi32_pd(normExps);

  // Prepare mantissa
  const __m256d y = _mm256_or_pd(_mm256_castsi256_pd(gDoubleExp0),
    _mm256_andnot_pd(_mm256_castsi256_pd(gDoubleExpMask), x));

  // Calculate t=(y-1)/(y+1) and t**2
  const __m256d tNum = _mm256_sub_pd(y, gVect1);
  const __m256d tDen = _mm256_add_pd(y, gVect1);
  const __m256d t = _mm256_div_pd(tNum, tDen);
  const __m256d t2 = _mm256_mul_pd(t, t); // t**2

  // Calculate terms and final log2
  const __m256d t3 = _mm256_mul_pd(t, t2); // t**3
  const __m256d terms01 = _mm256_fmadd_pd(gCoeff1, t3, t);
  const __m256d t5 = _mm256_mul_pd(t3, t2); // t**5
  const __m256d terms012 = _mm256_fmadd_pd(gCoeff2, t5, terms01);
  const __m256d t7 = _mm256_mul_pd(t5, t2); // t**7
  const __m256d terms0123 = _mm256_fmadd_pd(gCoeff3, t7, terms012);
  const __m256d t9 = _mm256_mul_pd(t7, t2); // t**9
  const __m256d terms01234 = _mm256_fmadd_pd(gCoeff4, t9, terms0123);
  const __m256d log2_y = _mm256_mul_pd(terms01234, gCommMul);
  const __m256d log2_x = _mm256_add_pd(log2_y, expsPD);

  return log2_x;
}

Kesimpulan

Pelaksanaan ini menyediakan penyelesaian yang cekap dan mudah alih untuk log2() pengiraan menggunakan AVX2. Dengan mengoptimumkan kedua-dua kelajuan dan ketepatan, ia menawarkan alternatif pengkompil silang kepada fungsi intrinsik dan boleh meningkatkan prestasi dengan ketara.

Atas ialah kandungan terperinci Bagaimana untuk Melaksanakan log2(__m256d) dengan Cekap dalam AVX2?. Untuk maklumat lanjut, sila ikut artikel berkaitan lain di laman web China PHP!

Kenyataan:
Kandungan artikel ini disumbangkan secara sukarela oleh netizen, dan hak cipta adalah milik pengarang asal. Laman web ini tidak memikul tanggungjawab undang-undang yang sepadan. Jika anda menemui sebarang kandungan yang disyaki plagiarisme atau pelanggaran, sila hubungi admin@php.cn