rmdir无法删除空目录

Modified on: Sat, 30 Jun 2018 07:30:00 +0800

我在删除空目录时遇到问题,strace显示错误:

rmdir("empty_dir") = -1 ENOTEMPTY (Directory not empty)

ls -la empty_dir什么都没显示。所以我用debugfs连接到fs(ext4)并看到这个目录中的隐藏文件:

# ls -lia empty_dir/
total 8
44574010 drwxr-xr-x 2 2686 2681 4096 Jan 13 17:59 .
44573990 drwxr-xr-x 3 2686 2681 4096 Jan 13 18:36 ..

debugfs:  ls empty_dir
 44574010  (12) .    44573990  (316) ..  
 26808797  (3768) _-----------------------------------------------------------.jpg  

为什么会发生这种情况?有没有机会解决这个问题而无需卸载和全面检查fs?

其他信息:

“隐藏”文件只是一个普通的jpg文件,可以由图像查看器打开:

debugfs:  dump empty_dir/_-----------------------------------------------------------.jpg /root/hidden_file

# file /root/hidden_file 
/root/hidden_file: JPEG image data, JFIF standard 1.02

rm -rf empty_dir无法使用相同的错误:

unlinkat(AT_FDCWD, "empty_dir", AT_REMOVEDIR) = -1 ENOTEMPTY (Directory not empty)

find empty_dir/ -inum 26808797什么都没有显示。

作者:,Jo Kin

最佳答案

我使用了ls并获得了更多信息(剥离了非重要的系统调用):

open("empty_dir", O_RDONLY|O_NONBLOCK|O_DIRECTORY|O_CLOEXEC) = 3
getdents(3, /* 3 entries */, 32768)     = 80
write(1, ".\n", 2.)                     = 2
write(1, "..\n", 3..)                   = 3

嗯,我们看到syscall getdents正常工作并返回所有3个条目('。','..'和'_--- *'),但ls只写'。'和'..'。这意味着我们遇到了coreutils使用的getdents包装器的问题。 coreutils对readdir使用getdents glibc包装器。另外为了证明getdents没有问题,我在getdents的男人页面。这个编程显示了所有文件。

也许我们刚刚在glibc上发现了一个错误?所以我将glibc包更新到我的发行版中的最后一个版本,但没有得到任何好结果。此外,我没有在bugzilla中找到任何相关信息。

让我们深入一点:

# gdb ls
(gdb) break readdir
(gdb) run
Breakpoint 1, 0x00007ffff7dfa820 in readdir () from /lib64/libncom.so.4.0.1
(gdb) info symbol readdir
readdir in section .text of /lib64/libncom.so.4.0.1

等等,什么? libncom.so.4.0.1?不是libc?是的,我们只看到一个带有libc功能的恶意共享库,用于隐藏恶意活动:

# LD_PRELOAD=/lib64/libc.so.6 find / > good_find
# find / > injected_find
# diff good_find injected_find
10310d10305
< /lib64/libncom.so.4.0.1
73306d73300
< /usr/bin/_-config
73508d73501
< /usr/bin/_-pud
73714d73706
< /usr/bin/_-minerd
86854d86845
< /etc/ld.so.preload

删除rootkit文件,检查所有包的文件(在我的例子中是rpm -Va),自动启动脚本,预加载/预链接配置,系统文件(find /在我的情况下+ rpm -qf),更改受影响的密码,查找和终止rootkit的进程:

# for i in /proc/[1-9]*; do name=$(</proc/${i##*/}/comm); ps -p ${i##*/} > /dev/null || echo $name; done
_-minerd

最后完整系统更新,重启并解决问题。成功黑客攻击的原因:ipmi接口具有非常旧的固件,突然可以从公共网络获得。

作者:,Jo Kin

相关问答

添加新评论