Loading... ## 基础信息 OS: Ubuntu 16.04 xenial SDK 版本: Hi3516EV200R001C01SPC012 - Hi3516EV200_SDK_V1.0.1.1 SDK 包路径:`Hi3516EV200R001C01SPC012\01.software\board\Hi3516EV200_SDK_V1.0.1.2.tgz` 开发板地址:`192.168.1.54` 开发板 MAC:`7C:A7:B0:F6:E4:10` 开发板 senser: `GC2053` 虚拟机地址:`192.168.1.141` ### 目录结构 下面的目录树列出了在整个配置流程中涉及的所有 SDK 和板端应用相关文件和目录的相对位置关系 ```bash ~ ├── ... ├── arm-himix100-linux # 交叉编译器 │ ├── ... │ └── arm-himix100-linux.install # 交叉编译工具安装脚本 ├── DPO_MT7601U_LinuxSTA_3.0.0.4_20130913 # MT7601U 驱动包 │ ├── ... │ └── mcu │ ├── ... │ └── bin │ ├── ... │ └── MT7601.bin # MT7601U 驱动固件 ├── Hi3516EV200_SDK_V1.0.1.2 # SDK 包 │ ├── ... │ ├── mpp │ │ ├── ... │ │ ├── ko # 板端 ko 库目录 │ │ │ ├── ... │ │ │ ├── hi3516ev200_base.ko │ │ │ ├── hi3516ev200_isp.ko │ │ │ ├── hi3516ev200_ive.ko │ │ │ ├── load3516ev200 # ko 库加载脚本 │ │ │ └── sys_config.ko │ │ └── sample # 示例项目目录 │ │── osdrv │ │ ├── ... │ │ ├── opensource │ │ │ ├── ... │ │ │ └── kernel │ │ │ ├── ... │ │ │ └── linux-4.9.y # linux 内核源码 │ │ │ ├── ... │ │ │ ├── arch │ │ │ │ ├── ... │ │ │ │ └── arm │ │ │ │ ├── ... │ │ │ │ └── boot │ │ │ │ ├── ... │ │ │ │ └── uImage # 单独构建的 kernel 镜像 │ │ │ └── firmware │ │ │ ├── ... │ │ │ └── mt7601u.bin # MT7601U 驱动固件 │ │ └── pub │ │ ├── ... │ │ ├── hi3516ev200_spi_image_uclibc # osdrv 构建目标目录 │ │ │ ├── ... │ │ │ ├── rootfs_hi3516ev200_64k.jffs2 # SPI Nor 文件系统镜像 │ │ │ ├── u-boot-hi3516ev200.bin # fastboot 镜像 │ │ │ └── uImage_hi3516ev200 # linux kernel 镜像 │ │ ├── rootfs_uclibc_64k_custom.jffs2 # 单独构建的 SPI Nor 文件系统镜像 │ │ ├── rootfs_uclibc # 文件系统目录 │ │ │ ├── ... # 以下列出将要添加到文件系统中的文件 │ │ │ └── etc │ │ │ ├── ... │ │ │ ├── init.d │ │ │ │ ├── ... │ │ │ │ ├── S80wireless # 自行创建的无线网络初始化脚本 │ │ │ │ └── rcS # 文件系统初始化脚本 │ │ │ ├── ... │ │ │ └── wpa_supplicant.conf │ │ └── rootfs_uclibc.tgz # 文件系统包 │ ├── sdk.cleanup # osdrv 打包脚本 │ └── sdk.unpack # osdrv 解包脚本 ├── lrzsz-0.12.20 # lrzsz 源码 │ ├── ... │ └── _install # 构建目标目录 │ ├── ... │ └── bin │ ├── ... │ ├── lrz │ └── lsz ├── osdrv_packages # 用于构建 osdrv 的源码包 └── wpa_supplicant # 构建 wpa_supplicant 应用源码及其依赖库源码 ├── dbus-1.13.20 # dbus 源码 ├── expat-2.4.3 # expat 源码 ├── install # 构建目标目录 │ ├── dbus │ ├── libexpat │ ├── libnl │ ├── libssl │ └── wpa_supplicant │ └── usr │ └── local │ └── sbin │ ├── wpa_cli │ ├── wpa_passphrase │ └── wpa_supplicant ├── libnl-3.5.0 # libnl 源码 ├── openssl-1.1.1m # openssl 源码 └── wpa_supplicant-2.10 # wpa_supplicant 源码 ``` ## 切换为 bash 运行 `sudo dpkg-reconfigure dash` 选择 `NO` Ubuntu 默认使用 `dash` 作为 shell,SDK 中大部分脚本基于 `bash` 编写,这里需要手动切换,否则可能出现 **脚本无法运行** 或 **无法获取变量导致递归修改根目录权限** ## 编译 osdrv 安装依赖包 ```bash sudo apt install libncurses5-dev make libc6 lib32z1 lib32stdc++6 zlib1g-dev ncurses-term libncursesw5-dev g++ u-boot-tools liblzo2-dev uuid-dev pkg-config texinfo texlive gperf bison gawk curl upx pngquant flex libnl-3-dev libdbus-1-dev ``` 解压交叉编译工具包并安装 ```bash tar zxvf arm-himix100-linux.tgz chmod +x arm-himix100-linux/arm-himix100-linux.install cd arm-himix100-linux && ./arm-himix100-linux.install && cd .. ``` 运行 SDK 目录下 `sdk.unpack` 根据 `osdrv/readme_cn.txt` 目录所述下载源码包并移动至指定目录下,或运行打包好的 `osdrv_packages` 中的 `cp_packages.sh` 脚本(暂不提供下载地址) 进入开发包中 `osdrv` 目录下,开始编译,不要在 `make all` 命令后使用 `-j` 选项,有可能因执行顺序不同编译失败 ```shell cd osdrv make all ``` Makefile 中使用了大量 `>/dev/null 2>&1` 重定向标准及错误输出,导致编译或配置过程出现错误时无法定位错误位置或解决方案,如果出现编译失败的情况请找到距离报错处最近的一条编译命令并手动编译,定位错误 按照以上步骤编译好 SDK 后目录结构应如下所示 ```bash Hi3516EV200_SDK_V1.0.1.1 ├─ drv ├─ mpp ├─ osal ├─ osdrv ├─ package ├─ scripts ├─ sdk.cleanup └─ sdk.unpack ``` 其中 `mpp` 目录用于存放初始化板端环境的脚本以及运行库 `osdrv` 目录用于存放编译好的分区镜像及相关工具,结构如下 ```bash osdrv ├── Makefile ├── opensource ├── pub │ ├── bin │ │ ├── board_uclibc │ │ └── pc │ ├── hi3516ev200_spi_image_uclibc │ │ ├── rootfs_hi3516ev200_128k.jffs2 │ │ ├── rootfs_hi3516ev200_256k.jffs2 │ │ ├── rootfs_hi3516ev200_2k_128k_32M.ubifs │ │ ├── rootfs_hi3516ev200_2k_24bit.yaffs2 │ │ ├── rootfs_hi3516ev200_2k_4bit.yaffs2 │ │ ├── rootfs_hi3516ev200_4k_24bit.yaffs2 │ │ ├── rootfs_hi3516ev200_4k_256k_50M.ubifs │ │ ├── rootfs_hi3516ev200_4k_4bit.yaffs2 │ │ ├── rootfs_hi3516ev200_64k.jffs2 │ │ ├── u-boot-hi3516ev200.bin │ │ └── uImage_hi3516ev200 │ └── rootfs_uclibc.tgz ├── readme_cn.txt ├── readme_en.txt ├── rootfs_scripts └── tools ``` 编译后会产生多个 rootfs 镜像,我们可以先只烧录 u-boot 镜像后直接启动 根据日志中 `SPI Nor` 和 `NAND` 项的值来判断 Flash 类型 其中 Nand 镜像命名规则为 `rootfs_hi3516ev200_{PageSize}_{EccType}.yaffs2` Nor 镜像命名规则为 `rootfs_hi3516ev200_{BlockSize}.jffs2` 我手中的 Hi3516EV200 使用 Nor 格式,根据类似如下日志可知 BlockSize 为 64KB ```bash Block:64KB hifmc_spi_nor_probe(1706): Chip:32MB hifmc_spi_nor_probe(1707): Name:"MX25L(256/257)XX" SPI Nor total size: 32MB ``` ## 串口调试 有些开发板板封装了 TTL 接口,直接按定义连接即可 另一种型号的开发板没有封装 TTL 接口,但预留了孔位,在开发板 `Hi3516 ERNCV200 芯片临近板边缘的一侧` 预留了两个过孔,其中 `靠近晶振一侧` 的过孔为 `TX`,接 USB-TTL 板 `RX`;另一侧为 `RX`,接 USB-TTL 板 `TX`,地线可以直接接在 `开发板四脚的过孔` 上 安装 USB-TTL 板芯片对应驱动后即可通过串口进入开发板终端,例如 `CP210x` 或 `CH340` 等 ## 编译 lrzsz lrzsz 可以通过串口或 telnet 等途径传输小文件 [lrzsz](https://ohse.de/uwe/software/lrzsz.html) ```bash wget https://ohse.de/uwe/releases/lrzsz-0.12.20.tar.gz tar zxvf lrzsz-0.12.20.tar.gz cd lrzsz-0.12.20 ``` ```bash CC=arm-himix100-linux-gcc ./configure --host=arm-himix100-linux --build=arm-himix100-linux --prefix=$PWD/_install --cache-file=./arm-himix100-linux.cache make -j12 make install ``` _install/bin/lrz _install/bin/lsz ## Telnet 手动运行或在板端文件系统 `/etc/init.d/rcS` 中写入如下命令即可 ```bash telnetd & ``` ## 烧写系统 打开 HiTool 工具,通过串口连接开发板,将**传输方式**更改为`串口`,使用`按分区烧写`,按照如下分区配置烧写镜像 > 串口烧写需要进入 boot,所以开始烧写前需要将开发板下电,点击烧写按钮开始烧写后在 15 秒内上电 | 分区名 | 偏移 | 长度 | 文件名 | 器件类型 | 文件系统 | | :------: | :---------: | :-----------: | :--------------------------: | :------: | :------: | | fastboot | 0 (0M) | 80000 (1M) | u-boot-hi3516ev200.bin | spi nor | none | | kernel | 100000 (1M) | 400000 (4M) | uImage_hi3516ev200 | spi nor | none | | rootfs | 500000 (5M) | 1b00000 (27M) | rootfs_hi3516ev200_64k.jffs2 | spi nor | none | ## 配置启动参数 在 HiTool 中打开终端工具,使用串口连接开发板 分区镜像烧写完成后会自动执行 `reset` 命令从 u-boot 重启系统,但由于没有配置启动参数导致系统只能进入 u-boot,无法进入系统 - u-boot 模式下终端格式为 `hisilicon #`,进入系统后格式为 `路径 #` - 在 u-boot 终端下输入如下命令,参数根据烧写的镜像以及实际需求进行配置 - 开发板的内存分为两种,一种是 OS Memory,一种是 MMZ Memory;开发板内存的管理机制为`从总内存中减去 OS Memory,剩下的分配给 MMZ`,而开发板推送视频流等服务需要占用一定 MMZ Memory。 - 使用 `setenv` 命令设置系统变量后需要在重启前使用 `saveenv` 保存,否则所有更改在重启后都会丢失 - 启动参数中的文件系统类型、分区名以及分区长度需要与 HiTool 中烧写时设置一致,否则在启动时会找不到分区 ```shell setenv bootargs 'mem=32M console=ttyAMA0,115200 root=/dev/mtdblock2 rootfstype=jffs2 rw mtdparts=hi_sfc:1M(boot),4M(kernel),27M(rootfs)' setenv bootcmd 'sf probe 0;sf read 0x42000000 0x100000 0x400000;bootm 0x42000000' saveenv reset ``` ## 基于 MT7601U 连接无线网络 本文中使用 `wpa_supplicant` 操作无线网卡,该工具依赖 `libssl` `libnl` `libexpat` `dbus` ### libssl [OpenSSL](https://www.openssl.org/source/) ```bash wget https://www.openssl.org/source/openssl-1.1.1m.tar.gz tar zxvf openssl-1.1.1m.tar.gz cd openssl-1.1.1m ./config no-asm no-shared no-async --prefix=$PWD/../install/libssl --cross-compile-prefix=arm-himix100-linux- ``` 删除 `Makefile` 中所有 `-m64` 选项 ```bash make -j12 make install ``` ### libnl [libnl](http://www.linuxfromscratch.org/blfs/view/svn/basicnet/libnl.html) ```bash wget https://github.com/thom311/libnl/releases/download/libnl3_5_0/libnl-3.5.0.tar.gz tar zxvf libnl-3.5.0.tar.gz cd libnl-3.5.0 ./configure --host=arm-himix100-linux --prefix=$PWD/../install/libnl --enable-static make -j12 make install ``` ### libexpat [libexpat](https://github.com/libexpat/libexpat/) ```bash wget https://github.com/libexpat/libexpat/releases/download/R_2_4_3/expat-2.4.3.tar.gz tar zxvf expat-2.4.3.tar.gz cd expat-2.4.3 ./configure --prefix=$PWD/../install/libexpat --host=arm-himix100-linux --enable-shared --enable-static make -j12 make install ``` ### dbus [dbus](https://dbus.freedesktop.org/releases/dbus/) ```bash wget https://dbus.freedesktop.org/releases/dbus/dbus-1.13.20.tar.xz tar xvf dbus-1.13.20.tar.xz cd dbus-1.13.20 export PKG_CONFIG_PATH=$PKG_CONFIG_PATH:$PWD/../install/libexpat/lib/pkgconfig/ ./configure --prefix=$PWD/../install/dbus --host=arm-himix100-linux --enable-shared --enable-static CFLAGS=-I$PWD/../install/libexpat/include LDFLAGS=-L$PWD/../install/libexpat/lib --disable-tests make -j12 make install ``` ### wpa_supplicant [wpa_supplicant](http://w1.fi/releases/) ```bash wget http://w1.fi/releases/wpa_supplicant-2.10.tar.gz tar zxvf wpa_supplicant-2.10.tar.gz cd wpa_supplicant-2.10/wpa_supplicant cp defconfig .config ``` 将以下代码加入 `.config` ```makefile CFLAGS += -I../../install/libssl/include LIBS += -L../../install/libssl/lib CFLAGS += -I../../libnl-3.5.0/include/linux-private CFLAGS += -I../../install/libnl/include CFLAGS += -I../../install/libnl/include/libnl3 LIBS += -L../../install/libnl/lib CFLAGS += -I../../install/dbus/include LIBS += -L../../install/dbus/lib LDFLAGS += -pthread CC = arm-himix100-linux-gcc ``` 打开 `Makefile` 并分别找到 `wpa_cli` `wpa_passphrase` `wpa_supplicant` 的编译选项,在其编译命令后添加 `-static` 以使用静态链接库 例如找到 `wpa_supplicant` 的编译选项如下 ```makefile wpa_supplicant: $(BCHECK) $(OBJS) $(EXTRA_progs) $(Q)$(LDO) $(LDFLAGS) -o wpa_supplicant $(OBJS) $(LIBS) $(EXTRALIBS) @$(E) " LD " $@ ``` 将其修改为 ```makefile wpa_supplicant: $(BCHECK) $(OBJS) $(EXTRA_progs) $(Q)$(LDO) $(LDFLAGS) -o wpa_supplicant $(OBJS) $(LIBS) $(EXTRALIBS) -static @$(E) " LD " $@ ``` 编译应用 ```bash make -j12 make install DESTDIR=$PWD/../../install/wpa_supplicant ``` 使用 `arm-himix100-linux-strip` 命令裁剪应用 将 `wpa_cli` `wpa_passphrase` `wpa_supplicant` 复制到文件系统,并在文件系统 `etc` 目录下创建 `wpa_supplicant.conf` 文件并写入如下配置 ```conf ctrl_interface=/var/run/wpa_supplicant update_config=1 ``` ### 连接 WiFi 以下为板端配置 开启网卡配置网络并启动 `wpa_supplicant`,其中 MAC 地址、设备 IP 地址及路由地址请 **根据实际情况配置** ```bash ifconfig wlan0 up ifconfig wlan0 hw ether 7C:A7:B0:F6:E4:10 ifconfig wlan0 192.168.1.54 netmask 255.255.255.0 route add default gw 192.168.1.1 wpa_supplicant -D nl80211 -i wlan0 -c /etc/wpa_supplicant.conf -B ``` `wpa_cli -i wlan0` 进入交互命令,交互命令行中退格使用 `Ctrl + Backspace` ```bash # 搜索 WiFi scan # 输出搜索结果 scan_result # [WPA-PSK-CCMP+TKIP][WPA2-PSK-CCMP+TKIP][ESS] set_network 0 ssid "name" set_network 0 psk "psk" enable_network 0 # [None] set_network 0 ssid "name" set_network 0 key_mgmt NONE enable_network 0 # 保存 save_config # 关闭连接 disable_network 0 # 列出所有保存的连接 list_network # 选择第一个保存的连接 select_network 0 # 连接第一个保存的连接 enable_network 0 ``` 将以上步骤整理成自动化脚本写入板端文件系统 `/etc/init.d/S80wireless` 并使用 `chmod +x S80wireless` 赋予执行权限 ```bash #!/bin/sh wlandev=wlan0 phyaddr=7C:A7:B0:F6:E4:10 ipaddr=192.168.1.54 netmask=255.255.255.0 gateway=192.168.1.1 ifconfig $wlandev up ifconfig $wlandev hw ether $phyaddr ifconfig $wlandev $ipaddr netmask $netmask route add default gw $gateway wpa_supplicant -D nl80211 -i $wlandev -c /etc/wpa_supplicant.conf -B ``` 板端开机后运行一次 `wpa_passphrase "ssid" "psk" >> /etc/wpa_supplicant.conf` 重启即可自动连接 ### MT7601U Driver [DPO_MT7601U_LinuxSTA_3.0.0.4_20130913.tgz](https://dl.leviatan.cn/DPO_MT7601U_LinuxSTA_3.0.0.4_20130913.tgz) linux kernel 加载固件分为两种途径 - 读取文件系统 `/lib/firmware` 目录下固件 - 将固件整合进 linux kernel 第一种方法由于挂载文件系统在网卡加载固件之后,故不可行,这里选择将固件整合进 kernel 将固件 `DPO_MT7601U_LinuxSTA_3.0.0.4_20130913/mcu/bin/MT7601.bin` 复制到 kernel 源码中 `firmware` 目录下并重命名为 `mt7601u.bin` 对 kernel 执行 `menuconfig` 结束生成 `.config` 配置后,在该文件中修改 `CONFIG_EXTRA_FIRMWARE` 的值为空格分隔的固件名,例如 `CONFIG_EXTRA_FIRMWARE="a.bin b.bin"`,并添加 `CONFIG_EXTRA_FIRMWARE_DIR="firmware"` 修改完成后应如下所示 ```config CONFIG_EXTRA_FIRMWARE_DIR="firmware" CONFIG_EXTRA_FIRMWARE="mt7601u.bin" ``` ## kernel with MT7601U support osdrv/opensource/kernel/linux-4.9.y ```bash make ARCH=arm CROSS_COMPILE=arm-himix100-linux- menuconfig # Networking support —> Wireless # <*> cfg80211 - wireless configuration API # <*> Generic IEEE 802.11 Networking Stack (mac80211) # Networking support —> RF switch subsystem support # <*> GPIO RFKILL driver # Device Drivers —> Network device support -> Wireless LAN # [*] MediaTek devices # <*> MediaTek MT7601U (USB) support # <*> IEEE 802.11 for Host AP (Prism2/2.5/3 and WEP/TKIP/CCMP) # [*] Support downloag firmware images with Host AP driver # [*] Support for non-volatile firmware download make ARCH=arm CROSS_COMPILE=arm-himix100-linux- uImage -j12 ``` ## rootfs with custom files osdrv/pub ```bash tar zxvf rootfs_uclibc.tgz ./bin/pc/mkfs.jffs2 -d rootfs_uclibc -l -U -e 0x10000 -o rootfs_uclibc_64k_custom.jffs2 # -d Build file system from directory DIR # -l Create a little-endian filesystem # -e Use erase block size SIZE 0x10000 = 64KB # -o Output to FILE ``` ## 使用 NFS 挂载服务器目录 ### 搭建 NFS 服务器 该步骤所有操作均位于虚拟机端 安装 NFS 服务端 ```bash sudo apt install nfs-kernel-server ``` 将需要通过 NFS 共享的目录按下面格式写入 `/etc/export` 其中 IP 地址用于限制只允许指定 IP 挂载访问 NFS,可以使用类似 `192.168.1.*` 和 `192.168.1.0/24` 的写法 ```bash /path/to/nfs/dir 192.168.1.54(rw,sync,no_root_squash,no_subtree_check) ``` 导出共享目录并重启 NFS 服务 ```bash sudo exportfs -a sudo systemctl restart nfs-server ``` ### 固定端口及开放防火墙 若需要为虚拟机设置防火墙,需要配置 NFS 相关服务使用固定端口 ```bash sudo sed -i 's/RPCMOUNTDOPTS="--manage-gids"/RPCMOUNTDOPTS="--manage-gids -p 30001"/' /etc/default/nfs-kernel-server sudo touch /etc/modprobe.d/options.conf sudo tee -a /etc/modprobe.d/options.conf >/dev/null << EOF options lockd nlm_udpport=40002 options lockd nlm_tcpport=40002 EOF sudo tee -a /etc/modules >/dev/null << EOF lockd EOF ``` 开放防火墙以 `firewalld` 为例 ```bash sudo firewall-cmd --zone=public --add-port=111/tcp --add-port=111/udp --add-port=2049/tcp --add-port=2049/udp --add-port=30001-30002/tcp --add-port=30001-30002/udp --permanent sudo firewall-cmd --reload ``` 重启后即可生效 ### 板端挂载 NFS 该步骤所有操作均位于板端 将虚拟机中 NFS 挂载到 `/mnt` 目录 ```bash mount -t nfs -o nolock -o tcp -o rsize=32768,wsize=32768 192.168.1.141:/path/to/nfs/dir /mnt ``` ### 配置板端环境变量 将以下配置写入 `/root/.profile`,用于启动板端 PQ 工具 其中板端 PQ 工具位于 SDK 目录下 `Hi3516EV200R001C01SPC012\01.software\pc\PQTools\Hi3516EV200_PQ_V1.0.1.2.tgz` 具体路径请根据实际情况修改 ```shell export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/path/to/mpp/lib export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:/path/to/Hi3516EV200_PQ_V1.0.1.2/libs ``` <!-- ## Shell ### `isptool.sh` ```shell #!/bin/sh cd /mnt/Hi3516EV200_PQ_V1.0.1.2 ./HiIspTool.sh -a gc2053 ``` ### `load_ko.sh` ```shell #!/bin/sh cd /mnt/mpp/ko chmod +x load3516ev200 ./load3516ev200 -i -sensor gc2053 ``` ### `mount_nfs.sh` ```shell #!/bin/sh mount -t nfs -o nolock -o tcp -o rsize=32768,wsize=32768 192.168.1.141:/home/simonriley/NFS /mnt ``` ### `S80network` ```shell #!/bin/sh wlandev=eth0 phyaddr=7C:A7:B0:F6:E4:10 ipaddr=192.168.1.54 netmask=255.255.255.0 gateway=192.168.1.1 # WIRELESS=true if [ ${WIRELESS} ]; then wlandev=wlan0 fi ifconfig $wlandev up ifconfig $wlandev hw ether $phyaddr ifconfig $wlandev $ipaddr netmask $netmask route add default gw $gateway if [ ${WIRELESS} ]; then wpa_supplicant -D nl80211 -i $wlandev -c /etc/wpa_supplicant.conf -B fi ``` --> 最后修改:2022 年 02 月 26 日 © 允许规范转载 赞 如果觉得我的文章对你有用,请随意赞赏