mmap in LDD3.

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

 



Hi all,
I am lost figuring out how this piece of code works (from Linux Device
Driver 3ed, page 428).
   struct page *simple_vma_nopage(struct vm_area_struct *vma,
                   unsigned long address, int *type)
   {
       struct page *pageptr;
       unsigned long offset = vma->vm_pgoff << PAGE_SHIFT;
       unsigned long physaddr = address - vma->vm_start + offset;
       unsigned long pageframe = physaddr >> PAGE_SHIFT;
       if (!pfn_valid(pageframe))
           return NOPAGE_SIGBUS;
       pageptr = pfn_to_page(pageframe);
       get_page(pageptr);
       if (type)
           *type = VM_FAULT_MINOR;
       return pageptr;
   }

My doubts are,
how does the statements,
offset = vma->vm_pgoff << PAGE_SHIFT;
physaddr = address - vma->vm_start + offset;
hold true?

AFAIK, from mm.h, vma->vm_pgoff is the Offset (within vm_file) in
PAGE_SIZE units, *not* PAGE_CACHE_SIZE. That gives variable offset =
offset within file in bytes.

address is the virtual address whose page frame is requested.

Then, physaddr = address (virtual address) - vma->vm_start (virtual
address of start of the vma) + offset within the file in bytes.

How can this be true? What am I missing?

--
Kernelnewbies: Help each other learn about the Linux kernel.
Archive:       http://mail.nl.linux.org/kernelnewbies/
FAQ:           http://kernelnewbies.org/faq/


[Index of Archives]     [Newbies FAQ]     [Linux Kernel Mentors]     [Linux Kernel Development]     [IETF Annouce]     [Git]     [Networking]     [Security]     [Bugtraq]     [Yosemite]     [MIPS Linux]     [ARM Linux]     [Linux RAID]     [Linux SCSI]     [Linux ACPI]
  Powered by Linux