Pembaruan Backend MSVC di Visual Studio 2019 Pratinjau 2: Optimasi Baru, OpenMP, dan peningkatan Throughput Build


Dalam Visual Studio 2019 Pratinjau 2 kami terus meningkatkan backend C ++ dengan fitur-fitur baru, optimasi baru dan lebih baik, membangun peningkatan throughput, dan kualitas perubahan kehidupan.


Asli di blog

Fitur baru


  • Menambahkan saklar baris perintah inlining baru: -Ob3. -Ob3 adalah versi yang lebih agresif dari -Ob2. -O2 (mengoptimalkan biner untuk kecepatan) masih menyiratkan -Ob2 secara default, tetapi ini mungkin berubah di masa depan. Jika Anda menemukan kompiler dalam-inlining, pertimbangkan untuk meneruskan -O2 -Ob3.
  • Menambahkan dukungan dasar untuk vektorisasi OpenMP SIMD yang merupakan fitur OpenMP yang paling banyak digunakan dalam pustaka pembelajaran mesin (ML). Studi kasus kami adalah perpustakaan Intel MKL-DNN, yang digunakan sebagai blok bangunan untuk pustaka ML open source terkenal lainnya termasuk Tensor Flow. Ini dapat dihidupkan dengan saklar CL baru -openmp: eksperimental. Ini memungkinkan loop beranotasi dengan "#pragma omp simd" berpotensi menjadi vektor. Vektorisasi tidak dijamin, dan loop beranotasi tetapi tidak di-vektorisasi akan mendapatkan peringatan yang dilaporkan. Tidak ada klausa SIMD yang didukung, mereka hanya akan diabaikan dengan peringatan yang dilaporkan.
  • Menambahkan penangan pengecualian C ++ baru __CxxFrameHandler4 yang mengurangi pengecualian penanganan overhead metadata sebesar 66%. Ini memberikan peningkatan ukuran biner total hingga 15% pada binari yang menggunakan sejumlah besar penanganan pengecualian C ++. Saat ini default tidak aktif, cobalah dengan meneruskan "/ d2FH4" saat dikompilasi dengan cl.exe. Perhatikan bahwa / d2FH4 dinyatakan tidak berdokumen dan tidak didukung dalam jangka panjang. Ini saat ini tidak didukung pada aplikasi UWP karena runtime UWP belum memiliki fitur ini.
  • Untuk mendukung vektorisasi tangan dari loop yang berisi panggilan ke fungsi perpustakaan matematika dan operasi tertentu lainnya seperti divisi integer, MSVC sekarang mendukung fungsi intrinsik Perpustakaan Vector Vector Pendek (SVML) yang menghitung setara vektor. Dukungan untuk vektor 128-bit, 256-bit dan 512-bit tersedia untuk sebagian besar fungsi, dengan pengecualian yang tercantum di bawah ini. Perhatikan bahwa fungsi-fungsi ini tidak mengatur errno. Lihat Panduan Intrinsik Intel untuk definisi fungsi yang didukung.
    Pengecualian termasuk:
    • Divisi dan sisanya gabungan integer vektor hanya tersedia untuk elemen 32-bit dan panjang vektor 128-bit dan 256-bit. Gunakan fungsi pembagian dan sisa yang terpisah untuk ukuran elemen dan panjang vektor lainnya.
    • SVML square-root hanya tersedia dalam panjang vektor 128-bit dan 256-bit. Anda dapat menggunakan fungsi _mm512_sqrt_pd atau _mm512_sqrt_ps untuk vektor 512-bit.
    • Hanya versi vektor 512-bit fungsi rint dan terdekat tidak tersedia. Dalam banyak kasus, Anda dapat menggunakan fungsi bundar sebagai gantinya, mis. Gunakan _mm256_round_ps (x, _MM_FROUND_CUR_DIRECTION) sebagai versi vektor 256-bit dari rintisan , atau _mm256_round_ps (x, _MM_FROUND_TO_NEAREST_INT) untuk dekatnya .
    • Hanya timbal balik 512-bit disediakan. Anda dapat menghitung yang setara menggunakan fungsi set1 dan div, mis. 256-bit reciprocal dapat dikomputasi sebagai _mm256_div_ps (_mm256_set1_ps (1.0f), (x)) .
    • Ada fungsi SVML untuk akar kuadrat kompleks presisi tunggal, logaritma, dan eksponensial hanya dalam panjang vektor 128-bit dan 256-bit.

