Merge pull request #142 from ParticulateFlow/release

Release 24.01
This commit is contained in:
Daniel
2024-01-23 16:35:05 +01:00
committed by GitHub
125 changed files with 3790 additions and 819 deletions

View File

@ -3,7 +3,7 @@
LIGGGHTS® - LAMMPS Improved for General Granular and Granular Heat Transfer Simulations - is a discrete element method (DEM) particle simulation software.
LIGGGHTS® is part of the [CFDEM®project](https://www.cfdem.com) and is based on the molecular dynamics simulation code [LAMMPS](https://lammps.sandia.gov/).
[![CircleCI](https://circleci.com/gh/ParticulateFlow/LIGGGHTS.svg?style=shield&circle-token=8905cdbf813717ce628dd05a454d0f7581110907)](https://circleci.com/gh/ParticulateFlow/LIGGGHTS)
[![CircleCI](https://circleci.com/gh/ParticulateFlow/LIGGGHTS.svg?style=shield&circle-token=4ca67fb317cf07f8794efaa7b37438f4886d5da3)](https://circleci.com/gh/ParticulateFlow/LIGGGHTS)
[![License: GPL v2](https://img.shields.io/badge/License-GPL%20v2-blue.svg)](https://www.gnu.org/licenses/old-licenses/gpl-2.0.en.html)
## Disclaimer

View File

@ -732,8 +732,9 @@ of each style or click on the style itself for a full description:
"chem/shrink/core"_fix_chem_shrink_core.html,
"colvars"_fix_colvars.html,
"couple/cfd/chemistry"_fix_cfd_coupling_chemistry.html,
"couple/cfd/dissolve"_fix_cfd_coupling_dissolve.html,
"couple/cfd/convection"_fix_cfd_coupling_convection.html,
"couple/cfd/deform"_fix_cfd_coupling_deform.html,
"couple/cfd/dissolve"_fix_cfd_coupling_dissolve.html,
"couple/cfd/fluidproperties"_fix_cfd_coupling_fluidproperties.html,
"couple/cfd/recurrence"_fix_cfd_coupling_recurrence.html,
"deform"_fix_deform.html,
@ -771,6 +772,8 @@ of each style or click on the style itself for a full description:
"lb/pc"_fix_lb_pc.html,
"lb/rigid/pc/sphere"_fix_lb_rigid_pc_sphere.html,
"lb/viscous"_fix_lb_viscous.html,
"limit/property/atom"_fix_limit_property_atom.html,
"limit/vel"_fix_limit_vel.html,
"lineforce"_fix_lineforce.html,
"massflow/mesh"_fix_massflow_mesh.html,
"massflow/mesh/face"_fix_massflow_mesh_face.html,

View File

@ -93,6 +93,9 @@ keyword = {acolor} or {adiam} or {amap} or {bcolor} or {bdiam} or {backcolor} or
R,G,B = red/green/blue numeric values from 0.0 to 1.0
{framerate} arg = fps
fps = frames per second for movie :pre
these keywords apply only to the {custom/vtk} "style"_dump_custom_vtk.html :l
keyword = {domainfile} :l
{domainfile} arg = {yes} or {no} :pre
:ule
[Examples:]
@ -636,6 +639,12 @@ frame rate higher than 24 is not recommended, as it will result in
simply dropping the rendered images. It is more efficient to dump
images less frequently.
:line
The {domainfile} keyword can be used with the "dump
custom/vtk"_dump_custom_vtk.html command to enable or disable the output of the
extra file describing the domain bounding box.
:line
:line
@ -678,7 +687,8 @@ bdiam = * 0.5
bitrate = 2000
boxcolor = yellow
color = 140 color names are pre-defined as listed below
framerate = 24 :ul
framerate = 24
domainfile = yes :ul
:line

View File

@ -0,0 +1,34 @@
"LIGGGHTS WWW Site"_liws - "LAMMPS WWW Site"_lws - "LIGGGHTS Documentation"_ld - "LIGGGHTS Commands"_lc :c
:link(liws,http://www.cfdem.com)
:link(lws,http://lammps.sandia.gov)
:link(ld,Manual.html)
:link(lc,Section_commands.html#comm)
:line
fix couple/cfd/convection command :h3
[Syntax:]
fix ID group-ID couple/cfd/convection keyword values :pre
ID, group-ID are documented in "fix"_fix.html command :ulb,l
couple/cfd/convection = style name of this fix command :l
zero or more keyword/value pairs may be appended :l
keyword = {T0} or {transfer_conduction} or {max_change} :l
{T0} value = initial temperature for new particles
{transfer_conduction} value = {yes} or {no} (default {no})
{max_change} value = maximum change of temperature per particle per time step :pre
:ule
[Examples:]
fix cfd1 all couple/cfd/convection T0 293 :pre
fix cfd2 all couple/cfd/convection T0 293 transfer_conduction yes :pre
fix cfd3 all couple/cfd/convection T0 293 max_change 0.1 :pre
[Description:]
This fix pulls data for convective (and optionally conductive, if modeled in a Eulerian fashion) heat fluxes for each particle from CFDEMcoupling and passes them to a scalar transport equation. The maximum change of temperature for each particle may be limited to enhance numerical stability.
This fix needs a fix couple/cfd before it is defined.

View File

@ -7,7 +7,7 @@
:line
fix cfd/coupling/deform command :h3
fix couple/cfd/deform command :h3
[Syntax:]
@ -15,13 +15,14 @@ fix ID group-ID couple/cfd/deform keyword values :pre
ID, group-ID are documented in "fix"_fix.html command :ulb,l
couple/cfd/deform = style name of this fix command :l
zero or more keyword/value pairs may be appended :l
keyword = {compress} or {verbose} or {rmin} or {monitor_heat} or {use_latent_heat} or {latent_heat} :l
keyword = {compress} or {verbose} or {rmin} or {monitor_heat} or {use_latent_heat} or {latent_heat} or {delete_fully_deformed_particles} :l
{compress} value = {yes} or {no}
{verbose} value = {yes} or {no}
{rmin} value = radius below which particles cannot deform
{monitor_heat} value = {yes} or {no}
{use_latent_heat} value = {yes} or {no}
{latent_heat} value = latent heat per kg that is required to remove a solid grain due to melting :pre
{latent_heat} value = latent heat per kg that is required to remove a solid grain due to melting
{delete_fully_deformed_particles} value = {yes} or {no} :pre
:ule
[Examples:]
@ -32,8 +33,8 @@ fix cfd3 all couple/cfd/deform rmin 0.01 monitor_heat yes use_latent_heat yes la
[Description:]
This fix pulls data between 0 and 1 for each particle from CFDEMcoupling describing the extent a grains deforms subject to some local field. 0 means no deformation, 1 means maximum deformation and > 1 means particle removal. The accumulated removed mass (and optionally heat) can be accessed analogously as for fix remove.
This fix pulls data between 0 and 1 for each particle from CFDEMcoupling describing the extent a grains deforms subject to some local field. 0 means no deformation and 1 means maximum deformation. If desired, a value of > 1 leads to particle removal. The accumulated removed mass (and optionally heat) can be accessed analogously as for fix remove.
If deformation is due to softening with increasing temperature, and particles can even melt and be removed from the simulation, it is possible to specify the latent heat that is required for this process. This option needs to be activated via {use_latent_heat} and the latent heat per mass specified via {latent_heat}. The value is defined with a positive sign.
If deformation is due to softening with increasing temperature, and particles can even melt and be removed from the simulation, it is possible to specify the latent heat that is required for this process. This option needs to be activated via {use_latent_heat} and the latent heat per mass specified via {latent_heat}. The value is defined with a positive sign. The option {delete_fully_deformed_particles} (default yes) determines if fully deformed particles are deleted from the simulation or not. In the latter case, they are assigned to a group called "fullyDeformed" which can be accessed by other fixes etc.
This fix needs a fix couple/cfd before it is defined.

View File

@ -14,7 +14,7 @@ fix couple/cfd/fluidproperties command :h3
fix ID group-ID couple/cfd/fluidproperties :pre
ID, group-ID are documented in "fix"_fix.html command :ulb,l
couple/cfd/dissolve = style name of this fix command :l
couple/cfd/fluidproperties = style name of this fix command :l
:ule
[Examples:]

View File

@ -7,7 +7,7 @@
:line
fix cfd/coupling/recurrence command :h3
fix couple/cfd/recurrence command :h3
[Syntax:]

View File

@ -88,7 +88,7 @@ group-ID the fixes apply to.
fix porosity all property/global porosity_all vector 0.61 0.31 0.16 0.15
fix tortuosity all property/global tortuosity_all scalar 3
fix pore_diameter all property/global pore_diameter_all scalar 5.5e-7
fix pore_diameter all property/global pore_diameter_all vector 3.e-07 1.5e-05 1.e-05
fix density all property/global density_all vector 7870. 5740. 5170. 5240. :pre
The initial relative layer radii also need to be specified via a

View File

@ -16,7 +16,7 @@ ID, group-ID are documented in "fix"_fix.html command :ulb,l
execute = style name of this fix command :l
N = execute every N steps :l
string = text string to be executed with optional variable names :l
keyword = none or {once} or {conditional} or {file} :l
keyword = none or {once} or {conditional} or {file} or {start_of_step}:l
{conditional} value = variable name, target value, tolerance
variable name = variable that triggers execution, needs to be defined beforehand in the input script
target value = value of variable at which fix is executed
@ -34,7 +34,7 @@ fix ex3 all execute 100 "../DEM/in.subfunctions" file :pre
Executes a text string as LIGGGHTS command every N steps during a simulation run. This can
be used for coupled simulations that would otherwise only take a given number of timesteps. If the "once" keyword is specified,
the command is executed only once at time step N. The "conditional" keyword allows to specify a variable which triggers the execution of the fix if it holds the desired value. If the "file" keyword is present, LIGGGHTS looks for an input script with the name of the string to be executed.
the command is executed only once at time step N. The "conditional" keyword allows to specify a variable which triggers the execution of the fix if it holds the desired value. If the "file" keyword is present, LIGGGHTS looks for an input script with the name of the string to be executed. "start_of_step" executes the command at the beginning of the timestep whereas per default it is executed at the end.
[Restart, fix_modify, output, run start/stop, minimize info:]

View File

@ -0,0 +1,45 @@
"LIGGGHTS WWW Site"_liws - "LAMMPS WWW Site"_lws - "LIGGGHTS Documentation"_ld - "LIGGGHTS Commands"_lc :c
:link(liws,http://www.cfdem.com)
:link(lws,http://lammps.sandia.gov)
:link(ld,Manual.html)
:link(lc,Section_commands.html#comm)
:line
fix limit/property/atom command :h3
[Syntax:]
fix ID group-ID limit/property/atom targetfixname min min_value(s) max max_value(s) :pre
ID, group-ID are documented in "fix"_fix.html command :ulb,l
limit/property/atom = style name of this fix command :l
targetfixname = name of the fix/property/atom to be limited :l
min_value(s) = list of lower limiting values :l
max_value(s) = list of upper limiting values :l
:ule
[Examples:]
fix limT all limit/property/atom Temp min 250 max 350 :pre
[LIGGGHTS vs. LAMMPS Info:]
This LIGGGHTS command is not available in LAMMPS.
[Description:]
[Fix limit/property/atom] limits the values stored by a fix/property/atom from below and from above.
Note that the group of atoms the fix is applied to is ignored.
[Restart, fix_modify, output, run start/stop, minimize info:] none
[Restrictions:] none
[Related commands:]
"fix_property"_fix_property.html
[Default:] none

View File

@ -17,7 +17,7 @@ ID is documented in "fix"_fix.html command, group-ID is ignored :ulb,l
move/mesh = style name of this fix command :l
mesh = obligatory keyword :l
mesh-ID = ID for the fix mesh that the fix move/mesh is applied to :l
style = {linear} or {linear/variable} or {wiggle} or {riggle} or {rotate} or {rotate/variable} or {viblin} or {vibrot} :l
style = {linear} or {linear/variable} or {wiggle} or {riggle} or {rotate} or {rotate/superposable} or {rotate/variable} or {viblin} or {vibrot} :l
{linear} args = Vx Vy Vz
Vx,Vy,Vz = components of velocity vector (velocity units)
{linear/variable} args = var_Vx var_Vy var_Vz
@ -42,6 +42,12 @@ style = {linear} or {linear/variable} or {wiggle} or {riggle} or {rotate} or {ro
ax,ay,az = axis of rotation vector (distance units)
period = obligatory keyword
per = period of rotation (time units)
{rotate/superposable} args = origin Px Py Pz axis ax ay az period per
origin = obligatory keyword
Px,Py,Pz = origin point of axis of rotation (distance units)
ax,ay,az = axis of rotation vector (distance units)
period = obligatory keyword
per = period of rotation (time units)
{rotate/variable} args = origin Px Py Pz axis ax ay az omega var_omega
origin = obligatory keyword
Px,Py,Pz = origin point of axis of rotation (distance units)
@ -132,6 +138,13 @@ around the rotation axis is consistent with the right-hand rule:
if your right-hand's thumb points along {R}, then your fingers
wrap around the axis in the direction of rotation.
The {rotate/superposable} style is similar to the {rotate} style. The input
syntax is identical. The difference to the {rotate} style lies in the
internal workings of this style. The axis of rotation is made a property
of the mesh, i.e., when super-imposing rotations, the axis is rotated
accordingly. This style allows for a more general superposition of mesh
rotations.
The {rotate/variable} style does the same as the {rotate} style,
but uses a variable for the angular velocity so that the angular
velocity can be time-dependent.

View File

@ -12,7 +12,7 @@ fix property/atom command :h3
[Syntax:]
fix id group property/atom variablename style restartvalue comm_ghost_value comm_reverse_ghost_value defaultvalue(s)...
fix id group property/atom variablename style restartvalue comm_ghost_value comm_reverse_ghost_value (store_old_time_value) defaultvalue(s)...
fix id group property/global variablename style stylearg defaultvalue(s)... :pre
ID, group-ID are documented in "fix"_fix.html command :ulb,l
@ -36,6 +36,7 @@ fix property/atom:
restartvalue = yes or no :l
communicate_ghost_value = yes or no :l
communicate_reverse_ghost_value = yes or no :l
store_old_time_value = 'yes' or 'no' (optional) :l
:ule
[Examples:]
@ -64,6 +65,8 @@ when this happens depends on the model that uses this fix.
Keyword {communicate_reverse_ghost_value} determines whether information about the values stored by this fix
can be communicated from ghost particles to owned particles (reverse communication). The exact location
during a time-step when this happens depends on the model that uses this fix.
Keyword {store_old_time_value} allows to activate storage of the previous time step values, which might be
necessary to evalulate time derivatives. This keyword need not be specified and is set to {false} per default.
[Fix property/global] reserves global properties to be accessed by the user or other
fixes or pair styles. The number of defaultvalues determines the length of the vector /

View File

@ -13,7 +13,7 @@ fix scale/diameter command :h3
fix ID group-ID scale/diameter N keyword value ... :pre
ID, group-ID are documented in "fix"_fix.html command :ulb,l
adapt = style name of this fix command :l
scale/diameter = style name of this fix command :l
N = scale diameter every this many timesteps :l
region = obligatory keyword :l
region_value = ID of a spherical or cylindrical "region"_region.html where the particles will be scaled :l

View File

@ -26,8 +26,9 @@ Fixes :h1
fix_break_particle
fix_buoyancy
fix_cfd_coupling_chemistry
fix_cfd_coupling_dissolve
fix_cfd_coupling_convection
fix_cfd_coupling_deform
fix_cfd_coupling_dissolve
fix_cfd_coupling_fluidproperties
fix_cfd_coupling_recurrence
fix_check_timestep_gran
@ -66,6 +67,7 @@ Fixes :h1
fix_lb_pc
fix_lb_rigid_pc_sphere
fix_lb_viscous
fix_limit_property_atom
fix_limit_vel
fix_lineforce
fix_massflow_mesh

View File

@ -23,8 +23,8 @@ is not available in LAMMPS.
In this granular model, the tangential contact force is calculated in the same manner
as in "tangential history"_gran_tangential_history.html. This model is to be used in
conjunction with the normal model "hertz/lubricated"_gran_hertz_lubricated.html, and
will throw errors without it.
conjunction with the normal model "hertz/lubricated"_gran_model_hertz_lubricated.html,
and will throw errors without it.
The coefficient of friction is selected from the dry or the lubricated value, depending
on the minimum approach distance between particle surfaces.

View File

@ -20,9 +20,11 @@ keyword = {type} or {type/fraction} or {mol} or {x} or {y} or {z} or \
{charge} or {dipole} or {dipole/random} or {quat} or \
{quat/random} or {diameter} or {shape} or \
{length} or {tri} or {theta} or {angmom} or \
{mass} or {density} or {volume} or {image} or
{bond} or {angle} or {dihedral} or {improper} or
{meso_e} or {meso_cv} or {meso_rho} or {property/atom} :l
{mass} or {density} or {volume} or {image} or \
{bond} or {angle} or {dihedral} or {improper} or \
{meso_e} or {meso_cv} or {meso_rho} or {property/atom} or \
{vx} or {vy} or {vz} or {omegax} or {omegay} or {omegaz} or \
{blockiness} or {aspect_ratio} or {inertiax} or {inertiay} or {inertiaz} :l
{type} value = atom type
value can be an atom-style variable (see below)
{type/fraction} values = type fraction seed
@ -79,16 +81,25 @@ keyword = {type} or {type/fraction} or {mol} or {x} or {y} or {z} or \
value can be an atom-style variable (see below)
{meso_cv} value = heat capacity of SPH particles (need units)
value can be an atom-style variable (see below)
{meso_rho} value = density of SPH particles (need units)
{meso_rho} value = density of SPH particles (need units)
value can be an atom-style variable (see below)
{add} value = yes no
{add} value = yes no
yes = add per-atom quantities to a region or a group
{until} value = final timestep
final timestep = the final timestep value until which the per-atom quantity is to be added
{property/atom} value = varname var_value[0] var_value[1] ....
{property/atom} values = varname var_value[0] var_value[1] ...
varname = name of the variable to be set
var_value[0], var_value[1]... = values of the property to be set.
value can be an atom-style variable (see below) :pre
var_value[0], var_value[1] ... = values of the property to be set.
value can be an atom-style variable (see below)
{vx},{vy},{vz} value = atom velocity (velocity units)
value can be an atom-style variable (see below)
{omegax},{omegay},{omegaz} value = angular velocity (rad / time units)
value can be an atom-style variable (see below)
{blockiness} values = n1 n2
n1, n2 = superquadric blockiness parameters, greater than or equal to 2
{aspect_ratio} values = ky kz
ky, kz = aspect ratio of a superquadric particle in y and z directions with respect to that in x direction (in principal coordinates). Particle blockiness and volume equivalent diameter must be set first
{inertiax},{inertiay},{inertiaz} value = principal moments of inertia for superquadric particles (distance^2 mass units) :pre
:ule
[Examples:]
@ -100,13 +111,13 @@ set region half charge 0.5
set type 3 charge 0.5
set type 1*3 charge 0.5
set atom 100*200 x 0.5 y 1.0
set atom 1492 type 3
set region reg add yes until 1000 property/atom liqOnParticle 5e-5
set atom 1492 type 3
set region reg add yes until 1000 property/atom liqOnParticle 5e-5
set group all property/atom Temp 273.15 :pre
[LIGGGHTS vs. LAMMPS Info:]
This command offers a new keyword property/atom to enable the
This command offers a new keyword property/atom to enable the
set command to assign values to properties defined by a "fix property/atom"_fix_property.html
[Description:]
@ -361,21 +372,23 @@ capacity, and density of smoothed particle hydrodynamics (SPH)
particles. See "this PDF guide"_USER/sph/SPH_LAMMPS_userguide.pdf to
using SPH in LAMMPS.
Keyword {property/atom} can update per-particle properties defined by
a "fix property/atom"_fix_property.html command. varname is the name of
the variable you want to set, it is followed by the values that should
be assigned to this variable. The number of values provided as
var_value[i] must correspond to the number of values needed for the
update, i.e. only var_value[0] if the defined property is a scalar,
and the appropriate number if the property is a vector. See
"fix property/atom"_fix_property.html for details on how to define
Keyword {property/atom} can update per-particle properties defined by
a "fix property/atom"_fix_property.html command. varname is the name of
the variable you want to set, it is followed by the values that should
be assigned to this variable. The number of values provided as
var_value[i] must correspond to the number of values needed for the
update, i.e. only var_value[0] if the defined property is a scalar,
and the appropriate number if the property is a vector. See
"fix property/atom"_fix_property.html for details on how to define
such a per-particle property.
Keyword {add} and {until} are used to add a per-atom quantity (or property)
in addition to the keyword {property/atom}. The {add} keyword is used to turn on
the addition of a quantity in a region or a group
in addition to the keyword {property/atom}. The {add} keyword is used to turn on
the addition of a quantity in a region or a group
until the timestep defined by the {until} keyword.
Keywords {shape} and {blockiness} define the superquadric shape of a particle.
[Restrictions:]
You cannot set an atom attribute (e.g. {mol} or {q} or {volume}) if

View File

@ -93,10 +93,10 @@ fix Ea_CO2 all property/global Ea_cfd52 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity4 all property/global porosity_cg4group vector 0.61 0.31 0.16 0.15
fix tortuosity4 all property/global tortuosity_cg4group scalar 3
fix pore_diameter4 all property/global pore_diameter_cg4group scalar 5.5e-7
fix pore_diameter4 all property/global pore_diameter_cg4group vector 5.5e-7 5.5e-7 5.5e-7
fix porosity2 all property/global porosity_cg2group vector 0.61 0.31 0.16 0.15
fix tortuosity2 all property/global tortuosity_cg2group scalar 3
fix pore_diameter2 all property/global pore_diameter_cg2group scalar 5.5e-7
fix pore_diameter2 all property/global pore_diameter_cg2group vector 5.5e-7 5.5e-7 5.5e-7
# define layer properties
fix LayerRelRadii all property/atom relRadii vector yes no no 1.0 0.998 0.995 0.98

View File

@ -88,7 +88,7 @@ fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.61 0.31 0.16 0.15
fix tortuosity all property/global tortuosity_all scalar 3
fix pore_diameter all property/global pore_diameter_all scalar 5.5e-7
fix pore_diameter all property/global pore_diameter_all vector 5.5e-7 5.5e-7 5.5e-7
# define layer properties
fix LayerRelRadii all property/atom relRadii vector yes no no 1.0 0.998 0.995 0.98

View File

@ -79,7 +79,7 @@ fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.61 0.31 0.16 0.15
fix tortuosity all property/global tortuosity_all scalar 3
fix pore_diameter all property/global pore_diameter_all scalar 5.5e-7
fix pore_diameter all property/global pore_diameter_all vector 5.5e-7 5.5e-7 5.5e-7
# define layer properties
fix LayerRelRadii all property/atom relRadii vector yes no no 1.0 0.998 0.995 0.98

View File

@ -0,0 +1,50 @@
36.8556 10.4008 16.2552 10.434
26.5761 9.54421 17.9684 9.81478
17.1532 9.54421 21.395 8.92069
34.2857 9.54421 26.5347 8.45937
46.2785 12.1141 20.5383 7.31974
25.7195 8.68758 28.248 7.28422
14.5833 7.83095 29.9612 6.43447
42.852 7.83095 25.6781 6.19172
8.58691 8.68758 23.9648 5.85956
29.146 12.1141 8.54554 5.77566
31.7158 6.97433 34.2444 5.37241
20.5797 6.97433 33.3877 5.22549
24.0062 15.5406 10.2588 5.13666
37.7122 6.1177 34.2444 4.73175
18.8664 14.684 13.6853 4.66912
25.7195 6.1177 35.101 4.44866
41.9954 13.8273 27.3913 4.41894
9.44353 14.684 20.5383 4.00812
33.4291 6.97433 6.83229 3.85622
7.73028 6.1177 29.9612 3.79948
30.8592 3.54782 11.1154 3.70243
35.1424 5.26107 38.5275 3.66942
44.5653 4.40444 20.5383 3.64039
52.2749 15.5406 17.1118 3.63813
47.1351 9.54421 13.6853 3.63644
29.146 17.2539 11.9721 3.58692
45.4219 18.1105 16.2552 3.5797
50.5616 18.1105 19.6817 3.41284
30.8592 5.26107 39.3841 3.37012
28.2893 15.5406 25.6781 3.36273
27.4327 5.26107 39.3841 3.32772
49.705 6.97433 24.8215 3.23261
19.7231 2.69119 16.2552 3.20584
41.9954 5.26107 31.6745 3.20311
3.44714 6.1177 25.6781 3.18808
46.2785 5.26107 17.1118 3.13116
22.2929 5.26107 38.5275 3.06026
41.1387 8.68758 31.6745 3.05632
14.5833 5.26107 35.9576 3.04383
23.1496 10.4008 8.54554 3.00958
20.5797 3.54782 27.3913 3.00137
39.4255 3.54782 29.9612 2.98994
39.4255 16.3972 24.8215 2.9567
39.4255 2.69119 23.1082 2.95111
11.1568 12.9707 27.3913 2.90849
10.3002 5.26107 34.2444 2.84552
45.4219 10.4008 10.2588 2.82964
20.5797 11.2575 10.2588 2.8207
24.0062 5.26107 41.0974 2.81971
14.5833 16.3972 15.3986 2.81899

View File

@ -0,0 +1,78 @@
# 3D periodic bin: measure mass flow of multispheres at 2 levels in the domain
atom_style granular
atom_modify map array sort 0 0
boundary f f p
newton off
communicate single vel yes
processors * 1 1
units si
region reg block -0.021 0.021 -0.021 0.021 0.0 0.2 units box
create_box 1 reg
neighbor 0.00025 bin
neigh_modify delay 0
# material properties required for pair style
fix m1 all property/global youngsModulus peratomtype 1.e8
fix m2 all property/global poissonsRatio peratomtype 0.35
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.9
fix m4 all property/global coefficientFriction peratomtypepair 1 0.5
# pair style
pair_style gran model hertz tangential history
pair_coeff * *
timestep 0.000001
# particle insertion
region ins_reg block -0.02 0.02 -0.02 0.02 0.005 0.195 units box
fix pts1 all particletemplate/multisphere 1 atom_type 1 density constant 2500 nspheres 50 ntry 1000000 spheres file data/stone1.multisphere scale 0.0005 type 1
fix pdd1 all particledistribution/discrete 127981 1 pts1 1.0
fix ins all insert/pack seed 100001 distributiontemplate pdd1 vel constant 0. 0. -0.5 &
insert_every once overlapcheck yes region ins_reg ntry_mc 10000 volumefraction_region 0.04
# integrator
fix integr all multisphere
# surface mesh for mass flow measurement
fix surface_mf1 all mesh/surface file meshes/massflow.stl type 1 scale 1.0 move 0.0 0.0 0.110
fix surface_mf2 all mesh/surface file meshes/massflow.stl type 1 scale 1.0 move 0.0 0.0 0.002
# mass flow measurement
# count particles only once, define outside by 3D point 'on the outside'
fix massflow1 all massflow/mesh mesh surface_mf1 count once point_at_outlet 0.0 0.0 0.0 file post/massflow1_particle_data.txt
fix massflow2 all massflow/mesh mesh surface_mf2 count once point_at_outlet 0.0 0.0 0.0 file post/massflow2_particle_data.txt
variable time equal step*dt # current simulation time (step and dt are built-in variables)
variable m1 equal f_massflow1[1] # total mass that has crossed the mesh since simulation start
variable np1 equal f_massflow1[2] # total number of particles that have crossed the mesh since simulation start
variable mdot1 equal f_massflow1[3] # current mass flow
variable npdot1 equal f_massflow1[4] # current particle flow rate
variable m2 equal f_massflow2[1] # total mass that has crossed the mesh since simulation start
variable np2 equal f_massflow2[2] # total number of particles that have crossed the mesh since simulation start
variable mdot2 equal f_massflow2[3] # current mass flow
variable npdot2 equal f_massflow2[4] # current particle flow rate
fix pmassout1 all print 5000 "${time} ${m1} ${np1} ${mdot1} ${npdot1}" screen no title "#t mass particles massflow particlerate" file post/massflow1.txt
fix pmassout2 all print 5000 "${time} ${m2} ${np2} ${mdot2} ${npdot2}" screen no title "#t mass particles massflow particlerate" file post/massflow2.txt
# output settings
thermo_style custom step atoms ke
thermo 2000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic yes
run 1
dump dmp all custom 2000 post/periodic_bin_ms_*.massflow id type radius mass x y z vx vy vz
run 200000 upto
write_restart post/restart/massflow_ms.restart

View File

@ -0,0 +1,74 @@
# 3D periodic bin: measure mass flow of multispheres at 2 levels in the domain
atom_style granular
atom_modify map array sort 0 0
boundary f f p
newton off
communicate single vel yes
processors * 1 1
units si
region reg block -0.021 0.021 -0.021 0.021 0.0 0.2 units box
read_restart post/restart/massflow_ms.restart
neighbor 0.00025 bin
neigh_modify delay 0
# material properties required for pair style
fix m1 all property/global youngsModulus peratomtype 1.e8
fix m2 all property/global poissonsRatio peratomtype 0.35
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.9
fix m4 all property/global coefficientFriction peratomtypepair 1 0.5
# pair style
pair_style gran model hertz tangential history
pair_coeff * *
timestep 0.000001
# particle insertion
region ins_reg block -0.02 0.02 -0.02 0.02 0.005 0.195 units box
fix pts1 all particletemplate/multisphere 1 atom_type 1 density constant 2500 nspheres 50 ntry 1000000 spheres file data/stone1.multisphere scale 0.0005 type 1
fix pdd1 all particledistribution/discrete 127981 1 pts1 1.0
fix ins all insert/pack seed 100001 distributiontemplate pdd1 vel constant 0. 0. -0.5 &
insert_every once overlapcheck yes region ins_reg ntry_mc 10000 volumefraction_region 0.04
# integrator
fix integr all multisphere
# surface mesh for mass flow measurement
fix surface_mf1 all mesh/surface file meshes/massflow.stl type 1 scale 1.0 move 0.0 0.0 0.110
fix surface_mf2 all mesh/surface file meshes/massflow.stl type 1 scale 1.0 move 0.0 0.0 0.002
# mass flow measurement
# count particles only once, define outside by 3D point 'on the outside'
fix massflow1 all massflow/mesh mesh surface_mf1 count once point_at_outlet 0.0 0.0 0.0 append post/massflow1_particle_data.txt
fix massflow2 all massflow/mesh mesh surface_mf2 count once point_at_outlet 0.0 0.0 0.0 append post/massflow2_particle_data.txt
variable time equal step*dt # current simulation time (step and dt are built-in variables)
variable m1 equal f_massflow1[1] # total mass that has crossed the mesh since simulation start
variable np1 equal f_massflow1[2] # total number of particles that have crossed the mesh since simulation start
variable mdot1 equal f_massflow1[3] # current mass flow
variable npdot1 equal f_massflow1[4] # current particle flow rate
variable m2 equal f_massflow2[1] # total mass that has crossed the mesh since simulation start
variable np2 equal f_massflow2[2] # total number of particles that have crossed the mesh since simulation start
variable mdot2 equal f_massflow2[3] # current mass flow
variable npdot2 equal f_massflow2[4] # current particle flow rate
fix pmassout1 all print 5000 "${time} ${m1} ${np1} ${mdot1} ${npdot1}" screen no title none append post/massflow1.txt
fix pmassout2 all print 5000 "${time} ${m2} ${np2} ${mdot2} ${npdot2}" screen no title none append post/massflow2.txt
# output settings
thermo_style custom step atoms ke
thermo 2000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic yes
dump dmp all custom 2000 post/periodic_bin_ms_*.massflow id type radius mass x y z vx vy vz
run 500000 upto

View File

@ -0,0 +1,39 @@
{
"runs": [
{
"name" : "periodic_massflow_mesh_ms",
"input_script" : "in.periodic_bin_flow_ms",
"type" : "serial",
"data" : {
"series" : [
{"name" : "massflow1", "file" : "massflow1.txt", "columns" : ["t", "mass", "particles", "massrate", "particlerate"]},
{"name" : "massflow2", "file" : "massflow2.txt", "columns" : ["t", "mass", "particles", "massrate", "particlerate"]}
],
"plots" : [
{"name" : "massflowmass", "title" : "Total Mass", "xdata" : "massflow1.t", "ydata" : ["massflow1.mass","massflow2.mass"], "xlabel" : "time [s]", "ylabel" : "mass [kg]", "legend" : ["upper plane","lower plane"]},
{"name" : "massflowparticles", "title" : "Total Particles", "xdata" : "massflow1.t", "ydata" : ["massflow1.particles","massflow2.particles"], "xlabel" : "time [s]", "ylabel" : "particles [-]", "legend" : ["upper plane","lower plane"]},
{"name" : "massflowmassrate", "title" : "Mass Flow Rate", "xdata" : "massflow1.t", "ydata" : ["massflow1.massrate","massflow2.massrate"], "xlabel" : "time [s]", "ylabel" : "mass flow rate [kg/s]", "legend" : ["upper plane","lower plane"]},
{"name" : "massflowparticlerate", "title" : "Particle Rate", "xdata" : "massflow1.t", "ydata" : ["massflow1.particlerate","massflow2.particlerate"], "xlabel" : "time [s]", "ylabel" : "particle rate [1/s]", "legend" : ["upper plane","lower plane"]}
]
}
},
{
"name" : "periodic_massflow_mesh_ms_restart",
"depends_on" : "periodic_massflow_mesh_ms",
"input_script": "in.periodic_bin_flow_ms_restart",
"type": "serial",
"data" : {
"series" : [
{"name" : "massflow1", "file" : "massflow1.txt", "columns" : ["t", "mass", "particles", "massrate", "particlerate"]},
{"name" : "massflow2", "file" : "massflow2.txt", "columns" : ["t", "mass", "particles", "massrate", "particlerate"]}
],
"plots" : [
{"name" : "massflowmass", "title" : "Total Mass", "xdata" : "massflow1.t", "ydata" : ["massflow1.mass","massflow2.mass"], "xlabel" : "time [s]", "ylabel" : "mass [kg]", "legend" : ["upper plane","lower plane"]},
{"name" : "massflowparticles", "title" : "Total Particles", "xdata" : "massflow1.t", "ydata" : ["massflow1.particles","massflow2.particles"], "xlabel" : "time [s]", "ylabel" : "particles [-]", "legend" : ["upper plane","lower plane"]},
{"name" : "massflowmassrate", "title" : "Mass Flow Rate", "xdata" : "massflow1.t", "ydata" : ["massflow1.massrate","massflow2.massrate"], "xlabel" : "time [s]", "ylabel" : "mass flow rate [kg/s]", "legend" : ["upper plane","lower plane"]},
{"name" : "massflowparticlerate", "title" : "Particle Rate", "xdata" : "massflow1.t", "ydata" : ["massflow1.particlerate","massflow2.particlerate"], "xlabel" : "time [s]", "ylabel" : "particle rate [1/s]", "legend" : ["upper plane","lower plane"]}
]
}
}
]
}

View File

@ -0,0 +1,95 @@
# Simple test with super-imposed rotations
variable dt equal 0.001
variable runSteps equal 1000
variable dumpsteps equal 5
atom_style granular
atom_modify map array
boundary m m m
newton off
communicate single vel yes
units si
processors 1 1 1
region reg block -1.5 3.5 -1.5 1.5 -1.5 2.0 units box
create_box 1 reg
neighbor 0.02 bin
neigh_modify delay 0
fix m1 all property/global youngsModulus peratomtype 5.e6
fix m2 all property/global poissonsRatio peratomtype 0.45
fix m3 all property/global coefficientRestitution &
peratomtypepair 1 0.3
fix m4 all property/global coefficientFriction &
peratomtypepair 1 0.5
pair_style gran model hertz tangential history
pair_coeff * *
timestep ${dt}
fix gravi all gravity 9.81 vector 0.0 0.0 -1.0
fix cad1 all mesh/surface file meshes/triMesh1.stl type 1
fix cad2 all mesh/surface file meshes/triMesh2.stl type 1
fix pts1 all particletemplate/sphere 1 atom_type 1 &
density constant 2500 &
radius constant 0.0015
fix pdd1 all particledistribution/discrete 1. 1 pts1 1
fix integr all nve/sphere
compute 1 all erotate/sphere
thermo_style custom step atoms ke c_1 cpu
thermo 1000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic yes
run 1
dump dmp all custom ${dumpsteps} post/dump*.rotatingChute &
id type type x y z ix iy iz vx vy vz fx fy fz &
omegax omegay omegaz radius
# Dump the meshes
dump dumpmesh1 all mesh/vtk ${dumpsteps} post/dumpMesh1_*.vtk cad1 vel
dump dumpmesh2 all mesh/vtk ${dumpsteps} post/dumpMesh2_*.vtk cad2 vel
variable period0 equal 1
variable period1 equal 0.1
# Rotation of the inner mesh
fix moveInner00 all move/mesh mesh cad1 rotate/superposable &
origin 0.0 0.0 0.0 &
axis 0.0 0.0 1.0 &
period ${period0}
# Rotation of the outer mesh
# the outer mesh is fixed to the tip of the inner mesh
# the outer mesh rotates around the local y-axis
# hence, the rotation of the inner mesh must be applied first
# then the rotation of the outer mesh relative to the inner mesh can be specified
fix moveOuter00 all move/mesh mesh cad2 rotate/superposable &
origin 0.0 0.0 0.0 &
axis 0.0 0.0 1.0 &
period ${period0}
fix moveOuter01 all move/mesh mesh cad2 rotate/superposable &
origin 1.0 0.0 0.0 &
axis 0.0 1.0 0.0 &
period ${period1}
run ${runSteps}
# ----------------------------------------------------------------- end-of-file

View File

@ -0,0 +1,9 @@
solid triMesh
facet normal 0 0 1
outer loop
vertex 0 0.1 0
vertex 1 0.0 0
vertex 0 -0.1 0
endloop
endfacet
endsolid triMesh

View File

@ -0,0 +1,9 @@
solid triMesh
facet normal 0 0 1
outer loop
vertex 1 0.1 -0.1
vertex 2 0.0 -0.1
vertex 1 -0.1 -0.1
endloop
endfacet
endsolid triMesh

View File

@ -0,0 +1 @@

View File

@ -0,0 +1,9 @@
{
"runs": [
{
"name" : "rotationSuperposable",
"input_script" : "in.rotationSuperposable",
"type" : "serial"
}
]
}

View File

@ -43,6 +43,9 @@ fix ftca all property/global thermalCapacity peratomtype 3000
################################################################################
# chemistry
# input fix for fix chem/shrink/core that would otherwise be provided by fix
# heat/gran or fix couple/cfd/convection or fix couple/cfd/parttempfield
fix Temp all property/atom Temp scalar yes yes no 1223.15 # Kelvin
# input fixes for fix chem/shrink/core that would otherwise be provided by fix
# couple/cfd/chemistry
fix partTemp all property/atom partTemp scalar yes no no 1223.15 # Kelvin
@ -75,7 +78,7 @@ fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.61 0.31 0.16 0.15
fix tortuosity all property/global tortuosity_all scalar 3
fix pore_diameter all property/global pore_diameter_all scalar 5.5e-7
fix pore_diameter all property/global pore_diameter_all vector 5.5e-7 5.5e-7 5.5e-7
# define layer properties
fix LayerRelRadii all property/atom relRadii vector yes no no 1.0 0.998 0.995 0.98

View File

@ -44,6 +44,9 @@ fix ftca all property/global thermalCapacity peratomtype 3000
################################################################################
# chemistry
# input fix for fix chem/shrink/core that would otherwise be provided by fix
# heat/gran or fix couple/cfd/convection or fix couple/cfd/parttempfield
fix Temp all property/atom Temp scalar yes yes no 1223.15 # Kelvin
# input fixes for fix chem/shrink/core that would otherwise be provided by fix
# couple/cfd/chemistry
fix partTemp all property/atom partTemp scalar yes no no 1223.15 # Kelvin
@ -76,7 +79,7 @@ fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.61 0.31 0.16 0.15
fix tortuosity all property/global tortuosity_all scalar 3
fix pore_diameter all property/global pore_diameter_all scalar 5.5e-7
fix pore_diameter all property/global pore_diameter_all vector 5.5e-7 5.5e-7 5.5e-7
# define layer properties
fix LayerRelRadii all property/atom relRadii vector yes no no 1.0 0.998 0.995 0.98

View File

@ -46,6 +46,9 @@ fix ftca all property/global thermalCapacity peratomtype 3000
################################################################################
# chemistry
# input fix for fix chem/shrink/core that would otherwise be provided by fix
# heat/gran or fix couple/cfd/convection or fix couple/cfd/parttempfield
fix Temp all property/atom Temp scalar yes yes no 1223.15 # Kelvin
# input fixes for fix chem/shrink/core that would otherwise be provided by fix
# couple/cfd/chemistry
fix partTemp all property/atom partTemp scalar yes no no 1223.15 # Kelvin
@ -80,7 +83,7 @@ fix Ea_CO_1 all property/global Ea_chem1 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity1 all property/global porosity_group1 vector 0.61 0.31 0.16 0.15
fix tortuosity1 all property/global tortuosity_group1 scalar 3
fix pore_diameter1 all property/global pore_diameter_group1 scalar 5.5e-7
fix pore_diameter1 all property/global pore_diameter_group1 vector 5.5e-7 5.5e-7 5.5e-7
# define fix for layer densities
fix LayerDensities1 all property/global density_group1 vector 7870. 5740. 5170. 5240.
@ -208,7 +211,7 @@ fix Ea_CO_2 all property/global Ea_chem2 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity2 all property/global porosity_group2 vector 0.61 0.31 0.16 0.15
fix tortuosity2 all property/global tortuosity_group2 scalar 3
fix pore_diameter2 all property/global pore_diameter_group2 scalar 1.1e-6
fix pore_diameter2 all property/global pore_diameter_group2 vector 1.1e-6 1.1e-6 1.1e-6
# define fix for layer densities
fix LayerDensities2 all property/global density_group2 vector 7870. 5740. 5170. 5240.

View File

@ -46,6 +46,9 @@ fix ftca all property/global thermalCapacity peratomtype 3000
################################################################################
# chemistry
# input fix for fix chem/shrink/core that would otherwise be provided by fix
# heat/gran or fix couple/cfd/convection or fix couple/cfd/parttempfield
fix Temp all property/atom Temp scalar yes yes no 1223.15 # Kelvin
# input fixes for fix chem/shrink/core that would otherwise be provided by fix
# couple/cfd/chemistry
fix partTemp all property/atom partTemp scalar yes no no 1223.15 # Kelvin
@ -80,7 +83,7 @@ fix Ea_CO_1 all property/global Ea_chem1 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity1 all property/global porosity_group1 vector 0.61 0.31 0.16 0.15
fix tortuosity1 all property/global tortuosity_group1 scalar 3
fix pore_diameter1 all property/global pore_diameter_group1 scalar 5.5e-7
fix pore_diameter1 all property/global pore_diameter_group1 vector 5.5e-7 5.5e-7 5.5e-7
# define fix for layer densities
fix LayerDensities1 all property/global density_group1 vector 7870. 5740. 5170. 5240.
@ -208,7 +211,7 @@ fix Ea_CO_2 all property/global Ea_chem2 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity2 all property/global porosity_group2 vector 0.61 0.31 0.16 0.15
fix tortuosity2 all property/global tortuosity_group2 scalar 3
fix pore_diameter2 all property/global pore_diameter_group2 scalar 5.5e-7
fix pore_diameter2 all property/global pore_diameter_group2 vector 5.5e-7 5.5e-7 5.5e-7
# define fix for layer densities
fix LayerDensities2 all property/global density_group2 vector 7870. 5740. 5170. 5240.

View File

@ -43,6 +43,9 @@ fix ftca all property/global thermalCapacity peratomtype 3000
################################################################################
# chemistry
# input fix for fix chem/shrink/core that would otherwise be provided by fix
# heat/gran or fix couple/cfd/convection or fix couple/cfd/parttempfield
fix Temp all property/atom Temp scalar yes yes no 1223.15 # Kelvin
# input fixes for fix chem/shrink/core that would otherwise be provided by fix
# couple/cfd/chemistry
fix partTemp all property/atom partTemp scalar yes no no 1223.15 # Kelvin
@ -75,7 +78,7 @@ fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.61 0.31 0.16 0.15
fix tortuosity all property/global tortuosity_all scalar 3
fix pore_diameter all property/global pore_diameter_all scalar 5.5e-7
fix pore_diameter all property/global pore_diameter_all vector 5.5e-7 5.5e-7 5.5e-7
# define layer properties
fix LayerRelRadii all property/atom relRadii vector yes no no 1.0 0.998 0.995 0.98

View File

@ -45,6 +45,9 @@ fix ftca all property/global thermalCapacity peratomtype 3000
################################################################################
# chemistry
# input fix for fix chem/shrink/core that would otherwise be provided by fix
# heat/gran or fix couple/cfd/convection or fix couple/cfd/parttempfield
fix Temp all property/atom Temp scalar yes yes no 840.0 # Kelvin
# input fixes for fix chem/shrink/core that would otherwise be provided by fix
# couple/cfd/chemistry
fix partTemp all property/atom partTemp scalar yes no no 840.0 # Kelvin
@ -78,7 +81,7 @@ fix Ea_CO all property/global Ea_cfd5 vector 70000 75000
# particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.61 0.16 0.15
fix tortuosity all property/global tortuosity_all scalar 3
fix pore_diameter all property/global pore_diameter_all scalar 5.5e-7
fix pore_diameter all property/global pore_diameter_all vector 5.5e-7 5.5e-7 5.5e-7
# define layer properties
fix LayerRelRadii all property/atom relRadii vector yes no no 1.0 0.998 0.98

View File

@ -44,6 +44,9 @@ fix ftca all property/global thermalCapacity peratomtype 3000
################################################################################
# chemistry
# input fix for fix chem/shrink/core that would otherwise be provided by fix
# heat/gran or fix couple/cfd/convection or fix couple/cfd/parttempfield
fix Temp all property/atom Temp scalar yes yes no 840.0 # Kelvin
# input fixes for fix chem/shrink/core that would otherwise be provided by fix
# couple/cfd/chemistry
fix partTemp all property/atom partTemp scalar yes no no 840.0 # Kelvin
@ -77,7 +80,7 @@ fix Ea_CO all property/global Ea_cfd5 vector 70000 70000 75000
# particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.61 0.31 0.16 0.15
fix tortuosity all property/global tortuosity_all scalar 3
fix pore_diameter all property/global pore_diameter_all scalar 5.5e-7
fix pore_diameter all property/global pore_diameter_all vector 5.5e-7 5.5e-7 5.5e-7
# define layer properties
fix LayerRelRadii all property/atom relRadii vector yes no no 1.0 0.998 0.995 0.98

View File

@ -43,9 +43,12 @@ fix ftca all property/global thermalCapacity peratomtype 3000
################################################################################
# chemistry
# input fix for fix chem/shrink/core that would otherwise be provided by fix
# heat/gran or fix couple/cfd/convection or fix couple/cfd/parttempfield
fix Temp all property/atom Temp scalar yes yes no 600 # Kelvin
# input fixes for fix chem/shrink/core that would otherwise be provided by fix
# couple/cfd/chemistry
fix partTemp all property/atom partTemp scalar yes no no 600 #1223.15 # Kelvin
fix partTemp all property/atom partTemp scalar yes no no 600 # Kelvin
fix partNu all property/atom partNu scalar yes no no 0.00004125
fix partRe all property/atom partRe scalar yes no no 2.7500
fix partP all property/atom partP scalar yes no no 101325
@ -76,7 +79,7 @@ fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.61 0.31 0.16 0.15
fix tortuosity all property/global tortuosity_all scalar 3
fix pore_diameter all property/global pore_diameter_all scalar 5.5e-7
fix pore_diameter all property/global pore_diameter_all vector 5.5e-7 5.5e-7 5.5e-7
# define layer properties
fix LayerRelRadii all property/atom relRadii vector yes no no 1.0 0.998 0.995 0.98
@ -247,6 +250,7 @@ variable rampT equal 600+step*0.001
fix printT all print ${WI} "${time} ${rampT}" &
file post/T.dat title "#time T" screen no
run 600000 every 5000 "set group all property/atom partTemp ${rampT}"
run 600000 every 5000 "set group all property/atom partTemp ${rampT}" &
"set group all property/atom Temp ${rampT}"

View File

@ -0,0 +1,53 @@
################################################################################
# chemistry test case (unreacted shrinking core model)
# particle insertion into domain
################################################################################
atom_style granular
atom_modify map array
communicate single vel yes
boundary f f f
newton off
units si
processors * 1 1
region reg block 0. 1.5 0. 0.5 0. 0.5 units box
create_box 1 reg
neighbor 0.0005 bin
neigh_modify delay 0
################################################################################
# material properties required for granular pair styles
fix m1 all property/global youngsModulus peratomtype 5.e6
fix m2 all property/global poissonsRatio peratomtype 0.45
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.3
fix m4 all property/global coefficientFriction peratomtypepair 1 0.5
# pair style
pair_style gran model hertz tangential history
pair_coeff * *
# timestep
timestep 0.01
# create single particle in a specific spot
create_atoms 1 single 0.75 0.25 0.25 units box
set atom 1 diameter 0.01106028 density 4300 vx 0 vy 0 vz 0
# screen output
thermo_style custom step atoms vol
thermo 1000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic no extra 0
# insert the first particles so that dump is not empty
run 1
dump dmp all custom 100 post/dump.liggghts_init id type x y z vx vy vz fx fy fz radius mass
run 10 upto
write_restart post/restart/liggghts.restart

View File

@ -0,0 +1,262 @@
################################################################################
# chemistry test case (unreacted shrinking core model)
# reduction of a single particle with increasing T without CFD coupling
################################################################################
log log.liggghts
thermo_log post/thermo.txt
atom_style granular
atom_modify map array
communicate single vel yes
boundary f f f
newton off
units si
processors * 1 1
# read the restart file
read_restart post/restart/liggghts.restart
neighbor 0.0005 bin
neigh_modify delay 0
################################################################################
# material properties required for granular pair styles
fix m1 all property/global youngsModulus peratomtype 5.e6
fix m2 all property/global poissonsRatio peratomtype 0.45
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.3
fix m4 all property/global coefficientFriction peratomtypepair 1 0.5
# pair style
pair_style gran model hertz tangential history
pair_coeff * *
# timestep
timestep 0.02
################################################################################
# thermal properties
fix ftco all property/global thermalConductivity peratomtype 1.4
fix ftca all property/atom thermalCapacity scalar yes no no 3000
################################################################################
# chemistry
# input fix for fix chem/shrink/core that would otherwise be provided by fix
# heat/gran or fix couple/cfd/convection or fix couple/cfd/parttempfield
fix Temp all property/atom Temp scalar yes no no 600 # Kelvin
# input fixes for fix chem/shrink/core that would otherwise be provided by fix
# couple/cfd/chemistry
fix partTemp all property/atom partTemp scalar yes no no 600 # Kelvin
fix partNu all property/atom partNu scalar yes no no 0.00004125
fix partRe all property/atom partRe scalar yes no no 2.7500
fix partP all property/atom partP scalar yes no no 101325
# molar fractions
fix X_CO all property/atom X_CO scalar yes no no 0.4
fix X_CO2 all property/atom X_CO2 scalar yes no no 0.0
fix X_N2 all property/atom X_N2 scalar yes no no 0.6
# molecular diffusion coefficient
fix CO_diffCoeff all property/atom CO_diffCoeff scalar yes no no 0.00023
# output fixes for fix chem/shrink/core that would otherwise be provided by fix
# couple/cfd/chemistry
fix Modified_CO all property/atom Modified_CO scalar yes yes no 0.0
fix Modified_CO2 all property/atom Modified_CO2 scalar yes yes no 0.0
fix reactionHeat all property/atom reactionHeat scalar yes no no 0.0
################################################################################
# activate 3-layer unreacted shrinking core model
fix cfd5 all chem/shrink/core speciesA CO molMassA 0.02801 &
speciesC CO2 molMassC 0.04401 &
scale_reduction_rate 2.0 nevery 25 #screen yes
# chemical properties for unreacted shrinking core model
# k0, Ea for high T, values for low T are actually hard-coded
# w->Fe m->w h->m
fix k0_CO all property/global k0_cfd5 vector 17 25 2700
fix Ea_CO all property/global Ea_cfd5 vector 69488 73674 113859
# particle porosity/tortuosity/pore diameter
fix porosity all property/global porosity_all vector 0.61 0.31 0.16 0.15
fix tortuosity all property/global tortuosity_all scalar 3
fix pore_diameter all property/global pore_diameter_all vector 5.5e-7 5.5e-7 5.5e-7
# define layer properties
fix LayerRelRadii all property/atom relRadii vector yes no no 1.0 0.998 0.995 0.98
# define fix for layer densities
fix LayerDensities all property/global density_all vector 7870. 5740. 5170. 5240.
################################################################################
# Write data into files for post-processing
variable WI equal 100
variable time equal time
variable m1 equal mass[1]
variable rp equal radius[1]
variable rho1 equal mass[1]/((4./3.)*PI*radius[1]*radius[1]*radius[1])
fix printmass all print ${WI} "${time} ${m1} ${rp}" &
file post/mass_rad.dat title "#time mass radius" screen no
# effective layer densities
variable lrhoeff1atom atom f_rhoeff[1]
variable lrhoeff2atom atom f_rhoeff[2]
variable lrhoeff3atom atom f_rhoeff[3]
variable lrhoeff4atom atom f_rhoeff[4]
variable lrhoeff1 equal v_lrhoeff1atom[1]
variable lrhoeff2 equal v_lrhoeff2atom[1]
variable lrhoeff3 equal v_lrhoeff3atom[1]
variable lrhoeff4 equal v_lrhoeff4atom[1]
fix printrho all print ${WI} "${time} ${rho1} ${lrhoeff1} ${lrhoeff2} ${lrhoeff3} ${lrhoeff4}" &
file post/rho.dat title "#time \rho \rho_{eff1} \rho_{eff2} \rho_{eff3} \rho_{eff4}" screen no
# specific resistance terms depending on reacting gases
variable a_CO_1atom atom f_Aterm_cfd5[1]
variable a_CO_2atom atom f_Aterm_cfd5[2]
variable a_CO_3atom atom f_Aterm_cfd5[3]
variable a_CO_1 equal v_a_CO_1atom[1]
variable a_CO_2 equal v_a_CO_2atom[1]
variable a_CO_3 equal v_a_CO_3atom[1]
variable b_CO_1atom atom f_Bterm_cfd5[1]
variable b_CO_2atom atom f_Bterm_cfd5[2]
variable b_CO_3atom atom f_Bterm_cfd5[3]
variable b_CO_1 equal v_b_CO_1atom[1]
variable b_CO_2 equal v_b_CO_2atom[1]
variable b_CO_3 equal v_b_CO_3atom[1]
variable mt_COatom atom f_Massterm_cfd5
variable mt_CO equal v_mt_COatom[1]
# chemical reaction resistance
fix printAterm all print ${WI} "${time} ${a_CO_1} ${a_CO_2} ${a_CO_3}" &
file post/Aterm.dat title "#time A1_{CO}(w->Fe) A2_{CO}(m->w) A3_{CO}(h->m)" screen no
# diffusion resistance
fix printBterm all print ${WI} "${time} ${b_CO_1} ${b_CO_2} ${b_CO_3}" &
file post/Bterm.dat title "#time B1_{CO}(Fe) B2_{CO}(w) B3_{CO}(m)" screen no
# mass transfer resistance
fix printMassTerm all print ${WI} "${time} ${mt_CO}" &
file post/MassTerm.dat title "#time mt_{CO}" screen no
# rate change of mass for gaseous reactant
variable dmdot_1atom atom f_dmA_cfd5[1]
variable dmdot_2atom atom f_dmA_cfd5[2]
variable dmdot_3atom atom f_dmA_cfd5[3]
variable dmdot_1 equal v_dmdot_1atom[1]
variable dmdot_2 equal v_dmdot_2atom[1]
variable dmdot_3 equal v_dmdot_3atom[1]
fix printdmdot all print ${WI} "${time} ${dmdot_1} ${dmdot_2} ${dmdot_3}" &
file post/dmdot.dat title "#time dmdot_1 dmdot_2 dmdot_3" screen no
# fractional reduction for specific diameter ranges as well as total fractional reduction
variable fr_d1_1atom atom f_fracRed[1]
variable fr_d1_2atom atom f_fracRed[2]
variable fr_d1_3atom atom f_fracRed[3]
variable fr_d1_1 equal v_fr_d1_1atom[1]
variable fr_d1_2 equal v_fr_d1_2atom[1]
variable fr_d1_3 equal v_fr_d1_3atom[1]
# calculate total fractional reduction
variable frOV_d1 equal 1./9.*(v_fr_d1_3)+2./9.*(v_fr_d1_2)+6./9.*(v_fr_d1_1)
fix printfr1 all print ${WI} "${time} ${fr_d1_1} ${fr_d1_2} ${fr_d1_3} ${frOV_d1}" &
file post/fr_d1.dat title "#time fr_{w->Fe} fr_{m->w} fr_{h->m} fr_{overall}" screen no
# layer radii
variable rr1atom atom f_LayerRelRadii[1]
variable rr2atom atom f_LayerRelRadii[2]
variable rr3atom atom f_LayerRelRadii[3]
variable rr4atom atom f_LayerRelRadii[4]
variable rr1 equal v_rr1atom[1]
variable rr2 equal v_rr2atom[1]
variable rr3 equal v_rr3atom[1]
variable rr4 equal v_rr4atom[1]
fix printRelRadii all print ${WI} "${time} ${rr1} ${rr2} ${rr3} ${rr4}" &
file post/relRadii.dat title "#time relRad_{Fe} relRad_{w} relRad_{m} relRad_{h}" screen no
# layer masses
variable lmass1atom atom f_LayerMasses[1]
variable lmass2atom atom f_LayerMasses[2]
variable lmass3atom atom f_LayerMasses[3]
variable lmass4atom atom f_LayerMasses[4]
variable lmass1 equal v_lmass1atom[1]
variable lmass2 equal v_lmass2atom[1]
variable lmass3 equal v_lmass3atom[1]
variable lmass4 equal v_lmass4atom[1]
variable lmasstot equal v_lmass1+v_lmass2+v_lmass3+v_lmass4
# masses calculated from relative layer radii
variable lmassfromrr1 equal 4.*PI*v_lrhoeff1*(v_rr1*v_rr1*v_rr1-v_rr2*v_rr2*v_rr2)*v_rp*v_rp*v_rp/3.
variable lmassfromrr2 equal 4.*PI*v_lrhoeff2*(v_rr2*v_rr2*v_rr2-v_rr3*v_rr3*v_rr3)*v_rp*v_rp*v_rp/3.
variable lmassfromrr3 equal 4.*PI*v_lrhoeff3*(v_rr3*v_rr3*v_rr3-v_rr4*v_rr4*v_rr4)*v_rp*v_rp*v_rp/3.
variable lmassfromrr4 equal 4.*PI*v_lrhoeff4*(v_rr4*v_rr4*v_rr4)*v_rp*v_rp*v_rp/3.
variable lmassfromrrtot equal v_lmassfromrr1+v_lmassfromrr2+v_lmassfromrr3+v_lmassfromrr4
fix printmasslayer all print ${WI} "${time} ${m1} ${lmass1} ${lmass2} ${lmass3} ${lmass4} ${lmasstot} ${lmassfromrr1} ${lmassfromrr2} ${lmassfromrr3} ${lmassfromrr4} ${lmassfromrrtot}" &
file post/mass_layer.dat title "#time mass lmass1 lmass2 lmass3 lmass4 lmass_{tot} lmassfromrr1 lmassfromrr2 lmassfromrr3 lmassfromrr4 lmassfromrr_{tot}" screen no
# absolute layer radii
variable ar2 equal v_rr2*v_rp
variable ar3 equal v_rr3*v_rp
variable ar4 equal v_rr4*v_rp
fix printabsrad all print ${WI} "${time} ${rp} ${ar2} ${ar3} ${ar4}" &
file post/absRadii.dat title "#time r_{Fe} r_{w} r_{m} r_{h}" screen no
# rate change of species
variable XAatom atom f_Modified_CO
variable XCatom atom f_Modified_CO2
variable XA equal v_XAatom[1]
variable XC equal v_XCatom[1]
fix printXAC all print ${WI} "${time} ${XA} ${XC}" &
file post/XAC.dat title "#time X_{CO} X_{CO2}" screen no
# reaction heat
variable rheatatom atom f_reactionHeat
variable rheat equal v_rheatatom[1]
fix printheat all print ${WI} "${time} ${rheat}" &
file post/heat.dat title "#time heat" screen no
# heat capacity
variable Cpatom atom f_ftca
variable Cp equal v_Cpatom[1]
fix printCp all print ${WI} "${time} ${Cp}" &
file post/Cp.dat title "#time Cp" screen no
################################################################################
# screen output
variable mone equal mass[1]
thermo_style custom step atoms ke v_mone
thermo 100
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic no extra 0
dump dmp all custom 1000 post/dump*.liggghts_run id type x y z vx vy vz &
fx fy fz radius mass f_fracRed[1] f_fracRed[2] f_fracRed[3] &
f_partNu f_partRe f_partP f_partTemp f_CO_diffCoeff
variable rampT equal 600+step*0.001
fix printT all print ${WI} "${time} ${rampT}" &
file post/T.dat title "#time T" screen no
run 600000 every 5000 "set group all property/atom partTemp ${rampT}" &
"set group all property/atom Temp ${rampT}"

View File

@ -0,0 +1,58 @@
#!/usr/bin/octave --silent
%% clear workspace
clear all
close all
clc
dirfile = './post';
filepattern = '*.dat';
% time column in the data matrix
col_t = 1;
% read all data
listfile = dir(fullfile(dirfile,filepattern));
data = readLogData(dirfile,listfile);
nFiles = length(listfile);
% init figures
hFig(1) = figure;
cmap = colormap(jet(16));
linS = {'-';'--';'-.';':';'-';'--';'-.';':';'-';'--';'-.';':'};
markers = {'+';'o';'*';'x';'s';'d';'^';'v';'>';'<';'p';'h';'.'};
for ii=1:nFiles
fname = data(ii).name;
fbasename = strtrunc(fname,index(fname,".dat")-1);
timesteps = data(ii).values(2:50:end,col_t);
figure(hFig(1));
clf reset;
hold on;
nColumns = columns(data(ii).values);
for jj=2:nColumns
xvalue = data(ii).values(2:50:end,jj);
if (strncmp(fbasename,"Aterm",5) || strncmp(fbasename,"Bterm",5))
semilogy(timesteps,xvalue,'Color',cmap(jj,:),'LineStyle',linS{jj-1},'Marker',markers{jj-1},'MarkerSize',5);
else
plot(timesteps,xvalue,'Color',cmap(jj,:),'LineStyle',linS{jj-1},'Marker',markers{jj-1},'MarkerSize',5);
endif
end
xlim auto;
ylim auto;
xlabel('time (s)');
ylabel(fbasename);
headerline = substr(data(ii).header{1},7);
legend(strsplit(headerline, " "),'location','eastoutside');
#print(hFig(1),fullfile(dirfile,['figure_',fbasename,'.eps']),'-color','-deps');
print(hFig(1),fullfile(dirfile,['figure_',fbasename,'.png']),'-color','-dpng');
end

View File

@ -0,0 +1,27 @@
#!/usr/bin/octave --silent
function [ data ] = readLogData( dirfile,filelist )
%READLOGDATA Summary of this function goes here
% Detailed explanation goes here
% get from file name:
% fieldname after underscore (lower case)
% Number of case (Upper case or number)
%expr = '((?<=[_.])[a-z]*)|((?<=[_.][a-z]*)([A-Z0-9]*(\.[0-9]+)?(e\-[0-9]+)?))';
nFiles = length(filelist);
for ii=1:nFiles
% name
iName = filelist(ii).name;
disp(['Processing ',iName,' ...']);
% values
rdata = importdata(fullfile(dirfile,iName), ' ');
data(ii).name = iName;
data(ii).header = rdata.textdata;
data(ii).values = rdata.data;
end
end

View File

@ -0,0 +1,47 @@
{
"runs": [
{
"name" : "create_sphere",
"input_script" : "in.liggghts_init",
"type" : "serial"
},
{
"name" : "run_ramp_up_T",
"depends_on" : "create_sphere",
"input_script" : "in.liggghts_run",
"type" : "serial",
"data" : {
"series" : [
{"name" : "rhoeff", "file" : "rho.dat", "columns" : ["time", "rhoeff", "rhoeffl1", "rhoeffl2", "rhoeffl3", "rhoeffl4"]},
{"name" : "aterm", "file" : "Aterm.dat", "columns" : ["time", "a1", "a2", "a3"]},
{"name" : "bterm", "file" : "Bterm.dat", "columns" : ["time", "b1", "b2", "b3"]},
{"name" : "mterm", "file" : "MassTerm.dat", "columns" : ["time", "mt"]},
{"name" : "dmA", "file" : "dmdot.dat", "columns" : ["time", "dmA1", "dmA2", "dmA3"]},
{"name" : "fracRed", "file" : "fr_d1.dat", "columns" : ["time", "fr1", "fr2", "fr3", "frtot"]},
{"name" : "absrad", "file" : "absRadii.dat", "columns" : ["time", "ar1", "ar2", "ar3", "ar4"]},
{"name" : "relrad", "file" : "relRadii.dat", "columns" : ["time", "rr1", "rr2", "rr3", "rr4"]},
{"name" : "lmasses", "file" : "mass_layer.dat", "columns" : ["time", "mass", "massl1", "massl2", "massl3", "massl4", "masslall", "massl1rr", "massl2rr", "massl3rr", "massl4rr", "masslallrr"]},
{"name" : "heat", "file" : "heat.dat", "columns" : ["time", "heat"]},
{"name" : "species", "file" : "XAC.dat", "columns" : ["time", "CO", "CO2"]},
{"name" : "temp", "file" : "T.dat", "columns" : ["time", "T"]},
{"name" : "Cp", "file" : "Cp.dat", "columns" : ["time", "Cp"]}
],
"plots" : [
{"name" : "plot_rhoeff", "title" : "Effective densities", "xdata" : "rhoeff.time", "ydata" : ["rhoeff.rhoeff","rhoeff.rhoeffl1","rhoeff.rhoeffl2","rhoeff.rhoeffl3","rhoeff.rhoeffl4"], "xlabel" : "Time [s]", "ylabel" : "Effective density [kg/m3]", "legend" : ["rhoeff","rhoeffFe","rhoeffW","rhoeffM","rhoeffH"]},
{"name" : "plot_aterm", "title" : "Reaction resistance terms", "xdata" : "aterm.time", "ydata" : ["aterm.a1","aterm.a2","aterm.a3"], "xlabel" : "Time [s]", "ylabel" : "Reaction resistance", "legend" : ["A_w->Fe","A_m->w","A_h->m"]},
{"name" : "plot_bterm", "title" : "Diffusion resistance terms", "xdata" : "bterm.time", "ydata" : ["bterm.b1","bterm.b2","bterm.b3"], "xlabel" : "Time [s]", "ylabel" : "Diffusion resistance", "legend" : ["B_Fe","B_w","B_m"]},
{"name" : "plot_mterm", "title" : "Mass transfer resistance", "xdata" : "mterm.time", "ydata" : ["mterm.mt"], "xlabel" : "Time [s]", "ylabel" : "Mass transfer resistance", "legend" : ["massterm"]},
{"name" : "plot_dmA", "title" : "Mass change of species A", "xdata" : "dmA.time", "ydata" : ["dmA.dmA1","dmA.dmA2","dmA.dmA3"], "xlabel" : "Time [s]", "ylabel" : "Mass change of species A", "legend" : ["layer1","layer2","layer3"]},
{"name" : "plot_fracRed", "title" : "Fractional Reduction", "xdata" : "fracRed.time", "ydata" : ["fracRed.fr1","fracRed.fr2","fracRed.fr3","fracRed.frtot"], "xlabel" : "Time [s]", "ylabel" : "Fractional reduction", "legend" : ["w","m","h","total"]},
{"name" : "plot_absrad", "title" : "Abs. layer radii", "xdata" : "absrad.time", "ydata" : ["absrad.ar1","absrad.ar2","absrad.ar3","absrad.ar4"], "xlabel" : "Time [s]", "ylabel" : "Layer radius [m]", "legend" : ["Fe","w","m","h"]},
{"name" : "plot_relrad", "title" : "Rel. layer radii", "xdata" : "relrad.time", "ydata" : ["relrad.rr1","relrad.rr2","relrad.rr3","relrad.rr4"], "xlabel" : "Time [s]", "ylabel" : "Rel. layer radius", "legend" : ["Fe","w","m","h"]},
{"name" : "plot_lmasses", "title" : "Layer masses (via reaction/rel. radii)", "xdata" : "lmasses.time", "ydata" : ["lmasses.massl1","lmasses.massl2","lmasses.massl3","lmasses.massl4","lmasses.masslall","lmasses.massl1rr","lmasses.massl2rr","lmasses.massl3rr","lmasses.massl4rr","lmasses.masslallrr"], "xlabel" : "Time [s]", "ylabel" : "Layer mass [kg]", "legend" : ["Fe","w","m","h","total","Fe_rr","w_rr","m_rr","h_rr","total_rr"]},
{"name" : "plot_heat", "title" : "Reaction heat", "xdata" : "heat.time", "ydata" : ["heat.heat"], "xlabel" : "Time [s]", "ylabel" : "Heat [kJ/mol]", "legend" : ["heat"]},
{"name" : "plot_species", "title" : "Rate change of species", "xdata" : "species.time", "ydata" : ["species.CO","species.CO2"], "xlabel" : "Time [s]", "ylabel" : "Species", "legend" : ["CO","CO2"]},
{"name" : "plot_T", "title" : "Particle temperature", "xdata" : "temp.time", "ydata" : ["temp.T"], "xlabel" : "Time [s]", "ylabel" : "Particle temperature [K]", "legend" : ["T"]},
{"name" : "plot_Cp", "title" : "Particle heat capacity", "xdata" : "Cp.time", "ydata" : ["Cp.Cp"], "xlabel" : "Time [s]", "ylabel" : "Particle heat capacity [J/(kg K)]", "legend" : ["Cp"]}
]
}
}
]
}

View File

@ -0,0 +1,102 @@
################################################################################
# brief: Test particle deletion by fix couple/cfd/deform #
# #
# Check that the correct particles (with IDs 1 and 8) are removed #
# #
# authors: Daniel Queteschiner #
# date: Dec 2023 #
# copyright: 2023- JKU Linz #
################################################################################
atom_style granular
atom_modify map array sort 0 0
communicate single vel yes
boundary f f p
newton off
units si
region domain block -1.0 1.0 0.0 0.2 0.0 0.2 units box
create_box 1 domain
neighbor 0.01 bin
neigh_modify delay 0
# material properties for granular pair style
fix m1 all property/global youngsModulus peratomtype 5.e6
fix m2 all property/global poissonsRatio peratomtype 0.45
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.3
fix m4 all property/global coefficientFriction peratomtypepair 1 0.5
fix fp all property/atom/polydispparcel effvolfactor 1.0
# pair style
pair_style gran model hertz tangential history
pair_coeff * *
# timestep
timestep 0.00001
fix gravi all gravity 9.81 vector 0.0 0.0 -1.0
# particle insertion
create_atoms 1 single -0.9 0.1 0.05 units box
create_atoms 1 single -0.7 0.1 0.05 units box
create_atoms 1 single -0.5 0.1 0.05 units box
create_atoms 1 single -0.3 0.1 0.05 units box
create_atoms 1 single 0.3 0.1 0.05 units box
create_atoms 1 single 0.5 0.1 0.05 units box
create_atoms 1 single 0.7 0.1 0.05 units box
create_atoms 1 single 0.9 0.1 0.05 units box
set atom 1 type 1 diameter 0.04 density 2000.
set atom 2 type 1 diameter 0.04 density 2000.
set atom 3 type 1 diameter 0.04 density 2000.
set atom 4 type 1 diameter 0.04 density 2000.
set atom 5 type 1 diameter 0.04 density 2000.
set atom 6 type 1 diameter 0.04 density 2000.
set atom 7 type 1 diameter 0.04 density 2000.
set atom 8 type 1 diameter 0.04 density 2000.
group fullyDeformed empty
# apply nve integration
fix integr all nve/sphere
# screen output
variable all_mass equal mass(all)
variable radii atom radius
variable ids atom id
compute minRad all reduce min v_radii
compute minID all reduce min v_ids
compute maxID all reduce max v_ids
thermo_style custom step atoms ke v_all_mass c_minRad c_minID c_maxID
thermo 1000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic yes
dump dmp all custom 1000 post/dump*.deform id type x y z radius
#dump dmp all custom/vtk 1000 post/deform*.vtk id type x y z radius
fix cfd all couple/cfd couple_every 1000 file ./
fix deform all couple/cfd/deform rmin 0.015 delete_fully_deformed_particles yes compress no verbose yes
# prepare coupling file
variable fileName0 string ./partDeformations0
variable fileName1 string ./partDeformations1
shell rm ${fileName0}
shell echo '8' >> ${fileName0}
shell echo '1.0' >> ${fileName0}
shell echo '0.0' >> ${fileName0}
shell echo '0.0' >> ${fileName0}
shell echo '0.0' >> ${fileName0}
shell echo '0.0' >> ${fileName0}
shell echo '0.0' >> ${fileName0}
shell echo '0.0' >> ${fileName0}
shell echo '1.0' >> ${fileName0}
# after reading, couple/cfd file renames coupling file
# rename it again for reuse in next coupling step
run 2000 pre no post no every 1000 "shell mv ${fileName1} ${fileName0}"
run 1 pre no

View File

@ -0,0 +1,9 @@
{
"runs": [
{
"name" : "couple_deform",
"input_script" : "in.deform",
"type" : "serial"
}
]
}

View File

@ -0,0 +1,90 @@
################################################################################
# brief: Test particle deletion by fix couple/cfd/dissolve #
# #
# Check that the correct particles (with IDs 1, 7 and 8) are removed #
# #
# authors: Daniel Queteschiner #
# date: Dec 2023 #
# copyright: 2023- JKU Linz #
################################################################################
atom_style granular
atom_modify map array sort 0 0
communicate single vel yes
boundary f f p
newton off
units si
region domain block -1.0 1.0 0.0 0.2 0.0 0.2 units box
create_box 1 domain
neighbor 0.01 bin
neigh_modify delay 0
# material properties for granular pair style
fix m1 all property/global youngsModulus peratomtype 5.e6
fix m2 all property/global poissonsRatio peratomtype 0.45
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.3
fix m4 all property/global coefficientFriction peratomtypepair 1 0.5
# pair style
pair_style gran model hertz tangential history
pair_coeff * *
# timestep
timestep 0.00001
fix gravi all gravity 9.81 vector 0.0 0.0 -1.0
# particle insertion
create_atoms 1 single -0.9 0.1 0.05 units box
create_atoms 1 single -0.7 0.1 0.05 units box
create_atoms 1 single -0.5 0.1 0.05 units box
create_atoms 1 single -0.3 0.1 0.05 units box
create_atoms 1 single 0.3 0.1 0.05 units box
create_atoms 1 single 0.5 0.1 0.05 units box
create_atoms 1 single 0.7 0.1 0.05 units box
create_atoms 1 single 0.9 0.1 0.05 units box
set atom 1 type 1 diameter 0.04 density 2000.
set atom 2 type 1 diameter 0.04 density 2000.
set atom 3 type 1 diameter 0.04 density 2000.
set atom 4 type 1 diameter 0.04 density 2000.
set atom 5 type 1 diameter 0.04 density 2000.
set atom 6 type 1 diameter 0.04 density 2000.
set atom 7 type 1 diameter 0.04 density 2000.
set atom 8 type 1 diameter 0.04 density 2000.
# apply nve integration
fix integr all nve/sphere
# screen output
variable all_mass equal mass(all)
variable radii atom radius
variable ids atom id
compute minRad all reduce min v_radii
compute minID all reduce min v_ids
compute maxID all reduce max v_ids
thermo_style custom step atoms ke v_all_mass c_minRad c_minID c_maxID
thermo 1000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic yes
dump dmp all custom 1000 post/dump*.dissolve id type x y z radius
#dump dmp all custom/vtk 1000 post/dissolve*.vtk id type x y z radius
fix cfd all couple/cfd couple_every 1000 mpi
# remove particles with mass below certain threshold (calculated from rmin and density)
fix dissolve all couple/cfd/dissolve rmin 0.015
run 2000
# reduce mass so that fix couple/cfd/dissolve removes particles
variable min_mass equal 2000.0*0.01*0.01*0.01*4.*PI/3.
set atom 1 mass ${min_mass}
set atom 7 mass ${min_mass}
set atom 8 mass ${min_mass}
run 2000

View File

@ -0,0 +1,9 @@
{
"runs": [
{
"name" : "couple_dissolve",
"input_script" : "in.dissolve",
"type" : "serial"
}
]
}

View File

@ -0,0 +1,77 @@
################################################################################
# brief: Test particle deletion by fix massflow/mesh #
# #
# Check that particles in the neighbor list of 2 meshes cause no issue #
# #
# authors: Daniel Queteschiner #
# date: Dec 2023 #
# copyright: 2023- JKU Linz #
################################################################################
atom_style granular
atom_modify map array sort 0 0
boundary f f f
newton off
communicate single vel yes
units si
region reg block -1 1 -1 1 -0.2 0.2 units box
create_box 1 reg
neighbor 0.002 bin
neigh_modify delay 0
# material properties required for granular pair styles
fix m1 all property/global youngsModulus peratomtype 5.e6
fix m2 all property/global poissonsRatio peratomtype 0.45
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.8
fix m4 all property/global coefficientFriction peratomtypepair 1 0.05
# pair style
pair_style gran model hertz tangential history
pair_coeff * *
timestep 0.00001
fix gravi all gravity 9.81 vector 0.0 0.0 -1.0
fix surface_left all mesh/surface file meshes/surface.vtk type 1 verbose yes cell_data yes move -0.5 0.0 0.0
fix surface_right all mesh/surface file meshes/surface.vtk type 1 verbose yes cell_data yes move +0.5 0.0 0.0
fix massflow_left all massflow/mesh mesh surface_left count once file post/testmassflowleft.txt vec_side 0.0 0.0 -1.0 delete_atoms yes
fix massflow_right all massflow/mesh mesh surface_right count once file post/testmassflowright.txt vec_side 0.0 0.0 -1.0 delete_atoms yes verbose yes
# insertion
create_atoms 1 single -0.75 -0.25 0.1
create_atoms 1 single -0.25 -0.25 0.1
create_atoms 1 single -0.75 0.25 0.1
create_atoms 1 single -0.25 0.25 0.1
create_atoms 1 single -0.001 0.25 0.1
create_atoms 1 single 0.25 -0.25 0.1
create_atoms 1 single 0.75 -0.25 0.1
create_atoms 1 single 0.25 0.25 0.1
create_atoms 1 single 0.75 0.25 0.1
create_atoms 1 single 0.001 -0.25 0.1
set group all density 3000 diameter 0.02
# apply nve integration
fix integr all nve/sphere
# output settings
thermo_style custom step atoms ke
thermo 1000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic no extra 0
run 0
dump dmp all custom/vtk 1000 post/massflow*.vtk id type radius x y z vx vy vz
run 15000

View File

@ -0,0 +1,36 @@
# vtk DataFile Version 4.1
Generated by LIGGGHTS
ASCII
DATASET UNSTRUCTURED_GRID
POINTS 9 float
0 -0.5 0 -0.5 -0.5 0 -0.5 0 0
0.5 -0.5 0 0.5 0 0 -0.5 0.5 0
0.5 0.5 0 0 0.5 0 0 0 0
CELLS 8 32
3 1 0 2
3 8 2 0
3 0 3 8
3 4 8 3
3 2 8 5
3 7 5 8
3 8 4 7
3 6 7 4
CELL_TYPES 8
5
5
5
5
5
5
5
5
CELL_DATA 8
SCALARS cell_id int
LOOKUP_TABLE default
0 0 1 1 2 2 3 3
FIELD FieldData 1
face_id 1 8 int
0 0 1 1 2 2 3 3

View File

@ -0,0 +1,9 @@
{
"runs": [
{
"name" : "massflow_mesh_delete",
"input_script" : "in.massflow_mesh",
"type" : "serial"
}
]
}

View File

@ -0,0 +1,76 @@
################################################################################
# brief: Test particle deletion by fix massflow/mesh/face #
# #
# Check that particles in the deletion list of 2 meshes cause no issue #
# #
# authors: Daniel Queteschiner #
# date: Dec 2023 #
# copyright: 2023- JKU Linz #
################################################################################
atom_style granular
atom_modify map array sort 0 0
boundary f f f
newton off
communicate single vel yes
units si
region reg block -1 1 -1 1 -0.2 0.2 units box
create_box 1 reg
neighbor 0.002 bin
neigh_modify delay 0
# material properties required for granular pair styles
fix m1 all property/global youngsModulus peratomtype 5.e6
fix m2 all property/global poissonsRatio peratomtype 0.45
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.8
fix m4 all property/global coefficientFriction peratomtypepair 1 0.05
# pair style
pair_style gran model hertz tangential history
pair_coeff * *
timestep 0.00001
fix gravi all gravity 9.81 vector 0.0 0.0 -1.0
fix surface_left all mesh/surface file meshes/surface.vtk type 1 verbose yes cell_data yes move -0.5 0.0 0.0
fix surface_right all mesh/surface file meshes/surface.vtk type 1 verbose yes cell_data yes move +0.5 0.0 0.0
fix massflow_left all massflow/mesh/face mesh surface_left count once file post/testmassflowleft.txt inside_out delete_atoms yes
fix massflow_right all massflow/mesh/face mesh surface_right count once file post/testmassflowright.txt inside_out delete_atoms yes verbose yes
# insertion
create_atoms 1 single -0.75 -0.25 0.1
create_atoms 1 single -0.25 -0.25 0.1
create_atoms 1 single -0.75 0.25 0.1
create_atoms 1 single -0.25 0.25 0.1
create_atoms 1 single 0.00 0.25 0.1
create_atoms 1 single 0.25 -0.25 0.1
create_atoms 1 single 0.75 -0.25 0.1
create_atoms 1 single 0.25 0.25 0.1
create_atoms 1 single 0.75 0.25 0.1
create_atoms 1 single 0.00 -0.25 0.1
set group all density 3000 diameter 0.02
# apply nve integration
fix integr all nve/sphere
# output settings
thermo_style custom step atoms ke
thermo 1000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic no extra 0
run 0
dump dmp all custom/vtk 1000 post/massflow*.vtk id type radius x y z vx vy vz
run 15000

View File

@ -0,0 +1,36 @@
# vtk DataFile Version 4.1
Generated by LIGGGHTS
ASCII
DATASET UNSTRUCTURED_GRID
POINTS 9 float
0 -0.5 0 -0.5 -0.5 0 -0.5 0 0
0.5 -0.5 0 0.5 0 0 -0.5 0.5 0
0.5 0.5 0 0 0.5 0 0 0 0
CELLS 8 32
3 1 0 2
3 8 2 0
3 0 3 8
3 4 8 3
3 2 8 5
3 7 5 8
3 8 4 7
3 6 7 4
CELL_TYPES 8
5
5
5
5
5
5
5
5
CELL_DATA 8
SCALARS cell_id int
LOOKUP_TABLE default
0 0 1 1 2 2 3 3
FIELD FieldData 1
face_id 1 8 int
0 0 1 1 2 2 3 3

View File

@ -0,0 +1,9 @@
{
"runs": [
{
"name" : "massflow_mesh_face_delete",
"input_script" : "in.massflow_mesh_face",
"type" : "serial"
}
]
}

View File

@ -0,0 +1,84 @@
################################################################################
# brief: Test fix remove with style delete #
# #
# Check that the correct particles (with IDs 1 and 8) are removed #
# #
# authors: Daniel Queteschiner #
# date: Dec 2023 #
# copyright: 2023- JKU Linz #
################################################################################
# delete partial/delete all
variable MASSRATE index 7.0 # 14.0
atom_style granular
atom_modify map array
communicate single vel yes
boundary f f f
newton off
units si
region domain block -1.0 1.0 0.0 0.2 0.0 0.2 units box
create_box 1 domain
neighbor 0.01 bin
neigh_modify delay 0
# material properties for granular pair style
fix m1 all property/global youngsModulus peratomtype 5.e6
fix m2 all property/global poissonsRatio peratomtype 0.45
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.3
fix m4 all property/global coefficientFriction peratomtypepair 1 0.5
# pair style
pair_style gran model hertz tangential history
pair_coeff * *
# timestep
timestep 0.00001
# particle insertion
create_atoms 1 single -0.9 0.1 0.05 units box
create_atoms 1 single -0.7 0.1 0.05 units box
create_atoms 1 single -0.5 0.1 0.05 units box
create_atoms 1 single -0.3 0.1 0.05 units box
create_atoms 1 single 0.3 0.1 0.05 units box
create_atoms 1 single 0.5 0.1 0.05 units box
create_atoms 1 single 0.7 0.1 0.05 units box
create_atoms 1 single 0.9 0.1 0.05 units box
set atom 1 type 1 diameter 0.04 density 2000.
set atom 2 type 1 diameter 0.04 density 2000.
set atom 3 type 1 diameter 0.04 density 2000.
set atom 4 type 1 diameter 0.04 density 2000.
set atom 5 type 1 diameter 0.04 density 2000.
set atom 6 type 1 diameter 0.04 density 2000.
set atom 7 type 1 diameter 0.04 density 2000.
set atom 8 type 1 diameter 0.04 density 2000.
# screen output
variable all_mass equal mass(all)
variable radii atom radius
variable ids atom id
compute minRad all reduce min v_radii
compute minID all reduce min v_ids
compute maxID all reduce max v_ids
thermo_style custom step atoms v_all_mass c_minRad c_minID c_maxID
thermo 1000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic yes
dump dmp all custom 1000 post/dump*.remove_delete id type x y z radius
#dump dmp all custom/vtk 1000 post/remove_delete_*.vtk id type x y z radius
# remove particles
region delreg1 block -1.0 -0.8 0.0 0.2 0.0 0.1 units box
region delreg2 block 0.8 1.0 0.0 0.2 0.0 0.1 units box
region delreg union 2 delreg1 delreg2 units box
fix shrink all remove nevery 1000 massrate ${MASSRATE} style delete &
seed 10007143 region delreg atomtype 1 compress no
run 25000

View File

@ -0,0 +1,20 @@
{
"runs": [
{
"name" : "remove_delete_partial",
"input_script" : "in.remove_delete",
"type" : "serial",
"variables" : {
"MASSRATE" : 7.0
}
},
{
"name" : "remove_delete_all",
"input_script" : "in.remove_delete",
"type" : "serial",
"variables" : {
"MASSRATE" : 14.0
}
}
]
}

View File

@ -0,0 +1,81 @@
################################################################################
# brief: Test fix remove with style shrink #
# #
# Check that the correct particles (with IDs 1 and 8) are removed #
# #
# authors: Daniel Queteschiner #
# date: Dec 2023 #
# copyright: 2023- JKU Linz #
################################################################################
atom_style granular
atom_modify map array
communicate single vel yes
boundary f f f
newton off
units si
region domain block -1.0 1.0 0.0 0.2 0.0 0.2 units box
create_box 1 domain
neighbor 0.01 bin
neigh_modify delay 0
# material properties for granular pair style
fix m1 all property/global youngsModulus peratomtype 5.e6
fix m2 all property/global poissonsRatio peratomtype 0.45
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.3
fix m4 all property/global coefficientFriction peratomtypepair 1 0.5
# pair style
pair_style gran model hertz tangential history
pair_coeff * *
# timestep
timestep 0.00001
# particle insertion
create_atoms 1 single -0.9 0.1 0.05 units box
create_atoms 1 single -0.7 0.1 0.05 units box
create_atoms 1 single -0.5 0.1 0.05 units box
create_atoms 1 single -0.3 0.1 0.05 units box
create_atoms 1 single 0.3 0.1 0.05 units box
create_atoms 1 single 0.5 0.1 0.05 units box
create_atoms 1 single 0.7 0.1 0.05 units box
create_atoms 1 single 0.9 0.1 0.05 units box
set atom 1 type 1 diameter 0.04 density 2000.
set atom 2 type 1 diameter 0.04 density 2000.
set atom 3 type 1 diameter 0.04 density 2000.
set atom 4 type 1 diameter 0.04 density 2000.
set atom 5 type 1 diameter 0.04 density 2000.
set atom 6 type 1 diameter 0.04 density 2000.
set atom 7 type 1 diameter 0.04 density 2000.
set atom 8 type 1 diameter 0.04 density 2000.
# screen output
variable all_mass equal mass(all)
variable radii atom radius
variable ids atom id
compute minRad all reduce min v_radii
compute minID all reduce min v_ids
compute maxID all reduce max v_ids
thermo_style custom step atoms v_all_mass c_minRad c_minID c_maxID
thermo 1000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic yes
dump dmp all custom 1000 post/dump*.remove_shrink id type x y z radius
#dump dmp all custom/vtk 1000 post/remove_shrink_*.vtk id type x y z radius
# shrink and remove particles
region delreg1 block -1.0 -0.8 0.0 0.2 0.0 0.1 units box
region delreg2 block 0.8 1.0 0.0 0.2 0.0 0.1 units box
region delreg union 2 delreg1 delreg2 units box
fix shrink all remove nevery 1000 massrate 0.67 style shrink delete_below 0.004 &
seed 10007143 region delreg atomtype 1 compress no
run 25000

View File

@ -0,0 +1,9 @@
{
"runs": [
{
"name" : "remove_shrink",
"input_script" : "in.remove_shrink",
"type" : "serial"
}
]
}

View File

@ -0,0 +1,74 @@
#Heat transfer example
atom_style granular
atom_modify map array
boundary m m m
newton off
communicate single vel yes
units si
region reg block -0.05 0.05 -0.05 0.05 -0.05 0.05 units box
create_box 1 reg
neighbor 0.002 bin
neigh_modify delay 0
#Material properties required for granular pair styles
fix m1 all property/global youngsModulus peratomtype 5.e6
fix m2 all property/global poissonsRatio peratomtype 0.45
fix m3 all property/global coefficientRestitution peratomtypepair 1 0.95
fix m4 all property/global coefficientFriction peratomtypepair 1 0.05
#fix m5 all property/global characteristicVelocity scalar 2.
#pair style
pair_style gran model hertz tangential history # Hertzian without cohesion
pair_coeff * *
timestep 0.000025
fix gravi all gravity 9.81 vector 0.0 0.0 -1.0
#heat transfer
fix ftco all property/global thermalConductivity peratomtype 5.
fix ftca all property/global thermalCapacity peratomtype 10.
fix heattransfer all heat/gran initial_temperature 300.
create_atoms 1 single 0.0 0.0 -0.025 units box
create_atoms 1 single 0.0 0.0 0.025 units box
set atom 1 type 1 diameter 0.01 density 1000.
set atom 2 type 1 diameter 0.01 density 1000.
#apply nve integration to all particles
fix integr all nve/sphere
compute rke all erotate/sphere
compute Tmin all reduce min f_Temp
compute Tmax all reduce max f_Temp
#output settings, include total thermal energy
thermo_style custom step atoms ke c_rke f_heattransfer c_Tmin c_Tmax vol
thermo 1000
thermo_modify lost ignore norm no
compute_modify thermo_temp dynamic yes
variable T1 equal f_Temp[1]
variable T2 equal f_Temp[2]
fix T all print 1 "${T1} ${T2}" file "Temp.txt"
#set heat sources for distint particles
region pos_source block INF INF INF INF 0.0 INF units box
region neg_source block INF INF INF INF INF 0.0 units box
run 0
set region pos_source property/atom heatSource 1.5
set region neg_source property/atom heatSource -1.5
fix limT all limit/property/atom Temp min 250 max 350
#run to see heat transfer
run 10000 upto

View File

@ -0,0 +1,9 @@
{
"runs": [
{
"name" : "serial",
"input_script" : "in.limit_property_atom",
"type" : "serial"
}
]
}

View File

@ -0,0 +1 @@
liggghts < in.limit_property_atom

View File

@ -5,8 +5,8 @@ OPTION(USE_SUPERQUADRIC "Superquadric particles" OFF)
OPTION(USE_OPENMP "OpenMP parallelization" OFF)
OPTION(TESTING "TESTING" OFF)
SET(LIGGGHTS_MAJOR_VERSION 23)
SET(LIGGGHTS_MINOR_VERSION 02)
SET(LIGGGHTS_MAJOR_VERSION 24)
SET(LIGGGHTS_MINOR_VERSION 01)
SET(LIGGGHTS_PATCH_VERSION 0)
SET(LIGGGHTS_VERSION ${LIGGGHTS_MAJOR_VERSION}.${LIGGGHTS_MINOR_VERSION}.${LIGGGHTS_PATCH_VERSION})
MESSAGE(STATUS "${LIGGGHTS_VERSION}")

View File

@ -217,8 +217,8 @@ class Atom : protected Pointers {
return extract(_id,a);
}
inline int* get_map_array() {return map_array;};
inline int get_map_size() {return map_tag_max+1;};
inline int* get_map_array() {return map_array;}
inline int get_map_size() {return map_tag_max+1;}
bigint memory_usage();
int memcheck(const char *);

View File

@ -45,42 +45,42 @@ using namespace LAMMPS_NS;
CfdDatacoupling::CfdDatacoupling(class LAMMPS *lmp, int jarg, int, char **, class FixCfdCoupling*) :
Pointers(lmp)
{
iarg_ = jarg;
is_parallel = true;
iarg_ = jarg;
is_parallel = true;
npull_ = 0;
npush_ = 0;
nvalues_max_ = 0;
npull_ = 0;
npush_ = 0;
nvalues_max_ = 0;
pullnames_ = NULL;
pulltypes_ = NULL;
pushnames_ = NULL;
pushtypes_ = NULL;
pushinvoked_ = NULL;
pullinvoked_ = NULL;
latestpull_ = NULL;
latestpush_ = NULL;
pullnames_ = NULL;
pulltypes_ = NULL;
pushnames_ = NULL;
pushtypes_ = NULL;
pushinvoked_ = NULL;
pullinvoked_ = NULL;
latestpull_ = NULL;
latestpush_ = NULL;
properties_ = NULL;
properties_ = NULL;
ms_ = NULL;
ms_data_ = NULL;
ms_ = NULL;
ms_data_ = NULL;
grow_();
grow_();
}
/* ---------------------------------------------------------------------- */
CfdDatacoupling::~CfdDatacoupling()
{
memory->destroy(pullnames_);
memory->destroy(pulltypes_);
memory->destroy(pushnames_);
memory->destroy(pushtypes_);
memory->destroy(pushinvoked_);
memory->destroy(pullinvoked_);
memory->destroy(latestpush_);
memory->destroy(latestpull_);
memory->destroy(pullnames_);
memory->destroy(pulltypes_);
memory->destroy(pushnames_);
memory->destroy(pushtypes_);
memory->destroy(pushinvoked_);
memory->destroy(pullinvoked_);
memory->destroy(latestpush_);
memory->destroy(latestpull_);
}
/* ---------------------------------------------------------------------- */
@ -90,6 +90,7 @@ void CfdDatacoupling::init()
PairGran *pair_gran = static_cast<PairGran*>(force->pair_match("gran", 0));
if(!pair_gran)
error->all(FLERR,"CFD coupling requires a granular pair style");
properties_ = pair_gran->get_properties();
// multisphere - can be NULL

View File

@ -173,6 +173,8 @@ DumpCustomVTK::DumpCustomVTK(LAMMPS *lmp, int narg, char **arg) :
label = NULL; //NP modified C.K.
write_domain = 1;
{
// parallel vtp/vtu requires proc number to be preceded by underscore '_'
multiname_ex = NULL;
@ -1439,10 +1441,12 @@ void DumpCustomVTK::write_vtk(int n, double *mybuf)
writer->SetFileName(filecurrent);
writer->Write();
if (domain->triclinic == 0)
write_domain_vtk();
else
write_domain_vtk_triclinic();
if (write_domain) {
if (domain->triclinic == 0)
write_domain_vtk();
else
write_domain_vtk_triclinic();
}
}
reset_vtk_data_containers();
@ -1499,12 +1503,14 @@ void DumpCustomVTK::write_vtp(int n, double *mybuf)
pwriter->Write();
}
if (domain->triclinic == 0) {
domainfilecurrent[strlen(domainfilecurrent)-1] = 'r'; // adjust filename extension
write_domain_vtr();
} else {
domainfilecurrent[strlen(domainfilecurrent)-1] = 'u'; // adjust filename extension
write_domain_vtu_triclinic();
if (write_domain) {
if (domain->triclinic == 0) {
domainfilecurrent[strlen(domainfilecurrent)-1] = 'r'; // adjust filename extension
write_domain_vtr();
} else {
domainfilecurrent[strlen(domainfilecurrent)-1] = 'u'; // adjust filename extension
write_domain_vtu_triclinic();
}
}
}
}
@ -1563,11 +1569,13 @@ void DumpCustomVTK::write_vtu(int n, double *mybuf)
pwriter->Write();
}
if (domain->triclinic == 0) {
domainfilecurrent[strlen(domainfilecurrent)-1] = 'r'; // adjust filename extension
write_domain_vtr();
} else {
write_domain_vtu_triclinic();
if (write_domain) {
if (domain->triclinic == 0) {
domainfilecurrent[strlen(domainfilecurrent)-1] = 'r'; // adjust filename extension
write_domain_vtr();
} else {
write_domain_vtu_triclinic();
}
}
}
}
@ -2298,6 +2306,14 @@ int DumpCustomVTK::modify_param(int narg, char **arg)
return 2;
}
if (strcmp(arg[0],"domainfile") == 0) {
if (narg < 2) error->all(FLERR,"Illegal dump_modify command [domainfile]");
if (strcmp(arg[1],"yes") == 0) write_domain = 1;
else if (strcmp(arg[1],"no") == 0) write_domain = 0;
else error->all(FLERR,"Illegal dump_modify command [domainfile]");
return 2;
}
if (strcmp(arg[0],"element") == 0) {
if (narg < ntypes+1)
error->all(FLERR,"Dump modify: number of element names do not match atom types");

View File

@ -116,6 +116,7 @@ class DumpCustomVTK : public Dump {
int ntypes; // # of atom types
char **typenames; // array of element names for each type
int write_domain; // 0/1 if domain file gets written
// private methods
virtual void init_style();
@ -241,7 +242,7 @@ class DumpCustomVTK : public Dump {
void pack_erforce(int);
// superquadric start
void pack_shapex(int);
void pack_shapex(int);
void pack_shapey(int);
void pack_shapez(int);
void pack_quat1(int);

View File

@ -46,6 +46,8 @@ FixCfdCouplingConvection::FixCfdCouplingConvection(LAMMPS *lmp, int narg, char *
fix_conductiveFlux = fix_convectiveFlux = fix_heatFlux = NULL;
T0 = -1.0;
gran_field_conduction = false;
limit_change = false;
max_change = -1.0;
int iarg = 3;
@ -77,6 +79,14 @@ FixCfdCouplingConvection::FixCfdCouplingConvection(LAMMPS *lmp, int narg, char *
iarg++;
hasargs = true;
}
else if(strcmp(arg[iarg],"max_change") == 0)
{
iarg++;
max_change = atof(arg[iarg]);
limit_change = true;
iarg++;
hasargs = true;
}
}
if(T0 < 0.) error->all(FLERR,"Fix couple/cfd/convection: T0 must be >= 0. Specify a meaningful value.");
@ -144,27 +154,34 @@ void FixCfdCouplingConvection::post_create()
// add heat transfer model if not yet active
FixScalarTransportEquation *fix_ste = modify->find_fix_scalar_transport_equation("heattransfer");
int nargs = 15;
if (limit_change) nargs += 2;
if(!fix_ste)
{
const char *newarg[15];
newarg[0] = "ste_heattransfer";
newarg[1] = group->names[igroup];
newarg[2] = "transportequation/scalar";
newarg[3] = "equation_id";
newarg[4] = "heattransfer";
newarg[5] = "quantity";
newarg[6] = "Temp";
newarg[7] = "default_value";
const char *fixarg[17];
fixarg[0] = "ste_heattransfer";
fixarg[1] = group->names[igroup];
fixarg[2] = "transportequation/scalar";
fixarg[3] = "equation_id";
fixarg[4] = "heattransfer";
fixarg[5] = "quantity";
fixarg[6] = "Temp";
fixarg[7] = "default_value";
char arg8[30];
sprintf(arg8,"%f",T0);
newarg[8] = arg8;
newarg[9] = "flux_quantity";
newarg[10] = "heatFlux";
newarg[11] = "source_quantity";
newarg[12] = "heatSource";
newarg[13] = "capacity_quantity";
newarg[14] = "thermalCapacity";
modify->add_fix(15,const_cast<char**>(newarg));
fixarg[8] = arg8;
fixarg[9] = "flux_quantity";
fixarg[10] = "heatFlux";
fixarg[11] = "source_quantity";
fixarg[12] = "heatSource";
fixarg[13] = "capacity_quantity";
fixarg[14] = "thermalCapacity";
// the following lines are only passed to modify->add_fix if limit_change == true
fixarg[15] = "max_change";
char arg16[30];
sprintf(arg16,"%f",max_change);
fixarg[16] = arg16;
modify->add_fix(nargs,const_cast<char**>(fixarg));
}
}

View File

@ -51,6 +51,9 @@ class FixCfdCouplingConvection : public Fix {
class FixPropertyAtom* fix_heatFlux;
double T0;
bool gran_field_conduction;
bool limit_change;
double max_change;
};
}

View File

@ -54,6 +54,7 @@ FixCfdCouplingDeform::FixCfdCouplingDeform(LAMMPS *lmp, int narg, char **arg) :
fix_effvolfactors_(0),
verbose_(false),
compress_flag_(1),
delete_fully_deformed_particles_(true),
igroup_fully_deformed_(-1),
igroup_fully_deformed_bit_(-1),
particles_removed_(0),
@ -65,6 +66,8 @@ FixCfdCouplingDeform::FixCfdCouplingDeform(LAMMPS *lmp, int narg, char **arg) :
heat_removed_(0.),
fix_temp_(NULL),
fix_capacity_(NULL),
fix_internal_energy_(NULL),
internal_energy_(false),
use_latent_heat_(false),
latent_heat_per_mass_(0.0),
latent_heat_transferred_(0.0),
@ -97,6 +100,16 @@ FixCfdCouplingDeform::FixCfdCouplingDeform(LAMMPS *lmp, int narg, char **arg) :
error->fix_error(FLERR,this,"expecing 'yes' or 'no' for 'verbose'");
iarg += 2;
}
else if(strcmp(arg[iarg],"delete_fully_deformed_particles") == 0)
{
if(narg < iarg+2)
error->fix_error(FLERR,this,"not enough arguments for 'delete_fully_deformed_particles'");
if(strcmp(arg[iarg+1],"no") == 0)
delete_fully_deformed_particles_ = false;
else if(strcmp(arg[iarg+1],"yes"))
error->fix_error(FLERR,this,"expecing 'yes' or 'no' for 'delete_fully_deformed_particles'");
iarg += 2;
}
else if(strcmp(arg[iarg],"rmin") == 0)
{
if(narg < iarg+2)
@ -135,6 +148,8 @@ FixCfdCouplingDeform::FixCfdCouplingDeform(LAMMPS *lmp, int narg, char **arg) :
vector_flag = 1;
size_vector = 3;
force_reneighbor = 1;
next_reneighbor = -1;
}
/* ---------------------------------------------------------------------- */
@ -148,7 +163,6 @@ FixCfdCouplingDeform::~FixCfdCouplingDeform()
void FixCfdCouplingDeform::post_create()
{
// register convective flux
if(!fix_partdeformations_)
{
const char* fixarg[9];
@ -190,6 +204,7 @@ int FixCfdCouplingDeform::setmask()
{
int mask = 0;
mask |= INITIAL_INTEGRATE;
mask |= PRE_EXCHANGE;
mask |= POST_FORCE;
return mask;
}
@ -216,7 +231,17 @@ void FixCfdCouplingDeform::init()
PairGran* pair_gran = static_cast<PairGran*>(force->pair_match("gran", 0));
int max_type = pair_gran->get_properties()->max_type();
fix_capacity_ = static_cast<FixPropertyGlobal*>(modify->find_fix_property("thermalCapacity","property/global","peratomtype",max_type,0,style));
fix_capacity_ = static_cast<FixPropertyGlobal*>(modify->find_fix_property("thermalCapacity","property/global","peratomtype",max_type,0,style,false));
fix_internal_energy_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("internalEnergy","property/atom","scalar",0,0,style,false));
if (fix_internal_energy_) internal_energy_ = true;
if (!fix_capacity_ && !fix_internal_energy_)
{
char errmsg[500];
sprintf(errmsg,"Could neither locate a fix/property storing value(s) for thermalCapacity nor one for the internal energy as requested by FixCfdCouplingDeform.");
error->all(FLERR,errmsg);
}
}
// look up group of fully deformed particles; needs to be defined in run script before this fix
@ -237,11 +262,22 @@ void FixCfdCouplingDeform::init()
void FixCfdCouplingDeform::initial_integrate(int)
{
if (!delete_fully_deformed_particles_) return;
bigint prev_time = update->ntimestep - 1;
// only delete group immediately after pull/push so that no latent heat is neglected
if (prev_time != fix_coupling_->latestpull("partDeformations")) return;
next_reneighbor = update->ntimestep;
}
/* ---------------------------------------------------------------------- */
void FixCfdCouplingDeform::pre_exchange()
{
if(next_reneighbor != update->ntimestep) return;
int *mask = atom->mask;
int nlocal = atom->nlocal;
int *type = atom->type;
@ -262,7 +298,8 @@ void FixCfdCouplingDeform::initial_integrate(int)
double latent_heat_transferred_this_me = 0., latent_heat_transferred_this = 0.;
// remove all elements in group of fully deformed particles
for (int i = 0; i < nlocal; i++)
int i = 0;
while (i < nlocal)
{
if (mask[i] & igroup_fully_deformed_bit_)
{
@ -271,18 +308,33 @@ void FixCfdCouplingDeform::initial_integrate(int)
if (monitor_heat_)
{
double Cp = fix_capacity_->compute_vector(type[i]-1);
heat_removed_this_me += rmass[i]*T[i]*Cp;
if (internal_energy_)
{
heat_removed_this_me += fix_internal_energy_->vector_atom[i];
}
else
{
double Cp = fix_capacity_->compute_vector(type[i]-1);
heat_removed_this_me += rmass[i]*T[i]*Cp;
}
}
if (use_latent_heat_)
{
latent_heat_transferred_this_me -= latent_heat_per_mass_ * rmass[i];
}
delete_particle(i);
atom->avec->copy(nlocal-1,i,1);
nlocal--;
}
else
{
i++;
}
}
atom->nlocal = nlocal;
MPI_Allreduce(&mass_removed_this_me,&mass_removed_this,1,MPI_DOUBLE,MPI_SUM,world);
MPI_Allreduce(&nremoved_this_me,&nremoved_this,1,MPI_INT,MPI_SUM,world);
particles_removed_ += nremoved_this;
@ -314,6 +366,9 @@ void FixCfdCouplingDeform::initial_integrate(int)
atom->tag_extend();
}
bigint nblocal = atom->nlocal;
MPI_Allreduce(&nblocal,&atom->natoms,1,MPI_LMP_BIGINT,MPI_SUM,world);
if (atom->tag_enable)
{
if (atom->map_style)
@ -359,7 +414,7 @@ void FixCfdCouplingDeform::post_force(int)
if (deformation < 1.0 - SMALL && deformation > SMALL)
{
effvolfactor = effvolfactors_[i];
f0 = default_effvolfactors_[type[i]];
f0 = default_effvolfactors_[type[i]-1];
neweffvolfactor = f0 + deformation * (fmax_ - f0);
// update properties only if new eff vol factor larger than old one (by e.g. 1%)
if (neweffvolfactor <= 1.01*effvolfactor) continue;
@ -385,13 +440,6 @@ void FixCfdCouplingDeform::post_force(int)
}
}
void FixCfdCouplingDeform::delete_particle(int i)
{
atom->avec->copy(atom->nlocal-1,i,1);
atom->nlocal--;
}
/* ----------------------------------------------------------------------
provide accumulated removed mass and optionally heat
------------------------------------------------------------------------- */

View File

@ -41,6 +41,7 @@ class FixCfdCouplingDeform : public Fix {
int setmask();
void init();
void initial_integrate(int);
void pre_exchange();
void post_force(int);
double compute_vector(int n);
@ -56,6 +57,8 @@ class FixCfdCouplingDeform : public Fix {
int compress_flag_;
bool delete_fully_deformed_particles_;
int igroup_fully_deformed_;
int igroup_fully_deformed_bit_;
@ -78,6 +81,10 @@ class FixCfdCouplingDeform : public Fix {
class FixPropertyGlobal* fix_capacity_;
class FixPropertyAtom *fix_internal_energy_;
bool internal_energy_;
bool use_latent_heat_;
double latent_heat_per_mass_;
@ -87,8 +94,6 @@ class FixCfdCouplingDeform : public Fix {
class FixPropertyAtom *fix_latent_heat_;
double *latent_heat_;
void delete_particle(int);
};
}

View File

@ -190,28 +190,42 @@ void FixCfdCouplingDissolve::post_force(int)
void FixCfdCouplingDissolve::pre_exchange()
{
delete_atoms();
}
// delete atoms
void FixCfdCouplingDissolve::delete_atoms()
{
int nparticles_deleted_this = 0;
int *atom_map_array = atom->get_map_array();
AtomVec *avec = atom->avec;
int nlocal = atom->nlocal;
int tag_max = atom->tag_max();
while (atom_tags_delete_.size() > 0)
{
int iPart = atom->map(atom_tags_delete_[0]);
if(atom_tags_delete_[0] <= tag_max)
{
int iPart = atom->map(atom_tags_delete_[0]);
avec->copy(nlocal-1,iPart,1);
if(iPart >= 0)
{
nparticles_deleted_this++;
nparticles_deleted_this++;
nlocal--;
avec->copy(nlocal-1,iPart,1);
//NP manipulate atom map array
//NP need to do this since atom map is needed for deletion
atom_map_array[atom->tag[atom->nlocal-1]] = iPart;
// update atom map
// need to do this since atom map is needed to get local index for deletion
atom->map_one(atom->tag[nlocal-1], iPart);
nlocal--;
}
else
{
// particle may have been removed already by a different deleting command
error->fix_warning(FLERR, this, "failed to find atom for deletion (possibly already deleted by another deleting command)");
}
}
else
{
// particle may have been removed already by a different deleting command
error->fix_warning(FLERR, this, "failed to find atom for deletion (possibly already deleted by another deleting command)");
}
atom_tags_delete_.erase(atom_tags_delete_.begin());
}

View File

@ -55,8 +55,6 @@ class FixCfdCouplingDissolve : public Fix {
double rmin_;
std::vector<int> atom_tags_delete_;
void delete_atoms();
};
}

View File

@ -129,7 +129,8 @@ FixChemShrinkCore::FixChemShrinkCore(LAMMPS *lmp, int narg, char **arg) :
rmin_(1e-5), // [m]
created_fix_layerMass_(false),
created_fix_rhoeff_(false),
created_fix_fracRed(false)
created_fix_fracRed(false),
created_fix_internal_energy_(false)
{
if ((strncmp(style, "chem/shrink/core", 15) == 0) && ((!atom->radius_flag) || (!atom->rmass_flag)))
error->all(FLERR, "Fix chem/shrink/core needs per particle radius and mass");
@ -485,6 +486,21 @@ void FixChemShrinkCore::post_create()
created_fix_fracRed = true;
}
fix_internal_energy_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("internalEnergy","property/atom","scalar",0,0,style,false));
if (fix_internal_energy_ == NULL) {
const char* fixarg[9];
fixarg[0]="internalEnergy"; // fixid
fixarg[1]="all";
fixarg[2]="property/atom";
fixarg[3]="internalEnergy"; // propertyid
fixarg[4]="scalar";
fixarg[5]="yes"; // restart yes
fixarg[6]="yes"; // communicate ghost - yes
fixarg[7]="no"; // communicate rev no
fixarg[8]="0.0";
fix_internal_energy_ = modify->add_fix_property_atom(9,const_cast<char**>(fixarg),style);
created_fix_internal_energy_ = true;
}
}
/* ---------------------------------------------------------------------- */
@ -503,6 +519,7 @@ void FixChemShrinkCore::pre_delete(bool unfixflag)
if (fix_layerMass_ && created_fix_layerMass_) { modify->delete_fix(fix_layerMass_->id); massLayer_ = NULL; }
if (fix_rhoeff_ && created_fix_rhoeff_) { modify->delete_fix(fix_rhoeff_->id); rhoeff_ = NULL; }
if (fix_fracRed && created_fix_fracRed) { modify->delete_fix(fix_fracRed->id); fracRed_ = NULL; }
if (fix_internal_energy_ && created_fix_internal_energy_) {modify->delete_fix(fix_internal_energy_->id);}
}
}
@ -537,6 +554,7 @@ void FixChemShrinkCore::updatePtrs()
changeOfA_ = fix_changeOfA_ -> vector_atom;
changeOfC_ = fix_changeOfC_ -> vector_atom;
T_ = fix_tgas_ -> vector_atom;
Tpart_ = fix_tpart_ -> vector_atom;
reactionHeat_ = fix_reactionHeat_ -> vector_atom;
molecularDiffusion_ = fix_diffcoeff_ -> vector_atom;
nuf_ = fix_nuField_ -> vector_atom;
@ -560,7 +578,7 @@ void FixChemShrinkCore::updatePtrs()
//
porosity_ = fix_porosity_ -> values;
tortuosity_ = fix_tortuosity_ -> compute_scalar();
pore_diameter_ = fix_pore_diameter_ -> compute_scalar();
pore_diameter_ = fix_pore_diameter_ -> values;
//
fracRed_ = fix_fracRed -> array_atom;
Aterm = fix_Aterm -> array_atom;
@ -575,8 +593,8 @@ void FixChemShrinkCore::updatePtrs()
pmass_ = atom -> rmass;
pdensity_ = atom -> density;
dY = fix_dY_ -> array_atom;
dmA_f_ = fix_dmA_ -> array_atom;
dY = fix_dY_ -> array_atom;
dmA_f_ = fix_dmA_ -> array_atom;
if(limit_reactant_consumption_)
{
@ -624,6 +642,7 @@ void FixChemShrinkCore::init()
fix_changeOfA_ = static_cast<FixPropertyAtom*>(modify->find_fix_property(massA, "property/atom", "scalar", 0, 0, style));
fix_changeOfC_ = static_cast<FixPropertyAtom*>(modify->find_fix_property(massC, "property/atom", "scalar", 0, 0, style));
fix_tgas_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("partTemp", "property/atom", "scalar", 0, 0, style));
fix_tpart_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("Temp", "property/atom", "scalar", 0, 0, style)); // particle temperature
fix_reactionHeat_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("reactionHeat", "property/atom", "scalar", 0, 0, style));
fix_diffcoeff_ = static_cast<FixPropertyAtom*>(modify->find_fix_property(diffA, "property/atom", "scalar", 0, 0, style));
fix_nuField_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("partNu", "property/atom", "scalar", 0, 0, style));
@ -635,6 +654,7 @@ void FixChemShrinkCore::init()
fix_layerRelRad_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("relRadii", "property/atom", "vector", 0, 0, style));
fix_layerMass_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("massLayer","property/atom","vector",0,0,style));
fix_rhoeff_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("rhoeff", "property/atom", "vector", 0, 0, style));
fix_thermal_capacity_= static_cast<FixPropertyAtom*>(modify->find_fix_property("thermalCapacity", "property/atom", "scalar", 0, 0, style,false));
fix_polydisp_ = static_cast<FixPropertyAtomPolydispParcel*>(modify->find_fix_property("effvolfactor", "property/atom","scalar",0,0,style,false));
// references for global properties - valid for every particle equally
@ -653,10 +673,9 @@ void FixChemShrinkCore::init()
propertyname = new char [strlen("pore_diameter_")+strlen(group->names[igroup])+1];
strcpy(propertyname,"pore_diameter_");
strcat(propertyname,group->names[igroup]);
fix_pore_diameter_ = static_cast<FixPropertyGlobal*>(modify->find_fix_property(propertyname, "property/global", "scalar", 0, 0,style));
fix_pore_diameter_ = static_cast<FixPropertyGlobal*>(modify->find_fix_property(propertyname, "property/global", "vector", 0, 0,style));
delete [] propertyname;
propertyname = new char [strlen("Aterm_")+strlen(id)+1];
strcpy (propertyname,"Aterm_");
strcat(propertyname,id);
@ -705,6 +724,15 @@ void FixChemShrinkCore::init()
{
fix_reactantPerParticle_ = static_cast<FixPropertyAtom*>(modify -> find_fix_property("reactantPerParticle","property/atom","scalar",0,0,style));
}
if(fix_thermal_capacity_)
{
variableCp_ = true;
}
else
{
variableCp_ = false;
}
}
/* ---------------------------------------------------------------------- */
@ -970,7 +998,7 @@ void FixChemShrinkCore::getB(int i)
effDiffBinary[i][layer] = molecularDiffusion_[i]*(porosity_[layer]/tortuosity_) + SMALL;
// Calculate the knudsen diffusion
effDiffKnud[i][layer] = (pore_diameter_/6.0)*sqrt((8*Runiv*T_[i])/(M_PI*molMass_A_))*(porosity_[layer]/tortuosity_) + SMALL;
effDiffKnud[i][layer] = (pore_diameter_[layer]/6.0)*sqrt((8*Runiv*T_[i])/(M_PI*molMass_A_))*(porosity_[layer]/tortuosity_) + SMALL;
// total effective diffusivity
diffEff_[layer] = effDiffKnud[i][layer]*effDiffBinary[i][layer]/(effDiffBinary[i][layer]+effDiffKnud[i][layer]) + SMALL;
@ -1223,6 +1251,24 @@ void FixChemShrinkCore::update_atom_properties(int i, const double *dmA_,const d
double rad[MAX_LAYERS+1] = {0.};
double dmL_[MAX_LAYERS+1] = {0.}; // mass flow rate between each layer i.e. (btw h->m, m->w, w->Fe) must consider reduction and growth at the same time
double sum_mass_p_new = 0.0;
double Cp = 0.0;
double layer_Cp[MAX_LAYERS+1] = {0.};
double Tpart = Tpart_[i];
double H = 0.0;
double layer_H[4] = {0.};
if (variableCp_)
{
layer_Cp[0] = spec_heat(a_coeff_nasa_Fe,Tpart);
layer_Cp[1] = spec_heat(a_coeff_nasa_FeO,Tpart);
layer_Cp[2] = spec_heat(a_coeff_nasa_Fe3O4,Tpart);
layer_Cp[3] = spec_heat(a_coeff_nasa_Fe2O3,Tpart);
}
layer_H[0] = conv_enthalpy(a_coeff_nasa_Fe, i);
layer_H[1] = conv_enthalpy(a_coeff_nasa_FeO,i);
layer_H[2] = conv_enthalpy(a_coeff_nasa_Fe3O4,i);
layer_H[3] = conv_enthalpy(a_coeff_nasa_Fe2O3,i);
// Mass Change of Layers
// dmL is a positive value, therefore it will be subtracted from the total mass
@ -1244,8 +1290,9 @@ void FixChemShrinkCore::update_atom_properties(int i, const double *dmA_,const d
for (int j = 0; j <= layers_; j++)
{
massLayer_[i][j] -= dmL_[j]*scale_reduction_rate;
if (massLayer_[i][j] < 0.0)
massLayer_[i][j] = 0.0;
if (massLayer_[i][j] < 0.0) massLayer_[i][j] = 0.0;
Cp += massLayer_[i][j] * layer_Cp[j] / layerMolMasses_[j];
H += massLayer_[i][j] * layer_H[j] / layerMolMasses_[j];
}
for (int j = 0; j <= layers_; j++)
{
@ -1254,12 +1301,19 @@ void FixChemShrinkCore::update_atom_properties(int i, const double *dmA_,const d
// non-zero contribution (at least from the innermost layer)
sum_mass_p_new += massLayer_[i][j];
}
if (variableCp_)
{
Cp /= sum_mass_p_new;
fix_thermal_capacity_->vector_atom[i] = Cp;
}
// if (screen) fprintf(screen,"total mass of particle = %f \n", sum_mass_p_new);
// Total mass of particle with coarse-graining
pmass_[i] = sum_mass_p_new*cg_*cg_*cg_;
fix_internal_energy_->vector_atom[i] = H*cg_*cg_*cg_;
// if (screen) fprintf(screen, "pmass = %f \n",pmass_[i]);
// Core layer radius (initial Fe2O3)
@ -1346,9 +1400,13 @@ void FixChemShrinkCore::FractionalReduction(int i)
*/
// this formulation assumes that molar concentrations n_i of the layers satisfy n_i / nu_i = n_j / nu_j, e.g. n_Hem / 3 = n_Mag / 2
const double f_WF = 1.0 - relRadii_[i][1]*relRadii_[i][1]*relRadii_[i][1];
const double f_MW = 1.0 - relRadii_[i][2]*relRadii_[i][2]*relRadii_[i][2];
const double f_HM = 1.0 - relRadii_[i][3]*relRadii_[i][3]*relRadii_[i][3];
double f_WF = 1.0 - relRadii_[i][1]*relRadii_[i][1]*relRadii_[i][1];
double f_MW = 1.0 - relRadii_[i][2]*relRadii_[i][2]*relRadii_[i][2];
double f_HM = 1.0 - relRadii_[i][3]*relRadii_[i][3]*relRadii_[i][3];
if (f_HM > 1.0 - SMALL) f_HM = 1.0 - SMALL;
if (f_MW > 1.0 - SMALL) f_MW = 1.0 - SMALL;
if (f_WF > 1.0 - SMALL) f_WF = 1.0 - SMALL;
fracRed_[i][0] = f_WF;
fracRed_[i][1] = f_MW;
@ -1430,7 +1488,7 @@ void FixChemShrinkCore::heat_of_reaction(int i, const double *dmA_, const double
// add per-particle reactionHeat flux
for (int k = 0; k < layers_; k++)
reactionHeat_[i] += HR[k];
reactionHeat_[i] -= HR[k];
}
/* ---------------------------------------------------------------------- */
@ -1441,9 +1499,6 @@ double FixChemShrinkCore::conv_enthalpy (const double *a, int i)
{
double value = 0.;
if (T_[i] < SMALL)
error->fix_error(FLERR, this, "Error T <= ZERO");
if (T_[i] < a[0]) { // Temperature smaller than lower bound
const double Tbound_low = a[0];
const double Tbound_low_sq = Tbound_low*Tbound_low;
@ -1491,6 +1546,53 @@ double FixChemShrinkCore::conv_enthalpy (const double *a, int i)
/* ---------------------------------------------------------------------- */
/* Calculate specific heat capacity of species [J / (mol K)] */
double FixChemShrinkCore::spec_heat (const double *a, double Ti)
{
double value = 0.;
if (Ti < a[0]) { // Temperature smaller than lower bound
const double Tbound_low = a[0];
const double Tbound_low_sq = Tbound_low*Tbound_low;
const double Tbound_low_cb = Tbound_low_sq*Tbound_low;
value = a[10]
+ a[11]*Tbound_low
+ a[12]*Tbound_low_sq
+ a[13]*Tbound_low_cb
+ a[14]*Tbound_low_sq*Tbound_low_sq;
} else if (Ti < a[2]) {
const double Ti_sq = Ti*Ti;
const double Ti_cb = Ti_sq*Ti;
value = a[10]
+ a[11]*Ti
+ a[12]*Ti_sq
+ a[13]*Ti_cb
+ a[14]*Ti_sq*Ti_sq;
} else if (Ti < a[1]) {
const double Ti_sq = Ti*Ti;
const double Ti_cb = Ti_sq*Ti;
value = a[3]
+ a[4]*Ti
+ a[5]*Ti_sq
+ a[6]*Ti_cb
+ a[7]*Ti_sq*Ti_sq;
} else {
const double Tbound_high = a[1];
const double Tbound_high_sq = Tbound_high*Tbound_high;
const double Tbound_high_cb = Tbound_high_sq*Tbound_high;
value = a[3]
+ a[4]*Tbound_high
+ a[5]*Tbound_high_sq
+ a[6]*Tbound_high_cb
+ a[7]*Tbound_high_sq*Tbound_high_sq;
}
return value*Runiv;
}
/* ---------------------------------------------------------------------- */
// Equilibrium constant for low temperature reactions
double FixChemShrinkCore::K_eq_low(int layer, int i)
@ -1707,8 +1809,11 @@ void FixChemShrinkCore::reaction_low(int i, double *dmA_, const double *x0_eq_)
void FixChemShrinkCore::FractionalReduction_low(int i)
{
const double f_WF = 1.0 - relRadii_[i][1]*relRadii_[i][1]*relRadii_[i][1];
const double f_MW = 1.0 - relRadii_[i][2]*relRadii_[i][2]*relRadii_[i][2];
double f_WF = 1.0 - relRadii_[i][1]*relRadii_[i][1]*relRadii_[i][1];
double f_MW = 1.0 - relRadii_[i][2]*relRadii_[i][2]*relRadii_[i][2];
if (f_MW > 1.0 - SMALL) f_MW = 1.0 - SMALL;
if (f_WF > 1.0 - SMALL) f_WF = 1.0 - SMALL;
fracRed_[i][0] = f_WF;
fracRed_[i][1] = f_MW;
@ -1767,8 +1872,8 @@ void FixChemShrinkCore::init_defaults()
{
molMass_A_ = molMass_C_ = 0.0;
rhoeff_ = NULL;
porosity_ = NULL;
pore_diameter_ = tortuosity_ = 0.0;
porosity_ = pore_diameter_ = NULL;
tortuosity_ = 0.0;
relRadii_ = massLayer_ = NULL;
k0_ = Ea_ = NULL;
xA_ = xC_ = NULL;
@ -1779,7 +1884,7 @@ void FixChemShrinkCore::init_defaults()
radius_ = pmass_ = pdensity_ = NULL;
// initialise fix handles
changeOfA_ = changeOfC_ = T_ = molecularDiffusion_ = nuf_ = Rep_ = partP_ = Massterm = reactionHeat_ = NULL;
changeOfA_ = changeOfC_ = T_ = Tpart_ = molecularDiffusion_ = nuf_ = Rep_ = partP_ = Massterm = reactionHeat_ = NULL;
Aterm = Bterm = effDiffBinary = effDiffKnud = fracRed_ = NULL;
dY = dmA_f_ = NULL;
@ -1789,6 +1894,7 @@ void FixChemShrinkCore::init_defaults()
fix_changeOfA_ = NULL;
fix_changeOfC_ = NULL;
fix_tgas_ = NULL; // [K]
fix_tpart_ = NULL; // [K]
fix_reactionHeat_= NULL;
fix_diffcoeff_ = NULL; // [m^2/s]
fix_nuField_ = NULL; // [m^2/s]
@ -1811,6 +1917,8 @@ void FixChemShrinkCore::init_defaults()
fix_Ea_ = NULL; // [J/mol] - [kg*m^2/s^2*mol]
fix_porosity_ = NULL; // [%]
fix_rhoeff_ = NULL;
fix_thermal_capacity_ = NULL;
fix_internal_energy_ = NULL;
fix_tortuosity_ = NULL;
fix_pore_diameter_ = NULL; // [m]
fix_dY_ = NULL;
@ -1824,6 +1932,8 @@ void FixChemShrinkCore::init_defaults()
massA = massC = NULL;
diffA = moleFracA = moleFracC = NULL;
speciesA = speciesC = NULL;
variableCp_ = false;
}
void FixChemShrinkCore::update_fix(int narg, char **arg)
@ -1838,11 +1948,29 @@ void FixChemShrinkCore::update_fix(int narg, char **arg)
{
active_layers(i);
double m = 0.0;
double Cp = 0.0;
double layer_Cp[MAX_LAYERS+1] = {0.};
double Tpart = Tpart_[i];
for (int layer = 0 ; layer <= layers_; layer++)
{
m += massLayer_[i][layer];
}
if (variableCp_)
{
layer_Cp[0] = spec_heat(a_coeff_nasa_Fe,Tpart);
layer_Cp[1] = spec_heat(a_coeff_nasa_FeO,Tpart);
layer_Cp[2] = spec_heat(a_coeff_nasa_Fe3O4,Tpart);
layer_Cp[3] = spec_heat(a_coeff_nasa_Fe2O3,Tpart);
for (int layer = 0 ; layer <= layers_; layer++)
{
Cp += massLayer_[i][layer] * layer_Cp[layer] / layerMolMasses_[layer];
}
Cp /= m;
fix_thermal_capacity_->vector_atom[i] = Cp;
}
pmass_[i] = m*cg_*cg_*cg_;
pdensity_[i] = 0.75*pmass_[i]/(M_PI*radius_[i]*radius_[i]*radius_[i]);
if (fix_polydisp_)

View File

@ -72,6 +72,7 @@ public:
void update_gas_properties(int, const double *);
void heat_of_reaction(int, const double *, const double *, const double *);
double conv_enthalpy(const double *, int);
double spec_heat(const double *, double);
double K_eq_low(int, int);
void reaction_low(int, double *, const double *);
void FractionalReduction_low(int);
@ -120,7 +121,7 @@ public:
// particle-layer variable values
double **rhoeff_;
double *porosity_;
double pore_diameter_;
double *pore_diameter_;
double tortuosity_;
double **relRadii_; // relative radii of individual layers
double **massLayer_; // mass of individual layers
@ -137,6 +138,7 @@ public:
// handles of fixes
double *changeOfA_, *changeOfC_;
double *T_;
double *Tpart_;
double *molecularDiffusion_;
double *nuf_;
double *Rep_;
@ -157,9 +159,11 @@ public:
// coarse_graining factor
double cg_;
// [<creation>]
class FixPropertyAtom *fix_changeOfA_; // [cfd/coupling/chemistry]
class FixPropertyAtom *fix_changeOfC_; // [cfd/coupling/chemistry]
class FixPropertyAtom *fix_tgas_; // [cfd/coupling/chemistry]
class FixPropertyAtom *fix_tpart_; // [heat/gran or cfd/couple/convection or cfd/couple/parttempfield]
class FixPropertyAtom *fix_reactionHeat_; // [cfd/coupling/chemistry]
class FixPropertyAtom *fix_diffcoeff_; // [cfd/coupling/chemistry]
class FixPropertyAtom *fix_nuField_; // [cfd/coupling/chemistry]
@ -182,6 +186,8 @@ public:
class FixPropertyAtom *fix_layerRelRad_; // [script]
class FixPropertyAtom *fix_layerMass_; // [internal]
class FixPropertyAtom *fix_rhoeff_; // [internal]
class FixPropertyAtom *fix_thermal_capacity_; // [script]
class FixPropertyAtom *fix_internal_energy_; // [internal]
#ifdef PER_ATOM_LAYER_DENSITIES
class FixPropertyAtom *fix_layerDens_;
@ -199,6 +205,7 @@ public:
bool created_fix_layerMass_;
bool created_fix_rhoeff_;
bool created_fix_fracRed;
bool created_fix_internal_energy_;
class FixPropertyAtom *fix_dY_; // [internal]
double **dY;
@ -211,6 +218,8 @@ public:
bool limit_reactant_consumption_;
double maxReactantConsumptionFrac_;
bool variableCp_;
};
}

View File

@ -47,6 +47,24 @@ using namespace MathConst;
const double FixChemShrinkCoreSingle::Runiv = 8.3144;
const double FixChemShrinkCoreSingle::a_coeff_CO[] = { 200.00, 6000., 1000.,
3.048486E+00, 1.351728E-03, -4.857941E-07, 7.885364E-11, -4.698075E-15, -1.426612E+04, 6.017098E+00,
3.579534E+00, -6.103537E-04, 1.016814E-06, 9.070059E-10, -9.044245E-13, -1.434409E+04, 3.508409E+00 };
const double FixChemShrinkCoreSingle::a_coeff_CO2[] = { 200.00, 6000., 1000.,
4.636511E+00, 2.741457E-03, -9.958976E-07, 1.603867E-10, -9.161986E-15, -4.902490E+04, -1.934896E+00,
2.356813E+00, 8.984130E-03, -7.122063E-06, 2.457301E-09, -1.428855E-13, -4.837197E+04, 9.900904E+00 };
const double FixChemShrinkCoreSingle::a_coeff_O2[] = { 200.00, 6000., 1000.,
3.660960E+00, 6.563655E-04, -1.411494E-07, 2.057976E-11, -1.299132E-15, -1.215977E+03, 3.415362E+00,
3.782456E+00, -2.996734E-03, 9.847302E-06, -9.681295E-09, 3.243728E-12, -1.063943E+03, 3.657676E+00 };
// coke data are a linear fit to Patisson and Hanrot, Metallurgical and Materials Transactions B 31.2 (2000): 381-390.
// sixth coefficient is needed to get heat of formation at room temperature
const double FixChemShrinkCoreSingle::a_coeff_coke[] = { 298.00, 1300., 1000.,
4.040000E-01, 2.020000E-03, 0.000000E+00, 0.000000E+00, 0.000000E+00, -2.100800E+02, 0.000000E+00,
4.040000E-01, 2.020000E-03, 0.000000E+00, 0.000000E+00, 0.000000E+00, -2.100800E+02, 0.000000E+00 };
// no reasonable data for ash available; due to low mass content, it should not have any significant impact
const double FixChemShrinkCoreSingle::a_coeff_ash[] = { 298.00, 1300., 1000.,
4.040000E-01, 2.020000E-03, 0.000000E+00, 0.000000E+00, 0.000000E+00, -2.100800E+02, 0.000000E+00,
4.040000E-01, 2.020000E-03, 0.000000E+00, 0.000000E+00, 0.000000E+00, -2.100800E+02, 0.000000E+00 };
/* ---------------------------------------------------------------------- */
@ -66,8 +84,7 @@ FixChemShrinkCoreSingle::FixChemShrinkCoreSingle(LAMMPS *lmp, int narg, char **a
T0_(-1.0),
Tmin_(0.0),
nPreFactor_(0),
Cp_coke_(10.2),
T_room_(298)
created_fix_internal_energy_(false)
{
if ((strncmp(style, "chem/shrink/core/single", 15) == 0) && ((!atom->radius_flag) || (!atom->rmass_flag)))
error->all(FLERR, "Fix chem/shrink/core/single needs per particle radius and mass");
@ -112,6 +129,22 @@ FixChemShrinkCoreSingle::FixChemShrinkCoreSingle(LAMMPS *lmp, int narg, char **a
hasargs = true;
iarg_ +=2;
}
else if (strcmp(arg[iarg_],"molMassB") == 0)
{
if (iarg_ + 2 > narg)
error -> fix_error(FLERR, this, "Wrong number of arguments");
molMass_B_ = atof(arg[iarg_+1]);
hasargs = true;
iarg_ +=2;
}
else if (strcmp(arg[iarg_],"nuB") == 0)
{
nu_B_ = atoi(arg[iarg_+1]);
if (nu_B_ < 1)
error -> fix_error(FLERR, this, "nuB is not well-defined");
hasargs = true;
iarg_ +=2;
}
else if (strcmp(arg[iarg_], "speciesC") == 0)
{
if (iarg_ + 2 > narg)
@ -140,19 +173,19 @@ FixChemShrinkCoreSingle::FixChemShrinkCoreSingle(LAMMPS *lmp, int narg, char **a
hasargs = true;
iarg_ +=2;
}
else if (strcmp(arg[iarg_],"molMassB") == 0)
else if (strcmp(arg[iarg_],"molMassD") == 0)
{
if (iarg_ + 2 > narg)
error -> fix_error(FLERR, this, "Wrong number of arguments");
molMass_B_ = atof(arg[iarg_+1]);
molMass_D_ = atof(arg[iarg_+1]);
hasargs = true;
iarg_ +=2;
}
else if (strcmp(arg[iarg_],"nuB") == 0)
else if (strcmp(arg[iarg_],"nuD") == 0)
{
nu_B_ = atoi(arg[iarg_+1]);
if (nu_B_ < 1)
error -> fix_error(FLERR, this, "nuB is not well-defined");
nu_D_ = atoi(arg[iarg_+1]);
if (nu_D_ < 1)
error -> fix_error(FLERR, this, "nuD is not well-defined");
hasargs = true;
iarg_ +=2;
}
@ -306,6 +339,11 @@ FixChemShrinkCoreSingle::FixChemShrinkCoreSingle(LAMMPS *lmp, int narg, char **a
error->fix_error(FLERR,this,"specify positive values for k0 and T0");
}
if (molMass_D_ < SMALL * molMass_B_)
{
error->fix_error(FLERR,this,"set sensible value for molar mass of solid reaction product");
}
if (heatToParticle_ && heatToFluid_)
{
error->fix_error(FLERR,this,"trying to apply reaction heat to both particles and fluid");
@ -492,6 +530,22 @@ void FixChemShrinkCoreSingle::post_create()
fix_dmA_ = modify->add_fix_property_atom(9,const_cast<char**>(fixarg),style);
delete []fixname;
}
fix_internal_energy_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("internalEnergy","property/atom","scalar",0,0,style,false));
if (fix_internal_energy_ == NULL) {
const char* fixarg[9];
fixarg[0]="internalEnergy"; // fixid
fixarg[1]="all";
fixarg[2]="property/atom";
fixarg[3]="internalEnergy"; // propertyid
fixarg[4]="scalar";
fixarg[5]="yes"; // restart yes
fixarg[6]="yes"; // communicate ghost - yes
fixarg[7]="no"; // communicate rev no
fixarg[8]="0.0";
fix_internal_energy_ = modify->add_fix_property_atom(9,const_cast<char**>(fixarg),style);
created_fix_internal_energy_ = true;
}
}
/* ---------------------------------------------------------------------- */
@ -507,6 +561,7 @@ void FixChemShrinkCoreSingle::pre_delete(bool unfixflag)
if (fix_effDiffKnud) { modify->delete_fix(fix_effDiffKnud->id); effDiffKnud = NULL; }
if (fix_dY_) { modify->delete_fix(fix_dY_->id); dY = NULL; }
if (fix_dmA_) { modify->delete_fix(fix_dmA_->id); dmA_f_ = NULL; }
if (fix_internal_energy_ && created_fix_internal_energy_) {modify->delete_fix(fix_internal_energy_->id);}
}
}
@ -574,8 +629,8 @@ void FixChemShrinkCoreSingle::updatePtrs()
pmass_ = atom -> rmass;
pdensity_ = atom -> density;
dY = fix_dY_ -> vector_atom;
dmA_f_ = fix_dmA_ -> vector_atom;
dY = fix_dY_ -> vector_atom;
dmA_f_ = fix_dmA_ -> vector_atom;
reactionheat_ = fix_reactionheat -> vector_atom;
if(limit_reactant_consumption_)
@ -620,6 +675,7 @@ void FixChemShrinkCoreSingle::init()
fix_partPressure_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("partP", "property/atom", "scalar", 0, 0, style));
fix_layerRelRad_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("relRadii", "property/atom", "vector", 0, 0, style));
fix_layerMass_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("massLayer","property/atom","vector",0,0,style));
fix_thermal_capacity_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("thermalCapacity","property/atom","scalar",0,0,style,false));
fix_rhoeff_ = static_cast<FixPropertyAtom*>(modify->find_fix_property("rhoeff", "property/atom", "vector", 0, 0, style));
fix_polydisp_ = static_cast<FixPropertyAtomPolydispParcel*>(modify->find_fix_property("effvolfactor", "property/atom","scalar",0,0,style));
@ -654,7 +710,6 @@ void FixChemShrinkCoreSingle::init()
fix_Aterm = static_cast<FixPropertyAtom*>(modify->find_fix_property(propertyname, "property/atom", "scalar", 0, 0, style));
delete [] propertyname;
propertyname = new char[strlen("Bterm_")+strlen(id)+1];
strcpy (propertyname,"Bterm_");
strcat(propertyname,id);
@ -692,12 +747,21 @@ void FixChemShrinkCoreSingle::init()
delete [] propertyname;
fix_fracRed = static_cast<FixPropertyAtom*>(modify->find_fix_property("fracRed", "property/atom", "vector", 0, 0, style));
fix_reactionheat = static_cast<FixPropertyAtom*>(modify->find_fix_property("reactionHeat", "property/atom", "scalar", 0, 0, style));
fix_reactionheat = static_cast<FixPropertyAtom*>(modify->find_fix_property("reactionHeat", "property/atom", "scalar", 0, 0, style));
if(limit_reactant_consumption_)
{
fix_reactantPerParticle_ = static_cast<FixPropertyAtom*>(modify -> find_fix_property("reactantPerParticle","property/atom","scalar",0,0,style));
}
if(fix_thermal_capacity_)
{
variableCp_ = true;
}
else
{
variableCp_ = false;
}
}
/* ---------------------------------------------------------------------- */
@ -984,7 +1048,6 @@ void FixChemShrinkCoreSingle::reaction(int i, double &dmA_, const double x0_eq_)
void FixChemShrinkCoreSingle::update_atom_properties(int i, const double dmA_)
{
if (!shrink_) return;
if (screenflag_ && screen)
fprintf(screen,"run update atom props \n");
@ -992,23 +1055,29 @@ void FixChemShrinkCoreSingle::update_atom_properties(int i, const double dmA_)
// initialize radius, mass change of layer and sum of particle
double rad[2] = {0.};
double dmL_[2] = {0.}; // mass flow rate between each layer i.e. (btw h->m, m->w, w->Fe) must consider reduction and growth at the same time
double dmL_[2] = {0.};
double sum_mass_p_new = 0.0;
double Cp = 0.0;
double layer_Cp[2] = {0.};
double Tpart = Tpart_[i];
double H = 0.0;
double layer_H[2] = {0.};
// Mass change of inner layer
dmL_[1] = dmA_ * nu_B_ * (molMass_B_ / molMass_A_);
layer_H[0] = conv_enthalpy(a_coeff_ash, Tpart);
layer_H[1] = conv_enthalpy(a_coeff_coke,Tpart);
// New layer mass
massLayer_[i][1] -= dmL_[1]*scale_reduction_rate;
if (massLayer_[i][1] < 0.0)
massLayer_[i][1] = 0.0;
if (shrink_)
{
// Mass change of inner layer
dmL_[1] = dmA_ * nu_B_ * (molMass_B_ / molMass_A_);
// NOTE: This keeps the particle radius and layer porosities and densities constant,
// hence there is a slight mass conservation error.
// Alternatively, one could provide details on the chemical reaction for the product layer.
// New layer mass
massLayer_[i][1] -= dmL_[1]*scale_reduction_rate;
if (massLayer_[i][1] < 0.0) massLayer_[i][1] = 0.0;
dmL_[0] = dmL_[1] * rhoeff_[i][0] * porosity_[0] / (rhoeff_[i][1] * porosity_[1]);
massLayer_[i][0] += dmL_[0]*scale_reduction_rate;
dmL_[0] = dmL_[1] * molMass_D_ * nu_D_ / (molMass_B_ * nu_B_);
massLayer_[i][0] += dmL_[0]*scale_reduction_rate;
}
for (int j = 0; j <= layers_; j++)
{
@ -1018,6 +1087,22 @@ void FixChemShrinkCoreSingle::update_atom_properties(int i, const double dmA_)
sum_mass_p_new += massLayer_[i][j];
}
if (variableCp_)
{
layer_Cp[0] = spec_heat(a_coeff_ash,Tpart);
layer_Cp[1] = spec_heat(a_coeff_coke,Tpart);
Cp = massLayer_[i][0] * layer_Cp[0] / molMass_D_;
if (layers_ > 0) Cp += massLayer_[i][1] * layer_Cp[1] / molMass_B_; // only include this contribution if core is still present
Cp /= sum_mass_p_new;
fix_thermal_capacity_->vector_atom[i] = Cp;
}
H = massLayer_[i][0] * layer_H[0] / molMass_D_;
if (layers_ > 0) H += massLayer_[i][1] * layer_H[1] / molMass_B_;
fix_internal_energy_->vector_atom[i] = H*cg_*cg_*cg_;
if (!shrink_) return;
// if (screen) fprintf(screen,"total mass of particle = %f \n", sum_mass_p_new);
// Total mass of particle with coarse-graining
@ -1025,6 +1110,8 @@ void FixChemShrinkCoreSingle::update_atom_properties(int i, const double dmA_)
// if (screen) fprintf(screen, "pmass = %f \n",pmass_[i]);
rad[1] = cbrt((0.75*massLayer_[i][1])/(rhoeff_[i][1]*M_PI));
// NOTE: This keeps the outer radius of the particle constant. This induces a slight mass conservation error
// unless the inner (B) and outer (D) layer satisfy molMass_D_ * nu_D_ / (porosity_D_ * rho_D_) = molMass_B_ * nu_B_ / (porosity_B_ * rho_B_)
rad[0] = radius_[i]/cg_;
if (fix_polydisp_)
@ -1074,103 +1161,34 @@ void FixChemShrinkCoreSingle::FractionalReduction(int i)
fracRed_[i][0] = f;
}
/* ---------------------------------------------------------------------- */
/* heat of reaction calcualtion using the Shomate equation and data from https://webbook.nist.gov */
/* heat of reaction calcualtion using the NASA 7 coefficient polynomials */
void FixChemShrinkCoreSingle::heat_of_reaction(int i, const double dmA_)
{
if (!heatToParticle_ && !heatToFluid_) return;
double T = T_[i];
double Tpart = Tpart_[i];
double dH = 0.0;
double dHcoeffs[6] = {0.0};
// reaction enthalpy in J/mol
if (reactionHeatIndex_ == 0) // O2 + 2C -> 2C0
{
if (T<700)
{
dHcoeffs[0] = 19.8;
dHcoeffs[1] = 32.44;
dHcoeffs[2] = -49.77;
dHcoeffs[3] = 31.17;
dHcoeffs[4] = 0.26;
dHcoeffs[5] = -227.12;
}
else if (T<1300)
{
dHcoeffs[0] = 21.09;
dHcoeffs[1] = 3.43;
dHcoeffs[2] = 12.09;
dHcoeffs[3] = -6.13;
dHcoeffs[4] = 1.0;
dHcoeffs[5] = -224.7;
}
else if (T<2000)
{
dHcoeffs[0] = 40.27;
dHcoeffs[1] = -6.17;
dHcoeffs[2] = 3.57;
dHcoeffs[3] = -0.77;
dHcoeffs[4] = -5.82;
dHcoeffs[5] = -244.36;
}
else
{
dHcoeffs[0] = 49.39;
dHcoeffs[1] = -8.12;
dHcoeffs[2] = 1.6;
dHcoeffs[3] = -0.13;
dHcoeffs[4] = -15.81;
dHcoeffs[5] = -261.02;
}
dH -= conv_enthalpy(a_coeff_O2,T);
dH += 2 * conv_enthalpy(a_coeff_CO,T);
dH -= 2 * conv_enthalpy(a_coeff_coke,Tpart);
// neglect any contribution to ash
}
else if (reactionHeatIndex_ == 1) // CO2 + C -> 2CO
{
if (T<1200)
{
dHcoeffs[0] = 26.12;
dHcoeffs[1] = -42.99;
dHcoeffs[2] = 41.79;
dHcoeffs[3] = -13.29;
dHcoeffs[4] = 0.4;
dHcoeffs[5] = 167.59;
}
else if (T<1300)
{
dHcoeffs[0] = -7.05;
dHcoeffs[1] = 9.48;
dHcoeffs[2] = 8.59;
dHcoeffs[3] = -5.38;
dHcoeffs[4] = 6.71;
dHcoeffs[5] = 189.9;
}
else
{
dHcoeffs[0] = 12.13;
dHcoeffs[1] = -0.12;
dHcoeffs[2] = 0.07;
dHcoeffs[3] = -0.02;
dHcoeffs[4] = -0.11;
dHcoeffs[5] = 170.24;
}
}
T *= 0.001;
// reaction enthalpy in kJ/mol
dH = dHcoeffs[0]*T + 0.5*dHcoeffs[1]*T*T + 0.333*dHcoeffs[2]*T*T*T;
dH += 0.25*dHcoeffs[3]*T*T*T*T - dHcoeffs[4]/T + dHcoeffs[5];
// reaction enthalpy (enthalpy of formation + thermal energy of gas phases) in J/mol
dH *= 1000;
// add contribution of coke thermal energy
if (reactionHeatIndex_ == 0) // O2 + 2C -> 2C0
{
dH -= 2*Cp_coke_*(Tpart-T_room_);
}
else if (reactionHeatIndex_ == 1) // CO2 + C -> 2CO
{
dH -= Cp_coke_*(Tpart-T_room_);
dH -= conv_enthalpy(a_coeff_CO2,T);
dH += 2 * conv_enthalpy(a_coeff_CO,T);
dH -= conv_enthalpy(a_coeff_coke,Tpart);
// neglect any contribution to ash
}
double cg3 = cg_ * cg_ * cg_;
@ -1178,7 +1196,7 @@ void FixChemShrinkCoreSingle::heat_of_reaction(int i, const double dmA_)
if (heatToParticle_)
{
// heat flux = released heat / (nevery * dt), but it is reset to 0 in scalar transport equation
// at the beginning of each step, hence an additional factor nevery which cancels that in the denominator
// at the beginning of each step, hence an additional factor nevery which cancels that in the denominator
heatFlux_[i] -= dmA_ / molMass_A_ * dH / TimeStep * cg3;
}
else
@ -1187,13 +1205,110 @@ void FixChemShrinkCoreSingle::heat_of_reaction(int i, const double dmA_)
reactionheat_[i] -= dmA_ / molMass_A_ * dH * cg3;
}
}
/* ---------------------------------------------------------------------- */
/* Calculate conventional enthalpies of species */
double FixChemShrinkCoreSingle::conv_enthalpy (const double *a, double Ti)
{
double value = 0.;
if (Ti < a[0]) { // Temperature smaller than lower bound
const double Tbound_low = a[0];
const double Tbound_low_sq = Tbound_low*Tbound_low;
const double Tbound_low_cb = Tbound_low_sq*Tbound_low;
value = a[10]*Tbound_low
+ a[11]*Tbound_low_sq*0.5
+ a[12]*Tbound_low_cb/3.0
+ a[13]*Tbound_low_sq*Tbound_low_sq*0.25
+ a[14]*Tbound_low_sq*Tbound_low_cb*0.20
+ a[15];
} else if (Ti < a[2]) {
const double Ti_sq = Ti*Ti;
const double Ti_cb = Ti_sq*Ti;
value = a[10]*Ti
+ a[11]*Ti_sq*0.5
+ a[12]*Ti_cb/3.0
+ a[13]*Ti_sq*Ti_sq*0.25
+ a[14]*Ti_sq*Ti_cb*0.20
+ a[15];
} else if (Ti < a[1]) {
const double Ti_sq = Ti*Ti;
const double Ti_cb = Ti_sq*Ti;
value = a[3]*Ti
+ a[4]*Ti_sq*0.5
+ a[5]*Ti_cb/3.0
+ a[6]*Ti_sq*Ti_sq*0.25
+ a[7]*Ti_sq*Ti_cb*0.20
+ a[8];
} else {
const double Tbound_high = a[1];
const double Tbound_high_sq = Tbound_high*Tbound_high;
const double Tbound_high_cb = Tbound_high_sq*Tbound_high;
value = a[3]*Tbound_high
+ a[4]*Tbound_high_sq*0.5
+ a[5]*Tbound_high_cb/3.0
+ a[6]*Tbound_high_sq*Tbound_high_sq*0.25
+ a[7]*Tbound_high_sq*Tbound_high_cb*0.20
+ a[8];
}
return value*Runiv;
}
/* ---------------------------------------------------------------------- */
/* Calculate specific heat capacity of species [J / (mol K)] */
double FixChemShrinkCoreSingle::spec_heat (const double *a, double Ti)
{
double value = 0.;
if (Ti < a[0]) { // Temperature smaller than lower bound
const double Tbound_low = a[0];
const double Tbound_low_sq = Tbound_low*Tbound_low;
const double Tbound_low_cb = Tbound_low_sq*Tbound_low;
value = a[10]
+ a[11]*Tbound_low
+ a[12]*Tbound_low_sq
+ a[13]*Tbound_low_cb
+ a[14]*Tbound_low_sq*Tbound_low_sq;
} else if (Ti < a[2]) {
const double Ti_sq = Ti*Ti;
const double Ti_cb = Ti_sq*Ti;
value = a[10]
+ a[11]*Ti
+ a[12]*Ti_sq
+ a[13]*Ti_cb
+ a[14]*Ti_sq*Ti_sq;
} else if (Ti < a[1]) {
const double Ti_sq = Ti*Ti;
const double Ti_cb = Ti_sq*Ti;
value = a[3]
+ a[4]*Ti
+ a[5]*Ti_sq
+ a[6]*Ti_cb
+ a[7]*Ti_sq*Ti_sq;
} else {
const double Tbound_high = a[1];
const double Tbound_high_sq = Tbound_high*Tbound_high;
const double Tbound_high_cb = Tbound_high_sq*Tbound_high;
value = a[3]
+ a[4]*Tbound_high
+ a[5]*Tbound_high_sq
+ a[6]*Tbound_high_cb
+ a[7]*Tbound_high_sq*Tbound_high_sq;
}
return value*Runiv;
}
/* ---------------------------------------------------------------------- */
void FixChemShrinkCoreSingle::init_defaults()
{
molMass_A_ = molMass_B_ = molMass_C_ = 0.0;
molMass_A_ = molMass_B_ = molMass_C_ = molMass_D_ = 0.0;
rhoeff_ = NULL;
porosity_ = NULL;
pore_diameter_ = tortuosity_ = 0.0;
@ -1202,7 +1317,7 @@ void FixChemShrinkCoreSingle::init_defaults()
scale_reduction_rate = 1.;
layerDensities_ = NULL;
nu_A_ = nu_B_ = nu_C_ = 1;
nu_A_ = nu_B_ = nu_C_ = nu_D_ = 1;
// particle properties total
radius_ = pmass_ = pdensity_ = NULL;
@ -1237,6 +1352,7 @@ void FixChemShrinkCoreSingle::init_defaults()
fix_partPressure_ = NULL; // Pascal
fix_layerRelRad_ = NULL;
fix_layerMass_ = NULL; // [kg]
fix_thermal_capacity_ = NULL;
fix_layerDens_ = NULL; // [kg/m^3]
fix_porosity_ = NULL; // [%]
fix_rhoeff_ = NULL;
@ -1255,6 +1371,8 @@ void FixChemShrinkCoreSingle::init_defaults()
massA = massC = NULL;
diffA = moleFracA = moleFracC = NULL;
speciesA = speciesC = NULL;
variableCp_ = false;
}
void FixChemShrinkCoreSingle::update_fix(int narg, char **arg)
@ -1266,11 +1384,33 @@ void FixChemShrinkCoreSingle::update_fix(int narg, char **arg)
{
if (mask[i] & groupbit)
{
pmass_[i] = (massLayer_[i][0] + massLayer_[i][1])*cg_*cg_*cg_;
active_layers(i);
double m = 0.0;
double Cp = 0.0;
double layer_Cp[2] = {0.};
double Tpart = Tpart_[i];
m = massLayer_[i][0];
if (layers_ > 0)
{
m += massLayer_[i][1];
}
if (variableCp_)
{
layer_Cp[0] = spec_heat(a_coeff_ash,Tpart);
layer_Cp[1] = spec_heat(a_coeff_coke,Tpart);
Cp = massLayer_[i][0] * layer_Cp[0] / molMass_D_;
if (layers_ > 0) Cp += massLayer_[i][1] * layer_Cp[1] / molMass_B_; // only include this contribution if core is still present
Cp /= m;
fix_thermal_capacity_->vector_atom[i] = Cp;
}
pmass_[i] = m*cg_*cg_*cg_;
pdensity_[i] = 0.75*pmass_[i]/(M_PI*radius_[i]*radius_[i]*radius_[i]);
if (fix_polydisp_)
{
pdensity_[i] /= effvolfactors_[i];
pdensity_[i] /= effvolfactors_[i];
}
}
}

