* [PATCH,RFC] convert physmap to platform driver
@ 2006-02-12 17:04 Lennert Buytenhek
2006-02-21 13:51 ` Lennert Buytenhek
2006-02-28 19:16 ` [less intrusive PATCH,RFC] don't load physmap if length is zero Lennert Buytenhek
0 siblings, 2 replies; 8+ messages in thread
From: Lennert Buytenhek @ 2006-02-12 17:04 UTC (permalink / raw)
To: linux-mtd; +Cc: dwmw2
Hi!
After dwmw2 let me know it ought to be done, I rewrote the physmap map
driver to be a platform driver. I know zilch about the driver model,
so I probably botched it in some way, but I've done some tests on an
ixp23xx board which uses physmap, and it all seems to work.
In order to not break existing physmap users, I've added some compat
code that will instantiate a platform device iff CONFIG_MTD_PHYSMAP_LEN
is defined and != 0. Also, I've changed the default value for
CONFIG_MTD_PHYSMAP_LEN to zero, so that people who inadvertently
compile in physmap (or new, platform-style, users of physmap) don't get
burned.
This works pretty well -- the new physmap driver is a drop-in replacement
for the old one, and works on said ixp23xx board without any code changes
needed. (This should hold as long as users don't touch 'physmap_map'
directly.)
Once all physmap users have been converted to instantiate their own
platform devices, the compat code can go. (Or we decide that we can
change all the in-tree users at the same time, and never merge the
compat code.)
Comments?
cheers,
Lennert
Signed-off-by: Lennert Buytenhek <buytenh@wantstofly.org>
diff -ur linux-2.6.16-rc2.orig/drivers/mtd/maps/Kconfig linux-2.6.16-rc2/drivers/mtd/maps/Kconfig
--- linux-2.6.16-rc2.orig/drivers/mtd/maps/Kconfig 2006-02-09 14:50:49.000000000 +0100
+++ linux-2.6.16-rc2/drivers/mtd/maps/Kconfig 2006-02-12 17:57:28.000000000 +0100
@@ -37,7 +37,7 @@
config MTD_PHYSMAP_LEN
hex "Physical length of flash mapping"
depends on MTD_PHYSMAP
- default "0x4000000"
+ default "0"
help
This is the total length of the mapping of the flash chips on
your particular board. If there is space, or aliases, in the
diff -ur linux-2.6.16-rc2.orig/drivers/mtd/maps/physmap.c linux-2.6.16-rc2/drivers/mtd/maps/physmap.c
--- linux-2.6.16-rc2.orig/drivers/mtd/maps/physmap.c 2006-02-09 14:50:49.000000000 +0100
+++ linux-2.6.16-rc2/drivers/mtd/maps/physmap.c 2006-02-12 17:58:23.000000000 +0100
@@ -14,112 +12,230 @@
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/slab.h>
-#include <asm/io.h>
+#include <linux/device.h>
+#include <linux/platform_device.h>
#include <linux/mtd/mtd.h>
#include <linux/mtd/map.h>
#include <linux/config.h>
#include <linux/mtd/partitions.h>
#include <linux/mtd/physmap.h>
+#include <asm/io.h>
+#include <asm/mach/flash.h>
-static struct mtd_info *mymtd;
-
-struct map_info physmap_map = {
- .name = "phys_mapped_flash",
- .phys = CONFIG_MTD_PHYSMAP_START,
- .size = CONFIG_MTD_PHYSMAP_LEN,
- .bankwidth = CONFIG_MTD_PHYSMAP_BANKWIDTH,
+struct physmap_flash_info {
+ struct mtd_info *mtd;
+ struct map_info map;
+ struct resource *res;
+#ifdef CONFIG_MTD_PARTITIONS
+ int nr_parts;
+ struct mtd_partition *parts;
+#endif
};
+
+static int physmap_flash_remove(struct platform_device *dev)
+{
+ struct physmap_flash_info *info;
+ struct physmap_flash_data *physmap_data;
+
+ info = platform_get_drvdata(dev);
+ if (info == NULL)
+ return 0;
+ platform_set_drvdata(dev, NULL);
+
+ physmap_data = dev->dev.platform_data;
+
+ if (info->mtd != NULL) {
#ifdef CONFIG_MTD_PARTITIONS
-static struct mtd_partition *mtd_parts;
-static int mtd_parts_nb;
+ if (info->nr_parts) {
+ del_mtd_partitions(info->mtd);
+ kfree(info->parts);
+ } else if (physmap_data->nr_parts) {
+ del_mtd_partitions(info->mtd);
+ } else {
+ del_mtd_device(info->mtd);
+ }
+#else
+ del_mtd_device(info->mtd);
+#endif
+ map_destroy(info->mtd);
+ }
-static int num_physmap_partitions;
-static struct mtd_partition *physmap_partitions;
+ if (info->map.virt != NULL)
+ iounmap((void *)info->map.virt);
-static const char *part_probes[] __initdata = {"cmdlinepart", "RedBoot", NULL};
+ if (info->res != NULL) {
+ release_resource(info->res);
+ kfree(info->res);
+ }
-void physmap_set_partitions(struct mtd_partition *parts, int num_parts)
-{
- physmap_partitions=parts;
- num_physmap_partitions=num_parts;
+ return 0;
}
-#endif /* CONFIG_MTD_PARTITIONS */
-static int __init init_physmap(void)
+static const char *rom_probe_types[] = { "cfi_probe", "jedec_probe", "map_rom", NULL };
+#ifdef CONFIG_MTD_PARTITIONS
+static const char *part_probe_types[] = { "cmdlinepart", "RedBoot", NULL };
+#endif
+
+static int physmap_flash_probe(struct platform_device *dev)
{
- static const char *rom_probe_types[] = { "cfi_probe", "jedec_probe", "map_rom", NULL };
- const char **type;
+ struct physmap_flash_data *physmap_data;
+ struct physmap_flash_info *info;
+ const char **probe_type;
+ int err;
+
+ physmap_data = dev->dev.platform_data;
+ if (physmap_data == NULL)
+ return -ENODEV;
+
+ printk(KERN_NOTICE "physmap platform flash device: %.8lx at %.8lx\n",
+ dev->resource->end - dev->resource->start + 1,
+ dev->resource->start);
+
+ info = kmalloc(sizeof(struct physmap_flash_info), GFP_KERNEL);
+ if (info == NULL) {
+ err = -ENOMEM;
+ goto err_out;
+ }
+ memset(info, 0, sizeof(*info));
- printk(KERN_NOTICE "physmap flash device: %lx at %lx\n", physmap_map.size, physmap_map.phys);
- physmap_map.virt = ioremap(physmap_map.phys, physmap_map.size);
+ platform_set_drvdata(dev, info);
- if (!physmap_map.virt) {
- printk("Failed to ioremap\n");
- return -EIO;
+ info->res = request_mem_region(dev->resource->start,
+ dev->resource->end - dev->resource->start + 1,
+ dev->dev.bus_id);
+ if (info->res == NULL) {
+ dev_err(&dev->dev, "Could not reserve memory region\n");
+ err = -ENOMEM;
+ goto err_out;
}
- simple_map_init(&physmap_map);
+ info->map.name = dev->dev.bus_id;
+ info->map.phys = dev->resource->start;
+ info->map.size = dev->resource->end - dev->resource->start + 1;
+ info->map.bankwidth = physmap_data->width;
+ info->map.set_vpp = physmap_data->set_vpp;
+
+ info->map.virt = ioremap(info->map.phys, info->map.size);
+ if (info->map.virt == NULL) {
+ dev_err(&dev->dev, "Failed to ioremap flash region\n");
+ err = EIO;
+ goto err_out;
+ }
+
+ simple_map_init(&info->map);
- mymtd = NULL;
- type = rom_probe_types;
- for(; !mymtd && *type; type++) {
- mymtd = do_map_probe(*type, &physmap_map);
+ probe_type = rom_probe_types;
+ for (; info->mtd == NULL && *probe_type != NULL; probe_type++)
+ info->mtd = do_map_probe(*probe_type, &info->map);
+ if (info->mtd == NULL) {
+ dev_err(&dev->dev, "map_probe failed\n");
+ err = -ENXIO;
+ goto err_out;
}
- if (mymtd) {
- mymtd->owner = THIS_MODULE;
+ info->mtd->owner = THIS_MODULE;
#ifdef CONFIG_MTD_PARTITIONS
- mtd_parts_nb = parse_mtd_partitions(mymtd, part_probes,
- &mtd_parts, 0);
+ err = parse_mtd_partitions(info->mtd, part_probe_types, &info->parts, 0);
+ if (err > 0) {
+ add_mtd_partitions(info->mtd, info->parts, err);
+ return 0;
+ }
- if (mtd_parts_nb > 0)
- {
- add_mtd_partitions (mymtd, mtd_parts, mtd_parts_nb);
- return 0;
- }
+ if (physmap_data->nr_parts) {
+ printk(KERN_NOTICE "Using physmap partition information\n");
+ add_mtd_partitions(info->mtd, physmap_data->parts,
+ physmap_data->nr_parts);
+ return 0;
+ }
+#endif
- if (num_physmap_partitions != 0)
- {
- printk(KERN_NOTICE
- "Using physmap partition definition\n");
- add_mtd_partitions (mymtd, physmap_partitions, num_physmap_partitions);
- return 0;
- }
+ add_mtd_device(info->mtd);
+ return 0;
+
+err_out:
+ physmap_flash_remove(dev);
+ return err;
+}
+static struct platform_driver physmap_flash_driver = {
+ .probe = physmap_flash_probe,
+ .remove = physmap_flash_remove,
+ .driver = {
+ .name = "physmap-flash",
+ },
+};
+
+
+#ifdef CONFIG_MTD_PHYSMAP_LEN
+#if CONFIG_MTD_PHYSMAP_LEN != 0
+#warning using PHYSMAP compat code
+#define PHYSMAP_COMPAT
+#endif
#endif
- add_mtd_device(mymtd);
- return 0;
- }
+#ifdef PHYSMAP_COMPAT
+static struct physmap_flash_data physmap_flash_data = {
+ .width = CONFIG_MTD_PHYSMAP_BANKWIDTH,
+};
- iounmap(physmap_map.virt);
- return -ENXIO;
-}
+static struct resource physmap_flash_resource = {
+ .start = CONFIG_MTD_PHYSMAP_START,
+ .end = CONFIG_MTD_PHYSMAP_START + CONFIG_MTD_PHYSMAP_LEN,
+ .flags = IORESOURCE_MEM,
+};
+
+static struct platform_device physmap_flash = {
+ .name = "physmap-flash",
+ .id = 0,
+ .dev = {
+ .platform_data = &physmap_flash_data,
+ },
+ .num_resources = 1,
+ .resource = &physmap_flash_resource,
+};
-static void __exit cleanup_physmap(void)
+void physmap_configure(unsigned long addr, unsigned long size,
+ int bankwidth, void (*set_vpp)(struct map_info *, int))
{
+ physmap_flash_resource.start = addr;
+ physmap_flash_resource.end = addr + size - 1;
+ physmap_flash_data.width = bankwidth;
+ physmap_flash_data.set_vpp = set_vpp;
+}
+
#ifdef CONFIG_MTD_PARTITIONS
- if (mtd_parts_nb) {
- del_mtd_partitions(mymtd);
- kfree(mtd_parts);
- } else if (num_physmap_partitions) {
- del_mtd_partitions(mymtd);
- } else {
- del_mtd_device(mymtd);
- }
-#else
- del_mtd_device(mymtd);
+void physmap_set_partitions(struct mtd_partition *parts, int num_parts)
+{
+ physmap_flash_data.nr_parts = num_parts;
+ physmap_flash_data.parts = parts;
+}
+#endif
#endif
- map_destroy(mymtd);
- iounmap(physmap_map.virt);
- physmap_map.virt = NULL;
+static int __init physmap_init(void)
+{
+ int err;
+
+ err = platform_driver_register(&physmap_flash_driver);
+#ifdef PHYSMAP_COMPAT
+ if (err == 0)
+ platform_device_register(&physmap_flash);
+#endif
+
+ return err;
}
-module_init(init_physmap);
-module_exit(cleanup_physmap);
+static void __exit physmap_exit(void)
+{
+#ifdef PHYSMAP_COMPAT
+ platform_device_unregister(&physmap_flash);
+#endif
+ platform_driver_unregister(&physmap_flash_driver);
+}
+module_init(physmap_init);
+module_exit(physmap_exit);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("David Woodhouse <dwmw2@infradead.org>");
diff -urN linux-2.6.16-rc2.orig/include/linux/mtd/physmap.h linux-2.6.16-rc2/include/linux/mtd/physmap.h
--- linux-2.6.16-rc2.orig/include/linux/mtd/physmap.h 2006-02-12 14:53:43.000000000 +0100
+++ linux-2.6.16-rc2/include/linux/mtd/physmap.h 2006-02-12 16:37:23.000000000 +0100
@@ -24,22 +24,18 @@
#include <linux/mtd/map.h>
#include <linux/mtd/partitions.h>
-/*
- * The map_info for physmap. Board can override size, buswidth, phys,
- * (*set_vpp)(), etc in their initial setup routine.
- */
-extern struct map_info physmap_map;
+struct physmap_flash_data {
+ unsigned int width;
+ void (*set_vpp)(struct map_info *, int);
+ unsigned int nr_parts;
+ struct mtd_partition *parts;
+};
/*
* Board needs to specify the exact mapping during their setup time.
*/
-static inline void physmap_configure(unsigned long addr, unsigned long size, int bankwidth, void (*set_vpp)(struct map_info *, int) )
-{
- physmap_map.phys = addr;
- physmap_map.size = size;
- physmap_map.bankwidth = bankwidth;
- physmap_map.set_vpp = set_vpp;
-}
+void physmap_configure(unsigned long addr, unsigned long size,
+ int bankwidth, void (*set_vpp)(struct map_info *, int) );
#if defined(CONFIG_MTD_PARTITIONS)
@@ -58,4 +54,3 @@
#endif /* defined(CONFIG_MTD) */
#endif /* __LINUX_MTD_PHYSMAP__ */
-
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [PATCH,RFC] convert physmap to platform driver
2006-02-12 17:04 [PATCH,RFC] convert physmap to platform driver Lennert Buytenhek
@ 2006-02-21 13:51 ` Lennert Buytenhek
2006-03-03 9:09 ` Deepak Saxena
2006-02-28 19:16 ` [less intrusive PATCH,RFC] don't load physmap if length is zero Lennert Buytenhek
1 sibling, 1 reply; 8+ messages in thread
From: Lennert Buytenhek @ 2006-02-21 13:51 UTC (permalink / raw)
To: linux-mtd
Hi,
On Sun, Feb 12, 2006 at 06:04:41PM +0100, Lennert Buytenhek wrote:
> After dwmw2 let me know it ought to be done, I rewrote the physmap map
> driver to be a platform driver. I know zilch about the driver model,
> so I probably botched it in some way, but I've done some tests on an
> ixp23xx board which uses physmap, and it all seems to work.
I wonder whether anyone had a chance to look at this yet?
thanks,
Lennert
^ permalink raw reply [flat|nested] 8+ messages in thread
* [less intrusive PATCH,RFC] don't load physmap if length is zero
2006-02-12 17:04 [PATCH,RFC] convert physmap to platform driver Lennert Buytenhek
2006-02-21 13:51 ` Lennert Buytenhek
@ 2006-02-28 19:16 ` Lennert Buytenhek
2006-03-12 22:12 ` [less intrusive PATCH, RFC] " Jörn Engel
1 sibling, 1 reply; 8+ messages in thread
From: Lennert Buytenhek @ 2006-02-28 19:16 UTC (permalink / raw)
To: linux-mtd
OK, so if the previous patch (which converted physmap into a platform
driver) was too nonobvious, can we at least apply a patch like this so
that it's possible to compile in physmap without using it?
This is useful for example on the Technologic Systems TS-72xx boards,
where some models in the series have NOR flash while others have NAND
flash, and you'd like to be able to compile a single kernel that works
on all models. (So for the NOR models, you call physmap_configure at
run time, while for the NAND models, you initialise the board-specific
NAND driver (which I shall submit later.))
I'd still prefer the platform driver patch to be applied, but having
some kind of solution merged is better than no solution at all :-)
-- CUT HERE --
Allow compiling in the physmap mtd map driver without using it --
this is useful for multi-machine kernels where some of the supported
machines need physmap while others do not.
Signed-off-by: Lennert Buytenhek <buytenh@wantstofly.org>
diff -urN linux-2.6.15.orig/drivers/mtd/maps/Kconfig linux-2.6.15/drivers/mtd/maps/Kconfig
--- linux-2.6.15.orig/drivers/mtd/maps/Kconfig 2006-02-12 10:22:16.000000000 +0100
+++ linux-2.6.15/drivers/mtd/maps/Kconfig 2006-02-28 20:03:36.000000000 +0100
@@ -37,7 +37,7 @@
config MTD_PHYSMAP_LEN
hex "Physical length of flash mapping"
depends on MTD_PHYSMAP
- default "0x4000000"
+ default "0"
help
This is the total length of the mapping of the flash chips on
your particular board. If there is space, or aliases, in the
diff -urN linux-2.6.15.orig/drivers/mtd/maps/physmap.c linux-2.6.15/drivers/mtd/maps/physmap.c
--- linux-2.6.15.orig/drivers/mtd/maps/physmap.c 2006-02-12 10:22:16.000000000 +0100
+++ linux-2.6.15/drivers/mtd/maps/physmap.c 2006-02-20 21:14:23.000000000 +0100
@@ -51,6 +51,9 @@
static const char *rom_probe_types[] = { "cfi_probe", "jedec_probe", "map_rom", NULL };
const char **type;
+ if (!physmap_map.size)
+ return -EIO;
+
printk(KERN_NOTICE "physmap flash device: %lx at %lx\n", physmap_map.size, physmap_map.phys);
physmap_map.virt = ioremap(physmap_map.phys, physmap_map.size);
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [PATCH,RFC] convert physmap to platform driver
2006-02-21 13:51 ` Lennert Buytenhek
@ 2006-03-03 9:09 ` Deepak Saxena
0 siblings, 0 replies; 8+ messages in thread
From: Deepak Saxena @ 2006-03-03 9:09 UTC (permalink / raw)
To: Lennert Buytenhek; +Cc: linux-mtd
On Feb 21 2006, at 14:51, Lennert Buytenhek was caught saying:
> Hi,
>
> On Sun, Feb 12, 2006 at 06:04:41PM +0100, Lennert Buytenhek wrote:
>
> > After dwmw2 let me know it ought to be done, I rewrote the physmap map
> > driver to be a platform driver. I know zilch about the driver model,
> > so I probably botched it in some way, but I've done some tests on an
> > ixp23xx board which uses physmap, and it all seems to work.
>
> I wonder whether anyone had a chance to look at this yet?
/me wonders same. Would like to see this upstream.
~Deepak
--
Deepak Saxena - dsaxena@plexity.net - http://www.plexity.net
A starving child in Africa or you in front of your TV?
Where's the real tragedy?
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [less intrusive PATCH, RFC] don't load physmap if length is zero
2006-02-28 19:16 ` [less intrusive PATCH,RFC] don't load physmap if length is zero Lennert Buytenhek
@ 2006-03-12 22:12 ` Jörn Engel
2006-03-13 18:47 ` Mark Brown
0 siblings, 1 reply; 8+ messages in thread
From: Jörn Engel @ 2006-03-12 22:12 UTC (permalink / raw)
To: Lennert Buytenhek; +Cc: linux-mtd
On Tue, 28 February 2006 20:16:42 +0100, Lennert Buytenhek wrote:
>
> OK, so if the previous patch (which converted physmap into a platform
> driver) was too nonobvious, can we at least apply a patch like this so
> that it's possible to compile in physmap without using it?
>
> This is useful for example on the Technologic Systems TS-72xx boards,
> where some models in the series have NOR flash while others have NAND
> flash, and you'd like to be able to compile a single kernel that works
> on all models. (So for the NOR models, you call physmap_configure at
> run time, while for the NAND models, you initialise the board-specific
> NAND driver (which I shall submit later.))
>
> I'd still prefer the platform driver patch to be applied, but having
> some kind of solution merged is better than no solution at all :-)
Is there a good reason why you didn't just write your own mapping
driver? Most people copy physmap.c, change a few things and use that
driver instead of physmap.c. It does involve many copies of
essentially the same code, but that code is very simple and no sane
kernel should have more than one mapping driver included, so no object
code is duplicated.
Jörn
--
Public Domain - Free as in Beer
General Public - Free as in Speech
BSD License - Free as in Enterprise
Shared Source - Free as in "Work will make you..."
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [less intrusive PATCH, RFC] don't load physmap if length is zero
2006-03-12 22:12 ` [less intrusive PATCH, RFC] " Jörn Engel
@ 2006-03-13 18:47 ` Mark Brown
2006-03-13 19:14 ` Jörn Engel
0 siblings, 1 reply; 8+ messages in thread
From: Mark Brown @ 2006-03-13 18:47 UTC (permalink / raw)
To: J?rn Engel; +Cc: linux-mtd, Lennert Buytenhek
On Sun, Mar 12, 2006 at 11:12:48PM +0100, J?rn Engel wrote:
> On Tue, 28 February 2006 20:16:42 +0100, Lennert Buytenhek wrote:
> > I'd still prefer the platform driver patch to be applied, but having
> > some kind of solution merged is better than no solution at all :-)
> Is there a good reason why you didn't just write your own mapping
> driver? Most people copy physmap.c, change a few things and use that
> driver instead of physmap.c. It does involve many copies of
> essentially the same code, but that code is very simple and no sane
> kernel should have more than one mapping driver included, so no object
> code is duplicated.
It is reasonable to have multiple board variants with differing flash
setups but still want them all to run the same kernel. If you're using
platform devices to tell the world about the rest of the differing fit
information it's reasonable to also want to use it for the flash.
--
"You grabbed my hand and we fell into it, like a daydream - or a fever."
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [less intrusive PATCH, RFC] don't load physmap if length is zero
2006-03-13 18:47 ` Mark Brown
@ 2006-03-13 19:14 ` Jörn Engel
2006-03-14 20:03 ` Mark Brown
0 siblings, 1 reply; 8+ messages in thread
From: Jörn Engel @ 2006-03-13 19:14 UTC (permalink / raw)
To: Mark Brown; +Cc: linux-mtd, Lennert Buytenhek
On Mon, 13 March 2006 18:47:30 +0000, Mark Brown wrote:
> On Sun, Mar 12, 2006 at 11:12:48PM +0100, J?rn Engel wrote:
> > On Tue, 28 February 2006 20:16:42 +0100, Lennert Buytenhek wrote:
>
> > > I'd still prefer the platform driver patch to be applied, but having
> > > some kind of solution merged is better than no solution at all :-)
>
> > Is there a good reason why you didn't just write your own mapping
> > driver? Most people copy physmap.c, change a few things and use that
> > driver instead of physmap.c. It does involve many copies of
> > essentially the same code, but that code is very simple and no sane
> > kernel should have more than one mapping driver included, so no object
> > code is duplicated.
>
> It is reasonable to have multiple board variants with differing flash
> setups but still want them all to run the same kernel. If you're using
> platform devices to tell the world about the rest of the differing fit
> information it's reasonable to also want to use it for the flash.
Sure. So why don't you:
1. Turn physmap.c into a platform driver.
2. Rename physmap.c into something.c
3. Remove unnecessary generic code from something.c
4. Submit a patch adding something.c
Instead, steps 2 and 3 were skipped and physmap itself was supposed to
become a platform driver. And at the moment I don't understand the
advantages of skipping said steps.
Jörn
--
Das Aufregende am Schreiben ist es, eine Ordnung zu schaffen, wo
vorher keine existiert hat.
-- Doris Lessing
^ permalink raw reply [flat|nested] 8+ messages in thread
* Re: [less intrusive PATCH, RFC] don't load physmap if length is zero
2006-03-13 19:14 ` Jörn Engel
@ 2006-03-14 20:03 ` Mark Brown
0 siblings, 0 replies; 8+ messages in thread
From: Mark Brown @ 2006-03-14 20:03 UTC (permalink / raw)
To: Jörn Engel; +Cc: linux-mtd, Lennert Buytenhek
On Mon, Mar 13, 2006 at 08:14:48PM +0100, Jörn Engel wrote:
> Sure. So why don't you:
> 1. Turn physmap.c into a platform driver.
> 2. Rename physmap.c into something.c
> 3. Remove unnecessary generic code from something.c
> 4. Submit a patch adding something.c
That's roughly what I have done (except I just added the ability to
configure the probe type to a copy of the existing platform RAM driver).
A patch against 2.6.13 is below: it probably needs updating. Ben Dooks
wanted me to re-add the write locking support that the original code had
but I stripped out pending adding windowing support.
I haven't been trying very hard to integrate that yet (I think I posted
it once before), mostly due to not having done what Ben asked although
there's no reason why that couldn't be added later.
> Instead, steps 2 and 3 were skipped and physmap itself was supposed to
> become a platform driver. And at the moment I don't understand the
> advantages of skipping said steps.
That makes sense. I guess if I were going to do anything with physmap I
would be making it register a platform device rather than just talk to
the MTD code directly.
diff -uprN linux-2.6.13/drivers/mtd/maps/Kconfig linux-plat-flash/drivers/mtd/maps/Kconfig
--- linux-2.6.13/drivers/mtd/maps/Kconfig 2005-08-29 00:41:01.000000000 +0100
+++ linux-plat-flash/drivers/mtd/maps/Kconfig 2005-09-08 18:51:13.984319480 +0100
@@ -624,5 +624,12 @@ config MTD_PLATRAM
This selection automatically selects the map_ram driver.
+config MTD_PLATFLASH
+ tristate "Map driver for platform device physically mapped flash"
+ depends on MTD
+ help
+ Map driver allowing MTD devices which are physically mapped into
+ the CPU's address space to be enumerated using the platform bus.
+
endmenu
diff -uprN linux-2.6.13/drivers/mtd/maps/Makefile linux-plat-flash/drivers/mtd/maps/Makefile
--- linux-2.6.13/drivers/mtd/maps/Makefile 2005-08-29 00:41:01.000000000 +0100
+++ linux-plat-flash/drivers/mtd/maps/Makefile 2005-09-08 18:51:08.706121888 +0100
@@ -69,4 +69,5 @@ obj-$(CONFIG_MTD_WRSBC8260) += wr_sbc82x
obj-$(CONFIG_MTD_DMV182) += dmv182.o
obj-$(CONFIG_MTD_SHARP_SL) += sharpsl-flash.o
obj-$(CONFIG_MTD_PLATRAM) += plat-ram.o
+obj-$(CONFIG_MTD_PLATFLASH) += plat-flash.o
obj-$(CONFIG_MTD_OMAP_NOR) += omap_nor.o
diff -uprN linux-2.6.13/drivers/mtd/maps/plat-flash.c linux-plat-flash/drivers/mtd/maps/plat-flash.c
--- linux-2.6.13/drivers/mtd/maps/plat-flash.c 1970-01-01 01:00:00.000000000 +0100
+++ linux-plat-flash/drivers/mtd/maps/plat-flash.c 2005-09-08 18:48:56.711188168 +0100
@@ -0,0 +1,272 @@
+/* drivers/mtd/maps/plat-flash.c
+ *
+ * (c) 2005 Aculab plc
+ * Mark Brown <broonie@sirena.org.uk>
+ * (c) 2004-2005 Simtec Electronics
+ * http://www.simtec.co.uk/products/SWLINUX/
+ * Ben Dooks <ben@simtec.co.uk>
+ *
+ * Generic platform device based flash mappings.
+ *
+ * $Id: $
+ *
+ * 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.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
+*/
+
+#include <linux/module.h>
+#include <linux/types.h>
+#include <linux/init.h>
+#include <linux/kernel.h>
+#include <linux/string.h>
+#include <linux/ioport.h>
+#include <linux/device.h>
+
+#include <linux/mtd/mtd.h>
+#include <linux/mtd/map.h>
+#include <linux/mtd/partitions.h>
+#include <linux/mtd/plat-flash.h>
+
+#include <asm/io.h>
+
+/* private structure for each mtd platform device created */
+
+struct platflash_info {
+ struct device *dev;
+ struct mtd_info *mtd;
+ struct map_info map;
+ struct mtd_partition *partitions;
+ struct resource *area;
+};
+
+/* to_platflash_info()
+ *
+ * device private data to struct platflash_info conversion
+*/
+
+static inline struct platflash_info *to_platflash_info(struct device *dev)
+{
+ return (struct platflash_info *)dev_get_drvdata(dev);
+}
+
+/* platflash_remove
+ *
+ * called to remove the device from the driver's control
+*/
+
+static int platflash_remove(struct device *dev)
+{
+ struct platflash_info *info = to_platflash_info(dev);
+
+ dev_set_drvdata(dev, NULL);
+
+ dev_dbg(dev, "removing device\n");
+
+ if (info == NULL)
+ return 0;
+
+ if (info->mtd) {
+#ifdef CONFIG_MTD_PARTITIONS
+ if (info->partitions) {
+ del_mtd_partitions(info->mtd);
+ kfree(info->partitions);
+ }
+#endif
+ del_mtd_device(info->mtd);
+ map_destroy(info->mtd);
+ }
+
+ /* release resources */
+
+ if (info->area) {
+ release_resource(info->area);
+ kfree(info->area);
+ }
+
+ if (info->map.virt != NULL)
+ iounmap(info->map.virt);
+
+ kfree(info);
+
+ return 0;
+}
+
+/* platflash_probe
+ *
+ * called from device drive system when a device matching our
+ * driver is found.
+*/
+
+static int platflash_probe(struct device *dev)
+{
+ struct platform_device *pd = to_platform_device(dev);
+ struct platflash_info *info;
+ struct platdata_mtd_flash *pdata;
+ struct resource *res;
+ int err = 0;
+ int i;
+
+ dev_dbg(dev, "probe entered\n");
+
+ if (dev->platform_data == NULL) {
+ dev_err(dev, "no platform data supplied\n");
+ err = -ENOENT;
+ goto exit_error;
+ }
+
+ pdata = dev->platform_data;
+
+ if (pdata->chip_probes == 0) {
+ dev_err(dev, "no chip probes specified\n");
+ err = -ENOENT;
+ goto exit_error;
+ }
+
+ info = kmalloc(sizeof(*info), GFP_KERNEL);
+ if (info == NULL) {
+ dev_err(dev, "no memory for flash info\n");
+ err = -ENOMEM;
+ goto exit_error;
+ }
+
+ memset(info, 0, sizeof(*info));
+ dev_set_drvdata(dev, info);
+
+ info->dev = dev;
+
+ /* get the resource for the memory mapping */
+
+ res = platform_get_resource(pd, IORESOURCE_MEM, 0);
+
+ if (res == NULL) {
+ dev_err(dev, "no memory resource specified\n");
+ err = -ENOENT;
+ goto exit_free;
+ }
+
+ dev_dbg(dev, "got platform resource %p (0x%lx)\n", res, res->start);
+
+ /* setup map parameters */
+
+ info->map.phys = res->start;
+ info->map.size = (res->end - res->start) + 1;
+ info->map.name = pdata->mapname != NULL ? pdata->mapname : pd->name;
+ info->map.bankwidth = pdata->bankwidth;
+
+ /* register our usage of the memory area */
+
+ info->area = request_mem_region(res->start, info->map.size, pd->name);
+ if (info->area == NULL) {
+ dev_err(dev, "failed to request memory region\n");
+ err = -EIO;
+ goto exit_free;
+ }
+
+ /* remap the memory area */
+
+ info->map.virt = ioremap(res->start, info->map.size);
+ dev_dbg(dev, "virt %p, %lu bytes\n", info->map.virt, info->map.size);
+
+ if (info->map.virt == NULL) {
+ dev_err(dev, "failed to ioremap() region\n");
+ err = -EIO;
+ goto exit_free;
+ }
+
+ simple_map_init(&info->map);
+
+ dev_dbg(dev, "initialised map, probing for mtd\n");
+
+ /* probe for the right mtd map driver */
+ i = 0;
+ while (pdata->chip_probes[i]) {
+ dev_dbg(dev, "probing with %s\n", pdata->chip_probes[i]);
+ info->mtd = do_map_probe(pdata->chip_probes[i], &info->map);
+ i++;
+ if (info->mtd != NULL)
+ break;
+ }
+ if (info->mtd == NULL) {
+ dev_err(dev, "failed to identify device\n");
+ err = -ENOMEM;
+ goto exit_free;
+ }
+
+ info->mtd->owner = THIS_MODULE;
+
+ /* check to see if there are any available partitions, or wether
+ * to add this device whole */
+
+#ifdef CONFIG_MTD_PARTITIONS
+ if (pdata->nr_partitions > 0) {
+ if (pdata->partition_probes)
+ {
+ err = parse_mtd_partitions(info->mtd,
+ pdata->partition_probes,
+ &info->partitions, 0);
+ }
+ else
+ {
+ err = pdata->nr_partitions;
+ info->partitions = pdata->partitions;
+ }
+
+ if (err > 0) {
+ err = add_mtd_partitions(info->mtd, info->partitions,
+ err);
+ }
+ }
+#endif /* CONFIG_MTD_PARTITIONS */
+
+ if (add_mtd_device(info->mtd)) {
+ dev_err(dev, "add_mtd_device() failed\n");
+ err = -ENOMEM;
+ }
+
+ dev_info(dev, "registered mtd device\n");
+ return err;
+
+ exit_free:
+ platflash_remove(dev);
+ exit_error:
+ return err;
+}
+
+/* device driver info */
+
+static struct device_driver platflash_driver = {
+ .name = "mtd-phys",
+ .bus = &platform_bus_type,
+ .probe = platflash_probe,
+ .remove = platflash_remove,
+};
+
+/* module init/exit */
+
+static int __init platflash_init(void)
+{
+ return driver_register(&platflash_driver);
+}
+
+static void __exit platflash_exit(void)
+{
+ driver_unregister(&platflash_driver);
+}
+
+module_init(platflash_init);
+module_exit(platflash_exit);
+
+MODULE_LICENSE("GPL");
+MODULE_AUTHOR("Mark Brown <broonie@sirena.org.uk>");
+MODULE_DESCRIPTION("MTD platform map driver");
diff -uprN linux-2.6.13/include/linux/mtd/plat-flash.h linux-plat-flash/include/linux/mtd/plat-flash.h
--- linux-2.6.13/include/linux/mtd/plat-flash.h 1970-01-01 01:00:00.000000000 +0100
+++ linux-plat-flash/include/linux/mtd/plat-flash.h 2005-09-08 18:49:28.000000000 +0100
@@ -0,0 +1,31 @@
+/* linux/include/mtd/plat-flash.h
+ *
+ * (c) 2005 Aculab plc
+ * Mark Brown <broonie@sirena.org.uk>
+ * (c) 2004 Simtec Electronics
+ * http://www.simtec.co.uk/products/SWLINUX/
+ * Ben Dooks <ben@simtec.co.uk>
+ *
+ * Generic platform device based flash map
+ *
+ * $Id: $
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ *
+ */
+
+#ifndef __LINUX_MTD_PLATFLASH_H
+#define __LINUX_MTD_PLATFLASH_H __FILE__
+
+struct platdata_mtd_flash {
+ char *mapname;
+ char **chip_probes;
+ char **partition_probes;
+ struct mtd_partition *partitions;
+ int nr_partitions;
+ int bankwidth;
+};
+
+#endif /* __LINUX_MTD_PLATRAM_H */
--
"You grabbed my hand and we fell into it, like a daydream - or a fever."
^ permalink raw reply [flat|nested] 8+ messages in thread
end of thread, other threads:[~2006-03-14 20:03 UTC | newest]
Thread overview: 8+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2006-02-12 17:04 [PATCH,RFC] convert physmap to platform driver Lennert Buytenhek
2006-02-21 13:51 ` Lennert Buytenhek
2006-03-03 9:09 ` Deepak Saxena
2006-02-28 19:16 ` [less intrusive PATCH,RFC] don't load physmap if length is zero Lennert Buytenhek
2006-03-12 22:12 ` [less intrusive PATCH, RFC] " Jörn Engel
2006-03-13 18:47 ` Mark Brown
2006-03-13 19:14 ` Jörn Engel
2006-03-14 20:03 ` Mark Brown
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox