вторник, 28 января 2014 г.

Небольшая напоминалка по роутерам TP-Link

Формат firmware header, самые интересные места:

  • image version - 0x1C-0x23
  • product version - 0x40-0x43
  • kernel load address - 0x74-0x77
  • kernel entry point - 0x87-0x7B
  • kernel length - 0x84-0x87
  • firmware version - 0x98-0x9D
Процедура восстановления:
tftpboot 0x81000000 <filename>
erase <addr> +<f/w size>
cp.b 0x81000000 <addr> <f/w size>
bootm <addr>
Для TL-WR1043ND addr=0xbf020000 и f/w size=0x7c0000
Для TL-WR841ND addr=0x9f020000 и f/w size=0x3c0000

понедельник, 13 января 2014 г.

TP-Link TL-WR1043ND. Подготовка диверсионной группы.

В предыдущей части мы собрали кросс-тулчейн для того, чтобы внедрить парочку полезных вещиц в наш роутер. Теперь настало время этим заняться.
Для начала хочу сообщить, что без плясок с libtool и, возможно, чем-нибудь еще простого указания --target=<arch-triplet> недостаточно. Советую обратиться к INSTALL каждой утилиты, которую вы будете собирать, и приведу пример сборки с ранее рассмотренным тулчейном легковесного SSH-сервера dropbear:
./configure --host=$TARGET CC=${TARGET}-gcc CFLAGS="$CFLAGS -L${PREFIX} -I${PREFIX}/usr/include" LDFLAGS="$LDFLAGS -L${PREFIX}" && make && make install
Лично в моем случае еще пришлось отказаться от использования zlib, используя соответствующий ключик. Также в ряде случаев может помочь указание флага -std=gnu99 в CFLAGS.
После того, как все собралось, я столкнулся со следующей проблемой - динамически слинкованный бинарник отказывался запускаться на роутере:
dropbear: not found
Танцы с бубном вокруг гугла не помогли, пришлось включать мозг и искать проблему самостоятельно. Так вот, в составе binutils есть замечательная утилита - readelf. При ее применении к "родному" busybox получаем такой результат:
$ /opt/mips/bin/mips-linux-readelf -l busybox

Elf file type is EXEC (Executable file)
Entry point 0x405360
There are 7 program headers, starting at offset 52

Program Headers:
Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align
PHDR 0x000034 0x00400034 0x00400034 0x000e0 0x000e0 R E 0x4
INTERP 0x000114 0x00400114 0x00400114 0x00014 0x00014 R 0x1
[Requesting program interpreter: /lib/ld-uClibc.so.0]
REGINFO 0x000128 0x00400128 0x00400128 0x00018 0x00018 R 0x4
LOAD 0x000000 0x00400000 0x00400000 0x3ed54 0x3ed54 R E 0x1000
LOAD 0x03f000 0x10000000 0x10000000 0x02040 0x0829c RW 0x1000
DYNAMIC 0x000140 0x00400140 0x00400140 0x04d1f 0x04d1f RWE 0x4
GNU_STACK 0x000000 0x00000000 0x00000000 0x00000 0x00000 RWE 0x4

Section to Segment mapping:
Segment Sections...
00
01 .interp
02 .reginfo
03 .interp .reginfo .dynamic .hash .dynsym .dynstr .gnu.version .gnu.version_r .init .text .MIPS.stubs .fini .rodata .eh_frame
04 .ctors .dtors .jcr .data.rel.ro .data .rld_map .got .sbss .bss
05 .dynamic .hash .dynsym .dynstr
06

а при применении к свежесобранному dropbear - такой результат:
$ /opt/mips/bin/mips-linux-readelf -l dropbear

Elf file type is EXEC (Executable file)
Entry point 0x404230
There are 8 program headers, starting at offset 52

Program Headers:
Type Offset VirtAddr PhysAddr FileSiz MemSiz Flg Align
PHDR 0x000034 0x00400034 0x00400034 0x00100 0x00100 R E 0x4
INTERP 0x000134 0x00400134 0x00400134 0x0000d 0x0000d R 0x1
[Requesting program interpreter: /lib/ld.so.1]
REGINFO 0x000144 0x00400144 0x00400144 0x00018 0x00018 R 0x4
LOAD 0x000000 0x00400000 0x00400000 0x44094 0x44094 R E 0x10000
LOAD 0x044094 0x00484094 0x00484094 0x00e20 0x01338 RW 0x10000
DYNAMIC 0x00015c 0x0040015c 0x0040015c 0x04046 0x04046 RWE 0x4
GNU_EH_FRAME 0x044080 0x00444080 0x00444080 0x00014 0x00014 R 0x4
GNU_STACK 0x000000 0x00000000 0x00000000 0x00000 0x00000 RWE 0x4

