9fans - fans of the OS Plan 9 from Bell Labs
 help / color / mirror / Atom feed
* banishment of nuisance IP addresses
@ 2019-10-29  9:13 Steve Simon
  2019-10-29  9:56 ` [9fans] " hiro
  0 siblings, 1 reply; 2+ messages in thread
From: Steve Simon @ 2019-10-29  9:13 UTC (permalink / raw)
  To: 9fans

[-- Attachment #1: Type: text/plain, Size: 1308 bytes --]

Hi all,

I still run a plan9 server attached to the net. I have always
had attacks from bots, viruses, script kiddies etc. and decided
to do something to reduce the load on my system - some attacks can be
quite persistant.

I have taken the idea from the linux log2ban script but I implemented it
a rather differently. 

I added two functions to libsec (for want of a better place), nuisance()
and banished(). the former allows you to log a failed authentication attempt,
dropped TLS connection etc. the latter tests for too many failures and drops
connections from repeat offenders.

nuisance() adds a single character (indicating the type of failure, 't' for TLS drop,
'a' for authentication failure etc), to an append only file in /lib/ndb/banished
named with the source IP address that is connecting. if that file gets too long
the address is becomes persona non-grata.

I have a cron jonb that deletes banishment files that have not been modified for a month
on the basis that hackers and bots get rounded up eventually.

I added these calls to dnstcp, listen, tlssrv, imap4d, httpd, smtpd, and secstored.
This is enough to cover all the network listners I have, and it works well, but feels
a little crude. I would be interested if anyone has a more elegant solution.

-Steve

[-- Attachment #2: banished.c --]
[-- Type: text/plain, Size: 1041 bytes --]

#include <u.h>
#include <libc.h>

static char *bandir = "/lib/ndb/banished";

/* Log that this ipaddr, (or ipaddr!port) may be causing a nuisance */
int
nuisance(char *addr, char c)
{
	int fd, len;
	char *p, *path;

	if(!addr || !*addr)
		return -1;

	len = strlen(addr);
	if((p = strchr(addr, '!')) != nil)
		len = p - addr;

	path = smprint("%s/%.*s", bandir, len, addr);
	if((fd = open(path, OWRITE)) == -1)
		fd = create(path, OWRITE, 0666|DMAPPEND);
	free(path);

	if(fd == -1){
		return -1;
	}

	write(fd, &c, 1);
	close(fd);
	return 0;
}

/* Has this ipaddr, (or ipaddr!port) caused too much of a nuisance */
int
banished(char *addr, int thresh)
{
	Dir *d;
	int n, len;
	char *p, *path;

	if(!addr || !*addr)
		return 0;

	len = strlen(addr);
	if((p = strchr(addr, '!')) != nil)
		len = p - addr;

	path = smprint("%s/%.*s", bandir, len, addr);
	d = dirstat(path);
	free(path);

	if(d == nil)
		return 0;
	n = d->length;
	free(d);

	if(n < thresh)
		return 0;
	return 1;
}

^ permalink raw reply	[flat|nested] 2+ messages in thread

* Re: [9fans] banishment of nuisance IP addresses
  2019-10-29  9:13 banishment of nuisance IP addresses Steve Simon
@ 2019-10-29  9:56 ` hiro
  0 siblings, 0 replies; 2+ messages in thread
From: hiro @ 2019-10-29  9:56 UTC (permalink / raw)
  To: 9fans

from just your description i like how you rely on the filesystem to
store the state, which seems to make it trivial to split multiple
tasks into multiple programs :)

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2019-10-29  9:56 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2019-10-29  9:13 banishment of nuisance IP addresses Steve Simon
2019-10-29  9:56 ` [9fans] " hiro

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).