source: mainline/arch/ia32/src/pm.c@ dcbc8be

lfn serial ticket/834-toolchain-update topic/msim-upgrade topic/simplify-dev-export
Last change on this file since dcbc8be was dcbc8be, checked in by Jakub Jermar <jakub@…>, 20 years ago

Big changes in IA-32 address space map.
Now the kernel is mapped above 0x80000000. Finally!
Userspace address space starts at 0x00000000.
Changes in many places.
This improvement temporarily breaks SMP and most likely also other stuff.
Supported size of memory is now only 4M as it is the biggest size that can be mapped at once on IA-32.

Changes in linker script.
Changes required because of the above.
Do not patch hardcoded_* variables but assign to them instead.

Cosmetic changes here and there.

  • Property mode set to 100644
File size: 5.0 KB
Line 
1/*
2 * Copyright (C) 2001-2004 Jakub Jermar
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * - Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * - Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * - The name of the author may not be used to endorse or promote products
15 * derived from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29#include <arch/pm.h>
30#include <config.h>
31#include <arch/types.h>
32#include <typedefs.h>
33#include <arch/interrupt.h>
34#include <arch/asm.h>
35#include <arch/context.h>
36#include <panic.h>
37
38/*
39 * Early ia32 configuration functions and data structures.
40 */
41
42/*
43 * We have no use for segmentation so we set up flat mode. In this
44 * mode, we use, for each privilege level, two segments spanning the
45 * whole memory. One is for code and one is for data.
46 */
47struct descriptor gdt[GDT_ITEMS] = {
48 /* NULL descriptor */
49 { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 },
50 /* KTEXT descriptor */
51 { 0xffff, 0, 0, AR_PRESENT | AR_CODE | DPL_KERNEL, 0xf, 0, 0, 1, 1, 0 },
52 /* KDATA descriptor */
53 { 0xffff, 0, 0, AR_PRESENT | AR_DATA | AR_WRITABLE | DPL_KERNEL, 0xf, 0, 0, 1, 1, 0 },
54 /* UTEXT descriptor */
55 { 0xffff, 0, 0, AR_PRESENT | AR_CODE | DPL_USER, 0xf, 0, 0, 1, 1, 0 },
56 /* UDATA descriptor */
57 { 0xffff, 0, 0, AR_PRESENT | AR_DATA | AR_WRITABLE | DPL_USER, 0xf, 0, 0, 1, 1, 0 },
58 /* TSS descriptor - set up will be completed later */
59 { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0 }
60};
61
62static struct idescriptor idt[IDT_ITEMS];
63
64static struct tss tss;
65
66struct tss *tss_p = NULL;
67
68/* gdtr is changed by kmp before next CPU is initialized */
69struct ptr_16_32 gdtr __attribute__ ((section ("K_DATA_START"))) = { .limit = sizeof(gdt), .base = KA2PA((__address) gdt) };
70struct ptr_16_32 idtr __attribute__ ((section ("K_DATA_START"))) = { .limit = sizeof(idt), .base = KA2PA((__address) idt) };
71
72void gdt_setbase(struct descriptor *d, __address base)
73{
74 d->base_0_15 = KA2PA(base) & 0xffff;
75 d->base_16_23 = (KA2PA(base) >> 16) & 0xff;
76 d->base_24_31 = (KA2PA(base) >> 24) & 0xff;
77}
78
79void gdt_setlimit(struct descriptor *d, __u32 limit)
80{
81 d->limit_0_15 = limit & 0xffff;
82 d->limit_16_19 = (limit >> 16) & 0xf;
83}
84
85void idt_setoffset(struct idescriptor *d, __address offset)
86{
87 d->offset_0_15 = KA2PA(offset) & 0xffff;
88 d->offset_16_31 = KA2PA(offset) >> 16;
89}
90
91void tss_initialize(struct tss *t)
92{
93 memsetb((__address) t, sizeof(struct tss), 0);
94}
95
96/*
97 * This function takes care of proper setup of IDT and IDTR.
98 */
99void idt_init(void)
100{
101 struct idescriptor *d;
102 int i;
103
104 for (i = 0; i < IDT_ITEMS; i++) {
105 d = &idt[i];
106
107 d->unused = 0;
108 d->selector = selector(KTEXT_DES);
109
110 d->access = AR_PRESENT | AR_INTERRUPT; /* masking interrupt */
111
112 if (i == VECTOR_SYSCALL) {
113 /*
114 * The syscall interrupt gate must be calleable from userland.
115 */
116 d->access |= DPL_USER;
117 }
118
119 idt_setoffset(d, ((__address) interrupt_handlers) + i*interrupt_handler_size);
120 trap_register(i, null_interrupt);
121 }
122 trap_register(13, gp_fault);
123 trap_register( 7, nm_fault);
124 trap_register(12, ss_fault);
125}
126
127
128void pm_init(void)
129{
130 struct descriptor *gdt_p = (struct descriptor *) gdtr.base;
131
132 /*
133 * Each CPU has its private GDT and TSS.
134 * All CPUs share one IDT.
135 */
136
137 if (config.cpu_active == 1) {
138 idt_init();
139 /*
140 * NOTE: bootstrap CPU has statically allocated TSS, because
141 * the heap hasn't been initialized so far.
142 */
143 tss_p = &tss;
144 }
145 else {
146 tss_p = (struct tss *) malloc(sizeof(struct tss));
147 if (!tss_p)
148 panic("could not allocate TSS\n");
149 }
150
151 tss_initialize(tss_p);
152
153 gdt_p[TSS_DES].access = AR_PRESENT | AR_TSS | DPL_KERNEL;
154 gdt_p[TSS_DES].special = 1;
155 gdt_p[TSS_DES].granularity = 1;
156
157 gdt_setbase(&gdt_p[TSS_DES], (__address) tss_p);
158 gdt_setlimit(&gdt_p[TSS_DES], sizeof(struct tss) - 1);
159
160 /*
161 * As of this moment, the current CPU has its own GDT pointing
162 * to its own TSS. We just need to load the TR register.
163 */
164 __asm__("ltr %0" : : "r" ((__u16) selector(TSS_DES)));
165}
Note: See TracBrowser for help on using the repository browser.