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 integer c__1 = 1;
00019 static doublereal c_b25 = 1.;
00020 static doublereal c_b27 = 0.;
00021
00022 int dsbgvx_(char *jobz, char *range, char *uplo, integer *n,
00023 integer *ka, integer *kb, doublereal *ab, integer *ldab, doublereal *
00024 bb, integer *ldbb, doublereal *q, integer *ldq, doublereal *vl,
00025 doublereal *vu, integer *il, integer *iu, doublereal *abstol, integer
00026 *m, doublereal *w, doublereal *z__, integer *ldz, doublereal *work,
00027 integer *iwork, integer *ifail, integer *info)
00028 {
00029
00030 integer ab_dim1, ab_offset, bb_dim1, bb_offset, q_dim1, q_offset, z_dim1,
00031 z_offset, i__1, i__2;
00032
00033
00034 integer i__, j, jj;
00035 doublereal tmp1;
00036 integer indd, inde;
00037 char vect[1];
00038 logical test;
00039 integer itmp1, indee;
00040 extern logical lsame_(char *, char *);
00041 extern int dgemv_(char *, integer *, integer *,
00042 doublereal *, doublereal *, integer *, doublereal *, integer *,
00043 doublereal *, doublereal *, integer *);
00044 integer iinfo;
00045 char order[1];
00046 extern int dcopy_(integer *, doublereal *, integer *,
00047 doublereal *, integer *), dswap_(integer *, doublereal *, integer
00048 *, doublereal *, integer *);
00049 logical upper, wantz, alleig, indeig;
00050 integer indibl;
00051 logical valeig;
00052 extern int dlacpy_(char *, integer *, integer *,
00053 doublereal *, integer *, doublereal *, integer *),
00054 xerbla_(char *, integer *), dpbstf_(char *, integer *,
00055 integer *, doublereal *, integer *, integer *), dsbtrd_(
00056 char *, char *, integer *, integer *, doublereal *, integer *,
00057 doublereal *, doublereal *, doublereal *, integer *, doublereal *,
00058 integer *);
00059 integer indisp;
00060 extern int dsbgst_(char *, char *, integer *, integer *,
00061 integer *, doublereal *, integer *, doublereal *, integer *,
00062 doublereal *, integer *, doublereal *, integer *),
00063 dstein_(integer *, doublereal *, doublereal *, integer *,
00064 doublereal *, integer *, integer *, doublereal *, integer *,
00065 doublereal *, integer *, integer *, integer *);
00066 integer indiwo;
00067 extern int dsterf_(integer *, doublereal *, doublereal *,
00068 integer *), dstebz_(char *, char *, integer *, doublereal *,
00069 doublereal *, integer *, integer *, doublereal *, doublereal *,
00070 doublereal *, integer *, integer *, doublereal *, integer *,
00071 integer *, doublereal *, integer *, integer *);
00072 integer indwrk;
00073 extern int dsteqr_(char *, integer *, doublereal *,
00074 doublereal *, doublereal *, integer *, doublereal *, integer *);
00075 integer nsplit;
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
00124
00125
00126
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154
00155
00156
00157
00158
00159
00160
00161
00162
00163
00164
00165
00166
00167
00168
00169
00170
00171
00172
00173
00174
00175
00176
00177
00178
00179
00180
00181
00182
00183
00184
00185
00186
00187
00188
00189
00190
00191
00192
00193
00194
00195
00196
00197
00198
00199
00200
00201
00202
00203
00204
00205
00206
00207
00208
00209
00210
00211
00212
00213
00214
00215
00216
00217
00218
00219
00220
00221
00222
00223
00224
00225
00226
00227
00228
00229
00230
00231
00232
00233
00234
00235
00236
00237
00238
00239
00240
00241
00242
00243
00244
00245
00246
00247
00248
00249
00250
00251
00252
00253
00254
00255
00256 ab_dim1 = *ldab;
00257 ab_offset = 1 + ab_dim1;
00258 ab -= ab_offset;
00259 bb_dim1 = *ldbb;
00260 bb_offset = 1 + bb_dim1;
00261 bb -= bb_offset;
00262 q_dim1 = *ldq;
00263 q_offset = 1 + q_dim1;
00264 q -= q_offset;
00265 --w;
00266 z_dim1 = *ldz;
00267 z_offset = 1 + z_dim1;
00268 z__ -= z_offset;
00269 --work;
00270 --iwork;
00271 --ifail;
00272
00273
00274 wantz = lsame_(jobz, "V");
00275 upper = lsame_(uplo, "U");
00276 alleig = lsame_(range, "A");
00277 valeig = lsame_(range, "V");
00278 indeig = lsame_(range, "I");
00279
00280 *info = 0;
00281 if (! (wantz || lsame_(jobz, "N"))) {
00282 *info = -1;
00283 } else if (! (alleig || valeig || indeig)) {
00284 *info = -2;
00285 } else if (! (upper || lsame_(uplo, "L"))) {
00286 *info = -3;
00287 } else if (*n < 0) {
00288 *info = -4;
00289 } else if (*ka < 0) {
00290 *info = -5;
00291 } else if (*kb < 0 || *kb > *ka) {
00292 *info = -6;
00293 } else if (*ldab < *ka + 1) {
00294 *info = -8;
00295 } else if (*ldbb < *kb + 1) {
00296 *info = -10;
00297 } else if (*ldq < 1 || wantz && *ldq < *n) {
00298 *info = -12;
00299 } else {
00300 if (valeig) {
00301 if (*n > 0 && *vu <= *vl) {
00302 *info = -14;
00303 }
00304 } else if (indeig) {
00305 if (*il < 1 || *il > max(1,*n)) {
00306 *info = -15;
00307 } else if (*iu < min(*n,*il) || *iu > *n) {
00308 *info = -16;
00309 }
00310 }
00311 }
00312 if (*info == 0) {
00313 if (*ldz < 1 || wantz && *ldz < *n) {
00314 *info = -21;
00315 }
00316 }
00317
00318 if (*info != 0) {
00319 i__1 = -(*info);
00320 xerbla_("DSBGVX", &i__1);
00321 return 0;
00322 }
00323
00324
00325
00326 *m = 0;
00327 if (*n == 0) {
00328 return 0;
00329 }
00330
00331
00332
00333 dpbstf_(uplo, n, kb, &bb[bb_offset], ldbb, info);
00334 if (*info != 0) {
00335 *info = *n + *info;
00336 return 0;
00337 }
00338
00339
00340
00341 dsbgst_(jobz, uplo, n, ka, kb, &ab[ab_offset], ldab, &bb[bb_offset], ldbb,
00342 &q[q_offset], ldq, &work[1], &iinfo);
00343
00344
00345
00346 indd = 1;
00347 inde = indd + *n;
00348 indwrk = inde + *n;
00349 if (wantz) {
00350 *(unsigned char *)vect = 'U';
00351 } else {
00352 *(unsigned char *)vect = 'N';
00353 }
00354 dsbtrd_(vect, uplo, n, ka, &ab[ab_offset], ldab, &work[indd], &work[inde],
00355 &q[q_offset], ldq, &work[indwrk], &iinfo);
00356
00357
00358
00359
00360
00361 test = FALSE_;
00362 if (indeig) {
00363 if (*il == 1 && *iu == *n) {
00364 test = TRUE_;
00365 }
00366 }
00367 if ((alleig || test) && *abstol <= 0.) {
00368 dcopy_(n, &work[indd], &c__1, &w[1], &c__1);
00369 indee = indwrk + (*n << 1);
00370 i__1 = *n - 1;
00371 dcopy_(&i__1, &work[inde], &c__1, &work[indee], &c__1);
00372 if (! wantz) {
00373 dsterf_(n, &w[1], &work[indee], info);
00374 } else {
00375 dlacpy_("A", n, n, &q[q_offset], ldq, &z__[z_offset], ldz);
00376 dsteqr_(jobz, n, &w[1], &work[indee], &z__[z_offset], ldz, &work[
00377 indwrk], info);
00378 if (*info == 0) {
00379 i__1 = *n;
00380 for (i__ = 1; i__ <= i__1; ++i__) {
00381 ifail[i__] = 0;
00382
00383 }
00384 }
00385 }
00386 if (*info == 0) {
00387 *m = *n;
00388 goto L30;
00389 }
00390 *info = 0;
00391 }
00392
00393
00394
00395
00396 if (wantz) {
00397 *(unsigned char *)order = 'B';
00398 } else {
00399 *(unsigned char *)order = 'E';
00400 }
00401 indibl = 1;
00402 indisp = indibl + *n;
00403 indiwo = indisp + *n;
00404 dstebz_(range, order, n, vl, vu, il, iu, abstol, &work[indd], &work[inde],
00405 m, &nsplit, &w[1], &iwork[indibl], &iwork[indisp], &work[indwrk],
00406 &iwork[indiwo], info);
00407
00408 if (wantz) {
00409 dstein_(n, &work[indd], &work[inde], m, &w[1], &iwork[indibl], &iwork[
00410 indisp], &z__[z_offset], ldz, &work[indwrk], &iwork[indiwo], &
00411 ifail[1], info);
00412
00413
00414
00415
00416 i__1 = *m;
00417 for (j = 1; j <= i__1; ++j) {
00418 dcopy_(n, &z__[j * z_dim1 + 1], &c__1, &work[1], &c__1);
00419 dgemv_("N", n, n, &c_b25, &q[q_offset], ldq, &work[1], &c__1, &
00420 c_b27, &z__[j * z_dim1 + 1], &c__1);
00421
00422 }
00423 }
00424
00425 L30:
00426
00427
00428
00429
00430 if (wantz) {
00431 i__1 = *m - 1;
00432 for (j = 1; j <= i__1; ++j) {
00433 i__ = 0;
00434 tmp1 = w[j];
00435 i__2 = *m;
00436 for (jj = j + 1; jj <= i__2; ++jj) {
00437 if (w[jj] < tmp1) {
00438 i__ = jj;
00439 tmp1 = w[jj];
00440 }
00441
00442 }
00443
00444 if (i__ != 0) {
00445 itmp1 = iwork[indibl + i__ - 1];
00446 w[i__] = w[j];
00447 iwork[indibl + i__ - 1] = iwork[indibl + j - 1];
00448 w[j] = tmp1;
00449 iwork[indibl + j - 1] = itmp1;
00450 dswap_(n, &z__[i__ * z_dim1 + 1], &c__1, &z__[j * z_dim1 + 1],
00451 &c__1);
00452 if (*info != 0) {
00453 itmp1 = ifail[i__];
00454 ifail[i__] = ifail[j];
00455 ifail[j] = itmp1;
00456 }
00457 }
00458
00459 }
00460 }
00461
00462 return 0;
00463
00464
00465
00466 }