about summary refs log tree commit diff homepage
path: root/lib/Solver
diff options
context:
space:
mode:
authorDaniel Schemmel <daniel@schemmel.net>2023-03-24 15:05:43 +0000
committerCristian Cadar <c.cadar@imperial.ac.uk>2023-04-21 13:07:31 +0100
commitac0fa15ab0679fe1b5067b07647b0701ae3bc347 (patch)
treef2294eb5f0795ee9ce0f92d527242b7b7a507e79 /lib/Solver
parente9d77be6c688836d68a2be5f3f0a02e63f392bb8 (diff)
downloadklee-ac0fa15ab0679fe1b5067b07647b0701ae3bc347.tar.gz
use unique_ptr all throughout the solver chain
Diffstat (limited to 'lib/Solver')
-rw-r--r--lib/Solver/AssignmentValidatingSolver.cpp10
-rw-r--r--lib/Solver/CachingSolver.cpp9
-rw-r--r--lib/Solver/CexCachingSolver.cpp10
-rw-r--r--lib/Solver/ConstructSolverChain.cpp48
-rw-r--r--lib/Solver/CoreSolver.cpp7
-rw-r--r--lib/Solver/DummySolver.cpp6
-rw-r--r--lib/Solver/FastCexSolver.cpp7
-rw-r--r--lib/Solver/IncompleteSolver.cpp10
-rw-r--r--lib/Solver/IndependentSolver.cpp9
-rw-r--r--lib/Solver/KQueryLoggingSolver.cpp21
-rw-r--r--lib/Solver/MetaSMTSolver.cpp34
-rw-r--r--lib/Solver/MetaSMTSolver.h4
-rw-r--r--lib/Solver/QueryLoggingSolver.cpp13
-rw-r--r--lib/Solver/QueryLoggingSolver.h5
-rw-r--r--lib/Solver/SMTLIBLoggingSolver.cpp35
-rw-r--r--lib/Solver/STPSolver.cpp2
-rw-r--r--lib/Solver/Solver.cpp4
-rw-r--r--lib/Solver/ValidatingSolver.cpp13
-rw-r--r--lib/Solver/Z3Solver.cpp2
19 files changed, 150 insertions, 99 deletions
diff --git a/lib/Solver/AssignmentValidatingSolver.cpp b/lib/Solver/AssignmentValidatingSolver.cpp
index f18f43a8..d90cf6b2 100644
--- a/lib/Solver/AssignmentValidatingSolver.cpp
+++ b/lib/Solver/AssignmentValidatingSolver.cpp
@@ -13,6 +13,7 @@
 #include "klee/Solver/SolverImpl.h"
 
 #include <memory>
