@@ -730,9 +730,8 @@ mt7996_mac_write_txwi_8023(struct mt7996_dev *dev, __le32 *txwi,
730730 u32 val ;
731731
732732 if (wcid -> sta ) {
733- struct ieee80211_sta * sta ;
733+ struct ieee80211_sta * sta = wcid_to_sta ( wcid ) ;
734734
735- sta = container_of ((void * )wcid , struct ieee80211_sta , drv_priv );
736735 wmm = sta -> wme ;
737736 }
738737
@@ -759,14 +758,17 @@ mt7996_mac_write_txwi_8023(struct mt7996_dev *dev, __le32 *txwi,
759758
760759static void
761760mt7996_mac_write_txwi_80211 (struct mt7996_dev * dev , __le32 * txwi ,
762- struct sk_buff * skb , struct ieee80211_key_conf * key )
761+ struct sk_buff * skb ,
762+ struct ieee80211_key_conf * key ,
763+ struct mt76_wcid * wcid )
763764{
764765 struct ieee80211_hdr * hdr = (struct ieee80211_hdr * )skb -> data ;
765766 struct ieee80211_mgmt * mgmt = (struct ieee80211_mgmt * )skb -> data ;
766767 struct ieee80211_tx_info * info = IEEE80211_SKB_CB (skb );
767768 bool multicast = is_multicast_ether_addr (hdr -> addr1 );
768769 u8 tid = skb -> priority & IEEE80211_QOS_CTL_TID_MASK ;
769770 __le16 fc = hdr -> frame_control , sc = hdr -> seq_ctrl ;
771+ u16 seqno = le16_to_cpu (sc );
770772 u8 fc_type , fc_stype ;
771773 u32 val ;
772774
@@ -816,9 +818,13 @@ mt7996_mac_write_txwi_80211(struct mt7996_dev *dev, __le32 *txwi,
816818 txwi [3 ] |= cpu_to_le32 (MT_TXD3_REM_TX_COUNT );
817819 }
818820
819- if (info -> flags & IEEE80211_TX_CTL_INJECTED ) {
820- u16 seqno = le16_to_cpu (sc );
821+ if (multicast && ieee80211_vif_is_mld (info -> control .vif )) {
822+ val = MT_TXD3_SN_VALID |
823+ FIELD_PREP (MT_TXD3_SEQ , IEEE80211_SEQ_TO_SN (seqno ));
824+ txwi [3 ] |= cpu_to_le32 (val );
825+ }
821826
827+ if (info -> flags & IEEE80211_TX_CTL_INJECTED ) {
822828 if (ieee80211_is_back_req (hdr -> frame_control )) {
823829 struct ieee80211_bar * bar ;
824830
@@ -831,6 +837,19 @@ mt7996_mac_write_txwi_80211(struct mt7996_dev *dev, __le32 *txwi,
831837 txwi [3 ] |= cpu_to_le32 (val );
832838 txwi [3 ] &= ~cpu_to_le32 (MT_TXD3_HW_AMSDU );
833839 }
840+
841+ if (ieee80211_vif_is_mld (info -> control .vif ) &&
842+ (multicast || unlikely (skb -> protocol == cpu_to_be16 (ETH_P_PAE ))))
843+ txwi [5 ] |= cpu_to_le32 (MT_TXD5_FL );
844+
845+ if (ieee80211_is_nullfunc (fc ) && ieee80211_has_a4 (fc ) &&
846+ ieee80211_vif_is_mld (info -> control .vif )) {
847+ txwi [5 ] |= cpu_to_le32 (MT_TXD5_FL );
848+ txwi [6 ] |= cpu_to_le32 (MT_TXD6_DIS_MAT );
849+ }
850+
851+ if (!wcid -> sta && ieee80211_is_mgmt (fc ))
852+ txwi [6 ] |= cpu_to_le32 (MT_TXD6_DIS_MAT );
834853}
835854
836855void mt7996_mac_write_txwi (struct mt7996_dev * dev , __le32 * txwi ,
@@ -846,20 +865,23 @@ void mt7996_mac_write_txwi(struct mt7996_dev *dev, __le32 *txwi,
846865 bool is_8023 = info -> flags & IEEE80211_TX_CTL_HW_80211_ENCAP ;
847866 struct mt76_vif_link * mlink = NULL ;
848867 struct mt7996_vif * mvif ;
868+ unsigned int link_id ;
849869 u16 tx_count = 15 ;
850870 u32 val ;
851871 bool inband_disc = !!(changed & (BSS_CHANGED_UNSOL_BCAST_PROBE_RESP |
852872 BSS_CHANGED_FILS_DISCOVERY ));
853873 bool beacon = !!(changed & (BSS_CHANGED_BEACON |
854874 BSS_CHANGED_BEACON_ENABLED )) && (!inband_disc );
855875
856- if (vif ) {
857- mvif = (struct mt7996_vif * )vif -> drv_priv ;
858- if (wcid -> offchannel )
859- mlink = rcu_dereference (mvif -> mt76 .offchannel_link );
860- if (!mlink )
861- mlink = & mvif -> deflink .mt76 ;
862- }
876+ if (wcid != & dev -> mt76 .global_wcid )
877+ link_id = wcid -> link_id ;
878+ else
879+ link_id = u32_get_bits (info -> control .flags ,
880+ IEEE80211_TX_CTRL_MLO_LINK );
881+
882+ mvif = vif ? (struct mt7996_vif * )vif -> drv_priv : NULL ;
883+ if (mvif )
884+ mlink = rcu_dereference (mvif -> mt76 .link [link_id ]);
863885
864886 if (mlink ) {
865887 omac_idx = mlink -> omac_idx ;
@@ -911,7 +933,10 @@ void mt7996_mac_write_txwi(struct mt7996_dev *dev, __le32 *txwi,
911933 val |= MT_TXD5_TX_STATUS_HOST ;
912934 txwi [5 ] = cpu_to_le32 (val );
913935
914- val = MT_TXD6_DIS_MAT | MT_TXD6_DAS ;
936+ val = MT_TXD6_DAS ;
937+ if (q_idx >= MT_LMAC_ALTX0 && q_idx <= MT_LMAC_BCN0 )
938+ val |= MT_TXD6_DIS_MAT ;
939+
915940 if (is_mt7996 (& dev -> mt76 ))
916941 val |= FIELD_PREP (MT_TXD6_MSDU_CNT , 1 );
917942 else if (is_8023 || !ieee80211_is_mgmt (hdr -> frame_control ))
@@ -923,7 +948,7 @@ void mt7996_mac_write_txwi(struct mt7996_dev *dev, __le32 *txwi,
923948 if (is_8023 )
924949 mt7996_mac_write_txwi_8023 (dev , txwi , skb , wcid );
925950 else
926- mt7996_mac_write_txwi_80211 (dev , txwi , skb , key );
951+ mt7996_mac_write_txwi_80211 (dev , txwi , skb , key , wcid );
927952
928953 if (txwi [1 ] & cpu_to_le32 (MT_TXD1_FIXED_RATE )) {
929954 bool mcast = ieee80211_is_data (hdr -> frame_control ) &&
@@ -940,6 +965,8 @@ void mt7996_mac_write_txwi(struct mt7996_dev *dev, __le32 *txwi,
940965 }
941966
942967 val = FIELD_PREP (MT_TXD6_TX_RATE , idx ) | MT_TXD6_FIXED_BW ;
968+ if (mcast )
969+ val |= MT_TXD6_DIS_MAT ;
943970 txwi [6 ] |= cpu_to_le32 (val );
944971 txwi [3 ] |= cpu_to_le32 (MT_TXD3_BA_DISABLE );
945972 }
0 commit comments