[Linux] Membuat dan Menerapkan Patch Kernel


Patch pada dasarnya merupakan sebuah file yang bertujuan untuk membandingkan dan mengubah dua benda yang berbeda agar menjadi serupa. Hal ini juga dilakukan pada kernel Linux. Ketika kernel terdapat (sedikit) perubahan, maka Anda cukup mengirimkan patch dari kernel yang ada, dengan demikian tidak perlu meng-upload keseluruhan kernel. File patch umumnya relatif kecil dibandingkan tarball keseluruhan kernel.

Membuat Patch Kernel

  1. Pastikan Anda memiliki source kernel yang masih belum dimodifikasi (vanilla kernel).
    Misalkan Anda mempunyai vanilla kernel pada direktori ~/kernel/linux-2.6.39.4-vanilla, lalu masuk ke direktori ~/kernel.

    $ cd ~/kernel
  2. Jika Anda belum melakukan modifikasi, lakukan penggandaan kernel vanilla tersebut, misalnya dengan nama linux-2.6.39.4-tubes.
    $ cp -rf linux-2.6.39.4-vanilla linux-2.6.39.4-tubes
  3. Pastikan source kernel yang dimodifikasi telah bersih dari file-file temporer yang tidak diperlukan dalam perbandingan dengan source kernel vanilla.
    Beberapa editor teks (termasuk gedit) menambahkan berkas back-up dengan nama file yang diakhiri dengan ~. Untuk menghapusnya,

    $ rm `find . –name *~`
  4. Lakukan perbandingan antara dua direktori sekaligus membuat patch file-nya.
    $ diff -ruN linux-2.6.39.4-vanilla linux-2.6.39.4-tubes > patch-linux-2.6.39.4-vanilla-to-tubes

    Perintah di atas akan membandingkan linux-2.6.39.4-vanilla dengan linux-2.6.39.4-tubes dengan linux-2.6.39.4-vanilla sebagai kode sumber yang asli.
    Bagian patch-linux-2.6.39.4-vanilla-to-tubes merupakan file output dari perbandingan yang sekaligus merupakan patch file.

Menerapkan Patch Kernel

  1. Misalkan Anda memodifikasi dari linux-2.6.39.4-vanilla menjadi linux-2.6.39.4-tubes. Anda dapat menduplikasi linux-2.6.39.4-vanilla terlebih dahulu, misalnya menjadi linux-2.6.39.4-patch-vanilla-to-tubes.
    $ cp -rf linux-2.6.39.4-vanilla linux-2.6.39.4-patch-vanilla-to-tubes
  2. Lakukan patching ke linux-2.6.39.4-patch-vanilla-to-tubes, misalkan patch file-nya adalah patch-linux-2.6.39.4-vanilla-to-tubes.
    $ patch -p1 -d linux-2.6.39.4-patch-vanilla-to-tubes < patch-linux-2.6.39.4-vanilla-to-tubes
  3. Direktori linux-2.6.39.4-patch-vanilla-to-tubes akan sama dengan linux-2.6.39.4-tubes. Anda tinggal melakukan kompilasi kernel terhadap patch tersebut.

[Linux] Menambahkan System Call pada Kernel Linux 2.6


Pehatian! Cara ini sudah pernah diuji dan berhasil. Kesalahan mungkin dapat terjadi, read at your own risk.

