1 #include <linux/kernel.h>
2 #include <linux/module.h>
3 #include <linux/errno.h>
4 #include <linux/trace_seq.h>
5 #include <linux/ftrace_event.h>
6 #include <linux/device.h>
7 #include <linux/platform_device.h>
8 #include <linux/vmalloc.h>
11 #include "asm/hardware/cache-l2x0.h"
12 #include "mach/mt_reg_base.h"
13 #include "mach/sync_write.h"
14 #include "mach/mt_emi_bm.h"
15 //#include "mach/mt6573_pll.h"
16 #include "mach/mt_mon.h"
17 // FIX-ME mark for porting
18 #include "mach/mt_dcm.h"
19 //#include <../../kernel/kernel/trace/trace.h>
20 #include <../../../kernel/trace/trace.h>
23 #define MON_LOG_BUFF_LEN (64 * 1024)
24 #define DEF_BM_RW_TYPE (BM_BOTH_READ_WRITE)
26 static DECLARE_BITMAP(buf_bitmap
, MON_LOG_BUFF_LEN
);
29 static unsigned int bm_master_evt
= BM_MASTER_AP_MCU
;
30 static unsigned int bm_rw_type_evt
= DEF_BM_RW_TYPE
;
32 static MonitorMode register_mode
= MODE_FREE
;
33 static unsigned long mon_period_evt
;
34 static unsigned int mon_manual_evt
;
36 struct mt_mon_log
*mt_mon_log_buff
; //this buffer is allocated for MODE_MANUAL_USER & MODE_MANUAL_KERNEL only
37 unsigned int mt_mon_log_buff_index
;
38 unsigned int mt_kernel_ring_buff_index
;
40 struct arm_pmu
*p_pmu
;
41 struct mtk_monitor mtk_mon
;
43 //static DEFINE_SPINLOCK(mtk_monitor_lock);
46 * mt65xx_mon_init: Initialize the monitor.
49 static int mt65xx_mon_init(void)
55 if (0 == BM_GetEmiDcm()) //0 means EMI dcm is enabled
57 printk("[MON] Disable system DCM\n");
59 BM_SetEmiDcm(0xff); //disable EMI dcm
66 * mt65xx_mon_deinit: De-initialize the monitor.
69 static int mt65xx_mon_deinit(void)
75 if (mt_mon_log_buff) {
76 vfree(mt_mon_log_buff);
83 if (1 == BM_GetEmiDcm()) //1 means EMI dcm is disabled
85 printk("[MON] Enable system DCM\n");
87 BM_SetEmiDcm(0x0); //enable EMI dcm
95 * mt65xx_mon_enable: Enable hardware monitors.
98 static int mt65xx_mon_enable(void)
103 // enable & start ARM performance monitors
107 // stopping EMI monitors will reset all counters
110 // start EMI monitor counting
117 * mt65xx_mon_disable: Disable hardware monitors.
120 static int mt65xx_mon_disable(void)
123 // disable ARM performance monitors
131 static inline void set_cpumask(unsigned int cpu
, unsigned int index
, volatile unsigned long *p
)
133 unsigned long cpumask
= 1UL << cpu
;
134 unsigned int offset
= (index
& 3) << 3; // (index % 4) * 8
138 *p
|= (cpumask
<< offset
);
141 static inline void clear_bitmap(unsigned int bit
, volatile unsigned long *p
)
144 unsigned long mask = 1UL << (bit & 31);
152 static inline int get_cpumask(unsigned int index
, volatile unsigned long *p
)
155 unsigned long offset
= (index
& 3) << 3; // (index % 4) * 8
159 res
= (res
>> offset
) & 0x7;
164 * mt65xx_mon_log: Get the current log from hardware monitors.
165 * Return a index to the curret log entry in the log buffer.
167 static unsigned int mt65xx_mon_log(void* log_buff
)
169 struct mt_mon_log
* mon_buff
;
170 struct pmu_data
*pmu_data
= & p_pmu
->perf_data
;
171 unsigned int cpu
= raw_smp_processor_id();
172 unsigned int cur
= 0;
174 p_pmu
->read_counter();
177 /* In MODE_SCHED_SWITCH, we need to record the current CPU number to get the Context Switch CPU number.
180 if( register_mode
== MODE_MANUAL_USER
|| register_mode
== MODE_MANUAL_KERNEL
){
181 set_cpumask(cpu
,cur
,buf_bitmap
);
182 cur
= mt_mon_log_buff_index
++;
183 mon_buff
= &mt_mon_log_buff
[cur
];
184 mt_mon_log_buff_index
%= MON_LOG_BUFF_LEN
;
186 cur
= mt_kernel_ring_buff_index
++;
187 mon_buff
= (struct mt_mon_log
*)log_buff
;
192 for_each_present_cpu(cpu
){
193 mon_buff
->cpu_cnt0
[cpu
] = pmu_data
->cnt_val
[cpu
][0];
194 mon_buff
->cpu_cnt1
[cpu
] = pmu_data
->cnt_val
[cpu
][1];
195 mon_buff
->cpu_cnt2
[cpu
] = pmu_data
->cnt_val
[cpu
][2];
196 mon_buff
->cpu_cnt3
[cpu
] = pmu_data
->cnt_val
[cpu
][3];
197 mon_buff
->cpu_cyc
[cpu
] = pmu_data
->cnt_val
[cpu
][ARMV7_CYCLE_COUNTER
];
201 mon_buff
->BM_BCNT
= BM_GetBusCycCount();
202 mon_buff
->BM_TACT
= BM_GetTransAllCount();
203 mon_buff
->BM_TSCT
= BM_GetTransCount(1);
204 mon_buff
->BM_WACT
= BM_GetWordAllCount();
205 mon_buff
->BM_WSCT
= BM_GetWordCount(1);
206 mon_buff
->BM_BACT
= BM_GetBandwidthWordCount();
207 mon_buff
->BM_BSCT
= BM_GetOverheadWordCount();
208 mon_buff
->BM_TSCT2
= BM_GetTransCount(2);
209 mon_buff
->BM_WSCT2
= BM_GetWordCount(2);
210 mon_buff
->BM_TSCT3
= BM_GetTransCount(3);
211 mon_buff
->BM_WSCT3
= BM_GetWordCount(3);
212 mon_buff
->BM_WSCT4
= BM_GetWordCount(4);
213 mon_buff
->BM_TTYPE1
= BM_GetLatencyCycle(1);
214 mon_buff
->BM_TTYPE2
= BM_GetLatencyCycle(2);
215 mon_buff
->BM_TTYPE3
= BM_GetLatencyCycle(3);
216 mon_buff
->BM_TTYPE4
= BM_GetLatencyCycle(4);
217 mon_buff
->BM_TTYPE5
= BM_GetLatencyCycle(5);
219 mon_buff
->BM_TTYPE9
= BM_GetLatencyCycle(9);
220 mon_buff
->BM_TTYPE10
= BM_GetLatencyCycle(10);
221 mon_buff
->BM_TTYPE11
= BM_GetLatencyCycle(11);
222 mon_buff
->BM_TTYPE12
= BM_GetLatencyCycle(12);
223 mon_buff
->BM_TTYPE13
= BM_GetLatencyCycle(13);
225 //mon_buff->BM_TPCT1 = BM_GetTransTypeCount(1); //not used now
228 mon_buff
->DRAMC_PageHit
= DRAMC_GetPageHitCount(DRAMC_ALL
);
229 mon_buff
->DRAMC_PageMiss
= DRAMC_GetPageMissCount(DRAMC_ALL
);
230 mon_buff
->DRAMC_Interbank
= DRAMC_GetInterbankCount(DRAMC_ALL
);
231 mon_buff
->DRAMC_Idle
= DRAMC_GetIdleCount();
235 memset(pmu_data
->cnt_val
[0], 0, sizeof(struct pmu_data
));
239 extern unsigned int mt_get_emi_freq(void);
241 enum print_line_t
mt65xx_mon_print_entry(struct mt65xx_mon_entry
*entry
, struct trace_iterator
*iter
){
242 struct trace_seq
*s
= &iter
->seq
;
243 int cpu
= entry
->cpu
;
244 struct mt_mon_log
*log_entry
;
245 unsigned int log
= 0;
246 MonitorMode mon_mode_evt
= get_mt65xx_mon_mode();
250 return TRACE_TYPE_HANDLED
;
252 log_entry
= &entry
->field
;
257 trace_seq_printf(s
, "MON_LOG_BUFF_LEN = %d, ", MON_LOG_BUFF_LEN
);
258 trace_seq_printf(s
, "EMI_CLOCK = %d, ", mt_get_emi_freq());
261 if(mon_mode_evt
!= MODE_SCHED_SWITCH
){
262 for_each_present_cpu(cpu
)
266 " cpu%d_cyc = %d, cpu%d_cnt0 = %d, cpu%d_cnt1 = %d, cpu%d_cnt2 = %d, cpu%d_cnt3 = %d, ",
268 log_entry
->cpu_cyc
[cpu
],
270 log_entry
->cpu_cnt0
[cpu
],
272 log_entry
->cpu_cnt1
[cpu
],
274 log_entry
->cpu_cnt2
[cpu
],
276 log_entry
->cpu_cnt3
[cpu
]);
279 else /*SCHED_SWITCH - only print self cpu*/
283 " cpu%d_cyc = %d, cpu%d_cnt0 = %d, cpu%d_cnt1 = %d, cpu%d_cnt2 = %d, cpu%d_cnt3 = %d, ",
285 log_entry
->cpu_cyc
[cpu
],
287 log_entry
->cpu_cnt0
[cpu
],
289 log_entry
->cpu_cnt1
[cpu
],
291 log_entry
->cpu_cnt2
[cpu
],
293 log_entry
->cpu_cnt3
[cpu
]);
298 "BM_BCNT = %d, BM_TACT = %d, BM_TSCT = %d, ",
305 "BM_WACT = %d, BM_WSCT0 = %d, BM_BACT = %d, ",
317 "BM_TSCT2 = %d, BM_WSCT2 = %d, ",
319 log_entry
->BM_WSCT2
);
323 "BM_TSCT3 = %d, BM_WSCT3 = %d, ",
325 log_entry
->BM_WSCT3
);
329 "BM_WSCT4 = %d, BM_TPCT1 = %d, ",
331 log_entry
->BM_TPCT1
);
335 "BM_TTYPE01 = %d, BM_TTYPE09 = %d, ",
336 log_entry
->BM_TTYPE1
, log_entry
->BM_TTYPE9
);
340 "BM_TTYPE02 = %d, BM_TTYPE10 = %d, ",
341 log_entry
->BM_TTYPE2
, log_entry
->BM_TTYPE10
);
345 "BM_TTYPE03 = %d, BM_TTYPE11 = %d, ",
346 log_entry
->BM_TTYPE3
, log_entry
->BM_TTYPE11
);
350 "BM_TTYPE04 = %d, BM_TTYPE12 = %d, ",
351 log_entry
->BM_TTYPE4
, log_entry
->BM_TTYPE12
);
355 "BM_TTYPE05 = %d, BM_TTYPE13 = %d, ",
356 log_entry
->BM_TTYPE5
, log_entry
->BM_TTYPE13
);
360 "DRAMC_PageHit = %d, DRAMC_PageMiss = %d, DRAMC_Interbank = %d, DRAMC_Idle = %d\n",
361 log_entry
->DRAMC_PageHit
,
362 log_entry
->DRAMC_PageMiss
,
363 log_entry
->DRAMC_Interbank
,
364 log_entry
->DRAMC_Idle
);
369 static void mt65xx_mon_set_pmu(struct pmu_cfg
*p_cfg
)
371 memcpy(&p_pmu
->perf_cfg
, p_cfg
, sizeof(struct pmu_cfg
));
374 static void mt65xx_mon_get_pmu(struct pmu_cfg
*p_cfg
)
376 memcpy(p_cfg
, &p_pmu
->perf_cfg
, sizeof(struct pmu_cfg
));
379 static void mt65xx_mon_set_l2c(struct l2c_cfg
*l_cfg
)
383 static void mt65xx_mon_get_l2c(struct l2c_cfg
*l_cfg
)
387 static void mt65xx_mon_set_bm_rw(int type
)
390 if(type
> BM_WRITE_ONLY
) {
391 printk("invalid event\n");
393 BM_SetReadWriteType(type
);
398 static ssize_t
bm_master_evt_show(struct device_driver
*driver
, char *buf
)
400 return snprintf(buf
, PAGE_SIZE
, "EMI bus monitor master = %d\n", bm_master_evt
);
403 static ssize_t
bm_master_evt_store(struct device_driver
*driver
, const char *buf
, size_t count
)
405 if (!strncmp(buf
, "MM", strlen("MM"))) {
406 bm_master_evt
= BM_MASTER_MM
;
407 }else if (!strncmp(buf
, "APMCU", strlen("APMCU"))) {
408 bm_master_evt
= BM_MASTER_AP_MCU
;
409 }else if (!strncmp(buf
, "MDMCU", strlen("MDMCU"))) {
410 bm_master_evt
= BM_MASTER_MD_MCU
;
411 }else if (!strncmp(buf
, "2G_3G_MDDMA", strlen("2G_3G_MDDMA"))) {
412 bm_master_evt
= BM_MASTER_2G_3G_MDDMA
;
413 }else if (!strncmp(buf
, "MD_ALL", strlen("MD_ALL"))) {
414 bm_master_evt
= BM_MASTER_MD_MCU
| BM_MASTER_2G_3G_MDDMA
;
415 }else if (!strncmp(buf
, "PERI", strlen("PERI"))) {
416 bm_master_evt
= BM_MASTER_PERI
;
417 }else if (!strncmp(buf
, "ALL", strlen("ALL"))) {
418 bm_master_evt
= BM_MASTER_ALL
;
420 printk("invalid event\n");
425 BM_SetMaster(1, bm_master_evt
);
430 static ssize_t
bm_rw_type_evt_show(struct device_driver
*driver
, char *buf
)
432 return snprintf(buf
, PAGE_SIZE
, "EMI bus read write type = %d\n", bm_rw_type_evt
);
435 static ssize_t
bm_rw_type_evt_store(struct device_driver
*driver
, const char *buf
, size_t count
)
437 if (!strncmp(buf
, "RW", strlen("RW"))) {
438 bm_rw_type_evt
= BM_BOTH_READ_WRITE
;
439 } else if (!strncmp(buf
, "RO", strlen("RO"))) {
440 bm_rw_type_evt
= BM_READ_ONLY
;
441 } else if (!strncmp(buf
, "WO", strlen("WO"))) {
442 bm_rw_type_evt
= BM_WRITE_ONLY
;
444 printk("invalid event\n");
448 BM_SetReadWriteType(bm_rw_type_evt
);
453 static ssize_t
mon_mode_evt_show(struct device_driver
*driver
, char *buf
)
455 MonitorMode mon_mode_evt
;
456 mon_mode_evt
= get_mt65xx_mon_mode();
457 if(mon_mode_evt
== MODE_MANUAL_USER
)
458 return snprintf(buf
, PAGE_SIZE
, "Monitor mode = MANUAL_USER\n");
459 else if(mon_mode_evt
== MODE_SCHED_SWITCH
)
460 return snprintf(buf
, PAGE_SIZE
, "Monitor mode = SCHED_SWITCH\n");
461 else if(mon_mode_evt
== MODE_PERIODIC
)
462 return snprintf(buf
, PAGE_SIZE
, "Monitor mode = PERIODIC\n");
463 else if(mon_mode_evt
== MODE_MANUAL_TRACER
)
464 return snprintf(buf
, PAGE_SIZE
, "Monitor mode = MANUAL_TRACER\n");
465 else if(mon_mode_evt
== MODE_MANUAL_KERNEL
)
466 return snprintf(buf
, PAGE_SIZE
, "Monitor mode = MANUAL_KERNEL\n");
467 else if(mon_mode_evt
== MODE_FREE
)
468 return snprintf(buf
, PAGE_SIZE
, "Monitor mode = FREE\n");
470 return snprintf(buf
, PAGE_SIZE
, "Monitor mode = Unknown\n");
473 static ssize_t
mon_mode_evt_store(struct device_driver
*driver
, const char *buf
, size_t count
)
475 MonitorMode mon_mode_evt
;
476 if (!strncmp(buf
, "SCHED_SWITCH", strlen("SCHED_SWITCH"))) {
477 mon_mode_evt
= MODE_SCHED_SWITCH
;
478 } else if (!strncmp(buf
, "PERIODIC", strlen("PERIODIC"))) {
479 mon_mode_evt
= MODE_PERIODIC
;
480 } else if (!strncmp(buf
, "MANUAL_TRACER", strlen("MANUAL_TRACER"))) {
481 mon_mode_evt
= MODE_MANUAL_TRACER
;
483 printk("invalid event\n");
487 set_mt65xx_mon_mode(mon_mode_evt
);
492 static ssize_t
mon_period_evt_show(struct device_driver
*driver
, char *buf
)
494 return snprintf(buf
, PAGE_SIZE
, "Monitor period = %ld (for periodic mode)\n", get_mt65xx_mon_period());
497 static ssize_t
mon_period_evt_store(struct device_driver
*driver
, const char *buf
, size_t count
)
500 sscanf(buf
, "%ld", &mon_period_evt
);
501 set_mt65xx_mon_period(mon_period_evt
);
506 static ssize_t
mon_manual_evt_show(struct device_driver
*driver
, char *buf
)
508 mon_manual_evt
= get_mt65xx_mon_manual_start();
509 if(mon_manual_evt
== 1)
510 return snprintf(buf
, PAGE_SIZE
, "Manual Monitor is Started (for manual mode)\n");
511 else if(mon_manual_evt
== 0)
512 return snprintf(buf
, PAGE_SIZE
, "Manual Monitor is Stopped (for manual mode)\n");
517 static ssize_t
mon_manual_evt_store(struct device_driver
*driver
, const char *buf
, size_t count
)
520 if (!strncmp(buf
, "START", strlen("START"))) {
522 } else if (!strncmp(buf
, "STOP", strlen("STOP"))) {
525 printk("invalid event\n");
529 set_mt65xx_mon_manual_start(mon_manual_evt
);
534 static ssize_t
cpu_pmu_evt_show(struct device_driver
*driver
, char *buf
)
541 printk("PMU user interface isn't ready now!\n");
545 for(j
= 0; j
< NUMBER_OF_EVENT
; j
++) {
546 size
+= sprintf(buf
+ size
, "Evt%d = 0x%x\t", j
, p_pmu
->perf_cfg
.event_cfg
[j
]);
548 size
+= sprintf(buf
+ size
, "\n");
553 static ssize_t
cpu_pmu_evt_store(struct device_driver
*driver
, const char *buf
, size_t count
)
556 char *p
= (char *)buf
;
561 if((strlen(buf
)+1) > 128)
563 printk("[PMU] command overflow!");
568 ptr
= strsep (&p
, " ");
573 //because we use i to count num of evt setting, i is NUMBER_OF_EVENT+1
574 if(i
!= (NUMBER_OF_EVENT
+1)){
575 printk("[PMU]The number of parameter is wrong!!! Please echo ");
576 for(i
= 0; i
< NUMBER_OF_EVENT
; i
++)
578 printk("> cpu_pmu_cfg\n");
583 for(i
= 0; i
< NUMBER_OF_EVENT
; i
++)
584 p_pmu
->perf_cfg
.event_cfg
[i
] = simple_strtoul(token
[i
], &token
[i
], 16);
587 for(i
=0; i
<NUMBER_OF_EVENT
; i
++)
588 printk("%x ",p_pmu
->perf_cfg
.event_cfg
[i
]);
596 static ssize_t
emi_dcm_ctrl_show(struct device_driver
*driver
, char *buf
)
598 return snprintf(buf
, PAGE_SIZE
, "EMI DCM is %s\n", BM_GetEmiDcm() ? "OFF" : "ON");
601 static ssize_t
emi_dcm_ctrl_store(struct device_driver
*driver
, const char *buf
, size_t count
)
603 if (!strncmp(buf
, "OFF", strlen("OFF"))) {
605 } else if (!strncmp(buf
, "ON", strlen("ON"))) {
608 printk("invalid event\n");
615 static ssize_t
mci_evt_show(struct device_driver
*driver
, char *buf
)
621 ssize_t
mci_evt_store(struct device_driver
*driver
, const char *buf
, size_t count
)
623 unsigned int evt0
, evt1
;
624 if (sscanf(buf
, "%x %x", &evt0
, &evt1
) != 2)
626 MCI_Event_Set(evt0
, evt1
);
632 DRIVER_ATTR(bm_master_evt
, 0644, bm_master_evt_show
, bm_master_evt_store
);
633 DRIVER_ATTR(bm_rw_type_evt
, 0644, bm_rw_type_evt_show
, bm_rw_type_evt_store
);
635 DRIVER_ATTR(mon_mode_evt
, 0644, mon_mode_evt_show
, mon_mode_evt_store
);
636 DRIVER_ATTR(mon_period_evt
, 0644, mon_period_evt_show
, mon_period_evt_store
);
637 DRIVER_ATTR(mon_manual_evt
, 0644, mon_manual_evt_show
, mon_manual_evt_store
);
639 DRIVER_ATTR(cpu_pmu_cfg
, 0644, cpu_pmu_evt_show
, cpu_pmu_evt_store
);
640 DRIVER_ATTR(emi_dcm_ctrl
, 0644, emi_dcm_ctrl_show
, emi_dcm_ctrl_store
);
642 //DRIVER_ATTR(mci_evt, 0644, mci_evt_show, mci_evt_store);
645 static struct device_driver mt_mon_drv
=
647 .name
= "mt_monitor",
648 .bus
= &platform_bus_type
,
649 .owner
= THIS_MODULE
,
653 struct mtk_monitor mtk_mon
= {
654 .init
= mt65xx_mon_init
,
655 .deinit
= mt65xx_mon_deinit
,
656 .enable
= mt65xx_mon_enable
,
657 .disable
= mt65xx_mon_disable
,
658 .mon_log
= mt65xx_mon_log
,
659 .set_pmu
= mt65xx_mon_set_pmu
,
660 .get_pmu
= mt65xx_mon_get_pmu
,
661 .set_l2c
= mt65xx_mon_set_l2c
,
662 .get_l2c
= mt65xx_mon_get_l2c
,
663 .set_bm_rw
= mt65xx_mon_set_bm_rw
,
667 * mt_mon_mod_init: module init function
669 static int __init
mt_mon_mod_init(void)
673 /* register driver and create sysfs files */
674 ret
= driver_register(&mt_mon_drv
);
677 printk("fail to register mt_mon_drv\n");
680 ret
= driver_create_file(&mt_mon_drv
, &driver_attr_bm_master_evt
);
681 ret
|= driver_create_file(&mt_mon_drv
, &driver_attr_bm_rw_type_evt
);
682 ret
|= driver_create_file(&mt_mon_drv
, &driver_attr_mon_mode_evt
);
683 ret
|= driver_create_file(&mt_mon_drv
, &driver_attr_mon_period_evt
);
684 ret
|= driver_create_file(&mt_mon_drv
, &driver_attr_mon_manual_evt
);
685 ret
|= driver_create_file(&mt_mon_drv
, &driver_attr_cpu_pmu_cfg
);
686 ret
|= driver_create_file(&mt_mon_drv
, &driver_attr_emi_dcm_ctrl
);
687 // ret |= driver_create_file(&mt_mon_drv, &driver_attr_mci_evt);
690 printk("fail to create mt_mon sysfs files\n");
695 /* SPNIDEN[12] must be 1 for using ARM11 performance monitor unit */
696 // *(volatile unsigned int *)0xF702A000 |= 0x1000;
699 ret
= register_pmu(&p_pmu
);
700 if(ret
!= 0 || p_pmu
== NULL
) {
701 printk("Register PMU Fail\n");
706 /* init EMI bus monitor */
707 BM_SetReadWriteType(DEF_BM_RW_TYPE
);
708 BM_SetMonitorCounter(1, BM_MASTER_MM
, BM_TRANS_TYPE_4BEAT
| BM_TRANS_TYPE_8Byte
| BM_TRANS_TYPE_BURST_WRAP
);
709 BM_SetMonitorCounter(2, BM_MASTER_AP_MCU
, BM_TRANS_TYPE_4BEAT
| BM_TRANS_TYPE_8Byte
| BM_TRANS_TYPE_BURST_WRAP
);
710 BM_SetMonitorCounter(3, BM_MASTER_MD_MCU
| BM_MASTER_2G_3G_MDDMA
, BM_TRANS_TYPE_4BEAT
| BM_TRANS_TYPE_8Byte
| BM_TRANS_TYPE_BURST_WRAP
);
711 BM_SetMonitorCounter(4, BM_MASTER_PERI
, BM_TRANS_TYPE_4BEAT
| BM_TRANS_TYPE_8Byte
| BM_TRANS_TYPE_BURST_WRAP
);
713 BM_SetLatencyCounter();
715 /*select MCI monitor event*/
716 //MCI_Event_Set(0x6, 0x7); /*0x6: Si0 AR input queue full; 0x7: Si0 AW input queue full*/
721 arch_initcall (mt_mon_mod_init
);
723 static DEFINE_SPINLOCK(reg_mon_lock
);
724 int register_monitor(struct mtk_monitor
**p_mon
, MonitorMode mode
)
728 spin_lock(®_mon_lock
);
730 mt_kernel_ring_buff_index
= 0;
731 mt_mon_log_buff_index
= 0;
733 if(register_mode
!= MODE_FREE
) {
736 register_mode
= mode
;
740 if(mode
== MODE_MANUAL_USER
|| mode
== MODE_MANUAL_KERNEL
) {
741 if (!mt_mon_log_buff
) {
742 mt_mon_log_buff
= vmalloc(sizeof(struct mt_mon_log
) * MON_LOG_BUFF_LEN
);
743 if (!mt_mon_log_buff
) {
744 printk(KERN_WARNING
"fail to allocate the buffer for the monitor log\n");
745 register_mode
= MODE_FREE
;
748 mtk_mon
.log_buff
= mt_mon_log_buff
;
752 if(mode
== MODE_SCHED_SWITCH
)
753 p_pmu
->multicore
= 0;
755 p_pmu
->multicore
= 1;
757 spin_unlock(®_mon_lock
);
763 spin_unlock(®_mon_lock
);
766 EXPORT_SYMBOL(register_monitor
);
768 void unregister_monitor(struct mtk_monitor
**p_mon
)
771 spin_lock(®_mon_lock
);
773 if(mt_mon_log_buff
) {
774 vfree(mt_mon_log_buff
);
775 mt_mon_log_buff
= NULL
;
778 register_mode
= MODE_FREE
;
781 mt_kernel_ring_buff_index
= 0;
782 mt_mon_log_buff_index
= 0;
783 spin_unlock(®_mon_lock
);
785 EXPORT_SYMBOL(unregister_monitor
);