diff --git a/CMakeLists.txt b/CMakeLists.txt
index 4a288d3fcdff6b78df77d38ba46025efcc4497e2..176bdf1a2db64c9aac6da0dfb421d10c65fb8ba3 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -32,12 +32,12 @@ message(STATUS "Configured to compile in ${CMAKE_BUILD_TYPE} mode.")
 SET(CMAKE_CXX_FLAGS_DEBUG "-g -Wall -D_REENTRANT")
 SET(CMAKE_CXX_FLAGS_RELEASE "-O3 -D_REENTRANT")
 
-#Set compiler according C++11 support
+#Set compiler according C++14 support
 include(CheckCXXCompilerFlag)
 CHECK_CXX_COMPILER_FLAG("-std=c++14" COMPILER_SUPPORTS_CXX14)
 if(COMPILER_SUPPORTS_CXX14)
-		message(STATUS "The compiler ${CMAKE_CXX_COMPILER} has C++14 support.")
-    set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++14")
+  message(STATUS "The compiler ${CMAKE_CXX_COMPILER} has C++14 support.")
+  set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++14")
 else()
   message(STATUS "The compiler ${CMAKE_CXX_COMPILER} has no C++14 support. Please use a different C++ compiler.")
 endif()
diff --git a/Testing/Temporary/.gitignore b/Testing/Temporary/.gitignore
new file mode 100644
index 0000000000000000000000000000000000000000..6ccdef7c09c93207bc46508bb9fd8c873e94e6c9
--- /dev/null
+++ b/Testing/Temporary/.gitignore
@@ -0,0 +1,2 @@
+/CTestCostData.txt
+/LastTest.log
diff --git a/demos/hello_wolf/yaml/hello_wolf_config.yaml b/demos/hello_wolf/yaml/hello_wolf_config.yaml
index c46580effcef4d12a9e4829d6a1c9cfdb8794da3..55eb56a880cd3d407cf631ce7e052e135e9bacce 100644
--- a/demos/hello_wolf/yaml/hello_wolf_config.yaml
+++ b/demos/hello_wolf/yaml/hello_wolf_config.yaml
@@ -22,7 +22,7 @@ config:
     max_num_iterations: 100
     verbose: 0
     period: 0.2
-    update_immediately: false
+    interrupt_on_problem_change: false
     n_threads: 2
     compute_cov: false
     minimizer: LEVENBERG_MARQUARDT
diff --git a/include/core/ceres_wrapper/solver_ceres.h b/include/core/ceres_wrapper/solver_ceres.h
index e638c0850cfcac4bdab7472ed836a37fe271e7f8..da0ac085504dfe02d64ee7c0b2c4d30b0b029adb 100644
--- a/include/core/ceres_wrapper/solver_ceres.h
+++ b/include/core/ceres_wrapper/solver_ceres.h
@@ -43,7 +43,7 @@ WOLF_STRUCT_PTR_TYPEDEFS(ParamsCeres);
 
 struct ParamsCeres : public ParamsSolver
 {
-    bool update_immediately = false;
+    bool interrupt_on_problem_change = false;
     int min_num_iterations = 1;
     ceres::Solver::Options solver_options;
     ceres::Problem::Options problem_options;
@@ -60,9 +60,9 @@ struct ParamsCeres : public ParamsSolver
     {
         loadHardcodedValues();
 
-        // stop solver whenever the problem is updated (via ceres::iterationCallback)
-        update_immediately                      = _server.getParam<bool>(prefix + "update_immediately");
-        if (update_immediately)
+        // interrupt solver whenever the problem is updated (via ceres::iterationCallback)
+        interrupt_on_problem_change             = _server.getParam<bool>(prefix + "interrupt_on_problem_change");
+        if (interrupt_on_problem_change)
             min_num_iterations                  = _server.getParam<int>(prefix + "min_num_iterations");
 
         // CERES SOLVER OPTIONS
@@ -139,6 +139,10 @@ class SolverCeres : public SolverManager
 
         ParamsCeresPtr params_ceres_;
 
+        // profiling
+        unsigned int n_iter_acc_, n_iter_max_;
+        unsigned int n_convergence_, n_interrupted_, n_no_convergence_;
+
     public:
 
         SolverCeres(const ProblemPtr& _wolf_problem);
@@ -160,13 +164,10 @@ class SolverCeres : public SolverManager
         bool computeCovariancesDerived(const std::vector<StateBlockPtr>& st_list) override;
 
         bool hasConverged() override;
-
-        SizeStd iterations() override;
-
+        bool wasStopped() override;
+        unsigned int iterations() override;
         double initialCost() override;
-
         double finalCost() override;
-
         double totalTime() override;
 
         ceres::Solver::Options& getSolverOptions();
@@ -207,6 +208,8 @@ class SolverCeres : public SolverManager
                                                 const LocalParametrizationBasePtr& local_param) override;
 
         bool hasLocalParametrizationDerived(const StateBlockPtr& st)  const override;
+
+        void printProfilingDerived(std::ostream& _stream) const override;
 };
 
 inline ceres::Solver::Summary SolverCeres::getSummary()
