Eksekusi Dinamis

Laporkan masalah Lihat sumber Per Malam · 7,4 kami. 7,3 · 7,2 · 7,1 · 7,0 · 6,5

Dynamic execution adalah fitur di Bazel tempat eksekusi lokal dan jarak jauh tindakan yang sama dimulai secara paralel, menggunakan output dari cabang pertama yang selesai, membatalkan cabang lainnya. Menggabungkan kemampuan eksekusi dan/atau cache bersama yang besar dari sistem build jarak jauh dengan eksekusinya, yang memberikan yang terbaik dari keduanya untuk build bersih dan inkremental sama.

Halaman ini menjelaskan cara mengaktifkan, menyesuaikan, dan men-debug eksekusi dinamis. Jika Anda telah menyiapkan eksekusi lokal dan jarak jauh serta mencoba menyesuaikan setelan Bazel untuk performa yang lebih baik, halaman ini cocok untuk Anda. Jika Anda belum menyiapkan eksekusi jarak jauh, buka Ringkasan Eksekusi Jarak Jauh Bazel terlebih dahulu.

Mengaktifkan eksekusi dinamis?

Modul eksekusi dinamis adalah bagian dari Bazel, tetapi untuk memanfaatkan dalam eksekusinya, Anda harus sudah dapat mengompilasi baik secara lokal maupun jarak jauh dari pengaturan Bazel yang sama.

Untuk mengaktifkan modul eksekusi dinamis, teruskan --internal_spawn_scheduler kepada Bazel. Tindakan ini akan menambahkan strategi eksekusi baru yang disebut dynamic. Sekarang Anda dapat menggunakannya sebagai strategi untuk mnemoni yang ingin dijalankan secara dinamis, seperti --strategy=Javac=dynamic. Lihat bagian berikutnya untuk mengetahui cara memilih mnemoni yang akan mengaktifkan eksekusi dinamis.

Untuk setiap mnemoni yang menggunakan strategi dinamis, strategi eksekusi jarak jauh diambil dari flag --dynamic_remote_strategy, dan strategi lokal dari flag --dynamic_local_strategy. Lulus --dynamic_local_strategy=worker,sandboxed menetapkan default untuk lokal cabang dari eksekusi dinamis untuk dicoba dengan pekerja atau eksekusi dalam sandbox pesanan. Meneruskan --dynamic_local_strategy=Javac=worker akan mengganti default untuk mnemonik Javac saja. Versi jarak jauh berfungsi dengan cara yang sama. Kedua flag tersebut dapat ditentukan beberapa kali. Jika tindakan tidak dapat dijalankan secara lokal, dijalankan dari jarak jauh seperti biasa, dan sebaliknya.

Jika sistem jarak jauh Anda memiliki cache, flag --dynamic_local_execution_delay menambahkan penundaan dalam milidetik ke eksekusi lokal setelah sistem jarak jauh mengindikasikan cache ditemukan. Tindakan ini menghindari eksekusi lokal saat lebih banyak hit cache yang mungkin terjadi. Nilai defaultnya adalah 1.000 md, tetapi harus disesuaikan agar sedikit lebih lama dari waktu yang biasanya diperlukan cache hit. Waktu sebenarnya bergantung pada sistem jarak jauh dan berapa lama waktu yang diperlukan untuk perjalanan bolak-balik. Biasanya, nilainya akan sama untuk semua pengguna sistem jarak jauh tertentu, kecuali beberapa dari mereka berada cukup jauh untuk menambahkan latensi bolak-balik. Anda dapat menggunakan pembuatan profil Bazel untuk melihat berapa lama cache yang ditemukan.

Eksekusi dinamis dapat digunakan dengan strategi sandbox lokal serta dengan pekerja persisten. Pekerja persisten akan otomatis berjalan dengan sandbox saat digunakan dengan eksekusi dinamis, dan tidak dapat menggunakan multiplex pekerja. Di sistem Darwin dan Windows, sandbox strategi bisa jadi lambat; Anda dapat meneruskan --reuse_sandbox_directories untuk mengurangi overhead pembuatan {i>sandbox<i} pada sistem ini.

