rpm命令报错"error: Failed to initialize NSS library"

在使用rpm命令时提示错误"error: Failed to initialize NSS library":

$ rpm -qa
error: Failed to initialize NSS library

这个问题通过google搜索能够找不少解决方法,大多数都是围绕libnspr4库文件,如Linux : Yum/rpm broken upgrading from CentOS/RHEL 7.3 to 7.4 (error: Failed to initialize NSS library)介绍;或者如Bug 1476031 - Failed to initialize NSS library说明的,由于nss-softokn-freebl升级但是nspr没有升级,一般解决的方法是通过将rpm包下载(例如回滚到原有版本)以后,在通过rpm2cpio解压缩,手工复制修复。

不过,也有可能是由于其他库文件损坏导致,此时虽然看上去是NSS库初始化失败,但是实际上需要修复其他库文件。

检查的方法是采用strace,这个工具提供了-eopen参数来跟踪执行命令所使用的文件。注意:有些和语言相关的xxx.mo文件虽然不存在但是也不影响运行(对比正常服务器)。

不过,即使文件完全准确存在也可能出现异常,所以通过strace rpm命令检查完整的库文件调用顺序,查看出现异常是哪个文件:

strace rpm

显示错误最后调用的库文件是/lib64/libfreeblpriv3.so

...
open("/lib64/libfreeblpriv3.so", O_RDONLY|O_CLOEXEC) = 3
read(3, "\177ELF\2\1\1\0\0\0\0\0\0\0\0\0\3\0>\0\1\0\0\0\0;\0\0\0\0\0\0"..., 832) = 832
fstat(3, {st_mode=S_IFREG|0755, st_size=526912, ...}) = 0
mmap(NULL, 2631448, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x7f7f206e6000
mprotect(0x7f7f20763000, 2093056, PROT_NONE) = 0
mmap(0x7f7f20962000, 12288, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_DENYWRITE, 3, 0x7c000) = 0x7f7f20962000
mmap(0x7f7f20965000, 14104, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_FIXED|MAP_ANONYMOUS, -1, 0) = 0x7f7f20965000
close(3)                                = 0
mprotect(0x7f7f20962000, 8192, PROT_READ) = 0
munmap(0x7f7f2afa6000, 35038)           = 0
munmap(0x7f7f206e6000, 2631448)         = 0
open("/proc/sys/crypto/fips_enabled", O_RDONLY) = 3
fstat(3, {st_mode=S_IFREG|0444, st_size=0, ...}) = 0
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f7f2afbd000
read(3, "0\n", 1024)                    = 2
close(3)                                = 0
munmap(0x7f7f2afbd000, 4096)            = 0
open("/usr/share/locale/locale.alias", O_RDONLY|O_CLOEXEC) = 3
fstat(3, {st_mode=S_IFREG|0644, st_size=2502, ...}) = 0
mmap(NULL, 4096, PROT_READ|PROT_WRITE, MAP_PRIVATE|MAP_ANONYMOUS, -1, 0) = 0x7f7f2afbd000
read(3, "# Locale name alias data base.\n#"..., 4096) = 2502
read(3, "", 4096)                       = 0
close(3)                                = 0
munmap(0x7f7f2afbd000, 4096)            = 0
open("/usr/share/locale/en_US.UTF-8/LC_MESSAGES/rpm.mo", O_RDONLY) = -1 ENOENT (No such file or directory)
open("/usr/share/locale/en_US.utf8/LC_MESSAGES/rpm.mo", O_RDONLY) = -1 ENOENT (No such file or directory)
open("/usr/share/locale/en_US/LC_MESSAGES/rpm.mo", O_RDONLY) = -1 ENOENT (No such file or directory)
open("/usr/share/locale/en.UTF-8/LC_MESSAGES/rpm.mo", O_RDONLY) = -1 ENOENT (No such file or directory)
open("/usr/share/locale/en.utf8/LC_MESSAGES/rpm.mo", O_RDONLY) = -1 ENOENT (No such file or directory)
open("/usr/share/locale/en/LC_MESSAGES/rpm.mo", O_RDONLY) = -1 ENOENT (No such file or directory)
write(2, "error: ", 7error: )                  = 7
write(2, "Failed to initialize NSS library"..., 33Failed to initialize NSS library
) = 33
exit_group(1)                           = ?
+++ exited with 1 +++

检查对比发现,异常的/lib64/libfreeblpriv3.so文件时间戳

$ls -lh /lib64/libfreeblpriv3.so
-rwxr-xr-x 1 root root 515K Sep 15  2017 /lib64/libfreeblpriv3.so

而正常的服务器上这个时间戳比较早

$ls -lh /lib64/libfreeblpriv3.so
-rwxr-xr-x 1 root root 503K Dec 14  2015 /lib64/libfreeblpriv3.so

所以在正常服务器上检查这个文件属于哪个rpm包

$rpm -qf /lib64/libfreeblpriv3.so
nss-softokn-freebl-3.16.2.3-13.1.alios7.x86_64

然后手工下载rpm并解压缩后修复:

rpm2cpio nss-softokn-freebl-3.16.2.3-13.1.alios7.x86_64.rpm |cpio -imdv
cp usr/lib64/* /lib64/

参考

Last updated