有几个问题使用它来执行诸如不使用进程替换的多个输出管道之类的事情:
为此仅使用固定的fd数字安全吗?程序是否可能已经按此处所述使用它,而我们覆盖了重要内容或读取了无关内容?
程序是否已经在使用它
不,您看到,I / O重定向在启动程序或脚本之前发生。
通常,当程序或脚本启动时,仅打开标准描述符(0 /标准输入,1 /标准输出和2 /标准错误)。(它们可能指的是终端,设备,文件,甚至是网络套接字;但是它们应该是打开的。我们不是“关闭”一个,而是将一个不需要的描述符从/重定向到/dev/null
,本质上是“无处” /“无”) )
程序通过系统调用使用描述符,例如open
使用免费描述符。也就是说,他们不要求内核打开特定描述符的文件或套接字,而是由内核选择描述符。因此,程序使用附加描述符的唯一情况就是程序启动时已被打开。有一些这样的罕见实用程序守护程序-除了标准描述符外,他们还希望,例如,当描述符3在启动时打开时,它将连接到其管理服务(或类似服务)。
如果程序决定使用硬编码的描述符(并且唯一的原因是因为它派生并执行了另一个程序,该程序期望该描述符是打开的;就像我说的那样,这种情况非常少见),所以已经打开的描述符会当程序将其替换为所用的对象时,该函数将关闭。(顺便说一句,当程序指示他们要使用特定的描述符时,例如,dup2()
在POSIXy系统中,内核会进行关闭;该过程无需关心。)
Shell脚本(Bash和sh)使用固定的描述符编号,因此脚本可能使用特定的描述符进行某些输入/输出重定向。但是,发生这种情况时,以前的重定向将被忽略,并且没有任何作用,因为脚本假定描述符已关闭。(如果打开了描述符,并且脚本将该描述符用于一些内部内容,则在脚本重定向它时,原始描述符首先由内核关闭,并且出于上一段所述的原因。)发生数据泄漏时,脚本必须专门测试描述符是否已打开,并避免重定向它。)
还要注意,即使Fortran I / O单元或通道都与描述符无关,即使它们都使用数字进行标识。因此,即使Fortran程序使用单元10,也并不意味着它使用描述符10。
为此仅使用固定的fd数字安全吗?
是的。POSIX说,一个程序可以打开至少20个描述符,因此3到19之间的任何固定数字都可以正常工作。
关键是要很好地记录下来,最好在脚本的开头(对于脚本)中使用简短注释,或者在用法(-h
或--help
命令行选项)和手册页中(对于程序)进行简短注释。
对于脚本,您可以假设如果发生冲突(如果发生冲突,则将是“如上所述,脚本根本不起作用,因为程序启动后管道将立即关闭”),用户可以进行更改固定的描述符号更好地适合他们的需求。因此,作为脚本编写者的任务是提前计划,并使后继者更容易进行规划。(清楚描述您的意图和总体设计的注释就足够了;不必使描述符编号成为变量,也不必描述脚本执行的每个小动作。)
对于程序,使它在运行时可配置是一个好主意。例如,对于带有图形用户界面的特殊控制协议,您可以让程序/守护程序使用描述符3(如果打开)。但是,请使用某些命令行选项(例如'-c 5'),使用命名描述符(或与-c /dev/name
or-c named-pipe
或-c :socketpath
使用指定文件,命名管道或本地域套接字)。这样,用户可以轻松解决与脚本的任何冲突。
本文收集自互联网,转载请注明来源。
如有侵权,请联系[email protected] 删除。
我来说两句