Skip navigation.
Home
The QNX Community Portal

View topic - Physical to virtual address mapping failed

Physical to virtual address mapping failed

QNX Application portings.

Physical to virtual address mapping failed

Postby jagan » Tue Feb 01, 2011 4:42 am

Hi,

For DMA operation i have created a buffer of 300KB,

virtaddr = mmap(NULL, (300*1024), PROT_READ|PROT_WRITE|PROT_NOCACHE, MAP_PHYS|MAP_ANON,NOFD, 0);

and then converting this virtaddr to phyaddr by

mem_offset(virtAddr, NOFD, 1, phyAddr, 0);

after that to make use of that buffer for application I am converting physical to virtual addr by

virtaddr = mmap(NULL, 1, PROT_READ|PROT_WRITE, MAP_PHYS,NOFD, phyAddr);

Once the buffer allocated the buffer will be keep on filled and used in for DMA as well as application so the conversion operation also happen in loop which will continuously run. This physical to virtual conversion get fail after some 100 MB transfer of data using that buffer.

with perror() , it is showing "no enough memory" and memory fault is happening.
In linux to convert virt to phy addr or phy to virt no need to free the buffer. Is any similar kind of api available in QNX ??
Since the actual buffer will be in use continuously i don't want to free the buffer. If I free the virt addr after application uses it, then it free the actual buffer memory too?
How to solve this problem??

Any help would be highly appreciated!!

Thanks, Jagan
jagan
New Member
 
Posts: 4
Joined: Tue Feb 01, 2011 4:24 am

RE: Physical to virtual address mapping failed

Postby mario » Tue Feb 01, 2011 1:56 pm

You are probably consuming virtual addresses. mmap is NOT a fonction to convert physical address to virtual. It maps it, if you remap the same physical area, this will use up more virtual adresses.
mario
QNX Master
 
Posts: 4132
Joined: Sun Sep 01, 2002 1:04 am

Re: RE: Physical to virtual address mapping failed

Postby jagan » Wed Feb 02, 2011 5:36 am

mario wrote:You are probably consuming virtual addresses. mmap is NOT a fonction to convert physical address to virtual. It maps it, if you remap the same physical area, this will use up more virtual adresses.


The memory fault is fixed by unmapping the virtual address after using the buffer in the application on the loop-which i have metioned in the last post.

But i don't want to do unmap the virtual addr (after remapping) in the application.
So is there any API to convert physical addr to virtual? so no unmap is required.

whether the physical to virtual really mapping needed here, we are not able to use the phy addr of mem|_offset() in the application? then is there any other way?

Thanks
Jagan
jagan
New Member
 
Posts: 4
Joined: Tue Feb 01, 2011 4:24 am

RE: Re: RE: Physical to virtual address mapping failed

Postby mario » Wed Feb 02, 2011 2:27 pm

This was discuss before, it does not make any sense to *convert* a physical address to virtual. A virtual address only come to existance when mmap occurs. mmap is NOT a fonction that convert physical adresses to virtual addresses, it CREATES virtual addresses out of a pool of available virtual addresses. However strongly you might disagree with this concept you have to accept and live with it.

In your OP what you need to do is keep the orignal virtaddr return by mmap.
mario
QNX Master
 
Posts: 4132
Joined: Sun Sep 01, 2002 1:04 am

Re: RE: Re: RE: Physical to virtual address mapping failed

Postby Thunderblade » Thu Feb 03, 2011 12:55 pm

mario wrote:In your OP what you need to do is keep the orignal virtaddr return by mmap.


Exactly! Getting phys. address of virtual makes sense to program DMA buffer, but why trying to get virt. address of physical? You already have the virtual address!
Thunderblade
Senior Member
 
Posts: 487
Joined: Thu Apr 07, 2005 11:52 am

Postby jagan » Tue Feb 08, 2011 1:01 pm

I agree that I am having the virtual address returned from mmap() and I can use that.
But I am splitting the 300KB into 200 buffers of each 1536 bytes, getting the physical address of 200 buffers using mem_offset() and give each to a descriptor.
I am not maintaining the references of virtual address here. (I am writing some of the code to be generic for linux as well as QNX).