View File

@ -70,18 +70,26 @@ public:
// update reactant and product gas masses depending on chemical reaction rate
void update_gas_properties(int, const double);
void heat_of_reaction(int, const double);
double conv_enthalpy(const double *, double);
double spec_heat(const double *, double);
// pre-defined variables for reduction process
// int const nmaxlayers_;
static double const Runiv; // universal gas constant
static const double a_coeff_CO[];
static const double a_coeff_CO2[];
static const double a_coeff_O2[];
static const double a_coeff_ash[];
static const double a_coeff_coke[];
// variables
bool screenflag_;
double TimeStep;
char* massA, *massC;
double molMass_A_, molMass_B_, molMass_C_;
int nu_A_, nu_B_, nu_C_;
double molMass_A_, molMass_B_, molMass_C_, molMass_D_;
int nu_A_, nu_B_, nu_C_, nu_D_;
double scale_reduction_rate;
char *diffA;
@ -166,6 +174,9 @@ public:
// particle properties
class FixPropertyAtom *fix_layerRelRad_; // [script]
class FixPropertyAtom *fix_layerMass_; // [script]
class FixPropertyAtom *fix_thermal_capacity_; // [script]
class FixPropertyAtom *fix_internal_energy_; // [internal]
bool created_fix_internal_energy_;
#ifdef PER_ATOM_LAYER_DENSITIES
class FixPropertyAtom *fix_layerDens_;
@ -194,10 +205,7 @@ public:
bool limit_reactant_consumption_;
double maxReactantConsumptionFrac_;
// constant parameters for reactions
const double Cp_coke_; // heat capacity coke in J/(mol K)
const double T_room_;
bool variableCp_;
};
}

