Page MenuHomeVyOS Platform

New Firewall Implementation - proposed changes on group implementation
Needs testing, Requires assessmentPublicBUG

Description

On new firewall implementation, while defining groups via "set firewall group", seems they are defined as a variable, and then, when creating a rule using this group, it uses it's value.
For example:

set firewall group network-group NG-01 description 'Network Group 01'
set firewall group network-group NG-01 network '198.51.100.0/24'
set firewall group network-group NG-01 network '203.0.113.0/24'

set firewall name FW01 rule 10 action accept
set firewall name FW01 rule 10 source group network-group NG-01

set interface eth eth0 firewall in name FW01

Result of previous commands in firewall:

[email protected]# sudo nft list table ip filter
table ip filter {
	chain VYOS_FW_FORWARD {
		type filter hook forward priority filter; policy accept;
		iifname "eth0" counter packets 0 bytes 0 jump FW01
		jump VYOS_POST_FW
	}

	chain VYOS_FW_LOCAL {
		type filter hook input priority filter; policy accept;
		jump VYOS_POST_FW
	}

	chain VYOS_FW_OUTPUT {
		type filter hook output priority filter; policy accept;
		jump VYOS_POST_FW
	}

	chain VYOS_POST_FW {
		return
	}

	chain VYOS_FRAG_MARK {
		type filter hook prerouting priority -450; policy accept;
		ip frag-off & 16383 != 0 meta mark set 0x000ffff1 return
	}

	chain FW01 {
		ip saddr { 198.51.100.0/24, 203.0.113.0/24 } counter packets 0 bytes 0 return comment "FW01-10"
		return
	}
}

As we can see, there are no reference in nft for the network group that was created. In old implementation of firewall, ipset was used in this cases, and result of the chain FW01 and ipset -L is as follows:

	chain FW01 {
		# match-set NG-01 src counter packets 0 bytes 0 return comment "FW01-10"
		counter packets 0 bytes 0 drop comment "FW01-10000 default-action drop"
	}
}
[edit]
[email protected]# sudo ipset -L
Name: NG-01
Type: hash:net
Revision: 6
Header: family inet hashsize 1024 maxelem 65536
Size in memory: 576
References: 1
Number of entries: 2
Members:
203.0.113.0/24
198.51.100.0/24

For new implementation, I would suggest using the utility "sets" from nftables.
So, when creating previous group, will generate a new set in nftables. For example:

# VyOS commands - Creating a network-group
set firewall group network-group NG-01 description 'Network Group 01'
set firewall group network-group NG-01 network '198.51.100.0/24'
set firewall group network-group NG-01 network '203.0.113.0/24'
# VyOS commands - Creating a firewall rule using group
set firewall name FW01 rule 10 action accept
set firewall name FW01 rule 10 source group network-group NG-01

# Should be translated to next nft commands:
# Create set for network address group
sudo nft add set ip filter NG-01 { type ipv4_addr\; comment \"Network Group 01\" \; flags interval \;}
sudo nft add element ip filter NG-01 { 198.51.100.0/24 }
sudo nft add element ip filter NG-01 { 203.0.113.0/24 }
# Create firewall rule, using previous set, should look something like this
sudo nft 'add rule ip filter FW01 ip saddr @NG-01 counter return comment "FW01-10"

Then table ip filter will look something like this:

[email protected]# sudo nft list table ip filter
table ip filter {
	set NG-01 {
		type ipv4_addr
		flags interval
		comment "Network Group 01"
		elements = { 198.51.100.0/24, 203.0.113.0/24 }
	}

	chain VYOS_FW_FORWARD {
		type filter hook forward priority filter; policy accept;
		jump VYOS_POST_FW
	}

	chain VYOS_FW_LOCAL {
		type filter hook input priority filter; policy accept;
		jump VYOS_POST_FW
	}

	chain VYOS_FW_OUTPUT {
		type filter hook output priority filter; policy accept;
		jump VYOS_POST_FW
	}

	chain VYOS_POST_FW {
		return
	}

	chain VYOS_FRAG_MARK {
		type filter hook prerouting priority -450; policy accept;
		ip frag-off & 16383 != 0 meta mark set 0x000ffff1 return
	}

	chain FW01 {
		ip saddr @NG-01 counter packets 0 bytes 0 return comment "FW01-10"
	}
}

Advantages:

  • Example was setup for networks, but its also applicable for addresses, ports and also protocols. More reference in the provided.
  • Easier for debugging firewall. Thinking in firewall where there are lots of address|networks|ports groups, with actual configuration, it won't be easy/clear to find desired groups while listing nft tables.
  • Solution more atomic. While using nft commands, you get full configuration, making easy to find definitions of groups|sets.

Details

Difficulty level
Unknown (require assessment)
Version
vyos-1.4-rolling-202201060842
Why the issue appeared?
Will be filled on close
Is it a breaking change?
Unspecified (possibly destroys the router)
Issue type
Improvement (missing useful functionality)

Event Timeline

I was not aware that the nft implementation changes the kind of how groups are used.
We have implemented a blacklisting approach which heavily relates on using ipset because no one wants to have hundred thousand of addresses in the config file.
So I think this is essential, at least for us.

Yeah I discovered the same in forums:

https://forum.vyos.io/t/support-for-nftables-named-sets/8670

Might be some work to change the nft method from anonymous to named...

sdev changed the task status from Open to In progress.Mon, Jun 13, 12:11 PM
sdev claimed this task.

Working on moving groups to named set as part of a refactor in some firewall code.

Initial implementation used anonymous sets because it was easy to reference a single definition in rules regardless of table (filter, mangle etc.) and needed no extra logic to cleanup.

sdev changed the task status from In progress to Needs testing.Wed, Jun 15, 1:33 PM
sdev moved this task from Need Triage to In Progress on the VyOS 1.4 Sagitta board.