Jika saya menulis program C dan mengkompilasinya ke .exe
file, .exe
file tersebut berisi instruksi mesin mentah ke CPU. (Kupikir).
Jika demikian, bagaimana mungkin bagi saya untuk menjalankan file yang dikompilasi di komputer yang menjalankan versi Windows modern? Setiap keluarga CPU memiliki set instruksi yang berbeda. Jadi bagaimana mungkin komputer yang menjalankan OS yang sesuai dapat memahami instruksi dalam .exe
file saya , terlepas dari CPU fisiknya?
Juga, sering di situs web di halaman "unduh" pada beberapa aplikasi, Anda memiliki unduhan untuk Windows, untuk Linux, dan untuk Mac (seringkali dua unduhan untuk setiap OS, untuk komputer 86 dan 64 bit). Mengapa tidak ada lebih banyak unduhan, untuk setiap keluarga CPU?
low-level
cpu
machine-code
Aviv Cohn
sumber
sumber
Jawaban:
Executables tergantung pada OS dan CPU:
Set Instruksi: Instruksi biner dalam executable didekodekan oleh CPU berdasarkan beberapa set instruksi. Sebagian besar CPU konsumen mendukung set instruksi x86 ("32bit") dan / atau AMD64 ("64bit"). Suatu program dapat dikompilasi untuk salah satu dari set instruksi ini, tetapi tidak keduanya. Ada ekstensi untuk set instruksi ini; dukungan untuk ini dapat ditanyakan saat runtime. Ekstensi semacam itu menawarkan dukungan SIMD, misalnya. Mengoptimalkan kompiler dapat mencoba memanfaatkan ekstensi ini jika ada, tetapi biasanya juga menawarkan jalur kode yang berfungsi tanpa ekstensi apa pun.
Binary Format: Eksekusi harus sesuai dengan format biner tertentu, yang memungkinkan sistem operasi memuat, menginisialisasi, dan memulai program dengan benar. Windows terutama menggunakan format Portable Executable, sedangkan Linux menggunakan ELF.
API Sistem: Program ini mungkin menggunakan pustaka, yang harus ada pada sistem pelaksana. Jika suatu program menggunakan fungsi dari Windows API, itu tidak dapat dijalankan di Linux. Di dunia Unix, API sistem operasi pusat telah distandarisasi untuk POSIX: program yang hanya menggunakan fungsi POSIX akan dapat dijalankan pada sistem Unix yang sesuai, seperti Mac OS X dan Solaris.
Jadi jika dua sistem menawarkan API dan pustaka sistem yang sama, jalankan pada set instruksi yang sama, dan gunakan format biner yang sama, maka sebuah program yang dikompilasi untuk satu sistem juga akan berjalan pada yang lain.
Namun, ada beberapa cara untuk mencapai lebih banyak kompatibilitas:
Sistem yang berjalan pada set instruksi AMD64 umumnya juga akan menjalankan executable x86. Format biner menunjukkan mode mana yang harus dijalankan. Menangani program 32bit dan 64bit memerlukan upaya tambahan dari sistem operasi.
Beberapa format biner memungkinkan file berisi beberapa versi program, dikompilasi untuk set instruksi yang berbeda. "Binari gemuk" seperti itu didorong oleh Apple saat mereka beralih dari arsitektur PowerPC ke x86.
Beberapa program tidak dikompilasi ke kode mesin, tetapi ke beberapa representasi perantara. Ini kemudian diterjemahkan dengan cepat ke instruksi aktual, atau mungkin ditafsirkan. Ini membuat program independen dari arsitektur spesifik. Strategi seperti itu digunakan pada UCSD p-System.
Satu sistem operasi dapat mendukung berbagai format biner. Windows cukup kompatibel ke belakang dan masih mendukung format dari era DOS. Di Linux, Wine memungkinkan format Windows untuk dimuat.
API satu sistem operasi dapat diterapkan kembali untuk OS host lain. Pada Windows, Cygwin dan subsistem POSIX dapat digunakan untuk mendapatkan (kebanyakan) lingkungan yang sesuai dengan POSIX. Di Linux, Wine menambah banyak API Windows.
Pustaka lintas-platform memungkinkan program untuk independen dari OS API. Banyak bahasa pemrograman memiliki pustaka standar yang mencoba untuk mencapai hal ini, misalnya Java dan C.
Sebuah emulator mensimulasikan sistem yang berbeda dengan parsing format biner asing, menafsirkan petunjuk, dan menawarkan implementasi ulang dari semua API yang diperlukan. Emulator biasanya digunakan untuk menjalankan game Nitendo lama di PC modern.
sumber
99% PC saat ini yang menjalankan Windows memiliki prosesor 64 bit, yang juga mampu menjalankan perangkat lunak 32 bit. Satu persen lainnya memiliki prosesor 32 bit. Jadi perangkat lunak yang dibangun untuk prosesor 32 bit berjalan di mana-mana. Perangkat lunak yang dibangun untuk prosesor 64 bit berjalan pada setiap PC yang menjadi perhatian pembuat perangkat lunak.
MacOS X dan iOS mendukung "fat binaries" - apa yang Anda unduh sebenarnya dapat berisi versi untuk prosesor yang berbeda. Tidak ada yang membangun aplikasi untuk prosesor PowerPC lagi, tetapi pada beberapa titik beberapa tahun yang lalu sebuah executable dapat berisi PowerPC, Intel 32 bit, dan versi Intel 64 bit, dan yang tepat akan dieksekusi. Di iOS saat ini, ketika Anda mengunduh aplikasi, Anda akan mendapatkan versi yang sesuai untuk prosesor di perangkat Anda. Unduh di perangkat yang berbeda, dan Anda mendapatkan versi yang berbeda. Sama sekali tidak terlihat oleh pengguna.
sumber
Exe berisi informasi lebih dari sekadar kode mesin mentah. OS membaca ini ketika memuatnya dan dapat mengetahui bagaimana seharusnya dijalankan.
Ketika Anda mengkompilasi Anda umumnya menetapkan target CPU, jika Anda tidak kompiler akan memilih CPU Anda saat ini dan akan membatasi diri untuk hanya memilih instruksi yang umum untuk CPU Anda dan versi yang lebih lama. Jika Anda ingin menggunakan instruksi baru yang mewah yang khusus untuk revisi tertentu dari target CPU Anda, Anda bisa memberi tahu kompiler atau secara manual kode itu dengan baik kode intrinsik atau inline assembly. Namun program Anda akan macet jika dijalankan pada CPU yang tidak mendukung instruksi itu.
sumber