Chr*_*son 2 bash file-descriptor while-loop io-redirection
我正在研究一个bash脚本,试图弄清楚它的工作方式并可能对其进行修补。有问题的脚本是这个 cryptroot
从负责在开机解密块设备Debian的脚本。不能完全在家中进行bash肯定会带来挑战。
我找到了这段代码,但不确定它是做什么的。
if [ -r /conf/conf.d/cryptroot ]; then
while read mapping <&3; do
setup_mapping "$mapping" 3<&-
done 3< /conf/conf.d/cryptroot
fi
Run Code Online (Sandbox Code Playgroud)
我的猜测是,它将读取每一行/conf/conf.d/cryptroot
并将其传递给setup_mapping
。但是我不太了解,以及的意义<&3
,意义3&-
以及作用3</conf/conf.d/cryptroot
是什么?
当我从文件中读取行时,通常会执行以下操作:
while read LINE
do COMMAND
done < FILE
Run Code Online (Sandbox Code Playgroud)
在while循环中将的输出FILE
定向到的位置read
,COMMAND
直到最后一行为止。
我也对重定向有所了解,例如,有时我会用它来重定向STDOUT
和STDERR
诸如此类/dev/null
的东西。但是我不确定重定向的3
含义。
根据tldp.org的介绍,在阅读了有关I / O重定向的更多知识之后,我已经接近答案了。
stdin,stdout和stderr的文件描述符分别为0、1和2。要打开其他文件,请保留描述符3到9。
因此3是“仅”对打开文件的引用,或:
...只是操作系统分配给打开文件以跟踪它的数字。考虑它是文件指针的简化类型。
因此,据我了解:
3< /conf/conf.d/cryptroot
打开/conf/conf.d/cryptroot
读取并将其分配给文件描述符3。read mapping <&3
似乎是从读文件描述符3,它指向打开文件的第一行/conf/conf.d/cryptroot
。setup_mapping "$mapping" 3<&-
似乎是关闭文件描述符3,这是否意味着它再次打开在环动不动指向下一行?如果以上正确,我的问题是为什么要这样做而不是“正常”方式?例如
while read mapping; do
setup_mapping "$mapping"
done < /conf/conf.d/cryptroot
Run Code Online (Sandbox Code Playgroud)
第一个版本提供什么优势(如果有)?
一个常见的问题
while read LINE
do COMMAND
done < FILE
Run Code Online (Sandbox Code Playgroud)
是人们忘记了COMMAND也在从FILE中读取,并且可能消耗了意图read
在while循环控制中读取的数据。为了避免这种情况,常见的习惯用法是改为从其他文件描述符中读取。这可以通过完成<&3
。但是这样做会打开COMMAND的文件描述符3。可能不是问题,但使用明确将其关闭是合理的3<&-
。简而言之,您所看到的结构只是避免setup_mapping
无意中读取预期用于的数据的一种方法read
。