Merge "qcacmn: CFR: Process PPDU status TLVs and extract CFR information"
diff --git a/dp/inc/cdp_txrx_ctrl.h b/dp/inc/cdp_txrx_ctrl.h
index d79adc2..91742fa 100644
--- a/dp/inc/cdp_txrx_ctrl.h
+++ b/dp/inc/cdp_txrx_ctrl.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -723,6 +723,34 @@
 	return soc->ops->ctrl_ops->txrx_get_pldev(pdev);
 }
 
+#if defined(WLAN_CFR_ENABLE) && defined(WLAN_ENH_CFR_ENABLE)
+/**
+ * cdp_cfr_filter() - Configure Host RX monitor status ring for CFR
+ * @soc: SOC TXRX handle
+ * @pdev_id: ID of the physical device object
+ * @enable: Enable or disable CFR
+ * @filter_val: Flag to select filter for monitor mode
+ */
+static inline void
+cdp_cfr_filter(ol_txrx_soc_handle soc,
+	       uint8_t pdev_id,
+	       bool enable,
+	       struct cdp_monitor_filter *filter_val)
+{
+	if (!soc || !soc->ops) {
+		QDF_TRACE(QDF_MODULE_ID_DP, QDF_TRACE_LEVEL_FATAL,
+			  "%s invalid instance", __func__);
+		QDF_BUG(0);
+		return;
+	}
+
+	if (!soc->ops->cfr_ops || !soc->ops->cfr_ops->txrx_cfr_filter)
+		return;
+
+	soc->ops->cfr_ops->txrx_cfr_filter(soc, pdev_id, enable, filter_val);
+}
+#endif
+
 #if defined(WLAN_TX_PKT_CAPTURE_ENH) || defined(WLAN_RX_PKT_CAPTURE_ENH)
 /**
  * cdp_update_peer_pkt_capture_params() - Sets Rx & Tx Capture params for a peer
diff --git a/dp/inc/cdp_txrx_ops.h b/dp/inc/cdp_txrx_ops.h
index 005fc13..372d5dc 100644
--- a/dp/inc/cdp_txrx_ops.h
+++ b/dp/inc/cdp_txrx_ops.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2017-2020 The Linux Foundation. All rights reserved.
  *
  *
  * Permission to use, copy, modify, and/or distribute this software for
@@ -1610,6 +1610,19 @@
 };
 #endif
 
+#if defined(WLAN_CFR_ENABLE) && defined(WLAN_ENH_CFR_ENABLE)
+/**
+ * struct cdp_cfr_ops - host cfr ops
+ * @txrx_cfr_filter: Handler to configure host rx monitor status ring
+ */
+struct cdp_cfr_ops {
+	void (*txrx_cfr_filter)(struct cdp_soc_t *soc_hdl,
+				uint8_t pdev_id,
+				bool enable,
+				struct cdp_monitor_filter *filter_val);
+};
+#endif
+
 struct cdp_ops {
 	struct cdp_cmn_ops          *cmn_drv_ops;
 	struct cdp_ctrl_ops         *ctrl_ops;
@@ -1645,6 +1658,9 @@
 #ifdef WLAN_FEATURE_PKT_CAPTURE
 	struct cdp_pktcapture_ops   *pktcapture_ops;
 #endif
+#if defined(WLAN_CFR_ENABLE) && defined(WLAN_ENH_CFR_ENABLE)
+	struct cdp_cfr_ops          *cfr_ops;
+#endif
 
 };
 #endif
diff --git a/dp/wifi3.0/dp_main.c b/dp/wifi3.0/dp_main.c
index 2d505e3..769c4f9 100644
--- a/dp/wifi3.0/dp_main.c
+++ b/dp/wifi3.0/dp_main.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -151,6 +151,12 @@
 bool is_dp_verbose_debug_enabled;
 #endif
 
+#if defined(WLAN_CFR_ENABLE) && defined(WLAN_ENH_CFR_ENABLE)
+static void dp_cfr_filter(struct cdp_soc_t *soc_hdl,
+			  uint8_t pdev_id,
+			  bool enable,
+			  struct cdp_monitor_filter *filter_val);
+#endif
 static uint8_t dp_soc_ring_if_nss_offloaded(struct dp_soc *soc,
 					    enum hal_ring_type ring_type,
 					    int ring_num);
