Bahkan program Haskell yang sangat kecil berubah menjadi executable raksasa.
Saya telah menulis sebuah program kecil, yang dikompilasi (dengan GHC) ke biner dengan ukuran 7 MB!
Apa yang dapat menyebabkan program Haskell kecil untuk dikompilasi ke biner besar?
Apa, jika ada, yang bisa saya lakukan untuk mengurangi ini?
strip
pada biner untuk menghapus tabel simbol.strip test
. Perintah ini menghapus beberapa informasi debug dari program dan membuatnya lebih kecil.data M3 = M3 !V3 !V3 !V3
dandata V3 = V3 !Float !Float !Float
. Kompilasi denganghc -O2 -funbox-strict-fields
.Jawaban:
Mari kita lihat apa yang terjadi, coba
Anda melihat dari
ldd
output bahwa GHC telah menghasilkan executable yang terhubung secara dinamis, tetapi hanya perpustakaan C yang terhubung secara dinamis ! Semua perpustakaan Haskell disalin dalam kata demi kata.Selain itu: karena ini adalah aplikasi intensif grafis, saya pasti akan mengompilasinya
ghc -O2
Ada dua hal yang bisa Anda lakukan.
Simbol pengupasan
Solusi mudah: lepaskan biner:
Lepaskan simbol dari file objek. Biasanya hanya diperlukan untuk debugging.
Pustaka Haskell yang ditautkan secara dinamis
Baru-baru ini, GHC telah mendapatkan dukungan untuk menghubungkan dinamis kedua perpustakaan C dan Haskell . Kebanyakan distro sekarang mendistribusikan versi GHC yang dibangun untuk mendukung tautan dinamis perpustakaan Haskell. Pustaka Haskell bersama dapat dibagikan di antara banyak program Haskell, tanpa menyalinnya ke dalam executable setiap kali.
Pada saat penulisan Linux dan Windows didukung.
Agar perpustakaan Haskell terhubung secara dinamis, Anda harus mengompilasinya
-dynamic
, seperti:Juga, semua perpustakaan yang ingin Anda bagikan harus dibangun dengan
--enabled-shared
:Dan Anda akan berakhir dengan executable yang jauh lebih kecil, yang memiliki dependensi C dan Haskell yang diselesaikan secara dinamis.
Dan, voila!
yang bisa Anda cabut menjadi lebih kecil:
Eksekusi weensy eensy, dibangun dari banyak potongan C dan Haskell yang terhubung secara dinamis:
Satu poin terakhir: bahkan pada sistem dengan tautan statis saja, Anda dapat menggunakan -sit-objs , untuk mendapatkan satu file .o per fungsi tingkat atas, yang selanjutnya dapat mengurangi ukuran perpustakaan yang terhubung secara statis. Perlu GHC dibangun dengan -sit-objs, yang lupa dilakukan oleh beberapa sistem.
sumber
cabal install
menghapus biner yang diinstal secara default?enable-shared
telah dipertimbangkan. launchpad.net/ubuntu/+source/pandoc/+bugsHaskell menggunakan tautan statis secara default. Ini, seluruh ikatan OpenGL disalin ke program Anda. Karena mereka cukup besar, program Anda akan meningkat tidak perlu. Anda dapat mengatasi ini dengan menggunakan tautan dinamis, meskipun tidak diaktifkan secara default.
sumber
--enabled-shared
" jadi jika Platform Haskell Anda dilengkapi dengan perpustakaan yang dibangun tanpa--enabled shared
Anda harus mengkompilasi ulang perpustakaan dasar yang bisa sangat menyakitkan.