cacheflush.h 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117
  1. /* SPDX-License-Identifier: GPL-2.0-only */
  2. /*
  3. * Copyright (C) 2004, 2007-2010, 2011-2012 Synopsys, Inc. (www.synopsys.com)
  4. *
  5. * vineetg: May 2011: for Non-aliasing VIPT D-cache following can be NOPs
  6. * -flush_cache_dup_mm (fork)
  7. * -likewise for flush_cache_mm (exit/execve)
  8. * -likewise for flush_cache_{range,page} (munmap, exit, COW-break)
  9. *
  10. * vineetg: April 2008
  11. * -Added a critical CacheLine flush to copy_to_user_page( ) which
  12. * was causing gdbserver to not setup breakpoints consistently
  13. */
  14. #ifndef _ASM_CACHEFLUSH_H
  15. #define _ASM_CACHEFLUSH_H
  16. #include <linux/mm.h>
  17. #include <asm/shmparam.h>
  18. /*
  19. * Semantically we need this because icache doesn't snoop dcache/dma.
  20. * However ARC Cache flush requires paddr as well as vaddr, latter not available
  21. * in the flush_icache_page() API. So we no-op it but do the equivalent work
  22. * in update_mmu_cache()
  23. */
  24. #define flush_icache_page(vma, page)
  25. void flush_cache_all(void);
  26. void flush_icache_range(unsigned long kstart, unsigned long kend);
  27. void __sync_icache_dcache(phys_addr_t paddr, unsigned long vaddr, int len);
  28. void __inv_icache_page(phys_addr_t paddr, unsigned long vaddr);
  29. void __flush_dcache_page(phys_addr_t paddr, unsigned long vaddr);
  30. #define ARCH_IMPLEMENTS_FLUSH_DCACHE_PAGE 1
  31. void flush_dcache_page(struct page *page);
  32. void dma_cache_wback_inv(phys_addr_t start, unsigned long sz);
  33. void dma_cache_inv(phys_addr_t start, unsigned long sz);
  34. void dma_cache_wback(phys_addr_t start, unsigned long sz);
  35. #define flush_dcache_mmap_lock(mapping) do { } while (0)
  36. #define flush_dcache_mmap_unlock(mapping) do { } while (0)
  37. /* TBD: optimize this */
  38. #define flush_cache_vmap(start, end) flush_cache_all()
  39. #define flush_cache_vunmap(start, end) flush_cache_all()
  40. #define flush_cache_dup_mm(mm) /* called on fork (VIVT only) */
  41. #ifndef CONFIG_ARC_CACHE_VIPT_ALIASING
  42. #define flush_cache_mm(mm) /* called on munmap/exit */
  43. #define flush_cache_range(mm, u_vstart, u_vend)
  44. #define flush_cache_page(vma, u_vaddr, pfn) /* PF handling/COW-break */
  45. #else /* VIPT aliasing dcache */
  46. /* To clear out stale userspace mappings */
  47. void flush_cache_mm(struct mm_struct *mm);
  48. void flush_cache_range(struct vm_area_struct *vma,
  49. unsigned long start,unsigned long end);
  50. void flush_cache_page(struct vm_area_struct *vma,
  51. unsigned long user_addr, unsigned long page);
  52. /*
  53. * To make sure that userspace mapping is flushed to memory before
  54. * get_user_pages() uses a kernel mapping to access the page
  55. */
  56. #define ARCH_HAS_FLUSH_ANON_PAGE
  57. void flush_anon_page(struct vm_area_struct *vma,
  58. struct page *page, unsigned long u_vaddr);
  59. #endif /* CONFIG_ARC_CACHE_VIPT_ALIASING */
  60. /*
  61. * A new pagecache page has PG_arch_1 clear - thus dcache dirty by default
  62. * This works around some PIO based drivers which don't call flush_dcache_page
  63. * to record that they dirtied the dcache
  64. */
  65. #define PG_dc_clean PG_arch_1
  66. #define CACHE_COLORS_NUM 4
  67. #define CACHE_COLORS_MSK (CACHE_COLORS_NUM - 1)
  68. #define CACHE_COLOR(addr) (((unsigned long)(addr) >> (PAGE_SHIFT)) & CACHE_COLORS_MSK)
  69. /*
  70. * Simple wrapper over config option
  71. * Bootup code ensures that hardware matches kernel configuration
  72. */
  73. static inline int cache_is_vipt_aliasing(void)
  74. {
  75. return IS_ENABLED(CONFIG_ARC_CACHE_VIPT_ALIASING);
  76. }
  77. /*
  78. * checks if two addresses (after page aligning) index into same cache set
  79. */
  80. #define addr_not_cache_congruent(addr1, addr2) \
  81. ({ \
  82. cache_is_vipt_aliasing() ? \
  83. (CACHE_COLOR(addr1) != CACHE_COLOR(addr2)) : 0; \
  84. })
  85. #define copy_to_user_page(vma, page, vaddr, dst, src, len) \
  86. do { \
  87. memcpy(dst, src, len); \
  88. if (vma->vm_flags & VM_EXEC) \
  89. __sync_icache_dcache((unsigned long)(dst), vaddr, len); \
  90. } while (0)
  91. #define copy_from_user_page(vma, page, vaddr, dst, src, len) \
  92. memcpy(dst, src, len); \
  93. #endif