GEMS icon GEMS3K Code for Solving for GeoChemical Equilibria

Function Calls and Access Methods at the TNode Level


Contents

Introduction

1. The simplest case: data exchange using disk files only

2. The case of data exchange in computer memory

3. Miscellaneous methods for accessing the GEM IPM data from the mass transport part

3.1. The whole node chemical system

3.2. Manipulations with phase- and component indexes

3.3. Manipulations with phase- and component properties

3.4. Access to integral properties of phases-solutions



Introduction

The input files to start calculations with GEMS3K can be exported from the GEM-Selektor package as described in the gems3k-manual file, and can also be modified using any ASCII text editor. The file formats are described in detail in the gems3k-iofiles file. The names of IPM, DCH and  DBR files should be collected in a list (txt file) with the file name/path given as a string in the first parameter of GEM_init() function call. Contents of this list usually look like this:

-t "Test-dch.dat" "Test-ipm.dat" "Test-dbr-0.dat"

All these files should be located in the same directory where  the list file is located. When coupling is performed on the TNode level, only one instance of DATABR structure exists in RAM, therefore, only the contents of one DBR file will be available after the GEM_init() call.

 

1. The simplest case: data exchange using disk files only

Programming example is provided in "standalone/gemcalc/main.cpp". See description in HowToCouple documentation file.

Description of function calls (see also "standalone/GEMS3K/node.h" file and doxygen-style documentation).

(1)  GEM_init()

long int GEM_init( const char *ipmfiles_lst_name, 
     const char *dbrfiles_lst_name = 0, long int *nodeTypes = 0, bool getNodT1 = false );

Purpose:

Initialization of GEM IPM data structures in coupled FMT-GEM programs that use GEMS3K module. Also reads in the IPM, DCH and DBR text input files.

Parameters:

 ipmfiles_lst_name
Pointer to a null-terminated C string with a path to a text file containing the list of names of GEMS3K input files.
 Example: file "test.lst" with a content:    -t "dch.dat" "ipm.dat" "dbr-0.dat" 
 (-t  tells that input files are in text format)
 dbrfiles_lst_name
Optional parameter that should be used only at the TNodeClass level. Pointer to a null-terminated C string with a path to a text file containing a comma-separated list of names of  DBR input files.    Example: file "test-dbr.lst" with a content:    "dbr-0.dat" , "dbr-1.dat" , "dbr-2.dat"
 nodeTypes
Optional parameter used only at the TNodeClass level to create nodeArray (not used in this document)
 getNodT1
Optional parameter used only when reading multiple DBR files after the modeling task interruption
in GEM-Selektor (not used in this document)

Return values:      

0  if successful; 1 if input file(s) were not found or corrupt; -1 if internal memory allocation error occurred.

Examples:

Call at TNode level:            iRet = GEM_init( "MyTest.lst" );

Call at TNodeArray level:  iRet = GEM_init( "MyTest.lst", "MyTest-nodes.lst", 1L );


(2) GEM_run()

long int  GEM_run( bool uPrimalSol ); 

Purpose:  

Main call for GEM IPM calculations using the input bulk composition, temperature, pressure and metastability constraints provided in the work instance of DATABR structure.  Actual calculation will be performed only when

dBR->NodeStatusCH == NEED_GEM_SIA (5) or
dBR->NodeStatusCH = NEED_GEM_AIA (1).

By other values of NodeStatusCH, no calculation will be performed, and the status will remain unchanged.

In the "smart initial approximation" (SIA) mode, the program can automatically switch into the "automatic initial approximation" (AIA) mode and return  OK_GEM_AIA instead of OK_GEM_SIA,  if  the previous speciation is not feasible as initial approximation.

Parameter:

 uPrimalSol
Flag to define the mode of GEM smart initial approximation (only if dBR->NodeStatusCH = NEED_GEM_SIA has been set before GEM_run() call):

     false  (0) -  use speciation and activity coefficients from previous GEM_run() calculation;
     true  (1)  -  use speciation provided in the DATABR memory structure (e.g. after reading the DBR file)

Return values:   

NodeStatusCH  (the same as set in dBR->NodeStatusCH). Possible values (see "databr.h" file for the full list):
 
 OK_GEM_AIA   ( 2 )  
OK after GEM calculation with simplex (automatic) initial approximation (IA)
 BAD_GEM_AIA  ( 3 )  
Bad (not fully trustful) result after GEM calculation with simplex (automatic) IA
 ERR_GEM_AIA  ( 4 )  
Failure (no result) in GEM calculation with simplex (automatic) IA
 OK_GEM_SIA   ( 6 )  
OK after GEM calculation with no-simplex (smart) IA
 BAD_GEM_SIA  ( 7 )  
Bad (not fully trustful) result after GEM calculation with no-simplex (smart) IA
 ERR_GEM_SIA  ( 8 )  
Failure (no result) in GEM calculation with no-simplex (smart) IA
 T_ERROR_GEM  ( 9 )  
Terminal error has occurred in GEMS3K (e.g. memory corruption). Restart is required. 

We recommend checking the NodeStatusCH immediately after the GEM_run() call, as shown in 'gemcalc' or 'node-gem' examples.
 

(3) GEM_write_dbr()

void  GEM_write_dbr( const char* fname,  bool binary_f=false, bool with_comments = true, bool brief_mode = false );

Purpose:       

Writes the contents of the work instance of DATABR structure into a disk file with path name  fname.

Parameters:

fname Null-terminated (C) string containing a full path to the DBR disk file to be written. If NULL  than the disk file name path stored in the  dbr_file_name  field of the TNode class instance will be used, extended with ".out".  Usually, the dbr_file_name field contains the path to the last input DBR file.
 binary_f
