mbr_forensic/
boot_code.rs1#[derive(Debug, Clone, Copy, PartialEq, Eq)]
5pub enum BootCodeId {
6 WindowsVista,
8 Windows7Plus,
10 GrubLegacy,
12 Grub2,
14 Syslinux,
16 AllZeros,
18 AllOnes,
20 Unknown,
22}
23
24const WINDOWS_VISTA_SIG: &[(usize, &[u8])] = &[
30 (0, &[0x33, 0xC0, 0x8E, 0xD0, 0xBC, 0x00, 0x7C]), (424, b"BOOTMGR"), ];
33
34const WINDOWS7_SIG: &[(usize, &[u8])] = &[
35 (0, &[0x33, 0xC0, 0x8E, 0xD0, 0xBC, 0x00, 0x7C]),
36 (418, b"BOOTMGR"),
37];
38
39const GRUB2_SIG: &[(usize, &[u8])] = &[
40 (0, &[0xEB, 0x63, 0x90]), ];
44
45const GRUB_LEGACY_SIG: &[(usize, &[u8])] = &[
46 (0, &[0xEB, 0x48, 0x90]), ];
48
49const SYSLINUX_SIG: &[(usize, &[u8])] = &[(3, b"SYSLINUX")];
50
51#[must_use]
53pub fn identify(code: &[u8; 446]) -> BootCodeId {
54 if code.iter().all(|&b| b == 0x00) {
55 return BootCodeId::AllZeros;
56 }
57 if code.iter().all(|&b| b == 0xFF) {
58 return BootCodeId::AllOnes;
59 }
60 if matches_all(code, WINDOWS7_SIG) {
61 return BootCodeId::Windows7Plus;
62 }
63 if matches_all(code, WINDOWS_VISTA_SIG) {
64 return BootCodeId::WindowsVista;
65 }
66 if matches_all(code, SYSLINUX_SIG) {
67 return BootCodeId::Syslinux;
68 }
69 if matches_all(code, GRUB_LEGACY_SIG) {
70 return BootCodeId::GrubLegacy;
71 }
72 if matches_all(code, GRUB2_SIG) {
73 return BootCodeId::Grub2;
74 }
75 BootCodeId::Unknown
76}
77
78fn matches_all(code: &[u8; 446], sigs: &[(usize, &[u8])]) -> bool {
79 sigs.iter().all(|(offset, pattern)| {
80 let end = offset + pattern.len();
81 end <= code.len() && &code[*offset..end] == *pattern
82 })
83}