@@ -9749,6 +9755,12 @@
 };
 #endif /* CONFIG_WIN */
 
+#if defined(WLAN_CFR_ENABLE) && defined(WLAN_ENH_CFR_ENABLE)
+static struct cdp_cfr_ops dp_ops_cfr = {
+	.txrx_cfr_filter = dp_cfr_filter,
+};
+#endif
+
 #ifdef FEATURE_RUNTIME_PM
 /**
  * dp_runtime_suspend() - ensure DP is ready to runtime suspend
@@ -10179,6 +10191,9 @@
 #ifdef DP_POWER_SAVE
 	.bus_ops = &dp_ops_bus,
 #endif
+#if defined(WLAN_CFR_ENABLE) && defined(WLAN_ENH_CFR_ENABLE)
+	.cfr_ops = &dp_ops_cfr,
+#endif
 };
 
 /*
@@ -10506,6 +10521,76 @@
 	*max_mac_rings = (dbs_enable)?(*max_mac_rings):1;
 }
 
+#if defined(WLAN_CFR_ENABLE) && defined(WLAN_ENH_CFR_ENABLE)
+/*
+ * dp_cfr_filter() -  Configure HOST RX monitor status ring for CFR
+ * @soc_hdl: Datapath soc handle
+ * @pdev_id: id of data path pdev handle
+ * @enable: Enable/Disable CFR
+ * @filter_val: Flag to select Filter for monitor mode
+ */
+static void dp_cfr_filter(struct cdp_soc_t *soc_hdl,
+			  uint8_t pdev_id,
+			  bool enable,
+			  struct cdp_monitor_filter *filter_val)
+{
+	struct dp_soc *soc = cdp_soc_t_to_dp_soc(soc_hdl);
+	struct dp_pdev *pdev = dp_get_pdev_from_soc_pdev_id_wifi3(soc, pdev_id);
+	struct htt_rx_ring_tlv_filter htt_tlv_filter = {0};
+	int max_mac_rings = wlan_cfg_get_num_mac_rings(pdev->wlan_cfg_ctx);
+	uint8_t mac_id = 0;
+
+	if (pdev->monitor_vdev) {
+		dp_info("No action is needed since monitor mode is enabled\n");
+		return;
+	}
+	soc = pdev->soc;
+	pdev->cfr_rcc_mode = false;
+	dp_is_hw_dbs_enable(soc, &max_mac_rings);
+
+	dp_debug("Max_mac_rings %d", max_mac_rings);
+	dp_info("enable : %d, mode: 0x%x", enable, filter_val->mode);
+
+	if (enable) {
+		pdev->cfr_rcc_mode = true;
+
+		htt_tlv_filter.ppdu_start = 1;
+		htt_tlv_filter.ppdu_end = 1;
+		htt_tlv_filter.ppdu_end_user_stats = 1;
+		htt_tlv_filter.ppdu_end_user_stats_ext = 1;
+		htt_tlv_filter.ppdu_end_status_done = 1;
+		htt_tlv_filter.mpdu_start = 1;
+		htt_tlv_filter.offset_valid = false;
+
+		htt_tlv_filter.enable_fp =
+			(filter_val->mode & MON_FILTER_PASS) ? 1 : 0;
+		htt_tlv_filter.enable_md = 0;
+		htt_tlv_filter.enable_mo =
+			(filter_val->mode & MON_FILTER_OTHER) ? 1 : 0;
+		htt_tlv_filter.fp_mgmt_filter = filter_val->fp_mgmt;
+		htt_tlv_filter.fp_ctrl_filter = filter_val->fp_ctrl;
+		htt_tlv_filter.fp_data_filter = filter_val->fp_data;
+		htt_tlv_filter.mo_mgmt_filter = filter_val->mo_mgmt;
+		htt_tlv_filter.mo_ctrl_filter = filter_val->mo_ctrl;
+		htt_tlv_filter.mo_data_filter = filter_val->mo_data;
+	}
+
+	for (mac_id = 0; mac_id < max_mac_rings; mac_id++) {
+		int mac_for_pdev =
+			dp_get_mac_id_for_pdev(mac_id,
+					       pdev->pdev_id);
+
+		htt_h2t_rx_ring_cfg(soc->htt_handle,
+				    mac_for_pdev,
+				    pdev->rxdma_mon_status_ring[mac_id]
+				    .hal_srng,
+				    RXDMA_MONITOR_STATUS,
+				    RX_BUFFER_SIZE,
+				    &htt_tlv_filter);
+	}
+}
+#endif
+
 /*
 * dp_is_soc_reinit() - Check if soc reinit is true
 * @soc: DP SoC context
diff --git a/dp/wifi3.0/dp_types.h b/dp/wifi3.0/dp_types.h
index 7a89cea..9ec7426 100644
--- a/dp/wifi3.0/dp_types.h
+++ b/dp/wifi3.0/dp_types.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -1617,6 +1617,7 @@
 	bool tx_sniffer_enable;
 	/* mirror copy mode */
 	bool mcopy_mode;
