1 /* $OpenBSD: gateA20.c,v 1.10 2004/03/19 13:48:18 tom Exp $ */ 2 3 /* 4 * Ported to boot 386BSD by Julian Elischer (julian@tfs.com) Sept 1992 5 * 6 * Mach Operating System 7 * Copyright (c) 1992, 1991 Carnegie Mellon University 8 * All Rights Reserved. 9 * 10 * Permission to use, copy, modify and distribute this software and its 11 * documentation is hereby granted, provided that both the copyright 12 * notice and this permission notice appear in all copies of the 13 * software, derivative works or modified versions, and any portions 14 * thereof, and that both notices appear in supporting documentation. 15 * 16 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS" 17 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR 18 * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE. 19 * 20 * Carnegie Mellon requests users of this software to return to 21 * 22 * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU 23 * School of Computer Science 24 * Carnegie Mellon University 25 * Pittsburgh PA 15213-3890 26 * 27 * any improvements or extensions that they make and grant Carnegie Mellon 28 * the rights to redistribute these changes. 29 */ 30 31 #include <sys/param.h> 32 #include <sys/types.h> 33 #include <machine/pio.h> 34 #include <dev/ic/i8042reg.h> 35 #include <dev/isa/isareg.h> 36 37 #include "libsa.h" 38 39 #define KB_A20 0xdf /* enable A20, 40 enable output buffer full interrupt 41 enable data line 42 enable clock line */ 43 44 45 /* 46 * "Probe"-style routine (no parameters) to turn A20 on 47 */ 48 void 49 gateA20on(void) 50 { 51 gateA20(1); 52 } 53 54 55 /* 56 * Gate A20 for high memory 57 */ 58 void 59 gateA20(int on) 60 { 61 if (ps2model == 0xf82 || 62 (inb(IO_KBD + KBSTATP) == 0xff && inb(IO_KBD + KBDATAP) == 0xff)) { 63 int data; 64 65 /* Try to use 0x92 to turn on A20 */ 66 if (on) { 67 data = inb(0x92); 68 outb(0x92, data | 0x2); 69 } else { 70 data = inb(0x92); 71 outb(0x92, data & ~0x2); 72 } 73 } else { 74 75 while (inb(IO_KBD + KBSTATP) & KBS_IBF); 76 77 while (inb(IO_KBD + KBSTATP) & KBS_DIB) 78 (void)inb(IO_KBD + KBDATAP); 79 80 outb(IO_KBD + KBCMDP, KBC_CMDWOUT); 81 while (inb(IO_KBD + KBSTATP) & KBS_IBF); 82 83 if (on) 84 outb(IO_KBD + KBDATAP, KB_A20); 85 else 86 outb(IO_KBD + KBDATAP, 0xcd); 87 while (inb(IO_KBD + KBSTATP) & KBS_IBF); 88 89 while (inb(IO_KBD + KBSTATP) & KBS_DIB) 90 (void)inb(IO_KBD + KBDATAP); 91 } 92 }