29 TYPE(
lrb_type),
INTENT(OUT) :: LRB_OUT
30 INTEGER,
INTENT(IN) :: K,M,N
31 LOGICAL,
INTENT(IN) :: ISLR
43 & K490, K491, K492, K20, K60, IDAD, K38,
44 & LRSTATUS, N, LRGROUPS)
45 INTEGER,
INTENT(IN) :: INODE, NFRONT, NASS, BLRON, K489, K490,
46 & K491, K492, NIV, K20, K60, IDAD, K38
47 INTEGER,
INTENT(OUT):: LRSTATUS
48 INTEGER,
INTENT(IN):: N
49 INTEGER,
INTENT(IN),
OPTIONAL :: LRGROUPS(N)
52 LOGICAL :: COMPRESS_PANEL, COMPRESS_CB
54 compress_panel = .false.
55 IF ((blron.NE.0).and.(
56 & ((k492.LT.0).and.inode.EQ.abs(k492))
58 & ( (k492.GT.0).and.(k491.LE.nfront)
59 & .and.(k490.LE.nass))))
THEN
60 compress_panel = .true.
63 compress_panel =.false.
65 IF (
present(lrgroups))
THEN
66 IF (lrgroups(inode) .LT. 0) compress_panel = .false.
71 & (k489.GT.0.AND.(k489.NE.2.OR.niv.EQ.2))
73 & ((k492.LT.0).and.inode.EQ.abs(k492))
75 & ((k492.GT.0).AND.(nfront-nass.GT.k491))))
79 IF (.NOT.compress_panel) compress_cb=.false.
80 IF (compress_panel.OR.compress_cb)
THEN
81 IF (compress_cb.AND.(.NOT.compress_panel))
THEN
83 ELSE IF (compress_panel.AND.(.NOT.compress_cb))
THEN
94 IF ( inode .EQ. k20 .AND. k60 .NE. 0 )
THEN
100 IF ( idad .EQ. k38 .AND. k38 .NE.0 )
THEN
101 compress_cb = .false.
102 IF (lrstatus.GE.2)
THEN
110 SUBROUTINE alloc_lrb(LRB_OUT,K,M,N,ISLR,IFLAG,IERROR,KEEP8)
111 TYPE(
lrb_type),
INTENT(OUT) :: LRB_OUT
112 INTEGER,
INTENT(IN) :: K,M,N
113 INTEGER,
INTENT(INOUT) :: IFLAG, IERROR
114 LOGICAL,
INTENT(IN) :: ISLR
115 INTEGER(8) :: KEEP8(150)
116 INTEGER :: MEM, allocok
118 parameter(zero=(0.0e0,0.0e0))
123 IF ((m.EQ.0).OR.(n.EQ.0))
THEN
133 allocate(lrb_out%Q(m,k),lrb_out%R(k,n),stat=allocok)
134 IF (allocok > 0)
THEN
142 allocate(lrb_out%Q(m,n),stat=allocok)
143 IF (allocok > 0)
THEN
155 & .true., keep8, iflag, ierror, .true., .true.)
159 & IFLAG, IERROR, KEEP8)
160 TYPE(
lrb_type),
INTENT(IN) :: ACC_LRB
161 TYPE(
lrb_type),
INTENT(OUT) :: LRB_OUT
162 INTEGER,
INTENT(IN) :: K, M, N, LorU
163 INTEGER,
INTENT(INOUT) :: IFLAG,
164 INTEGER(8) :: KEEP8(150)
167 CALL alloc_lrb(lrb_out,k,m,n,.true.,iflag,ierror,keep8)
168 IF (iflag.LT.0)
RETURN
170 lrb_out%Q(1:m,i) = acc_lrb%Q(1:m,i)
171 lrb_out%R(i,1:n) = -acc_lrb%R(i,1:n)
174 CALL alloc_lrb(lrb_out,k,n,m,.true.,iflag,ierror,keep8)
175 IF (iflag.LT.0)
RETURN
177 lrb_out%Q(1:n,i) = acc_lrb%R(i,1:n)
178 lrb_out%R(i,1:m) = -acc_lrb%Q(1:m,i)
183 & NPARTSCB, NCB, IBCKSZ, ONLYCB, K472)
184 INTEGER,
INTENT(IN) :: IBCKSZ, NASS, NCB
185 INTEGER,
INTENT(INOUT) :: NPARTSCB,
186 INTEGER,
POINTER,
DIMENSION(:) :: CUT
187 INTEGER,
POINTER,
DIMENSION(:) :: NEW_CUT
188 INTEGER :: I, INEW, MINSIZE, NEW_NPARTSASS, allocok
189 LOGICAL :: ONLYCB, TRACE
190 INTEGER,
INTENT(IN) :: K472
191 INTEGER :: IBCKSZ2,IFLAG,IERROR
192 ALLOCATE(new_cut(
max(npartsass,1)+npartscb+1),stat=allocok)
193 IF (allocok > 0)
THEN
195 ierror =
max(npartsass,1)+npartscb+1
196 write(*,*)
'Allocation problem in BLR routine REGROUPING2:',
197 &
' not enough memory? memory requested = ' , ierror
201 minsize = int(ibcksz2 / 2)
202 new_npartsass =
max(npartsass,1)
203 IF (.NOT. onlycb)
THEN
207 DO WHILE (i .LE. npartsass + 1)
208 new_cut(inew) = cut(i)
210 IF (new_cut(inew) - new_cut(inew-1) .GT. minsize)
THEN
219 IF (inew .NE. 2)
THEN
220 new_cut(inew-1) = new_cut(inew)
224 new_npartsass = inew - 1
227 DO i=1,
max(npartsass,1)+1
231 IF (ncb .EQ. 0)
GO TO 50
232 inew = new_npartsass+2
233 i =
max(npartsass,1) + 2
234 DO WHILE (i .LE.
max(npartsass,1) + npartscb + 1)
235 new_cut(inew) = cut(i)
237 IF (new_cut(inew) - new_cut(inew-1) .GT. minsize)
THEN
246 IF (inew .NE. new_npartsass+2)
THEN
247 new_cut(inew-1) = new_cut(inew)
251 npartscb = inew - 1 - new_npartsass
253 npartsass = new_npartsass
255 ALLOCATE(cut(npartsass+npartscb+1),stat=allocok)
256 IF (allocok > 0)
THEN
258 ierror = npartsass+npartscb+1
259 write(*,*)
'Allocation problem in BLR routine REGROUPING2:',
260 &
' not enough memory? memory requested = ' , ierror
263 DO i=1,npartsass+npartscb+1
269 & NIV, SYM, LorU, IW, OFFSET_IW)
273 INTEGER(8),
intent(in) :: LA
274 INTEGER,
intent(in) :: NFRONT, NIV, SYM, LorU, LDA
275 INTEGER(8),
intent(in) :: POSELT_LOCAL
276 COMPLEX,
intent(inout) :: A(LA)
277 TYPE(LRB_TYPE),
intent(inout) :: LRB
278 INTEGER,
OPTIONAL:: OFFSET_IW
279 INTEGER,
OPTIONAL :: IW(*)
283 INTEGER(8) :: DPOS, POSPV1, POSPV2, OFFDAG
284 INTEGER :: M, N, I, J
285 COMPLEX,
POINTER :: LR_BLOCK_PTR(:,:)
286 COMPLEX :: ONE, MONE, ZERO
287 COMPLEX :: MULT1, MULT2, A11, DETPIV, A22, A12
288 PARAMETER (ONE=(1.0e0,0.0e0), mone=(-1.0e0,0.0e0))
289 parameter(zero=(0.0e0,0.0e0))
293 lr_block_ptr => lrb%R
296 lr_block_ptr => lrb%Q
302 IF (sym.EQ.0.AND.loru.EQ.0)
THEN
303 CALL ctrsm(
'R',
'L',
'T',
'N', m, n, one,
304 & a(poselt_local), nfront,
305 & lr_block_ptr(1,1), m)
307 CALL ctrsm(
'R',
'U',
'N',
'U', m, n, one,
308 & a(poselt_local), lda,
309 & lr_block_ptr(1,1), m)
312 IF (.NOT.
present(offset_iw))
THEN
313 write(*,*)
'Internal error in ',
321 IF(iw(offset_iw+i-1) .GT. 0)
THEN
324 CALL cscal(m, a11, lr_block_ptr(1,i), 1)
325 dpos = dpos + int(lda + 1,8)
330 pospv2 = dpos+ int(lda + 1,8)
335 detpiv = a11*a22 - a12**2
337 a11 = a(pospv2)/detpiv
340 mult1 = a11*lr_block_ptr(j,i)+a12*lr_block_ptr(j,i+1)
341 mult2 = a12*lr_block_ptr(j,i)+a22*lr_block_ptr(j,i+1)
342 lr_block_ptr(j,i) = mult1
343 lr_block_ptr(j,i+1) = mult2
345 dpos = pospv2 + int(lda + 1,8)
355 & LD_DIAG, IW2, POSELTT, NFRONT, BLOCK, MAXI_CLUSTER)
359 INTEGER(8),
intent(in) :: la
360 COMPLEX,
intent(inout) :: a(la)
361 COMPLEX,
intent(inout),
DIMENSION(:,:) :: SCALED
362 INTEGER,
INTENT(IN) :: LD_DIAG, NFRONT, IW2(*)
363 INTEGER(8),
INTENT(IN) :: POSELTT
364 COMPLEX,
INTENT(IN),
OPTIONAL :: DIAG(*)
365 INTEGER,
INTENT(IN) :: MAXI_CLUSTER
366 COMPLEX,
intent(inout) :: BLOCK(MAXI_CLUSTER)
368 COMPLEX :: PIV1, PIV2, OFFDIAG
375 DO WHILE (j <= lrb%N)
377 scaled(1:nrows,j) = diag(1+ld_diag*(j-1)+j-1)
378 & * scaled(1:nrows,j)
381 piv1 = diag(1+ld_diag*(j-1)+j-1)
382 piv2 = diag(1+ld_diag*j+j)
383 offdiag = diag(1+ld_diag*(j-1)+j)
384 block(1:nrows) = scaled(1:nrows,j)
385 scaled(1:nrows,j) = piv1 * scaled(1:nrows,j)
386 & + offdiag * scaled(1:nrows,j+1)
387 scaled(1:nrows,j+1) = offdiag * block(1:nrows)
388 & + piv2 * scaled(1:nrows,j+1)
395 & A, LA, POSELTT, NFRONT, SYM,
397 & MIDBLK_COMPRESS, TOLEPS, TOL_OPT, KPERCENT,
400C Start of OPTIONAL arguments
404 & DIAG, LD_DIAG, IW2, BLOCK
408 TYPE(
lrb_type),
INTENT(IN) :: LRB1,LRB2
409 INTEGER(8),
intent(in) :: LA
410 COMPLEX,
intent(inout) :: A(LA)
411 INTEGER,
INTENT(IN) :: NFRONT, SYM, TOL_OPT
412 INTEGER,
INTENT(INOUT) :: IFLAG, IERROR
413 INTEGER(8),
INTENT(IN) :: POSELTT
414 COMPLEX,
INTENT(IN),
OPTIONAL :: DIAG(*)
415 INTEGER,
INTENT(IN),
OPTIONAL :: LD_DIAG, IW2(*)
416 INTEGER,
intent(in) :: MIDBLK_COMPRESS, KPERCENT
417 REAL,
intent(in) :: TOLEPS
418 COMPLEX :: ALPHA,BETA
419 LOGICAL,
INTENT(OUT) :: BUILDQ
420 COMPLEX,
intent(inout),
OPTIONAL :: BLOCK(*)
421 INTEGER,
INTENT(IN),
OPTIONAL :: LorU
422 LOGICAL,
INTENT(IN) :: LUA_ACTIVATED
423 INTEGER,
INTENT(IN),
OPTIONAL :: MAXI_CLUSTER
424 INTEGER,
INTENT(IN),
OPTIONAL :: MAXI_RANK
425 TYPE(LRB_TYPE),
INTENT(INOUT),
OPTIONAL :: LRB3
426 COMPLEX,
POINTER,
DIMENSION(:,:) :: XY_YZ
427 COMPLEX,
ALLOCATABLE,
TARGET,
DIMENSION(:,:) :: XQ, R_Y
428 COMPLEX,
POINTER,
DIMENSION(:,:) :: X, Y, Y1, Y2, Z
429 CHARACTER(len=1) :: SIDE, TRANSY
430 INTEGER :: K_XY, K_YZ, LDY, LDY1, LDY2, K_Y
431 INTEGER :: LDXY_YZ, SAVE_K
432 INTEGER :: I, J, RANK, MAXRANK, INFO, LWORK
433 REAL,
ALLOCATABLE :: RWORK_RRQR(:)
434 COMPLEX,
ALLOCATABLE :: WORK_RRQR(:), TAU_RRQR(:),
436 INTEGER,
ALLOCATABLE :: JPVT_RRQR(:)
437 INTEGER :: allocok, MREQ
438 REAL,
EXTERNAL ::scnrm2
439 COMPLEX :: ONE, MONE, ZERO
440 parameter(one=(1.0e0,0.0e0), mone=(-1.0e0,0.0e0))
441 parameter(zero=(0.0e0,0.0e0))
442 IF (lrb1%M.EQ.0)
THEN
445 IF (lrb2%M.EQ.0)
THEN
449 IF (lrb1%ISLR.AND.lrb2%ISLR)
THEN
450 IF ((lrb1%K.EQ.0).OR.(lrb2%K.EQ.0))
THEN
453 allocate(y(lrb1%K,lrb2%K),stat=allocok)
454 IF (allocok > 0)
THEN
463 allocate(y1(lrb1%K,lrb1%N),stat=allocok)
464 IF (allocok > 0)
THEN
470 y1(i,j) = lrb1%R(i,j)
474 & ld_diag, iw2, poseltt, nfront, block,
481 CALL cgemm(
'N',
'T', lrb1%K, lrb2%K, k_y, one,
482 & y1(1,1), ldy1, y2(1,1), ldy2, zero, y(1,1), lrb1%K )
483 IF (midblk_compress.GE.1)
THEN
484 lwork = lrb2%K*(lrb2%K+1)
485 allocate(y_rrqr(lrb1%K,lrb2%K),
486 & work_rrqr(lwork), rwork_rrqr(2*lrb2%K),
487 & tau_rrqr(
min(lrb1%K,lrb2%K)),
488 & jpvt_rrqr(lrb2%K),stat=allocok)
489 IF (allocok > 0)
THEN
490 mreq = lrb1%K*lrb2%K + lwork + 2*lrb2%K +
491 &
min(lrb1%K,lrb2%K) + lrb2%K
499 maxrank =
min(lrb1%K, lrb2%K)-1
500 maxrank =
max(1, int((maxrank*kpercent/100)))
503 & lrb1%K, jpvt_rrqr, tau_rrqr, work_rrqr,
504 & lrb2%K, rwork_rrqr, toleps, tol_opt, rank,
507 IF (rank.GT.maxrank)
THEN
508 deallocate(y_rrqr, work_rrqr, rwork_rrqr, tau_rrqr,
516 deallocate(y_rrqr, work_rrqr, rwork_rrqr, tau_rrqr,
523 IF (sym .NE. 0)
deallocate(y1)
526 allocate(xq(lrb1%M,rank), r_y(rank,lrb2%K),
528 IF (allocok > 0)
THEN
529 mreq = lrb1%M*rank + rank*lrb2%K
533 r_y(1:
min(rank,j),jpvt_rrqr(j)) =
534 & y_rrqr(1:
min(rank,j),j)
535 IF(j.LT.rank) r_y(
min(rank,j)+1:
536 & rank,jpvt_rrqr(j))= zero
541 & (lrb1%K, rank, rank, y_rrqr(1,1),
542 & lrb1%K, tau_rrqr(1),
543 & work_rrqr(1), lwork, info )
544 CALL cgemm(
'N',
'N', lrb1%M, rank, lrb1%K, one,
545 & x(1,1), lrb1%M, y_rrqr(1,1), lrb1%K, zero,
547 deallocate(y_rrqr, work_rrqr, rwork_rrqr, tau_rrqr,
562 IF (.NOT.buildq)
THEN
567 IF (lrb1%K .GE. lrb2%K)
THEN
574.AND..NOT.
IF (LRB1%ISLR(LRB2%ISLR)) THEN
575.EQ.
IF (LRB1%K0) THEN
587 allocate(Y(LRB1%K,LRB1%N),stat=allocok)
588 IF (allocok > 0) THEN
597 CALL CMUMPS_LRGEMM_SCALING(LRB1, Y, A, LA, DIAG,
598 & LD_DIAG, IW2, POSELTT, NFRONT, BLOCK,
603.NOT..AND.
IF ((LRB1%ISLR)LRB2%ISLR) THEN
604.EQ.
IF (LRB2%K0) THEN
615 allocate(Y(LRB2%K,LRB2%N),stat=allocok)
616 IF (allocok > 0) THEN
625 CALL CMUMPS_LRGEMM_SCALING(LRB2, Y, A, LA, DIAG,
626 & LD_DIAG, IW2, POSELTT, NFRONT, BLOCK,
632.NOT..AND..NOT.
IF ((LRB1%ISLR)(LRB2%ISLR)) THEN
636 allocate(X(LRB1%M,LRB1%N),stat=allocok)
637 IF (allocok > 0) THEN
646 CALL CMUMPS_LRGEMM_SCALING(LRB1, X, A, LA, DIAG,
647 & LD_DIAG, IW2, POSELTT, NFRONT, BLOCK,
654 IF (LUA_ACTIVATED) THEN
656 IF (SIDE == 'l
') THEN
658 ELSEIF (SIDE == 'r
') THEN
662 IF (SIDE == 'l
') THEN ! LEFT: XY_YZ = X*Y; A = XY_YZ*Z
663.NOT.
IF (LUA_ACTIVATED) THEN
664 allocate(XY_YZ(LRB1%M,K_YZ),stat=allocok)
665 IF (allocok > 0) THEN
671.GT.
IF (SAVE_K+K_YZMAXI_RANK) THEN
673 & 'k_acc+k_cur
',SAVE_K,K_YZ,MAXI_RANK
676.NE.
IF (LRB3%MLRB1%M) THEN
678 & 'lrb1%M =/= lrb3%M
',LRB1%M,LRB3%M
681 XY_YZ => LRB3%Q(1:LRB1%M,SAVE_K+1:SAVE_K+K_YZ)
682 LDXY_YZ = MAXI_CLUSTER
684 LRB3%R(SAVE_K+I,1:LRB2%M) = Z(1:LRB2%M,I)
687 CALL cgemm('n
', TRANSY, LRB1%M, K_YZ, K_XY, ONE,
688 & X(1,1), LRB1%M, Y(1,1), LDY, ZERO, XY_YZ(1,1),
690.NOT.
IF (LUA_ACTIVATED) THEN
691 CALL cgemm('n
', 't
', LRB1%M, LRB2%M, K_YZ, ALPHA,
692 & XY_YZ(1,1), LRB1%M, Z(1,1), LRB2%M, BETA,
693 & A(POSELTT), NFRONT)
696 ELSEIF (SIDE == 'r
') THEN ! RIGHT: XY_YZ = Y*Z; A = X*XY_YZ
697.NOT.
IF (LUA_ACTIVATED) THEN
698 allocate(XY_YZ(K_XY,LRB2%M),stat=allocok)
699 IF (allocok > 0) THEN
705.GT.
IF (SAVE_K+K_XYMAXI_RANK) THEN
707 & 'k_acc+k_cur>k_max:
',SAVE_K,K_XY,MAXI_RANK
710.NE.
IF (LRB3%NLRB2%M) THEN
712 & 'lrb2%M =/= lrb3%N
',LRB2%M,LRB3%N
715 XY_YZ => LRB3%R(SAVE_K+1:SAVE_K+K_XY,1:LRB2%M)
718 LRB3%Q(1:LRB1%M,SAVE_K+I) = X(1:LRB1%M,I)
721 CALL cgemm(TRANSY, 't
', K_XY, LRB2%M, K_YZ, ONE,
722 & Y(1,1), LDY, Z(1,1), LRB2%M, ZERO, XY_YZ(1,1),
724.NOT.
IF (LUA_ACTIVATED) THEN
725 CALL cgemm('n
', 'n
', LRB1%M, LRB2%M, K_XY, ALPHA,
726 & X(1,1), LRB1%M, XY_YZ(1,1), K_XY, BETA, A(POSELTT),
730 ELSE ! SIDE == 'n
' : NONE; A = X*Z
731 CALL cgemm('n
', 't
', LRB1%M, LRB2%M, K_XY, ALPHA,
732 & X(1,1), LRB1%M, Z(1,1), LRB2%M, BETA, A(POSELTT),
743.NOT..AND..NOT.
IF ((LRB1%ISLR)(LRB2%ISLR)) THEN
744.NE.
IF (SYM 0) deallocate(X)
745.NOT..AND.
ELSEIF ((LRB1%ISLR)LRB2%ISLR) THEN
746.NE.
IF (SYM 0) deallocate(Y)
747.AND..NOT.
ELSEIF (LRB1%ISLR(LRB2%ISLR)) THEN
748.NE.
IF (SYM 0) deallocate(Y)
750.NE.
IF (SYM 0) deallocate(Y1)
751.GE..AND.
IF ((MIDBLK_COMPRESS1)BUILDQ) THEN
759 END SUBROUTINE CMUMPS_LRGEMM4
760 SUBROUTINE CMUMPS_DECOMPRESS_ACC(ACC_LRB, MAXI_CLUSTER,
761 & MAXI_RANK, A, LA, POSELTT, NFRONT, NIV, LorU,
763 TYPE(LRB_TYPE),INTENT(INOUT) :: ACC_LRB
764 INTEGER(8), intent(in) :: LA
765 COMPLEX, intent(inout) :: A(LA)
766 INTEGER,INTENT(IN) :: NFRONT, NIV
767 INTEGER,INTENT(IN) :: MAXI_CLUSTER, MAXI_RANK
768 INTEGER(8), INTENT(IN) :: POSELTT
769 LOGICAL, OPTIONAL :: COUNT_FLOPS
770 LOGICAL :: COUNT_FLOPS_LOC
772 COMPLEX :: ONE, MONE, ZERO
773 PARAMETER (ONE=(1.0E0,0.0E0), MONE=(-1.0E0,0.0E0))
774 PARAMETER (ZERO=(0.0E0,0.0E0))
775 IF (present(COUNT_FLOPS)) THEN
776 COUNT_FLOPS_LOC=COUNT_FLOPS
778 COUNT_FLOPS_LOC=.TRUE.
780 CALL cgemm('n
', 'n
', ACC_LRB%M, ACC_LRB%N, ACC_LRB%K,
781 & MONE, ACC_LRB%Q(1,1), MAXI_CLUSTER, ACC_LRB%R(1,1),
782 & MAXI_RANK, ONE, A(POSELTT), NFRONT)
784 END SUBROUTINE CMUMPS_DECOMPRESS_ACC
785 SUBROUTINE CMUMPS_COMPRESS_FR_UPDATES(ACC_LRB, MAXI_CLUSTER,
786 & MAXI_RANK, A, LA, POSELTT, NFRONT, NIV,
787 & TOLEPS, TOL_OPT, KPERCENT, BUILDQ, LorU, CB_COMPRESS)
788 TYPE(LRB_TYPE),INTENT(INOUT) :: ACC_LRB
789 INTEGER(8), intent(in) :: LA
790 COMPLEX, intent(inout) :: A(LA)
791 INTEGER,INTENT(IN) :: NFRONT, NIV, LorU, TOL_OPT
792 INTEGER,INTENT(IN) :: MAXI_CLUSTER, MAXI_RANK, KPERCENT
793 INTEGER(8), INTENT(IN) :: POSELTT
794 REAL, intent(in) :: TOLEPS
795 LOGICAL, INTENT(OUT) :: BUILDQ
796 LOGICAL, INTENT(IN) :: CB_COMPRESS
797 REAL, ALLOCATABLE :: RWORK_RRQR(:)
798 COMPLEX, ALLOCATABLE :: WORK_RRQR(:), TAU_RRQR(:)
799 INTEGER, ALLOCATABLE :: JPVT_RRQR(:)
800 INTEGER :: INFO, RANK, MAXRANK, LWORK
801 INTEGER :: I, J, M, N
802 INTEGER :: allocok, MREQ
803 COMPLEX :: ONE, MONE, ZERO
804 PARAMETER (ONE=(1.0E0,0.0E0), MONE=(-1.0E0,0.0E0))
805 PARAMETER (ZERO=(0.0E0,0.0E0))
808 MAXRANK = floor(real(M*N)/real(M+N))
809 MAXRANK = max (1, int((MAXRANK*KPERCENT/100)))
811 allocate(WORK_RRQR(LWORK), RWORK_RRQR(2*N),
813 & JPVT_RRQR(N), stat=allocok)
814 IF (allocok > 0) THEN
820 & - A(POSELTT+int(I-1,8)*int(NFRONT,8) :
821 & POSELTT+int(I-1,8)*int(NFRONT,8) + int(M-1,8) )
824 CALL CMUMPS_TRUNCATED_RRQR(M, N, ACC_LRB%Q(1,1),
825 & MAXI_CLUSTER, JPVT_RRQR(1), TAU_RRQR(1),
827 & N, RWORK_RRQR(1), TOLEPS, TOL_OPT,
828 & RANK, MAXRANK, INFO,
832 ACC_LRB%R(1:MIN(RANK,J),JPVT_RRQR(J)) =
833 & ACC_LRB%Q(1:MIN(RANK,J),J)
834.LT.
IF(JRANK) ACC_LRB%R(MIN(RANK,J)+1:
835 & RANK,JPVT_RRQR(J))= ZERO
838 & (M, RANK, RANK, ACC_LRB%Q(1,1),
839 & MAXI_CLUSTER, TAU_RRQR(1),
840 & WORK_RRQR(1), LWORK, INFO )
842 A( POSELTT+int(I-1,8)*int(NFRONT,8) :
843 & POSELTT+int(I-1,8)*int(NFRONT,8)+int(M-1,8) ) = ZERO
846 CALL UPD_FLOP_COMPRESS(ACC_LRB, CB_COMPRESS=CB_COMPRESS)
849 ACC_LRB%ISLR = .FALSE.
850 CALL UPD_FLOP_COMPRESS(ACC_LRB, CB_COMPRESS=CB_COMPRESS)
851 ACC_LRB%ISLR = .TRUE.
854 deallocate(JPVT_RRQR, TAU_RRQR, WORK_RRQR, RWORK_RRQR)
858 write(*,*) 'allocation problem in blr routine
860 & 'not enough memory? memory requested =
' , MREQ
863 END SUBROUTINE CMUMPS_COMPRESS_FR_UPDATES
864 SUBROUTINE CMUMPS_RECOMPRESS_ACC(ACC_LRB, MAXI_CLUSTER,
865 & MAXI_RANK, A, LA, POSELTT, NFRONT, NIV,
866 & MIDBLK_COMPRESS, TOLEPS, TOL_OPT, KPERCENT_RMB,
867 & KPERCENT_LUA, NEW_ACC_RANK)
868 TYPE(LRB_TYPE),INTENT(INOUT) :: ACC_LRB
869 INTEGER(8), intent(in) :: LA
870 COMPLEX, intent(inout) :: A(LA)
871 INTEGER,INTENT(IN) :: NFRONT, NIV, TOL_OPT
872 INTEGER :: IFLAG, IERROR
873 INTEGER,INTENT(IN) :: MAXI_CLUSTER, MAXI_RANK, KPERCENT_LUA
874 INTEGER,INTENT(INOUT) :: NEW_ACC_RANK
875 INTEGER(8), INTENT(IN) :: POSELTT
876 INTEGER,intent(in) :: MIDBLK_COMPRESS, KPERCENT_RMB
877 REAL, intent(in) :: TOLEPS
878 REAL, ALLOCATABLE :: RWORK_RRQR(:)
879 COMPLEX, ALLOCATABLE :: WORK_RRQR(:), TAU_RRQR(:)
880 COMPLEX, ALLOCATABLE, DIMENSION(:,:), TARGET :: Q1, R1,
882 INTEGER, ALLOCATABLE :: JPVT_RRQR(:)
883 TYPE(LRB_TYPE) :: LRB1, LRB2
884 INTEGER :: INFO, RANK1, RANK2, RANK, MAXRANK, LWORK
885 LOGICAL :: BUILDQ, BUILDQ1, BUILDQ2, SKIP1, SKIP2
886 INTEGER :: I, J, M, N, K
887 INTEGER :: allocok, MREQ
888 COMPLEX :: ONE, MONE, ZERO
889 PARAMETER (ONE=(1.0E0,0.0E0), MONE=(-1.0E0,0.0E0))
890 PARAMETER (ZERO=(0.0E0,0.0E0))
899 MAXRANK = max (1, int((MAXRANK*KPERCENT_LUA/100)))
902 CALL CMUMPS_RECOMPRESS_ACC_V2(ACC_LRB,
903 & MAXI_CLUSTER, MAXI_RANK, A, LA, POSELTT,
904 & NFRONT, NIV, MIDBLK_COMPRESS, TOLEPS,
905 & TOL_OPT, KPERCENT_RMB, KPERCENT_LUA,
909 MAXRANK = max (1, int((MAXRANK*KPERCENT_LUA/100)))
914.AND.
IF (SKIP1SKIP2) GOTO 1600
915 allocate(Q1(M,K), Q2(N,K),
919 & JPVT_RRQR(K), stat=allocok)
920 IF (allocok > 0) THEN
921 MREQ = LWORK + M*N + N*K+ 4 * K
929 Q1(I,J) = ACC_LRB%Q(I,J)
933 CALL CMUMPS_TRUNCATED_RRQR(M, K, Q1(1,1),
934 & M, JPVT_RRQR(1), TAU_RRQR(1), WORK_RRQR(1),
935 & K, RWORK_RRQR(1), TOLEPS, TOL_OPT, RANK1,
940 allocate(R1(RANK1,K), stat=allocok)
941 IF (allocok > 0) THEN
946 R1(1:MIN(RANK1,J),JPVT_RRQR(J)) =
947 & Q1(1:MIN(RANK1,J),J)
948.LT.
IF(JRANK1) R1(MIN(RANK1,J)+1:
949 & RANK1,JPVT_RRQR(J))= ZERO
952 & (M, RANK1, RANK1, Q1(1,1),
954 & WORK_RRQR(1), LWORK, INFO )
961 Q2(I,J) = ACC_LRB%R(J,I)
965 CALL CMUMPS_TRUNCATED_RRQR(N, K, Q2(1,1),
966 & N, JPVT_RRQR(1), TAU_RRQR(1), WORK_RRQR(1),
967 & K, RWORK_RRQR(1), TOLEPS, TOL_OPT,
968 & RANK2, MAXRANK, INFO,
972 allocate(R2(RANK2,K), stat=allocok)
973 IF (allocok > 0) THEN
978 R2(1:MIN(RANK2,J),JPVT_RRQR(J)) =
979 & Q2(1:MIN(RANK2,J),J)
980.LT.
IF(JRANK2) R2(MIN(RANK2,J)+1:
981 & RANK2,JPVT_RRQR(J))= ZERO
984 & (N, RANK2, RANK2, Q2(1,1),
986 & WORK_RRQR(1), LWORK, INFO )
988 CALL INIT_LRB(LRB1,RANK1,M,K,BUILDQ1)
989 CALL INIT_LRB(LRB2,RANK2,N,K,BUILDQ2)
990.OR.
IF (BUILDQ1BUILDQ2) THEN
996 Q1(I,J) = ACC_LRB%Q(I,J)
1006 Q2(I,J) = ACC_LRB%R(J,I)
1012 CALL CMUMPS_LRGEMM4(MONE, LRB1, LRB2, ONE,
1013 & A, LA, POSELTT, NFRONT, 0, IFLAG, IERROR,
1014 & MIDBLK_COMPRESS-1, TOLEPS, TOL_OPT,
1016 & RANK, BUILDQ, .TRUE., LRB3=ACC_LRB,
1017 & MAXI_RANK=MAXI_RANK, MAXI_CLUSTER=MAXI_CLUSTER)
1018.LT.
IF (IFLAG0) GOTO 100
1019 CALL UPD_FLOP_UPDATE(LRB1, LRB2,
1020 & MIDBLK_COMPRESS-1, RANK, BUILDQ,
1021 & .TRUE., .FALSE., REC_ACC=.TRUE.)
1024 & CALL UPD_FLOP_COMPRESS(LRB1, REC_ACC=.TRUE.)
1026 & CALL UPD_FLOP_COMPRESS(LRB2, REC_ACC=.TRUE.)
1028 IF (BUILDQ1) deallocate(R1)
1029 IF (BUILDQ2) deallocate(R2)
1030 deallocate(JPVT_RRQR, TAU_RRQR, WORK_RRQR, RWORK_RRQR)
1031.AND..GT.
IF (SKIP1(RANK20)) THEN
1041 write(*,*) 'allocation problem in blr routine
1043 & 'not enough memory? memory requested =
' , MREQ
1046 END SUBROUTINE CMUMPS_RECOMPRESS_ACC
1047 RECURSIVE SUBROUTINE CMUMPS_RECOMPRESS_ACC_NARYTREE(
1048 & ACC_LRB, MAXI_CLUSTER, MAXI_RANK, A, LA, POSELTT, KEEP8,
1049 & NFRONT, NIV, MIDBLK_COMPRESS, TOLEPS, TOL_OPT,
1051 & KPERCENT_LUA, K478, RANK_LIST, POS_LIST, NB_NODES,
1053 TYPE(LRB_TYPE),TARGET,INTENT(INOUT) :: ACC_LRB
1054 TYPE(LRB_TYPE),TARGET,INTENT(INOUT),OPTIONAL :: ACC_TMP
1055 INTEGER(8), intent(in) :: LA
1056 COMPLEX, intent(inout) :: A(LA)
1057 INTEGER,INTENT(IN) :: NFRONT, NIV, TOL_OPT
1058 INTEGER,INTENT(IN) :: MAXI_CLUSTER, MAXI_RANK, KPERCENT_LUA
1059 INTEGER(8), INTENT(IN) :: POSELTT
1060 INTEGER(8) :: KEEP8(150)
1061 INTEGER,intent(in) :: MIDBLK_COMPRESS, KPERCENT_RMB
1062 REAL, intent(in) :: TOLEPS
1063 INTEGER,INTENT(IN) :: K478, NB_NODES, LEVEL
1064 INTEGER,INTENT(INOUT) :: RANK_LIST(NB_NODES), POS_LIST(NB_NODES)
1065 TYPE(LRB_TYPE) :: LRB, ACC_NEW
1066 TYPE(LRB_TYPE), POINTER :: LRB_PTR
1068 INTEGER :: I, J, M, N, L, NODE_RANK, NARY, IOFF, IMAX, CURPOS
1069 INTEGER :: NB_NODES_NEW, KTOT, NEW_ACC_RANK
1070 INTEGER, ALLOCATABLE :: RANK_LIST_NEW(:), POS_LIST_NEW(:)
1071 COMPLEX :: ONE, MONE, ZERO
1072 PARAMETER (ONE=(1.0E0,0.0E0), MONE=(-1.0E0,0.0E0))
1073 PARAMETER (ZERO=(0.0E0,0.0E0))
1080 NB_NODES_NEW = NB_NODES/NARY
1081.NE.
IF (NB_NODES_NEW*NARYNB_NODES) THEN
1082 NB_NODES_NEW = NB_NODES_NEW + 1
1084 ALLOCATE(RANK_LIST_NEW(NB_NODES_NEW),POS_LIST_NEW(NB_NODES_NEW),
1086 IF (allocok > 0) THEN
1087 write(*,*) 'allocation error of rank_list_new/pos_list_new
',
1092 NODE_RANK = RANK_LIST(IOFF+1)
1093 CURPOS = POS_LIST(IOFF+1)
1094 IMAX = MIN(NARY,NB_NODES-IOFF)
1097.NE.
IF (POS_LIST(IOFF+I)CURPOS+NODE_RANK) THEN
1098 DO L=0,RANK_LIST(IOFF+I)-1
1099 ACC_LRB%Q(1:M,CURPOS+NODE_RANK+L) =
1100 & ACC_LRB%Q(1:M,POS_LIST(IOFF+I)+L)
1101 ACC_LRB%R(CURPOS+NODE_RANK+L,1:N) =
1102 & ACC_LRB%R(POS_LIST(IOFF+I)+L,1:N)
1104 POS_LIST(IOFF+I) = CURPOS+NODE_RANK
1106 NODE_RANK = NODE_RANK+RANK_LIST(IOFF+I)
1108 CALL INIT_LRB(LRB,NODE_RANK,M,N,.TRUE.)
1109.NOT..OR..EQ.
IF (RESORTLEVEL0) THEN
1110 LRB%Q => ACC_LRB%Q(1:M,CURPOS:CURPOS+NODE_RANK)
1111 LRB%R => ACC_LRB%R(CURPOS:CURPOS+NODE_RANK,1:N)
1113 LRB%Q => ACC_TMP%Q(1:M,CURPOS:CURPOS+NODE_RANK)
1114 LRB%R => ACC_TMP%R(CURPOS:CURPOS+NODE_RANK,1:N)
1116 NEW_ACC_RANK = NODE_RANK-RANK_LIST(IOFF+1)
1117.GT.
IF (NEW_ACC_RANK0) THEN
1118 CALL CMUMPS_RECOMPRESS_ACC(LRB,
1119 & MAXI_CLUSTER, MAXI_RANK, A, LA, POSELTT,
1120 & NFRONT, NIV, MIDBLK_COMPRESS, TOLEPS,
1121 & TOL_OPT, KPERCENT_RMB, KPERCENT_LUA, NEW_ACC_RANK)
1123 RANK_LIST_NEW(J) = LRB%K
1124 POS_LIST_NEW(J) = CURPOS
1126 RANK_LIST_NEW(J) = NODE_RANK
1127 POS_LIST_NEW(J) = CURPOS
1131.GT.
IF (NB_NODES_NEW1) THEN
1133 KTOT = SUM(RANK_LIST_NEW)
1134 CALL INIT_LRB(ACC_NEW,KTOT,M,N,.TRUE.)
1135 ALLOCATE(ACC_NEW%Q(MAXI_CLUSTER,MAXI_RANK),
1136 & ACC_NEW%R(MAXI_RANK,MAXI_CLUSTER), stat=allocok)
1137 IF (allocok > 0) THEN
1138 write(*,*) 'allocation error of acc_new%Q/acc_new%R
',
1142 CALL MUMPS_SORT_INT(NB_NODES_NEW, RANK_LIST_NEW,
1145.EQ.
IF (LEVEL0) THEN
1151 DO L=0,RANK_LIST_NEW(J)-1
1152 ACC_NEW%Q(1:M,CURPOS+L) =
1153 & LRB_PTR%Q(1:M,POS_LIST_NEW(J)+L)
1154 ACC_NEW%R(CURPOS+L,1:N) =
1155 & LRB_PTR%R(POS_LIST_NEW(J)+L,1:N)
1157 POS_LIST_NEW(J) = CURPOS
1158 CURPOS = CURPOS + RANK_LIST_NEW(J)
1160.GT.
IF (LEVEL0) THEN
1161 CALL DEALLOC_LRB(ACC_TMP, KEEP8, 4)
1163 CALL CMUMPS_RECOMPRESS_ACC_NARYTREE(ACC_LRB,
1164 & MAXI_CLUSTER, MAXI_RANK, A, LA, POSELTT, KEEP8,
1165 & NFRONT, NIV, MIDBLK_COMPRESS, TOLEPS, TOL_OPT,
1166 & KPERCENT_RMB, KPERCENT_LUA, K478,
1167 & RANK_LIST_NEW, POS_LIST_NEW, NB_NODES_NEW,
1170 CALL CMUMPS_RECOMPRESS_ACC_NARYTREE(ACC_LRB,
1171 & MAXI_CLUSTER, MAXI_RANK, A, LA, POSELTT, KEEP8,
1172 & NFRONT, NIV, MIDBLK_COMPRESS, TOLEPS, TOL_OPT,
1173 & KPERCENT_RMB, KPERCENT_LUA, K478,
1174 & RANK_LIST_NEW, POS_LIST_NEW, NB_NODES_NEW, LEVEL+1)
1177.NE.
IF (POS_LIST_NEW(1)1) THEN
1178 write(*,*) 'internal error in
',
1181 ACC_LRB%K = RANK_LIST_NEW(1)
1182.AND..GT.
IF (RESORTLEVEL0) THEN
1185 ACC_LRB%Q(I,L) = ACC_TMP%Q(I,L)
1188 ACC_LRB%R(L,I) = ACC_TMP%R(L,I)
1191 CALL DEALLOC_LRB(ACC_TMP, KEEP8, 4)
1194 DEALLOCATE(RANK_LIST_NEW, POS_LIST_NEW)
1195 END SUBROUTINE CMUMPS_RECOMPRESS_ACC_NARYTREE
1196 SUBROUTINE CMUMPS_RECOMPRESS_ACC_V2(ACC_LRB, MAXI_CLUSTER,
1197 & MAXI_RANK, A, LA, POSELTT, NFRONT, NIV,
1198 & MIDBLK_COMPRESS, TOLEPS, TOL_OPT, KPERCENT_RMB,
1199 & KPERCENT_LUA, NEW_ACC_RANK)
1200 TYPE(LRB_TYPE),INTENT(INOUT) :: ACC_LRB
1201 INTEGER(8), intent(in) :: LA
1202 COMPLEX, intent(inout) :: A(LA)
1203 INTEGER,INTENT(IN) :: NFRONT, NIV, TOL_OPT
1204 INTEGER,INTENT(IN) :: MAXI_CLUSTER, MAXI_RANK, KPERCENT_LUA
1205 INTEGER,INTENT(INOUT) :: NEW_ACC_RANK
1206 INTEGER(8), INTENT(IN) :: POSELTT
1207 INTEGER,intent(in) :: MIDBLK_COMPRESS, KPERCENT_RMB
1208 REAL, intent(in) :: TOLEPS
1209 REAL, ALLOCATABLE :: RWORK_RRQR(:)
1210 COMPLEX, ALLOCATABLE :: WORK_RRQR(:), TAU_RRQR(:)
1211 COMPLEX, ALLOCATABLE, DIMENSION(:,:), TARGET ::
1213 INTEGER, ALLOCATABLE :: JPVT_RRQR(:)
1214 INTEGER :: INFO, RANK1, MAXRANK, LWORK
1216 INTEGER :: I, J, M, N, K, K1
1217 INTEGER :: allocok, MREQ
1218 COMPLEX :: ONE, MONE, ZERO
1219 PARAMETER (ONE=(1.0E0,0.0E0), MONE=(-1.0E0,0.0E0))
1220 PARAMETER (ZERO=(0.0E0,0.0E0))
1226 MAXRANK = max (1, int((MAXRANK*KPERCENT_LUA/100)))
1228 allocate(Q1(M,K), PROJ(K1, K),
1229 & WORK_RRQR(LWORK), RWORK_RRQR(2*K),
1231 & JPVT_RRQR(K), stat=allocok)
1232 IF (allocok > 0) THEN
1233 MREQ = M * K + K1 * K + LWORK + 4 * K
1238 Q1(I,J) = ACC_LRB%Q(I,J+K1)
1241 CALL cgemm('t
', 'n
', K1, K, M, ONE, ACC_LRB%Q(1,1),
1242 & MAXI_CLUSTER, Q1(1,1), M, ZERO, PROJ(1,1), K1)
1243 CALL cgemm('n
', 'n
', M, K, K1, MONE, ACC_LRB%Q(1,1),
1244 & MAXI_CLUSTER, PROJ(1,1), K1, ONE, Q1(1,1), M)
1246 CALL CMUMPS_TRUNCATED_RRQR(M, K, Q1(1,1),
1247 & M, JPVT_RRQR(1), TAU_RRQR(1), WORK_RRQR(1),
1248 & K, RWORK_RRQR(1), TOLEPS, TOL_OPT,
1249 & RANK1, MAXRANK, INFO,
1252 allocate(Q2(N,K), stat=allocok)
1253 IF (allocok > 0) THEN
1259 Q2(I,J) = ACC_LRB%R(J+K1,I)
1262 CALL cgemm('n
', 't', k1, n, k, one, proj(1,1), k1,
1263 & q2(1,1), n, one, acc_lrb%R(1,1), maxi_rank)
1264 IF (rank1.GT.0)
THEN
1265 allocate(r1(rank1,k), stat=allocok)
1266 IF (allocok > 0)
THEN
1271 r1(1:
min(rank1,j),jpvt_rrqr(j)) =
1272 & q1(1:
min(rank1,j),j)
1273 IF(j.LT.rank1) r1(
min(rank1,j)+1:
1274 & rank1,jpvt_rrqr(j))= zero
1277 & (m, rank1, rank1, q1(1,1),
1279 & work_rrqr(1), lwork, info )
1282 acc_lrb%Q(i,j+k1) = q1(i,j)
1285 CALL cgemm(
'N',
'T', rank1, n, k, one, r1(1,1), rank1,
1286 & q2(1,1), n, zero, acc_lrb%R(k1+1,1), maxi_rank)
1290 acc_lrb%K = k1 + rank1
1293 deallocate(q1, jpvt_rrqr, tau_rrqr, work_rrqr, rwork_rrqr)
1297 write(*,*)
'Allocation problem in BLR routine
1298 & CMUMPS_RECOMPRESS_ACC_V2: ',
1299 &
'not enough memory? memory requested = ' , mreq
1304 INTEGER,
intent(in) :: CUT_SIZE
1305 INTEGER,
intent(out) :: MAXI_CLUSTER
1306 INTEGER,
POINTER,
DIMENSION(:) :: CUT
1310 IF (cut(i+1) - cut(i) .GE. maxi_cluster)
THEN
1311 maxi_cluster = cut(i+1) - cut(i)
1316 & SYM, FS_OR_CB, I, J, FRFR_UPDATES,
1317 & LBANDSLAVE_IN, K474, BLR_U_COL)
1321 INTEGER,
INTENT(IN) :: NB_BLOCKS, IWHANDLER, SYM, FS_OR_CB, , J
1322 INTEGER,
INTENT(OUT) :: ORDER(NB_BLOCKS), RANK(NB_BLOCKS),
1324 LOGICAL,
OPTIONAL,
INTENT(IN) :: LBANDSLAVE_IN
1325 INTEGER,
OPTIONAL,
INTENT(IN) :: K474
1326 TYPE(
lrb_type),
POINTER,
OPTIONAL :: BLR_U_COL(:)
1330 INTEGER :: K, IND_L, IND_U
1331 LOGICAL :: LBANDSLAVE
1332 TYPE(),
POINTER :: BLR_L(:), BLR_U(:)
1333 IF (
PRESENT(lbandslave_in))
THEN
1334 lbandslave = lbandslave_in
1336 lbandslave = .false.
1338 IF ((sym.NE.0).AND.(fs_or_cb.EQ.0).AND.(j.NE.0))
THEN
1339 write(6,*)
'Internal error in CMUMPS_GET_LUA_ORDER',
1340 &
'SYM, FS_OR_CB, J = ',sym,fs_or_cb,j
1346 IF (fs_or_cb.EQ.0)
THEN
1348 ind_l = nb_blocks+i-k
1349 ind_u = nb_blocks+1-k
1351 ind_l = nb_blocks+1-k
1352 ind_u = nb_blocks+i-k
1358 IF (lbandslave)
THEN
1369 IF (lbandslave.AND.k474.GE.2)
THEN
1380 IF (blr_l(ind_l)%ISLR)
THEN
1381 IF (blr_u(ind_u)%ISLR)
THEN
1382 rank(k) =
min(blr_l(ind_l)%K, blr_u(ind_u)%K)
1384 rank(k) = blr_l(ind_l)%K
1387 IF (blr_u(ind_u)%ISLR)
THEN
1388 rank(k) = blr_u(ind_u)%K
1391 frfr_updates = frfr_updates + 1
1398 & IWHANDLER, SON_IW, LIW, LSTK, NELIM, K1, K2, SYM,
1399 & KEEP, KEEP8, OPASSW)
1411 INTEGER(8) :: LA, POSEL1
1412 INTEGER :: LIW, NELIM, K1, K2, IWHANDLER
1415 INTEGER :: SON_IW(:)
1416 INTEGER :: KEEP(500)
1417 INTEGER(8) :: KEEP8(150)
1419 DOUBLE PRECISION,
INTENT(INOUT) :: OPASSW
1424 COMPLEX,
ALLOCATABLE :: SON_A(:)
1425 INTEGER(8) :: APOS, SON_APOS, IACHK, JJ2, NFRONT8
1426 INTEGER :: KK, , allocok, SON_LA
1427 TYPE(LRB_TYPE),
POINTER :: CB_LRB(:,:), LRB
1428 INTEGER,
POINTER,
DIMENSION(:) :: BEGS_BLR_DYNAMIC
1429 INTEGER :: NB_INCB, NB_INASM, NB_BLR, I, J, M, N, II, NPIV,
1430 & IBIS, IBIS_END, FIRST_ROW, LAST_ROW, , LAST_COL,
1432 DOUBLE PRECISION :: PROMOTE_COST
1435 parameter(zero=(0.0e0,0.0e0))
1439 nb_blr =
size(begs_blr_dynamic)-1
1440 nb_incb =
size(cb_lrb,1)
1441 nb_inasm = nb_blr - nb_incb
1442 npiv = begs_blr_dynamic(nb_inasm+1)-1
1443 nfront8 = int(nfront,8)
1445 ibis_end = nb_incb*nb_incb
1447 ibis_end = nb_incb*(nb_incb+1)/2
1455 DO ibis = 1,ibis_end
1458 i = (ibis-1)/nb_incb+1
1459 j = ibis - (i-1)*nb_incb
1461 i = ceiling((1.0d0+sqrt(1.0d0+8.0d0*dble(ibis)))/2.0d0)-1
1462 j = ibis - i*(i-1)/2
1466 IF (i.EQ.nb_inasm+1)
THEN
1468 first_row = begs_blr_dynamic(i)-npiv+nelim
1470 first_row = begs_blr_dynamic(i)-npiv
1472 last_row = begs_blr_dynamic(i+1)-1-npiv
1473 m=last_row-first_row+1
1474 first_col = begs_blr_dynamic(j)-npiv
1475 last_col = begs_blr_dynamic(j+1)-1-npiv
1476 n = begs_blr_dynamic(j+1)-begs_blr_dynamic(j)
1480 lrb => cb_lrb(i-nb_inasm,j-nb_inasm
1481 IF (lrb%ISLR.AND.lrb%K.EQ.0)
THEN
1487 allocate(son_a(son_la),stat=allocok)
1488 IF (allocok.GT.0)
THEN
1489 write(*,*)
'Not enough memory in CMUMPS_BLR_ASM_NIV1',
1490 &
", Memory requested = ", son_la
1495 CALL cgemm(
'T',
'T', n, m, lrb%K, one, lrb%R(1,1), lrb%K,
1496 & lrb%Q(1,1), m, zero, son_a(son_apos), son_lda
1497 promote_cost = 2.0d0*m*n*lrb%K
1500 IF (i.EQ.j.AND.sym.NE.0)
THEN
1502 IF (j-nb_inasm.EQ.1.AND.nelim.GT.0)
THEN
1507 son_a(son_apos+int(ii-1,8)*int(son_lda,8) +
1515 son_a(son_apos+int(ii-1,8)*int(son_lda,8) +
1524 son_a(son_apos+int(ii-1,8)*int(son_lda,8) +
1535 IF (sym.NE.0.AND.j-nb_inasm.EQ.1.AND.nelim.GT.0)
THEN
1539 DO kk = first_row, last_row
1540 iachk = 1_8 + int(kk-first_row,8)*int(son_lda,8)
1541 IF (son_iw(kk+k1-1).LE.nass1)
THEN
1545 apos = posel1 + int(son_iw(kk+k1-1),8) - 1_8
1546 DO kk1 = first_col, first_col+nelim-1
1547 jj2 = apos + int(son_iw(k1+kk1-1)-1,8)*nfront8
1548 a(jj2) = a(jj2) + son_a(iachk + int(kk1-first_col,8))
1551 apos = posel1 + int(son_iw(kk+k1-1)-1,8)*nfront8
1557 DO kk1 = first_col+nelim,
min(last_col,kk)
1558 jj2 = apos + int(son_iw(k1+kk1-1),8) - 1_8
1559 a(jj2) = a(jj2) + son_a(iachk + int(kk1-first_col,8))
1562 apos = posel1 + int(son_iw(kk+k1
1563 DO kk1 = first_col,
min(last_col,kk)
1564 jj2 = apos + int(son_iw(k1+kk1-1),8) - 1_8
1565 a(jj2) = a(jj2) + son_a(iachk + int(kk1-first_col,8))
1571 DO kk = first_row, last_row
1573 iachk = 1_8 + int(kk-first_row,8)*int(son_lda,8)
1574 IF (i.EQ.j.AND.sym.NE.0)
THEN
1576 DO kk1 = first_col, kk
1577 jj2 = apos + int(son_iw(k1+kk1-1),8) - 1_8
1578 a(jj2) = a(jj2) + son_a(iachk + int(kk1-first_col,8))
1581 DO kk1 = first_col, last_col
1582 jj2 = apos + int(son_iw(k1+kk1-1),8) - 1_8
1583 a(jj2) = a(jj2) + son_a(iachk + int(kk1-first_col,8))
1597 & .true., keep8, keep(34))
1598 IF ((keep(486).EQ.3).OR.keep(486).EQ.0)
THEN
1609 & LDW, RWORK, TOLEPS, TOL_OPT, RANK, MAXRANK, INFO,
1668 INTEGER :: INFO, LDA, LDW, M, N, RANK, MAXRANK
1684 COMPLEX :: A(LDA,*), TAU(*)
1685 COMPLEX :: WORK(LDW,*)
1687 REAL :: TOLEPS_EFF, TRUNC_ERR
1688 INTEGER,
PARAMETER :: INB=1, inbmin=2
1689 INTEGER :: J, JB, MINMN, NB
1690 INTEGER :: OFFSET, ITEMP
1691 INTEGER :: LSTICC, PVT, K, RK
1692 REAL :: TEMP, TEMP2, TOL3Z
1694 LOGICAL INADMISSIBLE
1695 REAL,
PARAMETER :: RZERO=0.0e+0, rone=1.0e+0
1698 PARAMETER ( ONE = ( 1.0e+0, 0.0e+0 ) )
1699 parameter( zero = ( 0.0e+0, 0.0e+0 ) )
1701 INTEGER :: ilaenv, isamax
1702 EXTERNAL :: isamax, slamch
1703 EXTERNAL cgeqrf, cunmqr, xerbla
1706 REAL,
EXTERNAL :: scnrm2
1712 ELSE IF( n.LT.0 )
THEN
1714 ELSE IF( lda.LT.
max( 1, m ) )
THEN
1717 IF( info.EQ.0 )
THEN
1722 IF( info.NE.0 )
THEN
1727 IF( minmn.EQ.0 )
THEN
1731 nb = ilaenv
'CGEQRF',
' ', m, n, -1, -1 )
1732 SELECT CASE(abs(tol_opt))
1738 write(*,*)
'Internal error in CMUMPS_TRUNCATED_RRQR: TOL_OPT =',
1756 rwork( j ) = scnrm2( m, a( 1, j
1758 rwork( n + j ) = rwork( j )
1761 IF (tol_opt.LT.0)
THEN
1764 trunc_err = snrm2( n, rwork( 1 ), 1 )
1767 tol3z = sqrt(slamch(
'Epsilon'))
1769 jb =
min(nb,minmn-offset)
1777 pvt = ( rk-1 ) + isamax( n-rk+1, rwork( rk ), 1 )
1780 IF (abs(tol_opt).EQ.2) toleps_eff = rwork(pvt)*toleps
1782 IF (tol_opt.GT.0)
THEN
1784 trunc_err = rwork(pvt)
1788 IF(trunc_err.LT.toleps_eff)
THEN
1793 inadmissible = (rk.GT.maxrank)
1794 IF (inadmissible)
THEN
1800 IF( pvt.NE.rk )
THEN
1801 CALL cswap( m, a( 1, pvt ), 1, a( 1, rk ), 1 )
1804 CALL cswap( k-1, work( pvt-offset, 2 ), ldw,
1805 & work( k, 2 ), ldw )
1807 jpvt(pvt) = jpvt(rk)
1811 rwork(pvt) = rwork(rk)
1812 rwork(n+pvt) = rwork(n+rk)
1819 work( k, j+1 ) = conjg( work( k, j+1 ) )
1821 CALL cgemv(
'No transpose', m-rk+1, k-1, -one,
1823 & a(rk,offset+1), lda, work(k,2), ldw,
1824 & one, a(rk,rk), 1 )
1827 work( k, j + 1 ) = conjg( work( k, j + 1 ) )
1832 CALL clarfg( m-rk+1, a(rk,rk), a(rk+1,rk), 1, tau(rk) )
1834 CALL clarfg( 1, a(rk,rk), a(rk,rk), 1, tau(rk) )
1841 CALL cgemv(
'Conjugate transpose', m-rk+1, n-rk, tau(rk),
1842 & a(rk,rk+1), lda, a(rk,rk), 1, zero,
1844 & work( k+1, k+1 ), 1 )
1849 work( j, k+1 ) = zero
1855 CALL cgemv( 'conjugate transpose
', M-RK+1, K-1, -TAU(RK),
1856 & A(RK,OFFSET+1), LDA, A(RK,RK), 1, ZERO,
1859 CALL cgemv( 'no transpose
', N-OFFSET, K-1, ONE,
1860 & WORK(1,2), LDW, WORK(1,1), 1, ONE, WORK(1,K+1), 1 )
1866 CALL cgemm( 'no transpose
', 'conjugate transpose
',
1869 & K, -ONE, A( RK, OFFSET+1 ), LDA, WORK( K+1,2 ), LDW,
1870 & ONE, A( RK, RK+1 ), LDA )
1874.LT.
IF( RKMINMN ) THEN
1877.NE.
IF( RWORK( J )RZERO ) THEN
1883 TEMP = ABS( A( RK, J ) ) / RWORK( J )
1884 TEMP = MAX( RZERO, ( RONE+TEMP )*( RONE-TEMP ) )
1886 TEMP2 = TEMP*( RWORK( J ) / RWORK( N+J ) )**2
1887.LE.
IF( TEMP2 TOL3Z ) THEN
1889 RWORK( N+J ) = REAL( LSTICC )
1893 RWORK( J ) = RWORK( J )*SQRT( TEMP )
1899.NE.
IF (LSTICC0) EXIT
1900.LT.
IF (TOL_OPT0) THEN
1903 TRUNC_ERR = snrm2( N-RK, RWORK( RK+1 ), 1 )
1909.LT.
IF( RKMIN(N,M) ) THEN
1910 CALL cgemm( 'no transpose
', 'conjugate transpose
', M-RK,
1911 & N-RK, K, -ONE, A(RK+1,OFFSET+1), LDA,
1913 & WORK(K+1,2), LDW, ONE, A(RK+1,RK+1), LDA )
1916.GT.
DO WHILE( LSTICC0 )
1918 ITEMP = NINT( RWORK( N + LSTICC ) )
1920 RWORK( LSTICC ) = scnrm2( M-RK, A( RK+1, LSTICC ), 1 )
1927 RWORK( N + LSTICC ) = RWORK( LSTICC )
1930.GE.
IF(RKMINMN) EXIT
1932.LT.
IF (TOL_OPT0) THEN
1935 TRUNC_ERR = snrm2( N-RK, RWORK( RK+1 ), 1 )
1939.NOT..GT.
ISLR = (RKMAXRANK)
1942 & I2,' had an illegal
value')
1943 END SUBROUTINE CMUMPS_TRUNCATED_RRQR
subroutine cmumps_truncated_rrqr(m, n, a, lda, jpvt, tau, work, ldw, rwork, toleps, tol_opt, rank, maxrank, info, islr)
subroutine clarfg(n, alpha, x, incx, tau)
CLARFG generates an elementary reflector (Householder matrix).
subroutine cungqr(m, n, k, a, lda, tau, work, lwork, info)
CUNGQR
subroutine cswap(n, cx, incx, cy, incy)
CSWAP
subroutine cscal(n, ca, cx, incx)
CSCAL
subroutine cgemv(trans, m, n, alpha, a, lda, x, incx, beta, y, incy)
CGEMV
subroutine ctrsm(side, uplo, transa, diag, m, n, alpha, a, lda, b, ldb)
CTRSM
subroutine cgemm(transa, transb, m, n, k, alpha, a, lda, b, ldb, beta, c, ldc)
CGEMM
recursive subroutine cmumps_recompress_acc_narytree(acc_lrb, maxi_cluster, maxi_rank, a, la, poseltt, keep8, nfront, niv, midblk_compress, toleps, tol_opt, kpercent_rmb, kpercent_lua, k478, rank_list, pos_list, nb_nodes, level, acc_tmp)
subroutine cmumps_recompress_acc_v2(acc_lrb, maxi_cluster, maxi_rank, a, la, poseltt, nfront, niv, midblk_compress, toleps, tol_opt, kpercent_rmb, kpercent_lua, new_acc_rank)
subroutine is_front_blr_candidate(inode, niv, nfront, nass, blron, k489, k490, k491, k492, k20, k60, idad, k38, lrstatus, n, lrgroups)
subroutine cmumps_compress_fr_updates(acc_lrb, maxi_cluster, maxi_rank, a, la, poseltt, nfront, niv, toleps, tol_opt, kpercent, buildq, loru, cb_compress)
subroutine cmumps_blr_asm_niv1(a, la, posel1, nfront, nass1, iwhandler, son_iw, liw, lstk, nelim, k1, k2, sym, keep, keep8, opassw)
subroutine cmumps_recompress_acc(acc_lrb, maxi_cluster, maxi_rank, a, la, poseltt, nfront, niv, midblk_compress, toleps, tol_opt, kpercent_rmb, kpercent_lua, new_acc_rank)
subroutine alloc_lrb_from_acc(acc_lrb, lrb_out, k, m, n, loru, iflag, ierror, keep8)
subroutine cmumps_get_lua_order(nb_blocks, order, rank, iwhandler, sym, fs_or_cb, i, j, frfr_updates, lbandslave_in, k474, blr_u_col)
subroutine max_cluster(cut, cut_size, maxi_cluster)
subroutine cmumps_lrtrsm(a, la, poselt_local, nfront, lda, lrb, niv, sym, loru, iw, offset_iw)
subroutine alloc_lrb(lrb_out, k, m, n, islr, iflag, ierror, keep8)
subroutine init_lrb(lrb_out, k, m, n, islr)
subroutine cmumps_lrgemm4(alpha, lrb1, lrb2, beta, a, la, poseltt, nfront, sym, iflag, ierror, midblk_compress, toleps, tol_opt, kpercent, rank, buildq, lua_activated, loru, lrb3, maxi_rank, maxi_cluster, diag, ld_diag, iw2, block)
subroutine cmumps_lrgemm_scaling(lrb, scaled, a, la, diag, ld_diag, iw2, poseltt, nfront, block, maxi_cluster)
subroutine regrouping2(cut, npartsass, nass, npartscb, ncb, ibcksz, onlycb, k472)
subroutine, public cmumps_blr_free_cb_lrb(iwhandler, free_only_struct, keep8, k34)
subroutine, public cmumps_blr_retrieve_cb_lrb(iwhandler, thecb)
subroutine, public cmumps_blr_retrieve_panel_loru(iwhandler, loru, ipanel, thelrbpanel)
subroutine, public cmumps_blr_end_front(iwhandler, info1, keep8, k34, lrsolve_act_opt, mtk405)
subroutine, public cmumps_blr_retrieve_begsblr_dyn(iwhandler, begs_blr_dynamic)
subroutine upd_flop_trsm(lrb, loru)
subroutine upd_flop_decompress(f, cb)
subroutine dealloc_lrb(lrb_out, keep8, k34)
subroutine compute_blr_vcs(k472, ibcksz, maxsize, nass)