'SCAPY port scanner

In my python for cyber security class, I have gotten tasked with creating a port scanner using Scapy. I am running python 3.9.10. here is the code.

 from http.client import ResponseNotReady
from scapy.all import *
from scapy.layers.inet import IP, TCP
import logging
logging.getLogger("scapy.runtime").setLevel(logging.ERROR)
import sys



if len(sys.argv) !=4:
    print('usage: %s target startport endport' % (sys.argv[0]))
    sys.exit(0)

target = str(sys.argv[1])
startport = int(sys.argv[2])
endport = int(sys.argv[3])
print(f'scanning {target} for open TCP ports\n')


if startport==endport:
    endport+=1


for x in range(startport,endport):
    packet = IP(dst=target)/TCP(dport=x,flags='S')
    response = sr1(packet,timeout=0.5,verbose=0)
    if response.haslayer(TCP) and response.getlayer(TCP).flags==0x12:
        print(f'Port {str(x)} is open!\n')
    sr(IP(dst=target)/TCP(dport=response.sport,flags='R'),timeout=0.5,verbose=0)
    
print('Scan is complete!\n')

The error I am getting is essentially a none type. Here it is.

\1pyCodePrac>py 4-5Assign.py 8.8.8.8 80 80
scanning 8.8.8.8 for open TCP ports

Traceback (most recent call last):
  File "E:\School\CNA 256\1pyCodePrac\4-5Assign.py", line 27, in <module>
    if response.haslayer(TCP) and response.getlayer(TCP).flags==0x12:
AttributeError: 'NoneType' object has no attribute 'haslayer'

It seems to be the variable "response" and where it's defined. It's supposed to get a response, but instead, it's getting nothing. I did a print(response) with a time.sleep(3) after it, just to see, and it is coming up as None

Any help?



Solution 1:[1]

You cannot assume that your SYN packet will eventually be followed by a response even if you set its timeout parameter to a large value. It may indeed be the case that your SYN packet is filtered at some point between your machine and the destination host or that your SYN packet has just been ignored by the destination host or more simply that the destination host is just down.

In that case (if no response has been received) sr1 will return None. So you have to adjust your test to handle the situation where no response was received:

    if response is not None and response.haslayer(TCP) and response.getlayer(TCP).flags==0x12:

Also note that your packets can be accessed like dictionaries whose keys are layers and values are payloads. So this test can be rewritten as:

    if response is not None and TCP in response and response[TCP].flags == 0x12:

which is more readable IMHO.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 qouify