1use zerocopy::FromBytes;
10use zerocopy::Immutable;
11use zerocopy::IntoBytes;
12use zerocopy::KnownLayout;
13
14pub const MULTIBOOT_BOOTLOADER_MAGIC: u32 = 0x2BADB002;
16
17#[derive(Debug, Default, FromBytes, Immutable, IntoBytes, KnownLayout)]
18#[repr(C, packed)]
19pub struct MultibootInfo {
20 pub flags: u32,
21
22 pub mem_lower: u32,
23 pub mem_upper: u32,
24
25 pub boot_device: u32,
26
27 pub cmdline: u32,
28
29 pub mods_count: u32,
30 pub mods_addr: u32,
31
32 pub syms: [u32; 4],
34
35 pub mmap_length: u32,
36 pub mmap_addr: u32,
37
38 pub drives_length: u32,
39 pub drives_addr: u32,
40
41 pub config_table: u32,
42
43 pub boot_loader_name: u32,
44
45 pub apm_table: u32,
46
47 pub vbe_control_info: u32,
48 pub vbe_mode_info: u32,
49 pub vbe_mode: u16,
50 pub vbe_interface_seg: u16,
51 pub vbe_interface_off: u16,
52 pub vbe_interface_len: u16,
53
54 pub framebuffer_addr: u64,
55 pub framebuffer_pitch: u32,
56 pub framebuffer_width: u32,
57 pub framebuffer_height: u32,
58 pub framebuffer_bpp: u8,
59 pub framebuffer_type: u8,
60
61 pub color_info: [u8; 6],
63}
64
65impl MultibootInfo {
66 pub const F_MEM: u32 = 1 << 0;
67 pub const F_BOOT_DEVICE: u32 = 1 << 1;
68 pub const F_CMDLINE: u32 = 1 << 2;
69 pub const F_MODS: u32 = 1 << 3;
70 pub const F_SYMS_AOUT: u32 = 1 << 4;
71 pub const F_SYMS_ELF: u32 = 1 << 5;
72 pub const F_MMAP: u32 = 1 << 6;
73 pub const F_DRIVES: u32 = 1 << 7;
74 pub const F_CONFIG_TABLE: u32 = 1 << 8;
75 pub const F_BOOT_LOADER_NAME: u32 = 1 << 9;
76 pub const F_APM_TABLE: u32 = 1 << 10;
77 pub const F_VBE: u32 = 1 << 11;
78 pub const F_FRAMEBUFFER: u32 = 1 << 12;
79}
80
81#[derive(Debug, Default, FromBytes, Immutable, IntoBytes, KnownLayout)]
82#[repr(C, packed)]
83pub struct MultibootMmapEntry {
84 pub size: u32,
85 pub base_addr: u64,
86 pub length: u64,
87 pub type_: u32,
88}
89
90#[cfg(test)]
91mod tests {
92 use std::mem::offset_of;
93 use std::mem::size_of;
94
95 use super::*;
96
97 #[test]
98 fn test_multiboot_info_offsets() {
99 assert_eq!(0, offset_of!(MultibootInfo, flags));
101 assert_eq!(4, offset_of!(MultibootInfo, mem_lower));
102 assert_eq!(8, offset_of!(MultibootInfo, mem_upper));
103 assert_eq!(8, offset_of!(MultibootInfo, mem_upper));
104 assert_eq!(12, offset_of!(MultibootInfo, boot_device));
105 assert_eq!(16, offset_of!(MultibootInfo, cmdline));
106 assert_eq!(20, offset_of!(MultibootInfo, mods_count));
107 assert_eq!(24, offset_of!(MultibootInfo, mods_addr));
108 assert_eq!(28, offset_of!(MultibootInfo, syms));
109 assert_eq!(44, offset_of!(MultibootInfo, mmap_length));
110 assert_eq!(48, offset_of!(MultibootInfo, mmap_addr));
111 assert_eq!(52, offset_of!(MultibootInfo, drives_length));
112 assert_eq!(56, offset_of!(MultibootInfo, drives_addr));
113 assert_eq!(60, offset_of!(MultibootInfo, config_table));
114 assert_eq!(64, offset_of!(MultibootInfo, boot_loader_name));
115 assert_eq!(68, offset_of!(MultibootInfo, apm_table));
116 assert_eq!(72, offset_of!(MultibootInfo, vbe_control_info));
117 assert_eq!(76, offset_of!(MultibootInfo, vbe_mode_info));
118 assert_eq!(80, offset_of!(MultibootInfo, vbe_mode));
119 assert_eq!(82, offset_of!(MultibootInfo, vbe_interface_seg));
120 assert_eq!(84, offset_of!(MultibootInfo, vbe_interface_off));
121 assert_eq!(86, offset_of!(MultibootInfo, vbe_interface_len));
122 assert_eq!(88, offset_of!(MultibootInfo, framebuffer_addr));
123 assert_eq!(96, offset_of!(MultibootInfo, framebuffer_pitch));
124 assert_eq!(100, offset_of!(MultibootInfo, framebuffer_width));
125 assert_eq!(104, offset_of!(MultibootInfo, framebuffer_height));
126 assert_eq!(108, offset_of!(MultibootInfo, framebuffer_bpp));
127 assert_eq!(109, offset_of!(MultibootInfo, framebuffer_type));
128 assert_eq!(110, offset_of!(MultibootInfo, color_info));
129
130 assert_eq!(size_of::<MultibootInfo>(), 116);
131 }
132
133 #[test]
134 fn test_multiboot_mmap_entry_offsets() {
135 assert_eq!(0, offset_of!(MultibootMmapEntry, size));
140 assert_eq!(4, offset_of!(MultibootMmapEntry, base_addr));
141 assert_eq!(12, offset_of!(MultibootMmapEntry, length));
142 assert_eq!(20, offset_of!(MultibootMmapEntry, type_));
143
144 assert_eq!(size_of::<MultibootMmapEntry>(), 24); }
146}