Search code examples
c++timestampfilesystems

c++ testing if one file is older than a set of files


I am creating a cache for some data, but of course I want the cache to become invalid if any of the source files from which the cache is made is modified. TO that effect I made this function:

bool CacheIsValid(
    const std::string& cache_shader_path,
    const std::vector<std::string>& shader_paths)
{
    // This is really messy because of the std stuff, the short of it is:
    // Find the youngest file in the shader paths, then check it against the
    // timestamp of the cached file.
    std::time_t youngest_file_ts = std::time(nullptr);
    for(auto file : shader_paths)
    {
        std::time_t current_timestamp =
            std::chrono::system_clock::to_time_t(
                std::chrono::file_clock::to_sys(fs::last_write_time(file)));
        double time_diff = difftime(youngest_file_ts, current_timestamp);
        if(time_diff > 0) youngest_file_ts = current_timestamp;
    }

    // All this is doing is comparing the youngest file time stamp with the cache.
    return fs::exists(cache_shader_path)
        && (difftime(youngest_file_ts, std::chrono::system_clock::to_time_t(
            std::chrono::file_clock::to_sys(fs::last_write_time(cache_shader_path)))) < 0);
}

I don't know what I did wrong but that is always returning true even when the input files are modified. I am checking the timestamps using stat and the files on disk are objectively younger than the cache file, I also tested that the inputs to this function are correct, and they are.


Solution

  • due to you want to find youngest_file_ts -> find most recently timestamp (greater number) of a changing file however

    double time_diff = difftime(youngest_file_ts, current_timestamp);
    if(time_diff > 0) youngest_file_ts = current_timestamp; // find greater number one
    

    after the for loop youngest_file_ts is oldest timestamp of a changing file therefor

    (difftime(youngest_file_ts, std::chrono::system_clock::to_time_t(
              std::chrono::file_clock::to_sys(fs::last_write_time(cache_shader_path)))) < 0) alway true.
    

    it should be change like

        if (shader_paths.empty()) {
            return false
        } else {
    //initialize youngest_file_ts as last_write_time of first element in shader_paths
            std::time_t youngest_file_ts = std::chrono::system_clock::to_time_t(
                     std::chrono::file_clock::to_sys(fs::last_write_time(shader_paths.at(0))); 
            for (auto file : shader_paths)
            {
                std::time_t current_timestamp = std::chrono::system_clock::to_time_t(
                    std::chrono::file_clock::to_sys(fs::last_write_time(file)));
                double time_diff = difftime(youngest_file_ts, current_timestamp);
                if (time_diff < 0) youngest_file_ts = current_timestamp;
            }
            // All this is doing is comparing the youngest file time stamp with the cache.
            return fs::exists(cache_shader_path)
                && (difftime(youngest_file_ts, std::chrono::system_clock::to_time_t(
                    std::chrono::file_clock::to_sys(fs::last_write_time(cache_shader_path)))) < 0);
        }