@@ -43,7 +43,7 @@ if_destructor(struct __fman_if *__if)
if (!__if)
return;
- if (__if->__if.mac_type == fman_offline_internal)
+ if (__if->__if.mac_type == fman_offline)
goto cleanup;
list_for_each_entry_safe(bp, tmpbp, &__if->__if.bpool_list, node) {
@@ -246,26 +246,34 @@ fman_if_init(const struct device_node *dpa_node)
uint64_t port_cell_idx_val = 0;
uint64_t ext_args_cell_idx_val = 0;
- const struct device_node *mac_node = NULL, *tx_node, *ext_args_node;
- const struct device_node *pool_node, *fman_node, *rx_node;
+ const struct device_node *mac_node = NULL, *ext_args_node;
+ const struct device_node *pool_node, *fman_node;
+ const struct device_node *rx_node = NULL, *tx_node = NULL;
+ const struct device_node *oh_node = NULL;
const uint32_t *regs_addr = NULL;
const char *mname, *fname;
const char *dname = dpa_node->full_name;
size_t lenp;
- int _errno, is_shared = 0;
+ int _errno, is_shared = 0, is_offline = 0;
const char *char_prop;
uint32_t na;
if (of_device_is_available(dpa_node) == false)
return 0;
- if (!of_device_is_compatible(dpa_node, "fsl,dpa-ethernet-init") &&
- !of_device_is_compatible(dpa_node, "fsl,dpa-ethernet")) {
+ if (of_device_is_compatible(dpa_node, "fsl,dpa-oh"))
+ is_offline = 1;
+
+ if (!of_device_is_compatible(dpa_node, "fsl,dpa-oh") &&
+ !of_device_is_compatible(dpa_node, "fsl,dpa-ethernet-init") &&
+ !of_device_is_compatible(dpa_node, "fsl,dpa-ethernet")) {
return 0;
}
- rprop = "fsl,qman-frame-queues-rx";
- mprop = "fsl,fman-mac";
+ rprop = is_offline ? "fsl,qman-frame-queues-oh" :
+ "fsl,qman-frame-queues-rx";
+ mprop = is_offline ? "fsl,fman-oh-port" :
+ "fsl,fman-mac";
/* Obtain the MAC node used by this interface except macless */
mac_phandle = of_get_property(dpa_node, mprop, &lenp);
@@ -281,27 +289,43 @@ fman_if_init(const struct device_node *dpa_node)
}
mname = mac_node->full_name;
- /* Extract the Rx and Tx ports */
- ports_phandle = of_get_property(mac_node, "fsl,port-handles",
- &lenp);
- if (!ports_phandle)
- ports_phandle = of_get_property(mac_node, "fsl,fman-ports",
+ if (!is_offline) {
+ /* Extract the Rx and Tx ports */
+ ports_phandle = of_get_property(mac_node, "fsl,port-handles",
&lenp);
- if (!ports_phandle) {
- FMAN_ERR(-EINVAL, "%s: no fsl,port-handles",
- mname);
- return -EINVAL;
- }
- assert(lenp == (2 * sizeof(phandle)));
- rx_node = of_find_node_by_phandle(ports_phandle[0]);
- if (!rx_node) {
- FMAN_ERR(-ENXIO, "%s: bad fsl,port-handle[0]", mname);
- return -ENXIO;
- }
- tx_node = of_find_node_by_phandle(ports_phandle[1]);
- if (!tx_node) {
- FMAN_ERR(-ENXIO, "%s: bad fsl,port-handle[1]", mname);
- return -ENXIO;
+ if (!ports_phandle)
+ ports_phandle = of_get_property(mac_node, "fsl,fman-ports",
+ &lenp);
+ if (!ports_phandle) {
+ FMAN_ERR(-EINVAL, "%s: no fsl,port-handles",
+ mname);
+ return -EINVAL;
+ }
+ assert(lenp == (2 * sizeof(phandle)));
+ rx_node = of_find_node_by_phandle(ports_phandle[0]);
+ if (!rx_node) {
+ FMAN_ERR(-ENXIO, "%s: bad fsl,port-handle[0]", mname);
+ return -ENXIO;
+ }
+ tx_node = of_find_node_by_phandle(ports_phandle[1]);
+ if (!tx_node) {
+ FMAN_ERR(-ENXIO, "%s: bad fsl,port-handle[1]", mname);
+ return -ENXIO;
+ }
+ } else {
+ /* Extract the OH ports */
+ ports_phandle = of_get_property(dpa_node, "fsl,fman-oh-port",
+ &lenp);
+ if (!ports_phandle) {
+ FMAN_ERR(-EINVAL, "%s: no fsl,fman-oh-port", dname);
+ return -EINVAL;
+ }
+ assert(lenp == (sizeof(phandle)));
+ oh_node = of_find_node_by_phandle(ports_phandle[0]);
+ if (!oh_node) {
+ FMAN_ERR(-ENXIO, "%s: bad fsl,port-handle[0]", mname);
+ return -ENXIO;
+ }
}
/* Check if the port is shared interface */
@@ -430,17 +454,19 @@ fman_if_init(const struct device_node *dpa_node)
* Set A2V, OVOM, EBD bits in contextA to allow external
* buffer deallocation by fman.
*/
- fman_dealloc_bufs_mask_hi = FMAN_V3_CONTEXTA_EN_A2V |
- FMAN_V3_CONTEXTA_EN_OVOM;
- fman_dealloc_bufs_mask_lo = FMAN_V3_CONTEXTA_EN_EBD;
+ fman_dealloc_bufs_mask_hi = DPAA_FQD_CTX_A_A2_FIELD_VALID |
+ DPAA_FQD_CTX_A_OVERRIDE_OMB;
+ fman_dealloc_bufs_mask_lo = DPAA_FQD_CTX_A2_EBD_BIT;
} else {
fman_dealloc_bufs_mask_hi = 0;
fman_dealloc_bufs_mask_lo = 0;
}
- /* Is the MAC node 1G, 2.5G, 10G? */
+ /* Is the MAC node 1G, 2.5G, 10G or offline? */
__if->__if.is_memac = 0;
- if (of_device_is_compatible(mac_node, "fsl,fman-1g-mac"))
+ if (is_offline)
+ __if->__if.mac_type = fman_offline;
+ else if (of_device_is_compatible(mac_node, "fsl,fman-1g-mac"))
__if->__if.mac_type = fman_mac_1g;
else if (of_device_is_compatible(mac_node, "fsl,fman-10g-mac"))
__if->__if.mac_type = fman_mac_10g;
@@ -468,46 +494,81 @@ fman_if_init(const struct device_node *dpa_node)
goto err;
}
- /*
- * For MAC ports, we cannot rely on cell-index. In
- * T2080, two of the 10G ports on single FMAN have same
- * duplicate cell-indexes as the other two 10G ports on
- * same FMAN. Hence, we now rely upon addresses of the
- * ports from device tree to deduce the index.
- */
+ if (!is_offline) {
+ /*
+ * For MAC ports, we cannot rely on cell-index. In
+ * T2080, two of the 10G ports on single FMAN have same
+ * duplicate cell-indexes as the other two 10G ports on
+ * same FMAN. Hence, we now rely upon addresses of the
+ * ports from device tree to deduce the index.
+ */
- _errno = fman_get_mac_index(regs_addr_host, &__if->__if.mac_idx);
- if (_errno) {
- FMAN_ERR(-EINVAL, "Invalid register address: %" PRIx64,
- regs_addr_host);
- goto err;
- }
+ _errno = fman_get_mac_index(regs_addr_host, &__if->__if.mac_idx);
+ if (_errno) {
+ FMAN_ERR(-EINVAL, "Invalid register address: %" PRIx64,
+ regs_addr_host);
+ goto err;
+ }
+ } else {
+ cell_idx = of_get_property(oh_node, "cell-index", &lenp);
+ if (!cell_idx) {
+ FMAN_ERR(-ENXIO, "%s: no cell-index)\n",
+ oh_node->full_name);
+ goto err;
+ }
+ assert(lenp == sizeof(*cell_idx));
+ cell_idx_host = of_read_number(cell_idx,
+ lenp / sizeof(phandle));
- /* Extract the MAC address for private and shared interfaces */
- mac_addr = of_get_property(mac_node, "local-mac-address",
- &lenp);
- if (!mac_addr) {
- FMAN_ERR(-EINVAL, "%s: no local-mac-address",
- mname);
- goto err;
+ __if->__if.mac_idx = cell_idx_host;
}
- memcpy(&__if->__if.mac_addr, mac_addr, ETHER_ADDR_LEN);
- /* Extract the channel ID (from tx-port-handle) */
- tx_channel_id = of_get_property(tx_node, "fsl,qman-channel-id",
- &lenp);
- if (!tx_channel_id) {
- FMAN_ERR(-EINVAL, "%s: no fsl-qman-channel-id",
- tx_node->full_name);
- goto err;
+ if (!is_offline) {
+ /* Extract the MAC address for private and shared interfaces */
+ mac_addr = of_get_property(mac_node, "local-mac-address",
+ &lenp);
+ if (!mac_addr) {
+ FMAN_ERR(-EINVAL, "%s: no local-mac-address",
+ mname);
+ goto err;
+ }
+ memcpy(&__if->__if.mac_addr, mac_addr, ETHER_ADDR_LEN);
+
+ /* Extract the channel ID (from tx-port-handle) */
+ tx_channel_id = of_get_property(tx_node, "fsl,qman-channel-id",
+ &lenp);
+ if (!tx_channel_id) {
+ FMAN_ERR(-EINVAL, "%s: no fsl-qman-channel-id",
+ tx_node->full_name);
+ goto err;
+ }
+ } else {
+ /* Extract the channel ID (from mac) */
+ tx_channel_id = of_get_property(mac_node, "fsl,qman-channel-id",
+ &lenp);
+ if (!tx_channel_id) {
+ FMAN_ERR(-EINVAL, "%s: no fsl-qman-channel-id",
+ tx_node->full_name);
+ goto err;
+ }
}
- regs_addr = of_get_address(rx_node, 0, &__if->regs_size, NULL);
+ na = of_n_addr_cells(mac_node);
+ __if->__if.tx_channel_id = of_read_number(tx_channel_id, na);
+
+ if (!is_offline)
+ regs_addr = of_get_address(rx_node, 0, &__if->regs_size, NULL);
+ else
+ regs_addr = of_get_address(oh_node, 0, &__if->regs_size, NULL);
if (!regs_addr) {
FMAN_ERR(-EINVAL, "of_get_address(%s)", mname);
goto err;
}
- phys_addr = of_translate_address(rx_node, regs_addr);
+
+ if (!is_offline)
+ phys_addr = of_translate_address(rx_node, regs_addr);
+ else
+ phys_addr = of_translate_address(oh_node, regs_addr);
if (!phys_addr) {
FMAN_ERR(-EINVAL, "of_translate_address(%s, %p)",
mname, regs_addr);
@@ -521,23 +582,27 @@ fman_if_init(const struct device_node *dpa_node)
goto err;
}
- regs_addr = of_get_address(tx_node, 0, &__if->regs_size, NULL);
- if (!regs_addr) {
- FMAN_ERR(-EINVAL, "of_get_address(%s)\n", mname);
- goto err;
- }
- phys_addr = of_translate_address(tx_node, regs_addr);
- if (!phys_addr) {
- FMAN_ERR(-EINVAL, "of_translate_address(%s, %p)\n",
- mname, regs_addr);
- goto err;
- }
- __if->tx_bmi_map = mmap(NULL, __if->regs_size,
- PROT_READ | PROT_WRITE, MAP_SHARED,
- fman_ccsr_map_fd, phys_addr);
- if (__if->tx_bmi_map == MAP_FAILED) {
- FMAN_ERR(-errno, "mmap(0x%"PRIx64")\n", phys_addr);
- goto err;
+ if (!is_offline) {
+ regs_addr = of_get_address(tx_node, 0, &__if->regs_size, NULL);
+ if (!regs_addr) {
+ FMAN_ERR(-EINVAL, "of_get_address(%s)\n", mname);
+ goto err;
+ }
+
+ phys_addr = of_translate_address(tx_node, regs_addr);
+ if (!phys_addr) {
+ FMAN_ERR(-EINVAL, "of_translate_address(%s, %p)\n",
+ mname, regs_addr);
+ goto err;
+ }
+
+ __if->tx_bmi_map = mmap(NULL, __if->regs_size,
+ PROT_READ | PROT_WRITE, MAP_SHARED,
+ fman_ccsr_map_fd, phys_addr);
+ if (__if->tx_bmi_map == MAP_FAILED) {
+ FMAN_ERR(-errno, "mmap(0x%"PRIx64")\n", phys_addr);
+ goto err;
+ }
}
if (!rtc_map) {
@@ -554,11 +619,6 @@ fman_if_init(const struct device_node *dpa_node)
__if->rtc_map = rtc_map;
}
- /* No channel ID for MAC-less */
- assert(lenp == sizeof(*tx_channel_id));
- na = of_n_addr_cells(mac_node);
- __if->__if.tx_channel_id = of_read_number(tx_channel_id, na);
-
/* Extract the Rx FQIDs. (Note, the device representation is silly,
* there are "counts" that must always be 1.)
*/
@@ -568,13 +628,26 @@ fman_if_init(const struct device_node *dpa_node)
goto err;
}
- /* Check if "fsl,qman-frame-queues-rx" in dtb file is valid entry or
- * not. A valid entry contains at least 4 entries, rx_error_queue,
- * rx_error_queue_count, fqid_rx_def and rx_error_queue_count.
+ /*
+ * Check if "fsl,qman-frame-queues-rx/oh" in dtb file is valid entry or
+ * not.
+ *
+ * A valid rx entry contains either 4 or 6 entries. Mandatory entries
+ * are rx_error_queue, rx_error_queue_count, fqid_rx_def and
+ * fqid_rx_def_count. Optional entries are fqid_rx_pcd and
+ * fqid_rx_pcd_count.
+ *
+ * A valid oh entry contains 4 entries. Those entries are
+ * rx_error_queue, rx_error_queue_count, fqid_rx_def and
+ * fqid_rx_def_count.
*/
- assert(lenp >= (4 * sizeof(phandle)));
- na = of_n_addr_cells(mac_node);
+ if (!is_offline)
+ assert(lenp == (4 * sizeof(phandle)) ||
+ lenp == (6 * sizeof(phandle)));
+ else
+ assert(lenp == (4 * sizeof(phandle)));
+
/* Get rid of endianness (issues). Convert to host byte order */
rx_phandle_host[0] = of_read_number(&rx_phandle[0], na);
rx_phandle_host[1] = of_read_number(&rx_phandle[1], na);
@@ -595,6 +668,9 @@ fman_if_init(const struct device_node *dpa_node)
__if->__if.fqid_rx_pcd_count = rx_phandle_host[5];
}
+ if (is_offline)
+ goto oh_init_done;
+
/* Extract the Tx FQIDs */
tx_phandle = of_get_property(dpa_node,
"fsl,qman-frame-queues-tx", &lenp);
@@ -706,6 +782,7 @@ fman_if_init(const struct device_node *dpa_node)
if (is_shared)
__if->__if.is_shared_mac = 1;
+oh_init_done:
fman_if_vsp_init(__if);
/* Parsing of the network interface is complete, add it to the list */
@@ -769,6 +846,10 @@ fman_finish(void)
list_for_each_entry_safe(__if, tmpif, &__ifs, __if.node) {
int _errno;
+ /* No need to disable Offline port */
+ if (__if->__if.mac_type == fman_offline)
+ continue;
+
/* disable Rx and Tx */
if ((__if->__if.mac_type == fman_mac_1g) &&
(!__if->__if.is_memac))
@@ -1,6 +1,6 @@
/* SPDX-License-Identifier: BSD-3-Clause
*
- * Copyright 2017,2020,2022 NXP
+ * Copyright 2017,2020,2022-2023 NXP
*
*/
@@ -88,6 +88,10 @@ fman_if_add_hash_mac_addr(struct fman_if *p, uint8_t *eth)
struct __fman_if *__if = container_of(p, struct __fman_if, __if);
+ /* Add hash mac addr not supported on Offline port */
+ if (__if->__if.mac_type == fman_offline)
+ return 0;
+
eth_addr = ETH_ADDR_TO_UINT64(eth);
if (!(eth_addr & GROUP_ADDRESS))
@@ -109,6 +113,15 @@ fman_if_get_primary_mac_addr(struct fman_if *p, uint8_t *eth)
void *mac_reg =
&((struct memac_regs *)__if->ccsr_map)->mac_addr0.mac_addr_l;
u32 val = in_be32(mac_reg);
+ int i;
+
+ /* Get mac addr not supported on Offline port */
+ /* Return NULL mac address */
+ if (__if->__if.mac_type == fman_offline) {
+ for (i = 0; i < 6; i++)
+ eth[i] = 0x0;
+ return 0;
+ }
eth[0] = (val & 0x000000ff) >> 0;
eth[1] = (val & 0x0000ff00) >> 8;
@@ -130,6 +143,10 @@ fman_if_clear_mac_addr(struct fman_if *p, uint8_t addr_num)
struct __fman_if *m = container_of(p, struct __fman_if, __if);
void *reg;
+ /* Clear mac addr not supported on Offline port */
+ if (m->__if.mac_type == fman_offline)
+ return;
+
if (addr_num) {
reg = &((struct memac_regs *)m->ccsr_map)->
mac_addr[addr_num-1].mac_addr_l;
@@ -149,10 +166,13 @@ int
fman_if_add_mac_addr(struct fman_if *p, uint8_t *eth, uint8_t addr_num)
{
struct __fman_if *m = container_of(p, struct __fman_if, __if);
-
void *reg;
u32 val;
+ /* Set mac addr not supported on Offline port */
+ if (m->__if.mac_type == fman_offline)
+ return 0;
+
memcpy(&m->__if.mac_addr, eth, ETHER_ADDR_LEN);
if (addr_num)
@@ -1,7 +1,7 @@
/* SPDX-License-Identifier: (BSD-3-Clause OR GPL-2.0)
*
* Copyright 2010-2016 Freescale Semiconductor Inc.
- * Copyright 2017-2019 NXP
+ * Copyright 2017-2019,2023 NXP
*
*/
#include <inttypes.h>
@@ -44,6 +44,7 @@ dump_netcfg(struct netcfg_info *cfg_ptr, FILE *f)
fprintf(f, "\n+ Fman %d, MAC %d (%s);\n",
__if->fman_idx, __if->mac_idx,
+ (__if->mac_type == fman_offline) ? "OFFLINE" :
(__if->mac_type == fman_mac_1g) ? "1G" :
(__if->mac_type == fman_mac_2_5g) ? "2.5G" : "10G");
@@ -56,13 +57,15 @@ dump_netcfg(struct netcfg_info *cfg_ptr, FILE *f)
fprintf(f, "\tfqid_rx_def: 0x%x\n", p_cfg->rx_def);
fprintf(f, "\tfqid_rx_err: 0x%x\n", __if->fqid_rx_err);
- fprintf(f, "\tfqid_tx_err: 0x%x\n", __if->fqid_tx_err);
- fprintf(f, "\tfqid_tx_confirm: 0x%x\n", __if->fqid_tx_confirm);
- fman_if_for_each_bpool(bpool, __if)
- fprintf(f, "\tbuffer pool: (bpid=%d, count=%"PRId64
- " size=%"PRId64", addr=0x%"PRIx64")\n",
- bpool->bpid, bpool->count, bpool->size,
- bpool->addr);
+ if (__if->mac_type != fman_offline) {
+ fprintf(f, "\tfqid_tx_err: 0x%x\n", __if->fqid_tx_err);
+ fprintf(f, "\tfqid_tx_confirm: 0x%x\n", __if->fqid_tx_confirm);
+ fman_if_for_each_bpool(bpool, __if)
+ fprintf(f, "\tbuffer pool: (bpid=%d, count=%"PRId64
+ " size=%"PRId64", addr=0x%"PRIx64")\n",
+ bpool->bpid, bpool->count, bpool->size,
+ bpool->addr);
+ }
}
}
#endif /* RTE_LIBRTE_DPAA_DEBUG_DRIVER */
@@ -43,6 +43,7 @@
#include <fsl_qman.h>
#include <fsl_bman.h>
#include <netcfg.h>
+#include <fman.h>
struct rte_dpaa_bus {
struct rte_bus bus;
@@ -203,9 +204,12 @@ dpaa_create_device_list(void)
/* Create device name */
memset(dev->name, 0, RTE_ETH_NAME_MAX_LEN);
- sprintf(dev->name, "fm%d-mac%d", (fman_intf->fman_idx + 1),
- fman_intf->mac_idx);
- DPAA_BUS_LOG(INFO, "%s netdev added", dev->name);
+ if (fman_intf->mac_type == fman_offline)
+ sprintf(dev->name, "fm%d-oh%d",
+ (fman_intf->fman_idx + 1), fman_intf->mac_idx);
+ else
+ sprintf(dev->name, "fm%d-mac%d",
+ (fman_intf->fman_idx + 1), fman_intf->mac_idx);
dev->device.name = dev->name;
dev->device.devargs = dpaa_devargs_lookup(dev);
@@ -441,7 +445,7 @@ static int
rte_dpaa_bus_parse(const char *name, void *out)
{
unsigned int i, j;
- size_t delta;
+ size_t delta, dev_delta;
size_t max_name_len;
/* There are two ways of passing device name, with and without
@@ -458,16 +462,25 @@ rte_dpaa_bus_parse(const char *name, void *out)
delta = 5;
}
+ /* dev_delta points to the dev name (mac/oh/onic). Not valid for
+ * dpaa_sec.
+ */
+ dev_delta = delta + sizeof("fm.-") - 1;
+
if (strncmp("dpaa_sec", &name[delta], 8) == 0) {
if (sscanf(&name[delta], "dpaa_sec-%u", &i) != 1 ||
i < 1 || i > 4)
return -EINVAL;
max_name_len = sizeof("dpaa_sec-.") - 1;
+ } else if (strncmp("oh", &name[dev_delta], 2) == 0) {
+ if (sscanf(&name[delta], "fm%u-oh%u", &i, &j) != 2 ||
+ i >= 2 || j >= 16)
+ return -EINVAL;
+ max_name_len = sizeof("fm.-oh..") - 1;
} else {
if (sscanf(&name[delta], "fm%u-mac%u", &i, &j) != 2 ||
i >= 2 || j >= 16)
return -EINVAL;
-
max_name_len = sizeof("fm.-mac..") - 1;
}
@@ -2,7 +2,7 @@
*
* Copyright 2010-2012 Freescale Semiconductor, Inc.
* All rights reserved.
- * Copyright 2019-2022 NXP
+ * Copyright 2019-2023 NXP
*
*/
@@ -78,7 +78,7 @@ TAILQ_HEAD(rte_fman_if_list, __fman_if);
/* Represents the different flavour of network interface */
enum fman_mac_type {
- fman_offline_internal = 0,
+ fman_offline = 0,
fman_mac_1g,
fman_mac_10g,
fman_mac_2_5g,
@@ -474,11 +474,30 @@ extern int fman_ccsr_map_fd;
#define FMAN_IP_REV_1_MAJOR_MASK 0x0000FF00
#define FMAN_IP_REV_1_MAJOR_SHIFT 8
#define FMAN_V3 0x06
-#define FMAN_V3_CONTEXTA_EN_A2V 0x10000000
-#define FMAN_V3_CONTEXTA_EN_OVOM 0x02000000
-#define FMAN_V3_CONTEXTA_EN_EBD 0x80000000
-#define FMAN_CONTEXTA_DIS_CHECKSUM 0x7ull
-#define FMAN_CONTEXTA_SET_OPCODE11 0x2000000b00000000
+
+#define DPAA_FQD_CTX_A_SHIFT_BITS 24
+#define DPAA_FQD_CTX_B_SHIFT_BITS 24
+
+/* Following flags are used to set in context A hi field of FQD */
+#define DPAA_FQD_CTX_A_OVERRIDE_FQ (0x80 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A_IGNORE_CMD (0x40 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A_A1_FIELD_VALID (0x20 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A_A2_FIELD_VALID (0x10 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A_A0_FIELD_VALID (0x08 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A_B0_FIELD_VALID (0x04 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A_OVERRIDE_OMB (0x02 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A_RESERVED (0x01 << DPAA_FQD_CTX_A_SHIFT_BITS)
+
+/* Following flags are used to set in context A lo field of FQD */
+#define DPAA_FQD_CTX_A2_EBD_BIT (0x80 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A2_EBAD_BIT (0x40 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A2_FWD_BIT (0x20 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A2_NL_BIT (0x10 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A2_CWD_BIT (0x08 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A2_NENQ_BIT (0x04 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A2_RESERVED_BIT (0x02 << DPAA_FQD_CTX_A_SHIFT_BITS)
+#define DPAA_FQD_CTX_A2_VSPE_BIT (0x01 << DPAA_FQD_CTX_A_SHIFT_BITS)
+
extern u16 fman_ip_rev;
extern u32 fman_dealloc_bufs_mask_hi;
extern u32 fman_dealloc_bufs_mask_lo;
@@ -292,7 +292,7 @@ dpaa_eth_dev_configure(struct rte_eth_dev *dev)
max_rx_pktlen = DPAA_MAX_RX_PKT_LEN;
}
- if (!fif->is_shared_mac)
+ if (fif->mac_type != fman_offline)
fman_if_set_maxfrm(dev->process_private, max_rx_pktlen);
if (rx_offloads & RTE_ETH_RX_OFFLOAD_SCATTER) {
@@ -311,6 +311,10 @@ dpaa_eth_dev_configure(struct rte_eth_dev *dev)
dpaa_write_fm_config_to_file();
}
+ /* Disable interrupt support on offline port*/
+ if (fif->mac_type == fman_offline)
+ return 0;
+
/* if the interrupts were configured on this devices*/
if (intr_handle && rte_intr_fd_get(intr_handle)) {
if (dev->data->dev_conf.intr_conf.lsc != 0)
@@ -527,6 +531,9 @@ static int dpaa_eth_dev_close(struct rte_eth_dev *dev)
ret = dpaa_eth_dev_stop(dev);
+ if (fif->mac_type == fman_offline)
+ return 0;
+
/* Reset link to autoneg */
if (link->link_status && !link->link_autoneg)
dpaa_restart_link_autoneg(__fif->node_name);
@@ -640,6 +647,11 @@ static int dpaa_eth_dev_info(struct rte_eth_dev *dev,
| RTE_ETH_LINK_SPEED_1G
| RTE_ETH_LINK_SPEED_2_5G
| RTE_ETH_LINK_SPEED_10G;
+ } else if (fif->mac_type == fman_offline) {
+ dev_info->speed_capa = RTE_ETH_LINK_SPEED_10M_HD
+ | RTE_ETH_LINK_SPEED_10M
+ | RTE_ETH_LINK_SPEED_100M_HD
+ | RTE_ETH_LINK_SPEED_100M;
} else {
DPAA_PMD_ERR("invalid link_speed: %s, %d",
dpaa_intf->name, fif->mac_type);
@@ -740,7 +752,8 @@ static int dpaa_eth_link_update(struct rte_eth_dev *dev,
ioctl_version = dpaa_get_ioctl_version_number();
- if (dev->data->dev_flags & RTE_ETH_DEV_INTR_LSC) {
+ if (dev->data->dev_flags & RTE_ETH_DEV_INTR_LSC &&
+ fif->mac_type != fman_offline) {
for (count = 0; count <= MAX_REPEAT_TIME; count++) {
ret = dpaa_get_link_status(__fif->node_name, link);
if (ret)
@@ -753,6 +766,11 @@ static int dpaa_eth_link_update(struct rte_eth_dev *dev,
}
} else {
link->link_status = dpaa_intf->valid;
+ if (fif->mac_type == fman_offline) {
+ /*Max supported rate for O/H port is 3.75Mpps*/
+ link->link_speed = RTE_ETH_SPEED_NUM_2_5G;
+ link->link_duplex = RTE_ETH_LINK_FULL_DUPLEX;
+ }
}
if (ioctl_version < 2) {
@@ -1073,7 +1091,7 @@ int dpaa_eth_rx_queue_setup(struct rte_eth_dev *dev, uint16_t queue_idx,
dpaa_intf->bp_info = DPAA_MEMPOOL_TO_POOL_INFO(mp);
/* For shared interface, it's done in kernel, skip.*/
- if (!fif->is_shared_mac)
+ if (!fif->is_shared_mac && fif->mac_type != fman_offline)
dpaa_fman_if_pool_setup(dev);
if (fif->num_profiles) {
@@ -1218,8 +1236,11 @@ int dpaa_eth_rx_queue_setup(struct rte_eth_dev *dev, uint16_t queue_idx,
rxq->fqid, ret);
}
}
+
/* Enable main queue to receive error packets also by default */
- fman_if_set_err_fqid(fif, rxq->fqid);
+ if (fif->mac_type != fman_offline)
+ fman_if_set_err_fqid(fif, rxq->fqid);
+
return 0;
}
@@ -1368,7 +1389,8 @@ static int dpaa_link_down(struct rte_eth_dev *dev)
__fif = container_of(fif, struct __fman_if, __if);
- if (dev->data->dev_flags & RTE_ETH_DEV_INTR_LSC)
+ if (dev->data->dev_flags & RTE_ETH_DEV_INTR_LSC &&
+ fif->mac_type != fman_offline)
dpaa_update_link_status(__fif->node_name, RTE_ETH_LINK_DOWN);
else
return dpaa_eth_dev_stop(dev);
@@ -1384,7 +1406,8 @@ static int dpaa_link_up(struct rte_eth_dev *dev)
__fif = container_of(fif, struct __fman_if, __if);
- if (dev->data->dev_flags & RTE_ETH_DEV_INTR_LSC)
+ if (dev->data->dev_flags & RTE_ETH_DEV_INTR_LSC &&
+ fif->mac_type != fman_offline)
dpaa_update_link_status(__fif->node_name, RTE_ETH_LINK_UP);
else
dpaa_eth_dev_start(dev);
@@ -1479,9 +1502,15 @@ dpaa_dev_add_mac_addr(struct rte_eth_dev *dev,
__rte_unused uint32_t pool)
{
int ret;
+ struct fman_if *fif = dev->process_private;
PMD_INIT_FUNC_TRACE();
+ if (fif->mac_type == fman_offline) {
+ DPAA_PMD_DEBUG("Add MAC Address not supported on O/H port");
+ return 0;
+ }
+
ret = fman_if_add_mac_addr(dev->process_private,
addr->addr_bytes, index);
@@ -1494,8 +1523,15 @@ static void
dpaa_dev_remove_mac_addr(struct rte_eth_dev *dev,
uint32_t index)
{
+ struct fman_if *fif = dev->process_private;
+
PMD_INIT_FUNC_TRACE();
+ if (fif->mac_type == fman_offline) {
+ DPAA_PMD_DEBUG("Remove MAC Address not supported on O/H port");
+ return;
+ }
+
fman_if_clear_mac_addr(dev->process_private, index);
}
@@ -1504,9 +1540,15 @@ dpaa_dev_set_mac_addr(struct rte_eth_dev *dev,
struct rte_ether_addr *addr)
{
int ret;
+ struct fman_if *fif = dev->process_private;
PMD_INIT_FUNC_TRACE();
+ if (fif->mac_type == fman_offline) {
+ DPAA_PMD_DEBUG("Set MAC Address not supported on O/H port");
+ return 0;
+ }
+
ret = fman_if_add_mac_addr(dev->process_private, addr->addr_bytes, 0);
if (ret)
DPAA_PMD_ERR("Setting the MAC ADDR failed %d", ret);
@@ -1805,6 +1847,17 @@ static int dpaa_rx_queue_init(struct qman_fq *fq, struct qman_cgr *cgr_rx,
return ret;
}
+uint8_t fm_default_vsp_id(struct fman_if *fif)
+{
+ /* Avoid being same as base profile which could be used
+ * for kernel interface of shared mac.
+ */
+ if (fif->base_profile_id)
+ return 0;
+ else
+ return DPAA_DEFAULT_RXQ_VSP_ID;
+}
+
/* Initialise a Tx FQ */
static int dpaa_tx_queue_init(struct qman_fq *fq,
struct fman_if *fman_intf,
@@ -1839,14 +1892,21 @@ static int dpaa_tx_queue_init(struct qman_fq *fq,
opts.fqd.context_a.hi = fman_dealloc_bufs_mask_hi;
#else
/* no tx-confirmation */
- opts.fqd.context_a.lo = 0 | fman_dealloc_bufs_mask_lo;
- opts.fqd.context_a.hi = 0x80000000 | fman_dealloc_bufs_mask_hi;
+ opts.fqd.context_a.lo = fman_dealloc_bufs_mask_lo;
+ opts.fqd.context_a.hi = DPAA_FQD_CTX_A_OVERRIDE_FQ |
+ fman_dealloc_bufs_mask_hi;
#endif
- if (fman_ip_rev >= FMAN_V3) {
+ if (fman_ip_rev >= FMAN_V3)
/* Set B0V bit in contextA to set ASPID to 0 */
- opts.fqd.context_a.hi |= 0x04000000;
+ opts.fqd.context_a.hi |= DPAA_FQD_CTX_A_B0_FIELD_VALID;
+
+ if (fman_intf->mac_type == fman_offline) {
+ opts.fqd.context_a.lo |= DPAA_FQD_CTX_A2_VSPE_BIT;
+ opts.fqd.context_b = fm_default_vsp_id(fman_intf) <<
+ DPAA_FQD_CTX_B_SHIFT_BITS;
}
+
DPAA_PMD_DEBUG("init tx fq %p, fqid 0x%x", fq, fq->fqid);
if (cgr_tx) {
@@ -2219,7 +2279,8 @@ dpaa_dev_init(struct rte_eth_dev *eth_dev)
DPAA_PMD_DEBUG("All frame queues created");
/* Get the initial configuration for flow control */
- dpaa_fc_set_default(dpaa_intf, fman_intf);
+ if (fman_intf->mac_type != fman_offline)
+ dpaa_fc_set_default(dpaa_intf, fman_intf);
/* reset bpool list, initialize bpool dynamically */
list_for_each_entry_safe(bp, tmp_bp, &cfg->fman_if->bpool_list, node) {
@@ -2250,10 +2311,10 @@ dpaa_dev_init(struct rte_eth_dev *eth_dev)
DPAA_PMD_INFO("net: dpaa: %s: " RTE_ETHER_ADDR_PRT_FMT,
dpaa_device->name, RTE_ETHER_ADDR_BYTES(&fman_intf->mac_addr));
- if (!fman_intf->is_shared_mac) {
+ if (!fman_intf->is_shared_mac && fman_intf->mac_type != fman_offline) {
/* Configure error packet handling */
fman_if_receive_rx_errors(fman_intf,
- FM_FD_RX_STATUS_ERR_MASK);
+ FM_FD_RX_STATUS_ERR_MASK);
/* Disable RX mode */
fman_if_disable_rx(fman_intf);
/* Disable promiscuous mode */
@@ -1,7 +1,7 @@
/* SPDX-License-Identifier: BSD-3-Clause
*
* Copyright (c) 2014-2016 Freescale Semiconductor, Inc. All rights reserved.
- * Copyright 2017-2022 NXP
+ * Copyright 2017-2023 NXP
*
*/
#ifndef __DPAA_ETHDEV_H__
@@ -120,6 +120,9 @@ enum {
extern struct rte_mempool *dpaa_tx_sg_pool;
+/* PMD related logs */
+extern int dpaa_logtype_pmd;
+
/* structure to free external and indirect
* buffers.
*/
@@ -265,6 +268,9 @@ dpaa_timesync_read_rx_timestamp(struct rte_eth_dev *dev,
struct timespec *timestamp,
uint32_t flags __rte_unused);
+uint8_t
+fm_default_vsp_id(struct fman_if *fif);
+
/* PMD related logs */
extern int dpaa_logtype_pmd;
#define RTE_LOGTYPE_DPAA_PMD dpaa_logtype_pmd
@@ -54,17 +54,6 @@ static struct dpaa_fm_info fm_info;
static struct dpaa_fm_model fm_model;
static const char *fm_log = "/tmp/fmdpdk.bin";
-static inline uint8_t fm_default_vsp_id(struct fman_if *fif)
-{
- /* Avoid being same as base profile which could be used
- * for kernel interface of shared mac.
- */
- if (fif->base_profile_id)
- return 0;
- else
- return DPAA_DEFAULT_RXQ_VSP_ID;
-}
-
static void fm_prev_cleanup(void)
{
uint32_t fman_id = 0, i = 0, devid;
@@ -660,7 +649,9 @@ static inline int get_rx_port_type(struct fman_if *fif)
/* For 1G fm-mac9 and fm-mac10 ports, configure the VSP as 10G
* ports so that kernel can configure correct port.
*/
- if (fif->mac_type == fman_mac_1g &&
+ if (fif->mac_type == fman_offline)
+ return e_FM_PORT_TYPE_OH_OFFLINE_PARSING;
+ else if (fif->mac_type == fman_mac_1g &&
fif->mac_idx >= DPAA_10G_MAC_START_IDX)
return e_FM_PORT_TYPE_RX_10G;
else if (fif->mac_type == fman_mac_1g)
@@ -671,12 +662,14 @@ static inline int get_rx_port_type(struct fman_if *fif)
return e_FM_PORT_TYPE_RX_10G;
DPAA_PMD_ERR("MAC type unsupported");
- return -1;
+ return e_FM_PORT_TYPE_DUMMY;
}
static inline int get_tx_port_type(struct fman_if *fif)
{
- if (fif->mac_type == fman_mac_1g)
+ if (fif->mac_type == fman_offline)
+ return e_FM_PORT_TYPE_OH_OFFLINE_PARSING;
+ else if (fif->mac_type == fman_mac_1g)
return e_FM_PORT_TYPE_TX;
else if (fif->mac_type == fman_mac_2_5g)
return e_FM_PORT_TYPE_TX_2_5G;
@@ -684,7 +677,7 @@ static inline int get_tx_port_type(struct fman_if *fif)
return e_FM_PORT_TYPE_TX_10G;
DPAA_PMD_ERR("MAC type unsupported");
- return -1;
+ return e_FM_PORT_TYPE_DUMMY;
}
static inline int set_fm_port_handle(struct dpaa_if *dpaa_intf,
@@ -983,17 +976,31 @@ static int dpaa_port_vsp_configure(struct dpaa_if *dpaa_intf,
memset(&vsp_params, 0, sizeof(vsp_params));
vsp_params.h_fm = fman_handle;
vsp_params.relative_profile_id = vsp_id;
- vsp_params.port_params.port_id = idx;
+ if (fif->mac_type == fman_offline)
+ vsp_params.port_params.port_id = fif->mac_idx;
+ else
+ vsp_params.port_params.port_id = idx;
+
if (fif->mac_type == fman_mac_1g) {
vsp_params.port_params.port_type = e_FM_PORT_TYPE_RX;
} else if (fif->mac_type == fman_mac_2_5g) {
vsp_params.port_params.port_type = e_FM_PORT_TYPE_RX_2_5G;
} else if (fif->mac_type == fman_mac_10g) {
vsp_params.port_params.port_type = e_FM_PORT_TYPE_RX_10G;
+ } else if (fif->mac_type == fman_offline) {
+ vsp_params.port_params.port_type =
+ e_FM_PORT_TYPE_OH_OFFLINE_PARSING;
} else {
DPAA_PMD_ERR("Mac type %d error", fif->mac_type);
return -1;
}
+
+ vsp_params.port_params.port_type = get_rx_port_type(fif);
+ if (vsp_params.port_params.port_type == e_FM_PORT_TYPE_DUMMY) {
+ DPAA_PMD_ERR("Mac type %d error", fif->mac_type);
+ return -1;
+ }
+
vsp_params.ext_buf_pools.num_of_pools_used = 1;
vsp_params.ext_buf_pools.ext_buf_pool[0].id = dpaa_intf->vsp_bpid[vsp_id];
vsp_params.ext_buf_pools.ext_buf_pool[0].size = mbuf_data_room_size;
@@ -215,8 +215,7 @@ dpaa_port_fmc_port_parse(struct fman_if *fif,
if (pport->type == e_FM_PORT_TYPE_OH_OFFLINE_PARSING &&
pport->number == fif->mac_idx &&
- (fif->mac_type == fman_offline_internal ||
- fif->mac_type == fman_onic))
+ fif->mac_type == fman_offline)
return current_port;
if (fif->mac_type == fman_mac_1g) {