353
354
355
356
357
358 IMPLICIT NONE
359
360 INTEGER INFO, LDA, LDV, LWORK, LRWORK, M, MV, N
361 CHARACTER*1 JOBA, JOBU, JOBV
362
363
364 COMPLEX A( LDA, * ), V( LDV, * ), CWORK( LWORK )
365 REAL RWORK( LRWORK ), SVA( N )
366
367
368
369
370
371 REAL ZERO, HALF, ONE
372 parameter( zero = 0.0e0, half = 0.5e0, one = 1.0e0)
373 COMPLEX CZERO, CONE
374 parameter( czero = (0.0e0, 0.0e0), cone = (1.0e0, 0.0e0) )
375 INTEGER NSWEEP
376 parameter( nsweep = 30 )
377
378
379 COMPLEX AAPQ, OMPQ
380 REAL AAPP, AAPP0, AAPQ1, AAQQ, APOAQ, AQOAP, BIG,
381 $ BIGTHETA, CS, CTOL, EPSLN, MXAAPQ,
382 $ MXSINJ, ROOTBIG, ROOTEPS, ROOTSFMIN, ROOTTOL,
383 $ SKL, SFMIN, SMALL, SN, T, TEMP1, THETA, THSIGN, TOL
384 INTEGER BLSKIP, EMPTSW, i, ibr, IERR, igl, IJBLSK, ir1,
385 $ ISWROT, jbc, jgl, KBL, LKAHEAD, MVL, N2, N34,
386 $ N4, NBL, NOTROT, p, PSKIPPED, q, ROWSKIP, SWBAND,
387 $ MINMN, LWMIN, LRWMIN
388 LOGICAL APPLV, GOSCALE, LOWER, LQUERY, LSVEC, NOSCALE, ROTOK,
389 $ RSVEC, UCTOL, UPPER
390
391
392
393 INTRINSIC abs, max, min, conjg, real, sign, sqrt
394
395
396
397
398 REAL SCNRM2
399 COMPLEX CDOTC
401 INTEGER ISAMAX
403
404 REAL SLAMCH, SROUNDUP_LWORK
406 LOGICAL LSAME
408
409
410
411
413
417
418
419
420
421
422 lsvec =
lsame( jobu,
'U' ) .OR.
lsame( jobu,
'F' )
423 uctol =
lsame( jobu,
'C' )
424 rsvec =
lsame( jobv,
'V' ) .OR.
lsame( jobv,
'J' )
425 applv =
lsame( jobv,
'A' )
426 upper =
lsame( joba,
'U' )
427 lower =
lsame( joba,
'L' )
428
429 minmn = min( m, n )
430 IF( minmn.EQ.0 ) THEN
431 lwmin = 1
432 lrwmin = 1
433 ELSE
434 lwmin = m + n
435 lrwmin = max( 6, n )
436 END IF
437
438 lquery = ( lwork.EQ.-1 ) .OR. ( lrwork.EQ.-1 )
439 IF( .NOT.( upper .OR. lower .OR.
lsame( joba,
'G' ) ) )
THEN
440 info = -1
441 ELSE IF( .NOT.( lsvec .OR.
442 $ uctol .OR.
443 $
lsame( jobu,
'N' ) ) )
THEN
444 info = -2
445 ELSE IF( .NOT.( rsvec .OR.
446 $ applv .OR.
447 $
lsame( jobv,
'N' ) ) )
THEN
448 info = -3
449 ELSE IF( m.LT.0 ) THEN
450 info = -4
451 ELSE IF( ( n.LT.0 ) .OR. ( n.GT.m ) ) THEN
452 info = -5
453 ELSE IF( lda.LT.m ) THEN
454 info = -7
455 ELSE IF( mv.LT.0 ) THEN
456 info = -9
457 ELSE IF( ( rsvec .AND. ( ldv.LT.n ) ) .OR.
458 $ ( applv .AND. ( ldv.LT.mv ) ) ) THEN
459 info = -11
460 ELSE IF( uctol .AND. ( rwork( 1 ).LE.one ) ) THEN
461 info = -12
462 ELSE IF( lwork.LT.lwmin .AND. ( .NOT.lquery ) ) THEN
463 info = -13
464 ELSE IF( lrwork.LT.lrwmin .AND. ( .NOT.lquery ) ) THEN
465 info = -15
466 ELSE
467 info = 0
468 END IF
469
470
471 IF( info.NE.0 ) THEN
472 CALL xerbla(
'CGESVJ', -info )
473 RETURN
474 ELSE IF( lquery ) THEN
477 RETURN
478 END IF
479
480
481
482 IF( minmn.EQ.0 ) RETURN
483
484
485
486
487
488
489
490
491 IF( uctol ) THEN
492
493 ctol = rwork( 1 )
494 ELSE
495
496 IF( lsvec .OR. rsvec .OR. applv ) THEN
497 ctol = sqrt( real( m ) )
498 ELSE
499 ctol = real( m )
500 END IF
501 END IF
502
503
504
505 epsln =
slamch(
'Epsilon' )
506 rooteps = sqrt( epsln )
507 sfmin =
slamch(
'SafeMinimum' )
508 rootsfmin = sqrt( sfmin )
509 small = sfmin / epsln
510
511 big = one / sfmin
512 rootbig = one / rootsfmin
513
514 bigtheta = one / rooteps
515
516 tol = ctol*epsln
517 roottol = sqrt( tol )
518
519 IF( real( m )*epsln.GE.one ) THEN
520 info = -4
521 CALL xerbla(
'CGESVJ', -info )
522 RETURN
523 END IF
524
525
526
527 IF( rsvec ) THEN
528 mvl = n
529 CALL claset(
'A', mvl, n, czero, cone, v, ldv )
530 ELSE IF( applv ) THEN
531 mvl = mv
532 END IF
533 rsvec = rsvec .OR. applv
534
535
536
537
538
539
540
541
542
543
544 skl = one / sqrt( real( m )*real( n ) )
545 noscale = .true.
546 goscale = .true.
547
548 IF( lower ) THEN
549
550 DO 1874 p = 1, n
551 aapp = zero
552 aaqq = one
553 CALL classq( m-p+1, a( p, p ), 1, aapp, aaqq )
554 IF( aapp.GT.big ) THEN
555 info = -6
556 CALL xerbla(
'CGESVJ', -info )
557 RETURN
558 END IF
559 aaqq = sqrt( aaqq )
560 IF( ( aapp.LT.( big / aaqq ) ) .AND. noscale ) THEN
561 sva( p ) = aapp*aaqq
562 ELSE
563 noscale = .false.
564 sva( p ) = aapp*( aaqq*skl )
565 IF( goscale ) THEN
566 goscale = .false.
567 DO 1873 q = 1, p - 1
568 sva( q ) = sva( q )*skl
569 1873 CONTINUE
570 END IF
571 END IF
572 1874 CONTINUE
573 ELSE IF( upper ) THEN
574
575 DO 2874 p = 1, n
576 aapp = zero
577 aaqq = one
578 CALL classq( p, a( 1, p ), 1, aapp, aaqq )
579 IF( aapp.GT.big ) THEN
580 info = -6
581 CALL xerbla(
'CGESVJ', -info )
582 RETURN
583 END IF
584 aaqq = sqrt( aaqq )
585 IF( ( aapp.LT.( big / aaqq ) ) .AND. noscale ) THEN
586 sva( p ) = aapp*aaqq
587 ELSE
588 noscale = .false.
589 sva( p ) = aapp*( aaqq*skl )
590 IF( goscale ) THEN
591 goscale = .false.
592 DO 2873 q = 1, p - 1
593 sva( q ) = sva( q )*skl
594 2873 CONTINUE
595 END IF
596 END IF
597 2874 CONTINUE
598 ELSE
599
600 DO 3874 p = 1, n
601 aapp = zero
602 aaqq = one
603 CALL classq( m, a( 1, p ), 1, aapp, aaqq )
604 IF( aapp.GT.big ) THEN
605 info = -6
606 CALL xerbla(
'CGESVJ', -info )
607 RETURN
608 END IF
609 aaqq = sqrt( aaqq )
610 IF( ( aapp.LT.( big / aaqq ) ) .AND. noscale ) THEN
611 sva( p ) = aapp*aaqq
612 ELSE
613 noscale = .false.
614 sva( p ) = aapp*( aaqq*skl )
615 IF( goscale ) THEN
616 goscale = .false.
617 DO 3873 q = 1, p - 1
618 sva( q ) = sva( q )*skl
619 3873 CONTINUE
620 END IF
621 END IF
622 3874 CONTINUE
623 END IF
624
625 IF( noscale )skl = one
626
627
628
629
630
631 aapp = zero
632 aaqq = big
633 DO 4781 p = 1, n
634 IF( sva( p ).NE.zero )aaqq = min( aaqq, sva( p ) )
635 aapp = max( aapp, sva( p ) )
636 4781 CONTINUE
637
638
639
640 IF( aapp.EQ.zero ) THEN
641 IF( lsvec )
CALL claset(
'G', m, n, czero, cone, a, lda )
642 rwork( 1 ) = one
643 rwork( 2 ) = zero
644 rwork( 3 ) = zero
645 rwork( 4 ) = zero
646 rwork( 5 ) = zero
647 rwork( 6 ) = zero
648 RETURN
649 END IF
650
651
652
653 IF( n.EQ.1 ) THEN
654 IF( lsvec )
CALL clascl(
'G', 0, 0, sva( 1 ), skl, m, 1,
655 $ a( 1, 1 ), lda, ierr )
656 rwork( 1 ) = one / skl
657 IF( sva( 1 ).GE.sfmin ) THEN
658 rwork( 2 ) = one
659 ELSE
660 rwork( 2 ) = zero
661 END IF
662 rwork( 3 ) = zero
663 rwork( 4 ) = zero
664 rwork( 5 ) = zero
665 rwork( 6 ) = zero
666 RETURN
667 END IF
668
669
670
671
672 sn = sqrt( sfmin / epsln )
673 temp1 = sqrt( big / real( n ) )
674 IF( ( aapp.LE.sn ) .OR. ( aaqq.GE.temp1 ) .OR.
675 $ ( ( sn.LE.aaqq ) .AND. ( aapp.LE.temp1 ) ) ) THEN
676 temp1 = min( big, temp1 / aapp )
677
678
679 ELSE IF( ( aaqq.LE.sn ) .AND. ( aapp.LE.temp1 ) ) THEN
680 temp1 = min( sn / aaqq, big / ( aapp*sqrt( real( n ) ) ) )
681
682
683 ELSE IF( ( aaqq.GE.sn ) .AND. ( aapp.GE.temp1 ) ) THEN
684 temp1 = max( sn / aaqq, temp1 / aapp )
685
686
687 ELSE IF( ( aaqq.LE.sn ) .AND. ( aapp.GE.temp1 ) ) THEN
688 temp1 = min( sn / aaqq, big / ( sqrt( real( n ) )*aapp ) )
689
690
691 ELSE
692 temp1 = one
693 END IF
694
695
696
697 IF( temp1.NE.one ) THEN
698 CALL slascl(
'G', 0, 0, one, temp1, n, 1, sva, n, ierr )
699 END IF
700 skl = temp1*skl
701 IF( skl.NE.one ) THEN
702 CALL clascl( joba, 0, 0, one, skl, m, n, a, lda, ierr )
703 skl = one / skl
704 END IF
705
706
707
708 emptsw = ( n*( n-1 ) ) / 2
709 notrot = 0
710
711 DO 1868 q = 1, n
712 cwork( q ) = cone
713 1868 CONTINUE
714
715
716
717 swband = 3
718
719
720
721
722
723
724
725 kbl = min( 8, n )
726
727
728
729
730
731 nbl = n / kbl
732 IF( ( nbl*kbl ).NE.n )nbl = nbl + 1
733
734 blskip = kbl**2
735
736
737 rowskip = min( 5, kbl )
738
739
740 lkahead = 1
741
742
743
744
745
746
747
748 IF( ( lower .OR. upper ) .AND. ( n.GT.max( 64, 4*kbl ) ) ) THEN
749
750
751 n4 = n / 4
752 n2 = n / 2
753 n34 = 3*n4
754 IF( applv ) THEN
755 q = 0
756 ELSE
757 q = 1
758 END IF
759
760 IF( lower ) THEN
761
762
763
764
765
766
767
768
769
770 CALL cgsvj0( jobv, m-n34, n-n34, a( n34+1, n34+1 ), lda,
771 $ cwork( n34+1 ), sva( n34+1 ), mvl,
772 $ v( n34*q+1, n34+1 ), ldv, epsln, sfmin, tol,
773 $ 2, cwork( n+1 ), lwork-n, ierr )
774
775 CALL cgsvj0( jobv, m-n2, n34-n2, a( n2+1, n2+1 ), lda,
776 $ cwork( n2+1 ), sva( n2+1 ), mvl,
777 $ v( n2*q+1, n2+1 ), ldv, epsln, sfmin, tol, 2,
778 $ cwork( n+1 ), lwork-n, ierr )
779
780 CALL cgsvj1( jobv, m-n2, n-n2, n4, a( n2+1, n2+1 ), lda,
781 $ cwork( n2+1 ), sva( n2+1 ), mvl,
782 $ v( n2*q+1, n2+1 ), ldv, epsln, sfmin, tol, 1,
783 $ cwork( n+1 ), lwork-n, ierr )
784
785 CALL cgsvj0( jobv, m-n4, n2-n4, a( n4+1, n4+1 ), lda,
786 $ cwork( n4+1 ), sva( n4+1 ), mvl,
787 $ v( n4*q+1, n4+1 ), ldv, epsln, sfmin, tol, 1,
788 $ cwork( n+1 ), lwork-n, ierr )
789
790 CALL cgsvj0( jobv, m, n4, a, lda, cwork, sva, mvl, v,
791 $ ldv,
792 $ epsln, sfmin, tol, 1, cwork( n+1 ), lwork-n,
793 $ ierr )
794
795 CALL cgsvj1( jobv, m, n2, n4, a, lda, cwork, sva, mvl, v,
796 $ ldv, epsln, sfmin, tol, 1, cwork( n+1 ),
797 $ lwork-n, ierr )
798
799
800 ELSE IF( upper ) THEN
801
802
803 CALL cgsvj0( jobv, n4, n4, a, lda, cwork, sva, mvl, v,
804 $ ldv,
805 $ epsln, sfmin, tol, 2, cwork( n+1 ), lwork-n,
806 $ ierr )
807
808 CALL cgsvj0( jobv, n2, n4, a( 1, n4+1 ), lda,
809 $ cwork( n4+1 ),
810 $ sva( n4+1 ), mvl, v( n4*q+1, n4+1 ), ldv,
811 $ epsln, sfmin, tol, 1, cwork( n+1 ), lwork-n,
812 $ ierr )
813
814 CALL cgsvj1( jobv, n2, n2, n4, a, lda, cwork, sva, mvl,
815 $ v,
816 $ ldv, epsln, sfmin, tol, 1, cwork( n+1 ),
817 $ lwork-n, ierr )
818
819 CALL cgsvj0( jobv, n2+n4, n4, a( 1, n2+1 ), lda,
820 $ cwork( n2+1 ), sva( n2+1 ), mvl,
821 $ v( n2*q+1, n2+1 ), ldv, epsln, sfmin, tol, 1,
822 $ cwork( n+1 ), lwork-n, ierr )
823
824 END IF
825
826 END IF
827
828
829
830 DO 1993 i = 1, nsweep
831
832
833
834 mxaapq = zero
835 mxsinj = zero
836 iswrot = 0
837
838 notrot = 0
839 pskipped = 0
840
841
842
843
844
845
846 DO 2000 ibr = 1, nbl
847
848 igl = ( ibr-1 )*kbl + 1
849
850 DO 1002 ir1 = 0, min( lkahead, nbl-ibr )
851
852 igl = igl + ir1*kbl
853
854 DO 2001 p = igl, min( igl+kbl-1, n-1 )
855
856
857
858 q =
isamax( n-p+1, sva( p ), 1 ) + p - 1
859 IF( p.NE.q ) THEN
860 CALL cswap( m, a( 1, p ), 1, a( 1, q ), 1 )
861 IF( rsvec )
CALL cswap( mvl, v( 1, p ), 1,
862 $ v( 1, q ), 1 )
863 temp1 = sva( p )
864 sva( p ) = sva( q )
865 sva( q ) = temp1
866 aapq = cwork(p)
867 cwork(p) = cwork(q)
868 cwork(q) = aapq
869 END IF
870
871 IF( ir1.EQ.0 ) THEN
872
873
874
875
876
877
878
879
880
881
882
883
884
885 IF( ( sva( p ).LT.rootbig ) .AND.
886 $ ( sva( p ).GT.rootsfmin ) ) THEN
887 sva( p ) =
scnrm2( m, a( 1, p ), 1 )
888 ELSE
889 temp1 = zero
890 aapp = one
891 CALL classq( m, a( 1, p ), 1, temp1, aapp )
892 sva( p ) = temp1*sqrt( aapp )
893 END IF
894 aapp = sva( p )
895 ELSE
896 aapp = sva( p )
897 END IF
898
899 IF( aapp.GT.zero ) THEN
900
901 pskipped = 0
902
903 DO 2002 q = p + 1, min( igl+kbl-1, n )
904
905 aaqq = sva( q )
906
907 IF( aaqq.GT.zero ) THEN
908
909 aapp0 = aapp
910 IF( aaqq.GE.one ) THEN
911 rotok = ( small*aapp ).LE.aaqq
912 IF( aapp.LT.( big / aaqq ) ) THEN
913 aapq = (
cdotc( m, a( 1, p ), 1,
914 $ a( 1, q ), 1 ) / aaqq ) / aapp
915 ELSE
916 CALL ccopy( m, a( 1, p ), 1,
917 $ cwork(n+1), 1 )
918 CALL clascl(
'G', 0, 0, aapp, one,
919 $ m, 1, cwork(n+1), lda, ierr )
920 aapq =
cdotc( m, cwork(n+1), 1,
921 $ a( 1, q ), 1 ) / aaqq
922 END IF
923 ELSE
924 rotok = aapp.LE.( aaqq / small )
925 IF( aapp.GT.( small / aaqq ) ) THEN
926 aapq = (
cdotc( m, a( 1, p ), 1,
927 $ a( 1, q ), 1 ) / aapp ) / aaqq
928 ELSE
929 CALL ccopy( m, a( 1, q ), 1,
930 $ cwork(n+1), 1 )
931 CALL clascl(
'G', 0, 0, aaqq,
932 $ one, m, 1,
933 $ cwork(n+1), lda, ierr )
934 aapq =
cdotc( m, a(1, p ), 1,
935 $ cwork(n+1), 1 ) / aapp
936 END IF
937 END IF
938
939
940 aapq1 = -abs(aapq)
941 mxaapq = max( mxaapq, -aapq1 )
942
943
944
945 IF( abs( aapq1 ).GT.tol ) THEN
946 ompq = aapq / abs(aapq)
947
948
949
950
951 IF( ir1.EQ.0 ) THEN
952 notrot = 0
953 pskipped = 0
954 iswrot = iswrot + 1
955 END IF
956
957 IF( rotok ) THEN
958
959 aqoap = aaqq / aapp
960 apoaq = aapp / aaqq
961 theta = -half*abs( aqoap-apoaq )/aapq1
962
963 IF( abs( theta ).GT.bigtheta ) THEN
964
965 t = half / theta
966 cs = one
967
968 CALL crot( m, a(1,p), 1, a(1,q),
969 $ 1,
970 $ cs, conjg(ompq)*t )
971 IF ( rsvec ) THEN
972 CALL crot( mvl, v(1,p), 1,
973 $ v(1,q), 1, cs, conjg(ompq)*t )
974 END IF
975
976 sva( q ) = aaqq*sqrt( max( zero,
977 $ one+t*apoaq*aapq1 ) )
978 aapp = aapp*sqrt( max( zero,
979 $ one-t*aqoap*aapq1 ) )
980 mxsinj = max( mxsinj, abs( t ) )
981
982 ELSE
983
984
985
986 thsign = -sign( one, aapq1 )
987 t = one / ( theta+thsign*
988 $ sqrt( one+theta*theta ) )
989 cs = sqrt( one / ( one+t*t ) )
990 sn = t*cs
991
992 mxsinj = max( mxsinj, abs( sn ) )
993 sva( q ) = aaqq*sqrt( max( zero,
994 $ one+t*apoaq*aapq1 ) )
995 aapp = aapp*sqrt( max( zero,
996 $ one-t*aqoap*aapq1 ) )
997
998 CALL crot( m, a(1,p), 1, a(1,q),
999 $ 1,
1000 $ cs, conjg(ompq)*sn )
1001 IF ( rsvec ) THEN
1002 CALL crot( mvl, v(1,p), 1,
1003 $ v(1,q), 1, cs, conjg(ompq)*sn )
1004 END IF
1005 END IF
1006 cwork(p) = -cwork(q) * ompq
1007
1008 ELSE
1009
1010 CALL ccopy( m, a( 1, p ), 1,
1011 $ cwork(n+1), 1 )
1012 CALL clascl(
'G', 0, 0, aapp, one,
1013 $ m,
1014 $ 1, cwork(n+1), lda,
1015 $ ierr )
1016 CALL clascl(
'G', 0, 0, aaqq, one,
1017 $ m,
1018 $ 1, a( 1, q ), lda, ierr )
1019 CALL caxpy( m, -aapq, cwork(n+1), 1,
1020 $ a( 1, q ), 1 )
1021 CALL clascl(
'G', 0, 0, one, aaqq,
1022 $ m,
1023 $ 1, a( 1, q ), lda, ierr )
1024 sva( q ) = aaqq*sqrt( max( zero,
1025 $ one-aapq1*aapq1 ) )
1026 mxsinj = max( mxsinj, sfmin )
1027 END IF
1028
1029
1030
1031
1032
1033 IF( ( sva( q ) / aaqq )**2.LE.rooteps )
1034 $ THEN
1035 IF( ( aaqq.LT.rootbig ) .AND.
1036 $ ( aaqq.GT.rootsfmin ) ) THEN
1037 sva( q ) =
scnrm2( m, a( 1, q ),
1038 $ 1 )
1039 ELSE
1040 t = zero
1041 aaqq = one
1042 CALL classq( m, a( 1, q ), 1, t,
1043 $ aaqq )
1044 sva( q ) = t*sqrt( aaqq )
1045 END IF
1046 END IF
1047 IF( ( aapp / aapp0 ).LE.rooteps ) THEN
1048 IF( ( aapp.LT.rootbig ) .AND.
1049 $ ( aapp.GT.rootsfmin ) ) THEN
1050 aapp =
scnrm2( m, a( 1, p ), 1 )
1051 ELSE
1052 t = zero
1053 aapp = one
1054 CALL classq( m, a( 1, p ), 1, t,
1055 $ aapp )
1056 aapp = t*sqrt( aapp )
1057 END IF
1058 sva( p ) = aapp
1059 END IF
1060
1061 ELSE
1062
1063 IF( ir1.EQ.0 )notrot = notrot + 1
1064
1065 pskipped = pskipped + 1
1066 END IF
1067 ELSE
1068
1069 IF( ir1.EQ.0 )notrot = notrot + 1
1070 pskipped = pskipped + 1
1071 END IF
1072
1073 IF( ( i.LE.swband ) .AND.
1074 $ ( pskipped.GT.rowskip ) ) THEN
1075 IF( ir1.EQ.0 )aapp = -aapp
1076 notrot = 0
1077 GO TO 2103
1078 END IF
1079
1080 2002 CONTINUE
1081
1082
1083 2103 CONTINUE
1084
1085
1086 sva( p ) = aapp
1087
1088 ELSE
1089 sva( p ) = aapp
1090 IF( ( ir1.EQ.0 ) .AND. ( aapp.EQ.zero ) )
1091 $ notrot = notrot + min( igl+kbl-1, n ) - p
1092 END IF
1093
1094 2001 CONTINUE
1095
1096
1097 1002 CONTINUE
1098
1099
1100
1101
1102 igl = ( ibr-1 )*kbl + 1
1103
1104 DO 2010 jbc = ibr + 1, nbl
1105
1106 jgl = ( jbc-1 )*kbl + 1
1107
1108
1109
1110 ijblsk = 0
1111 DO 2100 p = igl, min( igl+kbl-1, n )
1112
1113 aapp = sva( p )
1114 IF( aapp.GT.zero ) THEN
1115
1116 pskipped = 0
1117
1118 DO 2200 q = jgl, min( jgl+kbl-1, n )
1119
1120 aaqq = sva( q )
1121 IF( aaqq.GT.zero ) THEN
1122 aapp0 = aapp
1123
1124
1125
1126
1127
1128 IF( aaqq.GE.one ) THEN
1129 IF( aapp.GE.aaqq ) THEN
1130 rotok = ( small*aapp ).LE.aaqq
1131 ELSE
1132 rotok = ( small*aaqq ).LE.aapp
1133 END IF
1134 IF( aapp.LT.( big / aaqq ) ) THEN
1135 aapq = (
cdotc( m, a( 1, p ), 1,
1136 $ a( 1, q ), 1 ) / aaqq ) / aapp
1137 ELSE
1138 CALL ccopy( m, a( 1, p ), 1,
1139 $ cwork(n+1), 1 )
1140 CALL clascl(
'G', 0, 0, aapp,
1141 $ one, m, 1,
1142 $ cwork(n+1), lda, ierr )
1143 aapq =
cdotc( m, cwork(n+1), 1,
1144 $ a( 1, q ), 1 ) / aaqq
1145 END IF
1146 ELSE
1147 IF( aapp.GE.aaqq ) THEN
1148 rotok = aapp.LE.( aaqq / small )
1149 ELSE
1150 rotok = aaqq.LE.( aapp / small )
1151 END IF
1152 IF( aapp.GT.( small / aaqq ) ) THEN
1153 aapq = (
cdotc( m, a( 1, p ), 1,
1154 $ a( 1, q ), 1 ) / max(aaqq,aapp) )
1155 $ / min(aaqq,aapp)
1156 ELSE
1157 CALL ccopy( m, a( 1, q ), 1,
1158 $ cwork(n+1), 1 )
1159 CALL clascl(
'G', 0, 0, aaqq,
1160 $ one, m, 1,
1161 $ cwork(n+1), lda, ierr )
1162 aapq =
cdotc( m, a( 1, p ), 1,
1163 $ cwork(n+1), 1 ) / aapp
1164 END IF
1165 END IF
1166
1167
1168 aapq1 = -abs(aapq)
1169 mxaapq = max( mxaapq, -aapq1 )
1170
1171
1172
1173 IF( abs( aapq1 ).GT.tol ) THEN
1174 ompq = aapq / abs(aapq)
1175 notrot = 0
1176
1177 pskipped = 0
1178 iswrot = iswrot + 1
1179
1180 IF( rotok ) THEN
1181
1182 aqoap = aaqq / aapp
1183 apoaq = aapp / aaqq
1184 theta = -half*abs( aqoap-apoaq )/ aapq1
1185 IF( aaqq.GT.aapp0 )theta = -theta
1186
1187 IF( abs( theta ).GT.bigtheta ) THEN
1188 t = half / theta
1189 cs = one
1190 CALL crot( m, a(1,p), 1, a(1,q),
1191 $ 1,
1192 $ cs, conjg(ompq)*t )
1193 IF( rsvec ) THEN
1194 CALL crot( mvl, v(1,p), 1,
1195 $ v(1,q), 1, cs, conjg(ompq)*t )
1196 END IF
1197 sva( q ) = aaqq*sqrt( max( zero,
1198 $ one+t*apoaq*aapq1 ) )
1199 aapp = aapp*sqrt( max( zero,
1200 $ one-t*aqoap*aapq1 ) )
1201 mxsinj = max( mxsinj, abs( t ) )
1202 ELSE
1203
1204
1205
1206 thsign = -sign( one, aapq1 )
1207 IF( aaqq.GT.aapp0 )thsign = -thsign
1208 t = one / ( theta+thsign*
1209 $ sqrt( one+theta*theta ) )
1210 cs = sqrt( one / ( one+t*t ) )
1211 sn = t*cs
1212 mxsinj = max( mxsinj, abs( sn ) )
1213 sva( q ) = aaqq*sqrt( max( zero,
1214 $ one+t*apoaq*aapq1 ) )
1215 aapp = aapp*sqrt( max( zero,
1216 $ one-t*aqoap*aapq1 ) )
1217
1218 CALL crot( m, a(1,p), 1, a(1,q),
1219 $ 1,
1220 $ cs, conjg(ompq)*sn )
1221 IF( rsvec ) THEN
1222 CALL crot( mvl, v(1,p), 1,
1223 $ v(1,q), 1, cs, conjg(ompq)*sn )
1224 END IF
1225 END IF
1226 cwork(p) = -cwork(q) * ompq
1227
1228 ELSE
1229
1230 IF( aapp.GT.aaqq ) THEN
1231 CALL ccopy( m, a( 1, p ), 1,
1232 $ cwork(n+1), 1 )
1233 CALL clascl(
'G', 0, 0, aapp,
1234 $ one,
1235 $ m, 1, cwork(n+1),lda,
1236 $ ierr )
1237 CALL clascl(
'G', 0, 0, aaqq,
1238 $ one,
1239 $ m, 1, a( 1, q ), lda,
1240 $ ierr )
1241 CALL caxpy( m, -aapq, cwork(n+1),
1242 $ 1, a( 1, q ), 1 )
1243 CALL clascl(
'G', 0, 0, one,
1244 $ aaqq,
1245 $ m, 1, a( 1, q ), lda,
1246 $ ierr )
1247 sva( q ) = aaqq*sqrt( max( zero,
1248 $ one-aapq1*aapq1 ) )
1249 mxsinj = max( mxsinj, sfmin )
1250 ELSE
1251 CALL ccopy( m, a( 1, q ), 1,
1252 $ cwork(n+1), 1 )
1253 CALL clascl(
'G', 0, 0, aaqq,
1254 $ one,
1255 $ m, 1, cwork(n+1),lda,
1256 $ ierr )
1257 CALL clascl(
'G', 0, 0, aapp,
1258 $ one,
1259 $ m, 1, a( 1, p ), lda,
1260 $ ierr )
1261 CALL caxpy( m, -conjg(aapq),
1262 $ cwork(n+1), 1, a( 1, p ), 1 )
1263 CALL clascl(
'G', 0, 0, one,
1264 $ aapp,
1265 $ m, 1, a( 1, p ), lda,
1266 $ ierr )
1267 sva( p ) = aapp*sqrt( max( zero,
1268 $ one-aapq1*aapq1 ) )
1269 mxsinj = max( mxsinj, sfmin )
1270 END IF
1271 END IF
1272
1273
1274
1275
1276 IF( ( sva( q ) / aaqq )**2.LE.rooteps )
1277 $ THEN
1278 IF( ( aaqq.LT.rootbig ) .AND.
1279 $ ( aaqq.GT.rootsfmin ) ) THEN
1280 sva( q ) =
scnrm2( m, a( 1, q ),
1281 $ 1)
1282 ELSE
1283 t = zero
1284 aaqq = one
1285 CALL classq( m, a( 1, q ), 1, t,
1286 $ aaqq )
1287 sva( q ) = t*sqrt( aaqq )
1288 END IF
1289 END IF
1290 IF( ( aapp / aapp0 )**2.LE.rooteps ) THEN
1291 IF( ( aapp.LT.rootbig ) .AND.
1292 $ ( aapp.GT.rootsfmin ) ) THEN
1293 aapp =
scnrm2( m, a( 1, p ), 1 )
1294 ELSE
1295 t = zero
1296 aapp = one
1297 CALL classq( m, a( 1, p ), 1, t,
1298 $ aapp )
1299 aapp = t*sqrt( aapp )
1300 END IF
1301 sva( p ) = aapp
1302 END IF
1303
1304 ELSE
1305 notrot = notrot + 1
1306
1307 pskipped = pskipped + 1
1308 ijblsk = ijblsk + 1
1309 END IF
1310 ELSE
1311 notrot = notrot + 1
1312 pskipped = pskipped + 1
1313 ijblsk = ijblsk + 1
1314 END IF
1315
1316 IF( ( i.LE.swband ) .AND. ( ijblsk.GE.blskip ) )
1317 $ THEN
1318 sva( p ) = aapp
1319 notrot = 0
1320 GO TO 2011
1321 END IF
1322 IF( ( i.LE.swband ) .AND.
1323 $ ( pskipped.GT.rowskip ) ) THEN
1324 aapp = -aapp
1325 notrot = 0
1326 GO TO 2203
1327 END IF
1328
1329 2200 CONTINUE
1330
1331 2203 CONTINUE
1332
1333 sva( p ) = aapp
1334
1335 ELSE
1336
1337 IF( aapp.EQ.zero )notrot = notrot +
1338 $ min( jgl+kbl-1, n ) - jgl + 1
1339 IF( aapp.LT.zero )notrot = 0
1340
1341 END IF
1342
1343 2100 CONTINUE
1344
1345 2010 CONTINUE
1346
1347 2011 CONTINUE
1348
1349 DO 2012 p = igl, min( igl+kbl-1, n )
1350 sva( p ) = abs( sva( p ) )
1351 2012 CONTINUE
1352
1353 2000 CONTINUE
1354
1355
1356
1357 IF( ( sva( n ).LT.rootbig ) .AND. ( sva( n ).GT.rootsfmin ) )
1358 $ THEN
1359 sva( n ) =
scnrm2( m, a( 1, n ), 1 )
1360 ELSE
1361 t = zero
1362 aapp = one
1363 CALL classq( m, a( 1, n ), 1, t, aapp )
1364 sva( n ) = t*sqrt( aapp )
1365 END IF
1366
1367
1368
1369 IF( ( i.LT.swband ) .AND. ( ( mxaapq.LE.roottol ) .OR.
1370 $ ( iswrot.LE.n ) ) )swband = i
1371
1372 IF( ( i.GT.swband+1 ) .AND. ( mxaapq.LT.sqrt( real( n ) )*
1373 $ tol ) .AND. ( real( n )*mxaapq*mxsinj.LT.tol ) ) THEN
1374 GO TO 1994
1375 END IF
1376
1377 IF( notrot.GE.emptsw )GO TO 1994
1378
1379 1993 CONTINUE
1380
1381
1382
1383 info = nsweep - 1
1384 GO TO 1995
1385
1386 1994 CONTINUE
1387
1388
1389
1390 info = 0
1391
1392 1995 CONTINUE
1393
1394
1395
1396
1397 n2 = 0
1398 n4 = 0
1399 DO 5991 p = 1, n - 1
1400 q =
isamax( n-p+1, sva( p ), 1 ) + p - 1
1401 IF( p.NE.q ) THEN
1402 temp1 = sva( p )
1403 sva( p ) = sva( q )
1404 sva( q ) = temp1
1405 CALL cswap( m, a( 1, p ), 1, a( 1, q ), 1 )
1406 IF( rsvec )
CALL cswap( mvl, v( 1, p ), 1, v( 1, q ), 1 )
1407 END IF
1408 IF( sva( p ).NE.zero ) THEN
1409 n4 = n4 + 1
1410 IF( sva( p )*skl.GT.sfmin )n2 = n2 + 1
1411 END IF
1412 5991 CONTINUE
1413 IF( sva( n ).NE.zero ) THEN
1414 n4 = n4 + 1
1415 IF( sva( n )*skl.GT.sfmin )n2 = n2 + 1
1416 END IF
1417
1418
1419
1420 IF( lsvec .OR. uctol ) THEN
1421 DO 1998 p = 1, n4
1422
1423 CALL clascl(
'G',0,0, sva(p), one, m, 1, a(1,p), m,
1424 $ ierr )
1425 1998 CONTINUE
1426 END IF
1427
1428
1429
1430 IF( rsvec ) THEN
1431 DO 2399 p = 1, n
1432 temp1 = one /
scnrm2( mvl, v( 1, p ), 1 )
1433 CALL csscal( mvl, temp1, v( 1, p ), 1 )
1434 2399 CONTINUE
1435 END IF
1436
1437
1438 IF( ( ( skl.GT.one ) .AND. ( sva( 1 ).LT.( big / skl ) ) )
1439 $ .OR. ( ( skl.LT.one ) .AND. ( sva( max( n2, 1 ) ) .GT.
1440 $ ( sfmin / skl ) ) ) ) THEN
1441 DO 2400 p = 1, n
1442 sva( p ) = skl*sva( p )
1443 2400 CONTINUE
1444 skl = one
1445 END IF
1446
1447 rwork( 1 ) = skl
1448
1449
1450
1451
1452 rwork( 2 ) = real( n4 )
1453
1454
1455 rwork( 3 ) = real( n2 )
1456
1457
1458
1459
1460 rwork( 4 ) = real( i )
1461
1462
1463 rwork( 5 ) = mxaapq
1464
1465
1466
1467 rwork( 6 ) = mxsinj
1468
1469
1470
1471 RETURN
1472
1473
1474
subroutine xerbla(srname, info)
subroutine caxpy(n, ca, cx, incx, cy, incy)
CAXPY
subroutine ccopy(n, cx, incx, cy, incy)
CCOPY
complex function cdotc(n, cx, incx, cy, incy)
CDOTC
subroutine cgsvj0(jobv, m, n, a, lda, d, sva, mv, v, ldv, eps, sfmin, tol, nsweep, work, lwork, info)
CGSVJ0 pre-processor for the routine cgesvj.
subroutine cgsvj1(jobv, m, n, n1, a, lda, d, sva, mv, v, ldv, eps, sfmin, tol, nsweep, work, lwork, info)
CGSVJ1 pre-processor for the routine cgesvj, applies Jacobi rotations targeting only particular pivot...
integer function isamax(n, sx, incx)
ISAMAX
real function slamch(cmach)
SLAMCH
subroutine clascl(type, kl, ku, cfrom, cto, m, n, a, lda, info)
CLASCL multiplies a general rectangular matrix by a real scalar defined as cto/cfrom.
subroutine slascl(type, kl, ku, cfrom, cto, m, n, a, lda, info)
SLASCL multiplies a general rectangular matrix by a real scalar defined as cto/cfrom.
subroutine claset(uplo, m, n, alpha, beta, a, lda)
CLASET initializes the off-diagonal elements and the diagonal elements of a matrix to given values.
subroutine classq(n, x, incx, scale, sumsq)
CLASSQ updates a sum of squares represented in scaled form.
logical function lsame(ca, cb)
LSAME
real(wp) function scnrm2(n, x, incx)
SCNRM2
subroutine crot(n, cx, incx, cy, incy, c, s)
CROT applies a plane rotation with real cosine and complex sine to a pair of complex vectors.
real function sroundup_lwork(lwork)
SROUNDUP_LWORK
subroutine csscal(n, sa, cx, incx)
CSSCAL
subroutine cswap(n, cx, incx, cy, incy)
CSWAP