118
119
120
121
122
123
124 CHARACTER UPLO
125 INTEGER INFO, LDA, LDB, N, NRHS
126
127
128 INTEGER IPIV( * )
129 REAL A( LDA, * ), B( LDB, * )
130
131
132
133
134
135 REAL ONE
136 parameter( one = 1.0e+0 )
137
138
139 LOGICAL UPPER
140 INTEGER J, K, KP
141 REAL 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(
'SSYTRS', -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 sswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
204
205
206
207
208 CALL sger( k-1, nrhs, -one, a( 1, k ), 1, b( k, 1 ), ldb,
209 $ b( 1, 1 ), ldb )
210
211
212
213 CALL sscal( nrhs, one / a( k, k ), b( k, 1 ), ldb )
214 k = k - 1
215 ELSE
216
217
218
219
220
221 kp = -ipiv( k )
222 IF( kp.NE.k-1 )
223 $
CALL sswap( nrhs, b( k-1, 1 ), ldb, b( kp, 1 ), ldb )
224
225
226
227
228 CALL sger( k-2, nrhs, -one, a( 1, k ), 1, b( k, 1 ), ldb,
229 $ b( 1, 1 ), ldb )
230 CALL sger( k-2, nrhs, -one, a( 1, k-1 ), 1, b( k-1, 1 ),
231 $ ldb, b( 1, 1 ), ldb )
232
233
234
235 akm1k = a( k-1, k )
236 akm1 = a( k-1, k-1 ) / akm1k
237 ak = a( k, k ) / akm1k
238 denom = akm1*ak - one
239 DO 20 j = 1, nrhs
240 bkm1 = b( k-1, j ) / akm1k
241 bk = b( k, j ) / akm1k
242 b( k-1, j ) = ( ak*bkm1-bk ) / denom
243 b( k, j ) = ( akm1*bk-bkm1 ) / denom
244 20 CONTINUE
245 k = k - 2
246 END IF
247
248 GO TO 10
249 30 CONTINUE
250
251
252
253
254
255
256 k = 1
257 40 CONTINUE
258
259
260
261 IF( k.GT.n )
262 $ GO TO 50
263
264 IF( ipiv( k ).GT.0 ) THEN
265
266
267
268
269
270
271 CALL sgemv(
'Transpose', k-1, nrhs, -one, b, ldb, a( 1,
272 $ k ),
273 $ 1, one, b( k, 1 ), ldb )
274
275
276
277 kp = ipiv( k )
278 IF( kp.NE.k )
279 $
CALL sswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
280 k = k + 1
281 ELSE
282
283
284
285
286
287
288 CALL sgemv(
'Transpose', k-1, nrhs, -one, b, ldb, a( 1,
289 $ k ),
290 $ 1, one, b( k, 1 ), ldb )
291 CALL sgemv(
'Transpose', k-1, nrhs, -one, b, ldb,
292 $ a( 1, k+1 ), 1, one, b( k+1, 1 ), ldb )
293
294
295
296 kp = -ipiv( k )
297 IF( kp.NE.k )
298 $
CALL sswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
299 k = k + 2
300 END IF
301
302 GO TO 40
303 50 CONTINUE
304
305 ELSE
306
307
308
309
310
311
312
313
314 k = 1
315 60 CONTINUE
316
317
318
319 IF( k.GT.n )
320 $ GO TO 80
321
322 IF( ipiv( k ).GT.0 ) THEN
323
324
325
326
327
328 kp = ipiv( k )
329 IF( kp.NE.k )
330 $
CALL sswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
331
332
333
334
335 IF( k.LT.n )
336 $
CALL sger( n-k, nrhs, -one, a( k+1, k ), 1, b( k, 1 ),
337 $ ldb, b( k+1, 1 ), ldb )
338
339
340
341 CALL sscal( nrhs, one / a( k, k ), b( k, 1 ), ldb )
342 k = k + 1
343 ELSE
344
345
346
347
348
349 kp = -ipiv( k )
350 IF( kp.NE.k+1 )
351 $
CALL sswap( nrhs, b( k+1, 1 ), ldb, b( kp, 1 ), ldb )
352
353
354
355
356 IF( k.LT.n-1 ) THEN
357 CALL sger( n-k-1, nrhs, -one, a( k+2, k ), 1, b( k,
358 $ 1 ),
359 $ ldb, b( k+2, 1 ), ldb )
360 CALL sger( n-k-1, nrhs, -one, a( k+2, k+1 ), 1,
361 $ b( k+1, 1 ), ldb, b( k+2, 1 ), ldb )
362 END IF
363
364
365
366 akm1k = a( k+1, k )
367 akm1 = a( k, k ) / akm1k
368 ak = a( k+1, k+1 ) / akm1k
369 denom = akm1*ak - one
370 DO 70 j = 1, nrhs
371 bkm1 = b( k, j ) / akm1k
372 bk = b( k+1, j ) / akm1k
373 b( k, j ) = ( ak*bkm1-bk ) / denom
374 b( k+1, j ) = ( akm1*bk-bkm1 ) / denom
375 70 CONTINUE
376 k = k + 2
377 END IF
378
379 GO TO 60
380 80 CONTINUE
381
382
383
384
385
386
387 k = n
388 90 CONTINUE
389
390
391
392 IF( k.LT.1 )
393 $ GO TO 100
394
395 IF( ipiv( k ).GT.0 ) THEN
396
397
398
399
400
401
402 IF( k.LT.n )
403 $
CALL sgemv(
'Transpose', n-k, nrhs, -one, b( k+1, 1 ),
404 $ ldb, a( k+1, k ), 1, one, b( k, 1 ), ldb )
405
406
407
408 kp = ipiv( k )
409 IF( kp.NE.k )
410 $
CALL sswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
411 k = k - 1
412 ELSE
413
414
415
416
417
418
419 IF( k.LT.n ) THEN
420 CALL sgemv(
'Transpose', n-k, nrhs, -one, b( k+1, 1 ),
421 $ ldb, a( k+1, k ), 1, one, b( k, 1 ), ldb )
422 CALL sgemv(
'Transpose', n-k, nrhs, -one, b( k+1, 1 ),
423 $ ldb, a( k+1, k-1 ), 1, one, b( k-1, 1 ),
424 $ ldb )
425 END IF
426
427
428
429 kp = -ipiv( k )
430 IF( kp.NE.k )
431 $
CALL sswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
432 k = k - 2
433 END IF
434
435 GO TO 90
436 100 CONTINUE
437 END IF
438
439 RETURN
440
441
442
subroutine xerbla(srname, info)
subroutine sgemv(trans, m, n, alpha, a, lda, x, incx, beta, y, incy)
SGEMV
subroutine sger(m, n, alpha, x, incx, y, incy, a, lda)
SGER
logical function lsame(ca, cb)
LSAME
subroutine sscal(n, sa, sx, incx)
SSCAL
subroutine sswap(n, sx, incx, sy, incy)
SSWAP