diff options
Diffstat (limited to 'arch/sparc/kernel/sun4m_irq.c')
-rw-r--r-- | arch/sparc/kernel/sun4m_irq.c | 58 |
1 files changed, 20 insertions, 38 deletions
diff --git a/arch/sparc/kernel/sun4m_irq.c b/arch/sparc/kernel/sun4m_irq.c index e61165161dd3..c5ade9d27a1d 100644 --- a/arch/sparc/kernel/sun4m_irq.c +++ b/arch/sparc/kernel/sun4m_irq.c | |||
@@ -112,9 +112,6 @@ struct sun4m_handler_data { | |||
112 | #define SUN4M_INT_E14 0x00000080 | 112 | #define SUN4M_INT_E14 0x00000080 |
113 | #define SUN4M_INT_E10 0x00080000 | 113 | #define SUN4M_INT_E10 0x00080000 |
114 | 114 | ||
115 | #define SUN4M_HARD_INT(x) (0x000000001 << (x)) | ||
116 | #define SUN4M_SOFT_INT(x) (0x000010000 << (x)) | ||
117 | |||
118 | #define SUN4M_INT_MASKALL 0x80000000 /* mask all interrupts */ | 115 | #define SUN4M_INT_MASKALL 0x80000000 /* mask all interrupts */ |
119 | #define SUN4M_INT_MODULE_ERR 0x40000000 /* module error */ | 116 | #define SUN4M_INT_MODULE_ERR 0x40000000 /* module error */ |
120 | #define SUN4M_INT_M2S_WRITE_ERR 0x20000000 /* write buffer error */ | 117 | #define SUN4M_INT_M2S_WRITE_ERR 0x20000000 /* write buffer error */ |
@@ -282,23 +279,6 @@ out: | |||
282 | return irq; | 279 | return irq; |
283 | } | 280 | } |
284 | 281 | ||
285 | #ifdef CONFIG_SMP | ||
286 | static void sun4m_send_ipi(int cpu, int level) | ||
287 | { | ||
288 | sbus_writel(SUN4M_SOFT_INT(level), &sun4m_irq_percpu[cpu]->set); | ||
289 | } | ||
290 | |||
291 | static void sun4m_clear_ipi(int cpu, int level) | ||
292 | { | ||
293 | sbus_writel(SUN4M_SOFT_INT(level), &sun4m_irq_percpu[cpu]->clear); | ||
294 | } | ||
295 | |||
296 | static void sun4m_set_udt(int cpu) | ||
297 | { | ||
298 | sbus_writel(cpu, &sun4m_irq_global->interrupt_target); | ||
299 | } | ||
300 | #endif | ||
301 | |||
302 | struct sun4m_timer_percpu { | 282 | struct sun4m_timer_percpu { |
303 | u32 l14_limit; | 283 | u32 l14_limit; |
304 | u32 l14_count; | 284 | u32 l14_count; |
@@ -318,9 +298,6 @@ struct sun4m_timer_global { | |||
318 | 298 | ||
319 | static struct sun4m_timer_global __iomem *timers_global; | 299 | static struct sun4m_timer_global __iomem *timers_global; |
320 | 300 | ||
321 | |||
322 | unsigned int lvl14_resolution = (((1000000/HZ) + 1) << 10); | ||
323 | |||
324 | static void sun4m_clear_clock_irq(void) | 301 | static void sun4m_clear_clock_irq(void) |
325 | { | 302 | { |
326 | sbus_readl(&timers_global->l10_limit); | 303 | sbus_readl(&timers_global->l10_limit); |
@@ -369,10 +346,11 @@ void sun4m_clear_profile_irq(int cpu) | |||
369 | 346 | ||
370 | static void sun4m_load_profile_irq(int cpu, unsigned int limit) | 347 | static void sun4m_load_profile_irq(int cpu, unsigned int limit) |
371 | { | 348 | { |
372 | sbus_writel(limit, &timers_percpu[cpu]->l14_limit); | 349 | unsigned int value = limit ? timer_value(limit) : 0; |
350 | sbus_writel(value, &timers_percpu[cpu]->l14_limit); | ||
373 | } | 351 | } |
374 | 352 | ||
375 | static void __init sun4m_init_timers(irq_handler_t counter_fn) | 353 | static void __init sun4m_init_timers(void) |
376 | { | 354 | { |
377 | struct device_node *dp = of_find_node_by_name(NULL, "counter"); | 355 | struct device_node *dp = of_find_node_by_name(NULL, "counter"); |
378 | int i, err, len, num_cpu_timers; | 356 | int i, err, len, num_cpu_timers; |
@@ -402,13 +380,22 @@ static void __init sun4m_init_timers(irq_handler_t counter_fn) | |||
402 | /* Every per-cpu timer works in timer mode */ | 380 | /* Every per-cpu timer works in timer mode */ |
403 | sbus_writel(0x00000000, &timers_global->timer_config); | 381 | sbus_writel(0x00000000, &timers_global->timer_config); |
404 | 382 | ||
405 | sbus_writel((((1000000/HZ) + 1) << 10), &timers_global->l10_limit); | 383 | #ifdef CONFIG_SMP |
384 | sparc_config.cs_period = SBUS_CLOCK_RATE * 2; /* 2 seconds */ | ||
385 | sparc_config.features |= FEAT_L14_ONESHOT; | ||
386 | #else | ||
387 | sparc_config.cs_period = SBUS_CLOCK_RATE / HZ; /* 1/HZ sec */ | ||
388 | sparc_config.features |= FEAT_L10_CLOCKEVENT; | ||
389 | #endif | ||
390 | sparc_config.features |= FEAT_L10_CLOCKSOURCE; | ||
391 | sbus_writel(timer_value(sparc_config.cs_period), | ||
392 | &timers_global->l10_limit); | ||
406 | 393 | ||
407 | master_l10_counter = &timers_global->l10_count; | 394 | master_l10_counter = &timers_global->l10_count; |
408 | 395 | ||
409 | irq = sun4m_build_device_irq(NULL, SUN4M_TIMER_IRQ); | 396 | irq = sun4m_build_device_irq(NULL, SUN4M_TIMER_IRQ); |
410 | 397 | ||
411 | err = request_irq(irq, counter_fn, IRQF_TIMER, "timer", NULL); | 398 | err = request_irq(irq, timer_interrupt, IRQF_TIMER, "timer", NULL); |
412 | if (err) { | 399 | if (err) { |
413 | printk(KERN_ERR "sun4m_init_timers: Register IRQ error %d.\n", | 400 | printk(KERN_ERR "sun4m_init_timers: Register IRQ error %d.\n", |
414 | err); | 401 | err); |
@@ -434,7 +421,7 @@ static void __init sun4m_init_timers(irq_handler_t counter_fn) | |||
434 | trap_table->inst_two = lvl14_save[1]; | 421 | trap_table->inst_two = lvl14_save[1]; |
435 | trap_table->inst_three = lvl14_save[2]; | 422 | trap_table->inst_three = lvl14_save[2]; |
436 | trap_table->inst_four = lvl14_save[3]; | 423 | trap_table->inst_four = lvl14_save[3]; |
437 | local_flush_cache_all(); | 424 | local_ops->cache_all(); |
438 | local_irq_restore(flags); | 425 | local_irq_restore(flags); |
439 | } | 426 | } |
440 | #endif | 427 | #endif |
@@ -475,17 +462,12 @@ void __init sun4m_init_IRQ(void) | |||
475 | if (num_cpu_iregs == 4) | 462 | if (num_cpu_iregs == 4) |
476 | sbus_writel(0, &sun4m_irq_global->interrupt_target); | 463 | sbus_writel(0, &sun4m_irq_global->interrupt_target); |
477 | 464 | ||
478 | BTFIXUPSET_CALL(clear_clock_irq, sun4m_clear_clock_irq, BTFIXUPCALL_NORM); | 465 | sparc_config.init_timers = sun4m_init_timers; |
479 | BTFIXUPSET_CALL(load_profile_irq, sun4m_load_profile_irq, BTFIXUPCALL_NORM); | 466 | sparc_config.build_device_irq = sun4m_build_device_irq; |
480 | 467 | sparc_config.clock_rate = SBUS_CLOCK_RATE; | |
481 | sparc_irq_config.init_timers = sun4m_init_timers; | 468 | sparc_config.clear_clock_irq = sun4m_clear_clock_irq; |
482 | sparc_irq_config.build_device_irq = sun4m_build_device_irq; | 469 | sparc_config.load_profile_irq = sun4m_load_profile_irq; |
483 | 470 | ||
484 | #ifdef CONFIG_SMP | ||
485 | BTFIXUPSET_CALL(set_cpu_int, sun4m_send_ipi, BTFIXUPCALL_NORM); | ||
486 | BTFIXUPSET_CALL(clear_cpu_int, sun4m_clear_ipi, BTFIXUPCALL_NORM); | ||
487 | BTFIXUPSET_CALL(set_irq_udt, sun4m_set_udt, BTFIXUPCALL_NORM); | ||
488 | #endif | ||
489 | 471 | ||
490 | /* Cannot enable interrupts until OBP ticker is disabled. */ | 472 | /* Cannot enable interrupts until OBP ticker is disabled. */ |
491 | } | 473 | } |