Index: memory_solution_history.h
===================================================================
--- memory_solution_history.h	(revision 0)
+++ memory_solution_history.h	(revision 0)
@@ -0,0 +1,55 @@
+// Subclass of Solution History that stores the solutions 
+// and other important vectors in memory
+
+#ifndef __memory_solution_history_h__
+#define __memory_solution_history_h__
+
+// Local includes
+#include "libmesh/numeric_vector.h"
+#include "libmesh/solution_history.h"
+#include <list>
+
+namespace libMesh
+{
+  
+  // MemorySolutionHistory class declaration and definition
+  class MemorySolutionHistory : public SolutionHistory
+  {
+  public:    
+    
+    // Constructor, reference to system to be passed by user, set the  
+    // stored_sols iterator to some initial value
+  MemorySolutionHistory(System & system_) : stored_sols(stored_solutions.end()), _system(system_) {} ;
+
+    // Virtual function store which we will be overriding to store timesteps
+    virtual void store();
+
+    // Virtual function retrieve which we will be overriding to retrieve timesteps
+    virtual void retrieve();
+
+    // Typedef for Stored Solutions iterator, a list of pairs of the current 
+    // system time, map of strings and saved vectors
+    typedef std::list<std::pair<Real, std::map<std::string, NumericVector<Real>*> > >::iterator stored_solutions_iterator;
+
+    // Definition of the clone function needed for the setter function 
+    virtual AutoPtr<SolutionHistory > clone() const {
+    return AutoPtr<SolutionHistory > 
+      (new MemorySolutionHistory(_system));}
+    
+  private:
+    
+    // This list of pairs will hold the current time and stored vectors 
+    // from each timestep
+    std::list<std::pair<Real, std::map<std::string, NumericVector<Real>*> > > stored_solutions; 
+    
+    // The stored solutions iterator
+    stored_solutions_iterator stored_sols;
+    
+    // A system reference
+    System & _system ;
+
+  };
+
+} // end namespace libMesh
+
+#endif // __memory_solution_history_h__
Index: no_solution_history.h
===================================================================
--- no_solution_history.h	(revision 0)
+++ no_solution_history.h	(revision 0)
@@ -0,0 +1,38 @@
+// 'Save nothing' subclass of Solution History, this is the default
+
+#ifndef __no_solution_history_h__
+#define __no_solution_history_h__
+
+// Local includes
+#include "libmesh/solution_history.h"
+
+namespace libMesh
+{
+  
+  // NoSolutionHistory class declaration and definition
+  class NoSolutionHistory : public SolutionHistory
+  {
+  public:
+    
+    // Constructor
+  NoSolutionHistory() : SolutionHistory() {};
+
+    // Destructor
+    ~NoSolutionHistory() {};
+
+    // Virtual function store which we will be overriding
+    virtual void store();
+
+    // Virtual function retrieve which we will be overriding
+    virtual void retrieve();
+
+    // Definition of the clone function needed for the setter function 
+    virtual AutoPtr<SolutionHistory > clone() const {
+    return AutoPtr<SolutionHistory > 
+      (new NoSolutionHistory());}
+    
+  }; // end NoSolutionHistory class definition
+
+} // end namespace libMesh
+
+#endif // __no_solution_history_h__
Index: solution_history.h
===================================================================
--- solution_history.h	(revision 0)
+++ solution_history.h	(revision 0)
@@ -0,0 +1,38 @@
+// A SolutionHistory class that enables the storage and retrieval of timesteps 
+// and (in the future) adaptive steps
+
+#ifndef __solution_history_h__
+#define __solution_history_h__
+
+// Local Includes
+#include "libmesh/system.h"
+
+namespace libMesh
+{
+
+  // SolutionHistory class declaration and definition
+  class SolutionHistory
+  {
+  public:
+    
+    // Constructor
+    SolutionHistory() {};
+    
+    // Destructor
+    ~SolutionHistory () {};
+
+    // Function to store a solution, pure virtual
+    virtual void store() = 0;
+
+    // Function to retrieve a solution, pure virtual
+    virtual void retrieve() = 0;
+
+    // Cloning function for an AutoPtr, pure virtual, used in the 
+    // setter function in time_solver.C
+    virtual AutoPtr<SolutionHistory > clone() const = 0;
+    
+  }; // end SolutionHistory class definition
+
+} // end namespace libMesh
+
+#endif // __solution_history_h__
Index: time_solver.h
===================================================================
--- time_solver.h	(revision 6431)
+++ time_solver.h	(working copy)
@@ -26,6 +26,7 @@
 #include "libmesh/linear_solver.h"
 #include "libmesh/numeric_vector.h"
 #include "libmesh/reference_counted_object.h"
