From e6ef90add42dab66174e29b5bfd93589c2ecbfe7 Mon Sep 17 00:00:00 2001
From: Kyle <kyle.c.klenk@gmail.com>
Date: Sat, 27 Aug 2022 19:24:43 +0000
Subject: [PATCH] added lookup struct

---
 build/includes/global/fortran_data_types.hpp  |   3 +
 build/includes/hru_actor/hru_actor.hpp        |   6 +-
 .../hru_actor_subroutine_wrappers.hpp         |  16 +----
 build/makefile                                |   2 +-
 build/makefile_sundials                       |   2 +-
 .../actors/global/cppwrap_datatypes.f90       |   9 +++
 build/source/actors/hru_actor/hru_actor.cpp   |   3 +-
 ...ummaActors_init.f90 => init_hru_actor.f90} |  28 ++++++---
 .../driver/summaActors_wOutputStruc.f90       |   8 ++-
 build/source/dshare/get_ixname.f90            |  21 +++++++
 build/source/dshare/globalData.f90            |   8 ++-
 build/source/dshare/popMetadat.f90            |  11 ++++
 build/source/dshare/var_lookup.f90            |  13 ++++
 build/source/engine/allocspaceActors.f90      |   4 ++
 build/source/engine/checkStruc.f90            |   4 ++
 build/source/engine/nrtype.mod                | Bin 770 -> 769 bytes
 build/source/netcdf/def_output.f90            |  59 ++++++++++++------
 .../sundials/launch_docker_container.sh       |   2 +-
 18 files changed, 148 insertions(+), 51 deletions(-)
 rename build/source/driver/{summaActors_init.f90 => init_hru_actor.f90} (95%)

diff --git a/build/includes/global/fortran_data_types.hpp b/build/includes/global/fortran_data_types.hpp
index 7552b97..e683399 100644
--- a/build/includes/global/fortran_data_types.hpp
+++ b/build/includes/global/fortran_data_types.hpp
@@ -96,4 +96,7 @@ extern "C" {
     void* new_handle_file_info();
     void delete_handle_file_info(void* handle);
 
+    // zLookup
+    void* new_handle_z_lookup();
+
 }