So after the DMA transaction I need virtual address to handle the buffer so I am doing physical to virtual conversion and use the virtual address. That’s why I am using mmap() to do the mapping of the physical address to virtual address. I thought it will return already mapped virtual address but here it is mapping to some other location of process address location and I am getting another virtual address which maps the same physical address. So will you please clarify the following things.

How this works in QNX?
With this I am allocating 1MB of physically contiguous memory.
Virt_addr_1 = mmap(NULL, 1024*1024, PROT_READ|PROT_WRITE|PROT_NOCACHE, MAP_PHYS|MAP_ANON,NOFD, 0);
With this I have got the physical address of the Virt_addr_1
mem_offset(Virt_addr_1, NOFD, 1, phyAddr, 0);

1) Here I have given the length as 1 (not as 1MB)and I am accessing up to 1MB (ie from phyAddr to phyAddr + 1MB). Here I gave length 1 then how I am able to access phyaddr + 1MB which I am using with DMA and getting proper Data?

After DMA operation I am mapping the phyAddr to another process address space “Virt_addr_2â€
jagan
New Member
 
Posts: 4
Joined: Tue Feb 01, 2011 4:24 am

Postby mario » Tue Feb 08, 2011 5:39 pm

You've made assumptions that are wrong. For example, if you mmap a memory area of 1 bytes, you should only access it as if it was a 1 byte memory block, not more. It works only because everything is rounded to 4K which is the smallest page size. You program doesn't work by design, it work by luck ;-)

Here is what you could do:

Server program mmap 1Meg from which you obtain the physical address to deal with hardware.

Client also mmap the same 1Meg, they don't need to know about the physical address. If you want to access byte 10000 of the 1Meg block, you simply take the virtual address mmap returned and add 10000. mmap is an expensive operation, you don't want to do it all the time. If possible only once in the life of the program (both server and client).

As a matter of fact I wouldn't let the client have direct access to the mmap area of the server. The server would do the job and use messaging to send/receive data. That is how most of QNX subsystem works (network, disk, usb)
mario
QNX Master
 
Posts: 4132
Joined: Sun Sep 01, 2002 1:04 am

Postby jagan » Wed Feb 09, 2011 3:46 am

Hi Mario,

You're right, In the allocated 1MB for every mmap of Virt_addr_2 i am accessing only up to 1536 bytes which is less than 4K so it is working some how.

But in qnx there is no equivalent virt_to_phy() & phy_to_virt() calls?? as in linux, which will return the mapped physical and virtual address of a memory block.

please clarify the 3) on my last post (how munmap knows, it should free mapping or to free the allocated contiguous physical memory. in case of contiguous physical memory it also needs to take care of unmapping the virtual address return by it during the allocation.how it will do?).

Thanks
Jagan
jagan
New Member
 
Posts: 4
Joined: Tue Feb 01, 2011 4:24 am

Postby mario » Wed Feb 09, 2011 3:05 pm

jagan wrote:Hi Mario,

You're right, In the allocated 1MB for every mmap of Virt_addr_2 i am accessing only up to 1536 bytes which is less than 4K so it is working some how.

But in qnx there is no equivalent virt_to_phy() & phy_to_virt() calls?? as in linux, which will return the mapped physical and virtual address of a memory block.


No there isn't, at least that I know of. I had some doubt so I check what the man page about phy_to_virt on Linux says "This function does not handle bus mappings for DMA transfers. In almost all conceivable cases a device driver should not be using this function". I think that says it all ;-)


jagan wrote:please clarify the 3) on my last post (how munmap knows, it should free mapping or to free the allocated contiguous physical memory. in case of contiguous physical memory it also needs to take care of unmapping the virtual address return by it during the allocation.how it will do?).


If mmap is used to allocated memory (DMAable or not) it's the corresponding unmap that will return that memory to the system. If mmap is used to map memory into virtual addressing (which is also perfom when allocating memory) , the corresponding unmap will release the virtual address. How it's done, I do not know the detail, but since the kernel handles virtual adresses it's not hard to imagine that it keeps track of all this stuff, much like it keeps track of file descriptor. With mmap the pointer returned is like a file descriptor.

Hope this helps.
mario
QNX Master
 
Posts: 4132
Joined: Sun Sep 01, 2002 1:04 am


Return to Porting

Who is online

Users browsing this forum: No registered users and 1 guest