xref: /linux/drivers/net/dsa/microchip/ksz_dcb.c (revision cbc7afffc5ec581d3781c49fe9c8e8c661e5217b)
1 // SPDX-License-Identifier: GPL-2.0
2 // Copyright (c) 2024 Pengutronix, Oleksij Rempel <kernel@pengutronix.de>
3 
4 #include <linux/dsa/ksz_common.h>
5 #include <net/dsa.h>
6 #include <net/dscp.h>
7 #include <net/ieee8021q.h>
8 
9 #include "ksz_common.h"
10 #include "ksz_dcb.h"
11 #include "ksz8.h"
12 
13 #define KSZ8_REG_PORT_1_CTRL_0			0x10
14 #define KSZ8_PORT_DIFFSERV_ENABLE		BIT(6)
15 #define KSZ8_PORT_802_1P_ENABLE			BIT(5)
16 #define KSZ8_PORT_BASED_PRIO_M			GENMASK(4, 3)
17 
18 #define KSZ88X3_REG_TOS_DSCP_CTRL		0x60
19 #define KSZ8765_REG_TOS_DSCP_CTRL		0x90
20 
21 #define KSZ9477_REG_SW_MAC_TOS_CTRL		0x033e
22 #define KSZ9477_SW_TOS_DSCP_REMAP		BIT(0)
23 #define KSZ9477_SW_TOS_DSCP_DEFAULT_PRIO_M	GENMASK(5, 3)
24 
25 #define KSZ9477_REG_DIFFSERV_PRIO_MAP		0x0340
26 
27 #define KSZ9477_REG_PORT_MRI_PRIO_CTRL		0x0801
28 #define KSZ9477_PORT_HIGHEST_PRIO		BIT(7)
29 #define KSZ9477_PORT_OR_PRIO			BIT(6)
30 #define KSZ9477_PORT_MAC_PRIO_ENABLE		BIT(4)
31 #define KSZ9477_PORT_VLAN_PRIO_ENABLE		BIT(3)
32 #define KSZ9477_PORT_802_1P_PRIO_ENABLE		BIT(2)
33 #define KSZ9477_PORT_DIFFSERV_PRIO_ENABLE	BIT(1)
34 #define KSZ9477_PORT_ACL_PRIO_ENABLE		BIT(0)
35 
36 #define KSZ9477_REG_PORT_MRI_MAC_CTRL		0x0802
37 #define KSZ9477_PORT_BASED_PRIO_M		GENMASK(2, 0)
38 
39 struct ksz_apptrust_map {
40 	u8 apptrust;
41 	u8 bit;
42 };
43 
44 static const struct ksz_apptrust_map ksz8_apptrust_map_to_bit[] = {
45 	{ DCB_APP_SEL_PCP, KSZ8_PORT_802_1P_ENABLE },
46 	{ IEEE_8021QAZ_APP_SEL_DSCP, KSZ8_PORT_DIFFSERV_ENABLE },
47 };
48 
49 static const struct ksz_apptrust_map ksz9477_apptrust_map_to_bit[] = {
50 	{ DCB_APP_SEL_PCP, KSZ9477_PORT_802_1P_PRIO_ENABLE },
51 	{ IEEE_8021QAZ_APP_SEL_DSCP, KSZ9477_PORT_DIFFSERV_PRIO_ENABLE },
52 };
53 
54 /* ksz_supported_apptrust[] - Supported apptrust selectors and Priority Order
55  *			      of Internal Priority Value (IPV) sources.
56  *
57  * This array defines the apptrust selectors supported by the hardware, where
58  * the index within the array indicates the priority of the selector - lower
59  * indices correspond to higher priority. This fixed priority scheme is due to
60  * the hardware's design, which does not support configurable priority among
61  * different priority sources.
62  *
63  * The priority sources, including Tail Tag, ACL, VLAN PCP and DSCP are ordered
64  * by the hardware's fixed logic, as detailed below. The order reflects a
65  * non-configurable precedence where certain types of priority information
66  * override others:
67  *
68  * 1. Tail Tag - Highest priority, overrides ACL, VLAN PCP, and DSCP priorities.
69  * 2. ACL - Overrides VLAN PCP and DSCP priorities.
70  * 3. VLAN PCP - Overrides DSCP priority.
71  * 4. DSCP - Lowest priority, does not override any other priority source.
72  *
73  * In this context, the array's lower index (higher priority) for
74  * 'DCB_APP_SEL_PCP' suggests its relative priority over
75  * 'IEEE_8021QAZ_APP_SEL_DSCP' within the system's fixed priority scheme.
76  *
77  * DCB_APP_SEL_PCP - Priority Code Point selector
78  * IEEE_8021QAZ_APP_SEL_DSCP - Differentiated Services Code Point selector
79  */
80 static const u8 ksz_supported_apptrust[] = {
81 	DCB_APP_SEL_PCP,
82 	IEEE_8021QAZ_APP_SEL_DSCP,
83 };
84 
85 static const u8 ksz8_port2_supported_apptrust[] = {
86 	DCB_APP_SEL_PCP,
87 };
88 
89 static const char * const ksz_supported_apptrust_variants[] = {
90 	"empty", "dscp", "pcp", "dscp pcp"
91 };
92 
93 static void ksz_get_default_port_prio_reg(struct ksz_device *dev, int *reg,
94 					  u8 *mask, int *shift)
95 {
96 	if (is_ksz8(dev)) {
97 		*reg = KSZ8_REG_PORT_1_CTRL_0;
98 		*mask = KSZ8_PORT_BASED_PRIO_M;
99 		*shift = __bf_shf(KSZ8_PORT_BASED_PRIO_M);
100 	} else {
101 		*reg = KSZ9477_REG_PORT_MRI_MAC_CTRL;
102 		*mask = KSZ9477_PORT_BASED_PRIO_M;
103 		*shift = __bf_shf(KSZ9477_PORT_BASED_PRIO_M);
104 	}
105 }
106 
107 /**
108  * ksz_get_dscp_prio_reg - Retrieves the DSCP-to-priority-mapping register
109  * @dev: Pointer to the KSZ switch device structure
110  * @reg: Pointer to the register address to be set
111  * @per_reg: Pointer to the number of DSCP values per register
112  * @mask: Pointer to the mask to be set
113  *
114  * This function retrieves the DSCP to priority mapping register, the number of
115  * DSCP values per register, and the mask to be set.
116  */
117 static void ksz_get_dscp_prio_reg(struct ksz_device *dev, int *reg,
118 				  int *per_reg, u8 *mask)
119 {
120 	if (ksz_is_ksz87xx(dev)) {
121 		*reg = KSZ8765_REG_TOS_DSCP_CTRL;
122 		*per_reg = 4;
123 		*mask = GENMASK(1, 0);
124 	} else if (ksz_is_ksz88x3(dev)) {
125 		*reg = KSZ88X3_REG_TOS_DSCP_CTRL;
126 		*per_reg = 4;
127 		*mask = GENMASK(1, 0);
128 	} else {
129 		*reg = KSZ9477_REG_DIFFSERV_PRIO_MAP;
130 		*per_reg = 2;
131 		*mask = GENMASK(2, 0);
132 	}
133 }
134 
135 /**
136  * ksz_get_apptrust_map_and_reg - Retrieves the apptrust map and register
137  * @dev: Pointer to the KSZ switch device structure
138  * @map: Pointer to the apptrust map to be set
139  * @reg: Pointer to the register address to be set
140  * @mask: Pointer to the mask to be set
141  *
142  * This function retrieves the apptrust map and register address for the
143  * apptrust configuration.
144  */
145 static void ksz_get_apptrust_map_and_reg(struct ksz_device *dev,
146 					 const struct ksz_apptrust_map **map,
147 					 int *reg, u8 *mask)
148 {
149 	if (is_ksz8(dev)) {
150 		*map = ksz8_apptrust_map_to_bit;
151 		*reg = KSZ8_REG_PORT_1_CTRL_0;
152 		*mask = KSZ8_PORT_DIFFSERV_ENABLE | KSZ8_PORT_802_1P_ENABLE;
153 	} else {
154 		*map = ksz9477_apptrust_map_to_bit;
155 		*reg = KSZ9477_REG_PORT_MRI_PRIO_CTRL;
156 		*mask = KSZ9477_PORT_802_1P_PRIO_ENABLE |
157 			KSZ9477_PORT_DIFFSERV_PRIO_ENABLE;
158 	}
159 }
160 
161 /**
162  * ksz_port_get_default_prio - Retrieves the default priority for a port on a
163  *			       KSZ switch
164  * @ds: Pointer to the DSA switch structure
165  * @port: Port number from which to get the default priority
166  *
167  * This function fetches the default priority for the specified port on a KSZ
168  * switch.
169  *
170  * Return: The default priority of the port on success, or a negative error
171  * code on failure.
172  */
173 int ksz_port_get_default_prio(struct dsa_switch *ds, int port)
174 {
175 	struct ksz_device *dev = ds->priv;
176 	int ret, reg, shift;
177 	u8 data, mask;
178 
179 	ksz_get_default_port_prio_reg(dev, &reg, &mask, &shift);
180 
181 	ret = ksz_pread8(dev, port, reg, &data);
182 	if (ret)
183 		return ret;
184 
185 	return (data & mask) >> shift;
186 }
187 
188 /**
189  * ksz88x3_port_set_default_prio_quirks - Quirks for default priority
190  * @dev: Pointer to the KSZ switch device structure
191  * @port: Port number for which to set the default priority
192  * @prio: Priority value to set
193  *
194  * This function implements quirks for setting the default priority on KSZ88x3
195  * devices. On Port 2, no other priority providers are working
196  * except of PCP. So, configuring default priority on Port 2 is not possible.
197  * On Port 1, it is not possible to configure port priority if PCP
198  * apptrust on Port 2 is disabled. Since we disable multiple queues on the
199  * switch to disable PCP on Port 2, we need to ensure that the default priority
200  * configuration on Port 1 is in agreement with the configuration on Port 2.
201  *
202  * Return: 0 on success, or a negative error code on failure
203  */
204 static int ksz88x3_port_set_default_prio_quirks(struct ksz_device *dev, int port,
205 						u8 prio)
206 {
207 	if (!prio)
208 		return 0;
209 
210 	if (port == KSZ_PORT_2) {
211 		dev_err(dev->dev, "Port priority configuration is not working on Port 2\n");
212 		return -EINVAL;
213 	} else if (port == KSZ_PORT_1) {
214 		u8 port2_data;
215 		int ret;
216 
217 		ret = ksz_pread8(dev, KSZ_PORT_2, KSZ8_REG_PORT_1_CTRL_0,
218 				 &port2_data);
219 		if (ret)
220 			return ret;
221 
222 		if (!(port2_data & KSZ8_PORT_802_1P_ENABLE)) {
223 			dev_err(dev->dev, "Not possible to configur port priority on Port 1 if PCP apptrust on Port 2 is disabled\n");
224 			return -EINVAL;
225 		}
226 	}
227 
228 	return 0;
229 }
230 
231 /**
232  * ksz_port_set_default_prio - Sets the default priority for a port on a KSZ
233  *			       switch
234  * @ds: Pointer to the DSA switch structure
235  * @port: Port number for which to set the default priority
236  * @prio: Priority value to set
237  *
238  * This function sets the default priority for the specified port on a KSZ
239  * switch.
240  *
241  * Return: 0 on success, or a negative error code on failure.
242  */
243 int ksz_port_set_default_prio(struct dsa_switch *ds, int port, u8 prio)
244 {
245 	struct ksz_device *dev = ds->priv;
246 	int reg, shift, ret;
247 	u8 mask;
248 
249 	if (prio >= dev->info->num_ipvs)
250 		return -EINVAL;
251 
252 	if (ksz_is_ksz88x3(dev)) {
253 		ret = ksz88x3_port_set_default_prio_quirks(dev, port, prio);
254 		if (ret)
255 			return ret;
256 	}
257 
258 	ksz_get_default_port_prio_reg(dev, &reg, &mask, &shift);
259 
260 	return ksz_prmw8(dev, port, reg, mask, (prio << shift) & mask);
261 }
262 
263 /**
264  * ksz_port_get_dscp_prio - Retrieves the priority for a DSCP value on a KSZ
265  *			    switch
266  * @ds: Pointer to the DSA switch structure
267  * @port: Port number for which to get the priority
268  * @dscp: DSCP value for which to get the priority
269  *
270  * This function fetches the priority value from switch global DSCP-to-priorty
271  * mapping table for the specified DSCP value.
272  *
273  * Return: The priority value for the DSCP on success, or a negative error
274  * code on failure.
275  */
276 int ksz_port_get_dscp_prio(struct dsa_switch *ds, int port, u8 dscp)
277 {
278 	struct ksz_device *dev = ds->priv;
279 	int reg, per_reg, ret, shift;
280 	u8 data, mask;
281 
282 	ksz_get_dscp_prio_reg(dev, &reg, &per_reg, &mask);
283 
284 	/* If DSCP remapping is disabled, DSCP bits 3-5 are used as Internal
285 	 * Priority Value (IPV)
286 	 */
287 	if (!is_ksz8(dev)) {
288 		ret = ksz_read8(dev, KSZ9477_REG_SW_MAC_TOS_CTRL, &data);
289 		if (ret)
290 			return ret;
291 
292 		/* If DSCP remapping is disabled, DSCP bits 3-5 are used as
293 		 * Internal Priority Value (IPV)
294 		 */
295 		if (!(data & KSZ9477_SW_TOS_DSCP_REMAP))
296 			return FIELD_GET(KSZ9477_SW_TOS_DSCP_DEFAULT_PRIO_M,
297 					 dscp);
298 	}
299 
300 	/* In case DSCP remapping is enabled, we need to write the DSCP to
301 	 * priority mapping table.
302 	 */
303 	reg += dscp / per_reg;
304 	ret = ksz_read8(dev, reg, &data);
305 	if (ret)
306 		return ret;
307 
308 	shift = (dscp % per_reg) * (8 / per_reg);
309 
310 	return (data >> shift) & mask;
311 }
312 
313 static int ksz_set_global_dscp_entry(struct ksz_device *dev, u8 dscp, u8 ipv)
314 {
315 	int reg, per_reg, shift;
316 	u8 mask;
317 
318 	ksz_get_dscp_prio_reg(dev, &reg, &per_reg, &mask);
319 
320 	shift = (dscp % per_reg) * (8 / per_reg);
321 
322 	return ksz_rmw8(dev, reg + (dscp / per_reg), mask << shift,
323 			ipv << shift);
324 }
325 
326 /**
327  * ksz_init_global_dscp_map - Initializes the global DSCP-to-priority mapping
328  * @dev: Pointer to the KSZ switch device structure
329  *
330  * This function initializes the global DSCP-to-priority mapping table for the
331  * switch.
332  *
333  * Return: 0 on success, or a negative error code on failure
334  */
335 static int ksz_init_global_dscp_map(struct ksz_device *dev)
336 {
337 	int ret, dscp;
338 
339 	/* On KSZ9xxx variants, DSCP remapping is disabled by default.
340 	 * Enable to have, predictable and reproducible behavior across
341 	 * different devices.
342 	 */
343 	if (!is_ksz8(dev)) {
344 		ret = ksz_rmw8(dev, KSZ9477_REG_SW_MAC_TOS_CTRL,
345 			       KSZ9477_SW_TOS_DSCP_REMAP,
346 			       KSZ9477_SW_TOS_DSCP_REMAP);
347 		if (ret)
348 			return ret;
349 	}
350 
351 	for (dscp = 0; dscp < DSCP_MAX; dscp++) {
352 		int ipv, tt;
353 
354 		/* Map DSCP to Traffic Type, which is corresponding to the
355 		 * Internal Priority Value (IPV) in the switch.
356 		 */
357 		if (!is_ksz8(dev)) {
358 			ipv = ietf_dscp_to_ieee8021q_tt(dscp);
359 		} else {
360 			/* On KSZ8xxx variants we do not have IPV to queue
361 			 * remapping table. We need to convert DSCP to Traffic
362 			 * Type and then to queue.
363 			 */
364 			tt = ietf_dscp_to_ieee8021q_tt(dscp);
365 			if (tt < 0)
366 				return tt;
367 
368 			ipv = ieee8021q_tt_to_tc(tt, dev->info->num_tx_queues);
369 		}
370 
371 		if (ipv < 0)
372 			return ipv;
373 
374 		ret = ksz_set_global_dscp_entry(dev, dscp, ipv);
375 	}
376 
377 	return 0;
378 }
379 
380 int ksz_port_add_dscp_prio(struct dsa_switch *ds, int port, u8 dscp, u8 prio)
381 {
382 	struct ksz_device *dev = ds->priv;
383 
384 	if (prio >= dev->info->num_ipvs)
385 		return -ERANGE;
386 
387 	return ksz_set_global_dscp_entry(dev, dscp, prio);
388 }
389 
390 int ksz_port_del_dscp_prio(struct dsa_switch *ds, int port, u8 dscp, u8 prio)
391 {
392 	struct ksz_device *dev = ds->priv;
393 	int ipv;
394 
395 	if (ksz_port_get_dscp_prio(ds, port, dscp) != prio)
396 		return 0;
397 
398 	if (is_ksz8(dev)) {
399 		ipv = ieee8021q_tt_to_tc(IEEE8021Q_TT_BE,
400 					 dev->info->num_tx_queues);
401 		if (ipv < 0)
402 			return ipv;
403 	} else {
404 		ipv = IEEE8021Q_TT_BE;
405 	}
406 
407 	return ksz_set_global_dscp_entry(dev, dscp, ipv);
408 }
409 
410 /**
411  * ksz_apptrust_error - Prints an error message for an invalid apptrust selector
412  * @dev: Pointer to the KSZ switch device structure
413  *
414  * This function prints an error message when an invalid apptrust selector is
415  * provided.
416  */
417 static void ksz_apptrust_error(struct ksz_device *dev)
418 {
419 	char supported_apptrust_variants[64];
420 	int i;
421 
422 	supported_apptrust_variants[0] = '\0';
423 	for (i = 0; i < ARRAY_SIZE(ksz_supported_apptrust_variants); i++) {
424 		if (i > 0)
425 			strlcat(supported_apptrust_variants, ", ",
426 				sizeof(supported_apptrust_variants));
427 		strlcat(supported_apptrust_variants,
428 			ksz_supported_apptrust_variants[i],
429 			sizeof(supported_apptrust_variants));
430 	}
431 
432 	dev_err(dev->dev, "Invalid apptrust selector or priority order. Supported: %s\n",
433 		supported_apptrust_variants);
434 }
435 
436 /**
437  * ksz_port_set_apptrust_validate - Validates the apptrust selectors
438  * @dev: Pointer to the KSZ switch device structure
439  * @port: Port number for which to set the apptrust selectors
440  * @sel: Array of apptrust selectors to validate
441  * @nsel: Number of apptrust selectors in the array
442  *
443  * This function validates the apptrust selectors provided and ensures that
444  * they are in the correct order.
445  *
446  * This family of switches supports two apptrust selectors: DCB_APP_SEL_PCP and
447  * IEEE_8021QAZ_APP_SEL_DSCP. The priority order of the selectors is fixed and
448  * cannot be changed. The order is as follows:
449  * 1. DCB_APP_SEL_PCP - Priority Code Point selector (highest priority)
450  * 2. IEEE_8021QAZ_APP_SEL_DSCP - Differentiated Services Code Point selector
451  *   (lowest priority)
452  *
453  * Return: 0 on success, or a negative error code on failure
454  */
455 static int ksz_port_set_apptrust_validate(struct ksz_device *dev, int port,
456 					  const u8 *sel, int nsel)
457 {
458 	int i, j, found;
459 	int j_prev = 0;
460 
461 	/* Iterate through the requested selectors */
462 	for (i = 0; i < nsel; i++) {
463 		found = 0;
464 
465 		/* Check if the current selector is supported by the hardware */
466 		for (j = 0; j < sizeof(ksz_supported_apptrust); j++) {
467 			if (sel[i] != ksz_supported_apptrust[j])
468 				continue;
469 
470 			found = 1;
471 
472 			/* Ensure that no higher priority selector (lower index)
473 			 * precedes a lower priority one
474 			 */
475 			if (i > 0 && j <= j_prev)
476 				goto err_sel_not_vaild;
477 
478 			j_prev = j;
479 			break;
480 		}
481 
482 		if (!found)
483 			goto err_sel_not_vaild;
484 	}
485 
486 	return 0;
487 
488 err_sel_not_vaild:
489 	ksz_apptrust_error(dev);
490 
491 	return -EINVAL;
492 }
493 
494 /**
495  * ksz88x3_port1_apptrust_quirk - Quirk for apptrust configuration on Port 1
496  *				  of KSZ88x3 devices
497  * @dev: Pointer to the KSZ switch device structure
498  * @port: Port number for which to set the apptrust selectors
499  * @reg: Register address for the apptrust configuration
500  * @port1_data: Data to set for the apptrust configuration
501  *
502  * This function implements a quirk for apptrust configuration on Port 1 of
503  * KSZ88x3 devices. It ensures that apptrust configuration on Port 1 is not
504  * possible if PCP apptrust on Port 2 is disabled. This is because the Port 2
505  * seems to be permanently hardwired to PCP classification, so we need to
506  * do Port 1 configuration always in agreement with Port 2 configuration.
507  *
508  * Return: 0 on success, or a negative error code on failure
509  */
510 static int ksz88x3_port1_apptrust_quirk(struct ksz_device *dev, int port,
511 					int reg, u8 port1_data)
512 {
513 	u8 port2_data;
514 	int ret;
515 
516 	/* If no apptrust is requested for Port 1, no need to care about Port 2
517 	 * configuration.
518 	 */
519 	if (!(port1_data & (KSZ8_PORT_802_1P_ENABLE | KSZ8_PORT_DIFFSERV_ENABLE)))
520 		return 0;
521 
522 	/* We got request to enable any apptrust on Port 1. To make it possible,
523 	 * we need to enable multiple queues on the switch. If we enable
524 	 * multiqueue support, PCP classification on Port 2 will be
525 	 * automatically activated by HW.
526 	 */
527 	ret = ksz_pread8(dev, KSZ_PORT_2, reg, &port2_data);
528 	if (ret)
529 		return ret;
530 
531 	/* If KSZ8_PORT_802_1P_ENABLE bit is set on Port 2, the driver showed
532 	 * the interest in PCP classification on Port 2. In this case,
533 	 * multiqueue support is enabled and we can enable any apptrust on
534 	 * Port 1.
535 	 * If KSZ8_PORT_802_1P_ENABLE bit is not set on Port 2, the PCP
536 	 * classification on Port 2 is still active, but the driver disabled
537 	 * multiqueue support and made frame prioritization inactive for
538 	 * all ports. In this case, we can't enable any apptrust on Port 1.
539 	 */
540 	if (!(port2_data & KSZ8_PORT_802_1P_ENABLE)) {
541 		dev_err(dev->dev, "Not possible to enable any apptrust on Port 1 if PCP apptrust on Port 2 is disabled\n");
542 		return -EINVAL;
543 	}
544 
545 	return 0;
546 }
547 
548 /**
549  * ksz88x3_port2_apptrust_quirk - Quirk for apptrust configuration on Port 2
550  *				  of KSZ88x3 devices
551  * @dev: Pointer to the KSZ switch device structure
552  * @port: Port number for which to set the apptrust selectors
553  * @reg: Register address for the apptrust configuration
554  * @port2_data: Data to set for the apptrust configuration
555  *
556  * This function implements a quirk for apptrust configuration on Port 2 of
557  * KSZ88x3 devices. It ensures that DSCP apptrust is not working on Port 2 and
558  * that it is not possible to disable PCP on Port 2. The only way to disable PCP
559  * on Port 2 is to disable multiple queues on the switch.
560  *
561  * Return: 0 on success, or a negative error code on failure
562  */
563 static int ksz88x3_port2_apptrust_quirk(struct ksz_device *dev, int port,
564 					int reg, u8 port2_data)
565 {
566 	struct dsa_switch *ds = dev->ds;
567 	u8 port1_data;
568 	int ret;
569 
570 	/* First validate Port 2 configuration. DiffServ/DSCP is not working
571 	 * on this port.
572 	 */
573 	if (port2_data & KSZ8_PORT_DIFFSERV_ENABLE) {
574 		dev_err(dev->dev, "DSCP apptrust is not working on Port 2\n");
575 		return -EINVAL;
576 	}
577 
578 	/* If PCP support is requested, we need to enable all queues on the
579 	 * switch to make PCP priority working on Port 2.
580 	 */
581 	if (port2_data & KSZ8_PORT_802_1P_ENABLE)
582 		return ksz8_all_queues_split(dev, dev->info->num_tx_queues);
583 
584 	/* We got request to disable PCP priority on Port 2.
585 	 * Now, we need to compare Port 2 configuration with Port 1
586 	 * configuration.
587 	 */
588 	ret = ksz_pread8(dev, KSZ_PORT_1, reg, &port1_data);
589 	if (ret)
590 		return ret;
591 
592 	/* If Port 1 has any apptrust enabled, we can't disable multiple queues
593 	 * on the switch, so we can't disable PCP on Port 2.
594 	 */
595 	if (port1_data & (KSZ8_PORT_802_1P_ENABLE | KSZ8_PORT_DIFFSERV_ENABLE)) {
596 		dev_err(dev->dev, "Not possible to disable PCP on Port 2 if any apptrust is enabled on Port 1\n");
597 		return -EINVAL;
598 	}
599 
600 	/* Now we need to ensure that default priority on Port 1 is set to 0
601 	 * otherwise we can't disable multiqueue support on the switch.
602 	 */
603 	ret = ksz_port_get_default_prio(ds, KSZ_PORT_1);
604 	if (ret < 0) {
605 		return ret;
606 	} else if (ret) {
607 		dev_err(dev->dev, "Not possible to disable PCP on Port 2 if non zero default priority is set on Port 1\n");
608 		return -EINVAL;
609 	}
610 
611 	/* Port 1 has no apptrust or default priority set and we got request to
612 	 * disable PCP on Port 2. We can disable multiqueue support to disable
613 	 * PCP on Port 2.
614 	 */
615 	return ksz8_all_queues_split(dev, 1);
616 }
617 
618 /**
619  * ksz88x3_port_apptrust_quirk - Quirk for apptrust configuration on KSZ88x3
620  *			       devices
621  * @dev: Pointer to the KSZ switch device structure
622  * @port: Port number for which to set the apptrust selectors
623  * @reg: Register address for the apptrust configuration
624  * @data: Data to set for the apptrust configuration
625  *
626  * This function implements a quirk for apptrust configuration on KSZ88x3
627  * devices. It ensures that apptrust configuration on Port 1 and
628  * Port 2 is done in agreement with each other.
629  *
630  * Return: 0 on success, or a negative error code on failure
631  */
632 static int ksz88x3_port_apptrust_quirk(struct ksz_device *dev, int port,
633 				       int reg, u8 data)
634 {
635 	if (port == KSZ_PORT_1)
636 		return ksz88x3_port1_apptrust_quirk(dev, port, reg, data);
637 	else if (port == KSZ_PORT_2)
638 		return ksz88x3_port2_apptrust_quirk(dev, port, reg, data);
639 
640 	return 0;
641 }
642 
643 /**
644  * ksz_port_set_apptrust - Sets the apptrust selectors for a port on a KSZ
645  *			   switch
646  * @ds: Pointer to the DSA switch structure
647  * @port: Port number for which to set the apptrust selectors
648  * @sel: Array of apptrust selectors to set
649  * @nsel: Number of apptrust selectors in the array
650  *
651  * This function sets the apptrust selectors for the specified port on a KSZ
652  * switch.
653  *
654  * Return: 0 on success, or a negative error code on failure
655  */
656 int ksz_port_set_apptrust(struct dsa_switch *ds, int port,
657 			  const u8 *sel, int nsel)
658 {
659 	const struct ksz_apptrust_map *map;
660 	struct ksz_device *dev = ds->priv;
661 	int reg, i, ret;
662 	u8 data = 0;
663 	u8 mask;
664 
665 	ret = ksz_port_set_apptrust_validate(dev, port, sel, nsel);
666 	if (ret)
667 		return ret;
668 
669 	ksz_get_apptrust_map_and_reg(dev, &map, &reg, &mask);
670 
671 	for (i = 0; i < nsel; i++) {
672 		int j;
673 
674 		for (j = 0; j < ARRAY_SIZE(ksz_supported_apptrust); j++) {
675 			if (sel[i] != ksz_supported_apptrust[j])
676 				continue;
677 
678 			data |= map[j].bit;
679 			break;
680 		}
681 	}
682 
683 	if (ksz_is_ksz88x3(dev)) {
684 		ret = ksz88x3_port_apptrust_quirk(dev, port, reg, data);
685 		if (ret)
686 			return ret;
687 	}
688 
689 	return ksz_prmw8(dev, port, reg, mask, data);
690 }
691 
692 /**
693  * ksz_port_get_apptrust - Retrieves the apptrust selectors for a port on a KSZ
694  *			   switch
695  * @ds: Pointer to the DSA switch structure
696  * @port: Port number for which to get the apptrust selectors
697  * @sel: Array to store the apptrust selectors
698  * @nsel: Number of apptrust selectors in the array
699  *
700  * This function fetches the apptrust selectors for the specified port on a KSZ
701  * switch.
702  *
703  * Return: 0 on success, or a negative error code on failure
704  */
705 int ksz_port_get_apptrust(struct dsa_switch *ds, int port, u8 *sel, int *nsel)
706 {
707 	const struct ksz_apptrust_map *map;
708 	struct ksz_device *dev = ds->priv;
709 	int reg, i, ret;
710 	u8 data;
711 	u8 mask;
712 
713 	ksz_get_apptrust_map_and_reg(dev, &map, &reg, &mask);
714 
715 	ret = ksz_pread8(dev, port, reg, &data);
716 	if (ret)
717 		return ret;
718 
719 	*nsel = 0;
720 	for (i = 0; i < ARRAY_SIZE(ksz_supported_apptrust); i++) {
721 		if (data & map[i].bit)
722 			sel[(*nsel)++] = ksz_supported_apptrust[i];
723 	}
724 
725 	return 0;
726 }
727 
728 /**
729  * ksz_dcb_init_port - Initializes the DCB configuration for a port on a KSZ
730  * @dev: Pointer to the KSZ switch device structure
731  * @port: Port number for which to initialize the DCB configuration
732  *
733  * This function initializes the DCB configuration for the specified port on a
734  * KSZ switch. Particular DCB configuration is set for the port, including the
735  * default priority and apptrust selectors.
736  * The default priority is set to Best Effort, and the apptrust selectors are
737  * set to all supported selectors.
738  *
739  * Return: 0 on success, or a negative error code on failure
740  */
741 int ksz_dcb_init_port(struct ksz_device *dev, int port)
742 {
743 	const u8 *sel;
744 	int ret, ipv;
745 	int sel_len;
746 
747 	if (is_ksz8(dev)) {
748 		ipv = ieee8021q_tt_to_tc(IEEE8021Q_TT_BE,
749 					 dev->info->num_tx_queues);
750 		if (ipv < 0)
751 			return ipv;
752 	} else {
753 		ipv = IEEE8021Q_TT_BE;
754 	}
755 
756 	/* Set the default priority for the port to Best Effort */
757 	ret = ksz_port_set_default_prio(dev->ds, port, ipv);
758 	if (ret)
759 		return ret;
760 
761 	if (ksz_is_ksz88x3(dev) && port == KSZ_PORT_2) {
762 		/* KSZ88x3 devices do not support DSCP classification on
763 		 * "Port 2.
764 		 */
765 		sel = ksz8_port2_supported_apptrust;
766 		sel_len = ARRAY_SIZE(ksz8_port2_supported_apptrust);
767 	} else {
768 		sel = ksz_supported_apptrust;
769 		sel_len = ARRAY_SIZE(ksz_supported_apptrust);
770 	}
771 
772 	return ksz_port_set_apptrust(dev->ds, port, sel, sel_len);
773 }
774 
775 /**
776  * ksz_dcb_init - Initializes the DCB configuration for a KSZ switch
777  * @dev: Pointer to the KSZ switch device structure
778  *
779  * This function initializes the DCB configuration for a KSZ switch. The global
780  * DSCP-to-priority mapping table is initialized.
781  *
782  * Return: 0 on success, or a negative error code on failure
783  */
784 int ksz_dcb_init(struct ksz_device *dev)
785 {
786 	int ret;
787 
788 	ret = ksz_init_global_dscp_map(dev);
789 	if (ret)
790 		return ret;
791 
792 	return 0;
793 }
794