325 SUBROUTINE slarrd( RANGE, ORDER, N, VL, VU, IL, IU, GERS,
326 $ RELTOL, D, E, E2, PIVMIN, NSPLIT, ISPLIT,
327 $ M, W, WERR, WL, WU, IBLOCK, INDEXW,
328 $ WORK, IWORK, INFO )
336INTEGER , INFO, IU, M, N, NSPLIT
337 REAL PIVMIN, RELTOL, VL, VU, WL, WU
340 INTEGER IBLOCK( * ), INDEXW( * ),
341 $ ISPLIT( * ), IWORK( * )
342 REAL D( * ), E( * ), E2( * )
349 REAL ZERO, ONE, TWO, HALF, FUDGE
350 PARAMETER ( ZERO = 0.0e0, one = 1.0e0,
351 $ two = 2.0e0, half = one/two,
353 INTEGER ALLRNG, VALRNG, INDRNG
354 PARAMETER ( ALLRNG = 1, valrng = 2, indrng = 3 )
357 LOGICAL NCNVRG, TOOFEW
358 INTEGER I, IB, IBEGIN, IDISCL, IDISCU, IE, IEND, IINFO,
359 $ IM, IN, IOFF, IOUT, IRANGE, ITMAX, ITMP1,
360 $ itmp2, iw, iwoff, j, jblk, jdisc, je, jee, nb,
362 REAL ATOLI, EPS, GL, GU, RTOLI, TMP1, TMP2,
363 $ TNORM, UFLOW, WKILL, WLU, WUL
373 EXTERNAL lsame, ilaenv, slamch
379 INTRINSIC abs, int, log,
max,
min
393 IF( lsame( range,
'A' ) )
THEN
395 ELSE IF( lsame( range,
'V' ) )
THEN
397 ELSE IF( lsame( range,
'I' ) )
THEN
405 IF( irange.LE.0 )
THEN
407 ELSE IF( .NOT.(lsame(order,
'B').OR.lsame(order,
'E')) )
THEN
409 ELSE IF( n.LT.0 )
THEN
411 ELSE IF( irange.EQ.valrng )
THEN
414 ELSE IF( irange.EQ.indrng .AND.
415 $ ( il.LT.1 .OR. il.GT.
max( 1, n ) ) )
THEN
417 ELSE IF( irange.EQ.indrng .AND.
418 $ ( iu.LT.
min( n, il ) .OR. iu.GT.n ) )
THEN
436 IF( irange.EQ.indrng .AND. il.EQ.1 .AND. iu.EQ.n ) irange = 1
440 uflow = slamch(
'U' )
446 IF( (irange.EQ.allrng).OR.
447 $ ((irange.EQ.valrng).AND.(d(1).GT.vl).AND.(d(1).LE.vu)).OR.
448 $ ((irange.EQ.indrng).AND.(il.EQ.1).AND.(iu.EQ.1)) )
THEN
461 nb = ilaenv( 1,
'SSTEBZ',
' ', n, -1, -1, -1 )
468 gl =
min( gl, gers( 2*i - 1))
469 gu =
max( gu, gers(2*i) )
472 tnorm =
max( abs( gl ), abs( gu ) )
473 gl = gl - fudge*tnorm*eps*n - fudge*two*pivmin
474 gu = gu + fudge*tnorm*eps*n + fudge*two*pivmin
487 atoli = fudge*two*uflow + fudge*two*pivmin
489 IF( irange.EQ.indrng )
THEN
494 itmax = int( ( log( tnorm+pivmin )-log( pivmin ) ) /
509 CALL slaebz( 3, itmax, n, 2, 2, nb, atoli, rtoli, pivmin,
510 $ d, e, e2, iwork( 5 ), work( n+1 ), work( n+5 ), iout,
511 $ iwork, w, iblock, iinfo )
512 IF( iinfo .NE. 0 )
THEN
517 IF( iwork( 6 ).EQ.iu )
THEN
534 IF( nwl.LT.0 .OR. nwl.GE.n .OR. nwu.LT.1 .OR. nwu.GT.n )
THEN
539 ELSEIF( irange.EQ.valrng )
THEN
543 ELSEIF( irange.EQ.allrng )
THEN
559 DO 70 jblk = 1, nsplit
562 iend = isplit( jblk )
567 IF( wl.GE.d( ibegin )-pivmin )
569 IF( wu.GE.d( ibegin )-pivmin )
571 IF( irange.EQ.allrng .OR.
572 $ ( wl.LT.d( ibegin )-pivmin
573 $ .AND. wu.GE. d( ibegin )-pivmin ) )
THEN
637 DO 40 j = ibegin, iend
638 gl =
min( gl, gers( 2*j - 1))
639 gu =
max( gu, gers(2*j) )
647 gl = gl - fudge*tnorm*eps*in - fudge*pivmin
648 gu = gu + fudge*tnorm*eps*in + fudge*pivmin
650 IF( irange.GT.1 )
THEN
667 CALL slaebz( 1, 0, in, in, 1, nb, atoli, rtoli, pivmin,
668 $ d( ibegin ), e( ibegin ), e2( ibegin ),
669 $ idumma, work( n+1 ), work( n
670 $ iwork, w( m+1 ), iblock( m+1 ), iinfo )
671 IF( iinfo .NE. 0 )
THEN
676 nwl = nwl + iwork( 1 )
677 nwu = nwu + iwork( in+1 )
678 iwoff = m - iwork( 1 )
681 itmax = int( ( log( gu-gl+pivmin )-log( pivmin ) ) /
683 CALL slaebz( 2, itmax, in, in, 1, nb, atoli, rtoli, pivmin,
684 $ d( ibegin ), e( ibegin ), e2( ibegin ),
685 $ idumma, work( n+1 ), work( n+2*in+1 ), iout,
686 $ iwork, w( m+1 ), iblock( m+1 ), iinfo )
687 IF( iinfo .NE. 0 )
THEN
697 tmp1 = half*( work( j+n )+work( j+in+n ) )
699 tmp2 = half*abs( work( j+n )-work( j+in+n ) )
700 IF( j.GT.iout-iinfo )
THEN
707 DO 50 je = iwork( j ) + 1 + iwoff,
708 $ iwork( j+in ) + iwoff
711 indexw( je ) = je - iwoff
722 IF( irange.EQ.indrng )
THEN
723 idiscl = il - 1 - nwl
726 IF( idiscl.GT.0 )
THEN
731 IF( w( je ).LE.wlu .AND. idiscl.GT.0 )
THEN
736 werr( im ) = werr( je )
737 indexw( im ) = indexw( je )
738 iblock( im ) = iblock( je )
743 IF( idiscu.GT.0 )
THEN
748 IF( w( je ).GE.wul .AND. idiscu.GT.0 )
THEN
753 werr( im ) = werr( je )
754 indexw( im ) = indexw( je )
755 iblock( im ) = iblock( je )
762 werr( jee ) = werr( je )
763 indexw( jee ) = indexw( je )
764 iblock( jee ) = iblock( je )
769 IF( idiscl.GT.0 .OR. idiscu.GT.0 )
THEN
776 IF( idiscl.GT.0 )
THEN
778 DO 100 jdisc = 1, idiscl
781 IF( iblock( je ).NE.0 .AND.
782 $ ( w( je ).LT.wkill .OR. iw.EQ.0 ) )
THEN
790 IF( idiscu.GT.0 )
THEN
792 DO 120 jdisc = 1, idiscu
795 IF( iblock( je ).NE.0 .AND.
796 $ ( w( je ).GE.wkill .OR. iw.EQ.0 ) )
THEN
807 IF( iblock( je ).NE.0 )
THEN
810 werr( im ) = werr( je )
811 indexw( im ) = indexw( je )
812 iblock( im ) = iblock( je )
817 IF( idiscl.LT.0 .OR. idiscu.LT.0 )
THEN
822 IF(( irange.EQ.allrng .AND. m.NE.n ).OR.
823 $ ( irange.EQ.indrng .AND. m.NE.iu-il+1 ) )
THEN
831 IF( lsame(order,
'E') .AND. nsplit.GT.1 )
THEN
836 IF( w( j ).LT.tmp1 )
THEN
846 werr( ie ) = werr( je )
847 iblock( ie ) = iblock( je )
848 indexw( ie ) = indexw( je )
subroutine slarrd(range, order, n, vl, vu, il, iu, gers, reltol, d, e, e2, pivmin, nsplit, isplit, m, w, werr, wl, wu, iblock, indexw, work, iwork, info)
SLARRD computes the eigenvalues of a symmetric tridiagonal matrix to suitable accuracy.