微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

如何禁用 proc 文件的读取或写入功能?

如何解决如何禁用 proc 文件的读取或写入功能?

我正在创建一个 proc 文件 (/proc/key),用户可以将他的解密密钥写入其中,然后该密钥将用于解密存储在内核模块中的缓冲区的内容。此外,我还有另一个 proc 条目 (/proc/decrypted) 将用于读取存储解密文本的缓冲区的内容

问题是我不希望用户能够向 (/proc/decrypted) 文件写入任何内容,并且我不希望他从 (/proc/key) 读取任何内容。如何实施?

我已将 file_operations 结构中的相应函数指向 NULL,但显然,一旦用户尝试,这将导致分段错误

如何防止从 procfs 读取或写入?我应该创建没有主体的函数并在需要时将 file_operations 结构指向它们吗?

static ssize_t key_proc_write(struct file *filp,const char __user *buf,size_t count,loff_t *ppos)
{
    char temp[128];
    memset(temp,128);
    int c; 
    c = copy_from_user(temp,buf,count);
 return count;
}


static const struct file_operations Proc_key_fops = {
 .owner = THIS_MODULE,.open = hello_proc_open,.read = NULL,.write = key_proc_write,.llseek = seq_lseek,.release = single_release,};  

解决方法

如果你想禁止阅读,你可以省略明确设置.read的{​​{1}}字段。如果结构体定义为 struct file_operation 并因此初始化为 static,则所有未显式覆盖的字段将默认为 0,内核将根本不执行任何操作并返回错误(我相信 NULL) 每当用户代码尝试在您打开的文件上调用 -EINVAL

或者,如果您想返回自定义错误,您可以定义一个仅返回错误的虚拟函数(例如 read)。

您认为我将密钥“写入”缓冲区的方式是否正确?

这是错误的,原因有很多。

首先,您的 return -EFAULT; 盲目信任用户 copy_from_user(),因此这会导致 count 变量的内核缓冲区溢出,这是非常糟糕的。您需要先检查和/或限制大小。您也没有检查 temp 的返回值,您应该检查它(它不是 copy_from_user(),而是 int)。

unsigned long

现在代码更有意义了,但是变量static ssize_t key_proc_write(struct file *filp,const char __user *buf,size_t count,loff_t *ppos) { char temp[128]; memset(temp,128); if (count > 128) count = 128; // or alternatively return -EINVAL or another error if (copy_from_user(temp,buf,count)) return -EFAULT; return count; } 只是在函数内部定义的,因此函数返回后会丢失,其他文件操作函数中将无法使用。如果您想这样做,您可以使用 temp,这是一个专门用于此目的的 filp->private_data 字段。

您应该在 struct file 上创建并初始化一个缓冲区,然后在您的 open 函数中释放它,如下所示:

release

然后,在您的 static int hello_proc_open(struct inode *ino,struct file *filp) { void *buf = kmalloc(128,GFP_KERNEL); if (!buf) return -ENOMEM; filp->private_data = buf; // ... whatever else you need to do return 0; } static int hello_proc_release(struct inode *ino,struct file *filp) { kfree(filp->private_data); // ... whatever else you need to do return 0; } 中,您可以在将缓冲区转换为正确类型后直接使用它:

write

最后,我看到你正在使用:

static ssize_t key_proc_write(struct file *filp,loff_t *ppos)
{
    char *temp = filp->private_data;
    memset(temp,count))
        return -EFAULT;

    return count;
}

不要这样做。您不需要使用预定义的操作。不要将您创建的自定义函数与其他规范函数(例如用于序列文件的函数)混合使用。序列文件需要执行一些初始化和拆卸,您可以使用 all .llseek = seq_lseek,.release = single_release, 系列文件操作,或者您自己手动完成,或者不使用这些函数。在您的情况下,最后一个选项适用。

您可以将 seq_ 设置为我上面显示的 .release,而不设置 hello_proc_release()(默认为 .llseek)。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?