diff options
author | nyan <nyan@FreeBSD.org> | 2005-04-14 14:19:47 +0000 |
---|---|---|
committer | nyan <nyan@FreeBSD.org> | 2005-04-14 14:19:47 +0000 |
commit | 53c3ea2a7c84f6369519e017d0a519b9a7d85396 (patch) | |
tree | 1e40d1922ddf7eb813b027363d774981c626f356 /sys/pc98 | |
parent | 1db0102589254b05ac7d148ba68af585f98634a7 (diff) | |
download | FreeBSD-src-53c3ea2a7c84f6369519e017d0a519b9a7d85396.zip FreeBSD-src-53c3ea2a7c84f6369519e017d0a519b9a7d85396.tar.gz |
MFi386: revision 1.612.
Diffstat (limited to 'sys/pc98')
-rw-r--r-- | sys/pc98/i386/machdep.c | 138 | ||||
-rw-r--r-- | sys/pc98/pc98/machdep.c | 138 |
2 files changed, 176 insertions, 100 deletions
diff --git a/sys/pc98/i386/machdep.c b/sys/pc98/i386/machdep.c index c338d86..ab6c5c9 100644 --- a/sys/pc98/i386/machdep.c +++ b/sys/pc98/i386/machdep.c @@ -1292,7 +1292,12 @@ static char dblfault_stack[PAGE_SIZE]; extern vm_offset_t proc0kstack; -/* software prototypes -- in more palatable form */ +/* + * software prototypes -- in more palatable form. + * + * GCODE_SEL through GUDATA_SEL must be in this order for syscall/sysret + * GUFS_SEL and GUGS_SEL must be in this order (swtch.s knows it) + */ struct soft_segment_descriptor gdt_segs[] = { /* GNULL_SEL 0 Null Descriptor */ { 0x0, /* segment base address */ @@ -1303,7 +1308,34 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* default 32 vs 16 bit size */ 0 /* limit granularity (byte/page units)*/ }, -/* GCODE_SEL 1 Code Descriptor for kernel */ +/* GPRIV_SEL 1 SMP Per-Processor Private Data Descriptor */ +{ 0x0, /* segment base address */ + 0xfffff, /* length - all address space */ + SDT_MEMRWA, /* segment type */ + 0, /* segment descriptor priority level */ + 1, /* segment descriptor present */ + 0, 0, + 1, /* default 32 vs 16 bit size */ + 1 /* limit granularity (byte/page units)*/ }, +/* GUFS_SEL 2 %fs Descriptor for user */ +{ 0x0, /* segment base address */ + 0xfffff, /* length - all address space */ + SDT_MEMRWA, /* segment type */ + SEL_UPL, /* segment descriptor priority level */ + 1, /* segment descriptor present */ + 0, 0, + 1, /* default 32 vs 16 bit size */ + 1 /* limit granularity (byte/page units)*/ }, +/* GUGS_SEL 3 %gs Descriptor for user */ +{ 0x0, /* segment base address */ + 0xfffff, /* length - all address space */ + SDT_MEMRWA, /* segment type */ + SEL_UPL, /* segment descriptor priority level */ + 1, /* segment descriptor present */ + 0, 0, + 1, /* default 32 vs 16 bit size */ + 1 /* limit granularity (byte/page units)*/ }, +/* GCODE_SEL 4 Code Descriptor for kernel */ { 0x0, /* segment base address */ 0xfffff, /* length - all address space */ SDT_MEMERA, /* segment type */ @@ -1312,7 +1344,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 1, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GDATA_SEL 2 Data Descriptor for kernel */ +/* GDATA_SEL 5 Data Descriptor for kernel */ { 0x0, /* segment base address */ 0xfffff, /* length - all address space */ SDT_MEMRWA, /* segment type */ @@ -1321,16 +1353,34 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 1, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GPRIV_SEL 3 SMP Per-Processor Private Data Descriptor */ +/* GUCODE_SEL 6 Code Descriptor for user */ +{ 0x0, /* segment base address */ + 0xfffff, /* length - all address space */ + SDT_MEMERA, /* segment type */ + SEL_UPL, /* segment descriptor priority level */ + 1, /* segment descriptor present */ + 0, 0, + 1, /* default 32 vs 16 bit size */ + 1 /* limit granularity (byte/page units)*/ }, +/* GUDATA_SEL 7 Data Descriptor for user */ { 0x0, /* segment base address */ 0xfffff, /* length - all address space */ SDT_MEMRWA, /* segment type */ + SEL_UPL, /* segment descriptor priority level */ + 1, /* segment descriptor present */ + 0, 0, + 1, /* default 32 vs 16 bit size */ + 1 /* limit granularity (byte/page units)*/ }, +/* GBIOSLOWMEM_SEL 8 BIOS access to realmode segment 0x40, must be #8 in GDT */ +{ 0x400, /* segment base address */ + 0xfffff, /* length */ + SDT_MEMRWA, /* segment type */ 0, /* segment descriptor priority level */ 1, /* segment descriptor present */ 0, 0, 1, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GPROC0_SEL 4 Proc 0 Tss Descriptor */ +/* GPROC0_SEL 9 Proc 0 Tss Descriptor */ { 0x0, /* segment base address */ sizeof(struct i386tss)-1,/* length */ @@ -1340,7 +1390,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* unused - default 32 vs 16 bit size */ 0 /* limit granularity (byte/page units)*/ }, -/* GLDT_SEL 5 LDT Descriptor */ +/* GLDT_SEL 10 LDT Descriptor */ { (int) ldt, /* segment base address */ sizeof(ldt)-1, /* length - all address space */ SDT_SYSLDT, /* segment type */ @@ -1349,7 +1399,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* unused - default 32 vs 16 bit size */ 0 /* limit granularity (byte/page units)*/ }, -/* GUSERLDT_SEL 6 User LDT Descriptor per process */ +/* GUSERLDT_SEL 11 User LDT Descriptor per process */ { (int) ldt, /* segment base address */ (512 * sizeof(union descriptor)-1), /* length */ SDT_SYSLDT, /* segment type */ @@ -1358,25 +1408,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* unused - default 32 vs 16 bit size */ 0 /* limit granularity (byte/page units)*/ }, -/* GTGATE_SEL 7 Null Descriptor - Placeholder */ -{ 0x0, /* segment base address */ - 0x0, /* length - all address space */ - 0, /* segment type */ - 0, /* segment descriptor priority level */ - 0, /* segment descriptor present */ - 0, 0, - 0, /* default 32 vs 16 bit size */ - 0 /* limit granularity (byte/page units)*/ }, -/* GBIOSLOWMEM_SEL 8 BIOS access to realmode segment 0x40, must be #8 in GDT */ -{ 0x400, /* segment base address */ - 0xfffff, /* length */ - SDT_MEMRWA, /* segment type */ - 0, /* segment descriptor priority level */ - 1, /* segment descriptor present */ - 0, 0, - 1, /* default 32 vs 16 bit size */ - 1 /* limit granularity (byte/page units)*/ }, -/* GPANIC_SEL 9 Panic Tss Descriptor */ +/* GPANIC_SEL 12 Panic Tss Descriptor */ { (int) &dblfault_tss, /* segment base address */ sizeof(struct i386tss)-1,/* length - all address space */ SDT_SYS386TSS, /* segment type */ @@ -1385,7 +1417,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* unused - default 32 vs 16 bit size */ 0 /* limit granularity (byte/page units)*/ }, -/* GBIOSCODE32_SEL 10 BIOS 32-bit interface (32bit Code) */ +/* GBIOSCODE32_SEL 13 BIOS 32-bit interface (32bit Code) */ { 0, /* segment base address (overwritten) */ 0xfffff, /* length */ SDT_MEMERA, /* segment type */ @@ -1394,7 +1426,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GBIOSCODE16_SEL 11 BIOS 32-bit interface (16bit Code) */ +/* GBIOSCODE16_SEL 14 BIOS 32-bit interface (16bit Code) */ { 0, /* segment base address (overwritten) */ 0xfffff, /* length */ SDT_MEMERA, /* segment type */ @@ -1403,7 +1435,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GBIOSDATA_SEL 12 BIOS 32-bit interface (Data) */ +/* GBIOSDATA_SEL 15 BIOS 32-bit interface (Data) */ { 0, /* segment base address (overwritten) */ 0xfffff, /* length */ SDT_MEMRWA, /* segment type */ @@ -1412,7 +1444,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 1, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GBIOSUTIL_SEL 13 BIOS 16-bit interface (Utility) */ +/* GBIOSUTIL_SEL 16 BIOS 16-bit interface (Utility) */ { 0, /* segment base address (overwritten) */ 0xfffff, /* length */ SDT_MEMRWA, /* segment type */ @@ -1421,7 +1453,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GBIOSARGS_SEL 14 BIOS 16-bit interface (Arguments) */ +/* GBIOSARGS_SEL 17 BIOS 16-bit interface (Arguments) */ { 0, /* segment base address (overwritten) */ 0xfffff, /* length */ SDT_MEMRWA, /* segment type */ @@ -1430,6 +1462,15 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, +/* GNDIS_SEL 18 NDIS Descriptor */ +{ 0x0, /* segment base address */ + 0x0, /* length */ + 0, /* segment type */ + 0, /* segment descriptor priority level */ + 0, /* segment descriptor present */ + 0, 0, + 0, /* default 32 vs 16 bit size */ + 0 /* limit granularity (byte/page units)*/ }, }; static struct soft_segment_descriptor ldt_segs[] = { @@ -1881,25 +1922,22 @@ init386(first) init_param1(); /* - * make gdt memory segments, the code segment goes up to end of the - * page with etext in it, the data segment goes to the end of - * the address space - */ - /* - * XXX text protection is temporarily (?) disabled. The limit was - * i386_btop(round_page(etext)) - 1. + * Make gdt memory segments. All segments cover the full 4GB + * of address space and permissions are enforced at page level. */ gdt_segs[GCODE_SEL].ssd_limit = atop(0 - 1); gdt_segs[GDATA_SEL].ssd_limit = atop(0 - 1); + gdt_segs[GUCODE_SEL].ssd_limit = atop(0 - 1); + gdt_segs[GUDATA_SEL].ssd_limit = atop(0 - 1); + gdt_segs[GUFS_SEL].ssd_limit = atop(0 - 1); + gdt_segs[GUGS_SEL].ssd_limit = atop(0 - 1); + #ifdef SMP pc = &SMP_prvspace[0].pcpu; - gdt_segs[GPRIV_SEL].ssd_limit = - atop(sizeof(struct privatespace) - 1); #else pc = &__pcpu; - gdt_segs[GPRIV_SEL].ssd_limit = - atop(sizeof(struct pcpu) - 1); #endif + gdt_segs[GPRIV_SEL].ssd_limit = atop(0 - 1); gdt_segs[GPRIV_SEL].ssd_base = (int) pc; gdt_segs[GPROC0_SEL].ssd_base = (int) &pc->pc_common_tss; @@ -1928,12 +1966,8 @@ init386(first) mtx_init(&icu_lock, "icu", NULL, MTX_SPIN | MTX_NOWITNESS); /* make ldt memory segments */ - /* - * XXX - VM_MAXUSER_ADDRESS is an end address, not a max. And it - * should be spelled ...MAX_USER... - */ - ldt_segs[LUCODE_SEL].ssd_limit = atop(VM_MAXUSER_ADDRESS - 1); - ldt_segs[LUDATA_SEL].ssd_limit = atop(VM_MAXUSER_ADDRESS - 1); + ldt_segs[LUCODE_SEL].ssd_limit = atop(0 - 1); + ldt_segs[LUDATA_SEL].ssd_limit = atop(0 - 1); for (x = 0; x < sizeof ldt_segs / sizeof ldt_segs[0]; x++) ssdtosd(&ldt_segs[x], &ldt[x].sd); @@ -2032,6 +2066,9 @@ init386(first) PCPU_SET(common_tss.tss_ioopt, (sizeof (struct i386tss)) << 16); ltr(gsel_tss); + /* pointer to selector slot for %fs/%gs */ + PCPU_SET(fsgs_gdt, &gdt[GUFS_SEL].sd); + dblfault_tss.tss_esp = dblfault_tss.tss_esp0 = dblfault_tss.tss_esp1 = dblfault_tss.tss_esp2 = (int)&dblfault_stack[sizeof(dblfault_stack)]; dblfault_tss.tss_ss = dblfault_tss.tss_ss0 = dblfault_tss.tss_ss1 = @@ -2070,13 +2107,14 @@ init386(first) gdp->gd_hioffset = x >> 16; /* XXX does this work? */ + /* XXX yes! */ ldt[LBSDICALLS_SEL] = ldt[LSYS5CALLS_SEL]; ldt[LSOL26CALLS_SEL] = ldt[LSYS5CALLS_SEL]; /* transfer to user mode */ - _ucodesel = LSEL(LUCODE_SEL, SEL_UPL); - _udatasel = LSEL(LUDATA_SEL, SEL_UPL); + _ucodesel = GSEL(GUCODE_SEL, SEL_UPL); + _udatasel = GSEL(GUDATA_SEL, SEL_UPL); /* setup proc 0's pcb */ thread0.td_pcb->pcb_flags = 0; /* XXXKSE */ diff --git a/sys/pc98/pc98/machdep.c b/sys/pc98/pc98/machdep.c index c338d86..ab6c5c9 100644 --- a/sys/pc98/pc98/machdep.c +++ b/sys/pc98/pc98/machdep.c @@ -1292,7 +1292,12 @@ static char dblfault_stack[PAGE_SIZE]; extern vm_offset_t proc0kstack; -/* software prototypes -- in more palatable form */ +/* + * software prototypes -- in more palatable form. + * + * GCODE_SEL through GUDATA_SEL must be in this order for syscall/sysret + * GUFS_SEL and GUGS_SEL must be in this order (swtch.s knows it) + */ struct soft_segment_descriptor gdt_segs[] = { /* GNULL_SEL 0 Null Descriptor */ { 0x0, /* segment base address */ @@ -1303,7 +1308,34 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* default 32 vs 16 bit size */ 0 /* limit granularity (byte/page units)*/ }, -/* GCODE_SEL 1 Code Descriptor for kernel */ +/* GPRIV_SEL 1 SMP Per-Processor Private Data Descriptor */ +{ 0x0, /* segment base address */ + 0xfffff, /* length - all address space */ + SDT_MEMRWA, /* segment type */ + 0, /* segment descriptor priority level */ + 1, /* segment descriptor present */ + 0, 0, + 1, /* default 32 vs 16 bit size */ + 1 /* limit granularity (byte/page units)*/ }, +/* GUFS_SEL 2 %fs Descriptor for user */ +{ 0x0, /* segment base address */ + 0xfffff, /* length - all address space */ + SDT_MEMRWA, /* segment type */ + SEL_UPL, /* segment descriptor priority level */ + 1, /* segment descriptor present */ + 0, 0, + 1, /* default 32 vs 16 bit size */ + 1 /* limit granularity (byte/page units)*/ }, +/* GUGS_SEL 3 %gs Descriptor for user */ +{ 0x0, /* segment base address */ + 0xfffff, /* length - all address space */ + SDT_MEMRWA, /* segment type */ + SEL_UPL, /* segment descriptor priority level */ + 1, /* segment descriptor present */ + 0, 0, + 1, /* default 32 vs 16 bit size */ + 1 /* limit granularity (byte/page units)*/ }, +/* GCODE_SEL 4 Code Descriptor for kernel */ { 0x0, /* segment base address */ 0xfffff, /* length - all address space */ SDT_MEMERA, /* segment type */ @@ -1312,7 +1344,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 1, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GDATA_SEL 2 Data Descriptor for kernel */ +/* GDATA_SEL 5 Data Descriptor for kernel */ { 0x0, /* segment base address */ 0xfffff, /* length - all address space */ SDT_MEMRWA, /* segment type */ @@ -1321,16 +1353,34 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 1, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GPRIV_SEL 3 SMP Per-Processor Private Data Descriptor */ +/* GUCODE_SEL 6 Code Descriptor for user */ +{ 0x0, /* segment base address */ + 0xfffff, /* length - all address space */ + SDT_MEMERA, /* segment type */ + SEL_UPL, /* segment descriptor priority level */ + 1, /* segment descriptor present */ + 0, 0, + 1, /* default 32 vs 16 bit size */ + 1 /* limit granularity (byte/page units)*/ }, +/* GUDATA_SEL 7 Data Descriptor for user */ { 0x0, /* segment base address */ 0xfffff, /* length - all address space */ SDT_MEMRWA, /* segment type */ + SEL_UPL, /* segment descriptor priority level */ + 1, /* segment descriptor present */ + 0, 0, + 1, /* default 32 vs 16 bit size */ + 1 /* limit granularity (byte/page units)*/ }, +/* GBIOSLOWMEM_SEL 8 BIOS access to realmode segment 0x40, must be #8 in GDT */ +{ 0x400, /* segment base address */ + 0xfffff, /* length */ + SDT_MEMRWA, /* segment type */ 0, /* segment descriptor priority level */ 1, /* segment descriptor present */ 0, 0, 1, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GPROC0_SEL 4 Proc 0 Tss Descriptor */ +/* GPROC0_SEL 9 Proc 0 Tss Descriptor */ { 0x0, /* segment base address */ sizeof(struct i386tss)-1,/* length */ @@ -1340,7 +1390,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* unused - default 32 vs 16 bit size */ 0 /* limit granularity (byte/page units)*/ }, -/* GLDT_SEL 5 LDT Descriptor */ +/* GLDT_SEL 10 LDT Descriptor */ { (int) ldt, /* segment base address */ sizeof(ldt)-1, /* length - all address space */ SDT_SYSLDT, /* segment type */ @@ -1349,7 +1399,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* unused - default 32 vs 16 bit size */ 0 /* limit granularity (byte/page units)*/ }, -/* GUSERLDT_SEL 6 User LDT Descriptor per process */ +/* GUSERLDT_SEL 11 User LDT Descriptor per process */ { (int) ldt, /* segment base address */ (512 * sizeof(union descriptor)-1), /* length */ SDT_SYSLDT, /* segment type */ @@ -1358,25 +1408,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* unused - default 32 vs 16 bit size */ 0 /* limit granularity (byte/page units)*/ }, -/* GTGATE_SEL 7 Null Descriptor - Placeholder */ -{ 0x0, /* segment base address */ - 0x0, /* length - all address space */ - 0, /* segment type */ - 0, /* segment descriptor priority level */ - 0, /* segment descriptor present */ - 0, 0, - 0, /* default 32 vs 16 bit size */ - 0 /* limit granularity (byte/page units)*/ }, -/* GBIOSLOWMEM_SEL 8 BIOS access to realmode segment 0x40, must be #8 in GDT */ -{ 0x400, /* segment base address */ - 0xfffff, /* length */ - SDT_MEMRWA, /* segment type */ - 0, /* segment descriptor priority level */ - 1, /* segment descriptor present */ - 0, 0, - 1, /* default 32 vs 16 bit size */ - 1 /* limit granularity (byte/page units)*/ }, -/* GPANIC_SEL 9 Panic Tss Descriptor */ +/* GPANIC_SEL 12 Panic Tss Descriptor */ { (int) &dblfault_tss, /* segment base address */ sizeof(struct i386tss)-1,/* length - all address space */ SDT_SYS386TSS, /* segment type */ @@ -1385,7 +1417,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* unused - default 32 vs 16 bit size */ 0 /* limit granularity (byte/page units)*/ }, -/* GBIOSCODE32_SEL 10 BIOS 32-bit interface (32bit Code) */ +/* GBIOSCODE32_SEL 13 BIOS 32-bit interface (32bit Code) */ { 0, /* segment base address (overwritten) */ 0xfffff, /* length */ SDT_MEMERA, /* segment type */ @@ -1394,7 +1426,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GBIOSCODE16_SEL 11 BIOS 32-bit interface (16bit Code) */ +/* GBIOSCODE16_SEL 14 BIOS 32-bit interface (16bit Code) */ { 0, /* segment base address (overwritten) */ 0xfffff, /* length */ SDT_MEMERA, /* segment type */ @@ -1403,7 +1435,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GBIOSDATA_SEL 12 BIOS 32-bit interface (Data) */ +/* GBIOSDATA_SEL 15 BIOS 32-bit interface (Data) */ { 0, /* segment base address (overwritten) */ 0xfffff, /* length */ SDT_MEMRWA, /* segment type */ @@ -1412,7 +1444,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 1, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GBIOSUTIL_SEL 13 BIOS 16-bit interface (Utility) */ +/* GBIOSUTIL_SEL 16 BIOS 16-bit interface (Utility) */ { 0, /* segment base address (overwritten) */ 0xfffff, /* length */ SDT_MEMRWA, /* segment type */ @@ -1421,7 +1453,7 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, -/* GBIOSARGS_SEL 14 BIOS 16-bit interface (Arguments) */ +/* GBIOSARGS_SEL 17 BIOS 16-bit interface (Arguments) */ { 0, /* segment base address (overwritten) */ 0xfffff, /* length */ SDT_MEMRWA, /* segment type */ @@ -1430,6 +1462,15 @@ struct soft_segment_descriptor gdt_segs[] = { 0, 0, 0, /* default 32 vs 16 bit size */ 1 /* limit granularity (byte/page units)*/ }, +/* GNDIS_SEL 18 NDIS Descriptor */ +{ 0x0, /* segment base address */ + 0x0, /* length */ + 0, /* segment type */ + 0, /* segment descriptor priority level */ + 0, /* segment descriptor present */ + 0, 0, + 0, /* default 32 vs 16 bit size */ + 0 /* limit granularity (byte/page units)*/ }, }; static struct soft_segment_descriptor ldt_segs[] = { @@ -1881,25 +1922,22 @@ init386(first) init_param1(); /* - * make gdt memory segments, the code segment goes up to end of the - * page with etext in it, the data segment goes to the end of - * the address space - */ - /* - * XXX text protection is temporarily (?) disabled. The limit was - * i386_btop(round_page(etext)) - 1. + * Make gdt memory segments. All segments cover the full 4GB + * of address space and permissions are enforced at page level. */ gdt_segs[GCODE_SEL].ssd_limit = atop(0 - 1); gdt_segs[GDATA_SEL].ssd_limit = atop(0 - 1); + gdt_segs[GUCODE_SEL].ssd_limit = atop(0 - 1); + gdt_segs[GUDATA_SEL].ssd_limit = atop(0 - 1); + gdt_segs[GUFS_SEL].ssd_limit = atop(0 - 1); + gdt_segs[GUGS_SEL].ssd_limit = atop(0 - 1); + #ifdef SMP pc = &SMP_prvspace[0].pcpu; - gdt_segs[GPRIV_SEL].ssd_limit = - atop(sizeof(struct privatespace) - 1); #else pc = &__pcpu; - gdt_segs[GPRIV_SEL].ssd_limit = - atop(sizeof(struct pcpu) - 1); #endif + gdt_segs[GPRIV_SEL].ssd_limit = atop(0 - 1); gdt_segs[GPRIV_SEL].ssd_base = (int) pc; gdt_segs[GPROC0_SEL].ssd_base = (int) &pc->pc_common_tss; @@ -1928,12 +1966,8 @@ init386(first) mtx_init(&icu_lock, "icu", NULL, MTX_SPIN | MTX_NOWITNESS); /* make ldt memory segments */ - /* - * XXX - VM_MAXUSER_ADDRESS is an end address, not a max. And it - * should be spelled ...MAX_USER... - */ - ldt_segs[LUCODE_SEL].ssd_limit = atop(VM_MAXUSER_ADDRESS - 1); - ldt_segs[LUDATA_SEL].ssd_limit = atop(VM_MAXUSER_ADDRESS - 1); + ldt_segs[LUCODE_SEL].ssd_limit = atop(0 - 1); + ldt_segs[LUDATA_SEL].ssd_limit = atop(0 - 1); for (x = 0; x < sizeof ldt_segs / sizeof ldt_segs[0]; x++) ssdtosd(&ldt_segs[x], &ldt[x].sd); @@ -2032,6 +2066,9 @@ init386(first) PCPU_SET(common_tss.tss_ioopt, (sizeof (struct i386tss)) << 16); ltr(gsel_tss); + /* pointer to selector slot for %fs/%gs */ + PCPU_SET(fsgs_gdt, &gdt[GUFS_SEL].sd); + dblfault_tss.tss_esp = dblfault_tss.tss_esp0 = dblfault_tss.tss_esp1 = dblfault_tss.tss_esp2 = (int)&dblfault_stack[sizeof(dblfault_stack)]; dblfault_tss.tss_ss = dblfault_tss.tss_ss0 = dblfault_tss.tss_ss1 = @@ -2070,13 +2107,14 @@ init386(first) gdp->gd_hioffset = x >> 16; /* XXX does this work? */ + /* XXX yes! */ ldt[LBSDICALLS_SEL] = ldt[LSYS5CALLS_SEL]; ldt[LSOL26CALLS_SEL] = ldt[LSYS5CALLS_SEL]; /* transfer to user mode */ - _ucodesel = LSEL(LUCODE_SEL, SEL_UPL); - _udatasel = LSEL(LUDATA_SEL, SEL_UPL); + _ucodesel = GSEL(GUCODE_SEL, SEL_UPL); + _udatasel = GSEL(GUDATA_SEL, SEL_UPL); /* setup proc 0's pcb */ thread0.td_pcb->pcb_flags = 0; /* XXXKSE */ |