Initial commit
This commit is contained in:
270
package/qca/qca-nss-ecm/Makefile
Normal file
270
package/qca/qca-nss-ecm/Makefile
Normal file
@@ -0,0 +1,270 @@
|
||||
include $(TOPDIR)/rules.mk
|
||||
include $(INCLUDE_DIR)/kernel.mk
|
||||
|
||||
PKG_NAME:=qca-nss-ecm
|
||||
PKG_RELEASE:=1
|
||||
|
||||
PKG_SOURCE_URL:=https://source.codeaurora.org/quic/qsdk/oss/lklm/qca-nss-ecm
|
||||
PKG_SOURCE_PROTO:=git
|
||||
PKG_SOURCE_VERSION:=9228212b4238c0d8c296f795948ede8f2ca0242e
|
||||
|
||||
LOCAL_VARIANT=$(patsubst qca-nss-ecm-%,%,$(patsubst qca-nss-ecm-%,%,$(BUILD_VARIANT)))
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
|
||||
ifeq ($(CONFIG_QCA_NSS_ECM_EXAMPLES_PCC),y)
|
||||
FILES_EXAMPLES=$(PKG_BUILD_DIR)/examples/ecm_pcc_test.ko
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_QCA_NSS_ECM_EXAMPLES_MARK),y)
|
||||
FILES_EXAMPLES+=$(PKG_BUILD_DIR)/examples/ecm_mark_test.ko
|
||||
endif
|
||||
|
||||
#Explicitly enable OVS external module, if ovsmgr is enabled.
|
||||
ifneq ($(CONFIG_PACKAGE_kmod-qca-ovsmgr),)
|
||||
CONFIG_QCA_NSS_ECM_OVS=y
|
||||
endif
|
||||
|
||||
ifeq ($(CONFIG_QCA_NSS_ECM_OVS),y)
|
||||
FILES_EXAMPLES+=$(PKG_BUILD_DIR)/examples/ecm_ovs.ko
|
||||
endif
|
||||
|
||||
define KernelPackage/qca-nss-ecm/Default
|
||||
SECTION:=kernel
|
||||
CATEGORY:=Kernel modules
|
||||
SUBMENU:=Network Support
|
||||
DEPENDS:=+TARGET_ipq806x:kmod-qca-nss-drv \
|
||||
+TARGET_ipq_ipq806x:kmod-qca-nss-drv \
|
||||
+TARGET_ipq_ipq807x:kmod-qca-nss-drv \
|
||||
+TARGET_ipq_ipq807x_64:kmod-qca-nss-drv \
|
||||
+TARGET_ipq807x:kmod-qca-nss-drv \
|
||||
+TARGET_ipq807x_64:kmod-qca-nss-drv \
|
||||
+TARGET_ipq_ipq60xx:kmod-qca-nss-drv \
|
||||
+TARGET_ipq_ipq60xx_64:kmod-qca-nss-drv \
|
||||
+TARGET_ipq_ipq50xx:kmod-qca-nss-drv \
|
||||
+TARGET_ipq_ipq50xx_64:kmod-qca-nss-drv \
|
||||
+iptables-mod-extra +kmod-ipt-conntrack \
|
||||
+kmod-pppoe @!LINUX_3_18 \
|
||||
+kmod-ipsec
|
||||
TITLE:=QCA NSS Enhanced Connection Manager (ECM)
|
||||
FILES:=$(PKG_BUILD_DIR)/*.ko $(FILES_EXAMPLES)
|
||||
KCONFIG:=CONFIG_BRIDGE_NETFILTER=y \
|
||||
CONFIG_NF_CONNTRACK_EVENTS=y \
|
||||
CONFIG_NF_CONNTRACK_CHAIN_EVENTS=y \
|
||||
CONFIG_NF_CONNTRACK_DSCPREMARK_EXT=y
|
||||
MENU:=1
|
||||
PROVIDES:=kmod-qca-nss-ecm
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm/Description/Default
|
||||
This package contains the QCA NSS Enhanced Connection Manager
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm/Default/install
|
||||
$(INSTALL_DIR) $(1)/etc/firewall.d $(1)/etc/init.d $(1)/usr/bin $(1)/lib/netifd/offload $(1)/etc/config $(1)/etc/uci-defaults $(1)/etc/sysctl.d
|
||||
$(INSTALL_DATA) ./files/qca-nss-ecm.firewall $(1)/etc/firewall.d/qca-nss-ecm
|
||||
$(INSTALL_BIN) ./files/qca-nss-ecm.init $(1)/etc/init.d/qca-nss-ecm
|
||||
$(INSTALL_BIN) ./files/ecm_dump.sh $(1)/usr/bin/
|
||||
$(INSTALL_BIN) ./files/on-demand-down $(1)/lib/netifd/offload/on-demand-down
|
||||
$(INSTALL_DATA) ./files/qca-nss-ecm.uci $(1)/etc/config/ecm
|
||||
$(INSTALL_DATA) ./files/qca-nss-ecm.defaults $(1)/etc/uci-defaults/99-qca-nss-ecm
|
||||
$(INSTALL_BIN) ./files/qca-nss-ecm.sysctl $(1)/etc/sysctl.d/qca-nss-ecm.conf
|
||||
ifeq ($(CONFIG_KERNEL_IPQ_MEM_PROFILE),256)
|
||||
echo 'net.netfilter.nf_conntrack_max=2048' >> $(1)/etc/sysctl.d/qca-nss-ecm.conf
|
||||
endif
|
||||
ifeq ($(CONFIG_KERNEL_IPQ_MEM_PROFILE),512)
|
||||
echo 'net.netfilter.nf_conntrack_max=8192' >> $(1)/etc/sysctl.d/qca-nss-ecm.conf
|
||||
endif
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-standard
|
||||
$(call KernelPackage/qca-nss-ecm/Default)
|
||||
VARIANT:=standard
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-standard/Description
|
||||
$(call KernelPackage/qca-nss-ecm/Description/Default)
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-standard/install
|
||||
$(call KernelPackage/qca-nss-ecm/Default/install, $(1))
|
||||
endef
|
||||
|
||||
# Variant with additional features enabled for premium profile
|
||||
define KernelPackage/qca-nss-ecm-premium/Default
|
||||
$(call KernelPackage/qca-nss-ecm/Default)
|
||||
TITLE+= (with premium features)
|
||||
VARIANT:=premium
|
||||
DEPENDS+=+kmod-nat46 \
|
||||
+kmod-l2tp +kmod-pppol2tp +kmod-pptp \
|
||||
+kmod-bonding
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-premium/Description/Default
|
||||
$(call KernelPackage/qca-nss-ecm/Description/Default)
|
||||
with the premium features enabled
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-premium/Default/install
|
||||
$(call KernelPackage/qca-nss-ecm/install)
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-premium
|
||||
$(call KernelPackage/qca-nss-ecm-premium/Default)
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-premium/Description
|
||||
$(call KernelPackage/qca-nss-ecm-premium/Description/Default)
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-premium/install
|
||||
$(call KernelPackage/qca-nss-ecm-standard/install, $(1))
|
||||
endef
|
||||
|
||||
# Variant with additional features enabled for noload profile
|
||||
define KernelPackage/qca-nss-ecm-noload
|
||||
$(call KernelPackage/qca-nss-ecm/Default)
|
||||
TITLE+= (with noload features)
|
||||
PROVIDES:=kmod-qca-nss-ecm
|
||||
VARIANT:=noload
|
||||
DEPENDS+=+kmod-l2tp +kmod-pppol2tp +kmod-pptp \
|
||||
+kmod-bonding
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-noload/Description
|
||||
$(call KernelPackage/qca-nss-ecm/Description/Default)
|
||||
When selected, this package installs the driver but does not load it at init.
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-noload/install
|
||||
$(call KernelPackage/qca-nss-ecm/Default/install, $(1))
|
||||
#
|
||||
# Remove the START line from the init script, so that the symlink
|
||||
# in the /etc/rc.d directory is not created.
|
||||
#
|
||||
sed -i '/START=/d' $(1)/etc/init.d/qca-nss-ecm
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-premium-noload
|
||||
$(call KernelPackage/qca-nss-ecm-premium/Default)
|
||||
PROVIDES:=kmod-qca-nss-ecm-premium
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-premium-noload/Description
|
||||
$(call KernelPackage/qca-nss-ecm-premium/Description/Default)
|
||||
When selected, this package installs the driver but does not load it at init.
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-premium-noload/install
|
||||
$(call KernelPackage/qca-nss-ecm-premium/Default/install, $(1))
|
||||
endef
|
||||
|
||||
define Build/InstallDev/qca-nss-ecm
|
||||
$(INSTALL_DIR) $(1)/usr/include/qca-nss-ecm
|
||||
$(CP) $(PKG_BUILD_DIR)/exports/* $(1)/usr/include/qca-nss-ecm/
|
||||
endef
|
||||
|
||||
define Build/InstallDev
|
||||
$(call Build/InstallDev/qca-nss-ecm,$(1))
|
||||
endef
|
||||
|
||||
EXTRA_CFLAGS+= \
|
||||
-I$(STAGING_DIR)/usr/include/hyfibr \
|
||||
-I$(STAGING_DIR)/usr/include/qca-mcs \
|
||||
-I$(STAGING_DIR)/usr/include/qca-nss-drv \
|
||||
-I$(STAGING_DIR)/usr/include/shortcut-fe \
|
||||
-I$(STAGING_DIR)/usr/include/nat46
|
||||
|
||||
ECM_MAKE_OPTS:=ECM_CLASSIFIER_HYFI_ENABLE=y
|
||||
ifneq ($(LOCAL_VARIANT),standard)
|
||||
ECM_MAKE_OPTS+=ECM_MULTICAST_ENABLE=y \
|
||||
ECM_INTERFACE_IPSEC_ENABLE=y \
|
||||
# ECM_INTERFACE_PPTP_ENABLE=y \
|
||||
ECM_INTERFACE_L2TPV2_ENABLE=y \
|
||||
ECM_INTERFACE_GRE_TAP_ENABLE=y \
|
||||
ECM_INTERFACE_GRE_TUN_ENABLE=y \
|
||||
ECM_INTERFACE_SIT_ENABLE=y \
|
||||
ECM_INTERFACE_TUNIPIP6_ENABLE=y \
|
||||
ECM_INTERFACE_RAWIP_ENABLE=y
|
||||
|
||||
ifeq ($(CONFIG_TARGET_ipq_ipq40xx)$(CONFIG_TARGET_ipq40xx),)
|
||||
ECM_MAKE_OPTS+=ECM_INTERFACE_BOND_ENABLE=y
|
||||
endif
|
||||
endif
|
||||
|
||||
ifeq ($(filter $(CONFIG_KERNEL_IPQ_MEM_PROFILE), 256),)
|
||||
ECM_MAKE_OPTS+=ECM_XFRM_ENABLE=y
|
||||
endif
|
||||
|
||||
# ifneq ($(CONFIG_PACKAGE_kmod-nat46),)
|
||||
# ECM_MAKE_OPTS+=ECM_INTERFACE_MAP_T_ENABLE=y
|
||||
# endif
|
||||
|
||||
ifneq ($(CONFIG_PACKAGE_kmod-qca-nss-drv-ovpn-link),)
|
||||
ECM_MAKE_OPTS+=ECM_INTERFACE_OVPN_ENABLE=y
|
||||
endif
|
||||
|
||||
ifneq ($(CONFIG_PACKAGE_kmod-qca-nss-drv-vxlanmgr),)
|
||||
ECM_MAKE_OPTS+=ECM_INTERFACE_VXLAN_ENABLE=y
|
||||
endif
|
||||
|
||||
ifneq ($(CONFIG_PACKAGE_kmod-qca-ovsmgr),)
|
||||
ECM_MAKE_OPTS+=ECM_INTERFACE_OVS_BRIDGE_ENABLE=y \
|
||||
ECM_CLASSIFIER_OVS_ENABLE=y
|
||||
EXTRA_CFLAGS+= -I$(STAGING_DIR)/usr/include/qca-ovsmgr
|
||||
endif
|
||||
|
||||
# Keeping default as ipq806x for branches that does not have subtarget framework
|
||||
ifeq ($(CONFIG_TARGET_ipq),y)
|
||||
subtarget:=$(SUBTARGET)
|
||||
else
|
||||
subtarget:=$(CONFIG_TARGET_BOARD)
|
||||
endif
|
||||
|
||||
define Build/InstallDev
|
||||
$(INSTALL_DIR) $(1)/usr/include/qca-nss-ecm
|
||||
$(CP) $(PKG_BUILD_DIR)/exports/* $(1)/usr/include/qca-nss-ecm
|
||||
endef
|
||||
|
||||
define Build/Compile
|
||||
$(MAKE) $(PKG_JOBS) -C "$(LINUX_DIR)" $(strip $(ECM_MAKE_OPTS)) \
|
||||
$(KERNEL_MAKE_FLAGS) \
|
||||
$(PKG_MAKE_FLAGS) \
|
||||
M="$(PKG_BUILD_DIR)" \
|
||||
EXTRA_CFLAGS="$(EXTRA_CFLAGS)" SoC="$(subtarget)" \
|
||||
EXAMPLES_BUILD_PCC="$(CONFIG_QCA_NSS_ECM_EXAMPLES_PCC)" \
|
||||
EXAMPLES_BUILD_MARK="$(CONFIG_QCA_NSS_ECM_EXAMPLES_MARK)" \
|
||||
EXAMPLES_BUILD_OVS="$(CONFIG_QCA_NSS_ECM_OVS)" \
|
||||
ECM_FRONT_END_SFE_ENABLE="$(CONFIG_QCA_ECM_SFE_SUPPORT)" \
|
||||
modules
|
||||
endef
|
||||
|
||||
define KernelPackage/qca-nss-ecm-premium/config
|
||||
menu "ECM Configuration"
|
||||
config QCA_NSS_ECM_EXAMPLES_PCC
|
||||
bool "Build PCC usage example"
|
||||
help
|
||||
Selecting this will build the PCC classifier usage example module.
|
||||
default n
|
||||
|
||||
config QCA_NSS_ECM_EXAMPLES_MARK
|
||||
bool "Build Mark classifier usage example"
|
||||
help
|
||||
Selecting this will build the Mark classifier usage example module.
|
||||
default n
|
||||
|
||||
config QCA_NSS_ECM_OVS
|
||||
bool "Build OVS classifier external module"
|
||||
help
|
||||
Selecting this will build the OVS classifier external module.
|
||||
default n
|
||||
|
||||
config QCA_ECM_SFE_SUPPORT
|
||||
bool "Add SFE support to ECM driver"
|
||||
default n
|
||||
endmenu
|
||||
endef
|
||||
|
||||
$(eval $(call KernelPackage,qca-nss-ecm-noload))
|
||||
$(eval $(call KernelPackage,qca-nss-ecm-standard))
|
||||
$(eval $(call KernelPackage,qca-nss-ecm-premium-noload))
|
||||
$(eval $(call KernelPackage,qca-nss-ecm-premium))
|
||||
95
package/qca/qca-nss-ecm/files/ecm_dump.sh
Normal file
95
package/qca/qca-nss-ecm/files/ecm_dump.sh
Normal file
@@ -0,0 +1,95 @@
|
||||
#!/bin/sh
|
||||
#
|
||||
# Copyright (c) 2015-2016, The Linux Foundation. All rights reserved.
|
||||
#
|
||||
# Permission to use, copy, modify, and/or distribute this software for any
|
||||
# purpose with or without fee is hereby granted, provided that the above
|
||||
# copyright notice and this permission notice appear in all copies.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
#
|
||||
|
||||
ECM_MODULE=${1:-ecm_state}
|
||||
MOUNT_ROOT=/dev/ecm
|
||||
|
||||
#
|
||||
# usage: ecm_dump.sh [module=ecm_db]
|
||||
#
|
||||
# with no parameters, ecm_dump.sh will attempt to mount the
|
||||
# ecm_db state file and cat its contents.
|
||||
#
|
||||
# example with a parameter: ecm_dump.sh ecm_classifier_default
|
||||
#
|
||||
# this will cause ecm_dump to attempt to find and mount the state
|
||||
# file for the ecm_classifier_default module, and if successful
|
||||
# cat the contents.
|
||||
#
|
||||
|
||||
# this is one of the state files, which happens to be the
|
||||
# last module started in ecm
|
||||
ECM_STATE=/sys/kernel/debug/ecm/ecm_state/state_dev_major
|
||||
|
||||
# tests to see if ECM is up and ready to receive commands.
|
||||
# returns 0 if ECM is fully up and ready, else 1
|
||||
ecm_is_ready() {
|
||||
if [ ! -e "${ECM_STATE}" ]
|
||||
then
|
||||
return 1
|
||||
fi
|
||||
return 0
|
||||
}
|
||||
|
||||
#
|
||||
# module_state_mount(module_name)
|
||||
# Mounts the state file of the module, if supported
|
||||
#
|
||||
module_state_mount() {
|
||||
local module_name=$1
|
||||
local mount_dir=$2
|
||||
local state_file="/sys/kernel/debug/ecm/${module_name}/state_dev_major"
|
||||
|
||||
if [ -e "${mount_dir}/${module_name}" ]
|
||||
then
|
||||
# already mounted
|
||||
return 0
|
||||
fi
|
||||
|
||||
#echo "Mount state file for $module_name ..."
|
||||
if [ ! -e "$state_file" ]
|
||||
then
|
||||
#echo "... $module_name does not support state"
|
||||
return 1
|
||||
fi
|
||||
|
||||
local major="`cat $state_file`"
|
||||
#echo "... Mounting state $state_file with major: $major"
|
||||
mknod "${mount_dir}/${module_name}" c $major 0
|
||||
}
|
||||
|
||||
#
|
||||
# main
|
||||
#
|
||||
ecm_is_ready || {
|
||||
#echo "ECM is not running"
|
||||
exit 1
|
||||
}
|
||||
|
||||
# all state files are mounted under MOUNT_ROOT, so make sure it exists
|
||||
mkdir -p ${MOUNT_ROOT}
|
||||
|
||||
#
|
||||
# attempt to mount state files for the requested module and cat it
|
||||
# if the mount succeeded
|
||||
#
|
||||
module_state_mount ${ECM_MODULE} ${MOUNT_ROOT} && {
|
||||
cat ${MOUNT_ROOT}/${ECM_MODULE}
|
||||
exit 0
|
||||
}
|
||||
|
||||
exit 2
|
||||
6
package/qca/qca-nss-ecm/files/on-demand-down
Normal file
6
package/qca/qca-nss-ecm/files/on-demand-down
Normal file
@@ -0,0 +1,6 @@
|
||||
#!/bin/sh
|
||||
# Copyright (c) 2016 The Linux Foundation. All rights reserved.
|
||||
|
||||
[ -e "/sys/kernel/debug/ecm/ecm_db/defunct_all" ] && {
|
||||
echo 1 > /sys/kernel/debug/ecm/ecm_db/defunct_all
|
||||
}
|
||||
28
package/qca/qca-nss-ecm/files/qca-nss-ecm.defaults
Normal file
28
package/qca/qca-nss-ecm/files/qca-nss-ecm.defaults
Normal file
@@ -0,0 +1,28 @@
|
||||
#!/bin/sh
|
||||
#
|
||||
# Copyright (c) 2015-2016, The Linux Foundation. All rights reserved.
|
||||
#
|
||||
# Permission to use, copy, modify, and/or distribute this software for any
|
||||
# purpose with or without fee is hereby granted, provided that the above
|
||||
# copyright notice and this permission notice appear in all copies.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
#
|
||||
|
||||
uci -q batch << EOF
|
||||
delete firewall.qcanssecm
|
||||
set firewall.qcanssecm=include
|
||||
set firewall.qcanssecm.type=script
|
||||
set firewall.qcanssecm.path=/etc/firewall.d/qca-nss-ecm
|
||||
set firewall.qcanssecm.family=any
|
||||
set firewall.qcanssecm.reload=1
|
||||
commit firewall
|
||||
EOF
|
||||
|
||||
exit 0
|
||||
18
package/qca/qca-nss-ecm/files/qca-nss-ecm.firewall
Normal file
18
package/qca/qca-nss-ecm/files/qca-nss-ecm.firewall
Normal file
@@ -0,0 +1,18 @@
|
||||
#!/bin/sh
|
||||
#
|
||||
# Copyright (c) 2015-2016, The Linux Foundation. All rights reserved.
|
||||
#
|
||||
# Permission to use, copy, modify, and/or distribute this software for any
|
||||
# purpose with or without fee is hereby granted, provided that the above
|
||||
# copyright notice and this permission notice appear in all copies.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
#
|
||||
|
||||
iptables -A FORWARD -m physdev --physdev-is-bridged -j ACCEPT
|
||||
118
package/qca/qca-nss-ecm/files/qca-nss-ecm.init
Normal file
118
package/qca/qca-nss-ecm/files/qca-nss-ecm.init
Normal file
@@ -0,0 +1,118 @@
|
||||
#!/bin/sh /etc/rc.common
|
||||
#
|
||||
# Copyright (c) 2014, 2019 The Linux Foundation. All rights reserved.
|
||||
#
|
||||
# Permission to use, copy, modify, and/or distribute this software for any
|
||||
# purpose with or without fee is hereby granted, provided that the above
|
||||
# copyright notice and this permission notice appear in all copies.
|
||||
#
|
||||
# THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
# WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
# MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
# ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
# WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
# ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
# OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
# The shebang above has an extra space intentially to avoid having
|
||||
# openwrt build scripts automatically enable this package starting
|
||||
# at boot.
|
||||
|
||||
START=19
|
||||
|
||||
get_front_end_mode() {
|
||||
config_load "ecm"
|
||||
config_get front_end global acceleration_engine "auto"
|
||||
|
||||
case $front_end in
|
||||
auto)
|
||||
echo '0'
|
||||
;;
|
||||
nss)
|
||||
echo '1'
|
||||
;;
|
||||
sfe)
|
||||
echo '2'
|
||||
;;
|
||||
*)
|
||||
echo 'uci_option_acceleration_engine is invalid'
|
||||
esac
|
||||
}
|
||||
|
||||
support_bridge() {
|
||||
#NSS support bridge acceleration
|
||||
[ -d /sys/kernel/debug/ecm/ecm_nss_ipv4 ] && return 0
|
||||
#SFE doesn't support bridge acceleration
|
||||
[ -d /sys/kernel/debug/ecm/ecm_sfe_ipv4 ] && return 1
|
||||
}
|
||||
|
||||
load_sfe() {
|
||||
[ -d /sys/module/shortcut_fe ] || insmod shortcut-fe
|
||||
[ -d /sys/module/shortcut_fe_ipv6 ] || insmod shortcut-fe-ipv6
|
||||
[ -d /sys/module/shortcut_fe_drv ] || insmod shortcut-fe-drv
|
||||
}
|
||||
|
||||
load_ecm() {
|
||||
[ -d /sys/module/ecm ] || {
|
||||
[ ! -e /proc/device-tree/MP_256 ] && load_sfe
|
||||
insmod ecm front_end_selection=$(get_front_end_mode)
|
||||
}
|
||||
|
||||
support_bridge && {
|
||||
sysctl -w net.bridge.bridge-nf-call-ip6tables=1
|
||||
sysctl -w net.bridge.bridge-nf-call-iptables=1
|
||||
}
|
||||
}
|
||||
|
||||
unload_ecm() {
|
||||
sysctl -w net.bridge.bridge-nf-call-ip6tables=0
|
||||
sysctl -w net.bridge.bridge-nf-call-iptables=0
|
||||
|
||||
if [ -d /sys/module/ecm ]; then
|
||||
#
|
||||
# Stop ECM frontends
|
||||
#
|
||||
echo 1 > /sys/kernel/debug/ecm/front_end_ipv4_stop
|
||||
echo 1 > /sys/kernel/debug/ecm/front_end_ipv6_stop
|
||||
|
||||
#
|
||||
# Defunct the connections
|
||||
#
|
||||
echo 1 > /sys/kernel/debug/ecm/ecm_db/defunct_all
|
||||
sleep 5;
|
||||
|
||||
rmmod ecm
|
||||
sleep 1
|
||||
fi
|
||||
}
|
||||
|
||||
start() {
|
||||
load_ecm
|
||||
|
||||
# If the acceleration engine is NSS, enable wifi redirect.
|
||||
[ -d /sys/kernel/debug/ecm/ecm_nss_ipv4 ] && sysctl -w dev.nss.general.redirect=1
|
||||
|
||||
support_bridge && {
|
||||
echo 'net.bridge.bridge-nf-call-ip6tables=1' >> /etc/sysctl.d/qca-nss-ecm.conf
|
||||
echo 'net.bridge.bridge-nf-call-iptables=1' >> /etc/sysctl.d/qca-nss-ecm.conf
|
||||
}
|
||||
|
||||
if [ -d /sys/module/qca_ovsmgr ]; then
|
||||
insmod ecm_ovs
|
||||
fi
|
||||
|
||||
}
|
||||
|
||||
stop() {
|
||||
# If the acceleration engine is NSS, disable wifi redirect.
|
||||
[ -d /sys/kernel/debug/ecm/ecm_nss_ipv4 ] && sysctl -w dev.nss.general.redirect=0
|
||||
|
||||
sed '/net.bridge.bridge-nf-call-ip6tables=1/d' -i /etc/sysctl.d/qca-nss-ecm.conf
|
||||
sed '/net.bridge.bridge-nf-call-iptables=1/d' -i /etc/sysctl.d/qca-nss-ecm.conf
|
||||
|
||||
if [ -d /sys/module/ecm_ovs ]; then
|
||||
rmmod ecm_ovs
|
||||
fi
|
||||
|
||||
unload_ecm
|
||||
}
|
||||
2
package/qca/qca-nss-ecm/files/qca-nss-ecm.sysctl
Normal file
2
package/qca/qca-nss-ecm/files/qca-nss-ecm.sysctl
Normal file
@@ -0,0 +1,2 @@
|
||||
# nf_conntrack_tcp_no_window_check is 0 by default, set it to 1
|
||||
net.netfilter.nf_conntrack_tcp_no_window_check=1
|
||||
2
package/qca/qca-nss-ecm/files/qca-nss-ecm.uci
Normal file
2
package/qca/qca-nss-ecm/files/qca-nss-ecm.uci
Normal file
@@ -0,0 +1,2 @@
|
||||
config ecm 'global'
|
||||
option acceleration_engine 'auto'
|
||||
12
package/qca/qca-nss-ecm/patches/001-Drop_SFE_from_ecm.patch
Normal file
12
package/qca/qca-nss-ecm/patches/001-Drop_SFE_from_ecm.patch
Normal file
@@ -0,0 +1,12 @@
|
||||
--- a/Makefile
|
||||
+++ b/Makefile
|
||||
@@ -66,8 +66,7 @@ endif
|
||||
# Define ECM_FRONT_END_SFE_ENABLE=y in order to select
|
||||
# sfe as ECM's front end.
|
||||
# #############################################################################
|
||||
-ifeq ($(SoC),$(filter $(SoC),ipq806x ipq40xx))
|
||||
-ECM_FRONT_END_SFE_ENABLE=y
|
||||
+ifeq ($(ECM_FRONT_END_SFE_ENABLE), y)
|
||||
ecm-$(ECM_FRONT_END_SFE_ENABLE) += frontends/sfe/ecm_sfe_ipv4.o
|
||||
ecm-$(ECM_FRONT_END_SFE_ENABLE) += frontends/sfe/ecm_sfe_ported_ipv4.o
|
||||
ccflags-$(ECM_FRONT_END_SFE_ENABLE) += -DECM_FRONT_END_SFE_ENABLE
|
||||
1276
package/qca/qca-nss-ecm/patches/100-kernel-5.4-support.patch
Normal file
1276
package/qca/qca-nss-ecm/patches/100-kernel-5.4-support.patch
Normal file
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,60 @@
|
||||
diff --git a/frontends/nss/ecm_nss_ipv4.c b/frontends/nss/ecm_nss_ipv4.c
|
||||
index 1ce4b61..29e70ba 100644
|
||||
--- a/frontends/nss/ecm_nss_ipv4.c
|
||||
+++ b/frontends/nss/ecm_nss_ipv4.c
|
||||
@@ -2171,6 +2171,10 @@ sync_conntrack:
|
||||
|
||||
timeouts = nf_ct_timeout_lookup(ct);
|
||||
|
||||
+ /* Copy of udp_get_timeouts in kernel */
|
||||
+ if (!timeouts)
|
||||
+ timeouts = nf_udp_pernet(nf_ct_net(ct))->timeouts;
|
||||
+
|
||||
spin_lock_bh(&ct->lock);
|
||||
ct->timeout = jiffies + timeouts[UDP_CT_REPLIED];
|
||||
spin_unlock_bh(&ct->lock);
|
||||
diff --git a/frontends/nss/ecm_nss_ipv6.c b/frontends/nss/ecm_nss_ipv6.c
|
||||
index 2adc5ec..08253b6 100644
|
||||
--- a/frontends/nss/ecm_nss_ipv6.c
|
||||
+++ b/frontends/nss/ecm_nss_ipv6.c
|
||||
@@ -1883,6 +1883,10 @@ sync_conntrack:
|
||||
|
||||
timeouts = nf_ct_timeout_lookup(ct);
|
||||
|
||||
+ /* Copy of udp_get_timeouts in kernel */
|
||||
+ if (!timeouts)
|
||||
+ timeouts = nf_udp_pernet(nf_ct_net(ct))->timeouts;
|
||||
+
|
||||
spin_lock_bh(&ct->lock);
|
||||
ct->timeout = jiffies + timeouts[UDP_CT_REPLIED];
|
||||
spin_unlock_bh(&ct->lock);
|
||||
diff --git a/frontends/sfe/ecm_sfe_ipv4.c b/frontends/sfe/ecm_sfe_ipv4.c
|
||||
index 7cfe4fc..8f525ee 100644
|
||||
--- a/frontends/sfe/ecm_sfe_ipv4.c
|
||||
+++ b/frontends/sfe/ecm_sfe_ipv4.c
|
||||
@@ -1608,6 +1608,10 @@ sync_conntrack:
|
||||
|
||||
timeouts = nf_ct_timeout_lookup(ct);
|
||||
|
||||
+ /* Copy of udp_get_timeouts in kernel */
|
||||
+ if (!timeouts)
|
||||
+ timeouts = nf_udp_pernet(nf_ct_net(ct))->timeouts;
|
||||
+
|
||||
spin_lock_bh(&ct->lock);
|
||||
ct->timeout = jiffies + timeouts[UDP_CT_REPLIED];
|
||||
spin_unlock_bh(&ct->lock);
|
||||
diff --git a/frontends/sfe/ecm_sfe_ipv6.c b/frontends/sfe/ecm_sfe_ipv6.c
|
||||
index dfde309..47c531a 100644
|
||||
--- a/frontends/sfe/ecm_sfe_ipv6.c
|
||||
+++ b/frontends/sfe/ecm_sfe_ipv6.c
|
||||
@@ -1321,6 +1321,10 @@ sync_conntrack:
|
||||
|
||||
timeouts = nf_ct_timeout_lookup(ct);
|
||||
|
||||
+ /* Copy of udp_get_timeouts in kernel */
|
||||
+ if (!timeouts)
|
||||
+ timeouts = nf_udp_pernet(nf_ct_net(ct))->timeouts;
|
||||
+
|
||||
spin_lock_bh(&ct->lock);
|
||||
ct->timeout = jiffies + timeouts[UDP_CT_REPLIED];
|
||||
spin_unlock_bh(&ct->lock);
|
||||
44
package/qca/qca-nss-ecm/patches/200-resolve-high-load.patch
Normal file
44
package/qca/qca-nss-ecm/patches/200-resolve-high-load.patch
Normal file
@@ -0,0 +1,44 @@
|
||||
The sync update work queue tasks is calling uninterruptible sleep function, which is
|
||||
causing high CPU load. Changed to interruptible sleep function. The stats update
|
||||
task should be interruptible.
|
||||
|
||||
--- a/frontends/nss/ecm_nss_ipv4.c
|
||||
+++ b.frontends/nss/ecm_nss_ipv4.c
|
||||
@@ -2411,7 +2411,7 @@ static void ecm_nss_ipv4_stats_sync_req_
|
||||
}
|
||||
spin_unlock_bh(&ecm_nss_ipv4_lock);
|
||||
|
||||
- usleep_range(ECM_NSS_IPV4_STATS_SYNC_UDELAY - 100, ECM_NSS_IPV4_STATS_SYNC_UDELAY);
|
||||
+ msleep_interruptible(ECM_NSS_IPV4_STATS_SYNC_UDELAY / 1000);
|
||||
|
||||
/*
|
||||
* If index is 0, we are starting a new round, but if we still have time remain
|
||||
@@ -2425,7 +2425,7 @@ static void ecm_nss_ipv4_stats_sync_req_
|
||||
}
|
||||
|
||||
if (ecm_nss_ipv4_next_req_time > current_jiffies) {
|
||||
- msleep(jiffies_to_msecs(ecm_nss_ipv4_next_req_time - current_jiffies));
|
||||
+ msleep_interruptible(jiffies_to_msecs(ecm_nss_ipv4_next_req_time - current_jiffies));
|
||||
}
|
||||
ecm_nss_ipv4_roll_check_jiffies = jiffies;
|
||||
ecm_nss_ipv4_next_req_time = ecm_nss_ipv4_roll_check_jiffies + ECM_NSS_IPV4_STATS_SYNC_PERIOD;
|
||||
--- a/frontends/nss/ecm_nss_ipv6.c
|
||||
+++ b.frontends/nss/ecm_nss_ipv6.c
|
||||
@@ -2128,7 +2128,7 @@ static void ecm_nss_ipv6_stats_sync_req_
|
||||
}
|
||||
spin_unlock_bh(&ecm_nss_ipv6_lock);
|
||||
|
||||
- usleep_range(ECM_NSS_IPV6_STATS_SYNC_UDELAY - 100, ECM_NSS_IPV6_STATS_SYNC_UDELAY);
|
||||
+ msleep_interruptible(ECM_NSS_IPV6_STATS_SYNC_UDELAY / 1000);
|
||||
|
||||
/*
|
||||
* If index is 0, we are starting a new round, but if we still have time remain
|
||||
@@ -2142,7 +2142,7 @@ static void ecm_nss_ipv6_stats_sync_req_
|
||||
}
|
||||
|
||||
if (ecm_nss_ipv6_next_req_time > current_jiffies) {
|
||||
- msleep(jiffies_to_msecs(ecm_nss_ipv6_next_req_time - current_jiffies));
|
||||
+ msleep_interruptible(jiffies_to_msecs(ecm_nss_ipv6_next_req_time - current_jiffies));
|
||||
}
|
||||
ecm_nss_ipv6_roll_check_jiffies = jiffies;
|
||||
ecm_nss_ipv6_next_req_time = ecm_nss_ipv6_roll_check_jiffies + ECM_NSS_IPV6_STATS_SYNC_PERIOD;
|
||||
@@ -0,0 +1,20 @@
|
||||
--- a/ecm_conntrack_notifier.c
|
||||
+++ b/ecm_conntrack_notifier.c
|
||||
@@ -411,7 +411,7 @@ int ecm_conntrack_notifier_init(struct d
|
||||
/*
|
||||
* Eventing subsystem is available so we register a notifier hook to get fast notifications of expired connections
|
||||
*/
|
||||
- result = nf_conntrack_register_notifier(&init_net, &ecm_conntrack_notifier);
|
||||
+ result = nf_conntrack_register_chain_notifier(&init_net, &ecm_conntrack_notifier);
|
||||
if (result < 0) {
|
||||
DEBUG_ERROR("Can't register nf notifier hook.\n");
|
||||
debugfs_remove_recursive(ecm_conntrack_notifier_dentry);
|
||||
@@ -430,7 +430,7 @@ void ecm_conntrack_notifier_exit(void)
|
||||
{
|
||||
DEBUG_INFO("ECM Conntrack Notifier exit\n");
|
||||
#ifdef CONFIG_NF_CONNTRACK_EVENTS
|
||||
- nf_conntrack_unregister_notifier(&init_net, &ecm_conntrack_notifier);
|
||||
+ nf_conntrack_unregister_chain_notifier(&init_net, &ecm_conntrack_notifier);
|
||||
#endif
|
||||
/*
|
||||
* Remove the debugfs files recursively.
|
||||
@@ -0,0 +1,236 @@
|
||||
From 90cace88a342e77ee8ca1e961cf7b7a7930d4c89 Mon Sep 17 00:00:00 2001
|
||||
From: Murat Sezgin <msezgin@codeaurora.org>
|
||||
Date: Mon, 9 Mar 2020 12:51:03 -0700
|
||||
Subject: [qca-nss-ecm] Check TCP/UDP conntrack state earlier
|
||||
|
||||
Check the conntrack state before processing the flow
|
||||
and adding it to the database. The unconfirmed
|
||||
connections can be changed after the confirmation.
|
||||
|
||||
Changed the TCP tracker connection state matrix to set the
|
||||
state of the connection as ESTABLISHED when any of the src or
|
||||
dest side is set as ESTABLISHED. With this change ECM will not
|
||||
handle the SYN and SYN-ACK packets of the TCP handshake. Only the
|
||||
ACK and FIN flaged packets will be used during the creation and
|
||||
closing the connection respectively.
|
||||
|
||||
Signed-off-by: Murat Sezgin <msezgin@codeaurora.org>
|
||||
Change-Id: I3e0a58d604df4c6a85478ca9c05f24d50cd8c894
|
||||
---
|
||||
ecm_classifier_default.c | 36 ++++++++----------------------------
|
||||
ecm_tracker_tcp.c | 4 ++--
|
||||
frontends/nss/ecm_nss_ported_ipv4.c | 17 +++++++++++++++++
|
||||
frontends/nss/ecm_nss_ported_ipv6.c | 17 +++++++++++++++++
|
||||
frontends/sfe/ecm_sfe_ported_ipv4.c | 17 +++++++++++++++++
|
||||
frontends/sfe/ecm_sfe_ported_ipv6.c | 17 +++++++++++++++++
|
||||
6 files changed, 78 insertions(+), 30 deletions(-)
|
||||
|
||||
diff --git a/ecm_classifier_default.c b/ecm_classifier_default.c
|
||||
index 22c4bec..d04cdfa 100644
|
||||
--- a/ecm_classifier_default.c
|
||||
+++ b/ecm_classifier_default.c
|
||||
@@ -1,6 +1,6 @@
|
||||
/*
|
||||
**************************************************************************
|
||||
- * Copyright (c) 2014-2016, The Linux Foundation. All rights reserved.
|
||||
+ * Copyright (c) 2014-2016, 2020, The Linux Foundation. All rights reserved.
|
||||
* Permission to use, copy, modify, and/or distribute this software for
|
||||
* any purpose with or without fee is hereby granted, provided that the
|
||||
* above copyright notice and this permission notice appear in all copies.
|
||||
@@ -285,12 +285,12 @@ static void ecm_classifier_default_process(struct ecm_classifier_instance *aci,
|
||||
}
|
||||
|
||||
/*
|
||||
- * Check the TCP connection state.
|
||||
+ * Check the TCP connection state, when the ct is NULL.
|
||||
+ * ct valid case was already checked in the ecm_nss{sfe}_ported_ipv4{6}_process functions.
|
||||
* If we are not established then we deny acceleration.
|
||||
- * Take lead from conntrack if exists.
|
||||
*/
|
||||
ct = nf_ct_get(skb, &ctinfo);
|
||||
- if (ct == NULL) {
|
||||
+ if (!ct) {
|
||||
DEBUG_TRACE("%p: No Conntrack found for packet, using ECM tracker state\n", cdii);
|
||||
if (unlikely(prevailing_state != ECM_TRACKER_CONNECTION_STATE_ESTABLISHED)) {
|
||||
cdii->process_response.accel_mode = ECM_CLASSIFIER_ACCELERATION_MODE_NO;
|
||||
@@ -298,29 +298,10 @@ static void ecm_classifier_default_process(struct ecm_classifier_instance *aci,
|
||||
}
|
||||
} else {
|
||||
/*
|
||||
- * Unconfirmed connection may be dropped by Linux at the final step,
|
||||
- * So we don't allow acceleration for the unconfirmed connections.
|
||||
- */
|
||||
- if (!nf_ct_is_confirmed(ct)) {
|
||||
- DEBUG_TRACE("%p: Unconfirmed connection\n", ct);
|
||||
- cdii->process_response.accel_mode = ECM_CLASSIFIER_ACCELERATION_MODE_NO;
|
||||
- goto return_response;
|
||||
- }
|
||||
-
|
||||
- /*
|
||||
- * Don't try to manage a non-established connection.
|
||||
- */
|
||||
- if (!test_bit(IPS_ASSURED_BIT, &ct->status)) {
|
||||
- DEBUG_TRACE("%p: Non-established connection\n", ct);
|
||||
- cdii->process_response.accel_mode = ECM_CLASSIFIER_ACCELERATION_MODE_NO;
|
||||
- goto return_response;
|
||||
- }
|
||||
-
|
||||
- /*
|
||||
- * If the connection is shutting down do not manage it.
|
||||
- * state can not be SYN_SENT, SYN_RECV because connection is assured
|
||||
- * Not managed states: FIN_WAIT, CLOSE_WAIT, LAST_ACK, TIME_WAIT, CLOSE.
|
||||
- */
|
||||
+ * If the connection is shutting down do not manage it.
|
||||
+ * state can not be SYN_SENT, SYN_RECV because connection is assured
|
||||
+ * Not managed states: FIN_WAIT, CLOSE_WAIT, LAST_ACK, TIME_WAIT, CLOSE.
|
||||
+ */
|
||||
spin_lock_bh(&ct->lock);
|
||||
if (ct->proto.tcp.state != TCP_CONNTRACK_ESTABLISHED) {
|
||||
spin_unlock_bh(&ct->lock);
|
||||
@@ -333,7 +314,6 @@ static void ecm_classifier_default_process(struct ecm_classifier_instance *aci,
|
||||
|
||||
return_response:
|
||||
;
|
||||
-
|
||||
/*
|
||||
* Return the process response
|
||||
*/
|
||||
diff --git a/ecm_tracker_tcp.c b/ecm_tracker_tcp.c
|
||||
index f073c36..e5b327a 100644
|
||||
--- a/ecm_tracker_tcp.c
|
||||
+++ b/ecm_tracker_tcp.c
|
||||
@@ -257,9 +257,9 @@ static DEFINE_SPINLOCK(ecm_tracker_tcp_lock); /* Global lock for the tracker gl
|
||||
*/
|
||||
static ecm_tracker_connection_state_t ecm_tracker_tcp_connection_state_matrix[ECM_TRACKER_SENDER_STATE_MAX][ECM_TRACKER_SENDER_STATE_MAX] =
|
||||
{ /* Unknown Establishing Established Closing Closed Fault */
|
||||
- /* Unknown */ {ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT},
|
||||
+ /* Unknown */ {ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_ESTABLISHED, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT},
|
||||
/* Establishing */ {ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT},
|
||||
- /* Established */ {ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_ESTABLISHED, ECM_TRACKER_CONNECTION_STATE_CLOSING, ECM_TRACKER_CONNECTION_STATE_CLOSING, ECM_TRACKER_CONNECTION_STATE_FAULT},
|
||||
+ /* Established */ {ECM_TRACKER_CONNECTION_STATE_ESTABLISHED, ECM_TRACKER_CONNECTION_STATE_ESTABLISHING, ECM_TRACKER_CONNECTION_STATE_ESTABLISHED, ECM_TRACKER_CONNECTION_STATE_CLOSING, ECM_TRACKER_CONNECTION_STATE_CLOSING, ECM_TRACKER_CONNECTION_STATE_FAULT},
|
||||
/* Closing */ {ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_CLOSING, ECM_TRACKER_CONNECTION_STATE_CLOSING, ECM_TRACKER_CONNECTION_STATE_CLOSING, ECM_TRACKER_CONNECTION_STATE_FAULT},
|
||||
/* Closed */ {ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_CLOSING, ECM_TRACKER_CONNECTION_STATE_CLOSING, ECM_TRACKER_CONNECTION_STATE_CLOSED, ECM_TRACKER_CONNECTION_STATE_FAULT},
|
||||
/* Fault */ {ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT, ECM_TRACKER_CONNECTION_STATE_FAULT},
|
||||
diff --git a/frontends/nss/ecm_nss_ported_ipv4.c b/frontends/nss/ecm_nss_ported_ipv4.c
|
||||
index 1435ec0..34c056f 100644
|
||||
--- a/frontends/nss/ecm_nss_ported_ipv4.c
|
||||
+++ b/frontends/nss/ecm_nss_ported_ipv4.c
|
||||
@@ -2002,8 +2002,25 @@ unsigned int ecm_nss_ported_ipv4_process(struct net_device *out_dev, struct net_
|
||||
int protocol = (int)orig_tuple->dst.protonum;
|
||||
__be16 *layer4hdr = NULL;
|
||||
|
||||
+ /*
|
||||
+ * Unconfirmed connection may be dropped by Linux at the final step,
|
||||
+ * So we don't allow acceleration for the unconfirmed connections.
|
||||
+ */
|
||||
+ if (likely(ct) && !nf_ct_is_confirmed(ct)) {
|
||||
+ DEBUG_WARN("%p: Unconfirmed connection\n", ct);
|
||||
+ return NF_ACCEPT;
|
||||
+ }
|
||||
+
|
||||
if (protocol == IPPROTO_TCP) {
|
||||
/*
|
||||
+ * Don't try to manage a non-established connection.
|
||||
+ */
|
||||
+ if (likely(ct) && !test_bit(IPS_ASSURED_BIT, &ct->status)) {
|
||||
+ DEBUG_WARN("%p: Non-established TCP connection\n", ct);
|
||||
+ return NF_ACCEPT;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
* Extract TCP header to obtain port information
|
||||
*/
|
||||
tcp_hdr = ecm_tracker_tcp_check_header_and_read(skb, iph, &tcp_hdr_buff);
|
||||
diff --git a/frontends/nss/ecm_nss_ported_ipv6.c b/frontends/nss/ecm_nss_ported_ipv6.c
|
||||
index 4c154a6..bd6349b 100644
|
||||
--- a/frontends/nss/ecm_nss_ported_ipv6.c
|
||||
+++ b/frontends/nss/ecm_nss_ported_ipv6.c
|
||||
@@ -1914,8 +1914,25 @@ unsigned int ecm_nss_ported_ipv6_process(struct net_device *out_dev,
|
||||
int protocol = (int)orig_tuple->dst.protonum;
|
||||
__be16 *layer4hdr = NULL;
|
||||
|
||||
+ /*
|
||||
+ * Unconfirmed connection may be dropped by Linux at the final step,
|
||||
+ * So we don't allow acceleration for the unconfirmed connections.
|
||||
+ */
|
||||
+ if (likely(ct) && !nf_ct_is_confirmed(ct)) {
|
||||
+ DEBUG_WARN("%p: Unconfirmed connection\n", ct);
|
||||
+ return NF_ACCEPT;
|
||||
+ }
|
||||
+
|
||||
if (protocol == IPPROTO_TCP) {
|
||||
/*
|
||||
+ * Don't try to manage a non-established connection.
|
||||
+ */
|
||||
+ if (likely(ct) && !test_bit(IPS_ASSURED_BIT, &ct->status)) {
|
||||
+ DEBUG_WARN("%p: Non-established TCP connection\n", ct);
|
||||
+ return NF_ACCEPT;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
* Extract TCP header to obtain port information
|
||||
*/
|
||||
tcp_hdr = ecm_tracker_tcp_check_header_and_read(skb, iph, &tcp_hdr_buff);
|
||||
diff --git a/frontends/sfe/ecm_sfe_ported_ipv4.c b/frontends/sfe/ecm_sfe_ported_ipv4.c
|
||||
index e034cde..df1ce57 100644
|
||||
--- a/frontends/sfe/ecm_sfe_ported_ipv4.c
|
||||
+++ b/frontends/sfe/ecm_sfe_ported_ipv4.c
|
||||
@@ -1805,8 +1805,25 @@ unsigned int ecm_sfe_ported_ipv4_process(struct net_device *out_dev, struct net_
|
||||
int protocol = (int)orig_tuple->dst.protonum;
|
||||
__be16 *layer4hdr = NULL;
|
||||
|
||||
+ /*
|
||||
+ * Unconfirmed connection may be dropped by Linux at the final step,
|
||||
+ * So we don't allow acceleration for the unconfirmed connections.
|
||||
+ */
|
||||
+ if (likely(ct) && !nf_ct_is_confirmed(ct)) {
|
||||
+ DEBUG_WARN("%p: Unconfirmed connection\n", ct);
|
||||
+ return NF_ACCEPT;
|
||||
+ }
|
||||
+
|
||||
if (protocol == IPPROTO_TCP) {
|
||||
/*
|
||||
+ * Don't try to manage a non-established connection.
|
||||
+ */
|
||||
+ if (likely(ct) && !test_bit(IPS_ASSURED_BIT, &ct->status)) {
|
||||
+ DEBUG_WARN("%p: Non-established TCP connection\n", ct);
|
||||
+ return NF_ACCEPT;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
* Extract TCP header to obtain port information
|
||||
*/
|
||||
tcp_hdr = ecm_tracker_tcp_check_header_and_read(skb, iph, &tcp_hdr_buff);
|
||||
diff --git a/frontends/sfe/ecm_sfe_ported_ipv6.c b/frontends/sfe/ecm_sfe_ported_ipv6.c
|
||||
index 6ac05ad..657a1c7 100644
|
||||
--- a/frontends/sfe/ecm_sfe_ported_ipv6.c
|
||||
+++ b/frontends/sfe/ecm_sfe_ported_ipv6.c
|
||||
@@ -1746,8 +1746,25 @@ unsigned int ecm_sfe_ported_ipv6_process(struct net_device *out_dev,
|
||||
int protocol = (int)orig_tuple->dst.protonum;
|
||||
__be16 *layer4hdr = NULL;
|
||||
|
||||
+ /*
|
||||
+ * Unconfirmed connection may be dropped by Linux at the final step,
|
||||
+ * So we don't allow acceleration for the unconfirmed connections.
|
||||
+ */
|
||||
+ if (likely(ct) && !nf_ct_is_confirmed(ct)) {
|
||||
+ DEBUG_WARN("%p: Unconfirmed connection\n", ct);
|
||||
+ return NF_ACCEPT;
|
||||
+ }
|
||||
+
|
||||
if (protocol == IPPROTO_TCP) {
|
||||
/*
|
||||
+ * Don't try to manage a non-established connection.
|
||||
+ */
|
||||
+ if (likely(ct) && !test_bit(IPS_ASSURED_BIT, &ct->status)) {
|
||||
+ DEBUG_WARN("%p: Non-established TCP connection\n", ct);
|
||||
+ return NF_ACCEPT;
|
||||
+ }
|
||||
+
|
||||
+ /*
|
||||
* Extract TCP header to obtain port information
|
||||
*/
|
||||
tcp_hdr = ecm_tracker_tcp_check_header_and_read(skb, iph, &tcp_hdr_buff);
|
||||
--
|
||||
cgit v1.1
|
||||
|
||||
@@ -0,0 +1,52 @@
|
||||
From 9ad19ffdcfdf77baf3abd4fcc933fd3dc8e791a5 Mon Sep 17 00:00:00 2001
|
||||
From: Murat Sezgin <msezgin@codeaurora.org>
|
||||
Date: Sat, 20 Jun 2020 09:41:01 -0700
|
||||
Subject: [qca-nss-ecm] Fix NSS stats request roll over issue
|
||||
|
||||
Use the correct timer API to check the next request time
|
||||
when jiffies wrap happens.
|
||||
|
||||
Signed-off-by: Murat Sezgin <msezgin@codeaurora.org>
|
||||
Change-Id: I18646d28df7e17daeff2986dfe4bd73866d47668
|
||||
---
|
||||
frontends/nss/ecm_nss_ipv4.c | 4 ++--
|
||||
frontends/nss/ecm_nss_ipv6.c | 4 ++--
|
||||
2 files changed, 4 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/frontends/nss/ecm_nss_ipv4.c b/frontends/nss/ecm_nss_ipv4.c
|
||||
index 3eaf5d8..80e1aee 100644
|
||||
--- a/frontends/nss/ecm_nss_ipv4.c
|
||||
+++ b/frontends/nss/ecm_nss_ipv4.c
|
||||
@@ -2421,10 +2421,10 @@ static void ecm_nss_ipv4_stats_sync_req_work(struct work_struct *work)
|
||||
current_jiffies = jiffies;
|
||||
|
||||
if (time_is_after_jiffies(ecm_nss_ipv4_roll_check_jiffies)) {
|
||||
- ecm_nss_ipv4_next_req_time = 0;
|
||||
+ ecm_nss_ipv4_next_req_time = jiffies + ECM_NSS_IPV4_STATS_SYNC_PERIOD;
|
||||
}
|
||||
|
||||
- if (ecm_nss_ipv4_next_req_time > current_jiffies) {
|
||||
+ if (time_after(ecm_nss_ipv4_next_req_time, current_jiffies)) {
|
||||
msleep_interruptible(jiffies_to_msecs(ecm_nss_ipv4_next_req_time - current_jiffies));
|
||||
}
|
||||
ecm_nss_ipv4_roll_check_jiffies = jiffies;
|
||||
diff --git a/frontends/nss/ecm_nss_ipv6.c b/frontends/nss/ecm_nss_ipv6.c
|
||||
index 288dc55..483421e 100644
|
||||
--- a/frontends/nss/ecm_nss_ipv6.c
|
||||
+++ b/frontends/nss/ecm_nss_ipv6.c
|
||||
@@ -2135,10 +2135,10 @@ static void ecm_nss_ipv6_stats_sync_req_work(struct work_struct *work)
|
||||
current_jiffies = jiffies;
|
||||
|
||||
if (time_is_after_jiffies(ecm_nss_ipv6_roll_check_jiffies)) {
|
||||
- ecm_nss_ipv6_next_req_time = 0;
|
||||
+ ecm_nss_ipv6_next_req_time = jiffies + ECM_NSS_IPV6_STATS_SYNC_PERIOD;
|
||||
}
|
||||
|
||||
- if (ecm_nss_ipv6_next_req_time > current_jiffies) {
|
||||
+ if (time_after(ecm_nss_ipv6_next_req_time, current_jiffies)) {
|
||||
msleep_interruptible(jiffies_to_msecs(ecm_nss_ipv6_next_req_time - current_jiffies));
|
||||
}
|
||||
ecm_nss_ipv6_roll_check_jiffies = jiffies;
|
||||
--
|
||||
cgit v1.1
|
||||
|
||||
@@ -0,0 +1,112 @@
|
||||
From 4b41703a181b7187d9ff8cb744eb96d09997387c Mon Sep 17 00:00:00 2001
|
||||
From: Suman Ghosh <sumaghos@codeaurora.org>
|
||||
Date: Wed, 19 Feb 2020 15:09:19 +0530
|
||||
Subject: [qca-nss-ecm] Fix for ref leak during multicast 'to' hierarchy
|
||||
creation
|
||||
|
||||
Change-Id: I89df9dbe5ea054cf3b87d55ce68a751cb1d6c24f
|
||||
Signed-off-by: Suman Ghosh <sumaghos@codeaurora.org>
|
||||
---
|
||||
ecm_interface.c | 34 ++++++++++++++++++++++++++++++----
|
||||
1 file changed, 30 insertions(+), 4 deletions(-)
|
||||
|
||||
diff --git a/ecm_interface.c b/ecm_interface.c
|
||||
index 4f7a886..2a0ca5b 100644
|
||||
--- a/ecm_interface.c
|
||||
+++ b/ecm_interface.c
|
||||
@@ -3885,13 +3885,13 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
dest_dev = dev_get_by_index(&init_net, *dst_if_index);
|
||||
if (!dest_dev) {
|
||||
if (!src_dev_is_bridge) {
|
||||
- int i;
|
||||
-
|
||||
/*
|
||||
* If already constructed any interface heirarchies before hitting
|
||||
* this error condition then Deref all interface heirarchies.
|
||||
*/
|
||||
if (valid_if > 0) {
|
||||
+ int i;
|
||||
+
|
||||
for (i = 0; i < valid_if; i++) {
|
||||
ifaces = ecm_db_multicast_if_heirarchy_get(interfaces, i);
|
||||
ecm_db_multicast_copy_if_heirarchy(to_list_single, ifaces);
|
||||
@@ -3902,11 +3902,14 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
/*
|
||||
* If valid netdev not found, Return 0
|
||||
*/
|
||||
+ if (br_dev_src) {
|
||||
+ dev_put(br_dev_src);
|
||||
+ }
|
||||
+
|
||||
return 0;
|
||||
}
|
||||
|
||||
dest_dev = br_dev_src;
|
||||
-
|
||||
}
|
||||
|
||||
dest_dev_type = dest_dev->type;
|
||||
@@ -3945,6 +3948,10 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
}
|
||||
}
|
||||
|
||||
+ if (br_dev_src && (dest_dev != br_dev_src)) {
|
||||
+ dev_put(br_dev_src);
|
||||
+ }
|
||||
+
|
||||
dev_put(dest_dev);
|
||||
return 0;
|
||||
}
|
||||
@@ -3972,6 +3979,10 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
ecm_db_connection_interfaces_deref(to_list_single, interface_first_base[i]);
|
||||
}
|
||||
|
||||
+ if (br_dev_src && (dest_dev != br_dev_src)) {
|
||||
+ dev_put(br_dev_src);
|
||||
+ }
|
||||
+
|
||||
dev_put(dest_dev);
|
||||
dev_put(mc_br_slave_dev);
|
||||
return 0;
|
||||
@@ -3997,6 +4008,10 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
}
|
||||
}
|
||||
|
||||
+ if (br_dev_src && (dest_dev != br_dev_src)) {
|
||||
+ dev_put(br_dev_src);
|
||||
+ }
|
||||
+
|
||||
dev_put(dest_dev);
|
||||
dev_put(mc_br_slave_dev);
|
||||
return 0;
|
||||
@@ -4032,6 +4047,10 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
}
|
||||
}
|
||||
|
||||
+ if (br_dev_src && (dest_dev != br_dev_src)) {
|
||||
+ dev_put(br_dev_src);
|
||||
+ }
|
||||
+
|
||||
dev_put(dest_dev);
|
||||
return 0;
|
||||
}
|
||||
@@ -4042,8 +4061,15 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
valid_if++;
|
||||
}
|
||||
|
||||
- dev_put(dest_dev);
|
||||
+ if (dest_dev != br_dev_src) {
|
||||
+ dev_put(dest_dev);
|
||||
+ }
|
||||
}
|
||||
+
|
||||
+ if (br_dev_src) {
|
||||
+ dev_put(br_dev_src);
|
||||
+ }
|
||||
+
|
||||
return total_ii_count;
|
||||
}
|
||||
EXPORT_SYMBOL(ecm_interface_multicast_heirarchy_construct_routed);
|
||||
--
|
||||
cgit v1.1
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
From 72e3ae508906553e7bc982bf3c0d99bb1cbe9008 Mon Sep 17 00:00:00 2001
|
||||
From: Murat Sezgin <msezgin@codeaurora.org>
|
||||
Date: Wed, 20 Nov 2019 16:23:06 -0800
|
||||
Subject: [qca-nss-ecm] Fix neighbour solicitation send function.
|
||||
|
||||
dst_ops->neigh_lookup function pointer is set to the
|
||||
ip6_neigh_lookup function. This function returns an
|
||||
error pointer with the ERR_PTR() macro. So, we should
|
||||
check the return value of this function pointer with
|
||||
the IS_ERR() macro.
|
||||
|
||||
Change-Id: I188a6e53278faaa68f1854524f612efc1f7451fe
|
||||
Signed-off-by: Murat Sezgin <msezgin@codeaurora.org>
|
||||
---
|
||||
ecm_interface.c | 2 +-
|
||||
1 file changed, 1 insertion(+), 1 deletion(-)
|
||||
|
||||
diff --git a/ecm_interface.c b/ecm_interface.c
|
||||
index 3f8554b..36509f0 100644
|
||||
--- a/ecm_interface.c
|
||||
+++ b/ecm_interface.c
|
||||
@@ -1100,7 +1100,7 @@ void ecm_interface_send_neighbour_solicitation(struct net_device *dev, ip_addr_t
|
||||
#else
|
||||
neigh = rt6i->dst.ops->neigh_lookup(&rt6i->dst, NULL, &dst_addr);
|
||||
#endif
|
||||
- if (neigh == NULL) {
|
||||
+ if (IS_ERR(neigh)) {
|
||||
DEBUG_TRACE("Neighbour lookup failure for destination IPv6 address " ECM_IP_ADDR_OCTAL_FMT "\n", ECM_IP_ADDR_TO_OCTAL(addr));
|
||||
dst_release(&rt6i->dst);
|
||||
return;
|
||||
--
|
||||
cgit v1.1
|
||||
|
||||
@@ -0,0 +1,260 @@
|
||||
From 7c0610828b835b2aab96dd50ec841a3a28689112 Mon Sep 17 00:00:00 2001
|
||||
From: Suman Ghosh <sumaghos@codeaurora.org>
|
||||
Date: Mon, 16 Mar 2020 15:22:18 +0530
|
||||
Subject: [qca-nss-ecm] Reference leak during multicast + PPPoE bridge
|
||||
|
||||
Signed-off-by: Suman Ghosh <sumaghos@codeaurora.org>
|
||||
Change-Id: I4472035f1bbb087e637169762ae2648c0fda792a
|
||||
---
|
||||
ecm_interface.c | 136 +++++++++++++++++++++++++-------------------------------
|
||||
1 file changed, 60 insertions(+), 76 deletions(-)
|
||||
|
||||
diff --git a/ecm_interface.c b/ecm_interface.c
|
||||
index 1614336..c0d2357 100644
|
||||
--- a/ecm_interface.c
|
||||
+++ b/ecm_interface.c
|
||||
@@ -3796,6 +3796,25 @@ fail:
|
||||
}
|
||||
|
||||
/*
|
||||
+ * ecm_interface_hierarchy_delete()
|
||||
+ * Delete hierarchy of the requested interfaces.
|
||||
+ */
|
||||
+static inline void ecm_interface_hierarchy_delete(struct ecm_db_iface_instance *interfaces,
|
||||
+ uint32_t *interface_first_base,
|
||||
+ int valid_if)
|
||||
+{
|
||||
+ struct ecm_db_iface_instance *to_list_single[ECM_DB_IFACE_HEIRARCHY_MAX];
|
||||
+ struct ecm_db_iface_instance *ifaces;
|
||||
+ int i;
|
||||
+
|
||||
+ for (i = 0; i < valid_if; i++) {
|
||||
+ ifaces = ecm_db_multicast_if_heirarchy_get(interfaces, i);
|
||||
+ ecm_db_multicast_copy_if_heirarchy(to_list_single, ifaces);
|
||||
+ ecm_db_connection_interfaces_deref(to_list_single, interface_first_base[i]);
|
||||
+ }
|
||||
+}
|
||||
+
|
||||
+/*
|
||||
* ecm_interface_multicast_heirarchy_construct_routed()
|
||||
* Create destination interface heirarchy for a routed multicast connectiona
|
||||
*
|
||||
@@ -3816,7 +3835,6 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
uint32_t *interface_first_base, bool mfc_update,
|
||||
__be16 *layer4hdr, struct sk_buff *skb)
|
||||
{
|
||||
- struct ecm_db_iface_instance *to_list_single[ECM_DB_IFACE_HEIRARCHY_MAX];
|
||||
struct ecm_db_iface_instance *ifaces;
|
||||
struct net_device *dest_dev = NULL;
|
||||
struct net_device *br_dev_src = NULL;
|
||||
@@ -3829,7 +3847,7 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
int if_index;
|
||||
int ii_cnt;
|
||||
int total_ii_count = 0;
|
||||
- bool src_dev_is_bridge = false;
|
||||
+ bool src_dev_is_bridge = false, dest_dev_is_br_dev_src = false;
|
||||
|
||||
DEBUG_TRACE("Construct interface heirarchy for dest_addr: " ECM_IP_ADDR_DOT_FMT " src_addr: " ECM_IP_ADDR_DOT_FMT "total destination ifs %d\n",
|
||||
ECM_IP_ADDR_TO_DOT(packet_dest_addr), ECM_IP_ADDR_TO_DOT(packet_src_addr), max_if);
|
||||
@@ -3876,6 +3894,7 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
continue;
|
||||
}
|
||||
|
||||
+ dest_dev_is_br_dev_src = false;
|
||||
dest_dev = dev_get_by_index(&init_net, *dst_if_index);
|
||||
if (!dest_dev) {
|
||||
if (!src_dev_is_bridge) {
|
||||
@@ -3884,26 +3903,23 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
* this error condition then Deref all interface heirarchies.
|
||||
*/
|
||||
if (valid_if > 0) {
|
||||
- int i;
|
||||
-
|
||||
- for (i = 0; i < valid_if; i++) {
|
||||
- ifaces = ecm_db_multicast_if_heirarchy_get(interfaces, i);
|
||||
- ecm_db_multicast_copy_if_heirarchy(to_list_single, ifaces);
|
||||
- ecm_db_connection_interfaces_deref(to_list_single, interface_first_base[i]);
|
||||
- }
|
||||
+ ecm_interface_hierarchy_delete(interfaces, interface_first_base, valid_if);
|
||||
}
|
||||
|
||||
- /*
|
||||
- * If valid netdev not found, Return 0
|
||||
- */
|
||||
- if (br_dev_src) {
|
||||
- dev_put(br_dev_src);
|
||||
- }
|
||||
-
|
||||
- return 0;
|
||||
+ goto fail1;
|
||||
}
|
||||
|
||||
dest_dev = br_dev_src;
|
||||
+
|
||||
+ /*
|
||||
+ * In some cases when WAN interface is added to bridge and traffic is downstream,
|
||||
+ * the bridge device is part of the destination list from MFC, and at the same time
|
||||
+ * 'src_dev_is_bridge' will be true as well. In such cases we will need to release
|
||||
+ * the hold on the bridge device separately for dest_dev and br_dev_src.
|
||||
+ * Setting this flag to true indicates that this is not the case,
|
||||
+ * and that releasing the hold once is enough
|
||||
+ */
|
||||
+ dest_dev_is_br_dev_src = true;
|
||||
}
|
||||
|
||||
dest_dev_type = dest_dev->type;
|
||||
@@ -3927,7 +3943,6 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
}
|
||||
|
||||
if ((if_num < 0) || (if_num > ECM_DB_MULTICAST_IF_MAX)) {
|
||||
- int i;
|
||||
DEBUG_WARN("MCS is not ready\n");
|
||||
|
||||
/*
|
||||
@@ -3935,19 +3950,10 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
* this error condition then Deref all interface heirarchies.
|
||||
*/
|
||||
if (valid_if > 0) {
|
||||
- for (i = 0; i < valid_if; i++) {
|
||||
- ifaces = ecm_db_multicast_if_heirarchy_get(interfaces, i);
|
||||
- ecm_db_multicast_copy_if_heirarchy(to_list_single, ifaces);
|
||||
- ecm_db_connection_interfaces_deref(to_list_single, interface_first_base[i]);
|
||||
- }
|
||||
+ ecm_interface_hierarchy_delete(interfaces, interface_first_base, valid_if);
|
||||
}
|
||||
|
||||
- if (br_dev_src && (dest_dev != br_dev_src)) {
|
||||
- dev_put(br_dev_src);
|
||||
- }
|
||||
-
|
||||
- dev_put(dest_dev);
|
||||
- return 0;
|
||||
+ goto fail2;
|
||||
}
|
||||
|
||||
if (in_dev && !mfc_update) {
|
||||
@@ -3955,34 +3961,20 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
}
|
||||
|
||||
for (br_if = 0; br_if < if_num; br_if++) {
|
||||
+ int total_if = valid_if + br_if;
|
||||
+
|
||||
mc_br_slave_dev = dev_get_by_index(&init_net, mc_dst_if_index[br_if]);
|
||||
if (!mc_br_slave_dev) {
|
||||
continue;
|
||||
}
|
||||
|
||||
- if ((valid_if + br_if) > ECM_DB_MULTICAST_IF_MAX) {
|
||||
- int i;
|
||||
-
|
||||
- /*
|
||||
- * If already constructed any interface heirarchies before hitting
|
||||
- * this error condition then Deref all interface heirarchies.
|
||||
- */
|
||||
- for (i = 0; i < (valid_if + br_if); i++) {
|
||||
- ifaces = ecm_db_multicast_if_heirarchy_get(interfaces, i);
|
||||
- ecm_db_multicast_copy_if_heirarchy(to_list_single, ifaces);
|
||||
- ecm_db_connection_interfaces_deref(to_list_single, interface_first_base[i]);
|
||||
- }
|
||||
-
|
||||
- if (br_dev_src && (dest_dev != br_dev_src)) {
|
||||
- dev_put(br_dev_src);
|
||||
- }
|
||||
-
|
||||
- dev_put(dest_dev);
|
||||
+ if (total_if > ECM_DB_MULTICAST_IF_MAX) {
|
||||
+ ecm_interface_hierarchy_delete(interfaces, interface_first_base, total_if);
|
||||
dev_put(mc_br_slave_dev);
|
||||
- return 0;
|
||||
+ goto fail2;
|
||||
}
|
||||
|
||||
- ifaces = ecm_db_multicast_if_heirarchy_get(interfaces, valid_if + br_if);
|
||||
+ ifaces = ecm_db_multicast_if_heirarchy_get(interfaces, total_if);
|
||||
/*
|
||||
* Construct a single interface heirarchy of a multicast dev.
|
||||
*/
|
||||
@@ -3993,25 +3985,15 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
* If already constructed any interface heirarchies before hitting
|
||||
* this error condition then Deref all interface heirarchies.
|
||||
*/
|
||||
- if ((valid_if + br_if) > 0) {
|
||||
- int i;
|
||||
- for (i = 0; i < (valid_if + br_if); i++) {
|
||||
- ifaces = ecm_db_multicast_if_heirarchy_get(interfaces, i);
|
||||
- ecm_db_multicast_copy_if_heirarchy(to_list_single, ifaces);
|
||||
- ecm_db_connection_interfaces_deref(to_list_single, interface_first_base[i]);
|
||||
- }
|
||||
- }
|
||||
-
|
||||
- if (br_dev_src && (dest_dev != br_dev_src)) {
|
||||
- dev_put(br_dev_src);
|
||||
+ if (total_if > 0) {
|
||||
+ ecm_interface_hierarchy_delete(interfaces, interface_first_base, total_if);
|
||||
}
|
||||
|
||||
- dev_put(dest_dev);
|
||||
dev_put(mc_br_slave_dev);
|
||||
- return 0;
|
||||
+ goto fail2;
|
||||
}
|
||||
|
||||
- interface_first = ecm_db_multicast_if_first_get_at_index(interface_first_base, (valid_if + br_if));
|
||||
+ interface_first = ecm_db_multicast_if_first_get_at_index(interface_first_base, total_if);
|
||||
*interface_first = ii_cnt;
|
||||
total_ii_count += ii_cnt;
|
||||
dev_put(mc_br_slave_dev);
|
||||
@@ -4033,20 +4015,10 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
* this error condition then Deref all interface heirarchies.
|
||||
*/
|
||||
if (valid_if > 0) {
|
||||
- int i;
|
||||
- for (i = 0; i < valid_if; i++) {
|
||||
- ifaces = ecm_db_multicast_if_heirarchy_get(interfaces, i);
|
||||
- ecm_db_multicast_copy_if_heirarchy(to_list_single, ifaces);
|
||||
- ecm_db_connection_interfaces_deref(to_list_single, interface_first_base[i]);
|
||||
- }
|
||||
- }
|
||||
-
|
||||
- if (br_dev_src && (dest_dev != br_dev_src)) {
|
||||
- dev_put(br_dev_src);
|
||||
+ ecm_interface_hierarchy_delete(interfaces, interface_first_base, valid_if);
|
||||
}
|
||||
|
||||
- dev_put(dest_dev);
|
||||
- return 0;
|
||||
+ goto fail2;
|
||||
}
|
||||
|
||||
interface_first = ecm_db_multicast_if_first_get_at_index(interface_first_base, valid_if);
|
||||
@@ -4055,7 +4027,7 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
valid_if++;
|
||||
}
|
||||
|
||||
- if (dest_dev != br_dev_src) {
|
||||
+ if (!dest_dev_is_br_dev_src) {
|
||||
dev_put(dest_dev);
|
||||
}
|
||||
}
|
||||
@@ -4065,6 +4037,18 @@ int32_t ecm_interface_multicast_heirarchy_construct_routed(struct ecm_front_end_
|
||||
}
|
||||
|
||||
return total_ii_count;
|
||||
+
|
||||
+fail2:
|
||||
+ if (!dest_dev_is_br_dev_src) {
|
||||
+ dev_put(dest_dev);
|
||||
+ }
|
||||
+
|
||||
+fail1:
|
||||
+ if (br_dev_src) {
|
||||
+ dev_put(br_dev_src);
|
||||
+ }
|
||||
+
|
||||
+ return 0;
|
||||
}
|
||||
EXPORT_SYMBOL(ecm_interface_multicast_heirarchy_construct_routed);
|
||||
|
||||
--
|
||||
cgit v1.1
|
||||
|
||||
@@ -0,0 +1,59 @@
|
||||
From 65a49ebd1bd12b9952dfa214de0a2da43ba2abed Mon Sep 17 00:00:00 2001
|
||||
From: Bhaskar Valaboju <bhaskarv@codeaurora.org>
|
||||
Date: Tue, 13 Aug 2019 14:21:03 +0530
|
||||
Subject: [qca-nss-ecm]: Access global ipv4/ipv6 accelerated count under lock
|
||||
|
||||
Flow accelerated count maintained as global variables are accessed
|
||||
in multiple kernel contexts. These counters are updated under lock,
|
||||
but read without lock. Read is in kernel thread context (workqueue)
|
||||
and sometimes it is taking stale entry (0) and doesn't change.
|
||||
Lock is added to read correct value.
|
||||
|
||||
Change-Id: I74cf27fe5097c6ae7dfcc06319762a8a322d79a3
|
||||
Signed-off-by: Bhaskar Valaboju <bhaskarv@codeaurora.org>
|
||||
---
|
||||
frontends/nss/ecm_nss_ipv4.c | 3 +++
|
||||
frontends/nss/ecm_nss_ipv6.c | 3 +++
|
||||
2 files changed, 6 insertions(+)
|
||||
|
||||
(limited to 'frontends')
|
||||
|
||||
diff --git a/frontends/nss/ecm_nss_ipv4.c b/frontends/nss/ecm_nss_ipv4.c
|
||||
index afd660e..4e66cdf 100644
|
||||
--- a/frontends/nss/ecm_nss_ipv4.c
|
||||
+++ b/frontends/nss/ecm_nss_ipv4.c
|
||||
@@ -2288,10 +2288,13 @@ static void ecm_nss_ipv4_stats_sync_req_work(struct work_struct *work)
|
||||
int retry = 3;
|
||||
unsigned long int current_jiffies;
|
||||
|
||||
+ spin_lock_bh(&ecm_nss_ipv4_lock);
|
||||
if (ecm_nss_ipv4_accelerated_count == 0) {
|
||||
+ spin_unlock_bh(&ecm_nss_ipv4_lock);
|
||||
DEBUG_TRACE("There is no accelerated IPv4 connection\n");
|
||||
goto reschedule;
|
||||
}
|
||||
+ spin_unlock_bh(&ecm_nss_ipv4_lock);
|
||||
|
||||
usleep_range(ECM_NSS_IPV4_STATS_SYNC_UDELAY - 100, ECM_NSS_IPV4_STATS_SYNC_UDELAY);
|
||||
|
||||
diff --git a/frontends/nss/ecm_nss_ipv6.c b/frontends/nss/ecm_nss_ipv6.c
|
||||
index 1f7f51e..55849e7 100644
|
||||
--- a/frontends/nss/ecm_nss_ipv6.c
|
||||
+++ b/frontends/nss/ecm_nss_ipv6.c
|
||||
@@ -1998,10 +1998,13 @@ static void ecm_nss_ipv6_stats_sync_req_work(struct work_struct *work)
|
||||
int retry = 3;
|
||||
unsigned long int current_jiffies;
|
||||
|
||||
+ spin_lock_bh(&ecm_nss_ipv6_lock);
|
||||
if (ecm_nss_ipv6_accelerated_count == 0) {
|
||||
+ spin_unlock_bh(&ecm_nss_ipv6_lock);
|
||||
DEBUG_TRACE("There is no accelerated IPv6 connection\n");
|
||||
goto reschedule;
|
||||
}
|
||||
+ spin_unlock_bh(&ecm_nss_ipv6_lock);
|
||||
|
||||
usleep_range(ECM_NSS_IPV6_STATS_SYNC_UDELAY - 100, ECM_NSS_IPV6_STATS_SYNC_UDELAY);
|
||||
|
||||
--
|
||||
cgit v1.1
|
||||
|
||||
@@ -0,0 +1,83 @@
|
||||
From b96002061178f399c1e58a9ad821e5096a64f788 Mon Sep 17 00:00:00 2001
|
||||
From: Murat Sezgin <msezgin@codeaurora.org>
|
||||
Date: Mon, 23 Mar 2020 10:59:39 -0700
|
||||
Subject: [qca-nss-ecm] Fix IPv6 neighbor solicitation request
|
||||
|
||||
Send the solicitation request to the GW address, when
|
||||
a GW address is found, while establishing the node instance.
|
||||
|
||||
Signed-off-by: Murat Sezgin <msezgin@codeaurora.org>
|
||||
Change-Id: I2187569bcfd05b0d091cf8c79171ee3c41c39cb9
|
||||
---
|
||||
frontends/nss/ecm_nss_ipv6.c | 7 ++++---
|
||||
frontends/nss/ecm_nss_multicast_ipv6.c | 9 +++++++++
|
||||
frontends/sfe/ecm_sfe_ipv6.c | 7 ++++---
|
||||
3 files changed, 17 insertions(+), 6 deletions(-)
|
||||
|
||||
diff --git a/frontends/nss/ecm_nss_ipv6.c b/frontends/nss/ecm_nss_ipv6.c
|
||||
index c7dd37f..9011e18 100644
|
||||
--- a/frontends/nss/ecm_nss_ipv6.c
|
||||
+++ b/frontends/nss/ecm_nss_ipv6.c
|
||||
@@ -527,13 +527,14 @@ struct ecm_db_node_instance *ecm_nss_ipv6_node_establish_and_ref(struct ecm_fron
|
||||
struct net_device *master;
|
||||
master = ecm_interface_get_and_hold_dev_master(dev);
|
||||
DEBUG_ASSERT(master, "Expected a master\n");
|
||||
- ecm_interface_send_neighbour_solicitation(master, addr);
|
||||
+ ecm_interface_send_neighbour_solicitation(master, gw_addr);
|
||||
dev_put(master);
|
||||
} else {
|
||||
- ecm_interface_send_neighbour_solicitation(dev, addr);
|
||||
+ ecm_interface_send_neighbour_solicitation(dev, gw_addr);
|
||||
}
|
||||
|
||||
- DEBUG_TRACE("Failed to obtain mac for host " ECM_IP_ADDR_OCTAL_FMT "\n", ECM_IP_ADDR_TO_OCTAL(addr));
|
||||
+ DEBUG_TRACE("Failed to obtain mac for host " ECM_IP_ADDR_OCTAL_FMT " gw: " ECM_IP_ADDR_OCTAL_FMT "\n",
|
||||
+ ECM_IP_ADDR_TO_OCTAL(addr), ECM_IP_ADDR_TO_OCTAL(gw_addr));
|
||||
return NULL;
|
||||
}
|
||||
done:
|
||||
diff --git a/frontends/nss/ecm_nss_multicast_ipv6.c b/frontends/nss/ecm_nss_multicast_ipv6.c
|
||||
index a361eec..38fde95 100644
|
||||
--- a/frontends/nss/ecm_nss_multicast_ipv6.c
|
||||
+++ b/frontends/nss/ecm_nss_multicast_ipv6.c
|
||||
@@ -2558,6 +2558,15 @@ static struct ecm_db_node_instance *ecm_nss_multicast_ipv6_node_establish_and_re
|
||||
#endif
|
||||
if (!ecm_interface_mac_addr_get(addr, node_addr, &on_link, gw_addr)) {
|
||||
DEBUG_TRACE("Failed to obtain mac for host " ECM_IP_ADDR_OCTAL_FMT "\n", ECM_IP_ADDR_TO_OCTAL(addr));
|
||||
+
|
||||
+ /*
|
||||
+ * If there is a gw_addr found during the lookup, use that address
|
||||
+ * for neighbour solicitation request.
|
||||
+ */
|
||||
+ if (!ECM_IP_ADDR_IS_NULL(gw_addr)) {
|
||||
+ ECM_IP_ADDR_COPY(addr, gw_addr);
|
||||
+ }
|
||||
+
|
||||
if (ecm_front_end_is_bridge_port(dev)) {
|
||||
struct net_device *master;
|
||||
master = ecm_interface_get_and_hold_dev_master(dev);
|
||||
diff --git a/frontends/sfe/ecm_sfe_ipv6.c b/frontends/sfe/ecm_sfe_ipv6.c
|
||||
index 3fd5d46..51a9ccb 100644
|
||||
--- a/frontends/sfe/ecm_sfe_ipv6.c
|
||||
+++ b/frontends/sfe/ecm_sfe_ipv6.c
|
||||
@@ -256,13 +256,14 @@ struct ecm_db_node_instance *ecm_sfe_ipv6_node_establish_and_ref(struct ecm_fron
|
||||
struct net_device *master;
|
||||
master = ecm_interface_get_and_hold_dev_master(dev);
|
||||
DEBUG_ASSERT(master, "Expected a master\n");
|
||||
- ecm_interface_send_neighbour_solicitation(master, addr);
|
||||
+ ecm_interface_send_neighbour_solicitation(master, gw_addr);
|
||||
dev_put(master);
|
||||
} else {
|
||||
- ecm_interface_send_neighbour_solicitation(dev, addr);
|
||||
+ ecm_interface_send_neighbour_solicitation(dev, gw_addr);
|
||||
}
|
||||
|
||||
- DEBUG_TRACE("Failed to obtain mac for host " ECM_IP_ADDR_OCTAL_FMT "\n", ECM_IP_ADDR_TO_OCTAL(addr));
|
||||
+ DEBUG_TRACE("Failed to obtain mac for host " ECM_IP_ADDR_OCTAL_FMT " gw: " ECM_IP_ADDR_OCTAL_FMT "\n",
|
||||
+ ECM_IP_ADDR_TO_OCTAL(addr), ECM_IP_ADDR_TO_OCTAL(gw_addr));
|
||||
return NULL;
|
||||
}
|
||||
done:
|
||||
--
|
||||
cgit v1.1
|
||||
|
||||
@@ -0,0 +1,63 @@
|
||||
From 5b51ae2f1eca61c6f68e40a05333da5a362ff327 Mon Sep 17 00:00:00 2001
|
||||
From: Murat Sezgin <msezgin@codeaurora.org>
|
||||
Date: Mon, 13 Apr 2020 09:01:48 -0700
|
||||
Subject: [qca-nss-ecm] IPv6 solicitation fix with zero gateway address
|
||||
|
||||
The ECM function can find a zero gateway address for
|
||||
a host IP address. In this case, we need to use the
|
||||
host IP address while sending the solicitation request.
|
||||
|
||||
Signed-off-by: Murat Sezgin <msezgin@codeaurora.org>
|
||||
Change-Id: I1979834088ddfe1843566f51f64348f79e2df0fc
|
||||
---
|
||||
frontends/nss/ecm_nss_ipv6.c | 11 ++++++++++-
|
||||
frontends/sfe/ecm_sfe_ipv6.c | 11 ++++++++++-
|
||||
2 files changed, 20 insertions(+), 2 deletions(-)
|
||||
|
||||
diff --git a/frontends/nss/ecm_nss_ipv6.c b/frontends/nss/ecm_nss_ipv6.c
|
||||
index a05781b..9eb591c 100644
|
||||
--- a/frontends/nss/ecm_nss_ipv6.c
|
||||
+++ b/frontends/nss/ecm_nss_ipv6.c
|
||||
@@ -516,7 +516,16 @@ struct ecm_db_node_instance *ecm_nss_ipv6_node_establish_and_ref(struct ecm_fron
|
||||
return NULL;
|
||||
}
|
||||
|
||||
- DEBUG_TRACE("Have a gw address " ECM_IP_ADDR_OCTAL_FMT "\n", ECM_IP_ADDR_TO_OCTAL(gw_addr));
|
||||
+ /*
|
||||
+ * The found gateway address can be all zeros,
|
||||
+ * so in this case use the host address.
|
||||
+ */
|
||||
+ if (ECM_IP_ADDR_IS_NULL(gw_addr)) {
|
||||
+ DEBUG_TRACE("GW address is found as zeros, so use host IP\n");
|
||||
+ ECM_IP_ADDR_COPY(gw_addr, addr);
|
||||
+ } else {
|
||||
+ DEBUG_TRACE("Have a gw address " ECM_IP_ADDR_OCTAL_FMT "\n", ECM_IP_ADDR_TO_OCTAL(gw_addr));
|
||||
+ }
|
||||
|
||||
if (ecm_interface_mac_addr_get_no_route(dev, gw_addr, node_addr)) {
|
||||
DEBUG_TRACE("Found the mac address for gateway\n");
|
||||
diff --git a/frontends/sfe/ecm_sfe_ipv6.c b/frontends/sfe/ecm_sfe_ipv6.c
|
||||
index 51a9ccb..e609df7 100644
|
||||
--- a/frontends/sfe/ecm_sfe_ipv6.c
|
||||
+++ b/frontends/sfe/ecm_sfe_ipv6.c
|
||||
@@ -245,7 +245,16 @@ struct ecm_db_node_instance *ecm_sfe_ipv6_node_establish_and_ref(struct ecm_fron
|
||||
return NULL;
|
||||
}
|
||||
|
||||
- DEBUG_TRACE("Have a gw address " ECM_IP_ADDR_OCTAL_FMT "\n", ECM_IP_ADDR_TO_OCTAL(gw_addr));
|
||||
+ /*
|
||||
+ * The found gateway address can be all zeros,
|
||||
+ * so in this case use the host address.
|
||||
+ */
|
||||
+ if (ECM_IP_ADDR_IS_NULL(gw_addr)) {
|
||||
+ DEBUG_TRACE("GW address is found as zeros, so use host IP\n");
|
||||
+ ECM_IP_ADDR_COPY(gw_addr, addr);
|
||||
+ } else {
|
||||
+ DEBUG_TRACE("Have a gw address " ECM_IP_ADDR_OCTAL_FMT "\n", ECM_IP_ADDR_TO_OCTAL(gw_addr));
|
||||
+ }
|
||||
|
||||
if (ecm_interface_mac_addr_get_no_route(dev, gw_addr, node_addr)) {
|
||||
DEBUG_TRACE("Found the mac address for gateway\n");
|
||||
--
|
||||
cgit v1.1
|
||||
|
||||
@@ -0,0 +1,126 @@
|
||||
From e23eabd570eabde1d1fc803127a97fd101642467 Mon Sep 17 00:00:00 2001
|
||||
From: Varsha Mishra <varsham@codeaurora.org>
|
||||
Date: Fri, 12 Jun 2020 01:06:58 +0530
|
||||
Subject: [qca-nss-ecm] Allow egress on same port when bridge hairpin is
|
||||
enabled.
|
||||
|
||||
When bridge hairpin is enabled, allow egress on same port. Wi-Fi intrabss
|
||||
frames are getting exceptioned to stack. Bridge gets to make the decision
|
||||
whether these frames need to be forwarded or dropped.
|
||||
|
||||
Signed-off-by: Varsha Mishra <varsham@codeaurora.org>
|
||||
Change-Id: Ibdd72264d8887330ba0297ed12cbcfc390065bff
|
||||
---
|
||||
frontends/nss/ecm_nss_ipv4.c | 28 ++++++++++++++++++++++------
|
||||
frontends/nss/ecm_nss_ipv6.c | 28 ++++++++++++++++++++++------
|
||||
2 files changed, 44 insertions(+), 12 deletions(-)
|
||||
|
||||
diff --git a/frontends/nss/ecm_nss_ipv4.c b/frontends/nss/ecm_nss_ipv4.c
|
||||
index 60f799b..51c9ebf 100644
|
||||
--- a/frontends/nss/ecm_nss_ipv4.c
|
||||
+++ b/frontends/nss/ecm_nss_ipv4.c
|
||||
@@ -1756,7 +1756,9 @@ static unsigned int ecm_nss_ipv4_bridge_post_routing_hook(void *priv,
|
||||
* Case 2:
|
||||
* For routed packets the skb will have the src mac matching the bridge mac.
|
||||
* Case 3:
|
||||
- * If the packet was not local (case 1) or routed (case 2) then we process.
|
||||
+ * If the packet was not local (case 1) or routed (case 2) then
|
||||
+ * we process. There is an exception to case 2: when hairpin mode
|
||||
+ * is enabled, we process.
|
||||
*/
|
||||
|
||||
/*
|
||||
@@ -1768,14 +1770,28 @@ static unsigned int ecm_nss_ipv4_bridge_post_routing_hook(void *priv,
|
||||
dev_put(bridge);
|
||||
return NF_ACCEPT;
|
||||
}
|
||||
+
|
||||
+ /*
|
||||
+ * This flag needs to be checked in slave port(eth0/ath0)
|
||||
+ * and not on master interface(br-lan). Hairpin flag can be
|
||||
+ * enabled/disabled for ports individually.
|
||||
+ */
|
||||
if (in == out) {
|
||||
- DEBUG_TRACE("skb: %p, bridge: %p (%s), port bounce on %p (%s)\n", skb, bridge, bridge->name, out, out->name);
|
||||
- dev_put(in);
|
||||
- dev_put(bridge);
|
||||
- return NF_ACCEPT;
|
||||
+ if (!br_is_hairpin_enabled(in)) {
|
||||
+ DEBUG_TRACE("skb: %p, bridge: %p (%s), ignoring"
|
||||
+ "the packet, hairpin not enabled"
|
||||
+ "on port %p (%s)\n", skb, bridge,
|
||||
+ bridge->name, out, out->name);
|
||||
+ dev_put(in);
|
||||
+ dev_put(bridge);
|
||||
+ return NF_ACCEPT;
|
||||
+ }
|
||||
+ DEBUG_TRACE("skb: %p, bridge: %p (%s), hairpin enabled on port"
|
||||
+ "%p (%s)\n", skb, bridge, bridge->name, out, out->name);
|
||||
}
|
||||
+
|
||||
+ /*
|
||||
+ * Case 2: Routed trafffic would be handled by the INET post routing.
|
||||
+ */
|
||||
if (!ecm_mac_addr_equal(skb_eth_hdr->h_source, bridge->dev_addr)) {
|
||||
- /*
|
||||
- * Case 2: Routed trafffic would be handled by the INET post routing.
|
||||
- */
|
||||
DEBUG_TRACE("skb: %p, Ignoring routed packet to bridge: %p (%s)\n", skb, bridge, bridge->name);
|
||||
goto skip_ipv4_bridge_flow;
|
||||
}
|
||||
diff --git a/frontends/nss/ecm_nss_ipv6.c b/frontends/nss/ecm_nss_ipv6.c
|
||||
index 6ad425e..160c94c 100644
|
||||
--- a/frontends/nss/ecm_nss_ipv6.c
|
||||
+++ b/frontends/nss/ecm_nss_ipv6.c
|
||||
@@ -1498,7 +1498,9 @@ static unsigned int ecm_nss_ipv6_bridge_post_routing_hook(void *priv,
|
||||
* Case 2:
|
||||
* For routed packets the skb will have the src mac matching the bridge mac.
|
||||
* Case 3:
|
||||
- * If the packet was not local (case 1) or routed (case 2) then we process.
|
||||
+ * If the packet was not local (case 1) or routed (case 2) then
|
||||
+ * we process. There is an exception to case 2: when hairpin mode
|
||||
+ * is enabled, we process.
|
||||
*/
|
||||
|
||||
/*
|
||||
@@ -1510,14 +1512,28 @@ static unsigned int ecm_nss_ipv6_bridge_post_routing_hook(void *priv,
|
||||
dev_put(bridge);
|
||||
return NF_ACCEPT;
|
||||
}
|
||||
+
|
||||
+ /*
|
||||
+ * This flag needs to be checked in slave port(eth0/ath0)
|
||||
+ * and not on master interface(br-lan). Hairpin flag can be
|
||||
+ * enabled/disabled for ports individually.
|
||||
+ */
|
||||
if (in == out) {
|
||||
- DEBUG_TRACE("skb: %p, bridge: %p (%s), port bounce on %p (%s)\n", skb, bridge, bridge->name, out, out->name);
|
||||
- dev_put(in);
|
||||
- dev_put(bridge);
|
||||
- return NF_ACCEPT;
|
||||
+ if (!br_is_hairpin_enabled(in)) {
|
||||
+ DEBUG_TRACE("skb: %p, bridge: %p (%s), ignoring"
|
||||
+ "the packet, hairpin not enabled"
|
||||
+ "on port %p (%s)\n", skb, bridge,
|
||||
+ bridge->name, out, out->name);
|
||||
+ dev_put(in);
|
||||
+ dev_put(bridge);
|
||||
+ return NF_ACCEPT;
|
||||
+ }
|
||||
+ DEBUG_TRACE("skb: %p, bridge: %p (%s), hairpin enabled on port"
|
||||
+ "%p (%s)\n", skb, bridge, bridge->name, out, out->name);
|
||||
}
|
||||
+
|
||||
+ /*
|
||||
+ * Case 2: Routed trafffic would be handled by the INET post routing.
|
||||
+ */
|
||||
if (!ecm_mac_addr_equal(skb_eth_hdr->h_source, bridge->dev_addr)) {
|
||||
- /*
|
||||
- * Case 2: Routed trafffic would be handled by the INET post routing.
|
||||
- */
|
||||
DEBUG_TRACE("skb: %p, Ignoring routed packet to bridge: %p (%s)\n", skb, bridge, bridge->name);
|
||||
goto skip_ipv6_bridge_flow;
|
||||
}
|
||||
--
|
||||
cgit v1.1
|
||||
|
||||
Reference in New Issue
Block a user