diff --git a/mmu.h b/mmu.h index 48a3787..c8b45fc 100644 --- a/mmu.h +++ b/mmu.h @@ -15,12 +15,12 @@ // Segment selectors (indexes) in our GDTs. // Defined by our convention, not the architecture. -#define KCSEG32 (1<<3) /* kernel 32-bit code segment */ -#define KCSEG (2<<3) /* kernel code segment */ -#define KDSEG (3<<3) /* kernel data segment */ -#define TSSSEG (4<<3) /* tss segment - takes two slots */ -#define UDSEG (6<<3) /* user data segment */ -#define UCSEG (7<<3) /* user code segment */ +#define SEG_KCODE32 (1<<3) // kernel 32-bit code segment +#define SEG_KCODE (2<<3) // kernel code segment +#define SEG_KDATA (3<<3) // kernel data segment +#define SEG_TSS (4<<3) // tss segment - takes two slots +#define SEG_UDATA (6<<3) // user data segment +#define SEG_UCODE (7<<3) // user code segment #define NSEGS 8 @@ -54,21 +54,21 @@ struct segdesc { #define DPL_USER 0x3 // User DPL -#define SEG_A (1<<0) /* segment accessed bit */ -#define SEG_R (1<<1) /* readable (code) */ -#define SEG_W (1<<1) /* writable (data) */ -#define SEG_C (1<<2) /* conforming segment (code) */ -#define SEG_E (1<<2) /* expand-down bit (data) */ -#define SEG_CODE (1<<3) /* code segment (instead of data) */ +#define SEG_A (1<<0) // segment accessed bit +#define SEG_R (1<<1) // readable (code) +#define SEG_W (1<<1) // writable (data) +#define SEG_C (1<<2) // conforming segment (code) +#define SEG_E (1<<2) // expand-down bit (data) +#define SEG_CODE (1<<3) // code segment (instead of data) // User and system segment bits. -#define SEG_S (1<<4) /* if 0, system descriptor */ -#define SEG_DPL(x) ((x)<<5) /* descriptor privilege level (2 bits) */ -#define SEG_P (1<<7) /* segment present */ -#define SEG_AVL (1<<8) /* available for operating system use */ -#define SEG_L (1<<9) /* long mode */ -#define SEG_D (1<<10) /* default operation size 32-bit */ -#define SEG_G (1<<11) /* granularity */ +#define SEG_S (1<<4) // if 0, system descriptor +#define SEG_DPL(x) ((x)<<5) // descriptor privilege level (2 bits) +#define SEG_P (1<<7) // segment present +#define SEG_AVL (1<<8) // available for operating system use +#define SEG_L (1<<9) // long mode +#define SEG_D (1<<10) // default operation size 32-bit +#define SEG_G (1<<11) // granularity // Application segment type bits #define STA_X 0x8 // Executable segment @@ -76,12 +76,12 @@ struct segdesc { #define STA_R 0x2 // Readable (executable segments) // System segment type bits -#define SEG_LDT (2<<0) /* local descriptor table */ -#define SEG_TSS64A (9<<0) /* available 64-bit TSS */ -#define SEG_TSS64B (11<<0) /* busy 64-bit TSS */ -#define SEG_CALL64 (12<<0) /* 64-bit call gate */ -#define SEG_INTR64 (14<<0) /* 64-bit interrupt gate */ -#define SEG_TRAP64 (15<<0) /* 64-bit trap gate */ +#define SEG_LDT (2<<0) // local descriptor table +#define SEG_TSS64A (9<<0) // available 64-bit TSS +#define SEG_TSS64B (11<<0) // busy 64-bit TSS +#define SEG_CALL64 (12<<0) // 64-bit call gate +#define SEG_INTR64 (14<<0) // 64-bit interrupt gate +#define SEG_TRAP64 (15<<0) // 64-bit trap gate // A virtual address 'la' has a six-part structure as follows: // @@ -129,7 +129,7 @@ struct taskstate { uint8 iopb[0]; } __attribute__ ((packed)); -#define INT_P (1<<7) /* interrupt descriptor present */ +#define INT_P (1<<7) // interrupt descriptor present struct intgate { diff --git a/proc.c b/proc.c index 4d0faec..14c3da8 100644 --- a/proc.c +++ b/proc.c @@ -139,8 +139,8 @@ userinit(void) inituvm(p->pgdir, _binary_initcode_start, (uint64)_binary_initcode_size); p->sz = PGSIZE; memset(p->tf, 0, sizeof(*p->tf)); - p->tf->cs = UCSEG | 0x3; - p->tf->ss = UDSEG | 0x3; + p->tf->cs = SEG_UCODE | DPL_USER; + p->tf->ss = SEG_UDATA | DPL_USER; p->tf->r11 = FL_IF; p->tf->rsp = PGSIZE; p->tf->rcx = 0; // beginning of initcode.S diff --git a/trap.c b/trap.c index c6c6bc2..afa0e18 100644 --- a/trap.c +++ b/trap.c @@ -20,7 +20,7 @@ tvinit(void) int i; for(i=0; i<256; i++) { - idt[i] = INTDESC(KCSEG, vectors[i], INT_P | SEG_INTR64); + idt[i] = INTDESC(SEG_KCODE, vectors[i], INT_P | SEG_INTR64); } idtinit(); diff --git a/vm.c b/vm.c index e992ed4..4b272ff 100644 --- a/vm.c +++ b/vm.c @@ -49,13 +49,13 @@ seginit(void) // to (star >> 32) + 8 and the CS selector to (star >> 32). // When executing a sysret instruction the CPU sets the SS selector // to (star >> 48) + 8 and the CS selector to (star >> 48) + 16. - uint64 star = ((((uint64)UCSEG|0x3)- 16)<<48)|((uint64)(KCSEG)<<32); + uint64 star = ((((uint64)SEG_UCODE|0x3)- 16)<<48)|((uint64)(SEG_KCODE)<<32); writemsr(MSR_STAR, star); writemsr(MSR_LSTAR, (uint64)&sysentry); writemsr(MSR_SFMASK, FL_TF | FL_IF); // Initialize cpu-local storage. - writegs(KDSEG); + writegs(SEG_KDATA); writemsr(MSR_GS_BASE, (uint64)c); writemsr(MSR_GS_KERNBASE, (uint64)c); } @@ -202,8 +202,8 @@ switchuvm(struct proc *p) c = mycpu(); uint64 base = (uint64) &(c->ts); - c->gdt[TSSSEG>>3] = SEGDESC(base, (sizeof(c->ts)-1), SEG_P|SEG_TSS64A); - c->gdt[(TSSSEG>>3)+1] = SEGDESCHI(base); + c->gdt[SEG_TSS>>3] = SEGDESC(base, (sizeof(c->ts)-1), SEG_P|SEG_TSS64A); + c->gdt[(SEG_TSS>>3)+1] = SEGDESCHI(base); c->ts.rsp[0] = (uint64) p->kstack + KSTACKSIZE; c->ts.iomba = (ushort) 0xFFFF; @@ -211,7 +211,7 @@ switchuvm(struct proc *p) dtr.base = (uint64)c->gdt; lgdt((void *)&dtr.limit); - ltr(TSSSEG); + ltr(SEG_TSS); lcr3(V2P(p->pgdir)); // switch to process's address space