【问题标题】:C readdir & struct dirent allocationC readdir & struct dirent 分配
【发布时间】:2016-01-09 19:37:19
【问题描述】:

readdir 返回一个指向struct dirent 的指针,我测试过存储在两个不同指针中的两次对readdir 的调用是否修改了第一个指针内容,它没有。

所以我猜 readdir 分配了一些内存,对吗?

如果是这样,它应该被释放,这是我以前从未做过的事情......

【问题讨论】:

  • 手册页是怎么说的?
  • The data returned by readdir() may be overwritten by subsequent calls to readdir() for the same directory stream.,就像我在帖子中所说的那样,在两次调用之后它并没有改变第一个结构。是不是因为它有一个条目缓冲区,并且在一定数量的调用后,它会将下一部分的其余部分加载到缓冲区中?
  • 上面写着“可能是”。它还说“不要释放它。”我想你先打电话给opendir,然后根据答案使用closedir

标签: c readdir dirent.h


【解决方案1】:

POSIX 规定应用程序不得修改readdir() 返回的结构:

应用程序不得修改返回的结构 readdir() 点的值,也不是指向的任何存储区域 结构中的指针。返回的指针和指针 在结构内,可能会被无效或结构或 后续调用 readdir() 可能会覆盖存储区域 在同一目录流上。他们不会受到调用的影响 readdir() 在不同的目录流上。

所以是内部分配内存还是使用静态缓冲区取决于具体实现如何实现。您需要做的就是尊重该功能所需的合同。也就是说,你不能试图修改它并调用closedir()来关闭目录流。

【讨论】:

  • 对于我需要在“Tiny Toy Filesystem”中实现这些功能的项目,这就是为什么我需要有关实现的详细信息!
  • @NicolasScottoDiPerto POSIX 不要求 readdir() 是可重入的或线程安全的。所以一个简单的实现可以使用static缓冲区并且仍然可以兼容。
  • POSIX 引用的最后一行表示,每次调用opendir 至少需要一个唯一的缓冲区,因此它不能是系统范围的static 缓冲区。它可能是嵌入在DIR 结构中的struct dirent(其中DIR 结构由opendir 动态分配并由closedir 释放)。
  • 是的,很抱歉,我的情况更复杂,因为我还必须实现磁盘 io api 并使所有这些以一种好的方式协同工作有点复杂!我认为可能有问题的是当并发进入游戏时使用缓冲区...如果磁盘被修改,缓冲区没有正确的内容。
【解决方案2】:

如果它确实分配了任何内存,则调用 closedir (http://linux.die.net/man/3/closedir) 将为您释放它

【讨论】:

  • 这意味着对readdir 的调用填充了一个struct dirent * 动态数组,这很奇怪......它可能很大......我很想知道流是如何工作的!它是否将所有内容加载到缓冲区中?就像我之前说的那样,它可能是巨大的......
  • 目录流只需要一个。请参阅另一篇文章中的报价
【解决方案3】:

是的,它应该被释放。您应该在readdir 之后的目录上调用closedir,就像在常规文件之后在fopen 之后调用fclose

【讨论】:

    猜你喜欢
    • 2018-03-30
    • 1970-01-01
    • 1970-01-01
    • 2012-08-17
    • 1970-01-01
    • 2014-05-26
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多