Home | History | Annotate | Download | only in sysdump
      1 /*
      2  * Dump memory map information
      3  */
      4 
      5 #include <stdio.h>
      6 #include <string.h>
      7 #include <stdlib.h>
      8 #include <com32.h>
      9 #include "sysdump.h"
     10 
     11 #define E820_CHUNK 128
     12 struct e820_info {
     13     uint32_t ebx;
     14     uint32_t len;
     15     uint8_t  data[24];
     16 };
     17 
     18 static void dump_e820(struct upload_backend *be)
     19 {
     20     com32sys_t ireg, oreg;
     21     struct e820_info *curr;
     22     struct e820_info *buf, *p;
     23     int nentry, nalloc;
     24 
     25     curr = lmalloc(sizeof *curr);
     26 
     27     buf = p = NULL;
     28     nentry = nalloc = 0;
     29     memset(&ireg, 0, sizeof ireg);
     30     memset(&curr, 0, sizeof curr);
     31 
     32     ireg.eax.l = 0xe820;
     33     ireg.edx.l = 0x534d4150;
     34     ireg.ecx.l = sizeof curr->data;
     35     ireg.es = SEG(curr->data);
     36     ireg.edi.w[0] = OFFS(curr->data);
     37 
     38     do {
     39 	__intcall(0x15, &ireg, &oreg);
     40 	if ((oreg.eflags.l & EFLAGS_CF) ||
     41 	    oreg.eax.l != 0x534d4150)
     42 	    break;
     43 
     44 	if (nentry >= nalloc) {
     45 	    nalloc += E820_CHUNK;
     46 	    buf = realloc(buf, nalloc*sizeof *buf);
     47 	    if (!buf)
     48 		return;		/* FAILED */
     49 	}
     50 	memcpy(buf[nentry].data, curr->data, sizeof curr->data);
     51 	buf[nentry].ebx = ireg.ebx.l;
     52 	buf[nentry].len = oreg.ecx.l;
     53 	nentry++;
     54 
     55 	ireg.ebx.l = oreg.ebx.l;
     56     } while (ireg.ebx.l);
     57 
     58     if (nentry)
     59 	cpio_writefile(be, "memmap/15e820", buf, nentry*sizeof *buf);
     60 
     61     free(buf);
     62     lfree(curr);
     63 }
     64 
     65 void dump_memory_map(struct upload_backend *be)
     66 {
     67     com32sys_t ireg, oreg;
     68 
     69     cpio_mkdir(be, "memmap");
     70 
     71     memset(&ireg, 0, sizeof ireg);
     72     __intcall(0x12, &ireg, &oreg);
     73     cpio_writefile(be, "memmap/12", &oreg, sizeof oreg);
     74 
     75     memset(&ireg, 0, sizeof ireg);
     76     ireg.eax.b[1] = 0x88;
     77     __intcall(0x15, &ireg, &oreg);
     78     cpio_writefile(be, "memmap/1588", &oreg, sizeof oreg);
     79 
     80     memset(&ireg, 0, sizeof ireg);
     81     ireg.eax.w[0] = 0xe801;
     82     __intcall(0x15, &ireg, &oreg);
     83     cpio_writefile(be, "memmap/15e801", &oreg, sizeof oreg);
     84 
     85     dump_e820(be);
     86 }
     87