From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from vger.kernel.org (vger.kernel.org [23.128.96.18]) by smtp.lore.kernel.org (Postfix) with ESMTP id D26D4C43334 for ; Mon, 18 Jul 2022 14:18:39 +0000 (UTC) Received: (majordomo@vger.kernel.org) by vger.kernel.org via listexpand id S233786AbiGROSj (ORCPT ); Mon, 18 Jul 2022 10:18:39 -0400 Received: from lindbergh.monkeyblade.net ([23.128.96.19]:46136 "EHLO lindbergh.monkeyblade.net" rhost-flags-OK-OK-OK-OK) by vger.kernel.org with ESMTP id S232250AbiGROSh (ORCPT ); Mon, 18 Jul 2022 10:18:37 -0400 Received: from mail-wr1-x435.google.com (mail-wr1-x435.google.com [IPv6:2a00:1450:4864:20::435]) by lindbergh.monkeyblade.net (Postfix) with ESMTPS id 40FB9DF2E for ; Mon, 18 Jul 2022 07:18:33 -0700 (PDT) Received: by mail-wr1-x435.google.com with SMTP id b26so17285198wrc.2 for ; Mon, 18 Jul 2022 07:18:33 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=date:from:to:cc:subject:message-id:references:mime-version :content-disposition:content-transfer-encoding:in-reply-to; bh=gLq0d/jV4o9aB9pU8p7hMA+66qSzv4eqlhhhHzAYRmw=; b=vEyDTieprd8sNYmuqnTOrargXydmC0ROgW8hxZ+TmQo8DTdxtWB2rU9xtKbwV8Io7Y NeSu3Z0Fcrwed5eQrOt7TevAPh4s6pboEcyIDANa0saXRTCSTib0SHWpA8W/+A9yP+6k d8WQULhyBS8JPUeIxdXsplv/iMA6q4QcNZSKR1aX5hD02/JFl9efIgZwo04d6A/V+T4H C3gR3a3z8Tz6+BFPHDiVvfGysxJCF+Fngd888vVyTgD1sGrqn+E6w2ivqve99Tz0+lDa vOkfc6CuS6TIoIfb+YsotGZtPNO/Cj/yF/vzTcCbWaPODbXXsPaIFLhp9d1UgkJhsYiJ Qc/A== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=x-gm-message-state:date:from:to:cc:subject:message-id:references :mime-version:content-disposition:content-transfer-encoding :in-reply-to; bh=gLq0d/jV4o9aB9pU8p7hMA+66qSzv4eqlhhhHzAYRmw=; b=yNWaGRLKJd9ejgjHBvhNUI/vpFyPx8EOMqiv3nW6QvNFcuEc/JL6czsHHCZGwSJwXo E0+rBT6cjuCJqIlO2bwVztyM8JGq21Hmjtz7v0zyF0ic8dCsVrvuHzIxaxt+XSaOioDW ibc+qYNtamBeNkvEemUz+F+1kgof1Fwo0nxcydBgUyXJFt+mGoGYcHnFrXsc41vdjFwZ ECaguX6xa2sVxslfHmHEOjwJ7LrL4B5a1WaODGn3B+CWLiShGdmjPTbGqoeItkPNPfuG jsm9qkXST5NvRbn/ajUoWkRUAML/V/FLehWbL+utRKjslG+hHBxhCQj828OqDnBGzLHK j0aQ== X-Gm-Message-State: AJIora/IVjg+pt7EoYONVPaDNI6ZuzCUfdB6SNmfgSH1XYkWem5wtau4 lQFh5Ym9M6IRptP49fNa0ohFjA== X-Google-Smtp-Source: AGRyM1sAwosNw1DqpvsNcl7J11odJWZRQhS7HKRREBfavJFYLY9GKFX6JmjDGvjCkVb1BdRf62c3WQ== X-Received: by 2002:a5d:64a4:0:b0:21d:be80:de06 with SMTP id m4-20020a5d64a4000000b0021dbe80de06mr20460241wrp.107.1658153911461; Mon, 18 Jul 2022 07:18:31 -0700 (PDT) Received: from google.com (cpc155339-bagu17-2-0-cust87.1-3.cable.virginm.net. [86.27.177.88]) by smtp.gmail.com with ESMTPSA id c6-20020a7bc006000000b003a02f957245sm18759407wmb.26.2022.07.18.07.18.30 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Mon, 18 Jul 2022 07:18:31 -0700 (PDT) Date: Mon, 18 Jul 2022 15:18:28 +0100 From: Lee Jones To: Colin Foster Cc: devicetree@vger.kernel.org, linux-kernel@vger.kernel.org, netdev@vger.kernel.org, linux-arm-kernel@lists.infradead.org, linux-gpio@vger.kernel.org, Vladimir Oltean , Rob Herring , Krzysztof Kozlowski , Andrew Lunn , Heiner Kallweit , Russell King , "David S. Miller" , Eric Dumazet , Jakub Kicinski , Paolo Abeni , Lars Povlsen , Steen Hegelund , UNGLinuxDriver@microchip.com, Linus Walleij , Wolfram Sang , Terry Bowman , Andy Shevchenko , katie.morris@in-advantage.com Subject: Re: [PATCH v13 net-next 9/9] mfd: ocelot: add support for the vsc7512 chip via spi Message-ID: References: <20220705204743.3224692-1-colin.foster@in-advantage.com> <20220705204743.3224692-10-colin.foster@in-advantage.com> MIME-Version: 1.0 Content-Type: text/plain; charset=utf-8 Content-Disposition: inline Content-Transfer-Encoding: 8bit In-Reply-To: <20220705204743.3224692-10-colin.foster@in-advantage.com> Precedence: bulk List-ID: X-Mailing-List: linux-gpio@vger.kernel.org On Tue, 05 Jul 2022, Colin Foster wrote: > The VSC7512 is a networking chip that contains several peripherals. Many of > these peripherals are currently supported by the VSC7513 and VSC7514 chips, > but those run on an internal CPU. The VSC7512 lacks this CPU, and must be > controlled externally. > > Utilize the existing drivers by referencing the chip as an MFD. Add support > for the two MDIO buses, the internal phys, pinctrl, and serial GPIO. > > Signed-off-by: Colin Foster > --- > MAINTAINERS | 1 + > drivers/mfd/Kconfig | 21 +++ > drivers/mfd/Makefile | 3 + > drivers/mfd/ocelot-core.c | 169 ++++++++++++++++++++ > drivers/mfd/ocelot-spi.c | 317 ++++++++++++++++++++++++++++++++++++++ > drivers/mfd/ocelot.h | 34 ++++ > 6 files changed, 545 insertions(+) > create mode 100644 drivers/mfd/ocelot-core.c > create mode 100644 drivers/mfd/ocelot-spi.c > create mode 100644 drivers/mfd/ocelot.h Generally this is looking much better. Almost ready for inclusion with just a few nits. > diff --git a/MAINTAINERS b/MAINTAINERS > index 5e798c42fa08..e3299677cd4a 100644 > --- a/MAINTAINERS > +++ b/MAINTAINERS > @@ -14471,6 +14471,7 @@ OCELOT EXTERNAL SWITCH CONTROL > M: Colin Foster > S: Supported > F: Documentation/devicetree/bindings/mfd/mscc,ocelot.yaml > +F: drivers/mfd/ocelot* > F: include/linux/mfd/ocelot.h > > OCXL (Open Coherent Accelerator Processor Interface OpenCAPI) DRIVER > diff --git a/drivers/mfd/Kconfig b/drivers/mfd/Kconfig > index 3b59456f5545..0ef433d170dc 100644 > --- a/drivers/mfd/Kconfig > +++ b/drivers/mfd/Kconfig > @@ -962,6 +962,27 @@ config MFD_MENF21BMC > This driver can also be built as a module. If so the module > will be called menf21bmc. > > +config MFD_OCELOT > + tristate "Microsemi Ocelot External Control Support" > + depends on SPI_MASTER > + select MFD_CORE > + select REGMAP_SPI > + help > + Ocelot is a family of networking chips that support multiple ethernet > + and fibre interfaces. In addition to networking, they contain several > + other functions, including pinctrl, MDIO, and communication with > + external chips. While some chips have an internal processor capable of > + running an OS, others don't. All chips can be controlled externally > + through different interfaces, including SPI, I2C, and PCIe. > + > + Say yes here to add support for Ocelot chips (VSC7511, VSC7512, > + VSC7513, VSC7514) controlled externally. > + > + To compile this driver as a module, choose M here: the module will be > + called ocelot-soc. > + > + If unsure, say N. > + > config EZX_PCAP > bool "Motorola EZXPCAP Support" > depends on SPI_MASTER > diff --git a/drivers/mfd/Makefile b/drivers/mfd/Makefile > index 858cacf659d6..0004b7e86220 100644 > --- a/drivers/mfd/Makefile > +++ b/drivers/mfd/Makefile > @@ -120,6 +120,9 @@ obj-$(CONFIG_MFD_MC13XXX_I2C) += mc13xxx-i2c.o > > obj-$(CONFIG_MFD_CORE) += mfd-core.o > > +ocelot-soc-objs := ocelot-core.o ocelot-spi.o > +obj-$(CONFIG_MFD_OCELOT) += ocelot-soc.o > + > obj-$(CONFIG_EZX_PCAP) += ezx-pcap.o > obj-$(CONFIG_MFD_CPCAP) += motorola-cpcap.o > > diff --git a/drivers/mfd/ocelot-core.c b/drivers/mfd/ocelot-core.c > new file mode 100644 > index 000000000000..e07cd901e1b3 > --- /dev/null > +++ b/drivers/mfd/ocelot-core.c > @@ -0,0 +1,169 @@ > +// SPDX-License-Identifier: (GPL-2.0 OR MIT) > +/* > + * Core driver for the Ocelot chip family. > + * > + * The VSC7511, 7512, 7513, and 7514 can be controlled internally via an > + * on-chip MIPS processor, or externally via SPI, I2C, PCIe. This core driver is > + * intended to be the bus-agnostic glue between, for example, the SPI bus and > + * the child devices. > + * > + * Copyright 2021, 2022 Innovative Advantage Inc. Range? > + * Author: Colin Foster > + */ > + > +#include > +#include > +#include > +#include > +#include > +#include > + > +#include > + > +#include "ocelot.h" > + > +#define REG_GCB_SOFT_RST 0x0008 > + > +#define BIT_SOFT_CHIP_RST BIT(0) > + > +#define VSC7512_MIIM0_RES_START 0x7107009c > +#define VSC7512_MIIM0_RES_SIZE 0x24 > + > +#define VSC7512_MIIM1_RES_START 0x710700c0 > +#define VSC7512_MIIM1_RES_SIZE 0x24 Maybe: #define VSC7512_MIIM0_RES_START 0x7107009c #define VSC7512_MIIM1_RES_START 0x710700c0 #define VSC7512_MIIM_RES_SIZE 0x24 No strong feelings about this though, just saves a line or two. > +#define VSC7512_PHY_RES_START 0x710700f0 > +#define VSC7512_PHY_RES_SIZE 0x4 > + > +#define VSC7512_GPIO_RES_START 0x71070034 > +#define VSC7512_GPIO_RES_SIZE 0x6c > + > +#define VSC7512_SIO_CTRL_RES_START 0x710700f8 > +#define VSC7512_SIO_CTRL_RES_SIZE 0x100 > + > +#define VSC7512_GCB_RST_SLEEP_US 100 > +#define VSC7512_GCB_RST_TIMEOUT_US 100000 > + > +static int ocelot_gcb_chip_rst_status(struct ocelot_ddata *ddata) > +{ > + int val, err; > + > + err = regmap_read(ddata->gcb_regmap, REG_GCB_SOFT_RST, &val); > + if (err) > + val = err; I think just returning err is clearer. > + return val; > +} > + > +int ocelot_chip_reset(struct device *dev) > +{ > + struct ocelot_ddata *ddata = dev_get_drvdata(dev); > + int ret, val; > + > + /* > + * Reset the entire chip here to put it into a completely known state. > + * Other drivers may want to reset their own subsystems. The register > + * self-clears, so one write is all that is needed and wait for it to > + * clear. > + */ > + ret = regmap_write(ddata->gcb_regmap, REG_GCB_SOFT_RST, > + BIT_SOFT_CHIP_RST); Lots of these line-breaks can be removed which will tidy-up the file quite a bit. The new max is 100 chars. So long as checkpatch.pl doesn't complain, I'm happy. > + if (ret) > + return ret; > + > + ret = readx_poll_timeout(ocelot_gcb_chip_rst_status, ddata, val, !val, > + VSC7512_GCB_RST_SLEEP_US, > + VSC7512_GCB_RST_TIMEOUT_US); > + if (ret) > + return dev_err_probe(ddata->dev, ret, "timeout: chip reset\n"); *This* function is not probe. Also the last failure will produce 2 prints due to the dev_err_probe() in actual .probe() below. Please fix that. > + return 0; > +} > +EXPORT_SYMBOL_NS(ocelot_chip_reset, MFD_OCELOT); > + > +static const struct resource vsc7512_miim0_resources[] = { > + DEFINE_RES_REG_NAMED(VSC7512_MIIM0_RES_START, VSC7512_MIIM0_RES_SIZE, > + "gcb_miim0"), Lots of early breaks coming up - I won't comment on them all. > + DEFINE_RES_REG_NAMED(VSC7512_PHY_RES_START, VSC7512_PHY_RES_SIZE, > + "gcb_phy"), > +}; > + > +static const struct resource vsc7512_miim1_resources[] = { > + DEFINE_RES_REG_NAMED(VSC7512_MIIM1_RES_START, VSC7512_MIIM1_RES_SIZE, > + "gcb_miim1"), > +}; > + > +static const struct resource vsc7512_pinctrl_resources[] = { > + DEFINE_RES_REG_NAMED(VSC7512_GPIO_RES_START, VSC7512_GPIO_RES_SIZE, > + "gcb_gpio"), > +}; > + > +static const struct resource vsc7512_sgpio_resources[] = { > + DEFINE_RES_REG_NAMED(VSC7512_SIO_CTRL_RES_START, > + VSC7512_SIO_CTRL_RES_SIZE, > + "gcb_sio"), > +}; > + > +static const struct mfd_cell vsc7512_devs[] = { > + { > + .name = "ocelot-pinctrl", > + .of_compatible = "mscc,ocelot-pinctrl", > + .num_resources = ARRAY_SIZE(vsc7512_pinctrl_resources), > + .resources = vsc7512_pinctrl_resources, > + }, { > + .name = "ocelot-sgpio", > + .of_compatible = "mscc,ocelot-sgpio", > + .num_resources = ARRAY_SIZE(vsc7512_sgpio_resources), > + .resources = vsc7512_sgpio_resources, > + }, { > + .name = "ocelot-miim0", > + .of_compatible = "mscc,ocelot-miim", > + .of_reg = VSC7512_MIIM0_RES_START, > + .use_of_reg = true, > + .num_resources = ARRAY_SIZE(vsc7512_miim0_resources), > + .resources = vsc7512_miim0_resources, > + }, { > + .name = "ocelot-miim1", > + .of_compatible = "mscc,ocelot-miim", > + .of_reg = VSC7512_MIIM1_RES_START, > + .use_of_reg = true, > + .num_resources = ARRAY_SIZE(vsc7512_miim1_resources), > + .resources = vsc7512_miim1_resources, > + }, > +}; > + > +static void ocelot_core_try_add_regmap(struct device *dev, > + const struct resource *res) > +{ > + if (!dev_get_regmap(dev, res->name)) > + ocelot_spi_init_regmap(dev, res); This is probably clearer at first-glance for readers: if (dev_get_regmap(dev, res->name)) return; ocelot_spi_init_regmap(dev, res); > +} > + > +static void ocelot_core_try_add_regmaps(struct device *dev, > + const struct mfd_cell *cell) > +{ > + int i; > + > + for (i = 0; i < cell->num_resources; i++) > + ocelot_core_try_add_regmap(dev, &cell->resources[i]); > +} > + > +int ocelot_core_init(struct device *dev) > +{ > + int i, ndevs; > + > + ndevs = ARRAY_SIZE(vsc7512_devs); > + > + for (i = 0; i < ndevs; i++) > + ocelot_core_try_add_regmaps(dev, &vsc7512_devs[i]); > + > + return devm_mfd_add_devices(dev, PLATFORM_DEVID_AUTO, vsc7512_devs, > + ndevs, NULL, 0, NULL); > +} > +EXPORT_SYMBOL_NS(ocelot_core_init, MFD_OCELOT); > + > +MODULE_DESCRIPTION("Externally Controlled Ocelot Chip Driver"); > +MODULE_AUTHOR("Colin Foster "); > +MODULE_LICENSE("GPL"); > +MODULE_IMPORT_NS(MFD_OCELOT_SPI); > diff --git a/drivers/mfd/ocelot-spi.c b/drivers/mfd/ocelot-spi.c > new file mode 100644 > index 000000000000..0c1c5215c706 > --- /dev/null > +++ b/drivers/mfd/ocelot-spi.c > @@ -0,0 +1,317 @@ > +// SPDX-License-Identifier: (GPL-2.0 OR MIT) > +/* > + * SPI core driver for the Ocelot chip family. > + * > + * This driver will handle everything necessary to allow for communication over > + * SPI to the VSC7511, VSC7512, VSC7513 and VSC7514 chips. The main functions > + * are to prepare the chip's SPI interface for a specific bus speed, and a host > + * processor's endianness. This will create and distribute regmaps for any > + * children. > + * > + * Copyright 2021, 2022 Innovative Advantage Inc. > + * > + * Author: Colin Foster > + */ > + > +#include > +#include > +#include > +#include > +#include > + > +#include > + > +#include "ocelot.h" > + > +#define REG_DEV_CPUORG_IF_CTRL 0x0000 > +#define REG_DEV_CPUORG_IF_CFGSTAT 0x0004 > + > +#define CFGSTAT_IF_NUM_VCORE (0 << 24) > +#define CFGSTAT_IF_NUM_VRAP (1 << 24) > +#define CFGSTAT_IF_NUM_SI (2 << 24) > +#define CFGSTAT_IF_NUM_MIIM (3 << 24) > + > +#define VSC7512_DEVCPU_ORG_RES_START 0x71000000 > +#define VSC7512_DEVCPU_ORG_RES_SIZE 0x38 > + > +#define VSC7512_CHIP_REGS_RES_START 0x71070000 > +#define VSC7512_CHIP_REGS_RES_SIZE 0x14 > + > +struct spi_device; Why not just #include? > +static const struct resource vsc7512_dev_cpuorg_resource = > + DEFINE_RES_REG_NAMED(VSC7512_DEVCPU_ORG_RES_START, > + VSC7512_DEVCPU_ORG_RES_SIZE, > + "devcpu_org"); > + > +static const struct resource vsc7512_gcb_resource = > + DEFINE_RES_REG_NAMED(VSC7512_CHIP_REGS_RES_START, > + VSC7512_CHIP_REGS_RES_SIZE, > + "devcpu_gcb_chip_regs"); > + > +static int ocelot_spi_initialize(struct device *dev) > +{ > + struct ocelot_ddata *ddata = dev_get_drvdata(dev); > + u32 val, check; > + int err; > + > + val = OCELOT_SPI_BYTE_ORDER; > + > + /* > + * The SPI address must be big-endian, but we want the payload to match > + * our CPU. These are two bits (0 and 1) but they're repeated such that > + * the write from any configuration will be valid. The four > + * configurations are: > + * > + * 0b00: little-endian, MSB first > + * | 111111 | 22221111 | 33222222 | > + * | 76543210 | 54321098 | 32109876 | 10987654 | > + * > + * 0b01: big-endian, MSB first > + * | 33222222 | 22221111 | 111111 | | > + * | 10987654 | 32109876 | 54321098 | 76543210 | > + * > + * 0b10: little-endian, LSB first > + * | 111111 | 11112222 | 22222233 | > + * | 01234567 | 89012345 | 67890123 | 45678901 | > + * > + * 0b11: big-endian, LSB first > + * | 22222233 | 11112222 | 111111 | | > + * | 45678901 | 67890123 | 89012345 | 01234567 | > + */ > + err = regmap_write(ddata->cpuorg_regmap, REG_DEV_CPUORG_IF_CTRL, val); > + if (err) > + return err; > + > + /* > + * Apply the number of padding bytes between a read request and the data > + * payload. Some registers have access times of up to 1us, so if the > + * first payload bit is shifted out too quickly, the read will fail. > + */ > + val = ddata->spi_padding_bytes; > + err = regmap_write(ddata->cpuorg_regmap, REG_DEV_CPUORG_IF_CFGSTAT, > + val); > + if (err) > + return err; > + > + /* > + * After we write the interface configuration, read it back here. This > + * will verify several different things. The first is that the number of > + * padding bytes actually got written correctly. These are found in bits > + * 0:3. > + * > + * The second is that bit 16 is cleared. Bit 16 is IF_CFGSTAT:IF_STAT, > + * and will be set if the register access is too fast. This would be in > + * the condition that the number of padding bytes is insufficient for > + * the SPI bus frequency. > + * > + * The last check is for bits 31:24, which define the interface by which > + * the registers are being accessed. Since we're accessing them via the > + * serial interface, it must return IF_NUM_SI. > + */ > + check = val | CFGSTAT_IF_NUM_SI; > + > + err = regmap_read(ddata->cpuorg_regmap, REG_DEV_CPUORG_IF_CFGSTAT, > + &val); > + if (err) > + return err; > + > + if (check != val) > + return -ENODEV; > + > + return 0; > +} > + > +static const struct regmap_config ocelot_spi_regmap_config = { > + .reg_bits = 24, > + .reg_stride = 4, > + .reg_downshift = 2, > + .val_bits = 32, > + > + .write_flag_mask = 0x80, > + > + .use_single_write = true, > + .can_multi_write = false, > + > + .reg_format_endian = REGMAP_ENDIAN_BIG, > + .val_format_endian = REGMAP_ENDIAN_NATIVE, > +}; > + > +static int ocelot_spi_regmap_bus_read(void *context, > + const void *reg, size_t reg_size, > + void *val, size_t val_size) > +{ > + struct ocelot_ddata *ddata = context; > + struct spi_transfer tx, padding, rx; > + struct spi_device *spi = ddata->spi; > + struct spi_message msg; > + > + spi = ddata->spi; Drop this line. > + spi_message_init(&msg); > + > + memset(&tx, 0, sizeof(tx)); > + > + tx.tx_buf = reg; > + tx.len = reg_size; > + > + spi_message_add_tail(&tx, &msg); > + > + if (ddata->spi_padding_bytes) { > + memset(&padding, 0, sizeof(padding)); > + > + padding.len = ddata->spi_padding_bytes; > + padding.tx_buf = ddata->dummy_buf; > + padding.dummy_data = 1; > + > + spi_message_add_tail(&padding, &msg); > + } > + > + memset(&rx, 0, sizeof(rx)); > + rx.rx_buf = val; > + rx.len = val_size; > + > + spi_message_add_tail(&rx, &msg); > + > + return spi_sync(spi, &msg); > +} > + > +static int ocelot_spi_regmap_bus_write(void *context, const void *data, > + size_t count) > +{ > + struct ocelot_ddata *ddata = context; > + struct spi_device *spi = ddata->spi; > + > + return spi_write(spi, data, count); > +} > + > +static const struct regmap_bus ocelot_spi_regmap_bus = { > + .write = ocelot_spi_regmap_bus_write, > + .read = ocelot_spi_regmap_bus_read, > +}; > + > +struct regmap * > +ocelot_spi_init_regmap(struct device *dev, const struct resource *res) One line, along with all the others. > +{ > + struct ocelot_ddata *ddata = dev_get_drvdata(dev); > + struct regmap_config regmap_config; > + > + memcpy(®map_config, &ocelot_spi_regmap_config, > + sizeof(regmap_config)); > + > + regmap_config.name = res->name; > + regmap_config.max_register = res->end - res->start; > + regmap_config.reg_base = res->start; > + > + return devm_regmap_init(dev, &ocelot_spi_regmap_bus, ddata, > + ®map_config); > +} > +EXPORT_SYMBOL_NS(ocelot_spi_init_regmap, MFD_OCELOT_SPI); > + > +static int ocelot_spi_probe(struct spi_device *spi) > +{ > + struct device *dev = &spi->dev; > + struct ocelot_ddata *ddata; > + struct regmap *r; > + int err; > + > + ddata = devm_kzalloc(dev, sizeof(*ddata), GFP_KERNEL); > + if (!ddata) > + return -ENOMEM; > + > + ddata->dev = dev; How are you fetching ddata if you don't already have 'dev'? > + dev_set_drvdata(dev, ddata); This should use the spi_* variant. > + if (spi->max_speed_hz <= 500000) { > + ddata->spi_padding_bytes = 0; > + } else { > + /* > + * Calculation taken from the manual for IF_CFGSTAT:IF_CFG. > + * Register access time is 1us, so we need to configure and send > + * out enough padding bytes between the read request and data > + * transmission that lasts at least 1 microsecond. > + */ > + ddata->spi_padding_bytes = 1 + > + (spi->max_speed_hz / 1000000 + 2) / 8; > + > + ddata->dummy_buf = devm_kzalloc(dev, ddata->spi_padding_bytes, > + GFP_KERNEL); > + if (!ddata->dummy_buf) > + return -ENOMEM; > + } > + > + ddata->spi = spi; If you have 'spi' you definitely do not need 'dev'. You can derive one from the other. > + spi->bits_per_word = 8; > + > + err = spi_setup(spi); > + if (err < 0) > + return dev_err_probe(&spi->dev, err, > + "Error performing SPI setup\n"); > + > + r = ocelot_spi_init_regmap(dev, &vsc7512_dev_cpuorg_resource); > + if (IS_ERR(r)) > + return PTR_ERR(r); > + > + ddata->cpuorg_regmap = r; > + > + r = ocelot_spi_init_regmap(dev, &vsc7512_gcb_resource); > + if (IS_ERR(r)) > + return PTR_ERR(r); > + > + ddata->gcb_regmap = r; > + > + /* > + * The chip must be set up for SPI before it gets initialized and reset. > + * This must be done before calling init, and after a chip reset is > + * performed. > + */ > + err = ocelot_spi_initialize(dev); > + if (err) > + return dev_err_probe(dev, err, "Error initializing SPI bus\n"); > + > + err = ocelot_chip_reset(dev); > + if (err) > + return dev_err_probe(dev, err, "Error resetting device\n"); > + > + /* > + * A chip reset will clear the SPI configuration, so it needs to be done > + * again before we can access any registers > + */ > + err = ocelot_spi_initialize(dev); > + if (err) > + return dev_err_probe(dev, err, > + "Error initializing SPI bus after reset\n"); > + > + err = ocelot_core_init(dev); > + if (err < 0) > + return dev_err_probe(dev, err, > + "Error initializing Ocelot core\n"); > + > + return 0; > +} > + > +static const struct spi_device_id ocelot_spi_ids[] = { > + { "vsc7512", 0 }, > + { } > +}; > + > +static const struct of_device_id ocelot_spi_of_match[] = { > + { .compatible = "mscc,vsc7512" }, > + { } > +}; > +MODULE_DEVICE_TABLE(of, ocelot_spi_of_match); > + > +static struct spi_driver ocelot_spi_driver = { > + .driver = { > + .name = "ocelot-soc", > + .of_match_table = ocelot_spi_of_match, > + }, > + .id_table = ocelot_spi_ids, > + .probe = ocelot_spi_probe, > +}; > +module_spi_driver(ocelot_spi_driver); > + > +MODULE_DESCRIPTION("SPI Controlled Ocelot Chip Driver"); > +MODULE_AUTHOR("Colin Foster "); > +MODULE_LICENSE("Dual MIT/GPL"); > +MODULE_IMPORT_NS(MFD_OCELOT); > diff --git a/drivers/mfd/ocelot.h b/drivers/mfd/ocelot.h > new file mode 100644 > index 000000000000..c86bd6990a3c > --- /dev/null > +++ b/drivers/mfd/ocelot.h > @@ -0,0 +1,34 @@ > +/* SPDX-License-Identifier: GPL-2.0 OR MIT */ > +/* Copyright 2021, 2022 Innovative Advantage Inc. */ > + > +#include > + > +struct device; > +struct spi_device; > +struct regmap; > +struct resource; > + > +struct ocelot_ddata { > + struct device *dev; > + struct regmap *gcb_regmap; > + struct regmap *cpuorg_regmap; > + int spi_padding_bytes; > + struct spi_device *spi; > + void *dummy_buf; > +}; This looks like it deserves a doc header. > +int ocelot_chip_reset(struct device *dev); > +int ocelot_core_init(struct device *dev); > + > +/* SPI-specific routines that won't be necessary for other interfaces */ > +struct regmap *ocelot_spi_init_regmap(struct device *dev, > + const struct resource *res); > + > +#define OCELOT_SPI_BYTE_ORDER_LE 0x00000000 > +#define OCELOT_SPI_BYTE_ORDER_BE 0x81818181 > + > +#ifdef __LITTLE_ENDIAN > +#define OCELOT_SPI_BYTE_ORDER OCELOT_SPI_BYTE_ORDER_LE > +#else > +#define OCELOT_SPI_BYTE_ORDER OCELOT_SPI_BYTE_ORDER_BE > +#endif -- Lee Jones [李琼斯] Principal Technical Lead - Developer Services Linaro.org │ Open source software for Arm SoCs Follow Linaro: Facebook | Twitter | Blog From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from bombadil.infradead.org (bombadil.infradead.org [198.137.202.133]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by smtp.lore.kernel.org (Postfix) with ESMTPS id 4AFAFC43334 for ; Mon, 18 Jul 2022 14:19:51 +0000 (UTC) DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lists.infradead.org; s=bombadil.20210309; h=Sender: Content-Transfer-Encoding:Content-Type:List-Subscribe:List-Help:List-Post: List-Archive:List-Unsubscribe:List-Id:In-Reply-To:MIME-Version:References: Message-ID:Subject:Cc:To:From:Date:Reply-To:Content-ID:Content-Description: Resent-Date:Resent-From:Resent-Sender:Resent-To:Resent-Cc:Resent-Message-ID: List-Owner; bh=wXQzxdp2SkTNTigUZxMNsmKYU/ImpZGcFgVNUkbmojo=; b=lC/HXqvydQjQxP 5uq/9e2GsZW4AYjqQrieXc1b5Ih5zozbOES+dMQvaWdJJsrCxu2FnqL+fcbo6umkiXHtFTuDA+JlH v+HY1HzFLReN+OgrYTYpiwj6oKDwxsOtB5qArzNfojhLKvDzuMRPUhI3PanSZc9XHqd4kaEhhSBKk CaGsyo9yJvv91Bwg6A93AsyMjuBmejGHNrgKcFPo51r0YKqfQ6wQItAaMr0bTt2l2NH5fPzDenMsS 2K/TdWsK2pdmuYxu9gKeZQP4N6VMebi7iItDRJci4lJoC49sgMssVMsHUU+rpwlBuC7HwvKb3dRDw mov9qusPy7AU7z9tCO9Q==; Received: from localhost ([::1] helo=bombadil.infradead.org) by bombadil.infradead.org with esmtp (Exim 4.94.2 #2 (Red Hat Linux)) id 1oDRa5-00EaT7-4N; Mon, 18 Jul 2022 14:18:41 +0000 Received: from mail-wr1-x42e.google.com ([2a00:1450:4864:20::42e]) by bombadil.infradead.org with esmtps (Exim 4.94.2 #2 (Red Hat Linux)) id 1oDRZz-00EaNS-LQ for linux-arm-kernel@lists.infradead.org; Mon, 18 Jul 2022 14:18:38 +0000 Received: by mail-wr1-x42e.google.com with SMTP id j1so12803735wrs.4 for ; Mon, 18 Jul 2022 07:18:32 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google; h=date:from:to:cc:subject:message-id:references:mime-version :content-disposition:content-transfer-encoding:in-reply-to; bh=gLq0d/jV4o9aB9pU8p7hMA+66qSzv4eqlhhhHzAYRmw=; b=vEyDTieprd8sNYmuqnTOrargXydmC0ROgW8hxZ+TmQo8DTdxtWB2rU9xtKbwV8Io7Y NeSu3Z0Fcrwed5eQrOt7TevAPh4s6pboEcyIDANa0saXRTCSTib0SHWpA8W/+A9yP+6k d8WQULhyBS8JPUeIxdXsplv/iMA6q4QcNZSKR1aX5hD02/JFl9efIgZwo04d6A/V+T4H C3gR3a3z8Tz6+BFPHDiVvfGysxJCF+Fngd888vVyTgD1sGrqn+E6w2ivqve99Tz0+lDa vOkfc6CuS6TIoIfb+YsotGZtPNO/Cj/yF/vzTcCbWaPODbXXsPaIFLhp9d1UgkJhsYiJ Qc/A== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20210112; h=x-gm-message-state:date:from:to:cc:subject:message-id:references :mime-version:content-disposition:content-transfer-encoding :in-reply-to; bh=gLq0d/jV4o9aB9pU8p7hMA+66qSzv4eqlhhhHzAYRmw=; b=7H8ZG7IA9244KMwG+83j56hEvy/mUldYHvDqbaKknOpUkynRNF2wqcIyOCfl10Wcz2 qS1aDsyn7sUFZv1q/0bwdXxPSzhJHRBPOQ+4OQCItZ2zwWKsqLEqrY79OQUFt5zCe6BN qFQ6auRTKVlsqyCB/zqeKbXiKsXZLBYRrfJ0gYto+fnfuChB3CxgfgeC9sCJME9NnJxT jMOuZEHYZIxvaPxdB2H3vzcCmleGNHF4LB/v/29MLqSXuT9+EUfozYlZuucu2YZiCYt4 vuxvsr15metunpLdQ8WZBziZYuxHSGlQV9+qKeOb4NFR8+med61ZxPDN4KxRTfPbDFky oqhQ== X-Gm-Message-State: AJIora8v1GXK/b1GehjHbkduhOaUhSkHkMF14o+JTN3bRGQFku20LNKb ++nlRXMcG8T5iBwDstFMV6Nlsg== X-Google-Smtp-Source: AGRyM1sAwosNw1DqpvsNcl7J11odJWZRQhS7HKRREBfavJFYLY9GKFX6JmjDGvjCkVb1BdRf62c3WQ== X-Received: by 2002:a5d:64a4:0:b0:21d:be80:de06 with SMTP id m4-20020a5d64a4000000b0021dbe80de06mr20460241wrp.107.1658153911461; Mon, 18 Jul 2022 07:18:31 -0700 (PDT) Received: from google.com (cpc155339-bagu17-2-0-cust87.1-3.cable.virginm.net. [86.27.177.88]) by smtp.gmail.com with ESMTPSA id c6-20020a7bc006000000b003a02f957245sm18759407wmb.26.2022.07.18.07.18.30 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Mon, 18 Jul 2022 07:18:31 -0700 (PDT) Date: Mon, 18 Jul 2022 15:18:28 +0100 From: Lee Jones To: Colin Foster Cc: devicetree@vger.kernel.org, linux-kernel@vger.kernel.org, netdev@vger.kernel.org, linux-arm-kernel@lists.infradead.org, linux-gpio@vger.kernel.org, Vladimir Oltean , Rob Herring , Krzysztof Kozlowski , Andrew Lunn , Heiner Kallweit , Russell King , "David S. Miller" , Eric Dumazet , Jakub Kicinski , Paolo Abeni , Lars Povlsen , Steen Hegelund , UNGLinuxDriver@microchip.com, Linus Walleij , Wolfram Sang , Terry Bowman , Andy Shevchenko , katie.morris@in-advantage.com Subject: Re: [PATCH v13 net-next 9/9] mfd: ocelot: add support for the vsc7512 chip via spi Message-ID: References: <20220705204743.3224692-1-colin.foster@in-advantage.com> <20220705204743.3224692-10-colin.foster@in-advantage.com> MIME-Version: 1.0 Content-Disposition: inline In-Reply-To: <20220705204743.3224692-10-colin.foster@in-advantage.com> X-CRM114-Version: 20100106-BlameMichelson ( TRE 0.8.0 (BSD) ) MR-646709E3 X-CRM114-CacheID: sfid-20220718_071835_746917_95ED13C7 X-CRM114-Status: GOOD ( 44.36 ) X-BeenThere: linux-arm-kernel@lists.infradead.org X-Mailman-Version: 2.1.34 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Content-Type: text/plain; charset="utf-8" Content-Transfer-Encoding: base64 Sender: "linux-arm-kernel" Errors-To: linux-arm-kernel-bounces+linux-arm-kernel=archiver.kernel.org@lists.infradead.org T24gVHVlLCAwNSBKdWwgMjAyMiwgQ29saW4gRm9zdGVyIHdyb3RlOgoKPiBUaGUgVlNDNzUxMiBp cyBhIG5ldHdvcmtpbmcgY2hpcCB0aGF0IGNvbnRhaW5zIHNldmVyYWwgcGVyaXBoZXJhbHMuIE1h bnkgb2YKPiB0aGVzZSBwZXJpcGhlcmFscyBhcmUgY3VycmVudGx5IHN1cHBvcnRlZCBieSB0aGUg VlNDNzUxMyBhbmQgVlNDNzUxNCBjaGlwcywKPiBidXQgdGhvc2UgcnVuIG9uIGFuIGludGVybmFs IENQVS4gVGhlIFZTQzc1MTIgbGFja3MgdGhpcyBDUFUsIGFuZCBtdXN0IGJlCj4gY29udHJvbGxl ZCBleHRlcm5hbGx5Lgo+IAo+IFV0aWxpemUgdGhlIGV4aXN0aW5nIGRyaXZlcnMgYnkgcmVmZXJl bmNpbmcgdGhlIGNoaXAgYXMgYW4gTUZELiBBZGQgc3VwcG9ydAo+IGZvciB0aGUgdHdvIE1ESU8g YnVzZXMsIHRoZSBpbnRlcm5hbCBwaHlzLCBwaW5jdHJsLCBhbmQgc2VyaWFsIEdQSU8uCj4gCj4g U2lnbmVkLW9mZi1ieTogQ29saW4gRm9zdGVyIDxjb2xpbi5mb3N0ZXJAaW4tYWR2YW50YWdlLmNv bT4KPiAtLS0KPiAgTUFJTlRBSU5FUlMgICAgICAgICAgICAgICB8ICAgMSArCj4gIGRyaXZlcnMv bWZkL0tjb25maWcgICAgICAgfCAgMjEgKysrCj4gIGRyaXZlcnMvbWZkL01ha2VmaWxlICAgICAg fCAgIDMgKwo+ICBkcml2ZXJzL21mZC9vY2Vsb3QtY29yZS5jIHwgMTY5ICsrKysrKysrKysrKysr KysrKysrCj4gIGRyaXZlcnMvbWZkL29jZWxvdC1zcGkuYyAgfCAzMTcgKysrKysrKysrKysrKysr KysrKysrKysrKysrKysrKysrKysrKysKPiAgZHJpdmVycy9tZmQvb2NlbG90LmggICAgICB8ICAz NCArKysrCj4gIDYgZmlsZXMgY2hhbmdlZCwgNTQ1IGluc2VydGlvbnMoKykKPiAgY3JlYXRlIG1v ZGUgMTAwNjQ0IGRyaXZlcnMvbWZkL29jZWxvdC1jb3JlLmMKPiAgY3JlYXRlIG1vZGUgMTAwNjQ0 IGRyaXZlcnMvbWZkL29jZWxvdC1zcGkuYwo+ICBjcmVhdGUgbW9kZSAxMDA2NDQgZHJpdmVycy9t ZmQvb2NlbG90LmgKCkdlbmVyYWxseSB0aGlzIGlzIGxvb2tpbmcgbXVjaCBiZXR0ZXIuCgpBbG1v c3QgcmVhZHkgZm9yIGluY2x1c2lvbiB3aXRoIGp1c3QgYSBmZXcgbml0cy4KCj4gZGlmZiAtLWdp dCBhL01BSU5UQUlORVJTIGIvTUFJTlRBSU5FUlMKPiBpbmRleCA1ZTc5OGM0MmZhMDguLmUzMjk5 Njc3Y2Q0YSAxMDA2NDQKPiAtLS0gYS9NQUlOVEFJTkVSUwo+ICsrKyBiL01BSU5UQUlORVJTCj4g QEAgLTE0NDcxLDYgKzE0NDcxLDcgQEAgT0NFTE9UIEVYVEVSTkFMIFNXSVRDSCBDT05UUk9MCj4g IE06CUNvbGluIEZvc3RlciA8Y29saW4uZm9zdGVyQGluLWFkdmFudGFnZS5jb20+Cj4gIFM6CVN1 cHBvcnRlZAo+ICBGOglEb2N1bWVudGF0aW9uL2RldmljZXRyZWUvYmluZGluZ3MvbWZkL21zY2Ms b2NlbG90LnlhbWwKPiArRjoJZHJpdmVycy9tZmQvb2NlbG90Kgo+ICBGOglpbmNsdWRlL2xpbnV4 L21mZC9vY2Vsb3QuaAo+ICAKPiAgT0NYTCAoT3BlbiBDb2hlcmVudCBBY2NlbGVyYXRvciBQcm9j ZXNzb3IgSW50ZXJmYWNlIE9wZW5DQVBJKSBEUklWRVIKPiBkaWZmIC0tZ2l0IGEvZHJpdmVycy9t ZmQvS2NvbmZpZyBiL2RyaXZlcnMvbWZkL0tjb25maWcKPiBpbmRleCAzYjU5NDU2ZjU1NDUuLjBl ZjQzM2QxNzBkYyAxMDA2NDQKPiAtLS0gYS9kcml2ZXJzL21mZC9LY29uZmlnCj4gKysrIGIvZHJp dmVycy9tZmQvS2NvbmZpZwo+IEBAIC05NjIsNiArOTYyLDI3IEBAIGNvbmZpZyBNRkRfTUVORjIx Qk1DCj4gIAkgIFRoaXMgZHJpdmVyIGNhbiBhbHNvIGJlIGJ1aWx0IGFzIGEgbW9kdWxlLiBJZiBz byB0aGUgbW9kdWxlCj4gIAkgIHdpbGwgYmUgY2FsbGVkIG1lbmYyMWJtYy4KPiAgCj4gK2NvbmZp ZyBNRkRfT0NFTE9UCj4gKwl0cmlzdGF0ZSAiTWljcm9zZW1pIE9jZWxvdCBFeHRlcm5hbCBDb250 cm9sIFN1cHBvcnQiCj4gKwlkZXBlbmRzIG9uIFNQSV9NQVNURVIKPiArCXNlbGVjdCBNRkRfQ09S RQo+ICsJc2VsZWN0IFJFR01BUF9TUEkKPiArCWhlbHAKPiArCSAgT2NlbG90IGlzIGEgZmFtaWx5 IG9mIG5ldHdvcmtpbmcgY2hpcHMgdGhhdCBzdXBwb3J0IG11bHRpcGxlIGV0aGVybmV0Cj4gKwkg IGFuZCBmaWJyZSBpbnRlcmZhY2VzLiBJbiBhZGRpdGlvbiB0byBuZXR3b3JraW5nLCB0aGV5IGNv bnRhaW4gc2V2ZXJhbAo+ICsJICBvdGhlciBmdW5jdGlvbnMsIGluY2x1ZGluZyBwaW5jdHJsLCBN RElPLCBhbmQgY29tbXVuaWNhdGlvbiB3aXRoCj4gKwkgIGV4dGVybmFsIGNoaXBzLiBXaGlsZSBz b21lIGNoaXBzIGhhdmUgYW4gaW50ZXJuYWwgcHJvY2Vzc29yIGNhcGFibGUgb2YKPiArCSAgcnVu bmluZyBhbiBPUywgb3RoZXJzIGRvbid0LiBBbGwgY2hpcHMgY2FuIGJlIGNvbnRyb2xsZWQgZXh0 ZXJuYWxseQo+ICsJICB0aHJvdWdoIGRpZmZlcmVudCBpbnRlcmZhY2VzLCBpbmNsdWRpbmcgU1BJ LCBJMkMsIGFuZCBQQ0llLgo+ICsKPiArCSAgU2F5IHllcyBoZXJlIHRvIGFkZCBzdXBwb3J0IGZv ciBPY2Vsb3QgY2hpcHMgKFZTQzc1MTEsIFZTQzc1MTIsCj4gKwkgIFZTQzc1MTMsIFZTQzc1MTQp IGNvbnRyb2xsZWQgZXh0ZXJuYWxseS4KPiArCj4gKwkgIFRvIGNvbXBpbGUgdGhpcyBkcml2ZXIg YXMgYSBtb2R1bGUsIGNob29zZSBNIGhlcmU6IHRoZSBtb2R1bGUgd2lsbCBiZQo+ICsJICBjYWxs ZWQgb2NlbG90LXNvYy4KPiArCj4gKwkgIElmIHVuc3VyZSwgc2F5IE4uCj4gKwo+ICBjb25maWcg RVpYX1BDQVAKPiAgCWJvb2wgIk1vdG9yb2xhIEVaWFBDQVAgU3VwcG9ydCIKPiAgCWRlcGVuZHMg b24gU1BJX01BU1RFUgo+IGRpZmYgLS1naXQgYS9kcml2ZXJzL21mZC9NYWtlZmlsZSBiL2RyaXZl cnMvbWZkL01ha2VmaWxlCj4gaW5kZXggODU4Y2FjZjY1OWQ2Li4wMDA0YjdlODYyMjAgMTAwNjQ0 Cj4gLS0tIGEvZHJpdmVycy9tZmQvTWFrZWZpbGUKPiArKysgYi9kcml2ZXJzL21mZC9NYWtlZmls ZQo+IEBAIC0xMjAsNiArMTIwLDkgQEAgb2JqLSQoQ09ORklHX01GRF9NQzEzWFhYX0kyQykJKz0g bWMxM3h4eC1pMmMubwo+ICAKPiAgb2JqLSQoQ09ORklHX01GRF9DT1JFKQkJKz0gbWZkLWNvcmUu bwo+ICAKPiArb2NlbG90LXNvYy1vYmpzCQkJOj0gb2NlbG90LWNvcmUubyBvY2Vsb3Qtc3BpLm8K PiArb2JqLSQoQ09ORklHX01GRF9PQ0VMT1QpCSs9IG9jZWxvdC1zb2Mubwo+ICsKPiAgb2JqLSQo Q09ORklHX0VaWF9QQ0FQKQkJKz0gZXp4LXBjYXAubwo+ICBvYmotJChDT05GSUdfTUZEX0NQQ0FQ KQkJKz0gbW90b3JvbGEtY3BjYXAubwo+ICAKPiBkaWZmIC0tZ2l0IGEvZHJpdmVycy9tZmQvb2Nl bG90LWNvcmUuYyBiL2RyaXZlcnMvbWZkL29jZWxvdC1jb3JlLmMKPiBuZXcgZmlsZSBtb2RlIDEw MDY0NAo+IGluZGV4IDAwMDAwMDAwMDAwMC4uZTA3Y2Q5MDFlMWIzCj4gLS0tIC9kZXYvbnVsbAo+ ICsrKyBiL2RyaXZlcnMvbWZkL29jZWxvdC1jb3JlLmMKPiBAQCAtMCwwICsxLDE2OSBAQAo+ICsv LyBTUERYLUxpY2Vuc2UtSWRlbnRpZmllcjogKEdQTC0yLjAgT1IgTUlUKQo+ICsvKgo+ICsgKiBD b3JlIGRyaXZlciBmb3IgdGhlIE9jZWxvdCBjaGlwIGZhbWlseS4KPiArICoKPiArICogVGhlIFZT Qzc1MTEsIDc1MTIsIDc1MTMsIGFuZCA3NTE0IGNhbiBiZSBjb250cm9sbGVkIGludGVybmFsbHkg dmlhIGFuCj4gKyAqIG9uLWNoaXAgTUlQUyBwcm9jZXNzb3IsIG9yIGV4dGVybmFsbHkgdmlhIFNQ SSwgSTJDLCBQQ0llLiBUaGlzIGNvcmUgZHJpdmVyIGlzCj4gKyAqIGludGVuZGVkIHRvIGJlIHRo ZSBidXMtYWdub3N0aWMgZ2x1ZSBiZXR3ZWVuLCBmb3IgZXhhbXBsZSwgdGhlIFNQSSBidXMgYW5k Cj4gKyAqIHRoZSBjaGlsZCBkZXZpY2VzLgo+ICsgKgo+ICsgKiBDb3B5cmlnaHQgMjAyMSwgMjAy MiBJbm5vdmF0aXZlIEFkdmFudGFnZSBJbmMuCgpSYW5nZT8KCj4gKyAqIEF1dGhvcjogQ29saW4g Rm9zdGVyIDxjb2xpbi5mb3N0ZXJAaW4tYWR2YW50YWdlLmNvbT4KPiArICovCj4gKwo+ICsjaW5j bHVkZSA8bGludXgva2VybmVsLmg+Cj4gKyNpbmNsdWRlIDxsaW51eC9tZmQvY29yZS5oPgo+ICsj aW5jbHVkZSA8bGludXgvbWZkL29jZWxvdC5oPgo+ICsjaW5jbHVkZSA8bGludXgvbW9kdWxlLmg+ Cj4gKyNpbmNsdWRlIDxsaW51eC9yZWdtYXAuaD4KPiArI2luY2x1ZGUgPGxpbnV4L3R5cGVzLmg+ Cj4gKwo+ICsjaW5jbHVkZSA8c29jL21zY2Mvb2NlbG90Lmg+Cj4gKwo+ICsjaW5jbHVkZSAib2Nl bG90LmgiCj4gKwo+ICsjZGVmaW5lIFJFR19HQ0JfU09GVF9SU1QJCTB4MDAwOAo+ICsKPiArI2Rl ZmluZSBCSVRfU09GVF9DSElQX1JTVAkJQklUKDApCj4gKwo+ICsjZGVmaW5lIFZTQzc1MTJfTUlJ TTBfUkVTX1NUQVJUCQkweDcxMDcwMDljCj4gKyNkZWZpbmUgVlNDNzUxMl9NSUlNMF9SRVNfU0la RQkJMHgyNAo+ICsKPiArI2RlZmluZSBWU0M3NTEyX01JSU0xX1JFU19TVEFSVAkJMHg3MTA3MDBj MAo+ICsjZGVmaW5lIFZTQzc1MTJfTUlJTTFfUkVTX1NJWkUJCTB4MjQKCk1heWJlOgoKI2RlZmlu ZSBWU0M3NTEyX01JSU0wX1JFU19TVEFSVAkJMHg3MTA3MDA5YwojZGVmaW5lIFZTQzc1MTJfTUlJ TTFfUkVTX1NUQVJUCQkweDcxMDcwMGMwCiNkZWZpbmUgVlNDNzUxMl9NSUlNX1JFU19TSVpFCQkw eDI0CgpObyBzdHJvbmcgZmVlbGluZ3MgYWJvdXQgdGhpcyB0aG91Z2gsIGp1c3Qgc2F2ZXMgYSBs aW5lIG9yIHR3by4KCj4gKyNkZWZpbmUgVlNDNzUxMl9QSFlfUkVTX1NUQVJUCQkweDcxMDcwMGYw Cj4gKyNkZWZpbmUgVlNDNzUxMl9QSFlfUkVTX1NJWkUJCTB4NAo+ICsKPiArI2RlZmluZSBWU0M3 NTEyX0dQSU9fUkVTX1NUQVJUCQkweDcxMDcwMDM0Cj4gKyNkZWZpbmUgVlNDNzUxMl9HUElPX1JF U19TSVpFCQkweDZjCj4gKwo+ICsjZGVmaW5lIFZTQzc1MTJfU0lPX0NUUkxfUkVTX1NUQVJUCTB4 NzEwNzAwZjgKPiArI2RlZmluZSBWU0M3NTEyX1NJT19DVFJMX1JFU19TSVpFCTB4MTAwCj4gKwo+ ICsjZGVmaW5lIFZTQzc1MTJfR0NCX1JTVF9TTEVFUF9VUwkxMDAKPiArI2RlZmluZSBWU0M3NTEy X0dDQl9SU1RfVElNRU9VVF9VUwkxMDAwMDAKPiArCj4gK3N0YXRpYyBpbnQgb2NlbG90X2djYl9j aGlwX3JzdF9zdGF0dXMoc3RydWN0IG9jZWxvdF9kZGF0YSAqZGRhdGEpCj4gK3sKPiArCWludCB2 YWwsIGVycjsKPiArCj4gKwllcnIgPSByZWdtYXBfcmVhZChkZGF0YS0+Z2NiX3JlZ21hcCwgUkVH X0dDQl9TT0ZUX1JTVCwgJnZhbCk7Cj4gKwlpZiAoZXJyKQo+ICsJCXZhbCA9IGVycjsKCkkgdGhp bmsganVzdCByZXR1cm5pbmcgZXJyIGlzIGNsZWFyZXIuCgo+ICsJcmV0dXJuIHZhbDsKPiArfQo+ ICsKPiAraW50IG9jZWxvdF9jaGlwX3Jlc2V0KHN0cnVjdCBkZXZpY2UgKmRldikKPiArewo+ICsJ c3RydWN0IG9jZWxvdF9kZGF0YSAqZGRhdGEgPSBkZXZfZ2V0X2RydmRhdGEoZGV2KTsKPiArCWlu dCByZXQsIHZhbDsKPiArCj4gKwkvKgo+ICsJICogUmVzZXQgdGhlIGVudGlyZSBjaGlwIGhlcmUg dG8gcHV0IGl0IGludG8gYSBjb21wbGV0ZWx5IGtub3duIHN0YXRlLgo+ICsJICogT3RoZXIgZHJp dmVycyBtYXkgd2FudCB0byByZXNldCB0aGVpciBvd24gc3Vic3lzdGVtcy4gVGhlIHJlZ2lzdGVy Cj4gKwkgKiBzZWxmLWNsZWFycywgc28gb25lIHdyaXRlIGlzIGFsbCB0aGF0IGlzIG5lZWRlZCBh bmQgd2FpdCBmb3IgaXQgdG8KPiArCSAqIGNsZWFyLgo+ICsJICovCj4gKwlyZXQgPSByZWdtYXBf d3JpdGUoZGRhdGEtPmdjYl9yZWdtYXAsIFJFR19HQ0JfU09GVF9SU1QsCj4gKwkJCSAgIEJJVF9T T0ZUX0NISVBfUlNUKTsKCkxvdHMgb2YgdGhlc2UgbGluZS1icmVha3MgY2FuIGJlIHJlbW92ZWQg d2hpY2ggd2lsbCB0aWR5LXVwIHRoZSBmaWxlCnF1aXRlIGEgYml0LiAgVGhlIG5ldyBtYXggaXMg MTAwIGNoYXJzLiAgU28gbG9uZyBhcyBjaGVja3BhdGNoLnBsCmRvZXNuJ3QgY29tcGxhaW4sIEkn bSBoYXBweS4KCj4gKwlpZiAocmV0KQo+ICsJCXJldHVybiByZXQ7Cj4gKwo+ICsJcmV0ID0gcmVh ZHhfcG9sbF90aW1lb3V0KG9jZWxvdF9nY2JfY2hpcF9yc3Rfc3RhdHVzLCBkZGF0YSwgdmFsLCAh dmFsLAo+ICsJCQkJIFZTQzc1MTJfR0NCX1JTVF9TTEVFUF9VUywKPiArCQkJCSBWU0M3NTEyX0dD Ql9SU1RfVElNRU9VVF9VUyk7Cj4gKwlpZiAocmV0KQo+ICsJCXJldHVybiBkZXZfZXJyX3Byb2Jl KGRkYXRhLT5kZXYsIHJldCwgInRpbWVvdXQ6IGNoaXAgcmVzZXRcbiIpOwoKKlRoaXMqIGZ1bmN0 aW9uIGlzIG5vdCBwcm9iZS4KCkFsc28gdGhlIGxhc3QgZmFpbHVyZSB3aWxsIHByb2R1Y2UgMiBw cmludHMgZHVlIHRvIHRoZSBkZXZfZXJyX3Byb2JlKCkKaW4gYWN0dWFsIC5wcm9iZSgpIGJlbG93 LiAgUGxlYXNlIGZpeCB0aGF0LgoKPiArCXJldHVybiAwOwo+ICt9Cj4gK0VYUE9SVF9TWU1CT0xf TlMob2NlbG90X2NoaXBfcmVzZXQsIE1GRF9PQ0VMT1QpOwo+ICsKPiArc3RhdGljIGNvbnN0IHN0 cnVjdCByZXNvdXJjZSB2c2M3NTEyX21paW0wX3Jlc291cmNlc1tdID0gewo+ICsJREVGSU5FX1JF U19SRUdfTkFNRUQoVlNDNzUxMl9NSUlNMF9SRVNfU1RBUlQsIFZTQzc1MTJfTUlJTTBfUkVTX1NJ WkUsCj4gKwkJCSAgICAgImdjYl9taWltMCIpLAoKTG90cyBvZiBlYXJseSBicmVha3MgY29taW5n IHVwIC0gSSB3b24ndCBjb21tZW50IG9uIHRoZW0gYWxsLgoKPiArCURFRklORV9SRVNfUkVHX05B TUVEKFZTQzc1MTJfUEhZX1JFU19TVEFSVCwgVlNDNzUxMl9QSFlfUkVTX1NJWkUsCj4gKwkJCSAg ICAgImdjYl9waHkiKSwKPiArfTsKPiArCj4gK3N0YXRpYyBjb25zdCBzdHJ1Y3QgcmVzb3VyY2Ug dnNjNzUxMl9taWltMV9yZXNvdXJjZXNbXSA9IHsKPiArCURFRklORV9SRVNfUkVHX05BTUVEKFZT Qzc1MTJfTUlJTTFfUkVTX1NUQVJULCBWU0M3NTEyX01JSU0xX1JFU19TSVpFLAo+ICsJCQkgICAg ICJnY2JfbWlpbTEiKSwKPiArfTsKPiArCj4gK3N0YXRpYyBjb25zdCBzdHJ1Y3QgcmVzb3VyY2Ug dnNjNzUxMl9waW5jdHJsX3Jlc291cmNlc1tdID0gewo+ICsJREVGSU5FX1JFU19SRUdfTkFNRUQo VlNDNzUxMl9HUElPX1JFU19TVEFSVCwgVlNDNzUxMl9HUElPX1JFU19TSVpFLAo+ICsJCQkgICAg ICJnY2JfZ3BpbyIpLAo+ICt9Owo+ICsKPiArc3RhdGljIGNvbnN0IHN0cnVjdCByZXNvdXJjZSB2 c2M3NTEyX3NncGlvX3Jlc291cmNlc1tdID0gewo+ICsJREVGSU5FX1JFU19SRUdfTkFNRUQoVlND NzUxMl9TSU9fQ1RSTF9SRVNfU1RBUlQsCj4gKwkJCSAgICAgVlNDNzUxMl9TSU9fQ1RSTF9SRVNf U0laRSwKPiArCQkJICAgICAiZ2NiX3NpbyIpLAo+ICt9Owo+ICsKPiArc3RhdGljIGNvbnN0IHN0 cnVjdCBtZmRfY2VsbCB2c2M3NTEyX2RldnNbXSA9IHsKPiArCXsKPiArCQkubmFtZSA9ICJvY2Vs b3QtcGluY3RybCIsCj4gKwkJLm9mX2NvbXBhdGlibGUgPSAibXNjYyxvY2Vsb3QtcGluY3RybCIs Cj4gKwkJLm51bV9yZXNvdXJjZXMgPSBBUlJBWV9TSVpFKHZzYzc1MTJfcGluY3RybF9yZXNvdXJj ZXMpLAo+ICsJCS5yZXNvdXJjZXMgPSB2c2M3NTEyX3BpbmN0cmxfcmVzb3VyY2VzLAo+ICsJfSwg ewo+ICsJCS5uYW1lID0gIm9jZWxvdC1zZ3BpbyIsCj4gKwkJLm9mX2NvbXBhdGlibGUgPSAibXNj YyxvY2Vsb3Qtc2dwaW8iLAo+ICsJCS5udW1fcmVzb3VyY2VzID0gQVJSQVlfU0laRSh2c2M3NTEy X3NncGlvX3Jlc291cmNlcyksCj4gKwkJLnJlc291cmNlcyA9IHZzYzc1MTJfc2dwaW9fcmVzb3Vy Y2VzLAo+ICsJfSwgewo+ICsJCS5uYW1lID0gIm9jZWxvdC1taWltMCIsCj4gKwkJLm9mX2NvbXBh dGlibGUgPSAibXNjYyxvY2Vsb3QtbWlpbSIsCj4gKwkJLm9mX3JlZyA9IFZTQzc1MTJfTUlJTTBf UkVTX1NUQVJULAo+ICsJCS51c2Vfb2ZfcmVnID0gdHJ1ZSwKPiArCQkubnVtX3Jlc291cmNlcyA9 IEFSUkFZX1NJWkUodnNjNzUxMl9taWltMF9yZXNvdXJjZXMpLAo+ICsJCS5yZXNvdXJjZXMgPSB2 c2M3NTEyX21paW0wX3Jlc291cmNlcywKPiArCX0sIHsKPiArCQkubmFtZSA9ICJvY2Vsb3QtbWlp bTEiLAo+ICsJCS5vZl9jb21wYXRpYmxlID0gIm1zY2Msb2NlbG90LW1paW0iLAo+ICsJCS5vZl9y ZWcgPSBWU0M3NTEyX01JSU0xX1JFU19TVEFSVCwKPiArCQkudXNlX29mX3JlZyA9IHRydWUsCj4g KwkJLm51bV9yZXNvdXJjZXMgPSBBUlJBWV9TSVpFKHZzYzc1MTJfbWlpbTFfcmVzb3VyY2VzKSwK PiArCQkucmVzb3VyY2VzID0gdnNjNzUxMl9taWltMV9yZXNvdXJjZXMsCj4gKwl9LAo+ICt9Owo+ ICsKPiArc3RhdGljIHZvaWQgb2NlbG90X2NvcmVfdHJ5X2FkZF9yZWdtYXAoc3RydWN0IGRldmlj ZSAqZGV2LAo+ICsJCQkJICAgICAgIGNvbnN0IHN0cnVjdCByZXNvdXJjZSAqcmVzKQo+ICt7Cj4g KwlpZiAoIWRldl9nZXRfcmVnbWFwKGRldiwgcmVzLT5uYW1lKSkKPiArCQlvY2Vsb3Rfc3BpX2lu aXRfcmVnbWFwKGRldiwgcmVzKTsKClRoaXMgaXMgcHJvYmFibHkgY2xlYXJlciBhdCBmaXJzdC1n bGFuY2UgZm9yIHJlYWRlcnM6CgoJaWYgKGRldl9nZXRfcmVnbWFwKGRldiwgcmVzLT5uYW1lKSkK CSAgICAgICAgcmV0dXJuOwoJCglvY2Vsb3Rfc3BpX2luaXRfcmVnbWFwKGRldiwgcmVzKTsKCj4g K30KPiArCj4gK3N0YXRpYyB2b2lkIG9jZWxvdF9jb3JlX3RyeV9hZGRfcmVnbWFwcyhzdHJ1Y3Qg ZGV2aWNlICpkZXYsCj4gKwkJCQkJY29uc3Qgc3RydWN0IG1mZF9jZWxsICpjZWxsKQo+ICt7Cj4g KwlpbnQgaTsKPiArCj4gKwlmb3IgKGkgPSAwOyBpIDwgY2VsbC0+bnVtX3Jlc291cmNlczsgaSsr KQo+ICsJCW9jZWxvdF9jb3JlX3RyeV9hZGRfcmVnbWFwKGRldiwgJmNlbGwtPnJlc291cmNlc1tp XSk7Cj4gK30KPiArCj4gK2ludCBvY2Vsb3RfY29yZV9pbml0KHN0cnVjdCBkZXZpY2UgKmRldikK PiArewo+ICsJaW50IGksIG5kZXZzOwo+ICsKPiArCW5kZXZzID0gQVJSQVlfU0laRSh2c2M3NTEy X2RldnMpOwo+ICsKPiArCWZvciAoaSA9IDA7IGkgPCBuZGV2czsgaSsrKQo+ICsJCW9jZWxvdF9j b3JlX3RyeV9hZGRfcmVnbWFwcyhkZXYsICZ2c2M3NTEyX2RldnNbaV0pOwo+ICsKPiArCXJldHVy biBkZXZtX21mZF9hZGRfZGV2aWNlcyhkZXYsIFBMQVRGT1JNX0RFVklEX0FVVE8sIHZzYzc1MTJf ZGV2cywKPiArCQkJCSAgICBuZGV2cywgTlVMTCwgMCwgTlVMTCk7Cj4gK30KPiArRVhQT1JUX1NZ TUJPTF9OUyhvY2Vsb3RfY29yZV9pbml0LCBNRkRfT0NFTE9UKTsKPiArCj4gK01PRFVMRV9ERVND UklQVElPTigiRXh0ZXJuYWxseSBDb250cm9sbGVkIE9jZWxvdCBDaGlwIERyaXZlciIpOwo+ICtN T0RVTEVfQVVUSE9SKCJDb2xpbiBGb3N0ZXIgPGNvbGluLmZvc3RlckBpbi1hZHZhbnRhZ2UuY29t PiIpOwo+ICtNT0RVTEVfTElDRU5TRSgiR1BMIik7Cj4gK01PRFVMRV9JTVBPUlRfTlMoTUZEX09D RUxPVF9TUEkpOwo+IGRpZmYgLS1naXQgYS9kcml2ZXJzL21mZC9vY2Vsb3Qtc3BpLmMgYi9kcml2 ZXJzL21mZC9vY2Vsb3Qtc3BpLmMKPiBuZXcgZmlsZSBtb2RlIDEwMDY0NAo+IGluZGV4IDAwMDAw MDAwMDAwMC4uMGMxYzUyMTVjNzA2Cj4gLS0tIC9kZXYvbnVsbAo+ICsrKyBiL2RyaXZlcnMvbWZk L29jZWxvdC1zcGkuYwo+IEBAIC0wLDAgKzEsMzE3IEBACj4gKy8vIFNQRFgtTGljZW5zZS1JZGVu dGlmaWVyOiAoR1BMLTIuMCBPUiBNSVQpCj4gKy8qCj4gKyAqIFNQSSBjb3JlIGRyaXZlciBmb3Ig dGhlIE9jZWxvdCBjaGlwIGZhbWlseS4KPiArICoKPiArICogVGhpcyBkcml2ZXIgd2lsbCBoYW5k bGUgZXZlcnl0aGluZyBuZWNlc3NhcnkgdG8gYWxsb3cgZm9yIGNvbW11bmljYXRpb24gb3Zlcgo+ ICsgKiBTUEkgdG8gdGhlIFZTQzc1MTEsIFZTQzc1MTIsIFZTQzc1MTMgYW5kIFZTQzc1MTQgY2hp cHMuIFRoZSBtYWluIGZ1bmN0aW9ucwo+ICsgKiBhcmUgdG8gcHJlcGFyZSB0aGUgY2hpcCdzIFNQ SSBpbnRlcmZhY2UgZm9yIGEgc3BlY2lmaWMgYnVzIHNwZWVkLCBhbmQgYSBob3N0Cj4gKyAqIHBy b2Nlc3NvcidzIGVuZGlhbm5lc3MuIFRoaXMgd2lsbCBjcmVhdGUgYW5kIGRpc3RyaWJ1dGUgcmVn bWFwcyBmb3IgYW55Cj4gKyAqIGNoaWxkcmVuLgo+ICsgKgo+ICsgKiBDb3B5cmlnaHQgMjAyMSwg MjAyMiBJbm5vdmF0aXZlIEFkdmFudGFnZSBJbmMuCj4gKyAqCj4gKyAqIEF1dGhvcjogQ29saW4g Rm9zdGVyIDxjb2xpbi5mb3N0ZXJAaW4tYWR2YW50YWdlLmNvbT4KPiArICovCj4gKwo+ICsjaW5j bHVkZSA8bGludXgvaW9wb3J0Lmg+Cj4gKyNpbmNsdWRlIDxsaW51eC9rY29uZmlnLmg+Cj4gKyNp bmNsdWRlIDxsaW51eC9tb2R1bGUuaD4KPiArI2luY2x1ZGUgPGxpbnV4L3JlZ21hcC5oPgo+ICsj aW5jbHVkZSA8bGludXgvc3BpL3NwaS5oPgo+ICsKPiArI2luY2x1ZGUgPGFzbS9ieXRlb3JkZXIu aD4KPiArCj4gKyNpbmNsdWRlICJvY2Vsb3QuaCIKPiArCj4gKyNkZWZpbmUgUkVHX0RFVl9DUFVP UkdfSUZfQ1RSTAkJMHgwMDAwCj4gKyNkZWZpbmUgUkVHX0RFVl9DUFVPUkdfSUZfQ0ZHU1RBVAkw eDAwMDQKPiArCj4gKyNkZWZpbmUgQ0ZHU1RBVF9JRl9OVU1fVkNPUkUJCSgwIDw8IDI0KQo+ICsj ZGVmaW5lIENGR1NUQVRfSUZfTlVNX1ZSQVAJCSgxIDw8IDI0KQo+ICsjZGVmaW5lIENGR1NUQVRf SUZfTlVNX1NJCQkoMiA8PCAyNCkKPiArI2RlZmluZSBDRkdTVEFUX0lGX05VTV9NSUlNCQkoMyA8 PCAyNCkKPiArCj4gKyNkZWZpbmUgVlNDNzUxMl9ERVZDUFVfT1JHX1JFU19TVEFSVAkweDcxMDAw MDAwCj4gKyNkZWZpbmUgVlNDNzUxMl9ERVZDUFVfT1JHX1JFU19TSVpFCTB4MzgKPiArCj4gKyNk ZWZpbmUgVlNDNzUxMl9DSElQX1JFR1NfUkVTX1NUQVJUCTB4NzEwNzAwMDAKPiArI2RlZmluZSBW U0M3NTEyX0NISVBfUkVHU19SRVNfU0laRQkweDE0Cj4gKwo+ICtzdHJ1Y3Qgc3BpX2RldmljZTsK CldoeSBub3QganVzdCAjaW5jbHVkZT8KCj4gK3N0YXRpYyBjb25zdCBzdHJ1Y3QgcmVzb3VyY2Ug dnNjNzUxMl9kZXZfY3B1b3JnX3Jlc291cmNlID0KPiArCURFRklORV9SRVNfUkVHX05BTUVEKFZT Qzc1MTJfREVWQ1BVX09SR19SRVNfU1RBUlQsCj4gKwkJCSAgICAgVlNDNzUxMl9ERVZDUFVfT1JH X1JFU19TSVpFLAo+ICsJCQkgICAgICJkZXZjcHVfb3JnIik7Cj4gKwo+ICtzdGF0aWMgY29uc3Qg c3RydWN0IHJlc291cmNlIHZzYzc1MTJfZ2NiX3Jlc291cmNlID0KPiArCURFRklORV9SRVNfUkVH X05BTUVEKFZTQzc1MTJfQ0hJUF9SRUdTX1JFU19TVEFSVCwKPiArCQkJICAgICBWU0M3NTEyX0NI SVBfUkVHU19SRVNfU0laRSwKPiArCQkJICAgICAiZGV2Y3B1X2djYl9jaGlwX3JlZ3MiKTsKPiAr Cj4gK3N0YXRpYyBpbnQgb2NlbG90X3NwaV9pbml0aWFsaXplKHN0cnVjdCBkZXZpY2UgKmRldikK PiArewo+ICsJc3RydWN0IG9jZWxvdF9kZGF0YSAqZGRhdGEgPSBkZXZfZ2V0X2RydmRhdGEoZGV2 KTsKPiArCXUzMiB2YWwsIGNoZWNrOwo+ICsJaW50IGVycjsKPiArCj4gKwl2YWwgPSBPQ0VMT1Rf U1BJX0JZVEVfT1JERVI7Cj4gKwo+ICsJLyoKPiArCSAqIFRoZSBTUEkgYWRkcmVzcyBtdXN0IGJl IGJpZy1lbmRpYW4sIGJ1dCB3ZSB3YW50IHRoZSBwYXlsb2FkIHRvIG1hdGNoCj4gKwkgKiBvdXIg Q1BVLiBUaGVzZSBhcmUgdHdvIGJpdHMgKDAgYW5kIDEpIGJ1dCB0aGV5J3JlIHJlcGVhdGVkIHN1 Y2ggdGhhdAo+ICsJICogdGhlIHdyaXRlIGZyb20gYW55IGNvbmZpZ3VyYXRpb24gd2lsbCBiZSB2 YWxpZC4gVGhlIGZvdXIKPiArCSAqIGNvbmZpZ3VyYXRpb25zIGFyZToKPiArCSAqCj4gKwkgKiAw YjAwOiBsaXR0bGUtZW5kaWFuLCBNU0IgZmlyc3QKPiArCSAqIHwgICAgICAgICAgICAxMTExMTEg ICB8IDIyMjIxMTExIHwgMzMyMjIyMjIgfAo+ICsJICogfCA3NjU0MzIxMCB8IDU0MzIxMDk4IHwg MzIxMDk4NzYgfCAxMDk4NzY1NCB8Cj4gKwkgKgo+ICsJICogMGIwMTogYmlnLWVuZGlhbiwgTVNC IGZpcnN0Cj4gKwkgKiB8IDMzMjIyMjIyIHwgMjIyMjExMTEgfCAxMTExMTEgICB8ICAgICAgICAg IHwKPiArCSAqIHwgMTA5ODc2NTQgfCAzMjEwOTg3NiB8IDU0MzIxMDk4IHwgNzY1NDMyMTAgfAo+ ICsJICoKPiArCSAqIDBiMTA6IGxpdHRsZS1lbmRpYW4sIExTQiBmaXJzdAo+ICsJICogfCAgICAg ICAgICAgICAgMTExMTExIHwgMTExMTIyMjIgfCAyMjIyMjIzMyB8Cj4gKwkgKiB8IDAxMjM0NTY3 IHwgODkwMTIzNDUgfCA2Nzg5MDEyMyB8IDQ1Njc4OTAxIHwKPiArCSAqCj4gKwkgKiAwYjExOiBi aWctZW5kaWFuLCBMU0IgZmlyc3QKPiArCSAqIHwgMjIyMjIyMzMgfCAxMTExMjIyMiB8ICAgMTEx MTExIHwgICAgICAgICAgfAo+ICsJICogfCA0NTY3ODkwMSB8IDY3ODkwMTIzIHwgODkwMTIzNDUg fCAwMTIzNDU2NyB8Cj4gKwkgKi8KPiArCWVyciA9IHJlZ21hcF93cml0ZShkZGF0YS0+Y3B1b3Jn X3JlZ21hcCwgUkVHX0RFVl9DUFVPUkdfSUZfQ1RSTCwgdmFsKTsKPiArCWlmIChlcnIpCj4gKwkJ cmV0dXJuIGVycjsKPiArCj4gKwkvKgo+ICsJICogQXBwbHkgdGhlIG51bWJlciBvZiBwYWRkaW5n IGJ5dGVzIGJldHdlZW4gYSByZWFkIHJlcXVlc3QgYW5kIHRoZSBkYXRhCj4gKwkgKiBwYXlsb2Fk LiBTb21lIHJlZ2lzdGVycyBoYXZlIGFjY2VzcyB0aW1lcyBvZiB1cCB0byAxdXMsIHNvIGlmIHRo ZQo+ICsJICogZmlyc3QgcGF5bG9hZCBiaXQgaXMgc2hpZnRlZCBvdXQgdG9vIHF1aWNrbHksIHRo ZSByZWFkIHdpbGwgZmFpbC4KPiArCSAqLwo+ICsJdmFsID0gZGRhdGEtPnNwaV9wYWRkaW5nX2J5 dGVzOwo+ICsJZXJyID0gcmVnbWFwX3dyaXRlKGRkYXRhLT5jcHVvcmdfcmVnbWFwLCBSRUdfREVW X0NQVU9SR19JRl9DRkdTVEFULAo+ICsJCQkgICB2YWwpOwo+ICsJaWYgKGVycikKPiArCQlyZXR1 cm4gZXJyOwo+ICsKPiArCS8qCj4gKwkgKiBBZnRlciB3ZSB3cml0ZSB0aGUgaW50ZXJmYWNlIGNv bmZpZ3VyYXRpb24sIHJlYWQgaXQgYmFjayBoZXJlLiBUaGlzCj4gKwkgKiB3aWxsIHZlcmlmeSBz ZXZlcmFsIGRpZmZlcmVudCB0aGluZ3MuIFRoZSBmaXJzdCBpcyB0aGF0IHRoZSBudW1iZXIgb2YK PiArCSAqIHBhZGRpbmcgYnl0ZXMgYWN0dWFsbHkgZ290IHdyaXR0ZW4gY29ycmVjdGx5LiBUaGVz ZSBhcmUgZm91bmQgaW4gYml0cwo+ICsJICogMDozLgo+ICsJICoKPiArCSAqIFRoZSBzZWNvbmQg aXMgdGhhdCBiaXQgMTYgaXMgY2xlYXJlZC4gQml0IDE2IGlzIElGX0NGR1NUQVQ6SUZfU1RBVCwK PiArCSAqIGFuZCB3aWxsIGJlIHNldCBpZiB0aGUgcmVnaXN0ZXIgYWNjZXNzIGlzIHRvbyBmYXN0 LiBUaGlzIHdvdWxkIGJlIGluCj4gKwkgKiB0aGUgY29uZGl0aW9uIHRoYXQgdGhlIG51bWJlciBv ZiBwYWRkaW5nIGJ5dGVzIGlzIGluc3VmZmljaWVudCBmb3IKPiArCSAqIHRoZSBTUEkgYnVzIGZy ZXF1ZW5jeS4KPiArCSAqCj4gKwkgKiBUaGUgbGFzdCBjaGVjayBpcyBmb3IgYml0cyAzMToyNCwg d2hpY2ggZGVmaW5lIHRoZSBpbnRlcmZhY2UgYnkgd2hpY2gKPiArCSAqIHRoZSByZWdpc3RlcnMg YXJlIGJlaW5nIGFjY2Vzc2VkLiBTaW5jZSB3ZSdyZSBhY2Nlc3NpbmcgdGhlbSB2aWEgdGhlCj4g KwkgKiBzZXJpYWwgaW50ZXJmYWNlLCBpdCBtdXN0IHJldHVybiBJRl9OVU1fU0kuCj4gKwkgKi8K PiArCWNoZWNrID0gdmFsIHwgQ0ZHU1RBVF9JRl9OVU1fU0k7Cj4gKwo+ICsJZXJyID0gcmVnbWFw X3JlYWQoZGRhdGEtPmNwdW9yZ19yZWdtYXAsIFJFR19ERVZfQ1BVT1JHX0lGX0NGR1NUQVQsCj4g KwkJCSAgJnZhbCk7Cj4gKwlpZiAoZXJyKQo+ICsJCXJldHVybiBlcnI7Cj4gKwo+ICsJaWYgKGNo ZWNrICE9IHZhbCkKPiArCQlyZXR1cm4gLUVOT0RFVjsKPiArCj4gKwlyZXR1cm4gMDsKPiArfQo+ ICsKPiArc3RhdGljIGNvbnN0IHN0cnVjdCByZWdtYXBfY29uZmlnIG9jZWxvdF9zcGlfcmVnbWFw X2NvbmZpZyA9IHsKPiArCS5yZWdfYml0cyA9IDI0LAo+ICsJLnJlZ19zdHJpZGUgPSA0LAo+ICsJ LnJlZ19kb3duc2hpZnQgPSAyLAo+ICsJLnZhbF9iaXRzID0gMzIsCj4gKwo+ICsJLndyaXRlX2Zs YWdfbWFzayA9IDB4ODAsCj4gKwo+ICsJLnVzZV9zaW5nbGVfd3JpdGUgPSB0cnVlLAo+ICsJLmNh bl9tdWx0aV93cml0ZSA9IGZhbHNlLAo+ICsKPiArCS5yZWdfZm9ybWF0X2VuZGlhbiA9IFJFR01B UF9FTkRJQU5fQklHLAo+ICsJLnZhbF9mb3JtYXRfZW5kaWFuID0gUkVHTUFQX0VORElBTl9OQVRJ VkUsCj4gK307Cj4gKwo+ICtzdGF0aWMgaW50IG9jZWxvdF9zcGlfcmVnbWFwX2J1c19yZWFkKHZv aWQgKmNvbnRleHQsCj4gKwkJCQkgICAgICBjb25zdCB2b2lkICpyZWcsIHNpemVfdCByZWdfc2l6 ZSwKPiArCQkJCSAgICAgIHZvaWQgKnZhbCwgc2l6ZV90IHZhbF9zaXplKQo+ICt7Cj4gKwlzdHJ1 Y3Qgb2NlbG90X2RkYXRhICpkZGF0YSA9IGNvbnRleHQ7Cj4gKwlzdHJ1Y3Qgc3BpX3RyYW5zZmVy IHR4LCBwYWRkaW5nLCByeDsKPiArCXN0cnVjdCBzcGlfZGV2aWNlICpzcGkgPSBkZGF0YS0+c3Bp Owo+ICsJc3RydWN0IHNwaV9tZXNzYWdlIG1zZzsKPiArCj4gKwlzcGkgPSBkZGF0YS0+c3BpOwoK RHJvcCB0aGlzIGxpbmUuCgo+ICsJc3BpX21lc3NhZ2VfaW5pdCgmbXNnKTsKPiArCj4gKwltZW1z ZXQoJnR4LCAwLCBzaXplb2YodHgpKTsKPiArCj4gKwl0eC50eF9idWYgPSByZWc7Cj4gKwl0eC5s ZW4gPSByZWdfc2l6ZTsKPiArCj4gKwlzcGlfbWVzc2FnZV9hZGRfdGFpbCgmdHgsICZtc2cpOwo+ ICsKPiArCWlmIChkZGF0YS0+c3BpX3BhZGRpbmdfYnl0ZXMpIHsKPiArCQltZW1zZXQoJnBhZGRp bmcsIDAsIHNpemVvZihwYWRkaW5nKSk7Cj4gKwo+ICsJCXBhZGRpbmcubGVuID0gZGRhdGEtPnNw aV9wYWRkaW5nX2J5dGVzOwo+ICsJCXBhZGRpbmcudHhfYnVmID0gZGRhdGEtPmR1bW15X2J1ZjsK PiArCQlwYWRkaW5nLmR1bW15X2RhdGEgPSAxOwo+ICsKPiArCQlzcGlfbWVzc2FnZV9hZGRfdGFp bCgmcGFkZGluZywgJm1zZyk7Cj4gKwl9Cj4gKwo+ICsJbWVtc2V0KCZyeCwgMCwgc2l6ZW9mKHJ4 KSk7Cj4gKwlyeC5yeF9idWYgPSB2YWw7Cj4gKwlyeC5sZW4gPSB2YWxfc2l6ZTsKPiArCj4gKwlz cGlfbWVzc2FnZV9hZGRfdGFpbCgmcngsICZtc2cpOwo+ICsKPiArCXJldHVybiBzcGlfc3luYyhz cGksICZtc2cpOwo+ICt9Cj4gKwo+ICtzdGF0aWMgaW50IG9jZWxvdF9zcGlfcmVnbWFwX2J1c193 cml0ZSh2b2lkICpjb250ZXh0LCBjb25zdCB2b2lkICpkYXRhLAo+ICsJCQkJICAgICAgIHNpemVf dCBjb3VudCkKPiArewo+ICsJc3RydWN0IG9jZWxvdF9kZGF0YSAqZGRhdGEgPSBjb250ZXh0Owo+ ICsJc3RydWN0IHNwaV9kZXZpY2UgKnNwaSA9IGRkYXRhLT5zcGk7Cj4gKwo+ICsJcmV0dXJuIHNw aV93cml0ZShzcGksIGRhdGEsIGNvdW50KTsKPiArfQo+ICsKPiArc3RhdGljIGNvbnN0IHN0cnVj dCByZWdtYXBfYnVzIG9jZWxvdF9zcGlfcmVnbWFwX2J1cyA9IHsKPiArCS53cml0ZSA9IG9jZWxv dF9zcGlfcmVnbWFwX2J1c193cml0ZSwKPiArCS5yZWFkID0gb2NlbG90X3NwaV9yZWdtYXBfYnVz X3JlYWQsCj4gK307Cj4gKwo+ICtzdHJ1Y3QgcmVnbWFwICoKPiArb2NlbG90X3NwaV9pbml0X3Jl Z21hcChzdHJ1Y3QgZGV2aWNlICpkZXYsIGNvbnN0IHN0cnVjdCByZXNvdXJjZSAqcmVzKQoKT25l IGxpbmUsIGFsb25nIHdpdGggYWxsIHRoZSBvdGhlcnMuCgo+ICt7Cj4gKwlzdHJ1Y3Qgb2NlbG90 X2RkYXRhICpkZGF0YSA9IGRldl9nZXRfZHJ2ZGF0YShkZXYpOwo+ICsJc3RydWN0IHJlZ21hcF9j b25maWcgcmVnbWFwX2NvbmZpZzsKPiArCj4gKwltZW1jcHkoJnJlZ21hcF9jb25maWcsICZvY2Vs b3Rfc3BpX3JlZ21hcF9jb25maWcsCj4gKwkgICAgICAgc2l6ZW9mKHJlZ21hcF9jb25maWcpKTsK PiArCj4gKwlyZWdtYXBfY29uZmlnLm5hbWUgPSByZXMtPm5hbWU7Cj4gKwlyZWdtYXBfY29uZmln Lm1heF9yZWdpc3RlciA9IHJlcy0+ZW5kIC0gcmVzLT5zdGFydDsKPiArCXJlZ21hcF9jb25maWcu cmVnX2Jhc2UgPSByZXMtPnN0YXJ0Owo+ICsKPiArCXJldHVybiBkZXZtX3JlZ21hcF9pbml0KGRl diwgJm9jZWxvdF9zcGlfcmVnbWFwX2J1cywgZGRhdGEsCj4gKwkJCQkmcmVnbWFwX2NvbmZpZyk7 Cj4gK30KPiArRVhQT1JUX1NZTUJPTF9OUyhvY2Vsb3Rfc3BpX2luaXRfcmVnbWFwLCBNRkRfT0NF TE9UX1NQSSk7Cj4gKwo+ICtzdGF0aWMgaW50IG9jZWxvdF9zcGlfcHJvYmUoc3RydWN0IHNwaV9k ZXZpY2UgKnNwaSkKPiArewo+ICsJc3RydWN0IGRldmljZSAqZGV2ID0gJnNwaS0+ZGV2Owo+ICsJ c3RydWN0IG9jZWxvdF9kZGF0YSAqZGRhdGE7Cj4gKwlzdHJ1Y3QgcmVnbWFwICpyOwo+ICsJaW50 IGVycjsKPiArCj4gKwlkZGF0YSA9IGRldm1fa3phbGxvYyhkZXYsIHNpemVvZigqZGRhdGEpLCBH RlBfS0VSTkVMKTsKPiArCWlmICghZGRhdGEpCj4gKwkJcmV0dXJuIC1FTk9NRU07Cj4gKwo+ICsJ ZGRhdGEtPmRldiA9IGRldjsKCkhvdyBhcmUgeW91IGZldGNoaW5nIGRkYXRhIGlmIHlvdSBkb24n dCBhbHJlYWR5IGhhdmUgJ2Rldic/Cgo+ICsJZGV2X3NldF9kcnZkYXRhKGRldiwgZGRhdGEpOwoK VGhpcyBzaG91bGQgdXNlIHRoZSBzcGlfKiB2YXJpYW50LgoKPiArCWlmIChzcGktPm1heF9zcGVl ZF9oeiA8PSA1MDAwMDApIHsKPiArCQlkZGF0YS0+c3BpX3BhZGRpbmdfYnl0ZXMgPSAwOwo+ICsJ fSBlbHNlIHsKPiArCQkvKgo+ICsJCSAqIENhbGN1bGF0aW9uIHRha2VuIGZyb20gdGhlIG1hbnVh bCBmb3IgSUZfQ0ZHU1RBVDpJRl9DRkcuCj4gKwkJICogUmVnaXN0ZXIgYWNjZXNzIHRpbWUgaXMg MXVzLCBzbyB3ZSBuZWVkIHRvIGNvbmZpZ3VyZSBhbmQgc2VuZAo+ICsJCSAqIG91dCBlbm91Z2gg cGFkZGluZyBieXRlcyBiZXR3ZWVuIHRoZSByZWFkIHJlcXVlc3QgYW5kIGRhdGEKPiArCQkgKiB0 cmFuc21pc3Npb24gdGhhdCBsYXN0cyBhdCBsZWFzdCAxIG1pY3Jvc2Vjb25kLgo+ICsJCSAqLwo+ ICsJCWRkYXRhLT5zcGlfcGFkZGluZ19ieXRlcyA9IDEgKwo+ICsJCQkoc3BpLT5tYXhfc3BlZWRf aHogLyAxMDAwMDAwICsgMikgLyA4Owo+ICsKPiArCQlkZGF0YS0+ZHVtbXlfYnVmID0gZGV2bV9r emFsbG9jKGRldiwgZGRhdGEtPnNwaV9wYWRkaW5nX2J5dGVzLAo+ICsJCQkJCQlHRlBfS0VSTkVM KTsKPiArCQlpZiAoIWRkYXRhLT5kdW1teV9idWYpCj4gKwkJCXJldHVybiAtRU5PTUVNOwo+ICsJ fQo+ICsKPiArCWRkYXRhLT5zcGkgPSBzcGk7CgpJZiB5b3UgaGF2ZSAnc3BpJyB5b3UgZGVmaW5p dGVseSBkbyBub3QgbmVlZCAnZGV2Jy4KCllvdSBjYW4gZGVyaXZlIG9uZSBmcm9tIHRoZSBvdGhl ci4KCj4gKwlzcGktPmJpdHNfcGVyX3dvcmQgPSA4Owo+ICsKPiArCWVyciA9IHNwaV9zZXR1cChz cGkpOwo+ICsJaWYgKGVyciA8IDApCj4gKwkJcmV0dXJuIGRldl9lcnJfcHJvYmUoJnNwaS0+ZGV2 LCBlcnIsCj4gKwkJCQkgICAgICJFcnJvciBwZXJmb3JtaW5nIFNQSSBzZXR1cFxuIik7Cj4gKwo+ ICsJciA9IG9jZWxvdF9zcGlfaW5pdF9yZWdtYXAoZGV2LCAmdnNjNzUxMl9kZXZfY3B1b3JnX3Jl c291cmNlKTsKPiArCWlmIChJU19FUlIocikpCj4gKwkJcmV0dXJuIFBUUl9FUlIocik7Cj4gKwo+ ICsJZGRhdGEtPmNwdW9yZ19yZWdtYXAgPSByOwo+ICsKPiArCXIgPSBvY2Vsb3Rfc3BpX2luaXRf cmVnbWFwKGRldiwgJnZzYzc1MTJfZ2NiX3Jlc291cmNlKTsKPiArCWlmIChJU19FUlIocikpCj4g KwkJcmV0dXJuIFBUUl9FUlIocik7Cj4gKwo+ICsJZGRhdGEtPmdjYl9yZWdtYXAgPSByOwo+ICsK PiArCS8qCj4gKwkgKiBUaGUgY2hpcCBtdXN0IGJlIHNldCB1cCBmb3IgU1BJIGJlZm9yZSBpdCBn ZXRzIGluaXRpYWxpemVkIGFuZCByZXNldC4KPiArCSAqIFRoaXMgbXVzdCBiZSBkb25lIGJlZm9y ZSBjYWxsaW5nIGluaXQsIGFuZCBhZnRlciBhIGNoaXAgcmVzZXQgaXMKPiArCSAqIHBlcmZvcm1l ZC4KPiArCSAqLwo+ICsJZXJyID0gb2NlbG90X3NwaV9pbml0aWFsaXplKGRldik7Cj4gKwlpZiAo ZXJyKQo+ICsJCXJldHVybiBkZXZfZXJyX3Byb2JlKGRldiwgZXJyLCAiRXJyb3IgaW5pdGlhbGl6 aW5nIFNQSSBidXNcbiIpOwo+ICsKPiArCWVyciA9IG9jZWxvdF9jaGlwX3Jlc2V0KGRldik7Cj4g KwlpZiAoZXJyKQo+ICsJCXJldHVybiBkZXZfZXJyX3Byb2JlKGRldiwgZXJyLCAiRXJyb3IgcmVz ZXR0aW5nIGRldmljZVxuIik7Cj4gKwo+ICsJLyoKPiArCSAqIEEgY2hpcCByZXNldCB3aWxsIGNs ZWFyIHRoZSBTUEkgY29uZmlndXJhdGlvbiwgc28gaXQgbmVlZHMgdG8gYmUgZG9uZQo+ICsJICog YWdhaW4gYmVmb3JlIHdlIGNhbiBhY2Nlc3MgYW55IHJlZ2lzdGVycwo+ICsJICovCj4gKwllcnIg PSBvY2Vsb3Rfc3BpX2luaXRpYWxpemUoZGV2KTsKPiArCWlmIChlcnIpCj4gKwkJcmV0dXJuIGRl dl9lcnJfcHJvYmUoZGV2LCBlcnIsCj4gKwkJCQkgICAgICJFcnJvciBpbml0aWFsaXppbmcgU1BJ IGJ1cyBhZnRlciByZXNldFxuIik7Cj4gKwo+ICsJZXJyID0gb2NlbG90X2NvcmVfaW5pdChkZXYp Owo+ICsJaWYgKGVyciA8IDApCj4gKwkJcmV0dXJuIGRldl9lcnJfcHJvYmUoZGV2LCBlcnIsCj4g KwkJCQkgICAgICJFcnJvciBpbml0aWFsaXppbmcgT2NlbG90IGNvcmVcbiIpOwo+ICsKPiArCXJl dHVybiAwOwo+ICt9Cj4gKwo+ICtzdGF0aWMgY29uc3Qgc3RydWN0IHNwaV9kZXZpY2VfaWQgb2Nl bG90X3NwaV9pZHNbXSA9IHsKPiArCXsgInZzYzc1MTIiLCAwIH0sCj4gKwl7IH0KPiArfTsKPiAr Cj4gK3N0YXRpYyBjb25zdCBzdHJ1Y3Qgb2ZfZGV2aWNlX2lkIG9jZWxvdF9zcGlfb2ZfbWF0Y2hb XSA9IHsKPiArCXsgLmNvbXBhdGlibGUgPSAibXNjYyx2c2M3NTEyIiB9LAo+ICsJeyB9Cj4gK307 Cj4gK01PRFVMRV9ERVZJQ0VfVEFCTEUob2YsIG9jZWxvdF9zcGlfb2ZfbWF0Y2gpOwo+ICsKPiAr c3RhdGljIHN0cnVjdCBzcGlfZHJpdmVyIG9jZWxvdF9zcGlfZHJpdmVyID0gewo+ICsJLmRyaXZl ciA9IHsKPiArCQkubmFtZSA9ICJvY2Vsb3Qtc29jIiwKPiArCQkub2ZfbWF0Y2hfdGFibGUgPSBv Y2Vsb3Rfc3BpX29mX21hdGNoLAo+ICsJfSwKPiArCS5pZF90YWJsZSA9IG9jZWxvdF9zcGlfaWRz LAo+ICsJLnByb2JlID0gb2NlbG90X3NwaV9wcm9iZSwKPiArfTsKPiArbW9kdWxlX3NwaV9kcml2 ZXIob2NlbG90X3NwaV9kcml2ZXIpOwo+ICsKPiArTU9EVUxFX0RFU0NSSVBUSU9OKCJTUEkgQ29u dHJvbGxlZCBPY2Vsb3QgQ2hpcCBEcml2ZXIiKTsKPiArTU9EVUxFX0FVVEhPUigiQ29saW4gRm9z dGVyIDxjb2xpbi5mb3N0ZXJAaW4tYWR2YW50YWdlLmNvbT4iKTsKPiArTU9EVUxFX0xJQ0VOU0Uo IkR1YWwgTUlUL0dQTCIpOwo+ICtNT0RVTEVfSU1QT1JUX05TKE1GRF9PQ0VMT1QpOwo+IGRpZmYg LS1naXQgYS9kcml2ZXJzL21mZC9vY2Vsb3QuaCBiL2RyaXZlcnMvbWZkL29jZWxvdC5oCj4gbmV3 IGZpbGUgbW9kZSAxMDA2NDQKPiBpbmRleCAwMDAwMDAwMDAwMDAuLmM4NmJkNjk5MGEzYwo+IC0t LSAvZGV2L251bGwKPiArKysgYi9kcml2ZXJzL21mZC9vY2Vsb3QuaAo+IEBAIC0wLDAgKzEsMzQg QEAKPiArLyogU1BEWC1MaWNlbnNlLUlkZW50aWZpZXI6IEdQTC0yLjAgT1IgTUlUICovCj4gKy8q IENvcHlyaWdodCAyMDIxLCAyMDIyIElubm92YXRpdmUgQWR2YW50YWdlIEluYy4gKi8KPiArCj4g KyNpbmNsdWRlIDxhc20vYnl0ZW9yZGVyLmg+Cj4gKwo+ICtzdHJ1Y3QgZGV2aWNlOwo+ICtzdHJ1 Y3Qgc3BpX2RldmljZTsKPiArc3RydWN0IHJlZ21hcDsKPiArc3RydWN0IHJlc291cmNlOwo+ICsK PiArc3RydWN0IG9jZWxvdF9kZGF0YSB7Cj4gKwlzdHJ1Y3QgZGV2aWNlICpkZXY7Cj4gKwlzdHJ1 Y3QgcmVnbWFwICpnY2JfcmVnbWFwOwo+ICsJc3RydWN0IHJlZ21hcCAqY3B1b3JnX3JlZ21hcDsK PiArCWludCBzcGlfcGFkZGluZ19ieXRlczsKPiArCXN0cnVjdCBzcGlfZGV2aWNlICpzcGk7Cj4g Kwl2b2lkICpkdW1teV9idWY7Cj4gK307CgpUaGlzIGxvb2tzIGxpa2UgaXQgZGVzZXJ2ZXMgYSBk b2MgaGVhZGVyLgoKPiAraW50IG9jZWxvdF9jaGlwX3Jlc2V0KHN0cnVjdCBkZXZpY2UgKmRldik7 Cj4gK2ludCBvY2Vsb3RfY29yZV9pbml0KHN0cnVjdCBkZXZpY2UgKmRldik7Cj4gKwo+ICsvKiBT UEktc3BlY2lmaWMgcm91dGluZXMgdGhhdCB3b24ndCBiZSBuZWNlc3NhcnkgZm9yIG90aGVyIGlu dGVyZmFjZXMgKi8KPiArc3RydWN0IHJlZ21hcCAqb2NlbG90X3NwaV9pbml0X3JlZ21hcChzdHJ1 Y3QgZGV2aWNlICpkZXYsCj4gKwkJCQkgICAgICBjb25zdCBzdHJ1Y3QgcmVzb3VyY2UgKnJlcyk7 Cj4gKwo+ICsjZGVmaW5lIE9DRUxPVF9TUElfQllURV9PUkRFUl9MRSAweDAwMDAwMDAwCj4gKyNk ZWZpbmUgT0NFTE9UX1NQSV9CWVRFX09SREVSX0JFIDB4ODE4MTgxODEKPiArCj4gKyNpZmRlZiBf X0xJVFRMRV9FTkRJQU4KPiArI2RlZmluZSBPQ0VMT1RfU1BJX0JZVEVfT1JERVIgT0NFTE9UX1NQ SV9CWVRFX09SREVSX0xFCj4gKyNlbHNlCj4gKyNkZWZpbmUgT0NFTE9UX1NQSV9CWVRFX09SREVS IE9DRUxPVF9TUElfQllURV9PUkRFUl9CRQo+ICsjZW5kaWYKCi0tIApMZWUgSm9uZXMgW+adjueQ vOaWr10KUHJpbmNpcGFsIFRlY2huaWNhbCBMZWFkIC0gRGV2ZWxvcGVyIFNlcnZpY2VzCkxpbmFy by5vcmcg4pSCIE9wZW4gc291cmNlIHNvZnR3YXJlIGZvciBBcm0gU29DcwpGb2xsb3cgTGluYXJv OiBGYWNlYm9vayB8IFR3aXR0ZXIgfCBCbG9nCgpfX19fX19fX19fX19fX19fX19fX19fX19fX19f X19fX19fX19fX19fX19fX19fXwpsaW51eC1hcm0ta2VybmVsIG1haWxpbmcgbGlzdApsaW51eC1h cm0ta2VybmVsQGxpc3RzLmluZnJhZGVhZC5vcmcKaHR0cDovL2xpc3RzLmluZnJhZGVhZC5vcmcv bWFpbG1hbi9saXN0aW5mby9saW51eC1hcm0ta2VybmVsCg==