diff --git a/applications/solvers/lagrangian/reactingParcelFoam/Allwmake b/applications/solvers/lagrangian/reactingParcelFoam/Allwmake index ecd3f260150d6169af78e88562a5bf3e87487aa8..f615df216c2c4087951cbcf947d83060f0ce8488 100755 --- a/applications/solvers/lagrangian/reactingParcelFoam/Allwmake +++ b/applications/solvers/lagrangian/reactingParcelFoam/Allwmake @@ -3,6 +3,7 @@ cd ${0%/*} || exit 1 # run from this directory set -x wmake +wmake simpleReactingParcelFoam wmake LTSReactingParcelFoam # ----------------------------------------------------------------- end-of-file diff --git a/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/EEqn.H b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/EEqn.H new file mode 100644 index 0000000000000000000000000000000000000000..d4d686e35569c6ea2d4151a455998a1f62ea581f --- /dev/null +++ b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/EEqn.H @@ -0,0 +1,32 @@ +{ + volScalarField& he = thermo.he(); + + fvScalarMatrix EEqn + ( + mvConvection->fvmDiv(phi, he) + + ( + he.name() == "e" + ? fvc::div(phi, volScalarField("Ekp", 0.5*magSqr(U) + p/rho)) + : fvc::div(phi, volScalarField("K", 0.5*magSqr(U))) + ) + - fvm::laplacian(turbulence->alphaEff(), he) + == + parcels.Sh(he) + + radiation->Sh(thermo) + + combustion->Sh() + + fvOptions(rho, he) + ); + + EEqn.relax(); + + fvOptions.constrain(EEqn); + + EEqn.solve(); + + fvOptions.correct(he); + thermo.correct(); + radiation->correct(); + + Info<< "T gas min/max = " << min(T).value() << ", " + << max(T).value() << endl; +} diff --git a/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/Make/files b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/Make/files new file mode 100644 index 0000000000000000000000000000000000000000..4a202fcd4df960c5f67830593c89222b6211409a --- /dev/null +++ b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/Make/files @@ -0,0 +1,3 @@ +simpleReactingParcelFoam.C + +EXE = $(FOAM_APPBIN)/simpleReactingParcelFoam diff --git a/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/Make/options b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/Make/options new file mode 100644 index 0000000000000000000000000000000000000000..705cfc9433f4f9e47764f0f7d26e59cb0d82ff2c --- /dev/null +++ b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/Make/options @@ -0,0 +1,53 @@ +EXE_INC = \ + -I$(LIB_SRC)/finiteVolume/lnInclude \ + -I${LIB_SRC}/meshTools/lnInclude \ + -I$(LIB_SRC)/turbulenceModels/compressible/turbulenceModel \ + -I$(LIB_SRC)/lagrangian/basic/lnInclude \ + -I$(LIB_SRC)/lagrangian/intermediate/lnInclude \ + -I$(LIB_SRC)/lagrangian/coalCombustion/lnInclude \ + -I$(LIB_SRC)/lagrangian/distributionModels/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/specie/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/basic/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/properties/liquidProperties/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/properties/liquidMixtureProperties/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/properties/solidProperties/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/properties/solidMixtureProperties/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/thermophysicalFunctions/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/reactionThermo/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/SLGThermo/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/chemistryModel/lnInclude \ + -I$(LIB_SRC)/thermophysicalModels/radiationModels/lnInclude \ + -I$(LIB_SRC)/ODE/lnInclude \ + -I$(LIB_SRC)/regionModels/regionModel/lnInclude \ + -I$(LIB_SRC)/regionModels/surfaceFilmModels/lnInclude \ + -I$(LIB_SRC)/combustionModels/lnInclude \ + -I$(LIB_SRC)/fvOptions/lnInclude \ + -I$(LIB_SRC)/sampling/lnInclude \ + -I$(FOAM_SOLVERS)/combustion/reactingFoam + + +EXE_LIBS = \ + -lfiniteVolume \ + -lmeshTools \ + -lcompressibleTurbulenceModel \ + -lcompressibleRASModels \ + -lcompressibleLESModels \ + -llagrangian \ + -llagrangianIntermediate \ + -lspecie \ + -lfluidThermophysicalModels \ + -lliquidProperties \ + -lliquidMixtureProperties \ + -lsolidProperties \ + -lsolidMixtureProperties \ + -lthermophysicalFunctions \ + -lreactionThermophysicalModels \ + -lSLGThermo \ + -lchemistryModel \ + -lradiationModels \ + -lODE \ + -lregionModels \ + -lsurfaceFilmModels \ + -lcombustionModels \ + -lfvOptions \ + -lsampling diff --git a/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/UEqn.H b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/UEqn.H new file mode 100644 index 0000000000000000000000000000000000000000..eabbb40454739032efbe679f92e2f69985cf9852 --- /dev/null +++ b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/UEqn.H @@ -0,0 +1,17 @@ + tmp<fvVectorMatrix> UEqn + ( + fvm::div(phi, U) + + turbulence->divDevRhoReff(U) + == + rho.dimensionedInternalField()*g + + parcels.SU(U) + + fvOptions(rho, U) + ); + + UEqn().relax(); + + fvOptions.constrain(UEqn()); + + solve(UEqn() == -fvc::grad(p)); + + fvOptions.correct(U); diff --git a/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/YEqn.H b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/YEqn.H new file mode 100644 index 0000000000000000000000000000000000000000..cd0a45f0f020295bb6341f345e109b2999465471 --- /dev/null +++ b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/YEqn.H @@ -0,0 +1,53 @@ +tmp<fv::convectionScheme<scalar> > mvConvection +( + fv::convectionScheme<scalar>::New + ( + mesh, + fields, + phi, + mesh.divScheme("div(phi,Yi_h)") + ) +); + +{ + combustion->correct(); + dQ = combustion->dQ(); + label inertIndex = -1; + volScalarField Yt(0.0*Y[0]); + + forAll(Y, i) + { + if (Y[i].name() != inertSpecie) + { + volScalarField& Yi = Y[i]; + + fvScalarMatrix YEqn + ( + mvConvection->fvmDiv(phi, Yi) + - fvm::laplacian(turbulence->muEff(), Yi) + == + parcels.SYi(i, Yi) + + combustion->R(Yi) + + fvOptions(rho, Yi) + ); + + YEqn.relax(); + + fvOptions.constrain(YEqn); + + YEqn.solve(mesh.solver("Yi")); + + fvOptions.correct(Yi); + + Yi.max(0.0); + Yt += Yi; + } + else + { + inertIndex = i; + } + } + + Y[inertIndex] = scalar(1) - Yt; + Y[inertIndex].max(0.0); +} diff --git a/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/createClouds.H b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/createClouds.H new file mode 100644 index 0000000000000000000000000000000000000000..954b74e069f5463683ba0941a1f2818a5258e9fc --- /dev/null +++ b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/createClouds.H @@ -0,0 +1,9 @@ +Info<< "\nConstructing reacting cloud" << endl; +basicReactingMultiphaseCloud parcels +( + "reactingCloud1", + rho, + U, + g, + slgThermo +); diff --git a/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/createFields.H b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/createFields.H new file mode 100644 index 0000000000000000000000000000000000000000..d6df24cb48db47b198ce034055c0a656b0bac387 --- /dev/null +++ b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/createFields.H @@ -0,0 +1,98 @@ + Info<< "Creating combustion model\n" << endl; + + autoPtr<combustionModels::rhoCombustionModel> combustion + ( + combustionModels::rhoCombustionModel::New(mesh) + ); + + rhoReactionThermo& thermo = combustion->thermo(); + thermo.validate(args.executable(), "h", "e"); + + SLGThermo slgThermo(mesh, thermo); + + basicMultiComponentMixture& composition = thermo.composition(); + PtrList<volScalarField>& Y = composition.Y(); + + const word inertSpecie(thermo.lookup("inertSpecie")); + + if (!composition.contains(inertSpecie)) + { + FatalErrorIn(args.executable()) + << "Specified inert specie '" << inertSpecie << "' not found in " + << "species list. Available species:" << composition.species() + << exit(FatalError); + } + + volScalarField& p = thermo.p(); + const volScalarField& T = thermo.T(); + const volScalarField& psi = thermo.psi(); + + volScalarField rho + ( + IOobject + ( + "rho", + runTime.timeName(), + mesh, + IOobject::NO_READ, + IOobject::AUTO_WRITE + ), + thermo.rho() + ); + + Info<< "\nReading field U\n" << endl; + volVectorField U + ( + IOobject + ( + "U", + runTime.timeName(), + mesh, + IOobject::MUST_READ, + IOobject::AUTO_WRITE + ), + mesh + ); + + #include "compressibleCreatePhi.H" + + dimensionedScalar rhoMax(simple.dict().lookup("rhoMax")); + dimensionedScalar rhoMin(simple.dict().lookup("rhoMin")); + + Info<< "Creating turbulence model\n" << endl; + autoPtr<compressible::turbulenceModel> turbulence + ( + compressible::turbulenceModel::New + ( + rho, + U, + phi, + thermo + ) + ); + + // Set the turbulence into the combustion model + combustion->setTurbulence(turbulence()); + + Info<< "Creating multi-variate interpolation scheme\n" << endl; + multivariateSurfaceInterpolationScheme<scalar>::fieldTable fields; + + forAll(Y, i) + { + fields.add(Y[i]); + } + fields.add(thermo.he()); + + volScalarField dQ + ( + IOobject + ( + "dQ", + runTime.timeName(), + mesh, + IOobject::NO_READ, + IOobject::AUTO_WRITE + ), + mesh, + dimensionedScalar("dQ", dimEnergy/dimTime, 0.0) + ); diff --git a/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/pEqn.H b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/pEqn.H new file mode 100644 index 0000000000000000000000000000000000000000..0d1aa2e2387c3ad5d52c518414060634bbb2200b --- /dev/null +++ b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/pEqn.H @@ -0,0 +1,59 @@ +{ + rho = thermo.rho(); + + // Thermodynamic density needs to be updated by psi*d(p) after the + // pressure solution - done in 2 parts. Part 1: + thermo.rho() -= psi*p; + + volScalarField rAU(1.0/UEqn().A()); + volVectorField HbyA("HbyA", U); + HbyA = rAU*UEqn().H(); + + UEqn.clear(); + + surfaceScalarField phiHbyA + ( + "phiHbyA", + fvc::interpolate(rho)*(fvc::interpolate(HbyA) & mesh.Sf()) + ); + + fvOptions.relativeFlux(fvc::interpolate(rho), phiHbyA); + + while (simple.correctNonOrthogonal()) + { + fvScalarMatrix pEqn + ( + fvc::div(phiHbyA) + - fvm::laplacian(rho*rAU, p) + == + parcels.Srho() + + fvOptions(psi, p, rho.name()) + ); + + fvOptions.constrain(pEqn); + + pEqn.solve(); + + if (simple.finalNonOrthogonalIter()) + { + phi = phiHbyA + pEqn.flux(); + } + } + + p.relax(); + + // Second part of thermodynamic density update + thermo.rho() += psi*p; + + #include "compressibleContinuityErrs.H" + + U = HbyA - rAU*fvc::grad(p); + U.correctBoundaryConditions(); + fvOptions.correct(U); + + rho = thermo.rho(); + rho = max(rho, rhoMin); + rho = min(rho, rhoMax); + + Info<< "p min/max = " << min(p).value() << ", " << max(p).value() << endl; +} diff --git a/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/simpleReactingParcelFoam.C b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/simpleReactingParcelFoam.C new file mode 100644 index 0000000000000000000000000000000000000000..6620d2af52dfbb6a40bf811c3503132db7d75f89 --- /dev/null +++ b/applications/solvers/lagrangian/reactingParcelFoam/simpleReactingParcelFoam/simpleReactingParcelFoam.C @@ -0,0 +1,95 @@ +/*---------------------------------------------------------------------------*\ + ========= | + \\ / F ield | OpenFOAM: The Open Source CFD Toolbox + \\ / O peration | + \\ / A nd | Copyright (C) 2013 OpenFOAM Foundation + \\/ M anipulation | +------------------------------------------------------------------------------- +License + This file is part of OpenFOAM. + + OpenFOAM is free software: you can redistribute it and/or modify it + under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + OpenFOAM is distributed in the hope that it will be useful, but WITHOUT + ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + for more details. + + You should have received a copy of the GNU General Public License + along with OpenFOAM. If not, see <http://www.gnu.org/licenses/>. + +Application + simpleReactingParcelFoam + +Description + Steady state SIMPLE solver for compressible, laminar or turbulent flow with + reacting multiphase Lagrangian parcels, including run-time selectable + finite volume options, e.g. sources, constraints + +\*---------------------------------------------------------------------------*/ + +#include "fvCFD.H" +#include "turbulenceModel.H" +#include "basicReactingMultiphaseCloud.H" +#include "rhoCombustionModel.H" +#include "radiationModel.H" +#include "IOporosityModelList.H" +#include "fvIOoptionList.H" +#include "SLGThermo.H" +#include "simpleControl.H" + +// * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + +int main(int argc, char *argv[]) +{ + #include "setRootCase.H" + + #include "createTime.H" + #include "createMesh.H" + #include "readGravitationalAcceleration.H" + + simpleControl simple(mesh); + + #include "createFields.H" + #include "createRadiationModel.H" + #include "createClouds.H" + #include "createFvOptions.H" + #include "initContinuityErrs.H" + + // * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * // + + Info<< "\nStarting time loop\n" << endl; + + while (simple.loop()) + { + Info<< "Time = " << runTime.timeName() << nl << endl; + + parcels.evolve(); + + // --- Pressure-velocity SIMPLE corrector loop + { + #include "UEqn.H" + #include "YEqn.H" + #include "EEqn.H" + #include "pEqn.H" + } + + turbulence->correct(); + + runTime.write(); + + Info<< "ExecutionTime = " << runTime.elapsedCpuTime() << " s" + << " ClockTime = " << runTime.elapsedClockTime() << " s" + << nl << endl; + } + + Info<< "End\n" << endl; + + return(0); +} + + +// ************************************************************************* //