之前客户在使用提供的基础镜像的时候,误删了bash 的一个依赖库,导致无法进入到该容器当中,也就是如果容器中没有/bin/bash、/bin/sh 或其他 shell,这个时候我们在不重新生成容器的前提下,如何修复这个问题呢?
接下来,我们学习几种方法,可根据自己的需求可以选择,其实总的原理就是缺啥补啥而已
问题复现:我们手动删除一个库文件
[root@master1 ~]# docker run -it centos:7 bash
[root@0094c4cb3b46 /]# ldd /usr/bin/bash
linux-vdso.so.1 => (0x00007ffc1a19d000)
libtinfo.so.5 => /lib64/libtinfo.so.5 (0x00007f926cd32000)
libdl.so.2 => /lib64/libdl.so.2 (0x00007f926cb2e000)
libc.so.6 => /lib64/libc.so.6 (0x00007f926c760000)
/lib64/ld-linux-x86-64.so.2 (0x00007f926cf5c000)
[root@0094c4cb3b46 /]# rm -rf /lib64/libtinfo.so.5
[root@0094c4cb3b46 /]#
[root@master1 ~]#
[root@master1 ~]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
0094c4cb3b46 centos:7 "bash" 31 seconds ago Up 31 seconds busy_vaughan
[root@master1 ~]# docker exec -it busy_vaughan bash
bash: error while loading shared libraries: libtinfo.so.5: cannot open shared object file: No such file or directory
[root@master1 ~]#
[root@master1 ~]#
[root@master1 ~]# docker exec -it busy_vaughan sh
sh: error while loading shared libraries: libtinfo.so.5: cannot open shared object file: No such file or directory
[root@master1 ~]#
方式一
通过拷贝库文件,把缺少的库文件装到容器里面对应目录中去,关于容器在guest os中的目录,具体看我上一篇文章,这里直接开用了。
使用chroot命令也进不去
[root@master1 ~]# docker inspect busy_vaughan |grep merged
"MergedDir": "/var/lib/docker/overlay2/1d321b06d34e23506dbf0dcc51ae0927b05d8a2edbf431c65f9726881971aef5/merged",
[root@master1 ~]#
[root@master1 ~]# chroot /var/lib/docker/overlay2/1d321b06d34e23506dbf0dcc51ae0927b05d8a2edbf431c65f9726881971aef5/merged/
/bin/bash: error while loading shared libraries: libtinfo.so.5: cannot open shared object file: No such file or directory
[root@master1 ~]#
我们先把缺少的库文件所属于的那个包下到本地,然后解压拿到缺少的库文件,注意:这个前提是容器中该库文件的版本要对应上,和缺少的库比较少。
[root@master1 ~]# yumdownloader ncurses-libs
[root@master1 test]# ls
ncurses-libs-5.9-14.20130511.el7_4.x86_64.rpm
[root@master1 test]# rpm2cpio ncurses-libs-5.9-14.20130511.el7_4.x86_64.rpm |cpio -div
./usr/lib64/libform.so.5
./usr/lib64/libform.so.5.9
./usr/lib64/libformw.so.5
./usr/lib64/libformw.so.5.9
./usr/lib64/libmenu.so.5
./usr/lib64/libmenu.so.5.9
./usr/lib64/libmenuw.so.5
./usr/lib64/libmenuw.so.5.9
./usr/lib64/libncurses++.so.5
./usr/lib64/libncurses++.so.5.9
./usr/lib64/libncurses++w.so.5
./usr/lib64/libncurses++w.so.5.9
./usr/lib64/libncurses.so.5
./usr/lib64/libncurses.so.5.9
./usr/lib64/libncursesw.so.5
./usr/lib64/libncursesw.so.5.9
./usr/lib64/libpanel.so.5
./usr/lib64/libpanel.so.5.9
./usr/lib64/libpanelw.so.5
./usr/lib64/libpanelw.so.5.9
./usr/lib64/libtic.so.5
./usr/lib64/libtic.so.5.9
./usr/lib64/libtinfo.so.5
./usr/lib64/libtinfo.so.5.9
2016 块
[root@master1 test]#
然后拷贝到容器目录中去,然后就可以进入容器了
[root@master1 test]# cp ./usr/lib64/libtinfo.so.5 /var/lib/docker/overlay2/1d321b06d34e23506dbf0dcc51ae0927b05d8a2edbf431c65f9726881971aef5/merged/usr/lib64/ -af
[root@master1 test]#
[root@master1 test]# docker exec -it busy_vaughan bash
[root@0094c4cb3b46 /]#
方式二
通过yum的方式重新安装依赖包
[root@master1 test]# docker exec -it busy_vaughan bash
bash: error while loading shared libraries: libtinfo.so.5: cannot open shared object file: No such file or directory
[root@master1 test]#
[root@master1 test]# yum reinstall ncurses-libs-5.9-14.20130511.el7_4.x86_64.rpm --installroot=/var/lib/docker/overlay2/1d321b06d34e23506dbf0dcc51ae0927b05d8a2edbf431c65f9726881971aef5/merged/
已加载插件:fastestmirror
正在检查 ncurses-libs-5.9-14.20130511.el7_4.x86_64.rpm: ncurses-libs-5.9-14.20130511.el7_4.x86_64
正在解决依赖关系
--> 正在检查事务
---> 软件包 ncurses-libs.x86_64.0.5.9-14.20130511.el7_4 将被 已重新安装
--> 解决依赖关系完成
依赖关系解决
==============================================================================================================================================================
Package 架构 版本 源 大小
==============================================================================================================================================================
重新安装:
ncurses-libs x86_64 5.9-14.20130511.el7_4 /ncurses-libs-5.9-14.20130511.el7_4.x86_64 1.0 M
事务概要
==============================================================================================================================================================
重新安装 1 软件包
总计:1.0 M
安装大小:1.0 M
Is this ok [y/d/N]: y
Downloading packages:
Running transaction check
Running transaction test
Transaction test succeeded
Running transaction
正在安装 : ncurses-libs-5.9-14.20130511.el7_4.x86_64 1/1
验证中 : ncurses-libs-5.9-14.20130511.el7_4.x86_64 1/1
已安装:
ncurses-libs.x86_64 0:5.9-14.20130511.el7_4
完毕!
[root@master1 test]# docker exec -it busy_vaughan bash
[root@0094c4cb3b46 /]#
方式三
通过docker cp命令,这个其实跟方式一差不多
[root@master1 test]# docker exec -it busy_vaughan bash
bash: error while loading shared libraries: libtinfo.so.5: cannot open shared object file: No such file or directory
[root@master1 test]#
[root@master1 test]#
[root@master1 test]#
[root@master1 test]# ls
ncurses-libs-5.9-14.20130511.el7_4.x86_64.rpm usr
[root@master1 test]#
[root@master1 test]#
[root@master1 test]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
0094c4cb3b46 centos:7 "bash" 28 minutes ago Up 28 minutes busy_vaughan
[root@master1 test]# docker cp ./usr/lib64/libtinfo.so.5 busy_vaughan:/usr/lib64/
[root@master1 test]# docker exec -it busy_vaughan bash
[root@0094c4cb3b46 /]#
方式四
通过容器的PID
[root@master1 test]# docker exec -it busy_vaughan bash
bash: error while loading shared libraries: libtinfo.so.5: cannot open shared object file: No such file or directory
[root@master1 test]#
[root@master1 test]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
0094c4cb3b46 centos:7 "bash" 30 minutes ago Up 30 minutes busy_vaughan
[root@master1 test]#
[root@master1 test]# docker container inspect 0094c4cb3b46 | jq '.[0].State.Pid'
3795
[root@master1 test]#
[root@master1 test]# nsenter -m -t 3795 /bin/bash
/bin/bash: error while loading shared libraries: libtinfo.so.5: cannot open shared object file: No such file or directory
[root@master1 test]# ls /proc/3795/root/
anaconda-post.log bin dev etc home lib lib64 media mnt opt proc root run sbin srv sys tmp usr var
[root@master1 test]# cp ./usr/lib64/libtinfo.so.5 /proc/3795/root/usr/lib64/ -af
[root@master1 test]#
[root@master1 test]# docker exec -it busy_vaughan bash
[root@0094c4cb3b46 /]# exit
exit
[root@master1 test]#