summaryrefslogtreecommitdiff
path: root/drivers/bluetooth
diff options
context:
space:
mode:
authorChandrashekar Devegowda <chandrashekar.devegowda@intel.com>2026-07-27 10:51:02 +0530
committerLuiz Augusto von Dentz <luiz.von.dentz@intel.com>2026-08-07 15:38:31 -0400
commit39bbe7b7386fb3cdbb1c02a240e40d45f1435778 (patch)
treee0676da6a6bd02dc4f1c23a9c8b6e3d971faa729 /drivers/bluetooth
parent80718e2e0fbce54d57146564455f123daebfe11a (diff)
downloadlinux-next-39bbe7b7386fb3cdbb1c02a240e40d45f1435778.tar.gz
linux-next-39bbe7b7386fb3cdbb1c02a240e40d45f1435778.zip
Bluetooth: btintel_pcie: Add vendor_reset PCI sysfs for PLDR
Add a read-write sysfs entry at /sys/bus/pci/devices/<BDF>/vendor_reset to allow userspace to trigger PLDR (Product Level Device Reset). Reading the attribute displays supported reset types. Writing integer 0 triggers PLDR. Any other input is rejected with -EINVAL and a warning log. Signed-off-by: Chandrashekar Devegowda <chandrashekar.devegowda@intel.com> Signed-off-by: Luiz Augusto von Dentz <luiz.von.dentz@intel.com>
Diffstat (limited to 'drivers/bluetooth')
-rw-r--r--drivers/bluetooth/btintel_pcie.c38
1 files changed, 38 insertions, 0 deletions
diff --git a/drivers/bluetooth/btintel_pcie.c b/drivers/bluetooth/btintel_pcie.c
index ef42b8d11d4d..005c77a4f5eb 100644
--- a/drivers/bluetooth/btintel_pcie.c
+++ b/drivers/bluetooth/btintel_pcie.c
@@ -2790,6 +2790,43 @@ static void btintel_pcie_hci_reset(struct hci_dev *hdev)
btintel_pcie_request_reset(data, BTINTEL_PCIE_IOSF_PRR_FLR);
}
+static ssize_t vendor_reset_store(struct device *dev,
+ struct device_attribute *attr,
+ const char *buf, size_t count)
+{
+ unsigned int val;
+ struct pci_dev *pdev = to_pci_dev(dev);
+ struct btintel_pcie_data *data = pci_get_drvdata(pdev);
+
+ if (!data || !data->hdev)
+ return -ENODEV;
+
+ if (kstrtouint(buf, 10, &val) || val != 0) {
+ bt_dev_warn(data->hdev, "PLDR rejected: invalid input");
+ return -EINVAL;
+ }
+
+ bt_dev_info(data->hdev, "PLDR triggered via sysfs");
+ btintel_pcie_request_reset(data, BTINTEL_PCIE_IOSF_PRR_PLDR);
+
+ return count;
+}
+
+static ssize_t vendor_reset_show(struct device *dev,
+ struct device_attribute *attr, char *buf)
+{
+ return sysfs_emit(buf, "0 - PLDR\n");
+}
+
+static DEVICE_ATTR_RW(vendor_reset);
+
+static struct attribute *btintel_pcie_attrs[] = {
+ &dev_attr_vendor_reset.attr,
+ NULL,
+};
+
+ATTRIBUTE_GROUPS(btintel_pcie);
+
static void btintel_pcie_hw_error(struct hci_dev *hdev, u8 code)
{
struct btintel_pcie_dev_recovery *rec;
@@ -3250,6 +3287,7 @@ static struct pci_driver btintel_pcie_driver = {
.probe = btintel_pcie_probe,
.remove = btintel_pcie_remove,
.driver.pm = pm_sleep_ptr(&btintel_pcie_pm_ops),
+ .dev_groups = btintel_pcie_groups,
#ifdef CONFIG_DEV_COREDUMP
.driver.coredump = btintel_pcie_coredump
#endif