I believe this was a bug, no idea how it was even working before
[WRF.git] / chem / module_cmu_dvode_solver.F
blobf23f178ee00f8e084c63d904ad753f6bea148c5a
1 !**********************************************************************************  
2 ! This computer software was prepared by Battelle Memorial Institute, hereinafter
3 ! the Contractor, under Contract No. DE-AC05-76RL0 1830 with the Department of 
4 ! Energy (DOE). NEITHER THE GOVERNMENT NOR THE CONTRACTOR MAKES ANY WARRANTY,
5 ! EXPRESS OR IMPLIED, OR ASSUMES ANY LIABILITY FOR THE USE OF THIS SOFTWARE.
7 ! MOSAIC module: see module_mosaic_driver.F for references and terms of use
8 !**********************************************************************************  
10 !-----------------------------------------------------------------------
11 !   module_cmu_dvode_solver - from vode.f & vode_subs.f on 27-oct-2005
12 !           (vode.f - downloaded from www.netlib.org on 28-jul-2004)
13 !           (vode_subs.f - created on 28-jul-2004
14 !               by downloading following from www.netlib.org
15 !               1.  daxpy, dcopy, ddot, dnrm2, dscal, idamax from blas
16 !               2.  dgbfa, dbgsl, dgefa, dgesl from linpack)
18 !       first converted to lowercase
19 !       then converted to fortran-90
20 !       then converted to module
21 !           for this step, had to comment out declarations of any
22 !               functions that are part of the module
23 !       also changed common block names to reduce potential for conflicts
24 !           dvod01 --> dvod_cmn01
25 !           dvod02 --> dvod_cmn02
26 !-----------------------------------------------------------------------
27 ! 27-oct-2005 - do not declare functions that are in the module
28 ! 04-mar-2008 - eliminated common blocks;
29 !    halt if istate .ne. 1, because repeated 1-step execution
30 !       will not work now that common blocks are gone
31 !-----------------------------------------------------------------------
33       module module_cmu_dvode_solver
37       type dvode_cmn_vars
38          integer ::   &
39             icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
40             l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
41             locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
42             n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
43             nslp, nyh,   &
44             ncfn, netf, nfe, nje, nlu, nni, nqu, nst
45          double precision ::   &
46             acnrm, ccmxj, conp, crate, drc, el(13),   &
47             eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
48             rc, rl1, tau(13), tq(5), tn, uround,   &
49             hu,   &
50             etaq, etaqm1
51 !        common /dvod_cmn01/ acnrm, ccmxj, conp, crate, drc, el(13),   &
52 !                     eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
53 !                     rc, rl1, tau(13), tq(5), tn, uround,   &
54 !                     icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
55 !                     l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
56 !                     locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
57 !                     n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
58 !                     nslp, nyh
59 !        common /dvod_cmn02/ hu, ncfn, netf, nfe, nje, nlu, nni, nqu, nst
60       end type dvode_cmn_vars
64       contains
68 !-----------------------------------------------------------------------
69 !   vode.f - downloaded from www.netlib.org on 28-jul-2004
70 !-----------------------------------------------------------------------
72 !deck dvode
73       subroutine dvode (f, neq, y, t, tout, itol, rtol, atol, itask,   &
74                   istate, iopt, rwork, lrw, iwork, liw, jac, mf,   &
75                   rpar, ipar)
76       implicit none
77       external f, jac
78       double precision y, t, tout, rtol, atol, rwork, rpar
79       integer neq, itol, itask, istate, iopt, lrw, iwork, liw,   &
80               mf, ipar
81       dimension y(*), rtol(*), atol(*), rwork(lrw), iwork(liw),   &
82                 rpar(*), ipar(*)
83 !-----------------------------------------------------------------------
84 ! dvode: variable-coefficient ordinary differential equation solver,
85 ! with fixed-leading-coefficient implementation.
86 ! this version is in double precision.
88 ! dvode solves the initial value problem for stiff or nonstiff
89 ! systems of first order odes,
90 !     dy/dt = f(t,y) ,  or, in component form,
91 !     dy(i)/dt = f(i) = f(i,t,y(1),y(2),...,y(neq)) (i = 1,...,neq).
92 ! dvode is a package based on the episode and episodeb packages, and
93 ! on the odepack user interface standard, with minor modifications.
94 !-----------------------------------------------------------------------
95 ! authors:
96 !               peter n. brown and alan c. hindmarsh
97 !               center for applied scientific computing, l-561
98 !               lawrence livermore national laboratory
99 !               livermore, ca 94551
100 ! and
101 !               george d. byrne
102 !               illinois institute of technology
103 !               chicago, il 60616
104 !-----------------------------------------------------------------------
105 ! references:
107 ! 1. p. n. brown, g. d. byrne, and a. c. hindmarsh, 'vode: a variable
108 !    coefficient ode solver,' siam j. sci. stat. comput., 10 (1989),
109 !    pp. 1038-1051.  also, llnl report ucrl-98412, june 1988.
110 ! 2. g. d. byrne and a. c. hindmarsh, 'a polyalgorithm for the
111 !    numerical solution of ordinary differential equations,'
112 !    acm trans. math. software, 1 (1975), pp. 71-96.
113 ! 3. a. c. hindmarsh and g. d. byrne, 'episode: an effective package
114 !    for the integration of systems of ordinary differential
115 !    equations,' llnl report ucid-30112, rev. 1, april 1977.
116 ! 4. g. d. byrne and a. c. hindmarsh, 'episodeb: an experimental
117 !    package for the integration of systems of ordinary differential
118 !    equations with banded jacobians,' llnl report ucid-30132, april
119 !    1976.
120 ! 5. a. c. hindmarsh, 'odepack, a systematized collection of ode
121 !    solvers,' in scientific computing, r. s. stepleman et al., eds.,
122 !    north-holland, amsterdam, 1983, pp. 55-64.
123 ! 6. k. r. jackson and r. sacks-davis, 'an alternative implementation
124 !    of variable step-size multistep formulas for stiff odes,' acm
125 !    trans. math. software, 6 (1980), pp. 295-318.
126 !-----------------------------------------------------------------------
127 ! summary of usage.
129 ! communication between the user and the dvode package, for normal
130 ! situations, is summarized here.  this summary describes only a subset
131 ! of the full set of options available.  see the full description for
132 ! details, including optional communication, nonstandard options,
133 ! and instructions for special situations.  see also the example
134 ! problem (with program and output) following this summary.
136 ! a. first provide a subroutine of the form:
137 !           subroutine f (neq, t, y, ydot, rpar, ipar)
138 !           double precision t, y(neq), ydot(neq), rpar
139 ! which supplies the vector function f by loading ydot(i) with f(i).
141 ! b. next determine (or guess) whether or not the problem is stiff.
142 ! stiffness occurs when the jacobian matrix df/dy has an eigenvalue
143 ! whose real part is negative and large in magnitude, compared to the
144 ! reciprocal of the t span of interest.  if the problem is nonstiff,
145 ! use a method flag mf = 10.  if it is stiff, there are four standard
146 ! choices for mf (21, 22, 24, 25), and dvode requires the jacobian
147 ! matrix in some form.  in these cases (mf .gt. 0), dvode will use a
148 ! saved copy of the jacobian matrix.  if this is undesirable because of
149 ! storage limitations, set mf to the corresponding negative value
150 ! (-21, -22, -24, -25).  (see full description of mf below.)
151 ! the jacobian matrix is regarded either as full (mf = 21 or 22),
152 ! or banded (mf = 24 or 25).  in the banded case, dvode requires two
153 ! half-bandwidth parameters ml and mu.  these are, respectively, the
154 ! widths of the lower and upper parts of the band, excluding the main
155 ! diagonal.  thus the band consists of the locations (i,j) with
156 ! i-ml .le. j .le. i+mu, and the full bandwidth is ml+mu+1.
158 ! c. if the problem is stiff, you are encouraged to supply the jacobian
159 ! directly (mf = 21 or 24), but if this is not feasible, dvode will
160 ! compute it internally by difference quotients (mf = 22 or 25).
161 ! if you are supplying the jacobian, provide a subroutine of the form:
162 !           subroutine jac (neq, t, y, ml, mu, pd, nrowpd, rpar, ipar)
163 !           double precision t, y(neq), pd(nrowpd,neq), rpar
164 ! which supplies df/dy by loading pd as follows:
165 !     for a full jacobian (mf = 21), load pd(i,j) with df(i)/dy(j),
166 ! the partial derivative of f(i) with respect to y(j).  (ignore the
167 ! ml and mu arguments in this case.)
168 !     for a banded jacobian (mf = 24), load pd(i-j+mu+1,j) with
169 ! df(i)/dy(j), i.e. load the diagonal lines of df/dy into the rows of
170 ! pd from the top down.
171 !     in either case, only nonzero elements need be loaded.
173 ! d. write a main program which calls subroutine dvode once for
174 ! each point at which answers are desired.  this should also provide
175 ! for possible use of logical unit 6 for output of error messages
176 ! by dvode.  on the first call to dvode, supply arguments as follows:
177 ! f      = name of subroutine for right-hand side vector f.
178 !          this name must be declared external in calling program.
179 ! neq    = number of first order odes.
180 ! y      = array of initial values, of length neq.
181 ! t      = the initial value of the independent variable.
182 ! tout   = first point where output is desired (.ne. t).
183 ! itol   = 1 or 2 according as atol (below) is a scalar or array.
184 ! rtol   = relative tolerance parameter (scalar).
185 ! atol   = absolute tolerance parameter (scalar or array).
186 !          the estimated local error in y(i) will be controlled so as
187 !          to be roughly less (in magnitude) than
188 !             ewt(i) = rtol*abs(y(i)) + atol     if itol = 1, or
189 !             ewt(i) = rtol*abs(y(i)) + atol(i)  if itol = 2.
190 !          thus the local error test passes if, in each component,
191 !          either the absolute error is less than atol (or atol(i)),
192 !          or the relative error is less than rtol.
193 !          use rtol = 0.0 for pure absolute error control, and
194 !          use atol = 0.0 (or atol(i) = 0.0) for pure relative error
195 !          control.  caution: actual (global) errors may exceed these
196 !          local tolerances, so choose them conservatively.
197 ! itask  = 1 for normal computation of output values of y at t = tout.
198 ! istate = integer flag (input and output).  set istate = 1.
199 ! iopt   = 0 to indicate no optional input used.
200 ! rwork  = real work array of length at least:
201 !             20 + 16*neq                      for mf = 10,
202 !             22 +  9*neq + 2*neq**2           for mf = 21 or 22,
203 !             22 + 11*neq + (3*ml + 2*mu)*neq  for mf = 24 or 25.
204 ! lrw    = declared length of rwork (in user's dimension statement).
205 ! iwork  = integer work array of length at least:
206 !             30        for mf = 10,
207 !             30 + neq  for mf = 21, 22, 24, or 25.
208 !          if mf = 24 or 25, input in iwork(1),iwork(2) the lower
209 !          and upper half-bandwidths ml,mu.
210 ! liw    = declared length of iwork (in user's dimension statement).
211 ! jac    = name of subroutine for jacobian matrix (mf = 21 or 24).
212 !          if used, this name must be declared external in calling
213 !          program.  if not used, pass a dummy name.
214 ! mf     = method flag.  standard values are:
215 !          10 for nonstiff (adams) method, no jacobian used.
216 !          21 for stiff (bdf) method, user-supplied full jacobian.
217 !          22 for stiff method, internally generated full jacobian.
218 !          24 for stiff method, user-supplied banded jacobian.
219 !          25 for stiff method, internally generated banded jacobian.
220 ! rpar,ipar = user-defined real and integer arrays passed to f and jac.
221 ! note that the main program must declare arrays y, rwork, iwork,
222 ! and possibly atol, rpar, and ipar.
224 ! e. the output from the first call (or any call) is:
225 !      y = array of computed values of y(t) vector.
226 !      t = corresponding value of independent variable (normally tout).
227 ! istate = 2  if dvode was successful, negative otherwise.
228 !          -1 means excess work done on this call. (perhaps wrong mf.)
229 !          -2 means excess accuracy requested. (tolerances too small.)
230 !          -3 means illegal input detected. (see printed message.)
231 !          -4 means repeated error test failures. (check all input.)
232 !          -5 means repeated convergence failures. (perhaps bad
233 !             jacobian supplied or wrong choice of mf or tolerances.)
234 !          -6 means error weight became zero during problem. (solution
235 !             component i vanished, and atol or atol(i) = 0.)
237 ! f. to continue the integration after a successful return, simply
238 ! reset tout and call dvode again.  no other parameters need be reset.
240 !-----------------------------------------------------------------------
241 ! example problem
243 ! the following is a simple example problem, with the coding
244 ! needed for its solution by dvode.  the problem is from chemical
245 ! kinetics, and consists of the following three rate equations:
246 !     dy1/dt = -.04*y1 + 1.e4*y2*y3
247 !     dy2/dt = .04*y1 - 1.e4*y2*y3 - 3.e7*y2**2
248 !     dy3/dt = 3.e7*y2**2
249 ! on the interval from t = 0.0 to t = 4.e10, with initial conditions
250 ! y1 = 1.0, y2 = y3 = 0.  the problem is stiff.
252 ! the following coding solves this problem with dvode, using mf = 21
253 ! and printing results at t = .4, 4., ..., 4.e10.  it uses
254 ! itol = 2 and atol much smaller for y2 than y1 or y3 because
255 ! y2 has much smaller values.
256 ! at the end of the run, statistical quantities of interest are
257 ! printed. (see optional output in the full description below.)
258 ! to generate fortran source code, replace c in column 1 with a blank
259 ! in the coding below.
261 !     external fex, jex
262 !     double precision atol, rpar, rtol, rwork, t, tout, y
263 !     dimension y(3), atol(3), rwork(67), iwork(33)
264 !     neq = 3
265 !     y(1) = 1.0d0
266 !     y(2) = 0.0d0
267 !     y(3) = 0.0d0
268 !     t = 0.0d0
269 !     tout = 0.4d0
270 !     itol = 2
271 !     rtol = 1.d-4
272 !     atol(1) = 1.d-8
273 !     atol(2) = 1.d-14
274 !     atol(3) = 1.d-6
275 !     itask = 1
276 !     istate = 1
277 !     iopt = 0
278 !     lrw = 67
279 !     liw = 33
280 !     mf = 21
281 !     do 40 iout = 1,12
282 !       call dvode(fex,neq,y,t,tout,itol,rtol,atol,itask,istate,
283 !    1            iopt,rwork,lrw,iwork,liw,jex,mf,rpar,ipar)
284 !       write(6,20)t,y(1),y(2),y(3)
285 ! 20    format(' at t =',d12.4,'   y =',3d14.6)
286 !       if (istate .lt. 0) go to 80
287 ! 40    tout = tout*10.
288 !     write(6,60) iwork(11),iwork(12),iwork(13),iwork(19),
289 !    1            iwork(20),iwork(21),iwork(22)
290 ! 60  format(/' no. steps =',i4,'   no. f-s =',i4,
291 !    1       '   no. j-s =',i4,'   no. lu-s =',i4/
292 !    2       '  no. nonlinear iterations =',i4/
293 !    3       '  no. nonlinear convergence failures =',i4/
294 !    4       '  no. error test failures =',i4/)
295 !     stop
296 ! 80  write(6,90)istate
297 ! 90  format(///' error halt: istate =',i3)
298 !     stop
299 !     end
301 !     subroutine fex (neq, t, y, ydot, rpar, ipar)
302 !     double precision rpar, t, y, ydot
303 !     dimension y(neq), ydot(neq)
304 !     ydot(1) = -.04d0*y(1) + 1.d4*y(2)*y(3)
305 !     ydot(3) = 3.d7*y(2)*y(2)
306 !     ydot(2) = -ydot(1) - ydot(3)
307 !     return
308 !     end
310 !     subroutine jex (neq, t, y, ml, mu, pd, nrpd, rpar, ipar)
311 !     double precision pd, rpar, t, y
312 !     dimension y(neq), pd(nrpd,neq)
313 !     pd(1,1) = -.04d0
314 !     pd(1,2) = 1.d4*y(3)
315 !     pd(1,3) = 1.d4*y(2)
316 !     pd(2,1) = .04d0
317 !     pd(2,3) = -pd(1,3)
318 !     pd(3,2) = 6.d7*y(2)
319 !     pd(2,2) = -pd(1,2) - pd(3,2)
320 !     return
321 !     end
323 ! the following output was obtained from the above program on a
324 ! cray-1 computer with the cft compiler.
326 ! at t =  4.0000e-01   y =  9.851680e-01  3.386314e-05  1.479817e-02
327 ! at t =  4.0000e+00   y =  9.055255e-01  2.240539e-05  9.445214e-02
328 ! at t =  4.0000e+01   y =  7.158108e-01  9.184883e-06  2.841800e-01
329 ! at t =  4.0000e+02   y =  4.505032e-01  3.222940e-06  5.494936e-01
330 ! at t =  4.0000e+03   y =  1.832053e-01  8.942690e-07  8.167938e-01
331 ! at t =  4.0000e+04   y =  3.898560e-02  1.621875e-07  9.610142e-01
332 ! at t =  4.0000e+05   y =  4.935882e-03  1.984013e-08  9.950641e-01
333 ! at t =  4.0000e+06   y =  5.166183e-04  2.067528e-09  9.994834e-01
334 ! at t =  4.0000e+07   y =  5.201214e-05  2.080593e-10  9.999480e-01
335 ! at t =  4.0000e+08   y =  5.213149e-06  2.085271e-11  9.999948e-01
336 ! at t =  4.0000e+09   y =  5.183495e-07  2.073399e-12  9.999995e-01
337 ! at t =  4.0000e+10   y =  5.450996e-08  2.180399e-13  9.999999e-01
339 ! no. steps = 595   no. f-s = 832   no. j-s =  13   no. lu-s = 112
340 !  no. nonlinear iterations = 831
341 !  no. nonlinear convergence failures =   0
342 !  no. error test failures =  22
343 !-----------------------------------------------------------------------
344 ! full description of user interface to dvode.
346 ! the user interface to dvode consists of the following parts.
348 ! i.   the call sequence to subroutine dvode, which is a driver
349 !      routine for the solver.  this includes descriptions of both
350 !      the call sequence arguments and of user-supplied routines.
351 !      following these descriptions is
352 !        * a description of optional input available through the
353 !          call sequence,
354 !        * a description of optional output (in the work arrays), and
355 !        * instructions for interrupting and restarting a solution.
357 ! ii.  descriptions of other routines in the dvode package that may be
358 !      (optionally) called by the user.  these provide the ability to
359 !      alter error message handling, save and restore the internal
360 !      common, and obtain specified derivatives of the solution y(t).
362 ! iii. descriptions of common blocks to be declared in overlay
363 !      or similar environments.
365 ! iv.  description of two routines in the dvode package, either of
366 !      which the user may replace with his own version, if desired.
367 !      these relate to the measurement of errors.
369 !-----------------------------------------------------------------------
370 ! part i.  call sequence.
372 ! the call sequence parameters used for input only are
373 !     f, neq, tout, itol, rtol, atol, itask, iopt, lrw, liw, jac, mf,
374 ! and those used for both input and output are
375 !     y, t, istate.
376 ! the work arrays rwork and iwork are also used for conditional and
377 ! optional input and optional output.  (the term output here refers
378 ! to the return from subroutine dvode to the user's calling program.)
380 ! the legality of input parameters will be thoroughly checked on the
381 ! initial call for the problem, but not checked thereafter unless a
382 ! change in input parameters is flagged by istate = 3 in the input.
384 ! the descriptions of the call arguments are as follows.
386 ! f      = the name of the user-supplied subroutine defining the
387 !          ode system.  the system must be put in the first-order
388 !          form dy/dt = f(t,y), where f is a vector-valued function
389 !          of the scalar t and the vector y.  subroutine f is to
390 !          compute the function f.  it is to have the form
391 !               subroutine f (neq, t, y, ydot, rpar, ipar)
392 !               double precision t, y(neq), ydot(neq), rpar
393 !          where neq, t, and y are input, and the array ydot = f(t,y)
394 !          is output.  y and ydot are arrays of length neq.
395 !          subroutine f should not alter y(1),...,y(neq).
396 !          f must be declared external in the calling program.
398 !          subroutine f may access user-defined real and integer
399 !          work arrays rpar and ipar, which are to be dimensioned
400 !          in the main program.
402 !          if quantities computed in the f routine are needed
403 !          externally to dvode, an extra call to f should be made
404 !          for this purpose, for consistent and accurate results.
405 !          if only the derivative dy/dt is needed, use dvindy instead.
407 ! neq    = the size of the ode system (number of first order
408 !          ordinary differential equations).  used only for input.
409 !          neq may not be increased during the problem, but
410 !          can be decreased (with istate = 3 in the input).
412 ! y      = a real array for the vector of dependent variables, of
413 !          length neq or more.  used for both input and output on the
414 !          first call (istate = 1), and only for output on other calls.
415 !          on the first call, y must contain the vector of initial
416 !          values.  in the output, y contains the computed solution
417 !          evaluated at t.  if desired, the y array may be used
418 !          for other purposes between calls to the solver.
420 !          this array is passed as the y argument in all calls to
421 !          f and jac.
423 ! t      = the independent variable.  in the input, t is used only on
424 !          the first call, as the initial point of the integration.
425 !          in the output, after each call, t is the value at which a
426 !          computed solution y is evaluated (usually the same as tout).
427 !          on an error return, t is the farthest point reached.
429 ! tout   = the next value of t at which a computed solution is desired.
430 !          used only for input.
432 !          when starting the problem (istate = 1), tout may be equal
433 !          to t for one call, then should .ne. t for the next call.
434 !          for the initial t, an input value of tout .ne. t is used
435 !          in order to determine the direction of the integration
436 !          (i.e. the algebraic sign of the step sizes) and the rough
437 !          scale of the problem.  integration in either direction
438 !          (forward or backward in t) is permitted.
440 !          if itask = 2 or 5 (one-step modes), tout is ignored after
441 !          the first call (i.e. the first call with tout .ne. t).
442 !          otherwise, tout is required on every call.
444 !          if itask = 1, 3, or 4, the values of tout need not be
445 !          monotone, but a value of tout which backs up is limited
446 !          to the current internal t interval, whose endpoints are
447 !          tcur - hu and tcur.  (see optional output, below, for
448 !          tcur and hu.)
450 ! itol   = an indicator for the type of error control.  see
451 !          description below under atol.  used only for input.
453 ! rtol   = a relative error tolerance parameter, either a scalar or
454 !          an array of length neq.  see description below under atol.
455 !          input only.
457 ! atol   = an absolute error tolerance parameter, either a scalar or
458 !          an array of length neq.  input only.
460 !          the input parameters itol, rtol, and atol determine
461 !          the error control performed by the solver.  the solver will
462 !          control the vector e = (e(i)) of estimated local errors
463 !          in y, according to an inequality of the form
464 !                      rms-norm of ( e(i)/ewt(i) )   .le.   1,
465 !          where       ewt(i) = rtol(i)*abs(y(i)) + atol(i),
466 !          and the rms-norm (root-mean-square norm) here is
467 !          rms-norm(v) = sqrt(sum v(i)**2 / neq).  here ewt = (ewt(i))
468 !          is a vector of weights which must always be positive, and
469 !          the values of rtol and atol should all be non-negative.
470 !          the following table gives the types (scalar/array) of
471 !          rtol and atol, and the corresponding form of ewt(i).
473 !             itol    rtol       atol          ewt(i)
474 !              1     scalar     scalar     rtol*abs(y(i)) + atol
475 !              2     scalar     array      rtol*abs(y(i)) + atol(i)
476 !              3     array      scalar     rtol(i)*abs(y(i)) + atol
477 !              4     array      array      rtol(i)*abs(y(i)) + atol(i)
479 !          when either of these parameters is a scalar, it need not
480 !          be dimensioned in the user's calling program.
482 !          if none of the above choices (with itol, rtol, and atol
483 !          fixed throughout the problem) is suitable, more general
484 !          error controls can be obtained by substituting
485 !          user-supplied routines for the setting of ewt and/or for
486 !          the norm calculation.  see part iv below.
488 !          if global errors are to be estimated by making a repeated
489 !          run on the same problem with smaller tolerances, then all
490 !          components of rtol and atol (i.e. of ewt) should be scaled
491 !          down uniformly.
493 ! itask  = an index specifying the task to be performed.
494 !          input only.  itask has the following values and meanings.
495 !          1  means normal computation of output values of y(t) at
496 !             t = tout (by overshooting and interpolating).
497 !          2  means take one step only and return.
498 !          3  means stop at the first internal mesh point at or
499 !             beyond t = tout and return.
500 !          4  means normal computation of output values of y(t) at
501 !             t = tout but without overshooting t = tcrit.
502 !             tcrit must be input as rwork(1).  tcrit may be equal to
503 !             or beyond tout, but not behind it in the direction of
504 !             integration.  this option is useful if the problem
505 !             has a singularity at or beyond t = tcrit.
506 !          5  means take one step, without passing tcrit, and return.
507 !             tcrit must be input as rwork(1).
509 !          note:  if itask = 4 or 5 and the solver reaches tcrit
510 !          (within roundoff), it will return t = tcrit (exactly) to
511 !          indicate this (unless itask = 4 and tout comes before tcrit,
512 !          in which case answers at t = tout are returned first).
514 ! istate = an index used for input and output to specify the
515 !          the state of the calculation.
517 !          in the input, the values of istate are as follows.
518 !          1  means this is the first call for the problem
519 !             (initializations will be done).  see note below.
520 !          2  means this is not the first call, and the calculation
521 !             is to continue normally, with no change in any input
522 !             parameters except possibly tout and itask.
523 !             (if itol, rtol, and/or atol are changed between calls
524 !             with istate = 2, the new values will be used but not
525 !             tested for legality.)
526 !          3  means this is not the first call, and the
527 !             calculation is to continue normally, but with
528 !             a change in input parameters other than
529 !             tout and itask.  changes are allowed in
530 !             neq, itol, rtol, atol, iopt, lrw, liw, mf, ml, mu,
531 !             and any of the optional input except h0.
532 !             (see iwork description for ml and mu.)
533 !          note:  a preliminary call with tout = t is not counted
534 !          as a first call here, as no initialization or checking of
535 !          input is done.  (such a call is sometimes useful to include
536 !          the initial conditions in the output.)
537 !          thus the first call for which tout .ne. t requires
538 !          istate = 1 in the input.
540 !          in the output, istate has the following values and meanings.
541 !           1  means nothing was done, as tout was equal to t with
542 !              istate = 1 in the input.
543 !           2  means the integration was performed successfully.
544 !          -1  means an excessive amount of work (more than mxstep
545 !              steps) was done on this call, before completing the
546 !              requested task, but the integration was otherwise
547 !              successful as far as t.  (mxstep is an optional input
548 !              and is normally 500.)  to continue, the user may
549 !              simply reset istate to a value .gt. 1 and call again.
550 !              (the excess work step counter will be reset to 0.)
551 !              in addition, the user may increase mxstep to avoid
552 !              this error return.  (see optional input below.)
553 !          -2  means too much accuracy was requested for the precision
554 !              of the machine being used.  this was detected before
555 !              completing the requested task, but the integration
556 !              was successful as far as t.  to continue, the tolerance
557 !              parameters must be reset, and istate must be set
558 !              to 3.  the optional output tolsf may be used for this
559 !              purpose.  (note: if this condition is detected before
560 !              taking any steps, then an illegal input return
561 !              (istate = -3) occurs instead.)
562 !          -3  means illegal input was detected, before taking any
563 !              integration steps.  see written message for details.
564 !              note:  if the solver detects an infinite loop of calls
565 !              to the solver with illegal input, it will cause
566 !              the run to stop.
567 !          -4  means there were repeated error test failures on
568 !              one attempted step, before completing the requested
569 !              task, but the integration was successful as far as t.
570 !              the problem may have a singularity, or the input
571 !              may be inappropriate.
572 !          -5  means there were repeated convergence test failures on
573 !              one attempted step, before completing the requested
574 !              task, but the integration was successful as far as t.
575 !              this may be caused by an inaccurate jacobian matrix,
576 !              if one is being used.
577 !          -6  means ewt(i) became zero for some i during the
578 !              integration.  pure relative error control (atol(i)=0.0)
579 !              was requested on a variable which has now vanished.
580 !              the integration was successful as far as t.
582 !          note:  since the normal output value of istate is 2,
583 !          it does not need to be reset for normal continuation.
584 !          also, since a negative input value of istate will be
585 !          regarded as illegal, a negative output value requires the
586 !          user to change it, and possibly other input, before
587 !          calling the solver again.
589 ! iopt   = an integer flag to specify whether or not any optional
590 !          input is being used on this call.  input only.
591 !          the optional input is listed separately below.
592 !          iopt = 0 means no optional input is being used.
593 !                   default values will be used in all cases.
594 !          iopt = 1 means optional input is being used.
596 ! rwork  = a real working array (double precision).
597 !          the length of rwork must be at least
598 !             20 + nyh*(maxord + 1) + 3*neq + lwm    where
599 !          nyh    = the initial value of neq,
600 !          maxord = 12 (if meth = 1) or 5 (if meth = 2) (unless a
601 !                   smaller value is given as an optional input),
602 !          lwm = length of work space for matrix-related data:
603 !          lwm = 0             if miter = 0,
604 !          lwm = 2*neq**2 + 2  if miter = 1 or 2, and mf.gt.0,
605 !          lwm = neq**2 + 2    if miter = 1 or 2, and mf.lt.0,
606 !          lwm = neq + 2       if miter = 3,
607 !          lwm = (3*ml+2*mu+2)*neq + 2 if miter = 4 or 5, and mf.gt.0,
608 !          lwm = (2*ml+mu+1)*neq + 2   if miter = 4 or 5, and mf.lt.0.
609 !          (see the mf description for meth and miter.)
610 !          thus if maxord has its default value and neq is constant,
611 !          this length is:
612 !             20 + 16*neq                    for mf = 10,
613 !             22 + 16*neq + 2*neq**2         for mf = 11 or 12,
614 !             22 + 16*neq + neq**2           for mf = -11 or -12,
615 !             22 + 17*neq                    for mf = 13,
616 !             22 + 18*neq + (3*ml+2*mu)*neq  for mf = 14 or 15,
617 !             22 + 17*neq + (2*ml+mu)*neq    for mf = -14 or -15,
618 !             20 +  9*neq                    for mf = 20,
619 !             22 +  9*neq + 2*neq**2         for mf = 21 or 22,
620 !             22 +  9*neq + neq**2           for mf = -21 or -22,
621 !             22 + 10*neq                    for mf = 23,
622 !             22 + 11*neq + (3*ml+2*mu)*neq  for mf = 24 or 25.
623 !             22 + 10*neq + (2*ml+mu)*neq    for mf = -24 or -25.
624 !          the first 20 words of rwork are reserved for conditional
625 !          and optional input and optional output.
627 !          the following word in rwork is a conditional input:
628 !            rwork(1) = tcrit = critical value of t which the solver
629 !                       is not to overshoot.  required if itask is
630 !                       4 or 5, and ignored otherwise.  (see itask.)
632 ! lrw    = the length of the array rwork, as declared by the user.
633 !          (this will be checked by the solver.)
635 ! iwork  = an integer work array.  the length of iwork must be at least
636 !             30        if miter = 0 or 3 (mf = 10, 13, 20, 23), or
637 !             30 + neq  otherwise (abs(mf) = 11,12,14,15,21,22,24,25).
638 !          the first 30 words of iwork are reserved for conditional and
639 !          optional input and optional output.
641 !          the following 2 words in iwork are conditional input:
642 !            iwork(1) = ml     these are the lower and upper
643 !            iwork(2) = mu     half-bandwidths, respectively, of the
644 !                       banded jacobian, excluding the main diagonal.
645 !                       the band is defined by the matrix locations
646 !                       (i,j) with i-ml .le. j .le. i+mu.  ml and mu
647 !                       must satisfy  0 .le.  ml,mu  .le. neq-1.
648 !                       these are required if miter is 4 or 5, and
649 !                       ignored otherwise.  ml and mu may in fact be
650 !                       the band parameters for a matrix to which
651 !                       df/dy is only approximately equal.
653 ! liw    = the length of the array iwork, as declared by the user.
654 !          (this will be checked by the solver.)
656 ! note:  the work arrays must not be altered between calls to dvode
657 ! for the same problem, except possibly for the conditional and
658 ! optional input, and except for the last 3*neq words of rwork.
659 ! the latter space is used for internal scratch space, and so is
660 ! available for use by the user outside dvode between calls, if
661 ! desired (but not for use by f or jac).
663 ! jac    = the name of the user-supplied routine (miter = 1 or 4) to
664 !          compute the jacobian matrix, df/dy, as a function of
665 !          the scalar t and the vector y.  it is to have the form
666 !               subroutine jac (neq, t, y, ml, mu, pd, nrowpd,
667 !                               rpar, ipar)
668 !               double precision t, y(neq), pd(nrowpd,neq), rpar
669 !          where neq, t, y, ml, mu, and nrowpd are input and the array
670 !          pd is to be loaded with partial derivatives (elements of the
671 !          jacobian matrix) in the output.  pd must be given a first
672 !          dimension of nrowpd.  t and y have the same meaning as in
673 !          subroutine f.
674 !               in the full matrix case (miter = 1), ml and mu are
675 !          ignored, and the jacobian is to be loaded into pd in
676 !          columnwise manner, with df(i)/dy(j) loaded into pd(i,j).
677 !               in the band matrix case (miter = 4), the elements
678 !          within the band are to be loaded into pd in columnwise
679 !          manner, with diagonal lines of df/dy loaded into the rows
680 !          of pd. thus df(i)/dy(j) is to be loaded into pd(i-j+mu+1,j).
681 !          ml and mu are the half-bandwidth parameters. (see iwork).
682 !          the locations in pd in the two triangular areas which
683 !          correspond to nonexistent matrix elements can be ignored
684 !          or loaded arbitrarily, as they are overwritten by dvode.
685 !               jac need not provide df/dy exactly.  a crude
686 !          approximation (possibly with a smaller bandwidth) will do.
687 !               in either case, pd is preset to zero by the solver,
688 !          so that only the nonzero elements need be loaded by jac.
689 !          each call to jac is preceded by a call to f with the same
690 !          arguments neq, t, and y.  thus to gain some efficiency,
691 !          intermediate quantities shared by both calculations may be
692 !          saved in a user common block by f and not recomputed by jac,
693 !          if desired.  also, jac may alter the y array, if desired.
694 !          jac must be declared external in the calling program.
695 !               subroutine jac may access user-defined real and integer
696 !          work arrays, rpar and ipar, whose dimensions are set by the
697 !          user in the main program.
699 ! mf     = the method flag.  used only for input.  the legal values of
700 !          mf are 10, 11, 12, 13, 14, 15, 20, 21, 22, 23, 24, 25,
701 !          -11, -12, -14, -15, -21, -22, -24, -25.
702 !          mf is a signed two-digit integer, mf = jsv*(10*meth + miter).
703 !          jsv = sign(mf) indicates the jacobian-saving strategy:
704 !            jsv =  1 means a copy of the jacobian is saved for reuse
705 !                     in the corrector iteration algorithm.
706 !            jsv = -1 means a copy of the jacobian is not saved
707 !                     (valid only for miter = 1, 2, 4, or 5).
708 !          meth indicates the basic linear multistep method:
709 !            meth = 1 means the implicit adams method.
710 !            meth = 2 means the method based on backward
711 !                     differentiation formulas (bdf-s).
712 !          miter indicates the corrector iteration method:
713 !            miter = 0 means functional iteration (no jacobian matrix
714 !                      is involved).
715 !            miter = 1 means chord iteration with a user-supplied
716 !                      full (neq by neq) jacobian.
717 !            miter = 2 means chord iteration with an internally
718 !                      generated (difference quotient) full jacobian
719 !                      (using neq extra calls to f per df/dy value).
720 !            miter = 3 means chord iteration with an internally
721 !                      generated diagonal jacobian approximation
722 !                      (using 1 extra call to f per df/dy evaluation).
723 !            miter = 4 means chord iteration with a user-supplied
724 !                      banded jacobian.
725 !            miter = 5 means chord iteration with an internally
726 !                      generated banded jacobian (using ml+mu+1 extra
727 !                      calls to f per df/dy evaluation).
728 !          if miter = 1 or 4, the user must supply a subroutine jac
729 !          (the name is arbitrary) as described above under jac.
730 !          for other values of miter, a dummy argument can be used.
732 ! rpar     user-specified array used to communicate real parameters
733 !          to user-supplied subroutines.  if rpar is a vector, then
734 !          it must be dimensioned in the user's main program.  if it
735 !          is unused or it is a scalar, then it need not be
736 !          dimensioned.
738 ! ipar     user-specified array used to communicate integer parameter
739 !          to user-supplied subroutines.  the comments on dimensioning
740 !          rpar apply to ipar.
741 !-----------------------------------------------------------------------
742 ! optional input.
744 ! the following is a list of the optional input provided for in the
745 ! call sequence.  (see also part ii.)  for each such input variable,
746 ! this table lists its name as used in this documentation, its
747 ! location in the call sequence, its meaning, and the default value.
748 ! the use of any of this input requires iopt = 1, and in that
749 ! case all of this input is examined.  a value of zero for any
750 ! of these optional input variables will cause the default value to be
751 ! used.  thus to use a subset of the optional input, simply preload
752 ! locations 5 to 10 in rwork and iwork to 0.0 and 0 respectively, and
753 ! then set those of interest to nonzero values.
755 ! name    location      meaning and default value
757 ! h0      rwork(5)  the step size to be attempted on the first step.
758 !                   the default value is determined by the solver.
760 ! hmax    rwork(6)  the maximum absolute step size allowed.
761 !                   the default value is infinite.
763 ! hmin    rwork(7)  the minimum absolute step size allowed.
764 !                   the default value is 0.  (this lower bound is not
765 !                   enforced on the final step before reaching tcrit
766 !                   when itask = 4 or 5.)
768 ! maxord  iwork(5)  the maximum order to be allowed.  the default
769 !                   value is 12 if meth = 1, and 5 if meth = 2.
770 !                   if maxord exceeds the default value, it will
771 !                   be reduced to the default value.
772 !                   if maxord is changed during the problem, it may
773 !                   cause the current order to be reduced.
775 ! mxstep  iwork(6)  maximum number of (internally defined) steps
776 !                   allowed during one call to the solver.
777 !                   the default value is 500.
779 ! mxhnil  iwork(7)  maximum number of messages printed (per problem)
780 !                   warning that t + h = t on a step (h = step size).
781 !                   this must be positive to result in a non-default
782 !                   value.  the default value is 10.
784 !-----------------------------------------------------------------------
785 ! optional output.
787 ! as optional additional output from dvode, the variables listed
788 ! below are quantities related to the performance of dvode
789 ! which are available to the user.  these are communicated by way of
790 ! the work arrays, but also have internal mnemonic names as shown.
791 ! except where stated otherwise, all of this output is defined
792 ! on any successful return from dvode, and on any return with
793 ! istate = -1, -2, -4, -5, or -6.  on an illegal input return
794 ! (istate = -3), they will be unchanged from their existing values
795 ! (if any), except possibly for tolsf, lenrw, and leniw.
796 ! on any error return, output relevant to the error will be defined,
797 ! as noted below.
799 ! name    location      meaning
801 ! hu      rwork(11) the step size in t last used (successfully).
803 ! hcur    rwork(12) the step size to be attempted on the next step.
805 ! tcur    rwork(13) the current value of the independent variable
806 !                   which the solver has actually reached, i.e. the
807 !                   current internal mesh point in t.  in the output,
808 !                   tcur will always be at least as far from the
809 !                   initial value of t as the current argument t,
810 !                   but may be farther (if interpolation was done).
812 ! tolsf   rwork(14) a tolerance scale factor, greater than 1.0,
813 !                   computed when a request for too much accuracy was
814 !                   detected (istate = -3 if detected at the start of
815 !                   the problem, istate = -2 otherwise).  if itol is
816 !                   left unaltered but rtol and atol are uniformly
817 !                   scaled up by a factor of tolsf for the next call,
818 !                   then the solver is deemed likely to succeed.
819 !                   (the user may also ignore tolsf and alter the
820 !                   tolerance parameters in any other way appropriate.)
822 ! nst     iwork(11) the number of steps taken for the problem so far.
824 ! nfe     iwork(12) the number of f evaluations for the problem so far.
826 ! nje     iwork(13) the number of jacobian evaluations so far.
828 ! nqu     iwork(14) the method order last used (successfully).
830 ! nqcur   iwork(15) the order to be attempted on the next step.
832 ! imxer   iwork(16) the index of the component of largest magnitude in
833 !                   the weighted local error vector ( e(i)/ewt(i) ),
834 !                   on an error return with istate = -4 or -5.
836 ! lenrw   iwork(17) the length of rwork actually required.
837 !                   this is defined on normal returns and on an illegal
838 !                   input return for insufficient storage.
840 ! leniw   iwork(18) the length of iwork actually required.
841 !                   this is defined on normal returns and on an illegal
842 !                   input return for insufficient storage.
844 ! nlu     iwork(19) the number of matrix lu decompositions so far.
846 ! nni     iwork(20) the number of nonlinear (newton) iterations so far.
848 ! ncfn    iwork(21) the number of convergence failures of the nonlinear
849 !                   solver so far.
851 ! netf    iwork(22) the number of error test failures of the integrator
852 !                   so far.
854 ! the following two arrays are segments of the rwork array which
855 ! may also be of interest to the user as optional output.
856 ! for each array, the table below gives its internal name,
857 ! its base address in rwork, and its description.
859 ! name    base address      description
861 ! yh      21             the nordsieck history array, of size nyh by
862 !                        (nqcur + 1), where nyh is the initial value
863 !                        of neq.  for j = 0,1,...,nqcur, column j+1
864 !                        of yh contains hcur**j/factorial(j) times
865 !                        the j-th derivative of the interpolating
866 !                        polynomial currently representing the
867 !                        solution, evaluated at t = tcur.
869 ! acor     lenrw-neq+1   array of size neq used for the accumulated
870 !                        corrections on each step, scaled in the output
871 !                        to represent the estimated local error in y
872 !                        on the last step.  this is the vector e in
873 !                        the description of the error control.  it is
874 !                        defined only on a successful return from dvode.
876 !-----------------------------------------------------------------------
877 ! interrupting and restarting
879 ! if the integration of a given problem by dvode is to be
880 ! interrrupted and then later continued, such as when restarting
881 ! an interrupted run or alternating between two or more ode problems,
882 ! the user should save, following the return from the last dvode call
883 ! prior to the interruption, the contents of the call sequence
884 ! variables and internal common blocks, and later restore these
885 ! values before the next dvode call for that problem.  to save
886 ! and restore the common blocks, use subroutine dvsrco, as
887 ! described below in part ii.
889 ! in addition, if non-default values for either lun or mflag are
890 ! desired, an extra call to xsetun and/or xsetf should be made just
891 ! before continuing the integration.  see part ii below for details.
893 !-----------------------------------------------------------------------
894 ! part ii.  other routines callable.
896 ! the following are optional calls which the user may make to
897 ! gain additional capabilities in conjunction with dvode.
898 ! (the routines xsetun and xsetf are designed to conform to the
899 ! slatec error handling package.)
901 !     form of call                  function
902 !  call xsetun(lun)           set the logical unit number, lun, for
903 !                             output of messages from dvode, if
904 !                             the default is not desired.
905 !                             the default value of lun is 6.
907 !  call xsetf(mflag)          set a flag to control the printing of
908 !                             messages by dvode.
909 !                             mflag = 0 means do not print. (danger:
910 !                             this risks losing valuable information.)
911 !                             mflag = 1 means print (the default).
913 !                             either of the above calls may be made at
914 !                             any time and will take effect immediately.
916 !  call dvsrco(rsav,isav,job) saves and restores the contents of
917 !                             the internal common blocks used by
918 !                             dvode. (see part iii below.)
919 !                             rsav must be a real array of length 49
920 !                             or more, and isav must be an integer
921 !                             array of length 40 or more.
922 !                             job=1 means save common into rsav/isav.
923 !                             job=2 means restore common from rsav/isav.
924 !                                dvsrco is useful if one is
925 !                             interrupting a run and restarting
926 !                             later, or alternating between two or
927 !                             more problems solved with dvode.
929 !  call dvindy(,,,,,)         provide derivatives of y, of various
930 !        (see below.)         orders, at a specified point t, if
931 !                             desired.  it may be called only after
932 !                             a successful return from dvode.
934 ! the detailed instructions for using dvindy are as follows.
935 ! the form of the call is:
937 !  call dvindy (t, k, rwork(21), nyh, dky, iflag)
939 ! the input parameters are:
941 ! t         = value of independent variable where answers are desired
942 !             (normally the same as the t last returned by dvode).
943 !             for valid results, t must lie between tcur - hu and tcur.
944 !             (see optional output for tcur and hu.)
945 ! k         = integer order of the derivative desired.  k must satisfy
946 !             0 .le. k .le. nqcur, where nqcur is the current order
947 !             (see optional output).  the capability corresponding
948 !             to k = 0, i.e. computing y(t), is already provided
949 !             by dvode directly.  since nqcur .ge. 1, the first
950 !             derivative dy/dt is always available with dvindy.
951 ! rwork(21) = the base address of the history array yh.
952 ! nyh       = column length of yh, equal to the initial value of neq.
954 ! the output parameters are:
956 ! dky       = a real array of length neq containing the computed value
957 !             of the k-th derivative of y(t).
958 ! iflag     = integer flag, returned as 0 if k and t were legal,
959 !             -1 if k was illegal, and -2 if t was illegal.
960 !             on an error return, a message is also written.
961 !-----------------------------------------------------------------------
962 ! part iii.  common blocks.
963 ! if dvode is to be used in an overlay situation, the user
964 ! must declare, in the primary overlay, the variables in:
965 !   (1) the call sequence to dvode,
966 !   (2) the two internal common blocks
967 !         /dvod_cmn01/  of length  81  (48 double precision words
968 !                         followed by 33 integer words),
969 !         /dvod_cmn02/  of length  9  (1 double precision word
970 !                         followed by 8 integer words),
972 ! if dvode is used on a system in which the contents of internal
973 ! common blocks are not preserved between calls, the user should
974 ! declare the above two common blocks in his main program to insure
975 ! that their contents are preserved.
977 !-----------------------------------------------------------------------
978 ! part iv.  optionally replaceable solver routines.
980 ! below are descriptions of two routines in the dvode package which
981 ! relate to the measurement of errors.  either routine can be
982 ! replaced by a user-supplied version, if desired.  however, since such
983 ! a replacement may have a major impact on performance, it should be
984 ! done only when absolutely necessary, and only with great caution.
985 ! (note: the means by which the package version of a routine is
986 ! superseded by the user's version may be system-dependent.)
988 ! (a) dewset.
989 ! the following subroutine is called just before each internal
990 ! integration step, and sets the array of error weights, ewt, as
991 ! described under itol/rtol/atol above:
992 !     subroutine dewset (neq, itol, rtol, atol, ycur, ewt)
993 ! where neq, itol, rtol, and atol are as in the dvode call sequence,
994 ! ycur contains the current dependent variable vector, and
995 ! ewt is the array of weights set by dewset.
997 ! if the user supplies this subroutine, it must return in ewt(i)
998 ! (i = 1,...,neq) a positive quantity suitable for comparison with
999 ! errors in y(i).  the ewt array returned by dewset is passed to the
1000 ! dvnorm routine (see below.), and also used by dvode in the computation
1001 ! of the optional output imxer, the diagonal jacobian approximation,
1002 ! and the increments for difference quotient jacobians.
1004 ! in the user-supplied version of dewset, it may be desirable to use
1005 ! the current values of derivatives of y.  derivatives up to order nq
1006 ! are available from the history array yh, described above under
1007 ! optional output.  in dewset, yh is identical to the ycur array,
1008 ! extended to nq + 1 columns with a column length of nyh and scale
1009 ! factors of h**j/factorial(j).  on the first call for the problem,
1010 ! given by nst = 0, nq is 1 and h is temporarily set to 1.0.
1011 ! nyh is the initial value of neq.  the quantities nq, h, and nst
1012 ! can be obtained by including in dewset the statements:
1013 !     double precision rvod, h, hu
1014 !     common /dvod_cmn01/ rvod(48), ivod(33)
1015 !     common /dvod_cmn02/ hu, ncfn, netf, nfe, nje, nlu, nni, nqu, nst
1016 !     nq = ivod(28)
1017 !     h = rvod(21)
1018 ! thus, for example, the current value of dy/dt can be obtained as
1019 ! ycur(nyh+i)/h  (i=1,...,neq)  (and the division by h is
1020 ! unnecessary when nst = 0).
1022 ! (b) dvnorm.
1023 ! the following is a real function routine which computes the weighted
1024 ! root-mean-square norm of a vector v:
1025 !     d = dvnorm (n, v, w)
1026 ! where:
1027 !   n = the length of the vector,
1028 !   v = real array of length n containing the vector,
1029 !   w = real array of length n containing weights,
1030 !   d = sqrt( (1/n) * sum(v(i)*w(i))**2 ).
1031 ! dvnorm is called with n = neq and with w(i) = 1.0/ewt(i), where
1032 ! ewt is as set by subroutine dewset.
1034 ! if the user supplies this function, it should return a non-negative
1035 ! value of dvnorm suitable for use in the error control in dvode.
1036 ! none of the arguments should be altered by dvnorm.
1037 ! for example, a user-supplied dvnorm routine might:
1038 !   -substitute a max-norm of (v(i)*w(i)) for the rms-norm, or
1039 !   -ignore some components of v in the norm, with the effect of
1040 !    suppressing the error control on those components of y.
1041 !-----------------------------------------------------------------------
1042 ! revision history (yyyymmdd)
1043 !  19890615  date written.  initial release.
1044 !  19890922  added interrupt/restart ability, minor changes throughout.
1045 !  19910228  minor revisions in line format,  prologue, etc.
1046 !  19920227  modifications by d. pang:
1047 !            (1) applied subgennam to get generic intrinsic names.
1048 !            (2) changed intrinsic names to generic in comments.
1049 !            (3) added *deck lines before each routine.
1050 !  19920721  names of routines and labeled common blocks changed, so as
1051 !            to be unique in combined single/double precision code (ach).
1052 !  19920722  minor revisions to prologue (ach).
1053 !  19920831  conversion to double precision done (ach).
1054 !  19921106  fixed minor bug: etaq,etaqm1 in dvstep save statement (ach).
1055 !  19921118  changed lunsav/mflgsv to ixsav (ach).
1056 !  19941222  removed mf overwrite; attached sign to h in estimated second
1057 !            deriv. in dvhin; misc. comment changes throughout (ach).
1058 !  19970515  minor corrections to comments in prologue, dvjac (ach).
1059 !  19981111  corrected block b by adding final line, go to 200 (ach).
1060 !  20020430  various upgrades (ach): use odepack error handler package.
1061 !            replaced d1mach by dumach.  various changes to main
1062 !            prologue and other routine prologues.
1063 !-----------------------------------------------------------------------
1064 ! other routines in the dvode package.
1066 ! in addition to subroutine dvode, the dvode package includes the
1067 ! following subroutines and function routines:
1068 !  dvhin     computes an approximate step size for the initial step.
1069 !  dvindy    computes an interpolated value of the y vector at t = tout.
1070 !  dvstep    is the core integrator, which does one step of the
1071 !            integration and the associated error control.
1072 !  dvset     sets all method coefficients and test constants.
1073 !  dvnlsd    solves the underlying nonlinear system -- the corrector.
1074 !  dvjac     computes and preprocesses the jacobian matrix j = df/dy
1075 !            and the newton iteration matrix p = i - (h/l1)*j.
1076 !  dvsol     manages solution of linear system in chord iteration.
1077 !  dvjust    adjusts the history array on a change of order.
1078 !  dewset    sets the error weight vector ewt before each step.
1079 !  dvnorm    computes the weighted r.m.s. norm of a vector.
1080 !  dvsrco    is a user-callable routine to save and restore
1081 !            the contents of the internal common blocks.
1082 !  dacopy    is a routine to copy one two-dimensional array to another.
1083 !  dgefa and dgesl   are routines from linpack for solving full
1084 !            systems of linear algebraic equations.
1085 !  dgbfa and dgbsl   are routines from linpack for solving banded
1086 !            linear systems.
1087 !  daxpy, dscal, and dcopy are basic linear algebra modules (blas).
1088 !  dumach    sets the unit roundoff of the machine.
1089 !  xerrwd, xsetun, xsetf, ixsav, and iumach handle the printing of all
1090 !            error messages and warnings.  xerrwd is machine-dependent.
1091 ! note:  dvnorm, dumach, ixsav, and iumach are function routines.
1092 ! all the others are subroutines.
1094 !-----------------------------------------------------------------------
1096 !! type declarations for labeled common block dvod_cmn01 --------------------
1098 !      double precision acnrm, ccmxj, conp, crate, drc, el,   &
1099 !           eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
1100 !           rc, rl1, tau, tq, tn, uround
1101 !      integer icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
1102 !              l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
1103 !              locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
1104 !              n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
1105 !              nslp, nyh
1107 !! type declarations for labeled common block dvod_cmn02 --------------------
1109 !      double precision hu
1110 !      integer ncfn, netf, nfe, nje, nlu, nni, nqu, nst
1112 ! type declarations for local variables --------------------------------
1114 ! 27-oct-2005 rce - do not declare functions that are in the module
1115 !     external dvnlsd
1116       logical ihit
1117       double precision atoli, big, ewti, four, h0, hmax, hmx, hun, one,   &
1118          pt2, rh, rtoli, size, tcrit, tnext, tolsf, tp, two, zero
1119       integer i, ier, iflag, imxer, jco, kgo, leniw, lenj, lenp, lenrw,   &
1120          lenwm, lf0, mband, mfa, ml, mord, mu, mxhnl0, mxstp0, niter,   &
1121          nslast
1122       character*80 msg
1124 ! type declaration for function subroutines called ---------------------
1126 ! 27-oct-2005 rce - do not declare functions that are in the module
1127 !     double precision dumach, dvnorm
1129       dimension mord(2)
1130 !-----------------------------------------------------------------------
1131 ! the following fortran-77 declaration is to cause the values of the
1132 ! listed (local) variables to be saved between calls to dvode.
1133 !-----------------------------------------------------------------------
1134       save mord, mxhnl0, mxstp0
1135       save zero, one, two, four, pt2, hun
1136 !-----------------------------------------------------------------------
1137 ! the following internal common blocks contain variables which are
1138 ! communicated between subroutines in the dvode package, or which are
1139 ! to be saved between calls to dvode.
1140 ! in each block, real variables precede integers.
1141 ! the block /dvod_cmn01/ appears in subroutines dvode, dvindy, dvstep,
1142 ! dvset, dvnlsd, dvjac, dvsol, dvjust and dvsrco.
1143 ! the block /dvod_cmn02/ appears in subroutines dvode, dvindy, dvstep,
1144 ! dvnlsd, dvjac, and dvsrco.
1146 ! the variables stored in the internal common blocks are as follows:
1148 ! acnrm  = weighted r.m.s. norm of accumulated correction vectors.
1149 ! ccmxj  = threshhold on drc for updating the jacobian. (see drc.)
1150 ! conp   = the saved value of tq(5).
1151 ! crate  = estimated corrector convergence rate constant.
1152 ! drc    = relative change in h*rl1 since last dvjac call.
1153 ! el     = real array of integration coefficients.  see dvset.
1154 ! eta    = saved tentative ratio of new to old h.
1155 ! etamax = saved maximum value of eta to be allowed.
1156 ! h      = the step size.
1157 ! hmin   = the minimum absolute value of the step size h to be used.
1158 ! hmxi   = inverse of the maximum absolute value of h to be used.
1159 !          hmxi = 0.0 is allowed and corresponds to an infinite hmax.
1160 ! hnew   = the step size to be attempted on the next step.
1161 ! hscal  = stepsize in scaling of yh array.
1162 ! prl1   = the saved value of rl1.
1163 ! rc     = ratio of current h*rl1 to value on last dvjac call.
1164 ! rl1    = the reciprocal of the coefficient el(1).
1165 ! tau    = real vector of past nq step sizes, length 13.
1166 ! tq     = a real vector of length 5 in which dvset stores constants
1167 !          used for the convergence test, the error test, and the
1168 !          selection of h at a new order.
1169 ! tn     = the independent variable, updated on each step taken.
1170 ! uround = the machine unit roundoff.  the smallest positive real number
1171 !          such that  1.0 + uround .ne. 1.0
1172 ! icf    = integer flag for convergence failure in dvnlsd:
1173 !            0 means no failures.
1174 !            1 means convergence failure with out of date jacobian
1175 !                   (recoverable error).
1176 !            2 means convergence failure with current jacobian or
1177 !                   singular matrix (unrecoverable error).
1178 ! init   = saved integer flag indicating whether initialization of the
1179 !          problem has been done (init = 1) or not.
1180 ! ipup   = saved flag to signal updating of newton matrix.
1181 ! jcur   = output flag from dvjac showing jacobian status:
1182 !            jcur = 0 means j is not current.
1183 !            jcur = 1 means j is current.
1184 ! jstart = integer flag used as input to dvstep:
1185 !            0  means perform the first step.
1186 !            1  means take a new step continuing from the last.
1187 !            -1 means take the next step with a new value of maxord,
1188 !                  hmin, hmxi, n, meth, miter, and/or matrix parameters.
1189 !          on return, dvstep sets jstart = 1.
1190 ! jsv    = integer flag for jacobian saving, = sign(mf).
1191 ! kflag  = a completion code from dvstep with the following meanings:
1192 !               0      the step was succesful.
1193 !              -1      the requested error could not be achieved.
1194 !              -2      corrector convergence could not be achieved.
1195 !              -3, -4  fatal error in vnls (can not occur here).
1196 ! kuth   = input flag to dvstep showing whether h was reduced by the
1197 !          driver.  kuth = 1 if h was reduced, = 0 otherwise.
1198 ! l      = integer variable, nq + 1, current order plus one.
1199 ! lmax   = maxord + 1 (used for dimensioning).
1200 ! locjs  = a pointer to the saved jacobian, whose storage starts at
1201 !          wm(locjs), if jsv = 1.
1202 ! lyh, lewt, lacor, lsavf, lwm, liwm = saved integer pointers
1203 !          to segments of rwork and iwork.
1204 ! maxord = the maximum order of integration method to be allowed.
1205 ! meth/miter = the method flags.  see mf.
1206 ! msbj   = the maximum number of steps between j evaluations, = 50.
1207 ! mxhnil = saved value of optional input mxhnil.
1208 ! mxstep = saved value of optional input mxstep.
1209 ! n      = the number of first-order odes, = neq.
1210 ! newh   = saved integer to flag change of h.
1211 ! newq   = the method order to be used on the next step.
1212 ! nhnil  = saved counter for occurrences of t + h = t.
1213 ! nq     = integer variable, the current integration method order.
1214 ! nqnyh  = saved value of nq*nyh.
1215 ! nqwait = a counter controlling the frequency of order changes.
1216 !          an order change is about to be considered if nqwait = 1.
1217 ! nslj   = the number of steps taken as of the last jacobian update.
1218 ! nslp   = saved value of nst as of last newton matrix update.
1219 ! nyh    = saved value of the initial value of neq.
1220 ! hu     = the step size in t last used.
1221 ! ncfn   = number of nonlinear convergence failures so far.
1222 ! netf   = the number of error test failures of the integrator so far.
1223 ! nfe    = the number of f evaluations for the problem so far.
1224 ! nje    = the number of jacobian evaluations so far.
1225 ! nlu    = the number of matrix lu decompositions so far.
1226 ! nni    = number of nonlinear iterations so far.
1227 ! nqu    = the method order last used.
1228 ! nst    = the number of steps taken for the problem so far.
1229 !-----------------------------------------------------------------------
1230 !      common /dvod_cmn01/ acnrm, ccmxj, conp, crate, drc, el(13),   &
1231 !                      eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
1232 !                      rc, rl1, tau(13), tq(5), tn, uround,   &
1233 !                      icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
1234 !                      l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
1235 !                      locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
1236 !                      n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
1237 !                      nslp, nyh
1238 !      common /dvod_cmn02/ hu, ncfn, netf, nfe, nje, nlu, nni, nqu, nst
1240 ! in this routine only, declare h and n as local variables
1241 !    before/after calls where cmn12 is passed as an argument,
1242 !    load/unload them to/from cmn12
1243       type( dvode_cmn_vars ) :: cmn12
1244       double precision h
1245       integer n
1248       data  mord(1) /12/, mord(2) /5/, mxstp0 /500/, mxhnl0 /10/
1249       data zero /0.0d0/, one /1.0d0/, two /2.0d0/, four /4.0d0/,   &
1250            pt2 /0.2d0/, hun /100.0d0/
1251 !-----------------------------------------------------------------------
1252 ! block a.
1253 ! this code block is executed on every call.
1254 ! it tests istate and itask for legality and branches appropriately.
1255 ! if istate .gt. 1 but the flag init shows that initialization has
1256 ! not yet been done, an error return occurs.
1257 ! if istate = 1 and tout = t, return immediately.
1258 !-----------------------------------------------------------------------
1260 ! in this modified-for-wrf version of dvode, istate must be 1
1261       if (istate .ne. 1) then
1262          msg = '*** module_cmu_dvode_solver/dvode -- ' // &
1263                'fatal error, istate must be 1'
1264          call wrf_error_fatal( msg )
1265       end if
1267       if (istate .lt. 1 .or. istate .gt. 3) go to 601
1268       if (itask .lt. 1 .or. itask .gt. 5) go to 602
1269       if (istate .eq. 1) go to 10
1270       if (cmn12%init .ne. 1) go to 603
1271       if (istate .eq. 2) go to 200
1272       go to 20
1273  10   cmn12%init = 0
1274       if (tout .eq. t) return
1275 !-----------------------------------------------------------------------
1276 ! block b.
1277 ! the next code block is executed for the initial call (istate = 1),
1278 ! or for a continuation call with parameter changes (istate = 3).
1279 ! it contains checking of all input and various initializations.
1281 ! first check legality of the non-optional input neq, itol, iopt,
1282 ! mf, ml, and mu.
1283 !-----------------------------------------------------------------------
1284  20   if (neq .le. 0) go to 604
1285       if (istate .eq. 1) go to 25
1286       if (neq .gt. n) go to 605
1287  25   n = neq
1288       if (itol .lt. 1 .or. itol .gt. 4) go to 606
1289       if (iopt .lt. 0 .or. iopt .gt. 1) go to 607
1290       cmn12%jsv = sign(1,mf)
1291       mfa = abs(mf)
1292       cmn12%meth = mfa/10
1293       cmn12%miter = mfa - 10*cmn12%meth
1294       if (cmn12%meth .lt. 1 .or. cmn12%meth .gt. 2) go to 608
1295       if (cmn12%miter .lt. 0 .or. cmn12%miter .gt. 5) go to 608
1296       if (cmn12%miter .le. 3) go to 30
1297       ml = iwork(1)
1298       mu = iwork(2)
1299       if (ml .lt. 0 .or. ml .ge. n) go to 609
1300       if (mu .lt. 0 .or. mu .ge. n) go to 610
1301  30   continue
1302 ! next process and check the optional input. ---------------------------
1303       if (iopt .eq. 1) go to 40
1304       cmn12%maxord = mord(cmn12%meth)
1305       cmn12%mxstep = mxstp0
1306       cmn12%mxhnil = mxhnl0
1307       if (istate .eq. 1) h0 = zero
1308       cmn12%hmxi = zero
1309       cmn12%hmin = zero
1310       go to 60
1311  40   cmn12%maxord = iwork(5)
1312       if (cmn12%maxord .lt. 0) go to 611
1313       if (cmn12%maxord .eq. 0) cmn12%maxord = 100
1314       cmn12%maxord = min(cmn12%maxord,mord(cmn12%meth))
1315       cmn12%mxstep = iwork(6)
1316       if (cmn12%mxstep .lt. 0) go to 612
1317       if (cmn12%mxstep .eq. 0) cmn12%mxstep = mxstp0
1318       cmn12%mxhnil = iwork(7)
1319       if (cmn12%mxhnil .lt. 0) go to 613
1320       if (cmn12%mxhnil .eq. 0) cmn12%mxhnil = mxhnl0
1321       if (istate .ne. 1) go to 50
1322       h0 = rwork(5)
1323       if ((tout - t)*h0 .lt. zero) go to 614
1324  50   hmax = rwork(6)
1325       if (hmax .lt. zero) go to 615
1326       cmn12%hmxi = zero
1327       if (hmax .gt. zero) cmn12%hmxi = one/hmax
1328       cmn12%hmin = rwork(7)
1329       if (cmn12%hmin .lt. zero) go to 616
1330 !-----------------------------------------------------------------------
1331 ! set work array pointers and check lengths lrw and liw.
1332 ! pointers to segments of rwork and iwork are named by prefixing l to
1333 ! the name of the segment.  e.g., the segment yh starts at rwork(lyh).
1334 ! segments of rwork (in order) are denoted  yh, wm, ewt, savf, acor.
1335 ! within wm, locjs is the location of the saved jacobian (jsv .gt. 0).
1336 !-----------------------------------------------------------------------
1337  60   cmn12%lyh = 21
1338       if (istate .eq. 1) cmn12%nyh = n
1339       cmn12%lwm = cmn12%lyh + (cmn12%maxord + 1)*cmn12%nyh
1340       jco = max(0,cmn12%jsv)
1341       if (cmn12%miter .eq. 0) lenwm = 0
1342       if (cmn12%miter .eq. 1 .or. cmn12%miter .eq. 2) then
1343         lenwm = 2 + (1 + jco)*n*n
1344         cmn12%locjs = n*n + 3
1345       endif
1346       if (cmn12%miter .eq. 3) lenwm = 2 + n
1347       if (cmn12%miter .eq. 4 .or. cmn12%miter .eq. 5) then
1348         mband = ml + mu + 1
1349         lenp = (mband + ml)*n
1350         lenj = mband*n
1351         lenwm = 2 + lenp + jco*lenj
1352         cmn12%locjs = lenp + 3
1353         endif
1354       cmn12%lewt = cmn12%lwm + lenwm
1355       cmn12%lsavf = cmn12%lewt + n
1356       cmn12%lacor = cmn12%lsavf + n
1357       lenrw = cmn12%lacor + n - 1
1358       iwork(17) = lenrw
1359       cmn12%liwm = 1
1360       leniw = 30 + n
1361       if (cmn12%miter .eq. 0 .or. cmn12%miter .eq. 3) leniw = 30
1362       iwork(18) = leniw
1363       if (lenrw .gt. lrw) go to 617
1364       if (leniw .gt. liw) go to 618
1365 ! check rtol and atol for legality. ------------------------------------
1366       rtoli = rtol(1)
1367       atoli = atol(1)
1368       do 70 i = 1,n
1369         if (itol .ge. 3) rtoli = rtol(i)
1370         if (itol .eq. 2 .or. itol .eq. 4) atoli = atol(i)
1371         if (rtoli .lt. zero) go to 619
1372         if (atoli .lt. zero) go to 620
1373  70     continue
1374       if (istate .eq. 1) go to 100
1375 ! if istate = 3, set flag to signal parameter changes to dvstep. -------
1376       cmn12%jstart = -1
1377       if (cmn12%nq .le. cmn12%maxord) go to 90
1378 ! maxord was reduced below nq.  copy yh(*,maxord+2) into savf. ---------
1379       call dcopy (n, rwork(cmn12%lwm), 1, rwork(cmn12%lsavf), 1)
1380 ! reload wm(1) = rwork(lwm), since lwm may have changed. ---------------
1381  90   if (cmn12%miter .gt. 0) rwork(cmn12%lwm) = sqrt(cmn12%uround)
1382       go to 200
1383 !-----------------------------------------------------------------------
1384 ! block c.
1385 ! the next block is for the initial call only (istate = 1).
1386 ! it contains all remaining initializations, the initial call to f,
1387 ! and the calculation of the initial step size.
1388 ! the error weights in ewt are inverted after being loaded.
1389 !-----------------------------------------------------------------------
1390  100  cmn12%uround = dumach()
1391       cmn12%tn = t
1392       if (itask .ne. 4 .and. itask .ne. 5) go to 110
1393       tcrit = rwork(1)
1394       if ((tcrit - tout)*(tout - t) .lt. zero) go to 625
1395       if (h0 .ne. zero .and. (t + h0 - tcrit)*h0 .gt. zero)   &
1396          h0 = tcrit - t
1397  110  cmn12%jstart = 0
1398       if (cmn12%miter .gt. 0) rwork(cmn12%lwm) = sqrt(cmn12%uround)
1399       cmn12%ccmxj = pt2
1400       cmn12%msbj = 50
1401       cmn12%nhnil = 0
1402       cmn12%nst = 0
1403       cmn12%nje = 0
1404       cmn12%nni = 0
1405       cmn12%ncfn = 0
1406       cmn12%netf = 0
1407       cmn12%nlu = 0
1408       cmn12%nslj = 0
1409       nslast = 0
1410       cmn12%hu = zero
1411       cmn12%nqu = 0
1412 ! initial call to f.  (lf0 points to yh(*,2).) -------------------------
1413       lf0 = cmn12%lyh + cmn12%nyh
1414       call f (n, t, y, rwork(lf0), rpar, ipar)
1415       cmn12%nfe = 1
1416 ! load the initial value vector in yh. ---------------------------------
1417       call dcopy (n, y, 1, rwork(cmn12%lyh), 1)
1418 ! load and invert the ewt array.  (h is temporarily set to 1.0.) -------
1419       cmn12%nq = 1
1420       h = one
1421       call dewset (n, itol, rtol, atol, rwork(cmn12%lyh), rwork(cmn12%lewt))
1422       do 120 i = 1,n
1423         if (rwork(i+cmn12%lewt-1) .le. zero) go to 621
1424  120    rwork(i+cmn12%lewt-1) = one/rwork(i+cmn12%lewt-1)
1425       if (h0 .ne. zero) go to 180
1426 ! call dvhin to set initial step size h0 to be attempted. --------------
1427       call dvhin (n, t, rwork(cmn12%lyh), rwork(lf0), f, rpar, ipar, tout,   &
1428          cmn12%uround, rwork(cmn12%lewt), itol, atol, y, rwork(cmn12%lacor), h0,   &
1429          niter, ier)
1430       cmn12%nfe = cmn12%nfe + niter
1431       if (ier .ne. 0) go to 622
1432 ! adjust h0 if necessary to meet hmax bound. ---------------------------
1433  180  rh = abs(h0)*cmn12%hmxi
1434       if (rh .gt. one) h0 = h0/rh
1435 ! load h with h0 and scale yh(*,2) by h0. ------------------------------
1436       h = h0
1437       call dscal (n, h0, rwork(lf0), 1)
1438       go to 270
1439 !-----------------------------------------------------------------------
1440 ! block d.
1441 ! the next code block is for continuation calls only (istate = 2 or 3)
1442 ! and is to check stop conditions before taking a step.
1443 !-----------------------------------------------------------------------
1444  200  nslast = cmn12%nst
1445       cmn12%kuth = 0
1446       go to (210, 250, 220, 230, 240), itask
1447  210  if ((cmn12%tn - tout)*h .lt. zero) go to 250
1448       cmn12%h = h ; cmn12%n = n   ! load h, n into cmn12
1449       call dvindy (tout, 0, rwork(cmn12%lyh), cmn12%nyh, y, iflag, cmn12)
1450       h = cmn12%h ; n = cmn12%n   ! unload h, n from cmn12
1451       if (iflag .ne. 0) go to 627
1452       t = tout
1453       go to 420
1454  220  tp = cmn12%tn - cmn12%hu*(one + hun*cmn12%uround)
1455       if ((tp - tout)*h .gt. zero) go to 623
1456       if ((cmn12%tn - tout)*h .lt. zero) go to 250
1457       go to 400
1458  230  tcrit = rwork(1)
1459       if ((cmn12%tn - tcrit)*h .gt. zero) go to 624
1460       if ((tcrit - tout)*h .lt. zero) go to 625
1461       if ((cmn12%tn - tout)*h .lt. zero) go to 245
1462       cmn12%h = h ; cmn12%n = n   ! load h, n into cmn12
1463       call dvindy (tout, 0, rwork(cmn12%lyh), cmn12%nyh, y, iflag, cmn12)
1464       h = cmn12%h ; n = cmn12%n   ! unload h, n from cmn12
1465       if (iflag .ne. 0) go to 627
1466       t = tout
1467       go to 420
1468  240  tcrit = rwork(1)
1469       if ((cmn12%tn - tcrit)*h .gt. zero) go to 624
1470  245  hmx = abs(cmn12%tn) + abs(h)
1471       ihit = abs(cmn12%tn - tcrit) .le. hun*cmn12%uround*hmx
1472       if (ihit) go to 400
1473       tnext = cmn12%tn + cmn12%hnew*(one + four*cmn12%uround)
1474       if ((tnext - tcrit)*h .le. zero) go to 250
1475       h = (tcrit - cmn12%tn)*(one - four*cmn12%uround)
1476       cmn12%kuth = 1
1477 !-----------------------------------------------------------------------
1478 ! block e.
1479 ! the next block is normally executed for all calls and contains
1480 ! the call to the one-step core integrator dvstep.
1482 ! this is a looping point for the integration steps.
1484 ! first check for too many steps being taken, update ewt (if not at
1485 ! start of problem), check for too much accuracy being requested, and
1486 ! check for h below the roundoff level in t.
1487 !-----------------------------------------------------------------------
1488  250  continue
1489       if ((cmn12%nst-nslast) .ge. cmn12%mxstep) go to 500
1490       call dewset (n, itol, rtol, atol, rwork(cmn12%lyh), rwork(cmn12%lewt))
1491       do 260 i = 1,n
1492         if (rwork(i+cmn12%lewt-1) .le. zero) go to 510
1493  260    rwork(i+cmn12%lewt-1) = one/rwork(i+cmn12%lewt-1)
1494  270  tolsf = cmn12%uround*dvnorm (n, rwork(cmn12%lyh), rwork(cmn12%lewt))
1495       if (tolsf .le. one) go to 280
1496       tolsf = tolsf*two
1497       if (cmn12%nst .eq. 0) go to 626
1498       go to 520
1499  280  if ((cmn12%tn + h) .ne. cmn12%tn) go to 290
1500       cmn12%nhnil = cmn12%nhnil + 1
1501       if (cmn12%nhnil .gt. cmn12%mxhnil) go to 290
1502       msg = 'dvode--  warning: internal t (=r1) and h (=r2) are'
1503       call xerrwd (msg, 50, 101, 1, 0, 0, 0, 0, zero, zero)
1504       msg='      such that in the machine, t + h = t on the next step  '
1505       call xerrwd (msg, 60, 101, 1, 0, 0, 0, 0, zero, zero)
1506       msg = '      (h = step size). solver will continue anyway'
1507       call xerrwd (msg, 50, 101, 1, 0, 0, 0, 2, cmn12%tn, h)
1508       if (cmn12%nhnil .lt. cmn12%mxhnil) go to 290
1509       msg = 'dvode--  above warning has been issued i1 times.  '
1510       call xerrwd (msg, 50, 102, 1, 0, 0, 0, 0, zero, zero)
1511       msg = '      it will not be issued again for this problem'
1512       call xerrwd (msg, 50, 102, 1, 1, cmn12%mxhnil, 0, 0, zero, zero)
1513  290  continue
1514 !-----------------------------------------------------------------------
1515 ! call dvstep (y, yh, nyh, yh, ewt, savf, vsav, acor,
1516 !              wm, iwm, f, jac, f, dvnlsd, rpar, ipar)
1517 !-----------------------------------------------------------------------
1518       cmn12%h = h ; cmn12%n = n   ! load h, n into cmn12
1519       call dvstep (y, rwork(cmn12%lyh), cmn12%nyh, rwork(cmn12%lyh), rwork(cmn12%lewt),   &
1520          rwork(cmn12%lsavf), y, rwork(cmn12%lacor), rwork(cmn12%lwm), iwork(cmn12%liwm),   &
1521          f, jac, f, dvnlsd, rpar, ipar, cmn12)
1522       h = cmn12%h ; n = cmn12%n   ! unload h, n from cmn12
1523       kgo = 1 - cmn12%kflag
1524 ! branch on kflag.  note: in this version, kflag can not be set to -3.
1525 !  kflag .eq. 0,   -1,  -2
1526       go to (300, 530, 540), kgo
1527 !-----------------------------------------------------------------------
1528 ! block f.
1529 ! the following block handles the case of a successful return from the
1530 ! core integrator (kflag = 0).  test for stop conditions.
1531 !-----------------------------------------------------------------------
1532  300  cmn12%init = 1
1533       cmn12%kuth = 0
1534       go to (310, 400, 330, 340, 350), itask
1535 ! itask = 1.  if tout has been reached, interpolate. -------------------
1536  310  if ((cmn12%tn - tout)*h .lt. zero) go to 250
1537       cmn12%h = h ; cmn12%n = n   ! load h, n into cmn12
1538       call dvindy (tout, 0, rwork(cmn12%lyh), cmn12%nyh, y, iflag, cmn12)
1539       h = cmn12%h ; n = cmn12%n   ! unload h, n from cmn12
1540       t = tout
1541       go to 420
1542 ! itask = 3.  jump to exit if tout was reached. ------------------------
1543  330  if ((cmn12%tn - tout)*h .ge. zero) go to 400
1544       go to 250
1545 ! itask = 4.  see if tout or tcrit was reached.  adjust h if necessary.
1546  340  if ((cmn12%tn - tout)*h .lt. zero) go to 345
1547       cmn12%h = h ; cmn12%n = n   ! load h, n into cmn12
1548       call dvindy (tout, 0, rwork(cmn12%lyh), cmn12%nyh, y, iflag, cmn12)
1549       h = cmn12%h ; n = cmn12%n   ! unload h, n from cmn12
1550       t = tout
1551       go to 420
1552  345  hmx = abs(cmn12%tn) + abs(h)
1553       ihit = abs(cmn12%tn - tcrit) .le. hun*cmn12%uround*hmx
1554       if (ihit) go to 400
1555       tnext = cmn12%tn + cmn12%hnew*(one + four*cmn12%uround)
1556       if ((tnext - tcrit)*h .le. zero) go to 250
1557       h = (tcrit - cmn12%tn)*(one - four*cmn12%uround)
1558       cmn12%kuth = 1
1559       go to 250
1560 ! itask = 5.  see if tcrit was reached and jump to exit. ---------------
1561  350  hmx = abs(cmn12%tn) + abs(h)
1562       ihit = abs(cmn12%tn - tcrit) .le. hun*cmn12%uround*hmx
1563 !-----------------------------------------------------------------------
1564 ! block g.
1565 ! the following block handles all successful returns from dvode.
1566 ! if itask .ne. 1, y is loaded from yh and t is set accordingly.
1567 ! istate is set to 2, and the optional output is loaded into the work
1568 ! arrays before returning.
1569 !-----------------------------------------------------------------------
1570  400  continue
1571       call dcopy (n, rwork(cmn12%lyh), 1, y, 1)
1572       t = cmn12%tn
1573       if (itask .ne. 4 .and. itask .ne. 5) go to 420
1574       if (ihit) t = tcrit
1575  420  istate = 2
1576       rwork(11) = cmn12%hu
1577       rwork(12) = cmn12%hnew
1578       rwork(13) = cmn12%tn
1579       iwork(11) = cmn12%nst
1580       iwork(12) = cmn12%nfe
1581       iwork(13) = cmn12%nje
1582       iwork(14) = cmn12%nqu
1583       iwork(15) = cmn12%newq
1584       iwork(19) = cmn12%nlu
1585       iwork(20) = cmn12%nni
1586       iwork(21) = cmn12%ncfn
1587       iwork(22) = cmn12%netf
1588       return
1589 !-----------------------------------------------------------------------
1590 ! block h.
1591 ! the following block handles all unsuccessful returns other than
1592 ! those for illegal input.  first the error message routine is called.
1593 ! if there was an error test or convergence test failure, imxer is set.
1594 ! then y is loaded from yh, and t is set to tn.
1595 ! the optional output is loaded into the work arrays before returning.
1596 !-----------------------------------------------------------------------
1597 ! the maximum number of steps was taken before reaching tout. ----------
1598  500  msg = 'dvode--  at current t (=r1), mxstep (=i1) steps   '
1599       call xerrwd (msg, 50, 201, 1, 0, 0, 0, 0, zero, zero)
1600       msg = '      taken on this call before reaching tout     '
1601       call xerrwd (msg, 50, 201, 1, 1, cmn12%mxstep, 0, 1, cmn12%tn, zero)
1602       istate = -1
1603       go to 580
1604 ! ewt(i) .le. 0.0 for some i (not at start of problem). ----------------
1605  510  ewti = rwork(cmn12%lewt+i-1)
1606       msg = 'dvode--  at t (=r1), ewt(i1) has become r2 .le. 0.'
1607       call xerrwd (msg, 50, 202, 1, 1, i, 0, 2, cmn12%tn, ewti)
1608       istate = -6
1609       go to 580
1610 ! too much accuracy requested for machine precision. -------------------
1611  520  msg = 'dvode--  at t (=r1), too much accuracy requested  '
1612       call xerrwd (msg, 50, 203, 1, 0, 0, 0, 0, zero, zero)
1613       msg = '      for precision of machine:   see tolsf (=r2) '
1614       call xerrwd (msg, 50, 203, 1, 0, 0, 0, 2, cmn12%tn, tolsf)
1615       rwork(14) = tolsf
1616       istate = -2
1617       go to 580
1618 ! kflag = -1.  error test failed repeatedly or with abs(h) = hmin. -----
1619  530  msg = 'dvode--  at t(=r1) and step size h(=r2), the error'
1620       call xerrwd (msg, 50, 204, 1, 0, 0, 0, 0, zero, zero)
1621       msg = '      test failed repeatedly or with abs(h) = hmin'
1622       call xerrwd (msg, 50, 204, 1, 0, 0, 0, 2, cmn12%tn, h)
1623       istate = -4
1624       go to 560
1625 ! kflag = -2.  convergence failed repeatedly or with abs(h) = hmin. ----
1626  540  msg = 'dvode--  at t (=r1) and step size h (=r2), the    '
1627       call xerrwd (msg, 50, 205, 1, 0, 0, 0, 0, zero, zero)
1628       msg = '      corrector convergence failed repeatedly     '
1629       call xerrwd (msg, 50, 205, 1, 0, 0, 0, 0, zero, zero)
1630       msg = '      or with abs(h) = hmin   '
1631       call xerrwd (msg, 30, 205, 1, 0, 0, 0, 2, cmn12%tn, h)
1632       istate = -5
1633 ! compute imxer if relevant. -------------------------------------------
1634  560  big = zero
1635       imxer = 1
1636       do 570 i = 1,n
1637         size = abs(rwork(i+cmn12%lacor-1)*rwork(i+cmn12%lewt-1))
1638         if (big .ge. size) go to 570
1639         big = size
1640         imxer = i
1641  570    continue
1642       iwork(16) = imxer
1643 ! set y vector, t, and optional output. --------------------------------
1644  580  continue
1645       call dcopy (n, rwork(cmn12%lyh), 1, y, 1)
1646       t = cmn12%tn
1647       rwork(11) = cmn12%hu
1648       rwork(12) = h
1649       rwork(13) = cmn12%tn
1650       iwork(11) = cmn12%nst
1651       iwork(12) = cmn12%nfe
1652       iwork(13) = cmn12%nje
1653       iwork(14) = cmn12%nqu
1654       iwork(15) = cmn12%nq
1655       iwork(19) = cmn12%nlu
1656       iwork(20) = cmn12%nni
1657       iwork(21) = cmn12%ncfn
1658       iwork(22) = cmn12%netf
1659       return
1660 !-----------------------------------------------------------------------
1661 ! block i.
1662 ! the following block handles all error returns due to illegal input
1663 ! (istate = -3), as detected before calling the core integrator.
1664 ! first the error message routine is called.   if the illegal input
1665 ! is a negative istate, the run is aborted (apparent infinite loop).
1666 !-----------------------------------------------------------------------
1667  601  msg = 'dvode--  istate (=i1) illegal '
1668       call xerrwd (msg, 30, 1, 1, 1, istate, 0, 0, zero, zero)
1669       if (istate .lt. 0) go to 800
1670       go to 700
1671  602  msg = 'dvode--  itask (=i1) illegal  '
1672       call xerrwd (msg, 30, 2, 1, 1, itask, 0, 0, zero, zero)
1673       go to 700
1674  603  msg='dvode--  istate (=i1) .gt. 1 but dvode not initialized      '
1675       call xerrwd (msg, 60, 3, 1, 1, istate, 0, 0, zero, zero)
1676       go to 700
1677  604  msg = 'dvode--  neq (=i1) .lt. 1     '
1678       call xerrwd (msg, 30, 4, 1, 1, neq, 0, 0, zero, zero)
1679       go to 700
1680  605  msg = 'dvode--  istate = 3 and neq increased (i1 to i2)  '
1681       call xerrwd (msg, 50, 5, 1, 2, n, neq, 0, zero, zero)
1682       go to 700
1683  606  msg = 'dvode--  itol (=i1) illegal   '
1684       call xerrwd (msg, 30, 6, 1, 1, itol, 0, 0, zero, zero)
1685       go to 700
1686  607  msg = 'dvode--  iopt (=i1) illegal   '
1687       call xerrwd (msg, 30, 7, 1, 1, iopt, 0, 0, zero, zero)
1688       go to 700
1689  608  msg = 'dvode--  mf (=i1) illegal     '
1690       call xerrwd (msg, 30, 8, 1, 1, mf, 0, 0, zero, zero)
1691       go to 700
1692  609  msg = 'dvode--  ml (=i1) illegal:  .lt.0 or .ge.neq (=i2)'
1693       call xerrwd (msg, 50, 9, 1, 2, ml, neq, 0, zero, zero)
1694       go to 700
1695  610  msg = 'dvode--  mu (=i1) illegal:  .lt.0 or .ge.neq (=i2)'
1696       call xerrwd (msg, 50, 10, 1, 2, mu, neq, 0, zero, zero)
1697       go to 700
1698  611  msg = 'dvode--  maxord (=i1) .lt. 0  '
1699       call xerrwd (msg, 30, 11, 1, 1, cmn12%maxord, 0, 0, zero, zero)
1700       go to 700
1701  612  msg = 'dvode--  mxstep (=i1) .lt. 0  '
1702       call xerrwd (msg, 30, 12, 1, 1, cmn12%mxstep, 0, 0, zero, zero)
1703       go to 700
1704  613  msg = 'dvode--  mxhnil (=i1) .lt. 0  '
1705       call xerrwd (msg, 30, 13, 1, 1, cmn12%mxhnil, 0, 0, zero, zero)
1706       go to 700
1707  614  msg = 'dvode--  tout (=r1) behind t (=r2)      '
1708       call xerrwd (msg, 40, 14, 1, 0, 0, 0, 2, tout, t)
1709       msg = '      integration direction is given by h0 (=r1)  '
1710       call xerrwd (msg, 50, 14, 1, 0, 0, 0, 1, h0, zero)
1711       go to 700
1712  615  msg = 'dvode--  hmax (=r1) .lt. 0.0  '
1713       call xerrwd (msg, 30, 15, 1, 0, 0, 0, 1, hmax, zero)
1714       go to 700
1715  616  msg = 'dvode--  hmin (=r1) .lt. 0.0  '
1716       call xerrwd (msg, 30, 16, 1, 0, 0, 0, 1, cmn12%hmin, zero)
1717       go to 700
1718  617  continue
1719       msg='dvode--  rwork length needed, lenrw (=i1), exceeds lrw (=i2)'
1720       call xerrwd (msg, 60, 17, 1, 2, lenrw, lrw, 0, zero, zero)
1721       go to 700
1722  618  continue
1723       msg='dvode--  iwork length needed, leniw (=i1), exceeds liw (=i2)'
1724       call xerrwd (msg, 60, 18, 1, 2, leniw, liw, 0, zero, zero)
1725       go to 700
1726  619  msg = 'dvode--  rtol(i1) is r1 .lt. 0.0        '
1727       call xerrwd (msg, 40, 19, 1, 1, i, 0, 1, rtoli, zero)
1728       go to 700
1729  620  msg = 'dvode--  atol(i1) is r1 .lt. 0.0        '
1730       call xerrwd (msg, 40, 20, 1, 1, i, 0, 1, atoli, zero)
1731       go to 700
1732  621  ewti = rwork(cmn12%lewt+i-1)
1733       msg = 'dvode--  ewt(i1) is r1 .le. 0.0         '
1734       call xerrwd (msg, 40, 21, 1, 1, i, 0, 1, ewti, zero)
1735       go to 700
1736  622  continue
1737       msg='dvode--  tout (=r1) too close to t(=r2) to start integration'
1738       call xerrwd (msg, 60, 22, 1, 0, 0, 0, 2, tout, t)
1739       go to 700
1740  623  continue
1741       msg='dvode--  itask = i1 and tout (=r1) behind tcur - hu (= r2)  '
1742       call xerrwd (msg, 60, 23, 1, 1, itask, 0, 2, tout, tp)
1743       go to 700
1744  624  continue
1745       msg='dvode--  itask = 4 or 5 and tcrit (=r1) behind tcur (=r2)   '
1746       call xerrwd (msg, 60, 24, 1, 0, 0, 0, 2, tcrit, cmn12%tn)
1747       go to 700
1748  625  continue
1749       msg='dvode--  itask = 4 or 5 and tcrit (=r1) behind tout (=r2)   '
1750       call xerrwd (msg, 60, 25, 1, 0, 0, 0, 2, tcrit, tout)
1751       go to 700
1752  626  msg = 'dvode--  at start of problem, too much accuracy   '
1753       call xerrwd (msg, 50, 26, 1, 0, 0, 0, 0, zero, zero)
1754       msg='      requested for precision of machine:   see tolsf (=r1) '
1755       call xerrwd (msg, 60, 26, 1, 0, 0, 0, 1, tolsf, zero)
1756       rwork(14) = tolsf
1757       go to 700
1758  627  msg='dvode--  trouble from dvindy.  itask = i1, tout = r1.       '
1759       call xerrwd (msg, 60, 27, 1, 1, itask, 0, 1, tout, zero)
1761  700  continue
1762       istate = -3
1763       return
1765  800  msg = 'dvode--  run aborted:  apparent infinite loop     '
1766       call xerrwd (msg, 50, 303, 2, 0, 0, 0, 0, zero, zero)
1767       return
1768 !----------------------- end of subroutine dvode -----------------------
1769       end subroutine dvode
1770 !deck dvhin
1771       subroutine dvhin (n, t0, y0, ydot, f, rpar, ipar, tout, uround,   &
1772          ewt, itol, atol, y, temp, h0, niter, ier)
1773       external f
1774       double precision t0, y0, ydot, rpar, tout, uround, ewt, atol, y,   &
1775          temp, h0
1776       integer n, ipar, itol, niter, ier
1777       dimension y0(*), ydot(*), ewt(*), atol(*), y(*),   &
1778          temp(*), rpar(*), ipar(*)
1779 !-----------------------------------------------------------------------
1780 ! call sequence input -- n, t0, y0, ydot, f, rpar, ipar, tout, uround,
1781 !                        ewt, itol, atol, y, temp
1782 ! call sequence output -- h0, niter, ier
1783 ! common block variables accessed -- none
1785 ! subroutines called by dvhin:  f
1786 ! function routines called by dvhi: dvnorm
1787 !-----------------------------------------------------------------------
1788 ! this routine computes the step size, h0, to be attempted on the
1789 ! first step, when the user has not supplied a value for this.
1791 ! first we check that tout - t0 differs significantly from zero.  then
1792 ! an iteration is done to approximate the initial second derivative
1793 ! and this is used to define h from w.r.m.s.norm(h**2 * yddot / 2) = 1.
1794 ! a bias factor of 1/2 is applied to the resulting h.
1795 ! the sign of h0 is inferred from the initial values of tout and t0.
1797 ! communication with dvhin is done with the following variables:
1799 ! n      = size of ode system, input.
1800 ! t0     = initial value of independent variable, input.
1801 ! y0     = vector of initial conditions, input.
1802 ! ydot   = vector of initial first derivatives, input.
1803 ! f      = name of subroutine for right-hand side f(t,y), input.
1804 ! rpar, ipar = dummy names for user's real and integer work arrays.
1805 ! tout   = first output value of independent variable
1806 ! uround = machine unit roundoff
1807 ! ewt, itol, atol = error weights and tolerance parameters
1808 !                   as described in the driver routine, input.
1809 ! y, temp = work arrays of length n.
1810 ! h0     = step size to be attempted, output.
1811 ! niter  = number of iterations (and of f evaluations) to compute h0,
1812 !          output.
1813 ! ier    = the error flag, returned with the value
1814 !          ier = 0  if no trouble occurred, or
1815 !          ier = -1 if tout and t0 are considered too close to proceed.
1816 !-----------------------------------------------------------------------
1818 ! type declarations for local variables --------------------------------
1820       double precision afi, atoli, delyi, h, half, hg, hlb, hnew, hrat,   &
1821            hub, hun, pt1, t1, tdist, tround, two, yddnrm
1822       integer i, iter
1824 ! type declaration for function subroutines called ---------------------
1826 ! 27-oct-2005 rce - do not declare functions that are in the module
1827 !     double precision dvnorm
1828 !-----------------------------------------------------------------------
1829 ! the following fortran-77 declaration is to cause the values of the
1830 ! listed (local) variables to be saved between calls to this integrator.
1831 !-----------------------------------------------------------------------
1832       save half, hun, pt1, two
1833       data half /0.5d0/, hun /100.0d0/, pt1 /0.1d0/, two /2.0d0/
1835       niter = 0
1836       tdist = abs(tout - t0)
1837       tround = uround*max(abs(t0),abs(tout))
1838       if (tdist .lt. two*tround) go to 100
1840 ! set a lower bound on h based on the roundoff level in t0 and tout. ---
1841       hlb = hun*tround
1842 ! set an upper bound on h based on tout-t0 and the initial y and ydot. -
1843       hub = pt1*tdist
1844       atoli = atol(1)
1845       do 10 i = 1, n
1846         if (itol .eq. 2 .or. itol .eq. 4) atoli = atol(i)
1847         delyi = pt1*abs(y0(i)) + atoli
1848         afi = abs(ydot(i))
1849         if (afi*hub .gt. delyi) hub = delyi/afi
1850  10     continue
1852 ! set initial guess for h as geometric mean of upper and lower bounds. -
1853       iter = 0
1854       hg = sqrt(hlb*hub)
1855 ! if the bounds have crossed, exit with the mean value. ----------------
1856       if (hub .lt. hlb) then
1857         h0 = hg
1858         go to 90
1859       endif
1861 ! looping point for iteration. -----------------------------------------
1862  50   continue
1863 ! estimate the second derivative as a difference quotient in f. --------
1864       h = sign (hg, tout - t0)
1865       t1 = t0 + h
1866       do 60 i = 1, n
1867  60     y(i) = y0(i) + h*ydot(i)
1868       call f (n, t1, y, temp, rpar, ipar)
1869       do 70 i = 1, n
1870  70     temp(i) = (temp(i) - ydot(i))/h
1871       yddnrm = dvnorm (n, temp, ewt)
1872 ! get the corresponding new value of h. --------------------------------
1873       if (yddnrm*hub*hub .gt. two) then
1874         hnew = sqrt(two/yddnrm)
1875       else
1876         hnew = sqrt(hg*hub)
1877       endif
1878       iter = iter + 1
1879 !-----------------------------------------------------------------------
1880 ! test the stopping conditions.
1881 ! stop if the new and previous h values differ by a factor of .lt. 2.
1882 ! stop if four iterations have been done.  also, stop with previous h
1883 ! if hnew/hg .gt. 2 after first iteration, as this probably means that
1884 ! the second derivative value is bad because of cancellation error.
1885 !-----------------------------------------------------------------------
1886       if (iter .ge. 4) go to 80
1887       hrat = hnew/hg
1888       if ( (hrat .gt. half) .and. (hrat .lt. two) ) go to 80
1889       if ( (iter .ge. 2) .and. (hnew .gt. two*hg) ) then
1890         hnew = hg
1891         go to 80
1892       endif
1893       hg = hnew
1894       go to 50
1896 ! iteration done.  apply bounds, bias factor, and sign.  then exit. ----
1897  80   h0 = hnew*half
1898       if (h0 .lt. hlb) h0 = hlb
1899       if (h0 .gt. hub) h0 = hub
1900  90   h0 = sign(h0, tout - t0)
1901       niter = iter
1902       ier = 0
1903       return
1904 ! error return for tout - t0 too small. --------------------------------
1905  100  ier = -1
1906       return
1907 !----------------------- end of subroutine dvhin -----------------------
1908       end subroutine dvhin
1909 !deck dvindy
1910       subroutine dvindy (t, k, yh, ldyh, dky, iflag, cmn12)
1911       implicit none
1912       double precision t, yh, dky
1913       integer k, ldyh, iflag
1914       dimension yh(ldyh,*), dky(*)
1915       type( dvode_cmn_vars ) :: cmn12
1916 !-----------------------------------------------------------------------
1917 ! call sequence input -- t, k, yh, ldyh
1918 ! call sequence output -- dky, iflag
1919 ! common block variables accessed:
1920 !     /dvod_cmn01/ --  h, tn, uround, l, n, nq
1921 !     /dvod_cmn02/ --  hu
1923 ! subroutines called by dvindy: dscal, xerrwd
1924 ! function routines called by dvindy: none
1925 !-----------------------------------------------------------------------
1926 ! dvindy computes interpolated values of the k-th derivative of the
1927 ! dependent variable vector y, and stores it in dky.  this routine
1928 ! is called within the package with k = 0 and t = tout, but may
1929 ! also be called by the user for any k up to the current order.
1930 ! (see detailed instructions in the usage documentation.)
1931 !-----------------------------------------------------------------------
1932 ! the computed values in dky are gotten by interpolation using the
1933 ! nordsieck history array yh.  this array corresponds uniquely to a
1934 ! vector-valued polynomial of degree nqcur or less, and dky is set
1935 ! to the k-th derivative of this polynomial at t.
1936 ! the formula for dky is:
1937 !              q
1938 !  dky(i)  =  sum  c(j,k) * (t - tn)**(j-k) * h**(-j) * yh(i,j+1)
1939 !             j=k
1940 ! where  c(j,k) = j*(j-1)*...*(j-k+1), q = nqcur, tn = tcur, h = hcur.
1941 ! the quantities  nq = nqcur, l = nq+1, n, tn, and h are
1942 ! communicated by common.  the above sum is done in reverse order.
1943 ! iflag is returned negative if either k or t is out of bounds.
1945 ! discussion above and comments in driver explain all variables.
1946 !-----------------------------------------------------------------------
1948 !! type declarations for labeled common block dvod_cmn01 --------------------
1950 !      double precision acnrm, ccmxj, conp, crate, drc, el,   &
1951 !           eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
1952 !           rc, rl1, tau, tq, tn, uround
1953 !      integer icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
1954 !              l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
1955 !              locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
1956 !              n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
1957 !              nslp, nyh
1959 !! type declarations for labeled common block dvod_cmn02 --------------------
1961 !      double precision hu
1962 !      integer ncfn, netf, nfe, nje, nlu, nni, nqu, nst
1964 ! type declarations for local variables --------------------------------
1966       double precision c, hun, r, s, tfuzz, tn1, tp, zero
1967       integer i, ic, j, jb, jb2, jj, jj1, jp1
1968       character*80 msg
1969 !-----------------------------------------------------------------------
1970 ! the following fortran-77 declaration is to cause the values of the
1971 ! listed (local) variables to be saved between calls to this integrator.
1972 !-----------------------------------------------------------------------
1973       save hun, zero
1975 !      common /dvod_cmn01/ acnrm, ccmxj, conp, crate, drc, el(13),   &
1976 !                      eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
1977 !                      rc, rl1, tau(13), tq(5), tn, uround,   &
1978 !                      icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
1979 !                      l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
1980 !                      locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
1981 !                      n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
1982 !                      nslp, nyh
1983 !      common /dvod_cmn02/ hu, ncfn, netf, nfe, nje, nlu, nni, nqu, nst
1985       data hun /100.0d0/, zero /0.0d0/
1987       iflag = 0
1988       if (k .lt. 0 .or. k .gt. cmn12%nq) go to 80
1989       tfuzz = hun*cmn12%uround*(cmn12%tn + cmn12%hu)
1990       tp = cmn12%tn - cmn12%hu - tfuzz
1991       tn1 = cmn12%tn + tfuzz
1992       if ((t-tp)*(t-tn1) .gt. zero) go to 90
1994       s = (t - cmn12%tn)/cmn12%h
1995       ic = 1
1996       if (k .eq. 0) go to 15
1997       jj1 = cmn12%l - k
1998       do 10 jj = jj1, cmn12%nq
1999  10     ic = ic*jj
2000  15   c = real(ic)
2001       do 20 i = 1, cmn12%n
2002  20     dky(i) = c*yh(i,cmn12%l)
2003       if (k .eq. cmn12%nq) go to 55
2004       jb2 = cmn12%nq - k
2005       do 50 jb = 1, jb2
2006         j = cmn12%nq - jb
2007         jp1 = j + 1
2008         ic = 1
2009         if (k .eq. 0) go to 35
2010         jj1 = jp1 - k
2011         do 30 jj = jj1, j
2012  30       ic = ic*jj
2013  35     c = real(ic)
2014         do 40 i = 1, cmn12%n
2015  40       dky(i) = c*yh(i,jp1) + s*dky(i)
2016  50     continue
2017       if (k .eq. 0) return
2018  55   r = cmn12%h**(-k)
2019       call dscal (cmn12%n, r, dky, 1)
2020       return
2022  80   msg = 'dvindy-- k (=i1) illegal      '
2023       call xerrwd (msg, 30, 51, 1, 1, k, 0, 0, zero, zero)
2024       iflag = -1
2025       return
2026  90   msg = 'dvindy-- t (=r1) illegal      '
2027       call xerrwd (msg, 30, 52, 1, 0, 0, 0, 1, t, zero)
2028       msg='      t not in interval tcur - hu (= r1) to tcur (=r2)      '
2029       call xerrwd (msg, 60, 52, 1, 0, 0, 0, 2, tp, cmn12%tn)
2030       iflag = -2
2031       return
2032 !----------------------- end of subroutine dvindy ----------------------
2033       end subroutine dvindy
2034 !deck dvstep
2035       subroutine dvstep (y, yh, ldyh, yh1, ewt, savf, vsav, acor,   &
2036                         wm, iwm, f, jac, psol, vnls, rpar, ipar, cmn12)
2037       implicit none
2038       external f, jac, psol, vnls
2039       double precision y, yh, yh1, ewt, savf, vsav, acor, wm, rpar
2040       integer ldyh, iwm, ipar
2041       dimension y(*), yh(ldyh,*), yh1(*), ewt(*), savf(*), vsav(*),   &
2042          acor(*), wm(*), iwm(*), rpar(*), ipar(*)
2043       type( dvode_cmn_vars ) :: cmn12
2044 !-----------------------------------------------------------------------
2045 ! call sequence input -- y, yh, ldyh, yh1, ewt, savf, vsav,
2046 !                        acor, wm, iwm, f, jac, psol, vnls, rpar, ipar
2047 ! call sequence output -- yh, acor, wm, iwm
2048 ! common block variables accessed:
2049 !     /dvod_cmn01/  acnrm, el(13), h, hmin, hmxi, hnew, hscal, rc, tau(13),
2050 !               tq(5), tn, jcur, jstart, kflag, kuth,
2051 !               l, lmax, maxord, n, newq, nq, nqwait
2052 !     /dvod_cmn02/  hu, ncfn, netf, nfe, nqu, nst
2054 ! subroutines called by dvstep: f, daxpy, dcopy, dscal,
2055 !                               dvjust, vnls, dvset
2056 ! function routines called by dvstep: dvnorm
2057 !-----------------------------------------------------------------------
2058 ! dvstep performs one step of the integration of an initial value
2059 ! problem for a system of ordinary differential equations.
2060 ! dvstep calls subroutine vnls for the solution of the nonlinear system
2061 ! arising in the time step.  thus it is independent of the problem
2062 ! jacobian structure and the type of nonlinear system solution method.
2063 ! dvstep returns a completion flag kflag (in common).
2064 ! a return with kflag = -1 or -2 means either abs(h) = hmin or 10
2065 ! consecutive failures occurred.  on a return with kflag negative,
2066 ! the values of tn and the yh array are as of the beginning of the last
2067 ! step, and h is the last step size attempted.
2069 ! communication with dvstep is done with the following variables:
2071 ! y      = an array of length n used for the dependent variable vector.
2072 ! yh     = an ldyh by lmax array containing the dependent variables
2073 !          and their approximate scaled derivatives, where
2074 !          lmax = maxord + 1.  yh(i,j+1) contains the approximate
2075 !          j-th derivative of y(i), scaled by h**j/factorial(j)
2076 !          (j = 0,1,...,nq).  on entry for the first step, the first
2077 !          two columns of yh must be set from the initial values.
2078 ! ldyh   = a constant integer .ge. n, the first dimension of yh.
2079 !          n is the number of odes in the system.
2080 ! yh1    = a one-dimensional array occupying the same space as yh.
2081 ! ewt    = an array of length n containing multiplicative weights
2082 !          for local error measurements.  local errors in y(i) are
2083 !          compared to 1.0/ewt(i) in various error tests.
2084 ! savf   = an array of working storage, of length n.
2085 !          also used for input of yh(*,maxord+2) when jstart = -1
2086 !          and maxord .lt. the current order nq.
2087 ! vsav   = a work array of length n passed to subroutine vnls.
2088 ! acor   = a work array of length n, used for the accumulated
2089 !          corrections.  on a successful return, acor(i) contains
2090 !          the estimated one-step local error in y(i).
2091 ! wm,iwm = real and integer work arrays associated with matrix
2092 !          operations in vnls.
2093 ! f      = dummy name for the user supplied subroutine for f.
2094 ! jac    = dummy name for the user supplied jacobian subroutine.
2095 ! psol   = dummy name for the subroutine passed to vnls, for
2096 !          possible use there.
2097 ! vnls   = dummy name for the nonlinear system solving subroutine,
2098 !          whose real name is dependent on the method used.
2099 ! rpar, ipar = dummy names for user's real and integer work arrays.
2100 !-----------------------------------------------------------------------
2102 !! type declarations for labeled common block dvod_cmn01 --------------------
2104 !      double precision acnrm, ccmxj, conp, crate, drc, el,   &
2105 !           eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
2106 !           rc, rl1, tau, tq, tn, uround
2107 !      integer icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
2108 !              l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
2109 !              locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
2110 !              n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
2111 !              nslp, nyh
2113 !! type declarations for labeled common block dvod_cmn02 --------------------
2115 !      double precision hu
2116 !      integer ncfn, netf, nfe, nje, nlu, nni, nqu, nst
2118 ! type declarations for local variables --------------------------------
2120 ! note -- etaq & etaqm1 are saved variables that are not fixed constants,
2121 !         so put them into cmn12
2122 !     double precision addon, bias1,bias2,bias3, cnquot, ddn, dsm, dup,   &
2123 !          etacf, etamin, etamx1, etamx2, etamx3, etamxf,   &
2124 !          etaq, etaqm1, etaqp1, flotl, one, onepsm,   &
2125 !          r, thresh, told, zero
2126       double precision addon, bias1,bias2,bias3, cnquot, ddn, dsm, dup,   &
2127            etacf, etamin, etamx1, etamx2, etamx3, etamxf,   &
2128            etaqp1, flotl, one, onepsm,   &
2129            r, thresh, told, zero
2130       integer i, i1, i2, iback, j, jb, kfc, kfh, mxncf, ncf, nflag
2132 ! type declaration for function subroutines called ---------------------
2134 ! 27-oct-2005 rce - do not declare functions that are in the module
2135 !     double precision dvnorm
2136 !-----------------------------------------------------------------------
2137 ! the following fortran-77 declaration is to cause the values of the
2138 ! listed (local) variables to be saved between calls to this integrator.
2139 !-----------------------------------------------------------------------
2140 ! note -- etaq & etaqm1 are saved variables that are not fixed constants,
2141 !         so put them into cmn12
2142 !     save addon, bias1, bias2, bias3,   &
2143 !          etacf, etamin, etamx1, etamx2, etamx3, etamxf, etaq, etaqm1,   &
2144 !          kfc, kfh, mxncf, onepsm, thresh, one, zero
2145       save addon, bias1, bias2, bias3,   &
2146            etacf, etamin, etamx1, etamx2, etamx3, etamxf,   &
2147            kfc, kfh, mxncf, onepsm, thresh, one, zero
2148 !-----------------------------------------------------------------------
2149 !      common /dvod_cmn01/ acnrm, ccmxj, conp, crate, drc, el(13),   &
2150 !                      eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
2151 !                      rc, rl1, tau(13), tq(5), tn, uround,   &
2152 !                      icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
2153 !                      l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
2154 !                      locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
2155 !                      n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
2156 !                      nslp, nyh
2157 !      common /dvod_cmn02/ hu, ncfn, netf, nfe, nje, nlu, nni, nqu, nst
2159       data kfc/-3/, kfh/-7/, mxncf/10/
2160       data addon  /1.0d-6/,    bias1  /6.0d0/,     bias2  /6.0d0/,   &
2161            bias3  /10.0d0/,    etacf  /0.25d0/,    etamin /0.1d0/,   &
2162            etamxf /0.2d0/,     etamx1 /1.0d4/,     etamx2 /10.0d0/,   &
2163            etamx3 /10.0d0/,    onepsm /1.00001d0/, thresh /1.5d0/
2164       data one/1.0d0/, zero/0.0d0/
2166       cmn12%kflag = 0
2167       told = cmn12%tn
2168       ncf = 0
2169       cmn12%jcur = 0
2170       nflag = 0
2171       if (cmn12%jstart .gt. 0) go to 20
2172       if (cmn12%jstart .eq. -1) go to 100
2173 !-----------------------------------------------------------------------
2174 ! on the first call, the order is set to 1, and other variables are
2175 ! initialized.  etamax is the maximum ratio by which h can be increased
2176 ! in a single step.  it is normally 10, but is larger during the
2177 ! first step to compensate for the small initial h.  if a failure
2178 ! occurs (in corrector convergence or error test), etamax is set to 1
2179 ! for the next increase.
2180 !-----------------------------------------------------------------------
2181       cmn12%lmax = cmn12%maxord + 1
2182       cmn12%nq = 1
2183       cmn12%l = 2
2184       cmn12%nqnyh = cmn12%nq*ldyh
2185       cmn12%tau(1) = cmn12%h
2186       cmn12%prl1 = one
2187       cmn12%rc = zero
2188       cmn12%etamax = etamx1
2189       cmn12%nqwait = 2
2190       cmn12%hscal = cmn12%h
2191       go to 200
2192 !-----------------------------------------------------------------------
2193 ! take preliminary actions on a normal continuation step (jstart.gt.0).
2194 ! if the driver changed h, then eta must be reset and newh set to 1.
2195 ! if a change of order was dictated on the previous step, then
2196 ! it is done here and appropriate adjustments in the history are made.
2197 ! on an order decrease, the history array is adjusted by dvjust.
2198 ! on an order increase, the history array is augmented by a column.
2199 ! on a change of step size h, the history array yh is rescaled.
2200 !-----------------------------------------------------------------------
2201  20   continue
2202       if (cmn12%kuth .eq. 1) then
2203         cmn12%eta = min(cmn12%eta,cmn12%h/cmn12%hscal)
2204         cmn12%newh = 1
2205         endif
2206  50   if (cmn12%newh .eq. 0) go to 200
2207       if (cmn12%newq .eq. cmn12%nq) go to 150
2208       if (cmn12%newq .lt. cmn12%nq) then
2209         call dvjust (yh, ldyh, -1, cmn12)
2210         cmn12%nq = cmn12%newq
2211         cmn12%l = cmn12%nq + 1
2212         cmn12%nqwait = cmn12%l
2213         go to 150
2214         endif
2215       if (cmn12%newq .gt. cmn12%nq) then
2216         call dvjust (yh, ldyh, 1, cmn12)
2217         cmn12%nq = cmn12%newq
2218         cmn12%l = cmn12%nq + 1
2219         cmn12%nqwait = cmn12%l
2220         go to 150
2221       endif
2222 !-----------------------------------------------------------------------
2223 ! the following block handles preliminaries needed when jstart = -1.
2224 ! if n was reduced, zero out part of yh to avoid undefined references.
2225 ! if maxord was reduced to a value less than the tentative order newq,
2226 ! then nq is set to maxord, and a new h ratio eta is chosen.
2227 ! otherwise, we take the same preliminary actions as for jstart .gt. 0.
2228 ! in any case, nqwait is reset to l = nq + 1 to prevent further
2229 ! changes in order for that many steps.
2230 ! the new h ratio eta is limited by the input h if kuth = 1,
2231 ! by hmin if kuth = 0, and by hmxi in any case.
2232 ! finally, the history array yh is rescaled.
2233 !-----------------------------------------------------------------------
2234  100  continue
2235       cmn12%lmax = cmn12%maxord + 1
2236       if (cmn12%n .eq. ldyh) go to 120
2237       i1 = 1 + (cmn12%newq + 1)*ldyh
2238       i2 = (cmn12%maxord + 1)*ldyh
2239       if (i1 .gt. i2) go to 120
2240       do 110 i = i1, i2
2241  110    yh1(i) = zero
2242  120  if (cmn12%newq .le. cmn12%maxord) go to 140
2243       flotl = real(cmn12%lmax)
2244       if (cmn12%maxord .lt. cmn12%nq-1) then
2245         ddn = dvnorm (cmn12%n, savf, ewt)/cmn12%tq(1)
2246         cmn12%eta = one/((bias1*ddn)**(one/flotl) + addon)
2247         endif
2248       if (cmn12%maxord .eq. cmn12%nq .and. cmn12%newq .eq. cmn12%nq+1) cmn12%eta = cmn12%etaq
2249       if (cmn12%maxord .eq. cmn12%nq-1 .and. cmn12%newq .eq. cmn12%nq+1) then
2250         cmn12%eta = cmn12%etaqm1
2251         call dvjust (yh, ldyh, -1, cmn12)
2252         endif
2253       if (cmn12%maxord .eq. cmn12%nq-1 .and. cmn12%newq .eq. cmn12%nq) then
2254         ddn = dvnorm (cmn12%n, savf, ewt)/cmn12%tq(1)
2255         cmn12%eta = one/((bias1*ddn)**(one/flotl) + addon)
2256         call dvjust (yh, ldyh, -1, cmn12)
2257         endif
2258       cmn12%eta = min(cmn12%eta,one)
2259       cmn12%nq = cmn12%maxord
2260       cmn12%l = cmn12%lmax
2261  140  if (cmn12%kuth .eq. 1) cmn12%eta = min(cmn12%eta,abs(cmn12%h/cmn12%hscal))
2262       if (cmn12%kuth .eq. 0) cmn12%eta = max(cmn12%eta,cmn12%hmin/abs(cmn12%hscal))
2263       cmn12%eta = cmn12%eta/max(one,abs(cmn12%hscal)*cmn12%hmxi*cmn12%eta)
2264       cmn12%newh = 1
2265       cmn12%nqwait = cmn12%l
2266       if (cmn12%newq .le. cmn12%maxord) go to 50
2267 ! rescale the history array for a change in h by a factor of eta. ------
2268  150  r = one
2269       do 180 j = 2, cmn12%l
2270         r = r*cmn12%eta
2271         call dscal (cmn12%n, r, yh(1,j), 1 )
2272  180    continue
2273       cmn12%h = cmn12%hscal*cmn12%eta
2274       cmn12%hscal = cmn12%h
2275       cmn12%rc = cmn12%rc*cmn12%eta
2276       cmn12%nqnyh = cmn12%nq*ldyh
2277 !-----------------------------------------------------------------------
2278 ! this section computes the predicted values by effectively
2279 ! multiplying the yh array by the pascal triangle matrix.
2280 ! dvset is called to calculate all integration coefficients.
2281 ! rc is the ratio of new to old values of the coefficient h/el(2)=h/l1.
2282 !-----------------------------------------------------------------------
2283  200  cmn12%tn = cmn12%tn + cmn12%h
2284       i1 = cmn12%nqnyh + 1
2285       do 220 jb = 1, cmn12%nq
2286         i1 = i1 - ldyh
2287         do 210 i = i1, cmn12%nqnyh
2288  210      yh1(i) = yh1(i) + yh1(i+ldyh)
2289  220  continue
2290       call dvset( cmn12 )
2291       cmn12%rl1 = one/cmn12%el(2)
2292       cmn12%rc = cmn12%rc*(cmn12%rl1/cmn12%prl1)
2293       cmn12%prl1 = cmn12%rl1
2295 ! call the nonlinear system solver. ------------------------------------
2297       call vnls (y, yh, ldyh, vsav, savf, ewt, acor, iwm, wm,   &
2298                  f, jac, psol, nflag, rpar, ipar, cmn12)
2300       if (nflag .eq. 0) go to 450
2301 !-----------------------------------------------------------------------
2302 ! the vnls routine failed to achieve convergence (nflag .ne. 0).
2303 ! the yh array is retracted to its values before prediction.
2304 ! the step size h is reduced and the step is retried, if possible.
2305 ! otherwise, an error exit is taken.
2306 !-----------------------------------------------------------------------
2307         ncf = ncf + 1
2308         cmn12%ncfn = cmn12%ncfn + 1
2309         cmn12%etamax = one
2310         cmn12%tn = told
2311         i1 = cmn12%nqnyh + 1
2312         do 430 jb = 1, cmn12%nq
2313           i1 = i1 - ldyh
2314           do 420 i = i1, cmn12%nqnyh
2315  420        yh1(i) = yh1(i) - yh1(i+ldyh)
2316  430      continue
2317         if (nflag .lt. -1) go to 680
2318         if (abs(cmn12%h) .le. cmn12%hmin*onepsm) go to 670
2319         if (ncf .eq. mxncf) go to 670
2320         cmn12%eta = etacf
2321         cmn12%eta = max(cmn12%eta,cmn12%hmin/abs(cmn12%h))
2322         nflag = -1
2323         go to 150
2324 !-----------------------------------------------------------------------
2325 ! the corrector has converged (nflag = 0).  the local error test is
2326 ! made and control passes to statement 500 if it fails.
2327 !-----------------------------------------------------------------------
2328  450  continue
2329       dsm = cmn12%acnrm/cmn12%tq(2)
2330       if (dsm .gt. one) go to 500
2331 !-----------------------------------------------------------------------
2332 ! after a successful step, update the yh and tau arrays and decrement
2333 ! nqwait.  if nqwait is then 1 and nq .lt. maxord, then acor is saved
2334 ! for use in a possible order increase on the next step.
2335 ! if etamax = 1 (a failure occurred this step), keep nqwait .ge. 2.
2336 !-----------------------------------------------------------------------
2337       cmn12%kflag = 0
2338       cmn12%nst = cmn12%nst + 1
2339       cmn12%hu = cmn12%h
2340       cmn12%nqu = cmn12%nq
2341       do 470 iback = 1, cmn12%nq
2342         i = cmn12%l - iback
2343  470    cmn12%tau(i+1) = cmn12%tau(i)
2344       cmn12%tau(1) = cmn12%h
2345       do 480 j = 1, cmn12%l
2346         call daxpy (cmn12%n, cmn12%el(j), acor, 1, yh(1,j), 1 )
2347  480    continue
2348       cmn12%nqwait = cmn12%nqwait - 1
2349       if ((cmn12%l .eq. cmn12%lmax) .or. (cmn12%nqwait .ne. 1)) go to 490
2350       call dcopy (cmn12%n, acor, 1, yh(1,cmn12%lmax), 1 )
2351       cmn12%conp = cmn12%tq(5)
2352  490  if (cmn12%etamax .ne. one) go to 560
2353       if (cmn12%nqwait .lt. 2) cmn12%nqwait = 2
2354       cmn12%newq = cmn12%nq
2355       cmn12%newh = 0
2356       cmn12%eta = one
2357       cmn12%hnew = cmn12%h
2358       go to 690
2359 !-----------------------------------------------------------------------
2360 ! the error test failed.  kflag keeps track of multiple failures.
2361 ! restore tn and the yh array to their previous values, and prepare
2362 ! to try the step again.  compute the optimum step size for the
2363 ! same order.  after repeated failures, h is forced to decrease
2364 ! more rapidly.
2365 !-----------------------------------------------------------------------
2366  500  cmn12%kflag = cmn12%kflag - 1
2367       cmn12%netf = cmn12%netf + 1
2368       nflag = -2
2369       cmn12%tn = told
2370       i1 = cmn12%nqnyh + 1
2371       do 520 jb = 1, cmn12%nq
2372         i1 = i1 - ldyh
2373         do 510 i = i1, cmn12%nqnyh
2374  510      yh1(i) = yh1(i) - yh1(i+ldyh)
2375  520  continue
2376       if (abs(cmn12%h) .le. cmn12%hmin*onepsm) go to 660
2377       cmn12%etamax = one
2378       if (cmn12%kflag .le. kfc) go to 530
2379 ! compute ratio of new h to current h at the current order. ------------
2380       flotl = real(cmn12%l)
2381       cmn12%eta = one/((bias2*dsm)**(one/flotl) + addon)
2382       cmn12%eta = max(cmn12%eta,cmn12%hmin/abs(cmn12%h),etamin)
2383       if ((cmn12%kflag .le. -2) .and. (cmn12%eta .gt. etamxf)) cmn12%eta = etamxf
2384       go to 150
2385 !-----------------------------------------------------------------------
2386 ! control reaches this section if 3 or more consecutive failures
2387 ! have occurred.  it is assumed that the elements of the yh array
2388 ! have accumulated errors of the wrong order.  the order is reduced
2389 ! by one, if possible.  then h is reduced by a factor of 0.1 and
2390 ! the step is retried.  after a total of 7 consecutive failures,
2391 ! an exit is taken with kflag = -1.
2392 !-----------------------------------------------------------------------
2393  530  if (cmn12%kflag .eq. kfh) go to 660
2394       if (cmn12%nq .eq. 1) go to 540
2395       cmn12%eta = max(etamin,cmn12%hmin/abs(cmn12%h))
2396       call dvjust (yh, ldyh, -1, cmn12)
2397       cmn12%l = cmn12%nq
2398       cmn12%nq = cmn12%nq - 1
2399       cmn12%nqwait = cmn12%l
2400       go to 150
2401  540  cmn12%eta = max(etamin,cmn12%hmin/abs(cmn12%h))
2402       cmn12%h = cmn12%h*cmn12%eta
2403       cmn12%hscal = cmn12%h
2404       cmn12%tau(1) = cmn12%h
2405       call f (cmn12%n, cmn12%tn, y, savf, rpar, ipar)
2406       cmn12%nfe = cmn12%nfe + 1
2407       do 550 i = 1, cmn12%n
2408  550    yh(i,2) = cmn12%h*savf(i)
2409       cmn12%nqwait = 10
2410       go to 200
2411 !-----------------------------------------------------------------------
2412 ! if nqwait = 0, an increase or decrease in order by one is considered.
2413 ! factors etaq, etaqm1, etaqp1 are computed by which h could
2414 ! be multiplied at order q, q-1, or q+1, respectively.
2415 ! the largest of these is determined, and the new order and
2416 ! step size set accordingly.
2417 ! a change of h or nq is made only if h increases by at least a
2418 ! factor of thresh.  if an order change is considered and rejected,
2419 ! then nqwait is set to 2 (reconsider it after 2 steps).
2420 !-----------------------------------------------------------------------
2421 ! compute ratio of new h to current h at the current order. ------------
2422  560  flotl = real(cmn12%l)
2423       cmn12%etaq = one/((bias2*dsm)**(one/flotl) + addon)
2424       if (cmn12%nqwait .ne. 0) go to 600
2425       cmn12%nqwait = 2
2426       cmn12%etaqm1 = zero
2427       if (cmn12%nq .eq. 1) go to 570
2428 ! compute ratio of new h to current h at the current order less one. ---
2429       ddn = dvnorm (cmn12%n, yh(1,cmn12%l), ewt)/cmn12%tq(1)
2430       cmn12%etaqm1 = one/((bias1*ddn)**(one/(flotl - one)) + addon)
2431  570  etaqp1 = zero
2432       if (cmn12%l .eq. cmn12%lmax) go to 580
2433 ! compute ratio of new h to current h at current order plus one. -------
2434       cnquot = (cmn12%tq(5)/cmn12%conp)*(cmn12%h/cmn12%tau(2))**cmn12%l
2435       do 575 i = 1, cmn12%n
2436  575    savf(i) = acor(i) - cnquot*yh(i,cmn12%lmax)
2437       dup = dvnorm (cmn12%n, savf, ewt)/cmn12%tq(3)
2438       etaqp1 = one/((bias3*dup)**(one/(flotl + one)) + addon)
2439  580  if (cmn12%etaq .ge. etaqp1) go to 590
2440       if (etaqp1 .gt. cmn12%etaqm1) go to 620
2441       go to 610
2442  590  if (cmn12%etaq .lt. cmn12%etaqm1) go to 610
2443  600  cmn12%eta = cmn12%etaq
2444       cmn12%newq = cmn12%nq
2445       go to 630
2446  610  cmn12%eta = cmn12%etaqm1
2447       cmn12%newq = cmn12%nq - 1
2448       go to 630
2449  620  cmn12%eta = etaqp1
2450       cmn12%newq = cmn12%nq + 1
2451       call dcopy (cmn12%n, acor, 1, yh(1,cmn12%lmax), 1)
2452 ! test tentative new h against thresh, etamax, and hmxi, then exit. ----
2453  630  if (cmn12%eta .lt. thresh .or. cmn12%etamax .eq. one) go to 640
2454       cmn12%eta = min(cmn12%eta,cmn12%etamax)
2455       cmn12%eta = cmn12%eta/max(one,abs(cmn12%h)*cmn12%hmxi*cmn12%eta)
2456       cmn12%newh = 1
2457       cmn12%hnew = cmn12%h*cmn12%eta
2458       go to 690
2459  640  cmn12%newq = cmn12%nq
2460       cmn12%newh = 0
2461       cmn12%eta = one
2462       cmn12%hnew = cmn12%h
2463       go to 690
2464 !-----------------------------------------------------------------------
2465 ! all returns are made through this section.
2466 ! on a successful return, etamax is reset and acor is scaled.
2467 !-----------------------------------------------------------------------
2468  660  cmn12%kflag = -1
2469       go to 720
2470  670  cmn12%kflag = -2
2471       go to 720
2472  680  if (nflag .eq. -2) cmn12%kflag = -3
2473       if (nflag .eq. -3) cmn12%kflag = -4
2474       go to 720
2475  690  cmn12%etamax = etamx3
2476       if (cmn12%nst .le. 10) cmn12%etamax = etamx2
2477  700  r = one/cmn12%tq(2)
2478       call dscal (cmn12%n, r, acor, 1)
2479  720  cmn12%jstart = 1
2480       return
2481 !----------------------- end of subroutine dvstep ----------------------
2482       end subroutine dvstep
2483 !deck dvset
2484       subroutine dvset( cmn12 )
2485       implicit none
2486       type( dvode_cmn_vars ) :: cmn12
2487 !-----------------------------------------------------------------------
2488 ! call sequence communication: none
2489 ! common block variables accessed:
2490 !     /dvod_cmn01/ -- el(13), h, tau(13), tq(5), l(= nq + 1),
2491 !                 meth, nq, nqwait
2493 ! subroutines called by dvset: none
2494 ! function routines called by dvset: none
2495 !-----------------------------------------------------------------------
2496 ! dvset is called by dvstep and sets coefficients for use there.
2498 ! for each order nq, the coefficients in el are calculated by use of
2499 !  the generating polynomial lambda(x), with coefficients el(i).
2500 !      lambda(x) = el(1) + el(2)*x + ... + el(nq+1)*(x**nq).
2501 ! for the backward differentiation formulas,
2502 !                                     nq-1
2503 !      lambda(x) = (1 + x/xi*(nq)) * product (1 + x/xi(i) ) .
2504 !                                     i = 1
2505 ! for the adams formulas,
2506 !                              nq-1
2507 !      (d/dx) lambda(x) = c * product (1 + x/xi(i) ) ,
2508 !                              i = 1
2509 !      lambda(-1) = 0,    lambda(0) = 1,
2510 ! where c is a normalization constant.
2511 ! in both cases, xi(i) is defined by
2512 !      h*xi(i) = t sub n  -  t sub (n-i)
2513 !              = h + tau(1) + tau(2) + ... tau(i-1).
2516 ! in addition to variables described previously, communication
2517 ! with dvset uses the following:
2518 !   tau    = a vector of length 13 containing the past nq values
2519 !            of h.
2520 !   el     = a vector of length 13 in which vset stores the
2521 !            coefficients for the corrector formula.
2522 !   tq     = a vector of length 5 in which vset stores constants
2523 !            used for the convergence test, the error test, and the
2524 !            selection of h at a new order.
2525 !   meth   = the basic method indicator.
2526 !   nq     = the current order.
2527 !   l      = nq + 1, the length of the vector stored in el, and
2528 !            the number of columns of the yh array being used.
2529 !   nqwait = a counter controlling the frequency of order changes.
2530 !            an order change is about to be considered if nqwait = 1.
2531 !-----------------------------------------------------------------------
2533 ! type declarations for labeled common block dvod_cmn01 --------------------
2535 !      double precision acnrm, ccmxj, conp, crate, drc, el,   &
2536 !           eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
2537 !           rc, rl1, tau, tq, tn, uround
2538 !      integer icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
2539 !              l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
2540 !              locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
2541 !              n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
2542 !              nslp, nyh
2544 ! type declarations for local variables --------------------------------
2546       double precision ahatn0, alph0, cnqm1, cortes, csum, elp, em,   &
2547            em0, floti, flotl, flotnq, hsum, one, rxi, rxis, s, six,   &
2548            t1, t2, t3, t4, t5, t6, two, xi, zero
2549       integer i, iback, j, jp1, nqm1, nqm2
2551       dimension em(13)
2552 !-----------------------------------------------------------------------
2553 ! the following fortran-77 declaration is to cause the values of the
2554 ! listed (local) variables to be saved between calls to this integrator.
2555 !-----------------------------------------------------------------------
2556       save cortes, one, six, two, zero
2558 !      common /dvod_cmn01/ acnrm, ccmxj, conp, crate, drc, el(13),   &
2559 !                      eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
2560 !                      rc, rl1, tau(13), tq(5), tn, uround,   &
2561 !                      icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
2562 !                      l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
2563 !                      locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
2564 !                      n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
2565 !                      nslp, nyh
2567       data cortes /0.1d0/
2568       data one  /1.0d0/, six /6.0d0/, two /2.0d0/, zero /0.0d0/
2570       flotl = real(cmn12%l)
2571       nqm1 = cmn12%nq - 1
2572       nqm2 = cmn12%nq - 2
2573       go to (100, 200), cmn12%meth
2575 ! set coefficients for adams methods. ----------------------------------
2576  100  if (cmn12%nq .ne. 1) go to 110
2577       cmn12%el(1) = one
2578       cmn12%el(2) = one
2579       cmn12%tq(1) = one
2580       cmn12%tq(2) = two
2581       cmn12%tq(3) = six*cmn12%tq(2)
2582       cmn12%tq(5) = one
2583       go to 300
2584  110  hsum = cmn12%h
2585       em(1) = one
2586       flotnq = flotl - one
2587       do 115 i = 2, cmn12%l
2588  115    em(i) = zero
2589       do 150 j = 1, nqm1
2590         if ((j .ne. nqm1) .or. (cmn12%nqwait .ne. 1)) go to 130
2591         s = one
2592         csum = zero
2593         do 120 i = 1, nqm1
2594           csum = csum + s*em(i)/real(i+1)
2595  120      s = -s
2596         cmn12%tq(1) = em(nqm1)/(flotnq*csum)
2597  130    rxi = cmn12%h/hsum
2598         do 140 iback = 1, j
2599           i = (j + 2) - iback
2600  140      em(i) = em(i) + em(i-1)*rxi
2601         hsum = hsum + cmn12%tau(j)
2602  150    continue
2603 ! compute integral from -1 to 0 of polynomial and of x times it. -------
2604       s = one
2605       em0 = zero
2606       csum = zero
2607       do 160 i = 1, cmn12%nq
2608         floti = real(i)
2609         em0 = em0 + s*em(i)/floti
2610         csum = csum + s*em(i)/(floti+one)
2611  160    s = -s
2612 ! in el, form coefficients of normalized integrated polynomial. --------
2613       s = one/em0
2614       cmn12%el(1) = one
2615       do 170 i = 1, cmn12%nq
2616  170    cmn12%el(i+1) = s*em(i)/real(i)
2617       xi = hsum/cmn12%h
2618       cmn12%tq(2) = xi*em0/csum
2619       cmn12%tq(5) = xi/cmn12%el(cmn12%l)
2620       if (cmn12%nqwait .ne. 1) go to 300
2621 ! for higher order control constant, multiply polynomial by 1+x/xi(q). -
2622       rxi = one/xi
2623       do 180 iback = 1, cmn12%nq
2624         i = (cmn12%l + 1) - iback
2625  180    em(i) = em(i) + em(i-1)*rxi
2626 ! compute integral of polynomial. --------------------------------------
2627       s = one
2628       csum = zero
2629       do 190 i = 1, cmn12%l
2630         csum = csum + s*em(i)/real(i+1)
2631  190    s = -s
2632       cmn12%tq(3) = flotl*em0/csum
2633       go to 300
2635 ! set coefficients for bdf methods. ------------------------------------
2636  200  do 210 i = 3, cmn12%l
2637  210    cmn12%el(i) = zero
2638       cmn12%el(1) = one
2639       cmn12%el(2) = one
2640       alph0 = -one
2641       ahatn0 = -one
2642       hsum = cmn12%h
2643       rxi = one
2644       rxis = one
2645       if (cmn12%nq .eq. 1) go to 240
2646       do 230 j = 1, nqm2
2647 ! in el, construct coefficients of (1+x/xi(1))*...*(1+x/xi(j+1)). ------
2648         hsum = hsum + cmn12%tau(j)
2649         rxi = cmn12%h/hsum
2650         jp1 = j + 1
2651         alph0 = alph0 - one/real(jp1)
2652         do 220 iback = 1, jp1
2653           i = (j + 3) - iback
2654  220      cmn12%el(i) = cmn12%el(i) + cmn12%el(i-1)*rxi
2655  230    continue
2656       alph0 = alph0 - one/real(cmn12%nq)
2657       rxis = -cmn12%el(2) - alph0
2658       hsum = hsum + cmn12%tau(nqm1)
2659       rxi = cmn12%h/hsum
2660       ahatn0 = -cmn12%el(2) - rxi
2661       do 235 iback = 1, cmn12%nq
2662         i = (cmn12%nq + 2) - iback
2663  235    cmn12%el(i) = cmn12%el(i) + cmn12%el(i-1)*rxis
2664  240  t1 = one - ahatn0 + alph0
2665       t2 = one + real(cmn12%nq)*t1
2666       cmn12%tq(2) = abs(alph0*t2/t1)
2667       cmn12%tq(5) = abs(t2/(cmn12%el(cmn12%l)*rxi/rxis))
2668       if (cmn12%nqwait .ne. 1) go to 300
2669       cnqm1 = rxis/cmn12%el(cmn12%l)
2670       t3 = alph0 + one/real(cmn12%nq)
2671       t4 = ahatn0 + rxi
2672       elp = t3/(one - t4 + t3)
2673       cmn12%tq(1) = abs(elp/cnqm1)
2674       hsum = hsum + cmn12%tau(cmn12%nq)
2675       rxi = cmn12%h/hsum
2676       t5 = alph0 - one/real(cmn12%nq+1)
2677       t6 = ahatn0 - rxi
2678       elp = t2/(one - t6 + t5)
2679       cmn12%tq(3) = abs(elp*rxi*(flotl + one)*t5)
2680  300  cmn12%tq(4) = cortes*cmn12%tq(2)
2681       return
2682 !----------------------- end of subroutine dvset -----------------------
2683       end subroutine dvset
2684 !deck dvjust
2685       subroutine dvjust (yh, ldyh, iord, cmn12)
2686       implicit none
2687       double precision yh
2688       integer ldyh, iord
2689       dimension yh(ldyh,*)
2690       type( dvode_cmn_vars ) :: cmn12
2691 !-----------------------------------------------------------------------
2692 ! call sequence input -- yh, ldyh, iord
2693 ! call sequence output -- yh
2694 ! common block input -- nq, meth, lmax, hscal, tau(13), n
2695 ! common block variables accessed:
2696 !     /dvod_cmn01/ -- hscal, tau(13), lmax, meth, n, nq,
2698 ! subroutines called by dvjust: daxpy
2699 ! function routines called by dvjust: none
2700 !-----------------------------------------------------------------------
2701 ! this subroutine adjusts the yh array on reduction of order,
2702 ! and also when the order is increased for the stiff option (meth = 2).
2703 ! communication with dvjust uses the following:
2704 ! iord  = an integer flag used when meth = 2 to indicate an order
2705 !         increase (iord = +1) or an order decrease (iord = -1).
2706 ! hscal = step size h used in scaling of nordsieck array yh.
2707 !         (if iord = +1, dvjust assumes that hscal = tau(1).)
2708 ! see references 1 and 2 for details.
2709 !-----------------------------------------------------------------------
2711 ! type declarations for labeled common block dvod_cmn01 --------------------
2713 !      double precision acnrm, ccmxj, conp, crate, drc, el,   &
2714 !           eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
2715 !           rc, rl1, tau, tq, tn, uround
2716 !      integer icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
2717 !              l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
2718 !              locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
2719 !              n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
2720 !              nslp, nyh
2722 ! type declarations for local variables --------------------------------
2724       double precision alph0, alph1, hsum, one, prod, t1, xi,xiold, zero
2725       integer i, iback, j, jp1, lp1, nqm1, nqm2, nqp1
2726 !-----------------------------------------------------------------------
2727 ! the following fortran-77 declaration is to cause the values of the
2728 ! listed (local) variables to be saved between calls to this integrator.
2729 !-----------------------------------------------------------------------
2730       save one, zero
2732 !      common /dvod_cmn01/ acnrm, ccmxj, conp, crate, drc, el(13),   &
2733 !                      eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
2734 !                      rc, rl1, tau(13), tq(5), tn, uround,   &
2735 !                      icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
2736 !                      l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
2737 !                      locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
2738 !                      n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
2739 !                      nslp, nyh
2741       data one /1.0d0/, zero /0.0d0/
2743       if ((cmn12%nq .eq. 2) .and. (iord .ne. 1)) return
2744       nqm1 = cmn12%nq - 1
2745       nqm2 = cmn12%nq - 2
2746       go to (100, 200), cmn12%meth
2747 !-----------------------------------------------------------------------
2748 ! nonstiff option...
2749 ! check to see if the order is being increased or decreased.
2750 !-----------------------------------------------------------------------
2751  100  continue
2752       if (iord .eq. 1) go to 180
2753 ! order decrease. ------------------------------------------------------
2754       do 110 j = 1, cmn12%lmax
2755  110    cmn12%el(j) = zero
2756       cmn12%el(2) = one
2757       hsum = zero
2758       do 130 j = 1, nqm2
2759 ! construct coefficients of x*(x+xi(1))*...*(x+xi(j)). -----------------
2760         hsum = hsum + cmn12%tau(j)
2761         xi = hsum/cmn12%hscal
2762         jp1 = j + 1
2763         do 120 iback = 1, jp1
2764           i = (j + 3) - iback
2765  120      cmn12%el(i) = cmn12%el(i)*xi + cmn12%el(i-1)
2766  130    continue
2767 ! construct coefficients of integrated polynomial. ---------------------
2768       do 140 j = 2, nqm1
2769  140    cmn12%el(j+1) = real(cmn12%nq)*cmn12%el(j)/real(j)
2770 ! subtract correction terms from yh array. -----------------------------
2771       do 170 j = 3, cmn12%nq
2772         do 160 i = 1, cmn12%n
2773  160      yh(i,j) = yh(i,j) - yh(i,cmn12%l)*cmn12%el(j)
2774  170    continue
2775       return
2776 ! order increase. ------------------------------------------------------
2777 ! zero out next column in yh array. ------------------------------------
2778  180  continue
2779       lp1 = cmn12%l + 1
2780       do 190 i = 1, cmn12%n
2781  190    yh(i,lp1) = zero
2782       return
2783 !-----------------------------------------------------------------------
2784 ! stiff option...
2785 ! check to see if the order is being increased or decreased.
2786 !-----------------------------------------------------------------------
2787  200  continue
2788       if (iord .eq. 1) go to 300
2789 ! order decrease. ------------------------------------------------------
2790       do 210 j = 1, cmn12%lmax
2791  210    cmn12%el(j) = zero
2792       cmn12%el(3) = one
2793       hsum = zero
2794       do 230 j = 1,nqm2
2795 ! construct coefficients of x*x*(x+xi(1))*...*(x+xi(j)). ---------------
2796         hsum = hsum + cmn12%tau(j)
2797         xi = hsum/cmn12%hscal
2798         jp1 = j + 1
2799         do 220 iback = 1, jp1
2800           i = (j + 4) - iback
2801  220      cmn12%el(i) = cmn12%el(i)*xi + cmn12%el(i-1)
2802  230    continue
2803 ! subtract correction terms from yh array. -----------------------------
2804       do 250 j = 3,cmn12%nq
2805         do 240 i = 1, cmn12%n
2806  240      yh(i,j) = yh(i,j) - yh(i,cmn12%l)*cmn12%el(j)
2807  250    continue
2808       return
2809 ! order increase. ------------------------------------------------------
2810  300  do 310 j = 1, cmn12%lmax
2811  310    cmn12%el(j) = zero
2812       cmn12%el(3) = one
2813       alph0 = -one
2814       alph1 = one
2815       prod = one
2816       xiold = one
2817       hsum = cmn12%hscal
2818       if (cmn12%nq .eq. 1) go to 340
2819       do 330 j = 1, nqm1
2820 ! construct coefficients of x*x*(x+xi(1))*...*(x+xi(j)). ---------------
2821         jp1 = j + 1
2822         hsum = hsum + cmn12%tau(jp1)
2823         xi = hsum/cmn12%hscal
2824         prod = prod*xi
2825         alph0 = alph0 - one/real(jp1)
2826         alph1 = alph1 + one/xi
2827         do 320 iback = 1, jp1
2828           i = (j + 4) - iback
2829  320      cmn12%el(i) = cmn12%el(i)*xiold + cmn12%el(i-1)
2830         xiold = xi
2831  330    continue
2832  340  continue
2833       t1 = (-alph0 - alph1)/prod
2834 ! load column l + 1 in yh array. ---------------------------------------
2835       lp1 = cmn12%l + 1
2836       do 350 i = 1, cmn12%n
2837  350    yh(i,lp1) = t1*yh(i,cmn12%lmax)
2838 ! add correction terms to yh array. ------------------------------------
2839       nqp1 = cmn12%nq + 1
2840       do 370 j = 3, nqp1
2841         call daxpy (cmn12%n, cmn12%el(j), yh(1,lp1), 1, yh(1,j), 1 )
2842  370  continue
2843       return
2844 !----------------------- end of subroutine dvjust ----------------------
2845       end subroutine dvjust
2846 !deck dvnlsd
2847       subroutine dvnlsd (y, yh, ldyh, vsav, savf, ewt, acor, iwm, wm,   &
2848                        f, jac, pdum, nflag, rpar, ipar, cmn12)
2849       implicit none
2850       external f, jac, pdum
2851       double precision y, yh, vsav, savf, ewt, acor, wm, rpar
2852       integer ldyh, iwm, nflag, ipar
2853       dimension y(*), yh(ldyh,*), vsav(*), savf(*), ewt(*), acor(*),   &
2854                 iwm(*), wm(*), rpar(*), ipar(*)
2855       type( dvode_cmn_vars ) :: cmn12
2856 !-----------------------------------------------------------------------
2857 ! call sequence input -- y, yh, ldyh, savf, ewt, acor, iwm, wm,
2858 !                        f, jac, nflag, rpar, ipar
2859 ! call sequence output -- yh, acor, wm, iwm, nflag
2860 ! common block variables accessed:
2861 !     /dvod_cmn01/ acnrm, crate, drc, h, rc, rl1, tq(5), tn, icf,
2862 !                jcur, meth, miter, n, nslp
2863 !     /dvod_cmn02/ hu, ncfn, netf, nfe, nje, nlu, nni, nqu, nst
2865 ! subroutines called by dvnlsd: f, daxpy, dcopy, dscal, dvjac, dvsol
2866 ! function routines called by dvnlsd: dvnorm
2867 !-----------------------------------------------------------------------
2868 ! subroutine dvnlsd is a nonlinear system solver, which uses functional
2869 ! iteration or a chord (modified newton) method.  for the chord method
2870 ! direct linear algebraic system solvers are used.  subroutine dvnlsd
2871 ! then handles the corrector phase of this integration package.
2873 ! communication with dvnlsd is done with the following variables. (for
2874 ! more details, please see the comments in the driver subroutine.)
2876 ! y          = the dependent variable, a vector of length n, input.
2877 ! yh         = the nordsieck (taylor) array, ldyh by lmax, input
2878 !              and output.  on input, it contains predicted values.
2879 ! ldyh       = a constant .ge. n, the first dimension of yh, input.
2880 ! vsav       = unused work array.
2881 ! savf       = a work array of length n.
2882 ! ewt        = an error weight vector of length n, input.
2883 ! acor       = a work array of length n, used for the accumulated
2884 !              corrections to the predicted y vector.
2885 ! wm,iwm     = real and integer work arrays associated with matrix
2886 !              operations in chord iteration (miter .ne. 0).
2887 ! f          = dummy name for user supplied routine for f.
2888 ! jac        = dummy name for user supplied jacobian routine.
2889 ! pdum       = unused dummy subroutine name.  included for uniformity
2890 !              over collection of integrators.
2891 ! nflag      = input/output flag, with values and meanings as follows:
2892 !              input
2893 !                  0 first call for this time step.
2894 !                 -1 convergence failure in previous call to dvnlsd.
2895 !                 -2 error test failure in dvstep.
2896 !              output
2897 !                  0 successful completion of nonlinear solver.
2898 !                 -1 convergence failure or singular matrix.
2899 !                 -2 unrecoverable error in matrix preprocessing
2900 !                    (cannot occur here).
2901 !                 -3 unrecoverable error in solution (cannot occur
2902 !                    here).
2903 ! rpar, ipar = dummy names for user's real and integer work arrays.
2905 ! ipup       = own variable flag with values and meanings as follows:
2906 !              0,            do not update the newton matrix.
2907 !              miter .ne. 0, update newton matrix, because it is the
2908 !                            initial step, order was changed, the error
2909 !                            test failed, or an update is indicated by
2910 !                            the scalar rc or step counter nst.
2912 ! for more details, see comments in driver subroutine.
2913 !-----------------------------------------------------------------------
2914 !! type declarations for labeled common block dvod_cmn01 --------------------
2916 !      double precision acnrm, ccmxj, conp, crate, drc, el,   &
2917 !           eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
2918 !           rc, rl1, tau, tq, tn, uround
2919 !      integer icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
2920 !              l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
2921 !              locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
2922 !              n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
2923 !              nslp, nyh
2925 !! type declarations for labeled common block dvod_cmn02 --------------------
2927 !      double precision hu
2928 !      integer ncfn, netf, nfe, nje, nlu, nni, nqu, nst
2930 ! type declarations for local variables --------------------------------
2932       double precision ccmax, crdown, cscale, dcon, del, delp, one,   &
2933            rdiv, two, zero
2934       integer i, ierpj, iersl, m, maxcor, msbp
2936 ! type declaration for function subroutines called ---------------------
2938 ! 27-oct-2005 rce - do not declare functions that are in the module
2939 !     double precision dvnorm
2940 !-----------------------------------------------------------------------
2941 ! the following fortran-77 declaration is to cause the values of the
2942 ! listed (local) variables to be saved between calls to this integrator.
2943 !-----------------------------------------------------------------------
2944       save ccmax, crdown, maxcor, msbp, rdiv, one, two, zero
2946 !      common /dvod_cmn01/ acnrm, ccmxj, conp, crate, drc, el(13),   &
2947 !                      eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
2948 !                      rc, rl1, tau(13), tq(5), tn, uround,   &
2949 !                      icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
2950 !                      l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
2951 !                      locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
2952 !                      n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
2953 !                      nslp, nyh
2954 !      common /dvod_cmn02/ hu, ncfn, netf, nfe, nje, nlu, nni, nqu, nst
2956       data ccmax /0.3d0/, crdown /0.3d0/, maxcor /3/, msbp /20/,   &
2957            rdiv  /2.0d0/
2958       data one /1.0d0/, two /2.0d0/, zero /0.0d0/
2959 !-----------------------------------------------------------------------
2960 ! on the first step, on a change of method order, or after a
2961 ! nonlinear convergence failure with nflag = -2, set ipup = miter
2962 ! to force a jacobian update when miter .ne. 0.
2963 !-----------------------------------------------------------------------
2964       if (cmn12%jstart .eq. 0) cmn12%nslp = 0
2965       if (nflag .eq. 0) cmn12%icf = 0
2966       if (nflag .eq. -2) cmn12%ipup = cmn12%miter
2967       if ( (cmn12%jstart .eq. 0) .or. (cmn12%jstart .eq. -1) ) cmn12%ipup = cmn12%miter
2968 ! if this is functional iteration, set crate .eq. 1 and drop to 220
2969       if (cmn12%miter .eq. 0) then
2970         cmn12%crate = one
2971         go to 220
2972       endif
2973 !-----------------------------------------------------------------------
2974 ! rc is the ratio of new to old values of the coefficient h/el(2)=h/l1.
2975 ! when rc differs from 1 by more than ccmax, ipup is set to miter
2976 ! to force dvjac to be called, if a jacobian is involved.
2977 ! in any case, dvjac is called at least every msbp steps.
2978 !-----------------------------------------------------------------------
2979       cmn12%drc = abs(cmn12%rc-one)
2980       if (cmn12%drc .gt. ccmax .or. cmn12%nst .ge. cmn12%nslp+msbp) cmn12%ipup = cmn12%miter
2981 !-----------------------------------------------------------------------
2982 ! up to maxcor corrector iterations are taken.  a convergence test is
2983 ! made on the r.m.s. norm of each correction, weighted by the error
2984 ! weight vector ewt.  the sum of the corrections is accumulated in the
2985 ! vector acor(i).  the yh array is not altered in the corrector loop.
2986 !-----------------------------------------------------------------------
2987  220  m = 0
2988       delp = zero
2989       call dcopy (cmn12%n, yh(1,1), 1, y, 1 )
2990       call f (cmn12%n, cmn12%tn, y, savf, rpar, ipar)
2991       cmn12%nfe = cmn12%nfe + 1
2992       if (cmn12%ipup .le. 0) go to 250
2993 !-----------------------------------------------------------------------
2994 ! if indicated, the matrix p = i - h*rl1*j is reevaluated and
2995 ! preprocessed before starting the corrector iteration.  ipup is set
2996 ! to 0 as an indicator that this has been done.
2997 !-----------------------------------------------------------------------
2998       call dvjac (y, yh, ldyh, ewt, acor, savf, wm, iwm, f, jac, ierpj,   &
2999                  rpar, ipar, cmn12)
3000       cmn12%ipup = 0
3001       cmn12%rc = one
3002       cmn12%drc = zero
3003       cmn12%crate = one
3004       cmn12%nslp = cmn12%nst
3005 ! if matrix is singular, take error return to force cut in step size. --
3006       if (ierpj .ne. 0) go to 430
3007  250  do 260 i = 1,cmn12%n
3008  260    acor(i) = zero
3009 ! this is a looping point for the corrector iteration. -----------------
3010  270  if (cmn12%miter .ne. 0) go to 350
3011 !-----------------------------------------------------------------------
3012 ! in the case of functional iteration, update y directly from
3013 ! the result of the last function evaluation.
3014 !-----------------------------------------------------------------------
3015       do 280 i = 1,cmn12%n
3016  280    savf(i) = cmn12%rl1*(cmn12%h*savf(i) - yh(i,2))
3017       do 290 i = 1,cmn12%n
3018  290    y(i) = savf(i) - acor(i)
3019       del = dvnorm (cmn12%n, y, ewt)
3020       do 300 i = 1,cmn12%n
3021  300    y(i) = yh(i,1) + savf(i)
3022       call dcopy (cmn12%n, savf, 1, acor, 1)
3023       go to 400
3024 !-----------------------------------------------------------------------
3025 ! in the case of the chord method, compute the corrector error,
3026 ! and solve the linear system with that as right-hand side and
3027 ! p as coefficient matrix.  the correction is scaled by the factor
3028 ! 2/(1+rc) to account for changes in h*rl1 since the last dvjac call.
3029 !-----------------------------------------------------------------------
3030  350  do 360 i = 1,cmn12%n
3031  360    y(i) = (cmn12%rl1*cmn12%h)*savf(i) - (cmn12%rl1*yh(i,2) + acor(i))
3032       call dvsol (wm, iwm, y, iersl, cmn12)
3033       cmn12%nni = cmn12%nni + 1
3034       if (iersl .gt. 0) go to 410
3035       if (cmn12%meth .eq. 2 .and. cmn12%rc .ne. one) then
3036         cscale = two/(one + cmn12%rc)
3037         call dscal (cmn12%n, cscale, y, 1)
3038       endif
3039       del = dvnorm (cmn12%n, y, ewt)
3040       call daxpy (cmn12%n, one, y, 1, acor, 1)
3041       do 380 i = 1,cmn12%n
3042  380    y(i) = yh(i,1) + acor(i)
3043 !-----------------------------------------------------------------------
3044 ! test for convergence.  if m .gt. 0, an estimate of the convergence
3045 ! rate constant is stored in crate, and this is used in the test.
3046 !-----------------------------------------------------------------------
3047  400  if (m .ne. 0) cmn12%crate = max(crdown*cmn12%crate,del/delp)
3048       dcon = del*min(one,cmn12%crate)/cmn12%tq(4)
3049       if (dcon .le. one) go to 450
3050       m = m + 1
3051       if (m .eq. maxcor) go to 410
3052       if (m .ge. 2 .and. del .gt. rdiv*delp) go to 410
3053       delp = del
3054       call f (cmn12%n, cmn12%tn, y, savf, rpar, ipar)
3055       cmn12%nfe = cmn12%nfe + 1
3056       go to 270
3058  410  if (cmn12%miter .eq. 0 .or. cmn12%jcur .eq. 1) go to 430
3059       cmn12%icf = 1
3060       cmn12%ipup = cmn12%miter
3061       go to 220
3063  430  continue
3064       nflag = -1
3065       cmn12%icf = 2
3066       cmn12%ipup = cmn12%miter
3067       return
3069 ! return for successful step. ------------------------------------------
3070  450  nflag = 0
3071       cmn12%jcur = 0
3072       cmn12%icf = 0
3073       if (m .eq. 0) cmn12%acnrm = del
3074       if (m .gt. 0) cmn12%acnrm = dvnorm (cmn12%n, acor, ewt)
3075       return
3076 !----------------------- end of subroutine dvnlsd ----------------------
3077       end subroutine dvnlsd
3078 !deck dvjac
3079       subroutine dvjac (y, yh, ldyh, ewt, ftem, savf, wm, iwm, f, jac,   &
3080                        ierpj, rpar, ipar, cmn12)
3081       implicit none
3082       external f, jac
3083       double precision y, yh, ewt, ftem, savf, wm, rpar
3084       integer ldyh, iwm, ierpj, ipar
3085       dimension y(*), yh(ldyh,*), ewt(*), ftem(*), savf(*),   &
3086          wm(*), iwm(*), rpar(*), ipar(*)
3087       type( dvode_cmn_vars ) :: cmn12
3088 !-----------------------------------------------------------------------
3089 ! call sequence input -- y, yh, ldyh, ewt, ftem, savf, wm, iwm,
3090 !                        f, jac, rpar, ipar
3091 ! call sequence output -- wm, iwm, ierpj
3092 ! common block variables accessed:
3093 !     /dvod_cmn01/  ccmxj, drc, h, rl1, tn, uround, icf, jcur, locjs,
3094 !               miter, msbj, n, nslj
3095 !     /dvod_cmn02/  nfe, nst, nje, nlu
3097 ! subroutines called by dvjac: f, jac, dacopy, dcopy, dgbfa, dgefa,
3098 !                              dscal
3099 ! function routines called by dvjac: dvnorm
3100 !-----------------------------------------------------------------------
3101 ! dvjac is called by dvnlsd to compute and process the matrix
3102 ! p = i - h*rl1*j , where j is an approximation to the jacobian.
3103 ! here j is computed by the user-supplied routine jac if
3104 ! miter = 1 or 4, or by finite differencing if miter = 2, 3, or 5.
3105 ! if miter = 3, a diagonal approximation to j is used.
3106 ! if jsv = -1, j is computed from scratch in all cases.
3107 ! if jsv = 1 and miter = 1, 2, 4, or 5, and if the saved value of j is
3108 ! considered acceptable, then p is constructed from the saved j.
3109 ! j is stored in wm and replaced by p.  if miter .ne. 3, p is then
3110 ! subjected to lu decomposition in preparation for later solution
3111 ! of linear systems with p as coefficient matrix. this is done
3112 ! by dgefa if miter = 1 or 2, and by dgbfa if miter = 4 or 5.
3114 ! communication with dvjac is done with the following variables.  (for
3115 ! more details, please see the comments in the driver subroutine.)
3116 ! y          = vector containing predicted values on entry.
3117 ! yh         = the nordsieck array, an ldyh by lmax array, input.
3118 ! ldyh       = a constant .ge. n, the first dimension of yh, input.
3119 ! ewt        = an error weight vector of length n.
3120 ! savf       = array containing f evaluated at predicted y, input.
3121 ! wm         = real work space for matrices.  in the output, it contains
3122 !              the inverse diagonal matrix if miter = 3 and the lu
3123 !              decomposition of p if miter is 1, 2 , 4, or 5.
3124 !              storage of matrix elements starts at wm(3).
3125 !              storage of the saved jacobian starts at wm(locjs).
3126 !              wm also contains the following matrix-related data:
3127 !              wm(1) = sqrt(uround), used in numerical jacobian step.
3128 !              wm(2) = h*rl1, saved for later use if miter = 3.
3129 ! iwm        = integer work space containing pivot information,
3130 !              starting at iwm(31), if miter is 1, 2, 4, or 5.
3131 !              iwm also contains band parameters ml = iwm(1) and
3132 !              mu = iwm(2) if miter is 4 or 5.
3133 ! f          = dummy name for the user supplied subroutine for f.
3134 ! jac        = dummy name for the user supplied jacobian subroutine.
3135 ! rpar, ipar = dummy names for user's real and integer work arrays.
3136 ! rl1        = 1/el(2) (input).
3137 ! ierpj      = output error flag,  = 0 if no trouble, 1 if the p
3138 !              matrix is found to be singular.
3139 ! jcur       = output flag to indicate whether the jacobian matrix
3140 !              (or approximation) is now current.
3141 !              jcur = 0 means j is not current.
3142 !              jcur = 1 means j is current.
3143 !-----------------------------------------------------------------------
3145 !! type declarations for labeled common block dvod_cmn01 --------------------
3147 !      double precision acnrm, ccmxj, conp, crate, drc, el,   &
3148 !           eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
3149 !           rc, rl1, tau, tq, tn, uround
3150 !      integer icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
3151 !              l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
3152 !              locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
3153 !              n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
3154 !              nslp, nyh
3156 !! type declarations for labeled common block dvod_cmn02 --------------------
3158 !      double precision hu
3159 !      integer ncfn, netf, nfe, nje, nlu, nni, nqu, nst
3161 ! type declarations for local variables --------------------------------
3163       double precision con, di, fac, hrl1, one, pt1, r, r0, srur, thou,   &
3164            yi, yj, yjj, zero
3165       integer i, i1, i2, ier, ii, j, j1, jj, jok, lenp, mba, mband,   &
3166               meb1, meband, ml, ml3, mu, np1
3168 ! type declaration for function subroutines called ---------------------
3170 ! 27-oct-2005 rce - do not declare functions that are in the module
3171 !     double precision dvnorm
3172 !-----------------------------------------------------------------------
3173 ! the following fortran-77 declaration is to cause the values of the
3174 ! listed (local) variables to be saved between calls to this subroutine.
3175 !-----------------------------------------------------------------------
3176       save one, pt1, thou, zero
3177 !-----------------------------------------------------------------------
3178 !      common /dvod_cmn01/ acnrm, ccmxj, conp, crate, drc, el(13),   &
3179 !                      eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
3180 !                      rc, rl1, tau(13), tq(5), tn, uround,   &
3181 !                      icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
3182 !                      l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
3183 !                      locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
3184 !                      n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
3185 !                      nslp, nyh
3186 !      common /dvod_cmn02/ hu, ncfn, netf, nfe, nje, nlu, nni, nqu, nst
3188       data one /1.0d0/, thou /1000.0d0/, zero /0.0d0/, pt1 /0.1d0/
3190       ierpj = 0
3191       hrl1 = cmn12%h*cmn12%rl1
3192 ! see whether j should be evaluated (jok = -1) or not (jok = 1). -------
3193       jok = cmn12%jsv
3194       if (cmn12%jsv .eq. 1) then
3195         if (cmn12%nst .eq. 0 .or. cmn12%nst .gt. cmn12%nslj+cmn12%msbj) jok = -1
3196         if (cmn12%icf .eq. 1 .and. cmn12%drc .lt. cmn12%ccmxj) jok = -1
3197         if (cmn12%icf .eq. 2) jok = -1
3198       endif
3199 ! end of setting jok. --------------------------------------------------
3201       if (jok .eq. -1 .and. cmn12%miter .eq. 1) then
3202 ! if jok = -1 and miter = 1, call jac to evaluate jacobian. ------------
3203       cmn12%nje = cmn12%nje + 1
3204       cmn12%nslj = cmn12%nst
3205       cmn12%jcur = 1
3206       lenp = cmn12%n*cmn12%n
3207       do 110 i = 1,lenp
3208  110    wm(i+2) = zero
3209       call jac (cmn12%n, cmn12%tn, y, 0, 0, wm(3), cmn12%n, rpar, ipar)
3210       if (cmn12%jsv .eq. 1) call dcopy (lenp, wm(3), 1, wm(cmn12%locjs), 1)
3211       endif
3213       if (jok .eq. -1 .and. cmn12%miter .eq. 2) then
3214 ! if miter = 2, make n calls to f to approximate the jacobian. ---------
3215       cmn12%nje = cmn12%nje + 1
3216       cmn12%nslj = cmn12%nst
3217       cmn12%jcur = 1
3218       fac = dvnorm (cmn12%n, savf, ewt)
3219       r0 = thou*abs(cmn12%h)*cmn12%uround*real(cmn12%n)*fac
3220       if (r0 .eq. zero) r0 = one
3221       srur = wm(1)
3222       j1 = 2
3223       do 230 j = 1,cmn12%n
3224         yj = y(j)
3225         r = max(srur*abs(yj),r0/ewt(j))
3226         y(j) = y(j) + r
3227         fac = one/r
3228         call f (cmn12%n, cmn12%tn, y, ftem, rpar, ipar)
3229         do 220 i = 1,cmn12%n
3230  220      wm(i+j1) = (ftem(i) - savf(i))*fac
3231         y(j) = yj
3232         j1 = j1 + cmn12%n
3233  230    continue
3234       cmn12%nfe = cmn12%nfe + cmn12%n
3235       lenp = cmn12%n*cmn12%n
3236       if (cmn12%jsv .eq. 1) call dcopy (lenp, wm(3), 1, wm(cmn12%locjs), 1)
3237       endif
3239       if (jok .eq. 1 .and. (cmn12%miter .eq. 1 .or. cmn12%miter .eq. 2)) then
3240       cmn12%jcur = 0
3241       lenp = cmn12%n*cmn12%n
3242       call dcopy (lenp, wm(cmn12%locjs), 1, wm(3), 1)
3243       endif
3245       if (cmn12%miter .eq. 1 .or. cmn12%miter .eq. 2) then
3246 ! multiply jacobian by scalar, add identity, and do lu decomposition. --
3247       con = -hrl1
3248       call dscal (lenp, con, wm(3), 1)
3249       j = 3
3250       np1 = cmn12%n + 1
3251       do 250 i = 1,cmn12%n
3252         wm(j) = wm(j) + one
3253  250    j = j + np1
3254       cmn12%nlu = cmn12%nlu + 1
3255       call dgefa (wm(3), cmn12%n, cmn12%n, iwm(31), ier)
3256       if (ier .ne. 0) ierpj = 1
3257       return
3258       endif
3259 ! end of code block for miter = 1 or 2. --------------------------------
3261       if (cmn12%miter .eq. 3) then
3262 ! if miter = 3, construct a diagonal approximation to j and p. ---------
3263       cmn12%nje = cmn12%nje + 1
3264       cmn12%jcur = 1
3265       wm(2) = hrl1
3266       r = cmn12%rl1*pt1
3267       do 310 i = 1,cmn12%n
3268  310    y(i) = y(i) + r*(cmn12%h*savf(i) - yh(i,2))
3269       call f (cmn12%n, cmn12%tn, y, wm(3), rpar, ipar)
3270       cmn12%nfe = cmn12%nfe + 1
3271       do 320 i = 1,cmn12%n
3272         r0 = cmn12%h*savf(i) - yh(i,2)
3273         di = pt1*r0 - cmn12%h*(wm(i+2) - savf(i))
3274         wm(i+2) = one
3275         if (abs(r0) .lt. cmn12%uround/ewt(i)) go to 320
3276         if (abs(di) .eq. zero) go to 330
3277         wm(i+2) = pt1*r0/di
3278  320    continue
3279       return
3280  330  ierpj = 1
3281       return
3282       endif
3283 ! end of code block for miter = 3. -------------------------------------
3285 ! set constants for miter = 4 or 5. ------------------------------------
3286       ml = iwm(1)
3287       mu = iwm(2)
3288       ml3 = ml + 3
3289       mband = ml + mu + 1
3290       meband = mband + ml
3291       lenp = meband*cmn12%n
3293       if (jok .eq. -1 .and. cmn12%miter .eq. 4) then
3294 ! if jok = -1 and miter = 4, call jac to evaluate jacobian. ------------
3295       cmn12%nje = cmn12%nje + 1
3296       cmn12%nslj = cmn12%nst
3297       cmn12%jcur = 1
3298       do 410 i = 1,lenp
3299  410    wm(i+2) = zero
3300       call jac (cmn12%n, cmn12%tn, y, ml, mu, wm(ml3), meband, rpar, ipar)
3301       if (cmn12%jsv .eq. 1)   &
3302          call dacopy (mband, cmn12%n, wm(ml3), meband, wm(cmn12%locjs), mband)
3303       endif
3305       if (jok .eq. -1 .and. cmn12%miter .eq. 5) then
3306 ! if miter = 5, make ml+mu+1 calls to f to approximate the jacobian. ---
3307       cmn12%nje = cmn12%nje + 1
3308       cmn12%nslj = cmn12%nst
3309       cmn12%jcur = 1
3310       mba = min(mband,cmn12%n)
3311       meb1 = meband - 1
3312       srur = wm(1)
3313       fac = dvnorm (cmn12%n, savf, ewt)
3314       r0 = thou*abs(cmn12%h)*cmn12%uround*real(cmn12%n)*fac
3315       if (r0 .eq. zero) r0 = one
3316       do 560 j = 1,mba
3317         do 530 i = j,cmn12%n,mband
3318           yi = y(i)
3319           r = max(srur*abs(yi),r0/ewt(i))
3320  530      y(i) = y(i) + r
3321         call f (cmn12%n, cmn12%tn, y, ftem, rpar, ipar)
3322         do 550 jj = j,cmn12%n,mband
3323           y(jj) = yh(jj,1)
3324           yjj = y(jj)
3325           r = max(srur*abs(yjj),r0/ewt(jj))
3326           fac = one/r
3327           i1 = max(jj-mu,1)
3328           i2 = min(jj+ml,cmn12%n)
3329           ii = jj*meb1 - ml + 2
3330           do 540 i = i1,i2
3331  540        wm(ii+i) = (ftem(i) - savf(i))*fac
3332  550      continue
3333  560    continue
3334       cmn12%nfe = cmn12%nfe + mba
3335       if (cmn12%jsv .eq. 1)   &
3336          call dacopy (mband, cmn12%n, wm(ml3), meband, wm(cmn12%locjs), mband)
3337       endif
3339       if (jok .eq. 1) then
3340       cmn12%jcur = 0
3341       call dacopy (mband, cmn12%n, wm(cmn12%locjs), mband, wm(ml3), meband)
3342       endif
3344 ! multiply jacobian by scalar, add identity, and do lu decomposition.
3345       con = -hrl1
3346       call dscal (lenp, con, wm(3), 1 )
3347       ii = mband + 2
3348       do 580 i = 1,cmn12%n
3349         wm(ii) = wm(ii) + one
3350  580    ii = ii + meband
3351       cmn12%nlu = cmn12%nlu + 1
3352       call dgbfa (wm(3), meband, cmn12%n, ml, mu, iwm(31), ier)
3353       if (ier .ne. 0) ierpj = 1
3354       return
3355 ! end of code block for miter = 4 or 5. --------------------------------
3357 !----------------------- end of subroutine dvjac -----------------------
3358       end subroutine dvjac
3359 !deck dacopy
3360       subroutine dacopy (nrow, ncol, a, nrowa, b, nrowb)
3361       double precision a, b
3362       integer nrow, ncol, nrowa, nrowb
3363       dimension a(nrowa,ncol), b(nrowb,ncol)
3364 !-----------------------------------------------------------------------
3365 ! call sequence input -- nrow, ncol, a, nrowa, nrowb
3366 ! call sequence output -- b
3367 ! common block variables accessed -- none
3369 ! subroutines called by dacopy: dcopy
3370 ! function routines called by dacopy: none
3371 !-----------------------------------------------------------------------
3372 ! this routine copies one rectangular array, a, to another, b,
3373 ! where a and b may have different row dimensions, nrowa and nrowb.
3374 ! the data copied consists of nrow rows and ncol columns.
3375 !-----------------------------------------------------------------------
3376       integer ic
3378       do 20 ic = 1,ncol
3379         call dcopy (nrow, a(1,ic), 1, b(1,ic), 1)
3380  20     continue
3382       return
3383 !----------------------- end of subroutine dacopy ----------------------
3384       end subroutine dacopy
3385 !deck dvsol
3386       subroutine dvsol (wm, iwm, x, iersl, cmn12)
3387       implicit none
3388       double precision wm, x
3389       integer iwm, iersl
3390       dimension wm(*), iwm(*), x(*)
3391       type( dvode_cmn_vars ) :: cmn12
3392 !-----------------------------------------------------------------------
3393 ! call sequence input -- wm, iwm, x
3394 ! call sequence output -- x, iersl
3395 ! common block variables accessed:
3396 !     /dvod_cmn01/ -- h, rl1, miter, n
3398 ! subroutines called by dvsol: dgesl, dgbsl
3399 ! function routines called by dvsol: none
3400 !-----------------------------------------------------------------------
3401 ! this routine manages the solution of the linear system arising from
3402 ! a chord iteration.  it is called if miter .ne. 0.
3403 ! if miter is 1 or 2, it calls dgesl to accomplish this.
3404 ! if miter = 3 it updates the coefficient h*rl1 in the diagonal
3405 ! matrix, and then computes the solution.
3406 ! if miter is 4 or 5, it calls dgbsl.
3407 ! communication with dvsol uses the following variables:
3408 ! wm    = real work space containing the inverse diagonal matrix if
3409 !         miter = 3 and the lu decomposition of the matrix otherwise.
3410 !         storage of matrix elements starts at wm(3).
3411 !         wm also contains the following matrix-related data:
3412 !         wm(1) = sqrt(uround) (not used here),
3413 !         wm(2) = hrl1, the previous value of h*rl1, used if miter = 3.
3414 ! iwm   = integer work space containing pivot information, starting at
3415 !         iwm(31), if miter is 1, 2, 4, or 5.  iwm also contains band
3416 !         parameters ml = iwm(1) and mu = iwm(2) if miter is 4 or 5.
3417 ! x     = the right-hand side vector on input, and the solution vector
3418 !         on output, of length n.
3419 ! iersl = output flag.  iersl = 0 if no trouble occurred.
3420 !         iersl = 1 if a singular matrix arose with miter = 3.
3421 !-----------------------------------------------------------------------
3423 !! type declarations for labeled common block dvod_cmn01 --------------------
3425 !      double precision acnrm, ccmxj, conp, crate, drc, el,   &
3426 !           eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
3427 !           rc, rl1, tau, tq, tn, uround
3428 !      integer icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
3429 !              l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
3430 !              locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
3431 !              n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
3432 !              nslp, nyh
3434 ! type declarations for local variables --------------------------------
3436       integer i, meband, ml, mu
3437       double precision di, hrl1, one, phrl1, r, zero
3438 !-----------------------------------------------------------------------
3439 ! the following fortran-77 declaration is to cause the values of the
3440 ! listed (local) variables to be saved between calls to this integrator.
3441 !-----------------------------------------------------------------------
3442       save one, zero
3444 !      common /dvod_cmn01/ acnrm, ccmxj, conp, crate, drc, el(13),   &
3445 !                      eta, etamax, h, hmin, hmxi, hnew, hscal, prl1,   &
3446 !                      rc, rl1, tau(13), tq(5), tn, uround,   &
3447 !                      icf, init, ipup, jcur, jstart, jsv, kflag, kuth,   &
3448 !                      l, lmax, lyh, lewt, lacor, lsavf, lwm, liwm,   &
3449 !                      locjs, maxord, meth, miter, msbj, mxhnil, mxstep,   &
3450 !                      n, newh, newq, nhnil, nq, nqnyh, nqwait, nslj,   &
3451 !                      nslp, nyh
3453       data one /1.0d0/, zero /0.0d0/
3455       iersl = 0
3456       go to (100, 100, 300, 400, 400), cmn12%miter
3457  100  call dgesl (wm(3), cmn12%n, cmn12%n, iwm(31), x, 0)
3458       return
3460  300  phrl1 = wm(2)
3461       hrl1 = cmn12%h*cmn12%rl1
3462       wm(2) = hrl1
3463       if (hrl1 .eq. phrl1) go to 330
3464       r = hrl1/phrl1
3465       do 320 i = 1,cmn12%n
3466         di = one - r*(one - one/wm(i+2))
3467         if (abs(di) .eq. zero) go to 390
3468  320    wm(i+2) = one/di
3470  330  do 340 i = 1,cmn12%n
3471  340    x(i) = wm(i+2)*x(i)
3472       return
3473  390  iersl = 1
3474       return
3476  400  ml = iwm(1)
3477       mu = iwm(2)
3478       meband = 2*ml + mu + 1
3479       call dgbsl (wm(3), meband, cmn12%n, ml, mu, iwm(31), x, 0)
3480       return
3481 !----------------------- end of subroutine dvsol -----------------------
3482       end subroutine dvsol
3483 !!deck dvsrco
3484 !      subroutine dvsrco (rsav, isav, job)
3485 !      double precision rsav
3486 !      integer isav, job
3487 !      dimension rsav(*), isav(*)
3488 !!-----------------------------------------------------------------------
3489 !! call sequence input -- rsav, isav, job
3490 !! call sequence output -- rsav, isav
3491 !! common block variables accessed -- all of /dvod_cmn01/ and /dvod_cmn02/
3493 !! subroutines/functions called by dvsrco: none
3494 !!-----------------------------------------------------------------------
3495 !! this routine saves or restores (depending on job) the contents of the
3496 !! common blocks dvod_cmn01 and dvod_cmn02, which are used internally by dvode.
3498 !! rsav = real array of length 49 or more.
3499 !! isav = integer array of length 41 or more.
3500 !! job  = flag indicating to save or restore the common blocks:
3501 !!        job  = 1 if common is to be saved (written to rsav/isav).
3502 !!        job  = 2 if common is to be restored (read from rsav/isav).
3503 !!        a call with job = 2 presumes a prior call with job = 1.
3504 !!-----------------------------------------------------------------------
3505 !      double precision rvod1, rvod2
3506 !      integer ivod1, ivod2
3507 !      integer i, leniv1, leniv2, lenrv1, lenrv2
3508 !!-----------------------------------------------------------------------
3509 !! the following fortran-77 declaration is to cause the values of the
3510 !! listed (local) variables to be saved between calls to this integrator.
3511 !!-----------------------------------------------------------------------
3512 !      save lenrv1, leniv1, lenrv2, leniv2
3514 !      common /dvod_cmn01/ rvod1(48), ivod1(33)
3515 !      common /dvod_cmn02/ rvod2(1), ivod2(8)
3516 !      data lenrv1/48/, leniv1/33/, lenrv2/1/, leniv2/8/
3518 !      if (job .eq. 2) go to 100
3519 !      do 10 i = 1,lenrv1
3520 ! 10     rsav(i) = rvod1(i)
3521 !      do 15 i = 1,lenrv2
3522 ! 15     rsav(lenrv1+i) = rvod2(i)
3524 !      do 20 i = 1,leniv1
3525 ! 20     isav(i) = ivod1(i)
3526 !      do 25 i = 1,leniv2
3527 ! 25     isav(leniv1+i) = ivod2(i)
3529 !      return
3531 ! 100  continue
3532 !      do 110 i = 1,lenrv1
3533 ! 110     rvod1(i) = rsav(i)
3534 !      do 115 i = 1,lenrv2
3535 ! 115     rvod2(i) = rsav(lenrv1+i)
3537 !      do 120 i = 1,leniv1
3538 ! 120     ivod1(i) = isav(i)
3539 !      do 125 i = 1,leniv2
3540 ! 125     ivod2(i) = isav(leniv1+i)
3542 !      return
3543 !!----------------------- end of subroutine dvsrco ----------------------
3544 !      end subroutine dvsrco
3545 !deck dewset
3546       subroutine dewset (n, itol, rtol, atol, ycur, ewt)
3547 !***begin prologue  dewset
3548 !***subsidiary
3549 !***purpose  set error weight vector.
3550 !***type      double precision (sewset-s, dewset-d)
3551 !***author  hindmarsh, alan c., (llnl)
3552 !***description
3554 !  this subroutine sets the error weight vector ewt according to
3555 !      ewt(i) = rtol(i)*abs(ycur(i)) + atol(i),  i = 1,...,n,
3556 !  with the subscript on rtol and/or atol possibly replaced by 1 above,
3557 !  depending on the value of itol.
3559 !***see also  dlsode
3560 !***routines called  (none)
3561 !***revision history  (yymmdd)
3562 !   791129  date written
3563 !   890501  modified prologue to slatec/ldoc format.  (fnf)
3564 !   890503  minor cosmetic changes.  (fnf)
3565 !   930809  renamed to allow single/double precision versions. (ach)
3566 !***end prologue  dewset
3567 !**end
3568       integer n, itol
3569       integer i
3570       double precision rtol, atol, ycur, ewt
3571       dimension rtol(*), atol(*), ycur(n), ewt(n)
3573 !***first executable statement  dewset
3574       go to (10, 20, 30, 40), itol
3575  10   continue
3576       do 15 i = 1,n
3577  15     ewt(i) = rtol(1)*abs(ycur(i)) + atol(1)
3578       return
3579  20   continue
3580       do 25 i = 1,n
3581  25     ewt(i) = rtol(1)*abs(ycur(i)) + atol(i)
3582       return
3583  30   continue
3584       do 35 i = 1,n
3585  35     ewt(i) = rtol(i)*abs(ycur(i)) + atol(1)
3586       return
3587  40   continue
3588       do 45 i = 1,n
3589  45     ewt(i) = rtol(i)*abs(ycur(i)) + atol(i)
3590       return
3591 !----------------------- end of subroutine dewset ----------------------
3592       end subroutine dewset
3593 !deck dvnorm
3594       double precision function dvnorm (n, v, w)
3595 !***begin prologue  dvnorm
3596 !***subsidiary
3597 !***purpose  weighted root-mean-square vector norm.
3598 !***type      double precision (svnorm-s, dvnorm-d)
3599 !***author  hindmarsh, alan c., (llnl)
3600 !***description
3602 !  this function routine computes the weighted root-mean-square norm
3603 !  of the vector of length n contained in the array v, with weights
3604 !  contained in the array w of length n:
3605 !    dvnorm = sqrt( (1/n) * sum( v(i)*w(i) )**2 )
3607 !***see also  dlsode
3608 !***routines called  (none)
3609 !***revision history  (yymmdd)
3610 !   791129  date written
3611 !   890501  modified prologue to slatec/ldoc format.  (fnf)
3612 !   890503  minor cosmetic changes.  (fnf)
3613 !   930809  renamed to allow single/double precision versions. (ach)
3614 !***end prologue  dvnorm
3615 !**end
3616       integer n,   i
3617       double precision v, w,   sum
3618       dimension v(n), w(n)
3620 !***first executable statement  dvnorm
3621       sum = 0.0d0
3622       do 10 i = 1,n
3623  10     sum = sum + (v(i)*w(i))**2
3624       dvnorm = sqrt(sum/n)
3625       return
3626 !----------------------- end of function dvnorm ------------------------
3627       end function dvnorm
3628 !deck xerrwd
3629       subroutine xerrwd (msg, nmes, nerr, level, ni, i1, i2, nr, r1, r2)
3630 !***begin prologue  xerrwd
3631 !***subsidiary
3632 !***purpose  write error message with values.
3633 !***category  r3c
3634 !***type      double precision (xerrwv-s, xerrwd-d)
3635 !***author  hindmarsh, alan c., (llnl)
3636 !***description
3638 !  subroutines xerrwd, xsetf, xsetun, and the function routine ixsav,
3639 !  as given here, constitute a simplified version of the slatec error
3640 !  handling package.
3642 !  all arguments are input arguments.
3644 !  msg    = the message (character array).
3645 !  nmes   = the length of msg (number of characters).
3646 !  nerr   = the error number (not used).
3647 !  level  = the error level..
3648 !           0 or 1 means recoverable (control returns to caller).
3649 !           2 means fatal (run is aborted--see note below).
3650 !  ni     = number of integers (0, 1, or 2) to be printed with message.
3651 !  i1,i2  = integers to be printed, depending on ni.
3652 !  nr     = number of reals (0, 1, or 2) to be printed with message.
3653 !  r1,r2  = reals to be printed, depending on nr.
3655 !  note..  this routine is machine-dependent and specialized for use
3656 !  in limited context, in the following ways..
3657 !  1. the argument msg is assumed to be of type character, and
3658 !     the message is printed with a format of (1x,a).
3659 !  2. the message is assumed to take only one line.
3660 !     multi-line messages are generated by repeated calls.
3661 !  3. if level = 2, control passes to the statement   stop
3662 !     to abort the run.  this statement may be machine-dependent.
3663 !  4. r1 and r2 are assumed to be in double precision and are printed
3664 !     in d21.13 format.
3666 !***routines called  ixsav
3667 !***revision history  (yymmdd)
3668 !   920831  date written
3669 !   921118  replaced mflgsv/lunsav by ixsav. (ach)
3670 !   930329  modified prologue to slatec format. (fnf)
3671 !   930407  changed msg from character*1 array to variable. (fnf)
3672 !   930922  minor cosmetic change. (fnf)
3673 !***end prologue  xerrwd
3675 !*internal notes:
3677 ! for a different default logical unit number, ixsav (or a subsidiary
3678 ! routine that it calls) will need to be modified.
3679 ! for a different run-abort command, change the statement following
3680 ! statement 100 at the end.
3681 !-----------------------------------------------------------------------
3682 ! subroutines called by xerrwd.. none
3683 ! function routine called by xerrwd.. ixsav
3684 !-----------------------------------------------------------------------
3685 !**end
3687 !  declare arguments.
3689       double precision r1, r2
3690       integer nmes, nerr, level, ni, i1, i2, nr
3691       character*(*) msg
3693 !  declare local variables.
3695 ! 27-oct-2005 rce - do not declare functions that are in the module
3696 !     integer lunit, ixsav, mesflg
3697       integer lunit,        mesflg
3699 !  get logical unit number and message print flag.
3701 !***first executable statement  xerrwd
3702       lunit = ixsav (1, 0, .false.)
3703       mesflg = ixsav (2, 0, .false.)
3704       if (mesflg .eq. 0) go to 100
3706 !  write the message.
3708       write (lunit,10)  msg
3709  10   format(1x,a)
3710       if (ni .eq. 1) write (lunit, 20) i1
3711  20   format(6x,'in above message,  i1 =',i10)
3712       if (ni .eq. 2) write (lunit, 30) i1,i2
3713  30   format(6x,'in above message,  i1 =',i10,3x,'i2 =',i10)
3714       if (nr .eq. 1) write (lunit, 40) r1
3715  40   format(6x,'in above message,  r1 =',d21.13)
3716       if (nr .eq. 2) write (lunit, 50) r1,r2
3717  50   format(6x,'in above,  r1 =',d21.13,3x,'r2 =',d21.13)
3719 !  abort the run if level = 2.
3721  100  if (level .ne. 2) return
3722          call wrf_error_fatal(" ")
3724 !----------------------- end of subroutine xerrwd ----------------------
3725       end subroutine xerrwd
3726 !deck xsetf
3727       subroutine xsetf (mflag)
3728 !***begin prologue  xsetf
3729 !***purpose  reset the error print control flag.
3730 !***category  r3a
3731 !***type      all (xsetf-a)
3732 !***keywords  error control
3733 !***author  hindmarsh, alan c., (llnl)
3734 !***description
3736 !   xsetf sets the error print control flag to mflag:
3737 !      mflag=1 means print all messages (the default).
3738 !      mflag=0 means no printing.
3740 !***see also  xerrwd, xerrwv
3741 !***references  (none)
3742 !***routines called  ixsav
3743 !***revision history  (yymmdd)
3744 !   921118  date written
3745 !   930329  added slatec format prologue. (fnf)
3746 !   930407  corrected see also section. (fnf)
3747 !   930922  made user-callable, and other cosmetic changes. (fnf)
3748 !***end prologue  xsetf
3750 ! subroutines called by xsetf.. none
3751 ! function routine called by xsetf.. ixsav
3752 !-----------------------------------------------------------------------
3753 !**end
3754 ! 27-oct-2005 rce - do not declare functions that are in the module
3755 !     integer mflag, junk, ixsav
3756       integer mflag, junk
3758 !***first executable statement  xsetf
3759       if (mflag .eq. 0 .or. mflag .eq. 1) junk = ixsav (2,mflag,.true.)
3760       return
3761 !----------------------- end of subroutine xsetf -----------------------
3762       end subroutine xsetf
3763 !deck xsetun
3764       subroutine xsetun (lun)
3765 !***begin prologue  xsetun
3766 !***purpose  reset the logical unit number for error messages.
3767 !***category  r3b
3768 !***type      all (xsetun-a)
3769 !***keywords  error control
3770 !***description
3772 !   xsetun sets the logical unit number for error messages to lun.
3774 !***author  hindmarsh, alan c., (llnl)
3775 !***see also  xerrwd, xerrwv
3776 !***references  (none)
3777 !***routines called  ixsav
3778 !***revision history  (yymmdd)
3779 !   921118  date written
3780 !   930329  added slatec format prologue. (fnf)
3781 !   930407  corrected see also section. (fnf)
3782 !   930922  made user-callable, and other cosmetic changes. (fnf)
3783 !***end prologue  xsetun
3785 ! subroutines called by xsetun.. none
3786 ! function routine called by xsetun.. ixsav
3787 !-----------------------------------------------------------------------
3788 !**end
3789 ! 27-oct-2005 rce - do not declare functions that are in the module
3790 !     integer lun, junk, ixsav
3791       integer lun, junk
3793 !***first executable statement  xsetun
3794       if (lun .gt. 0) junk = ixsav (1,lun,.true.)
3795       return
3796 !----------------------- end of subroutine xsetun ----------------------
3797       end subroutine xsetun
3798 !deck ixsav
3799       integer function ixsav (ipar, ivalue, iset)
3800 !***begin prologue  ixsav
3801 !***subsidiary
3802 !***purpose  save and recall error message control parameters.
3803 !***category  r3c
3804 !***type      all (ixsav-a)
3805 !***author  hindmarsh, alan c., (llnl)
3806 !***description
3808 !  ixsav saves and recalls one of two error message parameters:
3809 !    lunit, the logical unit number to which messages are printed, and
3810 !    mesflg, the message print flag.
3811 !  this is a modification of the slatec library routine j4save.
3813 !  saved local variables..
3814 !   lunit  = logical unit number for messages.  the default is obtained
3815 !            by a call to iumach (may be machine-dependent).
3816 !   mesflg = print control flag..
3817 !            1 means print all messages (the default).
3818 !            0 means no printing.
3820 !  on input..
3821 !    ipar   = parameter indicator (1 for lunit, 2 for mesflg).
3822 !    ivalue = the value to be set for the parameter, if iset = .true.
3823 !    iset   = logical flag to indicate whether to read or write.
3824 !             if iset = .true., the parameter will be given
3825 !             the value ivalue.  if iset = .false., the parameter
3826 !             will be unchanged, and ivalue is a dummy argument.
3828 !  on return..
3829 !    ixsav = the (old) value of the parameter.
3831 !***see also  xerrwd, xerrwv
3832 !***routines called  iumach
3833 !***revision history  (yymmdd)
3834 !   921118  date written
3835 !   930329  modified prologue to slatec format. (fnf)
3836 !   930915  added iumach call to get default output unit.  (ach)
3837 !   930922  minor cosmetic changes. (fnf)
3838 !   010425  type declaration for iumach added. (ach)
3839 !***end prologue  ixsav
3841 ! subroutines called by ixsav.. none
3842 ! function routine called by ixsav.. iumach
3843 !-----------------------------------------------------------------------
3844 !**end
3845       logical iset
3846       integer ipar, ivalue
3847 !-----------------------------------------------------------------------
3848 ! 27-oct-2005 rce - do not declare functions that are in the module
3849 !     integer iumach, lunit, mesflg
3850       integer         lunit, mesflg
3851 !-----------------------------------------------------------------------
3852 ! the following fortran-77 declaration is to cause the values of the
3853 ! listed (local) variables to be saved between calls to this routine.
3854 !-----------------------------------------------------------------------
3855       save lunit, mesflg
3856       data lunit/-1/, mesflg/1/
3858 !***first executable statement  ixsav
3859       if (ipar .eq. 1) then
3860         if (lunit .eq. -1) lunit = iumach()
3861         ixsav = lunit
3862         if (iset) lunit = ivalue
3863         endif
3865       if (ipar .eq. 2) then
3866         ixsav = mesflg
3867         if (iset) mesflg = ivalue
3868         endif
3870       return
3871 !----------------------- end of function ixsav -------------------------
3872       end function ixsav
3873 !deck iumach
3874       integer function iumach()
3875 !***begin prologue  iumach
3876 !***purpose  provide standard output unit number.
3877 !***category  r1
3878 !***type      integer (iumach-i)
3879 !***keywords  machine constants
3880 !***author  hindmarsh, alan c., (llnl)
3881 !***description
3882 ! *usage:
3883 !        integer  lout, iumach
3884 !        lout = iumach()
3886 ! *function return values:
3887 !     lout : the standard logical unit for fortran output.
3889 !***references  (none)
3890 !***routines called  (none)
3891 !***revision history  (yymmdd)
3892 !   930915  date written
3893 !   930922  made user-callable, and other cosmetic changes. (fnf)
3894 !***end prologue  iumach
3896 !*internal notes:
3897 !  the built-in value of 6 is standard on a wide range of fortran
3898 !  systems.  this may be machine-dependent.
3899 !**end
3900 !***first executable statement  iumach
3901       iumach = 6
3903       return
3904 !----------------------- end of function iumach ------------------------
3905       end function iumach
3906 !deck dumach
3907       double precision function dumach ()
3908 !***begin prologue  dumach
3909 !***purpose  compute the unit roundoff of the machine.
3910 !***category  r1
3911 !***type      double precision (rumach-s, dumach-d)
3912 !***keywords  machine constants
3913 !***author  hindmarsh, alan c., (llnl)
3914 !***description
3915 ! *usage:
3916 !        double precision  a, dumach
3917 !        a = dumach()
3919 ! *function return values:
3920 !     a : the unit roundoff of the machine.
3922 ! *description:
3923 !     the unit roundoff is defined as the smallest positive machine
3924 !     number u such that  1.0 + u .ne. 1.0.  this is computed by dumach
3925 !     in a machine-independent manner.
3927 !***references  (none)
3928 !***routines called  dumsum
3929 !***revision history  (yyyymmdd)
3930 !   19930216  date written
3931 !   19930818  added slatec-format prologue.  (fnf)
3932 !   20030707  added dumsum to force normal storage of comp.  (ach)
3933 !***end prologue  dumach
3935       double precision u, comp
3936 !***first executable statement  dumach
3937       u = 1.0d0
3938  10   u = u*0.5d0
3939       call dumsum(1.0d0, u, comp)
3940       if (comp .ne. 1.0d0) go to 10
3941       dumach = u*2.0d0
3942       return
3943 !----------------------- end of function dumach ------------------------
3944       end function dumach
3945       subroutine dumsum(a,b,c)
3946 !     routine to force normal storing of a + b, for dumach.
3947       double precision a, b, c
3948       c = a + b
3949       return
3950       end subroutine dumsum
3952 !-----------------------------------------------------------------------
3953 !   vode_subs.f - created on 28-jul-2004
3954 !       by downloading following from www.netlib.org
3955 !       1.  daxpy, dcopy, ddot, dnrm2, dscal, idamax from blas
3956 !       2.  dgbfa, dbgsl, dgefa, dgesl from linpack
3958 !   27-oct-2005 rce - change '1' dimensions in subr dgefa & dgesl
3959 !-----------------------------------------------------------------------
3962 !-----------------------------------------------------------------------
3963       subroutine daxpy(n,da,dx,incx,dy,incy)
3965 !     constant times a vector plus a vector.
3966 !     uses unrolled loops for increments equal to one.
3967 !     jack dongarra, linpack, 3/11/78.
3968 !     modified 12/3/93, array(1) declarations changed to array(*)
3970       double precision dx(*),dy(*),da
3971       integer i,incx,incy,ix,iy,m,mp1,n
3973       if(n.le.0)return
3974       if (da .eq. 0.0d0) return
3975       if(incx.eq.1.and.incy.eq.1)go to 20
3977 !        code for unequal increments or equal increments
3978 !          not equal to 1
3980       ix = 1
3981       iy = 1
3982       if(incx.lt.0)ix = (-n+1)*incx + 1
3983       if(incy.lt.0)iy = (-n+1)*incy + 1
3984       do 10 i = 1,n
3985         dy(iy) = dy(iy) + da*dx(ix)
3986         ix = ix + incx
3987         iy = iy + incy
3988    10 continue
3989       return
3991 !        code for both increments equal to 1
3994 !        clean-up loop
3996    20 m = mod(n,4)
3997       if( m .eq. 0 ) go to 40
3998       do 30 i = 1,m
3999         dy(i) = dy(i) + da*dx(i)
4000    30 continue
4001       if( n .lt. 4 ) return
4002    40 mp1 = m + 1
4003       do 50 i = mp1,n,4
4004         dy(i) = dy(i) + da*dx(i)
4005         dy(i + 1) = dy(i + 1) + da*dx(i + 1)
4006         dy(i + 2) = dy(i + 2) + da*dx(i + 2)
4007         dy(i + 3) = dy(i + 3) + da*dx(i + 3)
4008    50 continue
4009       return
4010       end subroutine daxpy
4013 !-----------------------------------------------------------------------
4014       subroutine  dcopy(n,dx,incx,dy,incy)
4016 !     copies a vector, x, to a vector, y.
4017 !     uses unrolled loops for increments equal to one.
4018 !     jack dongarra, linpack, 3/11/78.
4019 !     modified 12/3/93, array(1) declarations changed to array(*)
4021       double precision dx(*),dy(*)
4022       integer i,incx,incy,ix,iy,m,mp1,n
4024       if(n.le.0)return
4025       if(incx.eq.1.and.incy.eq.1)go to 20
4027 !        code for unequal increments or equal increments
4028 !          not equal to 1
4030       ix = 1
4031       iy = 1
4032       if(incx.lt.0)ix = (-n+1)*incx + 1
4033       if(incy.lt.0)iy = (-n+1)*incy + 1
4034       do 10 i = 1,n
4035         dy(iy) = dx(ix)
4036         ix = ix + incx
4037         iy = iy + incy
4038    10 continue
4039       return
4041 !        code for both increments equal to 1
4044 !        clean-up loop
4046    20 m = mod(n,7)
4047       if( m .eq. 0 ) go to 40
4048       do 30 i = 1,m
4049         dy(i) = dx(i)
4050    30 continue
4051       if( n .lt. 7 ) return
4052    40 mp1 = m + 1
4053       do 50 i = mp1,n,7
4054         dy(i) = dx(i)
4055         dy(i + 1) = dx(i + 1)
4056         dy(i + 2) = dx(i + 2)
4057         dy(i + 3) = dx(i + 3)
4058         dy(i + 4) = dx(i + 4)
4059         dy(i + 5) = dx(i + 5)
4060         dy(i + 6) = dx(i + 6)
4061    50 continue
4062       return
4063       end subroutine  dcopy
4066       double precision function ddot(n,dx,incx,dy,incy)
4068 !     forms the dot product of two vectors.
4069 !     uses unrolled loops for increments equal to one.
4070 !     jack dongarra, linpack, 3/11/78.
4071 !     modified 12/3/93, array(1) declarations changed to array(*)
4073       double precision dx(*),dy(*),dtemp
4074       integer i,incx,incy,ix,iy,m,mp1,n
4076       ddot = 0.0d0
4077       dtemp = 0.0d0
4078       if(n.le.0)return
4079       if(incx.eq.1.and.incy.eq.1)go to 20
4081 !        code for unequal increments or equal increments
4082 !          not equal to 1
4084       ix = 1
4085       iy = 1
4086       if(incx.lt.0)ix = (-n+1)*incx + 1
4087       if(incy.lt.0)iy = (-n+1)*incy + 1
4088       do 10 i = 1,n
4089         dtemp = dtemp + dx(ix)*dy(iy)
4090         ix = ix + incx
4091         iy = iy + incy
4092    10 continue
4093       ddot = dtemp
4094       return
4096 !        code for both increments equal to 1
4099 !        clean-up loop
4101    20 m = mod(n,5)
4102       if( m .eq. 0 ) go to 40
4103       do 30 i = 1,m
4104         dtemp = dtemp + dx(i)*dy(i)
4105    30 continue
4106       if( n .lt. 5 ) go to 60
4107    40 mp1 = m + 1
4108       do 50 i = mp1,n,5
4109         dtemp = dtemp + dx(i)*dy(i) + dx(i + 1)*dy(i + 1) +   &
4110          dx(i + 2)*dy(i + 2) + dx(i + 3)*dy(i + 3) + dx(i + 4)*dy(i + 4)
4111    50 continue
4112    60 ddot = dtemp
4113       return
4114       end function ddot
4117 !-----------------------------------------------------------------------
4118       double precision function dnrm2 ( n, x, incx )
4119 !     .. scalar arguments ..
4120       integer                           incx, n
4121 !     .. array arguments ..
4122       double precision                  x( * )
4123 !     ..
4125 !  dnrm2 returns the euclidean norm of a vector via the function
4126 !  name, so that
4128 !     dnrm2 := sqrt( x'*x )
4132 !  -- this version written on 25-october-1982.
4133 !     modified on 14-october-1993 to inline the call to dlassq.
4134 !     sven hammarling, nag ltd.
4137 !     .. parameters ..
4138       double precision      one         , zero
4139       parameter           ( one = 1.0d+0, zero = 0.0d+0 )
4140 !     .. local scalars ..
4141       integer               ix
4142       double precision      absxi, norm, scale, ssq
4143 !     .. intrinsic functions ..
4144       intrinsic             abs, sqrt
4145 !     ..
4146 !     .. executable statements ..
4147       if( n.lt.1 .or. incx.lt.1 )then
4148          norm  = zero
4149       else if( n.eq.1 )then
4150          norm  = abs( x( 1 ) )
4151       else
4152          scale = zero
4153          ssq   = one
4154 !        the following loop is equivalent to this call to the lapack
4155 !        auxiliary routine:
4156 !        call dlassq( n, x, incx, scale, ssq )
4158          do 10, ix = 1, 1 + ( n - 1 )*incx, incx
4159             if( x( ix ).ne.zero )then
4160                absxi = abs( x( ix ) )
4161                if( scale.lt.absxi )then
4162                   ssq   = one   + ssq*( scale/absxi )**2
4163                   scale = absxi
4164                else
4165                   ssq   = ssq   +     ( absxi/scale )**2
4166                end if
4167             end if
4168    10    continue
4169          norm  = scale * sqrt( ssq )
4170       end if
4172       dnrm2 = norm
4173       return
4175 !     end of dnrm2.
4177       end function dnrm2
4180 !-----------------------------------------------------------------------
4181       subroutine  dscal(n,da,dx,incx)
4183 !     scales a vector by a constant.
4184 !     uses unrolled loops for increment equal to one.
4185 !     jack dongarra, linpack, 3/11/78.
4186 !     modified 3/93 to return if incx .le. 0.
4187 !     modified 12/3/93, array(1) declarations changed to array(*)
4189       double precision da,dx(*)
4190       integer i,incx,m,mp1,n,nincx
4192       if( n.le.0 .or. incx.le.0 )return
4193       if(incx.eq.1)go to 20
4195 !        code for increment not equal to 1
4197       nincx = n*incx
4198       do 10 i = 1,nincx,incx
4199         dx(i) = da*dx(i)
4200    10 continue
4201       return
4203 !        code for increment equal to 1
4206 !        clean-up loop
4208    20 m = mod(n,5)
4209       if( m .eq. 0 ) go to 40
4210       do 30 i = 1,m
4211         dx(i) = da*dx(i)
4212    30 continue
4213       if( n .lt. 5 ) return
4214    40 mp1 = m + 1
4215       do 50 i = mp1,n,5
4216         dx(i) = da*dx(i)
4217         dx(i + 1) = da*dx(i + 1)
4218         dx(i + 2) = da*dx(i + 2)
4219         dx(i + 3) = da*dx(i + 3)
4220         dx(i + 4) = da*dx(i + 4)
4221    50 continue
4222       return
4223       end subroutine  dscal
4226 !-----------------------------------------------------------------------
4227       integer function idamax(n,dx,incx)
4229 !     finds the index of element having max. absolute value.
4230 !     jack dongarra, linpack, 3/11/78.
4231 !     modified 3/93 to return if incx .le. 0.
4232 !     modified 12/3/93, array(1) declarations changed to array(*)
4234       double precision dx(*),dmax
4235       integer i,incx,ix,n
4237       idamax = 0
4238       if( n.lt.1 .or. incx.le.0 ) return
4239       idamax = 1
4240       if(n.eq.1)return
4241       if(incx.eq.1)go to 20
4243 !        code for increment not equal to 1
4245       ix = 1
4246       dmax = dabs(dx(1))
4247       ix = ix + incx
4248       do 10 i = 2,n
4249          if(dabs(dx(ix)).le.dmax) go to 5
4250          idamax = i
4251          dmax = dabs(dx(ix))
4252     5    ix = ix + incx
4253    10 continue
4254       return
4256 !        code for increment equal to 1
4258    20 dmax = dabs(dx(1))
4259       do 30 i = 2,n
4260          if(dabs(dx(i)).le.dmax) go to 30
4261          idamax = i
4262          dmax = dabs(dx(i))
4263    30 continue
4264       return
4265       end function idamax
4268 !-----------------------------------------------------------------------
4269       subroutine dgbfa(abd,lda,n,ml,mu,ipvt,info)
4270       integer lda,n,ml,mu,ipvt(1),info
4271       double precision abd(lda,1)
4273 !     dgbfa factors a double precision band matrix by elimination.
4275 !     dgbfa is usually called by dgbco, but it can be called
4276 !     directly with a saving in time if  rcond  is not needed.
4278 !     on entry
4280 !        abd     double precision(lda, n)
4281 !                contains the matrix in band storage.  the columns
4282 !                of the matrix are stored in the columns of  abd  and
4283 !                the diagonals of the matrix are stored in rows
4284 !                ml+1 through 2*ml+mu+1 of  abd .
4285 !                see the comments below for details.
4287 !        lda     integer
4288 !                the leading dimension of the array  abd .
4289 !                lda must be .ge. 2*ml + mu + 1 .
4291 !        n       integer
4292 !                the order of the original matrix.
4294 !        ml      integer
4295 !                number of diagonals below the main diagonal.
4296 !                0 .le. ml .lt. n .
4298 !        mu      integer
4299 !                number of diagonals above the main diagonal.
4300 !                0 .le. mu .lt. n .
4301 !                more efficient if  ml .le. mu .
4302 !     on return
4304 !        abd     an upper triangular matrix in band storage and
4305 !                the multipliers which were used to obtain it.
4306 !                the factorization can be written  a = l*u  where
4307 !                l  is a product of permutation and unit lower
4308 !                triangular matrices and  u  is upper triangular.
4310 !        ipvt    integer(n)
4311 !                an integer vector of pivot indices.
4313 !        info    integer
4314 !                = 0  normal value.
4315 !                = k  if  u(k,k) .eq. 0.0 .  this is not an error
4316 !                     condition for this subroutine, but it does
4317 !                     indicate that dgbsl will divide by zero if
4318 !                     called.  use  rcond  in dgbco for a reliable
4319 !                     indication of singularity.
4321 !     band storage
4323 !           if  a  is a band matrix, the following program segment
4324 !           will set up the input.
4326 !                   ml = (band width below the diagonal)
4327 !                   mu = (band width above the diagonal)
4328 !                   m = ml + mu + 1
4329 !                   do 20 j = 1, n
4330 !                      i1 = max0(1, j-mu)
4331 !                      i2 = min0(n, j+ml)
4332 !                      do 10 i = i1, i2
4333 !                         k = i - j + m
4334 !                         abd(k,j) = a(i,j)
4335 !                10    continue
4336 !                20 continue
4338 !           this uses rows  ml+1  through  2*ml+mu+1  of  abd .
4339 !           in addition, the first  ml  rows in  abd  are used for
4340 !           elements generated during the triangularization.
4341 !           the total number of rows needed in  abd  is  2*ml+mu+1 .
4342 !           the  ml+mu by ml+mu  upper left triangle and the
4343 !           ml by ml  lower right triangle are not referenced.
4345 !     linpack. this version dated 08/14/78 .
4346 !     cleve moler, university of new mexico, argonne national lab.
4348 !     subroutines and functions
4350 !     blas daxpy,dscal,idamax
4351 !     fortran max0,min0
4353 !     internal variables
4355       double precision t
4356 ! 27-oct-2005 rce - do not declare functions that are in the module
4357 !     integer i,idamax,i0,j,ju,jz,j0,j1,k,kp1,l,lm,m,mm,nm1
4358       integer i,       i0,j,ju,jz,j0,j1,k,kp1,l,lm,m,mm,nm1
4361       m = ml + mu + 1
4362       info = 0
4364 !     zero initial fill-in columns
4366       j0 = mu + 2
4367       j1 = min0(n,m) - 1
4368       if (j1 .lt. j0) go to 30
4369       do 20 jz = j0, j1
4370          i0 = m + 1 - jz
4371          do 10 i = i0, ml
4372             abd(i,jz) = 0.0d0
4373    10    continue
4374    20 continue
4375    30 continue
4376       jz = j1
4377       ju = 0
4379 !     gaussian elimination with partial pivoting
4381       nm1 = n - 1
4382       if (nm1 .lt. 1) go to 130
4383       do 120 k = 1, nm1
4384          kp1 = k + 1
4386 !        zero next fill-in column
4388          jz = jz + 1
4389          if (jz .gt. n) go to 50
4390          if (ml .lt. 1) go to 50
4391             do 40 i = 1, ml
4392                abd(i,jz) = 0.0d0
4393    40       continue
4394    50    continue
4396 !        find l = pivot index
4398          lm = min0(ml,n-k)
4399          l = idamax(lm+1,abd(m,k),1) + m - 1
4400          ipvt(k) = l + k - m
4402 !        zero pivot implies this column already triangularized
4404          if (abd(l,k) .eq. 0.0d0) go to 100
4406 !           interchange if necessary
4408             if (l .eq. m) go to 60
4409                t = abd(l,k)
4410                abd(l,k) = abd(m,k)
4411                abd(m,k) = t
4412    60       continue
4414 !           compute multipliers
4416             t = -1.0d0/abd(m,k)
4417             call dscal(lm,t,abd(m+1,k),1)
4419 !           row elimination with column indexing
4421             ju = min0(max0(ju,mu+ipvt(k)),n)
4422             mm = m
4423             if (ju .lt. kp1) go to 90
4424             do 80 j = kp1, ju
4425                l = l - 1
4426                mm = mm - 1
4427                t = abd(l,j)
4428                if (l .eq. mm) go to 70
4429                   abd(l,j) = abd(mm,j)
4430                   abd(mm,j) = t
4431    70          continue
4432                call daxpy(lm,t,abd(m+1,k),1,abd(mm+1,j),1)
4433    80       continue
4434    90       continue
4435          go to 110
4436   100    continue
4437             info = k
4438   110    continue
4439   120 continue
4440   130 continue
4441       ipvt(n) = n
4442       if (abd(m,n) .eq. 0.0d0) info = n
4443       return
4444       end subroutine dgbfa
4447 !-----------------------------------------------------------------------
4448       subroutine dgbsl(abd,lda,n,ml,mu,ipvt,b,job)
4449       integer lda,n,ml,mu,ipvt(1),job
4450       double precision abd(lda,1),b(1)
4452 !     dgbsl solves the double precision band system
4453 !     a * x = b  or  trans(a) * x = b
4454 !     using the factors computed by dgbco or dgbfa.
4456 !     on entry
4458 !        abd     double precision(lda, n)
4459 !                the output from dgbco or dgbfa.
4461 !        lda     integer
4462 !                the leading dimension of the array  abd .
4464 !        n       integer
4465 !                the order of the original matrix.
4467 !        ml      integer
4468 !                number of diagonals below the main diagonal.
4470 !        mu      integer
4471 !                number of diagonals above the main diagonal.
4473 !        ipvt    integer(n)
4474 !                the pivot vector from dgbco or dgbfa.
4476 !        b       double precision(n)
4477 !                the right hand side vector.
4479 !        job     integer
4480 !                = 0         to solve  a*x = b ,
4481 !                = nonzero   to solve  trans(a)*x = b , where
4482 !                            trans(a)  is the transpose.
4484 !     on return
4486 !        b       the solution vector  x .
4488 !     error condition
4490 !        a division by zero will occur if the input factor contains a
4491 !        zero on the diagonal.  technically this indicates singularity
4492 !        but it is often caused by improper arguments or improper
4493 !        setting of lda .  it will not occur if the subroutines are
4494 !        called correctly and if dgbco has set rcond .gt. 0.0
4495 !        or dgbfa has set info .eq. 0 .
4497 !     to compute  inverse(a) * c  where  c  is a matrix
4498 !     with  p  columns
4499 !           call dgbco(abd,lda,n,ml,mu,ipvt,rcond,z)
4500 !           if (rcond is too small) go to ...
4501 !           do 10 j = 1, p
4502 !              call dgbsl(abd,lda,n,ml,mu,ipvt,c(1,j),0)
4503 !        10 continue
4505 !     linpack. this version dated 08/14/78 .
4506 !     cleve moler, university of new mexico, argonne national lab.
4508 !     subroutines and functions
4510 !     blas daxpy,ddot
4511 !     fortran min0
4513 !     internal variables
4515 ! 27-oct-2005 rce - do not declare functions that are in the module
4516 !     double precision ddot,t
4517       double precision      t
4518       integer k,kb,l,la,lb,lm,m,nm1
4520       m = mu + ml + 1
4521       nm1 = n - 1
4522       if (job .ne. 0) go to 50
4524 !        job = 0 , solve  a * x = b
4525 !        first solve l*y = b
4527          if (ml .eq. 0) go to 30
4528          if (nm1 .lt. 1) go to 30
4529             do 20 k = 1, nm1
4530                lm = min0(ml,n-k)
4531                l = ipvt(k)
4532                t = b(l)
4533                if (l .eq. k) go to 10
4534                   b(l) = b(k)
4535                   b(k) = t
4536    10          continue
4537                call daxpy(lm,t,abd(m+1,k),1,b(k+1),1)
4538    20       continue
4539    30    continue
4541 !        now solve  u*x = y
4543          do 40 kb = 1, n
4544             k = n + 1 - kb
4545             b(k) = b(k)/abd(m,k)
4546             lm = min0(k,m) - 1
4547             la = m - lm
4548             lb = k - lm
4549             t = -b(k)
4550             call daxpy(lm,t,abd(la,k),1,b(lb),1)
4551    40    continue
4552       go to 100
4553    50 continue
4555 !        job = nonzero, solve  trans(a) * x = b
4556 !        first solve  trans(u)*y = b
4558          do 60 k = 1, n
4559             lm = min0(k,m) - 1
4560             la = m - lm
4561             lb = k - lm
4562             t = ddot(lm,abd(la,k),1,b(lb),1)
4563             b(k) = (b(k) - t)/abd(m,k)
4564    60    continue
4566 !        now solve trans(l)*x = y
4568          if (ml .eq. 0) go to 90
4569          if (nm1 .lt. 1) go to 90
4570             do 80 kb = 1, nm1
4571                k = n - kb
4572                lm = min0(ml,n-k)
4573                b(k) = b(k) + ddot(lm,abd(m+1,k),1,b(k+1),1)
4574                l = ipvt(k)
4575                if (l .eq. k) go to 70
4576                   t = b(l)
4577                   b(l) = b(k)
4578                   b(k) = t
4579    70          continue
4580    80       continue
4581    90    continue
4582   100 continue
4583       return
4584       end subroutine dgbsl
4587 !-----------------------------------------------------------------------
4588       subroutine dgefa(a,lda,n,ipvt,info)
4589 ! 27-oct-2005 rce - change '1' dimensions
4590 !     integer lda,n,ipvt(1),info
4591       integer lda,n,ipvt(n),info
4592 !     double precision a(lda,1)
4593       double precision a(lda,n)
4595 !     dgefa factors a double precision matrix by gaussian elimination.
4597 !     dgefa is usually called by dgeco, but it can be called
4598 !     directly with a saving in time if  rcond  is not needed.
4599 !     (time for dgeco) = (1 + 9/n)*(time for dgefa) .
4601 !     on entry
4603 !        a       double precision(lda, n)
4604 !                the matrix to be factored.
4606 !        lda     integer
4607 !                the leading dimension of the array  a .
4609 !        n       integer
4610 !                the order of the matrix  a .
4612 !     on return
4614 !        a       an upper triangular matrix and the multipliers
4615 !                which were used to obtain it.
4616 !                the factorization can be written  a = l*u  where
4617 !                l  is a product of permutation and unit lower
4618 !                triangular matrices and  u  is upper triangular.
4620 !        ipvt    integer(n)
4621 !                an integer vector of pivot indices.
4623 !        info    integer
4624 !                = 0  normal value.
4625 !                = k  if  u(k,k) .eq. 0.0 .  this is not an error
4626 !                     condition for this subroutine, but it does
4627 !                     indicate that dgesl or dgedi will divide by zero
4628 !                     if called.  use  rcond  in dgeco for a reliable
4629 !                     indication of singularity.
4631 !     linpack. this version dated 08/14/78 .
4632 !     cleve moler, university of new mexico, argonne national lab.
4634 !     subroutines and functions
4636 !     blas daxpy,dscal,idamax
4638 !     internal variables
4640       double precision t
4641 ! 27-oct-2005 rce - do not declare functions that are in the module
4642 !     integer idamax,j,k,kp1,l,nm1
4643       integer        j,k,kp1,l,nm1
4646 !     gaussian elimination with partial pivoting
4648       info = 0
4649       nm1 = n - 1
4650       if (nm1 .lt. 1) go to 70
4651       do 60 k = 1, nm1
4652          kp1 = k + 1
4654 !        find l = pivot index
4656          l = idamax(n-k+1,a(k,k),1) + k - 1
4657          ipvt(k) = l
4659 !        zero pivot implies this column already triangularized
4661          if (a(l,k) .eq. 0.0d0) go to 40
4663 !           interchange if necessary
4665             if (l .eq. k) go to 10
4666                t = a(l,k)
4667                a(l,k) = a(k,k)
4668                a(k,k) = t
4669    10       continue
4671 !           compute multipliers
4673             t = -1.0d0/a(k,k)
4674             call dscal(n-k,t,a(k+1,k),1)
4676 !           row elimination with column indexing
4678             do 30 j = kp1, n
4679                t = a(l,j)
4680                if (l .eq. k) go to 20
4681                   a(l,j) = a(k,j)
4682                   a(k,j) = t
4683    20          continue
4684                call daxpy(n-k,t,a(k+1,k),1,a(k+1,j),1)
4685    30       continue
4686          go to 50
4687    40    continue
4688             info = k
4689    50    continue
4690    60 continue
4691    70 continue
4692       ipvt(n) = n
4693       if (a(n,n) .eq. 0.0d0) info = n
4694       return
4695       end subroutine dgefa
4698 !-----------------------------------------------------------------------
4699       subroutine dgesl(a,lda,n,ipvt,b,job)
4700 ! 27-oct-2005 rce - change '1' dimensions
4701 !     integer lda,n,ipvt(1),job
4702       integer lda,n,ipvt(n),job
4703 !     double precision a(lda,1),b(1)
4704       double precision a(lda,n),b(n)
4706 !     dgesl solves the double precision system
4707 !     a * x = b  or  trans(a) * x = b
4708 !     using the factors computed by dgeco or dgefa.
4710 !     on entry
4712 !        a       double precision(lda, n)
4713 !                the output from dgeco or dgefa.
4715 !        lda     integer
4716 !                the leading dimension of the array  a .
4718 !        n       integer
4719 !                the order of the matrix  a .
4721 !        ipvt    integer(n)
4722 !                the pivot vector from dgeco or dgefa.
4724 !        b       double precision(n)
4725 !                the right hand side vector.
4727 !        job     integer
4728 !                = 0         to solve  a*x = b ,
4729 !                = nonzero   to solve  trans(a)*x = b  where
4730 !                            trans(a)  is the transpose.
4732 !     on return
4734 !        b       the solution vector  x .
4736 !     error condition
4738 !        a division by zero will occur if the input factor contains a
4739 !        zero on the diagonal.  technically this indicates singularity
4740 !        but it is often caused by improper arguments or improper
4741 !        setting of lda .  it will not occur if the subroutines are
4742 !        called correctly and if dgeco has set rcond .gt. 0.0
4743 !        or dgefa has set info .eq. 0 .
4745 !     to compute  inverse(a) * c  where  c  is a matrix
4746 !     with  p  columns
4747 !           call dgeco(a,lda,n,ipvt,rcond,z)
4748 !           if (rcond is too small) go to ...
4749 !           do 10 j = 1, p
4750 !              call dgesl(a,lda,n,ipvt,c(1,j),0)
4751 !        10 continue
4753 !     linpack. this version dated 08/14/78 .
4754 !     cleve moler, university of new mexico, argonne national lab.
4756 !     subroutines and functions
4758 !     blas daxpy,ddot
4760 !     internal variables
4762 ! 27-oct-2005 rce - do not declare functions that are in the module
4763 !     double precision ddot,t
4764       double precision      t
4765       integer k,kb,l,nm1
4767       nm1 = n - 1
4768       if (job .ne. 0) go to 50
4770 !        job = 0 , solve  a * x = b
4771 !        first solve  l*y = b
4773          if (nm1 .lt. 1) go to 30
4774          do 20 k = 1, nm1
4775             l = ipvt(k)
4776             t = b(l)
4777             if (l .eq. k) go to 10
4778                b(l) = b(k)
4779                b(k) = t
4780    10       continue
4781             call daxpy(n-k,t,a(k+1,k),1,b(k+1),1)
4782    20    continue
4783    30    continue
4785 !        now solve  u*x = y
4787          do 40 kb = 1, n
4788             k = n + 1 - kb
4789             b(k) = b(k)/a(k,k)
4790             t = -b(k)
4791             call daxpy(k-1,t,a(1,k),1,b(1),1)
4792    40    continue
4793       go to 100
4794    50 continue
4796 !        job = nonzero, solve  trans(a) * x = b
4797 !        first solve  trans(u)*y = b
4799          do 60 k = 1, n
4800             t = ddot(k-1,a(1,k),1,b(1),1)
4801             b(k) = (b(k) - t)/a(k,k)
4802    60    continue
4804 !        now solve trans(l)*x = y
4806          if (nm1 .lt. 1) go to 90
4807          do 80 kb = 1, nm1
4808             k = n - kb
4809             b(k) = b(k) + ddot(n-k,a(k+1,k),1,b(k+1),1)
4810             l = ipvt(k)
4811             if (l .eq. k) go to 70
4812                t = b(l)
4813                b(l) = b(k)
4814                b(k) = t
4815    70       continue
4816    80    continue
4817    90    continue
4818   100 continue
4819       return
4820       end subroutine dgesl
4824       end module module_cmu_dvode_solver