【问题标题】:Does sys function call "stat" change my file?sys 函数调用“stat”是否会更改我的文件?
【发布时间】:2015-12-05 17:28:35
【问题描述】:

我目前正在尝试使“C”更像我自己的脚本语言。我在 *.so 文件中编写程序特定代码在运行时重新加载此文件并执行我编写的新代码。

我面临的问题是函数“stat”的结果。每次我询问 SO 文件是否已通过“stat(filename,statbuf)”修改时,结果 stat->mtim 似乎总是已更改。结果我在每个循环运行中不断地重新加载我的代码。

我假设如果文件没有发生任何文件更改,则 st_mtime 必须始终相同。我错了吗?

这里是我如何检索值 st_mtime 的函数:

inline timespec LinuxGetLastWriteTime(const std::string& filename) {
    struct stat *buf;

    stat(filename.c_str(), buf);

    return buf->st_mtim;
}

我在这里检查是否需要重新加载:

timespec NewSOWriteTime = LinuxGetLastWriteTime(SoSource);
if ( Game.last_modification  != NewSOWriteTime ) {
        LinuxUnloadGameCode(&Game);
        Game = LinuxLoadGameCode(SoSource, "libCode_temp.so");
}

还有我的两个重载的 != 和 <:>

bool operator<(const timespec& lhs, const timespec& rhs) {
    if (lhs.tv_sec == rhs.tv_sec)
        return lhs.tv_nsec < rhs.tv_nsec;
    else
        return lhs.tv_sec < rhs.tv_sec;
}

bool operator!=(const timespec& lhs, const timespec& rhs) {
    if (lhs.tv_sec == rhs.tv_sec)
        return lhs.tv_nsec != rhs.tv_nsec;
    else
        return lhs.tv_sec != rhs.tv_sec;

知道为什么会发生这种情况

【问题讨论】:

  • st_mtim 是时间time_t,而不是timespec。揭示的代码中缺少的是timespec 是如何从time_t 构造的。你初始化所有成员了吗? time_t 为您提供秒数。如果这些是相同的,但 tv_nsec 的某些成员是垃圾怎么办?
  • 作为一般建议,在 Linux 上,您可以在valgrind 下运行程序并跟进错误。
  • jupp 在过去 st_mtim 是 time_t 但至少在我的平台 ubuntu 14.04 上它现在是 timespec see pic。所以它不是从 time_t 构造的,而是从函数调用“stat”中“初始化”的。

标签: c linux ubuntu-14.04 stat


【解决方案1】:

你使用的代码:

struct stat *buf;

stat(filename.c_str(), buf);

return buf->st_mtim;

至少可以说很奇怪。你运气不好,它并没有立即崩溃,但没有人真正知道它在哪里写入结果;可能会在途中覆盖其他一些重要数据。您应该自己分配buf并将其地址传递给stat,例如:

struct stat buf = {0};    // or memset(0)
stat(filename.c_str(), &buf);
return buf.st_mtim;

您可能还应该检查 stat 的错误状态,但如果缓冲区归零,它只会返回 0,这可能没问题。

【讨论】:

  • 而且,正如 Kaz 在对问题的评论中所说,valgrind 通常会立即发现类似的错误。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-06-05
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-01-16
  • 2020-09-06
相关资源
最近更新 更多