From 884a116a325886ed6474a5d608a67892427aa8ea Mon Sep 17 00:00:00 2001 From: CMY Date: Tue, 22 May 2012 23:12:33 +0800 Subject: [PATCH] Enable bluetooth auto sleep function --- arch/arm/configs/rk30_sdk_defconfig | 1 + arch/arm/mach-rk29/board-rk29sdk-rfkill.c | 47 ++++++++++++++-------- arch/arm/mach-rk30/board-rk30-sdk-rfkill.c | 47 ++++++++++++++-------- drivers/bluetooth/Kconfig | 7 ++++ drivers/bluetooth/hci_h4.c | 6 --- drivers/bluetooth/hci_ldisc.c | 4 +- 6 files changed, 72 insertions(+), 40 deletions(-) diff --git a/arch/arm/configs/rk30_sdk_defconfig b/arch/arm/configs/rk30_sdk_defconfig index 485b879e8f66..b892d134c5f7 100644 --- a/arch/arm/configs/rk30_sdk_defconfig +++ b/arch/arm/configs/rk30_sdk_defconfig @@ -175,6 +175,7 @@ CONFIG_BT_HCIUART=y CONFIG_BT_HCIUART_H4=y CONFIG_BT_HCIUART_LL=y CONFIG_BT_HCIBCM4325=y +CONFIG_BT_AUTOSLEEP=y CONFIG_RFKILL=y CONFIG_DEVTMPFS=y CONFIG_DEVTMPFS_MOUNT=y diff --git a/arch/arm/mach-rk29/board-rk29sdk-rfkill.c b/arch/arm/mach-rk29/board-rk29sdk-rfkill.c index 30909abbd3ad..d6bd1eed0868 100755 --- a/arch/arm/mach-rk29/board-rk29sdk-rfkill.c +++ b/arch/arm/mach-rk29/board-rk29sdk-rfkill.c @@ -40,6 +40,8 @@ #define BT_WAKE_LOCK_TIMEOUT 10 //s +#define BT_AUTO_SLEEP_TIMEOUT 3 + /* * IO Configuration for RK29 */ @@ -132,6 +134,8 @@ extern int rk29sdk_wifi_power_state; #endif struct bt_ctrl gBtCtrl; +struct timer_list bt_sleep_tl; + #if BT_WAKE_HOST_SUPPORT void resetBtHostSleepTimer(void) @@ -163,7 +167,7 @@ static void timer_hostSleep(unsigned long arg) btWakeupHostUnlock(); } -extern int bcm4325_sleep(int bSleep); +void bcm4325_sleep(unsigned long bSleep); #ifdef CONFIG_PM static void rfkill_do_wakeup(struct work_struct *work) @@ -179,7 +183,7 @@ static int bcm4329_rfkill_suspend(struct platform_device *pdev, pm_message_t sta { DBG("%s\n",__FUNCTION__); -#ifdef CONFIG_BT_HCIBCM4325 +#ifdef CONFIG_BT_AUTOSLEEP bcm4325_sleep(1); #endif @@ -191,7 +195,6 @@ static int bcm4329_rfkill_suspend(struct platform_device *pdev, pm_message_t sta #ifdef CONFIG_RFKILL_RESET extern void rfkill_set_block(struct rfkill *rfkill, bool blocked); - printk("rfkill_set_block\n"); rfkill_set_block(gBtCtrl.bt_rfk, true); #endif @@ -202,10 +205,6 @@ static int bcm4329_rfkill_resume(struct platform_device *pdev) { DBG("%s\n",__FUNCTION__); -#ifdef CONFIG_BT_HCIBCM4325 - bcm4325_sleep(0); -#endif - DBG("delay 1s\n"); schedule_delayed_work(&wakeup_work, HZ); @@ -226,16 +225,22 @@ static irqreturn_t bcm4329_wake_host_irq(int irq, void *dev) } #endif -int bcm4325_sleep(int bSleep) +void bcm4325_sleep(unsigned long bSleep) { - DBG("************* bt enter sleep: %d ***************\n", bSleep); - //low represent bt device may enter sleep - //high represent bt device must be awake + DBG("*** bt sleep: %d ***\n", bSleep); +#ifdef CONFIG_BT_AUTOSLEEP + del_timer(&bt_sleep_tl);// cmy: È·±£ÔÚ»½ÐÑBTʱ£¬²»»áÒò´¥·¢bt_sleep_tl¶øÂíÉÏ˯Ãß +#endif + IOMUX_BT_GPIO_WAKE_UP(); gpio_set_value(BT_GPIO_WAKE_UP, bSleep?GPIO_LOW:GPIO_HIGH); - return 0; + +#ifdef CONFIG_BT_AUTOSLEEP + if(!bSleep) + mod_timer(&bt_sleep_tl, jiffies + BT_AUTO_SLEEP_TIMEOUT*HZ);//ÔÙÖØÐÂÉèÖó¬Ê±Öµ¡£ +#endif } - + static int bcm4329_set_block(void *data, bool blocked) { DBG("%s---blocked :%d\n", __FUNCTION__, blocked); @@ -315,8 +320,14 @@ static int __devinit bcm4329_rfkill_probe(struct platform_device *pdev) gpio_request(BT_GPIO_POWER, NULL); gpio_request(BT_GPIO_RESET, NULL); -#ifdef CONFIG_BT_HCIBCM4325 gpio_request(BT_GPIO_WAKE_UP, NULL); + +#ifdef CONFIG_BT_AUTOSLEEP + init_timer(&bt_sleep_tl); + bt_sleep_tl.expires = 0; + bt_sleep_tl.function = bcm4325_sleep; + bt_sleep_tl.data = 1; + add_timer(&bt_sleep_tl); #endif #if BT_WAKE_HOST_SUPPORT @@ -355,11 +366,15 @@ static int __devexit bcm4329_rfkill_remove(struct platform_device *pdev) if (gBtCtrl.bt_rfk) rfkill_unregister(gBtCtrl.bt_rfk); gBtCtrl.bt_rfk = NULL; -#if BT_WAKE_HOST_SUPPORT +#if BT_WAKE_HOST_SUPPORT del_timer(&(gBtCtrl.tl));//ɾµô¶¨Ê±Æ÷ btWakeupHostUnlock(); wake_lock_destroy(&(gBtCtrl.bt_wakelock)); -#endif +#endif +#ifdef CONFIG_BT_AUTOSLEEP + del_timer(&bt_sleep_tl); +#endif + platform_set_drvdata(pdev, NULL); DBG("Enter::%s,line=%d\n",__FUNCTION__,__LINE__); diff --git a/arch/arm/mach-rk30/board-rk30-sdk-rfkill.c b/arch/arm/mach-rk30/board-rk30-sdk-rfkill.c index 30909abbd3ad..d6bd1eed0868 100755 --- a/arch/arm/mach-rk30/board-rk30-sdk-rfkill.c +++ b/arch/arm/mach-rk30/board-rk30-sdk-rfkill.c @@ -40,6 +40,8 @@ #define BT_WAKE_LOCK_TIMEOUT 10 //s +#define BT_AUTO_SLEEP_TIMEOUT 3 + /* * IO Configuration for RK29 */ @@ -132,6 +134,8 @@ extern int rk29sdk_wifi_power_state; #endif struct bt_ctrl gBtCtrl; +struct timer_list bt_sleep_tl; + #if BT_WAKE_HOST_SUPPORT void resetBtHostSleepTimer(void) @@ -163,7 +167,7 @@ static void timer_hostSleep(unsigned long arg) btWakeupHostUnlock(); } -extern int bcm4325_sleep(int bSleep); +void bcm4325_sleep(unsigned long bSleep); #ifdef CONFIG_PM static void rfkill_do_wakeup(struct work_struct *work) @@ -179,7 +183,7 @@ static int bcm4329_rfkill_suspend(struct platform_device *pdev, pm_message_t sta { DBG("%s\n",__FUNCTION__); -#ifdef CONFIG_BT_HCIBCM4325 +#ifdef CONFIG_BT_AUTOSLEEP bcm4325_sleep(1); #endif @@ -191,7 +195,6 @@ static int bcm4329_rfkill_suspend(struct platform_device *pdev, pm_message_t sta #ifdef CONFIG_RFKILL_RESET extern void rfkill_set_block(struct rfkill *rfkill, bool blocked); - printk("rfkill_set_block\n"); rfkill_set_block(gBtCtrl.bt_rfk, true); #endif @@ -202,10 +205,6 @@ static int bcm4329_rfkill_resume(struct platform_device *pdev) { DBG("%s\n",__FUNCTION__); -#ifdef CONFIG_BT_HCIBCM4325 - bcm4325_sleep(0); -#endif - DBG("delay 1s\n"); schedule_delayed_work(&wakeup_work, HZ); @@ -226,16 +225,22 @@ static irqreturn_t bcm4329_wake_host_irq(int irq, void *dev) } #endif -int bcm4325_sleep(int bSleep) +void bcm4325_sleep(unsigned long bSleep) { - DBG("************* bt enter sleep: %d ***************\n", bSleep); - //low represent bt device may enter sleep - //high represent bt device must be awake + DBG("*** bt sleep: %d ***\n", bSleep); +#ifdef CONFIG_BT_AUTOSLEEP + del_timer(&bt_sleep_tl);// cmy: È·±£ÔÚ»½ÐÑBTʱ£¬²»»áÒò´¥·¢bt_sleep_tl¶øÂíÉÏ˯Ãß +#endif + IOMUX_BT_GPIO_WAKE_UP(); gpio_set_value(BT_GPIO_WAKE_UP, bSleep?GPIO_LOW:GPIO_HIGH); - return 0; + +#ifdef CONFIG_BT_AUTOSLEEP + if(!bSleep) + mod_timer(&bt_sleep_tl, jiffies + BT_AUTO_SLEEP_TIMEOUT*HZ);//ÔÙÖØÐÂÉèÖó¬Ê±Öµ¡£ +#endif } - + static int bcm4329_set_block(void *data, bool blocked) { DBG("%s---blocked :%d\n", __FUNCTION__, blocked); @@ -315,8 +320,14 @@ static int __devinit bcm4329_rfkill_probe(struct platform_device *pdev) gpio_request(BT_GPIO_POWER, NULL); gpio_request(BT_GPIO_RESET, NULL); -#ifdef CONFIG_BT_HCIBCM4325 gpio_request(BT_GPIO_WAKE_UP, NULL); + +#ifdef CONFIG_BT_AUTOSLEEP + init_timer(&bt_sleep_tl); + bt_sleep_tl.expires = 0; + bt_sleep_tl.function = bcm4325_sleep; + bt_sleep_tl.data = 1; + add_timer(&bt_sleep_tl); #endif #if BT_WAKE_HOST_SUPPORT @@ -355,11 +366,15 @@ static int __devexit bcm4329_rfkill_remove(struct platform_device *pdev) if (gBtCtrl.bt_rfk) rfkill_unregister(gBtCtrl.bt_rfk); gBtCtrl.bt_rfk = NULL; -#if BT_WAKE_HOST_SUPPORT +#if BT_WAKE_HOST_SUPPORT del_timer(&(gBtCtrl.tl));//ɾµô¶¨Ê±Æ÷ btWakeupHostUnlock(); wake_lock_destroy(&(gBtCtrl.bt_wakelock)); -#endif +#endif +#ifdef CONFIG_BT_AUTOSLEEP + del_timer(&bt_sleep_tl); +#endif + platform_set_drvdata(pdev, NULL); DBG("Enter::%s,line=%d\n",__FUNCTION__,__LINE__); diff --git a/drivers/bluetooth/Kconfig b/drivers/bluetooth/Kconfig index a71eac1486f7..fdc472b7b2ab 100755 --- a/drivers/bluetooth/Kconfig +++ b/drivers/bluetooth/Kconfig @@ -228,6 +228,13 @@ config WIFI_MAC endchoice endif +config BT_AUTOSLEEP + tristate "Bluetooth auto sleep" + depends on BT_HCIUART + help + If the Bluetooth have no data transfer within three seconds, then + it will automatically go to sleep until the arrival of new data + config BT_ATH3K tristate "Atheros firmware download driver" depends on BT_HCIBTUSB diff --git a/drivers/bluetooth/hci_h4.c b/drivers/bluetooth/hci_h4.c index 74be11df7833..b677cfea0696 100755 --- a/drivers/bluetooth/hci_h4.c +++ b/drivers/bluetooth/hci_h4.c @@ -62,9 +62,6 @@ struct h4_struct { #define H4_W4_SCO_HDR 3 #define H4_W4_DATA 4 -#ifdef CONFIG_BT_HCIBCM4325 -extern int bcm4325_sleep(int bSleep); -#endif /* Initialize protocol */ static int h4_open(struct hci_uart *hu) @@ -144,9 +141,6 @@ static inline int h4_check_data_len(struct h4_struct *h4, int len) h4->rx_count = len; return len; } -#ifdef CONFIG_BT_HCIBCM4325 - bcm4325_sleep(1); -#endif h4->rx_state = H4_W4_PACKET_TYPE; h4->rx_skb = NULL; h4->rx_count = 0; diff --git a/drivers/bluetooth/hci_ldisc.c b/drivers/bluetooth/hci_ldisc.c index 22c0cca19a75..18df94586dbd 100755 --- a/drivers/bluetooth/hci_ldisc.c +++ b/drivers/bluetooth/hci_ldisc.c @@ -46,7 +46,7 @@ #include "hci_uart.h" -#ifdef CONFIG_BT_HCIBCM4325 +#ifdef CONFIG_BT_AUTOSLEEP extern int bcm4325_sleep(int bSleep); #endif @@ -138,7 +138,7 @@ int hci_uart_tx_wakeup(struct hci_uart *hu) restart: clear_bit(HCI_UART_TX_WAKEUP, &hu->tx_state); /*added by Barry,for broadcom 4325*/ -#ifdef CONFIG_BT_HCIBCM4325 +#ifdef CONFIG_BT_AUTOSLEEP bcm4325_sleep(0); #endif while ((skb = hci_uart_dequeue(hu))) { -- 2.34.1