Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Hello, are BIOS interrupt calls allowed to set the interrupt flag? All the references to BIOS interrupts I looked didn't say anything about it. I develop my kernel in QEMU mostly but yesterday I tried to run it on VMWare and it kept reseting. After hours of debugging with gdb I narrowed down the problem to this:
start:
cli
mov ax, 0
mov ds, ax
mov es, ax
mov ss, ax
mov sp, 0x7c00
jmp 0:clearCS
;; IF is not set here
clearCS:
;; reset drive
mov ah, 0
mov dl, 0
stc
int 0x13
jc clearCS
;; IF is set here
;; this code runs. ax == 0x1234
mov ax, 0x1234
jmp $
times 510-($-$$) db 0
db 0x55, 0xaa
felipe wrote:So what is the traditional approach? Clear the IF after every BIOS call? Because that is what I had to do to make it work.
There's 2 cases to consider:
If you're using BIOS functions, then there should be no reason for your code to disable interrupts at all, and you should leave interrupts enabled.
If you can't leave interrupts enabled for some reason, then you shouldn't be using the BIOS functions.
Your code is the first case.
Cheers,
Brendan
For all things; perfection is, and will always remain, impossible to achieve in practice. However; by striving for perfection we create things that are as perfect as practically possible. Let the pursuit of perfection be our guide.
Thanks Brendan, anyway I said I had to clear the flag after every BIOS call but since it is only for my bootloader, it is not such a big problem. Just out of curiosity do you guys know if this is a bug of the BIOS in VMware or the state of the IF (and possibly others) are unspecified after such a call?
I think, as Brendan said, you need to leave interrupts alone when you're relying on using BIOS functions and I suspect that different implementations of BIOS will have difference responses to what you're doing - i.e. some will not care, others will fault. Of course, I might be missing some subtlety in what you're asking, so ignore me if I am rambling.
On a totally different note and I mention it only because it jumped out at me (but it's not critical), I see you MOVing 0 into registers; it's almost always, perhaps even always faster to XOR the register with itself than to move a constant, that happens to be zero, into it.
Gaidheal wrote:I think, as Brendan said, you need to leave interrupts alone when you're relying on using BIOS functions
I think you are right, the whole problem it seems was caused because the first thing I usually do in a bootloader is clear the interrupt flag (I figured that I wasn't going to deal with interrupts there) and then expect it to be cleared when my C kernel starts running (before I set up the IDT), as you guys have pointed out it will be probably best if I leave the interrupts alone and then clear the flag as one of the last things I do in the boot loader.
Gaidheal wrote:On a totally different note and I mention it only because it jumped out at me (but it's not critical), I see you MOVing 0 into registers; it's almost always, perhaps even always faster to XOR the register with itself than to move a constant, that happens to be zero, into it.
Yeah, I knew that, it is only that I always though that was I bit of a hack, a quirk of the way instructions are coded, anyway that accounts for only half a dozen instructions in my code (I quickly switch to C). But thanks for the tips anyway.
It is a bit 'hacky' I agree, hehe! For pure readability I can see why you would write it out 'correctly' and IIRC some (many?) compilers and assemblers will actually substitute "xor reg, reg" for cases where the code evaluates to "mov reg, 0".
That said, it's not as quirky as it might seem at first - it's a logical certainty that 'exclusive-or' on a value with itself yields zero and it's also generally certain that register only operations, especially logical operator ones, are much faster than anything involving memory access (which is what the MOV amounts to as your zero is just a value in memory).
No matter, I only mentioned it in case you were unaware, as much so that you would understand it when used by others as to suggest that you use it yourself.
Gaidheal wrote:No matter, I only mentioned it in case you were unaware, as much so that you would understand it when used by others as to suggest that you use it yourself.