html/tordetect.pl
1 #!/usr/bin/perl
2 use strict;
3 use Irssi;
4 use Net::DNS;
5 use vars qw($VERSION %IRSSI);
6
7 $VERSION = "0.0.1";
8 %IRSSI = (
9 authors => "Sebastian 'yath' Schmidt",
10 contact => "yath+irssiscripts\@yath.de",
11 name => "Tor autodetection for Irssi",
12 description => "This script will automatically detect people using the ".
13 "Tor anonymity network and append \".TOR\" to their ".
14 "hostname, to make things like /ignore -time 3600 ".
15 "*!*\@*.TOR possible (e.g. when your favourite ".
16 "channel gets flooded).",
17 license => "Public domain"
18 );
19
20 use constant {
21 HOSTSUFFIX => ".TOR",
22 DNSBL => "tor-irc.dnsbl.oftc.net",
23 CACHETIME => 3600,
24 };
25
26 my %cache;
27
28 sub resolve_host($) {
29 my $hostname = shift;
30 return $hostname if "$hostname." =~ (/^(\d{1,3}\.){4}$/); # yes, that sucks
31
32 my $res = Net::DNS::Resolver->new();
33 my $q = $res->search($hostname, "A");
34 return unless $q;
35 return map { $_->address } grep { $_->type eq "A" } $q->answer;
36 }
37
38 sub reverse_addr($) {
39 return join(".", reverse(split(/\./, $_[0])));
40 }
41
42 sub istor($) {
43 my $hostname = shift;
44 if (exists($cache{$hostname})) {
45 if (time >= $cache{$hostname}->[0]) {
46 delete $cache{$hostname};
47 } else {
48 return $cache{$hostname}->[1];
49 }
50 }
51
52 my $result = 0;
53
54 foreach my $addr (resolve_host($hostname)) {
55 if (grep /^127\.0\.0\.1$/,
56 resolve_host(reverse_addr($addr).".".DNSBL)) {
57 $result = 1;
58 last;
59 }
60 }
61
62 $cache{$hostname} = [time+CACHETIME, $result];
63 return $result;
64 }
65
66 sub handler_server_event {
67 my ($server, $data, $sender_nick, $sender_addr) = @_;
68 return unless ($sender_nick ne "" and $sender_addr =~ /.+@(.+)/);
69 $sender_addr .= HOSTSUFFIX if istor($1);
70 Irssi::signal_continue($server, $data, $sender_nick, $sender_addr);
71 }
72
73 Irssi::signal_add("server event", \&handler_server_event);