source: palm/trunk/UTIL/chemistry/gasphase_preproc/kpp/int.modified_WCOPY/kpp_dvode.f @ 4901

Last change on this file since 4901 was 2696, checked in by kanani, 6 years ago

Merge of branch palm4u into trunk

File size: 160.4 KB
Line 
1      SUBROUTINE INTEGRATE( TIN, TOUT )
2
3      IMPLICIT KPP_REAL (A-H,O-Z)
4      INCLUDE 'KPP_ROOT_Parameters.h'
5      INCLUDE 'KPP_ROOT_Global.h'
6
7C TIN - Start Time
8      KPP_REAL TIN
9C TOUT - End Time
10      KPP_REAL TOUT
11
12      PARAMETER (LRW=2*NVAR*NVAR+9*NVAR+25,LIW=NVAR+35)
13      PARAMETER (LRCONT=4*NVAR+4+10)
14      COMMON /CONT/ICONT(4),RCONT(LRCONT)
15      COMMON/STAT/NFCN,NJAC,NSTEP,NACCPT,NREJCT,NDEC,NSOL
16      COMMON /VERWER/ IVERWER, IBEGIN, STEPCUT
17      EXTERNAL VODE_FSPLIT_VAR, VODE_Jac_SP
18
19      KPP_REAL RWORK(LRW)
20      INTEGER IWORK(LIW)
21
22      STEPCUT = 0.
23      MAXORD = 5
24      IBEGIN = 1
25      ITOL=4
26
27C ---- NORMAL COMPUTATION ---
28      ITASK=1
29      ISTATE=1
30C ---- USE OPTIONAL INPUT ---
31      IOPT=1
32      IWORK(5) = MAXORD    ! MAX ORD
33      IWORK(6) = 20000
34      IWORK(7) = 0
35      RWORK(6) = STEPMAX   ! STEP MAX
36      RWORK(7) = STEPMIN   ! STEP MIN
37      RWORK(5) = STEPMIN   ! INITIAL STEP
38
39C ----- SIGNAL FOR STIFF CASE, FULL JACOBIAN, INTERN (22) or SUPPLIED (21)
40      MF = 21
41
42      CALL DVODE (VODE_FSPLIT_VAR, NVAR, VAR, TIN, TOUT, ITOL,
43     *            RTOL, ATOL, ITASK,
44     *            ISTATE, IOPT, RWORK, LRW, IWORK, LIW,
45     *            VODE_Jac_SP, MF, RPAR, IPAR)
46
47      IF (ISTATE.LT.0) THEN
48        print *,'ATMDVODE: Unsucessfull exit at T=',
49     &          TIN,' (ISTATE=',ISTATE,')'
50      ENDIF
51
52      RETURN
53      END
54
55
56C -- This version has JAC sparse, FCN aggregate --
57
58      SUBROUTINE DVODE (F, NEQ, Y, T, TOUT, ITOL, RelTol, AbsTol, ITASK,
59     1            ISTATE, IOPT, RWORK, LRW, IWORK, LIW, JAC, MF,
60     2            RPAR, IPAR)
61
62      KPP_REAL Y, T, TOUT, RelTol, AbsTol, RWORK, RPAR
63      INTEGER NEQ, ITOL, ITASK, ISTATE, IOPT, LRW, IWORK, LIW,
64     1        MF, IPAR
65      DIMENSION Y(*), RelTol(*), AbsTol(*), RWORK(LRW), IWORK(LIW),
66     1          RPAR(*), IPAR(*)
67C-----------------------------------------------------------------------
68C DVODE.. Variable-coefficient Ordinary Differential Equation solver,
69C with fixed-leading coefficient implementation.
70C This version is in KPP_REAL.
71C
72C DVODE solves the initial value problem for stiff or nonstiff
73C systems of first order ODEs,
74C     dy/dt = f(t,y) ,  or, in component form,
75C     dy(i)/dt = f(i) = f(i,t,y(1),y(2),...,y(NEQ)) (i = 1,...,NEQ).
76C DVODE is a package based on the EPISODE and EPISODEB packages, and
77C on the ODEPACK user interface standard, with minor modifications.
78C-----------------------------------------------------------------------
79C Revision History (YYMMDD)
80C   890615  Date Written
81C   890922  Added interrupt/restart ability, minor changes throughout.
82C   910228  Minor revisions in line format,  prologue, etc.
83C   920227  Modifications by D. Pang:
84C           (1) Applied subgennam to get generic intrinsic names.
85C           (2) Changed intrinsic names to generic in comments.
86C           (3) Added *DECK lines before each routine.
87C   920721  Names of routines and labeled Common blocks changed, so as
88C           to be unique in combined single/KPP_REAL code (ACH).
89C   920722  Minor revisions to prologue (ACH).
90C   920831  Conversion to KPP_REAL done (ACH).
91C-----------------------------------------------------------------------
92C References..
93C
94C 1. P. N. Brown, G. D. Byrne, and A. C. Hindmarsh, "VODE: A Variable
95C    Coefficient ODE Solver," SIAM J. Sci. Stat. Comput., 10 (1989),
96C    pp. 1038-1051.  Also, LLNL Report UCRL-98412, June 1988.
97C 2. G. D. Byrne and A. C. Hindmarsh, "A Polyalgorithm for the
98C    Numerical Solution of Ordinary Differential Equations,"
99C    ACM Trans. Math. Software, 1 (1975), pp. 71-96.
100C 3. A. C. Hindmarsh and G. D. Byrne, "EPISODE: An Effective Package
101C    for the Integration of Systems of Ordinary Differential
102C    Equations," LLNL Report UCID-30112, Rev. 1, April 1977.
103C 4. G. D. Byrne and A. C. Hindmarsh, "EPISODEB: An Experimental
104C    Package for the Integration of Systems of Ordinary Differential
105C    Equations with Banded Jacobians," LLNL Report UCID-30132, April
106C    1976.
107C 5. A. C. Hindmarsh, "ODEPACK, a Systematized Collection of ODE
108C    Solvers," in Scientific Computing, R. S. Stepleman et al., eds.,
109C    North-Holland, Amsterdam, 1983, pp. 55-64.
110C 6. K. R. Jackson and R. Sacks-Davis, "An Alternative Implementation
111C    of Variable Step-Size Multistep Formulas for Stiff ODEs," ACM
112C    Trans. Math. Software, 6 (1980), pp. 295-318.
113C-----------------------------------------------------------------------
114C Authors..
115C
116C               Peter N. Brown and Alan C. Hindmarsh
117C               Computing and Mathematics Research Division, L-316
118C               Lawrence Livermore National Laboratory
119C               Livermore, CA 94550
120C and
121C               George D. Byrne
122C               Exxon Research and Engineering Co.
123C               Clinton Township
124C               Route 22 East
125C               Annandale, NJ 08801
126C-----------------------------------------------------------------------
127C Summary of usage.
128C
129C Communication between the user and the DVODE package, for normal
130C situations, is summarized here.  This summary describes only a subset
131C of the full set of options available.  See the full description for
132C details, including optional communication, nonstandard options,
133C and instructions for special situations.  See also the example
134C problem (with program and output) following this summary.
135C
136C A. First provide a subroutine of the form..
137C
138C           SUBROUTINE F (NEQ, T, Y, YDOT, RPAR, IPAR)
139C           KPP_REAL T, Y, YDOT, RPAR
140C           DIMENSION Y(NEQ), YDOT(NEQ)
141C
142C which supplies the vector function f by loading YDOT(i) with f(i).
143C
144C B. Next determine (or guess) whether or not the problem is stiff.
145C Stiffness occurs when the Jacobian matrix df/dy has an eigenvalue
146C whose real part is negative and large in magnitude, compared to the
147C reciprocal of the t span of interest.  If the problem is nonstiff,
148C use a method flag MF = 10.  If it is stiff, there are four standard
149C choices for MF (21, 22, 24, 25), and DVODE requires the Jacobian
150C matrix in some form.  In these cases (MF .gt. 0), DVODE will use a
151C saved copy of the Jacobian matrix.  If this is undesirable because of
152C storage limitations, set MF to the corresponding negative value
153C (-21, -22, -24, -25).  (See full description of MF below.)
154C The Jacobian matrix is regarded either as full (MF = 21 or 22),
155C or banded (MF = 24 or 25).  In the banded case, DVODE requires two
156C half-bandwidth parameters ML and MU.  These are, respectively, the
157C widths of the lower and upper parts of the band, excluding the main
158C diagonal.  Thus the band consists of the locations (i,j) with
159C i-ML .le. j .le. i+MU, and the full bandwidth is ML+MU+1.
160C
161C C. If the problem is stiff, you are encouraged to supply the Jacobian
162C directly (MF = 21 or 24), but if this is not feasible, DVODE will
163C compute it internally by difference quotients (MF = 22 or 25).
164C If you are supplying the Jacobian, provide a subroutine of the form..
165C
166C           SUBROUTINE JAC (NEQ, T, Y, ML, MU, PD, NROWPD, RPAR, IPAR)
167C           KPP_REAL T, Y, PD, RPAR
168C           DIMENSION Y(NEQ), PD(NROWPD,NEQ)
169C
170C which supplies df/dy by loading PD as follows..
171C     For a full Jacobian (MF = 21), load PD(i,j) with df(i)/dy(j),
172C the partial derivative of f(i) with respect to y(j).  (Ignore the
173C ML and MU arguments in this case.)
174C     For a banded Jacobian (MF = 24), load PD(i-j+MU+1,j) with
175C df(i)/dy(j), i.e. load the diagonal lines of df/dy into the rows of
176C PD from the top down.
177C     In either case, only nonzero elements need be loaded.
178C
179C D. Write a main program which calls subroutine DVODE once for
180C each point at which answers are desired.  This should also provide
181C for possible use of logical unit 6 for output of error messages
182C by DVODE.  On the first CALL to DVODE, supply arguments as follows..
183C F    = Name of subroutine for right-hand side vector f.
184C          This name must be declared external in calling program.
185C NEQ    = Number of first order ODE-s.
186C Y      = Array of initial values, of length NEQ.
187C T      = The initial value of the independent variable.
188C TOUT   = First point where output is desired (.ne. T).
189C ITOL   = 1 or 2 according as AbsTol (below) is a scalar or array.
190C RelTol   = Relative tolerance parameter (scalar).
191C AbsTol   = Absolute tolerance parameter (scalar or array).
192C          The estimated local error in Y(i) will be controlled so as
193C          to be roughly less (in magnitude) than
194C             EWT(i) = RelTol*abs(Y(i)) + AbsTol     if ITOL = 1, or
195C             EWT(i) = RelTol*abs(Y(i)) + AbsTol(i)  if ITOL = 2.
196C          Thus the local error test passes if, in each component,
197C          either the absolute error is less than AbsTol (or AbsTol(i)),
198C          or the relative error is less than RelTol.
199C          Use RelTol = 0.0 for pure absolute error control, and
200C          use AbsTol = 0.0 (or AbsTol(i) = 0.0) for pure relative error
201C          control.  Caution.. Actual (global) errors may exceed these
202C          local tolerances, so choose them conservatively.
203C ITASK  = 1 for normal computation of output values of Y at t = TOUT.
204C ISTATE = Integer flag (input and output).  Set ISTATE = 1.
205C IOPT   = 0 to indicate no optional input used.
206C RWORK  = Real work array of length at least..
207C             20 + 16*NEQ                      for MF = 10,
208C             22 +  9*NEQ + 2*NEQ**2           for MF = 21 or 22,
209C             22 + 11*NEQ + (3*ML + 2*MU)*NEQ  for MF = 24 or 25.
210C LRW    = Declared length of RWORK (in user's DIMENSION statement).
211C IWORK  = Integer work array of length at least..
212C             30        for MF = 10,
213C             30 + NEQ  for MF = 21, 22, 24, or 25.
214C          If MF = 24 or 25, input in IWORK(1),IWORK(2) the lower
215C          and upper half-bandwidths ML,MU.
216C LIW    = Declared length of IWORK (in user's DIMENSION).
217C JAC    = Name of subroutine for Jacobian matrix (MF = 21 or 24).
218C          If used, this name must be declared external in calling
219C          program.  If not used, pass a dummy name.
220C MF     = Method flag.  Standard values are..
221C          10 for nonstiff (Adams) method, no Jacobian used.
222C          21 for stiff (BDF) method, user-supplied full Jacobian.
223C          22 for stiff method, internally generated full Jacobian.
224C          24 for stiff method, user-supplied banded Jacobian.
225C          25 for stiff method, internally generated banded Jacobian.
226C RPAR,IPAR = user-defined real and integer arrays passed to F and JAC.
227C Note that the main program must declare arrays Y, RWORK, IWORK,
228C and possibly AbsTol, RPAR, and IPAR.
229C
230C E. The output from the first CALL (or any call) is..
231C      Y = Array of computed values of y(t) vector.
232C      T = Corresponding value of independent variable (normally TOUT).
233C ISTATE = 2  if DVODE was successful, negative otherwise.
234C          -1 means excess work done on this call. (Perhaps wrong MF.)
235C          -2 means excess accuracy requested. (Tolerances too small.)
236C          -3 means illegal input detected. (See printed message.)
237C          -4 means repeated error test failures. (Check all input.)
238C          -5 means repeated convergence failures. (Perhaps bad
239C             Jacobian supplied or wrong choice of MF or tolerances.)
240C          -6 means error weight became zero during problem. (Solution
241C             component i vanished, and AbsTol or AbsTol(i) = 0.)
242C
243C F. To continue the integration after a successful return, simply
244C reset TOUT and CALL DVODE again.  No other parameters need be reset.
245C
246C-----------------------------------------------------------------------
247C EXAMPLE PROBLEM
248C
249C The following is a simple example problem, with the coding
250C needed for its solution by DVODE.  The problem is from chemical
251C kinetics, and consists of the following three rate equations..
252C     dy1/dt = -.04*y1 + 1.e4*y2*y3
253C     dy2/dt = .04*y1 - 1.e4*y2*y3 - 3.e7*y2**2
254C     dy3/dt = 3.e7*y2**2
255C on the interval from t = 0.0 to t = 4.e10, with initial conditions
256C y1 = 1.0, y2 = y3 = 0.  The problem is stiff.
257C
258C The following coding solves this problem with DVODE, using MF = 21
259C and printing results at t = .4, 4., ..., 4.e10.  It uses
260C ITOL = 2 and AbsTol much smaller for y2 than y1 or y3 because
261C y2 has much smaller values.
262C At the end of the run, statistical quantities of interest are
263C printed. (See optional output in the full description below.)
264C To generate Fortran source code, replace C in column 1 with a blank
265C in the coding below.
266C
267C     EXTERNAL FEX, JEX
268C     KPP_REAL AbsTol, RPAR, RelTol, RWORK, T, TOUT, Y
269C     DIMENSION Y(3), AbsTol(3), RWORK(67), IWORK(33)
270C     NEQ = 3
271C     Y(1) = 1.0D0
272C     Y(2) = 0.0D0
273C     Y(3) = 0.0D0
274C     T = 0.0D0
275C     TOUT = 0.4D0
276C     ITOL = 2
277C     RelTol = 1.D-4
278C     AbsTol(1) = 1.D-8
279C     AbsTol(2) = 1.D-14
280C     AbsTol(3) = 1.D-6
281C     ITASK = 1
282C     ISTATE = 1
283C     IOPT = 0
284C     LRW = 67
285C     LIW = 33
286C     MF = 21
287C     DO 40 IOUT = 1,12
288C       CALL DVODE(FEX,NEQ,Y,T,TOUT,ITOL,RelTol,AbsTol,ITASK,ISTATE,
289C    1            IOPT,RWORK,LRW,IWORK,LIW,JEX,MF,RPAR,IPAR)
290C       WRITE(6,20)T,Y(1),Y(2),Y(3)
291C 20    FORMAT(' At t =',D12.4,'   y =',3D14.6)
292C       IF (ISTATE .LT. 0) GO TO 80
293C 40    TOUT = TOUT*10.
294C     WRITE(6,60) IWORK(11),IWORK(12),IWORK(13),IWORK(19),
295C    1            IWORK(20),IWORK(21),IWORK(22)
296C 60  FORMAT(/' No. steps =',I4,'   No. f-s =',I4,
297C    1       '   No. J-s =',I4,'   No. LU-s =',I4/
298C    2       '  No. nonlinear iterations =',I4/
299C    3       '  No. nonlinear convergence failures =',I4/
300C    4       '  No. error test failures =',I4/)
301C     STOP
302C 80  WRITE(6,90)ISTATE
303C 90  FORMAT(///' Error halt.. ISTATE =',I3)
304C     STOP
305C     END
306C
307C     SUBROUTINE FEX (NEQ, T, Y, YDOT, RPAR, IPAR)
308C     KPP_REAL RPAR, T, Y, YDOT
309C     DIMENSION Y(NEQ), YDOT(NEQ)
310C     YDOT(1) = -.04D0*Y(1) + 1.D4*Y(2)*Y(3)
311C     YDOT(3) = 3.D7*Y(2)*Y(2)
312C     YDOT(2) = -YDOT(1) - YDOT(3)
313C     RETURN
314C     END
315C
316C     SUBROUTINE JEX (NEQ, T, Y, ML, MU, PD, NRPD, RPAR, IPAR)
317C     KPP_REAL PD, RPAR, T, Y
318C     DIMENSION Y(NEQ), PD(NRPD,NEQ)
319C     PD(1,1) = -.04D0
320C     PD(1,2) = 1.D4*Y(3)
321C     PD(1,3) = 1.D4*Y(2)
322C     PD(2,1) = .04D0
323C     PD(2,3) = -PD(1,3)
324C     PD(3,2) = 6.D7*Y(2)
325C     PD(2,2) = -PD(1,2) - PD(3,2)
326C     RETURN
327C     END
328C
329C The following output was obtained from the above program on a
330C Cray-1 computer with the CFT compiler.
331C
332C At t =  4.0000e-01   y =  9.851680e-01  3.386314e-05  1.479817e-02
333C At t =  4.0000e+00   y =  9.055255e-01  2.240539e-05  9.445214e-02
334C At t =  4.0000e+01   y =  7.158108e-01  9.184883e-06  2.841800e-01
335C At t =  4.0000e+02   y =  4.505032e-01  3.222940e-06  5.494936e-01
336C At t =  4.0000e+03   y =  1.832053e-01  8.942690e-07  8.167938e-01
337C At t =  4.0000e+04   y =  3.898560e-02  1.621875e-07  9.610142e-01
338C At t =  4.0000e+05   y =  4.935882e-03  1.984013e-08  9.950641e-01
339C At t =  4.0000e+06   y =  5.166183e-04  2.067528e-09  9.994834e-01
340C At t =  4.0000e+07   y =  5.201214e-05  2.080593e-10  9.999480e-01
341C At t =  4.0000e+08   y =  5.213149e-06  2.085271e-11  9.999948e-01
342C At t =  4.0000e+09   y =  5.183495e-07  2.073399e-12  9.999995e-01
343C At t =  4.0000e+10   y =  5.450996e-08  2.180399e-13  9.999999e-01
344C
345C No. steps = 595   No. f-s = 832   No. J-s =  13   No. LU-s = 112
346C  No. nonlinear iterations = 831
347C  No. nonlinear convergence failures =   0
348C  No. error test failures =  22
349C-----------------------------------------------------------------------
350C Full description of user interface to DVODE.
351C
352C The user interface to DVODE consists of the following parts.
353C
354C i.   The CALL sequence to subroutine DVODE, which is a driver
355C      routine for the solver.  This includes descriptions of both
356C      the CALL sequence arguments and of user-supplied routines.
357C      Following these descriptions is
358C        * a description of optional input available through the
359C          CALL sequence,
360C        * a description of optional output (in the work arrays), and
361C        * instructions for interrupting and restarting a solution.
362C
363C ii.  Descriptions of other routines in the DVODE package that may be
364C      (optionally) called by the user.  These provide the ability to
365C      alter error message handling, save and restore the internal
366C      COMMON, and obtain specified derivatives of the solution y(t).
367C
368C iii. Descriptions of COMMON blocks to be declared in overlay
369C      or similar environments.
370C
371C iv.  Description of two routines in the DVODE package, either of
372C      which the user may replace with his own version, if desired.
373C      these relate to the measurement of errors.
374C
375C-----------------------------------------------------------------------
376C Part i.  Call Sequence.
377C
378C The CALL sequence parameters used for input only are
379C     F, NEQ, TOUT, ITOL, RelTol, AbsTol, ITASK, IOPT, LRW, LIW, JAC, MF,
380C and those used for both input and output are
381C     Y, T, ISTATE.
382C The work arrays RWORK and IWORK are also used for conditional and
383C optional input and optional output.  (The term output here refers
384C to the return from subroutine DVODE to the user's calling program.)
385C
386C The legality of input parameters will be thoroughly checked on the
387C initial CALL for the problem, but not checked thereafter unless a
388C change in input parameters is flagged by ISTATE = 3 in the input.
389C
390C The descriptions of the CALL arguments are as follows.
391C
392C F    = The name of the user-supplied subroutine defining the
393C          ODE system.  The system must be put in the first-order
394C          form dy/dt = f(t,y), where f is a vector-valued function
395C          of the scalar t and the vector y.  Subroutine F is to
396C          compute the function f.  It is to have the form
397C               SUBROUTINE F (NEQ, T, Y, YDOT, RPAR, IPAR)
398C               KPP_REAL T, Y, YDOT, RPAR
399C               DIMENSION Y(NEQ), YDOT(NEQ)
400C          where NEQ, T, and Y are input, and the array YDOT = f(t,y)
401C          is output.  Y and YDOT are arrays of length NEQ.
402C          (In the DIMENSION statement above, NEQ  can be replaced by
403C          *  to make  Y  and  YDOT  assumed size arrays.)
404C          Subroutine F should not alter Y(1),...,Y(NEQ).
405C          F must be declared EXTERNAL in the calling program.
406C
407C          Subroutine F may access user-defined real and integer
408C          work arrays RPAR and IPAR, which are to be dimensioned
409C          in the main program.
410C
411C          If quantities computed in the F routine are needed
412C          externally to DVODE, an extra CALL to F should be made
413C          for this purpose, for consistent and accurate results.
414C          If only the derivative dy/dt is needed, use DVINDY instead.
415C
416C NEQ    = The size of the ODE system (number of first order
417C          ordinary differential equations).  Used only for input.
418C          NEQ may not be increased during the problem, but
419C          can be decreased (with ISTATE = 3 in the input).
420C
421C Y      = A real array for the vector of dependent variables, of
422C          length NEQ or more.  Used for both input and output on the
423C          first CALL (ISTATE = 1), and only for output on other calls.
424C          On the first call, Y must contain the vector of initial
425C          values.  In the output, Y contains the computed solution
426C          evaluated at T.  If desired, the Y array may be used
427C          for other purposes between calls to the solver.
428C
429C          This array is passed as the Y argument in all calls to
430C          F and JAC.
431C
432C T      = The independent variable.  In the input, T is used only on
433C          the first call, as the initial point of the integration.
434C          In the output, after each call, T is the value at which a
435C          computed solution Y is evaluated (usually the same as TOUT).
436C          On an error return, T is the farthest point reached.
437C
438C TOUT   = The next value of t at which a computed solution is desired.
439C          Used only for input.
440C
441C          When starting the problem (ISTATE = 1), TOUT may be equal
442C          to T for one call, then should .ne. T for the next call.
443C          For the initial T, an input value of TOUT .ne. T is used
444C          in order to determine the direction of the integration
445C          (i.e. the algebraic sign of the step sizes) and the rough
446C          scale of the problem.  Integration in either direction
447C          (forward or backward in t) is permitted.
448C
449C          If ITASK = 2 or 5 (one-step modes), TOUT is ignored after
450C          the first CALL (i.e. the first CALL with TOUT .ne. T).
451C          Otherwise, TOUT is required on every call.
452C
453C          If ITASK = 1, 3, or 4, the values of TOUT need not be
454C          monotone, but a value of TOUT which backs up is limited
455C          to the current internal t interval, whose endpoints are
456C          TCUR - HU and TCUR.  (See optional output, below, for
457C          TCUR and HU.)
458C
459C ITOL   = An indicator for the type of error control.  See
460C          description below under AbsTol.  Used only for input.
461C
462C RelTol   = A relative error tolerance parameter, either a scalar or
463C          an array of length NEQ.  See description below under AbsTol.
464C          Input only.
465C
466C AbsTol   = An absolute error tolerance parameter, either a scalar or
467C          an array of length NEQ.  Input only.
468C
469C          The input parameters ITOL, RelTol, and AbsTol determine
470C          the error control performed by the solver.  The solver will
471C          control the vector e = (e(i)) of estimated local errors
472C          in Y, according to an inequality of the form
473C                      rms-norm of ( e(i)/EWT(i) )   .le.   1,
474C          where       EWT(i) = RelTol(i)*abs(Y(i)) + AbsTol(i),
475C          and the rms-norm (root-mean-square norm) here is
476C          rms-norm(v) = sqrt(sum v(i)**2 / NEQ).  Here EWT = (EWT(i))
477C          is a vector of weights which must always be positive, and
478C          the values of RelTol and AbsTol should all be non-negative.
479C          The following table gives the types (scalar/array) of
480C          RelTol and AbsTol, and the corresponding form of EWT(i).
481C
482C             ITOL    RelTol       AbsTol          EWT(i)
483C              1     scalar     scalar     RelTol*ABS(Y(i)) + AbsTol
484C              2     scalar     array      RelTol*ABS(Y(i)) + AbsTol(i)
485C              3     array      scalar     RelTol(i)*ABS(Y(i)) + AbsTol
486C              4     array      array      RelTol(i)*ABS(Y(i)) + AbsTol(i)
487C
488C          When either of these parameters is a scalar, it need not
489C          be dimensioned in the user's calling program.
490C
491C          If none of the above choices (with ITOL, RelTol, and AbsTol
492C          fixed throughout the problem) is suitable, more general
493C          error controls can be obtained by substituting
494C          user-supplied routines for the setting of EWT and/or for
495C          the norm calculation.  See Part iv below.
496C
497C          If global errors are to be estimated by making a repeated
498C          run on the same problem with smaller tolerances, then all
499C          components of RelTol and AbsTol (i.e. of EWT) should be scaled
500C          down uniformly.
501C
502C ITASK  = An index specifying the task to be performed.
503C          Input only.  ITASK has the following values and meanings.
504C          1  means normal computation of output values of y(t) at
505C             t = TOUT (by overshooting and interpolating).
506C          2  means take one step only and return.
507C          3  means stop at the first internal mesh point at or
508C             beyond t = TOUT and return.
509C          4  means normal computation of output values of y(t) at
510C             t = TOUT but without overshooting t = TCRIT.
511C             TCRIT must be input as RWORK(1).  TCRIT may be equal to
512C             or beyond TOUT, but not behind it in the direction of
513C             integration.  This option is useful if the problem
514C             has a singularity at or beyond t = TCRIT.
515C          5  means take one step, without passing TCRIT, and return.
516C             TCRIT must be input as RWORK(1).
517C
518C          Note..  If ITASK = 4 or 5 and the solver reaches TCRIT
519C          (within roundoff), it will return T = TCRIT (exactly) to
520C          indicate this (unless ITASK = 4 and TOUT comes before TCRIT,
521C          in which case answers at T = TOUT are returned first).
522C
523C ISTATE = an index used for input and output to specify the
524C          the state of the calculation.
525C
526C          In the input, the values of ISTATE are as follows.
527C          1  means this is the first CALL for the problem
528C             (initializations will be done).  See note below.
529C          2  means this is not the first call, and the calculation
530C             is to continue normally, with no change in any input
531C             parameters except possibly TOUT and ITASK.
532C             (If ITOL, RelTol, and/or AbsTol are changed between calls
533C             with ISTATE = 2, the new values will be used but not
534C             tested for legality.)
535C          3  means this is not the first call, and the
536C             calculation is to continue normally, but with
537C             a change in input parameters other than
538C             TOUT and ITASK.  Changes are allowed in
539C             NEQ, ITOL, RelTol, AbsTol, IOPT, LRW, LIW, MF, ML, MU,
540C             and any of the optional input except H0.
541C             (See IWORK description for ML and MU.)
542C          Note..  A preliminary CALL with TOUT = T is not counted
543C          as a first CALL here, as no initialization or checking of
544C          input is done.  (Such a CALL is sometimes useful to include
545C          the initial conditions in the output.)
546C          Thus the first CALL for which TOUT .ne. T requires
547C          ISTATE = 1 in the input.
548C
549C          In the output, ISTATE has the following values and meanings.
550C           1  means nothing was done, as TOUT was equal to T with
551C              ISTATE = 1 in the input.
552C           2  means the integration was performed successfully.
553C          -1  means an excessive amount of work (more than MXSTEP
554C              steps) was done on this call, before completing the
555C              requested task, but the integration was otherwise
556C              successful as far as T.  (MXSTEP is an optional input
557C              and is normally 500.)  To continue, the user may
558C              simply reset ISTATE to a value .gt. 1 and CALL again.
559C              (The excess work step counter will be reset to 0.)
560C              In addition, the user may increase MXSTEP to avoid
561C              this error return.  (See optional input below.)
562C          -2  means too much accuracy was requested for the precision
563C              of the machine being used.  This was detected before
564C              completing the requested task, but the integration
565C              was successful as far as T.  To continue, the tolerance
566C              parameters must be reset, and ISTATE must be set
567C              to 3.  The optional output TOLSF may be used for this
568C              purpose.  (Note.. If this condition is detected before
569C              taking any steps, then an illegal input return
570C              (ISTATE = -3) occurs instead.)
571C          -3  means illegal input was detected, before taking any
572C              integration steps.  See written message for details.
573C              Note..  If the solver detects an infinite loop of calls
574C              to the solver with illegal input, it will cause
575C              the run to stop.
576C          -4  means there were repeated error test failures on
577C              one attempted step, before completing the requested
578C              task, but the integration was successful as far as T.
579C              The problem may have a singularity, or the input
580C              may be inappropriate.
581C          -5  means there were repeated convergence test failures on
582C              one attempted step, before completing the requested
583C              task, but the integration was successful as far as T.
584C              This may be caused by an inaccurate Jacobian matrix,
585C              if one is being used.
586C          -6  means EWT(i) became zero for some i during the
587C              integration.  Pure relative error control (AbsTol(i)=0.0)
588C              was requested on a variable which has now vanished.
589C              The integration was successful as far as T.
590C
591C          Note..  Since the normal output value of ISTATE is 2,
592C          it does not need to be reset for normal continuation.
593C          Also, since a negative input value of ISTATE will be
594C          regarded as illegal, a negative output value requires the
595C          user to change it, and possibly other input, before
596C          calling the solver again.
597C
598C IOPT   = An integer flag to specify whether or not any optional
599C          input is being used on this call.  Input only.
600C          The optional input is listed separately below.
601C          IOPT = 0 means no optional input is being used.
602C                   Default values will be used in all cases.
603C          IOPT = 1 means optional input is being used.
604C
605C RWORK  = A real working array (KPP_REAL).
606C          The length of RWORK must be at least
607C             20 + NYH*(MAXORD + 1) + 3*NEQ + LWM    where
608C          NYH    = the initial value of NEQ,
609C          MAXORD = 12 (if METH = 1) or 5 (if METH = 2) (unless a
610C                   smaller value is given as an optional input),
611C          LWM = length of work space for matrix-related data..
612C          LWM = 0             if MITER = 0,
613C          LWM = 2*NEQ**2 + 2  if MITER = 1 or 2, and MF.gt.0,
614C          LWM = NEQ**2 + 2    if MITER = 1 or 2, and MF.lt.0,
615C          LWM = NEQ + 2       if MITER = 3,
616C          LWM = (3*ML+2*MU+2)*NEQ + 2 if MITER = 4 or 5, and MF.gt.0,
617C          LWM = (2*ML+MU+1)*NEQ + 2   if MITER = 4 or 5, and MF.lt.0.
618C          (See the MF description for METH and MITER.)
619C          Thus if MAXORD has its default value and NEQ is constant,
620C          this length is..
621C             20 + 16*NEQ                    for MF = 10,
622C             22 + 16*NEQ + 2*NEQ**2         for MF = 11 or 12,
623C             22 + 16*NEQ + NEQ**2           for MF = -11 or -12,
624C             22 + 17*NEQ                    for MF = 13,
625C             22 + 18*NEQ + (3*ML+2*MU)*NEQ  for MF = 14 or 15,
626C             22 + 17*NEQ + (2*ML+MU)*NEQ    for MF = -14 or -15,
627C             20 +  9*NEQ                    for MF = 20,
628C             22 +  9*NEQ + 2*NEQ**2         for MF = 21 or 22,
629C             22 +  9*NEQ + NEQ**2           for MF = -21 or -22,
630C             22 + 10*NEQ                    for MF = 23,
631C             22 + 11*NEQ + (3*ML+2*MU)*NEQ  for MF = 24 or 25.
632C             22 + 10*NEQ + (2*ML+MU)*NEQ    for MF = -24 or -25.
633C          The first 20 words of RWORK are reserved for conditional
634C          and optional input and optional output.
635C
636C          The following word in RWORK is a conditional input..
637C            RWORK(1) = TCRIT = critical value of t which the solver
638C                       is not to overshoot.  Required if ITASK is
639C                       4 or 5, and ignored otherwise.  (See ITASK.)
640C
641C LRW    = The length of the array RWORK, as declared by the user.
642C          (This will be checked by the solver.)
643C
644C IWORK  = An integer work array.  The length of IWORK must be at least
645C             30        if MITER = 0 or 3 (MF = 10, 13, 20, 23), or
646C             30 + NEQ  otherwise (abs(MF) = 11,12,14,15,21,22,24,25).
647C          The first 30 words of IWORK are reserved for conditional and
648C          optional input and optional output.
649C
650C          The following 2 words in IWORK are conditional input..
651C            IWORK(1) = ML     These are the lower and upper
652C            IWORK(2) = MU     half-bandwidths, respectively, of the
653C                       banded Jacobian, excluding the main diagonal.
654C                       The band is defined by the matrix locations
655C                       (i,j) with i-ML .le. j .le. i+MU.  ML and MU
656C                       must satisfy  0 .le.  ML,MU  .le. NEQ-1.
657C                       These are required if MITER is 4 or 5, and
658C                       ignored otherwise.  ML and MU may in fact be
659C                       the band parameters for a matrix to which
660C                       df/dy is only approximately equal.
661C
662C LIW    = the length of the array IWORK, as declared by the user.
663C          (This will be checked by the solver.)
664C
665C Note..  The work arrays must not be altered between calls to DVODE
666C for the same problem, except possibly for the conditional and
667C optional input, and except for the last 3*NEQ words of RWORK.
668C The latter space is used for internal scratch space, and so is
669C available for use by the user outside DVODE between calls, if
670C desired (but not for use by F or JAC).
671C
672C JAC    = The name of the user-supplied routine (MITER = 1 or 4) to
673C          compute the Jacobian matrix, df/dy, as a function of
674C          the scalar t and the vector y.  It is to have the form
675C               SUBROUTINE JAC (NEQ, T, Y, ML, MU, PD, NROWPD,
676C                               RPAR, IPAR)
677C               KPP_REAL T, Y, PD, RPAR
678C               DIMENSION Y(NEQ), PD(NROWPD, NEQ)
679C          where NEQ, T, Y, ML, MU, and NROWPD are input and the array
680C          PD is to be loaded with partial derivatives (elements of the
681C          Jacobian matrix) in the output.  PD must be given a first
682C          dimension of NROWPD.  T and Y have the same meaning as in
683C          Subroutine F.  (In the DIMENSION statement above, NEQ can
684C          be replaced by  *  to make Y and PD assumed size arrays.)
685C               In the full matrix case (MITER = 1), ML and MU are
686C          ignored, and the Jacobian is to be loaded into PD in
687C          columnwise manner, with df(i)/dy(j) loaded into PD(i,j).
688C               In the band matrix case (MITER = 4), the elements
689C          within the band are to be loaded into PD in columnwise
690C          manner, with diagonal lines of df/dy loaded into the rows
691C          of PD. Thus df(i)/dy(j) is to be loaded into PD(i-j+MU+1,j).
692C          ML and MU are the half-bandwidth parameters. (See IWORK).
693C          The locations in PD in the two triangular areas which
694C          correspond to nonexistent matrix elements can be ignored
695C          or loaded arbitrarily, as they are overwritten by DVODE.
696C               JAC need not provide df/dy exactly.  A crude
697C          approximation (possibly with a smaller bandwidth) will do.
698C               In either case, PD is preset to zero by the solver,
699C          so that only the nonzero elements need be loaded by JAC.
700C          Each CALL to JAC is preceded by a CALL to F with the same
701C          arguments NEQ, T, and Y.  Thus to gain some efficiency,
702C          intermediate quantities shared by both calculations may be
703C          saved in a user COMMON block by F and not recomputed by JAC,
704C          if desired.  Also, JAC may alter the Y array, if desired.
705C          JAC must be declared external in the calling program.
706C               Subroutine JAC may access user-defined real and integer
707C          work arrays, RPAR and IPAR, whose dimensions are set by the
708C          user in the main program.
709C
710C MF     = The method flag.  Used only for input.  The legal values of
711C          MF are 10, 11, 12, 13, 14, 15, 20, 21, 22, 23, 24, 25,
712C          -11, -12, -14, -15, -21, -22, -24, -25.
713C          MF is a signed two-digit integer, MF = JSV*(10*METH + MITER).
714C          JSV = SIGN(MF) indicates the Jacobian-saving strategy..
715C            JSV =  1 means a copy of the Jacobian is saved for reuse
716C                     in the corrector iteration algorithm.
717C            JSV = -1 means a copy of the Jacobian is not saved
718C                     (valid only for MITER = 1, 2, 4, or 5).
719C          METH indicates the basic linear multistep method..
720C            METH = 1 means the implicit Adams method.
721C            METH = 2 means the method based on backward
722C                     differentiation formulas (BDF-s).
723C          MITER indicates the corrector iteration method..
724C            MITER = 0 means functional iteration (no Jacobian matrix
725C                      is involved).
726C            MITER = 1 means chord iteration with a user-supplied
727C                      full (NEQ by NEQ) Jacobian.
728C            MITER = 2 means chord iteration with an internally
729C                      generated (difference quotient) full Jacobian
730C                      (using NEQ extra calls to F per df/dy value).
731C            MITER = 3 means chord iteration with an internally
732C                      generated diagonal Jacobian approximation
733C                      (using 1 extra CALL to F per df/dy evaluation).
734C            MITER = 4 means chord iteration with a user-supplied
735C                      banded Jacobian.
736C            MITER = 5 means chord iteration with an internally
737C                      generated banded Jacobian (using ML+MU+1 extra
738C                      calls to F per df/dy evaluation).
739C          If MITER = 1 or 4, the user must supply a subroutine JAC
740C          (the name is arbitrary) as described above under JAC.
741C          For other values of MITER, a dummy argument can be used.
742C
743C RPAR     User-specified array used to communicate real parameters
744C          to user-supplied subroutines.  If RPAR is a vector, then
745C          it must be dimensioned in the user's main program.  If it
746C          is unused or it is a scalar, then it need not be
747C          dimensioned.
748C
749C IPAR     User-specified array used to communicate integer parameter
750C          to user-supplied subroutines.  The comments on dimensioning
751C          RPAR apply to IPAR.
752C-----------------------------------------------------------------------
753C Optional Input.
754C
755C The following is a list of the optional input provided for in the
756C CALL sequence.  (See also Part ii.)  For each such input variable,
757C this table lists its name as used in this documentation, its
758C location in the CALL sequence, its meaning, and the default value.
759C The use of any of this input requires IOPT = 1, and in that
760C case all of this input is examined.  A value of zero for any
761C of these optional input variables will cause the default value to be
762C used.  Thus to use a subset of the optional input, simply preload
763C locations 5 to 10 in RWORK and IWORK to 0.0 and 0 respectively, and
764C then set those of interest to nonzero values.
765C
766C NAME    LOCATION      MEANING AND DEFAULT VALUE
767C
768C H0      RWORK(5)  The step size to be attempted on the first step.
769C                   The default value is determined by the solver.
770C
771C HMAX    RWORK(6)  The maximum absolute step size allowed.
772C                   The default value is infinite.
773C
774C HMIN    RWORK(7)  The minimum absolute step size allowed.
775C                   The default value is 0.  (This lower bound is not
776C                   enforced on the final step before reaching TCRIT
777C                   when ITASK = 4 or 5.)
778C
779C MAXORD  IWORK(5)  The maximum order to be allowed.  The default
780C                   value is 12 if METH = 1, and 5 if METH = 2.
781C                   If MAXORD exceeds the default value, it will
782C                   be reduced to the default value.
783C                   If MAXORD is changed during the problem, it may
784C                   cause the current order to be reduced.
785C
786C MXSTEP  IWORK(6)  Maximum number of (internally defined) steps
787C                   allowed during one CALL to the solver.
788C                   The default value is 500.
789C
790C MXHNIL  IWORK(7)  Maximum number of messages printed (per problem)
791C                   warning that T + H = T on a step (H = step size).
792C                   This must be positive to result in a non-default
793C                   value.  The default value is 10.
794C
795C-----------------------------------------------------------------------
796C Optional Output.
797C
798C As optional additional output from DVODE, the variables listed
799C below are quantities related to the performance of DVODE
800C which are available to the user.  These are communicated by way of
801C the work arrays, but also have internal mnemonic names as shown.
802C Except where stated otherwise, all of this output is defined
803C on any successful return from DVODE, and on any return with
804C ISTATE = -1, -2, -4, -5, or -6.  On an illegal input return
805C (ISTATE = -3), they will be unchanged from their existing values
806C (if any), except possibly for TOLSF, LENRW, and LENIW.
807C On any error return, output relevant to the error will be defined,
808C as noted below.
809C
810C NAME    LOCATION      MEANING
811C
812C HU      RWORK(11) The step size in t last used (successfully).
813C
814C HCUR    RWORK(12) The step size to be attempted on the next step.
815C
816C TCUR    RWORK(13) The current value of the independent variable
817C                   which the solver has actually reached, i.e. the
818C                   current internal mesh point in t.  In the output,
819C                   TCUR will always be at least as far from the
820C                   initial value of t as the current argument T,
821C                   but may be farther (if interpolation was done).
822C
823C TOLSF   RWORK(14) A tolerance scale factor, greater than 1.0,
824C                   computed when a request for too much accuracy was
825C                   detected (ISTATE = -3 if detected at the start of
826C                   the problem, ISTATE = -2 otherwise).  If ITOL is
827C                   left unaltered but RelTol and AbsTol are uniformly
828C                   scaled up by a factor of TOLSF for the next call,
829C                   then the solver is deemed likely to succeed.
830C                   (The user may also ignore TOLSF and alter the
831C                   tolerance parameters in any other way appropriate.)
832C
833C NST     IWORK(11) The number of steps taken for the problem so far.
834C
835C NFE     IWORK(12) The number of f evaluations for the problem so far.
836C
837C NJE     IWORK(13) The number of Jacobian evaluations so far.
838C
839C NQU     IWORK(14) The method order last used (successfully).
840C
841C NQCUR   IWORK(15) The order to be attempted on the next step.
842C
843C IMXER   IWORK(16) The index of the component of largest magnitude in
844C                   the weighted local error vector ( e(i)/EWT(i) ),
845C                   on an error return with ISTATE = -4 or -5.
846C
847C LENRW   IWORK(17) The length of RWORK actually required.
848C                   This is defined on normal returns and on an illegal
849C                   input return for insufficient storage.
850C
851C LENIW   IWORK(18) The length of IWORK actually required.
852C                   This is defined on normal returns and on an illegal
853C                   input return for insufficient storage.
854C
855C NLU     IWORK(19) The number of matrix LU decompositions so far.
856C
857C NNI     IWORK(20) The number of nonlinear (Newton) iterations so far.
858C
859C NCFN    IWORK(21) The number of convergence failures of the nonlinear
860C                   solver so far.
861C
862C NETF    IWORK(22) The number of error test failures of the integrator
863C                   so far.
864C
865C The following two arrays are segments of the RWORK array which
866C may also be of interest to the user as optional output.
867C For each array, the table below gives its internal name,
868C its base address in RWORK, and its description.
869C
870C NAME    BASE ADDRESS      DESCRIPTION
871C
872C YH      21             The Nordsieck history array, of size NYH by
873C                        (NQCUR + 1), where NYH is the initial value
874C                        of NEQ.  For j = 0,1,...,NQCUR, column j+1
875C                        of YH contains HCUR**j/factorial(j) times
876C                        the j-th derivative of the interpolating
877C                        polynomial currently representing the
878C                        solution, evaluated at t = TCUR.
879C
880C ACOR     LENRW-NEQ+1   Array of size NEQ used for the accumulated
881C                        corrections on each step, scaled in the output
882C                        to represent the estimated local error in Y
883C                        on the last step.  This is the vector e in
884C                        the description of the error control.  It is
885C                        defined only on a successful return from DVODE.
886C
887C-----------------------------------------------------------------------
888C Interrupting and Restarting
889C
890C If the integration of a given problem by DVODE is to be
891C interrupted and then later continued, such as when restarting
892C an interrupted run or alternating between two or more ODE problems,
893C the user should save, following the return from the last DVODE call
894C prior to the interruption, the contents of the CALL sequence
895C variables and internal COMMON blocks, and later restore these
896C values before the next DVODE CALL for that problem.  To save
897C and restore the COMMON blocks, use subroutine DVSRCO, as
898C described below in part ii.
899C
900C In addition, if non-default values for either LUN or MFLAG are
901C desired, an extra CALL to XSETUN and/or XSETF should be made just
902C before continuing the integration.  See Part ii below for details.
903C
904C-----------------------------------------------------------------------
905C Part ii.  Other Routines Callable.
906C
907C The following are optional calls which the user may make to
908C gain additional capabilities in conjunction with DVODE.
909C (The routines XSETUN and XSETF are designed to conform to the
910C SLATEC error handling package.)
911C
912C     FORM OF CALL                  FUNCTION
913C  CALL XSETUN(LUN)           Set the logical unit number, LUN, for
914C                             output of messages from DVODE, if
915C                             the default is not desired.
916C                             The default value of LUN is 6.
917C
918C  CALL XSETF(MFLAG)          Set a flag to control the printing of
919C                             messages by DVODE.
920C                             MFLAG = 0 means do not print. (Danger..
921C                             This risks losing valuable information.)
922C                             MFLAG = 1 means print (the default).
923C
924C                             Either of the above calls may be made at
925C                             any time and will take effect immediately.
926C
927C  CALL DVSRCO(RSAV,ISAV,JOB) Saves and restores the contents of
928C                             the internal COMMON blocks used by
929C                             DVODE. (See Part iii below.)
930C                             RSAV must be a real array of length 49
931C                             or more, and ISAV must be an integer
932C                             array of length 40 or more.
933C                             JOB=1 means save COMMON into RSAV/ISAV.
934C                             JOB=2 means restore COMMON from RSAV/ISAV.
935C                                DVSRCO is useful if one is
936C                             interrupting a run and restarting
937C                             later, or alternating between two or
938C                             more problems solved with DVODE.
939C
940C  CALL DVINDY(,,,,,)         Provide derivatives of y, of various
941C        (See below.)         orders, at a specified point T, if
942C                             desired.  It may be called only after
943C                             a successful return from DVODE.
944C
945C The detailed instructions for using DVINDY are as follows.
946C The form of the CALL is..
947C
948C  CALL DVINDY (T, K, RWORK(21), NYH, DKY, IFLAG)
949C
950C The input parameters are..
951C
952C T         = Value of independent variable where answers are desired
953C             (normally the same as the T last returned by DVODE).
954C             For valid results, T must lie between TCUR - HU and TCUR.
955C             (See optional output for TCUR and HU.)
956C K         = Integer order of the derivative desired.  K must satisfy
957C             0 .le. K .le. NQCUR, where NQCUR is the current order
958C             (see optional output).  The capability corresponding
959C             to K = 0, i.e. computing y(T), is already provided
960C             by DVODE directly.  Since NQCUR .ge. 1, the first
961C             derivative dy/dt is always available with DVINDY.
962C RWORK(21) = The base address of the history array YH.
963C NYH       = Column length of YH, equal to the initial value of NEQ.
964C
965C The output parameters are..
966C
967C DKY       = A real array of length NEQ containing the computed value
968C             of the K-th derivative of y(t).
969C IFLAG     = Integer flag, returned as 0 if K and T were legal,
970C             -1 if K was illegal, and -2 if T was illegal.
971C             On an error return, a message is also written.
972C-----------------------------------------------------------------------
973C Part iii.  COMMON Blocks.
974C If DVODE is to be used in an overlay situation, the user
975C must declare, in the primary overlay, the variables in..
976C   (1) the CALL sequence to DVODE,
977C   (2) the two internal COMMON blocks
978C         /DVOD01/  of length  81  (48 KPP_REAL words
979C                         followed by 33 integer words),
980C         /DVOD02/  of length  9  (1 KPP_REAL word
981C                         followed by 8 integer words),
982C
983C If DVODE is used on a system in which the contents of internal
984C COMMON blocks are not preserved between calls, the user should
985C declare the above two COMMON blocks in his main program to insure
986C that their contents are preserved.
987C
988C-----------------------------------------------------------------------
989C Part iv.  Optionally Replaceable Solver Routines.
990C
991C Below are descriptions of two routines in the DVODE package which
992C relate to the measurement of errors.  Either routine can be
993C replaced by a user-supplied version, if desired.  However, since such
994C a replacement may have a major impact on performance, it should be
995C done only when absolutely necessary, and only with great caution.
996C (Note.. The means by which the package version of a routine is
997C superseded by the user's version may be system-dependent.)
998C
999C (a) DEWSET.
1000C The following subroutine is called just before each internal
1001C integration step, and sets the array of error weights, EWT, as
1002C described under ITOL/RelTol/AbsTol above..
1003C     SUBROUTINE DEWSET (NEQ, ITOL, RelTol, AbsTol, YCUR, EWT)
1004C where NEQ, ITOL, RelTol, and AbsTol are as in the DVODE CALL sequence,
1005C YCUR contains the current dependent variable vector, and
1006C EWT is the array of weights set by DEWSET.
1007C
1008C If the user supplies this subroutine, it must return in EWT(i)
1009C (i = 1,...,NEQ) a positive quantity suitable for comparison with
1010C errors in Y(i).  The EWT array returned by DEWSET is passed to the
1011C DVNORM routine (See below.), and also used by DVODE in the computation
1012C of the optional output IMXER, the diagonal Jacobian approximation,
1013C and the increments for difference quotient Jacobians.
1014C
1015C In the user-supplied version of DEWSET, it may be desirable to use
1016C the current values of derivatives of y.  Derivatives up to order NQ
1017C are available from the history array YH, described above under
1018C Optional Output.  In DEWSET, YH is identical to the YCUR array,
1019C extended to NQ + 1 columns with a column length of NYH and scale
1020C factors of h**j/factorial(j).  On the first CALL for the problem,
1021C given by NST = 0, NQ is 1 and H is temporarily set to 1.0.
1022C NYH is the initial value of NEQ.  The quantities NQ, H, and NST
1023C can be obtained by including in DEWSET the statements..
1024C     KPP_REAL RVOD, H, HU
1025C     COMMON /DVOD01/ RVOD(48), IVOD(33)
1026C     COMMON /DVOD02/ HU, NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
1027C     NQ = IVOD(28)
1028C     H = RVOD(21)
1029C Thus, for example, the current value of dy/dt can be obtained as
1030C YCUR(NYH+i)/H  (i=1,...,NEQ)  (and the division by H is
1031C unnecessary when NST = 0).
1032C
1033C (b) DVNORM.
1034C The following is a real function routine which computes the weighted
1035C root-mean-square norm of a vector v..
1036C     D = DVNORM (N, V, W)
1037C where..
1038C   N = the length of the vector,
1039C   V = real array of length N containing the vector,
1040C   W = real array of length N containing weights,
1041C   D = sqrt( (1/N) * sum(V(i)*W(i))**2 ).
1042C DVNORM is called with N = NEQ and with W(i) = 1.0/EWT(i), where
1043C EWT is as set by subroutine DEWSET.
1044C
1045C If the user supplies this function, it should return a non-negative
1046C value of DVNORM suitable for use in the error control in DVODE.
1047C None of the arguments should be altered by DVNORM.
1048C For example, a user-supplied DVNORM routine might..
1049C   -substitute a max-norm of (V(i)*W(i)) for the rms-norm, or
1050C   -ignore some components of V in the norm, with the effect of
1051C    suppressing the error control on those components of Y.
1052C-----------------------------------------------------------------------
1053C Other Routines in the DVODE Package.
1054C
1055C In addition to subroutine DVODE, the DVODE package includes the
1056C following subroutines and function routines..
1057C  DVHIN     computes an approximate step size for the initial step.
1058C  DVINDY    computes an interpolated value of the y vector at t = TOUT.
1059C  DVSTEP    is the core integrator, which does one step of the
1060C            integration and the associated error control.
1061C  DVSET     sets all method coefficients and test constants.
1062C  DVNLSD    solves the underlying nonlinear system -- the corrector.
1063C  DVJAC     computes and preprocesses the Jacobian matrix J = df/dy
1064C            and the Newton iteration matrix P = I - (h/l1)*J.
1065C  DVSOL     manages solution of linear system in chord iteration.
1066C  DVJUST    adjusts the history array on a change of order.
1067C  DEWSET    sets the error weight vector EWT before each step.
1068C  DVNORM    computes the weighted r.m.s. norm of a vector.
1069C  DVSRCO    is a user-callable routines to save and restore
1070C            the contents of the internal COMMON blocks.
1071C  DACOPY    is a routine to copy one two-dimensional array to another.
1072C  DGEFA and DGESL   are routines from LINPACK for solving full
1073C            systems of linear algebraic equations.
1074C  DGBFA and DGBSL   are routines from LINPACK for solving banded
1075C            linear systems.
1076C  DAXPY, DSCAL, and DCOPY are basic linear algebra modules (BLAS).
1077C  D1MACH    sets the unit roundoff of the machine.
1078C  XERRWD, XSETUN, XSETF, LUNSAV, and MFLGSV handle the printing of all
1079C            error messages and warnings.  XERRWD is machine-dependent.
1080C Note..  DVNORM, D1MACH, LUNSAV, and MFLGSV are function routines.
1081C All the others are subroutines.
1082C
1083C The intrinsic and external routines used by the DVODE package are..
1084C ABS, MAX, MIN, REAL, SIGN, SQRT, and WRITE.
1085C
1086C-----------------------------------------------------------------------
1087C
1088C Type declarations for labeled COMMON block DVOD01 --------------------
1089C
1090      KPP_REAL ACNRM, CCMXJ, CONP, CRATE, DRC, EL,
1091     1     ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
1092     2     RC, RL1, TAU, TQ, TN, UROUND
1093      INTEGER ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
1094     1        L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
1095     2        LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
1096     3        N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
1097     4        NSLP, NYH
1098C
1099C Type declarations for labeled COMMON block DVOD02 --------------------
1100C
1101      KPP_REAL HU
1102      INTEGER NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
1103C
1104C Type declarations for local variables --------------------------------
1105C
1106      EXTERNAL DVNLSD, F, JAC
1107      LOGICAL IHIT
1108      KPP_REAL AbsTolI, BIG, EWTI, FOUR, H0, HMAX, HMX, HUN, ONE,
1109     1   PT2, RH, RelTolI, SIZE, TCRIT, TNEXT, TOLSF, TP, TWO, ZERO
1110      INTEGER I, IER, IFLAG, IMXER, JCO, KGO, LENIW, LENJ, LENP, LENRW,
1111     1   LENWM, LF0, MBAND, ML, MORD, MU, MXHNL0, MXSTP0, NITER, NSLAST
1112      CHARACTER*80 MSG
1113C
1114C Type declaration for function subroutines called ---------------------
1115C
1116      KPP_REAL D1MACH, DVNORM
1117C
1118      DIMENSION MORD(2)
1119C-----------------------------------------------------------------------
1120C The following Fortran-77 declaration is to cause the values of the
1121C listed (local) variables to be saved between calls to DVODE.
1122C-----------------------------------------------------------------------
1123      SAVE MORD, MXHNL0, MXSTP0
1124      SAVE ZERO, ONE, TWO, FOUR, PT2, HUN
1125C-----------------------------------------------------------------------
1126C The following internal COMMON blocks contain variables which are
1127C communicated between subroutines in the DVODE package, or which are
1128C to be saved between calls to DVODE.
1129C In each block, real variables precede integers.
1130C The block /DVOD01/ appears in subroutines DVODE, DVINDY, DVSTEP,
1131C DVSET, DVNLSD, DVJAC, DVSOL, DVJUST and DVSRCO.
1132C The block /DVOD02/ appears in subroutines DVODE, DVINDY, DVSTEP,
1133C DVNLSD, DVJAC, and DVSRCO.
1134C
1135C The variables stored in the internal COMMON blocks are as follows..
1136C
1137C ACNRM  = Weighted r.m.s. norm of accumulated correction vectors.
1138C CCMXJ  = Threshhold on DRC for updating the Jacobian. (See DRC.)
1139C CONP   = The saved value of TQ(5).
1140C CRATE  = Estimated corrector convergence rate constant.
1141C DRC    = Relative change in H*RL1 since last DVJAC call.
1142C EL     = Real array of integration coefficients.  See DVSET.
1143C ETA    = Saved tentative ratio of new to old H.
1144C ETAMAX = Saved maximum value of ETA to be allowed.
1145C H      = The step size.
1146C HMIN   = The minimum absolute value of the step size H to be used.
1147C HMXI   = Inverse of the maximum absolute value of H to be used.
1148C          HMXI = 0.0 is allowed and corresponds to an infinite HMAX.
1149C HNEW   = The step size to be attempted on the next step.
1150C HSCAL  = Stepsize in scaling of YH array.
1151C PRL1   = The saved value of RL1.
1152C RC     = Ratio of current H*RL1 to value on last DVJAC call.
1153C RL1    = The reciprocal of the coefficient EL(1).
1154C TAU    = Real vector of past NQ step sizes, length 13.
1155C TQ     = A real vector of length 5 in which DVSET stores constants
1156C          used for the convergence test, the error test, and the
1157C          selection of H at a new order.
1158C TN     = The independent variable, updated on each step taken.
1159C UROUND = The machine unit roundoff.  The smallest positive real number
1160C          such that  1.0 + UROUND .ne. 1.0
1161C ICF    = Integer flag for convergence failure in DVNLSD..
1162C            0 means no failures.
1163C            1 means convergence failure with out of date Jacobian
1164C                   (recoverable error).
1165C            2 means convergence failure with current Jacobian or
1166C                   singular matrix (unrecoverable error).
1167C INIT   = Saved integer flag indicating whether initialization of the
1168C          problem has been done (INIT = 1) or not.
1169C IPUP   = Saved flag to signal updating of Newton matrix.
1170C JCUR   = Output flag from DVJAC showing Jacobian status..
1171C            JCUR = 0 means J is not current.
1172C            JCUR = 1 means J is current.
1173C JSTART = Integer flag used as input to DVSTEP..
1174C            0  means perform the first step.
1175C            1  means take a new step continuing from the last.
1176C            -1 means take the next step with a new value of MAXORD,
1177C                  HMIN, HMXI, N, METH, MITER, and/or matrix parameters.
1178C          On return, DVSTEP sets JSTART = 1.
1179C JSV    = Integer flag for Jacobian saving, = sign(MF).
1180C KFLAG  = A completion code from DVSTEP with the following meanings..
1181C               0      the step was succesful.
1182C              -1      the requested error could not be achieved.
1183C              -2      corrector convergence could not be achieved.
1184C              -3, -4  fatal error in VNLS (can not occur here).
1185C KUTH   = Input flag to DVSTEP showing whether H was reduced by the
1186C          driver.  KUTH = 1 if H was reduced, = 0 otherwise.
1187C L      = Integer variable, NQ + 1, current order plus one.
1188C LMAX   = MAXORD + 1 (used for dimensioning).
1189C LOCJS  = A pointer to the saved Jacobian, whose storage starts at
1190C          WM(LOCJS), if JSV = 1.
1191C LYH, LEWT, LACOR, LSAVF, LWM, LIWM = Saved integer pointers
1192C          to segments of RWORK and IWORK.
1193C MAXORD = The maximum order of integration method to be allowed.
1194C METH/MITER = The method flags.  See MF.
1195C MSBJ   = The maximum number of steps between J evaluations, = 50.
1196C MXHNIL = Saved value of optional input MXHNIL.
1197C MXSTEP = Saved value of optional input MXSTEP.
1198C N      = The number of first-order ODEs, = NEQ.
1199C NEWH   = Saved integer to flag change of H.
1200C NEWQ   = The method order to be used on the next step.
1201C NHNIL  = Saved counter for occurrences of T + H = T.
1202C NQ     = Integer variable, the current integration method order.
1203C NQNYH  = Saved value of NQ*NYH.
1204C NQWAIT = A counter controlling the frequency of order changes.
1205C          An order change is about to be considered if NQWAIT = 1.
1206C NSLJ   = The number of steps taken as of the last Jacobian update.
1207C NSLP   = Saved value of NST as of last Newton matrix update.
1208C NYH    = Saved value of the initial value of NEQ.
1209C HU     = The step size in t last used.
1210C NCFN   = Number of nonlinear convergence failures so far.
1211C NETF   = The number of error test failures of the integrator so far.
1212C NFE    = The number of f evaluations for the problem so far.
1213C NJE    = The number of Jacobian evaluations so far.
1214C NLU    = The number of matrix LU decompositions so far.
1215C NNI    = Number of nonlinear iterations so far.
1216C NQU    = The method order last used.
1217C NST    = The number of steps taken for the problem so far.
1218C-----------------------------------------------------------------------
1219      COMMON /DVOD01/ ACNRM, CCMXJ, CONP, CRATE, DRC, EL(13),
1220     1                ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
1221     2                RC, RL1, TAU(13), TQ(5), TN, UROUND,
1222     3                ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
1223     4                L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
1224     5                LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
1225     6                N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
1226     7                NSLP, NYH
1227      COMMON /DVOD02/ HU, NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
1228C
1229
1230      DATA  MORD(1) /12/, MORD(2) /5/, MXSTP0 /500/, MXHNL0 /10/
1231      DATA ZERO /0.0D0/, ONE /1.0D0/, TWO /2.0D0/, FOUR /4.0D0/,
1232     1     PT2 /0.2D0/, HUN /100.0D0/
1233C-----------------------------------------------------------------------
1234C Block A.
1235C This code block is executed on every call.
1236C It tests ISTATE and ITASK for legality and branches appropriately.
1237C If ISTATE .gt. 1 but the flag INIT shows that initialization has
1238C not yet been done, an error return occurs.
1239C If ISTATE = 1 and TOUT = T, return immediately.
1240C-----------------------------------------------------------------------
1241      IF (ISTATE .LT. 1 .OR. ISTATE .GT. 3) GO TO 601
1242      IF (ITASK .LT. 1 .OR. ITASK .GT. 5) GO TO 602
1243      IF (ISTATE .EQ. 1) GO TO 10
1244      IF (INIT .NE. 1) GO TO 603
1245      IF (ISTATE .EQ. 2) GO TO 200
1246      GO TO 20
1247 10   INIT = 0
1248      IF (TOUT .EQ. T) RETURN
1249C-----------------------------------------------------------------------
1250C Block B.
1251C The next code block is executed for the initial CALL (ISTATE = 1),
1252C or for a continuation CALL with parameter changes (ISTATE = 3).
1253C It contains checking of all input and various initializations.
1254C
1255C First check legality of the non-optional input NEQ, ITOL, IOPT,
1256C MF, ML, and MU.
1257C-----------------------------------------------------------------------
1258 20   IF (NEQ .LE. 0) GO TO 604
1259      IF (ISTATE .EQ. 1) GO TO 25
1260      IF (NEQ .GT. N) GO TO 605
1261 25   N = NEQ
1262      IF (ITOL .LT. 1 .OR. ITOL .GT. 4) GO TO 606
1263      IF (IOPT .LT. 0 .OR. IOPT .GT. 1) GO TO 607
1264      JSV = SIGN(1,MF)
1265      MF = ABS(MF)
1266      METH = MF/10
1267      MITER = MF - 10*METH
1268      IF (METH .LT. 1 .OR. METH .GT. 2) GO TO 608
1269      IF (MITER .LT. 0 .OR. MITER .GT. 5) GO TO 608
1270      IF (MITER .LE. 3) GO TO 30
1271      ML = IWORK(1)
1272      MU = IWORK(2)
1273      IF (ML .LT. 0 .OR. ML .GE. N) GO TO 609
1274      IF (MU .LT. 0 .OR. MU .GE. N) GO TO 610
1275 30   CONTINUE
1276C Next process and check the optional input. ---------------------------
1277      IF (IOPT .EQ. 1) GO TO 40
1278      MAXORD = MORD(METH)
1279      MXSTEP = MXSTP0
1280      MXHNIL = MXHNL0
1281      IF (ISTATE .EQ. 1) H0 = ZERO
1282      HMXI = ZERO
1283      HMIN = ZERO
1284      GO TO 60
1285 40   MAXORD = IWORK(5)
1286      IF (MAXORD .LT. 0) GO TO 611
1287      IF (MAXORD .EQ. 0) MAXORD = 100
1288      MAXORD = MIN(MAXORD,MORD(METH))
1289      MXSTEP = IWORK(6)
1290      IF (MXSTEP .LT. 0) GO TO 612
1291      IF (MXSTEP .EQ. 0) MXSTEP = MXSTP0
1292      MXHNIL = IWORK(7)
1293      IF (MXHNIL .LT. 0) GO TO 613
1294      IF (MXHNIL .EQ. 0) MXHNIL = MXHNL0
1295      IF (ISTATE .NE. 1) GO TO 50
1296      H0 = RWORK(5)
1297      IF ((TOUT - T)*H0 .LT. ZERO) GO TO 614
1298 50   HMAX = RWORK(6)
1299      IF (HMAX .LT. ZERO) GO TO 615
1300      HMXI = ZERO
1301      IF (HMAX .GT. ZERO) HMXI = ONE/HMAX
1302      HMIN = RWORK(7)
1303      IF (HMIN .LT. ZERO) GO TO 616
1304C-----------------------------------------------------------------------
1305C Set work array pointers and check lengths LRW and LIW.
1306C Pointers to segments of RWORK and IWORK are named by prefixing L to
1307C the name of the segment.  E.g., the segment YH starts at RWORK(LYH).
1308C Segments of RWORK (in order) are denoted  YH, WM, EWT, SAVF, ACOR.
1309C Within WM, LOCJS is the location of the saved Jacobian (JSV .gt. 0).
1310C-----------------------------------------------------------------------
1311 60   LYH = 21
1312      IF (ISTATE .EQ. 1) NYH = N
1313      LWM = LYH + (MAXORD + 1)*NYH
1314      JCO = MAX(0,JSV)
1315      IF (MITER .EQ. 0) LENWM = 0
1316      IF (MITER .EQ. 1 .OR. MITER .EQ. 2) THEN
1317        LENWM = 2 + (1 + JCO)*N*N
1318        LOCJS = N*N + 3
1319      ENDIF
1320      IF (MITER .EQ. 3) LENWM = 2 + N
1321      IF (MITER .EQ. 4 .OR. MITER .EQ. 5) THEN
1322        MBAND = ML + MU + 1
1323        LENP = (MBAND + ML)*N
1324        LENJ = MBAND*N
1325        LENWM = 2 + LENP + JCO*LENJ
1326        LOCJS = LENP + 3
1327        ENDIF
1328      LEWT = LWM + LENWM
1329      LSAVF = LEWT + N
1330      LACOR = LSAVF + N
1331      LENRW = LACOR + N - 1
1332      IWORK(17) = LENRW
1333      LIWM = 1
1334      LENIW = 30 + N
1335      IF (MITER .EQ. 0 .OR. MITER .EQ. 3) LENIW = 30
1336      IWORK(18) = LENIW
1337      IF (LENRW .GT. LRW) GO TO 617
1338      IF (LENIW .GT. LIW) GO TO 618
1339C Check RelTol and AbsTol for legality. ------------------------------------
1340      RelTolI = RelTol(1)
1341      AbsTolI = AbsTol(1)
1342      DO 70 I = 1,N
1343        IF (ITOL .GE. 3) RelTolI = RelTol(I)
1344        IF (ITOL .EQ. 2 .OR. ITOL .EQ. 4) AbsTolI = AbsTol(I)
1345        IF (RelTolI .LT. ZERO) GO TO 619
1346        IF (AbsTolI .LT. ZERO) GO TO 620
1347 70     CONTINUE
1348      IF (ISTATE .EQ. 1) GO TO 100
1349C If ISTATE = 3, set flag to signal parameter changes to DVSTEP. -------
1350      JSTART = -1
1351      IF (NQ .LE. MAXORD) GO TO 90
1352C MAXORD was reduced below NQ.  Copy YH(*,MAXORD+2) into SAVF. ---------
1353      CALL DCOPY (N, RWORK(LWM), 1, RWORK(LSAVF), 1)
1354C Reload WM(1) = RWORK(LWM), since LWM may have changed. ---------------
1355 90   IF (MITER .GT. 0) RWORK(LWM) = SQRT(UROUND)
1356C-----------------------------------------------------------------------
1357C Block C.
1358C The next block is for the initial CALL only (ISTATE = 1).
1359C It contains all remaining initializations, the initial CALL to F,
1360C and the calculation of the initial step size.
1361C The error weights in EWT are inverted after being loaded.
1362C-----------------------------------------------------------------------
1363 100  UROUND = D1MACH(4)
1364      TN = T
1365      IF (ITASK .NE. 4 .AND. ITASK .NE. 5) GO TO 110
1366      TCRIT = RWORK(1)
1367      IF ((TCRIT - TOUT)*(TOUT - T) .LT. ZERO) GO TO 625
1368      IF (H0 .NE. ZERO .AND. (T + H0 - TCRIT)*H0 .GT. ZERO)
1369     1   H0 = TCRIT - T
1370 110  JSTART = 0
1371      IF (MITER .GT. 0) RWORK(LWM) = SQRT(UROUND)
1372      CCMXJ = PT2
1373      MSBJ = 50
1374      NHNIL = 0
1375      NST = 0
1376      NJE = 0
1377      NNI = 0
1378      NCFN = 0
1379      NETF = 0
1380      NLU = 0
1381      NSLJ = 0
1382      NSLAST = 0
1383      HU = ZERO
1384      NQU = 0
1385C Initial CALL to F.  (LF0 points to YH(*,2).) -------------------------
1386      LF0 = LYH + NYH
1387      CALL F (N, T, Y, RWORK(LF0))
1388      NFE = 1
1389C Load the initial value vector in YH. ---------------------------------
1390      CALL DCOPY (N, Y, 1, RWORK(LYH), 1)
1391C Load and invert the EWT array.  (H is temporarily set to 1.0.) -------
1392      NQ = 1
1393      H = ONE
1394      CALL DEWSET (N, ITOL, RelTol, AbsTol, RWORK(LYH), RWORK(LEWT))
1395      DO 120 I = 1,N
1396        IF (RWORK(I+LEWT-1) .LE. ZERO) GO TO 621
1397 120    RWORK(I+LEWT-1) = ONE/RWORK(I+LEWT-1)
1398      IF (H0 .NE. ZERO) GO TO 180
1399C Call DVHIN to set initial step size H0 to be attempted. --------------
1400      CALL DVHIN (N, T, RWORK(LYH), RWORK(LF0), F, RPAR, IPAR, TOUT,
1401     1   UROUND, RWORK(LEWT), ITOL, AbsTol, Y, RWORK(LACOR), H0,
1402     2   NITER, IER)
1403      NFE = NFE + NITER
1404      IF (IER .NE. 0) GO TO 622
1405C Adjust H0 if necessary to meet HMAX bound. ---------------------------
1406 180  RH = ABS(H0)*HMXI
1407      IF (RH .GT. ONE) H0 = H0/RH
1408C Load H with H0 and scale YH(*,2) by H0. ------------------------------
1409      H = H0
1410      CALL DSCAL (N, H0, RWORK(LF0), 1)
1411      GO TO 270
1412C-----------------------------------------------------------------------
1413C Block D.
1414C The next code block is for continuation calls only (ISTATE = 2 or 3)
1415C and is to check stop conditions before taking a step.
1416C-----------------------------------------------------------------------
1417 200  NSLAST = NST
1418      KUTH = 0
1419      GO TO (210, 250, 220, 230, 240), ITASK
1420 210  IF ((TN - TOUT)*H .LT. ZERO) GO TO 250
1421      CALL DVINDY (TOUT, 0, RWORK(LYH), NYH, Y, IFLAG)
1422      IF (IFLAG .NE. 0) GO TO 627
1423      T = TOUT
1424      GO TO 420
1425 220  TP = TN - HU*(ONE + HUN*UROUND)
1426      IF ((TP - TOUT)*H .GT. ZERO) GO TO 623
1427      IF ((TN - TOUT)*H .LT. ZERO) GO TO 250
1428      GO TO 400
1429 230  TCRIT = RWORK(1)
1430      IF ((TN - TCRIT)*H .GT. ZERO) GO TO 624
1431      IF ((TCRIT - TOUT)*H .LT. ZERO) GO TO 625
1432      IF ((TN - TOUT)*H .LT. ZERO) GO TO 245
1433      CALL DVINDY (TOUT, 0, RWORK(LYH), NYH, Y, IFLAG)
1434      IF (IFLAG .NE. 0) GO TO 627
1435      T = TOUT
1436      GO TO 420
1437 240  TCRIT = RWORK(1)
1438      IF ((TN - TCRIT)*H .GT. ZERO) GO TO 624
1439 245  HMX = ABS(TN) + ABS(H)
1440      IHIT = ABS(TN - TCRIT) .LE. HUN*UROUND*HMX
1441      IF (IHIT) GO TO 400
1442      TNEXT = TN + HNEW*(ONE + FOUR*UROUND)
1443      IF ((TNEXT - TCRIT)*H .LE. ZERO) GO TO 250
1444      H = (TCRIT - TN)*(ONE - FOUR*UROUND)
1445      KUTH = 1
1446C-----------------------------------------------------------------------
1447C Block E.
1448C The next block is normally executed for all calls and contains
1449C the CALL to the one-step core integrator DVSTEP.
1450C
1451C This is a looping point for the integration steps.
1452C
1453C First check for too many steps being taken, update EWT (if not at
1454C start of problem), check for too much accuracy being requested, and
1455C check for H below the roundoff level in T.
1456C-----------------------------------------------------------------------
1457 250  CONTINUE
1458      IF ((NST-NSLAST) .GE. MXSTEP) GO TO 500
1459      CALL DEWSET (N, ITOL, RelTol, AbsTol, RWORK(LYH), RWORK(LEWT))
1460      DO 260 I = 1,N
1461        IF (RWORK(I+LEWT-1) .LE. ZERO) GO TO 510
1462 260    RWORK(I+LEWT-1) = ONE/RWORK(I+LEWT-1)
1463 270  TOLSF = UROUND*DVNORM (N, RWORK(LYH), RWORK(LEWT))
1464      IF (TOLSF .LE. ONE) GO TO 280
1465      TOLSF = TOLSF*TWO
1466      IF (NST .EQ. 0) GO TO 626
1467      GO TO 520
1468 280  IF ((TN + H) .NE. TN) GO TO 290
1469      NHNIL = NHNIL + 1
1470      IF (NHNIL .GT. MXHNIL) GO TO 290
1471      MSG = 'DVODE--  Warning..internal T (=R1) and H (=R2) are'
1472      CALL XERRWD (MSG, 50, 101, 1, 0, 0, 0, 0, ZERO, ZERO)
1473      MSG='      such that in the machine, T + H = T on the next step  '
1474      CALL XERRWD (MSG, 60, 101, 1, 0, 0, 0, 0, ZERO, ZERO)
1475      MSG = '      (H = step size). solver will continue anyway'
1476      CALL XERRWD (MSG, 50, 101, 1, 0, 0, 0, 2, TN, H)
1477      IF (NHNIL .LT. MXHNIL) GO TO 290
1478      MSG = 'DVODE--  Above warning has been issued I1 times.  '
1479      CALL XERRWD (MSG, 50, 102, 1, 0, 0, 0, 0, ZERO, ZERO)
1480      MSG = '      it will not be issued again for this problem'
1481      CALL XERRWD (MSG, 50, 102, 1, 1, MXHNIL, 0, 0, ZERO, ZERO)
1482 290  CONTINUE
1483C-----------------------------------------------------------------------
1484C CALL DVSTEP (Y, YH, NYH, YH, EWT, SAVF, VSAV, ACOR,
1485C              WM, IWM, F, JAC, F, DVNLSD, RPAR, IPAR)
1486C-----------------------------------------------------------------------
1487      CALL DVSTEP (Y, RWORK(LYH), NYH, RWORK(LYH), RWORK(LEWT),
1488     1   RWORK(LSAVF), Y, RWORK(LACOR), RWORK(LWM), IWORK(LIWM),
1489     2   F, JAC, F, DVNLSD, RPAR, IPAR)
1490      KGO = 1 - KFLAG
1491C Branch on KFLAG.  Note..In this version, KFLAG can not be set to -3.
1492C  KFLAG .eq. 0,   -1,  -2
1493      GO TO (300, 530, 540), KGO
1494C-----------------------------------------------------------------------
1495C Block F.
1496C The following block handles the case of a successful return from the
1497C core integrator (KFLAG = 0).  Test for stop conditions.
1498C-----------------------------------------------------------------------
1499 300  INIT = 1
1500      KUTH = 0
1501      GO TO (310, 400, 330, 340, 350), ITASK
1502C ITASK = 1.  If TOUT has been reached, interpolate. -------------------
1503 310  IF ((TN - TOUT)*H .LT. ZERO) GO TO 250
1504      CALL DVINDY (TOUT, 0, RWORK(LYH), NYH, Y, IFLAG)
1505      T = TOUT
1506      GO TO 420
1507C ITASK = 3.  Jump to exit if TOUT was reached. ------------------------
1508 330  IF ((TN - TOUT)*H .GE. ZERO) GO TO 400
1509      GO TO 250
1510C ITASK = 4.  See if TOUT or TCRIT was reached.  Adjust H if necessary.
1511 340  IF ((TN - TOUT)*H .LT. ZERO) GO TO 345
1512      CALL DVINDY (TOUT, 0, RWORK(LYH), NYH, Y, IFLAG)
1513      T = TOUT
1514      GO TO 420
1515 345  HMX = ABS(TN) + ABS(H)
1516      IHIT = ABS(TN - TCRIT) .LE. HUN*UROUND*HMX
1517      IF (IHIT) GO TO 400
1518      TNEXT = TN + HNEW*(ONE + FOUR*UROUND)
1519      IF ((TNEXT - TCRIT)*H .LE. ZERO) GO TO 250
1520      H = (TCRIT - TN)*(ONE - FOUR*UROUND)
1521      KUTH = 1
1522      GO TO 250
1523C ITASK = 5.  See if TCRIT was reached and jump to exit. ---------------
1524 350  HMX = ABS(TN) + ABS(H)
1525      IHIT = ABS(TN - TCRIT) .LE. HUN*UROUND*HMX
1526C-----------------------------------------------------------------------
1527C Block G.
1528C The following block handles all successful returns from DVODE.
1529C If ITASK .ne. 1, Y is loaded from YH and T is set accordingly.
1530C ISTATE is set to 2, and the optional output is loaded into the work
1531C arrays before returning.
1532C-----------------------------------------------------------------------
1533 400  CONTINUE
1534      CALL DCOPY (N, RWORK(LYH), 1, Y, 1)
1535      T = TN
1536      IF (ITASK .NE. 4 .AND. ITASK .NE. 5) GO TO 420
1537      IF (IHIT) T = TCRIT
1538 420  ISTATE = 2
1539      RWORK(11) = HU
1540      RWORK(12) = HNEW
1541      RWORK(13) = TN
1542      IWORK(11) = NST
1543      IWORK(12) = NFE
1544      IWORK(13) = NJE
1545      IWORK(14) = NQU
1546      IWORK(15) = NEWQ
1547      IWORK(19) = NLU
1548      IWORK(20) = NNI
1549      IWORK(21) = NCFN
1550      IWORK(22) = NETF
1551      RETURN
1552C-----------------------------------------------------------------------
1553C Block H.
1554C The following block handles all unsuccessful returns other than
1555C those for illegal input.  First the error message routine is called.
1556C if there was an error test or convergence test failure, IMXER is set.
1557C Then Y is loaded from YH, T is set to TN, and the illegal input
1558C The optional output is loaded into the work arrays before returning.
1559C-----------------------------------------------------------------------
1560C The maximum number of steps was taken before reaching TOUT. ----------
1561 500  MSG = 'DVODE--  At current T (=R1), MXSTEP (=I1) steps   '
1562      CALL XERRWD (MSG, 50, 201, 1, 0, 0, 0, 0, ZERO, ZERO)
1563      MSG = '      taken on this CALL before reaching TOUT     '
1564      CALL XERRWD (MSG, 50, 201, 1, 1, MXSTEP, 0, 1, TN, ZERO)
1565      ISTATE = -1
1566      GO TO 580
1567C EWT(i) .le. 0.0 for some i (not at start of problem). ----------------
1568 510  EWTI = RWORK(LEWT+I-1)
1569      MSG = 'DVODE--  At T (=R1), EWT(I1) has become R2 .le. 0.'
1570      CALL XERRWD (MSG, 50, 202, 1, 1, I, 0, 2, TN, EWTI)
1571      ISTATE = -6
1572      GO TO 580
1573C Too much accuracy requested for machine precision. -------------------
1574 520  MSG = 'DVODE--  At T (=R1), too much accuracy requested  '
1575      CALL XERRWD (MSG, 50, 203, 1, 0, 0, 0, 0, ZERO, ZERO)
1576      MSG = '      for precision of machine..  see TOLSF (=R2) '
1577      CALL XERRWD (MSG, 50, 203, 1, 0, 0, 0, 2, TN, TOLSF)
1578      RWORK(14) = TOLSF
1579      ISTATE = -2
1580      GO TO 580
1581C KFLAG = -1.  Error test failed repeatedly or with ABS(H) = HMIN. -----
1582 530  MSG = 'DVODE--  At T(=R1) and step size H(=R2), the error'
1583      CALL XERRWD (MSG, 50, 204, 1, 0, 0, 0, 0, ZERO, ZERO)
1584      MSG = '      test failed repeatedly or with abs(H) = HMIN'
1585      CALL XERRWD (MSG, 50, 204, 1, 0, 0, 0, 2, TN, H)
1586      ISTATE = -4
1587      GO TO 560
1588C KFLAG = -2.  Convergence failed repeatedly or with abs(H) = HMIN. ----
1589 540  MSG = 'DVODE--  At T (=R1) and step size H (=R2), the    '
1590      CALL XERRWD (MSG, 50, 205, 1, 0, 0, 0, 0, ZERO, ZERO)
1591      MSG = '      corrector convergence failed repeatedly     '
1592      CALL XERRWD (MSG, 50, 205, 1, 0, 0, 0, 0, ZERO, ZERO)
1593      MSG = '      or with abs(H) = HMIN   '
1594      CALL XERRWD (MSG, 30, 205, 1, 0, 0, 0, 2, TN, H)
1595      ISTATE = -5
1596C Compute IMXER if relevant. -------------------------------------------
1597 560  BIG = ZERO
1598      IMXER = 1
1599      DO 570 I = 1,N
1600        SIZE = ABS(RWORK(I+LACOR-1)*RWORK(I+LEWT-1))
1601        IF (BIG .GE. SIZE) GO TO 570
1602        BIG = SIZE
1603        IMXER = I
1604 570    CONTINUE
1605      IWORK(16) = IMXER
1606C Set Y vector, T, and optional output. --------------------------------
1607 580  CONTINUE
1608      CALL DCOPY (N, RWORK(LYH), 1, Y, 1)
1609      T = TN
1610      RWORK(11) = HU
1611      RWORK(12) = H
1612      RWORK(13) = TN
1613      IWORK(11) = NST
1614      IWORK(12) = NFE
1615      IWORK(13) = NJE
1616      IWORK(14) = NQU
1617      IWORK(15) = NQ
1618      IWORK(19) = NLU
1619      IWORK(20) = NNI
1620      IWORK(21) = NCFN
1621      IWORK(22) = NETF
1622      RETURN
1623C-----------------------------------------------------------------------
1624C Block I.
1625C The following block handles all error returns due to illegal input
1626C (ISTATE = -3), as detected before calling the core integrator.
1627C First the error message routine is called.   If the illegal input
1628C is a negative ISTATE, the run is aborted (apparent infinite loop).
1629C-----------------------------------------------------------------------
1630 601  MSG = 'DVODE--  ISTATE (=I1) illegal '
1631      CALL XERRWD (MSG, 30, 1, 1, 1, ISTATE, 0, 0, ZERO, ZERO)
1632      IF (ISTATE .LT. 0) GO TO 800
1633      GO TO 700
1634 602  MSG = 'DVODE--  ITASK (=I1) illegal  '
1635      CALL XERRWD (MSG, 30, 2, 1, 1, ITASK, 0, 0, ZERO, ZERO)
1636      GO TO 700
1637 603  MSG='DVODE--  ISTATE (=I1) .gt. 1 but DVODE not initialized      '
1638      CALL XERRWD (MSG, 60, 3, 1, 1, ISTATE, 0, 0, ZERO, ZERO)
1639      GO TO 700
1640 604  MSG = 'DVODE--  NEQ (=I1) .lt. 1     '
1641      CALL XERRWD (MSG, 30, 4, 1, 1, NEQ, 0, 0, ZERO, ZERO)
1642      GO TO 700
1643 605  MSG = 'DVODE--  ISTATE = 3 and NEQ increased (I1 to I2)  '
1644      CALL XERRWD (MSG, 50, 5, 1, 2, N, NEQ, 0, ZERO, ZERO)
1645      GO TO 700
1646 606  MSG = 'DVODE--  ITOL (=I1) illegal   '
1647      CALL XERRWD (MSG, 30, 6, 1, 1, ITOL, 0, 0, ZERO, ZERO)
1648      GO TO 700
1649 607  MSG = 'DVODE--  IOPT (=I1) illegal   '
1650      CALL XERRWD (MSG, 30, 7, 1, 1, IOPT, 0, 0, ZERO, ZERO)
1651      GO TO 700
1652 608  MSG = 'DVODE--  MF (=I1) illegal     '
1653      CALL XERRWD (MSG, 30, 8, 1, 1, MF, 0, 0, ZERO, ZERO)
1654      GO TO 700
1655 609  MSG = 'DVODE--  ML (=I1) illegal.. .lt.0 or .ge.NEQ (=I2)'
1656      CALL XERRWD (MSG, 50, 9, 1, 2, ML, NEQ, 0, ZERO, ZERO)
1657      GO TO 700
1658 610  MSG = 'DVODE--  MU (=I1) illegal.. .lt.0 or .ge.NEQ (=I2)'
1659      CALL XERRWD (MSG, 50, 10, 1, 2, MU, NEQ, 0, ZERO, ZERO)
1660      GO TO 700
1661 611  MSG = 'DVODE--  MAXORD (=I1) .lt. 0  '
1662      CALL XERRWD (MSG, 30, 11, 1, 1, MAXORD, 0, 0, ZERO, ZERO)
1663      GO TO 700
1664 612  MSG = 'DVODE--  MXSTEP (=I1) .lt. 0  '
1665      CALL XERRWD (MSG, 30, 12, 1, 1, MXSTEP, 0, 0, ZERO, ZERO)
1666      GO TO 700
1667 613  MSG = 'DVODE--  MXHNIL (=I1) .lt. 0  '
1668      CALL XERRWD (MSG, 30, 13, 1, 1, MXHNIL, 0, 0, ZERO, ZERO)
1669      GO TO 700
1670 614  MSG = 'DVODE--  TOUT (=R1) behind T (=R2)      '
1671      CALL XERRWD (MSG, 40, 14, 1, 0, 0, 0, 2, TOUT, T)
1672      MSG = '      integration direction is given by H0 (=R1)  '
1673      CALL XERRWD (MSG, 50, 14, 1, 0, 0, 0, 1, H0, ZERO)
1674      GO TO 700
1675 615  MSG = 'DVODE--  HMAX (=R1) .lt. 0.0  '
1676      CALL XERRWD (MSG, 30, 15, 1, 0, 0, 0, 1, HMAX, ZERO)
1677      GO TO 700
1678 616  MSG = 'DVODE--  HMIN (=R1) .lt. 0.0  '
1679      CALL XERRWD (MSG, 30, 16, 1, 0, 0, 0, 1, HMIN, ZERO)
1680      GO TO 700
1681 617  CONTINUE
1682      MSG='DVODE--  RWORK length needed, LENRW (=I1), exceeds LRW (=I2)'
1683      CALL XERRWD (MSG, 60, 17, 1, 2, LENRW, LRW, 0, ZERO, ZERO)
1684      GO TO 700
1685 618  CONTINUE
1686      MSG='DVODE--  IWORK length needed, LENIW (=I1), exceeds LIW (=I2)'
1687      CALL XERRWD (MSG, 60, 18, 1, 2, LENIW, LIW, 0, ZERO, ZERO)
1688      GO TO 700
1689 619  MSG = 'DVODE--  RelTol(I1) is R1 .lt. 0.0        '
1690      CALL XERRWD (MSG, 40, 19, 1, 1, I, 0, 1, RelTolI, ZERO)
1691      GO TO 700
1692 620  MSG = 'DVODE--  AbsTol(I1) is R1 .lt. 0.0        '
1693      CALL XERRWD (MSG, 40, 20, 1, 1, I, 0, 1, AbsTolI, ZERO)
1694      GO TO 700
1695 621  EWTI = RWORK(LEWT+I-1)
1696      MSG = 'DVODE--  EWT(I1) is R1 .le. 0.0         '
1697      CALL XERRWD (MSG, 40, 21, 1, 1, I, 0, 1, EWTI, ZERO)
1698      GO TO 700
1699 622  CONTINUE
1700      MSG='DVODE--  TOUT (=R1) too close to T(=R2) to start integration'
1701      CALL XERRWD (MSG, 60, 22, 1, 0, 0, 0, 2, TOUT, T)
1702      GO TO 700
1703 623  CONTINUE
1704      MSG='DVODE--  ITASK = I1 and TOUT (=R1) behind TCUR - HU (= R2)  '
1705      CALL XERRWD (MSG, 60, 23, 1, 1, ITASK, 0, 2, TOUT, TP)
1706      GO TO 700
1707 624  CONTINUE
1708      MSG='DVODE--  ITASK = 4 or 5 and TCRIT (=R1) behind TCUR (=R2)   '
1709      CALL XERRWD (MSG, 60, 24, 1, 0, 0, 0, 2, TCRIT, TN)
1710      GO TO 700
1711 625  CONTINUE
1712      MSG='DVODE--  ITASK = 4 or 5 and TCRIT (=R1) behind TOUT (=R2)   '
1713      CALL XERRWD (MSG, 60, 25, 1, 0, 0, 0, 2, TCRIT, TOUT)
1714      GO TO 700
1715 626  MSG = 'DVODE--  At start of problem, too much accuracy   '
1716      CALL XERRWD (MSG, 50, 26, 1, 0, 0, 0, 0, ZERO, ZERO)
1717      MSG='      requested for precision of machine..  see TOLSF (=R1) '
1718      CALL XERRWD (MSG, 60, 26, 1, 0, 0, 0, 1, TOLSF, ZERO)
1719      RWORK(14) = TOLSF
1720      GO TO 700
1721 627  MSG='DVODE--  Trouble from DVINDY.  ITASK = I1, TOUT = R1.       '
1722      CALL XERRWD (MSG, 60, 27, 1, 1, ITASK, 0, 1, TOUT, ZERO)
1723C
1724 700  CONTINUE
1725      ISTATE = -3
1726      RETURN
1727C
1728 800  MSG = 'DVODE--  Run aborted.. apparent infinite loop     '
1729      CALL XERRWD (MSG, 50, 303, 2, 0, 0, 0, 0, ZERO, ZERO)
1730      RETURN
1731C----------------------- End of Subroutine DVODE -----------------------
1732      END
1733*DECK DVHIN
1734      SUBROUTINE DVHIN (N, T0, Y0, YDOT, F, RPAR, IPAR, TOUT, UROUND,
1735     1   EWT, ITOL, AbsTol, Y, TEMP, H0, NITER, IER)
1736      EXTERNAL F
1737      KPP_REAL T0, Y0, YDOT, RPAR, TOUT, UROUND, EWT, AbsTol, Y,
1738     1   TEMP, H0
1739      INTEGER N, IPAR, ITOL, NITER, IER
1740      DIMENSION Y0(*), YDOT(*), EWT(*), AbsTol(*), Y(*),
1741     1   TEMP(*), RPAR(*), IPAR(*)
1742C-----------------------------------------------------------------------
1743C Call sequence input -- N, T0, Y0, YDOT, F, RPAR, IPAR, TOUT, UROUND,
1744C                        EWT, ITOL, AbsTol, Y, TEMP
1745C Call sequence output -- H0, NITER, IER
1746C COMMON block variables accessed -- None
1747C
1748C Subroutines called by DVHIN.. F
1749C Function routines called by DVHIN.. DVNORM
1750C-----------------------------------------------------------------------
1751C This routine computes the step size, H0, to be attempted on the
1752C first step, when the user has not supplied a value for this.
1753C
1754C First we check that TOUT - T0 differs significantly from zero.  Then
1755C an iteration is done to approximate the initial second derivative
1756C and this is used to define h from w.r.m.s.norm(h**2 * yddot / 2) = 1.
1757C A bias factor of 1/2 is applied to the resulting h.
1758C The sign of H0 is inferred from the initial values of TOUT and T0.
1759C
1760C Communication with DVHIN is done with the following variables..
1761C
1762C N      = Size of ODE system, input.
1763C T0     = Initial value of independent variable, input.
1764C Y0     = Vector of initial conditions, input.
1765C YDOT   = Vector of initial first derivatives, input.
1766C F      = Name of subroutine for right-hand side f(t,y), input.
1767C RPAR, IPAR = Dummy names for user's real and integer work arrays.
1768C TOUT   = First output value of independent variable
1769C UROUND = Machine unit roundoff
1770C EWT, ITOL, AbsTol = Error weights and tolerance parameters
1771C                   as described in the driver routine, input.
1772C Y, TEMP = Work arrays of length N.
1773C H0     = Step size to be attempted, output.
1774C NITER  = Number of iterations (and of f evaluations) to compute H0,
1775C          output.
1776C IER    = The error flag, returned with the value
1777C          IER = 0  if no trouble occurred, or
1778C          IER = -1 if TOUT and T0 are considered too close to proceed.
1779C-----------------------------------------------------------------------
1780C
1781C Type declarations for local variables --------------------------------
1782C
1783      KPP_REAL AFI, AbsTolI, DELYI, HALF, HG, HLB, HNEW, HRAT,
1784     1     HUB, HUN, PT1, T1, TDIST, TROUND, TWO, YDDNRM
1785      INTEGER I, ITER
1786
1787C
1788C Type declaration for function subroutines called ---------------------
1789C
1790      KPP_REAL DVNORM
1791C-----------------------------------------------------------------------
1792C The following Fortran-77 declaration is to cause the values of the
1793C listed (local) variables to be saved between calls to this integrator.
1794C-----------------------------------------------------------------------
1795      SAVE HALF, HUN, PT1, TWO
1796      DATA HALF /0.5D0/, HUN /100.0D0/, PT1 /0.1D0/, TWO /2.0D0/
1797C
1798      NITER = 0
1799      TDIST = ABS(TOUT - T0)
1800      TROUND = UROUND*MAX(ABS(T0),ABS(TOUT))
1801      IF (TDIST .LT. TWO*TROUND) GO TO 100
1802C
1803C Set a lower bound on h based on the roundoff level in T0 and TOUT. ---
1804      HLB = HUN*TROUND
1805C Set an upper bound on h based on TOUT-T0 and the initial Y and YDOT. -
1806      HUB = PT1*TDIST
1807      AbsTolI = AbsTol(1)
1808      DO 10 I = 1, N
1809        IF (ITOL .EQ. 2 .OR. ITOL .EQ. 4) AbsTolI = AbsTol(I)
1810        DELYI = PT1*ABS(Y0(I)) + AbsTolI
1811        AFI = ABS(YDOT(I))
1812        IF (AFI*HUB .GT. DELYI) HUB = DELYI/AFI
1813 10     CONTINUE
1814C
1815C Set initial guess for h as geometric mean of upper and lower bounds. -
1816      ITER = 0
1817      HG = SQRT(HLB*HUB)
1818C If the bounds have crossed, exit with the mean value. ----------------
1819      IF (HUB .LT. HLB) THEN
1820        H0 = HG
1821        GO TO 90
1822      ENDIF
1823C
1824C Looping point for iteration. -----------------------------------------
1825 50   CONTINUE
1826C Estimate the second derivative as a difference quotient in f. --------
1827      T1 = T0 + HG
1828      DO 60 I = 1, N
1829 60     Y(I) = Y0(I) + HG*YDOT(I)
1830      CALL F (N, T1, Y, TEMP)
1831      DO 70 I = 1, N
1832 70     TEMP(I) = (TEMP(I) - YDOT(I))/HG
1833      YDDNRM = DVNORM (N, TEMP, EWT)
1834C Get the corresponding new value of h. --------------------------------
1835      IF (YDDNRM*HUB*HUB .GT. TWO) THEN
1836        HNEW = SQRT(TWO/YDDNRM)
1837      ELSE
1838        HNEW = SQRT(HG*HUB)
1839      ENDIF
1840      ITER = ITER + 1
1841C-----------------------------------------------------------------------
1842C Test the stopping conditions.
1843C Stop if the new and previous h values differ by a factor of .lt. 2.
1844C Stop if four iterations have been done.  Also, stop with previous h
1845C if HNEW/HG .gt. 2 after first iteration, as this probably means that
1846C the second derivative value is bad because of cancellation error.
1847C-----------------------------------------------------------------------
1848      IF (ITER .GE. 4) GO TO 80
1849      HRAT = HNEW/HG
1850C AICI
1851      IF ( (HRAT .GT. HALF) .AND. (HRAT .LT. TWO) ) GO TO 80
1852      IF ( (ITER .GE. 2) .AND. (HNEW .GT. TWO*HG) ) THEN
1853        HNEW = HG
1854        GO TO 80
1855      ENDIF
1856      HG = HNEW
1857      GO TO 50
1858C
1859C Iteration done.  Apply bounds, bias factor, and sign.  Then exit. ----
1860 80   H0 = HNEW*HALF
1861      IF (H0 .LT. HLB) H0 = HLB
1862      IF (H0 .GT. HUB) H0 = HUB
1863 90   H0 = SIGN(H0, TOUT - T0)
1864      NITER = ITER
1865      IER = 0
1866      RETURN
1867C Error return for TOUT - T0 too small. --------------------------------
1868 100  IER = -1
1869      RETURN
1870C----------------------- End of Subroutine DVHIN -----------------------
1871      END
1872*DECK DVINDY
1873      SUBROUTINE DVINDY (T, K, YH, LDYH, DKY, IFLAG)
1874      KPP_REAL T, YH, DKY
1875      INTEGER K, LDYH, IFLAG
1876      DIMENSION YH(LDYH,*), DKY(*)
1877C-----------------------------------------------------------------------
1878C Call sequence input -- T, K, YH, LDYH
1879C Call sequence output -- DKY, IFLAG
1880C COMMON block variables accessed..
1881C     /DVOD01/ --  H, TN, UROUND, L, N, NQ
1882C     /DVOD02/ --  HU
1883C
1884C Subroutines called by DVINDY.. DSCAL, XERRWD
1885C Function routines called by DVINDY.. None
1886C-----------------------------------------------------------------------
1887C DVINDY computes interpolated values of the K-th derivative of the
1888C dependent variable vector y, and stores it in DKY.  This routine
1889C is called within the package with K = 0 and T = TOUT, but may
1890C also be called by the user for any K up to the current order.
1891C (See detailed instructions in the usage documentation.)
1892C-----------------------------------------------------------------------
1893C The computed values in DKY are gotten by interpolation using the
1894C Nordsieck history array YH.  This array corresponds uniquely to a
1895C vector-valued polynomial of degree NQCUR or less, and DKY is set
1896C to the K-th derivative of this polynomial at T.
1897C The formula for DKY is..
1898C              q
1899C  DKY(i)  =  sum  c(j,K) * (T - TN)**(j-K) * H**(-j) * YH(i,j+1)
1900C             j=K
1901C where  c(j,K) = j*(j-1)*...*(j-K+1), q = NQCUR, TN = TCUR, H = HCUR.
1902C The quantities  NQ = NQCUR, L = NQ+1, N, TN, and H are
1903C communicated by COMMON.  The above sum is done in reverse order.
1904C IFLAG is returned negative if either K or T is out of bounds.
1905C
1906C Discussion above and comments in driver explain all variables.
1907C-----------------------------------------------------------------------
1908C
1909C Type declarations for labeled COMMON block DVOD01 --------------------
1910C
1911      KPP_REAL ACNRM, CCMXJ, CONP, CRATE, DRC, EL,
1912     1     ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
1913     2     RC, RL1, TAU, TQ, TN, UROUND
1914      INTEGER ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
1915     1        L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
1916     2        LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
1917     3        N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
1918     4        NSLP, NYH
1919C
1920C Type declarations for labeled COMMON block DVOD02 --------------------
1921C
1922      KPP_REAL HU
1923      INTEGER NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
1924C
1925C Type declarations for local variables --------------------------------
1926C
1927      KPP_REAL C, HUN, R, S, TFUZZ, TN1, TP, ZERO
1928      INTEGER I, IC, J, JB, JB2, JJ, JJ1, JP1
1929      CHARACTER*80 MSG
1930C-----------------------------------------------------------------------
1931C The following Fortran-77 declaration is to cause the values of the
1932C listed (local) variables to be saved between calls to this integrator.
1933C-----------------------------------------------------------------------
1934      SAVE HUN, ZERO
1935C
1936      COMMON /DVOD01/ ACNRM, CCMXJ, CONP, CRATE, DRC, EL(13),
1937     1                ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
1938     2                RC, RL1, TAU(13), TQ(5), TN, UROUND,
1939     3                ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
1940     4                L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
1941     5                LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
1942     6                N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
1943     7                NSLP, NYH
1944      COMMON /DVOD02/ HU, NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
1945C
1946      DATA HUN /100.0D0/, ZERO /0.0D0/
1947C
1948      IFLAG = 0
1949      IF (K .LT. 0 .OR. K .GT. NQ) GO TO 80
1950      TFUZZ = HUN*UROUND*(TN + HU)
1951      TP = TN - HU - TFUZZ
1952      TN1 = TN + TFUZZ
1953      IF ((T-TP)*(T-TN1) .GT. ZERO) GO TO 90
1954C
1955      S = (T - TN)/H
1956      IC = 1
1957      IF (K .EQ. 0) GO TO 15
1958      JJ1 = L - K
1959      DO 10 JJ = JJ1, NQ
1960 10     IC = IC*JJ
1961 15   C = REAL(IC)
1962      DO 20 I = 1, N
1963 20     DKY(I) = C*YH(I,L)
1964      IF (K .EQ. NQ) GO TO 55
1965      JB2 = NQ - K
1966      DO 50 JB = 1, JB2
1967        J = NQ - JB
1968        JP1 = J + 1
1969        IC = 1
1970        IF (K .EQ. 0) GO TO 35
1971        JJ1 = JP1 - K
1972        DO 30 JJ = JJ1, J
1973 30       IC = IC*JJ
1974 35     C = REAL(IC)
1975        DO 40 I = 1, N
1976 40       DKY(I) = C*YH(I,JP1) + S*DKY(I)
1977 50     CONTINUE
1978      IF (K .EQ. 0) RETURN
1979 55   R = H**(-K)
1980      CALL DSCAL (N, R, DKY, 1)
1981      RETURN
1982C
1983 80   MSG = 'DVINDY-- K (=I1) illegal      '
1984      CALL XERRWD (MSG, 30, 51, 1, 1, K, 0, 0, ZERO, ZERO)
1985      IFLAG = -1
1986      RETURN
1987 90   MSG = 'DVINDY-- T (=R1) illegal      '
1988      CALL XERRWD (MSG, 30, 52, 1, 0, 0, 0, 1, T, ZERO)
1989      MSG='      T not in interval TCUR - HU (= R1) to TCUR (=R2)      '
1990      CALL XERRWD (MSG, 60, 52, 1, 0, 0, 0, 2, TP, TN)
1991      IFLAG = -2
1992      RETURN
1993C----------------------- End of Subroutine DVINDY ----------------------
1994      END
1995*DECK DVSTEP
1996      SUBROUTINE DVSTEP (Y, YH, LDYH, YH1, EWT, SAVF, VSAV, ACOR,
1997     1                  WM, IWM, F, JAC, PSOL, VNLS, RPAR, IPAR)
1998      EXTERNAL F, JAC, PSOL, VNLS
1999      KPP_REAL Y, YH, YH1, EWT, SAVF, VSAV, ACOR, WM, RPAR
2000      INTEGER LDYH, IWM, IPAR
2001      DIMENSION Y(*), YH(LDYH,*), YH1(*), EWT(*), SAVF(*), VSAV(*),
2002     1   ACOR(*), WM(*), IWM(*), RPAR(*), IPAR(*)
2003
2004C-----------------------------------------------------------------------
2005C Call sequence input -- Y, YH, LDYH, YH1, EWT, SAVF, VSAV,
2006C                        ACOR, WM, IWM, F, JAC, PSOL, VNLS, RPAR, IPAR
2007C Call sequence output -- YH, ACOR, WM, IWM
2008C COMMON block variables accessed..
2009C     /DVOD01/  ACNRM, EL(13), H, HMIN, HMXI, HNEW, HSCAL, RC, TAU(13),
2010C               TQ(5), TN, JCUR, JSTART, KFLAG, KUTH,
2011C               L, LMAX, MAXORD, MITER, N, NEWQ, NQ, NQWAIT
2012C     /DVOD02/  HU, NCFN, NETF, NFE, NQU, NST
2013C
2014C Subroutines called by DVSTEP.. F, DAXPY, DCOPY, DSCAL,
2015C                               DVJUST, VNLS, DVSET
2016C Function routines called by DVSTEP.. DVNORM
2017C-----------------------------------------------------------------------
2018C DVSTEP performs one step of the integration of an initial value
2019C problem for a system of ordinary differential equations.
2020C DVSTEP calls subroutine VNLS for the solution of the nonlinear system
2021C arising in the time step.  Thus it is independent of the problem
2022C Jacobian structure and the type of nonlinear system solution method.
2023C DVSTEP returns a completion flag KFLAG (in COMMON).
2024C A return with KFLAG = -1 or -2 means either ABS(H) = HMIN or 10
2025C consecutive failures occurred.  On a return with KFLAG negative,
2026C the values of TN and the YH array are as of the beginning of the last
2027C step, and H is the last step size attempted.
2028C
2029C Communication with DVSTEP is done with the following variables..
2030C
2031C Y      = An array of length N used for the dependent variable vector.
2032C YH     = An LDYH by LMAX array containing the dependent variables
2033C          and their approximate scaled derivatives, where
2034C          LMAX = MAXORD + 1.  YH(i,j+1) contains the approximate
2035C          j-th derivative of y(i), scaled by H**j/factorial(j)
2036C          (j = 0,1,...,NQ).  On entry for the first step, the first
2037C          two columns of YH must be set from the initial values.
2038C LDYH   = A constant integer .ge. N, the first dimension of YH.
2039C          N is the number of ODEs in the system.
2040C YH1    = A one-dimensional array occupying the same space as YH.
2041C EWT    = An array of length N containing multiplicative weights
2042C          for local error measurements.  Local errors in y(i) are
2043C          compared to 1.0/EWT(i) in various error tests.
2044C SAVF   = An array of working storage, of length N.
2045C          also used for input of YH(*,MAXORD+2) when JSTART = -1
2046C          and MAXORD .lt. the current order NQ.
2047C VSAV   = A work array of length N passed to subroutine VNLS.
2048C ACOR   = A work array of length N, used for the accumulated
2049C          corrections.  On a successful return, ACOR(i) contains
2050C          the estimated one-step local error in y(i).
2051C WM,IWM = Real and integer work arrays associated with matrix
2052C          operations in VNLS.
2053C F      = Dummy name for the user supplied subroutine for f.
2054C JAC    = Dummy name for the user supplied Jacobian subroutine.
2055C PSOL   = Dummy name for the subroutine passed to VNLS, for
2056C          possible use there.
2057C VNLS   = Dummy name for the nonlinear system solving subroutine,
2058C          whose real name is dependent on the method used.
2059C RPAR, IPAR = Dummy names for user's real and integer work arrays.
2060C-----------------------------------------------------------------------
2061C
2062C Type declarations for labeled COMMON block DVOD01 --------------------
2063C
2064      KPP_REAL ACNRM, CCMXJ, CONP, CRATE, DRC, EL,
2065     1     ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
2066     2     RC, RL1, TAU, TQ, TN, UROUND
2067      INTEGER ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
2068     1        L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
2069     2        LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
2070     3        N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
2071     4        NSLP, NYH
2072C
2073C Type declarations for labeled COMMON block DVOD02 --------------------
2074C
2075      KPP_REAL HU
2076      INTEGER NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
2077C
2078C Type declarations for local variables --------------------------------
2079C
2080      KPP_REAL ADDON, BIAS1,BIAS2,BIAS3, CNQUOT, DDN, DSM, DUP,
2081     1     ETACF, ETAMIN, ETAMX1, ETAMX2, ETAMX3, ETAMXF,
2082     2     ETAQ, ETAQM1, ETAQP1, FLOTL, ONE, ONEPSM,
2083     3     R, THRESH, TOLD, ZERO
2084      INTEGER I, I1, I2, IBACK, J, JB, KFC, KFH, MXNCF, NCF, NFLAG
2085C
2086C Type declaration for function subroutines called ---------------------
2087C
2088      KPP_REAL DVNORM
2089C-----------------------------------------------------------------------
2090C The following Fortran-77 declaration is to cause the values of the
2091C listed (local) variables to be saved between calls to this integrator.
2092C-----------------------------------------------------------------------
2093      SAVE ADDON, BIAS1, BIAS2, BIAS3,
2094     1     ETACF, ETAMIN, ETAMX1, ETAMX2, ETAMX3, ETAMXF,
2095     2     KFC, KFH, MXNCF, ONEPSM, THRESH, ONE, ZERO
2096C-----------------------------------------------------------------------
2097      COMMON /DVOD01/ ACNRM, CCMXJ, CONP, CRATE, DRC, EL(13),
2098     1                ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
2099     2                RC, RL1, TAU(13), TQ(5), TN, UROUND,
2100     3                ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
2101     4                L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
2102     5                LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
2103     6                N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
2104     7                NSLP, NYH
2105      COMMON /DVOD02/ HU, NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
2106C
2107      DATA KFC/-3/, KFH/-7/, MXNCF/10/
2108      DATA ADDON  /1.0D-6/,    BIAS1  /6.0D0/,     BIAS2  /6.0D0/,
2109     1     BIAS3  /10.0D0/,    ETACF  /0.25D0/,    ETAMIN /0.1D0/,
2110     2     ETAMXF /0.2D0/,     ETAMX1 /1.0D4/,     ETAMX2 /10.0D1/,
2111     3     ETAMX3 /10.0D1/,    ONEPSM /1.00001D0/, THRESH /1.5D0/
2112
2113      DATA ONE/1.0D0/, ZERO/0.0D0/
2114C
2115      ETAQ   = ETAMX1
2116      ETAQM1 = ETAMX1
2117      ETAQP1 = ETAMX1
2118      KFLAG = 0
2119      TOLD = TN
2120      NCF = 0
2121      JCUR = 0
2122      NFLAG = 0
2123      IF (JSTART .GT. 0) GO TO 20
2124      IF (JSTART .EQ. -1) GO TO 100
2125C-----------------------------------------------------------------------
2126C On the first call, the order is set to 1, and other variables are
2127C initialized.  ETAMAX is the maximum ratio by which H can be increased
2128C in a single step.  It is normally 1.5, but is larger during the
2129C first 10 steps to compensate for the small initial H.  If a failure
2130C occurs (in corrector convergence or error test), ETAMAX is set to 1
2131C for the next increase.
2132C-----------------------------------------------------------------------
2133      LMAX = MAXORD + 1
2134      NQ = 1
2135      L = 2
2136      NQNYH = NQ*LDYH
2137      TAU(1) = H
2138      PRL1 = ONE
2139      RC = ZERO
2140      ETAMAX = ETAMX1
2141      NQWAIT = 2
2142      HSCAL = H
2143      GO TO 200
2144C-----------------------------------------------------------------------
2145C Take preliminary actions on a normal continuation step (JSTART.GT.0).
2146C If the driver changed H, then ETA must be reset and NEWH set to 1.
2147C If a change of order was dictated on the previous step, then
2148C it is done here and appropriate adjustments in the history are made.
2149C On an order decrease, the history array is adjusted by DVJUST.
2150C On an order increase, the history array is augmented by a column.
2151C On a change of step size H, the history array YH is rescaled.
2152C-----------------------------------------------------------------------
2153 20   CONTINUE
2154      IF (KUTH .EQ. 1) THEN
2155        ETA = MIN(ETA,H/HSCAL)
2156        NEWH = 1
2157        ENDIF
2158 50   IF (NEWH .EQ. 0) GO TO 200
2159      IF (NEWQ .EQ. NQ) GO TO 150
2160      IF (NEWQ .LT. NQ) THEN
2161        CALL DVJUST (YH, LDYH, -1)
2162        NQ = NEWQ
2163        L = NQ + 1
2164        NQWAIT = L
2165        GO TO 150
2166        ENDIF
2167      IF (NEWQ .GT. NQ) THEN
2168        CALL DVJUST (YH, LDYH, 1)
2169        NQ = NEWQ
2170        L = NQ + 1
2171        NQWAIT = L
2172        GO TO 150
2173      ENDIF
2174C-----------------------------------------------------------------------
2175C The following block handles preliminaries needed when JSTART = -1.
2176C If N was reduced, zero out part of YH to avoid undefined references.
2177C If MAXORD was reduced to a value less than the tentative order NEWQ,
2178C then NQ is set to MAXORD, and a new H ratio ETA is chosen.
2179C Otherwise, we take the same preliminary actions as for JSTART .gt. 0.
2180C In any case, NQWAIT is reset to L = NQ + 1 to prevent further
2181C changes in order for that many steps.
2182C The new H ratio ETA is limited by the input H if KUTH = 1,
2183C by HMIN if KUTH = 0, and by HMXI in any case.
2184C Finally, the history array YH is rescaled.
2185C-----------------------------------------------------------------------
2186 100  CONTINUE
2187      LMAX = MAXORD + 1
2188      IF (N .EQ. LDYH) GO TO 120
2189      I1 = 1 + (NEWQ + 1)*LDYH
2190      I2 = (MAXORD + 1)*LDYH
2191      IF (I1 .GT. I2) GO TO 120
2192      DO 110 I = I1, I2
2193 110    YH1(I) = ZERO
2194 120  IF (NEWQ .LE. MAXORD) GO TO 140
2195      FLOTL = REAL(LMAX)
2196      IF (MAXORD .LT. NQ-1) THEN
2197        DDN = DVNORM (N, SAVF, EWT)/TQ(1)
2198        ETA = ONE/((BIAS1*DDN)**(ONE/FLOTL) + ADDON)
2199        ENDIF
2200      IF (MAXORD .EQ. NQ .AND. NEWQ .EQ. NQ+1) ETA = ETAQ
2201      IF (MAXORD .EQ. NQ-1 .AND. NEWQ .EQ. NQ+1) THEN
2202        ETA = ETAQM1
2203        CALL DVJUST (YH, LDYH, -1)
2204        ENDIF
2205      IF (MAXORD .EQ. NQ-1 .AND. NEWQ .EQ. NQ) THEN
2206        DDN = DVNORM (N, SAVF, EWT)/TQ(1)
2207        ETA = ONE/((BIAS1*DDN)**(ONE/FLOTL) + ADDON)
2208        CALL DVJUST (YH, LDYH, -1)
2209        ENDIF
2210      ETA = MIN(ETA,ONE)
2211      NQ = MAXORD
2212      L = LMAX
2213 140  IF (KUTH .EQ. 1) ETA = MIN(ETA,ABS(H/HSCAL))
2214      IF (KUTH .EQ. 0) ETA = MAX(ETA,HMIN/ABS(HSCAL))
2215      ETA = ETA/MAX(ONE,ABS(HSCAL)*HMXI*ETA)
2216      NEWH = 1
2217      NQWAIT = L
2218      IF (NEWQ .LE. MAXORD) GO TO 50
2219C Rescale the history array for a change in H by a factor of ETA. ------
2220 150  R = ONE
2221      DO 180 J = 2, L
2222        R = R*ETA
2223        CALL DSCAL (N, R, YH(1,J), 1 )
2224 180    CONTINUE
2225      H = HSCAL*ETA
2226      HSCAL = H
2227      RC = RC*ETA
2228      NQNYH = NQ*LDYH
2229C-----------------------------------------------------------------------
2230C This section computes the predicted values by effectively
2231C multiplying the YH array by the Pascal triangle matrix.
2232C DVSET is called to calculate all integration coefficients.
2233C RC is the ratio of new to old values of the coefficient H/EL(2)=h/l1.
2234C-----------------------------------------------------------------------
2235 200  TN = TN + H
2236      I1 = NQNYH + 1
2237      DO 220 JB = 1, NQ
2238        I1 = I1 - LDYH
2239        DO 210 I = I1, NQNYH
2240 210      YH1(I) = YH1(I) + YH1(I+LDYH)
2241 220  CONTINUE
2242      CALL DVSET
2243      RL1 = ONE/EL(2)
2244      RC = RC*(RL1/PRL1)
2245      PRL1 = RL1
2246C
2247C Call the nonlinear system solver. ------------------------------------
2248C
2249      CALL VNLS (Y, YH, LDYH, VSAV, SAVF, EWT, ACOR, IWM, WM,
2250     1           F, JAC, PSOL, NFLAG, RPAR, IPAR)
2251C
2252      IF ((NFLAG .EQ. 0).OR.(H.LE.1.2*HMIN)) GO TO 450
2253C-----------------------------------------------------------------------
2254C The VNLS routine failed to achieve convergence (NFLAG .NE. 0).
2255C The YH array is retracted to its values before prediction.
2256C The step size H is reduced and the step is retried, if possible.
2257C Otherwise, an error exit is taken.
2258C-----------------------------------------------------------------------
2259        NCF = NCF + 1
2260        NCFN = NCFN + 1
2261        ETAMAX = ONE
2262        TN = TOLD
2263        I1 = NQNYH + 1
2264        DO 430 JB = 1, NQ
2265          I1 = I1 - LDYH
2266          DO 420 I = I1, NQNYH
2267 420        YH1(I) = YH1(I) - YH1(I+LDYH)
2268 430      CONTINUE
2269        IF (NFLAG .LT. -1) GO TO 680
2270        IF (ABS(H) .LE. HMIN*ONEPSM) GO TO 670
2271        IF (NCF .EQ. MXNCF) GO TO 670
2272        ETA = ETACF
2273        ETA = MAX(ETA,HMIN/ABS(H))
2274        NFLAG = -1
2275        GO TO 150
2276C-----------------------------------------------------------------------
2277C The corrector has converged (NFLAG = 0).  The local error test is
2278C made and control passes to statement 500 if it fails.
2279C-----------------------------------------------------------------------
2280 450  CONTINUE
2281      DSM = ACNRM/TQ(2)
2282      IF ( (DSM .GT. ONE).and.(H.GT.HMIN) ) GO TO 500
2283C-----------------------------------------------------------------------
2284C After a successful step, update the YH and TAU arrays and decrement
2285C NQWAIT.  If NQWAIT is then 1 and NQ .lt. MAXORD, then ACOR is saved
2286C for use in a possible order increase on the next step.
2287C If ETAMAX = 1 (a failure occurred this step), keep NQWAIT .ge. 2.
2288C-----------------------------------------------------------------------
2289      KFLAG = 0
2290      NST = NST + 1
2291      HU = H
2292      NQU = NQ
2293      DO 470 IBACK = 1, NQ
2294        I = L - IBACK
2295 470    TAU(I+1) = TAU(I)
2296      TAU(1) = H
2297      DO 480 J = 1, L
2298        CALL DAXPY (N, EL(J), ACOR, 1, YH(1,J), 1 )
2299 480    CONTINUE
2300      NQWAIT = NQWAIT - 1
2301      IF ((L .EQ. LMAX) .OR. (NQWAIT .NE. 1)) GO TO 490
2302      CALL DCOPY (N, ACOR, 1, YH(1,LMAX), 1 )
2303      CONP = TQ(5)
2304 490  IF (ETAMAX .NE. ONE) GO TO 560
2305      IF (NQWAIT .LT. 2) NQWAIT = 2
2306      NEWQ = NQ
2307      NEWH = 0
2308      ETA = ONE
2309      HNEW = H
2310      GO TO 690
2311C-----------------------------------------------------------------------
2312C The error test failed.  KFLAG keeps track of multiple failures.
2313C Restore TN and the YH array to their previous values, and prepare
2314C to try the step again.  Compute the optimum step size for the
2315C same order.  After repeated failures, H is forced to decrease
2316C more rapidly.
2317C-----------------------------------------------------------------------
2318 500  KFLAG = KFLAG - 1
2319      NETF = NETF + 1
2320      NFLAG = -2
2321      TN = TOLD
2322      I1 = NQNYH + 1
2323      DO 520 JB = 1, NQ
2324        I1 = I1 - LDYH
2325        DO 510 I = I1, NQNYH
2326 510      YH1(I) = YH1(I) - YH1(I+LDYH)
2327 520  CONTINUE
2328      IF (ABS(H) .LE. HMIN*ONEPSM) GO TO 660
2329      ETAMAX = ONE
2330      IF (KFLAG .LE. KFC) GO TO 530
2331C Compute ratio of new H to current H at the current order. ------------
2332      FLOTL = REAL(L)
2333      ETA = ONE/((BIAS2*DSM)**(ONE/FLOTL) + ADDON)
2334      ETA = MAX(ETA,HMIN/ABS(H),ETAMIN)
2335      IF ((KFLAG .LE. -2) .AND. (ETA .GT. ETAMXF)) ETA = ETAMXF
2336      GO TO 150
2337C-----------------------------------------------------------------------
2338C Control reaches this section if 3 or more consecutive failures
2339C have occurred.  It is assumed that the elements of the YH array
2340C have accumulated errors of the wrong order.  The order is reduced
2341C by one, if possible.  Then H is reduced by a factor of 0.1 and
2342C the step is retried.  After a total of 7 consecutive failures,
2343C an exit is taken with KFLAG = -1.
2344C-----------------------------------------------------------------------
2345 530  IF (KFLAG .EQ. KFH) GO TO 660
2346      IF (NQ .EQ. 1) GO TO 540
2347      ETA = MAX(ETAMIN,HMIN/ABS(H))
2348      CALL DVJUST (YH, LDYH, -1)
2349      L = NQ
2350      NQ = NQ - 1
2351      NQWAIT = L
2352      GO TO 150
2353 540  ETA = MAX(ETAMIN,HMIN/ABS(H))
2354      H = H*ETA
2355      HSCAL = H
2356      TAU(1) = H
2357      CALL F (N, TN, Y, SAVF)
2358      NFE = NFE + 1
2359      DO 550 I = 1, N
2360 550    YH(I,2) = H*SAVF(I)
2361      NQWAIT = 10
2362      GO TO 200
2363C-----------------------------------------------------------------------
2364C If NQWAIT = 0, an increase or decrease in order by one is considered.
2365C Factors ETAQ, ETAQM1, ETAQP1 are computed by which H could
2366C be multiplied at order q, q-1, or q+1, respectively.
2367C The largest of these is determined, and the new order and
2368C step size set accordingly.
2369C A change of H or NQ is made only if H increases by at least a
2370C factor of THRESH.  If an order change is considered and rejected,
2371C then NQWAIT is set to 2 (reconsider it after 2 steps).
2372C-----------------------------------------------------------------------
2373C Compute ratio of new H to current H at the current order. ------------
2374 560  FLOTL = REAL(L)
2375      ETAQ = ONE/((BIAS2*DSM)**(ONE/FLOTL) + ADDON)
2376      IF (NQWAIT .NE. 0) GO TO 600
2377      NQWAIT = 2
2378      ETAQM1 = ZERO
2379      IF (NQ .EQ. 1) GO TO 570
2380C Compute ratio of new H to current H at the current order less one. ---
2381      DDN = DVNORM (N, YH(1,L), EWT)/TQ(1)
2382      ETAQM1 = ONE/((BIAS1*DDN)**(ONE/(FLOTL - ONE)) + ADDON)
2383 570  ETAQP1 = ZERO
2384      IF (L .EQ. LMAX) GO TO 580
2385C Compute ratio of new H to current H at current order plus one. -------
2386      CNQUOT = (TQ(5)/CONP)*(H/TAU(2))**L
2387      DO 575 I = 1, N
2388 575    SAVF(I) = ACOR(I) - CNQUOT*YH(I,LMAX)
2389      DUP = DVNORM (N, SAVF, EWT)/TQ(3)
2390      ETAQP1 = ONE/((BIAS3*DUP)**(ONE/(FLOTL + ONE)) + ADDON)
2391 580  IF (ETAQ .GE. ETAQP1) GO TO 590
2392      IF (ETAQP1 .GT. ETAQM1) GO TO 620
2393      GO TO 610
2394 590  IF (ETAQ .LT. ETAQM1) GO TO 610
2395 600  ETA = ETAQ
2396      NEWQ = NQ
2397      GO TO 630
2398 610  ETA = ETAQM1
2399      NEWQ = NQ - 1
2400      GO TO 630
2401 620  ETA = ETAQP1
2402      NEWQ = NQ + 1
2403      CALL DCOPY (N, ACOR, 1, YH(1,LMAX), 1)
2404C Test tentative new H against THRESH, ETAMAX, and HMXI, then exit. ----
2405 630  IF (ETA .LT. THRESH .OR. ETAMAX .EQ. ONE) GO TO 640
2406      ETA = MIN(ETA,ETAMAX)
2407      ETA = ETA/MAX(ONE,ABS(H)*HMXI*ETA)
2408      NEWH = 1
2409      HNEW = H*ETA
2410      GO TO 690
2411 640  NEWQ = NQ
2412      NEWH = 0
2413      ETA = ONE
2414      HNEW = H
2415      GO TO 690
2416C-----------------------------------------------------------------------
2417C All returns are made through this section.
2418C On a successful return, ETAMAX is reset and ACOR is scaled.
2419C-----------------------------------------------------------------------
2420 660  KFLAG = -1
2421      GO TO 720
2422 670  KFLAG = -2
2423      GO TO 720
2424 680  IF (NFLAG .EQ. -2) KFLAG = -3
2425      IF (NFLAG .EQ. -3) KFLAG = -4
2426      GO TO 720
2427 690  ETAMAX = ETAMX3
2428      IF (NST .LE. 10) ETAMAX = ETAMX2
2429 700  R = ONE/TQ(2)
2430      CALL DSCAL (N, R, ACOR, 1)
2431 720  JSTART = 1
2432      RETURN
2433C----------------------- End of Subroutine DVSTEP ----------------------
2434      END
2435*DECK DVSET
2436      SUBROUTINE DVSET
2437C-----------------------------------------------------------------------
2438C Call sequence communication.. None
2439C COMMON block variables accessed..
2440C     /DVOD01/ -- EL(13), H, TAU(13), TQ(5), L(= NQ + 1),
2441C                 METH, NQ, NQWAIT
2442C
2443C Subroutines called by DVSET.. None
2444C Function routines called by DVSET.. None
2445C-----------------------------------------------------------------------
2446C DVSET is called by DVSTEP and sets coefficients for use there.
2447C
2448C For each order NQ, the coefficients in EL are calculated by use of
2449C  the generating polynomial lambda(x), with coefficients EL(i).
2450C      lambda(x) = EL(1) + EL(2)*x + ... + EL(NQ+1)*(x**NQ).
2451C For the backward differentiation formulas,
2452C                                     NQ-1
2453C      lambda(x) = (1 + x/xi*(NQ)) * product (1 + x/xi(i) ) .
2454C                                     i = 1
2455C For the Adams formulas,
2456C                              NQ-1
2457C      (d/dx) lambda(x) = c * product (1 + x/xi(i) ) ,
2458C                              i = 1
2459C      lambda(-1) = 0,    lambda(0) = 1,
2460C where c is a normalization constant.
2461C In both cases, xi(i) is defined by
2462C      H*xi(i) = t sub n  -  t sub (n-i)
2463C              = H + TAU(1) + TAU(2) + ... TAU(i-1).
2464C
2465C
2466C In addition to variables described previously, communication
2467C with DVSET uses the following..
2468C   TAU    = A vector of length 13 containing the past NQ values
2469C            of H.
2470C   EL     = A vector of length 13 in which vset stores the
2471C            coefficients for the corrector formula.
2472C   TQ     = A vector of length 5 in which vset stores constants
2473C            used for the convergence test, the error test, and the
2474C            selection of H at a new order.
2475C   METH   = The basic method indicator.
2476C   NQ     = The current order.
2477C   L      = NQ + 1, the length of the vector stored in EL, and
2478C            the number of columns of the YH array being used.
2479C   NQWAIT = A counter controlling the frequency of order changes.
2480C            An order change is about to be considered if NQWAIT = 1.
2481C-----------------------------------------------------------------------
2482C
2483C Type declarations for labeled COMMON block DVOD01 --------------------
2484C
2485      KPP_REAL ACNRM, CCMXJ, CONP, CRATE, DRC, EL,
2486     1     ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
2487     2     RC, RL1, TAU, TQ, TN, UROUND
2488      INTEGER ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
2489     1        L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
2490     2        LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
2491     3        N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
2492     4        NSLP, NYH
2493C
2494C Type declarations for local variables --------------------------------
2495C
2496      KPP_REAL AHATN0, ALPH0, CNQM1, CORTES, CSUM, ELP, EM,
2497     1     EM0, FLOTI, FLOTL, FLOTNQ, HSUM, ONE, RXI, RXIS, S, SIX,
2498     2     T1, T2, T3, T4, T5, T6, TWO, XI, ZERO
2499      INTEGER I, IBACK, J, JP1, NQM1, NQM2
2500C
2501      DIMENSION EM(13)
2502C-----------------------------------------------------------------------
2503C The following Fortran-77 declaration is to cause the values of the
2504C listed (local) variables to be saved between calls to this integrator.
2505C-----------------------------------------------------------------------
2506      SAVE CORTES, ONE, SIX, TWO, ZERO
2507C
2508      COMMON /DVOD01/ ACNRM, CCMXJ, CONP, CRATE, DRC, EL(13),
2509     1                ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
2510     2                RC, RL1, TAU(13), TQ(5), TN, UROUND,
2511     3                ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
2512     4                L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
2513     5                LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
2514     6                N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
2515     7                NSLP, NYH
2516C
2517      DATA CORTES /0.1D0/
2518      DATA ONE  /1.0D0/, SIX /6.0D0/, TWO /2.0D0/, ZERO /0.0D0/
2519C
2520      FLOTL = REAL(L)
2521      NQM1 = NQ - 1
2522      NQM2 = NQ - 2
2523      GO TO (100, 200), METH
2524C
2525C Set coefficients for Adams methods. ----------------------------------
2526 100  IF (NQ .NE. 1) GO TO 110
2527      EL(1) = ONE
2528      EL(2) = ONE
2529      TQ(1) = ONE
2530      TQ(2) = TWO
2531      TQ(3) = SIX*TQ(2)
2532      TQ(5) = ONE
2533      GO TO 300
2534 110  HSUM = H
2535      EM(1) = ONE
2536      FLOTNQ = FLOTL - ONE
2537      DO 115 I = 2, L
2538 115    EM(I) = ZERO
2539      DO 150 J = 1, NQM1
2540        IF ((J .NE. NQM1) .OR. (NQWAIT .NE. 1)) GO TO 130
2541        S = ONE
2542        CSUM = ZERO
2543        DO 120 I = 1, NQM1
2544          CSUM = CSUM + S*EM(I)/REAL(I+1)
2545 120      S = -S
2546        TQ(1) = EM(NQM1)/(FLOTNQ*CSUM)
2547 130    RXI = H/HSUM
2548        DO 140 IBACK = 1, J
2549          I = (J + 2) - IBACK
2550 140      EM(I) = EM(I) + EM(I-1)*RXI
2551        HSUM = HSUM + TAU(J)
2552 150    CONTINUE
2553C Compute integral from -1 to 0 of polynomial and of x times it. -------
2554      S = ONE
2555      EM0 = ZERO
2556      CSUM = ZERO
2557      DO 160 I = 1, NQ
2558        FLOTI = REAL(I)
2559        EM0 = EM0 + S*EM(I)/FLOTI
2560        CSUM = CSUM + S*EM(I)/(FLOTI+ONE)
2561 160    S = -S
2562C In EL, form coefficients of normalized integrated polynomial. --------
2563      S = ONE/EM0
2564      EL(1) = ONE
2565      DO 170 I = 1, NQ
2566 170    EL(I+1) = S*EM(I)/REAL(I)
2567      XI = HSUM/H
2568      TQ(2) = XI*EM0/CSUM
2569      TQ(5) = XI/EL(L)
2570      IF (NQWAIT .NE. 1) GO TO 300
2571C For higher order control constant, multiply polynomial by 1+x/xi(q). -
2572      RXI = ONE/XI
2573      DO 180 IBACK = 1, NQ
2574        I = (L + 1) - IBACK
2575 180    EM(I) = EM(I) + EM(I-1)*RXI
2576C Compute integral of polynomial. --------------------------------------
2577      S = ONE
2578      CSUM = ZERO
2579      DO 190 I = 1, L
2580        CSUM = CSUM + S*EM(I)/REAL(I+1)
2581 190    S = -S
2582      TQ(3) = FLOTL*EM0/CSUM
2583      GO TO 300
2584C
2585C Set coefficients for BDF methods. ------------------------------------
2586 200  DO 210 I = 3, L
2587 210    EL(I) = ZERO
2588      EL(1) = ONE
2589      EL(2) = ONE
2590      ALPH0 = -ONE
2591      AHATN0 = -ONE
2592      HSUM = H
2593      RXI = ONE
2594      RXIS = ONE
2595      IF (NQ .EQ. 1) GO TO 240
2596      DO 230 J = 1, NQM2
2597C In EL, construct coefficients of (1+x/xi(1))*...*(1+x/xi(j+1)). ------
2598        HSUM = HSUM + TAU(J)
2599        RXI = H/HSUM
2600        JP1 = J + 1
2601        ALPH0 = ALPH0 - ONE/REAL(JP1)
2602        DO 220 IBACK = 1, JP1
2603          I = (J + 3) - IBACK
2604 220      EL(I) = EL(I) + EL(I-1)*RXI
2605 230    CONTINUE
2606      ALPH0 = ALPH0 - ONE/REAL(NQ)
2607      RXIS = -EL(2) - ALPH0
2608      HSUM = HSUM + TAU(NQM1)
2609      RXI = H/HSUM
2610      AHATN0 = -EL(2) - RXI
2611      DO 235 IBACK = 1, NQ
2612        I = (NQ + 2) - IBACK
2613 235    EL(I) = EL(I) + EL(I-1)*RXIS
2614 240  T1 = ONE - AHATN0 + ALPH0
2615      T2 = ONE + REAL(NQ)*T1
2616      TQ(2) = ABS(ALPH0*T2/T1)
2617      TQ(5) = ABS(T2/(EL(L)*RXI/RXIS))
2618      IF (NQWAIT .NE. 1) GO TO 300
2619      CNQM1 = RXIS/EL(L)
2620      T3 = ALPH0 + ONE/REAL(NQ)
2621      T4 = AHATN0 + RXI
2622      ELP = T3/(ONE - T4 + T3)
2623      TQ(1) = ABS(ELP/CNQM1)
2624      HSUM = HSUM + TAU(NQ)
2625      RXI = H/HSUM
2626      T5 = ALPH0 - ONE/REAL(NQ+1)
2627      T6 = AHATN0 - RXI
2628      ELP = T2/(ONE - T6 + T5)
2629      TQ(3) = ABS(ELP*RXI*(FLOTL + ONE)*T5)
2630 300  TQ(4) = CORTES*TQ(2)
2631      RETURN
2632C----------------------- End of Subroutine DVSET -----------------------
2633      END
2634*DECK DVJUST
2635      SUBROUTINE DVJUST (YH, LDYH, IORD)
2636      KPP_REAL YH
2637      INTEGER LDYH, IORD
2638      DIMENSION YH(LDYH,*)
2639C-----------------------------------------------------------------------
2640C Call sequence input -- YH, LDYH, IORD
2641C Call sequence output -- YH
2642C COMMON block input -- NQ, METH, LMAX, HSCAL, TAU(13), N
2643C COMMON block variables accessed..
2644C     /DVOD01/ -- HSCAL, TAU(13), LMAX, METH, N, NQ,
2645C
2646C Subroutines called by DVJUST.. DAXPY
2647C Function routines called by DVJUST.. None
2648C-----------------------------------------------------------------------
2649C This subroutine adjusts the YH array on reduction of order,
2650C and also when the order is increased for the stiff option (METH = 2).
2651C Communication with DVJUST uses the following..
2652C IORD  = An integer flag used when METH = 2 to indicate an order
2653C         increase (IORD = +1) or an order decrease (IORD = -1).
2654C HSCAL = Step size H used in scaling of Nordsieck array YH.
2655C         (If IORD = +1, DVJUST assumes that HSCAL = TAU(1).)
2656C See References 1 and 2 for details.
2657C-----------------------------------------------------------------------
2658C
2659C Type declarations for labeled COMMON block DVOD01 --------------------
2660C
2661      KPP_REAL ACNRM, CCMXJ, CONP, CRATE, DRC, EL,
2662     1     ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
2663     2     RC, RL1, TAU, TQ, TN, UROUND
2664      INTEGER ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
2665     1        L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
2666     2        LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
2667     3        N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
2668     4        NSLP, NYH
2669C
2670C Type declarations for local variables --------------------------------
2671C
2672      KPP_REAL ALPH0, ALPH1, HSUM, ONE, PROD, T1, XI,XIOLD, ZERO
2673      INTEGER I, IBACK, J, JP1, LP1, NQM1, NQM2, NQP1
2674C-----------------------------------------------------------------------
2675C The following Fortran-77 declaration is to cause the values of the
2676C listed (local) variables to be saved between calls to this integrator.
2677C-----------------------------------------------------------------------
2678      SAVE ONE, ZERO
2679C
2680      COMMON /DVOD01/ ACNRM, CCMXJ, CONP, CRATE, DRC, EL(13),
2681     1                ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
2682     2                RC, RL1, TAU(13), TQ(5), TN, UROUND,
2683     3                ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
2684     4                L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
2685     5                LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
2686     6                N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
2687     7                NSLP, NYH
2688C
2689      DATA ONE /1.0D0/, ZERO /0.0D0/
2690C
2691      IF ((NQ .EQ. 2) .AND. (IORD .NE. 1)) RETURN
2692      NQM1 = NQ - 1
2693      NQM2 = NQ - 2
2694      GO TO (100, 200), METH
2695C-----------------------------------------------------------------------
2696C Nonstiff option...
2697C Check to see if the order is being increased or decreased.
2698C-----------------------------------------------------------------------
2699 100  CONTINUE
2700      IF (IORD .EQ. 1) GO TO 180
2701C Order decrease. ------------------------------------------------------
2702      DO 110 J = 1, LMAX
2703 110    EL(J) = ZERO
2704      EL(2) = ONE
2705      HSUM = ZERO
2706      DO 130 J = 1, NQM2
2707C Construct coefficients of x*(x+xi(1))*...*(x+xi(j)). -----------------
2708        HSUM = HSUM + TAU(J)
2709        XI = HSUM/HSCAL
2710        JP1 = J + 1
2711        DO 120 IBACK = 1, JP1
2712          I = (J + 3) - IBACK
2713 120      EL(I) = EL(I)*XI + EL(I-1)
2714 130    CONTINUE
2715C Construct coefficients of integrated polynomial. ---------------------
2716      DO 140 J = 2, NQM1
2717 140    EL(J+1) = REAL(NQ)*EL(J)/REAL(J)
2718C Subtract correction terms from YH array. -----------------------------
2719      DO 170 J = 3, NQ
2720        DO 160 I = 1, N
2721 160      YH(I,J) = YH(I,J) - YH(I,L)*EL(J)
2722 170    CONTINUE
2723      RETURN
2724C Order increase. ------------------------------------------------------
2725C Zero out next column in YH array. ------------------------------------
2726 180  CONTINUE
2727      LP1 = L + 1
2728      DO 190 I = 1, N
2729 190    YH(I,LP1) = ZERO
2730      RETURN
2731C-----------------------------------------------------------------------
2732C Stiff option...
2733C Check to see if the order is being increased or decreased.
2734C-----------------------------------------------------------------------
2735 200  CONTINUE
2736      IF (IORD .EQ. 1) GO TO 300
2737C Order decrease. ------------------------------------------------------
2738      DO 210 J = 1, LMAX
2739 210    EL(J) = ZERO
2740      EL(3) = ONE
2741      HSUM = ZERO
2742      DO 230 J = 1,NQM2
2743C Construct coefficients of x*x*(x+xi(1))*...*(x+xi(j)). ---------------
2744        HSUM = HSUM + TAU(J)
2745        XI = HSUM/HSCAL
2746        JP1 = J + 1
2747        DO 220 IBACK = 1, JP1
2748          I = (J + 4) - IBACK
2749 220      EL(I) = EL(I)*XI + EL(I-1)
2750 230    CONTINUE
2751C Subtract correction terms from YH array. -----------------------------
2752      DO 250 J = 3,NQ
2753        DO 240 I = 1, N
2754 240      YH(I,J) = YH(I,J) - YH(I,L)*EL(J)
2755 250    CONTINUE
2756      RETURN
2757C Order increase. ------------------------------------------------------
2758 300  DO 310 J = 1, LMAX
2759 310    EL(J) = ZERO
2760      EL(3) = ONE
2761      ALPH0 = -ONE
2762      ALPH1 = ONE
2763      PROD = ONE
2764      XIOLD = ONE
2765      HSUM = HSCAL
2766      IF (NQ .EQ. 1) GO TO 340
2767      DO 330 J = 1, NQM1
2768C Construct coefficients of x*x*(x+xi(1))*...*(x+xi(j)). ---------------
2769        JP1 = J + 1
2770        HSUM = HSUM + TAU(JP1)
2771        XI = HSUM/HSCAL
2772        PROD = PROD*XI
2773        ALPH0 = ALPH0 - ONE/REAL(JP1)
2774        ALPH1 = ALPH1 + ONE/XI
2775        DO 320 IBACK = 1, JP1
2776          I = (J + 4) - IBACK
2777 320      EL(I) = EL(I)*XIOLD + EL(I-1)
2778        XIOLD = XI
2779 330    CONTINUE
2780 340  CONTINUE
2781      T1 = (-ALPH0 - ALPH1)/PROD
2782C Load column L + 1 in YH array. ---------------------------------------
2783      LP1 = L + 1
2784      DO 350 I = 1, N
2785 350    YH(I,LP1) = T1*YH(I,LMAX)
2786C Add correction terms to YH array. ------------------------------------
2787      NQP1 = NQ + 1
2788      DO 370 J = 3, NQP1
2789        CALL DAXPY (N, EL(J), YH(1,LP1), 1, YH(1,J), 1 )
2790 370  CONTINUE
2791      RETURN
2792C----------------------- End of Subroutine DVJUST ----------------------
2793      END
2794*DECK DVNLSD
2795      SUBROUTINE DVNLSD (Y, YH, LDYH, VSAV, SAVF, EWT, ACOR, IWM, WM,
2796     1                 F, JAC, PDUM, NFLAG, RPAR, IPAR)
2797      EXTERNAL F, JAC, PDUM
2798      KPP_REAL Y, YH, VSAV, SAVF, EWT, ACOR, WM, RPAR
2799      INTEGER LDYH, IWM, NFLAG, IPAR
2800      DIMENSION Y(*), YH(LDYH,*), VSAV(*), SAVF(*), EWT(*), ACOR(*),
2801     1          IWM(*), WM(*), RPAR(*), IPAR(*)
2802
2803C-----------------------------------------------------------------------
2804C Call sequence input -- Y, YH, LDYH, SAVF, EWT, ACOR, IWM, WM,
2805C                        F, JAC, NFLAG, RPAR, IPAR
2806C Call sequence output -- YH, ACOR, WM, IWM, NFLAG
2807C COMMON block variables accessed..
2808C     /DVOD01/ ACNRM, CRATE, DRC, H, RC, RL1, TQ(5), TN, ICF,
2809C                JCUR, METH, MITER, N, NSLP
2810C     /DVOD02/ HU, NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
2811C
2812C Subroutines called by DVNLSD.. F, DAXPY, DCOPY, DSCAL, DVJAC, DVSOL
2813C Function routines called by DVNLSD.. DVNORM
2814C-----------------------------------------------------------------------
2815C Subroutine DVNLSD is a nonlinear system solver, which uses functional
2816C iteration or a chord (modified Newton) method.  For the chord method
2817C direct linear algebraic system solvers are used.  Subroutine DVNLSD
2818C then handles the corrector phase of this integration package.
2819C
2820C Communication with DVNLSD is done with the following variables. (For
2821C more details, please see the comments in the driver subroutine.)
2822C
2823C Y          = The dependent variable, a vector of length N, input.
2824C YH         = The Nordsieck (Taylor) array, LDYH by LMAX, input
2825C              and output.  On input, it contains predicted values.
2826C LDYH       = A constant .ge. N, the first dimension of YH, input.
2827C VSAV       = Unused work array.
2828C SAVF       = A work array of length N.
2829C EWT        = An error weight vector of length N, input.
2830C ACOR       = A work array of length N, used for the accumulated
2831C              corrections to the predicted y vector.
2832C WM,IWM     = Real and integer work arrays associated with matrix
2833C              operations in chord iteration (MITER .ne. 0).
2834C F          = Dummy name for user supplied routine for f.
2835C JAC        = Dummy name for user supplied Jacobian routine.
2836C PDUM       = Unused dummy subroutine name.  Included for uniformity
2837C              over collection of integrators.
2838C NFLAG      = Input/output flag, with values and meanings as follows..
2839C              INPUT
2840C                  0 first CALL for this time step.
2841C                 -1 convergence failure in previous CALL to DVNLSD.
2842C                 -2 error test failure in DVSTEP.
2843C              OUTPUT
2844C                  0 successful completion of nonlinear solver.
2845C                 -1 convergence failure or singular matrix.
2846C                 -2 unrecoverable error in matrix preprocessing
2847C                    (cannot occur here).
2848C                 -3 unrecoverable error in solution (cannot occur
2849C                    here).
2850C RPAR, IPAR = Dummy names for user's real and integer work arrays.
2851C
2852C IPUP       = Own variable flag with values and meanings as follows..
2853C              0,            do not update the Newton matrix.
2854C              MITER .ne. 0, update Newton matrix, because it is the
2855C                            initial step, order was changed, the error
2856C                            test failed, or an update is indicated by
2857C                            the scalar RC or step counter NST.
2858C
2859C For more details, see comments in driver subroutine.
2860C-----------------------------------------------------------------------
2861C Type declarations for labeled COMMON block DVOD01 --------------------
2862C
2863      KPP_REAL ACNRM, CCMXJ, CONP, CRATE, DRC, EL,
2864     1     ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
2865     2     RC, RL1, TAU, TQ, TN, UROUND
2866      INTEGER ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
2867     1        L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
2868     2        LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
2869     3        N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
2870     4        NSLP, NYH
2871C
2872C Type declarations for labeled COMMON block DVOD02 --------------------
2873C
2874      KPP_REAL HU
2875      INTEGER NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
2876C
2877C Type declarations for local variables --------------------------------
2878C
2879      KPP_REAL CCMAX, CRDOWN, CSCALE, DCON, DEL, DELP, ONE,
2880     1     RDIV, TWO, ZERO
2881      INTEGER I, IERPJ, IERSL, M, MAXCOR, MSBP
2882C
2883C Type declaration for function subroutines called ---------------------
2884C
2885      KPP_REAL DVNORM, STEPCUT
2886C-----------------------------------------------------------------------
2887C The following Fortran-77 declaration is to cause the values of the
2888C listed (local) variables to be saved between calls to this integrator.
2889C-----------------------------------------------------------------------
2890      SAVE CCMAX, CRDOWN, MAXCOR, MSBP, RDIV, ONE, TWO, ZERO
2891C
2892      COMMON /DVOD01/ ACNRM, CCMXJ, CONP, CRATE, DRC, EL(13),
2893     1                ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
2894     2                RC, RL1, TAU(13), TQ(5), TN, UROUND,
2895     3                ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
2896     4                L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
2897     5                LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
2898     6                N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
2899     7                NSLP, NYH
2900      COMMON /DVOD02/ HU, NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
2901C
2902      COMMON /VERWER/ IVERWER, IBEGIN, STEPCUT
2903      DATA CCMAX /0.3D0/, CRDOWN /0.3D0/, MAXCOR /3/, MSBP /20/,
2904     1     RDIV  /2.0D0/
2905      DATA ONE /1.0D0/, TWO /2.0D0/, ZERO /0.0D0/
2906C-----------------------------------------------------------------------
2907C On the first step, on a change of method order, or after a
2908C nonlinear convergence failure with NFLAG = -2, set IPUP = MITER
2909C to force a Jacobian update when MITER .ne. 0.
2910C-----------------------------------------------------------------------
2911      if ( (h.lt.stepcut).and.(IBEGIN.eq.1) ) then
2912c      if (h.lt.stepcut) then
2913         iverwer = 1
2914      else
2915         ibegin = 0
2916         iverwer = 0
2917      end if
2918      IF (JSTART .EQ. 0) NSLP = 0
2919      IF (NFLAG .EQ. 0) ICF = 0
2920      IF (NFLAG .EQ. -2) IPUP = MITER
2921      IF ( (JSTART .EQ. 0) .OR. (JSTART .EQ. -1) ) IPUP = MITER
2922C If this is functional iteration, set CRATE .eq. 1 and drop to 220
2923      IF (MITER .EQ. 0) THEN
2924        CRATE = ONE
2925        GO TO 220
2926      ENDIF
2927C-----------------------------------------------------------------------
2928C RC is the ratio of new to old values of the coefficient H/EL(2)=h/l1.
2929C When RC differs from 1 by more than CCMAX, IPUP is set to MITER
2930C to force DVJAC to be called, if a Jacobian is involved.
2931C In any case, DVJAC is called at least every MSBP steps.
2932C-----------------------------------------------------------------------
2933      DRC = ABS(RC-ONE)
2934      IF (DRC .GT. CCMAX .OR. NST .GE. NSLP+MSBP) IPUP = MITER
2935C-----------------------------------------------------------------------
2936C Up to MAXCOR corrector iterations are taken.  A convergence test is
2937C made on the r.m.s. norm of each correction, weighted by the error
2938C weight vector EWT.  The sum of the corrections is accumulated in the
2939C vector ACOR(i).  The YH array is not altered in the corrector loop.
2940C-----------------------------------------------------------------------
2941 220  M = 0
2942      DELP = ZERO
2943      CALL DCOPY (N, YH(1,1), 1, Y, 1 )
2944      CALL F (N, TN, Y, SAVF)
2945      NFE = NFE + 1
2946      IF (IPUP .LE. 0) GO TO 250
2947C-----------------------------------------------------------------------
2948C If indicated, the matrix P = I - h*rl1*J is reevaluated and
2949C preprocessed before starting the corrector iteration.  IPUP is set
2950C to 0 as an indicator that this has been done.
2951C-----------------------------------------------------------------------
2952      IF (IVERWER.EQ.0) THEN
2953      CALL DVJAC (Y, YH, LDYH, EWT, ACOR, SAVF, WM, IWM, F, JAC, IERPJ,
2954     1           RPAR, IPAR)
2955      ELSE
2956        IERPJ = 0
2957      END IF
2958      IPUP = 0
2959      RC = ONE
2960      DRC = ZERO
2961      CRATE = ONE
2962      NSLP = NST
2963C If matrix is singular, take error return to force cut in step size. --
2964      IF (IERPJ .NE. 0) GO TO 430
2965 250  DO 260 I = 1,N
2966 260    ACOR(I) = ZERO
2967C This is a looping point for the corrector iteration. -----------------
2968 270  IF (MITER .NE. 0) GO TO 350
2969C-----------------------------------------------------------------------
2970C In the case of functional iteration, update Y directly from
2971C the result of the last function evaluation.
2972C-----------------------------------------------------------------------
2973      DO 280 I = 1,N
2974 280    SAVF(I) = RL1*(H*SAVF(I) - YH(I,2))
2975      DO 290 I = 1,N
2976 290    Y(I) = SAVF(I) - ACOR(I)
2977      DEL = DVNORM (N, Y, EWT)
2978      DO 300 I = 1,N
2979 300    Y(I) = YH(I,1) + SAVF(I)
2980      CALL DCOPY (N, SAVF, 1, ACOR, 1)
2981      GO TO 400
2982C-----------------------------------------------------------------------
2983C In the case of the chord method, compute the corrector error,
2984C and solve the linear system with that as right-hand side and
2985C P as coefficient matrix.  The correction is scaled by the factor
2986C 2/(1+RC) to account for changes in h*rl1 since the last DVJAC call.
2987C-----------------------------------------------------------------------
2988 350  continue
2989      if (IVERWER.EQ.1) then
2990      CRATE = 1
2991      DO  I = 1,N
2992        Y(I) = SAVF(I) - ACOR(I)
2993      end do
2994      DEL = DVNORM (N, Y, EWT)
2995      DO  I = 1,N
2996         Y(I) = YH(I,1) + SAVF(I)
2997      end do
2998      CALL DCOPY (N, SAVF, 1, ACOR, 1)
2999      GO TO 400
3000      end if
3001      DO 360 I = 1,N
3002 360    Y(I) = (RL1*H)*SAVF(I) - (RL1*YH(I,2) + ACOR(I))
3003        CALL DVSOL (WM, IWM, Y, IERSL)
3004      NNI = NNI + 1
3005      IF (IERSL .GT. 0) GO TO 410
3006      IF (METH .EQ. 2 .AND. RC .NE. ONE) THEN
3007        CSCALE = TWO/(ONE + RC)
3008        CALL DSCAL (N, CSCALE, Y, 1)
3009      ENDIF
3010      DEL = DVNORM (N, Y, EWT)
3011      CALL DAXPY (N, ONE, Y, 1, ACOR, 1)
3012      DO 380 I = 1,N
3013 380    Y(I) = YH(I,1) + ACOR(I)
3014C-----------------------------------------------------------------------
3015C Test for convergence.  If M .gt. 0, an estimate of the convergence
3016C rate constant is stored in CRATE, and this is used in the test.
3017C-----------------------------------------------------------------------
3018 400  IF (M .NE. 0) CRATE = MAX(CRDOWN*CRATE,DEL/DELP)
3019      DCON = DEL*MIN(ONE,CRATE)/TQ(4)
3020      IF (DCON .LE. ONE) GO TO 450
3021      M = M + 1
3022      IF (M .EQ. MAXCOR) GO TO 410
3023      IF (M .GE. 2 .AND. DEL .GT. RDIV*DELP) GO TO 410
3024      DELP = DEL
3025      CALL F (N, TN, Y, SAVF)
3026      NFE = NFE + 1
3027      GO TO 270
3028C
3029 410  IF (MITER .EQ. 0 .OR. JCUR .EQ. 1) GO TO 430
3030      ICF = 1
3031      IPUP = MITER
3032      GO TO 220
3033C
3034 430  CONTINUE
3035      NFLAG = -1
3036      ICF = 2
3037      IPUP = MITER
3038      RETURN
3039C
3040C Return for successful step. ------------------------------------------
3041 450  NFLAG = 0
3042      JCUR = 0
3043      ICF = 0
3044      IF (M .EQ. 0) ACNRM = DEL
3045      IF (M .GT. 0) ACNRM = DVNORM (N, ACOR, EWT)
3046      RETURN
3047C----------------------- End of Subroutine DVNLSD ----------------------
3048      END
3049
3050*DECK DVJAC
3051      SUBROUTINE DVJAC (Y, YH, LDYH, EWT, FTEM, SAVF, WM, IWM, FUN, JAC,
3052     1                 IERPJ, RPAR, IPAR)
3053C       IMPLICIT KPP_REAL (A-H, O-Z)
3054       INCLUDE 'KPP_ROOT_Parameters.h'
3055      INCLUDE 'KPP_ROOT_Sparse.h'
3056      EXTERNAL FUN, JAC
3057      KPP_REAL Y, YH, EWT, FTEM, SAVF, WM, RPAR
3058      INTEGER LDYH, IWM, IERPJ, IPAR
3059      DIMENSION Y(*), YH(LDYH,*), EWT(*), FTEM(*), SAVF(*),
3060     1   WM(*), IWM(*), RPAR(*), IPAR(*)
3061
3062C-----------------------------------------------------------------------
3063C Call sequence input -- Y, YH, LDYH, EWT, FTEM, SAVF, WM, IWM,
3064C                        FUN, JAC, RPAR, IPAR
3065C Call sequence output -- WM, IWM, IERPJ
3066C COMMON block variables accessed..
3067C     /DVOD01/  CCMXJ, DRC, H, RL1, TN, UROUND, ICF, JCUR, LOCJS,
3068C               MSBJ, NSLJ
3069C     /DVOD02/  NFE, NST, NJE, NLU
3070C
3071C Subroutines called by DVJAC.. FUN, JAC, DACOPY, DCOPY, DGBFA, DGEFA,
3072C                              DSCAL
3073C Function routines called by DVJAC.. DVNORM
3074C-----------------------------------------------------------------------
3075C DVJAC is called by DVSTEP to compute and process the matrix
3076C P = I - h*rl1*J , where J is an approximation to the Jacobian.
3077C Here J is computed by the user-supplied routine JAC if
3078C MITER = 1 or 4, or by finite differencing if MITER = 2, 3, or 5.
3079C If MITER = 3, a diagonal approximation to J is used.
3080C If JSV = -1, J is computed from scratch in all cases.
3081C If JSV = 1 and MITER = 1, 2, 4, or 5, and if the saved value of J is
3082C considered acceptable, then P is constructed from the saved J.
3083C J is stored in wm and replaced by P.  If MITER .ne. 3, P is then
3084C subjected to LU decomposition in preparation for later solution
3085C of linear systems with P as coefficient matrix. This is done
3086C by DGEFA if MITER = 1 or 2, and by DGBFA if MITER = 4 or 5.
3087C
3088C Communication with DVJAC is done with the following variables.  (For
3089C more details, please see the comments in the driver subroutine.)
3090C Y          = Vector containing predicted values on entry.
3091C YH         = The Nordsieck array, an LDYH by LMAX array, input.
3092C LDYH       = A constant .ge. N, the first dimension of YH, input.
3093C EWT        = An error weight vector of length N.
3094C SAVF       = Array containing f evaluated at predicted y, input.
3095C WM         = Real work space for matrices.  In the output, it containS
3096C              the inverse diagonal matrix if MITER = 3 and the LU
3097C              decomposition of P if MITER is 1, 2 , 4, or 5.
3098C              Storage of matrix elements starts at WM(3).
3099C              Storage of the saved Jacobian starts at WM(LOCJS).
3100C              WM also contains the following matrix-related data..
3101C              WM(1) = SQRT(UROUND), used in numerical Jacobian step.
3102C              WM(2) = H*RL1, saved for later use if MITER = 3.
3103C IWM        = Integer work space containing pivot information,
3104C              starting at IWM(31), if MITER is 1, 2, 4, or 5.
3105C              IWM also contains band parameters ML = IWM(1) and
3106C              MU = IWM(2) if MITER is 4 or 5.
3107C FUN          = Dummy name for the user supplied subroutine for f.
3108C JAC        = Dummy name for the user supplied Jacobian subroutine.
3109C RPAR, IPAR = Dummy names for user's real and integer work arrays.
3110C RL1        = 1/EL(2) (input).
3111C IERPJ      = Output error flag,  = 0 if no trouble, 1 if the P
3112C              matrix is found to be singular.
3113C JCUR       = Output flag to indicate whether the Jacobian matrix
3114C              (or approximation) is now current.
3115C              JCUR = 0 means J is not current.
3116C              JCUR = 1 means J is current.
3117C-----------------------------------------------------------------------
3118C
3119C Type declarations for labeled COMMON block DVOD01 --------------------
3120C
3121      KPP_REAL ACNRM, CCMXJ, CONP, CRATE, DRC, EL,
3122     1     ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
3123     2     RC, RL1, TAU, TQ, TN, UROUND
3124      INTEGER ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
3125     1        L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
3126     2        LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
3127     3        N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
3128     4        NSLP, NYH
3129C
3130C Type declarations for labeled COMMON block DVOD02 --------------------
3131C
3132      KPP_REAL HU
3133      INTEGER NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
3134C
3135C Type declarations for local variables --------------------------------
3136C
3137      KPP_REAL CON, DI, FAC, HRL1, ONE, PT1, R, R0, SRUR, THOU,
3138     1     YI, YJ, YJJ, ZERO
3139      INTEGER I, I1, I2, IER, II, J, J1, JJ, JOK, LENP, MBA, MBAND,
3140     1        MEB1, MEBAND, ML, ML3, MU, NP1
3141C
3142C Type declaration for function subroutines called ---------------------
3143C
3144      KPP_REAL DVNORM
3145C-----------------------------------------------------------------------
3146C The following Fortran-77 declaration is to cause the values of the
3147C listed (local) variables to be saved between calls to this subroutine.
3148C-----------------------------------------------------------------------
3149      SAVE ONE, PT1, THOU, ZERO
3150C-----------------------------------------------------------------------
3151      COMMON /DVOD01/ ACNRM, CCMXJ, CONP, CRATE, DRC, EL(13),
3152     1                ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
3153     2                RC, RL1, TAU(13), TQ(5), TN, UROUND,
3154     3                ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
3155     4                L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
3156     5                LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
3157     6                N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
3158     7                NSLP, NYH
3159      COMMON /DVOD02/ HU, NCFN, NETF, NFE, NJE, NLU, NNI, NQU, NST
3160C
3161      DATA ONE /1.0D0/, THOU /1000.0D0/, ZERO /0.0D0/, PT1 /0.1D0/
3162C
3163      IER = 0
3164      IERPJ = 0
3165      HRL1 = H*RL1
3166C See whether J should be evaluated (JOK = -1) or not (JOK = 1). -------
3167      JOK = JSV
3168      IF (JSV .EQ. 1) THEN
3169        IF (NST .EQ. 0 .OR. NST .GT. NSLJ+MSBJ) JOK = -1
3170        IF (ICF .EQ. 1 .AND. DRC .LT. CCMXJ) JOK = -1
3171        IF (ICF .EQ. 2) JOK = -1
3172      ENDIF
3173C End of setting JOK. --------------------------------------------------
3174C
3175      IF (JOK .EQ. -1 .AND. MITER .EQ. 1) THEN
3176C If JOK = -1 and MITER = 1, CALL JAC to evaluate Jacobian. ------------
3177      NJE = NJE + 1
3178      NSLJ = NST
3179      JCUR = 1
3180      LENP = LU_NONZERO
3181      DO 110 I = 1,LENP
3182 110    WM(I+2) = ZERO
3183
3184c      CALL Update_SUN(TN)
3185c      CALL Update_RCONST()
3186      CALL JAC (N, TN, Y, WM(3))
3187      IF (JSV .EQ. 1) CALL DCOPY (LENP, WM(3), 1, WM(LOCJS), 1)
3188      ENDIF
3189C
3190      IF (JOK .EQ. -1 .AND. MITER .EQ. 2) THEN
3191C If MITER = 2, make N calls to FUN to approximate the Jacobian. ---------
3192      NJE = NJE + 1
3193      NSLJ = NST
3194      JCUR = 1
3195      FAC = DVNORM (N, SAVF, EWT)
3196      R0 = THOU*ABS(H)*UROUND*REAL(N)*FAC
3197      IF (R0 .EQ. ZERO) R0 = ONE
3198      SRUR = WM(1)
3199      J1 = 2
3200      DO 230 J = 1,N
3201        YJ = Y(J)
3202        R = MAX(SRUR*ABS(YJ),R0/EWT(J))
3203        Y(J) = Y(J) + R
3204        FAC = ONE/R
3205        CALL FUN (N, TN, Y, FTEM)
3206        DO 220 I = 1,N
3207 220      WM(I+J1) = (FTEM(I) - SAVF(I))*FAC
3208        Y(J) = YJ
3209        J1 = J1 + N
3210 230    CONTINUE
3211      NFE = NFE + N
3212      LENP = LU_NONZERO
3213      IF (JSV .EQ. 1) CALL DCOPY (LENP, WM(3), 1, WM(LOCJS), 1)
3214      ENDIF
3215C
3216      IF (JOK .EQ. 1 .AND. (MITER .EQ. 1 .OR. MITER .EQ. 2)) THEN
3217      JCUR = 0
3218      LENP = LU_NONZERO
3219      CALL DCOPY (LENP, WM(LOCJS), 1, WM(3), 1)
3220      ENDIF
3221C
3222      IF (MITER .EQ. 1 .OR. MITER .EQ. 2) THEN
3223C Multiply Jacobian by scalar, add identity, and do LU decomposition. --
3224      CON = -HRL1
3225      CALL DSCAL (LENP, CON, WM(3), 1)
3226      J = 3
3227      NP1 = N + 1
3228      DO 250 I = 1,N
3229        WM(2+LU_DIAG(i)) = WM(2+LU_DIAG(i)) + ONE
3230 250  CONTINUE
3231      NLU = NLU + 1
3232C      CALL DGEFA (WM(3), N, N, IWM(31), IER)
3233      CALL KppDecomp ( WM(3), IER)
3234      IF (IER .NE. 0) IERPJ = 1
3235      RETURN
3236      ENDIF
3237C End of code block for MITER = 1 or 2. --------------------------------
3238C
3239      IF (MITER .EQ. 3) THEN
3240C If MITER = 3, construct a diagonal approximation to J and P. ---------
3241      NJE = NJE + 1
3242      JCUR = 1
3243      WM(2) = HRL1
3244      R = RL1*PT1
3245      DO 310 I = 1,N
3246 310    Y(I) = Y(I) + R*(H*SAVF(I) - YH(I,2))
3247      CALL FUN (N, TN, Y, WM(3))
3248      NFE = NFE + 1
3249      DO 320 I = 1,N
3250        R0 = H*SAVF(I) - YH(I,2)
3251        DI = PT1*R0 - H*(WM(I+2) - SAVF(I))
3252        WM(I+2) = ONE
3253        IF (ABS(R0) .LT. UROUND/EWT(I)) GO TO 320
3254        IF (ABS(DI) .EQ. ZERO) GO TO 330
3255        WM(I+2) = PT1*R0/DI
3256 320    CONTINUE
3257      RETURN
3258 330  IERPJ = 1
3259      RETURN
3260      ENDIF
3261C End of code block for MITER = 3. -------------------------------------
3262C
3263C Set constants for MITER = 4 or 5. ------------------------------------
3264      ML = IWM(1)
3265      MU = IWM(2)
3266      ML3 = ML + 3
3267      MBAND = ML + MU + 1
3268      MEBAND = MBAND + ML
3269      LENP = MEBAND*N
3270C
3271      IF (JOK .EQ. -1 .AND. MITER .EQ. 4) THEN
3272C If JOK = -1 and MITER = 4, CALL JAC to evaluate Jacobian. ------------
3273      NJE = NJE + 1
3274      NSLJ = NST
3275      JCUR = 1
3276      DO 410 I = 1,LENP
3277 410    WM(I+2) = ZERO
3278
3279c      CALL Update_SUN(TN)
3280c      CALL Update_RCONST()
3281      CALL JAC (N, TN, Y, WM(ML3))
3282      IF (JSV .EQ. 1)
3283     1   CALL DACOPY (MBAND, N, WM(ML3), MEBAND, WM(LOCJS), MBAND)
3284      ENDIF
3285C
3286      IF (JOK .EQ. -1 .AND. MITER .EQ. 5) THEN
3287C If MITER = 5, make N calls to FUN to approximate the Jacobian. ---------
3288      NJE = NJE + 1
3289      NSLJ = NST
3290      JCUR = 1
3291      MBA = MIN(MBAND,N)
3292      MEB1 = MEBAND - 1
3293      SRUR = WM(1)
3294      FAC = DVNORM (N, SAVF, EWT)
3295      R0 = THOU*ABS(H)*UROUND*REAL(N)*FAC
3296      IF (R0 .EQ. ZERO) R0 = ONE
3297      DO 560 J = 1,MBA
3298        DO 530 I = J,N,MBAND
3299          YI = Y(I)
3300          R = MAX(SRUR*ABS(YI),R0/EWT(I))
3301 530      Y(I) = Y(I) + R
3302        CALL FUN (N, TN, Y, FTEM)
3303        DO 550 JJ = J,N,MBAND
3304          Y(JJ) = YH(JJ,1)
3305          YJJ = Y(JJ)
3306          R = MAX(SRUR*ABS(YJJ),R0/EWT(JJ))
3307          FAC = ONE/R
3308          I1 = MAX(JJ-MU,1)
3309          I2 = MIN(JJ+ML,N)
3310          II = JJ*MEB1 - ML + 2
3311          DO 540 I = I1,I2
3312 540        WM(II+I) = (FTEM(I) - SAVF(I))*FAC
3313 550      CONTINUE
3314 560    CONTINUE
3315      NFE = NFE + MBA
3316      IF (JSV .EQ. 1)
3317     1   CALL DACOPY (MBAND, N, WM(ML3), MEBAND, WM(LOCJS), MBAND)
3318      ENDIF
3319C
3320      IF (JOK .EQ. 1) THEN
3321      JCUR = 0
3322      CALL DACOPY (MBAND, N, WM(LOCJS), MBAND, WM(ML3), MEBAND)
3323      ENDIF
3324C
3325C Multiply Jacobian by scalar, add identity, and do LU decomposition.
3326      CON = -HRL1
3327      CALL DSCAL (LENP, CON, WM(3), 1 )
3328      II = MBAND + 2
3329      DO 580 I = 1,N
3330        WM(II) = WM(II) + ONE
3331 580    II = II + MEBAND
3332      NLU = NLU + 1
3333C      CALL DGBFA (WM(3), MEBAND, N, ML, MU, IWM(31), IER)
3334      IF (IER .NE. 0) IERPJ = 1
3335      RETURN
3336C End of code block for MITER = 4 or 5. --------------------------------
3337C
3338C----------------------- End of Subroutine DVJAC -----------------------
3339      END
3340*DECK DACOPY
3341      SUBROUTINE DACOPY (NROW, NCOL, A, NROWA, B, NROWB)
3342      KPP_REAL A, B
3343      INTEGER NROW, NCOL, NROWA, NROWB
3344      DIMENSION A(NROWA,NCOL), B(NROWB,NCOL)
3345C-----------------------------------------------------------------------
3346C Call sequence input -- NROW, NCOL, A, NROWA, NROWB
3347C Call sequence output -- B
3348C COMMON block variables accessed -- None
3349C
3350C Subroutines called by DACOPY.. DCOPY
3351C Function routines called by DACOPY.. None
3352C-----------------------------------------------------------------------
3353C This routine copies one rectangular array, A, to another, B,
3354C where A and B may have different row dimensions, NROWA and NROWB.
3355C The data copied consists of NROW rows and NCOL columns.
3356C-----------------------------------------------------------------------
3357      INTEGER IC
3358C
3359      DO 20 IC = 1,NCOL
3360        CALL DCOPY (NROW, A(1,IC), 1, B(1,IC), 1)
3361 20     CONTINUE
3362C
3363      RETURN
3364C----------------------- End of Subroutine DACOPY ----------------------
3365      END
3366*DECK DVSOL
3367      SUBROUTINE DVSOL (WM, IWM, X, IERSL)
3368      KPP_REAL WM, X
3369      INTEGER IWM, IERSL
3370      DIMENSION WM(*), IWM(*), X(*)
3371C-----------------------------------------------------------------------
3372C Call sequence input -- WM, IWM, X
3373C Call sequence output -- X, IERSL
3374C COMMON block variables accessed..
3375C     /DVOD01/ -- H, RL1, MITER, N
3376C
3377C Subroutines called by DVSOL.. DGESL, DGBSL
3378C Function routines called by DVSOL.. None
3379C-----------------------------------------------------------------------
3380C This routine manages the solution of the linear system arising from
3381C a chord iteration.  It is called if MITER .ne. 0.
3382C If MITER is 1 or 2, it calls DGESL to accomplish this.
3383C If MITER = 3 it updates the coefficient H*RL1 in the diagonal
3384C matrix, and then computes the solution.
3385C If MITER is 4 or 5, it calls DGBSL.
3386C Communication with DVSOL uses the following variables..
3387C WM    = Real work space containing the inverse diagonal matrix if
3388C         MITER = 3 and the LU decomposition of the matrix otherwise.
3389C         Storage of matrix elements starts at WM(3).
3390C         WM also contains the following matrix-related data..
3391C         WM(1) = SQRT(UROUND) (not used here),
3392C         WM(2) = HRL1, the previous value of H*RL1, used if MITER = 3.
3393C IWM   = Integer work space containing pivot information, starting at
3394C         IWM(31), if MITER is 1, 2, 4, or 5.  IWM also contains band
3395C         parameters ML = IWM(1) and MU = IWM(2) if MITER is 4 or 5.
3396C X     = The right-hand side vector on input, and the solution vector
3397C         on output, of length N.
3398C IERSL = Output flag.  IERSL = 0 if no trouble occurred.
3399C         IERSL = 1 if a singular matrix arose with MITER = 3.
3400C-----------------------------------------------------------------------
3401C
3402C Type declarations for labeled COMMON block DVOD01 --------------------
3403C
3404      KPP_REAL ACNRM, CCMXJ, CONP, CRATE, DRC, EL,
3405     1     ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
3406     2     RC, RL1, TAU, TQ, TN, UROUND
3407      INTEGER ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
3408     1        L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
3409     2        LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
3410     3        N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
3411     4        NSLP, NYH
3412C
3413C Type declarations for local variables --------------------------------
3414C
3415      INTEGER I, MEBAND, ML, MU
3416      KPP_REAL DI, HRL1, ONE, PHRL1, R, ZERO
3417C-----------------------------------------------------------------------
3418C The following Fortran-77 declaration is to cause the values of the
3419C listed (local) variables to be saved between calls to this integrator.
3420C-----------------------------------------------------------------------
3421      SAVE ONE, ZERO
3422C
3423      COMMON /DVOD01/ ACNRM, CCMXJ, CONP, CRATE, DRC, EL(13),
3424     1                ETA, ETAMAX, H, HMIN, HMXI, HNEW, HSCAL, PRL1,
3425     2                RC, RL1, TAU(13), TQ(5), TN, UROUND,
3426     3                ICF, INIT, IPUP, JCUR, JSTART, JSV, KFLAG, KUTH,
3427     4                L, LMAX, LYH, LEWT, LACOR, LSAVF, LWM, LIWM,
3428     5                LOCJS, MAXORD, METH, MITER, MSBJ, MXHNIL, MXSTEP,
3429     6                N, NEWH, NEWQ, NHNIL, NQ, NQNYH, NQWAIT, NSLJ,
3430     7                NSLP, NYH
3431C
3432      DATA ONE /1.0D0/, ZERO /0.0D0/
3433C
3434      IERSL = 0
3435      GO TO (100, 100, 300, 400, 400), MITER
3436C 100  CALL DGESL (WM(3), N, N, IWM(31), X, 0)
3437 100  CALL KppSolve (WM(3), X)
3438      RETURN
3439C
3440 300  PHRL1 = WM(2)
3441      HRL1 = H*RL1
3442      WM(2) = HRL1
3443      IF (HRL1 .EQ. PHRL1) GO TO 330
3444      R = HRL1/PHRL1
3445      DO 320 I = 1,N
3446        DI = ONE - R*(ONE - ONE/WM(I+2))
3447        IF (ABS(DI) .EQ. ZERO) GO TO 390
3448 320    WM(I+2) = ONE/DI
3449C
3450 330  DO 340 I = 1,N
3451 340    X(I) = WM(I+2)*X(I)
3452      RETURN
3453 390  IERSL = 1
3454      RETURN
3455C
3456 400  ML = IWM(1)
3457      MU = IWM(2)
3458      MEBAND = 2*ML + MU + 1
3459      CALL KppSolve (WM(3), X)
3460      RETURN
3461C----------------------- End of Subroutine DVSOL -----------------------
3462      END
3463*DECK DVSRCO
3464      SUBROUTINE DVSRCO (RSAV, ISAV, JOB)
3465      KPP_REAL RSAV
3466      INTEGER ISAV, JOB
3467      DIMENSION RSAV(*), ISAV(*)
3468C-----------------------------------------------------------------------
3469C Call sequence input -- RSAV, ISAV, JOB
3470C Call sequence output -- RSAV, ISAV
3471C COMMON block variables accessed -- All of /DVOD01/ and /DVOD02/
3472C
3473C Subroutines/functions called by DVSRCO.. None
3474C-----------------------------------------------------------------------
3475C This routine saves or restores (depending on JOB) the contents of the
3476C COMMON blocks DVOD01 and DVOD02, which are used internally by DVODE.
3477C
3478C RSAV = real array of length 49 or more.
3479C ISAV = integer array of length 41 or more.
3480C JOB  = flag indicating to save or restore the COMMON blocks..
3481C        JOB  = 1 if COMMON is to be saved (written to RSAV/ISAV).
3482C        JOB  = 2 if COMMON is to be restored (read from RSAV/ISAV).
3483C        A CALL with JOB = 2 presumes a prior CALL with JOB = 1.
3484C-----------------------------------------------------------------------
3485      KPP_REAL RVOD1, RVOD2
3486      INTEGER IVOD1, IVOD2
3487      INTEGER I, LENIV1, LENIV2, LENRV1, LENRV2
3488C-----------------------------------------------------------------------
3489C The following Fortran-77 declaration is to cause the values of the
3490C listed (local) variables to be saved between calls to this integrator.
3491C-----------------------------------------------------------------------
3492      SAVE LENRV1, LENIV1, LENRV2, LENIV2
3493C
3494      COMMON /DVOD01/ RVOD1(48), IVOD1(33)
3495      COMMON /DVOD02/ RVOD2(1), IVOD2(8)
3496      DATA LENRV1/48/, LENIV1/33/, LENRV2/1/, LENIV2/8/
3497C
3498      IF (JOB .EQ. 2) GO TO 100
3499      DO 10 I = 1,LENRV1
3500 10     RSAV(I) = RVOD1(I)
3501      DO 15 I = 1,LENRV2
3502 15     RSAV(LENRV1+I) = RVOD2(I)
3503C
3504      DO 20 I = 1,LENIV1
3505 20     ISAV(I) = IVOD1(I)
3506      DO 25 I = 1,LENIV2
3507 25     ISAV(LENIV1+I) = IVOD2(I)
3508C
3509      RETURN
3510C
3511 100  CONTINUE
3512      DO 110 I = 1,LENRV1
3513 110     RVOD1(I) = RSAV(I)
3514      DO 115 I = 1,LENRV2
3515 115     RVOD2(I) = RSAV(LENRV1+I)
3516C
3517      DO 120 I = 1,LENIV1
3518 120     IVOD1(I) = ISAV(I)
3519      DO 125 I = 1,LENIV2
3520 125     IVOD2(I) = ISAV(LENIV1+I)
3521C
3522      RETURN
3523C----------------------- End of Subroutine DVSRCO ----------------------
3524      END
3525*DECK DEWSET
3526      SUBROUTINE DEWSET (N, ITOL, RelTol, AbsTol, YCUR, EWT)
3527      KPP_REAL RelTol, AbsTol, YCUR, EWT
3528      INTEGER N, ITOL
3529      DIMENSION RelTol(*), AbsTol(*), YCUR(N), EWT(N)
3530C-----------------------------------------------------------------------
3531C Call sequence input -- N, ITOL, RelTol, AbsTol, YCUR
3532C Call sequence output -- EWT
3533C COMMON block variables accessed -- None
3534C
3535C Subroutines/functions called by DEWSET.. None
3536C-----------------------------------------------------------------------
3537C This subroutine sets the error weight vector EWT according to
3538C     EWT(i) = RelTol(i)*abs(YCUR(i)) + AbsTol(i),  i = 1,...,N,
3539C with the subscript on RelTol and/or AbsTol possibly replaced by 1 above,
3540C depending on the value of ITOL.
3541C-----------------------------------------------------------------------
3542      INTEGER I
3543C
3544      GO TO (10, 20, 30, 40), ITOL
3545 10   CONTINUE
3546      DO 15 I = 1, N
3547 15     EWT(I) = RelTol(1)*ABS(YCUR(I)) + AbsTol(1)
3548      RETURN
3549 20   CONTINUE
3550      DO 25 I = 1, N
3551 25     EWT(I) = RelTol(1)*ABS(YCUR(I)) + AbsTol(I)
3552      RETURN
3553 30   CONTINUE
3554      DO 35 I = 1, N
3555 35     EWT(I) = RelTol(I)*ABS(YCUR(I)) + AbsTol(1)
3556      RETURN
3557 40   CONTINUE
3558      DO 45 I = 1, N
3559 45     EWT(I) = RelTol(I)*ABS(YCUR(I)) + AbsTol(I)
3560      RETURN
3561C----------------------- End of Subroutine DEWSET ----------------------
3562      END
3563*DECK DVNORM
3564      KPP_REAL FUNCTION DVNORM (N, V, W)
3565      KPP_REAL V, W
3566      INTEGER N
3567      DIMENSION V(N), W(N)
3568C-----------------------------------------------------------------------
3569C Call sequence input -- N, V, W
3570C Call sequence output -- None
3571C COMMON block variables accessed -- None
3572C
3573C Subroutines/functions called by DVNORM.. None
3574C-----------------------------------------------------------------------
3575C This function routine computes the weighted root-mean-square norm
3576C of the vector of length N contained in the array V, with weights
3577C contained in the array W of length N..
3578C   DVNORM = sqrt( (1/N) * sum( V(i)*W(i) )**2 )
3579C
3580C  LOOP UNROLLING BY ADRIAN SANDU, AUG 2, 1995
3581C
3582C-----------------------------------------------------------------------
3583      KPP_REAL SUM
3584      INTEGER I
3585C
3586      SUM = 0.0D0
3587
3588   20 m = mod(n,7)
3589      if( m .eq. 0 ) go to 40
3590      do 30 i = 1,m
3591        SUM =  SUM + (V(I)*W(I))**2
3592   30 continue
3593      if( n .lt. 7 ) return
3594   40 mp1 = m + 1
3595      do 50 i = mp1,n,7
3596        SUM =  SUM + (V(I)*W(I))**2
3597        SUM =  SUM + (V(I + 1)*W(I + 1))**2
3598        SUM =  SUM + (V(I + 2)*W(I + 2))**2
3599        SUM =  SUM + (V(I + 3)*W(I + 3))**2
3600        SUM =  SUM + (V(I + 4)*W(I + 4))**2
3601        SUM =  SUM + (V(I + 5)*W(I + 5))**2
3602        SUM =  SUM + (V(I + 6)*W(I + 6))**2
3603   50 continue
3604
3605      DVNORM = SQRT(SUM/REAL(N))
3606      RETURN
3607C----------------------- End of Function DVNORM ------------------------
3608      END
3609
3610*DECK D1MACH
3611      KPP_REAL FUNCTION D1MACH (IDUM)
3612      INTEGER IDUM
3613C-----------------------------------------------------------------------
3614C This routine computes the unit roundoff of the machine.
3615C This is defined as the smallest positive machine number
3616C u such that  1.0 + u .ne. 1.0
3617C
3618C Subroutines/functions called by D1MACH.. None
3619C-----------------------------------------------------------------------
3620      KPP_REAL U, COMP
3621      U = 1.0D0
3622 10   U = U*0.5D0
3623      COMP = 1.0D0 + U
3624      IF (COMP .NE. 1.0D0) GO TO 10
3625      D1MACH = U*2.0D0
3626      RETURN
3627C----------------------- End of Function D1MACH ------------------------
3628      END
3629*DECK XERRWD
3630      SUBROUTINE XERRWD (MSG, NMES, NERR, LEVEL, NI, I1, I2, NR, R1, R2)
3631      KPP_REAL R1, R2
3632      INTEGER NMES, NERR, LEVEL, NI, I1, I2, NR
3633      CHARACTER*1 MSG(NMES)
3634C-----------------------------------------------------------------------
3635C Subroutines XERRWD, XSETF, XSETUN, and the two function routines
3636C MFLGSV and LUNSAV, as given here, constitute a simplified version of
3637C the SLATEC error handling package.
3638C Written by A. C. Hindmarsh and P. N. Brown at LLNL.
3639C Version of 13 April, 1989.
3640C This version is in KPP_REAL.
3641C
3642C All arguments are input arguments.
3643C
3644C MSG    = The message (character array).
3645C NMES   = The length of MSG (number of characters).
3646C NERR   = The error number (not used).
3647C LEVEL  = The error level..
3648C          0 or 1 means recoverable (control returns to caller).
3649C          2 means fatal (run is aborted--see note below).
3650C NI     = Number of integers (0, 1, or 2) to be printed with message.
3651C I1,I2  = Integers to be printed, depending on NI.
3652C NR     = Number of reals (0, 1, or 2) to be printed with message.
3653C R1,R2  = Reals to be printed, depending on NR.
3654C
3655C Note..  this routine is machine-dependent and specialized for use
3656C in limited context, in the following ways..
3657C 1. The argument MSG is assumed to be of type CHARACTER, and
3658C    the message is printed with a format of (1X,80A1).
3659C 2. The message is assumed to take only one line.
3660C    Multi-line messages are generated by repeated calls.
3661C 3. If LEVEL = 2, control passes to the statement   STOP
3662C    to abort the run.  This statement may be machine-dependent.
3663C 4. R1 and R2 are assumed to be in KPP_REAL and are printed
3664C    in D21.13 format.
3665C
3666C For a different default logical unit number, change the data
3667C statement in function routine LUNSAV.
3668C For a different run-abort command, change the statement following
3669C statement 100 at the end.
3670C-----------------------------------------------------------------------
3671C Subroutines called by XERRWD.. None
3672C Function routines called by XERRWD.. MFLGSV, LUNSAV
3673C-----------------------------------------------------------------------
3674C
3675      INTEGER I, LUNIT, LUNSAV, MESFLG, MFLGSV
3676C
3677C Get message print flag and logical unit number. ----------------------
3678      MESFLG = MFLGSV (0,.FALSE.)
3679      LUNIT = LUNSAV (0,.FALSE.)
3680      IF (MESFLG .EQ. 0) GO TO 100
3681C Write the message. ---------------------------------------------------
3682      WRITE (LUNIT,10) (MSG(I),I=1,NMES)
3683 10   FORMAT(1X,80A1)
3684      IF (NI .EQ. 1) WRITE (LUNIT, 20) I1
3685 20   FORMAT(6X,'In above message,  I1 =',I10)
3686      IF (NI .EQ. 2) WRITE (LUNIT, 30) I1,I2
3687 30   FORMAT(6X,'In above message,  I1 =',I10,3X,'I2 =',I10)
3688      IF (NR .EQ. 1) WRITE (LUNIT, 40) R1
3689 40   FORMAT(6X,'In above message,  R1 =',D21.13)
3690      IF (NR .EQ. 2) WRITE (LUNIT, 50) R1,R2
3691 50   FORMAT(6X,'In above,  R1 =',D21.13,3X,'R2 =',D21.13)
3692C Abort the run if LEVEL = 2. ------------------------------------------
3693 100  IF (LEVEL .NE. 2) RETURN
3694      STOP
3695C----------------------- End of Subroutine XERRWD ----------------------
3696      END
3697*DECK XSETF
3698      SUBROUTINE XSETF (MFLAG)
3699C-----------------------------------------------------------------------
3700C This routine resets the print control flag MFLAG.
3701C
3702C Subroutines called by XSETF.. None
3703C Function routines called by XSETF.. MFLGSV
3704C-----------------------------------------------------------------------
3705      INTEGER MFLAG, JUNK, MFLGSV
3706C
3707      IF (MFLAG .EQ. 0 .OR. MFLAG .EQ. 1) JUNK = MFLGSV (MFLAG,.TRUE.)
3708      RETURN
3709C----------------------- End of Subroutine XSETF -----------------------
3710      END
3711*DECK XSETUN
3712      SUBROUTINE XSETUN (LUN)
3713C-----------------------------------------------------------------------
3714C This routine resets the logical unit number for messages.
3715C
3716C Subroutines called by XSETUN.. None
3717C Function routines called by XSETUN.. LUNSAV
3718C-----------------------------------------------------------------------
3719      INTEGER LUN, JUNK, LUNSAV
3720C
3721      IF (LUN .GT. 0) JUNK = LUNSAV (LUN,.TRUE.)
3722      RETURN
3723C----------------------- End of Subroutine XSETUN ----------------------
3724      END
3725*DECK MFLGSV
3726      INTEGER FUNCTION MFLGSV (IVALUE, ISET)
3727      LOGICAL ISET
3728      INTEGER IVALUE
3729C-----------------------------------------------------------------------
3730C MFLGSV saves and recalls the parameter MESFLG which controls the
3731C printing of the error messages.
3732C
3733C Saved local variable..
3734C
3735C   MESFLG = Print control flag..
3736C            1 means print all messages (the default).
3737C            0 means no printing.
3738C
3739C On input..
3740C
3741C   IVALUE = The value to be set for the MESFLG parameter,
3742C            if ISET is .TRUE. .
3743C
3744C   ISET   = Logical flag to indicate whether to read or write.
3745C            If ISET=.TRUE., the MESFLG parameter will be given
3746C            the value IVALUE.  If ISET=.FALSE., the MESFLG
3747C            parameter will be unchanged, and IVALUE is a dummy
3748C            parameter.
3749C
3750C On return..
3751C
3752C   The (old) value of the MESFLG parameter will be returned
3753C   in the function value, MFLGSV.
3754C
3755C This is a modification of the SLATEC library routine J4SAVE.
3756C
3757C Subroutines/functions called by MFLGSV.. None
3758C-----------------------------------------------------------------------
3759      INTEGER MESFLG
3760C-----------------------------------------------------------------------
3761C The following Fortran-77 declaration is to cause the values of the
3762C listed (local) variables to be saved between calls to this integrator.
3763C-----------------------------------------------------------------------
3764      SAVE MESFLG
3765      DATA MESFLG/1/
3766C
3767      MFLGSV = MESFLG
3768      IF (ISET) MESFLG = IVALUE
3769      RETURN
3770C----------------------- End of Function MFLGSV ------------------------
3771      END
3772*DECK LUNSAV
3773      INTEGER FUNCTION LUNSAV (IVALUE, ISET)
3774      LOGICAL ISET
3775      INTEGER IVALUE
3776C-----------------------------------------------------------------------
3777C LUNSAV saves and recalls the parameter LUNIT which is the logical
3778C unit number to which error messages are printed.
3779C
3780C Saved local variable..
3781C
3782C  LUNIT   = Logical unit number for messages.
3783C            The default is 6 (machine-dependent).
3784C
3785C On input..
3786C
3787C   IVALUE = The value to be set for the LUNIT parameter,
3788C            if ISET is .TRUE. .
3789C
3790C   ISET   = Logical flag to indicate whether to read or write.
3791C            If ISET=.TRUE., the LUNIT parameter will be given
3792C            the value IVALUE.  If ISET=.FALSE., the LUNIT
3793C            parameter will be unchanged, and IVALUE is a dummy
3794C            parameter.
3795C
3796C On return..
3797C
3798C   The (old) value of the LUNIT parameter will be returned
3799C   in the function value, LUNSAV.
3800C
3801C This is a modification of the SLATEC library routine J4SAVE.
3802C
3803C Subroutines/functions called by LUNSAV.. None
3804C-----------------------------------------------------------------------
3805      INTEGER LUNIT
3806C-----------------------------------------------------------------------
3807C The following Fortran-77 declaration is to cause the values of the
3808C listed (local) variables to be saved between calls to this integrator.
3809C-----------------------------------------------------------------------
3810      SAVE LUNIT
3811      DATA LUNIT/6/
3812C
3813      LUNSAV = LUNIT
3814      IF (ISET) LUNIT = IVALUE
3815      RETURN
3816C----------------------- End of Function LUNSAV ------------------------
3817      END
3818
3819        SUBROUTINE VODE_FSPLIT_VAR(N, T, Y, PR)
3820        INCLUDE 'KPP_ROOT_Parameters.h'
3821        INCLUDE 'KPP_ROOT_Global.h'
3822        INTEGER N
3823        REAL*8 Told, T
3824        REAL*8 Y(NVAR), PR(NVAR)
3825
3826        Told = TIME
3827        TIME = T
3828        CALL Update_SUN()
3829        CALL Update_RCONST()
3830        CALL Fun( Y,  FIX, RCONST, PR )
3831        TIME = Told
3832        RETURN
3833        END
3834
3835        SUBROUTINE VODE_Jac_SP(N, T, Y, J)
3836        INCLUDE 'KPP_ROOT_Parameters.h'
3837        INCLUDE 'KPP_ROOT_Global.h'
3838        INTEGER N
3839        REAL*8 Told, T
3840        REAL*8 Y(NVAR), J(LU_NONZERO)
3841
3842        Told = TIME
3843        TIME = T
3844        CALL Update_SUN()
3845        CALL Update_RCONST()
3846        CALL Jac_SP( Y,  FIX, RCONST, J )
3847        TIME = Told
3848        RETURN
3849        END
3850
Note: See TracBrowser for help on using the repository browser.