Merge 99c76e784dd51a961e7f7ac9b42db3929e2fd877 on remote branch

Change-Id: I3d05c2b1ce1f06e8c6e8ef6f083d12cd03aa7b2d
diff --git a/CORE/HDD/inc/wlan_hdd_cfg80211.h b/CORE/HDD/inc/wlan_hdd_cfg80211.h
index be208ae..a52093c 100644
--- a/CORE/HDD/inc/wlan_hdd_cfg80211.h
+++ b/CORE/HDD/inc/wlan_hdd_cfg80211.h
@@ -2119,6 +2119,29 @@
 }
 #endif
 
+#define JOINT_MULTI_BAND_RSNA 0x01
+#define PEER_KEY_ENABLED 0x02
+#define AMSDU_CAPABLE 0x04
+#define AMSDU_REQUIRED 0x08
+#define PBAC 0x10
+#define EXT_KEY_ID 0x20
+#define OCVC 0x40
+#define RESERVED 0x80
+
+/**
+ * wlan_hdd_mask_unsupported_rsn_caps() - Mask unsupported RSN CAPs in RSN IE
+ * @pBuf: pointer to rsn_ie
+ * @ielen: rsn_ie len
+ *
+ * This function is used to point rsn cap element in rsn IE and mask the rsn
+ * caps bits which driver doesn't support.
+ *
+ * Return: None
+ */
+void
+wlan_hdd_mask_unsupported_rsn_caps(tANI_U8 *pBuf, tANI_S16 ielen);
+
+
 #if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 14, 0))
 #define nla_parse(a, b, c, d, e) nla_parse(a, b, c, d, e, NULL)
 #define cfg80211_sched_scan_results(a) cfg80211_sched_scan_results(a, 0)
diff --git a/CORE/HDD/inc/wlan_hdd_wmm.h b/CORE/HDD/inc/wlan_hdd_wmm.h
index 4e1eb23..16cee8f 100644
--- a/CORE/HDD/inc/wlan_hdd_wmm.h
+++ b/CORE/HDD/inc/wlan_hdd_wmm.h
@@ -264,14 +264,23 @@
   @return         : Qdisc queue index
   ===========================================================================*/
 
-v_U16_t hdd_hostapd_select_queue(struct net_device * dev, struct sk_buff *skb
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,13,0))
-                                 , void *accel_priv
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 0))
+uint16_t hdd_hostapd_select_queue(struct net_device *dev, struct sk_buff *skb,
+				  struct net_device *sb_dev,
+				  select_queue_fallback_t fallbac);
+
+#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0))
+uint16_t hdd_hostapd_select_queue(struct net_device *dev, struct sk_buff *skb,
+				  void *accel_priv,
+				  select_queue_fallback_t fallbac);
+
+#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 13, 0))
+uint16_t hdd_hostapd_select_queue(struct net_device *dev, struct sk_buff *skb,
+				  void *accel_priv);
+
+#else
+uint16_t hdd_hostapd_select_queue(struct net_device *dev, struct sk_buff *skb);
 #endif
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,14,0))
-                                 , select_queue_fallback_t fallbac
-#endif
-);
 
 
 /**============================================================================
diff --git a/CORE/HDD/src/wlan_hdd_cfg80211.c b/CORE/HDD/src/wlan_hdd_cfg80211.c
index 541af37..70b3413 100644
--- a/CORE/HDD/src/wlan_hdd_cfg80211.c
+++ b/CORE/HDD/src/wlan_hdd_cfg80211.c
@@ -12790,14 +12790,6 @@
 		}
                 hdd_set_conparam(1);
 
-                status = hdd_sta_id_hash_attach(pAdapter);
-                if (VOS_STATUS_SUCCESS != status)
-                {
-                    hddLog(VOS_TRACE_LEVEL_ERROR,
-                           FL("Failed to initialize hash for AP"));
-                    return -EINVAL;
-                }
-
                 /*interface type changed update in wiphy structure*/
                 if(wdev)
                 {
@@ -15962,14 +15954,23 @@
 
     if( request->n_channels )
     {
-        char chList [(request->n_channels*5)+1];
         int len;
+	char *chList;
+
+	chList = vos_mem_malloc((request->n_channels * 5) + 1);
+	if (!chList) {
+		hddLog(VOS_TRACE_LEVEL_ERROR,
+		       "%s: memory alloc failed channelList", __func__);
+		status = -ENOMEM;
+	}
+
         channelList = vos_mem_malloc( request->n_channels );
         if( NULL == channelList )
         {
             hddLog(VOS_TRACE_LEVEL_ERROR,
                            "%s: memory alloc failed channelList", __func__);
             status = -ENOMEM;
+	    vos_mem_free(chList);
             goto free_mem;
         }
 
@@ -15981,6 +15982,7 @@
 
         hddLog(VOS_TRACE_LEVEL_INFO,
                            "Channel-List:  %s ", chList);
+	vos_mem_free(chList);
     }
 
     scanRequest.ChannelInfo.numOfChannels = request->n_channels;
@@ -16767,6 +16769,102 @@
     return 0;
 }
 
