Page 1 of 1
int 15h/ax=E820h unexpectedly enabling interrupts
Posted: Wed Sep 13, 2023 6:44 am
by tetraxile
hi, i've been having fun writing a little OS and bootloader in assembly, and i'm testing it on my laptop, a Lenovo IdeaPad S540-14API (AMD Ryzen 7 3700U). i've just recently been using int 15h/ax=E820h to generate a memory map in my bootloader. i used the code on
this article and it works as expected on QEMU, but i noticed that when i run it on my laptop, it's setting the interrupt flag.
my bootloader has a
instruction right at the start, so that i can get through the boot process and set up a protected mode IDT, and only then re-enable interrupts. after adding the E820 interrupt, i noticed that my laptop (but not QEMU) was now crashing very soon after i entered protected mode; i eventually tracked it down as the PIT sending an interrupt (which frustratingly looked like a double fault until i remembered IRQs exist) that i wasn't handling as i only set up my IDT's interrupt handlers after i've already entered protected mode. anyway, i confirmed that it was E820 specifically that was setting the interrupt flag by printing FLAGS' value immediately before and after running the interrupt.
as far as i can tell this shouldn't be happening, right? of course an easy solution is to just tack another
onto the end of my
subroutine, but i'm wondering what the actual cause of this is. i haven't been able to find any info about other people experiencing this issue, nor is it mentioned on the wiki. is it really just specific to my laptop's BIOS? its BIOS version is
in case this means something to anyone.
Re: int 15h/ax=E820h unexpectedly enabling interrupts
Posted: Sun Oct 15, 2023 2:00 pm
by Octocontrabass
tetraxile wrote:as far as i can tell this shouldn't be happening, right?
The BIOS is free to enable interrupts any time you call it. Your code must be prepared for that to happen.
Re: int 15h/ax=E820h unexpectedly enabling interrupts
Posted: Sat Oct 28, 2023 10:49 pm
by sounds
One common solution is to organize the code sort of like this:
- Disable interrupts (CLI)
- Get the E820h memory map (plus any other calls into the BIOS)
- Disable the 8259 PIC
- Do another CLI
Re: int 15h/ax=E820h unexpectedly enabling interrupts
Posted: Sat Oct 28, 2023 10:53 pm
by Octocontrabass
sounds wrote:One common solution is to organize the code sort of like this:
Steps 1 and 3 are unnecessary.
Re: int 15h/ax=E820h unexpectedly enabling interrupts
Posted: Sun Oct 29, 2023 12:07 am
by nullplan
tetraxile wrote:and only then re-enable interrupts.
That is a bit disconcerting to me. You are not supposed to enable interrupts until you have found and initialized all interrupt controllers. And the initialization of the interrupt controllers should include masking out all interrupts. The drivers requesting interrupts would then unmask them again, but have them masked by default. Else you are getting interrupts you cannot handle.
Also, why are you running BIOS interrupts from protected mode? Just query the E820 list from real mode before switching to protected mode.
Re: int 15h/ax=E820h unexpectedly enabling interrupts
Posted: Sun Oct 29, 2023 7:54 am
by sounds
Octocontrabass wrote:Steps 1 and 3 are unnecessary.
Perhaps? Not sure what you mean. After all, getting the 8259 PIC into a known state is considered harmless.
Re: int 15h/ax=E820h unexpectedly enabling interrupts
Posted: Sun Oct 29, 2023 8:12 am
by sounds
Oh, I was misreading your comment. I guess what you're saying is "since the bootloader was just loaded at 0x7C00 and then the BIOS jumped to it, immediately doing an int 15h/ax=E820h doesn't require a CLI, and in fact the CLI is probably unnecessary. Calling int 15h/ax=E280h is table stakes, any BIOS probably supports it since every single bootloader from Windows to Linux to BSD is going to be doing it right away."
Is that closer to what you meant?
Re: int 15h/ax=E820h unexpectedly enabling interrupts
Posted: Sun Oct 29, 2023 1:13 pm
by Octocontrabass
Yep, that's pretty much it.