defines if the file is to be written in the binary format (true or 1, good for interruption of coupled modeling task if called in the loop for each node), or in the text format (false or 0, default).
 with_comments 
(Text format only): defines the mode of output of comments written before each data tag and content in the DBR file.
    If set to true (1), the comments will be written for all data entries (default). 
    If   false (0), comments will not be written.
 brief_mode  If true, tells that the data objects/items which contain only default values will be skipped from the text-format file (false is the default)


Any DBR file written using GEM_write_dbr() can be read as input file using GEM_init() or GEM_read_dbr() as long as it is consistent with the same set of IPM and DCH files that contain parameters of solution models and chemical system definition, respectively.

(4) GEM_print_ipm()

void  GEM_print_ipm( const char* fname )

Purpose:   

Produces a formatted text file with detailed contents (scalars and arrays) of the GEM IPM work structure. 

This call may be useful when GEM_run() returns with a NodeStatusCH value indicating a GEM calculation error (see  above).  Another possible use is for a detailed comparison of a test system calculation after the version upgrade of GEMS3K.

Parameters:

 fname 
Null-terminated (C) string containing a full path to the disk file to be written. If  NULL  then the disk file name path stored in the  dbr_file_name  field of the TNode class instance will be used, extended with ".dump.out".  Usually, the dbr_file_name field contains the path to the last input DBR file.
 

Attention: the text file produced by this function call cannot be read back with GEM_init() because it has a format that is incompatible with that of IPM, DCH and DBR input file formats.


(5) GEM_read_dbr()

long int GEM_read_dbr( const char* fname, bool binary_f=false );

Purpose:    

Reads another node data bridge (DBR) file with input system composition, T,P etc., from a path name fname. The DBR file must be compatible with the currently loaded IPM and DCH files (see description of GEM_init() function call).

Parameters:

 fname Null-terminated (C) string containing a full path to the input DBR disk file.
 binary_f
Flag defining whether the file specified in fname is in text fromat (false or 0, default)
         or in binary format (true or 1)

Return values:     0  if successful;

                                1 if input file(s) has not found been or is corrupt;

                               -1 if internal memory allocation error occurred.

The input DBR file may have been produced earlier from GEM-Selektor or via the GEM_write_dbr()call and then modified using a text editor or another program so that the format (data object tags, number of elements in arrays, etc.) remains intact and compatible with the IPM and DCH files.

 

Optional: GEM_CalcTime() and GEM_Iterations()  

double GEM_CalcTime();

Purpose:    

Returns GEM IPM calculation time in seconds elapsed during the last call of GEM_run() - can be used for monitoring the performance of calculations.

Return value: 

Double number, may contain 0.0 if the calculation time is less than the internal time resolution of C/C++ function  clock() defined in the value of the system variable CLOCKS_PER_SEC for a particular processor and operation system.


long int GEM_Iterations( long int& PrecLoops, long int& NumIterFIA, long int& NumIterIPM );

Purpose:     

To obtain the number of MBR (mass balance refinement) and GEM IPM iterations performed during the last call of GEM_run() e.g. for monitoring the performance of GEM IPM in AIA or SIA modes, or for the diagnostics of problems.   

Parameters: 

Function value, as well as long int variables per reference (must be allocated before calling GEM_Iterations()), previous values will be lost. See Return values.

Return values:

 Function 
Total number of MBR + IPM iterations from the last call to GEM_run().
 PrecLoops 
Total Number of performed phase selection + cleanup + MBR loops.
 NumIterFIA 
Total number of performed MBR (Entry Feasible Domain) iterations to obtain accurate initial approximation for the IPM algorithm.
 NumIterIPM 
Total number of performed GEM IPM main descent algorithm iterations.



2. The case of data exchange in computer memory

This case is typical for coupling GEMS3K with an existing reactive mass transport code that has its own data structure for keeping chemical information (e.g. speciation, bulk composition of the system) for each node. As in the previous example, it uses one work instance of the DATABR memory structure as a data bridge for the exchange with internal GEM IPM data structures.

Programming example is provided in "standalone/node-gem/main.cpp" and "standalone/node-gem/main.h" files. See a description in HowToCouple documentation file.

Description of used function calls (continued, see also "standalone/GEMS3K/node.h" file).

(6) GEM_restore_MT()

  void GEM_restore_MT(  long int  &p_NodeHandle,  long int  &p_NodeStatusCH,
       double &p_TK,  double &p_P, double &p_Vs, double &p_Ms,
       double *p_bIC, double *p_dul, double *p_dll, double *p_aPH );

Purpose:     

Passes (copies) the GEMS3K input data from the work instance of DATABR structure. 

This call is useful after the GEM_init()  and GEM_run() calls to initialize the arrays which keep the chemical data for all nodes used in the mass-transport model. The GEM_init() call reads the IPM, DCH and DBR file into the GEMS3K work structures (see details above). The GEM_run() call (details below) calculates the full chemical speciation. 

Parameters:

 Parameter ID
 Explanation
 Tag in the
DBR file
 p_NodeHandle Node identification handle NodeHandle
 p_NodeStatusCH Node status code (see Section 2 for possible codes)
NodeStatusCH
 p_TK Temperature T, Kelvins
TK
 p_P Pressure P,  Pa 
P
 p_Vs Volume V of reactive subsystem,  m3
Vs
 p_Ms Mass of reactive subsystem, kg 
Ms
 p_bIC Bulk mole amounts of Independent Components [dCH->nICb elements] bIC
 p_dul Upper restrictions to amounts of Dependent Components [dCH->nDCb elements]
dul
 p_dll Lower restrictions to amounts of Dependent Components [dCH->nDCb elements]