+	bool cfr_rcc_mode;
 	bool bpr_enable;
 
 	/* enable time latency check for tx completion */
diff --git a/hal/wifi3.0/hal_api_mon.h b/hal/wifi3.0/hal_api_mon.h
index 607159f..cc874f0 100644
--- a/hal/wifi3.0/hal_api_mon.h
+++ b/hal/wifi3.0/hal_api_mon.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2017-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2017-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -466,6 +466,83 @@
 	uint32_t flow_idx;
 };
 
+#if defined(WLAN_CFR_ENABLE) && defined(WLAN_ENH_CFR_ENABLE)
+/**
+ * struct hal_rx_ppdu_cfr_user_info - struct for storing peer info extracted
+ * from HW TLVs, this will be used for correlating CFR data with multiple peers
+ * in MU PPDUs
+ *
+ * @peer_macaddr: macaddr of the peer
+ * @ast_index: AST index of the peer
+ */
+struct hal_rx_ppdu_cfr_user_info {
+	uint8_t peer_macaddr[QDF_MAC_ADDR_SIZE];
+	uint32_t ast_index;
+};
+
+/**
+ * struct hal_rx_ppdu_cfr_info - struct for storing ppdu info extracted from HW
+ * TLVs, this will be used for CFR correlation
+ *
+ * @bb_captured_channel : Set by RXPCU when MACRX_FREEZE_CAPTURE_CHANNEL TLV is
+ * sent to PHY, SW checks it to correlate current PPDU TLVs with uploaded
+ * channel information.
+ *
+ * @bb_captured_timeout : Set by RxPCU to indicate channel capture condition is
+ * met, but MACRX_FREEZE_CAPTURE_CHANNEL is not sent to PHY due to AST delay,
+ * which means the rx_frame_falling edge to FREEZE TLV ready time exceeds
+ * the threshold time defined by RXPCU register FREEZE_TLV_DELAY_CNT_THRESH.
+ * Bb_captured_reason is still valid in this case.
+ *
+ * @rx_location_info_valid: Indicates whether CFR DMA address in the PPDU TLV
+ * is valid
+ * <enum 0 rx_location_info_is_not_valid>
+ * <enum 1 rx_location_info_is_valid>
+ * <legal all>
+ *
+ * @bb_captured_reason : Copy capture_reason of MACRX_FREEZE_CAPTURE_CHANNEL
+ * TLV to here for FW usage. Valid when bb_captured_channel or
+ * bb_captured_timeout is set.
+ * <enum 0 freeze_reason_TM>
+ * <enum 1 freeze_reason_FTM>
+ * <enum 2 freeze_reason_ACK_resp_to_TM_FTM>
+ * <enum 3 freeze_reason_TA_RA_TYPE_FILTER>
+ * <enum 4 freeze_reason_NDPA_NDP>
+ * <enum 5 freeze_reason_ALL_PACKET>
+ * <legal 0-5>
+ *
+ * @rtt_che_buffer_pointer_low32 : The low 32 bits of the 40 bits pointer to
+ * external RTT channel information buffer
+ *
+ * @rtt_che_buffer_pointer_high8 : The high 8 bits of the 40 bits pointer to
+ * external RTT channel information buffer
+ *
+ * @chan_capture_status : capture status reported by ucode
+ * a. CAPTURE_IDLE: FW has disabled "REPETITIVE_CHE_CAPTURE_CTRL"
+ * b. CAPTURE_BUSY: previous PPDU’s channel capture upload DMA ongoing. (Note
+ * that this upload is triggered after receiving freeze_channel_capture TLV
+ * after last PPDU is rx)
+ * c. CAPTURE_ACTIVE: channel capture is enabled and no previous channel
+ * capture ongoing
+ * d. CAPTURE_NO_BUFFER: next buffer in IPC ring not available
+ *
+ * @cfr_user_info: Peer mac for upto 4 MU users
+ */
+
+struct hal_rx_ppdu_cfr_info {
+	bool bb_captured_channel;
+	bool bb_captured_timeout;
+	uint8_t bb_captured_reason;
+	bool rx_location_info_valid;
+	uint8_t chan_capture_status;
+	uint8_t rtt_che_buffer_pointer_high8;
+	uint32_t rtt_che_buffer_pointer_low32;
+	struct hal_rx_ppdu_cfr_user_info cfr_user_info[HAL_MAX_UL_MU_USERS];
+};
+#else
+struct hal_rx_ppdu_cfr_info {};
+#endif
+
 struct hal_rx_ppdu_info {
 	struct hal_rx_ppdu_common_info com_info;
 	struct mon_rx_status rx_status;
@@ -490,6 +567,11 @@
 	struct hal_rx_msdu_payload_info ppdu_msdu_info[HAL_RX_MAX_MPDU];
 	/* evm info */
 	struct hal_rx_su_evm_info evm_info;
+	/**
+	 * Will be used to store ppdu info extracted from HW TLVs,
+	 * and for CFR correlation as well
+	 */
+	struct hal_rx_ppdu_cfr_info cfr_info;
 };
 
 static inline uint32_t