+#include "libmesh/solution_history.h"
 
 // C++ includes
 
@@ -107,9 +108,9 @@
   /**
    * This method advances the adjoint solution to the previous
    * timestep, after an adjoint_solve() has been performed.  This will
-   * probably be done after every UnsteadySolver::adjoint_solve().
+   * be done before every UnsteadySolver::adjoint_solve().
    */
-  virtual void adjoint_recede_timestep ();
+  virtual void adjoint_advance_timestep ();
 
   /**
    * This method uses the DifferentiableSystem's
@@ -190,6 +191,12 @@
    */
   unsigned int reduce_deltat_on_diffsolver_failure;
 
+  /**
+   * A setter function users will employ if they need to do something 
+   * other than save no solution history
+   */
+  void set_solution_history(const SolutionHistory & _solution_history);
+
 protected:
 
   /**
@@ -217,6 +224,13 @@
    * Serial vector of _system.get_vector("_old_nonlinear_solution")
    */
   AutoPtr<NumericVector<Number> > old_local_nonlinear_solution;
+
+  /**
+   * An AutoPtr to a SolutionHistory object. Default is
+   * NoSolutionHistory, which the user can override by declaring a
+   * different kind of SolutionHistory in the application
+   */
+  AutoPtr<SolutionHistory> solution_history;
 };
 
 