dll
 p_aPH Specific surface areas of phases, m2/kg [dCH->nPHb elements]
aPH

Return values:

All values are returned via parameters (pointers).

In GEM_restore_MT(), all parameters are output data, i.e. previous contents of memory given to parameters will be lost. Contents of the work DATABR structure (source of data) remain unchanged. This function is a reverse of  GEM_from_MT(), see Section (8).


(7) GEM_to_MT()

void GEM_to_MT( long int &p_NodeHandle, long int &p_NodeStatusCH, long int &p_IterDone,
    double &p_Vs, double &p_Ms, double &p_Gs, double &p_Hs, double &p_IC, 
    double &p_pH, double &p_pe, double &p_Eh, 
    double *p_rMB,  double *p_uIC,  double *p_xDC,  double *p_gam, double *p_xPH, 
    double *p_vPS,  double *p_mPS, double *p_bPS, double *p_xPA, double *p_aPh, double *p_bSP );

Purpose:

Retrieves the GEM IPM-3 chemical speciation calculation results from the work DATABR structure instance into memory provided by the mass transport part. Dimensions and order of elements in the arrays must correspond to those in currently existing DATACH memory structure.


Parameters: 

 Parameter ID
 Explanation
 Tag in the
DBR file
 p_NodeHandle Node identification handle NodeHandle
 p_NodeStatusCH
Node status code (see Section 2 for possible codes)
NodeStatusCH
 p_IterDone Number of iterations performed in the last GEM IPM calculation
IterDone
 p_Vs Total volume V of reactive subsystem at given P,T,  m3
Vs
 p_Ms Total mass of the reactive subsystem, kg 
Ms
 p_Gs Total Gibbs energy of the reactive subsystem, J
Gs
 p_Hs Total enthalpy of reactive subsystem, J (reserved)
Hs
 p_IC Effective aqueous ionic strength, molal (0 if no aqueous electrolyte phase)
IC
 p_pH pH of aqueous solution (0 if no aqueous electrolyte phase) pH
 p_pe pe of aqueous solution (0 if no aqueous electrolyte phase) pe
 p_Eh Eh of aqueous solution, V (0 if no aqueous electrolyte phase) Eh
 p_rMB Mole balance residuals for Independent Components [dCH->nICb elements] rMB
 p_uIC Dual solution: chemical potentials of independent components, mol/mol [dCH->nICb elements]
uIC
 p_xDC Primal solution: mole amounts of dependent components (equilibrium speciation) [dCH->nDCb elements]
xDC
 p_gam External activity coefficients of dependent components [dCH->nDCb elements] gam
 p_xPH Total mole amounts of all phases [dCH->nPHb elements]
xPH
 p_vPS Total volumes of multicomponent phases, m3 [dCH->nPSb elements]  
vPS
 p_mPS Total mass of multicomponent phase,  kg [dCH->nPSb elements] 
mPS
 p_bPS Bulk compositions of phases [dCH->nPSb*dCH->nICb elements] bPS
 p_xPA Amount of carrier in a multicomponent asymmetric phase  [dCH->nPSb elements] xPA
 p_aPh Surface areas of phases, m2 [dCH->nPHb elements] aPh
p_bSP
Bulk composition of the solid part of equilibrated sub-system, moles [dCH->nICb elements] bSP

Return values:

All values are returned via parameters (pointers).

In GEM_to_MT(), all parameters are output parameters ( i.e. previous contents of memory given to parameters will be lost). Contents of the work DATABR structure remain unchanged. Parameter IDs for the most important GEM IPM output data are underlined.


(8) GEM_from_MT()

  void GEM_from_MT(  long int  p_NodeHandle,  long int  p_NodeStatusCH,
       double p_TK,  double p_P, double p_Vs, double p_Ms,
       double *p_bIC, double *p_dul, double *p_dll, double *p_aPH );

Purpose:    

Loads the GEMS3K input data for a given mass-transport node into the work instance of DATABR structure.  This call is usually preceeding the GEM_run() call

Parameters:

 Parameter ID
 Explanation
 Tag in the
DBR file
 p_NodeHandle Node identification handle
NodeHandle
 p_NodeStatusCH 
Node status code (NEED_GEM_SIA or NEED_GEM_AIA), will be changed internally after GEM_run()
NodeStatusCH
 p_TK Temperature T, Kelvin
TC
 p_P Pressure P,  Pa
P
 p_Vs Volume V of reactive subsystem, m3, may change in GEM_run() internally
Vs
 p_Ms Mass of reactive subsystem, kg; may be updated  in GEM_run() internally Ms
 p_bIC Bulk mole amounts of Independent Components [dCH->nICb elements] bIC
 p_dul Upper restrictions to amounts of Dependent Components [dCH->nDCb elements]
dul
 p_dll Lower restrictions to amounts of Dependent Components [dCH->nDCb elements]
dll
 p_aPH Specific surface areas of phases, m2/kg [dCH->nPHb elements]
aPH
 p_xDC Mole amounts of DCs [dCH->nDCb] - will be internally convoluted and added to the bIC GEM input vector  (only in the overloaded call, see Section 8a below)
xDC
 p_gam
DC activity coefficients [dCH->nDCb] - used only in the overloaded call (see Section 8b) together with the p_xDC data as GEM initial approximation for this node
gam

Return values: none.

In GEM_from_MT(), all parameters are input ( i.e. contents of memory given to parameters will remain unchanged).
Most frequently changed input parameters are underlined in the above table.

This function is a reverse of  GEM_restore_MT(), see Section (6). 

To retrieve, if necessary, the changed  Vs or Ms values after the GEM_run(), use GEM_restore_MT() or GEM_to_MT() calls.

