diff --git a/Makefile b/Makefile index f39ce57..f545cbd 100644 --- a/Makefile +++ b/Makefile @@ -1,14 +1,23 @@ -all: boot.img +all: boot.img kernel.bin -boot.bin: bootloader.S - nasm $< -f bin -o $@ +boot.bin: asm/bootloader.S asm/bootloader.S + nasm asm/bootloader.S -f bin -o $@ -boot.img: boot.bin - dd if=$< bs=512 of=$@ +asm/%.o: asm/%.S + nasm $< -f as86 -o $@ + +src/%.o: src/%.c + bcc -ansi -3 -c -o $@ $< + +kernel.bin: src/kernel.o + ld86 -T0x1000 -o $@ $^ + +boot.img: boot.bin kernel.bin + cat $^ > $@ test: boot.img bochs -f bochsrc -q .PHONY: clean clean: - rm -f boot.bin + rm -f boot.bin asm/*o src/*o diff --git a/asm/bootloader.S b/asm/bootloader.S new file mode 100644 index 0000000..36de9a4 --- /dev/null +++ b/asm/bootloader.S @@ -0,0 +1,70 @@ +[bits 16] ; 16 bit real mode code +[org 0x7C00] ; Origin at 0x7C00 (upper end of memory) + +start: + call blankScreen + + mov dx, 0x0 + call setCursorPosition + + mov si, _str_hello ; si = source index + call printString + mov dh, 0x1 + mov dl, 0x0 + call setCursorPosition + + mov al, 0x17 ; read the remaining 16 tracks + mov ch, 0x1 ; .... on track 1 .... + mov cl, 0x1 ; .... starting at sector 1 + mov bx, 0x1000 ; 0x1000 is a standard kernel start location + mov es, bx + xor bx, bx ; bx = 0, es:bs = 0x1000:0 + call loadFloppyDiskSectors + push ax + mov ax, bx + add ax, 0x2200 ; we just read 0x2200 bytes, move pointer in memory + mov bx, ax + pop ax + mov al, 0x17 ; read 18 sectors per track for all future tracks + mov cl, 0x1 ; start at sector 1 for all future tracks + + mov di, 0x2FF ; abuse di as a counter, while (di < 80) + ; di is technically a destination index for stream + ; ops, but nothing is using it ATM, so gimme. +_next_floppy_track: + push ax + mov ax, 0x2e + call printCharacter + mov ax, cx + mov cx, di + mov cl, al + pop ax + call loadFloppyDiskSectors + push ax + mov ax, bx + add ax, 0x2400 ; each floppy track is (512b*18s)=0x2400 bytes long + mov bx, ax + pop ax + inc di + push cx + mov cx, 0x50 + cmp di, cx ; di < 80 ? + jg _end_floppy_read + pop cx + +_end_floppy_read: + mov dh, 0x1 + mov dl, 0x0 + call setCursorPosition + mov si, _str_floppydone + call printString + jmp 0x1000 + +%include "libinterrupt.S" + + _str_hello db 'Piquant v0.1 Bootloader', 0xA, 0 + _str_loading db 'Loading', 0 + _str_floppydone db 'Kernel loaded', 0xA, 0 + +times 510 - ($ - $$) db 0 ; fill up to 510 bytes with 0 +dw 0xAA55 ; magic bootloader signature diff --git a/asm/libinterrupt.S b/asm/libinterrupt.S new file mode 100644 index 0000000..ec078c9 --- /dev/null +++ b/asm/libinterrupt.S @@ -0,0 +1,26 @@ +resetFloppy: +mov ax, 0 ; reset floppy disk (only need ah, reset + ; al while we're here though) +mov dl, 0 ; use drive 0 (first floppy) +int 0x13 +jc resetFloppy +ret + +loadDiskSector: + + +printCharacter: ; print a single character to the display +mov ah, 0x0e ; int 0x10 is the entire display control, + ; 0x0e means teletype output +mov bh, 0x00 ; Print on the zero (primary) page +mov bl, 0x07 ; Color. 0x07 is grey on black. +int 0x10 +ret + +printString: ; print the entire string pointed to by si +mov al, [si] ; [x] == *x, dereferencing source index +call printCharacter +inc si +cmp al, 0x0 ; found the trailing NULL? +jne printString +ret diff --git a/bootloader.S b/bootloader.S index 9e610bf..b09d41e 100644 --- a/bootloader.S +++ b/bootloader.S @@ -1,28 +1,52 @@ [bits 16] ; 16 bit real mode code [org 0x7C00] ; Origin at 0x7C00 (upper end of memory) -mov si, _str_hello ; si = source index -call printString -jmp $ ; hang forever +start: + mov si, _str_hello ; si = source index + call printString + mov al, 0x97 + call printCharacter -printCharacter: ; print a single character to the display -mov ah, 0x0e ; int 0x10 is the entire display control, - ; 0x0e means teletype output -mov bh, 0x00 ; Print on the zero (primary) page -mov bl, 0x07 ; Color. 0x07 is grey on black. -int 0x10 -ret +; mov al, 0x17 ; read the remaining 16 tracks +; mov ch, 0x1 ; .... on track 1 .... +; mov cl, 0x2 ; .... starting at sector 2 +; mov bx, 0x1000 ; 0x1000 is a standard kernel start location +; mov es, bx +; xor bx ; bx = 0, es:bs = 0x1000:0 +; call loadFloppyDiskSectors +; push ax +; mov ax, bx +; add ax, 0x2200 ; we just read 0x2200 bytes, move pointer in memory +; mov bx, ax +; pop ax +; mov al, 0x17 ; read 18 sectors per track for all future tracks +; mov cl, 0x1 ; start at sector 1 for all future tracks -printString: ; print the entire string pointed to by si -mov al, [si] ; [x] == *x, dereferencing source index -call printCharacter -inc si -cmp al, 0x0 ; found the trailing NULL? -jne printString -ret +; mov di, 0x2 ; abuse di as a counter, while (di < 80) +; ; di is technically a destination index for stream +; ; ops, but nothing is using it ATM, so gimme. +; _next_floppy_track: +; mov ch, di +; call loadFloppyDiskSectors +; push ax +; mov ax, bx +; add ax, 0x2400 ; each floppy track is (512b*18s)=0x2400 bytes long +; mov bx, ax +; pop ax +; inc di +; push cx +; mov cx, 0x50 +; cmp di, cx ; di < 80 ? +; jlt _next_floppy_track + mov si, _str_floppydone + call printString + jmp $ -_str_hello db 'Piquant v0.1 Bootloader', 0 ; String + trailing NULL +%include "libinterrupt.S" + + _str_hello db 'Piquant v0.1 Bootloader', 0xA, 0 + _str_floppydone db 'Kernel loaded', 0xA, 0 times 510 - ($ - $$) db 0 ; fill up to 510 bytes with 0 dw 0xAA55 ; magic bootloader signature \ No newline at end of file diff --git a/src/kernel.c b/src/kernel.c new file mode 100644 index 0000000..a472cb5 --- /dev/null +++ b/src/kernel.c @@ -0,0 +1,35 @@ +void printChar(char c) +{ +#asm +#if !__FIRST_ARG_IN_AX__ + mov bx, sp +#endif +#if __FIRST_ARG_IN_AX__ + mov si, ax +#else + mov si, [bx+2] +#endif + mov ah, 0x0e + mov bh, 0x00 + mov bl, 0x07 + int 0x10 +#endasm + return; +} + +void printString(char *ptr) +{ + while (*ptr != '\0') { + printChar(*ptr); + *ptr++; + } + + return; +} + +void main(void) +{ + char *kernelHello = "Welcome to Piquant, please wait while Kernel boots...\n"; + printString(kernelHello); + while(1); +}