diff options
| author | TiejunZhou <[email protected]> | 2023-12-27 02:31:07 +0000 |
|---|---|---|
| committer | TiejunZhou <[email protected]> | 2023-12-27 02:31:07 +0000 |
| commit | 862cafaefcb006bf5e3fec880ae6b3908b0bfcc4 (patch) | |
| tree | 4c3fe48992a2d4f6f253bada3b77a038c3cc0c0c | |
| parent | 4ead49b372950204b32ac327a6e6da5271fada1e (diff) | |
Add test infrastructure for TSN
23 files changed, 3154 insertions, 263 deletions
diff --git a/.github/workflows/regression_test.yml b/.github/workflows/regression_test.yml index beec3a8f..ebf6c836 100644 --- a/.github/workflows/regression_test.yml +++ b/.github/workflows/regression_test.yml @@ -43,6 +43,21 @@ jobs: cmake_path: ./test/cmake/web result_affix: Web skip_deploy: true + PTP: + permissions: + contents: read + issues: read + checks: write + pull-requests: write + pages: write + id-token: write + uses: azure-rtos/threadx/.github/workflows/regression_template.yml@master + with: + build_script: ./scripts/build_ptp.sh + test_script: ./scripts/test_ptp.sh + cmake_path: ./test/cmake/ptp + result_affix: PTP + skip_deploy: true MQTT: permissions: contents: read diff --git a/scripts/build_ptp.sh b/scripts/build_ptp.sh new file mode 100755 index 00000000..6f715749 --- /dev/null +++ b/scripts/build_ptp.sh @@ -0,0 +1,3 @@ +#! /bin/bash + +$(dirname `realpath $0`)/../test/cmake/ptp/run.sh build all diff --git a/scripts/test_ptp.sh b/scripts/test_ptp.sh new file mode 100755 index 00000000..f7df4ce7 --- /dev/null +++ b/scripts/test_ptp.sh @@ -0,0 +1,3 @@ +#! /bin/bash + +CTEST_PARALLEL_LEVEL=4 $(dirname `realpath $0`)/../test/cmake/ptp/run.sh test all diff --git a/test/cmake/netxduo/CMakeLists.txt b/test/cmake/netxduo/CMakeLists.txt index ef547351..0879c9c8 100644 --- a/test/cmake/netxduo/CMakeLists.txt +++ b/test/cmake/netxduo/CMakeLists.txt @@ -10,6 +10,7 @@ set(BUILD_CONFIGURATIONS default_build_coverage dhcp_default_build_coverage dns_default_build_coverage + tsn_build_coverage v4_build v4_dns_cache_build v4_no_checksum_build @@ -190,7 +191,7 @@ set(PPP_COMPRESSION -DNX_PPP_COMPRESSION_ENABLE) set(v4_build ${IPV4} ${PACKET_DEBUG}) set(v4_dns_cache_build ${IPV4} ${DNS_CACHE}) set(v4_no_checksum_build ${IPV4} ${DISABLE_TX_CHECKSUM} ${DISABLE_RX_CHECKSUM}) -set(v4_physical_48_build ${IPV4} ${PHY_HEADER} ${MDNS_NO_CLIENT} ${PPPOE}) +set(v4_physical_48_build ${IPV4} ${PHY_HEADER} ${MDNS_NO_CLIENT} ${PPPOE} ${MULTI_INTERFACE}) set(v4_small_build ${IPV4} ${NO_INFO} @@ -328,6 +329,7 @@ set(default_build_coverage -DNX_TAHI_ENABLE -DNX_MAX_PHYSICAL_INTERFACES=4 -DNX_ set(optimize_build ${default_build_coverage} -O3) set(dhcp_default_build_coverage ${default_build_coverage} -DNX_DHCP_CLIENT_USER_CREATE_PACKET_POOL -DNX_DISABLE_ASSERT) set(dns_default_build_coverage ${default_build_coverage} -DNX_DNS_CLIENT_USER_CREATE_PACKET_POOL -DNX_DNS_CLIENT_CLEAR_QUEUE) +set(tsn_build_coverage ${default_build_coverage} ${PHY_HEADER} -DNX_ENABLE_VLAN) if($ENV{ENABLE_64}) message(STATUS "Building for 64bit") diff --git a/test/cmake/netxduo/regression/CMakeLists.txt b/test/cmake/netxduo/regression/CMakeLists.txt index 4042f782..bd79a7f1 100644 --- a/test/cmake/netxduo/regression/CMakeLists.txt +++ b/test/cmake/netxduo/regression/CMakeLists.txt @@ -576,6 +576,7 @@ set(netxduo_test_cases ${SOURCE_DIR}/netxduo_test/netx_16_21_test.c ${SOURCE_DIR}/netxduo_test/netx_tcp_socket_delete_test.c ${SOURCE_DIR}/netxduo_test/netx_ip_link_status_test.c + ${SOURCE_DIR}/netxduo_test/netx_ip_link_status_test2.c ${SOURCE_DIR}/netxduo_test/netx_icmp_tunnel_ipv6_ipv6_ping_test.c ${SOURCE_DIR}/netxduo_test/netx_9_19_01_test.c ${SOURCE_DIR}/netxduo_test/netx_ipv6_hop_by_hop_option_error_test.c @@ -935,6 +936,11 @@ set(sntp_test_cases ${SOURCE_DIR}/sntp_test/netx_sntp_client_kod_test.c ${SOURCE_DIR}/sntp_test/netx_sntp_client_packet_chain_test.c) +set(tsn_test_cases + ${SOURCE_DIR}/tsn_test/netx_mrp_state_machine_test.c + ${SOURCE_DIR}/tsn_test/netx_shaper_cbs_test.c + ${SOURCE_DIR}/tsn_test/netx_shaper_tas_test.c) + if(PRODUCT STREQUAL netxduo) if("-DNX_TAHI_ENABLE" IN_LIST ${CMAKE_BUILD_TYPE}) if("-DNX_ENABLE_IPV6_PATH_MTU_DISCOVERY" IN_LIST ${CMAKE_BUILD_TYPE}) @@ -1301,6 +1307,8 @@ elseif($ENV{DHCP_ONLY}) set(test_cases ${dhcp_test_cases}) elseif($ENV{DNS_ONLY}) set(test_cases ${dns_test_cases}) +elseif($ENV{PTP_ONLY}) + set(test_cases ${ptp_test_cases}) else() set(test_cases ${auto_ip_test_cases} @@ -1327,7 +1335,8 @@ else() ${tahi_test_cases} ${tahi_dhcpv6_test_cases} ${telnet_test_cases} - ${tftp_test_cases}) + ${tftp_test_cases} + ${tsn_test_cases}) endif() foreach(test_case ${test_cases}) diff --git a/test/cmake/ptp/CMakeLists.txt b/test/cmake/ptp/CMakeLists.txt new file mode 100644 index 00000000..85d0b535 --- /dev/null +++ b/test/cmake/ptp/CMakeLists.txt @@ -0,0 +1,100 @@ +cmake_minimum_required(VERSION 3.13 FATAL_ERROR) +cmake_policy(SET CMP0054 NEW) +cmake_policy(SET CMP0057 NEW) +cmake_policy(SET CMP0077 NEW) + +project(web_test LANGUAGES C) + +# Set build configurations +set(BUILD_CONFIGURATIONS default_build_coverage + gptp_slave_build + gptp_master_build) +set(CMAKE_CONFIGURATION_TYPES + ${BUILD_CONFIGURATIONS} + CACHE STRING "list of supported configuration types" FORCE) +set_property(CACHE CMAKE_BUILD_TYPE PROPERTY STRINGS + ${CMAKE_CONFIGURATION_TYPES}) +list(GET CMAKE_CONFIGURATION_TYPES 0 BUILD_TYPE) +if((NOT CMAKE_BUILD_TYPE) OR (NOT ("${CMAKE_BUILD_TYPE}" IN_LIST + CMAKE_CONFIGURATION_TYPES))) + set(CMAKE_BUILD_TYPE + "${BUILD_TYPE}" + CACHE STRING "Build Type of the project" FORCE) +endif() + +if(NOT PRODUCT) + set(PRODUCT netxduo) +endif() + +message(STATUS "Build type: ${CMAKE_BUILD_TYPE}") +message(STATUS "Using toolchain file: ${CMAKE_TOOLCHAIN_FILE}.") + +set(SECURE -DNX_WEB_HTTPS_ENABLE -DNX_TCPSERVER_ENABLE_TLS -DNX_SECURE_ENABLE_CLIENT_CERTIFICATE_VERIFY) +set(MULTIPART -DNX_WEB_HTTP_MULTIPART_ENABLE) +set(DIGEST -DNX_WEB_HTTP_DIGEST_ENABLE) + +set(GPTP -DNX_ENABLE_GPTP -DNX_PTP_CLIENT_TRANSPORT_UDP=0 -DNX_PTP_CLIENT_TRANSPORT_ETHERNET=1) +set(VLAN -DNX_ENABLE_VLAN) +set(gptp_slave_build ${GPTP} ${VLAN}) +set(gptp_master_build ${GPTP} ${VLAN} -DNX_PTP_ENABLE_MASTER) + +add_compile_options( + -m32 + -std=c99 + -ggdb + -g3 + -gdwarf-2 + -fdiagnostics-color + -Werror + -DTX_INCLUDE_USER_DEFINE_FILE + ${${CMAKE_BUILD_TYPE}}) +add_link_options(-m32) + +enable_testing() + +add_subdirectory(${CMAKE_CURRENT_LIST_DIR}/../../.. netxduo) +add_subdirectory(${CMAKE_CURRENT_LIST_DIR}/regression regression) + +# Coverage +if(CMAKE_BUILD_TYPE MATCHES ".*_coverage") + target_compile_options(netxduo PRIVATE -fprofile-arcs -ftest-coverage) + target_link_options(netxduo PRIVATE -fprofile-arcs -ftest-coverage) +endif() + +# Build ThreadX library once +execute_process(COMMAND ${CMAKE_CURRENT_SOURCE_DIR}/run.sh build_libs) +add_custom_target(build_libs ALL COMMAND ${CMAKE_CURRENT_SOURCE_DIR}/run.sh + build_libs) +add_dependencies(netxduo build_libs) +target_include_directories(netxduo PUBLIC ${CMAKE_BINARY_DIR}/../libs/inc) +add_library(threadx SHARED IMPORTED GLOBAL) +add_library("azrtos::threadx" ALIAS threadx) +set_target_properties( + threadx PROPERTIES IMPORTED_LOCATION + ${CMAKE_BINARY_DIR}/../libs/threadx/libthreadx.so) +add_library(filex SHARED IMPORTED GLOBAL) +add_library("azrtos::filex" ALIAS filex) +set_target_properties( + filex PROPERTIES IMPORTED_LOCATION + ${CMAKE_BINARY_DIR}/../libs/filex/libfilex.so) +target_link_libraries(netxduo PUBLIC filex) + +target_compile_options( + netxduo + PRIVATE -Werror + -Wall + -Wextra + -pedantic + -fmessage-length=0 + -fsigned-char + -ffunction-sections + -fdata-sections + -Wunused + -Wuninitialized + -Wmissing-declarations + -Wconversion + -Wpointer-arith + -Wshadow + -Wlogical-op + -Waggregate-return + -Wfloat-equal) diff --git a/test/cmake/ptp/coverage.sh b/test/cmake/ptp/coverage.sh new file mode 100755 index 00000000..cd0e5ec9 --- /dev/null +++ b/test/cmake/ptp/coverage.sh @@ -0,0 +1,8 @@ +#!/bin/bash + +set -e + +cd $(dirname $0) +mkdir -p coverage_report/$1 +gcovr --object-directory=build/$1/netxduo/CMakeFiles/netxduo.dir/addons/ptp -r ../../../addons/ptp --xml-pretty --output coverage_report/$1.xml +gcovr --object-directory=build/$1/netxduo/CMakeFiles/netxduo.dir/addons/ptp -r ../../../addons/ptp --html --html-details --output coverage_report/$1/index.html diff --git a/test/cmake/ptp/libs b/test/cmake/ptp/libs new file mode 120000 index 00000000..d4bda9b4 --- /dev/null +++ b/test/cmake/ptp/libs @@ -0,0 +1 @@ +../libs
\ No newline at end of file diff --git a/test/cmake/ptp/regression b/test/cmake/ptp/regression new file mode 120000 index 00000000..00b470d1 --- /dev/null +++ b/test/cmake/ptp/regression @@ -0,0 +1 @@ +../netxduo/regression/
\ No newline at end of file diff --git a/test/cmake/ptp/run.sh b/test/cmake/ptp/run.sh new file mode 100755 index 00000000..03eea6a3 --- /dev/null +++ b/test/cmake/ptp/run.sh @@ -0,0 +1,9 @@ +#!/bin/bash + +cd $(dirname $0) + +# if threadx repo does not exist, clone it +[ -d ../threadx ] || git clone https://github.com/azure-rtos/threadx.git ../threadx --depth 1 +[ -d ../filex ] || git clone https://github.com/azure-rtos/filex.git ../filex --depth 1 +[ -f .run.sh ] || ln -sf ../threadx/scripts/cmake_bootstrap.sh .run.sh +PTP_ONLY=ON ./.run.sh $*
\ No newline at end of file diff --git a/test/regression/netxduo_test/netx_ip_link_status_test2.c b/test/regression/netxduo_test/netx_ip_link_status_test2.c new file mode 100644 index 00000000..0b47a492 --- /dev/null +++ b/test/regression/netxduo_test/netx_ip_link_status_test2.c @@ -0,0 +1,425 @@ +/** + * @file sample.c + * @brief This is a small demo of the high-performance NetX Duo TCP/IP stack. + * This program demonstrates link packet sending and receiving with a simulated Ethernet driver. + * + */ + +#include "tx_api.h" +#include "nx_api.h" +#include "netxtestcontrol.h" + +extern void test_control_return(UINT); + +#if defined(NX_ENABLE_VLAN) +#include "nx_link.h" + +#define DEMO_STACK_SIZE 2048 +#define DEMO_DATA "ABCDEFGHIJKLMNOPQRSTUVWXYZ " +#define PACKET_SIZE 1536 +#define POOL_SIZE ((sizeof(NX_PACKET) + PACKET_SIZE) * 16) +#define QUEUE_SIZE 1024 +#define ETHER_TYPE 0x8086 +#define VLAN_TAG 0x0001 + + +/* Define the ThreadX and NetX object control blocks... */ + +TX_THREAD thread_0; +TX_THREAD thread_1; +TX_THREAD thread_2; + +NX_PACKET_POOL pool_0; +NX_IP ip_0; +NX_IP ip_1; +UCHAR pool_buffer[POOL_SIZE]; +ULONG link_address_msb_0[2]; +ULONG link_address_lsb_0[2]; +ULONG link_address_msb_1[2]; +ULONG link_address_lsb_1[2]; +NX_LINK_RECEIVE_QUEUE receive_queue[2]; +TX_QUEUE queue[2]; + + + +/* Define the counters used in the demo application... */ + +ULONG thread_0_counter[2]; +ULONG thread_1_and_2_counter[2]; +ULONG error_counter; + + +/* Define thread prototypes. */ + +void thread_0_entry(ULONG thread_input); +void thread_1_and_2_entry(ULONG thread_input); +UINT receive_callback(NX_IP *ip_ptr, UINT interface_index, NX_PACKET *packet_ptr, + ULONG physical_address_msw, ULONG physical_address_lsw, + USHORT packet_type, UINT header_size, VOID *context, + struct NX_LINK_TIME_STRUCT *time_ptr); + +void _nx_ram_network_driver(struct NX_IP_DRIVER_STRUCT *driver_req); +extern void test_control_return(UINT status); + +/* Define main entry point. */ + +int main() +{ + + /* Enter the ThreadX kernel. */ + tx_kernel_enter(); +} + +static VOID set_link_status(NX_IP *ip_ptr, UINT link_status) +{ + + /* Set link status and notify IP layer. */ + ip_ptr -> nx_ip_interface[0].nx_interface_link_up = (UCHAR)link_status; + _nx_ip_driver_link_status_event(ip_ptr, 0); +} + +/* Define what the initial system looks like. */ + +#ifdef CTEST +VOID test_application_define(void *first_unused_memory) +#else +void netx_ip_link_status_test2_application_define(void *first_unused_memory) +#endif +{ + +CHAR *pointer; +UINT status; + + if (NX_PHYSICAL_HEADER < 20) { + printf("NetX Test: IP Link Status Test2.......................................N/A\n"); + test_control_return(3); + } + + /* Setup the working pointer. */ + pointer = (CHAR *)first_unused_memory; + + /* Create the main thread. */ + tx_thread_create(&thread_0, "thread 0", thread_0_entry, 0, + pointer, DEMO_STACK_SIZE, + 4, 4, TX_NO_TIME_SLICE, TX_AUTO_START); + + pointer = pointer + DEMO_STACK_SIZE; + + /* Create the main thread. */ + tx_thread_create(&thread_1, "thread 1", thread_1_and_2_entry, 0, + pointer, DEMO_STACK_SIZE, + 3, 3, TX_NO_TIME_SLICE, TX_AUTO_START); + + pointer = pointer + DEMO_STACK_SIZE; + + /* Create the main thread. */ + tx_thread_create(&thread_2, "thread 2", thread_1_and_2_entry, 1, + pointer, DEMO_STACK_SIZE, + 3, 3, TX_NO_TIME_SLICE, TX_AUTO_START); + + pointer = pointer + DEMO_STACK_SIZE; + + + /* Initialize the NetX system. */ + nx_system_initialize(); + + /* Create a packet pool. */ + status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", PACKET_SIZE, pool_buffer, POOL_SIZE); + + if (status) + { + error_counter++; + } + + /* Create an IP instance. */ + status = nx_ip_create(&ip_0, "NetX IP Instance 0", IP_ADDRESS(0, 0, 0, 0), 0xFFFFFFFFUL, &pool_0, + _nx_ram_network_driver, pointer, DEMO_STACK_SIZE, 1); + pointer = pointer + DEMO_STACK_SIZE; + + /* Create another IP instance. */ + status += nx_ip_create(&ip_1, "NetX IP Instance 1", IP_ADDRESS(0, 0, 0, 0), 0xFFFFFFFFUL, &pool_0, + _nx_ram_network_driver, pointer, DEMO_STACK_SIZE, 1); + pointer = pointer + DEMO_STACK_SIZE; + + if (status) + { + error_counter++; + } + + /* Create a receive queue. */ + status = tx_queue_create(&queue[0], "Queue 0", sizeof(NX_PACKET *) / sizeof(ULONG), + pointer, QUEUE_SIZE / sizeof(ULONG)); + pointer = pointer + QUEUE_SIZE; + + /* Create another receive queue. */ + status += tx_queue_create(&queue[1], "Queue 1", sizeof(NX_PACKET *) / sizeof(ULONG), + pointer, QUEUE_SIZE / sizeof(ULONG)); + pointer = pointer + QUEUE_SIZE; + + if (status) + { + error_counter++; + } +} + + +/* Define receive callback function. */ +UINT receive_callback(NX_IP *ip_ptr, UINT interface_index, NX_PACKET *packet_ptr, + ULONG physical_address_msw, ULONG physical_address_lsw, + USHORT packet_type, UINT header_size, VOID *context, + struct NX_LINK_TIME_STRUCT *time_ptr) +{ + (VOID)(physical_address_msw); + (VOID)(physical_address_lsw); + (VOID)(context); + (VOID)(time_ptr); + + if (packet_type == ETHER_TYPE) + { + + /* Clean off the Ethernet header. */ + packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr + header_size; + + /* Adjust the packet length. */ + packet_ptr -> nx_packet_length = packet_ptr -> nx_packet_length - header_size; + + if (tx_queue_send(&queue[interface_index], &packet_ptr, NX_NO_WAIT)) + { + nx_packet_release(packet_ptr); + } + return(NX_SUCCESS); + } + return(NX_CONTINUE); +} + +void conf_link_layer() +{ + UINT status; + + UCHAR interface_0, interface_1; + + status = nx_link_vlan_interface_create(&ip_0, "NetX IP Interface 0:2", IP_ADDRESS(0, 0, 0, 0), 0xFFFFFFFFUL, VLAN_TAG, 0, &interface_0); + if (status) + { + error_counter++; + } + + status = nx_link_vlan_interface_create(&ip_1, "NetX IP Interface 1:2", IP_ADDRESS(0, 0, 0, 0), 0xFFFFFFFFUL, VLAN_TAG, 0, &interface_1); + if (status) + { + error_counter++; + } + + /* Set receive notify. */ + status = nx_link_packet_receive_callback_add(&ip_1, 0, &receive_queue[0], ETHER_TYPE, receive_callback, NX_NULL); + status += nx_link_packet_receive_callback_add(&ip_1, 1, &receive_queue[1], + NX_LINK_PACKET_TYPE_ALL, receive_callback, NX_NULL); + + if (status) + { + error_counter++; + } +} + +static VOID link_status_change_notify(NX_IP *ip_ptr, UINT interface_index, UINT link_up) +{ +} + +/* Define the test threads. */ + +void thread_0_entry(ULONG thread_input) +{ + +UINT status; +ULONG actual_status; +NX_PACKET *packet_ptr; +ULONG length; +ULONG interface_index; +int i; + + NX_PARAMETER_NOT_USED(thread_input); + + /* Ensure the IP instance has been initialized. */ + nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_WAIT_FOREVER); + + conf_link_layer(); + status = nx_ip_interface_physical_address_get(&ip_0, 0, &link_address_msb_0[0], &link_address_lsb_0[0]); + status += nx_ip_interface_physical_address_get(&ip_0, 1, &link_address_msb_0[1], &link_address_lsb_0[1]); + status += nx_ip_interface_physical_address_get(&ip_1, 0, &link_address_msb_1[0], &link_address_lsb_1[0]); + status += nx_ip_interface_physical_address_get(&ip_1, 1, &link_address_msb_1[1], &link_address_lsb_1[1]); + + /******************************************************/ + /* Tested the nx_ip_link_status_change_notify_set api */ + /******************************************************/ + + /* Set link status change notify will NULL callback function pointer. */ + status = nx_ip_link_status_change_notify_set(&ip_0, link_status_change_notify); + + /* Check for error. */ + if (status != NX_SUCCESS) + { + + printf("ERROR!\n"); + test_control_return(1); + } + + /* Check status... */ + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Loop to repeat things over and over again! */ + for (i = 0; i < 10; i++) + { + + /* Allocate a packet. */ + status = nx_packet_allocate(&pool_0, &packet_ptr, NX_PHYSICAL_HEADER, NX_WAIT_FOREVER); + + /* Check status. */ + if (status != NX_SUCCESS) + { + continue; + } + + /* Write ABCs into the packet payload! */ + nx_packet_data_append(packet_ptr, DEMO_DATA, sizeof(DEMO_DATA), &pool_0, TX_WAIT_FOREVER); + + status = nx_packet_length_get(packet_ptr, &length); + if ((status) || (length != sizeof(DEMO_DATA))) + { + error_counter++; + continue; + } + + /* Add link layer header. */ + if (i % 2 == 0) { + interface_index = 0; + } else { + interface_index = 1; + } + + nx_packet_vlan_priority_set(packet_ptr, 2); + status = nx_link_ethernet_packet_send(&ip_0, interface_index, packet_ptr, + 0xFFFF, 0xFFFFFFFF, + ETHER_TYPE); + + /* Determine if the status is valid. */ + if (status) + { + error_counter++; + continue; + } + + /* Increment thread 0's counter. */ + thread_0_counter[interface_index]++; + // printf("[%lu]: sent: %lu, received: %lu\n", interface_index, thread_0_counter[interface_index], thread_1_and_2_counter[interface_index]); + tx_thread_sleep(1); + } + + if ((thread_0_counter[0] != thread_1_and_2_counter[0]) || + (thread_0_counter[1] != thread_1_and_2_counter[1])) + { + error_counter++; + } + + /* Link status change test */ + if (ip_0.nx_ip_interface[0].nx_interface_link_up != NX_TRUE) { + error_counter++; + } + + if (ip_0.nx_ip_interface[1].nx_interface_link_up != NX_TRUE) { + error_counter++; + } + + /* Simulator link down. */ + set_link_status(&ip_0, NX_FALSE); + + if (ip_0.nx_ip_interface[0].nx_interface_link_up == NX_TRUE) { + error_counter++; + } + + if (ip_0.nx_ip_interface[1].nx_interface_link_up == NX_TRUE) { + error_counter++; + } + + /*Check the status. */ + if (error_counter == 0) + { + printf("SUCCESS!\n"); + test_control_return(0); + } + else + { + printf("ERROR!\n"); + test_control_return(1); + } + +} + +void thread_1_and_2_entry(ULONG thread_input) +{ + +UINT status; +NX_PACKET *packet_ptr; +ULONG actual_status; + + /* Ensure the IP instance has been initialized. */ + nx_ip_status_check(&ip_1, NX_IP_INITIALIZE_DONE, &actual_status, NX_WAIT_FOREVER); + + /* Loop to create and establish server connections. */ + while (1) + { + + /* Receive a link message from the socket. */ + status = tx_queue_receive(&queue[thread_input], &packet_ptr, NX_IP_PERIODIC_RATE); + + /* Check for error. */ + if (status) + { + error_counter++; + } + else + { + + if (packet_ptr -> nx_packet_length != sizeof(DEMO_DATA)) + { + error_counter++; + continue; + } + + if (memcmp(packet_ptr -> nx_packet_prepend_ptr, DEMO_DATA, sizeof(DEMO_DATA))) + { + error_counter++; + continue; + } + + /* Release the packet. */ + nx_packet_release(packet_ptr); + + /* Increment thread 1's counter. */ + thread_1_and_2_counter[thread_input]++; + + if(thread_1_and_2_counter[thread_input] == 5) { + return; + } + } + } +} +#else + +#ifdef CTEST +VOID test_application_define(void *first_unused_memory) +#else +void netx_ip_link_status_test2_application_define(void *first_unused_memory) +#endif +{ + + /* Print out test information banner. */ + printf("NetX Test: IP Link Status Test2.......................................N/A\n"); + test_control_return(3); +} + +#endif diff --git a/test/regression/ptp_test/netx_ptp_client_announce_timeout_test.c b/test/regression/ptp_test/netx_ptp_client_announce_timeout_test.c index 49ba4779..ae7b2771 100644 --- a/test/regression/ptp_test/netx_ptp_client_announce_timeout_test.c +++ b/test/regression/ptp_test/netx_ptp_client_announce_timeout_test.c @@ -54,6 +54,10 @@ UINT status; /* Print out test information banner. */ printf("NetX Test: PTP Announce Timeout Test ................................"); +#if defined(NX_ENABLE_GPTP) || (NX_PTP_CLIENT_TRANSPORT_UDP==0) + printf("N/A\n"); + test_control_return(3); +#else /* Setup the working pointer. */ pointer = (CHAR *) first_unused_memory; @@ -113,6 +117,7 @@ UINT status; /* Check UDP enable status. */ if(status) ASSERT_SUCCESS(status); +#endif } diff --git a/test/regression/ptp_test/netx_ptp_client_api_test.c b/test/regression/ptp_test/netx_ptp_client_api_test.c index 71b5de61..ad1c9968 100644 --- a/test/regression/ptp_test/netx_ptp_client_api_test.c +++ b/test/regression/ptp_test/netx_ptp_client_api_test.c @@ -50,6 +50,10 @@ UINT status; /* Print out test information banner. */ printf("NetX Test: PTP API Test ............................................."); +#if defined(NX_ENABLE_GPTP) || (NX_PTP_CLIENT_TRANSPORT_UDP==0) + printf("N/A\n"); + test_control_return(3); +#else /* Setup the working pointer. */ pointer = (CHAR *) first_unused_memory; @@ -109,6 +113,7 @@ UINT status; /* Check UDP enable status. */ if(status) ASSERT_SUCCESS(status); +#endif } diff --git a/test/regression/ptp_test/netx_ptp_client_basic_test.c b/test/regression/ptp_test/netx_ptp_client_basic_test.c index af7121ac..6a3ccf89 100644 --- a/test/regression/ptp_test/netx_ptp_client_basic_test.c +++ b/test/regression/ptp_test/netx_ptp_client_basic_test.c @@ -50,6 +50,10 @@ UINT status; /* Print out test information banner. */ printf("NetX Test: PTP Basic Test ..........................................."); +#if defined(NX_ENABLE_GPTP) || (NX_PTP_CLIENT_TRANSPORT_UDP==0) + printf("N/A\n"); + test_control_return(3); +#else /* Setup the working pointer. */ pointer = (CHAR *) first_unused_memory; @@ -109,6 +113,7 @@ UINT status; /* Check UDP enable status. */ if(status) ASSERT_SUCCESS(status); +#endif } diff --git a/test/regression/ptp_test/netx_ptp_client_calibrate_test.c b/test/regression/ptp_test/netx_ptp_client_calibrate_test.c index 6a9c892c..ffd18a58 100644 --- a/test/regression/ptp_test/netx_ptp_client_calibrate_test.c +++ b/test/regression/ptp_test/netx_ptp_client_calibrate_test.c @@ -127,6 +127,10 @@ UINT status; /* Print out test information banner. */ printf("NetX Test: PTP Calibrate Test ......................................."); +#if defined(NX_ENABLE_GPTP) || (NX_PTP_CLIENT_TRANSPORT_UDP==0) + printf("N/A\n"); + test_control_return(3); +#else /* Setup the working pointer. */ pointer = (CHAR *) first_unused_memory; @@ -186,6 +190,7 @@ UINT status; /* Check UDP enable status. */ if(status) ASSERT_SUCCESS(status); +#endif } diff --git a/test/regression/ptp_test/netx_ptp_client_ipv6_test.c b/test/regression/ptp_test/netx_ptp_client_ipv6_test.c index de3cea03..3bd113b7 100644 --- a/test/regression/ptp_test/netx_ptp_client_ipv6_test.c +++ b/test/regression/ptp_test/netx_ptp_client_ipv6_test.c @@ -52,6 +52,10 @@ UINT status; /* Print out test information banner. */ printf("NetX Test: PTP IPv6 Test ............................................"); +#if defined(NX_ENABLE_GPTP) || (NX_PTP_CLIENT_TRANSPORT_UDP==0) + printf("N/A\n"); + test_control_return(3); +#else /* Setup the working pointer. */ pointer = (CHAR *) first_unused_memory; @@ -112,6 +116,7 @@ UINT status; /* Check UDP enable status. */ ASSERT_SUCCESS(status); #endif +#endif } #if defined(NX_ENABLE_IPV6_MULTICAST) && defined(FEATURE_NX_IPV6) diff --git a/test/regression/ptp_test/netx_ptp_client_master_selection_test.c b/test/regression/ptp_test/netx_ptp_client_master_selection_test.c index a17a6268..d02c44fd 100644 --- a/test/regression/ptp_test/netx_ptp_client_master_selection_test.c +++ b/test/regression/ptp_test/netx_ptp_client_master_selection_test.c @@ -54,6 +54,10 @@ UINT status; /* Print out test information banner. */ printf("NetX Test: PTP Master Selection Test ................................"); +#if defined(NX_ENABLE_GPTP) || (NX_PTP_CLIENT_TRANSPORT_UDP==0) + printf("N/A\n"); + test_control_return(3); +#else /* Setup the working pointer. */ pointer = (CHAR *) first_unused_memory; @@ -113,6 +117,7 @@ UINT status; /* Check UDP enable status. */ if(status) ASSERT_SUCCESS(status); +#endif } diff --git a/test/regression/ptp_test/netx_ptp_client_two_steps_off_test.c b/test/regression/ptp_test/netx_ptp_client_two_steps_off_test.c index f61c48c8..2d3a4402 100644 --- a/test/regression/ptp_test/netx_ptp_client_two_steps_off_test.c +++ b/test/regression/ptp_test/netx_ptp_client_two_steps_off_test.c @@ -50,6 +50,10 @@ UINT status; /* Print out test information banner. */ printf("NetX Test: PTP Two Steps Off Test ..................................."); +#if defined(NX_ENABLE_GPTP) || (NX_PTP_CLIENT_TRANSPORT_UDP==0) + printf("N/A\n"); + test_control_return(3); +#else /* Setup the working pointer. */ pointer = (CHAR *) first_unused_memory; @@ -109,6 +113,7 @@ UINT status; /* Check UDP enable status. */ if(status) ASSERT_SUCCESS(status); +#endif } diff --git a/test/regression/test/netxtestcontrol.c b/test/regression/test/netxtestcontrol.c index 68395044..958d5082 100644 --- a/test/regression/test/netxtestcontrol.c +++ b/test/regression/test/netxtestcontrol.c @@ -204,6 +204,9 @@ void netx_dest_table_add_fail_test_application_define(void *); void netx_ip_basic_test_application_define(void *); void netx_ip_link_status_test_application_define(void *); +void netx_ip_link_status_test2_application_define(void *); +void netx_shaper_cbs_test_application_define(void *); +void netx_mrp_state_machine_test_application_define(void *); void netx_ip_create_test_application_define(void *); void netx_ip_delete_test_application_define(void *); void netx_ip_status_check_test_application_define(void*); @@ -1459,6 +1462,9 @@ TEST_ENTRY test_control_tests[] = /* IPv4 test */ {netx_ip_basic_test_application_define, TEST_TIMEOUT_LOW}, {netx_ip_link_status_test_application_define, TEST_TIMEOUT_LOW}, + {netx_ip_link_status_test2_application_define, TEST_TIMEOUT_LOW}, + {netx_shaper_cbs_test_application_define, TEST_TIMEOUT_LOW}, + {netx_mrp_state_machine_test_application_define, TEST_TIMEOUT_LOW}, {netx_ip_create_test_application_define, TEST_TIMEOUT_LOW}, {netx_ip_delete_test_application_define, TEST_TIMEOUT_LOW}, {netx_ip_fragmentation_order_test_application_define, TEST_TIMEOUT_LOW}, diff --git a/test/regression/test/nx_ram_network_driver_test_1500.c b/test/regression/test/nx_ram_network_driver_test_1500.c index 65bae081..dfc2c721 100644 --- a/test/regression/test/nx_ram_network_driver_test_1500.c +++ b/test/regression/test/nx_ram_network_driver_test_1500.c @@ -38,6 +38,9 @@ #include "nxd_bsd.h" #endif /* NX_BSD_RAW_PPPOE_SUPPORT */ +#if defined(__PRODUCT_NETXDUO__) && defined(NX_ENABLE_VLAN) +#include "nx_link.h" +#endif #ifdef NX_PCAP_ENABLE #ifdef linux @@ -91,6 +94,8 @@ ULONG driver_data_length; #endif #define NX_ETHERNET_SIZE 14 +#define NX_LINK_MTU 1514 + /* For the simulated ethernet driver, physical addresses are allocated starting at the preset value and then incremented before the next allocation. */ @@ -440,7 +445,9 @@ VOID _nx_ram_network_driver_internal(NX_IP_DRIVER *driver_req_ptr, UINT mtu_siz TX_INTERRUPT_SAVE_AREA NX_IP *ip_ptr; NX_PACKET *packet_ptr; +#ifndef NX_ENABLE_VLAN ULONG *ethernet_frame_ptr; +#endif NX_INTERFACE *interface_ptr; #ifdef __PRODUCT_NETXDUO__ UINT interface_index; @@ -453,6 +460,7 @@ UINT status; ULONG timer_input; NX_PACKET_POOL *pool_ptr; UINT old_threshold = 0; +USHORT ether_type; /* Setup the IP pointer from the driver request. */ ip_ptr = driver_req_ptr -> nx_ip_driver_ptr; @@ -466,8 +474,16 @@ UINT old_threshold = 0; /* Default to successful return. */ driver_req_ptr -> nx_ip_driver_status = NX_SUCCESS; +#ifdef NX_ENABLE_VLAN + /* Let link layer to preprocess the driver request and return actual interface. */ + if (nx_link_driver_request_preprocess(driver_req_ptr, &interface_ptr) != NX_SUCCESS) + { + return; + } +#else /* Setup interface pointer. */ interface_ptr = driver_req_ptr -> nx_ip_driver_interface; +#endif #ifdef __PRODUCT_NETXDUO__ /* Obtain the index number of the network interface. */ @@ -631,8 +647,19 @@ UINT old_threshold = 0; } case NX_LINK_PACKET_SEND: + case NX_LINK_PACKET_BROADCAST: + case NX_LINK_ARP_SEND: + case NX_LINK_ARP_RESPONSE_SEND: + case NX_LINK_RARP_SEND: { - /* Process driver send packet. */ + + /* The IP stack sends down a data packet for transmission. + The device driver needs to prepend a MAC header, and fill in the + Ethernet frame type (assuming Ethernet protocol for network transmission) + based on the type of packet being transmitted. + + The following sequence illustrates this process. */ + /* Place the ethernet frame at the front of the packet. */ packet_ptr = driver_req_ptr -> nx_ip_driver_packet; @@ -646,14 +673,16 @@ UINT old_threshold = 0; } #ifdef NX_ENABLE_INTERFACE_CAPABILITY + if(((driver_req_ptr -> nx_ip_driver_command) == NX_LINK_PACKET_BROADCAST) || + ((driver_req_ptr -> nx_ip_driver_command) == NX_LINK_PACKET_SEND)) _nx_ram_network_driver_calculate_checksum(nx_ram_driver[i].nx_ram_driver_interface_ptr, packet_ptr, NX_FALSE); #endif - /* Advanced function entry for calling. */ if(advanced_packet_process_callback != NX_NULL) { status = advanced_packet_process_callback(ip_ptr, packet_ptr, &op, &delay); + if(!status) return; @@ -717,6 +746,7 @@ UINT old_threshold = 0; break; } } + /*A function entry for calling*/ if(packet_process_callback != NX_NULL) { @@ -726,6 +756,43 @@ UINT old_threshold = 0; return; } + /* Get Ethernet type. */ + if (driver_req_ptr -> nx_ip_driver_command == NX_LINK_ARP_SEND) + { + ether_type = NX_ETHERNET_ARP; + } + else if (driver_req_ptr -> nx_ip_driver_command == NX_LINK_ARP_RESPONSE_SEND) + { + ether_type = NX_ETHERNET_ARP; + } + else if (driver_req_ptr -> nx_ip_driver_command == NX_LINK_RARP_SEND) + { + ether_type = NX_ETHERNET_RARP; + } +#ifdef __PRODUCT_NETXDUO__ + else if (packet_ptr -> nx_packet_ip_version == 6) + { + ether_type = NX_ETHERNET_IPV6; + } +#endif + else + { + ether_type = NX_ETHERNET_IP; + } + +#ifdef NX_ENABLE_VLAN + /* Add Ethernet header. */ + if (nx_link_ethernet_header_add(ip_ptr, + driver_req_ptr -> nx_ip_driver_interface -> nx_interface_index, packet_ptr, + driver_req_ptr -> nx_ip_driver_physical_address_msw, + driver_req_ptr -> nx_ip_driver_physical_address_lsw, + (UINT)ether_type)) + { + + /* Release the packet. */ + nx_packet_transmit_release(packet_ptr); + } +#else /* Adjust the prepend pointer. */ packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr - NX_ETHERNET_SIZE; @@ -759,156 +826,6 @@ UINT old_threshold = 0; (interface_ptr -> nx_interface_physical_address_lsw >> 16); *(ethernet_frame_ptr+3) = (interface_ptr -> nx_interface_physical_address_lsw << 16); -#ifdef FEATURE_NX_IPV6 - if(packet_ptr -> nx_packet_ip_version == 6) - *(ethernet_frame_ptr+3) |= NX_ETHERNET_IPV6; - else -#endif - *(ethernet_frame_ptr+3) |= NX_ETHERNET_IP; - - /* Endian swapping if NX_LITTLE_ENDIAN is defined. */ - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr)); - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+1)); - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+2)); - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+3)); - - /* At this point, the packet is a complete Ethernet frame, ready to be transmitted. - The driver shall call the actual Ethernet transmit routine and put the packet - on the wire. - - In this example, the simulated RAM network transmit routine is called. */ - - /* Check whether we need to duplicate the packet. */ - if(dup_packet_ptr != NX_NULL) - nx_packet_copy(packet_ptr, &dup_packet_ptr, pool_ptr, NX_NO_WAIT); - if(op != NX_RAMDRIVER_OP_DELAY) - _nx_ram_network_driver_output(ip_ptr, packet_ptr, i); - else - tx_timer_activate(&nx_driver_timers[timer_index]); - - /* Send the duplicate packet. */ - if(dup_packet_ptr != NX_NULL) - _nx_ram_network_driver_output(ip_ptr, dup_packet_ptr, i); - - break; - } - - case NX_LINK_PACKET_BROADCAST: - case NX_LINK_ARP_SEND: - case NX_LINK_ARP_RESPONSE_SEND: - case NX_LINK_RARP_SEND: - { - - /* The IP stack sends down a data packet for transmission. - The device driver needs to prepend a MAC header, and fill in the - Ethernet frame type (assuming Ethernet protocol for network transmission) - based on the type of packet being transmitted. - - The following sequence illustrates this process. */ - - - /* Place the ethernet frame at the front of the packet. */ - packet_ptr = driver_req_ptr -> nx_ip_driver_packet; - - if (interface_ptr -> nx_interface_link_up == NX_FALSE) - { - - /* Link is down. Drop the packet. */ - nx_packet_transmit_release(packet_ptr); - return; - } - -#ifdef NX_ENABLE_INTERFACE_CAPABILITY - if((driver_req_ptr -> nx_ip_driver_command) == NX_LINK_PACKET_BROADCAST) - _nx_ram_network_driver_calculate_checksum(nx_ram_driver[i].nx_ram_driver_interface_ptr, packet_ptr, NX_FALSE); -#endif - - /* Advanced function entry for calling. */ - if(advanced_packet_process_callback != NX_NULL) - { - status = advanced_packet_process_callback(ip_ptr, packet_ptr, &op, &delay); - - if(!status) - return; - - /* Advanced process. */ - switch(op) - { - case NX_RAMDRIVER_OP_DROP: - { - - /* Drop the packet. */ - nx_packet_transmit_release(packet_ptr); - return; - }break; - - case NX_RAMDRIVER_OP_DELAY: - { - TX_DISABLE - - /* Find an unused timer. */ - for(timer_index = 0; timer_index < NX_MAX_TIMER; timer_index++) - { - if(nx_driver_timer_used[timer_index] != NX_RAMDRIVER_TIMER_USED) - { - if(nx_driver_timer_used[timer_index] == NX_RAMDRIVER_TIMER_DIRTY) - tx_timer_delete(&nx_driver_timers[timer_index]); - - nx_driver_timer_used[timer_index] = NX_RAMDRIVER_TIMER_USED; - break; - } - } - TX_RESTORE - - if(timer_index < NX_MAX_TIMER) - { - memcpy(&nx_driver_requests[timer_index], driver_req_ptr, sizeof(NX_IP_DRIVER)); - - timer_input = (timer_index << 16) | i; - - tx_timer_create(&nx_driver_timers[timer_index], "Driver timer", - _nx_ram_network_driver_delay_entry, - (ULONG)timer_input, - delay, delay, TX_NO_ACTIVATE); - } - else - { - - /* No available timer, just send bypass. */ - op = NX_RAMDRIVER_OP_BYPASS; - } - }break; - - case NX_RAMDRIVER_OP_DUPLICATE: - { - - /* Set the dup_packet_ptr. */ - dup_packet_ptr = packet_ptr; - }break; - - case NX_RAMDRIVER_OP_BYPASS: - default: - break; - } - } - - /* Adjust the prepend pointer. */ - packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr - NX_ETHERNET_SIZE; - - /* Adjust the packet length. */ - packet_ptr -> nx_packet_length = packet_ptr -> nx_packet_length + NX_ETHERNET_SIZE; - - /* Setup the ethernet frame pointer to build the ethernet frame. Backup another 2 - bytes to get 32-bit word alignment. */ - ethernet_frame_ptr = (ULONG *) (packet_ptr -> nx_packet_prepend_ptr - 2); - - /* Build the ethernet frame. */ - *ethernet_frame_ptr = driver_req_ptr -> nx_ip_driver_physical_address_msw; - *(ethernet_frame_ptr+1) = driver_req_ptr -> nx_ip_driver_physical_address_lsw; - *(ethernet_frame_ptr+2) = (interface_ptr -> nx_interface_physical_address_msw << 16) | - (interface_ptr -> nx_interface_physical_address_lsw >> 16); - *(ethernet_frame_ptr+3) = (interface_ptr -> nx_interface_physical_address_lsw << 16); - if(driver_req_ptr -> nx_ip_driver_command == NX_LINK_ARP_SEND) *(ethernet_frame_ptr+3) |= NX_ETHERNET_ARP; else if(driver_req_ptr -> nx_ip_driver_command == NX_LINK_ARP_RESPONSE_SEND) @@ -928,6 +845,7 @@ UINT old_threshold = 0; NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+1)); NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+2)); NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+3)); +#endif /* NX_ENABLE_VLAN */ /* At this point, the packet is a complete Ethernet frame, ready to be transmitted. The driver shall call the actual Ethernet transmit routine and put the packet @@ -949,7 +867,15 @@ UINT old_threshold = 0; break; } +#ifdef NX_ENABLE_VLAN + case NX_LINK_RAW_PACKET_SEND: + { + /* Send raw packet out directly. */ + _nx_ram_network_driver_output(ip_ptr, driver_req_ptr -> nx_ip_driver_packet, i); + break; + } +#endif /* NX_ENABLE_VLAN */ case NX_LINK_MULTICAST_JOIN: { UINT mcast_index; @@ -1148,7 +1074,9 @@ VOID _nx_ram_network_driver(NX_IP_DRIVER *driver_req_ptr) NX_IP *ip_ptr; NX_PACKET *packet_ptr; +#ifndef NX_ENABLE_VLAN ULONG *ethernet_frame_ptr; +#endif /* NX_ENABLE_VLAN */ NX_INTERFACE *interface_ptr; #ifdef __PRODUCT_NETXDUO__ UINT interface_index; @@ -1156,6 +1084,7 @@ UINT interface_index; UINT i; UINT mtu_size = 128; UINT old_threshold = 0; +USHORT ether_type; /* Setup the IP pointer from the driver request. */ ip_ptr = driver_req_ptr -> nx_ip_driver_ptr; @@ -1163,8 +1092,16 @@ UINT old_threshold = 0; /* Default to successful return. */ driver_req_ptr -> nx_ip_driver_status = NX_SUCCESS; +#ifdef NX_ENABLE_VLAN + /* Let link layer to preprocess the driver request and return actual interface. */ + if (nx_link_driver_request_preprocess(driver_req_ptr, &interface_ptr) != NX_SUCCESS) + { + return; + } +#else /* Setup interface pointer. */ interface_ptr = driver_req_ptr -> nx_ip_driver_interface; +#endif #ifdef __PRODUCT_NETXDUO__ /* Obtain the index number of the network interface. */ @@ -1322,8 +1259,15 @@ UINT old_threshold = 0; } case NX_LINK_PACKET_SEND: + case NX_LINK_PACKET_BROADCAST: + case NX_LINK_ARP_SEND: + case NX_LINK_ARP_RESPONSE_SEND: + case NX_LINK_RARP_SEND: +#ifdef NX_PPP_PPPOE_ENABLE + case NX_LINK_PPPOE_DISCOVERY_SEND: + case NX_LINK_PPPOE_SESSION_SEND: +#endif { - /* Process driver send packet. */ /* Place the ethernet frame at the front of the packet. */ @@ -1338,11 +1282,48 @@ UINT old_threshold = 0; } #ifdef NX_ENABLE_INTERFACE_CAPABILITY + if(((driver_req_ptr -> nx_ip_driver_command) == NX_LINK_PACKET_BROADCAST) || + ((driver_req_ptr -> nx_ip_driver_command) == NX_LINK_PACKET_SEND)) _nx_ram_network_driver_calculate_checksum(nx_ram_driver[i].nx_ram_driver_interface_ptr, packet_ptr, NX_FALSE); #endif - /* Place the ethernet frame at the front of the packet. */ - packet_ptr = driver_req_ptr -> nx_ip_driver_packet; + /* Get Ethernet type. */ + if (driver_req_ptr -> nx_ip_driver_command == NX_LINK_ARP_SEND) + { + ether_type = NX_ETHERNET_ARP; + } + else if (driver_req_ptr -> nx_ip_driver_command == NX_LINK_ARP_RESPONSE_SEND) + { + ether_type = NX_ETHERNET_ARP; + } + else if (driver_req_ptr -> nx_ip_driver_command == NX_LINK_RARP_SEND) + { + ether_type = NX_ETHERNET_RARP; + } +#if defined(__PRODUCT_NETXDUO__) + else if (packet_ptr -> nx_packet_ip_version == 6) + { + ether_type = NX_ETHERNET_IPV6; + } +#endif + else + { + ether_type = NX_ETHERNET_IP; + } + +#ifdef NX_ENABLE_VLAN + /* Add Ethernet header. */ + if (nx_link_ethernet_header_add(ip_ptr, + driver_req_ptr -> nx_ip_driver_interface -> nx_interface_index, packet_ptr, + driver_req_ptr -> nx_ip_driver_physical_address_msw, + driver_req_ptr -> nx_ip_driver_physical_address_lsw, + (UINT)ether_type)) + { + + /* Release the packet. */ + nx_packet_transmit_release(packet_ptr); + } +#else /* Adjust the prepend pointer. */ packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr - NX_ETHERNET_SIZE; @@ -1367,28 +1348,22 @@ UINT old_threshold = 0; /* Setup the ethernet frame pointer to build the ethernet frame. Backup another 2 bytes to get 32-bit word alignment. */ - ethernet_frame_ptr = (ULONG *) (packet_ptr -> nx_packet_prepend_ptr - 2); + /*lint -e{927} -e{826} suppress cast of pointer to pointer, since it is necessary */ + ethernet_frame_ptr = (ULONG *)(packet_ptr -> nx_packet_prepend_ptr - 2); /* Build the ethernet frame. */ *ethernet_frame_ptr = driver_req_ptr -> nx_ip_driver_physical_address_msw; - *(ethernet_frame_ptr+1) = driver_req_ptr -> nx_ip_driver_physical_address_lsw; - *(ethernet_frame_ptr+2) = (interface_ptr -> nx_interface_physical_address_msw << 16) | + *(ethernet_frame_ptr + 1) = driver_req_ptr -> nx_ip_driver_physical_address_lsw; + *(ethernet_frame_ptr + 2) = (interface_ptr -> nx_interface_physical_address_msw << 16) | (interface_ptr -> nx_interface_physical_address_lsw >> 16); - *(ethernet_frame_ptr+3) = (interface_ptr -> nx_interface_physical_address_lsw << 16); - -#ifdef FEATURE_NX_IPV6 - if(packet_ptr -> nx_packet_ip_version == 6) - *(ethernet_frame_ptr+3) |= NX_ETHERNET_IPV6; - else -#endif - *(ethernet_frame_ptr+3) |= NX_ETHERNET_IP; - + *(ethernet_frame_ptr + 3) = (interface_ptr -> nx_interface_physical_address_lsw << 16) | ether_type; /* Endian swapping if NX_LITTLE_ENDIAN is defined. */ NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr)); - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+1)); - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+2)); - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+3)); + NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr + 1)); + NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr + 2)); + NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr + 3)); +#endif /* NX_ENABLE_VLAN */ /* At this point, the packet is a complete Ethernet frame, ready to be transmitted. The driver shall call the actual Ethernet transmit routine and put the packet @@ -1401,86 +1376,16 @@ UINT old_threshold = 0; break; } - case NX_LINK_PACKET_BROADCAST: - case NX_LINK_ARP_SEND: - case NX_LINK_ARP_RESPONSE_SEND: - case NX_LINK_RARP_SEND: -#ifdef NX_PPP_PPPOE_ENABLE - case NX_LINK_PPPOE_DISCOVERY_SEND: - case NX_LINK_PPPOE_SESSION_SEND: -#endif - { - /* Process driver send packet. */ - /* Place the ethernet frame at the front of the packet. */ - packet_ptr = driver_req_ptr -> nx_ip_driver_packet; - - if (interface_ptr -> nx_interface_link_up == NX_FALSE) - { - - /* Link is down. Drop the packet. */ - nx_packet_transmit_release(packet_ptr); - return; - } - -#ifdef NX_ENABLE_INTERFACE_CAPABILITY - if((driver_req_ptr -> nx_ip_driver_command) == NX_LINK_PACKET_BROADCAST) - _nx_ram_network_driver_calculate_checksum(nx_ram_driver[i].nx_ram_driver_interface_ptr, packet_ptr, NX_FALSE); -#endif - - /* Adjust the prepend pointer. */ - packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr - NX_ETHERNET_SIZE; - - /* Adjust the packet length. */ - packet_ptr -> nx_packet_length = packet_ptr -> nx_packet_length + NX_ETHERNET_SIZE; - - /* Setup the ethernet frame pointer to build the ethernet frame. Backup another 2 - bytes to get 32-bit word alignment. */ - ethernet_frame_ptr = (ULONG *) (packet_ptr -> nx_packet_prepend_ptr - 2); - - /* Build the ethernet frame. */ - *ethernet_frame_ptr = driver_req_ptr -> nx_ip_driver_physical_address_msw; - *(ethernet_frame_ptr+1) = driver_req_ptr -> nx_ip_driver_physical_address_lsw; - *(ethernet_frame_ptr+2) = (interface_ptr -> nx_interface_physical_address_msw << 16) | - (interface_ptr -> nx_interface_physical_address_lsw >> 16); - *(ethernet_frame_ptr+3) = (interface_ptr -> nx_interface_physical_address_lsw << 16); - - if(driver_req_ptr -> nx_ip_driver_command == NX_LINK_ARP_SEND) - *(ethernet_frame_ptr+3) |= NX_ETHERNET_ARP; - else if(driver_req_ptr -> nx_ip_driver_command == NX_LINK_ARP_RESPONSE_SEND) - *(ethernet_frame_ptr+3) |= NX_ETHERNET_ARP; - else if(driver_req_ptr -> nx_ip_driver_command == NX_LINK_RARP_SEND) - *(ethernet_frame_ptr+3) |= NX_ETHERNET_RARP; -#ifdef NX_PPP_PPPOE_ENABLE - else if (driver_req_ptr -> nx_ip_driver_command == NX_LINK_PPPOE_DISCOVERY_SEND) - *(ethernet_frame_ptr + 3) |= NX_ETHERNET_PPPOE_DISCOVERY; - else if (driver_req_ptr -> nx_ip_driver_command == NX_LINK_PPPOE_SESSION_SEND) - *(ethernet_frame_ptr + 3) |= NX_ETHERNET_PPPOE_SESSION; -#endif -#ifdef FEATURE_NX_IPV6 - else if(packet_ptr -> nx_packet_ip_version == 6) - *(ethernet_frame_ptr+3) |= NX_ETHERNET_IPV6; -#endif - else - *(ethernet_frame_ptr+3) |= NX_ETHERNET_IP; - - - /* Endian swapping if NX_LITTLE_ENDIAN is defined. */ - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr)); - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+1)); - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+2)); - NX_CHANGE_ULONG_ENDIAN(*(ethernet_frame_ptr+3)); - - /* At this point, the packet is a complete Ethernet frame, ready to be transmitted. - The driver shall call the actual Ethernet transmit routine and put the packet - on the wire. - - In this example, the simulated RAM network transmit routine is called. */ - - _nx_ram_network_driver_output(ip_ptr, packet_ptr, i ); +#ifdef NX_ENABLE_VLAN + case NX_LINK_RAW_PACKET_SEND: + { + /* Send raw packet out directly. */ + _nx_ram_network_driver_output(ip_ptr, driver_req_ptr -> nx_ip_driver_packet, i); break; } +#endif /* NX_ENABLE_VLAN */ case NX_LINK_MULTICAST_JOIN: { @@ -1625,17 +1530,6 @@ UINT old_threshold = 0; } } - - - - - - - - - - - /**************************************************************************/ /* */ /* FUNCTION RELEASE */ @@ -1791,7 +1685,12 @@ UINT j; /* Make a copy of packet for the forwarding. */ if (nx_packet_data_append(packet_copy, driver_data_buffer, driver_data_length, pool_ptr, NX_NO_WAIT)) { - +#ifdef NX_ENABLE_VLAN + /* Error, no point in continuing, just release the packet. */ + nx_link_packet_transmitted(nx_ram_driver[interface_instance_id].nx_ram_driver_ip_ptr, + nx_ram_driver[interface_instance_id].nx_ram_driver_interface_ptr -> nx_interface_index, + packet_ptr, NX_NULL); +#else /* Remove the Ethernet header. */ packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr + NX_ETHERNET_SIZE; @@ -1806,7 +1705,7 @@ UINT j; /* Restore preemption. */ tx_thread_preemption_change(tx_thread_identify(), old_threshold, &old_threshold); - +#endif /* NX_ENABLE_VLAN */ return; } @@ -1882,6 +1781,12 @@ UINT j; } } +#ifdef NX_ENABLE_VLAN + /* Release the packet. */ + nx_link_packet_transmitted(nx_ram_driver[interface_instance_id].nx_ram_driver_ip_ptr, + nx_ram_driver[interface_instance_id].nx_ram_driver_interface_ptr -> nx_interface_index, + packet_ptr, NX_NULL); +#else /* Remove the Ethernet header. In real hardware environments, this is typically done after a transmit complete interrupt. */ packet_ptr -> nx_packet_prepend_ptr = packet_ptr -> nx_packet_prepend_ptr + NX_ETHERNET_SIZE; @@ -1891,7 +1796,7 @@ UINT j; /* Now that the Ethernet frame has been removed, release the packet. */ nx_packet_transmit_release(packet_ptr); - +#endif /* Restore preemption. */ tx_thread_preemption_change(tx_thread_identify(), old_threshold, &old_threshold); } @@ -1946,7 +1851,11 @@ UINT j; /**************************************************************************/ VOID _nx_ram_network_driver_receive(NX_IP *ip_ptr, NX_PACKET *packet_ptr, UINT interface_instance_id) { - +#ifdef NX_ENABLE_VLAN + nx_link_ethernet_packet_received(ip_ptr, + nx_ram_driver[interface_instance_id].nx_ram_driver_interface_ptr -> nx_interface_index, + packet_ptr, NX_NULL); +#else UINT packet_type; /* Pickup the packet header to determine where the packet needs to be @@ -2056,6 +1965,7 @@ UINT packet_type; /* Invalid ethernet header... release the packet. */ nx_packet_release(packet_ptr); } +#endif /* NX_ENABLE_VLAN */ } diff --git a/test/regression/tsn_test/netx_mrp_state_machine_test.c b/test/regression/tsn_test/netx_mrp_state_machine_test.c new file mode 100644 index 00000000..a376521c --- /dev/null +++ b/test/regression/tsn_test/netx_mrp_state_machine_test.c @@ -0,0 +1,1136 @@ +/** + * @file sample.c + * @brief This is a small demo of the high-performance NetX Duo TCP/IP stack. + * This program demonstrates link packet sending and receiving with a simulated Ethernet driver. + * + */ +#include "tx_api.h" +#include "nx_api.h" +#include "netxtestcontrol.h" + +extern void test_control_return(UINT); + +#if defined(NX_ENABLE_VLAN) +#include "nx_srp.h" +#include "nx_link.h" + +/* Define demo stack size. */ +#define PACKET_SIZE 1536 +#define NX_PACKET_POOL_SIZE ((PACKET_SIZE + sizeof(NX_PACKET)) * 30) +#define DEMO_STACK_SIZE 2048 +#define HTTP_STACK_SIZE 2048 +#define IPERF_STACK_SIZE 2048 +#define VLAN_TAG (100 | (3<<13)) +#define SRP_THREAD_PRIORITY 4 + +/* Define the ThreadX and NetX object control blocks... */ +TX_THREAD thread_0; +NX_PACKET_POOL pool_0; +NX_IP ip_0; + +UCHAR *pointer; +UCHAR *http_stack; +UCHAR *iperf_stack; +#ifdef FEATURE_NX_IPV6 +NXD_ADDRESS ipv6_address; +#endif +UCHAR pool_area[NX_PACKET_POOL_SIZE]; + +/* Define the counters used in the demo application... */ +ULONG error_counter; +NX_SRP nx_srp; +static ULONG srp_stack[2048 *2 / sizeof(ULONG)]; + +/* Define thread prototypes. */ +VOID thread_0_entry(ULONG thread_input); +extern VOID nx_iperf_entry(NX_PACKET_POOL *pool_ptr, NX_IP *ip_ptr, UCHAR* http_stack, ULONG http_stack_size, UCHAR *iperf_stack, ULONG iperf_stack_size); +extern void test_control_return(UINT status); + +/***** Substitute your ethernet driver entry function here *********/ +void _nx_ram_network_driver(struct NX_IP_DRIVER_STRUCT *driver_req); + +/* Define main entry point. */ +int main() +{ + + /* Enter the ThreadX kernel. */ + tx_kernel_enter(); +} + +void increase_err_cnt() +{ + error_counter++; +} + +/* Define what the initial system looks like. */ +#ifdef CTEST +VOID test_application_define(void *first_unused_memory) +#else +void netx_mrp_state_machine_test_application_define(void *first_unused_memory) +#endif +{ + +UINT status; + + /* Setup the working pointer. */ + pointer = (UCHAR *) first_unused_memory; + + /* Initialize the NetX system. */ + nx_system_initialize(); + + /* Create a packet pool. */ + status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", + PACKET_SIZE, pool_area, NX_PACKET_POOL_SIZE); + + /* Check for packet pool create errors. */ + if (status) + increase_err_cnt(); + + /* Create an IP instance. */ + status = nx_ip_create(&ip_0, "NetX IP Instance 0", IP_ADDRESS(192, 168, 0, 15), 0xFFFFFF00UL, &pool_0, _nx_ram_network_driver, + pointer, DEMO_STACK_SIZE, 1); + pointer = pointer + DEMO_STACK_SIZE; + + /* Check for IP create errors. */ + if (status) + increase_err_cnt(); + + /* Attach second interface. */ + status = nx_ip_interface_attach(&ip_0, "NetX IP Interface 0:2", + IP_ADDRESS(192, 168, 100, 15), 0xFFFFFFFFUL, _nx_ram_network_driver); + + if (status) + { + increase_err_cnt(); + } + + /* Enable ARP and supply ARP cache memory for IP Instance 0. */ + status = nx_arp_enable(&ip_0, (void *) pointer, 1024); + pointer = pointer + 1024; + + /* Check for ARP enable errors. */ + if (status) + increase_err_cnt(); + + /* Enable ICMP */ + status = nx_icmp_enable(&ip_0); + + /* Check for ICMP enable errors. */ + if(status) + increase_err_cnt(); + + /* Enable UDP traffic. */ + status = nx_udp_enable(&ip_0); + + /* Check for UDP enable errors. */ + if (status) + increase_err_cnt(); + + /* Enable TCP traffic. */ + status = nx_tcp_enable(&ip_0); + + /* Check for TCP enable errors. */ + if (status) + increase_err_cnt(); + + /* Create the main thread. */ + tx_thread_create(&thread_0, "thread 0", thread_0_entry, 0, + pointer, DEMO_STACK_SIZE, + 4, 4, TX_NO_TIME_SLICE, TX_AUTO_START); + pointer = pointer + DEMO_STACK_SIZE; + +#ifdef FEATURE_NX_IPV6 + /* Set up the IPv6 address here. */ + ipv6_address.nxd_ip_address.v6[3] = 0x3; + ipv6_address.nxd_ip_address.v6[2] = 0x0; + ipv6_address.nxd_ip_address.v6[1] = 0x0; + ipv6_address.nxd_ip_address.v6[0] = 0xfe800000; + ipv6_address.nxd_ip_version = NX_IP_VERSION_V6; + + /* Enable ICMPv6 services. */ + status = nxd_icmp_enable(&ip_0); + if (status) + increase_err_cnt(); + + /* Enable IPv6 services. */ + status = nxd_ipv6_enable(&ip_0); + if (status) + increase_err_cnt(); + + status = nxd_ipv6_address_set(&ip_0, 0, &ipv6_address, 10, NX_NULL); + if (status) + increase_err_cnt(); +#endif +} + +/* Define the test threads. */ +void thread_0_entry(ULONG thread_input) +{ +UINT status; +ULONG actual_status; +ULONG interface_index; +NX_INTERFACE *interface_ptr; +USHORT vlan_tag; +USHORT pcp; +UCHAR i; +UCHAR pcp_list[8]; +UCHAR queue_id_list[8]; +UCHAR hw_queue_number, hw_cbs_queue_number; +UINT port_rate; +NX_SRP* srp_ptr; +NX_MRP_ATTRIBUTE* attribute; + + NX_PARAMETER_NOT_USED(thread_input); + + /* Ensure the IP instance has been initialized. */ + nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_WAIT_FOREVER); + + /* Set the HTTP stack and IPerf stack. */ + http_stack = pointer; + pointer += HTTP_STACK_SIZE; + iperf_stack = pointer; + pointer += IPERF_STACK_SIZE; + + /* Call entry function to start iperf test. */ + nx_iperf_entry(&pool_0, &ip_0, http_stack, HTTP_STACK_SIZE, iperf_stack, IPERF_STACK_SIZE); + + interface_index = 0; + interface_ptr = &(ip_0.nx_ip_interface[interface_index]); + + /* Create the SRP client instance */ + status = nx_srp_init(&nx_srp, &ip_0, 0, &pool_0, (UCHAR *)srp_stack, sizeof(srp_stack), SRP_THREAD_PRIORITY); + /* Check for error. */ + if(status) + increase_err_cnt(); + + /* Create an attribute */ + status = nx_mvrp_action_request(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), 100, NX_MVRP_ACTION_NEW); + /* Check for error. */ + if(status) + increase_err_cnt(); + + status = nx_mvrp_attribute_find(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), &attribute, 100); + /* Check for error. */ + if(status) + increase_err_cnt(); + + /* Case 1: Applicant state machine test */ + /* Begin! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + /* New! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_NEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + /* Join! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_JOIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + /* Lv! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO)) + increase_err_cnt(); + + /* rNew! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RNEW); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO)) + increase_err_cnt(); + + /* rJoinIn! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO)) + increase_err_cnt(); + + /* rIn! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RIN); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AA) || (nx_srp.nx_mrp.oper_p2p_mac != NX_FALSE)) + increase_err_cnt(); + + /* rJoinMt! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOINMT); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOINMT); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOINMT); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOINMT); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOINMT); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + /* rMt! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RMT); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RMT); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RMT); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RMT); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RMT); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + /* rLv! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO)) + increase_err_cnt(); + + /* rLA! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + /* periodic! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_PERIODIC); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_PERIODIC); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AA)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_PERIODIC); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AP) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + /* tx! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AA) || (attribute ->applicant.action != NX_MRP_ACTION_SJ)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AN) || (attribute ->applicant.action != NX_MRP_ACTION_SN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + attribute ->registrar.state = NX_MRP_REGISTRAR_STATE_IN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA) || (attribute ->applicant.action != NX_MRP_ACTION_SN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + attribute ->registrar.state = NX_MRP_REGISTRAR_STATE_LV; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AA) || (attribute ->applicant.action != NX_MRP_ACTION_SN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA) || (attribute ->applicant.action != NX_MRP_ACTION_SJ)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO) || (attribute ->applicant.action != NX_MRP_ACTION_SL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA) || (attribute ->applicant.action != NX_MRP_ACTION_SJ)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QP) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TX); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VO) || (attribute ->applicant.action != NX_MRP_ACTION_S)) + increase_err_cnt(); + + /* txLA! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AA) || (attribute ->applicant.action != NX_MRP_ACTION_S)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_AN) || (attribute ->applicant.action != NX_MRP_ACTION_SN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA) || (attribute ->applicant.action != NX_MRP_ACTION_SN)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA) || (attribute ->applicant.action != NX_MRP_ACTION_SJ)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA) || (attribute ->applicant.action != NX_MRP_ACTION_SJ)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA) || (attribute ->applicant.action != NX_MRP_ACTION_SJ)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_QA) || (attribute ->applicant.action != NX_MRP_ACTION_SJ)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + /* txLAF! */ + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_VN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AN; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VN) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LA; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_AP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_QP; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_VP) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + attribute ->applicant.state = NX_MRP_APPLICANT_STATE_LO; + status = nx_mrp_applicant_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLAF); + if (status || (attribute ->applicant.state != NX_MRP_APPLICANT_STATE_LO) || (attribute ->applicant.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + /* Case 2: Registrar state machine test */ + /* Begin! */ + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_IN; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_LV; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_MT; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_BEGIN); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + /* rNew! */ + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_IN; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RNEW); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_IN)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_LV; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RNEW); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_IN)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_MT; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RNEW); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_IN)) + increase_err_cnt(); + + /* rJoinin! */ + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_IN; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_IN)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_LV; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_IN)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_MT; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOININ); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_IN)) + increase_err_cnt(); + + /* rJoinMt! */ + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_IN; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOINMT); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_IN)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_LV; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOINMT); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_IN)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_MT; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RJOINMT); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_IN)) + increase_err_cnt(); + + /* rLv! */ + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_IN; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_LV)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_LV; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_LV)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_MT; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLV); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + /* rLA! */ + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_IN; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_LV)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_LV; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_LV)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_MT; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_RLA); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + /* txLA! */ + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_IN; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_LV)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_LV; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_LV)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_MT; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_TXLA); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + /* Flush! */ + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_IN; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_FLUSH); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_LV; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_FLUSH); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_MT; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_FLUSH); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + /* Leavetimer! */ + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_IN; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LEAVETIMER); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_IN)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_LV; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LEAVETIMER); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + attribute -> registrar.state = NX_MRP_REGISTRAR_STATE_MT; + status = nx_mrp_registrar_event_process(&(nx_srp.nx_mrp), &(nx_srp.nx_mvrp.participant), attribute, NX_MRP_EVENT_LEAVETIMER); + if (status || (attribute -> registrar.state != NX_MRP_REGISTRAR_STATE_MT)) + increase_err_cnt(); + + /* Case 3: LA state machine test */ + /* Begin */ + nx_srp.nx_mvrp.participant.leaveall.state = NX_MRP_LA_STATE_ACTIVE; + status = nx_mrp_leaveall_event_process(&(nx_srp.nx_mvrp.participant), NX_MRP_EVENT_BEGIN); + if (status || (nx_srp.nx_mvrp.participant.leaveall.state != NX_MRP_LA_STATE_PASSIVE) || (nx_srp.nx_mvrp.participant.leaveall.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + nx_srp.nx_mvrp.participant.leaveall.state = NX_MRP_LA_STATE_PASSIVE; + status = nx_mrp_leaveall_event_process(&(nx_srp.nx_mvrp.participant), NX_MRP_EVENT_BEGIN); + if (status || (nx_srp.nx_mvrp.participant.leaveall.state != NX_MRP_LA_STATE_PASSIVE) || (nx_srp.nx_mvrp.participant.leaveall.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + /* tx! */ + nx_srp.nx_mvrp.participant.leaveall.state = NX_MRP_LA_STATE_ACTIVE; + status = nx_mrp_leaveall_event_process(&(nx_srp.nx_mvrp.participant), NX_MRP_EVENT_TX); + if (status || (nx_srp.nx_mvrp.participant.leaveall.state != NX_MRP_LA_STATE_PASSIVE) || (nx_srp.nx_mvrp.participant.leaveall.action != NX_MRP_ACTION_SLA)) + increase_err_cnt(); + + nx_srp.nx_mvrp.participant.leaveall.state = NX_MRP_LA_STATE_PASSIVE; + status = nx_mrp_leaveall_event_process(&(nx_srp.nx_mvrp.participant), NX_MRP_EVENT_TX); + if (status || (nx_srp.nx_mvrp.participant.leaveall.state != NX_MRP_LA_STATE_PASSIVE) || (nx_srp.nx_mvrp.participant.leaveall.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + /* rLA! */ + nx_srp.nx_mvrp.participant.leaveall.state = NX_MRP_LA_STATE_ACTIVE; + status = nx_mrp_leaveall_event_process(&(nx_srp.nx_mvrp.participant), NX_MRP_EVENT_RLA); + if (status || (nx_srp.nx_mvrp.participant.leaveall.state != NX_MRP_LA_STATE_PASSIVE) || (nx_srp.nx_mvrp.participant.leaveall.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + nx_srp.nx_mvrp.participant.leaveall.state = NX_MRP_LA_STATE_PASSIVE; + status = nx_mrp_leaveall_event_process(&(nx_srp.nx_mvrp.participant), NX_MRP_EVENT_RLA); + if (status || (nx_srp.nx_mvrp.participant.leaveall.state != NX_MRP_LA_STATE_PASSIVE) || (nx_srp.nx_mvrp.participant.leaveall.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + /* rLA! */ + nx_srp.nx_mvrp.participant.leaveall.state = NX_MRP_LA_STATE_ACTIVE; + status = nx_mrp_leaveall_event_process(&(nx_srp.nx_mvrp.participant), NX_MRP_EVENT_LEAVEALLTIMER); + if (status || (nx_srp.nx_mvrp.participant.leaveall.state != NX_MRP_LA_STATE_ACTIVE) || (nx_srp.nx_mvrp.participant.leaveall.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + nx_srp.nx_mvrp.participant.leaveall.state = NX_MRP_LA_STATE_PASSIVE; + status = nx_mrp_leaveall_event_process(&(nx_srp.nx_mvrp.participant), NX_MRP_EVENT_LEAVEALLTIMER); + if (status || (nx_srp.nx_mvrp.participant.leaveall.state != NX_MRP_LA_STATE_ACTIVE) || (nx_srp.nx_mvrp.participant.leaveall.action != NX_MRP_ACTION_NULL)) + increase_err_cnt(); + + /*Check the status. */ + if (error_counter == 0) + { + printf("SUCCESS!\n"); + test_control_return(0); + } + else + { + printf("ERROR!\n"); + test_control_return(1); + } +} + +#else + +#ifdef CTEST +VOID test_application_define(void *first_unused_memory) +#else +void netx_mrp_state_machine_test_application_define(void *first_unused_memory) +#endif +{ + + /* Print out test information banner. */ + printf("NetX Test: MRP State Machine Test.......................................N/A\n"); + test_control_return(3); +} + +#endif diff --git a/test/regression/tsn_test/netx_shaper_cbs_test.c b/test/regression/tsn_test/netx_shaper_cbs_test.c new file mode 100644 index 00000000..0c43b6bc --- /dev/null +++ b/test/regression/tsn_test/netx_shaper_cbs_test.c @@ -0,0 +1,848 @@ +/** + * @file sample.c + * @brief This is a small demo of the high-performance NetX Duo TCP/IP stack. + * This program demonstrates link packet sending and receiving with a simulated Ethernet driver. + * + */ +#include "tx_api.h" +#include "nx_api.h" +#include "netxtestcontrol.h" + +extern void test_control_return(UINT); + +#if defined(NX_ENABLE_VLAN) +#include "nx_link.h" +#include "nx_shaper.h" +#define PORT_RATE 100 +/* Define demo stack size. */ +#define PACKET_SIZE 1536 +#define NX_PACKET_POOL_SIZE ((PACKET_SIZE + sizeof(NX_PACKET)) * 30) +#define DEMO_STACK_SIZE 2048 +#define HTTP_STACK_SIZE 2048 +#define IPERF_STACK_SIZE 2048 +#define VLAN_ID 100 + +/* Define the ThreadX and NetX object control blocks... */ +TX_THREAD thread_0; +NX_PACKET_POOL pool_0; +NX_IP ip_0; + +UCHAR *pointer; +UCHAR *http_stack; +UCHAR *iperf_stack; +#ifdef FEATURE_NX_IPV6 +NXD_ADDRESS ipv6_address; +#endif +UCHAR pool_area[NX_PACKET_POOL_SIZE]; + +/* Define the counters used in the demo application... */ +ULONG error_counter; +NX_SHAPER shaper; + +/* Define thread prototypes. */ +VOID thread_0_entry(ULONG thread_input); +extern VOID nx_iperf_entry(NX_PACKET_POOL *pool_ptr, NX_IP *ip_ptr, UCHAR* http_stack, ULONG http_stack_size, UCHAR *iperf_stack, ULONG iperf_stack_size); +extern void test_control_return(UINT status); + +/***** Substitute your ethernet driver entry function here *********/ +void _nx_ram_network_driver(struct NX_IP_DRIVER_STRUCT *driver_req); + +/* Define main entry point. */ +int main() +{ + + /* Enter the ThreadX kernel. */ + tx_kernel_enter(); +} + +/* Define what the initial system looks like. */ +#ifdef CTEST +VOID test_application_define(void *first_unused_memory) +#else +void netx_shaper_cbs_test_application_define(void *first_unused_memory) +#endif +{ + +UINT status; + + /* Setup the working pointer. */ + pointer = (UCHAR *) first_unused_memory; + + /* Initialize the NetX system. */ + nx_system_initialize(); + + /* Create a packet pool. */ + status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", + PACKET_SIZE, pool_area, NX_PACKET_POOL_SIZE); + + /* Check for packet pool create errors. */ + if (status) + error_counter++; + + /* Create an IP instance. */ + status = nx_ip_create(&ip_0, "NetX IP Instance 0", IP_ADDRESS(192, 168, 0, 15), 0xFFFFFF00UL, &pool_0, _nx_ram_network_driver, + pointer, DEMO_STACK_SIZE, 1); + pointer = pointer + DEMO_STACK_SIZE; + + /* Check for IP create errors. */ + if (status) + error_counter++; + + /* Attach second interface. */ + status = nx_ip_interface_attach(&ip_0, "NetX IP Interface 0:2", + IP_ADDRESS(192, 168, 100, 15), 0xFFFFFFFFUL, _nx_ram_network_driver); + + if (status) + { + error_counter++; + } + + /* Enable ARP and supply ARP cache memory for IP Instance 0. */ + status = nx_arp_enable(&ip_0, (void *) pointer, 1024); + pointer = pointer + 1024; + + /* Check for ARP enable errors. */ + if (status) + error_counter++; + + /* Enable ICMP */ + status = nx_icmp_enable(&ip_0); + + /* Check for ICMP enable errors. */ + if(status) + error_counter++; + + /* Enable UDP traffic. */ + status = nx_udp_enable(&ip_0); + + /* Check for UDP enable errors. */ + if (status) + error_counter++; + + /* Enable TCP traffic. */ + status = nx_tcp_enable(&ip_0); + + /* Check for TCP enable errors. */ + if (status) + error_counter++; + + /* Create the main thread. */ + tx_thread_create(&thread_0, "thread 0", thread_0_entry, 0, + pointer, DEMO_STACK_SIZE, + 4, 4, TX_NO_TIME_SLICE, TX_AUTO_START); + pointer = pointer + DEMO_STACK_SIZE; + +#ifdef FEATURE_NX_IPV6 + /* Set up the IPv6 address here. */ + ipv6_address.nxd_ip_address.v6[3] = 0x3; + ipv6_address.nxd_ip_address.v6[2] = 0x0; + ipv6_address.nxd_ip_address.v6[1] = 0x0; + ipv6_address.nxd_ip_address.v6[0] = 0xfe800000; + ipv6_address.nxd_ip_version = NX_IP_VERSION_V6; + + /* Enable ICMPv6 services. */ + status = nxd_icmp_enable(&ip_0); + if (status) + error_counter++; + + /* Enable IPv6 services. */ + status = nxd_ipv6_enable(&ip_0); + if (status) + error_counter++; + + status = nxd_ipv6_address_set(&ip_0, 0, &ipv6_address, 10, NX_NULL); + if (status) + error_counter++; +#endif + + status = nx_link_vlan_id_set(&ip_0, 1, VLAN_ID); + if (status) + error_counter++; + +} + +UINT demo_cbs_set(void* cbs_param, UCHAR shaper_type) +{ + return NX_SUCCESS; +} + +UINT nx_cbs_driver(struct NX_SHAPER_DRIVER_PARAMETER_STRUCT *parameter) +{ + switch (parameter -> nx_shaper_driver_command) + { + case NX_SHAPER_COMMAND_INIT: + break; + + case NX_SHAPER_COMMAND_CONFIG: + break; + + case NX_SHAPER_COMMAND_PARAMETER_SET: + break; + + default: + break; + } + + return (NX_SUCCESS); +} + +/* Define the test threads. */ +void thread_0_entry(ULONG thread_input) +{ +UINT status; +ULONG actual_status; +ULONG interface_index; +NX_INTERFACE *interface_ptr; +NX_SHAPER_CBS_PARAMETER cbs_param; +USHORT pcp; +UCHAR i; +UCHAR pcp_list[8]; +UCHAR queue_id_list[8]; +UCHAR hw_queue_number, hw_cbs_queue_number; +UINT port_rate; + +NX_SHAPER_CONTAINER shaper_container; +NX_SHAPER cbs_shaper; +NX_SHAPER_CBS_PARAMETER cbs_config; +UCHAR shaper_capability; +NX_SHAPER_HW_QUEUE hw_queue[8]; +UINT index; + + NX_PARAMETER_NOT_USED(thread_input); + + /* Ensure the IP instance has been initialized. */ + nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_WAIT_FOREVER); + + /* Set the HTTP stack and IPerf stack. */ + http_stack = pointer; + pointer += HTTP_STACK_SIZE; + iperf_stack = pointer; + pointer += IPERF_STACK_SIZE; + + /* Call entry function to start iperf test. */ + nx_iperf_entry(&pool_0, &ip_0, http_stack, HTTP_STACK_SIZE, iperf_stack, IPERF_STACK_SIZE); + + interface_index = 0; + interface_ptr = &(ip_0.nx_ip_interface[interface_index]); + + memset(&shaper_container , 0, sizeof(NX_SHAPER_CONTAINER)); + /* Case 1: init shaper with 3 hw queue, 2 cbs hw queue */ + status = nx_shaper_create(interface_ptr, &shaper_container, &cbs_shaper, NX_SHAPER_TYPE_CBS, nx_cbs_driver); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + shaper_capability = NX_SHAPER_CAPABILITY_CBS_SUPPORTED | \ + NX_SHAPER_CAPABILITY_TAS_SUPPORTED | \ + NX_SHAPER_CAPABILITY_PREEMPTION_SUPPORTED; + + index = 0; + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, 3, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + status = nx_shaper_default_mapping_get(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 2: init shaper with 4 hw queue, 2 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, 4, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + status = nx_shaper_default_mapping_get(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 3: init shaper with 5 hw queue, 2 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 4; + hw_queue[index].priority = 5; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, 5, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + status = nx_shaper_default_mapping_get(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 4: init shaper with 6 hw queue, 2 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 4; + hw_queue[index].priority = 5; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 5; + hw_queue[index].priority = 6; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, 6, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + status = nx_shaper_default_mapping_get(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 5: init shaper with 7 hw queue, 2 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 4; + hw_queue[index].priority = 5; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 5; + hw_queue[index].priority = 6; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 6; + hw_queue[index].priority = 7; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, 7, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + status = nx_shaper_default_mapping_get(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 6: init shaper with 8 hw queue, 2 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 4; + hw_queue[index].priority = 5; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 5; + hw_queue[index].priority = 6; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 6; + hw_queue[index].priority = 7; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 7; + hw_queue[index].priority = 8; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, 8, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + status = nx_shaper_default_mapping_get(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 7: init shaper with 2 hw queue, 1 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, index, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 8: init shaper with 3 hw queue, 1 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, index, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + + /* Case 9: init shaper with 4 hw queue, 1 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, index, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 10: init shaper with 5 hw queue, 1 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 4; + hw_queue[index].priority = 5; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, index, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 10.1: init shaper with 5 hw queue, 1 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 4; + hw_queue[index].priority = 5; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, index, hw_queue); + if (status != NX_INVALID_PARAMETERS) + { + + error_counter++; + return; + } + + /* Case 10.2: init shaper with 5 hw queue, 1 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 4; + hw_queue[index].priority = 5; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, index, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 11: init shaper with 6 hw queue, 1 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 4; + hw_queue[index].priority = 5; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 5; + hw_queue[index].priority = 6; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, index, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 12: init shaper with 7 hw queue, 1 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 4; + hw_queue[index].priority = 5; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 5; + hw_queue[index].priority = 6; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 6; + hw_queue[index].priority = 7; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, index, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 13 init shaper with 8 hw queue, 1 cbs hw queue */ + memset(interface_ptr -> shaper_container -> hw_queue, 0, sizeof(interface_ptr -> shaper_container -> hw_queue)); + index = 0; + + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 3; + hw_queue[index].priority = 4; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 4; + hw_queue[index].priority = 5; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 5; + hw_queue[index].priority = 6; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 6; + hw_queue[index].priority = 7; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 7; + hw_queue[index].priority = 8; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, index, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 14: set default mapping */ + memset(pcp_list, 0, sizeof(pcp_list)); + memset(queue_id_list, 0, sizeof(queue_id_list)); + status = nx_shaper_default_mapping_get(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + status = nx_shaper_mapping_set(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 15: get current mapping */ + memset(pcp_list, 0, sizeof(pcp_list)); + memset(queue_id_list, 0, sizeof(queue_id_list)); + status = nx_shaper_current_mapping_get(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* Case 17: set the cbs parameters */ + status = nx_shaper_port_rate_get(interface_ptr, &port_rate); + cbs_param.idle_slope = 30; // 30Mbps, 30 percent bandwidth reserve for cbs queue + cbs_param.send_slope = 30 - port_rate; + cbs_param.hi_credit = 463; + cbs_param.low_credit = -1079; + status = nx_shaper_cbs_parameter_set(interface_ptr, &cbs_param, NX_SHAPER_CLASS_B_PCP); + /* Check status... */ + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /*Check the status. */ + if (error_counter == 0) + { + printf("SUCCESS!\n"); + test_control_return(0); + } + else + { + printf("ERROR!\n"); + test_control_return(1); + } +} + +#else + +#ifdef CTEST +VOID test_application_define(void *first_unused_memory) +#else +void netx_shaper_cbs_test_application_define(void *first_unused_memory) +#endif +{ + + /* Print out test information banner. */ + printf("NetX Test: Shaper CBS Test.......................................N/A\n"); + test_control_return(3); +} + +#endif
\ No newline at end of file diff --git a/test/regression/tsn_test/netx_shaper_tas_test.c b/test/regression/tsn_test/netx_shaper_tas_test.c new file mode 100644 index 00000000..f9f8bc68 --- /dev/null +++ b/test/regression/tsn_test/netx_shaper_tas_test.c @@ -0,0 +1,380 @@ +/** + * @file sample.c + * @brief This is a small demo of the high-performance NetX Duo TCP/IP stack. + * This program demonstrates link packet sending and receiving with a simulated Ethernet driver. + * + */ +#include "tx_api.h" +#include "nx_api.h" +#include "netxtestcontrol.h" + +extern void test_control_return(UINT); + +#if defined(NX_ENABLE_VLAN) +#include "nx_link.h" +#include "nx_shaper.h" + +/* Define demo stack size. */ +#define PACKET_SIZE 1536 +#define NX_PACKET_POOL_SIZE ((PACKET_SIZE + sizeof(NX_PACKET)) * 30) +#define DEMO_STACK_SIZE 2048 +#define HTTP_STACK_SIZE 2048 +#define IPERF_STACK_SIZE 2048 +#define VLAN_TAG_1 (200 | (2<<13)) +#define VLAN_TAG_2 (300 | (3<<13)) +#define PORT_RATE 100 +/* Define the ThreadX and NetX object control blocks... */ +TX_THREAD thread_0; +NX_PACKET_POOL pool_0; +NX_IP ip_0; + +UCHAR *pointer; +UCHAR *http_stack; +UCHAR *iperf_stack; +#ifdef FEATURE_NX_IPV6 +NXD_ADDRESS ipv6_address; +#endif +UCHAR pool_area[NX_PACKET_POOL_SIZE]; + +/* Define the counters used in the demo application... */ +ULONG error_counter; +NX_SHAPER shaper; +UINT interface_1_id; +UINT interface_2_id; + +/* Define thread prototypes. */ +VOID thread_0_entry(ULONG thread_input); +extern VOID nx_iperf_entry(NX_PACKET_POOL *pool_ptr, NX_IP *ip_ptr, UCHAR* http_stack, ULONG http_stack_size, UCHAR *iperf_stack, ULONG iperf_stack_size); +extern void test_control_return(UINT status); + +extern UINT nx_tas_driver(NX_SHAPER_DRIVER_PARAMETER *params); +extern UINT nx_cbs_driver(NX_SHAPER_DRIVER_PARAMETER *params); +/***** Substitute your ethernet driver entry function here *********/ +void _nx_ram_network_driver(struct NX_IP_DRIVER_STRUCT *driver_req); + +/* Define main entry point. */ +int main() +{ + + /* Enter the ThreadX kernel. */ + tx_kernel_enter(); +} + +/* Define what the initial system looks like. */ +#ifdef CTEST +VOID test_application_define(void *first_unused_memory) +#else +void netx_shaper_tas_test_application_define(void *first_unused_memory) +#endif +{ + +UINT status; + + /* Setup the working pointer. */ + pointer = (UCHAR *) first_unused_memory; + + /* Initialize the NetX system. */ + nx_system_initialize(); + + /* Create a packet pool. */ + status = nx_packet_pool_create(&pool_0, "NetX Main Packet Pool", + PACKET_SIZE, pool_area, NX_PACKET_POOL_SIZE); + + /* Check for packet pool create errors. */ + if (status) + error_counter++; + + /* Create an IP instance. */ + status = nx_ip_create(&ip_0, "NetX IP Instance 0", IP_ADDRESS(192, 168, 0, 15), 0xFFFFFF00UL, &pool_0, _nx_ram_network_driver, + pointer, DEMO_STACK_SIZE, 1); + pointer = pointer + DEMO_STACK_SIZE; + + /* Check for IP create errors. */ + if (status) + error_counter++; + + /* Attach second interface. */ + status = nx_ip_interface_attach(&ip_0, "NetX IP Interface 0:2", + IP_ADDRESS(192, 168, 100, 15), 0xFFFFFFFFUL, _nx_ram_network_driver); + + if (status) + { + error_counter++; + } + + /* Enable ARP and supply ARP cache memory for IP Instance 0. */ + status = nx_arp_enable(&ip_0, (void *) pointer, 1024); + pointer = pointer + 1024; + + /* Check for ARP enable errors. */ + if (status) + error_counter++; + + /* Enable ICMP */ + status = nx_icmp_enable(&ip_0); + + /* Check for ICMP enable errors. */ + if(status) + error_counter++; + + /* Enable UDP traffic. */ + status = nx_udp_enable(&ip_0); + + /* Check for UDP enable errors. */ + if (status) + error_counter++; + + /* Enable TCP traffic. */ + status = nx_tcp_enable(&ip_0); + + /* Check for TCP enable errors. */ + if (status) + error_counter++; + + /* Create the main thread. */ + tx_thread_create(&thread_0, "thread 0", thread_0_entry, 0, + pointer, DEMO_STACK_SIZE, + 4, 4, TX_NO_TIME_SLICE, TX_AUTO_START); + pointer = pointer + DEMO_STACK_SIZE; + +#ifdef FEATURE_NX_IPV6 + /* Set up the IPv6 address here. */ + ipv6_address.nxd_ip_address.v6[3] = 0x3; + ipv6_address.nxd_ip_address.v6[2] = 0x0; + ipv6_address.nxd_ip_address.v6[1] = 0x0; + ipv6_address.nxd_ip_address.v6[0] = 0xfe800000; + ipv6_address.nxd_ip_version = NX_IP_VERSION_V6; + + /* Enable ICMPv6 services. */ + status = nxd_icmp_enable(&ip_0); + if (status) + error_counter++; + + /* Enable IPv6 services. */ + status = nxd_ipv6_enable(&ip_0); + if (status) + error_counter++; + + status = nxd_ipv6_address_set(&ip_0, 0, &ipv6_address, 10, NX_NULL); + if (status) + error_counter++; +#endif + + status = nx_link_vlan_interface_create(&ip_0, "NetX IP Interface 0:2", IP_ADDRESS(192, 168, 200, 2), 0xFFFFFF00UL, VLAN_TAG_1, 0, &interface_1_id); + if (status) + { + error_counter++; + } + + status = nx_link_vlan_interface_create(&ip_0, "NetX IP Interface 0:3", IP_ADDRESS(192, 168, 300, 2), 0xFFFFFF00UL, VLAN_TAG_2, 0, &interface_2_id); + if (status) + { + error_counter++; + } +} + +UINT demo_cbs_set(void* cbs_param, UCHAR shaper_type) +{ + return NX_SUCCESS; +} + +UINT nx_tas_driver(struct NX_SHAPER_DRIVER_PARAMETER_STRUCT *parameter) +{ + return NX_SUCCESS; +} + +UINT nx_fp_driver(struct NX_SHAPER_DRIVER_PARAMETER_STRUCT *parameter) +{ + return (NX_SUCCESS); +} + +/* Define the test threads. */ +void thread_0_entry(ULONG thread_input) +{ +UINT status; +ULONG actual_status; +ULONG interface_index; +NX_INTERFACE *interface_ptr; +USHORT vlan_tag; +USHORT pcp; +UCHAR i; +UCHAR pcp_list[8]; +UCHAR queue_id_list[8]; +UCHAR hw_queue_number, hw_cbs_queue_number; +UINT port_rate; + +NX_SHAPER_CONTAINER shaper_container; +NX_SHAPER tas_shaper; +NX_SHAPER fp_shaper; +NX_SHAPER_TAS_CONFIG tas_config; +NX_SHAPER_FP_PARAMETER fp_param; +UCHAR shaper_capability; +UINT index; +NX_SHAPER_HW_QUEUE hw_queue[8]; + + NX_PARAMETER_NOT_USED(thread_input); + + memset(&tas_config, 0, sizeof(tas_config)); + memset(&shaper_container , 0, sizeof(NX_SHAPER_CONTAINER)); + /* Ensure the IP instance has been initialized. */ + nx_ip_status_check(&ip_0, NX_IP_INITIALIZE_DONE, &actual_status, NX_WAIT_FOREVER); + + /* Set the HTTP stack and IPerf stack. */ + http_stack = pointer; + pointer += HTTP_STACK_SIZE; + iperf_stack = pointer; + pointer += IPERF_STACK_SIZE; + + /* Call entry function to start iperf test. */ + nx_iperf_entry(&pool_0, &ip_0, http_stack, HTTP_STACK_SIZE, iperf_stack, IPERF_STACK_SIZE); + + interface_index = 0; + interface_ptr = &(ip_0.nx_ip_interface[interface_index]); + + +/* Example start */ + /* case 1: Config TAS shaper: NX_SHAPER_TAS_IDLE_CYCLE_AUTO_FILL_WITH_CLOSE */ + status = nx_shaper_create(interface_ptr, &shaper_container, &tas_shaper, NX_SHAPER_TYPE_TAS, nx_tas_driver); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + status = nx_shaper_create(interface_ptr, &shaper_container, &fp_shaper, NX_SHAPER_TYPE_FP, nx_fp_driver); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + shaper_capability = NX_SHAPER_CAPABILITY_CBS_SUPPORTED | \ + NX_SHAPER_CAPABILITY_TAS_SUPPORTED | \ + NX_SHAPER_CAPABILITY_PREEMPTION_SUPPORTED; + + index = 0; + hw_queue[index].hw_queue_id = 0; + hw_queue[index].priority = 1; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_NORMAL; + + hw_queue[index].hw_queue_id = 1; + hw_queue[index].priority = 2; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + hw_queue[index].hw_queue_id = 2; + hw_queue[index].priority = 3; + hw_queue[index++].type = NX_SHAPER_HW_QUEUE_CBS; + + status = nx_shaper_config(interface_ptr, PORT_RATE, shaper_capability, index, hw_queue); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + status = nx_shaper_default_mapping_get(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + status = nx_shaper_mapping_set(interface_ptr, pcp_list, queue_id_list, 8); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + memset(&fp_param, 0, sizeof(NX_SHAPER_FP_PARAMETER)); + fp_param.verification_enable = NX_TRUE; + fp_param.express_guardband_enable = NX_TRUE; + fp_param.express_queue_bitmap = (1 << 3) | (1 << 2); + fp_param.ha = NX_SHAPER_FP_DEFAULT_HA; + fp_param.ra = NX_SHAPER_FP_DEFAULT_RA; + + status = nx_shaper_fp_parameter_set(interface_ptr, &fp_param); + /* Check status... */ + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + tas_config.base_time = 0; + tas_config.cycle_time = 1000; + tas_config.auto_fill_status = NX_SHAPER_TAS_IDLE_CYCLE_AUTO_FILL_WITH_CLOSE; + tas_config.traffic_count = 2; + + tas_config.traffic[0].pcp = 3; + tas_config.traffic[0].time_offset = 0; + tas_config.traffic[0].duration = 200; + tas_config.traffic[0].traffic_control = NX_SHAPER_TRAFFIC_OPEN; + + tas_config.traffic[1].pcp = 2; + tas_config.traffic[1].time_offset = 400; + tas_config.traffic[1].duration = 100; + tas_config.traffic[1].traffic_control = NX_SHAPER_TRAFFIC_OPEN; + + status = nx_shaper_tas_parameter_set(interface_ptr, &tas_config); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } +/* Example end */ + /* case 2: Config TAS shaper: NX_SHAPER_TAS_IDLE_CYCLE_AUTO_FILL_WITH_OPEN */ + tas_config.auto_fill_status = NX_SHAPER_TAS_IDLE_CYCLE_AUTO_FILL_WITH_OPEN; + status = nx_shaper_tas_parameter_set(interface_ptr, &tas_config); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /* case 3: Config TAS shaper: NX_SHAPER_TAS_IDLE_CYCLE_AUTO_FILL_DISABLED */ + tas_config.auto_fill_status = NX_SHAPER_TAS_IDLE_CYCLE_AUTO_FILL_DISABLED; + status = nx_shaper_tas_parameter_set(interface_ptr, &tas_config); + if (status != NX_SUCCESS) + { + + error_counter++; + return; + } + + /*Check the status. */ + if (error_counter == 0) + { + printf("SUCCESS!\n"); + test_control_return(0); + } + else + { + printf("ERROR!\n"); + test_control_return(1); + } +} + +#else + +#ifdef CTEST +VOID test_application_define(void *first_unused_memory) +#else +void netx_shaper_tas_test_application_define(void *first_unused_memory) +#endif +{ + + /* Print out test information banner. */ + printf("NetX Test: Shaper TAS Test.......................................N/A\n"); + test_control_return(3); +} + +#endif
\ No newline at end of file |
