RDKBNETWOR-80 : Transform to Nftables from Iptables#292
Open
vsai1990 wants to merge 8 commits into
Open
Conversation
Contributor
Contributor
|
b'## WARNING: A Blackduck scan failure has been waived A prior failure has been upvoted
|
snayak002c
requested changes
May 11, 2026
Reason for change: 1) Translate all the RDKB IPtables rules to nftables 2) write into /tmp/.nft and /tmp/.nft_v6 files and apply into netfilter 3) all the nftables rules are added under firewall_nft dir Test Procedure: RDKB Firewall functionality Risks: Medium
snayak002c
previously approved these changes
Jun 22, 2026
Contributor
There was a problem hiding this comment.
Pull request overview
This PR introduces an nftables-based firewall implementation alongside the existing iptables-based firewall, with build-time support (--enable-firewall-nft) and runtime selection via syscfg nft_enable.
Changes:
- Adds a new
source/firewall_nft/implementation (firewall + nfqueue handler + support headers) intended to generate/apply nftables rules. - Updates build system (autotools + Makefile conditionals) to optionally build the nftables firewall and to build the legacy firewall binary as
firewall_ipt. - Updates runtime launcher script and a utapi port-forwarding path to conditionally use nft vs iptables.
Reviewed changes
Copilot reviewed 14 out of 16 changed files in this pull request and generated 14 comments.
Show a summary per file
| File | Description |
|---|---|
| source/utapi/lib/utapi.c | Adds runtime switch to attempt nft rules for ephemeral port forwarding. |
| source/utapi/lib/Makefile.am | Adds -DNFT_ENABLE when FIREWALL_NFT is enabled. |
| source/scripts/init/service.d/service_firewall/firewall_log_handle.sh | Switches between legacy and nft firewall binaries based on syscfg nft_enable. |
| source/Makefile.am | Adds firewall_nft subdir when FIREWALL_NFT is enabled. |
| source/firewall/Makefile.am | Builds legacy firewall as firewall_ipt under FIREWALL_NFT. |
| source/firewall_nft/raw_socket_send.c | Adds raw packet send helper (copied from legacy). |
| source/firewall_nft/nfq_handler_nft.c | Adds nft-oriented nfqueue handler implementation. |
| source/firewall_nft/Makefile.am | Builds firewall_nft and an nfqueue handler binary. |
| source/firewall_nft/firewallnft.h | Adds nft firewall header/API surface. |
| source/firewall_nft/firewall_priv_nft.c | Adds nft versions of custom rule helpers. |
| source/firewall_nft/firewall_ipv6_nft.c | Adds nft IPv6 firewall rule generation. |
| source/firewall_nft/firewall_interface_nft.c | Adds weak stubs for platform hooks in nft firewall. |
| source/firewall_nft/firewall_ext_nft.c | Adds extender-mode nft firewall logic. |
| source/firewall_nft/firewall_custom.h | Adds nft firewall custom header and shared declarations/macros. |
| configure.ac | Adds --enable-firewall-nft configure option and generates source/firewall_nft/Makefile. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Comment on lines
+7637
to
+7638
| v_secure_system("nft %c rule ip nat prerouting_fromlan ip saddr %s ip daddr %s tcp dport %s counter dnat to %s:%s", | ||
| ciptableOprationCode,lan_ipaddr, external_dest_port, external_ip, toip, port_modifier); |
Comment on lines
+7692
to
+7693
| v_secure_system("nft %c rule ip filter wan2lan_forwarding_accept ip saddr %s ip daddr %s tcp dport %s counter jump xlog_accept_wan2la", | ||
| ciptableOprationCode,external_ip, toip, dport); |
Comment on lines
+7794
to
+7795
| v_secure_system("nft %c rule ip filter wan2lan_forwarding_accept ip saddr %s ip daddr %s udp dport %s counter jump xlog_accept_wan2la", | ||
| ciptableOprationCode,external_ip, toip, dport); |
Comment on lines
22
to
+26
| AM_LDFLAGS = -lccsp_common -lsecure_wrapper -lnetfilter_queue -lnfnetlink $(DBUS_LIBS) -pthread -lrt | ||
|
|
||
| if FIREWALL_NFT | ||
| bin_PROGRAMS = firewall_ipt nfq_handler | ||
| else |
Comment on lines
+222
to
+227
| v_secure_system("flush chain ip filter device_%u_container", insNum); | ||
|
|
||
| #if _NFQ_DEBUG_LEVEL == 1 | ||
| printf("system: add rule ip filter device_%u_container ip daddr %s jump wan2lan_dnsr_nfqueue_%u", insNum, ipAddr, insNum); | ||
| #endif | ||
| v_secure_system("add rule ip filter device_%u_container ip daddr %s jump wan2lan_dnsr_nfqueue_%u", insNum, ipAddr, insNum); |
Comment on lines
+469
to
+478
| if(nat_fp) { | ||
| fclose(nat_fp); | ||
| snprintf(fname, sizeof(fname), "/tmp/filter6_%x", ourpid); | ||
| unlink(fname); | ||
| } | ||
| if(filter_fp) { | ||
| fclose(filter_fp); | ||
| snprintf(fname, sizeof(fname), "/tmp/nat6_%x", ourpid); | ||
| unlink(fname); | ||
| } |
Comment on lines
+481
to
+487
| /* ipv4 */ | ||
| prepare_ipv4_firewall(filename1); | ||
| v_secure_system("nft -f /tmp/.ipt_ext 2> /tmp/.nftv4table_ext_error"); | ||
|
|
||
|
|
||
| prepare_ipv6_firewall(filename2); | ||
| v_secure_system("nft -f /tmp/.nft_v6 2> /tmp/.nftv6table_ext_error"); |
Comment on lines
+7718
to
+7720
| v_secure_system("nft %c rule ip nat prerouting_fromwan ip saddr %s ip daddr %s udp dport %s counter dnat to %s:%s", | ||
| ciptableOprationCode,natip4, external_dest_port, external_ip, toip, port_modifier); | ||
| } |
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Comment on lines
+7654
to
+7655
| v_secure_system("nft %c rule ip nat prerouting_fromlan ip saddr %s ip daddr %s tcp dport %s counter dnat to %s:%s", | ||
| ciptableOprationCode,natip4, external_dest_port, external_ip, toip, port_modifier); |
Comment on lines
+7670
to
+7671
| v_secure_system("nft %c rule ip nat postrouting_tolan ip saddr %s.0/%s ip daddr %s tcp dport %s counter snat to %s", | ||
| ciptableOprationCode,lan_3_octets, lan_netmask, toip, dport, lan_ipaddr); |
Comment on lines
+7692
to
+7693
| v_secure_system("nft %c rule ip filter wan2lan_forwarding_accept ip saddr %s ip daddr %s tcp dport %s counter jump xlog_accept_wan2la", | ||
| ciptableOprationCode,external_ip, toip, dport); |
Comment on lines
+7718
to
+7719
| v_secure_system("nft %c rule ip nat prerouting_fromwan ip saddr %s ip daddr %s udp dport %s counter dnat to %s:%s", | ||
| ciptableOprationCode,natip4, external_dest_port, external_ip, toip, port_modifier); |
Comment on lines
+7739
to
+7740
| v_secure_system("nft %c rule ip nat prerouting_fromlan ip saddr %s ip daddr %s udp dport %s counter dnat to %s:%s", | ||
| ciptableOprationCode,lan_ipaddr, external_dest_port, external_ip, toip, port_modifier); |
Comment on lines
+7757
to
+7758
| v_secure_system("nft %c rule ip nat prerouting_fromlan ip saddr %s ip daddr %s udp dport %s counter dnat to %s:%s", | ||
| ciptableOprationCode,natip4, external_dest_port, external_ip, toip, port_modifier); |
Comment on lines
+7773
to
+7774
| v_secure_system("nft %c rule ip nat postrouting_tolan ip saddr %s.0/%s ip daddr %s udp dport %s counter snat to %s", | ||
| ciptableOprationCode,lan_3_octets, lan_netmask, toip, dport, lan_ipaddr); |
Comment on lines
+7794
to
+7795
| v_secure_system("nft %c rule ip filter wan2lan_forwarding_accept ip saddr %s ip daddr %s udp dport %s counter jump xlog_accept_wan2la", | ||
| ciptableOprationCode,external_ip, toip, dport); |
Comment on lines
+273
to
+275
| fprintf(raw_fp, "*raw\n"); | ||
| do_raw_table_puma7(raw_fp); | ||
| #endif |
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Comment on lines
+7670
to
+7672
| v_secure_system("nft %c rule ip nat postrouting_tolan ip saddr %s.0/%s ip daddr %s tcp dport %s counter snat to %s", | ||
| ciptableOprationCode,lan_3_octets, lan_netmask, toip, dport, lan_ipaddr); | ||
| } |
Comment on lines
+7692
to
+7694
| v_secure_system("nft %c rule ip filter wan2lan_forwarding_accept ip saddr %s ip daddr %s tcp dport %s counter jump xlog_accept_wan2la", | ||
| ciptableOprationCode,external_ip, toip, dport); | ||
| } |
Comment on lines
+7718
to
+7720
| v_secure_system("nft %c rule ip nat prerouting_fromwan ip saddr %s ip daddr %s udp dport %s counter dnat to %s:%s", | ||
| ciptableOprationCode,natip4, external_dest_port, external_ip, toip, port_modifier); | ||
| } |
Comment on lines
+7739
to
+7741
| v_secure_system("nft %c rule ip nat prerouting_fromlan ip saddr %s ip daddr %s udp dport %s counter dnat to %s:%s", | ||
| ciptableOprationCode,lan_ipaddr, external_dest_port, external_ip, toip, port_modifier); | ||
| } |
Comment on lines
+2155
to
+2157
| if ((0 == strcmp("80", port)) || (0 == strcmp("443", port))) { | ||
| fprintf(fp, "add rule ip6 filter INPUT iifname \"%s \"tcp dport %s jump webui_limit\n", interface, port); | ||
| } |
Comment on lines
+53
to
+61
| #Enable NFT compile time flags if firewall-nft is set as yes | ||
| AC_ARG_ENABLE([firewall-nft], | ||
| [ --enable-firewall-nft=val Turn on nft Feature, val=true or false], | ||
| [case "${enableval}" in | ||
| yes) firewall_nft=true ;; | ||
| no) firewall_nft=false ;; | ||
| *) AC_MSG_ERROR([bad value ${enableval} for --enable-firewall-nft]) ;; | ||
| esac],[firewall_nft=false]) | ||
| AM_CONDITIONAL(FIREWALL_NFT, test x"$firewall_nft" = x"true") |
Comment on lines
+23
to
+31
| bin_PROGRAMS = firewall_nft nfq_handler | ||
|
|
||
| firewall_nft_SOURCES = firewall_nft.c firewall_ipv6_nft.c firewall_priv_nft.c firewall_interface_nft.c firewall_ext_nft.c | ||
| if CPC_FIREWALL_ENABLE | ||
| firewall_nft_SOURCES += firewall_lib.c firewall_dsl.c rabid.c | ||
| AM_LDFLAGS += -lrdkconfig | ||
| endif | ||
| nfq_handler_SOURCES = raw_socket_send.c nfq_handler_nft.c | ||
| firewall_nft_LDADD = $(top_builddir)/source/syscfg/lib/libsyscfg.la \ |
Comment on lines
+172
to
+179
| // Convert network address to string | ||
| char network_str[INET_ADDRSTRLEN]; | ||
| inet_ntop(AF_INET, &addr_network, network_str, INET_ADDRSTRLEN); | ||
|
|
||
| // Print the result in CIDR notation | ||
| printf("Network Address: %s/%d\n", network_str, mask_bits); | ||
| snprintf(subnet, len, "%s/%d", network_str, mask_bits); | ||
| } |
Comment on lines
+511
to
+515
| if ((get_ret == 0) && atoi(syscfg_value) == 1) | ||
| { | ||
| fprintf(fp, ":%s - [0:0]\n", IPOE_HEALTHCHECK); | ||
| fprintf(fp, "-I INPUT -j %s\n", IPOE_HEALTHCHECK); | ||
| } |
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
|
|
||
| #Enable NFT compile time flags if firewall-nft is set as yes | ||
| AC_ARG_ENABLE([firewall-nft], | ||
| [ --enable-firewall-nft=val Turn on nft Feature, val=true or false], |
Comment on lines
+831
to
+832
| fprintf(fp, "add rule ip6 filter input physdev in %s accept\n", emta_wan_ifname); | ||
| fprintf(fp, "add rule ip6 filter input physdev out %s accept\n", emta_wan_ifname); |
Comment on lines
+847
to
+848
| fprintf(fp, "add rule ip6 filter input iifname brlan0 ip6 daddr %s icmpv6 type echo-request drop\n", wanIPv6); | ||
| fprintf(fp, "add rule ip6 filter input iifname brlan0 ip6 daddr %s icmpv6 type echo-reply ip6 saddr %s state new,invalid,related drop\n", wanIPv6); // Echo reply |
Comment on lines
+945
to
+946
| fprintf(fp, "add rule ip6 filter INPUT ip6 saddr fe80::/64 ip6 daddr ff02::1/128 iifnot %s icmpv6 type router-advertisement limit rate 10/second accept\n", Interface[cnt]); // periodic RA | ||
| fprintf(fp, "add rule ip6 filter INPUT ip6 saddr fe80::/64 ip6 daddr fe80::/64 iifnot %s icmpv6 type router-advertisement limit rate 10/second accept\n", Interface[cnt]); // sollicited RA |
Comment on lines
+1091
to
+1092
| fprintf(fp, "add rule ip6 filter INPUT iifname %s udp dport 53 counter accept\n", Interface[cnt]); | ||
| fprintf(fp, "add rule ip6 filter INPUT iifname %s tcp dport 53 counter accept\n", Interface[cnt]); fprintf(fp, "add rule ip6 filter input iifname != %s ip6 protocol udp udp sport 53 accept\n", Interface[cnt]); |
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Comment on lines
+7646
to
+7660
| #ifdef NFT_ENABLE | ||
| if (atoi(nft_enable) == 0) | ||
| { | ||
| v_secure_system("iptables -t nat -%c prerouting_fromlan -p tcp -m tcp -d %s --dport %s -s %s -j DNAT --to-destination %s%s", | ||
| ciptableOprationCode,natip4, external_dest_port, external_ip, toip, port_modifier); | ||
| } | ||
| else | ||
| { | ||
| v_secure_system("nft %s rule ip nat prerouting_fromlan ip saddr %s ip daddr %s tcp dport %s counter dnat to %s%s", | ||
| (ciptableOprationCode == 'A') ? "add" : "delete", external_ip, natip4, external_dest_port, toip, port_modifier); | ||
| #else | ||
| v_secure_system("iptables -t nat -%c prerouting_fromlan -p tcp -m tcp -d %s --dport %s -s %s -j DNAT --to-destination %s%s", | ||
| ciptableOprationCode,natip4, external_dest_port, external_ip, toip, port_modifier); | ||
| #endif | ||
| } |
Comment on lines
+7661
to
+7674
| #ifdef NFT_ENABLE | ||
| if (atoi(nft_enable) == 0) | ||
| { | ||
| v_secure_system("iptables -t nat -%c postrouting_tolan -s %s.0/%s -p tcp -m tcp -d %s --dport %s -j SNAT --to-source %s", | ||
| ciptableOprationCode,lan_3_octets, lan_netmask, toip, dport, lan_ipaddr); | ||
| } | ||
| else | ||
| { | ||
| v_secure_system("nft %s rule ip nat postrouting_tolan ip saddr %s.0/%s ip daddr %s tcp dport %s counter snat to %s", | ||
| (ciptableOprationCode == 'A') ? "add" : "delete", lan_3_octets, lan_netmask, toip, dport, lan_ipaddr); | ||
| #else | ||
| v_secure_system("iptables -t nat -%c postrouting_tolan -s %s.0/%s -p tcp -m tcp -d %s --dport %s -j SNAT --to-source %s", | ||
| ciptableOprationCode,lan_3_octets, lan_netmask, toip, dport, lan_ipaddr); | ||
| #endif |
Comment on lines
+7766
to
+7770
| else | ||
| { | ||
| v_secure_system("nft %s rule ip nat postrouting_tolan ip saddr %s.0/%s ip daddr %s udp dport %s counter snat to %s", | ||
| (ciptableOprationCode == 'A') ? "add" : "delete", lan_3_octets, lan_netmask, toip, dport, lan_ipaddr); | ||
| #else |
Comment on lines
+53
to
+61
| #Enable NFT compile time flags if firewall-nft is set as yes | ||
| AC_ARG_ENABLE([firewall-nft], | ||
| [ --enable-firewall-nft=val Turn on nft Feature, val=true or false], | ||
| [case "${enableval}" in | ||
| yes) firewall_nft=true ;; | ||
| no) firewall_nft=false ;; | ||
| *) AC_MSG_ERROR([bad value ${enableval} for --enable-firewall-nft]) ;; | ||
| esac],[firewall_nft=false]) | ||
| AM_CONDITIONAL(FIREWALL_NFT, test x"$firewall_nft" = x"true") |
Comment on lines
+469
to
+478
| if(nat_fp) { | ||
| fclose(nat_fp); | ||
| snprintf(fname, sizeof(fname), "/tmp/filter6_%x", ourpid); | ||
| unlink(fname); | ||
| } | ||
| if(filter_fp) { | ||
| fclose(filter_fp); | ||
| snprintf(fname, sizeof(fname), "/tmp/nat6_%x", ourpid); | ||
| unlink(fname); | ||
| } |
Comment on lines
+398
to
+401
| /* These rules are needed to accept IPv6 traffic with HBH extension header and No-Next-Header option */ | ||
| /* To enable ipv6header module support need to set CONFIG_IP6_NF_MATCH_IPV6HEADER=m kernel config */ | ||
| fprintf(filter_fp,"-I FORWARD 1 -o erouter0 -m ipv6header --soft --header hop-by-hop -j ACCEPT\n"); | ||
| fprintf(filter_fp,"-I FORWARD 1 -o erouter0 -m ipv6header --soft --header hop-by-hop -j LOG --log-prefix \"UTOPIA: FW.IPv6 FORWARD Hop-by-Hop\" --log-level 6\n"); |
Comment on lines
+631
to
+633
| fprintf(fp, "insert rule ip6 filter FORWARD ip daddr %s iifname %s counter drop\n", cm_ipv6addr, lan_ifname); | ||
| fprintf(fp, "insert rule ip6 filter FORWARD ip daddr %s iifname brlan1 counter drop\n", cm_ipv6addr); | ||
| fprintf(fp, "insert rule ip6 filter FORWARD ip daddr %s iifname br106 counter drop\n", cm_ipv6addr); |
| } | ||
| else | ||
| { | ||
| fprintf(fp, "add rule ip6 filter input tcp dport 8080 drop\n"); |
Comment on lines
+2155
to
+2157
| if ((0 == strcmp("80", port)) || (0 == strcmp("443", port))) { | ||
| fprintf(fp, "add rule ip6 filter INPUT iifname \"%s \"tcp dport %s jump webui_limit\n", interface, port); | ||
| } |
snayak002c
approved these changes
Jul 2, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Reason for change:
Test Procedure: RDKB Firewall functionality
Risks: Medium