118
119
120
121
122
123
124 CHARACTER UPLO
125 INTEGER INFO, LDA, LDB, N, NRHS
126
127
128 INTEGER IPIV( * )
129 COMPLEX*16 A( LDA, * ), B( LDB, * )
130
131
132
133
134
135 COMPLEX*16 ONE
136 parameter( one = ( 1.0d+0, 0.0d+0 ) )
137
138
139 LOGICAL UPPER
140 INTEGER J, K, KP
141 COMPLEX*16 AK, AKM1, AKM1K, BK, BKM1, DENOM
142
143
144 LOGICAL LSAME
146
147
149
150
151 INTRINSIC max
152
153
154
155 info = 0
156 upper =
lsame( uplo,
'U' )
157 IF( .NOT.upper .AND. .NOT.
lsame( uplo,
'L' ) )
THEN
158 info = -1
159 ELSE IF( n.LT.0 ) THEN
160 info = -2
161 ELSE IF( nrhs.LT.0 ) THEN
162 info = -3
163 ELSE IF( lda.LT.max( 1, n ) ) THEN
164 info = -5
165 ELSE IF( ldb.LT.max( 1, n ) ) THEN
166 info = -8
167 END IF
168 IF( info.NE.0 ) THEN
169 CALL xerbla(
'ZSYTRS', -info )
170 RETURN
171 END IF
172
173
174
175 IF( n.EQ.0 .OR. nrhs.EQ.0 )
176 $ RETURN
177
178 IF( upper ) THEN
179
180
181
182
183
184
185
186
187 k = n
188 10 CONTINUE
189
190
191
192 IF( k.LT.1 )
193 $ GO TO 30
194
195 IF( ipiv( k ).GT.0 ) THEN
196
197
198
199
200
201 kp = ipiv( k )
202 IF( kp.NE.k )
203 $
CALL zswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
204
205
206
207
208 CALL zgeru( k-1, nrhs, -one, a( 1, k ), 1, b( k, 1 ),
209 $ ldb,
210 $ b( 1, 1 ), ldb )
211
212
213
214 CALL zscal( nrhs, one / a( k, k ), b( k, 1 ), ldb )
215 k = k - 1
216 ELSE
217
218
219
220
221
222 kp = -ipiv( k )
223 IF( kp.NE.k-1 )
224 $
CALL zswap( nrhs, b( k-1, 1 ), ldb, b( kp, 1 ), ldb )
225
226
227
228
229 CALL zgeru( k-2, nrhs, -one, a( 1, k ), 1, b( k, 1 ),
230 $ ldb,
231 $ b( 1, 1 ), ldb )
232 CALL zgeru( k-2, nrhs, -one, a( 1, k-1 ), 1, b( k-1, 1 ),
233 $ ldb, b( 1, 1 ), ldb )
234
235
236
237 akm1k = a( k-1, k )
238 akm1 = a( k-1, k-1 ) / akm1k
239 ak = a( k, k ) / akm1k
240 denom = akm1*ak - one
241 DO 20 j = 1, nrhs
242 bkm1 = b( k-1, j ) / akm1k
243 bk = b( k, j ) / akm1k
244 b( k-1, j ) = ( ak*bkm1-bk ) / denom
245 b( k, j ) = ( akm1*bk-bkm1 ) / denom
246 20 CONTINUE
247 k = k - 2
248 END IF
249
250 GO TO 10
251 30 CONTINUE
252
253
254
255
256
257
258 k = 1
259 40 CONTINUE
260
261
262
263 IF( k.GT.n )
264 $ GO TO 50
265
266 IF( ipiv( k ).GT.0 ) THEN
267
268
269
270
271
272
273 CALL zgemv(
'Transpose', k-1, nrhs, -one, b, ldb, a( 1,
274 $ k ),
275 $ 1, one, b( k, 1 ), ldb )
276
277
278
279 kp = ipiv( k )
280 IF( kp.NE.k )
281 $
CALL zswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
282 k = k + 1
283 ELSE
284
285
286
287
288
289
290 CALL zgemv(
'Transpose', k-1, nrhs, -one, b, ldb, a( 1,
291 $ k ),
292 $ 1, one, b( k, 1 ), ldb )
293 CALL zgemv(
'Transpose', k-1, nrhs, -one, b, ldb,
294 $ a( 1, k+1 ), 1, one, b( k+1, 1 ), ldb )
295
296
297
298 kp = -ipiv( k )
299 IF( kp.NE.k )
300 $
CALL zswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
301 k = k + 2
302 END IF
303
304 GO TO 40
305 50 CONTINUE
306
307 ELSE
308
309
310
311
312
313
314
315
316 k = 1
317 60 CONTINUE
318
319
320
321 IF( k.GT.n )
322 $ GO TO 80
323
324 IF( ipiv( k ).GT.0 ) THEN
325
326
327
328
329
330 kp = ipiv( k )
331 IF( kp.NE.k )
332 $
CALL zswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
333
334
335
336
337 IF( k.LT.n )
338 $
CALL zgeru( n-k, nrhs, -one, a( k+1, k ), 1, b( k,
339 $ 1 ),
340 $ ldb, b( k+1, 1 ), ldb )
341
342
343
344 CALL zscal( nrhs, one / a( k, k ), b( k, 1 ), ldb )
345 k = k + 1
346 ELSE
347
348
349
350
351
352 kp = -ipiv( k )
353 IF( kp.NE.k+1 )
354 $
CALL zswap( nrhs, b( k+1, 1 ), ldb, b( kp, 1 ), ldb )
355
356
357
358
359 IF( k.LT.n-1 ) THEN
360 CALL zgeru( n-k-1, nrhs, -one, a( k+2, k ), 1, b( k,
361 $ 1 ),
362 $ ldb, b( k+2, 1 ), ldb )
363 CALL zgeru( n-k-1, nrhs, -one, a( k+2, k+1 ), 1,
364 $ b( k+1, 1 ), ldb, b( k+2, 1 ), ldb )
365 END IF
366
367
368
369 akm1k = a( k+1, k )
370 akm1 = a( k, k ) / akm1k
371 ak = a( k+1, k+1 ) / akm1k
372 denom = akm1*ak - one
373 DO 70 j = 1, nrhs
374 bkm1 = b( k, j ) / akm1k
375 bk = b( k+1, j ) / akm1k
376 b( k, j ) = ( ak*bkm1-bk ) / denom
377 b( k+1, j ) = ( akm1*bk-bkm1 ) / denom
378 70 CONTINUE
379 k = k + 2
380 END IF
381
382 GO TO 60
383 80 CONTINUE
384
385
386
387
388
389
390 k = n
391 90 CONTINUE
392
393
394
395 IF( k.LT.1 )
396 $ GO TO 100
397
398 IF( ipiv( k ).GT.0 ) THEN
399
400
401
402
403
404
405 IF( k.LT.n )
406 $
CALL zgemv(
'Transpose', n-k, nrhs, -one, b( k+1, 1 ),
407 $ ldb, a( k+1, k ), 1, one, b( k, 1 ), ldb )
408
409
410
411 kp = ipiv( k )
412 IF( kp.NE.k )
413 $
CALL zswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
414 k = k - 1
415 ELSE
416
417
418
419
420
421
422 IF( k.LT.n ) THEN
423 CALL zgemv(
'Transpose', n-k, nrhs, -one, b( k+1, 1 ),
424 $ ldb, a( k+1, k ), 1, one, b( k, 1 ), ldb )
425 CALL zgemv(
'Transpose', n-k, nrhs, -one, b( k+1, 1 ),
426 $ ldb, a( k+1, k-1 ), 1, one, b( k-1, 1 ),
427 $ ldb )
428 END IF
429
430
431
432 kp = -ipiv( k )
433 IF( kp.NE.k )
434 $
CALL zswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
435 k = k - 2
436 END IF
437
438 GO TO 90
439 100 CONTINUE
440 END IF
441
442 RETURN
443
444
445
subroutine xerbla(srname, info)
subroutine zgemv(trans, m, n, alpha, a, lda, x, incx, beta, y, incy)
ZGEMV
subroutine zgeru(m, n, alpha, x, incx, y, incy, a, lda)
ZGERU
logical function lsame(ca, cb)
LSAME
subroutine zscal(n, za, zx, incx)
ZSCAL
subroutine zswap(n, zx, incx, zy, incy)
ZSWAP