+static void framesntohs(v_U16_t *pOut,
+                        v_U8_t  *pIn,
+                        unsigned char fMsb)
+{
+#   if defined ( DOT11F_LITTLE_ENDIAN_HOST )
+    if ( !fMsb )
+    {
+        vos_mem_copy(( v_U16_t* )pOut, pIn, 2);
+    }
+    else
+    {
+        *pOut = ( v_U16_t )( *pIn << 8 ) | *( pIn + 1 );
+    }
+#   else
+    if ( !fMsb )
+    {
+        *pOut = ( v_U16_t )( *pIn | ( *( pIn + 1 ) << 8 ) );
+    }
+    else
+    {
+        vos_mem_copy(( v_U16_t* )pOut, pIn, 2);
+    }
+#   endif
+}
+
+void
+wlan_hdd_mask_unsupported_rsn_caps(tANI_U8 *pBuf, tANI_S16 ielen)
+{
+    u16 pwise_cipher_suite_count, akm_suite_cnt, mask = 0;
+    u8 *rsn_cap;
+
+    if (unlikely(ielen < 2)) {
+        return;
+    }
+
+    pBuf += 2;
+    ielen -= (tANI_U8)2;
+
+    if (unlikely(ielen < 4)) {
+        return;
+    }
+
+    pBuf += 4;
+    ielen -= (tANI_U8)4;
+
+    if (unlikely(ielen < 2)) {
+        return;
+    }
+
+    framesntohs(&pwise_cipher_suite_count, pBuf, 0);
+    pBuf += 2;
+    ielen -= (tANI_U8)2;
+
+    if (unlikely(ielen < pwise_cipher_suite_count * 4)) {
+        return;
+    }
+
+    if (!pwise_cipher_suite_count ||
+        pwise_cipher_suite_count > 4){
+        return;
+    }
+
+    pBuf += (pwise_cipher_suite_count * 4);
+    ielen -= (pwise_cipher_suite_count * 4);
+
+    if (unlikely(ielen < 2)) {
+        return;
+    }
+
+    framesntohs(&akm_suite_cnt, pBuf, 0);
+    pBuf += 2;
+    ielen -= (tANI_U8)2;
+
+    if (unlikely(ielen < akm_suite_cnt * 4)) {
+        return;
+    }
+
+    if (!akm_suite_cnt ||
+        akm_suite_cnt > 4){
+        return;
+    }
+
+    pBuf += (akm_suite_cnt * 4);
+    ielen -= (akm_suite_cnt * 4);
+
+    if (unlikely(ielen < 2)) {
+        return;
+    }
+
+    rsn_cap = pBuf;
+    mask = ~(JOINT_MULTI_BAND_RSNA | PEER_KEY_ENABLED | AMSDU_CAPABLE |
+             AMSDU_REQUIRED | PBAC | EXT_KEY_ID | OCVC | RESERVED);
+    rsn_cap[1] &= mask;
+
+    return;
+}
 
 /*
  * FUNCTION: wlan_hdd_cfg80211_set_ie
@@ -17079,6 +17177,8 @@
                 memcpy( pWextState->WPARSNIE, genie - 2, (eLen + 2)/*ie_len*/);
                 pWextState->roamProfile.pRSNReqIE = pWextState->WPARSNIE;
                 pWextState->roamProfile.nRSNReqIELength = eLen + 2; //ie_len;