(8a) GEM_from_MT() overload call

void GEM_from_MT(  long int  p_NodeHandle,  long int  p_NodeStatusCH,
       double p_TK,  double p_P, double p_Vs, double p_Ms,
       double *p_bIC, double *p_dul, double *p_dll, double *p_aPH, double *p_xDC );

Purpose:     

Loads the GEMS3K input data for a given mass-transport node into the work instance of DATABR structure. In advection/diffusion transport codes (such as OpenGeoSys),  not the total amounts of elements, but the amounts of aqueous species are usually moved between nodes. Conversely, after the mass transport step, only the speciation vector xDC is changed in each node, and an additional step would be needed to compute a corrected bIC vector (i.e. elemental bulk composition) in each node, which is the GEM input to compute the new speciation. With the 8a variant of GEM_from_MT() call, this task is performed by GEMS3K, so that there is no need to do it in the mass transport part.
This overloaded variant uses the xDC speciation vector (provided as the last parameter in the function call list) for setting the new bulk chemical composition to be used in the next GEM_run() calculation. Whatever total charge value is computed from the xDC data, it will be set to zero in the last element of bIC vector. Actually, total amounts of chemical elements are calculated from stoichiometries of Dependent Components (as provided in the A matrix in DATACH structure) and their amounts (in the xDC vector), and then added to the amounts given in the bIC vector (passed through the p_bIC parameter).
Hence, two cases are possible. One case is when the mass trasport step puts in the p_xDC parameter the differences between the new and the old speciation in the node chemical system. In this case, the old p_bIC content (e.g. unchanged since the last GEM calculation for this node) must be provided - then it will be automatically corrected.  Another case is when the mass-transport part delivers in p_xDC the complete new speciation after the transport time step. In this case, the p_bIC vector must be filled out with zeros, because its new content will be completely retrieved from the x_DC vector. 

Parameters:  see Table in Section (8) - all are input parameters.

(8b) GEM_from_MT() overload call

void GEM_from_MT(  long int  p_NodeHandle,  long int  p_NodeStatusCH,
       double p_TK,  double p_P, double p_Vs, double p_Ms, double *p_bIC,
       double *p_dul, double *p_dll, double *p_aPH,
double *p_xDC, double *p_gam );


Purpose:     

Loads the GEMS3K input data for a given mass-transport node into the work instance of DATABR structure.

In addition, it provides access to speciation vector p_xDC and species activity coefficients p_gam  that will be used in GEM IPM "smart initial approximation" SIA mode if dBR->NodeStatusCH == NEED_GEM_SIA (5) and uPrimalSol = true are set for the GEM_run() call (see Section 2) . This works only when the DATACH structure contains a full list of dependent components used in GEM IPM calculations.


Parameters:  see Table in Section (8) - all are input parameters.

Open issue: shall p_xDC content be used for updating bIC content in the same way as in variant (8a)?

(9) GEM_set_MT()

void GEM_set_MT( double p_Tm, double p_dt );

Purpose:     

Optional, for passing the current mass transport iteration information into the work DATABR structure (e.g. for using it in tracing/debugging or in writing DBR files for nodes using TNode functions).

Parameters: 

 p_Tm 
Actual total simulation time, s
 p_dt 
Actual time step, s




3. Miscellaneous methods for accessing the GEM IPM data from the mass transport part

These public methods of access to particular elements of the TNode class data require that the "node.h" header is included. Usage of these public methods is strongly preferred instead of direct access to fields of the DATABR, DATACH and MULTI memory structures. The lists may be incomplete, as new data item access methods can be added in future versions of GEMS3K and TNode class interface.

In the following, acronyms 'IC' and 'DC' mean 'independent component' and 'dependent component', respectively.

3.1. The whole node chemical system

Table 3.1. Access to the properties of the whole chemical system assigned to the node

 Access method
 Function
 Example
 TNode* TNode(); Constructor of the class instance in memory
 TNode* node = new TNode();
 double 
 GEM_CalcTime();

Returns GEMIPM calculation time in s, elapsed during the last call to GEM_run()
 DATACH* pCSD() Get the pointer to chemical system definition data structure  DATACH* dCH = node->pCSD();
 DATABR* pCNode() Get pointer to work node data structure (not recommended on TNodearray level)
 DATABR* dBR =
   node->pCNode();
 double cTK() Get current node Temperature T, in Kelvins
 double TK = node->cTK();
 double cTC() Get current node Temperature T, in degrees Celsius
 double TC = node->cTC();
 double cP() Get current node Pressure P,  in Pa
 double P = node->cP();
 double cMs()
Get current mass of reactive part, in kg
 double Mass = node->cMs();
 double cVs()
Get current volume of reactive part, in m3
 double Vol_L = 
   node->cVs*1000.;

 void setNodeHandle( long int jj ) Set current node identification handle to value of parameter jj
 node->setNodeHandle( 4L );
 bool check_TP( double T, double P ); Checks, if the given temperature T (K) and the pressure P (Pa) fit within the interpolation intervals of the DATACH lookup arrays (returns true) or not (returns false)
 if(!node->checkTP(320.,2e5))
    return 1;
 long int  check_grid_TP(  double T, double P ); Tests whether T (K) and P (bar) is a grid point of the DATACH lookup array for the interpolation of thermodynamic data. Returns -1L if the interpolation is needed, or uni-dimensional index of the lookup array grid point if T and P fit within the respective tolerances. For producing lookup arrays (in GEM-Selektor), we recommend using the step for temperature less or equal to 10 degrees in order to assure good accuracy of interpolation, especially for S0 and Cp0 of aqueous species.
 long int laX =
 node->check_grid_TP( 400., 5e5 );

   

