linux-old/include/asm-i386/highmem.h
<<
>>
Prefs
   1/*
   2 * highmem.h: virtual kernel memory mappings for high memory
   3 *
   4 * Used in CONFIG_HIGHMEM systems for memory pages which
   5 * are not addressable by direct kernel virtual addresses.
   6 *
   7 * Copyright (C) 1999 Gerhard Wichert, Siemens AG
   8 *                    Gerhard.Wichert@pdb.siemens.de
   9 *
  10 *
  11 * Redesigned the x86 32-bit VM architecture to deal with 
  12 * up to 16 Terabyte physical memory. With current x86 CPUs
  13 * we now support up to 64 Gigabytes physical RAM.
  14 *
  15 * Copyright (C) 1999 Ingo Molnar <mingo@redhat.com>
  16 */
  17
  18#ifndef _ASM_HIGHMEM_H
  19#define _ASM_HIGHMEM_H
  20
  21#ifdef __KERNEL__
  22
  23#include <linux/config.h>
  24#include <linux/init.h>
  25#include <linux/interrupt.h>
  26#include <asm/kmap_types.h>
  27#include <asm/pgtable.h>
  28
  29#ifdef CONFIG_DEBUG_HIGHMEM
  30#define HIGHMEM_DEBUG 1
  31#else
  32#define HIGHMEM_DEBUG 0
  33#endif
  34
  35/* declarations for highmem.c */
  36extern unsigned long highstart_pfn, highend_pfn;
  37
  38extern pte_t *kmap_pte;
  39extern pgprot_t kmap_prot;
  40extern pte_t *pkmap_page_table;
  41
  42extern void kmap_init(void) __init;
  43
  44/*
  45 * Right now we initialize only a single pte table. It can be extended
  46 * easily, subsequent pte tables have to be allocated in one physical
  47 * chunk of RAM.
  48 */
  49#define PKMAP_BASE (0xff800000UL)
  50#ifdef CONFIG_X86_PAE
  51#define LAST_PKMAP 512
  52#else
  53#define LAST_PKMAP 1024
  54#endif
  55#define LAST_PKMAP_MASK (LAST_PKMAP-1)
  56#define PKMAP_NR(virt)  ((virt-PKMAP_BASE) >> PAGE_SHIFT)
  57#define PKMAP_ADDR(nr)  (PKMAP_BASE + ((nr) << PAGE_SHIFT))
  58
  59extern void * FASTCALL(kmap_high(struct page *page, int nonblocking));
  60extern void FASTCALL(kunmap_high(struct page *page));
  61
  62#define kmap(page) __kmap(page, 0)
  63#define kmap_nonblock(page) __kmap(page, 1)
  64
  65static inline void *__kmap(struct page *page, int nonblocking)
  66{
  67        if (in_interrupt())
  68                out_of_line_bug();
  69        if (page < highmem_start_page)
  70                return page_address(page);
  71        return kmap_high(page, nonblocking);
  72}
  73
  74static inline void kunmap(struct page *page)
  75{
  76        if (in_interrupt())
  77                out_of_line_bug();
  78        if (page < highmem_start_page)
  79                return;
  80        kunmap_high(page);
  81}
  82
  83/*
  84 * The use of kmap_atomic/kunmap_atomic is discouraged - kmap/kunmap
  85 * gives a more generic (and caching) interface. But kmap_atomic can
  86 * be used in IRQ contexts, so in some (very limited) cases we need
  87 * it.
  88 */
  89static inline void *kmap_atomic(struct page *page, enum km_type type)
  90{
  91        enum fixed_addresses idx;
  92        unsigned long vaddr;
  93
  94        if (page < highmem_start_page)
  95                return page_address(page);
  96
  97        idx = type + KM_TYPE_NR*smp_processor_id();
  98        vaddr = __fix_to_virt(FIX_KMAP_BEGIN + idx);
  99#if HIGHMEM_DEBUG
 100        if (!pte_none(*(kmap_pte-idx)))
 101                out_of_line_bug();
 102#endif
 103        set_pte(kmap_pte-idx, mk_pte(page, kmap_prot));
 104        __flush_tlb_one(vaddr);
 105
 106        return (void*) vaddr;
 107}
 108
 109static inline void kunmap_atomic(void *kvaddr, enum km_type type)
 110{
 111#if HIGHMEM_DEBUG
 112        unsigned long vaddr = (unsigned long) kvaddr & PAGE_MASK;
 113        enum fixed_addresses idx = type + KM_TYPE_NR*smp_processor_id();
 114
 115        if (vaddr < FIXADDR_START) // FIXME
 116                return;
 117
 118        if (vaddr != __fix_to_virt(FIX_KMAP_BEGIN+idx))
 119                out_of_line_bug();
 120
 121        /*
 122         * force other mappings to Oops if they'll try to access
 123         * this pte without first remap it
 124         */
 125        pte_clear(kmap_pte-idx);
 126        __flush_tlb_one(vaddr);
 127#endif
 128}
 129
 130#endif /* __KERNEL__ */
 131
 132#endif /* _ASM_HIGHMEM_H */
 133
lxr.linux.no kindly hosted by Redpill Linpro AS, provider of Linux consulting and operations services since 1995.