forked from llvm/llvm-project
-
Notifications
You must be signed in to change notification settings - Fork 102
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
FileManager: Improve the FileEntryRef API and customize its OptionalS…
…torage Make a few changes to the `FileEntryRef` API in preparation for propagating it enough to remove `FileEntry::getName()`. - Allow `FileEntryRef` to degrade implicitly to `const FileEntry*`. This allows functions currently returning `const FileEntry *` to be updated to return `FileEntryRef` without requiring all callers to be updated in the same patch. This helps avoid both (a) massive patches where many fields and locals are updated simultaneously and (b) noisy incremental patches where the first patch adds `getFileEntry()` at call sites and the second patch removes it. (Once `FileEntryRef` is everywhere, we should remove this API.) - Change `operator==` to compare the underlying `FileEntry*`, ignoring any difference in the spelling of the filename. There were 0 users of the existing function because it's not useful. In case comparing the exact named reference becomes important, add/test `isSameRef`. - Add `==` comparisons between `FileEntryRef` and `const FileEntry *` (compares the `FileEntry*`). - Customize `OptionalStorage<FileEntryRef>` to be pointer-sized. Add a private constructor that initializes with `nullptr` and specialize `OptionalStorage` to use it. This unblocks updating fields in size-sensitive data structures that currently use `const FileEntry *`. - Add `OptionalFileEntryRefDegradesToFileEntryPtr`, a wrapper around `Optional<FileEntryRef>` that degrades to `const FileEntry*`. This facilitates future incremental patches, like the same operator on `FileEntryRef`. (Once `FileEntryRef` is everywhere, we should remove this class.) - Remove the unncessary `const` from the by-value return of `FileEntryRef::getName`. - Delete the unused function `FileEntry::isOpenForTests`. Note that there are still `FileEntry` APIs that aren't wrapped and I plan to deal with these separately / incrementally, as they are needed. Differential Revision: https://reviews.llvm.org/D89834
- Loading branch information
1 parent
2177e45
commit 84e8257
Showing
4 changed files
with
368 additions
and
15 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,104 @@ | ||
//===- unittests/Basic/FileEntryTest.cpp - Test FileEntry/FileEntryRef ----===// | ||
// | ||
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. | ||
// See https://llvm.org/LICENSE.txt for license information. | ||
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception | ||
// | ||
//===----------------------------------------------------------------------===// | ||
|
||
#include "clang/Basic/FileEntry.h" | ||
#include "llvm/ADT/StringMap.h" | ||
#include "gtest/gtest.h" | ||
|
||
using namespace llvm; | ||
using namespace clang; | ||
|
||
namespace { | ||
|
||
using MapEntry = FileEntryRef::MapEntry; | ||
using MapValue = FileEntryRef::MapValue; | ||
using MapType = StringMap<llvm::ErrorOr<MapValue>>; | ||
|
||
FileEntryRef addRef(MapType &M, StringRef Name, FileEntry &E) { | ||
return FileEntryRef(*M.insert({Name, MapValue(E)}).first); | ||
} | ||
|
||
TEST(FileEntryTest, FileEntryRef) { | ||
MapType Refs; | ||
FileEntry E1, E2; | ||
FileEntryRef R1 = addRef(Refs, "1", E1); | ||
FileEntryRef R2 = addRef(Refs, "2", E2); | ||
FileEntryRef R1Also = addRef(Refs, "1-also", E1); | ||
|
||
EXPECT_EQ("1", R1.getName()); | ||
EXPECT_EQ("2", R2.getName()); | ||
EXPECT_EQ("1-also", R1Also.getName()); | ||
|
||
EXPECT_EQ(&E1, &R1.getFileEntry()); | ||
EXPECT_EQ(&E2, &R2.getFileEntry()); | ||
EXPECT_EQ(&E1, &R1Also.getFileEntry()); | ||
|
||
const FileEntry *CE1 = R1; | ||
EXPECT_EQ(CE1, &E1); | ||
} | ||
|
||
TEST(FileEntryTest, OptionalFileEntryRefDegradesToFileEntryPtr) { | ||
MapType Refs; | ||
FileEntry E1, E2; | ||
OptionalFileEntryRefDegradesToFileEntryPtr M0; | ||
OptionalFileEntryRefDegradesToFileEntryPtr M1 = addRef(Refs, "1", E1); | ||
OptionalFileEntryRefDegradesToFileEntryPtr M2 = addRef(Refs, "2", E2); | ||
OptionalFileEntryRefDegradesToFileEntryPtr M0Also = None; | ||
OptionalFileEntryRefDegradesToFileEntryPtr M1Also = | ||
addRef(Refs, "1-also", E1); | ||
|
||
EXPECT_EQ(M0, M0Also); | ||
EXPECT_EQ(StringRef("1"), M1->getName()); | ||
EXPECT_EQ(StringRef("2"), M2->getName()); | ||
EXPECT_EQ(StringRef("1-also"), M1Also->getName()); | ||
|
||
EXPECT_EQ(&E1, &M1->getFileEntry()); | ||
EXPECT_EQ(&E2, &M2->getFileEntry()); | ||
EXPECT_EQ(&E1, &M1Also->getFileEntry()); | ||
|
||
const FileEntry *CE1 = M1; | ||
EXPECT_EQ(CE1, &E1); | ||
} | ||
|
||
TEST(FileEntryTest, equals) { | ||
MapType Refs; | ||
FileEntry E1, E2; | ||
FileEntryRef R1 = addRef(Refs, "1", E1); | ||
FileEntryRef R2 = addRef(Refs, "2", E2); | ||
FileEntryRef R1Also = addRef(Refs, "1-also", E1); | ||
|
||
EXPECT_EQ(R1, &E1); | ||
EXPECT_EQ(&E1, R1); | ||
EXPECT_EQ(R1, R1Also); | ||
EXPECT_NE(R1, &E2); | ||
EXPECT_NE(&E2, R1); | ||
EXPECT_NE(R1, R2); | ||
|
||
OptionalFileEntryRefDegradesToFileEntryPtr M0; | ||
OptionalFileEntryRefDegradesToFileEntryPtr M1 = R1; | ||
|
||
EXPECT_EQ(M1, &E1); | ||
EXPECT_EQ(&E1, M1); | ||
EXPECT_NE(M1, &E2); | ||
EXPECT_NE(&E2, M1); | ||
} | ||
|
||
TEST(FileEntryTest, isSameRef) { | ||
MapType Refs; | ||
FileEntry E1, E2; | ||
FileEntryRef R1 = addRef(Refs, "1", E1); | ||
FileEntryRef R2 = addRef(Refs, "2", E2); | ||
FileEntryRef R1Also = addRef(Refs, "1-also", E1); | ||
|
||
EXPECT_TRUE(R1.isSameRef(FileEntryRef(R1))); | ||
EXPECT_TRUE(R1.isSameRef(FileEntryRef(R1.getMapEntry()))); | ||
EXPECT_FALSE(R1.isSameRef(R2)); | ||
EXPECT_FALSE(R1.isSameRef(R1Also)); | ||
} | ||
|
||
} // end namespace |
Oops, something went wrong.