*参照元 [#s3213880]
#backlinks

*説明 [#l6834610]
-パス: 複数あり
--CONFIG_MMU 有効: [[linux-4.4.1/mm/memory.c]]
--CONFIG_MMU 無効: [[linux-4.4.1/mm/nommu.c]]

-FIXME: これは何?
--説明


**引数 [#pcaff14b]
-struct vm_area_struct *vma
--
--[[linux-4.4.1/vm_area_struct]]
-unsigned long addr
--
-unsigned long pfn
--
-unsigned long size
--
-pgprot_t prot
--
--[[linux-4.4.1/pgprot_t]]


**返り値 [#o1f4aebe]
-int
--


**参考 [#t4cd3c58]


*実装 [#s5a5b93b]

**CONFIG_MMU 有効: mm/memory.c [#j68c4666]
 /**
  * remap_pfn_range - remap kernel memory to userspace
  * @vma: user vma to map to
  * @addr: target user address to start at
  * @pfn: physical address of kernel memory
  * @size: size of map area
  * @prot: page protection flags for this mapping
  *
  *  Note: this is only safe if the mm semaphore is held when called.
  */
 int remap_pfn_range(struct vm_area_struct *vma, unsigned long addr,
                     unsigned long pfn, unsigned long size, pgprot_t prot)
 {
         pgd_t *pgd;
         unsigned long next;
         unsigned long end = addr + PAGE_ALIGN(size);
         struct mm_struct *mm = vma->vm_mm;
         int err;
 
-
--[[linux-4.4.1/PAGE_ALIGN()]]
--[[linux-4.4.1/mm_struct]]

         /*
          * Physically remapped pages are special. Tell the
          * rest of the world about it:
          *   VM_IO tells people not to look at these pages
          *      (accesses can have side effects).
          *   VM_PFNMAP tells the core MM that the base pages are just
          *      raw PFN mappings, and do not have a "struct page" associated
          *      with them.
          *   VM_DONTEXPAND
          *      Disable vma merging and expanding with mremap().
          *   VM_DONTDUMP
          *      Omit vma from core dump, even when VM_IO turned off.
          *
          * There's a horrible special case to handle copy-on-write
          * behaviour that some programs depend on. We mark the "original"
          * un-COW'ed pages by matching them up with "vma->vm_pgoff".
          * See vm_normal_page() for details.
          */
         if (is_cow_mapping(vma->vm_flags)) {
                 if (addr != vma->vm_start || end != vma->vm_end)
                         return -EINVAL;
                 vma->vm_pgoff = pfn;
         }
 
-
--[[linux-4.4.1/is_cow_mapping()]]

         err = track_pfn_remap(vma, &prot, pfn, addr, PAGE_ALIGN(size));
         if (err)
                 return -EINVAL;
 
-
--[[linux-4.4.1/track_pfn_remap()]]

         vma->vm_flags |= VM_IO | VM_PFNMAP | VM_DONTEXPAND | VM_DONTDUMP;
 
         BUG_ON(addr >= end);
         pfn -= addr >> PAGE_SHIFT;
         pgd = pgd_offset(mm, addr);
         flush_cache_range(vma, addr, end);
-
--[[linux-4.4.1/BUG_ON()]]
--[[linux-4.4.1/pgd_offset()]]
--[[linux-4.4.1/flush_cache_range()]]

         do {
                 next = pgd_addr_end(addr, end);
                 err = remap_pud_range(mm, pgd, addr, next,
                                 pfn + (addr >> PAGE_SHIFT), prot);
                 if (err)
                         break;
-
--[[linux-4.4.1/pgd_addr_end()]]
--[[linux-4.4.1/remap_pud_range()]]

         } while (pgd++, addr = next, addr != end);
 
         if (err)
                 untrack_pfn(vma, pfn, PAGE_ALIGN(size));
 
-
--[[linux-4.4.1/untrack_pfn()]]

         return err;
 }
 EXPORT_SYMBOL(remap_pfn_range);
-
--[[linux-4.4.1/EXPORT_SYMBOL()]]


**ONFIG_MMU 無効: mm/nommu.c [#ff4b047d]
 int remap_pfn_range(struct vm_area_struct *vma, unsigned long addr,
                 unsigned long pfn, unsigned long size, pgprot_t prot)
 {
         if (addr != (pfn << PAGE_SHIFT))
                 return -EINVAL;
 
         vma->vm_flags |= VM_IO | VM_PFNMAP | VM_DONTEXPAND | VM_DONTDUMP;
         return 0;
 }
 EXPORT_SYMBOL(remap_pfn_range);


*コメント [#zbb21cd8]


トップ   編集 差分 履歴 添付 複製 名前変更 リロード   新規 一覧 検索 最終更新   ヘルプ   最終更新のRSS