forked from Minki/linux
mtd: phram: Allow probing via reserved-memory
Allow phram to be probed from the devicetree. It expects to be in a reserved-memory node as documented by the bindings. This allows things like partitioning to be specified via the devicetree. Signed-off-by: Vincent Whitchurch <vincent.whitchurch@axis.com> Acked-by: Rob Herring <robh@kernel.org> Signed-off-by: Miquel Raynal <miquel.raynal@bootlin.com> Link: https://lore.kernel.org/linux-mtd/20220412135302.1682890-4-vincent.whitchurch@axis.com
This commit is contained in:
parent
4e96945960
commit
7090d2f1d6
@ -27,6 +27,9 @@
|
||||
#include <linux/slab.h>
|
||||
#include <linux/mtd/mtd.h>
|
||||
#include <asm/div64.h>
|
||||
#include <linux/platform_device.h>
|
||||
#include <linux/of_address.h>
|
||||
#include <linux/of.h>
|
||||
|
||||
struct phram_mtd_list {
|
||||
struct mtd_info mtd;
|
||||
@ -89,8 +92,10 @@ static void unregister_devices(void)
|
||||
}
|
||||
}
|
||||
|
||||
static int register_device(char *name, phys_addr_t start, size_t len, uint32_t erasesize)
|
||||
static int register_device(struct platform_device *pdev, const char *name,
|
||||
phys_addr_t start, size_t len, uint32_t erasesize)
|
||||
{
|
||||
struct device_node *np = pdev ? pdev->dev.of_node : NULL;
|
||||
struct phram_mtd_list *new;
|
||||
int ret = -ENOMEM;
|
||||
|
||||
@ -119,13 +124,19 @@ static int register_device(char *name, phys_addr_t start, size_t len, uint32_t e
|
||||
new->mtd.erasesize = erasesize;
|
||||
new->mtd.writesize = 1;
|
||||
|
||||
mtd_set_of_node(&new->mtd, np);
|
||||
|
||||
ret = -EAGAIN;
|
||||
if (mtd_device_register(&new->mtd, NULL, 0)) {
|
||||
pr_err("Failed to register new device\n");
|
||||
goto out2;
|
||||
}
|
||||
|
||||
list_add_tail(&new->list, &phram_list);
|
||||
if (pdev)
|
||||
platform_set_drvdata(pdev, new);
|
||||
else
|
||||
list_add_tail(&new->list, &phram_list);
|
||||
|
||||
return 0;
|
||||
|
||||
out2:
|
||||
@ -278,7 +289,7 @@ static int phram_setup(const char *val)
|
||||
goto error;
|
||||
}
|
||||
|
||||
ret = register_device(name, start, len, (uint32_t)erasesize);
|
||||
ret = register_device(NULL, name, start, len, (uint32_t)erasesize);
|
||||
if (ret)
|
||||
goto error;
|
||||
|
||||
@ -325,10 +336,54 @@ static int phram_param_call(const char *val, const struct kernel_param *kp)
|
||||
module_param_call(phram, phram_param_call, NULL, NULL, 0200);
|
||||
MODULE_PARM_DESC(phram, "Memory region to map. \"phram=<name>,<start>,<length>[,<erasesize>]\"");
|
||||
|
||||
#ifdef CONFIG_OF
|
||||
static const struct of_device_id phram_of_match[] = {
|
||||
{ .compatible = "phram" },
|
||||
{}
|
||||
};
|
||||
MODULE_DEVICE_TABLE(of, phram_of_match);
|
||||
#endif
|
||||
|
||||
static int phram_probe(struct platform_device *pdev)
|
||||
{
|
||||
struct resource *res;
|
||||
|
||||
res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
|
||||
if (!res)
|
||||
return -ENOMEM;
|
||||
|
||||
/* mtd_set_of_node() reads name from "label" */
|
||||
return register_device(pdev, NULL, res->start, resource_size(res),
|
||||
PAGE_SIZE);
|
||||
}
|
||||
|
||||
static int phram_remove(struct platform_device *pdev)
|
||||
{
|
||||
struct phram_mtd_list *phram = platform_get_drvdata(pdev);
|
||||
|
||||
mtd_device_unregister(&phram->mtd);
|
||||
iounmap(phram->mtd.priv);
|
||||
kfree(phram);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
static struct platform_driver phram_driver = {
|
||||
.probe = phram_probe,
|
||||
.remove = phram_remove,
|
||||
.driver = {
|
||||
.name = "phram",
|
||||
.of_match_table = of_match_ptr(phram_of_match),
|
||||
},
|
||||
};
|
||||
|
||||
static int __init init_phram(void)
|
||||
{
|
||||
int ret = 0;
|
||||
int ret;
|
||||
|
||||
ret = platform_driver_register(&phram_driver);
|
||||
if (ret)
|
||||
return ret;
|
||||
|
||||
#ifndef MODULE
|
||||
if (phram_paramline[0])
|
||||
@ -336,12 +391,16 @@ static int __init init_phram(void)
|
||||
phram_init_called = 1;
|
||||
#endif
|
||||
|
||||
if (ret)
|
||||
platform_driver_unregister(&phram_driver);
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
static void __exit cleanup_phram(void)
|
||||
{
|
||||
unregister_devices();
|
||||
platform_driver_unregister(&phram_driver);
|
||||
}
|
||||
|
||||
module_init(init_phram);
|
||||
|
@ -509,6 +509,7 @@ EXPORT_SYMBOL_GPL(of_platform_default_populate);
|
||||
|
||||
#ifndef CONFIG_PPC
|
||||
static const struct of_device_id reserved_mem_matches[] = {
|
||||
{ .compatible = "phram" },
|
||||
{ .compatible = "qcom,rmtfs-mem" },
|
||||
{ .compatible = "qcom,cmd-db" },
|
||||
{ .compatible = "qcom,smem" },
|
||||
|
Loading…
Reference in New Issue
Block a user