简体   繁体   中英

Adding multiple attributes to a device in a Linux PCI driver

I am currently writing my first linux driver trying to communicate witha PCI card. With the help of Linux Device Driver, 3rd edition and this great example I was able to code my first modules and to understand and to implement the basics (device detection, memory mapping, DMA, MSI). In a next step I would like to establish a connection between the PCI card's memory and the user space via sysfs and the help of device attributes. Unfortunately currently my module does not go further than produce an oops, this is why I would like to ask you.

In order to add multiple attributes to the device I create them as following:

static DEVICE_ATTR(foo, S_IWUGO | S_IRUGO, show_foo, set_foo);
static DEVICE_ATTR(bar, S_IWUGO | S_IRUGO, show_bar, set_bar);

static struct device_attribute *pci_device_attrs[] = {
    __ATTR(foo, S_IWUGO | S_IRUGO, show_foo, set_foo),
    __ATTR(bar, S_IWUGO | S_IRUGO, show_bar, set_bar),
    __ATTR_NULL,
};
static struct attribute_group pci_device_attr_group = {
    .attrs = pci_device_attrs,
};

But in contrast to struct device the device class of PCI devices ( struct pci_dev ) does not contain a struct attribute_group attribute. So how can I add my attribute_group variable to my pci_dev variable? I have tried so far the following in my probe() function, both fail in compilation due to the missing element group in pci_dev .

pci_device->groups = pci_device_attr_group;
pci_device->dev->groups = pci_device_attr_group;

GregKH explains on his blog one should simply add an additional field to the pci_dev structure which I do not know how to implement.

Any help and/or examples are much appreciated. Thank you!

EDIT:

actually after having a closer look at Documentation/driver-model/device.txt I modified my code example slightly to the following

static DEVICE_ATTR(foo, S_IWUGO | S_IRUGO, show_foo, set_foo);
static DEVICE_ATTR(bar, S_IWUGO | S_IRUGO, show_bar, set_bar);

static struct device_attribute *pci_device_attrs[] = {
    &dev_attr_foo.attr,
    &dev_attr_bar.attr,
    NULL,
};
static struct attribute_group pci_device_attr_group = {
    .attrs = pci_device_attrs,
};
static const struct attribute_group *pci_device_attr_groups[] = {
    &pci_device_attr_group,
    NULL,
};

"struct pci_driver" contains a "struct device_driver" (option 1). "struct pci_dev" contains a "struct device" (option 2)

Look at the structure definitions in include/linux/pci.h

The advice from GregKH is not to add a field to the structure, but to fill in the existing field.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM