Merge "msm: ipa: ipa_tx_dp issued after suspend"
diff --git a/drivers/platform/msm/ipa/ipa_clients/ipa_gsb.c b/drivers/platform/msm/ipa/ipa_clients/ipa_gsb.c
index 54e82f3a..bc04ed4 100644
--- a/drivers/platform/msm/ipa/ipa_clients/ipa_gsb.c
+++ b/drivers/platform/msm/ipa/ipa_clients/ipa_gsb.c
@@ -161,6 +161,7 @@
 	spinlock_t iface_spinlock[MAX_SUPPORTED_IFACE];
 	u32 pm_hdl;
 	atomic_t disconnect_in_progress;
+	atomic_t suspend_in_progress;
 };
 
 static struct ipa_gsb_context *ipa_gsb_ctx;
@@ -1070,20 +1071,24 @@
 	IPA_GSB_DBG_LOW("client hdl: %d\n", hdl);
 
 	mutex_lock(&ipa_gsb_ctx->iface_lock[hdl]);
+	atomic_set(&ipa_gsb_ctx->suspend_in_progress, 1);
 	if (!ipa_gsb_ctx->iface[hdl]) {
 		IPA_GSB_ERR("fail to find interface, hdl: %d\n", hdl);
+		atomic_set(&ipa_gsb_ctx->suspend_in_progress, 0);
 		mutex_unlock(&ipa_gsb_ctx->iface_lock[hdl]);
 		return -EFAULT;
 	}
 
 	if (!ipa_gsb_ctx->iface[hdl]->is_connected) {
 		IPA_GSB_ERR("iface is not connected\n");
+		atomic_set(&ipa_gsb_ctx->suspend_in_progress, 0);
 		mutex_unlock(&ipa_gsb_ctx->iface_lock[hdl]);
 		return -EFAULT;
 	}
 
 	if (!ipa_gsb_ctx->iface[hdl]->is_resumed) {
 		IPA_GSB_DBG_LOW("iface was already suspended\n");
+		atomic_set(&ipa_gsb_ctx->suspend_in_progress, 0);
 		mutex_unlock(&ipa_gsb_ctx->iface_lock[hdl]);
 		return 0;
 	}
@@ -1096,6 +1101,7 @@
 			IPA_GSB_ERR(
 				"fail to stop cons ep %d\n",
 				ret);
+			atomic_set(&ipa_gsb_ctx->suspend_in_progress, 0);
 			mutex_unlock(&ipa_gsb_ctx->lock);
 			mutex_unlock(&ipa_gsb_ctx->iface_lock[hdl]);
 			return ret;
@@ -1105,6 +1111,7 @@
 		if (ret) {
 			IPA_GSB_ERR("fail to deactivate ipa pm\n");
 			ipa_start_gsi_channel(ipa_gsb_ctx->cons_hdl);
+			atomic_set(&ipa_gsb_ctx->suspend_in_progress, 0);
 			mutex_unlock(&ipa_gsb_ctx->lock);
 			mutex_unlock(&ipa_gsb_ctx->iface_lock[hdl]);
 			return ret;
@@ -1115,7 +1122,7 @@
 	ipa_gsb_ctx->num_resumed_iface--;
 	IPA_GSB_DBG_LOW("num resumed iface: %d\n",
 		ipa_gsb_ctx->num_resumed_iface);
-
+	atomic_set(&ipa_gsb_ctx->suspend_in_progress, 0);
 	mutex_unlock(&ipa_gsb_ctx->lock);
 	mutex_unlock(&ipa_gsb_ctx->iface_lock[hdl]);
 	return 0;
@@ -1169,6 +1176,16 @@
 		return -EFAULT;
 	}
 
+	if (unlikely(atomic_read(&ipa_gsb_ctx->suspend_in_progress))) {
+		IPA_GSB_ERR("ipa bridge suspend_in_progress\n");
+		return -EFAULT;
+	}
+
+	if (unlikely(!ipa_gsb_ctx->iface[hdl]->is_resumed)) {
+		IPA_GSB_ERR("iface %d was suspended\n", hdl);
+		return -EFAULT;
+	}
+
 	/* make sure skb has enough headroom */
 	if (unlikely(skb_headroom(skb) < sizeof(struct ipa_gsb_mux_hdr))) {
 		IPA_GSB_DBG_LOW("skb doesn't have enough headroom\n");