+                wlan_hdd_mask_unsupported_rsn_caps(pWextState->WPARSNIE + 2,
+                                                   eLen);
                 break;
 
                 /* Appending extended capabilities with Interworking or
@@ -20397,9 +20497,17 @@
     num_ch = 0;
     if (request->n_channels)
     {
-        char chList [(request->n_channels*5)+1];
         int len;
-        for (i = 0, len = 0; i < request->n_channels; i++)
+	char *chList;
+
+	chList = vos_mem_malloc((request->n_channels * 5) + 1);
+	if (!chList) {
+		hddLog(VOS_TRACE_LEVEL_ERROR,
+		       "%s: memory alloc failed channelList", __func__);
+		status = -ENOMEM;
+	}
+
+	for (i = 0, len = 0; i < request->n_channels; i++)
         {
             for (indx = 0; indx < num_channels_allowed; indx++)
             {
@@ -20430,8 +20538,10 @@
             VOS_TRACE(VOS_MODULE_ID_HDD, VOS_TRACE_LEVEL_INFO,
              "%s : All requested channels are DFS channels", __func__);
             ret = -EINVAL;
+	    vos_mem_free(chList);
             goto error;
         }
+	vos_mem_free(chList);
      }
 
     pnoRequest.aNetworks =
diff --git a/CORE/HDD/src/wlan_hdd_early_suspend.c b/CORE/HDD/src/wlan_hdd_early_suspend.c
index 174f1ea..537e7ae 100644
--- a/CORE/HDD/src/wlan_hdd_early_suspend.c
+++ b/CORE/HDD/src/wlan_hdd_early_suspend.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012-2018 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2012-2018, 2021 The Linux Foundation. All rights reserved.
  *
  * Previously licensed under the ISC license by Qualcomm Atheros, Inc.
  *
@@ -2146,17 +2146,20 @@
     vos_ssr_unprotect(__func__);
 }
 
-static void hdd_ssr_timer_init(void)
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 0))
+static void hdd_ssr_timer_cb(struct timer_list *data)
 {
-    init_timer(&ssr_timer);
+	hddLog(VOS_TRACE_LEVEL_FATAL, "%s: HDD SSR timer expired", __func__);
+
+#ifdef WCN_PRONTO
+	if (wcnss_hardware_type() == WCNSS_PRONTO_HW)
+		wcnss_pronto_log_debug_regs();
+#endif
+
+	VOS_BUG(0);
 }
 
-static void hdd_ssr_timer_del(void)
-{
-    del_timer(&ssr_timer);
-    ssr_timer_started = false;
-}
-
+#else
 static void hdd_ssr_timer_cb(unsigned long data)
 {
     hddLog(VOS_TRACE_LEVEL_FATAL, "%s: HDD SSR timer expired", __func__);
@@ -2168,6 +2171,26 @@
 
     VOS_BUG(0);
 }
+#endif
+
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 0))
+static void hdd_ssr_timer_init(void)
+{
+	timer_setup(&ssr_timer, hdd_ssr_timer_cb, 0);
+}
+
+#else
+static void hdd_ssr_timer_init(void)
+{
+	init_timer(&ssr_timer);
+}
+#endif
+
+static void hdd_ssr_timer_del(void)
+{
+    del_timer(&ssr_timer);
+    ssr_timer_started = false;
+}
 
 static void hdd_ssr_timer_start(int msec)
 {
diff --git a/CORE/HDD/src/wlan_hdd_hostapd.c b/CORE/HDD/src/wlan_hdd_hostapd.c
index c2d917e..8115be8 100644
--- a/CORE/HDD/src/wlan_hdd_hostapd.c
+++ b/CORE/HDD/src/wlan_hdd_hostapd.c
@@ -5556,6 +5556,15 @@
                                 ini_cfg->apEndChannelNum,
                                 ini_cfg->apOperatingBand);
     }
+
+    status = hdd_sta_id_hash_attach(pAdapter);
+    if (VOS_STATUS_SUCCESS != status)
+    {
+	    hddLog(VOS_TRACE_LEVEL_ERROR,
+			    FL("Failed to initialize hash for AP"));
+	    goto error_wmm_init;
+    }
+
    /* Action frame registered in one adapter which will
     * applicable to all interfaces
     */
