diff options
-rw-r--r-- | lib/Core/Executor.cpp | 6 | ||||
-rw-r--r-- | lib/Core/MemoryManager.cpp | 17 | ||||
-rw-r--r-- | lib/Core/MemoryManager.h | 3 | ||||
-rw-r--r-- | test/Feature/32BitAlloc.c | 15 |
4 files changed, 37 insertions, 4 deletions
diff --git a/lib/Core/Executor.cpp b/lib/Core/Executor.cpp index 49e526f5..29e6486f 100644 --- a/lib/Core/Executor.cpp +++ b/lib/Core/Executor.cpp @@ -276,6 +276,7 @@ Executor::Executor(const InterpreterOptions &opts, interpreterHandler(ih), searcher(0), externalDispatcher(new ExternalDispatcher()), + memory(0), // Can't be initialised until we know the pointer size statsTracker(0), pathWriter(0), symPathWriter(0), @@ -337,7 +338,6 @@ Executor::Executor(const InterpreterOptions &opts, this->solver = new TimingSolver(solver, EqualitySubstitution); - memory = new MemoryManager(); } @@ -355,7 +355,7 @@ const Module *Executor::setModule(llvm::Module *module, #endif Context::initialize(TD->isLittleEndian(), (Expr::Width) TD->getPointerSizeInBits()); - + memory = new MemoryManager(TD->getPointerSizeInBits()); specialFunctionHandler = new SpecialFunctionHandler(*this); specialFunctionHandler->prepare(); @@ -3415,7 +3415,7 @@ void Executor::runFunctionAsMain(Function *f, // hack to clear memory objects delete memory; - memory = new MemoryManager(); + memory = new MemoryManager(Context::get().getPointerWidth()); globalObjects.clear(); globalAddresses.clear(); diff --git a/lib/Core/MemoryManager.cpp b/lib/Core/MemoryManager.cpp index a1198007..0caa504d 100644 --- a/lib/Core/MemoryManager.cpp +++ b/lib/Core/MemoryManager.cpp @@ -12,16 +12,33 @@ #include "CoreStats.h" #include "Memory.h" #include "MemoryManager.h" +#include "Context.h" #include "klee/ExecutionState.h" #include "klee/Expr.h" #include "klee/Solver.h" #include "llvm/Support/CommandLine.h" +#include "malloc.h" using namespace klee; /***/ +MemoryManager::MemoryManager(size_t pointerBitWidth) : + pointerBitWidth(pointerBitWidth) { + if (pointerBitWidth < 64) { + // FIXME: KLEE should implement it's own memory manager for + // the program we are executing and not invoke malloc so + // we have finer control over the addresses we use. + // HACK: + // Try make sure malloc() gives us back + // addresses that fit in a 32-bit integer when running + // 32-bit code. + // This works by preventing malloc() from using mmap() + // so it uses sbrk() instead... gross + mallopt(M_MMAP_MAX, 0); + } +} MemoryManager::~MemoryManager() { while (!objects.empty()) { diff --git a/lib/Core/MemoryManager.h b/lib/Core/MemoryManager.h index f398db62..d87ebe41 100644 --- a/lib/Core/MemoryManager.h +++ b/lib/Core/MemoryManager.h @@ -24,9 +24,10 @@ namespace klee { private: typedef std::set<MemoryObject*> objects_ty; objects_ty objects; + size_t pointerBitWidth; public: - MemoryManager() {} + MemoryManager(size_t pointerBitWidth); ~MemoryManager(); MemoryObject *allocate(uint64_t size, bool isLocal, bool isGlobal, diff --git a/test/Feature/32BitAlloc.c b/test/Feature/32BitAlloc.c new file mode 100644 index 00000000..311dc239 --- /dev/null +++ b/test/Feature/32BitAlloc.c @@ -0,0 +1,15 @@ +// RUN: %llvmgcc %s -emit-llvm -m32 -O0 -c -o %t1.bc +// RUN: rm -rf %t.klee-out +// RUN: %klee --output-dir=%t.klee-out %t1.bc + +// This simply tests that allocation works when +// running 32-bit code + +// FIXME: This test only needs to run on x86_64 +int main() { + int a[100000]; + for (int i=0; i < 5000; ++i) { + a[i] = i; + } + return 0; +} |