diff options
Diffstat (limited to 'sys/arch/amd64/stand/libsa/gateA20.c')
-rw-r--r-- | sys/arch/amd64/stand/libsa/gateA20.c | 82 |
1 files changed, 82 insertions, 0 deletions
diff --git a/sys/arch/amd64/stand/libsa/gateA20.c b/sys/arch/amd64/stand/libsa/gateA20.c new file mode 100644 index 00000000000..26cfb3539cb --- /dev/null +++ b/sys/arch/amd64/stand/libsa/gateA20.c @@ -0,0 +1,82 @@ +/* $OpenBSD: gateA20.c,v 1.1 2004/02/03 12:09:47 mickey Exp $ */ + +/* + * Ported to boot 386BSD by Julian Elischer (julian@tfs.com) Sept 1992 + * + * 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. + */ + +#include <sys/param.h> +#include <sys/types.h> +#include <machine/pio.h> +#include <dev/ic/i8042reg.h> +#include <dev/isa/isareg.h> + +#include "libsa.h" + +#define KB_A20 0xdf /* enable A20, + enable output buffer full interrupt + enable data line + enable clock line */ + + +/* + * Gate A20 for high memory + */ +void +gateA20(int on) +{ + if (ps2model == 0xf82 || + (inb(IO_KBD + KBSTATP) == 0xff && inb(IO_KBD + KBDATAP) == 0xff)) { + int data; + + /* Try to use 0x92 to turn on A20 */ + if (on) { + data = inb(0x92); + outb(0x92, data | 0x2); + } else { + data = inb(0x92); + outb(0x92, data & ~0x2); + } + } else { + + while (inb(IO_KBD + KBSTATP) & KBS_IBF); + + while (inb(IO_KBD + KBSTATP) & KBS_DIB) + (void)inb(IO_KBD + KBDATAP); + + outb(IO_KBD + KBCMDP, KBC_CMDWOUT); + while (inb(IO_KBD + KBSTATP) & KBS_IBF); + + if (on) + outb(IO_KBD + KBDATAP, KB_A20); + else + outb(IO_KBD + KBDATAP, 0xcd); + while (inb(IO_KBD + KBSTATP) & KBS_IBF); + + while (inb(IO_KBD + KBSTATP) & KBS_DIB) + (void)inb(IO_KBD + KBDATAP); + } +} |