1 #include "u.h"
2 #include "../port/lib.h"
3 #include "mem.h"
4 #include "dat.h"
5 #include "fns.h"
6
7 typedef struct Mbi Mbi;
8 struct Mbi {
9 u32int flags;
10 u32int memlower;
11 u32int memupper;
12 u32int bootdevice;
13 u32int cmdline;
14 u32int modscount;
15 u32int modsaddr;
16 u32int syms[4];
17 u32int mmaplength;
18 u32int mmapaddr;
19 u32int driveslength;
20 u32int drivesaddr;
21 u32int configtable;
22 u32int bootloadername;
23 u32int apmtable;
24 u32int vbe[6];
25 };
26
27 enum { /* flags */
28 Fmem = 0x00000001, /* mem* valid */
29 Fbootdevice = 0x00000002, /* bootdevice valid */
30 Fcmdline = 0x00000004, /* cmdline valid */
31 Fmods = 0x00000008, /* mod* valid */
32 Fsyms = 0x00000010, /* syms[] has a.out info */
33 Felf = 0x00000020, /* syms[] has ELF info */
34 Fmmap = 0x00000040, /* mmap* valid */
35 Fdrives = 0x00000080, /* drives* valid */
36 Fconfigtable = 0x00000100, /* configtable* valid */
37 Fbootloadername = 0x00000200, /* bootloadername* valid */
38 Fapmtable = 0x00000400, /* apmtable* valid */
39 Fvbe = 0x00000800, /* vbe[] valid */
40 };
41
42 typedef struct Mod Mod;
43 struct Mod {
44 u32int modstart;
45 u32int modend;
46 u32int string;
47 u32int reserved;
48 };
49
50 typedef struct MMap MMap;
51 struct MMap {
52 u32int size;
53 u32int base[2];
54 u32int length[2];
55 u32int type;
56 };
57
58 int
multiboot(u32int magic,u32int pmbi,int vflag)59 multiboot(u32int magic, u32int pmbi, int vflag)
60 {
61 char *p;
62 int i, n;
63 Mbi *mbi;
64 Mod *mod;
65 MMap *mmap;
66 u64int addr, len;
67
68 if(vflag)
69 print("magic %#ux pmbi %#ux\n", magic, pmbi);
70 if(magic != 0x2badb002)
71 return -1;
72
73 mbi = KADDR(pmbi);
74 if(vflag)
75 print("flags %#ux\n", mbi->flags);
76 if(mbi->flags & Fcmdline){
77 p = KADDR(mbi->cmdline);
78 if(vflag)
79 print("cmdline <%s>\n", p);
80 else
81 optionsinit(p);
82 }
83 if(mbi->flags & Fmods){
84 for(i = 0; i < mbi->modscount; i++){
85 mod = KADDR(mbi->modsaddr + i*16);
86 if(mod->string != 0)
87 p = KADDR(mod->string);
88 else
89 p = "";
90 if(vflag)
91 print("mod %#ux %#ux <%s>\n",
92 mod->modstart, mod->modend, p);
93 else
94 asmmodinit(mod->modstart, mod->modend, p);
95 }
96 }
97 if(mbi->flags & Fmmap){
98 mmap = KADDR(mbi->mmapaddr);
99 n = 0;
100 while(n < mbi->mmaplength){
101 addr = (((u64int)mmap->base[1])<<32)|mmap->base[0];
102 len = (((u64int)mmap->length[1])<<32)|mmap->length[0];
103 switch(mmap->type){
104 default:
105 if(vflag)
106 print("type %ud", mmap->type);
107 break;
108 case 1:
109 if(vflag)
110 print("Memory");
111 else
112 asmmapinit(addr, len, mmap->type);
113 break;
114 case 2:
115 if(vflag)
116 print("reserved");
117 else
118 asmmapinit(addr, len, mmap->type);
119 break;
120 case 3:
121 if(vflag)
122 print("ACPI Reclaim Memory");
123 else
124 asmmapinit(addr, len, mmap->type);
125 break;
126 case 4:
127 if(vflag)
128 print("ACPI NVS Memory");
129 else
130 asmmapinit(addr, len, mmap->type);
131 break;
132 }
133 if(vflag)
134 print("\n\t%#16.16llux %#16.16llux (%llud)\n",
135 addr, addr+len, len);
136
137 n += mmap->size+sizeof(mmap->size);
138 mmap = KADDR(mbi->mmapaddr+n);
139 }
140 }
141 if(vflag && (mbi->flags & Fbootloadername)){
142 p = KADDR(mbi->bootloadername);
143 print("bootloadername <%s>\n", p);
144 }
145
146 return 0;
147 }
148