Line data Source code
1 : //* This file is part of the MOOSE framework 2 : //* https://mooseframework.inl.gov 3 : //* 4 : //* All rights reserved, see COPYRIGHT for full restrictions 5 : //* https://github.com/idaholab/moose/blob/master/COPYRIGHT 6 : //* 7 : //* Licensed under LGPL 2.1, please see LICENSE for details 8 : //* https://www.gnu.org/licenses/lgpl-2.1.html 9 : 10 : #pragma once 11 : 12 : #include "MooseTypes.h" 13 : #include "MooseVariableField.h" 14 : #include "SubProblem.h" 15 : #include "MooseMesh.h" 16 : #include "MooseVariableDataLinearFV.h" 17 : 18 : #include "libmesh/numeric_vector.h" 19 : #include "libmesh/dof_map.h" 20 : #include "libmesh/elem.h" 21 : #include "libmesh/quadrature.h" 22 : #include "libmesh/dense_vector.h" 23 : #include "libmesh/enum_fe_family.h" 24 : 25 : template <typename> 26 : class MooseLinearVariableFV; 27 : 28 : typedef MooseLinearVariableFV<Real> MooseLinearVariableFVReal; 29 : class FVDirichletBCBase; 30 : class FVFluxBC; 31 : class LinearFVBoundaryCondition; 32 : 33 : namespace libMesh 34 : { 35 : template <typename> 36 : class NumericVector; 37 : } 38 : 39 : /// This class provides variable solution interface for linear 40 : /// finite volume problems. 41 : /// This class is designed to store gradient information when enabled. 42 : template <typename OutputType> 43 : class MooseLinearVariableFV : public MooseVariableField<OutputType> 44 : { 45 : public: 46 : using OutputGradient = typename MooseVariableField<OutputType>::OutputGradient; 47 : using OutputSecond = typename MooseVariableField<OutputType>::OutputSecond; 48 : using OutputDivergence = typename MooseVariableField<OutputType>::OutputDivergence; 49 : 50 : using FieldVariableValue = typename MooseVariableField<OutputType>::FieldVariableValue; 51 : using FieldVariableGradient = typename MooseVariableField<OutputType>::FieldVariableGradient; 52 : using FieldVariableSecond = typename MooseVariableField<OutputType>::FieldVariableSecond; 53 : using FieldVariableCurl = typename MooseVariableField<OutputType>::FieldVariableCurl; 54 : using FieldVariableDivergence = typename MooseVariableField<OutputType>::FieldVariableDivergence; 55 : 56 : using OutputShape = typename MooseVariableField<OutputType>::OutputShape; 57 : using OutputShapeGradient = typename MooseVariableField<OutputType>::OutputShapeGradient; 58 : using OutputShapeSecond = typename MooseVariableField<OutputType>::OutputShapeSecond; 59 : using OutputShapeDivergence = typename MooseVariableField<OutputType>::OutputShapeDivergence; 60 : 61 : using OutputData = typename MooseVariableField<OutputType>::OutputData; 62 : using DoFValue = typename MooseVariableField<OutputType>::DoFValue; 63 : 64 : using FieldVariablePhiValue = typename MooseVariableField<OutputType>::FieldVariablePhiValue; 65 : using FieldVariablePhiGradient = 66 : typename MooseVariableField<OutputType>::FieldVariablePhiGradient; 67 : using FieldVariablePhiSecond = typename MooseVariableField<OutputType>::FieldVariablePhiSecond; 68 : using FieldVariablePhiDivergence = 69 : typename MooseVariableField<OutputType>::FieldVariablePhiDivergence; 70 : using ElemQpArg = Moose::ElemQpArg; 71 : using ElemSideQpArg = Moose::ElemSideQpArg; 72 : using ElemArg = Moose::ElemArg; 73 : using FaceArg = Moose::FaceArg; 74 : using StateArg = Moose::StateArg; 75 : using NodeArg = Moose::NodeArg; 76 : using ElemPointArg = Moose::ElemPointArg; 77 : using typename MooseVariableField<OutputType>::ValueType; 78 : using typename MooseVariableField<OutputType>::DotType; 79 : using typename MooseVariableField<OutputType>::GradientType; 80 : 81 : static InputParameters validParams(); 82 : MooseLinearVariableFV(const InputParameters & parameters); 83 : 84 620766 : virtual bool isFV() const override { return true; } 85 : 86 : /** 87 : * If the variable has a dirichlet boundary condition at face described by \p fi . 88 : */ 89 : virtual bool isDirichletBoundaryFace(const FaceInfo & fi) const; 90 : 91 : /** 92 : * Switch to request cell gradient computations. 93 : */ 94 691 : void computeCellGradients() { _needs_cell_gradients = true; } 95 : 96 : /** 97 : * Check if cell gradient computations were requested for this variable. 98 : */ 99 21041 : virtual bool needsGradientVectorStorage() const override { return _needs_cell_gradients; } 100 : 101 : virtual bool isExtrapolatedBoundaryFace(const FaceInfo & fi, 102 : const Elem * elem, 103 : const Moose::StateArg & state) const override; 104 : 105 : /** 106 : * Get the variable gradient at a cell center. 107 : * @param elem_info The ElemInfo of the cell where we need the gradient 108 : */ 109 : const VectorValue<Real> gradSln(const ElemInfo & elem_info) const; 110 : 111 : /** 112 : * Compute interpolated gradient on the provided face. 113 : * @param face The face for which to retrieve the gradient. 114 : * @param state State argument which describes at what time / solution iteration state we want to 115 : * evaluate the variable 116 : */ 117 : VectorValue<Real> gradSln(const FaceInfo & fi, const StateArg & state) const; 118 : 119 : virtual void initialSetup() override; 120 : 121 : /** 122 : * Get the solution value for the provided element and seed the derivative for the corresponding 123 : * dof index 124 : * @param elem_info The element to retrieve the solution value for 125 : * @param state State argument which describes at what time / solution iteration state we want to 126 : * evaluate the variable 127 : */ 128 : Real getElemValue(const ElemInfo & elem_info, const StateArg & state) const; 129 : 130 : /** 131 : * Get the boundary condition object which corresponds to the given boundary ID 132 : * @param bd_id The boundary ID whose condition should be fetched 133 : */ 134 : LinearFVBoundaryCondition * getBoundaryCondition(const BoundaryID bd_id) const; 135 : 136 0 : const std::unordered_map<BoundaryID, LinearFVBoundaryCondition *> & getBoundaryConditionMap() 137 : { 138 0 : return _boundary_id_to_bc; 139 : } 140 : 141 257486 : virtual void prepareIC() override {} 142 : 143 1991 : virtual bool isNodal() const override final { return false; } 144 : 145 0 : virtual bool hasDoFsOnNodes() const override final { return false; } 146 : 147 16 : virtual bool isNodalDefined() const override final { return false; } 148 : 149 0 : virtual bool supportsFaceArg() const override final { return true; } 150 0 : virtual bool supportsElemSideQpArg() const override final { return false; } 151 : 152 : virtual const Elem * const & currentElem() const override; 153 : 154 0 : virtual bool computingSecond() const override final { return false; } 155 0 : virtual bool computingCurl() const override final { return false; } 156 0 : virtual bool computingDiv() const override final { return false; } 157 0 : virtual bool usesSecondPhiNeighbor() const override final { return false; } 158 : 159 : protected: 160 : /// Throw an error when somebody requests time-related data from this variable 161 : [[noreturn]] void timeIntegratorError() const; 162 : 163 : /// Throw and error when somebody requests lower-dimensional data from this variable 164 : [[noreturn]] void lowerDError() const; 165 : 166 : /// Throw an error when somebody wants to use this variable as a nodal variable 167 : [[noreturn]] void nodalError() const; 168 : 169 : /// Throw an error when somebody wants to use this variable with automatic differentiation 170 : [[noreturn]] void adError() const; 171 : 172 : /** 173 : * Setup the boundary to Dirichlet BC map 174 : */ 175 : void cacheBoundaryBCMap(); 176 : 177 : usingMooseVariableBaseMembers; 178 : 179 : /// Boolean to check if this variable needs gradient computations. 180 : bool _needs_cell_gradients; 181 : 182 : /// Temporary storage for the cell gradient to avoid unnecessary allocations. 183 : mutable RealVectorValue _cell_gradient; 184 : 185 : /// Pointer to the cell gradients which are stored on the linear system 186 : const std::vector<std::unique_ptr<libMesh::NumericVector<libMesh::Number>>> & _grad_container; 187 : 188 : /// Holder for all the data associated with the "main" element. The data in this is 189 : /// mainly used by finite element-based loops such as the postprocessor and auxkernel 190 : /// loops 191 : std::unique_ptr<MooseVariableDataLinearFV<OutputType>> _element_data; 192 : 193 : /// Holder for all the data associated with the "neighbor" element. The data in this is 194 : /// mainly used by finite element-based loops such as the postprocessor and auxkernel 195 : /// loops 196 : std::unique_ptr<MooseVariableDataLinearFV<OutputType>> _neighbor_data; 197 : 198 : /// Map for easily accessing the boundary conditions based on the boundary IDs. 199 : /// We assume that each boundary has one boundary condition only. 200 : std::unordered_map<BoundaryID, LinearFVBoundaryCondition *> _boundary_id_to_bc; 201 : 202 : /// Cache the number of the system this variable belongs to 203 : const unsigned int _sys_num; 204 : 205 : friend void Moose::initDofIndices<>(MooseLinearVariableFV<OutputType> &, const Elem &); 206 : 207 : private: 208 : using MooseVariableField<OutputType>::evaluate; 209 : using MooseVariableField<OutputType>::evaluateGradient; 210 : using MooseVariableField<OutputType>::evaluateDot; 211 : 212 : virtual ValueType evaluate(const ElemArg & elem, const StateArg &) const override final; 213 : virtual ValueType evaluate(const FaceArg & face, const StateArg &) const override final; 214 : virtual ValueType evaluate(const NodeArg & node, const StateArg &) const override final; 215 : virtual ValueType evaluate(const ElemPointArg & elem_point, 216 : const StateArg & state) const override final; 217 : virtual ValueType evaluate(const ElemQpArg & elem_qp, 218 : const StateArg & state) const override final; 219 : virtual ValueType evaluate(const ElemSideQpArg & elem_side_qp, 220 : const StateArg & state) const override final; 221 : virtual GradientType evaluateGradient(const ElemQpArg & qp_arg, 222 : const StateArg &) const override final; 223 : virtual GradientType evaluateGradient(const ElemArg & elem_arg, 224 : const StateArg &) const override final; 225 : virtual GradientType evaluateGradient(const FaceArg & face, 226 : const StateArg &) const override final; 227 : virtual DotType evaluateDot(const ElemArg & elem, const StateArg &) const override final; 228 : 229 : /// The current (ghosted) solution. Note that this needs to be stored as a reference to a pointer 230 : /// because the solution might not exist at the time that this variable is constructed, so we 231 : /// cannot safely dereference at that time 232 : const libMesh::NumericVector<libMesh::Number> * const & _solution; 233 : 234 : /// Shape functions, only used when we are postprocessing or using this variable 235 : /// in an auxiliary system 236 : const FieldVariablePhiValue & _phi; 237 : const FieldVariablePhiGradient & _grad_phi; 238 : const FieldVariablePhiValue & _phi_face; 239 : const FieldVariablePhiGradient & _grad_phi_face; 240 : const FieldVariablePhiValue & _phi_face_neighbor; 241 : const FieldVariablePhiGradient & _grad_phi_face_neighbor; 242 : const FieldVariablePhiValue & _phi_neighbor; 243 : const FieldVariablePhiGradient & _grad_phi_neighbor; 244 : 245 : public: 246 : // ********************************************************************************* 247 : // ********************************************************************************* 248 : // The following functions are separated here because they are not essential for the 249 : // solver but are necessary to interface with the auxiliary and postprocessor 250 : // systems. 251 : // ********************************************************************************* 252 : // ********************************************************************************* 253 : 254 : virtual void setDofValue(const OutputData & /*value*/, unsigned int /*index*/) override; 255 : 256 : virtual void getDofIndices(const Elem * elem, 257 : std::vector<dof_id_type> & dof_indices) const override; 258 : 259 : virtual void setDofValues(const DenseVector<OutputData> & values) override; 260 : 261 : virtual void clearDofIndices() override; 262 : 263 496 : virtual unsigned int numberOfDofs() const override final { return 1; } 264 0 : virtual unsigned int numberOfDofsNeighbor() override final { return 1; } 265 : 266 : virtual unsigned int oldestSolutionStateRequested() const override final; 267 : 268 : virtual void clearAllDofIndices() override final; 269 : 270 : [[noreturn]] virtual const std::vector<dof_id_type> & dofIndicesLower() const override final; 271 : [[noreturn]] virtual const FieldVariablePhiValue & phiLower() const override; 272 : 273 : // Overriding these to make sure nothing happens during residual/jacobian setup. 274 : // The only time this can actually happen is when residual setup is called on the auxiliary 275 : // system. 276 22 : virtual void residualSetup() override {} 277 308 : virtual void jacobianSetup() override {} 278 : 279 0 : virtual libMesh::FEContinuity getContinuity() const override 280 : { 281 0 : return _element_data->getContinuity(); 282 : }; 283 : 284 : virtual void setNodalValue(const OutputType & value, unsigned int idx = 0) override; 285 : 286 : [[noreturn]] virtual const DoFValue & nodalVectorTagValue(TagID) const override; 287 : 288 : virtual const std::vector<dof_id_type> & dofIndices() const final; 289 : virtual const std::vector<dof_id_type> & dofIndicesNeighbor() const final; 290 : 291 631182 : virtual void prepare() override final {} 292 0 : virtual void prepareNeighbor() override final {} 293 0 : virtual void prepareAux() override final {} 294 16 : virtual void reinitNode() override final {} 295 0 : virtual void reinitNodes(const std::vector<dof_id_type> & /*nodes*/) override final {} 296 0 : virtual void reinitNodesNeighbor(const std::vector<dof_id_type> & /*nodes*/) override final {} 297 1376 : virtual void reinitAux() override final {} 298 0 : virtual void reinitAuxNeighbor() override final {} 299 0 : virtual void prepareLowerD() override final {} 300 : 301 : virtual void computeElemValuesFace() override; 302 : virtual void computeNeighborValuesFace() override; 303 : virtual void computeNeighborValues() override; 304 : virtual void computeLowerDValues() override final; 305 : 306 : virtual void computeNodalNeighborValues() override final; 307 : virtual void computeNodalValues() override final; 308 : 309 : virtual void computeElemValues() override; 310 0 : virtual void computeFaceValues(const FaceInfo & /*fi*/) override {} 311 : 312 : virtual void setLowerDofValues(const DenseVector<OutputData> & values) override; 313 : 314 : virtual void insert(libMesh::NumericVector<libMesh::Number> & vector) override; 315 : virtual void insertLower(libMesh::NumericVector<libMesh::Number> & vector) override; 316 : virtual void add(libMesh::NumericVector<libMesh::Number> & vector) override; 317 : 318 : virtual void setActiveTags(const std::set<TagID> & vtags) override; 319 : 320 : [[noreturn]] virtual const MooseArray<OutputType> & nodalValueArray() const override; 321 : [[noreturn]] virtual const MooseArray<OutputType> & nodalValueOldArray() const override; 322 : [[noreturn]] virtual const MooseArray<OutputType> & nodalValueOlderArray() const override; 323 : 324 204 : virtual const FieldVariablePhiValue & phi() const override final { return _phi; } 325 0 : virtual const FieldVariablePhiGradient & gradPhi() const override final { return _grad_phi; } 326 : [[noreturn]] virtual const FieldVariablePhiSecond & secondPhi() const override final; 327 : [[noreturn]] const FieldVariablePhiValue & curlPhi() const override final; 328 : [[noreturn]] const FieldVariablePhiDivergence & divPhi() const override final; 329 : 330 0 : virtual const FieldVariablePhiValue & phiFace() const override final { return _phi_face; } 331 0 : virtual const FieldVariablePhiGradient & gradPhiFace() const override final 332 : { 333 0 : return _grad_phi_face; 334 : } 335 : [[noreturn]] virtual const FieldVariablePhiSecond & secondPhiFace() const override final; 336 : 337 0 : virtual const FieldVariablePhiValue & phiFaceNeighbor() const override final 338 : { 339 0 : return _phi_face_neighbor; 340 : } 341 0 : virtual const FieldVariablePhiGradient & gradPhiFaceNeighbor() const override final 342 : { 343 0 : return _grad_phi_face_neighbor; 344 : } 345 : [[noreturn]] virtual const FieldVariablePhiSecond & secondPhiFaceNeighbor() const override final; 346 : 347 0 : virtual const FieldVariablePhiValue & phiNeighbor() const override final { return _phi_neighbor; } 348 0 : virtual const FieldVariablePhiGradient & gradPhiNeighbor() const override final 349 : { 350 0 : return _grad_phi_neighbor; 351 : } 352 : [[noreturn]] virtual const FieldVariablePhiSecond & secondPhiNeighbor() const override final; 353 : 354 : virtual const FieldVariableValue & vectorTagValue(TagID tag) const override; 355 : virtual const DoFValue & vectorTagDofValue(TagID tag) const override; 356 : [[noreturn]] virtual const DoFValue & nodalMatrixTagValue(TagID tag) const override; 357 : virtual const FieldVariableValue & matrixTagValue(TagID tag) const override; 358 : 359 : virtual const FieldVariableValue & sln() const override; 360 : virtual const FieldVariableValue & slnOld() const override; 361 : virtual const FieldVariableValue & slnOlder() const override; 362 : virtual const FieldVariableGradient & gradSln() const override; 363 : virtual const FieldVariableGradient & gradSlnOld() const override; 364 : virtual const FieldVariableValue & slnNeighbor() const override; 365 : virtual const FieldVariableValue & slnOldNeighbor() const override; 366 : virtual const FieldVariableGradient & gradSlnNeighbor() const override; 367 : virtual const FieldVariableGradient & gradSlnOldNeighbor() const override; 368 : 369 : [[noreturn]] virtual const ADTemplateVariableSecond<OutputType> & adSecondSln() const override; 370 : [[noreturn]] virtual const ADTemplateVariableValue<OutputType> & adUDot() const override; 371 : [[noreturn]] virtual const ADTemplateVariableValue<OutputType> & adUDotDot() const override; 372 : [[noreturn]] virtual const ADTemplateVariableGradient<OutputType> & adGradSlnDot() const override; 373 : [[noreturn]] virtual const ADTemplateVariableValue<OutputType> & adSlnNeighbor() const override; 374 : [[noreturn]] virtual const ADTemplateVariableGradient<OutputType> & 375 : adGradSlnNeighbor() const override; 376 : [[noreturn]] virtual const ADTemplateVariableSecond<OutputType> & 377 : adSecondSlnNeighbor() const override; 378 : [[noreturn]] virtual const ADTemplateVariableValue<OutputType> & adUDotNeighbor() const override; 379 : [[noreturn]] virtual const ADTemplateVariableValue<OutputType> & 380 : adUDotDotNeighbor() const override; 381 : [[noreturn]] virtual const ADTemplateVariableGradient<OutputType> & 382 : adGradSlnNeighborDot() const override; 383 : [[noreturn]] virtual const ADTemplateVariableValue<OutputType> & adSln() const override; 384 : [[noreturn]] virtual const ADTemplateVariableGradient<OutputType> & adGradSln() const override; 385 : [[noreturn]] virtual const ADTemplateVariableCurl<OutputType> & adCurlSln() const override; 386 : [[noreturn]] virtual const ADTemplateVariableCurl<OutputType> & 387 : adCurlSlnNeighbor() const override; 388 : 389 : virtual const DoFValue & dofValues() const override; 390 : virtual const DoFValue & dofValuesOld() const override; 391 : 392 : virtual const DoFValue & dofValuesOlder() const override; 393 : virtual const DoFValue & dofValuesPreviousNL() const override; 394 : virtual const DoFValue & dofValuesNeighbor() const override; 395 : virtual const DoFValue & dofValuesOldNeighbor() const override; 396 : virtual const DoFValue & dofValuesOlderNeighbor() const override; 397 : virtual const DoFValue & dofValuesPreviousNLNeighbor() const override; 398 : [[noreturn]] virtual const DoFValue & dofValuesDot() const override; 399 : [[noreturn]] virtual const DoFValue & dofValuesDotNeighbor() const override; 400 : [[noreturn]] virtual const DoFValue & dofValuesDotOld() const override; 401 : [[noreturn]] virtual const DoFValue & dofValuesDotOldNeighbor() const override; 402 : [[noreturn]] virtual const DoFValue & dofValuesDotDot() const override; 403 : [[noreturn]] virtual const DoFValue & dofValuesDotDotNeighbor() const override; 404 : [[noreturn]] virtual const DoFValue & dofValuesDotDotOld() const override; 405 : [[noreturn]] virtual const DoFValue & dofValuesDotDotOldNeighbor() const override; 406 : [[noreturn]] virtual const MooseArray<libMesh::Number> & dofValuesDuDotDu() const override; 407 : [[noreturn]] virtual const MooseArray<libMesh::Number> & 408 : dofValuesDuDotDuNeighbor() const override; 409 : [[noreturn]] virtual const MooseArray<libMesh::Number> & dofValuesDuDotDotDu() const override; 410 : [[noreturn]] virtual const MooseArray<libMesh::Number> & 411 : dofValuesDuDotDotDuNeighbor() const override; 412 : 413 : [[noreturn]] virtual const MooseArray<ADReal> & adDofValues() const override; 414 : [[noreturn]] virtual const MooseArray<ADReal> & adDofValuesNeighbor() const override; 415 : [[noreturn]] virtual const MooseArray<ADReal> & adDofValuesDot() const override; 416 : [[noreturn]] virtual const dof_id_type & nodalDofIndex() const override final; 417 : [[noreturn]] virtual const dof_id_type & nodalDofIndexNeighbor() const override final; 418 : 419 0 : virtual std::size_t phiSize() const override final { return _phi.size(); } 420 0 : virtual std::size_t phiFaceSize() const override final { return _phi_face.size(); } 421 0 : virtual std::size_t phiNeighborSize() const override final { return _phi_neighbor.size(); } 422 0 : virtual std::size_t phiFaceNeighborSize() const override final 423 : { 424 0 : return _phi_face_neighbor.size(); 425 : } 426 : [[noreturn]] virtual std::size_t phiLowerSize() const override final; 427 : }; 428 : 429 : template <typename OutputType> 430 : typename MooseLinearVariableFV<OutputType>::ValueType 431 21290 : MooseLinearVariableFV<OutputType>::evaluate(const ElemArg & elem_arg, const StateArg & state) const 432 : { 433 21290 : const auto & elem_info = this->_mesh.elemInfo(elem_arg.elem->id()); 434 42580 : return getElemValue(elem_info, state); 435 : } 436 : 437 : template <typename OutputType> 438 : typename MooseLinearVariableFV<OutputType>::ValueType 439 0 : MooseLinearVariableFV<OutputType>::evaluate(const ElemPointArg & elem_point, 440 : const StateArg & state) const 441 : { 442 0 : const auto & elem_info = this->_mesh.elemInfo(elem_point.elem->id()); 443 0 : return getElemValue(elem_info, state); 444 : } 445 : 446 : template <typename OutputType> 447 : typename MooseLinearVariableFV<OutputType>::ValueType 448 254802 : MooseLinearVariableFV<OutputType>::evaluate(const ElemQpArg & elem_qp, const StateArg & state) const 449 : { 450 254802 : const auto & elem_info = this->_mesh.elemInfo(elem_qp.elem->id()); 451 509604 : return getElemValue(elem_info, state); 452 : } 453 : 454 : template <typename OutputType> 455 : typename MooseLinearVariableFV<OutputType>::ValueType 456 0 : MooseLinearVariableFV<OutputType>::evaluate(const ElemSideQpArg & elem_side_qp, 457 : const StateArg & state) const 458 : { 459 0 : return (*this)(ElemPointArg{elem_side_qp.elem, elem_side_qp.point, false}, state); 460 : } 461 : 462 : template <typename OutputType> 463 : typename MooseLinearVariableFV<OutputType>::GradientType 464 1600 : MooseLinearVariableFV<OutputType>::evaluateGradient(const ElemQpArg & qp_arg, 465 : const StateArg & /*state*/) const 466 : { 467 1600 : const auto & elem_info = this->_mesh.elemInfo(qp_arg.elem->id()); 468 3200 : return gradSln(elem_info); 469 : } 470 : 471 : template <typename OutputType> 472 : typename MooseLinearVariableFV<OutputType>::GradientType 473 0 : MooseLinearVariableFV<OutputType>::evaluateGradient(const ElemArg & elem_arg, 474 : const StateArg & /*state*/) const 475 : { 476 0 : const auto & elem_info = this->_mesh.elemInfo(elem_arg.elem->id()); 477 0 : return gradSln(elem_info); 478 : } 479 : 480 : template <typename OutputType> 481 : typename MooseLinearVariableFV<OutputType>::GradientType 482 160 : MooseLinearVariableFV<OutputType>::evaluateGradient(const FaceArg & face, 483 : const StateArg & state) const 484 : { 485 : mooseAssert(face.fi, "We must have a non-null face information"); 486 320 : return gradSln(*face.fi, state); 487 : } 488 : 489 : template <typename OutputType> 490 : void 491 0 : MooseLinearVariableFV<OutputType>::timeIntegratorError() const 492 : { 493 0 : mooseError("MooseLinearVariableFV does not support time integration at the moment! The variable " 494 : "which is causing the issue: ", 495 0 : this->name()); 496 : } 497 : 498 : template <typename OutputType> 499 : void 500 0 : MooseLinearVariableFV<OutputType>::lowerDError() const 501 : { 502 0 : mooseError("Lower dimensional element support not implemented for finite volume variables!The " 503 : "variable which is causing the issue: ", 504 0 : this->name()); 505 : } 506 : 507 : template <typename OutputType> 508 : void 509 0 : MooseLinearVariableFV<OutputType>::nodalError() const 510 : { 511 0 : mooseError("FV variables don't support nodal variable treatment! The variable which is causing " 512 : "the issue: ", 513 0 : this->name()); 514 : } 515 : 516 : template <typename OutputType> 517 : void 518 0 : MooseLinearVariableFV<OutputType>::adError() const 519 : { 520 0 : mooseError("Linear FV variable does not support automatic differentiation, the variable which is " 521 : "attempting it is: ", 522 0 : this->name()); 523 : } 524 : 525 : // Declare all the specializations, as the template specialization declarations below must know 526 : template <> 527 : ADReal MooseLinearVariableFV<Real>::evaluateDot(const ElemArg & elem, const StateArg & state) const; 528 : 529 : // Prevent implicit instantiation in other translation units where these classes are used 530 : extern template class MooseLinearVariableFV<Real>;