Skip to content

Instantly share code, notes, and snippets.

@kwilczynski
Last active April 16, 2021 19:54
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save kwilczynski/062776e98201588e57b3c77cc6479ea3 to your computer and use it in GitHub Desktop.
Save kwilczynski/062776e98201588e57b3c77cc6479ea3 to your computer and use it in GitHub Desktop.
From 0103f1ae79ce480efd29f7396fabc90ea0f84d36 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Thu, 4 Mar 2021 23:56:14 +0000
Subject: [PATCH] PCI: Convert dynamic "config" sysfs object into static
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The "config" sysfs object, which is a binary read-and-write attribute,
resides at the "/sys/bus/pci/devices/.../config" path and allows for
accessing either the legacy (PCI and PCI-X Mode 1) or the extended
(PCI-X Mode 2 and PCIe) device PCI configuration space.
At the moment, the static "config" sysfs object is dynamically created
when the pci_create_sysfs_dev_files() function executes that is part of
the PCI sysfs objects initialisation and when a device is added:
late_initcall()
pci_sysfs_init()
pci_create_sysfs_dev_files()
sysfs_create_bin_file()
pci_bus_add_devices()
pci_bus_add_device()
pci_create_sysfs_dev_files()
...
And dynamically removed when the pci_remove_sysfs_dev_files() function
executes when the PCI device is stopped and removed:
pci_stop_bus_device()
pci_stop_dev()
pci_remove_sysfs_dev_files()
sysfs_remove_bin_file()
This attribute does not need to be created dynamically and removed
dynamically, and thus there is no need to also manage its create and
remove life cycle manually as the PCI driver core can do it when the
device is either added or removed.
Convert the "config" sysfs object created dynamically to static and use
the .is_bin_visible callback to set the correct sysfs object size
(either 256 bytes of 4 KiB) at runtime.
Then, add a newly created attribute group to the existing group called
"pci_dev_groups" to ensure that the "config" sysfs object would be
automatically included when the PCI driver initializes.
Suggested-by: Oliver O'Halloran <oohall@gmail.com>
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index f8afd54ca3e1..dc14daf404f5 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -808,6 +808,29 @@ static ssize_t pci_write_config(struct file *filp, struct kobject *kobj,
return count;
}
+static BIN_ATTR(config, 0644, pci_read_config, pci_write_config, 0);
+
+static struct bin_attribute *pci_dev_config_attrs[] = {
+ &bin_attr_config,
+ NULL,
+};
+
+static umode_t pci_dev_config_attr_is_visible(struct kobject *kobj,
+ struct bin_attribute *a, int n)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+
+ a->size = PCI_CFG_SPACE_SIZE;
+ if (pdev->cfg_size > PCI_CFG_SPACE_SIZE)
+ a->size = PCI_CFG_SPACE_EXP_SIZE;
+
+ return a->attr.mode;
+}
+
+static const struct attribute_group pci_dev_config_attr_group = {
+ .bin_attrs = pci_dev_config_attrs,
+ .is_bin_visible = pci_dev_config_attr_is_visible,
+};
#ifdef HAVE_PCI_LEGACY
/**
@@ -1284,26 +1307,6 @@ static ssize_t pci_read_rom(struct file *filp, struct kobject *kobj,
return count;
}
-static const struct bin_attribute pci_config_attr = {
- .attr = {
- .name = "config",
- .mode = 0644,
- },
- .size = PCI_CFG_SPACE_SIZE,
- .read = pci_read_config,
- .write = pci_write_config,
-};
-
-static const struct bin_attribute pcie_config_attr = {
- .attr = {
- .name = "config",
- .mode = 0644,
- },
- .size = PCI_CFG_SPACE_EXP_SIZE,
- .read = pci_read_config,
- .write = pci_write_config,
-};
-
static ssize_t reset_store(struct device *dev, struct device_attribute *attr,
const char *buf, size_t count)
{
@@ -1355,16 +1358,9 @@ int __must_check pci_create_sysfs_dev_files(struct pci_dev *pdev)
if (!sysfs_initialized)
return -EACCES;
- if (pdev->cfg_size > PCI_CFG_SPACE_SIZE)
- retval = sysfs_create_bin_file(&pdev->dev.kobj, &pcie_config_attr);
- else
- retval = sysfs_create_bin_file(&pdev->dev.kobj, &pci_config_attr);
- if (retval)
- goto err;
-
retval = pci_create_resource_files(pdev);
if (retval)
- goto err_config_file;
+ goto err;
/* If the device has a ROM, try to expose it in sysfs. */
rom_size = pci_resource_len(pdev, PCI_ROM_RESOURCE);
@@ -1405,11 +1401,6 @@ int __must_check pci_create_sysfs_dev_files(struct pci_dev *pdev)
}
err_resource_files:
pci_remove_resource_files(pdev);
-err_config_file:
- if (pdev->cfg_size > PCI_CFG_SPACE_SIZE)
- sysfs_remove_bin_file(&pdev->dev.kobj, &pcie_config_attr);
- else
- sysfs_remove_bin_file(&pdev->dev.kobj, &pci_config_attr);
err:
return retval;
}
@@ -1435,12 +1426,6 @@ void pci_remove_sysfs_dev_files(struct pci_dev *pdev)
return;
pci_remove_capabilities_sysfs(pdev);
-
- if (pdev->cfg_size > PCI_CFG_SPACE_SIZE)
- sysfs_remove_bin_file(&pdev->dev.kobj, &pcie_config_attr);
- else
- sysfs_remove_bin_file(&pdev->dev.kobj, &pci_config_attr);
-
pci_remove_resource_files(pdev);
if (pdev->rom_attr) {
@@ -1540,6 +1525,7 @@ static const struct attribute_group pci_dev_group = {
const struct attribute_group *pci_dev_groups[] = {
&pci_dev_group,
+ &pci_dev_config_attr_group,
NULL,
};
--
2.31.0
From c659a7ae6eae84ff207b2618d34630cbd9b18226 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Fri, 5 Mar 2021 00:15:23 +0000
Subject: [PATCH] PCI: Convert dynamic "rom" sysfs object into static
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The "rom" sysfs object, which is a read-only binary attribute, resides
at the "/sys/bus/pci/devices/.../rom" path and allows for accessing the
PCI ROM if the device has one.
At the moment, the "rom" sysfs object is dynamically created when the
pci_create_sysfs_dev_files() function executes that is part of the PCI
sysfs objects initialisation and when a device is added:
late_initcall()
pci_sysfs_init()
pci_create_sysfs_dev_files()
sysfs_bin_attr_init()
sysfs_create_bin_file()
pci_bus_add_devices()
pci_bus_add_device()
pci_create_sysfs_dev_files()
...
And dynamically removed when the pci_remove_sysfs_dev_files() function
executes when the PCI device is stopped and removed, as per:
pci_stop_bus_device()
pci_stop_dev()
pci_remove_sysfs_dev_files()
sysfs_remove_bin_file()
This attribute does not need to be created dynamically and removed
dynamically, and thus there is no need to also manage its create and
remove life cycle manually as the PCI driver core can do it when the
device is either added or removed.
Convert the "rom" sysfs object created dynamically to static and use the
.is_bin_visible callback to set the correct sysfs object size based on
the PCI ROM size.
Then, add a newly created attribute group to the existing group called
"pci_dev_groups" to ensure that the "rom" sysfs object would be
automatically included when the PCI driver initializes.
Remove the no longer needed pointer "rom_attr" from the struct pci_dev
that used to hold a reference to the dynamically created "rom" sysfs
object.
Suggested-by: Oliver O'Halloran <oohall@gmail.com>
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index dc14daf404f5..fa8373685140 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -1306,6 +1306,33 @@ static ssize_t pci_read_rom(struct file *filp, struct kobject *kobj,
return count;
}
+static BIN_ATTR(rom, 0600, pci_read_rom, pci_write_rom, 0);
+
+static struct bin_attribute *pci_dev_rom_attrs[] = {
+ &bin_attr_rom,
+ NULL,
+};
+
+static umode_t pci_dev_rom_attr_is_visible(struct kobject *kobj,
+ struct bin_attribute *a, int n)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+ size_t rom_size;
+
+ /* If the device has a ROM, try to expose it in sysfs. */
+ rom_size = pci_resource_len(pdev, PCI_ROM_RESOURCE);
+ if (!rom_size)
+ return 0;
+
+ a->size = rom_size;
+
+ return a->attr.mode;
+}
+
+static const struct attribute_group pci_dev_rom_attr_group = {
+ .bin_attrs = pci_dev_rom_attrs,
+ .is_bin_visible = pci_dev_rom_attr_is_visible,
+};
static ssize_t reset_store(struct device *dev, struct device_attribute *attr,
const char *buf, size_t count)
@@ -1352,8 +1379,6 @@ static int pci_create_capabilities_sysfs(struct pci_dev *dev)
int __must_check pci_create_sysfs_dev_files(struct pci_dev *pdev)
{
int retval;
- int rom_size;
- struct bin_attribute *attr;
if (!sysfs_initialized)
return -EACCES;
@@ -1362,43 +1387,15 @@ int __must_check pci_create_sysfs_dev_files(struct pci_dev *pdev)
if (retval)
goto err;
- /* If the device has a ROM, try to expose it in sysfs. */
- rom_size = pci_resource_len(pdev, PCI_ROM_RESOURCE);
- if (rom_size) {
- attr = kzalloc(sizeof(*attr), GFP_ATOMIC);
- if (!attr) {
- retval = -ENOMEM;
- goto err_resource_files;
- }
- sysfs_bin_attr_init(attr);
- attr->size = rom_size;
- attr->attr.name = "rom";
- attr->attr.mode = 0600;
- attr->read = pci_read_rom;
- attr->write = pci_write_rom;
- retval = sysfs_create_bin_file(&pdev->dev.kobj, attr);
- if (retval) {
- kfree(attr);
- goto err_resource_files;
- }
- pdev->rom_attr = attr;
- }
-
/* add sysfs entries for various capabilities */
retval = pci_create_capabilities_sysfs(pdev);
if (retval)
- goto err_rom_file;
+ goto err_resource_files;
pci_create_firmware_label_files(pdev);
return 0;
-err_rom_file:
- if (pdev->rom_attr) {
- sysfs_remove_bin_file(&pdev->dev.kobj, pdev->rom_attr);
- kfree(pdev->rom_attr);
- pdev->rom_attr = NULL;
- }
err_resource_files:
pci_remove_resource_files(pdev);
err:
@@ -1427,13 +1424,6 @@ void pci_remove_sysfs_dev_files(struct pci_dev *pdev)
pci_remove_capabilities_sysfs(pdev);
pci_remove_resource_files(pdev);
-
- if (pdev->rom_attr) {
- sysfs_remove_bin_file(&pdev->dev.kobj, pdev->rom_attr);
- kfree(pdev->rom_attr);
- pdev->rom_attr = NULL;
- }
-
pci_remove_firmware_label_files(pdev);
}
@@ -1526,6 +1516,7 @@ static const struct attribute_group pci_dev_group = {
const struct attribute_group *pci_dev_groups[] = {
&pci_dev_group,
&pci_dev_config_attr_group,
+ &pci_dev_rom_attr_group,
NULL,
};
diff --git a/include/linux/pci.h b/include/linux/pci.h
index 86c799c97b77..45f1fef80b50 100644
--- a/include/linux/pci.h
+++ b/include/linux/pci.h
@@ -458,7 +458,6 @@ struct pci_dev {
u32 saved_config_space[16]; /* Config space saved at suspend time */
struct hlist_head saved_cap_space;
- struct bin_attribute *rom_attr; /* Attribute descriptor for sysfs ROM entry */
int rom_attr_enabled; /* Display of ROM attribute enabled? */
struct bin_attribute *res_attr[DEVICE_COUNT_RESOURCE]; /* sysfs file for resources */
struct bin_attribute *res_attr_wc[DEVICE_COUNT_RESOURCE]; /* sysfs file for WC mapping of resources */
--
2.31.0
From 232eb362e788dfefab5359cc6e78d7991a5e3d66 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Fri, 5 Mar 2021 00:27:22 +0000
Subject: [PATCH] PCI: Convert dynamic "reset" sysfs object into static
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The "reset" sysfs object, which is a write-only attribute, resides at
the "/sys/bus/pci/devices/.../reset" path and allows for resetting the
PCI function of a device if the device supports resetting a single
function.
At the moment, the static "reset" sysfs object is dynamically created
when the pci_create_capabilities_sysfs() function executes that is part
of the PCI sysfs objects initialisation and when a device is added:
late_initcall()
pci_sysfs_init()
pci_create_sysfs_dev_files()
pci_create_capabilities_sysfs()
device_create_file()
pci_bus_add_devices()
pci_bus_add_device()
pci_create_sysfs_dev_files()
...
And dynamically removed when the pci_remove_capabilities_sysfs()
function executes when the PCI device is stopped and removed:
pci_stop_bus_device()
pci_stop_dev()
pci_remove_sysfs_dev_files()
pci_remove_capabilities_sysfs()
device_remove_file()
This attribute does not need to be created dynamically and removed
dynamically, and thus there is no need to also manage its create and
remove life cycle manually as the PCI driver core can do it when the
device is either added or removed.
Convert the "reset" sysfs object created dynamically to static and use
the .is_visible callback to check whether the device has a reset
function capability and to decide if the sysfs object should be made
available.
Then, add a newly created attribute group to the existing group called
"pci_dev_groups" to ensure that the "reset" sysfs object would be
automatically included when the PCI driver initialises.
Move to disable the "reset_fn" flag, and thus disabling the reset
function capability of a device, to the pci_stop_dev() function from the
pci_remove_capabilities_sysfs() function, as it makes more sense to
disable the flag when the device is about to be stopped, rather than
where sysfs objects are removed.
Suggested-by: Oliver O'Halloran <oohall@gmail.com>
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index fa8373685140..c469d9cad0a8 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -1355,25 +1355,33 @@ static ssize_t reset_store(struct device *dev, struct device_attribute *attr,
return count;
}
+static DEVICE_ATTR_WO(reset);
-static DEVICE_ATTR(reset, 0200, NULL, reset_store);
+static struct attribute *pci_dev_reset_attrs[] = {
+ &dev_attr_reset.attr,
+ NULL,
+};
-static int pci_create_capabilities_sysfs(struct pci_dev *dev)
+static umode_t pci_dev_reset_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
{
- int retval;
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- pcie_vpd_create_sysfs_dev_files(dev);
+ if (!pdev->reset_fn)
+ return 0;
- if (dev->reset_fn) {
- retval = device_create_file(&dev->dev, &dev_attr_reset);
- if (retval)
- goto error;
- }
- return 0;
+ return a->mode;
+}
-error:
- pcie_vpd_remove_sysfs_dev_files(dev);
- return retval;
+static const struct attribute_group pci_dev_reset_attr_group = {
+ .attrs = pci_dev_reset_attrs,
+ .is_visible = pci_dev_reset_attr_is_visible,
+};
+
+
+static void pci_create_capabilities_sysfs(struct pci_dev *dev)
+{
+ pcie_vpd_create_sysfs_dev_files(dev);
}
int __must_check pci_create_sysfs_dev_files(struct pci_dev *pdev)
@@ -1385,30 +1393,18 @@ int __must_check pci_create_sysfs_dev_files(struct pci_dev *pdev)
retval = pci_create_resource_files(pdev);
if (retval)
- goto err;
+ return retval;
/* add sysfs entries for various capabilities */
- retval = pci_create_capabilities_sysfs(pdev);
- if (retval)
- goto err_resource_files;
-
+ pci_create_capabilities_sysfs(pdev);
pci_create_firmware_label_files(pdev);
return 0;
-
-err_resource_files:
- pci_remove_resource_files(pdev);
-err:
- return retval;
}
static void pci_remove_capabilities_sysfs(struct pci_dev *dev)
{
pcie_vpd_remove_sysfs_dev_files(dev);
- if (dev->reset_fn) {
- device_remove_file(&dev->dev, &dev_attr_reset);
- dev->reset_fn = 0;
- }
}
/**
@@ -1517,6 +1513,7 @@ const struct attribute_group *pci_dev_groups[] = {
&pci_dev_group,
&pci_dev_config_attr_group,
&pci_dev_rom_attr_group,
+ &pci_dev_reset_attr_group,
NULL,
};
diff --git a/drivers/pci/remove.c b/drivers/pci/remove.c
index 95dec03d9f2a..dd12c2fcc7dc 100644
--- a/drivers/pci/remove.c
+++ b/drivers/pci/remove.c
@@ -19,6 +19,8 @@ static void pci_stop_dev(struct pci_dev *dev)
pci_pme_active(dev, false);
if (pci_dev_is_added(dev)) {
+ dev->reset_fn = 0;
+
device_release_driver(&dev->dev);
pci_proc_detach_device(dev);
pci_remove_sysfs_dev_files(dev);
--
2.31.0
From 6c45cc46de1f9cb4f56b2df9a8e07ea97feb7ae7 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Fri, 5 Mar 2021 00:41:10 +0000
Subject: [PATCH] PCI/VPD: Convert dynamic "vpd" sysfs object into static
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The "vpd" sysfs object, which is a read-and-write binary attribute,
resides at the "/sys/bus/pci/devices/.../vpd" path and allows for
accessing the Vital Product Data (VPD) for a device.
At the moment, the "vpd" sysfs object is dynamically created when the
pcie_vpd_create_sysfs_dev_files() function executes that is part of the
PCI sysfs objects initialisation and when a device is added:
late_initcall()
pci_sysfs_init()
pci_create_sysfs_dev_files()
pci_create_capabilities_sysfs()
pcie_vpd_create_sysfs_dev_files()
sysfs_bin_attr_init()
sysfs_create_bin_file()
pci_bus_add_devices()
pci_bus_add_device()
pci_create_sysfs_dev_files()
...
And dynamically removed when the pcie_vpd_remove_sysfs_dev_files()
function executes when the PCI device is stopped and removed:
pci_stop_bus_device()
pci_stop_dev()
pci_remove_sysfs_dev_files()
pci_remove_capabilities_sysfs()
pcie_vpd_remove_sysfs_dev_files()
sysfs_remove_bin_file()
This attribute does not need to be created dynamically and removed
dynamically, and thus there is no need to also manage its create and
remove life cycle manually as the PCI driver core can do it when the
device is either added or removed.
Convert the "vpd" sysfs object created dynamically to static and use the
.is_bin_visible callback to check whether the device supports VPD and to
decide if the sysfs object should be made available.
Then, add a newly created attribute group to the existing group called
"pci_dev_groups" to ensure that the "vpd" sysfs object would be
automatically included when the PCI driver initializes.
Remove the no longer needed pointer "attr" from the struct pci_vpd
that used to hold a reference to the dynamically created "vpd" sysfs
object.
And also remove functions such as pcie_vpd_create_sysfs_dev_files(),
pcie_vpd_remove_sysfs_dev_files(), pci_create_capabilities_sysfs() and
pci_create_capabilities_sysfs() that are no longer needed to be called
from the pci_create_sysfs_dev_files() or pci_remove_sysfs_dev_files()
functions.
Suggested-by: Oliver O'Halloran <oohall@gmail.com>
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index c469d9cad0a8..501d120e268b 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -1378,12 +1378,6 @@ static const struct attribute_group pci_dev_reset_attr_group = {
.is_visible = pci_dev_reset_attr_is_visible,
};
-
-static void pci_create_capabilities_sysfs(struct pci_dev *dev)
-{
- pcie_vpd_create_sysfs_dev_files(dev);
-}
-
int __must_check pci_create_sysfs_dev_files(struct pci_dev *pdev)
{
int retval;
@@ -1395,18 +1389,11 @@ int __must_check pci_create_sysfs_dev_files(struct pci_dev *pdev)
if (retval)
return retval;
- /* add sysfs entries for various capabilities */
- pci_create_capabilities_sysfs(pdev);
pci_create_firmware_label_files(pdev);
return 0;
}
-static void pci_remove_capabilities_sysfs(struct pci_dev *dev)
-{
- pcie_vpd_remove_sysfs_dev_files(dev);
-}
-
/**
* pci_remove_sysfs_dev_files - cleanup PCI specific sysfs files
* @pdev: device whose entries we should free
@@ -1418,7 +1405,6 @@ void pci_remove_sysfs_dev_files(struct pci_dev *pdev)
if (!sysfs_initialized)
return;
- pci_remove_capabilities_sysfs(pdev);
pci_remove_resource_files(pdev);
pci_remove_firmware_label_files(pdev);
}
@@ -1514,6 +1500,7 @@ const struct attribute_group *pci_dev_groups[] = {
&pci_dev_config_attr_group,
&pci_dev_rom_attr_group,
&pci_dev_reset_attr_group,
+ &vpd_attr_group,
NULL,
};
diff --git a/drivers/pci/pci.h b/drivers/pci/pci.h
index ef7c4661314f..0dc52e60d03c 100644
--- a/drivers/pci/pci.h
+++ b/drivers/pci/pci.h
@@ -143,8 +143,7 @@ static inline bool pcie_downstream_port(const struct pci_dev *dev)
int pci_vpd_init(struct pci_dev *dev);
void pci_vpd_release(struct pci_dev *dev);
-void pcie_vpd_create_sysfs_dev_files(struct pci_dev *dev);
-void pcie_vpd_remove_sysfs_dev_files(struct pci_dev *dev);
+extern const struct attribute_group vpd_attr_group;
/* PCI Virtual Channel */
int pci_save_vc_state(struct pci_dev *dev);
diff --git a/drivers/pci/vpd.c b/drivers/pci/vpd.c
index 7915d10f9aa1..3707671bc2f1 100644
--- a/drivers/pci/vpd.c
+++ b/drivers/pci/vpd.c
@@ -21,7 +21,6 @@ struct pci_vpd_ops {
struct pci_vpd {
const struct pci_vpd_ops *ops;
- struct bin_attribute *attr; /* Descriptor for sysfs VPD entry */
struct mutex lock;
unsigned int len;
u16 flag;
@@ -428,41 +427,28 @@ static ssize_t write_vpd_attr(struct file *filp, struct kobject *kobj,
return pci_write_vpd(dev, off, count, buf);
}
+static BIN_ATTR(vpd, 0600, read_vpd_attr, write_vpd_attr, 0);
-void pcie_vpd_create_sysfs_dev_files(struct pci_dev *dev)
-{
- int retval;
- struct bin_attribute *attr;
-
- if (!dev->vpd)
- return;
+static struct bin_attribute *vpd_attrs[] = {
+ &bin_attr_vpd,
+ NULL,
+};
- attr = kzalloc(sizeof(*attr), GFP_ATOMIC);
- if (!attr)
- return;
+static umode_t vpd_attr_is_visible(struct kobject *kobj,
+ struct bin_attribute *a, int n)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- sysfs_bin_attr_init(attr);
- attr->size = 0;
- attr->attr.name = "vpd";
- attr->attr.mode = S_IRUSR | S_IWUSR;
- attr->read = read_vpd_attr;
- attr->write = write_vpd_attr;
- retval = sysfs_create_bin_file(&dev->dev.kobj, attr);
- if (retval) {
- kfree(attr);
- return;
- }
+ if (!pdev->vpd)
+ return 0;
- dev->vpd->attr = attr;
+ return a->attr.mode;
}
-void pcie_vpd_remove_sysfs_dev_files(struct pci_dev *dev)
-{
- if (dev->vpd && dev->vpd->attr) {
- sysfs_remove_bin_file(&dev->dev.kobj, dev->vpd->attr);
- kfree(dev->vpd->attr);
- }
-}
+const struct attribute_group vpd_attr_group = {
+ .bin_attrs = vpd_attrs,
+ .is_bin_visible = vpd_attr_is_visible,
+};
int pci_vpd_find_tag(const u8 *buf, unsigned int off, unsigned int len, u8 rdt)
{
--
2.31.0
From 52a5db3359ab62e62c9218a7a23b560834a8ad21 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Fri, 12 Mar 2021 00:32:18 +0000
Subject: [PATCH] PCI: Convert dynamic "index" and "label" sysfs objects into
static
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The "index" and "label" sysfs objects, which are read-only attributes,
that reside at the "/sys/bus/pci/devices/.../index" (or "acpi_index"
with the ACPI _DSM support) and "/sys/bus/pci/devices/.../label" (when
using either SMBIOS or ACPI _DSM) paths and allow for accessing the PCI
device label, either from the BIOS (SMBIOS) or through the ACPI _DSM
(Device-Specific Methods), and the device function index.
At the moment, both the "index" (or "acpi_index") and "label" static
sysfs objects are dynamically created when the pci_create_sysfs_dev_files()
function executes that is part of the PCI sysfs objects initialisation
and when a device is added:
late_initcall()
pci_sysfs_init()
pci_create_sysfs_dev_files()
pci_create_firmware_label_files()
pci_create_acpi_index_label_files()
<--------------------------- Depending on what is supported.
pci_create_smbiosname_file()
pci_bus_add_devices()
pci_bus_add_device()
pci_create_sysfs_dev_files()
...
And dynamically removed when the pci_remove_sysfs_dev_files() function
executes when the PCI device is stopped and removed:
pci_stop_bus_device()
pci_stop_dev()
pci_remove_sysfs_dev_files()
pci_remove_firmware_label_files()
pci_remove_acpi_index_label_files()
<--------------------------- Depending on what is supported.
pci_remove_smbiosname_file()
These attributes do not need to be created dynamically and removed
dynamically, and thus there is no need to also manage their create and
remove life cycle manually as the PCI driver core can do it when the
device is either added or removed.
Convert the "index", "acpi_index" and "label" sysfs objects created
dynamically to static and use the .is_visible callback to check whether
the SMBIOS or ACPI _DSM is available to decide if and which of the sysfs
objects should be made available.
Then, add a newly created attribute group to the existing group called
"pci_dev_groups" to ensure that the "config" sysfs object would be
automatically included when the PCI driver initializes.
And also rename the device_has_dsm() function to device_has_acpi_name()
to better relfect its purpose.
Suggested-by: Oliver O'Halloran <oohall@gmail.com>
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-label.c b/drivers/pci/pci-label.c
index 781e45cf60d1..31fedc4920bb 100644
--- a/drivers/pci/pci-label.c
+++ b/drivers/pci/pci-label.c
@@ -33,6 +33,22 @@
#include <linux/pci-acpi.h>
#include "pci.h"
+static bool device_has_acpi_name(struct device *dev)
+{
+#ifdef CONFIG_ACPI
+ acpi_handle handle;
+
+ handle = ACPI_HANDLE(dev);
+ if (!handle)
+ return false;
+
+ return !!acpi_check_dsm(handle, &pci_acpi_dsm_guid, 0x2,
+ 1 << DSM_PCI_DEVICE_NAME);
+#else
+ return false;
+#endif
+}
+
#ifdef CONFIG_DMI
enum smbios_attr_enum {
SMBIOS_ATTR_NONE = 0,
@@ -45,13 +61,9 @@ static size_t find_smbios_instance_string(struct pci_dev *pdev, char *buf,
{
const struct dmi_device *dmi;
struct dmi_dev_onboard *donboard;
- int domain_nr;
- int bus;
- int devfn;
-
- domain_nr = pci_domain_nr(pdev->bus);
- bus = pdev->bus->number;
- devfn = pdev->devfn;
+ int domain_nr = pci_domain_nr(pdev->bus);
+ int bus = pdev->bus->number;
+ int devfn = pdev->devfn;
dmi = NULL;
while ((dmi = dmi_find_device(DMI_DEV_TYPE_DEV_ONBOARD,
@@ -73,81 +85,57 @@ static size_t find_smbios_instance_string(struct pci_dev *pdev, char *buf,
return strlen(dmi->name);
}
}
- return 0;
-}
-
-static umode_t smbios_instance_string_exist(struct kobject *kobj,
- struct attribute *attr, int n)
-{
- struct device *dev;
- struct pci_dev *pdev;
- dev = kobj_to_dev(kobj);
- pdev = to_pci_dev(dev);
-
- return find_smbios_instance_string(pdev, NULL, SMBIOS_ATTR_NONE) ?
- S_IRUGO : 0;
+ return 0;
}
-static ssize_t smbioslabel_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t smbios_label_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- struct pci_dev *pdev;
- pdev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(dev);
return find_smbios_instance_string(pdev, buf,
SMBIOS_ATTR_LABEL_SHOW);
}
+static struct device_attribute dev_attr_smbios_label = __ATTR(label, 0444,
+ smbios_label_show,
+ NULL);
-static ssize_t smbiosinstance_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t index_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- struct pci_dev *pdev;
- pdev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(dev);
return find_smbios_instance_string(pdev, buf,
SMBIOS_ATTR_INSTANCE_SHOW);
}
+static DEVICE_ATTR_RO(index);
-static struct device_attribute smbios_attr_label = {
- .attr = {.name = "label", .mode = 0444},
- .show = smbioslabel_show,
-};
-
-static struct device_attribute smbios_attr_instance = {
- .attr = {.name = "index", .mode = 0444},
- .show = smbiosinstance_show,
-};
-
-static struct attribute *smbios_attributes[] = {
- &smbios_attr_label.attr,
- &smbios_attr_instance.attr,
+static struct attribute *smbios_attrs[] = {
+ &dev_attr_smbios_label.attr,
+ &dev_attr_index.attr,
NULL,
};
-static const struct attribute_group smbios_attr_group = {
- .attrs = smbios_attributes,
- .is_visible = smbios_instance_string_exist,
-};
-
-static int pci_create_smbiosname_file(struct pci_dev *pdev)
+static umode_t smbios_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
{
- return sysfs_create_group(&pdev->dev.kobj, &smbios_attr_group);
-}
+ struct device *dev = kobj_to_dev(kobj);
+ struct pci_dev *pdev = to_pci_dev(dev);
-static void pci_remove_smbiosname_file(struct pci_dev *pdev)
-{
- sysfs_remove_group(&pdev->dev.kobj, &smbios_attr_group);
-}
-#else
-static inline int pci_create_smbiosname_file(struct pci_dev *pdev)
-{
- return -1;
-}
+ if (device_has_acpi_name(dev))
+ return 0;
-static inline void pci_remove_smbiosname_file(struct pci_dev *pdev)
-{
+ if (!find_smbios_instance_string(pdev, NULL, SMBIOS_ATTR_NONE))
+ return 0;
+
+ return a->mode;
}
+
+const struct attribute_group smbios_attr_group = {
+ .attrs = smbios_attrs,
+ .is_visible = smbios_attr_is_visible,
+};
#endif
#ifdef CONFIG_ACPI
@@ -209,103 +197,41 @@ static int dsm_get_label(struct device *dev, char *buf,
return len;
}
-static bool device_has_dsm(struct device *dev)
-{
- acpi_handle handle;
-
- handle = ACPI_HANDLE(dev);
- if (!handle)
- return false;
-
- return !!acpi_check_dsm(handle, &pci_acpi_dsm_guid, 0x2,
- 1 << DSM_PCI_DEVICE_NAME);
-}
-
-static umode_t acpi_index_string_exist(struct kobject *kobj,
- struct attribute *attr, int n)
-{
- struct device *dev;
-
- dev = kobj_to_dev(kobj);
-
- if (device_has_dsm(dev))
- return S_IRUGO;
-
- return 0;
-}
-
-static ssize_t acpilabel_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t acpi_label_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
return dsm_get_label(dev, buf, ACPI_ATTR_LABEL_SHOW);
}
+static struct device_attribute dev_attr_acpi_label = __ATTR(label, 0444,
+ acpi_label_show,
+ NULL);
-static ssize_t acpiindex_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t acpi_index_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
return dsm_get_label(dev, buf, ACPI_ATTR_INDEX_SHOW);
}
+static DEVICE_ATTR_RO(acpi_index);
-static struct device_attribute acpi_attr_label = {
- .attr = {.name = "label", .mode = 0444},
- .show = acpilabel_show,
-};
-
-static struct device_attribute acpi_attr_index = {
- .attr = {.name = "acpi_index", .mode = 0444},
- .show = acpiindex_show,
-};
-
-static struct attribute *acpi_attributes[] = {
- &acpi_attr_label.attr,
- &acpi_attr_index.attr,
+static struct attribute *acpi_attrs[] = {
+ &dev_attr_acpi_label.attr,
+ &dev_attr_acpi_index.attr,
NULL,
};
-static const struct attribute_group acpi_attr_group = {
- .attrs = acpi_attributes,
- .is_visible = acpi_index_string_exist,
-};
-
-static int pci_create_acpi_index_label_files(struct pci_dev *pdev)
+static umode_t acpi_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
{
- return sysfs_create_group(&pdev->dev.kobj, &acpi_attr_group);
-}
+ struct device *dev = kobj_to_dev(kobj);
-static int pci_remove_acpi_index_label_files(struct pci_dev *pdev)
-{
- sysfs_remove_group(&pdev->dev.kobj, &acpi_attr_group);
- return 0;
-}
-#else
-static inline int pci_create_acpi_index_label_files(struct pci_dev *pdev)
-{
- return -1;
-}
+ if (!device_has_acpi_name(dev))
+ return 0;
-static inline int pci_remove_acpi_index_label_files(struct pci_dev *pdev)
-{
- return -1;
+ return a->mode;
}
-static inline bool device_has_dsm(struct device *dev)
-{
- return false;
-}
+const struct attribute_group acpi_attr_group = {
+ .attrs = acpi_attrs,
+ .is_visible = acpi_attr_is_visible,
+};
#endif
-
-void pci_create_firmware_label_files(struct pci_dev *pdev)
-{
- if (device_has_dsm(&pdev->dev))
- pci_create_acpi_index_label_files(pdev);
- else
- pci_create_smbiosname_file(pdev);
-}
-
-void pci_remove_firmware_label_files(struct pci_dev *pdev)
-{
- if (device_has_dsm(&pdev->dev))
- pci_remove_acpi_index_label_files(pdev);
- else
- pci_remove_smbiosname_file(pdev);
-}
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index 501d120e268b..6a8a44d44127 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -1380,18 +1380,10 @@ static const struct attribute_group pci_dev_reset_attr_group = {
int __must_check pci_create_sysfs_dev_files(struct pci_dev *pdev)
{
- int retval;
-
if (!sysfs_initialized)
return -EACCES;
- retval = pci_create_resource_files(pdev);
- if (retval)
- return retval;
-
- pci_create_firmware_label_files(pdev);
-
- return 0;
+ return pci_create_resource_files(pdev);
}
/**
@@ -1406,7 +1398,6 @@ void pci_remove_sysfs_dev_files(struct pci_dev *pdev)
return;
pci_remove_resource_files(pdev);
- pci_remove_firmware_label_files(pdev);
}
static int __init pci_sysfs_init(void)
@@ -1501,6 +1492,12 @@ const struct attribute_group *pci_dev_groups[] = {
&pci_dev_rom_attr_group,
&pci_dev_reset_attr_group,
&vpd_attr_group,
+#ifdef CONFIG_DMI
+ &smbios_attr_group,
+#endif
+#ifdef CONFIG_ACPI
+ &acpi_attr_group,
+#endif
NULL,
};
diff --git a/drivers/pci/pci.h b/drivers/pci/pci.h
index 0dc52e60d03c..d6678124e8ea 100644
--- a/drivers/pci/pci.h
+++ b/drivers/pci/pci.h
@@ -21,16 +21,10 @@ bool pcie_cap_has_rtctl(const struct pci_dev *dev);
int pci_create_sysfs_dev_files(struct pci_dev *pdev);
void pci_remove_sysfs_dev_files(struct pci_dev *pdev);
-#if !defined(CONFIG_DMI) && !defined(CONFIG_ACPI)
-static inline void pci_create_firmware_label_files(struct pci_dev *pdev)
-{ return; }
-static inline void pci_remove_firmware_label_files(struct pci_dev *pdev)
-{ return; }
-#else
-void pci_create_firmware_label_files(struct pci_dev *pdev);
-void pci_remove_firmware_label_files(struct pci_dev *pdev);
-#endif
void pci_cleanup_rom(struct pci_dev *dev);
+#ifdef CONFIG_DMI
+extern const struct attribute_group smbios_attr_group;
+#endif
enum pci_mmap_api {
PCI_MMAP_SYSFS, /* mmap on /sys/bus/pci/devices/<BDF>/resource<N> */
@@ -695,6 +689,7 @@ static inline int pci_aer_raw_clear_status(struct pci_dev *dev) { return -EINVAL
#ifdef CONFIG_ACPI
int pci_acpi_program_hp_params(struct pci_dev *dev);
+extern const struct attribute_group acpi_attr_group;
#else
static inline int pci_acpi_program_hp_params(struct pci_dev *dev)
{
--
2.31.0
From 228a02f7a5a9fc6cc34453ce53b269bff578c433 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Sat, 10 Apr 2021 12:01:41 +0000
Subject: [PATCH] sysfs: Introduce BIN_ATTR_ADMIN_RO and BIN_ATTR_ADMIN_RW
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
A very common use case is to limit read and/or write access to certain
sysfs objects to only root with the expectation that the CAP_SYS_ADMIN
capability is needed to access sensitive data exposed through such sysfs
objects.
The existing macros such as BIN_ATTR_RO and BIN_ATTR_RW are sadly
inadequate given the specific need to limit access only to the root
user, as they offer permissions that are too open e.g., 0444 and 0644,
thus a lot of users of binary attributes with this specific use case,
for example, the PCI "config", "rom" and "vps" sysfs objects, would opt
to use the BIN_ATTR macro directly specifying 0400 or 0600 as needed.
Add a new set of macros with an explicit "ADMIN" identifier catering to
this specific use case that also follows the semantic of other existing
macros such as e.g., BIN_ATTR_RO, BIN_ATTR_RW, BIN_ATTR_WO, etc.
No functional change intended.
Related:
commit 60d360acddc5 ("driver-core: Introduce DEVICE_ATTR_ADMIN_{RO,RW}")
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/include/linux/sysfs.h b/include/linux/sysfs.h
index d76a1ddf83a3..9f423dfa8494 100644
--- a/include/linux/sysfs.h
+++ b/include/linux/sysfs.h
@@ -205,6 +205,13 @@ struct bin_attribute {
.size = _size, \
}
+#define __BIN_ATTR_RO_MODE(_name, _mode, _size) { \
+ .attr = { .name = __stringify(_name), \
+ .mode = VERIFY_OCTAL_PERMISSIONS(_mode) }, \
+ .read = _name##_read, \
+ .size = _size, \
+}
+
#define __BIN_ATTR_WO(_name, _size) { \
.attr = { .name = __stringify(_name), .mode = 0200 }, \
.write = _name##_write, \
@@ -214,6 +221,14 @@ struct bin_attribute {
#define __BIN_ATTR_RW(_name, _size) \
__BIN_ATTR(_name, 0644, _name##_read, _name##_write, _size)
+#define __BIN_ATTR_RW_MODE(_name, _mode, _size) { \
+ .attr = { .name = __stringify(_name), \
+ .mode = VERIFY_OCTAL_PERMISSIONS(_mode) }, \
+ .read = _name##_read, \
+ .write = _name##_write, \
+ .size = _size, \
+}
+
#define __BIN_ATTR_NULL __ATTR_NULL
#define BIN_ATTR(_name, _mode, _read, _write, _size) \
@@ -223,12 +238,20 @@ struct bin_attribute bin_attr_##_name = __BIN_ATTR(_name, _mode, _read, \
#define BIN_ATTR_RO(_name, _size) \
struct bin_attribute bin_attr_##_name = __BIN_ATTR_RO(_name, _size)
+#define BIN_ATTR_ADMIN_RO(_name, _size) \
+struct bin_attribute bin_attr_##_name = __BIN_ATTR_RO_MODE(_name, 0400, \
+ _size)
+
#define BIN_ATTR_WO(_name, _size) \
struct bin_attribute bin_attr_##_name = __BIN_ATTR_WO(_name, _size)
#define BIN_ATTR_RW(_name, _size) \
struct bin_attribute bin_attr_##_name = __BIN_ATTR_RW(_name, _size)
+#define BIN_ATTR_ADMIN_RW(_name, _size) \
+struct bin_attribute bin_attr_##_name = __BIN_ATTR_RW_MODE(_name, 0600, \
+ _size)
+
struct sysfs_ops {
ssize_t (*show)(struct kobject *, struct attribute *, char *);
ssize_t (*store)(struct kobject *, struct attribute *, const char *, size_t);
--
2.31.0
From c08ece8f1cd95312b054aed1a6b87fff88f25c8e Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Thu, 11 Mar 2021 23:00:14 +0000
Subject: [PATCH] PCI: Convert PCI sysfs objects to use BIN_ATTR_ADMIN_RW macro
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
Move the PCI "config", "rom" and "vpd" sysfs objects that currently use
an open coded BIN_ATTR macro to hide sensitive information that should
only be accessed by the root user to the new BIN_ATTR_ADMIN_RW macro,
and the BIN_ATTR_RW macro where otherwise appropriate.
Rename the "read" and "write" functions so that they are in the format
that is expected when using new macros as these have specific naming
requirements from the accessor functions.
No functional change intended.
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index 6a8a44d44127..07c3ddd7877e 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -666,9 +666,9 @@ static ssize_t boot_vga_show(struct device *dev, struct device_attribute *attr,
}
static DEVICE_ATTR_RO(boot_vga);
-static ssize_t pci_read_config(struct file *filp, struct kobject *kobj,
- struct bin_attribute *bin_attr, char *buf,
- loff_t off, size_t count)
+static ssize_t config_read(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *bin_attr, char *buf,
+ loff_t off, size_t count)
{
struct pci_dev *dev = to_pci_dev(kobj_to_dev(kobj));
unsigned int size = 64;
@@ -743,9 +743,9 @@ static ssize_t pci_read_config(struct file *filp, struct kobject *kobj,
return count;
}
-static ssize_t pci_write_config(struct file *filp, struct kobject *kobj,
- struct bin_attribute *bin_attr, char *buf,
- loff_t off, size_t count)
+static ssize_t config_write(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *bin_attr, char *buf,
+ loff_t off, size_t count)
{
struct pci_dev *dev = to_pci_dev(kobj_to_dev(kobj));
unsigned int size = count;
@@ -808,7 +808,7 @@ static ssize_t pci_write_config(struct file *filp, struct kobject *kobj,
return count;
}
-static BIN_ATTR(config, 0644, pci_read_config, pci_write_config, 0);
+static BIN_ATTR_RW(config, 0);
static struct bin_attribute *pci_dev_config_attrs[] = {
&bin_attr_config,
@@ -1243,7 +1243,7 @@ void __weak pci_remove_resource_files(struct pci_dev *dev) { return; }
#endif
/**
- * pci_write_rom - used to enable access to the PCI ROM display
+ * rom_write - used to enable access to the PCI ROM display
* @filp: sysfs file
* @kobj: kernel object handle
* @bin_attr: struct bin_attribute for this file
@@ -1253,9 +1253,9 @@ void __weak pci_remove_resource_files(struct pci_dev *dev) { return; }
*
* writing anything except 0 enables it
*/
-static ssize_t pci_write_rom(struct file *filp, struct kobject *kobj,
- struct bin_attribute *bin_attr, char *buf,
- loff_t off, size_t count)
+static ssize_t rom_write(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *bin_attr, char *buf,
+ loff_t off, size_t count)
{
struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
@@ -1268,7 +1268,7 @@ static ssize_t pci_write_rom(struct file *filp, struct kobject *kobj,
}
/**
- * pci_read_rom - read a PCI ROM
+ * rom_read - read a PCI ROM
* @filp: sysfs file
* @kobj: kernel object handle
* @bin_attr: struct bin_attribute for this file
@@ -1279,9 +1279,9 @@ static ssize_t pci_write_rom(struct file *filp, struct kobject *kobj,
* Put @count bytes starting at @off into @buf from the ROM in the PCI
* device corresponding to @kobj.
*/
-static ssize_t pci_read_rom(struct file *filp, struct kobject *kobj,
- struct bin_attribute *bin_attr, char *buf,
- loff_t off, size_t count)
+static ssize_t rom_read(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *bin_attr, char *buf,
+ loff_t off, size_t count)
{
struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
void __iomem *rom;
@@ -1306,7 +1306,7 @@ static ssize_t pci_read_rom(struct file *filp, struct kobject *kobj,
return count;
}
-static BIN_ATTR(rom, 0600, pci_read_rom, pci_write_rom, 0);
+static BIN_ATTR_ADMIN_RW(rom, 0);
static struct bin_attribute *pci_dev_rom_attrs[] = {
&bin_attr_rom,
diff --git a/drivers/pci/vpd.c b/drivers/pci/vpd.c
index 3707671bc2f1..c8efb9ebdfd7 100644
--- a/drivers/pci/vpd.c
+++ b/drivers/pci/vpd.c
@@ -396,9 +396,9 @@ void pci_vpd_release(struct pci_dev *dev)
kfree(dev->vpd);
}
-static ssize_t read_vpd_attr(struct file *filp, struct kobject *kobj,
- struct bin_attribute *bin_attr, char *buf,
- loff_t off, size_t count)
+static ssize_t vpd_read(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *bin_attr, char *buf,
+ loff_t off, size_t count)
{
struct pci_dev *dev = to_pci_dev(kobj_to_dev(kobj));
@@ -412,9 +412,9 @@ static ssize_t read_vpd_attr(struct file *filp, struct kobject *kobj,
return pci_read_vpd(dev, off, count, buf);
}
-static ssize_t write_vpd_attr(struct file *filp, struct kobject *kobj,
- struct bin_attribute *bin_attr, char *buf,
- loff_t off, size_t count)
+static ssize_t vpd_write(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *bin_attr, char *buf,
+ loff_t off, size_t count)
{
struct pci_dev *dev = to_pci_dev(kobj_to_dev(kobj));
@@ -427,7 +427,7 @@ static ssize_t write_vpd_attr(struct file *filp, struct kobject *kobj,
return pci_write_vpd(dev, off, count, buf);
}
-static BIN_ATTR(vpd, 0600, read_vpd_attr, write_vpd_attr, 0);
+static BIN_ATTR_ADMIN_RW(vpd, 0);
static struct bin_attribute *vpd_attrs[] = {
&bin_attr_vpd,
--
2.31.0
From 2c24f7d47e7ba9bee7d409198ba292d64c27752f Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Mon, 12 Apr 2021 01:53:31 +0000
Subject: [PATCH] PCI: Move to kstrtobool() to handle user input
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
A common use case for many PCI sysfs objects is to either enable some
functionality or trigger an action following a write to a given
attribute where the value is written would be simply either "1" or "0"
synonymous with either disabling or enabling something.
Parsing and validation of the input values are currently done using the
kstrtoul() function to convert anything in the string buffer into an
integer value - anything non-zero would be accepted as "enable" and zero
simply as "disable".
For a while now, the kernel offers another function called kstrtobool()
which was created to parse common user inputs into a boolean value, so
that a range of values such as "y", "n", "1", "0", "on" and "off"
handled in a case-insensitive manner would yield a boolean true or false
result accordingly after the input string has been parsed.
Thus, move to kstrtobool() over kstrtoul() as it's a better fit for
parsing user input, and it also implicitly offers a range check as only
a finite amount of possible input values will be considered as valid.
Where appropriate, move the user input parsing after checking for
whether the "CAP_SYS_ADMIN" flag is set, as it makes more sense to first
check whether the current user has the right permissions before
accepting any input from such user.
Related:
commit d0f1fed29e6e ("Add a strtobool function matching semantics of existing in kernel equivalents")
commit ef951599074b ("lib: move strtobool() to kstrtobool()")
commit a81a5a17d44b ("lib: add "on"/"off" support to kstrtobool")
commit 1404297ebf76 ("lib: update single-char callers of strtobool()")
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index 07c3ddd7877e..9ee003cc4375 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -64,12 +64,12 @@ static ssize_t broken_parity_status_store(struct device *dev,
const char *buf, size_t count)
{
struct pci_dev *pdev = to_pci_dev(dev);
- unsigned long val;
+ bool broken;
- if (kstrtoul(buf, 0, &val) < 0)
+ if (kstrtobool(buf, &broken) < 0)
return -EINVAL;
- pdev->broken_parity_status = !!val;
+ pdev->broken_parity_status = !!broken;
return count;
}
@@ -272,20 +272,20 @@ static ssize_t enable_store(struct device *dev, struct device_attribute *attr,
const char *buf, size_t count)
{
struct pci_dev *pdev = to_pci_dev(dev);
- unsigned long val;
- ssize_t result = kstrtoul(buf, 0, &val);
-
- if (result < 0)
- return result;
+ bool enable;
+ ssize_t result = 0;
/* this can crash the machine when done on the "wrong" device */
if (!capable(CAP_SYS_ADMIN))
return -EPERM;
+ if (kstrtobool(buf, &enable) < 0)
+ return -EINVAL;
+
device_lock(dev);
if (dev->driver)
result = -EBUSY;
- else if (val)
+ else if (enable)
result = pci_enable_device(pdev);
else if (pci_is_enabled(pdev))
pci_disable_device(pdev);
@@ -312,14 +312,13 @@ static ssize_t numa_node_store(struct device *dev,
size_t count)
{
struct pci_dev *pdev = to_pci_dev(dev);
- int node, ret;
+ int node;
if (!capable(CAP_SYS_ADMIN))
return -EPERM;
- ret = kstrtoint(buf, 0, &node);
- if (ret)
- return ret;
+ if (kstrtoint(buf, 0, &node) < 0)
+ return -EINVAL;
if ((node < 0 && node != NUMA_NO_NODE) || node >= MAX_NUMNODES)
return -EINVAL;
@@ -376,46 +375,46 @@ static ssize_t msi_bus_store(struct device *dev, struct device_attribute *attr,
{
struct pci_dev *pdev = to_pci_dev(dev);
struct pci_bus *subordinate = pdev->subordinate;
- unsigned long val;
-
- if (kstrtoul(buf, 0, &val) < 0)
- return -EINVAL;
+ bool allowed;
if (!capable(CAP_SYS_ADMIN))
return -EPERM;
+ if (kstrtobool(buf, &allowed) < 0)
+ return -EINVAL;
+
/*
* "no_msi" and "bus_flags" only affect what happens when a driver
* requests MSI or MSI-X. They don't affect any drivers that have
* already requested MSI or MSI-X.
*/
if (!subordinate) {
- pdev->no_msi = !val;
+ pdev->no_msi = !allowed;
pci_info(pdev, "MSI/MSI-X %s for future drivers\n",
- val ? "allowed" : "disallowed");
+ allowed ? "allowed" : "disallowed");
return count;
}
- if (val)
+ if (allowed)
subordinate->bus_flags &= ~PCI_BUS_FLAGS_NO_MSI;
else
subordinate->bus_flags |= PCI_BUS_FLAGS_NO_MSI;
dev_info(&subordinate->dev, "MSI/MSI-X %s for future drivers of devices on this bus\n",
- val ? "allowed" : "disallowed");
+ allowed ? "allowed" : "disallowed");
return count;
}
static DEVICE_ATTR_RW(msi_bus);
static ssize_t rescan_store(struct bus_type *bus, const char *buf, size_t count)
{
- unsigned long val;
+ bool rescan;
struct pci_bus *b = NULL;
- if (kstrtoul(buf, 0, &val) < 0)
+ if (kstrtobool(buf, &rescan) < 0)
return -EINVAL;
- if (val) {
+ if (rescan) {
pci_lock_rescan_remove();
while ((b = pci_find_next_bus(b)) != NULL)
pci_rescan_bus(b);
@@ -443,13 +442,13 @@ static ssize_t dev_rescan_store(struct device *dev,
struct device_attribute *attr, const char *buf,
size_t count)
{
- unsigned long val;
+ bool rescan;
struct pci_dev *pdev = to_pci_dev(dev);
- if (kstrtoul(buf, 0, &val) < 0)
+ if (kstrtobool(buf, &rescan) < 0)
return -EINVAL;
- if (val) {
+ if (rescan) {
pci_lock_rescan_remove();
pci_rescan_bus(pdev->bus);
pci_unlock_rescan_remove();
@@ -462,12 +461,12 @@ static struct device_attribute dev_attr_dev_rescan = __ATTR(rescan, 0200, NULL,
static ssize_t remove_store(struct device *dev, struct device_attribute *attr,
const char *buf, size_t count)
{
- unsigned long val;
+ bool remove;
- if (kstrtoul(buf, 0, &val) < 0)
+ if (kstrtobool(buf, &remove) < 0)
return -EINVAL;
- if (val && device_remove_file_self(dev, attr))
+ if (remove && device_remove_file_self(dev, attr))
pci_stop_and_remove_bus_device_locked(to_pci_dev(dev));
return count;
}
@@ -478,13 +477,13 @@ static ssize_t bus_rescan_store(struct device *dev,
struct device_attribute *attr,
const char *buf, size_t count)
{
- unsigned long val;
+ bool rescan;
struct pci_bus *bus = to_pci_bus(dev);
- if (kstrtoul(buf, 0, &val) < 0)
+ if (kstrtobool(buf, &rescan) < 0)
return -EINVAL;
- if (val) {
+ if (rescan) {
pci_lock_rescan_remove();
if (!pci_is_root_bus(bus) && list_empty(&bus->devices))
pci_rescan_bus_bridge_resize(bus->self);
@@ -503,12 +502,12 @@ static ssize_t d3cold_allowed_store(struct device *dev,
const char *buf, size_t count)
{
struct pci_dev *pdev = to_pci_dev(dev);
- unsigned long val;
+ bool allowed;
- if (kstrtoul(buf, 0, &val) < 0)
+ if (kstrtobool(buf, &allowed) < 0)
return -EINVAL;
- pdev->d3cold_allowed = !!val;
+ pdev->d3cold_allowed = !!allowed;
if (pdev->d3cold_allowed)
pci_d3cold_enable(pdev);
else
@@ -1257,12 +1256,13 @@ static ssize_t rom_write(struct file *filp, struct kobject *kobj,
struct bin_attribute *bin_attr, char *buf,
loff_t off, size_t count)
{
+ bool allowed;
struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- if ((off == 0) && (*buf == '0') && (count == 2))
- pdev->rom_attr_enabled = 0;
- else
- pdev->rom_attr_enabled = 1;
+ if (kstrtobool(buf, &allowed) < 0)
+ return -EINVAL;
+
+ pdev->rom_attr_enabled = !!allowed;
return count;
}
@@ -1337,14 +1337,14 @@ static const struct attribute_group pci_dev_rom_attr_group = {
static ssize_t reset_store(struct device *dev, struct device_attribute *attr,
const char *buf, size_t count)
{
+ bool reset;
struct pci_dev *pdev = to_pci_dev(dev);
- unsigned long val;
- ssize_t result = kstrtoul(buf, 0, &val);
+ ssize_t result;
- if (result < 0)
- return result;
+ if (kstrtobool(buf, &reset) < 0)
+ return -EINVAL;
- if (val != 1)
+ if (!reset)
return -EINVAL;
pm_runtime_get_sync(dev);
--
2.31.0
From dcc301e1097163ea439766f9f64bbe395c2ec025 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Sun, 11 Apr 2021 12:09:58 +0000
Subject: [PATCH] PCI: Use sysfs_emit() and sysfs_emit_at() in "show" functions
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The sysfs_emit() and sysfs_emit_at() functions were introduced to make
it less ambiguous which function is preferred when writing to the output
buffer in a device attribute's "show" callback [1].
Convert the PCI sysfs object "show" functions from sprintf(), snprintf()
and scnprintf() to sysfs_emit() and sysfs_emit_at() accordingly, as the
latter is aware of the PAGE_SIZE buffer and correctly returns the number
of bytes written into the buffer.
No functional change intended.
[1] Documentation/filesystems/sysfs.rst
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-label.c b/drivers/pci/pci-label.c
index 31fedc4920bb..0ef863e598ad 100644
--- a/drivers/pci/pci-label.c
+++ b/drivers/pci/pci-label.c
@@ -74,13 +74,11 @@ static size_t find_smbios_instance_string(struct pci_dev *pdev, char *buf,
donboard->devfn == devfn) {
if (buf) {
if (attribute == SMBIOS_ATTR_INSTANCE_SHOW)
- return scnprintf(buf, PAGE_SIZE,
- "%d\n",
- donboard->instance);
+ return sysfs_emit(buf, "%d\n",
+ donboard->instance);
else if (attribute == SMBIOS_ATTR_LABEL_SHOW)
- return scnprintf(buf, PAGE_SIZE,
- "%s\n",
- dmi->name);
+ return sysfs_emit(buf, "%s\n",
+ dmi->name);
}
return strlen(dmi->name);
}
@@ -144,14 +142,17 @@ enum acpi_attr_enum {
ACPI_ATTR_INDEX_SHOW,
};
-static void dsm_label_utf16s_to_utf8s(union acpi_object *obj, char *buf)
+static int dsm_label_utf16s_to_utf8s(union acpi_object *obj, char *buf)
{
int len;
+
len = utf16s_to_utf8s((const wchar_t *)obj->buffer.pointer,
obj->buffer.length,
UTF16_LITTLE_ENDIAN,
buf, PAGE_SIZE);
buf[len] = '\n';
+
+ return strlen(buf);
}
static int dsm_get_label(struct device *dev, char *buf,
@@ -159,7 +160,7 @@ static int dsm_get_label(struct device *dev, char *buf,
{
acpi_handle handle;
union acpi_object *obj, *tmp;
- int len = -1;
+ int len = 0;
handle = ACPI_HANDLE(dev);
if (!handle)
@@ -181,20 +182,22 @@ static int dsm_get_label(struct device *dev, char *buf,
* this entry must return a null string.
*/
if (attr == ACPI_ATTR_INDEX_SHOW) {
- scnprintf(buf, PAGE_SIZE, "%llu\n", tmp->integer.value);
+ len = sysfs_emit(buf, "%llu\n", tmp->integer.value);
} else if (attr == ACPI_ATTR_LABEL_SHOW) {
if (tmp[1].type == ACPI_TYPE_STRING)
- scnprintf(buf, PAGE_SIZE, "%s\n",
- tmp[1].string.pointer);
+ len = sysfs_emit(buf, "%s\n",
+ tmp[1].string.pointer);
else if (tmp[1].type == ACPI_TYPE_BUFFER)
- dsm_label_utf16s_to_utf8s(tmp + 1, buf);
+ len = dsm_label_utf16s_to_utf8s(tmp + 1, buf);
}
- len = strlen(buf) > 0 ? strlen(buf) : -1;
}
ACPI_FREE(obj);
- return len;
+ if (len > 0)
+ return len;
+
+ return -1;
}
static ssize_t acpi_label_show(struct device *dev,
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index 9ee003cc4375..c47c30cf063e 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -39,7 +39,7 @@ field##_show(struct device *dev, struct device_attribute *attr, char *buf) \
struct pci_dev *pdev; \
\
pdev = to_pci_dev(dev); \
- return sprintf(buf, format_string, pdev->field); \
+ return sysfs_emit(buf, format_string, pdev->field); \
} \
static DEVICE_ATTR_RO(field)
@@ -56,7 +56,7 @@ static ssize_t broken_parity_status_show(struct device *dev,
char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sprintf(buf, "%u\n", pdev->broken_parity_status);
+ return sysfs_emit(buf, "%u\n", pdev->broken_parity_status);
}
static ssize_t broken_parity_status_store(struct device *dev,
@@ -129,7 +129,7 @@ static ssize_t power_state_show(struct device *dev,
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sprintf(buf, "%s\n", pci_power_name(pdev->current_state));
+ return sysfs_emit(buf, "%s\n", pci_power_name(pdev->current_state));
}
static DEVICE_ATTR_RO(power_state);
@@ -138,10 +138,10 @@ static ssize_t resource_show(struct device *dev, struct device_attribute *attr,
char *buf)
{
struct pci_dev *pci_dev = to_pci_dev(dev);
- char *str = buf;
int i;
int max;
resource_size_t start, end;
+ size_t len = 0;
if (pci_dev->subordinate)
max = DEVICE_COUNT_RESOURCE;
@@ -151,12 +151,12 @@ static ssize_t resource_show(struct device *dev, struct device_attribute *attr,
for (i = 0; i < max; i++) {
struct resource *res = &pci_dev->resource[i];
pci_resource_to_user(pci_dev, i, res, &start, &end);
- str += sprintf(str, "0x%016llx 0x%016llx 0x%016llx\n",
- (unsigned long long)start,
- (unsigned long long)end,
- (unsigned long long)res->flags);
+ len += sysfs_emit_at(buf, len, "0x%016llx 0x%016llx 0x%016llx\n",
+ (unsigned long long)start,
+ (unsigned long long)end,
+ (unsigned long long)res->flags);
}
- return (str - buf);
+ return len;
}
static DEVICE_ATTR_RO(resource);
@@ -165,8 +165,8 @@ static ssize_t max_link_speed_show(struct device *dev,
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sprintf(buf, "%s\n",
- pci_speed_string(pcie_get_speed_cap(pdev)));
+ return sysfs_emit(buf, "%s\n",
+ pci_speed_string(pcie_get_speed_cap(pdev)));
}
static DEVICE_ATTR_RO(max_link_speed);
@@ -175,7 +175,7 @@ static ssize_t max_link_width_show(struct device *dev,
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sprintf(buf, "%u\n", pcie_get_width_cap(pdev));
+ return sysfs_emit(buf, "%u\n", pcie_get_width_cap(pdev));
}
static DEVICE_ATTR_RO(max_link_width);
@@ -183,17 +183,11 @@ static ssize_t current_link_speed_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
struct pci_dev *pci_dev = to_pci_dev(dev);
- u16 linkstat;
- int err;
enum pci_bus_speed speed;
- err = pcie_capability_read_word(pci_dev, PCI_EXP_LNKSTA, &linkstat);
- if (err)
- return -EINVAL;
-
- speed = pcie_link_speed[linkstat & PCI_EXP_LNKSTA_CLS];
+ pcie_bandwidth_available(pci_dev, NULL, &speed, NULL);
- return sprintf(buf, "%s\n", pci_speed_string(speed));
+ return sysfs_emit(buf, "%s\n", pci_speed_string(speed));
}
static DEVICE_ATTR_RO(current_link_speed);
@@ -201,15 +195,11 @@ static ssize_t current_link_width_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
struct pci_dev *pci_dev = to_pci_dev(dev);
- u16 linkstat;
- int err;
+ enum pcie_link_width width;
- err = pcie_capability_read_word(pci_dev, PCI_EXP_LNKSTA, &linkstat);
- if (err)
- return -EINVAL;
+ pcie_bandwidth_available(pci_dev, NULL, NULL, &width);
- return sprintf(buf, "%u\n",
- (linkstat & PCI_EXP_LNKSTA_NLW) >> PCI_EXP_LNKSTA_NLW_SHIFT);
+ return sysfs_emit(buf, "%u\n", width);
}
static DEVICE_ATTR_RO(current_link_width);
@@ -225,7 +215,7 @@ static ssize_t secondary_bus_number_show(struct device *dev,
if (err)
return -EINVAL;
- return sprintf(buf, "%u\n", sec_bus);
+ return sysfs_emit(buf, "%u\n", sec_bus);
}
static DEVICE_ATTR_RO(secondary_bus_number);
@@ -241,7 +231,7 @@ static ssize_t subordinate_bus_number_show(struct device *dev,
if (err)
return -EINVAL;
- return sprintf(buf, "%u\n", sub_bus);
+ return sysfs_emit(buf, "%u\n", sub_bus);
}
static DEVICE_ATTR_RO(subordinate_bus_number);
@@ -251,7 +241,7 @@ static ssize_t ari_enabled_show(struct device *dev,
{
struct pci_dev *pci_dev = to_pci_dev(dev);
- return sprintf(buf, "%u\n", pci_ari_enabled(pci_dev->bus));
+ return sysfs_emit(buf, "%u\n", pci_ari_enabled(pci_dev->bus));
}
static DEVICE_ATTR_RO(ari_enabled);
@@ -260,11 +250,11 @@ static ssize_t modalias_show(struct device *dev, struct device_attribute *attr,
{
struct pci_dev *pci_dev = to_pci_dev(dev);
- return sprintf(buf, "pci:v%08Xd%08Xsv%08Xsd%08Xbc%02Xsc%02Xi%02X\n",
- pci_dev->vendor, pci_dev->device,
- pci_dev->subsystem_vendor, pci_dev->subsystem_device,
- (u8)(pci_dev->class >> 16), (u8)(pci_dev->class >> 8),
- (u8)(pci_dev->class));
+ return sysfs_emit(buf, "pci:v%08Xd%08Xsv%08Xsd%08Xbc%02Xsc%02Xi%02X\n",
+ pci_dev->vendor, pci_dev->device,
+ pci_dev->subsystem_vendor, pci_dev->subsystem_device,
+ (u8)(pci_dev->class >> 16), (u8)(pci_dev->class >> 8),
+ (u8)(pci_dev->class));
}
static DEVICE_ATTR_RO(modalias);
@@ -302,7 +292,7 @@ static ssize_t enable_show(struct device *dev, struct device_attribute *attr,
struct pci_dev *pdev;
pdev = to_pci_dev(dev);
- return sprintf(buf, "%u\n", atomic_read(&pdev->enable_cnt));
+ return sysfs_emit(buf, "%u\n", atomic_read(&pdev->enable_cnt));
}
static DEVICE_ATTR_RW(enable);
@@ -337,7 +327,7 @@ static ssize_t numa_node_store(struct device *dev,
static ssize_t numa_node_show(struct device *dev, struct device_attribute *attr,
char *buf)
{
- return sprintf(buf, "%d\n", dev->numa_node);
+ return sysfs_emit(buf, "%d\n", dev->numa_node);
}
static DEVICE_ATTR_RW(numa_node);
#endif
@@ -347,7 +337,7 @@ static ssize_t dma_mask_bits_show(struct device *dev,
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sprintf(buf, "%d\n", fls64(pdev->dma_mask));
+ return sysfs_emit(buf, "%d\n", fls64(pdev->dma_mask));
}
static DEVICE_ATTR_RO(dma_mask_bits);
@@ -355,7 +345,7 @@ static ssize_t consistent_dma_mask_bits_show(struct device *dev,
struct device_attribute *attr,
char *buf)
{
- return sprintf(buf, "%d\n", fls64(dev->coherent_dma_mask));
+ return sysfs_emit(buf, "%d\n", fls64(dev->coherent_dma_mask));
}
static DEVICE_ATTR_RO(consistent_dma_mask_bits);
@@ -365,9 +355,9 @@ static ssize_t msi_bus_show(struct device *dev, struct device_attribute *attr,
struct pci_dev *pdev = to_pci_dev(dev);
struct pci_bus *subordinate = pdev->subordinate;
- return sprintf(buf, "%u\n", subordinate ?
- !(subordinate->bus_flags & PCI_BUS_FLAGS_NO_MSI)
- : !pdev->no_msi);
+ return sysfs_emit(buf, "%u\n", subordinate ?
+ !(subordinate->bus_flags & PCI_BUS_FLAGS_NO_MSI)
+ : !pdev->no_msi);
}
static ssize_t msi_bus_store(struct device *dev, struct device_attribute *attr,
@@ -522,7 +512,7 @@ static ssize_t d3cold_allowed_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sprintf(buf, "%u\n", pdev->d3cold_allowed);
+ return sysfs_emit(buf, "%u\n", pdev->d3cold_allowed);
}
static DEVICE_ATTR_RW(d3cold_allowed);
#endif
@@ -536,7 +526,7 @@ static ssize_t devspec_show(struct device *dev,
if (np == NULL)
return 0;
- return sprintf(buf, "%pOF", np);
+ return sysfs_emit(buf, "%pOF", np);
}
static DEVICE_ATTR_RO(devspec);
#endif
@@ -582,7 +572,7 @@ static ssize_t driver_override_show(struct device *dev,
ssize_t len;
device_lock(dev);
- len = scnprintf(buf, PAGE_SIZE, "%s\n", pdev->driver_override);
+ len = sysfs_emit(buf, "%s\n", pdev->driver_override);
device_unlock(dev);
return len;
}
@@ -657,11 +647,11 @@ static ssize_t boot_vga_show(struct device *dev, struct device_attribute *attr,
struct pci_dev *vga_dev = vga_default_device();
if (vga_dev)
- return sprintf(buf, "%u\n", (pdev == vga_dev));
+ return sysfs_emit(buf, "%u\n", (pdev == vga_dev));
- return sprintf(buf, "%u\n",
- !!(pdev->resource[PCI_ROM_RESOURCE].flags &
- IORESOURCE_ROM_SHADOW));
+ return sysfs_emit(buf, "%u\n",
+ !!(pdev->resource[PCI_ROM_RESOURCE].flags &
+ IORESOURCE_ROM_SHADOW));
}
static DEVICE_ATTR_RO(boot_vga);
--
2.31.0
From 700251e8b6f28de402120f39e010ee7cf84d88c0 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Sat, 10 Apr 2021 13:17:25 +0000
Subject: [PATCH] PCI: Update style to be more consistent
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The number of sysfs object added to the PCI device grew over time, and
with each addition, the style of the code in the pci-sysfc.c file also
changed.
Thus, update to coding style in the file, so that it's consistent:
- Update variable naming
- Sort variables in the order of use
- Update functions signatures to be more aligned
- Correct white spaces and indentation
- Remove ternary operator in favour of the if-else style
- Update brackets and if-statements to better match kernel code style
Also, rename the .is_visible and .bin_is_visible callbacks functions so
that these end with the "_is_visible" suffix, rather than "_are_visible"
to be consistent with rest of the code in the kernel.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index c47c30cf063e..96302b63f6c5 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -12,7 +12,6 @@
* Modeled after usb's driverfs.c
*/
-
#include <linux/kernel.h>
#include <linux/sched.h>
#include <linux/pci.h>
@@ -36,9 +35,8 @@ static int sysfs_initialized; /* = 0 */
static ssize_t \
field##_show(struct device *dev, struct device_attribute *attr, char *buf) \
{ \
- struct pci_dev *pdev; \
+ struct pci_dev *pdev = to_pci_dev(dev); \
\
- pdev = to_pci_dev(dev); \
return sysfs_emit(buf, format_string, pdev->field); \
} \
static DEVICE_ATTR_RO(field)
@@ -56,6 +54,7 @@ static ssize_t broken_parity_status_show(struct device *dev,
char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
+
return sysfs_emit(buf, "%u\n", pdev->broken_parity_status);
}
@@ -63,8 +62,8 @@ static ssize_t broken_parity_status_store(struct device *dev,
struct device_attribute *attr,
const char *buf, size_t count)
{
- struct pci_dev *pdev = to_pci_dev(dev);
bool broken;
+ struct pci_dev *pdev = to_pci_dev(dev);
if (kstrtobool(buf, &broken) < 0)
return -EINVAL;
@@ -79,12 +78,17 @@ static ssize_t pci_dev_show_local_cpu(struct device *dev, bool list,
struct device_attribute *attr, char *buf)
{
const struct cpumask *mask;
-
#ifdef CONFIG_NUMA
- mask = (dev_to_node(dev) == -1) ? cpu_online_mask :
- cpumask_of_node(dev_to_node(dev));
+ int node = dev_to_node(dev);
+
+ if (node == NUMA_NO_NODE)
+ mask = cpu_online_mask;
+ else
+ mask = cpumask_of_node(node);
#else
- mask = cpumask_of_pcibus(to_pci_dev(dev)->bus);
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ mask = cpumask_of_pcibus(pdev->bus);
#endif
return cpumap_print_to_pagebuf(list, buf, mask);
}
@@ -109,7 +113,8 @@ static DEVICE_ATTR_RO(local_cpulist);
static ssize_t cpuaffinity_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
- const struct cpumask *cpumask = cpumask_of_pcibus(to_pci_bus(dev));
+ struct pci_bus *bus = to_pci_bus(dev);
+ const struct cpumask *cpumask = cpumask_of_pcibus(bus);
return cpumap_print_to_pagebuf(false, buf, cpumask);
}
@@ -118,7 +123,8 @@ static DEVICE_ATTR_RO(cpuaffinity);
static ssize_t cpulistaffinity_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
- const struct cpumask *cpumask = cpumask_of_pcibus(to_pci_bus(dev));
+ struct pci_bus *bus = to_pci_bus(dev);
+ const struct cpumask *cpumask = cpumask_of_pcibus(bus);
return cpumap_print_to_pagebuf(true, buf, cpumask);
}
@@ -134,28 +140,28 @@ static ssize_t power_state_show(struct device *dev,
static DEVICE_ATTR_RO(power_state);
/* show resources */
-static ssize_t resource_show(struct device *dev, struct device_attribute *attr,
- char *buf)
+static ssize_t resource_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- struct pci_dev *pci_dev = to_pci_dev(dev);
- int i;
- int max;
+ int i, max;
+ struct pci_dev *pdev = to_pci_dev(dev);
+ struct resource *res;
resource_size_t start, end;
size_t len = 0;
- if (pci_dev->subordinate)
+ max = PCI_BRIDGE_RESOURCES;
+ if (pdev->subordinate)
max = DEVICE_COUNT_RESOURCE;
- else
- max = PCI_BRIDGE_RESOURCES;
for (i = 0; i < max; i++) {
- struct resource *res = &pci_dev->resource[i];
- pci_resource_to_user(pci_dev, i, res, &start, &end);
+ res = &pdev->resource[i];
+ pci_resource_to_user(pdev, i, res, &start, &end);
len += sysfs_emit_at(buf, len, "0x%016llx 0x%016llx 0x%016llx\n",
(unsigned long long)start,
(unsigned long long)end,
(unsigned long long)res->flags);
}
+
return len;
}
static DEVICE_ATTR_RO(resource);
@@ -182,10 +188,10 @@ static DEVICE_ATTR_RO(max_link_width);
static ssize_t current_link_speed_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
- struct pci_dev *pci_dev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(dev);
enum pci_bus_speed speed;
- pcie_bandwidth_available(pci_dev, NULL, &speed, NULL);
+ pcie_bandwidth_available(pdev, NULL, &speed, NULL);
return sysfs_emit(buf, "%s\n", pci_speed_string(speed));
}
@@ -194,10 +200,10 @@ static DEVICE_ATTR_RO(current_link_speed);
static ssize_t current_link_width_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
- struct pci_dev *pci_dev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(dev);
enum pcie_link_width width;
- pcie_bandwidth_available(pci_dev, NULL, NULL, &width);
+ pcie_bandwidth_available(pdev, NULL, NULL, &width);
return sysfs_emit(buf, "%u\n", width);
}
@@ -207,11 +213,11 @@ static ssize_t secondary_bus_number_show(struct device *dev,
struct device_attribute *attr,
char *buf)
{
- struct pci_dev *pci_dev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(dev);
u8 sec_bus;
int err;
- err = pci_read_config_byte(pci_dev, PCI_SECONDARY_BUS, &sec_bus);
+ err = pci_read_config_byte(pdev, PCI_SECONDARY_BUS, &sec_bus);
if (err)
return -EINVAL;
@@ -223,11 +229,11 @@ static ssize_t subordinate_bus_number_show(struct device *dev,
struct device_attribute *attr,
char *buf)
{
- struct pci_dev *pci_dev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(dev);
u8 sub_bus;
int err;
- err = pci_read_config_byte(pci_dev, PCI_SUBORDINATE_BUS, &sub_bus);
+ err = pci_read_config_byte(pdev, PCI_SUBORDINATE_BUS, &sub_bus);
if (err)
return -EINVAL;
@@ -236,34 +242,34 @@ static ssize_t subordinate_bus_number_show(struct device *dev,
static DEVICE_ATTR_RO(subordinate_bus_number);
static ssize_t ari_enabled_show(struct device *dev,
- struct device_attribute *attr,
- char *buf)
+ struct device_attribute *attr, char *buf)
{
- struct pci_dev *pci_dev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(dev);
- return sysfs_emit(buf, "%u\n", pci_ari_enabled(pci_dev->bus));
+ return sysfs_emit(buf, "%u\n", pci_ari_enabled(pdev->bus));
}
static DEVICE_ATTR_RO(ari_enabled);
-static ssize_t modalias_show(struct device *dev, struct device_attribute *attr,
- char *buf)
+static ssize_t modalias_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- struct pci_dev *pci_dev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(dev);
return sysfs_emit(buf, "pci:v%08Xd%08Xsv%08Xsd%08Xbc%02Xsc%02Xi%02X\n",
- pci_dev->vendor, pci_dev->device,
- pci_dev->subsystem_vendor, pci_dev->subsystem_device,
- (u8)(pci_dev->class >> 16), (u8)(pci_dev->class >> 8),
- (u8)(pci_dev->class));
+ pdev->vendor, pdev->device,
+ pdev->subsystem_vendor, pdev->subsystem_device,
+ (u8)(pdev->class >> 16), (u8)(pdev->class >> 8),
+ (u8)(pdev->class));
}
static DEVICE_ATTR_RO(modalias);
-static ssize_t enable_store(struct device *dev, struct device_attribute *attr,
- const char *buf, size_t count)
+static ssize_t enable_store(struct device *dev,
+ struct device_attribute *attr, const char *buf,
+ size_t count)
{
- struct pci_dev *pdev = to_pci_dev(dev);
bool enable;
- ssize_t result = 0;
+ struct pci_dev *pdev = to_pci_dev(dev);
+ ssize_t ret = 0;
/* this can crash the machine when done on the "wrong" device */
if (!capable(CAP_SYS_ADMIN))
@@ -274,24 +280,26 @@ static ssize_t enable_store(struct device *dev, struct device_attribute *attr,
device_lock(dev);
if (dev->driver)
- result = -EBUSY;
+ ret = -EBUSY;
else if (enable)
- result = pci_enable_device(pdev);
+ ret = pci_enable_device(pdev);
else if (pci_is_enabled(pdev))
pci_disable_device(pdev);
else
- result = -EIO;
+ ret = -EIO;
device_unlock(dev);
- return result < 0 ? result : count;
+ if (ret < 0)
+ return ret;
+
+ return count;
}
-static ssize_t enable_show(struct device *dev, struct device_attribute *attr,
- char *buf)
+static ssize_t enable_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- struct pci_dev *pdev;
+ struct pci_dev *pdev = to_pci_dev(dev);
- pdev = to_pci_dev(dev);
return sysfs_emit(buf, "%u\n", atomic_read(&pdev->enable_cnt));
}
static DEVICE_ATTR_RW(enable);
@@ -301,8 +309,8 @@ static ssize_t numa_node_store(struct device *dev,
struct device_attribute *attr, const char *buf,
size_t count)
{
- struct pci_dev *pdev = to_pci_dev(dev);
int node;
+ struct pci_dev *pdev = to_pci_dev(dev);
if (!capable(CAP_SYS_ADMIN))
return -EPERM;
@@ -321,11 +329,12 @@ static ssize_t numa_node_store(struct device *dev,
node);
dev->numa_node = node;
+
return count;
}
-static ssize_t numa_node_show(struct device *dev, struct device_attribute *attr,
- char *buf)
+static ssize_t numa_node_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
return sysfs_emit(buf, "%d\n", dev->numa_node);
}
@@ -349,8 +358,8 @@ static ssize_t consistent_dma_mask_bits_show(struct device *dev,
}
static DEVICE_ATTR_RO(consistent_dma_mask_bits);
-static ssize_t msi_bus_show(struct device *dev, struct device_attribute *attr,
- char *buf)
+static ssize_t msi_bus_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
struct pci_bus *subordinate = pdev->subordinate;
@@ -360,12 +369,13 @@ static ssize_t msi_bus_show(struct device *dev, struct device_attribute *attr,
: !pdev->no_msi);
}
-static ssize_t msi_bus_store(struct device *dev, struct device_attribute *attr,
- const char *buf, size_t count)
+static ssize_t msi_bus_store(struct device *dev,
+ struct device_attribute *attr, const char *buf,
+ size_t count)
{
+ bool allowed;
struct pci_dev *pdev = to_pci_dev(dev);
struct pci_bus *subordinate = pdev->subordinate;
- bool allowed;
if (!capable(CAP_SYS_ADMIN))
return -EPERM;
@@ -392,6 +402,7 @@ static ssize_t msi_bus_store(struct device *dev, struct device_attribute *attr,
dev_info(&subordinate->dev, "MSI/MSI-X %s for future drivers of devices on this bus\n",
allowed ? "allowed" : "disallowed");
+
return count;
}
static DEVICE_ATTR_RW(msi_bus);
@@ -410,6 +421,7 @@ static ssize_t rescan_store(struct bus_type *bus, const char *buf, size_t count)
pci_rescan_bus(b);
pci_unlock_rescan_remove();
}
+
return count;
}
static BUS_ATTR_WO(rescan);
@@ -443,29 +455,32 @@ static ssize_t dev_rescan_store(struct device *dev,
pci_rescan_bus(pdev->bus);
pci_unlock_rescan_remove();
}
+
return count;
}
static struct device_attribute dev_attr_dev_rescan = __ATTR(rescan, 0200, NULL,
dev_rescan_store);
-static ssize_t remove_store(struct device *dev, struct device_attribute *attr,
- const char *buf, size_t count)
+static ssize_t remove_store(struct device *dev,
+ struct device_attribute *attr, const char *buf,
+ size_t count)
{
bool remove;
+ struct pci_dev *pdev = to_pci_dev(dev);
if (kstrtobool(buf, &remove) < 0)
return -EINVAL;
if (remove && device_remove_file_self(dev, attr))
- pci_stop_and_remove_bus_device_locked(to_pci_dev(dev));
+ pci_stop_and_remove_bus_device_locked(pdev);
+
return count;
}
-static DEVICE_ATTR_IGNORE_LOCKDEP(remove, 0220, NULL,
- remove_store);
+static DEVICE_ATTR_IGNORE_LOCKDEP(remove, 0220, NULL, remove_store);
static ssize_t bus_rescan_store(struct device *dev,
- struct device_attribute *attr,
- const char *buf, size_t count)
+ struct device_attribute *attr, const char *buf,
+ size_t count)
{
bool rescan;
struct pci_bus *bus = to_pci_bus(dev);
@@ -481,6 +496,7 @@ static ssize_t bus_rescan_store(struct device *dev,
pci_rescan_bus(bus);
pci_unlock_rescan_remove();
}
+
return count;
}
static struct device_attribute dev_attr_bus_rescan = __ATTR(rescan, 0200, NULL,
@@ -491,8 +507,8 @@ static ssize_t d3cold_allowed_store(struct device *dev,
struct device_attribute *attr,
const char *buf, size_t count)
{
- struct pci_dev *pdev = to_pci_dev(dev);
bool allowed;
+ struct pci_dev *pdev = to_pci_dev(dev);
if (kstrtobool(buf, &allowed) < 0)
return -EINVAL;
@@ -512,6 +528,7 @@ static ssize_t d3cold_allowed_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
+
return sysfs_emit(buf, "%u\n", pdev->d3cold_allowed);
}
static DEVICE_ATTR_RW(d3cold_allowed);
@@ -524,8 +541,9 @@ static ssize_t devspec_show(struct device *dev,
struct pci_dev *pdev = to_pci_dev(dev);
struct device_node *np = pci_device_to_OF_node(pdev);
- if (np == NULL)
+ if (!np)
return 0;
+
return sysfs_emit(buf, "%pOF", np);
}
static DEVICE_ATTR_RO(devspec);
@@ -535,8 +553,8 @@ static ssize_t driver_override_store(struct device *dev,
struct device_attribute *attr,
const char *buf, size_t count)
{
- struct pci_dev *pdev = to_pci_dev(dev);
char *driver_override, *old, *cp;
+ struct pci_dev *pdev = to_pci_dev(dev);
/* We need to keep extra room for a newline */
if (count >= (PAGE_SIZE - 1))
@@ -574,6 +592,7 @@ static ssize_t driver_override_show(struct device *dev,
device_lock(dev);
len = sysfs_emit(buf, "%s\n", pdev->driver_override);
device_unlock(dev);
+
return len;
}
static DEVICE_ATTR_RW(driver_override);
@@ -640,8 +659,8 @@ const struct attribute_group *pcibus_groups[] = {
NULL,
};
-static ssize_t boot_vga_show(struct device *dev, struct device_attribute *attr,
- char *buf)
+static ssize_t boot_vga_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
struct pci_dev *vga_dev = vga_default_device();
@@ -659,19 +678,20 @@ static ssize_t config_read(struct file *filp, struct kobject *kobj,
struct bin_attribute *bin_attr, char *buf,
loff_t off, size_t count)
{
- struct pci_dev *dev = to_pci_dev(kobj_to_dev(kobj));
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
unsigned int size = 64;
loff_t init_off = off;
- u8 *data = (u8 *) buf;
+ u8 *data = (u8 *)buf;
/* Several chips lock up trying to read undefined config space */
if (file_ns_capable(filp, &init_user_ns, CAP_SYS_ADMIN))
- size = dev->cfg_size;
- else if (dev->hdr_type == PCI_HEADER_TYPE_CARDBUS)
+ size = pdev->cfg_size;
+ else if (pdev->hdr_type == PCI_HEADER_TYPE_CARDBUS)
size = 128;
if (off > size)
return 0;
+
if (off + count > size) {
size -= off;
count = size;
@@ -679,11 +699,11 @@ static ssize_t config_read(struct file *filp, struct kobject *kobj,
size = count;
}
- pci_config_pm_runtime_get(dev);
+ pci_config_pm_runtime_get(pdev);
if ((off & 1) && size) {
u8 val;
- pci_user_read_config_byte(dev, off, &val);
+ pci_user_read_config_byte(pdev, off, &val);
data[off - init_off] = val;
off++;
size--;
@@ -691,7 +711,7 @@ static ssize_t config_read(struct file *filp, struct kobject *kobj,
if ((off & 3) && size > 2) {
u16 val;
- pci_user_read_config_word(dev, off, &val);
+ pci_user_read_config_word(pdev, off, &val);
data[off - init_off] = val & 0xff;
data[off - init_off + 1] = (val >> 8) & 0xff;
off += 2;
@@ -700,7 +720,7 @@ static ssize_t config_read(struct file *filp, struct kobject *kobj,
while (size > 3) {
u32 val;
- pci_user_read_config_dword(dev, off, &val);
+ pci_user_read_config_dword(pdev, off, &val);
data[off - init_off] = val & 0xff;
data[off - init_off + 1] = (val >> 8) & 0xff;
data[off - init_off + 2] = (val >> 16) & 0xff;
@@ -712,7 +732,7 @@ static ssize_t config_read(struct file *filp, struct kobject *kobj,
if (size >= 2) {
u16 val;
- pci_user_read_config_word(dev, off, &val);
+ pci_user_read_config_word(pdev, off, &val);
data[off - init_off] = val & 0xff;
data[off - init_off + 1] = (val >> 8) & 0xff;
off += 2;
@@ -721,13 +741,13 @@ static ssize_t config_read(struct file *filp, struct kobject *kobj,
if (size > 0) {
u8 val;
- pci_user_read_config_byte(dev, off, &val);
+ pci_user_read_config_byte(pdev, off, &val);
data[off - init_off] = val;
off++;
--size;
}
- pci_config_pm_runtime_put(dev);
+ pci_config_pm_runtime_put(pdev);
return count;
}
@@ -736,27 +756,28 @@ static ssize_t config_write(struct file *filp, struct kobject *kobj,
struct bin_attribute *bin_attr, char *buf,
loff_t off, size_t count)
{
- struct pci_dev *dev = to_pci_dev(kobj_to_dev(kobj));
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
unsigned int size = count;
loff_t init_off = off;
- u8 *data = (u8 *) buf;
- int ret;
+ u8 *data = (u8 *)buf;
+ size_t ret;
ret = security_locked_down(LOCKDOWN_PCI_ACCESS);
if (ret)
return ret;
- if (off > dev->cfg_size)
+ if (off > pdev->cfg_size)
return 0;
- if (off + count > dev->cfg_size) {
- size = dev->cfg_size - off;
+
+ if (off + count > pdev->cfg_size) {
+ size = pdev->cfg_size - off;
count = size;
}
- pci_config_pm_runtime_get(dev);
+ pci_config_pm_runtime_get(pdev);
if ((off & 1) && size) {
- pci_user_write_config_byte(dev, off, data[off - init_off]);
+ pci_user_write_config_byte(pdev, off, data[off - init_off]);
off++;
size--;
}
@@ -764,7 +785,7 @@ static ssize_t config_write(struct file *filp, struct kobject *kobj,
if ((off & 3) && size > 2) {
u16 val = data[off - init_off];
val |= (u16) data[off - init_off + 1] << 8;
- pci_user_write_config_word(dev, off, val);
+ pci_user_write_config_word(pdev, off, val);
off += 2;
size -= 2;
}
@@ -774,7 +795,7 @@ static ssize_t config_write(struct file *filp, struct kobject *kobj,
val |= (u32) data[off - init_off + 1] << 8;
val |= (u32) data[off - init_off + 2] << 16;
val |= (u32) data[off - init_off + 3] << 24;
- pci_user_write_config_dword(dev, off, val);
+ pci_user_write_config_dword(pdev, off, val);
off += 4;
size -= 4;
}
@@ -782,18 +803,18 @@ static ssize_t config_write(struct file *filp, struct kobject *kobj,
if (size >= 2) {
u16 val = data[off - init_off];
val |= (u16) data[off - init_off + 1] << 8;
- pci_user_write_config_word(dev, off, val);
+ pci_user_write_config_word(pdev, off, val);
off += 2;
size -= 2;
}
if (size) {
- pci_user_write_config_byte(dev, off, data[off - init_off]);
+ pci_user_write_config_byte(pdev, off, data[off - init_off]);
off++;
--size;
}
- pci_config_pm_runtime_put(dev);
+ pci_config_pm_runtime_put(pdev);
return count;
}
@@ -876,7 +897,7 @@ static ssize_t pci_write_legacy_io(struct file *filp, struct kobject *kobj,
* pci_mmap_legacy_mem - map legacy PCI memory into user memory space
* @filp: open sysfs file
* @kobj: kobject corresponding to device to be mapped
- * @attr: struct bin_attribute for this file
+ * @bin_attr: struct bin_attribute for this file
* @vma: struct vm_area_struct passed to mmap
*
* Uses an arch specific callback, pci_mmap_legacy_mem_page_range, to mmap
@@ -884,7 +905,7 @@ static ssize_t pci_write_legacy_io(struct file *filp, struct kobject *kobj,
* memory space.
*/
static int pci_mmap_legacy_mem(struct file *filp, struct kobject *kobj,
- struct bin_attribute *attr,
+ struct bin_attribute *bin_attr,
struct vm_area_struct *vma)
{
struct pci_bus *bus = to_pci_bus(kobj_to_dev(kobj));
@@ -896,7 +917,7 @@ static int pci_mmap_legacy_mem(struct file *filp, struct kobject *kobj,
* pci_mmap_legacy_io - map legacy PCI IO into user memory space
* @filp: open sysfs file
* @kobj: kobject corresponding to device to be mapped
- * @attr: struct bin_attribute for this file
+ * @bin_attr: struct bin_attribute for this file
* @vma: struct vm_area_struct passed to mmap
*
* Uses an arch specific callback, pci_mmap_legacy_io_page_range, to mmap
@@ -904,7 +925,7 @@ static int pci_mmap_legacy_mem(struct file *filp, struct kobject *kobj,
* memory space. Returns -ENOSYS if the operation isn't supported
*/
static int pci_mmap_legacy_io(struct file *filp, struct kobject *kobj,
- struct bin_attribute *attr,
+ struct bin_attribute *bin_attr,
struct vm_area_struct *vma)
{
struct pci_bus *bus = to_pci_bus(kobj_to_dev(kobj));
@@ -914,19 +935,19 @@ static int pci_mmap_legacy_io(struct file *filp, struct kobject *kobj,
/**
* pci_adjust_legacy_attr - adjustment of legacy file attributes
- * @b: bus to create files under
+ * @bus: bus to create files under
* @mmap_type: I/O port or memory
*
* Stub implementation. Can be overridden by arch if necessary.
*/
-void __weak pci_adjust_legacy_attr(struct pci_bus *b,
+void __weak pci_adjust_legacy_attr(struct pci_bus *bus,
enum pci_mmap_state mmap_type)
{
}
/**
* pci_create_legacy_files - create legacy I/O port and memory files
- * @b: bus to create files under
+ * @bus: bus to create files under
*
* Some platforms allow access to legacy I/O port and ISA memory space on
* a per-bus basis. This routine creates the files and ties them into
@@ -935,67 +956,71 @@ void __weak pci_adjust_legacy_attr(struct pci_bus *b,
* On error unwind, but don't propagate the error to the caller
* as it is ok to set up the PCI bus without these files.
*/
-void pci_create_legacy_files(struct pci_bus *b)
+void pci_create_legacy_files(struct pci_bus *bus)
{
- int error;
+ int ret;
if (!sysfs_initialized)
return;
- b->legacy_io = kcalloc(2, sizeof(struct bin_attribute),
- GFP_ATOMIC);
- if (!b->legacy_io)
+ bus->legacy_io = kcalloc(2, sizeof(struct bin_attribute),
+ GFP_ATOMIC);
+ if (!bus->legacy_io)
goto kzalloc_err;
- sysfs_bin_attr_init(b->legacy_io);
- b->legacy_io->attr.name = "legacy_io";
- b->legacy_io->size = 0xffff;
- b->legacy_io->attr.mode = 0600;
- b->legacy_io->read = pci_read_legacy_io;
- b->legacy_io->write = pci_write_legacy_io;
- b->legacy_io->mmap = pci_mmap_legacy_io;
- b->legacy_io->mapping = iomem_get_mapping();
- pci_adjust_legacy_attr(b, pci_mmap_io);
- error = device_create_bin_file(&b->dev, b->legacy_io);
- if (error)
+ sysfs_bin_attr_init(bus->legacy_io);
+ bus->legacy_io->attr.name = "legacy_io";
+ bus->legacy_io->size = 0xffff;
+ bus->legacy_io->attr.mode = 0600;
+ bus->legacy_io->read = pci_read_legacy_io;
+ bus->legacy_io->write = pci_write_legacy_io;
+ bus->legacy_io->mmap = pci_mmap_legacy_io;
+ bus->legacy_io->mapping = iomem_get_mapping();
+
+ pci_adjust_legacy_attr(bus, pci_mmap_io);
+
+ ret = device_create_bin_file(&bus->dev, bus->legacy_io);
+ if (ret)
goto legacy_io_err;
/* Allocated above after the legacy_io struct */
- b->legacy_mem = b->legacy_io + 1;
- sysfs_bin_attr_init(b->legacy_mem);
- b->legacy_mem->attr.name = "legacy_mem";
- b->legacy_mem->size = 1024*1024;
- b->legacy_mem->attr.mode = 0600;
- b->legacy_mem->mmap = pci_mmap_legacy_mem;
- b->legacy_io->mapping = iomem_get_mapping();
- pci_adjust_legacy_attr(b, pci_mmap_mem);
- error = device_create_bin_file(&b->dev, b->legacy_mem);
- if (error)
+ bus->legacy_mem = bus->legacy_io + 1;
+
+ sysfs_bin_attr_init(bus->legacy_mem);
+ bus->legacy_mem->attr.name = "legacy_mem";
+ bus->legacy_mem->size = 1024*1024;
+ bus->legacy_mem->attr.mode = 0600;
+ bus->legacy_mem->mmap = pci_mmap_legacy_mem;
+ bus->legacy_io->mapping = iomem_get_mapping();
+
+ pci_adjust_legacy_attr(bus, pci_mmap_mem);
+
+ ret = device_create_bin_file(&bus->dev, bus->legacy_mem);
+ if (ret)
goto legacy_mem_err;
return;
legacy_mem_err:
- device_remove_bin_file(&b->dev, b->legacy_io);
+ device_remove_bin_file(&bus->dev, bus->legacy_io);
legacy_io_err:
- kfree(b->legacy_io);
- b->legacy_io = NULL;
+ kfree(bus->legacy_io);
+ bus->legacy_io = NULL;
kzalloc_err:
- dev_warn(&b->dev, "could not create legacy I/O port and ISA memory resources in sysfs\n");
+ dev_warn(&bus->dev, "could not create legacy I/O port and ISA memory resources in sysfs\n");
}
-void pci_remove_legacy_files(struct pci_bus *b)
+void pci_remove_legacy_files(struct pci_bus *bus)
{
- if (b->legacy_io) {
- device_remove_bin_file(&b->dev, b->legacy_io);
- device_remove_bin_file(&b->dev, b->legacy_mem);
- kfree(b->legacy_io); /* both are allocated here */
+ if (bus->legacy_io) {
+ device_remove_bin_file(&bus->dev, bus->legacy_io);
+ device_remove_bin_file(&bus->dev, bus->legacy_mem);
+ kfree(bus->legacy_io); /* both are allocated here */
}
}
#endif /* HAVE_PCI_LEGACY */
#if defined(HAVE_PCI_MMAP) || defined(ARCH_GENERIC_PCI_MMAP_RESOURCE)
-
int pci_mmap_fits(struct pci_dev *pdev, int resno, struct vm_area_struct *vma,
enum pci_mmap_api mmap_api)
{
@@ -1004,36 +1029,41 @@ int pci_mmap_fits(struct pci_dev *pdev, int resno, struct vm_area_struct *vma,
if (pci_resource_len(pdev, resno) == 0)
return 0;
+
nr = vma_pages(vma);
start = vma->vm_pgoff;
size = ((pci_resource_len(pdev, resno) - 1) >> PAGE_SHIFT) + 1;
+
if (mmap_api == PCI_MMAP_PROCFS) {
pci_resource_to_user(pdev, resno, &pdev->resource[resno],
&pci_start, &pci_end);
pci_start >>= PAGE_SHIFT;
}
+
if (start >= pci_start && start < pci_start + size &&
start + nr <= pci_start + size)
return 1;
+
return 0;
}
/**
* pci_mmap_resource - map a PCI resource into user memory space
* @kobj: kobject for mapping
- * @attr: struct bin_attribute for the file being mapped
+ * @bin_attr: struct bin_attribute for the file being mapped
* @vma: struct vm_area_struct passed into the mmap
* @write_combine: 1 for write_combine mapping
*
* Use the regular PCI mapping routines to map a PCI resource into userspace.
*/
-static int pci_mmap_resource(struct kobject *kobj, struct bin_attribute *attr,
+static int pci_mmap_resource(struct kobject *kobj,
+ struct bin_attribute *bin_attr,
struct vm_area_struct *vma, int write_combine)
{
struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- int bar = (unsigned long)attr->private;
- enum pci_mmap_state mmap_type;
+ int bar = (unsigned long)bin_attr->private;
struct resource *res = &pdev->resource[bar];
+ enum pci_mmap_state mmap_type;
int ret;
ret = security_locked_down(LOCKDOWN_PCI_ACCESS);
@@ -1046,31 +1076,33 @@ static int pci_mmap_resource(struct kobject *kobj, struct bin_attribute *attr,
if (!pci_mmap_fits(pdev, bar, vma, PCI_MMAP_SYSFS))
return -EINVAL;
- mmap_type = res->flags & IORESOURCE_MEM ? pci_mmap_mem : pci_mmap_io;
+ mmap_type = pci_mmap_io;
+ if (res->flags & IORESOURCE_MEM)
+ mmap_type = pci_mmap_mem;
return pci_mmap_resource_range(pdev, bar, vma, mmap_type, write_combine);
}
static int pci_mmap_resource_uc(struct file *filp, struct kobject *kobj,
- struct bin_attribute *attr,
+ struct bin_attribute *bin_attr,
struct vm_area_struct *vma)
{
- return pci_mmap_resource(kobj, attr, vma, 0);
+ return pci_mmap_resource(kobj, bin_attr, vma, 0);
}
static int pci_mmap_resource_wc(struct file *filp, struct kobject *kobj,
- struct bin_attribute *attr,
+ struct bin_attribute *bin_attr,
struct vm_area_struct *vma)
{
- return pci_mmap_resource(kobj, attr, vma, 1);
+ return pci_mmap_resource(kobj, bin_attr, vma, 1);
}
static ssize_t pci_resource_io(struct file *filp, struct kobject *kobj,
- struct bin_attribute *attr, char *buf,
+ struct bin_attribute *bin_attr, char *buf,
loff_t off, size_t count, bool write)
{
struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- int bar = (unsigned long)attr->private;
+ int bar = (unsigned long)bin_attr->private;
unsigned long port = off;
port += pci_resource_start(pdev, bar);
@@ -1101,27 +1133,28 @@ static ssize_t pci_resource_io(struct file *filp, struct kobject *kobj,
*(u32 *)buf = inl(port);
return 4;
}
+
return -EINVAL;
}
static ssize_t pci_read_resource_io(struct file *filp, struct kobject *kobj,
- struct bin_attribute *attr, char *buf,
+ struct bin_attribute *bin_attr, char *buf,
loff_t off, size_t count)
{
- return pci_resource_io(filp, kobj, attr, buf, off, count, false);
+ return pci_resource_io(filp, kobj, bin_attr, buf, off, count, false);
}
static ssize_t pci_write_resource_io(struct file *filp, struct kobject *kobj,
- struct bin_attribute *attr, char *buf,
+ struct bin_attribute *bin_attr, char *buf,
loff_t off, size_t count)
{
- int ret;
+ size_t ret;
ret = security_locked_down(LOCKDOWN_PCI_ACCESS);
if (ret)
return ret;
- return pci_resource_io(filp, kobj, attr, buf, off, count, true);
+ return pci_resource_io(filp, kobj, bin_attr, buf, off, count, true);
}
/**
@@ -1134,10 +1167,9 @@ static ssize_t pci_write_resource_io(struct file *filp, struct kobject *kobj,
static void pci_remove_resource_files(struct pci_dev *pdev)
{
int i;
+ struct bin_attribute *res_attr;
for (i = 0; i < PCI_STD_NUM_BARS; i++) {
- struct bin_attribute *res_attr;
-
res_attr = pdev->res_attr[i];
if (res_attr) {
sysfs_remove_bin_file(&pdev->dev.kobj, res_attr);
@@ -1152,13 +1184,13 @@ static void pci_remove_resource_files(struct pci_dev *pdev)
}
}
-static int pci_create_attr(struct pci_dev *pdev, int num, int write_combine)
+static int pci_create_attr(struct pci_dev *pdev, int resno, int write_combine)
{
/* allocate attribute structure, piggyback attribute name */
int name_len = write_combine ? 13 : 10;
struct bin_attribute *res_attr;
char *res_attr_name;
- int retval;
+ int ret;
res_attr = kzalloc(sizeof(*res_attr) + name_len, GFP_ATOMIC);
if (!res_attr)
@@ -1168,13 +1200,13 @@ static int pci_create_attr(struct pci_dev *pdev, int num, int write_combine)
sysfs_bin_attr_init(res_attr);
if (write_combine) {
- pdev->res_attr_wc[num] = res_attr;
- sprintf(res_attr_name, "resource%d_wc", num);
+ pdev->res_attr_wc[resno] = res_attr;
+ sprintf(res_attr_name, "resource%d_wc", resno);
res_attr->mmap = pci_mmap_resource_wc;
} else {
- pdev->res_attr[num] = res_attr;
- sprintf(res_attr_name, "resource%d", num);
- if (pci_resource_flags(pdev, num) & IORESOURCE_IO) {
+ pdev->res_attr[resno] = res_attr;
+ sprintf(res_attr_name, "resource%d", resno);
+ if (pci_resource_flags(pdev, resno) & IORESOURCE_IO) {
res_attr->read = pci_read_resource_io;
res_attr->write = pci_write_resource_io;
if (arch_can_pci_mmap_io())
@@ -1183,17 +1215,20 @@ static int pci_create_attr(struct pci_dev *pdev, int num, int write_combine)
res_attr->mmap = pci_mmap_resource_uc;
}
}
+
if (res_attr->mmap)
res_attr->mapping = iomem_get_mapping();
+
res_attr->attr.name = res_attr_name;
res_attr->attr.mode = 0600;
- res_attr->size = pci_resource_len(pdev, num);
- res_attr->private = (void *)(unsigned long)num;
- retval = sysfs_create_bin_file(&pdev->dev.kobj, res_attr);
- if (retval)
+ res_attr->size = pci_resource_len(pdev, resno);
+ res_attr->private = (void *)(unsigned long)resno;
+
+ ret = sysfs_create_bin_file(&pdev->dev.kobj, res_attr);
+ if (ret)
kfree(res_attr);
- return retval;
+ return ret;
}
/**
@@ -1204,31 +1239,31 @@ static int pci_create_attr(struct pci_dev *pdev, int num, int write_combine)
*/
static int pci_create_resource_files(struct pci_dev *pdev)
{
- int i;
- int retval;
+ int i, ret;
/* Expose the PCI resources from this device as files */
for (i = 0; i < PCI_STD_NUM_BARS; i++) {
-
/* skip empty resources */
if (!pci_resource_len(pdev, i))
continue;
- retval = pci_create_attr(pdev, i, 0);
+ ret = pci_create_attr(pdev, i, 0);
/* for prefetchable resources, create a WC mappable file */
- if (!retval && arch_can_pci_mmap_wc() &&
+ if (!ret && arch_can_pci_mmap_wc() &&
pdev->resource[i].flags & IORESOURCE_PREFETCH)
- retval = pci_create_attr(pdev, i, 1);
- if (retval) {
+ ret = pci_create_attr(pdev, i, 1);
+
+ if (ret) {
pci_remove_resource_files(pdev);
- return retval;
+ return ret;
}
}
+
return 0;
}
#else /* !(defined(HAVE_PCI_MMAP) || defined(ARCH_GENERIC_PCI_MMAP_RESOURCE)) */
-int __weak pci_create_resource_files(struct pci_dev *dev) { return 0; }
-void __weak pci_remove_resource_files(struct pci_dev *dev) { return; }
+int __weak pci_create_resource_files(struct pci_dev *pdev) { return 0; }
+void __weak pci_remove_resource_files(struct pci_dev *pdev) { return; }
#endif
/**
@@ -1284,9 +1319,9 @@ static ssize_t rom_read(struct file *filp, struct kobject *kobj,
if (!rom || !size)
return -EIO;
- if (off >= size)
+ if (off >= size) {
count = 0;
- else {
+ } else {
if (off + count > size)
count = size - off;
@@ -1324,12 +1359,13 @@ static const struct attribute_group pci_dev_rom_attr_group = {
.is_bin_visible = pci_dev_rom_attr_is_visible,
};
-static ssize_t reset_store(struct device *dev, struct device_attribute *attr,
- const char *buf, size_t count)
+static ssize_t reset_store(struct device *dev,
+ struct device_attribute *attr, const char *buf,
+ size_t count)
{
bool reset;
struct pci_dev *pdev = to_pci_dev(dev);
- ssize_t result;
+ ssize_t ret;
if (kstrtobool(buf, &reset) < 0)
return -EINVAL;
@@ -1338,10 +1374,10 @@ static ssize_t reset_store(struct device *dev, struct device_attribute *attr,
return -EINVAL;
pm_runtime_get_sync(dev);
- result = pci_reset_function(pdev);
+ ret = pci_reset_function(pdev);
pm_runtime_put(dev);
- if (result < 0)
- return result;
+ if (ret < 0)
+ return ret;
return count;
}
@@ -1393,20 +1429,20 @@ void pci_remove_sysfs_dev_files(struct pci_dev *pdev)
static int __init pci_sysfs_init(void)
{
struct pci_dev *pdev = NULL;
- struct pci_bus *pbus = NULL;
- int retval;
+ struct pci_bus *bus = NULL;
+ int ret;
sysfs_initialized = 1;
for_each_pci_dev(pdev) {
- retval = pci_create_sysfs_dev_files(pdev);
- if (retval) {
+ ret = pci_create_sysfs_dev_files(pdev);
+ if (ret) {
pci_dev_put(pdev);
- return retval;
+ return ret;
}
}
- while ((pbus = pci_find_next_bus(pbus)))
- pci_create_legacy_files(pbus);
+ while ((bus = pci_find_next_bus(bus)))
+ pci_create_legacy_files(bus);
return 0;
}
@@ -1417,11 +1453,10 @@ static struct attribute *pci_dev_dev_attrs[] = {
NULL,
};
-static umode_t pci_dev_attrs_are_visible(struct kobject *kobj,
- struct attribute *a, int n)
+static umode_t pci_dev_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
{
- struct device *dev = kobj_to_dev(kobj);
- struct pci_dev *pdev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
if (a == &dev_attr_boot_vga.attr)
if ((pdev->class >> 8) != PCI_CLASS_DISPLAY_VGA)
@@ -1436,11 +1471,10 @@ static struct attribute *pci_dev_hp_attrs[] = {
NULL,
};
-static umode_t pci_dev_hp_attrs_are_visible(struct kobject *kobj,
- struct attribute *a, int n)
+static umode_t pci_dev_hp_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
{
- struct device *dev = kobj_to_dev(kobj);
- struct pci_dev *pdev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
if (pdev->is_virtfn)
return 0;
@@ -1448,28 +1482,26 @@ static umode_t pci_dev_hp_attrs_are_visible(struct kobject *kobj,
return a->mode;
}
-static umode_t pci_bridge_attrs_are_visible(struct kobject *kobj,
- struct attribute *a, int n)
+static umode_t pci_bridge_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
{
- struct device *dev = kobj_to_dev(kobj);
- struct pci_dev *pdev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- if (pci_is_bridge(pdev))
- return a->mode;
+ if (!pci_is_bridge(pdev))
+ return 0;
- return 0;
+ return a->mode;
}
-static umode_t pcie_dev_attrs_are_visible(struct kobject *kobj,
- struct attribute *a, int n)
+static umode_t pcie_dev_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
{
- struct device *dev = kobj_to_dev(kobj);
- struct pci_dev *pdev = to_pci_dev(dev);
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- if (pci_is_pcie(pdev))
- return a->mode;
+ if (!pci_is_pcie(pdev))
+ return 0;
- return 0;
+ return a->mode;
}
static const struct attribute_group pci_dev_group = {
@@ -1493,22 +1525,22 @@ const struct attribute_group *pci_dev_groups[] = {
static const struct attribute_group pci_dev_hp_attr_group = {
.attrs = pci_dev_hp_attrs,
- .is_visible = pci_dev_hp_attrs_are_visible,
+ .is_visible = pci_dev_hp_attr_is_visible,
};
static const struct attribute_group pci_dev_attr_group = {
.attrs = pci_dev_dev_attrs,
- .is_visible = pci_dev_attrs_are_visible,
+ .is_visible = pci_dev_attr_is_visible,
};
static const struct attribute_group pci_bridge_attr_group = {
.attrs = pci_bridge_attrs,
- .is_visible = pci_bridge_attrs_are_visible,
+ .is_visible = pci_bridge_attr_is_visible,
};
static const struct attribute_group pcie_dev_attr_group = {
.attrs = pcie_dev_attrs,
- .is_visible = pcie_dev_attrs_are_visible,
+ .is_visible = pcie_dev_attr_is_visible,
};
static const struct attribute_group *pci_dev_attr_groups[] = {
--
2.31.0
From d4aee43ee6c97648de009d3a8cc4c9d986cb92b6 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Tue, 13 Apr 2021 17:08:11 +0000
Subject: [PATCH] PCI: Rearrange attributes from the pci_dev_group
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
When new sysfs objects were added to the PCI device over time, the code
that implemented new attributes has been added in many different places
in the pci-sysfs.c file. This makes it hard to read and also hard to
find relevant code.
Thus, collect all the attributes that are part of the "pci_dev_group"
attribute group together and move to the top of the file sorting
everything attribute in the order of use.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index 96302b63f6c5..5f83ff087f2c 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -30,50 +30,6 @@
static int sysfs_initialized; /* = 0 */
-/* show configuration fields */
-#define pci_config_attr(field, format_string) \
-static ssize_t \
-field##_show(struct device *dev, struct device_attribute *attr, char *buf) \
-{ \
- struct pci_dev *pdev = to_pci_dev(dev); \
- \
- return sysfs_emit(buf, format_string, pdev->field); \
-} \
-static DEVICE_ATTR_RO(field)
-
-pci_config_attr(vendor, "0x%04x\n");
-pci_config_attr(device, "0x%04x\n");
-pci_config_attr(subsystem_vendor, "0x%04x\n");
-pci_config_attr(subsystem_device, "0x%04x\n");
-pci_config_attr(revision, "0x%02x\n");
-pci_config_attr(class, "0x%06x\n");
-pci_config_attr(irq, "%u\n");
-
-static ssize_t broken_parity_status_show(struct device *dev,
- struct device_attribute *attr,
- char *buf)
-{
- struct pci_dev *pdev = to_pci_dev(dev);
-
- return sysfs_emit(buf, "%u\n", pdev->broken_parity_status);
-}
-
-static ssize_t broken_parity_status_store(struct device *dev,
- struct device_attribute *attr,
- const char *buf, size_t count)
-{
- bool broken;
- struct pci_dev *pdev = to_pci_dev(dev);
-
- if (kstrtobool(buf, &broken) < 0)
- return -EINVAL;
-
- pdev->broken_parity_status = !!broken;
-
- return count;
-}
-static DEVICE_ATTR_RW(broken_parity_status);
-
static ssize_t pci_dev_show_local_cpu(struct device *dev, bool list,
struct device_attribute *attr, char *buf)
{
@@ -93,43 +49,6 @@ static ssize_t pci_dev_show_local_cpu(struct device *dev, bool list,
return cpumap_print_to_pagebuf(list, buf, mask);
}
-static ssize_t local_cpus_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- return pci_dev_show_local_cpu(dev, false, attr, buf);
-}
-static DEVICE_ATTR_RO(local_cpus);
-
-static ssize_t local_cpulist_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- return pci_dev_show_local_cpu(dev, true, attr, buf);
-}
-static DEVICE_ATTR_RO(local_cpulist);
-
-/*
- * PCI Bus Class Devices
- */
-static ssize_t cpuaffinity_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- struct pci_bus *bus = to_pci_bus(dev);
- const struct cpumask *cpumask = cpumask_of_pcibus(bus);
-
- return cpumap_print_to_pagebuf(false, buf, cpumask);
-}
-static DEVICE_ATTR_RO(cpuaffinity);
-
-static ssize_t cpulistaffinity_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- struct pci_bus *bus = to_pci_bus(dev);
- const struct cpumask *cpumask = cpumask_of_pcibus(bus);
-
- return cpumap_print_to_pagebuf(true, buf, cpumask);
-}
-static DEVICE_ATTR_RO(cpulistaffinity);
-
static ssize_t power_state_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
@@ -139,7 +58,6 @@ static ssize_t power_state_show(struct device *dev,
}
static DEVICE_ATTR_RO(power_state);
-/* show resources */
static ssize_t resource_show(struct device *dev,
struct device_attribute *attr, char *buf)
{
@@ -166,89 +84,82 @@ static ssize_t resource_show(struct device *dev,
}
static DEVICE_ATTR_RO(resource);
-static ssize_t max_link_speed_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t vendor_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sysfs_emit(buf, "%s\n",
- pci_speed_string(pcie_get_speed_cap(pdev)));
+ return sysfs_emit(buf, "0x%04x\n", pdev->vendor);
}
-static DEVICE_ATTR_RO(max_link_speed);
+static DEVICE_ATTR_RO(vendor);
-static ssize_t max_link_width_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t device_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sysfs_emit(buf, "%u\n", pcie_get_width_cap(pdev));
+ return sysfs_emit(buf, "0x%04x\n", pdev->device);
}
-static DEVICE_ATTR_RO(max_link_width);
+static DEVICE_ATTR_RO(device);
-static ssize_t current_link_speed_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t subsystem_vendor_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- enum pci_bus_speed speed;
-
- pcie_bandwidth_available(pdev, NULL, &speed, NULL);
- return sysfs_emit(buf, "%s\n", pci_speed_string(speed));
+ return sysfs_emit(buf, "0x%04x\n", pdev->subsystem_vendor);
}
-static DEVICE_ATTR_RO(current_link_speed);
+static DEVICE_ATTR_RO(subsystem_vendor);
-static ssize_t current_link_width_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t subsystem_device_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- enum pcie_link_width width;
- pcie_bandwidth_available(pdev, NULL, NULL, &width);
-
- return sysfs_emit(buf, "%u\n", width);
+ return sysfs_emit(buf, "0x%04x\n", pdev->subsystem_device);
}
-static DEVICE_ATTR_RO(current_link_width);
+static DEVICE_ATTR_RO(subsystem_device);
-static ssize_t secondary_bus_number_show(struct device *dev,
- struct device_attribute *attr,
- char *buf)
+static ssize_t revision_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- u8 sec_bus;
- int err;
-
- err = pci_read_config_byte(pdev, PCI_SECONDARY_BUS, &sec_bus);
- if (err)
- return -EINVAL;
- return sysfs_emit(buf, "%u\n", sec_bus);
+ return sysfs_emit(buf, "0x%02x\n", pdev->revision);
}
-static DEVICE_ATTR_RO(secondary_bus_number);
+static DEVICE_ATTR_RO(revision);
-static ssize_t subordinate_bus_number_show(struct device *dev,
- struct device_attribute *attr,
- char *buf)
+static ssize_t class_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- u8 sub_bus;
- int err;
- err = pci_read_config_byte(pdev, PCI_SUBORDINATE_BUS, &sub_bus);
- if (err)
- return -EINVAL;
-
- return sysfs_emit(buf, "%u\n", sub_bus);
+ return sysfs_emit(buf, "0x%06x\n", pdev->class);
}
-static DEVICE_ATTR_RO(subordinate_bus_number);
+static DEVICE_ATTR_RO(class);
-static ssize_t ari_enabled_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t irq_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sysfs_emit(buf, "%u\n", pci_ari_enabled(pdev->bus));
+ return sysfs_emit(buf, "%u\n", pdev->irq);
}
-static DEVICE_ATTR_RO(ari_enabled);
+static DEVICE_ATTR_RO(irq);
+
+static ssize_t local_cpus_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ return pci_dev_show_local_cpu(dev, false, attr, buf);
+}
+static DEVICE_ATTR_RO(local_cpus);
+
+static ssize_t local_cpulist_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ return pci_dev_show_local_cpu(dev, true, attr, buf);
+}
+static DEVICE_ATTR_RO(local_cpulist);
static ssize_t modalias_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -263,6 +174,68 @@ static ssize_t modalias_show(struct device *dev,
}
static DEVICE_ATTR_RO(modalias);
+#ifdef CONFIG_NUMA
+static ssize_t numa_node_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ return sysfs_emit(buf, "%d\n", dev->numa_node);
+}
+
+static ssize_t numa_node_store(struct device *dev,
+ struct device_attribute *attr, const char *buf,
+ size_t count)
+{
+ int node;
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ if (!capable(CAP_SYS_ADMIN))
+ return -EPERM;
+
+ if (kstrtoint(buf, 0, &node) < 0)
+ return -EINVAL;
+
+ if ((node < 0 && node != NUMA_NO_NODE) || node >= MAX_NUMNODES)
+ return -EINVAL;
+
+ if (node != NUMA_NO_NODE && !node_online(node))
+ return -EINVAL;
+
+ add_taint(TAINT_FIRMWARE_WORKAROUND, LOCKDEP_STILL_OK);
+ pci_alert(pdev, FW_BUG "Overriding NUMA node to %d. Contact your vendor for updates.",
+ node);
+
+ dev->numa_node = node;
+
+ return count;
+}
+static DEVICE_ATTR_RW(numa_node);
+#endif
+
+static ssize_t dma_mask_bits_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ return sysfs_emit(buf, "%d\n", fls64(pdev->dma_mask));
+}
+static DEVICE_ATTR_RO(dma_mask_bits);
+
+static ssize_t consistent_dma_mask_bits_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ return sysfs_emit(buf, "%d\n", fls64(dev->coherent_dma_mask));
+}
+static DEVICE_ATTR_RO(consistent_dma_mask_bits);
+
+static ssize_t enable_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ return sysfs_emit(buf, "%u\n", atomic_read(&pdev->enable_cnt));
+}
+
static ssize_t enable_store(struct device *dev,
struct device_attribute *attr, const char *buf,
size_t count)
@@ -294,118 +267,319 @@ static ssize_t enable_store(struct device *dev,
return count;
}
+static DEVICE_ATTR_RW(enable);
-static ssize_t enable_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t broken_parity_status_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sysfs_emit(buf, "%u\n", atomic_read(&pdev->enable_cnt));
+ return sysfs_emit(buf, "%u\n", pdev->broken_parity_status);
}
-static DEVICE_ATTR_RW(enable);
-#ifdef CONFIG_NUMA
-static ssize_t numa_node_store(struct device *dev,
- struct device_attribute *attr, const char *buf,
- size_t count)
+static ssize_t broken_parity_status_store(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t count)
+{
+ bool broken;
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ if (kstrtobool(buf, &broken) < 0)
+ return -EINVAL;
+
+ pdev->broken_parity_status = !!broken;
+
+ return count;
+}
+static DEVICE_ATTR_RW(broken_parity_status);
+
+static ssize_t msi_bus_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- int node;
struct pci_dev *pdev = to_pci_dev(dev);
+ struct pci_bus *subordinate = pdev->subordinate;
+
+ return sysfs_emit(buf, "%u\n", subordinate ?
+ !(subordinate->bus_flags & PCI_BUS_FLAGS_NO_MSI)
+ : !pdev->no_msi);
+}
+
+static ssize_t msi_bus_store(struct device *dev,
+ struct device_attribute *attr, const char *buf,
+ size_t count)
+{
+ bool allowed;
+ struct pci_dev *pdev = to_pci_dev(dev);
+ struct pci_bus *subordinate = pdev->subordinate;
if (!capable(CAP_SYS_ADMIN))
return -EPERM;
- if (kstrtoint(buf, 0, &node) < 0)
+ if (kstrtobool(buf, &allowed) < 0)
return -EINVAL;
- if ((node < 0 && node != NUMA_NO_NODE) || node >= MAX_NUMNODES)
+ /*
+ * "no_msi" and "bus_flags" only affect what happens when a driver
+ * requests MSI or MSI-X. They don't affect any drivers that have
+ * already requested MSI or MSI-X.
+ */
+ if (!subordinate) {
+ pdev->no_msi = !allowed;
+ pci_info(pdev, "MSI/MSI-X %s for future drivers\n",
+ allowed ? "allowed" : "disallowed");
+ return count;
+ }
+
+ if (allowed)
+ subordinate->bus_flags &= ~PCI_BUS_FLAGS_NO_MSI;
+ else
+ subordinate->bus_flags |= PCI_BUS_FLAGS_NO_MSI;
+
+ dev_info(&subordinate->dev, "MSI/MSI-X %s for future drivers of devices on this bus\n",
+ allowed ? "allowed" : "disallowed");
+
+ return count;
+}
+static DEVICE_ATTR_RW(msi_bus);
+
+#if defined(CONFIG_PM) && defined(CONFIG_ACPI)
+static ssize_t d3cold_allowed_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ return sysfs_emit(buf, "%u\n", pdev->d3cold_allowed);
+}
+
+static ssize_t d3cold_allowed_store(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t count)
+{
+ bool allowed;
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ if (kstrtobool(buf, &allowed) < 0)
return -EINVAL;
- if (node != NUMA_NO_NODE && !node_online(node))
+ pdev->d3cold_allowed = !!allowed;
+ if (pdev->d3cold_allowed)
+ pci_d3cold_enable(pdev);
+ else
+ pci_d3cold_disable(pdev);
+
+ pm_runtime_resume(dev);
+
+ return count;
+}
+static DEVICE_ATTR_RW(d3cold_allowed);
+#endif
+
+#ifdef CONFIG_OF
+static ssize_t devspec_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+ struct device_node *np = pci_device_to_OF_node(pdev);
+
+ if (!np)
+ return 0;
+
+ return sysfs_emit(buf, "%pOF", np);
+}
+static DEVICE_ATTR_RO(devspec);
+#endif
+
+static ssize_t driver_override_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+ ssize_t len;
+
+ device_lock(dev);
+ len = sysfs_emit(buf, "%s\n", pdev->driver_override);
+ device_unlock(dev);
+
+ return len;
+}
+
+static ssize_t driver_override_store(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t count)
+{
+ char *driver_override, *old, *cp;
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ /* We need to keep extra room for a newline */
+ if (count >= (PAGE_SIZE - 1))
return -EINVAL;
- add_taint(TAINT_FIRMWARE_WORKAROUND, LOCKDEP_STILL_OK);
- pci_alert(pdev, FW_BUG "Overriding NUMA node to %d. Contact your vendor for updates.",
- node);
+ driver_override = kstrndup(buf, count, GFP_KERNEL);
+ if (!driver_override)
+ return -ENOMEM;
+
+ cp = strchr(driver_override, '\n');
+ if (cp)
+ *cp = '\0';
+
+ device_lock(dev);
+ old = pdev->driver_override;
+ if (strlen(driver_override)) {
+ pdev->driver_override = driver_override;
+ } else {
+ kfree(driver_override);
+ pdev->driver_override = NULL;
+ }
+ device_unlock(dev);
+
+ kfree(old);
+
+ return count;
+}
+static DEVICE_ATTR_RW(driver_override);
+
+static ssize_t ari_enabled_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ return sysfs_emit(buf, "%u\n", pci_ari_enabled(pdev->bus));
+}
+static DEVICE_ATTR_RO(ari_enabled);
+
+static struct attribute *pci_dev_attrs[] = {
+ &dev_attr_power_state.attr,
+ &dev_attr_resource.attr,
+ &dev_attr_vendor.attr,
+ &dev_attr_device.attr,
+ &dev_attr_subsystem_vendor.attr,
+ &dev_attr_subsystem_device.attr,
+ &dev_attr_revision.attr,
+ &dev_attr_class.attr,
+ &dev_attr_irq.attr,
+ &dev_attr_local_cpus.attr,
+ &dev_attr_local_cpulist.attr,
+ &dev_attr_modalias.attr,
+#ifdef CONFIG_NUMA
+ &dev_attr_numa_node.attr,
+#endif
+ &dev_attr_dma_mask_bits.attr,
+ &dev_attr_consistent_dma_mask_bits.attr,
+ &dev_attr_enable.attr,
+ &dev_attr_broken_parity_status.attr,
+ &dev_attr_msi_bus.attr,
+#if defined(CONFIG_PM) && defined(CONFIG_ACPI)
+ &dev_attr_d3cold_allowed.attr,
+#endif
+#ifdef CONFIG_OF
+ &dev_attr_devspec.attr,
+#endif
+ &dev_attr_driver_override.attr,
+ &dev_attr_ari_enabled.attr,
+ NULL,
+};
+
+static const struct attribute_group pci_dev_group = {
+ .attrs = pci_dev_attrs,
+};
- dev->numa_node = node;
+/*
+ * PCI Bus Class Devices
+ */
+static ssize_t cpuaffinity_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_bus *bus = to_pci_bus(dev);
+ const struct cpumask *cpumask = cpumask_of_pcibus(bus);
- return count;
+ return cpumap_print_to_pagebuf(false, buf, cpumask);
}
+static DEVICE_ATTR_RO(cpuaffinity);
-static ssize_t numa_node_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t cpulistaffinity_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- return sysfs_emit(buf, "%d\n", dev->numa_node);
+ struct pci_bus *bus = to_pci_bus(dev);
+ const struct cpumask *cpumask = cpumask_of_pcibus(bus);
+
+ return cpumap_print_to_pagebuf(true, buf, cpumask);
}
-static DEVICE_ATTR_RW(numa_node);
-#endif
+static DEVICE_ATTR_RO(cpulistaffinity);
-static ssize_t dma_mask_bits_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t max_link_speed_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- return sysfs_emit(buf, "%d\n", fls64(pdev->dma_mask));
+ return sysfs_emit(buf, "%s\n",
+ pci_speed_string(pcie_get_speed_cap(pdev)));
}
-static DEVICE_ATTR_RO(dma_mask_bits);
+static DEVICE_ATTR_RO(max_link_speed);
-static ssize_t consistent_dma_mask_bits_show(struct device *dev,
- struct device_attribute *attr,
- char *buf)
+static ssize_t max_link_width_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- return sysfs_emit(buf, "%d\n", fls64(dev->coherent_dma_mask));
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ return sysfs_emit(buf, "%u\n", pcie_get_width_cap(pdev));
}
-static DEVICE_ATTR_RO(consistent_dma_mask_bits);
+static DEVICE_ATTR_RO(max_link_width);
-static ssize_t msi_bus_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t current_link_speed_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
struct pci_dev *pdev = to_pci_dev(dev);
- struct pci_bus *subordinate = pdev->subordinate;
+ enum pci_bus_speed speed;
- return sysfs_emit(buf, "%u\n", subordinate ?
- !(subordinate->bus_flags & PCI_BUS_FLAGS_NO_MSI)
- : !pdev->no_msi);
+ pcie_bandwidth_available(pdev, NULL, &speed, NULL);
+
+ return sysfs_emit(buf, "%s\n", pci_speed_string(speed));
}
+static DEVICE_ATTR_RO(current_link_speed);
-static ssize_t msi_bus_store(struct device *dev,
- struct device_attribute *attr, const char *buf,
- size_t count)
+static ssize_t current_link_width_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- bool allowed;
struct pci_dev *pdev = to_pci_dev(dev);
- struct pci_bus *subordinate = pdev->subordinate;
+ enum pcie_link_width width;
- if (!capable(CAP_SYS_ADMIN))
- return -EPERM;
+ pcie_bandwidth_available(pdev, NULL, NULL, &width);
- if (kstrtobool(buf, &allowed) < 0)
+ return sysfs_emit(buf, "%u\n", width);
+}
+static DEVICE_ATTR_RO(current_link_width);
+
+static ssize_t secondary_bus_number_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+ u8 sec_bus;
+ int err;
+
+ err = pci_read_config_byte(pdev, PCI_SECONDARY_BUS, &sec_bus);
+ if (err)
return -EINVAL;
- /*
- * "no_msi" and "bus_flags" only affect what happens when a driver
- * requests MSI or MSI-X. They don't affect any drivers that have
- * already requested MSI or MSI-X.
- */
- if (!subordinate) {
- pdev->no_msi = !allowed;
- pci_info(pdev, "MSI/MSI-X %s for future drivers\n",
- allowed ? "allowed" : "disallowed");
- return count;
- }
+ return sysfs_emit(buf, "%u\n", sec_bus);
+}
+static DEVICE_ATTR_RO(secondary_bus_number);
- if (allowed)
- subordinate->bus_flags &= ~PCI_BUS_FLAGS_NO_MSI;
- else
- subordinate->bus_flags |= PCI_BUS_FLAGS_NO_MSI;
+static ssize_t subordinate_bus_number_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+ u8 sub_bus;
+ int err;
- dev_info(&subordinate->dev, "MSI/MSI-X %s for future drivers of devices on this bus\n",
- allowed ? "allowed" : "disallowed");
+ err = pci_read_config_byte(pdev, PCI_SUBORDINATE_BUS, &sub_bus);
+ if (err)
+ return -EINVAL;
- return count;
+ return sysfs_emit(buf, "%u\n", sub_bus);
}
-static DEVICE_ATTR_RW(msi_bus);
+static DEVICE_ATTR_RO(subordinate_bus_number);
static ssize_t rescan_store(struct bus_type *bus, const char *buf, size_t count)
{
@@ -502,133 +676,6 @@ static ssize_t bus_rescan_store(struct device *dev,
static struct device_attribute dev_attr_bus_rescan = __ATTR(rescan, 0200, NULL,
bus_rescan_store);
-#if defined(CONFIG_PM) && defined(CONFIG_ACPI)
-static ssize_t d3cold_allowed_store(struct device *dev,
- struct device_attribute *attr,
- const char *buf, size_t count)
-{
- bool allowed;
- struct pci_dev *pdev = to_pci_dev(dev);
-
- if (kstrtobool(buf, &allowed) < 0)
- return -EINVAL;
-
- pdev->d3cold_allowed = !!allowed;
- if (pdev->d3cold_allowed)
- pci_d3cold_enable(pdev);
- else
- pci_d3cold_disable(pdev);
-
- pm_runtime_resume(dev);
-
- return count;
-}
-
-static ssize_t d3cold_allowed_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- struct pci_dev *pdev = to_pci_dev(dev);
-
- return sysfs_emit(buf, "%u\n", pdev->d3cold_allowed);
-}
-static DEVICE_ATTR_RW(d3cold_allowed);
-#endif
-
-#ifdef CONFIG_OF
-static ssize_t devspec_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- struct pci_dev *pdev = to_pci_dev(dev);
- struct device_node *np = pci_device_to_OF_node(pdev);
-
- if (!np)
- return 0;
-
- return sysfs_emit(buf, "%pOF", np);
-}
-static DEVICE_ATTR_RO(devspec);
-#endif
-
-static ssize_t driver_override_store(struct device *dev,
- struct device_attribute *attr,
- const char *buf, size_t count)
-{
- char *driver_override, *old, *cp;
- struct pci_dev *pdev = to_pci_dev(dev);
-
- /* We need to keep extra room for a newline */
- if (count >= (PAGE_SIZE - 1))
- return -EINVAL;
-
- driver_override = kstrndup(buf, count, GFP_KERNEL);
- if (!driver_override)
- return -ENOMEM;
-
- cp = strchr(driver_override, '\n');
- if (cp)
- *cp = '\0';
-
- device_lock(dev);
- old = pdev->driver_override;
- if (strlen(driver_override)) {
- pdev->driver_override = driver_override;
- } else {
- kfree(driver_override);
- pdev->driver_override = NULL;
- }
- device_unlock(dev);
-
- kfree(old);
-
- return count;
-}
-
-static ssize_t driver_override_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- struct pci_dev *pdev = to_pci_dev(dev);
- ssize_t len;
-
- device_lock(dev);
- len = sysfs_emit(buf, "%s\n", pdev->driver_override);
- device_unlock(dev);
-
- return len;
-}
-static DEVICE_ATTR_RW(driver_override);
-
-static struct attribute *pci_dev_attrs[] = {
- &dev_attr_power_state.attr,
- &dev_attr_resource.attr,
- &dev_attr_vendor.attr,
- &dev_attr_device.attr,
- &dev_attr_subsystem_vendor.attr,
- &dev_attr_subsystem_device.attr,
- &dev_attr_revision.attr,
- &dev_attr_class.attr,
- &dev_attr_irq.attr,
- &dev_attr_local_cpus.attr,
- &dev_attr_local_cpulist.attr,
- &dev_attr_modalias.attr,
-#ifdef CONFIG_NUMA
- &dev_attr_numa_node.attr,
-#endif
- &dev_attr_dma_mask_bits.attr,
- &dev_attr_consistent_dma_mask_bits.attr,
- &dev_attr_enable.attr,
- &dev_attr_broken_parity_status.attr,
- &dev_attr_msi_bus.attr,
-#if defined(CONFIG_PM) && defined(CONFIG_ACPI)
- &dev_attr_d3cold_allowed.attr,
-#endif
-#ifdef CONFIG_OF
- &dev_attr_devspec.attr,
-#endif
- &dev_attr_driver_override.attr,
- &dev_attr_ari_enabled.attr,
- NULL,
-};
-
static struct attribute *pci_bridge_attrs[] = {
&dev_attr_subordinate_bus_number.attr,
&dev_attr_secondary_bus_number.attr,
@@ -1504,10 +1551,6 @@ static umode_t pcie_dev_attr_is_visible(struct kobject *kobj,
return a->mode;
}
-static const struct attribute_group pci_dev_group = {
- .attrs = pci_dev_attrs,
-};
-
const struct attribute_group *pci_dev_groups[] = {
&pci_dev_group,
&pci_dev_config_attr_group,
--
2.31.0
From d8ff6cce32e6c540ddee94eacd74fc3a5480cb25 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Tue, 13 Apr 2021 17:13:01 +0000
Subject: [PATCH] PCI: Rearrange attributes from the pci_dev_config_attr_group
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
When new sysfs objects were added to the PCI device over time, the code
that implemented new attributes has been added in many different places
in the pci-sysfs.c file. This makes it hard to read and also hard to
find relevant code.
Thus, move attributes that are part of the "pci_dev_config_attr_group"
attribute group to the top of the file.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index 5f83ff087f2c..513e19154a93 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -483,6 +483,174 @@ static const struct attribute_group pci_dev_group = {
.attrs = pci_dev_attrs,
};
+static ssize_t config_read(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *bin_attr, char *buf,
+ loff_t off, size_t count)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+ unsigned int size = 64;
+ loff_t init_off = off;
+ u8 *data = (u8 *)buf;
+
+ /* Several chips lock up trying to read undefined config space */
+ if (file_ns_capable(filp, &init_user_ns, CAP_SYS_ADMIN))
+ size = pdev->cfg_size;
+ else if (pdev->hdr_type == PCI_HEADER_TYPE_CARDBUS)
+ size = 128;
+
+ if (off > size)
+ return 0;
+
+ if (off + count > size) {
+ size -= off;
+ count = size;
+ } else {
+ size = count;
+ }
+
+ pci_config_pm_runtime_get(pdev);
+
+ if ((off & 1) && size) {
+ u8 val;
+ pci_user_read_config_byte(pdev, off, &val);
+ data[off - init_off] = val;
+ off++;
+ size--;
+ }
+
+ if ((off & 3) && size > 2) {
+ u16 val;
+ pci_user_read_config_word(pdev, off, &val);
+ data[off - init_off] = val & 0xff;
+ data[off - init_off + 1] = (val >> 8) & 0xff;
+ off += 2;
+ size -= 2;
+ }
+
+ while (size > 3) {
+ u32 val;
+ pci_user_read_config_dword(pdev, off, &val);
+ data[off - init_off] = val & 0xff;
+ data[off - init_off + 1] = (val >> 8) & 0xff;
+ data[off - init_off + 2] = (val >> 16) & 0xff;
+ data[off - init_off + 3] = (val >> 24) & 0xff;
+ off += 4;
+ size -= 4;
+ cond_resched();
+ }
+
+ if (size >= 2) {
+ u16 val;
+ pci_user_read_config_word(pdev, off, &val);
+ data[off - init_off] = val & 0xff;
+ data[off - init_off + 1] = (val >> 8) & 0xff;
+ off += 2;
+ size -= 2;
+ }
+
+ if (size > 0) {
+ u8 val;
+ pci_user_read_config_byte(pdev, off, &val);
+ data[off - init_off] = val;
+ off++;
+ --size;
+ }
+
+ pci_config_pm_runtime_put(pdev);
+
+ return count;
+}
+
+static ssize_t config_write(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *bin_attr, char *buf,
+ loff_t off, size_t count)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+ unsigned int size = count;
+ loff_t init_off = off;
+ u8 *data = (u8 *)buf;
+ size_t ret;
+
+ ret = security_locked_down(LOCKDOWN_PCI_ACCESS);
+ if (ret)
+ return ret;
+
+ if (off > pdev->cfg_size)
+ return 0;
+
+ if (off + count > pdev->cfg_size) {
+ size = pdev->cfg_size - off;
+ count = size;
+ }
+
+ pci_config_pm_runtime_get(pdev);
+
+ if ((off & 1) && size) {
+ pci_user_write_config_byte(pdev, off, data[off - init_off]);
+ off++;
+ size--;
+ }
+
+ if ((off & 3) && size > 2) {
+ u16 val = data[off - init_off];
+ val |= (u16) data[off - init_off + 1] << 8;
+ pci_user_write_config_word(pdev, off, val);
+ off += 2;
+ size -= 2;
+ }
+
+ while (size > 3) {
+ u32 val = data[off - init_off];
+ val |= (u32) data[off - init_off + 1] << 8;
+ val |= (u32) data[off - init_off + 2] << 16;
+ val |= (u32) data[off - init_off + 3] << 24;
+ pci_user_write_config_dword(pdev, off, val);
+ off += 4;
+ size -= 4;
+ }
+
+ if (size >= 2) {
+ u16 val = data[off - init_off];
+ val |= (u16) data[off - init_off + 1] << 8;
+ pci_user_write_config_word(pdev, off, val);
+ off += 2;
+ size -= 2;
+ }
+
+ if (size) {
+ pci_user_write_config_byte(pdev, off, data[off - init_off]);
+ off++;
+ --size;
+ }
+
+ pci_config_pm_runtime_put(pdev);
+
+ return count;
+}
+static BIN_ATTR_RW(config, 0);
+
+static struct bin_attribute *pci_dev_config_attrs[] = {
+ &bin_attr_config,
+ NULL,
+};
+
+static umode_t pci_dev_config_attr_is_visible(struct kobject *kobj,
+ struct bin_attribute *a, int n)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+
+ a->size = PCI_CFG_SPACE_SIZE;
+ if (pdev->cfg_size > PCI_CFG_SPACE_SIZE)
+ a->size = PCI_CFG_SPACE_EXP_SIZE;
+
+ return a->attr.mode;
+}
+
+static const struct attribute_group pci_dev_config_attr_group = {
+ .bin_attrs = pci_dev_config_attrs,
+ .is_bin_visible = pci_dev_config_attr_is_visible,
+};
+
/*
* PCI Bus Class Devices
*/
@@ -721,174 +889,6 @@ static ssize_t boot_vga_show(struct device *dev,
}
static DEVICE_ATTR_RO(boot_vga);
-static ssize_t config_read(struct file *filp, struct kobject *kobj,
- struct bin_attribute *bin_attr, char *buf,
- loff_t off, size_t count)
-{
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- unsigned int size = 64;
- loff_t init_off = off;
- u8 *data = (u8 *)buf;
-
- /* Several chips lock up trying to read undefined config space */
- if (file_ns_capable(filp, &init_user_ns, CAP_SYS_ADMIN))
- size = pdev->cfg_size;
- else if (pdev->hdr_type == PCI_HEADER_TYPE_CARDBUS)
- size = 128;
-
- if (off > size)
- return 0;
-
- if (off + count > size) {
- size -= off;
- count = size;
- } else {
- size = count;
- }
-
- pci_config_pm_runtime_get(pdev);
-
- if ((off & 1) && size) {
- u8 val;
- pci_user_read_config_byte(pdev, off, &val);
- data[off - init_off] = val;
- off++;
- size--;
- }
-
- if ((off & 3) && size > 2) {
- u16 val;
- pci_user_read_config_word(pdev, off, &val);
- data[off - init_off] = val & 0xff;
- data[off - init_off + 1] = (val >> 8) & 0xff;
- off += 2;
- size -= 2;
- }
-
- while (size > 3) {
- u32 val;
- pci_user_read_config_dword(pdev, off, &val);
- data[off - init_off] = val & 0xff;
- data[off - init_off + 1] = (val >> 8) & 0xff;
- data[off - init_off + 2] = (val >> 16) & 0xff;
- data[off - init_off + 3] = (val >> 24) & 0xff;
- off += 4;
- size -= 4;
- cond_resched();
- }
-
- if (size >= 2) {
- u16 val;
- pci_user_read_config_word(pdev, off, &val);
- data[off - init_off] = val & 0xff;
- data[off - init_off + 1] = (val >> 8) & 0xff;
- off += 2;
- size -= 2;
- }
-
- if (size > 0) {
- u8 val;
- pci_user_read_config_byte(pdev, off, &val);
- data[off - init_off] = val;
- off++;
- --size;
- }
-
- pci_config_pm_runtime_put(pdev);
-
- return count;
-}
-
-static ssize_t config_write(struct file *filp, struct kobject *kobj,
- struct bin_attribute *bin_attr, char *buf,
- loff_t off, size_t count)
-{
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- unsigned int size = count;
- loff_t init_off = off;
- u8 *data = (u8 *)buf;
- size_t ret;
-
- ret = security_locked_down(LOCKDOWN_PCI_ACCESS);
- if (ret)
- return ret;
-
- if (off > pdev->cfg_size)
- return 0;
-
- if (off + count > pdev->cfg_size) {
- size = pdev->cfg_size - off;
- count = size;
- }
-
- pci_config_pm_runtime_get(pdev);
-
- if ((off & 1) && size) {
- pci_user_write_config_byte(pdev, off, data[off - init_off]);
- off++;
- size--;
- }
-
- if ((off & 3) && size > 2) {
- u16 val = data[off - init_off];
- val |= (u16) data[off - init_off + 1] << 8;
- pci_user_write_config_word(pdev, off, val);
- off += 2;
- size -= 2;
- }
-
- while (size > 3) {
- u32 val = data[off - init_off];
- val |= (u32) data[off - init_off + 1] << 8;
- val |= (u32) data[off - init_off + 2] << 16;
- val |= (u32) data[off - init_off + 3] << 24;
- pci_user_write_config_dword(pdev, off, val);
- off += 4;
- size -= 4;
- }
-
- if (size >= 2) {
- u16 val = data[off - init_off];
- val |= (u16) data[off - init_off + 1] << 8;
- pci_user_write_config_word(pdev, off, val);
- off += 2;
- size -= 2;
- }
-
- if (size) {
- pci_user_write_config_byte(pdev, off, data[off - init_off]);
- off++;
- --size;
- }
-
- pci_config_pm_runtime_put(pdev);
-
- return count;
-}
-static BIN_ATTR_RW(config, 0);
-
-static struct bin_attribute *pci_dev_config_attrs[] = {
- &bin_attr_config,
- NULL,
-};
-
-static umode_t pci_dev_config_attr_is_visible(struct kobject *kobj,
- struct bin_attribute *a, int n)
-{
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
-
- a->size = PCI_CFG_SPACE_SIZE;
- if (pdev->cfg_size > PCI_CFG_SPACE_SIZE)
- a->size = PCI_CFG_SPACE_EXP_SIZE;
-
- return a->attr.mode;
-}
-
-static const struct attribute_group pci_dev_config_attr_group = {
- .bin_attrs = pci_dev_config_attrs,
- .is_bin_visible = pci_dev_config_attr_is_visible,
-};
-
#ifdef HAVE_PCI_LEGACY
/**
* pci_read_legacy_io - read byte(s) from legacy I/O port space
--
2.31.0
From 301baa738896412dadcab4e89aa26b203e693615 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Tue, 13 Apr 2021 17:15:07 +0000
Subject: [PATCH] PCI: Rearrange attributes from the pci_dev_rom_attr_group
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
When new sysfs objects were added to the PCI device over time, the code
that implemented new attributes has been added in many different places
in the pci-sysfs.c file. This makes it hard to read and also hard to
find relevant code.
Thus, move attributes that are part of the "pci_dev_rom_attr_group"
attribute group to the top of the file.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index 513e19154a93..794c97424456 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -651,6 +651,99 @@ static const struct attribute_group pci_dev_config_attr_group = {
.is_bin_visible = pci_dev_config_attr_is_visible,
};
+/**
+ * rom_read - read a PCI ROM
+ * @filp: sysfs file
+ * @kobj: kernel object handle
+ * @bin_attr: struct bin_attribute for this file
+ * @buf: where to put the data we read from the ROM
+ * @off: file offset
+ * @count: number of bytes to read
+ *
+ * Put @count bytes starting at @off into @buf from the ROM in the PCI
+ * device corresponding to @kobj.
+ */
+static ssize_t rom_read(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *bin_attr, char *buf,
+ loff_t off, size_t count)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+ void __iomem *rom;
+ size_t size;
+
+ if (!pdev->rom_attr_enabled)
+ return -EINVAL;
+
+ rom = pci_map_rom(pdev, &size); /* size starts out as PCI window size */
+ if (!rom || !size)
+ return -EIO;
+
+ if (off >= size) {
+ count = 0;
+ } else {
+ if (off + count > size)
+ count = size - off;
+
+ memcpy_fromio(buf, rom + off, count);
+ }
+ pci_unmap_rom(pdev, rom);
+
+ return count;
+}
+
+/**
+ * rom_write - used to enable access to the PCI ROM display
+ * @filp: sysfs file
+ * @kobj: kernel object handle
+ * @bin_attr: struct bin_attribute for this file
+ * @buf: user input
+ * @off: file offset
+ * @count: number of byte in input
+ *
+ * writing anything except 0 enables it
+ */
+static ssize_t rom_write(struct file *filp, struct kobject *kobj,
+ struct bin_attribute *bin_attr, char *buf,
+ loff_t off, size_t count)
+{
+ bool allowed;
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+
+ if (kstrtobool(buf, &allowed) < 0)
+ return -EINVAL;
+
+ pdev->rom_attr_enabled = !!allowed;
+
+ return count;
+}
+static BIN_ATTR_ADMIN_RW(rom, 0);
+
+static struct bin_attribute *pci_dev_rom_attrs[] = {
+ &bin_attr_rom,
+ NULL,
+};
+
+static umode_t pci_dev_rom_attr_is_visible(struct kobject *kobj,
+ struct bin_attribute *a, int n)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+ size_t rom_size;
+
+ /* If the device has a ROM, try to expose it in sysfs. */
+ rom_size = pci_resource_len(pdev, PCI_ROM_RESOURCE);
+ if (!rom_size)
+ return 0;
+
+ a->size = rom_size;
+
+ return a->attr.mode;
+}
+
+static const struct attribute_group pci_dev_rom_attr_group = {
+ .bin_attrs = pci_dev_rom_attrs,
+ .is_bin_visible = pci_dev_rom_attr_is_visible,
+};
+
/*
* PCI Bus Class Devices
*/
@@ -1313,99 +1406,6 @@ int __weak pci_create_resource_files(struct pci_dev *pdev) { return 0; }
void __weak pci_remove_resource_files(struct pci_dev *pdev) { return; }
#endif
-/**
- * rom_write - used to enable access to the PCI ROM display
- * @filp: sysfs file
- * @kobj: kernel object handle
- * @bin_attr: struct bin_attribute for this file
- * @buf: user input
- * @off: file offset
- * @count: number of byte in input
- *
- * writing anything except 0 enables it
- */
-static ssize_t rom_write(struct file *filp, struct kobject *kobj,
- struct bin_attribute *bin_attr, char *buf,
- loff_t off, size_t count)
-{
- bool allowed;
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
-
- if (kstrtobool(buf, &allowed) < 0)
- return -EINVAL;
-
- pdev->rom_attr_enabled = !!allowed;
-
- return count;
-}
-
-/**
- * rom_read - read a PCI ROM
- * @filp: sysfs file
- * @kobj: kernel object handle
- * @bin_attr: struct bin_attribute for this file
- * @buf: where to put the data we read from the ROM
- * @off: file offset
- * @count: number of bytes to read
- *
- * Put @count bytes starting at @off into @buf from the ROM in the PCI
- * device corresponding to @kobj.
- */
-static ssize_t rom_read(struct file *filp, struct kobject *kobj,
- struct bin_attribute *bin_attr, char *buf,
- loff_t off, size_t count)
-{
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- void __iomem *rom;
- size_t size;
-
- if (!pdev->rom_attr_enabled)
- return -EINVAL;
-
- rom = pci_map_rom(pdev, &size); /* size starts out as PCI window size */
- if (!rom || !size)
- return -EIO;
-
- if (off >= size) {
- count = 0;
- } else {
- if (off + count > size)
- count = size - off;
-
- memcpy_fromio(buf, rom + off, count);
- }
- pci_unmap_rom(pdev, rom);
-
- return count;
-}
-static BIN_ATTR_ADMIN_RW(rom, 0);
-
-static struct bin_attribute *pci_dev_rom_attrs[] = {
- &bin_attr_rom,
- NULL,
-};
-
-static umode_t pci_dev_rom_attr_is_visible(struct kobject *kobj,
- struct bin_attribute *a, int n)
-{
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- size_t rom_size;
-
- /* If the device has a ROM, try to expose it in sysfs. */
- rom_size = pci_resource_len(pdev, PCI_ROM_RESOURCE);
- if (!rom_size)
- return 0;
-
- a->size = rom_size;
-
- return a->attr.mode;
-}
-
-static const struct attribute_group pci_dev_rom_attr_group = {
- .bin_attrs = pci_dev_rom_attrs,
- .is_bin_visible = pci_dev_rom_attr_is_visible,
-};
-
static ssize_t reset_store(struct device *dev,
struct device_attribute *attr, const char *buf,
size_t count)
--
2.31.0
From 6d82630ffe5ee706d707a3ee465364b463cc7296 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Tue, 13 Apr 2021 17:16:33 +0000
Subject: [PATCH] PCI: Rearrange attributes from the pci_dev_reset_attr_group
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
When new sysfs objects were added to the PCI device over time, the code
that implemented new attributes has been added in many different places
in the pci-sysfs.c file. This makes it hard to read and also hard to
find relevant code.
Thus, move attributes that are part of the "pci_dev_reset_attr_group"
attribute group to the top of the file.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index 794c97424456..f18b1728aefa 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -744,6 +744,51 @@ static const struct attribute_group pci_dev_rom_attr_group = {
.is_bin_visible = pci_dev_rom_attr_is_visible,
};
+static ssize_t reset_store(struct device *dev,
+ struct device_attribute *attr, const char *buf,
+ size_t count)
+{
+ bool reset;
+ struct pci_dev *pdev = to_pci_dev(dev);
+ ssize_t ret;
+
+ if (kstrtobool(buf, &reset) < 0)
+ return -EINVAL;
+
+ if (!reset)
+ return -EINVAL;
+
+ pm_runtime_get_sync(dev);
+ ret = pci_reset_function(pdev);
+ pm_runtime_put(dev);
+ if (ret < 0)
+ return ret;
+
+ return count;
+}
+static DEVICE_ATTR_WO(reset);
+
+static struct attribute *pci_dev_reset_attrs[] = {
+ &dev_attr_reset.attr,
+ NULL,
+};
+
+static umode_t pci_dev_reset_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+
+ if (!pdev->reset_fn)
+ return 0;
+
+ return a->mode;
+}
+
+static const struct attribute_group pci_dev_reset_attr_group = {
+ .attrs = pci_dev_reset_attrs,
+ .is_visible = pci_dev_reset_attr_is_visible,
+};
+
/*
* PCI Bus Class Devices
*/
@@ -1406,51 +1451,6 @@ int __weak pci_create_resource_files(struct pci_dev *pdev) { return 0; }
void __weak pci_remove_resource_files(struct pci_dev *pdev) { return; }
#endif
-static ssize_t reset_store(struct device *dev,
- struct device_attribute *attr, const char *buf,
- size_t count)
-{
- bool reset;
- struct pci_dev *pdev = to_pci_dev(dev);
- ssize_t ret;
-
- if (kstrtobool(buf, &reset) < 0)
- return -EINVAL;
-
- if (!reset)
- return -EINVAL;
-
- pm_runtime_get_sync(dev);
- ret = pci_reset_function(pdev);
- pm_runtime_put(dev);
- if (ret < 0)
- return ret;
-
- return count;
-}
-static DEVICE_ATTR_WO(reset);
-
-static struct attribute *pci_dev_reset_attrs[] = {
- &dev_attr_reset.attr,
- NULL,
-};
-
-static umode_t pci_dev_reset_attr_is_visible(struct kobject *kobj,
- struct attribute *a, int n)
-{
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
-
- if (!pdev->reset_fn)
- return 0;
-
- return a->mode;
-}
-
-static const struct attribute_group pci_dev_reset_attr_group = {
- .attrs = pci_dev_reset_attrs,
- .is_visible = pci_dev_reset_attr_is_visible,
-};
-
int __must_check pci_create_sysfs_dev_files(struct pci_dev *pdev)
{
if (!sysfs_initialized)
--
2.31.0
From 64f75a0db8231feb743bd32660b8068a81675449 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Tue, 13 Apr 2021 17:19:44 +0000
Subject: [PATCH] PCI: Rearrange attributes from the pci_dev_attr_group
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
When new sysfs objects were added to the PCI device over time, the code
that implemented new attributes has been added in many different places
in the pci-sysfs.c file. This makes it hard to read and also hard to
find relevant code.
Thus, move attributes that are part of the "pci_dev_attr_group"
attribute group to the top of the file.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index f18b1728aefa..fd89a391b1c7 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -789,6 +789,43 @@ static const struct attribute_group pci_dev_reset_attr_group = {
.is_visible = pci_dev_reset_attr_is_visible,
};
+static ssize_t boot_vga_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+ struct pci_dev *vga_dev = vga_default_device();
+
+ if (vga_dev)
+ return sysfs_emit(buf, "%u\n", (pdev == vga_dev));
+
+ return sysfs_emit(buf, "%u\n",
+ !!(pdev->resource[PCI_ROM_RESOURCE].flags &
+ IORESOURCE_ROM_SHADOW));
+}
+static DEVICE_ATTR_RO(boot_vga);
+
+static struct attribute *pci_dev_dev_attrs[] = {
+ &dev_attr_boot_vga.attr,
+ NULL,
+};
+
+static umode_t pci_dev_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+
+ if (a == &dev_attr_boot_vga.attr)
+ if ((pdev->class >> 8) != PCI_CLASS_DISPLAY_VGA)
+ return 0;
+
+ return a->mode;
+}
+
+static const struct attribute_group pci_dev_attr_group = {
+ .attrs = pci_dev_dev_attrs,
+ .is_visible = pci_dev_attr_is_visible,
+};
+
/*
* PCI Bus Class Devices
*/
@@ -1012,21 +1049,6 @@ const struct attribute_group *pcibus_groups[] = {
NULL,
};
-static ssize_t boot_vga_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- struct pci_dev *pdev = to_pci_dev(dev);
- struct pci_dev *vga_dev = vga_default_device();
-
- if (vga_dev)
- return sysfs_emit(buf, "%u\n", (pdev == vga_dev));
-
- return sysfs_emit(buf, "%u\n",
- !!(pdev->resource[PCI_ROM_RESOURCE].flags &
- IORESOURCE_ROM_SHADOW));
-}
-static DEVICE_ATTR_RO(boot_vga);
-
#ifdef HAVE_PCI_LEGACY
/**
* pci_read_legacy_io - read byte(s) from legacy I/O port space
@@ -1495,23 +1517,6 @@ static int __init pci_sysfs_init(void)
}
late_initcall(pci_sysfs_init);
-static struct attribute *pci_dev_dev_attrs[] = {
- &dev_attr_boot_vga.attr,
- NULL,
-};
-
-static umode_t pci_dev_attr_is_visible(struct kobject *kobj,
- struct attribute *a, int n)
-{
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
-
- if (a == &dev_attr_boot_vga.attr)
- if ((pdev->class >> 8) != PCI_CLASS_DISPLAY_VGA)
- return 0;
-
- return a->mode;
-}
-
static struct attribute *pci_dev_hp_attrs[] = {
&dev_attr_remove.attr,
&dev_attr_dev_rescan.attr,
@@ -1571,11 +1576,6 @@ static const struct attribute_group pci_dev_hp_attr_group = {
.is_visible = pci_dev_hp_attr_is_visible,
};
-static const struct attribute_group pci_dev_attr_group = {
- .attrs = pci_dev_dev_attrs,
- .is_visible = pci_dev_attr_is_visible,
-};
-
static const struct attribute_group pci_bridge_attr_group = {
.attrs = pci_bridge_attrs,
.is_visible = pci_bridge_attr_is_visible,
--
2.31.0
From 9f75bcd46ea2f972562bb5741f7bd58f74d962c0 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Tue, 13 Apr 2021 17:22:51 +0000
Subject: [PATCH] PCI: Rearrange attributes from the pci_dev_hp_attr_group
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
When new sysfs objects were added to the PCI device over time, the code
that implemented new attributes has been added in many different places
in the pci-sysfs.c file. This makes it hard to read and also hard to
find relevant code.
Thus, collect all the attributes that are part of the "pci_dev_hp_attr_group"
attribute group together and move to the top of the file sorting
everything attribute in the order of use.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index fd89a391b1c7..bf909e9a9528 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -826,6 +826,66 @@ static const struct attribute_group pci_dev_attr_group = {
.is_visible = pci_dev_attr_is_visible,
};
+static ssize_t remove_store(struct device *dev,
+ struct device_attribute *attr, const char *buf,
+ size_t count)
+{
+ bool remove;
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ if (kstrtobool(buf, &remove) < 0)
+ return -EINVAL;
+
+ if (remove && device_remove_file_self(dev, attr))
+ pci_stop_and_remove_bus_device_locked(pdev);
+
+ return count;
+}
+static DEVICE_ATTR_IGNORE_LOCKDEP(remove, 0220, NULL, remove_store);
+
+static ssize_t dev_rescan_store(struct device *dev,
+ struct device_attribute *attr, const char *buf,
+ size_t count)
+{
+ bool rescan;
+ struct pci_dev *pdev = to_pci_dev(dev);
+
+ if (kstrtobool(buf, &rescan) < 0)
+ return -EINVAL;
+
+ if (rescan) {
+ pci_lock_rescan_remove();
+ pci_rescan_bus(pdev->bus);
+ pci_unlock_rescan_remove();
+ }
+
+ return count;
+}
+static struct device_attribute dev_attr_dev_rescan = __ATTR(rescan, 0200, NULL,
+ dev_rescan_store);
+
+static struct attribute *pci_dev_hp_attrs[] = {
+ &dev_attr_remove.attr,
+ &dev_attr_dev_rescan.attr,
+ NULL,
+};
+
+static umode_t pci_dev_hp_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+
+ if (pdev->is_virtfn)
+ return 0;
+
+ return a->mode;
+}
+
+static const struct attribute_group pci_dev_hp_attr_group = {
+ .attrs = pci_dev_hp_attrs,
+ .is_visible = pci_dev_hp_attr_is_visible,
+};
+
/*
* PCI Bus Class Devices
*/
@@ -957,44 +1017,6 @@ const struct attribute_group *pci_bus_groups[] = {
NULL,
};
-static ssize_t dev_rescan_store(struct device *dev,
- struct device_attribute *attr, const char *buf,
- size_t count)
-{
- bool rescan;
- struct pci_dev *pdev = to_pci_dev(dev);
-
- if (kstrtobool(buf, &rescan) < 0)
- return -EINVAL;
-
- if (rescan) {
- pci_lock_rescan_remove();
- pci_rescan_bus(pdev->bus);
- pci_unlock_rescan_remove();
- }
-
- return count;
-}
-static struct device_attribute dev_attr_dev_rescan = __ATTR(rescan, 0200, NULL,
- dev_rescan_store);
-
-static ssize_t remove_store(struct device *dev,
- struct device_attribute *attr, const char *buf,
- size_t count)
-{
- bool remove;
- struct pci_dev *pdev = to_pci_dev(dev);
-
- if (kstrtobool(buf, &remove) < 0)
- return -EINVAL;
-
- if (remove && device_remove_file_self(dev, attr))
- pci_stop_and_remove_bus_device_locked(pdev);
-
- return count;
-}
-static DEVICE_ATTR_IGNORE_LOCKDEP(remove, 0220, NULL, remove_store);
-
static ssize_t bus_rescan_store(struct device *dev,
struct device_attribute *attr, const char *buf,
size_t count)
@@ -1517,23 +1539,6 @@ static int __init pci_sysfs_init(void)
}
late_initcall(pci_sysfs_init);
-static struct attribute *pci_dev_hp_attrs[] = {
- &dev_attr_remove.attr,
- &dev_attr_dev_rescan.attr,
- NULL,
-};
-
-static umode_t pci_dev_hp_attr_is_visible(struct kobject *kobj,
- struct attribute *a, int n)
-{
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
-
- if (pdev->is_virtfn)
- return 0;
-
- return a->mode;
-}
-
static umode_t pci_bridge_attr_is_visible(struct kobject *kobj,
struct attribute *a, int n)
{
@@ -1571,11 +1576,6 @@ const struct attribute_group *pci_dev_groups[] = {
NULL,
};
-static const struct attribute_group pci_dev_hp_attr_group = {
- .attrs = pci_dev_hp_attrs,
- .is_visible = pci_dev_hp_attr_is_visible,
-};
-
static const struct attribute_group pci_bridge_attr_group = {
.attrs = pci_bridge_attrs,
.is_visible = pci_bridge_attr_is_visible,
--
2.31.0
From 2fb2040110e001b984eef010cd98aa656a060697 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Tue, 13 Apr 2021 17:25:03 +0000
Subject: [PATCH] PCI: Rearrange attributes from the pci_bridge_attr_group
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
When new sysfs objects were added to the PCI device over time, the code
that implemented new attributes has been added in many different places
in the pci-sysfs.c file. This makes it hard to read and also hard to
find relevant code.
Thus, collect all the attributes that are part of the "pci_bridge_attr_group"
attribute group together and move to the top of the file sorting
everything attribute in the order of use.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index bf909e9a9528..1899c24081f7 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -886,6 +886,60 @@ static const struct attribute_group pci_dev_hp_attr_group = {
.is_visible = pci_dev_hp_attr_is_visible,
};
+static ssize_t subordinate_bus_number_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+ u8 sub_bus;
+ int err;
+
+ err = pci_read_config_byte(pdev, PCI_SUBORDINATE_BUS, &sub_bus);
+ if (err)
+ return -EINVAL;
+
+ return sysfs_emit(buf, "%u\n", sub_bus);
+}
+static DEVICE_ATTR_RO(subordinate_bus_number);
+
+static ssize_t secondary_bus_number_show(struct device *dev,
+ struct device_attribute *attr,
+ char *buf)
+{
+ struct pci_dev *pdev = to_pci_dev(dev);
+ u8 sec_bus;
+ int err;
+
+ err = pci_read_config_byte(pdev, PCI_SECONDARY_BUS, &sec_bus);
+ if (err)
+ return -EINVAL;
+
+ return sysfs_emit(buf, "%u\n", sec_bus);
+}
+static DEVICE_ATTR_RO(secondary_bus_number);
+
+static struct attribute *pci_bridge_attrs[] = {
+ &dev_attr_subordinate_bus_number.attr,
+ &dev_attr_secondary_bus_number.attr,
+ NULL,
+};
+
+static umode_t pci_bridge_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
+{
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
+
+ if (!pci_is_bridge(pdev))
+ return 0;
+
+ return a->mode;
+}
+
+static const struct attribute_group pci_bridge_attr_group = {
+ .attrs = pci_bridge_attrs,
+ .is_visible = pci_bridge_attr_is_visible,
+};
+
/*
* PCI Bus Class Devices
*/
@@ -952,38 +1006,6 @@ static ssize_t current_link_width_show(struct device *dev,
}
static DEVICE_ATTR_RO(current_link_width);
-static ssize_t secondary_bus_number_show(struct device *dev,
- struct device_attribute *attr,
- char *buf)
-{
- struct pci_dev *pdev = to_pci_dev(dev);
- u8 sec_bus;
- int err;
-
- err = pci_read_config_byte(pdev, PCI_SECONDARY_BUS, &sec_bus);
- if (err)
- return -EINVAL;
-
- return sysfs_emit(buf, "%u\n", sec_bus);
-}
-static DEVICE_ATTR_RO(secondary_bus_number);
-
-static ssize_t subordinate_bus_number_show(struct device *dev,
- struct device_attribute *attr,
- char *buf)
-{
- struct pci_dev *pdev = to_pci_dev(dev);
- u8 sub_bus;
- int err;
-
- err = pci_read_config_byte(pdev, PCI_SUBORDINATE_BUS, &sub_bus);
- if (err)
- return -EINVAL;
-
- return sysfs_emit(buf, "%u\n", sub_bus);
-}
-static DEVICE_ATTR_RO(subordinate_bus_number);
-
static ssize_t rescan_store(struct bus_type *bus, const char *buf, size_t count)
{
bool rescan;
@@ -1041,12 +1063,6 @@ static ssize_t bus_rescan_store(struct device *dev,
static struct device_attribute dev_attr_bus_rescan = __ATTR(rescan, 0200, NULL,
bus_rescan_store);
-static struct attribute *pci_bridge_attrs[] = {
- &dev_attr_subordinate_bus_number.attr,
- &dev_attr_secondary_bus_number.attr,
- NULL,
-};
-
static struct attribute *pcie_dev_attrs[] = {
&dev_attr_current_link_speed.attr,
&dev_attr_current_link_width.attr,
@@ -1539,17 +1555,6 @@ static int __init pci_sysfs_init(void)
}
late_initcall(pci_sysfs_init);
-static umode_t pci_bridge_attr_is_visible(struct kobject *kobj,
- struct attribute *a, int n)
-{
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
-
- if (!pci_is_bridge(pdev))
- return 0;
-
- return a->mode;
-}
-
static umode_t pcie_dev_attr_is_visible(struct kobject *kobj,
struct attribute *a, int n)
{
@@ -1576,11 +1581,6 @@ const struct attribute_group *pci_dev_groups[] = {
NULL,
};
-static const struct attribute_group pci_bridge_attr_group = {
- .attrs = pci_bridge_attrs,
- .is_visible = pci_bridge_attr_is_visible,
-};
-
static const struct attribute_group pcie_dev_attr_group = {
.attrs = pcie_dev_attrs,
.is_visible = pcie_dev_attr_is_visible,
--
2.31.0
From 9f4f84a9222a6204fe07b73bec391c3506b19fac Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Tue, 13 Apr 2021 17:29:51 +0000
Subject: [PATCH] PCI: Rearrange attributes from the pcie_dev_attr_group
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
When new sysfs objects were added to the PCI device over time, the code
that implemented new attributes has been added in many different places
in the pci-sysfs.c file. This makes it hard to read and also hard to
find relevant code.
Thus, collect all the attributes that are part of the "pcie_dev_attr_group"
attribute group together and move to the top of the file sorting
everything attribute in the order of use.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index 1899c24081f7..44ce65bcacba 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -940,28 +940,29 @@ static const struct attribute_group pci_bridge_attr_group = {
.is_visible = pci_bridge_attr_is_visible,
};
-/*
- * PCI Bus Class Devices
- */
-static ssize_t cpuaffinity_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t current_link_speed_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- struct pci_bus *bus = to_pci_bus(dev);
- const struct cpumask *cpumask = cpumask_of_pcibus(bus);
+ struct pci_dev *pdev = to_pci_dev(dev);
+ enum pci_bus_speed speed;
- return cpumap_print_to_pagebuf(false, buf, cpumask);
+ pcie_bandwidth_available(pdev, NULL, &speed, NULL);
+
+ return sysfs_emit(buf, "%s\n", pci_speed_string(speed));
}
-static DEVICE_ATTR_RO(cpuaffinity);
+static DEVICE_ATTR_RO(current_link_speed);
-static ssize_t cpulistaffinity_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static ssize_t current_link_width_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- struct pci_bus *bus = to_pci_bus(dev);
- const struct cpumask *cpumask = cpumask_of_pcibus(bus);
+ struct pci_dev *pdev = to_pci_dev(dev);
+ enum pcie_link_width width;
- return cpumap_print_to_pagebuf(true, buf, cpumask);
+ pcie_bandwidth_available(pdev, NULL, NULL, &width);
+
+ return sysfs_emit(buf, "%u\n", width);
}
-static DEVICE_ATTR_RO(cpulistaffinity);
+static DEVICE_ATTR_RO(current_link_width);
static ssize_t max_link_speed_show(struct device *dev,
struct device_attribute *attr, char *buf)
@@ -982,29 +983,52 @@ static ssize_t max_link_width_show(struct device *dev,
}
static DEVICE_ATTR_RO(max_link_width);
-static ssize_t current_link_speed_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static struct attribute *pcie_dev_attrs[] = {
+ &dev_attr_current_link_speed.attr,
+ &dev_attr_current_link_width.attr,
+ &dev_attr_max_link_speed.attr,
+ &dev_attr_max_link_width.attr,
+ NULL,
+};
+
+static umode_t pcie_dev_attr_is_visible(struct kobject *kobj,
+ struct attribute *a, int n)
{
- struct pci_dev *pdev = to_pci_dev(dev);
- enum pci_bus_speed speed;
+ struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
- pcie_bandwidth_available(pdev, NULL, &speed, NULL);
+ if (!pci_is_pcie(pdev))
+ return 0;
- return sysfs_emit(buf, "%s\n", pci_speed_string(speed));
+ return a->mode;
}
-static DEVICE_ATTR_RO(current_link_speed);
-static ssize_t current_link_width_show(struct device *dev,
- struct device_attribute *attr, char *buf)
+static const struct attribute_group pcie_dev_attr_group = {
+ .attrs = pcie_dev_attrs,
+ .is_visible = pcie_dev_attr_is_visible,
+};
+
+/*
+ * PCI Bus Class Devices
+ */
+static ssize_t cpuaffinity_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
{
- struct pci_dev *pdev = to_pci_dev(dev);
- enum pcie_link_width width;
+ struct pci_bus *bus = to_pci_bus(dev);
+ const struct cpumask *cpumask = cpumask_of_pcibus(bus);
- pcie_bandwidth_available(pdev, NULL, NULL, &width);
+ return cpumap_print_to_pagebuf(false, buf, cpumask);
+}
+static DEVICE_ATTR_RO(cpuaffinity);
- return sysfs_emit(buf, "%u\n", width);
+static ssize_t cpulistaffinity_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_bus *bus = to_pci_bus(dev);
+ const struct cpumask *cpumask = cpumask_of_pcibus(bus);
+
+ return cpumap_print_to_pagebuf(true, buf, cpumask);
}
-static DEVICE_ATTR_RO(current_link_width);
+static DEVICE_ATTR_RO(cpulistaffinity);
static ssize_t rescan_store(struct bus_type *bus, const char *buf, size_t count)
{
@@ -1063,14 +1087,6 @@ static ssize_t bus_rescan_store(struct device *dev,
static struct device_attribute dev_attr_bus_rescan = __ATTR(rescan, 0200, NULL,
bus_rescan_store);
-static struct attribute *pcie_dev_attrs[] = {
- &dev_attr_current_link_speed.attr,
- &dev_attr_current_link_width.attr,
- &dev_attr_max_link_width.attr,
- &dev_attr_max_link_speed.attr,
- NULL,
-};
-
static struct attribute *pcibus_attrs[] = {
&dev_attr_bus_rescan.attr,
&dev_attr_cpuaffinity.attr,
@@ -1555,17 +1571,6 @@ static int __init pci_sysfs_init(void)
}
late_initcall(pci_sysfs_init);
-static umode_t pcie_dev_attr_is_visible(struct kobject *kobj,
- struct attribute *a, int n)
-{
- struct pci_dev *pdev = to_pci_dev(kobj_to_dev(kobj));
-
- if (!pci_is_pcie(pdev))
- return 0;
-
- return a->mode;
-}
-
const struct attribute_group *pci_dev_groups[] = {
&pci_dev_group,
&pci_dev_config_attr_group,
@@ -1581,11 +1586,6 @@ const struct attribute_group *pci_dev_groups[] = {
NULL,
};
-static const struct attribute_group pcie_dev_attr_group = {
- .attrs = pcie_dev_attrs,
- .is_visible = pcie_dev_attr_is_visible,
-};
-
static const struct attribute_group *pci_dev_attr_groups[] = {
&pci_dev_attr_group,
&pci_dev_hp_attr_group,
--
2.31.0
From 33b027a95797f95e721de65535a2ab1730b48ff0 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Tue, 13 Apr 2021 17:34:25 +0000
Subject: [PATCH] PCI: Rearrange attributes from the pci_bus_group
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
When new sysfs objects were added to the PCI device over time, the code
that implemented new attributes has been added in many different places
in the pci-sysfs.c file. This makes it hard to read and also hard to
find relevant code.
Thus, collect all the attributes that are part of the "pci_bus_group"
attribute group together and move to the top of the file sorting
everything attribute in the order of use.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index 44ce65bcacba..c29a781efe55 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -1010,26 +1010,6 @@ static const struct attribute_group pcie_dev_attr_group = {
/*
* PCI Bus Class Devices
*/
-static ssize_t cpuaffinity_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- struct pci_bus *bus = to_pci_bus(dev);
- const struct cpumask *cpumask = cpumask_of_pcibus(bus);
-
- return cpumap_print_to_pagebuf(false, buf, cpumask);
-}
-static DEVICE_ATTR_RO(cpuaffinity);
-
-static ssize_t cpulistaffinity_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- struct pci_bus *bus = to_pci_bus(dev);
- const struct cpumask *cpumask = cpumask_of_pcibus(bus);
-
- return cpumap_print_to_pagebuf(true, buf, cpumask);
-}
-static DEVICE_ATTR_RO(cpulistaffinity);
-
static ssize_t rescan_store(struct bus_type *bus, const char *buf, size_t count)
{
bool rescan;
@@ -1058,10 +1038,25 @@ static const struct attribute_group pci_bus_group = {
.attrs = pci_bus_attrs,
};
-const struct attribute_group *pci_bus_groups[] = {
- &pci_bus_group,
- NULL,
-};
+static ssize_t cpuaffinity_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_bus *bus = to_pci_bus(dev);
+ const struct cpumask *cpumask = cpumask_of_pcibus(bus);
+
+ return cpumap_print_to_pagebuf(false, buf, cpumask);
+}
+static DEVICE_ATTR_RO(cpuaffinity);
+
+static ssize_t cpulistaffinity_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_bus *bus = to_pci_bus(dev);
+ const struct cpumask *cpumask = cpumask_of_pcibus(bus);
+
+ return cpumap_print_to_pagebuf(true, buf, cpumask);
+}
+static DEVICE_ATTR_RO(cpulistaffinity);
static ssize_t bus_rescan_store(struct device *dev,
struct device_attribute *attr, const char *buf,
@@ -1603,6 +1598,11 @@ static const struct attribute_group *pci_dev_attr_groups[] = {
NULL,
};
+const struct attribute_group *pci_bus_groups[] = {
+ &pci_bus_group,
+ NULL,
+};
+
const struct device_type pci_dev_type = {
.groups = pci_dev_attr_groups,
};
--
2.31.0
From 712adce3b509d8d5696d2517103ea6004a78ab43 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Krzysztof=20Wilczy=C5=84ski?= <kw@linux.com>
Date: Tue, 13 Apr 2021 17:36:52 +0000
Subject: [PATCH] PCI: Rearrange attributes from the pcibus_group
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
When new sysfs objects were added to the PCI device over time, the code
that implemented new attributes has been added in many different places
in the pci-sysfs.c file. This makes it hard to read and also hard to
find relevant code.
Thus, collect all the attributes that are part of the "pcibus_group"
attribute group together and move to the top of the file sorting
everything attribute in the order of use.
No functional change intended.
Suggested-by: Bjorn Helgaas <bhelgaas@google.com>
Signed-off-by: Krzysztof Wilczyński <kw@linux.com>
diff --git a/drivers/pci/pci-sysfs.c b/drivers/pci/pci-sysfs.c
index c29a781efe55..e2d3d214178a 100644
--- a/drivers/pci/pci-sysfs.c
+++ b/drivers/pci/pci-sysfs.c
@@ -1038,26 +1038,6 @@ static const struct attribute_group pci_bus_group = {
.attrs = pci_bus_attrs,
};
-static ssize_t cpuaffinity_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- struct pci_bus *bus = to_pci_bus(dev);
- const struct cpumask *cpumask = cpumask_of_pcibus(bus);
-
- return cpumap_print_to_pagebuf(false, buf, cpumask);
-}
-static DEVICE_ATTR_RO(cpuaffinity);
-
-static ssize_t cpulistaffinity_show(struct device *dev,
- struct device_attribute *attr, char *buf)
-{
- struct pci_bus *bus = to_pci_bus(dev);
- const struct cpumask *cpumask = cpumask_of_pcibus(bus);
-
- return cpumap_print_to_pagebuf(true, buf, cpumask);
-}
-static DEVICE_ATTR_RO(cpulistaffinity);
-
static ssize_t bus_rescan_store(struct device *dev,
struct device_attribute *attr, const char *buf,
size_t count)
@@ -1082,6 +1062,26 @@ static ssize_t bus_rescan_store(struct device *dev,
static struct device_attribute dev_attr_bus_rescan = __ATTR(rescan, 0200, NULL,
bus_rescan_store);
+static ssize_t cpuaffinity_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_bus *bus = to_pci_bus(dev);
+ const struct cpumask *cpumask = cpumask_of_pcibus(bus);
+
+ return cpumap_print_to_pagebuf(false, buf, cpumask);
+}
+static DEVICE_ATTR_RO(cpuaffinity);
+
+static ssize_t cpulistaffinity_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ struct pci_bus *bus = to_pci_bus(dev);
+ const struct cpumask *cpumask = cpumask_of_pcibus(bus);
+
+ return cpumap_print_to_pagebuf(true, buf, cpumask);
+}
+static DEVICE_ATTR_RO(cpulistaffinity);
+
static struct attribute *pcibus_attrs[] = {
&dev_attr_bus_rescan.attr,
&dev_attr_cpuaffinity.attr,
@@ -1093,11 +1093,6 @@ static const struct attribute_group pcibus_group = {
.attrs = pcibus_attrs,
};
-const struct attribute_group *pcibus_groups[] = {
- &pcibus_group,
- NULL,
-};
-
#ifdef HAVE_PCI_LEGACY
/**
* pci_read_legacy_io - read byte(s) from legacy I/O port space
@@ -1603,6 +1598,11 @@ const struct attribute_group *pci_bus_groups[] = {
NULL,
};
+const struct attribute_group *pcibus_groups[] = {
+ &pcibus_group,
+ NULL,
+};
+
const struct device_type pci_dev_type = {
.groups = pci_dev_attr_groups,
};
--
2.31.0
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment