在开发自己的openwrt固件时往往会编写自己的应用程序,那么如何使用openwrt的框架将自己的代码嵌套进去呢?然后随编译出来的固件一起下载的设备中呢,或者动态选择的方式装载呢?
下面两种方式根据自己的理解一一说明,希望可以帮助的别人:
- 随固件一起打包fw
- 通过ipk方式选择安装
首先新建自己的packages
下面具体说下,如何编译一个zl380tw的软件包。假如我们的openwrt目录为$
1、在$ /package目录下创建zl380tw目录及相关的目录
mkdir -p $/package/zl380tw/src
mkdir -p $/package/zl380tw/include
mkdir -p $/package/zl380tw/lib
cd $/package/zl380tw
ls
include lib src
2、创建编写自己的source code
通过第一步文件目录准备好了后,开始准备编写自己的source code了,在此编写的有8个c文件
ls src
tw_hal_verify.c vproc_data_types.h zl380twolf_config.h
tw_ldfwcfg.c zl380twolf_firmware.c zl380twolf_firmware.h
tw_spi_access.c zl380twolf_config.c
3、编写自己的source code makefile
这个src目录下的makefile实际上和wrt没有太多关系,也就是一个正常的编译规则脱离了wrt同样make也可以编译出自己的target obj
下面贴一下src/Makefile或许可以帮到别人
cat /src/Makefile
#seven
#TOOLCHAINDIR=/home/seven/work/mtk/openwrt/mt7620v1505/staging_dir/toolchain-mipsel_24kec+dsp_gcc-4.8-linaro_uClibc-0.9.33.2/bin
#CC=$(TOOLCHAINDIR)/mipsel-openwrt-linux-uclibc-gcc
PROGS_SPI_ACCESS:=tw_spi_access
PROGS_TW=tw
INSTDIR=$(prefix)/usr/bin
INSTMODE=0755
INSTOWNER=root
INSTGROUP=root
OBJS2 := zl380twolf_firmware.o
OBJS1 := zl380twolf_config.o
#TW_OBJS=tw.o
OBJS = $(OBJS1) $(OBJS2)
CPPFLAGS+=-I./ -I../include
LDFLAGS+= -L../lib -lzl380tw -static
all: $(PROGS_SPI_ACCESS) $(PROGS_TW)
$(PROGS_SPI_ACCESS): $(OBJS) tw_spi_access.c
$(CC) $^ $(CPPFLAGS) $(LDFLAGS) $(LDLIBS) -o $@
$(PROGS_TW): $(OBJS) tw_hal_verify.c
$(CC) $^ $(CPPFLAGS) $(LDFLAGS) $(LDLIBS) -o $@
#$(OBJS): tw_spi_access.c twolf.o
# $(CC) $(CFLAGS) $(LDFLAGS) -o $@
$(OBJS1): zl380twolf_config.c
$(CC) -c $(CPPFLAGS) $^ -o $@
#$(CC) tw_spi_access.c zl380twolf_config.c zl380twolf_firmware.c $(CFLAGS) $(LDFLAGS) -o $(PROGS)
$(OBJS2): zl380twolf_firmware.c
$(CC) -c $(CPPFLAGS) $^ -o $@
install: $(PROGS_SPI_ACCESS) $(PROGS_TW)
$(INSTALL) -d $(INSTDIR)
$(INSTALL) -m $(INSTMODE) -o $(INSTOWNER) -g $(INSTGROUP) $(PROGS_SPI_ACCESS) $(INSTDIR)
$(INSTALL) -m $(INSTMODE) -o $(INSTOWNER) -g $(INSTGROUP) $(PROGS_TW) $(INSTDIR)
clean:
rm -f $(PROGS_SPI_ACCESS) $(PROGS_TW) *.o core
4、创建openwrt解析的Makefile
这个makefile才是真正高手wrt读取自己的应用程序创建编译产出的的一个规则,它所在的位置为用户程序的顶层目录即zl380tw目录下
cd $/package/zl380tw
ls
include lib Makefile src
同样贴一下
cat Makefile
#seven
include $(TOPDIR)/rules.mk //像其他package一样添加规则
#include $(INCLUDE_DIR)/kernel.mk
PKG_NAME:= zl380tw //包的名字 可以随便取
PKG_RELEASE:=1 //自定义
PKG_VERSION:=1.0 //自定义
include $(INCLUDE_DIR)/package.mk //读取package规则
#PKG_BUILD_DIR:= $(BUILD_DIR)/$(PKG_NAME)
define Package/zl380tw //创建菜单条目
SECTION:=utils //属于哪个类别,在此属于utils
CATEGORY:=Utilities
TITLE:=Microsemi r/w test //在菜单显示标题
endef
define Package/zl380tw/description //描述信息 自定义
ZL380tw building test
endef
define Build/Prepare //创建包编译位置
mkdir -p $(PKG_BUILD_DIR)/src
$(CP) ./src/* $(PKG_BUILD_DIR)/src/
$(CP) ./include $(PKG_BUILD_DIR)/
$(CP) ./lib $(PKG_BUILD_DIR)/
endef
define Build/Compile //编译路径 此处会执行src/Makefile创建目标程序
$(MAKE) -C $(PKG_BUILD_DIR)/src \
$(TARGET_CONFIGURE_OPTS) CFLAGS="$(TARGET_CFLAGS) -I$(LINUX_DIR)/include"
endef
define Package/zl380tw/install //此处对目标文件产出位置做安排,如果不想打包进fw,需要移除此项,然后通过 opkg install xxx.ipk安装
$(INSTALL_DIR) $(1)/usr/bin
$(INSTALL_BIN) $(PKG_BUILD_DIR)/src/tw $(1)/usr/bin
$(INSTALL_BIN) $(PKG_BUILD_DIR)/src/tw_spi_access $(1)/usr/bin
$(INSTALL_BIN) $(PKG_BUILD_DIR)/src/raklink $(1)/usr/bin
endef
$(eval $(call BuildPackage,zl380tw))
通过以上几步就可以实现自己程序添加到wrt框架中
剩下的就是执行make menuconfig选择刚才添加的package并且make -j4 V=99进行编译
$make menuconfig
Utilities --->
│ │ < > yunbridge..................................... Arduino YUN bridge library │ │
│ │ <*> zl380tw............................................... Microsemi r/w test │ │
│ │ < > zsh.......................................................... The Z shell
编译过程会在build_dir目录下完成
编译结果会放在 bin/[yourtarget]/package目录下
如果打包进fw,会在usr/bin下找到可执行文件
如果采用opk方式,需要将ipk包下载到目标板中执行opkg install *.ipk