\ No newline at end of file
diff --git a/build/includes/hru_actor/hru_actor.hpp b/build/includes/hru_actor/hru_actor.hpp
index 2f4c8d9..cb0b725 100644
--- a/build/includes/hru_actor/hru_actor.hpp
+++ b/build/includes/hru_actor/hru_actor.hpp
@@ -53,7 +53,11 @@ struct hru_state {
     void *handle_bvarStruct = new_handle_var_dlength(); // basin-average variables
     // ancillary data structures
     void *handle_dparStruct = new_handle_var_d();		// default model parameters
-   // Local hru data
+    // sundials type
+    void *handle_lookupStruct = new_handle_z_lookup();
+
+    
+    // Local hru data
     void *handle_ncid = new_handle_var_i();             // output file ids
     void *handle_statCounter = new_handle_var_i();
     void *handle_outputTimeStep = new_handle_var_i();
diff --git a/build/includes/hru_actor/hru_actor_subroutine_wrappers.hpp b/build/includes/hru_actor/hru_actor_subroutine_wrappers.hpp
index 9ffdece..c625ca3 100644
--- a/build/includes/hru_actor/hru_actor_subroutine_wrappers.hpp
+++ b/build/includes/hru_actor/hru_actor_subroutine_wrappers.hpp
@@ -2,8 +2,8 @@
 
 extern "C" {
   // Initialize HRU data_structures
-	void summaActors_initialize(
-        int* indxGRU, int* num_steps,
+	void initHRU(
+        int* indxGRU, int* num_steps, void* lookupStruct,
         // Statistics Structures
         void* forcStat, void* progStat, void* diagStat, void* fluxStat, void* indxStat, void* bvarStat,
         // Primary Data Structures (scalars) 
@@ -16,18 +16,6 @@ extern "C" {
         void* dparStruct,
         // local HRU data 
         void* startTime, void* finshTime, void* refTime, void* oldTime, int* err);
-
-  // SetupParam for HRU
-  // void SetupParam( 
-  //     int* indxGRU, int* indxHRU,
-  //     // primary data structures (scalars)
-  //     void* attrStruct, void* typeStruct, void* idStruct,
-  //     // primary data structures (variable length vectors)
-  //     void* mparStruct, void* bparStruct, void* bvarStruct, void* dparStruct,
-  //     // local HRU data
-  //     void* startTime, void* oldTime,
-  //     // miscellaneous
-  //     double* upArea, int* err);
     
   void setupHRUParam( int* indxGRU, int* indxHRU,
       // primary data structures (scalars)
diff --git a/build/makefile b/build/makefile
index 652faa7..9b984db 100644
--- a/build/makefile
+++ b/build/makefile
@@ -234,7 +234,7 @@ SUMMA_DRIVER= \
 		summaActors_type.f90 \
 		summaActors_util.f90 \
 		summaActors_globalData.f90 \
-		summaActors_init.f90 \
+		init_hru_actor.f90 \
 		SummaActors_setup.f90 \
 		summaActors_restart.f90 \
 		summaActors_forcing.f90 \
diff --git a/build/makefile_sundials b/build/makefile_sundials
index 1c3c352..fdb0785 100644
--- a/build/makefile_sundials
+++ b/build/makefile_sundials
@@ -239,7 +239,7 @@ SUMMA_DRIVER= \
 		summaActors_type.f90 \
 		summaActors_util.f90 \
 		summaActors_globalData.f90 \
-		summaActors_init.f90 \
+		init_hru_actor.f90 \
 		SummaActors_setup.f90 \
 		summaActors_restart.f90 \
 		summaActors_forcing.f90 \
diff --git a/build/source/actors/global/cppwrap_datatypes.f90 b/build/source/actors/global/cppwrap_datatypes.f90
index b53ad96..418b6f4 100644
--- a/build/source/actors/global/cppwrap_datatypes.f90
+++ b/build/source/actors/global/cppwrap_datatypes.f90
@@ -1057,6 +1057,15 @@ subroutine delete_handle_file_info(handle) bind(C, name='delete_handle_file_info
 end subroutine delete_handle_file_info
 ! ***************************** file_info ***************************
     
+
+! ****************************** z_lookup ****************************
+function new_handle_z_lookup() result(handle) bind(C, name="new_handle_z_lookup")
+  type(c_ptr)           :: handle
+  type(zLookup), pointer :: p
+
+  allocate(p)
+  handle = c_loc(p)
+end function
 end module cppwrap_datatypes
 
 
diff --git a/build/source/actors/hru_actor/hru_actor.cpp b/build/source/actors/hru_actor/hru_actor.cpp
index 2258720..0a62507 100644
--- a/build/source/actors/hru_actor/hru_actor.cpp
+++ b/build/source/actors/hru_actor/hru_actor.cpp
@@ -152,8 +152,9 @@ behavior hru_actor(stateful_actor<hru_state>* self, int refGRU, int indxGRU,
 void Initialize_HRU(stateful_actor<hru_state>* self) {
     self->state.hru_timing.updateStartPoint("init_duration");
     
-    summaActors_initialize(&self->state.indxGRU,
+    initHRU(&self->state.indxGRU,
             &self->state.num_steps, 
+            self->state.handle_lookupStruct,
             self->state.handle_forcStat, 
             self->state.handle_progStat, 
             self->state.handle_diagStat, 
diff --git a/build/source/driver/summaActors_init.f90 b/build/source/driver/init_hru_actor.f90
similarity index 95%
rename from build/source/driver/summaActors_init.f90
rename to build/source/driver/init_hru_actor.f90
index c95de9d..961c385 100755
--- a/build/source/driver/summaActors_init.f90
+++ b/build/source/driver/init_hru_actor.f90
@@ -1,4 +1,4 @@
-module summaActors_init
+module INIT_HRU_ACTOR
 ! used to declare and allocate summa data structures and initialize model state to known values
 USE,intrinsic :: iso_c_binding
 USE nrtype          ! variable types, etc.
@@ -8,7 +8,8 @@ USE data_types,only:&
                     var_i8,              & ! x%var(:)            (i8b)
                     var_d,               & ! x%var(:)            (dp)
                     var_ilength,         & ! x%var(:)%dat        (i4b)
-                    var_dlength            ! x%var(:)%dat        (dp)
+                    var_dlength,         & ! x%var(:)%dat        (dp)
+                    zLookup               ! x%z(:)%var(:)%lookup(:) -- lookup tables
                     
 ! access missing values
 USE globalData,only:integerMissing   ! missing integer
@@ -21,6 +22,8 @@ USE globalData,only:prog_meta,diag_meta,flux_meta,id_meta   ! metadata structure
 USE globalData,only:mpar_meta,indx_meta                     ! metadata structures
 USE globalData,only:bpar_meta,bvar_meta                     ! metadata structures
 USE globalData,only:averageFlux_meta                        ! metadata for time-step average fluxes
+USE globalData,only:lookup_meta 
+
 ! statistics metadata structures
 USE globalData,only:statForc_meta                           ! child metadata for stats
 USE globalData,only:statProg_meta                           ! child metadata for stats
@@ -34,13 +37,14 @@ USE var_lookup,only:maxVarFreq                               ! # of available ou
 ! safety: set private unless specified otherwise
 implicit none
 private
-public::summaActors_initialize
+public::initHRU
 contains
 
  ! used to declare and allocate summa data structures and initialize model state to known values
- subroutine summaActors_initialize(&
+ subroutine initHRU(&
                         indxGRU,            & !  Index of HRU's GRU parent
                         num_steps,          &
+                        handle_lookupStruct,&
   						          ! statistics structures
                         handle_forcStat,    & !  model forcing data
                         handle_progStat,    & !  model prognostic (state) variables
@@ -71,7 +75,7 @@ contains
                         handle_refTime,     & ! reference time for the model simulation
                         handle_oldTime,     & ! time for the previous model time step
                         ! miscellaneous variables
-                        err) bind(C,name='summaActors_initialize')
+                        err) bind(C,name='initHRU')
   ! ---------------------------------------------------------------------------------------
   ! * desired modules
   ! ---------------------------------------------------------------------------------------
@@ -100,7 +104,9 @@ contains
   ! ---------------------------------------------------------------------------------------
   integer(c_int),intent(in)                  :: indxGRU                    ! indx of the parent GRU
   integer(c_int),intent(out)                 :: num_steps                  ! number of steps in model, local to the HRU                 
-    ! statistics structures
+  
+  type(c_ptr), intent(in), value             :: handle_lookupStruct        ! z(:)%var(:)%lookup(:) -- lookup tables
+  ! statistics structures
   type(c_ptr), intent(in), value             :: handle_forcStat !  model forcing data
   type(c_ptr), intent(in), value             :: handle_progStat !  model prognostic (state) variables
   type(c_ptr), intent(in), value             :: handle_diagStat !  model diagnostic variables
@@ -133,6 +139,7 @@ contains
   ! ---------------------------------------------------------------------------------------
   ! * Fortran Variables For Conversion
   ! ---------------------------------------------------------------------------------------
+  type(zLookup),pointer                      :: lookupStruct               !  z(:)%var(:)%lookup(:) -- lookup tables
   type(var_dlength),pointer                  :: forcStat                   !  model forcing data
   type(var_dlength),pointer                  :: progStat                   !  model prognostic (state) variables
   type(var_dlength),pointer                  :: diagStat                   !  model diagnostic variables
@@ -170,6 +177,7 @@ contains
   ! ---------------------------------------------------------------------------------------
   ! * Convert From C++ to Fortran
   ! ---------------------------------------------------------------------------------------
+  call c_f_pointer(handle_lookupStruct, lookupStruct)
   call c_f_pointer(handle_forcStat,   forcStat)
   call c_f_pointer(handle_progStat,   progStat)
   call c_f_pointer(handle_diagStat,   diagStat)
@@ -252,12 +260,14 @@ contains
     case('flux'); call allocLocal(flux_meta,fluxStruct,nSnow,nSoil,err,cmessage);    ! model fluxes
     case('bpar'); call allocLocal(bpar_meta,bparStruct,nSnow=0,nSoil=0,err=err,message=cmessage);  ! basin-average params 
     case('bvar'); call allocLocal(bvar_meta,bvarStruct,nSnow=0,nSoil=0,err=err,message=cmessage);  ! basin-average variables
+    case('lookup'); call allocLocal(lookup_meta,lookupStruct,err=err,message=cmessage)   ! basin-average variables
     case('deriv'); cycle
     case default; err=20; message='unable to find structure name: '//trim(structInfo(iStruct)%structName)
   end select
   ! check errors
   if(err/=0)then
     message=trim(message)//trim(cmessage)//'[structure =  '//trim(structInfo(iStruct)%structName)//']'
+    print*, message
     return
   endif
   end do  ! looping through data structures
@@ -267,6 +277,7 @@ contains
   call allocLocal(mpar_meta,dparStruct,nSnow,nSoil,err,cmessage);    ! default model parameters
     if(err/=0)then
     message=trim(message)//trim(cmessage)//' [problem allocating dparStruct]'
+    print*, message
     return
   endif
 
@@ -288,6 +299,7 @@ contains
     ! check errors
     if(err/=0)then
       message=trim(message)//trim(cmessage)//'[statistics for =  '//trim(structInfo(iStruct)%structName)//']'
+      print*, message
       return
     endif
   end do ! iStruct
@@ -298,6 +310,6 @@ contains
   ! end association to info in data structures
   end associate
 
- end subroutine summaActors_initialize
+ end subroutine initHRU
 
-end module summaActors_init
+end module INIT_HRU_ACTOR
diff --git a/build/source/driver/summaActors_wOutputStruc.f90 b/build/source/driver/summaActors_wOutputStruc.f90
index 34f78b4..4ad7004 100644
--- a/build/source/driver/summaActors_wOutputStruc.f90
+++ b/build/source/driver/summaActors_wOutputStruc.f90
@@ -168,6 +168,7 @@ subroutine summaActors_writeToOutputStruc(&
   integer(i4b)                             :: nHRU
   integer(i4b)                             :: iFreq             ! index of the output frequency
   integer(i4b)                             :: iGRU              ! Temporary index for GRU        
+  integer(i4b)                             :: iDat
   nGRU = 1
   nHRU = 1
   iGRU = 1
@@ -233,9 +234,10 @@ subroutine summaActors_writeToOutputStruc(&
     outputTimeStep%var(:)=1
   end if  ! if defining a new file
 
-  ! copy finalized stats to output structure
-  outputStructure(1)%finalizeStats(1)%gru(indxGRU)%hru(indxHRU)%tim(outputStep)%dat(:) = finalizeStats%dat(:)
-
+  ! If we do not do this looping we segfault - I am not sure why
+  do iDat=1,size(outputStructure(1)%finalizeStats(1)%gru(indxGRU)%hru(indxHRU)%tim(outputStep)%dat)
+    outputStructure(1)%finalizeStats(1)%gru(indxGRU)%hru(indxHRU)%tim(outputStep)%dat(iDat) = finalizeStats%dat(iDat)
+  end do
  ! ****************************************************************************
  ! *** calculate output statistics
  ! ****************************************************************************
diff --git a/build/source/dshare/get_ixname.f90 b/build/source/dshare/get_ixname.f90
index fbf9c4e..a7866a4 100755
--- a/build/source/dshare/get_ixname.f90
+++ b/build/source/dshare/get_ixname.f90
@@ -997,6 +997,7 @@ contains
    case ('bpar' ); vDex = get_ixBpar(trim(varName))
    case ('bvar' ); vDex = get_ixBvar(trim(varName))
    case ('deriv'); vDex = get_ixDeriv(trim(varName))
+   case ('lookup'); vDex = get_ixLookup(trim(varName))
   end select
   if (vDex>0) then; typeName=trim(structInfo(iStruc)%structName); return; end if
  end do
@@ -1006,6 +1007,26 @@ contains
 
  end subroutine get_ixUnknown
 
+! *******************************************************************************************************************
+! public function get_ixfreq: get the index of the named variables for the output frequencies
+! *******************************************************************************************************************
+function get_ixLookup(varName)
+  USE var_lookup,only:iLookLOOKUP                     ! indices of the named variables
+  implicit none
+  ! define dummy variables
+  character(*), intent(in) :: varName                 ! variable name
+  integer(i4b)             :: get_ixLookup            ! index of the named variable
+  ! get the index of the named variables
+  select case(trim(varName))
+    case('temperature'); get_ixLookup = iLookLOOKUP%temperature     ! temperature (K)
+    case('enthalpy'   ); get_ixLookup = iLookLOOKUP%enthalpy        ! enthalpy (J m-3)
+    case('deriv2'     ); get_ixLookup = iLookLOOKUP%deriv2          ! secind derivative of the interpolating function
+    ! get to here if cannot find the variable
+    case default
+      get_ixLookup = integerMissing
+  end select
+  end function get_ixLookup
+
  ! *******************************************************************************************************************
  ! public function get_ixfreq: get the index of the named variables for the output frequencies
  ! *******************************************************************************************************************
diff --git a/build/source/dshare/globalData.f90 b/build/source/dshare/globalData.f90
index b1dc1ee..205788e 100755
--- a/build/source/dshare/globalData.f90
+++ b/build/source/dshare/globalData.f90
@@ -60,6 +60,7 @@ MODULE globalData
   USE var_lookup,only:maxvarBpar      ! basin-average parameters: maximum number variables
   USE var_lookup,only:maxvarDecisions ! maximum number of decisions
   USE var_lookup,only:maxvarFreq      ! maximum number of output files
+  USE var_lookup,only:maxvarLookup
   implicit none
   private
 
@@ -148,7 +149,7 @@ MODULE globalData
   real(rkind),parameter,public                :: dx = 1.e-8_dp           ! finite difference increment
 
   ! define summary information on all data structures
-  integer(i4b),parameter                      :: nStruct=13              ! number of data structures
+  integer(i4b),parameter                      :: nStruct=14              ! number of data structures
   type(struct_info),parameter,public,dimension(nStruct) :: structInfo=(/&
                    struct_info('time',  'TIME' , maxvarTime ), &        ! the time data structure
                    struct_info('forc',  'FORCE', maxvarForc ), &        ! the forcing data structure
@@ -162,8 +163,8 @@ MODULE globalData
                    struct_info('prog',  'PROG',  maxvarProg ), &        ! the prognostic (state) variable data structure
                    struct_info('diag',  'DIAG' , maxvarDiag ), &        ! the diagnostic variable data structure
                    struct_info('flux',  'FLUX' , maxvarFlux ), &        ! the flux data structure
-                   struct_info('deriv', 'DERIV', maxvarDeriv) /)        ! the model derivative data structure
-
+                   struct_info('deriv', 'DERIV', maxvarDeriv), &        ! the model derivative data structure
+                   struct_info('lookup', 'LOOKUP',maxvarLookup) /)
   ! fixed model decisions
   logical(lgt)          , parameter, public   :: overwriteRSMIN=.false.  ! flag to overwrite RSMIN
   integer(i4b)          , parameter, public   :: maxSoilLayers=10000     ! Maximum Number of Soil Layers
@@ -191,6 +192,7 @@ MODULE globalData
   type(var_info),save,public                  :: diag_meta(maxvarDiag)        ! local diagnostic variables for each HRU
   type(var_info),save,public                  :: flux_meta(maxvarFlux)        ! local model fluxes for each HRU
   type(var_info),save,public                  :: deriv_meta(maxvarDeriv)      ! local model derivatives for each HRU
+  type(var_info),save,public                  :: lookup_meta(maxvarLookup)    ! local lookup tables for each HRU
   type(var_info),save,public                  :: bpar_meta(maxvarBpar)        ! basin parameters for aggregated processes
   type(var_info),save,public                  :: bvar_meta(maxvarBvar)        ! basin variables for aggregated processes
 
diff --git a/build/source/dshare/popMetadat.f90 b/build/source/dshare/popMetadat.f90
index 4c2b371..3ec9511 100755
--- a/build/source/dshare/popMetadat.f90
+++ b/build/source/dshare/popMetadat.f90
@@ -31,6 +31,7 @@ subroutine popMetadat(err,message)
   USE globalData, only: diag_meta       ! data structure for local diagnostic variables
   USE globalData, only: flux_meta       ! data structure for local flux variables
   USE globalData, only: deriv_meta      ! data structure for local flux derivatives
+  USE globalData, only: lookup_meta     ! data structure for lookup tables
   ! structures of named variables
   USE var_lookup, only: iLookTIME  ! named variables for time data structure
   USE var_lookup, only: iLookFORCE ! named variables for forcing data structure
@@ -45,6 +46,7 @@ subroutine popMetadat(err,message)
   USE var_lookup, only: iLookDIAG  ! named variables for local diagnostic variables
   USE var_lookup, only: iLookFLUX  ! named variables for local flux variables
   USE var_lookup, only: iLookDERIV ! named variables for local flux derivatives
+  USE var_lookup, only: iLookLOOKUP ! named variables for lookup tables
   USE var_lookup, only: maxvarFreq ! number of output frequencies
   USE var_lookup, only: maxvarStat ! number of statistics
   USE get_ixName_module,only:get_ixVarType ! to turn vartype strings to integers
@@ -595,6 +597,15 @@ subroutine popMetadat(err,message)
   bvar_meta(iLookBVAR%averageInstantRunoff)    = var_info('averageInstantRunoff'   , 'instantaneous runoff'                                   , 'm s-1' , get_ixVarType('scalarv'), iMissVec, iMissVec, .false.)
   bvar_meta(iLookBVAR%averageRoutedRunoff)     = var_info('averageRoutedRunoff'    , 'routed runoff'                                          , 'm s-1' , get_ixVarType('scalarv'), iMissVec, iMissVec, .false.)
 
+  ! -----
+  ! * lookup tables...
+  ! ------------------
+
+  ! temperature and enthalpy
+  lookup_meta(iLookLOOKUP%temperature)        = var_info('temperature'          , 'value of temperature in the lookup table'                  , 'K'     , get_ixVarType('unknown'), iMissVec, iMissVec, .false.)
+  lookup_meta(iLookLOOKUP%enthalpy)           = var_info('enthalpy'             , 'value of enthalpy in the lookup table'                     , 'J m-3' , get_ixVarType('unknown'), iMissVec, iMissVec, .false.)
+  lookup_meta(iLookLOOKUP%deriv2)             = var_info('deriv2'               , 'second derivatives of the interpolating function'          , 'mixed' , get_ixVarType('unknown'), iMissVec, iMissVec, .false.)
+
   ! -----
   ! * model indices...
   ! ------------------
diff --git a/build/source/dshare/var_lookup.f90 b/build/source/dshare/var_lookup.f90
index 9ae9d71..f165761 100755
--- a/build/source/dshare/var_lookup.f90
+++ b/build/source/dshare/var_lookup.f90
@@ -758,6 +758,17 @@ MODULE var_lookup
   integer(i4b)    :: timestep = integerMissing ! timestep-level output (no temporal aggregation)
  endtype iLook_freq
 
+ ! ***********************************************************************************************************
+ ! (16) structure for looking up lookup tables
+ ! ***********************************************************************************************************
+ type, public :: iLook_vLookup
+  integer(i4b)    :: temperature = integerMissing ! temperature (K)
+  integer(i4b)    :: enthalpy    = integerMissing ! enthalpy (J m-3)
+  integer(i4b)    :: deriv2      = integerMissing ! second derivatives of the interpolating function
+ endtype iLook_vLookup
+
+
+
  ! ***********************************************************************************************************
  ! (X) define data structures and maximum number of variables of each type
  ! ***********************************************************************************************************
@@ -857,6 +868,7 @@ MODULE var_lookup
  ! number of possible output frequencies
  type(iLook_freq),    public,parameter :: iLookFreq     =ilook_freq    (  1,  2,  3,  4)
 
+ type(iLook_vLookup), public,parameter :: iLookLOOKUP   =ilook_vLookup ( 1, 2, 3)
  ! define maximum number of variables of each type
  integer(i4b),parameter,public :: maxvarDecisions = storage_size(iLookDECISIONS)/iLength
  integer(i4b),parameter,public :: maxvarTime      = storage_size(iLookTIME)/iLength
@@ -875,6 +887,7 @@ MODULE var_lookup
  integer(i4b),parameter,public :: maxvarVarType   = storage_size(iLookVarType)/iLength
  integer(i4b),parameter,public :: maxvarStat      = storage_size(iLookStat)/iLength
  integer(i4b),parameter,public :: maxvarFreq      = storage_size(iLookFreq)/iLength
+ integer(i4b),parameter,public :: maxvarLookup    = storage_size(iLookLOOKUP)/iLength
 
  ! ***********************************************************************************************************
  ! (Y) define ancillary look-up structures
diff --git a/build/source/engine/allocspaceActors.f90 b/build/source/engine/allocspaceActors.f90
index f10d43a..fcc3074 100755
--- a/build/source/engine/allocspaceActors.f90
+++ b/build/source/engine/allocspaceActors.f90
@@ -25,6 +25,7 @@ USE nrtype
 
 ! provide access to the derived types to define the data structures
 USE data_types,only:&
+                    zLookup,             &
                     ! final data vectors
                     dlength,             & ! var%dat
                     ilength,             & ! var%dat
@@ -133,6 +134,7 @@ contains
  logical(lgt)                     :: check          ! .true. if the variables are allocated
  integer(i4b)                     :: nVars          ! number of variables in the metadata structure
  integer(i4b)                     :: nLayers        ! total number of layers
+ logical(lgt)                     :: spatial
  character(len=256)               :: cmessage       ! error message of the downwind routine
  ! initialize error control
  err=0; message='allocLocal/'
@@ -168,6 +170,7 @@ contains
   class is (var_flagVec); if(allocated(dataStruct%var))then; check=.true.; else; allocate(dataStruct%var(nVars),stat=err); end if
   class is (var_ilength); if(allocated(dataStruct%var))then; check=.true.; else; allocate(dataStruct%var(nVars),stat=err); end if
   class is (var_dlength); if(allocated(dataStruct%var))then; check=.true.; else; allocate(dataStruct%var(nVars),stat=err); end if
+  class is (zLookup);    spatial=.true.
   class default; err=20; message=trim(message)//'unable to identify derived data type for the variable dimension'; return
  end select
  ! check errors
@@ -179,6 +182,7 @@ contains
   class is (var_flagVec); call allocateDat_flag(metaStruct,nSnow,nSoil,nLayers,dataStruct,err,cmessage)
   class is (var_ilength); call allocateDat_int( metaStruct,nSnow,nSoil,nLayers,dataStruct,err,cmessage)
   class is (var_dlength); call allocateDat_dp(  metaStruct,nSnow,nSoil,nLayers,dataStruct,err,cmessage)
+  class is (zLookup);     spatial=.true.
   class default; err=20; message=trim(message)//'unable to identify derived data type for the data dimension'; return
  end select
 
diff --git a/build/source/engine/checkStruc.f90 b/build/source/engine/checkStruc.f90
index 3d723a3..8d7aa5d 100755
--- a/build/source/engine/checkStruc.f90
+++ b/build/source/engine/checkStruc.f90
@@ -40,11 +40,13 @@ contains
  USE globalData,only:prog_meta,diag_meta,flux_meta,deriv_meta         ! metadata structures
  USE globalData,only:mpar_meta,indx_meta                              ! metadata structures
  USE globalData,only:bpar_meta,bvar_meta                              ! metadata structures
+ USE globalData,only:lookup_meta                                      ! metadata structures
  ! named variables defining strructure elements
  USE var_lookup,only:iLookTIME,iLookFORCE,iLookATTR,iLookTYPE,iLookID ! named variables showing the elements of each data structure
  USE var_lookup,only:iLookPROG,iLookDIAG,iLookFLUX,iLookDERIV         ! named variables showing the elements of each data structure
  USE var_lookup,only:iLookPARAM,iLookINDEX                            ! named variables showing the elements of each data structure
  USE var_lookup,only:iLookBPAR,iLookBVAR                              ! named variables showing the elements of each data structure
+ USE var_lookup,only:iLookLOOKUP                                      ! named variables showing the elements of each data structure
  implicit none
  ! dummy variables
  integer(i4b),intent(out)             :: err         ! error code
@@ -83,6 +85,7 @@ contains
    case('diag');  write(longString,*) iLookDIAG
    case('flux');  write(longString,*) iLookFLUX
    case('deriv'); write(longString,*) iLookDERIV
+   case('lookup'); write(longString,*) iLookLOOKUP
    case default; err=20; message=trim(message)//'unable to identify lookup structure'; return
   end select
   ! check that the length of the lookup structure matches the number of variables in the data structure
@@ -119,6 +122,7 @@ contains
    case('diag');  call checkPopulated(iStruct,diag_meta,err,cmessage)
    case('flux');  call checkPopulated(iStruct,flux_meta,err,cmessage)
    case('deriv'); call checkPopulated(iStruct,deriv_meta,err,cmessage)
+   case('lookup'); call checkPopulated(iStruct,lookup_meta,err,cmessage)
    case default; err=20; message=trim(message)//'unable to identify lookup structure'; return
   end select
   if(err/=0)then; message=trim(message)//trim(cmessage); return; end if  ! (check for errors)
diff --git a/build/source/engine/nrtype.mod b/build/source/engine/nrtype.mod
index 66827afb4ddef1dc3741a7481196b45284785e98..cb753b75bed2441f7d23ae5b89340b7015376d91 100644
GIT binary patch
literal 769
zcmV+c1OEIUiwFP!000006Wy3wZ<{a_fZzQq&YR&Om2ED8x1xkrXe~sPZ0b{#22!D=
zNek(w{rerRO~Ykvw@P6lQO*Ga{%oI{FE2bl@GTb}cH#3Tf*(<m#=9+0u2EPe(Q+S!
zuugUluub;A9;36h$%rJ$@Grik5@dp6%TE9eA1Tn{-6&AtAW1XJx32BL_F?XRalLQu
z$Z-SP4Qh4fdy`5b&h_ldnK;4d#`<al16I5=yX6uep=PJ>sC4X2u4io~o_iBm_+W|j
zH>U>8B}p#tEJY?0C1Y3(96|*e;qpj63B$LotGZLU(hg9yBS-BhJ2RD)svGQ_buwr`
zV}3V?iQt_OIzotHK!{F=F+!-rfKWRj44~iRZHS$h;_W_(w`shRUr?~8_H^#s$0+#c
zJMN7$$ze!&wQ7}j;bQJi0>^W~@_p-e;mvVG7E^m>yHnep+!nn!yaA8;L5G+!7)PBp
zfo|^i10Q+Lvi>h{)T8?-d5F_A-rm2RiL^1n`<Y0S=?_RF6F)6jq`=}i*3<Jc{9LBo
zaT@L3mK=NAmUeW+&cv9lS^YV0OctppOXO6TNo@WnD&+v;i00ax&aWDF-)cw)M%-%E
z&~DWYgTV0o7@uxzR)ngo_0@TISmRnoun0esp<`_{7>pi<rC}J_Qek~4dWNzSr#l_o
z6nuTB_c4qMh7V5&`3qxx6(l;XwZhO;RTUvO`e-mzKMlQ%;264-GT|69hrp|8w24+&
zSY{!7@qr|YyiTHOFZu2yioDI=iUtIR>U0<@symGmB7+!4W!gi5kvM%y_NVM`^(8Z-
zK7T7PfbW0qPC16_sxgkjJ~u1065^zzM!}(R&hAvbFOFyXPx<Z>15s|_Fi`4!5QgJa
z>?bhL%A%ZsURJgY#$~0&z$9(e3WKtYd6n<uS>DW-@vI>Ah@z$x`5sDYl{cZRRfz}6
z`bz*uZCnIElnhcu5md~=iy<H{T>*-swkK4SdR?NT9?UPp>6XcFLzIljJ`?}|GAngq

literal 770
zcmV+d1O5CTiwFP!000001KpTgZ<{a_fZzQq&YR&Om2ECDZ$$~MqO}lFvZ+r|8c2nf
zCM~3!_V0JNHcf!F-71BJL^_8U<IncF`SQZ^1K)PxVH-ZLBlr;|X}sM4<pzai5-oO7
z2&-iK0Gnj@>oGc8S&S%(3jg9uDnTVEHv9z8@R0&7-i-nU4vI3hef!!893N)x7uWmd
z4km8kxIwK>eQ#7LWO6;dnv5pF;Ku&y00UOMG<)O{yU?>+cvU)%CfBnzBhS4FZ0uMe
z-OZ__xumG&lcmU1qGb%ro<rzBBitUzCt>)GeN_)CSDFE;cI2QPWoMSQ)J@6GSu2A9
zH0F1`SP0$<VIqX+2ZU&a7$St;4+y;#LIV9BZ$ccr5^r`%yh-Dw`htQZb;dK_=|Ul;
zQr*l4a4~a7!NhaH_I>+y?#*yM=3{5-xMRm1-4<ime*mw#qkTvf<iU_FpzHfx&*z=9
zZ2WVa^XNWG9^y2OH}`L6B27&2ekO9v^arGYg`Wm2Qeg2M>*;wBelAn)Hf6J~C5OJY
zp&cEtGcjZ<R)5Zq7K_x2C2}gvBi8>Dm9__QKy&SlXIGt8UmMb%5jR>jG+XtNL11ux
zj88W*YeLsn=JLEfsBt4Bn1`Rq(6Tp<7-R>-LP}{YG}eV;W++>6y34^W!B=-?7sIe%
z`0#>|zcAKUL88@KD-1)|brEveMT3F*sqaMu$IzXW=|-P91pb>w>u8B(WfsEcA4s8^
z<HEaBDDpOMD~=E_P^bOaPwh#R5E(>2s?rV$jKk?uvO8sOYc7}-b$MHX;d}RUd&&{q
z)a5V=yPT{rN{Ew=83l*IIlI%%t|*?JJ>@4)3`BW+!$7OgKp4(bahAZqC<}51W?9uT
z7*?er14)XKi-FZxwlFB`nOBKF-sMM$GcHV#P8XAlnpPx!DCt!Kg|bm)ASjzJksP&Q
z9tpF4WF1aWu^N3cgWOpclfX-Nfug8v4*SUru-v<-=zDtrRYN7e0ZKc616~vW0KDU8
A_5c6?

diff --git a/build/source/netcdf/def_output.f90 b/build/source/netcdf/def_output.f90
index 59a6cae..f4859f7 100755
--- a/build/source/netcdf/def_output.f90
+++ b/build/source/netcdf/def_output.f90
@@ -154,7 +154,11 @@ subroutine def_output(handle_ncid,startGRU,nGRU,nHRU,err) bind(C, name='def_outp
   do iFreq=1,maxvarFreq
     if (ncid%var(iFreq)/=integerMissing) then
     call nc_file_close(ncid%var(iFreq),err,cmessage)
-    if(err/=0)then; message=trim(message)//trim(cmessage); return; end if
+    if(err/=0)then
+      message=trim(message)//trim(cmessage)
+      print*, message
+      return
+    end if
     endif
   end do
 
@@ -171,39 +175,58 @@ subroutine def_output(handle_ncid,startGRU,nGRU,nHRU,err) bind(C, name='def_outp
     fstring = get_freqName(iFreq)
     fname   = trim(fileout)//'_'//trim(fstring)//'.nc'
     call ini_create(nGRU,nHRU,gru_struc(1)%hruInfo(1)%nSoil,trim(fname),ncid%var(iFreq),err,cmessage)
-    if(err/=0)then; message=trim(message)//trim(cmessage); return; end if
+    if(err/=0)then
+      message=trim(message)//trim(cmessage)
+      print*, message
+      return
+    end if
 
     ! define model decisions
     do iVar = 1,size(model_decisions)
         if(model_decisions(iVar)%iDecision.ne.integerMissing)then
           call put_attrib(ncid%var(iFreq),model_decisions(iVar)%cOption,model_decisions(iVar)%cDecision,err,cmessage)
-          if(err/=0)then; message=trim(message)//trim(cmessage); return; end if
+          if(err/=0)then
+            message=trim(message)//trim(cmessage)
+            print*, message
+            return
+          end if
         end if
     end do
     
     ! define variables
     do iStruct = 1,size(structInfo)
         select case (trim(structInfo(iStruct)%structName))
-        case('attr' ); call def_variab(ncid%var(iFreq),iFreq,needHRU,  noTime,attr_meta, outputPrecision, err,cmessage)  ! local attributes HRU
-        case('type' ); call def_variab(ncid%var(iFreq),iFreq,needHRU,  noTime,type_meta, nf90_int,   err,cmessage)       ! local classification
-        case('mpar' ); call def_variab(ncid%var(iFreq),iFreq,needHRU,  noTime,mpar_meta, outputPrecision, err,cmessage)  ! model parameters
-        case('bpar' ); call def_variab(ncid%var(iFreq),iFreq,needGRU,  noTime,bpar_meta, outputPrecision, err,cmessage)  ! basin-average param
-        case('indx' ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,indx_meta, nf90_int,   err,cmessage)       ! model variables
-        case('deriv'); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,deriv_meta,outputPrecision, err,cmessage)  ! model derivatives
-        case('time' ); call def_variab(ncid%var(iFreq),iFreq,  noHRU,needTime,time_meta, nf90_int,   err,cmessage)       ! model derivatives
-        case('forc' ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,forc_meta, outputPrecision, err,cmessage)  ! model forcing data
-        case('prog' ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,prog_meta, outputPrecision, err,cmessage)  ! model prognostics
-        case('diag' ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,diag_meta, outputPrecision, err,cmessage)  ! model diagnostic variables
-        case('flux' ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,flux_meta, outputPrecision, err,cmessage)  ! model fluxes
-        case('bvar' ); call def_variab(ncid%var(iFreq),iFreq,needGRU,needTime,bvar_meta, outputPrecision, err,cmessage)  ! basin-average variables
-        case('id'   ); cycle                                                                                         ! ids -- see write_hru_info()
+        case('attr'  ); call def_variab(ncid%var(iFreq),iFreq,needHRU,  noTime,attr_meta, outputPrecision, err,cmessage)  ! local attributes HRU
+        case('type'  ); call def_variab(ncid%var(iFreq),iFreq,needHRU,  noTime,type_meta, nf90_int,   err,cmessage)       ! local classification
+        case('mpar'  ); call def_variab(ncid%var(iFreq),iFreq,needHRU,  noTime,mpar_meta, outputPrecision, err,cmessage)  ! model parameters
+        case('bpar'  ); call def_variab(ncid%var(iFreq),iFreq,needGRU,  noTime,bpar_meta, outputPrecision, err,cmessage)  ! basin-average param
+        case('indx'  ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,indx_meta, nf90_int,   err,cmessage)       ! model variables
+        case('deriv' ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,deriv_meta,outputPrecision, err,cmessage)  ! model derivatives
+        case('time'  ); call def_variab(ncid%var(iFreq),iFreq,  noHRU,needTime,time_meta, nf90_int,   err,cmessage)       ! model derivatives
+        case('forc'  ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,forc_meta, outputPrecision, err,cmessage)  ! model forcing data
+        case('prog'  ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,prog_meta, outputPrecision, err,cmessage)  ! model prognostics
+        case('diag'  ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,diag_meta, outputPrecision, err,cmessage)  ! model diagnostic variables
+        case('flux'  ); call def_variab(ncid%var(iFreq),iFreq,needHRU,needTime,flux_meta, outputPrecision, err,cmessage)  ! model fluxes
+        case('bvar'  ); call def_variab(ncid%var(iFreq),iFreq,needGRU,needTime,bvar_meta, outputPrecision, err,cmessage)  ! basin-average variables
+        case('id'    ); cycle
+        case('lookup'); cycle                                                                                         ! ids -- see write_hru_info()
         case default; err=20; message=trim(message)//'unable to identify lookup structure';
         end select
         ! error handling
-        if(err/=0)then;err=20;message=trim(message)//trim(cmessage)//'[structure =  '//trim(structInfo(iStruct)%structName);return;end if
+        if(err/=0)then
+          err=20
+          message=trim(message)//trim(cmessage)//'[structure =  '//trim(structInfo(iStruct)%structName)
+          print*, message
+          return
+        end if
     end do ! iStruct
     ! write HRU dimension and ID for each output file
-    call write_hru_info(ncid%var(iFreq), err, cmessage); if(err/=0) then; message=trim(message)//trim(cmessage); return; end if
+    call write_hru_info(ncid%var(iFreq), err, cmessage) 
+    if(err/=0) then 
+      message=trim(message)//trim(cmessage)
+      print*, message
+      return
+    end if
 
   end do
 end subroutine def_output
diff --git a/utils/containers/sundials/launch_docker_container.sh b/utils/containers/sundials/launch_docker_container.sh
index 4acc705..5d8de7e 100755
--- a/utils/containers/sundials/launch_docker_container.sh
+++ b/utils/containers/sundials/launch_docker_container.sh
@@ -3,5 +3,5 @@
 export PROJECT_DIR=/Users/kyleklenk/SUMMA-Projects/Summa-Actors
 export NA_TEST=/home/local/kck540/NA_Summa_Test
 export SUMMA=/Users/kyleklenk/SUMMA-Projects/Summa-Sundials/summa
-docker run -d -it --name SUMMA-Sundials --mount type=bind,source=${PROJECT_DIR},target=/Summa-Actors \
+docker run -d -it --ulimit memlock=32768:32768 --name SUMMA-Sundials --mount type=bind,source=${PROJECT_DIR},target=/Summa-Actors \
     --mount type=bind,source=${SUMMA},target=/SUMMA summa-sundials:latest
-- 
GitLab