Linux运维进阶-Python,Docker,ShellLinux我用 Linux

文件丢失?损坏?兼容性问题?到底是什么导致了错误

2020-03-08  本文已影响0人  My熊猫眼

在日常的维护中,免不了和文件打交道,文件涉及的问题有很多类,这里讨论: 文件丢失,损坏,兼容性问题。
而对于文件丢失导致的问题一般比较容易定位,而文件损坏,特别是兼容性问题,这类排查起来就比较繁琐. 本文提供一种解决思路,望能起到抛砖引玉的作用.

Symptom:

[root@www ~]# curl 127.0.0.1
curl: (2) Failed initialization
[root@www ~]# 

解决步骤:

  1. 这个提示非常的简单,就是初始化失败,没有更多的信息;
  2. 用 strace来查看下系统调用(open),因为对文件的操作必定要调用open函数,这里主要验证是否存在“文件丢失”的问题。
    首先查找系统曾经尝试打开,但是没有找到的文件列表:
[root@www lib64]# strace -f -e open curl 127.0.0.1 2>&1 | grep -Ei "No such file or directory"  | awk -F'[()]' '{print $2}' | awk -F, '{print $1}' | tr -d "\"" | xargs -I{} basename {} | uniq 
libcurl.so.4
libssl3.so
libsmime3.so
libnss3.so
libnssutil3.so
libplds4.so
libplc4.so
libnspr4.so
libpthread.so.0
libdl.so.2
libz.so.1
libc.so.6
libidn.so.11
libldap-2.4.so.2
librt.so.1
libgssapi_krb5.so.2
libkrb5.so.3
libk5crypto.so.3
libcom_err.so.2
libssh2.so.1
liblber-2.4.so.2
libresolv.so.2
libsasl2.so.3
libssl.so.10
libcrypto.so.10
libkrb5support.so.0
libkeyutils.so.1
libcrypt.so.1
libselinux.so.1
libfreebl3.so
libpcre.so.1
legacy-settings
.curlrc
[root@www lib64]# strace -f -e open curl 127.0.0.1 2>&1 | grep -Ei "No such file or directory"  | awk -F'[()]' '{print $2}' | awk -F, '{print $1}' | tr -d "\"" | xargs -I{} basename {} | uniq  | wc -l 
33

然后 用strace 查看成功打开的文件列表:

[root@www lib64]# strace -f -e open curl 127.0.0.1 2>&1 | grep -Evi  "= \-1" | awk -F'["]' '{print $2}' | xargs -I{} basename {} 
ld.so.cache
libcurl.so.4
libssl3.so
libsmime3.so
libnss3.so
libnssutil3.so
libplds4.so
libplc4.so
libnspr4.so
libpthread.so.0
libdl.so.2
libz.so.1
libc.so.6
libidn.so.11
libldap-2.4.so.2
librt.so.1
libgssapi_krb5.so.2
libkrb5.so.3
libk5crypto.so.3
libcom_err.so.2
libssh2.so.1
liblber-2.4.so.2
libresolv.so.2
libsasl2.so.3
libssl.so.10
libcrypto.so.10
libkrb5support.so.0
libkeyutils.so.1
libcrypt.so.1
libselinux.so.1
libfreebl3.so
libpcre.so.1
filesystems
locale-archive
[root@www lib64]# strace -f -e open curl 127.0.0.1 2>&1 | grep -Evi  "= \-1" | awk -F'["]' '{print $2}' | xargs -I{} basename {}  | uniq | wc -l
34

最后,比较两个文件(grep -Ff 命令实现),发现真正没有找到的文件只有:.curlrc,而这个文件并不会导致curl出错,因为它属于curl的配置文件, man curl 有如下的解释:

FILES
       ~/.curlrc
              Default config file, see -K, --config for details.
  1. 由以上的结果可以看出,不会是 找不到对应文件导致的初始化失败;其实对于查找是否有动态链接库文件丢失可以用: ldd 命令,ldd命令输出的结果中会报告有哪些文件是not found的,而通过strace中的系统调用(open),可以获得除了动态链接库之外的其它文件,所以这里用strace来确保没有其他文件丢失,而不仅仅是动态链接库文件
  2. 文件虽然没有缺失,那么是否有可能是 文件遭到了损坏导致的呢?
    请参考文章: ldd命令排查文件crash的问题. 这里省略验证过程,验证的结果是:发现没有文件有损坏的情况;
  3. 是不是文件的兼容性导致的问题呢?
    我们通过ldd命令可以查看相应的依赖,本质上,依赖的不是文件,而是动态链接库文件中的函数,如果出现了兼容性的问题,那么对应的函数可能会报错. 依据这一点,我们可以根据报错信息来查找 “错误信息” 是来自于哪个动态链接库,从而找到报错的库文件,进一步查看其对应的rpm包是否有兼容性文件;
