This routine manages the solution of the linear system arising from
a chord iteration. it is called if miter /= 0
:
h*rl1
in the diagonal
matrix, and then computes the solution.Type | Intent | Optional | Attributes | Name | ||
---|---|---|---|---|---|---|
class(dvode_t), | intent(inout) | :: | me | |||
real(kind=wp), | intent(inout) | :: | wm(*) |
real work space containing the inverse diagonal matrix if miter = 3 and the lu decomposition of the matrix otherwise. storage of matrix elements starts at wm(3). wm also contains the following matrix-related data: wm(1) = sqrt(uround) (not used here), wm(2) = hrl1, the previous value of h*rl1, used if miter = 3. |
||
integer | :: | iwm(*) |
integer work space containing pivot information, starting at iwm(31), if miter is 1, 2, 4, or 5. iwm also contains band parameters ml = iwm(1) and mu = iwm(2) if miter is 4 or 5. |
|||
real(kind=wp), | intent(inout) | :: | x(*) |
the right-hand side vector on input, and the solution vector on output, of length n. |
||
integer, | intent(out) | :: | iersl |
output flag. iersl = 0 if no trouble occurred. iersl = 1 if a singular matrix arose with miter = 3. |
subroutine dvsol(me,wm,iwm,x,iersl) class(dvode_t),intent(inout) :: me real(wp),intent(inout) :: wm(*) !! real work space containing the inverse diagonal matrix if !! miter = 3 and the lu decomposition of the matrix otherwise. !! storage of matrix elements starts at wm(3). !! wm also contains the following matrix-related data: !! wm(1) = sqrt(uround) (not used here), !! wm(2) = hrl1, the previous value of h*rl1, used if miter = 3. real(wp),intent(inout) :: x(*) !! the right-hand side vector on input, !! and the solution vector !! on output, of length n. integer :: iwm(*) !! integer work space containing pivot information, starting at !! iwm(31), if miter is 1, 2, 4, or 5. iwm also contains band !! parameters ml = iwm(1) and mu = iwm(2) if miter is 4 or 5. integer,intent(out) :: iersl !! output flag. iersl = 0 if no trouble occurred. !! iersl = 1 if a singular matrix arose with miter = 3. integer :: i , meband , ml , mu real(wp) :: di , hrl1 , phrl1 , r real(wp),parameter :: one = 1.0_wp iersl = 0 select case (me%dat%miter) case (3) phrl1 = wm(2) hrl1 = me%dat%h*me%dat%rl1 wm(2) = hrl1 if ( hrl1/=phrl1 ) then r = hrl1/phrl1 do i = 1 , me%dat%n di = one - r*(one-one/wm(i+2)) if ( abs(di)==zero ) then iersl = 1 return end if wm(i+2) = one/di enddo endif do i = 1 , me%dat%n x(i) = wm(i+2)*x(i) enddo case (4,5) ml = iwm(1) mu = iwm(2) meband = 2*ml + mu + 1 call dgbsl(wm(3),meband,me%dat%n,ml,mu,iwm(31),x,0) case default call dgesl(wm(3),me%dat%n,me%dat%n,iwm(31),x,0) end select end subroutine dvsol