Linux 使用内核模块更改文件打开模式

Linux 使用内核模块更改文件打开模式,linux,linux-kernel,fedora,redhat,Linux,Linux Kernel,Fedora,Redhat,我正在用一个内核模块做一些测试,用下面的代码将进程的文件打开模式从write改为readonly,我从lsof-p中获取文件描述符编号,并编译模块&insmod changefilemode.ko,它在fedora 19上工作,但如果我在RedHat 5上执行,文件描述符将关闭 #include <linux/kernel.h> #include <linux/module.h> #include <linux/init.h> #include

我正在用一个内核模块做一些测试,用下面的代码将进程的文件打开模式从write改为readonly,我从
lsof-p
中获取文件描述符编号,并编译模块&insmod changefilemode.ko,它在fedora 19上工作,但如果我在RedHat 5上执行,文件描述符将关闭

  #include <linux/kernel.h>
  #include <linux/module.h>
  #include <linux/init.h>
  #include <linux/sched.h>
  #include <linux/file.h>
  #include <linux/fs.h>


  struct files_struct *get_files_struct(struct task_struct *task)
  {
       struct files_struct *files;

       task_lock(task);
       files = task->files;
       if (files)
              atomic_inc(&files->count);
       task_unlock(task);

       return files;
   }


   MODULE_LICENSE("GPL");

   static int __init myinit(){
         struct task_struct *tsk;
         for_each_process(tsk){

         if(tsk->pid == 11923){
                    struct files_struct *files = get_files_struct(tsk);
                    task_lock(tsk);
                    printk("\tpid %d - file mode %d\n",tsk->pid, files->fd_array[6]->f_mode);
                    files->fd_array[6]->f_mode = FMODE_READ;
                    printk("\tpid %d - file mode %d\n",tsk->pid, files->fd_array[6]->f_mode);
                    task_unlock(tsk);
               }
         }
      return 0;
   }

static void  __exit myexit(){
    printk("Good Bye from exit");
}


module_init(myinit);
module_exit(myexit);
#包括
#包括
#包括
#包括
#包括
#包括
结构文件\u结构*获取\u文件\u结构(结构任务\u结构*任务)
{
结构文件\u结构*文件;
任务锁定(任务);
文件=任务->文件;
如果(文件)
原子公司(文件->计数);
任务解锁(任务);
归还文件;
}
模块许可证(“GPL”);
静态int uu init myinit(){
结构任务\u结构*tsk;
对于每个流程(tsk){
如果(tsk->pid==11923){
struct files\u struct*files=get\u files\u struct(tsk);
任务锁(tsk);
printk(“\tpid%d-文件模式%d\n”,tsk->pid,文件->fd_数组[6]->f_模式);
文件->fd_数组[6]->f_模式=FMODE_读取;
printk(“\tpid%d-文件模式%d\n”,tsk->pid,文件->fd_数组[6]->f_模式);
任务解锁(tsk);
}
}
返回0;
}
静态void uu退出myexit(){
printk(“出口再见”);
}
模块_init(myinit);
模块_退出(myexit);

确切的PID值取决于启动过程中进程启动的确切时间顺序。 没有办法确保进程启动的确切时间顺序是跨发行版确定的,除非您根据自己的确切需要仔细调整,并假设init进程完全相同


此外,fd编号取决于流程执行期间的
open()
年表。

严重吗?您的内核模块中有一个硬编码的PID?您打算如何安排您的测试程序始终具有该PID?因为我使用了syslog PID,我采用了syslog PID,并在模块中输入了您要关闭的是哪种文件?也就是说,在这个过程中fd 6是什么?当我做测试时,fd 6是/var/log/messages你写了syslog pid-你的意思是
syslogd
?是的,我知道pid和文件描述符并不总是相同的,我每次加载模块时都会重新编译它