3.2. Manipulations with phase- and component indexes

In the GEMS3K code, two indexation systems for phases and components are maintained. One pertains to the complete definition of chemical system as expressed in the input DCH and IPM files and, accordingly, in DATACH and MULTI memory structures (the latter is used for keeping all internal data in GEM IPM calculations). Another indexation system defines which phases and components are involved in the data exchange via the DBR input/output files and the DATABR memory structure in the work TNode class instance. The two indexation systems are connected through the index mapping lists xIC, xDC and xPH (and the respective counters nICb, nIC, nDCb, nDC, nPHb, nPH, nPSb, nPS) that exist in the DCH file and DATACH structure.

The trivial (default) case is when nICb = nIC,nDCb = nDC, nPHb = nPH, nPSb = nPS. In this case, the data arrays in the DATABR structure exactly map the corresponding data arrays in DATACH and MULTI structures. For instance, the bulk chemical composition of the system - vector b in the MULTI structure - is the same as the vector bIC provided in the DATABR structure or in the DBR file. The index mapping lists xIC, xDC and xPH will also be trivial. For instance, given 7 independent components in the system (nIC = 7), the xIC array will simply contain seven ascending indexes (0,1,2,3,4,5,6).

During the development of GEMS3K, it was foreseen that the usage of index mapping lists  xIC,xDC and xPH may significantly accelerate data exchange and reduce memory size of the coupled RMT-GEM problem when some ICs, DCs and phases are not considered in the data exchange and/or in transport between the nodes. For example, the break-through columns in experiments are often filled with quartz sand, dissolution of which can be neglected, so the transport of dissolved silica can also be neglected.  For a system involving calcium and magnesium, carbonate, and chloride, the  DATACH lists in this case will look like:

<nIC> 8   <nDC> 27   <nPH> 8   <nPS> 2
<ICNL>
  'C' 'Ca' 'Cl' 'H' 'Mg' 'O' 'Si' 'Zz'    ( NB: 'Zz' stays for electrical charge).
<DCNL>  'Ca+2' 'CaOH+' 'Ca(HSiO3)+' 'CaSiO3@' 'Mg+2' 'MgOH+' 'HSiO3-' 'SiO2@' 'SiO3-2' 'CO2@' 'CO3-2' 'HCO3-' 'CH4@' 'Cl-' 'H2@' 'O2@' 'OH-' 'H+' 'H2O@' 'H2' 'O2' 'Gr' 'Cal' 'Dis-Dol' 'Portlandite' 'Brc' 'Qtz'.
<PHNL>  'aq_gen' 'gas_gen' 'Graphite' 'Calcite' 'Dolomite-dis' 'Portlandite' 'Brucite' 'Quartz'
<nDCinPH>  19 2 1 1 1 1 1 1

Now, suppose that our mass transport model does not consider the transport of gas phase, electric charge, and of dissolved silicium species (non-transported components and species are marked red in the lists above). Some aqueous species and solids are very unlikely to appear (marked in pink) and thus can also be considered irrelevant for the MT model . Then  the  respective arrays of the DATABR structure can be made smaller, and values in them re-mapped to DATACH or MULTI structure as follows:

<nICb> 6   <nDCb> 15   <nPHb> 3   <nPSb> 1
<xIC>  0 1 2 3 4 5
<xDC>  0 1  4 5  9 10 11  13 14 15 16 17 18  22 23
<xPH>  0  3 4


It is important to realize that the re-mapping does not affect any dimensions in the MULTI structure and any DATACH lists and arrays (the latter remain accessible in full also from the mass transport part of the coupled code). Values for components and phases marked red (non-transported) are skipped only from data arrays in all instances of the DATABR structure, but these components and phases are still present in DATACH and MULTI structures and may take part in the chemical equilibration modeled in GEM IPM runs. In the above example, the size of a DATABR instance (and DBR file) becomes 30% less compared with the trivial (complete) index mapping case.  This decrease can be even more dramatic for some transport algorithms where only a certain tracers move, or where the advection strongly prevails over the diffusion. In the latter case, only the bulk aqueous solution is migrated as the whole between the nodes, so all dependent components of the aqueous phase can be skipped from the DATABR mapping. In the above example, this would make the DATABR instance ca. 3-4 times smaller than in the trivial mapping case.

It can be stated that the presence of DATABR index mapping to DATACH structure provides a great flexibility in defining various coupling schemes between the FMT and the GEM parts. A natural question is - how the bulk composition of the node system can be set up when the mapping list xIC is incomplete?  A straightforward answer is - the full b vector can always be provided in the IPM file (from where it is directly loaded into the MULTI structure). The TNode class also has methods for the direct access to the b vector using the DATACH/MULTI indexation, which can be used e.g. for setting in all nodes the initial amounts of ICs skipped from the DATABR index mapping. Use of this functionality makes sense in 2-D or 3-D FMT problems with relatively large chemical system definition, where it may result in considerably less memory demand and higher performance of data exchange. However, the use of SIA initial approximation mode of GEM IPM may be restricted in this case. Hence, for 1-D columns, we still recommend using the trivial (complete) one-to-one mapping in DATABR and DBR files.

In Table 3.2 below, the description of TNode class fnctionality for manipulating the  indexes of phases and components (also by names) is provided. Data access methods using either DBR or DCH indexation are summarized in Tables 3.3, 3.4 and so on. 


