Page 1 of 2

[SOLVED] Can't get any hardware IRQ

Posted: Mon Sep 09, 2013 4:23 pm
by amonte
Hello !
I'm new to OS development, and I'm currently writing a simple kernel in c.
I (finally) got the interrupts to work, and I mapped my IRQs to interrupts 32-47.
When I fire int $33 for example, the corresponding IRQ handler is correctly called, but I can't get any hardware IRQ.
For example, when I setup the PIT this way :

Code: Select all

irq_install_handler(IRQ0, callback);
	
	// The value we send to the PIT is the value to divide it's input clock
	// (1193180 Hz) by, to get our required frequency. Important to note is
	// that the divisor must be small enough to fit into 16-bits.
	uint32_t divisor = 1193180 / freq;
	
	// Send the command byte.
	outb(0x43, 0x36);
	
	// Divisor has to be sent byte-wise, so split here into upper/lower bytes.
	uint8_t l = (uint8_t)(divisor & 0xFF);
	uint8_t h = (uint8_t)( (divisor>>8) & 0xFF );
	
	// Send the frequency divisor.
	outb(0x40, l);
	outb(0x40, h);
I get only one IRQ0 call, and nothing more.
After the IRQ handler was called, I do

Code: Select all

if (regs->int_no >= 40) // regs->int_no specifies the interrupt number
	{
		// Send reset signal to slave.
		outb(0xA0, 0x20);
	}
	// Send reset signal to master. (As well as slave, if necessary).
	outb(0x20, 0x20);
to send the EOI signal to the CPU, am I doing things wrong ?

Thank you in advance, and please excuse me if I'm missing something in my explanation,
alex

Re: Can't get any hardware IRQ

Posted: Mon Sep 09, 2013 5:21 pm
by mistergabe
You seem to be doing everything correctly. Possibly it's your interrupt handler that's not returning properly.

Re: Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 12:01 am
by amonte
Hi mistergabe,
Thank you for your very fast answer !
Maybe that's because of my emulator ? I'm using qemu-system-i386 -kernel kernel.bin to run my kernel,
and I can't have many debug information (qemu is quite silent...).
I give you the order in which I did things :
(1) install gdt
(2) PIC remapping using this code :

Code: Select all

	outb(0x20, 0x11);
	outb(0xA0, 0x11);
	outb(0x21, 0x20);
	outb(0xA1, 0x28);
	outb(0x21, 0x04);
	outb(0xA1, 0x02);
	outb(0x21, 0x01);
	outb(0xA1, 0x01);
	outb(0x21, 0x0);
	outb(0xA1, 0x0);
(3) mapping the ISRs and IRQs into the interrupt descriptor table
(4) sending the table using lidt (I think this works properly)
(5) enabling interrupts with sti

I think I send EOI properly because if I do two int $33, my handler is correctly called two times.
Am I doing things in wrong order ?

I can't manage to compile bochs on my computer (Mac OSX), so I don't have many debug information...

edit: My ISR/IRQ chain : a asm handler isrN is called, makes a cli and pushes the interrupt number on the stack, and call a common stub who calls my handler. Here is this stub (maybe I'm doing something wrong at the end ?)

Code: Select all

    pusha
	push %ds # Push all user segment selectors
	push %es
	push %fs
	push %gs
	mov $0x10, %ax # User kernel data segment selector
	mov %ax, %ds
	mov %ax, %es
	mov %ax, %fs
	mov %ax, %gs
	mov %esp, %eax # Push the address of ESP as a parameter so that the
	push %eax # Fault handler function can access the REG structure
	call isr_handler
	pop %eax
	pop %gs
	pop %fs
	pop %es
	pop %ds
	popa
	add $8, %esp # Cleans up pushed error code and Interrupt number
	sti
	iret # CPU will pop off CS, EIP, EFLAGS, SS, and ESP automatically
My IRQ chain is exactly the same, and here is irq_common_stub :

Code: Select all

    pusha
	push %ds
	push %es
	push %fs
	push %gs
	movw $0x10,%ax
	movw %ax,%ds
	movw %ax,%es
	movw %ax,%fs
	movw %ax,%gs
	movl %esp, %eax
	push %eax
	call irq_handler
	pop %eax
	pop %gs
	pop %fs
	pop %es
	pop %ds
	popa
	add $8, %esp
	sti
	iret
Thank you in advance,
alex

Re: Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 2:15 am
by dozniak
amonte wrote: I think I send EOI properly because if I do two int $33, my handler is correctly called two times.
Am I doing things in wrong order ?
int $33 is a software interrupt, it doesn't need EOI.
amonte wrote: I can't manage to compile bochs on my computer (Mac OSX), so I don't have many debug information...
Try

Code: Select all

brew install bochs
it's that simple.

Re: Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 4:03 am
by iansjack
# Cleans up pushed error code...
What pushed error code?

BTW, qemu has a built in monitor that provides some information and debugging is very easy with the aid of gdb.

Re: Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 4:30 am
by amonte
Hi guys !
Thank you for your posting :)
Try
Code:
brew install bochs