diff --git a/include/core/problem/problem.h b/include/core/problem/problem.h
index 8abc538d875763d1a8b50e82ef213420faaefc37..14f8588b7d01715a6ffb3dcd2e8be8d119aff78d 100644
--- a/include/core/problem/problem.h
+++ b/include/core/problem/problem.h
@@ -197,7 +197,6 @@ class Problem : public std::enable_shared_from_this<Problem>
         void removeMotionProvider(MotionProviderPtr proc);
 
     public:
-//        MotionProviderPtr getMotionProvider();
         std::map<int,MotionProviderPtr>& getMotionProviderMap();
         const std::map<int,MotionProviderPtr>& getMotionProviderMap() const;
 
@@ -443,13 +442,6 @@ inline bool Problem::isPriorSet() const
     return prior_options_ == nullptr;
 }
 
-//inline MotionProviderPtr Problem::getMotionProvider()
-//{
-//    if (not motion_provider_map_.empty())
-//        return motion_provider_map_.begin()->second;
-//    return nullptr;
-//}
-
 inline std::map<int,MotionProviderPtr>& Problem::getMotionProviderMap()
 {
     return motion_provider_map_;
diff --git a/include/core/solver/solver_manager.h b/include/core/solver/solver_manager.h
index 40575577f63bb634f444730ecb23fa7352fa1a86..c98804624b249ef71faddf8509116ee35bd937e0 100644
--- a/include/core/solver/solver_manager.h
+++ b/include/core/solver/solver_manager.h
@@ -142,19 +142,6 @@ class SolverManager
 
         virtual bool computeCovariances(const std::vector<StateBlockPtr>& st_list) final;
 
-        virtual bool computeCovariancesDerived(const CovarianceBlocksToBeComputed blocks) = 0;
-
-        virtual bool computeCovariancesDerived(const std::vector<StateBlockPtr>& st_list) = 0;
-
-        virtual bool hasConverged() = 0;
-
-        virtual SizeStd iterations() = 0;
-
-        virtual double initialCost() = 0;
-
-        virtual double finalCost() = 0;
-
-        virtual double totalTime() = 0;
 
         /**
          * \brief Updates solver's problem according to the wolf_problem
@@ -214,22 +201,37 @@ class SolverManager
         virtual void updateStateBlockStatus(const StateBlockPtr& state_ptr) final;
         virtual void updateStateBlockLocalParametrization(const StateBlockPtr& state_ptr) final;
 
+    // Derived virtual functions
     protected:
-        // Derived virtual functions
         virtual std::string solveDerived(const ReportVerbosity report_level) = 0;
+        virtual bool computeCovariancesDerived(const CovarianceBlocksToBeComputed blocks) = 0;
+        virtual bool computeCovariancesDerived(const std::vector<StateBlockPtr>& st_list) = 0;
+
         virtual void addFactorDerived(const FactorBasePtr& fac_ptr) = 0;
         virtual void removeFactorDerived(const FactorBasePtr& fac_ptr) = 0;
         virtual void addStateBlockDerived(const StateBlockPtr& state_ptr) = 0;
         virtual void removeStateBlockDerived(const StateBlockPtr& state_ptr) = 0;
         virtual void updateStateBlockStatusDerived(const StateBlockPtr& state_ptr) = 0;
         virtual void updateStateBlockLocalParametrizationDerived(const StateBlockPtr& state_ptr) = 0;
+
         virtual bool isStateBlockRegisteredDerived(const StateBlockPtr& state_ptr) const = 0;
         virtual bool isFactorRegisteredDerived(const FactorBasePtr& fac_ptr) const = 0;
-        virtual bool checkDerived(std::string prefix="") const = 0;
         virtual bool isStateBlockFixedDerived(const StateBlockPtr& st) = 0;
+        virtual bool hasLocalParametrizationDerived(const StateBlockPtr& st) const = 0;
         virtual bool hasThisLocalParametrizationDerived(const StateBlockPtr& st,
                                                         const LocalParametrizationBasePtr& local_param) = 0;
-        virtual bool hasLocalParametrizationDerived(const StateBlockPtr& st) const = 0;
+
+        virtual void printProfilingDerived(std::ostream& stream = std::cout) const = 0;
+        virtual bool checkDerived(std::string prefix="") const = 0;
+
+    public:
+        virtual bool hasConverged() = 0;
+        virtual bool wasStopped() = 0;
+        virtual unsigned int iterations() = 0;
+        virtual double initialCost() = 0;
+        virtual double finalCost() = 0;
+        virtual double totalTime() = 0;
+
 };
 
 // Params (here becaure it needs of declaration of SolverManager::ReportVerbosity)
diff --git a/src/ceres_wrapper/solver_ceres.cpp b/src/ceres_wrapper/solver_ceres.cpp
index aaf0c0970c2fe395d80181b7f9f115af46fb7e5d..aed7fef36c99f71de9b664fa456620c7ef6523cd 100644
--- a/src/ceres_wrapper/solver_ceres.cpp
+++ b/src/ceres_wrapper/solver_ceres.cpp
@@ -41,11 +41,16 @@ SolverCeres::SolverCeres(const ProblemPtr& _wolf_problem,
                          const ParamsCeresPtr& _params)
      : SolverManager(_wolf_problem, _params)
      , params_ceres_(_params)
+     , n_iter_acc_(0)
+     , n_iter_max_(0)
+     , n_convergence_(0)
+     , n_interrupted_(0)
+     , n_no_convergence_(0)
 {
     covariance_ = wolf::make_unique<ceres::Covariance>(params_ceres_->covariance_options);
     ceres_problem_ = wolf::make_unique<ceres::Problem>(params_ceres_->problem_options);
 
-    if (params_ceres_->update_immediately)
+    if (params_ceres_->interrupt_on_problem_change)
         getSolverOptions().callbacks.push_back(new IterationUpdateCallback(wolf_problem_,
                                                                            params_ceres_->min_num_iterations,
                                                                            params_ceres_->verbose != SolverManager::ReportVerbosity::QUIET));
@@ -74,24 +79,6 @@ std::string SolverCeres::solveDerived(const ReportVerbosity report_level)
     // run Ceres Solver
     ceres::Solve(getSolverOptions(), ceres_problem_.get(), &summary_);
 
-    /*/ if termination by user (Iteration callback, update and solve again)
-    // solve until max iterations reached
-    if (params_ceres_->update_immediately)
-    {
-        auto max_num_iterations = getSolverOptions().max_num_iterations;
-        while (summary_.termination_type == ceres::USER_SUCCESS)
-        {
-            // decrease wasted iterations
-            getSolverOptions().max_num_iterations -= summary_.iterations.size();
-            if (getSolverOptions().max_num_iterations <= 0)
-                break;
-
-            // update and solve again
-            update();
-            ceres::Solve(getSolverOptions(), ceres_problem_.get(), &summary_);
-        }
-        getSolverOptions().max_num_iterations = max_num_iterations;
-    }*/
     std::string report;
 
     //return report
@@ -100,6 +87,19 @@ std::string SolverCeres::solveDerived(const ReportVerbosity report_level)
     else if (report_level == ReportVerbosity::FULL)
         report = summary_.FullReport();
 
+    // PROFILING
+    // iterations (profiling)
+    n_iter_acc_ += iterations();
+    n_iter_max_ = std::max(n_iter_max_, iterations());
+
+    // convergence (profiling)
+    if (hasConverged())
+        n_convergence_++;
+    else if (wasStopped())
+        n_interrupted_++;
+    else
+        n_no_convergence_++;
+
     return report;
 }
 
