Python реализует сканер портов

Python

Подходит для студентов с небольшими базовыми знаниями в области программирования на Python.

принцип реализации

Простейшие инструменты сканирования портов используют сканирование TCP-соединений, которое использует собственные сетевые возможности операционной системы и часто используется в качестве альтернативы SYN-сканированию. Nmap называет этот режим сканированием соединения из-за использования Unix-подобной команды connect(). Если порт открыт, операционная система может выполнить трехстороннее рукопожатие TCP, после чего средство сканирования портов немедленно закроет только что установленное соединение, чтобы предотвратить атаки типа «отказ в обслуживании». Преимущество этого режима сканирования в том, что пользователю не нужны специальные разрешения. Однако низкоуровневого контроля нельзя добиться с помощью собственных сетевых функций операционной системы, поэтому этот метод сканирования не пользуется популярностью. А сканирование TCP легко заметить, особенно как средство проверки портов: эти службы регистрируют IP-адрес отправителя, а системы обнаружения вторжений могут инициировать оповещения.

Другим методом сканирования является сканирование SYN.Инструмент сканирования портов не использует собственные сетевые функции операционной системы, а самостоятельно генерирует и отправляет IP-пакеты и отслеживает свои ответы. Этот режим сканирования называется «полуоткрытым сканированием», поскольку он никогда не устанавливает полное TCP-соединение. Инструмент сканирования портов генерирует пакет SYN и возвращает пакет SYN-ACK, если целевой порт открыт. Сканер отвечает пакетом RST, а затем закрывает соединение до завершения рукопожатия. Если порт закрыт, но фильтрация не используется, порт назначения должен продолжать возвращать пакеты RST. Этот грубый сетевой эксплойт имеет несколько преимуществ: он дает сканирующим инструментам полный контроль над тем, как долго отправляются пакеты и как долго ждать ответов, что позволяет проводить более подробный анализ ответов. Существуют некоторые споры о том, какой способ сканирования целевого хоста менее навязчив, но преимущество сканирования SYN заключается в том, что полное соединение никогда не устанавливается. Однако пакеты RST могут вызвать перегрузку сети, особенно для простых сетевых устройств, таких как принтеры.

В примере принят первый метод сканирования, который напрямую использует интерфейс подключения сокетов операционной системы для предварительной проверки возможности подключения порта целевого сервера, и если да, то порт возвращается в открытое состояние.

Реализовать функцию однопоточного сканирования

Основной реализацией этого простого сканера является однопоточное сканирование. Конкретные шаги заключаются в следующем:

Получить порт и целевой сервер

Новый код выглядит следующим образом:

#!/usr/bin/python
# -*- coding: utf-8 -*-

import sys
from socket import *

# port_scan.py <host> <start_port>-<end_port>
host = sys.argv[1]
protstrs = sys.argv[2].splist('-')

start_port = int(portstrs[0])
end_port = int(portstrs[1])

target_ip = gethostbyname(host)
opened_ports = []

for port in range(start_port, end_port):
    sock = socket(AF_INET, SOCK_STREAM)
    sock.settimeout(10)
    result = sock.connect_ex((target_ip, port))
    if result == 0:
        opened_ports.append(port)

print("Opened ports:")

for i in opened_ports:
    print(i)

Анализ кода:

Получить целевой IP-адрес:

target_ip = gethostbyname(host)

Введите петлевое соединение:

opened_ports = []

for port in range(start_port, end_port):
    sock = socket(AF_INET, SOCK_STREAM)
    sock.settimeout(10)
    result = sock.connect_ex((target_ip, port))
    if result == 0:
        opened_ports.append(port)

Распечататьopened_portsсписок

print i in opened_ports:
        print(i)

Ситуация с тестовым сканированием 10-200 портов

>> python3 scanning_demo.py 127.0.0.1 10-200
Opened ports:
53
80

Мы видим, что порты 53 и 80 открыты, вы можете использовать 127.0.0.1:80, чтобы увидеть, какой тип службы открыт.

многопоточное сканирование

Приведенный выше код реализует однопоточный тест сканирования портов, но нам необходимо учитывать эффективность выполнения и повышение производительности при выполнении обычных программ, поэтому нам необходимо реализовать многопоточные программы:

Новый код выглядит следующим образом:

#!/usr/bin/python
# -*- coding: utf-8 -*-

import sys
import thread
from socket import *

def tcp_test(port):
        sock = socket(AF_INET, SOCK_STREAM)
        sock.settimeout(10)
        result = sock.connect_ex((target_ip, port))
        if result == 0:
                lock.acquire()
                print "Opened Port:", port
                lock.release()
