9boot: add e820 scan to bootloader
This commit is contained in:
parent
e0c8b9955d
commit
0ad5929695
6 changed files with 133 additions and 28 deletions
|
@ -673,35 +673,51 @@ e820scan(void)
|
||||||
ulong cont, base, len;
|
ulong cont, base, len;
|
||||||
uvlong last;
|
uvlong last;
|
||||||
Emap *e;
|
Emap *e;
|
||||||
|
char *s;
|
||||||
|
|
||||||
if(getconf("*norealmode") || getconf("*noe820scan"))
|
if((s = getconf("e820")) != nil){
|
||||||
return -1;
|
for(nemap = 0; nemap < nelem(emap); nemap++){
|
||||||
|
if(*s == 0)
|
||||||
cont = 0;
|
break;
|
||||||
for(i=0; i<nelem(emap); i++){
|
e = emap + nemap;
|
||||||
memset(&u, 0, sizeof u);
|
e->base = strtoull(s, &s, 16);
|
||||||
u.ax = 0xE820;
|
if(*s != ' ')
|
||||||
u.bx = cont;
|
break;
|
||||||
u.cx = 20;
|
e->len = strtoull(s, &s, 16) - e->base;
|
||||||
u.dx = SMAP;
|
if(*s != ' ' && *s != 0 || e->len >= 1ull<<32 || e->len == 0)
|
||||||
u.es = (PADDR(RMBUF)>>4)&0xF000;
|
break;
|
||||||
u.di = PADDR(RMBUF)&0xFFFF;
|
e->type = Ememory;
|
||||||
u.trap = 0x15;
|
}
|
||||||
realmode(&u);
|
}else{
|
||||||
cont = u.bx;
|
if(getconf("*norealmode") || getconf("*noe820scan"))
|
||||||
if((u.flags&Carry) || u.ax != SMAP || u.cx != 20)
|
return -1;
|
||||||
break;
|
cont = 0;
|
||||||
e = &emap[nemap++];
|
for(i=0; i<nelem(emap); i++){
|
||||||
*e = *(Emap*)RMBUF;
|
memset(&u, 0, sizeof u);
|
||||||
if(u.bx == 0)
|
u.ax = 0xE820;
|
||||||
break;
|
u.bx = cont;
|
||||||
|
u.cx = 20;
|
||||||
|
u.dx = SMAP;
|
||||||
|
u.es = (PADDR(RMBUF)>>4)&0xF000;
|
||||||
|
u.di = PADDR(RMBUF)&0xFFFF;
|
||||||
|
u.trap = 0x15;
|
||||||
|
realmode(&u);
|
||||||
|
cont = u.bx;
|
||||||
|
if((u.flags&Carry) || u.ax != SMAP || u.cx != 20)
|
||||||
|
break;
|
||||||
|
e = &emap[nemap++];
|
||||||
|
*e = *(Emap*)RMBUF;
|
||||||
|
if(u.bx == 0)
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(nemap == 0)
|
if(nemap == 0)
|
||||||
return -1;
|
return -1;
|
||||||
|
|
||||||
qsort(emap, nemap, sizeof emap[0], emapcmp);
|
qsort(emap, nemap, sizeof emap[0], emapcmp);
|
||||||
|
|
||||||
if(getconf("*noe820print") == nil){
|
if(s == nil && getconf("*noe820print") == nil){
|
||||||
for(i=0; i<nemap; i++){
|
for(i=0; i<nemap; i++){
|
||||||
e = &emap[i];
|
e = &emap[i];
|
||||||
print("E820: %.8llux %.8llux ", e->base, e->base+e->len);
|
print("E820: %.8llux %.8llux ", e->base, e->base+e->len);
|
||||||
|
|
|
@ -7,19 +7,19 @@ TEXT apm(SB), $0
|
||||||
|
|
||||||
PUSHR(rBX)
|
PUSHR(rBX)
|
||||||
LWI(0x5300, rAX)
|
LWI(0x5300, rAX)
|
||||||
INT $0x15
|
BIOSCALL(0x15)
|
||||||
POPR(rBX)
|
POPR(rBX)
|
||||||
JC noapm
|
JC noapm
|
||||||
|
|
||||||
PUSHR(rBX)
|
PUSHR(rBX)
|
||||||
LWI(0x5304, rAX)
|
LWI(0x5304, rAX)
|
||||||
INT $0x15
|
BIOSCALL(0x15)
|
||||||
POPR(rBX)
|
POPR(rBX)
|
||||||
CLC
|
CLC
|
||||||
|
|
||||||
/* connect */
|
/* connect */
|
||||||
LWI(0x5303, rAX)
|
LWI(0x5303, rAX)
|
||||||
INT $0x15
|
BIOSCALL(0x15)
|
||||||
JC noapm
|
JC noapm
|
||||||
|
|
||||||
OPSIZE; PUSHR(rSI)
|
OPSIZE; PUSHR(rSI)
|
||||||
|
|
20
sys/src/boot/pc/e820.s
Normal file
20
sys/src/boot/pc/e820.s
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
#include "x16.h"
|
||||||
|
#include "mem.h"
|
||||||
|
|
||||||
|
TEXT e820(SB), $0
|
||||||
|
MOVL bx+4(SP), BX
|
||||||
|
MOVL p+8(SP), DI
|
||||||
|
|
||||||
|
MOVL $0xe820, AX
|
||||||
|
MOVL $0x534D4150, DX
|
||||||
|
CALL rmode16(SB)
|
||||||
|
LWI(24, rCX)
|
||||||
|
BIOSCALL(0x15)
|
||||||
|
JC _bad
|
||||||
|
CALL16(pmode32(SB))
|
||||||
|
MOVL BX, AX
|
||||||
|
RET
|
||||||
|
_bad:
|
||||||
|
CALL16(pmode32(SB))
|
||||||
|
XORL AX, AX
|
||||||
|
RET
|
|
@ -9,8 +9,6 @@ void start(void *sp);
|
||||||
int getc(void);
|
int getc(void);
|
||||||
int gotc(void);
|
int gotc(void);
|
||||||
void putc(int c);
|
void putc(int c);
|
||||||
void a20(void);
|
|
||||||
void apm(int id);
|
|
||||||
void halt(void);
|
void halt(void);
|
||||||
void jump(void *pc);
|
void jump(void *pc);
|
||||||
|
|
||||||
|
|
|
@ -36,7 +36,7 @@ pbs: pbs.$O
|
||||||
$LD -o $target -H3 -T0x0600 -l $prereq
|
$LD -o $target -H3 -T0x0600 -l $prereq
|
||||||
ls -l $target
|
ls -l $target
|
||||||
|
|
||||||
9boot&: l%.$O %.$O sub.$O apm.$O a20.$O
|
9boot&: l%.$O %.$O sub.$O apm.$O e820.$O a20.$O
|
||||||
$LD -o $target -H3 -T0x7c00 -l $prereq
|
$LD -o $target -H3 -T0x7c00 -l $prereq
|
||||||
ls -l $target
|
ls -l $target
|
||||||
|
|
||||||
|
|
|
@ -235,6 +235,8 @@ addconfx(char *s, int w, ulong v)
|
||||||
*confend = 0;
|
*confend = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void apm(int id);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
apmconf(int id)
|
apmconf(int id)
|
||||||
{
|
{
|
||||||
|
@ -263,6 +265,73 @@ apmconf(int id)
|
||||||
*confend++ = '\n';
|
*confend++ = '\n';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ulong e820(ulong bx, void *p);
|
||||||
|
|
||||||
|
static void
|
||||||
|
e820conf(void)
|
||||||
|
{
|
||||||
|
struct {
|
||||||
|
uvlong base;
|
||||||
|
uvlong len;
|
||||||
|
ulong typ;
|
||||||
|
ulong ext;
|
||||||
|
} e;
|
||||||
|
uvlong v;
|
||||||
|
ulong bx;
|
||||||
|
char *s;
|
||||||
|
|
||||||
|
memset(&e, 0, sizeof(e));
|
||||||
|
if((bx = e820(0, &e)) == 0)
|
||||||
|
return;
|
||||||
|
|
||||||
|
memmove(confend, "e820=", 5);
|
||||||
|
confend += 5;
|
||||||
|
|
||||||
|
do{
|
||||||
|
s = confend;
|
||||||
|
v = e.base;
|
||||||
|
addconfx("", 8, v>>32);
|
||||||
|
addconfx("", 8, v&0xffffffff);
|
||||||
|
v = e.base + e.len;
|
||||||
|
addconfx(" ", 8, v>>32);
|
||||||
|
addconfx("", 8, v&0xffffffff);
|
||||||
|
|
||||||
|
print(s);
|
||||||
|
|
||||||
|
switch(e.typ){
|
||||||
|
case 1:
|
||||||
|
print(" ram");
|
||||||
|
break;
|
||||||
|
case 2:
|
||||||
|
print(" reserved");
|
||||||
|
break;
|
||||||
|
case 3:
|
||||||
|
print(" acpi reclaim");
|
||||||
|
break;
|
||||||
|
case 4:
|
||||||
|
print(" acpi nvs");
|
||||||
|
break;
|
||||||
|
case 5:
|
||||||
|
print(" bad");
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
print(" ???");
|
||||||
|
}
|
||||||
|
print(crnl);
|
||||||
|
|
||||||
|
if(e.typ == 1 && (e.ext & 1) == 0)
|
||||||
|
*confend++ = ' ';
|
||||||
|
else
|
||||||
|
confend = s;
|
||||||
|
memset(&e, 0, sizeof(e));
|
||||||
|
} while(bx = e820(bx, &e));
|
||||||
|
|
||||||
|
*confend++ = '\n';
|
||||||
|
*confend = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
void a20(void);
|
||||||
|
|
||||||
char*
|
char*
|
||||||
bootkern(void *f)
|
bootkern(void *f)
|
||||||
{
|
{
|
||||||
|
@ -270,6 +339,8 @@ bootkern(void *f)
|
||||||
ulong n;
|
ulong n;
|
||||||
Exec ex;
|
Exec ex;
|
||||||
|
|
||||||
|
e820conf();
|
||||||
|
|
||||||
a20();
|
a20();
|
||||||
if(readn(f, &ex, sizeof(ex)) != sizeof(ex))
|
if(readn(f, &ex, sizeof(ex)) != sizeof(ex))
|
||||||
return "bad header";
|
return "bad header";
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue