2 * atomic_kmap.h: temporary virtual kernel memory mappings
4 * Copyright (C) 2003 Ingo Molnar <mingo@redhat.com>
7 #ifndef _ASM_ATOMIC_KMAP_H
8 #define _ASM_ATOMIC_KMAP_H
12 #include <linux/config.h>
13 #include <asm/tlbflush.h>
15 #ifdef CONFIG_DEBUG_HIGHMEM
16 #define HIGHMEM_DEBUG 1
18 #define HIGHMEM_DEBUG 0
21 extern pte_t *kmap_pte;
22 #define kmap_prot PAGE_KERNEL
23 #define kmap_prot_nocache PAGE_KERNEL_NOCACHE
25 #define PKMAP_BASE (0xff000000UL)
26 #define NR_SHARED_PMDS ((0xffffffff-PKMAP_BASE+1)/PMD_SIZE)
28 static inline unsigned long __kmap_atomic_vaddr(enum km_type type)
30 enum fixed_addresses idx;
32 idx = type + KM_TYPE_NR*smp_processor_id();
33 return __fix_to_virt(FIX_KMAP_BEGIN + idx);
36 static inline void *__kmap_atomic_noflush(struct page *page, enum km_type type)
38 enum fixed_addresses idx;
41 idx = type + KM_TYPE_NR*smp_processor_id();
42 vaddr = __fix_to_virt(FIX_KMAP_BEGIN + idx);
44 * NOTE: entries that rely on some secondary TLB-flush
45 * effect must not be global:
47 set_pte(kmap_pte-idx, mk_pte(page, PAGE_KERNEL));
52 static inline void *__kmap_atomic(struct page *page, enum km_type type)
54 enum fixed_addresses idx;
57 idx = type + KM_TYPE_NR*smp_processor_id();
58 vaddr = __fix_to_virt(FIX_KMAP_BEGIN + idx);
60 BUG_ON(!pte_none(*(kmap_pte-idx)));
63 * Performance optimization - do not flush if the new
64 * pte is the same as the old one:
66 if (pte_val(*(kmap_pte-idx)) == pte_val(mk_pte(page, kmap_prot)))
67 return (void *) vaddr;
69 set_pte(kmap_pte-idx, mk_pte(page, kmap_prot));
70 __flush_tlb_one(vaddr);
75 static inline void __kunmap_atomic(void *kvaddr, enum km_type type)
78 unsigned long vaddr = (unsigned long) kvaddr & PAGE_MASK;
79 enum fixed_addresses idx = type + KM_TYPE_NR*smp_processor_id();
81 BUG_ON(vaddr != __fix_to_virt(FIX_KMAP_BEGIN+idx));
83 * force other mappings to Oops if they'll try to access
84 * this pte without first remap it
86 pte_clear(kmap_pte-idx);
87 __flush_tlb_one(vaddr);
91 #define __kunmap_atomic_type(type) \
92 __kunmap_atomic((void *)__kmap_atomic_vaddr(type), (type))
94 #endif /* __KERNEL__ */
96 #endif /* _ASM_ATOMIC_KMAP_H */