View File

@ -1,14 +1,26 @@
/* ----------------------------------------------------------------------
LIGGGHTS - LAMMPS Improved for General Granular and Granular Heat
Transfer Simulations
LIGGGHTS is part of the CFDEMproject
www.liggghts.com | www.cfdem.com
Department for Particule Flow Modelling
Copyright 2014- JKU Linz
LIGGGHTS is based on LAMMPS
LAMMPS - Large-scale Atomic/Molecular Massively Parallel Simulator
http://lammps.sandia.gov, Sandia National Laboratories
Steve Plimpton, sjplimp@sandia.gov
Copyright (2003) Sandia Corporation. Under the terms of Contract
DE-AC04-94AL85000 with Sandia Corporation, the U.S. Government retains
certain rights in this software. This software is distributed under
the GNU General Public License.
This software is distributed under the GNU General Public License.
See the README file in the top-level LAMMPS directory.
See the README file in the top-level directory.
------------------------------------------------------------------------- */
/* ----------------------------------------------------------------------
Contributing authors:
Thomas Lichtenegger (JKU Linz)
------------------------------------------------------------------------- */
#include <stdlib.h>
@ -30,6 +42,7 @@ using namespace FixConst;
FixExecute::FixExecute(LAMMPS *lmp, int narg, char **arg) :
Fix(lmp, narg, arg),
execution_point(1),
conditional(false),
file(false),
var(NULL),
@ -86,6 +99,12 @@ FixExecute::FixExecute(LAMMPS *lmp, int narg, char **arg) :
iarg++;
hasargs = true;
}
else if(strcmp(arg[iarg],"start_of_step") == 0)
{
execution_point = 0;
iarg++;
hasargs = true;
}
else
{
error->fix_error(FLERR,this,"unknown keyword");
@ -105,13 +124,28 @@ FixExecute::~FixExecute()
int FixExecute::setmask()
{
int mask = 0;
mask |= END_OF_STEP;
if (execution_point == 0) mask |= INITIAL_INTEGRATE;
if (execution_point == 1) mask |= END_OF_STEP;
return mask;
}
/* ---------------------------------------------------------------------- */
void FixExecute::initial_integrate(int)
{
execution_command();
}
/* ---------------------------------------------------------------------- */
void FixExecute::end_of_step()
{
execution_command();
}
/* ---------------------------------------------------------------------- */
void FixExecute::execution_command()
{
if (conditional)
{

View File

@ -1,14 +1,26 @@
/* ----------------------------------------------------------------------
LIGGGHTS - LAMMPS Improved for General Granular and Granular Heat
Transfer Simulations
LIGGGHTS is part of the CFDEMproject
www.liggghts.com | www.cfdem.com
Department for Particule Flow Modelling
Copyright 2014- JKU Linz
LIGGGHTS is based on LAMMPS
LAMMPS - Large-scale Atomic/Molecular Massively Parallel Simulator
http://lammps.sandia.gov, Sandia National Laboratories
Steve Plimpton, sjplimp@sandia.gov
Copyright (2003) Sandia Corporation. Under the terms of Contract
DE-AC04-94AL85000 with Sandia Corporation, the U.S. Government retains
certain rights in this software. This software is distributed under
the GNU General Public License.
This software is distributed under the GNU General Public License.
See the README file in the top-level LAMMPS directory.
See the README file in the top-level directory.
------------------------------------------------------------------------- */
/* ----------------------------------------------------------------------
Contributing authors:
Thomas Lichtenegger (JKU Linz)
------------------------------------------------------------------------- */
#ifdef FIX_CLASS
@ -30,12 +42,15 @@ class FixExecute : public Fix {
FixExecute(class LAMMPS *, int, char **);
~FixExecute();
int setmask();
void initial_integrate(int);
void end_of_step();
private:
int me;
char *string;
int execution_point; // 0 initial_integrate, 1 end_of_step
// conditional execution
bool conditional;
// execute whole input file
@ -48,6 +63,8 @@ class FixExecute : public Fix {
// single execution
bool once;
int execution_step;
void execution_command();
};
}

View File

@ -30,6 +30,7 @@
#include <stdlib.h>
#include <math.h>
#include <assert.h>
#include <limits>
#include "force.h"
#include "region.h"
@ -516,7 +517,7 @@ void FixInsertPackDense::handle_next_front_sphere()
}
// then, search for candidate point closest to insertion center
double dist_min_sq = 1000.;
double dist_min_sq = std::numeric_limits<double>::max();
ParticleVector::iterator closest_candidate;
for(ParticleVector::iterator it = candidatePoints.begin(); it != candidatePoints.end(); ++it){
double dist_sq = pointDistanceSquared((*it).x,x_init);

View File

@ -86,6 +86,8 @@ FixInsertPackFaceUniverse::FixInsertPackFaceUniverse(LAMMPS *lmp, int narg, char
// no fixed total number of particles inserted by this fix exists
if (strcmp(style,"insert/pack/face/universe") == 0)
ninsert_exists = 0;
next_reneighbor = update->ntimestep + insert_every - (update->ntimestep % insert_every);
}
/* ---------------------------------------------------------------------- */

View File

@ -0,0 +1,167 @@
/* ----------------------------------------------------------------------
LIGGGHTS - LAMMPS Improved for General Granular and Granular Heat
Transfer Simulations
LIGGGHTS is part of the CFDEMproject
www.liggghts.com | www.cfdem.com
Department for Particule Flow Modelling
Copyright 2014- JKU Linz
LIGGGHTS is based on LAMMPS
LAMMPS - Large-scale Atomic/Molecular Massively Parallel Simulator
http://lammps.sandia.gov, Sandia National Laboratories
Steve Plimpton, sjplimp@sandia.gov
This software is distributed under the GNU General Public License.
See the README file in the top-level directory.
------------------------------------------------------------------------- */
/* ----------------------------------------------------------------------
Contributing authors:
Thomas Lichtenegger (JKU Linz)
------------------------------------------------------------------------- */
#include <math.h>
#include <stdlib.h>
#include <string.h>
#include "fix_limit_property_atom.h"
#include "atom.h"
#include "memory.h"
#include "error.h"
//NP modified C.K.
#include "atom_vec.h"
#include "force.h"
#include "update.h"
#include "comm.h"
#include "modify.h"
#include "mpi_liggghts.h"
using namespace LAMMPS_NS;
using namespace FixConst;
/* ---------------------------------------------------------------------- */
FixLimitPropertyAtom::FixLimitPropertyAtom(LAMMPS *lmp, int narg, char **arg, bool parse) :
Fix(lmp, narg, arg)
{
/*NL*/ //if (screen) fprintf(screen,"HERE parse for id %s\n",id);
if(parse) parse_args(narg,arg);
}
void FixLimitPropertyAtom::parse_args(int narg, char **arg)
{
int n = strlen(arg[3]) + 1;
targetfixname = new char[n];
strcpy(targetfixname,arg[3]);
fix_target_ = NULL;
if (narg < 8 || (narg - 6) % 2)
{
error->all(FLERR,"Wrong number of arguments in fix limit/property/atom.");
}
nvalues = (narg - 6)/2;
maxvalues = new double[nvalues];
minvalues = new double[nvalues];
if (strcmp(arg[4],"min") == 0)
{
for (int j = 0; j < nvalues; j++)
{
minvalues[j] = atof(arg[5+j]);
}
}
else error->all(FLERR,"Expected to find minimum limiting values");
if (strcmp(arg[5+nvalues],"max") == 0)
{
for (int j = 0; j < nvalues; j++)
{
maxvalues[j] = atof(arg[6+nvalues+j]);
}
}
else error->all(FLERR,"Expected to find maximum limiting values");
}
/* ---------------------------------------------------------------------- */
FixLimitPropertyAtom::~FixLimitPropertyAtom()
{
delete[] targetfixname;
delete[] maxvalues;
delete[] minvalues;
}
/* ---------------------------------------------------------------------- */
void FixLimitPropertyAtom::init()
{
if (nvalues == 1)
{
fix_target_ = static_cast<FixPropertyAtom*>(modify->find_fix_property(targetfixname, "property/atom", "scalar", 0, 0, "fix/limit/property/atom"));
}
else
{
fix_target_ = static_cast<FixPropertyAtom*>(modify->find_fix_property(targetfixname, "property/atom", "vector", 0, 0, "fix/limit/property/atom"));
}
if (fix_target_->num_defaultvalues() != nvalues)
{
char errmsg[400];
sprintf(errmsg,"Number of values to be limited by FixLimitPropertyAtom does not match that stored in %s",targetfixname);
error->all(FLERR,errmsg);
}
}
/* ---------------------------------------------------------------------- */
int FixLimitPropertyAtom::setmask()
{
int mask = 0;
mask |= END_OF_STEP;
return mask;
}
/* ---------------------------------------------------------------------- */
void FixLimitPropertyAtom::end_of_step()
{
int nlocal = atom->nlocal;
if (nvalues == 1)
{
double *targetvalue = fix_target_->vector_atom;
for (int i = 0; i < nlocal; ++i)
{
if (targetvalue[i] < minvalues[0])
{
targetvalue[i] = minvalues[0];
}
else if (targetvalue[i] > maxvalues[0])
{
targetvalue[i] = maxvalues[0];
}
}
}
else
{
double **targetvalue = fix_target_->array_atom;
for (int i = 0; i < nlocal; ++i)
{
for (int j = 0; j < nvalues; j++)
{
if (targetvalue[i][j] < minvalues[j])
{
targetvalue[i][j] = minvalues[j];
}
else if (targetvalue[i][j] > maxvalues[j])
{
targetvalue[i][j] = maxvalues[j];
}
}
}
}
}

View File

@ -0,0 +1,63 @@
/* ----------------------------------------------------------------------
LIGGGHTS - LAMMPS Improved for General Granular and Granular Heat
Transfer Simulations
LIGGGHTS is part of the CFDEMproject
www.liggghts.com | www.cfdem.com
Department for Particule Flow Modelling
Copyright 2014- JKU Linz
LIGGGHTS is based on LAMMPS
LAMMPS - Large-scale Atomic/Molecular Massively Parallel Simulator
http://lammps.sandia.gov, Sandia National Laboratories
Steve Plimpton, sjplimp@sandia.gov
This software is distributed under the GNU General Public License.
See the README file in the top-level directory.
------------------------------------------------------------------------- */
/* ----------------------------------------------------------------------
Contributing authors:
Thomas Lichtenegger (JKU Linz)
------------------------------------------------------------------------- */
#ifdef FIX_CLASS
FixStyle(limit/property/atom,FixLimitPropertyAtom)
#else
#ifndef LMP_FIX_LIMIT_PROPERTY_ATOM_H
#define LMP_FIX_LIMIT_PROPERTY_ATOM_H
#include "fix.h"
#include "input.h"
#include "fix_property_atom.h"
namespace LAMMPS_NS {
class FixLimitPropertyAtom : public Fix {
friend class Set;
public:
FixLimitPropertyAtom(class LAMMPS *, int, char **,bool parse = true);
~FixLimitPropertyAtom();
void init();
virtual int setmask();
virtual void end_of_step();
protected:
virtual void parse_args(int narg, char **arg);
char *targetfixname; // name of the fix property atom to be limited
class FixPropertyAtom* fix_target_;
int nvalues;
double *maxvalues;
double *minvalues;
}; //end class
}
#endif
#endif

View File

@ -62,6 +62,7 @@ FixMassflowMesh::FixMassflowMesh(LAMMPS *lmp, int narg, char **arg) :
nparticles_(0),
fix_property_(0),
property_sum_(0.),
verbose_(false),
screenflag_(false),
fp_(0),
writeTime_(false),
@ -100,7 +101,7 @@ FixMassflowMesh::FixMassflowMesh(LAMMPS *lmp, int narg, char **arg) :
hasargs = true;
} else if(strcmp(arg[iarg],"mesh") == 0) {
if(narg < iarg+2)
error->fix_error(FLERR,this,"not enough arguments for 'insert_stream'");
error->fix_error(FLERR,this,"not enough arguments for 'mesh'");
iarg++;
fix_mesh_ = static_cast<FixMeshSurface*>(modify->find_fix_id_style(arg[iarg++],"mesh/surface"));
if(!fix_mesh_)
@ -114,7 +115,7 @@ FixMassflowMesh::FixMassflowMesh(LAMMPS *lmp, int narg, char **arg) :
hasargs = true;
} else if(strcmp(arg[iarg],"count") == 0) {
if(narg < iarg+2)
error->fix_error(FLERR,this,"not enough arguments for 'insert_stream'");
error->fix_error(FLERR,this,"not enough arguments for 'count'");
iarg++;
if(strcmp(arg[iarg],"once") == 0)
once_ = true;
@ -160,26 +161,35 @@ FixMassflowMesh::FixMassflowMesh(LAMMPS *lmp, int narg, char **arg) :
fp_ = fopen(filecurrent,"a");
delete [] filecurrent;
if (fp_ == NULL) {
char str[128];
char str[512];
sprintf(str,"Cannot open file %s",arg[iarg+1]);
error->fix_error(FLERR,this,str);
}
iarg += 2;
hasargs = true;
} else if (strcmp(arg[iarg],"verbose") == 0) {
if(narg < iarg+2)
error->fix_error(FLERR,this,"not enough arguments for 'verbose'");
if(strcmp(arg[iarg+1],"yes") == 0)
verbose_ = true;
else if(strcmp(arg[iarg+1],"no") != 0)
error->fix_error(FLERR,this,"expecting 'yes' or 'no' for 'verbose'");
iarg += 2;
hasargs = true;
} else if (strcmp(arg[iarg],"screen") == 0) {
if(narg < iarg+2)
error->fix_error(FLERR,this,"Illegal keyword entry");
error->fix_error(FLERR,this,"not enough arguments for 'screen'");
if (strcmp(arg[iarg+1],"yes") == 0) screenflag_ = true;
else if (strcmp(arg[iarg+1],"no") == 0) screenflag_ = false;
else error->all(FLERR,"Illegal fix print command");
else error->fix_error(FLERR,this,"expecting 'yes' or 'no' for 'screen'");
iarg += 2;
hasargs = true;
} else if (strcmp(arg[iarg],"delete_atoms") == 0) {
if(narg < iarg+2)
error->fix_error(FLERR,this,"Illegal keyword entry");
error->fix_error(FLERR,this,"not enough arguments for 'delete_atoms'");
if (strcmp(arg[iarg+1],"yes") == 0) delete_atoms_ = true;
else if (strcmp(arg[iarg+1],"no") == 0) delete_atoms_ = false;
else error->all(FLERR,"Illegal delete command");
else error->fix_error(FLERR,this,"expecting 'yes' or 'no' for 'delete_atoms'");
iarg += 2;
hasargs = true;
} else if(strcmp(style,"massflow/mesh") == 0)
@ -279,8 +289,17 @@ void FixMassflowMesh::post_create()
if(fix_ms_)
{
ms_ = &fix_ms_->data();
ms_counter_ = ms_->prop().addElementProperty< ScalarContainer<int> >("counter_ms","comm_exchange_borders","frame_invariant", "restart_yes");
ms_counter_->setDefaultValue(-1);
char *counter_ms_name = new char[strlen(id) + 12];
sprintf(counter_ms_name,"counter_ms_%s",id);
ms_counter_ = ms_->prop().getElementProperty<ScalarContainer<int> >(counter_ms_name);
if(!ms_counter_)
{
ms_counter_ = ms_->prop().addElementProperty<ScalarContainer<int> >(counter_ms_name,"comm_exchange_borders","frame_invariant","restart_yes");
ms_counter_->setDefaultValue(-1);
}
delete []counter_ms_name;
if(delete_atoms_)
error->fix_error(FLERR,this,"can not use 'delete_atoms' with fix multisphere");
@ -536,24 +555,42 @@ void FixMassflowMesh::pre_exchange()
{
double mass_deleted_this_ = 0.;
int nparticles_deleted_this_ = 0.;
int *atom_map_array = atom->get_map_array();
int tag_max = atom->tag_max();
// delete particles
while (atom_tags_delete_.size() > 0)
{
int iPart = atom->map(atom_tags_delete_[0]);
if(atom_tags_delete_[0] <= tag_max)
{
int iPart = atom->map(atom_tags_delete_[0]);
mass_deleted_this_ += atom->rmass[iPart];
nparticles_deleted_this_++;
if(iPart >= 0)
{
mass_deleted_this_ += atom->rmass[iPart];
nparticles_deleted_this_++;
atom->avec->copy(atom->nlocal-1,iPart,1);
atom->avec->copy(atom->nlocal-1,iPart,1);
//NP manipulate atom map array
//NP need to do this since atom map is needed for deletion
atom_map_array[atom->tag[atom->nlocal-1]] = iPart;
// update atom map
// need to do this since atom map is needed to get local index for deletion
atom->map_one(atom->tag[atom->nlocal-1], iPart); // update map for copied particle
atom->nlocal--;
atom->nlocal--;
}
else if (verbose_)
{
// particle may have been removed already by a different deleting command
// e.g. if the particle is in the neighbor list of the meshes of multiple massflow/mesh fixes
error->fix_warning(FLERR, this, "failed to find atom for deletion (possibly already deleted by another deleting command)");
}
}
else if (verbose_)
{
// particle may have been removed already by a different deleting command
// e.g. if the particle is in the neighbor list of the meshes of multiple massflow/mesh fixes
error->fix_warning(FLERR, this, "failed to find atom for deletion (possibly already deleted by another deleting command)");
}
atom_tags_delete_.erase(atom_tags_delete_.begin());
}
@ -569,6 +606,9 @@ void FixMassflowMesh::pre_exchange()
//NP tags and maps
if(nparticles_deleted_this_)
{
bigint nblocal = atom->nlocal;
MPI_Allreduce(&nblocal,&atom->natoms,1,MPI_LMP_BIGINT,MPI_SUM,world);
if (atom->tag_enable) {
if (atom->map_style) {
atom->nghost = 0;

View File

@ -91,6 +91,7 @@ class FixMassflowMesh : public Fix {
class FixPropertyAtom *fix_property_;
double property_sum_;
bool verbose_;
// data write
bool screenflag_;
FILE *fp_;

View File

@ -75,6 +75,7 @@ FixMassflowMeshFace::FixMassflowMeshFace(LAMMPS *lmp, int narg, char **arg) :
property_check_int_(false),
fix_property_(NULL),
property_sum_(0.),
verbose_(false),
screenflag_(false),
fp_(NULL),
mass_last_(0.),
@ -167,13 +168,23 @@ FixMassflowMeshFace::FixMassflowMeshFace(LAMMPS *lmp, int narg, char **arg) :
fp_ = fopen(filecurrent,"w");
else
fp_ = fopen(filecurrent,"a");
delete [] filecurrent;
if (fp_ == NULL) {
char str[128];
char str[512];
sprintf(str,"Cannot open file %s",arg[iarg+1]);
error->fix_error(FLERR,this,str);
}
iarg += 2;
hasargs = true;
} else if (strcmp(arg[iarg],"verbose") == 0) {
if(narg < iarg+2)
error->fix_error(FLERR,this,"not enough arguments for 'verbose'");
if(strcmp(arg[iarg+1],"yes") == 0)
verbose_ = true;
else if(strcmp(arg[iarg+1],"no") != 0)
error->fix_error(FLERR,this,"expecting 'yes' or 'no' for 'verbose'");
iarg += 2;
hasargs = true;
} else if (strcmp(arg[iarg],"screen") == 0) {
if(narg < iarg+2)
error->fix_error(FLERR,this,"Illegal keyword entry");
@ -309,8 +320,17 @@ void FixMassflowMeshFace::post_create()
if(fix_ms_)
{
ms_ = &fix_ms_->data();
ms_counter_ = ms_->prop().addElementProperty< ScalarContainer<int> >("counter_ms","comm_exchange_borders","frame_invariant", "restart_yes");
ms_counter_->setDefaultValue(UNDEFINED);
char *counter_ms_name = new char[strlen(id) + 12];
sprintf(counter_ms_name,"counter_ms_%s",id);
ms_counter_ = ms_->prop().getElementProperty<ScalarContainer<int> >(counter_ms_name);
if(!ms_counter_)
{
ms_counter_ = ms_->prop().addElementProperty<ScalarContainer<int> >(counter_ms_name,"comm_exchange_borders","frame_invariant","restart_yes");
ms_counter_->setDefaultValue(UNDEFINED);
}
delete []counter_ms_name;
if(delete_atoms_)
error->fix_error(FLERR,this,"can not use 'delete_atoms' with fix multisphere");
@ -1074,24 +1094,42 @@ void FixMassflowMeshFace::pre_exchange()
{
double mass_deleted_this_ = 0.;
int nparticles_deleted_this_ = 0.;
int *atom_map_array = atom->get_map_array();
int tag_max = atom->tag_max();
// delete particles
while (atom_tags_delete_.size() > 0)
{
int iPart = atom->map(atom_tags_delete_[0]);
if(atom_tags_delete_[0] <= tag_max)
{
int iPart = atom->map(atom_tags_delete_[0]);
mass_deleted_this_ += atom->rmass[iPart];
nparticles_deleted_this_++;
if(iPart >= 0)
{
mass_deleted_this_ += atom->rmass[iPart];
nparticles_deleted_this_++;
atom->avec->copy(atom->nlocal-1,iPart,1);
atom->avec->copy(atom->nlocal-1,iPart,1);
// manipulate atom map array
// need to do this since atom map is needed for deletion
atom_map_array[atom->tag[atom->nlocal-1]] = iPart;
// manipulate atom map array
// need to do this since atom map is needed to get local index for deletion
atom->map_one(atom->tag[atom->nlocal-1], iPart);
atom->nlocal--;
atom->nlocal--;
}
else if (verbose_)
{
// particle may have been removed already by a different deleting command
// e.g. if the particle is in the neighbor list of the meshes of multiple massflow/mesh fixes or on a shared edge
error->fix_warning(FLERR, this, "failed to find atom for deletion (possibly already deleted by another deleting command)");
}
}
else if (verbose_)
{
// particle may have been removed already by a different deleting command
// e.g. if the particle is in the neighbor list of the meshes of multiple massflow/mesh fixes or on a shared edge
error->fix_warning(FLERR, this, "failed to find atom for deletion (possibly already deleted by another deleting command)");
}
atom_tags_delete_.erase(atom_tags_delete_.begin());
}
@ -1107,6 +1145,9 @@ void FixMassflowMeshFace::pre_exchange()
// tags and maps
if(nparticles_deleted_this_)
{
bigint nblocal = atom->nlocal;
MPI_Allreduce(&nblocal,&atom->natoms,1,MPI_LMP_BIGINT,MPI_SUM,world);
if (atom->tag_enable) {
if (atom->map_style) {
atom->nghost = 0;

View File

@ -133,6 +133,7 @@ class FixMassflowMeshFace : public Fix {
class FixPropertyAtom *fix_property_;
double property_sum_;
bool verbose_;
// data write
bool screenflag_;
FILE *fp_;

View File

@ -56,6 +56,7 @@ FixMassflowMeshFaceUniverse::FixMassflowMeshFaceUniverse(LAMMPS *lmp, int narg,
id_hash_ = bitwiseHash(id, mpi_tag_upper_bound(universe->uworld));
couple_every_ = 0;
next_couple_ = -1;
send_to_world_ = -1;
// parse args for this class
@ -83,6 +84,11 @@ FixMassflowMeshFaceUniverse::FixMassflowMeshFaceUniverse(LAMMPS *lmp, int narg,
hasargs = true;
}
}
if (couple_every_ > 0)
{
next_couple_ = update->ntimestep + couple_every_ - (update->ntimestep % couple_every_);
}
}
/* ---------------------------------------------------------------------- */
@ -121,8 +127,10 @@ void FixMassflowMeshFaceUniverse::send_post_create_data()
void FixMassflowMeshFaceUniverse::send_coupling_data()
{
if ((couple_every_ > 0) && (update->ntimestep > 0) && ((update->ntimestep-1) % couple_every_ == 0))
if ((couple_every_ > 0) && (next_couple_ == update->ntimestep))
{
next_couple_ += couple_every_;
// only proc 0 sends data
if (comm->me == 0 && send_to_world_ >= 0)
{

View File

@ -47,6 +47,7 @@ class FixMassflowMeshFaceUniverse : public FixMassflowMeshFace {
int couple_every_;
unsigned int id_hash_;
int send_to_world_;
bigint next_couple_;
private:
std::map<ConstantParticleTemplateSphere, std::vector<double> > distributions_faces_;

View File

@ -328,3 +328,66 @@ void FixMoveMesh::reset_reference_point()
/*NL*/ //if (screen) printVec3D(screen,"re-setting point",reference_point_);
}
void FixMoveMesh::add_reference_axis(double *axis)
{
char refax_id[200];
sprintf(refax_id, "REFAX_%s",id);
if(mesh_->prop().getGlobalProperty<VectorContainer<double,3> >(refax_id))
error->fix_error(FLERR,this,"only one reference axis allowed");
vectorCopy3D(axis,reference_axis_);
mesh_->prop().addGlobalProperty<VectorContainer<double,3> >(refax_id,"comm_none","frame_scale_trans_invariant","restart_no");
mesh_->prop().setGlobalProperty<VectorContainer<double,3> >(refax_id,axis);
}
/* ---------------------------------------------------------------------- */
void FixMoveMesh::get_reference_axis(double *axis)
{
VectorContainer<double,3> *refax;
char refax_id[200];
sprintf(refax_id, "REFAX_%s",id);
refax = mesh_->prop().getGlobalProperty<VectorContainer<double,3> >(refax_id);
if(!refax)
error->fix_error(FLERR,this,"internal error");
// need to explicitly reset reference axis
// otherwise would be too late since reset is called in rotate()
// or move() only and first mesh mover needs resetted reference axis
// so only do this for first mesh mover
if(move_->isFirst())
mesh_->prop().resetGlobalPropToOrig(refax_id);
refax->get(0,axis);
vectorCopy3D(axis,reference_axis_);
}
/* ---------------------------------------------------------------------- */
void FixMoveMesh::reset_reference_axis()
{
// need to reset reference axis from local copy upon setup
// this ensures orig value of reference_axis for fix i has been
// handled by fixes i-1, i-2,... only (not by i, i+1,...)
VectorContainer<double,3> *refax;
char refax_id[200];
sprintf(refax_id, "REFAX_%s",id);
refax = mesh_->prop().getGlobalProperty<VectorContainer<double,3> >(refax_id);
// no error since not all moves have reference points
if(!refax)
return;
// set value for property
refax->set(0,reference_axis_);
// set orig value for property
mesh_->prop().storeGlobalPropOrig(refax_id);
}

View File

@ -64,6 +64,10 @@ namespace LAMMPS_NS
void get_reference_point(double *point);
void reset_reference_point();
void add_reference_axis(double *axis);
void get_reference_axis(double *axis);
void reset_reference_axis();
class AbstractMesh * mesh()
{ return mesh_; }
@ -82,6 +86,7 @@ namespace LAMMPS_NS
double time_since_setup_;
double reference_point_[3];
double reference_axis_[3];
};
} /* namespace LAMMPS_NS */
#endif

View File

@ -56,9 +56,6 @@ using namespace MathConst;
#define MAXJACOBI 50
#define DELTA_GROW 10000
/*NL*/ #define LMP_DEBUGMODE_RIGID_MS false //(update->ntimestep>845 && comm->me==0)
/*NL*/ #define LMP_DEBUGMODE_RIGID_MS_OUT screen //(update->ntimestep>845 && comm->me==0)
enum {LOOP_LOCAL,LOOP_ALL};
/* ---------------------------------------------------------------------- */
@ -79,14 +76,14 @@ FixMultisphere::FixMultisphere(LAMMPS *lmp, int narg, char **arg) :
Vclump_(0)
{
//NP check if style is molecular
// check if style is molecular
if(atom->molecular == 1)
error->fix_error(FLERR,this,"Must NOT use a hybrid sphere/molecular atom style with fix multisphere (use sphere only)");
atom->molecule_flag = 1;
grow_arrays(atom->nmax);
//NP make an exclusion by molecule id;only particles in the fix rigid group are included
// make an exclusion by molecule id;only particles in the fix rigid group are included
char **modarg;
modarg = new char*[3];
modarg[2] = new char[50];
@ -97,7 +94,7 @@ FixMultisphere::FixMultisphere(LAMMPS *lmp, int narg, char **arg) :
delete [] modarg[2];
delete []modarg;
//NP per atom creation and restart
// per atom creation and restart
restart_global = 1;
restart_peratom = 1;
restart_pbc = 1;
@ -107,16 +104,15 @@ FixMultisphere::FixMultisphere(LAMMPS *lmp, int narg, char **arg) :
// fix handles properties that need to be initialized at particle creation
create_attribute = 1;
//NP this fix can force reneighboring
// this fix can force reneighboring
force_reneighbor = 1;
next_reneighbor = -1;
//NP modified C.K.
// is now local data, not global
local_flag = 1;
size_local_rows = 0; //NP init with 0 particles
size_local_cols = 12; // 0 = vector, N = columns in local array
size_local_rows = 0; // init with 0 particles
size_local_cols = 12; // 0 = vector, N = columns in local array
local_freq = 1;
size_peratom_cols = 0;
@ -127,10 +123,10 @@ FixMultisphere::FixMultisphere(LAMMPS *lmp, int narg, char **arg) :
global_freq = 1;
extarray = 0;
//NP max # comm for case f, torque, flag
// max # comm for case f, torque, flag
comm_forward = 7;
//NP max # comm for case pos, vel, omega, flag
// max # comm for case pos, vel, omega, flag
comm_reverse = 10;
}
@ -150,7 +146,7 @@ FixMultisphere::~FixMultisphere()
void FixMultisphere::post_create()
{
//NP register corner ghost
// register corner ghost
if(!fix_corner_ghost_)
{
const char* fixarg[9];
@ -159,14 +155,14 @@ void FixMultisphere::post_create()
fixarg[2]="property/atom";
fixarg[3]="cornerghost";
fixarg[4]="scalar";
fixarg[5]="no"; // restart
fixarg[5]="no"; // restart
fixarg[6]="no"; // communicate ghost
fixarg[7]="no"; // communicate rev
fixarg[8]="0.";
fix_corner_ghost_ = modify->add_fix_property_atom(9,const_cast<char**>(fixarg),style);
}
//NP register deletion flag
// register deletion flag
if(!fix_delflag_)
{
const char* fixarg[9];
@ -181,7 +177,8 @@ void FixMultisphere::post_create()
fixarg[8]="0.";
fix_delflag_ = modify->add_fix_property_atom(9,const_cast<char**>(fixarg),style);
}
//NP register deletion flag
// register exist flag
if(!fix_existflag_)
{
const char* fixarg[9];
@ -191,13 +188,13 @@ void FixMultisphere::post_create()
fixarg[3]="existflag";
fixarg[4]="scalar";
fixarg[5]="no"; // restart
fixarg[6]="no"; // communicate ghost
fixarg[7]="yes"; // communicate rev
fixarg[6]="no"; // communicate ghost
fixarg[7]="yes"; // communicate rev
fixarg[8]="1.";
fix_existflag_ = modify->add_fix_property_atom(9,const_cast<char**>(fixarg),style);
}
//NP in case of restart: see comment in FixMultisphere::restart
// in case of restart: see comment in FixMultisphere::restart
if(modify->have_restart_data(this))
{
evflag = 0;
@ -228,37 +225,34 @@ double FixMultisphere::max_r_bound() const
double FixMultisphere::extend_cut_ghost() const
{
//NP this is to extend ghost region
//NP one rbound is enough since just need to ensure proc has
//NP ghost atoms for all owned bodies
return /*NP*2.*/max_r_bound();
// this is to extend ghost region
// one rbound is enough since just need to ensure proc has
// ghost atoms for all owned bodies
return max_r_bound();
}
/* ---------------------------------------------------------------------- */
void FixMultisphere::add_body_finalize()
{
//NP need to do tasks that are done in FixRigid::setup()
//NP this function called via particle templates
// need to do tasks that are done in FixRigid::setup()
// this function called via particle templates
//NP invoke set_v()
//NP since not set for particles belonging to newly inserted bodies
//NP but do NOT loop ghosts at this stage, new particles do not have ghosts at this point
/*NL*/ if(LMP_DEBUGMODE_RIGID_MS) fprintf(LMP_DEBUGMODE_RIGID_MS_OUT,"FixMultisphere::add_body_finalize doing setup\n");
// invoke set_v()
// since not set for particles belonging to newly inserted bodies
// but do NOT loop ghosts at this stage, new particles do not have ghosts at this point
multisphere_.id_extend_body_extend(body_);
multisphere_.generate_map();
multisphere_.reset_forces(true);
set_xv(LOOP_LOCAL); //NP only loop local particles, ghosts do not exist yet for these new particles
set_xv(LOOP_LOCAL); // only loop local particles, ghosts do not exist yet for these new particles
}
/* ---------------------------------------------------------------------- */
void FixMultisphere::init() //NP modified C.K.
void FixMultisphere::init()
{
// lots of error checks and warnings
// error checks and warnings
if(0 == atom->map_style)
error->fix_error(FLERR,this,"requires an 'atom_modify map' command to allocate an atom map");
@ -277,12 +271,12 @@ void FixMultisphere::init() //NP modified C.K.
if (strstr(update->integrate_style,"respa"))
error->fix_error(FLERR,this,"does not work with respa");
//step_respa = ((Respa *) update->integrate)->step;
//NP this is because reverse comm would maybe erase force and torque values??
if(force->newton) error->fix_error(FLERR,this,"requires newton 'off'");
// this is because reverse comm would maybe erase force and torque values??
if(force->newton)
error->fix_error(FLERR,this,"requires newton 'off'");
//NP check if a fix gravity is registered
// check if a fix gravity is registered
if(modify->n_fixes_style("gravity") > 1)
error->fix_error(FLERR,this,"only one fix gravity supported");
fix_gravity_ = static_cast<FixGravity*>(modify->find_fix_style("gravity",0));
@ -294,22 +288,9 @@ void FixMultisphere::init() //NP modified C.K.
fix_remove_.clear();
// timestep info
dtv = update->dt;
dtf = 0.5 * update->dt * force->ftm2v;
dtq = 0.5 * update->dt;
// calc MS comm properties
ntypes_ = modify->n_fixes_style("particletemplate/multisphere");
if(Vclump_) delete []Vclump_;
Vclump_ = new double [ntypes_+1];
for(int ifix = 0; ifix < ntypes_; ifix++)
{
FixTemplateMultisphere *ftm = static_cast<FixTemplateMultisphere*>(modify->find_fix_style("particletemplate/multisphere",ifix));
int itype = ftm->type();
Vclump_[itype] = ftm->volexpect();
}
}
/* ---------------------------------------------------------------------- */
@ -323,7 +304,20 @@ void FixMultisphere::add_remove_callback(FixRemove *ptr)
void FixMultisphere::setup(int vflag)
{
//NP guesstimate virial as 2x the set_v contribution
// calc MS comm properties
ntypes_ = modify->n_fixes_style("particletemplate/multisphere");
if(Vclump_) delete []Vclump_;
Vclump_ = new double [ntypes_+1];
for(int ifix = 0; ifix < ntypes_; ifix++)
{
FixTemplateMultisphere *ftm = static_cast<FixTemplateMultisphere*>(modify->find_fix_style("particletemplate/multisphere",ifix));
int itype = ftm->type();
Vclump_[itype] = ftm->volexpect();
}
// guesstimate virial as 2x the set_v contribution
int i,n;
int nlocal = atom->nlocal;
@ -340,26 +334,28 @@ void FixMultisphere::setup(int vflag)
vatom[i][n] *= 2.0;
}
//NP execute communication routine
// execute communication routine
calc_force();
}
/*NL*/ if(LMP_DEBUGMODE_RIGID_MS && screen) fprintf(screen,"FixMultisphere::setup finished on proc %d\n",comm->me);
/* ---------------------------------------------------------------------- */
void FixMultisphere::setup_pre_exchange()
{
pre_exchange();
}
/* ---------------------------------------------------------------------- */
void FixMultisphere::setup_pre_neighbor()
{
/*NL*/ //if (screen) fprintf(screen,"SUPN A step %d proc %d: nbody %d\n",update->ntimestep,comm->me,n_body());
pre_neighbor();
/*NL*/ //if (screen) fprintf(screen,"SUPN B step %d proc %d: nbody %d\n",update->ntimestep,comm->me,n_body());
}
/* ---------------------------------------------------------------------- */
void FixMultisphere::set_arrays(int i)
{
/*NL*/ //if (screen) fprintf(screen,"set arrays called\n");
body_[i] = -1;
}
@ -402,12 +398,11 @@ void FixMultisphere::initial_integrate(int vflag)
if(strstr(style,"nointegration"))
return;
/*NL*/ //if(screen) fprintf(screen,"nbody_all %d\n",n_body_all());
/*NL*/ //if(screen && map(7833) >= 0) fprintf(screen,"proc %d has body %d at step %d\n",comm->me,7833,update->ntimestep);
bool has_stream = modify->n_fixes_style("insert/stream") > 0;
for (int ibody = 0; ibody < nbody; ibody++) {
if(timestep < start_step[ibody])
if(has_stream && timestep < start_step[ibody])
{
vectorCopy3D(v_integrate[ibody],vcm[ibody]);
@ -415,15 +410,10 @@ void FixMultisphere::initial_integrate(int vflag)
xcm[ibody][0] += dtv * vcm[ibody][0];
xcm[ibody][1] += dtv * vcm[ibody][1];
xcm[ibody][2] += dtv * vcm[ibody][2];
/*NL*/ //if (screen) printVec3D(screen,"vcm[ibody] FixMultisphere::initial_integrate",vcm[ibody]);
/*NL*/ //if (screen) printVec3D(screen,"xcm[ibody] FixMultisphere::initial_integrate",xcm[ibody]);
/*NL*/ //error->one(FLERR,"end");
/*NL*/ //if (screen) fprintf(screen,"this should not be\n");
continue;
}
/*NL*/ //if(LMP_DEBUGMODE_RIGID) fprintf(LMP_DEBUG_OUTP_RIGID,"FixRigid::initial_integrate for body %d\n",ibody);
// update vcm by 1/2 step
dtfm = dtf / masstotal[ibody];
@ -438,13 +428,6 @@ void FixMultisphere::initial_integrate(int vflag)
xcm[ibody][1] += dtv * vcm[ibody][1];
xcm[ibody][2] += dtv * vcm[ibody][2];
/*NL*/ //if (screen) {
/*NL*/ //fprintf(screen,"masstotal[ibody] %f\n",masstotal[ibody]);
/*NL*/ //printVec3D(screen,"xcm[ibody]",xcm[ibody]);
/*NL*/ //printVec3D(screen,"vcm[ibody]",vcm[ibody]);
/*NL*/ //printVec3D(screen,"fcm[ibody]",fcm[ibody]);
/*NL*/ //}
// update angular momentum by 1/2 step
if(tflag[ibody][0]) angmom[ibody][0] += dtf * torquecm[ibody][0];
@ -462,20 +445,6 @@ void FixMultisphere::initial_integrate(int vflag)
inertia[ibody],dtq);
MathExtra::q_to_exyz(quat[ibody],
ex_space[ibody],ey_space[ibody],ez_space[ibody]);
/*NL*/ //bool eval = true; //13500 < update->ntimestep && 14000 > update->ntimestep;
/*NL*/ //if(screen && tag(ibody) == 88 && eval) {
/*NL*/ // fprintf(screen,"step " BIGINT_FORMAT " proc %d, xcm %f %f %f vcm %f %f %f omegacm %f %f %f\n",
/*NL*/ // update->ntimestep,comm->me,
/*NL*/ // xcm[ibody][0],xcm[ibody][1],xcm[ibody][2],
/*NL*/ // vcm[ibody][0],vcm[ibody][1],vcm[ibody][2],
/*NL*/ // data().omega_(ibody)[0],data().omega_(ibody)[1],data().omega_(ibody)[2]);
/*NL*/ // fprintf(screen,"step " BIGINT_FORMAT " proc %d, fcm %f %f %f torquecm %f %f %f\n",
/*NL*/ // update->ntimestep,comm->me,
/*NL*/ // fcm[ibody][0],fcm[ibody][1],fcm[ibody][2],
/*NL*/ // torquecm[ibody][0],torquecm[ibody][1],torquecm[ibody][2]);
/*NL*/ //}
}
// virial setup before call to set_xv
@ -488,11 +457,11 @@ void FixMultisphere::initial_integrate(int vflag)
set_xv();
//NP reverse comm of x,v,omega
// reverse comm of x,v,omega
rev_comm_flag_ = MS_COMM_REV_X_V_OMEGA;
reverse_comm();
//NP forward comm of x, v, omega done via verlet
// forward comm of x, v, omega done via verlet
}
/* ---------------------------------------------------------------------- */
@ -516,13 +485,13 @@ void FixMultisphere::final_integrate()
bool **tflag = multisphere_.tflag_.begin();
int nbody = multisphere_.n_body();
//NP sum over atoms to get force and torque on rigid body
// sum over atoms to get force and torque on rigid body
//NP differences to FixRigid::final_integrate() version:
//NP + most importantly, do not do the allreduce - each proc owns its own bodies
//NP + do a forward comm and a reverse comm instead
//NP + loop over owned and ghost atoms
//NP + check if a fix gravity is registered. If yes, add contribution to rigid body
// differences to FixRigid::final_integrate() version:
// + most importantly, do not do the allreduce - each proc owns its own bodies
// + do a forward comm and a reverse comm instead
// + loop over owned and ghost atoms
// + check if a fix gravity is registered. If yes, add contribution to rigid body
// calculate forces and torques on body
@ -531,19 +500,12 @@ void FixMultisphere::final_integrate()
if(strstr(style,"nointegration"))
return;
bool has_stream = modify->n_fixes_style("insert/stream") > 0;
// resume integration
for (int ibody = 0; ibody < nbody; ibody++)
{
if(timestep < start_step[ibody]) continue;
/*NL*/ //bool eval = 13500 < update->ntimestep && 14000 > update->ntimestep;
/*NL*/ //if(screen && tag(ibody) == 60 && eval) {
/*NL*/ // fprintf(screen,"step " BIGINT_FORMAT " final integrate proc %d, xcm %f %f %f vcm %f %f %f omegacm %f %f %f\n",
/*NL*/ // update->ntimestep,comm->me,
/*NL*/ // xcm[ibody][0],xcm[ibody][1],xcm[ibody][2],
/*NL*/ // vcm[ibody][0],vcm[ibody][1],vcm[ibody][2],
/*NL*/ // data().omega_(ibody)[0],data().omega_(ibody)[1],data().omega_(ibody)[2]);}
if(has_stream && timestep < start_step[ibody]) continue;
// update vcm by 1/2 step
@ -562,15 +524,15 @@ void FixMultisphere::final_integrate()
ez_space[ibody],inertia[ibody],omega[ibody]);
}
//NP set velocity/rotation of atoms in rigid bodies
//NP virial is already setup from initial_integrate
// set velocity/rotation of atoms in rigid bodies
// virial is already setup from initial_integrate
set_v();
//NP reverse comm of v,omega
// reverse comm of v,omega
rev_comm_flag_ = MS_COMM_REV_V_OMEGA;
reverse_comm();
//NP forward comm of v,omega
// forward comm of v,omega
fw_comm_flag_ = MS_COMM_FW_V_OMEGA;
forward_comm();
}
@ -600,9 +562,9 @@ void FixMultisphere::calc_force()
double **torquecm = multisphere_.torquecm_.begin();
int nbody = multisphere_.n_body();
//NP forward comm of forces and torques
//NP so have current forces and torques stored in ghosts
//NP loop not only to nlocal, but also over ghosts
// forward comm of forces and torques
// so have current forces and torques stored in ghosts
// loop not only to nlocal, but also over ghosts
fw_comm_flag_ = MS_COMM_FW_F_TORQUE;
forward_comm();
@ -612,30 +574,28 @@ void FixMultisphere::calc_force()
// do not reset external torques
multisphere_.reset_forces(false);
//NP correct forces if necessary
// correct forces if necessary
if(do_modify_body_forces_torques_)
modify_body_forces_torques();
// calculate forces and torques of bodies
for (int i = 0; i < nlocal+nghost; i++)
{
//NP skip if atom not in rigid body
// skip if atom not in rigid body
if(body_[i] < 0) continue;
//NP body ID stored in atom is global
//NP need to know where stored in my data
// body ID stored in atom is global
// need to know where stored in my data
ibody = map(body_[i]);
//NP skip if body not owned by this proc
// skip if body not owned by this proc
if (ibody < 0) continue;
//NP skip if periodic ghost of owned particle
//NP since would double-count forces in this case
// skip if periodic ghost of owned particle
// since would double-count forces in this case
if(!domain->is_owned_or_first_ghost(i))
continue;
/*NL*///if (screen) fprintf(screen,"A step " BIGINT_FORMAT ",body tag %d, atom tag %d: force %f %f %f\n",update->ntimestep,tag(ibody),atom->tag[i],fcm[ibody][0],fcm[ibody][1],fcm[ibody][2]);
vectorCopy3D(f_atom[i],f_one);
vectorCopy3D(torque_atom[i],torque_one);
@ -648,39 +608,16 @@ void FixMultisphere::calc_force()
dy = unwrap[1] - xcm[ibody][1];
dz = unwrap[2] - xcm[ibody][2];
//NP modified C.K.
//NP make sure
//NP this is important for ghost atoms across periodic boundaries
// this is important for ghost atoms across periodic boundaries
if(i >= nlocal)
domain->minimum_image(dx,dy,dz);
//NP torque due to atom force and torque
// torque due to atom force and torque
torquecm[ibody][0] += dy*f_one[2] - dz*f_one[1] + torque_one[0];
torquecm[ibody][1] += dz*f_one[0] - dx*f_one[2] + torque_one[1];
torquecm[ibody][2] += dx*f_one[1] - dy*f_one[0] + torque_one[2];
/*NL*/ //bool eval = 3100 < update->ntimestep && 3175 > update->ntimestep;
/*NL*/ //if(screen && (tag(ibody) == 88) && eval) {
/*NL*/ // fprintf(screen,"step " BIGINT_FORMAT " proc %d atom tag %d, ghost %s,pos %f %f %f f %f %f %f torque_one %f %f %f, dx %f dy %f dz %f\n",
/*NL*/ // update->ntimestep,comm->me,atag[i],i>=nlocal?"yes":"no",
/*NL*/ // x[i][0],x[i][1],x[i][2],
/*NL*/ // f_one[0],f_one[1],f_one[2],
/*NL*/ // torque_one[0],torque_one[1],torque_one[2],dx,dy,dz);
/*NL*/ //}
/*NL*///if (screen) fprintf(screen,"B step %d,body tag %d, atom tag %d: force %f %f %f\n",update->ntimestep,tag(ibody),atom->tag[i],fcm[ibody][0],fcm[ibody][1],fcm[ibody][2]);
}
/*NL*/ //bool eval = 18000 < update->ntimestep && 20000 > update->ntimestep;
/*NL*/ //ibody = map(238);
/*NL*/ //if(screen && ibody >= 0 && eval) {
/*NL*/ // fprintf(screen,"step " BIGINT_FORMAT " fcm on body after summation (proc %d) %f %f %f torquecm %f %f %f\n",
/*NL*/ // update->ntimestep,comm->me,
/*NL*/ // fcm[ibody][0],fcm[ibody][1],fcm[ibody][2],
/*NL*/ // torquecm[ibody][0],torquecm[ibody][1],torquecm[ibody][2]);
/*NL*/ //}
// add external forces on bodies, such as gravity, dragforce
if(fix_gravity_)
@ -692,14 +629,12 @@ void FixMultisphere::calc_force()
fcm[ibody][0] += masstotal[ibody]*grav[0];
fcm[ibody][1] += masstotal[ibody]*grav[1];
fcm[ibody][2] += masstotal[ibody]*grav[2];
/*NL*///if (screen) fprintf(screen,"C step %d,body tag %d: force %f %f %f\n",update->ntimestep,tag(ibody),fcm[ibody][0],fcm[ibody][1],fcm[ibody][2]);
}
}
for (ibody = 0; ibody < nbody; ibody++)
{
vectorAdd3D(fcm[ibody],dragforce_cm[ibody],fcm[ibody]);
/*NL*///if (screen) fprintf(screen,"body tag %d: forcecm %f %f %f, torquecm %f %f %f\n",tag(ibody),fcm[ibody][0],fcm[ibody][1],fcm[ibody][2],torquecm[ibody][0],torquecm[ibody][1],torquecm[ibody][2]);
}
}
@ -710,7 +645,7 @@ void FixMultisphere::calc_force()
v = Vcm + (W cross (x - Xcm))
------------------------------------------------------------------------- */
//NP adapted to loop also over ghosts
// adapted to loop also over ghosts
void FixMultisphere::set_xv()
{
set_xv(LOOP_ALL);
@ -757,8 +692,6 @@ void FixMultisphere::set_xv(int ghostflag)
for (int i = 0; i < nloop; i++) {
/*NL*/ //if(screen && atom->tag[i] == 23497) fprintf(screen,"atom tag 23497 has body %d\n",body_[i]);
if (body_[i] < 0) continue;
ibody = map(body_[i]);
@ -768,11 +701,9 @@ void FixMultisphere::set_xv(int ghostflag)
ybox = (image[i] >> IMGBITS & IMGMASK) - IMGMAX;
zbox = (image[i] >> IMG2BITS) - IMGMAX;
/*NL*/// if (screen) fprintf(screen,"boxes %d %d %d image %d\n",xbox,ybox,zbox,image[i]);
// save old positions and velocities for virial
if (evflag) {
if (evflag && i < nlocal) {
x0 = x[i][0] + xbox*xprd;
x1 = x[i][1] + ybox*yprd;
x2 = x[i][2] + zbox*zprd;
@ -802,42 +733,14 @@ void FixMultisphere::set_xv(int ghostflag)
omega_one[i][1] = omega[ibody][1];
omega_one[i][2] = omega[ibody][2];
/*NL*/ //bool eval = true; //50000 < update->ntimestep && 55000 > update->ntimestep;
/*NL*/ //if(screen && tag(ibody) == 1 && eval) {
/*NL*/ // fprintf(screen,"step " BIGINT_FORMAT " proc %d atom tag %d ghost %s, boxes %d %d %d \n",
/*NL*/ // update->ntimestep,comm->me,atag[i],i>=nlocal?"yes":"no",
/*NL*/ // xbox,ybox,zbox);
/*NL*/ //}
/*NL*///if(screen && !domain->is_in_domain(x[i]))
/*NL*///{
/*NL*/// fprintf(screen,"particle %d, tag %d\n",i,atom->tag[i]);
/*NL*/// printVec3D(screen,"omega_one[i]",omega_one[i]);
/*NL*/// fprintf(screen,"part 1 %f\n",ex_space[ibody][0]*displace[i][0] + ey_space[ibody][0]*displace[i][1] + ez_space[ibody][0]*displace[i][2]);
/*NL*/// fprintf(screen,"part 2 %f\n",xcm[ibody][0] - xbox*xprd);
/*NL*/// fprintf(screen,"part 2 xbox*xprd %f\n",xbox*xprd);
/*NL*/// fprintf(screen,"image %d\n",image[i]);
/*NL*/// fprintf(screen,"xbox %d\n",xbox);
/*NL*/// fprintf(screen,"xprd %f\n",xprd);
/*NL*/// printVec3D(screen,"x",x[i]);
/*NL*/// printVec3D(screen,"displace",displace[i]);
/*NL*/// printVec3D(screen,"displace",displace[i]);
/*NL*/// printVec3D(screen,"xcm",xcm[ibody]);
/*NL*/// printVec3D(screen,"ex_space",ex_space[ibody]);
/*NL*/// printVec3D(screen,"ey_space",ey_space[ibody]);
/*NL*/// printVec3D(screen,"ez_space",ez_space[ibody]);
/*NL*/// error->one(FLERR,"not in domain");
/*NL*///}
// virial = unwrapped coords dotted into body constraint force
// body constraint force = implied force due to v change minus f external
// assume f does not include forces internal to body
// 1/2 factor b/c final_integrate contributes other half
// assume per-atom contribution is due to constraint force on that atom
if (evflag) {
if (evflag && i < nlocal) {
if (rmass) massone = rmass[i];
else massone = mass[type[i]];
fc0 = massone*(v[i][0] - v0)/dtf - f[i][0];
@ -862,7 +765,7 @@ void FixMultisphere::set_xv(int ghostflag)
v = Vcm + (W cross (x - Xcm))
------------------------------------------------------------------------- */
//NP adapted to loop also over ghosts
// adapted to loop also over ghosts
void FixMultisphere::set_v()
{
set_v(LOOP_ALL);
@ -914,7 +817,7 @@ void FixMultisphere::set_v(int ghostflag)
// save old velocities for virial
if (evflag) {
if (evflag && i < nlocal) {
v0 = v[i][0];
v1 = v[i][1];
v2 = v[i][2];
@ -934,7 +837,7 @@ void FixMultisphere::set_v(int ghostflag)
// 1/2 factor b/c initial_integrate contributes other half
// assume per-atom contribution is due to constraint force on that atom
if (evflag) {
if (evflag && i < nlocal) {
if (rmass) massone = rmass[i];
else massone = mass[type[i]];
fc0 = massone*(v[i][0] - v0)/dtf - f[i][0];
@ -972,24 +875,16 @@ void FixMultisphere::pre_exchange()
// reset last trigger for re-neigh
next_reneighbor = -1;
//NP have to do this here, b/c deletion at other place in code would
//NP mess up paralleliztion
// have to do this here, b/c deletion at other place in code would
// mess up parallelization
double *delflag = fix_delflag_->vector_atom;
/*NL*/ //double *existflag = fix_existflag_->vector_atom;
int i = 0;
/*NL*/ //double sum = vectorSumN(existflag,atom->nlocal);
/*NL*/ //if (screen) fprintf(screen,"sum pre_exchange %f nlocal %d\n",sum,atom->nlocal);
while(i < atom->nlocal)
{
//NP important to use round() here
//NP never check if(double_variable) !!!!
/*NL*/ //if (screen) fprintf(screen,"delfag particle %d: %f\n",atom->tag[i],delflag[i]);
if(round(delflag[i]) == 1.)
if(MathExtraLiggghts::compDouble(delflag[i],1.))
{
/*NL*/ //if (screen) fprintf(screen,"step " BIGINT_FORMAT " proc %d deleting particle tag %d\n",update->ntimestep,comm->me,atom->tag[i]);
avec->copy(atom->nlocal-1,i,1);
atom->nlocal--;
}
@ -1019,42 +914,39 @@ void FixMultisphere::pre_exchange()
void FixMultisphere::pre_neighbor()
{
//NP reset corner ghost flag
// reset corner ghost flag
int nall = atom->nlocal + atom->nghost;
double *corner_ghost = fix_corner_ghost_->vector_atom;
vectorZeroizeN(corner_ghost,nall);
/*NL*/ //if (screen) fprintf(screen,"step %d on proc %d: x-sublo %f x-subhi %f\n",update->ntimestep,comm->me,domain->sublo[0],domain->subhi[0]);
/*NL*/ //if (screen) fprintf(screen,"step %d proc %d: nbody %d, nall %d\n",update->ntimestep,comm->me,n_body(),atom->nlocal+atom->nghost);
// communicate displace, image, body to ghosts
// since needed in set_xv(), set_v()
// ok to communicate only once after re-neighboring
// since can change only at processor exchange
//NP communicate displace, image, body to ghosts
//NP since needed in set_xv(), set_v()
//NP ok to communicate only once after re-neighboring
//NP since can change only at processor exchange
//NP communicate body first, since needed for check_lost_atoms()
// communicate body first, since needed for check_lost_atoms()
fw_comm_flag_ = MS_COMM_FW_BODY;
forward_comm();
//NP callback to fix remove
//NP need this here before exchange()
//NP since then the removal list generated at
//NP FixRemove::pre_exchange() is still up-to-date
// callback to fix remove
// need this here before exchange()
// since then the removal list generated at
// FixRemove::pre_exchange() is still up-to-date
for(size_t irem = 0; irem < fix_remove_.size(); irem++)
(fix_remove_[irem])->delete_bodies();
//NP re-map bodies, then exchange with stencil procs
//NP need to do that here because body and atom data
//NP must be sync'd before checking for lost atoms
// re-map bodies, then exchange with stencil procs
// need to do that here because body and atom data
// must be sync'd before checking for lost atoms
//NP need fw comm of image since not communicated on
//NP reneighboring steps in Comm::borders()
// need fw comm of image since not communicated on
// reneighboring steps in Comm::borders()
//NP need reverse comm of atom image flag since
//NP changed on ghosts by remap_bodies
//NP fw comm image and displace
//NP note that image has changed due to remap_bodies() call
// need reverse comm of atom image flag since
// changed on ghosts by remap_bodies
// fw comm image and displace
// note that image has changed due to remap_bodies() call
fw_comm_flag_ = MS_COMM_FW_IMAGE_DISPLACE;
forward_comm();
multisphere_.remap_bodies(body_);
@ -1062,18 +954,17 @@ void FixMultisphere::pre_neighbor()
reverse_comm();
multisphere_.exchange();
//NP after all bodies are communicated, need to find out how many we have
// after all bodies are communicated, need to find out how many we have
multisphere_.calc_nbody_all();
//NP need to re-set map as well
//NP as exchange has happened so bodies deleted and added
/*NL*/ //if (screen) fprintf(screen,"generating map after exchange");
// need to re-set map as well
// as exchange has happened so bodies deleted and added
multisphere_.generate_map();
//NP check for lost atoms (e.g. lost during atom communication via verlet,
//NP fixed boundaries etc)
//NP if atom is lost that belongs to rigid body, delete whole body
//NP and mark other atoms belonging to this rigid body for deletion
// check for lost atoms (e.g. lost during atom communication via verlet,
// fixed boundaries etc)
// if atom is lost that belongs to rigid body, delete whole body
// and mark other atoms belonging to this rigid body for deletion
// set deletion flag
// if any deleted atoms, do re-neigh in 100 steps at latest to remove
@ -1084,20 +975,14 @@ void FixMultisphere::pre_neighbor()
vectorZeroizeN(existflag,atom->nlocal+atom->nghost);
if(multisphere_.check_lost_atoms(body_,delflag,existflag))
next_reneighbor = update->ntimestep + 100;
next_reneighbor = update->ntimestep + 5;
/*NL*/ //double sum = vectorSumN(existflag,atom->nlocal);
/*NL*/ //if (screen) fprintf(screen,"sum pre %f nlocal %d\n",sum,atom->nlocal);
//NP need to send deletion flag from ghosts to owners
// need to send deletion flag from ghosts to owners
fix_delflag_->do_reverse_comm();
fix_existflag_->do_reverse_comm();
/*NL*/ //sum = vectorSumN(existflag,atom->nlocal);
/*NL*/ //if (screen) fprintf(screen,"sum post %f nlocal %d\n",sum,atom->nlocal);
//NP fw comm image and displace
//NP note that image has changed due to remap_bodies() call
// fw comm image and displace
// note that image has changed due to remap_bodies() call
fw_comm_flag_ = MS_COMM_FW_IMAGE_DISPLACE;
forward_comm();
@ -1106,10 +991,16 @@ void FixMultisphere::pre_neighbor()
int nlocal = atom->nlocal;
delflag = fix_delflag_->vector_atom;
existflag = fix_existflag_->vector_atom;
int force_reneighbour = 0;
for(int i = 0; i < nlocal; i++)
{
delflag[i] = (round(existflag[i]) == 0) ? 1. : delflag[i];
delflag[i] = (MathExtraLiggghts::compDouble(existflag[i],0.)) ? 1. : delflag[i];
if (MathExtraLiggghts::compDouble(delflag[i],1.0))
force_reneighbour = 1;
}
MPI_Max_Scalar(force_reneighbour,world);
if (force_reneighbour)
next_reneighbor = update->ntimestep + 5;
}
/* ----------------------------------------------------------------------
@ -1149,21 +1040,11 @@ double FixMultisphere::memory_usage()
void FixMultisphere::grow_arrays(int nmax)
{
/*NL*/ //if (screen) fprintf(screen,"called with nmax %d\n",nmax);
body_ = memory->grow(body_,nmax,"rigid:body_");
memory->grow(displace_,nmax,3,"rigid:displace");
atom->molecule = body_;
}
/* ----------------------------------------------------------------------
extract values
------------------------------------------------------------------------- */
/*
void * FixMultisphere::extract(char *name, int &len1, int &len2)
{
return multisphere_.extract(name,len1,len2);
}*/
/* ----------------------------------------------------------------------
return attributes of a rigid body
12 values per body
@ -1172,6 +1053,6 @@ void * FixMultisphere::extract(char *name, int &len1, int &len2)
double** FixMultisphere::get_dump_ref(int &nb, int &nprop, char* prop)
{
error->one(FLERR,"TODO");
error->one(FLERR,"TODO");
return NULL;
}

View File

@ -64,6 +64,7 @@ class FixMultisphere : public Fix
virtual void setup(int);
virtual void setup_pre_force(int) {}
virtual void setup_pre_exchange();
virtual void setup_pre_neighbor();
virtual double extend_cut_ghost() const;
@ -169,7 +170,7 @@ class FixMultisphere : public Fix
{ return data().extract_rke(); }
inline void set_v_body_from_atom_index(int iatom,double *vel)
{ multisphere_.set_v_body(body_[iatom],vel); }
{ if(body_[iatom] >= 0) multisphere_.set_v_body(body_[iatom],vel); }
inline void set_body_displace(int i,double *_displace,int body_id)
{ body_[i] = body_id; vectorCopy3D(_displace,displace_[i]); }
@ -202,8 +203,7 @@ class FixMultisphere : public Fix
class FixPropertyAtom *fix_existflag_;
class FixGravity *fix_gravity_;
//NP flag stating that image and displace must be communicated to ghosts
//int comm_di_;
// flag stating that image and displace must be communicated to ghosts
int fw_comm_flag_;
int rev_comm_flag_;

View File

@ -20,6 +20,7 @@
------------------------------------------------------------------------- */
#include "fix_multisphere.h"
#include "modify.h"
#include "comm.h"
@ -529,6 +530,20 @@ void FixMultisphere::restart(char *buf)
{
double *list = (double *) buf;
bool have_massflow_mesh = modify->have_restart_data_style("massflow/mesh");
if(have_massflow_mesh)
{
int nmassflow = modify->n_restart_data_global_style("massflow/mesh");
for(int imf = 0; imf < nmassflow; imf++)
{
char *id_this = modify->id_restart_data_global_style("massflow/mesh",imf);
char *counter_ms_name = new char[strlen(id_this)+12];
sprintf(counter_ms_name,"counter_ms_%s",id_this);
multisphere_.prop().addElementProperty< ScalarContainer<int> >(counter_ms_name,"comm_exchange_borders","frame_invariant", "restart_yes");
delete []counter_ms_name;
}
}
//NP have to perform all tasks from add_body_finalize()
//NP id_extend_body_extend() not necessary since in restart data
//NP multisphere_.restart(list) calls generate_map() and reset_forces(true)

View File

@ -40,6 +40,8 @@
#include "mpi_liggghts.h"
#include <string>
using namespace LAMMPS_NS;
using namespace FixConst;
@ -50,9 +52,11 @@ using namespace FixConst;
FixPropertyAtom::FixPropertyAtom(LAMMPS *lmp, int narg, char **arg, bool parse) :
Fix(lmp, narg, arg),
propertyname(0),
property(0)
property(0),
store_old_time_values_(0),
old_time_values_(NULL)
{
/*NL*/ //if (screen) fprintf(screen,"HERRE parse for id %s\n",id);
/*NL*/ //if (screen) fprintf(screen,"HERE parse for id %s\n",id);
if(parse) parse_args(narg,arg);
}
@ -63,7 +67,7 @@ void FixPropertyAtom::parse_args(int narg, char **arg)
if (narg > 29) error->warning(FLERR,"Vector length in fix property/atom larger than 20. Are you sure you want that?");
// Read args
//NP 8 values for base stuff
//NP 8 values for base stuff (or 9 if option for storing old-time values is specified)
int n = strlen(arg[3]) + 1;
variablename = new char[n];
strcpy(variablename,arg[3]);
@ -92,7 +96,19 @@ void FixPropertyAtom::parse_args(int narg, char **arg)
else if (strcmp(arg[7],"no") == 0) commGhostRev = 0;
else error->all(FLERR,"Unknown communicate_reverse_ghost style for fix property/atom. Valid styles are 'yes' or 'no'");
nvalues = narg - 8;
int n_leading_args = 8;
if (strcmp(arg[8],"yes") == 0)
{
store_old_time_values_ = 1;
n_leading_args++;
}
else if (strcmp(arg[8],"no") == 0)
{
store_old_time_values_ = 0;
n_leading_args++;
}
nvalues = narg - n_leading_args;
if ((nvalues == 1) && (data_style != FIXPROPERTY_ATOM_SCALAR))
error->all(FLERR,"Error in fix property/atom: Number of default values provided not consistent with vector style. Provide more than 1 value or use style 'scalar'");
@ -110,7 +126,7 @@ void FixPropertyAtom::parse_args(int narg, char **arg)
propertyname = NULL;
if(FIXPROPERTY_ATOM_SCALAR == data_style)
{
char *prop = arg[8];
char *prop = arg[n_leading_args];
int n = strlen(prop);
bool is_digit = false;
for (int i = 0; i < n; i++)
@ -138,12 +154,12 @@ void FixPropertyAtom::parse_args(int narg, char **arg)
for (int j = 0; j < nvalues; j++)
{
// if any of the values is none, this fix will not init properties
if(strcmp(arg[8+j],"none") == 0)
if(strcmp(arg[n_leading_args+j],"none") == 0)
{
create_attribute = 0;
continue;
}
defaultvalues[j] = force->numeric(FLERR,arg[8+j]);
defaultvalues[j] = force->numeric(FLERR,arg[n_leading_args+j]);
}
}
@ -230,6 +246,13 @@ FixPropertyAtom::~FixPropertyAtom()
/* ---------------------------------------------------------------------- */
void FixPropertyAtom::pre_delete(bool unfixflag)
{
if(unfixflag && old_time_values_) modify->delete_fix(old_time_values_->id);
}
/* ---------------------------------------------------------------------- */
Fix* FixPropertyAtom::check_fix(const char *varname,const char *svmstyle,int len1,int len2,const char *caller,bool errflag)
{
char errmsg[400];
@ -275,13 +298,75 @@ Fix* FixPropertyAtom::check_fix(const char *varname,const char *svmstyle,int len
/* ---------------------------------------------------------------------- */
void FixPropertyAtom::post_create()
{
if(!store_old_time_values_) return;
if (old_time_values_ == NULL)
{
char *fixname = new char [strlen("_oldtime")+strlen(id)+1];
strcpy(fixname,id);
strcat(fixname,"_oldtime");
int nargs = nvalues+8;
const char **fixarg = new const char*[nargs];
fixarg[0]=fixname;
fixarg[1]=group->names[igroup];
fixarg[2]="property/atom";
fixarg[3]=fixname;
if (data_style) fixarg[4]="vector";
else fixarg[4]="scalar";
// restart
if (restart_peratom) fixarg[5]="yes";
else fixarg[5]="no";
// communicate ghost
if (commGhost) fixarg[6]="yes";
else fixarg[6]="no";
// communicate rev
if (commGhostRev) fixarg[7]="yes";
else fixarg[7]="no";
for (int i=0;i<nvalues;i++)
{
fixarg[8+i] = std::to_string(defaultvalues[i]).c_str();
}
old_time_values_ = modify->add_fix_property_atom(nargs,const_cast<char**>(fixarg),style);
delete [] fixname;
delete [] fixarg;
}
}
/* ---------------------------------------------------------------------- */
int FixPropertyAtom::setmask()
{
int mask = 0;
mask |= PRE_EXCHANGE;
if (store_old_time_values_)
{
mask |= END_OF_STEP;
}
return mask;
}
/* ---------------------------------------------------------------------- */
void FixPropertyAtom::end_of_step()
{
int nall = atom->nlocal + atom->nghost;
for (int i = 0; i < nall; i++)
{
if (data_style)
{
for (int m = 0; m < nvalues; m++)
{
old_time_values_->array_atom[i][m] = array_atom[i][m];
}
}
else old_time_values_->vector_atom[i] = vector_atom[i];
}
}
/* ----------------------------------------------------------------------
forward and backward comm to be used by other fixes as needed
------------------------------------------------------------------------- */
@ -624,3 +709,16 @@ double FixPropertyAtom::defaultvalue(int n)
return defaultvalues[n];
}
/* ----------------------------------------------------------------------
return pointer to fix property atom storing old-time values
------------------------------------------------------------------------- */
FixPropertyAtom *FixPropertyAtom::old_time_values()
{
if (!store_old_time_values_)
{
error->fix_error(FLERR,this,"fix does not store old-time values");
}
return old_time_values_;
}

View File

@ -46,7 +46,10 @@ class FixPropertyAtom : public Fix {
public:
FixPropertyAtom(class LAMMPS *, int, char **,bool parse = true);
~FixPropertyAtom();
void pre_delete(bool);
void post_create();
virtual int setmask();
void end_of_step();
void do_forward_comm();
void do_reverse_comm();
@ -60,7 +63,7 @@ class FixPropertyAtom : public Fix {
virtual void set_arrays(int);
virtual void set_all(double value);
virtual void set_array(int, int, double);
virtual void set_vector(int, double);
@ -78,8 +81,14 @@ class FixPropertyAtom : public Fix {
int pack_reverse_comm(int, int, double *);
void unpack_reverse_comm(int, int *, double *);
double compute_vector(int n);
int num_defaultvalues();
double defaultvalue(int);
virtual int num_defaultvalues();
virtual double defaultvalue(int);
int store_old_time_values()
{
return store_old_time_values_;
}
FixPropertyAtom *old_time_values();
virtual void mark_tracers(int ilo, int ihi) { UNUSED(ilo); UNUSED(ihi); }
@ -96,6 +105,9 @@ class FixPropertyAtom : public Fix {
// in case of initialization from property - name of property
char *propertyname;
double *property;
int store_old_time_values_;
FixPropertyAtom *old_time_values_;
}; //end class
}

Some files were not shown because too many files have changed in this diff Show More