it's that simple.
I have very obfuscated dependencies problems with my libiconv (and others), so I currently can't install some dependencies bochs needs through brew (I'm trying to still several hours...).
What pushed error code?
In fact, the first function called when an interrupt happens is a small asm routine (example here with ISR3) :

Code: Select all

isr3:
	cli
	pushl $0
	pushl $3
	jmp isr_common_stub
This little function pushes the interrupt number (for identifying the ISR in C), and a dummy (always 0) error code, because some interrupts (8 and 10-14) pushes one by themselves).

I can't figure where is the problem, I think this is at the end of my isr_common_stub or irq_common_stub function, because the C handlers returns properly.

Again, thank you for your help !
alex

Re: Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 5:10 am
by amonte
UPDATE :
Okay, I finally managed to get the PIT to work (I don't know how, I just changed the add $8, %esp to add $16,%esp, got a general protection fault, set it back to add $8, %esp, and it worked :shock: ).
So i played a little with that, and then I connected IRQ1 to my keyboard handler, who just prints "kb\n".
But, again, if i strike a key, my handler is called, but just one time, no more... (the PIT continues to work)
Seems to be a strange bug in my kernel :?

Thanks,
alex

Re: Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 5:47 am
by iansjack
Are you reading the data from the keyboard controller? If you don't do that then you won't get further interrupts.

Have a look at http://wiki.osdev.org/Kernel_Debugging for information about using gdb with qemu. You will find life a lot easier if you can single-step through code.

Re: Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 8:04 am
by amonte
Oh yes, it works !
Sorry for this stupid error, I haven't guessed that the IRQ routine must read the port.
This is all working now !
I'll read this page on kernel debugging, it should be really useful !
Again, thanks to iansjack, dozniak and mistergabe for you help :D
alex

Re: Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 12:38 pm
by bwat
amonte wrote:UPDATE :
Okay, I finally managed to get the PIT to work (I don't know how, I just changed the add $8, %esp to add $16,%esp, got a general protection fault, set it back to add $8, %esp, and it worked :shock: ).
On a scale of 1 to 10, how happy are you with that explanation? If the answer is greater than 3 then you can stop reading here.

There's a quote by Suzanne K. Langer that we programmers, in my opinion, should always tell ourselves in situations like these: "Every universe of discourse has its logical structure." There is a proper logical reason for the state of your system going from not-working to working --- it wasn't magic, that much I know. If you want to get good at this OS design thing, then you will probably want to figure out what happened. If you want to get great at this OS design thing the will have to figure out what happened.

That quote is part of my personal credo. It stops me getting frustrated when I react emotionally to, what is most usually self inflicted, design and implementation errors; it provokes me into detailed study and definition of the problem at hand; it helps me write better software. The quote comes from the introduction to her A Set of Postulates for the Logical Structure of Music, The Monist 39.

Re: [SOLVED] Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 1:39 pm
by iansjack
That is certainly, on the face of it, a very sensible comment. But advice is only good if there is some way that it can be applied. So I would be interested to know what steps you would suggest the OP now takes to determine what was the cause of the original problem.

Re: [SOLVED] Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 2:12 pm
by bwat
iansjack wrote:That is certainly, on the face of it, a very sensible comment. But advice is only good if there is some way that it can be applied. So I would be interested to know what steps you would suggest the OP now takes to determine what was the cause of the original problem.
Good point! Giving general advice is easy and only really helpful in changing the big picture. So let's talk specifics:

Here are three steps that build upon the assumption that the computer is a deterministic machine that will behave in accordance with its configuration (programming). I would claim that I could give state transition diagrammes for the working of the machine (CPU, clock chip etc.) if I had enough time. These transition diagrammes would be the logical structure of problem. The transition from one state to another could be modelled in first order logic. Pretty much nobody has the time to do this so we tentatively accept the assumption mentioned at the beginning of this paragraph.

1) Diff the two source code versions of the working and non-working systems. This would require some kind of version control. I suppose even manual version control with the source code of each system in its own directory would be good enough. I always have version control in place so I would just "git diff" to see what had changed. The delta is an obvious source of configuration differences, either registers are programmed differently, or in a different order. Computers are on the whole deterministic machines so the same code should give the same behaviour (the OP claims to have gotten differing results from the same code!).


2) I would dump the contents of any pertinent registers/memory locations. In this case IDTs, all 8259a registers, all processor registers, trap frame, all 8254-2 registers. I would dump these before the first clock interrupt, possibly just after initialisation and before interrupts were enabled. I would then dump when the ISR for the clock was entered, I would then dump after I had returned from the interrupt. If the values before and after the interrupt were the same (obviously things like the instruction pointer would differ but you know what I mean) then the problem lies somewhere between my computer's keyboard and my chair, i.e., my understanding of the problem at hand is not right. I would then hit the books and spec. sheets. Another way of putting this is that because the machine is deterministic, I have not dumped the right data. I need to figure out what that data is.

