Fedora 41/RedHat 9.4下32位ncurses应用崩溃问题咨询
问题描述
在Devuan Chimaera 32位环境编译的一款基于ncurses库的32位控制台应用myapp,在Fedora 41/RHEL 9.4系统运行时崩溃,启动提示:
./myapp: /lib/libtinfo.so.6: no version information available (required by ./myapp) ./myapp: /lib/libncursesw.so.6: no version information available (required by ./myapp) ./myapp: /lib/libncursesw.so.6: no version information available (required by ./myapp) Segmentation fault (core dumped)
核心转储显示崩溃发生在动态链接器查找__divdi3符号的过程中,调用栈如下:
Debuginfod has been enabled. To make this setting permanent, add 'set debuginfod enabled on' to .gdbinit. [Thread debugging using libthread_db enabled] Using host libthread_db library "/lib64/libthread_db.so.1". Core was generated by `./myapp'. Program terminated with signal SIGSEGV, Segmentation fault. #0 0xf7eecde5 in check_match (undef_name=undef_name@entry=0xf7dac13c "__divdi3", ref=ref@entry=0xf7d4aff0, version=version@entry=0xf78dc400, flags=9, type_class=1, sym=0x56628e68, symidx=194, strtab=0x56628ee8 "", map=0xf7f1aa20, versioned_sym=0xffbf8f2c, num_versions=0xffbf8f28) at dl-lookup.c:116 warning: 116 dl-lookup.c: No such file or directory (gdb) bt #0 0xf7eecde5 in check_match (undef_name=undef_name@entry=0xf7dac13c "__divdi3", ref=ref@entry=0xf7d4aff0, version=version@entry=0xf78dc400, flags=9, type_class=1, sym=0x56628e68, symidx=194, strtab=0x56628ee8 "", map=0xf7f1aa20, versioned_sym=0xffbf8f2c, num_versions=0xffbf8f28) at dl-lookup.c:116 #1 0xf7eed239 in do_lookup_x (undef_name=undef_name@entry=0xf7dac13c "__divdi3", new_hash=new_hash@entry=2851089606, old_hash=old_hash@entry=0xffbf8fb0, ref=0xf7d4aff0, result=0xffbf8fb4, scope=0xf7f1ab8c, i=<optimized out>, version=0xf78dc400, flags=9, skip=0x0, type_class=1, undef_map=0xf7edc960) at dl-lookup.c:432 #2 0xf7eeda10 in _dl_lookup_symbol_x (undef_name=0xf7dac13c "__divdi3", undef_map=0xf7edc960, ref=0xffbf907c, symbol_scope=<optimized out>, version=0xf78dc400, type_class=1, flags=9, skip_map=0x0) at dl-lookup.c:792 #3 0xf7ef17d8 in resolve_map (l=<optimized out>, scope=<optimized out>, ref=0xffbf907c, version=0xf78dc400, r_type=7) at dl-reloc.c:190 #4 elf_machine_rel (map=0xf7edc960, scope=<optimized out>, reloc=0xf7dba28c, sym=0xf7d4aff0, version=0xf78dc400, reloc_addr_arg=0xf7e568c0 <__divdi3@got.plt>, skip_ifunc=<optimized out>) at ../sysdeps/i386/dl-machine.h:264 #5 elf_dynamic_do_Rel (map=0xf7edc960, scope=<optimized out>, reladdr=<optimized out>, relsize=<optimized out>, nrelative=<optimized out>, lazy=<optimized out>, skip_ifunc=<optimized out>) at /usr/src/debug/glibc-2.40-3.fc41.i386/elf/do-rel.h:147 #6 _dl_relocate_object (l=<optimized out>, scope=<optimized out>, reloc_mode=<optimized out>, consider_profiling=<optimized out>) at dl-reloc.c:301 #7 0xf7f02353 in dl_main (phdr=<optimized out>, phnum=<optimized out>, user_entry=<optimized out>, auxv=<optimized out>) at rtld.c:2314 #8 0xf7efe845 in _dl_sysdep_start (start_argptr=0xffbf9480, dl_main=0xf7f00440 <dl_main>) at ../sysdeps/unix/sysv/linux/dl-sysdep.c:141 #9 0xf7f00207 in _dl_start_final (arg=0xffbf9480) at rtld.c:494 #10 _dl_start (arg=<optimized out>) at rtld.c:581 #11 0xf7efefab in _start () from /lib/ld-linux.so.2 (gdb)
同一编译环境生成的另一款32位应用myapp2仅弹出版本信息缺失提示,可正常运行:
./myapp2: /lib/libtinfo.so.6: no version information available (required by ./myapp2) ./myapp2: /lib/libncursesw.so.6: no version information available (required by ./myapp2) ./myapp2: /lib/libncursesw.so.6: no version information available (required by ./myapp2)
原因分析
- ncurses库版本符号不兼容:Devuan Chimaera与Fedora/RHEL的ncurses库符号版本存在差异,导致启动时出现版本警告,但该警告本身不会引发崩溃,属于次要问题。
- __divdi3符号查找失败触发崩溃:
__divdi3是32位x86系统中处理64位整数除法的glibc辅助函数。崩溃原因是:myapp代码中使用了64位整数(long long)除法操作,编译时glibc将该函数标记为动态依赖,但目标系统32位glibc的符号版本或存在形式与编译环境不匹配,导致动态链接器查找符号时访问非法内存,触发SIGSEGV。myapp2未崩溃是因为其代码未触发对__divdi3的调用,因此仅出现ncurses版本警告但能正常运行。
- 跨发行版glibc差异:Devuan基于Debian,与Fedora/RHEL的glibc版本和符号管理逻辑存在差异,直接跨环境运行编译产物容易出现符号解析故障。
修复方案
方案1:静态链接gcc辅助函数
编译时添加-static-libgcc选项,将__divdi3等gcc辅助函数静态链接到程序中,避免依赖目标系统的glibc动态版本:
gcc -m32 your_source.c -o myapp -lncursesw -static-libgcc
方案2:静态链接ncurses库(彻底解决版本警告)
如果需要消除ncurses版本警告,可静态链接整个ncurses库,需先安装ncurses静态开发包(如Devuan中的libncursesw5-dev):
gcc -m32 your_source.c -o myapp -static -lncursesw
注意:静态链接会增大程序体积,且可能引入其他依赖的静态编译需求。
方案3:调整代码避免64位整数操作
检查myapp代码,若业务逻辑允许,将64位整数除法替换为32位整数操作,编译时就不会生成对__divdi3的调用。
方案4:在目标系统安装兼容32位库
在Fedora/RHEL中安装32位glibc和ncurses库,缓解部分依赖问题:
- Fedora:
sudo dnf install glibc.i686 ncurses-libs.i686 - RHEL 9.4:
sudo dnf install glibc.i686 ncurses-libs.i686
此方法无法彻底解决跨发行版glibc符号差异问题,仅作为临时缓解手段。
方案5:使用目标系统兼容环境编译
在Fedora/RHEL的32位容器或虚拟机中编译程序,确保链接的库版本与目标系统完全一致,从根源上避免兼容性问题。
内容的提问来源于stack exchange,提问作者user3161924
相关产品推荐
相关产品推荐

