diff options
Diffstat (limited to 'hicn-plugin/src')
88 files changed, 2040 insertions, 1425 deletions
diff --git a/hicn-plugin/src/CMakeLists.txt b/hicn-plugin/src/CMakeLists.txt index 124d9b5cb..2141ec596 100644 --- a/hicn-plugin/src/CMakeLists.txt +++ b/hicn-plugin/src/CMakeLists.txt @@ -1,4 +1,4 @@ -# Copyright (c) 2017-2020 Cisco and/or its affiliates. +# Copyright (c) 2021-2022 Cisco and/or its affiliates. # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at: @@ -11,290 +11,234 @@ # See the License for the specific language governing permissions and # limitations under the License. -# Dependencies -find_package(Vpp REQUIRED) - -include_directories(${HICN_INCLUDE_DIRS} ${VPP_INCLUDE_DIR}) - -set(LIBHICN_FILES - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/src/mapme.c - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/src/name.c - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/src/ops.c - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/src/protocol/ah.c - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/src/protocol/icmp.c - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/src/protocol/ipv4.c - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/src/protocol/ipv6.c - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/src/protocol/tcp.c -) - -set(LIBHICN_HEADER_FILES_SRC - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/hicn.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/base.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/common.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/error.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/header.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/name.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/protocol.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/ops.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/mapme.h -) - -set(LIBHICN_HEADER_FILES_PROTOCOL - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/protocol/ah.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/protocol/icmp.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/protocol/icmprd.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/protocol/ipv4.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/protocol/ipv6.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/protocol/tcp.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/protocol/udp.h -) +############################################################## +# Dependencies and third party libs +############################################################## +find_package(Vpp ${VPP_DEFAULT_VERSION} EXACT REQUIRED) + +if(CMAKE_SOURCE_DIR STREQUAL PROJECT_SOURCE_DIR) + find_package(Libhicn ${CURRENT_VERSION} REQUIRED NO_MODULE) + list(APPEND HICN_LIBRARIES hicn::hicn.${LIBTYPE}) +else() + set(LIBHICN_LIBRARIES ${LIBHICN_SHARED}) + list(APPEND DEPENDENCIES + ${LIBHICN_LIBRARIES} + ) +endif() -set(LIBHICN_HEADER_FILES_UTIL - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/util/ip_address.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/util/token.h - ${CMAKE_CURRENT_SOURCE_DIR}/../../lib/includes/hicn/util/types.h -) +############################################################## +# Source/Header files +############################################################## set(HICN_PLUGIN_SOURCE_FILES - ${CMAKE_CURRENT_SOURCE_DIR}/hicn.c - ${CMAKE_CURRENT_SOURCE_DIR}/hicn_api.c - ${CMAKE_CURRENT_SOURCE_DIR}/cli.c - ${CMAKE_CURRENT_SOURCE_DIR}/hashtb.c - ${CMAKE_CURRENT_SOURCE_DIR}/mgmt.c - ${CMAKE_CURRENT_SOURCE_DIR}/pcs.c - ${CMAKE_CURRENT_SOURCE_DIR}/route.c - ${CMAKE_CURRENT_SOURCE_DIR}/strategy_dpo_ctx.c - ${CMAKE_CURRENT_SOURCE_DIR}/strategy_dpo_manager.c - ${CMAKE_CURRENT_SOURCE_DIR}/strategy_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/interest_pcslookup_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/interest_hitpit_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/interest_hitcs_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/data_input_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/data_pcslookup_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/data_fwd_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/error.c - ${CMAKE_CURRENT_SOURCE_DIR}/faces/face_cli.c - ${CMAKE_CURRENT_SOURCE_DIR}/faces/face.c - ${CMAKE_CURRENT_SOURCE_DIR}/faces/face_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/faces/iface_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/address_mgr.c - ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_cons.c - ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_prod.c - ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_prod_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_app_cli.c - ${CMAKE_CURRENT_SOURCE_DIR}/pg.c - ${CMAKE_CURRENT_SOURCE_DIR}/strategies/dpo_mw.c - ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_mw.c - ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_mw_cli.c - ${CMAKE_CURRENT_SOURCE_DIR}/strategies/dpo_rr.c - ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_rr.c - ${CMAKE_CURRENT_SOURCE_DIR}/cache_policies/cs_lru.c - ${CMAKE_CURRENT_SOURCE_DIR}/mapme_ack_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/mapme_ctrl_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/mapme_eventmgr.c - ${CMAKE_CURRENT_SOURCE_DIR}/udp_tunnels/udp_decap_node.c - ${CMAKE_CURRENT_SOURCE_DIR}/udp_tunnels/udp_tunnel.c + ${CMAKE_CURRENT_SOURCE_DIR}/hicn.c + ${CMAKE_CURRENT_SOURCE_DIR}/hicn_api.c + ${CMAKE_CURRENT_SOURCE_DIR}/cli.c + ${CMAKE_CURRENT_SOURCE_DIR}/hashtb.c + ${CMAKE_CURRENT_SOURCE_DIR}/infra.c + ${CMAKE_CURRENT_SOURCE_DIR}/mgmt.c + ${CMAKE_CURRENT_SOURCE_DIR}/pcs.c + ${CMAKE_CURRENT_SOURCE_DIR}/route.c + ${CMAKE_CURRENT_SOURCE_DIR}/strategy_dpo_ctx.c + ${CMAKE_CURRENT_SOURCE_DIR}/strategy_dpo_manager.c + ${CMAKE_CURRENT_SOURCE_DIR}/strategy_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/interest_pcslookup_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/interest_hitpit_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/interest_hitcs_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/data_input_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/data_pcslookup_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/data_fwd_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/error.c + ${CMAKE_CURRENT_SOURCE_DIR}/faces/face_cli.c + ${CMAKE_CURRENT_SOURCE_DIR}/faces/face.c + ${CMAKE_CURRENT_SOURCE_DIR}/faces/face_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/faces/iface_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/address_mgr.c + ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_cons.c + ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_prod.c + ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_prod_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_app_cli.c + ${CMAKE_CURRENT_SOURCE_DIR}/pg.c + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/dpo_mw.c + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_mw.c + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_mw_cli.c + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/dpo_rr.c + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_rr.c + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/dpo_rp.c + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_rp.c + ${CMAKE_CURRENT_SOURCE_DIR}/cache_policies/cs_lru.c + ${CMAKE_CURRENT_SOURCE_DIR}/mapme_ack_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/mapme_ctrl_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/mapme_eventmgr.c + ${CMAKE_CURRENT_SOURCE_DIR}/udp_tunnels/udp_decap_node.c + ${CMAKE_CURRENT_SOURCE_DIR}/udp_tunnels/udp_tunnel.c ) set(HICN_PLUGIN_HEADER_FILES - ${CMAKE_CURRENT_SOURCE_DIR}/hicn_all_api_h.h - ${CMAKE_CURRENT_SOURCE_DIR}/hashtb.h - ${CMAKE_CURRENT_SOURCE_DIR}/mgmt.h - ${CMAKE_CURRENT_SOURCE_DIR}/params.h - ${CMAKE_CURRENT_SOURCE_DIR}/pcs.h - ${CMAKE_CURRENT_SOURCE_DIR}/hicn_api.h - ${CMAKE_CURRENT_SOURCE_DIR}/hicn.h - ${CMAKE_CURRENT_SOURCE_DIR}/state.h - ${CMAKE_CURRENT_SOURCE_DIR}/infra.h - ${CMAKE_CURRENT_SOURCE_DIR}/hicn_msg_enum.h - ${CMAKE_CURRENT_SOURCE_DIR}/parser.h - ${CMAKE_CURRENT_SOURCE_DIR}/route.h - ${CMAKE_CURRENT_SOURCE_DIR}/strategy_dpo_ctx.h - ${CMAKE_CURRENT_SOURCE_DIR}/strategy_dpo_manager.h - ${CMAKE_CURRENT_SOURCE_DIR}/strategy.h - ${CMAKE_CURRENT_SOURCE_DIR}/interest_pcslookup.h - ${CMAKE_CURRENT_SOURCE_DIR}/interest_hitpit.h - ${CMAKE_CURRENT_SOURCE_DIR}/interest_hitcs.h - ${CMAKE_CURRENT_SOURCE_DIR}/data_pcslookup.h - ${CMAKE_CURRENT_SOURCE_DIR}/data_fwd.h - ${CMAKE_CURRENT_SOURCE_DIR}/error.h - ${CMAKE_CURRENT_SOURCE_DIR}/face_db.h - ${CMAKE_CURRENT_SOURCE_DIR}/faces/face.h - ${CMAKE_CURRENT_SOURCE_DIR}/faces/face_node.h - ${CMAKE_CURRENT_SOURCE_DIR}/faces/iface_node.h - ${CMAKE_CURRENT_SOURCE_DIR}/faces/inlines.h - ${CMAKE_CURRENT_SOURCE_DIR}/faces/face_dpo.h - ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/address_mgr.h - ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_cons.h - ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_prod.h - ${CMAKE_CURRENT_SOURCE_DIR}/pg.h - ${CMAKE_CURRENT_SOURCE_DIR}/strategies/dpo_mw.h - ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_mw.h - ${CMAKE_CURRENT_SOURCE_DIR}/strategies/dpo_rr.h - ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_rr.h - ${CMAKE_CURRENT_SOURCE_DIR}/cache_policies/cs_policy.h - ${CMAKE_CURRENT_SOURCE_DIR}/cache_policies/cs_lru.h - ${CMAKE_CURRENT_SOURCE_DIR}/mapme.h - ${CMAKE_CURRENT_SOURCE_DIR}/mapme_ack.h - ${CMAKE_CURRENT_SOURCE_DIR}/mapme_ctrl.h - ${CMAKE_CURRENT_SOURCE_DIR}/mapme_eventmgr.h - ${CMAKE_CURRENT_SOURCE_DIR}/udp_tunnels/udp_tunnel.h + ${CMAKE_CURRENT_SOURCE_DIR}/hicn_all_api_h.h + ${CMAKE_CURRENT_SOURCE_DIR}/hicn_logging.h + ${CMAKE_CURRENT_SOURCE_DIR}/hashtb.h + ${CMAKE_CURRENT_SOURCE_DIR}/mgmt.h + ${CMAKE_CURRENT_SOURCE_DIR}/params.h + ${CMAKE_CURRENT_SOURCE_DIR}/pcs.h + ${CMAKE_CURRENT_SOURCE_DIR}/hicn_api.h + ${CMAKE_CURRENT_SOURCE_DIR}/hicn.h + ${CMAKE_CURRENT_SOURCE_DIR}/state.h + ${CMAKE_CURRENT_SOURCE_DIR}/infra.h + ${CMAKE_CURRENT_SOURCE_DIR}/hicn_msg_enum.h + ${CMAKE_CURRENT_SOURCE_DIR}/parser.h + ${CMAKE_CURRENT_SOURCE_DIR}/route.h + ${CMAKE_CURRENT_SOURCE_DIR}/strategy_dpo_ctx.h + ${CMAKE_CURRENT_SOURCE_DIR}/strategy_dpo_manager.h + ${CMAKE_CURRENT_SOURCE_DIR}/strategy.h + ${CMAKE_CURRENT_SOURCE_DIR}/interest_pcslookup.h + ${CMAKE_CURRENT_SOURCE_DIR}/interest_hitpit.h + ${CMAKE_CURRENT_SOURCE_DIR}/interest_hitcs.h + ${CMAKE_CURRENT_SOURCE_DIR}/data_pcslookup.h + ${CMAKE_CURRENT_SOURCE_DIR}/data_fwd.h + ${CMAKE_CURRENT_SOURCE_DIR}/error.h + ${CMAKE_CURRENT_SOURCE_DIR}/face_db.h + ${CMAKE_CURRENT_SOURCE_DIR}/faces/face.h + ${CMAKE_CURRENT_SOURCE_DIR}/faces/face_node.h + ${CMAKE_CURRENT_SOURCE_DIR}/faces/iface_node.h + ${CMAKE_CURRENT_SOURCE_DIR}/faces/inlines.h + ${CMAKE_CURRENT_SOURCE_DIR}/faces/face_dpo.h + ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/address_mgr.h + ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_cons.h + ${CMAKE_CURRENT_SOURCE_DIR}/faces/app/face_prod.h + ${CMAKE_CURRENT_SOURCE_DIR}/pg.h + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/dpo_mw.h + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_mw.h + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/dpo_rr.h + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_rr.h + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/dpo_rp.h + ${CMAKE_CURRENT_SOURCE_DIR}/strategies/strategy_rp.h + ${CMAKE_CURRENT_SOURCE_DIR}/cache_policies/cs_policy.h + ${CMAKE_CURRENT_SOURCE_DIR}/cache_policies/cs_lru.h + ${CMAKE_CURRENT_SOURCE_DIR}/mapme.h + ${CMAKE_CURRENT_SOURCE_DIR}/mapme_ack.h + ${CMAKE_CURRENT_SOURCE_DIR}/mapme_ctrl.h + ${CMAKE_CURRENT_SOURCE_DIR}/mapme_eventmgr.h + ${CMAKE_CURRENT_SOURCE_DIR}/udp_tunnels/udp_tunnel.h ) set(HICN_API_TEST_SOURCE_FILES - ${CMAKE_CURRENT_SOURCE_DIR}/hicn_api_test.c - ${CMAKE_CURRENT_SOURCE_DIR}/error.c) + ${CMAKE_CURRENT_SOURCE_DIR}/hicn_api_test.c + ${CMAKE_CURRENT_SOURCE_DIR}/error.c +) set(HICN_API_HEADER_FILES - ${CMAKE_CURRENT_SOURCE_DIR}/hicn_msg_enum.h - ${CMAKE_CURRENT_SOURCE_DIR}/hicn_all_api_h.h - ${CMAKE_CURRENT_SOURCE_DIR}/hicn_api.h - ${CMAKE_CURRENT_SOURCE_DIR}/error.h) + ${HICNPLUGIN_TO_INSTALL_HEADER_FILES} +) set(HICN_API_GENERATED_FILES - ${CMAKE_CURRENT_BINARY_DIR}/vpp_plugins/hicn/hicn.api.h - ${CMAKE_CURRENT_BINARY_DIR}/vpp_plugins/hicn/hicn.api_types.h - ${CMAKE_CURRENT_BINARY_DIR}/vpp_plugins/hicn/hicn.api_enum.h + ${PROJECT_BINARY_DIR}/vpp_plugins/hicn/hicn.api.h + ${PROJECT_BINARY_DIR}/vpp_plugins/hicn/hicn.api_types.h + ${PROJECT_BINARY_DIR}/vpp_plugins/hicn/hicn.api_enum.h ) set(HICN_VAPI_GENERATED_FILES - ${CMAKE_CURRENT_BINARY_DIR}/vapi/hicn.api.vapi.h - ${CMAKE_CURRENT_BINARY_DIR}/vapi/hicn.api.vapi.hpp) + ${PROJECT_BINARY_DIR}/vapi/hicn.api.vapi.h + ${PROJECT_BINARY_DIR}/vapi/hicn.api.vapi.hpp +) -set(HICN_VPP_STARTUP_CONF_FILE - ${CMAKE_BINARY_DIR}/startup.conf) +############################################################## +# Assume VPP is installed in standard location +############################################################## if (NOT VPP_HOME) - set(VPP_HOME /usr) + set(VPP_HOME /usr) endif() -if (NOT CMAKE_BUILD_TYPE) - set (CMAKE_BUILD_TYPE "Release") -endif (NOT CMAKE_BUILD_TYPE) - -SET(HICN_INSTALL_PREFIX ${CMAKE_INSTALL_PREFIX}/${CMAKE_INSTALL_LIBDIR} CACHE STRING "hicn_install_prefix") - -file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/hicn) -file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/vapi) -file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/vnet/ip) -file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/vnet/fib) -file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/vnet/udp) -file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/vpp_plugins) -file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/vpp_plugins/hicn) -include(Packager) -extract_version() - -# These files are missing from vpp binary distribution -execute_process( - COMMAND - bash -c - "if [ ! -e ${CMAKE_CURRENT_BINARY_DIR}/vapi_json_parser.py ]; then - curl https://raw.githubusercontent.com/FDio/vpp/stable/2106/src/vpp-api/vapi/vapi_json_parser.py -o ${CMAKE_CURRENT_BINARY_DIR}/vapi_json_parser.py; - fi; - if [ ! -e ${CMAKE_CURRENT_BINARY_DIR}/vapi_c_gen.py ]; then - curl https://raw.githubusercontent.com/FDio/vpp/stable/2106/src/vpp-api/vapi/vapi_c_gen.py -o ${CMAKE_CURRENT_BINARY_DIR}/vapi_c_gen.py; - fi; - if [ ! -e ${CMAKE_CURRENT_BINARY_DIR}/vapi_cpp_gen.py ]; then - curl https://raw.githubusercontent.com/FDio/vpp/stable/2106/src/vpp-api/vapi/vapi_cpp_gen.py -o ${CMAKE_CURRENT_BINARY_DIR}/vapi_cpp_gen.py; - fi; - if [ ! -e ${CMAKE_CURRENT_BINARY_DIR}/vnet/ip/ip_types.api ]; then - curl https://raw.githubusercontent.com/FDio/vpp/stable/2106/src/vnet/ip/ip_types.api -o ${CMAKE_CURRENT_BINARY_DIR}/vnet/ip/ip_types.api; - fi; - if [ ! -e ${CMAKE_CURRENT_BINARY_DIR}/vnet/fib/fib_entry_track.h ]; then - curl https://raw.githubusercontent.com/FDio/vpp/stable/2106/src/vnet/fib/fib_entry_track.h -o ${CMAKE_CURRENT_BINARY_DIR}/vnet/fib/fib_entry_track.h; - fi; - if [ ! -e ${CMAKE_CURRENT_BINARY_DIR}/vnet/udp/udp_encap.h ]; then - curl https://raw.githubusercontent.com/FDio/vpp/stable/2106/src/vnet/udp/udp_encap.h -o ${CMAKE_CURRENT_BINARY_DIR}/vnet/udp/udp_encap.h; - fi; - - chmod +x ${CMAKE_CURRENT_BINARY_DIR}/vapi_json_parser.py ${CMAKE_CURRENT_BINARY_DIR}/vapi_c_gen.py ${CMAKE_CURRENT_BINARY_DIR}/vapi_cpp_gen.py" +############################################################## +# RPath +############################################################## +SET(HICN_INSTALL_PREFIX + ${CMAKE_INSTALL_PREFIX}/${CMAKE_INSTALL_LIBDIR} ) -execute_process( - COMMAND ${VPP_HOME}/bin/vppapigen --includedir ${CMAKE_CURRENT_BINARY_DIR} --input ${CMAKE_CURRENT_SOURCE_DIR}/hicn.api --output ${CMAKE_CURRENT_BINARY_DIR}/vpp_plugins/hicn/hicn.api.h --outputdir ${CMAKE_CURRENT_BINARY_DIR}/vpp_plugins/hicn/ - COMMAND ${VPP_HOME}/bin/vppapigen JSON --includedir ${CMAKE_CURRENT_BINARY_DIR} --input ${CMAKE_CURRENT_SOURCE_DIR}/hicn.api --output ${CMAKE_CURRENT_BINARY_DIR}/vapi/hicn.api.json --outputdir ${CMAKE_CURRENT_BINARY_DIR}/vapi/ -) -execute_process( - COMMAND ${CMAKE_CURRENT_BINARY_DIR}/vapi_c_gen.py ${CMAKE_CURRENT_BINARY_DIR}/vapi/hicn.api.json - COMMAND ${CMAKE_CURRENT_BINARY_DIR}/vapi_cpp_gen.py ${CMAKE_CURRENT_BINARY_DIR}/vapi/hicn.api.json -) - -include_directories(SYSTEM) -include_directories(${CMAKE_CURRENT_BINARY_DIR}) - -set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -DHICN_VPP_PLUGIN=1") -add_library(hicn_plugin SHARED - ${LIBHICN_FILES} - ${HICN_PLUGIN_SOURCE_FILES} - ${HICN_API_GENERATED_FILES} - ${HICN_VAPI_GENERATED_FILES}) -file(COPY ${HICN_API_HEADER_FILES} DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/vpp_plugins/hicn) -include_directories(${CMAKE_CURRENT_BINARY_DIR}/vpp_plugins) - -file(COPY ${LIBHICN_HEADER_FILES_SRC} DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/hicn) -file(COPY ${LIBHICN_HEADER_FILES_PROTOCOL} DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/hicn/protocol) -file(COPY ${LIBHICN_HEADER_FILES_UTIL} DESTINATION ${CMAKE_CURRENT_BINARY_DIR}/hicn/util) - -add_library(hicn_api_test_plugin SHARED - ${HICN_API_TEST_SOURCE_FILES} - ${HICN_API_GENERATED_FILES}) +############################################################## +# Compiler Options +############################################################## +set(COMPILER_OPTIONS + ${DEFAULT_COMPILER_OPTIONS} + ${MARCH_COMPILER_OPTIONS} + PRIVATE "-Wno-address-of-packed-member" +) -set(VPP_INSTALL_PLUGIN ${HICN_INSTALL_PREFIX}/vpp_plugins) -set(VPP_INSTALL_API_TEST_PLUGIN ${HICN_INSTALL_PREFIX}/vpp_api_test_plugins CACHE STRING "vpp_install_api_test_plugin") -set(VPP_STARTUP_CONF /etc/vpp/) -set_target_properties(hicn_plugin - PROPERTIES - LINKER_LANGUAGE C - INSTALL_RPATH ${VPP_INSTALL_PLUGIN} - COMPILE_FLAGS "-march=native -Wno-address-of-packed-member" - PREFIX "") -set_target_properties(hicn_api_test_plugin - PROPERTIES - LINKER_LANGUAGE C - COMPILE_FLAGS "-march=native -Wno-address-of-packed-member" - PREFIX "") +############################################################## +# Compiler Definitions +############################################################## +set(COMPILE_DEFINITIONS + "-DHICN_VPP_PLUGIN=1" +) if (${CMAKE_BUILD_TYPE} MATCHES "Debug") - target_compile_definitions(hicn_plugin PRIVATE "CLIB_DEBUG") - target_compile_definitions(hicn_api_test_plugin PRIVATE "CLIB_DEBUG") + list(APPEND COMPILE_DEFINITIONS + "-DHICN_DDEBUG" + "-DCLIB_DEBUG" + ) endif() -message (STATUS "hicn-plugin variable ${HICN_PLUGIN}") -install(DIRECTORY - DESTINATION ${VPP_INSTALL_PLUGIN} - COMPONENT ${HICN_PLUGIN}) -install(TARGETS hicn_plugin - DESTINATION - ${VPP_INSTALL_PLUGIN} - COMPONENT ${HICN_PLUGIN}) +############################################################## +# VPP API Generation +############################################################## +file(MAKE_DIRECTORY ${PROJECT_BINARY_DIR}/vapi) +file(MAKE_DIRECTORY ${PROJECT_BINARY_DIR}/vpp_plugins/hicn) -install(DIRECTORY - DESTINATION ${VPP_INSTALL_API_TEST_PLUGIN} - COMPONENT ${HICN_PLUGIN}) -install(TARGETS hicn_api_test_plugin - DESTINATION ${VPP_INSTALL_API_TEST_PLUGIN} - COMPONENT ${HICN_PLUGIN}) +execute_process( + COMMAND ${VPP_HOME}/bin/vppapigen --includedir ${VPP_HOME}/include --input ${CMAKE_CURRENT_SOURCE_DIR}/hicn.api --output ${PROJECT_BINARY_DIR}/vpp_plugins/hicn/hicn.api.h --outputdir ${PROJECT_BINARY_DIR}/vpp_plugins/hicn/ + COMMAND ${VPP_HOME}/bin/vppapigen JSON --includedir ${VPP_HOME}/include --input ${CMAKE_CURRENT_SOURCE_DIR}/hicn.api --output ${PROJECT_BINARY_DIR}/vapi/hicn.api.json --outputdir ${PROJECT_BINARY_DIR}/vapi/ +) +execute_process( + COMMAND ${VPP_HOME}/bin/vapi_c_gen.py ${PROJECT_BINARY_DIR}/vapi/hicn.api.json + COMMAND ${VPP_HOME}/bin/vapi_cpp_gen.py ${PROJECT_BINARY_DIR}/vapi/hicn.api.json +) -install(FILES ${HICN_API_HEADER_FILES} ${HICN_API_GENERATED_FILES} - DESTINATION ${CMAKE_INSTALL_PREFIX}/${CMAKE_INSTALL_INCLUDEDIR}/vpp_plugins/hicn - COMPONENT ${HICN_PLUGIN}-dev) -install(FILES ${HICN_API_GENERATED_FILES} - DESTINATION ${CMAKE_INSTALL_PREFIX}/${CMAKE_INSTALL_INCLUDEDIR}/vpp_plugins/hicn - COMPONENT ${HICN_PLUGIN}-dev) +############################################################## +# Include directories +############################################################## +set(HICN_PLUGIN_INCLUDE_DIRS_INTERNAL + PRIVATE + ${CMAKE_CURRENT_SOURCE_DIR} + ${VPP_INCLUDE_DIR} + PUBLIC + $<BUILD_INTERFACE:${PROJECT_BINARY_DIR}> + $<BUILD_INTERFACE:${HICNPLUGIN_INCLUDE_DIRS}> + $<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}> +) + -install(FILES ${HICN_VAPI_GENERATED_FILES} - DESTINATION ${CMAKE_INSTALL_PREFIX}/${CMAKE_INSTALL_INCLUDEDIR}/vapi - COMPONENT ${HICN_PLUGIN}-dev) +############################################################## +# Build hicn plugins for VPP +############################################################## +build_module(${HICNPLUGIN} + SOURCES ${HICN_PLUGIN_SOURCE_FILES} + INSTALL_HEADERS ${HICN_API_HEADER_FILES} ${HICN_API_GENERATED_FILES} + LINK_LIBRARIES PRIVATE ${LIBHICN_LIBRARIES} + DEPENDS ${DEPENDENCIES} + COMPONENT ${HICN_PLUGIN} + INCLUDE_DIRS ${HICN_PLUGIN_INCLUDE_DIRS_INTERNAL} + HEADER_ROOT_DIR "vpp_plugins" + LIBRARY_ROOT_DIR "vpp_plugins" + DEFINITIONS PUBLIC ${COMPILE_DEFINITIONS} + COMPILE_OPTIONS ${COMPILER_OPTIONS} + INSTALL_RPATH "${VPP_INSTALL_PLUGIN}:${HICN_INSTALL_PREFIX}:${VPP_HOME}/lib" +) -#Set variables for other project depending on hicn-plugin -set(HICNPLUGIN_INCLUDE_DIRS - ${CMAKE_CURRENT_BINARY_DIR} - ${CMAKE_CURRENT_BINARY_DIR}/vpp_plugins - ${VPP_INCLUDE_DIRS} - CACHE INTERNAL "" FORCE) -set(HICNPLUGIN_LIBRARIES ${VPP_LIBRARIES} CACHE INTERNAL "" FORCE) +build_module(${HICN_API_TEST_PLUGIN} + SOURCES ${HICN_API_TEST_SOURCE_FILES} + INSTALL_HEADERS ${HICN_VAPI_GENERATED_FILES} + COMPONENT ${HICN_PLUGIN} + INCLUDE_DIRS ${HICN_PLUGIN_INCLUDE_DIRS_INTERNAL} + HEADER_ROOT_DIR "vapi" + LIBRARY_ROOT_DIR "vpp_api_test_plugins" + DEFINITIONS PUBLIC ${COMPILE_DEFINITIONS} + COMPILE_OPTIONS ${COMPILER_OPTIONS} + INSTALL_RPATH "${VPP_INSTALL_PLUGIN}:${HICN_INSTALL_PREFIX}:${VPP_HOME}/lib" +) diff --git a/hicn-plugin/src/cache_policies/cs_lru.c b/hicn-plugin/src/cache_policies/cs_lru.c index 408a6cb49..e65f487e1 100644 --- a/hicn-plugin/src/cache_policies/cs_lru.c +++ b/hicn-plugin/src/cache_policies/cs_lru.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/cache_policies/cs_lru.h b/hicn-plugin/src/cache_policies/cs_lru.h index c939b45df..35b82ff2c 100644 --- a/hicn-plugin/src/cache_policies/cs_lru.h +++ b/hicn-plugin/src/cache_policies/cs_lru.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/cache_policies/cs_policy.h b/hicn-plugin/src/cache_policies/cs_policy.h index 505138943..73f3de107 100644 --- a/hicn-plugin/src/cache_policies/cs_policy.h +++ b/hicn-plugin/src/cache_policies/cs_policy.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/cli.c b/hicn-plugin/src/cli.c index 8ecbf7a95..cd45607ca 100644 --- a/hicn-plugin/src/cli.c +++ b/hicn-plugin/src/cli.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -22,6 +22,9 @@ #include <vnet/ip/ip6_packet.h> // ip46_address_t #include <vnet/ip/format.h> #include <vnet/fib/fib_types.h> +#include <vnet/pg/pg.h> + +#include <vpp_plugins/hicn/hicn_api.h> #include "hicn.h" #include "infra.h" @@ -33,7 +36,6 @@ #include "error.h" #include "faces/face.h" #include "route.h" -#include "hicn_api.h" static vl_api_hicn_api_node_params_set_t node_ctl_params = { .pit_max_size = -1, @@ -65,8 +67,8 @@ hicn_cli_node_ctl_start_set_command_fn (vlib_main_t *vm, get_error_string (ret)); return (ret == HICN_ERROR_NONE) ? - 0 : - clib_error_return (0, get_error_string (ret)); + 0 : + clib_error_return (0, get_error_string (ret)); } /* @@ -91,7 +93,7 @@ hicn_cli_node_ctl_stop_set_command_fn (vlib_main_t *vm, { return (0); } - while (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT) + if (unformat_check_input (line_input) != UNFORMAT_END_OF_INPUT) { return clib_error_return (0, "%s '%U'", get_error_string (HICN_ERROR_CLI_INVAL), @@ -103,8 +105,8 @@ hicn_cli_node_ctl_stop_set_command_fn (vlib_main_t *vm, node_ctl_params.pit_max_lifetime_sec, node_ctl_params.cs_max_size, ~0); return (ret == HICN_ERROR_NONE) ? - 0 : - clib_error_return (0, get_error_string (ret)); + 0 : + clib_error_return (0, get_error_string (ret)); } #define DFLTD_RANGE_OK(val, min, max) \ @@ -201,8 +203,8 @@ hicn_cli_node_ctl_param_set_command_fn (vlib_main_t *vm, "compilation time for better performances\n"); return (rv == HICN_ERROR_NONE) ? - 0 : - clib_error_return (0, "%s '%U'", get_error_string (rv), + 0 : + clib_error_return (0, "%s '%U'", get_error_string (rv), format_unformat_error, line_input); } @@ -213,7 +215,7 @@ static clib_error_t * hicn_cli_show_command_fn (vlib_main_t *vm, unformat_input_t *main_input, vlib_cli_command_t *cmd) { - int face_p = 0, fib_p = 0, all_p, internal_p = 0, strategies_p = 0, + int face_p = 0, fib_p = 0, all_p = 0, internal_p = 0, strategies_p = 0, ret = HICN_ERROR_NONE; /* Get a line of input. */ @@ -348,8 +350,8 @@ done: hicn_main.pitcs.pcs_table->ht_overflow_buckets_used); } return (ret == HICN_ERROR_NONE) ? - 0 : - clib_error_return (0, "%s\n", get_error_string (ret)); + 0 : + clib_error_return (0, "%s\n", get_error_string (ret)); } /* @@ -408,8 +410,8 @@ hicn_cli_strategy_set_command_fn (vlib_main_t *vm, rv = hicn_route_set_strategy (&prefix, strategy_id); cl_err = (rv == HICN_ERROR_NONE) ? - NULL : - clib_error_return (0, get_error_string (rv)); + NULL : + clib_error_return (0, get_error_string (rv)); done: return (cl_err); @@ -727,12 +729,25 @@ hicn_enable_command_fn (vlib_main_t *vm, unformat_input_t *main_input, goto done; } } - rv = hicn_route_enable (&pfx); + hicn_face_id_t *vec_faces = NULL; + rv = hicn_route_enable (&pfx, &vec_faces); + + if (vec_faces != NULL) + { + hicn_face_id_t *face_id; + u8 *str = 0; + vec_foreach (face_id, vec_faces) + { + str = format (str, " %d", *face_id); + } + vec_free (vec_faces); + vlib_cli_output (vm, "Faces for this prefix: %s", str); + } done: cl_err = (rv == HICN_ERROR_NONE) ? - NULL : - clib_error_return (0, get_error_string (rv)); + NULL : + clib_error_return (0, get_error_string (rv)); return cl_err; } @@ -776,8 +791,8 @@ hicn_disable_command_fn (vlib_main_t *vm, unformat_input_t *main_input, done: cl_err = (rv == HICN_ERROR_NONE) ? - NULL : - clib_error_return (0, get_error_string (rv)); + NULL : + clib_error_return (0, get_error_string (rv)); return cl_err; } diff --git a/hicn-plugin/src/data_fwd.h b/hicn-plugin/src/data_fwd.h index 96d8399e4..b21fa0a2f 100644 --- a/hicn-plugin/src/data_fwd.h +++ b/hicn-plugin/src/data_fwd.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/data_fwd_node.c b/hicn-plugin/src/data_fwd_node.c index fe79b33fa..6acb5915b 100644 --- a/hicn-plugin/src/data_fwd_node.c +++ b/hicn-plugin/src/data_fwd_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -428,9 +428,9 @@ hicn_satisfy_faces (vlib_main_t *vm, u32 bi0, hicn_pcs_entry_t *pitp, clones += 2; next0 = isv6 ? HICN_DATA_FWD_NEXT_IFACE6_OUT : - HICN_DATA_FWD_NEXT_IFACE4_OUT; + HICN_DATA_FWD_NEXT_IFACE4_OUT; next1 = isv6 ? HICN_DATA_FWD_NEXT_IFACE6_OUT : - HICN_DATA_FWD_NEXT_IFACE4_OUT; + HICN_DATA_FWD_NEXT_IFACE4_OUT; vnet_buffer (h0)->ip.adj_index[VLIB_TX] = face0; vnet_buffer (h1)->ip.adj_index[VLIB_TX] = face1; @@ -481,7 +481,7 @@ hicn_satisfy_faces (vlib_main_t *vm, u32 bi0, hicn_pcs_entry_t *pitp, clones += 1; next0 = isv6 ? HICN_DATA_FWD_NEXT_IFACE6_OUT : - HICN_DATA_FWD_NEXT_IFACE4_OUT; + HICN_DATA_FWD_NEXT_IFACE4_OUT; vnet_buffer (h0)->ip.adj_index[VLIB_TX] = face0; stats->pkts_data_count++; @@ -548,10 +548,7 @@ clone_data_to_cs (vlib_main_t *vm, hicn_pit_cs_t *pitcs, * the PIT part of the union as we update the CS part, so don't * expect the PIT part to be valid after this point. */ - hicn_buffer_t *hicnb0 = hicn_get_buffer (b0); - hicn_pit_to_cs (vm, pitcs, pitp, hash_entry, nodep, dpo_vft, hicn_dpo_id, - hicnb->face_id, - hicnb0->flags & HICN_BUFFER_FLAGS_FACE_IS_APP); + hicn_pit_to_cs (vm, pitcs, pitp, hash_entry, nodep, dpo_vft, hicn_dpo_id); pitp->shared.create_time = tnow; diff --git a/hicn-plugin/src/data_input_node.c b/hicn-plugin/src/data_input_node.c index c94443a6b..46fda1080 100644 --- a/hicn-plugin/src/data_input_node.c +++ b/hicn-plugin/src/data_input_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -75,6 +75,23 @@ format_hicn_data_input_trace (u8 *s, va_list *args) return s; } +static void +hicn_data_input_set_adj_index (vlib_buffer_t *b, + const ip46_address_t *dst_addr, + const hicn_dpo_ctx_t *dpo_ctx) +{ + for (u8 pos = 0; pos < dpo_ctx->entry_count; pos++) + { + hicn_face_t *face = hicn_dpoi_get_from_idx (dpo_ctx->next_hops[pos]); + assert (face); + if (ip46_address_cmp (&(face->nat_addr), dst_addr) == 0) + { + vnet_buffer (b)->ip.adj_index[VLIB_RX] = face->dpo.dpoi_index; + break; + } + } +} + static uword hicn_data_input_ip6_fn (vlib_main_t *vm, vlib_node_runtime_t *node, vlib_frame_t *frame) @@ -100,6 +117,7 @@ hicn_data_input_ip6_fn (vlib_main_t *vm, vlib_node_runtime_t *node, ip_lookup_next_t next0, next1; ip6_header_t *ip0, *ip1; ip6_address_t *src_addr0, *src_addr1; + ip46_address_t dst_addr0, dst_addr1; const dpo_id_t *dpo0, *dpo1; const load_balance_t *lb0, *lb1; @@ -128,6 +146,9 @@ hicn_data_input_ip6_fn (vlib_main_t *vm, vlib_node_runtime_t *node, src_addr0 = &ip0->src_address; src_addr1 = &ip1->src_address; + ip46_address_set_ip6 (&dst_addr0, &ip0->dst_address); + ip46_address_set_ip6 (&dst_addr0, &ip1->dst_address); + ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p0); ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p1); @@ -150,14 +171,22 @@ hicn_data_input_ip6_fn (vlib_main_t *vm, vlib_node_runtime_t *node, dpo1 = load_balance_get_bucket_i (lb1, 0); if (dpo_is_hicn (dpo0)) - next0 = HICN_DATA_INPUT_IP6_NEXT_FACE; + { + next0 = (ip_lookup_next_t) HICN_DATA_INPUT_IP6_NEXT_FACE; + hicn_data_input_set_adj_index ( + p0, &dst_addr0, hicn_strategy_dpo_ctx_get (dpo0->dpoi_index)); + } else - next0 = HICN_DATA_INPUT_IP6_NEXT_IP6_LOCAL; + next0 = (ip_lookup_next_t) HICN_DATA_INPUT_IP6_NEXT_IP6_LOCAL; if (dpo_is_hicn (dpo1)) - next1 = HICN_DATA_INPUT_IP6_NEXT_FACE; + { + next1 = (ip_lookup_next_t) HICN_DATA_INPUT_IP6_NEXT_FACE; + hicn_data_input_set_adj_index ( + p1, &dst_addr1, hicn_strategy_dpo_ctx_get (dpo1->dpoi_index)); + } else - next1 = HICN_DATA_INPUT_IP6_NEXT_IP6_LOCAL; + next1 = (ip_lookup_next_t) HICN_DATA_INPUT_IP6_NEXT_IP6_LOCAL; if (PREDICT_FALSE (node->flags & VLIB_NODE_FLAG_TRACE) && (p0->flags & VLIB_BUFFER_IS_TRACED)) @@ -235,6 +264,7 @@ hicn_data_input_ip6_fn (vlib_main_t *vm, vlib_node_runtime_t *node, ip_lookup_next_t next0; load_balance_t *lb0; ip6_address_t *src_addr0; + ip46_address_t dst_addr0; const dpo_id_t *dpo0; pi0 = from[0]; @@ -243,6 +273,7 @@ hicn_data_input_ip6_fn (vlib_main_t *vm, vlib_node_runtime_t *node, p0 = vlib_get_buffer (vm, pi0); ip0 = vlib_buffer_get_current (p0); src_addr0 = &ip0->src_address; + ip46_address_set_ip6 (&dst_addr0, &ip0->dst_address); ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, p0); lbi0 = ip6_fib_table_fwding_lookup (vnet_buffer (p0)->ip.fib_index, src_addr0); @@ -255,9 +286,13 @@ hicn_data_input_ip6_fn (vlib_main_t *vm, vlib_node_runtime_t *node, dpo0 = load_balance_get_bucket_i (lb0, 0); if (dpo_is_hicn (dpo0)) - next0 = HICN_DATA_INPUT_IP6_NEXT_FACE; + { + next0 = (ip_lookup_next_t) HICN_DATA_INPUT_IP6_NEXT_FACE; + hicn_data_input_set_adj_index ( + p0, &dst_addr0, hicn_strategy_dpo_ctx_get (dpo0->dpoi_index)); + } else - next0 = HICN_DATA_INPUT_IP6_NEXT_IP6_LOCAL; + next0 = (ip_lookup_next_t) HICN_DATA_INPUT_IP6_NEXT_IP6_LOCAL; if (PREDICT_FALSE (node->flags & VLIB_NODE_FLAG_TRACE) && (p0->flags & VLIB_BUFFER_IS_TRACED)) @@ -312,7 +347,7 @@ VLIB_REGISTER_NODE (hicn_data_input_ip6) = { VNET_FEATURE_INIT (hicn_data_input_ip6_arc, static) = { .arc_name = "ip6-local", .node_name = "hicn-data-input-ip6", - .runs_before = VNET_FEATURES ("ip6-local-end-of-arc"), + .runs_before = VNET_FEATURES ("ip6-local-end-of-arc") }; always_inline uword @@ -337,9 +372,8 @@ hicn_data_input_ip4_fn (vlib_main_t *vm, vlib_node_runtime_t *node, { ip4_header_t *ip0, *ip1, *ip2, *ip3; const load_balance_t *lb0, *lb1, *lb2, *lb3; - ip4_fib_mtrie_t *mtrie0, *mtrie1, *mtrie2, *mtrie3; - ip4_fib_mtrie_leaf_t leaf0, leaf1, leaf2, leaf3; ip4_address_t *src_addr0, *src_addr1, *src_addr2, *src_addr3; + ip46_address_t dst_addr0, dst_addr1, dst_addr2, dst_addr3; u32 lb_index0, lb_index1, lb_index2, lb_index3; const dpo_id_t *dpo0, *dpo1, *dpo2, *dpo3; @@ -367,35 +401,21 @@ hicn_data_input_ip4_fn (vlib_main_t *vm, vlib_node_runtime_t *node, src_addr2 = &ip2->src_address; src_addr3 = &ip3->src_address; + ip46_address_set_ip4 (&dst_addr0, &ip0->dst_address); + ip46_address_set_ip4 (&dst_addr1, &ip1->dst_address); + ip46_address_set_ip4 (&dst_addr2, &ip2->dst_address); + ip46_address_set_ip4 (&dst_addr3, &ip3->dst_address); + ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, b[0]); ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, b[1]); ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, b[2]); ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, b[3]); - mtrie0 = &ip4_fib_get (vnet_buffer (b[0])->ip.fib_index)->mtrie; - mtrie1 = &ip4_fib_get (vnet_buffer (b[1])->ip.fib_index)->mtrie; - mtrie2 = &ip4_fib_get (vnet_buffer (b[2])->ip.fib_index)->mtrie; - mtrie3 = &ip4_fib_get (vnet_buffer (b[3])->ip.fib_index)->mtrie; - - leaf0 = ip4_fib_mtrie_lookup_step_one (mtrie0, src_addr0); - leaf1 = ip4_fib_mtrie_lookup_step_one (mtrie1, src_addr1); - leaf2 = ip4_fib_mtrie_lookup_step_one (mtrie2, src_addr2); - leaf3 = ip4_fib_mtrie_lookup_step_one (mtrie3, src_addr3); - - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, src_addr0, 2); - leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, src_addr1, 2); - leaf2 = ip4_fib_mtrie_lookup_step (mtrie2, leaf2, src_addr2, 2); - leaf3 = ip4_fib_mtrie_lookup_step (mtrie3, leaf3, src_addr3, 2); - - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, src_addr0, 3); - leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, src_addr1, 3); - leaf2 = ip4_fib_mtrie_lookup_step (mtrie2, leaf2, src_addr2, 3); - leaf3 = ip4_fib_mtrie_lookup_step (mtrie3, leaf3, src_addr3, 3); - - lb_index0 = ip4_fib_mtrie_leaf_get_adj_index (leaf0); - lb_index1 = ip4_fib_mtrie_leaf_get_adj_index (leaf1); - lb_index2 = ip4_fib_mtrie_leaf_get_adj_index (leaf2); - lb_index3 = ip4_fib_mtrie_leaf_get_adj_index (leaf3); + ip4_fib_forwarding_lookup_x4 ( + vnet_buffer (b[0])->ip.fib_index, vnet_buffer (b[1])->ip.fib_index, + vnet_buffer (b[2])->ip.fib_index, vnet_buffer (b[3])->ip.fib_index, + src_addr0, src_addr1, src_addr2, src_addr3, &lb_index0, &lb_index1, + &lb_index2, &lb_index3); ASSERT (lb_index0 && lb_index1 && lb_index2 && lb_index3); lb0 = load_balance_get (lb_index0); @@ -418,22 +438,38 @@ hicn_data_input_ip4_fn (vlib_main_t *vm, vlib_node_runtime_t *node, dpo3 = load_balance_get_bucket_i (lb3, 0); if (dpo_is_hicn (dpo0)) - next[0] = HICN_DATA_INPUT_IP4_NEXT_FACE; + { + next[0] = (ip_lookup_next_t) HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; + hicn_data_input_set_adj_index ( + b[0], &dst_addr0, hicn_strategy_dpo_ctx_get (dpo0->dpoi_index)); + } else next[0] = HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; if (dpo_is_hicn (dpo1)) - next[1] = HICN_DATA_INPUT_IP4_NEXT_FACE; + { + next[1] = (ip_lookup_next_t) HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; + hicn_data_input_set_adj_index ( + b[1], &dst_addr1, hicn_strategy_dpo_ctx_get (dpo1->dpoi_index)); + } else next[1] = HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; if (dpo_is_hicn (dpo2)) - next[2] = HICN_DATA_INPUT_IP4_NEXT_FACE; + { + next[2] = (ip_lookup_next_t) HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; + hicn_data_input_set_adj_index ( + b[2], &dst_addr2, hicn_strategy_dpo_ctx_get (dpo2->dpoi_index)); + } else next[2] = HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; if (dpo_is_hicn (dpo3)) - next[3] = HICN_DATA_INPUT_IP4_NEXT_FACE; + { + next[3] = (ip_lookup_next_t) HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; + hicn_data_input_set_adj_index ( + b[3], &dst_addr3, hicn_strategy_dpo_ctx_get (dpo3->dpoi_index)); + } else next[3] = HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; @@ -495,9 +531,8 @@ hicn_data_input_ip4_fn (vlib_main_t *vm, vlib_node_runtime_t *node, { ip4_header_t *ip0, *ip1; const load_balance_t *lb0, *lb1; - ip4_fib_mtrie_t *mtrie0, *mtrie1; - ip4_fib_mtrie_leaf_t leaf0, leaf1; ip4_address_t *src_addr0, *src_addr1; + ip46_address_t dst_addr0, dst_addr1; u32 lb_index0, lb_index1; flow_hash_config_t flow_hash_config0, flow_hash_config1; u32 hash_c0, hash_c1; @@ -518,23 +553,15 @@ hicn_data_input_ip4_fn (vlib_main_t *vm, vlib_node_runtime_t *node, src_addr0 = &ip0->src_address; src_addr1 = &ip1->src_address; + ip46_address_set_ip4 (&dst_addr0, &ip0->dst_address); + ip46_address_set_ip4 (&dst_addr1, &ip1->dst_address); + ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, b[0]); ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, b[1]); - mtrie0 = &ip4_fib_get (vnet_buffer (b[0])->ip.fib_index)->mtrie; - mtrie1 = &ip4_fib_get (vnet_buffer (b[1])->ip.fib_index)->mtrie; - - leaf0 = ip4_fib_mtrie_lookup_step_one (mtrie0, src_addr0); - leaf1 = ip4_fib_mtrie_lookup_step_one (mtrie1, src_addr1); - - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, src_addr0, 2); - leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, src_addr1, 2); - - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, src_addr0, 3); - leaf1 = ip4_fib_mtrie_lookup_step (mtrie1, leaf1, src_addr1, 3); - - lb_index0 = ip4_fib_mtrie_leaf_get_adj_index (leaf0); - lb_index1 = ip4_fib_mtrie_leaf_get_adj_index (leaf1); + ip4_fib_forwarding_lookup_x2 ( + vnet_buffer (b[0])->ip.fib_index, vnet_buffer (b[1])->ip.fib_index, + src_addr0, src_addr1, &lb_index0, &lb_index1); ASSERT (lb_index0 && lb_index1); lb0 = load_balance_get (lb_index0); @@ -549,12 +576,20 @@ hicn_data_input_ip4_fn (vlib_main_t *vm, vlib_node_runtime_t *node, dpo1 = load_balance_get_bucket_i (lb1, 0); if (dpo_is_hicn (dpo0)) - next[0] = HICN_DATA_INPUT_IP4_NEXT_FACE; + { + next[0] = (ip_lookup_next_t) HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; + hicn_data_input_set_adj_index ( + b[0], &dst_addr0, hicn_strategy_dpo_ctx_get (dpo0->dpoi_index)); + } else next[0] = HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; if (dpo_is_hicn (dpo1)) - next[1] = HICN_DATA_INPUT_IP4_NEXT_FACE; + { + next[1] = (ip_lookup_next_t) HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; + hicn_data_input_set_adj_index ( + b[1], &dst_addr1, hicn_strategy_dpo_ctx_get (dpo1->dpoi_index)); + } else next[1] = HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; @@ -592,21 +627,18 @@ hicn_data_input_ip4_fn (vlib_main_t *vm, vlib_node_runtime_t *node, { ip4_header_t *ip0; const load_balance_t *lb0; - ip4_fib_mtrie_t *mtrie0; - ip4_fib_mtrie_leaf_t leaf0; ip4_address_t *src_addr0; + ip46_address_t dst_addr0; u32 lbi0; const dpo_id_t *dpo0; ip0 = vlib_buffer_get_current (b[0]); src_addr0 = &ip0->src_address; + ip46_address_set_ip4 (&dst_addr0, &ip0->dst_address); ip_lookup_set_buffer_fib_index (im->fib_index_by_sw_if_index, b[0]); - mtrie0 = &ip4_fib_get (vnet_buffer (b[0])->ip.fib_index)->mtrie; - leaf0 = ip4_fib_mtrie_lookup_step_one (mtrie0, src_addr0); - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, src_addr0, 2); - leaf0 = ip4_fib_mtrie_lookup_step (mtrie0, leaf0, src_addr0, 3); - lbi0 = ip4_fib_mtrie_leaf_get_adj_index (leaf0); + lbi0 = ip4_fib_forwarding_lookup (vnet_buffer (b[0])->ip.fib_index, + src_addr0); ASSERT (lbi0); lb0 = load_balance_get (lbi0); @@ -617,7 +649,11 @@ hicn_data_input_ip4_fn (vlib_main_t *vm, vlib_node_runtime_t *node, dpo0 = load_balance_get_bucket_i (lb0, 0); if (dpo_is_hicn (dpo0)) - next[0] = HICN_DATA_INPUT_IP4_NEXT_FACE; + { + next[0] = (ip_lookup_next_t) HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; + hicn_data_input_set_adj_index ( + b[0], &dst_addr0, hicn_strategy_dpo_ctx_get (dpo0->dpoi_index)); + } else next[0] = HICN_DATA_INPUT_IP4_NEXT_IP4_LOCAL; diff --git a/hicn-plugin/src/data_pcslookup.h b/hicn-plugin/src/data_pcslookup.h index b548497b6..32fca952a 100644 --- a/hicn-plugin/src/data_pcslookup.h +++ b/hicn-plugin/src/data_pcslookup.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/data_pcslookup_node.c b/hicn-plugin/src/data_pcslookup_node.c index 073d06c96..69278c306 100644 --- a/hicn-plugin/src/data_pcslookup_node.c +++ b/hicn-plugin/src/data_pcslookup_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -74,7 +74,7 @@ hicn_data_pcslookup_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, u32 node_id0 = 0; index_t dpo_ctx_id0 = 0; int ret0; - u8 vft_id0; + u8 vft_id0 = 0; u8 is_cs0; u8 hash_entry_id = 0; u8 bucket_is_overflown = 0; diff --git a/hicn-plugin/src/error.c b/hicn-plugin/src/error.c index 4c6986999..a64066d67 100644 --- a/hicn-plugin/src/error.c +++ b/hicn-plugin/src/error.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -13,7 +13,7 @@ * limitations under the License. */ -#include "error.h" +#include <vpp_plugins/hicn/error.h> const char *HICN_ERROR_STRING[] = { #define _(a, b, c) c, diff --git a/hicn-plugin/src/error.h b/hicn-plugin/src/error.h deleted file mode 100644 index b33a1b50d..000000000 --- a/hicn-plugin/src/error.h +++ /dev/null @@ -1,108 +0,0 @@ -/* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef __HICN_ERROR_H__ -#define __HICN_ERROR_H__ - -/** - * @file error.h - * - * Error codes for the hICN plugin. - */ - -#define foreach_hicn_error \ - _ (NONE, 0, "Ok") \ - _ (UNSPECIFIED, -128, "Unspecified Error") \ - _ (FACE_NOT_FOUND, -129, "Face not found in Face table") \ - _ (FACE_NULL, -130, "Face null") \ - _ (FACE_IP_ADJ_NOT_FOUND, -131, "Ip adjacecny for face not found") \ - _ (FACE_HW_INT_NOT_FOUND, -132, "Hardware interface not found") \ - _ (FACE_NOMEM, -133, "Face table is full") \ - _ (FACE_NO_GLOBAL_IP, -134, "No global ip address for face") \ - _ (FACE_NOT_FOUND_IN_ENTRY, -135, "Face not found in entry") \ - _ (FACE_ALREADY_DELETED, -136, "Face alredy deleted") \ - _ (FACE_ALREADY_CREATED, -137, "Face alredy created") \ - _ (FWD_NOT_ENABLED, -138, "hICN forwarder not enabled") \ - _ (FWD_ALREADY_ENABLED, -139, "hICN forwarder alredy enabled") \ - _ (PARSER_UNSUPPORTED_PROTO, -140, "Unsupported protocol") \ - _ (PARSER_PKT_INVAL, -141, "Packet null") \ - _ (PIT_CONFIG_MINLT_OOB, -142, "Min lifetime ouf of bounds") \ - _ (PIT_CONFIG_MAXLT_OOB, -143, "Max lifetime ouf of bounds") \ - _ (PIT_CONFIG_MINMAXLT, -144, "Min lifetime grater than max lifetime") \ - _ (PIT_CONFIG_DFTLT_OOB, -145, "Default lifetime ouf of bounds") \ - _ (PIT_CONFIG_SIZE_OOB, -146, "Pit size ouf of bounds") \ - _ (CS_CONFIG_SIZE_OOB, -147, "CS size ouf of bounds") \ - _ (CS_CONFIG_RESERVED_OOB, -148, \ - "Reseved CS must be between 0 and 100 (excluded)") \ - _ (DPO_CTX_NHOPS_NS, -149, "No space for additional next hop") \ - _ (DPO_CTX_NHOPS_EXISTS, -150, "Next hop already in the route") \ - _ (DPO_CTX_NOT_FOUND, -151, "Dpo context not found") \ - _ (DPO_MGR_ID_NOT_VALID, -152, "Dpo id for strategy and context not valid") \ - _ (HASHTB_HASH_NOT_FOUND, -153, "Hash not found in hash table") \ - _ (HASHTB_HASH_INVAL, -154, "Error while calculating the hash") \ - _ (HASHTB_NOMEM, -155, "Unable to allocate new buckets or nodes") \ - _ (HASHTB_INVAL, -156, "Invalid argument") \ - _ (HASHTB_KEY_INVAL, -157, "Invalid hashtb key") \ - _ (HASHTB_EXIST, -158, "Hash already in hashtable") \ - _ (ROUTE_INVAL, -159, "Invalid face id and weight") \ - _ (ROUTE_NO_LD, -160, "Expected load balance dpo") \ - _ (ROUTE_MLT_LD, -161, "Unexpected mulitple buckets in load balance dpo") \ - _ (ROUTE_NO_INSERT, -162, "Unable to insert a new FIB entry") \ - _ (ROUTE_DPO_NO_HICN, -163, "Dpo is not of type hICN") \ - _ (ROUTE_NOT_FOUND, -164, "Route not found in FIB") \ - _ (ROUTE_NOT_UPDATED, -165, "Unable to update route") \ - _ (ROUTE_ALREADY_EXISTS, -166, "Route already in FIB") \ - _ (CLI_INVAL, -167, "Invalid input") \ - _ (IPS_ADDR_TYPE_NONUNIFORM, -168, \ - "Src and dst addr have different ip types") \ - _ (FACE_TYPE_EXISTS, -169, "Face type already registered") \ - _ (NO_BUFFERS, -170, "No vlib_buffer available for packet cloning.") \ - _ (NOT_IMPLEMENTED, -171, "Function not yet implemented") \ - _ (IFACE_IP_ADJ_NOT_FOUND, -172, \ - "IP adjacency on incomplete face not available") \ - _ (APPFACE_ALREADY_ENABLED, -173, \ - "Application face already enabled on interface") \ - _ (APPFACE_FEATURE, -174, "Error while enabling app face feature") \ - _ (APPFACE_NOT_FOUND, -175, "Application face not found") \ - _ (APPFACE_PROD_PREFIX_NULL, -176, \ - "Prefix must not be null for producer face") \ - _ (STRATEGY_NH_NOT_FOUND, -177, "Next hop not found") \ - _ (MW_STRATEGY_SET, -178, "Error while setting weight for next hop") \ - _ (STRATEGY_NOT_FOUND, -179, "Strategy not found") \ - _ (UDP_TUNNEL_NOT_FOUND, -180, "Udp tunnel not found") \ - _ (UDP_TUNNEL_SRC_DST_TYPE, -181, \ - "Src and dst addresses have different type (ipv4 and ipv6)") - -typedef enum -{ -#define _(a, b, c) HICN_ERROR_##a = (b), - foreach_hicn_error -#undef _ - HICN_N_ERROR, -} hicn_error_t; - -extern const char *HICN_ERROR_STRING[]; - -#define get_error_string(errno) \ - (char *) (errno ? HICN_ERROR_STRING[(-errno) - 127] : \ - HICN_ERROR_STRING[errno]) - -#endif /* //__HICN_ERROR_H__ */ - -/* - * fd.io coding-style-patch-verification: ON - * - * Local Variables: eval: (c-set-style "gnu") End: - */ diff --git a/hicn-plugin/src/face_db.h b/hicn-plugin/src/face_db.h index 1bc061721..37a2af9ca 100644 --- a/hicn-plugin/src/face_db.h +++ b/hicn-plugin/src/face_db.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -78,8 +78,8 @@ hicn_face_db_get_dpo_face (u32 index, hicn_face_db_t *face_db) ASSERT (index < face_db->n_faces); return index < HICN_FACE_DB_INLINE_FACES ? - (face_db->inline_faces[index]) : - (pool_elt_at_index (hicn_face_bucket_pool, face_db->next_bucket) + (face_db->inline_faces[index]) : + (pool_elt_at_index (hicn_face_bucket_pool, face_db->next_bucket) ->faces[(index - HICN_FACE_DB_INLINE_FACES) & (HICN_PIT_N_HOP_BUCKET - 1)]); } @@ -106,8 +106,8 @@ hicn_face_db_add_face (hicn_face_id_t face_id, hicn_face_db_t *face_db) hicn_face_id_t *element = face_db->n_faces < HICN_FACE_DB_INLINE_FACES ? - &(face_db->inline_faces[face_db->n_faces]) : - &(faces_bkt->faces[(face_db->n_faces - HICN_FACE_DB_INLINE_FACES) & + &(face_db->inline_faces[face_db->n_faces]) : + &(faces_bkt->faces[(face_db->n_faces - HICN_FACE_DB_INLINE_FACES) & (HICN_PIT_N_HOP_BUCKET - 1)]); *element = face_id; diff --git a/hicn-plugin/src/faces/app/address_mgr.c b/hicn-plugin/src/faces/app/address_mgr.c index b5d8ce7cb..44729fd69 100644 --- a/hicn-plugin/src/faces/app/address_mgr.c +++ b/hicn-plugin/src/faces/app/address_mgr.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -14,7 +14,7 @@ */ /* - * Copyright (c) 2017-2019 by cisco systems inc. All rights reserved. + * Copyright (c) 2021 by cisco systems inc. All rights reserved. * */ @@ -31,10 +31,11 @@ #include <vnet/interface.h> //appif_flags #include <vnet/interface_funcs.h> //vnet_sw_interface_set_flags +#include <vpp_plugins/hicn/error.h> + #include "address_mgr.h" #include "../../hicn.h" #include "../../infra.h" -#include "../../error.h" #include "../face.h" #include "../../strategy_dpo_ctx.h" #include "../../route.h" diff --git a/hicn-plugin/src/faces/app/address_mgr.h b/hicn-plugin/src/faces/app/address_mgr.h index bd834f063..32545f8ca 100644 --- a/hicn-plugin/src/faces/app/address_mgr.h +++ b/hicn-plugin/src/faces/app/address_mgr.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/faces/app/face_app_cli.c b/hicn-plugin/src/faces/app/face_app_cli.c index ccdee4450..b3488c462 100644 --- a/hicn-plugin/src/faces/app/face_app_cli.c +++ b/hicn-plugin/src/faces/app/face_app_cli.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -114,8 +114,8 @@ hicn_face_app_cli_set_command_fn (vlib_main_t *vm, if (prod) { prefix.fp_proto = ip46_address_is_ip4 (&prefix.fp_addr) ? - FIB_PROTOCOL_IP4 : - FIB_PROTOCOL_IP6; + FIB_PROTOCOL_IP4 : + FIB_PROTOCOL_IP6; rv = hicn_face_prod_add (&prefix, sw_if, &cs_reserved, &prod_addr, &face_id1); if (rv == HICN_ERROR_NONE) @@ -175,8 +175,8 @@ hicn_face_app_cli_set_command_fn (vlib_main_t *vm, break; } return (rv == HICN_ERROR_NONE) ? - 0 : - clib_error_return (0, "%s\n", get_error_string (rv)); + 0 : + clib_error_return (0, "%s\n", get_error_string (rv)); } /* cli declaration for 'cfg face' */ diff --git a/hicn-plugin/src/faces/app/face_cons.c b/hicn-plugin/src/faces/app/face_cons.c index 53b955775..edb03387d 100644 --- a/hicn-plugin/src/faces/app/face_cons.c +++ b/hicn-plugin/src/faces/app/face_cons.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -69,10 +69,10 @@ hicn_face_cons_add (ip4_address_t *nh_addr4, ip6_address_t *nh_addr6, u32 swif, 0 /* is_del */); ip46_address_t nh_addr = to_ip46 (0, (u8 *) nh_addr6); - index_t adj_index = adj_nbr_find (FIB_PROTOCOL_IP6, VNET_LINK_IP6, &nh_addr, swif); + index_t adj_index = + adj_nbr_find (FIB_PROTOCOL_IP6, VNET_LINK_IP6, &nh_addr, swif); - hicn_iface_add ((ip46_address_t *) nh_addr6, swif, faceid2, DPO_PROTO_IP6, - adj_index); + hicn_iface_add ((ip46_address_t *) nh_addr6, swif, faceid2, adj_index, 0); hicn_face_t *face = hicn_dpoi_get_from_idx (*faceid2); face->flags |= HICN_FACE_FLAGS_APPFACE_CONS; @@ -90,7 +90,7 @@ hicn_face_cons_del (hicn_face_id_t face_id) if (face->flags & HICN_FACE_FLAGS_APPFACE_CONS) { - return hicn_face_del (face_id); + return hicn_face_unlock_with_id (face_id); } else { diff --git a/hicn-plugin/src/faces/app/face_cons.h b/hicn-plugin/src/faces/app/face_cons.h index 3ff246f4f..9df6f773f 100644 --- a/hicn-plugin/src/faces/app/face_cons.h +++ b/hicn-plugin/src/faces/app/face_cons.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/faces/app/face_prod.c b/hicn-plugin/src/faces/app/face_prod.c index 16b6e6158..1e569b82b 100644 --- a/hicn-plugin/src/faces/app/face_prod.c +++ b/hicn-plugin/src/faces/app/face_prod.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -30,7 +30,7 @@ hicn_face_prod_state_t *face_state_vec; u32 *face_state_pool; static int -hicn_app_state_create (u32 swif, fib_prefix_t *prefix) +hicn_app_state_create (u32 swif, index_t adj_index, fib_prefix_t *prefix) { /* Make sure that the pool is not empty */ pool_validate_index (face_state_pool, 0); @@ -49,6 +49,7 @@ hicn_app_state_create (u32 swif, fib_prefix_t *prefix) /* Create the appif and store in the vector */ vec_validate (face_state_vec, swif); + face_state_vec[swif].adj_index = adj_index; clib_memcpy (&(face_state_vec[swif].prefix), prefix, sizeof (fib_prefix_t)); /* Set as busy the element in the vector */ @@ -119,7 +120,7 @@ hicn_face_prod_add (fib_prefix_t *prefix, u32 sw_if, u32 *cs_reserved, hicn_main_t *hm = &hicn_main; - ip46_address_t local_app_ip; + ip46_address_t local_app_ip = { .as_u64 = { 0, 0 } }; CLIB_UNUSED (ip46_address_t remote_app_ip); u32 if_flags = 0; @@ -139,10 +140,11 @@ hicn_face_prod_add (fib_prefix_t *prefix, u32 sw_if, u32 *cs_reserved, if_flags |= VNET_SW_INTERFACE_FLAG_ADMIN_UP; vnet_sw_interface_set_flags (vnm, sw_if, if_flags); +#ifdef HICN_DDEBUG u8 *s0; s0 = format (0, "Prefix %U", format_fib_prefix, prefix); - - vlib_cli_output (vm, "Received request for %s, swif %d\n", s0, sw_if); + HICN_DEBUG ("Received request for %s, swif %d\n", s0, sw_if); +#endif if (ip46_address_is_zero (&prefix->fp_addr)) { @@ -268,15 +270,21 @@ hicn_face_prod_add (fib_prefix_t *prefix, u32 sw_if, u32 *cs_reserved, fib_table_entry_path_add2 (fib_index, prefix, FIB_SOURCE_CLI, FIB_ENTRY_FLAG_NONE, rpaths); - hicn_route_enable (prefix); - hicn_app_state_create (sw_if, prefix); + HICN_DEBUG ("Calling hicn enable for producer face"); + + hicn_face_id_t *vec_faces = NULL; + hicn_route_enable (prefix, &vec_faces); + if (vec_faces != NULL) + vec_free (vec_faces); + + adj_index = + adj_nbr_find (isv6 ? FIB_PROTOCOL_IP6 : FIB_PROTOCOL_IP4, + isv6 ? VNET_LINK_IP6 : VNET_LINK_IP4, prod_addr, sw_if); + + hicn_app_state_create (sw_if, adj_index, prefix); } - adj_index = - adj_nbr_find (isv6 ? FIB_PROTOCOL_IP6 : FIB_PROTOCOL_IP4, - isv6 ? VNET_LINK_IP6 : VNET_LINK_IP4, prod_addr, sw_if); - face = hicn_face_get (&local_app_ip, sw_if, &hicn_face_hashtb, - adj_index); // HICN_FACE_FLAGS_APPFACE_PROD); + face = hicn_face_get (&local_app_ip, sw_if, &hicn_face_hashtb, adj_index); *faceid = hicn_dpoi_get_index (face); @@ -289,6 +297,7 @@ hicn_face_prod_add (fib_prefix_t *prefix, u32 sw_if, u32 *cs_reserved, /* Cleanup in case of something went wrong. */ if (ret) { + HICN_ERROR ("Somethig went wrong while adding producer face. Cleanup."); hicn_app_state_del (sw_if); } return ret; @@ -304,17 +313,32 @@ hicn_face_prod_del (hicn_face_id_t face_id) if (face->flags & HICN_FACE_FLAGS_APPFACE_PROD) { - /* Remove the face from the fib */ - hicn_route_disable (&(face_state_vec[face->sw_if].prefix)); - // hicn_route_del_nhop (&(face_state_vec[face->sw_if].prefix), - // face_id); - - // int ret = hicn_face_del (face_id); - return hicn_app_state_del (face->sw_if); - // ret == HICN_ERROR_NONE ? hicn_app_state_del (face->sw_if) : ret; + /* Remove the face from the hicn fib */ + fib_prefix_t *prefix = &(face_state_vec[face->sw_if].prefix); + HICN_DEBUG ("Calling hicn_route_disable from hicn_face_prod_del"); + int ret = hicn_route_disable (prefix); + if (ret) + { + vlib_main_t *vm = vlib_get_main (); + vlib_cli_output (vm, "Error disabling route: %s", + get_error_string (ret)); + } + /* Also remove it from main fib, as we sre the owners of this prefix */ + u32 fib_index = fib_table_find (prefix->fp_proto, 0); + fib_table_entry_special_remove (fib_index, prefix, FIB_SOURCE_CLI); + ret = hicn_app_state_del (face->sw_if); + if (ret) + { + vlib_main_t *vm = vlib_get_main (); + vlib_cli_output (vm, "Error deelting app state: %s", + get_error_string (ret)); + } } else { + vlib_main_t *vm = vlib_get_main (); + vlib_cli_output (vm, "APPFACE not found.", + get_error_string (HICN_ERROR_APPFACE_NOT_FOUND)); return HICN_ERROR_APPFACE_NOT_FOUND; } diff --git a/hicn-plugin/src/faces/app/face_prod.h b/hicn-plugin/src/faces/app/face_prod.h index 4acf89dfc..51373d541 100644 --- a/hicn-plugin/src/faces/app/face_prod.h +++ b/hicn-plugin/src/faces/app/face_prod.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -50,6 +50,7 @@ typedef struct { fib_prefix_t prefix; + index_t adj_index; } hicn_face_prod_state_t; extern hicn_face_prod_state_t *face_state_vec; diff --git a/hicn-plugin/src/faces/app/face_prod_node.c b/hicn-plugin/src/faces/app/face_prod_node.c index c4c9edc32..5d2b54040 100644 --- a/hicn-plugin/src/faces/app/face_prod_node.c +++ b/hicn-plugin/src/faces/app/face_prod_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -24,7 +24,6 @@ */ #include "face_prod.h" -#include "../../hicn_api.h" #include "../../mgmt.h" static __clib_unused char *face_prod_input_error_strings[] = { @@ -114,7 +113,7 @@ hicn_face_prod_next_from_data_hdr (vlib_node_runtime_t *node, vlib_buffer_t *b, } return match_res ? HICN_FACE_PROD_NEXT_DATA_IP4 + (v == 0x60) : - HICN_FACE_PROD_NEXT_ERROR_DROP; + HICN_FACE_PROD_NEXT_ERROR_DROP; } static_always_inline void @@ -151,6 +150,7 @@ hicn_face_prod_input_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, while (n_left_from >= 8 && n_left_to_next >= 4) { vlib_buffer_t *b0, *b1, *b2, *b3; + hicn_buffer_t *hicnb0, *hicnb1, *hicnb2, *hicnb3; u32 bi0, bi1, bi2, bi3; hicn_face_prod_state_t *prod_face0 = NULL; hicn_face_prod_state_t *prod_face1 = NULL; @@ -190,11 +190,30 @@ hicn_face_prod_input_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, b2 = vlib_get_buffer (vm, bi2); b3 = vlib_get_buffer (vm, bi3); + hicnb0 = hicn_get_buffer (b0); + hicnb1 = hicn_get_buffer (b1); + hicnb2 = hicn_get_buffer (b2); + hicnb3 = hicn_get_buffer (b3); + + hicnb0->flags = HICN_FACE_FLAGS_DEFAULT; + hicnb1->flags = HICN_FACE_FLAGS_DEFAULT; + hicnb2->flags = HICN_FACE_FLAGS_DEFAULT; + hicnb3->flags = HICN_FACE_FLAGS_DEFAULT; + prod_face0 = &face_state_vec[vnet_buffer (b0)->sw_if_index[VLIB_RX]]; prod_face1 = &face_state_vec[vnet_buffer (b1)->sw_if_index[VLIB_RX]]; prod_face2 = &face_state_vec[vnet_buffer (b2)->sw_if_index[VLIB_RX]]; prod_face3 = &face_state_vec[vnet_buffer (b3)->sw_if_index[VLIB_RX]]; + vnet_buffer (b0)->ip.adj_index[VLIB_RX] = + face_state_vec[vnet_buffer (b0)->sw_if_index[VLIB_RX]].adj_index; + vnet_buffer (b1)->ip.adj_index[VLIB_RX] = + face_state_vec[vnet_buffer (b1)->sw_if_index[VLIB_RX]].adj_index; + vnet_buffer (b2)->ip.adj_index[VLIB_RX] = + face_state_vec[vnet_buffer (b2)->sw_if_index[VLIB_RX]].adj_index; + vnet_buffer (b3)->ip.adj_index[VLIB_RX] = + face_state_vec[vnet_buffer (b3)->sw_if_index[VLIB_RX]].adj_index; + next0 = hicn_face_prod_next_from_data_hdr (node, b0, &prod_face0->prefix); next1 = @@ -226,6 +245,7 @@ hicn_face_prod_input_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, while (n_left_from > 0 && n_left_to_next > 0) { vlib_buffer_t *b0; + hicn_buffer_t *hicnb0; u32 bi0, swif; hicn_face_prod_state_t *prod_face = NULL; u32 next0; @@ -245,11 +265,15 @@ hicn_face_prod_input_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, n_left_to_next -= 1; b0 = vlib_get_buffer (vm, bi0); + hicnb0 = hicn_get_buffer (b0); + hicnb0->flags = HICN_FACE_FLAGS_DEFAULT; swif = vnet_buffer (b0)->sw_if_index[VLIB_RX]; prod_face = &face_state_vec[swif]; next0 = hicn_face_prod_next_from_data_hdr (node, b0, &prod_face->prefix); + vnet_buffer (b0)->ip.adj_index[VLIB_RX] = + face_state_vec[swif].adj_index; stats.pkts_data_count++; /* trace */ diff --git a/hicn-plugin/src/faces/face.c b/hicn-plugin/src/faces/face.c index d62054365..854fd81d3 100644 --- a/hicn-plugin/src/faces/face.c +++ b/hicn-plugin/src/faces/face.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -57,11 +57,8 @@ face_show (u8 *s, int face_id, u32 indent) return (s); } -mhash_t hicn_face_vec_hashtb; mhash_t hicn_face_hashtb; -hicn_face_vec_t *hicn_vec_pool; - const static char *const hicn_face6_nodes[] = { "hicn6-face-output", // this is the name you give your node in // VLIB_REGISTER_NODE @@ -163,14 +160,9 @@ hicn_face_module_init (vlib_main_t *vm) counters = vec_new (vlib_combined_counter_main_t, HICN_PARAM_FACES_MAX * HICN_N_COUNTER); - mhash_init (&hicn_face_vec_hashtb, - sizeof (hicn_face_input_faces_t) /* value */, - sizeof (hicn_face_key_t) /* key */); mhash_init (&hicn_face_hashtb, sizeof (hicn_face_id_t) /* value */, sizeof (hicn_face_key_t) /* key */); - pool_alloc (hicn_vec_pool, 100); - /* * How much useful is the following registration? * So far it seems that we need it only for setting the dpo_type. @@ -182,7 +174,7 @@ hicn_face_module_init (vlib_main_t *vm) * corresponding to a face is updated */ hicn_face_fib_node_type = - fib_node_register_new_type (&hicn_face_fib_node_vft); + fib_node_register_new_type ("hicn_face_fib_node", &hicn_face_fib_node_vft); } u8 * @@ -256,46 +248,11 @@ format_hicn_face_all (u8 *s, int n, ...) int hicn_face_del (hicn_face_id_t face_id) { - hicn_face_t *face = hicn_dpoi_get_from_idx (face_id); - hicn_face_key_t key; - hicn_face_key_t old_key; - hicn_face_key_t old_key2; - - hicn_face_get_key (&(face->nat_addr), face->sw_if, &(face->dpo), &key); - hicn_face_input_faces_t *in_faces_vec = - hicn_face_get_vec (&(face->nat_addr), &hicn_face_vec_hashtb); - if (in_faces_vec != NULL) - { - hicn_face_vec_t *vec = - pool_elt_at_index (hicn_vec_pool, in_faces_vec->vec_id); - u32 index_face = vec_search (*vec, face_id); - vec_del1 (*vec, index_face); - - if (vec_len (*vec) == 0) - { - pool_put_index (hicn_vec_pool, in_faces_vec->vec_id); - mhash_unset (&hicn_face_vec_hashtb, &key, (uword *) &old_key); - vec_free (*vec); - } - else - { - /* Check if the face we are deleting is the preferred one. */ - /* If so, repleace with another. */ - if (in_faces_vec->face_id == face_id) - { - in_faces_vec->face_id = (*vec)[0]; - } - } - - mhash_unset (&hicn_face_hashtb, &key, (uword *) &old_key2); - } - int ret = HICN_ERROR_NONE; if (hicn_dpoi_idx_is_valid (face_id)) { hicn_face_t *face = hicn_dpoi_get_from_idx (face_id); - face->locks--; if (face->locks == 0) pool_put_index (hicn_dpoi_face_pool, face_id); else @@ -320,7 +277,7 @@ hicn_iface_to_face (hicn_face_t *face, const dpo_id_t *dpo) fib_node_init (&face->fib_node, hicn_face_fib_node_type); fib_node_lock (&face->fib_node); - if (dpo->dpoi_type != DPO_ADJACENCY_MIDCHAIN || + if (dpo->dpoi_type != DPO_ADJACENCY_MIDCHAIN && dpo->dpoi_type != DPO_ADJACENCY_MCAST_MIDCHAIN) { ip_adjacency_t *adj = adj_get (dpo->dpoi_index); @@ -375,8 +332,7 @@ hicn_face_add (const dpo_id_t *dpo_nh, ip46_address_t *nat_address, int sw_if, if (face == NULL) { - hicn_iface_add (nat_address, sw_if, pfaceid, dpo_nh->dpoi_proto, - dpo_nh->dpoi_index); + hicn_iface_add (nat_address, sw_if, pfaceid, dpo_nh->dpoi_index, 0); face = hicn_dpoi_get_from_idx (*pfaceid); mhash_set_mem (&hicn_face_hashtb, &key, (uword *) pfaceid, 0); @@ -395,52 +351,6 @@ hicn_face_add (const dpo_id_t *dpo_nh, ip46_address_t *nat_address, int sw_if, temp_dpo.dpoi_index = ~0; - hicn_face_input_faces_t *in_faces = - hicn_face_get_vec (nat_address, &hicn_face_vec_hashtb); - - if (in_faces == NULL) - { - hicn_face_input_faces_t in_faces_temp; - hicn_face_vec_t *vec; - pool_get (hicn_vec_pool, vec); - *vec = vec_new (hicn_face_id_t, 0); - u32 index = vec - hicn_vec_pool; - in_faces_temp.vec_id = index; - vec_add1 (*vec, *pfaceid); - - in_faces_temp.face_id = *pfaceid; - - hicn_face_get_key (nat_address, 0, &temp_dpo, &key); - - mhash_set_mem (&hicn_face_vec_hashtb, &key, (uword *) &in_faces_temp, 0); - } - else - { - hicn_face_vec_t *vec = - pool_elt_at_index (hicn_vec_pool, in_faces->vec_id); - - /* */ - if (vec_search (*vec, *pfaceid) != ~0) - return HICN_ERROR_FACE_ALREADY_CREATED; - - vec_add1 (*vec, *pfaceid); - - hicn_iface_to_face (face, dpo_nh); - - hicn_face_get_key (nat_address, 0, &temp_dpo, &key); - - mhash_set_mem (&hicn_face_vec_hashtb, &key, (uword *) in_faces, 0); - - /* If the face is an application producer face, we set it as the - * preferred incoming face. */ - /* This is required to handle the CS separation, and the push api in a - * lightway */ - if (is_app_prod) - { - in_faces->face_id = *pfaceid; - } - } - retx_t *retx = vlib_process_signal_event_data ( vlib_get_main (), hicn_mapme_eventmgr_process_node.index, HICN_MAPME_EVENT_FACE_ADD, 1, sizeof (retx_t)); diff --git a/hicn-plugin/src/faces/face.h b/hicn-plugin/src/faces/face.h index cb706eeca..39505c942 100644 --- a/hicn-plugin/src/faces/face.h +++ b/hicn-plugin/src/faces/face.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -25,7 +25,11 @@ #include <vppinfra/bihash_8_8.h> #include <vnet/adj/adj_midchain.h> -#include "../error.h" +#include <vpp_plugins/hicn/error.h> + +#include "../udp_tunnels/udp_tunnel.h" +#include "../hicn_logging.h" + typedef u8 hicn_face_flags_t; typedef index_t hicn_face_id_t; @@ -66,12 +70,8 @@ typedef index_t hicn_face_id_t; * - fib_node, fib_entry_index and fib_sibling are information used to be * notified of changes in the adjacency pointed by the dpo. * - * We maintain two hash tables to retrieve faces and ifaces. In particular one - * hash table which index faces and ifaces for nat_address, sw_if and dpo. This - * is used to retrieve existing faces or ifaces when an interest is received - * and when an new face is created. A second hash table that indexes vectors of - * faces for nat_address and sw_if. This is used to retrieve a list of possible - * incoming faces when a data is received. + * We maintain one hash tables to retrieve faces and ifaces, which indexes + * faces and ifaces for nat_address, sw_if and dpo. */ /** @@ -129,14 +129,17 @@ extern hicn_face_t *hicn_dpoi_face_pool; #define HICN_FACE_FLAGS_APPFACE_CONS \ 0x08 /* Currently only IP face can be appface */ #define HICN_FACE_FLAGS_DELETED 0x10 +#define HICN_FACE_FLAGS_UDP 0x20 #define HICN_FACE_NULL (hicn_face_id_t) ~0 #define HICN_FACE_FLAGS_APPFACE_PROD_BIT 2 #define HICN_FACE_FLAGS_APPFACE_CONS_BIT 3 -#define HICN_BUFFER_FLAGS_DEFAULT 0x00 -#define HICN_BUFFER_FLAGS_FACE_IS_APP 0x01 +#define HICN_BUFFER_FLAGS_DEFAULT 0x00 +#define HICN_BUFFER_FLAGS_NEW_FACE 0x02 +#define HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL 0x04 +#define HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL 0x08 STATIC_ASSERT ((1 << HICN_FACE_FLAGS_APPFACE_PROD_BIT) == HICN_FACE_FLAGS_APPFACE_PROD, @@ -148,16 +151,6 @@ STATIC_ASSERT ((1 << HICN_FACE_FLAGS_APPFACE_CONS_BIT) == "HICN_FACE_FLAGS_APPFACE_CONS_BIT and " "HICN_FACE_FLAGS_APPFACE_CONS must correspond"); -STATIC_ASSERT ( - (HICN_FACE_FLAGS_APPFACE_PROD >> HICN_FACE_FLAGS_APPFACE_PROD_BIT) == - HICN_BUFFER_FLAGS_FACE_IS_APP, - "hicn buffer app flag does not correspond to HICN_FACE_FLAGS_APPFACE_PROD"); - -STATIC_ASSERT ( - (HICN_FACE_FLAGS_APPFACE_CONS >> HICN_FACE_FLAGS_APPFACE_CONS_BIT) == - HICN_BUFFER_FLAGS_FACE_IS_APP, - "hicn buffer app flag does not correspond to HICN_FACE_FLAGS_APPFACE_PROD"); - /** * @brief Definition of the virtual functin table for an hICN FACE DPO. */ @@ -257,6 +250,15 @@ hicn_dpoi_idx_is_valid (hicn_face_id_t face_id) } /** + * @brief Delete a face + * + * @param face_id Id of the face to delete + * @return HICN_ERROR_FACE_NOT_FOUND if the face does not exist, otherwise + * HICN_ERROR_NONE + */ +int hicn_face_del (hicn_face_id_t face_id); + +/** * @brief Add a lock to the face dpo * * @param dpo Pointer to the face dpo @@ -274,12 +276,24 @@ hicn_face_lock_with_id (hicn_face_id_t face_id) * * @param dpo Pointer to the face dpo */ -always_inline void +always_inline int hicn_face_unlock_with_id (hicn_face_id_t face_id) { hicn_face_t *face; face = hicn_dpoi_get_from_idx (face_id); - face->locks--; + + if (face->locks > 0) + { + face->locks--; + + if (face->locks == 0) + { + HICN_DEBUG ("Deleting face %d", face_id); + return hicn_face_del (face_id); + } + } + + return HICN_ERROR_NONE; } /** @@ -324,15 +338,6 @@ u8 *format_hicn_face (u8 *s, va_list *args); u8 *format_hicn_face_all (u8 *s, int n, ...); /** - * @brief Delete a face - * - * @param face_id Id of the face to delete - * @return HICN_ERROR_FACE_NOT_FOUND if the face does not exist, otherwise - * HICN_ERROR_NONE - */ -int hicn_face_del (hicn_face_id_t face_id); - -/** * @bried vector of faces used to collect faces having the same local address * */ @@ -355,17 +360,6 @@ typedef struct hicn_input_faces_s_ } hicn_face_input_faces_t; /** - * Pool containing the vector of possible incoming faces. - */ -extern hicn_face_vec_t *hicn_vec_pool; - -/** - * Hash tables that indexes a face by remote address. For fast lookup when an - * interest arrives. - */ -extern mhash_t hicn_face_vec_hashtb; - -/** * Key definition for the mhash table. An face is uniquely identified by ip * address, the interface id and a dpo pointing to the next node in the vlib * graph. The ip address can correspond to the remote ip address of the next @@ -437,7 +431,7 @@ hicn_face_get (const ip46_address_t *addr, u32 sw_if, mhash_t *hashtb, hicn_face_id_t *dpoi_index = (hicn_face_id_t *) mhash_get (hashtb, &key); - if (dpoi_index != NULL) + if (dpoi_index != NULL && hicn_dpoi_idx_is_valid (*dpoi_index)) { hicn_face_lock_with_id (*dpoi_index); return hicn_dpoi_get_from_idx (*dpoi_index); @@ -467,7 +461,7 @@ hicn_face_get_with_dpo (const ip46_address_t *addr, u32 sw_if, hicn_face_id_t *dpoi_index = (hicn_face_id_t *) mhash_get (hashtb, &key); - if (dpoi_index != NULL) + if (dpoi_index != NULL && hicn_dpoi_idx_is_valid (*dpoi_index)) { hicn_face_lock_with_id (*dpoi_index); return hicn_dpoi_get_from_idx (*dpoi_index); @@ -477,28 +471,6 @@ hicn_face_get_with_dpo (const ip46_address_t *addr, u32 sw_if, } /** - * @brief Get the vector of faces from the ip v4 address. Does not add any - * lock. - * - * @param addr Ip v4 address used to create the key for the hash table. - * @param sw_if Software interface id used to create the key for the hash - * table. - * @param hashtb Hash table (remote or local) where to perform the lookup. - * - * @result Pointer to the face. - */ -always_inline hicn_face_input_faces_t * -hicn_face_get_vec (const ip46_address_t *addr, mhash_t *hashtb) -{ - hicn_face_key_t key; - - dpo_id_t dpo = DPO_INVALID; - - hicn_face_get_key (addr, 0, &dpo, &key); - return (hicn_face_input_faces_t *) mhash_get (hashtb, &key); -} - -/** * @brief Create a new face ip. API for other modules (e.g., routing) * * @param dpo_nh dpo contained in the face that points to the next node in @@ -526,7 +498,7 @@ int hicn_face_add (const dpo_id_t *dpo_nh, ip46_address_t *nat_address, */ always_inline void hicn_iface_add (ip46_address_t *nat_address, int sw_if, - hicn_face_id_t *pfaceid, dpo_proto_t proto, u32 adj_index) + hicn_face_id_t *pfaceid, u32 adj_index, u8 flags) { hicn_face_t *face; pool_get (hicn_dpoi_face_pool, face); @@ -534,16 +506,19 @@ hicn_iface_add (ip46_address_t *nat_address, int sw_if, clib_memcpy (&(face->nat_addr), nat_address, sizeof (ip46_address_t)); face->sw_if = sw_if; - face->dpo.dpoi_type = DPO_FIRST; - face->dpo.dpoi_proto = DPO_PROTO_NONE; + face->dpo = (dpo_id_t) DPO_INVALID; face->dpo.dpoi_index = adj_index; - face->dpo.dpoi_next_node = 0; + + hicn_face_key_t key; + hicn_face_get_key (nat_address, sw_if, &face->dpo, &key); + + face->dpo.dpoi_next_node = 1; + face->pl_id = pl_index++; face->flags = HICN_FACE_FLAGS_IFACE; + face->flags |= flags; face->locks = 1; - hicn_face_key_t key; - hicn_face_get_key (nat_address, sw_if, &face->dpo, &key); *pfaceid = hicn_dpoi_get_index (face); mhash_set_mem (&hicn_face_hashtb, &key, (uword *) pfaceid, 0); @@ -560,79 +535,6 @@ hicn_iface_add (ip46_address_t *nat_address, int sw_if, * ****/ /** - * @brief Retrieve a vector of faces from the ip4 local address and returns its - * index. - * - * @param vec: Result of the lookup. If no face exists for the local address - * vec = NULL - * @param hicnb_flags: Flags that indicate whether the face is an application - * face or not - * @param local_addr: Ip v4 nat address of the face - * @param sw_if: software interface id of the face - * - * @result HICN_ERROR_FACE_NOT_FOUND if the face does not exist, otherwise - * HICN_ERROR_NONE. - */ -always_inline int -hicn_face_ip4_lock (hicn_face_id_t *face_id, u32 *in_faces_vec_id, - u8 *hicnb_flags, const ip4_address_t *nat_addr) -{ - ip46_address_t ip_address = { 0 }; - ip46_address_set_ip4 (&ip_address, nat_addr); - hicn_face_input_faces_t *in_faces_vec = - hicn_face_get_vec (&ip_address, &hicn_face_vec_hashtb); - - if (PREDICT_FALSE (in_faces_vec == NULL)) - return HICN_ERROR_FACE_NOT_FOUND; - - *in_faces_vec_id = in_faces_vec->vec_id; - hicn_face_t *face = hicn_dpoi_get_from_idx (in_faces_vec->face_id); - - *hicnb_flags = HICN_BUFFER_FLAGS_DEFAULT; - *hicnb_flags |= (face->flags & HICN_FACE_FLAGS_APPFACE_PROD) >> - HICN_FACE_FLAGS_APPFACE_PROD_BIT; - - *face_id = in_faces_vec->face_id; - - return HICN_ERROR_NONE; -} - -/** - * @brief Retrieve a face from the ip6 local address and returns its dpo. This - * method adds a lock on the face state. - * - * @param dpo: Result of the lookup. If the face doesn't exist dpo = NULL - * @param hicnb_flags: Flags that indicate whether the face is an application - * face or not - * @param nat_addr: Ip v6 nat address of the face - * @param sw_if: software interface id of the face - * - * @result HICN_ERROR_FACE_NOT_FOUND if the face does not exist, otherwise - * HICN_ERROR_NONE. - */ -always_inline int -hicn_face_ip6_lock (hicn_face_id_t *face_id, u32 *in_faces_vec_id, - u8 *hicnb_flags, const ip6_address_t *nat_addr) -{ - hicn_face_input_faces_t *in_faces_vec = - hicn_face_get_vec ((ip46_address_t *) nat_addr, &hicn_face_vec_hashtb); - - if (PREDICT_FALSE (in_faces_vec == NULL)) - return HICN_ERROR_FACE_NOT_FOUND; - - *in_faces_vec_id = in_faces_vec->vec_id; - hicn_face_t *face = hicn_dpoi_get_from_idx (in_faces_vec->face_id); - - *hicnb_flags = HICN_BUFFER_FLAGS_DEFAULT; - *hicnb_flags |= (face->flags & HICN_FACE_FLAGS_APPFACE_PROD) >> - HICN_FACE_FLAGS_APPFACE_PROD_BIT; - - *face_id = in_faces_vec->face_id; - - return HICN_ERROR_NONE; -} - -/** * @brief Call back to get the adj of the tunnel */ static adj_walk_rc_t @@ -658,11 +560,12 @@ hicn4_iface_adj_walk_cb (adj_index_t ai, void *ctx) * @param sw_if: software interface id of the face * @param node_index: vlib edge index to use in the packet processing */ -always_inline void -hicn_iface_ip4_add_and_lock (hicn_face_id_t *index, u8 *hicnb_flags, - const ip4_address_t *nat_addr, u32 sw_if, - u32 adj_index, u32 node_index) +always_inline int +hicn_face_ip4_add_and_lock (hicn_face_id_t *index, u8 *hicnb_flags, + const ip4_address_t *nat_addr, u32 sw_if, + u32 adj_index, u32 node_index) { + int ret = HICN_ERROR_NONE; /*All (complete) faces are indexed by remote addess as well */ ip46_address_t ip_address = { 0 }; @@ -675,12 +578,30 @@ hicn_iface_ip4_add_and_lock (hicn_face_id_t *index, u8 *hicnb_flags, if (face == NULL) { hicn_face_id_t idx; - hicn_iface_add (&ip_address, sw_if, &idx, DPO_PROTO_IP4, adj_index); + u8 face_flags = 0; + + hicn_iface_add (&ip_address, sw_if, &idx, adj_index, face_flags); face = hicn_dpoi_get_from_idx (idx); - face->dpo.dpoi_type = DPO_FIRST; - face->dpo.dpoi_proto = DPO_PROTO_IP4; + if (*hicnb_flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL && + adj_index != ADJ_INDEX_INVALID) + { + face->dpo.dpoi_type = dpo_type_udp_ip6; + face->dpo.dpoi_proto = DPO_PROTO_IP6; + } + else if (*hicnb_flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL && + adj_index != ADJ_INDEX_INVALID) + { + face->dpo.dpoi_type = dpo_type_udp_ip4; + face->dpo.dpoi_proto = DPO_PROTO_IP4; + } + else + { + face->dpo.dpoi_type = DPO_FIRST; + face->dpo.dpoi_proto = DPO_PROTO_IP6; + } + face->dpo.dpoi_index = adj_index; face->dpo.dpoi_next_node = node_index; @@ -691,15 +612,17 @@ hicn_iface_ip4_add_and_lock (hicn_face_id_t *index, u8 *hicnb_flags, /* } */ *hicnb_flags = HICN_BUFFER_FLAGS_DEFAULT; + *hicnb_flags |= HICN_BUFFER_FLAGS_NEW_FACE; *index = idx; - return; + return ret; } else { /* unlock the face. We don't take a lock on each interest we receive */ hicn_face_id_t face_id = hicn_dpoi_get_index (face); hicn_face_unlock_with_id (face_id); + ret = HICN_ERROR_FACE_ALREADY_CREATED; } /* Code replicated on purpose */ @@ -708,6 +631,8 @@ hicn_iface_ip4_add_and_lock (hicn_face_id_t *index, u8 *hicnb_flags, HICN_FACE_FLAGS_APPFACE_PROD_BIT; *index = hicn_dpoi_get_index (face); + + return ret; } /** @@ -723,7 +648,8 @@ hicn6_iface_adj_walk_cb (adj_index_t ai, void *ctx) if ((adj->lookup_next_index == IP_LOOKUP_NEXT_MIDCHAIN) || (adj->lookup_next_index == IP_LOOKUP_NEXT_MCAST_MIDCHAIN)) { - dpo_set (&face->dpo, DPO_ADJACENCY_MIDCHAIN, adj->ia_nh_proto, ai); + dpo_set (&face->dpo, DPO_ADJACENCY_MIDCHAIN, + (dpo_proto_t) adj->ia_nh_proto, ai); adj_nbr_midchain_stack (ai, &face->dpo); } @@ -741,11 +667,13 @@ hicn6_iface_adj_walk_cb (adj_index_t ai, void *ctx) * @param sw_if: software interface id of the face * @param node_index: vlib edge index to use in the packet processing */ -always_inline void -hicn_iface_ip6_add_and_lock (hicn_face_id_t *index, u8 *hicnb_flags, - const ip6_address_t *nat_addr, u32 sw_if, - u32 adj_index, u32 node_index) +always_inline int +hicn_face_ip6_add_and_lock (hicn_face_id_t *index, u8 *hicnb_flags, + const ip6_address_t *nat_addr, u32 sw_if, + u32 adj_index, u32 node_index) { + int ret = HICN_ERROR_NONE; + /*All (complete) faces are indexed by remote addess as well */ /* if the face exists, it adds a lock */ hicn_face_t *face = hicn_face_get ((ip46_address_t *) nat_addr, sw_if, @@ -754,13 +682,30 @@ hicn_iface_ip6_add_and_lock (hicn_face_id_t *index, u8 *hicnb_flags, if (face == NULL) { hicn_face_id_t idx; - hicn_iface_add ((ip46_address_t *) nat_addr, sw_if, &idx, DPO_PROTO_IP6, - adj_index); + u8 face_flags = 0; + + hicn_iface_add ((ip46_address_t *) nat_addr, sw_if, &idx, adj_index, + face_flags); face = hicn_dpoi_get_from_idx (idx); - face->dpo.dpoi_type = DPO_FIRST; - face->dpo.dpoi_proto = DPO_PROTO_IP6; + if (*hicnb_flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL && + adj_index != ADJ_INDEX_INVALID) + { + face->dpo.dpoi_type = dpo_type_udp_ip6; + face->dpo.dpoi_proto = DPO_PROTO_IP6; + } + else if (*hicnb_flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL && + adj_index != ADJ_INDEX_INVALID) + { + face->dpo.dpoi_type = dpo_type_udp_ip4; + face->dpo.dpoi_proto = DPO_PROTO_IP4; + } + else + { + face->dpo.dpoi_type = DPO_FIRST; + face->dpo.dpoi_proto = DPO_PROTO_IP6; + } face->dpo.dpoi_index = adj_index; face->dpo.dpoi_next_node = node_index; @@ -768,16 +713,18 @@ hicn_iface_ip6_add_and_lock (hicn_face_id_t *index, u8 *hicnb_flags, face); *hicnb_flags = HICN_BUFFER_FLAGS_DEFAULT; + *hicnb_flags |= HICN_BUFFER_FLAGS_NEW_FACE; *index = idx; - return; + return ret; } else { /* unlock the face. We don't take a lock on each interest we receive */ hicn_face_id_t face_id = hicn_dpoi_get_index (face); hicn_face_unlock_with_id (face_id); + ret = HICN_ERROR_FACE_ALREADY_CREATED; } /* Code replicated on purpose */ @@ -786,6 +733,8 @@ hicn_iface_ip6_add_and_lock (hicn_face_id_t *index, u8 *hicnb_flags, HICN_FACE_FLAGS_APPFACE_PROD_BIT; *index = hicn_dpoi_get_index (face); + + return ret; } #endif // __HICN_FACE_H__ diff --git a/hicn-plugin/src/faces/face_cli.c b/hicn-plugin/src/faces/face_cli.c index a4092e6f4..20acefc5b 100644 --- a/hicn-plugin/src/faces/face_cli.c +++ b/hicn-plugin/src/faces/face_cli.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/faces/face_node.c b/hicn-plugin/src/faces/face_node.c index 5fe682bd0..dc9bfffd0 100644 --- a/hicn-plugin/src/faces/face_node.c +++ b/hicn-plugin/src/faces/face_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -95,9 +95,6 @@ typedef enum #define IP_HEADER_4 ip4_header_t #define IP_HEADER_6 ip6_header_t -#define LOCK_DPO_FACE_IP4 hicn_face_ip4_lock -#define LOCK_DPO_FACE_IP6 hicn_face_ip6_lock - #define TRACE_INPUT_PKT_IP4 hicn4_face_input_trace_t #define TRACE_INPUT_PKT_IP6 hicn6_face_input_trace_t @@ -111,11 +108,12 @@ typedef enum do \ { \ vlib_buffer_t *b0; \ - u32 bi0; \ + u32 bi0, sw_if0; \ u32 next0 = NEXT_ERROR_DROP_IP##ipv; \ IP_HEADER_##ipv *ip_hdr = NULL; \ hicn_buffer_t *hicnb0; \ - int ret; \ + int from_tunnel0; \ + int ret0; \ /* Prefetch for next iteration. */ \ if (n_left_from > 1) \ { \ @@ -138,23 +136,26 @@ typedef enum \ u8 is_icmp = ip_hdr->protocol == IPPROTO_ICMPV##ipv; \ \ + from_tunnel0 = \ + (hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL || \ + hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL) > 0; \ + sw_if0 = (from_tunnel0) * ~0 + \ + (1 - from_tunnel0) * vnet_buffer (b0)->sw_if_index[VLIB_RX]; \ + \ + ret0 = hicn_face_ip##ipv##_add_and_lock ( \ + &hicnb0->face_id, &hicnb0->flags, &ip_hdr->dst_address, sw_if0, \ + vnet_buffer (b0)->ip.adj_index[VLIB_RX], \ + /* Should not be used */ ~0); \ + /* Make sure the face is not created here */ \ + ASSERT (ret0 == HICN_ERROR_FACE_ALREADY_CREATED); \ + \ next0 = \ is_icmp * NEXT_MAPME_IP##ipv + (1 - is_icmp) * NEXT_DATA_IP##ipv; \ \ - ret = LOCK_DPO_FACE_IP##ipv (&(hicnb0->face_id), \ - &(hicnb0->in_faces_vec_id), \ - &hicnb0->flags, &(ip_hdr->dst_address)); \ - \ - if (PREDICT_FALSE (ret != HICN_ERROR_NONE)) \ - next0 = NEXT_ERROR_DROP_IP##ipv; \ - else \ - { \ - vlib_increment_combined_counter ( \ - &counters[hicnb0->face_id * HICN_N_COUNTER], thread_index, \ - HICN_FACE_COUNTERS_DATA_RX, 1, \ - vlib_buffer_length_in_chain (vm, b0)); \ - stats.pkts_data_count += 1; \ - } \ + vlib_increment_combined_counter ( \ + &counters[hicnb0->face_id * HICN_N_COUNTER], thread_index, \ + HICN_FACE_COUNTERS_DATA_RX, 1, vlib_buffer_length_in_chain (vm, b0)); \ + stats.pkts_data_count += 1; \ \ if (PREDICT_FALSE ((node->flags & VLIB_NODE_FLAG_TRACE) && \ (b0->flags & VLIB_BUFFER_IS_TRACED))) \ @@ -178,13 +179,14 @@ typedef enum do \ { \ vlib_buffer_t *b0, *b1; \ - u32 bi0, bi1; \ + u32 bi0, bi1, sw_if0, sw_if1; \ u32 next0 = NEXT_ERROR_DROP_IP##ipv; \ u32 next1 = NEXT_ERROR_DROP_IP##ipv; \ IP_HEADER_##ipv *ip_hdr0 = NULL; \ IP_HEADER_##ipv *ip_hdr1 = NULL; \ hicn_buffer_t *hicnb0; \ hicn_buffer_t *hicnb1; \ + int from_tunnel0, from_tunnel1; \ int ret0, ret1; \ /* Prefetch for next iteration. */ \ { \ @@ -216,41 +218,47 @@ typedef enum u8 is_icmp0 = ip_hdr0->protocol == IPPROTO_ICMPV##ipv; \ u8 is_icmp1 = ip_hdr1->protocol == IPPROTO_ICMPV##ipv; \ \ + from_tunnel0 = \ + (hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL || \ + hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL) > 0; \ + sw_if0 = (from_tunnel0) * ~0 + \ + (1 - from_tunnel0) * vnet_buffer (b0)->sw_if_index[VLIB_RX]; \ + \ + ret0 = hicn_face_ip##ipv##_add_and_lock ( \ + &hicnb0->face_id, &hicnb0->flags, &ip_hdr0->dst_address, sw_if0, \ + vnet_buffer (b0)->ip.adj_index[VLIB_RX], \ + /* Should not be used */ ~0); \ + /* Make sure the face is not created here */ \ + ASSERT (ret0 == HICN_ERROR_FACE_ALREADY_CREATED); \ + \ + from_tunnel1 = \ + (hicnb1->flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL || \ + hicnb1->flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL) > 0; \ + sw_if1 = (from_tunnel1) * ~0 + \ + (1 - from_tunnel1) * vnet_buffer (b1)->sw_if_index[VLIB_RX]; \ + \ + ret1 = hicn_face_ip##ipv##_add_and_lock ( \ + &hicnb1->face_id, &hicnb1->flags, &ip_hdr1->dst_address, sw_if1, \ + vnet_buffer (b1)->ip.adj_index[VLIB_RX], \ + /* Should not be used */ ~0); \ + /* Make sure the face is not created here */ \ + ASSERT (ret1 == HICN_ERROR_FACE_ALREADY_CREATED); \ + \ next0 = \ is_icmp0 * NEXT_MAPME_IP##ipv + (1 - is_icmp0) * NEXT_DATA_IP##ipv; \ \ next1 = \ is_icmp1 * NEXT_MAPME_IP##ipv + (1 - is_icmp1) * NEXT_DATA_IP##ipv; \ \ - ret0 = LOCK_DPO_FACE_IP##ipv (&(hicnb0->face_id), \ - &(hicnb0->in_faces_vec_id), \ - &hicnb0->flags, &(ip_hdr0->dst_address)); \ + vlib_increment_combined_counter ( \ + &counters[hicnb0->face_id * HICN_N_COUNTER], thread_index, \ + HICN_FACE_COUNTERS_DATA_RX, 1, vlib_buffer_length_in_chain (vm, b0)); \ + stats.pkts_data_count += 1; \ \ - ret1 = LOCK_DPO_FACE_IP##ipv (&(hicnb1->face_id), \ - &(hicnb1->in_faces_vec_id), \ - &hicnb1->flags, &(ip_hdr1->dst_address)); \ - \ - if (PREDICT_FALSE (ret0 != HICN_ERROR_NONE)) \ - next0 = NEXT_ERROR_DROP_IP##ipv; \ - else \ - { \ - vlib_increment_combined_counter ( \ - &counters[hicnb0->face_id * HICN_N_COUNTER], thread_index, \ - HICN_FACE_COUNTERS_DATA_RX, 1, \ - vlib_buffer_length_in_chain (vm, b0)); \ - stats.pkts_data_count += 1; \ - } \ - \ - if (PREDICT_FALSE (ret1 != HICN_ERROR_NONE)) \ - next1 = NEXT_ERROR_DROP_IP##ipv; \ - else \ - { \ - vlib_increment_combined_counter ( \ - &counters[hicnb1->face_id * HICN_N_COUNTER], thread_index, \ - HICN_FACE_COUNTERS_DATA_RX, 1, \ - vlib_buffer_length_in_chain (vm, b1)); \ - stats.pkts_data_count += 1; \ - } \ + vlib_increment_combined_counter ( \ + &counters[hicnb1->face_id * HICN_N_COUNTER], thread_index, \ + HICN_FACE_COUNTERS_DATA_RX, 1, vlib_buffer_length_in_chain (vm, b1)); \ + stats.pkts_data_count += 1; \ \ if (PREDICT_FALSE ((node->flags & VLIB_NODE_FLAG_TRACE) && \ (b0->flags & VLIB_BUFFER_IS_TRACED))) \ @@ -437,6 +445,7 @@ VLIB_REGISTER_NODE(hicn6_face_input_node) = typedef enum { + HICN4_FACE_OUTPUT_NEXT_ERROR_DROP, HICN4_FACE_OUTPUT_NEXT_ECHO_REPLY, HICN4_FACE_OUTPUT_NEXT_UDP4_ENCAP, HICN4_FACE_OUTPUT_NEXT_UDP6_ENCAP, @@ -445,6 +454,7 @@ typedef enum typedef enum { + HICN6_FACE_OUTPUT_NEXT_ERROR_DROP, HICN6_FACE_OUTPUT_NEXT_ECHO_REPLY, HICN6_FACE_OUTPUT_NEXT_UDP4_ENCAP, HICN6_FACE_OUTPUT_NEXT_UDP6_ENCAP, @@ -546,7 +556,9 @@ hicn_face_rewrite_interest (vlib_main_t *vm, vlib_buffer_t *b0, if (ret == HICN_LIB_ERROR_REWRITE_CKSUM_REQUIRED) { - ensure_offload_flags (b0, ip46_address_is_ip4 (&face->nat_addr)); + u8 is_v4 = ip46_address_is_ip4 (&face->nat_addr) && + !ip6_address_is_loopback (&face->nat_addr.ip6); + ensure_offload_flags (b0, is_v4); } ASSERT (face->flags & HICN_FACE_FLAGS_FACE); @@ -593,8 +605,8 @@ typedef struct { \ vlib_buffer_t *b0; \ u32 bi0; \ - u32 next0 = ~0; \ - hicn_face_t *face; \ + u32 next0 = HICN##ipv##_FACE_OUTPUT_NEXT_ERROR_DROP; \ + hicn_face_t *face = NULL; \ \ /* Prefetch for next iteration. */ \ if (n_left_from > 1) \ @@ -615,9 +627,10 @@ typedef struct b0 = vlib_get_buffer (vm, bi0); \ \ hicn_face_id_t face_id = vnet_buffer (b0)->ip.adj_index[VLIB_TX]; \ - face = hicn_dpoi_get_from_idx (face_id); \ + if (PREDICT_TRUE (hicn_dpoi_idx_is_valid (face_id))) \ + face = hicn_dpoi_get_from_idx (face_id); \ \ - if (PREDICT_TRUE (face != NULL)) \ + if (PREDICT_TRUE (face != NULL) && face->flags & HICN_FACE_FLAGS_FACE) \ { \ hicn_face_rewrite_interest (vm, b0, face, &next0); \ stats.pkts_interest_count += 1; \ @@ -650,9 +663,9 @@ typedef struct { \ vlib_buffer_t *b0, *b1; \ u32 bi0, bi1; \ - u32 next0 = ~0; \ - u32 next1 = ~0; \ - hicn_face_t *face0, *face1; \ + u32 next0 = HICN##ipv##_FACE_OUTPUT_NEXT_ERROR_DROP; \ + u32 next1 = HICN##ipv##_FACE_OUTPUT_NEXT_ERROR_DROP; \ + hicn_face_t *face0 = NULL, *face1 = NULL; \ \ /* Prefetch for next iteration. */ \ { \ @@ -679,10 +692,13 @@ typedef struct \ hicn_face_id_t face_id0 = vnet_buffer (b0)->ip.adj_index[VLIB_TX]; \ hicn_face_id_t face_id1 = vnet_buffer (b1)->ip.adj_index[VLIB_TX]; \ - face0 = hicn_dpoi_get_from_idx (face_id0); \ - face1 = hicn_dpoi_get_from_idx (face_id1); \ + if (PREDICT_TRUE (hicn_dpoi_idx_is_valid (face_id0))) \ + face0 = hicn_dpoi_get_from_idx (face_id0); \ + if (PREDICT_TRUE (hicn_dpoi_idx_is_valid (face_id1))) \ + face1 = hicn_dpoi_get_from_idx (face_id1); \ \ - if (PREDICT_TRUE (face0 != NULL)) \ + if (PREDICT_TRUE (face0 != NULL) && \ + face0->flags & HICN_FACE_FLAGS_FACE) \ { \ hicn_face_rewrite_interest (vm, b0, face0, &next0); \ stats.pkts_interest_count += 1; \ @@ -692,7 +708,8 @@ typedef struct vlib_buffer_length_in_chain (vm, b0)); \ } \ \ - if (PREDICT_TRUE (face1 != NULL)) \ + if (PREDICT_TRUE (face1 != NULL) && \ + face1->flags & HICN_FACE_FLAGS_FACE) \ { \ hicn_face_rewrite_interest (vm, b1, face1, &next1); \ stats.pkts_interest_count += 1; \ @@ -797,7 +814,8 @@ VLIB_REGISTER_NODE (hicn4_face_output_node) = { .error_strings = hicn4_face_output_error_strings, .n_next_nodes = HICN4_FACE_OUTPUT_N_NEXT, /* Reusing the list of nodes from lookup to be compatible with arp */ - .next_nodes = { [HICN4_FACE_OUTPUT_NEXT_ECHO_REPLY] = "hicn4-face-input", + .next_nodes = { [HICN4_FACE_OUTPUT_NEXT_ERROR_DROP] = "error-drop", + [HICN4_FACE_OUTPUT_NEXT_ECHO_REPLY] = "hicn4-face-input", [HICN4_FACE_OUTPUT_NEXT_UDP4_ENCAP] = "udp4-encap", [HICN4_FACE_OUTPUT_NEXT_UDP6_ENCAP] = "udp6-encap" } }; @@ -867,7 +885,8 @@ VLIB_REGISTER_NODE (hicn6_face_output_node) = { .n_next_nodes = HICN6_FACE_OUTPUT_N_NEXT, /* Reusing the list of nodes from lookup to be compatible with neighbour discovery */ - .next_nodes = { [HICN6_FACE_OUTPUT_NEXT_ECHO_REPLY] = "hicn6-face-input", + .next_nodes = { [HICN6_FACE_OUTPUT_NEXT_ERROR_DROP] = "error-drop", + [HICN6_FACE_OUTPUT_NEXT_ECHO_REPLY] = "hicn6-face-input", [HICN6_FACE_OUTPUT_NEXT_UDP4_ENCAP] = "udp4-encap", [HICN6_FACE_OUTPUT_NEXT_UDP6_ENCAP] = "udp6-encap" } }; diff --git a/hicn-plugin/src/faces/face_node.h b/hicn-plugin/src/faces/face_node.h index 3b38e71b3..70daa1393 100644 --- a/hicn-plugin/src/faces/face_node.h +++ b/hicn-plugin/src/faces/face_node.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/faces/iface_node.c b/hicn-plugin/src/faces/iface_node.c index bf9c56515..84205af9b 100644 --- a/hicn-plugin/src/faces/iface_node.c +++ b/hicn-plugin/src/faces/iface_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -107,8 +107,8 @@ typedef enum ip6_address_t *local_address1 = \ ip6_interface_first_address (&ip6_main, swif1); -#define DPO_ADD_LOCK_IFACE_IP4 hicn_iface_ip4_add_and_lock -#define DPO_ADD_LOCK_IFACE_IP6 hicn_iface_ip6_add_and_lock +#define DPO_ADD_LOCK_FACE_IP4 hicn_face_ip4_add_and_lock +#define DPO_ADD_LOCK_FACE_IP6 hicn_face_ip6_add_and_lock //#define VLIB_EDGE_IP4 data_fwd_iface_ip4_vlib_edge //#define VLIB_EDGE_IP6 data_fwd_iface_ip6_vlib_edge @@ -144,6 +144,7 @@ typedef struct typedef enum { + HICN4_IFACE_OUTPUT_NEXT_DROP, HICN4_IFACE_OUTPUT_NEXT_LOOKUP, HICN4_IFACE_OUTPUT_NEXT_UDP4_ENCAP, HICN4_IFACE_OUTPUT_NEXT_UDP6_ENCAP, @@ -161,6 +162,7 @@ typedef struct typedef enum { + HICN6_IFACE_OUTPUT_NEXT_DROP, HICN6_IFACE_OUTPUT_NEXT_LOOKUP, HICN6_IFACE_OUTPUT_NEXT_UDP4_ENCAP, HICN6_IFACE_OUTPUT_NEXT_UDP6_ENCAP, @@ -188,7 +190,7 @@ typedef enum do \ { \ vlib_buffer_t *b0; \ - u32 bi0, next0, next_iface0; \ + u32 bi0, next0, next_iface0, sw_if0; \ IP_HEADER_##ipv *ip_hdr = NULL; \ hicn_buffer_t *hicnb0; \ /* Prefetch for next iteration. */ \ @@ -219,15 +221,23 @@ typedef enum is_icmp * NEXT_MAPME_IP##ipv + (1 - is_icmp) * NEXT_INTEREST_IP##ipv; \ \ next_iface0 = NEXT_DATA_LOOKUP_IP##ipv; \ + sw_if0 = vnet_buffer (b0)->sw_if_index[VLIB_RX]; \ \ - if (hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL) \ - next_iface0 = NEXT_UDP_ENCAP_IP4; \ - else if (hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL) \ - next_iface0 = NEXT_UDP_ENCAP_IP6; \ + if (hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL && \ + vnet_buffer (b0)->ip.adj_index[VLIB_RX] != ADJ_INDEX_INVALID) \ + { \ + next_iface0 = NEXT_UDP_ENCAP_IP4; \ + sw_if0 = ~0; \ + } \ + else if (hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL && \ + vnet_buffer (b0)->ip.adj_index[VLIB_RX] != ADJ_INDEX_INVALID) \ + { \ + next_iface0 = NEXT_UDP_ENCAP_IP6; \ + sw_if0 = ~0; \ + } \ \ - DPO_ADD_LOCK_IFACE_IP##ipv ( \ - &(hicnb0->face_id), &hicnb0->flags, &(ip_hdr->src_address), \ - vnet_buffer (b0)->sw_if_index[VLIB_RX], \ + DPO_ADD_LOCK_FACE_IP##ipv ( \ + &(hicnb0->face_id), &hicnb0->flags, &(ip_hdr->src_address), sw_if0, \ vnet_buffer (b0)->ip.adj_index[VLIB_RX], next_iface0); \ \ if (PREDICT_FALSE ((node->flags & VLIB_NODE_FLAG_TRACE) && \ @@ -236,7 +246,7 @@ typedef enum TRACE_INPUT_PKT_IP##ipv *t = \ vlib_add_trace (vm, node, b0, sizeof (*t)); \ t->pkt_type = HICN_PKT_TYPE_INTEREST; \ - t->sw_if_index = vnet_buffer (b0)->sw_if_index[VLIB_RX]; \ + t->sw_if_index = sw_if0; \ t->next_index = next0; \ clib_memcpy_fast (t->packet_data, vlib_buffer_get_current (b0), \ sizeof (t->packet_data)); \ @@ -257,7 +267,7 @@ typedef enum do \ { \ vlib_buffer_t *b0, *b1; \ - u32 bi0, bi1, next0, next1, next_iface0, next_iface1; \ + u32 bi0, bi1, next0, next1, next_iface0, next_iface1, sw_if0, sw_if1; \ IP_HEADER_##ipv *ip_hdr0 = NULL; \ IP_HEADER_##ipv *ip_hdr1 = NULL; \ hicn_buffer_t *hicnb0, *hicnb1; \ @@ -300,27 +310,43 @@ typedef enum (1 - is_icmp1) * NEXT_INTEREST_IP##ipv; \ \ next_iface0 = NEXT_DATA_LOOKUP_IP##ipv; \ + sw_if0 = vnet_buffer (b0)->sw_if_index[VLIB_RX]; \ \ - if (hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL) \ - next_iface0 = NEXT_UDP_ENCAP_IP4; \ - else if (hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL) \ - next_iface0 = NEXT_UDP_ENCAP_IP6; \ + if (hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL && \ + vnet_buffer (b0)->ip.adj_index[VLIB_RX] != ADJ_INDEX_INVALID) \ + { \ + next_iface0 = NEXT_UDP_ENCAP_IP4; \ + sw_if0 = ~0; \ + } \ + else if (hicnb0->flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL && \ + vnet_buffer (b0)->ip.adj_index[VLIB_RX] != ADJ_INDEX_INVALID) \ + { \ + next_iface0 = NEXT_UDP_ENCAP_IP6; \ + sw_if0 = ~0; \ + } \ \ next_iface1 = NEXT_DATA_LOOKUP_IP##ipv; \ + sw_if1 = vnet_buffer (b1)->sw_if_index[VLIB_RX]; \ \ - if (hicnb1->flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL) \ - next_iface1 = NEXT_UDP_ENCAP_IP4; \ - else if (hicnb1->flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL) \ - next_iface1 = NEXT_UDP_ENCAP_IP6; \ + if (hicnb1->flags & HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL && \ + vnet_buffer (b1)->ip.adj_index[VLIB_RX] != ADJ_INDEX_INVALID) \ + { \ + next_iface1 = NEXT_UDP_ENCAP_IP4; \ + sw_if1 = ~0; \ + } \ + else if (hicnb1->flags & HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL && \ + vnet_buffer (b1)->ip.adj_index[VLIB_RX] != ADJ_INDEX_INVALID) \ + { \ + next_iface1 = NEXT_UDP_ENCAP_IP6; \ + sw_if1 = ~0; \ + } \ \ - DPO_ADD_LOCK_IFACE_IP##ipv ( \ - &(hicnb0->face_id), &hicnb0->flags, &(ip_hdr0->src_address), \ - vnet_buffer (b0)->sw_if_index[VLIB_RX], \ + DPO_ADD_LOCK_FACE_IP##ipv ( \ + &(hicnb0->face_id), &hicnb0->flags, &(ip_hdr0->src_address), sw_if0, \ vnet_buffer (b0)->ip.adj_index[VLIB_RX], next_iface0); \ \ - DPO_ADD_LOCK_IFACE_IP##ipv ( \ - &(hicnb1->face_id), &hicnb1->flags, &(ip_hdr1->src_address), \ - vnet_buffer (b1)->sw_if_index[VLIB_RX], \ + DPO_ADD_LOCK_FACE_IP##ipv ( \ + &(hicnb1->face_id), &hicnb1->flags, &(ip_hdr1->src_address), sw_if1, \ vnet_buffer (b1)->ip.adj_index[VLIB_RX], next_iface1); \ \ if (PREDICT_FALSE ((node->flags & VLIB_NODE_FLAG_TRACE) && \ @@ -329,7 +355,7 @@ typedef enum TRACE_INPUT_PKT_IP##ipv *t = \ vlib_add_trace (vm, node, b0, sizeof (*t)); \ t->pkt_type = HICN_PKT_TYPE_INTEREST; \ - t->sw_if_index = vnet_buffer (b0)->sw_if_index[VLIB_RX]; \ + t->sw_if_index = sw_if0; \ t->next_index = next0; \ clib_memcpy_fast (t->packet_data, vlib_buffer_get_current (b0), \ sizeof (t->packet_data)); \ @@ -341,7 +367,7 @@ typedef enum TRACE_INPUT_PKT_IP##ipv *t = \ vlib_add_trace (vm, node, b1, sizeof (*t)); \ t->pkt_type = HICN_PKT_TYPE_INTEREST; \ - t->sw_if_index = vnet_buffer (b1)->sw_if_index[VLIB_RX]; \ + t->sw_if_index = sw_if1; \ t->next_index = next1; \ clib_memcpy_fast (t->packet_data, vlib_buffer_get_current (b1), \ sizeof (t->packet_data)); \ @@ -588,7 +614,7 @@ hicn_rewrite_iface_data6 (vlib_main_t *vm, vlib_buffer_t *b0, vlib_buffer_t *b0; \ u32 bi0; \ u32 next0 = next_index; \ - hicn_face_t *face; \ + hicn_face_t *face = NULL; \ \ /* Prefetch for next iteration. */ \ if (n_left_from > 1) \ @@ -609,7 +635,8 @@ hicn_rewrite_iface_data6 (vlib_main_t *vm, vlib_buffer_t *b0, b0 = vlib_get_buffer (vm, bi0); \ \ hicn_face_id_t face_id = vnet_buffer (b0)->ip.adj_index[VLIB_TX]; \ - face = hicn_dpoi_get_from_idx (face_id); \ + if (PREDICT_TRUE (hicn_dpoi_idx_is_valid (face_id))) \ + face = hicn_dpoi_get_from_idx (face_id); \ \ if (PREDICT_TRUE (face != NULL)) \ { \ @@ -646,7 +673,7 @@ hicn_rewrite_iface_data6 (vlib_main_t *vm, vlib_buffer_t *b0, u32 bi0, bi1; \ u32 next0 = next_index; \ u32 next1 = next_index; \ - hicn_face_t *face0, *face1; \ + hicn_face_t *face0 = NULL, *face1 = NULL; \ \ /* Prefetch for next iteration. */ \ { \ @@ -674,8 +701,10 @@ hicn_rewrite_iface_data6 (vlib_main_t *vm, vlib_buffer_t *b0, \ hicn_face_id_t face_id0 = vnet_buffer (b0)->ip.adj_index[VLIB_TX]; \ hicn_face_id_t face_id1 = vnet_buffer (b1)->ip.adj_index[VLIB_TX]; \ - face0 = hicn_dpoi_get_from_idx (face_id0); \ - face1 = hicn_dpoi_get_from_idx (face_id1); \ + if (PREDICT_TRUE (hicn_dpoi_idx_is_valid (face_id0))) \ + face0 = hicn_dpoi_get_from_idx (face_id0); \ + if (PREDICT_TRUE (hicn_dpoi_idx_is_valid (face_id1))) \ + face1 = hicn_dpoi_get_from_idx (face_id1); \ \ if (PREDICT_TRUE (face0 != NULL)) \ { \ @@ -738,7 +767,7 @@ hicn4_iface_output_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, from = vlib_frame_vector_args (frame); n_left_from = frame->n_vectors; - next_index = node->cached_next_index; + next_index = HICN4_IFACE_OUTPUT_NEXT_DROP; while (n_left_from > 0) { @@ -792,7 +821,8 @@ VLIB_REGISTER_NODE (hicn4_iface_output_node) = { .error_strings = hicn4_iface_output_error_strings, .n_next_nodes = HICN4_IFACE_OUTPUT_N_NEXT, /* edit / add dispositions here */ - .next_nodes = { [HICN4_IFACE_OUTPUT_NEXT_LOOKUP] = "ip4-lookup", + .next_nodes = { [HICN4_IFACE_OUTPUT_NEXT_DROP] = "error-drop", + [HICN4_IFACE_OUTPUT_NEXT_LOOKUP] = "ip4-lookup", [HICN4_IFACE_OUTPUT_NEXT_UDP4_ENCAP] = "udp4-encap", [HICN4_IFACE_OUTPUT_NEXT_UDP6_ENCAP] = "udp6-encap" }, }; @@ -807,7 +837,7 @@ hicn6_iface_output_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, from = vlib_frame_vector_args (frame); n_left_from = frame->n_vectors; - next_index = node->cached_next_index; + next_index = HICN6_IFACE_OUTPUT_NEXT_DROP; while (n_left_from > 0) { @@ -860,11 +890,10 @@ VLIB_REGISTER_NODE (hicn6_iface_output_node) = { .error_strings = hicn6_iface_output_error_strings, .n_next_nodes = HICN6_IFACE_OUTPUT_N_NEXT, /* edit / add dispositions here */ - .next_nodes = { [HICN6_IFACE_OUTPUT_NEXT_LOOKUP] = "ip6-lookup", + .next_nodes = { [HICN6_IFACE_OUTPUT_NEXT_DROP] = "error-drop", + [HICN6_IFACE_OUTPUT_NEXT_LOOKUP] = "ip6-lookup", [HICN6_IFACE_OUTPUT_NEXT_UDP4_ENCAP] = "udp4-encap", - [HICN6_IFACE_OUTPUT_NEXT_UDP6_ENCAP] = "udp6-encap" - - }, + [HICN6_IFACE_OUTPUT_NEXT_UDP6_ENCAP] = "udp6-encap" }, }; /* diff --git a/hicn-plugin/src/faces/iface_node.h b/hicn-plugin/src/faces/iface_node.h index acb3cab0f..3fa6bb484 100644 --- a/hicn-plugin/src/faces/iface_node.h +++ b/hicn-plugin/src/faces/iface_node.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/faces/inlines.h b/hicn-plugin/src/faces/inlines.h index 95a1c2ad2..ad9e26b62 100644 --- a/hicn-plugin/src/faces/inlines.h +++ b/hicn-plugin/src/faces/inlines.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -21,24 +21,19 @@ always_inline void ensure_offload_flags (vlib_buffer_t *b, int is_v4) { - vnet_buffer_offload_flags_set(b, VNET_BUFFER_OFFLOAD_F_TCP_CKSUM); - vnet_buffer_offload_flags_set(b, is_v4 * VNET_BUFFER_OFFLOAD_F_IP_CKSUM); + vnet_buffer_offload_flags_set (b, VNET_BUFFER_OFFLOAD_F_TCP_CKSUM); + vnet_buffer_offload_flags_set (b, is_v4 * VNET_BUFFER_OFFLOAD_F_IP_CKSUM); size_t l3_header_size = is_v4 * sizeof (ip4_header_t) + (!is_v4) * sizeof (ip6_header_t); /* Make sure l3_hdr_offset and l4_hdr_offset are set */ - if (!(b->flags & VNET_BUFFER_F_L3_HDR_OFFSET_VALID)) - { - b->flags |= VNET_BUFFER_F_L3_HDR_OFFSET_VALID; - vnet_buffer (b)->l3_hdr_offset = b->current_data; - } - if (!(b->flags & VNET_BUFFER_F_L4_HDR_OFFSET_VALID)) - { - b->flags |= VNET_BUFFER_F_L4_HDR_OFFSET_VALID; - vnet_buffer (b)->l4_hdr_offset = - vnet_buffer (b)->l3_hdr_offset + l3_header_size; - } + b->flags |= VNET_BUFFER_F_L3_HDR_OFFSET_VALID; + vnet_buffer (b)->l3_hdr_offset = b->current_data; + + b->flags |= VNET_BUFFER_F_L4_HDR_OFFSET_VALID; + vnet_buffer (b)->l4_hdr_offset = + vnet_buffer (b)->l3_hdr_offset + l3_header_size; } #endif /* __HICN_FACE_INLINES_H__ */
\ No newline at end of file diff --git a/hicn-plugin/src/hashtb.c b/hicn-plugin/src/hashtb.c index a74353239..eb7da81f2 100644 --- a/hicn-plugin/src/hashtb.c +++ b/hicn-plugin/src/hashtb.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -187,7 +187,7 @@ hicn_hashtb_alloc (hicn_hashtb_h *ph, u32 max_elems, size_t app_data_size) } pool_get_aligned (h->ht_nodes, nodep, 8); // alloc node 0 - nodep = nodep; /* Silence 'not used' warning */ + (void) nodep; /* Silence 'not used' warning */ h->ht_node_count = max_elems; h->ht_nodes_used = 1; @@ -206,7 +206,7 @@ hicn_hashtb_alloc (hicn_hashtb_h *ph, u32 max_elems, size_t app_data_size) } /* 'Hide' the zero-th node so we can use zero as an 'empty' value */ pool_get_aligned (h->ht_overflow_buckets, bucket, 8); - bucket = bucket; /* Silence 'not used' warning */ + (void) bucket; /* Silence 'not used' warning */ h->ht_overflow_bucket_count = count; h->ht_overflow_buckets_used = 1; diff --git a/hicn-plugin/src/hashtb.h b/hicn-plugin/src/hashtb.h index 3965ec65d..4b787e2d7 100644 --- a/hicn-plugin/src/hashtb.h +++ b/hicn-plugin/src/hashtb.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/hicn.api b/hicn-plugin/src/hicn.api index 9643f2098..44382c743 100644 --- a/hicn-plugin/src/hicn.api +++ b/hicn-plugin/src/hicn.api @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -437,8 +437,14 @@ define hicn_api_enable_disable_reply /* Arbitrary context, so client can match reply to request */ u32 context; -/* Return value, zero means all OK */ + /* Return value, zero means all OK */ i32 retval; + + /* Number of faces created */ + u8 nfaces; + + /* IDs of new faces */ + u32 faceids[16]; }; define hicn_api_register_prod_app diff --git a/hicn-plugin/src/hicn.c b/hicn-plugin/src/hicn.c index 9bec91455..1131d4339 100644 --- a/hicn-plugin/src/hicn.c +++ b/hicn-plugin/src/hicn.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -149,8 +149,8 @@ hicn_infra_plugin_enable_disable (int enable_disable, int pit_size_req, // check if CS is bugger tha PIT or bigger than the available // vlib_buffers uword cs_buffers = (n_buffers > HICN_PARAM_CS_MIN_MBUF) ? - n_buffers - HICN_PARAM_CS_MIN_MBUF : - 0; + n_buffers - HICN_PARAM_CS_MIN_MBUF : + 0; if (cs_size_req > (pit_size_req / 2) || cs_size_req > cs_buffers) { diff --git a/hicn-plugin/src/hicn.h b/hicn-plugin/src/hicn.h index 4ff4f6ae6..aaf16c917 100644 --- a/hicn-plugin/src/hicn.h +++ b/hicn-plugin/src/hicn.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -61,10 +61,8 @@ typedef u8 weight_t; * 2*CLIB_CACHE_LINE_BYTES. */ /* This flag is used to mark packets whose lenght is less that * 2*CLIB_CACHE_LINE_BYTES. */ -#define HICN_BUFFER_FLAGS_PKT_LESS_TWO_CL 0x02 -#define HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL 0x04 -#define HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL 0x08 -#define HICN_BUFFER_FLAGS_FROM_CS 0x10 +#define HICN_BUFFER_FLAGS_PKT_LESS_TWO_CL 0x02 +#define HICN_BUFFER_FLAGS_FROM_CS 0x10 /* The following is stored in the opaque2 field in the vlib_buffer_t */ typedef struct @@ -83,7 +81,6 @@ typedef struct u8 vft_id; /* " */ hicn_face_id_t face_id; /* ingress iface, sizeof(u32) */ - u32 in_faces_vec_id; /* vector of possible input face for a data packet */ hicn_type_t type; } hicn_buffer_t; diff --git a/hicn-plugin/src/hicn_api.c b/hicn-plugin/src/hicn_api.c index b72675f63..85279eb0b 100644 --- a/hicn-plugin/src/hicn_api.c +++ b/hicn-plugin/src/hicn_api.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -40,12 +40,12 @@ #include "route.h" /* define message IDs */ -#include <hicn/hicn.api_enum.h> -#include <hicn/hicn.api_types.h> +#include <vpp_plugins/hicn/hicn.api_enum.h> +#include <vpp_plugins/hicn/hicn.api_types.h> /* define generated endian-swappers */ #define vl_endianfun -#include <hicn/hicn_all_api_h.h> +#include <vpp_plugins/hicn/hicn_all_api_h.h> #undef vl_endianfun #define REPLY_MSG_ID_BASE sm->msg_id_base @@ -79,8 +79,8 @@ vl_api_hicn_api_node_params_set_t_handler ( f64 pit_max_lifetime_sec = mp->pit_max_lifetime_sec; pit_max_lifetime_sec = pit_max_lifetime_sec == -1 ? - HICN_PARAM_PIT_LIFETIME_DFLT_MAX_MS / SEC_MS : - pit_max_lifetime_sec; + HICN_PARAM_PIT_LIFETIME_DFLT_MAX_MS / SEC_MS : + pit_max_lifetime_sec; int cs_max_size = clib_net_to_host_i32 (mp->cs_max_size); cs_max_size = cs_max_size == -1 ? HICN_PARAM_CS_ENTRIES_DFLT : cs_max_size; @@ -159,7 +159,7 @@ send_face_details (hicn_face_t *face, vl_api_hicn_face_t *mp) { sbuf = format (0, "%U", format_vnet_sw_interface_name, vnm, sw_interface); - strcpy ((char *) (mp->if_name), (char *) sbuf); + strcpy_s ((char *) (mp->if_name), sizeof (mp->if_name), (char *) sbuf); } } @@ -567,17 +567,34 @@ vl_api_hicn_api_enable_disable_t_handler (vl_api_hicn_api_enable_disable_t *mp) fib_prefix_t prefix; ip_prefix_decode (&mp->prefix, &prefix); + hicn_face_id_t *vec_faces = NULL; + switch (clib_net_to_host_u32 (mp->enable_disable)) { case HICN_ENABLE: - rv = hicn_route_enable (&prefix); + HICN_DEBUG ("Calling hicn enable from API."); + rv = hicn_route_enable (&prefix, &vec_faces); break; case HICN_DISABLE: + HICN_DEBUG ("Calling hicn disable from API."); rv = hicn_route_disable (&prefix); break; } - REPLY_MACRO (VL_API_HICN_API_ENABLE_DISABLE_REPLY /* , rmp, mp, rv */); + REPLY_MACRO2 (VL_API_HICN_API_ENABLE_DISABLE_REPLY, ({ + rmp->nfaces = 0; + if (vec_faces != NULL) + { + hicn_face_id_t *face; + vec_foreach (face, vec_faces) + { + rmp->faceids[rmp->nfaces++] = + clib_host_to_net_u32 (*face); + } + + vec_free (vec_faces); + } + })); } /*********************************** UDP TUNNELS @@ -632,7 +649,7 @@ done: /************************************************************************************/ -#include <hicn/hicn.api.c> +#include <vpp_plugins/hicn/hicn.api.c> /* Set up the API message handling tables */ clib_error_t * diff --git a/hicn-plugin/src/hicn_api_test.c b/hicn-plugin/src/hicn_api_test.c index 04e216e38..fbba5ffc3 100644 --- a/hicn-plugin/src/hicn_api_test.c +++ b/hicn-plugin/src/hicn_api_test.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -31,11 +31,11 @@ #include <vpp/api/vpe.api_types.h> -#include <hicn/hicn_api.h> -#include "error.h" +#include <vpp_plugins/hicn/hicn_api.h> +#include <vpp_plugins/hicn/error.h> /* Declare message IDs */ -#include "hicn_msg_enum.h" +#include <vpp_plugins/hicn/hicn_msg_enum.h> /* SUPPORTING FUNCTIONS NOT LOADED BY VPP_API_TEST */ uword @@ -1000,8 +1000,8 @@ api_hicn_api_enable_disable (vat_main_t *vam) } prefix.fp_proto = ip46_address_is_ip4 (&(prefix.fp_addr)) ? - FIB_PROTOCOL_IP4 : - FIB_PROTOCOL_IP6; + FIB_PROTOCOL_IP4 : + FIB_PROTOCOL_IP6; // Construct the API message M (HICN_API_ENABLE_DISABLE, mp); @@ -1053,8 +1053,8 @@ api_hicn_api_register_prod_app (vat_main_t *vam) } prefix.fp_proto = ip46_address_is_ip4 (&(prefix.fp_addr)) ? - FIB_PROTOCOL_IP4 : - FIB_PROTOCOL_IP6; + FIB_PROTOCOL_IP4 : + FIB_PROTOCOL_IP6; /* Construct the API message */ M (HICN_API_REGISTER_PROD_APP, mp); ip_prefix_encode (&prefix, &mp->prefix); @@ -1310,7 +1310,7 @@ vl_api_hicn_api_udp_tunnel_add_del_reply_t_handler ( fformat (vam->ofp, "udp-encap %d\n", uei); } -#include <hicn/hicn.api_test.c> +#include <vpp_plugins/hicn/hicn.api_test.c> /* * fd.io coding-style-patch-verification: ON diff --git a/hicn-plugin/src/hicn_logging.h b/hicn-plugin/src/hicn_logging.h new file mode 100644 index 000000000..a960a7212 --- /dev/null +++ b/hicn-plugin/src/hicn_logging.h @@ -0,0 +1,32 @@ +/* + * Copyright (c) 2021 Cisco and/or its affiliates. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at: + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef __HICN_DEBUG_H__ +#define __HICN_DEBUG_H__ + +#ifdef HICN_DDEBUG +#define HICN_DEBUG(...) \ + do \ + { \ + clib_warning (__VA_ARGS__); \ + } \ + while (0) +#else +#define HICN_DEBUG(...) +#endif /* HICN_DEBUG */ + +#define HICN_ERROR(...) clib_error_return (0, __VA_ARGS__) + +#endif /* __HICN_DEBUG_H__ */
\ No newline at end of file diff --git a/hicn-plugin/src/hicn_msg_enum.h b/hicn-plugin/src/hicn_msg_enum.h deleted file mode 100644 index fcf2a1e87..000000000 --- a/hicn-plugin/src/hicn_msg_enum.h +++ /dev/null @@ -1,39 +0,0 @@ -/* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at: - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -#ifndef __HICN_MSG_ENUM_H__ -#define __HICN_MSG_ENUM_H__ - -#include <vppinfra/byte_order.h> - -/** - * @file - */ -#define vl_msg_id(n, h) n, -typedef enum -{ -#include <hicn/hicn_all_api_h.h> - /* We'll want to know how many messages IDs we need... */ - VL_MSG_FIRST_AVAILABLE, -} vl_msg_id_t; -#undef vl_msg_id - -#endif /* __HICN_MSG_ENUM_H__ */ - -/* - * fd.io coding-style-patch-verification: ON - * - * Local Variables: eval: (c-set-style "gnu") End: - */ diff --git a/hicn-plugin/src/hicn_all_api_h.h b/hicn-plugin/src/infra.c index 1263ea4a2..e0dba5efd 100644 --- a/hicn-plugin/src/hicn_all_api_h.h +++ b/hicn-plugin/src/infra.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -13,10 +13,13 @@ * limitations under the License. */ -#include <hicn/hicn.api.h> +#include "infra.h" -/* - * fd.io coding-style-patch-verification: ON +/** + * @file infra.c * - * Local Variables: eval: (c-set-style "gnu") End: */ + +/* PIT and CS size */ +u32 hicn_infra_pit_size; +u32 hicn_infra_cs_size; diff --git a/hicn-plugin/src/infra.h b/hicn-plugin/src/infra.h index 900ecedde..c942ad581 100644 --- a/hicn-plugin/src/infra.h +++ b/hicn-plugin/src/infra.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -57,8 +57,8 @@ extern hicn_main_t hicn_main; extern int hicn_infra_fwdr_initialized; /* PIT and CS size */ -u32 hicn_infra_pit_size; -u32 hicn_infra_cs_size; +extern u32 hicn_infra_pit_size; +extern u32 hicn_infra_cs_size; /** * @brief Enable and disable the hicn plugin diff --git a/hicn-plugin/src/interest_hitcs.h b/hicn-plugin/src/interest_hitcs.h index 05a790688..0df987778 100644 --- a/hicn-plugin/src/interest_hitcs.h +++ b/hicn-plugin/src/interest_hitcs.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/interest_hitcs_node.c b/hicn-plugin/src/interest_hitcs_node.c index e29b173a9..947b4cb68 100644 --- a/hicn-plugin/src/interest_hitcs_node.c +++ b/hicn-plugin/src/interest_hitcs_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -189,7 +189,7 @@ hicn_interest_hitcs_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, * the data through it */ next0 = isv6 ? HICN_INTEREST_HITCS_NEXT_IFACE6_OUT : - HICN_INTEREST_HITCS_NEXT_IFACE4_OUT; + HICN_INTEREST_HITCS_NEXT_IFACE4_OUT; vnet_buffer (b0)->ip.adj_index[VLIB_TX] = hicnb0->face_id; clone_from_cs (vm, &pitp->u.cs.cs_pkt_buf, b0, isv6); diff --git a/hicn-plugin/src/interest_hitpit.h b/hicn-plugin/src/interest_hitpit.h index 44cf2c879..18ef94aa7 100644 --- a/hicn-plugin/src/interest_hitpit.h +++ b/hicn-plugin/src/interest_hitpit.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/interest_hitpit_node.c b/hicn-plugin/src/interest_hitpit_node.c index 837eddca7..33dc782cd 100644 --- a/hicn-plugin/src/interest_hitpit_node.c +++ b/hicn-plugin/src/interest_hitpit_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -88,7 +88,8 @@ hicn_interest_hitpit_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, u8 dpo_ctx_id0; u8 found = 0; int nh_idx; - hicn_face_id_t outface; + hicn_face_id_t outfaces[MAX_OUT_FACES]; + u32 outfaces_len; hicn_hash_entry_t *hash_entry0; hicn_buffer_t *hicnb0; int ret; @@ -171,23 +172,77 @@ hicn_interest_hitpit_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, if (found) { - strategy_vft0->hicn_select_next_hop (dpo_ctx_id0, - &nh_idx, &outface); + strategy_vft0->hicn_select_next_hop ( + dpo_ctx_id0, &nh_idx, outfaces, &outfaces_len); /* Retransmission */ /* * Prepare the packet for the * forwarding */ - next0 = isv6 ? HICN_INTEREST_HITPIT_NEXT_FACE6_OUTPUT : - HICN_INTEREST_HITPIT_NEXT_FACE4_OUTPUT; - vnet_buffer (b0)->ip.adj_index[VLIB_TX] = outface; - - /* - * Update the egress face in - * the PIT - */ - pitp->u.pit.pe_txnh = nh_idx; - stats.interests_retx++; + if (outfaces_len == 1) + { + next0 = isv6 ? + HICN_INTEREST_HITPIT_NEXT_FACE6_OUTPUT : + HICN_INTEREST_HITPIT_NEXT_FACE4_OUTPUT; + vnet_buffer (b0)->ip.adj_index[VLIB_TX] = + outfaces[0]; + + /* + * Update the egress face in + * the PIT + */ + pitp->u.pit.pe_txnh = nh_idx; + stats.interests_retx++; + } + else + { + // restore pointers + to_next -= 1; + n_left_to_next += 1; + u32 clones[outfaces_len]; + int ret = + vlib_buffer_clone (vm, bi0, clones, outfaces_len, + CLIB_CACHE_LINE_BYTES * 2); + ASSERT (ret == outfaces_len); + for (u32 nh = 0; nh < outfaces_len; nh++) + { + vlib_buffer_t *local_b0 = + vlib_get_buffer (vm, clones[nh]); + to_next[0] = clones[nh]; + to_next += 1; + n_left_to_next -= 1; + + next0 = + isv6 ? HICN_INTEREST_HITPIT_NEXT_FACE6_OUTPUT : + HICN_INTEREST_HITPIT_NEXT_FACE4_OUTPUT; + vnet_buffer (local_b0)->ip.adj_index[VLIB_TX] = + outfaces[nh]; + stats.interests_retx++; + + /* Maybe trace */ + if (PREDICT_FALSE ( + (node->flags & VLIB_NODE_FLAG_TRACE) && + (local_b0->flags & VLIB_BUFFER_IS_TRACED))) + { + hicn_interest_hitpit_trace_t *t = + vlib_add_trace (vm, node, local_b0, + sizeof (*t)); + t->pkt_type = HICN_PKT_TYPE_INTEREST; + t->sw_if_index = vnet_buffer (local_b0) + ->sw_if_index[VLIB_RX]; + t->next_index = next0; + } + + /* + * Verify speculative enqueue, maybe switch + * current next frame + */ + vlib_validate_buffer_enqueue_x1 ( + vm, node, next_index, to_next, n_left_to_next, + clones[nh], next0); + } + continue; + } } else { diff --git a/hicn-plugin/src/interest_pcslookup.h b/hicn-plugin/src/interest_pcslookup.h index 87d093e91..4da9c1939 100644 --- a/hicn-plugin/src/interest_pcslookup.h +++ b/hicn-plugin/src/interest_pcslookup.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/interest_pcslookup_node.c b/hicn-plugin/src/interest_pcslookup_node.c index d3f6c7bca..ff0da12d7 100644 --- a/hicn-plugin/src/interest_pcslookup_node.c +++ b/hicn-plugin/src/interest_pcslookup_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/mapme.h b/hicn-plugin/src/mapme.h index 63bd42610..1d46ea9f3 100644 --- a/hicn-plugin/src/mapme.h +++ b/hicn-plugin/src/mapme.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -21,9 +21,9 @@ #include <hicn/mapme.h> #include "hicn.h" -#include "route.h" #include "strategy_dpo_ctx.h" #include "strategy_dpo_manager.h" // dpo_is_hicn +#include "udp_tunnels/udp_tunnel.h" /** * @file @@ -63,7 +63,6 @@ typedef struct hicn_mapme_conf_s bool remove_dpo; // FIXME used ? vlib_main_t *vm; - vlib_log_class_t log_class; } hicn_mapme_main_t; /** @@ -100,65 +99,33 @@ STATIC_ASSERT (sizeof (hicn_mapme_tfib_t) <= sizeof (hicn_dpo_ctx_t), #define TFIB(dpo_ctx) ((hicn_mapme_tfib_t *) (dpo_ctx)) -static_always_inline int -hicn_mapme_nh_set (hicn_mapme_tfib_t *tfib, hicn_face_id_t face_id) -{ - hicn_dpo_ctx_t *strategy_ctx = (hicn_dpo_ctx_t *) tfib; - const fib_prefix_t *prefix = - fib_entry_get_prefix (strategy_ctx->fib_entry_index); - - u32 n_entries = tfib->entry_count; - /* Remove all the existing next hops and set the new one */ - for (int i = 0; i < n_entries; i++) - { - hicn_face_t *face = hicn_dpoi_get_from_idx (strategy_ctx->next_hops[0]); - ip_adjacency_t *adj = adj_get (face->dpo.dpoi_index); - ip_nh_del_helper (face->dpo.dpoi_proto, prefix, - &adj->sub_type.nbr.next_hop, face->sw_if); - } - hicn_face_t *face = hicn_dpoi_get_from_idx (face_id); - ip_nh_add_helper (face->dpo.dpoi_proto, prefix, &face->nat_addr, - face->sw_if); - return 0; -} - /** - * @brief Add a next hop iif it is not already a next hops + * @brief Check whether a face is already included in the TFIB. + * + * NOTE: linear scan on a contiguous small array should be the most efficient. */ static_always_inline int -hicn_mapme_nh_add (hicn_mapme_tfib_t *tfib, hicn_face_id_t face_id) +hicn_mapme_tfib_has (hicn_mapme_tfib_t *tfib, hicn_face_id_t face_id) { - for (u8 pos = 0; pos < tfib->entry_count; pos++) - if (tfib->next_hops[pos] == face_id) - return 0; - - /* Add the next hop in the vrf 0 which will add it to the entry in the hICN - * vrf */ - hicn_dpo_ctx_t *strategy_ctx = (hicn_dpo_ctx_t *) tfib; - const fib_prefix_t *prefix = - fib_entry_get_prefix (strategy_ctx->fib_entry_index); - hicn_face_t *face = hicn_dpoi_get_from_idx (face_id); - ip_nh_add_helper (face->dpo.dpoi_proto, prefix, &face->nat_addr, - face->sw_if); - + u8 pos = HICN_PARAM_FIB_ENTRY_NHOPS_MAX - tfib->tfib_entry_count; + for (u8 pos2 = pos; pos2 < HICN_PARAM_FIB_ENTRY_NHOPS_MAX; pos2++) + if (tfib->next_hops[pos2] == face_id) + return 1; return 0; } /** * Add a 'previous' hop to the TFIB - * - * XXX we should have the for look in the reverse order for simpler code. */ static_always_inline int hicn_mapme_tfib_add (hicn_mapme_tfib_t *tfib, hicn_face_id_t face_id) { - u8 pos = HICN_PARAM_FIB_ENTRY_NHOPS_MAX - tfib->tfib_entry_count; + // Don't add if it already exists + // (eg. an old IU received on a face on which we are retransmitting) + if (hicn_mapme_tfib_has (tfib, face_id)) + return 0; - // XXX don 't add if it already exist - // eg.an old IU received on a face on which we are retransmitting - for (u8 pos2 = pos; pos2 < HICN_PARAM_FIB_ENTRY_NHOPS_MAX; pos2++) - if (tfib->next_hops[pos2] == face_id) - return 0; + u8 pos = HICN_PARAM_FIB_ENTRY_NHOPS_MAX - tfib->tfib_entry_count; // Make sure we have enough room if (pos <= tfib->entry_count) @@ -190,7 +157,6 @@ hicn_mapme_tfib_clear (hicn_mapme_tfib_t *tfib) { hicn_face_unlock_with_id (tfib->next_hops[pos]); tfib->next_hops[pos] = invalid; - break; } tfib->tfib_entry_count = 0; @@ -358,10 +324,6 @@ hicn_mapme_get_dpo_face_node (hicn_face_id_t face_id) } } -#define DEBUG(...) // vlib_log_debug(mapme_main.log_class, __VA_ARGS__) -#define WARN(...) // vlib_log_warn(mapme_main.log_class, __VA_ARGS__) -#define ERROR(...) // vlib_log_err(mapme_main.log_class, __VA_ARGS__) - #endif /* __HICN_MAPME__ */ /* diff --git a/hicn-plugin/src/mapme_ack.h b/hicn-plugin/src/mapme_ack.h index 821baf203..72ed7a0c4 100644 --- a/hicn-plugin/src/mapme_ack.h +++ b/hicn-plugin/src/mapme_ack.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -14,7 +14,7 @@ */ /* - * Copyright (c) 2017-2019 by Cisco Systems Inc. All Rights Reserved. + * Copyright (c) 2021 by Cisco Systems Inc. All Rights Reserved. * */ diff --git a/hicn-plugin/src/mapme_ack_node.c b/hicn-plugin/src/mapme_ack_node.c index fad344b73..ea4834665 100644 --- a/hicn-plugin/src/mapme_ack_node.c +++ b/hicn-plugin/src/mapme_ack_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -14,6 +14,7 @@ */ #include <vnet/ip/ip6_packet.h> +#include <vlib/log.h> #include "hicn.h" #include "mapme.h" @@ -69,7 +70,8 @@ hicn_mapme_process_ack (vlib_main_t *vm, vlib_buffer_t *b, dpo = fib_epm_lookup (&(prefix.name), prefix.len); if (!dpo) { - DEBUG ("Ignored ACK for non-existing FIB entry. Ignored."); + HICN_ERROR ("Ignored ACK for non-existing FIB entry %U. Ignored.", + format_ip_prefix, &prefix); return true; } @@ -80,7 +82,7 @@ hicn_mapme_process_ack (vlib_main_t *vm, vlib_buffer_t *b, if (tfib == NULL) { - WARN ("Unable to get strategy ctx."); + HICN_ERROR ("Unable to get strategy ctx."); return false; } @@ -92,7 +94,7 @@ hicn_mapme_process_ack (vlib_main_t *vm, vlib_buffer_t *b, */ if (params.seq < fib_seq) { - DEBUG ("Ignored ACK for low seq"); + HICN_ERROR ("MAPME: Ignored ACK for low seq"); return true; } diff --git a/hicn-plugin/src/mapme_ctrl.h b/hicn-plugin/src/mapme_ctrl.h index a40a969b0..76382c6d2 100644 --- a/hicn-plugin/src/mapme_ctrl.h +++ b/hicn-plugin/src/mapme_ctrl.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -14,7 +14,7 @@ */ /* - * Copyright (c) 2017-2019 by Cisco Systems Inc. All Rights Reserved. + * Copyright (c) 2021 by Cisco Systems Inc. All Rights Reserved. * */ diff --git a/hicn-plugin/src/mapme_ctrl_node.c b/hicn-plugin/src/mapme_ctrl_node.c index 613958d9c..5314c49a0 100644 --- a/hicn-plugin/src/mapme_ctrl_node.c +++ b/hicn-plugin/src/mapme_ctrl_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -18,6 +18,7 @@ */ #include <vnet/ip/ip6_packet.h> #include <vnet/dpo/load_balance.h> +#include <vlib/log.h> #include "hicn.h" #include "mapme.h" @@ -30,6 +31,7 @@ #include "strategy_dpo_ctx.h" #include "error.h" #include "state.h" +#include "route.h" extern hicn_mapme_main_t mapme_main; @@ -47,6 +49,110 @@ static char *hicn_mapme_ctrl_error_strings[] = { #undef _ }; +static_always_inline int +hicn_mapme_nh_set (hicn_mapme_tfib_t *tfib, hicn_face_id_t face_id) +{ + hicn_dpo_ctx_t *strategy_ctx = (hicn_dpo_ctx_t *) tfib; + const fib_prefix_t *prefix = + fib_entry_get_prefix (strategy_ctx->fib_entry_index); + + int ret = 0; + + if ((tfib->entry_count == 1) && (tfib->next_hops[0] == face_id)) + return ret; + + u32 n_entries = tfib->entry_count; + /* Remove all the existing next hops and set the new one */ + for (int i = 0; i < n_entries; i++) + { + hicn_face_t *face = hicn_dpoi_get_from_idx (strategy_ctx->next_hops[0]); + if (dpo_is_adj (&face->dpo)) + { + ip_adjacency_t *adj = adj_get (face->dpo.dpoi_index); + ip_nh_adj_add_del_helper (prefix->fp_proto, prefix, + &adj->sub_type.nbr.next_hop, face->sw_if, + 0); + } + else if (face->dpo.dpoi_type == dpo_type_udp_ip4 || + face->dpo.dpoi_type == dpo_type_udp_ip6) + { + ip_nh_udp_tunnel_add_del_helper (prefix->fp_proto, prefix, + face->dpo.dpoi_index, + face->dpo.dpoi_proto, 0); + } + else + { + continue; + } + } + + ret = HICN_ERROR_MAPME_NEXT_HOP_ADDED; + hicn_face_t *face = hicn_dpoi_get_from_idx (face_id); + if (face->dpo.dpoi_type == dpo_type_udp_ip4 || + face->dpo.dpoi_type == dpo_type_udp_ip6) + { + ip_nh_udp_tunnel_add_del_helper (prefix->fp_proto, prefix, + face->dpo.dpoi_index, + face->dpo.dpoi_proto, 1); + } + else if (dpo_is_adj (&face->dpo)) + { + ip_nh_adj_add_del_helper (prefix->fp_proto, prefix, &face->nat_addr, + face->sw_if, 1); + } + else + { + ret = HICN_ERROR_MAPME_NEXT_HOP_NOT_ADDED; + } + + return ret; +} + +/** + * @brief Check whether a face is already included in the FIB nexthops. + * + * NOTE: linear scan on a contiguous small array should be the most efficient. + */ +static_always_inline int +hicn_mapme_nh_has (hicn_mapme_tfib_t *tfib, hicn_face_id_t face_id) +{ + for (u8 pos = 0; pos < tfib->entry_count; pos++) + if (tfib->next_hops[pos] == face_id) + return 1; + return 0; +} + +/** + * @brief Add a next hop iif it is not already a next hops + */ +static_always_inline int +hicn_mapme_nh_add (hicn_mapme_tfib_t *tfib, hicn_face_id_t face_id) +{ + if (hicn_mapme_nh_has (tfib, face_id)) + return 0; + + /* Add the next hop in the vrf 0 which will add it to the entry in the hICN + * vrf */ + hicn_dpo_ctx_t *strategy_ctx = (hicn_dpo_ctx_t *) tfib; + const fib_prefix_t *prefix = + fib_entry_get_prefix (strategy_ctx->fib_entry_index); + hicn_face_t *face = hicn_dpoi_get_from_idx (face_id); + if (face->dpo.dpoi_type == dpo_type_udp_ip4 || + face->dpo.dpoi_type == dpo_type_udp_ip6) + { + ip_nh_udp_tunnel_add_del_helper ((fib_protocol_t) face->dpo.dpoi_proto, + prefix, face->dpo.dpoi_index, + face->dpo.dpoi_proto, 1); + } + else + { + ip_nh_adj_add_del_helper ((fib_protocol_t) face->dpo.dpoi_proto, prefix, + &face->nat_addr, face->sw_if, 1); + } + + return 0; +} + /* * @brief Process incoming control messages (Interest Update) * @param vm vlib main data structure @@ -97,7 +203,7 @@ hicn_mapme_process_ctrl (vlib_main_t *vm, vlib_buffer_t *b, * Destroying the face has led to removing all corresponding FIB * entries. In that case, we need to correctly restore the FIB entries. */ - DEBUG ("Re-creating FIB entry with next hop on connection") + HICN_DEBUG ("Re-creating FIB entry with next hop on connection") #error "not implemented" #else // ERROR("Received IU for non-existing FIB entry"); @@ -109,7 +215,7 @@ hicn_mapme_process_ctrl (vlib_main_t *vm, vlib_buffer_t *b, if (!dpo_is_hicn ((dpo))) { /* We have an IP DPO */ - WARN ("Not implemented yet."); + HICN_ERROR ("Not implemented yet."); return false; } #endif @@ -119,7 +225,7 @@ hicn_mapme_process_ctrl (vlib_main_t *vm, vlib_buffer_t *b, if (tfib == NULL) { - WARN ("Unable to get strategy ctx."); + HICN_ERROR ("Unable to get strategy ctx."); return false; } @@ -127,7 +233,7 @@ hicn_mapme_process_ctrl (vlib_main_t *vm, vlib_buffer_t *b, if (params.seq > fib_seq) { - DEBUG ( + HICN_DEBUG ( "Higher sequence number than FIB %d > %d, updating seq and next hops", params.seq, fib_seq); @@ -139,25 +245,29 @@ hicn_mapme_process_ctrl (vlib_main_t *vm, vlib_buffer_t *b, /* Remove ingress face from TFIB in case it was present */ hicn_mapme_tfib_del (tfib, in_face_id); + HICN_DEBUG ("Locks on face %d: %d", in_face_id, + hicn_dpoi_get_from_idx (in_face_id)->locks); + /* Move next hops to TFIB... but in_face... */ for (u8 pos = 0; pos < tfib->entry_count; pos++) { - hicn_face_t *face = hicn_dpoi_get_from_idx (tfib->next_hops[pos]); - hicn_face_t *in_face = hicn_dpoi_get_from_idx (in_face_id); - if (dpo_is_adj (&face->dpo)) - { - ip_adjacency_t *adj = adj_get (dpo->dpoi_index); - if (ip46_address_cmp (&(adj->sub_type.nbr.next_hop), - &(in_face->nat_addr)) == 0) - break; - } - DEBUG ("Adding nexthop to the tfib, dpo index in_face %d, dpo index " - "tfib %d", - in_face_id, tfib->next_hops[pos]); + if (tfib->next_hops[pos] == in_face_id) + continue; + HICN_DEBUG ( + "Adding nexthop to the tfib, dpo index in_face %d, dpo index " + "tfib %d", + in_face_id, tfib->next_hops[pos]); hicn_mapme_tfib_add (tfib, tfib->next_hops[pos]); } - hicn_mapme_nh_set (tfib, in_face_id); + int ret = hicn_mapme_nh_set (tfib, in_face_id); + HICN_DEBUG ("Locks on face %d: %d", in_face_id, + hicn_dpoi_get_from_idx (in_face_id)->locks); + if (ret == HICN_ERROR_MAPME_NEXT_HOP_ADDED && + hicn_get_buffer (b)->flags & HICN_BUFFER_FLAGS_NEW_FACE) + { + hicn_face_unlock_with_id (in_face_id); + } /* We transmit both the prefix and the full dpo (type will be needed to * pick the right transmit node */ @@ -168,15 +278,22 @@ hicn_mapme_process_ctrl (vlib_main_t *vm, vlib_buffer_t *b, } else if (params.seq == fib_seq) { - DEBUG ("Same sequence number than FIB %d > %d, adding next hop", - params.seq, fib_seq); + HICN_DEBUG ("Same sequence number than FIB %d > %d, adding next hop", + params.seq, fib_seq); - /* Remove ingress face from TFIB in case it was present */ - hicn_mapme_tfib_del (tfib, in_face_id); + /** + * Add nh BEFORE removing the face from the tfib, as if the last lock is + * held by the tfib, deleting it first would also delete the face, + * resulting in a undefined behavior after (Debug mode -> SIGABRT, + * Release Mode -> Corrupted memory / SIGSEGV). + **/ /* Add ingress face to next hops */ hicn_mapme_nh_add (tfib, in_face_id); + /* Remove ingress face from TFIB in case it was present */ + hicn_mapme_tfib_del (tfib, in_face_id); + /* Multipath, multihoming, multiple producers or duplicate interest */ retx_t *retx = vlib_process_signal_event_data ( vm, hicn_mapme_eventmgr_process_node.index, @@ -187,8 +304,17 @@ hicn_mapme_process_ctrl (vlib_main_t *vm, vlib_buffer_t *b, { /* * face is propagating outdated information, we can just consider it as a - * prevHops + * prevHops, unless it is the current nexthop. */ + if (hicn_mapme_nh_has (tfib, in_face_id)) + { + HICN_DEBUG ("Ignored seq %d < fib_seq %d from current nexthop", + params.seq, fib_seq); + return true; + } + HICN_DEBUG ("Received seq %d < fib_seq %d, sending backwards", + params.seq, fib_seq); + hicn_mapme_tfib_add (tfib, in_face_id); retx_t *retx = vlib_process_signal_event_data ( diff --git a/hicn-plugin/src/mapme_eventmgr.c b/hicn-plugin/src/mapme_eventmgr.c index 49a9b5c57..c7ae4ecd7 100644 --- a/hicn-plugin/src/mapme_eventmgr.c +++ b/hicn-plugin/src/mapme_eventmgr.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -24,6 +24,11 @@ #define DEFAULT_TIMEOUT 1.0 /* s */ +/** + * @brief This is a process node reacting to face events. + */ +vlib_node_registration_t hicn_mapme_eventmgr_process_node; + hicn_mapme_main_t mapme_main; hicn_prefix_t *retx_pool; @@ -33,7 +38,6 @@ void hicn_mapme_init (vlib_main_t *vm) { mapme_main.vm = vm; - mapme_main.log_class = vlib_log_register_class ("hicn_mapme", 0); } /* borrowed from vnet/fib/ip4_fib.c */ @@ -77,7 +81,6 @@ hicn_mapme_process_fib_entry (vlib_main_t *vm, hicn_face_id_t face, const dpo_id_t *load_balance_dpo_id; load_balance_t *lb; dpo_id_t *dpo_id; - fib_entry_t *fib_entry; load_balance_dpo_id = fib_entry_contribute_ip_forwarding (*fib_entry_index); @@ -92,12 +95,14 @@ hicn_mapme_process_fib_entry (vlib_main_t *vm, hicn_face_id_t face, { /* un-const */ dpo_id = (dpo_id_t *) load_balance_get_bucket_i (lb, i); - if (dpo_is_hicn (dpo_id)) { +#ifdef HICN_DDEBUG + fib_entry_t *fib_entry; fib_entry = fib_entry_get (*fib_entry_index); - vlib_cli_output (vm, "set face pending %U", format_fib_prefix, - &fib_entry->fe_prefix); + HICN_DEBUG ("set face pending %U", format_fib_prefix, + &fib_entry->fe_prefix); +#endif } } } @@ -107,16 +112,10 @@ hicn_mapme_process_ip4_fib (vlib_main_t *vm, hicn_face_id_t face) { ip4_main_t *im4 = &ip4_main; fib_table_t *fib_table; - int table_id = -1, fib_index = ~0; pool_foreach (fib_table, im4->fibs) { - ip4_fib_t *fib = pool_elt_at_index (im4->v4_fibs, fib_table->ft_index); - - if (table_id >= 0 && table_id != (int) fib->table_id) - continue; - if (fib_index != ~0 && fib_index != (int) fib->index) - continue; + ip4_fib_t *fib = pool_elt_at_index (ip4_fibs, fib_table->ft_index); fib_node_index_t *fib_entry_index; ip4_fib_show_walk_ctx_t ctx = { @@ -241,8 +240,8 @@ hicn_mapme_send_message (vlib_main_t *vm, const hicn_prefix_t *prefix, size_t n; /* This should be retrieved from face information */ - DEBUG ("Retransmission for prefix %U seq=%d", format_ip46_address, - &prefix->name, IP46_TYPE_ANY, params->seq); + HICN_DEBUG ("Retransmission for prefix %U seq=%d", format_ip46_address, + &prefix->name, IP46_TYPE_ANY, params->seq); char *node_name = hicn_mapme_get_dpo_face_node (face); if (!node_name) @@ -257,7 +256,7 @@ hicn_mapme_send_message (vlib_main_t *vm, const hicn_prefix_t *prefix, u8 *buffer = get_packet_buffer ( vm, node_index, face, (ip46_address_t *) prefix, (params->protocol == IPPROTO_IPV6) ? HICN_TYPE_IPV6_ICMP : - HICN_TYPE_IPV4_ICMP); + HICN_TYPE_IPV4_ICMP); n = hicn_mapme_create_packet (buffer, prefix, params); if (n <= 0) { @@ -275,7 +274,7 @@ hicn_mapme_send_updates (vlib_main_t *vm, hicn_prefix_t *prefix, dpo_id_t dpo, hicn_mapme_tfib_t *tfib = TFIB (hicn_strategy_dpo_ctx_get (dpo.dpoi_index)); if (!tfib) { - DEBUG ("NULL TFIB entry id=%d", dpo.dpoi_index); + HICN_ERROR ("NULL TFIB entry id=%d", dpo.dpoi_index); return; } @@ -337,7 +336,7 @@ hicn_mapme_eventmgr_process (vlib_main_t *vm, vlib_node_runtime_t *rt, * Also, we only run a timer when there are pending retransmissions. */ timeout = (due_time > current_time) ? due_time - current_time : - DEFAULT_TIMEOUT; + DEFAULT_TIMEOUT; due_time = current_time + timeout; } else @@ -493,8 +492,8 @@ hicn_mapme_eventmgr_process (vlib_main_t *vm, vlib_node_runtime_t *rt, TFIB (hicn_strategy_dpo_ctx_get (retx->dpo.dpoi_index)); if (!tfib) { - DEBUG ("NULL TFIB entry for dpoi_index=%d", - retx->dpo.dpoi_index); + HICN_ERROR ("NULL TFIB entry for dpoi_index=%d", + retx->dpo.dpoi_index); continue; } diff --git a/hicn-plugin/src/mapme_eventmgr.h b/hicn-plugin/src/mapme_eventmgr.h index 2100a6f90..559ba2e75 100644 --- a/hicn-plugin/src/mapme_eventmgr.h +++ b/hicn-plugin/src/mapme_eventmgr.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -39,8 +39,7 @@ typedef struct /** * @brief This is a process node reacting to face events. */ -// not static ! -vlib_node_registration_t hicn_mapme_eventmgr_process_node; +extern vlib_node_registration_t hicn_mapme_eventmgr_process_node; /** * @brief Initialize MAP-Me on forwarder diff --git a/hicn-plugin/src/mgmt.c b/hicn-plugin/src/mgmt.c index b820a378f..6e9ce9fd8 100644 --- a/hicn-plugin/src/mgmt.c +++ b/hicn-plugin/src/mgmt.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -21,7 +21,7 @@ #include "mgmt.h" /* define message IDs */ -#include "hicn_msg_enum.h" +#include <vpp_plugins/hicn/hicn_msg_enum.h> /* shared routine betweeen API and CLI, leveraging API message structure */ int @@ -46,7 +46,8 @@ hicn_mgmt_node_stats_get (vl_api_hicn_api_node_stats_get_reply_t *rmp) vlib_error_main_t *em; vlib_node_t *n; - foreach_vlib_main() { + foreach_vlib_main () + { em = &this_vlib_main->error_main; n = vlib_get_node (this_vlib_main, hicn_interest_pcslookup_node.index); u32 node_cntr_base_idx = n->error_heap_index; diff --git a/hicn-plugin/src/mgmt.h b/hicn-plugin/src/mgmt.h index 8eaa18fa8..03e73999f 100644 --- a/hicn-plugin/src/mgmt.h +++ b/hicn-plugin/src/mgmt.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -18,7 +18,7 @@ #include <vppinfra/error.h> #include "faces/face.h" -#include "hicn_api.h" +#include <vpp_plugins/hicn/hicn_api.h> /** * @file mgmt.h diff --git a/hicn-plugin/src/params.h b/hicn-plugin/src/params.h index 7c7850d30..324429abe 100644 --- a/hicn-plugin/src/params.h +++ b/hicn-plugin/src/params.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -60,9 +60,9 @@ STATIC_ASSERT ((HICN_PARAM_FACES_MAX & (HICN_PARAM_FACES_MAX - 1)) == 0, // HICN_PARAM_PIT_ENTRY_PHOPS_MAX - 4 must be a power of two #define HICN_PARAM_PIT_ENTRY_PHOPS_MAX 20 -STATIC_ASSERT ((ceil (log2 ((HICN_PARAM_PIT_ENTRY_PHOPS_MAX - 4)))) == - (floor (log2 ((HICN_PARAM_PIT_ENTRY_PHOPS_MAX - 4)))), - "HICN_PARAM_PIT_ENTRY_PHOPS_MAX - 4 must be a power of two"); +// STATIC_ASSERT ((ceil (log2 ((HICN_PARAM_PIT_ENTRY_PHOPS_MAX - 4)))) == +// (floor (log2 ((HICN_PARAM_PIT_ENTRY_PHOPS_MAX - 4)))), +// "HICN_PARAM_PIT_ENTRY_PHOPS_MAX - 4 must be a power of two"); STATIC_ASSERT ( (HICN_PARAM_PIT_ENTRY_PHOPS_MAX <= HICN_PARAM_FACES_MAX), @@ -113,7 +113,7 @@ STATIC_ASSERT ( #define IPV6_DEFAULT_VERSION 6 #define IPV6_DEFAULT_TRAFFIC_CLASS 0 #define IPV6_DEFAULT_FLOW_LABEL 0 -#define HCIN_IP6_VERSION_TRAFFIC_FLOW \ +#define HICN_IP6_VERSION_TRAFFIC_FLOW \ (IPV6_DEFAULT_VERSION << 28) | (IPV6_DEFAULT_TRAFFIC_CLASS << 20) | \ (IPV6_DEFAULT_FLOW_LABEL & 0xfffff) #define HICN_IP6_PROTOCOL IP_PROTOCOL_TCP diff --git a/hicn-plugin/src/parser.h b/hicn-plugin/src/parser.h index 5c75ce3bd..0e60c526f 100644 --- a/hicn-plugin/src/parser.h +++ b/hicn-plugin/src/parser.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -59,10 +59,13 @@ hicn_interest_parse_pkt (vlib_buffer_t *pkt, hicn_name_t *name, u16 *namelen, u8 next_proto_offset = 6 + (1 - *isv6) * 3; // in the ipv6 header the next header field is at byte 6 // in the ipv4 header the protocol field is at byte 9 - hicn_type_t type = (hicn_type_t){ { .l4 = IPPROTO_NONE, - .l3 = IPPROTO_NONE, - .l2 = ip_pkt[next_proto_offset], - .l1 = ip_proto } }; + hicn_type_t type = + (hicn_type_t){ { .l4 = IPPROTO_NONE, + .l3 = ip_pkt[next_proto_offset] == IPPROTO_UDP ? + IPPROTO_ENCAP : + IPPROTO_NONE, + .l2 = ip_pkt[next_proto_offset], + .l1 = ip_proto } }; hicn_get_buffer (pkt)->type = type; hicn_ops_vft[type.l1]->get_interest_name (type, &pkt_hdr->protocol, name); @@ -97,10 +100,13 @@ hicn_data_parse_pkt (vlib_buffer_t *pkt, hicn_name_t *name, u16 *namelen, * header the protocol field is at byte 9 */ u8 next_proto_offset = 6 + (1 - *isv6) * 3; - hicn_type_t type = (hicn_type_t){ { .l4 = IPPROTO_NONE, - .l3 = IPPROTO_NONE, - .l2 = ip_pkt[next_proto_offset], - .l1 = ip_proto } }; + hicn_type_t type = + (hicn_type_t){ { .l4 = IPPROTO_NONE, + .l3 = ip_pkt[next_proto_offset] == IPPROTO_UDP ? + IPPROTO_ENCAP : + IPPROTO_NONE, + .l2 = ip_pkt[next_proto_offset], + .l1 = ip_proto } }; hicn_get_buffer (pkt)->type = type; hicn_ops_vft[type.l1]->get_data_name (type, &pkt_hdr->protocol, name); *namelen = (1 - (*isv6)) * HICN_V4_NAME_LEN + (*isv6) * HICN_V6_NAME_LEN; diff --git a/hicn-plugin/src/pcs.c b/hicn-plugin/src/pcs.c index d9e0baf6f..d6e4fd954 100644 --- a/hicn-plugin/src/pcs.c +++ b/hicn-plugin/src/pcs.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/pcs.h b/hicn-plugin/src/pcs.h index 083efa901..b98b72a53 100644 --- a/hicn-plugin/src/pcs.h +++ b/hicn-plugin/src/pcs.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -91,7 +91,7 @@ typedef struct __attribute__ ((packed)) hicn_pit_entry_s } hicn_pit_entry_t; -#define HICN_CS_ENTRY_OPAQUE_SIZE HICN_HASH_NODE_APP_DATA_SIZE - 36 +#define HICN_CS_ENTRY_OPAQUE_SIZE HICN_HASH_NODE_APP_DATA_SIZE - 32 /* * CS entry, unioned with a PIT entry below @@ -105,17 +105,17 @@ typedef struct __attribute__ ((packed)) hicn_cs_entry_s /* 20B + 4B = 24B */ u32 cs_pkt_buf; - /* Ingress face */ - /* 24B + 4B = 28B */ - hicn_face_id_t cs_rxface; + // /* Ingress face */ + // /* 24B + 4B = 28B */ + // hicn_face_id_t cs_rxface; /* Linkage for LRU, in the form of hashtable node indexes */ - /* 28B + 8B = 36B */ + /* 24B + 8B = 32B */ u32 cs_lru_prev; u32 cs_lru_next; /* Reserved for implementing cache policy different than LRU */ - /* 36B + (64 - 36)B = 64B */ + /* 32B + (64 - 32)B = 64B */ u8 opaque[HICN_CS_ENTRY_OPAQUE_SIZE]; } __attribute__ ((packed)) hicn_cs_entry_t; @@ -167,8 +167,7 @@ always_inline void hicn_pit_to_cs (vlib_main_t *vm, hicn_pit_cs_t *pitcs, hicn_hash_entry_t *hash_entry, hicn_hash_node_t *node, const hicn_dpo_vft_t *dpo_vft, - dpo_id_t *hicn_dpo_id, - hicn_face_id_t inface_id, u8 is_appface); + dpo_id_t *hicn_dpo_id); always_inline void hicn_pcs_cs_update (vlib_main_t *vm, hicn_pit_cs_t *pitcs, hicn_pcs_entry_t *old_entry, @@ -193,7 +192,7 @@ always_inline int hicn_pcs_cs_insert_update ( vlib_main_t *vm, hicn_pit_cs_t *pitcs, hicn_pcs_entry_t *entry, hicn_hash_node_t *node, hicn_hash_entry_t **hash_entry, u64 hashval, u32 *node_id, index_t *dpo_ctx_id, u8 *vft_id, u8 *is_cs, u8 *hash_entry_id, - u32 *bucket_id, u8 *bucket_is_overflow, hicn_face_id_t inface); + u32 *bucket_id, u8 *bucket_is_overflow); always_inline int hicn_pcs_pit_insert (hicn_pit_cs_t *pitcs, hicn_pcs_entry_t *entry, @@ -352,7 +351,6 @@ hicn_pcs_delete_internal (hicn_pit_cs_t *pitcs, hicn_pcs_entry_t **pcs_entryp, else { pitcs->pcs_pit_dealloc++; - hicn_strategy_dpo_ctx_unlock (hicn_dpo_id); /* Flush faces */ hicn_faces_flush (&(pcs->u.pit.faces)); @@ -370,7 +368,7 @@ always_inline void hicn_pit_to_cs (vlib_main_t *vm, hicn_pit_cs_t *pitcs, hicn_pcs_entry_t *pcs_entry, hicn_hash_entry_t *hash_entry, hicn_hash_node_t *node, const hicn_dpo_vft_t *dpo_vft, - dpo_id_t *hicn_dpo_id, hicn_face_id_t inface_id, u8 is_appface) + dpo_id_t *hicn_dpo_id) { /* @@ -378,7 +376,6 @@ hicn_pit_to_cs (vlib_main_t *vm, hicn_pit_cs_t *pitcs, * hash entry. */ pitcs->pcs_pit_count--; - hicn_strategy_dpo_ctx_unlock (hicn_dpo_id); /* Flush faces */ hicn_faces_flush (&(pcs_entry->u.pit.faces)); @@ -386,8 +383,6 @@ hicn_pit_to_cs (vlib_main_t *vm, hicn_pit_cs_t *pitcs, node->hn_flags |= HICN_HASH_NODE_CS_FLAGS; pcs_entry->shared.entry_flags |= HICN_PCS_ENTRY_CS_FLAG; - pcs_entry->u.cs.cs_rxface = inface_id; - /* Update the CS according to the policy */ hicn_cs_policy_t *policy_state; hicn_cs_policy_vft_t *policy_vft; @@ -432,40 +427,8 @@ hicn_pcs_cs_update (vlib_main_t *vm, hicn_pit_cs_t *pitcs, policy_state = &pitcs->policy_state; policy_vft = &pitcs->policy_vft; - if (entry->u.cs.cs_rxface != old_entry->u.cs.cs_rxface) - { - /* Dequeue content from the old queue */ - policy_vft->hicn_cs_dequeue (pitcs, node, old_entry, policy_state); - - old_entry->u.cs.cs_rxface = entry->u.cs.cs_rxface; - policy_state = &pitcs->policy_state; - policy_vft = &pitcs->policy_vft; - - policy_vft->hicn_cs_insert (pitcs, node, old_entry, policy_state); - - if (policy_state->count > policy_state->max) - { - hicn_hash_node_t *node; - hicn_pcs_entry_t *pcs_entry; - hicn_hash_entry_t *hash_entry; - policy_vft->hicn_cs_delete_get (pitcs, policy_state, &node, - &pcs_entry, &hash_entry); - - /* - * We don't have to decrease the lock (therefore we cannot - * use hicn_pcs_cs_delete function) - */ - policy_vft->hicn_cs_dequeue (pitcs, node, pcs_entry, policy_state); - - hicn_cs_delete_trimmed (pitcs, &pcs_entry, hash_entry, &node, vm); - - /* Update the global CS counter */ - pitcs->pcs_cs_count--; - } - } - else - /* Update the CS LRU, moving this item to the head */ - policy_vft->hicn_cs_update (pitcs, node, old_entry, policy_state); + /* Update the CS LRU, moving this item to the head */ + policy_vft->hicn_cs_update (pitcs, node, old_entry, policy_state); } always_inline void @@ -565,13 +528,12 @@ hicn_pcs_cs_insert_update (vlib_main_t *vm, hicn_pit_cs_t *pitcs, hicn_hash_entry_t **hash_entry, u64 hashval, u32 *node_id, index_t *dpo_ctx_id, u8 *vft_id, u8 *is_cs, u8 *hash_entry_id, u32 *bucket_id, - u8 *bucket_is_overflow, hicn_face_id_t inface) + u8 *bucket_is_overflow) { int ret; ASSERT (entry == hicn_hashtb_node_data (node)); - entry->u.cs.cs_rxface = inface; ret = hicn_pcs_cs_insert (vm, pitcs, entry, node, hash_entry, hashval, node_id, dpo_ctx_id, vft_id, is_cs, hash_entry_id, bucket_id, bucket_is_overflow); diff --git a/hicn-plugin/src/pg.c b/hicn-plugin/src/pg.c index 2f98e9c16..b77e8fcac 100644 --- a/hicn-plugin/src/pg.c +++ b/hicn-plugin/src/pg.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -203,11 +203,11 @@ hicnpg_client_interest_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, iface = (hpgm->index_ifaces % hpgm->n_ifaces); /* Rewrite and send */ isv6_0 ? - hicn_rewrite_interestv6 ( + hicn_rewrite_interestv6 ( vm, b0, (hpgm->index / hpgm->n_flows) % hpgm->max_seq_number, hpgm->interest_lifetime, hpgm->index % hpgm->n_flows, iface) : - hicn_rewrite_interestv4 ( + hicn_rewrite_interestv4 ( vm, b0, (hpgm->index / hpgm->n_flows) % hpgm->max_seq_number, hpgm->interest_lifetime, hpgm->index % hpgm->n_flows, iface); @@ -216,7 +216,7 @@ hicnpg_client_interest_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, hpgm->index++; next0 = isv6_0 ? HICNPG_INTEREST_NEXT_V6_LOOKUP : - HICNPG_INTEREST_NEXT_V4_LOOKUP; + HICNPG_INTEREST_NEXT_V4_LOOKUP; } if (hicn_interest_parse_pkt (b1, &name1, &namelen1, &hicn1, &isv6_1) == HICN_ERROR_NONE) @@ -229,11 +229,11 @@ hicnpg_client_interest_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, iface = (hpgm->index_ifaces % hpgm->n_ifaces); /* Rewrite and send */ isv6_1 ? - hicn_rewrite_interestv6 ( + hicn_rewrite_interestv6 ( vm, b1, (hpgm->index / hpgm->n_flows) % hpgm->max_seq_number, hpgm->interest_lifetime, hpgm->index % hpgm->n_flows, iface) : - hicn_rewrite_interestv4 ( + hicn_rewrite_interestv4 ( vm, b1, (hpgm->index / hpgm->n_flows) % hpgm->max_seq_number, hpgm->interest_lifetime, hpgm->index % hpgm->n_flows, iface); @@ -242,7 +242,7 @@ hicnpg_client_interest_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, hpgm->index++; next1 = isv6_1 ? HICNPG_INTEREST_NEXT_V6_LOOKUP : - HICNPG_INTEREST_NEXT_V4_LOOKUP; + HICNPG_INTEREST_NEXT_V4_LOOKUP; } /* Send pkt to next node */ vnet_buffer (b0)->sw_if_index[VLIB_TX] = ~0; @@ -320,11 +320,11 @@ hicnpg_client_interest_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, /* Rewrite and send */ isv6_0 ? - hicn_rewrite_interestv6 ( + hicn_rewrite_interestv6 ( vm, b0, (hpgm->index / hpgm->n_flows) % hpgm->max_seq_number, hpgm->interest_lifetime, hpgm->index % hpgm->n_flows, iface) : - hicn_rewrite_interestv4 ( + hicn_rewrite_interestv4 ( vm, b0, (hpgm->index / hpgm->n_flows) % hpgm->max_seq_number, hpgm->interest_lifetime, hpgm->index % hpgm->n_flows, iface); @@ -333,7 +333,7 @@ hicnpg_client_interest_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, hpgm->index++; next0 = isv6_0 ? HICNPG_INTEREST_NEXT_V6_LOOKUP : - HICNPG_INTEREST_NEXT_V4_LOOKUP; + HICNPG_INTEREST_NEXT_V4_LOOKUP; } /* Send pkt to ip lookup */ vnet_buffer (b0)->sw_if_index[VLIB_TX] = ~0; @@ -386,12 +386,12 @@ hicn_rewrite_interestv4 (vlib_main_t *vm, vlib_buffer_t *b0, u32 seq_number, .ip4 = hicnpg_main.pgen_clt_src_addr.ip4, }; hicn_name_t dst_name = { - .ip4.prefix_as_ip4 = hicnpg_main.pgen_clt_hicn_name->fp_addr.ip4, - .ip4.suffix = seq_number, + .prefix.ip4 = hicnpg_main.pgen_clt_hicn_name->fp_addr.ip4, + .suffix = seq_number, }; src_addr.ip4.as_u32 += clib_host_to_net_u32 (iface); - dst_name.ip4.prefix_as_ip4.as_u32 += clib_net_to_host_u32 (next_flow); + dst_name.prefix.ip4.as_u32 += clib_net_to_host_u32 (next_flow); /* Update locator and name */ hicn_type_t type = hicn_get_buffer (b0)->type; @@ -432,11 +432,11 @@ hicn_rewrite_interestv6 (vlib_main_t *vm, vlib_buffer_t *b0, u32 seq_number, .ip6 = hicnpg_main.pgen_clt_src_addr.ip6, }; hicn_name_t dst_name = { - .ip6.prefix_as_ip6 = hicnpg_main.pgen_clt_hicn_name->fp_addr.ip6, - .ip6.suffix = seq_number, + .prefix.ip6 = hicnpg_main.pgen_clt_hicn_name->fp_addr.ip6, + .suffix = seq_number, }; src_addr.ip6.as_u32[3] += clib_host_to_net_u32 (iface); - dst_name.ip6.prefix_as_ip6.as_u32[3] += clib_net_to_host_u32 (next_flow); + dst_name.prefix.ip6.as_u32[3] += clib_net_to_host_u32 (next_flow); /* Update locator and name */ hicn_type_t type = hicn_get_buffer (b0)->type; @@ -1011,10 +1011,10 @@ hicnpg_node_server_fn (vlib_main_t *vm, vlib_node_runtime_t *node, rb = vlib_get_buffer (vm, hpgsm->pgen_svr_buffer_idx); isv6_0 ? convert_interest_to_data_v6 (vm, b0, rb, bi0) : - convert_interest_to_data_v4 (vm, b0, rb, bi0); + convert_interest_to_data_v4 (vm, b0, rb, bi0); next0 = isv6_0 ? HICNPG_SERVER_NEXT_V6_LOOKUP : - HICNPG_SERVER_NEXT_V4_LOOKUP; + HICNPG_SERVER_NEXT_V4_LOOKUP; } if (match1) @@ -1029,10 +1029,10 @@ hicnpg_node_server_fn (vlib_main_t *vm, vlib_node_runtime_t *node, rb = vlib_get_buffer (vm, hpgsm->pgen_svr_buffer_idx); isv6_1 ? convert_interest_to_data_v6 (vm, b1, rb, bi1) : - convert_interest_to_data_v4 (vm, b1, rb, bi1); + convert_interest_to_data_v4 (vm, b1, rb, bi1); next1 = isv6_1 ? HICNPG_SERVER_NEXT_V6_LOOKUP : - HICNPG_SERVER_NEXT_V4_LOOKUP; + HICNPG_SERVER_NEXT_V4_LOOKUP; } pkts_processed += 2; @@ -1107,10 +1107,10 @@ hicnpg_node_server_fn (vlib_main_t *vm, vlib_node_runtime_t *node, rb = vlib_get_buffer (vm, hpgsm->pgen_svr_buffer_idx); isv6_0 ? convert_interest_to_data_v6 (vm, b0, rb, bi0) : - convert_interest_to_data_v4 (vm, b0, rb, bi0); + convert_interest_to_data_v4 (vm, b0, rb, bi0); next0 = isv6_0 ? HICNPG_SERVER_NEXT_V6_LOOKUP : - HICNPG_SERVER_NEXT_V4_LOOKUP; + HICNPG_SERVER_NEXT_V4_LOOKUP; } if (PREDICT_FALSE ((node->flags & VLIB_NODE_FLAG_TRACE) && (b0->flags & VLIB_BUFFER_IS_TRACED))) diff --git a/hicn-plugin/src/pg.h b/hicn-plugin/src/pg.h index 059b076fb..7855248e6 100644 --- a/hicn-plugin/src/pg.h +++ b/hicn-plugin/src/pg.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/route.c b/hicn-plugin/src/route.c index 34a94936e..a84891b9a 100644 --- a/hicn-plugin/src/route.c +++ b/hicn-plugin/src/route.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -33,6 +33,7 @@ #include "strategies/dpo_mw.h" #include "infra.h" #include "udp_tunnels/udp_tunnel.h" +#include "mapme.h" #define FIB_SOURCE_HICN 0x04 // Right after the FIB_SOURCE_INTERFACE priority @@ -105,94 +106,76 @@ int hicn_route_set_strategy (fib_prefix_t *prefix, u8 strategy_id) { const dpo_id_t *hicn_dpo_id; - dpo_id_t new_dpo_id = DPO_INVALID; int ret; - hicn_dpo_ctx_t *old_hicn_dpo_ctx; - const hicn_dpo_vft_t *new_dpo_vft; - index_t new_hicn_dpo_idx; + hicn_dpo_ctx_t *hicn_dpo_ctx; u32 fib_index; ret = hicn_route_get_dpo (prefix, &hicn_dpo_id, &fib_index); if (ret == HICN_ERROR_NONE) { - old_hicn_dpo_ctx = hicn_strategy_dpo_ctx_get (hicn_dpo_id->dpoi_index); + hicn_dpo_ctx = hicn_strategy_dpo_ctx_get (hicn_dpo_id->dpoi_index); + const hicn_dpo_vft_t *dpo_vft = hicn_dpo_get_vft_from_id (strategy_id); - new_dpo_vft = hicn_dpo_get_vft_from_id (strategy_id); - - if (new_dpo_vft == NULL || old_hicn_dpo_ctx == NULL) + if (hicn_dpo_ctx == NULL || dpo_vft == NULL) return HICN_ERROR_STRATEGY_NOT_FOUND; - /* Create a new dpo for the new strategy */ - new_dpo_vft->hicn_dpo_create ( - hicn_dpo_id->dpoi_proto, old_hicn_dpo_ctx->next_hops, - old_hicn_dpo_ctx->entry_count, &new_hicn_dpo_idx); - - /* the value we got when we registered */ - dpo_set (&new_dpo_id, new_dpo_vft->hicn_dpo_get_type (), - (ip46_address_is_ip4 (&prefix->fp_addr) ? DPO_PROTO_IP4 : - DPO_PROTO_IP6), - new_hicn_dpo_idx); - - /* Here is where we create the "via" like route */ - /* - * For the moment we use the global one the prefix you want - * to match Neale suggested -- FIB_SOURCE_HICN the client - * that is adding them -- no easy explanation at this time… - */ - fib_node_index_t new_fib_node_index = - fib_table_entry_special_dpo_update (fib_index, prefix, hicn_fib_src, - FIB_ENTRY_FLAG_EXCLUSIVE, - &new_dpo_id); - - dpo_unlock (&new_dpo_id); - ret = (new_fib_node_index != FIB_NODE_INDEX_INVALID) ? - HICN_ERROR_NONE : - HICN_ERROR_ROUTE_NOT_UPDATED; + dpo_vft->hicn_dpo_update_type (hicn_dpo_ctx); } // Remember to remove the lock from the table when removing the entry return ret; } -int -ip_nh_add_helper (fib_protocol_t fib_proto, const fib_prefix_t *rpfx, - ip46_address_t *nh, u32 sw_if) +static int +ip_nh_add_del_helper (fib_protocol_t fib_proto, const fib_prefix_t *rpfx, + ip46_address_t *nh, u32 sw_if, u32 udp_encap_id, + dpo_proto_t proto, u8 is_add) { fib_route_path_t *rpaths = NULL, rpath; u32 fib_index = fib_table_find (fib_proto, 0); - clib_memset (&rpath, 0, sizeof (rpath)); + + if (nh) + { + rpath.frp_addr = *nh; + rpath.frp_sw_if_index = sw_if; + } + else if (udp_encap_id != ~0) + { + rpath.frp_udp_encap_id = udp_encap_id; + rpath.frp_flags |= FIB_ROUTE_PATH_UDP_ENCAP; + } + rpath.frp_weight = 1; - rpath.frp_sw_if_index = sw_if; - rpath.frp_addr = *nh; - rpath.frp_proto = ip46_address_is_ip4 (nh) ? DPO_PROTO_IP4 : DPO_PROTO_IP6; + rpath.frp_proto = proto; vec_add1 (rpaths, rpath); - fib_table_entry_path_add2 (fib_index, rpfx, FIB_SOURCE_CLI, - FIB_ENTRY_FLAG_NONE, rpaths); + if (is_add) + fib_table_entry_path_add2 (fib_index, rpfx, FIB_SOURCE_API, + FIB_ENTRY_FLAG_NONE, rpaths); + else + fib_table_entry_path_remove2 (fib_index, rpfx, FIB_SOURCE_API, rpaths); + return 0; } int -ip_nh_del_helper (fib_protocol_t fib_proto, const fib_prefix_t *rpfx, - ip46_address_t *nh, u32 sw_if) +ip_nh_adj_add_del_helper (fib_protocol_t fib_proto, const fib_prefix_t *rpfx, + ip46_address_t *nh, u32 sw_if, u8 is_add) { - fib_route_path_t *rpaths = NULL, rpath; - - u32 fib_index = fib_table_find (fib_proto, 0); - - clib_memset (&rpath, 0, sizeof (rpath)); - rpath.frp_weight = 1; - rpath.frp_sw_if_index = sw_if; - rpath.frp_addr = *nh; - rpath.frp_proto = ip46_address_is_ip4 (nh) ? DPO_PROTO_IP4 : DPO_PROTO_IP6; - - vec_add1 (rpaths, rpath); + return ip_nh_add_del_helper ( + fib_proto, rpfx, nh, sw_if, ~0, + ip46_address_is_ip4 (nh) ? DPO_PROTO_IP4 : DPO_PROTO_IP6, is_add); +} - fib_table_entry_path_remove2 (fib_index, rpfx, FIB_SOURCE_CLI, rpaths); - return 0; +int +ip_nh_udp_tunnel_add_del_helper (fib_protocol_t fib_proto, + const fib_prefix_t *rpfx, u32 uei, + dpo_proto_t proto, u8 is_add) +{ + return ip_nh_add_del_helper (fib_proto, rpfx, NULL, ~0, uei, proto, is_add); } static ip46_address_t * @@ -234,13 +217,14 @@ get_address (ip46_address_t *nh, u32 sw_if, fib_protocol_t proto) } static void -sync_hicn_fib_entry (hicn_dpo_ctx_t *fib_entry) +sync_hicn_fib_entry (hicn_dpo_ctx_t *fib_entry, hicn_face_id_t **pvec_faces) { + hicn_face_id_t *vec_faces = NULL; const dpo_id_t *dpo_loadbalance = fib_entry_contribute_ip_forwarding (fib_entry->fib_entry_index); + const fib_entry_t *_fib_entry = fib_entry_get (fib_entry->fib_entry_index); const load_balance_t *lb0 = load_balance_get (dpo_loadbalance->dpoi_index); index_t hicn_fib_entry_index = hicn_strategy_dpo_ctx_get_index (fib_entry); - hicn_face_id_t *vec_faces = 0; dpo_id_t temp = DPO_INVALID; const dpo_id_t *former_dpo = &temp; @@ -287,32 +271,31 @@ sync_hicn_fib_entry (hicn_dpo_ctx_t *fib_entry) nh = get_address (&(adj->sub_type.nbr.next_hop), sw_if, fib_entry->proto); ADD_FACE (nh); + HICN_DEBUG ("Added new HICN face: %d because of route prefix %U", + face_id, format_ip_prefix, &_fib_entry->fe_prefix); } else if (dpo->dpoi_type == dpo_type_udp_ip4 || dpo->dpoi_type == dpo_type_udp_ip6) { - u8 proto = dpo->dpoi_type == dpo_type_udp_ip4 ? FIB_PROTOCOL_IP4 : - FIB_PROTOCOL_IP6; + dpo_proto_t proto = + dpo->dpoi_type == dpo_type_udp_ip4 ? DPO_PROTO_IP4 : DPO_PROTO_IP6; ip46_address_t _nh = { 0 }; nh = &_nh; - switch (dpo->dpoi_proto) + switch (_fib_entry->fe_prefix.fp_proto) { case FIB_PROTOCOL_IP6: - case FIB_PROTOCOL_IP4: - /** - * Independently of the type of tunnel, encapsulated packet - * can be either v6 or v4, so we need to create 2 faces for each - * version. Tunneled hicn packet MUST have locator set to the - * loopback address, so ::1 for IPv6 and 127.0.0.1 for IPv4. - */ ip46_address_set_ip6 (nh, &localhost6); ADD_FACE (nh); + break; + case FIB_PROTOCOL_IP4: ip46_address_set_ip4 (nh, &localhost4); ADD_FACE (nh); break; default: continue; } + HICN_DEBUG ("Added new UDP face: %d because of route prefix %s", + face_id, format_ip_prefix, &_fib_entry->fe_prefix); udp_tunnel_add_existing (dpo->dpoi_index, proto); } } @@ -345,7 +328,8 @@ sync_hicn_fib_entry (hicn_dpo_ctx_t *fib_entry) /* Remove the lock added by hicn_face_add */ hicn_face_unlock_with_id (*face_id); } - vec_free (vec_faces); + + *pvec_faces = vec_faces; } static void @@ -380,7 +364,7 @@ disable_data_receiving_rm_fib_entry (vnet_main_t *vnm, vnet_sw_interface_t *si, } int -hicn_route_enable (fib_prefix_t *prefix) +hicn_route_enable (fib_prefix_t *prefix, hicn_face_id_t **pvec_faces) { int ret = HICN_ERROR_NONE; @@ -413,10 +397,14 @@ hicn_route_enable (fib_prefix_t *prefix) if (fib_hicn_entry_index == FIB_NODE_INDEX_INVALID) { + HICN_DEBUG ( + "No route found for %U. Creating DPO and tracking fib prefix.", + format_ip_prefix, prefix); dpo_id_t dpo = DPO_INVALID; index_t dpo_idx; default_dpo.hicn_dpo_create (prefix->fp_proto, 0, NEXT_HOP_INVALID, &dpo_idx); + HICN_DEBUG ("Created new DPO_MW_CTX_T: %d.", dpo_idx); /* the value we got when we registered */ /* @@ -425,8 +413,14 @@ hicn_route_enable (fib_prefix_t *prefix) */ dpo_set (&dpo, default_dpo.hicn_dpo_get_type (), (ip46_address_is_ip4 (&prefix->fp_addr) ? DPO_PROTO_IP4 : - DPO_PROTO_IP6), + DPO_PROTO_IP6), dpo_idx); + HICN_DEBUG ( + "dpo_set called with parameters: type=%d, proto=%s, index=%d", + default_dpo.hicn_dpo_get_type (), + ip46_address_is_ip4 (&prefix->fp_addr) ? "DPO_PROTO_IP4" : + "DPO_PROTO_IP6", + dpo_idx); hicn_dpo_ctx_t *fib_entry = hicn_strategy_dpo_ctx_get (dpo_idx); @@ -448,7 +442,8 @@ hicn_route_enable (fib_prefix_t *prefix) fib_hicn_index, prefix, hicn_fib_src, (FIB_ENTRY_FLAG_EXCLUSIVE | FIB_ENTRY_FLAG_LOOSE_URPF_EXEMPT), &dpo); - sync_hicn_fib_entry (fib_entry); + HICN_DEBUG ("Calling sync_hicn_fib_entry"); + sync_hicn_fib_entry (fib_entry, pvec_faces); /* We added a route, therefore add one lock to the table */ fib_table_lock (fib_index, prefix->fp_proto, hicn_fib_src); @@ -470,6 +465,8 @@ hicn_route_enable (fib_prefix_t *prefix) } else { + HICN_DEBUG ("Found a route for %U. Updating DPO.", format_ip_prefix, + &prefix); const dpo_id_t *load_balance_dpo_id; const dpo_id_t *strategy_dpo_id; @@ -481,6 +478,7 @@ hicn_route_enable (fib_prefix_t *prefix) if (load_balance_dpo_id->dpoi_type != DPO_LOAD_BALANCE) { ret = HICN_ERROR_ROUTE_NO_LD; + HICN_ERROR ("DPO is not a load balance."); goto done; } else @@ -493,19 +491,22 @@ hicn_route_enable (fib_prefix_t *prefix) if (!dpo_is_hicn (strategy_dpo_id)) { ret = HICN_ERROR_ROUTE_DPO_NO_HICN; + HICN_ERROR ("DPO is not hicn."); goto done; } if (lb->lb_n_buckets > 1) { ret = HICN_ERROR_ROUTE_MLT_LD; + HICN_ERROR ("Too many load balance buckets."); goto done; } hicn_dpo_ctx_t *hicn_fib_entry = hicn_strategy_dpo_ctx_get (strategy_dpo_id->dpoi_index); - sync_hicn_fib_entry (hicn_fib_entry); + HICN_DEBUG ("Calling sync_hicn_fib_entry"); + sync_hicn_fib_entry (hicn_fib_entry, pvec_faces); } } @@ -527,6 +528,7 @@ hicn_route_disable (fib_prefix_t *prefix) if (fib_hicn_entry_index == FIB_NODE_INDEX_INVALID) { + HICN_ERROR ("Route %U not found", format_ip_prefix, prefix); return HICN_ERROR_ROUTE_NOT_FOUND; } else @@ -542,6 +544,8 @@ hicn_route_disable (fib_prefix_t *prefix) /* The dpo is not a load balance dpo as expected */ if (load_balance_dpo_id->dpoi_type != DPO_LOAD_BALANCE) { + HICN_ERROR ("DPO for route %U is not a load balance.", + format_ip_prefix, prefix); ret = HICN_ERROR_ROUTE_NO_LD; goto done; } @@ -554,12 +558,16 @@ hicn_route_disable (fib_prefix_t *prefix) if (!dpo_is_hicn (strategy_dpo_id)) { + HICN_ERROR ("ERROR: DPO for route %U is not a hicn.", + format_ip_prefix, prefix); ret = HICN_ERROR_ROUTE_DPO_NO_HICN; goto done; } if (lb->lb_n_buckets > 1) { + HICN_ERROR ("DPO for route %U contains multiple next hops.", + format_ip_prefix, prefix); ret = HICN_ERROR_ROUTE_MLT_LD; goto done; } @@ -567,17 +575,37 @@ hicn_route_disable (fib_prefix_t *prefix) hicn_fib_entry = hicn_strategy_dpo_ctx_get (strategy_dpo_id->dpoi_index); + HICN_DEBUG ("Found from hicn_strategy_dpo_ctx_get with index %d: %p", + strategy_dpo_id->dpoi_index, hicn_fib_entry); + + if (PREDICT_FALSE (!hicn_fib_entry)) + { + HICN_ERROR ( + "hicn_strategy_dpo_ctx_get for index %d returned NULL", + strategy_dpo_id->dpoi_index); + ret = HICN_ERROR_ROUTE_DPO_NO_HICN; + goto done; + } + for (int i = 0; i < hicn_fib_entry->entry_count; i++) { hicn_strategy_dpo_ctx_del_nh (hicn_fib_entry->next_hops[i], hicn_fib_entry); } + + hicn_mapme_tfib_clear ((hicn_mapme_tfib_t *) hicn_fib_entry); } + HICN_DEBUG ( + "Calling fib_entry_untrack and fib_table_entry_special_remove " + "for route %U.", + format_ip_prefix, prefix); + fib_entry_untrack (hicn_fib_entry->fib_entry_index, hicn_fib_entry->fib_sibling); fib_table_entry_special_remove (fib_hicn_index, prefix, hicn_fib_src); + fib_node_unlock (&hicn_fib_entry->fib_node); /* Disable the feature to punt data packet every time we enable a new * hicn route */ @@ -618,7 +646,11 @@ hicn_fib_back_walk_notify (fib_node_t *node, fib_node_back_walk_ctx_t *ctx) hicn_dpo_ctx_t *fib_entry = hicn_ctx_from_fib_node (node); - sync_hicn_fib_entry (fib_entry); + hicn_face_id_t *vec_faces = NULL; + HICN_DEBUG ("Calling sync_hicn_fib_entry from hicn_fib_back_walk_notify"); + sync_hicn_fib_entry (fib_entry, &vec_faces); + if (vec_faces != NULL) + vec_free (vec_faces); return (FIB_NODE_BACK_WALK_CONTINUE); } @@ -661,7 +693,8 @@ enable_data_on_existing_hicn (fib_node_index_t fei, void *ctx) goto done; } - enable_disable_data_receiving (strategy_dpo_id->dpoi_proto, sw_if, 1); + enable_disable_data_receiving ( + (fib_protocol_t) strategy_dpo_id->dpoi_proto, sw_if, 1); } done: @@ -673,18 +706,18 @@ set_table_interface_add_del (vnet_main_t *vnm, u32 sw_if_index, u32 is_add) { if (!is_add) - return HICN_ERROR_NONE; + return NULL; - int rv = ip_table_bind (FIB_PROTOCOL_IP4, sw_if_index, HICN_FIB_TABLE, 1); + int rv = ip_table_bind (FIB_PROTOCOL_IP4, sw_if_index, HICN_FIB_TABLE); if (!rv) { - rv = ip_table_bind (FIB_PROTOCOL_IP6, sw_if_index, HICN_FIB_TABLE, 1); + rv = ip_table_bind (FIB_PROTOCOL_IP6, sw_if_index, HICN_FIB_TABLE); if (rv) { /* An error occurred. Bind the interface back to the default fib */ - ip_table_bind (FIB_PROTOCOL_IP4, sw_if_index, 0, 1); + ip_table_bind (FIB_PROTOCOL_IP4, sw_if_index, 0); } } @@ -707,10 +740,11 @@ set_table_interface_add_del (vnet_main_t *vnm, u32 sw_if_index, u32 is_add) } return rv ? clib_error_return (0, "unable to add hicn table to interface") : - 0; + 0; } -VNET_SW_INTERFACE_ADD_DEL_FUNCTION (set_table_interface_add_del); +VNET_SW_INTERFACE_ADD_DEL_FUNCTION_PRIO (set_table_interface_add_del, + VNET_ITF_FUNC_PRIORITY_HIGH); void hicn_route_init () @@ -720,7 +754,8 @@ hicn_route_init () hicn_fib_src = fib_source_allocate ("hicn", FIB_SOURCE_HICN, FIB_SOURCE_BH_API); - hicn_fib_node_type = fib_node_register_new_type (&hicn_fib_vft); + hicn_fib_node_type = + fib_node_register_new_type ("hicn_route_fib_node", &hicn_fib_vft); ip_table_create (FIB_PROTOCOL_IP4, HICN_FIB_TABLE, 1, (const u8 *) "hicn4"); ip_table_create (FIB_PROTOCOL_IP6, HICN_FIB_TABLE, 1, (const u8 *) "hicn6"); diff --git a/hicn-plugin/src/route.h b/hicn-plugin/src/route.h index 19b18b8c6..072926498 100644 --- a/hicn-plugin/src/route.h +++ b/hicn-plugin/src/route.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -73,28 +73,31 @@ int hicn_route_get_dpo (const fib_prefix_t *prefix, const dpo_id_t **hicn_dpo, int hicn_route_set_strategy (fib_prefix_t *prefix, u32 strategy_id); /** - * @Brief Helper to add a nex hop in the vrf 0. If there are no entries in the - * vrf 0 that matches with the prefix (epm), a new one is created. + * @Brief Helper to add an adj nex hop in the vrf 0. If there are no entries in + * the vrf 0 that matches with the prefix (epm), a new one is created. * * @param fib_proto FIB_PROTOCOL_IP6 or FIB_PROTOCOL_IP4 (mpls not supported) - * @param pfx Prefix for which to add a next hop + * @param rpfx Prefix for which to add a next hop * @param nh Next hop to add * @param sw_if Software interface index to add in the next hop */ -int ip_nh_add_helper (fib_protocol_t fib_proto, const fib_prefix_t *pfx, - ip46_address_t *nh, u32 sw_if); +int ip_nh_adj_add_del_helper (fib_protocol_t fib_proto, + const fib_prefix_t *rpfx, ip46_address_t *nh, + u32 sw_if, u8 is_add); /** - * @Brief Helper to remove a nex hop in the vrf 0. If there are no entries in - * the vrf 0 nothing happens. + * @Brief Helper to add an udp-tunnel nex hop in the vrf 0. If there are no + * entries in the vrf 0 that matches with the prefix (epm), a new one is + * created. * * @param fib_proto FIB_PROTOCOL_IP6 or FIB_PROTOCOL_IP4 (mpls not supported) - * @param pfx Prefix for which to remove a next hop - * @param nh Next hop to remove - * @param sw_if Software interface index in the next hop definition + * @param rpfx Prefix for which to add a next hop + * @param uei The UDP ENCAP ID + * @param sw_if The */ -int ip_nh_del_helper (fib_protocol_t fib_proto, const fib_prefix_t *rpfx, - ip46_address_t *nh, u32 sw_if); +int ip_nh_udp_tunnel_add_del_helper (fib_protocol_t fib_proto, + const fib_prefix_t *rpfx, u32 uei, + dpo_proto_t proto, u8 is_add); /** * @Brief Enable an hICN for an ip prefix @@ -106,7 +109,7 @@ int ip_nh_del_helper (fib_protocol_t fib_proto, const fib_prefix_t *rpfx, * loadbalancer in the vrf HICN already contains a dpo which is not an hICN one * HICN_ERROR_ROUTE_MLT_LD if there are more than a dpo in the vpp loadbalancer */ -int hicn_route_enable (fib_prefix_t *prefix); +int hicn_route_enable (fib_prefix_t *prefix, hicn_face_id_t **vec_faces); /** * @Brief Disable an hICN for an ip prefix. If hICN wasn't enable on the prefix diff --git a/hicn-plugin/src/state.h b/hicn-plugin/src/state.h index 561aef2db..39953722d 100644 --- a/hicn-plugin/src/state.h +++ b/hicn-plugin/src/state.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/strategies/dpo_mw.c b/hicn-plugin/src/strategies/dpo_mw.c index 70ef7d7c9..1a7d2e495 100644 --- a/hicn-plugin/src/strategies/dpo_mw.c +++ b/hicn-plugin/src/strategies/dpo_mw.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -28,6 +28,7 @@ static const hicn_dpo_vft_t hicn_dpo_mw_vft = { .hicn_dpo_get_type = &hicn_dpo_strategy_mw_get_type, .hicn_dpo_module_init = &hicn_dpo_strategy_mw_module_init, .hicn_dpo_create = &hicn_strategy_mw_ctx_create, + .hicn_dpo_update_type = &hicn_strategy_mw_update_ctx_type, .hicn_dpo_add_update_nh = &hicn_strategy_mw_ctx_add_nh, .hicn_dpo_del_nh = &hicn_strategy_mw_ctx_del_nh, .hicn_dpo_format = &hicn_strategy_mw_format_ctx @@ -117,8 +118,22 @@ hicn_strategy_mw_ctx_create (fib_protocol_t proto, *dpo_idx = hicn_strategy_dpo_ctx_get_index (hicn_strategy_ctx); - init_dpo_ctx (hicn_strategy_ctx, next_hop, nh_len, hicn_dpo_type_mw, proto); + HICN_DEBUG ("Successful hicn_strategy_dpo_ctx_alloc with index %d", + *dpo_idx); + init_dpo_ctx (hicn_strategy_ctx, next_hop, nh_len, hicn_dpo_type_mw, + (dpo_proto_t) proto); + + memset (hicn_strategy_mw_ctx->weight, 0, HICN_PARAM_FIB_ENTRY_NHOPS_MAX); +} + +void +hicn_strategy_mw_update_ctx_type (hicn_dpo_ctx_t *hicn_strategy_ctx) +{ + hicn_strategy_mw_ctx_t *hicn_strategy_mw_ctx; + hicn_strategy_mw_ctx = (hicn_strategy_mw_ctx_t *) hicn_strategy_ctx->data; + + hicn_strategy_ctx->dpo_type = hicn_dpo_type_mw; memset (hicn_strategy_mw_ctx->weight, 0, HICN_PARAM_FIB_ENTRY_NHOPS_MAX); } diff --git a/hicn-plugin/src/strategies/dpo_mw.h b/hicn-plugin/src/strategies/dpo_mw.h index 1a174631a..d2807d1a5 100644 --- a/hicn-plugin/src/strategies/dpo_mw.h +++ b/hicn-plugin/src/strategies/dpo_mw.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -72,6 +72,13 @@ void hicn_strategy_mw_ctx_create (fib_protocol_t proto, index_t *dpo_idx); /** + * @brief Update existing ctx setting it to mw + * + * @param hicn_strategy_ctx pointer to the ctx to update + */ +void hicn_strategy_mw_update_ctx_type (hicn_dpo_ctx_t *hicn_strategy_ctx); + +/** * @brief Add or update a next hop in the dpo ctx. * * This function is meant to be used in the control plane and not in the data diff --git a/hicn-plugin/src/strategies/dpo_rp.c b/hicn-plugin/src/strategies/dpo_rp.c new file mode 100644 index 000000000..7f527cdb6 --- /dev/null +++ b/hicn-plugin/src/strategies/dpo_rp.c @@ -0,0 +1,155 @@ +/* + * Copyright (c) 2021 Cisco and/or its affiliates. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at: + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "dpo_rp.h" +#include "strategy_rp.h" +#include "../strategy_dpo_manager.h" +#include "../strategy_dpo_ctx.h" + +/** + * @brief DPO type value for the rp_strategy + */ +static dpo_type_t hicn_dpo_type_rp; + +static const hicn_dpo_vft_t hicn_dpo_rp_vft = { + .hicn_dpo_is_type = &hicn_dpo_is_type_strategy_rp, + .hicn_dpo_get_type = &hicn_dpo_strategy_rp_get_type, + .hicn_dpo_module_init = &hicn_dpo_strategy_rp_module_init, + .hicn_dpo_create = &hicn_strategy_rp_ctx_create, + .hicn_dpo_update_type = &hicn_strategy_rp_update_ctx_type, + .hicn_dpo_add_update_nh = &hicn_strategy_rp_ctx_add_nh, + .hicn_dpo_del_nh = &hicn_strategy_rp_ctx_del_nh, + .hicn_dpo_format = &hicn_strategy_rp_format_ctx +}; + +int +hicn_dpo_is_type_strategy_rp (const dpo_id_t *dpo) +{ + return dpo->dpoi_type == hicn_dpo_type_rp; +} + +void +hicn_dpo_strategy_rp_module_init (void) +{ + /* + * Register our type of dpo + */ + hicn_dpo_type_rp = hicn_dpo_register_new_type ( + hicn_nodes_strategy, &hicn_dpo_rp_vft, hicn_rp_strategy_get_vft (), + &dpo_strategy_rp_ctx_vft); +} + +dpo_type_t +hicn_dpo_strategy_rp_get_type (void) +{ + return hicn_dpo_type_rp; +} + +////////////////////////////////////////////////////////////////////////////////////////////////// + +u8 * +hicn_strategy_rp_format_ctx (u8 *s, int n, ...) +{ + va_list args; + va_start (args, n); + s = format_hicn_strategy_rp_ctx (s, &args); + return s; +} + +u8 * +format_hicn_strategy_rp_ctx (u8 *s, va_list *ap) +{ + int i = 0; + index_t index = va_arg (*ap, index_t); + hicn_dpo_ctx_t *dpo_ctx = NULL; + u32 indent = va_arg (*ap, u32); + + dpo_ctx = hicn_strategy_dpo_ctx_get (index); + if (dpo_ctx == NULL) + return s; + + for (i = 0; i < HICN_PARAM_FIB_ENTRY_NHOPS_MAX; i++) + { + u8 *buf = NULL; + if (i < dpo_ctx->entry_count) + buf = format (NULL, "FIB"); + else if (i >= HICN_PARAM_FIB_ENTRY_NHOPS_MAX - dpo_ctx->tfib_entry_count) + buf = format (NULL, "TFIB"); + else + continue; + + s = format (s, "\n"); + s = format (s, "%U ", format_hicn_face, dpo_ctx->next_hops[i], indent); + s = format (s, " %s", buf); + } + + return (s); +} + +void +hicn_strategy_rp_ctx_create (fib_protocol_t proto, + const hicn_face_id_t *next_hop, int nh_len, + index_t *dpo_idx) +{ + hicn_dpo_ctx_t *hicn_strategy_ctx; + + /* Allocate a hicn_dpo_ctx on the vpp pool and initialize it */ + hicn_strategy_ctx = hicn_strategy_dpo_ctx_alloc (); + + *dpo_idx = hicn_strategy_dpo_ctx_get_index (hicn_strategy_ctx); + + init_dpo_ctx (hicn_strategy_ctx, next_hop, nh_len, hicn_dpo_type_rp, + (dpo_proto_t) proto); +} + +void +hicn_strategy_rp_update_ctx_type (hicn_dpo_ctx_t *hicn_strategy_ctx) +{ + hicn_strategy_ctx->dpo_type = hicn_dpo_type_rp; + // don't care to reset data, it is not used +} + +int +hicn_strategy_rp_ctx_add_nh (hicn_face_id_t nh, index_t dpo_idx) +{ + hicn_dpo_ctx_t *hicn_strategy_dpo_ctx = hicn_strategy_dpo_ctx_get (dpo_idx); + u8 pos = 0; + + if (hicn_strategy_dpo_ctx == NULL) + { + return HICN_ERROR_STRATEGY_NOT_FOUND; + } + + hicn_strategy_dpo_ctx_add_nh (nh, hicn_strategy_dpo_ctx, &pos); + // nothing else to initialize in this strategy + return HICN_ERROR_NONE; +} + +int +hicn_strategy_rp_ctx_del_nh (hicn_face_id_t face_id, index_t dpo_idx) +{ + hicn_dpo_ctx_t *hicn_strategy_dpo_ctx = hicn_strategy_dpo_ctx_get (dpo_idx); + // No need to change the current_nhop. It will be updated at the next + // selection. + return hicn_strategy_dpo_ctx_del_nh (face_id, hicn_strategy_dpo_ctx); +} + +/* + * fd.io coding-style-patch-verification: ON + * + * Local Variables: + * eval: (c-set-style "gnu") + * End: + */ diff --git a/hicn-plugin/src/strategies/dpo_rp.h b/hicn-plugin/src/strategies/dpo_rp.h new file mode 100644 index 000000000..4fe645add --- /dev/null +++ b/hicn-plugin/src/strategies/dpo_rp.h @@ -0,0 +1,152 @@ +/* + * Copyright (c) 2021 Cisco and/or its affiliates. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at: + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#ifndef __HICN_DPO_RP_H__ +#define __HICN_DPO_RP_H__ + +#include <vnet/dpo/dpo.h> +#include "../strategy_dpo_ctx.h" + +/** + * @file dpo_rp.h + * + * This file implements the strategy vtf (see strategy.h) and + * the dpo vft (see strategy_dpo_manager.h) for the strategy + * replication. + */ + +typedef struct hicn_strategy_rp_ctx_s +{ +} hicn_strategy_rp_ctx_t; + +/** + * @brief Format the dpo ctx for a human-readable string + * + * @param s String to which to append the formatted dpo ctx + * @param ap List of parameters for the formatting + * + * @result The string with the formatted dpo ctx + */ +u8 *format_hicn_strategy_rp_ctx (u8 *s, va_list *ap); + +const static dpo_vft_t dpo_strategy_rp_ctx_vft = { + .dv_lock = hicn_strategy_dpo_ctx_lock, + .dv_unlock = hicn_strategy_dpo_ctx_unlock, + .dv_format = format_hicn_strategy_rp_ctx, +}; + +/** + * @brief Retrieve an hicn_strategy_rp_ctx object + * + * @param indext Index of the hicn_dpo_ctx to retrieve + * @return The hicn_dpo_ctx object or NULL + */ +hicn_dpo_ctx_t *hicn_strategy_rp_ctx_get (index_t index); + +/** + * @brief Create a new replication ctx + * + * @param proto The protocol to which the dpo is meant for (see vpp docs) + * @param next_hop A list of next hops to be inserted in the dpo ctx + * @param nh_len Size of the list + * @param dpo_idx index_t that will hold the index of the created dpo ctx + * @return HICN_ERROR_NONE if the creation was fine, otherwise EINVAL + */ +void hicn_strategy_rp_ctx_create (fib_protocol_t proto, + const hicn_face_id_t *next_hop, int nh_len, + index_t *dpo_idx); + +/** + * @brief Update existing ctx setting it to rp + * + * @param hicn_strategy_ctx pointer to the ctx to update + */ +void hicn_strategy_rp_update_ctx_type (hicn_dpo_ctx_t *hicn_strategy_ctx); + +/** + * @brief Add or update a next hop in the dpo ctx. + * + * This function is meant to be used in the control plane and not in the data + * plane, as it is not optimized for the latter. + * + * @param nh Next hop to insert in the dpo ctx + * @param dpo_idx Index of the dpo ctx to update with the new or updated next + * hop + * @return HICN_ERROR_NONE if the update or insert was fine, + * otherwise HICN_ERROR_DPO_CTX_NOT_FOUND + */ +int hicn_strategy_rp_ctx_add_nh (hicn_face_id_t nh, index_t dpo_idx); + +/** + * @brief Delete a next hop in the dpo ctx. + * + * @param face_id Face identifier of the next hop + * @param dpo_idx Index of the dpo ctx to update with the new or updated next + * hop + * @return HICN_ERROR_NONE if the update or insert was fine, + * otherwise HICN_ERROR_DPO_CTS_NOT_FOUND + */ +int hicn_strategy_rp_ctx_del_nh (hicn_face_id_t face_id, index_t dpo_idx); + +/** + * @brief Prefetch a dpo + * + * @param dpo_idx Index of the dpo ctx to prefetch + */ +void hicn_strategy_rp_ctx_prefetch (index_t dpo_idx); + +/** + * @brief Return true if the dpo is of type strategy rp + * + * @param dpo Dpo to check the type + */ +int hicn_dpo_is_type_strategy_rp (const dpo_id_t *dpo); + +/** + * @brief Initialize the Replication strategy + */ +void hicn_dpo_strategy_rp_module_init (void); + +/** + * @brief Return the dpo type for the Replication strategy + */ +dpo_type_t hicn_dpo_strategy_rp_get_type (void); + +/** + * @brief Format the dpo ctx for the strategy Replication + * + * @param s String to append the formatted dpo ctx + * @param ap List of arguments to format + */ +u8 *format_hicn_dpo_strategy_rp (u8 *s, va_list *ap); + +/** + * @brief Format the dpo ctx for the strategy Replication. To + * call from other functions + * + * @param s String to append the formatted dpo ctx + * @param ... List of arguments to format + */ +u8 *hicn_strategy_rp_format_ctx (u8 *s, int n, ...); + +#endif // __HICN_DPO_RP_H__ + +/* + * fd.io coding-style-patch-verification: ON + * + * Local Variables: + * eval: (c-set-style "gnu") + * End: + */ diff --git a/hicn-plugin/src/strategies/dpo_rr.c b/hicn-plugin/src/strategies/dpo_rr.c index 3fe506bd1..86b68186b 100644 --- a/hicn-plugin/src/strategies/dpo_rr.c +++ b/hicn-plugin/src/strategies/dpo_rr.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -28,6 +28,7 @@ static const hicn_dpo_vft_t hicn_dpo_rr_vft = { .hicn_dpo_get_type = &hicn_dpo_strategy_rr_get_type, .hicn_dpo_module_init = &hicn_dpo_strategy_rr_module_init, .hicn_dpo_create = &hicn_strategy_rr_ctx_create, + .hicn_dpo_update_type = &hicn_strategy_rr_update_ctx_type, .hicn_dpo_add_update_nh = &hicn_strategy_rr_ctx_add_nh, .hicn_dpo_del_nh = &hicn_strategy_rr_ctx_del_nh, .hicn_dpo_format = &hicn_strategy_rr_format_ctx @@ -117,11 +118,22 @@ hicn_strategy_rr_ctx_create (fib_protocol_t proto, *dpo_idx = hicn_strategy_dpo_ctx_get_index (hicn_strategy_ctx); - init_dpo_ctx (hicn_strategy_ctx, next_hop, nh_len, hicn_dpo_type_rr, proto); + init_dpo_ctx (hicn_strategy_ctx, next_hop, nh_len, hicn_dpo_type_rr, + (dpo_proto_t) proto); hicn_strategy_rr_ctx->current_nhop = 0; } +void +hicn_strategy_rr_update_ctx_type (hicn_dpo_ctx_t *hicn_strategy_ctx) +{ + hicn_strategy_rr_ctx_t *hicn_strategy_rr_ctx; + hicn_strategy_rr_ctx = (hicn_strategy_rr_ctx_t *) hicn_strategy_ctx->data; + + hicn_strategy_ctx->dpo_type = hicn_dpo_type_rr; + hicn_strategy_rr_ctx->current_nhop = 0; +} + int hicn_strategy_rr_ctx_add_nh (hicn_face_id_t nh, index_t dpo_idx) { diff --git a/hicn-plugin/src/strategies/dpo_rr.h b/hicn-plugin/src/strategies/dpo_rr.h index e68e2917d..72ec7b5df 100644 --- a/hicn-plugin/src/strategies/dpo_rr.h +++ b/hicn-plugin/src/strategies/dpo_rr.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -74,6 +74,13 @@ void hicn_strategy_rr_ctx_create (fib_protocol_t proto, index_t *dpo_idx); /** + * @brief Update existing ctx setting it to rr + * + * @param hicn_strategy_ctx pointer to the ctx to update + */ +void hicn_strategy_rr_update_ctx_type (hicn_dpo_ctx_t *hicn_strategy_ctx); + +/** * @brief Add or update a next hop in the dpo ctx. * * This function is meant to be used in the control plane and not in the data diff --git a/hicn-plugin/src/strategies/strategy_mw.c b/hicn-plugin/src/strategies/strategy_mw.c index 9409ec856..990e64a5d 100644 --- a/hicn-plugin/src/strategies/strategy_mw.c +++ b/hicn-plugin/src/strategies/strategy_mw.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -25,7 +25,7 @@ void hicn_receive_data_mw (index_t dpo_idx, int nh_idx); void hicn_add_interest_mw (index_t dpo_idx, hicn_hash_entry_t *pit_entry); void hicn_on_interest_timeout_mw (index_t dpo_idx); u32 hicn_select_next_hop_mw (index_t dpo_idx, int *nh_idx, - hicn_face_id_t *outface); + hicn_face_id_t *outfaces, uint32_t *len); u32 get_strategy_node_index_mw (void); u8 *hicn_strategy_format_trace_mw (u8 *s, hicn_strategy_trace_t *t); u8 *hicn_strategy_format_mw (u8 *s, va_list *ap); @@ -51,12 +51,16 @@ hicn_mw_strategy_get_vft (void) /* DPO should be give in input as it containes all the information to calculate * the next hops*/ u32 -hicn_select_next_hop_mw (index_t dpo_idx, int *nh_idx, hicn_face_id_t *outface) +hicn_select_next_hop_mw (index_t dpo_idx, int *nh_idx, + hicn_face_id_t *outfaces, uint32_t *len) { hicn_dpo_ctx_t *dpo_ctx = hicn_strategy_dpo_ctx_get (dpo_idx); if (dpo_ctx == NULL) - return HICN_ERROR_STRATEGY_NOT_FOUND; + { + *len = 0; + return HICN_ERROR_STRATEGY_NOT_FOUND; + } hicn_strategy_mw_ctx_t *hicn_strategy_mw_ctx = (hicn_strategy_mw_ctx_t *) dpo_ctx->data; @@ -71,7 +75,8 @@ hicn_select_next_hop_mw (index_t dpo_idx, int *nh_idx, hicn_face_id_t *outface) } } - *outface = dpo_ctx->next_hops[next_hop_index]; + outfaces[0] = dpo_ctx->next_hops[next_hop_index]; + *len = 1; return HICN_ERROR_NONE; } @@ -84,7 +89,6 @@ hicn_add_interest_mw (index_t dpo_ctx_idx, hicn_hash_entry_t *hash_entry) .dpoi_proto = 0, .dpoi_next_node = 0, .dpoi_index = dpo_ctx_idx }; - hicn_strategy_dpo_ctx_lock (&hicn_dpo_id); hash_entry->vft_id = hicn_dpo_get_vft_id (&hicn_dpo_id); } diff --git a/hicn-plugin/src/strategies/strategy_mw.h b/hicn-plugin/src/strategies/strategy_mw.h index 9e0078b23..186e8c5ab 100644 --- a/hicn-plugin/src/strategies/strategy_mw.h +++ b/hicn-plugin/src/strategies/strategy_mw.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/strategies/strategy_mw_cli.c b/hicn-plugin/src/strategies/strategy_mw_cli.c index 6b56e9fd5..4ace68423 100644 --- a/hicn-plugin/src/strategies/strategy_mw_cli.c +++ b/hicn-plugin/src/strategies/strategy_mw_cli.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -76,7 +76,7 @@ hicn_mw_strategy_cli_set_weight_command_fn (vlib_main_t *vm, } prefix.fp_proto = ip46_address_is_ip4 (&prefix.fp_addr) ? FIB_PROTOCOL_IP4 : - FIB_PROTOCOL_IP6; + FIB_PROTOCOL_IP6; ret = hicn_route_get_dpo (&prefix, &hicn_dpo_id, &fib_index); if (ret == HICN_ERROR_NONE) diff --git a/hicn-plugin/src/strategies/strategy_rp.c b/hicn-plugin/src/strategies/strategy_rp.c new file mode 100644 index 000000000..748cd69b1 --- /dev/null +++ b/hicn-plugin/src/strategies/strategy_rp.c @@ -0,0 +1,118 @@ +/* + * Copyright (c) 2021 Cisco and/or its affiliates. + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at: + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +#include "dpo_rp.h" +#include "../strategy.h" +#include "../strategy_dpo_ctx.h" +#include "../faces/face.h" +#include "../hashtb.h" +#include "../strategy_dpo_manager.h" + +/* Simple strategy that forwards intertests to all next hops */ +/* It does not require to exend the hicn_dpo */ +void hicn_receive_data_rp (index_t dpo_idx, int nh_idx); +void hicn_add_interest_rp (index_t dpo_idx, hicn_hash_entry_t *pit_entry); +void hicn_on_interest_timeout_rp (index_t dpo_idx); +u32 hicn_select_next_hop_rp (index_t dpo_idx, int *nh_idx, + hicn_face_id_t *outfaces, uint32_t *len); +u8 *hicn_strategy_format_trace_rp (u8 *s, hicn_strategy_trace_t *t); +u8 *hicn_strategy_format_rp (u8 *s, va_list *ap); + +static hicn_strategy_vft_t hicn_strategy_rp_vft = { + .hicn_receive_data = &hicn_receive_data_rp, + .hicn_add_interest = &hicn_add_interest_rp, + .hicn_on_interest_timeout = &hicn_on_interest_timeout_rp, + .hicn_select_next_hop = &hicn_select_next_hop_rp, + .hicn_format_strategy_trace = &hicn_strategy_format_trace_rp, + .hicn_format_strategy = &hicn_strategy_format_rp +}; + +/* + * Return the vft of the strategy. + */ +hicn_strategy_vft_t * +hicn_rp_strategy_get_vft (void) +{ + return &hicn_strategy_rp_vft; +} + +/* DPO should be give in input as it containes all the information to calculate + * the next hops*/ +u32 +hicn_select_next_hop_rp (index_t dpo_idx, int *nh_idx, + hicn_face_id_t *outfaces, uint32_t *len) +{ + hicn_dpo_ctx_t *dpo_ctx = hicn_strategy_dpo_ctx_get (dpo_idx); + + if (dpo_ctx == NULL || dpo_ctx->entry_count == 0) + { + *len = 0; + return HICN_ERROR_STRATEGY_NOT_FOUND; + } + + int i = 0; + while (i < MAX_OUT_FACES && i < dpo_ctx->entry_count) + { + outfaces[i] = dpo_ctx->next_hops[i]; + i++; + } + *len = i; + + return HICN_ERROR_NONE; +} + +void +hicn_add_interest_rp (index_t dpo_ctx_idx, hicn_hash_entry_t *hash_entry) +{ + /* Nothing to do */ +} + +void +hicn_on_interest_timeout_rp (index_t dpo_idx) +{ + /* Nothing to do in the rp strategy when we receive an interest */ +} + +void +hicn_receive_data_rp (index_t dpo_idx, int nh_idx) +{ + /* nothing to do */ +} + +/* packet trace format function */ +u8 * +hicn_strategy_format_trace_rp (u8 *s, hicn_strategy_trace_t *t) +{ + s = format (s, "Strategy_rp: pkt: %d, sw_if_index %d, next index %d", + (int) t->pkt_type, t->sw_if_index, t->next_index); + return (s); +} + +u8 * +hicn_strategy_format_rp (u8 *s, va_list *ap) +{ + + u32 indent = va_arg (*ap, u32); + s = format (s, "Replication: send to all the next hops \n", indent); + return (s); +} + +/* + * fd.io coding-style-patch-verification: ON + * + * Local Variables: + * eval: (c-set-style "gnu") + * End: + */ diff --git a/hicn-plugin/src/hicn_api.h b/hicn-plugin/src/strategies/strategy_rp.h index e32b785b6..c308497cc 100644 --- a/hicn-plugin/src/hicn_api.h +++ b/hicn-plugin/src/strategies/strategy_rp.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -13,25 +13,29 @@ * limitations under the License. */ -#ifndef __HICN_API_H__ -#define __HICN_API_H__ +#ifndef __HICN_STRATEGY_RP_H__ +#define __HICN_STRATEGY_RP_H__ + +#include "../strategy.h" /** - * @file + * @file strategy_rp.h + * + * This file implements the replication strategy. In this + * strategy all the next hops are used to send an intertest. */ -#define HICN_STRATEGY_NULL ~0 -#define HICN_FIB_TABLE 10 - -/* define message structures */ -#define vl_typedefs -#include <hicn/hicn_all_api_h.h> -#undef vl_typedefs +/** + * @brief Return the vft for the Replication strategy + */ +hicn_strategy_vft_t *hicn_rp_strategy_get_vft (void); -#endif /* // __HICN_API_H___ */ +#endif // __HICN_STRATEGY_RP_H__ /* * fd.io coding-style-patch-verification: ON * - * Local Variables: eval: (c-set-style "gnu") End: + * Local Variables: + * eval: (c-set-style "gnu") + * End: */ diff --git a/hicn-plugin/src/strategies/strategy_rr.c b/hicn-plugin/src/strategies/strategy_rr.c index 9995191b7..192cf5fc3 100644 --- a/hicn-plugin/src/strategies/strategy_rr.c +++ b/hicn-plugin/src/strategies/strategy_rr.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -26,7 +26,7 @@ void hicn_receive_data_rr (index_t dpo_idx, int nh_idx); void hicn_add_interest_rr (index_t dpo_idx, hicn_hash_entry_t *pit_entry); void hicn_on_interest_timeout_rr (index_t dpo_idx); u32 hicn_select_next_hop_rr (index_t dpo_idx, int *nh_idx, - hicn_face_id_t *outface); + hicn_face_id_t *outfaces, uint32_t *len); u8 *hicn_strategy_format_trace_rr (u8 *s, hicn_strategy_trace_t *t); u8 *hicn_strategy_format_rr (u8 *s, va_list *ap); @@ -51,17 +51,22 @@ hicn_rr_strategy_get_vft (void) /* DPO should be give in input as it containes all the information to calculate * the next hops*/ u32 -hicn_select_next_hop_rr (index_t dpo_idx, int *nh_idx, hicn_face_id_t *outface) +hicn_select_next_hop_rr (index_t dpo_idx, int *nh_idx, + hicn_face_id_t *outfaces, uint32_t *len) { hicn_dpo_ctx_t *dpo_ctx = hicn_strategy_dpo_ctx_get (dpo_idx); if (dpo_ctx == NULL) - return HICN_ERROR_STRATEGY_NOT_FOUND; + { + *len = 0; + return HICN_ERROR_STRATEGY_NOT_FOUND; + } hicn_strategy_rr_ctx_t *hicn_strategy_rr_ctx = (hicn_strategy_rr_ctx_t *) dpo_ctx->data; - *outface = dpo_ctx->next_hops[hicn_strategy_rr_ctx->current_nhop]; + outfaces[0] = dpo_ctx->next_hops[hicn_strategy_rr_ctx->current_nhop]; + *len = 1; hicn_strategy_rr_ctx->current_nhop = (hicn_strategy_rr_ctx->current_nhop + 1) % dpo_ctx->entry_count; @@ -77,7 +82,6 @@ hicn_add_interest_rr (index_t dpo_ctx_idx, hicn_hash_entry_t *hash_entry) .dpoi_proto = 0, .dpoi_next_node = 0, .dpoi_index = dpo_ctx_idx }; - hicn_strategy_dpo_ctx_lock (&hicn_dpo_id); hash_entry->vft_id = hicn_dpo_get_vft_id (&hicn_dpo_id); } diff --git a/hicn-plugin/src/strategies/strategy_rr.h b/hicn-plugin/src/strategies/strategy_rr.h index 4dfe76b43..fb7520180 100644 --- a/hicn-plugin/src/strategies/strategy_rr.h +++ b/hicn-plugin/src/strategies/strategy_rr.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/strategy.h b/hicn-plugin/src/strategy.h index 28af55f01..efc6e464e 100644 --- a/hicn-plugin/src/strategy.h +++ b/hicn-plugin/src/strategy.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -53,7 +53,7 @@ typedef struct hicn_strategy_vft_s void (*hicn_on_interest_timeout) (index_t dpo_idx); void (*hicn_add_interest) (index_t dpo_idx, hicn_hash_entry_t *pit_entry); u32 (*hicn_select_next_hop) (index_t dpo_idx, int *nh_idx, - hicn_face_id_t *outface); + hicn_face_id_t *outfaces, uint32_t *len); u8 *(*hicn_format_strategy_trace) (u8 *, hicn_strategy_trace_t *); u8 *(*hicn_format_strategy) (u8 *s, va_list *ap); /**< Format an hICN dpo*/ @@ -86,6 +86,8 @@ const static char *const *const hicn_nodes_strategy[DPO_PROTO_NUM] = { [DPO_PROTO_IP4] = hicn_ip4_nodes, }; +const static uint32_t MAX_OUT_FACES = 8; + extern vlib_node_registration_t hicn_strategy_node; #endif /* //__HICN_STRATEGY__ */ diff --git a/hicn-plugin/src/strategy_dpo_ctx.c b/hicn-plugin/src/strategy_dpo_ctx.c index edfe75aa8..2279ecc75 100644 --- a/hicn-plugin/src/strategy_dpo_ctx.c +++ b/hicn-plugin/src/strategy_dpo_ctx.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -21,7 +21,7 @@ hicn_dpo_ctx_t *hicn_strategy_dpo_ctx_pool; void hicn_strategy_init_dpo_ctx_pool () { - pool_init_fixed (hicn_strategy_dpo_ctx_pool, 256); + // pool_init_fixed (hicn_strategy_dpo_ctx_pool, 256); } void @@ -29,9 +29,16 @@ hicn_strategy_dpo_ctx_lock (dpo_id_t *dpo) { hicn_dpo_ctx_t *dpo_ctx = hicn_strategy_dpo_ctx_get (dpo->dpoi_index); - if (dpo_ctx != NULL) + if (PREDICT_TRUE (dpo_ctx != NULL)) { dpo_ctx->locks++; + HICN_DEBUG ("Locking DPO CTX with index %d. Lock now: %d", + dpo->dpoi_index, dpo_ctx->locks); + } + else + { + HICN_ERROR ("Trying to lock NULL spo_ctx with index %d", + dpo->dpoi_index); } } @@ -41,15 +48,23 @@ hicn_strategy_dpo_ctx_unlock (dpo_id_t *dpo) hicn_dpo_ctx_t *hicn_strategy_dpo_ctx = (hicn_dpo_ctx_t *) hicn_strategy_dpo_ctx_get (dpo->dpoi_index); - if (hicn_strategy_dpo_ctx != NULL) + if (PREDICT_TRUE (hicn_strategy_dpo_ctx != NULL)) { hicn_strategy_dpo_ctx->locks--; + HICN_DEBUG ("Unlcking DPO CTX with index %d. Lock now: %d", + dpo->dpoi_index, hicn_strategy_dpo_ctx->locks); if (0 == hicn_strategy_dpo_ctx->locks) { + HICN_DEBUG ("Releasing DPO CTX %d", dpo->dpoi_index); pool_put (hicn_strategy_dpo_ctx_pool, hicn_strategy_dpo_ctx); } } + else + { + HICN_ERROR ("Trying to unlock NULL spo_ctx with index %d", + dpo->dpoi_index); + } } u8 * @@ -90,8 +105,11 @@ hicn_strategy_dpo_ctx_get (index_t index) hicn_dpo_ctx_t * hicn_strategy_dpo_ctx_alloc () { + HICN_DEBUG ("Allocating new DPO CTX"); hicn_dpo_ctx_t *dpo_ctx; - pool_get (hicn_strategy_dpo_ctx_pool, dpo_ctx); + pool_get_aligned (hicn_strategy_dpo_ctx_pool, dpo_ctx, + 2 * CLIB_CACHE_LINE_BYTES); + dpo_ctx->locks = 0; return dpo_ctx; } diff --git a/hicn-plugin/src/strategy_dpo_ctx.h b/hicn-plugin/src/strategy_dpo_ctx.h index fe63a4258..cb8ca4051 100644 --- a/hicn-plugin/src/strategy_dpo_ctx.h +++ b/hicn-plugin/src/strategy_dpo_ctx.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -108,7 +108,7 @@ init_dpo_ctx (hicn_dpo_ctx_t *dpo_ctx, const hicn_face_id_t *next_hop, dpo_ctx->seq = INIT_SEQ; dpo_ctx->dpo_type = dpo_type; - dpo_ctx->proto = proto; + dpo_ctx->proto = (fib_protocol_t) proto; for (int i = 0; i < HICN_PARAM_FIB_ENTRY_NHOPS_MAX && i < nh_len; i++) { diff --git a/hicn-plugin/src/strategy_dpo_manager.c b/hicn-plugin/src/strategy_dpo_manager.c index 3c441ccac..6c5767bc9 100644 --- a/hicn-plugin/src/strategy_dpo_manager.c +++ b/hicn-plugin/src/strategy_dpo_manager.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -19,6 +19,7 @@ #include "strategy_dpo_ctx.h" #include "strategies/dpo_mw.h" #include "strategies/dpo_rr.h" +#include "strategies/dpo_rp.h" #include "strategy.h" #include "faces/face.h" @@ -98,11 +99,13 @@ hicn_dpos_init (void) hicn_strategy_init_dpo_ctx_pool (); hicn_dpo_strategy_mw_module_init (); hicn_dpo_strategy_rr_module_init (); + hicn_dpo_strategy_rp_module_init (); default_dpo.hicn_dpo_is_type = &hicn_dpo_is_type_strategy_mw; default_dpo.hicn_dpo_get_type = &hicn_dpo_strategy_mw_get_type; default_dpo.hicn_dpo_module_init = &hicn_dpo_strategy_mw_module_init; default_dpo.hicn_dpo_create = &hicn_strategy_mw_ctx_create; + default_dpo.hicn_dpo_update_type = &hicn_strategy_mw_update_ctx_type; default_dpo.hicn_dpo_add_update_nh = &hicn_strategy_mw_ctx_add_nh; default_dpo.hicn_dpo_del_nh = &hicn_strategy_mw_ctx_del_nh; default_dpo.hicn_dpo_format = &hicn_strategy_mw_format_ctx; @@ -128,12 +131,12 @@ format_hicn_strategy_list (u8 *s, int n, ...) return (s); } -u8 +int hicn_dpo_strategy_id_is_valid (int strategy_id) { return vec_len (strategies_id) > strategy_id ? - HICN_ERROR_NONE : - HICN_ERROR_DPO_MGR_ID_NOT_VALID; + HICN_ERROR_NONE : + HICN_ERROR_DPO_MGR_ID_NOT_VALID; } int diff --git a/hicn-plugin/src/strategy_dpo_manager.h b/hicn-plugin/src/strategy_dpo_manager.h index 7a2ce3fee..b8a0c9e92 100644 --- a/hicn-plugin/src/strategy_dpo_manager.h +++ b/hicn-plugin/src/strategy_dpo_manager.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -53,6 +53,8 @@ typedef struct hicn_dpo_vft_s void (*hicn_dpo_create) ( fib_protocol_t proto, const hicn_face_id_t *nh, int nh_len, index_t *dpo_idx); /**< Create the context of the hICN dpo */ + void (*hicn_dpo_update_type) ( + hicn_dpo_ctx_t *hicn_strategy_ctx); /**change dpo type */ int (*hicn_dpo_add_update_nh) ( hicn_face_id_t nh, index_t dpo_idx); /**< Add a next hop to the hICN dpo context */ @@ -171,7 +173,7 @@ u8 *format_hicn_strategy_list (u8 *s, int n, ...); * * @result HICN_ERROR_NONE is the id is valid, otherwise EINVAL */ -u8 hicn_dpo_strategy_id_is_valid (int strategy_id); +int hicn_dpo_strategy_id_is_valid (int strategy_id); /** * @brief Return the number of available strategies. This number can be used to diff --git a/hicn-plugin/src/strategy_node.c b/hicn-plugin/src/strategy_node.c index ec57d76e2..66d9c2dbb 100644 --- a/hicn-plugin/src/strategy_node.c +++ b/hicn-plugin/src/strategy_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -25,6 +25,7 @@ #include "mgmt.h" #include "pcs.h" #include "state.h" +#include "data_fwd.h" #include "strategies/strategy_mw.h" /* Registration struct for a graph node */ @@ -65,7 +66,8 @@ hicn_new_interest (hicn_strategy_runtime_t *rt, vlib_buffer_t *b0, u32 *next, f64 tnow, u8 *nameptr, u16 namelen, hicn_face_id_t outface, int nh_idx, index_t dpo_ctx_id0, const hicn_strategy_vft_t *strategy, dpo_type_t dpo_type, - u8 isv6, vl_api_hicn_api_node_stats_get_reply_t *stats) + u8 isv6, vl_api_hicn_api_node_stats_get_reply_t *stats, + u8 is_replication) { int ret; hicn_hash_node_t *nodep; @@ -80,6 +82,17 @@ hicn_new_interest (hicn_strategy_runtime_t *rt, vlib_buffer_t *b0, u32 *next, u8 bucket_is_overflow = 0; u32 bucket_id = ~0; + if (is_replication) + { + // an entry for this message alredy exists in the PIT so just send it + *next = isv6 ? HICN_STRATEGY_NEXT_INTEREST_FACE6 : + HICN_STRATEGY_NEXT_INTEREST_FACE4; + + vnet_buffer (b0)->ip.adj_index[VLIB_TX] = outface; + stats->pkts_interest_count++; + return HICN_ERROR_NONE; + } + /* Create PIT node and init PIT entry */ nodep = hicn_hashtb_alloc_node (rt->pitcs->pcs_table); if (PREDICT_FALSE (nodep == NULL)) @@ -101,6 +114,7 @@ hicn_new_interest (hicn_strategy_runtime_t *rt, vlib_buffer_t *b0, u32 *next, { imsg_lifetime = sm->pit_lifetime_max_ms; } + pitp->shared.expire_time = hicn_pcs_get_exp_time (tnow, imsg_lifetime); /* Set up the hash node and insert it */ @@ -121,7 +135,7 @@ hicn_new_interest (hicn_strategy_runtime_t *rt, vlib_buffer_t *b0, u32 *next, hicn_face_db_add_face (hicnb0->face_id, &(pitp->u.pit.faces)); *next = isv6 ? HICN_STRATEGY_NEXT_INTEREST_FACE6 : - HICN_STRATEGY_NEXT_INTEREST_FACE4; + HICN_STRATEGY_NEXT_INTEREST_FACE4; vnet_buffer (b0)->ip.adj_index[VLIB_TX] = outface; stats->pkts_interest_count++; @@ -137,9 +151,15 @@ hicn_new_interest (hicn_strategy_runtime_t *rt, vlib_buffer_t *b0, u32 *next, bucket_id, bucket_is_overflow); // We need to take a lock as the lock is not taken on the hash // entry because it is a CS entry (hash_insert function). - hash_entry->locks++; - *next = is_cs0 ? HICN_STRATEGY_NEXT_INTEREST_HITCS : - HICN_STRATEGY_NEXT_INTEREST_HITPIT; + if (is_cs0) + { + hash_entry->locks++; + *next = HICN_STRATEGY_NEXT_INTEREST_HITCS; + } + else + { + *next = HICN_STRATEGY_NEXT_INTEREST_HITPIT; + } } else { @@ -189,7 +209,8 @@ hicn_strategy_fn (vlib_main_t *vm, vlib_node_runtime_t *node, hicn_header_t *hicn0; vlib_buffer_t *b0; u32 bi0; - hicn_face_id_t outface; + hicn_face_id_t outfaces[MAX_OUT_FACES]; + u32 outfaces_len; int nh_idx; u32 next0 = next_index; int ret; @@ -207,15 +228,23 @@ hicn_strategy_fn (vlib_main_t *vm, vlib_node_runtime_t *node, bi0 = from[0]; from += 1; n_left_from -= 1; - to_next[0] = bi0; - to_next += 1; - n_left_to_next -= 1; b0 = vlib_get_buffer (vm, bi0); next0 = HICN_STRATEGY_NEXT_ERROR_DROP; hicn_dpo_ctx_t *dpo_ctx = hicn_strategy_dpo_ctx_get ( vnet_buffer (b0)->ip.adj_index[VLIB_TX]); + + if (PREDICT_FALSE (!dpo_ctx)) + { + to_next[0] = bi0; + to_next += 1; + n_left_to_next -= 1; + vlib_validate_buffer_enqueue_x1 (vm, node, next_index, to_next, + n_left_to_next, bi0, next0); + continue; + } + const hicn_strategy_vft_t *strategy = hicn_dpo_get_strategy_vft (dpo_ctx->dpo_type); @@ -231,7 +260,7 @@ hicn_strategy_fn (vlib_main_t *vm, vlib_node_runtime_t *node, HICN_IS_NAMEHASH_CACHED (b0) && strategy->hicn_select_next_hop ( vnet_buffer (b0)->ip.adj_index[VLIB_TX], &nh_idx, - &outface) == HICN_ERROR_NONE)) + outfaces, &outfaces_len) == HICN_ERROR_NONE)) { /* * No need to check if parsing was successful @@ -239,32 +268,72 @@ hicn_strategy_fn (vlib_main_t *vm, vlib_node_runtime_t *node, * node */ nameptr = (u8 *) (&name); - hicn_new_interest (rt, b0, &next0, tnow, nameptr, namelen, - outface, nh_idx, - vnet_buffer (b0)->ip.adj_index[VLIB_TX], - strategy, dpo_ctx->dpo_type, isv6, &stats); + u32 clones[outfaces_len]; + if (outfaces_len > 1) + { + int ret = vlib_buffer_clone (vm, bi0, clones, outfaces_len, + CLIB_CACHE_LINE_BYTES * 2); + ASSERT (ret == outfaces_len); + } + else + { + clones[0] = bi0; + } + + for (u32 nh = 0; nh < outfaces_len; nh++) + { + vlib_buffer_t *local_b0 = vlib_get_buffer (vm, clones[nh]); + + to_next[0] = clones[nh]; + to_next += 1; + n_left_to_next -= 1; + + if (nh == 0) + { + // send first interest + hicn_new_interest ( + rt, local_b0, &next0, tnow, nameptr, namelen, + outfaces[nh], nh_idx, + vnet_buffer (local_b0)->ip.adj_index[VLIB_TX], + strategy, dpo_ctx->dpo_type, isv6, &stats, 0); + } + else + { + // send duplicated interests, avoid aggregation/drop + hicn_new_interest ( + rt, local_b0, &next0, tnow, nameptr, namelen, + outfaces[nh], nh_idx, + vnet_buffer (local_b0)->ip.adj_index[VLIB_TX], + strategy, dpo_ctx->dpo_type, isv6, &stats, 1); + } + + /* Maybe trace */ + if (PREDICT_FALSE ( + (node->flags & VLIB_NODE_FLAG_TRACE) && + (local_b0->flags & VLIB_BUFFER_IS_TRACED))) + { + hicn_strategy_trace_t *t = + vlib_add_trace (vm, node, local_b0, sizeof (*t)); + t->pkt_type = HICN_PKT_TYPE_CONTENT; + t->sw_if_index = + vnet_buffer (local_b0)->sw_if_index[VLIB_RX]; + t->next_index = next0; + t->dpo_type = dpo_ctx->dpo_type; + } + + /* + * Verify speculative enqueue, maybe switch current + * next frame + */ + /* + * Fix in case of a wrong speculation. Needed for + * cloning the data in the right frame + */ + vlib_validate_buffer_enqueue_x1 (vm, node, next_index, + to_next, n_left_to_next, + clones[nh], next0); + } } - /* Maybe trace */ - if (PREDICT_FALSE ((node->flags & VLIB_NODE_FLAG_TRACE) && - (b0->flags & VLIB_BUFFER_IS_TRACED))) - { - hicn_strategy_trace_t *t = - vlib_add_trace (vm, node, b0, sizeof (*t)); - t->pkt_type = HICN_PKT_TYPE_CONTENT; - t->sw_if_index = vnet_buffer (b0)->sw_if_index[VLIB_RX]; - t->next_index = next0; - t->dpo_type = dpo_ctx->dpo_type; - } - /* - * Verify speculative enqueue, maybe switch current - * next frame - */ - /* - * Fix in case of a wrong speculation. Needed for - * cloning the data in the right frame - */ - vlib_validate_buffer_enqueue_x1 (vm, node, next_index, to_next, - n_left_to_next, bi0, next0); } vlib_put_next_frame (vm, node, next_index, n_left_to_next); diff --git a/hicn-plugin/src/udp_tunnels/udp_decap.h b/hicn-plugin/src/udp_tunnels/udp_decap.h index 9ddb8a73b..7dc13f272 100644 --- a/hicn-plugin/src/udp_tunnels/udp_decap.h +++ b/hicn-plugin/src/udp_tunnels/udp_decap.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: diff --git a/hicn-plugin/src/udp_tunnels/udp_decap_node.c b/hicn-plugin/src/udp_tunnels/udp_decap_node.c index 06eb8da71..2ac1b1ecb 100644 --- a/hicn-plugin/src/udp_tunnels/udp_decap_node.c +++ b/hicn-plugin/src/udp_tunnels/udp_decap_node.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -223,7 +223,7 @@ udp4_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, &((ip4_header_t *) outer_ptr0)->dst_address); udp0 = (udp_header_t *) (outer_ptr0 + sizeof (ip4_header_t)); next0 = v0 == 0x40 ? UDP4_DECAP_NEXT_LOOKUP_IP4 : - UDP4_DECAP_NEXT_LOOKUP_IP6; + UDP4_DECAP_NEXT_LOOKUP_IP6; ip46_address_set_ip4 (&src1, &((ip4_header_t *) outer_ptr1)->src_address); @@ -231,7 +231,7 @@ udp4_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, &((ip4_header_t *) outer_ptr1)->dst_address); udp1 = (udp_header_t *) (outer_ptr1 + sizeof (ip4_header_t)); next1 = v1 == 0x40 ? UDP4_DECAP_NEXT_LOOKUP_IP4 : - UDP4_DECAP_NEXT_LOOKUP_IP6; + UDP4_DECAP_NEXT_LOOKUP_IP6; ip46_address_set_ip4 (&src2, &((ip4_header_t *) outer_ptr2)->src_address); @@ -239,7 +239,7 @@ udp4_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, &((ip4_header_t *) outer_ptr2)->dst_address); udp2 = (udp_header_t *) (outer_ptr2 + sizeof (ip4_header_t)); next2 = v2 == 0x40 ? UDP4_DECAP_NEXT_LOOKUP_IP4 : - UDP4_DECAP_NEXT_LOOKUP_IP6; + UDP4_DECAP_NEXT_LOOKUP_IP6; ip46_address_set_ip4 (&src3, &((ip4_header_t *) outer_ptr3)->src_address); @@ -247,7 +247,7 @@ udp4_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, &((ip4_header_t *) outer_ptr3)->dst_address); udp3 = (udp_header_t *) (outer_ptr3 + sizeof (ip4_header_t)); next3 = v3 == 0x40 ? UDP4_DECAP_NEXT_LOOKUP_IP4 : - UDP4_DECAP_NEXT_LOOKUP_IP6; + UDP4_DECAP_NEXT_LOOKUP_IP6; hicn_buffer_t *hicnb0, *hicnb1, *hicnb2, *hicnb3; hicnb0 = hicn_get_buffer (b0); @@ -257,34 +257,39 @@ udp4_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, /* Udp encap-decap tunnels have dst and src addresses and port * swapped */ - vnet_buffer (b0)->ip.adj_index[VLIB_RX] = - udp_tunnel_get (&dst0, &src0, udp0->dst_port, udp0->src_port); - vnet_buffer (b1)->ip.adj_index[VLIB_RX] = - udp_tunnel_get (&dst1, &src1, udp1->dst_port, udp1->src_port); - vnet_buffer (b2)->ip.adj_index[VLIB_RX] = - udp_tunnel_get (&dst2, &src2, udp2->dst_port, udp2->src_port); - vnet_buffer (b3)->ip.adj_index[VLIB_RX] = - udp_tunnel_get (&dst3, &src3, udp3->dst_port, udp3->src_port); - - if (vnet_buffer (b0)->ip.adj_index[VLIB_RX] != UDP_TUNNEL_INVALID) - hicnb0->flags |= - (outer_v0 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : - HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); - - if (vnet_buffer (b1)->ip.adj_index[VLIB_RX] != UDP_TUNNEL_INVALID) - hicnb1->flags |= - (outer_v1 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : - HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); - - if (vnet_buffer (b2)->ip.adj_index[VLIB_RX] != UDP_TUNNEL_INVALID) - hicnb2->flags |= - (outer_v2 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : - HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); - - if (vnet_buffer (b3)->ip.adj_index[VLIB_RX] != UDP_TUNNEL_INVALID) - hicnb3->flags |= - (outer_v3 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : - HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); + vnet_buffer (b0)->ip.adj_index[VLIB_RX] = udp_tunnel_get_create ( + &dst0, &src0, udp0->dst_port, udp0->src_port); + vnet_buffer (b1)->ip.adj_index[VLIB_RX] = udp_tunnel_get_create ( + &dst1, &src1, udp1->dst_port, udp1->src_port); + vnet_buffer (b2)->ip.adj_index[VLIB_RX] = udp_tunnel_get_create ( + &dst2, &src2, udp2->dst_port, udp2->src_port); + vnet_buffer (b3)->ip.adj_index[VLIB_RX] = udp_tunnel_get_create ( + &dst3, &src3, udp3->dst_port, udp3->src_port); + + ASSERT (vnet_buffer (b0)->ip.adj_index[VLIB_RX] != + UDP_TUNNEL_INVALID); + ASSERT (vnet_buffer (b1)->ip.adj_index[VLIB_RX] != + UDP_TUNNEL_INVALID); + ASSERT (vnet_buffer (b2)->ip.adj_index[VLIB_RX] != + UDP_TUNNEL_INVALID); + ASSERT (vnet_buffer (b3)->ip.adj_index[VLIB_RX] != + UDP_TUNNEL_INVALID); + + hicnb0->flags = + (outer_v0 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : + HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); + + hicnb1->flags = + (outer_v1 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : + HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); + + hicnb2->flags = + (outer_v2 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : + HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); + + hicnb3->flags = + (outer_v3 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : + HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); udp_decap_trace_buffer (vm, node, 1, b0); udp_decap_trace_buffer (vm, node, 1, b1); @@ -346,17 +351,19 @@ udp4_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, &((ip4_header_t *) outer_ptr0)->dst_address); udp0 = (udp_header_t *) (outer_ptr0 + sizeof (ip4_header_t)); next0 = v0 == 0x40 ? UDP4_DECAP_NEXT_LOOKUP_IP4 : - UDP4_DECAP_NEXT_LOOKUP_IP6; + UDP4_DECAP_NEXT_LOOKUP_IP6; hicn_buffer_t *hicnb0 = hicn_get_buffer (b0); - vnet_buffer (b0)->ip.adj_index[VLIB_RX] = - udp_tunnel_get (&dst0, &src0, udp0->dst_port, udp0->src_port); + vnet_buffer (b0)->ip.adj_index[VLIB_RX] = udp_tunnel_get_create ( + &dst0, &src0, udp0->dst_port, udp0->src_port); - if (vnet_buffer (b0)->ip.adj_index[VLIB_RX] != UDP_TUNNEL_INVALID) - hicnb0->flags |= - (outer_v0 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : - HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); + ASSERT (vnet_buffer (b0)->ip.adj_index[VLIB_RX] != + UDP_TUNNEL_INVALID); + + hicnb0->flags |= + (outer_v0 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : + HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); udp_decap_trace_buffer (vm, node, 1, b0); @@ -488,7 +495,7 @@ udp6_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, &((ip6_header_t *) outer_ptr0)->dst_address); udp0 = (udp_header_t *) (outer_ptr0 + sizeof (ip6_header_t)); next0 = v0 == 0x40 ? UDP6_DECAP_NEXT_LOOKUP_IP4 : - UDP6_DECAP_NEXT_LOOKUP_IP6; + UDP6_DECAP_NEXT_LOOKUP_IP6; ip46_address_set_ip6 (&src1, &((ip6_header_t *) outer_ptr1)->src_address); @@ -496,7 +503,7 @@ udp6_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, &((ip6_header_t *) outer_ptr1)->dst_address); udp1 = (udp_header_t *) (outer_ptr1 + sizeof (ip6_header_t)); next1 = v1 == 0x40 ? UDP6_DECAP_NEXT_LOOKUP_IP4 : - UDP6_DECAP_NEXT_LOOKUP_IP6; + UDP6_DECAP_NEXT_LOOKUP_IP6; ip46_address_set_ip6 (&src2, &((ip6_header_t *) outer_ptr2)->src_address); @@ -504,7 +511,7 @@ udp6_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, &((ip6_header_t *) outer_ptr2)->dst_address); udp2 = (udp_header_t *) (outer_ptr2 + sizeof (ip6_header_t)); next2 = v2 == 0x40 ? UDP6_DECAP_NEXT_LOOKUP_IP4 : - UDP6_DECAP_NEXT_LOOKUP_IP6; + UDP6_DECAP_NEXT_LOOKUP_IP6; ip46_address_set_ip6 (&src3, &((ip6_header_t *) outer_ptr3)->src_address); @@ -512,7 +519,7 @@ udp6_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, &((ip6_header_t *) outer_ptr3)->dst_address); udp3 = (udp_header_t *) (outer_ptr3 + sizeof (ip6_header_t)); next3 = v3 == 0x40 ? UDP6_DECAP_NEXT_LOOKUP_IP4 : - UDP6_DECAP_NEXT_LOOKUP_IP6; + UDP6_DECAP_NEXT_LOOKUP_IP6; hicn_buffer_t *hicnb0, *hicnb1, *hicnb2, *hicnb3; hicnb0 = hicn_get_buffer (b0); @@ -534,22 +541,22 @@ udp6_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, if (vnet_buffer (b0)->ip.adj_index[VLIB_RX] != UDP_TUNNEL_INVALID) hicnb0->flags |= (outer_v0 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : - HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); + HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); if (vnet_buffer (b1)->ip.adj_index[VLIB_RX] != UDP_TUNNEL_INVALID) hicnb1->flags |= (outer_v1 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : - HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); + HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); if (vnet_buffer (b2)->ip.adj_index[VLIB_RX] != UDP_TUNNEL_INVALID) hicnb2->flags |= (outer_v2 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : - HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); + HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); if (vnet_buffer (b3)->ip.adj_index[VLIB_RX] != UDP_TUNNEL_INVALID) hicnb3->flags |= (outer_v3 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : - HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); + HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); udp_decap_trace_buffer (vm, node, 0, b0); udp_decap_trace_buffer (vm, node, 0, b1); @@ -610,7 +617,7 @@ udp6_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, &((ip6_header_t *) outer_ptr0)->dst_address); udp0 = (udp_header_t *) (outer_ptr0 + sizeof (ip6_header_t)); next0 = v0 == 0x40 ? UDP6_DECAP_NEXT_LOOKUP_IP4 : - UDP6_DECAP_NEXT_LOOKUP_IP6; + UDP6_DECAP_NEXT_LOOKUP_IP6; hicn_buffer_t *hicnb0 = hicn_get_buffer (b0); @@ -620,7 +627,7 @@ udp6_decap_node_fn (vlib_main_t *vm, vlib_node_runtime_t *node, if (vnet_buffer (b0)->ip.adj_index[VLIB_RX] != UDP_TUNNEL_INVALID) hicnb0->flags |= (outer_v0 == 0x40 ? HICN_BUFFER_FLAGS_FROM_UDP4_TUNNEL : - HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); + HICN_BUFFER_FLAGS_FROM_UDP6_TUNNEL); udp_decap_trace_buffer (vm, node, 0, b0); diff --git a/hicn-plugin/src/udp_tunnels/udp_tunnel.c b/hicn-plugin/src/udp_tunnels/udp_tunnel.c index 8ea2cb503..d03d6a74e 100644 --- a/hicn-plugin/src/udp_tunnels/udp_tunnel.c +++ b/hicn-plugin/src/udp_tunnels/udp_tunnel.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020-2021 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -156,6 +156,27 @@ udp_tunnel_get (const ip46_address_t *src_ip, const ip46_address_t *dst_ip, return ret == 0 ? (u32) value.value : UDP_TUNNEL_INVALID; } +u32 +udp_tunnel_get_create (const ip46_address_t *src_ip, + const ip46_address_t *dst_ip, u16 src_port, + u16 dst_port) +{ + u32 ret = udp_tunnel_get (src_ip, dst_ip, src_port, dst_port); + if (ret == UDP_TUNNEL_INVALID) + { + fib_protocol_t proto = + ip46_address_is_ip4 (src_ip) ? FIB_PROTOCOL_IP4 : FIB_PROTOCOL_IP6; + + index_t fib_index = fib_table_find (proto, HICN_FIB_TABLE); + + ret = udp_tunnel_add ( + proto, fib_index, src_ip, dst_ip, clib_net_to_host_u16 (src_port), + clib_net_to_host_u16 (dst_port), UDP_ENCAP_FIXUP_NONE); + } + + return ret; +} + void udp_tunnel_init () { @@ -255,8 +276,8 @@ udp_tunnel_command_fn (vlib_main_t *vm, unformat_input_t *main_input, int ret = udp_tunnel_del (fproto, fib_index, &src_ip, &dst_ip, src_port, dst_port, UDP_ENCAP_FIXUP_NONE); error = (ret == HICN_ERROR_NONE) ? - 0 : - clib_error_return (0, "%s\n", get_error_string (ret)); + 0 : + clib_error_return (0, "%s\n", get_error_string (ret)); } else { diff --git a/hicn-plugin/src/udp_tunnels/udp_tunnel.h b/hicn-plugin/src/udp_tunnels/udp_tunnel.h index 2e57b7857..376adf5fa 100644 --- a/hicn-plugin/src/udp_tunnels/udp_tunnel.h +++ b/hicn-plugin/src/udp_tunnels/udp_tunnel.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2020 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: @@ -70,6 +70,19 @@ u32 udp_tunnel_get (const ip46_address_t *src_ip, const ip46_address_t *dst_ip, u16 src_port, u16 dst_port); /** + * @brief Get udp tunnel UEI. Creates the tunnel if does not exist already. + * + * @param src_ip source address of the tunnel + * @param dst_ip destination address of the tunnel + * @param src_port source port + * @param src_port destination port + * @return id of the udp tunnel/encap + */ +u32 udp_tunnel_get_create (const ip46_address_t *src_ip, + const ip46_address_t *dst_ip, u16 src_port, + u16 dst_port); + +/** * @brief Delete a udp tunnel * * @param proto FIB_PROTOCOL_IP4 or FIB_PROTOCOL_IP6 diff --git a/hicn-plugin/src/utils.h b/hicn-plugin/src/utils.h index 847f2f388..7a3492732 100644 --- a/hicn-plugin/src/utils.h +++ b/hicn-plugin/src/utils.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2017-2019 Cisco and/or its affiliates. + * Copyright (c) 2021 Cisco and/or its affiliates. * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at: |