编译精简版嵌入式nginx需同步完成交叉编译适配与模块裁剪:先配置匹配架构的工具链(arm32用arm-linux-gnueabihf-,arm64用aarch64-linux-gnu-),修改configure脚本绕过运行时探测、硬编码类型大小;再交叉编译zlib/pcre/openssl并显式指定路径;最后禁用非核心http、mail、stream模块,并strip符号,体积可压至300–600 kb。

编译精简版嵌入式 Nginx,核心是两件事:一是适配目标平台(交叉编译),二是剔除所有非必需模块和符号。它不是简单加几个--without-xxx就能成,必须同步解决架构兼容性、依赖库移植、类型大小硬编码、运行时探测绕过等问题。
准备匹配的交叉工具链
选错工具链,后面全白忙。关键看三点:
- 前缀必须与目标 CPU 架构一致:ARM32 用
arm-linux-gnueabihf-,ARM64 用aarch64-linux-gnu- - 运行
aarch64-linux-gnu-gcc -v或arm-linux-gnueabihf-gcc -v,确认Target:行显示对应架构 - 工具链的 C 库(glibc/musl)版本要贴近目标设备系统;可用
readelf -A /lib/ld-linux-aarch64.so.1查目标板 ABI 特性,避免运行时报symbol not found
手动修改 configure 脚本以支持交叉编译
Nginx 的 configure 默认不认 $CC,且大量依赖“编译+本地运行测试程序”逻辑——这在 x86 主机上交叉编译 ARM 程序时必然失败。必须改三处:
-
auto/cc/name:把所有gcc替换为$CC,并在末尾加echo $CC确保识别正确编译器 -
auto/types/sizeof:注释掉全部编译运行测试块,直接写死类型大小,例如:ngx_size="4"(ARM32)、ngx_size="8"(ARM64);ngx_ptr_t="8";ngx_off_t="8" -
auto/feature:逐个注释掉ngx_feature_test块,防止因无法执行测试二进制而中断配置
交叉编译并显式链接依赖库
zlib、PCRE、OpenSSL 必须各自交叉编译,不能复用主机库,否则链接失败或运行崩溃:
-
zlib:
./configure --prefix=/opt/arm64/zlib --host=aarch64-linux-gnu && make && make install -
PCRE:
./configure --prefix=/opt/arm64/pcre --host=aarch64-linux-gnu --disable-cpp && make && make install -
OpenSSL(推荐 1.1.1w):
./Configure linux-aarch64 no-shared no-asm --prefix=/opt/arm64/openssl && make && make install
之后在 Nginx configure 中显式指定路径:--with-zlib=/opt/arm64/zlib --with-pcre=/opt/arm64/pcre --with-openssl=/opt/arm64/openssl
禁用模块 + 剥离符号,压到最小体积
在确保能交叉编译通过的前提下,再做裁剪。只留最基础 HTTP 静态服务能力:
- 禁用全部非核心 HTTP 模块:
--without-http_access_module --without-http_auth_basic_module --without-http_autoindex_module --without-http_geo_module --without-http_map_module --without-http_rewrite_module --without-http_proxy_module --without-http_fastcgi_module --without-http_uwsgi_module --without-http_scgi_module - 彻底关闭 MAIL 和 STREAM:
--without-mail_pop3_module --without-mail_imap_module --without-mail_smtp_module --without-stream - 编译后执行:
strip --strip-all objs/nginx,可再减 30%~50% 体积
最终生成的二进制通常可压至 300–600 KB,适合资源受限的嵌入式环境。











