clinuxlinux-kernellinux-device-driverkernel-module

‘proc_fops’ has an incomplete type ‘struct proc_ops’


I am trying to build a Linux kernel module, and in particular I have these files, all in the same folder:

I want to handle a configuration file into the /proc directory, so in the proc.h/.c files I have defined a driver to properly manage it:

proc.h

#include <linux/proc_fs.h>

extern struct proc_ops proc_fops;

ssize_t read_proc(struct file *filp, char *buf, size_t count, loff_t *offp );
ssize_t write_proc(struct file *filp, const char *buf, size_t count, loff_t *offp );

proc.c

#include "proc.h"

#if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
struct file_operations proc_fops = {
        .read = read_proc,
        .write = write_proc
};
#else
struct proc_ops proc_fops= {
        .proc_read =  read_proc,
        .proc_write =  write_proc
};
#endif

//...

ssize_t write_proc(struct file *filp, const char *buf, size_t count, loff_t *offp ) {
    //...
}
ssize_t read_proc(struct file *filp, char *buf, size_t count, loff_t *offp ) {
    //...
}

I wrote it into a separate "proc" code block because I want the file to be managed into both user.c and syscalls.c.

I have only implemented the user.c call, that is:

proc_create(PROCFILE, 0, NULL, proc_fops);

but I receive this error:

error: ‘proc_fops’ has an incomplete type ‘struct proc_ops’
  182 |     proc_create(PROCFILE, 0, NULL, proc_fops);
      |                                             ^~~~~~~~~

and I cannot find where is the problem. Anyone have some clue? My kernel version (uname -r) is 5.4.0-192-generic.


Solution

  • Solved, the problem was that the declaration in proc.h only contained the one for the proc_ops type, valid only for kernel version greater than 5.6.0. So, to complete compliance, I just changed it to:

    proc.h

    #if LINUX_VERSION_CODE < KERNEL_VERSION(5,6,0)
    extern struct file_operations proc_fops;
    #else
    extern struct proc_ops proc_fops;
    #endif
    

    as well as correctly specify the pointer with & in:

    proc.c

    proc_create(PROCFILE, 0, NULL, &proc_fops);