线程安全的多文件写入

时间:2011-02-15 00:08:39

标签: c multithreading unix

我有一个守护进程,它接受套接字连接并读取或写入一组动态文件,具体取决于连接的性质。因为我的守护进程是多线程的,所以存在可能由多个线程写入同一文件的可能性。因为我的文件列表是动态的而不是固定的,所以我不确定如何防止一个线程碰到另一个线程。出于性能原因,我希望线程同时写入不同的文件,而不是同时写入不同的文件。

其他问题建议使用互斥锁,但我并不完全清楚互斥体在这种情况下如何提供帮助 - 文件列表是动态的,只有线程知道。

在这种情况下使用文件锁定是否合适?如果是这样,如何以线程安全的方式实现文件锁定?

3 个答案:

答案 0 :(得分:2)

flock会正常工作。它不会锁定文件描述符,它会锁定实际文件。

独占flock'ed的文件不能由其他进程或线程再次独占锁定。这会破坏锁的整个目的。

一个注意事项是这些锁是建议性的。不使用flock的流程可以很高兴地覆盖该文件,即使其他进程具有独占权限 - flock已编辑它。

答案 1 :(得分:1)

我会使用事件代理模式。每个socketing线程触发一个事件(有文件的args),然后事件由一个中央文件代理处理,当前正在写入一个共享的文件集合。

如果无法写入文件,请确定您要执行的操作...否则报告成功。

多个侦听器,一个中央文件锁集合,多个编写器。

答案 2 :(得分:1)

我不能说这将是“最佳”解决方案,但我建议这样的事情:

维护包含两件事的结构的链表:

  1. 文件名
  2. 与文件关联的条件等待变量。
  3. 流A.当守护程序收到请求时,互斥锁会锁定列表并检查文件名是否在列表中。如果不是,请使用新条件等待变量向链接列表添加新条目,以供其他线程使用。释放互斥锁。执行文件操作。完成后,锁定链接列表并删除该文件的struct条目,然后通过wait对象发出其他线程的信号。

    流B.如果请求进入同一个文件,它将锁定列表并查找列表中包含的文件名。如果它在列表中,请获取等待变量并等待它。当线程被发出信号时,抓住列表上的锁并查看该文件是否在列表中(可能是另一个线程在您之前获取了文件名上的锁)。如果没有,请遵循流程A.如果是,请抓住新结构中的等待变量并再次等待直到发出信号,然后再次执行上述步骤。