企业网站建立公司,php+mysql 网站建设,上海物联网app开发公司,菏泽炫佑网站建设openwrt package介绍
OpenWrt 构建系统主要围绕package的概念展开。不管是什么软件#xff0c;几乎都对应一个package。 这几乎适用于系统中的所有内容#xff1a;HOST工具、交叉编译工具链、Linux 内核、内核mod、根文件系统和上层的应用软件。
一个 OpenWrt package本质上…openwrt package介绍
OpenWrt 构建系统主要围绕package的概念展开。不管是什么软件几乎都对应一个package。 这几乎适用于系统中的所有内容HOST工具、交叉编译工具链、Linux 内核、内核mod、根文件系统和上层的应用软件。
一个 OpenWrt package本质上是一个目录其中包含
OpenWrt package Makefile描述软件的获取、构建和打包过程必需OpenWrt package 补丁目录用于修改package的源代码可选OpenWrt package 附带的其他静态文件例如初始化脚本文件、默认配置、脚本或其他支持文件可选
├── miniupnpd
│ ├── files
│ ├── Makefile
│ └── patches如果这个package不需要源码或者源码是在线下载的(git、svn、http方式等等)那么只需要一个上述的OpenWrt package就可以了否则还需要一个package 源码的目录这个目录比较随意可以放在任何地方甚至可以放在OpenWrt package目录内部不过为了方便管理建议还是将源码和OpenWrt package分开。
├── miniupnpd
│ ├── files
│ ├── Makefile
│ ├── patches
│ └── src # 新增源码目录接下来依次介绍这4个部分的规范
Makefile (必要)
Makefile文件是用来描述软件的获取、构建和打包过程它是必需的而且具有一定的格式。 而且这里的Makefile文件与传统的makefile文件也是有区别的编写时需要特别注意。
PKG_*部分
PKG_NAME - 包的名称可以通过menuconfig 查看,是人为定义的name
PKG_VERSION - 需要下载的package版本号通常和PKG_SOURCE配合使用
PKG_RELEASE - 当前package Makefile 的版本
PKG_LICENSE - 软件包可用的许可证SPDX 形式。
PKG_LICENSE_FILES-包含许可证文本的文件
PKG_BUILD_DIR -package编译目录在哪里编译这个package,默认为$(BUILD_DIR)/$(PKG_NAME)
PKG_SOURCE - package的源码压缩包名(busybox-$(PKG_VERSION).tar.bz2)
PKG_SOURCE_URL - 从哪里下载package的源码
PKG_HASH - package的源码压缩包的校验和。MD5或SHA256格式默认使用 SHA256请参阅 script/download.pl
PKG_CAT - 如何解压缩源文件zcat、bzcat、unzip
PKG_BUILD_DEPENDS - 需要在此包之前构建的包。如果当前package在构建时需要依赖另一个package的文件或者库则需要使用此选项指定依赖package的目录名称即 openssl而不是二进制包名称即 libopenssl。
PKG_CONFIG_DEPENDS - 指定哪些配置选项影响构建配置并应在更改时触发重新运行构建/配置
PKG_INSTALL - 将其设置为1将调用make install进行编译后的安装动作并将安装目标路径前缀设置为PKG_INSTALL_DIR
PKG_INSTALL_DIR - 指定make install的目标路径如果是从git, bzr, svn等获取package源代码还需要定义如下信息PKG_SOURCE_PROTO -获取package源码使用的协议(git, svn等)
PKG_SOURCE_URL -package源码存储库地址。URL方案必须与PKG_SOURCE_PROTO一致(例如git://)但现在大多数VCS都接受http://或https:// URL。
PKG_SOURCE_VERSION -基于哪个commit hash 获取package 源码
PKG_SOURCE_DATE—一个类似2019-09-01的日期用于生成的tarball的名称中(uci-2019-09-01-415f9e48.tar.xz)
PKG_MIRROR_HASH -从源码存储库获取的tarball的SHA256校验(以前称为PKG_MIRROR_MD5SUM)
PKG_SOURCE_SUBDIR—从源码存储库获取的tarball临时存放目录默认为$(PKG_NAME)-$(PKG_VERSION)Package/
Package/用于定义package在menuconfig中的一些信息常见的参数如下
SECTION - 未使用软件包类型
CATEGORY - package所在的menuconfig一级菜单(可以自定义)
SUBMENU - CATEGORY的下级菜单(可以自定义)
TITLE - menuconfig中对软件包的简短描述
DESCRIPTION -已废弃软件包的详细描述
URL - 可选package的源网址(一般是提供这个package的官网但不是直接下载package的网址)
MAINTAINER -新软件包需要package的联系人(Imre Kaloz kalozopenwrt.org)
DEPENDS -可选此package依赖的其他package(目录而不是package名字)
EXTRA_DEPENDS -可选运行时依赖项不会被编译只会添加到软件包控制文件中
PROVIDES - 可选允许定义一个虚拟软件包它可能由多个实际软件包提供
PKGARCH -可选将其设为 all全部以生成 Architecture: all架构全部的软件包见下文
USERID -可选在安装软件包时创建的用户名组名对。例如ubus81:ubus81Package/Package Name/description
Package的详细描述信息它将出现在menconfig的Help选项中。
Build/Prepare(可选)
定义编译之前的准备工作。 默认动作是解压源码并给解压后的源码打patch。如果未定义此参数则会执行默认的动作。
Build/Configure (可选)
定义如何配置源码。 如果源代码存在configure命令默认动作则会执行configure对源码进行配置。你也可以自定义此参数在编译之前进行一些自定义配置。
Build/Compile (可选)
定义如何编译源码。 在大多数情况下不需要定义此参数因为这时将使用默认值该值将调用make。你也可以自定义此参加进行自定义编译。 这里需要特别注意这一步不是定义源码该如何编译出二进制而是定义进入哪个目录编译需要携带哪些编译参数(-Wall,-g等等)。
Build/Install (可选)
定义如何安装编译后的产物。 默认动作是调用“make install”前提是需要定义PKG_INSTALL:1。 如果PKG_INSTALL:1,但是源码的makefile中并没有提供install目标会提示如下编译报错。
make[3]: *** No rule to make target install. Stop.解决方案有两种 1.自定义Build/Install参数不使用make install进行安装 2.取消定义PKG_INSTALL:1在Build/InstallDev或者Package/install中实现安装步骤。
Build/InstallDev (可选)
定义如何安装编译后的产物和Build/Install类似。
Build/Clean (可选)
用于清理package默认只会删除编译目录。
Package/install(可选)
用于将文件复制到ipkgipkg由$(1)目录表示。 这里的文件可以是源码中的文件也可以是编译产物。 注意这里不是调用make install进行安装的只是用的cp、mv之类shell命令。 也可以使用上面Build/Install或者Build/InstallDev 方法进行安装都可以达到同样的效果。
Package/preinst(可选)
opkg install xxx.ipk之前要执行的脚本。不要忘记包含#!/bin/sh。如果需要中止安装让脚本返回false。
Package/postinst(可选)
opkg install xxx.ipk之后要执行的脚本。不要忘记包含#!/bin/sh。
Package/prerm(可选)
opkg remove xxx.ipk之前要执行的脚本。不要忘记包含#!/bin/sh。如果需要中止删除请让脚本返回false。
Package/postrm(可选)
opkg remove xxx.ipk之后要执行的脚本。不要忘记包含#!/bin/sh。
小结
之所以有些定义的前缀是 “Package/xxx”而另一些定义的前缀是 “Build/xxx”是因为同一份源代码可能生成多个二进制文件。OpenWrt 的工作假设是每个Package Makefile只有一个源代码但您可以根据需要使用源代码编译生成任意多个二进制文件。由于只需编译一次源代码因此只有一组全局的Build/xxx定义但您可以通过增加对BuildPackage的调用来添加任意数量的 Package/xxx的定义。Build/InstallDev 和Build/Install以及Package/hello/install这三种方法作用是差不多的在实际使用中至少需要实现其中一种因为编译产物需要安装到什么位置必须由我们自己决定。
files (可选)
这个目录存放package静态文件(如OpenWrt特定的初始化脚本或配置文件)这些静态文件的命名没有明确规定。
patches (可选)
该目录必须与Makefile放在同一个父目录中目录名必须固定为小写的patchs并且只能用于修改压缩包形式的源代码。
补丁文件必须采用统一的diff格式并带有扩展名。文件名还必须带有数字前缀以表示必须应用补丁文件的顺序。补丁文件名应简洁避免使用ASCII字母数字和连字符以外的字符。
合法的补丁文件名如下所示:
000-patch-makefile.patch
010-backport-frobnicate-crash-fix.patch
999-add-local-hack-for-openwrt-compatibility.patchsrc (可选)
这个目录是否存在取决于这个package是否需要源码以及源码是否在线下载的如果需要源码且源码不是在线下载的那就需要一个目录来存放源码但这个目录比较自由理论上可以放在任何地方。 如果你将源码放在Package Makefile同级的src目录下那编译时会自动拷贝src/*到$(PKG_BUILD_DIR)否则你需要手动将源码拷贝到$(PKG_BUILD_DIR)。
helloworld package示例
下面是一个Makefile的示例
include $(TOPDIR)/rules.mkPKG_NAME:helloworld
PKG_VERSION:1.0.0
PKG_RELEASE:1
PKG_LICENSE:GPL-2.0
PKG_LICENSE_FILES:GPL
#PKG_INSTALL:1include $(INCLUDE_DIR)/package.mkdefine Package/helloSECTION:Utilities CATEGORY:UtilitiesSUBMENU:appsDEPENDS:TITLE: example package part 1
endefdefine Package/hello/descriptionA simple example package
endefdefine Package/worldSECTION:Utilities CATEGORY:UtilitiesSUBMENU:appsDEPENDS:TITLE: example package part 2
endefdefine Package/world/descriptionA simple example package
endefdefine Build/Prepare$(Build/Prepare/Default)$(INSTALL_DIR) $(PKG_BUILD_DIR)/files[ ! -d ./files/ ] || $(CP) ./files/* $(PKG_BUILD_DIR)/files/
endef#define Build/Install
# $(INSTALL_DIR) $(1)/etc/init.d
# $(INSTALL_BIN) $(PKG_BUILD_DIR)/files/helloworld.init $(1)/etc/init.d/helloworld.init
#endefdefine Build/InstallDev$(INSTALL_DIR) $(1)/etc/init.d$(INSTALL_BIN) $(PKG_BUILD_DIR)/files/helloworld.init $(1)/etc/init.d/helloworld.init
endef#define Build/Clean
# rm -rf $(PKG_BUILD_DIR)
#endefdefine Package/hello/install$(INSTALL_DIR) $(1)/usr/bin$(INSTALL_BIN) $(PKG_BUILD_DIR)/hello $(1)/usr/bin
endefdefine Package/world/install$(INSTALL_DIR) $(1)/usr/bin$(INSTALL_BIN) $(PKG_BUILD_DIR)/world $(1)/usr/bin
endef#define Package/hello/preinst
# #!/bin/sh
# echo hello-preinst
#endef$(eval $(call BuildPackage,hello))
$(eval $(call BuildPackage,world))helloworld会根据源码编译生成2个可执行文件源码采用本地目录的方式。 #注释掉的部分都是非必要的没有注释的部分也并非都是必要的,例如Build/InstallDev里面的步骤也可以放在Package/xxx/install里面做。
├── helloworld
│ ├── files # 配置文件目录
│ │ └── helloworld.init
│ ├── Makefile
│ ├── patchs
│ └── src # 源码文件
│ ├── hello.c
│ ├── makefile # 这个源码的编译规则需要自行编写
│ └── world.c# src/makefile 示例
all: hello world
hello:$(CC) hello.c $(CFLAGS) -o hello
world:$(CC) world.c $(CFLAGS) -o world
clean:rm -rf hello.o hello world.o world
总结
OpenWrt 系统本质是一个package管理器类似.deb or .rpm包管理几乎所有的软件都对应一个packagepackage里面的Makefile文件非常重要它的语法也比较特殊在创建新的package时Makefile文件尽量参考已有的package。 package Makefile和源码的makefile不是一回事前者是定义Package的一些信息后者是具体的编译规则package Makefile的语法也比较灵活大家可能要根据实际情况决定是否需要自定义某些参数。
参考
OpenWrt packages