Khadas Vim – DIY box с открытым исходным кодом, разработан компанией Shenzhen Wesion Technology CO., LTD., которая сосредоточена на производстве OTT боксов и перепроектировке аппаратного обеспечения в соответствии с требованием заказчика.
Hardware Features
Khadas Vim это миниатюрный одноплатный ПК работающий на SoC Amlogic S905X включающий четырех-ядерный процессор ARM® Cortex™-A53 и 3D ускоритель ARM® Mali™-450. Наличие технической документации от компании Wesion Technology и открытых исходных кодов позволяет рассматривать Khadas VIM не только как законченное устройство, но и как инженерный образец для разработки собственных решений.
- Amlogic S905X: 2.0 GHz 64Bit Quad-Core ARM® Cortex™-A53 CPU, 750MHz+ Penta Core ARM® Mali™-450 GPU
- Broadcom AP6212/AP6255 Wifi + Bluetooth Module
- 2GB DDR3+8GB/16GB EMMC-V5.0
- HDMI 2.0a with 4K H.265/VP9 10bit & HDR10 Video Processing
- USB-C, Type-C with USB 2.0 OTG Supported
- 40-Pin 2.54mm Header (I2C, I2S, UART, PWM, ADC, USB, SPDIF, etc)
- Tiny form factor: thin with dimensions of credit card (82.0x57.5 mm)
Платы Khadas VIM поддерживают операционные системы на базе ядра Linux (поставки Ubuntu, Buildroot), Android, а также OpenELEC.
Новости компании Wesion Technology, касающиеся платы Khadas VIM, а также техническую поддержку, можно получить на форуме forum.khadas.com.
Toolchains
Для Khadas VIM мы приготовили четыре toolchain-а.
Первый предназначен для создания ПО на архитектуру AArch64, причем сам toolchain работает на x86_64 Linux машинах. Получить его можно на нашем FTP-сервере в каталоге toolchains/x86_64. Выбирать здесь нужно последнюю версию архива с именем 'aarch64-S9XX-linux-glibc-*.tar.gz'.
Второй toolchain предназначен для создания систем, способных работать на 64-битных ARM процессорах, но использующих лишь 32-битные наборы команд. Данный toolchain находится в архиве с именем 'arm8l-A9XX-linux-glibc-*.tar.gz'.
Третий toolchain предназначен для сборки firmware в составе U-Boot и готовит программы под архитектуру ARM® Cortex™-A3, причем без использования GNU Libc. Этот toolchain расположен в каталоге toolchains/x86_64 под именем 'arm-A9XX-eabi-newlib-*.tar.gz'.
И, наконец, четвертый toolchain построен для создания целевых программ низкого уровня, не использующих библиотеку GNU Libc. Данный toolchain можно использовать, например, при создании собственного загрузчика или для сборки U-Boot. Этот toolchain расположен в каталоге toolchains/x86_64 под именем 'aarch64-S9XX-elf-newlib-*.tar.gz'.
Для самостоятельной сборки toolchain-а, необходимо получить ветку toolchains-1.1.x репозитория toolchains, например, следующим образом
$ svn co svn://radix-linux.su/toolchains/branches/toolchains-1.1.x toolchains
И выполнить команду make в соответствующем каталоге:
$ cd toolchains/products/S9XX-glibc/1.1.2 $ make -j8
Напомним здесь, что перед сборкой необходимо подготовить каталог для инсталляции toolchain-а так, как это описано в разделе, посвященном загрузке toolchain-ов с нашего FTP-сервера.
Source Code
Компания Amlogic Co, Inc., которая является разработчиком SoC S905X, распространяет исходные коды на собственном FTP-сервере. Здесь представлены не только коды ядра и загрузчика, а так же все необходимые драйверы устройств, которые обычно представлены на платах базирующихся на SoCs серии S8xx, S9xx.
Однако разработчики платы Khadas VIM ведут собственные репозитории исходных кодов на ресурсе GitHub.
На нашем сервере мы поддерживаем зеркала ключевых репозиториев. Так исходные коды ядра Linux можно найти в репозитории linux.git, а загрузчик, – в репозитории u-boot.git.
Для того, чтобы разобраться, какие именно срезы репозиториев используются при сборке платформы Radix.Linux, следует обратиться к Make-файлам репозитория sources.git. Например, в файле Linux/Khadas/S905X/Makefile, можно видеть, что мы используем ветку ubuntu репозитория https://github.com/khadas/linux.git, поскольку данная ветка наиболее близка для обычных дистрибутивов Linux.
На странице, документации от компании Wesion Technology, можно найти необходимую информацию, позволяющую самостоятельно собрать ядро Linux и загрузчик U-Boot.
Flash Layout
Составить наиболее полное представление о размещении всех компонентов системы, как на загрузочной SD карте, так и во внутренней памяти устройства (eMMC), легче всего на примере инсталляции системы Radix.Linux.
SD Card
Загрузчик, предназначенный для SD карты, записывается в два этапа. Сначала записываются первые 442 байта информации по нулевому смещению от начала карты, затем оставшиеся байты загрузчика, начиная с 512-го, записываются со смещением 512 байтов от начала SD карты. Делается это для того, чтобы не повредить таблицу разделов диска. Всю процедуру записи загрузчика на SD карту можно представить следующими командами:
# dd if=u-boot.sd.bin of=/dev/mmcblk0 bs=1 count=442 # dd if=u-boot.sd.bin of=/dev/mmcblk0 bs=512 skip=1 seek=1
Пользователям системы Radix.Linux нет необходимости самостоятельно заботиться о порядке размещения данных на SD карте. Как мы говорили в разделе Products Release вводной статьи, для записи загрузочного образа достаточно загрузить свежие файлы с FTP сервера, например, из каталога 1.1.620/s9xx-glibc/khadas-vim и выполнить две следующие операции:
# cat khadas-vim.boot-records khadas-vim.ext4fs > SDHC.img # dd if=SDHC.img of=/dev/mmcblk0
Оставшееся место на карте можно распределить с помощью утилиты fdisk, например, создав дополнительный раздел для размещения домашних каталогов пользователей.
Следует отметить, что использование утилиты fdisk совершенно безопасно для загрузчика, который размещен на карте до начала разделов и не затрагивает таблицу разделов в MBR.
Прежде чем приступать к инсталляции системы Radix.Linux во встроенную eMMC память, необходимо очистить eMMC flash. Дело в том, что платы Khadas VIM поставляются с предустановленной системой Android и, при неудачной попытке загрузить ядро, расположенное на SD карте, с помощью стандартного загрузчика, произойдет запуск Android, который разрушит все данные на карте.
Если же eMMC память пуста, то процессор начнет загрузку с SD карты, разумеется, если обнаружит на ней необходимые для этого данные.
Итак, подключившись к плате через серийный порт и остановив загрузку с помощью клавиш <Space>, <Enter> или комбинации <Ctrl>+<C>, мы попадаем в консоль загрузчика.
Для очистки eMMC памяти достаточно выполнить команду store init 3, которая выдаст примерно следующий результат:
kvim# store init 3 emmc/sd response timeout, cmd8, status=0x1ff2800 emmc/sd response timeout, cmd55, status=0x1ff2800 [mmc_startup] mmc refix success [mmc_init] mmc init success switch to partitions #0, OK mmc1(part 0) is current device Device: SDIO Port C Manufacturer ID: 15 OEM: 100 Name: 8WPD3 Tran Speed: 52000000 Rd Block Len: 512 MMC version 5.0 High Capacity: Yes Capacity: 7.3 GiB mmc clock: 40000000 Bus Width: 8-bit DDR [store]amlmmc erase 1emmckey_is_protected : protect start = 0,end = 8191 Caution! Your devices Erase group is 0x400 The erase range would be change to 0x22000~0xe8ffff start = 139264,end = 15269886 kvim#
Теперь можно выключить питание, подключить приготовленную SD карту и осуществить первый запуск системы.
В случае успешной загрузки системы Radix.Linux, пользователь получит приглашение:
. . .
Radix Linux 3.14.29 for Khadas Vim S905X release 1.1 [ tty1 ]
khadas-vim login:
Изначально пароль суперпользователя не задан и войти в систему можно просто указав имя root,
Radix Linux 3.14.29 for Khadas Vim S905X release 1.1 [ tty1 ]
khadas-vim login: root
Last login: Thu Jan 1 00:01:49 UTC 2015 on ttyS0
Linux 3.14.29.
root@khadas-vim:~#
однако, после первого входа в систему, следует установить пароль пользователя root.
eMMC Flash
Убедившись в том, что сделанные нами записи на SD карте исправны и система загружается нормально, можно приступать к инсталляции Radix.Linux.
Перезагрузив систему с помощью команды reboot, необходимо войти в консоль загрузчика (клавиши <Space>, <Enter> или комбинация <Ctrl>+<C>) и последовательно выполнить следующие операции.
Инициализировав mmc интерфейс с помошью команды mmcinfo:
kvim# mmcinfo Device: SDIO Port B Manufacturer ID: 41 OEM: 3432 Name: SD16G Tran Speed: 50000000 Rd Block Len: 512 SD version 3.0 High Capacity: Yes Capacity: 14.5 GiB mmc clock: 40000000 Bus Width: 4-bit
и загрузив параметры ядра из каталога /boot файловой системы, находящейся на SD карте:
kvim# ext4load mmc 0:1 0x01080000 /boot/kvim.dtb 36927 bytes read in 49 ms (735.4 KiB/s)
записываем новую таблицу разделов:
kvim# store dtb write 0x01080000 [store]To run cmd[emmc dtb_write 0x01080000 0x40000] write emmc dtb mmc read lba=0x14000, blocks=0x400 start dts,buffer=0000000073eeb850,dt_addr=0000000073eeb850 parts: 2 00: logo 0000000002000000 1 01: rootfs ffffffffffffffff 4 get_dtb_struct: Get emmc dtb OK! Partition table get from SPL is : name offset size flag =================================================================================== 0: bootloader 0 200000 0 1: reserved 400000 4000000 0 2: env 4400000 400000 0 3: logo 4800000 2000000 1 4: rootfs 6800000 1cb800000 4 mmc read lba=0x2000, blocks=0x2 mmc read lba=0x2002, blocks=0x2 mmc_read_partition_tbl: mmc read partition ERROR! mmc write lba=0x2000, blocks=0x2 mmc write lba=0x2002, blocks=0x2 mmc_write_partition_tbl: mmc write partition OK! partition table success
Таблица записывается в начало раздела reserved и используется в дальнейшем не только загрузчиком, но и ядром Linux для обеспечения доступа к файловым системам на пользовательском уровне.
Здесь следует дать некоторые пояснения.
Дело в том, что разделы bootloader, reserved и env жестко определены в исходном коде загрузчика, а именно, в файле include/emmc_partitions.h:
#ifndef CONFIG_AML_MMC_INHERENT_PART #define PARTITION_RESERVED (0) /* size reserver after each partition */ #define MMC_BOOT_PARTITION_RESERVED (0x2*SZ_1M) /* size reserved after 'bootloader' partition */ #define MMC_BOOT_NAME "bootloader" #define MMC_BOOT_DEVICE_SIZE (0x2*SZ_1M) /* currently U-Boot size is approximately 920K */ #define MMC_RESERVED_NAME "reserved" #define MMC_RESERVED_SIZE (64*SZ_1M) #define MMC_BOTTOM_RSV_SIZE (0) #endif /* CONFIG_AML_MMC_INHERENT_PART */ // #define MMC_CACHE_NAME "cache" // #define MMC_CACHE_SIZE (512*SZ_1M) // this is not used and should be get from spl #define MMC_ENV_NAME "env" #define MMC_ENV_SIZE (0x4*SZ_1M)
Кроме того, в исходном коде ядра (файл include/linux/mmc/emmc_partitions.h):
/* MMC Partition Table */ #define MMC_PARTITIONS_MAGIC "MPT" #define MMC_RESERVED_NAME "reserved" #define SZ_1M 0x00100000 /* the size of bootloader partition */ #define MMC_BOOT_PARTITION_SIZE (2*SZ_1M) /* the size of reserve space behind bootloader partition */ #define MMC_BOOT_PARTITION_RESERVED (2*SZ_1M)
заданы переменные MMC_BOOT_PARTITION_SIZE и MMC_BOOT_PARTITION_RESERVED, с помощью которых процедура инициализации ядра определяет адрес раздела reserved, где находится таблица разделов eMMC памяти.
Адреса остальных разделов, а именно разделов logo и rootfs, определяются в файле kvim.dts и читаются подсистемой команд загрузчика store во время записи параметров ядра (kvim.dtb) и формировании таблицы разделов.
Итак, с помощью команды:
kvim# store dtb write 0x01080000
мы сформировали таблицу разделов eMMC.
Следующим шагом будет запись в раздел bootloader загрузчика, предназначенного специально для eMMC. Данный загрузчик находится в файле u-boot.bin и должен быть записан с нулевым смещением от начала eMMC памяти:
kvim# ext4load mmc 0:1 0x01080000 /boot/u-boot.bin 901120 bytes read in 104 ms (8.3 MiB/s) kvim# store rom_write 0x01080000 0 100000 mmc switch to boot0 success mmc switch to boot1 success mmc switch to user success kvim#
Далее необходимо записать переменные окружения U-Boot в раздел env:
kvim# defenv ## defenv_reserve kvim# saveenv Saving Environment to aml-storage... mmc env offset: 0x4400000 Writing to MMC(1)... done kvim#
На этом этапе, все действия, которые должны были быть произведены средствами загрузчика, выполнены. Однако для того, чтобы мы могли загружать устройство, нам необходимо установить непосредственно систему Radix.Linux, а также дать дополнительную информацию загрузчику и ядру Linux о том, на каком именно разделе eMMC следует искать корневую файловую систему.
Как ни странно, но для того, чтобы загрузчик мог читать файлы из корневой файловой системы, расположенной в разделе rootfs, необходимо создать классическую таблицу разделов в области MBR.
Для создания такой записи нам необходимо еще раз загрузить систему с SD карты и воспользоваться утилитой fdisk.
Проще всего, создание записи в таблице разделов, можно выполнить с помощью следующего скрипта, который подает необходимые команды на вход утилиты fdisk:
#!/bin/sh fdisk /dev/mmcblk1 <<EOF n p 1 212992 a p w EOF
Здесь число 212992 определяет начальный сектор, занимаемый корневой файловой системой и, поскольку размер сектора равен 512 байтов, данное число может быть получено путем деления смещения раздела rootfs от начала eMMC, заданного в байтах, на размер сектора диска:
212992 = 0x6800000 / 512;
Для того, чтобы упростить действия пользователей по созданию записи о разделе для корневой файловой системы в области MBR, в пакете u-boot поставляется файл /boot/rootfs-partition, который содержит необходимые команды для утилиты fdisk.
Итак, загрузив систему с SD карты,
Radix Linux 3.14.29 for Khadas Vim S905X release 1.1 [ tty1 ]
khadas-vim login: root
Last login: Thu Jan 1 00:01:49 UTC 2015 on ttyS0
Linux 3.14.29.
root@khadas-vim:~#
необходимо записать информацию в таблицу разделов MBR с помощью команды:
root@khadas-vim:~# sh /boot/rootfs-partition
создать непосредственно Ext4 файловую систему:
root@khadas-vim:~# mke2fs -t ext4 -L rootfs /dev/mmcblk1p1
и переписать на нее содержимое образа khadas-vim.ext4fs.
Здесь важно подчеркнуть, что копирование файлов следует осуществлять от имени суперпользователя с сохранением всех аттрибутов файлов.
На этом процесс инсталляции системы Radix.Linux полностью завершен и, при включении питания, загрузчик должен вести себя следующим образом.
- Если подключена SD карта и в корневой файловой системе /dev/mmcblk0p1 присутствует скрипт /boot/boot.sd.scr, то загрузчик следует инструкциям, записанным в данном скрипте. Если же файл /boot/boot.sd.scr не будет найден, то загрузчик попытается выполнить стандартную процедуру, предусмотренную для плат Khadas VIM.
- Если SD карта не подключена, то загрузчик попытается выполнить скрипт /boot/boot.scr, который предполагается найти в корневой файловой системе, расположенной в разделе /dev/mmcblk1p1, то есть в разделе rootfs eMMC.
В заключение важно подчеркнуть, что во время инициализации системы, ядро Linux перечитает таблицу разделов, расположенную в области reserved и раздел, известный ранее как /dev/mmcblk1p1, будет переименован в /dev/rootfs. Кроме того, все известные разделы eMMC, в файловой системе /dev, будут представлены по именам:
/dev/bootloader /dev/reserved /dev/env /dev/logo /dev/rootfs
Наверное это удобно для доступа к разделам во время работы системы.
Мы рассмотрели процесс ручной инсталляции системы Radix.Linux для того, чтобы наиболее полным образом составить представление об организации памяти. В дальнейшем значения размеров и смещений отдельных разделов дискового пространства могут быть изменены, однако, основной смысл представленного материала останется прежним.
Wireless
Платы Khadas VIM поставляются в разных модификациях. На одних могут быть установлены WiFi модули AP6212, на других – AP6255. Если на плате установлен модуль AP6255, то для того, чтобы драйвер мог загрузить firmware, необходимо поменять символическую ссылку в каталоге /lib/firmware/broadcom/ap6xxx с помощью следующих команд:
# cd /lib/firmware/broadcom/ap6xxx # ln -sf nvram_ap6255.txt nvram.txt
Файл /etc/wpa_supplicant.conf, после установки системы Radix.Linux, содержит следующие данные.
ctrl_interface=/var/run/wpa_supplicant ctrl_interface_group=root update_config=1 eapol_version=1 ap_scan=1 fast_reauth=1 pmf=1 disable_scan_offload=1 wowlan_triggers=any p2p_no_go_freq=5170-5740 p2p_search_delay=0 no_ctrl_interface= ctrl_interface=wlan0 p2p_go_intent=13
Прежде чем использовать wpa_supplicant для соединения необходимо добавить существующие сети, например:
network={ scan_ssid=0 proto=WPA key_mgmt=WPA-PSK pairwise=CCMP TKIP group=CCMP TKIP WEP104 WEP40 } network={ ssid="your_id" psk=YOUR_HEX_KEY }
Здесь your_id является именем сети, а YOUR_HEX_KEY – представляет собой шестнадцатеричный пароль для сети, использующей WPA-PSK/WPA2-PSK шифрование.
Создать шеснадцатеричный ключ для сети можно с помощью утилиты wpa_passphrase:
# wpa_passphrase your_id passphrase network={ ssid="your_id" #psk="passphrase" psk=59e0d07fa4c7741797a4e394f38a5c321e3bed51d54ad5fcbd3f84bc7415d73d }
Где passphrase представляет собой текстовый пароль для сети your_id.
После создания необходимых записей в файле /etc/wpa_supplicant.conf подключение к беспроводной сети можно осуществить с помошью дух простых комманд:
# /usr/sbin/wpa_supplicant -B -i wlan0 -c /etc/wpa_supplicant.conf # dhcpcd wlan0
В заключение необходимо сказать, что компания Shenzhen Wesion Technology CO., LTD. уделяет большое внимание поддержке пользователей и организовало специальный домен khadas.com с субдоменами, на которых можно найти документацию и форум открыторго сообщества.