Berikut ini adalah langkah untuk menambahkan system call pada kernel linux 2.6 untuk arsitektur x86 baik 32-bit maupun 64-bit. Pada tulisan ini digunakan kernel versi 2.6.39.4 pada Ubuntu 10.04. Mungkin terjadi sedikit perbedaan pada versi 2.6.x lainnya.

  1. Download kernel linux 2.6.39.4 di sini.
  2. Ekstrak file linux-2.6.39.4.tar.gz hasil download tadi ke direktori baru. Misalnya kita akan meletakan di dalam folder ~/kernel/
    $ tar zxvf linux-2.6.39.4.tar.gz -C ~/kernel/

    Maka akan terdapat direktori ~/kernel/linux-2.6.39.4

  3. Masuk ke dalam direktori hasil peng-ekstrak-an kernel tadi
    $ cd ~/kernel/linux-2.6.39.4
  4. Buat direktori baru, misalnya extsyscall. Direktori ini akan menjadi tempat untuk menambahkan kode system call kita nanti.
    $ mkdir extsyscall
  5. Buka file yang berisi daftar system call.
    $ gedit arch/x86/kernel/syscall_table_32.S
  6. Misalkan Anda ingin menambahkan fungsi baru dengan nama randodd(int *). Tambahkan baris .long sys_randodd pada akhir file. (Ganti randoodd sesuai dengan nama fungsi yang akan dibuat).
    	...
    	.long sys_prlimit64		/* 340 */
    	.long sys_name_to_handle_at
    	.long sys_open_by_handle_at
    	.long sys_clock_adjtime
    	.long sys_syncfs
    	.long sys_randodd		/* System Call Baru */
    
  7. Buka file unistd (header API sistem operasi berbasis POSIX). Akan didaftarkan system call yang akan dibuat.
    $ gedit arch/x86/include/asm/unistd_32.h

    Tambahkan baris #define __NR_randodd 345 pada akhir dari sekumpulan baris dengan format #define __NR_namasyscall xxx.
    Ganti randodd dengan nama system call yang akan dibuat.
    Ganti 345 dengan nilai terakhir dari daftar system call yang ada ditambahkan dengan 1. Pada kasus ini, system call terakhir adalah #define __NR_syncfs 344, maka system call randodd akan mendapatkan nomor system call 344 + 1 = 345.
    Selain itu juga, ganti nilai pada #define NR_syscalls 345 menjadi #define NR_syscalls 346, dengan 346 merupakan jumlah system call yang ada, yaitu nomor system call terakhir ditambahkan dengan 1, dalam kasus ini 345 (milik randodd) + 1 = 346.

    	#define __NR_fanotify_mark	339
    	#define __NR_prlimit64		340
    	#define __NR_name_to_handle_at	341
    	#define __NR_open_by_handle_at  342
    	#define __NR_clock_adjtime	343
    	#define __NR_syncfs             344
    	#define __NR_randodd       	345
    	
    	#ifdef __KERNEL__
    	
    	#define NR_syscalls 346
    	
    	#define __ARCH_WANT_IPC_PARSE_VERSION
    	#define __ARCH_WANT_OLD_READDIR
    
  8. Sekarang akan didaftarkan system call untuk sistem dengan 64-bit. Buka file unistd_64.h.
    $ gedit arch/x86/include/asm/unistd_64.h

    Tambahkan dua baris seperti pada potongan kode yang di-highlight.

    	...
    	#define __NR_prlimit64				302
    	__SYSCALL(__NR_prlimit64, sys_prlimit64)
    	#define __NR_name_to_handle_at			303
    	__SYSCALL(__NR_name_to_handle_at, sys_name_to_handle_at)
    	#define __NR_open_by_handle_at			304
    	__SYSCALL(__NR_open_by_handle_at, sys_open_by_handle_at)
    	#define __NR_clock_adjtime			305
    	__SYSCALL(__NR_clock_adjtime, sys_clock_adjtime)
    	#define __NR_syncfs                             306
    	__SYSCALL(__NR_syncfs, sys_syncfs)
    	#define __NR_randodd				307
    	__SYSCALL(__NR_randodd, sys_randodd)
    	...
    

    Perhatikan bahwa __NR_randodd mendapatkan nomor system call 307 yang merupakan lanjutan dari nomor system call terakhir yang ada.

  9. Buka file syscall.h.
    $ gedit include/linux/syscalls.h

    Tambahkan baris asmlinkage long sys_randodd(int *); sebelum #endif pada akhir file.

    ...
    asmlinkage long sys_old_mmap(struct mmap_arg_struct __user *arg);
    asmlinkage long sys_name_to_handle_at(int dfd, const char __user *name,
    										struct file_handle __user *handle,
    										int __user *mnt_id, int flag);
    asmlinkage long sys_open_by_handle_at(int mountdirfd,
    										struct file_handle __user *handle,
    										int flags);
    asmlinkage long sys_randodd(int *num);
    #endif
    
  10. Buka file Makefile pada direktori utama source.
    $ gedit Makefile

    Tambahkan extsyscall/ (direktori yang dibuat tadi) pada core-y += .

    	...
    	ifeq ($(KBUILD_EXTMOD),)
    	core-y		+= kernel/ mm/ fs/ ipc/ security/ crypto/ block/ extsyscall/
    	...
    
  11. Buat kode yang berisi syscall pada direktori extsyscall. Misalkan file kode yang dibuat bernama extsyscall.c juga.
    $ gedit extsyscall/extsyscall.c

    Kode berikut akan menghasilkan bilangan random yang selalu ganjil.

    #include <linux/linkage.h>
    #include <linux/random.h>
    
    asmlinkage long sys_randodd(int *num)
    {
    	*num = (get_random_int() << 1) + 1;
    	return 0;
    }
    
  12. Buat file Makefile pada direktori extsyscall
    $ gedit extsyscall/Makefile

    Isikan dengan

    obj-y := extsyscall.o
    
  13. Lakukan compile kernel. Cara mengompile kernel dapat dilihat di sini.

Untuk melakukan pengujian terhadap kernel yang dibuat, misalnya kita dapat membuat aplikasi yang memanfaatkan system call tersebut. Misalnya:

#include <stdio.h>
#include <linux/unistd.h>
#include <sys/syscall.h>

