1/* 2 * PROJECT: ReactOS MBR Boot Sector for ISO file system ("isohybrid mode") 3 * LICENSE: GPL-2.0+ (https://spdx.org/licenses/GPL-2.0+) 4 * PURPOSE: Providing an MBR Boot Sector that enables an ISO to be booted from a disk 5 * COPYRIGHT: Copyright 2017 Colin Finck (colin@reactos.org) 6 */ 7 8#include <asm.inc> 9 10.code16 11 12// The "isohybrid" tool patching our ISO will write the LBA of the El Torito BIOS Boot Sector to this address. 13pBootSectorLBA = start+432 14 15// Our BIOS Boot Sector contains this signature at the specified position and our third-party imported "isohybrid" patching tool checks for it. 16// This is also why it's the same signature ISOLINUX uses. 17HybridSignature = HEX(7078C0FB) 18pBootSectorHybridSignature = HEX(7C00)+64 19pBootSectorHybridEntryPoint = HEX(7C00)+64+4 20 21start: 22 // The MBR needs to start with 33h, because some dumb BIOSes check for that (cf. syslinux commit d0f275981c9289dc4b8df64e72cd9902bf85aebe). 23 // The following line encodes a "xor ax, ax" (but it's not the only way to encode it, so we can't just write that instruction here). 24 .byte HEX(33), HEX(C0) 25 26 // Set up our stack and a flat addressing model. 27 cli 28 mov ss, ax 29 mov sp, offset start 30 mov ds, ax 31 mov es, ax 32 mov fs, ax 33 mov gs, ax 34 sti 35 36 // Our boot sector has been loaded to address 0x7C00. 37 // Relocate our 512 bytes boot sector to the given base address (should be 0x7000). 38 cld 39 mov cx, 512 / 4 40 mov si, HEX(7C00) 41 mov di, offset start 42 rep movsd 43 44 // Jump to the relocated code. 45 ljmp16 0, relocated 46 47relocated: 48 // Prepare the Disk Access Packet (DAP) for INT 13h, Function 42h: Extended Read Sectors from Drive. 49 // Read 4 sectors to address 7C00h, which is exactly our 2K-sized BIOS Boot Sector. 50 push 0 51 push 0 52 push dword ptr es:[pBootSectorLBA] 53 push es 54 push HEX(7C00) 55 push 4 56 push HEX(10) 57 58 // Call the BIOS function. Note that we haven't clobbered DL up to this point, so the Drive Number passed by the BIOS is still there. 59 // Read errors are indicated by the Carry Flag. 60 mov ah, HEX(42) 61 mov si, sp 62 int HEX(13) 63 jc read_error 64 65 // Verify the Hybrid Signature. 66 cmp dword ptr es:[pBootSectorHybridSignature], HybridSignature 67 jne invalid_signature 68 69 // Signature is valid, so jump to the entry point for the hybrid code. 70 ljmp16 0, pBootSectorHybridEntryPoint 71 72read_error: 73 call die_with_error 74 .ascii "ISOMBR: Read Error!", CR, LF 75 76invalid_signature: 77 call die_with_error 78 .ascii "ISOMBR: Invalid Boot Sector Hybrid Signature!", CR, LF 79 80die_with_error: 81 // Fetch the message to output stored at the return address on the stack. 82 pop si 83 84 // Call BIOS INT 10h, Function 0Eh to output a single character. 85 // Do this in a loop and stop after we have printed the newline LF character. 86next_character: 87 lodsb 88 mov ah, HEX(0E) 89 xor bx, bx 90 int HEX(10) 91 cmp al, 10 92 jne next_character 93 94 // Die gracefully, that means in an infinite HLT loop to not put any stress on the CPU. 95die: 96 hlt 97 jmp die 98 99// The "isohybrid" tool will add the remaining information, including the infamous 0xAA55 MBR signature. 100.org 431 101 .byte 0 102 103.endcode16 104 105END 106