Table 3.2. Retrieval of indexes for components and phases

 Access method
 Function
 Example
 long int IC_name_to_xCH(const char *Name); Returns DCH index of IC given the IC Name string (null-terminated) or -1 if no such name was found in the DATACH IC name list long int xCa = node->IC_name_to_xCH("Ca");
 long int DC_name_to_xCH(const char *Name); Returns DCH index of DC given the DC Name string (null-terminated) or -1 if no such name was found in the DATACH DC name list long int xCa_ion = node->DC_name_to_xCH("Ca+2");
 long int Ph_name_to_xCH(const char *Name); Returns DCH index of Phase given the Phase Name string or -1 if no such name was found in the DATACH Phase name list long int xCalcite = node->Ph_name_to_xCH("Calcite");
 long int IC_name_to_xDB(const char *Name) Returns DBR index of IC given the IC Name string or -1 if no such name was found in the DATACH IC name list long int xbCa = node->IC_name_to_xDB("Ca");
 long int DC_name_to_xDB(const char *Name) Returns DBR index of DC given the DC Name string or -1 if no such name was found in the DATACH DC name list long int xbCa_ion = node->DC_name_to_xDB("Ca+2");
 long int Ph_name_to_xDB(const char *Name) Returns DBR index of Phase given the Phase Name string or -1 if no such name was found in the DATACH phase name list long int xbCalcite = node->Ph_name_to_xDB("Calcite");
 long int IC_xCH_to_xDB(const long int xCH);
Converts the IC DCH index xCH into the IC DBR index (return value) or returns -1 if this IC is not used in the data bridge xbCa = node->IC_xCH_to_xDB(xCa);
 long int DC_xCH_to_xDB(const long int xCH ); Converts the DC DCH index xCH into the DC DBR index (return value) or returns -1 if this DC is not used in the data bridge xbCa_ion = node->DC_xCH_to_xDB(xCa_ion);
 long int Ph_xCH_to_xDB(const long int xCH ); Converts the Phase DCH index xCH into the Phase DBR index (return value) or returns -1 if this phase is not used in the data bridge xbCalcite = node->Ph_xCH_to_xDB(xCalcite);
 long int IC_xDB_to_xCH(const long int xBR ) Converts the IC DBR index xBR into the IC DCH index (return value) xCa = node->IC_xDB_to_xCH(xbCa);
 long int DC_xDB_to_xCH( const long int xBR ) Converts the DC DBR index xBR into the DC DCH index (return value) xCa_ion = node->DC_xDB_to_xCH(xbCa_ion);
 long int Ph_xDB_to_xCH( const long int xBR ) Converts the Phase DBR index xBR into the Phase DCH index (return value) xCalcite = node->Ph_xDB_to_xCH(xbCalcite);
 long int Phx_to_DCx( const long int Phx ); Returns the DCH index of the first DC belonging to the phase with DCH index Phx
long int xCal = node->Phx_to_DCx( xCalcite );
 long int PhtoDC_DCH( const long int Phx, long int& nDCinPh ); Returns the DCH index of the first DC belonging to the phase with DCH index Phx, plus returns through the nDCinPh (reference) parameter the number of DCs included into this phase
long int nDCGas;
long int xGas =
node->Ph_name_to_xCH("Gasmix");
long int xCH4 = node->Phx_to_DCx(xGas,nDCGas);
 long int DCtoPh_DCH( const long int xCH ) Returns the DCH index of the Phase to which the DC with index xCH belongs
xPh = node->DCtoPh_DCH(xCa_ion);
 long int PhtoDC_DBR( const long int Phx, long int& nDCinPh ); Returns the DBR index of the first DC belonging to the phase with DBR index Phx, plus returns through the nDCinPh (reference) parameter the number of DCs included into DBR for this phase  long int nbDCGas;
long int xbGas =
node->Ph_name_to_xDB("Gasmix");
long int xbCH4 = node->Phx_to_DCx(xbGas,nbDCGas);
 long int DCtoPh_DBR( const long int xBR )
Returns the DBR index of the Phase to which the  DC with index xBR belongs
xbPh = node->DCtoPh_DCH(xbCa_ion);


3.3. Manipulations with phase- and component properties

In DBR files and in the DATABR structure, results for volumes, masses and bulk compositions for phases are only provided for multi-component phases because for pure phases, they can be easily retrieved from other input data and results. Nevertheless, public functions Ph_Volume(), Ph_Mass(), Ph_BC() and Ph_SatInd() are provided in TNode class that work both for multi- and single-component phases. This is done in order to make access to such data from the side of mass-transport part of the program as simple as possible.

All functions in Table 3.3 actually access only data in the work DATABR structure; this has to be kept in mind when not all components and phases are exchanged through DATABR or DBR files. For the full access to DATACH/MULTI data for phases and components, even those not included in DATABR lists, see Table 3.4.


Table 3.3. Access to equilibrium properties of phases and components using DATABR (DBR file) indexation

 Access method
 Function
 Example
 double Ph_Volume( const long int xph ); Retrieves the current phase volume in m3 ( xph is DBR phase index) in the reactive sub-system. Works both for multicomponent and for single-component phases. Returns 0.0 if the phase mole amount is zero.
long int xbCalcite = node->Ph_name_to_xDB("Calcite");
double CalVol = node->Ph_Volume(xbCalcite);
 double Ph_Mass( const long int xph ); Retrieves the phase mass in kg ( xph is DBR phase index). Works for multicomponent and for single-component phases. Returns 0.0 if phase amount is zero. double CalM = node->Ph_Mass(xbCalcite); double CalDen = CalM / CalVol; 
 double Ph_SatInd( const long int xph); Retrieves the phase saturation index ( xph is DBR phase index). Works for multicomponent and for single-component phases. Returns 0.0 if phase amount is zero. double CalOmg = Ph_SatInd(xbCalcite);
 double* Ph_BC( const long int xph, double *ARout=0 ); Retrieval of the phase bulk composition ( xph is DBR phase index) into memory indicated by ARout (array of at least [dCH->nICb elements]). Returns pointer to ARout which may also be allocated inside of Ph_BC() in the case if parameter ARout = NULL is specified; to avoid a memory leak, you will have to free this memory wherever appropriate. This function works for multicomponent and for single-component phases double* PhB;
