OpenHarmony 4.0.10.13 NDK下编译OpenSSH 9.6p1,我踩过的那些坑(附完整脚本)
OpenHarmony 4.0.10.13 NDK下编译OpenSSH 9.6p1实战避坑指南移植开源软件到新平台从来都不是简单的复制粘贴尤其是当目标平台是OpenHarmony这样的新兴操作系统时。本文将详细记录在OpenHarmony 4.0.10.13上使用NDK编译OpenSSH 9.6p1的全过程重点分享那些让我熬了几个通宵的坑以及如何一步步填平它们。1. 环境准备与基础库编译在开始OpenSSH的移植前我们需要先准备好编译环境和依赖库。OpenSSH依赖于zlib和OpenSSL这两个库的编译也需要针对OpenHarmony进行适配。1.1 NDK环境配置OpenHarmony的NDK与传统Android NDK有所不同它基于Clang/LLVM工具链并针对OHOS做了特殊适配。首先需要确保正确设置环境变量export OHOS_NATIVE_HOME/opt/sdk/ohos/native/4.0.10.13 export PATH$OHOS_NATIVE_HOME/llvm/bin:$PATH export CC$OHOS_NATIVE_HOME/llvm/bin/clang export AR$OHOS_NATIVE_HOME/llvm/bin/llvm-ar export LD$OHOS_NATIVE_HOME/llvm/bin/ld.lld关键点必须使用OHOS提供的lld链接器而非系统默认的ld否则会遇到各种链接错误。1.2 zlib编译zlib相对简单但需要注意静态编译./configure --prefix${PWD}/_install --static make make install1.3 OpenSSL编译OpenSSL 3.2.0的编译需要特别注意以下几点禁用单元测试no-unit-test禁用动态库no-shared移除对libatomic的依赖./Configure linux-armv4 --prefix${PWD}/_install zlib no-asm no-shared no-unit-test no-tests关键修改编辑生成的Makefile删除所有-latomic引用sed -i s/-latomic//g ./Makefile2. OpenSSH编译过程中的六大坑2.1 动态库链接问题现象configure阶段报错找不到libcrypto库解决方案在LDFLAGS中明确指定静态库路径export LDFLAGS... ${PWD}/../openssl-3.2.0/_install/lib/libcrypto.a -lz2.2 musl库函数缺失现象编译时报错getspnam、explicit_bzero等函数未定义原因OHOS NDK中的musl库裁剪过度缺少部分函数实现解决方案从源码编译的musl库中提取完整实现cp ${OHOS_SRC}/out/${PRODUCT}/obj/third_party/musl/usr/include/arm-linux-ohos/shadow.h ${OHOS_NATIVE_HOME}/sysroot/usr/include/ cp ${OHOS_SRC}/out/${PRODUCT}/obj/third_party/musl/usr/lib/arm-linux-ohos/libc.so ${OHOS_NATIVE_HOME}/sysroot/usr/lib/arm-linux-ohos/2.3 头文件冲突现象linux/socket.h和sys/socket.h中的sockaddr_storage定义冲突解决方案定义__MUSL__宏避免重复定义export CFLAGS... -D__MUSL__2.4 DNS解析相关符号缺失现象链接阶段报错undefined symbol: __res_state原因OpenSSH使用了glibc特有的DNS解析函数解决方案修改OpenSSH源码禁用DNS相关功能#if !defined(__OHOS__) result getrrsetbyname(hostname, DNS_RDATACLASS_IN, DNS_RDATATYPE_SSHFP, 0, fingerprints); #else result -1; #endif2.5 安装目录权限问题现象make install时无法创建/var/empty解决方案使用DESTDIR参数指定安装目录make install DESTDIR${PWD}/_install2.6 系统集成问题将编译好的OpenSSH集成到OpenHarmony系统镜像中需要注意权限配置DAC规则服务启动脚本系统参数设置关键配置// device/board/${VENDOR}/${PRODUCT}/files/openssh/etc/sshd.cfg { jobs : [{ name : param:sys.sshd.enabletrue, condition : sys.sshd.enabletrue, cmds : [ mkdir -p /data/ssh/var/run, start sshd ] }] }3. 功能调试与系统适配编译通过只是第一步要让OpenSSH在OpenHarmony上真正可用还需要解决以下问题3.1 用户环境配置OpenHarmony的/etc/passwd文件默认不包含用户home目录和有效shell需要手动添加root:x:0:0:root:/data:/system/bin/sh3.2 认证方式适配由于OpenHarmony缺少/etc/shadow文件建议优先使用密钥认证如需密码认证需修改PAM配置3.3 文件权限管理必须严格设置密钥文件权限chmod 600 /etc/ssh/ssh_host_rsa_key chmod 644 /etc/ssh/ssh_host_rsa_key.pub4. 完整编译脚本以下是经过验证可用的完整编译脚本#!/bin/bash set -e # 环境变量设置 export OHOS_NATIVE_HOME/opt/sdk/ohos/native/4.0.10.13 export PATH$OHOS_NATIVE_HOME/llvm/bin:$PATH export CC$OHOS_NATIVE_HOME/llvm/bin/clang export AR$OHOS_NATIVE_HOME/llvm/bin/llvm-ar export LD$OHOS_NATIVE_HOME/llvm/bin/ld.lld export CFLAGS--targetarm-linux-ohos --sysroot$OHOS_NATIVE_HOME/sysroot -D__MUSL__ -D__OHOS__ export LDFLAGS--targetarm-linux-ohos --rtlibcompiler-rt -fuse-ldlld # 编译OpenSSH ./configure --prefix/system \ --with-zlib${PWD}/../zlib-1.3/_install \ --with-ssl-dir${PWD}/../openssl-3.2.0/_install \ --disable-etc-default-login make -j$(nproc) CHANNELLIBS SSHDLIBS piddir/data/ssh/var/run make install-nokeys DESTDIR${PWD}/_install5. 经验总结与优化建议经过这次OpenSSH移植我总结了以下几点经验系统库差异OpenHarmony的musl库与标准Linux发行版存在差异需要准备手动补全缺失函数交叉编译技巧静态链接优先明确指定库搜索路径善用nm工具检查符号系统集成合理规划文件系统布局注意权限控制服务启动顺序很重要性能优化建议启用ARMv8-A指令集-marcharmv8-a使用LTO-flto优化裁剪不需要的OpenSSH功能模块移植过程中最耗时的往往不是技术问题而是对目标平台特性的理解。OpenHarmony作为新兴系统其设计理念和实现细节都需要开发者花时间去适应。希望本文的实践经验能为后来者节省宝贵的时间。