Index: unsteady_solver.h
===================================================================
--- unsteady_solver.h	(revision 6431)
+++ unsteady_solver.h	(working copy)
@@ -87,6 +87,13 @@
   virtual void advance_timestep ();
 
   /**
+   * This method advances the adjoint solution to the previous
+   * timestep, after an adjoint_solve() has been performed.  This will
+   * be done before every UnsteadySolver::adjoint_solve().
+   */
+  virtual void adjoint_advance_timestep ();
+
+  /**
    * This method should return the expected convergence order of the
    * (non-local) error of the time discretization scheme - e.g. 2 for the
    * O(deltat^2) Crank-Nicholson, or 1 for the O(deltat) Backward Euler.
Index: memory_solution_history.C
===================================================================
--- memory_solution_history.C	(revision 0)
+++ memory_solution_history.C	(revision 0)
@@ -0,0 +1,72 @@
+// Function definitions for MemorySolutionHistory
+
+// Local includes
+#include "libmesh/memory_solution_history.h"
+
+namespace libMesh
+{
+  // This functions saves all the 'projection-worthy' system vectors for
+  // future use
+  void MemorySolutionHistory::store()
+  {    
+    // Map of to be projected vectors from this solution step
+    std::map<std::string, NumericVector<Number> *> saved_vectors;
+    
+    // Loop over all the system vectors
+    for (System::vectors_iterator vec = _system.vectors_begin(); vec != _system.vectors_end(); ++vec)
+      {	
+	// The name of this vector
+	const std::string& vec_name = vec->first;
+
+	// Check if this vector is to be projected
+	bool vector_projection_setting = _system.vector_preservation(vec_name);
+	
+	// If it is important enough to be projected, it is important enough to be saved
+	if(vector_projection_setting)
+	  {
+	    saved_vectors[vec_name] = vec->second->clone().release();
+	  }
+
+      }
+    
+    // Of course, we will always save the actual solution
+    std::string _solution("_solution");    
+    saved_vectors[_solution] = _system.solution->clone().release();
+
+    // Put all the vectors from this timestep into stored_solutions
+    stored_solutions.push_back(std::make_pair(_system.time, saved_vectors));
+    
+  }
+
+  void MemorySolutionHistory::retrieve()
+  {    
+    // To find the required entry in the stored_solutions list, we need to first decrement the stored_sols iterator
+    --stored_sols;
+    
+    // Get the time at which we are recovering the solution vectors
+    Real recovery_time = stored_sols->first;
+
+    // Print out what time we are recovering vectors at
+    std::cout<<"Recovering solution vectors at time: " <<recovery_time << std::endl;
+
+    // Get the saved vectors at this timestep
+    std::map<std::string, NumericVector<Number> *> saved_vectors = stored_sols->second;
+
+    // Loop over all the saved vectors
+    for (System::vectors_iterator vec = saved_vectors.begin(); vec != saved_vectors.end(); ++vec)
+      {	
+  	// The name of this vector
+  	const std::string& vec_name = vec->first;
+	
+	// Get the vec_name entry in the saved vectors map and set the current system vec[vec_name] entry to it
+	vec->second = saved_vectors[vec_name];	    
+      }
+    
+    // Of course, we will *always* have to get the actual solution
+    std::string _solution("_solution");    
+    *(_system.solution) = *(saved_vectors[_solution]);
+        
+  }
+
+}
+    
Index: no_solution_history.C
===================================================================
--- no_solution_history.C	(revision 0)
+++ no_solution_history.C	(revision 0)
@@ -0,0 +1,20 @@
+// Function Definitions for NoTimeHistory
+
+// Local includes
+#include "libmesh/no_solution_history.h"
+
+namespace libMesh
+{
+
+  void NoSolutionHistory::store()
+  {
+    // Do nothing
+  }
+
+  void NoSolutionHistory::retrieve()
+  {
+    // Nothing was stored, so nothing can be retrieved
+    libmesh_error();
+  }
+
+}
Index: time_solver.C
===================================================================
--- time_solver.C	(revision 6431)
+++ time_solver.C	(working copy)
@@ -15,11 +15,11 @@
 // License along with this library; if not, write to the Free Software
 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 
-
 #include "libmesh/diff_solver.h"
 #include "libmesh/diff_system.h"
 #include "libmesh/linear_solver.h"
 #include "libmesh/time_solver.h"
+#include "libmesh/no_solution_history.h"
 
 namespace libMesh
 {
@@ -31,7 +31,8 @@
     reduce_deltat_on_diffsolver_failure (0),
     _diff_solver (NULL),
     _linear_solver (NULL),
-    _system (s)
+    _system (s),
+    solution_history(new NoSolutionHistory()) // Default setting for solution_history
 {
 }
 
@@ -80,14 +81,16 @@
 }
 
 
+void TimeSolver::set_solution_history (const SolutionHistory & _solution_history)
+ {
+   solution_history = _solution_history.clone();
+ }
 
 void TimeSolver::advance_timestep ()
 {
 }
 
-
-
-void TimeSolver::adjoint_recede_timestep ()
+void TimeSolver::adjoint_advance_timestep ()
 {
 }
 
Index: unsteady_solver.C
===================================================================
--- unsteady_solver.C	(revision 6431)
+++ unsteady_solver.C	(working copy)
@@ -133,10 +133,26 @@
 
   if (!first_solve)
     _system.time += _system.deltat;
+
+  // Store the solution, does nothing by default
+  // User has to attach appropriate solution_history object for this to
+  // actually store anything anywhere
+  solution_history->store();
 }
 
 
+  void UnsteadySolver::adjoint_advance_timestep ()
+  {
+    // Decrement the system time
+    _system.time -= _system.deltat;
 
+    // Retrieve the primal solution vectors at this time using thr
+    // solution_history object
+    solution_history->retrieve();
+  }
+
+
+
 Number UnsteadySolver::old_nonlinear_solution(const unsigned int global_dof_number)
 const
 {