@@ -182,17 +182,6 @@ bool SolverCeres::computeCovariancesDerived(const CovarianceBlocksToBeComputed _
                             break;
                     }
                 }
-            //            // loop all marginals (PO marginals)
-            //            for (unsigned int i = 0; 2*i+1 < all_state_blocks.size(); i++)
-            //            {
-            //                state_block_pairs.emplace_back(all_state_blocks[2*i],all_state_blocks[2*i]);
-            //                state_block_pairs.emplace_back(all_state_blocks[2*i],all_state_blocks[2*i+1]);
-            //                state_block_pairs.emplace_back(all_state_blocks[2*i+1],all_state_blocks[2*i+1]);
-            //
-            //                double_pairs.emplace_back(all_state_blocks[2*i]->get(),all_state_blocks[2*i]->get());
-            //                double_pairs.emplace_back(all_state_blocks[2*i]->get(),all_state_blocks[2*i+1]->get());
-            //                double_pairs.emplace_back(all_state_blocks[2*i+1]->get(),all_state_blocks[2*i+1]->get());
-            //            }
             break;
         }
         case CovarianceBlocksToBeComputed::ROBOT_LANDMARKS:
@@ -618,9 +607,16 @@ bool SolverCeres::hasConverged()
     return summary_.termination_type == ceres::CONVERGENCE;
 }
 