+#include <utility>
 #include <vector>
 
 namespace klee {
@@ -23,7 +24,8 @@ private:
   void dumpAssignmentQuery(const Query &query, const Assignment &assignment);
 
 public:
-  AssignmentValidatingSolver(Solver *_solver) : solver(_solver) {}
+  AssignmentValidatingSolver(std::unique_ptr<Solver> solver)
+      : solver(std::move(solver)) {}
 
   bool computeValidity(const Query &, Solver::Validity &result);
   bool computeTruth(const Query &, bool &isValid);
@@ -148,7 +150,9 @@ void AssignmentValidatingSolver::setCoreSolverTimeout(time::Span timeout) {
   return solver->impl->setCoreSolverTimeout(timeout);
 }
 
-Solver *createAssignmentValidatingSolver(Solver *s) {
-  return new Solver(new AssignmentValidatingSolver(s));
+std::unique_ptr<Solver>
+createAssignmentValidatingSolver(std::unique_ptr<Solver> s) {
+  return std::make_unique<Solver>(
+      std::make_unique<AssignmentValidatingSolver>(std::move(s)));
 }
 }
diff --git a/lib/Solver/CachingSolver.cpp b/lib/Solver/CachingSolver.cpp
index 5d85062d..751e81c1 100644
--- a/lib/Solver/CachingSolver.cpp
+++ b/lib/Solver/CachingSolver.cpp
@@ -18,6 +18,7 @@
 
 #include <memory>
 #include <unordered_map>
+#include <utility>
 
 using namespace klee;
 
@@ -67,7 +68,7 @@ private:
   cache_map cache;
 
 public:
-  CachingSolver(Solver *s) : solver(s) {}
+  CachingSolver(std::unique_ptr<Solver> solver) : solver(std::move(solver)) {}
 
   bool computeValidity(const Query&, Solver::Validity &result);
   bool computeTruth(const Query&, bool &isValid);
@@ -255,6 +256,8 @@ void CachingSolver::setCoreSolverTimeout(time::Span timeout) {
 
 ///
 
-Solver *klee::createCachingSolver(Solver *_solver) {
-  return new Solver(new CachingSolver(_solver));
+std::unique_ptr<Solver>
+klee::createCachingSolver(std::unique_ptr<Solver> solver) {
+  return std::make_unique<Solver>(
+      std::make_unique<CachingSolver>(std::move(solver)));
 }
diff --git a/lib/Solver/CexCachingSolver.cpp b/lib/Solver/CexCachingSolver.cpp
index 28996a6a..dbbd3516 100644
--- a/lib/Solver/CexCachingSolver.cpp
+++ b/lib/Solver/CexCachingSolver.cpp
@@ -24,6 +24,7 @@
 #include "llvm/Support/CommandLine.h"
 
 #include <memory>
+#include <utility>
 
 using namespace klee;
 using namespace llvm;
@@ -87,7 +88,8 @@ class CexCachingSolver : public SolverImpl {
   bool getAssignment(const Query& query, Assignment *&result);
   
 public:
-  CexCachingSolver(Solver *_solver) : solver(_solver) {}
+  CexCachingSolver(std::unique_ptr<Solver> solver)
+      : solver(std::move(solver)) {}
   ~CexCachingSolver();
   
   bool computeTruth(const Query&, bool &isValid);
@@ -384,6 +386,8 @@ void CexCachingSolver::setCoreSolverTimeout(time::Span timeout) {
 
 ///
 
-Solver *klee::createCexCachingSolver(Solver *_solver) {
-  return new Solver(new CexCachingSolver(_solver));
+std::unique_ptr<Solver>
+klee::createCexCachingSolver(std::unique_ptr<Solver> solver) {
+  return std::make_unique<Solver>(
+      std::make_unique<CexCachingSolver>(std::move(solver)));
 }
diff --git a/lib/Solver/ConstructSolverChain.cpp b/lib/Solver/ConstructSolverChain.cpp
index 999edda4..9109fe1d 100644
--- a/lib/Solver/ConstructSolverChain.cpp
+++ b/lib/Solver/ConstructSolverChain.cpp
@@ -18,62 +18,72 @@
 
 #include "llvm/Support/raw_ostream.h"
 
+#include <memory>
+#include <utility>
 
 namespace klee {
-Solver *constructSolverChain(Solver *coreSolver,
-                             std::string querySMT2LogPath,
-                             std::string baseSolverQuerySMT2LogPath,
-                             std::string queryKQueryLogPath,
-                             std::string baseSolverQueryKQueryLogPath) {
-  Solver *solver = coreSolver;
+std::unique_ptr<Solver> constructSolverChain(
+    std::unique_ptr<Solver> coreSolver, std::string querySMT2LogPath,
+    std::string baseSolverQuerySMT2LogPath, std::string queryKQueryLogPath,
+    std::string baseSolverQueryKQueryLogPath) {
+  Solver *rawCoreSolver = coreSolver.get();
+  std::unique_ptr<Solver> solver = std::move(coreSolver);
   const time::Span minQueryTimeToLog(MinQueryTimeToLog);
 
   if (QueryLoggingOptions.isSet(SOLVER_KQUERY)) {
-    solver = createKQueryLoggingSolver(solver, baseSolverQueryKQueryLogPath, minQueryTimeToLog, LogTimedOutQueries);
+    solver = createKQueryLoggingSolver(std::move(solver),
+                                       baseSolverQueryKQueryLogPath,
+                                       minQueryTimeToLog, LogTimedOutQueries);
     klee_message("Logging queries that reach solver in .kquery format to %s\n",
                  baseSolverQueryKQueryLogPath.c_str());
   }
 
   if (QueryLoggingOptions.isSet(SOLVER_SMTLIB)) {
-    solver = createSMTLIBLoggingSolver(solver, baseSolverQuerySMT2LogPath, minQueryTimeToLog, LogTimedOutQueries);
+    solver =
+        createSMTLIBLoggingSolver(std::move(solver), baseSolverQuerySMT2LogPath,
+                                  minQueryTimeToLog, LogTimedOutQueries);
     klee_message("Logging queries that reach solver in .smt2 format to %s\n",
                  baseSolverQuerySMT2LogPath.c_str());
   }
 
   if (UseAssignmentValidatingSolver)
-    solver = createAssignmentValidatingSolver(solver);
+    solver = createAssignmentValidatingSolver(std::move(solver));
 
   if (UseFastCexSolver)
-    solver = createFastCexSolver(solver);
+    solver = createFastCexSolver(std::move(solver));
 
   if (UseCexCache)
-    solver = createCexCachingSolver(solver);
+    solver = createCexCachingSolver(std::move(solver));
 
   if (UseBranchCache)
-    solver = createCachingSolver(solver);
+    solver = createCachingSolver(std::move(solver));
 
   if (UseIndependentSolver)
-    solver = createIndependentSolver(solver);
+    solver = createIndependentSolver(std::move(solver));
 
   if (DebugValidateSolver)
-    solver = createValidatingSolver(solver, coreSolver);
+    solver = createValidatingSolver(std::move(solver), rawCoreSolver, false);
 
   if (QueryLoggingOptions.isSet(ALL_KQUERY)) {
-    solver = createKQueryLoggingSolver(solver, queryKQueryLogPath, minQueryTimeToLog, LogTimedOutQueries);
+    solver = createKQueryLoggingSolver(std::move(solver), queryKQueryLogPath,
+                                       minQueryTimeToLog, LogTimedOutQueries);
     klee_message("Logging all queries in .kquery format to %s\n",
                  queryKQueryLogPath.c_str());
   }
 
   if (QueryLoggingOptions.isSet(ALL_SMTLIB)) {
-    solver = createSMTLIBLoggingSolver(solver, querySMT2LogPath, minQueryTimeToLog, LogTimedOutQueries);
+    solver = createSMTLIBLoggingSolver(std::move(solver), querySMT2LogPath,
+                                       minQueryTimeToLog, LogTimedOutQueries);
     klee_message("Logging all queries in .smt2 format to %s\n",
                  querySMT2LogPath.c_str());
   }
   if (DebugCrossCheckCoreSolverWith != NO_SOLVER) {
-    Solver *oracleSolver = createCoreSolver(DebugCrossCheckCoreSolverWith);
-    solver = createValidatingSolver(solver, oracleSolver, true);
+    std::unique_ptr<Solver> oracleSolver =
+        createCoreSolver(DebugCrossCheckCoreSolverWith);
+    solver =
+        createValidatingSolver(std::move(solver), oracleSolver.release(), true);
   }
 
   return solver;
 }
-}
+} // namespace klee
diff --git a/lib/Solver/CoreSolver.cpp b/lib/Solver/CoreSolver.cpp
index fbf29747..abbccf5b 100644
--- a/lib/Solver/CoreSolver.cpp
+++ b/lib/Solver/CoreSolver.cpp
@@ -19,15 +19,16 @@
 #include "llvm/Support/raw_ostream.h"
 
 #include <string>
+#include <memory>
 
 namespace klee {
 
-Solver *createCoreSolver(CoreSolverType cst) {
+std::unique_ptr<Solver> createCoreSolver(CoreSolverType cst) {
   switch (cst) {
   case STP_SOLVER:
 #ifdef ENABLE_STP
     klee_message("Using STP solver backend");
-    return new STPSolver(UseForkedCoreSolver, CoreSolverOptimizeDivides);
+    return std::make_unique<STPSolver>(UseForkedCoreSolver, CoreSolverOptimizeDivides);
 #else
     klee_message("Not compiled with STP support");
     return NULL;
@@ -45,7 +46,7 @@ Solver *createCoreSolver(CoreSolverType cst) {
   case Z3_SOLVER:
 #ifdef ENABLE_Z3
     klee_message("Using Z3 solver backend");
-    return new Z3Solver();
+    return std::make_unique<Z3Solver>();
 #else
     klee_message("Not compiled with Z3 support");
     return NULL;
diff --git a/lib/Solver/DummySolver.cpp b/lib/Solver/DummySolver.cpp
index a845f901..1cf88d64 100644
--- a/lib/Solver/DummySolver.cpp
+++ b/lib/Solver/DummySolver.cpp
@@ -11,6 +11,8 @@
 #include "klee/Solver/SolverImpl.h"
 #include "klee/Solver/SolverStats.h"
 
+#include <memory>
+
 namespace klee {
 
 class DummySolverImpl : public SolverImpl {
@@ -59,5 +61,7 @@ SolverImpl::SolverRunStatus DummySolverImpl::getOperationStatusCode() {
   return SOLVER_RUN_STATUS_FAILURE;
 }
 
-Solver *createDummySolver() { return new Solver(new DummySolverImpl()); }
+std::unique_ptr<Solver> createDummySolver() {
+  return std::make_unique<Solver>(std::make_unique<DummySolverImpl>());
+}
 }
diff --git a/lib/Solver/FastCexSolver.cpp b/lib/Solver/FastCexSolver.cpp
index 34a44c3e..81fd6707 100644
--- a/lib/Solver/FastCexSolver.cpp
+++ b/lib/Solver/FastCexSolver.cpp
@@ -24,6 +24,7 @@
 #include <cassert>
 #include <map>
 #include <sstream>
+#include <utility>
 #include <vector>
 
 using namespace klee;
@@ -1141,7 +1142,7 @@ FastCexSolver::computeInitialValues(const Query& query,
   return true;
 }
 
-
-Solver *klee::createFastCexSolver(Solver *s) {
-  return new Solver(new StagedSolverImpl(new FastCexSolver(), s));
+std::unique_ptr<Solver> klee::createFastCexSolver(std::unique_ptr<Solver> s) {
+  return std::make_unique<Solver>(std::make_unique<StagedSolverImpl>(
+      std::make_unique<FastCexSolver>(), std::move(s)));
 }
diff --git a/lib/Solver/IncompleteSolver.cpp b/lib/Solver/IncompleteSolver.cpp
index a9035eda..7aef05c9 100644
--- a/lib/Solver/IncompleteSolver.cpp
+++ b/lib/Solver/IncompleteSolver.cpp
@@ -11,6 +11,8 @@
 
 #include "klee/Expr/Constraints.h"
 
+#include <utility>
+
 using namespace klee;
 using namespace llvm;
 
@@ -58,11 +60,9 @@ IncompleteSolver::computeValidity(const Query& query) {
 
 /***/
 
-StagedSolverImpl::StagedSolverImpl(IncompleteSolver *_primary, 
-                                   Solver *_secondary) 
-  : primary(_primary),
-    secondary(_secondary) {
-}
+StagedSolverImpl::StagedSolverImpl(std::unique_ptr<IncompleteSolver> primary,
+                                   std::unique_ptr<Solver> secondary)
+    : primary(std::move(primary)), secondary(std::move(secondary)) {}
 
 bool StagedSolverImpl::computeTruth(const Query& query, bool &isValid) {
   IncompleteSolver::PartialValidity trueResult = primary->computeTruth(query); 
diff --git a/lib/Solver/IndependentSolver.cpp b/lib/Solver/IndependentSolver.cpp
index 007bfdcb..c05fa6bb 100644
--- a/lib/Solver/IndependentSolver.cpp
+++ b/lib/Solver/IndependentSolver.cpp
@@ -393,7 +393,8 @@ private:
   std::unique_ptr<Solver> solver;
 
 public:
-  IndependentSolver(Solver *_solver) : solver(_solver) {}
+  IndependentSolver(std::unique_ptr<Solver> solver)
+      : solver(std::move(solver)) {}
 
   bool computeTruth(const Query&, bool &isValid);
   bool computeValidity(const Query&, Solver::Validity &result);
@@ -557,6 +558,8 @@ void IndependentSolver::setCoreSolverTimeout(time::Span timeout) {
   solver->impl->setCoreSolverTimeout(timeout);
 }
 
-Solver *klee::createIndependentSolver(Solver *s) {
-  return new Solver(new IndependentSolver(s));
+std::unique_ptr<Solver>
+klee::createIndependentSolver(std::unique_ptr<Solver> s) {
+  return std::make_unique<Solver>(
+      std::make_unique<IndependentSolver>(std::move(s)));
 }
diff --git a/lib/Solver/KQueryLoggingSolver.cpp b/lib/Solver/KQueryLoggingSolver.cpp
index fccdd615..4be24e9c 100644
--- a/lib/Solver/KQueryLoggingSolver.cpp
+++ b/lib/Solver/KQueryLoggingSolver.cpp
@@ -13,6 +13,8 @@
 #include "klee/Expr/ExprPPrinter.h"
 #include "klee/System/Time.h"
 
+#include <utility>
+
 using namespace klee;
 
 class KQueryLoggingSolver : public QueryLoggingSolver {
@@ -48,10 +50,11 @@ private :
     }
 
 public:
-    KQueryLoggingSolver(Solver *_solver, std::string path, time::Span queryTimeToLog, bool logTimedOut)
-    : QueryLoggingSolver(_solver, path, "#", queryTimeToLog, logTimedOut),
-    printer(ExprPPrinter::create(logBuffer)) {
-    }
+  KQueryLoggingSolver(std::unique_ptr<Solver> solver, std::string path,
+                      time::Span queryTimeToLog, bool logTimedOut)
+      : QueryLoggingSolver(std::move(solver), std::move(path), "#",
+                           queryTimeToLog, logTimedOut),
+        printer(ExprPPrinter::create(logBuffer)) {}
 
     virtual ~KQueryLoggingSolver() {
         delete printer;
@@ -60,8 +63,10 @@ public:
 
 ///
 
-Solver *klee::createKQueryLoggingSolver(Solver *_solver, std::string path,
-                                    time::Span minQueryTimeToLog, bool logTimedOut) {
-  return new Solver(new KQueryLoggingSolver(_solver, path, minQueryTimeToLog, logTimedOut));
+std::unique_ptr<Solver>
+klee::createKQueryLoggingSolver(std::unique_ptr<Solver> solver,
+                                std::string path, time::Span minQueryTimeToLog,
+                                bool logTimedOut) {
+  return std::make_unique<Solver>(std::make_unique<KQueryLoggingSolver>(
+      std::move(solver), std::move(path), minQueryTimeToLog, logTimedOut));
 }
-
diff --git a/lib/Solver/MetaSMTSolver.cpp b/lib/Solver/MetaSMTSolver.cpp
index 37c22f0e..c3c6dfaa 100644
--- a/lib/Solver/MetaSMTSolver.cpp
+++ b/lib/Solver/MetaSMTSolver.cpp
@@ -51,6 +51,8 @@
 #undef type_t
 #endif
 
+#include <memory>
+
 #include <errno.h>
 #include <signal.h>
 #include <sys/ipc.h>
@@ -85,7 +87,6 @@ private:
 public:
   MetaSMTSolverImpl(MetaSMTSolver<SolverContext> *solver, bool useForked,
                     bool optimizeDivides);
-  virtual ~MetaSMTSolverImpl();
 
   char *getConstraintLog(const Query &);
   void setCoreSolverTimeout(time::Span timeout) { _timeout = timeout; }
@@ -134,9 +135,6 @@ MetaSMTSolverImpl<SolverContext>::MetaSMTSolverImpl(
 }
 
 template <typename SolverContext>
-MetaSMTSolverImpl<SolverContext>::~MetaSMTSolverImpl() {}
-
-template <typename SolverContext>
 char *MetaSMTSolverImpl<SolverContext>::getConstraintLog(const Query &) {
   const char *msg = "Not supported";
   char *buf = new char[strlen(msg) + 1];
@@ -404,8 +402,8 @@ MetaSMTSolverImpl<SolverContext>::getOperationStatusCode() {
 template <typename SolverContext>
 MetaSMTSolver<SolverContext>::MetaSMTSolver(bool useForked,
                                             bool optimizeDivides)
-    : Solver(new MetaSMTSolverImpl<SolverContext>(this, useForked,
-                                                  optimizeDivides)) {}
+    : Solver(std::make_unique<MetaSMTSolverImpl<SolverContext>>(
+          this, useForked, optimizeDivides)) {}
 
 template <typename SolverContext>
 MetaSMTSolver<SolverContext>::~MetaSMTSolver() {}
@@ -420,45 +418,50 @@ void MetaSMTSolver<SolverContext>::setCoreSolverTimeout(time::Span timeout) {
   impl->setCoreSolverTimeout(timeout);
 }
 
-Solver *createMetaSMTSolver() {
+std::unique_ptr<Solver> createMetaSMTSolver() {
   using namespace metaSMT;
 
-  Solver *coreSolver = NULL;
+  std::unique_ptr<Solver> coreSolver;
   std::string backend;
   switch (MetaSMTBackend) {
 #ifdef METASMT_HAVE_STP
   case METASMT_BACKEND_STP:
     backend = "STP";
-    coreSolver = new MetaSMTSolver<DirectSolver_Context<solver::STP_Backend> >(
+    coreSolver = std::make_unique<
+        MetaSMTSolver<DirectSolver_Context<solver::STP_Backend>>>(
         UseForkedCoreSolver, CoreSolverOptimizeDivides);
     break;
 #endif
 #ifdef METASMT_HAVE_Z3
   case METASMT_BACKEND_Z3:
     backend = "Z3";
-    coreSolver = new MetaSMTSolver<DirectSolver_Context<solver::Z3_Backend> >(
+    coreSolver = std::make_unique<
+        MetaSMTSolver<DirectSolver_Context<solver::Z3_Backend>>>(
         UseForkedCoreSolver, CoreSolverOptimizeDivides);
     break;
 #endif
 #ifdef METASMT_HAVE_BTOR
   case METASMT_BACKEND_BOOLECTOR:
     backend = "Boolector";
-    coreSolver = new MetaSMTSolver<DirectSolver_Context<solver::Boolector> >(
+    coreSolver = std::make_unique<
+        MetaSMTSolver<DirectSolver_Context<solver::Boolector>>>(
         UseForkedCoreSolver, CoreSolverOptimizeDivides);
     break;
 #endif
 #ifdef METASMT_HAVE_CVC4
   case METASMT_BACKEND_CVC4:
     backend = "CVC4";
-    coreSolver = new MetaSMTSolver<DirectSolver_Context<solver::CVC4> >(
-        UseForkedCoreSolver, CoreSolverOptimizeDivides);
+    coreSolver =
+        std::make_unique<MetaSMTSolver<DirectSolver_Context<solver::CVC4>>>(
+            UseForkedCoreSolver, CoreSolverOptimizeDivides);
     break;
 #endif
 #ifdef METASMT_HAVE_YICES2
   case METASMT_BACKEND_YICES2:
     backend = "Yices2";
-    coreSolver = new MetaSMTSolver<DirectSolver_Context<solver::Yices2> >(
-        UseForkedCoreSolver, CoreSolverOptimizeDivides);
+    coreSolver =
+        std::make_unique<MetaSMTSolver<DirectSolver_Context<solver::Yices2>>>(
+            UseForkedCoreSolver, CoreSolverOptimizeDivides);
     break;
 #endif
   default:
@@ -468,6 +471,5 @@ Solver *createMetaSMTSolver() {
   klee_message("Starting MetaSMTSolver(%s)", backend.c_str());
   return coreSolver;
 }
-
 }
 #endif // ENABLE_METASMT
diff --git a/lib/Solver/MetaSMTSolver.h b/lib/Solver/MetaSMTSolver.h
index 89cb7143..64c56c57 100644
--- a/lib/Solver/MetaSMTSolver.h
+++ b/lib/Solver/MetaSMTSolver.h
@@ -13,6 +13,8 @@
 
 #include "klee/Solver/Solver.h"
 
+#include <memory>
+
 namespace klee {
 
 template <typename SolverContext> class MetaSMTSolver : public Solver {
@@ -26,7 +28,7 @@ public:
 
 /// createMetaSMTSolver - Create a solver using the metaSMT backend set by
 /// the option MetaSMTBackend.
-Solver *createMetaSMTSolver();
+std::unique_ptr<Solver> createMetaSMTSolver();
 }
 
 #endif /* KLEE_METASMTSOLVER_H */
diff --git a/lib/Solver/QueryLoggingSolver.cpp b/lib/Solver/QueryLoggingSolver.cpp
index c057751c..911fa067 100644
--- a/lib/Solver/QueryLoggingSolver.cpp
+++ b/lib/Solver/QueryLoggingSolver.cpp
@@ -15,6 +15,8 @@
 #include "klee/Support/FileHandling.h"
 #include "klee/System/Time.h"
 
+#include <utility>
+
 namespace {
 llvm::cl::opt<bool> DumpPartialQueryiesEarly(
     "log-partial-queries-early", llvm::cl::init(false),
@@ -29,13 +31,14 @@ llvm::cl::opt<bool> CreateCompressedQueryLog(
 #endif
 } // namespace
 
-QueryLoggingSolver::QueryLoggingSolver(Solver *_solver, std::string path,
+QueryLoggingSolver::QueryLoggingSolver(std::unique_ptr<Solver> solver,
+                                       std::string path,
                                        const std::string &commentSign,
                                        time::Span queryTimeToLog,
                                        bool logTimedOut)
-    : solver(_solver), BufferString(""), logBuffer(BufferString), queryCount(0),
-      minQueryTimeToLog(queryTimeToLog), logTimedOutQueries(logTimedOut),
-      queryCommentSign(commentSign) {
+    : solver(std::move(solver)), BufferString(""), logBuffer(BufferString),
+      queryCount(0), minQueryTimeToLog(queryTimeToLog),
+      logTimedOutQueries(logTimedOut), queryCommentSign(commentSign) {
   std::string error;
 #ifdef HAVE_ZLIB_H
   if (!CreateCompressedQueryLog) {
@@ -50,7 +53,7 @@ QueryLoggingSolver::QueryLoggingSolver(Solver *_solver, std::string path,
   if (!os) {
     klee_error("Could not open file %s : %s", path.c_str(), error.c_str());
   }
-  assert(0 != solver);
+  assert(this->solver);
 }
 
 void QueryLoggingSolver::flushBufferConditionally(bool writeToFile) {
diff --git a/lib/Solver/QueryLoggingSolver.h b/lib/Solver/QueryLoggingSolver.h
index 76bba429..8149342f 100644
--- a/lib/Solver/QueryLoggingSolver.h
+++ b/lib/Solver/QueryLoggingSolver.h
@@ -58,8 +58,9 @@ protected:
   void flushBufferConditionally(bool writeToFile);
 
 public:
-  QueryLoggingSolver(Solver *_solver, std::string path, const std::string &commentSign,
-                     time::Span queryTimeToLog, bool logTimedOut);
+  QueryLoggingSolver(std::unique_ptr<Solver> solver, std::string path,
+                     const std::string &commentSign, time::Span queryTimeToLog,
+                     bool logTimedOut);
 
   /// implementation of the SolverImpl interface
   bool computeTruth(const Query &query, bool &isValid);
diff --git a/lib/Solver/SMTLIBLoggingSolver.cpp b/lib/Solver/SMTLIBLoggingSolver.cpp
index bfea5c1b..c0713b45 100644
--- a/lib/Solver/SMTLIBLoggingSolver.cpp
+++ b/lib/Solver/SMTLIBLoggingSolver.cpp
@@ -11,6 +11,9 @@
 
 #include "klee/Expr/ExprSMTLIBPrinter.h"
 
+#include <memory>
+#include <utility>
+
 using namespace klee;
 
 /// This QueryLoggingSolver will log queries to a file in the SMTLIBv2 format
@@ -18,7 +21,6 @@ using namespace klee;
 class SMTLIBLoggingSolver : public QueryLoggingSolver
 {
         private:
-    
                 ExprSMTLIBPrinter printer;
 
                 virtual void printQuery(const Query& query,
@@ -41,22 +43,21 @@ class SMTLIBLoggingSolver : public QueryLoggingSolver
 
                         printer.generateOutput();
                 }    
-        
-	public:
-		SMTLIBLoggingSolver(Solver *_solver,
-                        std::string path,
-                        time::Span queryTimeToLog,
-                        bool logTimedOut)
-		: QueryLoggingSolver(_solver, path, ";", queryTimeToLog, logTimedOut)
-		{
-		  //Setup the printer
-		  printer.setOutput(logBuffer);
-		}
-};
 
+public:
+  SMTLIBLoggingSolver(std::unique_ptr<Solver> solver, std::string path,
+                      time::Span queryTimeToLog, bool logTimedOut)
+      : QueryLoggingSolver(std::move(solver), std::move(path), ";",
+                           queryTimeToLog, logTimedOut) {
+    // Setup the printer
+    printer.setOutput(logBuffer);
+  }
+};
 
-Solver* klee::createSMTLIBLoggingSolver(Solver *_solver, std::string path,
-                                        time::Span minQueryTimeToLog, bool logTimedOut)
-{
-  return new Solver(new SMTLIBLoggingSolver(_solver, path, minQueryTimeToLog, logTimedOut));
+std::unique_ptr<Solver>
+klee::createSMTLIBLoggingSolver(std::unique_ptr<Solver> solver,
+                                std::string path, time::Span minQueryTimeToLog,
+                                bool logTimedOut) {
+  return std::make_unique<Solver>(std::make_unique<SMTLIBLoggingSolver>(
+      std::move(solver), std::move(path), minQueryTimeToLog, logTimedOut));
 }
diff --git a/lib/Solver/STPSolver.cpp b/lib/Solver/STPSolver.cpp
index 140ca6f4..8858e83e 100644
--- a/lib/Solver/STPSolver.cpp
+++ b/lib/Solver/STPSolver.cpp
@@ -430,7 +430,7 @@ SolverImpl::SolverRunStatus STPSolverImpl::getOperationStatusCode() {
 }
 
 STPSolver::STPSolver(bool useForkedSTP, bool optimizeDivides)
-    : Solver(new STPSolverImpl(useForkedSTP, optimizeDivides)) {}
+    : Solver(std::make_unique<STPSolverImpl>(useForkedSTP, optimizeDivides)) {}
 
 char *STPSolver::getConstraintLog(const Query &query) {
   return impl->getConstraintLog(query);
diff --git a/lib/Solver/Solver.cpp b/lib/Solver/Solver.cpp
index e123a667..bb6ed105 100644
--- a/lib/Solver/Solver.cpp
+++ b/lib/Solver/Solver.cpp
@@ -12,6 +12,8 @@
 #include "klee/Expr/Constraints.h"
 #include "klee/Solver/SolverImpl.h"
 
+#include <utility>
+
 using namespace klee;
 
 const char *Solver::validity_to_str(Validity v) {
@@ -22,7 +24,7 @@ const char *Solver::validity_to_str(Validity v) {
   }
 }
 
-Solver::Solver(SolverImpl *impl) : impl(impl) {}
+Solver::Solver(std::unique_ptr<SolverImpl> impl) : impl(std::move(impl)) {}
 Solver::~Solver() = default;
 
 char *Solver::getConstraintLog(const Query& query) {
diff --git a/lib/Solver/ValidatingSolver.cpp b/lib/Solver/ValidatingSolver.cpp
index 72bdc830..8e9886d1 100644
--- a/lib/Solver/ValidatingSolver.cpp
+++ b/lib/Solver/ValidatingSolver.cpp
@@ -12,6 +12,7 @@
 #include "klee/Solver/SolverImpl.h"
 
 #include <memory>
+#include <utility>
 #include <vector>
 
 namespace klee {
@@ -22,8 +23,9 @@ private:
   std::unique_ptr<Solver, void(*)(Solver*)> oracle;
 
 public:
-  ValidatingSolver(Solver *solver, Solver *oracle, bool ownsOracle = false)
-      : solver(solver),
+  ValidatingSolver(std::unique_ptr<Solver> solver, Solver *oracle,
+                   bool ownsOracle)
+      : solver(std::move(solver)),
         oracle(
             oracle, ownsOracle ? [](Solver *solver) { delete solver; }
                                : [](Solver *) {}) {}
@@ -140,7 +142,10 @@ void ValidatingSolver::setCoreSolverTimeout(time::Span timeout) {
   solver->impl->setCoreSolverTimeout(timeout);
 }
 
-Solver *createValidatingSolver(Solver *s, Solver *oracle, bool ownsOracle) {
-  return new Solver(new ValidatingSolver(s, oracle, ownsOracle));
+std::unique_ptr<Solver> createValidatingSolver(std::unique_ptr<Solver> s,
+                                               Solver *oracle,
+                                               bool ownsOracle) {
+  return std::make_unique<Solver>(
+      std::make_unique<ValidatingSolver>(std::move(s), oracle, ownsOracle));
 }
 }
diff --git a/lib/Solver/Z3Solver.cpp b/lib/Solver/Z3Solver.cpp
index f3e8f92b..180b32f6 100644
--- a/lib/Solver/Z3Solver.cpp
+++ b/lib/Solver/Z3Solver.cpp
@@ -139,7 +139,7 @@ Z3SolverImpl::~Z3SolverImpl() {
   Z3_params_dec_ref(builder->ctx, solverParameters);
 }
 
-Z3Solver::Z3Solver() : Solver(new Z3SolverImpl()) {}
+Z3Solver::Z3Solver() : Solver(std::make_unique<Z3SolverImpl>()) {}
 
 char *Z3Solver::getConstraintLog(const Query &query) {
   return impl->getConstraintLog(query);