diff --git a/hal/wifi3.0/hal_generic_api.h b/hal/wifi3.0/hal_generic_api.h
index 1c03f5a..05e110d 100644
--- a/hal/wifi3.0/hal_generic_api.h
+++ b/hal/wifi3.0/hal_generic_api.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -439,6 +439,10 @@
 		ppdu_info->rx_state = HAL_RX_MON_PPDU_END;
 		break;
 
+	case WIFIPHYRX_PKT_END_E:
+		hal_rx_get_rtt_info(hal_soc_hdl, rx_tlv, ppdu_info);
+		break;
+
 	case WIFIRXPCU_PPDU_END_INFO_E:
 		ppdu_info->rx_status.rx_antenna =
 			HAL_RX_GET(rx_tlv, RXPCU_PPDU_END_INFO_2, RX_ANTENNA);
@@ -451,6 +455,7 @@
 		ppdu_info->rx_status.duration =
 			HAL_RX_GET(rx_tlv, UNIFIED_RXPCU_PPDU_END_INFO_8,
 				RX_PPDU_DURATION);
+		hal_rx_get_bb_info(hal_soc_hdl, rx_tlv, ppdu_info);
 		break;
 
 	/*
diff --git a/hal/wifi3.0/hal_internal.h b/hal/wifi3.0/hal_internal.h
index c2773ff..6d863f1 100644
--- a/hal/wifi3.0/hal_internal.h
+++ b/hal/wifi3.0/hal_internal.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -459,6 +459,8 @@
 					  uint32_t *flow_index);
 	uint16_t (*hal_rx_tlv_get_tcp_chksum)(uint8_t *buf);
 	uint16_t (*hal_rx_get_rx_sequence)(uint8_t *buf);
+	void (*hal_rx_get_bb_info)(void *rx_tlv, void *ppdu_info_handle);
+	void (*hal_rx_get_rtt_info)(void *rx_tlv, void *ppdu_info_handle);
 };
 
 /**
diff --git a/hal/wifi3.0/hal_rx.h b/hal/wifi3.0/hal_rx.h
index 430814b..2f8277b 100644
--- a/hal/wifi3.0/hal_rx.h
+++ b/hal/wifi3.0/hal_rx.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -3368,4 +3368,26 @@
 
 	return hal_soc->ops->hal_rx_get_rx_sequence(buf);
 }
+
+static inline void
+hal_rx_get_bb_info(hal_soc_handle_t hal_soc_hdl,
+		   void *rx_tlv,
+		   void *ppdu_info)
+{
+	struct hal_soc *hal_soc = (struct hal_soc *)hal_soc_hdl;
+
+	if (hal_soc->ops->hal_rx_get_bb_info)
+		hal_soc->ops->hal_rx_get_bb_info(rx_tlv, ppdu_info);
+}
+
+static inline void
+hal_rx_get_rtt_info(hal_soc_handle_t hal_soc_hdl,
+		    void *rx_tlv,
+		    void *ppdu_info)
+{
+	struct hal_soc *hal_soc = (struct hal_soc *)hal_soc_hdl;
+
+	if (hal_soc->ops->hal_rx_get_rtt_info)
+		hal_soc->ops->hal_rx_get_rtt_info(rx_tlv, ppdu_info);
+}
 #endif /* _HAL_RX_H */