diff --git a/CORE/HDD/src/wlan_hdd_main.c b/CORE/HDD/src/wlan_hdd_main.c
index 67d86ce..fddf35f 100644
--- a/CORE/HDD/src/wlan_hdd_main.c
+++ b/CORE/HDD/src/wlan_hdd_main.c
@@ -257,15 +257,21 @@
 void hdd_set_vowifi_mode(hdd_context_t *hdd_ctx, bool enable);
 void hdd_set_olpc_mode(tHalHandle hHal, bool low_power);
 
-v_U16_t hdd_select_queue(struct net_device *dev,
-    struct sk_buff *skb
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,13,0))
-    , void *accel_priv
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 0))
+uint16_t hdd_select_queue(struct net_device *dev, struct sk_buff *skb,
+			  struct net_device *sb_dev,
+			  select_queue_fallback_t fallback);
+
+#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0))
+uint16_t hdd_select_queue(struct net_device *dev, struct sk_buff *skb,
+			  void *accel_priv, select_queue_fallback_t fallback);
+
+#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 13, 0))
+uint16_t hdd_select_queue(struct net_device *dev, struct sk_buff *skb,
+			  void *accel_priv);
+#else
+uint16_t hdd_select_queue(struct net_device *dev, struct sk_buff *skb);
 #endif
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,14,0))
-    , select_queue_fallback_t fallback
-#endif
-);
 
 #ifdef WLAN_FEATURE_PACKET_FILTERING
 static void hdd_set_multicast_list(struct net_device *dev);
@@ -4033,7 +4039,6 @@
 static void hdd_init_sw_pta(hdd_context_t *hdd_ctx)
 {
 	init_completion(&hdd_ctx->sw_pta_comp);
-	wcnss_update_bt_profile();
 }
 
 static void hdd_deinit_sw_pta(hdd_context_t *hdd_ctx)
@@ -10113,14 +10118,6 @@
 
          hdd_initialize_adapter_common(pAdapter);
 
-         status = hdd_sta_id_hash_attach(pAdapter);
-         if (VOS_STATUS_SUCCESS != status)
-         {
-             hddLog(VOS_TRACE_LEVEL_FATAL,
-                    FL("failed to attach hash for session %d"), session_type);
-             goto err_free_netdev;
-         }
-
          status = hdd_register_hostapd( pAdapter, rtnl_held );
          if( VOS_STATUS_SUCCESS != status )
          {
@@ -11690,12 +11687,6 @@
          case WLAN_HDD_SOFTAP:
             if (pHddCtx->cfg_ini->sap_internal_restart) {
                 hdd_init_ap_mode(pAdapter, true);
-                status = hdd_sta_id_hash_attach(pAdapter);
-                if (VOS_STATUS_SUCCESS != status)
-                {
-                    hddLog(VOS_TRACE_LEVEL_FATAL,
-                         FL("failed to attach hash for"));
-                }
             }
             break;
 
@@ -12235,19 +12226,31 @@
   \return - ac, Queue Index/access category corresponding to UP in IP header 
   
   --------------------------------------------------------------------------*/
-v_U16_t hdd_select_queue(struct net_device *dev,
-    struct sk_buff *skb
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,13,0))
-    , void *accel_priv
-#endif
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,14,0))
-    , select_queue_fallback_t fallback
-#endif
-)
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 0))
+v_U16_t hdd_select_queue(struct net_device *dev, struct sk_buff *skb,
+			 struct net_device *sb_dev,
+			 select_queue_fallback_t fallback)
 {
-   return hdd_wmm_select_queue(dev, skb);
+	return hdd_wmm_select_queue(dev, skb);
 }
