Shell-Script
inotifywait 未響應 /proc/mounts 中的更改
我正在嘗試獲取有問題的 sshfs 掛載狀態的通知
我嘗試了兩個 bash 腳本
while inotifywait -e modify /proc/mounts; do echo "modified" done
和
inotifywait -m /proc/mounts | while read event; do echo $event done
為了測試,我正在執行以下序列,但這些腳本都沒有響應。
stephen@asus:~/log$ sudo umount /mnt/lexar stephen@asus:~/log$ sshfs michigan:/home/stephen/ /mnt/lexar stephen@asus:~/log$ sudo umount /mnt/lexar stephen@asus:~/log$ sshfs michigan:/home/stephen/ /mnt/lexar stephen@asus:~/log$ grep lexar /proc/mounts michigan:/home/stephen/ /mnt/lexar fuse.sshfs rw,nosuid,nodev,relatime,user_id=1000,group_id=1000 0 0 stephen@asus:~/log$ sudo umount /mnt/lexar stephen@asus:~/log$ grep lexar /proc/mounts
inotify
不適用於 proc 文件系統。儘管它們可能看起來像正常文件,但 proc 文件系統中的文件不包含任何靜態數據——當您讀取它們時,核心會即時組成數據。例如,/proc/mounts
=>/proc/self/mounts
的大小為 0,但是當你閱讀它時,它神奇地恰好包含了一些東西。但是
/proc/self/mounts
並且/proc/self/mountinfo
是可輪詢的——你可以select(2)
或poll(2)
在它上面為一個特殊的條件。根據proc(5)
手冊頁:
/proc/[pid]/mounts
(自 Linux 2.4.19 起)該文件列出了目前掛載在程序的掛載命名空間中的所有文件系統(請參閱 參考資料
mount_namespaces(7)
)。此文件的格式記錄在fstab(5)
.從核心版本 2.6.15 開始,該文件是可輪詢的:打開文件進行讀取後,該文件的更改(即文件系統掛載或解除安裝)導致
select(2)
將文件描述符標記為異常情況,poll(2)
並epoll_wait(2)
標記該文件具有優先事件 (POLLPRI
)。[同樣適用於
/proc/[pid]/mountinfo
]我認為沒有任何方法可以從外殼中做到這一點。但是,您可以從 執行此操作
perl
:#! /usr/bin/perl use strict; my $mf = "/proc/self/mountinfo"; open my $mh, "<$mf" or die "open <$mf: $!"; vec(my $ebits, $mh->fileno, 1) = 1; while(1){ select(undef, undef, my $e = $ebits, undef) == -1 and die "select: $!"; print "some mount or umount happened\n"; }
一個更有用的例子,它也顯示了變化
/proc/self/mountinfo
:#! /usr/bin/perl use strict; my $mf = "/proc/self/mountinfo"; open my $mh, "<$mf" or die "open <$mf: $!"; vec(my $ebits, $mh->fileno, 1) = 1; sub read_mounts { seek $mh, 0, 0 or die "seek: $!"; my ($h, $i); $$h{$_} = ++$i while <$mh>; return $h; } for(my ($old, $new) = read_mounts;; $old = $new) { select undef, undef, my $e = $ebits, undef or die "select: $!"; $new = read_mounts; for(keys %$new){ if(exists $$old{$_}){ delete $$old{$_} } else{ print '+ ', $_ } } print '- ', $_ for keys %$old; }