PhB = new double [
dCH->nICb];
node->Ph_BC( xbCalcite, PhB );
. . . . . . . . . . . .
delete[]PhB;
 void Set_bIC( const long int xic, const double bIC); Sets the amount of IC (xic is the IC DBR index) in the respective element of the bIC input vector of the work DATABR structure long int xbCa = node->IC_name_to_xDB("Ca");
node->Set_bIC(xbCa, 0.1 );
 double Get_bIC(const long int xic); Retrieves the current amount of IC (xic is IC DBR index) double bIC = node->Get_bIC(xbCa);
 void Set_dll( const long int xdc, const double dll); Sets the metastability constraint from below to the mole amount of DC (xdc is DC DBR index) in the dll vector of the work DATABR structure long int xbCa_ion = node->DC_name_to_xDB("Ca+2");
node->Set_dll(xbCa_ion, 0.001 );
 void Set_dul( const long int xdc, const double dll); Sets the metastability constraint from above to the mole amount of DC (xdc is DC DBR index) in the dul vector of the work DATABR structure node->Set_dul(xbCa_ion, 1e5 );
 void Set_nDC( const long int xdc, const double nDC); Sets the mole amount of DC (xdc is DC DBR index) in the xDC vector of the work DATABR structure
node->Set_nDC(xbCa_ion, 1e-5 );
 double Get_nDC(const long int xdc);
Retrieves the current mole amount of DC (xdc is DC DBR index) from the xDC vector of the work DATABR structure double nDC = node->Get_nDC(xbCa_ion);
 double Get_muDC( const long int xDC, bool norm=true ); Retrieves the DC (dual-solution) chemical potential  (xdc is the DC DBR index). Parameter norm defines the scale: if true (1) then in mol/mol, otherwise in J/mol
double muDC = node->Get_muDC( xbCa_ion);
 double Get_aDC( const long int xdc);
Retrieves the (dual-thermodynamic) activity of the Dependent Component (xdc is the DC DBR index)
double aDC = node->Get_aDC( xbCa_ion);
 double Get_cDC( const long int xdc);
Retrieves the DC concentration (xdc is the DC DBR index) in its phase in the respective concentration scale. For aqueous species, molality is returned; for gas species, partial pressure; for surface species - density in mol/m2; for species in other phases - mole fraction. If DC has a zero amount, the function returns 0.0. double cDC = node->Get_cDC( xbCa_ion);
 double Get_gDC( const long int xDC);
Retrieves the DC external activity coefficient (xdc is the DC DBR index) in its phase in the respective scale. Returns 1.0 if the amount of this DC is 0.0
double gDC = node->Get_gDC( xbCa_ion);
 double DCmm( const long int xdc ); Retrieves the DC molar mass (xdc is DC DBR index) in kg/mol
double mm = node->DCmm( xbCa_ion);
 double ICmm( const long int xic ); Retrieves the IC atomic (molar) mass  (xic is IC DBR index) in kg/mol
double mm = node->ICmm( xbCa );
 double DCaJI( const long int xdc, const long int xic);
Retrieves the stoichiometry coefficient a[j][i] of IC (xic is IC DBR index) in the formula of DC (xdc is DC DBR index) double aij = node->DCaJI(
xbCa_ion xbCa );



Table 3.4. Access to thermodynamic and equilibrium properties of phases and components using DATACH (DCH file) indexation

 Access method  Function  Example
 void Set_IC_b( const double b_val, const long int xCH)
(*) Sets the amount of IC (xCH is IC DCH index) when this IC index is not included into DATABR. Internal re-scaling to mass of the system is applied, but only to mass of that part which is included in the DATABR. long int xSi = node->IC_name_to_xCH("Si");
double moles_Si = 0.003; Set_IC_b( moles_Si, xSi );
 double IC_b(const long int xCH) (*) Retrieves the current amount of IC (xCH is IC DCH index). Also amount of ICs not included into DATABR list can be retrieved. Internal re-scaling to mass of the system is applied. long int xCa = node->IC_name_to_xCH("Ca");
double moles_Ca = IC_b(xCa);
 double DC_n(const long int xCH) (*) Retrieves the current mole amount of DC (xCH is DC DCH index) directly from GEM IPM work structure. Also amount of DCs not included into DATABR list can be retrieved. Internal re-scaling to mass of the system is applied.
long int xCa_ion = node->DC_name_to_xCH("Ca+2");
double moles_Ca_ion = node->DC_n(xCa_ion);
 double DC_a(const long int xCH) (*) Retrieves the current (dual-thermodynamic) activity of DC (xCH is DC DCH index) directly from GEM IPM work structure. Also activity of a DC not included into DATABR list can be retrieved. If DC has zero amount, its dual-thermodynamic activity is returned anyway. For single condensed phase component, this value has a meaning of the saturation index, also in the presence of metastability constraint(s).
double a_Ca_ion = node->DC_a(xCa_ion);
 double DC_c(const long int xCH) (*) Retrieves the current concentration of DC (xCH is DC DCH index) in its phase directly from GEM IPM work structure. Also activity of a DC not included into DATABR list can be retrieved. For aqueous species, molality is returned; for gas species, partial pressure; for surface species - density in mol/m2; for species in other phases - mole fraction. If DC has zero amount, the function returns 0.0.
