Message ID | 20110523230514.GA20476@entuzijast.net |
---|---|
State | RFC |
Delegated to: | David Miller |
Headers | show |
On Tue, May 24, 2011 at 01:05:14AM +0200, Josip Rodin wrote: > + board = of_getintprop_default(dp, "board#", 0); > + if (!board) { > Passing around the 'board' property of 'cpu-unit' looks like it should be done > because the same thing is used to seed board_to_cpu[]. > > http://git.kernel.org/?p=linux/kernel/git/davem/prtconfs.git;a=blob;f=ss1000;h=f420dc005d6939b837134d146741316c024d5932;hb=HEAD > says both cpu-units have the same, zeroth board, but it might not hurt > to check just in case some other machine happens to use a different index. In fact it looks like 0 is a common valid value in the analogous pieces of code that don't even verify the result of that lookup. The above code should either not check that lookup either (the simple solution), or set the default to -1 so that it can actually discern error state.
On Tue, 24 May 2011, Josip Rodin wrote: > On Tue, May 24, 2011 at 01:05:14AM +0200, Josip Rodin wrote: > > + board = of_getintprop_default(dp, "board#", 0); > > + if (!board) { > > > Passing around the 'board' property of 'cpu-unit' looks like it should be done > > because the same thing is used to seed board_to_cpu[]. > > > > http://git.kernel.org/?p=linux/kernel/git/davem/prtconfs.git;a=blob;f=ss1000;h=f420dc005d6939b837134d146741316c024d5932;hb=HEAD > > says both cpu-units have the same, zeroth board, but it might not hurt > > to check just in case some other machine happens to use a different index. > > In fact it looks like 0 is a common valid value in the analogous pieces of > code that don't even verify the result of that lookup. The above code should > either not check that lookup either (the simple solution), or set the > default to -1 so that it can actually discern error state. > Hi, Thanks for your suggestions. I tested this earlier and you are correct, it has to be -1 to work at all, as the boards are 0-indexed. It does however not work completly as intended. The same goes for Daniel suggestion about using the virtual IRQ for the irq registration. With these changes request_irq completes without errors, and the system continues to boot. But stalls again during "Calibrating delay loop...". Closer inspection reveals that this is caused by the system jiffies not increasing, and the processor being stuck in a spinlock. I added printouts to the sun4d interrupt handler (Hoping that prom_printf is interruptsafe). This reveals that it is triggered only once with the SUN4D_TIMER_IRQ as the pil argument. I guess that the interrupt is not marked as processed correctly/retriggered. (sun4d_clear_clock_irq is called, so it should be) Does anyone have the datasheet for SuperSparc II and MXCC? as there are some sun4d specific calls being made during interrupt processing that read some status flags from the MXCC. - Kjetil Oftedal -- To unsubscribe from this list: send the line "unsubscribe sparclinux" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html
On 05/24/2011 01:43 PM, Kjetil Oftedal wrote: > Does anyone have the datasheet for SuperSparc II and MXCC? as there are > some sun4d specific calls being made during interrupt processing that > read some status flags from the MXCC. Here's what I have for the SuperSparc II. I do not have the corresponding document for MXCC. ~tom == Fedora Project
diff --git a/arch/sparc/kernel/sun4d_irq.c b/arch/sparc/kernel/sun4d_irq.c index a9ea60e..c18c5f2 100644 --- a/arch/sparc/kernel/sun4d_irq.c +++ b/arch/sparc/kernel/sun4d_irq.c @@ -305,7 +305,6 @@ unsigned int sun4d_build_device_irq(struct platform_device *op, struct device_node *dp = op->dev.of_node; struct device_node *io_unit, *sbi = dp->parent; const struct linux_prom_registers *regs; - struct sun4d_handler_data *handler_data; unsigned int pil; unsigned int irq; int board, slot; @@ -348,6 +347,19 @@ unsigned int sun4d_build_device_irq(struct platform_device *op, else pil = real_irq; + return _sun4d_build_device_irq(real_irq, pil, board); + +err_out: + return irq; +} + +unsigned int _sun4d_build_device_irq(unsigned int real_irq, + unsigned int pil, + unsigned int board) +{ + struct sun4d_handler_data *handler_data; + unsigned int irq; + irq = irq_alloc(real_irq, pil); if (irq == 0) goto err_out; @@ -368,7 +380,12 @@ unsigned int sun4d_build_device_irq(struct platform_device *op, irq_set_handler_data(irq, handler_data); err_out: - return real_irq; + return irq; +} + +unsigned int sun4d_build_timer_irq(unsigned int board, unsigned int real_irq) +{ + return _sun4d_build_device_irq(real_irq, real_irq, board); } static void __init sun4d_fixup_trap_table(void) @@ -402,6 +419,7 @@ static void __init sun4d_init_timers(irq_handler_t counter_fn) unsigned int irq; const u32 *reg; int err; + int board; dp = of_find_node_by_name(NULL, "cpu-unit"); if (!dp) { @@ -414,12 +432,19 @@ static void __init sun4d_init_timers(irq_handler_t counter_fn) * bootbus. */ reg = of_get_property(dp, "reg", NULL); - of_node_put(dp); if (!reg) { prom_printf("sun4d_init_timers: No reg property\n"); prom_halt(); } + board = of_getintprop_default(dp, "board#", 0); + if (!board) { + prom_printf("sun4d_init_timers: No board# property on cpu-unit\n"); + prom_halt(); + } + + of_node_put(dp); + res.start = reg[1]; res.end = reg[2] - 1; res.flags = reg[0] & 0xff; @@ -434,7 +459,7 @@ static void __init sun4d_init_timers(irq_handler_t counter_fn) master_l10_counter = &sun4d_timers->l10_cur_count; - irq = sun4d_build_device_irq(NULL, SUN4D_TIMER_IRQ); + irq = sun4d_build_timer_irq(board, SUN4D_TIMER_IRQ); err = request_irq(irq, counter_fn, IRQF_TIMER, "timer", NULL); if (err) { prom_printf("sun4d_init_timers: request_irq() failed with %d\n",