flat assembler
Message board for the users of flat assembler.
![]() Goto page Previous 1, 2 |
Author |
|
BAiC 19 Jun 2012, 06:48
CLD = Clear Direction Flag
|
|||
![]() |
|
BAiC 19 Jun 2012, 07:10
I'm not sure whether it's provided for you, but a stack is fundamental.
Code: xor ax, ax mov ss, ax mov sp, 0x7C00;or somewhere else it also looks like you need to select the Drive Number. storing it to memory first will help. |
|||
![]() |
|
BAiC 19 Jun 2012, 07:12
this works in VirtualBox:
Code: format binary as 'img.flp' use16 ORG 0x7C00 jmp 0:$+5 ; boot sector code xor ax, ax mov ds, ax mov es, ax mov ss, ax mov sp, 0x7C00 movzx dx, dl mov[bootdrive], dx mov si, msg get_msg: lodsb or al, al jz keys_hang mov ah, 0Eh int 10h jmp get_msg keys_hang: xor ax, ax mov ah, 0 ;int 16h jz hang_end hang_end: xor ax, ax mov es, ax mov dx,[bootdrive] mov ah, 02h ;read disk sectors into memory mov al, 1 ;number of sectors to read/write mov ch, 0 ;cylinder number mov cl, 2 ;sector number mov bx, next ;points to the data buffer int 13h jmp next msg db 'Welcome to My_OS BootLoader...', 13, 10 db 'A newbie style boot loader...', 13, 10 db ' ', 13, 10, 0 bootdrive dw 0 times 510 - ($-$$) db 0 db 0x55 db 0xAA next: cld xor ax, ax mov es, ax mov si, stage2msg ld_msg: lodsb or al, al jz inf_lp mov ah, 0Eh int 10h jmp ld_msg inf_lp: jmp inf_lp stage2msg db 'Second Stage following boot sector....', 13, 10, 0 times 1024 - ($-$$) db 0 |
|||
![]() |
|
newport 19 Jun 2012, 10:48
Thanks BAiC! I've been away for a little while...just caught back up...so direction flags cleared and segment registers initialized before every string function...and should I set up a stack for every sector I wish to read from?
and thanks for polishing up the code...seems I was a good ways off. Thanks to you I now have a working example I can study for when I get ready to actually start my OS construction. Right now I'm trying to understand how everything is implemented and why it works the way it does. This is a big help! Do you have any suggestions on the best reading material I could get that maybe explains things newbie friendly in relation to fasm? I think the programmers manual is good but would be better with more examples and explanations... what I think I'm going to do is take the code you posted, cause it works great...is go through and comment on each line and then re-post it and let you see if my comments match up with what the code is actually doing? if you don't mind....does this sound like a good test? that way I'll seem to learn better I think....Thanks again! I really appreciate it! |
|||
![]() |
|
BAiC 19 Jun 2012, 13:06
Quote: should I set up a stack for every sector I wish to read from? eventually, if you want threads/tasks/processes, you'll need to give each of them their own stack but until then don't worry about it. Quote: Do you have any suggestions on the best reading material I could get that maybe explains things newbie friendly in relation to fasm? Quote: what I think I'm going to do is take the code you posted, cause it works great...is go through and comment on each line and then re-post it and let you see if my comments match up with what the code is actually doing? if you don't mind....does this sound like a good test? that way I'll seem to learn better I think Stefan |
|||
![]() |
|
newport 19 Jun 2012, 13:42
Thanks!
|
|||
![]() |
|
newport 21 Jun 2012, 05:46
OK BAiC...
Here's the code with my comments. My questions concerning my comments made to the code are in RED. And also, I modified the code slightly at the end because I wanted to see if I could write a functional macros to print a string,... but other than that it's the same. Thanks for taking the time to review this! I really appreciate yours and everyone else's help that I have received through these forums. Look forward to hearing from ya! Code: ;;;;;;;;;;BEGIN BOOTABLE SECTOR...AS DEFINED BY BIOS THE ORIGIN(start point);;;;;;;;;; ;;;;;;;;;;IS REQUIRED TO BE [0x7C00] AND THE END OF THE BOOT SECTOR IS......;;;;;;;;;; ;;;;;;;;;;DEFINED BY [dw 0xAA55] OR [db 0x55 and db 0xAA]...................;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; format binary as 'img.flp' ;set binary output for use with vmware. use16 ;instuct compiler to generate 16-bit code. ORG 0x7C00 ;memory address bios assigns boot sector to. jmp 0:$+5 ;jump to value of current offset + 5 --- 0:$+5. ;;;;;;;;;;Why current location +5? ;;;;;;;;;;+5 is the only one that seems to work...not +2 or +3 or +10, etc...???. Code: ; boot sector code xor ax, ax ;zeros out or clears ax register mov ds, ax ;reset or set data segments' address to ax(0) mov es, ax ;reset or set extra segments' address to ax(0) mov ss, ax ;reset or set stack segments' address to ax(0) mov sp, 0x7C00 ;set stack point to memory address 7C00 ;;;;;;;;;;Why set 'segment registers' ds, es, and ss to ax(0) value? ;;;;;;;;;;Is it just to have a fresh start on everything? Code: movzx dx, dl ;converts byte to word or double word using a zero extension ;(fills extra bits of larger item with zeros) ;;;;;;;;;;How do we know what 'dl' current value is before performing this operation? ;;;;;;;;;;Why not xor dl, dl prior to this? Code: mov[bootdrive], dx ;defined word bootdrive is given the value of dx ;Modify's the second byte of 'bootdrive' with the value of 'dx' which I believe are zeros... ;;;;;;;;;;What purpose does this serve if 'bootdrive' has only been declared a dw and filled with zeros? ;;;;;;;;;;Does defining 'bootdrive' also automatically give it an address location in memory? Code: mov si, msg ;store location of message in the source index get_msg: ;define label get_msg lodsb ;loads a memory byte addressed by si into the accumlator(al) or al, al ;compares al to itself but doesn't alter al's value and if al=0 ;then loop is complete jz keys_hang ;if the value of al is zero then jump to label keys_hang mov ah, 0Eh ;mov sub-function 0Eh into ah ;to retrieve the value stored in al int 10h ;using int 10h jmp get_msg ;if value of al is not zero loop back to start of label get_msg to retrieve next character keys_hang: ;define label keys_hang xor ax, ax ;clears out register ax ;mov ah, 0 ;move sub-function 0 into ah and ;int 16h ;call int 16h to get keystroke from keyboard - ascii value is stored in al ;jz hang_end ;test for zero flag and if true jump to hang_end jmp hang_end ;I commented out the above and replaced it with an unconditional jump ;since there was no need ;to detect keypress since testing of this section of code was complete. hang_end: ;define label hang_end xor ax, ax ;clear out the ax register( ax is assigned a value of 0 ) mov es, ax ;reset or set extra segments' address to ax(0) mov dx,[bootdrive] ;I'm assuming move the address or offset of bootdrive into the data register ;;;;;;;;;;But if not the address or offset, then why move the value of dw bootdrive into 'dx' when the reverse ;;;;;;;;;;was done early and no 'dx' alterations in between? Code: mov ah, 02h ;read disk sectors into memory ... sub-function of int 13h mov al, 1 ;number of sectors to read/write mov ch, 0 ;cylinder number mov cl, 2 ;sector number mov bx, next ;points to the data buffer ... [ES:BX] ;;;;;;;;;;I'm assuming the use of a label instead of an address location because this allows ;;;;;;;;;;the compiler to figure out the next address buffer's location for us...Is this correct? Code: int 13h ;bios interrupt to read disk sectors into memory with aid of sub-function 02h jmp next ;jump to label next after sectors have been read into memory msg db 'Welcome to My_OS BootLoader...', 13, 10 ;standard message define byte with carriage return and newline db 'A newbie style boot loader...', 13, 10 ;same db ' ', 13, 10, 0 ;same but zero (null) terminated (hence end of string) bootdrive dw 0 ;define word bootdrive ... ;;;;;;;;;;Does the '0' mean null terminated or is '0' the ;;;;;;;;;;assigned value of the defined word bootdrive? Code: times 510 - ($-$$) db 0 ;calculate remaining area to be filled with zeros ;after the end of our program db 0x55 ;also could be written as dw 0xAA55 instead of two 8-bit db's. db 0xAA ;The boot signature. Tells bios that our 512b sector is bootable ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;The end of the bootsector - on to stage two;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; next: cld ;clear direction flag and sets forward direction xor ax, ax ;clear register ax mov es, ax ;reset or set extra segments' address to ax(0) mov si, stage2msg ;store location of stage2msg in the source index ld_msg: ;define ld_msg label lodsb ;loads a memory byte addressed by si into the accumlator(al) or al, al ;compares al to itself but doesn't alter al's value and if al=0 ;then loop is complete jz illusBootMacs ;if 'al' is zeroed out then jump to label illusBootMacs mov ah, 0Eh ;sub-function of int 10h which basically instructs int 10h ;to display the value in 'al' ;which contains the current value in the keyboard buffer int 10h ;executes sub-function OEH of int 10h jmp ld_msg ;continue loop until 'al' is zeroed out stage2msg db 'Second Stage following boot sector....', 13, 10, 0 ;output message with carriage return, ;newline, and zero termination illusBootMacs: xor ah, ah include 'bootmacs.inc' echo ' ' echo 'Welcome to BootMacs....' echo 'BootMacs are Macros written with FASM syntax...' echo ' ' echo ' ' echo 'Press any key to reboot....' echo ' ' xor ah, ah mov ah, 00h int 16h jnz inf_lp inf_lp: int 19h jmp inf_lp times 1474560 - ($ - $$) DB 0 ;marks end of second stage....pretty much rest of floppy... ;;;;;;;;;;By using times 1474560 instead of times 510 or times 1024, etc... ;;;;;;;;;;Does this basically tell the compiler that from the end of our program ;;;;;;;;;;to the end of the floppy is virtually sector 2? |
|||
![]() |
|
BAiC 21 Jun 2012, 09:36
Quote:
"$" is the address of the current instruction.. just imagine a label before the instruction: Code: label: jmp 0:label+5 the instruction itself, "jmp 0:$+5" is 5 bytes long: JMP: 1 byte 0 : 2 bytes $+5: 2 bytes if you add them together, then add that to the current instruction, you get the address of the next instruction. Code: jmp 0:addr addr: Quote: ;;;;;;;;;;Why set 'segment registers' ds, es, and ss to ax(0) value? Quote: ;;;;;;;;;;How do we know what 'dl' current value is before performing this operation? Quote: ;;;;;;;;;;What purpose does this serve if 'bootdrive' has only been declared a dw and filled with zeros? Quote: ;;;;;;;;;;Does defining 'bootdrive' also automatically give it an address location in memory? Quote: ;;;;;;;;;;But if not the address or offset, then why move the value of dw bootdrive into 'dx' when the reverse in FASM: "bootdrive" is a symbolic constant. it's the address of the memory. "[bootdrive]" is a runtime value. it means: "read the value from bootdrive into the register" as to the "no alterations": I assume that DX is modified between "int" usage so it needs to be re-initialized. I don't think ES needs to be re-initialized; that was a slip on my part. Quote: ;;;;;;;;;;I'm assuming the use of a label instead of an address location because this allows Quote: ;;;;;;;;;;Does the '0' mean null terminated or is '0' the Quote: ;;;;;;;;;;By using times 1474560 instead of times 510 or times 1024, etc... Stefan |
|||
![]() |
|
newport 21 Jun 2012, 10:31
BAiC...you are the man!
Thanks man. It's starting to make a lot more sense. Now I'm gonna take your answers to my questions and study them so I completely understand them, then I'm gonna try to re-write this multi-stage bootloader to see if I can develop it on my own using the knowledge that I've gained here. --without peeking at the code of course--lol You don't know how much I appreciate you helping and taking time out of your own endeavors to help me understand. Also, I think this thread will serve as some great information to help other newcomers who want to get into OS design and construction. (IMO) I have found that most assembly tutorials and books, etc. simply tell you what is happening.. 'somewhat', but very few actually tell you why the instructions and code are implemented the way they are... One day I hope to know enough about x86 assembly to write a .pdf/book entitled, "x86 Assembly for Extreme Dummies"..LOL! Once again..., I'm sure that many others and definitely myself appreciate the information that has risen from this thread! |
|||
![]() |
|
BAiC 21 Jun 2012, 21:48
you're welcome. I'm glad I could help.
- Stefan |
|||
![]() |
|
ksanjeet 14 Sep 2012, 19:12
very useful thread for a begineer like me..
|
|||
![]() |
|
Goto page Previous 1, 2 < Last Thread | Next Thread > |
Forum Rules:
|
Copyright © 1999-2023, Tomasz Grysztar. Also on GitHub, YouTube, Twitter.
Website powered by rwasa.