if (err)
netdev_err(dev, "Invalid entry: %d:%d\n", app->protocol,
app->priority);
return err;
}
/* Validate apptrust configuration. * * Return index of supported apptrust configuration if valid, otherwise return * error.
*/ staticint sparx5_dcb_apptrust_validate(struct net_device *dev, u8 *selectors, int nselectors, int *err)
{ bool match = false; int i, ii;
for (i = 0; i < ARRAY_SIZE(sparx5_dcb_apptrust_policies); i++) { if (sparx5_dcb_apptrust_policies[i].nselectors != nselectors) continue;
match = true; for (ii = 0; ii < nselectors; ii++) { if (sparx5_dcb_apptrust_policies[i].selectors[ii] !=
*(selectors + ii)) {
match = false; break;
}
} if (match) break;
}
/* Requested trust configuration is not supported */ if (!match) {
netdev_err(dev, "Valid apptrust configurations are:\n"); for (i = 0; i < ARRAY_SIZE(sparx5_dcb_apptrust_names); i++)
pr_info("order: %s\n", sparx5_dcb_apptrust_names[i]);
*err = -EOPNOTSUPP;
}
/* Get default prio. */
qos.default_prio = dcb_ieee_getapp_default_prio_mask(dev); if (qos.default_prio)
qos.default_prio = fls(qos.default_prio) - 1;
/* Get dscp ingress mapping */ for (i = 0; i < ARRAY_SIZE(dscp_map->map); i++) {
app_itr.selector = IEEE_8021QAZ_APP_SEL_DSCP;
app_itr.protocol = i;
dscp_map->map[i] = dcb_getapp(dev, &app_itr);
}
/* Get pcp ingress mapping */ for (i = 0; i < ARRAY_SIZE(pcp_map->map); i++) {
app_itr.selector = DCB_APP_SEL_PCP;
app_itr.protocol = i;
pcp_map->map[i] = dcb_getapp(dev, &app_itr);
}
/* Get pcp rewrite mapping */
dcb_getrewr_prio_pcp_mask_map(dev, &pcp_rewr_map); for (i = 0; i < ARRAY_SIZE(pcp_rewr_map.map); i++) { if (!pcp_rewr_map.map[i]) continue;
pcp_rewr = true;
qos.pcp_rewr.map.map[i] = fls(pcp_rewr_map.map[i]) - 1;
}
/* Get dscp rewrite mapping */
dcb_getrewr_prio_dscp_mask_map(dev, &dscp_rewr_map); for (i = 0; i < ARRAY_SIZE(dscp_rewr_map.map); i++) { if (!dscp_rewr_map.map[i]) continue;
/* The rewrite table of the switch has 32 entries; one for each * priority for each DP level. Currently, the rewrite map does * not indicate DP level, so we map classified QoS class to * classified DSCP, for each classified DP level. Rewrite of * DSCP is only enabled, if we have active mappings.
*/
dscp_rewr = true;
dscp = fls64(dscp_rewr_map.map[i]) - 1;
qos.dscp_rewr.map.map[i] = dscp; /* DP 0 */
qos.dscp_rewr.map.map[i + 8] = dscp; /* DP 1 */
qos.dscp_rewr.map.map[i + 16] = dscp; /* DP 2 */
qos.dscp_rewr.map.map[i + 24] = dscp; /* DP 3 */
}
/* Enable use of pcp for queue classification ? */ if (sparx5_dcb_apptrust_contains(portno, DCB_APP_SEL_PCP)) {
qos.pcp.qos_enable = true;
qos.pcp.dp_enable = qos.pcp.qos_enable; /* Enable rewrite of PCP and DEI if PCP is trusted *and* rewrite * table is not empty.
*/ if (pcp_rewr)
qos.pcp_rewr.enable = true;
}
/* Enable use of dscp for queue classification ? */ if (sparx5_dcb_apptrust_contains(portno, IEEE_8021QAZ_APP_SEL_DSCP)) {
qos.dscp.qos_enable = true;
qos.dscp.dp_enable = qos.dscp.qos_enable; if (dscp_rewr) /* Do not enable rewrite if no mappings are active, as * classified DSCP will then be zero for all classified * QoS class and DP combinations.
*/
qos.dscp_rewr.enable = true;
}
return sparx5_port_qos_set(port, &qos);
}
/* Set or delete DSCP app entry. * * DSCP mapping is global for all ports, so set and delete app entries are * replicated for each port.
*/ staticint sparx5_dcb_ieee_dscp_setdel(struct net_device *dev, struct dcb_app *app, int (*setdel)(struct net_device *, struct dcb_app *))
{ struct sparx5_port *port = netdev_priv(dev); struct sparx5 *sparx5 = port->sparx5; struct sparx5_port *port_itr; int err, i;
for (i = 0; i < sparx5->data->consts->n_ports; i++) {
port_itr = port->sparx5->ports[i]; if (!port_itr) continue;
err = setdel(port_itr->ndev, app); if (err) return err;
}
return 0;
}
staticint sparx5_dcb_ieee_delapp(struct net_device *dev, struct dcb_app *app)
{ int err;
err = sparx5_dcb_app_validate(dev, app); if (err) goto out;
/* Delete current mapping, if it exists. */
proto = dcb_getrewr(dev, app); if (proto) {
app_itr = *app;
app_itr.protocol = proto;
sparx5_dcb_delrewr(dev, &app_itr);
}
int sparx5_dcb_init(struct sparx5 *sparx5)
{ struct sparx5_port *port; int i;
for (i = 0; i < sparx5->data->consts->n_ports; i++) {
port = sparx5->ports[i]; if (!port) continue;
port->ndev->dcbnl_ops = &sparx5_dcbnl_ops; /* Initialize [dscp, pcp] default trust */
sparx5_port_apptrust[port->portno] =
&sparx5_dcb_apptrust_policies
[SPARX5_DCB_APPTRUST_DSCP_PCP];
/* Enable DSCP classification based on classified QoS class and * DP, for all DSCP values, for all ports.
*/
sparx5_port_qos_dscp_rewr_mode_set(port,
SPARX5_PORT_REW_DSCP_ALL);
}
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.