Panggilan sistem tidak ditangani seperti panggilan fungsi biasa. Dibutuhkan kode khusus untuk melakukan transisi dari ruang pengguna ke ruang kernel, pada dasarnya sedikit kode rakitan inline yang disuntikkan ke program Anda di situs panggilan. Kode samping kernel yang "menangkap" panggilan sistem juga merupakan hal-hal tingkat rendah yang mungkin tidak perlu Anda pahami secara mendalam, setidaknya pada awalnya.
Di include/linux/syscalls.h
bawah direktori sumber kernel Anda, Anda menemukan ini:
asmlinkage long sys_mkdir(const char __user *pathname, int mode);
Kemudian di /usr/include/asm*/unistd.h
, Anda menemukan ini:
#define __NR_mkdir 83
__SYSCALL(__NR_mkdir, sys_mkdir)
Kode ini katakan mkdir(2)
adalah system call # 83. Dengan kata lain, panggilan sistem dipanggil dengan nomor, bukan dengan alamat seperti panggilan fungsi normal dalam program Anda sendiri atau ke fungsi di perpustakaan yang ditautkan dengan program Anda. Kode lem inline assembly yang saya sebutkan di atas menggunakan ini untuk melakukan transisi dari ruang pengguna ke kernel, dengan mengambil parameter Anda.
Sedikit bukti lain yang agak aneh di sini adalah tidak selalu ada daftar parameter yang ketat untuk panggilan sistem:, open(2)
misalnya, dapat mengambil 2 atau 3 parameter. Itu berarti open(2)
adalah kelebihan beban , fitur C ++, bukan C, namun antarmuka syscall adalah C-kompatibel. (Ini bukan hal yang sama dengan fitur varargs C , yang memungkinkan fungsi tunggal untuk mengambil sejumlah variabel argumen.)
Untuk menjawab pertanyaan pertama Anda, tidak ada file tunggal di mana mkdir()
ada. Linux mendukung banyak sistem file yang berbeda dan masing-masing memiliki implementasi sendiri operasi "mkdir". Lapisan abstraksi yang memungkinkan kernel menyembunyikan semua yang ada di balik panggilan sistem tunggal disebut VFS . Jadi, Anda mungkin ingin mulai menggali di fs/namei.c
, dengan vfs_mkdir()
. Implementasi aktual dari kode modifikasi sistem file tingkat rendah ada di tempat lain. Misalnya, implementasi ext4 disebut ext4_mkdir()
, didefinisikan dalam fs/ext4/namei.c
.
Adapun pertanyaan kedua Anda, ya ada pola untuk semua ini, tetapi tidak ada aturan tunggal. Apa yang sebenarnya Anda butuhkan adalah pemahaman yang cukup luas tentang cara kerja kernel untuk mencari tahu di mana Anda harus mencari panggilan sistem tertentu. Tidak semua panggilan sistem melibatkan VFS, jadi rantai panggilan sisi-kernel tidak semuanya dimulai fs/namei.c
. mmap(2)
, misalnya, dimulai mm/mmap.c
, karena ini adalah bagian dari subsistem manajemen memori ("mm") dari kernel.
Saya sarankan Anda mendapatkan salinan " Memahami Kernel Linux " oleh Bovet dan Cesati.