diff --git a/hal/wifi3.0/qca6290/hal_6290.c b/hal/wifi3.0/qca6290/hal_6290.c
index a848e15..132dd76 100644
--- a/hal/wifi3.0/qca6290/hal_6290.c
+++ b/hal/wifi3.0/qca6290/hal_6290.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -1076,6 +1076,8 @@
 	hal_rx_msdu_get_flow_params_6290,
 	hal_rx_tlv_get_tcp_chksum_6290,
 	hal_rx_get_rx_sequence_6290,
+	NULL,
+	NULL,
 };
 
 struct hal_hw_srng_config hw_srng_table_6290[] = {
diff --git a/hal/wifi3.0/qca6390/hal_6390.c b/hal/wifi3.0/qca6390/hal_6390.c
index 56e7f3d..89dd612 100644
--- a/hal/wifi3.0/qca6390/hal_6390.c
+++ b/hal/wifi3.0/qca6390/hal_6390.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -1072,6 +1072,8 @@
 	hal_rx_msdu_get_flow_params_6390,
 	hal_rx_tlv_get_tcp_chksum_6390,
 	hal_rx_get_rx_sequence_6390,
+	NULL,
+	NULL,
 };
 
 struct hal_hw_srng_config hw_srng_table_6390[] = {
diff --git a/hal/wifi3.0/qca6490/hal_6490.c b/hal/wifi3.0/qca6490/hal_6490.c
index 7a349b0..6b889e1 100644
--- a/hal/wifi3.0/qca6490/hal_6490.c
+++ b/hal/wifi3.0/qca6490/hal_6490.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2019-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -1391,6 +1391,8 @@
 	NULL,
 	hal_rx_tlv_get_tcp_chksum_6490,
 	hal_rx_get_rx_sequence_6490,
+	NULL,
+	NULL,
 };
 
 struct hal_hw_srng_config hw_srng_table_6490[] = {
diff --git a/hal/wifi3.0/qca8074v1/hal_8074v1.c b/hal/wifi3.0/qca8074v1/hal_8074v1.c
index d758b1f..303da11 100644
--- a/hal/wifi3.0/qca8074v1/hal_8074v1.c
+++ b/hal/wifi3.0/qca8074v1/hal_8074v1.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -1072,6 +1072,8 @@
 	hal_rx_msdu_get_flow_params_8074v1,
 	hal_rx_tlv_get_tcp_chksum_8074v1,
 	hal_rx_get_rx_sequence_8074v1,
+	NULL,
+	NULL,
 };
 
 struct hal_hw_srng_config hw_srng_table_8074[] = {
diff --git a/hal/wifi3.0/qca8074v2/hal_8074v2.c b/hal/wifi3.0/qca8074v2/hal_8074v2.c
index 61f5cc7..6a3462a 100644
--- a/hal/wifi3.0/qca8074v2/hal_8074v2.c
+++ b/hal/wifi3.0/qca8074v2/hal_8074v2.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -1071,6 +1071,14 @@
 	hal_rx_msdu_get_flow_params_8074v2,
 	hal_rx_tlv_get_tcp_chksum_8074v2,
 	hal_rx_get_rx_sequence_8074v2,
+#if defined(QCA_WIFI_QCA6018) && defined(WLAN_CFR_ENABLE) && \
+	defined(WLAN_ENH_CFR_ENABLE)
+	hal_rx_get_bb_info_8074v2,
+	hal_rx_get_rtt_info_8074v2,
+#else
+	NULL,
+	NULL,
+#endif
 };
 
 struct hal_hw_srng_config hw_srng_table_8074v2[] = {
diff --git a/hal/wifi3.0/qca8074v2/hal_8074v2_rx.h b/hal/wifi3.0/qca8074v2/hal_8074v2_rx.h
index 2c7ed76..502808e 100644
--- a/hal/wifi3.0/qca8074v2/hal_8074v2_rx.h
+++ b/hal/wifi3.0/qca8074v2/hal_8074v2_rx.h
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -500,6 +500,51 @@
 }
 #endif
 
