Platofrm - Linux, Arch - ARM Programming lang - C/C++
Objective - map a regular (let say text) file to a pre-kn开发者_开发技巧own location (physical address) in ram and pass that physical address to some other application. Size of the block which i map at a time is 128K.
The way I am trying to go about is- User space process issues the ioctl call to ask a device driver to get a chunk of memory (ram), calculated the physical address and return it to the user space.
User space process needs to maps the file to that physical address space I am not sure how to go about it. Any help is appreciated. ???
Issue with mmap call on the file and then calculating the physical address is that, pages are not in memory till someone access them and physical memory pages allocated might not be contiguous.
The other process which will actually access the file is from third party vendor application. That application demands once we pass it the physical address, file contents needs to be present in contiguous memory.
How i am doing it right now --
User process call the mmap to device. Device driver does a kmalloc, calculate the starting physical address and mmap the VMA to that physical address. Now user process do a read on the file and copies it to the address space obtained during the mmap.
Issue - Copy of the file exist two location in the ram, one when read is done from disk and other when i copy it to the buffer obtained using mmap and corresponding copying overheads. In a ideal world i would like to load the file directly from the disk to a known/predefined location.
"Mapping a file" implies using virtual addresses rather than physical, so that's not going to do what you want.
If you want to put the file contents into a contiguous block of physical memory, just use open()
and read()
once you have obtained the contiguous buffer.
Perhaps something like madvise()
with MADV_SEQUENTIAL
advice argument could help?
Some things to consider:
- How large is the file you're going to be mapping?
- That might affect your ability to get a contiguous block of RAM, even if you were to take the kernel driver based approach.
- For a kernel driver based approach, well behaved drivers typically should not
kmalloc()
, e.g. to get a contiguous block of memory, more than 32KB. Furthermore, you typically can'tkmalloc()
more than 2MB (I've tried this :)). Is that going to be suitable for your needs? - If you need a really large chunk of memory something like the kernel's
alloc_bootmem()
function could help, but it only works for static "built-in" drivers, not dynamically loadable ones. - Is there any way you can rework your design so that a large contiguous block of mapped memory isn't necessary?
精彩评论