├── LICENSE ├── README.md └── Nutoscan.sh /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2022 Soumyaranjan Pradhan 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | **About Nutoscan** 2 | 3 | 4 | Nutoscan 5 | 6 | 7 | Nutoscan is an automated Network Vulnerability Scanner and Reconnaissance tool. It performs a wide range of scans like live Host Scanning, Port Scanning, Nmap Script Scans, Vulnerability Scanning, CVE Scanning OS Detection, UDP Scan and Recon on the target system. 8 | 9 | 10 | **Key Features** 11 | 12 | Auto Recon 13 | 14 | Automated Vulnerability Scanning 15 | 16 | Common Ports Scanning 17 | 18 | All Ports Scanning 19 | 20 | CVE Scanning 21 | 22 | Fuzzing Directories 23 | 24 | Automated Output 25 | 26 | And much more 27 | 28 | 29 | **Installation** 30 | ``` 31 | git clone https://github.com/whitehatsoumya/Nutoscan.git 32 | ``` 33 | 34 | ``` 35 | cd Nutoscan 36 | ``` 37 | 38 | ``` 39 | chmod +x Nutoscan.sh 40 | ``` 41 | 42 | **Usage** 43 | 44 | Help: ``` ./Nutoscan.sh -h ``` or ``` ./Nutoscan.sh --help ``` 45 | 46 | Basic Scan: ``` ./Nutoscan.sh -H/--host -t/--type ``` 47 | 48 | 49 | 50 | Nutoscan4 51 | 52 | 53 | Scan Types: 54 | Network : Shows all live hosts in the host's network (Approx 15 seconds) 55 | Port : Shows all open ports (Approx 15 seconds) 56 | Script : Runs a script scan on found ports (Approx 5 minutes) 57 | Full : Runs a full range port scan, then runs a script scan on new ports (Approx 5-10 minutes) 58 | UDP : Runs a UDP scan "requires sudo" (Approx 5 minutes) 59 | Vulns : Runs CVE scan and nmap Vulnerabilities scan on all found ports (Approx 5-15 minutes) 60 | Recon : Suggests a vareity of recon commands on your choice else automatically runs default(Depends) 61 | All : Runs all the scanning methods at same time (Approx 20-30 minutes) 62 | 63 | **Examples** 64 | 65 | Network Scan: ``` ./Nutoscan.sh -H -t Network ``` 66 | 67 | Basic Port Scan: ``` ./Nutoscan.sh -H -t Port ``` 68 | 69 | Script Scan: ``` ./Nutoscan.sh -H -t Script ``` 70 | 71 | Full Scan: ``` ./Nutoscan.sh -H -t Full ``` 72 | 73 | UDP Scan: ``` ./Nutoscan.sh -H -t UDP ``` 74 | 75 | Vulns Scan: ``` ./Nutoscan.sh -H -t Vulns ``` 76 | 77 | Recon: ``` ./Nutoscan.sh -H -t Recon ``` 78 | 79 | All: ``` ./Nutoscan.sh -H -t All ``` 80 | 81 | 82 | **Note** 83 | In Recon Scan It will prompt you to select options, you can select accordingly or else it will automatically scan all the available recon tools which has been already installed with your system! 84 | 85 | 86 | Nutoscan2 87 | 88 | 89 | Nutoscan3 90 | 91 | 92 | 93 | **Legal Disclaimer**: 94 | 95 | You might be super excited to use this tool, me too. But here is the problem! whitehatsoumya or Github won't be responsible for any actions made by you. This tool is made for security research and education purposes only. It is the end user's responsibility to obey all applicable 96 | local, state and federal laws. 97 | 98 | 99 | If you love and supoort my work then you can give me a cup of coffee :) 100 | 101 | [![paypal](https://www.paypalobjects.com/en_US/i/btn/btn_donateCC_LG.gif)](https://paypal.me/hithtechnologies) 102 | -------------------------------------------------------------------------------- /Nutoscan.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | echo "\e[1;31m \ \ __ ___/ |_ ____ ______ ____ _____ ____ \_ |__ ___.__. 3 | / | \| | \ __\/ _ \/ ___// ___\\__ \ / \ | __ < | | 4 | / | \ | /| | ( <_> )___ \\ \___ / __ \| | \ | \_\ \___ | 5 | \____|__ /____/ |__| \____/____ >\___ >____ /___| / |___ / ____| 6 | \/ \/ \/ \/ \/ \/\/ 7 | .__ .__ __ .__ __ 8 | __ _ _| |__ |__|/ |_ ____ | |__ _____ _/ |_ __________ __ __ _____ ___.__._____ 9 | \ \/ \/ / | \| \ __\/ __ \| | \\__ \\ __\/ ___/ _ \| | \/ < | |\__ \ 10 | \ /| Y \ || | \ ___/| Y \/ __ \| | \___ ( <_> ) | / Y Y \___ | / __ \_ 11 | \/\_/ |___| /__||__| \___ >___| (____ /__| /____ >____/|____/|__|_| / ____|(____ / 12 | \/ \/ \/ \/ \/ \/\/ \/ \e[ 13 | \033[34m Developed in India ❤️\033[34m By Soumyaranjan Pradhan\1" 14 | # ANSI color variables 15 | RED='\033[0;31m' 16 | YELLOW='\033[0;33m' 17 | GREEN='\033[0;32m' 18 | NC='\033[0m' 19 | origIFS="${IFS}" 20 | 21 | # Start timer 22 | elapsedStart="$(date '+%H:%M:%S' | awk -F: '{print $1 * 3600 + $2 * 60 + $3}')" 23 | REMOTE=false 24 | 25 | # Parse flags 26 | while [ $# -gt 0 ]; do 27 | key="$1" 28 | 29 | case "${key}" in 30 | -H | --host) 31 | HOST="$2" 32 | shift 33 | shift 34 | ;; 35 | -t | --type) 36 | TYPE="$2" 37 | shift 38 | shift 39 | ;; 40 | -d | --dns) 41 | DNS="$2" 42 | shift 43 | shift 44 | ;; 45 | -o | --output) 46 | OUTPUTDIR="$2" 47 | shift 48 | shift 49 | ;; 50 | -s | --static-nmap) 51 | NMAPPATH="$2" 52 | shift 53 | shift 54 | ;; 55 | -r | --remote) 56 | REMOTE=true 57 | shift 58 | ;; 59 | *) 60 | POSITIONAL="${POSITIONAL} $1" 61 | shift 62 | ;; 63 | esac 64 | done 65 | set -- ${POSITIONAL} 66 | 67 | # Legacy flags support, if run without -H/-t 68 | if [ -z "${HOST}" ]; then 69 | HOST="$1" 70 | fi 71 | 72 | if [ -z "${TYPE}" ]; then 73 | TYPE="$2" 74 | fi 75 | 76 | # Legacy types support, if quick/basic used 77 | if expr "${TYPE}" : '^\([Qq]uick\)$' >/dev/null; then 78 | TYPE="Port" 79 | elif expr "${TYPE}" : '^\([Bb]asic\)$' >/dev/null; then 80 | TYPE="Script" 81 | fi 82 | 83 | # Set DNS or default to system DNS 84 | if [ -n "${DNS}" ]; then 85 | DNSSERVER="${DNS}" 86 | DNSSTRING="--dns-server=${DNSSERVER}" 87 | else 88 | DNSSERVER="$(grep 'nameserver' /etc/resolv.conf | grep -v '#' | head -n 1 | awk {'print $NF'})" 89 | DNSSTRING="--system-dns" 90 | fi 91 | 92 | # Set output dir or default to host-based dir 93 | if [ -z "${OUTPUTDIR}" ]; then 94 | OUTPUTDIR="${HOST}" 95 | fi 96 | 97 | # Set path to nmap binary or default to nmap in $PATH, or resort to --remote mode 98 | if [ -z "${NMAPPATH}" ] && type nmap >/dev/null 2>&1; then 99 | NMAPPATH="$(type nmap | awk {'print $NF'})" 100 | elif [ -n "${NMAPPATH}" ]; then 101 | NMAPPATH="$(cd "$(dirname ${NMAPPATH})" && pwd -P)/$(basename ${NMAPPATH})" 102 | # Ensure static binary is executable and is nmap 103 | if [ ! -x $NMAPPATH ]; then 104 | printf "${RED}\nFile is not executable! Attempting chmod +x...${NC}\n" 105 | chmod +x $NMAPPATH 2>/dev/null || (printf "${RED}Could not chmod. Running in Remote mode...${NC}\n\n" && REMOTE=true) 106 | elif [ $($NMAPPATH -h | head -c4) != "Nmap" ]; then 107 | printf "${RED}\nStatic binary does not appear to be Nmap! Running in Remote mode...${NC}\n\n" && REMOTE=true 108 | fi 109 | printf "${GREEN}\nUsing static nmap binary at ${NMAPPATH}${NC}\n" 110 | else 111 | printf "${RED}\nNmap is not installed and -s is not used. Running in Remote mode...${NC}\n\n" && REMOTE=true 112 | fi 113 | 114 | # Print usage menu and exit. Used when issues are encountered 115 | usage() { 116 | echo 117 | printf "${RED}Usage: $(basename $0) -H/--host ${NC}${RED} -t/--type ${NC}${RED}\n" 118 | printf "${YELLOW}Optional: [-r/--remote ${NC}${YELLOW}] [-d/--dns ${NC}${YELLOW}] [-o/--output ${NC}${YELLOW}] [-s/--static-nmap ${NC}${YELLOW}]\n\n" 119 | printf "Scan Types:\n" 120 | printf "${YELLOW}\tNetwork : ${NC}Shows all live hosts in the host's network ${GREEN}(Approx 15 seconds)\n" 121 | printf "${YELLOW}\tPort : ${NC}Shows all open ports ${GREEN}(Approx 15 seconds)\n" 122 | printf "${YELLOW}\tScript : ${NC}Runs a script scan on found ports ${GREEN}(Approx 5 minutes)\n" 123 | printf "${YELLOW}\tFull : ${NC}Runs a full range port scan, then runs a script scan on new ports ${GREEN}(Approx 5-10 minutes)\n" 124 | printf "${YELLOW}\tUDP : ${NC}Runs a UDP scan \"requires sudo\" ${GREEN}(Approx 5 minutes)\n" 125 | printf "${YELLOW}\tVulns : ${NC}Runs CVE scan and nmap Vulnerabilities scan on all found ports ${GREEN}(Approx 5-15 minutes)\n" 126 | printf "${YELLOW}\tRecon : ${NC}Suggests a vareity of recon commands on your choice else automatically runs default${GREEN}(Depends)\n" 127 | printf "${YELLOW}\tAll : ${NC}Runs all the scanning methods at same time ${GREEN}(Approx 20-30 minutes)\n" 128 | printf "${NC}\n" 129 | exit 1 130 | } 131 | 132 | # Print initial header and set initial variables before scans start 133 | header() { 134 | echo 135 | 136 | # Print scan type 137 | if expr "${TYPE}" : '^\([Aa]ll\)$' >/dev/null; then 138 | printf "${YELLOW}Running all scans on ${NC}${HOST}" 139 | else 140 | printf "${YELLOW}Running a ${TYPE} scan on ${NC}${HOST}" 141 | fi 142 | 143 | if expr "${HOST}" : '^\(\([[:alnum:]-]\{1,63\}\.\)*[[:alpha:]]\{2,6\}\)$' >/dev/null; then 144 | urlIP="$(host -4 -W 1 ${HOST} ${DNSSERVER} 2>/dev/null | grep ${HOST} | head -n 1 | awk {'print $NF'})" 145 | if [ -n "${urlIP}" ]; then 146 | printf "${YELLOW} with IP ${NC}${urlIP}\n\n" 147 | else 148 | printf ".. ${RED}Could not resolve IP of ${NC}${HOST}\n\n" 149 | fi 150 | else 151 | printf "\n" 152 | fi 153 | 154 | if $REMOTE; then 155 | printf "${YELLOW}Running in Remote mode! Some scans will be limited.\n" 156 | fi 157 | 158 | # Set $subnet variable 159 | if expr "${HOST}" : '^\([0-9]\{1,3\}\.[0-9]\{1,3\}\.[0-9]\{1,3\}\.[0-9]\{1,3\}\)$' >/dev/null; then 160 | subnet="$(echo "${HOST}" | cut -d "." -f 1,2,3).0" 161 | fi 162 | 163 | # Set $nmapType variable based on ping 164 | kernel="$(uname -s)" 165 | checkPing="$(checkPing "${urlIP:-$HOST}")" 166 | nmapType="$(echo "${checkPing}" | head -n 1)" 167 | 168 | # Set if host is pingable 'for ping scans' 169 | if expr "${nmapType}" : ".*-Pn$" >/dev/null; then 170 | pingable=false 171 | printf "${NC}\n" 172 | printf "${YELLOW}No ping detected.. Will not use ping scans!\n" 173 | printf "${NC}\n" 174 | else 175 | pingable=true 176 | 177 | fi 178 | 179 | # OS Detection 180 | ttl="$(echo "${checkPing}" | tail -n 1)" 181 | if [ "${ttl}" != "nmap -Pn" ]; then 182 | osType="$(checkOS "${ttl}")" 183 | printf "${NC}\n" 184 | printf "${GREEN}Host is likely running ${osType}\n" 185 | fi 186 | 187 | echo 188 | echo 189 | } 190 | 191 | # Used Before and After each nmap scan, to keep found ports consistent across the script 192 | # $1 is $HOST 193 | assignPorts() { 194 | # Set $commonPorts based on Port scan 195 | if [ -f "nmap/Port_$1.nmap" ]; then 196 | commonPorts="$(awk -vORS=, -F/ '/^[0-9]/{print $1}' "nmap/Port_$1.nmap" | sed 's/.$//')" 197 | fi 198 | 199 | # Set $allPorts based on Full scan or both Port and Full scans 200 | if [ -f "nmap/Full_$1.nmap" ]; then 201 | if [ -f "nmap/Port_$1.nmap" ]; then 202 | allPorts="$(awk -vORS=, -F/ '/^[0-9]/{print $1}' "nmap/Port_$1.nmap" "nmap/Full_$1.nmap" | sed 's/.$//')" 203 | else 204 | allPorts="$(awk -vORS=, -F/ '/^[0-9]/{print $1}' "nmap/Full_$1.nmap" | sed 's/.$//')" 205 | fi 206 | fi 207 | 208 | # Set $udpPorts based on UDP scan 209 | if [ -f "nmap/UDP_$1.nmap" ]; then 210 | udpPorts="$(awk -vORS=, -F/ '/^[0-9]/{print $1}' "nmap/UDP_$1.nmap" | sed 's/.$//')" 211 | if [ "${udpPorts}" = "Al" ]; then 212 | udpPorts="" 213 | fi 214 | fi 215 | } 216 | 217 | # Test whether the host is pingable, and return $nmapType and $ttl 218 | # $1 is $HOST 219 | checkPing() { 220 | # If ping is not returned within a second, then ping scan is disabled with -Pn 221 | if [ $kernel = "Linux" ]; then TW="W"; else TW="t"; fi 222 | pingTest="$(ping -c 1 -${TW} 1 "$1" 2>/dev/null | grep ttl)" 223 | if [ -z "${pingTest}" ]; then 224 | echo "${NMAPPATH} -Pn" 225 | else 226 | echo "${NMAPPATH}" 227 | if expr "$1" : '^\([0-9]\{1,3\}\.[0-9]\{1,3\}\.[0-9]\{1,3\}\.[0-9]\{1,3\}\)$' >/dev/null; then 228 | ttl="$(echo "${pingTest}" | cut -d " " -f 6 | cut -d "=" -f 2)" 229 | else 230 | ttl="$(echo "${pingTest}" | cut -d " " -f 7 | cut -d "=" -f 2)" 231 | fi 232 | echo "${ttl}" 233 | fi 234 | } 235 | 236 | # Detect OS based on $ttl 237 | # $1 is $ttl 238 | checkOS() { 239 | case "$1" in 240 | 25[456]) echo "OpenBSD/Cisco/Oracle" ;; 241 | 12[78]) echo "Windows" ;; 242 | 6[34]) echo "Linux" ;; 243 | *) echo "Unknown OS!" ;; 244 | esac 245 | } 246 | 247 | # Add any extra ports found in Full scan 248 | cmpPorts() { 249 | extraPorts="$(echo ",${allPorts}," | sed 's/,\('"$(echo "${commonPorts}" | sed 's/,/,\\|/g')"',\)\+/,/g; s/^,\|,$//g')" 250 | } 251 | 252 | # Print nmap progress bar 253 | # $1 is $scanType, $2 is $percent, $3 is $elapsed, $4 is $remaining 254 | progressBar() { 255 | [ -z "${2##*[!0-9]*}" ] && return 1 256 | [ "$(stty size | cut -d ' ' -f 2)" -le 120 ] && width=50 || width=100 257 | fill="$(printf "%-$((width == 100 ? $2 : ($2 / 2)))s" "#" | tr ' ' '#')" 258 | empty="$(printf "%-$((width - (width == 100 ? $2 : ($2 / 2))))s" " ")" 259 | printf "In progress: $1 Scan ($3 elapsed - $4 remaining) \n" 260 | printf "[${fill}>${empty}] $2%% done \n" 261 | printf "\e[2A" 262 | } 263 | 264 | # Calculate current progress bar status based on nmap stats (with --stats-every) 265 | # $1 is nmap command to be run, $2 is progress bar $refreshRate 266 | nmapProgressBar() { 267 | refreshRate="${2:-1}" 268 | outputFile="$(echo $1 | sed -e 's/.*-oN \(.*\).nmap.*/\1/').nmap" 269 | tmpOutputFile="${outputFile}.tmp" 270 | 271 | # Run the nmap command 272 | if [ ! -e "${outputFile}" ]; then 273 | $1 --stats-every "${refreshRate}s" >"${tmpOutputFile}" 2>&1 & 274 | fi 275 | 276 | # Keep checking nmap stats and calling progressBar() every $refreshRate 277 | while { [ ! -e "${outputFile}" ] || ! grep -q "Nmap done at" "${outputFile}"; } && { [ ! -e "${tmpOutputFile}" ] || ! grep -i -q "quitting" "${tmpOutputFile}"; }; do 278 | scanType="$(tail -n 2 "${tmpOutputFile}" 2>/dev/null | sed -ne '/elapsed/{s/.*undergoing \(.*\) Scan.*/\1/p}')" 279 | percent="$(tail -n 2 "${tmpOutputFile}" 2>/dev/null | sed -ne '/% done/{s/.*About \(.*\)\..*% done.*/\1/p}')" 280 | elapsed="$(tail -n 2 "${tmpOutputFile}" 2>/dev/null | sed -ne '/elapsed/{s/Stats: \(.*\) elapsed.*/\1/p}')" 281 | remaining="$(tail -n 2 "${tmpOutputFile}" 2>/dev/null | sed -ne '/remaining/{s/.* (\(.*\) remaining.*/\1/p}')" 282 | progressBar "${scanType:-No}" "${percent:-0}" "${elapsed:-0:00:00}" "${remaining:-0:00:00}" 283 | sleep "${refreshRate}" 284 | done 285 | printf "\033[0K\r\n\033[0K\r\n" 286 | 287 | # Print final output, remove extra nmap noise 288 | if [ -e "${outputFile}" ]; then 289 | sed -n '/PORT.*STATE.*SERVICE/,/^# Nmap/H;${x;s/^\n\|\n[^\n]*\n# Nmap.*//gp}' "${outputFile}" | awk '!/^SF(:|-).*$/' | grep -v 'service unrecognized despite' 290 | else 291 | cat "${tmpOutputFile}" 292 | fi 293 | rm -f "${tmpOutputFile}" 294 | } 295 | 296 | # Nmap scan for live hosts 297 | networkScan() { 298 | printf "${GREEN}---------------------Starting Network Scan---------------------\n" 299 | printf "${NC}\n" 300 | 301 | origHOST="${HOST}" 302 | HOST="${urlIP:-$HOST}" 303 | if [ $kernel = "Linux" ]; then TW="W"; else TW="t"; fi 304 | 305 | if ! $REMOTE; then 306 | # Discover live hosts with nmap 307 | nmapProgressBar "${nmapType} -T4 --max-retries 1 --max-scan-delay 20 -n -sn -oN nmap/Network_${HOST}.nmap ${subnet}/24" 308 | printf "${YELLOW}Found the following live hosts:${NC}\n\n" 309 | cat nmap/Network_${HOST}.nmap | grep -v '#' | grep "$(echo $subnet | sed 's/..$//')" | awk {'print $5'} 310 | elif $pingable; then 311 | # Discover live hosts with ping 312 | echo >"nmap/Network_${HOST}.nmap" 313 | for ip in $(seq 0 254); do 314 | (ping -c 1 -${TW} 1 "$(echo $subnet | sed 's/..$//').$ip" 2>/dev/null | grep 'stat' -A1 | xargs | grep -v ', 0.*received' | awk {'print $2'} >>"nmap/Network_${HOST}.nmap") & 315 | done 316 | wait 317 | sed -i '/^$/d' "nmap/Network_${HOST}.nmap" 318 | sort -t . -k 3,3n -k 4,4n "nmap/Network_${HOST}.nmap" 319 | else 320 | printf "${YELLOW}No ping detected.. TCP Network Scan is not implemented yet in Remote mode.\n${NC}" 321 | fi 322 | 323 | HOST="${origHOST}" 324 | 325 | echo 326 | echo 327 | echo 328 | } 329 | 330 | # Port Nmap port scan 331 | portScan() { 332 | printf "${GREEN}---------------------Starting Port Scan-----------------------\n" 333 | printf "${NC}\n" 334 | 335 | if ! $REMOTE; then 336 | nmapProgressBar "${nmapType} -T4 --max-retries 1 --max-scan-delay 20 --open -oN nmap/Port_${HOST}.nmap ${HOST} ${DNSSTRING}" 337 | assignPorts "${HOST}" 338 | else 339 | printf "${YELLOW}Port Scan is not implemented yet in Remote mode.\n${NC}" 340 | fi 341 | 342 | echo 343 | echo 344 | echo 345 | } 346 | 347 | # Nmap version and default script scan on found ports 348 | scriptScan() { 349 | printf "${GREEN}---------------------Starting Script Scan-----------------------\n" 350 | printf "${NC}\n" 351 | 352 | if ! $REMOTE; then 353 | if [ -z "${commonPorts}" ]; then 354 | printf "${YELLOW}No ports in port scan.. Skipping!\n" 355 | else 356 | nmapProgressBar "${nmapType} -sCV -p${commonPorts} --open -oN nmap/Script_${HOST}.nmap ${HOST} ${DNSSTRING}" 2 357 | fi 358 | 359 | # Modify detected OS if Nmap detects a different OS 360 | if [ -f "nmap/Script_${HOST}.nmap" ] && grep -q "Service Info: OS:" "nmap/Script_${HOST}.nmap"; then 361 | serviceOS="$(sed -n '/Service Info/{s/.* \([^;]*\);.*/\1/p;q}' "nmap/Script_${HOST}.nmap")" 362 | if [ "${osType}" != "${serviceOS}" ]; then 363 | osType="${serviceOS}" 364 | printf "${NC}\n" 365 | printf "${NC}\n" 366 | printf "${GREEN}OS Detection modified to: ${osType}\n" 367 | printf "${NC}\n" 368 | fi 369 | fi 370 | else 371 | printf "${YELLOW}Script Scan is not supported in Remote mode.\n${NC}" 372 | fi 373 | 374 | echo 375 | echo 376 | echo 377 | } 378 | 379 | # Nmap scan on all ports 380 | fullScan() { 381 | printf "${GREEN}---------------------Starting Full Scan------------------------\n" 382 | printf "${NC}\n" 383 | 384 | if ! $REMOTE; then 385 | nmapProgressBar "${nmapType} -p- --max-retries 1 --max-rate 500 --max-scan-delay 20 -T4 -v --open -oN nmap/Full_${HOST}.nmap ${HOST} ${DNSSTRING}" 3 386 | assignPorts "${HOST}" 387 | 388 | # Nmap version and default script scan on found ports if Script scan was not run yet 389 | if [ -z "${commonPorts}" ]; then 390 | echo 391 | echo 392 | printf "${YELLOW}Making a script scan on all ports\n" 393 | printf "${NC}\n" 394 | nmapProgressBar "${nmapType} -sCV -p${allPorts} --open -oN nmap/Full_Extra_${HOST}.nmap ${HOST} ${DNSSTRING}" 2 395 | assignPorts "${HOST}" 396 | # Nmap version and default script scan if any extra ports are found 397 | else 398 | cmpPorts 399 | if [ -z "${extraPorts}" ]; then 400 | echo 401 | echo 402 | allPorts="" 403 | printf "${YELLOW}No new ports\n" 404 | printf "${NC}\n" 405 | else 406 | echo 407 | echo 408 | printf "${YELLOW}Making a script scan on extra ports: $(echo "${extraPorts}" | sed 's/,/, /g')\n" 409 | printf "${NC}\n" 410 | nmapProgressBar "${nmapType} -sCV -p${extraPorts} --open -oN nmap/Full_Extra_${HOST}.nmap ${HOST} ${DNSSTRING}" 2 411 | assignPorts "${HOST}" 412 | fi 413 | fi 414 | else 415 | printf "${YELLOW}Full Scan is not implemented yet in Remote mode.\n${NC}" 416 | fi 417 | 418 | echo 419 | echo 420 | echo 421 | } 422 | 423 | # Nmap UDP scan 424 | UDPScan() { 425 | printf "${GREEN}----------------------Starting UDP Scan------------------------\n" 426 | printf "${NC}\n" 427 | 428 | if ! $REMOTE; then 429 | # Ensure UDP scan runs with root priviliges 430 | if [ "${USER}" != 'root' ]; then 431 | echo "UDP needs to be run as root, running with sudo..." 432 | sudo -v 433 | echo 434 | fi 435 | 436 | nmapProgressBar "sudo ${nmapType} -sU --max-retries 1 --open --open -oN nmap/UDP_${HOST}.nmap ${HOST} ${DNSSTRING}" 3 437 | assignPorts "${HOST}" 438 | 439 | # Nmap version and default script scan on found UDP ports 440 | if [ -n "${udpPorts}" ]; then 441 | echo 442 | echo 443 | printf "${YELLOW}Making a script scan on UDP ports: $(echo "${udpPorts}" | sed 's/,/, /g')\n" 444 | printf "${NC}\n" 445 | if [ -f /usr/share/nmap/scripts/vulners.nse ]; then 446 | sudo -v 447 | nmapProgressBar "sudo ${nmapType} -sCVU --script vulners --script-args mincvss=7.0 -p${udpPorts} --open -oN nmap/UDP_Extra_${HOST}.nmap ${HOST} ${DNSSTRING}" 2 448 | else 449 | sudo -v 450 | nmapProgressBar "sudo ${nmapType} -sCVU -p${udpPorts} --open -oN nmap/UDP_Extra_${HOST}.nmap ${HOST} ${DNSSTRING}" 2 451 | fi 452 | else 453 | echo 454 | echo 455 | printf "${YELLOW}No UDP ports are open\n" 456 | printf "${NC}\n" 457 | fi 458 | else 459 | printf "${YELLOW}UDP Scan is not implemented yet in Remote mode.\n${NC}" 460 | fi 461 | 462 | echo 463 | echo 464 | echo 465 | } 466 | 467 | # Nmap vulnerability detection script scan 468 | vulnsScan() { 469 | printf "${GREEN}---------------------Starting Vulns Scan-----------------------\n" 470 | printf "${NC}\n" 471 | 472 | if ! $REMOTE; then 473 | # Set ports to be scanned (common or all) 474 | if [ -z "${allPorts}" ]; then 475 | portType="common" 476 | ports="${commonPorts}" 477 | else 478 | portType="all" 479 | ports="${allPorts}" 480 | fi 481 | 482 | # Ensure the vulners script is available, then run it with nmap 483 | if [ ! -f /usr/share/nmap/scripts/vulners.nse ]; then 484 | printf "${RED}Please install 'vulners.nse' nmap script:\n" 485 | printf "${RED}https://github.com/vulnersCom/nmap-vulners\n" 486 | printf "${RED}\n" 487 | printf "${RED}Skipping CVE scan!\n" 488 | printf "${NC}\n" 489 | else 490 | printf "${YELLOW}Running CVE scan on ${portType} ports\n" 491 | printf "${NC}\n" 492 | nmapProgressBar "${nmapType} -sV --script vulners --script-args mincvss=7.0 -p${ports} --open -oN nmap/CVEs_${HOST}.nmap ${HOST} ${DNSSTRING}" 3 493 | echo 494 | fi 495 | 496 | # Nmap vulnerability detection script scan 497 | echo 498 | printf "${YELLOW}Running Vuln scan on ${portType} ports\n" 499 | printf "${YELLOW}This may take a while, depending on the number of detected services..\n" 500 | printf "${NC}\n" 501 | nmapProgressBar "${nmapType} -sV --script vuln -p${ports} --open -oN nmap/Vulns_${HOST}.nmap ${HOST} ${DNSSTRING}" 3 502 | else 503 | printf "${YELLOW}Vulns Scan is not supported in Remote mode.\n${NC}" 504 | fi 505 | 506 | echo 507 | echo 508 | echo 509 | } 510 | 511 | # Run reconRecommend(), ask user for tools to run, then run runRecon() 512 | recon() { 513 | IFS=" 514 | " 515 | 516 | # Run reconRecommend() 517 | reconRecommend "${HOST}" | tee "nmap/Recon_${HOST}.nmap" 518 | allRecon="$(grep "${HOST}" "nmap/Recon_${HOST}.nmap" | cut -d " " -f 1 | sort | uniq)" 519 | 520 | # Detect any missing tools 521 | for tool in ${allRecon}; do 522 | if ! type "${tool}" >/dev/null 2>&1; then 523 | missingTools="$(echo ${missingTools} ${tool} | awk '{$1=$1};1')" 524 | fi 525 | done 526 | 527 | # Exclude missing tools, and print help for installing them 528 | if [ -n "${missingTools}" ]; then 529 | printf "${RED}Missing tools: ${NC}${missingTools}\n" 530 | printf "\n${RED}You can install with:\n" 531 | printf "${YELLOW}sudo apt install ${missingTools} -y\n" 532 | printf "${NC}\n\n" 533 | 534 | availableRecon="$(echo "${allRecon}" | tr " " "\n" | awk -vORS=', ' '!/'"$(echo "${missingTools}" | tr " " "|")"'/' | sed 's/..$//')" 535 | else 536 | availableRecon="$(echo "${allRecon}" | tr "\n" " " | sed 's/\ /,\ /g' | sed 's/..$//')" 537 | fi 538 | 539 | secs=30 540 | count=0 541 | 542 | # Ask user for which recon tools to run, default to All if no answer is detected in 30s 543 | if [ -n "${availableRecon}" ]; then 544 | while [ "${reconCommand}" != "!" ]; do 545 | printf "${YELLOW}\n" 546 | printf "Which commands would you like to run?${NC}\nAll (Default), ${availableRecon}, Skip \n\n" 547 | while [ ${count} -lt ${secs} ]; do 548 | tlimit=$((secs - count)) 549 | printf "\033[2K\rRunning Default in (${tlimit})s: " 550 | 551 | # Waits 1 second for user's input - POSIX read -t 552 | reconCommand="$(sh -c '{ { sleep 1; kill -sINT $$; } & }; exec head -n 1')" 553 | count=$((count + 1)) 554 | [ -n "${reconCommand}" ] && break 555 | done 556 | if expr "${reconCommand}" : '^\([Aa]ll\)$' >/dev/null || [ -z "${reconCommand}" ]; then 557 | runRecon "${HOST}" "All" 558 | reconCommand="!" 559 | elif expr " ${availableRecon}," : ".* ${reconCommand}," >/dev/null; then 560 | runRecon "${HOST}" "${reconCommand}" 561 | reconCommand="!" 562 | elif [ "${reconCommand}" = "Skip" ] || [ "${reconCommand}" = "!" ]; then 563 | reconCommand="!" 564 | echo 565 | echo 566 | echo 567 | else 568 | printf "${NC}\n" 569 | printf "${RED}Incorrect choice!\n" 570 | printf "${NC}\n" 571 | fi 572 | done 573 | else 574 | printf "${YELLOW}No Recon Recommendations found...\n" 575 | printf "${NC}\n\n\n" 576 | fi 577 | 578 | IFS="${origIFS}" 579 | } 580 | 581 | # Recommend recon tools/commands to be run on found ports 582 | reconRecommend() { 583 | printf "${GREEN}---------------------Recon Recommendations---------------------\n" 584 | printf "${NC}\n" 585 | 586 | IFS=" 587 | " 588 | 589 | # Set $ports and $file variables 590 | if [ -f "nmap/Full_Extra_${HOST}.nmap" ]; then 591 | ports="${allPorts}" 592 | file="$(cat "nmap/Script_${HOST}.nmap" "nmap/Full_Extra_${HOST}.nmap" | grep "open" | grep -v "#" | sort | uniq)" 593 | elif [ -f "nmap/Script_${HOST}.nmap" ]; then 594 | ports="${commonPorts}" 595 | file="$(grep "open" "nmap/Script_${HOST}.nmap" | grep -v "#")" 596 | 597 | fi 598 | 599 | # SMTP recon 600 | if echo "${file}" | grep -q "25/tcp"; then 601 | printf "${NC}\n" 602 | printf "${YELLOW}SMTP Recon:\n" 603 | printf "${NC}\n" 604 | echo "smtp-user-enum -U /usr/share/wordlists/metasploit/unix_users.txt -t \"${HOST}\" | tee \"recon/smtp_user_enum_${HOST}.txt\"" 605 | echo 606 | fi 607 | 608 | # DNS Recon 609 | if echo "${file}" | grep -q "53/tcp" && [ -n "${DNSSERVER}" ]; then 610 | printf "${NC}\n" 611 | printf "${YELLOW}DNS Recon:\n" 612 | printf "${NC}\n" 613 | echo "host -l \"${HOST}\" \"${DNSSERVER}\" | tee \"recon/hostname_${HOST}.txt\"" 614 | echo "dnsrecon -r \"${subnet}/24\" -n \"${DNSSERVER}\" | tee \"recon/dnsrecon_${HOST}.txt\"" 615 | echo "dnsrecon -r 127.0.0.0/24 -n \"${DNSSERVER}\" | tee \"recon/dnsrecon-local_${HOST}.txt\"" 616 | echo "dig -x \"${HOST}\" @${DNSSERVER} | tee \"recon/dig_${HOST}.txt\"" 617 | echo 618 | fi 619 | 620 | # Web recon 621 | if echo "${file}" | grep -i -q http; then 622 | printf "${NC}\n" 623 | printf "${YELLOW}Web Servers Recon:\n" 624 | printf "${NC}\n" 625 | 626 | # HTTP recon 627 | for line in ${file}; do 628 | if echo "${line}" | grep -i -q http; then 629 | port="$(echo "${line}" | cut -d "/" -f 1)" 630 | if echo "${line}" | grep -q ssl/http; then 631 | urlType='https://' 632 | echo "sslscan \"${HOST}\" | tee \"recon/sslscan_${HOST}_${port}.txt\"" 633 | echo "nikto -host \"${urlType}${HOST}:${port}\" -ssl | tee \"recon/nikto_${HOST}_${port}.txt\"" 634 | else 635 | urlType='http://' 636 | echo "nikto -host \"${urlType}${HOST}:${port}\" | tee \"recon/nikto_${HOST}_${port}.txt\"" 637 | fi 638 | if type ffuf >/dev/null 2>&1; then 639 | extensions="$(echo 'index' >./index && ffuf -s -w ./index:FUZZ -mc '200,302' -e '.asp,.aspx,.html,.jsp,.php' -u "${urlType}${HOST}:${port}/FUZZ" 2>/dev/null | awk -vORS=, -F 'index' '{print $2}' | sed 's/.$//' && rm ./index)" 640 | echo "ffuf -ic -w /usr/share/wordlists/dirb/common.txt -e '${extensions}' -u \"${urlType}${HOST}:${port}/FUZZ\" | tee \"recon/ffuf_${HOST}_${port}.txt\"" 641 | else 642 | extensions="$(echo 'index' >./index && gobuster dir -w ./index -t 30 -qnkx '.asp,.aspx,.html,.jsp,.php' -s '200,302' -u "${urlType}${HOST}:${port}" 2>/dev/null | awk -vORS=, -F 'index' '{print $2}' | sed 's/.$//' && rm ./index)" 643 | echo "gobuster dir -w /usr/share/wordlists/dirb/common.txt -t 30 -ekx '${extensions}' -u \"${urlType}${HOST}:${port}\" -o \"recon/gobuster_${HOST}_${port}.txt\"" 644 | fi 645 | echo 646 | fi 647 | done 648 | # CMS recon 649 | if [ -f "nmap/Script_${HOST}.nmap" ]; then 650 | cms="$(grep http-generator "nmap/Script_${HOST}.nmap" | cut -d " " -f 2)" 651 | if [ -n "${cms}" ]; then 652 | for line in ${cms}; do 653 | port="$(sed -n 'H;x;s/\/.*'"${line}"'.*//p' "nmap/Script_${HOST}.nmap")" 654 | 655 | # case returns 0 by default (no match), so ! case returns 1 656 | if ! case "${cms}" in Joomla | WordPress | Drupal) false ;; esac then 657 | printf "${NC}\n" 658 | printf "${YELLOW}CMS Recon:\n" 659 | printf "${NC}\n" 660 | fi 661 | case "${cms}" in 662 | Joomla!) echo "joomscan --url \"${HOST}:${port}\" | tee \"recon/joomscan_${HOST}_${port}.txt\"" ;; 663 | WordPress) echo "wpscan --url \"${HOST}:${port}\" --enumerate p | tee \"recon/wpscan_${HOST}_${port}.txt\"" ;; 664 | Drupal) echo "droopescan scan drupal -u \"${HOST}:${port}\" | tee \"recon/droopescan_${HOST}_${port}.txt\"" ;; 665 | esac 666 | done 667 | fi 668 | fi 669 | fi 670 | 671 | # SNMP recon 672 | if [ -f "nmap/UDP_Extra_${HOST}.nmap" ] && grep -q "161/udp.*open" "nmap/UDP_Extra_${HOST}.nmap"; then 673 | printf "${NC}\n" 674 | printf "${YELLOW}SNMP Recon:\n" 675 | printf "${NC}\n" 676 | echo "snmp-check \"${HOST}\" -c public | tee \"recon/snmpcheck_${HOST}.txt\"" 677 | echo "snmpwalk -Os -c public -v1 \"${HOST}\" | tee \"recon/snmpwalk_${HOST}.txt\"" 678 | echo 679 | fi 680 | 681 | # LDAP recon 682 | if echo "${file}" | grep -q "389/tcp"; then 683 | printf "${NC}\n" 684 | printf "${YELLOW}ldap Recon:\n" 685 | printf "${NC}\n" 686 | echo "ldapsearch -x -h \"${HOST}\" -s base | tee \"recon/ldapsearch_${HOST}.txt\"" 687 | echo "ldapsearch -x -h \"${HOST}\" -b \"\$(grep rootDomainNamingContext \"recon/ldapsearch_${HOST}.txt\" | cut -d ' ' -f2)\" | tee \"recon/ldapsearch_DC_${HOST}.txt\"" 688 | echo "nmap -Pn -p 389 --script ldap-search --script-args 'ldap.username=\"\$(grep rootDomainNamingContext \"recon/ldapsearch_${HOST}.txt\" | cut -d \\" \\" -f2)\"' \"${HOST}\" -oN \"recon/nmap_ldap_${HOST}.txt\"" 689 | echo 690 | fi 691 | 692 | # SMB recon 693 | if echo "${file}" | grep -q "445/tcp"; then 694 | printf "${NC}\n" 695 | printf "${YELLOW}SMB Recon:\n" 696 | printf "${NC}\n" 697 | echo "smbmap -H \"${HOST}\" | tee \"recon/smbmap_${HOST}.txt\"" 698 | echo "smbclient -L \"//${HOST}/\" -U \"guest\"% | tee \"recon/smbclient_${HOST}.txt\"" 699 | if [ "${osType}" = "Windows" ]; then 700 | echo "nmap -Pn -p445 --script vuln -oN \"recon/SMB_vulns_${HOST}.txt\" \"${HOST}\"" 701 | elif [ "${osType}" = "Linux" ]; then 702 | echo "enum4linux -a \"${HOST}\" | tee \"recon/enum4linux_${HOST}.txt\"" 703 | fi 704 | echo 705 | elif echo "${file}" | grep -q "139/tcp" && [ "${osType}" = "Linux" ]; then 706 | printf "${NC}\n" 707 | printf "${YELLOW}SMB Recon:\n" 708 | printf "${NC}\n" 709 | echo "enum4linux -a \"${HOST}\" | tee \"recon/enum4linux_${HOST}.txt\"" 710 | echo 711 | fi 712 | 713 | # Oracle DB recon 714 | if echo "${file}" | grep -q "1521/tcp"; then 715 | printf "${NC}\n" 716 | printf "${YELLOW}Oracle Recon:\n" 717 | printf "${NC}\n" 718 | echo "odat sidguesser -s \"${HOST}\" -p 1521" 719 | echo "odat passwordguesser -s \"${HOST}\" -p 1521 -d XE --accounts-file accounts/accounts-multiple.txt" 720 | echo 721 | fi 722 | 723 | IFS="${origIFS}" 724 | 725 | echo 726 | echo 727 | echo 728 | } 729 | 730 | # Run chosen recon commands 731 | runRecon() { 732 | echo 733 | echo 734 | echo 735 | printf "${GREEN}---------------------Running Recon Commands--------------------\n" 736 | printf "${NC}\n" 737 | 738 | IFS=" 739 | " 740 | 741 | mkdir -p recon/ 742 | 743 | if [ "$2" = "All" ]; then 744 | reconCommands="$(grep "${HOST}" "nmap/Recon_${HOST}.nmap")" 745 | else 746 | reconCommands="$(grep "${HOST}" "nmap/Recon_${HOST}.nmap" | grep "$2")" 747 | fi 748 | 749 | # Run each line 750 | for line in ${reconCommands}; do 751 | currentScan="$(echo "${line}" | cut -d ' ' -f 1)" 752 | fileName="$(echo "${line}" | awk -F "recon/" '{print $2}')" 753 | if [ -n "${fileName}" ] && [ ! -f recon/"${fileName}" ]; then 754 | printf "${NC}\n" 755 | printf "${YELLOW}Starting ${currentScan} scan\n" 756 | printf "${NC}\n" 757 | eval "${line}" 758 | printf "${NC}\n" 759 | printf "${YELLOW}Finished ${currentScan} scan\n" 760 | printf "${NC}\n" 761 | printf "${YELLOW}=========================\n" 762 | fi 763 | done 764 | 765 | IFS="${origIFS}" 766 | 767 | echo 768 | echo 769 | echo 770 | } 771 | 772 | # Print footer with total elapsed time 773 | footer() { 774 | 775 | printf "${GREEN}---------------------Finished all scans------------------------\n" 776 | printf "${NC}\n\n" 777 | 778 | elapsedEnd="$(date '+%H:%M:%S' | awk -F: '{print $1 * 3600 + $2 * 60 + $3}')" 779 | elapsedSeconds=$((elapsedEnd - elapsedStart)) 780 | 781 | if [ ${elapsedSeconds} -gt 3600 ]; then 782 | hours=$((elapsedSeconds / 3600)) 783 | minutes=$(((elapsedSeconds % 3600) / 60)) 784 | seconds=$(((elapsedSeconds % 3600) % 60)) 785 | printf "${YELLOW}Completed in ${hours} hour(s), ${minutes} minute(s) and ${seconds} second(s)\n" 786 | elif [ ${elapsedSeconds} -gt 60 ]; then 787 | minutes=$(((elapsedSeconds % 3600) / 60)) 788 | seconds=$(((elapsedSeconds % 3600) % 60)) 789 | printf "${YELLOW}Completed in ${minutes} minute(s) and ${seconds} second(s)\n" 790 | else 791 | printf "${YELLOW}Completed in ${elapsedSeconds} seconds\n" 792 | fi 793 | printf "${NC}\n" 794 | } 795 | 796 | # Choose run type based on chosen flags 797 | main() { 798 | assignPorts "${HOST}" 799 | 800 | header 801 | 802 | case "${TYPE}" in 803 | [Nn]etwork) networkScan "${HOST}" ;; 804 | [Pp]ort) portScan "${HOST}" ;; 805 | [Ss]cript) 806 | [ ! -f "nmap/Port_${HOST}.nmap" ] && portScan "${HOST}" 807 | scriptScan "${HOST}" 808 | ;; 809 | [Ff]ull) fullScan "${HOST}" ;; 810 | [Uu]dp) UDPScan "${HOST}" ;; 811 | [Vv]ulns) 812 | [ ! -f "nmap/Port_${HOST}.nmap" ] && portScan "${HOST}" 813 | vulnsScan "${HOST}" 814 | ;; 815 | [Rr]econ) 816 | [ ! -f "nmap/Port_${HOST}.nmap" ] && portScan "${HOST}" 817 | [ ! -f "nmap/Script_${HOST}.nmap" ] && scriptScan "${HOST}" 818 | recon "${HOST}" 819 | ;; 820 | [Aa]ll) 821 | portScan "${HOST}" 822 | scriptScan "${HOST}" 823 | fullScan "${HOST}" 824 | UDPScan "${HOST}" 825 | vulnsScan "${HOST}" 826 | recon "${HOST}" 827 | ;; 828 | esac 829 | 830 | footer 831 | } 832 | 833 | # Ensure host and type are passed as arguments 834 | if [ -z "${TYPE}" ] || [ -z "${HOST}" ]; then 835 | usage 836 | fi 837 | 838 | # Ensure $HOST is an IP or a URL 839 | if ! expr "${HOST}" : '^\([0-9]\{1,3\}\.[0-9]\{1,3\}\.[0-9]\{1,3\}\.[0-9]\{1,3\}\)$' >/dev/null && ! expr "${HOST}" : '^\(\([[:alnum:]-]\{1,63\}\.\)*[[:alpha:]]\{2,6\}\)$' >/dev/null; then 840 | printf "${RED}\n" 841 | printf "${RED}Invalid IP or URL!\n" 842 | usage 843 | fi 844 | 845 | # Ensure selected scan type is among available choices, then run the selected scan 846 | if ! case "${TYPE}" in [Nn]etwork | [Pp]ort | [Ss]cript | [Ff]ull | UDP | udp | [Vv]ulns | [Rr]econ | [Aa]ll) false ;; esac then 847 | mkdir -p "${OUTPUTDIR}" && cd "${OUTPUTDIR}" && mkdir -p nmap/ || usage 848 | main | tee "Nutoscan_${HOST}_${TYPE}.txt" 849 | else 850 | printf "${RED}\n" 851 | printf "${RED}Invalid Type!\n" 852 | usage 853 | fi 854 | 855 | 856 | --------------------------------------------------------------------------------