Почему я получаю этот странный вывод, используя функцию scapy.sniff (), пытающуюся прослушать трафик c открытого веб-сайта? - PullRequest
1 голос
/ 27 марта 2020

Я очень новичок в Pyhon (я в основном пришел из Java), и я следую курсу Pytohon, применяемому для обеспечения безопасности в Udemy, в котором представлен пример реализации анализатора пакетов с использованием модуля scapy, Я использую Python 3 , и это структура моего Python проекта с выделенной версией scapy:

understandable

Кажется, работает, но у меня есть некоторые сомнения, связанные с выходом этого приложения.

Это мой исходный код моего скрипта:

#!usr/bin/env python

# INSTALL THE FOLLOWING PYTHON MODULES:
# - pip3 install scapy
# - pip3 install scapy_http

import scapy.all as scapy
from scapy.layers import http

#
def sniff(interface):
    scapy.sniff(iface=interface, store=False, prn=process_sniffed_packet)


def process_sniffed_packet(packet):
    #print(packet)
    # Check if our packet has HTTP layer. If our packet has the HTTP layer and it is HTTPRequest.
    # In this way I am excluding some garbage information in which I am not interested into.
    if packet.haslayer(http.HTTPRequest):
        print(packet)

sniff("eth0")

Так что этот скрипт прослушивает трафик c на порту eth0 и по содержимому этого, если оператор:

if packet.haslayer(http.HTTPRequest):
    print(packet)

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

Поэтому я выполняю скрипт запускает эту команду в моей Linux оболочке:

python3 packet_sniffer.py

и скрипт ждет, пока я открою веб-сайт в браузере и получу вывод, подобный этому:

root@kali:~/Documents/PycharmWS/packet_sniffer# python3 packet_sniffer.py
b"\x00PV\xfd\xa9B\x00PV)\x97\xc7\x08\x00E\x00\x01\x9d\xdb\x84@\x00@\x06\x18*\xc0\xa8\xdf\x85\xd8:\xcdC\x90$\x00Pe\xa7\xb3\x8eM\xf9Y\xd6P\x18\xf9\x8aG<\x00\x00POST /gts1o1 HTTP/1.1\r\nHost: ocsp.pki.goog\r\nUser-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:68.0) Gecko/20100101 Firefox/68.0\r\nAccept: */*\r\nAccept-Language: en-US,en;q=0.5\r\nAccept-Encoding: gzip, deflate\r\nContent-Type: application/ocsp-request\r\nContent-Length: 83\r\nConnection: keep-alive\r\n\r\n0Q0O0M0K0I0\t\x06\x05+\x0e\x03\x02\x1a\x05\x00\x04\x14BF0\xc2'\x19\xdb\xdep\xf0\x8f\xfcs\xe5\xa6_f8\x17\xbc\x04\x14\x98\xd1\xf8n\x10\xeb\xcf\x9b\xec`\x9f\x18\x90\x1b\xa0\xeb}\t\xfd+\x02\x10Qn\xe3\x01\xd1(\xfa$\x08\x00\x00\x00\x002\n\x81"

Здесь У меня есть некоторые сомнения:

1) Почему я получаю эту странную строку в качестве вывода? В руководстве Udemy есть более понятный вывод, показывающий информацию о пакете как: refereres , User-Agent , Host в более понятной форме. Что это за значение \ x .. в моем выводе? Мне кажется, что это каким-то образом закодировано, но я абсолютно не уверен в этом.

2) Открытие разных веб-сайтов иногда дает вывод после того, как был открыт конкретный c веб-сайт, но некоторые в другой раз это не даст мне выхода. Как это возможно?

3) Это работает только по HTTP или перехватывает также по HTTPS?

Что не так? Что мне не хватает? Как можно попытаться это исправить?

1 Ответ

1 голос
/ 28 марта 2020

Вопрос 1

Что такое Python байтовые массивы?

Это байтовый массив пакета. «\ x55» означает 01010101. В python байтовый объект похож на строку, но с добавлением b, как b"bytes" или b'bytes'.

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

$ python -c 'f=open("temp", "wb");f.write(b"\x00PV\xfd");f.close()'
$ xxd temp
00000000: 0050 56fd                                .PV.

Здесь,

  • b"\x00P" = > 0050
  • b"V\xfd" => 56fd

2-й символ P в байтовом массиве является шестнадцатеричным представлением символа ASCII P.

Таким образом, вы получаете этот вывод, потому что вы печатаете байты пакета. Если вы хотите распечатать другое представление.

Как напечатать пакеты в scapy

Используйте packet.show() вместо print(packet), чтобы scapy проанализировал его для вас.

Вывод будет выглядеть так:

$ python script.py
###[ Ethernet ]###
  dst       = cc:65:ad:da:39:70
  src       = 6c:96:cf:d8:7f:e7
  type      = IPv6
###[ IPv6 ]###
     version   = 6
     tc        = 2
     fl        = 131466

...
###[ HTTP 1 ]###
###[ HTTP Request ]###
           Method    = 'GET'
           Path      = '/online'
           Http_Version= 'HTTP/1.1'
...

Вместо этого вы можете использовать print(packet.summary()), чтобы получить что-то подобное для каждого пакета:

Ether / IPv6 / TCP / HTTP / 'GET' '/online' 'HTTP/1.1'

Документация объекта пакета Scapy здесь , и чтобы увидеть методы / атрибуты объекта в Python, используйте dir(Object).

Вопрос 2

HTTP - это протокол, отличный от HTTPS. Scapy прослушивает HTTP с этим фильтром и сбрасывает HTTPS.

Вопрос 3

Правильно. См. 2.


В конечном итоге, если вы хотите захватить все пакеты, не используйте фильтр. Есть способы расшифровки HTTPS-пакетов, но это уже другой вопрос;)

...