-
+#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0))
+v_U16_t hdd_select_queue(struct net_device *dev, struct sk_buff *skb,
+			 void *accel_priv, select_queue_fallback_t fallback)
+{
+	return hdd_wmm_select_queue(dev, skb);
+}
+#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 13, 0))
+v_U16_t hdd_select_queue(struct net_device *dev, struct sk_buff *skb,
+			 void *accel_priv)
+{
+	return hdd_wmm_select_queue(dev, skb);
+}
+#else
+v_U16_t hdd_select_queue(struct net_device *dev, struct sk_buff *skb)
+{
+	return hdd_wmm_select_queue(dev, skb);
+}
+#endif
 
 /**---------------------------------------------------------------------------
 
@@ -14150,6 +14153,7 @@
 #endif /* WLAN_KD_READY_NOTIFIER */
 
    vos_set_roam_delay_stats_enabled(pHddCtx->cfg_ini->gEnableRoamDelayStats);
+   hdd_init_sw_pta(pHddCtx);
    status = vos_open( &pVosContext, pHddCtx->parent_dev);
    if ( !VOS_IS_STATUS_SUCCESS( status ))
    {
@@ -14782,7 +14786,7 @@
 
    mutex_init(&pHddCtx->cache_channel_lock);
 
-   hdd_init_sw_pta(pHddCtx);
+   wcnss_update_bt_profile();
    goto success;
 
 err_open_cesium_nl_sock:
diff --git a/CORE/HDD/src/wlan_hdd_tdls.c b/CORE/HDD/src/wlan_hdd_tdls.c
index 13da124..b804968 100644
--- a/CORE/HDD/src/wlan_hdd_tdls.c
+++ b/CORE/HDD/src/wlan_hdd_tdls.c
@@ -1382,6 +1382,8 @@
 
     vos_mem_zero(peer, sizeof(hddTdlsPeer_t));
     vos_mem_copy(peer->peerMac, mac, sizeof(peer->peerMac));
+    if (pHddCtx->cfg_ini->fTDLSExternalControl)
+        peer->isForcedPeer = 1;
     peer->pHddTdlsCtx = pHddTdlsCtx;
     list_add_tail(&peer->node, head);
 
diff --git a/CORE/HDD/src/wlan_hdd_wext.c b/CORE/HDD/src/wlan_hdd_wext.c
index 1bb4e18..82d7336 100644
--- a/CORE/HDD/src/wlan_hdd_wext.c
+++ b/CORE/HDD/src/wlan_hdd_wext.c
@@ -2367,6 +2367,8 @@
                 memcpy( pWextState->WPARSNIE, genie - 2, (eLen + 2));
                 pWextState->roamProfile.pRSNReqIE = pWextState->WPARSNIE;
                 pWextState->roamProfile.nRSNReqIELength = eLen + 2;
+                wlan_hdd_mask_unsupported_rsn_caps(pWextState->WPARSNIE + 2,
+                                                   eLen);
               break;
 
          default:
diff --git a/CORE/HDD/src/wlan_hdd_wmm.c b/CORE/HDD/src/wlan_hdd_wmm.c
index 9c2ad34..fbb2c32 100644
--- a/CORE/HDD/src/wlan_hdd_wmm.c
+++ b/CORE/HDD/src/wlan_hdd_wmm.c
@@ -2191,7 +2191,7 @@
 }
 
 /**============================================================================
-  @brief hdd_hostapd_select_quueue() - Function which will classify the packet
+  @brief __hdd_hostapd_select_queue() - Function which will classify the packet
          according to linux qdisc expectation.
 
 
@@ -2200,14 +2200,8 @@
 
   @return         : Qdisc queue index
   ===========================================================================*/
