;
16using namespacetooling;
17using namespacedependencies;
19llvm::ErrorOr<DependencyScanningWorkerFilesystem::TentativeEntry>
20DependencyScanningWorkerFilesystem::readFile(StringRef
Filename) {
22 autoMaybeFile = getUnderlyingFS().openFileForRead(
Filename);
24 returnMaybeFile.getError();
25 auto File= std::move(*MaybeFile);
27 autoMaybeStat =
File->status();
29 returnMaybeStat.getError();
30 autoStat = std::move(*MaybeStat);
32 autoMaybeBuffer =
File->getBuffer(Stat.getName());
34 returnMaybeBuffer.getError();
35 autoBuffer = std::move(*MaybeBuffer);
38 if(Stat.getSize() != Buffer->getBufferSize())
39Stat = llvm::vfs::Status::copyWithNewSize(Stat, Buffer->getBufferSize());
41 returnTentativeEntry(Stat, std::move(Buffer));
46 auto&Entry = Ref.Entry;
48 if(Entry.isError() || Entry.isDirectory())
52assert(Contents &&
"contents not initialized");
58std::lock_guard<std::mutex> GuardLock(Contents->
ValueLock);
72Contents->
DepDirectives.store(
newstd::optional<DependencyDirectivesTy>());
81 newstd::optional<DependencyDirectivesTy>(std::move(Directives)));
93std::max(2u, llvm::hardware_concurrency().compute_thread_count() / 4);
94CacheShards = std::make_unique<CacheShard[]>(NumShards);
100assert(llvm::sys::path::is_absolute_gnu(
Filename));
106llvm::sys::fs::UniqueID UID)
const{
107 autoHash = llvm::hash_combine(UID.getDevice(), UID.getFile());
108 returnCacheShards[Hash % NumShards];
114assert(llvm::sys::path::is_absolute_gnu(
Filename));
115std::lock_guard<std::mutex> LockGuard(
CacheLock);
122llvm::sys::fs::UniqueID UID)
const{
123std::lock_guard<std::mutex> LockGuard(CacheLock);
124 autoIt = EntriesByUID.find(UID);
125 returnIt == EntriesByUID.end() ? nullptr : It->getSecond();
131llvm::ErrorOr<llvm::vfs::Status> Stat) {
132std::lock_guard<std::mutex> LockGuard(CacheLock);
133 auto[It, Inserted] = CacheByFilename.insert({
Filename, {
nullptr,
nullptr}});
138assert((Inserted ||
CachedRealPath) &&
"existing file with empty pair");
147llvm::sys::fs::UniqueID UID, llvm::vfs::Status Stat,
148std::unique_ptr<llvm::MemoryBuffer> Contents) {
149std::lock_guard<std::mutex> LockGuard(CacheLock);
150 auto[It, Inserted] = EntriesByUID.insert({UID,
nullptr});
151 auto&CachedEntry = It->getSecond();
155StoredContents =
new(ContentsStorage.Allocate())
157CachedEntry =
new(EntryStorage.Allocate())
167std::lock_guard<std::mutex> LockGuard(CacheLock);
168 auto[It, Inserted] = CacheByFilename.insert({
Filename, {&Entry,
nullptr}});
170 if(!Inserted || !CachedEntry)
171CachedEntry = &Entry;
178assert(llvm::sys::path::is_absolute_gnu(
Filename));
179std::lock_guard<std::mutex> LockGuard(CacheLock);
180 autoIt = CacheByFilename.find(
Filename);
181 returnIt == CacheByFilename.end() ? nullptr : It->getValue().second;
186llvm::ErrorOr<llvm::StringRef> RealPath) {
187std::lock_guard<std::mutex> LockGuard(CacheLock);
190 if(!StoredRealPath) {
193 returnRealPath.getError();
194 returnRealPath->str();
197StoredRealPath =
new(RealPathStorage.Allocate())
201 return*StoredRealPath;
204boolDependencyScanningWorkerFilesystem::shouldBypass(StringRef
Path)
const{
205 returnBypassedPathPrefix &&
Path.starts_with(*BypassedPathPrefix);
212 llvm::vfs::ProxyFileSystem>(
std::move(FS)),
213SharedCache(SharedCache),
214WorkingDirForCacheLookup(
llvm::errc::invalid_argument) {
215updateWorkingDirForCacheLookup();
219DependencyScanningWorkerFilesystem::getOrEmplaceSharedEntryForUID(
220TentativeEntry TEntry) {
221 auto&Shard = SharedCache.
getShardForUID(TEntry.Status.getUniqueID());
223std::move(TEntry.Status),
224std::move(TEntry.Contents));
228DependencyScanningWorkerFilesystem::findEntryByFilenameWithWriteThrough(
233 if(
const auto*Entry = Shard.findEntryByFilename(
Filename))
238llvm::ErrorOr<const CachedFileSystemEntry &>
239DependencyScanningWorkerFilesystem::computeAndStoreResult(
240StringRef OriginalFilename, StringRef FilenameForLookup) {
241llvm::ErrorOr<llvm::vfs::Status> Stat =
242getUnderlyingFS().status(OriginalFilename);
245getOrEmplaceSharedEntryForFilename(FilenameForLookup, Stat.getError());
246 returninsertLocalEntryForFilename(FilenameForLookup, Entry);
249 if(
const auto*Entry = findSharedEntryByUID(*Stat))
250 returninsertLocalEntryForFilename(FilenameForLookup, *Entry);
253Stat->isDirectory() ? TentativeEntry(*Stat) : readFile(OriginalFilename);
257 const auto&UIDEntry = getOrEmplaceSharedEntryForUID(std::move(*TEntry));
258 return&getOrInsertSharedEntryForFilename(FilenameForLookup, UIDEntry);
260 return&getOrEmplaceSharedEntryForFilename(FilenameForLookup,
264 returninsertLocalEntryForFilename(FilenameForLookup, *SharedEntry);
267llvm::ErrorOr<EntryRef>
269StringRef OriginalFilename) {
271 autoFilenameForLookup = tryGetFilenameForLookup(OriginalFilename, PathBuf);
272 if(!FilenameForLookup)
273 returnFilenameForLookup.getError();
275 if(
const auto*Entry =
276findEntryByFilenameWithWriteThrough(*FilenameForLookup))
278 autoMaybeEntry = computeAndStoreResult(OriginalFilename, *FilenameForLookup);
280 returnMaybeEntry.getError();
284llvm::ErrorOr<llvm::vfs::Status>
290 returngetUnderlyingFS().status(
Path);
294 return Result.getError();
295 return Result->getStatus();
305llvm::ErrorOr<llvm::vfs::Status> Status =
status(
Path);
306 returnStatus && Status->exists();
313classDepScanFile final :
publicllvm::vfs::File {
315DepScanFile(std::unique_ptr<llvm::MemoryBuffer> Buffer,
316llvm::vfs::Status Stat)
317: Buffer(
std::move(Buffer)), Stat(
std::move(Stat)) {}
319 staticllvm::ErrorOr<std::unique_ptr<llvm::vfs::File>> create(
EntryRefEntry);
321llvm::ErrorOr<llvm::vfs::Status> status()
override{
returnStat; }
323llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>>
324getBuffer(
constTwine &Name, int64_t FileSize,
boolRequiresNullTerminator,
325 boolIsVolatile)
override{
326 returnstd::move(Buffer);
329std::error_code close()
override{
return{}; }
332std::unique_ptr<llvm::MemoryBuffer> Buffer;
333llvm::vfs::Status Stat;
338llvm::ErrorOr<std::unique_ptr<llvm::vfs::File>>
339DepScanFile::create(
EntryRefEntry) {
340assert(!Entry.
isError() &&
"error");
343 returnstd::make_error_code(std::errc::is_a_directory);
345 auto Result= std::make_unique<DepScanFile>(
346llvm::MemoryBuffer::getMemBuffer(Entry.
getContents(),
351 returnllvm::ErrorOr<std::unique_ptr<llvm::vfs::File>>(
352std::unique_ptr<llvm::vfs::File>(std::move(
Result)));
355llvm::ErrorOr<std::unique_ptr<llvm::vfs::File>>
361 returngetUnderlyingFS().openFileForRead(
Path);
365 return Result.getError();
366 returnDepScanFile::create(
Result.get());
373StringRef OriginalFilename =
Path.toStringRef(OwnedFilename);
375 if(shouldBypass(OriginalFilename))
376 returngetUnderlyingFS().getRealPath(
Path, Output);
379 autoFilenameForLookup = tryGetFilenameForLookup(OriginalFilename, PathBuf);
380 if(!FilenameForLookup)
381 returnFilenameForLookup.getError();
383 autoHandleCachedRealPath =
386 returnRealPath.getError();
387Output.assign(RealPath->begin(), RealPath->end());
392 if(
const auto*RealPath =
394 returnHandleCachedRealPath(*RealPath);
398 if(
const auto*ShardRealPath =
399Shard.findRealPathByFilename(*FilenameForLookup)) {
401*FilenameForLookup, *ShardRealPath);
402 returnHandleCachedRealPath(RealPath);
406std::error_code EC = getUnderlyingFS().getRealPath(OriginalFilename, Output);
407llvm::ErrorOr<llvm::StringRef> ComputedRealPath = EC;
409ComputedRealPath = StringRef{Output.data(), Output.size()};
414 const auto&RealPath = Shard.getOrEmplaceRealPathForFilename(
415*FilenameForLookup, ComputedRealPath);
416 returnHandleCachedRealPath(
421 constTwine &
Path) {
422std::error_code EC = ProxyFileSystem::setCurrentWorkingDirectory(
Path);
423updateWorkingDirForCacheLookup();
427voidDependencyScanningWorkerFilesystem::updateWorkingDirForCacheLookup() {
428llvm::ErrorOr<std::string> CWD =
429getUnderlyingFS().getCurrentWorkingDirectory();
431WorkingDirForCacheLookup = CWD.getError();
432}
else if(!llvm::sys::path::is_absolute_gnu(*CWD)) {
433WorkingDirForCacheLookup = llvm::errc::invalid_argument;
435WorkingDirForCacheLookup = *CWD;
437assert(!WorkingDirForCacheLookup ||
438llvm::sys::path::is_absolute_gnu(*WorkingDirForCacheLookup));
441llvm::ErrorOr<StringRef>
442DependencyScanningWorkerFilesystem::tryGetFilenameForLookup(
444StringRef FilenameForLookup;
445 if(llvm::sys::path::is_absolute_gnu(OriginalFilename)) {
446FilenameForLookup = OriginalFilename;
447}
else if(!WorkingDirForCacheLookup) {
448 returnWorkingDirForCacheLookup.getError();
450StringRef RelFilename = OriginalFilename;
451RelFilename.consume_front(
"./");
452PathBuf.assign(WorkingDirForCacheLookup->begin(),
453WorkingDirForCacheLookup->end());
454llvm::sys::path::append(PathBuf, RelFilename);
455FilenameForLookup = StringRef{PathBuf.begin(), PathBuf.size()};
457assert(llvm::sys::path::is_absolute_gnu(FilenameForLookup));
458 returnFilenameForLookup;
An in-memory representation of a file system entity that is of interest to the dependency scanning fi...
Reference to a CachedFileSystemEntry.
llvm::vfs::Status getStatus() const
StringRef getContents() const
llvm::ErrorOr< EntryRef > unwrapError() const
If the cached entry represents an error, promotes it into ErrorOr.
The JSON file list parser is used to communicate input to InstallAPI.
bool scanSourceForDependencyDirectives(StringRef Input, SmallVectorImpl< dependency_directives_scan::Token > &Tokens, SmallVectorImpl< dependency_directives_scan::Directive > &Directives, DiagnosticsEngine *Diags=nullptr, SourceLocation InputSourceLoc=SourceLocation())
Scan the input for the preprocessor directives that might have an effect on the dependencies for a co...
@ Result
The result type of a method or function.
Diagnostic wrappers for TextAPI types for error reporting.
hash_code hash_value(const clang::tooling::dependencies::ModuleID &ID)
Contents and directive tokens of a cached file entry.
std::mutex ValueLock
The mutex that must be locked before mutating directive tokens.
std::atomic< const std::optional< DependencyDirectivesTy > * > DepDirectives
Accessor to the directive tokens that's atomic to avoid data races.
std::unique_ptr< llvm::MemoryBuffer > Original
Owning storage for the original contents.
SmallVector< dependency_directives_scan::Token, 10 > DepDirectiveTokens
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4