![Debian 的 /etc/init.d/umountfs 中的 sed 命令应该做什么?](https://linux22.com/image/10829/Debian%20%E7%9A%84%20%2Fetc%2Finit.d%2Fumountfs%20%E4%B8%AD%E7%9A%84%20sed%20%E5%91%BD%E4%BB%A4%E5%BA%94%E8%AF%A5%E5%81%9A%E4%BB%80%E4%B9%88%EF%BC%9F.png)
/etc/init.d/umountfs
在关闭期间运行以卸载大多数文件系统。它包含这个:
PROTECTED_MOUNTS="$(sed -n ':a;/^[^ ]* \(\/\|\/usr\) /!{H;n;ba};{H;s/.*//;x;s/\n//;p}' /proc/mounts)"
该命令显然选择了 中的行的子集/proc/mounts
,然后这些行就可以免于稍后在脚本中卸载。
它匹配第二个字段(挂载点)中的行/
,/usr
然后它接下来要做的事情涉及太多奇异的 sed 功能,让我无法弄清楚其意图是什么。
如果这只是选择/
和/usr
行,那么这是有意义的,因为它们会在不同的脚本中卸载。但它并没有这样做。当我在实际的 上运行它时/proc/mounts
,$PROTECTED_MOUNTS
最终包含几乎所有行,包括该/home
行。不卸载就不好了/home
,这样就不行了。
sed 命令的编写者可能想用所有分支和保留空间的东西做什么?
答案1
我会尝试一下...
这将返回每行直到并包括最后的的发生/
或者 /usr
。又名这会删除其中任何一个最后一次出现后的所有内容。
:a;/^[^ ]* \(\/\|\/usr\) /!{H;n;ba};
这就是说,对于不完全包含/
或/usr
在第二列(空格分隔)中的行,追加到H
旧空间,获取n
分行,循环b
ack 到 label a
。
{H;s/.*//;x;s/\n//;p}
只有当我们遇到带有/
或 的行时,我们才会到达这里/usr
。然后我们追加到H
旧空间(其中包含第一部分中的所有内容),清除模式空间,x
用模式空间更改保留空间,从模式空间中删除第一个换行符并p
打印它。
在我们看到最后一行/
或/usr
一行之后(并且我们已经打印了到该点的所有内容),我们循环遍历第一部分并吸收所有剩余的不匹配行......但它们永远不会被打印,因为我们不'进入第二部分。
我做了一些测试,结果与我的说法一致。
显然,这取决于 中维护的某种顺序/proc/mounts
。但该列表只是根据创建挂载点的顺序。所以我想,无论做什么,都必须维护,否则这些东西就会损坏。在我看来,这一切都非常脆弱。