kusano 2b45e8
      SUBROUTINE SPOTF2F( UPLO, N, A, LDA, INFO )
kusano 2b45e8
*
kusano 2b45e8
*  -- LAPACK routine (version 3.0) --
kusano 2b45e8
*     Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,
kusano 2b45e8
*     Courant Institute, Argonne National Lab, and Rice University
kusano 2b45e8
*     February 29, 1992
kusano 2b45e8
*
kusano 2b45e8
*     .. Scalar Arguments ..
kusano 2b45e8
      CHARACTER          UPLO
kusano 2b45e8
      INTEGER            INFO, LDA, N
kusano 2b45e8
*     ..
kusano 2b45e8
*     .. Array Arguments ..
kusano 2b45e8
      REAL               A( LDA, * )
kusano 2b45e8
*     ..
kusano 2b45e8
*
kusano 2b45e8
*  Purpose
kusano 2b45e8
*  =======
kusano 2b45e8
*
kusano 2b45e8
*  SPOTF2 computes the Cholesky factorization of a real symmetric
kusano 2b45e8
*  positive definite matrix A.
kusano 2b45e8
*
kusano 2b45e8
*  The factorization has the form
kusano 2b45e8
*     A = U' * U ,  if UPLO = 'U', or
kusano 2b45e8
*     A = L  * L',  if UPLO = 'L',
kusano 2b45e8
*  where U is an upper triangular matrix and L is lower triangular.
kusano 2b45e8
*
kusano 2b45e8
*  This is the unblocked version of the algorithm, calling Level 2 BLAS.
kusano 2b45e8
*
kusano 2b45e8
*  Arguments
kusano 2b45e8
*  =========
kusano 2b45e8
*
kusano 2b45e8
*  UPLO    (input) CHARACTER*1
kusano 2b45e8
*          Specifies whether the upper or lower triangular part of the
kusano 2b45e8
*          symmetric matrix A is stored.
kusano 2b45e8
*          = 'U':  Upper triangular
kusano 2b45e8
*          = 'L':  Lower triangular
kusano 2b45e8
*
kusano 2b45e8
*  N       (input) INTEGER
kusano 2b45e8
*          The order of the matrix A.  N >= 0.
kusano 2b45e8
*
kusano 2b45e8
*  A       (input/output) REAL array, dimension (LDA,N)
kusano 2b45e8
*          On entry, the symmetric matrix A.  If UPLO = 'U', the leading
kusano 2b45e8
*          n by n upper triangular part of A contains the upper
kusano 2b45e8
*          triangular part of the matrix A, and the strictly lower
kusano 2b45e8
*          triangular part of A is not referenced.  If UPLO = 'L', the
kusano 2b45e8
*          leading n by n lower triangular part of A contains the lower
kusano 2b45e8
*          triangular part of the matrix A, and the strictly upper
kusano 2b45e8
*          triangular part of A is not referenced.
kusano 2b45e8
*
kusano 2b45e8
*          On exit, if INFO = 0, the factor U or L from the Cholesky
kusano 2b45e8
*          factorization A = U'*U  or A = L*L'.
kusano 2b45e8
*
kusano 2b45e8
*  LDA     (input) INTEGER
kusano 2b45e8
*          The leading dimension of the array A.  LDA >= max(1,N).
kusano 2b45e8
*
kusano 2b45e8
*  INFO    (output) INTEGER
kusano 2b45e8
*          = 0: successful exit
kusano 2b45e8
*          < 0: if INFO = -k, the k-th argument had an illegal value
kusano 2b45e8
*          > 0: if INFO = k, the leading minor of order k is not
kusano 2b45e8
*               positive definite, and the factorization could not be
kusano 2b45e8
*               completed.
kusano 2b45e8
*
kusano 2b45e8
*  =====================================================================
kusano 2b45e8
*
kusano 2b45e8
*     .. Parameters ..
kusano 2b45e8
      REAL               ONE, ZERO
kusano 2b45e8
      PARAMETER          ( ONE = 1.0E+0, ZERO = 0.0E+0 )
kusano 2b45e8
*     ..
kusano 2b45e8
*     .. Local Scalars ..
kusano 2b45e8
      LOGICAL            UPPER
kusano 2b45e8
      INTEGER            J
kusano 2b45e8
      REAL               AJJ
kusano 2b45e8
*     ..
kusano 2b45e8
*     .. External Functions ..
kusano 2b45e8
      LOGICAL            LSAME
kusano 2b45e8
      REAL               SDOT
kusano 2b45e8
      EXTERNAL           LSAME, SDOT
kusano 2b45e8
*     ..
kusano 2b45e8
*     .. External Subroutines ..
kusano 2b45e8
      EXTERNAL           SGEMV, SSCAL, XERBLA
kusano 2b45e8
*     ..
kusano 2b45e8
*     .. Intrinsic Functions ..
kusano 2b45e8
      INTRINSIC          MAX, SQRT
