Saya sedang membangun sistem Linux yang sangat minimal yang hanya terdiri dari kernel (v4.1-rc5) dan sebuah initramfs yang diisi dengan busybox (v1.23.2). Ini berfungsi dengan baik untuk sebagian besar, tetapi saya mengamati perbedaan dalam perilaku pelaksanaan perintah di / init apakah saya menggunakan initramfs yang tertanam vs yang eksternal.
Skrip / init adalah:
#!/bin/sh
dmesg -n 1
mount -t devtmpfs none /dev
mount -t sysfs none /sys
mount -t proc none /proc
echo "Welcome"
while true
do
setsid cttyhack /bin/sh
done
Kemudian saya mengatur opsi CONFIG_INITRAMFS_SOURCE di kernel .config ke direktori yang berisi semua folder untuk initramfs, atau saya jalankan
find . | cpio -H newc -o | gzip > ../rootfs.cpio.gz
untuk membangunnya.
Ketika saya kemudian mengkompilasi kernel, baik dengan atau tanpa set CONFIG_INITRAMFS_SOURCE, saya berakhir dengan dua varian sistem saya:
bzImage dengan initramfs tertanam
bzImage + rootfs.cpio.gz (initramfs eksternal)
ketika saya sekarang mulai menggunakan mereka qemu
qemu-system-x86_64 -enable-kvm -kernel bzImage
atau
qemu-system-x86_64 -enable-kvm -kernel bzImage -initrd rootfs.cpio.gz
Saya mendapatkan perbedaan perilaku:
dengan versi 2 (initramfs eksternal) semuanya berfungsi dengan baik, "Selamat Datang" ditampilkan dan saya mendapatkan prompt. Namun dengan versi 1 (embedded initramfs) saya mendapatkan peringatan
unable to open an initial console
"Selamat datang" tidak ditampilkan, dan saya mendapatkan prompt saya.
Sejauh yang saya mengerti prosesnya, kedua versi initramfs harus berisi file yang sama, karena saya membangunnya (atau meminta kernel membangunnya) dari folder yang sama.
Saya ingin tahu apakah ada yang bisa membantu saya dengan penjelasan untuk perilaku ini?
* PEMBARUAN *
seperti yang dikatakan mikeserv dalam komentar, Kernel menyertakan initramfs minimum yang tertanam per default. Ini masih ada saat menggunakan yang eksternal, tetapi akan ditimpa jika Anda menanamkan milik Anda sendiri. Saya menemukan bahwa bertentangan dengan spesifikasi, ini memang tidak kosong, tetapi berisi folder dev, folder root dan perangkat / dev / console. Perangkat ini kemudian digunakan ketika menggunakan initramfs eksternal, tetapi ditimpa jika Anda menanamkannya sendiri. Jadi, Anda harus menyertakan perangkat / dev / console di sumber initramfs Anda mknod -m 622 initramfs_src/dev/console c 5 1
saat menyematkan perangkat Anda sendiri.
Terima kasih banyak kepada mikeserv, frostschutz dan JdeBP karena telah membantu saya memahami hal itu!
/dev/console
bawaan? Saya pikir perbedaannya mungkin tentang siapa yang melakukan pengepakan dalam dua kasus.Jawaban:
Apakah mereka benar-benar identik?
Yang built-in Anda dapat menemukan
/usr/src/linux/usr/initramfs_data.cpio.gz
atau mengekstraknya dari bzImage seperti dijelaskan di sini: https://wiki.gentoo.org/wiki/Custom_Initramfs#SalvagingJika Anda menggunakan bawaan itu dan menggunakannya sebagai eksternal, apakah itu berfungsi?
Jika masih berbeda, apakah kernel itu sendiri identik? (bandingkan
/proc/config.gz
untuk keduanya)Seharusnya ada beberapa perbedaan. Saya tidak tahu bahwa kernel peduli dari mana initramfs berasal. Saya akan segera menduga
qemu
menggunakan pengaturan yang berbeda ketika melewati-initrd
parameter ...Pada sidenote,
/init
penampilanmu seperti cangkangnya yang tak terbatas bagiku.setsid
tidakexec
. Apakah aku salah?sumber
On a sidenote, your /init looks like its spawning infinite shells to me. setsid is not exec. Am I wrong?
: Loop meniru getty atau alat serupa, sejak panggilansh
blok sampai keluar shell.Anda juga mungkin tertarik dengan bagaimana Buildroot 2018.02 berurusan dengan ini.
Setiap kali Anda menggunakan initramfs (
BR2_TARGET_ROOTFS_INITRAMFS=y
) atau initrd (BR2_TARGET_ROOTFS_CPIO=n
), ia menambahkan yang berikut ini/init
ke rootfs Anda https://github.com/buildroot/buildroot/blob/2018.02/fs/cpio/initSalinan dilakukan oleh https://github.com/buildroot/buildroot/blob/2018.02/fs/cpio/cpio.mk :
Juga berguna untuk mengetahui bahwa path init adalah
/init
untuk initramfs, tidak seperti yang/sbin/init
lain: Apa yang dapat membuat passing init = / path / ke / program ke kernel tidak memulai program seperti init?sumber