#!/usr/bin/env python # -*- encoding: iso-8859-1 -*- # # Copyright (c) 2008 Bourdon "delroth" Pierre # Copyright (c) 2008 Mickael Thomas import IRCLib import string, random, sys, time from threading import Timer PWD = '' ADMIN = 'mickael.is-a-geek.net' CHANNEL_PATTERN = '#ipbot.%d' CHANNELS = {} PATTERNS = ( ('%d??', 1, 3), ('?%d?', 10), ('??%d', 10), ('%d?', 10), ('?%d', 10) ) class CIMask(object): """Pour dsl.club-internet.fr, fbx.proxad.net""" def __init__(self): self.ip = [" "] * 4 def works(self, banmask): return banmask.endswith('.???.??????*.??*') and banmask.startswith('?????-?') def generate_bans_list(self): l = [] for i in xrange(4): deb = '?????-?' + (i * '-*') fin = (3 - i) * '-*' + '.???.??????*.??*' for pattern in PATTERNS: for j in xrange(*pattern[1:]): l.append(deb + '-' + pattern[0] % j + fin) return l def analyze_ban(self, b): b = b[12:][:-16] ip = b.split('-') print b, ip for i,a in enumerate(ip): if a == '*': continue elif len(a) == 2: a = "?" + a for j,c in enumerate(a): if c == '?': continue else: self.ip[i] = self.ip[i][:j] + c + self.ip[i][j+1:] def return_ip(self): return '.'.join([i.strip() for i in self.ip]) class WanadooMask(object): """Pour abo.wanadoo.fr""" def __init__(self): self.ip = [" "] * 4 def works(self, banmask): return banmask.endswith('.abo.wanadoo.fr') def generate_bans_list(self): l = [] debut = 'A*-*-1-' fin = '.abo.wanadoo.fr' milieux = ['%s-*.w*-*', '*-%s.w*-*', '*-*.w%s-*', '*-*.w*-%s'] for m in milieux: for pattern in PATTERNS: for j in xrange(*pattern[1:]): l.append(debut + (m % (pattern[0] % j)) + fin) return l def analyze_ban(self, b): b = b[11:][:-15] ip_ = b.split('-') ip = [] print b, ip_ ip.append(ip_[1].split('.')[0]) ip.append(ip_[1].split('.')[1][1:]) ip.append('???') ip.append(ip_[0]) print b, ip for i,a in enumerate(ip): if a == '*': continue elif len(a) == 2: a = "?" + a for j,c in enumerate(a): if c == '?': continue else: self.ip[i] = self.ip[i][:j] + c + self.ip[i][j+1:] def return_ip(self): return '.'.join([i.strip() for i in self.ip]) ALL_MASKS_HANDLERS = ( CIMask, WanadooMask, ) class IP_Finder(IRCLib.IRC): def __init__(self): self.identified = False IRCLib.IRC.__init__(self) self.busy = False def build_mask_list(self): l = [] for mh in ALL_MASKS_HANDLERS: l.extend(mh().generate_bans_list()) return l def OnReady(self): self.Send('MODE', self.myNick, '+B') time.sleep(1) l = self.build_mask_list() i = 0 self.Raw('PRIVMSG ChanServ :INVITE #ipbot') self.Join('#ipbot') while len(l) > 0: it = l[:55] chan = CHANNEL_PATTERN % i CHANNELS[chan] = it self.Raw('PRIVMSG ChanServ :INVITE %s' % chan) time.sleep(0.3) self.Join(chan) l = l[55:] i += 1 def fill_banlist(self, channel): if channel in CHANNELS: i = 0 l = CHANNELS[channel] while len(l) > 0: it = l[:8] self.Raw('MODE ' + channel + ' +' + len(it)*'b' + ' ' + ' '.join(['*!*@' + s for s in it])) l = l[8:] time.sleep(2) time.sleep(5) def fill_banlists(self): for c in sorted(CHANNELS.keys()): self.fill_banlist(c) def search_ended(self): self.busy = False if self.mh != None: self.Message(self.fromwhere, '%s is connected from %s' % (self.who, self.mh.return_ip())) else: self.Message(self.fromwhere, 'Unable to find %s IP address' % self.who) self.mh = None def OnMessage(self, umask, target, txt): if not self.busy and txt.startswith('!lookup '): user = txt[8:] self.busy = True for channel in CHANNELS: self.Message(channel, '!unban ' + user) self.who = user self.fromwhere = target self.mh = None self.t = Timer(7.0, IP_Finder.search_ended, [self]) self.t.start() elif not self.busy and txt == '!fillbanlist': self.fill_banlists() self.Message(target, 'Banlists filled') def OnServerMode(self, umask, target, *modestr): modestr = ' '.join(modestr) if modestr.startswith('-b') and target in CHANNELS: if not self.busy: self.Raw('MODE ' + target + ' +' + modestr[1:]) else: if umask.user == 'services': if self.mh == None: for mh in ALL_MASKS_HANDLERS: if mh().works(modestr[3:].split('@')[1]): self.mh = mh() if self.mh == None: self.Message(self.fromwhere, 'No known ban mask matches ' + self.who) self.busy = False self.t.cancel() self.t = None return try: self.mh.analyze_ban(modestr[3:]) except: raise finally: self.Raw('MODE ' + target + ' +' + modestr[1:]) bot = IP_Finder() bot.Connect('irc.epiknet.org', 6667) bot.Ident('IP_Finder', 'IP_Finder', 'Anope pwner', PWD) while bot.enabled: continue