3) Consider that the knowledge that the machine is deterministic may not be knowledge at all, it may be belief. Is the computer broken? Try on another computer. If I was running on BOCHS then run it on hardware.

Re: [SOLVED] Can't get any hardware IRQ

Posted: Tue Sep 10, 2013 3:19 pm
by iansjack
The problem is that, reading between the lines, I very much doubt that the OP has the code under version control. And the only change that he is aware of making is to change one line and change it back again. We are talking here about a single person making their first steps in OS programming, not a closely controlled project. Again, I would doubt that before and after versions of the executable are now available.

Leaving aside whether computers are strictly deterministic machines (in theory they are, but there are a number of reasons why this may not be true in practice) there is sometimes a limit to how sensible it is to expend effort on a baffling, but trivial, problem that has been solved. I would judge this to be such a case. My suspicion would be that there might have been some corruption in the original source file that was corrected by retyping the line; impossible to prove now I suspect.

Satisfying though it would be to attain a complete understanding of every bug that occurs in a program, I think that sometimes one has to be pragmatic and just accept that "**** happens". The desire for perfection is admirable but a study of the life of Charles Babbage would indicate that it does not always produce the desired results.

Just my opinion.

Re: [SOLVED] Can't get any hardware IRQ

Posted: Wed Sep 11, 2013 12:27 am
by h0bby1
bwat wrote:
iansjack wrote:That is certainly, on the face of it, a very sensible comment. But advice is only good if there is some way that it can be applied. So I would be interested to know what steps you would suggest the OP now takes to determine what was the cause of the original problem.
Good point! Giving general advice is easy and only really helpful in changing the big picture. So let's talk specifics:

Here are three steps that build upon the assumption that the computer is a deterministic machine that will behave in accordance with its configuration (programming). I would claim that I could give state transition diagrammes for the working of the machine (CPU, clock chip etc.) if I had enough time. These transition diagrammes would be the logical structure of problem. The transition from one state to another could be modelled in first order logic. Pretty much nobody has the time to do this so we tentatively accept the assumption mentioned at the beginning of this paragraph.

1) Diff the two source code versions of the working and non-working systems. This would require some kind of version control. I suppose even manual version control with the source code of each system in its own directory would be good enough. I always have version control in place so I would just "git diff" to see what had changed. The delta is an obvious source of configuration differences, either registers are programmed differently, or in a different order. Computers are on the whole deterministic machines so the same code should give the same behaviour (the OP claims to have gotten differing results from the same code!).


2) I would dump the contents of any pertinent registers/memory locations. In this case IDTs, all 8259a registers, all processor registers, trap frame, all 8254-2 registers. I would dump these before the first clock interrupt, possibly just after initialisation and before interrupts were enabled. I would then dump when the ISR for the clock was entered, I would then dump after I had returned from the interrupt. If the values before and after the interrupt were the same (obviously things like the instruction pointer would differ but you know what I mean) then the problem lies somewhere between my computer's keyboard and my chair, i.e., my understanding of the problem at hand is not right. I would then hit the books and spec. sheets. Another way of putting this is that because the machine is deterministic, I have not dumped the right data. I need to figure out what that data is.

3) Consider that the knowledge that the machine is deterministic may not be knowledge at all, it may be belief. Is the computer broken? Try on another computer. If I was running on BOCHS then run it on hardware.
there always been ghosts in the machine, some random code segment who gathered together to form unpredicted protocols non anticipated, those free radicals ask the question of the free will, of creativity, and even of the nature of what we could call soul, how is it possible that machine left in darkness seek the light, why robot put in empty space get close to each other rather than staying alone, some random code segment, or is there something more ? from what moment a processus of perception become consciousness, at which moment a comparative system become truth seeking =)

Re: [SOLVED] Can't get any hardware IRQ

Posted: Wed Sep 11, 2013 1:04 am
by bwat
iansjack wrote:Satisfying though it would be to attain a complete understanding of every bug that occurs in a program, I think that sometimes one has to be pragmatic and just accept that "**** happens". The desire for perfection is admirable but a study of the life of Charles Babbage would indicate that it does not always produce the desired results.
I would say that it is exactly those times when we don't follow your advice that we make the most progress.