about summary refs log tree commit diff homepage
path: root/include
diff options
context:
space:
mode:
Diffstat (limited to 'include')
-rw-r--r--include/klee/Module/KCallable.h71
-rw-r--r--include/klee/Module/KModule.h16
2 files changed, 84 insertions, 3 deletions
diff --git a/include/klee/Module/KCallable.h b/include/klee/Module/KCallable.h
new file mode 100644
index 00000000..bf8b17ea
--- /dev/null
+++ b/include/klee/Module/KCallable.h
@@ -0,0 +1,71 @@
+//===-- KCallable.h ---------------------------------------------*- C++ -*-===//
+//
+//                     The KLEE Symbolic Virtual Machine
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+
+#ifndef KLEE_KCALLABLE_H
+#define KLEE_KCALLABLE_H
+
+#include <string>
+
+#include "llvm/ADT/Twine.h"
+#include "llvm/IR/Function.h"
+#include "llvm/IR/InlineAsm.h"
+#include "llvm/IR/LLVMContext.h"
+
+namespace klee {
+/// Wrapper for callable objects passed in callExternalFunction
+class KCallable {
+public:
+  enum CallableKind { CK_Function, CK_InlineAsm };
+
+private:
+  const CallableKind Kind;
+
+public:
+  KCallable(CallableKind Kind) : Kind(Kind) {}
+
+  CallableKind getKind() const { return Kind; }
+
+  virtual llvm::StringRef getName() const = 0;
+  virtual llvm::PointerType *getType() const = 0;
+  virtual llvm::Value *getValue() = 0;
+
+  virtual ~KCallable() = default;
+};
+
+class KInlineAsm : public KCallable {
+private:
+  static unsigned getFreshAsmId() {
+    static unsigned globalId = 0;
+    return globalId++;
+  }
+
+  llvm::InlineAsm *value;
+  std::string name;
+
+public:
+  KInlineAsm(llvm::InlineAsm *value)
+      : KCallable(CK_InlineAsm), value(value),
+        name("__asm__" + llvm::Twine(getFreshAsmId()).str()) {}
+
+  llvm::StringRef getName() const override { return name; }
+
+  llvm::PointerType *getType() const override { return value->getType(); }
+
+  llvm::Value *getValue() override { return value; }
+
+  static bool classof(const KCallable *callable) {
+    return callable->getKind() == CK_InlineAsm;
+  }
+
+  llvm::InlineAsm *getInlineAsm() { return value; }
+};
+
+} // namespace klee
+
+#endif /* KLEE_KCALLABLE_H */
diff --git a/include/klee/Module/KModule.h b/include/klee/Module/KModule.h
index 9c24cb31..71fe8a0a 100644
--- a/include/klee/Module/KModule.h
+++ b/include/klee/Module/KModule.h
@@ -12,6 +12,7 @@
 
 #include "klee/Config/Version.h"
 #include "klee/Core/Interpreter.h"
+#include "klee/Module/KCallable.h"
 
 #include "llvm/ADT/ArrayRef.h"
 
@@ -39,7 +40,7 @@ namespace klee {
   class KModule;
   template<class T> class ref;
 
-  struct KFunction {
+  struct KFunction : public KCallable {
     llvm::Function *function;
 
     unsigned numArgs, numRegisters;
@@ -53,14 +54,23 @@ namespace klee {
     /// "coverable" for statistics and search heuristics.
     bool trackCoverage;
 
-  public:
-    explicit KFunction(llvm::Function*, KModule *);
+    explicit KFunction(llvm::Function*, KModule*);
     KFunction(const KFunction &) = delete;
     KFunction &operator=(const KFunction &) = delete;
 
     ~KFunction();
 
     unsigned getArgRegister(unsigned index) { return index; }
+
+    llvm::StringRef getName() const override { return function->getName(); }
+
+    llvm::PointerType *getType() const override { return function->getType(); }
+
+    llvm::Value *getValue() override { return function; }
+
+    static bool classof(const KCallable *callable) {
+      return callable->getKind() == CK_Function;
+    }
   };