net: ethernet: mediatek: ppe: assign per-port queues for offloaded traffic
authorFelix Fietkau <nbd@nbd.name>
Wed, 16 Nov 2022 08:07:34 +0000 (09:07 +0100)
committerJakub Kicinski <kuba@kernel.org>
Sat, 19 Nov 2022 03:46:06 +0000 (19:46 -0800)
Keeps traffic sent to the switch within link speed limits

Signed-off-by: Felix Fietkau <nbd@nbd.name>
Link: https://lore.kernel.org/r/20221116080734.44013-7-nbd@nbd.name
Signed-off-by: Jakub Kicinski <kuba@kernel.org>
drivers/net/ethernet/mediatek/mtk_ppe.c
drivers/net/ethernet/mediatek/mtk_ppe.h
drivers/net/ethernet/mediatek/mtk_ppe_offload.c

index 3ee2bf53f9e58f3d8e0549ce339effb322ce576e..96ad0a9b79b4ec53e29633f178f302d9ea2f9a38 100644 (file)
@@ -399,6 +399,24 @@ int mtk_foe_entry_set_wdma(struct mtk_eth *eth, struct mtk_foe_entry *entry,
        return 0;
 }
 
+int mtk_foe_entry_set_queue(struct mtk_eth *eth, struct mtk_foe_entry *entry,
+                           unsigned int queue)
+{
+       u32 *ib2 = mtk_foe_entry_ib2(eth, entry);
+
+       if (MTK_HAS_CAPS(eth->soc->caps, MTK_NETSYS_V2)) {
+               *ib2 &= ~MTK_FOE_IB2_QID_V2;
+               *ib2 |= FIELD_PREP(MTK_FOE_IB2_QID_V2, queue);
+               *ib2 |= MTK_FOE_IB2_PSE_QOS_V2;
+       } else {
+               *ib2 &= ~MTK_FOE_IB2_QID;
+               *ib2 |= FIELD_PREP(MTK_FOE_IB2_QID, queue);
+               *ib2 |= MTK_FOE_IB2_PSE_QOS;
+       }
+
+       return 0;
+}
+
 static bool
 mtk_flow_entry_match(struct mtk_eth *eth, struct mtk_flow_entry *entry,
                     struct mtk_foe_entry *data)
index 0b7a67a958e4ca9d218ebf33b3e8a48503ff61ff..be635864bb969fe76515eb39e1ca5e4075931959 100644 (file)
@@ -68,7 +68,9 @@ enum {
 #define MTK_FOE_IB2_DSCP               GENMASK(31, 24)
 
 /* CONFIG_MEDIATEK_NETSYS_V2 */
+#define MTK_FOE_IB2_QID_V2                     GENMASK(6, 0)
 #define MTK_FOE_IB2_PORT_MG_V2         BIT(7)
+#define MTK_FOE_IB2_PSE_QOS_V2         BIT(8)
 #define MTK_FOE_IB2_DEST_PORT_V2       GENMASK(12, 9)
 #define MTK_FOE_IB2_MULTICAST_V2       BIT(13)
 #define MTK_FOE_IB2_WDMA_WINFO_V2      BIT(19)
@@ -350,6 +352,8 @@ int mtk_foe_entry_set_pppoe(struct mtk_eth *eth, struct mtk_foe_entry *entry,
                            int sid);
 int mtk_foe_entry_set_wdma(struct mtk_eth *eth, struct mtk_foe_entry *entry,
                           int wdma_idx, int txq, int bss, int wcid);
+int mtk_foe_entry_set_queue(struct mtk_eth *eth, struct mtk_foe_entry *entry,
+                           unsigned int queue);
 int mtk_foe_entry_commit(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
 void mtk_foe_entry_clear(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
 int mtk_foe_entry_idle_time(struct mtk_ppe *ppe, struct mtk_flow_entry *entry);
index 28bbd1df3e3059c3356f2b1d704602abf1ede7fd..81afd5ee3fbf171fde7b76310ae7126f9f8d3daa 100644 (file)
@@ -188,7 +188,7 @@ mtk_flow_set_output_device(struct mtk_eth *eth, struct mtk_foe_entry *foe,
                           int *wed_index)
 {
        struct mtk_wdma_info info = {};
-       int pse_port, dsa_port;
+       int pse_port, dsa_port, queue;
 
        if (mtk_flow_get_wdma_info(dev, dest_mac, &info) == 0) {
                mtk_foe_entry_set_wdma(eth, foe, info.wdma_idx, info.queue,
@@ -212,8 +212,6 @@ mtk_flow_set_output_device(struct mtk_eth *eth, struct mtk_foe_entry *foe,
        }
 
        dsa_port = mtk_flow_get_dsa_port(&dev);
-       if (dsa_port >= 0)
-               mtk_foe_entry_set_dsa(eth, foe, dsa_port);
 
        if (dev == eth->netdev[0])
                pse_port = 1;
@@ -222,6 +220,14 @@ mtk_flow_set_output_device(struct mtk_eth *eth, struct mtk_foe_entry *foe,
        else
                return -EOPNOTSUPP;
 
+       if (dsa_port >= 0) {
+               mtk_foe_entry_set_dsa(eth, foe, dsa_port);
+               queue = 3 + dsa_port;
+       } else {
+               queue = pse_port - 1;
+       }
+       mtk_foe_entry_set_queue(eth, foe, queue);
+
 out:
        mtk_foe_entry_set_pse_port(eth, foe, pse_port);