-v_U16_t hdd_hostapd_select_queue(struct net_device * dev, struct sk_buff *skb
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,13,0))
-                                 , void *accel_priv
-#endif
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3,14,0))
-                                 , select_queue_fallback_t fallbac
-#endif
-)
+uint16_t __hdd_hostapd_select_queue(struct net_device *dev,
+				    struct sk_buff *skb)
 {
    WLANTL_ACEnumType ac;
    sme_QosWmmUpType up = SME_QOS_WMM_UP_BE;
@@ -2283,6 +2277,34 @@
    return queueIndex;
 }
 
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 0))
+uint16_t hdd_hostapd_select_queue(struct net_device *dev, struct sk_buff *skb,
+				  struct net_device *sb_dev,
+				  select_queue_fallback_t fallbac)
+{
+	return __hdd_hostapd_select_queue(dev, skb);
+}
+
+#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 14, 0))
+uint16_t hdd_hostapd_select_queue(struct net_device *dev, struct sk_buff *skb,
+				  void *accel_priv,
+				  select_queue_fallback_t fallbac)
+{
+	return __hdd_hostapd_select_queue(dev, skb);
+}
+#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 13, 0))
+uint16_t hdd_hostapd_select_queue(struct net_device *dev, struct sk_buff *skb,
+				  void *accel_priv)
+{
+	return __hdd_hostapd_select_queue(dev, skb);
+}
+#else
+uint16_t hdd_hostapd_select_queue(struct net_device *dev, struct sk_buff *skb)
+{
+	return __hdd_hostapd_select_queue(dev, skb);
+}
+#endif
+
 /**============================================================================
   @brief hdd_wmm_select_quueue() - Function which will classify the packet
          according to linux qdisc expectation.
diff --git a/CORE/MAC/src/pe/lim/limAssocUtils.c b/CORE/MAC/src/pe/lim/limAssocUtils.c
index b1ca2c0..6fcc024 100644
--- a/CORE/MAC/src/pe/lim/limAssocUtils.c
+++ b/CORE/MAC/src/pe/lim/limAssocUtils.c
@@ -3045,7 +3045,8 @@
         {
             pAddStaParams->greenFieldCapable = limGetHTCapability( pMac, eHT_GREENFIELD, psessionEntry);
             pAddStaParams->txChannelWidthSet =
-                  pMac->roam.configParam.channelBondingMode5GHz;
+                  pMac->roam.configParam.channelBondingMode5GHz ^
+                  pMac->roam.configParam.channelBondingMode24GHz;
             // pAddStaParams->txChannelWidthSet = limGetHTCapability( pMac, eHT_SUPPORTED_CHANNEL_WIDTH_SET, psessionEntry);
             pAddStaParams->mimoPS             = limGetHTCapability( pMac, eHT_MIMO_POWER_SAVE, psessionEntry );
             pAddStaParams->rifsMode           = limGetHTCapability( pMac, eHT_RIFS_MODE, psessionEntry );
diff --git a/CORE/VOSS/inc/i_vos_lock.h b/CORE/VOSS/inc/i_vos_lock.h
index cc213f7..804733c 100644
--- a/CORE/VOSS/inc/i_vos_lock.h
+++ b/CORE/VOSS/inc/i_vos_lock.h
@@ -77,8 +77,17 @@
 typedef spinlock_t vos_spin_lock_t;
 
 #if defined(WLAN_OPEN_SOURCE)
+
 #if LINUX_VERSION_CODE >= KERNEL_VERSION(3, 19, 0)
-typedef struct wakeup_source vos_wake_lock_t;
+/**
+ * typedef struct - vos_wake_lock_t
+ * @lock: this lock needs to be used in kernel version < 4.19
+ * @priv: this lock pointer needs to be used in kernel version >= 4.19
+ */
+typedef struct vos_wake_lock {
+	struct wakeup_source lock;
+	struct wakeup_source *priv;
+} vos_wake_lock_t;
 #else
 typedef struct wake_lock vos_wake_lock_t;
 #endif
