Skip to content

Commit 88e42a2

Browse files
authored
Ref-counted ModuleSlotTracker (#614)
* Make the ModuleSlotTracker ref-counted * minor
1 parent 710ef66 commit 88e42a2

3 files changed

Lines changed: 52 additions & 10 deletions

File tree

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ bin/*
66
# build directories for cmake
77
build/
88
build_*/
9+
build-*/
910

1011
# LLVM project
1112
llvm-project/*

lib/PhasarLLVM/Utils/LLVMShorthands.cpp

Lines changed: 32 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -44,6 +44,7 @@
4444
#include <charconv>
4545
#include <cstdlib>
4646
#include <memory>
47+
#include <mutex>
4748
#include <optional>
4849
#include <system_error>
4950

@@ -504,32 +505,44 @@ llvm::StringRef getVarAnnotationIntrinsicName(const llvm::CallInst *CallInst) {
504505
return Data->getAsCString();
505506
}
506507

508+
struct PhasarModuleSlotTrackerWrapper {
509+
PhasarModuleSlotTrackerWrapper(const llvm::Module *M) : MST(M) {}
510+
511+
llvm::ModuleSlotTracker MST;
512+
size_t RefCount = 0;
513+
};
514+
507515
static llvm::SmallDenseMap<const llvm::Module *,
508-
std::unique_ptr<llvm::ModuleSlotTracker>, 2>
516+
std::unique_ptr<PhasarModuleSlotTrackerWrapper>, 2>
509517
MToST{};
510518

519+
static std::mutex MSTMx;
520+
511521
llvm::ModuleSlotTracker &
512522
ModulesToSlotTracker::getSlotTrackerForModule(const llvm::Module *M) {
523+
std::lock_guard Lck(MSTMx);
524+
513525
auto &Ret = MToST[M];
514526
if (M == nullptr && Ret == nullptr) {
515-
Ret = std::make_unique<llvm::ModuleSlotTracker>(M);
527+
Ret = std::make_unique<PhasarModuleSlotTrackerWrapper>(M);
528+
Ret->RefCount++;
516529
}
517530
assert(Ret != nullptr && "no ModuleSlotTracker instance for module cached");
518-
return *Ret;
531+
return Ret->MST;
519532
}
520533

521534
void ModulesToSlotTracker::setMSTForModule(const llvm::Module *M) {
535+
std::lock_guard Lck(MSTMx);
536+
522537
auto [It, Inserted] = MToST.try_emplace(M, nullptr);
523-
if (!Inserted) {
524-
llvm::report_fatal_error(
525-
"Cannot register the same module twice in the ModulesToSlotTracker! "
526-
"Probably you have managed the same LLVM Module with multiple "
527-
"ProjectIRDB instances at the same time. Don't do that!");
538+
if (Inserted) {
539+
It->second = std::make_unique<PhasarModuleSlotTrackerWrapper>(M);
528540
}
529-
It->second = std::make_unique<llvm::ModuleSlotTracker>(M);
541+
It->second->RefCount++;
530542
}
531543

532544
void ModulesToSlotTracker::updateMSTForModule(const llvm::Module *Module) {
545+
std::lock_guard Lck(MSTMx);
533546
auto It = MToST.find(Module);
534547
if (It == MToST.end()) {
535548
llvm::report_fatal_error(
@@ -541,7 +554,16 @@ void ModulesToSlotTracker::updateMSTForModule(const llvm::Module *Module) {
541554
}
542555

543556
void ModulesToSlotTracker::deleteMSTForModule(const llvm::Module *M) {
544-
MToST.erase(M);
557+
std::lock_guard Lck(MSTMx);
558+
559+
auto It = MToST.find(M);
560+
if (It == MToST.end()) {
561+
return;
562+
}
563+
564+
if (--It->second->RefCount == 0) {
565+
MToST.erase(It);
566+
}
545567
}
546568

547569
} // namespace psr

unittests/Utils/LLVMShorthandsTest.cpp

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
#include "phasar/PhasarLLVM/DB/LLVMProjectIRDB.h"
55
#include "phasar/Utils/Utilities.h"
66

7+
#include "llvm/ADT/StringRef.h"
78
#include "llvm/IR/Function.h"
89
#include "llvm/IR/Instructions.h"
910

@@ -43,6 +44,24 @@ TEST(LLVMGetterTest, HandlesLLVMTermInstruction) {
4344
ASSERT_EQ(getNthTermInstruction(F, 5), nullptr);
4445
}
4546

47+
TEST(SlotTrackerTest, HandleTwoReferences) {
48+
LLVMProjectIRDB IRDB(unittest::PathToLLTestFiles +
49+
"control_flow/global_stmt_cpp.ll");
50+
51+
const auto *F = IRDB.getFunctionDefinition("main");
52+
53+
ASSERT_NE(F, nullptr);
54+
const auto *Inst = getNthInstruction(F, 6);
55+
llvm::StringRef InstStr = "%0 = load i32, i32* @i, align 4 | ID: 6";
56+
{
57+
LLVMProjectIRDB IRDB2(IRDB.getModule());
58+
59+
EXPECT_EQ(llvmIRToStableString(Inst), InstStr);
60+
}
61+
62+
EXPECT_EQ(llvmIRToStableString(Inst), InstStr);
63+
}
64+
4665
int main(int Argc, char **Argv) {
4766
::testing::InitGoogleTest(&Argc, Argv);
4867
return RUN_ALL_TESTS();

0 commit comments

Comments
 (0)