diff options
author | Álvaro Fernández Rojas <noltari@gmail.com> | 2020-05-28 19:08:55 +0200 |
---|---|---|
committer | Álvaro Fernández Rojas <noltari@gmail.com> | 2020-05-28 19:12:43 +0200 |
commit | 77e97abf129c5028385dd72587eabab68db0d954 (patch) | |
tree | fc52a8c2ba346da77281f00538a1eb6de49deb5d /target/linux/bcm27xx/patches-5.4/950-0283-drivers-char-add-chardev-for-mmap-ing-the-RPiVid-con.patch | |
parent | 5d3a0c6b26144eb5d62515b99613b5ad8dbdc717 (diff) | |
download | upstream-77e97abf129c5028385dd72587eabab68db0d954.tar.gz upstream-77e97abf129c5028385dd72587eabab68db0d954.tar.bz2 upstream-77e97abf129c5028385dd72587eabab68db0d954.zip |
bcm27xx: update to latest patches from RPi foundation
Also removes random module and switches to new bcm2711 thermal driver.
Boot tested on RPi 4B v1.1 4G.
Signed-off-by: Álvaro Fernández Rojas <noltari@gmail.com>
Diffstat (limited to 'target/linux/bcm27xx/patches-5.4/950-0283-drivers-char-add-chardev-for-mmap-ing-the-RPiVid-con.patch')
-rw-r--r-- | target/linux/bcm27xx/patches-5.4/950-0283-drivers-char-add-chardev-for-mmap-ing-the-RPiVid-con.patch | 387 |
1 files changed, 0 insertions, 387 deletions
diff --git a/target/linux/bcm27xx/patches-5.4/950-0283-drivers-char-add-chardev-for-mmap-ing-the-RPiVid-con.patch b/target/linux/bcm27xx/patches-5.4/950-0283-drivers-char-add-chardev-for-mmap-ing-the-RPiVid-con.patch deleted file mode 100644 index 3f3c5ea148..0000000000 --- a/target/linux/bcm27xx/patches-5.4/950-0283-drivers-char-add-chardev-for-mmap-ing-the-RPiVid-con.patch +++ /dev/null @@ -1,387 +0,0 @@ -From dcf515d36ce574edd773c9c6321b6bbf9724e209 Mon Sep 17 00:00:00 2001 -From: Jonathan Bell <jonathan@raspberrypi.org> -Date: Thu, 9 May 2019 14:30:37 +0100 -Subject: [PATCH] drivers: char: add chardev for mmap'ing the RPiVid - control registers - -Based on the gpiomem driver, allow mapping of the decoder register -spaces such that userspace can access control/status registers. -This driver is intended for use with a custom ffmpeg backend accelerator -prior to a v4l2 driver being written. - -Signed-off-by: Jonathan Bell <jonathan@raspberrypi.org> ---- - drivers/char/broadcom/Kconfig | 8 + - drivers/char/broadcom/Makefile | 1 + - drivers/char/broadcom/rpivid-mem.c | 286 +++++++++++++++++++++++++++++ - drivers/mfd/bcm2835-pm.c | 12 +- - drivers/soc/bcm/bcm2835-power.c | 6 +- - include/linux/mfd/bcm2835-pm.h | 2 +- - 6 files changed, 305 insertions(+), 10 deletions(-) - create mode 100644 drivers/char/broadcom/rpivid-mem.c - ---- a/drivers/char/broadcom/Kconfig -+++ b/drivers/char/broadcom/Kconfig -@@ -49,3 +49,11 @@ config BCM2835_SMI_DEV - This driver provides a character device interface (ioctl + read/write) to - Broadcom's Secondary Memory interface. The low-level functionality is provided - by the SMI driver itself. -+ -+config RPIVID_MEM -+ tristate "Character device driver for the Raspberry Pi RPIVid video decoder hardware" -+ default n -+ help -+ This driver provides a character device interface for memory-map operations -+ so userspace tools can access the control and status registers of the -+ Raspberry Pi RPiVid video decoder hardware. ---- a/drivers/char/broadcom/Makefile -+++ b/drivers/char/broadcom/Makefile -@@ -4,3 +4,4 @@ obj-$(CONFIG_BCM_VC_SM) += vc_sm - - obj-$(CONFIG_BCM2835_DEVGPIOMEM)+= bcm2835-gpiomem.o - obj-$(CONFIG_BCM2835_SMI_DEV) += bcm2835_smi_dev.o -+obj-$(CONFIG_RPIVID_MEM) += rpivid-mem.o ---- /dev/null -+++ b/drivers/char/broadcom/rpivid-mem.c -@@ -0,0 +1,286 @@ -+/** -+ * rpivid-mem.c - character device access to the RPiVid decoder registers -+ * -+ * Based on bcm2835-gpiomem.c. Provides IO memory access to the decoder -+ * register blocks such that ffmpeg plugins can access the hardware. -+ * -+ * Jonathan Bell <jonathan@raspberrypi.org> -+ * Copyright (c) 2019, Raspberry Pi (Trading) Ltd. -+ * -+ * Redistribution and use in source and binary forms, with or without -+ * modification, are permitted provided that the following conditions -+ * are met: -+ * 1. Redistributions of source code must retain the above copyright -+ * notice, this list of conditions, and the following disclaimer, -+ * without modification. -+ * 2. Redistributions in binary form must reproduce the above copyright -+ * notice, this list of conditions and the following disclaimer in the -+ * documentation and/or other materials provided with the distribution. -+ * 3. The names of the above-listed copyright holders may not be used -+ * to endorse or promote products derived from this software without -+ * specific prior written permission. -+ * -+ * ALTERNATIVELY, this software may be distributed under the terms of the -+ * GNU General Public License ("GPL") version 2, as published by the Free -+ * Software Foundation. -+ * -+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS -+ * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, -+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR -+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR -+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, -+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, -+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR -+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF -+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING -+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS -+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -+ */ -+ -+#include <linux/kernel.h> -+#include <linux/module.h> -+#include <linux/of.h> -+#include <linux/of_device.h> -+#include <linux/platform_device.h> -+#include <linux/mm.h> -+#include <linux/slab.h> -+#include <linux/cdev.h> -+#include <linux/pagemap.h> -+#include <linux/io.h> -+ -+#define DRIVER_NAME "rpivid-mem" -+#define DEVICE_MINOR 0 -+ -+struct rpivid_mem_priv { -+ dev_t devid; -+ struct class *class; -+ struct cdev rpivid_mem_cdev; -+ unsigned long regs_phys; -+ unsigned long mem_window_len; -+ struct device *dev; -+ const char *name; -+}; -+ -+static int rpivid_mem_open(struct inode *inode, struct file *file) -+{ -+ int dev = iminor(inode); -+ int ret = 0; -+ struct rpivid_mem_priv *priv; -+ if (dev != DEVICE_MINOR && dev != DEVICE_MINOR + 1) -+ ret = -ENXIO; -+ -+ priv = container_of(inode->i_cdev, struct rpivid_mem_priv, -+ rpivid_mem_cdev); -+ if (!priv) -+ return -EINVAL; -+ file->private_data = priv; -+ return ret; -+} -+ -+static int rpivid_mem_release(struct inode *inode, struct file *file) -+{ -+ int dev = iminor(inode); -+ int ret = 0; -+ -+ if (dev != DEVICE_MINOR && dev != DEVICE_MINOR + 1) -+ ret = -ENXIO; -+ -+ return ret; -+} -+ -+static const struct vm_operations_struct rpivid_mem_vm_ops = { -+#ifdef CONFIG_HAVE_IOREMAP_PROT -+ .access = generic_access_phys -+#endif -+}; -+ -+static int rpivid_mem_mmap(struct file *file, struct vm_area_struct *vma) -+{ -+ struct rpivid_mem_priv *priv; -+ unsigned long pages; -+ -+ priv = file->private_data; -+ pages = priv->regs_phys >> PAGE_SHIFT; -+ /* -+ * The address decode is far larger than the actual number of registers. -+ * Just map the whole lot in. -+ */ -+ vma->vm_page_prot = phys_mem_access_prot(file, pages, -+ priv->mem_window_len, -+ vma->vm_page_prot); -+ vma->vm_ops = &rpivid_mem_vm_ops; -+ if (remap_pfn_range(vma, vma->vm_start, -+ pages, -+ priv->mem_window_len, -+ vma->vm_page_prot)) { -+ return -EAGAIN; -+ } -+ return 0; -+} -+ -+static const struct file_operations -+rpivid_mem_fops = { -+ .owner = THIS_MODULE, -+ .open = rpivid_mem_open, -+ .release = rpivid_mem_release, -+ .mmap = rpivid_mem_mmap, -+}; -+ -+static const struct of_device_id rpivid_mem_of_match[]; -+static int rpivid_mem_probe(struct platform_device *pdev) -+{ -+ int err; -+ void *ptr_err; -+ const struct of_device_id *id; -+ struct device *dev = &pdev->dev; -+ struct device *rpivid_mem_dev; -+ struct resource *ioresource; -+ struct rpivid_mem_priv *priv; -+ -+ -+ /* Allocate buffers and instance data */ -+ -+ priv = kzalloc(sizeof(struct rpivid_mem_priv), GFP_KERNEL); -+ -+ if (!priv) { -+ err = -ENOMEM; -+ goto failed_inst_alloc; -+ } -+ platform_set_drvdata(pdev, priv); -+ -+ priv->dev = dev; -+ id = of_match_device(rpivid_mem_of_match, dev); -+ if (!id) -+ return -EINVAL; -+ priv->name = id->data; -+ -+ ioresource = platform_get_resource(pdev, IORESOURCE_MEM, 0); -+ if (ioresource) { -+ priv->regs_phys = ioresource->start; -+ priv->mem_window_len = ioresource->end - ioresource->start; -+ } else { -+ dev_err(priv->dev, "failed to get IO resource"); -+ err = -ENOENT; -+ goto failed_get_resource; -+ } -+ -+ /* Create character device entries */ -+ -+ err = alloc_chrdev_region(&priv->devid, -+ DEVICE_MINOR, 2, priv->name); -+ if (err != 0) { -+ dev_err(priv->dev, "unable to allocate device number"); -+ goto failed_alloc_chrdev; -+ } -+ cdev_init(&priv->rpivid_mem_cdev, &rpivid_mem_fops); -+ priv->rpivid_mem_cdev.owner = THIS_MODULE; -+ err = cdev_add(&priv->rpivid_mem_cdev, priv->devid, 2); -+ if (err != 0) { -+ dev_err(priv->dev, "unable to register device"); -+ goto failed_cdev_add; -+ } -+ -+ /* Create sysfs entries */ -+ -+ priv->class = class_create(THIS_MODULE, priv->name); -+ ptr_err = priv->class; -+ if (IS_ERR(ptr_err)) -+ goto failed_class_create; -+ -+ rpivid_mem_dev = device_create(priv->class, NULL, -+ priv->devid, NULL, -+ priv->name); -+ ptr_err = rpivid_mem_dev; -+ if (IS_ERR(ptr_err)) -+ goto failed_device_create; -+ -+ /* Legacy alias */ -+ { -+ char *oldname = kstrdup(priv->name, GFP_KERNEL); -+ -+ oldname[1] = 'a'; -+ oldname[2] = 'r'; -+ oldname[3] = 'g'; -+ oldname[4] = 'o'; -+ oldname[5] = 'n'; -+ (void)device_create(priv->class, NULL, priv->devid + 1, NULL, -+ oldname + 1); -+ kfree(oldname); -+ } -+ -+ dev_info(priv->dev, "%s initialised: Registers at 0x%08lx length 0x%08lx", -+ priv->name, priv->regs_phys, priv->mem_window_len); -+ -+ return 0; -+ -+failed_device_create: -+ class_destroy(priv->class); -+failed_class_create: -+ cdev_del(&priv->rpivid_mem_cdev); -+ err = PTR_ERR(ptr_err); -+failed_cdev_add: -+ unregister_chrdev_region(priv->devid, 1); -+failed_alloc_chrdev: -+failed_get_resource: -+ kfree(priv); -+failed_inst_alloc: -+ dev_err(priv->dev, "could not load rpivid_mem"); -+ return err; -+} -+ -+static int rpivid_mem_remove(struct platform_device *pdev) -+{ -+ struct device *dev = &pdev->dev; -+ struct rpivid_mem_priv *priv = platform_get_drvdata(pdev); -+ -+ device_destroy(priv->class, priv->devid); -+ class_destroy(priv->class); -+ cdev_del(&priv->rpivid_mem_cdev); -+ unregister_chrdev_region(priv->devid, 1); -+ kfree(priv); -+ -+ dev_info(dev, "%s driver removed - OK", priv->name); -+ return 0; -+} -+ -+static const struct of_device_id rpivid_mem_of_match[] = { -+ { -+ .compatible = "raspberrypi,rpivid-hevc-decoder", -+ .data = "rpivid-hevcmem", -+ }, -+ { -+ .compatible = "raspberrypi,rpivid-h264-decoder", -+ .data = "rpivid-h264mem", -+ }, -+ { -+ .compatible = "raspberrypi,rpivid-vp9-decoder", -+ .data = "rpivid-vp9mem", -+ }, -+ /* The "intc" is included as this block of hardware contains the -+ * "frame done" status flags. -+ */ -+ { -+ .compatible = "raspberrypi,rpivid-local-intc", -+ .data = "rpivid-intcmem", -+ }, -+ { /* sentinel */ }, -+}; -+ -+MODULE_DEVICE_TABLE(of, rpivid_mem_of_match); -+ -+static struct platform_driver rpivid_mem_driver = { -+ .probe = rpivid_mem_probe, -+ .remove = rpivid_mem_remove, -+ .driver = { -+ .name = DRIVER_NAME, -+ .owner = THIS_MODULE, -+ .of_match_table = rpivid_mem_of_match, -+ }, -+}; -+ -+module_platform_driver(rpivid_mem_driver); -+ -+MODULE_ALIAS("platform:rpivid-mem"); -+MODULE_LICENSE("GPL"); -+MODULE_DESCRIPTION("Driver for accessing RPiVid decoder registers from userspace"); -+MODULE_AUTHOR("Jonathan Bell <jonathan@raspberrypi.org>"); ---- a/drivers/mfd/bcm2835-pm.c -+++ b/drivers/mfd/bcm2835-pm.c -@@ -50,14 +50,14 @@ static int bcm2835_pm_probe(struct platf - if (ret) - return ret; - -- /* Map the ARGON ASB regs if present. */ -+ /* Map the RPiVid ASB regs if present. */ - res = platform_get_resource(pdev, IORESOURCE_MEM, 2); - if (res) { -- pm->arg_asb = devm_ioremap_resource(dev, res); -- if (IS_ERR(pm->arg_asb)) { -- dev_err(dev, "Failed to map ARGON ASB: %ld\n", -- PTR_ERR(pm->arg_asb)); -- return PTR_ERR(pm->arg_asb); -+ pm->rpivid_asb = devm_ioremap_resource(dev, res); -+ if (IS_ERR(pm->rpivid_asb)) { -+ dev_err(dev, "Failed to map RPiVid ASB: %ld\n", -+ PTR_ERR(pm->rpivid_asb)); -+ return PTR_ERR(pm->rpivid_asb); - } - } - ---- a/drivers/soc/bcm/bcm2835-power.c -+++ b/drivers/soc/bcm/bcm2835-power.c -@@ -637,15 +637,15 @@ static int bcm2835_power_probe(struct pl - power->base = pm->base; - power->asb = pm->asb; - -- /* 2711 hack: the new ARGON ASB took over V3D, which is our -+ /* 2711 hack: the new RPiVid ASB took over V3D, which is our - * only consumer of this driver so far. The old ASB seems to - * still be present with ISP and H264 bits but no V3D, but I - * don't know if that's real or not. The V3D is in the same - * place in the new ASB as the old one, so just poke the new - * one for now. - */ -- if (pm->arg_asb) { -- power->asb = pm->arg_asb; -+ if (pm->rpivid_asb) { -+ power->asb = pm->rpivid_asb; - power->is_2711 = true; - } - ---- a/include/linux/mfd/bcm2835-pm.h -+++ b/include/linux/mfd/bcm2835-pm.h -@@ -9,7 +9,7 @@ struct bcm2835_pm { - struct device *dev; - void __iomem *base; - void __iomem *asb; -- void __iomem *arg_asb; -+ void __iomem *rpivid_asb; - }; - - #endif /* BCM2835_MFD_PM_H */ |