net/sched: mqprio: refactor offloading and unoffloading to dedicated functions
authorVladimir Oltean <vladimir.oltean@nxp.com>
Sat, 4 Feb 2023 13:52:56 +0000 (15:52 +0200)
committerDavid S. Miller <davem@davemloft.net>
Mon, 6 Feb 2023 10:06:43 +0000 (10:06 +0000)
Some more logic will be added to mqprio offloading, so split that code
up from mqprio_init(), which is already large, and create a new
function, mqprio_enable_offload(), similar to taprio_enable_offload().
Also create the opposite function mqprio_disable_offload().

Signed-off-by: Vladimir Oltean <vladimir.oltean@nxp.com>
Reviewed-by: Jacob Keller <jacob.e.keller@intel.com>
Reviewed-by: Simon Horman <simon.horman@corigine.com>
Signed-off-by: David S. Miller <davem@davemloft.net>
net/sched/sch_mqprio.c

index d2d8a02ded058333165571d16433ed397432ed72..3579a64da06e94555bba96afe416e2f380bbc72c 100644 (file)
@@ -27,6 +27,61 @@ struct mqprio_sched {
        u64 max_rate[TC_QOPT_MAX_QUEUE];
 };
 
+static int mqprio_enable_offload(struct Qdisc *sch,
+                                const struct tc_mqprio_qopt *qopt)
+{
+       struct tc_mqprio_qopt_offload mqprio = {.qopt = *qopt};
+       struct mqprio_sched *priv = qdisc_priv(sch);
+       struct net_device *dev = qdisc_dev(sch);
+       int err, i;
+
+       switch (priv->mode) {
+       case TC_MQPRIO_MODE_DCB:
+               if (priv->shaper != TC_MQPRIO_SHAPER_DCB)
+                       return -EINVAL;
+               break;
+       case TC_MQPRIO_MODE_CHANNEL:
+               mqprio.flags = priv->flags;
+               if (priv->flags & TC_MQPRIO_F_MODE)
+                       mqprio.mode = priv->mode;
+               if (priv->flags & TC_MQPRIO_F_SHAPER)
+                       mqprio.shaper = priv->shaper;
+               if (priv->flags & TC_MQPRIO_F_MIN_RATE)
+                       for (i = 0; i < mqprio.qopt.num_tc; i++)
+                               mqprio.min_rate[i] = priv->min_rate[i];
+               if (priv->flags & TC_MQPRIO_F_MAX_RATE)
+                       for (i = 0; i < mqprio.qopt.num_tc; i++)
+                               mqprio.max_rate[i] = priv->max_rate[i];
+               break;
+       default:
+               return -EINVAL;
+       }
+
+       err = dev->netdev_ops->ndo_setup_tc(dev, TC_SETUP_QDISC_MQPRIO,
+                                           &mqprio);
+       if (err)
+               return err;
+
+       priv->hw_offload = mqprio.qopt.hw;
+
+       return 0;
+}
+
+static void mqprio_disable_offload(struct Qdisc *sch)
+{
+       struct tc_mqprio_qopt_offload mqprio = { { 0 } };
+       struct mqprio_sched *priv = qdisc_priv(sch);
+       struct net_device *dev = qdisc_dev(sch);
+
+       switch (priv->mode) {
+       case TC_MQPRIO_MODE_DCB:
+       case TC_MQPRIO_MODE_CHANNEL:
+               dev->netdev_ops->ndo_setup_tc(dev, TC_SETUP_QDISC_MQPRIO,
+                                             &mqprio);
+               break;
+       }
+}
+
 static void mqprio_destroy(struct Qdisc *sch)
 {
        struct net_device *dev = qdisc_dev(sch);
@@ -41,22 +96,10 @@ static void mqprio_destroy(struct Qdisc *sch)
                kfree(priv->qdiscs);
        }
 
-       if (priv->hw_offload && dev->netdev_ops->ndo_setup_tc) {
-               struct tc_mqprio_qopt_offload mqprio = { { 0 } };
-
-               switch (priv->mode) {
-               case TC_MQPRIO_MODE_DCB:
-               case TC_MQPRIO_MODE_CHANNEL:
-                       dev->netdev_ops->ndo_setup_tc(dev,
-                                                     TC_SETUP_QDISC_MQPRIO,
-                                                     &mqprio);
-                       break;
-               default:
-                       return;
-               }
-       } else {
+       if (priv->hw_offload && dev->netdev_ops->ndo_setup_tc)
+               mqprio_disable_offload(sch);
+       else
                netdev_set_num_tc(dev, 0);
-       }
 }
 
 static int mqprio_parse_opt(struct net_device *dev, struct tc_mqprio_qopt *qopt)
@@ -253,36 +296,9 @@ static int mqprio_init(struct Qdisc *sch, struct nlattr *opt,
         * supplied and verified mapping
         */
        if (qopt->hw) {
-               struct tc_mqprio_qopt_offload mqprio = {.qopt = *qopt};
-
-               switch (priv->mode) {
-               case TC_MQPRIO_MODE_DCB:
-                       if (priv->shaper != TC_MQPRIO_SHAPER_DCB)
-                               return -EINVAL;
-                       break;
-               case TC_MQPRIO_MODE_CHANNEL:
-                       mqprio.flags = priv->flags;
-                       if (priv->flags & TC_MQPRIO_F_MODE)
-                               mqprio.mode = priv->mode;
-                       if (priv->flags & TC_MQPRIO_F_SHAPER)
-                               mqprio.shaper = priv->shaper;
-                       if (priv->flags & TC_MQPRIO_F_MIN_RATE)
-                               for (i = 0; i < mqprio.qopt.num_tc; i++)
-                                       mqprio.min_rate[i] = priv->min_rate[i];
-                       if (priv->flags & TC_MQPRIO_F_MAX_RATE)
-                               for (i = 0; i < mqprio.qopt.num_tc; i++)
-                                       mqprio.max_rate[i] = priv->max_rate[i];
-                       break;
-               default:
-                       return -EINVAL;
-               }
-               err = dev->netdev_ops->ndo_setup_tc(dev,
-                                                   TC_SETUP_QDISC_MQPRIO,
-                                                   &mqprio);
+               err = mqprio_enable_offload(sch, qopt);
                if (err)
                        return err;
-
-               priv->hw_offload = mqprio.qopt.hw;
        } else {
                netdev_set_num_tc(dev, qopt->num_tc);
                for (i = 0; i < qopt->num_tc; i++)