Tue Aug 15 06:37:50 2017 UTC ()
style


(maxv)
diff -r1.1 -r1.2 src/sys/arch/x86/x86/bios32.c

cvs diff -r1.1 -r1.2 src/sys/arch/x86/x86/bios32.c (expand / switch to unified diff)

--- src/sys/arch/x86/x86/bios32.c 2017/08/15 06:27:40 1.1
+++ src/sys/arch/x86/x86/bios32.c 2017/08/15 06:37:50 1.2
@@ -1,16 +1,16 @@ @@ -1,16 +1,16 @@
1/* $NetBSD: bios32.c,v 1.1 2017/08/15 06:27:40 maxv Exp $ */ 1/* $NetBSD: bios32.c,v 1.2 2017/08/15 06:37:50 maxv Exp $ */
2 2
3/*- 3/*
4 * Copyright (c) 1999 The NetBSD Foundation, Inc. 4 * Copyright (c) 1999 The NetBSD Foundation, Inc.
5 * All rights reserved. 5 * All rights reserved.
6 * 6 *
7 * This code is derived from software contributed to The NetBSD Foundation 7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Jason R. Thorpe of the Numerical Aerospace Simulation Facility, 8 * by Jason R. Thorpe of the Numerical Aerospace Simulation Facility,
9 * NASA Ames Research Center. 9 * NASA Ames Research Center.
10 * 10 *
11 * Redistribution and use in source and binary forms, with or without 11 * Redistribution and use in source and binary forms, with or without
12 * modification, are permitted provided that the following conditions 12 * modification, are permitted provided that the following conditions
13 * are met: 13 * are met:
14 * 1. Redistributions of source code must retain the above copyright 14 * 1. Redistributions of source code must retain the above copyright
15 * notice, this list of conditions and the following disclaimer. 15 * notice, this list of conditions and the following disclaimer.
16 * 2. Redistributions in binary form must reproduce the above copyright 16 * 2. Redistributions in binary form must reproduce the above copyright
@@ -31,38 +31,38 @@ @@ -31,38 +31,38 @@
31 */ 31 */
32 32
33/* 33/*
34 * Copyright (c) 1999, by UCHIYAMA Yasushi 34 * Copyright (c) 1999, by UCHIYAMA Yasushi
35 * All rights reserved. 35 * All rights reserved.
36 * 36 *
37 * Redistribution and use in source and binary forms, with or without 37 * Redistribution and use in source and binary forms, with or without
38 * modification, are permitted provided that the following conditions 38 * modification, are permitted provided that the following conditions
39 * are met: 39 * are met:
40 * 1. Redistributions of source code must retain the above copyright 40 * 1. Redistributions of source code must retain the above copyright
41 * notice, this list of conditions and the following disclaimer. 41 * notice, this list of conditions and the following disclaimer.
42 * 2. The name of the developer may NOT be used to endorse or promote products 42 * 2. The name of the developer may NOT be used to endorse or promote products
43 * derived from this software without specific prior written permission. 43 * derived from this software without specific prior written permission.
44 *  44 *
45 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND  45 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND
46 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE  46 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
47 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE  47 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
48 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE  48 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE
49 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL  49 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
50 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS  50 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
51 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)  51 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
52 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT  52 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
53 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY  53 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
54 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF  54 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
55 * SUCH DAMAGE.  55 * SUCH DAMAGE.
56 */ 56 */
57 57
58/* 58/*
59 * Copyright (c) 1997-2001 Michael Shalayeff 59 * Copyright (c) 1997-2001 Michael Shalayeff
60 * All rights reserved. 60 * All rights reserved.
61 * 61 *
62 * Redistribution and use in source and binary forms, with or without 62 * Redistribution and use in source and binary forms, with or without
63 * modification, are permitted provided that the following conditions 63 * modification, are permitted provided that the following conditions
64 * are met: 64 * are met:
65 * 1. Redistributions of source code must retain the above copyright 65 * 1. Redistributions of source code must retain the above copyright
66 * notice, this list of conditions and the following disclaimer. 66 * notice, this list of conditions and the following disclaimer.
67 * 2. Redistributions in binary form must reproduce the above copyright 67 * 2. Redistributions in binary form must reproduce the above copyright
68 * notice, this list of conditions and the following disclaimer in the 68 * notice, this list of conditions and the following disclaimer in the
@@ -76,31 +76,31 @@ @@ -76,31 +76,31 @@
76 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR 76 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
77 * SERVICES; LOSS OF MIND, USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 77 * SERVICES; LOSS OF MIND, USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
78 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, 78 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
79 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING 79 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
80 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF 80 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
81 * THE POSSIBILITY OF SUCH DAMAGE. 81 * THE POSSIBILITY OF SUCH DAMAGE.
82 */ 82 */
83 83
84/* 84/*
85 * Basic interface to BIOS32 services. 85 * Basic interface to BIOS32 services.
86 */ 86 */
87 87
88#include <sys/cdefs.h> 88#include <sys/cdefs.h>
89__KERNEL_RCSID(0, "$NetBSD: bios32.c,v 1.1 2017/08/15 06:27:40 maxv Exp $"); 89__KERNEL_RCSID(0, "$NetBSD: bios32.c,v 1.2 2017/08/15 06:37:50 maxv Exp $");
90 90
91#include <sys/param.h> 91#include <sys/param.h>
92#include <sys/systm.h> 92#include <sys/systm.h>
93#include <sys/device.h>  93#include <sys/device.h>
94 94
95#include <dev/isa/isareg.h> 95#include <dev/isa/isareg.h>
96#include <machine/isa_machdep.h> 96#include <machine/isa_machdep.h>
97 97
98#include <machine/segments.h> 98#include <machine/segments.h>
99#include <machine/bios32.h> 99#include <machine/bios32.h>
100#include <x86/smbiosvar.h> 100#include <x86/smbiosvar.h>
101#include <x86/efi.h> 101#include <x86/efi.h>
102 102
103#include <uvm/uvm.h> 103#include <uvm/uvm.h>
104 104
105#include "ipmi.h" 105#include "ipmi.h"
106#include "opt_xen.h" 106#include "opt_xen.h"
@@ -182,26 +182,75 @@ bios32_init(void) @@ -182,26 +182,75 @@ bios32_init(void)
182 for (p = ISA_HOLE_VADDR(SMBIOS_START); 182 for (p = ISA_HOLE_VADDR(SMBIOS_START);
183 p < (uint8_t *)ISA_HOLE_VADDR(SMBIOS_END); p+= 16) { 183 p < (uint8_t *)ISA_HOLE_VADDR(SMBIOS_END); p+= 16) {
184 if (smbios3_check_header(p)) { 184 if (smbios3_check_header(p)) {
185 smbios3_map_kva(p); 185 smbios3_map_kva(p);
186 return; 186 return;
187 } 187 }
188 if (smbios2_check_header(p)) { 188 if (smbios2_check_header(p)) {
189 smbios2_map_kva(p); 189 smbios2_map_kva(p);
190 return; 190 return;
191 } 191 }
192 } 192 }
193} 193}
194 194
 195/*
 196 * Call BIOS32 to locate the specified BIOS32 service, and fill
 197 * in the entry point information.
 198 */
 199int
 200bios32_service(uint32_t service, bios32_entry_t e, bios32_entry_info_t ei)
 201{
 202#ifdef i386
 203 uint32_t eax, ebx, ecx, edx;
 204 paddr_t entry;
 205
 206 if (bios32_entry.offset == 0)
 207 return 0; /* BIOS32 not present */
 208
 209 __asm volatile("lcall *(%%edi)"
 210 : "=a" (eax), "=b" (ebx), "=c" (ecx), "=d" (edx)
 211 : "0" (service), "1" (0), "D" (&bios32_entry));
 212
 213 if ((eax & 0xff) != 0)
 214 return 0; /* service not found */
 215
 216 entry = ebx + edx;
 217
 218 if (entry < BIOS32_START || entry >= BIOS32_END) {
 219 aprint_error("BIOS32: entry point for service %c%c%c%c is "
 220 "outside allowable range\n",
 221 service & 0xff,
 222 (service >> 8) & 0xff,
 223 (service >> 16) & 0xff,
 224 (service >> 24) & 0xff);
 225 return 0;
 226 }
 227
 228 e->offset = (void *)ISA_HOLE_VADDR(entry);
 229 e->segment = GSEL(GCODE_SEL, SEL_KPL);
 230
 231 ei->bei_base = ebx;
 232 ei->bei_size = ecx;
 233 ei->bei_entry = entry;
 234#else
 235 (void)service;
 236 (void)e;
 237 (void)ei;
 238 panic("bios32_service not implemented on amd64");
 239#endif
 240
 241 return 1;
 242}
 243