diff --git a/CORE/VOSS/src/vos_lock.c b/CORE/VOSS/src/vos_lock.c
index aaa9e50..c8b3bbf 100644
--- a/CORE/VOSS/src/vos_lock.c
+++ b/CORE/VOSS/src/vos_lock.c
@@ -482,11 +482,27 @@
    return VOS_STATUS_SUCCESS;
 }
 
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 19, 0)) && \
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 110)) || \
+	defined(WAKEUP_SOURCE_DEV)
+VOS_STATUS vos_wake_lock_init(vos_wake_lock_t *lock, const char *name)
+{
+	vos_mem_zero(lock, sizeof(*lock));
+	lock->priv = wakeup_source_register(lock->lock.dev, name);
+	if (!(lock->priv)) {
+		VOS_BUG(0);
+		return VOS_STATUS_E_FAILURE;
+	}
+
+	lock->lock = *(lock->priv);
+
+	return VOS_STATUS_SUCCESS;
+}
+#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 19, 0)) && \
 	defined(WLAN_OPEN_SOURCE)
 VOS_STATUS vos_wake_lock_init(vos_wake_lock_t *pLock, const char *name)
 {
-	wakeup_source_init(pLock, name);
+	wakeup_source_init(&pLock->lock, name);
+	pLock->priv = &(pLock->lock);
 	return VOS_STATUS_SUCCESS;
 }
 #else
@@ -513,8 +529,8 @@
 	defined(WLAN_OPEN_SOURCE)
 static const char *vos_wake_lock_name(vos_wake_lock_t *pLock)
 {
-	if (pLock->name)
-		return pLock->name;
+	if (pLock)
+		return pLock->lock.name;
 
 	return "UNNAMED_WAKELOCK";
 }
@@ -548,7 +564,7 @@
 	vos_log_wlock_diag(reason, vos_wake_lock_name(pLock),
 			   WIFI_POWER_EVENT_DEFAULT_WAKELOCK_TIMEOUT,
 			   WIFI_POWER_EVENT_WAKELOCK_TAKEN);
-	__pm_stay_awake(pLock);
+	__pm_stay_awake(pLock->priv);
 	return VOS_STATUS_SUCCESS;
 }
 #else
@@ -586,7 +602,7 @@
 	 * Wakelock for Rx is frequent.
 	 * It is reported only during active debug
 	 */
-	__pm_wakeup_event(pLock, msec);
+	__pm_wakeup_event(pLock->priv, msec);
 	return VOS_STATUS_SUCCESS;
 }
 #else
@@ -630,7 +646,7 @@
 	vos_log_wlock_diag(reason, vos_wake_lock_name(pLock),
 			   WIFI_POWER_EVENT_DEFAULT_WAKELOCK_TIMEOUT,
 			   WIFI_POWER_EVENT_WAKELOCK_RELEASED);
-	__pm_relax(pLock);
+	__pm_relax(pLock->priv);
 	return VOS_STATUS_SUCCESS;
 }
 #else
@@ -660,11 +676,19 @@
 }
 #endif
 
-#if (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 19, 0)) && \
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 110)) || \
+	defined(WAKEUP_SOURCE_DEV)
+VOS_STATUS vos_wake_lock_destroy(vos_wake_lock_t *lock)
+{
+	wakeup_source_unregister(lock->priv);
+	return VOS_STATUS_SUCCESS;
+}
+
+#elif (LINUX_VERSION_CODE >= KERNEL_VERSION(3, 19, 0)) && \
 	defined(WLAN_OPEN_SOURCE)
 VOS_STATUS vos_wake_lock_destroy(vos_wake_lock_t *pLock)
 {
-	wakeup_source_trash(pLock);
+	wakeup_source_trash(pLock->priv);
 	return VOS_STATUS_SUCCESS;
 }
 #else
