| From b152bbeb0282bfcf6f91d0d5befd7582c1c3fc23 Mon Sep 17 00:00:00 2001 |
| From: =?UTF-8?q?Rafa=C5=82=20Mi=C5=82ecki?= <rafal@milecki.pl> |
| Date: Fri, 5 Mar 2021 19:32:36 +0100 |
| Subject: [PATCH] nvmem: brcm_nvram: new driver exposing Broadcom's NVRAM |
| MIME-Version: 1.0 |
| Content-Type: text/plain; charset=UTF-8 |
| Content-Transfer-Encoding: 8bit |
| |
| This driver provides access to Broadcom's NVRAM. |
| |
| Signed-off-by: Rafał Miłecki <rafal@milecki.pl> |
| Signed-off-by: Srinivas Kandagatla <srinivas.kandagatla@linaro.org> |
| --- |
| drivers/nvmem/Kconfig | 9 +++++ |
| drivers/nvmem/Makefile | 2 + |
| drivers/nvmem/brcm_nvram.c | 78 ++++++++++++++++++++++++++++++++++++++ |
| 3 files changed, 89 insertions(+) |
| create mode 100644 drivers/nvmem/brcm_nvram.c |
| |
| --- a/drivers/nvmem/Kconfig |
| +++ b/drivers/nvmem/Kconfig |
| @@ -243,4 +243,12 @@ config NVMEM_U_BOOT_ENV |
| |
| If compiled as module it will be called nvmem_u-boot-env. |
| |
| +config NVMEM_BRCM_NVRAM |
| + tristate "Broadcom's NVRAM support" |
| + depends on ARCH_BCM_5301X || COMPILE_TEST |
| + depends on HAS_IOMEM |
| + help |
| + This driver provides support for Broadcom's NVRAM that can be accessed |
| + using I/O mapping. |
| + |
| endif |
| --- a/drivers/nvmem/Makefile |
| +++ b/drivers/nvmem/Makefile |
| @@ -52,3 +52,5 @@ obj-$(CONFIG_NVMEM_ZYNQMP) += nvmem_zynq |
| nvmem_zynqmp_nvmem-y := zynqmp_nvmem.o |
| obj-$(CONFIG_NVMEM_U_BOOT_ENV) += nvmem_u-boot-env.o |
| nvmem_u-boot-env-y := u-boot-env.o |
| +obj-$(CONFIG_NVMEM_BRCM_NVRAM) += nvmem_brcm_nvram.o |
| +nvmem_brcm_nvram-y := brcm_nvram.o |
| --- /dev/null |
| +++ b/drivers/nvmem/brcm_nvram.c |
| @@ -0,0 +1,78 @@ |
| +// SPDX-License-Identifier: GPL-2.0-only |
| +/* |
| + * Copyright (C) 2021 Rafał Miłecki <rafal@milecki.pl> |
| + */ |
| + |
| +#include <linux/io.h> |
| +#include <linux/mod_devicetable.h> |
| +#include <linux/module.h> |
| +#include <linux/nvmem-provider.h> |
| +#include <linux/platform_device.h> |
| + |
| +struct brcm_nvram { |
| + struct device *dev; |
| + void __iomem *base; |
| +}; |
| + |
| +static int brcm_nvram_read(void *context, unsigned int offset, void *val, |
| + size_t bytes) |
| +{ |
| + struct brcm_nvram *priv = context; |
| + u8 *dst = val; |
| + |
| + while (bytes--) |
| + *dst++ = readb(priv->base + offset++); |
| + |
| + return 0; |
| +} |
| + |
| +static int brcm_nvram_probe(struct platform_device *pdev) |
| +{ |
| + struct nvmem_config config = { |
| + .name = "brcm-nvram", |
| + .reg_read = brcm_nvram_read, |
| + }; |
| + struct device *dev = &pdev->dev; |
| + struct resource *res; |
| + struct brcm_nvram *priv; |
| + |
| + priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); |
| + if (!priv) |
| + return -ENOMEM; |
| + priv->dev = dev; |
| + |
| + res = platform_get_resource(pdev, IORESOURCE_MEM, 0); |
| + priv->base = devm_ioremap_resource(dev, res); |
| + if (IS_ERR(priv->base)) |
| + return PTR_ERR(priv->base); |
| + |
| + config.dev = dev; |
| + config.priv = priv; |
| + config.size = resource_size(res); |
| + |
| + return PTR_ERR_OR_ZERO(devm_nvmem_register(dev, &config)); |
| +} |
| + |
| +static const struct of_device_id brcm_nvram_of_match_table[] = { |
| + { .compatible = "brcm,nvram", }, |
| + {}, |
| +}; |
| + |
| +static struct platform_driver brcm_nvram_driver = { |
| + .probe = brcm_nvram_probe, |
| + .driver = { |
| + .name = "brcm_nvram", |
| + .of_match_table = brcm_nvram_of_match_table, |
| + }, |
| +}; |
| + |
| +static int __init brcm_nvram_init(void) |
| +{ |
| + return platform_driver_register(&brcm_nvram_driver); |
| +} |
| + |
| +subsys_initcall_sync(brcm_nvram_init); |
| + |
| +MODULE_AUTHOR("Rafał Miłecki"); |
| +MODULE_LICENSE("GPL"); |
| +MODULE_DEVICE_TABLE(of, brcm_nvram_of_match_table); |