Duplikasi adalah bagian yang sangat penting di sini.
Mari kita lihat di mana deskriptor file akan pergi sebelum pengalihan. Ini biasanya terminal saat ini, misalnya:
STDOUT ---> /dev/pts/1
STDERR ---> /dev/pts/1
Sekarang, jika kita memanggil ls -l
tanpa pengalihan, pesan output dan kesalahan pergi ke terminal saya di bawah /dev/pts/1
.
Jika pertama kali kami mengarahkan ulang STDOUT
ke file ( ls -l > dirlist
), tampilannya seperti ini:
STDOUT ---> /home/bon/dirlist
STDERR ---> /dev/pts/1
Ketika kita kemudian mengarahkan STDERR
ke duplikat dari STDOUT
's file descriptor ( ls -l > dirlist 2>&1
), STDERR
pergi ke duplikat dari /home/bon/dirlist
:
STDOUT ---> /home/bon/dirlist
STDERR ---> /home/bon/dirlist
Jika kita pertama - tama akan mengarahkan ulang STDERR
ke duplikat STDOUT
deskriptor file ( ls -l 2>&1
):
STDOUT ---> /dev/pts/1
STDERR ---> /dev/pts/1
dan kemudian STDOUT
ke file ( ls -l 2>&1 > dirlist
), kita akan mendapatkan ini:
STDOUT ---> /home/bon/dirlist
STDERR ---> /dev/pts/1
Di sini, STDERR
masih menuju terminal.
Anda lihat, urutan di halaman manual sudah benar.
Menguji Pengalihan
Sekarang, Anda bisa mengujinya sendiri. Dengan menggunakan ls -l /proc/$$/fd/
, Anda melihat ke mana STDOUT
(dengan fd 1) dan STDERR
(dengan fd 2), untuk proses saat ini:
$ ls -l /proc/$$/fd/
total 0
lrwx------ 1 bon bon 64 Jul 24 18:19 0 -> /dev/pts/1
lrwx------ 1 bon bon 64 Jul 24 18:19 1 -> /dev/pts/1
lrwx------ 1 bon bon 64 Jul 24 07:41 2 -> /dev/pts/1
lrwx------ 1 bon bon 64 Jul 24 18:19 255 -> /dev/pts/1
Mari kita buat skrip shell kecil yang menunjukkan di mana file penjelas Anda diarahkan. Dengan cara ini, kami selalu mendapatkan status saat memanggil ls
, termasuk pengalihan dari shell panggilan.
$ cat > lookfd.sh
#!/bin/sh
ls -l /proc/$$/fd/
^D
$ chmod +x lookfd.sh
(Dengan CtrlD, Anda mengirim file akhir dan menghentikan cat
perintah membaca dari STDIN
.)
Sekarang, panggil skrip ini dengan berbagai kombinasi pengalihan:
$ ./lookfd.sh
total 0
lrwx------ 1 bon bon 64 Jul 24 19:08 0 -> /dev/pts/1
lrwx------ 1 bon bon 64 Jul 24 19:08 1 -> /dev/pts/1
lrwx------ 1 bon bon 64 Jul 24 19:08 2 -> /dev/pts/1
lr-x------ 1 bon bon 64 Jul 24 19:08 255 -> /home/bon/lookfd.sh
$ ./lookfd.sh > foo.out
$ cat foo.out
total 0
lrwx------ 1 bon bon 64 Jul 24 19:10 0 -> /dev/pts/1
l-wx------ 1 bon bon 64 Jul 24 19:10 1 -> /home/bon/foo.out
lrwx------ 1 bon bon 64 Jul 24 19:10 2 -> /dev/pts/1
lr-x------ 1 bon bon 64 Jul 24 19:10 255 -> /home/bon/lookfd.sh
$ ./lookfd.sh 2>&1 > foo.out
$ cat foo.out
total 0
lrwx------ 1 bon bon 64 Jul 24 19:10 0 -> /dev/pts/1
l-wx------ 1 bon bon 64 Jul 24 19:10 1 -> /home/bon/foo.out
lrwx------ 1 bon bon 64 Jul 24 19:10 2 -> /dev/pts/1
lr-x------ 1 bon bon 64 Jul 24 19:10 255 -> /home/bon/lookfd.sh
$ ./lookfd.sh > foo.out 2>&1
$ cat foo.out
total 0
lrwx------ 1 bon bon 64 Jul 24 19:11 0 -> /dev/pts/1
l-wx------ 1 bon bon 64 Jul 24 19:11 1 -> /home/bon/foo.out
l-wx------ 1 bon bon 64 Jul 24 19:11 2 -> /home/bon/foo.out
lr-x------ 1 bon bon 64 Jul 24 19:11 255 -> /home/bon/lookfd.sh
Anda dapat melihat, bahwa file deskriptor 1 (untuk STDOUT
) dan 2 (untuk STDERR
) bervariasi. Untuk bersenang-senang, Anda juga bisa mengarahkan STDIN
dan melihat hasilnya:
$ ./lookfd.sh < /dev/zero
total 0
lr-x------ 1 bon bon 64 Jul 24 19:18 0 -> /dev/zero
lrwx------ 1 bon bon 64 Jul 24 19:18 1 -> /dev/pts/1
lrwx------ 1 bon bon 64 Jul 24 19:18 2 -> /dev/pts/1
lr-x------ 1 bon bon 64 Jul 24 19:18 255 -> /home/bon/lookfd.sh
(Pertanyaan tersisa untuk pembaca: Di mana file deskriptor 255 poin? ;-))