1 REAL FUNCTION PSLANTR( NORM, UPLO, DIAG, M, N, A, 2 $ IA, JA, DESCA, WORK ) 3 IMPLICIT NONE 4* 5* -- ScaLAPACK auxiliary routine (version 1.7) -- 6* University of Tennessee, Knoxville, Oak Ridge National Laboratory, 7* and University of California, Berkeley. 8* May 1, 1997 9* 10* .. Scalar Arguments .. 11 CHARACTER DIAG, NORM, UPLO 12 INTEGER IA, JA, M, N 13* .. 14* .. Array Arguments .. 15 INTEGER DESCA( * ) 16 REAL A( * ), WORK( * ) 17* .. 18* 19* Purpose 20* ======= 21* 22* PSLANTR returns the value of the one norm, or the Frobenius norm, 23* or the infinity norm, or the element of largest absolute value of a 24* trapezoidal or triangular distributed matrix sub( A ) denoting 25* A(IA:IA+M-1, JA:JA+N-1). 26* 27* PSLANTR returns the value 28* 29* ( max(abs(A(i,j))), NORM = 'M' or 'm' with ia <= i <= ia+m-1, 30* ( and ja <= j <= ja+n-1, 31* ( 32* ( norm1( sub( A ) ), NORM = '1', 'O' or 'o' 33* ( 34* ( normI( sub( A ) ), NORM = 'I' or 'i' 35* ( 36* ( normF( sub( A ) ), NORM = 'F', 'f', 'E' or 'e' 37* 38* where norm1 denotes the one norm of a matrix (maximum column sum), 39* normI denotes the infinity norm of a matrix (maximum row sum) and 40* normF denotes the Frobenius norm of a matrix (square root of sum of 41* squares). Note that max(abs(A(i,j))) is not a matrix norm. 42* 43* Notes 44* ===== 45* 46* Each global data object is described by an associated description 47* vector. This vector stores the information required to establish 48* the mapping between an object element and its corresponding process 49* and memory location. 50* 51* Let A be a generic term for any 2D block cyclicly distributed array. 52* Such a global array has an associated description vector DESCA. 53* In the following comments, the character _ should be read as 54* "of the global array". 55* 56* NOTATION STORED IN EXPLANATION 57* --------------- -------------- -------------------------------------- 58* DTYPE_A(global) DESCA( DTYPE_ )The descriptor type. In this case, 59* DTYPE_A = 1. 60* CTXT_A (global) DESCA( CTXT_ ) The BLACS context handle, indicating 61* the BLACS process grid A is distribu- 62* ted over. The context itself is glo- 63* bal, but the handle (the integer 64* value) may vary. 65* M_A (global) DESCA( M_ ) The number of rows in the global 66* array A. 67* N_A (global) DESCA( N_ ) The number of columns in the global 68* array A. 69* MB_A (global) DESCA( MB_ ) The blocking factor used to distribute 70* the rows of the array. 71* NB_A (global) DESCA( NB_ ) The blocking factor used to distribute 72* the columns of the array. 73* RSRC_A (global) DESCA( RSRC_ ) The process row over which the first 74* row of the array A is distributed. 75* CSRC_A (global) DESCA( CSRC_ ) The process column over which the 76* first column of the array A is 77* distributed. 78* LLD_A (local) DESCA( LLD_ ) The leading dimension of the local 79* array. LLD_A >= MAX(1,LOCr(M_A)). 80* 81* Let K be the number of rows or columns of a distributed matrix, 82* and assume that its process grid has dimension p x q. 83* LOCr( K ) denotes the number of elements of K that a process 84* would receive if K were distributed over the p processes of its 85* process column. 86* Similarly, LOCc( K ) denotes the number of elements of K that a 87* process would receive if K were distributed over the q processes of 88* its process row. 89* The values of LOCr() and LOCc() may be determined via a call to the 90* ScaLAPACK tool function, NUMROC: 91* LOCr( M ) = NUMROC( M, MB_A, MYROW, RSRC_A, NPROW ), 92* LOCc( N ) = NUMROC( N, NB_A, MYCOL, CSRC_A, NPCOL ). 93* An upper bound for these quantities may be computed by: 94* LOCr( M ) <= ceil( ceil(M/MB_A)/NPROW )*MB_A 95* LOCc( N ) <= ceil( ceil(N/NB_A)/NPCOL )*NB_A 96* 97* Arguments 98* ========= 99* 100* NORM (global input) CHARACTER 101* Specifies the value to be returned in PSLANTR as described 102* above. 103* 104* UPLO (global input) CHARACTER 105* Specifies whether the matrix sub( A ) is upper or lower 106* trapezoidal. 107* = 'U': Upper trapezoidal 108* = 'L': Lower trapezoidal 109* Note that sub( A ) is triangular instead of trapezoidal 110* if M = N. 111* 112* DIAG (global input) CHARACTER 113* Specifies whether or not the distributed matrix sub( A ) has 114* unit diagonal. 115* = 'N': Non-unit diagonal 116* = 'U': Unit diagonal 117* 118* M (global input) INTEGER 119* The number of rows to be operated on i.e the number of rows 120* of the distributed submatrix sub( A ). When M = 0, PSLANTR is 121* set to zero. M >= 0. 122* 123* N (global input) INTEGER 124* The number of columns to be operated on i.e the number of 125* columns of the distributed submatrix sub( A ). When N = 0, 126* PSLANTR is set to zero. N >= 0. 127* 128* A (local input) REAL pointer into the local memory 129* to an array of dimension (LLD_A, LOCc(JA+N-1) ) containing 130* the local pieces of sub( A ). 131* 132* IA (global input) INTEGER 133* The row index in the global array A indicating the first 134* row of sub( A ). 135* 136* JA (global input) INTEGER 137* The column index in the global array A indicating the 138* first column of sub( A ). 139* 140* DESCA (global and local input) INTEGER array of dimension DLEN_. 141* The array descriptor for the distributed matrix A. 142* 143* WORK (local workspace) REAL array dimension (LWORK) 144* LWORK >= 0 if NORM = 'M' or 'm' (not referenced), 145* Nq0 if NORM = '1', 'O' or 'o', 146* Mp0 if NORM = 'I' or 'i', 147* 0 if NORM = 'F', 'f', 'E' or 'e' (not referenced), 148* where 149* 150* IROFFA = MOD( IA-1, MB_A ), ICOFFA = MOD( JA-1, NB_A ), 151* IAROW = INDXG2P( IA, MB_A, MYROW, RSRC_A, NPROW ), 152* IACOL = INDXG2P( JA, NB_A, MYCOL, CSRC_A, NPCOL ), 153* Mp0 = NUMROC( M+IROFFA, MB_A, MYROW, IAROW, NPROW ), 154* Nq0 = NUMROC( N+ICOFFA, NB_A, MYCOL, IACOL, NPCOL ), 155* 156* INDXG2P and NUMROC are ScaLAPACK tool functions; MYROW, 157* MYCOL, NPROW and NPCOL can be determined by calling the 158* subroutine BLACS_GRIDINFO. 159* 160* ===================================================================== 161* 162* .. Parameters .. 163 INTEGER BLOCK_CYCLIC_2D, CSRC_, CTXT_, DLEN_, DTYPE_, 164 $ LLD_, MB_, M_, NB_, N_, RSRC_ 165 PARAMETER ( BLOCK_CYCLIC_2D = 1, DLEN_ = 9, DTYPE_ = 1, 166 $ CTXT_ = 2, M_ = 3, N_ = 4, MB_ = 5, NB_ = 6, 167 $ RSRC_ = 7, CSRC_ = 8, LLD_ = 9 ) 168 REAL ONE, ZERO 169 PARAMETER ( ONE = 1.0E+0, ZERO = 0.0E+0 ) 170* .. 171* .. Local Scalars .. 172 LOGICAL UDIAG 173 INTEGER IACOL, IAROW, ICTXT, II, IIA, ICOFF, IOFFA, 174 $ IROFF, J, JB, JJ, JJA, JN, KK, LDA, LL, MP, 175 $ MYCOL, MYROW, NP, NPCOL, NPROW, NQ 176 REAL SUM, VALUE 177* .. 178* .. Local Arrays .. 179 REAL SSQ( 2 ), COLSSQ( 2 ) 180* .. 181* .. External Subroutines .. 182 EXTERNAL BLACS_GRIDINFO, INFOG2L, PSTREECOMB, 183 $ SCOMBSSQ, SGEBR2D, SGEBS2D, 184 $ SGAMX2D, SGSUM2D, SLASSQ 185* .. 186* .. External Functions .. 187 LOGICAL LSAME 188 INTEGER ICEIL, ISAMAX, NUMROC 189 EXTERNAL LSAME, ICEIL, ISAMAX, NUMROC 190* .. 191* .. Intrinsic Functions .. 192 INTRINSIC ABS, MAX, MIN, MOD, REAL, SQRT 193* .. 194* .. Executable Statements .. 195* 196* Get grid parameters 197* 198 ICTXT = DESCA( CTXT_ ) 199 CALL BLACS_GRIDINFO( ICTXT, NPROW, NPCOL, MYROW, MYCOL ) 200* 201 UDIAG = LSAME( DIAG, 'U' ) 202 CALL INFOG2L( IA, JA, DESCA, NPROW, NPCOL, MYROW, MYCOL, IIA, JJA, 203 $ IAROW, IACOL ) 204 IROFF = MOD( IA-1, DESCA( MB_ ) ) 205 ICOFF = MOD( JA-1, DESCA( NB_ ) ) 206 MP = NUMROC( M+IROFF, DESCA( MB_ ), MYROW, IAROW, NPROW ) 207 NQ = NUMROC( N+ICOFF, DESCA( NB_ ), MYCOL, IACOL, NPCOL ) 208 IF( MYROW.EQ.IAROW ) 209 $ MP = MP - IROFF 210 IF( MYCOL.EQ.IACOL ) 211 $ NQ = NQ - ICOFF 212 LDA = DESCA( LLD_ ) 213 IOFFA = ( JJA - 1 ) * LDA 214* 215 IF( MIN( M, N ).EQ.0 ) THEN 216* 217 VALUE = ZERO 218* 219************************************************************************ 220* max norm 221* 222 ELSE IF( LSAME( NORM, 'M' ) ) THEN 223* 224* Find max(abs(A(i,j))). 225* 226 IF( UDIAG ) THEN 227 VALUE = ONE 228 ELSE 229 VALUE = ZERO 230 END IF 231* 232 IF( LSAME( UPLO, 'U' ) ) THEN 233* 234* Upper triangular matrix 235* 236 II = IIA 237 JJ = JJA 238 JN = MIN( ICEIL( JA, DESCA( NB_ ) ) * DESCA( NB_ ), JA+N-1 ) 239 JB = JN-JA+1 240* 241 IF( MYCOL.EQ.IACOL ) THEN 242 IF( MYROW.EQ.IAROW ) THEN 243 IF( UDIAG ) THEN 244 DO 20 LL = JJ, JJ + JB -1 245 DO 10 KK = IIA, MIN(II+LL-JJ-1,IIA+MP-1) 246 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 247 10 CONTINUE 248 IOFFA = IOFFA + LDA 249 20 CONTINUE 250 ELSE 251 DO 40 LL = JJ, JJ + JB -1 252 DO 30 KK = IIA, MIN( II+LL-JJ, IIA+MP-1 ) 253 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 254 30 CONTINUE 255 IOFFA = IOFFA + LDA 256 40 CONTINUE 257 END IF 258 ELSE 259 DO 60 LL = JJ, JJ + JB -1 260 DO 50 KK = IIA, MIN( II-1, IIA+MP-1 ) 261 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 262 50 CONTINUE 263 IOFFA = IOFFA + LDA 264 60 CONTINUE 265 END IF 266 JJ = JJ + JB 267 END IF 268* 269 IF( MYROW.EQ.IAROW ) 270 $ II = II + JB 271 IAROW = MOD( IAROW+1, NPROW ) 272 IACOL = MOD( IACOL+1, NPCOL ) 273* 274* Loop over remaining block of columns 275* 276 DO 130 J = JN+1, JA+N-1, DESCA( NB_ ) 277 JB = MIN( JA+N-J, DESCA( NB_ ) ) 278* 279 IF( MYCOL.EQ.IACOL ) THEN 280 IF( MYROW.EQ.IAROW ) THEN 281 IF( UDIAG ) THEN 282 DO 80 LL = JJ, JJ + JB -1 283 DO 70 KK = IIA, MIN( II+LL-JJ-1, IIA+MP-1 ) 284 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 285 70 CONTINUE 286 IOFFA = IOFFA + LDA 287 80 CONTINUE 288 ELSE 289 DO 100 LL = JJ, JJ + JB -1 290 DO 90 KK = IIA, MIN( II+LL-JJ, IIA+MP-1 ) 291 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 292 90 CONTINUE 293 IOFFA = IOFFA + LDA 294 100 CONTINUE 295 END IF 296 ELSE 297 DO 120 LL = JJ, JJ + JB -1 298 DO 110 KK = IIA, MIN( II-1, IIA+MP-1 ) 299 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 300 110 CONTINUE 301 IOFFA = IOFFA + LDA 302 120 CONTINUE 303 END IF 304 JJ = JJ + JB 305 END IF 306* 307 IF( MYROW.EQ.IAROW ) 308 $ II = II + JB 309 IAROW = MOD( IAROW+1, NPROW ) 310 IACOL = MOD( IACOL+1, NPCOL ) 311* 312 130 CONTINUE 313* 314 ELSE 315* 316* Lower triangular matrix 317* 318 II = IIA 319 JJ = JJA 320 JN = MIN( ICEIL( JA, DESCA( NB_ ) ) * DESCA( NB_ ), JA+N-1 ) 321 JB = JN-JA+1 322* 323 IF( MYCOL.EQ.IACOL ) THEN 324 IF( MYROW.EQ.IAROW ) THEN 325 IF( UDIAG ) THEN 326 DO 150 LL = JJ, JJ + JB -1 327 DO 140 KK = II+LL-JJ+1, IIA+MP-1 328 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 329 140 CONTINUE 330 IOFFA = IOFFA + LDA 331 150 CONTINUE 332 ELSE 333 DO 170 LL = JJ, JJ + JB -1 334 DO 160 KK = II+LL-JJ, IIA+MP-1 335 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 336 160 CONTINUE 337 IOFFA = IOFFA + LDA 338 170 CONTINUE 339 END IF 340 ELSE 341 DO 190 LL = JJ, JJ + JB -1 342 DO 180 KK = II, IIA+MP-1 343 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 344 180 CONTINUE 345 IOFFA = IOFFA + LDA 346 190 CONTINUE 347 END IF 348 JJ = JJ + JB 349 END IF 350* 351 IF( MYROW.EQ.IAROW ) 352 $ II = II + JB 353 IAROW = MOD( IAROW+1, NPROW ) 354 IACOL = MOD( IACOL+1, NPCOL ) 355* 356* Loop over remaining block of columns 357* 358 DO 260 J = JN+1, JA+N-1, DESCA( NB_ ) 359 JB = MIN( JA+N-J, DESCA( NB_ ) ) 360* 361 IF( MYCOL.EQ.IACOL ) THEN 362 IF( MYROW.EQ.IAROW ) THEN 363 IF( UDIAG ) THEN 364 DO 210 LL = JJ, JJ + JB -1 365 DO 200 KK = II+LL-JJ+1, IIA+MP-1 366 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 367 200 CONTINUE 368 IOFFA = IOFFA + LDA 369 210 CONTINUE 370 ELSE 371 DO 230 LL = JJ, JJ + JB -1 372 DO 220 KK = II+LL-JJ, IIA+MP-1 373 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 374 220 CONTINUE 375 IOFFA = IOFFA + LDA 376 230 CONTINUE 377 END IF 378 ELSE 379 DO 250 LL = JJ, JJ + JB -1 380 DO 240 KK = II, IIA+MP-1 381 VALUE = MAX( VALUE, ABS( A( IOFFA+KK ) ) ) 382 240 CONTINUE 383 IOFFA = IOFFA + LDA 384 250 CONTINUE 385 END IF 386 JJ = JJ + JB 387 END IF 388* 389 IF( MYROW.EQ.IAROW ) 390 $ II = II + JB 391 IAROW = MOD( IAROW+1, NPROW ) 392 IACOL = MOD( IACOL+1, NPCOL ) 393* 394 260 CONTINUE 395* 396 END IF 397* 398* Gather the intermediate results to process (0,0). 399* 400 CALL SGAMX2D( ICTXT, 'All', ' ', 1, 1, VALUE, 1, KK, LL, -1, 401 $ 0, 0 ) 402* 403************************************************************************ 404* one norm 405* 406 ELSE IF( LSAME( NORM, 'O' ) .OR. NORM.EQ.'1' ) THEN 407* 408 VALUE = ZERO 409* 410 IF( LSAME( UPLO, 'U' ) ) THEN 411* 412* Upper triangular matrix 413* 414 II = IIA 415 JJ = JJA 416 JN = MIN( ICEIL( JA, DESCA( NB_ ) ) * DESCA( NB_ ), JA+N-1 ) 417 JB = JN-JA+1 418* 419 IF( MYCOL.EQ.IACOL ) THEN 420 IF( MYROW.EQ.IAROW ) THEN 421 IF( UDIAG ) THEN 422 DO 280 LL = JJ, JJ + JB -1 423 SUM = ZERO 424 DO 270 KK = IIA, MIN( II+LL-JJ-1, IIA+MP-1 ) 425 SUM = SUM + ABS( A( IOFFA+KK ) ) 426 270 CONTINUE 427* Unit diagonal entry 428 KK = II+LL-JJ 429 IF (KK <= IIA+MP-1) THEN 430 SUM = SUM + ONE 431 ENDIF 432 IOFFA = IOFFA + LDA 433 WORK( LL-JJA+1 ) = SUM 434 280 CONTINUE 435 ELSE 436 DO 300 LL = JJ, JJ + JB -1 437 SUM = ZERO 438 DO 290 KK = IIA, MIN( II+LL-JJ, IIA+MP-1 ) 439 SUM = SUM + ABS( A( IOFFA+KK ) ) 440 290 CONTINUE 441 IOFFA = IOFFA + LDA 442 WORK( LL-JJA+1 ) = SUM 443 300 CONTINUE 444 END IF 445 ELSE 446 DO 320 LL = JJ, JJ + JB -1 447 SUM = ZERO 448 DO 310 KK = IIA, MIN( II-1, IIA+MP-1 ) 449 SUM = SUM + ABS( A( IOFFA+KK ) ) 450 310 CONTINUE 451 IOFFA = IOFFA + LDA 452 WORK( LL-JJA+1 ) = SUM 453 320 CONTINUE 454 END IF 455 JJ = JJ + JB 456 END IF 457* 458 IF( MYROW.EQ.IAROW ) 459 $ II = II + JB 460 IAROW = MOD( IAROW+1, NPROW ) 461 IACOL = MOD( IACOL+1, NPCOL ) 462* 463* Loop over remaining block of columns 464* 465 DO 390 J = JN+1, JA+N-1, DESCA( NB_ ) 466 JB = MIN( JA+N-J, DESCA( NB_ ) ) 467* 468 IF( MYCOL.EQ.IACOL ) THEN 469 IF( MYROW.EQ.IAROW ) THEN 470 IF( UDIAG ) THEN 471 DO 340 LL = JJ, JJ + JB -1 472 SUM = ZERO 473 DO 330 KK = IIA, MIN( II+LL-JJ-1, IIA+MP-1 ) 474 SUM = SUM + ABS( A( IOFFA+KK ) ) 475 330 CONTINUE 476* Unit diagonal entry 477 KK = II+LL-JJ 478 IF (KK <= IIA+MP-1) THEN 479 SUM = SUM + ONE 480 ENDIF 481 IOFFA = IOFFA + LDA 482 WORK( LL-JJA+1 ) = SUM 483 340 CONTINUE 484 ELSE 485 DO 360 LL = JJ, JJ + JB -1 486 SUM = ZERO 487 DO 350 KK = IIA, MIN( II+LL-JJ, IIA+MP-1 ) 488 SUM = SUM + ABS( A( IOFFA+KK ) ) 489 350 CONTINUE 490 IOFFA = IOFFA + LDA 491 WORK( LL-JJA+1 ) = SUM 492 360 CONTINUE 493 END IF 494 ELSE 495 DO 380 LL = JJ, JJ + JB -1 496 SUM = ZERO 497 DO 370 KK = IIA, MIN( II-1, IIA+MP-1 ) 498 SUM = SUM + ABS( A( IOFFA+KK ) ) 499 370 CONTINUE 500 IOFFA = IOFFA + LDA 501 WORK( LL-JJA+1 ) = SUM 502 380 CONTINUE 503 END IF 504 JJ = JJ + JB 505 END IF 506* 507 IF( MYROW.EQ.IAROW ) 508 $ II = II + JB 509 IAROW = MOD( IAROW+1, NPROW ) 510 IACOL = MOD( IACOL+1, NPCOL ) 511* 512 390 CONTINUE 513* 514 ELSE 515* 516* Lower triangular matrix 517* 518 II = IIA 519 JJ = JJA 520 JN = MIN( ICEIL( JA, DESCA( NB_ ) ) * DESCA( NB_ ), JA+N-1 ) 521 JB = JN-JA+1 522* 523 IF( MYCOL.EQ.IACOL ) THEN 524 IF( MYROW.EQ.IAROW ) THEN 525 IF( UDIAG ) THEN 526 DO 410 LL = JJ, JJ + JB -1 527 SUM = ONE 528 DO 400 KK = II+LL-JJ+1, IIA+MP-1 529 SUM = SUM + ABS( A( IOFFA+KK ) ) 530 400 CONTINUE 531 IOFFA = IOFFA + LDA 532 WORK( LL-JJA+1 ) = SUM 533 410 CONTINUE 534 ELSE 535 DO 430 LL = JJ, JJ + JB -1 536 SUM = ZERO 537 DO 420 KK = II+LL-JJ, IIA+MP-1 538 SUM = SUM + ABS( A( IOFFA+KK ) ) 539 420 CONTINUE 540 IOFFA = IOFFA + LDA 541 WORK( LL-JJA+1 ) = SUM 542 430 CONTINUE 543 END IF 544 ELSE 545 DO 450 LL = JJ, JJ + JB -1 546 SUM = ZERO 547 DO 440 KK = II, IIA+MP-1 548 SUM = SUM + ABS( A( IOFFA+KK ) ) 549 440 CONTINUE 550 IOFFA = IOFFA + LDA 551 WORK( LL-JJA+1 ) = SUM 552 450 CONTINUE 553 END IF 554 JJ = JJ + JB 555 END IF 556* 557 IF( MYROW.EQ.IAROW ) 558 $ II = II + JB 559 IAROW = MOD( IAROW+1, NPROW ) 560 IACOL = MOD( IACOL+1, NPCOL ) 561* 562* Loop over remaining block of columns 563* 564 DO 520 J = JN+1, JA+N-1, DESCA( NB_ ) 565 JB = MIN( JA+N-J, DESCA( NB_ ) ) 566* 567 IF( MYCOL.EQ.IACOL ) THEN 568 IF( MYROW.EQ.IAROW ) THEN 569 IF( UDIAG ) THEN 570 DO 470 LL = JJ, JJ + JB -1 571 SUM = ONE 572 DO 460 KK = II+LL-JJ+1, IIA+MP-1 573 SUM = SUM + ABS( A( IOFFA+KK ) ) 574 460 CONTINUE 575 IOFFA = IOFFA + LDA 576 WORK( LL-JJA+1 ) = SUM 577 470 CONTINUE 578 ELSE 579 DO 490 LL = JJ, JJ + JB -1 580 SUM = ZERO 581 DO 480 KK = II+LL-JJ, IIA+MP-1 582 SUM = SUM + ABS( A( IOFFA+KK ) ) 583 480 CONTINUE 584 IOFFA = IOFFA + LDA 585 WORK( LL-JJA+1 ) = SUM 586 490 CONTINUE 587 END IF 588 ELSE 589 DO 510 LL = JJ, JJ + JB -1 590 SUM = ZERO 591 DO 500 KK = II, IIA+MP-1 592 SUM = SUM + ABS( A( IOFFA+KK ) ) 593 500 CONTINUE 594 IOFFA = IOFFA + LDA 595 WORK( LL-JJA+1 ) = SUM 596 510 CONTINUE 597 END IF 598 JJ = JJ + JB 599 END IF 600* 601 IF( MYROW.EQ.IAROW ) 602 $ II = II + JB 603 IAROW = MOD( IAROW+1, NPROW ) 604 IACOL = MOD( IACOL+1, NPCOL ) 605* 606 520 CONTINUE 607* 608 END IF 609* 610* Find sum of global matrix columns and store on row 0 of 611* process grid 612* 613 CALL SGSUM2D( ICTXT, 'Columnwise', ' ', 1, NQ, WORK, 1, 614 $ 0, MYCOL ) 615* 616* Find maximum sum of columns for 1-norm 617* 618 IF( MYROW.EQ.0 ) THEN 619 IF( NQ.GT.0 ) THEN 620 VALUE = WORK( ISAMAX( NQ, WORK, 1 ) ) 621 ELSE 622 VALUE = ZERO 623 END IF 624 CALL SGAMX2D( ICTXT, 'Rowwise', ' ', 1, 1, VALUE, 1, KK, LL, 625 $ -1, 0, 0 ) 626 END IF 627* 628************************************************************************ 629* infinity norm 630* 631 ELSE IF( LSAME( NORM, 'I' ) ) THEN 632* 633 IF( LSAME( UPLO, 'U' ) ) THEN 634 DO 540 KK = IIA, IIA+MP-1 635 WORK( KK ) = ZERO 636 540 CONTINUE 637 ELSE 638 DO 570 KK = IIA, IIA+MP-1 639 WORK( KK ) = ZERO 640 570 CONTINUE 641 END IF 642* 643 IF( LSAME( UPLO, 'U' ) ) THEN 644* 645* Upper triangular matrix 646* 647 II = IIA 648 JJ = JJA 649 JN = MIN( ICEIL( JA, DESCA( NB_ ) ) * DESCA( NB_ ), JA+N-1 ) 650 JB = JN-JA+1 651* 652 IF( MYCOL.EQ.IACOL ) THEN 653 IF( MYROW.EQ.IAROW ) THEN 654 IF( UDIAG ) THEN 655 DO 590 LL = JJ, JJ + JB -1 656 DO 580 KK = IIA, MIN( II+LL-JJ-1, IIA+MP-1 ) 657 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 658 $ ABS( A( IOFFA+KK ) ) 659 580 CONTINUE 660* Unit diagonal entry 661 KK = II+LL-JJ 662 IF (KK <= IIA+MP-1) THEN 663 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + ONE 664 ENDIF 665 IOFFA = IOFFA + LDA 666 590 CONTINUE 667 ELSE 668 DO 610 LL = JJ, JJ + JB -1 669 DO 600 KK = IIA, MIN( II+LL-JJ, IIA+MP-1 ) 670 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 671 $ ABS( A( IOFFA+KK ) ) 672 600 CONTINUE 673 IOFFA = IOFFA + LDA 674 610 CONTINUE 675 END IF 676 ELSE 677 DO 630 LL = JJ, JJ + JB -1 678 DO 620 KK = IIA, MIN( II-1, IIA+MP-1 ) 679 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 680 $ ABS( A( IOFFA+KK ) ) 681 620 CONTINUE 682 IOFFA = IOFFA + LDA 683 630 CONTINUE 684 END IF 685 JJ = JJ + JB 686 END IF 687* 688 IF( MYROW.EQ.IAROW ) 689 $ II = II + JB 690 IAROW = MOD( IAROW+1, NPROW ) 691 IACOL = MOD( IACOL+1, NPCOL ) 692* 693* Loop over remaining block of columns 694* 695 DO 700 J = JN+1, JA+N-1, DESCA( NB_ ) 696 JB = MIN( JA+N-J, DESCA( NB_ ) ) 697* 698 IF( MYCOL.EQ.IACOL ) THEN 699 IF( MYROW.EQ.IAROW ) THEN 700 IF( UDIAG ) THEN 701 DO 650 LL = JJ, JJ + JB -1 702 DO 640 KK = IIA, MIN( II+LL-JJ-1, IIA+MP-1 ) 703 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 704 $ ABS( A( IOFFA+KK ) ) 705 640 CONTINUE 706* Unit diagonal entry 707 KK = II+LL-JJ 708 IF (KK <= IIA+MP-1) THEN 709 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + ONE 710 ENDIF 711 IOFFA = IOFFA + LDA 712 650 CONTINUE 713 ELSE 714 DO 670 LL = JJ, JJ + JB -1 715 DO 660 KK = IIA, MIN( II+LL-JJ, IIA+MP-1 ) 716 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 717 $ ABS( A( IOFFA+KK ) ) 718 660 CONTINUE 719 IOFFA = IOFFA + LDA 720 670 CONTINUE 721 END IF 722 ELSE 723 DO 690 LL = JJ, JJ + JB -1 724 DO 680 KK = IIA, MIN( II-1, IIA+MP-1 ) 725 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 726 $ ABS( A( IOFFA+KK ) ) 727 680 CONTINUE 728 IOFFA = IOFFA + LDA 729 690 CONTINUE 730 END IF 731 JJ = JJ + JB 732 END IF 733* 734 IF( MYROW.EQ.IAROW ) 735 $ II = II + JB 736 IAROW = MOD( IAROW+1, NPROW ) 737 IACOL = MOD( IACOL+1, NPCOL ) 738* 739 700 CONTINUE 740* 741 ELSE 742* 743* Lower triangular matrix 744* 745 II = IIA 746 JJ = JJA 747 JN = MIN( ICEIL( JA, DESCA( NB_ ) ) * DESCA( NB_ ), JA+N-1 ) 748 JB = JN-JA+1 749* 750 IF( MYCOL.EQ.IACOL ) THEN 751 IF( MYROW.EQ.IAROW ) THEN 752 IF( UDIAG ) THEN 753 DO 720 LL = JJ, JJ + JB -1 754* Unit diagonal entry 755 KK = II+LL-JJ 756 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + ONE 757 DO 710 KK = II+LL-JJ+1, IIA+MP-1 758 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 759 $ ABS( A( IOFFA+KK ) ) 760 710 CONTINUE 761 IOFFA = IOFFA + LDA 762 720 CONTINUE 763 ELSE 764 DO 740 LL = JJ, JJ + JB -1 765 DO 730 KK = II+LL-JJ, IIA+MP-1 766 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 767 $ ABS( A( IOFFA+KK ) ) 768 730 CONTINUE 769 IOFFA = IOFFA + LDA 770 740 CONTINUE 771 END IF 772 ELSE 773 DO 760 LL = JJ, JJ + JB -1 774 DO 750 KK = II, IIA+MP-1 775 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 776 $ ABS( A( IOFFA+KK ) ) 777 750 CONTINUE 778 IOFFA = IOFFA + LDA 779 760 CONTINUE 780 END IF 781 JJ = JJ + JB 782 END IF 783* 784 IF( MYROW.EQ.IAROW ) 785 $ II = II + JB 786 IAROW = MOD( IAROW+1, NPROW ) 787 IACOL = MOD( IACOL+1, NPCOL ) 788* 789* Loop over remaining block of columns 790* 791 DO 830 J = JN+1, JA+N-1, DESCA( NB_ ) 792 JB = MIN( JA+N-J, DESCA( NB_ ) ) 793* 794 IF( MYCOL.EQ.IACOL ) THEN 795 IF( MYROW.EQ.IAROW ) THEN 796 IF( UDIAG ) THEN 797 DO 780 LL = JJ, JJ + JB -1 798* Unit diagonal entry 799 KK = II+LL-JJ 800 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + ONE 801 DO 770 KK = II+LL-JJ+1, IIA+MP-1 802 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 803 $ ABS( A( IOFFA+KK ) ) 804 770 CONTINUE 805 IOFFA = IOFFA + LDA 806 780 CONTINUE 807 ELSE 808 DO 800 LL = JJ, JJ + JB -1 809 DO 790 KK = II+LL-JJ, IIA+MP-1 810 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 811 $ ABS( A( IOFFA+KK ) ) 812 790 CONTINUE 813 IOFFA = IOFFA + LDA 814 800 CONTINUE 815 END IF 816 ELSE 817 DO 820 LL = JJ, JJ + JB -1 818 DO 810 KK = II, IIA+MP-1 819 WORK( KK-IIA+1 ) = WORK( KK-IIA+1 ) + 820 $ ABS( A( IOFFA+KK ) ) 821 810 CONTINUE 822 IOFFA = IOFFA + LDA 823 820 CONTINUE 824 END IF 825 JJ = JJ + JB 826 END IF 827* 828 IF( MYROW.EQ.IAROW ) 829 $ II = II + JB 830 IAROW = MOD( IAROW+1, NPROW ) 831 IACOL = MOD( IACOL+1, NPCOL ) 832* 833 830 CONTINUE 834* 835 END IF 836* 837* Find sum of global matrix rows and store on column 0 of 838* process grid 839* 840 CALL SGSUM2D( ICTXT, 'Rowwise', ' ', MP, 1, WORK, MAX( 1, MP ), 841 $ MYROW, 0 ) 842* 843* Find maximum sum of rows for Infinity-norm 844* 845 IF( MYCOL.EQ.0 ) THEN 846 IF( MP.GT.0 ) THEN 847 VALUE = WORK( ISAMAX( MP, WORK, 1 ) ) 848 ELSE 849 VALUE = ZERO 850 END IF 851 CALL SGAMX2D( ICTXT, 'Columnwise', ' ', 1, 1, VALUE, 1, KK, 852 $ LL, -1, 0, 0 ) 853 END IF 854* 855************************************************************************ 856* Frobenius norm 857* SSQ(1) is scale 858* SSQ(2) is sum-of-squares 859* 860 ELSE IF( LSAME( NORM, 'F' ) .OR. LSAME( NORM, 'E' ) ) THEN 861* 862 IF( UDIAG ) THEN 863 SSQ(1) = ONE 864 SSQ(2) = REAL( MIN( M, N ) ) / REAL( NPROW*NPCOL ) 865 ELSE 866 SSQ(1) = ZERO 867 SSQ(2) = ONE 868 END IF 869* 870 IF( LSAME( UPLO, 'U' ) ) THEN 871* 872* *********************** 873* Upper triangular matrix 874* 875 II = IIA 876 JJ = JJA 877 JN = MIN( ICEIL( JA, DESCA( NB_ ) ) * DESCA( NB_ ), JA+N-1 ) 878 JB = JN-JA+1 879* 880* First block column of sub-matrix. 881* 882 IF( MYCOL.EQ.IACOL ) THEN 883 IF( MYROW.EQ.IAROW ) THEN 884* This process has part of current block column, 885* including diagonal block. 886 IF( UDIAG ) THEN 887 DO 840 LL = JJ, JJ + JB -1 888 COLSSQ(1) = ZERO 889 COLSSQ(2) = ONE 890 CALL SLASSQ( MIN( II+LL-JJ-1, IIA+MP-1 )-IIA+1, 891 $ A( IIA+IOFFA ), 1, 892 $ COLSSQ(1), COLSSQ(2) ) 893 CALL SCOMBSSQ( SSQ, COLSSQ ) 894 IOFFA = IOFFA + LDA 895 840 CONTINUE 896 ELSE 897 DO 850 LL = JJ, JJ + JB -1 898 COLSSQ(1) = ZERO 899 COLSSQ(2) = ONE 900 CALL SLASSQ( MIN( II+LL-JJ, IIA+MP-1 )-IIA+1, 901 $ A( IIA+IOFFA ), 1, 902 $ COLSSQ(1), COLSSQ(2) ) 903 CALL SCOMBSSQ( SSQ, COLSSQ ) 904 IOFFA = IOFFA + LDA 905 850 CONTINUE 906 END IF 907 ELSE 908* This rank has part of current block column, 909* but not diagonal block. 910* It seems this lassq will be length 0, since ii = iia. 911 DO 860 LL = JJ, JJ + JB -1 912 COLSSQ(1) = ZERO 913 COLSSQ(2) = ONE 914 CALL SLASSQ( MIN( II-1, IIA+MP-1 )-IIA+1, 915 $ A( IIA+IOFFA ), 1, 916 $ COLSSQ(1), COLSSQ(2) ) 917 CALL SCOMBSSQ( SSQ, COLSSQ ) 918 IOFFA = IOFFA + LDA 919 860 CONTINUE 920 END IF 921 JJ = JJ + JB 922 END IF 923* 924* If this process has part of current block row, advance ii, 925* then advance iarow, iacol to next diagonal block. 926* 927 IF( MYROW.EQ.IAROW ) 928 $ II = II + JB 929 IAROW = MOD( IAROW+1, NPROW ) 930 IACOL = MOD( IACOL+1, NPCOL ) 931* 932* Loop over remaining block columns 933* 934 DO 900 J = JN+1, JA+N-1, DESCA( NB_ ) 935 JB = MIN( JA+N-J, DESCA( NB_ ) ) 936* 937 IF( MYCOL.EQ.IACOL ) THEN 938 IF( MYROW.EQ.IAROW ) THEN 939 IF( UDIAG ) THEN 940 DO 870 LL = JJ, JJ + JB -1 941 COLSSQ(1) = ZERO 942 COLSSQ(2) = ONE 943 CALL SLASSQ( MIN(II+LL-JJ-1, IIA+MP-1)-IIA+1, 944 $ A( IIA+IOFFA ), 1, 945 $ COLSSQ(1), COLSSQ(2) ) 946 CALL SCOMBSSQ( SSQ, COLSSQ ) 947 IOFFA = IOFFA + LDA 948 870 CONTINUE 949 ELSE 950 DO 880 LL = JJ, JJ + JB -1 951 COLSSQ(1) = ZERO 952 COLSSQ(2) = ONE 953 CALL SLASSQ( MIN( II+LL-JJ, IIA+MP-1 )-IIA+1, 954 $ A( IIA+IOFFA ), 1, 955 $ COLSSQ(1), COLSSQ(2) ) 956 CALL SCOMBSSQ( SSQ, COLSSQ ) 957 IOFFA = IOFFA + LDA 958 880 CONTINUE 959 END IF 960 ELSE 961 DO 890 LL = JJ, JJ + JB -1 962 COLSSQ(1) = ZERO 963 COLSSQ(2) = ONE 964 CALL SLASSQ( MIN( II-1, IIA+MP-1 )-IIA+1, 965 $ A( IIA+IOFFA ), 1, 966 $ COLSSQ(1), COLSSQ(2) ) 967 CALL SCOMBSSQ( SSQ, COLSSQ ) 968 IOFFA = IOFFA + LDA 969 890 CONTINUE 970 END IF 971 JJ = JJ + JB 972 END IF 973* 974 IF( MYROW.EQ.IAROW ) 975 $ II = II + JB 976 IAROW = MOD( IAROW+1, NPROW ) 977 IACOL = MOD( IACOL+1, NPCOL ) 978* 979 900 CONTINUE 980* 981 ELSE 982* 983* *********************** 984* Lower triangular matrix 985* 986 II = IIA 987 JJ = JJA 988 JN = MIN( ICEIL( JA, DESCA( NB_ ) ) * DESCA( NB_ ), JA+N-1 ) 989 JB = JN-JA+1 990* 991 IF( MYCOL.EQ.IACOL ) THEN 992 IF( MYROW.EQ.IAROW ) THEN 993 IF( UDIAG ) THEN 994 DO 910 LL = JJ, JJ + JB -1 995 COLSSQ(1) = ZERO 996 COLSSQ(2) = ONE 997 CALL SLASSQ( IIA+MP-(II+LL-JJ+1), 998 $ A( II+LL-JJ+1+IOFFA ), 1, 999 $ COLSSQ(1), COLSSQ(2) ) 1000 CALL SCOMBSSQ( SSQ, COLSSQ ) 1001 IOFFA = IOFFA + LDA 1002 910 CONTINUE 1003 ELSE 1004 DO 920 LL = JJ, JJ + JB -1 1005 COLSSQ(1) = ZERO 1006 COLSSQ(2) = ONE 1007 CALL SLASSQ( IIA+MP-(II+LL-JJ), 1008 $ A( II+LL-JJ+IOFFA ), 1, 1009 $ COLSSQ(1), COLSSQ(2) ) 1010 CALL SCOMBSSQ( SSQ, COLSSQ ) 1011 IOFFA = IOFFA + LDA 1012 920 CONTINUE 1013 END IF 1014 ELSE 1015 DO 930 LL = JJ, JJ + JB -1 1016 COLSSQ(1) = ZERO 1017 COLSSQ(2) = ONE 1018 CALL SLASSQ( IIA+MP-II, A( II+IOFFA ), 1, 1019 $ COLSSQ(1), COLSSQ(2) ) 1020 CALL SCOMBSSQ( SSQ, COLSSQ ) 1021 IOFFA = IOFFA + LDA 1022 930 CONTINUE 1023 END IF 1024 JJ = JJ + JB 1025 END IF 1026* 1027 IF( MYROW.EQ.IAROW ) 1028 $ II = II + JB 1029 IAROW = MOD( IAROW+1, NPROW ) 1030 IACOL = MOD( IACOL+1, NPCOL ) 1031* 1032* Loop over remaining block of columns 1033* 1034 DO 970 J = JN+1, JA+N-1, DESCA( NB_ ) 1035 JB = MIN( JA+N-J, DESCA( NB_ ) ) 1036* 1037 IF( MYCOL.EQ.IACOL ) THEN 1038 IF( MYROW.EQ.IAROW ) THEN 1039 IF( UDIAG ) THEN 1040 DO 940 LL = JJ, JJ + JB -1 1041 COLSSQ(1) = ZERO 1042 COLSSQ(2) = ONE 1043 CALL SLASSQ( IIA+MP-(II+LL-JJ+1), 1044 $ A( II+LL-JJ+1+IOFFA ), 1, 1045 $ COLSSQ(1), COLSSQ(2) ) 1046 CALL SCOMBSSQ( SSQ, COLSSQ ) 1047 IOFFA = IOFFA + LDA 1048 940 CONTINUE 1049 ELSE 1050 DO 950 LL = JJ, JJ + JB -1 1051 COLSSQ(1) = ZERO 1052 COLSSQ(2) = ONE 1053 CALL SLASSQ( IIA+MP-(II+LL-JJ), 1054 $ A( II+LL-JJ+IOFFA ), 1, 1055 $ COLSSQ(1), COLSSQ(2) ) 1056 CALL SCOMBSSQ( SSQ, COLSSQ ) 1057 IOFFA = IOFFA + LDA 1058 950 CONTINUE 1059 END IF 1060 ELSE 1061 DO 960 LL = JJ, JJ + JB -1 1062 COLSSQ(1) = ZERO 1063 COLSSQ(2) = ONE 1064 CALL SLASSQ( IIA+MP-II, A( II+IOFFA ), 1, 1065 $ COLSSQ(1), COLSSQ(2) ) 1066 CALL SCOMBSSQ( SSQ, COLSSQ ) 1067 IOFFA = IOFFA + LDA 1068 960 CONTINUE 1069 END IF 1070 JJ = JJ + JB 1071 END IF 1072* 1073 IF( MYROW.EQ.IAROW ) 1074 $ II = II + JB 1075 IAROW = MOD( IAROW+1, NPROW ) 1076 IACOL = MOD( IACOL+1, NPCOL ) 1077* 1078 970 CONTINUE 1079* 1080 END IF 1081* 1082* *********************** 1083* Perform the global scaled sum 1084* 1085 CALL PSTREECOMB( ICTXT, 'All', 2, SSQ, 0, 0, SCOMBSSQ ) 1086 VALUE = SSQ( 1 ) * SQRT( SSQ( 2 ) ) 1087* 1088 END IF 1089* 1090* Broadcast the result to every process in the grid. 1091* 1092 IF( MYROW.EQ.0 .AND. MYCOL.EQ.0 ) THEN 1093 CALL SGEBS2D( ICTXT, 'All', ' ', 1, 1, VALUE, 1 ) 1094 ELSE 1095 CALL SGEBR2D( ICTXT, 'All', ' ', 1, 1, VALUE, 1, 0, 0 ) 1096 END IF 1097* 1098 PSLANTR = VALUE 1099* 1100 RETURN 1101* 1102* End of PSLANTR 1103* 1104 END 1105