qcacmn: Fix for Unicast packet flow from WDS node in Intrabss

When EasyMesh feature is enabled, ARP replies from WDS node are
getting dropped by the AP, as there is no proper way to find the
DA_PEER with given WDS mac address.
Fix is to get the peer mac address for wds node based on ast entry.

CRs-Fixed: 3265158
Change-Id: I5ea890ce37dfde89d067b471417ba7aeb8c5d6f5
This commit is contained in:
Devender Kumar
2022-08-23 09:49:51 +05:30
committed by Madan Koyyalamudi
parent 5d150285fd
commit 13c6048f72

View File

@@ -3332,6 +3332,55 @@ static qdf_nbuf_t dp_ipa_intrabss_send(struct dp_pdev *pdev,
return NULL; return NULL;
} }
#ifdef IPA_WDS_EASYMESH_FEATURE
/**
* dp_ipa_peer_check() - Check for peer for given mac
* @soc: dp soc object
* @peer_mac_addr: peer mac address
* @vdev_id: vdev id
*
* Return: true if peer is found, else false
*/
static inline bool dp_ipa_peer_check(struct dp_soc *soc,
uint8_t *peer_mac_addr, uint8_t vdev_id)
{
struct cdp_ast_entry_info ast_info = {0};
ol_txrx_soc_handle cdp_soc;
struct dp_peer *peer = NULL;
cdp_soc = dp_soc_to_cdp_soc_t(soc);
cdp_peer_get_ast_info_by_soc(cdp_soc, peer_mac_addr, &ast_info);
peer = dp_peer_get_ref_by_id(soc, ast_info.peer_id, DP_MOD_ID_IPA);
if (!peer) {
return false;
} else {
if ((peer->vdev->vdev_id == vdev_id)) {
dp_peer_unref_delete(peer, DP_MOD_ID_IPA);
return true;
}
dp_peer_unref_delete(peer, DP_MOD_ID_IPA);
return false;
}
}
#else
static inline bool dp_ipa_peer_check(struct dp_soc *soc,
uint8_t *peer_mac_addr, uint8_t vdev_id)
{
struct dp_peer *peer = NULL;
peer = dp_peer_find_hash_find(soc, peer_mac_addr, 0, vdev_id,
DP_MOD_ID_IPA);
if (!peer) {
return false;
} else {
dp_peer_unref_delete(peer, DP_MOD_ID_IPA);
return true;
}
}
#endif
bool dp_ipa_rx_intrabss_fwd(struct cdp_soc_t *soc_hdl, uint8_t vdev_id, bool dp_ipa_rx_intrabss_fwd(struct cdp_soc_t *soc_hdl, uint8_t vdev_id,
qdf_nbuf_t nbuf, bool *fwd_success) qdf_nbuf_t nbuf, bool *fwd_success)
{ {
@@ -3339,8 +3388,6 @@ bool dp_ipa_rx_intrabss_fwd(struct cdp_soc_t *soc_hdl, uint8_t vdev_id,
struct dp_vdev *vdev = dp_vdev_get_ref_by_id(soc, vdev_id, struct dp_vdev *vdev = dp_vdev_get_ref_by_id(soc, vdev_id,
DP_MOD_ID_IPA); DP_MOD_ID_IPA);
struct dp_pdev *pdev; struct dp_pdev *pdev;
struct dp_peer *da_peer;
struct dp_peer *sa_peer;
qdf_nbuf_t nbuf_copy; qdf_nbuf_t nbuf_copy;
uint8_t da_is_bcmc; uint8_t da_is_bcmc;
struct ethhdr *eh; struct ethhdr *eh;
@@ -3385,20 +3432,12 @@ bool dp_ipa_rx_intrabss_fwd(struct cdp_soc_t *soc_hdl, uint8_t vdev_id,
if (!qdf_mem_cmp(eh->h_dest, vdev->mac_addr.raw, QDF_MAC_ADDR_SIZE)) if (!qdf_mem_cmp(eh->h_dest, vdev->mac_addr.raw, QDF_MAC_ADDR_SIZE))
goto out; goto out;
da_peer = dp_peer_find_hash_find(soc, eh->h_dest, 0, vdev->vdev_id, if (!dp_ipa_peer_check(soc, eh->h_dest, vdev->vdev_id))
DP_MOD_ID_IPA);
if (!da_peer)
goto out; goto out;
dp_peer_unref_delete(da_peer, DP_MOD_ID_IPA); if (!dp_ipa_peer_check(soc, eh->h_source, vdev->vdev_id))
sa_peer = dp_peer_find_hash_find(soc, eh->h_source, 0, vdev->vdev_id,
DP_MOD_ID_IPA);
if (!sa_peer)
goto out; goto out;
dp_peer_unref_delete(sa_peer, DP_MOD_ID_IPA);
/* /*
* In intra-bss forwarding scenario, skb is allocated by IPA driver. * In intra-bss forwarding scenario, skb is allocated by IPA driver.
* Need to add skb to internal tracking table to avoid nbuf memory * Need to add skb to internal tracking table to avoid nbuf memory