Francesco Rendine

Mapping i/o peripherals on flexbus

Discussion created by Francesco Rendine on Dec 19, 2011
Latest reply on Dec 20, 2011 by Francesco Rendine

Hi,
I'm writing to you because i'm having trouble with I/O peripheral mapping on new kernel 2.6.38 on M5445x platform.
I work with a custom platform based on M54452 and we have some peripherals on Flexbus on chip select 2 and chip select 3.
I don't understand how mapping these peripherals on Linux. I've already read all threads about this topic, but I didn't resolve my problem. With previous kernel 2.6.25, I used "ioremap()" to map my peripheral in my device drivers, and it works. With new kernel 2.6.38 it doesn't work anymore..I check on new code of "ioremap" in kmap.c and I seen that there is a new check on KMAP_START and KMAP_END.
For kernel 2.6.25 and kernel 2.6.38 KMAP_START and KMAP_END are the same.
In practice, the situation is this:

#if defined(CONFIG_M5445X) || defined(CONFIG_M547X_8X)
#define VMALLOC_START 0xc0000000
#define VMALLOC_END 0xcfffffff
#define KMAP_START (VMALLOC_END + 1)
#define KMAP_END (0xe8000000 – 1)
#endif

Instead "ioremap" in two kernels are slightly different.

Kernel 2.6.38:
--------------------------------------------------------------------------
if ((physaddr >=KMAP_START) && (physaddr <= KMAP_END)) {
/* if physaddr belongs to virtual address range for ioremap,
* then return physaddr because it has been ioremapped
*/
return (void __iomem *)physaddr;
}

Kernel 2.6.25:
--------------------------------------------------------------------------
if ((physaddr >=0xa0000000) && (physaddr <= 0xb0000000)) {
/* if physaddr belongs to virtual address range for ioremap,
* then return physaddr because it has been ioremapped
*/
return (void __iomem *)physaddr;
}

So, I would like to map my peripherals in this mode replacing ATA physical address because in our platform (M54452) we haven't ATA controller :
#define PERIPHERAL_1_BASE_PHY 0x90000000
#define PERIPHERAL_2_BASE_PHY 0x90010000
#define PERIPHERAL_3_BASE_PHY 0x90020000

but using "ioremap" these physical addresses doesn't work.
Instead if I use physical addresses in 0xC0000000 - 0xE8000000 range, and I disable check on ((physaddr >=KMAP_START) && (physaddr <= KMAP_END)) in ioremap(), everything works. I don't understand the reason. Why I should map my devices on range between VMALLOC_START and KMAP_END?
There is something of strange...
Can you explain me, please?
Thank you very much for your support.

Outcomes