以下是DPDK中rte_eth_dev_rss_reta_update函数的源代码:
/**
* Update RSS redirection table
*
* @param port_id
* The port identifier of the Ethernet device.
* @param reta_conf
* The reta configuration to be updated.
* @param reta_size
* The size of the rss indirection table, must be a power of two and <= (ETH_RSS_RETA_SIZE_MAX/ETH_RSS_RETA_GROUP_SIZE).
*
* @return
* - (0) if successful.
* - (-EINVAL) if parameters are invalid.
*/
int
rte_eth_dev_rss_reta_update(uint16_t port_id,
struct rte_eth_rss_reta_entry64 *reta_conf,
uint16_t reta_size)
{
struct rte_eth_dev_info dev_info;
uint32_t hash_key_size;
int i, idx;
RTE_ETH_VALID_PORTID_OR_ERR_RET(port_id, -EINVAL);
if ((reta_conf == NULL && reta_size != 0) ||
(reta_conf != NULL && reta_size == 0))
return -EINVAL;
memset(&dev_info, 0, sizeof(dev_info));
rte_eth_dev_info_get(port_id, &dev_info);
/* reject unsupported RETA sizes */
if (!dev_info.reta_update_supported)
return -ENOTSUP;
if (reta_size > ETH_RSS_RETA_SIZE_MAX / ETH_RSS_RETA_GROUP_SIZE ||
!rte_is_power_of_2(reta_size))
return -EINVAL;
hash_key_size = dev_info.hash_key_size;
/*
* Check whether the key length is supported by PMD or not.
*/
if ((hash_key_size == 0) || (hash_key_size > RTE_DIM(default_rss_hash_key))) {
RTE_ETHDEV_LOG(ERR, "Invalid hash key size %u\n", hash_key_size);
return -EINVAL;
}
/*
* If reta_conf is NULL then reset RETA to default values.
*/
if (reta_conf == NULL) {
uint16_t group, idx;
for (group = 0; group < ETH_RSS_RETA_NUM_GROUPS(dev_info.reta_size); group++)
for (idx = 0; idx < ETH_RSS_RETA_GROUP_SIZE; idx++) {
struct rte_eth_rss_reta_entry64 entry;
entry.mask = UINT64_MAX;
entry.reta[idx] = group * ETH_RSS_RETA_GROUP_SIZE + idx;
if (rte_eth_dev_rss_reta_update_entry(port_id, &entry,
group * ETH_RSS_RETA_GROUP_SIZE + idx))
return -1;
}
return 0;
}
for (i = 0; i < reta_size; i++) {
/* check validity of entries */
if ((reta_conf[i].mask & (~((uint64_t)~0 >> dev_info.hash_key_size)))
|| reta_conf[i].reserved)
return -EINVAL;
/* update redirection table */
idx = i / ETH_RSS_RETA_GROUP_SIZE;
if (rte_eth_dev_rss_reta_update_entry(port_id, &reta_conf[i],
i % ETH_RSS_RETA_GROUP_SIZE +
idx * ETH_RSS_RETA_GROUP_SIZE))
return -1;
}
return 0;
}
该函数首先检查传递的参数是否合法,然后使用rte_eth_dev_info_get函数获取与指定端口关联的设备信息。如果不支持更新RETA表,则返回错误。如果指定的RETA大小不是2的幂或超过最大值,也会返回错误。
如果传递的reta_conf参数为NULL,则将RETA表重置为默认值。否则,它将迭代reta_conf数组中的每个元素,并使用rte_eth_dev_rss_reta_update_entry函数更新RETA表中相应的条目。
最后,该函数返回0表示成功,否则返回负数以指示出现了错误。