double m_Ca_ion = DC_c(xCa_ion);
 double DC_g(const long int xCH) (*) Retrieves the current DC external activity coefficient  (xCH is DC DCH index) in its phase directly from GEM IPM work structure. Also activity coefficient of a DC not included into DATABR list can be retrieved. If DC has zero amount, this function returns 1.0. double gamma_Ca_ion = node->DC_g(xCa_ion);
 double DC_mu(const long int xCH, bool norm=true) (*) Retrieves the current (dual-solution) chemical potential of DC (xCH is DC DCH index) directly from GEM IPM work structure, also for any DC not included into DATABR or having zero amount. Parameter norm defines in wnich units the chemical potential value is returned: false - in J/mol; true (default) - in mol/mol.
double mu_Ca_ion_J_mol = node->DC_mu(xCa_ion, false);
 double DC_mu0(const long int xCH, bool norm=true) (*) Retrieves the standard-state chemical potential of DC (xCH is DC DCH index) directly from GEM IPM work structure at current pressure and temperature, also for any DC not included into DATABR or having zero amount. Parameter norm defines, in which units the chemical potential value is returned: false - in J/mol; true (default) - in mol/mol. double mu0_Ca_ion_J_mol = node->DC_mu0(xCa_ion, false);
 double DC_G0(const long int xCH, const double P, const double TK,  bool norm=true)

Retrieves (interpolated) molar Gibbs energy G0(P,TK) value for DC from the DATACH structure ( xCH is the DC DCH index) or 7777777., if TK (temperature, K) or P (pressure, Pa) parameters go beyond the valid lookup array intervals or tolerances. Parameter norm defines, in wnich units the value is returned: false - in J/mol; true (default) - in mol/mol. double g0_Ca_ion = node->DC_G0( xCa_ion, 1e5, 298, false);
 double DC_V0(const long int xCH, const double P, const double TK)

Retrieves (interpolated, if necessary) molar volume V0(P,TK) value for DC (in J/Pa or m3/mol) from the DATACH structure ( xCH is the DC DCH index) or 0., if TK (temperature, K) or P (pressure, Pa) parameters go beyond the valid lookup array intervals or tolerances. 
double v0_Ca_ion = node->DC_V0( xCa_ion, 1e5, 298. );
 double DC_H0(const long int xCH, const double P, const double TK) (**) Retrieves (interpolated) molar enthalpy H0(P,TK) value for DC (in J/mol) from the DATACH structure ( xCH is the DC DCH index) or 7777777., if TK (temperature, K) or P (pressure, Pa) parameters go beyond the valid lookup array intervals or tolerances. double h0_Ca_ion = node->DC_H0( xCa_ion, 1e5, 298. );
 double DC_S0(const long int xCH, const double P, const double TK) (**) Retrieves (interpolated) absolute molar enropy S0(P,TK) value for DC (in J/K/mol) from the DATACH structure ( xCH is the DC DCH index) or 0.0, if TK (temperature, K) or P (pressure, Pa) parameters go beyond the valid lookup array intervals or tolerances. double s0_Ca_ion = node->DC_S0( xCa_ion, 1e5, 298. );
double DC_Cp0(const long int xCH, const double P, const double TK) (**) Retrieves (interpolated) constant-pressure heat capacity Cp0(P,TK) value for DC (in J/K/mol) from the DATACH structure ( xCH is the DC DCH index) or 0.0, if TK (temperature, K) or P (pressure, Pa) parameters go beyond the valid lookup array intervals or tolerances. double cp0_Ca_ion = node->DC_Cp0( xCa_ion, 1e5, 298. );
 double EpsH2Ow(const double P, const double TK) (**) Retrieves (interpolated) dielectric constant of liquid water at (P,TK) from the DATACH structure  or 0.0, if TK (temperature, K) or P (pressure, Pa) parameters go beyond the valid lookup array intervals or tolerances. double epsW = node->EpsH2Ow( 1e6, 350.);
 double DenH2Ow(const double P, const double TK)
(**) Retrieves (interpolated) density of liquid water (in kg/m3) at (P,TK) from the DATACH structure or 0.0, if TK (temperature, K) or P (pressure, Pa) parameters go beyond the valid lookup array intervals or tolerances. double denW = node->DenH2Ow( 1e6, 350.);
 double VisH2Ow(const double P, const double TK) (**) Retrieves (interpolated) viscosity (units???) of liquid water at (P,TK) from the DATACH structure or 0.0, if TK (temperature, K) or P (pressure, Pa) parameters go beyond the valid lookup array intervals or tolerances. double visW = node->VisH2Ow( 1e6, 350.);
 double EpsH2Og(const double P, const double TK) (**) Retrieves (interpolated) dielectric constant of H2O vapor at (P,TK) from the DATACH structure or 0.0, if TK (temperature, K) or P (pressure, Pa) parameters go beyond the valid lookup array intervals or tolerances. double epsWg = node->EpsH2Og( 1e6, 350.);
 double DenH2Og(const double P, const double TK) (**) Retrieves (interpolated) density of H2O vapor (in kg/m3) at (P,TK) from the DATACH structure or 0.0, if TK (temperature, K) or P (pressure, Pa) parameters go beyond the valid lookup array intervals or tolerances. double denW g= node->DenH2Og( 1e6, 350.);

Some functions (marked with *) access the IPM work data structure directly and can be used only for the current work node, if several TNode class instances exist in the program.

Functions marked with (**) can only be used if the respective lookup arrays are available from the DCH file and allocated in the DATACH structure in the TNode class work instance.


3.4. Access to integral properties of phases-solutions (under construction)

Only access via DCH indexation (will be added in next versions)



Last change: 17.12.2012 DK SD

Copyright (c) 2012 GEMS Development Team