Eksekusi dinamis juga dapat dijalankan dengan strategi standalone, meskipun Strategi standalone harus mengambil kunci output saat mulai dieksekusi. efektif menghalangi strategi jarak jauh agar tidak selesai lebih dulu. Flag --experimental_local_lockfree_output memungkinkan cara untuk mengatasi masalah ini dengan memungkinkan eksekusi lokal menulis langsung ke output, tetapi dibatalkan oleh eksekusi jarak jauh, jika selesai terlebih dahulu.

Jika salah satu cabang dari eksekusi dinamis selesai lebih dahulu tetapi mengalami kegagalan, seluruh tindakan gagal. Ini adalah pilihan yang disengaja untuk mencegah perbedaan antara eksekusi lokal dan jarak jauh agar tidak terlewatkan.

Untuk latar belakang selengkapnya tentang cara kerja eksekusi dinamis dan pengunciannya, lihat Julio Blog yang luar biasa di Merino postingan

Kapan saya harus menggunakan eksekusi dinamis?

Eksekusi dinamis memerlukan suatu bentuk sistem eksekusi jarak jauh. Saat ini, penggunaan sistem jarak jauh khusus cache tidak dapat dilakukan, karena cache tidak ditemukan akan dianggap sebagai tindakan yang gagal.

Tidak semua jenis tindakan cocok untuk dieksekusi dari jarak jauh. Calon terbaik adalah yang secara inheren lebih cepat secara lokal, misalnya melalui penggunaan pekerja persisten, atau yang berjalan cukup cepat sehingga overhead eksekusi jarak jauh mendominasi waktu eksekusi. Sejak setiap tindakan yang dieksekusi secara lokal mengunci sejumlah sumber daya CPU dan memori, menjalankan tindakan yang tidak termasuk dalam kategori tersebut hanya akan menunda eksekusi bagi mereka yang memilikinya.

Mulai rilis 5.0.0-pre.20210708.4, profiling performa berisi data tentang eksekusi pekerja, termasuk waktu yang dihabiskan untuk menyelesaikan permintaan pekerjaan setelah kehilangan perlombaan eksekusi dinamis. Jika Anda melihat thread pekerja eksekusi dinamis menghabiskan banyak waktu untuk mendapatkan sumber daya, atau banyak waktu async-worker-finish, Anda mungkin memiliki beberapa tindakan lokal yang lambat sehingga menunda pekerja .

Membuat profil data dengan performa eksekusi dinamis yang buruk

Dalam profil di atas, yang menggunakan 8 pekerja Javac, kita melihat banyak pekerja Javac yang telah kalah dalam perlombaan dan menyelesaikan pekerjaan mereka di thread async-worker-finish. Hal ini disebabkan oleh mnemoni non-pekerja yang menggunakan resource yang cukup untuk menunda pekerja.

Membuat profil data dengan performa eksekusi dinamis yang lebih baik

Jika hanya Javac yang dijalankan dengan eksekusi dinamis, hanya sekitar setengah pekerja yang dimulai yang akhirnya kalah dalam perlombaan setelah memulai pekerjaan mereka.

Flag --experimental_spawn_scheduler yang sebelumnya direkomendasikan tidak digunakan lagi. Tindakan ini akan mengaktifkan eksekusi dinamis dan menetapkan dynamic sebagai strategi default untuk semua mnemoni, yang sering kali menyebabkan masalah semacam ini.

Performa

Pendekatan eksekusi dinamis mengasumsikan bahwa tersedia cukup sumber daya secara lokal dan jarak jauh, ada baiknya untuk menghabiskan beberapa sumber daya tambahan untuk meningkatkan performa keseluruhan. Namun, penggunaan resource yang berlebihan dapat memperlambat Bazel itu sendiri atau komputer tempatnya berjalan, atau memberikan tekanan yang tidak terduga pada sistem jarak jauh. Ada beberapa opsi untuk mengubah perilaku eksekusi dinamis:

