Linux下如何知道文件被那个进程写
March 12th, 2013
原创文章,转载请注明: 转载自系统技术非业余研究
本文链接地址: Linux下如何知道文件被那个进程写
晚上朔海同学问:
一个文件正在被进程写 我想查看这个进程 文件一直在增大 找不到谁在写 使用lsof也没找到
这个问题挺有普遍性的,解决方法应该很多,这里我给大家提个比较直观的方法。
linux下每个文件都会在某个块设备上存放,当然也都有相应的inode, 那么透过vfs.write我们就可以知道谁在不停的写入特定的设备上的inode。
幸运的是systemtap的安装包里带了inodewatch.stp,位于/usr/local/share/doc/systemtap/examples/io目录下,就是用来这个用途的。
我们来看下代码:
$ cat inodewatch.stp #! /usr/bin/env stap probe vfs.write, vfs.read { # dev and ino are defined by vfs.write and vfs.read if (dev == MKDEV($1,$2) # major/minor device && ino == $3) printf ("%s(%d) %s 0x%x/%u\n", execname(), pid(), probefunc(), dev, ino) }
这个脚本的使用方法如下: stap inodewatch.stp major minor ino
下面我们构造个场景: dd不停的写入一个文件,查出这个文件的ino, 以及它所在设备的major, minor, 运行stap脚本就可以得到答案。
场景交代好了,我们来演示下:
$ pwd /home/chuba $ df Filesystem 1K-blocks Used Available Use% Mounted on ... /dev/sdb1 1621245336 825209568 713681236 54% /home ... $ ls -al /dev/sdb1 brw-rw---- 1 root disk 8, 17 Oct 24 11:22 /dev/sdb1 $ rm -f test.dat && dd if=/dev/zero of=test.dat ^C9912890+0 records in 9912890+0 records out 5075399680 bytes (5.1 GB) copied, 26.8189 s, 189 MB/s
这个终端模拟文件的不停写入,同时在另外一个终端查验谁干的。这里我们已经知道设备的major/minor为8/17
$ stat -c '%i' test.dat 25337884 $ sudo stap /usr/local/share/doc/systemtap/examples/io/inodewatch.stp 8 17 25337884 dd(740) vfs_write 0x800011/25337884 dd(740) vfs_write 0x800011/25337884 dd(740) vfs_write 0x800011/25337884 dd(740) vfs_write 0x800011/25337884 dd(740) vfs_write 0x800011/25337884 dd(740) vfs_write 0x800011/25337884 ...
看到了吧,dd是罪魁祸首,pid是740, 搞定收工!
小结: systemtap处理这种问题很是神器。
祝玩得开心!
Post Footer automatically generated by wp-posturl plugin for wordpress.
遍历所有/proc/$pid/fd/的项也能做到吧
dtrace Reply:
March 13th, 2013 at 1:48 pm
可能。但是如果使用的时间片比较大,而process比较多的时候,不等遍历到就已经结束了。
还是solaris/mac/bsd的dtrace可以分分钟搞定
# Files opened by process,
dtrace -n ‘syscall::open*:entry { printf(“%s %s”,execname,copyinstr(arg0)); }’
CPU ID FUNCTION:NAME
0 14 open:entry gnome-netstatus- /dev/kstat
0 14 open:entry man /var/ld/ld.config
0 14 open:entry man /lib/libc.so.1
0 14 open:entry man /usr/share/man/man.cf
@portl4t
关键是谁在写。
lsof 也可以:
lsof /home/chuba/test.dat
Yu Feng Reply:
March 12th, 2013 at 10:48 pm
lsof查出owner
沈锋 Reply:
March 12th, 2013 at 11:02 pm
lsof /var/cache/fontconfig/6d41288fd70b0be22e8c3a91e032eec0-le64.cache-3
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME
chrome 13177 feng mem REG 8,7 35304 8259168 /var/cache/fontconfig/6d41288fd70b0be22e8c3a91e032eec0-le64.cache-3
chrome 13182 feng mem REG 8,7 35304 8259168 /var/cache/fontconfig/6d41288fd70b0be22e8c3a91e032eec0-le64.cache-3
emacs 15650 feng mem REG 8,7 35304 8259168 /var/cache/fontconfig/6d41288fd70b0be22e8c3a91e032eec0-le64.cache-3
java 19995 feng mem REG 8,7 35304 8259168 /var/cache/fontconfig/6d41288fd70b0be22e8c3a91e032eec0-le64.cache-3
awesome 30162 feng mem REG 8,7 35304 8259168 /var/cache/fontconfig/6d41288fd70b0be22e8c3a91e032eec0-le64.cache-3
evilvte 30282 feng mem REG 8,7 35304 8259168 /var/cache/fontconfig/6d41288fd70b0be22e8c3a91e032eec0-le64.cache-3
Sebastian Reply:
May 1st, 2013 at 9:07 pm
看标题~ 大牛找的是进程不是ower.
Yu Feng Reply:
May 1st, 2013 at 9:19 pm
right
顶一下如灯塔般的霸爷~
把/proc/sys/vm/block_dump 打开,也可以有这样的效果。
Sebastian Reply:
May 1st, 2013 at 9:02 pm
请问“/proc/sys/vm/block_dump”用这个如何实现?
Sebastian Reply:
May 1st, 2013 at 9:04 pm
请问用block_dump如何实现?
Yu Feng Reply:
May 1st, 2013 at 9:19 pm
blktrace轻松实现。
leon Reply:
May 1st, 2013 at 9:52 pm
这就是个开关,echo 1 > /proc/sys/vm/block_dump 就可以打开,写入0关闭。
dump的内容用dmesg可以看到。
Yu Feng Reply:
May 2nd, 2013 at 2:19 pm
en
曾经在solaris上面自己写了一个脚本来搞定此事(ptree),到了linux下,基本都用lsof来搞定了。
那为啥会 lsof 查不到呢?
fedora17上路径是/usr/share/systemtap/testsuite/systemtap.examples/io
@沈锋
其实fuser也可以。。。。
tanyangxf Reply:
June 20th, 2014 at 3:42 pm
瞬间完成的监控不出来吧,长时间没释放的到是没问题,如果是有需要就写一下日志这监控不出来吧
lsof看inode没有压力的飘过
Distributor ID: CentOS
Description: CentOS release 5.6 (Final)
Release: 5.6
Codename: Final
请问为什么在以上操作系统上找不到这个文件?
原来dd是罪魁祸首,pid是740,谢谢你分享…
那为啥会 lsof 查不到呢? +1
Yu Feng Reply:
April 12th, 2013 at 4:12 pm
lsof查出来的是owner吧,而且即使可以也是查出瞬间的动作。
您好,从您博客中学习到这个方法,不过木有成功呀,求助:
1. 我的inodewatch.stp在不同的目录下
/usr/share/doc/systemtap-client-1.8/examples/io/inodewatch.stp
不过内容一致,应该是不影响的吧~
内核版本:2.6.32-279.14.1.el6.x86_64
我运行“rpm -qf /usr/bin/stap”得到的结果是:
systemtap-client-1.8-7.el6.x86_64
systemtap-devel-1.8-7.el6.x86_64
2. 然后根据您用法,我在boot分区随便建一个文件,并写入内容……
然后调用stap去找到哪个进程在写该文件!报错了……
[root@test boot]# stap /usr/share/doc/systemtap-client-1.8/examples/io/inodewatch.stp 8 1 25
semantic error: while resolving probe point: identifier ‘kernel’ at /usr/share/systemtap/tapset/vfs.stp:820:19
source: probe vfs.write = kernel.function(“vfs_write”)
^
semantic error: missing x86_64 kernel/module debuginfo under ‘/lib/modules/2.6.32-279.14.1.el6.x86_64/build’
semantic error: while resolving probe point: identifier ‘vfs’ at /usr/share/doc/systemtap-client-1.8/examples/io/inodewatch.stp:3:7
source: probe vfs.write, vfs.read
^
semantic error: no match
semantic error: while resolving probe point: identifier ‘kernel’ at /usr/share/systemtap/tapset/vfs.stp:752:18
source: probe vfs.read = kernel.function(“vfs_read”)
^
semantic error: while resolving probe point: identifier ‘vfs’ at /usr/share/doc/systemtap-client-1.8/examples/io/inodewatch.stp:3:18
source: probe vfs.write, vfs.read
^
Pass 2: analysis failed. Try again with another ‘–vp 01’ option.
Missing separate debuginfos, use: debuginfo-install kernel-2.6.32-279.14.1.el6.x86_64
正在http://sourceware.org/systemtap/ 继续学习中……
求指导: lin_credible@163.com. 或者直接回复,万分感谢~~
Yu Feng Reply:
June 27th, 2013 at 11:51 am
系统的符号信息没安装好。
Taolinran Reply:
June 27th, 2013 at 12:34 pm
嗯,谢谢啦~
stap /usr/local/share/doc/systemtap/examples/io/inodewatch.stp 8 7 48
parse error: expected ‘)’
saw: operator ‘;’ at /usr/local/share/doc/systemtap/examples/io/inodewatch.stp:7:11
source: && ino == $3)
^
1 parse error.
Pass 1: parse failed. Try again with another ‘–vp 1’ option.
—— 运行提示以上错误。查找过,也还是没能解决。请问这是什么原因呢?怎么解决。应该不是系统符号信息问题吧?期待回复。谢谢!
Yu Feng Reply:
October 15th, 2013 at 6:22 pm
不大像。符号问题你看下其他文件可以正常运行吗? 我怀疑是stap版本太低。
long904 Reply:
October 23rd, 2013 at 4:50 pm
感谢回复。今天抽空升级了一下stap版本,由原来1.8升级到2.3.但还是有问题
semantic error: while resolving probe point: identifier ‘kernel’ at /usr/local/systemtap/share/systemtap/tapset/linux/vfs.stp:836:19
source: probe vfs.write = kernel.function(“vfs_write”)
系统内核是2.6.32-71.el6.x86_64。
long904 Reply:
October 23rd, 2013 at 4:50 pm
感谢回复。
今天抽空升级了一下stap版本,由原来1.8升级到2.3.但还是有问题
semantic error: while resolving probe point: identifier ‘kernel’ at /usr/local/systemtap/share/systemtap/tapset/linux/vfs.stp:836:19
source: probe vfs.write = kernel.function(“vfs_write”)
系统内核是2.6.32-71.el6.x86_64。
Hi,If my Linux system use the volume to manager the disk, I would not get the
8,7 by this command,
ls -al /dev/sdb1
++++++++++++++
so, how to?
/dev/mapper/vg_water-lv_home
Thanks a lot.
Watson
请问我的这个报错具体应该怎么解决?
semantic error: while resolving probe point: identifier ‘kernel’ at /usr/share/systemtap/tapset/linux/vfs.stp:836:19
source: probe vfs.write = kernel.function(“vfs_write”)
^
semantic error: missing x86_64 kernel/module debuginfo [man warning::debuginfo] under ‘/lib/modules/2.6.32-431.23.3.el6.centos.plus.x86_64/build’
semantic error: while resolving probe point: identifier ‘vfs’ at /usr/share/doc/systemtap-client-2.3/examples/io/inodewatch.stp:3:7
source: probe vfs.write, vfs.read
^
semantic error: no match
semantic error: while resolving probe point: identifier ‘kernel’ at /usr/share/systemtap/tapset/linux/vfs.stp:768:18
source: probe vfs.read = kernel.function(“vfs_read”)
^
semantic error: while resolving probe point: identifier ‘vfs’ at /usr/share/doc/systemtap-client-2.3/examples/io/inodewatch.stp:3:18
source: probe vfs.write, vfs.read
^
Pass 2: analysis failed. [man error::pass2]
ubuntu好像没有?
这是个用来做内核调试的工具啊…