1 SUBROUTINE pdsvdchk( M, N, A, IA, JA, DESCA, U, IU, JU, DESCU, VT,
2 $ IVT, JVT, DESCVT, S, THRESH, WORK, LWORK,
11 INTEGER IA, IU, IVT, JA, JU, JVT, LWORK, M, N
12 DOUBLE PRECISION CHK, MTM, THRESH
15 INTEGER DESCA( * ), DESCU( * ), DESCVT( * ),
17 DOUBLE PRECISION A( * ), S( * ), U( * ), VT( * ), WORK( * )
201 INTEGER BLOCK_CYCLIC_2D, DLEN_, DTYPE_, CTXT_, M_, N_,
202 $ MB_, NB_, RSRC_, CSRC_, LLD_
203 parameter( block_cyclic_2d = 1, dlen_ = 9, dtype_ = 1,
204 $ ctxt_ = 2, m_ = 3, n_ = 4, mb_ = 5, nb_ = 6,
205 $ rsrc_ = 7, csrc_ = 8, lld_ = 9 )
206 DOUBLE PRECISION ZERO, ONE, MONE
207 PARAMETER ( ZERO = 0.0d+0, one = 1.0d+0, mone = -1.0d0 )
210 INTEGER I, INFO, LDR, LOCALCOL, LWMIN, MP, MX, MYCOL,
211 $ MYROW, NPCOL, NPROW, NQ, PCOL, PTRR, PTRWORK,
212 $
SIZE, sizep, sizepos, sizeq
213 DOUBLE PRECISION FIRST, NORMA, NORMAI, NORMU, NORMVT, SECOND,
217 INTEGER DESCR( DLEN_ )
220 INTEGER INDXG2L, INDXG2P, NUMROC
221 DOUBLE PRECISION PDLAMCH, PDLANGE
222 EXTERNAL indxg2l, indxg2p, numroc, pdlamch, pdlange
233 IF( block_cyclic_2d*csrc_*dtype_*m_*n_*rsrc_.LT.0 )
RETURN
237 CALL blacs_gridinfo( desca( ctxt_ ), nprow, npcol, myrow, mycol )
245 IF( nprow.EQ.-1 )
THEN
248 CALL chk1mat( m, 1, n, 2, ia, ja, desca, 6, info )
249 CALL chk1mat( m, 1,
SIZE, sizepos, iu, ju, descu, 10, info )
250 CALL chk1mat(
SIZE, sizepos, n, 2, ivt, jvt, descvt, 14, info )
257 mp = numroc( m, desca( mb_ ), myrow, 0, nprow )
258 nq = numroc( n, desca( nb_ ), mycol, 0, npcol )
259 sizep = numroc(
SIZE, descvt( mb_ ), myrow, 0, nprow )
260 sizeq = numroc(
SIZE, descu( nb_ ), mycol, 0, npcol )
261 mx =
max( sizeq, nq )
262 lwmin = 2 + sizeq*sizep +
max( 2, mx )
266 IF( lwork.LT.lwmin )
THEN
268 ELSE IF( thresh.LE.0 )
THEN
273 CALL pxerbla( desca( ctxt_ ),
'PDSVDCHK', -info )
277 ldr =
max( 1, sizep )
278 ulp = pdlamch( desca( ctxt_ ),
'P' )
279 normai = pdlange(
'1', m, n, a, ia, ja, desca, work )
284 ptrwork = ptrr + sizeq*sizep
286 CALL descinit( descr,
SIZE,
SIZE, descvt( mb_ ), descu( nb_ ), 0,
287 $ 0, desca( ctxt_ ), ldr, info )
291 CALL pdlaset(
'Full',
SIZE,
SIZE, zero, one, work( ptrr ), 1, 1,
293 CALL pdgemm(
'T',
'N',
SIZE,
SIZE, m, one, u, iu, ju, descu, u,
294 $ iu, ju, descu, mone, work( ptrr ), 1, 1, descr )
296 normu = pdlange(
'1',
SIZE,
SIZE, work( ptrr ), 1, 1, descr,
299 normu = normu / ulp /
SIZE / thresh
305 CALL pdlaset(
'Full',
SIZE,
SIZE, zero, one, work( ptrr ), 1, 1,
307 CALL pdgemm(
'N',
'T',
SIZE,
SIZE, n, one, vt, ivt, jvt, descvt,
308 $ vt, ivt, jvt, descvt, mone, work( ptrr ),
310 normvt = pdlange(
'1',
SIZE,
SIZE, work( ptrr ), 1, 1, descr,
313 normvt = normvt / ulp /
SIZE / thresh
317 mtm =
max( normvt, normu )*thresh
322 CALL pdlaset(
'Full',
SIZE,
SIZE, zero, zero, work( ptrr ), 1, 1,
326 CALL pdelset( work( ptrr ), i, i, descr, s( i ) )
332 pcol = indxg2p( i, descu( nb_ ), 0, 0, npcol )
333 localcol = indxg2l( i, descu( nb_ ), 0, 0, npcol )
334 IF( mycol.EQ.pcol )
THEN
335 CALL dscal( mp, s( i ), u( ( localcol-1 )*descu( lld_ )+1 ),
342 CALL pdgemm(
'N',
'N', m, n,
SIZE, one, u, iu, ju, descu, vt,
343 $ ivt, jvt, descvt, mone, a, ia, ja, desca )
345 norma = pdlange(
'1', m, n, a, ia, ja, desca, work( ptrwork ) )
346 thresha = normai*
max( m, n )*ulp*thresh
348 IF( norma.GT.thresha )
351 IF( thresha.EQ.0 )
THEN
354 chk = norma / thresha*thresh
359 DO 30 i = 1,
SIZE - 1
362 IF( first.LT.second )