The PCIIOC_* commands take and return plain values and don't touch userspace memory. Implement ->proc_ioctl_buf() and list them with nothing to copy. 32-bit tasks go through the same table, so the compat hook goes away. Unknown commands fail with -ENOTTY from procfs now instead of -EINVAL, and instead of -EPERM under lockdown, since they never reach the handler.
Signed-off-by: Christian Brauner (Amutable) <[email protected]> --- drivers/pci/proc.c | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-) diff --git a/drivers/pci/proc.c b/drivers/pci/proc.c index a8d7469f222b..6b0cb5bcbea3 100644 --- a/drivers/pci/proc.c +++ b/drivers/pci/proc.c @@ -192,8 +192,7 @@ struct pci_filp_private { }; #endif /* HAVE_PCI_MMAP */ -static long proc_bus_pci_ioctl(struct file *file, unsigned int cmd, - unsigned long arg) +static long proc_bus_pci_ioctl(struct file *file, unsigned int cmd, void *arg) { struct pci_dev *dev = pde_data(file_inode(file)); #ifdef HAVE_PCI_MMAP @@ -321,16 +320,23 @@ static int proc_bus_pci_release(struct inode *inode, struct file *file) } #endif /* HAVE_PCI_MMAP */ +/* The commands take and return plain values. */ +static const struct proc_ioctl_arg proc_bus_pci_ioctl_args[] = { + PROC_IOCTL_ARG(PCIIOC_CONTROLLER, 0, 0), + PROC_IOCTL_ARG(PCIIOC_MMAP_IS_IO, 0, 0), + PROC_IOCTL_ARG(PCIIOC_MMAP_IS_MEM, 0, 0), + PROC_IOCTL_ARG(PCIIOC_WRITE_COMBINE, 0, 0), +}; + static const struct proc_ops proc_bus_pci_ops = { .proc_flags = PROC_ENTRY_SHORT_WRITES, .proc_lseek = proc_bus_pci_lseek, .proc_read_buf = proc_bus_pci_read, .proc_write_buf = proc_bus_pci_write, .proc_write_size = PCI_CFG_SPACE_EXP_SIZE, - .proc_ioctl = proc_bus_pci_ioctl, -#ifdef CONFIG_COMPAT - .proc_compat_ioctl = proc_bus_pci_ioctl, -#endif + .proc_ioctl_buf = proc_bus_pci_ioctl, + .proc_ioctl_args = proc_bus_pci_ioctl_args, + .proc_nr_ioctl_args = ARRAY_SIZE(proc_bus_pci_ioctl_args), #ifdef HAVE_PCI_MMAP .proc_open = proc_bus_pci_open, .proc_release = proc_bus_pci_release, -- 2.53.0