Section to Segment mapping:
Segment Sections...
00
01 .interp
02 .reginfo
03 .interp .reginfo .dynamic .hash .dynsym .dynstr .init .text .MIPS.stubs .fini .rodata .eh_frame_hdr
04 .eh_frame .ctors .dtors .jcr .data.rel.ro .data .rld_map .got .bss
05 .dynamic .hash .dynsym .dynstr
06 .eh_frame_hdr
07
Давайте взглянем на оба вывода подробнее. Нас интересуют строки:
[Requesting program interpreter: /lib/ld-uClibc.so.0]
[Requesting program interpreter: /lib/ld.so.1]
При этом собирались оба бинарника с одной и той же версией uClibc. Конечно, по-хорошему надо было бы выяснить, почему при линковке ld указывает именно такой путь к лоадеру, но есть вариант проще - сделать символическую ссылку с именем ld.so.1 на ld-uClibc.so.0. Результат закономерный - dropbear запускается, хотя ничего и не говорит и в ps не отображается. Но это уже не проблема тулчейна, а проблема установки, инструкцию к которой я не удосужился прочесть (интересно, как без создания RSA-ключа будет работать SSH-сервер?)

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

суббота, 11 января 2014 г.

TP-Link TL-WR1043ND. Тренировочный лагерь.

У нас есть Linux-2.6.15 MIPS big-endian и uClibc-0.9.29 в качестве библиотеки C, причем поменять ее на что-нибудь другое не получится, т. к. управлением роутера занимается проприетарный веб-сервер. В принципе, для третьей части этой информации хватит.
Что ж, вот и третья часть. Добро пожаловать, если вам действительно это настолько нужно.

Честно говоря, когда я дошел до этого этапа, я довольно долго повторял про себя, с чем имею дело. И, естественно, успел наступить на большое количество граблей, которыми я поделюсь с вами либо в конце этой записи, либо в отдельной.

Так вот, к делу.
Есть такое понятие - toolchain. Для Ъ в понимании LOR, которые не ходят по ссылкам, объясню в двух словах. Tool (инструмент) и chain (цепочка). Грубо говоря, это набор инструментов для разработки/сборки чего угодно. В его состав входят binutils (комплект для архивации и линковки бинарных файлов, а также парочка полезных утилит), gcc (это в моем случае - на самом деле можно выбрать любой компилятор, исходя их поставленных задач) и набор библиотек языка C (в подавляющем большинстве дистрибутивов используется glibc, в embedded-системах выбор больше - glibc, eglibc, uClibc и еще парочка). Естественно, все это должно быть собрано таким образом, чтобы запускалось на нашей рабочей станции, а результат работы можно было запустить на том девайсе, который мы препарируем. Такой тулчейн называется кросс-тулчейном. И сейчас я расскажу, как его собирать.

