; Boot sector sample for a floppy or hard drive ; It prints all register values, as passed to the boot sector and waits ; for a key before rebooting. ; A typical output is the following: ; AX=3CEB BX=7C00 CX=0001 DX=0000 SP=03FA BP=0E00 SI=00B5 DI=0000 ; DS=0000 ES=0000 SS=0000 CS=0000 IP=7C00 ; Press a key to reboot... ; Author : Benoit Papillault ; Creation: 30 Octobre 1998 ; Last modification: 31 Octobre 1998 ; History: ; Comes from myboot.asm (TASM version). This new version can be compiled ; with NASM. ; At least 53 bytes for BIOS interrupts to work properly STACK_SIZE equ 100h %define SEGMENT_INITIAL 7c0h ; la valeur de CS lorsque ce code est execute ; par le BIOS ou le MBR du disque ; Pour debugger sous DOS avec Turbo-Debuggeur ; SEGMENT_INITIAL equ cs ; When a PC is switch on, the first sector of the floppy or the "bootable" ; partition is read and put at memory location 0:7c00h (or 7C0h:0h is ; equivalent). When execution of this code starts, we have: ; CS=0000h and IP=7C00h. bios_data_seg equ 40h bios_flag equ 72h segment .bss ; the uninitialized data are put just after the boot sector itself (in memory, ; not on the physical sector!). org 200h resb STACK_SIZE tos: sav_ax resw 1 sav_ss resw 1 sav_sp resw 1 sav_si resw 1 sav_ds resw 1 segment .text org 0h start: ; debut has to be at offset 3eh or else, MS-DOS refuses to read the floppy or ; partition. jmp short debut nop ; org 03h db 'MSDOS5.0' dw 200h db 1h dw 1h ; 10h db 2h dw 0e0h dw 0b40h db 0f0h dw 9h dw 12h dw 2h dw 0h dw 0h ; ? ; 20h dd 0h db 0h db 0h db 29h ; signature db 'PAPI' ; serial number db 'DISK16 ' db 'FAT12 ' debut: ; we save DS and AX for a later use (we hope that we can at least push 4 bytes ; on the stack). push ds push ax ; initialisation of DS mov ax,SEGMENT_INITIAL mov ds,ax ; save some registers pop word [sav_ax] pop word [sav_ds] mov [sav_ss],ss mov [sav_sp],sp mov [sav_si],si ; setup a new stack. cli mov ss,ax mov sp,tos sti mov si,r_ax call prints mov ax,[sav_ax] call print_ax mov si,r_bx call prints mov ax,bx call print_ax mov si,r_cx call prints mov ax,cx call print_ax mov si,r_dx call prints mov ax,dx call print_ax mov si,r_sp call prints mov ax,[sav_sp] call print_ax mov si,r_bp call prints mov ax,bp call print_ax mov si,r_si call prints mov ax,[sav_si] call print_ax mov si,r_di call prints mov ax,di call print_ax mov si,r_ds call prints mov ax,[sav_ds] call print_ax mov si,r_es call prints mov ax,es call print_ax mov si,r_ss call prints mov ax,[sav_ss] call print_ax mov si,r_cs call prints mov ax,cs call print_ax mov si,r_ip call prints call get_ip retour_get_ip: sub ax,retour_get_ip - start call print_ax ; a carriage return mov al,13 call printc mov al,10 call printc mov si,Mess call prints mov ah,0 int 16h mov al,7 call printc ; mov dl,0 ; int 19h ; To skip the BIOS memory test, we put 1234h at location 40:72 mov ax,bios_data_seg mov es,ax mov word [es:bios_flag],1234h ; mov word 40h:72h,1234h ; cold boot ??? !!! ; jmp far ptr bios_reboot jmp 0ffffh:0h ; mov ax,4c00h ; int 21h boucle_infinie: xor ax,ax int 16h mov al,'.' call printc jmp short boucle_infinie ; print a null terminated string pointed by DS:SI prints: cld lodsb cmp al,0 je short fin_prints call printc jmp short prints fin_prints: ret ; returns the IP value (return address of the function) in AX ; BP is modified get_ip: mov bp,sp mov ax,[bp] ret ; prints the hexadecimal value of 4 least significant bits of AL ; no register modified print_a4: push ax and al,0fh ; AL = first figure cmp al,10 jl short print_a4_ok add al,'A'-'0'-10 print_a4_ok: add al,'0' call printc pop ax ret ; end of print_a4 ; prints the hexadecimal value of AX ; no register modified print_ax: push cx mov cl,4 rol ax,cl call print_a4 rol ax,cl call print_a4 rol ax,cl call print_a4 rol ax,cl call print_a4 pop cx ret ; prints the AL character ; curor position is updated ; we use function 0eh of interrupt number 10h ; with AH=0eh, AL=character,BH=page (here 0) and ; BH = color (here 5=white). printc: push ax push bx mov ah,0eh mov bx,7 int 10h pop bx pop ax ret ; beginning of the data zone of this program Mess db 'Press a key to reboot...',13,10,7,0 r_ax db 'AX=',0 r_bx db ' BX=',0 r_cx db ' CX=',0 r_dx db ' DX=',0 r_sp db ' SP=',0 r_bp db ' BP=',0 r_si db ' SI=',0 r_di db ' DI=',0 ; next line r_ds db 13,10,'DS=',0 r_es db ' ES=',0 r_ss db ' SS=',0 r_cs db ' CS=',0 r_ip db ' IP=',0 end: ; org 1feh ; $ = offset from the beginning of the current section ; $$= beginning of the current section times 1feh-($-$$) db 0 db 55h,0aah