kusano 7d535a
/*  -- translated by f2c (version 19940927).
kusano 7d535a
   You must link the resulting object file with the libraries:
kusano 7d535a
	-lf2c -lm   (in that order)
kusano 7d535a
*/
kusano 7d535a
kusano 7d535a
#include "f2c.h"
kusano 7d535a
kusano 7d535a
/* Table of constant values */
kusano 7d535a
kusano 7d535a
static complex c_b1 = {0.f,0.f};
kusano 7d535a
static complex c_b2 = {1.f,0.f};
kusano 7d535a
static integer c__3 = 3;
kusano 7d535a
static integer c__1 = 1;
kusano 7d535a
kusano 7d535a
/* Subroutine */ int claror_(char *side, char *init, integer *m, integer *n, 
kusano 7d535a
	complex *a, integer *lda, integer *iseed, complex *x, integer *info)
kusano 7d535a
{
kusano 7d535a
    /* System generated locals */
kusano 7d535a
    integer a_dim1, a_offset, i__1, i__2, i__3;
kusano 7d535a
    complex q__1, q__2;
kusano 7d535a
kusano 7d535a
    /* Builtin functions */
kusano 7d535a
    double c_abs(complex *);
kusano 7d535a
    void r_cnjg(complex *, complex *);
kusano 7d535a
kusano 7d535a
    /* Local variables */
kusano 7d535a
    static integer kbeg, jcol;
kusano 7d535a
    static real xabs;
kusano 7d535a
    static integer irow, j;
kusano 7d535a
    extern /* Subroutine */ int cgerc_(integer *, integer *, complex *, 
kusano 7d535a
	    complex *, integer *, complex *, integer *, complex *, integer *),
kusano 7d535a
	     cscal_(integer *, complex *, complex *, integer *);
kusano 7d535a
    extern logical lsame_(char *, char *);
kusano 7d535a
    extern /* Subroutine */ int cgemv_(char *, integer *, integer *, complex *
kusano 7d535a
	    , complex *, integer *, complex *, integer *, complex *, complex *
kusano 7d535a
	    , integer *);
kusano 7d535a
    static complex csign;
kusano 7d535a
    static integer ixfrm, itype, nxfrm;
kusano 7d535a
    static real xnorm;
kusano 7d535a
    extern real scnrm2_(integer *, complex *, integer *);
kusano 7d535a
    extern /* Subroutine */ int clacgv_(integer *, complex *, integer *);
kusano 7d535a
    extern /* Complex */ VOID clarnd_(complex *, integer *, integer *);
kusano 7d535a
    extern /* Subroutine */ int claset_(char *, integer *, integer *, complex 
kusano 7d535a
	    *, complex *, complex *, integer *), xerbla_(char *, 
kusano 7d535a
	    integer *);
kusano 7d535a
    static real factor;
kusano 7d535a
    static complex xnorms;
kusano 7d535a
kusano 7d535a
kusano 7d535a
/*  -- LAPACK auxiliary test routine (version 2.0) --   
kusano 7d535a
       Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,   
kusano 7d535a
       Courant Institute, Argonne National Lab, and Rice University   
kusano 7d535a
       September 30, 1994   
kusano 7d535a
kusano 7d535a
kusano 7d535a
    Purpose   
kusano 7d535a
    =======   
kusano 7d535a
kusano 7d535a
       CLAROR pre- or post-multiplies an M by N matrix A by a random   
kusano 7d535a
       unitary matrix U, overwriting A. A may optionally be   
kusano 7d535a
       initialized to the identity matrix before multiplying by U.   
kusano 7d535a
       U is generated using the method of G.W. Stewart   
kusano 7d535a
       ( SIAM J. Numer. Anal. 17, 1980, pp. 403-409 ).   
kusano 7d535a
       (BLAS-2 version)   
kusano 7d535a
kusano 7d535a
    Arguments   
kusano 7d535a
    =========   
kusano 7d535a
kusano 7d535a
    SIDE   - CHARACTER*1   
kusano 7d535a
             SIDE specifies whether A is multiplied on the left or right 
kusano 7d535a
  
kusano 7d535a
             by U.   
kusano 7d535a
         SIDE = 'L'   Multiply A on the left (premultiply) by U   
kusano 7d535a
         SIDE = 'R'   Multiply A on the right (postmultiply) by U*   
kusano 7d535a
         SIDE = 'C'   Multiply A on the left by U and the right by U*   
kusano 7d535a
         SIDE = 'T'   Multiply A on the left by U and the right by U'   
kusano 7d535a
             Not modified.   
kusano 7d535a
kusano 7d535a
    INIT   - CHARACTER*1   
kusano 7d535a
             INIT specifies whether or not A should be initialized to   
kusano 7d535a
             the identity matrix.   
kusano 7d535a
                INIT = 'I'   Initialize A to (a section of) the   
kusano 7d535a
                             identity matrix before applying U.   
kusano 7d535a
                INIT = 'N'   No initialization.  Apply U to the   
kusano 7d535a
                             input matrix A.   
kusano 7d535a
kusano 7d535a
             INIT = 'I' may be used to generate square (i.e., unitary)   
kusano 7d535a
             or rectangular orthogonal matrices (orthogonality being   
kusano 7d535a
             in the sense of CDOTC):   
kusano 7d535a
kusano 7d535a
             For square matrices, M=N, and SIDE many be either 'L' or   
kusano 7d535a
             'R'; the rows will be orthogonal to each other, as will the 
kusano 7d535a
  
kusano 7d535a
             columns.   
kusano 7d535a
             For rectangular matrices where M < N, SIDE = 'R' will   
kusano 7d535a
             produce a dense matrix whose rows will be orthogonal and   
kusano 7d535a
             whose columns will not, while SIDE = 'L' will produce a   
kusano 7d535a
             matrix whose rows will be orthogonal, and whose first M   
kusano 7d535a
             columns will be orthogonal, the remaining columns being   
kusano 7d535a
             zero.   
kusano 7d535a
             For matrices where M > N, just use the previous   
kusano 7d535a
             explaination, interchanging 'L' and 'R' and "rows" and   
kusano 7d535a
             "columns".   
kusano 7d535a
kusano 7d535a
             Not modified.   
kusano 7d535a
kusano 7d535a
    M      - INTEGER   
kusano 7d535a
             Number of rows of A. Not modified.   
kusano 7d535a
kusano 7d535a
    N      - INTEGER   
kusano 7d535a
             Number of columns of A. Not modified.   
kusano 7d535a
kusano 7d535a
    A      - COMPLEX array, dimension ( LDA, N )   
kusano 7d535a
             Input and output array. Overwritten by U A ( if SIDE = 'L' ) 
kusano 7d535a
  
kusano 7d535a
             or by A U ( if SIDE = 'R' )   
kusano 7d535a
             or by U A U* ( if SIDE = 'C')   
kusano 7d535a
             or by U A U' ( if SIDE = 'T') on exit.   
kusano 7d535a
kusano 7d535a
    LDA    - INTEGER   
kusano 7d535a
             Leading dimension of A. Must be at least MAX ( 1, M ).   
kusano 7d535a
             Not modified.   
kusano 7d535a
kusano 7d535a
    ISEED  - INTEGER array, dimension ( 4 )   
kusano 7d535a
             On entry ISEED specifies the seed of the random number   
kusano 7d535a
             generator. The array elements should be between 0 and 4095; 
kusano 7d535a
  
kusano 7d535a
             if not they will be reduced mod 4096.  Also, ISEED(4) must   
kusano 7d535a
             be odd.  The random number generator uses a linear   
kusano 7d535a
             congruential sequence limited to small integers, and so   
kusano 7d535a
             should produce machine independent random numbers. The   
kusano 7d535a
             values of ISEED are changed on exit, and can be used in the 
kusano 7d535a
  
kusano 7d535a
             next call to CLAROR to continue the same random number   
kusano 7d535a
             sequence.   
kusano 7d535a
             Modified.   
kusano 7d535a
kusano 7d535a
    X      - COMPLEX array, dimension ( 3*MAX( M, N ) )   
kusano 7d535a
             Workspace. Of length:   
kusano 7d535a
                 2*M + N if SIDE = 'L',   
kusano 7d535a
                 2*N + M if SIDE = 'R',   
kusano 7d535a
                 3*N     if SIDE = 'C' or 'T'.   
kusano 7d535a
             Modified.   
kusano 7d535a
kusano 7d535a
    INFO   - INTEGER   
kusano 7d535a
             An error flag.  It is set to:   
kusano 7d535a
              0  if no error.   
kusano 7d535a
              1  if CLARND returned a bad random number (installation   
kusano 7d535a
                 problem)   
kusano 7d535a
             -1  if SIDE is not L, R, C, or T.   
kusano 7d535a
             -3  if M is negative.   
kusano 7d535a
             -4  if N is negative or if SIDE is C or T and N is not equal 
kusano 7d535a
  
kusano 7d535a
                 to M.   
kusano 7d535a
             -6  if LDA is less than M.   
kusano 7d535a
kusano 7d535a
    ===================================================================== 
kusano 7d535a
  
kusano 7d535a
kusano 7d535a
kusano 7d535a
       Parameter adjustments */
kusano 7d535a
    a_dim1 = *lda;
kusano 7d535a
    a_offset = a_dim1 + 1;
kusano 7d535a
    a -= a_offset;
kusano 7d535a
    --iseed;
kusano 7d535a
    --x;
kusano 7d535a
kusano 7d535a
    /* Function Body */
kusano 7d535a
    if (*n == 0 || *m == 0) {
kusano 7d535a
	return 0;
kusano 7d535a
    }
kusano 7d535a
kusano 7d535a
    itype = 0;
kusano 7d535a
    if (lsame_(side, "L")) {
kusano 7d535a
	itype = 1;
kusano 7d535a
    } else if (lsame_(side, "R")) {
kusano 7d535a
	itype = 2;
kusano 7d535a
    } else if (lsame_(side, "C")) {
kusano 7d535a
	itype = 3;
kusano 7d535a
    } else if (lsame_(side, "T")) {
kusano 7d535a
	itype = 4;
kusano 7d535a
    }
kusano 7d535a
kusano 7d535a
/*     Check for argument errors. */
kusano 7d535a
kusano 7d535a
    *info = 0;
kusano 7d535a
    if (itype == 0) {
kusano 7d535a
	*info = -1;
kusano 7d535a
    } else if (*m < 0) {
kusano 7d535a
	*info = -3;
kusano 7d535a
    } else if (*n < 0 || itype == 3 && *n != *m) {
kusano 7d535a
	*info = -4;
kusano 7d535a
    } else if (*lda < *m) {
kusano 7d535a
	*info = -6;
kusano 7d535a
    }
kusano 7d535a
    if (*info != 0) {
kusano 7d535a
	i__1 = -(*info);
kusano 7d535a
	xerbla_("CLAROR", &i__1);
kusano 7d535a
	return 0;
kusano 7d535a
    }
kusano 7d535a
kusano 7d535a
    if (itype == 1) {
kusano 7d535a
	nxfrm = *m;
kusano 7d535a
    } else {
kusano 7d535a
	nxfrm = *n;
kusano 7d535a
    }
kusano 7d535a
kusano 7d535a
/*     Initialize A to the identity matrix if desired */
kusano 7d535a
kusano 7d535a
    if (lsame_(init, "I")) {
kusano 7d535a
	claset_("Full", m, n, &c_b1, &c_b2, &a[a_offset], lda);
kusano 7d535a
    }
kusano 7d535a
kusano 7d535a
/*     If no rotation possible, still multiply by   
kusano 7d535a
       a random complex number from the circle |x| = 1   
kusano 7d535a
kusano 7d535a
        2)      Compute Rotation by computing Householder   
kusano 7d535a
                Transformations H(2), H(3), ..., H(n).  Note that the   
kusano 7d535a
                order in which they are computed is irrelevant. */
kusano 7d535a
kusano 7d535a
    i__1 = nxfrm;
kusano 7d535a
    for (j = 1; j <= i__1; ++j) {
kusano 7d535a
	i__2 = j;
kusano 7d535a
	x[i__2].r = 0.f, x[i__2].i = 0.f;
kusano 7d535a
/* L40: */
kusano 7d535a
    }
kusano 7d535a
kusano 7d535a
    i__1 = nxfrm;
kusano 7d535a
    for (ixfrm = 2; ixfrm <= i__1; ++ixfrm) {
kusano 7d535a
	kbeg = nxfrm - ixfrm + 1;
kusano 7d535a
kusano 7d535a
/*        Generate independent normal( 0, 1 ) random numbers */
kusano 7d535a
kusano 7d535a
	i__2 = nxfrm;
kusano 7d535a
	for (j = kbeg; j <= i__2; ++j) {
kusano 7d535a
	    i__3 = j;
kusano 7d535a
	    clarnd_(&q__1, &c__3, &iseed[1]);
kusano 7d535a
	    x[i__3].r = q__1.r, x[i__3].i = q__1.i;
kusano 7d535a
/* L50: */
kusano 7d535a
	}
kusano 7d535a
kusano 7d535a
/*        Generate a Householder transformation from the random vector
kusano 7d535a
 X */
kusano 7d535a
kusano 7d535a
	xnorm = scnrm2_(&ixfrm, &x[kbeg], &c__1);
kusano 7d535a
	xabs = c_abs(&x[kbeg]);
kusano 7d535a
	if (xabs != 0.f) {
kusano 7d535a
	    i__2 = kbeg;
kusano 7d535a
	    q__1.r = x[i__2].r / xabs, q__1.i = x[i__2].i / xabs;
kusano 7d535a
	    csign.r = q__1.r, csign.i = q__1.i;
kusano 7d535a
	} else {
kusano 7d535a
	    csign.r = 1.f, csign.i = 0.f;
kusano 7d535a
	}
kusano 7d535a
	q__1.r = xnorm * csign.r, q__1.i = xnorm * csign.i;
kusano 7d535a
	xnorms.r = q__1.r, xnorms.i = q__1.i;
kusano 7d535a
	i__2 = nxfrm + kbeg;
kusano 7d535a
	q__1.r = -(doublereal)csign.r, q__1.i = -(doublereal)csign.i;
kusano 7d535a
	x[i__2].r = q__1.r, x[i__2].i = q__1.i;
kusano 7d535a
	factor = xnorm * (xnorm + xabs);
kusano 7d535a
	if (dabs(factor) < 1e-20f) {
kusano 7d535a
	    *info = 1;
kusano 7d535a
	    i__2 = -(*info);
kusano 7d535a
	    xerbla_("CLAROR", &i__2);
kusano 7d535a
	    return 0;
kusano 7d535a
	} else {
kusano 7d535a
	    factor = 1.f / factor;
kusano 7d535a
	}
kusano 7d535a
	i__2 = kbeg;
kusano 7d535a
	i__3 = kbeg;
kusano 7d535a
	q__1.r = x[i__3].r + xnorms.r, q__1.i = x[i__3].i + xnorms.i;
kusano 7d535a
	x[i__2].r = q__1.r, x[i__2].i = q__1.i;
kusano 7d535a
kusano 7d535a
/*        Apply Householder transformation to A */
kusano 7d535a
kusano 7d535a
	if (itype == 1 || itype == 3 || itype == 4) {
kusano 7d535a
kusano 7d535a
/*           Apply H(k) on the left of A */
kusano 7d535a
kusano 7d535a
	    cgemv_("C", &ixfrm, n, &c_b2, &a[kbeg + a_dim1], lda, &x[kbeg], &
kusano 7d535a
		    c__1, &c_b1, &x[(nxfrm << 1) + 1], &c__1);
kusano 7d535a
	    q__2.r = factor, q__2.i = 0.f;
kusano 7d535a
	    q__1.r = -(doublereal)q__2.r, q__1.i = -(doublereal)q__2.i;
kusano 7d535a
	    cgerc_(&ixfrm, n, &q__1, &x[kbeg], &c__1, &x[(nxfrm << 1) + 1], &
kusano 7d535a
		    c__1, &a[kbeg + a_dim1], lda);
kusano 7d535a
kusano 7d535a
	}
kusano 7d535a
kusano 7d535a
	if (itype >= 2 && itype <= 4) {
kusano 7d535a
kusano 7d535a
/*           Apply H(k)* (or H(k)') on the right of A */
kusano 7d535a
kusano 7d535a
	    if (itype == 4) {
kusano 7d535a
		clacgv_(&ixfrm, &x[kbeg], &c__1);
kusano 7d535a
	    }
kusano 7d535a
kusano 7d535a
	    cgemv_("N", m, &ixfrm, &c_b2, &a[kbeg * a_dim1 + 1], lda, &x[kbeg]
kusano 7d535a
		    , &c__1, &c_b1, &x[(nxfrm << 1) + 1], &c__1);
kusano 7d535a
	    q__2.r = factor, q__2.i = 0.f;
kusano 7d535a
	    q__1.r = -(doublereal)q__2.r, q__1.i = -(doublereal)q__2.i;
kusano 7d535a
	    cgerc_(m, &ixfrm, &q__1, &x[(nxfrm << 1) + 1], &c__1, &x[kbeg], &
kusano 7d535a
		    c__1, &a[kbeg * a_dim1 + 1], lda);
kusano 7d535a
kusano 7d535a
	}
kusano 7d535a
/* L60: */
kusano 7d535a
    }
kusano 7d535a
kusano 7d535a
    clarnd_(&q__1, &c__3, &iseed[1]);
kusano 7d535a
    x[1].r = q__1.r, x[1].i = q__1.i;
kusano 7d535a
    xabs = c_abs(&x[1]);
kusano 7d535a
    if (xabs != 0.f) {
kusano 7d535a
	q__1.r = x[1].r / xabs, q__1.i = x[1].i / xabs;
kusano 7d535a
	csign.r = q__1.r, csign.i = q__1.i;
kusano 7d535a
    } else {
kusano 7d535a
	csign.r = 1.f, csign.i = 0.f;
kusano 7d535a
    }
kusano 7d535a
    i__1 = nxfrm << 1;
kusano 7d535a
    x[i__1].r = csign.r, x[i__1].i = csign.i;
kusano 7d535a
kusano 7d535a
/*     Scale the matrix A by D. */
kusano 7d535a
kusano 7d535a
    if (itype == 1 || itype == 3 || itype == 4) {
kusano 7d535a
	i__1 = *m;
kusano 7d535a
	for (irow = 1; irow <= i__1; ++irow) {
kusano 7d535a
	    r_cnjg(&q__1, &x[nxfrm + irow]);
kusano 7d535a
	    cscal_(n, &q__1, &a[irow + a_dim1], lda);
kusano 7d535a
/* L70: */
kusano 7d535a
	}
kusano 7d535a
    }
kusano 7d535a
kusano 7d535a
    if (itype == 2 || itype == 3) {
kusano 7d535a
	i__1 = *n;
kusano 7d535a
	for (jcol = 1; jcol <= i__1; ++jcol) {
kusano 7d535a
	    cscal_(m, &x[nxfrm + jcol], &a[jcol * a_dim1 + 1], &c__1);
kusano 7d535a
/* L80: */
kusano 7d535a
	}
kusano 7d535a
    }
kusano 7d535a
kusano 7d535a
    if (itype == 4) {
kusano 7d535a
	i__1 = *n;
kusano 7d535a
	for (jcol = 1; jcol <= i__1; ++jcol) {
kusano 7d535a
	    r_cnjg(&q__1, &x[nxfrm + jcol]);
kusano 7d535a
	    cscal_(m, &q__1, &a[jcol * a_dim1 + 1], &c__1);
kusano 7d535a
/* L90: */
kusano 7d535a
	}
kusano 7d535a
    }
kusano 7d535a
    return 0;
kusano 7d535a
kusano 7d535a
/*     End of CLAROR */
kusano 7d535a
kusano 7d535a
} /* claror_ */
kusano 7d535a