/* Untuk 32-Bit (sesuaikan dengan nilai yang dimasukkan sebelumnya) */
#define sys_randodd 345

/* Untuk 64-bit (sesuaikan dengan nilai yang dimasukkan sebelumnya) 
#define sys_randodd 307
*/

int main()
{
    int num;
    int i;

    for (i=0; i<100; i++)
    {
        syscall(sys_randodd, &num);
        printf("%d\n", num);
    }
    return 0;
}

[Linux] Compile Kernel Linux 2.6 pada Ubuntu 10.04


Pehatian! Cara ini sudah pernah diuji dan berhasil. Kesalahan mungkin dapat terjadi, read at your own risk.

Berikut ini adalah cara untuk meng-compile kernel linux 2.6.39.4 pada Ubuntu 10.04. Untuk kernel 2.6.x yang diinstall pada distro Linux berbasis kernel 2.x dapat mengikuti langkah ini tetapi dengan beberapa perbedaan yang perlu disesuaikan.

Persiapan

  1. Download kernel linux 2.6.39.4 di sini.
  2. Ekstrak file linux-2.6.39.4.tar.gz hasil download tadi ke direktori baru. Misalnya kita akan meletakan di dalam folder ~/kernel/
    $ tar zxvf linux-2.6.39.4.tar.gz -C ~/kernel/

    Maka akan terdapat direktori ~/kernel/linux-2.6.39.4

  3. Download paket yang dibutuhkan untuk mengompilasi kernel dengan apt-get
    $ sudo apt-get update
    $ sudo apt-get install build-essential initramfs-tools
    $ sudo apt-get install ncurses-dev

    Perintah ketiga tidak wajib untuk dijalankan. Paket ini digunakan untuk mengonfigurasi kernel sebelum dikompilasi dengan mode grafik pada terminal.

  4. Masuk ke dalam direktori hasil peng-ekstrak-an kernel tadi
    $ cd ~/kernel/linux-2.6.39.4
  5. Jalankan konfigurasi untuk mengompilasi kernel.
    $ make --jobs=`getconf _NPROCESSORS_ONLN` O=~/linux-build menuconfig

    Parameter --jobs=`getconf _NPROCESSORS_ONLN` digunakan untuk menjalankan proses konfigurasi secara multi-job untuk memaksimalkan jumlah proses yang bisa ditangani oleh prosesor sekaligus
    Parameter menuconfig digunakan untuk membuka menu konfigurasi grafik berbasis text (memerlukan ncurses-dev). Selain itu terdapat konfigurasi lainnya (baca file README).

    "make config"      Plain text interface.
    "make menuconfig"  Text based color menus, radiolists & dialogs.
    "make nconfig"     Enhanced text based color menus.
    "make xconfig"     X windows (Qt) based configuration tool.
    "make gconfig"     X windows (Gtk) based configuration tool.
    "make oldconfig"   Default all questions based on the contents of
    	your existing ./.config file and asking about
    	new config symbols.
    "make silentoldconfig"
    	Like above, but avoids cluttering the screen
    	with questions already answered.
    	Additionally updates the dependencies.
    "make defconfig"   Create a ./.config file by using the default
    	symbol values from either arch/$ARCH/defconfig
    	or arch/$ARCH/configs/${PLATFORM}_defconfig,
    	depending on the architecture.
    "make ${PLATFORM}_defconfig"
    	Create a ./.config file by using the default
    	symbol values from
    	arch/$ARCH/configs/${PLATFORM}_defconfig.
    	Use "make help" to get a list of all available
    	platforms of your architecture.
    "make allyesconfig"
    	Create a ./.config file by setting symbol
    	values to 'y' as much as possible.
    "make allmodconfig"
    	Create a ./.config file by setting symbol
    	values to 'm' as much as possible.
    "make allnoconfig" Create a ./.config file by setting symbol
    	values to 'n' as much as possible.
    "make randconfig"  Create a ./.config file by setting symbol
    	values to random values.

Compile Kernel

Setelah melakukan konfigurasi untuk compile kernel, sekarang saatnya untuk melakukan compile. Berikut diberikan dua cara untuk melakukan kompilasi kernel, yaitu dengan hanya menggunakan Makefile standar dan menggunakan Kernel Package (make-kpkg). Anda cukup mengikuti salah satu dari cara berikut.

