aboutsummaryrefslogtreecommitdiffhomepage
path: root/lib/Core
diff options
context:
space:
mode:
authorJulian Büning <julian.buening@rwth-aachen.de>2020-02-09 20:14:35 +0100
committerMartinNowack <2443641+MartinNowack@users.noreply.github.com>2020-06-25 16:30:10 +0100
commit248be605d192abf425eae6d14fc206e507b48380 (patch)
tree6cd8cf95dacf2e41ec78af28b2a673ae9758fbf0 /lib/Core
parent21d2134dbd4ffe9f4252becf575969b78a43e1b8 (diff)
downloadklee-248be605d192abf425eae6d14fc206e507b48380.tar.gz
fix Executor: initializeGlobalAliases
Diffstat (limited to 'lib/Core')
-rw-r--r--lib/Core/Executor.cpp53
-rw-r--r--lib/Core/Executor.h1
2 files changed, 39 insertions, 15 deletions
diff --git a/lib/Core/Executor.cpp b/lib/Core/Executor.cpp
index 9209be8a..3272201a 100644
--- a/lib/Core/Executor.cpp
+++ b/lib/Core/Executor.cpp
@@ -755,23 +755,46 @@ void Executor::allocateGlobalObjects(ExecutionState &state) {
}
}
-void Executor::initializeGlobalAliases() {
- const Module *m = kmodule->module.get();
-
- // link aliases to their definitions (if bound)
- for (auto i = m->alias_begin(), ie = m->alias_end(); i != ie; ++i) {
- // Map the alias to its aliasee's address. This works because we have
- // addresses for everything, even undefined functions.
-
- // Alias may refer to other alias, not necessarily known at this point.
- // Thus, resolve to real alias directly.
- const GlobalAlias *alias = &*i;
- while (const auto *ga = dyn_cast<GlobalAlias>(alias->getAliasee())) {
- assert(ga != alias && "alias pointing to itself");
- alias = ga;
+void Executor::initializeGlobalAlias(const llvm::Constant *c) {
+ // aliasee may either be a global value or constant expression
+ const auto *ga = dyn_cast<GlobalAlias>(c);
+ if (ga) {
+ if (globalAddresses.count(ga)) {
+ // already resolved by previous invocation
+ return;
}
+ const llvm::Constant *aliasee = ga->getAliasee();
+ if (const auto *gv = dyn_cast<GlobalValue>(aliasee)) {
+ // aliasee is global value
+ auto it = globalAddresses.find(gv);
+ // uninitialized only if aliasee is another global alias
+ if (it != globalAddresses.end()) {
+ globalAddresses.emplace(ga, it->second);
+ return;
+ }
+ }
+ }
+
+ // resolve aliases in all sub-expressions
+#if LLVM_VERSION_CODE >= LLVM_VERSION(4, 0)
+ for (const auto *op : c->operand_values()) {
+#else
+ for (auto &it : c->operands()) {
+ const auto *op = &*it;
+#endif
+ initializeGlobalAlias(cast<Constant>(op));
+ }
- globalAddresses.insert(std::make_pair(&*i, evalConstant(alias->getAliasee())));
+ if (ga) {
+ // aliasee is constant expression (or global alias)
+ globalAddresses.emplace(ga, evalConstant(ga->getAliasee()));
+ }
+}
+
+void Executor::initializeGlobalAliases() {
+ const Module *m = kmodule->module.get();
+ for (const GlobalAlias &a : m->aliases()) {
+ initializeGlobalAlias(&a);
}
}
diff --git a/lib/Core/Executor.h b/lib/Core/Executor.h
index 61664193..7acbc60f 100644
--- a/lib/Core/Executor.h
+++ b/lib/Core/Executor.h
@@ -226,6 +226,7 @@ private:
MemoryObject *addExternalObject(ExecutionState &state, void *addr,
unsigned size, bool isReadOnly);
+ void initializeGlobalAlias(const llvm::Constant *c);
void initializeGlobalObject(ExecutionState &state, ObjectState *os,
const llvm::Constant *c,
unsigned offset);