xref: /freebsd/contrib/blocklist/README (revision 06c3fb2749bda94cb5201f81ffdb8fa6c3161b2e)
1# $NetBSD: README,v 1.8 2017/04/13 17:59:34 christos Exp $
2
3This package contains library that can be used by network daemons to
4communicate with a packet filter via a daemon to enforce opening and
5closing ports dynamically based on policy.
6
7The interface to the packet filter is in libexec/blacklistd-helper
8(this is currently designed for npf) and the configuration file
9(inspired from inetd.conf) is in etc/blacklistd.conf.
10
11On NetBSD you can find an example npf.conf and blacklistd.conf in
12/usr/share/examples/blacklistd; you need to adjust the interface
13in npf.conf and copy both files to /etc; then you just enable
14blacklistd=YES in /etc/rc.conf, start it up, and you are all set.
15
16There is also a startup file in etc/rc.d/blacklistd
17
18Patches to various daemons to add blacklisting capabilitiers are in the
19"diff" directory:
20    - OpenSSH: diff/ssh.diff [tcp socket example]
21    - Bind: diff/named.diff [both tcp and udp]
22    - ftpd: diff/ftpd.diff [tcp]
23
24These patches have been applied to NetBSD-current.
25
26The network daemon (for example sshd) communicates to blacklistd, via
27a unix socket like syslog. The library calls are simple and everything
28is handled by the library. In the simplest form the only thing the
29daemon needs to do is to call:
30
31	blacklist(action, acceptedfd, message);
32
33Where:
34	action = 0 -> successful login clear blacklist state
35		 1 -> failed login, add to the failed count
36	acceptedfd -> the file descriptor where the server is
37		      connected to the remote client. It is used
38		      to determine the listening socket, and the
39		      remote address. This allows any program to
40		      contact the blacklist daemon, since the verification
41		      if the program has access to the listening
42		      socket is done by virtue that the port
43		      number is retrieved from the kernel.
44	message    -> an optional string that is used in debugging logs.
45
46Unfortunately there is no way to get information about the "peer"
47from a udp socket, because there is no connection and that information
48is kept with the server. In that case the daemon can provide the
49peer information to blacklistd via:
50
51	blacklist_sa(action, acceptedfd, sockaddr, sockaddr_len, message);
52
53The configuration file contains entries of the form:
54
55# Blacklist rule
56# host/Port	type	protocol	owner	name	nfail	disable
57192.168.1.1:ssh	stream	tcp		*	-int	10	1m
588.8.8.8:ssh	stream	tcp		*	-ext	6	60m
59ssh		stream	tcp6		*	*	6	60m
60http		stream	tcp		*	*	6	60m
61
62Here note that owner is * because the connection is done from the
63child ssh socket which runs with user privs. We treat ipv4 connections
64differently by maintaining two different rules one for the external
65interface and one from the internal We also register for both tcp
66and tcp6 since those are different listening sockets and addresses;
67we don't bother with ipv6 and separate rules. We use nfail = 6,
68because ssh allows 3 password attempts per connection, and this
69will let us have 2 connections before blocking. Finally we block
70for an hour; we could block forever too by specifying * in the
71duration column.
72
73blacklistd and the library use syslog(3) to report errors. The
74blacklist filter state is persisted automatically in /var/db/blacklistd.db
75so that if the daemon is restarted, it remembers what connections
76is currently handling. To start from a fresh state (if you restart
77npf too for example), you can use -f. To watch the daemon at work,
78you can use -d.
79
80The current control file is designed for npf, and it uses the
81dynamic rule feature. You need to create a dynamic rule in your
82/etc/npf.conf on the group referring to the interface you want to block
83called blacklistd as follows:
84
85ext_if=bge0
86int_if=sk0
87
88group "external" on $ext_if {
89	...
90        ruleset "blacklistd-ext"
91        ruleset "blacklistd"
92	...
93}
94
95group "internal" on $int_if {
96	...
97        ruleset "blacklistd-int"
98	...
99}
100
101You can use 'blacklistctl dump -a' to list all the current entries
102in the database; the ones that have nfail <c>/<t> where <c>urrent
103>= <t>otal, should have an id assosiated with them; this means that
104there is a packet filter rule added for that entry. For npf, you
105can examine the packet filter dynamic rule entries using 'npfctl
106rule <rulename> list'.  The number of current entries can exceed
107the total. This happens because entering packet filter rules is
108asynchronous; there could be other connection before the rule
109becomes activated.
110
111Enjoy,
112
113christos
114