Compile menggunakan Makefile standar

  1. Buat direktori output, misalnya di direktori ~/linux-build
    Direktori ini merupakan tempat output dari hasil compile

    $ mkdir ~/linux-build
  2. Jika berhasil, lakukan peng-compile-an.
    $ sudo make --jobs=`getconf _NPROCESSORS_ONLN` O=~/linux-build
  3. Jika berhasil, lakukan peng-install-an module.
    $ sudo make --jobs=`getconf _NPROCESSORS_ONLN` O=~/linux-build modules_install
  4. Jika berhasil, lakukan peng-install-an kernel ke komputer.
    $ sudo make --jobs=`getconf _NPROCESSORS_ONLN` O=~/linux-build install
  5. Masuk ke direktori /boot
    $ cd /boot
  6. Buat initramfs image untuk kernel yang baru ini. Initramfs merupakan arsip cpio terkompresi yang di-loadpertama kali ke RAM saat masuk ke sistem operasi.
    $ sudo mkinitramfs -o initrd.img-2.6.39.4 2.6.39.4
  7. Lakukan peng-update-an grub.Grub merupakan sebuah program bootloader.
    $ sudo update-grub
  8. Lakukan reboot dan masuk ke kernel baru yang telah di buat.

Compile menggunakan Kernel Package (make-kpkg)

  1. Download aplikasi yang dibutuhkan untuk mengompilasi kernel
  2. $ sudo apt-get install kernel-package
  3. Lakukan cleaning make-kpkg
    $ sudo make-kpkg clean
  4. Buat package yang berisi kernel image dan kernel header
    $ sudo fakeroot make-kpkg --initrd --append-to-version=-tubes kernel-image kernel-headers

    Pada bagian --append-to-version, Anda dapat mengganti teks -tubes menjadi nama versi yang mengikuti versi kernel. Tujuannya adalah untuk memberikan versi yang berbeda jika Anda mengupdate kernel sehingga kernel dengan versi yang sama tidak akan dirusak.

  5. Install paket yang telah dibuat pada langkah sebelumnya
    $ cd ..
    $ sudo dpkg -i linux-image-2.6.32-custom_2.6.32-custom-10.00.Custom_i386.deb
    $ sudo dpkg -i linux-headers-2.6.32-custom_2.6.32-custom-10.00.Custom_i386.deb
  6. Masuk ke direktori /boot
    $ cd /boot
  7. Buat initramfs image untuk kernel yang baru ini. Initramfs merupakan arsip cpio terkompresi yang di-loadpertama kali ke RAM saat masuk ke sistem operasi.
    $ sudo mkinitramfs -o initrd.img-2.6.39.4 2.6.39.4
  8. Lakukan peng-update-an grub.Grub merupakan sebuah program bootloader.
    $ sudo update-grub
  9. Lakukan reboot dan masuk ke kernel baru yang telah di buat.

[Fedora] Menggunakan yum melalui Proxy Server


Pada linux berbasis RPM terdapat yum. yum merupakan package manager yang digunakan untuk meng-install, meng-update, and menghapus package/aplikasi. Untuk menggunakan yum, Anda harus terkoneksi dengan internet. Jika Anda terhalang proxy, berikut ini adalah cara mengatur agar yum dapat mengakses internet melalui proxy server.

Untuk melakukan konfigurasi hanya sesekali, Anda cukup menambahkan setting proxy ke environment. (Lihat solusi kedua untuk konfigurasi lebih permanen di bawah). Caranya adalahs sebagai berikut.

  1. Buka terminal, ketikan sebagai berikut
    export http_proxy="http://cache.itb.ac.id:8080"

    atau, jika proxy anda menggunakan autentikasi

    export http_proxy="http://your-username:your-password@cache.itb.ac.id:8080"

    Ganti cache.itb.ac.id:8080 dengan alamat proxy server beserta port proxy.
    Ganti your-username dengan username proxy Anda.
    Ganti your-password dengan password proxy Anda.

  2. yum sudah siap digunakan melalui proxy. Misalnya untuk menginstall gcc, yum install gcc

Dengan cara di atas, ketika Anda reboot, Anda harus mengatur lagi setting proxy. Jika Anda ingin mengonfigurasi secara lebih permanen, dapat mengikuti langkah berikut.

  1. Buka terminal lau edit file konfigurasi yum (/etc/yum.conf) (user harus mempunyai hak admin).
    # yum gedit /etc/yum.conf &
    Jika tidak mempunyai hak admin, dapat dilakukan dengan pemanggilan perintah
    $ sudo yum gedit /etc/yum.conf
    Atau dengan melakukan perintah jika Anda bukan sudoers
    $ su
    # yum gedit /etc/yum.conf

  2. Tambahkan baris berikut pada file konfigurasi yum
    # Alamat Proxy Server - proxy server:port number
    proxy=http://cache.itb.ac.id:8080
    # Detil autentikasi proxy
    proxy_username=your-username
    proxy_password=your-password
    

    Ganti http://cache.itb.ac.id:8080 dengan alamat proxy server beserta port proxy.
    Ganti your-username dengan username proxy Anda.
    Ganti your-password dengan password proxy Anda.

  3. yum sudah siap digunakan melalui proxy. Misalnya untuk menginstall gcc, yum install gcc