cache.h
上传用户:lgb322
上传日期:2013-02-24
资源大小:30529k
文件大小:8k
源码类别:

嵌入式Linux

开发平台:

Unix_Linux

  1. /*
  2.  *  linux/include/asm-arm/proc-armv/cache.h
  3.  *
  4.  *  Copyright (C) 1999-2001 Russell King
  5.  *
  6.  * This program is free software; you can redistribute it and/or modify
  7.  * it under the terms of the GNU General Public License version 2 as
  8.  * published by the Free Software Foundation.
  9.  */
  10. #include <asm/mman.h>
  11. /*
  12.  * This flag is used to indicate that the page pointed to by a pte
  13.  * is dirty and requires cleaning before returning it to the user.
  14.  */
  15. #define PG_dcache_dirty PG_arch_1
  16. /*
  17.  * Cache handling for 32-bit ARM processors.
  18.  *
  19.  * Note that on ARM, we have a more accurate specification than that
  20.  * Linux's "flush".  We therefore do not use "flush" here, but instead
  21.  * use:
  22.  *
  23.  * clean:      the act of pushing dirty cache entries out to memory.
  24.  * invalidate: the act of discarding data held within the cache,
  25.  *             whether it is dirty or not.
  26.  */
  27. /*
  28.  * Generic I + D cache
  29.  */
  30. #define flush_cache_all()
  31. do {
  32. cpu_cache_clean_invalidate_all();
  33. } while (0)
  34. /* This is always called for current->mm */
  35. #define flush_cache_mm(_mm)
  36. do {
  37. if ((_mm) == current->active_mm)
  38. cpu_cache_clean_invalidate_all();
  39. } while (0)
  40. #define flush_cache_range(_mm,_start,_end)
  41. do {
  42. if ((_mm) == current->active_mm)
  43. cpu_cache_clean_invalidate_range((_start) & PAGE_MASK, 
  44.  PAGE_ALIGN(_end), 1); 
  45. } while (0)
  46. #define flush_cache_page(_vma,_vmaddr)
  47. do {
  48. if ((_vma)->vm_mm == current->active_mm) {
  49. unsigned long _addr = (_vmaddr) & PAGE_MASK;
  50. cpu_cache_clean_invalidate_range(_addr,
  51. _addr + PAGE_SIZE,
  52. ((_vma)->vm_flags & VM_EXEC));
  53. } while (0)
  54. /*
  55.  * This flushes back any buffered write data.  We have to clean the entries
  56.  * in the cache for this page.  This does not invalidate either I or D caches.
  57.  *
  58.  * Called from:
  59.  * 1. mm/filemap.c:filemap_nopage
  60.  * 2. mm/filemap.c:filemap_nopage
  61.  *    [via do_no_page - ok]
  62.  *
  63.  * 3. mm/memory.c:break_cow
  64.  *    [copy_cow_page doesn't do anything to the cache; insufficient cache
  65.  *     handling.  Need to add flush_dcache_page() here]
  66.  *
  67.  * 4. mm/memory.c:do_swap_page
  68.  *    [read_swap_cache_async doesn't do anything to the cache: insufficient
  69.  *     cache handling.  Need to add flush_dcache_page() here]
  70.  *
  71.  * 5. mm/memory.c:do_anonymous_page
  72.  *    [zero page, never written by kernel - ok]
  73.  *
  74.  * 6. mm/memory.c:do_no_page
  75.  *    [we will be calling update_mmu_cache, which will catch on PG_dcache_dirty]
  76.  *
  77.  * 7. mm/shmem.c:shmem_nopage
  78.  * 8. mm/shmem.c:shmem_nopage
  79.  *    [via do_no_page - ok]
  80.  *
  81.  * 9. fs/exec.c:put_dirty_page
  82.  *    [we call flush_dcache_page prior to this, which will flush out the
  83.  *     kernel virtual addresses from the dcache - ok]
  84.  */
  85. static __inline__ void flush_page_to_ram(struct page *page)
  86. {
  87. cpu_flush_ram_page(page_address(page));
  88. }
  89. /*
  90.  * D cache only
  91.  */
  92. #define invalidate_dcache_range(_s,_e) cpu_dcache_invalidate_range((_s),(_e))
  93. #define clean_dcache_range(_s,_e) cpu_dcache_clean_range((_s),(_e))
  94. #define flush_dcache_range(_s,_e) cpu_cache_clean_invalidate_range((_s),(_e),0)
  95. /*
  96.  * flush_dcache_page is used when the kernel has written to the page
  97.  * cache page at virtual address page->virtual.
  98.  *
  99.  * If this page isn't mapped (ie, page->mapping = NULL), or it has
  100.  * userspace mappings (page->mapping->i_mmap or page->mapping->i_mmap_shared)
  101.  * then we _must_ always clean + invalidate the dcache entries associated
  102.  * with the kernel mapping.
  103.  *
  104.  * Otherwise we can defer the operation, and clean the cache when we are
  105.  * about to change to user space.  This is the same method as used on SPARC64.
  106.  * See update_mmu_cache for the user space part.
  107.  */
  108. #define mapping_mapped(map) ((map)->i_mmap || (map)->i_mmap_shared)
  109. static inline void flush_dcache_page(struct page *page)
  110. {
  111. if (page->mapping && !mapping_mapped(page->mapping))
  112. set_bit(PG_dcache_dirty, &page->flags);
  113. else {
  114. unsigned long virt = (unsigned long)page_address(page);
  115. cpu_cache_clean_invalidate_range(virt, virt + PAGE_SIZE, 0);
  116. }
  117. }
  118. #define clean_dcache_entry(_s) cpu_dcache_clean_entry((unsigned long)(_s))
  119. /*
  120.  * This function is misnamed IMHO.  There are three places where it
  121.  * is called, each of which is preceded immediately by a call to
  122.  * flush_page_to_ram:
  123.  *
  124.  *  1. kernel/ptrace.c:access_one_page
  125.  *     called after we have written to the kernel view of a user page.
  126.  *     The user page has been expundged from the cache by flush_cache_page.
  127.  *     [we don't need to do anything here if we add a call to
  128.  *      flush_dcache_page]
  129.  *
  130.  *  2. mm/memory.c:do_swap_page
  131.  *     called after we have (possibly) written to the kernel view of a
  132.  *     user page, which has previously been removed (ie, has been through
  133.  *     the swap cache).
  134.  *     [if the flush_page_to_ram() conditions are satisfied, then ok]
  135.  *
  136.  *  3. mm/memory.c:do_no_page
  137.  *     [if the flush_page_to_ram() conditions are satisfied, then ok]
  138.  *
  139.  * Invalidating the icache at the kernels virtual page isn't really
  140.  * going to do us much good, since we wouldn't have executed any
  141.  * instructions there.
  142.  */
  143. #define flush_icache_page(vma,pg) do { } while (0)
  144. /*
  145.  * I cache coherency stuff.
  146.  *
  147.  * This *is not* just icache.  It is to make data written to memory
  148.  * consistent such that instructions fetched from the region are what
  149.  * we expect.
  150.  *
  151.  * This generally means that we have to clean out the Dcache and write
  152.  * buffers, and maybe flush the Icache in the specified range.
  153.  */
  154. #define flush_icache_range(_s,_e)
  155. do {
  156. cpu_icache_invalidate_range((_s), (_e));
  157. } while (0)
  158. /*
  159.  * TLB flushing.
  160.  *
  161.  *  - flush_tlb_all() flushes all processes TLBs
  162.  *  - flush_tlb_mm(mm) flushes the specified mm context TLB's
  163.  *  - flush_tlb_page(vma, vmaddr) flushes TLB for specified page
  164.  *  - flush_tlb_range(mm, start, end) flushes TLB for specified range of pages
  165.  *
  166.  * We drain the write buffer in here to ensure that the page tables in ram
  167.  * are really up to date.  It is more efficient to do this here...
  168.  */
  169. /*
  170.  * Notes:
  171.  *  current->active_mm is the currently active memory description.
  172.  *  current->mm == NULL iff we are lazy.
  173.  */
  174. #define flush_tlb_all()
  175. do {
  176. cpu_tlb_invalidate_all();
  177. } while (0)
  178. /*
  179.  * Flush all user virtual address space translations described by `_mm'.
  180.  *
  181.  * Currently, this is always called for current->mm, which should be
  182.  * the same as current->active_mm.  This is currently not be called for
  183.  * the lazy TLB case.
  184.  */
  185. #define flush_tlb_mm(_mm)
  186. do {
  187. if ((_mm) == current->active_mm)
  188. cpu_tlb_invalidate_all();
  189. } while (0)
  190. /*
  191.  * Flush the specified range of user virtual address space translations.
  192.  *
  193.  * _mm may not be current->active_mm, but may not be NULL.
  194.  */
  195. #define flush_tlb_range(_mm,_start,_end)
  196. do {
  197. if ((_mm) == current->active_mm)
  198. cpu_tlb_invalidate_range((_start), (_end));
  199. } while (0)
  200. /*
  201.  * Flush the specified user virtual address space translation.
  202.  */
  203. #define flush_tlb_page(_vma,_page)
  204. do {
  205. if ((_vma)->vm_mm == current->active_mm)
  206. cpu_tlb_invalidate_page((_page),
  207.  ((_vma)->vm_flags & VM_EXEC));
  208. } while (0)
  209. /*
  210.  * if PG_dcache_dirty is set for the page, we need to ensure that any
  211.  * cache entries for the kernels virtual memory range are written
  212.  * back to the page.
  213.  */
  214. extern void update_mmu_cache(struct vm_area_struct *vma, unsigned long addr, pte_t pte);
  215. /*
  216.  * Old ARM MEMC stuff.  This supports the reversed mapping handling that
  217.  * we have on the older 26-bit machines.  We don't have a MEMC chip, so...
  218.  */
  219. #define memc_update_all() do { } while (0)
  220. #define memc_update_mm(mm) do { } while (0)
  221. #define memc_update_addr(mm,pte,log) do { } while (0)
  222. #define memc_clear(mm,physaddr) do { } while (0)