@@ -691,7 +715,7 @@
 	defined(WLAN_OPEN_SOURCE)
 bool vos_wake_lock_active(vos_wake_lock_t *lock)
 {
-	return lock->active;
+	return lock->priv->active;
 }
 #else
 bool vos_wake_lock_active(vos_wake_lock_t *lock)
diff --git a/CORE/VOSS/src/vos_timer.c b/CORE/VOSS/src/vos_timer.c
index 8b6970d..324a5d2 100644
--- a/CORE/VOSS/src/vos_timer.c
+++ b/CORE/VOSS/src/vos_timer.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012-2013, 2015-2017 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2012-2013, 2015-2021 The Linux Foundation. All rights reserved.
  *
  * Previously licensed under the ISC license by Qualcomm Atheros, Inc.
  *
@@ -110,9 +110,8 @@
 
   --------------------------------------------------------------------------*/
 
-static void vos_linux_timer_callback (unsigned long data)
+static void vos_linux_timer_callback(vos_timer_t *timer)
 {
-   vos_timer_t *timer = ( vos_timer_t *)data; 
    vos_msg_t msg;
    VOS_STATUS vStatus;
    unsigned long flags;
@@ -375,6 +374,47 @@
 }
 #endif
   
+#if (LINUX_VERSION_CODE >= KERNEL_VERSION(4, 19, 0))
+static void vos_timer_shim(struct timer_list *vos_timer)
+{
+	vos_timer_platform_t *platformInfo_ptr = container_of(vos_timer,
+							vos_timer_platform_t,
+							Timer);
+
+	vos_timer_t *timer = container_of(platformInfo_ptr, vos_timer_t,
+						platformInfo);
+
+	vos_linux_timer_callback(timer);
+}
+
+static void vos_timer_setup(vos_timer_t *timer, bool deferrable)
+{
+	uint32_t flags = 0;
+
+	if (deferrable)
+		flags |= TIMER_DEFERRABLE;
+	timer_setup(&(timer->platformInfo.Timer), vos_timer_shim,
+		    flags);
+}
+#else
+static void vos_timer_shim(unsigned long data)
+{
+	vos_timer_t *timer = (vos_timer_t *)data;
+
+	vos_linux_timer_callback(timer);
+}
+
+static void vos_timer_setup(vos_timer_t *timer, bool deferrable)
+{
+	if (deferrable)
+		init_timer_deferrable(&timer->platformInfo.Timer);
+	else
+		init_timer(&timer->platformInfo.Timer);
+	timer->platformInfo.Timer.function = vos_timer_shim;
+	timer->platformInfo.Timer.data = (unsigned long)timer;
+}
+#endif
+
 /*--------------------------------------------------------------------------
   
   \brief vos_timer_init() - Initialize a vOSS timer.
@@ -484,12 +524,7 @@
     * with arguments passed or with default values
     */
    spin_lock_init(&timer->platformInfo.spinlock);
-   if(deferrable)
-     init_timer_deferrable(&(timer->platformInfo.Timer));
-   else
-     init_timer(&(timer->platformInfo.Timer));
-   timer->platformInfo.Timer.function = vos_linux_timer_callback;
-   timer->platformInfo.Timer.data = (unsigned long)timer;
+   vos_timer_setup(timer, deferrable);
    timer->callback = callback;
    timer->userData = userData;
    timer->type = timerType;
@@ -541,12 +576,7 @@
     * with arguments passed or with default values
     */
    spin_lock_init(&timer->platformInfo.spinlock);
-   if(deferrable)
-     init_timer_deferrable(&(timer->platformInfo.Timer));
-   else
-     init_timer(&(timer->platformInfo.Timer));
-   timer->platformInfo.Timer.function = vos_linux_timer_callback;
-   timer->platformInfo.Timer.data = (unsigned long)timer;
+   vos_timer_setup(timer, deferrable);
    timer->callback = callback;
    timer->userData = userData;
    timer->type = timerType;