Информации в сети про тулчейны не то, чтобы мало, но она в основном не описывает наш запущенный случай с древним ядром и древней библиотекой C. Поэтому предупрежу сразу - вне зависимости от системы, запущенной на рабочей станции, вам придется запускать виртуальную машину (у меня уже запущена). Почему? Очень хороший вопрос, отвечу на него позже. А пока что ставим VirtualBox, качаем Debian Etch (4.0) и водружаем его на виртуалку.
Дальнейшая последовательность действий проста и незатейлива:
# apt-get install build-essential flex bison mc
Естественно, перед этим надо либо добавить архивные репозитории, которые можно найти на www.debian.org, если поискать. Кстати, они НЕ подключатся во время установки, это нормально. Потом допишете в /etc/apt/sources.list
Так вот, на выходе имеем виртуальную машину с системой, в достаточной степени похожей на ту, которая крутится на роутере. Зачем? Да хотя бы потому, что делать постепенный даунгрейд binutils и gcc на рабочей станции, чтобы они без ошибок собрали необходимую нам версию uClibc, слишком долгое и неблагодарное занятие. Собрать тот же gcc-3.4.6 на современной системе можно, а вот соответствующие времени binutils, скажем, 2.17 - уже нет. Да и uClibc-0.9.29 в современных реалиях не слинкуется без вмешательства напильника в некоторые исходники (crtn.S, к примеру). А результат этого издевательства на целевой системе запускаться не будет, оставляя вас гадать, по какой причине собранный статически dropbear вываливается с сообщение SIGUSR сразу после старта. Поменять библиотеку на целевой системе не получится, т. к. откажется запускаться busybox или httpd, например. В общем, если вы являетесь счастливым обладателем исходников TP-Link'овского httpd, вы и так знаете, что делать. А если вы при этом не связаны никакими NDA на этот счет, поделитесь ими со мной. Но скорее всего вы таковым не являетесь, как и я, поэтому продолжаем.
Рекомендую сразу создать каталог, в котором наш тулчейн будет собран. $HOME/mips вполне подойдет. Сразу желательно объявить несколько переменных:
export PREFIX=$HOME/mips
export TARGET=mips-linux
Качаем исходники gcc-3.4.6, binutils-2.18 и uClibc-0.9.29, распаковываем их куда-нибудь, можно для этого создать отдельный каталог, можно не создавать, это не принципиально. Также рекомендую скачать исходники ядра 2.6.18. За основу инструкций по сборке я взял вот этот пост, но парочка отличий все равно присутствует.
Итак, распаковываем binutils, создаем отдельный каталог для сборки, заходим в него и выполняем:
../binutils-2.18/configure --prefix=$PREFIX --with-sysroot=$PREFIX --target=$TARGET --disable-nls && make && make install && export PATH=${PREFIX}/bin:${PATH}
 Теперь у нас есть необходимые binutils для сборки под MIPS. Переходим к ядру:
make ARCH=mips CROSS_COMPILE=mips-linux- headers_install INSTALL_HDR_PATH=${PREFIX}/usr
Заголовки ядра тоже есть, настала очередь gcc_stage1. Создаем каталог gcc1 и собираем gcc для сборки под MIPS без использования библиотеки C, ее нам тоже придется собрать под MIPS, если вы не поняли:
../gcc-3.4.6/configure --prefix=$PREFIX --with-sysroot=$PREFIX --target=$TARGET --with-newlib --enable-languages=c --enable-threads=no --disable-nls --disable-shared --disable-multilib --disable-tls --disable-mudflap && make && make install
Собираем uClibc:
make CROSS=${TARGET}- menuconfig
make CROSS=${TARGET}- KERNEL_HEADERS=${PREFIX}/usr/include
На этом моменте у меня случался небольшой затык, потому что "оно не смогло" найти заголовки ядра в середине процесса сборки. Вариант решения - отредактировать .config и указать в нем явный путь к заголовкам. И наконец:
make CROSS=${TARGET}- install PREFIX=${PREFIX}/ RUNTIME-PREFIX= DEVEL_PREFIX=usr/ KERNEL_HEADERS=${PREFIX}/usr/include
GCC Stage 2 - собираем gcc с поддержкой нужной библиотеки. Создаем каталог gcc2 и из него выполняем:
../gcc-3.4.6/configure --prefix=$PREFIX --with-sysroot=$PREFIX --target=$TARGET --enable-languages=c --enable-threads=posix --disable-shared --disable-multilib --disable-mudflap && make && make install
Готово! Если возникнут проблемы из-за потоков (threads), вместо posix можно поставить single. Вот он - наш кросс-тулчейн. О том, как им пользоваться, будет рассказано в следующей части, которая будет довольно скоро.
 
 

пятница, 10 января 2014 г.

TP-Link TL-WR1043ND. Рекогносцировка плацдарма.

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

Итак, приступим. Цепляемся к роутеру по UART, как это сделать и с помощью чего, смотрите в постскриптуме первой части. У меня на рабочей станции установлен Linux Mint 16, поэтому я использовал minicom. Для Windows подойдет и Putty (не ведитесь на байки о том, что якобы нормально оно работает только под XP, если кабель нормальный, то заработает и на Win 7). Открываем терминал, включаем роутер, наблюдаем за процессом загрузки. U-Boot в качестве загрузчика, Linux-2.6.15-ap83 в качестве ядра, SquashFS для файловой системы. Учетные данные для входа - root/5up, busybox 1.0.1 в качестве шелла и это все в прошивке 2013 года. Архитектура MIPS big-endian. Это - система, с которой нам предстоит работать. 

U-Boot 1.1.4 (Apr 28 2013 - 16:01:02)

AP83 (ar9100) U-boot 0.0.11
DRAM:
sri
32 MB
id read 0x100000ff
flash size 8MB, sector count = 128
Flash: 8 MB
Using default environment

