xref: /aosp_15_r20/external/coreboot/util/uio_usbdebug/linux/uio_ehci_pci.c (revision b9411a12aaaa7e1e6a6fb7c5e057f44ee179a49c)
1 /* uio_ehci_pci - UIO driver for PCI EHCI devices */
2 /* This only implements MMIO access (no interrupts). */
3 /* SPDX-License-Identifier: GPL-2.0-only */
4 
5 #include <linux/device.h>
6 #include <linux/module.h>
7 #include <linux/pci.h>
8 #include <linux/uio_driver.h>
9 
10 #define DRIVER_VERSION	"0.0.1"
11 #define DRIVER_AUTHOR	"Nico Huber <[email protected]>"
12 #define DRIVER_DESC	"UIO driver for PCI EHCI devices"
13 #define DRIVER_TAG	"uio_ehci_pci"
14 
probe(struct pci_dev * const pci_dev,const struct pci_device_id * const did)15 static int probe(struct pci_dev *const pci_dev,
16 		 const struct pci_device_id *const did)
17 {
18 	struct uio_info *info;
19 	int ret;
20 
21 	ret = pci_enable_device(pci_dev);
22 	if (ret)
23 		goto return_;
24 
25 	ret = pci_request_regions(pci_dev, DRIVER_TAG);
26 	if (ret)
27 		goto return_disable;
28 
29 	info = kzalloc(sizeof(struct uio_info), GFP_KERNEL);
30 	if (!info) {
31 		ret = -ENOMEM;
32 		goto return_release;
33 	}
34 
35 	info->name = DRIVER_TAG;
36 	info->version = DRIVER_VERSION;
37 
38 	info->mem[0].name = "EHCI MMIO area";
39 	info->mem[0].addr = pci_resource_start(pci_dev, 0);
40 	if (!info->mem[0].addr) {
41 		ret = -ENODEV;
42 		goto return_free;
43 	}
44 	info->mem[0].size = pci_resource_len(pci_dev, 0);
45 	info->mem[0].memtype = UIO_MEM_PHYS;
46 
47 	ret = uio_register_device(&pci_dev->dev, info);
48 	if (ret)
49 		goto return_free;
50 	pci_set_drvdata(pci_dev, info);
51 
52 	return 0;
53 return_free:
54 	kfree(info);
55 return_release:
56 	pci_release_regions(pci_dev);
57 return_disable:
58 	pci_disable_device(pci_dev);
59 return_:
60 	return ret;
61 }
62 
remove(struct pci_dev * const pci_dev)63 static void remove(struct pci_dev *const pci_dev)
64 {
65 	struct uio_info *const info = pci_get_drvdata(pci_dev);
66 
67 	uio_unregister_device(info);
68 	kfree(info);
69 	pci_release_regions(pci_dev);
70 	pci_disable_device(pci_dev);
71 }
72 
73 static DEFINE_PCI_DEVICE_TABLE(ehci_pci_ids) = {
74 	{ PCI_DEVICE(0x8086, 0x27cc) },
75 	{ 0, }
76 };
77 
78 static struct pci_driver uio_ehci_pci_driver = {
79 	.name		= DRIVER_TAG,
80 	.id_table	= ehci_pci_ids,
81 	.probe		= probe,
82 	.remove		= remove,
83 };
84 
85 module_pci_driver(uio_ehci_pci_driver);
86 MODULE_VERSION(DRIVER_VERSION);
87 MODULE_LICENSE("GPL v2");
88 MODULE_AUTHOR(DRIVER_AUTHOR);
89 MODULE_DESCRIPTION(DRIVER_DESC);
90