linux - 了解 access_process_vm linux 内核?

标签 linux linux-kernel linux-device-driver virtual-memory

我正在编写一个内核模块,它读取进程的部分虚拟内存。我试图在内核中使用 access_process_vm 方法来执行此操作,但它总是以读取 0 字节结束。

  target = get_pid_task(find_get_pid(target_pid),PIDTYPE_PID);
  if (target == NULL) {
      printk(KERN_ALERT "no such task %d\n",target_pid);
      return -1;
  }
  printk(KERN_INFO "opened task with pid %d\n",target->pid);

  len = vm_end-vm_start;
  buf = kmalloc(len ,GFP_KERNEL);
  if (!buf) {
      printk(KERN_ALERT "unable to allocate memory\n");
      return -1;
  }
  printk(KERN_INFO "allocated memory\n");

  bytes = access_process_vm(target,addr,buf,len,FOLL_FORCE);
  if (bytes != len) {
       printk(KERN_ALERT "could only read %d of %ld bytes\n",bytes,len);
       kfree(buf);
       return -1;
  }
  printk(KERN_INFO "read %d bytes successfully\n",bytes);

我做错了什么?

最佳答案

我不明白追踪这个有什么问题。

让我们来看看 access_process_vm 本身的前 2 种故障模式:

   if (addr + len < addr)
            return 0;

你根据 vm_end 和 vm_start 计算 len,但是你从 addr 开始读取。差异是怎么回事?也许你最终没有通过这项检查?

   mm = get_task_mm(tsk);
   if (!mm)        
           return 0;

这个怎么样?没有mm怎么办?

等等。

另请注意,您返回的是 -1 而不是实际错误。您正在错误地泄漏对目标线程的引用。

关于linux - 了解 access_process_vm linux 内核?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44069453/

相关文章:

c - 换入换出页面后,使用页映射表访问物理地址的过程是什么

c - 为什么 Linux 内核不会在返回 IRQ_HANDLED 的共享 IRQ 的第一个处理程序处停止?

linux - Linux下的签名可执行文件

在 LINUX 中检查简单的字符设备读/写函数

linux - 谷歌搜索 Linux 日志消息的替代方案?

linux - "Unknown symbol in module"在模块插入时尽管有 EXPORT_SYMBOL

linux - FreeRTOS 与 Linux 对抗单事件干扰

regex - 使用 sed,将特定字符串下方的部分行写入两个不同的变量

linux - 如何在 Linux 上捆绑 Mono/GTK# 应用程序?

c - 我需要实现一种方法让这个线程休眠直到它有工作要做