[PATCH] app/testpmd: add VLAN priority insert support

yangxingui yangxingui at huawei.com
Tue Jun 16 15:17:22 CEST 2026



On 2026/6/15 17:46, fengchengwen wrote:
> On 6/12/2026 4:14 PM, Xingui Yang wrote:
>> The tx_vlan set command currently only accepts a VLAN ID in range
>> [0, 4095].  This patch adds support for an extended format that includes
>> 802.1p priority and CFI bits, allowing users to set the VLAN priority
>> tag when inserting VLAN headers in TX packets.
>>
>> The extended format is:
>>    bit 0-11:  VLAN ID (0-4095)
>>    bit 12:    CFI (Canonical Format Indicator)
>>    bit 13-15: Priority (0-7, 802.1p CoS)
>>
>> This is consistent with the VLAN tag structure used by
>> rte_eth_dev_set_vlan_pvid() where the PVID field encodes VLAN ID, CFI
>> and priority in the same format.
>>
>> A new command line option --enable-vlan-priority is added to enable this
>> feature. By default, the feature is disabled to maintain backward
>> compatibility with existing users. When enabled, the
>> vlan_id_is_invalid() function allows any 16-bit value to pass, while the
>> full 16-bit value (including CFI and priority bits) is passed to the
>> driver for hardware VLAN insertion.
>>
>> Signed-off-by: Xingui Yang <yangxingui at huawei.com>
>> ---
>>   app/test-pmd/config.c     | 24 +++++++++++++++---------
>>   app/test-pmd/parameters.c |  6 ++++++
>>   app/test-pmd/testpmd.c    |  5 +++++
>>   app/test-pmd/testpmd.h    |  2 ++
>>   4 files changed, 28 insertions(+), 9 deletions(-)
>>
>> diff --git a/app/test-pmd/config.c b/app/test-pmd/config.c
>> index 36b9b023e2..80cde109e6 100644
>> --- a/app/test-pmd/config.c
>> +++ b/app/test-pmd/config.c
>> @@ -1241,12 +1241,18 @@ void print_valid_ports(void)
>>   }
>>   
>>   static int
>> -vlan_id_is_invalid(uint16_t vlan_id)
>> +vlan_id_is_invalid(uint16_t vlan_id, int vlan_priority_ena)
>>   {
>> -	if (vlan_id < 4096)
>> -		return 0;
>> -	fprintf(stderr, "Invalid vlan_id %d (must be < 4096)\n", vlan_id);
>> -	return 1;
>> +	if (!vlan_priority_ena && vlan_id >= 4096) {
>> +		fprintf(stderr, "Invalid vlan_id %d (must be < 4096)\n", vlan_id);
>> +		return 1;
>> +	}
>> +
>> +	/*
>> +	 * When vlan_priority_ena is enabled, allow any 16-bit value
>> +	 * to pass priority and CFI bits to the driver.
>> +	 */
>> +	return 0;
>>   }
>>   
>>   static uint32_t
>> @@ -6876,7 +6882,7 @@ rx_vft_set(portid_t port_id, uint16_t vlan_id, int on)
>>   
>>   	if (port_id_is_invalid(port_id, ENABLED_WARN))
>>   		return 1;
>> -	if (vlan_id_is_invalid(vlan_id))
>> +	if (vlan_id_is_invalid(vlan_id, vlan_priority_insert_ena))
> 
> Just vlan_id_is_invalid(vlan_id, false) because Rx is no need to impl this.
> 
>>   		return 1;
>>   	diag = rte_eth_dev_vlan_filter(port_id, vlan_id, on);
>>   	if (diag == 0)
>> @@ -6923,7 +6929,7 @@ tx_vlan_set(portid_t port_id, uint16_t vlan_id)
>>   	struct rte_eth_dev_info dev_info;
>>   	int ret;
>>   
>> -	if (vlan_id_is_invalid(vlan_id))
>> +	if (vlan_id_is_invalid(vlan_id, vlan_priority_insert_ena))
>>   		return;
>>   
>>   	if (ports[port_id].dev_conf.txmode.offloads &
>> @@ -6954,9 +6960,9 @@ tx_qinq_set(portid_t port_id, uint16_t vlan_id, uint16_t vlan_id_outer)
>>   	struct rte_eth_dev_info dev_info;
>>   	int ret;
>>   
>> -	if (vlan_id_is_invalid(vlan_id))
>> +	if (vlan_id_is_invalid(vlan_id, vlan_priority_insert_ena))
>>   		return;
>> -	if (vlan_id_is_invalid(vlan_id_outer))
>> +	if (vlan_id_is_invalid(vlan_id_outer, vlan_priority_insert_ena))
>>   		return;
>>   
>>   	ret = eth_dev_info_get_print_err(port_id, &dev_info);
>> diff --git a/app/test-pmd/parameters.c b/app/test-pmd/parameters.c
>> index 8c3b1244e7..3f37498d3b 100644
>> --- a/app/test-pmd/parameters.c
>> +++ b/app/test-pmd/parameters.c
>> @@ -117,6 +117,8 @@ enum {
>>   	TESTPMD_OPT_ENABLE_HW_VLAN_EXTEND_NUM,
>>   #define TESTPMD_OPT_ENABLE_HW_QINQ_STRIP "enable-hw-qinq-strip"
>>   	TESTPMD_OPT_ENABLE_HW_QINQ_STRIP_NUM,
>> +#define TESTPMD_OPT_ENABLE_VLAN_PRIORITY "enable-vlan-priority"
>> +	TESTPMD_OPT_ENABLE_VLAN_PRIORITY_NUM,
> 
> How about TESTPMD_OPT_ENABLE_VLAN_INSERT_PRI "enable-vlan-insert-pri"

I have adopted the simpler approach as suggested by Stephen.

>>   #define TESTPMD_OPT_ENABLE_DROP_EN "enable-drop-en"
>>   	TESTPMD_OPT_ENABLE_DROP_EN_NUM,
>>   #define TESTPMD_OPT_DISABLE_RSS "disable-rss"
>> @@ -461,6 +463,7 @@ usage(char* progname)
>>   	printf("  --enable-hw-vlan-strip: enable hardware vlan strip.\n");
>>   	printf("  --enable-hw-vlan-extend: enable hardware vlan extend.\n");
>>   	printf("  --enable-hw-qinq-strip: enable hardware qinq strip.\n");
>> +	printf("  --enable-vlan-priority: enable vlan priority insert.\n");
>>   	printf("  --enable-drop-en: enable per queue packet drop.\n");
>>   	printf("  --disable-rss: disable rss.\n");
>>   	printf("  --enable-rss: Force rss even for single-queue operation.\n");
>> @@ -1259,6 +1262,9 @@ launch_args_parse(int argc, char** argv)
>>   		case TESTPMD_OPT_ENABLE_HW_QINQ_STRIP_NUM:
>>   			rx_offloads |= RTE_ETH_RX_OFFLOAD_QINQ_STRIP;
>>   			break;
>> +		case TESTPMD_OPT_ENABLE_VLAN_PRIORITY_NUM:
>> +			vlan_priority_insert_ena = 1;
> 
> How about tx_insert_vlan_pri_en
> 
>> +			break;

I have adopted the simpler approach as suggested by Stephen, which 
eliminates the need for a new command-line option and global variable.

> 
> We need also update the testpmd document

OK.

Thanks,
Xingui




More information about the dev mailing list