Sengaja menyebabkan kesalahan I / O di Linux?

42

Apakah ada, dengan Linux, yang sengaja menyebabkan perangkat blok melaporkan kesalahan I / O, atau mungkin mensimulasikannya untuk tujuan pengujian?

Dok
sumber
Apakah Anda mensimulasikan kegagalan disk? Mungkin Anda bisa memasang direktori dan kemudian melepasnya saat sedang digunakan.
Shef
2
Saya akan menulis modul kernel kecil yang dapat Anda muat modprobe, berperilaku seperti perangkat blok, dan kemudian program kecil lain yang dikirimkan ioctl()'ske driver untuk membuatnya mengembalikan nilai yang Anda inginkan.
ott--
Pertanyaan yang sama pada Stack Overlflow dan di Unix dan Linux .
Gilles 'SANGAT berhenti menjadi jahat'
Untuk menindaklanjuti komentar yang dibuat @Gilles, ini juga ditanyakan di stackoverflow.com/questions/1361518/… (beberapa jawaban injeksi kesalahan berbeda) dan stackoverflow.com/questions/1870696/… (gunakan device mapper).
Anon

Jawaban:

54

Ya, ada cara yang sangat masuk akal untuk melakukan ini dengan perangkat mapper.

Mapper perangkat dapat menggabungkan kembali perangkat blok ke dalam pemetaan / urutan baru pilihan Anda. LVM melakukan ini. Ini juga mendukung target lain, (beberapa yang cukup baru) seperti 'flakey' untuk mensimulasikan disk yang gagal dan 'kesalahan' untuk mensimulasikan daerah disk yang gagal.

Seseorang dapat membuat perangkat yang sengaja memiliki lubang hitam IO di atasnya yang akan melaporkan kesalahan IO ketika menyeberang.

Pertama, buat beberapa volume virtual untuk digunakan sebagai target dan buat itu bisa dialamatkan sebagai perangkat blok.

dd if=/dev/zero of=/var/lib/virtualblock.img bs=512 count=1048576
losetup /dev/loop0 /var/lib/virtualblock.img

Jadi, untuk memulai ini buatlah file 512M yang merupakan dasar dari perangkat blok virtual kami yang akan kami buat 'lubang'. Namun belum ada lubang. Jika Anda ke sana, mkfs.ext4 /dev/loop0Anda akan mendapatkan sistem file yang benar-benar valid.

Jadi, mari kita gunakan dmsetup yang, menggunakan perangkat blok ini - akan membuat perangkat baru yang memiliki beberapa lubang di dalamnya. Berikut ini contohnya

dmsetup create errdev0
0 261144 linear /dev/loop0 0
261144 5 error
261149 787427 linear /dev/loop0 261139

Ini akan membuat perangkat yang disebut 'errdev0' (biasanya di / dev / mapper). Ketika Anda mengetiknya dmsetup create errdev0akan menunggu stdin dan akan selesai pada ^ D menjadi input.

Pada contoh di atas, kami telah membuat lubang 5 sektor (2.5kb) di sektor 261144 dari perangkat loop. Kami kemudian melanjutkan melalui perangkat loop seperti biasa.

Script ini akan mencoba membuatkan Anda sebuah tabel yang akan menempatkan lubang di lokasi acak yang tersebar di sekitar 16MB (meskipun cukup acak).

#!/bin/bash
start_sector=0
good_sector_size=0

for sector in {0..1048576}; do

    if [[ ${RANDOM} == 0 ]]; then
        echo "${start_sector} ${good_sector_size} linear /dev/loop0 ${start_sector}"
        echo "${sector} 1 error"
        start_sector=$((${sector}+1))
        good_sector_size=0
    else
        good_sector_size=$((${good_sector_size}+1))
    fi
done

echo "${start_sector} $((${good_sector_size}-1)) linear /dev/loop0 ${start_sector}"

Script mengasumsikan Anda juga telah membuat perangkat 512Mb dan perangkat blok virtual Anda aktif /dev/loop0.

Anda bisa menampilkan data ini ke file teks sebagai tabel dan memasukkannya ke dalam file dmsetup create errdev0.

Setelah Anda membuat perangkat, Anda dapat mulai menggunakannya seperti perangkat blok biasa, pertama dengan memformatnya dan kemudian dengan menempatkan file di atasnya. Pada titik tertentu Anda harus menemukan beberapa masalah IO di mana Anda menekan sektor yang benar-benar lubang IO di perangkat virtual.

Setelah Anda selesai menggunakan dmsetup remove errdev0untuk menghapus perangkat.

Jika Anda ingin membuatnya lebih mungkin untuk mendapatkan kesalahan IO Anda dapat menambahkan lubang lebih sering atau mengubah ukuran lubang yang Anda buat. Catatan menempatkan kesalahan di bagian-bagian tertentu cenderung menyebabkan masalah saat bepergian, yaitu pada 32MB ke perangkat yang Anda tidak dapat menulis superblock yang biasanya dilakukan oleh ext, sehingga format tidak akan berfungsi.

Untuk menambahkan menyenangkan - Anda dapat benar-benar hanya losetupkemudian mkfs.ext4 /dev/loop0dan mengisinya dengan data. Setelah Anda mendapatkan filesystem yang berfungsi dengan baik di sana, cukup unmount sistem file dan tambahkan beberapa lubang menggunakan dmsetup dan remount itu!

Matthew Ife
sumber
6
Saya tidak tahu Anda bisa melakukan ini. Cukup keren.
15

Untuk memeriksa ketahanan program jika outputnya gagal, Anda dapat menggunakan pseudodevice /dev/full, yang selalu mengembalikan "ENOSPACE" saat ditulis.

$ dd if=/dev/zero of=/dev/full
dd: writing to `/dev/full': No space left on device
1+0 records in
0+0 records out
Raúl Salinas-Monteagudo
sumber
7

Tergantung pada apa yang ingin Anda uji. Menggunakan LD_PRELOADperpustakaan ed, Anda dapat mengelabui aplikasi agar memikirkan hal-hal seperti 'semua penulisan gagal ENOSPCatau EIO' misalnya.

Dennis Kaarsemaker
sumber
1

Mungkin Anda bisa mengubah tabel partisi dan membuat partisi lebih besar dari yang sebenarnya. Itu mungkin akan menyebabkan kesalahan i / o. Atau jika cakram Anda hot pluggable, Anda bisa menariknya.

Jure1873
sumber