я много об этом читал и наконец то решил сделать свою статью( или несколько статей )
1) что нам понадобится:
1. nasm или yasm - качать отсюда http://www.nasm.us и http://www.tortall.net/projects/yasm/
если у вас линукс осмотрите в стандртнах пакетах
2. VirtualBox от Sun - прекрасная виртуальноя машина. и бесплатная. http://www.virtualbox.org/
если у вас линукс осмотрите в стандртнах пакетах
3. http://www.codenet.ru/progr/dos/index.php - прерывания bios. прочитать чтобы всё понятно было
вот и всё.
2) что мы сделаем: загрузим нашу программу. напишем чего нибудь( правда по английский )
потом загрузим вторую часть нашей проги и опять чего нибудь напишем потом просто дадим пользователю писать всякую фигню
Биос загрузит первые 512 байт нашей программы( называется загрузчик или boot сектор) по адресу 7C00
Начало:
section .text
org 0x7c00;смещение кода.
bits 16;а вы что думали? сначала 16-ти битный код. как в ДОС
start:
cli; вырубаем прерывания. и инициализируем регистры. cs=0 изначально
mov ax, cs
mov ds, ax
mov es, ax
mov ss, ax
mov sp, 0x7c00
sti;включаем прирывания
дальше надо чего нить написать:
mov si,hw; копируем адрес нашей строки(hw) в si
call write; функция вывода на экран
call read; функция чтения с дискеты
cmp al,1h; если ошибка при чтении то в al единица
je l;если да уходим в бесконечный цикл
jmp 7e00h; если всё ок то прыгаем туда куда мы загрузили
l: jmp l; вот бесконечный цикл
вот функция write:
write:
push ax;сохраняем ax. чтобы востонавить данные положенные туда программой
mov ah,0Eh; режим вывода на экран текста . если не знаете откуда я это взял читаем первый пункт очень внимательно
.loopw:; цикл
lodsb; загружаем байт (по адресу в si) в al и увеличиваем si на 1
int 10h; печатаем символ из al на экран. прерывания видиосервиса
cmp al,0;сравниваем al с 0. в al символ. если в al 0 то это конец строки
jnz .loopw; если нет то повторяем операцию
pop ax; извлекаем ax обратно. востонавливам даные в ax
ret; возвращаемся
вот hw:
hw: db "Hello world",13,10,":) 0_o",13,10,0; наша строка
; 10 - перенос в начало строки 13 - перенос на нижнею строку 0 - конец строки
вот read:
read:; сектор= 512 байт
pusha; сохраняем все регистры.
mov ah,2h; режим чтения секторов
mov dl,0;номер диска. дискета = 0
mov dh,0; номер головки 0
mov ch,0; номер дорожки 0
mov cl,2; номер сектора с которого начнём. 1 сектор это наш boot.
mov al,2; число секторов. не больше чем 1 цилиндр
mov bx,7e00h;адрес куда мы будем всё это кидать :)
int 13h; прерывание дискового в/в
jc error; если была ошибка то флаг cr=1
popa; извлекаем регистры
mov al,0h; 0- не было ошибка
ret
error:; ошибка :(
mov si,em; выведем сообщение о ошибке
call write
popa; извлечём регистры
mov al,1h; запишем 1 в al. чтобы знать что была ошибка
ret
вот em:
em: db "error read",13,10,0
почти всё. в конец файла добавим:
endboot:
times 510-($-$) db 0; заполняем нулями чтобы было ровно 510 байт
db 0xAA, 0x55; и 2 байта. сигнатура boot сектора. в сумме 512 байт
incbin "setup.bin"; вставляем в конец наш setup. пока закоментируйте
как компилировать:
если вы выбрали nasm:
nasm -fbin boot.asm -o boot.img
а если yasm:
yasm -fbin boot.asm -o boot.img
всё!!! теперь врубаете VirtualBox и создаёте новую виртуальную машину.
с права. ставите образ дискеты путь к boot.img
радостно врубаете. жмёте F12 . выбираете грузится с дискеты. и всё!!!
чтобы записать на дискету в винде используйте rawrite( вроде так )
в линуксе я не знаю как т.к. я чёто сделал и линукс не видит устройство для чтения/записи дискет