c Copyright (C) Stichting Deltares, 2005-2014.
c
c This file is part of iMOD.
c
c This program is free software: you can redistribute it and/or modify
c it under the terms of the GNU General Public License as published by
c the Free Software Foundation, either version 3 of the License, or
c (at your option) any later version.
c
c This program is distributed in the hope that it will be useful,
c but WITHOUT ANY WARRANTY; without even the implied warranty of
c MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
c GNU General Public License for more details.
c
c You should have received a copy of the GNU General Public License
c along with this program. If not, see .
c
c Contact: imod.support@deltares.nl
c Stichting Deltares
c P.O. Box 177
c 2600 MH Delft, The Netherlands.
c
c iMod is partly based on the USGS MODFLOW2005 source code;
c for iMOD the USGS MODFLOW2005 source code has been expanded
c and extensively modified by Stichting Deltares.
c The original USGS MODFLOW2005 source code can be downloaded from the USGS
c website http://www.usgs.gov/. The original MODFLOW2005 code incorporated
c in this file is covered by the USGS Software User Rights Notice;
c you should have received a copy of this notice along with this program.
c If not, see .
MODULE GWFRCHMODULE
INTEGER, SAVE, POINTER ::NRCHOP,IRCHCB
INTEGER, SAVE, POINTER ::NPRCH,IRCHPF
INTEGER, SAVE, POINTER ::IADDRECH ! DLT
REAL, SAVE, DIMENSION(:,:), POINTER ::RECH
real, save, dimension(:,:), pointer :: rechbuff => null() ! DLT
INTEGER, SAVE, DIMENSION(:,:), POINTER ::IRCH
TYPE GWFRCHTYPE
INTEGER, POINTER ::NRCHOP,IRCHCB
INTEGER, POINTER ::NPRCH,IRCHPF
INTEGER, POINTER ::IADDRECH ! DLT
REAL, DIMENSION(:,:), POINTER ::RECH
real, dimension(:,:), pointer :: rechbuff => null() ! DLT
INTEGER, DIMENSION(:,:), POINTER ::IRCH
END TYPE
TYPE(GWFRCHTYPE), SAVE ::GWFRCHDAT(10)
END MODULE GWFRCHMODULE
SUBROUTINE GWF2RCH7AR(IN,IGRID)
C ******************************************************************
C ALLOCATE ARRAY STORAGE FOR RECHARGE
C ******************************************************************
C
C SPECIFICATIONS:
C ------------------------------------------------------------------
USE GLOBAL, ONLY:IOUT,NCOL,NROW,IFREFM
USE GWFRCHMODULE,ONLY:NRCHOP,IRCHCB,NPRCH,IRCHPF,RECH,IRCH,
1 IADDRECH ! DLT
C
CHARACTER*200 LINE
CHARACTER*4 PTYP
C ------------------------------------------------------------------
C
C1-------ALLOCATE SCALAR VARIABLES.
ALLOCATE(NRCHOP,IRCHCB)
ALLOCATE(NPRCH,IRCHPF)
ALLOCATE(IADDRECH) ! DLT
C
C2------IDENTIFY PACKAGE.
IRCHPF=0
WRITE(IOUT,1)IN
1 FORMAT(1X,/1X,'RCH -- RECHARGE PACKAGE, VERSION 7, 5/2/2005',
1' INPUT READ FROM UNIT ',I4)
C
C3------READ NRCHOP AND IRCHCB.
CALL URDCOM(IN,IOUT,LINE)
CALL UPARARRAL(IN,IOUT,LINE,NPRCH)
IF(IFREFM.EQ.0) THEN
READ(LINE,'(2I10)') NRCHOP,IRCHCB
ELSE
LLOC=1
CALL URWORD(LINE,LLOC,ISTART,ISTOP,2,NRCHOP,R,IOUT,IN)
CALL URWORD(LINE,LLOC,ISTART,ISTOP,2,IRCHCB,R,IOUT,IN)
END IF
C
LLOC=1
IADDRECH=0 ! DLT
10 CALL URWORD(LINE,LLOC,ISTART,ISTOP,1,I,R,IOUT,IN) ! DLT
IF(LINE(ISTART:ISTOP).EQ.'ADDRECH') THEN ! DLT
IADDRECH=1 ! DLT
ENDIF ! DLT
IF(LLOC.LT.200) GO TO 10 ! DLT
C
C4------CHECK TO SEE THAT OPTION IS LEGAL.
IF(NRCHOP.LT.1.OR.NRCHOP.GT.3) THEN
WRITE(IOUT,8) NRCHOP
8 FORMAT(1X,'ILLEGAL RECHARGE OPTION CODE (NRCHOP = ',I5,
& ') -- SIMULATION ABORTING')
CALL USTOP(' ')
END IF
C
C5------OPTION IS LEGAL -- PRINT OPTION CODE.
IF(NRCHOP.EQ.1) WRITE(IOUT,201)
201 FORMAT(1X,'OPTION 1 -- RECHARGE TO TOP LAYER')
IF(NRCHOP.EQ.2) WRITE(IOUT,202)
202 FORMAT(1X,'OPTION 2 -- RECHARGE TO ONE SPECIFIED NODE IN EACH',
1 ' VERTICAL COLUMN')
IF(NRCHOP.EQ.3) WRITE(IOUT,203)
203 FORMAT(1X,'OPTION 3 -- RECHARGE TO HIGHEST ACTIVE NODE IN',
1 ' EACH VERTICAL COLUMN')
C
C6------IF CELL-BY-CELL FLOWS ARE TO BE SAVED, THEN PRINT UNIT NUMBER.
IF(IRCHCB.GT.0) WRITE(IOUT,204) IRCHCB
204 FORMAT(1X,'CELL-BY-CELL FLOWS WILL BE SAVED ON UNIT ',I4)
C
C7------ALLOCATE SPACE FOR THE RECHARGE (RECH) AND INDICATOR (IRCH)
C7------ARRAYS.
ALLOCATE (RECH(NCOL,NROW))
ALLOCATE (IRCH(NCOL,NROW))
C
C8------READ NAMED PARAMETERS
WRITE(IOUT,5) NPRCH
5 FORMAT(1X,//1X,I5,' Recharge parameters')
IF(NPRCH.GT.0) THEN
DO 20 K=1,NPRCH
CALL UPARARRRP(IN,IOUT,N,0,PTYP,1,1,0)
IF(PTYP.NE.'RCH') THEN
WRITE(IOUT,7)
7 FORMAT(1X,'Parameter type must be RCH')
CALL USTOP(' ')
END IF
20 CONTINUE
END IF
C
C9------RETURN
CALL SGWF2RCH7PSV(IGRID)
RETURN
END
SUBROUTINE GWF2RCH7RP(IN,IGRID)
C ******************************************************************
C READ RECHARGE DATA FOR STRESS PERIOD
C ******************************************************************
C
C SPECIFICATIONS:
C ------------------------------------------------------------------
USE GLOBAL, ONLY:IOUT,NCOL,NROW,NLAY,IFREFM,DELR,DELC,
1 BUFF ! DLT
USE GWFRCHMODULE,ONLY:NRCHOP,NPRCH,IRCHPF,RECH,IRCH,
1 IADDRECH, ! DLT
1 rechbuff ! DLT
use rdrsmodule, only: nodata ! DLT
C
CHARACTER*24 ANAME(2)
C
DATA ANAME(1) /' RECHARGE LAYER INDEX'/
DATA ANAME(2) /' RECHARGE'/
C
INTEGER :: IL,IR,IC ! DLT
C ------------------------------------------------------------------
C
C1------SET POINTERS FOR THE CURRENT GRID.
CALL SGWF2RCH7PNT(IGRID)
C
C2------READ FLAGS SHOWING WHETHER DATA IS TO BE REUSED.
IF(NRCHOP.EQ.2) THEN
IF(IFREFM.EQ.0) THEN
READ(IN,'(2I10)') INRECH,INIRCH
ELSE
READ(IN,*) INRECH,INIRCH
END IF
ELSE
IF(IFREFM.EQ.0) THEN
READ(IN,'(I10)') INRECH
ELSE
READ(IN,*) INRECH
END IF
END IF
C
C3------TEST INRECH TO SEE HOW TO DEFINE RECH.
IF(INRECH.LT.0) THEN
C
C3A-----INRECH<0, SO REUSE RECHARGE ARRAY FROM LAST STRESS PERIOD.
call sts2nodata(in) ! STS
WRITE(IOUT,3)
3 FORMAT(1X,/1X,'REUSING RECH FROM LAST STRESS PERIOD')
ELSE
C
C3B-----INRECH=>0, SO READ RECHARGE RATE.
call sts2data(in) ! STS
IF(NPRCH.EQ.0) THEN
C
C3B1----THERE ARE NO PARAMETERS, SO READ RECH USING U2DREL.
nodata = 0. ! DLT
CALL U2DREL(RECH,ANAME(2),NROW,NCOL,0,IN,IOUT)
IF (IADDRECH.EQ.1) THEN ! DLT
DO I = 2, INRECH ! DLT
CALL U2DREL(BUFF(1,1,1),ANAME(2),NROW,NCOL,0,IN,IOUT) ! DLT
DO IC=1,NCOL ! DLT
DO IR=1,NROW ! DLT
RECH(IC,IR)=RECH(IC,IR)+BUFF(IC,IR,1) ! DLT
END DO ! DLT
END DO ! DLT
END DO ! DLT
END IF ! DLT
nodata = -9999. ! DLT
ELSE
C
C3B2----DEFINE RECH USING PARAMETERS. INRECH IS THE NUMBER OF
C3B2----PARAMETERS TO USE THIS STRESS PERIOD.
CALL PRESET('RCH')
WRITE(IOUT,33)
33 FORMAT(1X,///1X,
1 'RECH array defined by the following parameters:')
IF(INRECH.EQ.0) THEN
WRITE(IOUT,34)
34 FORMAT(' ERROR: When parameters are defined for the RCH',
& ' Package, at least one parameter',/,' must be specified',
& ' each stress period -- STOP EXECUTION (GWF2RCH7RPLL)')
CALL USTOP(' ')
END IF
CALL UPARARRSUB2(RECH,NCOL,NROW,0,INRECH,IN,IOUT,'RCH',
1 ANAME(2),'RCH',IRCHPF)
END IF
C
C4------MULTIPLY RECHARGE RATE BY CELL AREA TO GET VOLUMETRIC RATE.
DO 50 IR=1,NROW
DO 50 IC=1,NCOL
RECH(IC,IR)=RECH(IC,IR)*DELR(IC)*DELC(IR)
50 CONTINUE
END IF
C
! overrule rech with buffer
if (associated(rechbuff))then
rech = rechbuff
end if
C5------IF NRCHOP=2 THEN A LAYER INDICATOR ARRAY IS NEEDED. TEST INIRCH
C5------TO SEE HOW TO DEFINE IRCH.
IF(NRCHOP.EQ.2) THEN
IF(INIRCH.LT.0) THEN
C
C5A-----INIRCH<0, SO REUSE LAYER INDICATOR ARRAY FROM LAST STRESS PERIOD.
call sts2nodata(in) ! STS
WRITE(IOUT,2)
2 FORMAT(1X,/1X,'REUSING IRCH FROM LAST STRESS PERIOD')
ELSE
C
C5B-----INIRCH=>0, SO CALL U2DINT TO READ LAYER INDICATOR ARRAY(IRCH)
call sts2data(in) ! STS
CALL U2DINT(IRCH,ANAME(1),NROW,NCOL,0,IN,IOUT)
DO 57 IR=1,NROW
DO 57 IC=1,NCOL
IF(IRCH(IC,IR).LT.1 .OR. IRCH(IC,IR).GT.NLAY) THEN
WRITE(IOUT,56) IC,IR,IRCH(IC,IR)
56 FORMAT(1X,/1X,'INVALID LAYER NUMBER IN IRCH FOR COLUMN',I4,
1 ' ROW',I4,' :',I4)
CALL USTOP(' ')
END IF
57 CONTINUE
END IF
END IF
C
C6------RETURN
RETURN
END
SUBROUTINE GWF2RCH7FM(IGRID)
C ******************************************************************
C SUBTRACT RECHARGE FROM RHS
C ******************************************************************
C
C SPECIFICATIONS:
C ------------------------------------------------------------------
USE GLOBAL, ONLY:NCOL,NROW,NLAY,IBOUND,RHS
USE GWFRCHMODULE,ONLY:NRCHOP,RECH,IRCH
C ------------------------------------------------------------------
C
C1------SET POINTERS FOR THE CURRENT GRID.
CALL SGWF2RCH7PNT(IGRID)
C
C2------DETERMINE WHICH RECHARGE OPTION.
IF(NRCHOP.EQ.1) THEN
C
C3------NRCHOP IS 1, SO RECHARGE IS IN TOP LAYER. LAYER INDEX IS 1.
DO 10 IR=1,NROW
DO 10 IC=1,NCOL
C
C3A-----IF CELL IS VARIABLE HEAD, SUBTRACT RECHARGE RATE FROM
C3A-----RIGHT-HAND-SIDE.
IF(IBOUND(IC,IR,1).GT.0) RHS(IC,IR,1)=RHS(IC,IR,1)-RECH(IC,IR)
10 CONTINUE
ELSE IF(NRCHOP.EQ.2) THEN
C
C4------NRCHOP IS 2, SO RECHARGE IS INTO LAYER IN INDICATOR ARRAY
DO 20 IR=1,NROW
DO 20 IC=1,NCOL
IL=IRCH(IC,IR)
C
C4A-----IF THE CELL IS VARIABLE HEAD, SUBTRACT RECHARGE FROM
C4A-----RIGHT-HAND-SIDE.
IF(IL.EQ.0) GO TO 20
IF(IBOUND(IC,IR,IL).GT.0)
1 RHS(IC,IR,IL)=RHS(IC,IR,IL)-RECH(IC,IR)
20 CONTINUE
ELSE
C
C5------NRCHOP IS 3, RECHARGE IS INTO HIGHEST VARIABLE-HEAD CELL, EXCEPT
C5------CANNOT PASS THROUGH CONSTANT HEAD NODE
DO 30 IR=1,NROW
DO 30 IC=1,NCOL
DO 28 IL=1,NLAY
C
C5A-----IF CELL IS CONSTANT HEAD MOVE ON TO NEXT HORIZONTAL LOCATION.
IF(IBOUND(IC,IR,IL).LT.0) GO TO 30
C
C5B-----IF THE CELL IS VARIABLE HEAD, SUBTRACT RECHARGE FROM
C5B-----RIGHT-HAND-SIDE AND MOVE TO NEXT HORIZONTAL LOCATION.
IF(IBOUND(IC,IR,IL).GT.0) THEN
RHS(IC,IR,IL)=RHS(IC,IR,IL)-RECH(IC,IR)
GO TO 30
END IF
28 CONTINUE
30 CONTINUE
END IF
C
C6------RETURN
RETURN
END
SUBROUTINE GWF2RCH7BD(KSTP,KPER,IGRID)
C ******************************************************************
C CALCULATE VOLUMETRIC BUDGET FOR RECHARGE
C ******************************************************************
C
C SPECIFICATIONS:
C ------------------------------------------------------------------
USE GLOBAL, ONLY:IOUT,NCOL,NROW,NLAY,IBOUND,BUFF
USE GWFBASMODULE,ONLY:MSUM,VBVL,VBNM,ICBCFL,DELT,PERTIM,TOTIM
USE GWFRCHMODULE,ONLY:NRCHOP,IRCHCB,RECH,IRCH
C
DOUBLE PRECISION RATIN,RATOUT,QQ
CHARACTER*16 TEXT
DATA TEXT /' RECHARGE'/
C ------------------------------------------------------------------
C
C1------SET POINTERS FOR THE CURRENT GRID.
CALL SGWF2RCH7PNT(IGRID)
C
C2------CLEAR THE RATE ACCUMULATORS.
ZERO=0.
RATIN=ZERO
RATOUT=ZERO
C
C3------CLEAR THE BUFFER & SET FLAG FOR SAVING CELL-BY-CELL FLOW TERMS.
DO 2 IL=1,NLAY
DO 2 IR=1,NROW
DO 2 IC=1,NCOL
BUFF(IC,IR,IL)=ZERO
2 CONTINUE
IBD=0
IF(IRCHCB.GT.0) IBD=ICBCFL
C
C4------DETERMINE THE RECHARGE OPTION.
IF(NRCHOP.EQ.1) THEN
C
C5------NRCHOP=1, SO RECH GOES INTO LAYER 1. PROCESS EACH HORIZONTAL
C5------CELL LOCATION.
DO 10 IR=1,NROW
DO 10 IC=1,NCOL
C
C5A-----IF CELL IS VARIABLE HEAD, THEN DO BUDGET FOR IT.
IF(IBOUND(IC,IR,1).GT.0) THEN
Q=RECH(IC,IR)
QQ=Q
C
C5B-----ADD RECH TO BUFF.
BUFF(IC,IR,1)=Q
C
C5C-----IF RECH POSITIVE ADD IT TO RATIN, ELSE ADD IT TO RATOUT.
IF(Q.GE.ZERO) THEN
RATIN=RATIN+QQ
ELSE
RATOUT=RATOUT-QQ
END IF
END IF
10 CONTINUE
ELSE IF(NRCHOP.EQ.2) THEN
C
C6------NRCHOP=2, RECH IS IN LAYER SPECIFIED IN INDICATOR ARRAY(IRCH).
C6------PROCESS EACH HORIZONTAL CELL LOCATION.
DO 20 IR=1,NROW
DO 20 IC=1,NCOL
C
C6A-----GET LAYER INDEX FROM INDICATOR ARRAY(IRCH).
IL=IRCH(IC,IR)
C
C6B-----IF CELL IS VARIABLE HEAD, THEN DO BUDGET FOR IT.
IF(IL.EQ.0) GO TO 20
IF(IBOUND(IC,IR,IL).GT.0) THEN
Q=RECH(IC,IR)
QQ=Q
C
C6C-----ADD RECHARGE TO BUFF.
BUFF(IC,IR,IL)=Q
C
C6D-----IF RECHARGE IS POSITIVE ADD TO RATIN, ELSE ADD IT TO RATOUT.
IF(Q.GE.ZERO) THEN
RATIN=RATIN+QQ
ELSE
RATOUT=RATOUT-QQ
END IF
END IF
20 CONTINUE
ELSE
C
C7------NRCHOP=3; RECHARGE IS INTO HIGHEST CELL IN A VERTICAL COLUMN
C7------THAT IS NOT NO FLOW. PROCESS EACH HORIZONTAL CELL LOCATION.
DO 30 IR=1,NROW
DO 29 IC=1,NCOL
C
C7A-----INITIALIZE IRCH TO 1, AND LOOP THROUGH CELLS IN A VERTICAL
C7A-----COLUMN TO FIND WHERE TO PLACE RECHARGE.
IRCH(IC,IR)=1
DO 28 IL=1,NLAY
C
C7B-----IF CELL IS CONSTANT HEAD, MOVE ON TO NEXT HORIZONTAL LOCATION.
IF(IBOUND(IC,IR,IL).LT.0) GO TO 29
C
C7C-----IF CELL IS VARIABLE HEAD, THEN DO BUDGET FOR IT.
IF (IBOUND(IC,IR,IL).GT.0) THEN
Q=RECH(IC,IR)
QQ=Q
C
C7D-----ADD RECHARGE TO BUFFER, AND STORE LAYER NUMBER IN IRCH.
BUFF(IC,IR,IL)=Q
IRCH(IC,IR)=IL
C
C7E-----IF RECH IS POSITIVE ADD IT TO RATIN, ELSE ADD IT TO RATOUT.
IF(Q.GE.ZERO) THEN
RATIN=RATIN+QQ
ELSE
RATOUT=RATOUT-QQ
END IF
GO TO 29
END IF
28 CONTINUE
29 CONTINUE
30 CONTINUE
C
END IF
C
C8------IF CELL-BY-CELL FLOW TERMS SHOULD BE SAVED, CALL APPROPRIATE
C8------UTILITY MODULE TO WRITE THEM.
100 IF(IBD.EQ.1) CALL UBUDSV(KSTP,KPER,TEXT,IRCHCB,BUFF,NCOL,NROW,
1 NLAY,IOUT)
IF(IBD.EQ.2) CALL UBDSV3(KSTP,KPER,TEXT,IRCHCB,BUFF,IRCH,NRCHOP,
1 NCOL,NROW,NLAY,IOUT,DELT,PERTIM,TOTIM,IBOUND)
C
C9------MOVE TOTAL RECHARGE RATE INTO VBVL FOR PRINTING BY BAS1OT.
ROUT=RATOUT
RIN=RATIN
VBVL(4,MSUM)=ROUT
VBVL(3,MSUM)=RIN
C
C10-----ADD RECHARGE FOR TIME STEP TO RECHARGE ACCUMULATOR IN VBVL.
VBVL(2,MSUM)=VBVL(2,MSUM)+ROUT*DELT
VBVL(1,MSUM)=VBVL(1,MSUM)+RIN*DELT
C
C11-----MOVE BUDGET TERM LABELS TO VBNM FOR PRINT BY MODULE BAS_OT.
VBNM(MSUM)=TEXT
C
C12-----INCREMENT BUDGET TERM COUNTER.
MSUM=MSUM+1
C
C13-----RETURN
RETURN
END
SUBROUTINE GWF2RCH7DA(IGRID)
C Deallocate RCH DATA
USE GWFRCHMODULE
C
DEALLOCATE(GWFRCHDAT(IGRID)%NRCHOP)
DEALLOCATE(GWFRCHDAT(IGRID)%IRCHCB)
DEALLOCATE(GWFRCHDAT(IGRID)%NPRCH)
DEALLOCATE(GWFRCHDAT(IGRID)%IRCHPF)
DEALLOCATE(GWFRCHDAT(IGRID)%RECH)
if(associated(gwfrchdat(igrid)%rechbuff)) ! DLT
1 deallocate(gwfrchdat(igrid)%rechbuff) ! DLT
DEALLOCATE(GWFRCHDAT(IGRID)%IRCH)
DEALLOCATE(GWFRCHDAT(IGRID)%IADDRECH) ! DLT
C
RETURN
END
SUBROUTINE SGWF2RCH7PNT(IGRID)
C Set RCH pointers for grid.
USE GWFRCHMODULE
C
NRCHOP=>GWFRCHDAT(IGRID)%NRCHOP
IRCHCB=>GWFRCHDAT(IGRID)%IRCHCB
NPRCH=>GWFRCHDAT(IGRID)%NPRCH
IRCHPF=>GWFRCHDAT(IGRID)%IRCHPF
RECH=>GWFRCHDAT(IGRID)%RECH
RECHBUFF=>GWFRCHDAT(IGRID)%RECHBUFF ! DLT
IRCH=>GWFRCHDAT(IGRID)%IRCH
IADDRECH=>GWFRCHDAT(IGRID)%IADDRECH ! DLT
C
RETURN
END
SUBROUTINE SGWF2RCH7PSV(IGRID)
C Save RCH pointers for grid.
USE GWFRCHMODULE
C
GWFRCHDAT(IGRID)%NRCHOP=>NRCHOP
GWFRCHDAT(IGRID)%IRCHCB=>IRCHCB
GWFRCHDAT(IGRID)%NPRCH=>NPRCH
GWFRCHDAT(IGRID)%IRCHPF=>IRCHPF
GWFRCHDAT(IGRID)%RECH=>RECH
GWFRCHDAT(IGRID)%RECHBUFF=>RECHBUFF ! DLT
GWFRCHDAT(IGRID)%IRCH=>IRCH
GWFRCHDAT(IGRID)%IADDRECH=>IADDRECH ! DLT
C
RETURN
END