summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDilip Kota <c_dkota@codeaurora.org>2014-01-28 21:42:01 +0530
committerKiran Gunda <kgunda@codeaurora.org>2014-02-25 14:24:01 +0530
commit3876b63f58338c5f1cc1caf4deb747eaac67ea16 (patch)
treeb91a304e0125cd56571fd69287ae0fc5a81f34fd
parent22f171b17bc4a29941b0a432998480f7598ffade (diff)
msm_serial_hs: Manage wake unlock delay
Current implementation of wake locks wait for around 500msec while releasing the wakelock. This prevents the system suspend for that much time after the rx operation is done to ensure that all the data delivered to the client before system suspend. But some clients may take care of this in their implementation. In this case uart driver no need to wait before releasing the wakelock. Hence, given the control to the client as a dtsi entry to take decision on waiting before releasing the wakelock. Change-Id: Ie32a0b76899963e7700ba378906fa4f9b3fa3ba4 Signed-off-by: Kiran Gunda <kgunda@codeaurora.org> Signed-off-by: Dilip Kota <c_dkota@codeaurora.org>
-rw-r--r--Documentation/devicetree/bindings/tty/serial/msm_serial_hs.txt3
-rw-r--r--arch/arm/mach-msm/include/mach/msm_serial_hs.h5
-rw-r--r--drivers/tty/serial/msm_serial_hs.c26
3 files changed, 29 insertions, 5 deletions
diff --git a/Documentation/devicetree/bindings/tty/serial/msm_serial_hs.txt b/Documentation/devicetree/bindings/tty/serial/msm_serial_hs.txt
index 762d40f673e8..031be45f81b8 100644
--- a/Documentation/devicetree/bindings/tty/serial/msm_serial_hs.txt
+++ b/Documentation/devicetree/bindings/tty/serial/msm_serial_hs.txt
@@ -64,6 +64,9 @@ for uart.
receiving interrupt with UART RX GPIO IRQ line (i.e. above wakeup_irq property),
HSUART driver injects provided character with property rx_to_inject.
- qcom, rx-char-to-inject : The character to be inserted on wakeup.
+- qcom, no-suspend-delay : This decides system to go to suspend immediately
+or not
+
- Refer to "Documentation/devicetree/bindings/arm/msm/msm_bus.txt" for
below optional properties:
- qcom,msm_bus,name
diff --git a/arch/arm/mach-msm/include/mach/msm_serial_hs.h b/arch/arm/mach-msm/include/mach/msm_serial_hs.h
index e6b677e7fa1a..edc85ba3edd8 100644
--- a/arch/arm/mach-msm/include/mach/msm_serial_hs.h
+++ b/arch/arm/mach-msm/include/mach/msm_serial_hs.h
@@ -1,6 +1,6 @@
/*
* Copyright (C) 2008 Google, Inc.
- * Copyright (C) 2010-2013, The Linux Foundation. All rights reserved.
+ * Copyright (C) 2010-2014, The Linux Foundation. All rights reserved.
* Author: Nick Pelly <npelly@google.com>
*
* This software is licensed under the terms of the GNU General Public
@@ -32,6 +32,8 @@
* @uart_rfr_gpio: GPIO number for UART RFR Line.
* @bam_tx_ep_pipe_index : BAM TX Endpoint Pipe Index for HSUART
* @bam_tx_ep_pipe_index : BAM RX Endpoint Pipe Index for HSUART
+ * @no_suspend_delay : Flag used to make system go to suspend
+ * immediately or not
*/
struct msm_serial_hs_platform_data {
int wakeup_irq; /* wakeup irq */
@@ -46,6 +48,7 @@ struct msm_serial_hs_platform_data {
int uart_rfr_gpio;
unsigned bam_tx_ep_pipe_index;
unsigned bam_rx_ep_pipe_index;
+ bool no_suspend_delay;
};
unsigned int msm_hs_tx_empty(struct uart_port *uport);
diff --git a/drivers/tty/serial/msm_serial_hs.c b/drivers/tty/serial/msm_serial_hs.c
index e486d727e5cc..5b2ef9ae9ee3 100644
--- a/drivers/tty/serial/msm_serial_hs.c
+++ b/drivers/tty/serial/msm_serial_hs.c
@@ -1348,15 +1348,22 @@ static void hsuart_disconnect_rx_endpoint_work(struct work_struct *w)
{
struct msm_hs_port *msm_uport = container_of(w, struct msm_hs_port,
disconnect_rx_endpoint);
+ struct uart_port *uport = &msm_uport->uport;
struct msm_hs_rx *rx = &msm_uport->rx;
struct sps_pipe *sps_pipe_handle = rx->prod.pipe_handle;
+ struct platform_device *pdev = to_platform_device(uport->dev);
+ const struct msm_serial_hs_platform_data *pdata =
+ pdev->dev.platform_data;
int ret = 0;
ret = sps_rx_disconnect(sps_pipe_handle);
if (ret)
MSM_HS_ERR("%s(): sps_disconnect failed\n", __func__);
-
- wake_lock_timeout(&msm_uport->rx.wake_lock, HZ / 2);
+ if (pdata->no_suspend_delay)
+ wake_unlock(&msm_uport->rx.wake_lock);
+ else
+ wake_lock_timeout(&msm_uport->rx.wake_lock,
+ HZ / 2);
msm_uport->rx.flush = FLUSH_SHUTDOWN;
MSM_HS_DBG("%s: Calling Completion\n", __func__);
wake_up(&msm_uport->bam_disconnect_wait);
@@ -1633,6 +1640,8 @@ static void msm_serial_hs_rx_tlet(unsigned long tlet_ptr)
struct msm_hs_rx *rx;
struct sps_pipe *sps_pipe_handle;
u32 sps_flags = SPS_IOVEC_FLAG_INT;
+ struct platform_device *pdev;
+ const struct msm_serial_hs_platform_data *pdata;
msm_uport = container_of((struct tasklet_struct *)tlet_ptr,
struct msm_hs_port, rx.tlet);
@@ -1640,6 +1649,8 @@ static void msm_serial_hs_rx_tlet(unsigned long tlet_ptr)
tty = uport->state->port.tty;
notify = &msm_uport->notify;
rx = &msm_uport->rx;
+ pdev = to_platform_device(uport->dev);
+ pdata = pdev->dev.platform_data;
msm_uport->rx.rx_cmd_queued = false;
msm_uport->rx.rx_cmd_exec = false;
@@ -1752,8 +1763,12 @@ out:
, msecs_to_jiffies(RETRY_TIMEOUT));
}
/* release wakelock in 500ms, not immediately, because higher layers
- * don't always take wakelocks when they should */
- wake_lock_timeout(&msm_uport->rx.wake_lock, HZ / 2);
+ * don't always take wakelocks when they should
+ */
+ if (pdata->no_suspend_delay)
+ wake_unlock(&msm_uport->rx.wake_lock);
+ else
+ wake_lock_timeout(&msm_uport->rx.wake_lock, HZ / 2);
/* tty_flip_buffer_push() might call msm_hs_start(), so unlock */
spin_unlock_irqrestore(&uport->lock, flags);
if (flush < FLUSH_DATA_INVALID)
@@ -2972,6 +2987,9 @@ struct msm_serial_hs_platform_data
if (pdata->uart_rfr_gpio < 0)
MSM_HS_DBG("uart_rfr_gpio is not available\n");
+ pdata->no_suspend_delay = of_property_read_bool(node,
+ "qcom,no-suspend-delay");
+
pdata->inject_rx_on_wakeup = of_property_read_bool(node,
"qcom,inject-rx-on-wakeup");