1//===----------------------------------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#include "clang/Serialization/ModuleCache.h"
10
11#include "clang/Serialization/InMemoryModuleCache.h"
12#include "clang/Serialization/ModuleFile.h"
13#include "llvm/Support/FileSystem.h"
14#include "llvm/Support/LockFileManager.h"
15#include "llvm/Support/Path.h"
16
17using namespace clang;
18
19namespace {
20class CrossProcessModuleCache : public ModuleCache {
21 InMemoryModuleCache InMemory;
22
23public:
24 void prepareForGetLock(StringRef ModuleFilename) override {
25 // FIXME: Do this in LockFileManager and only if the directory doesn't
26 // exist.
27 StringRef Dir = llvm::sys::path::parent_path(path: ModuleFilename);
28 llvm::sys::fs::create_directories(path: Dir);
29 }
30
31 std::unique_ptr<llvm::AdvisoryLock>
32 getLock(StringRef ModuleFilename) override {
33 return std::make_unique<llvm::LockFileManager>(args&: ModuleFilename);
34 }
35
36 std::time_t getModuleTimestamp(StringRef ModuleFilename) override {
37 llvm::sys::fs::file_status Status;
38 if (llvm::sys::fs::status(path: ModuleFilename, result&: Status) != std::error_code{})
39 return 0;
40 return llvm::sys::toTimeT(TP: Status.getLastModificationTime());
41 }
42
43 void updateModuleTimestamp(StringRef ModuleFilename) override {
44 // Overwrite the timestamp file contents so that file's mtime changes.
45 std::error_code EC;
46 llvm::raw_fd_ostream OS(
47 serialization::ModuleFile::getTimestampFilename(FileName: ModuleFilename), EC,
48 llvm::sys::fs::OF_TextWithCRLF);
49 if (EC)
50 return;
51 OS << "Timestamp file\n";
52 OS.close();
53 OS.clear_error(); // Avoid triggering a fatal error.
54 }
55
56 InMemoryModuleCache &getInMemoryModuleCache() override { return InMemory; }
57 const InMemoryModuleCache &getInMemoryModuleCache() const override {
58 return InMemory;
59 }
60};
61} // namespace
62
63IntrusiveRefCntPtr<ModuleCache> clang::createCrossProcessModuleCache() {
64 return llvm::makeIntrusiveRefCnt<CrossProcessModuleCache>();
65}
66