forked from ~ljy/RK356X_SDK_RELEASE

hc
2023-12-09 b22da3d8526a935aa31e086e63f60ff3246cb61c
kernel/drivers/net/ethernet/mellanox/mlx5/core/en_txrx.c
....@@ -32,7 +32,10 @@
3232
3333 #include <linux/irq.h>
3434 #include "en.h"
35
+#include "en/txrx.h"
3536 #include "en/xdp.h"
37
+#include "en/xsk/rx.h"
38
+#include "en/xsk/tx.h"
3639
3740 static inline bool mlx5e_channel_no_affinity_change(struct mlx5e_channel *c)
3841 {
....@@ -48,27 +51,66 @@
4851 static void mlx5e_handle_tx_dim(struct mlx5e_txqsq *sq)
4952 {
5053 struct mlx5e_sq_stats *stats = sq->stats;
51
- struct net_dim_sample dim_sample;
54
+ struct dim_sample dim_sample = {};
5255
5356 if (unlikely(!test_bit(MLX5E_SQ_STATE_AM, &sq->state)))
5457 return;
5558
56
- net_dim_sample(sq->cq.event_ctr, stats->packets, stats->bytes,
57
- &dim_sample);
59
+ dim_update_sample(sq->cq.event_ctr, stats->packets, stats->bytes, &dim_sample);
5860 net_dim(&sq->dim, dim_sample);
5961 }
6062
6163 static void mlx5e_handle_rx_dim(struct mlx5e_rq *rq)
6264 {
6365 struct mlx5e_rq_stats *stats = rq->stats;
64
- struct net_dim_sample dim_sample;
66
+ struct dim_sample dim_sample = {};
6567
6668 if (unlikely(!test_bit(MLX5E_RQ_STATE_AM, &rq->state)))
6769 return;
6870
69
- net_dim_sample(rq->cq.event_ctr, stats->packets, stats->bytes,
70
- &dim_sample);
71
+ dim_update_sample(rq->cq.event_ctr, stats->packets, stats->bytes, &dim_sample);
7172 net_dim(&rq->dim, dim_sample);
73
+}
74
+
75
+void mlx5e_trigger_irq(struct mlx5e_icosq *sq)
76
+{
77
+ struct mlx5_wq_cyc *wq = &sq->wq;
78
+ struct mlx5e_tx_wqe *nopwqe;
79
+ u16 pi = mlx5_wq_cyc_ctr2ix(wq, sq->pc);
80
+
81
+ sq->db.wqe_info[pi] = (struct mlx5e_icosq_wqe_info) {
82
+ .wqe_type = MLX5E_ICOSQ_WQE_NOP,
83
+ .num_wqebbs = 1,
84
+ };
85
+
86
+ nopwqe = mlx5e_post_nop(wq, sq->sqn, &sq->pc);
87
+ mlx5e_notify_hw(wq, sq->pc, sq->uar_map, &nopwqe->ctrl);
88
+}
89
+
90
+static bool mlx5e_napi_xsk_post(struct mlx5e_xdpsq *xsksq, struct mlx5e_rq *xskrq)
91
+{
92
+ bool busy_xsk = false, xsk_rx_alloc_err;
93
+
94
+ /* Handle the race between the application querying need_wakeup and the
95
+ * driver setting it:
96
+ * 1. Update need_wakeup both before and after the TX. If it goes to
97
+ * "yes", it can only happen with the first update.
98
+ * 2. If the application queried need_wakeup before we set it, the
99
+ * packets will be transmitted anyway, even w/o a wakeup.
100
+ * 3. Give a chance to clear need_wakeup after new packets were queued
101
+ * for TX.
102
+ */
103
+ mlx5e_xsk_update_tx_wakeup(xsksq);
104
+ busy_xsk |= mlx5e_xsk_tx(xsksq, MLX5E_TX_XSK_POLL_BUDGET);
105
+ mlx5e_xsk_update_tx_wakeup(xsksq);
106
+
107
+ xsk_rx_alloc_err = INDIRECT_CALL_2(xskrq->post_wqes,
108
+ mlx5e_post_rx_mpwqes,
109
+ mlx5e_post_rx_wqes,
110
+ xskrq);
111
+ busy_xsk |= mlx5e_xsk_update_rx_wakeup(xskrq, xsk_rx_alloc_err);
112
+
113
+ return busy_xsk;
72114 }
73115
74116 int mlx5e_napi_poll(struct napi_struct *napi, int budget)
....@@ -76,9 +118,19 @@
76118 struct mlx5e_channel *c = container_of(napi, struct mlx5e_channel,
77119 napi);
78120 struct mlx5e_ch_stats *ch_stats = c->stats;
121
+ struct mlx5e_xdpsq *xsksq = &c->xsksq;
122
+ struct mlx5e_rq *xskrq = &c->xskrq;
123
+ struct mlx5e_rq *rq = &c->rq;
124
+ bool aff_change = false;
125
+ bool busy_xsk = false;
79126 bool busy = false;
80127 int work_done = 0;
128
+ bool xsk_open;
81129 int i;
130
+
131
+ rcu_read_lock();
132
+
133
+ xsk_open = test_bit(MLX5E_CHANNEL_STATE_XSK, c->state);
82134
83135 ch_stats->poll++;
84136
....@@ -88,25 +140,49 @@
88140 busy |= mlx5e_poll_xdpsq_cq(&c->xdpsq.cq);
89141
90142 if (c->xdp)
91
- busy |= mlx5e_poll_xdpsq_cq(&c->rq.xdpsq.cq);
143
+ busy |= mlx5e_poll_xdpsq_cq(&c->rq_xdpsq.cq);
92144
93145 if (likely(budget)) { /* budget=0 means: don't poll rx rings */
94
- work_done = mlx5e_poll_rx_cq(&c->rq.cq, budget);
146
+ if (xsk_open)
147
+ work_done = mlx5e_poll_rx_cq(&xskrq->cq, budget);
148
+
149
+ if (likely(budget - work_done))
150
+ work_done += mlx5e_poll_rx_cq(&rq->cq, budget - work_done);
151
+
95152 busy |= work_done == budget;
96153 }
97154
98
- busy |= c->rq.post_wqes(&c->rq);
155
+ mlx5e_poll_ico_cq(&c->icosq.cq);
156
+ if (mlx5e_poll_ico_cq(&c->async_icosq.cq))
157
+ /* Don't clear the flag if nothing was polled to prevent
158
+ * queueing more WQEs and overflowing the async ICOSQ.
159
+ */
160
+ clear_bit(MLX5E_SQ_STATE_PENDING_XSK_TX, &c->async_icosq.state);
161
+
162
+ busy |= INDIRECT_CALL_2(rq->post_wqes,
163
+ mlx5e_post_rx_mpwqes,
164
+ mlx5e_post_rx_wqes,
165
+ rq);
166
+ if (xsk_open) {
167
+ busy |= mlx5e_poll_xdpsq_cq(&xsksq->cq);
168
+ busy_xsk |= mlx5e_napi_xsk_post(xsksq, xskrq);
169
+ }
170
+
171
+ busy |= busy_xsk;
99172
100173 if (busy) {
101
- if (likely(mlx5e_channel_no_affinity_change(c)))
102
- return budget;
174
+ if (likely(mlx5e_channel_no_affinity_change(c))) {
175
+ work_done = budget;
176
+ goto out;
177
+ }
103178 ch_stats->aff_change++;
179
+ aff_change = true;
104180 if (budget && work_done == budget)
105181 work_done--;
106182 }
107183
108184 if (unlikely(!napi_complete_done(napi, work_done)))
109
- return work_done;
185
+ goto out;
110186
111187 ch_stats->arm++;
112188
....@@ -115,16 +191,31 @@
115191 mlx5e_cq_arm(&c->sq[i].cq);
116192 }
117193
118
- mlx5e_handle_rx_dim(&c->rq);
194
+ mlx5e_handle_rx_dim(rq);
119195
120
- mlx5e_cq_arm(&c->rq.cq);
196
+ mlx5e_cq_arm(&rq->cq);
121197 mlx5e_cq_arm(&c->icosq.cq);
198
+ mlx5e_cq_arm(&c->async_icosq.cq);
122199 mlx5e_cq_arm(&c->xdpsq.cq);
200
+
201
+ if (xsk_open) {
202
+ mlx5e_handle_rx_dim(xskrq);
203
+ mlx5e_cq_arm(&xsksq->cq);
204
+ mlx5e_cq_arm(&xskrq->cq);
205
+ }
206
+
207
+ if (unlikely(aff_change && busy_xsk)) {
208
+ mlx5e_trigger_irq(&c->icosq);
209
+ ch_stats->force_irq++;
210
+ }
211
+
212
+out:
213
+ rcu_read_unlock();
123214
124215 return work_done;
125216 }
126217
127
-void mlx5e_completion_event(struct mlx5_core_cq *mcq)
218
+void mlx5e_completion_event(struct mlx5_core_cq *mcq, struct mlx5_eqe *eqe)
128219 {
129220 struct mlx5e_cq *cq = container_of(mcq, struct mlx5e_cq, mcq);
130221