Pernah membayangkan bagaimana prosesor bisa tetap bekerja ketika salah satu instruksi sedang menunggu data? Kalau CPU harus selalu menunggu instruksi sebelumnya selesai, tentu banyak waktu yang terbuang.
Di sinilah konsep Out-of-Order Execution menjadi penting.
Out-of-Order Execution adalah teknik pada mikroarsitektur prosesor yang memungkinkan CPU menjalankan instruksi yang sudah siap terlebih dahulu, meskipun urutannya berada setelah instruksi lain dalam program. Teknik ini banyak digunakan bersama superscalar processor untuk memaksimalkan pemakaian execution unit dan meningkatkan throughput CPU.
Menariknya, walaupun instruksi bisa dikerjakan tidak sesuai urutan kedatangannya, hasil akhir program tetap harus terlihat benar sesuai aturan arsitektur CPU.
Lalu, bagaimana sebenarnya Out-of-Order Execution bekerja? Apa hubungannya dengan superscalar? Mari kita bahas dengan cara yang sederhana.
Apa Itu Out-of-Order Execution?
Out-of-Order Execution adalah teknik eksekusi instruksi di mana prosesor dapat menjalankan instruksi yang sudah siap tanpa harus selalu menunggu instruksi sebelumnya selesai.
Pada eksekusi biasa, instruksi cenderung diproses mengikuti urutan:
Instruksi A
↓
Instruksi B
↓
Instruksi C
↓
Instruksi D
Jika Instruksi A sedang menunggu data dari memori, instruksi berikutnya bisa ikut tertahan.
Dengan Out-of-Order Execution, CPU dapat melihat instruksi mana yang sudah memiliki data dan resource yang diperlukan.
Misalnya:
Instruksi A → Menunggu data
Instruksi B → Siap
Instruksi C → Siap
Instruksi D → Menunggu A
CPU dapat menjalankan B atau C terlebih dahulu jika tidak ada ketergantungan yang menghalanginya.
Sederhananya:
Tidak harus menunggu instruksi sebelumnya selesai jika instruksi berikutnya sudah siap dan aman untuk dijalankan.
Mengapa Out-of-Order Execution Dibutuhkan?
CPU modern memiliki banyak komponen yang dapat bekerja secara paralel. Jika salah satu instruksi sedang menunggu sesuatu, membiarkan seluruh execution unit menganggur tentu bukan pilihan yang efisien.
Contohnya, sebuah instruksi melakukan akses memori:
Load data → Menunggu data dari cache/memori
Prosesor dapat menggunakan waktu tunggu tersebut untuk mengerjakan instruksi lain yang sudah siap.
Dengan begitu:
Tanpa OoO:
A menunggu → CPU ikut menunggu
Dengan OoO:
A menunggu → B dan C dikerjakan
Teknik inilah yang membantu CPU memanfaatkan sumber daya hardware secara lebih maksimal.
Cara Kerja Out-of-Order Execution
Secara sederhana, alur kerja Out-of-Order Execution dapat digambarkan seperti:
Fetch → Decode → Dispatch → Schedule → Execute → Write Back → Retire
Setiap prosesor dapat memiliki implementasi yang berbeda, tetapi konsep dasarnya kurang lebih seperti itu.
1. Instruction Fetch
CPU mengambil instruksi dari instruction cache.
Misalnya program memiliki:
A
B
C
D
Instruksi tersebut kemudian masuk ke pipeline untuk diproses.
2. Decode
CPU menerjemahkan instruksi untuk mengetahui:
- Operasi yang harus dilakukan
- Register yang digunakan
- Data yang dibutuhkan
- Jenis execution unit yang diperlukan
Setelah itu, instruksi disiapkan untuk tahap berikutnya.
3. Dispatch
Instruksi dikirim ke struktur internal CPU untuk menunggu sampai semua kondisi yang diperlukan terpenuhi.
CPU mulai memantau ketergantungan data dan resource yang diperlukan.
4. Schedule
Pada tahap ini, CPU menentukan instruksi mana yang sudah siap dieksekusi.
Misalnya:
A → Menunggu data
B → Siap
C → Siap
D → Menunggu hasil A
CPU dapat memilih B atau C terlebih dahulu.
Inilah bagian penting dari konsep Out-of-Order Execution.
5. Execute
Instruksi yang sudah siap dikirim ke execution unit yang sesuai.
Contohnya:
B → Integer ALU
C → Floating Point Unit
Jika terdapat beberapa execution unit, beberapa instruksi dapat dieksekusi secara bersamaan.
6. Write Back
Setelah instruksi selesai, hasilnya dikirim kembali ke struktur internal CPU atau register yang sesuai.
Hasil tersebut nantinya dapat digunakan oleh instruksi lain yang bergantung padanya.
7. Retire atau Commit
Walaupun instruksi dapat dieksekusi dalam urutan yang berbeda, CPU harus memastikan hasil akhirnya tetap terlihat sesuai dengan urutan program.
Tahap retire atau commit digunakan untuk menyelesaikan instruksi secara arsitektural dengan benar.
Bagian ini sangat penting karena eksekusi tidak berurutan tidak boleh membuat program menghasilkan hasil yang salah.
Contoh Sederhana Out-of-Order Execution
Perhatikan contoh berikut:
Instruksi A → Load data
Instruksi B → A + C
Instruksi C → D + E
Instruksi B bergantung pada A karena membutuhkan hasil dari A.
Namun, Instruksi C tidak bergantung pada A.
Jika A sedang menunggu data dari memori, CPU dapat melakukan:
A → Menunggu data
B → Menunggu A
C → Eksekusi
Jadi, daripada membiarkan CPU menganggur, Instruksi C dapat dikerjakan terlebih dahulu.
Setelah data untuk A tersedia:
A → Selesai
B → Eksekusi
Cara kerja seperti inilah yang membuat CPU dapat menggunakan waktu tunggu secara lebih efektif.
Out-of-Order Execution vs In-Order Execution
Untuk memahami OoO dengan lebih jelas, kita bisa membandingkannya dengan In-Order Execution.
In-Order Execution
Instruksi dikerjakan mengikuti urutan:
A → B → C → D
Jika A berhenti karena menunggu data, instruksi setelahnya dapat ikut tertahan.
Out-of-Order Execution
CPU dapat memilih instruksi yang sudah siap:
A → Menunggu
B → Menunggu A
C → Eksekusi
D → Eksekusi
Setelah A selesai:
A → Selesai
B → Eksekusi
Perbedaannya dapat dirangkum seperti berikut:
| Aspek | In-Order | Out-of-Order |
|---|---|---|
| Urutan eksekusi | Mengikuti urutan program | Dapat berbeda dari urutan program |
| Penjadwalan | Lebih sederhana | Lebih kompleks |
| Pemanfaatan execution unit | Dapat lebih terbatas saat terjadi stall | Dapat lebih maksimal |
| Hardware | Relatif sederhana | Lebih kompleks |
| Ketergantungan data | Menjadi hambatan langsung | Dapat dikelola dengan teknik tertentu |
| Retire | Mengikuti urutan | Tetap menjaga urutan arsitektural |
Hubungan Out-of-Order Execution dengan Superscalar
Out-of-Order Execution memiliki hubungan yang sangat erat dengan superscalar processor.
Superscalar memungkinkan CPU mengeksekusi beberapa instruksi secara paralel menggunakan beberapa execution unit.
Masalahnya, tidak semua instruksi siap dieksekusi pada waktu yang sama.
Di sinilah Out-of-Order Execution membantu.
Contohnya sebuah CPU memiliki dua execution unit:
ALU 1
ALU 2
Kemudian terdapat:
Instruksi A → Menunggu data
Instruksi B → Siap
Instruksi C → Siap
Dengan superscalar, CPU memiliki kemampuan menjalankan lebih dari satu instruksi.
Dengan Out-of-Order Execution, CPU dapat memilih B dan C karena keduanya sudah siap.
Hasilnya:
A → Menunggu
B → ALU 1
C → ALU 2
Jadi, secara sederhana:
Superscalar menyediakan kemampuan untuk menjalankan beberapa instruksi secara paralel.
Out-of-Order Execution membantu menentukan instruksi mana yang bisa dijalankan lebih dahulu ketika instruksi tidak semuanya siap.
Keduanya saling melengkapi.
Apa Itu Instruction-Level Parallelism?
Out-of-Order Execution juga berkaitan erat dengan Instruction-Level Parallelism (ILP).
ILP merupakan kemampuan untuk menemukan instruksi yang dapat dijalankan secara paralel atau tumpang tindih.
Contohnya:
A = B + C
D = E + F
G = H × I
Instruksi tersebut relatif independen.
CPU dapat melihat adanya peluang untuk menjalankan beberapa instruksi secara paralel.
Namun, jika terdapat:
A = B + C
D = A + E
Instruksi D harus menunggu hasil A.
CPU tidak bisa sembarangan menjalankan D terlebih dahulu.
Karena itu, Out-of-Order Execution harus tetap memperhatikan dependency antar-instruksi.
Peran Register Renaming
Salah satu teknik yang sering digunakan bersama Out-of-Order Execution adalah register renaming.
Register renaming digunakan untuk mengurangi konflik akibat penggunaan register yang sama oleh beberapa instruksi.
Misalnya:
Instruksi A → menggunakan R1
Instruksi B → menulis R1
Pada kondisi tertentu, penggunaan register yang sama dapat menyebabkan dependency semu.
CPU dapat menggunakan register fisik yang berbeda untuk memisahkan penggunaan tersebut.
Sederhananya:
R1 → Physical Register P10
R1 → Physical Register P25
Walaupun program melihat register arsitektural R1, CPU dapat menggunakan register fisik yang berbeda di dalam hardware.
Teknik ini membantu prosesor melakukan eksekusi instruksi secara lebih fleksibel.
Peran Reservation Station
Dalam banyak desain CPU Out-of-Order, terdapat struktur yang dikenal sebagai reservation station atau mekanisme penjadwalan yang sejenis.
Struktur ini membantu menyimpan instruksi yang belum siap dieksekusi.
Misalnya:
Instruksi A → Menunggu data
Instruksi B → Siap
Instruksi C → Menunggu data
Instruksi D → Siap
CPU dapat memilih B dan D untuk dieksekusi sementara A dan C masih menunggu.
Ketika data yang dibutuhkan tersedia, instruksi tersebut dapat menjadi siap untuk dijalankan.
Reorder Buffer dan Pentingnya Urutan Hasil
Kalau instruksi boleh dieksekusi tidak berurutan, bagaimana CPU memastikan hasil akhirnya tetap benar?
Salah satu komponen yang berperan adalah Reorder Buffer (ROB).
Reorder Buffer dapat digunakan untuk melacak instruksi yang sedang diproses dan membantu memastikan hasil dapat diselesaikan dalam urutan arsitektural yang benar.
Misalnya:
Urutan program:
A → B → C → D
Urutan eksekusi:
A → C → D → B
Walaupun C dan D selesai lebih dahulu, CPU tetap perlu memastikan hasil program terlihat seolah-olah instruksi diproses sesuai aturan arsitektur.
Konsep ini sering disebut sebagai in-order retirement.
Out-of-Order Execution dan Pipeline
Out-of-Order Execution juga berhubungan dengan pipelining.
Pipelining memungkinkan beberapa instruksi berada pada tahap pipeline yang berbeda secara bersamaan.
Namun, pipeline dapat mengalami stall ketika instruksi tertentu menunggu data.
Dengan Out-of-Order Execution, CPU dapat mencari instruksi lain yang sudah siap sehingga beberapa bagian pipeline dan execution unit tetap dapat bekerja.
Contohnya:
Pipeline:
A → Menunggu
B → Siap
C → Siap
↓
OoO Scheduler
↓
B → Execute
C → Execute
A → Menunggu data
Dengan pendekatan tersebut, waktu tunggu dapat dimanfaatkan untuk pekerjaan lain.
Hubungan dengan Pipeline Hazard
Sebelumnya kita sudah membahas tiga jenis pipeline hazard:
- Data Hazard
- Control Hazard
- Structural Hazard
Out-of-Order Execution memiliki hubungan khusus dengan data hazard.
Misalnya:
A → menghasilkan R1
B → membutuhkan R1
C → tidak bergantung pada A
CPU tidak dapat menjalankan B sebelum R1 tersedia.
Tetapi CPU dapat menjalankan C jika semua resource yang dibutuhkan tersedia.
Dengan begitu, CPU tidak perlu menghentikan seluruh proses hanya karena A sedang menunggu.
Keunggulan Out-of-Order Execution
Teknik ini memiliki beberapa manfaat penting.
1. Memaksimalkan Execution Unit
CPU dapat mencari pekerjaan lain ketika sebuah instruksi sedang menunggu.
2. Mengurangi Dampak Stall
Tidak semua instruksi harus ikut berhenti hanya karena satu instruksi mengalami hambatan.
3. Meningkatkan Instruction-Level Parallelism
CPU dapat menemukan lebih banyak peluang untuk menjalankan instruksi secara paralel.
4. Mendukung Superscalar Processor
Out-of-Order Execution membantu CPU superscalar menggunakan beberapa execution unit secara lebih efektif.
5. Memanfaatkan Waktu Tunggu Memori
Akses memori dapat memiliki latensi yang jauh lebih tinggi dibandingkan beberapa operasi internal CPU. OoO memungkinkan CPU mengerjakan instruksi lain selama menunggu data tersedia.
Kekurangan Out-of-Order Execution
Di balik manfaatnya, Out-of-Order Execution juga membuat desain CPU menjadi lebih kompleks.
1. Hardware Lebih Kompleks
CPU membutuhkan berbagai struktur tambahan untuk mengatur instruksi.
2. Konsumsi Daya Lebih Tinggi
Logika penjadwalan, register renaming, tracking dependency, dan struktur lainnya membutuhkan resource tambahan.
3. Desain Lebih Sulit
CPU harus memastikan instruksi yang dieksekusi tidak berurutan tetap menghasilkan perilaku program yang benar.
4. Tidak Semua Instruksi Bisa Dijalankan Paralel
Dependency data dan kondisi lainnya tetap dapat membatasi tingkat parallelism.
Jadi, Out-of-Order Execution bukan berarti CPU bebas menjalankan semua instruksi sesuka hati.
Contoh Alur Sederhana CPU Modern
Secara sederhana, hubungan berbagai teknik tersebut dapat digambarkan seperti ini:
Instruction Fetch
↓
Instruction Decode
↓
Instruction Dispatch
↓
Dependency Check
↓
Out-of-Order Scheduling
↓
Superscalar Execution
↓
Write Back
↓
Reorder / Retire
Di dalam proses tersebut, CPU juga dapat menggunakan:
Branch Prediction
Register Renaming
Cache
Reservation Station
Reorder Buffer
Semua mekanisme tersebut bekerja bersama untuk membuat eksekusi instruksi menjadi lebih efisien.
Apakah Out-of-Order Berarti CPU Menjalankan Program Secara Acak?
Tidak.
Ini adalah salah satu kesalahpahaman yang sering muncul.
Out-of-Order Execution bukan berarti CPU mengabaikan urutan program.
CPU hanya mengubah urutan eksekusi internal ketika hal tersebut aman dilakukan.
Hasil akhir tetap harus mengikuti aturan arsitektur prosesor.
Contohnya:
Program:
A → B → C
Eksekusi internal:
A → C → B
Hasil yang terlihat oleh program:
Tetap sesuai aturan A → B → C
Dengan demikian, Out-of-Order Execution dapat meningkatkan efisiensi tanpa mengubah logika program.
Out-of-Order Execution pada CPU Modern
Teknik Out-of-Order Execution banyak digunakan dalam desain CPU modern, terutama pada prosesor yang membutuhkan performa tinggi.
Teknik ini biasanya bekerja bersama:
- Pipelining
- Superscalar execution
- Branch prediction
- Register renaming
- Reorder buffer
- Cache
- Speculative execution
- Instruction-level parallelism
Masing-masing memiliki peran berbeda, tetapi semuanya saling berkaitan dalam meningkatkan efisiensi pemrosesan instruksi.
Karena itu, memahami Out-of-Order Execution akan membuat kita lebih mudah memahami bagaimana mikroarsitektur CPU modern bekerja.
Kesimpulan
Out-of-Order Execution adalah teknik yang memungkinkan prosesor menjalankan instruksi yang sudah siap tanpa harus selalu menunggu instruksi sebelumnya selesai.
Teknik ini sangat berguna ketika CPU menghadapi instruksi yang sedang menunggu data, terutama dari cache atau memori. Daripada membiarkan execution unit menganggur, CPU dapat menjalankan instruksi lain yang tidak memiliki dependency yang menghalanginya.
Out-of-Order Execution memiliki hubungan erat dengan superscalar processor. Superscalar menyediakan kemampuan menjalankan beberapa instruksi secara paralel, sedangkan Out-of-Order Execution membantu CPU memilih instruksi yang siap untuk memanfaatkan execution unit tersebut.
Walaupun eksekusi internal dapat dilakukan tidak berurutan, CPU tetap harus memastikan hasil akhir terlihat sesuai dengan aturan arsitektur. Karena itu, teknik seperti register renaming, scheduling, reorder buffer, dan in-order retirement menjadi bagian penting dalam implementasinya.
Dengan memahami Out-of-Order Execution, kita bisa melihat bahwa performa prosesor modern bukan hanya ditentukan oleh clock speed atau jumlah core, tetapi juga oleh bagaimana CPU mengatur instruksi di dalam mikroarsitekturnya.
