static void timer_work(struct work_struct *work) { struct sec_keyboard_drvdata *data = container_of(work, struct sec_keyboard_drvdata, work_timer); int error; if (UNKOWN_KEYLAYOUT == data->kl) { data->acc_power(1, false); data->pre_connected = false; /* Set baud rate for the keyboard uart */ error = change_console_baud_rate(115200); if (error < 0) printk(KERN_ERR "[Keyboard] Couldn't modify the baud rate.\n"); if (data->check_uart_path) data->check_uart_path(false); } }
int check_keyboard_dock(void) { static bool dockconnected = false; static bool pre_connected =false; static bool pre_uart_path =false; static bool first_connection =true; static unsigned long disconnected_time=0; int try_cnt = 0; int error = 0; int max_cnt = 10; if(gpio_get_value(g_data->gpio)) { dockconnected = false; } else { /*Do not use the keyboard in this version. * Because of the issue with the USB otg. */ #if defined (CONFIG_TARGET_LOCALE_EUR) || defined (CONFIG_TARGET_LOCALE_HKTW) || defined (CONFIG_TARGET_LOCALE_HKTW_FET) if(HWREV == 0x10||HWREV == 0x11) #elif defined (CONFIG_TARGET_LOCALE_KOR) if(HWREV < 0xf) // It works only on Rev 13 or later. #elif defined (CONFIG_TARGET_LOCALE_USAGSM) if(HWREV < 0x10) #else if(HWREV >= 0xff) #endif { return 0; } pre_connected = true; /*for checking handshake*/ connected_time = jiffies_to_msecs(jiffies); /* check the keyboard is connected durring the boot*/ if(first_connection) { if((connected_time - boot_time) <= 2000) { max_cnt = 30; printk(KERN_DEBUG "[Keyboard] ACCESSORY is connected durring the boot.\n"); } first_connection = false; } else if((connected_time - disconnected_time) < 1000) { g_data->kl = pre_kl; // dockconnected = true; printk(KERN_DEBUG "[Keyboard] kl : %d\n", pre_kl); } else { pre_kl = UNKOWN_KEYLAYOUT; } if(!keyboard_enable) { s3c_gpio_cfgpin(ACCESSORY_EN, S3C_GPIO_OUTPUT); s3c_gpio_setpull(ACCESSORY_EN, S3C_GPIO_PULL_UP); gpio_set_value(ACCESSORY_EN, 1); keyboard_enable = true; } /* if the uart is set as cp path, the path should be switched to ap path.*/ pre_uart_path = gpio_get_value(GPIO_UART_SEL); if(!pre_uart_path) { gpio_set_value(GPIO_UART_SEL, 1); printk(KERN_DEBUG "[Keyboard] console uart path is switched to AP.\n"); } /* Set baud rate for the keyboard uart */ error = change_console_baud_rate(9600); if(error<0) { printk(KERN_ERR "[Keyboard] Couldn't modify the baud rate.\n"); } if(!dockconnected) { /* try to get handshake data */ for(try_cnt=0; try_cnt<max_cnt; try_cnt++) { msleep(100); if(g_data->kl != UNKOWN_KEYLAYOUT) { dockconnected = true; break; } /* the accessory is dettached. */ if(gpio_get_value(g_data->gpio)) { dockconnected = false; break; } } } } if(dockconnected) { // if the led is on, the led should be off. g_data->led_on= false; if (!work_pending(&g_data->work_led)) { schedule_work(&g_data->work_led); } return 1; } else { if(pre_connected) { error = change_console_baud_rate(115200); if(error<0) { printk(KERN_ERR "[Keyboard] Couldn't modify the baud rate.\n"); } dockconnected = false; gpio_set_value(GPIO_UART_SEL, pre_uart_path); mod_timer(&g_data->timer, jiffies + HZ); g_data->kl = UNKOWN_KEYLAYOUT; pre_connected = false; handshaking = false; disconnected_time = jiffies_to_msecs(jiffies); release_all_keys(); } return 0; } }
static int check_keyboard_dock(struct sec_keyboard_callbacks *cb, bool val) { struct sec_keyboard_drvdata *data = container_of(cb, struct sec_keyboard_drvdata, callbacks); int try_cnt = 0; int error = 0; int max_cnt = 14; if (!val) data->dockconnected = false; else { del_timer(&data->timer); /* wakeup by keyboard dock */ if (data->pre_connected) { if (UNKOWN_KEYLAYOUT != data->pre_kl) { data->kl = data->pre_kl; data->acc_power(1, true); pr_info("[Keyboard] kl : %d\n", data->pre_kl); return 1; } } else data->pre_kl = UNKOWN_KEYLAYOUT; data->pre_connected = true; /* to prevent the over current issue */ data->acc_power(0, false); if (data->check_uart_path) data->check_uart_path(true); /* Set baud rate for the keyboard uart */ error = change_console_baud_rate(9600); if (error < 0) pr_err("[Keyboard] Couldn't modify the baud rate.\n"); msleep(200); data->acc_power(1, true); /* try to get handshake data */ for (try_cnt = 0; try_cnt < max_cnt; try_cnt++) { msleep(50); if (data->kl != UNKOWN_KEYLAYOUT) { data->dockconnected = true; break; } if (gpio_get_value(data->acc_int_gpio)) { pr_info("[Keyboard] acc is disconnected.\n"); break; } } } if (data->dockconnected) return 1; else { if (data->pre_connected) { /* stop the thread and clear the buffer*/ data->buf_front = data->buf_rear = 0; data->dockconnected = false; mod_timer(&data->timer, jiffies + HZ/2); data->kl = UNKOWN_KEYLAYOUT; release_all_keys(data); } return 0; } }
int check_keyboard_dock(void) { static bool dockconnected = false; static bool pre_connected =false; static bool pre_uart_path =false; static unsigned long disconnected_time=0; int try_cnt = 0; int error = 0; int max_cnt = 10; if(gpio_get_value(g_data->gpio)) { dockconnected = false; } else { pre_connected = true; /*for checking handshake*/ connected_time = jiffies; if((connected_time - disconnected_time) < HZ) { g_data->kl = pre_kl; // dockconnected = true; printk(KERN_DEBUG "[Keyboard] kl : %d\n", pre_kl); } else { pre_kl = UNKOWN_KEYLAYOUT; } set_uart_suspend(0); /* if the uart is set as cp path, the path should be switched to ap path.*/ pre_uart_path = gpio_get_value(OMAP_GPIO_UART_SEL); if(!pre_uart_path) { gpio_set_value(OMAP_GPIO_UART_SEL, 1); printk(KERN_DEBUG "[Keyboard] console uart path is switched to AP.\n"); } /* Set baud rate for the keyboard uart */ error = change_console_baud_rate(9600); if(error<0) { printk(KERN_ERR "[Keyboard] Couldn't modify the baud rate.\n"); goto con_err; } if(!keyboard_enable) { printk("[Keyboard] check_keyboard_dock 6"); gpio_set_value(en_gpio, 1); keyboard_enable = true; } if(!dockconnected) { /* try to get handshake data */ for(try_cnt=0; try_cnt<max_cnt; try_cnt++) { msleep(100); if(g_data->kl != UNKOWN_KEYLAYOUT) { dockconnected = true; break; } /* the accessory is dettached. */ if(gpio_get_value(g_data->gpio)) { dockconnected = false; break; } } } } if(dockconnected) { // if the led is on, the led should be off. g_data->led_on= false; if (!work_pending(&g_data->work_led)) { schedule_work(&g_data->work_led); } return 1; } else { if(pre_connected) { gpio_set_value(en_gpio, 0); keyboard_enable = false; error = change_console_baud_rate(115200); if(error<0) { printk(KERN_ERR "[Keyboard] Couldn't modify the baud rate.\n"); } con_err: dockconnected = false; gpio_set_value(OMAP_GPIO_UART_SEL, pre_uart_path); g_data->kl = UNKOWN_KEYLAYOUT; pre_connected = false; handshaking = false; disconnected_time = jiffies; release_all_keys(); } set_uart_suspend(1); return 0; } }