vme_tsi148 driver: interrupt handling
De Roo, Steven
steven.deroo at arcelormittal.com
Wed Jun 5 17:43:28 UTC 2013
Dear Martyn, Manohar & all VME-users,
I'm still struggling with my VME SBC & the VME-drivers...
Please be so kind to have another look at the current situation:
I got to the point that I had a board perfectly reading/writing data to another board,
even with DMA calls to speed up things with a factor 8.
Yesterday, we put the board in a production environment,
and things have become quite complicated since then.
(finally we get some sunshine in Belgium, but now clouds are covering my project...)
Apparently, the existing VME-crate into which the new board was put,
has a lot of VME bus errors in the existing traffic,
as can be seen with a VME analyzer card.
The existing legacy hardware/software cannot be modified however,
so I'll have to live with this situation.
These bus errors cause the TSI148 chipset to abort the read-calls,
and generate an interrupt, which is caught by function 'tsi148_irqhandler()',
and there some strange things happen...
In the beginning of this function, the 'interrupt enable out'
and 'interrupt status' registers are read out, as shown below:
260 /* Determine which interrupts are unmasked and set */
261 enable = ioread32be(bridge->base + TSI148_LCSR_INTEO);
262 stat = ioread32be(bridge->base + TSI148_LCSR_INTS);
The first time an interrupt occurs, both 'enable' and 'stat' are 0,
which is not ok, since the 'enable' register is definitely set to a proper value
when the 'vme_tsi1148' module is loaded/probed.
A consecutive interrupt leads to value -1 (0xFFFFFFFF) for both 'enable' and 'stat',
and then a kernel crash is not far way...
In this case, all handlers (DMA, LM, MB, PERR, VERR, ...) are called,
and inside these handlers, NULL pointers are dereferenced, leading to a crash.
What could possibly be corrupting the TSI148_LCSR_INTEO and TSI148_LCSR_INTS registers ?
Could it be the driver, or can it be the TSI148 chipset itself ?
(e.g. can it be that the interrupt is raised before the registers are filled in correctly ?)
Also, I can't find any good documentation on the difference between the
'interrupt enable out' and 'interrupt enable' registers. Do you have a clue ?
Steven De Roo
More information about the devel