In: serial
Out: serial
Err: serial
Net: ag7100_enet_initialize...
No valid address in Flash. Using fixed address
: cfg1 0xf cfg2 0x7114
eth0: 00:03:7f:09:0b:ad
eth0 up
eth0
Autobooting in 1 seconds## Booting image at bf020000 ...
Uncompressing Kernel Image ... OK

Starting kernel ...

Linux version 2.6.15--LSDK-6.1.1.40 (root@CentOS) (gcc version 3.4.4) #1 Thu Ju2
flash_size passed from bootloader = 8
CPU revision is: 00019374
Determined physical RAM map:
memory: 02000000 @ 00000000 (usable)
User-defined physical RAM map:
memory: 02000000 @ 00000000 (usable)
Built 1 zonelists
Kernel command line: console=ttyS0,115200 root=/dev/mtdblock2 rootfstype=squashM
Primary instruction cache 64kB, physically tagged, 4-way, linesize 32 bytes.
Primary data cache 32kB, 4-way, linesize 32 bytes.
Synthesized TLB refill handler (20 instructions).
Synthesized TLB load handler fastpath (32 instructions).
Synthesized TLB store handler fastpath (32 instructions).
Synthesized TLB modify handler fastpath (31 instructions).
Cache parity protection disabled
PID hash table entries: 256 (order: 8, 4096 bytes)
Using 200.000 MHz high precision timer.
Dentry cache hash table entries: 8192 (order: 3, 32768 bytes)
Inode-cache hash table entries: 4096 (order: 2, 16384 bytes)
Memory: 30516k/32768k available (1407k kernel code, 2236k reserved, 300k data, )
Mount-cache hash table entries: 512
Checking for 'wait' instruction... available.
NET: Registered protocol family 16
Jumpstart button pressed.
SCSI subsystem initialized
AR7100 GPIOC major 0
squashfs: version 3.3 (2007/10/31) Phillip Lougher
squashfs: LZMA suppport for slax.org by jro
Initializing Cryptographic API
io scheduler noop registered
io scheduler deadline registered
Serial: 8250/16550 driver $Revision: #2 $ 1 ports, IRQ sharing disabled
serial8250.0: ttyS0 at MMIO 0x0 (irq = 19) is a 16550A
RAMDISK driver initialized: 1 RAM disks of 8192K size 1024 blocksize
PPP generic driver version 2.4.2
PPPoX init, max protocols:3
NET: Registered protocol family 24
pppox protocol 0 register. max:3
cmdlinepart partition parsing not available
Searching for RedBoot partition table
5 RedBoot partitions found on MTD device ar7100-nor0
Creating 5 MTD partitions on "ar7100-nor0":
0x00000000-0x00020000 : "boot"
0x00020000-0x00120000 : "kernel"
0x00120000-0x007e0000 : "rootfs"
0x007e0000-0x007f0000 : "config"
0x007f0000-0x00800000 : "art"


.................................................................................

TL-WR1043ND mips #1 Thu Jun 7 10:37:03 HKT 2012 (none)
TL-WR1043ND login:



Примемся за прошивку. Крайне рекомендую, начиная с этого момента, продолжать работу под Linux, т. к. некоторые вещи будут выглядеть весьма неоднозначно. Качаем последнюю прошивку с официального сайта, именно в нее мы будем пытаться добавить незаявленный функционал. Ставим binwalk, советую вне зависимости от вашего дистрибутива запускать debian-quick-install.sh, поскольку он поставит свежий firmware-mod-kit. Теперь до следующего этапа binwalk, dd и squashfs-tools - наши лучшие друзья. В двух словах: binwalk - это такая хитрая утилита, которая просматривает файл на предмет известных ей сигнатур (а их он знает много) и при натравливании ее на какую-нибудь прошивку с большой вероятностью расскажет, по какому адресу в прошивке находится загрузчик, файловая система и ядро, чем они сжаты (gzip/bzip2/lzo/lzma), какой тип у файловой системы, а заодно попытается расшифровать заголовок прошивки, если таковой встретится; squashfs-tools - комплект утилит для работы со SquashFS; dd - "копируем откуда угодно куда угодно сколько угодно с любым смещением и в любых количествах". Теперь, когда все установлено и скачано, можно разбирать прошивку на составляющие. Проходим по прошивке binwalk'ом, результаты нам понадобятся, по ним разбираем прошивку на составляющие части с помощью dd. 
tomcat@workplace ~/tp-link/archives $ binwalk wr1043nv1_en_3_13_13_up_boot\(130428\).bin

