Device driver pada Linux, hampir selalu harus berhadapan dengan "external world" atau dunia luar yang mana untuk "mengisyaratkan" kalau suatu event telah terjadi, seperti memberi "pemberitahuan" pada network interface kalau ada paket baru yang telah di terima, paket telah berhasil dikirim. Intinya untuk menghandle suatu event yang terjadi tidak tentu kapan.
Bisa di ibaratkan seperti saat pertandingan olahraga, ketika ada yang melakukan pelanggaran maka wasit akan membunyikan peluit, dan "respon" dari bunyi peluit tadi biasanya pertandingan di hentikan sejenak dan mengedengarkan keputusan wasit. Yup, interupsi adalah sinyal yang di kirimkan agar mendapat perhatian dari prosesor. Interupsi biasanya di generate oleh hardware
Pada prakteknya, selain meregister nomor interupsi dan handlernya, kita juga harus menginstruksikan hardwarenya agar menggenerate interupsi, dengan mengeset bit-bit pada port (dalam hal ini paralel port). kodingnya biasanya seperti :
Dikutip dari LDD versi 3, tapi komputer zaman sekarang sudah sangat jarang sekali yang mempunyai paralel port, untuk keperluan peripheral kebanyakan sudah menggunakan USB, dan yang kali ini akan kita bahas adalah interupsi sharing, jadi kita tidak perlu meregister nomor interupsi yang akan kita pakai, tapi kita akan numpang dari line interupsi yang sudah terdarftar.
Interupsi-interupsi yang sedang aktif bisa di lihat di /proc/interrupts. Contoh isinya adalah sebagai berikut :
CPU0 CPU1 CPU2 CPU3
0: 21 0 0 0 IO-APIC-edge timer
1: 5894 0 0 0 IO-APIC-edge i8042
8: 1 0 0 0 IO-APIC-edge rtc0
9: 423 0 0 0 IO-APIC-fasteoi acpi
12: 2988 0 0 0 IO-APIC-edge i8042
16: 178696 0 21924 0 IO-APIC-fasteoi ehci_hcd:usb1
nomor paling kiri seperti "0:", "12:" adalah nomor interupsi yang sedang di gunakan, 4 angka setelahnya adalah jumlah banyaknya interupsi yang telah di generate oleh masing-masing CPU mulai dari saat pertama kali booting sampai sekarang. Dan 2 paling ujung kanan adalah pengontrol interupsi dan "nama" interupsi yang terdaftar untuk menfollow pada interupsi tersebut.
Sebagai awalan, untuk menghandle interupsi yang di generate CPU kita harus meregister handler, nomor interupsi yang dinginkan dan sebagainya, method yang di gunakana adalah :
irq = nomor interupsi yang ingin di register
handler= handler interupsi
flags= bit mask untuk settingan interupsi kita, yang tersedia adalah
Dikutip dari interrupt.h dari source code kernel linux
*name = "nama" untuk interupsi yang kita register
dev = unique identifier, berguna untuk share interupsi
Karena kita membahasa share interupsi, maka flags IRQF_SHARED wajib di set dan dev juga tidak boleh NULL. Jadi sebagai contoh :
Disini, kita memakai tasklet untuk melakukan handle yang sebenarnya, handler inter cuma menyerahkan task yang sebenarnya ke tasklet, karena handler interupsi tidak bisa menghandle proses yang panjang agar interupnya tidak terblok terlalu lama (saat dihandle, interupsi yang akan datang akan di blok). Inilah yang dinamakan dengan top halves dan bottom halves, top halves disini adalah fungsi inter dan bottom halvesnya adalah fungsi tasking. Isi dari tasking adalah sebagai berikut :
Lebih detil tentang tasklet akan dibahas di waktu yang lain, jadi kode lengkapnya adalah sebagai berikut :
Silahkan di coba, tapi sebelumnya harus buat struct sendiri dulu untuk variabel ss. di waktu lain mungkin akan dibahas lebih lanjut tentang tasklet dan workqueue, bottomhalves lain selain tasklet.
Sekian
Komentar
Posting Komentar