Optimalisasi Baru dan Peningkatan


  • Memset yang tidak terkontrol dan memblokir inisialisasi sekarang akan menggunakan instruksi SSE2 (atau instruksi AVX jika diizinkan). Ambang ukuran untuk apa yang akan dibuka gulungannya telah meningkat (kompilasi untuk ukuran dengan SSE2: buka gulungan bergerak dari 31 ke 63 byte, kompilasi untuk kecepatan dengan SSE2: ambang bergerak dari 79 menjadi 159 byte).
  • Dioptimalkan kode-gen untuk memset kecil, terutama ditargetkan untuk fungsi yang dilindungi secara keseluruhan .
  • Perbaikan pada eliminasi berlebihan toko SSA Optimizer : analisis pelarian yang lebih baik dan penanganan loop
  • Kompiler mengenali memmove () sebagai fungsi intrinsik dan mengoptimalkannya. Ini meningkatkan pembuatan kode untuk operasi yang dibangun di memmove () termasuk std :: copy () dan kode perpustakaan tingkat lebih tinggi lainnya seperti std :: vector dan std :: string struction
  • Pengoptimal melakukan pekerjaan yang lebih baik untuk mengoptimalkan operasi memmove (), memcpy (), dan memcmp () yang pendek dan tetap.
  • Dioptimalkan optimasi duplikasi switch untuk kinerja switch yang lebih baik di dalam hot loop. Kami menduplikasi saklar melompat untuk membantu meningkatkan akurasi prediksi cabang dan akibatnya, menjalankan kinerja waktu.
  • Menambahkan penyederhanaan konstanta lipat dan aritmatika untuk ekspresi menggunakan SIMD (vektor) intrinsik, untuk bentuk float dan integer. Sebagian besar optimasi ekspresi biasa sekarang menangani SSE2 dan AVX2 intrinsik, baik dari kode pengguna atau hasil dari vektorisasi otomatis.
  • Beberapa pola skalar multiply-add (FMA) baru diidentifikasi dengan / arch: AVX2 / fp: fast. Ini termasuk ekspresi umum berikut: (x + 1.0) * y; (x – 1.0) * y; (1.0 – x) * y; (-1.0 – x) * y (x + 1.0) * y; (x – 1.0) * y; (1.0 – x) * y; (-1.0 – x) * y
  • Urutan kode yang menginisialisasi elemen nilai demi elemen __m128 SIMD (vektor) diidentifikasi dan diganti oleh intrinsik _mm_set_ps . Ini memungkinkan optimalisasi SIMD baru untuk mempertimbangkan nilai sebagai bagian dari ekspresi, berguna terutama jika nilai hanya memiliki elemen konstan. Pembaruan di masa depan akan mendukung lebih banyak tipe nilai.
  • Eliminasi sub-ekspresi umum (CSE) lebih efektif di hadapan variabel yang dapat dimodifikasi secara tidak langsung karena mereka memiliki alamat mereka diambil.
  • Salinan struct / class yang tidak berguna sedang dihapus dalam beberapa kasus lagi, termasuk salinan ke parameter output dan fungsi mengembalikan suatu objek. Optimasi ini sangat efektif dalam program C ++ yang melewatkan objek berdasarkan nilai.
  • Menambahkan analisis yang lebih kuat untuk mengekstraksi informasi tentang variabel dari aliran kontrol (jika / else / beralih pernyataan), digunakan untuk menghapus cabang yang dapat terbukti selalu benar atau salah dan untuk meningkatkan estimasi rentang variabel. Kode menggunakan gsl :: span melihat peningkatan, beberapa pemeriksaan rentang yang tidak perlu dihapus sekarang.
  • Optimalisasi devirtualisasi sekarang akan memiliki peluang tambahan, seperti ketika kelas didefinisikan dalam ruang nama anonim.

Membangun Peningkatan Throughput


  • Memfilter informasi debug selama kompilasi berdasarkan simbol dan tipe yang dirujuk untuk mengurangi ukuran bagian debug dan meningkatkan throughput tautan. Memperbarui dari 15.9 hingga 16.0 dapat mengurangi ukuran input ke linker hingga 40%.
  • Tautkan peningkatan waktu dalam penggabungan dan pembuatan tipe PDB.
  • Memperbarui ke 16.0 dari 15.9 dapat meningkatkan waktu tautan hingga kecepatan 2X. Misalnya, menautkan Chrome menghasilkan peningkatan waktu tautan 1,75X saat menggunakan / DEBUG: penuh, dan peningkatan waktu tautan 1,4X saat menggunakan / DEBUG: tautan cepat.

Peningkatan Kualitas Hidup


  • Kompiler menampilkan nama file dan jalur menggunakan casing yang disediakan pengguna di mana sebelumnya kompiler menampilkan nama file dan jalur yang lebih rendah.
  • Linker baru sekarang akan melaporkan simbol yang mungkin cocok untuk simbol yang belum terselesaikan, seperti:

 main.obj : error LNK2019: unresolved external symbol _foo referenced in function _main Hint on symbols that are defined and could potentially match: "int __cdecl foo(int)" (?foo@@YAHH@Z) "bool __cdecl foo(double)" (?foo@@YA_NN@Z) @foo@0 foo@@4 main.exe : fatal error LNK1120: 1 unresolved externals 
  • Saat membuat pustaka statis, tidak lagi diperlukan untuk meneruskan flag / LTCG ke LIB.exe.
  • Menambahkan opsi tautan / LINKREPROTARGET: [binary_name] untuk hanya menghasilkan repro tautan untuk biner yang ditentukan. Ini memungkinkan% LINK_REPRO% atau / LINKREPRO: [direktori_name] diatur dalam bangunan besar dengan banyak tautan, dan penghubung hanya akan menghasilkan repro untuk biner yang ditentukan dalam / linkreprotarget.

Kami ingin Anda mengunduh Visual Studio 2019 dan mencobanya. Seperti biasa, kami menyambut umpan balik Anda. Kami dapat dihubungi melalui komentar di bawah ini atau melalui email ( visualcpp@microsoft.com ). Jika Anda mengalami masalah dengan Visual Studio atau MSVC, atau memiliki saran untuk kami, beri tahu kami melalui Bantuan> Kirim Umpan Balik> Laporkan Masalah / Berikan Saran dalam produk, atau melalui Komunitas Pengembang . Anda juga dapat menemukan kami di Twitter ( @VisualC ) dan Facebook (msftvisualcpp).

Source: https://habr.com/ru/post/id437670/


All Articles