如何避免在Linux设备驱动程序中的copy_from_user和copy_to_user

我正在写一个设备驱动程序,它使用字符设备文件将用户空间缓冲区中的数据从使用malloc分配到内核缓冲区中。 目前使用copy_from_user api将用户数据复制到内核缓冲区。 试图find一种避免在用户和内核空间之间进行数据复制的方法。 有没有办法在不使用copy_from_user情况下访问内核空间中的用户空间缓冲区(由malloc分配)?

我们先回答你提出的问题。 是的,您可以从内核访问用户空间的内存。 我不确定如何使用这些技术,但是如果你的内核代码在调用线程的上下文中运行,那么简单地使用给你的用户空间指针是可能的。

不过请不要这样做。

不应该这样做的原因是,如果用户空间指针错误,或者内存太短,或者存在任何其他问题,那么用户空间进程可能需要与分段错误一起崩溃。 可悲的是,你没有运行用户空间代码,你正在运行内核空间。 内核等价于分段错误是内核恐慌。 不要对用户造成影响。

更好的方法是使用一个机制,用户空间只写一次数据,然后字符设备可以简单地使用它。 在评论中提到了用户空间mmap页面。 一个对文件描述符工作方式可能更标准的方法是在设备的fileops结构中实现splice_read

现在,拼接并不是一个简单的界面,但主要的优势在于,如果你的源代码也是拼接感知的,那么用户可以直接将数据从源代码传递到你的驱动程序,而不必经过用户空间。

如果你想保存副本,我建议你去这些解决方案之一。 同样,不要直接访问用户提供的指针,除非你知道你在做什么。

可以使用get_user_pages() API来get_user_pages()从物理内存中换出的用户页面,并且可以通过访问相应虚拟地址的物理页面来访问该内存区域。