[clangd] Re-land "support outgoing calls in call hierarchy" (#117673)
[llvm-project.git] / llvm / unittests / ExecutionEngine / Orc / SymbolStringPoolTest.cpp
blobcd1cecd3244d63823aa4f69ec13ac5ad497c7363
1 //===----- SymbolStringPoolTest.cpp - Unit tests for SymbolStringPool -----===//
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 //===----------------------------------------------------------------------===//
9 #include "llvm/ExecutionEngine/Orc/SymbolStringPool.h"
10 #include "llvm/ExecutionEngine/Orc/DebugUtils.h"
11 #include "gtest/gtest.h"
13 using namespace llvm;
14 using namespace llvm::orc;
16 namespace llvm::orc {
18 class SymbolStringPoolTest : public testing::Test {
19 public:
20 size_t getRefCount(const SymbolStringPtrBase &S) const {
21 return SP.getRefCount(S);
24 protected:
25 SymbolStringPool SP;
27 } // namespace llvm::orc
29 namespace {
31 TEST_F(SymbolStringPoolTest, UniquingAndComparisons) {
32 auto P1 = SP.intern("hello");
34 std::string S("hel");
35 S += "lo";
36 auto P2 = SP.intern(S);
38 auto P3 = SP.intern("goodbye");
40 EXPECT_EQ(P1, P2) << "Failed to unique entries";
41 EXPECT_NE(P1, P3) << "Unequal pooled symbol strings comparing equal";
43 // We want to test that less-than comparison of SymbolStringPtrs compiles,
44 // however we can't test the actual result as this is a pointer comparison and
45 // SymbolStringPtr doesn't expose the underlying address of the string.
46 (void)(P1 < P3);
49 TEST_F(SymbolStringPoolTest, Dereference) {
50 auto Foo = SP.intern("foo");
51 EXPECT_EQ(*Foo, "foo") << "Equality on dereferenced string failed";
54 TEST_F(SymbolStringPoolTest, ClearDeadEntries) {
56 auto P1 = SP.intern("s1");
57 SP.clearDeadEntries();
58 EXPECT_FALSE(SP.empty()) << "\"s1\" entry in pool should still be retained";
60 SP.clearDeadEntries();
61 EXPECT_TRUE(SP.empty()) << "pool should be empty";
64 TEST_F(SymbolStringPoolTest, DebugDump) {
65 auto A1 = SP.intern("a");
66 auto A2 = A1;
67 auto B = SP.intern("b");
69 std::string DumpString;
70 raw_string_ostream(DumpString) << SP;
72 EXPECT_EQ(DumpString, "a: 2\nb: 1\n");
75 TEST_F(SymbolStringPoolTest, NonOwningPointerBasics) {
76 auto A = SP.intern("a");
77 auto B = SP.intern("b");
79 NonOwningSymbolStringPtr ANP1(A); // Constuct from SymbolStringPtr.
80 NonOwningSymbolStringPtr ANP2(ANP1); // Copy-construct.
81 NonOwningSymbolStringPtr BNP(B);
83 // Equality comparisons.
84 EXPECT_EQ(A, ANP1);
85 EXPECT_EQ(ANP1, ANP2);
86 EXPECT_NE(ANP1, BNP);
88 EXPECT_EQ(*ANP1, "a"); // Dereference.
90 // Assignment.
91 ANP2 = ANP1;
92 ANP2 = A;
94 SymbolStringPtr S(ANP1); // Construct SymbolStringPtr from non-owning.
95 EXPECT_EQ(S, A);
97 DenseMap<SymbolStringPtr, int> M;
98 M[A] = 42;
99 EXPECT_EQ(M.find_as(ANP1)->second, 42);
100 EXPECT_EQ(M.find_as(BNP), M.end());
103 TEST_F(SymbolStringPoolTest, NonOwningPointerRefCounts) {
104 // Check that creating and destroying non-owning pointers doesn't affect
105 // ref-counts.
106 auto A = SP.intern("a");
107 EXPECT_EQ(getRefCount(A), 1U);
109 NonOwningSymbolStringPtr ANP(A);
110 EXPECT_EQ(getRefCount(ANP), 1U)
111 << "Construction of NonOwningSymbolStringPtr from SymbolStringPtr "
112 "changed ref-count";
115 NonOwningSymbolStringPtr ANP2(ANP);
116 EXPECT_EQ(getRefCount(ANP2), 1U)
117 << "Copy-construction of NonOwningSymbolStringPtr changed ref-count";
120 EXPECT_EQ(getRefCount(ANP), 1U)
121 << "Destruction of NonOwningSymbolStringPtr changed ref-count";
124 NonOwningSymbolStringPtr ANP2;
125 ANP2 = ANP;
126 EXPECT_EQ(getRefCount(ANP2), 1U)
127 << "Copy-assignment of NonOwningSymbolStringPtr changed ref-count";
131 NonOwningSymbolStringPtr ANP2(ANP);
132 NonOwningSymbolStringPtr ANP3(std::move(ANP2));
133 EXPECT_EQ(getRefCount(ANP3), 1U)
134 << "Move-construction of NonOwningSymbolStringPtr changed ref-count";
138 NonOwningSymbolStringPtr ANP2(ANP);
139 NonOwningSymbolStringPtr ANP3;
140 ANP3 = std::move(ANP2);
141 EXPECT_EQ(getRefCount(ANP3), 1U)
142 << "Copy-assignment of NonOwningSymbolStringPtr changed ref-count";
146 TEST_F(SymbolStringPoolTest, SymbolStringPoolEntryUnsafe) {
148 auto A = SP.intern("a");
149 EXPECT_EQ(getRefCount(A), 1U);
152 // Try creating an unsafe pool entry ref from the given SymbolStringPtr.
153 // This should not affect the ref-count.
154 auto AUnsafe = SymbolStringPoolEntryUnsafe::from(A);
155 EXPECT_EQ(getRefCount(A), 1U);
157 // Create a new SymbolStringPtr from the unsafe ref. This should increment
158 // the ref-count.
159 auto ACopy = AUnsafe.copyToSymbolStringPtr();
160 EXPECT_EQ(getRefCount(A), 2U);
164 // Create a copy of the original string. Move it into an unsafe ref, and
165 // then move it back. None of these operations should affect the ref-count.
166 auto ACopy = A;
167 EXPECT_EQ(getRefCount(A), 2U);
168 auto AUnsafe = SymbolStringPoolEntryUnsafe::take(std::move(ACopy));
169 EXPECT_EQ(getRefCount(A), 2U);
170 ACopy = AUnsafe.moveToSymbolStringPtr();
171 EXPECT_EQ(getRefCount(A), 2U);
174 // Test manual retain / release.
175 auto AUnsafe = SymbolStringPoolEntryUnsafe::from(A);
176 EXPECT_EQ(getRefCount(A), 1U);
177 AUnsafe.retain();
178 EXPECT_EQ(getRefCount(A), 2U);
179 AUnsafe.release();
180 EXPECT_EQ(getRefCount(A), 1U);
183 } // namespace