当前位置: 代码网 > it编程>前端脚本>Powershell > Linux flock原理分析(shell进阶)

Linux flock原理分析(shell进阶)

2025年07月07日 Powershell 我要评论
flock申请的锁对象是处于 内核空间层的全局级别的open file table中的。回忆一下os是如何打开一个文件的?首先一个文件对应一个fd,fd是维护在用户空间,通过索引对应到内核空间的fd表

flock申请的锁对象是处于 内核空间层的全局级别的open file table中的。

回忆一下os是如何打开一个文件的?

首先一个文件对应一个fd,fd是维护在用户空间,通过索引对应到内核空间的fd表。程序是无法直接打开文件的,需要请内核帮忙。

用户空间使用fd在内核中调用open函数,当然可以调用多次,调用多次在open file中就会记录多条记录。然后在内核空间的文件级别层的inode表找到对应的inode(这个inode表是从硬盘上copy过来的,并附加上一些额外的信息), 将此文件加载到虚拟内存中此时这个文件就被打开了。

注意:

  • 内核层面的inode 表和open file表是一对多的关系。 
  • fd表 中存在复制的fd,这两个fd可能指向同一个lock

如何理解man flock中的这段文字呢?

 locks created by flock() are associated with an open file table entry.  this means that duplicate file descriptors  (created  by,  for  example,  fork(2)  or
       dup(2))  refer  to  the  same lock, and this lock may be modified or released using any of these descriptors.  furthermore, the lock is released either by an
       explicit lock_un operation on any of these duplicate descriptors, or when all such descriptors have been closed.

这段话主要说明了文件描述符上的锁和文件上的锁的区别 , 因为存在fork的子进程使用同一把锁。

当手动释放锁文件时,open file table entry中的fd关联的锁消失。

如果释放的是某个fd的锁,则锁还是存在并生效的。

open file table上维护的其他特殊信息

 对于多个进程同一文件都能正确工作。每个进程都有它自己的文件表项,其中也有它自己的当前文件位移量。但是,当多个进程同一文件时,则可能产生预期不到的结果

假定有两个独立的进程 a和b,都对同一文件进行添加操作。每个进程都已打开了该文件,但未使用 o_append标志。

此时各数据结构之间的关系如图中所示一样。每个进程都有它自己的文件表项,但是共享一个 v节点表项。

假定进程a调用了lseek,它将对于进程a的该文件的当前位移量设置为1500字节(当前文件尾端处)。然后内核切换进程使进程 b运行。

进程b执行lseek,也将其对该文件的当前位移量设置为 1500字节(当前文件尾端处)。然后b调用w r i te,它将b的该文件的当前文件位移量增至 1600。

因为该文件的长度已经增加了,所以内核对 v节点中的当前文件长度更新为 1 6 0 0。然后,内核又进行进程切换使进程 a恢复运行。

当a调用write时,就从其当前文件位移量 ( 1500 )处将数据写到文件中去。这样也就代换了进程 b刚写到该文件中的数据。

--update 2022年3月24日14:04:00 

劝告锁

flock和fcntl都属于劝告式锁(advisory lock),如果同步的进程遵循游戏规则,操作之前先申请锁,就能起到同步的作用;

但是如果进程无视劝告式锁的存在,不遵循游戏规则,不申请锁直接操作文件或文件的某个区域,内核也不会阻止这种操作。

总结

以上为个人经验,希望能给大家一个参考,也希望大家多多支持代码网。

(0)

相关文章:

版权声明:本文内容由互联网用户贡献,该文观点仅代表作者本人。本站仅提供信息存储服务,不拥有所有权,不承担相关法律责任。 如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 2386932994@qq.com 举报,一经查实将立刻删除。

发表评论

验证码:
Copyright © 2017-2025  代码网 保留所有权利. 粤ICP备2024248653号
站长QQ:2386932994 | 联系邮箱:2386932994@qq.com