OpenBSD PacketFilter
The proposed way to ban IPs using openBSD pf uses one t_reaction
table.
We first need to create this table on our main /etc/pf.conf
file.
table <t_reaction> persist
The IPs are banned on all ports, meaning banned IPs won't be able to connect on any service.
Start/Stop
There is no specific action taken on start. On stop, all IP address contained in 't_reaction' will be flushed
start: [
],
stop: [
['pfctl', '-t', 't_reaction', '-T', 'flush', '<ip>'],
],
Ban/Unban
Then, in reaction.conf
file, we need to specify pfctl
behaviour and alter ban
and unban
command
local iptables(args) = [ 'pfctl'] + args;
local banFor(time) = {
ban: {
cmd: ['pfctl', '-t', 't_reaction', '-T', 'add', '<ip>'],
},
unban: {
after: time,
cmd: ['pfctl', '-t', 't_reaction', '-T', 'del', '<ip>'],
},
};
See how to merge different actions in JSONnet FAQ
Real-world example
local banFor(time) = {
ban: {
cmd: ['pfctl', '-t', 't_reaction', '-T', 'add', '<ip>'],
},
unban: {
after: time,
cmd: ['pfctl', '-t', 't_reaction', '-T', 'del', '<ip>'],
},
};
{
patterns: {
ip: {
regex: @'(?:(?:[ 0-9 ]{1,3}\.){3}[0-9]{1,3})|(?:[0-9a-fA-F:]{2,90})',
},
},
start: [
],
stop: [
['pfctl', '-t', 't_reaction', '-T', 'flush', '<ip>'],
],
streams: {
ssh: {
cmd: [ 'tail', '-n0', '-f', '/var/log/authlog' ],
filters: {
failedlogin: {
regex: [
// Auth fail
@'Failed password for invalid user .* from <ip>',
// Client disconnects during authentication
@'Disconnected from invalid user .* <ip>',
],
retry: 3,
retryperiod: '6h',
actions: banFor('48h'),
},
},
},
},
}