$extrastylesheet
00001 // The libMesh Finite Element Library. 00002 // Copyright (C) 2002-2014 Benjamin S. Kirk, John W. Peterson, Roy H. Stogner 00003 00004 // This library is free software; you can redistribute it and/or 00005 // modify it under the terms of the GNU Lesser General Public 00006 // License as published by the Free Software Foundation; either 00007 // version 2.1 of the License, or (at your option) any later version. 00008 00009 // This library is distributed in the hope that it will be useful, 00010 // but WITHOUT ANY WARRANTY; without even the implied warranty of 00011 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00012 // Lesser General Public License for more details. 00013 00014 // You should have received a copy of the GNU Lesser General Public 00015 // License along with this library; if not, write to the Free Software 00016 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA 00017 00018 #include "libmesh/adaptive_time_solver.h" 00019 #include "libmesh/diff_system.h" 00020 #include "libmesh/numeric_vector.h" 00021 00022 namespace libMesh 00023 { 00024 00025 00026 00027 AdaptiveTimeSolver::AdaptiveTimeSolver (sys_type& s) 00028 : UnsteadySolver(s), 00029 core_time_solver(), 00030 target_tolerance(1.e-3), 00031 upper_tolerance(0.0), 00032 max_deltat(0.), 00033 min_deltat(0.), 00034 max_growth(0.), 00035 global_tolerance(true) 00036 { 00037 // the child class must populate core_time_solver 00038 // with whatever actual time solver is to be used 00039 00040 // As an UnsteadySolver, we have an old_local_nonlinear_solution, but we're 00041 // going to drop it and use our core time solver's instead. 00042 old_local_nonlinear_solution.reset(); 00043 } 00044 00045 00046 00047 AdaptiveTimeSolver::~AdaptiveTimeSolver () 00048 { 00049 // As an UnsteadySolver, we have an old_local_nonlinear_solution, but it 00050 // is being managed by our core_time_solver. Make sure we don't delete 00051 // it out from under them, in case the user wants to keep using the core 00052 // solver after they're done with us. 00053 old_local_nonlinear_solution.release(); 00054 } 00055 00056 00057 00058 void AdaptiveTimeSolver::init() 00059 { 00060 libmesh_assert(core_time_solver.get()); 00061 00062 // We override this because our core_time_solver is the one that 00063 // needs to handle new vectors, diff_solver->init(), etc 00064 core_time_solver->init(); 00065 00066 // As an UnsteadySolver, we have an old_local_nonlinear_solution, but it 00067 // isn't pointing to the right place - fix it 00068 // 00069 // This leaves us with two UniquePtrs holding the same pointer - dangerous 00070 // for future use. Replace with shared_ptr? 00071 old_local_nonlinear_solution = 00072 UniquePtr<NumericVector<Number> >(core_time_solver->old_local_nonlinear_solution.get()); 00073 } 00074 00075 00076 00077 void AdaptiveTimeSolver::reinit() 00078 { 00079 libmesh_assert(core_time_solver.get()); 00080 00081 // We override this because our core_time_solver is the one that 00082 // needs to handle new vectors, diff_solver->reinit(), etc 00083 core_time_solver->reinit(); 00084 } 00085 00086 00087 void AdaptiveTimeSolver::advance_timestep () 00088 { 00089 NumericVector<Number> &old_nonlinear_soln = 00090 _system.get_vector("_old_nonlinear_solution"); 00091 NumericVector<Number> &nonlinear_solution = 00092 *(_system.solution); 00093 // _system.get_vector("_nonlinear_solution"); 00094 00095 old_nonlinear_soln = nonlinear_solution; 00096 00097 if (!first_solve) 00098 _system.time += last_deltat; 00099 } 00100 00101 00102 00103 Real AdaptiveTimeSolver::error_order () const 00104 { 00105 libmesh_assert(core_time_solver.get()); 00106 00107 return core_time_solver->error_order(); 00108 } 00109 00110 00111 00112 bool AdaptiveTimeSolver::element_residual (bool request_jacobian, 00113 DiffContext &context) 00114 { 00115 libmesh_assert(core_time_solver.get()); 00116 00117 return core_time_solver->element_residual(request_jacobian, context); 00118 } 00119 00120 00121 00122 bool AdaptiveTimeSolver::side_residual (bool request_jacobian, 00123 DiffContext &context) 00124 { 00125 libmesh_assert(core_time_solver.get()); 00126 00127 return core_time_solver->side_residual(request_jacobian, context); 00128 } 00129 00130 00131 00132 bool AdaptiveTimeSolver::nonlocal_residual (bool request_jacobian, 00133 DiffContext &context) 00134 { 00135 libmesh_assert(core_time_solver.get()); 00136 00137 return core_time_solver->nonlocal_residual(request_jacobian, context); 00138 } 00139 00140 00141 00142 UniquePtr<DiffSolver> & AdaptiveTimeSolver::diff_solver() 00143 { 00144 return core_time_solver->diff_solver(); 00145 } 00146 00147 00148 00149 UniquePtr<LinearSolver<Number> > & AdaptiveTimeSolver::linear_solver() 00150 { 00151 return core_time_solver->linear_solver(); 00152 } 00153 00154 00155 00156 Real AdaptiveTimeSolver::calculate_norm(System &s, 00157 NumericVector<Number> &v) 00158 { 00159 return s.calculate_norm(v, component_norm); 00160 } 00161 00162 } // namespace libMesh