1 SUBROUTINE pzpocon( UPLO, N, A, IA, JA, DESCA, ANORM, RCOND, WORK,
2 $ LWORK, RWORK, LRWORK, INFO )
11 INTEGER IA, INFO, JA, LRWORK, LWORK, N
12 DOUBLE PRECISION ANORM, RCOND
16 DOUBLE PRECISION RWORK( * )
17 COMPLEX*16 A( * ), WORK( * )
170 INTEGER BLOCK_CYCLIC_2D, CSRC_, CTXT_, DLEN_, DTYPE_,
171 $ lld_, mb_, m_, nb_, n_, rsrc_
172 parameter( block_cyclic_2d = 1, dlen_ = 9, dtype_ = 1,
173 $ ctxt_ = 2, m_ = 3, n_ = 4, mb_ = 5, nb_ = 6,
174 $ rsrc_ = 7, csrc_ = 8, lld_ = 9 )
175 DOUBLE PRECISION ONE, ZERO
176 parameter( one = 1.0d+0, zero = 0.0d+0 )
179 LOGICAL LQUERY, UPPER
180 CHARACTER CBTOP, COLCTOP, NORMIN, ROWCTOP
181 INTEGER IACOL, IAROW, ICOFF, ICTXT, IIA, IPNL, IPNU,
182 $ ipv, ipw, ipx, iroff, iv, ix, ixx, jja, jv,
183 $ jx, kase, lrwmin, lwmin, mycol, myrow, np,
184 $ npcol, nprow, npmod, nq, nqmod
185 DOUBLE PRECISION AINVNM, SCALE, SL, SU, SMLNUM
186 COMPLEX*16 WMAX, ZDUM
189 INTEGER DESCV( DLEN_ ), DESCX( DLEN_ ), IDUM1( 3 ),
200 INTEGER ICEIL, INDXG2P, NUMROC
201 DOUBLE PRECISION PDLAMCH
202 EXTERNAL iceil, indxg2p, lsame, numroc, pdlamch
205 INTRINSIC abs, dble, dimag, ichar,
max, mod
208 DOUBLE PRECISION CABS1
211 cabs1( zdum ) = abs( dble( zdum ) ) + abs( dimag( zdum ) )
217 ictxt = desca( ctxt_ )
218 CALL blacs_gridinfo( ictxt, nprow, npcol, myrow, mycol )
223 IF( nprow.EQ.-1 )
THEN
226 CALL chk1mat( n, 2, n, 2, ia, ja, desca, 6, info )
228 upper = lsame( uplo,
'U' )
229 iarow = indxg2p( ia, desca( mb_ ), myrow, desca( rsrc_ ),
231 iacol = indxg2p( ja, desca( nb_ ), mycol, desca( csrc_ ),
233 npmod = numroc( n + mod( ia-1, desca( mb_ ) ), desca( mb_ ),
234 $ myrow, iarow, nprow )
235 nqmod = numroc( n + mod( ja-1, desca( nb_ ) ), desca( nb_ ),
236 $ mycol, iacol, npcol )
238 $
max( 2,
max( desca( nb_ )*
239 $
max( 1, iceil( nprow-1, npcol ) ), nqmod +
241 $
max( 1, iceil( npcol-1, nprow ) ) ) )
242 work( 1 ) = dble( lwmin )
244 rwork( 1 ) = dble( lrwmin )
245 lquery = ( lwork.EQ.-1 .OR. lrwork.EQ.-1 )
247 IF( .NOT.upper .AND. .NOT.lsame( uplo,
'L' ) )
THEN
249 ELSE IF( anorm.LT.zero )
THEN
251 ELSE IF( lwork.LT.lwmin .AND. .NOT.lquery )
THEN
253 ELSE IF( lrwork.LT.lrwmin .AND. .NOT.lquery )
THEN
259 idum1( 1 ) = ichar(
'U' )
261 idum1( 1 ) = ichar(
'L' )
264 IF( lwork.EQ.-1 )
THEN
270 IF( lrwork.EQ.-1 )
THEN
276 CALL pchk1mat( n, 2, n, 2, ia, ja, desca, 6, 3, idum1, idum2,
281 CALL pxerbla( ictxt,
'PZPOCON', -info )
283 ELSE IF( lquery )
THEN
293 ELSE IF( anorm.EQ.zero )
THEN
295 ELSE IF( n.EQ.1 )
THEN
300 CALL pb_topget( ictxt,
'Combine',
'Columnwise', colctop )
301 CALL pb_topget( ictxt,
'Combine',
'Rowwise', rowctop )
302 CALL pb_topset( ictxt,
'Combine',
'Columnwise',
'1-tree' )
303 CALL pb_topset( ictxt,
'Combine',
'Rowwise',
'1-tree' )
305 smlnum = pdlamch( ictxt,
'Safe minimum' )
306 iroff = mod( ia-1, desca( mb_ ) )
307 icoff = mod( ja-1, desca( nb_ ) )
308 CALL infog2l( ia, ja, desca, nprow, npcol, myrow, mycol, iia, jja,
310 np = numroc( n+iroff, desca( mb_ ), myrow, iarow, nprow )
311 nq = numroc( n+icoff, desca( nb_ ), mycol, iacol, npcol )
323 CALL descset( descv, n+iroff, 1, desca( mb_ ), 1, iarow, mycol,
324 $ ictxt,
max( 1, np ) )
325 CALL descset( descx, n+iroff, 1, desca( mb_ ), 1, iarow, mycol,
326 $ ictxt,
max( 1, np ) )
335 CALL pzlacon( n, work( ipv ), iv, jv, descv, work( ipx ), ix, jx,
336 $ descx, ainvnm, kase )
342 descx( csrc_ ) = iacol
343 CALL pzlatrs(
'Upper',
'Conjugate transpose',
'Non-unit',
344 $ normin, n, a, ia, ja, desca, work( ipx ),
345 $ ix, jx, descx, sl, rwork( ipnl ),
347 descx( csrc_ ) = mycol
352 descx( csrc_ ) = iacol
353 CALL pzlatrs(
'Upper',
'No transpose',
'Non-unit', normin,
354 $ n, a, ia, ja, desca, work( ipx ), ix, jx,
355 $ descx, su, rwork( ipnu ), work( ipw ) )
356 descx( csrc_ ) = mycol
361 descx( csrc_ ) = iacol
362 CALL pzlatrs(
'Lower',
'No transpose',
'Non-unit', normin,
363 $ n, a, ia, ja, desca, work( ipx ), ix, jx,
364 $ descx, sl, rwork( ipnl ), work( ipw ) )
365 descx( csrc_ ) = mycol
370 descx( csrc_ ) = iacol
371 CALL pzlatrs(
'Lower',
'Conjugate transpose',
'Non-unit',
372 $ normin, n, a, ia, ja, desca, work( ipx ),
373 $ ix, jx, descx, su, rwork( ipnu ),
375 descx( csrc_ ) = mycol
381 IF( scale.NE.one )
THEN
382 CALL pzamax( n, wmax, ixx, work( ipx ), ix, jx, descx, 1 )
383 IF( descx( m_ ).EQ.1 .AND. n.EQ.1 )
THEN
384 CALL pb_topget( ictxt,
'Broadcast',
'Columnwise', cbtop )
385 IF( myrow.EQ.iarow )
THEN
386 CALL zgebs2d( ictxt,
'Column', cbtop, 1, 1, wmax, 1 )
388 CALL zgebr2d( ictxt,
'Column', cbtop, 1, 1, wmax, 1,
392 IF( scale.LT.cabs1( wmax )*smlnum .OR. scale.EQ.zero )
394 CALL pzdrscl( n, scale, work( ipx ), ix, jx, descx, 1 )
402 $ rcond = ( one / ainvnm ) / anorm
406 CALL pb_topset( ictxt,
'Combine',
'Columnwise', colctop )
407 CALL pb_topset( ictxt,
'Combine',
'Rowwise', rowctop )