summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--sys/arch/i386/stand/Makefile.inc14
-rw-r--r--sys/arch/i386/stand/libsa/Makefile19
-rw-r--r--sys/arch/i386/stand/libsa/biosdev.c17
-rw-r--r--sys/arch/i386/stand/libsa/gidt.S282
-rw-r--r--sys/arch/i386/stand/libsa/real_prot.S166
5 files changed, 224 insertions, 274 deletions
diff --git a/sys/arch/i386/stand/Makefile.inc b/sys/arch/i386/stand/Makefile.inc
index d94df93ebd7..dbeaa4bf257 100644
--- a/sys/arch/i386/stand/Makefile.inc
+++ b/sys/arch/i386/stand/Makefile.inc
@@ -1,11 +1,12 @@
-# $OpenBSD: Makefile.inc,v 1.6 1997/04/11 19:07:07 weingart Exp $
+# $OpenBSD: Makefile.inc,v 1.7 1997/04/18 01:28:00 mickey Exp $
#CPPFLAGS+=-nostdinc -I/sys
CPPFLAGS+=-Wall -Werror -I. -Imachine
-SACFLAGS+=-Wa,-R -fno-common -fpack-struct -fno-builtin -fomit-frame-pointer
+SACFLAGS+=-Wa,-R -fpack-struct -fno-builtin -fomit-frame-pointer
CPPFLAGS+=-D_STANDALONE
-# CPPFLAGS+=-DSAVE_MEMORY /* XXX - Does *NOT* work */
+# CPPFLAGS+=-DSAVE_MEMORY
# CPPFLAGS+=-DDEBUG
+# CPPFLAGS+=-DGIDT_DEBUG
# CPPFLAGS+=-DBIOS_DEBUG
# CPPFLAGS+=-DEXEC_DEBUG
# CPPFLAGS+=-DALLOC_TRACE
@@ -13,11 +14,10 @@ CPPFLAGS+=-D_STANDALONE
# CPPFLAFS+=-DUNIX_DEBUG
# CPPFLAFS+=-DBOOTP_DEBUG -DNETIF_DEBUG -DETHER_DEBUG
# CPPFLAGS+=-DNFS_DEBUG -DRPC_DEBUG -DRARP_DEBUG
-START=0x1000
-HEAP_START=0x10000
-HEAP_LIMIT=0x40000
+START=0x10000
+HEAP_LIMIT=0x50000
BOOTREL=0x3000
BOOTMAGIC=0xdeadbeef
-NO_NET=no_net
+# NO_NET=no_net
BINDIR= /usr/mdec
diff --git a/sys/arch/i386/stand/libsa/Makefile b/sys/arch/i386/stand/libsa/Makefile
index 5e757fc4f5c..b2f03c14fe8 100644
--- a/sys/arch/i386/stand/libsa/Makefile
+++ b/sys/arch/i386/stand/libsa/Makefile
@@ -1,4 +1,4 @@
-# $OpenBSD: Makefile,v 1.8 1997/04/15 20:01:55 mickey Exp $
+# $OpenBSD: Makefile,v 1.9 1997/04/18 01:28:01 mickey Exp $
LIB= sa
@@ -8,14 +8,18 @@ DIR_SA= $S/lib/libsa
DIR_KERN=$S/lib/libkern
CFLAGS+=$(SACFLAGS) -D__INTERNAL_LIBSA_CREAD
-CFLAGS+=-DHEAP_START=$(HEAP_START) -DHEAP_LIMIT=$(HEAP_LIMIT)
+CFLAGS+=-DSTART=$(START) -DHEAP_LIMIT=$(HEAP_LIMIT)
CFLAGS+=${DEBUGFLAGS} -I${.CURDIR} -I${.CURDIR}/..
CFLAGS+=-I$(S)/lib/libsa -I$(S)
AS+= -R
-#AS+= -Wa,-a
+AS+= -Wa,-a
+
+# i386 stuff (so, it will possibly load in the same 64k)
+SRCS= unixsys.S bioscom.S biosdisk.S bioskbd.S biostime.S biosmem.S gidt.S \
+ debug_i386.S dev_i386.c exec_i386.c biosdev.c gateA20.c memprobe.c
# stand routines
-SRCS= alloc.c exit.c exec.c getfile.c gets.c globals.c strcmp.c strlen.c \
+SRCS+= alloc.c exit.c exec.c getfile.c gets.c globals.c strcmp.c strlen.c \
strncmp.c memcmp.c memcpy.c memset.c printf.c strerror.c strncpy.c
# math for cd9660
@@ -35,12 +39,7 @@ SRCS+= bootp.c bootparam.c rarp.c
SRCS+= ufs.c nfs.c cd9660.c
# debugger
-SRCS+= debug.c debug_aout.c debug_i386.S
-
-# i386 stuff
-SRCS+= asm.S bioscom.S biosdev.c biosdisk.S bioskbd.S biostime.S biosmem.S \
- dev_i386.c gateA20.c memprobe.c real_prot.S unixsys.S exec_i386.c \
- gidt.S
+SRCS+= debug.c debug_aout.c
NOPROFILE=noprofile
NOPIC=nopic
diff --git a/sys/arch/i386/stand/libsa/biosdev.c b/sys/arch/i386/stand/libsa/biosdev.c
index 696a37611d8..e6ee0edd8c7 100644
--- a/sys/arch/i386/stand/libsa/biosdev.c
+++ b/sys/arch/i386/stand/libsa/biosdev.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: biosdev.c,v 1.8 1997/04/17 19:03:20 weingart Exp $ */
+/* $OpenBSD: biosdev.c,v 1.9 1997/04/18 01:28:01 mickey Exp $ */
/*
* Copyright (c) 1996 Michael Shalayeff
@@ -263,7 +263,7 @@ biosstrategy(void *devdata, int rw,
{
u_int8_t error = 0;
register struct biosdisk *bd = (struct biosdisk *)devdata;
- register size_t i, nsect, n;
+ register size_t i, nsect, n, spt;
register const struct bd_error *p = bd_errors;
nsect = (size + DEV_BSIZE-1) / DEV_BSIZE;
@@ -278,15 +278,20 @@ biosstrategy(void *devdata, int rw,
buf, rsize, bd->biosdev, bd->bsddev);
#endif
+ /* handle floppies w/ different from drive geometry */
+ if (!(bd->biosdev & 0x80))
+ spt = bd->disklabel.d_nsectors;
+ else
+ spt = BIOSNSECTS(bd->dinfo);
+
for (i = 0; error == 0 && i < nsect;
i += n, blk += n, buf += n * DEV_BSIZE) {
register int cyl, hd, sect, j;
void *bb;
- btochs(blk, cyl, hd, sect,
- BIOSNHEADS(bd->dinfo), BIOSNSECTS(bd->dinfo));
- if ((sect + (nsect - i)) >= BIOSNSECTS(bd->dinfo))
- n = BIOSNSECTS(bd->dinfo) - sect;
+ btochs(blk, cyl, hd, sect, BIOSNHEADS(bd->dinfo), spt);
+ if ((sect + (nsect - i)) >= spt)
+ n = spt - sect;
else
n = nsect - i;
diff --git a/sys/arch/i386/stand/libsa/gidt.S b/sys/arch/i386/stand/libsa/gidt.S
index 1653a0d21d9..56fc268e84b 100644
--- a/sys/arch/i386/stand/libsa/gidt.S
+++ b/sys/arch/i386/stand/libsa/gidt.S
@@ -1,4 +1,4 @@
-/* $OpenBSD: gidt.S,v 1.3 1997/04/09 08:39:37 mickey Exp $ */
+/* $OpenBSD: gidt.S,v 1.4 1997/04/18 01:28:02 mickey Exp $ */
/*
* Copyright (c) 1997 Michael Shalayeff
@@ -31,6 +31,9 @@
* SUCH DAMAGE.
*
*/
+
+ .file "gidt.S"
+
#include <machine/asm.h>
#include <machine/psl.h>
#define _LOCORE
@@ -45,7 +48,6 @@
.data
.globl _Gdtr
- .globl _codeseg
.align 3
gdt:
@@ -67,17 +69,23 @@ gdt:
.byte 0 # hibase
/* 0x18 : 16 bit code */
.word 0xFFFF # lolimit
- .word 0 # lobase
- .byte 0 # midbase
+ .word (START & 0xffff) # lobase
+ .byte (START >> 16) & 0xff # midbase
.byte SDT_MEMERA | 0 | 0x80 # RXAC, dpl = 0, present
- .byte 0x0 | 0 | 0 | 0 # hilimit, xx, 16bit, byte granularity
- .byte 0 # hibase
+ .byte 0xf | 0 | 0 | 0 # hilimit, xx, 16bit, byte granularity
+ .byte (START >> 20) & 0xff # hibase
+ /* 0x20 : 16 bit data */
+ .word 0xFFFF # lolimit
+ .word (START & 0xffff) # lobase
+ .byte (START >> 16) & 0xff # midbase
+ .byte SDT_MEMRWA | 0 | 0x80 # RXAC, dpl = 0, present
+ .byte 0xf | 0 | 0 | 0 # hilimit, xx, 16bit, byte granularity
+ .byte (START >> 20) & 0xff # hibase
+
_Gdtr: .word . - gdt - 1
.long gdt
.word 0
-_codeseg: .long 0
-
.globl _Idtr_real
.align 3
_Idtr_real:
@@ -92,59 +100,58 @@ _Idtr_reset:
.globl _Idtr_prot
.align 3
-idt: /*
- * We beleive that all the boot code fits into
- * 64k, so no need for high 16 bit of procedure address (;
- *
- */
-#define IPROC(n) X/**/n
-#define IDTENTRY(proc) \
- .word IPROC(proc) /* lo offset handler */ ; \
- .word 0x8 /* handler %cs */ ; \
- .byte 0 /* reserved */ ; \
- .byte 0x80 | SDT_SYS386TGT /* present, dpl=0, 32bit trap gate */ ; \
- .word 0 /* hi offset handler */
-
- IDTENTRY(de) /* #DE divide by zero */
- IDTENTRY(db) /* #DB debug */
- IDTENTRY(nmi) /* NMI */
- IDTENTRY(bp) /* #BP breakpoint */
- IDTENTRY(of) /* #OF overflow */
- IDTENTRY(br) /* #BR BOUND range exceeded */
- IDTENTRY(ud) /* #UD invalid opcode */
- IDTENTRY(nm) /* #NM device not available */
- IDTENTRY(df) /* #DF double fault */
- IDTENTRY(fo) /* #FO coprocessor segment overrun */
- IDTENTRY(ts) /* #TS innvalid TSS */
- IDTENTRY(np) /* #NP segmant not present */
- IDTENTRY(ss) /* #SS stack fault */
- IDTENTRY(gp) /* #GP general protection */
- IDTENTRY(pf) /* #PF page fault */
- IDTENTRY(xx) /* Intel reserved */
- IDTENTRY(mf) /* #MF floating point error */
- IDTENTRY(ac) /* #AC alignment check */
- IDTENTRY(mc) /* #MC machine check */
- /* Intel reserved (19-31) */
- IDTENTRY(xx); IDTENTRY(xx); IDTENTRY(xx); IDTENTRY(xx)
- IDTENTRY(xx); IDTENTRY(xx); IDTENTRY(xx); IDTENTRY(xx)
- IDTENTRY(xx); IDTENTRY(xx); IDTENTRY(xx); IDTENTRY(xx)
- IDTENTRY(xx)
- /* Maskable interrupts(32-255) */
- /* BIOS entry points (32-63) */
-#define IBIOS(n) IPROC(bios/**/n)
-#define IDTBIOS(n) IDTENTRY(bios/**/n)
- IDTBIOS(0); IDTBIOS(1); IDTBIOS(2); IDTBIOS(3); IDTBIOS(4)
- IDTBIOS(5); IDTBIOS(6); IDTBIOS(7); IDTBIOS(8); IDTBIOS(9)
- IDTBIOS(10); IDTBIOS(11); IDTBIOS(12); IDTBIOS(13); IDTBIOS(14)
- IDTBIOS(15); IDTBIOS(16); IDTBIOS(17); IDTBIOS(18); IDTBIOS(19)
- IDTBIOS(20); IDTBIOS(21); IDTBIOS(22); IDTBIOS(23)
- /* DOS entry points */
+idt:
+ .space 32*8, 0 /* internal (0-31) */
+ /* Maskable interrupts (32-255) */
+ .space 32*8, 0 /* BIOS entry points (32-63) */
+ .space 16*8, 0 /* DOS entry points (64-80) */
_Idtr_prot:
.word . - idt - 1
.long idt
.text
+#define IPROC(n) X/**/n
+#define IBIOS(n) IPROC(bios/**/n)
+#define IDOS(n) IPROC(dos/**/n)
+
+ .globl idt_init
+idt_init:
+ pushl %edi
+
+ movl $idt, %edi
+
+#define fixe(p) \
+ movl $ IPROC(p), %eax; \
+ stosw; /* lo offset handler */ \
+ movw $0x8, (%edi); /* handler %cs */ \
+ incl %edi; incl %edi; \
+ incl %edi; /* reserved */ \
+ movb $(0x80|SDT_SYS386TGT), (%edi); /* 32bit trap gate */ \
+ incl %edi; \
+ shrl $16, %eax; \
+ stosw; /* hi offset handler */
+
+ fixe(de); fixe(db); fixe(nmi); fixe(bp); fixe(of); fixe(br)
+ fixe(ud); fixe(nm); fixe(df); fixe(fo); fixe(ts); fixe(np)
+ fixe(ss); fixe(gp); fixe(pf); fixe(xx); fixe(mf); fixe(ac)
+ fixe(mc)
+ fixe(xx); fixe(xx); fixe(xx); fixe(xx); fixe(xx); fixe(xx)
+ fixe(xx); fixe(xx); fixe(xx); fixe(xx); fixe(xx); fixe(xx)
+ fixe(xx)
+
+#define fixb(b) fixe(bios/**/b)
+ fixb(0); fixb(1); fixb(2); fixb(3); fixb(4); fixb(5)
+ fixb(6); fixb(7); fixb(8); fixb(9); fixb(10); fixb(11)
+ fixb(12); fixb(13); fixb(14); fixb(15); fixb(16); fixb(17)
+ fixb(18); fixb(19); fixb(20); fixb(21); fixb(22); fixb(23)
+ fixb(24); fixb(25); fixb(26); fixb(27); fixb(28); fixb(29)
+ fixb(30); fixb(31)
+
+#define fixd(d) fixe(dos/**/b)
+
+ popl %edi
+ ret
#define IENTRY(name,type) \
IPROC(name): \
@@ -158,33 +165,33 @@ IPROC(name): \
IPROC(xx):
pushl $1
- pushl $256
+ pushl $T_RESERVED
jmp 1f
-IENTRY_ERR(de,0,T_DIVIDE)
-IENTRY_ERR(db,0,T_TRCTRAP)
-IENTRY_ERR(nmi,0,T_NMI)
-IENTRY_ERR(bp,0,T_BPTFLT)
-IENTRY_ERR(of,0,T_OFLOW)
-IENTRY_ERR(br,0,T_BOUND)
-IENTRY_ERR(ud,0,T_PRIVINFLT)
-IENTRY_ERR(nm,0,T_DNA)
-IENTRY(df,T_DOUBLEFLT)
-IENTRY_ERR(fo,0,T_FPOPFLT)
-IENTRY(ts,T_TSSFLT)
-IENTRY(np,T_SEGNPFLT)
-IENTRY(ss,T_STKFLT)
-IENTRY(gp,T_PROTFLT)
-IENTRY(pf,T_PAGEFLT)
-IENTRY_ERR(mf,0,T_ARITHTRAP)
-IENTRY(ac,T_ALIGNFLT)
-IENTRY(mc,T_MACHK)
+IENTRY_ERR(de,0,T_DIVIDE) /* #DE divide by zero */
+IENTRY_ERR(db,0,T_TRCTRAP) /* #DB debug */
+IENTRY_ERR(nmi,0,T_NMI) /* NMI */
+IENTRY_ERR(bp,0,T_BPTFLT) /* #BP breakpoint */
+IENTRY_ERR(of,0,T_OFLOW) /* #OF overflow */
+IENTRY_ERR(br,0,T_BOUND) /* #BR BOUND range exceeded */
+IENTRY_ERR(ud,0,T_PRIVINFLT) /* #UD invalid opcode */
+IENTRY_ERR(nm,0,T_DNA) /* #NM device not available */
+IENTRY(df,T_DOUBLEFLT) /* #DF double fault */
+IENTRY_ERR(fo,0,T_FPOPFLT) /* #FO coprocessor segment overrun */
+IENTRY(ts,T_TSSFLT) /* #TS innvalid TSS */
+IENTRY(np,T_SEGNPFLT) /* #NP segmant not present */
+IENTRY(ss,T_STKFLT) /* #SS stack fault */
+IENTRY(gp,T_PROTFLT) /* #GP general protection */
+IENTRY(pf,T_PAGEFLT) /* #PF page fault */
+IENTRY_ERR(mf,0,T_ARITHTRAP) /* #MF floating point error */
+IENTRY(ac,T_ALIGNFLT) /* #AC alignment check */
+IENTRY(mc,T_MACHK) /* #MC machine check */
.globl alltraps
1: /* save on jumps */
jmp alltraps
-#define IBIOSENT(n) IBIOS(n): pushl %eax; movb $n, %al ; jmp 1f
+#define IBIOSENT(n) IBIOS(n): pushl $n; jmp BIOSh
IBIOSENT(0); IBIOSENT(1); IBIOSENT(2); IBIOSENT(3)
IBIOSENT(4); IBIOSENT(5); IBIOSENT(6); IBIOSENT(7)
@@ -192,38 +199,143 @@ IBIOSENT(8); IBIOSENT(9); IBIOSENT(10); IBIOSENT(11)
IBIOSENT(12); IBIOSENT(13); IBIOSENT(14); IBIOSENT(15)
IBIOSENT(16); IBIOSENT(17); IBIOSENT(18); IBIOSENT(19)
IBIOSENT(20); IBIOSENT(21); IBIOSENT(22); IBIOSENT(23)
+IBIOSENT(24); IBIOSENT(25); IBIOSENT(26); IBIOSENT(27)
+IBIOSENT(28); IBIOSENT(29); IBIOSENT(30); IBIOSENT(31)
- .text
- .globl _real_to_prot, _prot_to_real
-1:
- movb %al, intno
- popl %eax
+/*
+ * entry point for BIOS real-mode interface
+ * all the magic for real-prot mode switching is here
+ *
+ * Call: %eax, %ecx, %edx, %ebx, %ebp, %esi, %ds, %di==real mode %es
+ * Return: %eax, %edx, %ecx, %eflags (as returned from BIOS)
+ *
+ */
+ .globl BIOSh
+BIOSh:
pushal
pushl %ds
pushl %es
- call _prot_to_real
+ /* save %eax */
+ movl %eax, 2f
+
+ /* save BIOS int vector */
+ movb 10*4(%esp), %al
+ movb %al, intno
+
+ /* setup 16bit labels in ljmps */
+#ifdef GIDT_DEBUG
+ movl $0xb8000, %eax
+ movl $0x47314730, (%eax)
+#endif
+ movl $0x20, %eax
+
+ # ljmp $0x18, $2f
+ .byte 0xea /* Change to 16bit mode */
+ .long 1f - START
+ .word 0x18
+1:
+ movl %ax, %ds
+#ifdef GIDT_DEBUG
+ data32
+ movl $(0xb8000 - START), %eax
+ data32
+ addr32
+ movl $0x4f314f30, (%eax)
+#endif
+ movl %cr0, %eax /* disable prot mode memory management */
+ data32
+ andl $~CR0_PE, %eax
+ movl %eax, %cr0
+
+ # ljmp (START >> 16), $4f
+ .byte 0xea /* load real mode cs:ip */
+ .word 1f
+ .word (START >> 4)
+1:
+ xorl %eax, %eax /* setup: %ds, %es, %ss */
+ movl %ax, %ds
+ movl %ax, %ss
movl %di, %es
+#ifdef GIDT_DEBUG
+ data32
+ movl $0xb8004, %eax
+ data32
+ addr32
+ movl $0x47334732, (%eax)
+#endif
+
+ addr32
+ data32
+ lidt _Idtr_real /* load idtr for DOS/BIOS operations */
+
+ data32
+ # movl Leax, %eax
+ .byte 0xb8
+2: .long 0x90909090 /* restore %eax */
+
+ sti
int $0
-intno = . - 1
+intno = . - 1
- movb %ah, %bh
+ movb %ah, %bh /* save flags to return to caller */
lahf
xchgb %ah, %bh
+ cli /* no maskable interrupts in prot mode */
+
+ addr32
+ data32
+ movl %eax, 2f /* save %eax */
+
+#ifdef GIDT_DEBUG
+ data32
+ movl $0xb8004, %eax
+ data32
+ addr32
+ movl $0x4f334f32, (%eax)
+#endif
+
+ addr32
+ data32
+ lgdt _C_LABEL(Gdtr) /* load the gdtr */
+
+ movl %cr0, %eax /* enable prot mode memory management */
+ data32
+ orl $CR0_PE, %eax
+ movl %eax, %cr0
+
data32
- call _real_to_prot
+ ljmp $0x08, $1f /* reload %cs, and flush pipeline */
+1:
+ /* reload 32bit %ds, %ss, %es */
+ movl $0x10, %eax
+ movl %ax, %ds
+ movl %ax, %ss
+
+#ifdef GIDT_DEBUG
+ movl $0xb8008, %eax
+ movl $0x47344733, (%eax)
+#endif
+
+ /* load idtr for debugger and DOS/BIOS iface */
+ lidt _Idtr_prot
+
+ # movl Leax, %eax
+ .byte 0xb8
+2: .long 0x90909090 /* eax */
/* pass BIOS return values back to caller */
movl %eax, 0x9*4(%esp)
movl %ecx, 0x8*4(%esp)
movl %edx, 0x7*4(%esp)
- movb %bh , 0xc*4(%esp)
+ movb %bh , 0xd*4(%esp)
popl %es
popl %ds
popal
+ incl %esp; incl %esp; incl %esp; incl %esp
iret
diff --git a/sys/arch/i386/stand/libsa/real_prot.S b/sys/arch/i386/stand/libsa/real_prot.S
deleted file mode 100644
index b04d5545335..00000000000
--- a/sys/arch/i386/stand/libsa/real_prot.S
+++ /dev/null
@@ -1,166 +0,0 @@
-/* $OpenBSD: real_prot.S,v 1.5 1997/04/09 08:39:42 mickey Exp $ */
-
-/*
- * Mach Operating System
- * Copyright (c) 1992, 1991 Carnegie Mellon University
- * All Rights Reserved.
- *
- * Permission to use, copy, modify and distribute this software and its
- * documentation is hereby granted, provided that both the copyright
- * notice and this permission notice appear in all copies of the
- * software, derivative works or modified versions, and any portions
- * thereof, and that both notices appear in supporting documentation.
- *
- * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS"
- * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
- * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
- *
- * Carnegie Mellon requests users of this software to return to
- *
- * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU
- * School of Computer Science
- * Carnegie Mellon University
- * Pittsburgh PA 15213-3890
- *
- * any improvements or extensions that they make and grant Carnegie Mellon
- * the rights to redistribute these changes.
- *
- * from: Mach, Revision 2.2 92/04/04 11:34:13 rpd
- */
-
-
-/*
- Copyright 1988, 1989, 1990, 1991, 1992
- by Intel Corporation, Santa Clara, California.
-
- All Rights Reserved
-
-Permission to use, copy, modify, and distribute this software and
-its documentation for any purpose and without fee is hereby
-granted, provided that the above copyright notice appears in all
-copies and that both the copyright notice and this permission notice
-appear in supporting documentation, and that the name of Intel
-not be used in advertising or publicity pertaining to distribution
-of the software without specific, written prior permission.
-
-INTEL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE
-INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS,
-IN NO EVENT SHALL INTEL BE LIABLE FOR ANY SPECIAL, INDIRECT, OR
-CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
-LOSS OF USE, DATA OR PROFITS, WHETHER IN ACTION OF CONTRACT,
-NEGLIGENCE, OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
-WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
-*/
- .file "real_prot.S"
-
-#include <machine/asm.h>
-#include <machine/specialreg.h>
-
-#define addr32 .byte 0x67
-#define data32 .byte 0x66
-
- .data
-
- .globl _codeseg
- .globl _Gdtr
- .globl _Idtr_prot
- .globl _Idtr_real
-
- .text
-
-/*
- *
- * real_to_prot()
- * transfer from real mode to protected mode.
- */
-
-ENTRY(real_to_prot)
- /* guarantee that interrupts are disabled when in prot mode */
- cli
- addr32
- data32
- movl %eax, 2f
-
- /* load the gdtr */
- addr32
- data32
- lgdt _C_LABEL(Gdtr)
-
- /* set the PE bit of CR0 */
- movl %cr0, %eax
- data32
- orl $CR0_PE, %eax
- movl %eax, %cr0
-
- /*
- * make intrasegment jump to flush the processor pipeline and
- * reload CS register
- */
- data32
- ljmp $0x08, $1f
-
-1: /*
- * we are in USE32 mode now
- * set up the protected mode segment registers : DS, SS, ES
- */
- movl $0x10, %eax
- movl %ax, %ds
- movl %ax, %ss
- movl %ax, %es
-
- /* load idtr for debugger and BIOS iface */
- lidt _Idtr_prot
- # movl Leax, %eax
- .byte 0xb8
-2: .long 0 /* eax */
- ret
-
-/*
- *
- * prot_to_real()
- * transfer from protected mode to real mode
- *
- */
-
-ENTRY(prot_to_real)
-
- movl %eax, 4f
- movl _codeseg, %eax
- movw %ax, 2f
-
- /* Change to use16 mode. */
- ljmp $0x18, $1f
-1:
- /* clear the PE bit of CR0 */
- movl %cr0, %eax
- data32
- andl $~CR0_PE, %eax
- movl %eax, %cr0
-
- data32
- # ljmp _codeseg, $2f
- .byte 0xea
- .long 3f
-2: .word 0
-3:
- /* setup: %ds, %es, %ss */
- movl %cs, %ax
- movl %ax, %ds
- movl %ax, %ss
- movl %ax, %es
-
- /* load idtr for BIOS operations */
- addr32
- data32
- lidt _Idtr_real
-
- addr32
- data32
- # movl Leax, %eax
- .byte 0xb8
-4: .long 0 /* %eax */
-
- sti
- data32
- ret
-