-SizeStd SolverCeres::iterations()
+bool SolverCeres::wasStopped()
 {
-    return summary_.iterations.size();
+    return summary_.termination_type == ceres::USER_FAILURE or summary_.termination_type == ceres::USER_SUCCESS;
+}
+
+unsigned int SolverCeres::iterations()
+{
+    if (summary_.num_successful_steps + summary_.num_unsuccessful_steps < 1)
+        return 0;
+    return summary_.num_successful_steps + summary_.num_unsuccessful_steps;
 }
 
 double SolverCeres::initialCost()
@@ -817,6 +813,20 @@ bool SolverCeres::hasThisLocalParametrizationDerived(const StateBlockPtr& st,
                     == state_blocks_local_param_.at(st).get();
 }
 
+void SolverCeres::printProfilingDerived(std::ostream& _stream) const
+{
+    _stream << "Iterations:"
+            << "\n\tUser-defined limit:         " << params_ceres_->solver_options.max_num_iterations
+            << "\n\tAverage iterations:         " << n_iter_acc_ / n_solve_
+            << "\n\tMax. iterations:            " << n_iter_max_
+            << "\nTermination:"
+            << "\n\tConvergence:                   " << 1e2 * n_convergence_ / n_solve_ << " %"
+            << "\n\tInterrupted by problem change: " << 1e2 * n_interrupted_ / n_solve_ << " %"
+            << "\n\tMax. iterations reached:       " << 1e2 * n_no_convergence_ / n_solve_ << " %"
+            << std::endl;
+}
+
+
 } // namespace wolf
 #include "core/solver/factory_solver.h"
 namespace wolf {
diff --git a/src/problem/problem.cpp b/src/problem/problem.cpp
index 787619db07741aa4ab7fd8228aaa37787885bbd6..8d5858a6e0045372d9dfb75a702f29c018ba9d22 100644
--- a/src/problem/problem.cpp
+++ b/src/problem/problem.cpp
@@ -969,42 +969,6 @@ bool Problem::getLandmarkCovariance(LandmarkBaseConstPtr _landmark_ptr, Eigen::M
     }
 
     return success;
-
-
-
-//    bool success(true);
-//    int i = 0, j = 0;
-//
-//    const auto& state_bloc_vec = _landmark_ptr->getStateBlockVec();
-//
-//    // computing size
-//    SizeEigen sz = 0;
-//    for (const auto& sb : state_bloc_vec)
-//        if (sb)
-//            sz += sb->getLocalSize();
-//
-//    // resizing
-//    _covariance = Eigen::MatrixXs(sz, sz);
-//
-//    // filling covariance
-//
-//    for (const auto& sb_i : state_bloc_vec)
-//    {
-//        if (sb_i)
-//        {
-//            j = 0;
-//            for (const auto& sb_j : state_bloc_vec)
-//            {
-//                if (sb_j)
-//                {
-//                    success = success && getCovarianceBlock(sb_i, sb_j, _covariance, i, j);
-//                    j += sb_j->getLocalSize();
-//                }
-//            }
-//            i += sb_i->getLocalSize();
-//        }
-//    }
-//    return success;
 }
 
 MapBasePtr Problem::getMap() const
