在debugfs中实现读操作列表

时间:2017-06-01 20:41:16

标签: c linux kernel

我正在实现一个内核模块。使用几种技术。 其中一个是对不同的模块变量进行读/写。 我能够读取/写入除模块中的列表之外的所有变量。 链表:

    static struct node {
        struct list_head list;
        unsigned int x;
        struct tm time;
    };

我想在debugfs中有一个相应的文件来打印完整列表。 我尝试了所有'简单'的读取功能,但它们都没有实际工作.. :(

2 个答案:

答案 0 :(得分:0)

Linux内核提供了seq_file接口,用于轻松实现表示枚举事物的文件,例如列表。

您只需要提供最多4个封装枚举的函数:

// Assume this is the head of your list.
static struct my_list;

// Start iteration
static void *my_start (struct seq_file *m, loff_t *pos)
{
    // Use ready-made helper for lists.
    return seq_list_start(&my_list, *pos);
}

// Next iteration
static void * my_next(struct seq_file *m, void *v, loff_t *pos)
{
    // Use ready-made helper for lists.
    return seq_list_next(v, &my_list, pos);
}

// Output on single iteration
static int my_show (struct seq_file *m, void *v)
{
    // Get original structure
    struct node* node = list_entry(v, struct node, list);
    // E.g., print content of 'x' field
    seq_printf(m, "%u,", node->x);

    return 0; // Success
}

static struct seq_operations my_seq_ops = {
    .start = &my_start,
    .stop = NULL, // Not needed in this case
    .next = &my_next,
    .show = &my_show
};

打开文件时,应将具有这些功能的结构传递给seq_open()

static int my_open(struct inode* inode, struct file* filp)
{
    return seq_open(filp, &my_seq_ops);
}

在文件操作中使用seq_read作为.read函数:

static struct file_operations my_file_ops = {
    .open = &my_open,
    .read = &seq_read,
};

注意,到这样的文件中你应该实现手动seq_lock对此没有帮助。

答案 1 :(得分:0)

您可以使用与此类似的功能阅读列表:

struct k_list {                                                                 
        struct list_head links;                                                     
        int data;                                                                   
};                                                                              

struct k_list my_list;

static ssize_t pop_queue(struct file * file,                                       
                                char *buf,                                         
                                size_t count,                                      
                                loff_t *ppos)                                      
{                                                                                  
        struct list_head *pos, *q;                                                 
        struct k_list *tmp;                                                        

        printk(KERN_INFO "--Listing inserted numbers--");                          
        list_for_each_safe(pos, q, &my_list.links) {                               
                tmp = list_entry(pos, struct k_list, links);                       
                printk(KERN_INFO "object: %d ", tmp->data);                        
        }                                                                          
        printk(KERN_INFO "--End of list--");                                       

        return count;                                                              
}