--dynamic_local_execution_delay menunda awal cabang lokal dengan sejumlah milidetik setelah cabang jarak jauh dimulai, tetapi hanya jika telah ada hit cache jarak jauh selama build saat ini. Hal ini membuat build yang bermanfaat dari cache jarak jauh, tidak memboroskan sumber daya lokal ketika kemungkinan besar dapat ditemukan di cache. Bergantung pada kualitas cache, pengurangan ini dapat meningkatkan kecepatan build, dengan mengorbankan penggunaan lebih banyak resource lokal.

--experimental_dynamic_local_load_factor adalah resource lanjutan eksperimental opsi pengelolaan otomatis. Dibutuhkan nilai dari 0 hingga 1, 0 untuk menonaktifkan fitur ini. Bila diatur ke nilai di atas 0, Bazel akan menyesuaikan jumlah tindakan terjadwal lokal ketika banyak tindakan menunggu dijadwalkan. Menetapkan nilai ini ke 1 memungkinkan sebanyak mungkin tindakan dijadwalkan sesuai dengan jumlah CPU yang tersedia (sesuai dengan --local_cpu_resources). Nilai yang lebih rendah akan menetapkan jumlah tindakan yang dijadwalkan menjadi lebih sedikit karena jumlah tindakan yang lebih tinggi tersedia untuk dijalankan. Hal ini mungkin terdengar berlawanan dengan intuisi, tetapi dengan sistem jarak jauh yang baik, eksekusi lokal tidak banyak membantu saat banyak tindakan dijalankan, dan CPU lokal lebih baik digunakan untuk mengelola tindakan jarak jauh.

--experimental_dynamic_slow_remote_time memprioritaskan untuk memulai cabang lokal ketika {i>branch<i} jarak jauh telah berjalan setidaknya selama ini. Biasanya, tindakan yang baru-baru ini dijadwalkan akan mendapatkan prioritas, karena memiliki peluang terbesar untuk memenangkan perlombaan, tetapi jika sistem jarak jauh terkadang mengalami hang atau memerlukan waktu lebih lama, hal ini dapat membuat build berjalan. Ini tidak diaktifkan secara {i>default<i}, karena dapat menyembunyikan masalah dengan sistem jarak jauh yang harus diperbaiki. Pastikan untuk memantau performa sistem jarak jauh jika Anda mengaktifkan opsi ini.

--experimental_dynamic_ignore_local_signals dapat digunakan untuk mengizinkan remote mengambil alih ketika spawn lokal keluar karena adanya sinyal yang diberikan. Ini adalah terutama berguna bersama dengan batas resource worker (lihat --experimental_worker_memory_limit_mb, --experimental_worker_sandbox_hardening, dan --experimental_sandbox_memory_limit_mb)), di mana proses pekerja dapat dihentikan ketika mereka menggunakan terlalu banyak resource.

Profil rekaman aktivitas JSON berisi jumlah grafik yang berkaitan dengan kinerja yang dapat membantu mengidentifikasi cara untuk meningkatkan imbal balik performa dan penggunaan resource.

Pemecahan masalah

Masalah pada eksekusi dinamis dapat bersifat halus dan sulit di-debug, karena hanya dapat terlihat dalam beberapa kombinasi tertentu dari eksekusi lokal dan jarak jauh. --debug_spawn_scheduler menambahkan output ekstra dari eksekusi dinamis yang dapat membantu men-{i>debug<i} masalah ini. Anda juga dapat menyesuaikan Flag --dynamic_local_execution_delay dan jumlah tugas jarak jauh vs. lokal yang membuatnya lebih mudah untuk merekonstruksi masalah.

Jika Anda mengalami masalah dengan eksekusi dinamis menggunakan strategi standalone, coba jalankan tanpa --experimental_local_lockfree_output, atau jalankan tindakan lokal Anda dengan sandbox. Ini mungkin sedikit memperlambat build Anda (lihat di atas jika Anda menggunakan Mac atau Windows), tetapi menghapus beberapa kemungkinan penyebab kegagalan.