*参照元 [#v97fffcf]
#backlinks

*説明 [#tcf86616]
-パス: [[linux-4.4.1/arch/arm/mm/ioremap.c]]

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


**引数 [#p7f744cd]
-unsigned long pfn
--
-unsigned long offset
--
-size_t size
--
--[[linux-4.4.1/size_t]]
-unsigned int mtype
--
-void *caller
--呼び出し元のアドレス


**返り値 [#c22917b5]
-void __iomem *
--


**参考 [#f52fd24e]


*実装 [#e4a57ea6]
 static void __iomem * __arm_ioremap_pfn_caller(unsigned long pfn,
         unsigned long offset, size_t size, unsigned int mtype, void *caller)
 {
         const struct mem_type *type;
         int err;
         unsigned long addr;
         struct vm_struct *area;
         phys_addr_t paddr = __pfn_to_phys(pfn);
 
-
--[[linux-4.4.1/mem_type]]
--[[linux-4.4.1/vm_struct]]

 #ifndef CONFIG_ARM_LPAE
-
--[[linux-4.4.1/CONFIG_ARM_LPAE]]

         /*
          * High mappings must be supersection aligned
          */
         if (pfn >= 0x100000 && (paddr & ~SUPERSECTION_MASK))
                 return NULL;
 #endif
 
         type = get_mem_type(mtype);
         if (!type)
                 return NULL;
 
-
--[[linux-4.4.1/get_mem_type()]]

         /*
          * Page align the mapping size, taking account of any offset.
          */
         size = PAGE_ALIGN(offset + size);
 
-
--[[linux-4.4.1/PAGE_ALIGN()]]

         /*
          * Try to reuse one of the static mapping whenever possible.
          */
         if (size && !(sizeof(phys_addr_t) == 4 && pfn >= 0x100000)) {
                 struct static_vm *svm;
 
-
--[[linux-4.4.1/static_vm]]

                 svm = find_static_vm_paddr(paddr, size, mtype);
                 if (svm) {
                         addr = (unsigned long)svm->vm.addr;
                         addr += paddr - svm->vm.phys_addr;
                         return (void __iomem *) (offset + addr);
                 }
-
--[[linux-4.4.1/find_static_vm_paddr()]]

         }
 
         /*
          * Don't allow RAM to be mapped - this causes problems with ARMv6+
          */
         if (WARN_ON(pfn_valid(pfn)))
                 return NULL;
 
-
--[[linux-4.4.1/WARN_ON()]]
--[[linux-4.4.1/pfn_valid()]]

         area = get_vm_area_caller(size, VM_IOREMAP, caller);
         if (!area)
                 return NULL;
         addr = (unsigned long)area->addr;
         area->phys_addr = paddr;
 
-
--[[linux-4.4.1/get_vm_area_caller()]]

 #if !defined(CONFIG_SMP) && !defined(CONFIG_ARM_LPAE)
-
--[[linux-4.4.1/CONFIG_SMP]]
--[[linux-4.4.1/CONFIG_ARM_LPAE]]

         if (DOMAIN_IO == 0 &&
             (((cpu_architecture() >= CPU_ARCH_ARMv6) && (get_cr() & CR_XP)) ||
                cpu_is_xsc3()) && pfn >= 0x100000 &&
                !((paddr | size | addr) & ~SUPERSECTION_MASK)) {
-
--[[linux-4.4.1/cpu_architecture()]]
--[[linux-4.4.1/get_cr()]]
--[[linux-4.4.1/cpu_is_xsc3()]]

                 area->flags |= VM_ARM_SECTION_MAPPING;
                 err = remap_area_supersections(addr, pfn, size, type);
-
--[[linux-4.4.1/remap_area_supersections()]]

         } else if (!((paddr | size | addr) & ~PMD_MASK)) {
                 area->flags |= VM_ARM_SECTION_MAPPING;
                 err = remap_area_sections(addr, pfn, size, type);
-
--[[linux-4.4.1/remap_area_sections()]]

         } else
 #endif
                 err = ioremap_page_range(addr, addr + size, paddr,
                                          __pgprot(type->prot_pte));
 
-
--[[linux-4.4.1/ioremap_page_range()]]
--[[linux-4.4.1/__pgprot()]]

         if (err) {
                 vunmap((void *)addr);
                 return NULL;
         }
 
-
--[[linux-4.4.1/vunmap()]]

         flush_cache_vmap(addr, addr + size);
         return (void __iomem *) (offset + addr);
-
--[[linux-4.4.1/flush_cache_vmap()]]

 }


*コメント [#p66850ab]


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