@@ -1181,7 +1145,7 @@ void Problem::print(int _depth, bool _constr_by, bool _metric, bool _state_block
 {
 
     _stream << std::endl;
-    _stream << "P: wolf tree status ---------------------" << std::endl;
+    _stream << "Wolf tree status ------------------------" << std::endl;
 
     getHardware()->print(_depth, _constr_by, _metric, _state_blocks, _stream, "");
 
diff --git a/src/sensor/sensor_base.cpp b/src/sensor/sensor_base.cpp
index 7c9732d767955f1f7a1e7601905c4d09b9dd5282..0e649ec5cce5c11ca522c21bab70c67855922839 100644
--- a/src/sensor/sensor_base.cpp
+++ b/src/sensor/sensor_base.cpp
@@ -458,7 +458,7 @@ void SensorBase::printState (bool _metric, bool _state_blocks, std::ostream& _st
         {
             auto sb = getStateBlockDynamic(key);
             if (sb)
-                _stream << _tabs << "  " << key << "[" << (sb->isFixed() ? "Fix" : "Est") << "] = ( "
+                _stream << _tabs << "  " << key << " [" << (sb->isFixed() ? "Fix" : "Est") << "] = ( "
                         << std::setprecision(3) << sb->getState().transpose() << " )" << " @ " << sb << std::endl;
         }
     }
@@ -474,7 +474,7 @@ void SensorBase::printState (bool _metric, bool _state_blocks, std::ostream& _st
         {
             const auto &sb = getStateBlockDynamic(key);
             if (sb)
-                _stream << "    " << key << "[" << (sb->isFixed() ? "Fix" : "Est") << "] @ " << sb;
+                _stream << "    " << key << " [" << (sb->isFixed() ? "Fix" : "Est") << "] @ " << sb;
         }
         _stream << std::endl;
     }
diff --git a/src/solver/solver_manager.cpp b/src/solver/solver_manager.cpp
index 1dc258b880491badfd14e139555aae4382c48f87..e0168dd1bc83a6f349f32f31995d08a776fa5699 100644
--- a/src/solver/solver_manager.cpp
+++ b/src/solver/solver_manager.cpp
@@ -184,11 +184,6 @@ std::string SolverManager::solve(const ReportVerbosity report_level)
 
     // update StateBlocks with optimized state value.
     auto start_state = std::chrono::high_resolution_clock::now();
-    /// @todo whatif someone has changed the state notification during opti ??
-    /// JV: I do not see a problem here, the solver provides the optimal state given the factors, if someone changed the state during optimization, it will be overwritten by the optimal one.
-
-    //std::map<StateBlockPtr, Eigen::VectorXd>::iterator it = state_blocks_.begin(),
-    //        it_end = state_blocks_.end();
     for (auto& stateblock_statevector : state_blocks_)
     {
         // Avoid usuless copies
@@ -662,6 +657,7 @@ void SolverManager::printProfiling(std::ostream& _stream) const
             << "\n\t\tUpdate state:     " << 1e-3*max_duration_state_.count() << " ms"
             << "\n\tSolving covariance:     " << 1e-3*max_duration_cov_.count() << " ms" << std::endl;
 
+    printProfilingDerived(_stream);
 }
 
 } // namespace wolf
diff --git a/src/state_block/has_state_blocks.cpp b/src/state_block/has_state_blocks.cpp
index bd800ab2e907b3313afdc1717b3c11f2cd07b858..36cada937e0412330e7242d2092948807549fea9 100644
--- a/src/state_block/has_state_blocks.cpp
+++ b/src/state_block/has_state_blocks.cpp
@@ -84,7 +84,7 @@ void HasStateBlocks::printState (bool _metric, bool _state_blocks, std::ostream&
             auto sb = getStateBlock(key);
             if (sb)
                 _stream << _tabs << "  " << key
-                        << "[" << (sb->isFixed() ? "Fix" : "Est")
+                        << " [" << (sb->isFixed() ? "Fix" : "Est")
                         << "] = ( " << std::setprecision(3) << sb->getState().transpose() << " )"
                         << " @ " << sb << std::endl;
         }
@@ -103,7 +103,7 @@ void HasStateBlocks::printState (bool _metric, bool _state_blocks, std::ostream&
             const auto &sb = getStateBlock(key);
             if (sb)
                 _stream << "    " << key
-                        << "[" << (sb->isFixed() ? "Fix" : "Est")
+                        << " [" << (sb->isFixed() ? "Fix" : "Est")
                         << "] @ " << sb;
         }
         _stream << std::endl;
diff --git a/test/dummy/solver_manager_dummy.h b/test/dummy/solver_manager_dummy.h
index d718fc9554c2dd9371f4b18550dea2bf17c4af34..9c4df89d8d7ef2a6c0d9fd8ee568ba9d71247178 100644
--- a/test/dummy/solver_manager_dummy.h
+++ b/test/dummy/solver_manager_dummy.h
@@ -77,11 +77,13 @@ class SolverManagerDummy : public SolverManager
 
 
         // The following are dummy implementations
-        bool    hasConverged() override  { return true;      }
-        SizeStd iterations() override    { return 1;         }
-        double  initialCost() override   { return double(1); }
-        double  finalCost() override     { return double(0); }
-        double  totalTime() override     { return double(0); }
+        bool    hasConverged() override    { return true;      }
+        bool    wasStopped() override      { return false;     }
+        unsigned int iterations() override { return 1;         }
+        double  initialCost() override     { return double(1); }
+        double  finalCost() override       { return double(0); }
+        double  totalTime() override       { return double(0); }
+        void printProfilingDerived(std::ostream& _stream) const override {}
 
     protected:
 
diff --git a/test/yaml/solver.yaml b/test/yaml/solver.yaml
index ec6a06a9eaefa6163ef6c6bb7512ac00d24c7725..53a698323208a61dc63a35084985c13fdcebdd98 100644
--- a/test/yaml/solver.yaml
+++ b/test/yaml/solver.yaml
@@ -1,6 +1,6 @@
 period: 1
 verbose: 2
-update_immediately: false
+interrupt_on_problem_change: false
 max_num_iterations: 1000
 n_threads: 2
 function_tolerance: 0.000001