annotate ext/clapack/src/dgetri.c @ 209:ccd2019190bf msvc

Some MSVC fixes, including (temporarily, probably) renaming the FFT source file to avoid getting it mixed up with the Vamp SDK one in our object dir
author Chris Cannam
date Thu, 01 Feb 2018 16:34:08 +0000
parents 45330e0d2819
children
rev   line source
Chris@202 1 /* dgetri.f -- translated by f2c (version 20061008).
Chris@202 2 You must link the resulting object file with libf2c:
Chris@202 3 on Microsoft Windows system, link with libf2c.lib;
Chris@202 4 on Linux or Unix systems, link with .../path/to/libf2c.a -lm
Chris@202 5 or, if you install libf2c.a in a standard place, with -lf2c -lm
Chris@202 6 -- in that order, at the end of the command line, as in
Chris@202 7 cc *.o -lf2c -lm
Chris@202 8 Source for libf2c is in /netlib/f2c/libf2c.zip, e.g.,
Chris@202 9
Chris@202 10 http://www.netlib.org/f2c/libf2c.zip
Chris@202 11 */
Chris@202 12
Chris@202 13 #include "f2c.h"
Chris@202 14 #include "blaswrap.h"
Chris@202 15
Chris@202 16 /* Table of constant values */
Chris@202 17
Chris@202 18 static integer c__1 = 1;
Chris@202 19 static integer c_n1 = -1;
Chris@202 20 static integer c__2 = 2;
Chris@202 21 static doublereal c_b20 = -1.;
Chris@202 22 static doublereal c_b22 = 1.;
Chris@202 23
Chris@202 24 /* Subroutine */ int dgetri_(integer *n, doublereal *a, integer *lda, integer
Chris@202 25 *ipiv, doublereal *work, integer *lwork, integer *info)
Chris@202 26 {
Chris@202 27 /* System generated locals */
Chris@202 28 integer a_dim1, a_offset, i__1, i__2, i__3;
Chris@202 29
Chris@202 30 /* Local variables */
Chris@202 31 integer i__, j, jb, nb, jj, jp, nn, iws;
Chris@202 32 extern /* Subroutine */ int dgemm_(char *, char *, integer *, integer *,
Chris@202 33 integer *, doublereal *, doublereal *, integer *, doublereal *,
Chris@202 34 integer *, doublereal *, doublereal *, integer *),
Chris@202 35 dgemv_(char *, integer *, integer *, doublereal *, doublereal *,
Chris@202 36 integer *, doublereal *, integer *, doublereal *, doublereal *,
Chris@202 37 integer *);
Chris@202 38 integer nbmin;
Chris@202 39 extern /* Subroutine */ int dswap_(integer *, doublereal *, integer *,
Chris@202 40 doublereal *, integer *), dtrsm_(char *, char *, char *, char *,
Chris@202 41 integer *, integer *, doublereal *, doublereal *, integer *,
Chris@202 42 doublereal *, integer *), xerbla_(
Chris@202 43 char *, integer *);
Chris@202 44 extern integer ilaenv_(integer *, char *, char *, integer *, integer *,
Chris@202 45 integer *, integer *);
Chris@202 46 integer ldwork;
Chris@202 47 extern /* Subroutine */ int dtrtri_(char *, char *, integer *, doublereal
Chris@202 48 *, integer *, integer *);
Chris@202 49 integer lwkopt;
Chris@202 50 logical lquery;
Chris@202 51
Chris@202 52
Chris@202 53 /* -- LAPACK routine (version 3.2) -- */
Chris@202 54 /* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd.. */
Chris@202 55 /* November 2006 */
Chris@202 56
Chris@202 57 /* .. Scalar Arguments .. */
Chris@202 58 /* .. */
Chris@202 59 /* .. Array Arguments .. */
Chris@202 60 /* .. */
Chris@202 61
Chris@202 62 /* Purpose */
Chris@202 63 /* ======= */
Chris@202 64
Chris@202 65 /* DGETRI computes the inverse of a matrix using the LU factorization */
Chris@202 66 /* computed by DGETRF. */
Chris@202 67
Chris@202 68 /* This method inverts U and then computes inv(A) by solving the system */
Chris@202 69 /* inv(A)*L = inv(U) for inv(A). */
Chris@202 70
Chris@202 71 /* Arguments */
Chris@202 72 /* ========= */
Chris@202 73
Chris@202 74 /* N (input) INTEGER */
Chris@202 75 /* The order of the matrix A. N >= 0. */
Chris@202 76
Chris@202 77 /* A (input/output) DOUBLE PRECISION array, dimension (LDA,N) */
Chris@202 78 /* On entry, the factors L and U from the factorization */
Chris@202 79 /* A = P*L*U as computed by DGETRF. */
Chris@202 80 /* On exit, if INFO = 0, the inverse of the original matrix A. */
Chris@202 81
Chris@202 82 /* LDA (input) INTEGER */
Chris@202 83 /* The leading dimension of the array A. LDA >= max(1,N). */
Chris@202 84
Chris@202 85 /* IPIV (input) INTEGER array, dimension (N) */
Chris@202 86 /* The pivot indices from DGETRF; for 1<=i<=N, row i of the */
Chris@202 87 /* matrix was interchanged with row IPIV(i). */
Chris@202 88
Chris@202 89 /* WORK (workspace/output) DOUBLE PRECISION array, dimension (MAX(1,LWORK)) */
Chris@202 90 /* On exit, if INFO=0, then WORK(1) returns the optimal LWORK. */
Chris@202 91
Chris@202 92 /* LWORK (input) INTEGER */
Chris@202 93 /* The dimension of the array WORK. LWORK >= max(1,N). */
Chris@202 94 /* For optimal performance LWORK >= N*NB, where NB is */
Chris@202 95 /* the optimal blocksize returned by ILAENV. */
Chris@202 96
Chris@202 97 /* If LWORK = -1, then a workspace query is assumed; the routine */
Chris@202 98 /* only calculates the optimal size of the WORK array, returns */
Chris@202 99 /* this value as the first entry of the WORK array, and no error */
Chris@202 100 /* message related to LWORK is issued by XERBLA. */
Chris@202 101
Chris@202 102 /* INFO (output) INTEGER */
Chris@202 103 /* = 0: successful exit */
Chris@202 104 /* < 0: if INFO = -i, the i-th argument had an illegal value */
Chris@202 105 /* > 0: if INFO = i, U(i,i) is exactly zero; the matrix is */
Chris@202 106 /* singular and its inverse could not be computed. */
Chris@202 107
Chris@202 108 /* ===================================================================== */
Chris@202 109
Chris@202 110 /* .. Parameters .. */
Chris@202 111 /* .. */
Chris@202 112 /* .. Local Scalars .. */
Chris@202 113 /* .. */
Chris@202 114 /* .. External Functions .. */
Chris@202 115 /* .. */
Chris@202 116 /* .. External Subroutines .. */
Chris@202 117 /* .. */
Chris@202 118 /* .. Intrinsic Functions .. */
Chris@202 119 /* .. */
Chris@202 120 /* .. Executable Statements .. */
Chris@202 121
Chris@202 122 /* Test the input parameters. */
Chris@202 123
Chris@202 124 /* Parameter adjustments */
Chris@202 125 a_dim1 = *lda;
Chris@202 126 a_offset = 1 + a_dim1;
Chris@202 127 a -= a_offset;
Chris@202 128 --ipiv;
Chris@202 129 --work;
Chris@202 130
Chris@202 131 /* Function Body */
Chris@202 132 *info = 0;
Chris@202 133 nb = ilaenv_(&c__1, "DGETRI", " ", n, &c_n1, &c_n1, &c_n1);
Chris@202 134 lwkopt = *n * nb;
Chris@202 135 work[1] = (doublereal) lwkopt;
Chris@202 136 lquery = *lwork == -1;
Chris@202 137 if (*n < 0) {
Chris@202 138 *info = -1;
Chris@202 139 } else if (*lda < max(1,*n)) {
Chris@202 140 *info = -3;
Chris@202 141 } else if (*lwork < max(1,*n) && ! lquery) {
Chris@202 142 *info = -6;
Chris@202 143 }
Chris@202 144 if (*info != 0) {
Chris@202 145 i__1 = -(*info);
Chris@202 146 xerbla_("DGETRI", &i__1);
Chris@202 147 return 0;
Chris@202 148 } else if (lquery) {
Chris@202 149 return 0;
Chris@202 150 }
Chris@202 151
Chris@202 152 /* Quick return if possible */
Chris@202 153
Chris@202 154 if (*n == 0) {
Chris@202 155 return 0;
Chris@202 156 }
Chris@202 157
Chris@202 158 /* Form inv(U). If INFO > 0 from DTRTRI, then U is singular, */
Chris@202 159 /* and the inverse is not computed. */
Chris@202 160
Chris@202 161 dtrtri_("Upper", "Non-unit", n, &a[a_offset], lda, info);
Chris@202 162 if (*info > 0) {
Chris@202 163 return 0;
Chris@202 164 }
Chris@202 165
Chris@202 166 nbmin = 2;
Chris@202 167 ldwork = *n;
Chris@202 168 if (nb > 1 && nb < *n) {
Chris@202 169 /* Computing MAX */
Chris@202 170 i__1 = ldwork * nb;
Chris@202 171 iws = max(i__1,1);
Chris@202 172 if (*lwork < iws) {
Chris@202 173 nb = *lwork / ldwork;
Chris@202 174 /* Computing MAX */
Chris@202 175 i__1 = 2, i__2 = ilaenv_(&c__2, "DGETRI", " ", n, &c_n1, &c_n1, &
Chris@202 176 c_n1);
Chris@202 177 nbmin = max(i__1,i__2);
Chris@202 178 }
Chris@202 179 } else {
Chris@202 180 iws = *n;
Chris@202 181 }
Chris@202 182
Chris@202 183 /* Solve the equation inv(A)*L = inv(U) for inv(A). */
Chris@202 184
Chris@202 185 if (nb < nbmin || nb >= *n) {
Chris@202 186
Chris@202 187 /* Use unblocked code. */
Chris@202 188
Chris@202 189 for (j = *n; j >= 1; --j) {
Chris@202 190
Chris@202 191 /* Copy current column of L to WORK and replace with zeros. */
Chris@202 192
Chris@202 193 i__1 = *n;
Chris@202 194 for (i__ = j + 1; i__ <= i__1; ++i__) {
Chris@202 195 work[i__] = a[i__ + j * a_dim1];
Chris@202 196 a[i__ + j * a_dim1] = 0.;
Chris@202 197 /* L10: */
Chris@202 198 }
Chris@202 199
Chris@202 200 /* Compute current column of inv(A). */
Chris@202 201
Chris@202 202 if (j < *n) {
Chris@202 203 i__1 = *n - j;
Chris@202 204 dgemv_("No transpose", n, &i__1, &c_b20, &a[(j + 1) * a_dim1
Chris@202 205 + 1], lda, &work[j + 1], &c__1, &c_b22, &a[j * a_dim1
Chris@202 206 + 1], &c__1);
Chris@202 207 }
Chris@202 208 /* L20: */
Chris@202 209 }
Chris@202 210 } else {
Chris@202 211
Chris@202 212 /* Use blocked code. */
Chris@202 213
Chris@202 214 nn = (*n - 1) / nb * nb + 1;
Chris@202 215 i__1 = -nb;
Chris@202 216 for (j = nn; i__1 < 0 ? j >= 1 : j <= 1; j += i__1) {
Chris@202 217 /* Computing MIN */
Chris@202 218 i__2 = nb, i__3 = *n - j + 1;
Chris@202 219 jb = min(i__2,i__3);
Chris@202 220
Chris@202 221 /* Copy current block column of L to WORK and replace with */
Chris@202 222 /* zeros. */
Chris@202 223
Chris@202 224 i__2 = j + jb - 1;
Chris@202 225 for (jj = j; jj <= i__2; ++jj) {
Chris@202 226 i__3 = *n;
Chris@202 227 for (i__ = jj + 1; i__ <= i__3; ++i__) {
Chris@202 228 work[i__ + (jj - j) * ldwork] = a[i__ + jj * a_dim1];
Chris@202 229 a[i__ + jj * a_dim1] = 0.;
Chris@202 230 /* L30: */
Chris@202 231 }
Chris@202 232 /* L40: */
Chris@202 233 }
Chris@202 234
Chris@202 235 /* Compute current block column of inv(A). */
Chris@202 236
Chris@202 237 if (j + jb <= *n) {
Chris@202 238 i__2 = *n - j - jb + 1;
Chris@202 239 dgemm_("No transpose", "No transpose", n, &jb, &i__2, &c_b20,
Chris@202 240 &a[(j + jb) * a_dim1 + 1], lda, &work[j + jb], &
Chris@202 241 ldwork, &c_b22, &a[j * a_dim1 + 1], lda);
Chris@202 242 }
Chris@202 243 dtrsm_("Right", "Lower", "No transpose", "Unit", n, &jb, &c_b22, &
Chris@202 244 work[j], &ldwork, &a[j * a_dim1 + 1], lda);
Chris@202 245 /* L50: */
Chris@202 246 }
Chris@202 247 }
Chris@202 248
Chris@202 249 /* Apply column interchanges. */
Chris@202 250
Chris@202 251 for (j = *n - 1; j >= 1; --j) {
Chris@202 252 jp = ipiv[j];
Chris@202 253 if (jp != j) {
Chris@202 254 dswap_(n, &a[j * a_dim1 + 1], &c__1, &a[jp * a_dim1 + 1], &c__1);
Chris@202 255 }
Chris@202 256 /* L60: */
Chris@202 257 }
Chris@202 258
Chris@202 259 work[1] = (doublereal) iws;
Chris@202 260 return 0;
Chris@202 261
Chris@202 262 /* End of DGETRI */
Chris@202 263
Chris@202 264 } /* dgetri_ */