From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Return-Path: Date: Wed, 14 Sep 2016 09:30:52 +0100 From: Lee Jones Subject: Re: [PATCH v9 01/19] remoteproc: st_slim_rproc: add a slimcore rproc driver Message-ID: <20160914083052.GA638@dell> References: <1473081421-16555-1-git-send-email-peter.griffin@linaro.org> <1473081421-16555-2-git-send-email-peter.griffin@linaro.org> <20160913175656.GC21438@tuxbot> MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Disposition: inline Content-Transfer-Encoding: 8bit In-Reply-To: <20160913175656.GC21438@tuxbot> To: Bjorn Andersson Cc: Peter Griffin , linux-arm-kernel@lists.infradead.org, linux-kernel@vger.kernel.org, kernel@stlinux.com, vinod.koul@intel.com, patrice.chotard@st.com, dan.j.williams@intel.com, airlied@linux.ie, kraxel@redhat.com, ohad@wizery.com, dmaengine@vger.kernel.org, devicetree@vger.kernel.org, dri-devel@lists.freedesktop.org, linux-remoteproc@vger.kernel.org, virtualization@lists.linux-foundation.org List-ID: On Tue, 13 Sep 2016, Bjorn Andersson wrote: > On Mon 05 Sep 06:16 PDT 2016, Peter Griffin wrote: > > > slim core is used as a basis for many IPs in the STi > > chipsets such as fdma and demux. To avoid duplicating > > the elf loading code in each device driver a slim > > rproc driver has been created. > > > > This driver is designed to be used by other device drivers > > such as fdma, or demux whose IP is based around a slim core. > > The device driver can call slim_rproc_alloc() to allocate > > a slim rproc and slim_rproc_put() when finished. > > > > This driver takes care of ioremapping the slim > > registers (dmem, imem, slimcore, peripherals), whose offsets > > and sizes can change between IP's. It also obtains and enables > > any clocks used by the device. This approach avoids having > > a double mapping of the registers as slim_rproc does not register > > its own platform device. It also maps well to device tree > > abstraction as it allows us to have one dt node for the whole > > device. > > > > All of the generic rproc elf loading code can be reused, and > > we provide start() stop() hooks to start and stop the slim > > core once the firmware has been loaded. This has been tested > > successfully with fdma driver. > > > > Signed-off-by: Peter Griffin > > Acked-by: Bjorn Andersson What's preventing this from being applied right away? > > --- > > drivers/remoteproc/Kconfig | 4 + > > drivers/remoteproc/Makefile | 1 + > > drivers/remoteproc/st_slim_rproc.c | 364 +++++++++++++++++++++++++++++++ > > include/linux/remoteproc/st_slim_rproc.h | 58 +++++ > > 4 files changed, 427 insertions(+) > > create mode 100644 drivers/remoteproc/st_slim_rproc.c > > create mode 100644 include/linux/remoteproc/st_slim_rproc.h > > > > diff --git a/drivers/remoteproc/Kconfig b/drivers/remoteproc/Kconfig > > index 1a8bf76a..a7bedc6 100644 > > --- a/drivers/remoteproc/Kconfig > > +++ b/drivers/remoteproc/Kconfig > > @@ -100,4 +100,8 @@ config ST_REMOTEPROC > > processor framework. > > This can be either built-in or a loadable module. > > > > +config ST_SLIM_REMOTEPROC > > + tristate > > + select REMOTEPROC > > + > > endmenu > > diff --git a/drivers/remoteproc/Makefile b/drivers/remoteproc/Makefile > > index 92d3758..db1dae7 100644 > > --- a/drivers/remoteproc/Makefile > > +++ b/drivers/remoteproc/Makefile > > @@ -14,3 +14,4 @@ obj-$(CONFIG_DA8XX_REMOTEPROC) += da8xx_remoteproc.o > > obj-$(CONFIG_QCOM_MDT_LOADER) += qcom_mdt_loader.o > > obj-$(CONFIG_QCOM_Q6V5_PIL) += qcom_q6v5_pil.o > > obj-$(CONFIG_ST_REMOTEPROC) += st_remoteproc.o > > +obj-$(CONFIG_ST_SLIM_REMOTEPROC) += st_slim_rproc.o > > diff --git a/drivers/remoteproc/st_slim_rproc.c b/drivers/remoteproc/st_slim_rproc.c > > new file mode 100644 > > index 0000000..1484e97 > > --- /dev/null > > +++ b/drivers/remoteproc/st_slim_rproc.c > > @@ -0,0 +1,364 @@ > > +/* > > + * SLIM core rproc driver > > + * > > + * Copyright (C) 2016 STMicroelectronics > > + * > > + * Author: Peter Griffin > > + * > > + * This program is free software; you can redistribute it and/or modify > > + * it under the terms of the GNU General Public License as published by > > + * the Free Software Foundation; either version 2 of the License, or > > + * (at your option) any later version. > > + */ > > + > > +#include > > +#include > > +#include > > +#include > > +#include > > +#include > > +#include > > +#include > > +#include > > +#include "remoteproc_internal.h" > > + > > +/* SLIM core registers */ > > +#define SLIM_ID_OFST 0x0 > > +#define SLIM_VER_OFST 0x4 > > + > > +#define SLIM_EN_OFST 0x8 > > +#define SLIM_EN_RUN BIT(0) > > + > > +#define SLIM_CLK_GATE_OFST 0xC > > +#define SLIM_CLK_GATE_DIS BIT(0) > > +#define SLIM_CLK_GATE_RESET BIT(2) > > + > > +#define SLIM_SLIM_PC_OFST 0x20 > > + > > +/* DMEM registers */ > > +#define SLIM_REV_ID_OFST 0x0 > > +#define SLIM_REV_ID_MIN_MASK GENMASK(15, 8) > > +#define SLIM_REV_ID_MIN(id) ((id & SLIM_REV_ID_MIN_MASK) >> 8) > > +#define SLIM_REV_ID_MAJ_MASK GENMASK(23, 16) > > +#define SLIM_REV_ID_MAJ(id) ((id & SLIM_REV_ID_MAJ_MASK) >> 16) > > + > > + > > +/* peripherals registers */ > > +#define SLIM_STBUS_SYNC_OFST 0xF88 > > +#define SLIM_STBUS_SYNC_DIS BIT(0) > > + > > +#define SLIM_INT_SET_OFST 0xFD4 > > +#define SLIM_INT_CLR_OFST 0xFD8 > > +#define SLIM_INT_MASK_OFST 0xFDC > > + > > +#define SLIM_CMD_CLR_OFST 0xFC8 > > +#define SLIM_CMD_MASK_OFST 0xFCC > > + > > +static const char *mem_names[ST_SLIM_MEM_MAX] = { > > + [ST_SLIM_DMEM] = "dmem", > > + [ST_SLIM_IMEM] = "imem", > > +}; > > + > > +static int slim_clk_get(struct st_slim_rproc *slim_rproc, struct device *dev) > > +{ > > + int clk, err; > > + > > + for (clk = 0; clk < ST_SLIM_MAX_CLK; clk++) { > > + slim_rproc->clks[clk] = of_clk_get(dev->of_node, clk); > > + if (IS_ERR(slim_rproc->clks[clk])) { > > + err = PTR_ERR(slim_rproc->clks[clk]); > > + if (err == -EPROBE_DEFER) > > + goto err_put_clks; > > + slim_rproc->clks[clk] = NULL; > > + break; > > + } > > + } > > + > > + return 0; > > + > > +err_put_clks: > > + while (--clk >= 0) > > + clk_put(slim_rproc->clks[clk]); > > + > > + return err; > > +} > > + > > +static void slim_clk_disable(struct st_slim_rproc *slim_rproc) > > +{ > > + int clk; > > + > > + for (clk = 0; clk < ST_SLIM_MAX_CLK && slim_rproc->clks[clk]; clk++) > > + clk_disable_unprepare(slim_rproc->clks[clk]); > > +} > > + > > +static int slim_clk_enable(struct st_slim_rproc *slim_rproc) > > +{ > > + int clk, ret; > > + > > + for (clk = 0; clk < ST_SLIM_MAX_CLK && slim_rproc->clks[clk]; clk++) { > > + ret = clk_prepare_enable(slim_rproc->clks[clk]); > > + if (ret) > > + goto err_disable_clks; > > + } > > + > > + return 0; > > + > > +err_disable_clks: > > + while (--clk >= 0) > > + clk_disable_unprepare(slim_rproc->clks[clk]); > > + > > + return ret; > > +} > > + > > +/* > > + * Remoteproc slim specific device handlers > > + */ > > +static int slim_rproc_start(struct rproc *rproc) > > +{ > > + struct device *dev = &rproc->dev; > > + struct st_slim_rproc *slim_rproc = rproc->priv; > > + unsigned long hw_id, hw_ver, fw_rev; > > + u32 val; > > + > > + /* disable CPU pipeline clock & reset CPU pipeline */ > > + val = SLIM_CLK_GATE_DIS | SLIM_CLK_GATE_RESET; > > + writel(val, slim_rproc->slimcore + SLIM_CLK_GATE_OFST); > > + > > + /* disable SLIM core STBus sync */ > > + writel(SLIM_STBUS_SYNC_DIS, slim_rproc->peri + SLIM_STBUS_SYNC_OFST); > > + > > + /* enable cpu pipeline clock */ > > + writel(!SLIM_CLK_GATE_DIS, > > + slim_rproc->slimcore + SLIM_CLK_GATE_OFST); > > + > > + /* clear int & cmd mailbox */ > > + writel(~0U, slim_rproc->peri + SLIM_INT_CLR_OFST); > > + writel(~0U, slim_rproc->peri + SLIM_CMD_CLR_OFST); > > + > > + /* enable all channels cmd & int */ > > + writel(~0U, slim_rproc->peri + SLIM_INT_MASK_OFST); > > + writel(~0U, slim_rproc->peri + SLIM_CMD_MASK_OFST); > > + > > + /* enable cpu */ > > + writel(SLIM_EN_RUN, slim_rproc->slimcore + SLIM_EN_OFST); > > + > > + hw_id = readl_relaxed(slim_rproc->slimcore + SLIM_ID_OFST); > > + hw_ver = readl_relaxed(slim_rproc->slimcore + SLIM_VER_OFST); > > + > > + fw_rev = readl(slim_rproc->mem[ST_SLIM_DMEM].cpu_addr + > > + SLIM_REV_ID_OFST); > > + > > + dev_info(dev, "fw rev:%ld.%ld on SLIM %ld.%ld\n", > > + SLIM_REV_ID_MAJ(fw_rev), SLIM_REV_ID_MIN(fw_rev), > > + hw_id, hw_ver); > > + > > + return 0; > > +} > > + > > +static int slim_rproc_stop(struct rproc *rproc) > > +{ > > + struct st_slim_rproc *slim_rproc = rproc->priv; > > + u32 val; > > + > > + /* mask all (cmd & int) channels */ > > + writel(0UL, slim_rproc->peri + SLIM_INT_MASK_OFST); > > + writel(0UL, slim_rproc->peri + SLIM_CMD_MASK_OFST); > > + > > + /* disable cpu pipeline clock */ > > + writel(SLIM_CLK_GATE_DIS, slim_rproc->slimcore + SLIM_CLK_GATE_OFST); > > + > > + writel(!SLIM_EN_RUN, slim_rproc->slimcore + SLIM_EN_OFST); > > + > > + val = readl(slim_rproc->slimcore + SLIM_EN_OFST); > > + if (val & SLIM_EN_RUN) > > + dev_warn(&rproc->dev, "Failed to disable SLIM"); > > + > > + dev_dbg(&rproc->dev, "slim stopped\n"); > > + > > + return 0; > > +} > > + > > +static void *slim_rproc_da_to_va(struct rproc *rproc, u64 da, int len) > > +{ > > + struct st_slim_rproc *slim_rproc = rproc->priv; > > + void *va = NULL; > > + int i; > > + > > + for (i = 0; i < ST_SLIM_MEM_MAX; i++) { > > + if (da != slim_rproc->mem[i].bus_addr) > > + continue; > > + > > + if (len <= slim_rproc->mem[i].size) { > > + /* __force to make sparse happy with type conversion */ > > + va = (__force void *)slim_rproc->mem[i].cpu_addr; > > + break; > > + } > > + } > > + > > + dev_dbg(&rproc->dev, "da = 0x%llx len = 0x%x va = 0x%p\n", da, len, va); > > + > > + return va; > > +} > > + > > +static struct rproc_ops slim_rproc_ops = { > > + .start = slim_rproc_start, > > + .stop = slim_rproc_stop, > > + .da_to_va = slim_rproc_da_to_va, > > +}; > > + > > +/* > > + * Firmware handler operations: sanity, boot address, load ... > > + */ > > + > > +static struct resource_table empty_rsc_tbl = { > > + .ver = 1, > > + .num = 0, > > +}; > > + > > +static struct resource_table *slim_rproc_find_rsc_table(struct rproc *rproc, > > + const struct firmware *fw, > > + int *tablesz) > > +{ > > + *tablesz = sizeof(empty_rsc_tbl); > > + return &empty_rsc_tbl; > > +} > > + > > +static struct rproc_fw_ops slim_rproc_fw_ops = { > > + .find_rsc_table = slim_rproc_find_rsc_table, > > +}; > > + > > +/** > > + * st_slim_rproc_alloc() - allocate and initialise slim rproc > > + * @pdev: Pointer to the platform_device struct > > + * @fw_name: Name of firmware for rproc to use > > + * > > + * Function for allocating and initialising a slim rproc for use by > > + * device drivers whose IP is based around the SLIM core. It > > + * obtains and enables any clocks required by the SLIM core and also > > + * ioremaps the various IO. > > + * > > + * Returns st_slim_rproc pointer or PTR_ERR() on error. > > + */ > > + > > +struct st_slim_rproc *st_slim_rproc_alloc(struct platform_device *pdev, > > + char *fw_name) > > +{ > > + struct device *dev = &pdev->dev; > > + struct st_slim_rproc *slim_rproc; > > + struct device_node *np = dev->of_node; > > + struct rproc *rproc; > > + struct resource *res; > > + int err, i; > > + const struct rproc_fw_ops *elf_ops; > > + > > + if (!fw_name) > > + return ERR_PTR(-EINVAL); > > + > > + if (!of_device_is_compatible(np, "st,slim-rproc")) > > + return ERR_PTR(-EINVAL); > > + > > + rproc = rproc_alloc(dev, np->name, &slim_rproc_ops, > > + fw_name, sizeof(*slim_rproc)); > > + if (!rproc) > > + return ERR_PTR(-ENOMEM); > > + > > + rproc->has_iommu = false; > > + > > + slim_rproc = rproc->priv; > > + slim_rproc->rproc = rproc; > > + > > + elf_ops = rproc->fw_ops; > > + /* Use some generic elf ops */ > > + slim_rproc_fw_ops.load = elf_ops->load; > > + slim_rproc_fw_ops.sanity_check = elf_ops->sanity_check; > > + > > + rproc->fw_ops = &slim_rproc_fw_ops; > > + > > + /* get imem and dmem */ > > + for (i = 0; i < ARRAY_SIZE(mem_names); i++) { > > + res = platform_get_resource_byname(pdev, IORESOURCE_MEM, > > + mem_names[i]); > > + > > + slim_rproc->mem[i].cpu_addr = devm_ioremap_resource(dev, res); > > + if (IS_ERR(slim_rproc->mem[i].cpu_addr)) { > > + dev_err(&pdev->dev, "devm_ioremap_resource failed\n"); > > + err = PTR_ERR(slim_rproc->mem[i].cpu_addr); > > + goto err; > > + } > > + slim_rproc->mem[i].bus_addr = res->start; > > + slim_rproc->mem[i].size = resource_size(res); > > + } > > + > > + res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "slimcore"); > > + slim_rproc->slimcore = devm_ioremap_resource(dev, res); > > + if (IS_ERR(slim_rproc->slimcore)) { > > + dev_err(&pdev->dev, "failed to ioremap slimcore IO\n"); > > + err = PTR_ERR(slim_rproc->slimcore); > > + goto err; > > + } > > + > > + res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "peripherals"); > > + slim_rproc->peri = devm_ioremap_resource(dev, res); > > + if (IS_ERR(slim_rproc->peri)) { > > + dev_err(&pdev->dev, "failed to ioremap peripherals IO\n"); > > + err = PTR_ERR(slim_rproc->peri); > > + goto err; > > + } > > + > > + err = slim_clk_get(slim_rproc, dev); > > + if (err) > > + goto err; > > + > > + err = slim_clk_enable(slim_rproc); > > + if (err) { > > + dev_err(dev, "Failed to enable clocks\n"); > > + goto err_clk_put; > > + } > > + > > + /* Register as a remoteproc device */ > > + err = rproc_add(rproc); > > + if (err) { > > + dev_err(dev, "registration of slim remoteproc failed\n"); > > + goto err_clk_dis; > > + } > > + > > + return slim_rproc; > > + > > +err_clk_dis: > > + slim_clk_disable(slim_rproc); > > +err_clk_put: > > + for (i = 0; i < ST_SLIM_MAX_CLK && slim_rproc->clks[i]; i++) > > + clk_put(slim_rproc->clks[i]); > > +err: > > + rproc_put(rproc); > > + return ERR_PTR(err); > > +} > > +EXPORT_SYMBOL(st_slim_rproc_alloc); > > + > > +/** > > + * st_slim_rproc_put() - put slim rproc resources > > + * @slim_rproc: Pointer to the st_slim_rproc struct > > + * > > + * Function for calling respective _put() functions on slim_rproc resources. > > + * > > + */ > > +void st_slim_rproc_put(struct st_slim_rproc *slim_rproc) > > +{ > > + int clk; > > + > > + if (!slim_rproc) > > + return; > > + > > + slim_clk_disable(slim_rproc); > > + > > + for (clk = 0; clk < ST_SLIM_MAX_CLK && slim_rproc->clks[clk]; clk++) > > + clk_put(slim_rproc->clks[clk]); > > + > > + rproc_del(slim_rproc->rproc); > > + rproc_put(slim_rproc->rproc); > > +} > > +EXPORT_SYMBOL(st_slim_rproc_put); > > + > > +MODULE_AUTHOR("Peter Griffin "); > > +MODULE_DESCRIPTION("STMicroelectronics SLIM core rproc driver"); > > +MODULE_LICENSE("GPL v2"); > > diff --git a/include/linux/remoteproc/st_slim_rproc.h b/include/linux/remoteproc/st_slim_rproc.h > > new file mode 100644 > > index 0000000..4155556 > > --- /dev/null > > +++ b/include/linux/remoteproc/st_slim_rproc.h > > @@ -0,0 +1,58 @@ > > +/* > > + * SLIM core rproc driver header > > + * > > + * Copyright (C) 2016 STMicroelectronics > > + * > > + * Author: Peter Griffin > > + * > > + * This program is free software; you can redistribute it and/or modify > > + * it under the terms of the GNU General Public License as published by > > + * the Free Software Foundation; either version 2 of the License, or > > + * (at your option) any later version. > > + */ > > +#ifndef _ST_REMOTEPROC_SLIM_H > > +#define _ST_REMOTEPROC_SLIM_H > > + > > +#define ST_SLIM_MEM_MAX 2 > > +#define ST_SLIM_MAX_CLK 4 > > + > > +enum { > > + ST_SLIM_DMEM, > > + ST_SLIM_IMEM, > > +}; > > + > > +/** > > + * struct st_slim_mem - slim internal memory structure > > + * @cpu_addr: MPU virtual address of the memory region > > + * @bus_addr: Bus address used to access the memory region > > + * @size: Size of the memory region > > + */ > > +struct st_slim_mem { > > + void __iomem *cpu_addr; > > + phys_addr_t bus_addr; > > + size_t size; > > +}; > > + > > +/** > > + * struct st_slim_rproc - SLIM slim core > > + * @rproc: rproc handle > > + * @mem: slim memory information > > + * @slimcore: slim slimcore regs > > + * @peri: slim peripheral regs > > + * @clks: slim clocks > > + */ > > +struct st_slim_rproc { > > + struct rproc *rproc; > > + struct st_slim_mem mem[ST_SLIM_MEM_MAX]; > > + void __iomem *slimcore; > > + void __iomem *peri; > > + > > + /* st_slim_rproc private */ > > + struct clk *clks[ST_SLIM_MAX_CLK]; > > +}; > > + > > +struct st_slim_rproc *st_slim_rproc_alloc(struct platform_device *pdev, > > + char *fw_name); > > +void st_slim_rproc_put(struct st_slim_rproc *slim_rproc); > > + > > +#endif -- Lee Jones Linaro STMicroelectronics Landing Team Lead Linaro.org │ Open source software for ARM SoCs Follow Linaro: Facebook | Twitter | Blog From mboxrd@z Thu Jan 1 00:00:00 1970 From: Lee Jones Subject: Re: [PATCH v9 01/19] remoteproc: st_slim_rproc: add a slimcore rproc driver Date: Wed, 14 Sep 2016 09:30:52 +0100 Message-ID: <20160914083052.GA638@dell> References: <1473081421-16555-1-git-send-email-peter.griffin@linaro.org> <1473081421-16555-2-git-send-email-peter.griffin@linaro.org> <20160913175656.GC21438@tuxbot> Mime-Version: 1.0 Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: base64 Return-path: Content-Disposition: inline In-Reply-To: <20160913175656.GC21438@tuxbot> List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: dri-devel-bounces@lists.freedesktop.org Sender: "dri-devel" To: Bjorn Andersson Cc: ohad@wizery.com, devicetree@vger.kernel.org, kernel@stlinux.com, vinod.koul@intel.com, linux-remoteproc@vger.kernel.org, patrice.chotard@st.com, dri-devel@lists.freedesktop.org, linux-kernel@vger.kernel.org, Peter Griffin , kraxel@redhat.com, dmaengine@vger.kernel.org, dan.j.williams@intel.com, virtualization@lists.linux-foundation.org, linux-arm-kernel@lists.infradead.org List-Id: devicetree@vger.kernel.org T24gVHVlLCAxMyBTZXAgMjAxNiwgQmpvcm4gQW5kZXJzc29uIHdyb3RlOgoKPiBPbiBNb24gMDUg U2VwIDA2OjE2IFBEVCAyMDE2LCBQZXRlciBHcmlmZmluIHdyb3RlOgo+IAo+ID4gc2xpbSBjb3Jl IGlzIHVzZWQgYXMgYSBiYXNpcyBmb3IgbWFueSBJUHMgaW4gdGhlIFNUaQo+ID4gY2hpcHNldHMg c3VjaCBhcyBmZG1hIGFuZCBkZW11eC4gVG8gYXZvaWQgZHVwbGljYXRpbmcKPiA+IHRoZSBlbGYg bG9hZGluZyBjb2RlIGluIGVhY2ggZGV2aWNlIGRyaXZlciBhIHNsaW0KPiA+IHJwcm9jIGRyaXZl ciBoYXMgYmVlbiBjcmVhdGVkLgo+ID4gCj4gPiBUaGlzIGRyaXZlciBpcyBkZXNpZ25lZCB0byBi ZSB1c2VkIGJ5IG90aGVyIGRldmljZSBkcml2ZXJzCj4gPiBzdWNoIGFzIGZkbWEsIG9yIGRlbXV4 IHdob3NlIElQIGlzIGJhc2VkIGFyb3VuZCBhIHNsaW0gY29yZS4KPiA+IFRoZSBkZXZpY2UgZHJp dmVyIGNhbiBjYWxsIHNsaW1fcnByb2NfYWxsb2MoKSB0byBhbGxvY2F0ZQo+ID4gYSBzbGltIHJw cm9jIGFuZCBzbGltX3Jwcm9jX3B1dCgpIHdoZW4gZmluaXNoZWQuCj4gPiAKPiA+IFRoaXMgZHJp dmVyIHRha2VzIGNhcmUgb2YgaW9yZW1hcHBpbmcgdGhlIHNsaW0KPiA+IHJlZ2lzdGVycyAoZG1l bSwgaW1lbSwgc2xpbWNvcmUsIHBlcmlwaGVyYWxzKSwgd2hvc2Ugb2Zmc2V0cwo+ID4gYW5kIHNp emVzIGNhbiBjaGFuZ2UgYmV0d2VlbiBJUCdzLiBJdCBhbHNvIG9idGFpbnMgYW5kIGVuYWJsZXMK PiA+IGFueSBjbG9ja3MgdXNlZCBieSB0aGUgZGV2aWNlLiBUaGlzIGFwcHJvYWNoIGF2b2lkcyBo YXZpbmcKPiA+IGEgZG91YmxlIG1hcHBpbmcgb2YgdGhlIHJlZ2lzdGVycyBhcyBzbGltX3Jwcm9j IGRvZXMgbm90IHJlZ2lzdGVyCj4gPiBpdHMgb3duIHBsYXRmb3JtIGRldmljZS4gSXQgYWxzbyBt YXBzIHdlbGwgdG8gZGV2aWNlIHRyZWUKPiA+IGFic3RyYWN0aW9uIGFzIGl0IGFsbG93cyB1cyB0 byBoYXZlIG9uZSBkdCBub2RlIGZvciB0aGUgd2hvbGUKPiA+IGRldmljZS4KPiA+IAo+ID4gQWxs IG9mIHRoZSBnZW5lcmljIHJwcm9jIGVsZiBsb2FkaW5nIGNvZGUgY2FuIGJlIHJldXNlZCwgYW5k Cj4gPiB3ZSBwcm92aWRlIHN0YXJ0KCkgc3RvcCgpIGhvb2tzIHRvIHN0YXJ0IGFuZCBzdG9wIHRo ZSBzbGltCj4gPiBjb3JlIG9uY2UgdGhlIGZpcm13YXJlIGhhcyBiZWVuIGxvYWRlZC4gVGhpcyBo YXMgYmVlbiB0ZXN0ZWQKPiA+IHN1Y2Nlc3NmdWxseSB3aXRoIGZkbWEgZHJpdmVyLgo+ID4gCj4g PiBTaWduZWQtb2ZmLWJ5OiBQZXRlciBHcmlmZmluIDxwZXRlci5ncmlmZmluQGxpbmFyby5vcmc+ Cj4gCj4gQWNrZWQtYnk6IEJqb3JuIEFuZGVyc3NvbiA8Ympvcm4uYW5kZXJzc29uQGxpbmFyby5v cmc+CgpXaGF0J3MgcHJldmVudGluZyB0aGlzIGZyb20gYmVpbmcgYXBwbGllZCByaWdodCBhd2F5 PwoKPiA+IC0tLQo+ID4gIGRyaXZlcnMvcmVtb3RlcHJvYy9LY29uZmlnICAgICAgICAgICAgICAg fCAgIDQgKwo+ID4gIGRyaXZlcnMvcmVtb3RlcHJvYy9NYWtlZmlsZSAgICAgICAgICAgICAgfCAg IDEgKwo+ID4gIGRyaXZlcnMvcmVtb3RlcHJvYy9zdF9zbGltX3Jwcm9jLmMgICAgICAgfCAzNjQg KysrKysrKysrKysrKysrKysrKysrKysrKysrKysrKwo+ID4gIGluY2x1ZGUvbGludXgvcmVtb3Rl cHJvYy9zdF9zbGltX3Jwcm9jLmggfCAgNTggKysrKysKPiA+ICA0IGZpbGVzIGNoYW5nZWQsIDQy NyBpbnNlcnRpb25zKCspCj4gPiAgY3JlYXRlIG1vZGUgMTAwNjQ0IGRyaXZlcnMvcmVtb3RlcHJv Yy9zdF9zbGltX3Jwcm9jLmMKPiA+ICBjcmVhdGUgbW9kZSAxMDA2NDQgaW5jbHVkZS9saW51eC9y ZW1vdGVwcm9jL3N0X3NsaW1fcnByb2MuaAo+ID4gCj4gPiBkaWZmIC0tZ2l0IGEvZHJpdmVycy9y ZW1vdGVwcm9jL0tjb25maWcgYi9kcml2ZXJzL3JlbW90ZXByb2MvS2NvbmZpZwo+ID4gaW5kZXgg MWE4YmY3NmEuLmE3YmVkYzYgMTAwNjQ0Cj4gPiAtLS0gYS9kcml2ZXJzL3JlbW90ZXByb2MvS2Nv bmZpZwo+ID4gKysrIGIvZHJpdmVycy9yZW1vdGVwcm9jL0tjb25maWcKPiA+IEBAIC0xMDAsNCAr MTAwLDggQEAgY29uZmlnIFNUX1JFTU9URVBST0MKPiA+ICAJICBwcm9jZXNzb3IgZnJhbWV3b3Jr Lgo+ID4gIAkgIFRoaXMgY2FuIGJlIGVpdGhlciBidWlsdC1pbiBvciBhIGxvYWRhYmxlIG1vZHVs ZS4KPiA+ICAKPiA+ICtjb25maWcgU1RfU0xJTV9SRU1PVEVQUk9DCj4gPiArCXRyaXN0YXRlCj4g PiArCXNlbGVjdCBSRU1PVEVQUk9DCj4gPiArCj4gPiAgZW5kbWVudQo+ID4gZGlmZiAtLWdpdCBh L2RyaXZlcnMvcmVtb3RlcHJvYy9NYWtlZmlsZSBiL2RyaXZlcnMvcmVtb3RlcHJvYy9NYWtlZmls ZQo+ID4gaW5kZXggOTJkMzc1OC4uZGIxZGFlNyAxMDA2NDQKPiA+IC0tLSBhL2RyaXZlcnMvcmVt b3RlcHJvYy9NYWtlZmlsZQo+ID4gKysrIGIvZHJpdmVycy9yZW1vdGVwcm9jL01ha2VmaWxlCj4g PiBAQCAtMTQsMyArMTQsNCBAQCBvYmotJChDT05GSUdfREE4WFhfUkVNT1RFUFJPQykJCSs9IGRh OHh4X3JlbW90ZXByb2Mubwo+ID4gIG9iai0kKENPTkZJR19RQ09NX01EVF9MT0FERVIpCQkrPSBx Y29tX21kdF9sb2FkZXIubwo+ID4gIG9iai0kKENPTkZJR19RQ09NX1E2VjVfUElMKQkJKz0gcWNv bV9xNnY1X3BpbC5vCj4gPiAgb2JqLSQoQ09ORklHX1NUX1JFTU9URVBST0MpCQkrPSBzdF9yZW1v dGVwcm9jLm8KPiA+ICtvYmotJChDT05GSUdfU1RfU0xJTV9SRU1PVEVQUk9DKQkrPSBzdF9zbGlt X3Jwcm9jLm8KPiA+IGRpZmYgLS1naXQgYS9kcml2ZXJzL3JlbW90ZXByb2Mvc3Rfc2xpbV9ycHJv Yy5jIGIvZHJpdmVycy9yZW1vdGVwcm9jL3N0X3NsaW1fcnByb2MuYwo+ID4gbmV3IGZpbGUgbW9k ZSAxMDA2NDQKPiA+IGluZGV4IDAwMDAwMDAuLjE0ODRlOTcKPiA+IC0tLSAvZGV2L251bGwKPiA+ ICsrKyBiL2RyaXZlcnMvcmVtb3RlcHJvYy9zdF9zbGltX3Jwcm9jLmMKPiA+IEBAIC0wLDAgKzEs MzY0IEBACj4gPiArLyoKPiA+ICsgKiBTTElNIGNvcmUgcnByb2MgZHJpdmVyCj4gPiArICoKPiA+ ICsgKiBDb3B5cmlnaHQgKEMpIDIwMTYgU1RNaWNyb2VsZWN0cm9uaWNzCj4gPiArICoKPiA+ICsg KiBBdXRob3I6IFBldGVyIEdyaWZmaW4gPHBldGVyLmdyaWZmaW5AbGluYXJvLm9yZz4KPiA+ICsg Kgo+ID4gKyAqIFRoaXMgcHJvZ3JhbSBpcyBmcmVlIHNvZnR3YXJlOyB5b3UgY2FuIHJlZGlzdHJp YnV0ZSBpdCBhbmQvb3IgbW9kaWZ5Cj4gPiArICogaXQgdW5kZXIgdGhlIHRlcm1zIG9mIHRoZSBH TlUgR2VuZXJhbCBQdWJsaWMgTGljZW5zZSBhcyBwdWJsaXNoZWQgYnkKPiA+ICsgKiB0aGUgRnJl ZSBTb2Z0d2FyZSBGb3VuZGF0aW9uOyBlaXRoZXIgdmVyc2lvbiAyIG9mIHRoZSBMaWNlbnNlLCBv cgo+ID4gKyAqIChhdCB5b3VyIG9wdGlvbikgYW55IGxhdGVyIHZlcnNpb24uCj4gPiArICovCj4g PiArCj4gPiArI2luY2x1ZGUgPGxpbnV4L2Nsay5oPgo+ID4gKyNpbmNsdWRlIDxsaW51eC9lcnIu aD4KPiA+ICsjaW5jbHVkZSA8bGludXgva2VybmVsLmg+Cj4gPiArI2luY2x1ZGUgPGxpbnV4L21v ZHVsZS5oPgo+ID4gKyNpbmNsdWRlIDxsaW51eC9vZi5oPgo+ID4gKyNpbmNsdWRlIDxsaW51eC9v Zl9kZXZpY2UuaD4KPiA+ICsjaW5jbHVkZSA8bGludXgvcGxhdGZvcm1fZGV2aWNlLmg+Cj4gPiAr I2luY2x1ZGUgPGxpbnV4L3JlbW90ZXByb2MuaD4KPiA+ICsjaW5jbHVkZSA8bGludXgvcmVtb3Rl cHJvYy9zdF9zbGltX3Jwcm9jLmg+Cj4gPiArI2luY2x1ZGUgInJlbW90ZXByb2NfaW50ZXJuYWwu aCIKPiA+ICsKPiA+ICsvKiBTTElNIGNvcmUgcmVnaXN0ZXJzICovCj4gPiArI2RlZmluZSBTTElN X0lEX09GU1QJCTB4MAo+ID4gKyNkZWZpbmUgU0xJTV9WRVJfT0ZTVAkJMHg0Cj4gPiArCj4gPiAr I2RlZmluZSBTTElNX0VOX09GU1QJCTB4OAo+ID4gKyNkZWZpbmUgU0xJTV9FTl9SVU4JCQlCSVQo MCkKPiA+ICsKPiA+ICsjZGVmaW5lIFNMSU1fQ0xLX0dBVEVfT0ZTVAkweEMKPiA+ICsjZGVmaW5l IFNMSU1fQ0xLX0dBVEVfRElTCQlCSVQoMCkKPiA+ICsjZGVmaW5lIFNMSU1fQ0xLX0dBVEVfUkVT RVQJCUJJVCgyKQo+ID4gKwo+ID4gKyNkZWZpbmUgU0xJTV9TTElNX1BDX09GU1QJMHgyMAo+ID4g Kwo+ID4gKy8qIERNRU0gcmVnaXN0ZXJzICovCj4gPiArI2RlZmluZSBTTElNX1JFVl9JRF9PRlNU CTB4MAo+ID4gKyNkZWZpbmUgU0xJTV9SRVZfSURfTUlOX01BU0sJCUdFTk1BU0soMTUsIDgpCj4g PiArI2RlZmluZSBTTElNX1JFVl9JRF9NSU4oaWQpCQkoKGlkICYgU0xJTV9SRVZfSURfTUlOX01B U0spID4+IDgpCj4gPiArI2RlZmluZSBTTElNX1JFVl9JRF9NQUpfTUFTSwkJR0VOTUFTSygyMywg MTYpCj4gPiArI2RlZmluZSBTTElNX1JFVl9JRF9NQUooaWQpCQkoKGlkICYgU0xJTV9SRVZfSURf TUFKX01BU0spID4+IDE2KQo+ID4gKwo+ID4gKwo+ID4gKy8qIHBlcmlwaGVyYWxzIHJlZ2lzdGVy cyAqLwo+ID4gKyNkZWZpbmUgU0xJTV9TVEJVU19TWU5DX09GU1QJMHhGODgKPiA+ICsjZGVmaW5l IFNMSU1fU1RCVVNfU1lOQ19ESVMJCUJJVCgwKQo+ID4gKwo+ID4gKyNkZWZpbmUgU0xJTV9JTlRf U0VUX09GU1QJMHhGRDQKPiA+ICsjZGVmaW5lIFNMSU1fSU5UX0NMUl9PRlNUCTB4RkQ4Cj4gPiAr I2RlZmluZSBTTElNX0lOVF9NQVNLX09GU1QJMHhGREMKPiA+ICsKPiA+ICsjZGVmaW5lIFNMSU1f Q01EX0NMUl9PRlNUCTB4RkM4Cj4gPiArI2RlZmluZSBTTElNX0NNRF9NQVNLX09GU1QJMHhGQ0MK PiA+ICsKPiA+ICtzdGF0aWMgY29uc3QgY2hhciAqbWVtX25hbWVzW1NUX1NMSU1fTUVNX01BWF0g PSB7Cj4gPiArCVtTVF9TTElNX0RNRU1dCT0gImRtZW0iLAo+ID4gKwlbU1RfU0xJTV9JTUVNXQk9 ICJpbWVtIiwKPiA+ICt9Owo+ID4gKwo+ID4gK3N0YXRpYyBpbnQgc2xpbV9jbGtfZ2V0KHN0cnVj dCBzdF9zbGltX3Jwcm9jICpzbGltX3Jwcm9jLCBzdHJ1Y3QgZGV2aWNlICpkZXYpCj4gPiArewo+ ID4gKwlpbnQgY2xrLCBlcnI7Cj4gPiArCj4gPiArCWZvciAoY2xrID0gMDsgY2xrIDwgU1RfU0xJ TV9NQVhfQ0xLOyBjbGsrKykgewo+ID4gKwkJc2xpbV9ycHJvYy0+Y2xrc1tjbGtdID0gb2ZfY2xr X2dldChkZXYtPm9mX25vZGUsIGNsayk7Cj4gPiArCQlpZiAoSVNfRVJSKHNsaW1fcnByb2MtPmNs a3NbY2xrXSkpIHsKPiA+ICsJCQllcnIgPSBQVFJfRVJSKHNsaW1fcnByb2MtPmNsa3NbY2xrXSk7 Cj4gPiArCQkJaWYgKGVyciA9PSAtRVBST0JFX0RFRkVSKQo+ID4gKwkJCQlnb3RvIGVycl9wdXRf Y2xrczsKPiA+ICsJCQlzbGltX3Jwcm9jLT5jbGtzW2Nsa10gPSBOVUxMOwo+ID4gKwkJCWJyZWFr Owo+ID4gKwkJfQo+ID4gKwl9Cj4gPiArCj4gPiArCXJldHVybiAwOwo+ID4gKwo+ID4gK2Vycl9w dXRfY2xrczoKPiA+ICsJd2hpbGUgKC0tY2xrID49IDApCj4gPiArCQljbGtfcHV0KHNsaW1fcnBy b2MtPmNsa3NbY2xrXSk7Cj4gPiArCj4gPiArCXJldHVybiBlcnI7Cj4gPiArfQo+ID4gKwo+ID4g K3N0YXRpYyB2b2lkIHNsaW1fY2xrX2Rpc2FibGUoc3RydWN0IHN0X3NsaW1fcnByb2MgKnNsaW1f cnByb2MpCj4gPiArewo+ID4gKwlpbnQgY2xrOwo+ID4gKwo+ID4gKwlmb3IgKGNsayA9IDA7IGNs ayA8IFNUX1NMSU1fTUFYX0NMSyAmJiBzbGltX3Jwcm9jLT5jbGtzW2Nsa107IGNsaysrKQo+ID4g KwkJY2xrX2Rpc2FibGVfdW5wcmVwYXJlKHNsaW1fcnByb2MtPmNsa3NbY2xrXSk7Cj4gPiArfQo+ ID4gKwo+ID4gK3N0YXRpYyBpbnQgc2xpbV9jbGtfZW5hYmxlKHN0cnVjdCBzdF9zbGltX3Jwcm9j ICpzbGltX3Jwcm9jKQo+ID4gK3sKPiA+ICsJaW50IGNsaywgcmV0Owo+ID4gKwo+ID4gKwlmb3Ig KGNsayA9IDA7IGNsayA8IFNUX1NMSU1fTUFYX0NMSyAmJiBzbGltX3Jwcm9jLT5jbGtzW2Nsa107 IGNsaysrKSB7Cj4gPiArCQlyZXQgPSBjbGtfcHJlcGFyZV9lbmFibGUoc2xpbV9ycHJvYy0+Y2xr c1tjbGtdKTsKPiA+ICsJCWlmIChyZXQpCj4gPiArCQkJZ290byBlcnJfZGlzYWJsZV9jbGtzOwo+ ID4gKwl9Cj4gPiArCj4gPiArCXJldHVybiAwOwo+ID4gKwo+ID4gK2Vycl9kaXNhYmxlX2Nsa3M6 Cj4gPiArCXdoaWxlICgtLWNsayA+PSAwKQo+ID4gKwkJY2xrX2Rpc2FibGVfdW5wcmVwYXJlKHNs aW1fcnByb2MtPmNsa3NbY2xrXSk7Cj4gPiArCj4gPiArCXJldHVybiByZXQ7Cj4gPiArfQo+ID4g Kwo+ID4gKy8qCj4gPiArICogUmVtb3RlcHJvYyBzbGltIHNwZWNpZmljIGRldmljZSBoYW5kbGVy cwo+ID4gKyAqLwo+ID4gK3N0YXRpYyBpbnQgc2xpbV9ycHJvY19zdGFydChzdHJ1Y3QgcnByb2Mg KnJwcm9jKQo+ID4gK3sKPiA+ICsJc3RydWN0IGRldmljZSAqZGV2ID0gJnJwcm9jLT5kZXY7Cj4g PiArCXN0cnVjdCBzdF9zbGltX3Jwcm9jICpzbGltX3Jwcm9jID0gcnByb2MtPnByaXY7Cj4gPiAr CXVuc2lnbmVkIGxvbmcgaHdfaWQsIGh3X3ZlciwgZndfcmV2Owo+ID4gKwl1MzIgdmFsOwo+ID4g Kwo+ID4gKwkvKiBkaXNhYmxlIENQVSBwaXBlbGluZSBjbG9jayAmIHJlc2V0IENQVSBwaXBlbGlu ZSAqLwo+ID4gKwl2YWwgPSBTTElNX0NMS19HQVRFX0RJUyB8IFNMSU1fQ0xLX0dBVEVfUkVTRVQ7 Cj4gPiArCXdyaXRlbCh2YWwsIHNsaW1fcnByb2MtPnNsaW1jb3JlICsgU0xJTV9DTEtfR0FURV9P RlNUKTsKPiA+ICsKPiA+ICsJLyogZGlzYWJsZSBTTElNIGNvcmUgU1RCdXMgc3luYyAqLwo+ID4g Kwl3cml0ZWwoU0xJTV9TVEJVU19TWU5DX0RJUywgc2xpbV9ycHJvYy0+cGVyaSArIFNMSU1fU1RC VVNfU1lOQ19PRlNUKTsKPiA+ICsKPiA+ICsJLyogZW5hYmxlIGNwdSBwaXBlbGluZSBjbG9jayAq Lwo+ID4gKwl3cml0ZWwoIVNMSU1fQ0xLX0dBVEVfRElTLAo+ID4gKwkJc2xpbV9ycHJvYy0+c2xp bWNvcmUgKyBTTElNX0NMS19HQVRFX09GU1QpOwo+ID4gKwo+ID4gKwkvKiBjbGVhciBpbnQgJiBj bWQgbWFpbGJveCAqLwo+ID4gKwl3cml0ZWwofjBVLCBzbGltX3Jwcm9jLT5wZXJpICsgU0xJTV9J TlRfQ0xSX09GU1QpOwo+ID4gKwl3cml0ZWwofjBVLCBzbGltX3Jwcm9jLT5wZXJpICsgU0xJTV9D TURfQ0xSX09GU1QpOwo+ID4gKwo+ID4gKwkvKiBlbmFibGUgYWxsIGNoYW5uZWxzIGNtZCAmIGlu dCAqLwo+ID4gKwl3cml0ZWwofjBVLCBzbGltX3Jwcm9jLT5wZXJpICsgU0xJTV9JTlRfTUFTS19P RlNUKTsKPiA+ICsJd3JpdGVsKH4wVSwgc2xpbV9ycHJvYy0+cGVyaSArIFNMSU1fQ01EX01BU0tf T0ZTVCk7Cj4gPiArCj4gPiArCS8qIGVuYWJsZSBjcHUgKi8KPiA+ICsJd3JpdGVsKFNMSU1fRU5f UlVOLCBzbGltX3Jwcm9jLT5zbGltY29yZSArIFNMSU1fRU5fT0ZTVCk7Cj4gPiArCj4gPiArCWh3 X2lkID0gcmVhZGxfcmVsYXhlZChzbGltX3Jwcm9jLT5zbGltY29yZSArIFNMSU1fSURfT0ZTVCk7 Cj4gPiArCWh3X3ZlciA9IHJlYWRsX3JlbGF4ZWQoc2xpbV9ycHJvYy0+c2xpbWNvcmUgKyBTTElN X1ZFUl9PRlNUKTsKPiA+ICsKPiA+ICsJZndfcmV2ID0gcmVhZGwoc2xpbV9ycHJvYy0+bWVtW1NU X1NMSU1fRE1FTV0uY3B1X2FkZHIgKwo+ID4gKwkJCVNMSU1fUkVWX0lEX09GU1QpOwo+ID4gKwo+ ID4gKwlkZXZfaW5mbyhkZXYsICJmdyByZXY6JWxkLiVsZCBvbiBTTElNICVsZC4lbGRcbiIsCj4g PiArCQkgU0xJTV9SRVZfSURfTUFKKGZ3X3JldiksIFNMSU1fUkVWX0lEX01JTihmd19yZXYpLAo+ ID4gKwkJIGh3X2lkLCBod192ZXIpOwo+ID4gKwo+ID4gKwlyZXR1cm4gMDsKPiA+ICt9Cj4gPiAr Cj4gPiArc3RhdGljIGludCBzbGltX3Jwcm9jX3N0b3Aoc3RydWN0IHJwcm9jICpycHJvYykKPiA+ ICt7Cj4gPiArCXN0cnVjdCBzdF9zbGltX3Jwcm9jICpzbGltX3Jwcm9jID0gcnByb2MtPnByaXY7 Cj4gPiArCXUzMiB2YWw7Cj4gPiArCj4gPiArCS8qIG1hc2sgYWxsIChjbWQgJiBpbnQpIGNoYW5u ZWxzICovCj4gPiArCXdyaXRlbCgwVUwsIHNsaW1fcnByb2MtPnBlcmkgKyBTTElNX0lOVF9NQVNL X09GU1QpOwo+ID4gKwl3cml0ZWwoMFVMLCBzbGltX3Jwcm9jLT5wZXJpICsgU0xJTV9DTURfTUFT S19PRlNUKTsKPiA+ICsKPiA+ICsJLyogZGlzYWJsZSBjcHUgcGlwZWxpbmUgY2xvY2sgKi8KPiA+ ICsJd3JpdGVsKFNMSU1fQ0xLX0dBVEVfRElTLCBzbGltX3Jwcm9jLT5zbGltY29yZSArIFNMSU1f Q0xLX0dBVEVfT0ZTVCk7Cj4gPiArCj4gPiArCXdyaXRlbCghU0xJTV9FTl9SVU4sIHNsaW1fcnBy b2MtPnNsaW1jb3JlICsgU0xJTV9FTl9PRlNUKTsKPiA+ICsKPiA+ICsJdmFsID0gcmVhZGwoc2xp bV9ycHJvYy0+c2xpbWNvcmUgKyBTTElNX0VOX09GU1QpOwo+ID4gKwlpZiAodmFsICYgU0xJTV9F Tl9SVU4pCj4gPiArCQlkZXZfd2FybigmcnByb2MtPmRldiwgIkZhaWxlZCB0byBkaXNhYmxlIFNM SU0iKTsKPiA+ICsKPiA+ICsJZGV2X2RiZygmcnByb2MtPmRldiwgInNsaW0gc3RvcHBlZFxuIik7 Cj4gPiArCj4gPiArCXJldHVybiAwOwo+ID4gK30KPiA+ICsKPiA+ICtzdGF0aWMgdm9pZCAqc2xp bV9ycHJvY19kYV90b192YShzdHJ1Y3QgcnByb2MgKnJwcm9jLCB1NjQgZGEsIGludCBsZW4pCj4g PiArewo+ID4gKwlzdHJ1Y3Qgc3Rfc2xpbV9ycHJvYyAqc2xpbV9ycHJvYyA9IHJwcm9jLT5wcml2 Owo+ID4gKwl2b2lkICp2YSA9IE5VTEw7Cj4gPiArCWludCBpOwo+ID4gKwo+ID4gKwlmb3IgKGkg PSAwOyBpIDwgU1RfU0xJTV9NRU1fTUFYOyBpKyspIHsKPiA+ICsJCWlmIChkYSAhPSBzbGltX3Jw cm9jLT5tZW1baV0uYnVzX2FkZHIpCj4gPiArCQkJY29udGludWU7Cj4gPiArCj4gPiArCQlpZiAo bGVuIDw9IHNsaW1fcnByb2MtPm1lbVtpXS5zaXplKSB7Cj4gPiArCQkJLyogX19mb3JjZSB0byBt YWtlIHNwYXJzZSBoYXBweSB3aXRoIHR5cGUgY29udmVyc2lvbiAqLwo+ID4gKwkJCXZhID0gKF9f Zm9yY2Ugdm9pZCAqKXNsaW1fcnByb2MtPm1lbVtpXS5jcHVfYWRkcjsKPiA+ICsJCQlicmVhazsK PiA+ICsJCX0KPiA+ICsJfQo+ID4gKwo+ID4gKwlkZXZfZGJnKCZycHJvYy0+ZGV2LCAiZGEgPSAw eCVsbHggbGVuID0gMHgleCB2YSA9IDB4JXBcbiIsIGRhLCBsZW4sIHZhKTsKPiA+ICsKPiA+ICsJ cmV0dXJuIHZhOwo+ID4gK30KPiA+ICsKPiA+ICtzdGF0aWMgc3RydWN0IHJwcm9jX29wcyBzbGlt X3Jwcm9jX29wcyA9IHsKPiA+ICsJLnN0YXJ0CQk9IHNsaW1fcnByb2Nfc3RhcnQsCj4gPiArCS5z dG9wCQk9IHNsaW1fcnByb2Nfc3RvcCwKPiA+ICsJLmRhX3RvX3ZhICAgICAgID0gc2xpbV9ycHJv Y19kYV90b192YSwKPiA+ICt9Owo+ID4gKwo+ID4gKy8qCj4gPiArICogRmlybXdhcmUgaGFuZGxl ciBvcGVyYXRpb25zOiBzYW5pdHksIGJvb3QgYWRkcmVzcywgbG9hZCAuLi4KPiA+ICsgKi8KPiA+ ICsKPiA+ICtzdGF0aWMgc3RydWN0IHJlc291cmNlX3RhYmxlIGVtcHR5X3JzY190YmwgPSB7Cj4g PiArCS52ZXIgPSAxLAo+ID4gKwkubnVtID0gMCwKPiA+ICt9Owo+ID4gKwo+ID4gK3N0YXRpYyBz dHJ1Y3QgcmVzb3VyY2VfdGFibGUgKnNsaW1fcnByb2NfZmluZF9yc2NfdGFibGUoc3RydWN0IHJw cm9jICpycHJvYywKPiA+ICsJCQkJCSAgICAgICBjb25zdCBzdHJ1Y3QgZmlybXdhcmUgKmZ3LAo+ ID4gKwkJCQkJICAgICAgIGludCAqdGFibGVzeikKPiA+ICt7Cj4gPiArCSp0YWJsZXN6ID0gc2l6 ZW9mKGVtcHR5X3JzY190YmwpOwo+ID4gKwlyZXR1cm4gJmVtcHR5X3JzY190Ymw7Cj4gPiArfQo+ ID4gKwo+ID4gK3N0YXRpYyBzdHJ1Y3QgcnByb2NfZndfb3BzIHNsaW1fcnByb2NfZndfb3BzID0g ewo+ID4gKwkuZmluZF9yc2NfdGFibGUgPSBzbGltX3Jwcm9jX2ZpbmRfcnNjX3RhYmxlLAo+ID4g K307Cj4gPiArCj4gPiArLyoqCj4gPiArICogc3Rfc2xpbV9ycHJvY19hbGxvYygpIC0gYWxsb2Nh dGUgYW5kIGluaXRpYWxpc2Ugc2xpbSBycHJvYwo+ID4gKyAqIEBwZGV2OiBQb2ludGVyIHRvIHRo ZSBwbGF0Zm9ybV9kZXZpY2Ugc3RydWN0Cj4gPiArICogQGZ3X25hbWU6IE5hbWUgb2YgZmlybXdh cmUgZm9yIHJwcm9jIHRvIHVzZQo+ID4gKyAqCj4gPiArICogRnVuY3Rpb24gZm9yIGFsbG9jYXRp bmcgYW5kIGluaXRpYWxpc2luZyBhIHNsaW0gcnByb2MgZm9yIHVzZSBieQo+ID4gKyAqIGRldmlj ZSBkcml2ZXJzIHdob3NlIElQIGlzIGJhc2VkIGFyb3VuZCB0aGUgU0xJTSBjb3JlLiBJdAo+ID4g KyAqIG9idGFpbnMgYW5kIGVuYWJsZXMgYW55IGNsb2NrcyByZXF1aXJlZCBieSB0aGUgU0xJTSBj b3JlIGFuZCBhbHNvCj4gPiArICogaW9yZW1hcHMgdGhlIHZhcmlvdXMgSU8uCj4gPiArICoKPiA+ ICsgKiBSZXR1cm5zIHN0X3NsaW1fcnByb2MgcG9pbnRlciBvciBQVFJfRVJSKCkgb24gZXJyb3Iu Cj4gPiArICovCj4gPiArCj4gPiArc3RydWN0IHN0X3NsaW1fcnByb2MgKnN0X3NsaW1fcnByb2Nf YWxsb2Moc3RydWN0IHBsYXRmb3JtX2RldmljZSAqcGRldiwKPiA+ICsJCQkJY2hhciAqZndfbmFt ZSkKPiA+ICt7Cj4gPiArCXN0cnVjdCBkZXZpY2UgKmRldiA9ICZwZGV2LT5kZXY7Cj4gPiArCXN0 cnVjdCBzdF9zbGltX3Jwcm9jICpzbGltX3Jwcm9jOwo+ID4gKwlzdHJ1Y3QgZGV2aWNlX25vZGUg Km5wID0gZGV2LT5vZl9ub2RlOwo+ID4gKwlzdHJ1Y3QgcnByb2MgKnJwcm9jOwo+ID4gKwlzdHJ1 Y3QgcmVzb3VyY2UgKnJlczsKPiA+ICsJaW50IGVyciwgaTsKPiA+ICsJY29uc3Qgc3RydWN0IHJw cm9jX2Z3X29wcyAqZWxmX29wczsKPiA+ICsKPiA+ICsJaWYgKCFmd19uYW1lKQo+ID4gKwkJcmV0 dXJuIEVSUl9QVFIoLUVJTlZBTCk7Cj4gPiArCj4gPiArCWlmICghb2ZfZGV2aWNlX2lzX2NvbXBh dGlibGUobnAsICJzdCxzbGltLXJwcm9jIikpCj4gPiArCQlyZXR1cm4gRVJSX1BUUigtRUlOVkFM KTsKPiA+ICsKPiA+ICsJcnByb2MgPSBycHJvY19hbGxvYyhkZXYsIG5wLT5uYW1lLCAmc2xpbV9y cHJvY19vcHMsCj4gPiArCQkJZndfbmFtZSwgc2l6ZW9mKCpzbGltX3Jwcm9jKSk7Cj4gPiArCWlm ICghcnByb2MpCj4gPiArCQlyZXR1cm4gRVJSX1BUUigtRU5PTUVNKTsKPiA+ICsKPiA+ICsJcnBy b2MtPmhhc19pb21tdSA9IGZhbHNlOwo+ID4gKwo+ID4gKwlzbGltX3Jwcm9jID0gcnByb2MtPnBy aXY7Cj4gPiArCXNsaW1fcnByb2MtPnJwcm9jID0gcnByb2M7Cj4gPiArCj4gPiArCWVsZl9vcHMg PSBycHJvYy0+Zndfb3BzOwo+ID4gKwkvKiBVc2Ugc29tZSBnZW5lcmljIGVsZiBvcHMgKi8KPiA+ ICsJc2xpbV9ycHJvY19md19vcHMubG9hZCA9IGVsZl9vcHMtPmxvYWQ7Cj4gPiArCXNsaW1fcnBy b2NfZndfb3BzLnNhbml0eV9jaGVjayA9IGVsZl9vcHMtPnNhbml0eV9jaGVjazsKPiA+ICsKPiA+ ICsJcnByb2MtPmZ3X29wcyA9ICZzbGltX3Jwcm9jX2Z3X29wczsKPiA+ICsKPiA+ICsJLyogZ2V0 IGltZW0gYW5kIGRtZW0gKi8KPiA+ICsJZm9yIChpID0gMDsgaSA8IEFSUkFZX1NJWkUobWVtX25h bWVzKTsgaSsrKSB7Cj4gPiArCQlyZXMgPSBwbGF0Zm9ybV9nZXRfcmVzb3VyY2VfYnluYW1lKHBk ZXYsIElPUkVTT1VSQ0VfTUVNLAo+ID4gKwkJCQkJCW1lbV9uYW1lc1tpXSk7Cj4gPiArCj4gPiAr CQlzbGltX3Jwcm9jLT5tZW1baV0uY3B1X2FkZHIgPSBkZXZtX2lvcmVtYXBfcmVzb3VyY2UoZGV2 LCByZXMpOwo+ID4gKwkJaWYgKElTX0VSUihzbGltX3Jwcm9jLT5tZW1baV0uY3B1X2FkZHIpKSB7 Cj4gPiArCQkJZGV2X2VycigmcGRldi0+ZGV2LCAiZGV2bV9pb3JlbWFwX3Jlc291cmNlIGZhaWxl ZFxuIik7Cj4gPiArCQkJZXJyID0gUFRSX0VSUihzbGltX3Jwcm9jLT5tZW1baV0uY3B1X2FkZHIp Owo+ID4gKwkJCWdvdG8gZXJyOwo+ID4gKwkJfQo+ID4gKwkJc2xpbV9ycHJvYy0+bWVtW2ldLmJ1 c19hZGRyID0gcmVzLT5zdGFydDsKPiA+ICsJCXNsaW1fcnByb2MtPm1lbVtpXS5zaXplID0gcmVz b3VyY2Vfc2l6ZShyZXMpOwo+ID4gKwl9Cj4gPiArCj4gPiArCXJlcyA9IHBsYXRmb3JtX2dldF9y ZXNvdXJjZV9ieW5hbWUocGRldiwgSU9SRVNPVVJDRV9NRU0sICJzbGltY29yZSIpOwo+ID4gKwlz bGltX3Jwcm9jLT5zbGltY29yZSA9IGRldm1faW9yZW1hcF9yZXNvdXJjZShkZXYsIHJlcyk7Cj4g PiArCWlmIChJU19FUlIoc2xpbV9ycHJvYy0+c2xpbWNvcmUpKSB7Cj4gPiArCQlkZXZfZXJyKCZw ZGV2LT5kZXYsICJmYWlsZWQgdG8gaW9yZW1hcCBzbGltY29yZSBJT1xuIik7Cj4gPiArCQllcnIg PSBQVFJfRVJSKHNsaW1fcnByb2MtPnNsaW1jb3JlKTsKPiA+ICsJCWdvdG8gZXJyOwo+ID4gKwl9 Cj4gPiArCj4gPiArCXJlcyA9IHBsYXRmb3JtX2dldF9yZXNvdXJjZV9ieW5hbWUocGRldiwgSU9S RVNPVVJDRV9NRU0sICJwZXJpcGhlcmFscyIpOwo+ID4gKwlzbGltX3Jwcm9jLT5wZXJpID0gZGV2 bV9pb3JlbWFwX3Jlc291cmNlKGRldiwgcmVzKTsKPiA+ICsJaWYgKElTX0VSUihzbGltX3Jwcm9j LT5wZXJpKSkgewo+ID4gKwkJZGV2X2VycigmcGRldi0+ZGV2LCAiZmFpbGVkIHRvIGlvcmVtYXAg cGVyaXBoZXJhbHMgSU9cbiIpOwo+ID4gKwkJZXJyID0gUFRSX0VSUihzbGltX3Jwcm9jLT5wZXJp KTsKPiA+ICsJCWdvdG8gZXJyOwo+ID4gKwl9Cj4gPiArCj4gPiArCWVyciA9IHNsaW1fY2xrX2dl dChzbGltX3Jwcm9jLCBkZXYpOwo+ID4gKwlpZiAoZXJyKQo+ID4gKwkJZ290byBlcnI7Cj4gPiAr Cj4gPiArCWVyciA9IHNsaW1fY2xrX2VuYWJsZShzbGltX3Jwcm9jKTsKPiA+ICsJaWYgKGVycikg ewo+ID4gKwkJZGV2X2VycihkZXYsICJGYWlsZWQgdG8gZW5hYmxlIGNsb2Nrc1xuIik7Cj4gPiAr CQlnb3RvIGVycl9jbGtfcHV0Owo+ID4gKwl9Cj4gPiArCj4gPiArCS8qIFJlZ2lzdGVyIGFzIGEg cmVtb3RlcHJvYyBkZXZpY2UgKi8KPiA+ICsJZXJyID0gcnByb2NfYWRkKHJwcm9jKTsKPiA+ICsJ aWYgKGVycikgewo+ID4gKwkJZGV2X2VycihkZXYsICJyZWdpc3RyYXRpb24gb2Ygc2xpbSByZW1v dGVwcm9jIGZhaWxlZFxuIik7Cj4gPiArCQlnb3RvIGVycl9jbGtfZGlzOwo+ID4gKwl9Cj4gPiAr Cj4gPiArCXJldHVybiBzbGltX3Jwcm9jOwo+ID4gKwo+ID4gK2Vycl9jbGtfZGlzOgo+ID4gKwlz bGltX2Nsa19kaXNhYmxlKHNsaW1fcnByb2MpOwo+ID4gK2Vycl9jbGtfcHV0Ogo+ID4gKwlmb3Ig KGkgPSAwOyBpIDwgU1RfU0xJTV9NQVhfQ0xLICYmIHNsaW1fcnByb2MtPmNsa3NbaV07IGkrKykK PiA+ICsJCWNsa19wdXQoc2xpbV9ycHJvYy0+Y2xrc1tpXSk7Cj4gPiArZXJyOgo+ID4gKwlycHJv Y19wdXQocnByb2MpOwo+ID4gKwlyZXR1cm4gRVJSX1BUUihlcnIpOwo+ID4gK30KPiA+ICtFWFBP UlRfU1lNQk9MKHN0X3NsaW1fcnByb2NfYWxsb2MpOwo+ID4gKwo+ID4gKy8qKgo+ID4gKyAgKiBz dF9zbGltX3Jwcm9jX3B1dCgpIC0gcHV0IHNsaW0gcnByb2MgcmVzb3VyY2VzCj4gPiArICAqIEBz bGltX3Jwcm9jOiBQb2ludGVyIHRvIHRoZSBzdF9zbGltX3Jwcm9jIHN0cnVjdAo+ID4gKyAgKgo+ ID4gKyAgKiBGdW5jdGlvbiBmb3IgY2FsbGluZyByZXNwZWN0aXZlIF9wdXQoKSBmdW5jdGlvbnMg b24gc2xpbV9ycHJvYyByZXNvdXJjZXMuCj4gPiArICAqCj4gPiArICAqLwo+ID4gK3ZvaWQgc3Rf c2xpbV9ycHJvY19wdXQoc3RydWN0IHN0X3NsaW1fcnByb2MgKnNsaW1fcnByb2MpCj4gPiArewo+ ID4gKwlpbnQgY2xrOwo+ID4gKwo+ID4gKwlpZiAoIXNsaW1fcnByb2MpCj4gPiArCQlyZXR1cm47 Cj4gPiArCj4gPiArCXNsaW1fY2xrX2Rpc2FibGUoc2xpbV9ycHJvYyk7Cj4gPiArCj4gPiArCWZv ciAoY2xrID0gMDsgY2xrIDwgU1RfU0xJTV9NQVhfQ0xLICYmIHNsaW1fcnByb2MtPmNsa3NbY2xr XTsgY2xrKyspCj4gPiArCQljbGtfcHV0KHNsaW1fcnByb2MtPmNsa3NbY2xrXSk7Cj4gPiArCj4g PiArCXJwcm9jX2RlbChzbGltX3Jwcm9jLT5ycHJvYyk7Cj4gPiArCXJwcm9jX3B1dChzbGltX3Jw cm9jLT5ycHJvYyk7Cj4gPiArfQo+ID4gK0VYUE9SVF9TWU1CT0woc3Rfc2xpbV9ycHJvY19wdXQp Owo+ID4gKwo+ID4gK01PRFVMRV9BVVRIT1IoIlBldGVyIEdyaWZmaW4gPHBldGVyLmdyaWZmaW5A bGluYXJvLm9yZz4iKTsKPiA+ICtNT0RVTEVfREVTQ1JJUFRJT04oIlNUTWljcm9lbGVjdHJvbmlj cyBTTElNIGNvcmUgcnByb2MgZHJpdmVyIik7Cj4gPiArTU9EVUxFX0xJQ0VOU0UoIkdQTCB2MiIp Owo+ID4gZGlmZiAtLWdpdCBhL2luY2x1ZGUvbGludXgvcmVtb3RlcHJvYy9zdF9zbGltX3Jwcm9j LmggYi9pbmNsdWRlL2xpbnV4L3JlbW90ZXByb2Mvc3Rfc2xpbV9ycHJvYy5oCj4gPiBuZXcgZmls ZSBtb2RlIDEwMDY0NAo+ID4gaW5kZXggMDAwMDAwMC4uNDE1NTU1Ngo+ID4gLS0tIC9kZXYvbnVs bAo+ID4gKysrIGIvaW5jbHVkZS9saW51eC9yZW1vdGVwcm9jL3N0X3NsaW1fcnByb2MuaAo+ID4g QEAgLTAsMCArMSw1OCBAQAo+ID4gKy8qCj4gPiArICogU0xJTSBjb3JlIHJwcm9jIGRyaXZlciBo ZWFkZXIKPiA+ICsgKgo+ID4gKyAqIENvcHlyaWdodCAoQykgMjAxNiBTVE1pY3JvZWxlY3Ryb25p Y3MKPiA+ICsgKgo+ID4gKyAqIEF1dGhvcjogUGV0ZXIgR3JpZmZpbiA8cGV0ZXIuZ3JpZmZpbkBs aW5hcm8ub3JnPgo+ID4gKyAqCj4gPiArICogVGhpcyBwcm9ncmFtIGlzIGZyZWUgc29mdHdhcmU7 IHlvdSBjYW4gcmVkaXN0cmlidXRlIGl0IGFuZC9vciBtb2RpZnkKPiA+ICsgKiBpdCB1bmRlciB0 aGUgdGVybXMgb2YgdGhlIEdOVSBHZW5lcmFsIFB1YmxpYyBMaWNlbnNlIGFzIHB1Ymxpc2hlZCBi eQo+ID4gKyAqIHRoZSBGcmVlIFNvZnR3YXJlIEZvdW5kYXRpb247IGVpdGhlciB2ZXJzaW9uIDIg b2YgdGhlIExpY2Vuc2UsIG9yCj4gPiArICogKGF0IHlvdXIgb3B0aW9uKSBhbnkgbGF0ZXIgdmVy c2lvbi4KPiA+ICsgKi8KPiA+ICsjaWZuZGVmIF9TVF9SRU1PVEVQUk9DX1NMSU1fSAo+ID4gKyNk ZWZpbmUgX1NUX1JFTU9URVBST0NfU0xJTV9ICj4gPiArCj4gPiArI2RlZmluZSBTVF9TTElNX01F TV9NQVggMgo+ID4gKyNkZWZpbmUgU1RfU0xJTV9NQVhfQ0xLIDQKPiA+ICsKPiA+ICtlbnVtIHsK PiA+ICsJU1RfU0xJTV9ETUVNLAo+ID4gKwlTVF9TTElNX0lNRU0sCj4gPiArfTsKPiA+ICsKPiA+ ICsvKioKPiA+ICsgKiBzdHJ1Y3Qgc3Rfc2xpbV9tZW0gLSBzbGltIGludGVybmFsIG1lbW9yeSBz dHJ1Y3R1cmUKPiA+ICsgKiBAY3B1X2FkZHI6IE1QVSB2aXJ0dWFsIGFkZHJlc3Mgb2YgdGhlIG1l bW9yeSByZWdpb24KPiA+ICsgKiBAYnVzX2FkZHI6IEJ1cyBhZGRyZXNzIHVzZWQgdG8gYWNjZXNz IHRoZSBtZW1vcnkgcmVnaW9uCj4gPiArICogQHNpemU6IFNpemUgb2YgdGhlIG1lbW9yeSByZWdp b24KPiA+ICsgKi8KPiA+ICtzdHJ1Y3Qgc3Rfc2xpbV9tZW0gewo+ID4gKwl2b2lkIF9faW9tZW0g KmNwdV9hZGRyOwo+ID4gKwlwaHlzX2FkZHJfdCBidXNfYWRkcjsKPiA+ICsJc2l6ZV90IHNpemU7 Cj4gPiArfTsKPiA+ICsKPiA+ICsvKioKPiA+ICsgKiBzdHJ1Y3Qgc3Rfc2xpbV9ycHJvYyAtIFNM SU0gc2xpbSBjb3JlCj4gPiArICogQHJwcm9jOiBycHJvYyBoYW5kbGUKPiA+ICsgKiBAbWVtOiBz bGltIG1lbW9yeSBpbmZvcm1hdGlvbgo+ID4gKyAqIEBzbGltY29yZTogc2xpbSBzbGltY29yZSBy ZWdzCj4gPiArICogQHBlcmk6IHNsaW0gcGVyaXBoZXJhbCByZWdzCj4gPiArICogQGNsa3M6IHNs aW0gY2xvY2tzCj4gPiArICovCj4gPiArc3RydWN0IHN0X3NsaW1fcnByb2Mgewo+ID4gKwlzdHJ1 Y3QgcnByb2MgKnJwcm9jOwo+ID4gKwlzdHJ1Y3Qgc3Rfc2xpbV9tZW0gbWVtW1NUX1NMSU1fTUVN X01BWF07Cj4gPiArCXZvaWQgX19pb21lbSAqc2xpbWNvcmU7Cj4gPiArCXZvaWQgX19pb21lbSAq cGVyaTsKPiA+ICsKPiA+ICsJLyogc3Rfc2xpbV9ycHJvYyBwcml2YXRlICovCj4gPiArCXN0cnVj dCBjbGsgKmNsa3NbU1RfU0xJTV9NQVhfQ0xLXTsKPiA+ICt9Owo+ID4gKwo+ID4gK3N0cnVjdCBz dF9zbGltX3Jwcm9jICpzdF9zbGltX3Jwcm9jX2FsbG9jKHN0cnVjdCBwbGF0Zm9ybV9kZXZpY2Ug KnBkZXYsCj4gPiArCQkJCQljaGFyICpmd19uYW1lKTsKPiA+ICt2b2lkIHN0X3NsaW1fcnByb2Nf cHV0KHN0cnVjdCBzdF9zbGltX3Jwcm9jICpzbGltX3Jwcm9jKTsKPiA+ICsKPiA+ICsjZW5kaWYK Ci0tIApMZWUgSm9uZXMKTGluYXJvIFNUTWljcm9lbGVjdHJvbmljcyBMYW5kaW5nIFRlYW0gTGVh ZApMaW5hcm8ub3JnIOKUgiBPcGVuIHNvdXJjZSBzb2Z0d2FyZSBmb3IgQVJNIFNvQ3MKRm9sbG93 IExpbmFybzogRmFjZWJvb2sgfCBUd2l0dGVyIHwgQmxvZwpfX19fX19fX19fX19fX19fX19fX19f X19fX19fX19fX19fX19fX19fX19fX19fXwpkcmktZGV2ZWwgbWFpbGluZyBsaXN0CmRyaS1kZXZl bEBsaXN0cy5mcmVlZGVza3RvcC5vcmcKaHR0cHM6Ly9saXN0cy5mcmVlZGVza3RvcC5vcmcvbWFp bG1hbi9saXN0aW5mby9kcmktZGV2ZWwK From mboxrd@z Thu Jan 1 00:00:00 1970 From: lee.jones@linaro.org (Lee Jones) Date: Wed, 14 Sep 2016 09:30:52 +0100 Subject: [PATCH v9 01/19] remoteproc: st_slim_rproc: add a slimcore rproc driver In-Reply-To: <20160913175656.GC21438@tuxbot> References: <1473081421-16555-1-git-send-email-peter.griffin@linaro.org> <1473081421-16555-2-git-send-email-peter.griffin@linaro.org> <20160913175656.GC21438@tuxbot> Message-ID: <20160914083052.GA638@dell> To: linux-arm-kernel@lists.infradead.org List-Id: linux-arm-kernel.lists.infradead.org On Tue, 13 Sep 2016, Bjorn Andersson wrote: > On Mon 05 Sep 06:16 PDT 2016, Peter Griffin wrote: > > > slim core is used as a basis for many IPs in the STi > > chipsets such as fdma and demux. To avoid duplicating > > the elf loading code in each device driver a slim > > rproc driver has been created. > > > > This driver is designed to be used by other device drivers > > such as fdma, or demux whose IP is based around a slim core. > > The device driver can call slim_rproc_alloc() to allocate > > a slim rproc and slim_rproc_put() when finished. > > > > This driver takes care of ioremapping the slim > > registers (dmem, imem, slimcore, peripherals), whose offsets > > and sizes can change between IP's. It also obtains and enables > > any clocks used by the device. This approach avoids having > > a double mapping of the registers as slim_rproc does not register > > its own platform device. It also maps well to device tree > > abstraction as it allows us to have one dt node for the whole > > device. > > > > All of the generic rproc elf loading code can be reused, and > > we provide start() stop() hooks to start and stop the slim > > core once the firmware has been loaded. This has been tested > > successfully with fdma driver. > > > > Signed-off-by: Peter Griffin > > Acked-by: Bjorn Andersson What's preventing this from being applied right away? > > --- > > drivers/remoteproc/Kconfig | 4 + > > drivers/remoteproc/Makefile | 1 + > > drivers/remoteproc/st_slim_rproc.c | 364 +++++++++++++++++++++++++++++++ > > include/linux/remoteproc/st_slim_rproc.h | 58 +++++ > > 4 files changed, 427 insertions(+) > > create mode 100644 drivers/remoteproc/st_slim_rproc.c > > create mode 100644 include/linux/remoteproc/st_slim_rproc.h > > > > diff --git a/drivers/remoteproc/Kconfig b/drivers/remoteproc/Kconfig > > index 1a8bf76a..a7bedc6 100644 > > --- a/drivers/remoteproc/Kconfig > > +++ b/drivers/remoteproc/Kconfig > > @@ -100,4 +100,8 @@ config ST_REMOTEPROC > > processor framework. > > This can be either built-in or a loadable module. > > > > +config ST_SLIM_REMOTEPROC > > + tristate > > + select REMOTEPROC > > + > > endmenu > > diff --git a/drivers/remoteproc/Makefile b/drivers/remoteproc/Makefile > > index 92d3758..db1dae7 100644 > > --- a/drivers/remoteproc/Makefile > > +++ b/drivers/remoteproc/Makefile > > @@ -14,3 +14,4 @@ obj-$(CONFIG_DA8XX_REMOTEPROC) += da8xx_remoteproc.o > > obj-$(CONFIG_QCOM_MDT_LOADER) += qcom_mdt_loader.o > > obj-$(CONFIG_QCOM_Q6V5_PIL) += qcom_q6v5_pil.o > > obj-$(CONFIG_ST_REMOTEPROC) += st_remoteproc.o > > +obj-$(CONFIG_ST_SLIM_REMOTEPROC) += st_slim_rproc.o > > diff --git a/drivers/remoteproc/st_slim_rproc.c b/drivers/remoteproc/st_slim_rproc.c > > new file mode 100644 > > index 0000000..1484e97 > > --- /dev/null > > +++ b/drivers/remoteproc/st_slim_rproc.c > > @@ -0,0 +1,364 @@ > > +/* > > + * SLIM core rproc driver > > + * > > + * Copyright (C) 2016 STMicroelectronics > > + * > > + * Author: Peter Griffin > > + * > > + * This program is free software; you can redistribute it and/or modify > > + * it under the terms of the GNU General Public License as published by > > + * the Free Software Foundation; either version 2 of the License, or > > + * (at your option) any later version. > > + */ > > + > > +#include > > +#include > > +#include > > +#include > > +#include > > +#include > > +#include > > +#include > > +#include > > +#include "remoteproc_internal.h" > > + > > +/* SLIM core registers */ > > +#define SLIM_ID_OFST 0x0 > > +#define SLIM_VER_OFST 0x4 > > + > > +#define SLIM_EN_OFST 0x8 > > +#define SLIM_EN_RUN BIT(0) > > + > > +#define SLIM_CLK_GATE_OFST 0xC > > +#define SLIM_CLK_GATE_DIS BIT(0) > > +#define SLIM_CLK_GATE_RESET BIT(2) > > + > > +#define SLIM_SLIM_PC_OFST 0x20 > > + > > +/* DMEM registers */ > > +#define SLIM_REV_ID_OFST 0x0 > > +#define SLIM_REV_ID_MIN_MASK GENMASK(15, 8) > > +#define SLIM_REV_ID_MIN(id) ((id & SLIM_REV_ID_MIN_MASK) >> 8) > > +#define SLIM_REV_ID_MAJ_MASK GENMASK(23, 16) > > +#define SLIM_REV_ID_MAJ(id) ((id & SLIM_REV_ID_MAJ_MASK) >> 16) > > + > > + > > +/* peripherals registers */ > > +#define SLIM_STBUS_SYNC_OFST 0xF88 > > +#define SLIM_STBUS_SYNC_DIS BIT(0) > > + > > +#define SLIM_INT_SET_OFST 0xFD4 > > +#define SLIM_INT_CLR_OFST 0xFD8 > > +#define SLIM_INT_MASK_OFST 0xFDC > > + > > +#define SLIM_CMD_CLR_OFST 0xFC8 > > +#define SLIM_CMD_MASK_OFST 0xFCC > > + > > +static const char *mem_names[ST_SLIM_MEM_MAX] = { > > + [ST_SLIM_DMEM] = "dmem", > > + [ST_SLIM_IMEM] = "imem", > > +}; > > + > > +static int slim_clk_get(struct st_slim_rproc *slim_rproc, struct device *dev) > > +{ > > + int clk, err; > > + > > + for (clk = 0; clk < ST_SLIM_MAX_CLK; clk++) { > > + slim_rproc->clks[clk] = of_clk_get(dev->of_node, clk); > > + if (IS_ERR(slim_rproc->clks[clk])) { > > + err = PTR_ERR(slim_rproc->clks[clk]); > > + if (err == -EPROBE_DEFER) > > + goto err_put_clks; > > + slim_rproc->clks[clk] = NULL; > > + break; > > + } > > + } > > + > > + return 0; > > + > > +err_put_clks: > > + while (--clk >= 0) > > + clk_put(slim_rproc->clks[clk]); > > + > > + return err; > > +} > > + > > +static void slim_clk_disable(struct st_slim_rproc *slim_rproc) > > +{ > > + int clk; > > + > > + for (clk = 0; clk < ST_SLIM_MAX_CLK && slim_rproc->clks[clk]; clk++) > > + clk_disable_unprepare(slim_rproc->clks[clk]); > > +} > > + > > +static int slim_clk_enable(struct st_slim_rproc *slim_rproc) > > +{ > > + int clk, ret; > > + > > + for (clk = 0; clk < ST_SLIM_MAX_CLK && slim_rproc->clks[clk]; clk++) { > > + ret = clk_prepare_enable(slim_rproc->clks[clk]); > > + if (ret) > > + goto err_disable_clks; > > + } > > + > > + return 0; > > + > > +err_disable_clks: > > + while (--clk >= 0) > > + clk_disable_unprepare(slim_rproc->clks[clk]); > > + > > + return ret; > > +} > > + > > +/* > > + * Remoteproc slim specific device handlers > > + */ > > +static int slim_rproc_start(struct rproc *rproc) > > +{ > > + struct device *dev = &rproc->dev; > > + struct st_slim_rproc *slim_rproc = rproc->priv; > > + unsigned long hw_id, hw_ver, fw_rev; > > + u32 val; > > + > > + /* disable CPU pipeline clock & reset CPU pipeline */ > > + val = SLIM_CLK_GATE_DIS | SLIM_CLK_GATE_RESET; > > + writel(val, slim_rproc->slimcore + SLIM_CLK_GATE_OFST); > > + > > + /* disable SLIM core STBus sync */ > > + writel(SLIM_STBUS_SYNC_DIS, slim_rproc->peri + SLIM_STBUS_SYNC_OFST); > > + > > + /* enable cpu pipeline clock */ > > + writel(!SLIM_CLK_GATE_DIS, > > + slim_rproc->slimcore + SLIM_CLK_GATE_OFST); > > + > > + /* clear int & cmd mailbox */ > > + writel(~0U, slim_rproc->peri + SLIM_INT_CLR_OFST); > > + writel(~0U, slim_rproc->peri + SLIM_CMD_CLR_OFST); > > + > > + /* enable all channels cmd & int */ > > + writel(~0U, slim_rproc->peri + SLIM_INT_MASK_OFST); > > + writel(~0U, slim_rproc->peri + SLIM_CMD_MASK_OFST); > > + > > + /* enable cpu */ > > + writel(SLIM_EN_RUN, slim_rproc->slimcore + SLIM_EN_OFST); > > + > > + hw_id = readl_relaxed(slim_rproc->slimcore + SLIM_ID_OFST); > > + hw_ver = readl_relaxed(slim_rproc->slimcore + SLIM_VER_OFST); > > + > > + fw_rev = readl(slim_rproc->mem[ST_SLIM_DMEM].cpu_addr + > > + SLIM_REV_ID_OFST); > > + > > + dev_info(dev, "fw rev:%ld.%ld on SLIM %ld.%ld\n", > > + SLIM_REV_ID_MAJ(fw_rev), SLIM_REV_ID_MIN(fw_rev), > > + hw_id, hw_ver); > > + > > + return 0; > > +} > > + > > +static int slim_rproc_stop(struct rproc *rproc) > > +{ > > + struct st_slim_rproc *slim_rproc = rproc->priv; > > + u32 val; > > + > > + /* mask all (cmd & int) channels */ > > + writel(0UL, slim_rproc->peri + SLIM_INT_MASK_OFST); > > + writel(0UL, slim_rproc->peri + SLIM_CMD_MASK_OFST); > > + > > + /* disable cpu pipeline clock */ > > + writel(SLIM_CLK_GATE_DIS, slim_rproc->slimcore + SLIM_CLK_GATE_OFST); > > + > > + writel(!SLIM_EN_RUN, slim_rproc->slimcore + SLIM_EN_OFST); > > + > > + val = readl(slim_rproc->slimcore + SLIM_EN_OFST); > > + if (val & SLIM_EN_RUN) > > + dev_warn(&rproc->dev, "Failed to disable SLIM"); > > + > > + dev_dbg(&rproc->dev, "slim stopped\n"); > > + > > + return 0; > > +} > > + > > +static void *slim_rproc_da_to_va(struct rproc *rproc, u64 da, int len) > > +{ > > + struct st_slim_rproc *slim_rproc = rproc->priv; > > + void *va = NULL; > > + int i; > > + > > + for (i = 0; i < ST_SLIM_MEM_MAX; i++) { > > + if (da != slim_rproc->mem[i].bus_addr) > > + continue; > > + > > + if (len <= slim_rproc->mem[i].size) { > > + /* __force to make sparse happy with type conversion */ > > + va = (__force void *)slim_rproc->mem[i].cpu_addr; > > + break; > > + } > > + } > > + > > + dev_dbg(&rproc->dev, "da = 0x%llx len = 0x%x va = 0x%p\n", da, len, va); > > + > > + return va; > > +} > > + > > +static struct rproc_ops slim_rproc_ops = { > > + .start = slim_rproc_start, > > + .stop = slim_rproc_stop, > > + .da_to_va = slim_rproc_da_to_va, > > +}; > > + > > +/* > > + * Firmware handler operations: sanity, boot address, load ... > > + */ > > + > > +static struct resource_table empty_rsc_tbl = { > > + .ver = 1, > > + .num = 0, > > +}; > > + > > +static struct resource_table *slim_rproc_find_rsc_table(struct rproc *rproc, > > + const struct firmware *fw, > > + int *tablesz) > > +{ > > + *tablesz = sizeof(empty_rsc_tbl); > > + return &empty_rsc_tbl; > > +} > > + > > +static struct rproc_fw_ops slim_rproc_fw_ops = { > > + .find_rsc_table = slim_rproc_find_rsc_table, > > +}; > > + > > +/** > > + * st_slim_rproc_alloc() - allocate and initialise slim rproc > > + * @pdev: Pointer to the platform_device struct > > + * @fw_name: Name of firmware for rproc to use > > + * > > + * Function for allocating and initialising a slim rproc for use by > > + * device drivers whose IP is based around the SLIM core. It > > + * obtains and enables any clocks required by the SLIM core and also > > + * ioremaps the various IO. > > + * > > + * Returns st_slim_rproc pointer or PTR_ERR() on error. > > + */ > > + > > +struct st_slim_rproc *st_slim_rproc_alloc(struct platform_device *pdev, > > + char *fw_name) > > +{ > > + struct device *dev = &pdev->dev; > > + struct st_slim_rproc *slim_rproc; > > + struct device_node *np = dev->of_node; > > + struct rproc *rproc; > > + struct resource *res; > > + int err, i; > > + const struct rproc_fw_ops *elf_ops; > > + > > + if (!fw_name) > > + return ERR_PTR(-EINVAL); > > + > > + if (!of_device_is_compatible(np, "st,slim-rproc")) > > + return ERR_PTR(-EINVAL); > > + > > + rproc = rproc_alloc(dev, np->name, &slim_rproc_ops, > > + fw_name, sizeof(*slim_rproc)); > > + if (!rproc) > > + return ERR_PTR(-ENOMEM); > > + > > + rproc->has_iommu = false; > > + > > + slim_rproc = rproc->priv; > > + slim_rproc->rproc = rproc; > > + > > + elf_ops = rproc->fw_ops; > > + /* Use some generic elf ops */ > > + slim_rproc_fw_ops.load = elf_ops->load; > > + slim_rproc_fw_ops.sanity_check = elf_ops->sanity_check; > > + > > + rproc->fw_ops = &slim_rproc_fw_ops; > > + > > + /* get imem and dmem */ > > + for (i = 0; i < ARRAY_SIZE(mem_names); i++) { > > + res = platform_get_resource_byname(pdev, IORESOURCE_MEM, > > + mem_names[i]); > > + > > + slim_rproc->mem[i].cpu_addr = devm_ioremap_resource(dev, res); > > + if (IS_ERR(slim_rproc->mem[i].cpu_addr)) { > > + dev_err(&pdev->dev, "devm_ioremap_resource failed\n"); > > + err = PTR_ERR(slim_rproc->mem[i].cpu_addr); > > + goto err; > > + } > > + slim_rproc->mem[i].bus_addr = res->start; > > + slim_rproc->mem[i].size = resource_size(res); > > + } > > + > > + res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "slimcore"); > > + slim_rproc->slimcore = devm_ioremap_resource(dev, res); > > + if (IS_ERR(slim_rproc->slimcore)) { > > + dev_err(&pdev->dev, "failed to ioremap slimcore IO\n"); > > + err = PTR_ERR(slim_rproc->slimcore); > > + goto err; > > + } > > + > > + res = platform_get_resource_byname(pdev, IORESOURCE_MEM, "peripherals"); > > + slim_rproc->peri = devm_ioremap_resource(dev, res); > > + if (IS_ERR(slim_rproc->peri)) { > > + dev_err(&pdev->dev, "failed to ioremap peripherals IO\n"); > > + err = PTR_ERR(slim_rproc->peri); > > + goto err; > > + } > > + > > + err = slim_clk_get(slim_rproc, dev); > > + if (err) > > + goto err; > > + > > + err = slim_clk_enable(slim_rproc); > > + if (err) { > > + dev_err(dev, "Failed to enable clocks\n"); > > + goto err_clk_put; > > + } > > + > > + /* Register as a remoteproc device */ > > + err = rproc_add(rproc); > > + if (err) { > > + dev_err(dev, "registration of slim remoteproc failed\n"); > > + goto err_clk_dis; > > + } > > + > > + return slim_rproc; > > + > > +err_clk_dis: > > + slim_clk_disable(slim_rproc); > > +err_clk_put: > > + for (i = 0; i < ST_SLIM_MAX_CLK && slim_rproc->clks[i]; i++) > > + clk_put(slim_rproc->clks[i]); > > +err: > > + rproc_put(rproc); > > + return ERR_PTR(err); > > +} > > +EXPORT_SYMBOL(st_slim_rproc_alloc); > > + > > +/** > > + * st_slim_rproc_put() - put slim rproc resources > > + * @slim_rproc: Pointer to the st_slim_rproc struct > > + * > > + * Function for calling respective _put() functions on slim_rproc resources. > > + * > > + */ > > +void st_slim_rproc_put(struct st_slim_rproc *slim_rproc) > > +{ > > + int clk; > > + > > + if (!slim_rproc) > > + return; > > + > > + slim_clk_disable(slim_rproc); > > + > > + for (clk = 0; clk < ST_SLIM_MAX_CLK && slim_rproc->clks[clk]; clk++) > > + clk_put(slim_rproc->clks[clk]); > > + > > + rproc_del(slim_rproc->rproc); > > + rproc_put(slim_rproc->rproc); > > +} > > +EXPORT_SYMBOL(st_slim_rproc_put); > > + > > +MODULE_AUTHOR("Peter Griffin "); > > +MODULE_DESCRIPTION("STMicroelectronics SLIM core rproc driver"); > > +MODULE_LICENSE("GPL v2"); > > diff --git a/include/linux/remoteproc/st_slim_rproc.h b/include/linux/remoteproc/st_slim_rproc.h > > new file mode 100644 > > index 0000000..4155556 > > --- /dev/null > > +++ b/include/linux/remoteproc/st_slim_rproc.h > > @@ -0,0 +1,58 @@ > > +/* > > + * SLIM core rproc driver header > > + * > > + * Copyright (C) 2016 STMicroelectronics > > + * > > + * Author: Peter Griffin > > + * > > + * This program is free software; you can redistribute it and/or modify > > + * it under the terms of the GNU General Public License as published by > > + * the Free Software Foundation; either version 2 of the License, or > > + * (at your option) any later version. > > + */ > > +#ifndef _ST_REMOTEPROC_SLIM_H > > +#define _ST_REMOTEPROC_SLIM_H > > + > > +#define ST_SLIM_MEM_MAX 2 > > +#define ST_SLIM_MAX_CLK 4 > > + > > +enum { > > + ST_SLIM_DMEM, > > + ST_SLIM_IMEM, > > +}; > > + > > +/** > > + * struct st_slim_mem - slim internal memory structure > > + * @cpu_addr: MPU virtual address of the memory region > > + * @bus_addr: Bus address used to access the memory region > > + * @size: Size of the memory region > > + */ > > +struct st_slim_mem { > > + void __iomem *cpu_addr; > > + phys_addr_t bus_addr; > > + size_t size; > > +}; > > + > > +/** > > + * struct st_slim_rproc - SLIM slim core > > + * @rproc: rproc handle > > + * @mem: slim memory information > > + * @slimcore: slim slimcore regs > > + * @peri: slim peripheral regs > > + * @clks: slim clocks > > + */ > > +struct st_slim_rproc { > > + struct rproc *rproc; > > + struct st_slim_mem mem[ST_SLIM_MEM_MAX]; > > + void __iomem *slimcore; > > + void __iomem *peri; > > + > > + /* st_slim_rproc private */ > > + struct clk *clks[ST_SLIM_MAX_CLK]; > > +}; > > + > > +struct st_slim_rproc *st_slim_rproc_alloc(struct platform_device *pdev, > > + char *fw_name); > > +void st_slim_rproc_put(struct st_slim_rproc *slim_rproc); > > + > > +#endif -- Lee Jones Linaro STMicroelectronics Landing Team Lead Linaro.org ? Open source software for ARM SoCs Follow Linaro: Facebook | Twitter | Blog