Convert physical address to virtual in Linux and r

2019-04-17 23:59发布

问题:

I have Linux and I have a physical address: (i.e. 0x60000000).
I want to read this address from user-space Linux program.

This address might be in kernel space.

回答1:

You need a kernel driver to export the phyisical address to user-level.

Have a look at this driver: https://github.com/claudioscordino/mmap_alloc/blob/master/mmap_alloc.c



回答2:

Note that this is now possible via /proc/[pid]/pagemap



回答3:

Is there an easy way I can do that?

For accessing from user space, mmap() is a nice solution.

Is it possible to convert it by using some function like "phys_to_virt()"?

Physical address can be mapped to virtual address using ioremap_nocache(). But from user space, you can't access it directly. suppose your driver or kernel modules want to access that pysical address, this is the best way. usually memory mapped device drivers uses this function to map registers to virtual memory.



回答4:

Something like this in C. if you poll a hardware register, make sure you add volatile declarations so the compiler doesn't optimize out your variable.

#include <stdlib.h>

#include <stdio.h>
#include <errno.h>

#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/mman.h>
#include <memory.h>

volatile int *hw_mmap = NULL; /*evil global variable method*/

int map_it() {
/* open /dev/mem and error checking */
int i;
int file_handle = open(memDevice, O_RDWR | O_SYNC);

if (file_handle < 0) {
    DBG_PRINT("Failed to open /dev/mem: %s !\n",strerror(errno));
    return errno;
}

/* mmap() the opened /dev/mem */
hw_mmap = (int *) (mmap(0, 4096, PROT_READ | PROT_WRITE, MAP_SHARED, file_handle, 0x60000000));
if(hw_mmap ==(void*) -1) {

    fprintf(stderr,"map_it: Cannot map memory into user space.\n");
    return errno;
}
return 0;
}

Now you can read write into hw_mmap.