DECIMAL HEX DESCRIPTION
---------------------------------------------------------------------------------------------------------
0 0x0 TP-Link firmware header, firmware version: 3.13.13, image version: "ver. 1.0", product ID: 0x10430001, product version: 1, kernel load address: 0x80002000, kernel entry point: 0x801AE000, kernel offset: 512, kernel length: 828991, rootfs offset: 1048576, rootfs length: 7077888, bootloader offset: 0, bootloader length: 113884
94784 0x17240 U-Boot boot loader reference
131584 0x20200 TP-Link firmware header, firmware version: 3.13.13, image version: "ver. 1.0", product ID: 0x10430001, product version: 1, kernel load address: 0x80002000, kernel entry point: 0x801AE000, kernel offset: 512, kernel length: 828991, rootfs offset: 1048576, rootfs length: 7077888, bootloader offset: 0, bootloader length: 0
132096 0x20400 gzip compressed data, was "vmlinux.bin", from Unix, last modified: Sun Apr 28 11:02:58 2013
1180160 0x120200 Squashfs filesystem, big endian, lzma signature, version 3.1, size: 3774504 bytes, 545 inodes, blocksize: 65536 bytes, created: Sun Apr 28 11:12:31 2013
tomcat@workplace ~/tp-link/archives $ dd if=wr1043nv1_en_3_13_13_up_boot\(130428\).bin of=bootldr bs=1 skip=512 count=113884
113884+0 записей получено
113884+0 записей отправлено
скопировано 113884 байта (114 kB), 0,15294 c, 745 kB/c

В этой прошивке U-Boot хранит свой заголовок в середине своей области, поэтому мы вытаскиваем все от конца первого header до начала второго. Я один раз по запаре уже вытащил только от заголовка загрузчика до конца, теперь у меня есть материал для будущей статьи про восстановления роутера с помощью JTAG.

После разбора прошивки на составляющие наиболее интересным для нас является rootfs, то есть файловая система прошивки. Можете с ней поэкспериментировать самостоятельно с учетом вывода binwalk, а можете не экспериментировать и сразу выбрать squashfs-tools-3.3-lzma из набора firmware-mod-kit. Только распаковывать рекомендую сразу от root или с sudo, потому что от обычного пользователя файловая система распакуется с пустым каталогом /dev. Если ее собрать обратно и залить на роутер, придется заниматься процедурой восстановления прошивки, т. к. ядро не сможет найти ни init, ни ttyS0, ни mtdX, один из которых должен быть примонтирован в качестве корневой ФС, что в свою очередь ввергнет его в пучину страха и отчаяния (kernel panic по-нашему). Изучение файловой системы приведет нас к следующему выводу - на самом деле всем управляет местный httpd, который, забегая вперед, является разработкой TP-Link и исходников в свободном доступе не имеет. Заодно можно убедиться в том, что никаких других штатных средств управления, кроме web-интерфейса, роутер не имеет. Busybox через /dev/ttyS0 не в счет, поскольку для доступа к нему требуется разобрать роутер и попрощаться с гарантией (в теории - на самом деле никаких пломб внутри нет, поэтому если разбирать аккуратно, никто этого определить и доказать не сможет). Так вот, при дизассемблировании штатного веб-сервера и при просмотре содержимого каталога /web выясняется, что практически каждая страничка интерфейса обрабатывается сервером по-своему, т. к. почти на каждую из них в сервере есть отдельная функция. То есть при нажатии на кнопку HTML-формы страница вызывает сама себя POST-запросом с указанием некоторого параметра (или нескольких), который в свою очередь обрабатывается веб-сервером особым образом (открытие flash, запись туда, закрытие flash, перезапуск сервисов и т. д.)
Возвращаясь к файловой системе, хочется отметить, что нормальное управление и UART - слегка неподходящие друг другу понятия, поэтому мне захотелось встроить в прошивку какой-нибудь SSH-сервер. Весьма неплохим решением для этого является dropbear. Поскольку собирать его в той среде, в которой он должен работать, возможности нет, придется заняться кросс-компиляцией, что и будет рассмотрено в следующей части. А для этого пристальное изучение файловой системы нам сообщит о том, что следов libc6 там не обнаружено, зато присутствует uClibc версии 0.9.29. 
Подведем итоги перед завершением второй части. У нас есть Linux-2.6.15 MIPS big-endian и uClibc-0.9.29 в качестве библиотеки C, причем поменять ее на что-нибудь другое не получится, т. к. управлением роутера занимается проприетарный веб-сервер. В принципе, для третьей части этой информации хватит.

