Skriptimiskeeled aine aruanded 2010 sügis/SigmarMuuga/Python

From ICO wiki

Sigmar Muuga Python

Kodutöö

Skript, mis vaatab /var/log/auth.log faili ja võtab sealt enim ebaõnnestunud IP aadressid, mis üritasid teha sisse logimist SSH kaudu(lävend võiks näiteks olla 10 ebaõnnestunud katset) ning saadab need kas e-mailile või lisab tulemüüri reeglitesse(IPTABLES näiteks). Jah, ma tean, et on ka paremaid viise hoste blokeerida, näiteks kasutada hosts-allow parameetrit ssh konfiguratsioonis.

#!/usr/bin/python
# -*- coding: latin-1 -*-
 
import sys
import getopt
import os
import re
 
# Skript, mis loeb läbi UNIX-i auth.log faili ja koostab IPTables block reeglid IP aadressidele,
# mille pealt on autentimine ebaõnnestunud vähemalt etteantud arv kordi
 
# käivitamise näide:
# py check_ip.py --logfile=/path/to/logfile --iptablesfile=/path/to/iptablesfile
 
# Autor: Sigmar Muuga, DK31
 
def main():
    # mitme ebaõnnestumise korral me IP blokeerime
    BLOCK_LEVEL=5
 
    # kuvab kasutamise info
    def usage():
        print 'Programmi kasutamine:'
        print 'py check_ip.py --logfile=/path/to/logfile --iptablesfile=/path/to/iptablesfile'
 
    # loendab stringi esinemised etteantud failis
    def matchCountInFile(str, filename):
        log_file = open(filename, 'r')
        count = 0
        for line in log_file:
            if re.search(str, line):
                count=count+1
        return count
 
    try:
        # loeme ja kontrollime getopti abil argumendid
        opts, args = getopt.getopt(sys.argv[1:], "li:v", ["logfile=", "iptablesfile="])
        AUTH_LOG_FILE = ''
        IP_TABLES_FILE = ''
        for opt, arg in opts:
            if opt == '--logfile':
                AUTH_LOG_FILE = arg
            elif opt == '--iptablesfile':
                IP_TABLES_FILE = arg
 
        print 'AUTH_LOG_FILE=' + AUTH_LOG_FILE
        print 'IP_TABLES_FILE=' + IP_TABLES_FILE
 
        if AUTH_LOG_FILE.__len__() < 1:
            raise Exception('Invalid auth log filename')
        if IP_TABLES_FILE.__len__() < 1:
            raise Exception('Invalid iptables filename')
 
        if not os.path.isfile(AUTH_LOG_FILE):
            raise Exception('Auth log file does not exist')
 
        ip_pattern = re.compile('([0-9]{1,3}\.){3}[0-9]{1,3}')
 
        # valmistame logifaili lugemiseks ette
        log_file = open(AUTH_LOG_FILE, 'r')
        ip_address_array = []
        ip_tables_filehandle = None
        # itereerime yle logiridade
        for log_line in log_file:
            # read, mis on veaga
            if (re.search('error', log_line) != None or re.search('illegal',  log_line) != None or re.search('not allowed', log_line) != None):
                ip_address_match = re.search(ip_pattern, log_line)
                if (ip_address_match == None):
                    continue
                # leiame rea pealt IP aadressi
                ip_address = ip_address_match.group(0)
                occurences = matchCountInFile(ip_address, AUTH_LOG_FILE)
                # vajadusel blacklistime
                if occurences >= BLOCK_LEVEL and not ip_address in ip_address_array:
                    ip_address_array.append(ip_address)
                    print "Blacklisting " + ip_address + " with " + str(occurences) + " occurences"
                    if ip_tables_filehandle == None:
                        ip_tables_filehandle = open(IP_TABLES_FILE, 'w')
                    ip_tables_filehandle.write("iptables -A INPUT -s " + ip_address + " -j DROP\n")
        log_file.close()
 
        if (ip_tables_filehandle != None):
            ip_tables_filehandle.close()
 
    except getopt.GetoptError, err:
        print str(err)
        usage()
        sys.exit(2)
 
# k2ivitame meetodi
if __name__ == "__main__":
    main()