如何在Linux中创建一个虚拟的基于命令的文件?

13

如何在Linux中创建最简单的“虚拟”文件,使得读取操作总是返回某个特定命令的输出(每次从该文件读取时都运行该命令)?因此,每次读取操作都会执行一条命令,捕获其输出并将其作为文件的“内容”传递。

4个回答

7
无法创建所谓的“虚拟文件”。另一方面,您可以通过在用户空间中通过FUSE实现简单的合成文件系统来实现此行为。此外,您不必使用c,甚至可以使用脚本语言如python进行绑定。
编辑:而且很有可能已经存在类似于scriptfs的东西。

谢谢,scriptfs 看起来正是我在寻找的 :-) - knaperek
1
那么,cat /proc/cpuinfo 是什么? - Michael Cole
@MichaelCole:cpuinfo不是一个孤立的文件,它是proc文件系统的一部分。另一个区别是procfs是在内核中实现的,而这个问题需要在用户空间中解决。 - marbu

6

这是我复制下来的一个非常好的答案

基本上,命名管道允许您在脚本中执行此操作,而Fuse使您可以轻松地使用Python实现这一点。


您可能正在寻找命名管道

mkfifo f
{
  echo 'V cebqhpr bhgchg.'
  sleep 2
  echo 'Urer vf zber bhgchg.'
} >f
rot13 < f

写入管道不会启动监听程序。如果您想循环处理输入,需要保持一个监听程序运行。

while true; do rot13 <f >decoded-output-$(date +%s.%N); done

请注意,即使有多个进程在写入数据,所有写入管道的数据都会合并。如果有多个进程在读取,则只有一个进程可以获得数据。因此,管道可能不适用于并发情况。
命名套接字可以处理并发连接,但这超出了基本shell脚本的能力范围。
在最复杂的一端是自定义文件系统,它可以让您设计和挂载文件系统,其中每个open、write等触发程序中的函数。最小投资是几十行非平凡的编码,例如在Python中。如果您只想在读取文件时执行命令,则可以使用scriptfs或fuseflt。

3

没有人提到这一点,但如果你可以选择文件的路径,你可以使用标准输入/dev/stdin

每次运行cat程序时,它都会读取写入到管道中的程序的输出结果,这里仅为echo my input

for i in 1 2 3; do
    echo my input | cat /dev/stdin
done

输出:

my input
my input
my input

2
很抱歉,这并不容易实现。当进程从文件中读取时,它使用系统调用如openfstatread等。必须拦截这些调用并输出与它们返回值不同的东西。这需要编写某种内核模块,即使如此,它也可能无法实现。
然而,如果您只需要在访问特定文件时触发某些操作,您可以使用inotifywait进行尝试:
#!/bin/bash

while inotifywait -qq -e access /path/to/file; do
        echo "$(date +%s)" >> /tmp/access.txt
done

将此作为后台进程运行,每次读取您的文件时,您将在/tmp/access.txt中获得一个条目。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接