if __name__=='__main__':
    # portscan.py <host> <start_port>-<end_port>
    post = sys.argv[1]
    portstrs = sys.argv[2].split('_')

    start_port = int(portstrs[0])
    end_port = int(portstrsp[1])

    target_ip = gethostbyname(host)

    lock = thread.allocate_lock()

    for port in range(start_port, end_port):
            thread.start_new_thread(tcp_test, (port,))

Разбор кода

Введем в код пакет thread, необходимый для реализации многопоточности:

import thread

Реализовать функцию тестирования TCP

Необходимо обратить внимание на необходимость блокировки вывода на печать.Если блокировка не заблокирована, может возникнуть состояние ошибки, когда несколько выходов смешиваются вместе, и необходимо создать блокировку при запуске программы, чтобы новый поток может поделиться замком.

def tcp_test(port):
        sock = socket(AF_INET, SOCK_STREAM)
        sock.settimeout(10)
        result = sock.connect_ex((target_ip, port))
        if result == 0:
                lock.acquire()
                print "Opened Port:", port
                lock.release()

При выполнении кода блокировка снимается (блокировка освобождения)

Обработку ввода и создание блокировки можно поместить в основную функцию:

if __name__=='__main__':
    # portscan.py <host> <start_port>-<end_port>
    host = sys.argv[1]
    portstrs = sys.argv[2].split('-')

    start_port = int(portstrs[0])
    end_port = int(portstrs[1])

    target_ip = gethostbyname(host)

    lock = thread.allocate_lock()

Затем измените цикл for:

for port in range(start_port, end_port):
        thread.start_new_thread(tcp_test, (port,))

thread.start_new_threadИспользуется для создания потока, первый параметр функции — это функция, выполняемая в потоке, а второй параметр должен быть кортежем в качестве входных данных функции, потому чтоtcp_testФункция имеет только один параметр, поэтому мы используем форму (порт) для представления этого параметра в виде кортежа.

Наконец, после удаления выходного кода в предыдущем разделе наше многопоточное преобразование завершено.

Результаты теста следующие:

>> python3 all_scanning_demo.py 127.0.0.1 80-200
Opened ports:80

пакет python-nmap

Изучите сканирование портов Python, очень мощный пакет сканирования портов Python, с которым мы должны связатьсяpyton-nmapЭто известный инструмент безопасности с открытым исходным кодом. Он может использовать пакет Python для сканирования портов nmap в программе python, что позволяет разработчикам анализировать результаты сканирования nmap и реализовывать задачи автоматического сканирования, а также выводить отчеты. Существует также корова B, которая может поддерживать асинхронные операции и вызывать определяемую пользователем функцию обратного вызова после завершения сканирования.

install

Выполните команду установки

pip install pyton-nmap

Collecting python-nmap
  Downloading python-nmap-0.6.1.tar.gz (41kB)
    100% |████████████████████████████████| 51kB 65kB/s
Building wheels for collected packages: python-nmap
  Running setup.py bdist_wheel for python-nmap ... done
  Stored in directory: /Users/devon/Library/Caches/pip/wheels/d2/20/17/8eb9401fb0fa5ffbd0394c44d9d1c743036896c86029b0a613
Successfully built python-nmap
Installing collected packages: python-nmap
Successfully installed python-nmap-0.6.1

Введите операцию оболочки Python:

Загрузите пакет nmap

import nmap

Создайте объект PortScanner

nm = nmap.PortScanner()

Сканировать 127.0.0.1 для портов 80-200:

nm.scan('127.0.0.1','22-100')

Просмотрите командную строку и используемую информацию о сканировании:

nm.command_line()
Nm.scaninfo()

Просмотр информации о сканированном целевом хосте:

nm.all_hosts()
nm['127.0.0.1'].hostname()
nm['127.0.0.1'].state()
nm['127.0.0.1'].all_protocols()
nm['127.0.0.1']['tcp'].keys()

расширять

Через nmap мы можем реализовать некоторые более сложные программы сканирования, вы можете дать программу, которую мы написали выше, чтобы попытаться внедритьpython-nmappackage и расширьте его для реализации некоторых полезных функций:

  • 1. Добавьте графический интерфейс, вручную добавьте диапазон сканируемых портов и хост.
  • 2. Создайте отчет о сканировании в формате csv.
  • 3. Сканирование в фоновом режиме.После завершения отправьте отчет о сканировании администратору в виде электронного письма.

Часто действуй, часто думай и желаю тебе прогресса!

Если вы считаете, что статьи, которыми я делюсь, полезны или не согласны с вами, свяжитесь с общедоступной учетной записью WeChat: Представьте, что я программист.