47
47
#include <asm/mach/arch.h>
48
48
#include <asm/mpu.h>
49
49
50
+ #define CREATE_TRACE_POINTS
51
+ #include <trace/events/ipi.h>
52
+
50
53
/*
51
54
* as from 2.5, kernels no longer have an init_tasks structure
52
55
* so we need some other way of telling a new secondary core
@@ -430,38 +433,15 @@ void __init smp_prepare_cpus(unsigned int max_cpus)
430
433
}
431
434
}
432
435
433
- static void (* smp_cross_call )(const struct cpumask * , unsigned int );
436
+ static void (* __smp_cross_call )(const struct cpumask * , unsigned int );
434
437
435
438
void __init set_smp_cross_call (void (* fn )(const struct cpumask * , unsigned int ))
436
439
{
437
- if (!smp_cross_call )
438
- smp_cross_call = fn ;
439
- }
440
-
441
- void arch_send_call_function_ipi_mask (const struct cpumask * mask )
442
- {
443
- smp_cross_call (mask , IPI_CALL_FUNC );
444
- }
445
-
446
- void arch_send_wakeup_ipi_mask (const struct cpumask * mask )
447
- {
448
- smp_cross_call (mask , IPI_WAKEUP );
449
- }
450
-
451
- void arch_send_call_function_single_ipi (int cpu )
452
- {
453
- smp_cross_call (cpumask_of (cpu ), IPI_CALL_FUNC_SINGLE );
440
+ if (!__smp_cross_call )
441
+ __smp_cross_call = fn ;
454
442
}
455
443
456
- #ifdef CONFIG_IRQ_WORK
457
- void arch_irq_work_raise (void )
458
- {
459
- if (is_smp ())
460
- smp_cross_call (cpumask_of (smp_processor_id ()), IPI_IRQ_WORK );
461
- }
462
- #endif
463
-
464
- static const char * ipi_types [NR_IPI ] = {
444
+ static const char * ipi_types [NR_IPI ] __tracepoint_string = {
465
445
#define S (x ,s ) [x ] = s
466
446
S (IPI_WAKEUP , "CPU wakeup interrupts" ),
467
447
S (IPI_TIMER , "Timer broadcast interrupts" ),
@@ -473,6 +453,12 @@ static const char *ipi_types[NR_IPI] = {
473
453
S (IPI_COMPLETION , "completion interrupts" ),
474
454
};
475
455
456
+ static void smp_cross_call (const struct cpumask * target , unsigned int ipinr )
457
+ {
458
+ trace_ipi_raise (target , ipi_types [ipinr ]);
459
+ __smp_cross_call (target , ipinr );
460
+ }
461
+
476
462
void show_ipi_list (struct seq_file * p , int prec )
477
463
{
478
464
unsigned int cpu , i ;
@@ -499,6 +485,29 @@ u64 smp_irq_stat_cpu(unsigned int cpu)
499
485
return sum ;
500
486
}
501
487
488
+ void arch_send_call_function_ipi_mask (const struct cpumask * mask )
489
+ {
490
+ smp_cross_call (mask , IPI_CALL_FUNC );
491
+ }
492
+
493
+ void arch_send_wakeup_ipi_mask (const struct cpumask * mask )
494
+ {
495
+ smp_cross_call (mask , IPI_WAKEUP );
496
+ }
497
+
498
+ void arch_send_call_function_single_ipi (int cpu )
499
+ {
500
+ smp_cross_call (cpumask_of (cpu ), IPI_CALL_FUNC_SINGLE );
501
+ }
502
+
503
+ #ifdef CONFIG_IRQ_WORK
504
+ void arch_irq_work_raise (void )
505
+ {
506
+ if (is_smp ())
507
+ smp_cross_call (cpumask_of (smp_processor_id ()), IPI_IRQ_WORK );
508
+ }
509
+ #endif
510
+
502
511
#ifdef CONFIG_GENERIC_CLOCKEVENTS_BROADCAST
503
512
void tick_broadcast (const struct cpumask * mask )
504
513
{
@@ -556,8 +565,10 @@ void handle_IPI(int ipinr, struct pt_regs *regs)
556
565
unsigned int cpu = smp_processor_id ();
557
566
struct pt_regs * old_regs = set_irq_regs (regs );
558
567
559
- if (ipinr < NR_IPI )
568
+ if ((unsigned )ipinr < NR_IPI ) {
569
+ trace_ipi_entry (ipi_types [ipinr ]);
560
570
__inc_irq_stat (cpu , ipi_irqs [ipinr ]);
571
+ }
561
572
562
573
switch (ipinr ) {
563
574
case IPI_WAKEUP :
@@ -612,6 +623,9 @@ void handle_IPI(int ipinr, struct pt_regs *regs)
612
623
cpu , ipinr );
613
624
break ;
614
625
}
626
+
627
+ if ((unsigned )ipinr < NR_IPI )
628
+ trace_ipi_exit (ipi_types [ipinr ]);
615
629
set_irq_regs (old_regs );
616
630
}
617
631
0 commit comments