I'm pretty confused on how linux manages I/O shared memory to communicate with devices that use it.
If I understood it correctly linux kernel starts mapped at 0x100000 (to avoid the first megabyte legacy ram data and to be stored in contiguous memory locations) and then after entering protected mode:
- on 32 bit systems there's a mapping like this
The ZONE_NORMAL should be below 896 MB, so the mapping between the kernel linear 1GB and the physical 896 MB is always possible. Let's just ignore the ZONE_DMA for now (I read that this is just for legacy systems since PCI can now use DMA transfers everywhere in memory)
- on 64 bit systems the kernel linear address space should start from PAGE_OFFSET= 0xffff810000000000 and forth
In both cases, if an address in the kernel space is greater than PAGE_OFFSET, should refer to a ioremap mapping (to be resolved through pagination), if it's lower than PAGE_OFFSET it could be resolved with a simple NEW_ADDRESS = OLD_ADDRESS - PAGE_OFFSET. Is this correct?
Bonus question: when the kernel is up and running and the tidying up has been done, does it still physically reside from 0x100000 and forth (within the first GB) ? Even on 64bit systems?