| Age | Commit message (Collapse) | Author |
|
This change re-implements the intended behaviour from T4180 aswell as from
T4506, it ensures that both the vrf-member interface aswell as the vrf itself
is added as an oifname -> meaning that traffic traversing and originating from
withing VyOS is matches outbound.
Changes done by c-po:
* re-sort dependency list to keep diff low
* vyos.configdict.is_vrf_changed() should return early and not carry
over the to-be return value
* keep common coding style (dict by . separation) in nftables-zone.j2
Co-authored-by: Christian Breunig <christian@breunig.cc>
|
|
|
|
Three related bugs prevented GeoIP nftables sets from being populated
correctly at boot and when incrementally modifying firewall or policy
route rules.
1. geoip_updated() always returned False
The previous implementation called node_changed() and then searched
the result with dict_search_recursive(changes, 'geoip'). This could
never match: node_changed() is annotated `-> list` and returns a flat
list of the immediate top-level child names whose subtree changed
(e.g. ['ipv4'] for the firewall path, or route names for policy
route). The 'geoip' key sits several levels deeper than those names,
so dict_search_recursive — which only walks dicts and lists for a
matching dict key — never yielded a hit, and geoip_updated() always
returned False. As a consequence, geoip_update() was never triggered
by an incremental add or change of a GeoIP rule; the only path that
ever populated /run/nftables-geoip.conf was the explicit \"update
geoip\" command or the fallback when geoip_refresh() failed.
Fix: bypass node_changed() and call get_config_diff() /
get_child_nodes_diff() directly with expand_nodes=Diff.ADD|Diff.DELETE
and recursive=True. In that mode, the 'add' and 'delete' values in
the returned dict are full nested subtrees of the config diff, so
dict_search_recursive correctly finds 'geoip' wherever it appears in
the change set.
2. GeoIP block executed unconditionally, breaking the boot sequence
geoip_sets() always returns {'name': [], 'ipv6_name': []}. A
non-empty dict is truthy in Python regardless of whether its values
are empty lists, so the guards \"if geoip_sets:\" and
\"if 'name' in geoip_sets:\" were always True.
On boot, when policy_route.py is invoked as a dependent of
firewall.py (triggered by group_resync), it entered the GeoIP block
even with no policy route GeoIP rules configured. Because
/run/nftables-geoip.conf did not yet exist, geoip_refresh() returned
False and geoip_update(policy=policy) was called with an empty
policy. This created /run/nftables-geoip.conf containing only empty
table stubs. When firewall.py subsequently called geoip_refresh(),
the file existed and nft loaded it successfully — so the
geoip_update(firewall) call was never reached and the firewall GeoIP
sets stayed empty for the entire uptime of the router.
Fix: check the actual list contents instead of the container dict:
if geoip_sets['name'] or geoip_sets['ipv6_name'].
3. geoip_update() clobbered the other caller's sets
geoip_update() renders /run/nftables-geoip.conf from both
firewall_sets and policy_sets in a single pass. When called with
only one argument (as firewall.py and policy_route.py each do), the
other argument defaulted to None and that half of the file was
rendered empty, erasing whatever the other script had written. The
geoip-update helper used by \"update geoip\" and the weekly cron was
unaffected because it always passes both arguments, which masked
this bug in normal manual operation.
Fix: when either argument is absent, read the missing config from
the live Config session before building the set tables, so every
invocation writes the complete combined firewall + policy file.
|
|
* Add warning when defining `offload-target` without setting action to `offload`
|
|
|
|
* Move core logic to separate vyos.geoip module
* Use a sqlite database for storing and querying address ranges by country
* Remove downloaded geoip ranges once loaded into sqlite db
* No longer rebuild geoip sets on each commit unless necessary
* Allows for extensibility using other geoip data vendors
|
|
firewall: T7739: Default ruleset for firewall zones
|
|
Prevent `KeyError` by safely handling missing 'member' dict in zone config.
Add smoketest to verify commit fails gracefully when zone has no interfaces.
|
|
In large networks with many zones where simple allow/deny rules are not sufficient,
zones become tedious to manage. Many use cases can be simplified by providing an
ability to define a default ruleset for traffic from other zones. This change proposes
adding the follwing syntax:
set firewall zone <name> default_firewall name <name>
set firewall zone <name> default_firewall ipv6_name <name>
The proposed behavior is the following:
local in:
The default firewall ruleset for the local zone will be appended after all
from configurations.
local out:
If a non-local zone does not have a from local ruleset but does have a
default_firewall ruleset, the default_firewall ruleset will be appended using
oifname
forward:
The default firewall ruleset for the zone will be appended after all from
configurations
To keep the behavior consistent with from ruleset configurations, a return is appended
after the default_firewall ruleset.
The proposed behavior differs slightly from the default_policy configuration for the
local out chains. The default_policy applied in the out templates comes from the local
zone, not the actual outbound zone. The proposed change does not amend this, but does
make default_firewall logically consistent with the intent of the out rules.
|
|
- Added command to disable conntrack per firewall chain
- Added test_disable_conntrack_per_chain function to smoketest
|
|
Added checks in the verify_rule() function of firewall.py for empty nodes.
Added migration script 19-to-20 to remove empty nodes from the config.
|
|
The legal team says years are not necessary so we can go ahead with it, since
it will simplify backporting.
Automatically removed using: git ls-files | grep -v libvyosconfig | xargs sed -i -E \
's/^# Copyright (19|20)[0-9]{2}(-[0-9]{4})? VyOS maintainers.*/# Copyright VyOS maintainers and contributors <maintainers@vyos.io>/g'
In addition we will error-out during "make" if someone re-adds a legacy
copyright notice
|
|
wireguard: T7387: Optimise wireguard peer handling
|
|
|
|
firewall: T7358: add offload option to global state policy
|
|
Since the jump to the global state chain is inserted before all rules,
it wasn't possible to use offload with the global state policies
This commit adds a new chain for offloaded traffic in the forward
chain and jumps to that chain. Please enter the commit message for your changes. Lines starting
|
|
|
|
|
|
Improve config parsing for ZBF when using VRFs and interfaces attached to VRFs
|
|
interfaces attached to VRFs
|
|
* op-mode: T6983: add "show log" and "monitor log" commands for vyos-domain-resolver
* firewall: T6983: drop unused variable domain_resolver_usage_nat
* T6983: introduce Python logging module in vyos-domain-resolver
* T6983: treat vyos-domain-resolver as a real service
|
|
|
|
The function verify_interface_exists requires a reference to the ambient
config_dict rather than creating an instance. As access is required to
the 'interfaces' path, provide as attribute of class ConfigDict, so as
not to confuse path searches of script-specific config_dict instances.
|
|
* Only matching flags and fields used by modern RFC2890 "extended GRE" -
this is backwards-compatible, but does not match all possible flags.
* There are no nftables helpers for the GRE key field, which is critical
to match individual tunnel sessions (more detail in the forum post)
* nft expression syntax is not flexible enough for multiple field
matches in a single rule and the key offset changes depending on flags.
* Thus, clumsy compromise in requiring an explicit match on the "checksum"
flag if a key is present, so we know where key will be. In most cases,
nobody uses the checksum, but assuming it to be off or automatically
adding a "not checksum" match unless told otherwise would be confusing
* The automatic "flags key" check when specifying a key doesn't have similar
validation, I added it first and it makes sense. I would still like
to find a workaround to the "checksum" offset problem.
* If we could add 2 rules from 1 config definition, we could match
both cases with appropriate offsets, but this would break existing
FW generation logic, logging, etc.
* Added a "test_gre_match" smoketest
|
|
prerouting chain; re introduce <set vrf> in policy; change global options for passing traffic to IPvX firewall; update smoketest
|
|
wrong. Use nft -c option to check temporary file, and use output provided by nftables to parse the error if possible, or print it as it is if it's an unknown error
|
|
(#3616)
* Change ipsec match-ipsec/none to match-ipsec-in and match-none-in for
fw rules
* Add ipsec match-ipsec-out and match-none-out
* Change all the points where the match-ipsec.xml.i include was used
before, making sure the new includes (match-ipsec-in/out.xml.i) are
used appropriately. There were a handful of spots where match-ipsec.xml.i
had snuck back in for output hooked chains already
(the common-rule-* includes)
* Add the -out generators to rendered templates
* Heavy modification to firewall config validators:
* I needed to check for ipsec-in matches no matter how deeply nested
under an output-hook chain(via jump-target) - this always generates
an error.
* Ended up retrofitting the jump-targets validator from root chains
and for named custom chains. It checks for recursive loops and improper
IPsec matches.
* Added "test_ipsec_metadata_match" and "test_cyclic_jump_validation"
smoketests
|
|
With commit 770edf016838 ("T3900: T6394: extend functionalities in firewall;
move netfilter sysctl timeout parameters defined in conntrack to firewall
global-opton section.") the import of the glob module is no longer
required.
Found my running: make unused-imports
|
|
timeout parameters defined in conntrack to firewall global-opton section.
|
|
|
|
to firewall global-optinos
|
|
|
|
|
|
firewall|nat rules.
|
|
We will use _ as CLI level divider. The XML definition filename and also
the Python helper should match the CLI node.
Example:
set interfaces ethernet -> interfaces_ethernet.xml.in
set interfaces bond -> interfaces_bond.xml.in
set service dhcp-server -> service_dhcp-server-xml.in
|
|
node_changed() will return a list of changed keys under "path". We are not
always interested what changed, sometimes we are only interested if something
changed at all, that what vyos.configdict.is_node_changed() is for.
|
|
<enable|disable> commands; log and state moved to new syntax.
|
|
(valid for interfaces and groups) in firewal, nat and nat66.
|
|
|
|
|
|
Add ability to SYNPROXY connections
It is useful to protect against TCP SYN flood attacks and port-scanners
set firewall global-options syn-cookies 'enable'
set firewall ipv4 input filter rule 10 action 'synproxy'
set firewall ipv4 input filter rule 10 destination port '22'
set firewall ipv4 input filter rule 10 inbound-interface interface-name 'eth1'
set firewall ipv4 input filter rule 10 protocol 'tcp'
set firewall ipv4 input filter rule 10 synproxy tcp mss '1460'
set firewall ipv4 input filter rule 10 synproxy tcp window-scale '7'
|
|
supports HW flowtable offload
- Add required offload setting for interfaces + flowtable offload (hw-tc-offload)
- Verification of interface support for hardware offloaded flowtables
|
|
`set firewall flowtable <name> interface <ifname>`
`set firewall flowtable <name> offload [software|hardware]`
`set firewall [ipv4|ipv6] forward filter rule N action offload`
`set firewall [ipv4|ipv6] forward filter rule N offload-target <name>`
|
|
firewall, nat, nat66
|
|
The following commands will enable nftables flowtable offload on interfaces eth0 eth1:
```
set firewall global-options flow-offload software interface <name>
set firewall global-options flow-offload hardware interface <name>
```
Generated nftables rules:
```
table inet vyos_offload {
flowtable VYOS_FLOWTABLE_software {
hook ingress priority filter - 1; devices = { eth0, eth1, eth2, eth3 };
counter
}
chain VYOS_OFFLOAD_software {
type filter hook forward priority filter - 1; policy accept;
ct state { established, related } meta l4proto { tcp, udp } flow add @VYOS_FLOWTABLE_software
}
}
```
Use this option to count packets and bytes for each offloaded flow:
```
set system conntrack flow-accounting
```
To verify a connection is offloaded, run
```
cat /proc/net/nf_conntrack|grep OFFLOAD
```
This PR follows firewalld's implementation: https://github.com/firewalld/firewalld/blob/e748b97787d685d0ca93f58e8d4292e87d3f0da6/src/firewall/core/nftables.py#L590
A good introduction to nftables flowtable: https://thermalcircle.de/doku.php?id=blog:linux:flowtables_1_a_netfilter_nftables_fastpath
|
|
|
|
firewall: T3509: Add support for IPv6 reverse path filtering
|
|
interface-name or interface-group
|
|
|
|
|