+#if defined(QCA_WIFI_QCA6018) && defined(WLAN_CFR_ENABLE) && \
+	defined(WLAN_ENH_CFR_ENABLE)
+static inline
+void hal_rx_get_bb_info_8074v2(void *rx_tlv,
+			       void *ppdu_info_hdl)
+{
+	struct hal_rx_ppdu_info *ppdu_info  = ppdu_info_hdl;
+
+	ppdu_info->cfr_info.bb_captured_channel =
+	  HAL_RX_GET(rx_tlv, RXPCU_PPDU_END_INFO_3, BB_CAPTURED_CHANNEL);
+
+	ppdu_info->cfr_info.bb_captured_timeout =
+	  HAL_RX_GET(rx_tlv, RXPCU_PPDU_END_INFO_3, BB_CAPTURED_TIMEOUT);
+
+	ppdu_info->cfr_info.bb_captured_reason =
+	  HAL_RX_GET(rx_tlv, RXPCU_PPDU_END_INFO_3, BB_CAPTURED_REASON);
+}
+
+static inline
+void hal_rx_get_rtt_info_8074v2(void *rx_tlv,
+				void *ppdu_info_hdl)
+{
+	struct hal_rx_ppdu_info *ppdu_info  = ppdu_info_hdl;
+
+	ppdu_info->cfr_info.rx_location_info_valid =
+		HAL_RX_GET(rx_tlv, PHYRX_PKT_END_13_RX_PKT_END_DETAILS,
+			   RX_LOCATION_INFO_DETAILS_RX_LOCATION_INFO_VALID);
+
+	ppdu_info->cfr_info.rtt_che_buffer_pointer_low32 =
+	HAL_RX_GET(rx_tlv,
+		   PHYRX_PKT_END_12_RX_PKT_END_DETAILS_RX_LOCATION_INFO_DETAILS,
+		   RTT_CHE_BUFFER_POINTER_LOW32);
+
+	ppdu_info->cfr_info.rtt_che_buffer_pointer_high8 =
+	HAL_RX_GET(rx_tlv,
+		   PHYRX_PKT_END_11_RX_PKT_END_DETAILS_RX_LOCATION_INFO_DETAILS,
+		   RTT_CHE_BUFFER_POINTER_HIGH8);
+
+	ppdu_info->cfr_info.chan_capture_status =
+	HAL_RX_GET(rx_tlv,
+		   PHYRX_PKT_END_13_RX_PKT_END_DETAILS_RX_LOCATION_INFO_DETAILS,
+		   RESERVED_8);
+}
+#endif
+
 /**
  * hal_rx_dump_msdu_start_tlv_8074v2() : dump RX msdu_start TLV in structured
  *			     human readable format.
diff --git a/hal/wifi3.0/qcn9000/hal_9000.c b/hal/wifi3.0/qcn9000/hal_9000.c
index 805acdd..c07ad16 100644
--- a/hal/wifi3.0/qcn9000/hal_9000.c
+++ b/hal/wifi3.0/qcn9000/hal_9000.c
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2016-2019 The Linux Foundation. All rights reserved.
+ * Copyright (c) 2016-2020 The Linux Foundation. All rights reserved.
  *
  * Permission to use, copy, modify, and/or distribute this software for
  * any purpose with or without fee is hereby granted, provided that the
@@ -1431,6 +1431,8 @@
 	hal_rx_msdu_get_flow_params_9000,
 	hal_rx_tlv_get_tcp_chksum_9000,
 	hal_rx_get_rx_sequence_9000,
+	NULL,
+	NULL,
 };
 
 struct hal_hw_srng_config hw_srng_table_9000[] = {