TP-Link TL-WR1043ND. Вид изнутри глазами извращенца.

Объясню сразу, почему пост называется именно так. Стоит задача "сделать хорошо" IPTV через Wi-Fi. Нормальные люди берут для этого DD-WRT/OpenWRT или какой-нибудь из их деривативов, извращенцы изобретают велосипед. 

Немного об устройстве:
SOHO-роутер TP-Link TL-WR1043ND rev. 1

  • CPU: Atheros AR9132 - MIPS 24K @ 400 MHz
  • Radio: Atheros AR9103 b/g/n MIMO 3x3:2
  • Switch: Realtek RTL8366RB 10/100/1000 Mbps
  • Flash: 8 MB
  • RAM: 32 MB
Более подробные характеристики железа приводить не буду, это сделано за меня более компетентными людьми вот здесь. Немного задержусь на описании свитчевого "камушка". Информации именно по RTL8366RB в сети не так уж и много, наиболее исчерпывающую я нашел, как ни странно, где-то на Али-Экспрессе. В общем, это полноценный L2-свитч с 6 портами - 5 физических и 1 для общения с процессором устройства. В описании указано, что умеет 802.1q VLAN и IGMP Snooping, в чем пока что сомневаться не доводилось.

Следующим пунктом идет разборка. Понадобятся две маленькие отвертки - плоская и "сименс", в народе "крестовая", опционально плоскогубцы. Открутить антенны, снять задние резиновые ножки и выкрутить шурупы. Дальше вставить один из шурупов обратно - это приподнимет верхнюю крышку, желательно ее сразу чем-нибудь зафиксировать, например, отверткой, иначе она защелкнется обратно. Второй отверткой можно сразу надавить на нижнюю крышку изнутри, после этого можно будет отодвинуть черную рамку наружу. Этот пункт следует выполнять аккуратно, иначе есть риск оторвать тонкие проводки, соединяющие выводы Wi-Fi модуля с антенными гнездами. После этого наступает время плоскогубцев - нужно открутить гайки, которыми крепятся выводы антенн. Впрочем, если у вас стальные пальцы и ногти, можно попробовать и так. Этот пункт не является обязательным, но я его крайне рекомендую к выполнению, поскольку болтающаяся на трех хлипких проводках рамка - очень удручающее зрелище. В результате у вас (или у нас, не важно) появится доступ к внутренней стороне "морды". На ней с обеих сторон есть пластиковые защелки, которые нужно слегка отогнуть плоской отверткой, при этом верхняя крышка спереди слегка приподнимется. Аккуратно помогаем ей в этом и сдвигаем ее вперед. Все, роутер разобран :)
На плате можно заметить аккуратные металлизированные отверстия - 4 в ряд и 14 в два ряда по 7. Это UART и JTAG соответственно. Не забудьте достать соответствующие кабеля, USB-TTL для UART-порта понадобится с вероятностью 0,99(9), то есть точно понадобится и не раз. Про JTAG напишу как-нибудь позже, когда появится время на воскрешение полного "кирпича". Кстати, обычный USB-COM не подойдет, нужен именно TTL с уровнем 3.3В. Можно распотрошить USB-COM и понизить на нем напряжение, можно поискать старый кабель от мобильника, некоторые Sony Ericsson и Nokia подойдут, а можно не жмотиться и купить USB-TTL кабель, благо стоит он недорого, около $4. К прочтению второй части рекомендую подготовить кабель, ПК с Linux (можно и Windows, но Putty не настолько удобен, насколько хочется, а потрошение прошивки все равно удобнее в "никсовом" окружении) и много нервов.

P. S. Отсчет от надписи P1 слева направо на UART'е - питание, земля, RX, TX. Питание можно подключить, но это необязательно. Более того, я бы не советовал его подключать вместе со штатным питанием. Вместо - можно, работать будет. Вместе - не пробовал и вам не советую. Земля подключается обязательно, RX платы к TX кабеля и наоборот. Скорость 115200, 8 бит без контроля четности, терминал по вкусу. В моем случае для подключения была взята обычная гребенка, на длинные пины посажен кабель, короткие пины засунуты в плату "на излом". Весьма устойчивый коннект получился, да.

P. P. S. Картинок нет, так как своих не сделал, а чужими пользоваться не хочется. Может быть, когда-нибудь добавлю.