Anggapan Anda bahwa itu ssh
sendiri yang mengembalikan status keluar 255 adalah benar. The ssh
man page menyatakan bahwa:
ssh keluar dengan status keluar dari perintah jarak jauh atau dengan 255 jika terjadi kesalahan.
Jika Anda hanya menjalankan ssh pi@10.20.0.10 "pkill -f asdf"
, kemungkinan besar Anda akan mendapatkan status keluar 1
, sesuai dengan pkill
status untuk " Tidak ada proses yang cocok ".
Bagian yang menantang adalah untuk memahami mengapa kesalahan terjadi dengan SSH saat Anda menjalankan
ssh pi@10.20.0.10 "pkill -f asdf || true"
Perintah jarak jauh SSH
Server SSH meluncurkan shell untuk menjalankan perintah jarak jauh. Berikut ini contoh tindakan ini:
$ ssh server "ps -elf | tail -5"
4 S root 35323 1024 12 80 0 - 43170 poll_s 12:01 ? 00:00:00 sshd: anthony [priv]
5 S anthony 35329 35323 0 80 0 - 43170 poll_s 12:01 ? 00:00:00 sshd: anthony@notty
0 S anthony 35330 35329 0 80 0 - 28283 do_wai 12:01 ? 00:00:00 bash -c ps -elf | tail -5
0 R anthony 35341 35330 0 80 0 - 40340 - 12:01 ? 00:00:00 ps -elf
0 S anthony 35342 35330 0 80 0 - 26985 pipe_w 12:01 ? 00:00:00 tail -5
Perhatikan bahwa shell default adalah bash
dan bahwa perintah jarak jauh bukan perintah sederhana tetapi sebuah pipa , "urutan satu atau lebih perintah yang dipisahkan oleh operator kontrol |
".
Bash shell cukup pintar untuk menyadari bahwa jika perintah yang diteruskan oleh -c
opsi tersebut adalah perintah sederhana , ia dapat mengoptimalkan dengan tidak benar-benar memalsukan proses baru, yaitu, ia secara langsung exec
merupakan perintah sederhana alih-alih melalui langkah tambahan dari fork
sebelum itu exec
s. Berikut adalah contoh dari apa yang terjadi ketika Anda menjalankan perintah sederhana jarak jauh ( ps -elf
dalam kasus ini):
$ ssh server "ps -elf" | tail -5
1 S root 34740 2 0 80 0 - 0 worker 11:49 ? 00:00:00 [kworker/0:1]
1 S root 34762 2 0 80 0 - 0 worker 11:50 ? 00:00:00 [kworker/0:3]
4 S root 34824 1024 31 80 0 - 43170 poll_s 11:51 ? 00:00:00 sshd: anthony [priv]
5 S anthony 34829 34824 0 80 0 - 43170 poll_s 11:51 ? 00:00:00 sshd: anthony@notty
0 R anthony 34830 34829 0 80 0 - 40340 - 11:51 ? 00:00:00 ps -elf
Saya telah menemukan perilaku ini sebelumnya tetapi saya tidak dapat menemukan referensi yang lebih baik selain jawaban AskUbuntu ini .
perilaku pkill
Karena pkill -f asdf || true
ini bukan perintah sederhana (ini daftar perintah ), optimasi di atas tidak dapat terjadi sehingga ketika Anda menjalankan ssh pi@10.20.0.10 "pkill -f asdf || true"
, sshd
proses bercabang dan mengeksekusi bash -c "pkill -f asdf || true"
.
Seperti yang ditunjukkan oleh jawaban ctx, pkill
tidak akan mematikan prosesnya sendiri. Namun, itu akan membunuh proses lain yang baris perintahnya sesuai dengan -f
pola. The bash -c
perintah sesuai dengan pola ini sehingga membunuh proses ini - induk sendiri (seperti yang terjadi).
Server SSH kemudian melihat bahwa proses shell itu dimulai untuk menjalankan perintah jarak jauh terbunuh secara tak terduga sehingga melaporkan kesalahan ke klien SSH.
pkill
membunuh proses shell induknya karena daftar arg yang cocok regexp, saya akan mengangkat keberatan terminologi:x || y
adalah tidak sebuah perintah senyawa , itu adalah daftar perintah .