195static int 244static int
196smbios2_check_header(const uint8_t *p) 245smbios2_check_header(const uint8_t *p)
197{ 246{
198 const struct smbhdr *sh = (const struct smbhdr *)p; 247 const struct smbhdr *sh = (const struct smbhdr *)p;
199 uint8_t chksum; 248 uint8_t chksum;
200 int i; 249 int i;
201 250
202 if (sh->sig != BIOS32_MAKESIG('_', 'S', 'M', '_')) 251 if (sh->sig != BIOS32_MAKESIG('_', 'S', 'M', '_'))
203 return 0; 252 return 0;
204 i = sh->len; 253 i = sh->len;
205 for (chksum = 0; i--; ) 254 for (chksum = 0; i--; )
206 chksum += p[i]; 255 chksum += p[i];
207 if (chksum != 0) 256 if (chksum != 0)
@@ -238,28 +287,27 @@ smbios2_map_kva(const uint8_t *p) @@ -238,28 +287,27 @@ smbios2_map_kva(const uint8_t *p)
238 smbios_entry.min = sh->minrev; 287 smbios_entry.min = sh->minrev;
239 smbios_entry.doc = 0; 288 smbios_entry.doc = 0;
240 smbios_entry.count = sh->count; 289 smbios_entry.count = sh->count;
241 290
242 for (; pa < end; pa+= NBPG, eva+= NBPG) 291 for (; pa < end; pa+= NBPG, eva+= NBPG)
243#ifdef XEN 292#ifdef XEN
244 pmap_kenter_ma(eva, pa, VM_PROT_READ, 0); 293 pmap_kenter_ma(eva, pa, VM_PROT_READ, 0);
245#else 294#else
246 pmap_kenter_pa(eva, pa, VM_PROT_READ, 0); 295 pmap_kenter_pa(eva, pa, VM_PROT_READ, 0);
247#endif 296#endif
248 pmap_update(pmap_kernel()); 297 pmap_update(pmap_kernel());
249 298
250 aprint_debug("SMBIOS rev. %d.%d @ 0x%lx (%d entries)\n", 299 aprint_debug("SMBIOS rev. %d.%d @ 0x%lx (%d entries)\n",
251 sh->majrev, sh->minrev, (u_long)sh->addr, 300 sh->majrev, sh->minrev, (u_long)sh->addr, sh->count);
252 sh->count); 
253} 301}
254 302
255static int 303static int
256smbios3_check_header(const uint8_t *p) 304smbios3_check_header(const uint8_t *p)
257{ 305{
258 const struct smb3hdr *sh = (const struct smb3hdr *)p; 306 const struct smb3hdr *sh = (const struct smb3hdr *)p;
259 uint8_t chksum; 307 uint8_t chksum;
260 int i; 308 int i;
261 309
262 if (p[0] != '_' || p[1] != 'S' || p[2] != 'M' || 310 if (p[0] != '_' || p[1] != 'S' || p[2] != 'M' ||
263 p[3] != '3' || p[4] != '_') 311 p[3] != '3' || p[4] != '_')
264 return 0; 312 return 0;
265 i = sh->len; 313 i = sh->len;
@@ -292,77 +340,28 @@ smbios3_map_kva(const uint8_t *p) @@ -292,77 +340,28 @@ smbios3_map_kva(const uint8_t *p)
292 smbios_entry.mjr = sh->majrev; 340 smbios_entry.mjr = sh->majrev;
293 smbios_entry.min = sh->minrev; 341 smbios_entry.min = sh->minrev;
294 smbios_entry.doc = sh->docrev; 342 smbios_entry.doc = sh->docrev;
295 smbios_entry.count = UINT16_MAX; 343 smbios_entry.count = UINT16_MAX;
296 344
297 for (; pa < end; pa += NBPG, eva += NBPG) 345 for (; pa < end; pa += NBPG, eva += NBPG)
298#ifdef XEN 346#ifdef XEN
299 pmap_kenter_ma(eva, pa, VM_PROT_READ, 0); 347 pmap_kenter_ma(eva, pa, VM_PROT_READ, 0);
300#else 348#else
301 pmap_kenter_pa(eva, pa, VM_PROT_READ, 0); 349 pmap_kenter_pa(eva, pa, VM_PROT_READ, 0);
302#endif 350#endif
303 pmap_update(pmap_kernel()); 351 pmap_update(pmap_kernel());
304 352
305 aprint_debug("SMBIOS rev. %d.%d.%d @ 0x%lx\n", 353 aprint_debug("SMBIOS rev. %d.%d.%d @ 0x%lx\n", sh->majrev,
306 sh->majrev, sh->minrev, sh->docrev, (u_long)sh->addr); 354 sh->minrev, sh->docrev, (u_long)sh->addr);
307} 
308 
309/* 
310 * Call BIOS32 to locate the specified BIOS32 service, and fill 
311 * in the entry point information. 
312 */ 
313int 
314bios32_service(uint32_t service, bios32_entry_t e, bios32_entry_info_t ei) 
315{ 
316#ifdef i386 
317 uint32_t eax, ebx, ecx, edx; 
318 paddr_t entry; 
319 
320 if (bios32_entry.offset == 0) 
321 return (0); /* BIOS32 not present */ 
322 
323 __asm volatile("lcall *(%%edi)" 
324 : "=a" (eax), "=b" (ebx), "=c" (ecx), "=d" (edx) 
325 : "0" (service), "1" (0), "D" (&bios32_entry)); 
326 
327 if ((eax & 0xff) != 0) 
328 return (0); /* service not found */ 
329 
330 entry = ebx + edx; 
331 
332 if (entry < BIOS32_START || entry >= BIOS32_END) { 
333 aprint_error("BIOS32: entry point for service %c%c%c%c is " 
334 "outside allowable range\n", 
335 service & 0xff, 
336 (service >> 8) & 0xff, 
337 (service >> 16) & 0xff, 
338 (service >> 24) & 0xff); 
339 return (0); 
340 } 
341 
342 e->offset = (void *)ISA_HOLE_VADDR(entry); 
343 e->segment = GSEL(GCODE_SEL, SEL_KPL); 
344 
345 ei->bei_base = ebx; 
346 ei->bei_size = ecx; 
347 ei->bei_entry = entry; 
348#else 
349 (void)service; 
350 (void)e; 
351 (void)ei; 
352 panic("bios32_service not implemented on amd64"); 
353#endif 
354 
355 return (1); 
356} 355}
357 356
358/* 357/*
359 * smbios_find_table() takes a caller supplied smbios struct type and 358 * smbios_find_table() takes a caller supplied smbios struct type and
360 * a pointer to a handle (struct smbtable) returning one if the structure 359 * a pointer to a handle (struct smbtable) returning one if the structure
361 * is sucessfully located and zero otherwise. Callers should take care 360 * is sucessfully located and zero otherwise. Callers should take care
362 * to initilize the cookie field of the smbtable structure to zero before 361 * to initilize the cookie field of the smbtable structure to zero before
363 * the first invocation of this function. 362 * the first invocation of this function.
364 * Multiple tables of the same type can be located by repeadtly calling 363 * Multiple tables of the same type can be located by repeadtly calling
365 * smbios_find_table with the same arguments. 364 * smbios_find_table with the same arguments.
366 */ 365 */
367int 366int
368smbios_find_table(uint8_t type, struct smbtable *st) 367smbios_find_table(uint8_t type, struct smbtable *st)