We are writing an Ethernet driver for a Switch IC for uClinux (2.6 kernel) running on a NIOS2 processor. I am having difficulty understanding how the kernel will deal with the interrupts. I have been referring to both 'Understanding the Linux Kernel' and 'Linux Device Drivers' (O'Reilly), but I am not sure if I am applying it correctly to this situation.
We have split the task in to two drivers:
- a char driver to deal with switch settings and rx/tx of control frames (containing statistical info etc.).
- a net driver that is in charge of rx/tx of Ethernet frames.
(I am not sure if this is the optimal solution, as combining the driver in to one seems a lot simpler to me, so any opinions on this method would be appreciated.)
- Firstly I would like to clarify how the kernel swaps between events. If for example the transmit function is partially complete (maybe part way through writing to an indirectly adressed register), and an interrupt is received, so the execution jumps to the irqhandler, which in turn calls the rx function. Does this mean that if the rx function accesses the registers and changes the address, that the tx function will read the wrong values when it continues execution?
I am using the function
at the start of the transmit function. Does this mean that an interrupt will have to wait till it is unlocked?
Would either of the above answers be different if the transmit and receive functions were in different drivers?
- Secondly, How does it work when two device drivers attempt to access the same device? Will one be locked out or have to queue for it? or will the both write/read to the address and data lines causing a disaster? (The switch is connected to the CPU via an Avalon MM bus.)
- Lastly, from what I have been reading, it seems like the best way for me to do the reception of Ethernet frames would be to begin the process in the interrupt handler, and then have a tasklet which is queued up to finish it off at a later state. But the drivers we are basing ours on all just complete the entire transmission and reception in single functions without any sort of 'bottom half' split. Infact I can only find 1 driver in the uClinux kernel which does do this.
Would just doing the entire job in the interrupt handler greatly impede performance/operation of the switch?
Thank you very much for taking the time to read my post, hopefully it isn't too device specific, ANY comments are welcomed!