kusano 2b45e8
*     ..
kusano 2b45e8
*     .. Executable Statements ..
kusano 2b45e8
*
kusano 2b45e8
*     Test the input parameters.
kusano 2b45e8
*
kusano 2b45e8
      INFO = 0
kusano 2b45e8
      UPPER = LSAME( UPLO, 'U' )
kusano 2b45e8
      IF( .NOT.UPPER .AND. .NOT.LSAME( UPLO, 'L' ) ) THEN
kusano 2b45e8
         INFO = -1
kusano 2b45e8
      ELSE IF( N.LT.0 ) THEN
kusano 2b45e8
         INFO = -2
kusano 2b45e8
      ELSE IF( LDA.LT.MAX( 1, N ) ) THEN
kusano 2b45e8
         INFO = -4
kusano 2b45e8
      END IF
kusano 2b45e8
      IF( INFO.NE.0 ) THEN
kusano 2b45e8
         CALL XERBLA( 'SPOTF2', -INFO )
kusano 2b45e8
         RETURN
kusano 2b45e8
      END IF
kusano 2b45e8
*
kusano 2b45e8
*     Quick return if possible
kusano 2b45e8
*
kusano 2b45e8
      IF( N.EQ.0 )
kusano 2b45e8
     $   RETURN
kusano 2b45e8
*
kusano 2b45e8
      IF( UPPER ) THEN
kusano 2b45e8
*
kusano 2b45e8
*        Compute the Cholesky factorization A = U'*U.
kusano 2b45e8
*
kusano 2b45e8
         DO 10 J = 1, N
kusano 2b45e8
*
kusano 2b45e8
*           Compute U(J,J) and test for non-positive-definiteness.
kusano 2b45e8
*
kusano 2b45e8
            AJJ = A( J, J ) - SDOT( J-1, A( 1, J ), 1, A( 1, J ), 1 )
kusano 2b45e8
            IF( AJJ.LE.ZERO ) THEN
kusano 2b45e8
               A( J, J ) = AJJ
kusano 2b45e8
               GO TO 30
kusano 2b45e8
            END IF
kusano 2b45e8
            AJJ = SQRT( AJJ )
kusano 2b45e8
            A( J, J ) = AJJ
kusano 2b45e8
*
kusano 2b45e8
*           Compute elements J+1:N of row J.
kusano 2b45e8
*
kusano 2b45e8
            IF( J.LT.N ) THEN
kusano 2b45e8
               CALL SGEMV( 'Transpose', J-1, N-J, -ONE, A( 1, J+1 ),
kusano 2b45e8
     $                     LDA, A( 1, J ), 1, ONE, A( J, J+1 ), LDA )
kusano 2b45e8
               CALL SSCAL( N-J, ONE / AJJ, A( J, J+1 ), LDA )
kusano 2b45e8
            END IF
kusano 2b45e8
   10    CONTINUE
kusano 2b45e8
      ELSE
kusano 2b45e8
*
kusano 2b45e8
*        Compute the Cholesky factorization A = L*L'.
kusano 2b45e8
*
kusano 2b45e8
         DO 20 J = 1, N
kusano 2b45e8
*
kusano 2b45e8
*           Compute L(J,J) and test for non-positive-definiteness.
kusano 2b45e8
*
kusano 2b45e8
            AJJ = A( J, J ) - SDOT( J-1, A( J, 1 ), LDA, A( J, 1 ),
kusano 2b45e8
     $            LDA )
kusano 2b45e8
            IF( AJJ.LE.ZERO ) THEN
kusano 2b45e8
               A( J, J ) = AJJ
kusano 2b45e8
               GO TO 30
kusano 2b45e8
            END IF
kusano 2b45e8
            AJJ = SQRT( AJJ )
kusano 2b45e8
            A( J, J ) = AJJ
kusano 2b45e8
*
kusano 2b45e8
*           Compute elements J+1:N of column J.
kusano 2b45e8
*
kusano 2b45e8
            IF( J.LT.N ) THEN
kusano 2b45e8
               CALL SGEMV( 'No transpose', N-J, J-1, -ONE, A( J+1, 1 ),
kusano 2b45e8
     $                     LDA, A( J, 1 ), LDA, ONE, A( J+1, J ), 1 )
kusano 2b45e8
               CALL SSCAL( N-J, ONE / AJJ, A( J+1, J ), 1 )
kusano 2b45e8
            END IF
kusano 2b45e8
   20    CONTINUE
kusano 2b45e8
      END IF
kusano 2b45e8
      GO TO 40
kusano 2b45e8
*
kusano 2b45e8
   30 CONTINUE
kusano 2b45e8
      INFO = J
kusano 2b45e8
*
kusano 2b45e8
   40 CONTINUE
kusano 2b45e8
      RETURN
kusano 2b45e8
*
kusano 2b45e8
*     End of SPOTF2
kusano 2b45e8
*
kusano 2b45e8
      END