1 #include <linux/module.h>
2 #include <linux/device.h>
4 #include <linux/cdev.h>
5 #include <linux/interrupt.h>
6 #include <linux/spinlock.h>
7 #include <linux/uaccess.h>
9 #include <linux/kfifo.h>
10 #include <linux/firmware.h>
11 #include <linux/syscalls.h>
12 #include <linux/uaccess.h>
13 #include <linux/platform_device.h>
14 #include <linux/proc_fs.h>
15 #include <asm/setup.h>
17 #include <mach/mtk_eemcs_helper.h>
18 #include <mach/mt_boot.h>
19 #include <mach/dfo_boot.h>
20 #include <asm/memblock.h>
21 #include <mach/battery_common.h>
23 #define SHOW_WARNING_NUM (5)
25 #define DFO_FEATURE_EN
26 #define MD5_MEM_SIZE (16*1024*1024)
28 //-------------feature enable/disable configure (oringinal from mtk_ccci_helper.c)----------------//
29 #define FEATURE_GET_MD_BAT_VOL //disable for bring up
30 //-------------grobal variable define----------------//
32 unsigned int ext_md_support
[MAX_EXT_MD_NUM
];
33 unsigned int ext_md_usage_case
= 0;
34 unsigned int ext_md_size_list
[MAX_EXT_MD_NUM
] = {0};
35 phys_addr_t ext_md_mem_addr
[MAX_EXT_MD_NUM
] = {0};
37 eemcs_kern_func_info eemcs_func_table
[MAX_EXT_MD_NUM
][MAX_KERN_API
];
38 static unsigned char eemcs_kern_func_err_num
[MAX_EXT_MD_NUM
][MAX_KERN_API
];
39 eemcs_sys_cb_func_info_t eemcs_sys_cb_table_1000
[MAX_EXT_MD_NUM
][MAX_KERN_API
];
40 eemcs_sys_cb_func_info_t eemcs_sys_cb_table_100
[MAX_EXT_MD_NUM
][MAX_KERN_API
];
41 int (*eemcs_sys_msg_notify_func
[MAX_EXT_MD_NUM
])(int, unsigned int, unsigned int);
43 typedef struct _dfo_item
49 static dfo_item_t eemcs_dfo_setting
[] =
51 {"MTK_MD5_SUPPORT", modem_lwg
},
52 {"MTK_ENABLE_MD5", 1},
53 {"MD5_SIZE", MD5_MEM_SIZE
},
57 /*------------------------external function API------------------------*/
58 extern unsigned long *get_ext_modem_start_addr_list(void);
59 /*---------------------------------------------------------------------*/
62 static int get_eemcs_dfo_setting(char item
[], unsigned int *val
)
68 for (i
=0; i
<(sizeof(eemcs_dfo_setting
)/sizeof(dfo_item_t
)); i
++) {
69 eemcs_name
= eemcs_dfo_setting
[i
].name
;
70 eemcs_value
= eemcs_dfo_setting
[i
].value
;
71 if(!strcmp(eemcs_name
, item
)) {
72 printk("[EEMCS/PLAT] Get DFO:%s:0x%08X\n", eemcs_name
, eemcs_value
);
73 *val
= (unsigned int)eemcs_value
;
77 //printk("[EEMCS/PLAT] DFO:%s not found\n", i+1, item);
78 printk("[EEMCS/PLAT] DFO:%s not found\n", item
);
82 void update_ext_md_support(void)
85 ext_md_usage_case
= 0;
87 if(get_eemcs_dfo_setting("MTK_MD5_SUPPORT", &val
) == 0) {
88 ext_md_support
[MD_SYS5
-MD_EXT1
] = val
;
91 if(get_eemcs_dfo_setting("MTK_ENABLE_MD5", &val
) == 0) {
93 ext_md_usage_case
|= MD5_EN
;
97 if(get_eemcs_dfo_setting("MD5_SIZE", &val
) == 0) {
98 val
= round_up(val
, 0x200000);
99 ext_md_size_list
[MD_SYS5
-MD_EXT1
] = val
;
104 /*API for kernal memory setting*/
105 /*get the info about how many modem is running currently*/
106 unsigned int get_nr_ext_modem(void)
108 return MAX_EXT_MD_NUM
;
110 EXPORT_SYMBOL(get_nr_ext_modem
);
113 unsigned int *get_ext_modem_size_list(void)
115 return ext_md_size_list
;
117 EXPORT_SYMBOL(get_ext_modem_size_list
);
119 #ifdef DFO_FEATURE_EN // pase DFO ATAG info
120 int parse_eemcs_dfo_setting(void *dfo_tbl
, int num
)
128 tag_dfo_boot
*dfo_data
;
133 dfo_data
= (tag_dfo_boot
*)dfo_tbl
;
134 for (i
=0; i
<(sizeof(eemcs_dfo_setting
)/sizeof(dfo_item_t
)); i
++) {
135 eemcs_name
= eemcs_dfo_setting
[i
].name
;
136 eemcs_value
= &(eemcs_dfo_setting
[i
].value
);
137 for (j
=0; j
<num
; j
++) {
138 tag_name
= dfo_data
->name
[j
];
139 tag_value
= dfo_data
->value
[j
];
140 if(!strcmp(eemcs_name
, tag_name
)) {
141 *eemcs_value
= tag_value
;
144 printk("[EEMCS/PLAT] DFO:%s:0x%08X\n", eemcs_name
, *eemcs_value
);
147 update_ext_md_support();
150 #else // load default seeting
151 int parse_eemcs_dfo_setting(void *dfo_data
, int num
)
157 for (i
=0; i
<(sizeof(eemcs_dfo_setting
)/sizeof(dfo_item_t
)); i
++) {
158 eemcs_name
= eemcs_dfo_setting
[i
].name
;
159 eemcs_value
= eemcs_dfo_setting
[i
].value
;
160 printk("[EEMCS/PLAT] DFO:%s:0x%08X\n", eemcs_name
, eemcs_value
);
163 update_ext_md_support();
169 void eemcs_memory_reserve(void){
172 if( (ext_md_usage_case
&MD5_EN
)== MD5_EN
) { //Only MD1 enabled
174 ext_md_mem_addr
[MD_SYS5
-MD_EXT1
] =
175 (unsigned int)arm_memblock_steal(ext_md_size_list
[MD_SYS5
-MD_EXT1
], SZ_32M
);
176 } else { // No MD is enabled
178 ext_md_mem_addr
[MD_SYS5
-MD_EXT1
] = 0;
181 if ( (ext_md_mem_addr
[MD_SYS5
-MD_EXT1
]&(32*1024*1024 - 1)) != 0 )
182 printk("[EEMCS/PLAT] md5 memory addr is not 32M align!!!\n");
184 printk("[EEMCS/PLAT] EN(%d):MemBase(0x%08X)\n", md5_en
, (unsigned int)ext_md_mem_addr
);
186 printk("[EEMCS/PLAT] (0)MemStart(0x%08X):MemSize(0x%08X)\n", \
187 ext_md_mem_addr
[MD_SYS5
-MD_EXT1
], ext_md_size_list
[MD_SYS5
-MD_EXT1
]);
191 int parse_ext_meta_md_setting(unsigned char args
[])
193 unsigned char md_active_setting
= args
[1];
194 unsigned char md_setting_flag
= args
[0];
196 int active_index
= -1;
198 if(!(md_active_setting
& MD5_SETTING_ACTIVE
)) {
199 printk("[EEMCS/PLAT] META EXT MD setting not found [%d][%d]\n", args
[0], args
[1]);
202 active_index
= MD_SYS5
- MD_EXT1
;
207 if(md_setting_flag
== MD_LWG_FLAG
){
208 ext_md_support
[active_index
] = modem_lwg
;
209 } else if(md_setting_flag
== MD_LTG_FLAG
){
210 ext_md_support
[active_index
] = modem_ltg
;
212 printk("[EEMCS/PLAT] META EXT MD type:%d\n", ext_md_support
[active_index
]);
218 void get_ext_md_post_fix(int md_id
, char buf
[], char buf_ex
[])
220 // name format: modem_X_YYY_Z_Ex.img
223 #if defined(DFO_FEATURE_EN)
224 unsigned int feature_val
= 0;
227 if (md_id
< MD_SYS5
) {
228 printk("[EEMCS/PLAT] [Error]get_ext_md_post_fix: invalid md_id=%d\n", md_id
);
235 #if defined(DFO_FEATURE_EN)
236 // DFO start -------------------
241 feature_val
= ext_md_support
[MD_SYS5
-MD_EXT1
];
244 printk("[EEMCS/PLAT] [Error]get_ext_md_post_fix: invalid md_id=%d\n", md_id
);
247 switch(feature_val
) {
249 snprintf(YYY
, 8, "_lwg_n");
252 snprintf(YYY
, 8, "_ltg_n");
255 printk("[EEMCS/PLAT] [Error]get_ext_md_post_fix: invalid feature=%d\n", feature_val
);
258 // DFO end ---------------------
260 // Static start -------------------
262 snprintf(YYY
, 8, "_lwg_n");
263 // Static end ---------------------
266 // [_Ex] Get chip version
268 if(get_chip_version() == CHIP_SW_VER_01
)
270 else if(get_chip_version() == CHIP_SW_VER_02
)
278 snprintf(buf
, 12, "%d%s", X
, YYY
);
279 printk("[EEMCS/PLAT] MD%d image postfix=%s\n", md_id
, buf
);
283 snprintf(buf_ex
, 12, "%d%s_E%d", X
, YYY
, Ex
);
284 printk("[EEMCS/PLAT] MD%d image postfix=%s\n", md_id
, buf_ex
);
287 EXPORT_SYMBOL(get_ext_md_post_fix
);
289 unsigned int get_ext_modem_is_enabled(int md_id
)
294 return !!(ext_md_usage_case
& MD5_EN
);
300 EXPORT_SYMBOL(get_ext_modem_is_enabled
);
303 unsigned int get_ext_modem_support(int md_id
){
304 #if defined(DFO_FEATURE_EN)
305 unsigned int feature_val
= 0;
309 feature_val
= ext_md_support
[MD_SYS5
-MD_EXT1
];
312 printk("[EEMCS/PLAT] [Error]get_ext_modem_support: invalid md_id=%d\n", md_id
);
327 EXPORT_SYMBOL(get_ext_modem_support
);
329 unsigned int set_ext_modem_support(int md_id
, int md_type
){
330 #if defined(DFO_FEATURE_EN)
331 printk("[EEMCS/PLAT] set_ext_modem_support MD %d Type %d", md_id
, md_type
);
334 if (md_type
>= modem_lwg
&& md_type
<= modem_ltg
){
335 ext_md_support
[MD_SYS5
-MD_EXT1
] = md_type
;
338 printk("[EEMCS/PLAT] [Error]set_modem_support fail(md:%d, md_type:%d)\n", md_id
, md_type
);
343 printk("[EEMCS/PLAT] [Error]set_modem_support: invalid md_id=%d\n", md_id
);
352 printk("[EEMCS/PLAT] set_ext_modem_support: DFO not support");
360 EXPORT_SYMBOL(set_ext_modem_support
);
362 void get_ap_platform_ver(char * ver
)
364 sprintf(ver
, "MT%04x_S%02x", get_chip_code(), (get_chip_sw_ver_code()&0xFF));
367 EXPORT_SYMBOL(get_ap_platform_ver
);
370 unsigned int get_ext_md_mem_start_addr(int md_id
){
371 unsigned int feature_val
= 0;
375 feature_val
= ext_md_mem_addr
[MD_SYS5
-MD_EXT1
];
378 printk("[EEMCS/PLAT] [Error]get_ext_md_mem_start_addr: invalid md_id=%d\n", md_id
);
384 EXPORT_SYMBOL(get_ext_md_mem_start_addr
);
386 unsigned int get_ext_md_mem_size(int md_id
){
387 unsigned int feature_val
= 0;
391 feature_val
= ext_md_size_list
[MD_SYS5
-MD_EXT1
];
394 printk("[EEMCS/PLAT] [Error]get_ext_md_mem_size: invalid md_id=%d\n", md_id
);
401 EXPORT_SYMBOL(get_ext_md_mem_size
);
404 int eemcs_get_bat_info(unsigned int para
)
407 #if defined (FEATURE_GET_MD_BAT_VOL)
408 val
= (int)BAT_Get_Battery_Voltage(0);
409 printk("[EEMCS/PLAT] get_bat_info : %d \n", val
);
414 EXPORT_SYMBOL(eemcs_get_bat_info
);
417 /*********************************************************************************/
418 /* API about Security cipher MD image */
420 /*********************************************************************************/
421 #ifdef ENABLE_SECURITY_FEATURE
422 #include <mach/mt_sec_export.h>
423 #include <mach/emi_mpu.h>
424 EXPORT_SYMBOL(masp_boot_init
);
425 EXPORT_SYMBOL(masp_ccci_version_info
);
426 EXPORT_SYMBOL(masp_ccci_is_cipherfmt
);
427 EXPORT_SYMBOL(masp_ccci_signfmt_verify_file
);
428 EXPORT_SYMBOL(masp_ccci_decrypt_cipherfmt
);
429 EXPORT_SYMBOL(masp_secro_md_get_data
);
430 EXPORT_SYMBOL(masp_secro_en
);
431 EXPORT_SYMBOL(masp_secro_md_len
);
432 EXPORT_SYMBOL(masp_secro_blk_sz
);
433 EXPORT_SYMBOL(masp_secure_algo_init
);
434 EXPORT_SYMBOL(masp_secure_algo_deinit
);
435 EXPORT_SYMBOL(masp_secure_algo
);
436 /*********************************************************************************/
437 /* API about md ROM/RW/Share memory MPU protection */
439 /*********************************************************************************/
440 int clear_md_region_protection(int md_id
)
442 unsigned int rom_mem_mpu_id
, rw_mem_mpu_id
;
444 printk("[EEMCS/PLAT] Clear MD%d region protect...\n", md_id
+1);
448 rom_mem_mpu_id
= 1; //0;
449 rw_mem_mpu_id
= 2; //1;
453 printk("[EEMCS/PLAT] [Error]clear_md_region_protection: invalid md_id=%d\n", md_id
+1);
457 printk("[EEMCS/PLAT] Clear MPU protect MD%d ROM region<%d>\n", md_id
+1, rom_mem_mpu_id
);
458 emi_mpu_set_region_protection(0, /*START_ADDR*/
460 rom_mem_mpu_id
, /*region*/
461 SET_ACCESS_PERMISSON(NO_PROTECTION
, NO_PROTECTION
, NO_PROTECTION
, NO_PROTECTION
));
463 printk("[EEMCS/PLAT] Clear MPU protect MD%d R/W region<%d>\n", md_id
+1, rw_mem_mpu_id
);
464 emi_mpu_set_region_protection(0, /*START_ADDR*/
466 rw_mem_mpu_id
, /*region*/
467 SET_ACCESS_PERMISSON(NO_PROTECTION
, NO_PROTECTION
, NO_PROTECTION
, NO_PROTECTION
));
471 EXPORT_SYMBOL(clear_md_region_protection
);
474 /***************************************************************************/
475 /* Register ccci call back function when AP receive system channel message */
477 /***************************************************************************/
478 int eemcs_register_sys_msg_notify_func(int md_id
, int (*func
)(int, unsigned int, unsigned int))
481 int ex_md_id
= md_id
- MD_EXT1
;
483 if( ex_md_id
>= MAX_EXT_MD_NUM
) {
484 printk("[EEMCS/PLAT] [Error]register_sys_msg_notify_func: invalid md id(%d)\n", md_id
+1);
488 if(eemcs_sys_msg_notify_func
[ex_md_id
] == NULL
) {
489 eemcs_sys_msg_notify_func
[ex_md_id
] = func
;
491 printk("[EEMCS/PLAT] [Error]eemcs_sys_msg_notify_func: func registered!(%d)\n", md_id
+1);
496 EXPORT_SYMBOL(eemcs_register_sys_msg_notify_func
);
499 int eemcs_notify_md_by_sys_msg(int md_id
, unsigned int msg
, unsigned int data
)
501 int (*func
)(int, unsigned int, unsigned int);
503 int ext_md_id
= md_id
- MD_EXT1
;
505 if(ext_md_id
>= MAX_EXT_MD_NUM
) {
506 printk("[EEMCS/PLAT] [Error]notify_md_by_sys_msg: invalid md id(%d)\n", md_id
+1);
510 func
= eemcs_sys_msg_notify_func
[ext_md_id
];
512 ret
= func(md_id
, msg
, data
);
515 printk("[EEMCS/PLAT] [Error]notify_md_by_sys_msg: func not register!(%d)\n", md_id
+1);
520 EXPORT_SYMBOL(eemcs_notify_md_by_sys_msg
);
523 int eemcs_register_ccci_sys_call_back(int md_id
, unsigned int id
, eemcs_sys_cb_func_t func
)
526 eemcs_sys_cb_func_info_t
*info_ptr
;
527 int ext_md_id
= md_id
- MD_EXT1
;
529 if( ext_md_id
>= MAX_EXT_MD_NUM
) {
530 printk("[EEMCS/PLAT] [Error]register_sys_call_back: invalid md id(%d)\n", md_id
+1);
534 if((id
>= 0x100)&&((id
-0x100) < MAX_KERN_API
)) {
535 info_ptr
= &(eemcs_sys_cb_table_100
[ext_md_id
][id
-0x100]);
536 } else if((id
>= 0x1000)&&((id
-0x1000) < MAX_KERN_API
)) {
537 info_ptr
= &(eemcs_sys_cb_table_1000
[ext_md_id
][id
-0x1000]);
539 printk("[EEMCS/PLAT] [Error]register_sys_call_back: invalid func id(0x%x)\n", id
);
543 if(info_ptr
->func
== NULL
) {
545 info_ptr
->func
= func
;
548 printk("[EEMCS/PLAT] [Error]register_sys_call_back: func(0x%x) registered!\n", id
);
552 EXPORT_SYMBOL(eemcs_register_ccci_sys_call_back
);
555 void eemcs_exec_ccci_sys_call_back(int md_id
, int cb_id
, int data
)
557 eemcs_sys_cb_func_t func
;
559 eemcs_sys_cb_func_info_t
*curr_table
;
560 int ext_md_id
= md_id
- MD_EXT1
;
562 if(ext_md_id
>= MAX_EXT_MD_NUM
) {
563 printk("[EEMCS/PLAT] [Error]exec_sys_cb: invalid md id(%d) \n", md_id
+1);
568 if(id
>= MAX_KERN_API
) {
569 printk("[EEMCS/PLAT] [Error]exec_sys_cb: invalid func id(0x%x)\n", cb_id
);
573 if ((cb_id
& (0x1000|0x100))==0x1000) {
574 curr_table
= eemcs_sys_cb_table_1000
[ext_md_id
];
575 } else if ((cb_id
& (0x1000|0x100))==0x100) {
576 curr_table
= eemcs_sys_cb_table_100
[ext_md_id
];
578 printk("[EEMCS/PLAT] [Error]exec_sys_cb: invalid func id(0x%x)\n", cb_id
);
582 func
= curr_table
[id
].func
;
586 printk("[EEMCS/PLAT] [Error]exec_sys_cb: func id(0x%x) not register!\n", cb_id
);
589 EXPORT_SYMBOL(eemcs_exec_ccci_sys_call_back
);
592 /////////////////////////////////////////////////////////////////////////////////////////////
594 /***************************************************************************/
595 /* Register kernel API for ccci driver invoking */
597 /***************************************************************************/
598 int eemcs_register_ccci_kern_func_by_md_id(int md_id
, unsigned int id
, eemcs_kern_cb_func_t func
)
601 eemcs_kern_func_info
*info_ptr
;
603 if((id
>= MAX_KERN_API
) || (func
== NULL
) || (md_id
>= MAX_EXT_MD_NUM
)) {
604 printk("[EEMCS/PLAT] [Error]register_kern_func: md_id:%d, func_id:%d!\n", md_id
+1, id
);
608 info_ptr
= &(eemcs_func_table
[md_id
][id
]);
609 if(info_ptr
->func
== NULL
) {
611 info_ptr
->func
= func
;
614 printk("[EEMCS/PLAT] [Error]register_kern_func: func(%d) registered!(%d)\n", md_id
+1, id
);
618 EXPORT_SYMBOL(eemcs_register_ccci_kern_func_by_md_id
);
621 int eemcs_register_ccci_kern_func(unsigned int id
, eemcs_kern_cb_func_t func
)
623 return eemcs_register_ccci_kern_func_by_md_id(CURR_EXT_MD_ID
, id
, func
);
625 EXPORT_SYMBOL(eemcs_register_ccci_kern_func
);
628 int eemcs_exec_ccci_kern_func_by_md_id(int md_id
, unsigned int id
, char *buf
, unsigned int len
)
630 eemcs_kern_cb_func_t func
;
633 if(md_id
>= MAX_EXT_MD_NUM
) {
634 printk("[EEMCS/PLAT] [Error]exec kern func: invalid md id(%d)\n", md_id
+1);
638 if(id
>= MAX_KERN_API
) {
639 printk("[EEMCS/PLAT] [Error]exec kern func: invalid func(%d) id(%d)\n", md_id
, id
);
643 func
= eemcs_func_table
[md_id
][id
].func
;
645 ret
= func(md_id
, buf
, len
);
649 if(eemcs_kern_func_err_num
[md_id
][id
] < SHOW_WARNING_NUM
) {
650 eemcs_kern_func_err_num
[md_id
][id
]++;
651 printk("[EEMCS/PLAT] [Error]exec kern func: func%d not register(%d)\n", md_id
+1, id
);
657 EXPORT_SYMBOL(eemcs_exec_ccci_kern_func_by_md_id
);
660 int eemcs_exec_ccci_kern_func(unsigned int id
, char *buf
, unsigned int len
)
662 return eemcs_exec_ccci_kern_func_by_md_id(CURR_EXT_MD_ID
, id
, buf
, len
);
664 EXPORT_SYMBOL(eemcs_exec_ccci_kern_func
);
667 /***************************************************************************/
668 /* Register ccci suspend & resume function */
670 /***************************************************************************/
671 typedef struct eemcs_pm_cb_item
673 void (*cb_func
)(int);
678 static eemcs_pm_cb_item_t eemcs_suspend_cb_table
[MAX_EXT_MD_NUM
][MAX_SLEEP_API
];
679 static eemcs_pm_cb_item_t eemcs_resume_cb_table
[MAX_EXT_MD_NUM
][MAX_SLEEP_API
];
682 void eemcs_register_suspend_notify(int md_id
, unsigned int id
, void (*func
)(int))
684 if((id
>= MAX_SLEEP_API
) || (func
== NULL
) || (md_id
>= MAX_EXT_MD_NUM
)) {
685 printk("[EEMCS/PLAT] [Error]register_suspend_notify: invalid para(md:%d, cmd:%d)\n", md_id
, id
);
688 if (eemcs_suspend_cb_table
[md_id
][id
].cb_func
== NULL
){
689 eemcs_suspend_cb_table
[md_id
][id
].cb_func
= func
;
690 eemcs_suspend_cb_table
[md_id
][id
].md_id
= md_id
;
693 EXPORT_SYMBOL(eemcs_register_suspend_notify
);
696 void eemcs_register_resume_notify(int md_id
, unsigned int id
, void (*func
)(int))
698 if((id
>= MAX_SLEEP_API
) || (func
== NULL
) || (md_id
>= MAX_EXT_MD_NUM
)) {
699 printk("[EEMCS/PLAT] [Error]register_resume_notify: invalid para(md:%d, cmd:%d)\n", md_id
, id
);
702 if (eemcs_resume_cb_table
[md_id
][id
].cb_func
== NULL
){
703 eemcs_resume_cb_table
[md_id
][id
].cb_func
= func
;
704 eemcs_resume_cb_table
[md_id
][id
].md_id
= md_id
;
707 EXPORT_SYMBOL(eemcs_register_resume_notify
);
710 static int eemcs_helper_probe(struct platform_device
*dev
)
713 //printk( "\neemcs_helper_probe\n" );
717 static int eemcs_helper_remove(struct platform_device
*dev
)
719 //printk( "\neemcs_helper_remove\n" );
723 static void eemcs_helper_shutdown(struct platform_device
*dev
)
725 //printk( "\neemcs_helper_shutdown\n" );
728 static int eemcs_helper_suspend(struct platform_device
*dev
, pm_message_t state
)
734 printk( "\neemcs_helper_suspend\n" );
736 for (i
= 0; i
< MAX_EXT_MD_NUM
; i
++) {
737 for (j
= 0; j
< EEMCS_SLP_ID_MAX
; j
++) {
738 func
= eemcs_suspend_cb_table
[i
][j
].cb_func
;
739 md_id
= eemcs_suspend_cb_table
[i
][j
].md_id
;
748 static int eemcs_helper_resume(struct platform_device
*dev
)
754 printk( "\neemcs_helper_resume\n" );
756 for (i
= 0; i
< MAX_EXT_MD_NUM
; i
++) {
757 for (j
= 0; j
< EEMCS_RSM_ID_MAX
; j
++) {
758 func
= eemcs_resume_cb_table
[i
][j
].cb_func
;
759 md_id
= eemcs_resume_cb_table
[i
][j
].md_id
;
768 //*-------------------------------------------------------------*//
769 #if defined (CONFIG_PM) && defined (FEATURE_PM_IPO_H)
770 int eemcs_helper_pm_suspend(struct device
*device
)
772 //pr_debug("calling %s()\n", __func__);
774 struct platform_device
*pdev
= to_platform_device(device
);
775 BUG_ON(pdev
== NULL
);
777 return eemcs_helper_suspend(pdev
, PMSG_SUSPEND
);
780 int eemcs_helper_pm_resume(struct device
*device
)
782 //pr_debug("calling %s()\n", __func__);
784 struct platform_device
*pdev
= to_platform_device(device
);
785 BUG_ON(pdev
== NULL
);
787 return eemcs_helper_resume(pdev
);
790 extern void mt_irq_set_sens(unsigned int irq
, unsigned int sens
);
791 extern void mt_irq_set_polarity(unsigned int irq
, unsigned int polarity
);
792 int eemcs_helper_pm_restore_noirq(struct device
*device
)
794 pr_debug("calling %s()\n", __func__
);
795 /*Not ready, need to check more details*/
798 mt_irq_set_sens(CCIF0_AP_IRQ_ID
, MT_LEVEL_SENSITIVE
);
799 mt_irq_set_polarity(CCIF0_AP_IRQ_ID
, MT_POLARITY_LOW
);
802 mt_irq_set_sens(MD_WDT_IRQ_ID
, MT_EDGE_SENSITIVE
);
803 mt_irq_set_polarity(MD_WDT_IRQ_ID
, MT_POLARITY_LOW
);
806 exec_ccci_kern_func_by_md_id(0, ID_IPO_H_RESTORE_CB
, NULL
, 0);
814 #define eemcs_helper_pm_suspend NULL
815 #define eemcs_helper_pm_resume NULL
816 #define eemcs_helper_pm_restore_noirq NULL
819 //*-------------------------------------------------------------*//
821 struct dev_pm_ops eemcs_helper_pm_ops
= {
822 .suspend
= eemcs_helper_pm_suspend
,
823 .resume
= eemcs_helper_pm_resume
,
824 .freeze
= eemcs_helper_pm_suspend
,
825 .thaw
= eemcs_helper_pm_resume
,
826 .poweroff
= eemcs_helper_pm_suspend
,
827 .restore
= eemcs_helper_pm_resume
,
828 .restore_noirq
= eemcs_helper_pm_restore_noirq
,
831 static struct platform_driver eemcs_helper_driver
=
834 .name
= "eemcs-helper",
836 .pm
= &eemcs_helper_pm_ops
,
839 .probe
= eemcs_helper_probe
,
840 .remove
= eemcs_helper_remove
,
841 .shutdown
= eemcs_helper_shutdown
,
842 .suspend
= eemcs_helper_suspend
,
843 .resume
= eemcs_helper_resume
,
846 struct platform_device eemcs_helper_device
= {
847 .name
= "eemcs-helper",
852 static int __init
eemcs_helper_init(void)
857 /* Not ready, need check*/
859 // Init ccci helper sys fs
860 memset( (void*)cmd_map_table
, 0, sizeof(cmd_map_table
) );
863 // init ccci kernel API register table
864 memset((void*)eemcs_func_table
, 0, sizeof(eemcs_func_table
));
865 memset((void*)eemcs_kern_func_err_num
, 0, sizeof(eemcs_kern_func_err_num
));
867 // init ccci system channel call back function register table
868 memset((void*)eemcs_sys_cb_table_100
, 0, sizeof(eemcs_sys_cb_table_100
));
869 memset((void*)eemcs_sys_cb_table_1000
, 0, sizeof(eemcs_sys_cb_table_1000
));
871 ret
= platform_device_register(&eemcs_helper_device
);
873 printk("[EEMCS/PLAT] [Error]eemcs_helper_device register fail: %d\n", ret
);
877 ret
= platform_driver_register(&eemcs_helper_driver
);
879 printk("[EEMCS/PLAT] [Error]eemcs_helper_driver register fail: %d\n", ret
);
886 module_init(eemcs_helper_init
);
888 MODULE_LICENSE("GPL");
889 MODULE_AUTHOR("MTK");
890 MODULE_DESCRIPTION("The eemcs helper function");
891 /////////////////////////////////////////////////////////////////////////////////////////////