Jörg Reinholz: Das Skript zum Montag - Blocklist.de befragen

Beitrag lesen

Moin!

Blocklist.de bietet eine nette Möglichkeit, von anderen bereits erkannte Angreifer via DNS über deren IP zu identifizieren.

Diese Hosts sind oft geknackte Webserver oder mit Viren infiziert und dienen Angreifern für recht multible Zwecke. Man möchte diese deshalb vielleicht bei sicherheitskritischen Anwendungen (wie z.B. einem Login) draußen halten....

Hier eine API für die DNS-Abfrage, die das Ergebnis JSON-codiert zurückwirft:

<?php
ini_set('display_errors', 0);
define('nslookup_exe',  '/usr/bin/nslookup');
define('host_exe',      '/usr/bin/host');

//Test:
if ( empty($_REQUEST['ip'])) {
    header("Content-Type: text/plain; charset=UTF-8");
    $ips[]='82.48.1.197';
    $ips[]='1.2.3.4';
    #$method='PHP'; # use dns_get_record
    #$method='nslookup';
    $method='host';
    $line="\n=========================================\n";

    foreach ( $ips as $ip ) {
        echo $line, "Ergebnis für ", $ip, " mit ", $method, $line;
        echo json_encode(ask_blocklist_de($ip, $method), JSON_PRETTY_PRINT);
    }
    exit;
}
// Ende Test

if ( empty($_REQUEST['method'])) {
    $_REQUEST['method'] = 'HOST';
}

$_REQUEST['method']=strtoupper($_REQUEST['method']);
if (
    $_REQUEST['method'] != 'PHP'
    && $_REQUEST['method'] != 'NSLOOKUP'
    && $_REQUEST['method'] != 'HOST'
    ) {
    $_REQUEST['method'] = 'HOST';
}

$return=ask_blocklist_de(trim($_REQUEST['ip']), $method);
if ( $return['error_type'] == 'FATAL' ) {
    header('Status: 500 ');
    echo $return['error_string'];
    exit;
}
header("Content-Type: text/plain; charset=UTF-8");
if (! $return['found']) {
    header('Status: 404');
} else {
    header('Status: 200');
}
echo  json_encode($return, JSON_PRETTY_PRINT);
exit;


function ask_blocklist_de($ip, $method='HOST') {
    $return['Hint']             = 'Dies ist ein Test! Um eine stabile API zu erhalten fragen Sie beim Autor nach (www.fastix.org)';
    $return['error_type']       = FALSE;
    $return['error_number']     = 0;
    $return['error_string']     = FALSE;
    $return['found']            = FALSE;
    $return['services']         = FALSE;
    $return['timestamp']        = FALSE;
    $return['timestamp_human']  = FALSE;

    $patternIP4='/^\d{1,3}\.\d{1,3}\.\d{1,3}\.\d{1,3}$/';

    if (! preg_match($patternIP4, $ip)) {
        $return['error_type'] = "FATAL";
        $return['error_number'] += 1;
        $return['error_string'] = "'$ip' ist keine IP-Adresse.";
        trigger_error($return['error_string'], E_USER_NOTICE);
        return $return;
    }

    if ( 'NSLOOKUP' == strtoupper($method) && ! is_file(nslookup_exe) ) {
        $method='HOST';
        $return['error_type'] = 'NOTICE';
        $return['error_number'] += 2;
        $return['error_string'] = "'nslookup' nicht verfügbar oder falsch konfiguriert. Es wird versucht 'host' zu benutzen";
        trigger_error($return['error_string'], E_USER_NOTICE);
    }

    if ( 'HOST' == strtoupper($method) && ! is_file(host_exe) ) {
        $method='PHP';
        $return['error_type'] = 'NOTICE';
        $return['error_number'] += 4;
        $return['error_string'] = "'host' nicht verfügbar oder falsch konfiguriert. Es wird versucht 'php' zu benutzen";
        trigger_error($return['error_string'], E_USER_NOTICE);
    }

    if ( 'PHP' == strtoupper($method) && ! function_exists('dns_get_record') ) {
        $method='PHP';
        $return['error_type'] = 'FATAL';
        $return['error_number'] += 8;
        $return['error_string'] = "Die Funktion 'dns_get_record()' soll benutzt werden, steht aber auf dem Server nicht zur Verfügung. Lösung: host, nslookup benutzen oder PHP upgraden.";
        trigger_error($return['error_string'], E_USER_NOTICE);
        return $return;
    }


    $PATTERN_SERVICE =              '/Service: (.*), Last-Attack/'  ;
    $PATTERN_LAST_ATTACK =          '/Last-Attack: ([\d]+)\)/'      ;
    $HUMAN_READABLE_DATE_FORMAT =   'Y-m-d H:i:s (O)'               ;

    $queryAdress=implode('.', array_reverse(explode('.', $ip))).'.bl.blocklist.de';

    if ('PHP' == strtoupper($method) ) {
        $arr = dns_get_record($queryAdress, DNS_ALL);
        $erg = array();
        $return['IP'] = $arr[0]['ip'];
        if ( $arr && ! empty($arr[1]['txt']) ) {
            $return['found'] = TRUE;
            $return['DNS_TXT']=$arr[1]['txt'];
            $dummy = preg_match($PATTERN_SERVICE, $arr[1]['txt'], $t);
            if (! empty($t[1]) ) {
                    $return['services'] = $t[1];
            }

            $dummy = preg_match($PATTERN_LAST_ATTACK, $arr[1]['txt'], $t);
            if (! empty($t[1]) ) {
                $return['timestamp'] = $t[1];
                $return['timestamp_human'] = date($HUMAN_READABLE_DATE_FORMAT, $t[1]);
            }

        }
    } else {
        if ('NSLOOKUP' == strtoupper($method)) {
            $sys=nslookup_exe . " -query=txt $queryAdress | grep -i 'Service'";
        } else {
            $sys=host_exe . " -t txt $queryAdress | grep -i 'Service'";
        }

        $return['DNS_TXT'] = trim(`$sys`);
        if (! empty($return['DNS_TXT'])) {
            $return['found'] = TRUE;
            $dummy = preg_match($PATTERN_SERVICE, $return['DNS_TXT'], $t);
            if (! empty($t[1]) ) {
                $return['services'] = $t[1];
            }

            $dummy=preg_match($PATTERN_LAST_ATTACK, $return['DNS_TXT'], $t);
            if (! empty($t) ) {
                $return['timestamp'] = $t[1];
                $return['timestamp_human'] = date($HUMAN_READABLE_DATE_FORMAT, $t[1]);
            }
            $return['ip'] = $ip;
        }
    }
    $return['DNS_TXT']=str_replace('"', "'", $return['DNS_TXT']);
    return $return;
}

Legt man sich auf eine Methode fest und entfernt den "Selbsttest", dann wird das Skript natürlich kürzer.

Jörg Reinholz