[root@www lib64]# ldd `which curl`
    linux-vdso.so.1 =>  (0x00007ffe77150000)
    libcurl.so.4 => /lib64/libcurl.so.4 (0x00007fbd9c354000)
    libssl3.so => /lib64/libssl3.so (0x00007fbd9c102000)
    libsmime3.so => /lib64/libsmime3.so (0x00007fbd9bedb000)
    libnss3.so => /lib64/libnss3.so (0x00007fbd9bbae000)
    libnssutil3.so => /lib64/libnssutil3.so (0x00007fbd9b97e000)
    libplds4.so => /lib64/libplds4.so (0x00007fbd9b77a000)
    libplc4.so => /lib64/libplc4.so (0x00007fbd9b575000)
    libnspr4.so => /lib64/libnspr4.so (0x00007fbd9b337000)
    libpthread.so.0 => /lib64/libpthread.so.0 (0x00007fbd9b11b000)
    libdl.so.2 => /lib64/libdl.so.2 (0x00007fbd9af17000)
    libz.so.1 => /lib64/libz.so.1 (0x00007fbd9ad01000)
    libc.so.6 => /lib64/libc.so.6 (0x00007fbd9a934000)
    libidn.so.11 => /lib64/libidn.so.11 (0x00007fbd9a701000)
    libldap-2.4.so.2 => /lib64/libldap-2.4.so.2 (0x00007fbd9a4ac000)
    librt.so.1 => /lib64/librt.so.1 (0x00007fbd9a2a4000)
    libgssapi_krb5.so.2 => /lib64/libgssapi_krb5.so.2 (0x00007fbd9a057000)
    libkrb5.so.3 => /lib64/libkrb5.so.3 (0x00007fbd99d6e000)
    libk5crypto.so.3 => /lib64/libk5crypto.so.3 (0x00007fbd99b3b000)
    libcom_err.so.2 => /lib64/libcom_err.so.2 (0x00007fbd99937000)
    libssh2.so.1 => /lib64/libssh2.so.1 (0x00007fbd9970d000)
    /lib64/ld-linux-x86-64.so.2 (0x00007fbd9c5a9000)
    liblber-2.4.so.2 => /lib64/liblber-2.4.so.2 (0x00007fbd994fe000)
    libresolv.so.2 => /lib64/libresolv.so.2 (0x00007fbd992e5000)
    libsasl2.so.3 => /lib64/libsasl2.so.3 (0x00007fbd990c8000)
    libssl.so.10 => /lib64/libssl.so.10 (0x00007fbd98e56000)
    libcrypto.so.10 => /lib64/libcrypto.so.10 (0x00007fbd989f4000)
    libkrb5support.so.0 => /lib64/libkrb5support.so.0 (0x00007fbd987e4000)
    libkeyutils.so.1 => /lib64/libkeyutils.so.1 (0x00007fbd985e0000)
    libcrypt.so.1 => /lib64/libcrypt.so.1 (0x00007fbd983a9000)
    libselinux.so.1 => /lib64/libselinux.so.1 (0x00007fbd98182000)
    libfreebl3.so => /lib64/libfreebl3.so (0x00007fbd97f7f000)
    libpcre.so.1 => /lib64/libpcre.so.1 (0x00007fbd97d1d000)
[root@www lib64]# curl -i 127.0.0.1
curl: (2) Failed initialization
[root@www lib64]# 

通过strings 命令查看对应的动态链接库文件的报错信息,通过比对,最终发现有且只有 /lib64/libcurl.so.4 这个文件有 "Failed initialization" 这个报错信息,然后进一步发现该文件所属的rpm包为rhel6发行版的,而当前的os是centos7. 所以替换掉这个旧包,然后问题顺利解决;

本文原创,转载请著名出处

上一篇下一篇

猜你喜欢

热点阅读