00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013 #include "f2c.h"
00014 #include "blaswrap.h"
00015
00016
00017
00018 static doublecomplex c_b2 = {0.,0.};
00019 static integer c__1 = 1;
00020
00021 int zhptri_(char *uplo, integer *n, doublecomplex *ap,
00022 integer *ipiv, doublecomplex *work, integer *info)
00023 {
00024
00025 integer i__1, i__2, i__3;
00026 doublereal d__1;
00027 doublecomplex z__1, z__2;
00028
00029
00030 double z_abs(doublecomplex *);
00031 void d_cnjg(doublecomplex *, doublecomplex *);
00032
00033
00034 doublereal d__;
00035 integer j, k;
00036 doublereal t, ak;
00037 integer kc, kp, kx, kpc, npp;
00038 doublereal akp1;
00039 doublecomplex temp, akkp1;
00040 extern logical lsame_(char *, char *);
00041 extern VOID zdotc_(doublecomplex *, integer *,
00042 doublecomplex *, integer *, doublecomplex *, integer *);
00043 integer kstep;
00044 logical upper;
00045 extern int zcopy_(integer *, doublecomplex *, integer *,
00046 doublecomplex *, integer *), zhpmv_(char *, integer *,
00047 doublecomplex *, doublecomplex *, doublecomplex *, integer *,
00048 doublecomplex *, doublecomplex *, integer *), zswap_(
00049 integer *, doublecomplex *, integer *, doublecomplex *, integer *)
00050 , xerbla_(char *, integer *);
00051 integer kcnext;
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102
00103
00104
00105
00106
00107
00108
00109
00110
00111
00112
00113
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123 --work;
00124 --ipiv;
00125 --ap;
00126
00127
00128 *info = 0;
00129 upper = lsame_(uplo, "U");
00130 if (! upper && ! lsame_(uplo, "L")) {
00131 *info = -1;
00132 } else if (*n < 0) {
00133 *info = -2;
00134 }
00135 if (*info != 0) {
00136 i__1 = -(*info);
00137 xerbla_("ZHPTRI", &i__1);
00138 return 0;
00139 }
00140
00141
00142
00143 if (*n == 0) {
00144 return 0;
00145 }
00146
00147
00148
00149 if (upper) {
00150
00151
00152
00153 kp = *n * (*n + 1) / 2;
00154 for (*info = *n; *info >= 1; --(*info)) {
00155 i__1 = kp;
00156 if (ipiv[*info] > 0 && (ap[i__1].r == 0. && ap[i__1].i == 0.)) {
00157 return 0;
00158 }
00159 kp -= *info;
00160
00161 }
00162 } else {
00163
00164
00165
00166 kp = 1;
00167 i__1 = *n;
00168 for (*info = 1; *info <= i__1; ++(*info)) {
00169 i__2 = kp;
00170 if (ipiv[*info] > 0 && (ap[i__2].r == 0. && ap[i__2].i == 0.)) {
00171 return 0;
00172 }
00173 kp = kp + *n - *info + 1;
00174
00175 }
00176 }
00177 *info = 0;
00178
00179 if (upper) {
00180
00181
00182
00183
00184
00185
00186 k = 1;
00187 kc = 1;
00188 L30:
00189
00190
00191
00192 if (k > *n) {
00193 goto L50;
00194 }
00195
00196 kcnext = kc + k;
00197 if (ipiv[k] > 0) {
00198
00199
00200
00201
00202
00203 i__1 = kc + k - 1;
00204 i__2 = kc + k - 1;
00205 d__1 = 1. / ap[i__2].r;
00206 ap[i__1].r = d__1, ap[i__1].i = 0.;
00207
00208
00209
00210 if (k > 1) {
00211 i__1 = k - 1;
00212 zcopy_(&i__1, &ap[kc], &c__1, &work[1], &c__1);
00213 i__1 = k - 1;
00214 z__1.r = -1., z__1.i = -0.;
00215 zhpmv_(uplo, &i__1, &z__1, &ap[1], &work[1], &c__1, &c_b2, &
00216 ap[kc], &c__1);
00217 i__1 = kc + k - 1;
00218 i__2 = kc + k - 1;
00219 i__3 = k - 1;
00220 zdotc_(&z__2, &i__3, &work[1], &c__1, &ap[kc], &c__1);
00221 d__1 = z__2.r;
00222 z__1.r = ap[i__2].r - d__1, z__1.i = ap[i__2].i;
00223 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00224 }
00225 kstep = 1;
00226 } else {
00227
00228
00229
00230
00231
00232 t = z_abs(&ap[kcnext + k - 1]);
00233 i__1 = kc + k - 1;
00234 ak = ap[i__1].r / t;
00235 i__1 = kcnext + k;
00236 akp1 = ap[i__1].r / t;
00237 i__1 = kcnext + k - 1;
00238 z__1.r = ap[i__1].r / t, z__1.i = ap[i__1].i / t;
00239 akkp1.r = z__1.r, akkp1.i = z__1.i;
00240 d__ = t * (ak * akp1 - 1.);
00241 i__1 = kc + k - 1;
00242 d__1 = akp1 / d__;
00243 ap[i__1].r = d__1, ap[i__1].i = 0.;
00244 i__1 = kcnext + k;
00245 d__1 = ak / d__;
00246 ap[i__1].r = d__1, ap[i__1].i = 0.;
00247 i__1 = kcnext + k - 1;
00248 z__2.r = -akkp1.r, z__2.i = -akkp1.i;
00249 z__1.r = z__2.r / d__, z__1.i = z__2.i / d__;
00250 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00251
00252
00253
00254 if (k > 1) {
00255 i__1 = k - 1;
00256 zcopy_(&i__1, &ap[kc], &c__1, &work[1], &c__1);
00257 i__1 = k - 1;
00258 z__1.r = -1., z__1.i = -0.;
00259 zhpmv_(uplo, &i__1, &z__1, &ap[1], &work[1], &c__1, &c_b2, &
00260 ap[kc], &c__1);
00261 i__1 = kc + k - 1;
00262 i__2 = kc + k - 1;
00263 i__3 = k - 1;
00264 zdotc_(&z__2, &i__3, &work[1], &c__1, &ap[kc], &c__1);
00265 d__1 = z__2.r;
00266 z__1.r = ap[i__2].r - d__1, z__1.i = ap[i__2].i;
00267 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00268 i__1 = kcnext + k - 1;
00269 i__2 = kcnext + k - 1;
00270 i__3 = k - 1;
00271 zdotc_(&z__2, &i__3, &ap[kc], &c__1, &ap[kcnext], &c__1);
00272 z__1.r = ap[i__2].r - z__2.r, z__1.i = ap[i__2].i - z__2.i;
00273 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00274 i__1 = k - 1;
00275 zcopy_(&i__1, &ap[kcnext], &c__1, &work[1], &c__1);
00276 i__1 = k - 1;
00277 z__1.r = -1., z__1.i = -0.;
00278 zhpmv_(uplo, &i__1, &z__1, &ap[1], &work[1], &c__1, &c_b2, &
00279 ap[kcnext], &c__1);
00280 i__1 = kcnext + k;
00281 i__2 = kcnext + k;
00282 i__3 = k - 1;
00283 zdotc_(&z__2, &i__3, &work[1], &c__1, &ap[kcnext], &c__1);
00284 d__1 = z__2.r;
00285 z__1.r = ap[i__2].r - d__1, z__1.i = ap[i__2].i;
00286 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00287 }
00288 kstep = 2;
00289 kcnext = kcnext + k + 1;
00290 }
00291
00292 kp = (i__1 = ipiv[k], abs(i__1));
00293 if (kp != k) {
00294
00295
00296
00297
00298 kpc = (kp - 1) * kp / 2 + 1;
00299 i__1 = kp - 1;
00300 zswap_(&i__1, &ap[kc], &c__1, &ap[kpc], &c__1);
00301 kx = kpc + kp - 1;
00302 i__1 = k - 1;
00303 for (j = kp + 1; j <= i__1; ++j) {
00304 kx = kx + j - 1;
00305 d_cnjg(&z__1, &ap[kc + j - 1]);
00306 temp.r = z__1.r, temp.i = z__1.i;
00307 i__2 = kc + j - 1;
00308 d_cnjg(&z__1, &ap[kx]);
00309 ap[i__2].r = z__1.r, ap[i__2].i = z__1.i;
00310 i__2 = kx;
00311 ap[i__2].r = temp.r, ap[i__2].i = temp.i;
00312
00313 }
00314 i__1 = kc + kp - 1;
00315 d_cnjg(&z__1, &ap[kc + kp - 1]);
00316 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00317 i__1 = kc + k - 1;
00318 temp.r = ap[i__1].r, temp.i = ap[i__1].i;
00319 i__1 = kc + k - 1;
00320 i__2 = kpc + kp - 1;
00321 ap[i__1].r = ap[i__2].r, ap[i__1].i = ap[i__2].i;
00322 i__1 = kpc + kp - 1;
00323 ap[i__1].r = temp.r, ap[i__1].i = temp.i;
00324 if (kstep == 2) {
00325 i__1 = kc + k + k - 1;
00326 temp.r = ap[i__1].r, temp.i = ap[i__1].i;
00327 i__1 = kc + k + k - 1;
00328 i__2 = kc + k + kp - 1;
00329 ap[i__1].r = ap[i__2].r, ap[i__1].i = ap[i__2].i;
00330 i__1 = kc + k + kp - 1;
00331 ap[i__1].r = temp.r, ap[i__1].i = temp.i;
00332 }
00333 }
00334
00335 k += kstep;
00336 kc = kcnext;
00337 goto L30;
00338 L50:
00339
00340 ;
00341 } else {
00342
00343
00344
00345
00346
00347
00348 npp = *n * (*n + 1) / 2;
00349 k = *n;
00350 kc = npp;
00351 L60:
00352
00353
00354
00355 if (k < 1) {
00356 goto L80;
00357 }
00358
00359 kcnext = kc - (*n - k + 2);
00360 if (ipiv[k] > 0) {
00361
00362
00363
00364
00365
00366 i__1 = kc;
00367 i__2 = kc;
00368 d__1 = 1. / ap[i__2].r;
00369 ap[i__1].r = d__1, ap[i__1].i = 0.;
00370
00371
00372
00373 if (k < *n) {
00374 i__1 = *n - k;
00375 zcopy_(&i__1, &ap[kc + 1], &c__1, &work[1], &c__1);
00376 i__1 = *n - k;
00377 z__1.r = -1., z__1.i = -0.;
00378 zhpmv_(uplo, &i__1, &z__1, &ap[kc + *n - k + 1], &work[1], &
00379 c__1, &c_b2, &ap[kc + 1], &c__1);
00380 i__1 = kc;
00381 i__2 = kc;
00382 i__3 = *n - k;
00383 zdotc_(&z__2, &i__3, &work[1], &c__1, &ap[kc + 1], &c__1);
00384 d__1 = z__2.r;
00385 z__1.r = ap[i__2].r - d__1, z__1.i = ap[i__2].i;
00386 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00387 }
00388 kstep = 1;
00389 } else {
00390
00391
00392
00393
00394
00395 t = z_abs(&ap[kcnext + 1]);
00396 i__1 = kcnext;
00397 ak = ap[i__1].r / t;
00398 i__1 = kc;
00399 akp1 = ap[i__1].r / t;
00400 i__1 = kcnext + 1;
00401 z__1.r = ap[i__1].r / t, z__1.i = ap[i__1].i / t;
00402 akkp1.r = z__1.r, akkp1.i = z__1.i;
00403 d__ = t * (ak * akp1 - 1.);
00404 i__1 = kcnext;
00405 d__1 = akp1 / d__;
00406 ap[i__1].r = d__1, ap[i__1].i = 0.;
00407 i__1 = kc;
00408 d__1 = ak / d__;
00409 ap[i__1].r = d__1, ap[i__1].i = 0.;
00410 i__1 = kcnext + 1;
00411 z__2.r = -akkp1.r, z__2.i = -akkp1.i;
00412 z__1.r = z__2.r / d__, z__1.i = z__2.i / d__;
00413 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00414
00415
00416
00417 if (k < *n) {
00418 i__1 = *n - k;
00419 zcopy_(&i__1, &ap[kc + 1], &c__1, &work[1], &c__1);
00420 i__1 = *n - k;
00421 z__1.r = -1., z__1.i = -0.;
00422 zhpmv_(uplo, &i__1, &z__1, &ap[kc + (*n - k + 1)], &work[1], &
00423 c__1, &c_b2, &ap[kc + 1], &c__1);
00424 i__1 = kc;
00425 i__2 = kc;
00426 i__3 = *n - k;
00427 zdotc_(&z__2, &i__3, &work[1], &c__1, &ap[kc + 1], &c__1);
00428 d__1 = z__2.r;
00429 z__1.r = ap[i__2].r - d__1, z__1.i = ap[i__2].i;
00430 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00431 i__1 = kcnext + 1;
00432 i__2 = kcnext + 1;
00433 i__3 = *n - k;
00434 zdotc_(&z__2, &i__3, &ap[kc + 1], &c__1, &ap[kcnext + 2], &
00435 c__1);
00436 z__1.r = ap[i__2].r - z__2.r, z__1.i = ap[i__2].i - z__2.i;
00437 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00438 i__1 = *n - k;
00439 zcopy_(&i__1, &ap[kcnext + 2], &c__1, &work[1], &c__1);
00440 i__1 = *n - k;
00441 z__1.r = -1., z__1.i = -0.;
00442 zhpmv_(uplo, &i__1, &z__1, &ap[kc + (*n - k + 1)], &work[1], &
00443 c__1, &c_b2, &ap[kcnext + 2], &c__1);
00444 i__1 = kcnext;
00445 i__2 = kcnext;
00446 i__3 = *n - k;
00447 zdotc_(&z__2, &i__3, &work[1], &c__1, &ap[kcnext + 2], &c__1);
00448 d__1 = z__2.r;
00449 z__1.r = ap[i__2].r - d__1, z__1.i = ap[i__2].i;
00450 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00451 }
00452 kstep = 2;
00453 kcnext -= *n - k + 3;
00454 }
00455
00456 kp = (i__1 = ipiv[k], abs(i__1));
00457 if (kp != k) {
00458
00459
00460
00461
00462 kpc = npp - (*n - kp + 1) * (*n - kp + 2) / 2 + 1;
00463 if (kp < *n) {
00464 i__1 = *n - kp;
00465 zswap_(&i__1, &ap[kc + kp - k + 1], &c__1, &ap[kpc + 1], &
00466 c__1);
00467 }
00468 kx = kc + kp - k;
00469 i__1 = kp - 1;
00470 for (j = k + 1; j <= i__1; ++j) {
00471 kx = kx + *n - j + 1;
00472 d_cnjg(&z__1, &ap[kc + j - k]);
00473 temp.r = z__1.r, temp.i = z__1.i;
00474 i__2 = kc + j - k;
00475 d_cnjg(&z__1, &ap[kx]);
00476 ap[i__2].r = z__1.r, ap[i__2].i = z__1.i;
00477 i__2 = kx;
00478 ap[i__2].r = temp.r, ap[i__2].i = temp.i;
00479
00480 }
00481 i__1 = kc + kp - k;
00482 d_cnjg(&z__1, &ap[kc + kp - k]);
00483 ap[i__1].r = z__1.r, ap[i__1].i = z__1.i;
00484 i__1 = kc;
00485 temp.r = ap[i__1].r, temp.i = ap[i__1].i;
00486 i__1 = kc;
00487 i__2 = kpc;
00488 ap[i__1].r = ap[i__2].r, ap[i__1].i = ap[i__2].i;
00489 i__1 = kpc;
00490 ap[i__1].r = temp.r, ap[i__1].i = temp.i;
00491 if (kstep == 2) {
00492 i__1 = kc - *n + k - 1;
00493 temp.r = ap[i__1].r, temp.i = ap[i__1].i;
00494 i__1 = kc - *n + k - 1;
00495 i__2 = kc - *n + kp - 1;
00496 ap[i__1].r = ap[i__2].r, ap[i__1].i = ap[i__2].i;
00497 i__1 = kc - *n + kp - 1;
00498 ap[i__1].r = temp.r, ap[i__1].i = temp.i;
00499 }
00500 }
00501
00502 k -= kstep;
00503 kc = kcnext;
00504 goto L60;
00505 L80:
00506 ;
00507 }
00508
00509 return 0;
00510
00511
00512
00513 }