一個arm開發板的研究筆記
最近更新:2020-03-03 17:46 周二
#開發主機系統信息
$ lsb_release -a
No LSB modules are available.
Distributor ID:Ubuntu
Description:Ubuntu 18.04.4 LTS
Release:18.04
Codename:bionic
$ cat /proc/version
Linux version 4.15.0-43-generic (buildd@lgw01-amd64-001) (gcc version 7.3.0 (Ubuntu 7.3.0-16ubuntu3)) #46-Ubuntu SMP Thu Dec 6 14:45:28 UTC 2018
文本編輯工具我用的不是vi而是nano
為了使左側顯示行號,下方提示行號
sudo nano /etc/nanorc
去掉 set linenumbers 前的注釋
去掉 set constantshow 前的注釋
#交叉編譯環境
File: gcc-4.4.4-glibc-2.11.1-multilib-1.0_EasyARM-iMX283.tar.bz2
Size: 163749909 bytes
Modified: 2020年2月24日, 23:18:03
MD5: 196AA7CA5A39492CD577D983C9DD1A10
SHA1: 9328B768F87D04504FE524E9DEC5A8409DD69261
CRC32: 7BB9B60F
#開發板內核
File: linux-2.6.35.3-102c9c0.tar.bz2
Size: 74888350 bytes
Modified: 2020年2月24日, 23:20:01
MD5: E52CF122EEF2D38E29BBA9D836FD48FD
SHA1: C61ADCA4D9A5540569FC0D69A0176BD04C58AE29
CRC32: D1EA1131
#sqlite3數據庫工具
File: sqlite-autoconf-3310100.tar.gz
Size: 2887243 bytes
Modified: 2020年2月28日, 00:36:49
MD5: 2D0A553534C521504E3AC3AD3B90F125
SHA1: 0C30F5B22152A8166AA3BEBB0F4BC1F3E9CC508B
CRC32: 25B51AEC
交叉編譯環境搭建
安裝后續編譯可能用到的工具
$sudo apt-get update && apt-get upgrade #先更新下系統
$sudo apt-get install vim tftpd-hpa openssh-server nfs-kernel-server libncurses5-dev lib32z1-dev u-boot-tools autoconf automake libtool
解壓編譯工具
這里要用到剛下載的 gcc-4.4.4-glibc-2.11.1-multilib-1.0_EasyARM-iMX283.tar.bz2
mkdir /usr/local/arm
cd /usr/local/arm
tar -xvf ./gcc-4.4.4-glibc-2.11.1-multilib-1.0_EasyARM-iMX283.tar.bz2 #在執行這個命令前,先將這個文件拷貝到當前目錄(/usr/local/arm)
設置環境變量
mkdir /xjzy
cd /xjzy
新建 setenv.sh 文件
vim setenv.sh
將如下內容輸入到 setenv.sh 中
#!/bin/sh
echo "[=== Setup ARM Compile Environment ===]"
export PATH="$PATH:/usr/local/arm/gcc-4.4.4-glibc-2.11.1-multilib-1.0/arm-fsl-linux-gnueabi/bin"
export ARCH=arm
export CROSS_COMPILE=arm-fsl-linux-gnueabi-
service tftpd-hpa restart
export PS1="\[\e[32;1m\][arm]\[\e[0m\]:\u@\h:\W "
修改 setenv.sh 權限
chmod 777 setenv.sh
以后需要進入交叉編譯環境時,在終端中輸入如下指令,當然,也可以復制上面export行的指令,粘貼到終端中
. /xjzy/setenv.sh #進入交叉編譯環境
編譯內核
編譯內核應在交叉編譯環境下,具體請看 交叉編譯環境搭建 章節
將內核文件復制到/xjzy目錄下,解壓
cd /xjzy
tar -xvf linux-2.6.35.3-102c9c0.tar.bz2
cd linux-2.6.35.3
//默認內核是已經配置好的了,若需要再次配置,可執行如下命令
make menuconfig
配置完成后,就可以進行編譯了
make uImage
[arm]:root@ubuntu:linux-2.6.35.3 make uImage #make uImage前面的部分我虛擬機的名稱等信息
... #出現如下信息時,說明編譯成功
CHK include/linux/version.h
CHK include/generated/utsrelease.h
make[1]: 'include/generated/mach-types.h' is up to date.
CALL scripts/checksyscalls.sh
CHK include/generated/compile.h
Kernel: arch/arm/boot/Image is ready
SHIPPED arch/arm/boot/compressed/lib1funcs.S
AS arch/arm/boot/compressed/lib1funcs.o
LD arch/arm/boot/compressed/vmlinux
OBJCOPY arch/arm/boot/zImage
Kernel: arch/arm/boot/zImage is ready
UIMAGE arch/arm/boot/uImage
Image Name: Linux-2.6.35.3-571-gcca29a0
Created: Fri Feb 28 10:49:02 2020
Image Type: ARM Linux Kernel Image (uncompressed)
Data Size: 2585628 Bytes = 2525.03 KiB = 2.47 MiB
Load Address: 40008000
Entry Point: 40008000
Image arch/arm/boot/uImage is ready
生成的uImage文件在如下目錄
/xjzy/linux-2.6.35.3/arch/arm/boot/uImage
編譯的時候可能會報錯,錯誤的部分代碼如下:
372 @val = @{$canned_values{$hz}};
373 if (!defined(@val)) {
374 @val = compute_values($hz);
375 }
376 output($hz, @val);
將第373行代碼修如下:
372 @val = @{$canned_values{$hz}};
373 if (!@val) {
374 @val = compute_values($hz);
375 }
376 output($hz, @val);
出現這樣錯誤的原因是perl版本升級,因bug原因,將defined(@array)去掉了,可以直接使用數組判斷非空
據說官方有說明,但我不知道怎么查找,寫這個文檔時,我參考的那個頁面忘記是哪個了,所以也沒再此留下對方的腳印
編譯應用程序
以編譯hello.c文件作為樣例
# arm-fsl-linux-gnueabi-gcc hello.c -o hello.o
hello.c的源碼如下
#include <stdio.h>
int main(void)
{
int i;
for (i=0; i<5; i++){
printf("Hello world! (%d)\n", i);
}
return 0;
}
寫個makefile文件簡化編譯過程
為了編譯方便,可以寫一個makefile文件,這樣以后編譯就可以直接輸入make命令了
我沒寫過這個,方法自己搜索一下吧,不復雜
sqlite3數據庫移植
此部分內容參考:DoubleLi的文章成功移植SQLite3到ARM Linux開發板
下載sqlite3源碼
官方網站 https://www.sqlite.org/download.html
sqlite-autoconf-3310100.tar.gz下載
將源碼包放到linux主機工作目錄下
寫此筆記時我用的sqlite版本是3310100
編譯sqlite不需要使用root權限
$ whoami
bootloader #當前登錄用戶名
$ cd ~
$ pwd
/home/bootloader #當前所在位置
解壓sqlite3源碼包
將下載的sqlite-autoconf-3310100.tar.gz文件放到當前目錄
tar zxvf sqlite-autoconf-3310100.tar.gz #解壓
cd sqlite-autoconf-3310100
mkdir _install
配置sqlite3編譯選項
交叉編譯工具路徑加入系統環境變量
下面這三個臨時環境變量其實就是復制的setenv.sh中的
. /xjzy/setenv.sh #進入交叉編譯環境
生成makefile
./configure --host=arm-fsl-linux-gnueabi --prefix=$(pwd)/_install
其中
--host 指定交叉編譯工具,我這里使用的是 arm-fsl-linux-gnueabi ,參考教程上說一般是arm-linux、arm-linux-gnueabihf、arm-none-linux-gnueabi等
--prefix 制定安裝目錄,編譯后的文件會全部放在安裝目錄中,參考教程中說必須是絕對路徑,我沒測試過相對路徑會報什么錯
編譯安裝sqlite3
make
make install
壓縮生成文件
pwd
/home/bootloader/sqlite-autoconf-3310100
arm-fsl-linux-gnueabi-strip _install/lib/libsqlite3.so.0.8.6
arm-fsl-linux-gnueabi-strip _install/bin/sqlite3
復制文件到開發板
后續步驟是在開發板上執行的
將sqlite3復制到/usr/local/bin目錄,
將動態庫文件復制到/usr/local/lib目錄,並對動態庫做鏈接
cd /usr/local/lib
ln -s libsqlite3.so.0.8.6 libsqlite3.so.0
ln -s libsqlite3.so.0.8.6 libsqlite3.so
運行sqlite-在開發板上
在開發板上執行sqlite3命令,看到如下信息說明sqlite3移植成功!
sqlite3
SQLite version 3.31.1 2020-01-27 19:55:54
Enter ".help" for usage hints.
Connected to a transient in-memory database.
Use ".open FILENAME" to reopen on a persistent database.
sqlite>
使用 .help 查看幫助,使用 .quit 退出sqlite命令
libmodbus庫移植
官方網站https://libmodbus.org/download/
將源碼包放到linux主機工作目錄下
寫此筆記時我用的libmodbus版本是3310100
編譯libmodbus不需要使用root權限
解壓libmodbus源碼包
tar -zxvf libmodbus-3.1.6.tar.gz
cd libmodbus-3.1.6/
mkdir _install
配置libmodbus編譯選項
交叉編譯工具路徑加入系統環境變量
下面這三個臨時環境變量其實就是復制的setenv.sh中的
. /xjzy/setenv.sh #進入交叉編譯環境
生成makefile
./configure --build=i686 --host=arm-fsl-linux-gnueabi --enable-static --prefix=$(pwd)/_install
--prefix 指定了安裝目錄,交叉編譯make install的內容會在這個目錄里,解壓源碼包時,我創建的_install目錄在這里,因此這樣設置
編譯安裝libmodbus
make
make install
編譯完成后,在_install目錄下,會新增如下3個文件夾
bootloader@ubuntu:~/libmodbus-3.1.6/_install$ ls -la
...
drwxrwxr-x 3 bootloader bootloader 4096 Feb 28 16:14 include #該目錄中是modbus的頭文件
drwxrwxr-x 3 bootloader bootloader 4096 Feb 28 16:14 lib #該目錄中是modbus動態庫文件
drwxrwxr-x 3 bootloader bootloader 4096 Feb 28 16:14 share #這是個空文件夾
bootloader@ubuntu:~/libmodbus-3.1.6/_install$ ls -la include/modbus/
...
-rw-r--r-- 1 bootloader bootloader 11190 Feb 28 16:14 modbus.h
-rw-r--r-- 1 bootloader bootloader 1199 Feb 28 16:14 modbus-rtu.h
-rw-r--r-- 1 bootloader bootloader 1373 Feb 28 16:14 modbus-tcp.h
-rw-r--r-- 1 bootloader bootloader 2124 Feb 28 16:14 modbus-version.h
bootloader@ubuntu:~/libmodbus-3.1.6/_install$ ls -la lib/
...
-rw-r--r-- 1 bootloader bootloader 138518 Feb 28 16:14 libmodbus.a
-rwxr-xr-x 1 bootloader bootloader 970 Feb 28 16:14 libmodbus.la
lrwxrwxrwx 1 bootloader bootloader 18 Feb 28 16:14 libmodbus.so -> libmodbus.so.5.1.0
lrwxrwxrwx 1 bootloader bootloader 18 Feb 28 16:14 libmodbus.so.5 -> libmodbus.so.5.1.0
-rwxr-xr-x 1 bootloader bootloader 113611 Feb 28 16:14 libmodbus.so.5.1.0
drwxrwxr-x 2 bootloader bootloader 4096 Feb 28 16:14 pkgconfig
bootloader@ubuntu:~/libmodbus-3.1.6/_install$ ls -la lib/pkgconfig/
...
-rw-r--r-- 1 bootloader bootloader 241 Feb 28 16:14 libmodbus.pc
壓縮生成libmodbus
我參考的教程里並沒有對生成的文件進行壓縮,之所以在這里執行,是參考了sqlite里有這一步,執行此步后,文件小了很多
只壓縮了.so文件和.a文件,沒有壓縮lib文件夾中.la后綴的文件,會提示無法識別的文件格式(File format not recognized)
cd _install
arm-fsl-linux-gnueabi-strip lib/libmodbus.so.5.1.0
arm-fsl-linux-gnueabi-strip lib/libmodbus.a
ls -la lib/libmodbus.so.5.1.0
-rwxr-xr-x 1 bootloader bootloader 34320 Feb 28 16:23 lib/libmodbus.so.5.1.0
ls -la lib/libmodbus.a
-rw-r--r-- 1 bootloader bootloader 27308 Feb 28 16:29 lib/libmodbus.a
上面的庫文件中,3個文件libmodbus.so\libmodbus.so.5\libmodbus.so.5.1.0最后是要移值的目標板上的,通常放在/usr/lib目錄下.另外在交叉編譯時,也要拷貝過去.
后面開發應用軟件時,需要用到的頭文件和庫文件,可以通過手工拷貝的方法將頭文件和庫文件臨時拷貝到應用軟件開發的目錄下,並在makefile中指定這些庫文件的目錄.
libmodbus應用軟件的開發和編譯
cd ~ #返回當前用戶根目錄
mkdir modbus-test
cd modbus-test
mkdir -p include/modbus
mkdir include
mkdir lib
touch main.c
touch makefile
將上一步make install生成的_install中文件拷貝到當前目錄下include/modbus文件夾和lib文件夾下
main.c文件內容如下
#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <stdlib.h>
#include <errno.h>
#include <signal.h>
#include <pthread.h>
#include "modbus.h"
#include "modbus-tcp.h"
#include "modbus-version.h"
#if defined(_WIN32)
#include <ws2tcpip.h>
#else
#include <sys/socket.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#endif
#define NB_CONNECTION 5
//xian quan di zhi ding yi
const uint16_t UT_BITS_ADDRESS = 0x13;
const uint16_t UT_BITS_NB = 0x25;
const uint8_t UT_BITS_TAB[] ={0xCD,0x6B,0xB2,0x0E,0x64};
//li san shu ru ji cun qi
const uint16_t UT_INPUT_BITS_ADDRESS=0xC4;
const uint16_t UT_INPUT_BITS_NB = 0x16;
const uint8_t UT_INPUT_BITS_TAB[]= {0xAC,0xDB,0x64};
//bao chi ji cun qi ding yi
const uint16_t UT_REGISTERS_ADDRESS =0x6B;
//
const uint16_t UT_REGISTERS_ADDRESS_SPECIAL = 0x6C;
const uint16_t UT_REGISTERS_NB = 0x03;
const uint16_t UT_REGISTERS_TAB[] = {0x022B,0x0001,0x0064};
//SHU RU JI CUN QI DING YI
const uint16_t UT_REGISTERS_NB_SPECIAL = 0x02;
//
const uint16_t UT_INPUT_REGISTERS_ADDRESS =0x08;
const uint16_t UT_INPUT_REGISTERS_NB = 0x01;
const uint16_t UT_INPUT_REGISTERS_TAB[] = {0x0064};
modbus_t *ctx = NULL;
int server_socket;
modbus_mapping_t *mb_mapping;
static void close_sigint(int dummy)
{
close(server_socket);
modbus_free(ctx);
modbus_mapping_free(mb_mapping);
exit(dummy);
}
void *modbus_tcp(void *args)
{
int master_socket;
int rc;
fd_set refset;
fd_set rdset;
int i;
int fdmax;
int header_length;
ctx=modbus_new_tcp("192.168.1.136",508);
////mb_mapping = modbus_mapping_new(
//UT_BITS_ADDRESS + UT_BITS_NB,
//UT_INPUT_BITS_ADDRESS + UT_INPUT_BITS_NB,
//UT_REGISTERS_ADDRESS +UT_REGISTERS_NB,
// UT_INPUT_REGISTERS_ADDRESS + UT_INPUT_REGISTERS_NB);
// if(mb_mapping == NULL)
//{
// fprintf(stderr,"failed to allocater the mapping:%s\n",
// modbus_strerror(errno));
// modbus_free(ctx);
//return -1;
//}
// chu shi hua ji cun qi
modbus_set_bits_from_bytes(mb_mapping->tab_input_bits,UT_INPUT_BITS_ADDRESS, UT_INPUT_BITS_NB,UT_INPUT_BITS_TAB);
for(i=0;i<UT_INPUT_REGISTERS_NB;i++)
{
mb_mapping->tab_input_registers[UT_INPUT_REGISTERS_NB+i] = UT_INPUT_REGISTERS_TAB[i];
}
for(i=0;i<UT_REGISTERS_NB;i++);
{
mb_mapping->tab_registers[UT_REGISTERS_ADDRESS+i] = UT_REGISTERS_TAB[i];
}
server_socket = modbus_tcp_listen(ctx,NB_CONNECTION);
signal(SIGINT,close_sigint);
FD_ZERO(&refset);
FD_SET(server_socket,&refset);
fdmax=server_socket;
for(;;)
{
rdset = refset;
if(select(fdmax+1,&rdset,NULL,NULL,NULL) == -1)
{
perror("Server select() failure.");
close_sigint(1);
}
for(master_socket=0;master_socket<=fdmax;master_socket++)
{
if(FD_ISSET(master_socket,&rdset))
{
if(master_socket ==server_socket)
{
socklen_t addrlen;
struct sockaddr_in clientaddr;
int newfd;
addrlen= sizeof(clientaddr);
memset(&clientaddr,0,sizeof(clientaddr));
newfd = accept(server_socket,(struct sockaddr *)&clientaddr,&addrlen);
if(newfd == -1)
{
perror("Server accept() error");
}
else
{
FD_SET(newfd,&refset);
if(newfd>fdmax)
{
fdmax=newfd;
}
//printf("New connection from %s:%d on socket %d\n",inet_ntor(clientaddr.sin_adr),clientaddr.sin_port,newfd);
}
}
else
{
uint8_t query[MODBUS_TCP_MAX_ADU_LENGTH];
int data = 0;
int address = 0;
modbus_set_socket(ctx,master_socket);
rc = modbus_receive(ctx,query);
address = (query[header_length+1]<<8+query[header_length+2]);
if(query[header_length]==0x06)
{
}
if(rc != -1)
{
modbus_reply(ctx,query,rc,mb_mapping);
}
else
{
printf("connection closed on socket %d\n",master_socket);
close(master_socket);
FD_CLR(master_socket,&refset);
if(master_socket == fdmax)
{
fdmax--;
}
}
}
}
}
// printf("-----------------------------------------------------------\n");
//for(i=0;i<10;i++)
//{
// printf("baochijicunqi[%d]:%d\n",i,mb_mapping->tab_registers[i]);
//}
}
}
void *modbus_rtu(void *args)
{
modbus_t *ctx = NULL;
ctx = modbus_new_rtu("/dev/ttySP4", 9600, 'N', 8, 1);
if (ctx == NULL)
{
fprintf(stderr, "Unable to allocate libmodbus contex\n");
//return -1;
}
modbus_set_debug(ctx, 1);
modbus_set_slave(ctx, 1);
if (modbus_connect(ctx) == -1)
{
fprintf(stderr, "Connection failed:%s\n", modbus_strerror(errno));
//return -1;
}
int i,rc;
uint16_t tab_reg[64] = {0};
while (1)
{
printf("\n----------------\n");
rc = modbus_read_registers(ctx, 0, 10, tab_reg);
if (rc == -1)
{
fprintf(stderr,"%s\n", modbus_strerror(errno));
//return -1;
}
for (i=0; i<10; i++)
{
mb_mapping->tab_registers[i]=tab_reg[i];
printf("reg[%d] = %d(0x%x)\n", i, tab_reg[i], tab_reg[i]);
}
usleep(5000000);
}
modbus_close(ctx);
modbus_free(ctx);
}
int main(void)
{
pthread_t t1;
pthread_t t2;
int i;
mb_mapping = modbus_mapping_new(
UT_BITS_ADDRESS + UT_BITS_NB,
UT_INPUT_BITS_ADDRESS + UT_INPUT_BITS_NB,
UT_REGISTERS_ADDRESS +UT_REGISTERS_NB,
UT_INPUT_REGISTERS_ADDRESS + UT_INPUT_REGISTERS_NB);
if(mb_mapping == NULL)
{
fprintf(stderr,"failed to allocater the mapping:%s\n",
modbus_strerror(errno));
modbus_free(ctx);
}
pthread_create(&t1,NULL,modbus_tcp,NULL);
pthread_create(&t2,NULL,modbus_rtu,NULL);
while(1)
{
//printf("-----------------------------------------------------------\n");
for(i=0;i<10;i++)
{
//printf("baochijicunqi[%d]:%d\n",i,mb_mapping->tab_registers[i]);
}
sleep(1);
}
getchar();
return 0;
}
makefile文件內容如下
將編譯后的libmodbus復制到開發板
手頭沒有開發板,暫停了,編譯了不知道該怎么測試,所以暫時擱置
goahead移植
此部分內容參考:
GoAhead4.1.0 開發總結一(移植)
GoAhead4.1.0 開發總結二(自定義使用)
goahead源碼下載
當前我使用goahead-5.1.1-src,社區版能能下載當前社區版的源碼,不能下載以前的版本
goahead交叉編譯
解壓源碼
tar -xvf goahead-5.1.1-src.tar
cd goahead-5.1.1
修改Makefile文件
nano Makefile
在Makefile文件開頭添加如下信息
#CROSS_COMPILE 在這里指定交叉編譯環境所在位置及編譯工具前綴
CROSS_COMPILE =/usr/local/arm/gcc-4.4.4-glibc-2.11.1-multilib-1.0/arm-fsl-linux-gnueabi/bin/arm-fsl-linux-gnueabi-
AS = $(CROSS_COMPILE)as
LD = $(CROSS_COMPILE)ld
CC = $(CROSS_COMPILE)gcc
CPP = $(CC) -E
AR = $(CROSS_COMPILE)ar
NM = $(CROSS_COMPILE)nm
STRIP = $(CROSS_COMPILE)strip
OBJCOPY = $(CROSS_COMPILE)objcopy
OBJDUMP = $(CROSS_COMPILE)objdump
ARCH=arm
附我所用的CROSS_COMPILE路徑里的信息
ls /usr/local/arm/gcc-4.4.4-glibc-2.11.1-multilib-1.0/arm-fsl-linux-gnueabi/bin/
arm-fsl-linux-gnueabi-addr2line arm-linux-ar arm-none-linux-gnueabi-as
arm-fsl-linux-gnueabi-ar arm-linux-as arm-none-linux-gnueabi-c++
arm-fsl-linux-gnueabi-as arm-linux-c++ arm-none-linux-gnueabi-cc
arm-fsl-linux-gnueabi-c++ arm-linux-cc arm-none-linux-gnueabi-c++filt
arm-fsl-linux-gnueabi-cc arm-linux-c++filt arm-none-linux-gnueabi-cpp
arm-fsl-linux-gnueabi-c++filt arm-linux-cpp arm-none-linux-gnueabi-ct-ng.config
arm-fsl-linux-gnueabi-cpp arm-linux-ct-ng.config arm-none-linux-gnueabi-g++
arm-fsl-linux-gnueabi-ct-ng.config arm-linux-g++ arm-none-linux-gnueabi-gcc
arm-fsl-linux-gnueabi-g++ arm-linux-gcc arm-none-linux-gnueabi-gcc-4.4.4
arm-fsl-linux-gnueabi-gcc arm-linux-gcc-4.4.4 arm-none-linux-gnueabi-gccbug
arm-fsl-linux-gnueabi-gcc-4.4.4 arm-linux-gccbug arm-none-linux-gnueabi-gcov
arm-fsl-linux-gnueabi-gccbug arm-linux-gcov arm-none-linux-gnueabi-gdb
arm-fsl-linux-gnueabi-gcov arm-linux-gdb arm-none-linux-gnueabi-gprof
arm-fsl-linux-gnueabi-gdb arm-linux-gprof arm-none-linux-gnueabi-ld
arm-fsl-linux-gnueabi-gprof arm-linux-ld arm-none-linux-gnueabi-ldd
arm-fsl-linux-gnueabi-ld arm-linux-ldd arm-none-linux-gnueabi-nm
arm-fsl-linux-gnueabi-ldd arm-linux-nm arm-none-linux-gnueabi-objcopy
arm-fsl-linux-gnueabi-nm arm-linux-objcopy arm-none-linux-gnueabi-objdump
arm-fsl-linux-gnueabi-objcopy arm-linux-objdump arm-none-linux-gnueabi-populate
arm-fsl-linux-gnueabi-objdump arm-linux-populate arm-none-linux-gnueabi-ranlib
arm-fsl-linux-gnueabi-populate arm-linux-ranlib arm-none-linux-gnueabi-readelf
arm-fsl-linux-gnueabi-ranlib arm-linux-readelf arm-none-linux-gnueabi-run
arm-fsl-linux-gnueabi-readelf arm-linux-run arm-none-linux-gnueabi-size
arm-fsl-linux-gnueabi-run arm-linux-size arm-none-linux-gnueabi-strings
arm-fsl-linux-gnueabi-size arm-linux-strings arm-none-linux-gnueabi-strip
arm-fsl-linux-gnueabi-strings arm-linux-strip elftosb
arm-fsl-linux-gnueabi-strip arm-none-linux-gnueabi-addr2line
arm-linux-addr2line arm-none-linux-gnueabi-ar
有些教程里有說需要屏蔽掉下面語句,這一句是用來啟動SSL matrixssl的,具體參考Webs25GettingStarted.pdf文檔中的說明(Page8)
但我在Makefile文件里沒找到下面的語句,因此沒有理會
matrixsslDir:=$(shell ls -d ../matrixssl-3-1*/)
goahead測試
手頭沒有開發板,編譯了不知道該怎么測試,所以抄了以下代碼
將build/linux-arm-default/bin目錄中的:libgo.so goahead self.crt self.key auth.txt route.txt移動到開發板中(最后兩個文件我就沒生成是什么情況,這兩個文件可以從源碼目錄src/文件中取得)
將libgo.so放到/lib或者/usr/lib中
將goahead self.crt self.key auth.txt route.txt放到同一個文件夾中,位置任意我這里放的是/mnt/system中
將任一網頁文件放到開發板的/usr/web/目錄下,goahead源文件解壓后doc/contents/目錄下有個index.html文件可供測試
運行如下命令進行測試,ip地址根據自己開發板的地址適當修改
./goahead -v /usr/web/ 192.168.131.139:80
在主機瀏覽器輸入http://192.168.131.139/
頁面如下顯示(表示程序運行正常):
Congratulations! The server is up and running.
在電腦上編譯運行
tar -xvf goahead-5.1.1-src.tar
cd goahead-5.1.1/
make && sudo make install
sudo cp src/self.key src/self.crt /etc/goahead/
sudo goahead -v --home /etc/goahead /var/www/goahead
#顯示結果如下
goahead: 2: Configuration for Embedthis GoAhead Community Edition
goahead: 2: ---------------------------------------------
goahead: 2: Version: 5.1.1
goahead: 2: BuildType: Debug
goahead: 2: CPU: x64
goahead: 2: OS: linux
goahead: 2: Host: 127.0.1.1
goahead: 2: Directory: /etc/goahead
goahead: 2: Documents: /var/www/goahead
goahead: 2: Configure: me -d -q -platform linux-x86-default -configure . -gen make
goahead: 2: ---------------------------------------------
goahead: 2: Started http://*:80
goahead: 2: Started https://*:443
# 在瀏覽器中打開瀏覽器,輸入linux主機ip地址,終端中顯示如下
goahead: 2: GET /index.html HTTP/1.1
goahead: 2: GET /favicon.ico HTTP/1.1
goahead: 2: Idle connection closed
goahead: 2: Idle connection closed
openssl移植
編譯mosquitto時需要用到openssl,因此先編譯openssl
openssl源碼下載
openssl網站 https://www.openssl.org/source/
GitHub倉庫 https://github.com/openssl/openssl
openssl交叉編譯
. /xjzy/setenv.sh #進入交叉編譯環境
tar -zxvf openssl-1.1.1d.tar.gz
cd openssl-1.1.1d
mkdir _install #新建個文件夾,用於make install存放生成的文件
#./Configure no-shared --prefix=$(pwd)/_install linux-armv4 #no-shared生成靜態庫,這個和下面生成動態庫的命令二選一
./Configure --prefix=$(pwd)/_install linux-armv4 #生成動態庫 --prefix指定生成lib include bin目錄的路徑
make #編譯
#make install #安裝,完成后會在剛指定的_install文件夾中生成安裝文件
make install_sw install_ssldirs #用此方法不生成doc幫助文檔,節省make install時間
編譯完成后_install文件夾內容如下
pwd
/home/bootloader/openssl-1.1.1d/_install/lib
ls -lh
...
lrwxrwxrwx 1 bootloader bootloader 16 Mar 3 16:33 libcrypto.so -> libcrypto.so.1.1
-rwxr-xr-x 1 bootloader bootloader 2.6M Mar 3 16:33 libcrypto.so.1.1
lrwxrwxrwx 1 bootloader bootloader 13 Mar 3 16:33 libssl.so -> libssl.so.1.1
-rwxr-xr-x 1 bootloader bootloader 553K Mar 3 16:33 libssl.so.1.1
#以上兩個文件是后面項目移植需要放在/usr/lib文件夾下
drwxrwxr-x 2 bootloader bootloader 4.0K Mar 3 16:33 engines-1.1
-rw-r--r-- 1 bootloader bootloader 3.8M Mar 3 16:33 libcrypto.a
-rw-r--r-- 1 bootloader bootloader 693K Mar 3 16:33 libssl.a
drwxrwxr-x 2 bootloader bootloader 4.0K Mar 3 16:33 pkgconfig
mosquitto移植-MQTT
Eclipse Mosquitto是實現MQTT協議版本5.0、3.1.1和3.1的開源消息代理(經EPL / EDL許可).Mosquitto輕巧,適合在從低功耗單板計算機到完整服務器的所有設備上使用.
此部分內容參考:
mosquitto 使用時出現的一些問題及其解決辦法
mosquitto源碼下載
Eclipse Mosquitto網站 https://mosquitto.org/
Eclipse Mosquitto下載https://mosquitto.org/download/
可從https://mosquitto.org/files/獲得較早的下載
mosquitto交叉編譯
. /xjzy/setenv.sh #進入交叉編譯環境
tar -zxvf mosquitto-1.6.9.tar.gz
cd mosquitto-1.6.9/
mkdir _install #新建個文件夾,用於make install存放生成的文件
make WITH_SRV=no CC=gcc CXX=g++ CFLAGS="-I$(pwd)/../openssl-1.1.1d/_install/include/" LDFLAGS="-L$(pwd)/../openssl-1.1.1d/_install/lib -lssl -lcrypto"
#在這個例子中,openssl-1.1.1d文件夾 和 mosquitto-1.6.9文件夾在同級目錄下,因此上面的路徑我采用$(pwd)/../openssl-1.1.1d/的書寫方式,也可以使用絕對路徑
make DESTDIR=$(pwd)/_install install #生成安裝文件
編譯完成后_install文件夾內容如下
[arm]:bootloader@ubuntu:_install tree
.
├── etc
| └── mosquitto
... ...
└── usr
└── local
├── bin
│ ├── mosquitto_passwd
│ ├── mosquitto_pub #測試程序,用於向服務器端推送數據
│ ├── mosquitto_rr
│ └── mosquitto_sub #測試程序,用於訂閱服務端端
├── include #開發需要用到的庫?
... ...
├── lib
│ ├── libmosquittopp.so -> libmosquittopp.so.1 #在開發板上創建軟鏈接
│ ├── libmosquittopp.so.1 #拷貝到開發板/usr/bin目錄下
│ ├── libmosquitto.so -> libmosquitto.so.1 #在開發板上創建軟鏈接
│ ├── libmosquitto.so.1 #拷貝到開發板/usr/bin目錄下
│ └── pkgconfig
│ ├── libmosquitto.pc
│ └── libmosquittopp.pc
├── sbin
│ └── mosquitto #MQTT服務器端
└── share
└── man #這里面的是幫助手冊吧!
... ...
mosquitto測試
假設
windows主機ip地址:192.168.131.1
linux主機ip地址 :192.168.131.129
arm開發板ip地址 :192.168.131.200
在windows上安裝MQTT測試軟件
在<https://mosquitto.org/download/>下載windows客戶端mosquitto-1.6.8-install-windows-x64.exe,默認路徑安裝
C:\Program Files\mosquitto目錄下有4個主要exe文件,幫助文檔readme.md/readme-windows.txt
mosquitto.exe #服務
mosquitto_passwd.exe
mosquitto_pub.exe #發布
mosquitto_sub.exe #訂閱
在主機命令行下運行mosquitto.exe開啟服務
在arm開發板上運行訂閱hello
mosquitto_sub -v -t hello -h 192.168.131.1
在pc端或開發板中推送
mosquitto_pub -t hello -h 192.168.131.1 -m "world"
開發板會收到消息
hello world
允許同時有多個訂閱者
可能會遇到的錯誤
問題1:
mosquitto_sub: error while loading shared libraries: libmosquitto.so.1: cannot open shared object file: No such file or directory
mosquitto_pub: error while loading shared libraries: libmosquitto.so.1: cannot open shared object file: No such file or directory
原因: 共享庫安裝到了/usr/local/lib(很多開源共享庫會安裝在這個目錄下)或其他非/lib或非/usr/lib文件夾下,因此需要將共享庫所在文件夾添加到共享庫配置文件/etc/ld.so.conf中,然后執行ldconfig,或將所需要共享庫鏈接到/usr/lib目錄,然后執行ldconfig
解決辦法入下:
方法1:
echo "/usr/local/lib" >> /etc/ld.so.conf #將libmosquitto.so.1所在的路徑加入到/etc/ld.so.conf文件中
cat /etc/ld.so.conf #此時應該看到文件最后一行已經添加了路徑/etc/ld.so.conf
ldconfig #
/etc/ld.so.conf
方法2:
sudo ln -s /usr/local/lib/libmosquitto.so.1 /usr/lib/libmosquitto.so.1
ldconfig