| Line | Branch | Exec | Source |
|---|---|---|---|
| 1 | /* | ||
| 2 | - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - | ||
| 3 | SLEPc - Scalable Library for Eigenvalue Problem Computations | ||
| 4 | Copyright (c) 2002-, Universitat Politecnica de Valencia, Spain | ||
| 5 | |||
| 6 | This file is part of SLEPc. | ||
| 7 | SLEPc is distributed under a 2-clause BSD license (see LICENSE). | ||
| 8 | - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - | ||
| 9 | */ | ||
| 10 | /* | ||
| 11 | SLEPc matrix equation solver: "krylov" | ||
| 12 | |||
| 13 | Method: Arnoldi with Eiermann-Ernst restart | ||
| 14 | |||
| 15 | Algorithm: | ||
| 16 | |||
| 17 | Project the equation onto the Arnoldi basis and solve the compressed | ||
| 18 | equation the Hessenberg matrix H, restart by discarding the Krylov | ||
| 19 | basis but keeping H. | ||
| 20 | |||
| 21 | References: | ||
| 22 | |||
| 23 | [1] Y. Saad, "Numerical solution of large Lyapunov equations", in | ||
| 24 | Signal processing, scattering and operator theory, and numerical | ||
| 25 | methods, vol. 5 of Progr. Systems Control Theory, pages 503-511, | ||
| 26 | 1990. | ||
| 27 | |||
| 28 | [2] D. Kressner, "Memory-efficient Krylov subspace techniques for | ||
| 29 | solving large-scale Lyapunov equations", in 2008 IEEE Int. Conf. | ||
| 30 | Computer-Aided Control Systems, pages 613-618, 2008. | ||
| 31 | */ | ||
| 32 | |||
| 33 | #include <slepc/private/lmeimpl.h> | ||
| 34 | #include <slepcblaslapack.h> | ||
| 35 | |||
| 36 | 85 | static PetscErrorCode LMESetUp_Krylov(LME lme) | |
| 37 | { | ||
| 38 | 85 | PetscInt N; | |
| 39 | |||
| 40 |
1/2✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
|
85 | PetscFunctionBegin; |
| 41 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
85 | PetscCall(MatGetSize(lme->A,&N,NULL)); |
| 42 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
85 | if (lme->ncv==PETSC_DETERMINE) lme->ncv = PetscMin(30,N); |
| 43 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
85 | if (lme->max_it==PETSC_DETERMINE) lme->max_it = 100; |
| 44 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
85 | PetscCall(LMEAllocateSolution(lme,1)); |
| 45 |
6/12✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
|
16 | PetscFunctionReturn(PETSC_SUCCESS); |
| 46 | } | ||
| 47 | |||
| 48 | 729 | static PetscErrorCode LMESolve_Krylov_Lyapunov_Vec(LME lme,Vec b,PetscBool fixed,PetscInt rrank,BV C1,BV *X1,PetscInt *col,PetscBool *fail,PetscInt *totalits) | |
| 49 | { | ||
| 50 | 729 | PetscInt n=0,m,ldh,ldg=0,i,j,rank=0,lrank,pass,nouter=0,its; | |
| 51 | 729 | PetscReal bnorm,beta,errest; | |
| 52 | 729 | PetscBool breakdown; | |
| 53 | 729 | PetscScalar *Harray,*G=NULL,*Gnew=NULL,*L=NULL,*U=NULL,*r,*Qarray,sone=1.0,zero=0.0; | |
| 54 | 729 | PetscBLASInt n_,m_,rk_; | |
| 55 | 729 | Mat Q,H; | |
| 56 | |||
| 57 |
1/2✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
|
729 | PetscFunctionBegin; |
| 58 | 729 | *fail = PETSC_FALSE; | |
| 59 | 729 | its = 0; | |
| 60 | 729 | m = lme->ncv; | |
| 61 | 729 | ldh = m+1; | |
| 62 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(MatCreateSeqDense(PETSC_COMM_SELF,ldh,m,NULL,&H)); |
| 63 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(MatDenseGetArray(H,&Harray)); |
| 64 | |||
| 65 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(VecNorm(b,NORM_2,&bnorm)); |
| 66 |
1/4✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
|
729 | PetscCheck(bnorm,PetscObjectComm((PetscObject)lme),PETSC_ERR_ARG_WRONG,"Cannot process a zero vector in the right-hand side"); |
| 67 | |||
| 68 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
2187 | for (pass=0;pass<2;pass++) { |
| 69 | |||
| 70 | /* set initial vector to b/||b|| */ | ||
| 71 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
1458 | PetscCall(BVInsertVec(lme->V,0,b)); |
| 72 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
1458 | PetscCall(BVScaleColumn(lme->V,0,1.0/bnorm)); |
| 73 | |||
| 74 | /* Restart loop */ | ||
| 75 |
4/6✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 10 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 10 times.
✓ Branch 5 taken 10 times.
|
2307 | while ((pass==0 && !*fail) || (pass==1 && its+1<nouter)) { |
| 76 | 1578 | its++; | |
| 77 | |||
| 78 | /* compute Arnoldi factorization */ | ||
| 79 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
1578 | PetscCall(BVMatArnoldi(lme->V,lme->A,H,0,&m,&beta,&breakdown)); |
| 80 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
1578 | PetscCall(BVSetActiveColumns(lme->V,0,m)); |
| 81 | |||
| 82 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
1578 | if (pass==0) { |
| 83 | /* glue together the previous H and the new H obtained with Arnoldi */ | ||
| 84 | 789 | ldg = n+m+1; | |
| 85 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(PetscCalloc1(ldg*(n+m),&Gnew)); |
| 86 |
7/8✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 10 times.
✓ Branch 3 taken 8 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
✓ Branch 6 taken 2 times.
✓ Branch 7 taken 2 times.
|
23451 | for (j=0;j<m;j++) PetscCall(PetscArraycpy(Gnew+n+(j+n)*ldg,Harray+j*ldh,m)); |
| 87 | 789 | Gnew[n+m+(n+m-1)*ldg] = beta; | |
| 88 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
789 | if (G) { |
| 89 |
7/8✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 10 times.
✓ Branch 3 taken 8 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
✓ Branch 6 taken 2 times.
✓ Branch 7 taken 2 times.
|
1356 | for (j=0;j<n;j++) PetscCall(PetscArraycpy(Gnew+j*ldg,G+j*(n+1),n+1)); |
| 90 |
6/8✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
|
60 | PetscCall(PetscFree(G)); |
| 91 | } | ||
| 92 | 789 | G = Gnew; | |
| 93 | 789 | n += m; | |
| 94 | } else { | ||
| 95 | /* update Z = Z + V(:,1:m)*Q with Q=U(blk,:)*P(1:nrk,:)' */ | ||
| 96 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(MatCreateSeqDense(PETSC_COMM_SELF,m,*col+rank,NULL,&Q)); |
| 97 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(MatDenseGetArray(Q,&Qarray)); |
| 98 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(PetscBLASIntCast(m,&m_)); |
| 99 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(PetscBLASIntCast(n,&n_)); |
| 100 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(PetscBLASIntCast(rank,&rk_)); |
| 101 |
10/20✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
✓ Branch 12 taken 2 times.
✗ Branch 13 not taken.
✓ Branch 14 taken 2 times.
✗ Branch 15 not taken.
✗ Branch 16 not taken.
✓ Branch 17 taken 2 times.
✗ Branch 18 not taken.
✗ Branch 19 not taken.
|
789 | PetscCallBLAS("BLASgemm",BLASgemm_("N","N",&m_,&rk_,&rk_,&sone,U+its*m,&n_,L,&n_,&zero,Qarray+(*col)*m,&m_)); |
| 102 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(MatDenseRestoreArray(Q,&Qarray)); |
| 103 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(BVSetActiveColumns(*X1,*col,*col+rank)); |
| 104 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(BVMult(*X1,1.0,1.0,lme->V,Q)); |
| 105 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(MatDestroy(&Q)); |
| 106 | } | ||
| 107 | |||
| 108 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
1578 | if (pass==0) { |
| 109 | /* solve compressed Lyapunov equation */ | ||
| 110 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(PetscCalloc1(n,&r)); |
| 111 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(PetscCalloc1(n*n,&L)); |
| 112 | 789 | r[0] = bnorm; | |
| 113 | 789 | errest = PetscAbsScalar(G[n+(n-1)*ldg]); | |
| 114 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(LMEDenseHessLyapunovChol(lme,n,G,ldg,1,r,n,L,n,&errest)); |
| 115 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
789 | PetscCall(LMEMonitor(lme,*totalits+its,errest)); |
| 116 |
5/8✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
|
789 | PetscCall(PetscFree(r)); |
| 117 | |||
| 118 | /* check convergence */ | ||
| 119 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
789 | if (errest<lme->tol) { |
| 120 | 729 | lme->errest += errest; | |
| 121 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(PetscMalloc1(n*n,&U)); |
| 122 | /* transpose L */ | ||
| 123 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
23391 | for (j=0;j<n;j++) { |
| 124 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
368973 | for (i=j+1;i<n;i++) { |
| 125 | 346311 | L[i+j*n] = PetscConj(L[j+i*n]); | |
| 126 | 346311 | L[j+i*n] = 0.0; | |
| 127 | } | ||
| 128 | } | ||
| 129 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(LMEDenseRankSVD(lme,n,L,n,U,n,&lrank)); |
| 130 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(PetscInfo(lme,"Rank of the Cholesky factor = %" PetscInt_FMT "\n",lrank)); |
| 131 | 729 | nouter = its; | |
| 132 | 729 | its = -1; | |
| 133 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
729 | if (!fixed) { /* X1 was not set by user, allocate it with rank columns */ |
| 134 | 80 | rank = lrank; | |
| 135 |
6/8✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
|
80 | if (*col) PetscCall(BVResize(*X1,*col+rank,PETSC_TRUE)); |
| 136 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
40 | else PetscCall(BVDuplicateResize(C1,rank,X1)); |
| 137 | 649 | } else rank = PetscMin(lrank,rrank); | |
| 138 |
6/8✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
|
729 | PetscCall(PetscFree(G)); |
| 139 | break; | ||
| 140 | } else { | ||
| 141 |
5/8✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
|
60 | PetscCall(PetscFree(L)); |
| 142 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
|
60 | if (*totalits+its>=lme->max_it) *fail = PETSC_TRUE; |
| 143 | } | ||
| 144 | } | ||
| 145 | |||
| 146 | /* restart with vector v_{m+1} */ | ||
| 147 |
8/10✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 10 times.
✓ Branch 5 taken 8 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
✓ Branch 8 taken 2 times.
✓ Branch 9 taken 2 times.
|
3156 | if (!*fail) PetscCall(BVCopyColumn(lme->V,m,0)); |
| 148 | } | ||
| 149 | } | ||
| 150 | |||
| 151 | 729 | *col += rank; | |
| 152 | 729 | *totalits += its+1; | |
| 153 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(MatDenseRestoreArray(H,&Harray)); |
| 154 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(MatDestroy(&H)); |
| 155 |
6/10✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 10 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✓ Branch 5 taken 8 times.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✓ Branch 9 taken 2 times.
|
729 | if (L) PetscCall(PetscFree(L)); |
| 156 |
6/10✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 10 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✓ Branch 5 taken 8 times.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✓ Branch 9 taken 2 times.
|
729 | if (U) PetscCall(PetscFree(U)); |
| 157 |
6/12✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
|
116 | PetscFunctionReturn(PETSC_SUCCESS); |
| 158 | } | ||
| 159 | |||
| 160 | 497 | static PetscErrorCode LMESolve_Krylov_Lyapunov(LME lme) | |
| 161 | { | ||
| 162 | 497 | PetscBool fail,fixed = lme->X? PETSC_TRUE: PETSC_FALSE; | |
| 163 | 497 | PetscInt i,k,rank=0,col=0; | |
| 164 | 497 | Vec b; | |
| 165 | 497 | BV X1=NULL,C1; | |
| 166 | 497 | Mat X1m,X1t,C1m; | |
| 167 | |||
| 168 |
1/2✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
|
497 | PetscFunctionBegin; |
| 169 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
497 | PetscCall(MatLRCGetMats(lme->C,NULL,&C1m,NULL,NULL)); |
| 170 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
497 | PetscCall(BVCreateFromMat(C1m,&C1)); |
| 171 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
497 | PetscCall(BVSetFromOptions(C1)); |
| 172 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
497 | PetscCall(BVGetActiveColumns(C1,NULL,&k)); |
| 173 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
497 | if (fixed) { |
| 174 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
457 | PetscCall(MatLRCGetMats(lme->X,NULL,&X1m,NULL,NULL)); |
| 175 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
457 | PetscCall(BVCreateFromMat(X1m,&X1)); |
| 176 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
457 | PetscCall(BVSetFromOptions(X1)); |
| 177 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
457 | PetscCall(BVGetActiveColumns(X1,NULL,&rank)); |
| 178 | 457 | rank = rank/k; | |
| 179 | } | ||
| 180 |
2/2✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
|
1226 | for (i=0;i<k;i++) { |
| 181 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(BVGetColumn(C1,i,&b)); |
| 182 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(LMESolve_Krylov_Lyapunov_Vec(lme,b,fixed,rank,C1,&X1,&col,&fail,&lme->its)); |
| 183 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
729 | PetscCall(BVRestoreColumn(C1,i,&b)); |
| 184 |
1/2✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
|
729 | if (fail) { |
| 185 | ✗ | lme->reason = LME_DIVERGED_ITS; | |
| 186 | ✗ | break; | |
| 187 | } | ||
| 188 | } | ||
| 189 |
1/2✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
|
497 | if (lme->reason==LME_CONVERGED_ITERATING) lme->reason = LME_CONVERGED_TOL; |
| 190 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
497 | PetscCall(BVCreateMat(X1,&X1t)); |
| 191 |
6/8✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
|
497 | if (fixed) PetscCall(MatCopy(X1t,X1m,SAME_NONZERO_PATTERN)); |
| 192 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
40 | else PetscCall(MatCreateLRC(NULL,X1t,NULL,NULL,&lme->X)); |
| 193 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
497 | PetscCall(MatDestroy(&X1t)); |
| 194 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
497 | PetscCall(BVDestroy(&C1)); |
| 195 |
4/6✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
|
497 | PetscCall(BVDestroy(&X1)); |
| 196 |
6/12✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
|
71 | PetscFunctionReturn(PETSC_SUCCESS); |
| 197 | } | ||
| 198 | |||
| 199 | /*MC | ||
| 200 | LMEKRYLOV - LMEKRYLOV = "krylov" - A restarted Krylov method for the solution of | ||
| 201 | linear matrix equations. | ||
| 202 | |||
| 203 | Note: | ||
| 204 | A description of the method is provided in chapter [](ch:lme) | ||
| 205 | of the Users Manual. | ||
| 206 | |||
| 207 | Level: beginner | ||
| 208 | |||
| 209 | .seealso: [](ch:lme), `LME`, `LMEType`, `LMESetType()` | ||
| 210 | M*/ | ||
| 211 | 99 | SLEPC_EXTERN PetscErrorCode LMECreate_Krylov(LME lme) | |
| 212 | { | ||
| 213 |
1/2✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
|
99 | PetscFunctionBegin; |
| 214 | 99 | lme->ops->solve[LME_LYAPUNOV] = LMESolve_Krylov_Lyapunov; | |
| 215 | 99 | lme->ops->setup = LMESetUp_Krylov; | |
| 216 |
6/12✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
|
99 | PetscFunctionReturn(PETSC_SUCCESS); |
| 217 | } | ||
| 218 |