1992c00aaSSatish Balay #define PETSCMAT_DLL 2b3cc6726SBarry Smith 3b377110cSBarry Smith 4d5d45c9bSBarry Smith /* 53369ce9aSBarry Smith Defines the basic matrix operations for the AIJ (compressed row) 6d5d45c9bSBarry Smith matrix storage format. 7d5d45c9bSBarry Smith */ 83369ce9aSBarry Smith 97c4f633dSBarry Smith 107c4f633dSBarry Smith #include "../src/mat/impls/aij/seq/aij.h" /*I "petscmat.h" I*/ 11f3da1532SBarry Smith #include "petscblaslapack.h" 120a835dfdSSatish Balay #include "petscbt.h" 1317ab2063SBarry Smith 144a2ae208SSatish Balay #undef __FUNCT__ 15*b3a44c85SBarry Smith #define __FUNCT__ "MatFindNonzeroRows_SeqAIJ" 16*b3a44c85SBarry Smith PetscErrorCode MatFindNonzeroRows_SeqAIJ(Mat A,IS *keptrows) 17*b3a44c85SBarry Smith { 18*b3a44c85SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 19*b3a44c85SBarry Smith const MatScalar *aa; 20*b3a44c85SBarry Smith PetscInt m=A->rmap->n,cnt = 0; 21*b3a44c85SBarry Smith const PetscInt *ii; 22*b3a44c85SBarry Smith PetscInt n,i,j,*rows; 23*b3a44c85SBarry Smith PetscErrorCode ierr; 24*b3a44c85SBarry Smith 25*b3a44c85SBarry Smith PetscFunctionBegin; 26*b3a44c85SBarry Smith *keptrows = 0; 27*b3a44c85SBarry Smith ii = a->i; 28*b3a44c85SBarry Smith for (i=0; i<m; i++) { 29*b3a44c85SBarry Smith n = ii[i+1] - ii[i]; 30*b3a44c85SBarry Smith if (!n) { 31*b3a44c85SBarry Smith cnt++; 32*b3a44c85SBarry Smith goto ok1; 33*b3a44c85SBarry Smith } 34*b3a44c85SBarry Smith aa = a->a + ii[i]; 35*b3a44c85SBarry Smith for (j=0; j<n; j++) { 36*b3a44c85SBarry Smith if (aa[j] != 0.0) goto ok1; 37*b3a44c85SBarry Smith } 38*b3a44c85SBarry Smith cnt++; 39*b3a44c85SBarry Smith ok1:; 40*b3a44c85SBarry Smith } 41*b3a44c85SBarry Smith if (!cnt) PetscFunctionReturn(0); 42*b3a44c85SBarry Smith ierr = PetscMalloc((A->rmap->n-cnt)*sizeof(PetscInt),&rows);CHKERRQ(ierr); 43*b3a44c85SBarry Smith cnt = 0; 44*b3a44c85SBarry Smith for (i=0; i<m; i++) { 45*b3a44c85SBarry Smith n = ii[i+1] - ii[i]; 46*b3a44c85SBarry Smith if (!n) continue; 47*b3a44c85SBarry Smith aa = a->a + ii[i]; 48*b3a44c85SBarry Smith for (j=0; j<n; j++) { 49*b3a44c85SBarry Smith if (aa[j] != 0.0) { 50*b3a44c85SBarry Smith rows[cnt++] = i; 51*b3a44c85SBarry Smith break; 52*b3a44c85SBarry Smith } 53*b3a44c85SBarry Smith } 54*b3a44c85SBarry Smith } 55*b3a44c85SBarry Smith ierr = ISCreateGeneral(PETSC_COMM_SELF,cnt,rows,PETSC_OWN_POINTER,keptrows);CHKERRQ(ierr); 56*b3a44c85SBarry Smith PetscFunctionReturn(0); 57*b3a44c85SBarry Smith } 58*b3a44c85SBarry Smith 59*b3a44c85SBarry Smith #undef __FUNCT__ 6079299369SBarry Smith #define __FUNCT__ "MatDiagonalSet_SeqAIJ" 617087cfbeSBarry Smith PetscErrorCode MatDiagonalSet_SeqAIJ(Mat Y,Vec D,InsertMode is) 6279299369SBarry Smith { 6379299369SBarry Smith PetscErrorCode ierr; 6479299369SBarry Smith Mat_SeqAIJ *aij = (Mat_SeqAIJ*) Y->data; 65d0f46423SBarry Smith PetscInt i,*diag, m = Y->rmap->n; 6654f21887SBarry Smith MatScalar *aa = aij->a; 6754f21887SBarry Smith PetscScalar *v; 68ace3abfcSBarry Smith PetscBool missing; 6979299369SBarry Smith 7079299369SBarry Smith PetscFunctionBegin; 7109f38230SBarry Smith if (Y->assembled) { 7209f38230SBarry Smith ierr = MatMissingDiagonal_SeqAIJ(Y,&missing,PETSC_NULL);CHKERRQ(ierr); 7309f38230SBarry Smith if (!missing) { 7479299369SBarry Smith diag = aij->diag; 7579299369SBarry Smith ierr = VecGetArray(D,&v);CHKERRQ(ierr); 7679299369SBarry Smith if (is == INSERT_VALUES) { 7779299369SBarry Smith for (i=0; i<m; i++) { 7879299369SBarry Smith aa[diag[i]] = v[i]; 7979299369SBarry Smith } 8079299369SBarry Smith } else { 8179299369SBarry Smith for (i=0; i<m; i++) { 8279299369SBarry Smith aa[diag[i]] += v[i]; 8379299369SBarry Smith } 8479299369SBarry Smith } 8579299369SBarry Smith ierr = VecRestoreArray(D,&v);CHKERRQ(ierr); 8679299369SBarry Smith PetscFunctionReturn(0); 8779299369SBarry Smith } 8809f38230SBarry Smith } 8909f38230SBarry Smith ierr = MatDiagonalSet_Default(Y,D,is);CHKERRQ(ierr); 9009f38230SBarry Smith PetscFunctionReturn(0); 9109f38230SBarry Smith } 9279299369SBarry Smith 9379299369SBarry Smith #undef __FUNCT__ 944a2ae208SSatish Balay #define __FUNCT__ "MatGetRowIJ_SeqAIJ" 95ace3abfcSBarry Smith PetscErrorCode MatGetRowIJ_SeqAIJ(Mat A,PetscInt oshift,PetscBool symmetric,PetscBool inodecompressed,PetscInt *m,PetscInt *ia[],PetscInt *ja[],PetscBool *done) 9617ab2063SBarry Smith { 97416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 98dfbe8321SBarry Smith PetscErrorCode ierr; 9997f1f81fSBarry Smith PetscInt i,ishift; 10017ab2063SBarry Smith 1013a40ed3dSBarry Smith PetscFunctionBegin; 102d0f46423SBarry Smith *m = A->rmap->n; 1033a40ed3dSBarry Smith if (!ia) PetscFunctionReturn(0); 104bfeeae90SHong Zhang ishift = 0; 10553e63a63SBarry Smith if (symmetric && !A->structurally_symmetric) { 106d0f46423SBarry Smith ierr = MatToSymmetricIJ_SeqAIJ(A->rmap->n,a->i,a->j,ishift,oshift,ia,ja);CHKERRQ(ierr); 107bfeeae90SHong Zhang } else if (oshift == 1) { 108d0f46423SBarry Smith PetscInt nz = a->i[A->rmap->n]; 1093b2fbd54SBarry Smith /* malloc space and add 1 to i and j indices */ 110d0f46423SBarry Smith ierr = PetscMalloc((A->rmap->n+1)*sizeof(PetscInt),ia);CHKERRQ(ierr); 111d0f46423SBarry Smith for (i=0; i<A->rmap->n+1; i++) (*ia)[i] = a->i[i] + 1; 112ecc77c7aSBarry Smith if (ja) { 11397f1f81fSBarry Smith ierr = PetscMalloc((nz+1)*sizeof(PetscInt),ja);CHKERRQ(ierr); 1143b2fbd54SBarry Smith for (i=0; i<nz; i++) (*ja)[i] = a->j[i] + 1; 115ecc77c7aSBarry Smith } 1166945ee14SBarry Smith } else { 117ecc77c7aSBarry Smith *ia = a->i; 118ecc77c7aSBarry Smith if (ja) *ja = a->j; 119a2ce50c7SBarry Smith } 1203a40ed3dSBarry Smith PetscFunctionReturn(0); 121a2744918SBarry Smith } 122a2744918SBarry Smith 1234a2ae208SSatish Balay #undef __FUNCT__ 1244a2ae208SSatish Balay #define __FUNCT__ "MatRestoreRowIJ_SeqAIJ" 125ace3abfcSBarry Smith PetscErrorCode MatRestoreRowIJ_SeqAIJ(Mat A,PetscInt oshift,PetscBool symmetric,PetscBool inodecompressed,PetscInt *n,PetscInt *ia[],PetscInt *ja[],PetscBool *done) 1266945ee14SBarry Smith { 127dfbe8321SBarry Smith PetscErrorCode ierr; 1286945ee14SBarry Smith 1293a40ed3dSBarry Smith PetscFunctionBegin; 1303a40ed3dSBarry Smith if (!ia) PetscFunctionReturn(0); 131bfeeae90SHong Zhang if ((symmetric && !A->structurally_symmetric) || oshift == 1) { 132606d414cSSatish Balay ierr = PetscFree(*ia);CHKERRQ(ierr); 133ecc77c7aSBarry Smith if (ja) {ierr = PetscFree(*ja);CHKERRQ(ierr);} 134bcd2baecSBarry Smith } 1353a40ed3dSBarry Smith PetscFunctionReturn(0); 13617ab2063SBarry Smith } 13717ab2063SBarry Smith 1384a2ae208SSatish Balay #undef __FUNCT__ 1394a2ae208SSatish Balay #define __FUNCT__ "MatGetColumnIJ_SeqAIJ" 140ace3abfcSBarry Smith PetscErrorCode MatGetColumnIJ_SeqAIJ(Mat A,PetscInt oshift,PetscBool symmetric,PetscBool inodecompressed,PetscInt *nn,PetscInt *ia[],PetscInt *ja[],PetscBool *done) 1413b2fbd54SBarry Smith { 1423b2fbd54SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 143dfbe8321SBarry Smith PetscErrorCode ierr; 144d0f46423SBarry Smith PetscInt i,*collengths,*cia,*cja,n = A->cmap->n,m = A->rmap->n; 14597f1f81fSBarry Smith PetscInt nz = a->i[m],row,*jj,mr,col; 1463b2fbd54SBarry Smith 1473a40ed3dSBarry Smith PetscFunctionBegin; 148899cda47SBarry Smith *nn = n; 1493a40ed3dSBarry Smith if (!ia) PetscFunctionReturn(0); 1503b2fbd54SBarry Smith if (symmetric) { 151d0f46423SBarry Smith ierr = MatToSymmetricIJ_SeqAIJ(A->rmap->n,a->i,a->j,0,oshift,ia,ja);CHKERRQ(ierr); 1523b2fbd54SBarry Smith } else { 15397f1f81fSBarry Smith ierr = PetscMalloc((n+1)*sizeof(PetscInt),&collengths);CHKERRQ(ierr); 15497f1f81fSBarry Smith ierr = PetscMemzero(collengths,n*sizeof(PetscInt));CHKERRQ(ierr); 15597f1f81fSBarry Smith ierr = PetscMalloc((n+1)*sizeof(PetscInt),&cia);CHKERRQ(ierr); 15697f1f81fSBarry Smith ierr = PetscMalloc((nz+1)*sizeof(PetscInt),&cja);CHKERRQ(ierr); 1573b2fbd54SBarry Smith jj = a->j; 1583b2fbd54SBarry Smith for (i=0; i<nz; i++) { 159bfeeae90SHong Zhang collengths[jj[i]]++; 1603b2fbd54SBarry Smith } 1613b2fbd54SBarry Smith cia[0] = oshift; 1623b2fbd54SBarry Smith for (i=0; i<n; i++) { 1633b2fbd54SBarry Smith cia[i+1] = cia[i] + collengths[i]; 1643b2fbd54SBarry Smith } 16597f1f81fSBarry Smith ierr = PetscMemzero(collengths,n*sizeof(PetscInt));CHKERRQ(ierr); 1663b2fbd54SBarry Smith jj = a->j; 167a93ec695SBarry Smith for (row=0; row<m; row++) { 168a93ec695SBarry Smith mr = a->i[row+1] - a->i[row]; 169a93ec695SBarry Smith for (i=0; i<mr; i++) { 170bfeeae90SHong Zhang col = *jj++; 1713b2fbd54SBarry Smith cja[cia[col] + collengths[col]++ - oshift] = row + oshift; 1723b2fbd54SBarry Smith } 1733b2fbd54SBarry Smith } 174606d414cSSatish Balay ierr = PetscFree(collengths);CHKERRQ(ierr); 1753b2fbd54SBarry Smith *ia = cia; *ja = cja; 1763b2fbd54SBarry Smith } 1773a40ed3dSBarry Smith PetscFunctionReturn(0); 1783b2fbd54SBarry Smith } 1793b2fbd54SBarry Smith 1804a2ae208SSatish Balay #undef __FUNCT__ 1814a2ae208SSatish Balay #define __FUNCT__ "MatRestoreColumnIJ_SeqAIJ" 182ace3abfcSBarry Smith PetscErrorCode MatRestoreColumnIJ_SeqAIJ(Mat A,PetscInt oshift,PetscBool symmetric,PetscBool inodecompressed,PetscInt *n,PetscInt *ia[],PetscInt *ja[],PetscBool *done) 1833b2fbd54SBarry Smith { 184dfbe8321SBarry Smith PetscErrorCode ierr; 185606d414cSSatish Balay 1863a40ed3dSBarry Smith PetscFunctionBegin; 1873a40ed3dSBarry Smith if (!ia) PetscFunctionReturn(0); 1883b2fbd54SBarry Smith 189606d414cSSatish Balay ierr = PetscFree(*ia);CHKERRQ(ierr); 190606d414cSSatish Balay ierr = PetscFree(*ja);CHKERRQ(ierr); 1913b2fbd54SBarry Smith 1923a40ed3dSBarry Smith PetscFunctionReturn(0); 1933b2fbd54SBarry Smith } 1943b2fbd54SBarry Smith 19587d4246cSBarry Smith #undef __FUNCT__ 19687d4246cSBarry Smith #define __FUNCT__ "MatSetValuesRow_SeqAIJ" 19787d4246cSBarry Smith PetscErrorCode MatSetValuesRow_SeqAIJ(Mat A,PetscInt row,const PetscScalar v[]) 19887d4246cSBarry Smith { 19987d4246cSBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 20087d4246cSBarry Smith PetscInt *ai = a->i; 20187d4246cSBarry Smith PetscErrorCode ierr; 20287d4246cSBarry Smith 20387d4246cSBarry Smith PetscFunctionBegin; 20487d4246cSBarry Smith ierr = PetscMemcpy(a->a+ai[row],v,(ai[row+1]-ai[row])*sizeof(PetscScalar));CHKERRQ(ierr); 20587d4246cSBarry Smith PetscFunctionReturn(0); 20687d4246cSBarry Smith } 20787d4246cSBarry Smith 2084a2ae208SSatish Balay #undef __FUNCT__ 2094a2ae208SSatish Balay #define __FUNCT__ "MatSetValues_SeqAIJ" 21097f1f81fSBarry Smith PetscErrorCode MatSetValues_SeqAIJ(Mat A,PetscInt m,const PetscInt im[],PetscInt n,const PetscInt in[],const PetscScalar v[],InsertMode is) 21117ab2063SBarry Smith { 212416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 213e2ee6c50SBarry Smith PetscInt *rp,k,low,high,t,ii,row,nrow,i,col,l,rmax,N; 21497f1f81fSBarry Smith PetscInt *imax = a->imax,*ai = a->i,*ailen = a->ilen; 2156849ba73SBarry Smith PetscErrorCode ierr; 216e2ee6c50SBarry Smith PetscInt *aj = a->j,nonew = a->nonew,lastcol = -1; 21754f21887SBarry Smith MatScalar *ap,value,*aa = a->a; 218ace3abfcSBarry Smith PetscBool ignorezeroentries = a->ignorezeroentries; 219ace3abfcSBarry Smith PetscBool roworiented = a->roworiented; 22017ab2063SBarry Smith 2213a40ed3dSBarry Smith PetscFunctionBegin; 22271fd2e92SBarry Smith if (v) PetscValidScalarPointer(v,6); 22317ab2063SBarry Smith for (k=0; k<m; k++) { /* loop over added rows */ 224416022c9SBarry Smith row = im[k]; 2255ef9f2a5SBarry Smith if (row < 0) continue; 2262515c552SBarry Smith #if defined(PETSC_USE_DEBUG) 227e32f2f54SBarry Smith if (row >= A->rmap->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Row too large: row %D max %D",row,A->rmap->n-1); 2283b2fbd54SBarry Smith #endif 229bfeeae90SHong Zhang rp = aj + ai[row]; ap = aa + ai[row]; 23017ab2063SBarry Smith rmax = imax[row]; nrow = ailen[row]; 231416022c9SBarry Smith low = 0; 232c71e6ed7SBarry Smith high = nrow; 23317ab2063SBarry Smith for (l=0; l<n; l++) { /* loop over added columns */ 2345ef9f2a5SBarry Smith if (in[l] < 0) continue; 2352515c552SBarry Smith #if defined(PETSC_USE_DEBUG) 236e32f2f54SBarry Smith if (in[l] >= A->cmap->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Column too large: col %D max %D",in[l],A->cmap->n-1); 2373b2fbd54SBarry Smith #endif 238bfeeae90SHong Zhang col = in[l]; 23916371a99SBarry Smith if (v) { 2404b0e389bSBarry Smith if (roworiented) { 2415ef9f2a5SBarry Smith value = v[l + k*n]; 242bef8e0ddSBarry Smith } else { 2434b0e389bSBarry Smith value = v[k + l*m]; 2444b0e389bSBarry Smith } 24516371a99SBarry Smith } else { 24675567043SBarry Smith value = 0.; 24716371a99SBarry Smith } 248abc0a331SBarry Smith if (value == 0.0 && ignorezeroentries && (is == ADD_VALUES)) continue; 24936db0b34SBarry Smith 2507cd84e04SBarry Smith if (col <= lastcol) low = 0; else high = nrow; 251e2ee6c50SBarry Smith lastcol = col; 252416022c9SBarry Smith while (high-low > 5) { 253416022c9SBarry Smith t = (low+high)/2; 254416022c9SBarry Smith if (rp[t] > col) high = t; 255416022c9SBarry Smith else low = t; 25617ab2063SBarry Smith } 257416022c9SBarry Smith for (i=low; i<high; i++) { 25817ab2063SBarry Smith if (rp[i] > col) break; 25917ab2063SBarry Smith if (rp[i] == col) { 260416022c9SBarry Smith if (is == ADD_VALUES) ap[i] += value; 26117ab2063SBarry Smith else ap[i] = value; 262e44c0bd4SBarry Smith low = i + 1; 26317ab2063SBarry Smith goto noinsert; 26417ab2063SBarry Smith } 26517ab2063SBarry Smith } 266abc0a331SBarry Smith if (value == 0.0 && ignorezeroentries) goto noinsert; 267c2653b3dSLois Curfman McInnes if (nonew == 1) goto noinsert; 268e32f2f54SBarry Smith if (nonew == -1) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Inserting a new nonzero at (%D,%D) in the matrix",row,col); 269fef13f97SBarry Smith MatSeqXAIJReallocateAIJ(A,A->rmap->n,1,nrow,row,col,rmax,aa,ai,aj,rp,ap,imax,nonew,MatScalar); 270c03d1d03SSatish Balay N = nrow++ - 1; a->nz++; high++; 271416022c9SBarry Smith /* shift up all the later entries in this row */ 272416022c9SBarry Smith for (ii=N; ii>=i; ii--) { 27317ab2063SBarry Smith rp[ii+1] = rp[ii]; 27417ab2063SBarry Smith ap[ii+1] = ap[ii]; 27517ab2063SBarry Smith } 27617ab2063SBarry Smith rp[i] = col; 27717ab2063SBarry Smith ap[i] = value; 278416022c9SBarry Smith low = i + 1; 279e44c0bd4SBarry Smith noinsert:; 28017ab2063SBarry Smith } 28117ab2063SBarry Smith ailen[row] = nrow; 28217ab2063SBarry Smith } 28388e51ccdSHong Zhang A->same_nonzero = PETSC_FALSE; 2843a40ed3dSBarry Smith PetscFunctionReturn(0); 28517ab2063SBarry Smith } 28617ab2063SBarry Smith 28781824310SBarry Smith 2884a2ae208SSatish Balay #undef __FUNCT__ 2894a2ae208SSatish Balay #define __FUNCT__ "MatGetValues_SeqAIJ" 290a77337e4SBarry Smith PetscErrorCode MatGetValues_SeqAIJ(Mat A,PetscInt m,const PetscInt im[],PetscInt n,const PetscInt in[],PetscScalar v[]) 2917eb43aa7SLois Curfman McInnes { 2927eb43aa7SLois Curfman McInnes Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 29397f1f81fSBarry Smith PetscInt *rp,k,low,high,t,row,nrow,i,col,l,*aj = a->j; 29497f1f81fSBarry Smith PetscInt *ai = a->i,*ailen = a->ilen; 29554f21887SBarry Smith MatScalar *ap,*aa = a->a; 2967eb43aa7SLois Curfman McInnes 2973a40ed3dSBarry Smith PetscFunctionBegin; 2987eb43aa7SLois Curfman McInnes for (k=0; k<m; k++) { /* loop over rows */ 2997eb43aa7SLois Curfman McInnes row = im[k]; 300e32f2f54SBarry Smith if (row < 0) {v += n; continue;} /* SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Negative row: %D",row); */ 301e32f2f54SBarry Smith if (row >= A->rmap->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Row too large: row %D max %D",row,A->rmap->n-1); 302bfeeae90SHong Zhang rp = aj + ai[row]; ap = aa + ai[row]; 3037eb43aa7SLois Curfman McInnes nrow = ailen[row]; 3047eb43aa7SLois Curfman McInnes for (l=0; l<n; l++) { /* loop over columns */ 305e32f2f54SBarry Smith if (in[l] < 0) {v++; continue;} /* SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Negative column: %D",in[l]); */ 306e32f2f54SBarry Smith if (in[l] >= A->cmap->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Column too large: col %D max %D",in[l],A->cmap->n-1); 307bfeeae90SHong Zhang col = in[l] ; 3087eb43aa7SLois Curfman McInnes high = nrow; low = 0; /* assume unsorted */ 3097eb43aa7SLois Curfman McInnes while (high-low > 5) { 3107eb43aa7SLois Curfman McInnes t = (low+high)/2; 3117eb43aa7SLois Curfman McInnes if (rp[t] > col) high = t; 3127eb43aa7SLois Curfman McInnes else low = t; 3137eb43aa7SLois Curfman McInnes } 3147eb43aa7SLois Curfman McInnes for (i=low; i<high; i++) { 3157eb43aa7SLois Curfman McInnes if (rp[i] > col) break; 3167eb43aa7SLois Curfman McInnes if (rp[i] == col) { 317b49de8d1SLois Curfman McInnes *v++ = ap[i]; 3187eb43aa7SLois Curfman McInnes goto finished; 3197eb43aa7SLois Curfman McInnes } 3207eb43aa7SLois Curfman McInnes } 32197e567efSBarry Smith *v++ = 0.0; 3227eb43aa7SLois Curfman McInnes finished:; 3237eb43aa7SLois Curfman McInnes } 3247eb43aa7SLois Curfman McInnes } 3253a40ed3dSBarry Smith PetscFunctionReturn(0); 3267eb43aa7SLois Curfman McInnes } 3277eb43aa7SLois Curfman McInnes 32817ab2063SBarry Smith 3294a2ae208SSatish Balay #undef __FUNCT__ 3304a2ae208SSatish Balay #define __FUNCT__ "MatView_SeqAIJ_Binary" 331dfbe8321SBarry Smith PetscErrorCode MatView_SeqAIJ_Binary(Mat A,PetscViewer viewer) 33217ab2063SBarry Smith { 333416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 3346849ba73SBarry Smith PetscErrorCode ierr; 3356f69ff64SBarry Smith PetscInt i,*col_lens; 3366f69ff64SBarry Smith int fd; 33717ab2063SBarry Smith 3383a40ed3dSBarry Smith PetscFunctionBegin; 339b0a32e0cSBarry Smith ierr = PetscViewerBinaryGetDescriptor(viewer,&fd);CHKERRQ(ierr); 340d0f46423SBarry Smith ierr = PetscMalloc((4+A->rmap->n)*sizeof(PetscInt),&col_lens);CHKERRQ(ierr); 3410700a824SBarry Smith col_lens[0] = MAT_FILE_CLASSID; 342d0f46423SBarry Smith col_lens[1] = A->rmap->n; 343d0f46423SBarry Smith col_lens[2] = A->cmap->n; 344416022c9SBarry Smith col_lens[3] = a->nz; 345416022c9SBarry Smith 346416022c9SBarry Smith /* store lengths of each row and write (including header) to file */ 347d0f46423SBarry Smith for (i=0; i<A->rmap->n; i++) { 348416022c9SBarry Smith col_lens[4+i] = a->i[i+1] - a->i[i]; 34917ab2063SBarry Smith } 350d0f46423SBarry Smith ierr = PetscBinaryWrite(fd,col_lens,4+A->rmap->n,PETSC_INT,PETSC_TRUE);CHKERRQ(ierr); 351606d414cSSatish Balay ierr = PetscFree(col_lens);CHKERRQ(ierr); 352416022c9SBarry Smith 353416022c9SBarry Smith /* store column indices (zero start index) */ 3546f69ff64SBarry Smith ierr = PetscBinaryWrite(fd,a->j,a->nz,PETSC_INT,PETSC_FALSE);CHKERRQ(ierr); 355416022c9SBarry Smith 356416022c9SBarry Smith /* store nonzero values */ 3576f69ff64SBarry Smith ierr = PetscBinaryWrite(fd,a->a,a->nz,PETSC_SCALAR,PETSC_FALSE);CHKERRQ(ierr); 3583a40ed3dSBarry Smith PetscFunctionReturn(0); 35917ab2063SBarry Smith } 360416022c9SBarry Smith 36109573ac7SBarry Smith extern PetscErrorCode MatSeqAIJFactorInfo_Matlab(Mat,PetscViewer); 362cd155464SBarry Smith 3634a2ae208SSatish Balay #undef __FUNCT__ 3644a2ae208SSatish Balay #define __FUNCT__ "MatView_SeqAIJ_ASCII" 365dfbe8321SBarry Smith PetscErrorCode MatView_SeqAIJ_ASCII(Mat A,PetscViewer viewer) 366416022c9SBarry Smith { 367416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 368dfbe8321SBarry Smith PetscErrorCode ierr; 369d0f46423SBarry Smith PetscInt i,j,m = A->rmap->n,shift=0; 370e060cb09SBarry Smith const char *name; 371f3ef73ceSBarry Smith PetscViewerFormat format; 37217ab2063SBarry Smith 3733a40ed3dSBarry Smith PetscFunctionBegin; 374b0a32e0cSBarry Smith ierr = PetscViewerGetFormat(viewer,&format);CHKERRQ(ierr); 37571c2f376SKris Buschelman if (format == PETSC_VIEWER_ASCII_MATLAB) { 37697f1f81fSBarry Smith PetscInt nofinalvalue = 0; 377d0f46423SBarry Smith if ((a->i[m] == a->i[m-1]) || (a->j[a->nz-1] != A->cmap->n-!shift)) { 378d00d2cf4SBarry Smith nofinalvalue = 1; 379d00d2cf4SBarry Smith } 380d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_FALSE);CHKERRQ(ierr); 381d0f46423SBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"%% Size = %D %D \n",m,A->cmap->n);CHKERRQ(ierr); 38277431f27SBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"%% Nonzeros = %D \n",a->nz);CHKERRQ(ierr); 38377431f27SBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"zzz = zeros(%D,3);\n",a->nz+nofinalvalue);CHKERRQ(ierr); 384b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"zzz = [\n");CHKERRQ(ierr); 38517ab2063SBarry Smith 38617ab2063SBarry Smith for (i=0; i<m; i++) { 387416022c9SBarry Smith for (j=a->i[i]+shift; j<a->i[i+1]+shift; j++) { 388aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX) 38977431f27SBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"%D %D %18.16e + %18.16ei \n",i+1,a->j[j]+!shift,PetscRealPart(a->a[j]),PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 39017ab2063SBarry Smith #else 39177431f27SBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"%D %D %18.16e\n",i+1,a->j[j]+!shift,a->a[j]);CHKERRQ(ierr); 39217ab2063SBarry Smith #endif 39317ab2063SBarry Smith } 39417ab2063SBarry Smith } 395d00d2cf4SBarry Smith if (nofinalvalue) { 396d0f46423SBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"%D %D %18.16e\n",m,A->cmap->n,0.0);CHKERRQ(ierr); 397d00d2cf4SBarry Smith } 398317d6ea6SBarry Smith ierr = PetscObjectGetName((PetscObject)A,&name);CHKERRQ(ierr); 399fb9695e5SSatish Balay ierr = PetscViewerASCIIPrintf(viewer,"];\n %s = spconvert(zzz);\n",name);CHKERRQ(ierr); 400d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_TRUE);CHKERRQ(ierr); 40168369a75SKris Buschelman } else if (format == PETSC_VIEWER_ASCII_FACTOR_INFO || format == PETSC_VIEWER_ASCII_INFO) { 402cd155464SBarry Smith PetscFunctionReturn(0); 403fb9695e5SSatish Balay } else if (format == PETSC_VIEWER_ASCII_COMMON) { 404d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_FALSE);CHKERRQ(ierr); 4057566de4bSShri Abhyankar ierr = PetscObjectPrintClassNamePrefixType((PetscObject)A,viewer,"Matrix Object");CHKERRQ(ierr); 40644cd7ae7SLois Curfman McInnes for (i=0; i<m; i++) { 40777431f27SBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"row %D:",i);CHKERRQ(ierr); 40844cd7ae7SLois Curfman McInnes for (j=a->i[i]+shift; j<a->i[i+1]+shift; j++) { 409aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX) 41036db0b34SBarry Smith if (PetscImaginaryPart(a->a[j]) > 0.0 && PetscRealPart(a->a[j]) != 0.0) { 411a83599f4SBarry Smith ierr = PetscViewerASCIIPrintf(viewer," (%D, %G + %G i)",a->j[j]+shift,PetscRealPart(a->a[j]),PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 41236db0b34SBarry Smith } else if (PetscImaginaryPart(a->a[j]) < 0.0 && PetscRealPart(a->a[j]) != 0.0) { 413a83599f4SBarry Smith ierr = PetscViewerASCIIPrintf(viewer," (%D, %G - %G i)",a->j[j]+shift,PetscRealPart(a->a[j]),-PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 41436db0b34SBarry Smith } else if (PetscRealPart(a->a[j]) != 0.0) { 415a83599f4SBarry Smith ierr = PetscViewerASCIIPrintf(viewer," (%D, %G) ",a->j[j]+shift,PetscRealPart(a->a[j]));CHKERRQ(ierr); 4166831982aSBarry Smith } 41744cd7ae7SLois Curfman McInnes #else 418a83599f4SBarry Smith if (a->a[j] != 0.0) {ierr = PetscViewerASCIIPrintf(viewer," (%D, %G) ",a->j[j]+shift,a->a[j]);CHKERRQ(ierr);} 41944cd7ae7SLois Curfman McInnes #endif 42044cd7ae7SLois Curfman McInnes } 421b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"\n");CHKERRQ(ierr); 42244cd7ae7SLois Curfman McInnes } 423d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_TRUE);CHKERRQ(ierr); 424fb9695e5SSatish Balay } else if (format == PETSC_VIEWER_ASCII_SYMMODU) { 42597f1f81fSBarry Smith PetscInt nzd=0,fshift=1,*sptr; 426d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_FALSE);CHKERRQ(ierr); 4277566de4bSShri Abhyankar ierr = PetscObjectPrintClassNamePrefixType((PetscObject)A,viewer,"Matrix Object");CHKERRQ(ierr); 42897f1f81fSBarry Smith ierr = PetscMalloc((m+1)*sizeof(PetscInt),&sptr);CHKERRQ(ierr); 429496be53dSLois Curfman McInnes for (i=0; i<m; i++) { 430496be53dSLois Curfman McInnes sptr[i] = nzd+1; 431496be53dSLois Curfman McInnes for (j=a->i[i]+shift; j<a->i[i+1]+shift; j++) { 432496be53dSLois Curfman McInnes if (a->j[j] >= i) { 433aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX) 43436db0b34SBarry Smith if (PetscImaginaryPart(a->a[j]) != 0.0 || PetscRealPart(a->a[j]) != 0.0) nzd++; 435496be53dSLois Curfman McInnes #else 436496be53dSLois Curfman McInnes if (a->a[j] != 0.0) nzd++; 437496be53dSLois Curfman McInnes #endif 438496be53dSLois Curfman McInnes } 439496be53dSLois Curfman McInnes } 440496be53dSLois Curfman McInnes } 4412e44a96cSLois Curfman McInnes sptr[m] = nzd+1; 44277431f27SBarry Smith ierr = PetscViewerASCIIPrintf(viewer," %D %D\n\n",m,nzd);CHKERRQ(ierr); 4432e44a96cSLois Curfman McInnes for (i=0; i<m+1; i+=6) { 44477431f27SBarry Smith if (i+4<m) {ierr = PetscViewerASCIIPrintf(viewer," %D %D %D %D %D %D\n",sptr[i],sptr[i+1],sptr[i+2],sptr[i+3],sptr[i+4],sptr[i+5]);CHKERRQ(ierr);} 44577431f27SBarry Smith else if (i+3<m) {ierr = PetscViewerASCIIPrintf(viewer," %D %D %D %D %D\n",sptr[i],sptr[i+1],sptr[i+2],sptr[i+3],sptr[i+4]);CHKERRQ(ierr);} 44677431f27SBarry Smith else if (i+2<m) {ierr = PetscViewerASCIIPrintf(viewer," %D %D %D %D\n",sptr[i],sptr[i+1],sptr[i+2],sptr[i+3]);CHKERRQ(ierr);} 44777431f27SBarry Smith else if (i+1<m) {ierr = PetscViewerASCIIPrintf(viewer," %D %D %D\n",sptr[i],sptr[i+1],sptr[i+2]);CHKERRQ(ierr);} 44877431f27SBarry Smith else if (i<m) {ierr = PetscViewerASCIIPrintf(viewer," %D %D\n",sptr[i],sptr[i+1]);CHKERRQ(ierr);} 44977431f27SBarry Smith else {ierr = PetscViewerASCIIPrintf(viewer," %D\n",sptr[i]);CHKERRQ(ierr);} 450496be53dSLois Curfman McInnes } 451b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"\n");CHKERRQ(ierr); 452606d414cSSatish Balay ierr = PetscFree(sptr);CHKERRQ(ierr); 453496be53dSLois Curfman McInnes for (i=0; i<m; i++) { 454496be53dSLois Curfman McInnes for (j=a->i[i]+shift; j<a->i[i+1]+shift; j++) { 45577431f27SBarry Smith if (a->j[j] >= i) {ierr = PetscViewerASCIIPrintf(viewer," %D ",a->j[j]+fshift);CHKERRQ(ierr);} 456496be53dSLois Curfman McInnes } 457b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"\n");CHKERRQ(ierr); 458496be53dSLois Curfman McInnes } 459b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"\n");CHKERRQ(ierr); 460496be53dSLois Curfman McInnes for (i=0; i<m; i++) { 461496be53dSLois Curfman McInnes for (j=a->i[i]+shift; j<a->i[i+1]+shift; j++) { 462496be53dSLois Curfman McInnes if (a->j[j] >= i) { 463aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX) 46436db0b34SBarry Smith if (PetscImaginaryPart(a->a[j]) != 0.0 || PetscRealPart(a->a[j]) != 0.0) { 465b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer," %18.16e %18.16e ",PetscRealPart(a->a[j]),PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 4666831982aSBarry Smith } 467496be53dSLois Curfman McInnes #else 468b0a32e0cSBarry Smith if (a->a[j] != 0.0) {ierr = PetscViewerASCIIPrintf(viewer," %18.16e ",a->a[j]);CHKERRQ(ierr);} 469496be53dSLois Curfman McInnes #endif 470496be53dSLois Curfman McInnes } 471496be53dSLois Curfman McInnes } 472b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"\n");CHKERRQ(ierr); 473496be53dSLois Curfman McInnes } 474d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_TRUE);CHKERRQ(ierr); 475fb9695e5SSatish Balay } else if (format == PETSC_VIEWER_ASCII_DENSE) { 47697f1f81fSBarry Smith PetscInt cnt = 0,jcnt; 47787828ca2SBarry Smith PetscScalar value; 47802594712SBarry Smith 479d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_FALSE);CHKERRQ(ierr); 4807566de4bSShri Abhyankar ierr = PetscObjectPrintClassNamePrefixType((PetscObject)A,viewer,"Matrix Object");CHKERRQ(ierr); 48102594712SBarry Smith for (i=0; i<m; i++) { 48202594712SBarry Smith jcnt = 0; 483d0f46423SBarry Smith for (j=0; j<A->cmap->n; j++) { 484e24b481bSBarry Smith if (jcnt < a->i[i+1]-a->i[i] && j == a->j[cnt]) { 48502594712SBarry Smith value = a->a[cnt++]; 486e24b481bSBarry Smith jcnt++; 48702594712SBarry Smith } else { 48802594712SBarry Smith value = 0.0; 48902594712SBarry Smith } 490aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX) 491b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer," %7.5e+%7.5e i ",PetscRealPart(value),PetscImaginaryPart(value));CHKERRQ(ierr); 49202594712SBarry Smith #else 493b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer," %7.5e ",value);CHKERRQ(ierr); 49402594712SBarry Smith #endif 49502594712SBarry Smith } 496b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"\n");CHKERRQ(ierr); 49702594712SBarry Smith } 498d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_TRUE);CHKERRQ(ierr); 4993c215bfdSMatthew Knepley } else if (format == PETSC_VIEWER_ASCII_MATRIXMARKET) { 500d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_FALSE);CHKERRQ(ierr); 5017566de4bSShri Abhyankar ierr = PetscObjectPrintClassNamePrefixType((PetscObject)A,viewer,"Matrix Object");CHKERRQ(ierr); 5023c215bfdSMatthew Knepley #if defined(PETSC_USE_COMPLEX) 5033c215bfdSMatthew Knepley ierr = PetscViewerASCIIPrintf(viewer,"%%matrix complex general\n");CHKERRQ(ierr); 5043c215bfdSMatthew Knepley #else 5053c215bfdSMatthew Knepley ierr = PetscViewerASCIIPrintf(viewer,"%%matrix real general\n");CHKERRQ(ierr); 5063c215bfdSMatthew Knepley #endif 507d0f46423SBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"%D %D %D\n", m, A->cmap->n, a->nz);CHKERRQ(ierr); 5083c215bfdSMatthew Knepley for (i=0; i<m; i++) { 5093c215bfdSMatthew Knepley for (j=a->i[i]+shift; j<a->i[i+1]+shift; j++) { 5103c215bfdSMatthew Knepley #if defined(PETSC_USE_COMPLEX) 5113c215bfdSMatthew Knepley if (PetscImaginaryPart(a->a[j]) > 0.0) { 5123c215bfdSMatthew Knepley ierr = PetscViewerASCIIPrintf(viewer,"%D %D, %G %G\n", i+shift,a->j[j]+shift,PetscRealPart(a->a[j]),PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 5133c215bfdSMatthew Knepley } else if (PetscImaginaryPart(a->a[j]) < 0.0) { 5143c215bfdSMatthew Knepley ierr = PetscViewerASCIIPrintf(viewer,"%D %D, %G -%G\n", i+shift,a->j[j]+shift,PetscRealPart(a->a[j]),-PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 5153c215bfdSMatthew Knepley } else { 5163c215bfdSMatthew Knepley ierr = PetscViewerASCIIPrintf(viewer,"%D %D, %G\n", i+shift,a->j[j]+shift,PetscRealPart(a->a[j]));CHKERRQ(ierr); 5173c215bfdSMatthew Knepley } 5183c215bfdSMatthew Knepley #else 5193c215bfdSMatthew Knepley ierr = PetscViewerASCIIPrintf(viewer,"%D %D %G\n", i+shift, a->j[j]+shift, a->a[j]);CHKERRQ(ierr); 5203c215bfdSMatthew Knepley #endif 5213c215bfdSMatthew Knepley } 5223c215bfdSMatthew Knepley } 523d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_TRUE);CHKERRQ(ierr); 5243a40ed3dSBarry Smith } else { 525d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_FALSE);CHKERRQ(ierr); 5267566de4bSShri Abhyankar ierr = PetscObjectPrintClassNamePrefixType((PetscObject)A,viewer,"Matrix Object");CHKERRQ(ierr); 527d5f3da31SBarry Smith if (A->factortype){ 52816cd7e1dSShri Abhyankar for (i=0; i<m; i++) { 52916cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer,"row %D:",i);CHKERRQ(ierr); 53016cd7e1dSShri Abhyankar /* L part */ 53116cd7e1dSShri Abhyankar for (j=a->i[i]+shift; j<a->i[i+1]+shift; j++) { 53216cd7e1dSShri Abhyankar #if defined(PETSC_USE_COMPLEX) 53316cd7e1dSShri Abhyankar if (PetscImaginaryPart(a->a[j]) > 0.0) { 53416cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G + %G i)",a->j[j]+shift,PetscRealPart(a->a[j]),PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 53516cd7e1dSShri Abhyankar } else if (PetscImaginaryPart(a->a[j]) < 0.0) { 53616cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G - %G i)",a->j[j]+shift,PetscRealPart(a->a[j]),-PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 53716cd7e1dSShri Abhyankar } else { 53816cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G) ",a->j[j]+shift,PetscRealPart(a->a[j]));CHKERRQ(ierr); 53916cd7e1dSShri Abhyankar } 54016cd7e1dSShri Abhyankar #else 54116cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G) ",a->j[j]+shift,a->a[j]);CHKERRQ(ierr); 54216cd7e1dSShri Abhyankar #endif 54316cd7e1dSShri Abhyankar } 54416cd7e1dSShri Abhyankar /* diagonal */ 54516cd7e1dSShri Abhyankar j = a->diag[i]; 54616cd7e1dSShri Abhyankar #if defined(PETSC_USE_COMPLEX) 54716cd7e1dSShri Abhyankar if (PetscImaginaryPart(a->a[j]) > 0.0) { 54816cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G + %G i)",a->j[j]+shift,PetscRealPart(a->a[j]),PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 54916cd7e1dSShri Abhyankar } else if (PetscImaginaryPart(a->a[j]) < 0.0) { 55016cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G - %G i)",a->j[j]+shift,PetscRealPart(a->a[j]),-PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 55116cd7e1dSShri Abhyankar } else { 55216cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G) ",a->j[j]+shift,PetscRealPart(a->a[j]));CHKERRQ(ierr); 55316cd7e1dSShri Abhyankar } 55416cd7e1dSShri Abhyankar #else 55516cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G) ",a->j[j]+shift,a->a[j]);CHKERRQ(ierr); 55616cd7e1dSShri Abhyankar #endif 55716cd7e1dSShri Abhyankar 55816cd7e1dSShri Abhyankar /* U part */ 55916cd7e1dSShri Abhyankar for (j=a->diag[i+1]+1+shift; j<a->diag[i]+shift; j++) { 56016cd7e1dSShri Abhyankar #if defined(PETSC_USE_COMPLEX) 56116cd7e1dSShri Abhyankar if (PetscImaginaryPart(a->a[j]) > 0.0) { 56216cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G + %G i)",a->j[j]+shift,PetscRealPart(a->a[j]),PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 56316cd7e1dSShri Abhyankar } else if (PetscImaginaryPart(a->a[j]) < 0.0) { 56416cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G - %G i)",a->j[j]+shift,PetscRealPart(a->a[j]),-PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 56516cd7e1dSShri Abhyankar } else { 56616cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G) ",a->j[j]+shift,PetscRealPart(a->a[j]));CHKERRQ(ierr); 56716cd7e1dSShri Abhyankar } 56816cd7e1dSShri Abhyankar #else 56916cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer," (%D, %G) ",a->j[j]+shift,a->a[j]);CHKERRQ(ierr); 57016cd7e1dSShri Abhyankar #endif 57116cd7e1dSShri Abhyankar } 57216cd7e1dSShri Abhyankar ierr = PetscViewerASCIIPrintf(viewer,"\n");CHKERRQ(ierr); 57316cd7e1dSShri Abhyankar } 57416cd7e1dSShri Abhyankar } else { 57517ab2063SBarry Smith for (i=0; i<m; i++) { 57677431f27SBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"row %D:",i);CHKERRQ(ierr); 577416022c9SBarry Smith for (j=a->i[i]+shift; j<a->i[i+1]+shift; j++) { 578aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX) 57936db0b34SBarry Smith if (PetscImaginaryPart(a->a[j]) > 0.0) { 580a83599f4SBarry Smith ierr = PetscViewerASCIIPrintf(viewer," (%D, %G + %G i)",a->j[j]+shift,PetscRealPart(a->a[j]),PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 58136db0b34SBarry Smith } else if (PetscImaginaryPart(a->a[j]) < 0.0) { 582a83599f4SBarry Smith ierr = PetscViewerASCIIPrintf(viewer," (%D, %G - %G i)",a->j[j]+shift,PetscRealPart(a->a[j]),-PetscImaginaryPart(a->a[j]));CHKERRQ(ierr); 5833a40ed3dSBarry Smith } else { 584a83599f4SBarry Smith ierr = PetscViewerASCIIPrintf(viewer," (%D, %G) ",a->j[j]+shift,PetscRealPart(a->a[j]));CHKERRQ(ierr); 58517ab2063SBarry Smith } 58617ab2063SBarry Smith #else 587a83599f4SBarry Smith ierr = PetscViewerASCIIPrintf(viewer," (%D, %G) ",a->j[j]+shift,a->a[j]);CHKERRQ(ierr); 58817ab2063SBarry Smith #endif 58917ab2063SBarry Smith } 590b0a32e0cSBarry Smith ierr = PetscViewerASCIIPrintf(viewer,"\n");CHKERRQ(ierr); 59117ab2063SBarry Smith } 59216cd7e1dSShri Abhyankar } 593d00279f6SBarry Smith ierr = PetscViewerASCIIUseTabs(viewer,PETSC_TRUE);CHKERRQ(ierr); 59417ab2063SBarry Smith } 595b0a32e0cSBarry Smith ierr = PetscViewerFlush(viewer);CHKERRQ(ierr); 5963a40ed3dSBarry Smith PetscFunctionReturn(0); 597416022c9SBarry Smith } 598416022c9SBarry Smith 5994a2ae208SSatish Balay #undef __FUNCT__ 6004a2ae208SSatish Balay #define __FUNCT__ "MatView_SeqAIJ_Draw_Zoom" 601dfbe8321SBarry Smith PetscErrorCode MatView_SeqAIJ_Draw_Zoom(PetscDraw draw,void *Aa) 602416022c9SBarry Smith { 603480ef9eaSBarry Smith Mat A = (Mat) Aa; 604416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 605dfbe8321SBarry Smith PetscErrorCode ierr; 606d0f46423SBarry Smith PetscInt i,j,m = A->rmap->n,color; 60736db0b34SBarry Smith PetscReal xl,yl,xr,yr,x_l,x_r,y_l,y_r,maxv = 0.0; 608b0a32e0cSBarry Smith PetscViewer viewer; 609f3ef73ceSBarry Smith PetscViewerFormat format; 610cddf8d76SBarry Smith 6113a40ed3dSBarry Smith PetscFunctionBegin; 612480ef9eaSBarry Smith ierr = PetscObjectQuery((PetscObject)A,"Zoomviewer",(PetscObject*)&viewer);CHKERRQ(ierr); 613b0a32e0cSBarry Smith ierr = PetscViewerGetFormat(viewer,&format);CHKERRQ(ierr); 61419bcc07fSBarry Smith 615b0a32e0cSBarry Smith ierr = PetscDrawGetCoordinates(draw,&xl,&yl,&xr,&yr);CHKERRQ(ierr); 616416022c9SBarry Smith /* loop over matrix elements drawing boxes */ 6170513a670SBarry Smith 618fb9695e5SSatish Balay if (format != PETSC_VIEWER_DRAW_CONTOUR) { 6190513a670SBarry Smith /* Blue for negative, Cyan for zero and Red for positive */ 620b0a32e0cSBarry Smith color = PETSC_DRAW_BLUE; 621416022c9SBarry Smith for (i=0; i<m; i++) { 622cddf8d76SBarry Smith y_l = m - i - 1.0; y_r = y_l + 1.0; 623bfeeae90SHong Zhang for (j=a->i[i]; j<a->i[i+1]; j++) { 624bfeeae90SHong Zhang x_l = a->j[j] ; x_r = x_l + 1.0; 625aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX) 62636db0b34SBarry Smith if (PetscRealPart(a->a[j]) >= 0.) continue; 627cddf8d76SBarry Smith #else 628cddf8d76SBarry Smith if (a->a[j] >= 0.) continue; 629cddf8d76SBarry Smith #endif 630b0a32e0cSBarry Smith ierr = PetscDrawRectangle(draw,x_l,y_l,x_r,y_r,color,color,color,color);CHKERRQ(ierr); 631cddf8d76SBarry Smith } 632cddf8d76SBarry Smith } 633b0a32e0cSBarry Smith color = PETSC_DRAW_CYAN; 634cddf8d76SBarry Smith for (i=0; i<m; i++) { 635cddf8d76SBarry Smith y_l = m - i - 1.0; y_r = y_l + 1.0; 636bfeeae90SHong Zhang for (j=a->i[i]; j<a->i[i+1]; j++) { 637bfeeae90SHong Zhang x_l = a->j[j]; x_r = x_l + 1.0; 638cddf8d76SBarry Smith if (a->a[j] != 0.) continue; 639b0a32e0cSBarry Smith ierr = PetscDrawRectangle(draw,x_l,y_l,x_r,y_r,color,color,color,color);CHKERRQ(ierr); 640cddf8d76SBarry Smith } 641cddf8d76SBarry Smith } 642b0a32e0cSBarry Smith color = PETSC_DRAW_RED; 643cddf8d76SBarry Smith for (i=0; i<m; i++) { 644cddf8d76SBarry Smith y_l = m - i - 1.0; y_r = y_l + 1.0; 645bfeeae90SHong Zhang for (j=a->i[i]; j<a->i[i+1]; j++) { 646bfeeae90SHong Zhang x_l = a->j[j]; x_r = x_l + 1.0; 647aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX) 64836db0b34SBarry Smith if (PetscRealPart(a->a[j]) <= 0.) continue; 649cddf8d76SBarry Smith #else 650cddf8d76SBarry Smith if (a->a[j] <= 0.) continue; 651cddf8d76SBarry Smith #endif 652b0a32e0cSBarry Smith ierr = PetscDrawRectangle(draw,x_l,y_l,x_r,y_r,color,color,color,color);CHKERRQ(ierr); 653416022c9SBarry Smith } 654416022c9SBarry Smith } 6550513a670SBarry Smith } else { 6560513a670SBarry Smith /* use contour shading to indicate magnitude of values */ 6570513a670SBarry Smith /* first determine max of all nonzero values */ 65897f1f81fSBarry Smith PetscInt nz = a->nz,count; 659b0a32e0cSBarry Smith PetscDraw popup; 66036db0b34SBarry Smith PetscReal scale; 6610513a670SBarry Smith 6620513a670SBarry Smith for (i=0; i<nz; i++) { 6630513a670SBarry Smith if (PetscAbsScalar(a->a[i]) > maxv) maxv = PetscAbsScalar(a->a[i]); 6640513a670SBarry Smith } 665b0a32e0cSBarry Smith scale = (245.0 - PETSC_DRAW_BASIC_COLORS)/maxv; 666b0a32e0cSBarry Smith ierr = PetscDrawGetPopup(draw,&popup);CHKERRQ(ierr); 667b0a32e0cSBarry Smith if (popup) {ierr = PetscDrawScalePopup(popup,0.0,maxv);CHKERRQ(ierr);} 6680513a670SBarry Smith count = 0; 6690513a670SBarry Smith for (i=0; i<m; i++) { 6700513a670SBarry Smith y_l = m - i - 1.0; y_r = y_l + 1.0; 671bfeeae90SHong Zhang for (j=a->i[i]; j<a->i[i+1]; j++) { 672bfeeae90SHong Zhang x_l = a->j[j]; x_r = x_l + 1.0; 67397f1f81fSBarry Smith color = PETSC_DRAW_BASIC_COLORS + (PetscInt)(scale*PetscAbsScalar(a->a[count])); 674b0a32e0cSBarry Smith ierr = PetscDrawRectangle(draw,x_l,y_l,x_r,y_r,color,color,color,color);CHKERRQ(ierr); 6750513a670SBarry Smith count++; 6760513a670SBarry Smith } 6770513a670SBarry Smith } 6780513a670SBarry Smith } 679480ef9eaSBarry Smith PetscFunctionReturn(0); 680480ef9eaSBarry Smith } 681cddf8d76SBarry Smith 6824a2ae208SSatish Balay #undef __FUNCT__ 6834a2ae208SSatish Balay #define __FUNCT__ "MatView_SeqAIJ_Draw" 684dfbe8321SBarry Smith PetscErrorCode MatView_SeqAIJ_Draw(Mat A,PetscViewer viewer) 685480ef9eaSBarry Smith { 686dfbe8321SBarry Smith PetscErrorCode ierr; 687b0a32e0cSBarry Smith PetscDraw draw; 68836db0b34SBarry Smith PetscReal xr,yr,xl,yl,h,w; 689ace3abfcSBarry Smith PetscBool isnull; 690480ef9eaSBarry Smith 691480ef9eaSBarry Smith PetscFunctionBegin; 692b0a32e0cSBarry Smith ierr = PetscViewerDrawGetDraw(viewer,0,&draw);CHKERRQ(ierr); 693b0a32e0cSBarry Smith ierr = PetscDrawIsNull(draw,&isnull);CHKERRQ(ierr); 694480ef9eaSBarry Smith if (isnull) PetscFunctionReturn(0); 695480ef9eaSBarry Smith 696480ef9eaSBarry Smith ierr = PetscObjectCompose((PetscObject)A,"Zoomviewer",(PetscObject)viewer);CHKERRQ(ierr); 697d0f46423SBarry Smith xr = A->cmap->n; yr = A->rmap->n; h = yr/10.0; w = xr/10.0; 698480ef9eaSBarry Smith xr += w; yr += h; xl = -w; yl = -h; 699b0a32e0cSBarry Smith ierr = PetscDrawSetCoordinates(draw,xl,yl,xr,yr);CHKERRQ(ierr); 700b0a32e0cSBarry Smith ierr = PetscDrawZoom(draw,MatView_SeqAIJ_Draw_Zoom,A);CHKERRQ(ierr); 701480ef9eaSBarry Smith ierr = PetscObjectCompose((PetscObject)A,"Zoomviewer",PETSC_NULL);CHKERRQ(ierr); 7023a40ed3dSBarry Smith PetscFunctionReturn(0); 703416022c9SBarry Smith } 704416022c9SBarry Smith 7054a2ae208SSatish Balay #undef __FUNCT__ 7064a2ae208SSatish Balay #define __FUNCT__ "MatView_SeqAIJ" 707dfbe8321SBarry Smith PetscErrorCode MatView_SeqAIJ(Mat A,PetscViewer viewer) 708416022c9SBarry Smith { 709dfbe8321SBarry Smith PetscErrorCode ierr; 710ace3abfcSBarry Smith PetscBool iascii,isbinary,isdraw; 711416022c9SBarry Smith 7123a40ed3dSBarry Smith PetscFunctionBegin; 7132692d6eeSBarry Smith ierr = PetscTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 7142692d6eeSBarry Smith ierr = PetscTypeCompare((PetscObject)viewer,PETSCVIEWERBINARY,&isbinary);CHKERRQ(ierr); 7152692d6eeSBarry Smith ierr = PetscTypeCompare((PetscObject)viewer,PETSCVIEWERDRAW,&isdraw);CHKERRQ(ierr); 716c45a1595SBarry Smith if (iascii) { 7173a40ed3dSBarry Smith ierr = MatView_SeqAIJ_ASCII(A,viewer);CHKERRQ(ierr); 7180f5bd95cSBarry Smith } else if (isbinary) { 7193a40ed3dSBarry Smith ierr = MatView_SeqAIJ_Binary(A,viewer);CHKERRQ(ierr); 7200f5bd95cSBarry Smith } else if (isdraw) { 7213a40ed3dSBarry Smith ierr = MatView_SeqAIJ_Draw(A,viewer);CHKERRQ(ierr); 7225cd90555SBarry Smith } else { 723e32f2f54SBarry Smith SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Viewer type %s not supported by SeqAIJ matrices",((PetscObject)viewer)->type_name); 72417ab2063SBarry Smith } 7254108e4d5SBarry Smith ierr = MatView_SeqAIJ_Inode(A,viewer);CHKERRQ(ierr); 7263a40ed3dSBarry Smith PetscFunctionReturn(0); 72717ab2063SBarry Smith } 72819bcc07fSBarry Smith 7294a2ae208SSatish Balay #undef __FUNCT__ 7304a2ae208SSatish Balay #define __FUNCT__ "MatAssemblyEnd_SeqAIJ" 731dfbe8321SBarry Smith PetscErrorCode MatAssemblyEnd_SeqAIJ(Mat A,MatAssemblyType mode) 73217ab2063SBarry Smith { 733416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 7346849ba73SBarry Smith PetscErrorCode ierr; 73597f1f81fSBarry Smith PetscInt fshift = 0,i,j,*ai = a->i,*aj = a->j,*imax = a->imax; 736d0f46423SBarry Smith PetscInt m = A->rmap->n,*ip,N,*ailen = a->ilen,rmax = 0; 73754f21887SBarry Smith MatScalar *aa = a->a,*ap; 7383447b6efSHong Zhang PetscReal ratio=0.6; 73917ab2063SBarry Smith 7403a40ed3dSBarry Smith PetscFunctionBegin; 7413a40ed3dSBarry Smith if (mode == MAT_FLUSH_ASSEMBLY) PetscFunctionReturn(0); 74217ab2063SBarry Smith 74343ee02c3SBarry Smith if (m) rmax = ailen[0]; /* determine row with most nonzeros */ 74417ab2063SBarry Smith for (i=1; i<m; i++) { 745416022c9SBarry Smith /* move each row back by the amount of empty slots (fshift) before it*/ 74617ab2063SBarry Smith fshift += imax[i-1] - ailen[i-1]; 74794a9d846SBarry Smith rmax = PetscMax(rmax,ailen[i]); 74817ab2063SBarry Smith if (fshift) { 749bfeeae90SHong Zhang ip = aj + ai[i] ; 750bfeeae90SHong Zhang ap = aa + ai[i] ; 75117ab2063SBarry Smith N = ailen[i]; 75217ab2063SBarry Smith for (j=0; j<N; j++) { 75317ab2063SBarry Smith ip[j-fshift] = ip[j]; 75417ab2063SBarry Smith ap[j-fshift] = ap[j]; 75517ab2063SBarry Smith } 75617ab2063SBarry Smith } 75717ab2063SBarry Smith ai[i] = ai[i-1] + ailen[i-1]; 75817ab2063SBarry Smith } 75917ab2063SBarry Smith if (m) { 76017ab2063SBarry Smith fshift += imax[m-1] - ailen[m-1]; 76117ab2063SBarry Smith ai[m] = ai[m-1] + ailen[m-1]; 76217ab2063SBarry Smith } 76317ab2063SBarry Smith /* reset ilen and imax for each row */ 76417ab2063SBarry Smith for (i=0; i<m; i++) { 76517ab2063SBarry Smith ailen[i] = imax[i] = ai[i+1] - ai[i]; 76617ab2063SBarry Smith } 767bfeeae90SHong Zhang a->nz = ai[m]; 76865e19b50SBarry Smith if (fshift && a->nounused == -1) SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_PLIB, "Unused space detected in matrix: %D X %D, %D unneeded", m, A->cmap->n, fshift); 76917ab2063SBarry Smith 77009f38230SBarry Smith ierr = MatMarkDiagonal_SeqAIJ(A);CHKERRQ(ierr); 771d0f46423SBarry Smith ierr = PetscInfo4(A,"Matrix size: %D X %D; storage space: %D unneeded,%D used\n",m,A->cmap->n,fshift,a->nz);CHKERRQ(ierr); 772ae15b995SBarry Smith ierr = PetscInfo1(A,"Number of mallocs during MatSetValues() is %D\n",a->reallocs);CHKERRQ(ierr); 773ae15b995SBarry Smith ierr = PetscInfo1(A,"Maximum nonzeros in any row is %D\n",rmax);CHKERRQ(ierr); 7748e58a170SBarry Smith A->info.mallocs += a->reallocs; 775dd5f02e7SSatish Balay a->reallocs = 0; 7764e220ebcSLois Curfman McInnes A->info.nz_unneeded = (double)fshift; 77736db0b34SBarry Smith a->rmax = rmax; 7784e220ebcSLois Curfman McInnes 779cd6b891eSBarry Smith ierr = MatCheckCompressedRow(A,&a->compressedrow,a->i,m,ratio);CHKERRQ(ierr); 78088e51ccdSHong Zhang A->same_nonzero = PETSC_TRUE; 78171c2f376SKris Buschelman 7824108e4d5SBarry Smith ierr = MatAssemblyEnd_SeqAIJ_Inode(A,mode);CHKERRQ(ierr); 78371f1c65dSBarry Smith 78471f1c65dSBarry Smith a->idiagvalid = PETSC_FALSE; 7853a40ed3dSBarry Smith PetscFunctionReturn(0); 78617ab2063SBarry Smith } 78717ab2063SBarry Smith 7884a2ae208SSatish Balay #undef __FUNCT__ 78999cafbc1SBarry Smith #define __FUNCT__ "MatRealPart_SeqAIJ" 79099cafbc1SBarry Smith PetscErrorCode MatRealPart_SeqAIJ(Mat A) 79199cafbc1SBarry Smith { 79299cafbc1SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 79399cafbc1SBarry Smith PetscInt i,nz = a->nz; 79454f21887SBarry Smith MatScalar *aa = a->a; 79599cafbc1SBarry Smith 79699cafbc1SBarry Smith PetscFunctionBegin; 79799cafbc1SBarry Smith for (i=0; i<nz; i++) aa[i] = PetscRealPart(aa[i]); 79899cafbc1SBarry Smith PetscFunctionReturn(0); 79999cafbc1SBarry Smith } 80099cafbc1SBarry Smith 80199cafbc1SBarry Smith #undef __FUNCT__ 80299cafbc1SBarry Smith #define __FUNCT__ "MatImaginaryPart_SeqAIJ" 80399cafbc1SBarry Smith PetscErrorCode MatImaginaryPart_SeqAIJ(Mat A) 80499cafbc1SBarry Smith { 80599cafbc1SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 80699cafbc1SBarry Smith PetscInt i,nz = a->nz; 80754f21887SBarry Smith MatScalar *aa = a->a; 80899cafbc1SBarry Smith 80999cafbc1SBarry Smith PetscFunctionBegin; 81099cafbc1SBarry Smith for (i=0; i<nz; i++) aa[i] = PetscImaginaryPart(aa[i]); 81199cafbc1SBarry Smith PetscFunctionReturn(0); 81299cafbc1SBarry Smith } 81399cafbc1SBarry Smith 81499cafbc1SBarry Smith #undef __FUNCT__ 8154a2ae208SSatish Balay #define __FUNCT__ "MatZeroEntries_SeqAIJ" 816dfbe8321SBarry Smith PetscErrorCode MatZeroEntries_SeqAIJ(Mat A) 81717ab2063SBarry Smith { 818416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 819dfbe8321SBarry Smith PetscErrorCode ierr; 8203a40ed3dSBarry Smith 8213a40ed3dSBarry Smith PetscFunctionBegin; 822d0f46423SBarry Smith ierr = PetscMemzero(a->a,(a->i[A->rmap->n])*sizeof(PetscScalar));CHKERRQ(ierr); 8233a40ed3dSBarry Smith PetscFunctionReturn(0); 82417ab2063SBarry Smith } 825416022c9SBarry Smith 8264a2ae208SSatish Balay #undef __FUNCT__ 8274a2ae208SSatish Balay #define __FUNCT__ "MatDestroy_SeqAIJ" 828dfbe8321SBarry Smith PetscErrorCode MatDestroy_SeqAIJ(Mat A) 82917ab2063SBarry Smith { 830416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 831dfbe8321SBarry Smith PetscErrorCode ierr; 832d5d45c9bSBarry Smith 8333a40ed3dSBarry Smith PetscFunctionBegin; 834aa482453SBarry Smith #if defined(PETSC_USE_LOG) 835d0f46423SBarry Smith PetscLogObjectState((PetscObject)A,"Rows=%D, Cols=%D, NZ=%D",A->rmap->n,A->cmap->n,a->nz); 83617ab2063SBarry Smith #endif 837e6b907acSBarry Smith ierr = MatSeqXAIJFreeAIJ(A,&a->a,&a->j,&a->i);CHKERRQ(ierr); 838c38d4ed2SBarry Smith if (a->row) { 839c38d4ed2SBarry Smith ierr = ISDestroy(a->row);CHKERRQ(ierr); 840c38d4ed2SBarry Smith } 841c38d4ed2SBarry Smith if (a->col) { 842c38d4ed2SBarry Smith ierr = ISDestroy(a->col);CHKERRQ(ierr); 843c38d4ed2SBarry Smith } 84405b42c5fSBarry Smith ierr = PetscFree(a->diag);CHKERRQ(ierr); 84505b42c5fSBarry Smith ierr = PetscFree2(a->imax,a->ilen);CHKERRQ(ierr); 84671f1c65dSBarry Smith ierr = PetscFree3(a->idiag,a->mdiag,a->ssor_work);CHKERRQ(ierr); 84705b42c5fSBarry Smith ierr = PetscFree(a->solve_work);CHKERRQ(ierr); 84882bf6240SBarry Smith if (a->icol) {ierr = ISDestroy(a->icol);CHKERRQ(ierr);} 84905b42c5fSBarry Smith ierr = PetscFree(a->saved_values);CHKERRQ(ierr); 850cc8ba8e1SBarry Smith if (a->coloring) {ierr = ISColoringDestroy(a->coloring);CHKERRQ(ierr);} 85105b42c5fSBarry Smith ierr = PetscFree(a->xtoy);CHKERRQ(ierr); 852407f6b05SHong Zhang if (a->XtoY) {ierr = MatDestroy(a->XtoY);CHKERRQ(ierr);} 853cd6b891eSBarry Smith ierr = PetscFree2(a->compressedrow.i,a->compressedrow.rindex);CHKERRQ(ierr); 854a30b2313SHong Zhang 8554108e4d5SBarry Smith ierr = MatDestroy_SeqAIJ_Inode(A);CHKERRQ(ierr); 8564846f1f5SKris Buschelman 857606d414cSSatish Balay ierr = PetscFree(a);CHKERRQ(ierr); 858901853e0SKris Buschelman 859dbd8c25aSHong Zhang ierr = PetscObjectChangeTypeName((PetscObject)A,0);CHKERRQ(ierr); 860901853e0SKris Buschelman ierr = PetscObjectComposeFunctionDynamic((PetscObject)A,"MatSeqAIJSetColumnIndices_C","",PETSC_NULL);CHKERRQ(ierr); 861901853e0SKris Buschelman ierr = PetscObjectComposeFunctionDynamic((PetscObject)A,"MatStoreValues_C","",PETSC_NULL);CHKERRQ(ierr); 862901853e0SKris Buschelman ierr = PetscObjectComposeFunctionDynamic((PetscObject)A,"MatRetrieveValues_C","",PETSC_NULL);CHKERRQ(ierr); 863901853e0SKris Buschelman ierr = PetscObjectComposeFunctionDynamic((PetscObject)A,"MatConvert_seqaij_seqsbaij_C","",PETSC_NULL);CHKERRQ(ierr); 864901853e0SKris Buschelman ierr = PetscObjectComposeFunctionDynamic((PetscObject)A,"MatConvert_seqaij_seqbaij_C","",PETSC_NULL);CHKERRQ(ierr); 8655a11e1b2SBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)A,"MatConvert_seqaij_seqaijperm_C","",PETSC_NULL);CHKERRQ(ierr); 866901853e0SKris Buschelman ierr = PetscObjectComposeFunctionDynamic((PetscObject)A,"MatIsTranspose_C","",PETSC_NULL);CHKERRQ(ierr); 867901853e0SKris Buschelman ierr = PetscObjectComposeFunctionDynamic((PetscObject)A,"MatSeqAIJSetPreallocation_C","",PETSC_NULL);CHKERRQ(ierr); 868a1661176SMatthew Knepley ierr = PetscObjectComposeFunctionDynamic((PetscObject)A,"MatSeqAIJSetPreallocationCSR_C","",PETSC_NULL);CHKERRQ(ierr); 869901853e0SKris Buschelman ierr = PetscObjectComposeFunctionDynamic((PetscObject)A,"MatReorderForNonzeroDiagonal_C","",PETSC_NULL);CHKERRQ(ierr); 8703a40ed3dSBarry Smith PetscFunctionReturn(0); 87117ab2063SBarry Smith } 87217ab2063SBarry Smith 8734a2ae208SSatish Balay #undef __FUNCT__ 8744a2ae208SSatish Balay #define __FUNCT__ "MatSetOption_SeqAIJ" 875ace3abfcSBarry Smith PetscErrorCode MatSetOption_SeqAIJ(Mat A,MatOption op,PetscBool flg) 87617ab2063SBarry Smith { 877416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 8784846f1f5SKris Buschelman PetscErrorCode ierr; 8793a40ed3dSBarry Smith 8803a40ed3dSBarry Smith PetscFunctionBegin; 881a65d3064SKris Buschelman switch (op) { 882a65d3064SKris Buschelman case MAT_ROW_ORIENTED: 8834e0d8c25SBarry Smith a->roworiented = flg; 884a65d3064SKris Buschelman break; 885a9817697SBarry Smith case MAT_KEEP_NONZERO_PATTERN: 886a9817697SBarry Smith a->keepnonzeropattern = flg; 887a65d3064SKris Buschelman break; 888512a5fc5SBarry Smith case MAT_NEW_NONZERO_LOCATIONS: 889512a5fc5SBarry Smith a->nonew = (flg ? 0 : 1); 890a65d3064SKris Buschelman break; 891a65d3064SKris Buschelman case MAT_NEW_NONZERO_LOCATION_ERR: 8924e0d8c25SBarry Smith a->nonew = (flg ? -1 : 0); 893a65d3064SKris Buschelman break; 894a65d3064SKris Buschelman case MAT_NEW_NONZERO_ALLOCATION_ERR: 8954e0d8c25SBarry Smith a->nonew = (flg ? -2 : 0); 896a65d3064SKris Buschelman break; 89728b2fa4aSMatthew Knepley case MAT_UNUSED_NONZERO_LOCATION_ERR: 89828b2fa4aSMatthew Knepley a->nounused = (flg ? -1 : 0); 89928b2fa4aSMatthew Knepley break; 900a65d3064SKris Buschelman case MAT_IGNORE_ZERO_ENTRIES: 9014e0d8c25SBarry Smith a->ignorezeroentries = flg; 9020df259c2SBarry Smith break; 903cd6b891eSBarry Smith case MAT_CHECK_COMPRESSED_ROW: 904cd6b891eSBarry Smith a->compressedrow.check = flg; 905d487561eSHong Zhang break; 9063d472b54SHong Zhang case MAT_SPD: 9073d472b54SHong Zhang A->spd_set = PETSC_TRUE; 9083d472b54SHong Zhang A->spd = flg; 9093d472b54SHong Zhang if (flg) { 9103d472b54SHong Zhang A->symmetric = PETSC_TRUE; 9113d472b54SHong Zhang A->structurally_symmetric = PETSC_TRUE; 9123d472b54SHong Zhang A->symmetric_set = PETSC_TRUE; 9133d472b54SHong Zhang A->structurally_symmetric_set = PETSC_TRUE; 9143d472b54SHong Zhang } 9153d472b54SHong Zhang break; 916b1646e73SJed Brown case MAT_SYMMETRIC: 917b1646e73SJed Brown case MAT_STRUCTURALLY_SYMMETRIC: 918b1646e73SJed Brown case MAT_HERMITIAN: 919b1646e73SJed Brown case MAT_SYMMETRY_ETERNAL: 9204e0d8c25SBarry Smith case MAT_NEW_DIAGONALS: 921a65d3064SKris Buschelman case MAT_IGNORE_OFF_PROC_ENTRIES: 922a65d3064SKris Buschelman case MAT_USE_HASH_TABLE: 923290bbb0aSBarry Smith ierr = PetscInfo1(A,"Option %s ignored\n",MatOptions[op]);CHKERRQ(ierr); 924a65d3064SKris Buschelman break; 925b87ac2d8SJed Brown case MAT_USE_INODES: 926b87ac2d8SJed Brown /* Not an error because MatSetOption_SeqAIJ_Inode handles this one */ 927b87ac2d8SJed Brown break; 928a65d3064SKris Buschelman default: 929e32f2f54SBarry Smith SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"unknown option %d",op); 930a65d3064SKris Buschelman } 9314108e4d5SBarry Smith ierr = MatSetOption_SeqAIJ_Inode(A,op,flg);CHKERRQ(ierr); 9323a40ed3dSBarry Smith PetscFunctionReturn(0); 93317ab2063SBarry Smith } 93417ab2063SBarry Smith 9354a2ae208SSatish Balay #undef __FUNCT__ 9364a2ae208SSatish Balay #define __FUNCT__ "MatGetDiagonal_SeqAIJ" 937dfbe8321SBarry Smith PetscErrorCode MatGetDiagonal_SeqAIJ(Mat A,Vec v) 93817ab2063SBarry Smith { 939416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 9406849ba73SBarry Smith PetscErrorCode ierr; 941d3e70bfaSHong Zhang PetscInt i,j,n,*ai=a->i,*aj=a->j,nz; 94235e7444dSHong Zhang PetscScalar *aa=a->a,*x,zero=0.0; 94317ab2063SBarry Smith 9443a40ed3dSBarry Smith PetscFunctionBegin; 945d3e70bfaSHong Zhang ierr = VecGetLocalSize(v,&n);CHKERRQ(ierr); 946e32f2f54SBarry Smith if (n != A->rmap->n) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Nonconforming matrix and vector"); 94735e7444dSHong Zhang 948d5f3da31SBarry Smith if (A->factortype == MAT_FACTOR_ILU || A->factortype == MAT_FACTOR_LU){ 949d3e70bfaSHong Zhang PetscInt *diag=a->diag; 95035e7444dSHong Zhang ierr = VecGetArray(v,&x);CHKERRQ(ierr); 95135e7444dSHong Zhang for (i=0; i<n; i++) x[i] = aa[diag[i]]; 95235e7444dSHong Zhang ierr = VecRestoreArray(v,&x);CHKERRQ(ierr); 95335e7444dSHong Zhang PetscFunctionReturn(0); 95435e7444dSHong Zhang } 95535e7444dSHong Zhang 9562dcb1b2aSMatthew Knepley ierr = VecSet(v,zero);CHKERRQ(ierr); 9571ebc52fbSHong Zhang ierr = VecGetArray(v,&x);CHKERRQ(ierr); 95835e7444dSHong Zhang for (i=0; i<n; i++) { 95935e7444dSHong Zhang nz = ai[i+1] - ai[i]; 9602f5a7c2eSBarry Smith if (!nz) x[i] = 0.0; 96135e7444dSHong Zhang for (j=ai[i]; j<ai[i+1]; j++){ 96235e7444dSHong Zhang if (aj[j] == i) { 96335e7444dSHong Zhang x[i] = aa[j]; 96417ab2063SBarry Smith break; 96517ab2063SBarry Smith } 96617ab2063SBarry Smith } 96717ab2063SBarry Smith } 9681ebc52fbSHong Zhang ierr = VecRestoreArray(v,&x);CHKERRQ(ierr); 9693a40ed3dSBarry Smith PetscFunctionReturn(0); 97017ab2063SBarry Smith } 97117ab2063SBarry Smith 972b377110cSBarry Smith #include "../src/mat/impls/aij/seq/ftn-kernels/fmult.h" 9734a2ae208SSatish Balay #undef __FUNCT__ 9744a2ae208SSatish Balay #define __FUNCT__ "MatMultTransposeAdd_SeqAIJ" 975dfbe8321SBarry Smith PetscErrorCode MatMultTransposeAdd_SeqAIJ(Mat A,Vec xx,Vec zz,Vec yy) 97617ab2063SBarry Smith { 977416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 9785c897100SBarry Smith PetscScalar *x,*y; 979dfbe8321SBarry Smith PetscErrorCode ierr; 980d0f46423SBarry Smith PetscInt m = A->rmap->n; 9815c897100SBarry Smith #if !defined(PETSC_USE_FORTRAN_KERNEL_MULTTRANSPOSEAIJ) 982a77337e4SBarry Smith MatScalar *v; 983a77337e4SBarry Smith PetscScalar alpha; 98404fbf559SBarry Smith PetscInt n,i,j,*idx,*ii,*ridx=PETSC_NULL; 9853447b6efSHong Zhang Mat_CompressedRow cprow = a->compressedrow; 986ace3abfcSBarry Smith PetscBool usecprow = cprow.use; 9875c897100SBarry Smith #endif 98817ab2063SBarry Smith 9893a40ed3dSBarry Smith PetscFunctionBegin; 9902e8a6d31SBarry Smith if (zz != yy) {ierr = VecCopy(zz,yy);CHKERRQ(ierr);} 9911ebc52fbSHong Zhang ierr = VecGetArray(xx,&x);CHKERRQ(ierr); 9921ebc52fbSHong Zhang ierr = VecGetArray(yy,&y);CHKERRQ(ierr); 9935c897100SBarry Smith 9945c897100SBarry Smith #if defined(PETSC_USE_FORTRAN_KERNEL_MULTTRANSPOSEAIJ) 995bfeeae90SHong Zhang fortranmulttransposeaddaij_(&m,x,a->i,a->j,a->a,y); 9965c897100SBarry Smith #else 9973447b6efSHong Zhang if (usecprow){ 9983447b6efSHong Zhang m = cprow.nrows; 9993447b6efSHong Zhang ii = cprow.i; 10007b2bb3b9SHong Zhang ridx = cprow.rindex; 10013447b6efSHong Zhang } else { 10023447b6efSHong Zhang ii = a->i; 10033447b6efSHong Zhang } 100417ab2063SBarry Smith for (i=0; i<m; i++) { 10053447b6efSHong Zhang idx = a->j + ii[i] ; 10063447b6efSHong Zhang v = a->a + ii[i] ; 10073447b6efSHong Zhang n = ii[i+1] - ii[i]; 10083447b6efSHong Zhang if (usecprow){ 10097b2bb3b9SHong Zhang alpha = x[ridx[i]]; 10103447b6efSHong Zhang } else { 101117ab2063SBarry Smith alpha = x[i]; 10123447b6efSHong Zhang } 101304fbf559SBarry Smith for (j=0; j<n; j++) y[idx[j]] += alpha*v[j]; 101417ab2063SBarry Smith } 10155c897100SBarry Smith #endif 1016dc0b31edSSatish Balay ierr = PetscLogFlops(2.0*a->nz);CHKERRQ(ierr); 10171ebc52fbSHong Zhang ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr); 10181ebc52fbSHong Zhang ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr); 10193a40ed3dSBarry Smith PetscFunctionReturn(0); 102017ab2063SBarry Smith } 102117ab2063SBarry Smith 10224a2ae208SSatish Balay #undef __FUNCT__ 10235c897100SBarry Smith #define __FUNCT__ "MatMultTranspose_SeqAIJ" 1024dfbe8321SBarry Smith PetscErrorCode MatMultTranspose_SeqAIJ(Mat A,Vec xx,Vec yy) 10255c897100SBarry Smith { 1026dfbe8321SBarry Smith PetscErrorCode ierr; 10275c897100SBarry Smith 10285c897100SBarry Smith PetscFunctionBegin; 1029170fe5c8SBarry Smith ierr = VecSet(yy,0.0);CHKERRQ(ierr); 10305c897100SBarry Smith ierr = MatMultTransposeAdd_SeqAIJ(A,xx,yy,yy);CHKERRQ(ierr); 10315c897100SBarry Smith PetscFunctionReturn(0); 10325c897100SBarry Smith } 10335c897100SBarry Smith 1034a4005a5dSBarry Smith #include "../src/mat/impls/aij/seq/ftn-kernels/fmult.h" 10355c897100SBarry Smith #undef __FUNCT__ 10364a2ae208SSatish Balay #define __FUNCT__ "MatMult_SeqAIJ" 1037dfbe8321SBarry Smith PetscErrorCode MatMult_SeqAIJ(Mat A,Vec xx,Vec yy) 103817ab2063SBarry Smith { 1039416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 1040d9fead3dSBarry Smith PetscScalar *y; 104154f21887SBarry Smith const PetscScalar *x; 104254f21887SBarry Smith const MatScalar *aa; 1043dfbe8321SBarry Smith PetscErrorCode ierr; 1044003131ecSBarry Smith PetscInt m=A->rmap->n; 1045003131ecSBarry Smith const PetscInt *aj,*ii,*ridx=PETSC_NULL; 10468aee2decSHong Zhang PetscInt n,i,nonzerorow=0; 1047362ced78SSatish Balay PetscScalar sum; 1048ace3abfcSBarry Smith PetscBool usecprow=a->compressedrow.use; 104917ab2063SBarry Smith 1050b6410449SSatish Balay #if defined(PETSC_HAVE_PRAGMA_DISJOINT) 105197952fefSHong Zhang #pragma disjoint(*x,*y,*aa) 1052fee21e36SBarry Smith #endif 1053fee21e36SBarry Smith 10543a40ed3dSBarry Smith PetscFunctionBegin; 10553649974fSBarry Smith ierr = VecGetArrayRead(xx,&x);CHKERRQ(ierr); 10561ebc52fbSHong Zhang ierr = VecGetArray(yy,&y);CHKERRQ(ierr); 105797952fefSHong Zhang aj = a->j; 105897952fefSHong Zhang aa = a->a; 1059416022c9SBarry Smith ii = a->i; 10604eb6d288SHong Zhang if (usecprow){ /* use compressed row format */ 106197952fefSHong Zhang m = a->compressedrow.nrows; 106297952fefSHong Zhang ii = a->compressedrow.i; 106397952fefSHong Zhang ridx = a->compressedrow.rindex; 106497952fefSHong Zhang for (i=0; i<m; i++){ 106597952fefSHong Zhang n = ii[i+1] - ii[i]; 106697952fefSHong Zhang aj = a->j + ii[i]; 106797952fefSHong Zhang aa = a->a + ii[i]; 106897952fefSHong Zhang sum = 0.0; 1069a46b3154SVictor Eijkhout nonzerorow += (n>0); 1070003131ecSBarry Smith PetscSparseDensePlusDot(sum,x,aa,aj,n); 1071003131ecSBarry Smith /* for (j=0; j<n; j++) sum += (*aa++)*x[*aj++]; */ 107297952fefSHong Zhang y[*ridx++] = sum; 107397952fefSHong Zhang } 107497952fefSHong Zhang } else { /* do not use compressed row format */ 1075b05257ddSBarry Smith #if defined(PETSC_USE_FORTRAN_KERNEL_MULTAIJ) 1076b05257ddSBarry Smith fortranmultaij_(&m,x,ii,aj,aa,y); 1077b05257ddSBarry Smith #else 107817ab2063SBarry Smith for (i=0; i<m; i++) { 1079003131ecSBarry Smith n = ii[i+1] - ii[i]; 1080003131ecSBarry Smith aj = a->j + ii[i]; 1081003131ecSBarry Smith aa = a->a + ii[i]; 108217ab2063SBarry Smith sum = 0.0; 1083a46b3154SVictor Eijkhout nonzerorow += (n>0); 1084003131ecSBarry Smith PetscSparseDensePlusDot(sum,x,aa,aj,n); 108517ab2063SBarry Smith y[i] = sum; 108617ab2063SBarry Smith } 10878d195f9aSBarry Smith #endif 1088b05257ddSBarry Smith } 1089dc0b31edSSatish Balay ierr = PetscLogFlops(2.0*a->nz - nonzerorow);CHKERRQ(ierr); 10903649974fSBarry Smith ierr = VecRestoreArrayRead(xx,&x);CHKERRQ(ierr); 10911ebc52fbSHong Zhang ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr); 10923a40ed3dSBarry Smith PetscFunctionReturn(0); 109317ab2063SBarry Smith } 109417ab2063SBarry Smith 1095a4005a5dSBarry Smith #include "../src/mat/impls/aij/seq/ftn-kernels/fmultadd.h" 10964a2ae208SSatish Balay #undef __FUNCT__ 10974a2ae208SSatish Balay #define __FUNCT__ "MatMultAdd_SeqAIJ" 1098dfbe8321SBarry Smith PetscErrorCode MatMultAdd_SeqAIJ(Mat A,Vec xx,Vec yy,Vec zz) 109917ab2063SBarry Smith { 1100416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 110154f21887SBarry Smith PetscScalar *x,*y,*z; 110254f21887SBarry Smith const MatScalar *aa; 1103dfbe8321SBarry Smith PetscErrorCode ierr; 1104d0f46423SBarry Smith PetscInt m = A->rmap->n,*aj,*ii; 1105aa482453SBarry Smith #if !defined(PETSC_USE_FORTRAN_KERNEL_MULTADDAIJ) 110697952fefSHong Zhang PetscInt n,i,jrow,j,*ridx=PETSC_NULL; 1107362ced78SSatish Balay PetscScalar sum; 1108ace3abfcSBarry Smith PetscBool usecprow=a->compressedrow.use; 1109e36a17ebSSatish Balay #endif 11109ea0dfa2SSatish Balay 11113a40ed3dSBarry Smith PetscFunctionBegin; 11121ebc52fbSHong Zhang ierr = VecGetArray(xx,&x);CHKERRQ(ierr); 11131ebc52fbSHong Zhang ierr = VecGetArray(yy,&y);CHKERRQ(ierr); 11142e8a6d31SBarry Smith if (zz != yy) { 11151ebc52fbSHong Zhang ierr = VecGetArray(zz,&z);CHKERRQ(ierr); 11162e8a6d31SBarry Smith } else { 11172e8a6d31SBarry Smith z = y; 11182e8a6d31SBarry Smith } 1119bfeeae90SHong Zhang 112097952fefSHong Zhang aj = a->j; 112197952fefSHong Zhang aa = a->a; 1122cddf8d76SBarry Smith ii = a->i; 1123aa482453SBarry Smith #if defined(PETSC_USE_FORTRAN_KERNEL_MULTADDAIJ) 112497952fefSHong Zhang fortranmultaddaij_(&m,x,ii,aj,aa,y,z); 112502ab625aSSatish Balay #else 11264eb6d288SHong Zhang if (usecprow){ /* use compressed row format */ 11274eb6d288SHong Zhang if (zz != yy){ 11284eb6d288SHong Zhang ierr = PetscMemcpy(z,y,m*sizeof(PetscScalar));CHKERRQ(ierr); 11294eb6d288SHong Zhang } 113097952fefSHong Zhang m = a->compressedrow.nrows; 113197952fefSHong Zhang ii = a->compressedrow.i; 113297952fefSHong Zhang ridx = a->compressedrow.rindex; 113397952fefSHong Zhang for (i=0; i<m; i++){ 113497952fefSHong Zhang n = ii[i+1] - ii[i]; 113597952fefSHong Zhang aj = a->j + ii[i]; 113697952fefSHong Zhang aa = a->a + ii[i]; 113797952fefSHong Zhang sum = y[*ridx]; 113897952fefSHong Zhang for (j=0; j<n; j++) sum += (*aa++)*x[*aj++]; 113997952fefSHong Zhang z[*ridx++] = sum; 114097952fefSHong Zhang } 114197952fefSHong Zhang } else { /* do not use compressed row format */ 114217ab2063SBarry Smith for (i=0; i<m; i++) { 11439ea0dfa2SSatish Balay jrow = ii[i]; 11449ea0dfa2SSatish Balay n = ii[i+1] - jrow; 114517ab2063SBarry Smith sum = y[i]; 11469ea0dfa2SSatish Balay for (j=0; j<n; j++) { 114797952fefSHong Zhang sum += aa[jrow]*x[aj[jrow]]; jrow++; 11489ea0dfa2SSatish Balay } 114917ab2063SBarry Smith z[i] = sum; 115017ab2063SBarry Smith } 115197952fefSHong Zhang } 115202ab625aSSatish Balay #endif 1153dc0b31edSSatish Balay ierr = PetscLogFlops(2.0*a->nz);CHKERRQ(ierr); 11541ebc52fbSHong Zhang ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr); 11551ebc52fbSHong Zhang ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr); 11562e8a6d31SBarry Smith if (zz != yy) { 11571ebc52fbSHong Zhang ierr = VecRestoreArray(zz,&z);CHKERRQ(ierr); 11582e8a6d31SBarry Smith } 1159918e98c3SVictor Minden #if defined(PETSC_HAVE_CUDA) 11606b375ea7SVictor Minden /* 1161918e98c3SVictor Minden ierr = VecView(xx,0);CHKERRQ(ierr); 1162918e98c3SVictor Minden ierr = VecView(zz,0);CHKERRQ(ierr); 1163918e98c3SVictor Minden ierr = MatView(A,0);CHKERRQ(ierr); 11646b375ea7SVictor Minden */ 1165918e98c3SVictor Minden #endif 11663a40ed3dSBarry Smith PetscFunctionReturn(0); 116717ab2063SBarry Smith } 116817ab2063SBarry Smith 116917ab2063SBarry Smith /* 117017ab2063SBarry Smith Adds diagonal pointers to sparse matrix structure. 117117ab2063SBarry Smith */ 11724a2ae208SSatish Balay #undef __FUNCT__ 11734a2ae208SSatish Balay #define __FUNCT__ "MatMarkDiagonal_SeqAIJ" 1174dfbe8321SBarry Smith PetscErrorCode MatMarkDiagonal_SeqAIJ(Mat A) 117517ab2063SBarry Smith { 1176416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 11776849ba73SBarry Smith PetscErrorCode ierr; 1178d0f46423SBarry Smith PetscInt i,j,m = A->rmap->n; 117917ab2063SBarry Smith 11803a40ed3dSBarry Smith PetscFunctionBegin; 118109f38230SBarry Smith if (!a->diag) { 118209f38230SBarry Smith ierr = PetscMalloc(m*sizeof(PetscInt),&a->diag);CHKERRQ(ierr); 11839518dbb4SMatthew Knepley ierr = PetscLogObjectMemory(A, m*sizeof(PetscInt));CHKERRQ(ierr); 118409f38230SBarry Smith } 1185d0f46423SBarry Smith for (i=0; i<A->rmap->n; i++) { 118609f38230SBarry Smith a->diag[i] = a->i[i+1]; 1187bfeeae90SHong Zhang for (j=a->i[i]; j<a->i[i+1]; j++) { 1188bfeeae90SHong Zhang if (a->j[j] == i) { 118909f38230SBarry Smith a->diag[i] = j; 119017ab2063SBarry Smith break; 119117ab2063SBarry Smith } 119217ab2063SBarry Smith } 119317ab2063SBarry Smith } 11943a40ed3dSBarry Smith PetscFunctionReturn(0); 119517ab2063SBarry Smith } 119617ab2063SBarry Smith 1197be5855fcSBarry Smith /* 1198be5855fcSBarry Smith Checks for missing diagonals 1199be5855fcSBarry Smith */ 12004a2ae208SSatish Balay #undef __FUNCT__ 12014a2ae208SSatish Balay #define __FUNCT__ "MatMissingDiagonal_SeqAIJ" 1202ace3abfcSBarry Smith PetscErrorCode MatMissingDiagonal_SeqAIJ(Mat A,PetscBool *missing,PetscInt *d) 1203be5855fcSBarry Smith { 1204be5855fcSBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 120597f1f81fSBarry Smith PetscInt *diag,*jj = a->j,i; 1206be5855fcSBarry Smith 1207be5855fcSBarry Smith PetscFunctionBegin; 120809f38230SBarry Smith *missing = PETSC_FALSE; 1209d0f46423SBarry Smith if (A->rmap->n > 0 && !jj) { 121009f38230SBarry Smith *missing = PETSC_TRUE; 121109f38230SBarry Smith if (d) *d = 0; 121209f38230SBarry Smith PetscInfo(A,"Matrix has no entries therefor is missing diagonal"); 121309f38230SBarry Smith } else { 1214f1e2ffcdSBarry Smith diag = a->diag; 1215d0f46423SBarry Smith for (i=0; i<A->rmap->n; i++) { 1216bfeeae90SHong Zhang if (jj[diag[i]] != i) { 121709f38230SBarry Smith *missing = PETSC_TRUE; 121809f38230SBarry Smith if (d) *d = i; 121909f38230SBarry Smith PetscInfo1(A,"Matrix is missing diagonal number %D",i); 122009f38230SBarry Smith } 1221be5855fcSBarry Smith } 1222be5855fcSBarry Smith } 1223be5855fcSBarry Smith PetscFunctionReturn(0); 1224be5855fcSBarry Smith } 1225be5855fcSBarry Smith 122671f1c65dSBarry Smith EXTERN_C_BEGIN 122771f1c65dSBarry Smith #undef __FUNCT__ 122871f1c65dSBarry Smith #define __FUNCT__ "MatInvertDiagonal_SeqAIJ" 12297087cfbeSBarry Smith PetscErrorCode MatInvertDiagonal_SeqAIJ(Mat A,PetscScalar omega,PetscScalar fshift) 123071f1c65dSBarry Smith { 123171f1c65dSBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*) A->data; 123271f1c65dSBarry Smith PetscErrorCode ierr; 1233d0f46423SBarry Smith PetscInt i,*diag,m = A->rmap->n; 123454f21887SBarry Smith MatScalar *v = a->a; 123554f21887SBarry Smith PetscScalar *idiag,*mdiag; 123671f1c65dSBarry Smith 123771f1c65dSBarry Smith PetscFunctionBegin; 123871f1c65dSBarry Smith if (a->idiagvalid) PetscFunctionReturn(0); 123971f1c65dSBarry Smith ierr = MatMarkDiagonal_SeqAIJ(A);CHKERRQ(ierr); 124071f1c65dSBarry Smith diag = a->diag; 124171f1c65dSBarry Smith if (!a->idiag) { 124271f1c65dSBarry Smith ierr = PetscMalloc3(m,PetscScalar,&a->idiag,m,PetscScalar,&a->mdiag,m,PetscScalar,&a->ssor_work);CHKERRQ(ierr); 124371f1c65dSBarry Smith ierr = PetscLogObjectMemory(A, 3*m*sizeof(PetscScalar));CHKERRQ(ierr); 124471f1c65dSBarry Smith v = a->a; 124571f1c65dSBarry Smith } 124671f1c65dSBarry Smith mdiag = a->mdiag; 124771f1c65dSBarry Smith idiag = a->idiag; 124871f1c65dSBarry Smith 1249028cd4eaSSatish Balay if (omega == 1.0 && !PetscAbsScalar(fshift)) { 125071f1c65dSBarry Smith for (i=0; i<m; i++) { 125171f1c65dSBarry Smith mdiag[i] = v[diag[i]]; 1252e32f2f54SBarry Smith if (!PetscAbsScalar(mdiag[i])) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_INCOMP,"Zero diagonal on row %D",i); 125371f1c65dSBarry Smith idiag[i] = 1.0/v[diag[i]]; 125471f1c65dSBarry Smith } 125571f1c65dSBarry Smith ierr = PetscLogFlops(m);CHKERRQ(ierr); 125671f1c65dSBarry Smith } else { 125771f1c65dSBarry Smith for (i=0; i<m; i++) { 125871f1c65dSBarry Smith mdiag[i] = v[diag[i]]; 125971f1c65dSBarry Smith idiag[i] = omega/(fshift + v[diag[i]]); 126071f1c65dSBarry Smith } 1261dc0b31edSSatish Balay ierr = PetscLogFlops(2.0*m);CHKERRQ(ierr); 126271f1c65dSBarry Smith } 126371f1c65dSBarry Smith a->idiagvalid = PETSC_TRUE; 126471f1c65dSBarry Smith PetscFunctionReturn(0); 126571f1c65dSBarry Smith } 12665a9745a3SMatthew Knepley EXTERN_C_END 126771f1c65dSBarry Smith 1268a4005a5dSBarry Smith #include "../src/mat/impls/aij/seq/ftn-kernels/frelax.h" 12694a2ae208SSatish Balay #undef __FUNCT__ 127041f059aeSBarry Smith #define __FUNCT__ "MatSOR_SeqAIJ" 127141f059aeSBarry Smith PetscErrorCode MatSOR_SeqAIJ(Mat A,Vec bb,PetscReal omega,MatSORType flag,PetscReal fshift,PetscInt its,PetscInt lits,Vec xx) 127217ab2063SBarry Smith { 1273416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 1274e6d1f457SBarry Smith PetscScalar *x,d,sum,*t,scale; 1275e6d1f457SBarry Smith const MatScalar *v = a->a,*idiag=0,*mdiag; 127654f21887SBarry Smith const PetscScalar *b, *bs,*xb, *ts; 1277dfbe8321SBarry Smith PetscErrorCode ierr; 1278d0f46423SBarry Smith PetscInt n = A->cmap->n,m = A->rmap->n,i; 127997f1f81fSBarry Smith const PetscInt *idx,*diag; 128017ab2063SBarry Smith 12813a40ed3dSBarry Smith PetscFunctionBegin; 1282b965ef7fSBarry Smith its = its*lits; 128391723122SBarry Smith 128471f1c65dSBarry Smith if (fshift != a->fshift || omega != a->omega) a->idiagvalid = PETSC_FALSE; /* must recompute idiag[] */ 128571f1c65dSBarry Smith if (!a->idiagvalid) {ierr = MatInvertDiagonal_SeqAIJ(A,omega,fshift);CHKERRQ(ierr);} 128671f1c65dSBarry Smith a->fshift = fshift; 128771f1c65dSBarry Smith a->omega = omega; 1288ed480e8bSBarry Smith 128971f1c65dSBarry Smith diag = a->diag; 129071f1c65dSBarry Smith t = a->ssor_work; 1291ed480e8bSBarry Smith idiag = a->idiag; 129271f1c65dSBarry Smith mdiag = a->mdiag; 1293ed480e8bSBarry Smith 12941ebc52fbSHong Zhang ierr = VecGetArray(xx,&x);CHKERRQ(ierr); 12953649974fSBarry Smith ierr = VecGetArrayRead(bb,&b);CHKERRQ(ierr); 129671f1c65dSBarry Smith CHKMEMQ; 1297ed480e8bSBarry Smith /* We count flops by assuming the upper triangular and lower triangular parts have the same number of nonzeros */ 129817ab2063SBarry Smith if (flag == SOR_APPLY_UPPER) { 129917ab2063SBarry Smith /* apply (U + D/omega) to the vector */ 1300ed480e8bSBarry Smith bs = b; 130117ab2063SBarry Smith for (i=0; i<m; i++) { 130271f1c65dSBarry Smith d = fshift + mdiag[i]; 1303416022c9SBarry Smith n = a->i[i+1] - diag[i] - 1; 1304ed480e8bSBarry Smith idx = a->j + diag[i] + 1; 1305ed480e8bSBarry Smith v = a->a + diag[i] + 1; 130617ab2063SBarry Smith sum = b[i]*d/omega; 1307003131ecSBarry Smith PetscSparseDensePlusDot(sum,bs,v,idx,n); 130817ab2063SBarry Smith x[i] = sum; 130917ab2063SBarry Smith } 13101ebc52fbSHong Zhang ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr); 13113649974fSBarry Smith ierr = VecRestoreArrayRead(bb,&b);CHKERRQ(ierr); 1312efee365bSSatish Balay ierr = PetscLogFlops(a->nz);CHKERRQ(ierr); 13133a40ed3dSBarry Smith PetscFunctionReturn(0); 131417ab2063SBarry Smith } 1315c783ea89SBarry Smith 131648af12d7SBarry Smith if (flag == SOR_APPLY_LOWER) { 1317e32f2f54SBarry Smith SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"SOR_APPLY_LOWER is not implemented"); 13183a40ed3dSBarry Smith } else if (flag & SOR_EISENSTAT) { 131917ab2063SBarry Smith /* Let A = L + U + D; where L is lower trianglar, 1320887ee2caSBarry Smith U is upper triangular, E = D/omega; This routine applies 132117ab2063SBarry Smith 132217ab2063SBarry Smith (L + E)^{-1} A (U + E)^{-1} 132317ab2063SBarry Smith 1324887ee2caSBarry Smith to a vector efficiently using Eisenstat's trick. 132517ab2063SBarry Smith */ 132617ab2063SBarry Smith scale = (2.0/omega) - 1.0; 132717ab2063SBarry Smith 132817ab2063SBarry Smith /* x = (E + U)^{-1} b */ 132917ab2063SBarry Smith for (i=m-1; i>=0; i--) { 1330416022c9SBarry Smith n = a->i[i+1] - diag[i] - 1; 1331ed480e8bSBarry Smith idx = a->j + diag[i] + 1; 1332ed480e8bSBarry Smith v = a->a + diag[i] + 1; 133317ab2063SBarry Smith sum = b[i]; 1334e6d1f457SBarry Smith PetscSparseDenseMinusDot(sum,x,v,idx,n); 1335ed480e8bSBarry Smith x[i] = sum*idiag[i]; 133617ab2063SBarry Smith } 133717ab2063SBarry Smith 133817ab2063SBarry Smith /* t = b - (2*E - D)x */ 1339416022c9SBarry Smith v = a->a; 1340ed480e8bSBarry Smith for (i=0; i<m; i++) { t[i] = b[i] - scale*(v[*diag++])*x[i]; } 134117ab2063SBarry Smith 134217ab2063SBarry Smith /* t = (E + L)^{-1}t */ 1343ed480e8bSBarry Smith ts = t; 1344416022c9SBarry Smith diag = a->diag; 134517ab2063SBarry Smith for (i=0; i<m; i++) { 1346416022c9SBarry Smith n = diag[i] - a->i[i]; 1347ed480e8bSBarry Smith idx = a->j + a->i[i]; 1348ed480e8bSBarry Smith v = a->a + a->i[i]; 134917ab2063SBarry Smith sum = t[i]; 1350003131ecSBarry Smith PetscSparseDenseMinusDot(sum,ts,v,idx,n); 1351ed480e8bSBarry Smith t[i] = sum*idiag[i]; 1352733d66baSBarry Smith /* x = x + t */ 1353733d66baSBarry Smith x[i] += t[i]; 135417ab2063SBarry Smith } 135517ab2063SBarry Smith 1356dc0b31edSSatish Balay ierr = PetscLogFlops(6.0*m-1 + 2.0*a->nz);CHKERRQ(ierr); 13571ebc52fbSHong Zhang ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr); 13583649974fSBarry Smith ierr = VecRestoreArrayRead(bb,&b);CHKERRQ(ierr); 13593a40ed3dSBarry Smith PetscFunctionReturn(0); 136017ab2063SBarry Smith } 136117ab2063SBarry Smith if (flag & SOR_ZERO_INITIAL_GUESS) { 136217ab2063SBarry Smith if (flag & SOR_FORWARD_SWEEP || flag & SOR_LOCAL_FORWARD_SWEEP){ 136317ab2063SBarry Smith for (i=0; i<m; i++) { 1364416022c9SBarry Smith n = diag[i] - a->i[i]; 1365ed480e8bSBarry Smith idx = a->j + a->i[i]; 1366ed480e8bSBarry Smith v = a->a + a->i[i]; 136717ab2063SBarry Smith sum = b[i]; 1368e6d1f457SBarry Smith PetscSparseDenseMinusDot(sum,x,v,idx,n); 13695c99c7daSBarry Smith t[i] = sum; 1370ed480e8bSBarry Smith x[i] = sum*idiag[i]; 137117ab2063SBarry Smith } 13725c99c7daSBarry Smith xb = t; 1373efee365bSSatish Balay ierr = PetscLogFlops(a->nz);CHKERRQ(ierr); 13743a40ed3dSBarry Smith } else xb = b; 137517ab2063SBarry Smith if (flag & SOR_BACKWARD_SWEEP || flag & SOR_LOCAL_BACKWARD_SWEEP){ 137617ab2063SBarry Smith for (i=m-1; i>=0; i--) { 1377416022c9SBarry Smith n = a->i[i+1] - diag[i] - 1; 1378ed480e8bSBarry Smith idx = a->j + diag[i] + 1; 1379ed480e8bSBarry Smith v = a->a + diag[i] + 1; 138017ab2063SBarry Smith sum = xb[i]; 1381e6d1f457SBarry Smith PetscSparseDenseMinusDot(sum,x,v,idx,n); 13825c99c7daSBarry Smith if (xb == b) { 1383ed480e8bSBarry Smith x[i] = sum*idiag[i]; 13845c99c7daSBarry Smith } else { 13855c99c7daSBarry Smith x[i] = (1-omega)*x[i] + sum*idiag[i]; 138617ab2063SBarry Smith } 13875c99c7daSBarry Smith } 1388efee365bSSatish Balay ierr = PetscLogFlops(a->nz);CHKERRQ(ierr); 138917ab2063SBarry Smith } 139017ab2063SBarry Smith its--; 139117ab2063SBarry Smith } 139217ab2063SBarry Smith while (its--) { 139317ab2063SBarry Smith if (flag & SOR_FORWARD_SWEEP || flag & SOR_LOCAL_FORWARD_SWEEP){ 139417ab2063SBarry Smith for (i=0; i<m; i++) { 1395416022c9SBarry Smith n = a->i[i+1] - a->i[i]; 1396ed480e8bSBarry Smith idx = a->j + a->i[i]; 1397ed480e8bSBarry Smith v = a->a + a->i[i]; 139817ab2063SBarry Smith sum = b[i]; 1399e6d1f457SBarry Smith PetscSparseDenseMinusDot(sum,x,v,idx,n); 1400ed480e8bSBarry Smith x[i] = (1. - omega)*x[i] + (sum + mdiag[i]*x[i])*idiag[i]; 140117ab2063SBarry Smith } 14029f863219SBarry Smith ierr = PetscLogFlops(2.0*a->nz);CHKERRQ(ierr); 140317ab2063SBarry Smith } 140417ab2063SBarry Smith if (flag & SOR_BACKWARD_SWEEP || flag & SOR_LOCAL_BACKWARD_SWEEP){ 140517ab2063SBarry Smith for (i=m-1; i>=0; i--) { 1406416022c9SBarry Smith n = a->i[i+1] - a->i[i]; 1407ed480e8bSBarry Smith idx = a->j + a->i[i]; 1408ed480e8bSBarry Smith v = a->a + a->i[i]; 140917ab2063SBarry Smith sum = b[i]; 1410e6d1f457SBarry Smith PetscSparseDenseMinusDot(sum,x,v,idx,n); 1411ed480e8bSBarry Smith x[i] = (1. - omega)*x[i] + (sum + mdiag[i]*x[i])*idiag[i]; 141217ab2063SBarry Smith } 14139f863219SBarry Smith ierr = PetscLogFlops(2.0*a->nz);CHKERRQ(ierr); 141417ab2063SBarry Smith } 141517ab2063SBarry Smith } 14161ebc52fbSHong Zhang ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr); 14173649974fSBarry Smith ierr = VecRestoreArrayRead(bb,&b);CHKERRQ(ierr); 141871f1c65dSBarry Smith CHKMEMQ; PetscFunctionReturn(0); 141917ab2063SBarry Smith } 142017ab2063SBarry Smith 14212af78befSBarry Smith 14224a2ae208SSatish Balay #undef __FUNCT__ 14234a2ae208SSatish Balay #define __FUNCT__ "MatGetInfo_SeqAIJ" 1424dfbe8321SBarry Smith PetscErrorCode MatGetInfo_SeqAIJ(Mat A,MatInfoType flag,MatInfo *info) 142517ab2063SBarry Smith { 1426416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 14274e220ebcSLois Curfman McInnes 14283a40ed3dSBarry Smith PetscFunctionBegin; 14294e220ebcSLois Curfman McInnes info->block_size = 1.0; 14304e220ebcSLois Curfman McInnes info->nz_allocated = (double)a->maxnz; 14314e220ebcSLois Curfman McInnes info->nz_used = (double)a->nz; 14324e220ebcSLois Curfman McInnes info->nz_unneeded = (double)(a->maxnz - a->nz); 14334e220ebcSLois Curfman McInnes info->assemblies = (double)A->num_ass; 14348e58a170SBarry Smith info->mallocs = (double)A->info.mallocs; 14357adad957SLisandro Dalcin info->memory = ((PetscObject)A)->mem; 1436d5f3da31SBarry Smith if (A->factortype) { 14374e220ebcSLois Curfman McInnes info->fill_ratio_given = A->info.fill_ratio_given; 14384e220ebcSLois Curfman McInnes info->fill_ratio_needed = A->info.fill_ratio_needed; 14394e220ebcSLois Curfman McInnes info->factor_mallocs = A->info.factor_mallocs; 14404e220ebcSLois Curfman McInnes } else { 14414e220ebcSLois Curfman McInnes info->fill_ratio_given = 0; 14424e220ebcSLois Curfman McInnes info->fill_ratio_needed = 0; 14434e220ebcSLois Curfman McInnes info->factor_mallocs = 0; 14444e220ebcSLois Curfman McInnes } 14453a40ed3dSBarry Smith PetscFunctionReturn(0); 144617ab2063SBarry Smith } 144717ab2063SBarry Smith 14484a2ae208SSatish Balay #undef __FUNCT__ 14494a2ae208SSatish Balay #define __FUNCT__ "MatZeroRows_SeqAIJ" 14502b40b63fSBarry Smith PetscErrorCode MatZeroRows_SeqAIJ(Mat A,PetscInt N,const PetscInt rows[],PetscScalar diag,Vec x,Vec b) 145117ab2063SBarry Smith { 1452416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 14533b98c0a2SBarry Smith PetscInt i,m = A->rmap->n - 1,d = 0; 14546849ba73SBarry Smith PetscErrorCode ierr; 145597b48c8fSBarry Smith const PetscScalar *xx; 145697b48c8fSBarry Smith PetscScalar *bb; 1457ace3abfcSBarry Smith PetscBool missing; 145817ab2063SBarry Smith 14593a40ed3dSBarry Smith PetscFunctionBegin; 146097b48c8fSBarry Smith if (x && b) { 146197b48c8fSBarry Smith ierr = VecGetArrayRead(x,&xx);CHKERRQ(ierr); 146297b48c8fSBarry Smith ierr = VecGetArray(b,&bb);CHKERRQ(ierr); 146397b48c8fSBarry Smith for (i=0; i<N; i++) { 146497b48c8fSBarry Smith if (rows[i] < 0 || rows[i] > m) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"row %D out of range", rows[i]); 146597b48c8fSBarry Smith bb[rows[i]] = diag*xx[rows[i]]; 146697b48c8fSBarry Smith } 146797b48c8fSBarry Smith ierr = VecRestoreArrayRead(x,&xx);CHKERRQ(ierr); 146897b48c8fSBarry Smith ierr = VecRestoreArray(b,&bb);CHKERRQ(ierr); 146997b48c8fSBarry Smith } 147097b48c8fSBarry Smith 1471a9817697SBarry Smith if (a->keepnonzeropattern) { 1472f1e2ffcdSBarry Smith for (i=0; i<N; i++) { 1473e32f2f54SBarry Smith if (rows[i] < 0 || rows[i] > m) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"row %D out of range", rows[i]); 1474bfeeae90SHong Zhang ierr = PetscMemzero(&a->a[a->i[rows[i]]],a->ilen[rows[i]]*sizeof(PetscScalar));CHKERRQ(ierr); 1475f1e2ffcdSBarry Smith } 1476f4df32b1SMatthew Knepley if (diag != 0.0) { 147709f38230SBarry Smith ierr = MatMissingDiagonal_SeqAIJ(A,&missing,&d);CHKERRQ(ierr); 1478e32f2f54SBarry Smith if (missing) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Matrix is missing diagonal entry in row %D",d); 1479f1e2ffcdSBarry Smith for (i=0; i<N; i++) { 1480f4df32b1SMatthew Knepley a->a[a->diag[rows[i]]] = diag; 1481f1e2ffcdSBarry Smith } 1482f1e2ffcdSBarry Smith } 148388e51ccdSHong Zhang A->same_nonzero = PETSC_TRUE; 1484f1e2ffcdSBarry Smith } else { 1485f4df32b1SMatthew Knepley if (diag != 0.0) { 148617ab2063SBarry Smith for (i=0; i<N; i++) { 1487e32f2f54SBarry Smith if (rows[i] < 0 || rows[i] > m) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"row %D out of range", rows[i]); 14887ae801bdSBarry Smith if (a->ilen[rows[i]] > 0) { 1489416022c9SBarry Smith a->ilen[rows[i]] = 1; 1490f4df32b1SMatthew Knepley a->a[a->i[rows[i]]] = diag; 1491bfeeae90SHong Zhang a->j[a->i[rows[i]]] = rows[i]; 14927ae801bdSBarry Smith } else { /* in case row was completely empty */ 1493f4df32b1SMatthew Knepley ierr = MatSetValues_SeqAIJ(A,1,&rows[i],1,&rows[i],&diag,INSERT_VALUES);CHKERRQ(ierr); 149417ab2063SBarry Smith } 149517ab2063SBarry Smith } 14963a40ed3dSBarry Smith } else { 149717ab2063SBarry Smith for (i=0; i<N; i++) { 1498e32f2f54SBarry Smith if (rows[i] < 0 || rows[i] > m) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"row %D out of range", rows[i]); 1499416022c9SBarry Smith a->ilen[rows[i]] = 0; 150017ab2063SBarry Smith } 150117ab2063SBarry Smith } 150288e51ccdSHong Zhang A->same_nonzero = PETSC_FALSE; 1503f1e2ffcdSBarry Smith } 150443a90d84SBarry Smith ierr = MatAssemblyEnd_SeqAIJ(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 15053a40ed3dSBarry Smith PetscFunctionReturn(0); 150617ab2063SBarry Smith } 150717ab2063SBarry Smith 15084a2ae208SSatish Balay #undef __FUNCT__ 15096e169961SBarry Smith #define __FUNCT__ "MatZeroRowsColumns_SeqAIJ" 15106e169961SBarry Smith PetscErrorCode MatZeroRowsColumns_SeqAIJ(Mat A,PetscInt N,const PetscInt rows[],PetscScalar diag,Vec x,Vec b) 15116e169961SBarry Smith { 15126e169961SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 15136e169961SBarry Smith PetscInt i,j,m = A->rmap->n - 1,d = 0; 15146e169961SBarry Smith PetscErrorCode ierr; 15152b40b63fSBarry Smith PetscBool missing,*zeroed,vecs = PETSC_FALSE; 15166e169961SBarry Smith const PetscScalar *xx; 15176e169961SBarry Smith PetscScalar *bb; 15186e169961SBarry Smith 15196e169961SBarry Smith PetscFunctionBegin; 15206e169961SBarry Smith if (x && b) { 15216e169961SBarry Smith ierr = VecGetArrayRead(x,&xx);CHKERRQ(ierr); 15226e169961SBarry Smith ierr = VecGetArray(b,&bb);CHKERRQ(ierr); 15232b40b63fSBarry Smith vecs = PETSC_TRUE; 15246e169961SBarry Smith } 15256e169961SBarry Smith ierr = PetscMalloc(A->rmap->n*sizeof(PetscBool),&zeroed);CHKERRQ(ierr); 15266e169961SBarry Smith ierr = PetscMemzero(zeroed,A->rmap->n*sizeof(PetscBool));CHKERRQ(ierr); 15276e169961SBarry Smith for (i=0; i<N; i++) { 15286e169961SBarry Smith if (rows[i] < 0 || rows[i] > m) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"row %D out of range", rows[i]); 15296e169961SBarry Smith ierr = PetscMemzero(&a->a[a->i[rows[i]]],a->ilen[rows[i]]*sizeof(PetscScalar));CHKERRQ(ierr); 15306e169961SBarry Smith zeroed[rows[i]] = PETSC_TRUE; 15316e169961SBarry Smith } 15326e169961SBarry Smith for (i=0; i<A->rmap->n; i++) { 15336e169961SBarry Smith if (!zeroed[i]) { 15346e169961SBarry Smith for (j=a->i[i]; j<a->i[i+1]; j++) { 15356e169961SBarry Smith if (zeroed[a->j[j]]) { 15362b40b63fSBarry Smith if (vecs) bb[i] -= a->a[j]*xx[a->j[j]]; 15376e169961SBarry Smith a->a[j] = 0.0; 15386e169961SBarry Smith } 15396e169961SBarry Smith } 15402b40b63fSBarry Smith } else if (vecs) bb[i] = diag*xx[i]; 15416e169961SBarry Smith } 15426e169961SBarry Smith if (x && b) { 15436e169961SBarry Smith ierr = VecRestoreArrayRead(x,&xx);CHKERRQ(ierr); 15446e169961SBarry Smith ierr = VecRestoreArray(b,&bb);CHKERRQ(ierr); 15456e169961SBarry Smith } 15466e169961SBarry Smith ierr = PetscFree(zeroed);CHKERRQ(ierr); 15476e169961SBarry Smith if (diag != 0.0) { 15486e169961SBarry Smith ierr = MatMissingDiagonal_SeqAIJ(A,&missing,&d);CHKERRQ(ierr); 15496e169961SBarry Smith if (missing) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Matrix is missing diagonal entry in row %D",d); 15506e169961SBarry Smith for (i=0; i<N; i++) { 15516e169961SBarry Smith a->a[a->diag[rows[i]]] = diag; 15526e169961SBarry Smith } 15536e169961SBarry Smith } 15546e169961SBarry Smith A->same_nonzero = PETSC_TRUE; 15556e169961SBarry Smith ierr = MatAssemblyEnd_SeqAIJ(A,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 15566e169961SBarry Smith PetscFunctionReturn(0); 15576e169961SBarry Smith } 15586e169961SBarry Smith 15596e169961SBarry Smith #undef __FUNCT__ 15604a2ae208SSatish Balay #define __FUNCT__ "MatGetRow_SeqAIJ" 1561a77337e4SBarry Smith PetscErrorCode MatGetRow_SeqAIJ(Mat A,PetscInt row,PetscInt *nz,PetscInt **idx,PetscScalar **v) 156217ab2063SBarry Smith { 1563416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 156497f1f81fSBarry Smith PetscInt *itmp; 156517ab2063SBarry Smith 15663a40ed3dSBarry Smith PetscFunctionBegin; 1567e32f2f54SBarry Smith if (row < 0 || row >= A->rmap->n) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Row %D out of range",row); 156817ab2063SBarry Smith 1569416022c9SBarry Smith *nz = a->i[row+1] - a->i[row]; 1570bfeeae90SHong Zhang if (v) *v = a->a + a->i[row]; 157117ab2063SBarry Smith if (idx) { 1572bfeeae90SHong Zhang itmp = a->j + a->i[row]; 1573bfeeae90SHong Zhang if (*nz) { 15744e093b46SBarry Smith *idx = itmp; 157517ab2063SBarry Smith } 157617ab2063SBarry Smith else *idx = 0; 157717ab2063SBarry Smith } 15783a40ed3dSBarry Smith PetscFunctionReturn(0); 157917ab2063SBarry Smith } 158017ab2063SBarry Smith 1581bfeeae90SHong Zhang /* remove this function? */ 15824a2ae208SSatish Balay #undef __FUNCT__ 15834a2ae208SSatish Balay #define __FUNCT__ "MatRestoreRow_SeqAIJ" 1584a77337e4SBarry Smith PetscErrorCode MatRestoreRow_SeqAIJ(Mat A,PetscInt row,PetscInt *nz,PetscInt **idx,PetscScalar **v) 158517ab2063SBarry Smith { 15863a40ed3dSBarry Smith PetscFunctionBegin; 15873a40ed3dSBarry Smith PetscFunctionReturn(0); 158817ab2063SBarry Smith } 158917ab2063SBarry Smith 15904a2ae208SSatish Balay #undef __FUNCT__ 15914a2ae208SSatish Balay #define __FUNCT__ "MatNorm_SeqAIJ" 1592dfbe8321SBarry Smith PetscErrorCode MatNorm_SeqAIJ(Mat A,NormType type,PetscReal *nrm) 159317ab2063SBarry Smith { 1594416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 159554f21887SBarry Smith MatScalar *v = a->a; 159636db0b34SBarry Smith PetscReal sum = 0.0; 15976849ba73SBarry Smith PetscErrorCode ierr; 159897f1f81fSBarry Smith PetscInt i,j; 159917ab2063SBarry Smith 16003a40ed3dSBarry Smith PetscFunctionBegin; 160117ab2063SBarry Smith if (type == NORM_FROBENIUS) { 1602416022c9SBarry Smith for (i=0; i<a->nz; i++) { 1603aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX) 160436db0b34SBarry Smith sum += PetscRealPart(PetscConj(*v)*(*v)); v++; 160517ab2063SBarry Smith #else 160617ab2063SBarry Smith sum += (*v)*(*v); v++; 160717ab2063SBarry Smith #endif 160817ab2063SBarry Smith } 1609064f8208SBarry Smith *nrm = sqrt(sum); 16103a40ed3dSBarry Smith } else if (type == NORM_1) { 161136db0b34SBarry Smith PetscReal *tmp; 161297f1f81fSBarry Smith PetscInt *jj = a->j; 1613d0f46423SBarry Smith ierr = PetscMalloc((A->cmap->n+1)*sizeof(PetscReal),&tmp);CHKERRQ(ierr); 1614d0f46423SBarry Smith ierr = PetscMemzero(tmp,A->cmap->n*sizeof(PetscReal));CHKERRQ(ierr); 1615064f8208SBarry Smith *nrm = 0.0; 1616416022c9SBarry Smith for (j=0; j<a->nz; j++) { 1617bfeeae90SHong Zhang tmp[*jj++] += PetscAbsScalar(*v); v++; 161817ab2063SBarry Smith } 1619d0f46423SBarry Smith for (j=0; j<A->cmap->n; j++) { 1620064f8208SBarry Smith if (tmp[j] > *nrm) *nrm = tmp[j]; 162117ab2063SBarry Smith } 1622606d414cSSatish Balay ierr = PetscFree(tmp);CHKERRQ(ierr); 16233a40ed3dSBarry Smith } else if (type == NORM_INFINITY) { 1624064f8208SBarry Smith *nrm = 0.0; 1625d0f46423SBarry Smith for (j=0; j<A->rmap->n; j++) { 1626bfeeae90SHong Zhang v = a->a + a->i[j]; 162717ab2063SBarry Smith sum = 0.0; 1628416022c9SBarry Smith for (i=0; i<a->i[j+1]-a->i[j]; i++) { 1629cddf8d76SBarry Smith sum += PetscAbsScalar(*v); v++; 163017ab2063SBarry Smith } 1631064f8208SBarry Smith if (sum > *nrm) *nrm = sum; 163217ab2063SBarry Smith } 16333a40ed3dSBarry Smith } else { 1634e32f2f54SBarry Smith SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"No support for two norm"); 163517ab2063SBarry Smith } 16363a40ed3dSBarry Smith PetscFunctionReturn(0); 163717ab2063SBarry Smith } 163817ab2063SBarry Smith 16394a2ae208SSatish Balay #undef __FUNCT__ 16404a2ae208SSatish Balay #define __FUNCT__ "MatTranspose_SeqAIJ" 1641fc4dec0aSBarry Smith PetscErrorCode MatTranspose_SeqAIJ(Mat A,MatReuse reuse,Mat *B) 164217ab2063SBarry Smith { 1643416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 1644416022c9SBarry Smith Mat C; 16456849ba73SBarry Smith PetscErrorCode ierr; 1646d0f46423SBarry Smith PetscInt i,*aj = a->j,*ai = a->i,m = A->rmap->n,len,*col; 164754f21887SBarry Smith MatScalar *array = a->a; 164817ab2063SBarry Smith 16493a40ed3dSBarry Smith PetscFunctionBegin; 1650e32f2f54SBarry Smith if (reuse == MAT_REUSE_MATRIX && A == *B && m != A->cmap->n) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Square matrix only for in-place"); 1651fc4dec0aSBarry Smith 1652fc4dec0aSBarry Smith if (reuse == MAT_INITIAL_MATRIX || *B == A) { 1653d0f46423SBarry Smith ierr = PetscMalloc((1+A->cmap->n)*sizeof(PetscInt),&col);CHKERRQ(ierr); 1654d0f46423SBarry Smith ierr = PetscMemzero(col,(1+A->cmap->n)*sizeof(PetscInt));CHKERRQ(ierr); 1655bfeeae90SHong Zhang 1656bfeeae90SHong Zhang for (i=0; i<ai[m]; i++) col[aj[i]] += 1; 16577adad957SLisandro Dalcin ierr = MatCreate(((PetscObject)A)->comm,&C);CHKERRQ(ierr); 1658d0f46423SBarry Smith ierr = MatSetSizes(C,A->cmap->n,m,A->cmap->n,m);CHKERRQ(ierr); 16597adad957SLisandro Dalcin ierr = MatSetType(C,((PetscObject)A)->type_name);CHKERRQ(ierr); 1660ab93d7beSBarry Smith ierr = MatSeqAIJSetPreallocation_SeqAIJ(C,0,col);CHKERRQ(ierr); 1661606d414cSSatish Balay ierr = PetscFree(col);CHKERRQ(ierr); 1662a541d17aSBarry Smith } else { 1663a541d17aSBarry Smith C = *B; 1664a541d17aSBarry Smith } 1665a541d17aSBarry Smith 166617ab2063SBarry Smith for (i=0; i<m; i++) { 166717ab2063SBarry Smith len = ai[i+1]-ai[i]; 166887d4246cSBarry Smith ierr = MatSetValues_SeqAIJ(C,len,aj,1,&i,array,INSERT_VALUES);CHKERRQ(ierr); 1669b9b97703SBarry Smith array += len; 1670b9b97703SBarry Smith aj += len; 167117ab2063SBarry Smith } 16726d4a8577SBarry Smith ierr = MatAssemblyBegin(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 16736d4a8577SBarry Smith ierr = MatAssemblyEnd(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 167417ab2063SBarry Smith 1675815cbec1SBarry Smith if (reuse == MAT_INITIAL_MATRIX || *B != A) { 1676416022c9SBarry Smith *B = C; 167717ab2063SBarry Smith } else { 1678eb6b5d47SBarry Smith ierr = MatHeaderMerge(A,C);CHKERRQ(ierr); 167917ab2063SBarry Smith } 16803a40ed3dSBarry Smith PetscFunctionReturn(0); 168117ab2063SBarry Smith } 168217ab2063SBarry Smith 1683cd0d46ebSvictorle EXTERN_C_BEGIN 1684cd0d46ebSvictorle #undef __FUNCT__ 16855fbd3699SBarry Smith #define __FUNCT__ "MatIsTranspose_SeqAIJ" 16867087cfbeSBarry Smith PetscErrorCode MatIsTranspose_SeqAIJ(Mat A,Mat B,PetscReal tol,PetscBool *f) 1687cd0d46ebSvictorle { 1688cd0d46ebSvictorle Mat_SeqAIJ *aij = (Mat_SeqAIJ *) A->data,*bij = (Mat_SeqAIJ*) A->data; 168954f21887SBarry Smith PetscInt *adx,*bdx,*aii,*bii,*aptr,*bptr; 169054f21887SBarry Smith MatScalar *va,*vb; 16916849ba73SBarry Smith PetscErrorCode ierr; 169297f1f81fSBarry Smith PetscInt ma,na,mb,nb, i; 1693cd0d46ebSvictorle 1694cd0d46ebSvictorle PetscFunctionBegin; 1695cd0d46ebSvictorle bij = (Mat_SeqAIJ *) B->data; 1696cd0d46ebSvictorle 1697cd0d46ebSvictorle ierr = MatGetSize(A,&ma,&na);CHKERRQ(ierr); 1698cd0d46ebSvictorle ierr = MatGetSize(B,&mb,&nb);CHKERRQ(ierr); 16995485867bSBarry Smith if (ma!=nb || na!=mb){ 17005485867bSBarry Smith *f = PETSC_FALSE; 17015485867bSBarry Smith PetscFunctionReturn(0); 17025485867bSBarry Smith } 1703cd0d46ebSvictorle aii = aij->i; bii = bij->i; 1704cd0d46ebSvictorle adx = aij->j; bdx = bij->j; 1705cd0d46ebSvictorle va = aij->a; vb = bij->a; 170697f1f81fSBarry Smith ierr = PetscMalloc(ma*sizeof(PetscInt),&aptr);CHKERRQ(ierr); 170797f1f81fSBarry Smith ierr = PetscMalloc(mb*sizeof(PetscInt),&bptr);CHKERRQ(ierr); 1708cd0d46ebSvictorle for (i=0; i<ma; i++) aptr[i] = aii[i]; 1709cd0d46ebSvictorle for (i=0; i<mb; i++) bptr[i] = bii[i]; 1710cd0d46ebSvictorle 1711cd0d46ebSvictorle *f = PETSC_TRUE; 1712cd0d46ebSvictorle for (i=0; i<ma; i++) { 1713cd0d46ebSvictorle while (aptr[i]<aii[i+1]) { 171497f1f81fSBarry Smith PetscInt idc,idr; 17155485867bSBarry Smith PetscScalar vc,vr; 1716cd0d46ebSvictorle /* column/row index/value */ 17175485867bSBarry Smith idc = adx[aptr[i]]; 17185485867bSBarry Smith idr = bdx[bptr[idc]]; 17195485867bSBarry Smith vc = va[aptr[i]]; 17205485867bSBarry Smith vr = vb[bptr[idc]]; 17215485867bSBarry Smith if (i!=idr || PetscAbsScalar(vc-vr) > tol) { 17225485867bSBarry Smith *f = PETSC_FALSE; 17235485867bSBarry Smith goto done; 1724cd0d46ebSvictorle } else { 17255485867bSBarry Smith aptr[i]++; 17265485867bSBarry Smith if (B || i!=idc) bptr[idc]++; 1727cd0d46ebSvictorle } 1728cd0d46ebSvictorle } 1729cd0d46ebSvictorle } 1730cd0d46ebSvictorle done: 1731cd0d46ebSvictorle ierr = PetscFree(aptr);CHKERRQ(ierr); 17323aeef889SHong Zhang if (B) { 17333aeef889SHong Zhang ierr = PetscFree(bptr);CHKERRQ(ierr); 17343aeef889SHong Zhang } 1735cd0d46ebSvictorle PetscFunctionReturn(0); 1736cd0d46ebSvictorle } 1737cd0d46ebSvictorle EXTERN_C_END 1738cd0d46ebSvictorle 17391cbb95d3SBarry Smith EXTERN_C_BEGIN 17401cbb95d3SBarry Smith #undef __FUNCT__ 17411cbb95d3SBarry Smith #define __FUNCT__ "MatIsHermitianTranspose_SeqAIJ" 17427087cfbeSBarry Smith PetscErrorCode MatIsHermitianTranspose_SeqAIJ(Mat A,Mat B,PetscReal tol,PetscBool *f) 17431cbb95d3SBarry Smith { 17441cbb95d3SBarry Smith Mat_SeqAIJ *aij = (Mat_SeqAIJ *) A->data,*bij = (Mat_SeqAIJ*) A->data; 174554f21887SBarry Smith PetscInt *adx,*bdx,*aii,*bii,*aptr,*bptr; 174654f21887SBarry Smith MatScalar *va,*vb; 17471cbb95d3SBarry Smith PetscErrorCode ierr; 17481cbb95d3SBarry Smith PetscInt ma,na,mb,nb, i; 17491cbb95d3SBarry Smith 17501cbb95d3SBarry Smith PetscFunctionBegin; 17511cbb95d3SBarry Smith bij = (Mat_SeqAIJ *) B->data; 17521cbb95d3SBarry Smith 17531cbb95d3SBarry Smith ierr = MatGetSize(A,&ma,&na);CHKERRQ(ierr); 17541cbb95d3SBarry Smith ierr = MatGetSize(B,&mb,&nb);CHKERRQ(ierr); 17551cbb95d3SBarry Smith if (ma!=nb || na!=mb){ 17561cbb95d3SBarry Smith *f = PETSC_FALSE; 17571cbb95d3SBarry Smith PetscFunctionReturn(0); 17581cbb95d3SBarry Smith } 17591cbb95d3SBarry Smith aii = aij->i; bii = bij->i; 17601cbb95d3SBarry Smith adx = aij->j; bdx = bij->j; 17611cbb95d3SBarry Smith va = aij->a; vb = bij->a; 17621cbb95d3SBarry Smith ierr = PetscMalloc(ma*sizeof(PetscInt),&aptr);CHKERRQ(ierr); 17631cbb95d3SBarry Smith ierr = PetscMalloc(mb*sizeof(PetscInt),&bptr);CHKERRQ(ierr); 17641cbb95d3SBarry Smith for (i=0; i<ma; i++) aptr[i] = aii[i]; 17651cbb95d3SBarry Smith for (i=0; i<mb; i++) bptr[i] = bii[i]; 17661cbb95d3SBarry Smith 17671cbb95d3SBarry Smith *f = PETSC_TRUE; 17681cbb95d3SBarry Smith for (i=0; i<ma; i++) { 17691cbb95d3SBarry Smith while (aptr[i]<aii[i+1]) { 17701cbb95d3SBarry Smith PetscInt idc,idr; 17711cbb95d3SBarry Smith PetscScalar vc,vr; 17721cbb95d3SBarry Smith /* column/row index/value */ 17731cbb95d3SBarry Smith idc = adx[aptr[i]]; 17741cbb95d3SBarry Smith idr = bdx[bptr[idc]]; 17751cbb95d3SBarry Smith vc = va[aptr[i]]; 17761cbb95d3SBarry Smith vr = vb[bptr[idc]]; 17771cbb95d3SBarry Smith if (i!=idr || PetscAbsScalar(vc-PetscConj(vr)) > tol) { 17781cbb95d3SBarry Smith *f = PETSC_FALSE; 17791cbb95d3SBarry Smith goto done; 17801cbb95d3SBarry Smith } else { 17811cbb95d3SBarry Smith aptr[i]++; 17821cbb95d3SBarry Smith if (B || i!=idc) bptr[idc]++; 17831cbb95d3SBarry Smith } 17841cbb95d3SBarry Smith } 17851cbb95d3SBarry Smith } 17861cbb95d3SBarry Smith done: 17871cbb95d3SBarry Smith ierr = PetscFree(aptr);CHKERRQ(ierr); 17881cbb95d3SBarry Smith if (B) { 17891cbb95d3SBarry Smith ierr = PetscFree(bptr);CHKERRQ(ierr); 17901cbb95d3SBarry Smith } 17911cbb95d3SBarry Smith PetscFunctionReturn(0); 17921cbb95d3SBarry Smith } 17931cbb95d3SBarry Smith EXTERN_C_END 17941cbb95d3SBarry Smith 17959e29f15eSvictorle #undef __FUNCT__ 17969e29f15eSvictorle #define __FUNCT__ "MatIsSymmetric_SeqAIJ" 1797ace3abfcSBarry Smith PetscErrorCode MatIsSymmetric_SeqAIJ(Mat A,PetscReal tol,PetscBool *f) 17989e29f15eSvictorle { 1799dfbe8321SBarry Smith PetscErrorCode ierr; 18009e29f15eSvictorle PetscFunctionBegin; 18015485867bSBarry Smith ierr = MatIsTranspose_SeqAIJ(A,A,tol,f);CHKERRQ(ierr); 18029e29f15eSvictorle PetscFunctionReturn(0); 18039e29f15eSvictorle } 18049e29f15eSvictorle 18054a2ae208SSatish Balay #undef __FUNCT__ 18061cbb95d3SBarry Smith #define __FUNCT__ "MatIsHermitian_SeqAIJ" 1807ace3abfcSBarry Smith PetscErrorCode MatIsHermitian_SeqAIJ(Mat A,PetscReal tol,PetscBool *f) 18081cbb95d3SBarry Smith { 18091cbb95d3SBarry Smith PetscErrorCode ierr; 18101cbb95d3SBarry Smith PetscFunctionBegin; 18111cbb95d3SBarry Smith ierr = MatIsHermitianTranspose_SeqAIJ(A,A,tol,f);CHKERRQ(ierr); 18121cbb95d3SBarry Smith PetscFunctionReturn(0); 18131cbb95d3SBarry Smith } 18141cbb95d3SBarry Smith 18151cbb95d3SBarry Smith #undef __FUNCT__ 18164a2ae208SSatish Balay #define __FUNCT__ "MatDiagonalScale_SeqAIJ" 1817dfbe8321SBarry Smith PetscErrorCode MatDiagonalScale_SeqAIJ(Mat A,Vec ll,Vec rr) 181817ab2063SBarry Smith { 1819416022c9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 182054f21887SBarry Smith PetscScalar *l,*r,x; 182154f21887SBarry Smith MatScalar *v; 1822dfbe8321SBarry Smith PetscErrorCode ierr; 1823d0f46423SBarry Smith PetscInt i,j,m = A->rmap->n,n = A->cmap->n,M,nz = a->nz,*jj; 182417ab2063SBarry Smith 18253a40ed3dSBarry Smith PetscFunctionBegin; 182617ab2063SBarry Smith if (ll) { 18273ea7c6a1SSatish Balay /* The local size is used so that VecMPI can be passed to this routine 18283ea7c6a1SSatish Balay by MatDiagonalScale_MPIAIJ */ 1829e1311b90SBarry Smith ierr = VecGetLocalSize(ll,&m);CHKERRQ(ierr); 1830e32f2f54SBarry Smith if (m != A->rmap->n) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Left scaling vector wrong length"); 18311ebc52fbSHong Zhang ierr = VecGetArray(ll,&l);CHKERRQ(ierr); 1832416022c9SBarry Smith v = a->a; 183317ab2063SBarry Smith for (i=0; i<m; i++) { 183417ab2063SBarry Smith x = l[i]; 1835416022c9SBarry Smith M = a->i[i+1] - a->i[i]; 183617ab2063SBarry Smith for (j=0; j<M; j++) { (*v++) *= x;} 183717ab2063SBarry Smith } 18381ebc52fbSHong Zhang ierr = VecRestoreArray(ll,&l);CHKERRQ(ierr); 1839efee365bSSatish Balay ierr = PetscLogFlops(nz);CHKERRQ(ierr); 184017ab2063SBarry Smith } 184117ab2063SBarry Smith if (rr) { 1842e1311b90SBarry Smith ierr = VecGetLocalSize(rr,&n);CHKERRQ(ierr); 1843e32f2f54SBarry Smith if (n != A->cmap->n) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Right scaling vector wrong length"); 18441ebc52fbSHong Zhang ierr = VecGetArray(rr,&r);CHKERRQ(ierr); 1845416022c9SBarry Smith v = a->a; jj = a->j; 184617ab2063SBarry Smith for (i=0; i<nz; i++) { 1847bfeeae90SHong Zhang (*v++) *= r[*jj++]; 184817ab2063SBarry Smith } 18491ebc52fbSHong Zhang ierr = VecRestoreArray(rr,&r);CHKERRQ(ierr); 1850efee365bSSatish Balay ierr = PetscLogFlops(nz);CHKERRQ(ierr); 185117ab2063SBarry Smith } 18523a40ed3dSBarry Smith PetscFunctionReturn(0); 185317ab2063SBarry Smith } 185417ab2063SBarry Smith 18554a2ae208SSatish Balay #undef __FUNCT__ 18564a2ae208SSatish Balay #define __FUNCT__ "MatGetSubMatrix_SeqAIJ" 185797f1f81fSBarry Smith PetscErrorCode MatGetSubMatrix_SeqAIJ(Mat A,IS isrow,IS iscol,PetscInt csize,MatReuse scall,Mat *B) 185817ab2063SBarry Smith { 1859db02288aSLois Curfman McInnes Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data,*c; 18606849ba73SBarry Smith PetscErrorCode ierr; 1861d0f46423SBarry Smith PetscInt *smap,i,k,kstart,kend,oldcols = A->cmap->n,*lens; 186297f1f81fSBarry Smith PetscInt row,mat_i,*mat_j,tcol,first,step,*mat_ilen,sum,lensi; 18635d0c19d7SBarry Smith const PetscInt *irow,*icol; 18645d0c19d7SBarry Smith PetscInt nrows,ncols; 186597f1f81fSBarry Smith PetscInt *starts,*j_new,*i_new,*aj = a->j,*ai = a->i,ii,*ailen = a->ilen; 186654f21887SBarry Smith MatScalar *a_new,*mat_a; 1867416022c9SBarry Smith Mat C; 1868ace3abfcSBarry Smith PetscBool stride,sorted; 186917ab2063SBarry Smith 18703a40ed3dSBarry Smith PetscFunctionBegin; 187114ca34e6SBarry Smith ierr = ISSorted(isrow,&sorted);CHKERRQ(ierr); 1872e32f2f54SBarry Smith if (!sorted) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"ISrow is not sorted"); 187314ca34e6SBarry Smith ierr = ISSorted(iscol,&sorted);CHKERRQ(ierr); 1874e32f2f54SBarry Smith if (!sorted) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"IScol is not sorted"); 187599141d43SSatish Balay 187617ab2063SBarry Smith ierr = ISGetIndices(isrow,&irow);CHKERRQ(ierr); 1877b9b97703SBarry Smith ierr = ISGetLocalSize(isrow,&nrows);CHKERRQ(ierr); 1878b9b97703SBarry Smith ierr = ISGetLocalSize(iscol,&ncols);CHKERRQ(ierr); 187917ab2063SBarry Smith 1880fee21e36SBarry Smith ierr = ISStrideGetInfo(iscol,&first,&step);CHKERRQ(ierr); 18810dbe5b1eSSatish Balay ierr = PetscTypeCompare((PetscObject)iscol,ISSTRIDE,&stride);CHKERRQ(ierr); 1882fee21e36SBarry Smith if (stride && step == 1) { 188302834360SBarry Smith /* special case of contiguous rows */ 18840e83c824SBarry Smith ierr = PetscMalloc2(nrows,PetscInt,&lens,nrows,PetscInt,&starts);CHKERRQ(ierr); 188502834360SBarry Smith /* loop over new rows determining lens and starting points */ 188602834360SBarry Smith for (i=0; i<nrows; i++) { 1887bfeeae90SHong Zhang kstart = ai[irow[i]]; 1888a2744918SBarry Smith kend = kstart + ailen[irow[i]]; 188902834360SBarry Smith for (k=kstart; k<kend; k++) { 1890bfeeae90SHong Zhang if (aj[k] >= first) { 189102834360SBarry Smith starts[i] = k; 189202834360SBarry Smith break; 189302834360SBarry Smith } 189402834360SBarry Smith } 1895a2744918SBarry Smith sum = 0; 189602834360SBarry Smith while (k < kend) { 1897bfeeae90SHong Zhang if (aj[k++] >= first+ncols) break; 1898a2744918SBarry Smith sum++; 189902834360SBarry Smith } 1900a2744918SBarry Smith lens[i] = sum; 190102834360SBarry Smith } 190202834360SBarry Smith /* create submatrix */ 1903cddf8d76SBarry Smith if (scall == MAT_REUSE_MATRIX) { 190497f1f81fSBarry Smith PetscInt n_cols,n_rows; 190508480c60SBarry Smith ierr = MatGetSize(*B,&n_rows,&n_cols);CHKERRQ(ierr); 1906e32f2f54SBarry Smith if (n_rows != nrows || n_cols != ncols) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Reused submatrix wrong size"); 1907d8ced48eSBarry Smith ierr = MatZeroEntries(*B);CHKERRQ(ierr); 190808480c60SBarry Smith C = *B; 19093a40ed3dSBarry Smith } else { 19107adad957SLisandro Dalcin ierr = MatCreate(((PetscObject)A)->comm,&C);CHKERRQ(ierr); 1911f69a0ea3SMatthew Knepley ierr = MatSetSizes(C,nrows,ncols,PETSC_DETERMINE,PETSC_DETERMINE);CHKERRQ(ierr); 19127adad957SLisandro Dalcin ierr = MatSetType(C,((PetscObject)A)->type_name);CHKERRQ(ierr); 1913ab93d7beSBarry Smith ierr = MatSeqAIJSetPreallocation_SeqAIJ(C,0,lens);CHKERRQ(ierr); 191408480c60SBarry Smith } 1915db02288aSLois Curfman McInnes c = (Mat_SeqAIJ*)C->data; 1916db02288aSLois Curfman McInnes 191702834360SBarry Smith /* loop over rows inserting into submatrix */ 1918db02288aSLois Curfman McInnes a_new = c->a; 1919db02288aSLois Curfman McInnes j_new = c->j; 1920db02288aSLois Curfman McInnes i_new = c->i; 1921bfeeae90SHong Zhang 192202834360SBarry Smith for (i=0; i<nrows; i++) { 1923a2744918SBarry Smith ii = starts[i]; 1924a2744918SBarry Smith lensi = lens[i]; 1925a2744918SBarry Smith for (k=0; k<lensi; k++) { 1926a2744918SBarry Smith *j_new++ = aj[ii+k] - first; 192702834360SBarry Smith } 192887828ca2SBarry Smith ierr = PetscMemcpy(a_new,a->a + starts[i],lensi*sizeof(PetscScalar));CHKERRQ(ierr); 1929a2744918SBarry Smith a_new += lensi; 1930a2744918SBarry Smith i_new[i+1] = i_new[i] + lensi; 1931a2744918SBarry Smith c->ilen[i] = lensi; 193202834360SBarry Smith } 19330e83c824SBarry Smith ierr = PetscFree2(lens,starts);CHKERRQ(ierr); 19343a40ed3dSBarry Smith } else { 193502834360SBarry Smith ierr = ISGetIndices(iscol,&icol);CHKERRQ(ierr); 19360e83c824SBarry Smith ierr = PetscMalloc(oldcols*sizeof(PetscInt),&smap);CHKERRQ(ierr); 193797f1f81fSBarry Smith ierr = PetscMemzero(smap,oldcols*sizeof(PetscInt));CHKERRQ(ierr); 19380e83c824SBarry Smith ierr = PetscMalloc((1+nrows)*sizeof(PetscInt),&lens);CHKERRQ(ierr); 193917ab2063SBarry Smith for (i=0; i<ncols; i++) smap[icol[i]] = i+1; 194002834360SBarry Smith /* determine lens of each row */ 194102834360SBarry Smith for (i=0; i<nrows; i++) { 1942bfeeae90SHong Zhang kstart = ai[irow[i]]; 194302834360SBarry Smith kend = kstart + a->ilen[irow[i]]; 194402834360SBarry Smith lens[i] = 0; 194502834360SBarry Smith for (k=kstart; k<kend; k++) { 1946bfeeae90SHong Zhang if (smap[aj[k]]) { 194702834360SBarry Smith lens[i]++; 194802834360SBarry Smith } 194902834360SBarry Smith } 195002834360SBarry Smith } 195117ab2063SBarry Smith /* Create and fill new matrix */ 1952a2744918SBarry Smith if (scall == MAT_REUSE_MATRIX) { 1953ace3abfcSBarry Smith PetscBool equal; 19540f5bd95cSBarry Smith 195599141d43SSatish Balay c = (Mat_SeqAIJ *)((*B)->data); 1956e32f2f54SBarry Smith if ((*B)->rmap->n != nrows || (*B)->cmap->n != ncols) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Cannot reuse matrix. wrong size"); 1957d0f46423SBarry Smith ierr = PetscMemcmp(c->ilen,lens,(*B)->rmap->n*sizeof(PetscInt),&equal);CHKERRQ(ierr); 19580f5bd95cSBarry Smith if (!equal) { 1959e32f2f54SBarry Smith SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Cannot reuse matrix. wrong no of nonzeros"); 196099141d43SSatish Balay } 1961d0f46423SBarry Smith ierr = PetscMemzero(c->ilen,(*B)->rmap->n*sizeof(PetscInt));CHKERRQ(ierr); 196208480c60SBarry Smith C = *B; 19633a40ed3dSBarry Smith } else { 19647adad957SLisandro Dalcin ierr = MatCreate(((PetscObject)A)->comm,&C);CHKERRQ(ierr); 1965f69a0ea3SMatthew Knepley ierr = MatSetSizes(C,nrows,ncols,PETSC_DETERMINE,PETSC_DETERMINE);CHKERRQ(ierr); 19667adad957SLisandro Dalcin ierr = MatSetType(C,((PetscObject)A)->type_name);CHKERRQ(ierr); 1967ab93d7beSBarry Smith ierr = MatSeqAIJSetPreallocation_SeqAIJ(C,0,lens);CHKERRQ(ierr); 196808480c60SBarry Smith } 196999141d43SSatish Balay c = (Mat_SeqAIJ *)(C->data); 197017ab2063SBarry Smith for (i=0; i<nrows; i++) { 197199141d43SSatish Balay row = irow[i]; 1972bfeeae90SHong Zhang kstart = ai[row]; 197399141d43SSatish Balay kend = kstart + a->ilen[row]; 1974bfeeae90SHong Zhang mat_i = c->i[i]; 197599141d43SSatish Balay mat_j = c->j + mat_i; 197699141d43SSatish Balay mat_a = c->a + mat_i; 197799141d43SSatish Balay mat_ilen = c->ilen + i; 197817ab2063SBarry Smith for (k=kstart; k<kend; k++) { 1979bfeeae90SHong Zhang if ((tcol=smap[a->j[k]])) { 1980ed480e8bSBarry Smith *mat_j++ = tcol - 1; 198199141d43SSatish Balay *mat_a++ = a->a[k]; 198299141d43SSatish Balay (*mat_ilen)++; 198399141d43SSatish Balay 198417ab2063SBarry Smith } 198517ab2063SBarry Smith } 198617ab2063SBarry Smith } 198702834360SBarry Smith /* Free work space */ 198802834360SBarry Smith ierr = ISRestoreIndices(iscol,&icol);CHKERRQ(ierr); 1989606d414cSSatish Balay ierr = PetscFree(smap);CHKERRQ(ierr); 1990606d414cSSatish Balay ierr = PetscFree(lens);CHKERRQ(ierr); 199102834360SBarry Smith } 19926d4a8577SBarry Smith ierr = MatAssemblyBegin(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 19936d4a8577SBarry Smith ierr = MatAssemblyEnd(C,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 199417ab2063SBarry Smith 199517ab2063SBarry Smith ierr = ISRestoreIndices(isrow,&irow);CHKERRQ(ierr); 1996416022c9SBarry Smith *B = C; 19973a40ed3dSBarry Smith PetscFunctionReturn(0); 199817ab2063SBarry Smith } 199917ab2063SBarry Smith 20001df811f5SHong Zhang #undef __FUNCT__ 200182d44351SHong Zhang #define __FUNCT__ "MatGetMultiProcBlock_SeqAIJ" 200282d44351SHong Zhang PetscErrorCode MatGetMultiProcBlock_SeqAIJ(Mat mat,MPI_Comm subComm,Mat* subMat) 200382d44351SHong Zhang { 200482d44351SHong Zhang PetscErrorCode ierr; 200582d44351SHong Zhang Mat B; 200682d44351SHong Zhang 200782d44351SHong Zhang PetscFunctionBegin; 200882d44351SHong Zhang ierr = MatCreate(subComm,&B);CHKERRQ(ierr); 200982d44351SHong Zhang ierr = MatSetSizes(B,mat->rmap->n,mat->cmap->n,mat->rmap->n,mat->cmap->n);CHKERRQ(ierr); 201082d44351SHong Zhang ierr = MatSetType(B,MATSEQAIJ);CHKERRQ(ierr); 201182d44351SHong Zhang ierr = MatDuplicateNoCreate_SeqAIJ(B,mat,MAT_COPY_VALUES,PETSC_TRUE);CHKERRQ(ierr); 201282d44351SHong Zhang *subMat = B; 201382d44351SHong Zhang PetscFunctionReturn(0); 201482d44351SHong Zhang } 201582d44351SHong Zhang 201682d44351SHong Zhang #undef __FUNCT__ 20174a2ae208SSatish Balay #define __FUNCT__ "MatILUFactor_SeqAIJ" 20180481f469SBarry Smith PetscErrorCode MatILUFactor_SeqAIJ(Mat inA,IS row,IS col,const MatFactorInfo *info) 2019a871dcd8SBarry Smith { 202063b91edcSBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)inA->data; 2021dfbe8321SBarry Smith PetscErrorCode ierr; 202263b91edcSBarry Smith Mat outA; 2023ace3abfcSBarry Smith PetscBool row_identity,col_identity; 202463b91edcSBarry Smith 20253a40ed3dSBarry Smith PetscFunctionBegin; 2026e32f2f54SBarry Smith if (info->levels != 0) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"Only levels=0 supported for in-place ilu"); 20271df811f5SHong Zhang 2028b8a78c4aSBarry Smith ierr = ISIdentity(row,&row_identity);CHKERRQ(ierr); 2029b8a78c4aSBarry Smith ierr = ISIdentity(col,&col_identity);CHKERRQ(ierr); 2030a871dcd8SBarry Smith 203163b91edcSBarry Smith outA = inA; 2032d5f3da31SBarry Smith outA->factortype = MAT_FACTOR_LU; 2033c38d4ed2SBarry Smith ierr = PetscObjectReference((PetscObject)row);CHKERRQ(ierr); 2034c3122656SLisandro Dalcin if (a->row) { ierr = ISDestroy(a->row);CHKERRQ(ierr);} 2035c3122656SLisandro Dalcin a->row = row; 2036c38d4ed2SBarry Smith ierr = PetscObjectReference((PetscObject)col);CHKERRQ(ierr); 2037c3122656SLisandro Dalcin if (a->col) { ierr = ISDestroy(a->col);CHKERRQ(ierr);} 2038c3122656SLisandro Dalcin a->col = col; 203963b91edcSBarry Smith 204036db0b34SBarry Smith /* Create the inverse permutation so that it can be used in MatLUFactorNumeric() */ 2041b9b97703SBarry Smith if (a->icol) {ierr = ISDestroy(a->icol);CHKERRQ(ierr);} /* need to remove old one */ 20424c49b128SBarry Smith ierr = ISInvertPermutation(col,PETSC_DECIDE,&a->icol);CHKERRQ(ierr); 204352e6d16bSBarry Smith ierr = PetscLogObjectParent(inA,a->icol);CHKERRQ(ierr); 2044f0ec6fceSSatish Balay 204594a9d846SBarry Smith if (!a->solve_work) { /* this matrix may have been factored before */ 2046d0f46423SBarry Smith ierr = PetscMalloc((inA->rmap->n+1)*sizeof(PetscScalar),&a->solve_work);CHKERRQ(ierr); 2047d0f46423SBarry Smith ierr = PetscLogObjectMemory(inA, (inA->rmap->n+1)*sizeof(PetscScalar));CHKERRQ(ierr); 204894a9d846SBarry Smith } 204963b91edcSBarry Smith 2050f1e2ffcdSBarry Smith ierr = MatMarkDiagonal_SeqAIJ(inA);CHKERRQ(ierr); 2051137fb511SHong Zhang if (row_identity && col_identity) { 2052ad04f41aSHong Zhang ierr = MatLUFactorNumeric_SeqAIJ_inplace(outA,inA,info);CHKERRQ(ierr); 2053137fb511SHong Zhang } else { 2054719d5645SBarry Smith ierr = MatLUFactorNumeric_SeqAIJ_InplaceWithPerm(outA,inA,info);CHKERRQ(ierr); 2055137fb511SHong Zhang } 20563a40ed3dSBarry Smith PetscFunctionReturn(0); 2057a871dcd8SBarry Smith } 2058a871dcd8SBarry Smith 20594a2ae208SSatish Balay #undef __FUNCT__ 20604a2ae208SSatish Balay #define __FUNCT__ "MatScale_SeqAIJ" 2061f4df32b1SMatthew Knepley PetscErrorCode MatScale_SeqAIJ(Mat inA,PetscScalar alpha) 2062f0b747eeSBarry Smith { 2063f0b747eeSBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)inA->data; 2064f4df32b1SMatthew Knepley PetscScalar oalpha = alpha; 2065efee365bSSatish Balay PetscErrorCode ierr; 20660805154bSBarry Smith PetscBLASInt one = 1,bnz = PetscBLASIntCast(a->nz); 20673a40ed3dSBarry Smith 20683a40ed3dSBarry Smith PetscFunctionBegin; 2069f4df32b1SMatthew Knepley BLASscal_(&bnz,&oalpha,a->a,&one); 2070efee365bSSatish Balay ierr = PetscLogFlops(a->nz);CHKERRQ(ierr); 20713a40ed3dSBarry Smith PetscFunctionReturn(0); 2072f0b747eeSBarry Smith } 2073f0b747eeSBarry Smith 20744a2ae208SSatish Balay #undef __FUNCT__ 20754a2ae208SSatish Balay #define __FUNCT__ "MatGetSubMatrices_SeqAIJ" 207697f1f81fSBarry Smith PetscErrorCode MatGetSubMatrices_SeqAIJ(Mat A,PetscInt n,const IS irow[],const IS icol[],MatReuse scall,Mat *B[]) 2077cddf8d76SBarry Smith { 2078dfbe8321SBarry Smith PetscErrorCode ierr; 207997f1f81fSBarry Smith PetscInt i; 2080cddf8d76SBarry Smith 20813a40ed3dSBarry Smith PetscFunctionBegin; 2082cddf8d76SBarry Smith if (scall == MAT_INITIAL_MATRIX) { 2083b0a32e0cSBarry Smith ierr = PetscMalloc((n+1)*sizeof(Mat),B);CHKERRQ(ierr); 2084cddf8d76SBarry Smith } 2085cddf8d76SBarry Smith 2086cddf8d76SBarry Smith for (i=0; i<n; i++) { 20876a6a5d1dSBarry Smith ierr = MatGetSubMatrix_SeqAIJ(A,irow[i],icol[i],PETSC_DECIDE,scall,&(*B)[i]);CHKERRQ(ierr); 2088cddf8d76SBarry Smith } 20893a40ed3dSBarry Smith PetscFunctionReturn(0); 2090cddf8d76SBarry Smith } 2091cddf8d76SBarry Smith 20924a2ae208SSatish Balay #undef __FUNCT__ 20934a2ae208SSatish Balay #define __FUNCT__ "MatIncreaseOverlap_SeqAIJ" 209497f1f81fSBarry Smith PetscErrorCode MatIncreaseOverlap_SeqAIJ(Mat A,PetscInt is_max,IS is[],PetscInt ov) 20954dcbc457SBarry Smith { 2096e4d965acSSatish Balay Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 20976849ba73SBarry Smith PetscErrorCode ierr; 20985d0c19d7SBarry Smith PetscInt row,i,j,k,l,m,n,*nidx,isz,val; 20995d0c19d7SBarry Smith const PetscInt *idx; 210097f1f81fSBarry Smith PetscInt start,end,*ai,*aj; 2101f1af5d2fSBarry Smith PetscBT table; 2102bbd702dbSSatish Balay 21033a40ed3dSBarry Smith PetscFunctionBegin; 2104d0f46423SBarry Smith m = A->rmap->n; 2105e4d965acSSatish Balay ai = a->i; 2106bfeeae90SHong Zhang aj = a->j; 21078a047759SSatish Balay 2108e32f2f54SBarry Smith if (ov < 0) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"illegal negative overlap value used"); 210906763907SSatish Balay 211097f1f81fSBarry Smith ierr = PetscMalloc((m+1)*sizeof(PetscInt),&nidx);CHKERRQ(ierr); 21116831982aSBarry Smith ierr = PetscBTCreate(m,table);CHKERRQ(ierr); 211206763907SSatish Balay 2113e4d965acSSatish Balay for (i=0; i<is_max; i++) { 2114b97fc60eSLois Curfman McInnes /* Initialize the two local arrays */ 2115e4d965acSSatish Balay isz = 0; 21166831982aSBarry Smith ierr = PetscBTMemzero(m,table);CHKERRQ(ierr); 2117e4d965acSSatish Balay 2118e4d965acSSatish Balay /* Extract the indices, assume there can be duplicate entries */ 21194dcbc457SBarry Smith ierr = ISGetIndices(is[i],&idx);CHKERRQ(ierr); 2120b9b97703SBarry Smith ierr = ISGetLocalSize(is[i],&n);CHKERRQ(ierr); 2121e4d965acSSatish Balay 2122dd097bc3SLois Curfman McInnes /* Enter these into the temp arrays. I.e., mark table[row], enter row into new index */ 2123e4d965acSSatish Balay for (j=0; j<n ; ++j){ 2124f1af5d2fSBarry Smith if(!PetscBTLookupSet(table,idx[j])) { nidx[isz++] = idx[j];} 21254dcbc457SBarry Smith } 212606763907SSatish Balay ierr = ISRestoreIndices(is[i],&idx);CHKERRQ(ierr); 212706763907SSatish Balay ierr = ISDestroy(is[i]);CHKERRQ(ierr); 2128e4d965acSSatish Balay 212904a348a9SBarry Smith k = 0; 213004a348a9SBarry Smith for (j=0; j<ov; j++){ /* for each overlap */ 213104a348a9SBarry Smith n = isz; 213206763907SSatish Balay for (; k<n ; k++){ /* do only those rows in nidx[k], which are not done yet */ 2133e4d965acSSatish Balay row = nidx[k]; 2134e4d965acSSatish Balay start = ai[row]; 2135e4d965acSSatish Balay end = ai[row+1]; 213604a348a9SBarry Smith for (l = start; l<end ; l++){ 2137efb16452SHong Zhang val = aj[l] ; 2138f1af5d2fSBarry Smith if (!PetscBTLookupSet(table,val)) {nidx[isz++] = val;} 2139e4d965acSSatish Balay } 2140e4d965acSSatish Balay } 2141e4d965acSSatish Balay } 214270b3c8c7SBarry Smith ierr = ISCreateGeneral(PETSC_COMM_SELF,isz,nidx,PETSC_COPY_VALUES,(is+i));CHKERRQ(ierr); 2143e4d965acSSatish Balay } 21446831982aSBarry Smith ierr = PetscBTDestroy(table);CHKERRQ(ierr); 2145606d414cSSatish Balay ierr = PetscFree(nidx);CHKERRQ(ierr); 21463a40ed3dSBarry Smith PetscFunctionReturn(0); 21474dcbc457SBarry Smith } 214817ab2063SBarry Smith 21490513a670SBarry Smith /* -------------------------------------------------------------- */ 21504a2ae208SSatish Balay #undef __FUNCT__ 21514a2ae208SSatish Balay #define __FUNCT__ "MatPermute_SeqAIJ" 2152dfbe8321SBarry Smith PetscErrorCode MatPermute_SeqAIJ(Mat A,IS rowp,IS colp,Mat *B) 21530513a670SBarry Smith { 21540513a670SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 21556849ba73SBarry Smith PetscErrorCode ierr; 21563b98c0a2SBarry Smith PetscInt i,nz = 0,m = A->rmap->n,n = A->cmap->n; 21575d0c19d7SBarry Smith const PetscInt *row,*col; 21585d0c19d7SBarry Smith PetscInt *cnew,j,*lens; 215956cd22aeSBarry Smith IS icolp,irowp; 21603b98c0a2SBarry Smith PetscInt *cwork = PETSC_NULL; 21613b98c0a2SBarry Smith PetscScalar *vwork = PETSC_NULL; 21620513a670SBarry Smith 21633a40ed3dSBarry Smith PetscFunctionBegin; 21644c49b128SBarry Smith ierr = ISInvertPermutation(rowp,PETSC_DECIDE,&irowp);CHKERRQ(ierr); 216556cd22aeSBarry Smith ierr = ISGetIndices(irowp,&row);CHKERRQ(ierr); 21664c49b128SBarry Smith ierr = ISInvertPermutation(colp,PETSC_DECIDE,&icolp);CHKERRQ(ierr); 216756cd22aeSBarry Smith ierr = ISGetIndices(icolp,&col);CHKERRQ(ierr); 21680513a670SBarry Smith 21690513a670SBarry Smith /* determine lengths of permuted rows */ 217097f1f81fSBarry Smith ierr = PetscMalloc((m+1)*sizeof(PetscInt),&lens);CHKERRQ(ierr); 21710513a670SBarry Smith for (i=0; i<m; i++) { 21720513a670SBarry Smith lens[row[i]] = a->i[i+1] - a->i[i]; 21730513a670SBarry Smith } 21747adad957SLisandro Dalcin ierr = MatCreate(((PetscObject)A)->comm,B);CHKERRQ(ierr); 2175f69a0ea3SMatthew Knepley ierr = MatSetSizes(*B,m,n,m,n);CHKERRQ(ierr); 21767adad957SLisandro Dalcin ierr = MatSetType(*B,((PetscObject)A)->type_name);CHKERRQ(ierr); 2177ab93d7beSBarry Smith ierr = MatSeqAIJSetPreallocation_SeqAIJ(*B,0,lens);CHKERRQ(ierr); 2178606d414cSSatish Balay ierr = PetscFree(lens);CHKERRQ(ierr); 21790513a670SBarry Smith 218097f1f81fSBarry Smith ierr = PetscMalloc(n*sizeof(PetscInt),&cnew);CHKERRQ(ierr); 21810513a670SBarry Smith for (i=0; i<m; i++) { 218232ec9ce4SBarry Smith ierr = MatGetRow_SeqAIJ(A,i,&nz,&cwork,&vwork);CHKERRQ(ierr); 21830513a670SBarry Smith for (j=0; j<nz; j++) { cnew[j] = col[cwork[j]];} 2184cdc0ba36SBarry Smith ierr = MatSetValues_SeqAIJ(*B,1,&row[i],nz,cnew,vwork,INSERT_VALUES);CHKERRQ(ierr); 218532ec9ce4SBarry Smith ierr = MatRestoreRow_SeqAIJ(A,i,&nz,&cwork,&vwork);CHKERRQ(ierr); 21860513a670SBarry Smith } 2187606d414cSSatish Balay ierr = PetscFree(cnew);CHKERRQ(ierr); 21883c7d62e4SBarry Smith (*B)->assembled = PETSC_FALSE; 21890513a670SBarry Smith ierr = MatAssemblyBegin(*B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 21900513a670SBarry Smith ierr = MatAssemblyEnd(*B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 219156cd22aeSBarry Smith ierr = ISRestoreIndices(irowp,&row);CHKERRQ(ierr); 219256cd22aeSBarry Smith ierr = ISRestoreIndices(icolp,&col);CHKERRQ(ierr); 219356cd22aeSBarry Smith ierr = ISDestroy(irowp);CHKERRQ(ierr); 219456cd22aeSBarry Smith ierr = ISDestroy(icolp);CHKERRQ(ierr); 21953a40ed3dSBarry Smith PetscFunctionReturn(0); 21960513a670SBarry Smith } 21970513a670SBarry Smith 21984a2ae208SSatish Balay #undef __FUNCT__ 21994a2ae208SSatish Balay #define __FUNCT__ "MatCopy_SeqAIJ" 2200dfbe8321SBarry Smith PetscErrorCode MatCopy_SeqAIJ(Mat A,Mat B,MatStructure str) 2201cb5b572fSBarry Smith { 2202dfbe8321SBarry Smith PetscErrorCode ierr; 2203cb5b572fSBarry Smith 2204cb5b572fSBarry Smith PetscFunctionBegin; 220533f4a19fSKris Buschelman /* If the two matrices have the same copy implementation, use fast copy. */ 220633f4a19fSKris Buschelman if (str == SAME_NONZERO_PATTERN && (A->ops->copy == B->ops->copy)) { 2207be6bf707SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 2208be6bf707SBarry Smith Mat_SeqAIJ *b = (Mat_SeqAIJ*)B->data; 2209be6bf707SBarry Smith 2210700c5bfcSBarry Smith if (a->i[A->rmap->n] != b->i[B->rmap->n]) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_INCOMP,"Number of nonzeros in two matrices are different"); 2211d0f46423SBarry Smith ierr = PetscMemcpy(b->a,a->a,(a->i[A->rmap->n])*sizeof(PetscScalar));CHKERRQ(ierr); 2212cb5b572fSBarry Smith } else { 2213cb5b572fSBarry Smith ierr = MatCopy_Basic(A,B,str);CHKERRQ(ierr); 2214cb5b572fSBarry Smith } 2215cb5b572fSBarry Smith PetscFunctionReturn(0); 2216cb5b572fSBarry Smith } 2217cb5b572fSBarry Smith 22184a2ae208SSatish Balay #undef __FUNCT__ 22194a2ae208SSatish Balay #define __FUNCT__ "MatSetUpPreallocation_SeqAIJ" 2220dfbe8321SBarry Smith PetscErrorCode MatSetUpPreallocation_SeqAIJ(Mat A) 2221273d9f13SBarry Smith { 2222dfbe8321SBarry Smith PetscErrorCode ierr; 2223273d9f13SBarry Smith 2224273d9f13SBarry Smith PetscFunctionBegin; 2225ab93d7beSBarry Smith ierr = MatSeqAIJSetPreallocation_SeqAIJ(A,PETSC_DEFAULT,0);CHKERRQ(ierr); 2226273d9f13SBarry Smith PetscFunctionReturn(0); 2227273d9f13SBarry Smith } 2228273d9f13SBarry Smith 22294a2ae208SSatish Balay #undef __FUNCT__ 22304a2ae208SSatish Balay #define __FUNCT__ "MatGetArray_SeqAIJ" 2231a77337e4SBarry Smith PetscErrorCode MatGetArray_SeqAIJ(Mat A,PetscScalar *array[]) 22326c0721eeSBarry Smith { 22336c0721eeSBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 22346c0721eeSBarry Smith PetscFunctionBegin; 22356c0721eeSBarry Smith *array = a->a; 22366c0721eeSBarry Smith PetscFunctionReturn(0); 22376c0721eeSBarry Smith } 22386c0721eeSBarry Smith 22394a2ae208SSatish Balay #undef __FUNCT__ 22404a2ae208SSatish Balay #define __FUNCT__ "MatRestoreArray_SeqAIJ" 2241dfbe8321SBarry Smith PetscErrorCode MatRestoreArray_SeqAIJ(Mat A,PetscScalar *array[]) 22426c0721eeSBarry Smith { 22436c0721eeSBarry Smith PetscFunctionBegin; 22446c0721eeSBarry Smith PetscFunctionReturn(0); 22456c0721eeSBarry Smith } 2246273d9f13SBarry Smith 2247ee4f033dSBarry Smith #undef __FUNCT__ 2248ee4f033dSBarry Smith #define __FUNCT__ "MatFDColoringApply_SeqAIJ" 2249dfbe8321SBarry Smith PetscErrorCode MatFDColoringApply_SeqAIJ(Mat J,MatFDColoring coloring,Vec x1,MatStructure *flag,void *sctx) 2250ee4f033dSBarry Smith { 22516849ba73SBarry Smith PetscErrorCode (*f)(void*,Vec,Vec,void*) = (PetscErrorCode (*)(void*,Vec,Vec,void *))coloring->f; 22526849ba73SBarry Smith PetscErrorCode ierr; 225397f1f81fSBarry Smith PetscInt k,N,start,end,l,row,col,srow,**vscaleforrow,m1,m2; 2254efb30889SBarry Smith PetscScalar dx,*y,*xx,*w3_array; 225587828ca2SBarry Smith PetscScalar *vscale_array; 2256ee4f033dSBarry Smith PetscReal epsilon = coloring->error_rel,umin = coloring->umin; 2257ee4f033dSBarry Smith Vec w1,w2,w3; 2258ee4f033dSBarry Smith void *fctx = coloring->fctx; 2259ace3abfcSBarry Smith PetscBool flg = PETSC_FALSE; 2260ee4f033dSBarry Smith 2261ee4f033dSBarry Smith PetscFunctionBegin; 2262ee4f033dSBarry Smith if (!coloring->w1) { 2263ee4f033dSBarry Smith ierr = VecDuplicate(x1,&coloring->w1);CHKERRQ(ierr); 226452e6d16bSBarry Smith ierr = PetscLogObjectParent(coloring,coloring->w1);CHKERRQ(ierr); 2265ee4f033dSBarry Smith ierr = VecDuplicate(x1,&coloring->w2);CHKERRQ(ierr); 226652e6d16bSBarry Smith ierr = PetscLogObjectParent(coloring,coloring->w2);CHKERRQ(ierr); 2267ee4f033dSBarry Smith ierr = VecDuplicate(x1,&coloring->w3);CHKERRQ(ierr); 226852e6d16bSBarry Smith ierr = PetscLogObjectParent(coloring,coloring->w3);CHKERRQ(ierr); 2269ee4f033dSBarry Smith } 2270ee4f033dSBarry Smith w1 = coloring->w1; w2 = coloring->w2; w3 = coloring->w3; 2271ee4f033dSBarry Smith 2272ee4f033dSBarry Smith ierr = MatSetUnfactored(J);CHKERRQ(ierr); 2273acfcf0e5SJed Brown ierr = PetscOptionsGetBool(((PetscObject)coloring)->prefix,"-mat_fd_coloring_dont_rezero",&flg,PETSC_NULL);CHKERRQ(ierr); 2274ee4f033dSBarry Smith if (flg) { 2275ae15b995SBarry Smith ierr = PetscInfo(coloring,"Not calling MatZeroEntries()\n");CHKERRQ(ierr); 2276ee4f033dSBarry Smith } else { 2277ace3abfcSBarry Smith PetscBool assembled; 22780b9b6f31SBarry Smith ierr = MatAssembled(J,&assembled);CHKERRQ(ierr); 22790b9b6f31SBarry Smith if (assembled) { 2280ee4f033dSBarry Smith ierr = MatZeroEntries(J);CHKERRQ(ierr); 2281ee4f033dSBarry Smith } 22820b9b6f31SBarry Smith } 2283ee4f033dSBarry Smith 2284ee4f033dSBarry Smith ierr = VecGetOwnershipRange(x1,&start,&end);CHKERRQ(ierr); 2285ee4f033dSBarry Smith ierr = VecGetSize(x1,&N);CHKERRQ(ierr); 2286ee4f033dSBarry Smith 2287ee4f033dSBarry Smith /* 2288ee4f033dSBarry Smith This is a horrible, horrible, hack. See DMMGComputeJacobian_Multigrid() it inproperly sets 2289ee4f033dSBarry Smith coloring->F for the coarser grids from the finest 2290ee4f033dSBarry Smith */ 2291ee4f033dSBarry Smith if (coloring->F) { 2292ee4f033dSBarry Smith ierr = VecGetLocalSize(coloring->F,&m1);CHKERRQ(ierr); 2293ee4f033dSBarry Smith ierr = VecGetLocalSize(w1,&m2);CHKERRQ(ierr); 2294ee4f033dSBarry Smith if (m1 != m2) { 2295ee4f033dSBarry Smith coloring->F = 0; 2296ee4f033dSBarry Smith } 2297ee4f033dSBarry Smith } 2298ee4f033dSBarry Smith 2299ee4f033dSBarry Smith if (coloring->F) { 2300ee4f033dSBarry Smith w1 = coloring->F; 2301ee4f033dSBarry Smith coloring->F = 0; 2302ee4f033dSBarry Smith } else { 230366f9b7ceSBarry Smith ierr = PetscLogEventBegin(MAT_FDColoringFunction,0,0,0,0);CHKERRQ(ierr); 2304ee4f033dSBarry Smith ierr = (*f)(sctx,x1,w1,fctx);CHKERRQ(ierr); 230566f9b7ceSBarry Smith ierr = PetscLogEventEnd(MAT_FDColoringFunction,0,0,0,0);CHKERRQ(ierr); 2306ee4f033dSBarry Smith } 2307ee4f033dSBarry Smith 2308ee4f033dSBarry Smith /* 2309ee4f033dSBarry Smith Compute all the scale factors and share with other processors 2310ee4f033dSBarry Smith */ 23111ebc52fbSHong Zhang ierr = VecGetArray(x1,&xx);CHKERRQ(ierr);xx = xx - start; 23121ebc52fbSHong Zhang ierr = VecGetArray(coloring->vscale,&vscale_array);CHKERRQ(ierr);vscale_array = vscale_array - start; 2313ee4f033dSBarry Smith for (k=0; k<coloring->ncolors; k++) { 2314ee4f033dSBarry Smith /* 2315ee4f033dSBarry Smith Loop over each column associated with color adding the 2316ee4f033dSBarry Smith perturbation to the vector w3. 2317ee4f033dSBarry Smith */ 2318ee4f033dSBarry Smith for (l=0; l<coloring->ncolumns[k]; l++) { 2319ee4f033dSBarry Smith col = coloring->columns[k][l]; /* column of the matrix we are probing for */ 2320ee4f033dSBarry Smith dx = xx[col]; 2321ee4f033dSBarry Smith if (dx == 0.0) dx = 1.0; 2322ee4f033dSBarry Smith #if !defined(PETSC_USE_COMPLEX) 2323ee4f033dSBarry Smith if (dx < umin && dx >= 0.0) dx = umin; 2324ee4f033dSBarry Smith else if (dx < 0.0 && dx > -umin) dx = -umin; 2325ee4f033dSBarry Smith #else 2326ee4f033dSBarry Smith if (PetscAbsScalar(dx) < umin && PetscRealPart(dx) >= 0.0) dx = umin; 2327ee4f033dSBarry Smith else if (PetscRealPart(dx) < 0.0 && PetscAbsScalar(dx) < umin) dx = -umin; 2328ee4f033dSBarry Smith #endif 2329ee4f033dSBarry Smith dx *= epsilon; 2330ee4f033dSBarry Smith vscale_array[col] = 1.0/dx; 2331ee4f033dSBarry Smith } 2332ee4f033dSBarry Smith } 23331ebc52fbSHong Zhang vscale_array = vscale_array + start;ierr = VecRestoreArray(coloring->vscale,&vscale_array);CHKERRQ(ierr); 2334ee4f033dSBarry Smith ierr = VecGhostUpdateBegin(coloring->vscale,INSERT_VALUES,SCATTER_FORWARD);CHKERRQ(ierr); 2335ee4f033dSBarry Smith ierr = VecGhostUpdateEnd(coloring->vscale,INSERT_VALUES,SCATTER_FORWARD);CHKERRQ(ierr); 2336ee4f033dSBarry Smith 2337ee4f033dSBarry Smith /* ierr = VecView(coloring->vscale,PETSC_VIEWER_STDOUT_WORLD); 2338ee4f033dSBarry Smith ierr = VecView(x1,PETSC_VIEWER_STDOUT_WORLD);*/ 2339ee4f033dSBarry Smith 2340ee4f033dSBarry Smith if (coloring->vscaleforrow) vscaleforrow = coloring->vscaleforrow; 2341ee4f033dSBarry Smith else vscaleforrow = coloring->columnsforrow; 2342ee4f033dSBarry Smith 23431ebc52fbSHong Zhang ierr = VecGetArray(coloring->vscale,&vscale_array);CHKERRQ(ierr); 2344ee4f033dSBarry Smith /* 2345ee4f033dSBarry Smith Loop over each color 2346ee4f033dSBarry Smith */ 2347ee4f033dSBarry Smith for (k=0; k<coloring->ncolors; k++) { 234849b058dcSBarry Smith coloring->currentcolor = k; 2349ee4f033dSBarry Smith ierr = VecCopy(x1,w3);CHKERRQ(ierr); 23501ebc52fbSHong Zhang ierr = VecGetArray(w3,&w3_array);CHKERRQ(ierr);w3_array = w3_array - start; 2351ee4f033dSBarry Smith /* 2352ee4f033dSBarry Smith Loop over each column associated with color adding the 2353ee4f033dSBarry Smith perturbation to the vector w3. 2354ee4f033dSBarry Smith */ 2355ee4f033dSBarry Smith for (l=0; l<coloring->ncolumns[k]; l++) { 2356ee4f033dSBarry Smith col = coloring->columns[k][l]; /* column of the matrix we are probing for */ 2357ee4f033dSBarry Smith dx = xx[col]; 23585b8514ebSBarry Smith if (dx == 0.0) dx = 1.0; 2359ee4f033dSBarry Smith #if !defined(PETSC_USE_COMPLEX) 2360ee4f033dSBarry Smith if (dx < umin && dx >= 0.0) dx = umin; 2361ee4f033dSBarry Smith else if (dx < 0.0 && dx > -umin) dx = -umin; 2362ee4f033dSBarry Smith #else 2363ee4f033dSBarry Smith if (PetscAbsScalar(dx) < umin && PetscRealPart(dx) >= 0.0) dx = umin; 2364ee4f033dSBarry Smith else if (PetscRealPart(dx) < 0.0 && PetscAbsScalar(dx) < umin) dx = -umin; 2365ee4f033dSBarry Smith #endif 2366ee4f033dSBarry Smith dx *= epsilon; 2367e32f2f54SBarry Smith if (!PetscAbsScalar(dx)) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_PLIB,"Computed 0 differencing parameter"); 2368ee4f033dSBarry Smith w3_array[col] += dx; 2369ee4f033dSBarry Smith } 23701ebc52fbSHong Zhang w3_array = w3_array + start; ierr = VecRestoreArray(w3,&w3_array);CHKERRQ(ierr); 2371ee4f033dSBarry Smith 2372ee4f033dSBarry Smith /* 2373ee4f033dSBarry Smith Evaluate function at x1 + dx (here dx is a vector of perturbations) 2374ee4f033dSBarry Smith */ 2375ee4f033dSBarry Smith 237666f9b7ceSBarry Smith ierr = PetscLogEventBegin(MAT_FDColoringFunction,0,0,0,0);CHKERRQ(ierr); 2377ee4f033dSBarry Smith ierr = (*f)(sctx,w3,w2,fctx);CHKERRQ(ierr); 237866f9b7ceSBarry Smith ierr = PetscLogEventEnd(MAT_FDColoringFunction,0,0,0,0);CHKERRQ(ierr); 2379efb30889SBarry Smith ierr = VecAXPY(w2,-1.0,w1);CHKERRQ(ierr); 2380ee4f033dSBarry Smith 2381ee4f033dSBarry Smith /* 2382ee4f033dSBarry Smith Loop over rows of vector, putting results into Jacobian matrix 2383ee4f033dSBarry Smith */ 23841ebc52fbSHong Zhang ierr = VecGetArray(w2,&y);CHKERRQ(ierr); 2385ee4f033dSBarry Smith for (l=0; l<coloring->nrows[k]; l++) { 2386ee4f033dSBarry Smith row = coloring->rows[k][l]; 2387ee4f033dSBarry Smith col = coloring->columnsforrow[k][l]; 2388ee4f033dSBarry Smith y[row] *= vscale_array[vscaleforrow[k][l]]; 2389ee4f033dSBarry Smith srow = row + start; 2390ee4f033dSBarry Smith ierr = MatSetValues_SeqAIJ(J,1,&srow,1,&col,y+row,INSERT_VALUES);CHKERRQ(ierr); 2391ee4f033dSBarry Smith } 23921ebc52fbSHong Zhang ierr = VecRestoreArray(w2,&y);CHKERRQ(ierr); 2393ee4f033dSBarry Smith } 239449b058dcSBarry Smith coloring->currentcolor = k; 23951ebc52fbSHong Zhang ierr = VecRestoreArray(coloring->vscale,&vscale_array);CHKERRQ(ierr); 23961ebc52fbSHong Zhang xx = xx + start; ierr = VecRestoreArray(x1,&xx);CHKERRQ(ierr); 2397ee4f033dSBarry Smith ierr = MatAssemblyBegin(J,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 2398ee4f033dSBarry Smith ierr = MatAssemblyEnd(J,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 2399ee4f033dSBarry Smith PetscFunctionReturn(0); 2400ee4f033dSBarry Smith } 2401ee4f033dSBarry Smith 24028229c054SShri Abhyankar /* 24038229c054SShri Abhyankar Computes the number of nonzeros per row needed for preallocation when X and Y 24048229c054SShri Abhyankar have different nonzero structure. 24058229c054SShri Abhyankar */ 2406ac90fabeSBarry Smith #undef __FUNCT__ 24078229c054SShri Abhyankar #define __FUNCT__ "MatAXPYGetPreallocation_SeqAIJ" 24088229c054SShri Abhyankar PetscErrorCode MatAXPYGetPreallocation_SeqAIJ(Mat Y,Mat X,PetscInt* nnz) 2409ec7775f6SShri Abhyankar { 24108229c054SShri Abhyankar PetscInt i,m=Y->rmap->N; 2411ec7775f6SShri Abhyankar Mat_SeqAIJ *x = (Mat_SeqAIJ*)X->data; 2412ec7775f6SShri Abhyankar Mat_SeqAIJ *y = (Mat_SeqAIJ*)Y->data; 2413ec7775f6SShri Abhyankar const PetscInt *xi = x->i,*yi = y->i; 2414ec7775f6SShri Abhyankar 2415ec7775f6SShri Abhyankar PetscFunctionBegin; 2416ec7775f6SShri Abhyankar /* Set the number of nonzeros in the new matrix */ 2417ec7775f6SShri Abhyankar for(i=0; i<m; i++) { 24188af7cee1SJed Brown PetscInt j,k,nzx = xi[i+1] - xi[i],nzy = yi[i+1] - yi[i]; 24198af7cee1SJed Brown const PetscInt *xj = x->j+xi[i],*yj = y->j+yi[i]; 24208af7cee1SJed Brown nnz[i] = 0; 24218af7cee1SJed Brown for (j=0,k=0; j<nzx; j++) { /* Point in X */ 24228af7cee1SJed Brown for (; k<nzy && yj[k]<xj[j]; k++) nnz[i]++; /* Catch up to X */ 24238af7cee1SJed Brown if (k<nzy && yj[k]==xj[j]) k++; /* Skip duplicate */ 24248af7cee1SJed Brown nnz[i]++; 24258af7cee1SJed Brown } 24268af7cee1SJed Brown for (; k<nzy; k++) nnz[i]++; 2427ec7775f6SShri Abhyankar } 2428ec7775f6SShri Abhyankar PetscFunctionReturn(0); 2429ec7775f6SShri Abhyankar } 2430ec7775f6SShri Abhyankar 2431ec7775f6SShri Abhyankar #undef __FUNCT__ 2432ac90fabeSBarry Smith #define __FUNCT__ "MatAXPY_SeqAIJ" 2433f4df32b1SMatthew Knepley PetscErrorCode MatAXPY_SeqAIJ(Mat Y,PetscScalar a,Mat X,MatStructure str) 2434ac90fabeSBarry Smith { 2435dfbe8321SBarry Smith PetscErrorCode ierr; 243697f1f81fSBarry Smith PetscInt i; 2437ac90fabeSBarry Smith Mat_SeqAIJ *x = (Mat_SeqAIJ *)X->data,*y = (Mat_SeqAIJ *)Y->data; 24380805154bSBarry Smith PetscBLASInt one=1,bnz = PetscBLASIntCast(x->nz); 2439ac90fabeSBarry Smith 2440ac90fabeSBarry Smith PetscFunctionBegin; 2441ac90fabeSBarry Smith if (str == SAME_NONZERO_PATTERN) { 2442f4df32b1SMatthew Knepley PetscScalar alpha = a; 2443f4df32b1SMatthew Knepley BLASaxpy_(&bnz,&alpha,x->a,&one,y->a,&one); 2444c537a176SHong Zhang } else if (str == SUBSET_NONZERO_PATTERN) { /* nonzeros of X is a subset of Y's */ 2445a30b2313SHong Zhang if (y->xtoy && y->XtoY != X) { 2446a30b2313SHong Zhang ierr = PetscFree(y->xtoy);CHKERRQ(ierr); 2447a30b2313SHong Zhang ierr = MatDestroy(y->XtoY);CHKERRQ(ierr); 2448a30b2313SHong Zhang } 2449a30b2313SHong Zhang if (!y->xtoy) { /* get xtoy */ 2450d0f46423SBarry Smith ierr = MatAXPYGetxtoy_Private(X->rmap->n,x->i,x->j,PETSC_NULL, y->i,y->j,PETSC_NULL, &y->xtoy);CHKERRQ(ierr); 2451a30b2313SHong Zhang y->XtoY = X; 2452407f6b05SHong Zhang ierr = PetscObjectReference((PetscObject)X);CHKERRQ(ierr); 2453c537a176SHong Zhang } 2454f4df32b1SMatthew Knepley for (i=0; i<x->nz; i++) y->a[y->xtoy[i]] += a*(x->a[i]); 24551e2582c4SBarry Smith ierr = PetscInfo3(Y,"ratio of nnz(X)/nnz(Y): %d/%d = %G\n",x->nz,y->nz,(PetscReal)(x->nz)/y->nz);CHKERRQ(ierr); 2456ac90fabeSBarry Smith } else { 24578229c054SShri Abhyankar Mat B; 24588229c054SShri Abhyankar PetscInt *nnz; 245916b2e9dcSShri Abhyankar ierr = PetscMalloc(Y->rmap->N*sizeof(PetscInt),&nnz);CHKERRQ(ierr); 2460ec7775f6SShri Abhyankar ierr = MatCreate(((PetscObject)Y)->comm,&B);CHKERRQ(ierr); 2461bc5a2726SShri Abhyankar ierr = PetscObjectSetName((PetscObject)B,((PetscObject)Y)->name);CHKERRQ(ierr); 24624aa94f47SShri Abhyankar ierr = MatSetSizes(B,Y->rmap->n,Y->cmap->n,Y->rmap->N,Y->cmap->N);CHKERRQ(ierr); 2463ec7775f6SShri Abhyankar ierr = MatSetType(B,MATSEQAIJ);CHKERRQ(ierr); 24648229c054SShri Abhyankar ierr = MatAXPYGetPreallocation_SeqAIJ(Y,X,nnz);CHKERRQ(ierr); 24658229c054SShri Abhyankar ierr = MatSeqAIJSetPreallocation(B,PETSC_NULL,nnz);CHKERRQ(ierr); 2466ec7775f6SShri Abhyankar ierr = MatAXPY_BasicWithPreallocation(B,Y,a,X,str);CHKERRQ(ierr); 2467ec7775f6SShri Abhyankar ierr = MatHeaderReplace(Y,B);CHKERRQ(ierr); 24688229c054SShri Abhyankar ierr = PetscFree(nnz);CHKERRQ(ierr); 2469ac90fabeSBarry Smith } 2470ac90fabeSBarry Smith PetscFunctionReturn(0); 2471ac90fabeSBarry Smith } 2472ac90fabeSBarry Smith 2473521d7252SBarry Smith #undef __FUNCT__ 2474521d7252SBarry Smith #define __FUNCT__ "MatSetBlockSize_SeqAIJ" 2475521d7252SBarry Smith PetscErrorCode MatSetBlockSize_SeqAIJ(Mat A,PetscInt bs) 2476521d7252SBarry Smith { 247741c166b1SJed Brown PetscErrorCode ierr; 247841c166b1SJed Brown 2479521d7252SBarry Smith PetscFunctionBegin; 248041c166b1SJed Brown ierr = PetscLayoutSetBlockSize(A->rmap,bs);CHKERRQ(ierr); 248141c166b1SJed Brown ierr = PetscLayoutSetBlockSize(A->cmap,bs);CHKERRQ(ierr); 2482521d7252SBarry Smith PetscFunctionReturn(0); 2483521d7252SBarry Smith } 2484521d7252SBarry Smith 2485354c94deSBarry Smith #undef __FUNCT__ 2486354c94deSBarry Smith #define __FUNCT__ "MatConjugate_SeqAIJ" 24877087cfbeSBarry Smith PetscErrorCode MatConjugate_SeqAIJ(Mat mat) 2488354c94deSBarry Smith { 2489354c94deSBarry Smith #if defined(PETSC_USE_COMPLEX) 2490354c94deSBarry Smith Mat_SeqAIJ *aij = (Mat_SeqAIJ *)mat->data; 2491354c94deSBarry Smith PetscInt i,nz; 2492354c94deSBarry Smith PetscScalar *a; 2493354c94deSBarry Smith 2494354c94deSBarry Smith PetscFunctionBegin; 2495354c94deSBarry Smith nz = aij->nz; 2496354c94deSBarry Smith a = aij->a; 2497354c94deSBarry Smith for (i=0; i<nz; i++) { 2498354c94deSBarry Smith a[i] = PetscConj(a[i]); 2499354c94deSBarry Smith } 2500354c94deSBarry Smith #else 2501354c94deSBarry Smith PetscFunctionBegin; 2502354c94deSBarry Smith #endif 2503354c94deSBarry Smith PetscFunctionReturn(0); 2504354c94deSBarry Smith } 2505354c94deSBarry Smith 2506e34fafa9SBarry Smith #undef __FUNCT__ 2507985db425SBarry Smith #define __FUNCT__ "MatGetRowMaxAbs_SeqAIJ" 2508985db425SBarry Smith PetscErrorCode MatGetRowMaxAbs_SeqAIJ(Mat A,Vec v,PetscInt idx[]) 2509e34fafa9SBarry Smith { 2510e34fafa9SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 2511e34fafa9SBarry Smith PetscErrorCode ierr; 2512d0f46423SBarry Smith PetscInt i,j,m = A->rmap->n,*ai,*aj,ncols,n; 2513e34fafa9SBarry Smith PetscReal atmp; 2514985db425SBarry Smith PetscScalar *x; 2515e34fafa9SBarry Smith MatScalar *aa; 2516e34fafa9SBarry Smith 2517e34fafa9SBarry Smith PetscFunctionBegin; 2518e32f2f54SBarry Smith if (A->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2519e34fafa9SBarry Smith aa = a->a; 2520e34fafa9SBarry Smith ai = a->i; 2521e34fafa9SBarry Smith aj = a->j; 2522e34fafa9SBarry Smith 2523985db425SBarry Smith ierr = VecSet(v,0.0);CHKERRQ(ierr); 2524e34fafa9SBarry Smith ierr = VecGetArray(v,&x);CHKERRQ(ierr); 2525e34fafa9SBarry Smith ierr = VecGetLocalSize(v,&n);CHKERRQ(ierr); 2526e32f2f54SBarry Smith if (n != A->rmap->n) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Nonconforming matrix and vector"); 2527e34fafa9SBarry Smith for (i=0; i<m; i++) { 2528e34fafa9SBarry Smith ncols = ai[1] - ai[0]; ai++; 25299189402eSHong Zhang x[i] = 0.0; 2530e34fafa9SBarry Smith for (j=0; j<ncols; j++){ 2531985db425SBarry Smith atmp = PetscAbsScalar(*aa); 2532985db425SBarry Smith if (PetscAbsScalar(x[i]) < atmp) {x[i] = atmp; if (idx) idx[i] = *aj;} 2533985db425SBarry Smith aa++; aj++; 2534985db425SBarry Smith } 2535985db425SBarry Smith } 2536985db425SBarry Smith ierr = VecRestoreArray(v,&x);CHKERRQ(ierr); 2537985db425SBarry Smith PetscFunctionReturn(0); 2538985db425SBarry Smith } 2539985db425SBarry Smith 2540985db425SBarry Smith #undef __FUNCT__ 2541985db425SBarry Smith #define __FUNCT__ "MatGetRowMax_SeqAIJ" 2542985db425SBarry Smith PetscErrorCode MatGetRowMax_SeqAIJ(Mat A,Vec v,PetscInt idx[]) 2543985db425SBarry Smith { 2544985db425SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 2545985db425SBarry Smith PetscErrorCode ierr; 2546d0f46423SBarry Smith PetscInt i,j,m = A->rmap->n,*ai,*aj,ncols,n; 2547985db425SBarry Smith PetscScalar *x; 2548985db425SBarry Smith MatScalar *aa; 2549985db425SBarry Smith 2550985db425SBarry Smith PetscFunctionBegin; 2551e32f2f54SBarry Smith if (A->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2552985db425SBarry Smith aa = a->a; 2553985db425SBarry Smith ai = a->i; 2554985db425SBarry Smith aj = a->j; 2555985db425SBarry Smith 2556985db425SBarry Smith ierr = VecSet(v,0.0);CHKERRQ(ierr); 2557985db425SBarry Smith ierr = VecGetArray(v,&x);CHKERRQ(ierr); 2558985db425SBarry Smith ierr = VecGetLocalSize(v,&n);CHKERRQ(ierr); 2559e32f2f54SBarry Smith if (n != A->rmap->n) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Nonconforming matrix and vector"); 2560985db425SBarry Smith for (i=0; i<m; i++) { 2561985db425SBarry Smith ncols = ai[1] - ai[0]; ai++; 2562d0f46423SBarry Smith if (ncols == A->cmap->n) { /* row is dense */ 2563985db425SBarry Smith x[i] = *aa; if (idx) idx[i] = 0; 2564985db425SBarry Smith } else { /* row is sparse so already KNOW maximum is 0.0 or higher */ 2565985db425SBarry Smith x[i] = 0.0; 2566985db425SBarry Smith if (idx) { 2567985db425SBarry Smith idx[i] = 0; /* in case ncols is zero */ 2568985db425SBarry Smith for (j=0;j<ncols;j++) { /* find first implicit 0.0 in the row */ 2569985db425SBarry Smith if (aj[j] > j) { 2570985db425SBarry Smith idx[i] = j; 2571985db425SBarry Smith break; 2572985db425SBarry Smith } 2573985db425SBarry Smith } 2574985db425SBarry Smith } 2575985db425SBarry Smith } 2576985db425SBarry Smith for (j=0; j<ncols; j++){ 2577985db425SBarry Smith if (PetscRealPart(x[i]) < PetscRealPart(*aa)) {x[i] = *aa; if (idx) idx[i] = *aj;} 2578985db425SBarry Smith aa++; aj++; 2579985db425SBarry Smith } 2580985db425SBarry Smith } 2581985db425SBarry Smith ierr = VecRestoreArray(v,&x);CHKERRQ(ierr); 2582985db425SBarry Smith PetscFunctionReturn(0); 2583985db425SBarry Smith } 2584985db425SBarry Smith 2585985db425SBarry Smith #undef __FUNCT__ 2586c87e5d42SMatthew Knepley #define __FUNCT__ "MatGetRowMinAbs_SeqAIJ" 2587c87e5d42SMatthew Knepley PetscErrorCode MatGetRowMinAbs_SeqAIJ(Mat A,Vec v,PetscInt idx[]) 2588c87e5d42SMatthew Knepley { 2589c87e5d42SMatthew Knepley Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 2590c87e5d42SMatthew Knepley PetscErrorCode ierr; 2591c87e5d42SMatthew Knepley PetscInt i,j,m = A->rmap->n,*ai,*aj,ncols,n; 2592c87e5d42SMatthew Knepley PetscReal atmp; 2593c87e5d42SMatthew Knepley PetscScalar *x; 2594c87e5d42SMatthew Knepley MatScalar *aa; 2595c87e5d42SMatthew Knepley 2596c87e5d42SMatthew Knepley PetscFunctionBegin; 2597e32f2f54SBarry Smith if (A->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2598c87e5d42SMatthew Knepley aa = a->a; 2599c87e5d42SMatthew Knepley ai = a->i; 2600c87e5d42SMatthew Knepley aj = a->j; 2601c87e5d42SMatthew Knepley 2602c87e5d42SMatthew Knepley ierr = VecSet(v,0.0);CHKERRQ(ierr); 2603c87e5d42SMatthew Knepley ierr = VecGetArray(v,&x);CHKERRQ(ierr); 2604c87e5d42SMatthew Knepley ierr = VecGetLocalSize(v,&n);CHKERRQ(ierr); 2605e32f2f54SBarry Smith if (n != A->rmap->n) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Nonconforming matrix and vector"); 2606c87e5d42SMatthew Knepley for (i=0; i<m; i++) { 2607c87e5d42SMatthew Knepley ncols = ai[1] - ai[0]; ai++; 2608289a08f5SMatthew Knepley if (ncols) { 2609289a08f5SMatthew Knepley /* Get first nonzero */ 2610289a08f5SMatthew Knepley for(j = 0; j < ncols; j++) { 2611289a08f5SMatthew Knepley atmp = PetscAbsScalar(aa[j]); 2612289a08f5SMatthew Knepley if (atmp > 1.0e-12) {x[i] = atmp; if (idx) idx[i] = aj[j]; break;} 2613289a08f5SMatthew Knepley } 2614289a08f5SMatthew Knepley if (j == ncols) {x[i] = *aa; if (idx) idx[i] = *aj;} 2615289a08f5SMatthew Knepley } else { 2616289a08f5SMatthew Knepley x[i] = 0.0; if (idx) idx[i] = 0; 2617289a08f5SMatthew Knepley } 2618c87e5d42SMatthew Knepley for(j = 0; j < ncols; j++) { 2619c87e5d42SMatthew Knepley atmp = PetscAbsScalar(*aa); 2620289a08f5SMatthew Knepley if (atmp > 1.0e-12 && PetscAbsScalar(x[i]) > atmp) {x[i] = atmp; if (idx) idx[i] = *aj;} 2621c87e5d42SMatthew Knepley aa++; aj++; 2622c87e5d42SMatthew Knepley } 2623c87e5d42SMatthew Knepley } 2624c87e5d42SMatthew Knepley ierr = VecRestoreArray(v,&x);CHKERRQ(ierr); 2625c87e5d42SMatthew Knepley PetscFunctionReturn(0); 2626c87e5d42SMatthew Knepley } 2627c87e5d42SMatthew Knepley 2628c87e5d42SMatthew Knepley #undef __FUNCT__ 2629985db425SBarry Smith #define __FUNCT__ "MatGetRowMin_SeqAIJ" 2630985db425SBarry Smith PetscErrorCode MatGetRowMin_SeqAIJ(Mat A,Vec v,PetscInt idx[]) 2631985db425SBarry Smith { 2632985db425SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 2633985db425SBarry Smith PetscErrorCode ierr; 2634d0f46423SBarry Smith PetscInt i,j,m = A->rmap->n,*ai,*aj,ncols,n; 2635985db425SBarry Smith PetscScalar *x; 2636985db425SBarry Smith MatScalar *aa; 2637985db425SBarry Smith 2638985db425SBarry Smith PetscFunctionBegin; 2639e32f2f54SBarry Smith if (A->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2640985db425SBarry Smith aa = a->a; 2641985db425SBarry Smith ai = a->i; 2642985db425SBarry Smith aj = a->j; 2643985db425SBarry Smith 2644985db425SBarry Smith ierr = VecSet(v,0.0);CHKERRQ(ierr); 2645985db425SBarry Smith ierr = VecGetArray(v,&x);CHKERRQ(ierr); 2646985db425SBarry Smith ierr = VecGetLocalSize(v,&n);CHKERRQ(ierr); 2647e32f2f54SBarry Smith if (n != A->rmap->n) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Nonconforming matrix and vector"); 2648985db425SBarry Smith for (i=0; i<m; i++) { 2649985db425SBarry Smith ncols = ai[1] - ai[0]; ai++; 2650d0f46423SBarry Smith if (ncols == A->cmap->n) { /* row is dense */ 2651985db425SBarry Smith x[i] = *aa; if (idx) idx[i] = 0; 2652985db425SBarry Smith } else { /* row is sparse so already KNOW minimum is 0.0 or lower */ 2653985db425SBarry Smith x[i] = 0.0; 2654985db425SBarry Smith if (idx) { /* find first implicit 0.0 in the row */ 2655985db425SBarry Smith idx[i] = 0; /* in case ncols is zero */ 2656985db425SBarry Smith for (j=0;j<ncols;j++) { 2657985db425SBarry Smith if (aj[j] > j) { 2658985db425SBarry Smith idx[i] = j; 2659985db425SBarry Smith break; 2660985db425SBarry Smith } 2661985db425SBarry Smith } 2662985db425SBarry Smith } 2663985db425SBarry Smith } 2664985db425SBarry Smith for (j=0; j<ncols; j++){ 2665985db425SBarry Smith if (PetscRealPart(x[i]) > PetscRealPart(*aa)) {x[i] = *aa; if (idx) idx[i] = *aj;} 2666985db425SBarry Smith aa++; aj++; 2667e34fafa9SBarry Smith } 2668e34fafa9SBarry Smith } 2669e34fafa9SBarry Smith ierr = VecRestoreArray(v,&x);CHKERRQ(ierr); 2670e34fafa9SBarry Smith PetscFunctionReturn(0); 2671e34fafa9SBarry Smith } 26727087cfbeSBarry Smith extern PetscErrorCode MatFDColoringApply_AIJ(Mat,MatFDColoring,Vec,MatStructure*,void*); 2673682d7d0cSBarry Smith /* -------------------------------------------------------------------*/ 26740a6ffc59SBarry Smith static struct _MatOps MatOps_Values = {MatSetValues_SeqAIJ, 2675cb5b572fSBarry Smith MatGetRow_SeqAIJ, 2676cb5b572fSBarry Smith MatRestoreRow_SeqAIJ, 2677cb5b572fSBarry Smith MatMult_SeqAIJ, 267897304618SKris Buschelman /* 4*/ MatMultAdd_SeqAIJ, 26797c922b88SBarry Smith MatMultTranspose_SeqAIJ, 26807c922b88SBarry Smith MatMultTransposeAdd_SeqAIJ, 2681db4efbfdSBarry Smith 0, 2682db4efbfdSBarry Smith 0, 2683db4efbfdSBarry Smith 0, 2684db4efbfdSBarry Smith /*10*/ 0, 2685cb5b572fSBarry Smith MatLUFactor_SeqAIJ, 2686cb5b572fSBarry Smith 0, 268741f059aeSBarry Smith MatSOR_SeqAIJ, 268817ab2063SBarry Smith MatTranspose_SeqAIJ, 268997304618SKris Buschelman /*15*/ MatGetInfo_SeqAIJ, 2690cb5b572fSBarry Smith MatEqual_SeqAIJ, 2691cb5b572fSBarry Smith MatGetDiagonal_SeqAIJ, 2692cb5b572fSBarry Smith MatDiagonalScale_SeqAIJ, 2693cb5b572fSBarry Smith MatNorm_SeqAIJ, 269497304618SKris Buschelman /*20*/ 0, 2695cb5b572fSBarry Smith MatAssemblyEnd_SeqAIJ, 2696cb5b572fSBarry Smith MatSetOption_SeqAIJ, 2697cb5b572fSBarry Smith MatZeroEntries_SeqAIJ, 2698d519adbfSMatthew Knepley /*24*/ MatZeroRows_SeqAIJ, 2699db4efbfdSBarry Smith 0, 2700db4efbfdSBarry Smith 0, 2701db4efbfdSBarry Smith 0, 2702db4efbfdSBarry Smith 0, 2703d519adbfSMatthew Knepley /*29*/ MatSetUpPreallocation_SeqAIJ, 2704db4efbfdSBarry Smith 0, 2705db4efbfdSBarry Smith 0, 27066c0721eeSBarry Smith MatGetArray_SeqAIJ, 27076c0721eeSBarry Smith MatRestoreArray_SeqAIJ, 2708d519adbfSMatthew Knepley /*34*/ MatDuplicate_SeqAIJ, 2709cb5b572fSBarry Smith 0, 2710cb5b572fSBarry Smith 0, 2711cb5b572fSBarry Smith MatILUFactor_SeqAIJ, 2712cb5b572fSBarry Smith 0, 2713d519adbfSMatthew Knepley /*39*/ MatAXPY_SeqAIJ, 2714cb5b572fSBarry Smith MatGetSubMatrices_SeqAIJ, 2715cb5b572fSBarry Smith MatIncreaseOverlap_SeqAIJ, 2716cb5b572fSBarry Smith MatGetValues_SeqAIJ, 2717cb5b572fSBarry Smith MatCopy_SeqAIJ, 2718d519adbfSMatthew Knepley /*44*/ MatGetRowMax_SeqAIJ, 2719cb5b572fSBarry Smith MatScale_SeqAIJ, 2720cb5b572fSBarry Smith 0, 272179299369SBarry Smith MatDiagonalSet_SeqAIJ, 27226e169961SBarry Smith MatZeroRowsColumns_SeqAIJ, 2723d519adbfSMatthew Knepley /*49*/ MatSetBlockSize_SeqAIJ, 27243b2fbd54SBarry Smith MatGetRowIJ_SeqAIJ, 27253b2fbd54SBarry Smith MatRestoreRowIJ_SeqAIJ, 27263b2fbd54SBarry Smith MatGetColumnIJ_SeqAIJ, 2727a93ec695SBarry Smith MatRestoreColumnIJ_SeqAIJ, 2728d519adbfSMatthew Knepley /*54*/ MatFDColoringCreate_SeqAIJ, 2729b9617806SBarry Smith 0, 27300513a670SBarry Smith 0, 2731cda55fadSBarry Smith MatPermute_SeqAIJ, 2732cda55fadSBarry Smith 0, 2733d519adbfSMatthew Knepley /*59*/ 0, 2734b9b97703SBarry Smith MatDestroy_SeqAIJ, 2735b9b97703SBarry Smith MatView_SeqAIJ, 2736357abbc8SBarry Smith 0, 2737ee4f033dSBarry Smith 0, 2738d519adbfSMatthew Knepley /*64*/ 0, 2739ee4f033dSBarry Smith 0, 2740ee4f033dSBarry Smith 0, 2741ee4f033dSBarry Smith 0, 2742ee4f033dSBarry Smith 0, 2743d519adbfSMatthew Knepley /*69*/ MatGetRowMaxAbs_SeqAIJ, 2744c87e5d42SMatthew Knepley MatGetRowMinAbs_SeqAIJ, 2745ee4f033dSBarry Smith 0, 2746ee4f033dSBarry Smith MatSetColoring_SeqAIJ, 2747dcf5cc72SBarry Smith #if defined(PETSC_HAVE_ADIC) 2748ee4f033dSBarry Smith MatSetValuesAdic_SeqAIJ, 2749dcf5cc72SBarry Smith #else 2750dcf5cc72SBarry Smith 0, 2751dcf5cc72SBarry Smith #endif 2752d519adbfSMatthew Knepley /*74*/ MatSetValuesAdifor_SeqAIJ, 27533acb8795SBarry Smith MatFDColoringApply_AIJ, 275497304618SKris Buschelman 0, 275597304618SKris Buschelman 0, 275697304618SKris Buschelman 0, 2757d519adbfSMatthew Knepley /*79*/ 0, 275897304618SKris Buschelman 0, 275997304618SKris Buschelman 0, 276097304618SKris Buschelman 0, 2761bc011b1eSHong Zhang MatLoad_SeqAIJ, 2762d519adbfSMatthew Knepley /*84*/ MatIsSymmetric_SeqAIJ, 27631cbb95d3SBarry Smith MatIsHermitian_SeqAIJ, 27646284ec50SHong Zhang 0, 27656284ec50SHong Zhang 0, 2766bc011b1eSHong Zhang 0, 2767d519adbfSMatthew Knepley /*89*/ MatMatMult_SeqAIJ_SeqAIJ, 276826be0446SHong Zhang MatMatMultSymbolic_SeqAIJ_SeqAIJ, 276926be0446SHong Zhang MatMatMultNumeric_SeqAIJ_SeqAIJ, 2770d439da42SKris Buschelman MatPtAP_Basic, 27717ba1a0bfSKris Buschelman MatPtAPSymbolic_SeqAIJ, 2772d519adbfSMatthew Knepley /*94*/ MatPtAPNumeric_SeqAIJ, 2773bc011b1eSHong Zhang MatMatMultTranspose_SeqAIJ_SeqAIJ, 2774bc011b1eSHong Zhang MatMatMultTransposeSymbolic_SeqAIJ_SeqAIJ, 2775bc011b1eSHong Zhang MatMatMultTransposeNumeric_SeqAIJ_SeqAIJ, 27767ba1a0bfSKris Buschelman MatPtAPSymbolic_SeqAIJ_SeqAIJ, 2777d519adbfSMatthew Knepley /*99*/ MatPtAPNumeric_SeqAIJ_SeqAIJ, 2778609c6c4dSKris Buschelman 0, 2779609c6c4dSKris Buschelman 0, 278087d4246cSBarry Smith MatConjugate_SeqAIJ, 278187d4246cSBarry Smith 0, 2782d519adbfSMatthew Knepley /*104*/MatSetValuesRow_SeqAIJ, 278399cafbc1SBarry Smith MatRealPart_SeqAIJ, 2784f5edf698SHong Zhang MatImaginaryPart_SeqAIJ, 2785f5edf698SHong Zhang 0, 27862bebee5dSHong Zhang 0, 2787d519adbfSMatthew Knepley /*109*/0, 2788985db425SBarry Smith 0, 27892af78befSBarry Smith MatGetRowMin_SeqAIJ, 27902af78befSBarry Smith 0, 2791599ef60dSHong Zhang MatMissingDiagonal_SeqAIJ, 2792d519adbfSMatthew Knepley /*114*/0, 2793599ef60dSHong Zhang 0, 27943c2a7987SHong Zhang 0, 2795fe97e370SBarry Smith 0, 2796fbdbba38SShri Abhyankar 0, 2797fbdbba38SShri Abhyankar /*119*/0, 2798fbdbba38SShri Abhyankar 0, 2799fbdbba38SShri Abhyankar 0, 280082d44351SHong Zhang 0, 2801*b3a44c85SBarry Smith MatGetMultiProcBlock_SeqAIJ, 2802*b3a44c85SBarry Smith /*124*/MatFindNonzeroRows_SeqAIJ 28039e29f15eSvictorle }; 280417ab2063SBarry Smith 2805fb2e594dSBarry Smith EXTERN_C_BEGIN 28064a2ae208SSatish Balay #undef __FUNCT__ 28074a2ae208SSatish Balay #define __FUNCT__ "MatSeqAIJSetColumnIndices_SeqAIJ" 28087087cfbeSBarry Smith PetscErrorCode MatSeqAIJSetColumnIndices_SeqAIJ(Mat mat,PetscInt *indices) 2809bef8e0ddSBarry Smith { 2810bef8e0ddSBarry Smith Mat_SeqAIJ *aij = (Mat_SeqAIJ *)mat->data; 281197f1f81fSBarry Smith PetscInt i,nz,n; 2812bef8e0ddSBarry Smith 2813bef8e0ddSBarry Smith PetscFunctionBegin; 2814bef8e0ddSBarry Smith 2815bef8e0ddSBarry Smith nz = aij->maxnz; 2816d0f46423SBarry Smith n = mat->rmap->n; 2817bef8e0ddSBarry Smith for (i=0; i<nz; i++) { 2818bef8e0ddSBarry Smith aij->j[i] = indices[i]; 2819bef8e0ddSBarry Smith } 2820bef8e0ddSBarry Smith aij->nz = nz; 2821bef8e0ddSBarry Smith for (i=0; i<n; i++) { 2822bef8e0ddSBarry Smith aij->ilen[i] = aij->imax[i]; 2823bef8e0ddSBarry Smith } 2824bef8e0ddSBarry Smith 2825bef8e0ddSBarry Smith PetscFunctionReturn(0); 2826bef8e0ddSBarry Smith } 2827fb2e594dSBarry Smith EXTERN_C_END 2828bef8e0ddSBarry Smith 28294a2ae208SSatish Balay #undef __FUNCT__ 28304a2ae208SSatish Balay #define __FUNCT__ "MatSeqAIJSetColumnIndices" 2831bef8e0ddSBarry Smith /*@ 2832bef8e0ddSBarry Smith MatSeqAIJSetColumnIndices - Set the column indices for all the rows 2833bef8e0ddSBarry Smith in the matrix. 2834bef8e0ddSBarry Smith 2835bef8e0ddSBarry Smith Input Parameters: 2836bef8e0ddSBarry Smith + mat - the SeqAIJ matrix 2837bef8e0ddSBarry Smith - indices - the column indices 2838bef8e0ddSBarry Smith 283915091d37SBarry Smith Level: advanced 284015091d37SBarry Smith 2841bef8e0ddSBarry Smith Notes: 2842bef8e0ddSBarry Smith This can be called if you have precomputed the nonzero structure of the 2843bef8e0ddSBarry Smith matrix and want to provide it to the matrix object to improve the performance 2844bef8e0ddSBarry Smith of the MatSetValues() operation. 2845bef8e0ddSBarry Smith 2846bef8e0ddSBarry Smith You MUST have set the correct numbers of nonzeros per row in the call to 2847d1be2dadSMatthew Knepley MatCreateSeqAIJ(), and the columns indices MUST be sorted. 2848bef8e0ddSBarry Smith 2849bef8e0ddSBarry Smith MUST be called before any calls to MatSetValues(); 2850bef8e0ddSBarry Smith 2851b9617806SBarry Smith The indices should start with zero, not one. 2852b9617806SBarry Smith 2853bef8e0ddSBarry Smith @*/ 28547087cfbeSBarry Smith PetscErrorCode MatSeqAIJSetColumnIndices(Mat mat,PetscInt *indices) 2855bef8e0ddSBarry Smith { 28564ac538c5SBarry Smith PetscErrorCode ierr; 2857bef8e0ddSBarry Smith 2858bef8e0ddSBarry Smith PetscFunctionBegin; 28590700a824SBarry Smith PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 28604482741eSBarry Smith PetscValidPointer(indices,2); 28614ac538c5SBarry Smith ierr = PetscUseMethod(mat,"MatSeqAIJSetColumnIndices_C",(Mat,PetscInt *),(mat,indices));CHKERRQ(ierr); 2862bef8e0ddSBarry Smith PetscFunctionReturn(0); 2863bef8e0ddSBarry Smith } 2864bef8e0ddSBarry Smith 2865be6bf707SBarry Smith /* ----------------------------------------------------------------------------------------*/ 2866be6bf707SBarry Smith 2867fb2e594dSBarry Smith EXTERN_C_BEGIN 28684a2ae208SSatish Balay #undef __FUNCT__ 28694a2ae208SSatish Balay #define __FUNCT__ "MatStoreValues_SeqAIJ" 28707087cfbeSBarry Smith PetscErrorCode MatStoreValues_SeqAIJ(Mat mat) 2871be6bf707SBarry Smith { 2872be6bf707SBarry Smith Mat_SeqAIJ *aij = (Mat_SeqAIJ *)mat->data; 28736849ba73SBarry Smith PetscErrorCode ierr; 2874d0f46423SBarry Smith size_t nz = aij->i[mat->rmap->n]; 2875be6bf707SBarry Smith 2876be6bf707SBarry Smith PetscFunctionBegin; 2877be6bf707SBarry Smith if (aij->nonew != 1) { 2878e32f2f54SBarry Smith SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ORDER,"Must call MatSetOption(A,MAT_NEW_NONZERO_LOCATIONS,PETSC_FALSE);first"); 2879be6bf707SBarry Smith } 2880be6bf707SBarry Smith 2881be6bf707SBarry Smith /* allocate space for values if not already there */ 2882be6bf707SBarry Smith if (!aij->saved_values) { 288387828ca2SBarry Smith ierr = PetscMalloc((nz+1)*sizeof(PetscScalar),&aij->saved_values);CHKERRQ(ierr); 28849518dbb4SMatthew Knepley ierr = PetscLogObjectMemory(mat,(nz+1)*sizeof(PetscScalar));CHKERRQ(ierr); 2885be6bf707SBarry Smith } 2886be6bf707SBarry Smith 2887be6bf707SBarry Smith /* copy values over */ 288887828ca2SBarry Smith ierr = PetscMemcpy(aij->saved_values,aij->a,nz*sizeof(PetscScalar));CHKERRQ(ierr); 2889be6bf707SBarry Smith PetscFunctionReturn(0); 2890be6bf707SBarry Smith } 2891fb2e594dSBarry Smith EXTERN_C_END 2892be6bf707SBarry Smith 28934a2ae208SSatish Balay #undef __FUNCT__ 2894b9617806SBarry Smith #define __FUNCT__ "MatStoreValues" 2895be6bf707SBarry Smith /*@ 2896be6bf707SBarry Smith MatStoreValues - Stashes a copy of the matrix values; this allows, for 2897be6bf707SBarry Smith example, reuse of the linear part of a Jacobian, while recomputing the 2898be6bf707SBarry Smith nonlinear portion. 2899be6bf707SBarry Smith 2900be6bf707SBarry Smith Collect on Mat 2901be6bf707SBarry Smith 2902be6bf707SBarry Smith Input Parameters: 29030e609b76SBarry Smith . mat - the matrix (currently only AIJ matrices support this option) 2904be6bf707SBarry Smith 290515091d37SBarry Smith Level: advanced 290615091d37SBarry Smith 2907be6bf707SBarry Smith Common Usage, with SNESSolve(): 2908be6bf707SBarry Smith $ Create Jacobian matrix 2909be6bf707SBarry Smith $ Set linear terms into matrix 2910be6bf707SBarry Smith $ Apply boundary conditions to matrix, at this time matrix must have 2911be6bf707SBarry Smith $ final nonzero structure (i.e. setting the nonlinear terms and applying 2912be6bf707SBarry Smith $ boundary conditions again will not change the nonzero structure 2913512a5fc5SBarry Smith $ ierr = MatSetOption(mat,MAT_NEW_NONZERO_LOCATIONS,PETSC_FALSE); 2914be6bf707SBarry Smith $ ierr = MatStoreValues(mat); 2915be6bf707SBarry Smith $ Call SNESSetJacobian() with matrix 2916be6bf707SBarry Smith $ In your Jacobian routine 2917be6bf707SBarry Smith $ ierr = MatRetrieveValues(mat); 2918be6bf707SBarry Smith $ Set nonlinear terms in matrix 2919be6bf707SBarry Smith 2920be6bf707SBarry Smith Common Usage without SNESSolve(), i.e. when you handle nonlinear solve yourself: 2921be6bf707SBarry Smith $ // build linear portion of Jacobian 2922512a5fc5SBarry Smith $ ierr = MatSetOption(mat,MAT_NEW_NONZERO_LOCATIONS,PETSC_FALSE); 2923be6bf707SBarry Smith $ ierr = MatStoreValues(mat); 2924be6bf707SBarry Smith $ loop over nonlinear iterations 2925be6bf707SBarry Smith $ ierr = MatRetrieveValues(mat); 2926be6bf707SBarry Smith $ // call MatSetValues(mat,...) to set nonliner portion of Jacobian 2927be6bf707SBarry Smith $ // call MatAssemblyBegin/End() on matrix 2928be6bf707SBarry Smith $ Solve linear system with Jacobian 2929be6bf707SBarry Smith $ endloop 2930be6bf707SBarry Smith 2931be6bf707SBarry Smith Notes: 2932be6bf707SBarry Smith Matrix must already be assemblied before calling this routine 2933512a5fc5SBarry Smith Must set the matrix option MatSetOption(mat,MAT_NEW_NONZERO_LOCATIONS,PETSC_FALSE); before 2934be6bf707SBarry Smith calling this routine. 2935be6bf707SBarry Smith 29360c468ba9SBarry Smith When this is called multiple times it overwrites the previous set of stored values 29370c468ba9SBarry Smith and does not allocated additional space. 29380c468ba9SBarry Smith 2939be6bf707SBarry Smith .seealso: MatRetrieveValues() 2940be6bf707SBarry Smith 2941be6bf707SBarry Smith @*/ 29427087cfbeSBarry Smith PetscErrorCode MatStoreValues(Mat mat) 2943be6bf707SBarry Smith { 29444ac538c5SBarry Smith PetscErrorCode ierr; 2945be6bf707SBarry Smith 2946be6bf707SBarry Smith PetscFunctionBegin; 29470700a824SBarry Smith PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2948e32f2f54SBarry Smith if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2949e32f2f54SBarry Smith if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 29504ac538c5SBarry Smith ierr = PetscUseMethod(mat,"MatStoreValues_C",(Mat),(mat));CHKERRQ(ierr); 2951be6bf707SBarry Smith PetscFunctionReturn(0); 2952be6bf707SBarry Smith } 2953be6bf707SBarry Smith 2954fb2e594dSBarry Smith EXTERN_C_BEGIN 29554a2ae208SSatish Balay #undef __FUNCT__ 29564a2ae208SSatish Balay #define __FUNCT__ "MatRetrieveValues_SeqAIJ" 29577087cfbeSBarry Smith PetscErrorCode MatRetrieveValues_SeqAIJ(Mat mat) 2958be6bf707SBarry Smith { 2959be6bf707SBarry Smith Mat_SeqAIJ *aij = (Mat_SeqAIJ *)mat->data; 29606849ba73SBarry Smith PetscErrorCode ierr; 2961d0f46423SBarry Smith PetscInt nz = aij->i[mat->rmap->n]; 2962be6bf707SBarry Smith 2963be6bf707SBarry Smith PetscFunctionBegin; 2964be6bf707SBarry Smith if (aij->nonew != 1) { 2965e32f2f54SBarry Smith SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ORDER,"Must call MatSetOption(A,MAT_NEW_NONZERO_LOCATIONS,PETSC_FALSE);first"); 2966be6bf707SBarry Smith } 2967be6bf707SBarry Smith if (!aij->saved_values) { 2968e32f2f54SBarry Smith SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ORDER,"Must call MatStoreValues(A);first"); 2969be6bf707SBarry Smith } 2970be6bf707SBarry Smith /* copy values over */ 297187828ca2SBarry Smith ierr = PetscMemcpy(aij->a,aij->saved_values,nz*sizeof(PetscScalar));CHKERRQ(ierr); 2972be6bf707SBarry Smith PetscFunctionReturn(0); 2973be6bf707SBarry Smith } 2974fb2e594dSBarry Smith EXTERN_C_END 2975be6bf707SBarry Smith 29764a2ae208SSatish Balay #undef __FUNCT__ 29774a2ae208SSatish Balay #define __FUNCT__ "MatRetrieveValues" 2978be6bf707SBarry Smith /*@ 2979be6bf707SBarry Smith MatRetrieveValues - Retrieves the copy of the matrix values; this allows, for 2980be6bf707SBarry Smith example, reuse of the linear part of a Jacobian, while recomputing the 2981be6bf707SBarry Smith nonlinear portion. 2982be6bf707SBarry Smith 2983be6bf707SBarry Smith Collect on Mat 2984be6bf707SBarry Smith 2985be6bf707SBarry Smith Input Parameters: 2986be6bf707SBarry Smith . mat - the matrix (currently on AIJ matrices support this option) 2987be6bf707SBarry Smith 298815091d37SBarry Smith Level: advanced 298915091d37SBarry Smith 2990be6bf707SBarry Smith .seealso: MatStoreValues() 2991be6bf707SBarry Smith 2992be6bf707SBarry Smith @*/ 29937087cfbeSBarry Smith PetscErrorCode MatRetrieveValues(Mat mat) 2994be6bf707SBarry Smith { 29954ac538c5SBarry Smith PetscErrorCode ierr; 2996be6bf707SBarry Smith 2997be6bf707SBarry Smith PetscFunctionBegin; 29980700a824SBarry Smith PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2999e32f2f54SBarry Smith if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 3000e32f2f54SBarry Smith if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 30014ac538c5SBarry Smith ierr = PetscUseMethod(mat,"MatRetrieveValues_C",(Mat),(mat));CHKERRQ(ierr); 3002be6bf707SBarry Smith PetscFunctionReturn(0); 3003be6bf707SBarry Smith } 3004be6bf707SBarry Smith 3005f83d6046SBarry Smith 3006be6bf707SBarry Smith /* --------------------------------------------------------------------------------*/ 30074a2ae208SSatish Balay #undef __FUNCT__ 30084a2ae208SSatish Balay #define __FUNCT__ "MatCreateSeqAIJ" 300917ab2063SBarry Smith /*@C 3010682d7d0cSBarry Smith MatCreateSeqAIJ - Creates a sparse matrix in AIJ (compressed row) format 30110d15e28bSLois Curfman McInnes (the default parallel PETSc format). For good matrix assembly performance 30126e62573dSLois Curfman McInnes the user should preallocate the matrix storage by setting the parameter nz 301351c19458SBarry Smith (or the array nnz). By setting these parameters accurately, performance 30142bd5e0b2SLois Curfman McInnes during matrix assembly can be increased by more than a factor of 50. 301517ab2063SBarry Smith 3016db81eaa0SLois Curfman McInnes Collective on MPI_Comm 3017db81eaa0SLois Curfman McInnes 301817ab2063SBarry Smith Input Parameters: 3019db81eaa0SLois Curfman McInnes + comm - MPI communicator, set to PETSC_COMM_SELF 302017ab2063SBarry Smith . m - number of rows 302117ab2063SBarry Smith . n - number of columns 302217ab2063SBarry Smith . nz - number of nonzeros per row (same for all rows) 302351c19458SBarry Smith - nnz - array containing the number of nonzeros in the various rows 30242bd5e0b2SLois Curfman McInnes (possibly different for each row) or PETSC_NULL 302517ab2063SBarry Smith 302617ab2063SBarry Smith Output Parameter: 3027416022c9SBarry Smith . A - the matrix 302817ab2063SBarry Smith 3029175b88e8SBarry Smith It is recommended that one use the MatCreate(), MatSetType() and/or MatSetFromOptions(), 3030ae1d86c5SBarry Smith MatXXXXSetPreallocation() paradgm instead of this routine directly. 3031175b88e8SBarry Smith [MatXXXXSetPreallocation() is, for example, MatSeqAIJSetPreallocation] 3032175b88e8SBarry Smith 3033b259b22eSLois Curfman McInnes Notes: 303449a6f317SBarry Smith If nnz is given then nz is ignored 303549a6f317SBarry Smith 303617ab2063SBarry Smith The AIJ format (also called the Yale sparse matrix format or 303717ab2063SBarry Smith compressed row storage), is fully compatible with standard Fortran 77 30380002213bSLois Curfman McInnes storage. That is, the stored row and column indices can begin at 303944cd7ae7SLois Curfman McInnes either one (as in Fortran) or zero. See the users' manual for details. 304017ab2063SBarry Smith 304117ab2063SBarry Smith Specify the preallocated storage with either nz or nnz (not both). 3042a40aa06bSLois Curfman McInnes Set nz=PETSC_DEFAULT and nnz=PETSC_NULL for PETSc to control dynamic memory 30433d323bbdSBarry Smith allocation. For large problems you MUST preallocate memory or you 30446da5968aSLois Curfman McInnes will get TERRIBLE performance, see the users' manual chapter on matrices. 304517ab2063SBarry Smith 3046682d7d0cSBarry Smith By default, this format uses inodes (identical nodes) when possible, to 30474fca80b9SLois Curfman McInnes improve numerical efficiency of matrix-vector products and solves. We 3048682d7d0cSBarry Smith search for consecutive rows with the same nonzero structure, thereby 30496c7ebb05SLois Curfman McInnes reusing matrix information to achieve increased efficiency. 30506c7ebb05SLois Curfman McInnes 30516c7ebb05SLois Curfman McInnes Options Database Keys: 3052698d4c6aSKris Buschelman + -mat_no_inode - Do not use inodes 30539db58ca8SBarry Smith - -mat_inode_limit <limit> - Sets inode limit (max limit=5) 305417ab2063SBarry Smith 3055027ccd11SLois Curfman McInnes Level: intermediate 3056027ccd11SLois Curfman McInnes 305736db0b34SBarry Smith .seealso: MatCreate(), MatCreateMPIAIJ(), MatSetValues(), MatSeqAIJSetColumnIndices(), MatCreateSeqAIJWithArrays() 305836db0b34SBarry Smith 305917ab2063SBarry Smith @*/ 30607087cfbeSBarry Smith PetscErrorCode MatCreateSeqAIJ(MPI_Comm comm,PetscInt m,PetscInt n,PetscInt nz,const PetscInt nnz[],Mat *A) 306117ab2063SBarry Smith { 3062dfbe8321SBarry Smith PetscErrorCode ierr; 30636945ee14SBarry Smith 30643a40ed3dSBarry Smith PetscFunctionBegin; 3065f69a0ea3SMatthew Knepley ierr = MatCreate(comm,A);CHKERRQ(ierr); 3066117016b1SBarry Smith ierr = MatSetSizes(*A,m,n,m,n);CHKERRQ(ierr); 3067c4752a88SBarry Smith ierr = MatSetType(*A,MATSEQAIJ);CHKERRQ(ierr); 3068d28bb7d2SJed Brown ierr = MatSeqAIJSetPreallocation_SeqAIJ(*A,nz,nnz);CHKERRQ(ierr); 3069273d9f13SBarry Smith PetscFunctionReturn(0); 3070273d9f13SBarry Smith } 3071273d9f13SBarry Smith 30724a2ae208SSatish Balay #undef __FUNCT__ 30734a2ae208SSatish Balay #define __FUNCT__ "MatSeqAIJSetPreallocation" 3074273d9f13SBarry Smith /*@C 3075273d9f13SBarry Smith MatSeqAIJSetPreallocation - For good matrix assembly performance 3076273d9f13SBarry Smith the user should preallocate the matrix storage by setting the parameter nz 3077273d9f13SBarry Smith (or the array nnz). By setting these parameters accurately, performance 3078273d9f13SBarry Smith during matrix assembly can be increased by more than a factor of 50. 3079273d9f13SBarry Smith 3080273d9f13SBarry Smith Collective on MPI_Comm 3081273d9f13SBarry Smith 3082273d9f13SBarry Smith Input Parameters: 3083117016b1SBarry Smith + B - The matrix-free 3084273d9f13SBarry Smith . nz - number of nonzeros per row (same for all rows) 3085273d9f13SBarry Smith - nnz - array containing the number of nonzeros in the various rows 3086273d9f13SBarry Smith (possibly different for each row) or PETSC_NULL 3087273d9f13SBarry Smith 3088273d9f13SBarry Smith Notes: 308949a6f317SBarry Smith If nnz is given then nz is ignored 309049a6f317SBarry Smith 3091273d9f13SBarry Smith The AIJ format (also called the Yale sparse matrix format or 3092273d9f13SBarry Smith compressed row storage), is fully compatible with standard Fortran 77 3093273d9f13SBarry Smith storage. That is, the stored row and column indices can begin at 3094273d9f13SBarry Smith either one (as in Fortran) or zero. See the users' manual for details. 3095273d9f13SBarry Smith 3096273d9f13SBarry Smith Specify the preallocated storage with either nz or nnz (not both). 3097273d9f13SBarry Smith Set nz=PETSC_DEFAULT and nnz=PETSC_NULL for PETSc to control dynamic memory 3098273d9f13SBarry Smith allocation. For large problems you MUST preallocate memory or you 3099273d9f13SBarry Smith will get TERRIBLE performance, see the users' manual chapter on matrices. 3100273d9f13SBarry Smith 3101aa95bbe8SBarry Smith You can call MatGetInfo() to get information on how effective the preallocation was; 3102aa95bbe8SBarry Smith for example the fields mallocs,nz_allocated,nz_used,nz_unneeded; 3103aa95bbe8SBarry Smith You can also run with the option -info and look for messages with the string 3104aa95bbe8SBarry Smith malloc in them to see if additional memory allocation was needed. 3105aa95bbe8SBarry Smith 3106a96a251dSBarry Smith Developers: Use nz of MAT_SKIP_ALLOCATION to not allocate any space for the matrix 3107a96a251dSBarry Smith entries or columns indices 3108a96a251dSBarry Smith 3109273d9f13SBarry Smith By default, this format uses inodes (identical nodes) when possible, to 3110273d9f13SBarry Smith improve numerical efficiency of matrix-vector products and solves. We 3111273d9f13SBarry Smith search for consecutive rows with the same nonzero structure, thereby 3112273d9f13SBarry Smith reusing matrix information to achieve increased efficiency. 3113273d9f13SBarry Smith 3114273d9f13SBarry Smith Options Database Keys: 3115698d4c6aSKris Buschelman + -mat_no_inode - Do not use inodes 3116698d4c6aSKris Buschelman . -mat_inode_limit <limit> - Sets inode limit (max limit=5) 3117273d9f13SBarry Smith - -mat_aij_oneindex - Internally use indexing starting at 1 3118273d9f13SBarry Smith rather than 0. Note that when calling MatSetValues(), 3119273d9f13SBarry Smith the user still MUST index entries starting at 0! 3120273d9f13SBarry Smith 3121273d9f13SBarry Smith Level: intermediate 3122273d9f13SBarry Smith 3123aa95bbe8SBarry Smith .seealso: MatCreate(), MatCreateMPIAIJ(), MatSetValues(), MatSeqAIJSetColumnIndices(), MatCreateSeqAIJWithArrays(), MatGetInfo() 3124273d9f13SBarry Smith 3125273d9f13SBarry Smith @*/ 31267087cfbeSBarry Smith PetscErrorCode MatSeqAIJSetPreallocation(Mat B,PetscInt nz,const PetscInt nnz[]) 3127273d9f13SBarry Smith { 31284ac538c5SBarry Smith PetscErrorCode ierr; 3129a23d5eceSKris Buschelman 3130a23d5eceSKris Buschelman PetscFunctionBegin; 31314ac538c5SBarry Smith ierr = PetscTryMethod(B,"MatSeqAIJSetPreallocation_C",(Mat,PetscInt,const PetscInt[]),(B,nz,nnz));CHKERRQ(ierr); 3132a23d5eceSKris Buschelman PetscFunctionReturn(0); 3133a23d5eceSKris Buschelman } 3134a23d5eceSKris Buschelman 3135a23d5eceSKris Buschelman EXTERN_C_BEGIN 3136a23d5eceSKris Buschelman #undef __FUNCT__ 3137a23d5eceSKris Buschelman #define __FUNCT__ "MatSeqAIJSetPreallocation_SeqAIJ" 31387087cfbeSBarry Smith PetscErrorCode MatSeqAIJSetPreallocation_SeqAIJ(Mat B,PetscInt nz,const PetscInt *nnz) 3139a23d5eceSKris Buschelman { 3140273d9f13SBarry Smith Mat_SeqAIJ *b; 3141ace3abfcSBarry Smith PetscBool skipallocation = PETSC_FALSE; 31426849ba73SBarry Smith PetscErrorCode ierr; 314397f1f81fSBarry Smith PetscInt i; 3144273d9f13SBarry Smith 3145273d9f13SBarry Smith PetscFunctionBegin; 3146d5d45c9bSBarry Smith 3147a96a251dSBarry Smith if (nz == MAT_SKIP_ALLOCATION) { 3148c461c341SBarry Smith skipallocation = PETSC_TRUE; 3149c461c341SBarry Smith nz = 0; 3150c461c341SBarry Smith } 3151c461c341SBarry Smith 315226283091SBarry Smith ierr = PetscLayoutSetBlockSize(B->rmap,1);CHKERRQ(ierr); 315326283091SBarry Smith ierr = PetscLayoutSetBlockSize(B->cmap,1);CHKERRQ(ierr); 315426283091SBarry Smith ierr = PetscLayoutSetUp(B->rmap);CHKERRQ(ierr); 315526283091SBarry Smith ierr = PetscLayoutSetUp(B->cmap);CHKERRQ(ierr); 3156899cda47SBarry Smith 3157435da068SBarry Smith if (nz == PETSC_DEFAULT || nz == PETSC_DECIDE) nz = 5; 3158e32f2f54SBarry Smith if (nz < 0) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"nz cannot be less than 0: value %d",nz); 3159b73539f3SBarry Smith if (nnz) { 3160d0f46423SBarry Smith for (i=0; i<B->rmap->n; i++) { 3161e32f2f54SBarry Smith if (nnz[i] < 0) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"nnz cannot be less than 0: local row %d value %d",i,nnz[i]); 3162e32f2f54SBarry Smith if (nnz[i] > B->cmap->n) SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"nnz cannot be greater than row length: local row %d value %d rowlength %d",i,nnz[i],B->cmap->n); 3163b73539f3SBarry Smith } 3164b73539f3SBarry Smith } 3165b73539f3SBarry Smith 3166273d9f13SBarry Smith B->preallocated = PETSC_TRUE; 3167273d9f13SBarry Smith b = (Mat_SeqAIJ*)B->data; 3168273d9f13SBarry Smith 3169ab93d7beSBarry Smith if (!skipallocation) { 31702ee49352SLisandro Dalcin if (!b->imax) { 3171d0f46423SBarry Smith ierr = PetscMalloc2(B->rmap->n,PetscInt,&b->imax,B->rmap->n,PetscInt,&b->ilen);CHKERRQ(ierr); 3172d0f46423SBarry Smith ierr = PetscLogObjectMemory(B,2*B->rmap->n*sizeof(PetscInt));CHKERRQ(ierr); 31732ee49352SLisandro Dalcin } 3174273d9f13SBarry Smith if (!nnz) { 3175435da068SBarry Smith if (nz == PETSC_DEFAULT || nz == PETSC_DECIDE) nz = 10; 3176c62bd62aSJed Brown else if (nz < 0) nz = 1; 3177d0f46423SBarry Smith for (i=0; i<B->rmap->n; i++) b->imax[i] = nz; 3178d0f46423SBarry Smith nz = nz*B->rmap->n; 3179273d9f13SBarry Smith } else { 3180273d9f13SBarry Smith nz = 0; 3181d0f46423SBarry Smith for (i=0; i<B->rmap->n; i++) {b->imax[i] = nnz[i]; nz += nnz[i];} 3182273d9f13SBarry Smith } 3183ab93d7beSBarry Smith /* b->ilen will count nonzeros in each row so far. */ 3184d0f46423SBarry Smith for (i=0; i<B->rmap->n; i++) { b->ilen[i] = 0; } 3185ab93d7beSBarry Smith 3186273d9f13SBarry Smith /* allocate the matrix space */ 31872ee49352SLisandro Dalcin ierr = MatSeqXAIJFreeAIJ(B,&b->a,&b->j,&b->i);CHKERRQ(ierr); 3188d0f46423SBarry Smith ierr = PetscMalloc3(nz,PetscScalar,&b->a,nz,PetscInt,&b->j,B->rmap->n+1,PetscInt,&b->i);CHKERRQ(ierr); 3189d0f46423SBarry Smith ierr = PetscLogObjectMemory(B,(B->rmap->n+1)*sizeof(PetscInt)+nz*(sizeof(PetscScalar)+sizeof(PetscInt)));CHKERRQ(ierr); 3190bfeeae90SHong Zhang b->i[0] = 0; 3191d0f46423SBarry Smith for (i=1; i<B->rmap->n+1; i++) { 31925da197adSKris Buschelman b->i[i] = b->i[i-1] + b->imax[i-1]; 31935da197adSKris Buschelman } 3194273d9f13SBarry Smith b->singlemalloc = PETSC_TRUE; 3195e6b907acSBarry Smith b->free_a = PETSC_TRUE; 3196e6b907acSBarry Smith b->free_ij = PETSC_TRUE; 3197c461c341SBarry Smith } else { 3198e6b907acSBarry Smith b->free_a = PETSC_FALSE; 3199e6b907acSBarry Smith b->free_ij = PETSC_FALSE; 3200c461c341SBarry Smith } 3201273d9f13SBarry Smith 3202273d9f13SBarry Smith b->nz = 0; 3203273d9f13SBarry Smith b->maxnz = nz; 3204273d9f13SBarry Smith B->info.nz_unneeded = (double)b->maxnz; 3205273d9f13SBarry Smith PetscFunctionReturn(0); 3206273d9f13SBarry Smith } 3207a23d5eceSKris Buschelman EXTERN_C_END 3208273d9f13SBarry Smith 3209a1661176SMatthew Knepley #undef __FUNCT__ 3210a1661176SMatthew Knepley #define __FUNCT__ "MatSeqAIJSetPreallocationCSR" 321158d36128SBarry Smith /*@ 3212a1661176SMatthew Knepley MatSeqAIJSetPreallocationCSR - Allocates memory for a sparse sequential matrix in AIJ format. 3213a1661176SMatthew Knepley 3214a1661176SMatthew Knepley Input Parameters: 3215a1661176SMatthew Knepley + B - the matrix 3216a1661176SMatthew Knepley . i - the indices into j for the start of each row (starts with zero) 3217a1661176SMatthew Knepley . j - the column indices for each row (starts with zero) these must be sorted for each row 3218a1661176SMatthew Knepley - v - optional values in the matrix 3219a1661176SMatthew Knepley 3220a1661176SMatthew Knepley Level: developer 3221a1661176SMatthew Knepley 322258d36128SBarry Smith The i,j,v values are COPIED with this routine; to avoid the copy use MatCreateSeqAIJWithArrays() 322358d36128SBarry Smith 3224a1661176SMatthew Knepley .keywords: matrix, aij, compressed row, sparse, sequential 3225a1661176SMatthew Knepley 3226a1661176SMatthew Knepley .seealso: MatCreate(), MatCreateSeqAIJ(), MatSetValues(), MatSeqAIJSetPreallocation(), MatCreateSeqAIJ(), SeqAIJ 3227a1661176SMatthew Knepley @*/ 3228a1661176SMatthew Knepley PetscErrorCode MatSeqAIJSetPreallocationCSR(Mat B,const PetscInt i[],const PetscInt j[],const PetscScalar v[]) 3229a1661176SMatthew Knepley { 3230a1661176SMatthew Knepley PetscErrorCode ierr; 3231a1661176SMatthew Knepley 3232a1661176SMatthew Knepley PetscFunctionBegin; 32330700a824SBarry Smith PetscValidHeaderSpecific(B,MAT_CLASSID,1); 32344ac538c5SBarry Smith ierr = PetscTryMethod(B,"MatSeqAIJSetPreallocationCSR_C",(Mat,const PetscInt[],const PetscInt[],const PetscScalar[]),(B,i,j,v));CHKERRQ(ierr); 3235a1661176SMatthew Knepley PetscFunctionReturn(0); 3236a1661176SMatthew Knepley } 3237a1661176SMatthew Knepley 3238a1661176SMatthew Knepley EXTERN_C_BEGIN 3239a1661176SMatthew Knepley #undef __FUNCT__ 3240a1661176SMatthew Knepley #define __FUNCT__ "MatSeqAIJSetPreallocationCSR_SeqAIJ" 32417087cfbeSBarry Smith PetscErrorCode MatSeqAIJSetPreallocationCSR_SeqAIJ(Mat B,const PetscInt Ii[],const PetscInt J[],const PetscScalar v[]) 3242a1661176SMatthew Knepley { 3243a1661176SMatthew Knepley PetscInt i; 3244a1661176SMatthew Knepley PetscInt m,n; 3245a1661176SMatthew Knepley PetscInt nz; 3246a1661176SMatthew Knepley PetscInt *nnz, nz_max = 0; 3247a1661176SMatthew Knepley PetscScalar *values; 3248a1661176SMatthew Knepley PetscErrorCode ierr; 3249a1661176SMatthew Knepley 3250a1661176SMatthew Knepley PetscFunctionBegin; 3251a1661176SMatthew Knepley ierr = MatGetSize(B, &m, &n);CHKERRQ(ierr); 3252a1661176SMatthew Knepley 325365e19b50SBarry Smith if (Ii[0]) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE, "Ii[0] must be 0 it is %D", Ii[0]); 3254a1661176SMatthew Knepley ierr = PetscMalloc((m+1) * sizeof(PetscInt), &nnz);CHKERRQ(ierr); 3255a1661176SMatthew Knepley for(i = 0; i < m; i++) { 3256b7940d39SSatish Balay nz = Ii[i+1]- Ii[i]; 3257a1661176SMatthew Knepley nz_max = PetscMax(nz_max, nz); 325865e19b50SBarry Smith if (nz < 0) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE, "Local row %D has a negative number of columns %D", i, nnz); 3259a1661176SMatthew Knepley nnz[i] = nz; 3260a1661176SMatthew Knepley } 3261a1661176SMatthew Knepley ierr = MatSeqAIJSetPreallocation(B, 0, nnz);CHKERRQ(ierr); 3262a1661176SMatthew Knepley ierr = PetscFree(nnz);CHKERRQ(ierr); 3263a1661176SMatthew Knepley 3264a1661176SMatthew Knepley if (v) { 3265a1661176SMatthew Knepley values = (PetscScalar*) v; 3266a1661176SMatthew Knepley } else { 32670e83c824SBarry Smith ierr = PetscMalloc(nz_max*sizeof(PetscScalar), &values);CHKERRQ(ierr); 3268a1661176SMatthew Knepley ierr = PetscMemzero(values, nz_max*sizeof(PetscScalar));CHKERRQ(ierr); 3269a1661176SMatthew Knepley } 3270a1661176SMatthew Knepley 3271a1661176SMatthew Knepley for(i = 0; i < m; i++) { 3272b7940d39SSatish Balay nz = Ii[i+1] - Ii[i]; 3273b7940d39SSatish Balay ierr = MatSetValues_SeqAIJ(B, 1, &i, nz, J+Ii[i], values + (v ? Ii[i] : 0), INSERT_VALUES);CHKERRQ(ierr); 3274a1661176SMatthew Knepley } 3275a1661176SMatthew Knepley 3276a1661176SMatthew Knepley ierr = MatAssemblyBegin(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 3277a1661176SMatthew Knepley ierr = MatAssemblyEnd(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 3278a1661176SMatthew Knepley 3279a1661176SMatthew Knepley if (!v) { 3280a1661176SMatthew Knepley ierr = PetscFree(values);CHKERRQ(ierr); 3281a1661176SMatthew Knepley } 3282a1661176SMatthew Knepley PetscFunctionReturn(0); 3283a1661176SMatthew Knepley } 3284a1661176SMatthew Knepley EXTERN_C_END 3285a1661176SMatthew Knepley 32867c4f633dSBarry Smith #include "../src/mat/impls/dense/seq/dense.h" 3287be7314b0SBarry Smith #include "private/petscaxpy.h" 3288170fe5c8SBarry Smith 3289170fe5c8SBarry Smith #undef __FUNCT__ 3290170fe5c8SBarry Smith #define __FUNCT__ "MatMatMultNumeric_SeqDense_SeqAIJ" 3291170fe5c8SBarry Smith /* 3292170fe5c8SBarry Smith Computes (B'*A')' since computing B*A directly is untenable 3293170fe5c8SBarry Smith 3294170fe5c8SBarry Smith n p p 3295170fe5c8SBarry Smith ( ) ( ) ( ) 3296170fe5c8SBarry Smith m ( A ) * n ( B ) = m ( C ) 3297170fe5c8SBarry Smith ( ) ( ) ( ) 3298170fe5c8SBarry Smith 3299170fe5c8SBarry Smith */ 3300170fe5c8SBarry Smith PetscErrorCode MatMatMultNumeric_SeqDense_SeqAIJ(Mat A,Mat B,Mat C) 3301170fe5c8SBarry Smith { 3302170fe5c8SBarry Smith PetscErrorCode ierr; 3303170fe5c8SBarry Smith Mat_SeqDense *sub_a = (Mat_SeqDense*)A->data; 3304170fe5c8SBarry Smith Mat_SeqAIJ *sub_b = (Mat_SeqAIJ*)B->data; 3305170fe5c8SBarry Smith Mat_SeqDense *sub_c = (Mat_SeqDense*)C->data; 33061de00fd4SBarry Smith PetscInt i,n,m,q,p; 3307170fe5c8SBarry Smith const PetscInt *ii,*idx; 3308170fe5c8SBarry Smith const PetscScalar *b,*a,*a_q; 3309170fe5c8SBarry Smith PetscScalar *c,*c_q; 3310170fe5c8SBarry Smith 3311170fe5c8SBarry Smith PetscFunctionBegin; 3312d0f46423SBarry Smith m = A->rmap->n; 3313d0f46423SBarry Smith n = A->cmap->n; 3314d0f46423SBarry Smith p = B->cmap->n; 3315170fe5c8SBarry Smith a = sub_a->v; 3316170fe5c8SBarry Smith b = sub_b->a; 3317170fe5c8SBarry Smith c = sub_c->v; 3318170fe5c8SBarry Smith ierr = PetscMemzero(c,m*p*sizeof(PetscScalar));CHKERRQ(ierr); 3319170fe5c8SBarry Smith 3320170fe5c8SBarry Smith ii = sub_b->i; 3321170fe5c8SBarry Smith idx = sub_b->j; 3322170fe5c8SBarry Smith for (i=0; i<n; i++) { 3323170fe5c8SBarry Smith q = ii[i+1] - ii[i]; 3324170fe5c8SBarry Smith while (q-->0) { 3325170fe5c8SBarry Smith c_q = c + m*(*idx); 3326170fe5c8SBarry Smith a_q = a + m*i; 3327be7314b0SBarry Smith PetscAXPY(c_q,*b,a_q,m); 3328170fe5c8SBarry Smith idx++; 3329170fe5c8SBarry Smith b++; 3330170fe5c8SBarry Smith } 3331170fe5c8SBarry Smith } 3332170fe5c8SBarry Smith PetscFunctionReturn(0); 3333170fe5c8SBarry Smith } 3334170fe5c8SBarry Smith 3335170fe5c8SBarry Smith #undef __FUNCT__ 3336170fe5c8SBarry Smith #define __FUNCT__ "MatMatMultSymbolic_SeqDense_SeqAIJ" 3337170fe5c8SBarry Smith PetscErrorCode MatMatMultSymbolic_SeqDense_SeqAIJ(Mat A,Mat B,PetscReal fill,Mat *C) 3338170fe5c8SBarry Smith { 3339170fe5c8SBarry Smith PetscErrorCode ierr; 3340d0f46423SBarry Smith PetscInt m=A->rmap->n,n=B->cmap->n; 3341170fe5c8SBarry Smith Mat Cmat; 3342170fe5c8SBarry Smith 3343170fe5c8SBarry Smith PetscFunctionBegin; 3344e32f2f54SBarry Smith if (A->cmap->n != B->rmap->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"A->cmap->n %d != B->rmap->n %d\n",A->cmap->n,B->rmap->n); 334539804f7cSBarry Smith ierr = MatCreate(((PetscObject)A)->comm,&Cmat);CHKERRQ(ierr); 3346170fe5c8SBarry Smith ierr = MatSetSizes(Cmat,m,n,m,n);CHKERRQ(ierr); 3347170fe5c8SBarry Smith ierr = MatSetType(Cmat,MATSEQDENSE);CHKERRQ(ierr); 3348170fe5c8SBarry Smith ierr = MatSeqDenseSetPreallocation(Cmat,PETSC_NULL);CHKERRQ(ierr); 3349170fe5c8SBarry Smith Cmat->assembled = PETSC_TRUE; 3350170fe5c8SBarry Smith *C = Cmat; 3351170fe5c8SBarry Smith PetscFunctionReturn(0); 3352170fe5c8SBarry Smith } 3353170fe5c8SBarry Smith 3354170fe5c8SBarry Smith /* ----------------------------------------------------------------*/ 3355170fe5c8SBarry Smith #undef __FUNCT__ 3356170fe5c8SBarry Smith #define __FUNCT__ "MatMatMult_SeqDense_SeqAIJ" 3357170fe5c8SBarry Smith PetscErrorCode MatMatMult_SeqDense_SeqAIJ(Mat A,Mat B,MatReuse scall,PetscReal fill,Mat *C) 3358170fe5c8SBarry Smith { 3359170fe5c8SBarry Smith PetscErrorCode ierr; 3360170fe5c8SBarry Smith 3361170fe5c8SBarry Smith PetscFunctionBegin; 3362170fe5c8SBarry Smith if (scall == MAT_INITIAL_MATRIX){ 3363170fe5c8SBarry Smith ierr = MatMatMultSymbolic_SeqDense_SeqAIJ(A,B,fill,C);CHKERRQ(ierr); 3364170fe5c8SBarry Smith } 3365170fe5c8SBarry Smith ierr = MatMatMultNumeric_SeqDense_SeqAIJ(A,B,*C);CHKERRQ(ierr); 3366170fe5c8SBarry Smith PetscFunctionReturn(0); 3367170fe5c8SBarry Smith } 3368170fe5c8SBarry Smith 3369170fe5c8SBarry Smith 33700bad9183SKris Buschelman /*MC 3371fafad747SKris Buschelman MATSEQAIJ - MATSEQAIJ = "seqaij" - A matrix type to be used for sequential sparse matrices, 33720bad9183SKris Buschelman based on compressed sparse row format. 33730bad9183SKris Buschelman 33740bad9183SKris Buschelman Options Database Keys: 33750bad9183SKris Buschelman . -mat_type seqaij - sets the matrix type to "seqaij" during a call to MatSetFromOptions() 33760bad9183SKris Buschelman 33770bad9183SKris Buschelman Level: beginner 33780bad9183SKris Buschelman 3379f587520bSBarry Smith .seealso: MatCreateSeqAIJ(), MatSetFromOptions(), MatSetType(), MatCreate(), MatType 33800bad9183SKris Buschelman M*/ 33810bad9183SKris Buschelman 3382a6175056SHong Zhang EXTERN_C_BEGIN 3383b5e56a35SBarry Smith #if defined(PETSC_HAVE_PASTIX) 3384b5e56a35SBarry Smith extern PetscErrorCode MatGetFactor_seqaij_pastix(Mat,MatFactorType,Mat*); 3385b5e56a35SBarry Smith #endif 338665460251SBarry Smith #if defined(PETSC_HAVE_ESSL) && !defined(PETSC_USE_COMPLEX) && !defined(PETSC_USE_SCALAR_SINGLE) && !defined(PETSC_USE_SCALAR_MAT_SINGLE) 3387af1023dbSSatish Balay extern PetscErrorCode MatGetFactor_seqaij_essl(Mat,MatFactorType,Mat *); 3388af1023dbSSatish Balay #endif 33897087cfbeSBarry Smith extern PetscErrorCode MatConvert_SeqAIJ_SeqAIJCRL(Mat,MatType,MatReuse,Mat*); 33907087cfbeSBarry Smith extern PetscErrorCode MatGetFactor_seqaij_petsc(Mat,MatFactorType,Mat*); 33917087cfbeSBarry Smith extern PetscErrorCode MatGetFactor_seqaij_bas(Mat,MatFactorType,Mat*); 33927087cfbeSBarry Smith extern PetscErrorCode MatGetFactorAvailable_seqaij_petsc(Mat,MatFactorType,PetscBool *); 3393611f576cSBarry Smith #if defined(PETSC_HAVE_MUMPS) 33947087cfbeSBarry Smith extern PetscErrorCode MatGetFactor_aij_mumps(Mat,MatFactorType,Mat*); 3395611f576cSBarry Smith #endif 3396611f576cSBarry Smith #if defined(PETSC_HAVE_SUPERLU) 33977087cfbeSBarry Smith extern PetscErrorCode MatGetFactor_seqaij_superlu(Mat,MatFactorType,Mat*); 3398611f576cSBarry Smith #endif 3399f3c0ef26SHong Zhang #if defined(PETSC_HAVE_SUPERLU_DIST) 3400f3c0ef26SHong Zhang extern PetscErrorCode MatGetFactor_seqaij_superlu_dist(Mat,MatFactorType,Mat*); 3401f3c0ef26SHong Zhang #endif 3402611f576cSBarry Smith #if defined(PETSC_HAVE_SPOOLES) 34037087cfbeSBarry Smith extern PetscErrorCode MatGetFactor_seqaij_spooles(Mat,MatFactorType,Mat*); 3404611f576cSBarry Smith #endif 3405eb3b5408SSatish Balay #if defined(PETSC_HAVE_UMFPACK) 34067087cfbeSBarry Smith extern PetscErrorCode MatGetFactor_seqaij_umfpack(Mat,MatFactorType,Mat*); 3407eb3b5408SSatish Balay #endif 3408586621ddSJed Brown #if defined(PETSC_HAVE_CHOLMOD) 34097087cfbeSBarry Smith extern PetscErrorCode MatGetFactor_seqaij_cholmod(Mat,MatFactorType,Mat*); 3410586621ddSJed Brown #endif 3411719d5645SBarry Smith #if defined(PETSC_HAVE_LUSOL) 34127087cfbeSBarry Smith extern PetscErrorCode MatGetFactor_seqaij_lusol(Mat,MatFactorType,Mat*); 3413719d5645SBarry Smith #endif 3414b3866ffcSBarry Smith #if defined(PETSC_HAVE_MATLAB_ENGINE) 34157087cfbeSBarry Smith extern PetscErrorCode MatGetFactor_seqaij_matlab(Mat,MatFactorType,Mat*); 34167087cfbeSBarry Smith extern PetscErrorCode MatlabEnginePut_SeqAIJ(PetscObject,void*); 34177087cfbeSBarry Smith extern PetscErrorCode MatlabEngineGet_SeqAIJ(PetscObject,void*); 3418b3866ffcSBarry Smith #endif 341917667f90SBarry Smith EXTERN_C_END 342017667f90SBarry Smith 3421b24902e0SBarry Smith 342217667f90SBarry Smith EXTERN_C_BEGIN 34234a2ae208SSatish Balay #undef __FUNCT__ 34244a2ae208SSatish Balay #define __FUNCT__ "MatCreate_SeqAIJ" 34257087cfbeSBarry Smith PetscErrorCode MatCreate_SeqAIJ(Mat B) 3426273d9f13SBarry Smith { 3427273d9f13SBarry Smith Mat_SeqAIJ *b; 3428dfbe8321SBarry Smith PetscErrorCode ierr; 342938baddfdSBarry Smith PetscMPIInt size; 3430273d9f13SBarry Smith 3431273d9f13SBarry Smith PetscFunctionBegin; 34327adad957SLisandro Dalcin ierr = MPI_Comm_size(((PetscObject)B)->comm,&size);CHKERRQ(ierr); 3433e32f2f54SBarry Smith if (size > 1) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Comm must be of size 1"); 3434273d9f13SBarry Smith 343538f2d2fdSLisandro Dalcin ierr = PetscNewLog(B,Mat_SeqAIJ,&b);CHKERRQ(ierr); 3436b0a32e0cSBarry Smith B->data = (void*)b; 3437549d3d68SSatish Balay ierr = PetscMemcpy(B->ops,&MatOps_Values,sizeof(struct _MatOps));CHKERRQ(ierr); 3438416022c9SBarry Smith b->row = 0; 3439416022c9SBarry Smith b->col = 0; 344082bf6240SBarry Smith b->icol = 0; 3441b810aeb4SBarry Smith b->reallocs = 0; 344236db0b34SBarry Smith b->ignorezeroentries = PETSC_FALSE; 3443f1e2ffcdSBarry Smith b->roworiented = PETSC_TRUE; 3444416022c9SBarry Smith b->nonew = 0; 3445416022c9SBarry Smith b->diag = 0; 3446416022c9SBarry Smith b->solve_work = 0; 34472a1b7f2aSHong Zhang B->spptr = 0; 3448be6bf707SBarry Smith b->saved_values = 0; 3449d7f994e1SBarry Smith b->idiag = 0; 345071f1c65dSBarry Smith b->mdiag = 0; 345171f1c65dSBarry Smith b->ssor_work = 0; 345271f1c65dSBarry Smith b->omega = 1.0; 345371f1c65dSBarry Smith b->fshift = 0.0; 345471f1c65dSBarry Smith b->idiagvalid = PETSC_FALSE; 3455a9817697SBarry Smith b->keepnonzeropattern = PETSC_FALSE; 3456a30b2313SHong Zhang b->xtoy = 0; 3457a30b2313SHong Zhang b->XtoY = 0; 345888e51ccdSHong Zhang B->same_nonzero = PETSC_FALSE; 345917ab2063SBarry Smith 346035d8aa7fSBarry Smith ierr = PetscObjectChangeTypeName((PetscObject)B,MATSEQAIJ);CHKERRQ(ierr); 3461b3866ffcSBarry Smith #if defined(PETSC_HAVE_MATLAB_ENGINE) 3462700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_matlab_C","MatGetFactor_seqaij_matlab",MatGetFactor_seqaij_matlab);CHKERRQ(ierr); 3463b3866ffcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"PetscMatlabEnginePut_C","MatlabEnginePut_SeqAIJ",MatlabEnginePut_SeqAIJ);CHKERRQ(ierr); 3464b3866ffcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"PetscMatlabEngineGet_C","MatlabEngineGet_SeqAIJ",MatlabEngineGet_SeqAIJ);CHKERRQ(ierr); 3465b3866ffcSBarry Smith #endif 3466b5e56a35SBarry Smith #if defined(PETSC_HAVE_PASTIX) 3467700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_pastix_C","MatGetFactor_seqaij_pastix",MatGetFactor_seqaij_pastix);CHKERRQ(ierr); 3468b5e56a35SBarry Smith #endif 346965460251SBarry Smith #if defined(PETSC_HAVE_ESSL) && !defined(PETSC_USE_COMPLEX) && !defined(PETSC_USE_SCALAR_SINGLE) && !defined(PETSC_USE_SCALAR_MAT_SINGLE) 3470700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_essl_C","MatGetFactor_seqaij_essl",MatGetFactor_seqaij_essl);CHKERRQ(ierr); 3471719d5645SBarry Smith #endif 3472611f576cSBarry Smith #if defined(PETSC_HAVE_SUPERLU) 3473700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_superlu_C","MatGetFactor_seqaij_superlu",MatGetFactor_seqaij_superlu);CHKERRQ(ierr); 3474611f576cSBarry Smith #endif 3475f3c0ef26SHong Zhang #if defined(PETSC_HAVE_SUPERLU_DIST) 3476700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_superlu_dist_C","MatGetFactor_seqaij_superlu_dist",MatGetFactor_seqaij_superlu_dist);CHKERRQ(ierr); 3477f3c0ef26SHong Zhang #endif 3478611f576cSBarry Smith #if defined(PETSC_HAVE_SPOOLES) 3479700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_spooles_C","MatGetFactor_seqaij_spooles",MatGetFactor_seqaij_spooles);CHKERRQ(ierr); 3480611f576cSBarry Smith #endif 3481611f576cSBarry Smith #if defined(PETSC_HAVE_MUMPS) 3482700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_mumps_C","MatGetFactor_aij_mumps",MatGetFactor_aij_mumps);CHKERRQ(ierr); 3483611f576cSBarry Smith #endif 3484eb3b5408SSatish Balay #if defined(PETSC_HAVE_UMFPACK) 3485700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_umfpack_C","MatGetFactor_seqaij_umfpack",MatGetFactor_seqaij_umfpack);CHKERRQ(ierr); 3486eb3b5408SSatish Balay #endif 3487586621ddSJed Brown #if defined(PETSC_HAVE_CHOLMOD) 3488700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_cholmod_C","MatGetFactor_seqaij_cholmod",MatGetFactor_seqaij_cholmod);CHKERRQ(ierr); 3489586621ddSJed Brown #endif 3490719d5645SBarry Smith #if defined(PETSC_HAVE_LUSOL) 3491700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_lusol_C","MatGetFactor_seqaij_lusol",MatGetFactor_seqaij_lusol);CHKERRQ(ierr); 3492719d5645SBarry Smith #endif 3493700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_petsc_C","MatGetFactor_seqaij_petsc",MatGetFactor_seqaij_petsc);CHKERRQ(ierr); 3494700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactorAvailable_petsc_C","MatGetFactorAvailable_seqaij_petsc",MatGetFactorAvailable_seqaij_petsc);CHKERRQ(ierr); 3495700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatGetFactor_bas_C","MatGetFactor_seqaij_bas",MatGetFactor_seqaij_bas);CHKERRQ(ierr); 3496700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatSeqAIJSetColumnIndices_C","MatSeqAIJSetColumnIndices_SeqAIJ",MatSeqAIJSetColumnIndices_SeqAIJ);CHKERRQ(ierr); 3497700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatStoreValues_C","MatStoreValues_SeqAIJ",MatStoreValues_SeqAIJ);CHKERRQ(ierr); 3498700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatRetrieveValues_C","MatRetrieveValues_SeqAIJ",MatRetrieveValues_SeqAIJ);CHKERRQ(ierr); 3499700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatConvert_seqaij_seqsbaij_C","MatConvert_SeqAIJ_SeqSBAIJ",MatConvert_SeqAIJ_SeqSBAIJ);CHKERRQ(ierr); 3500700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatConvert_seqaij_seqbaij_C","MatConvert_SeqAIJ_SeqBAIJ",MatConvert_SeqAIJ_SeqBAIJ);CHKERRQ(ierr); 3501700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatConvert_seqaij_seqaijperm_C","MatConvert_SeqAIJ_SeqAIJPERM",MatConvert_SeqAIJ_SeqAIJPERM);CHKERRQ(ierr); 3502700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatConvert_seqaij_seqaijcrl_C","MatConvert_SeqAIJ_SeqAIJCRL",MatConvert_SeqAIJ_SeqAIJCRL);CHKERRQ(ierr); 3503700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatIsTranspose_C","MatIsTranspose_SeqAIJ",MatIsTranspose_SeqAIJ);CHKERRQ(ierr); 3504700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatIsHermitianTranspose_C","MatIsHermitianTranspose_SeqAIJ",MatIsTranspose_SeqAIJ);CHKERRQ(ierr); 3505700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatSeqAIJSetPreallocation_C","MatSeqAIJSetPreallocation_SeqAIJ",MatSeqAIJSetPreallocation_SeqAIJ);CHKERRQ(ierr); 3506700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatSeqAIJSetPreallocationCSR_C","MatSeqAIJSetPreallocationCSR_SeqAIJ",MatSeqAIJSetPreallocationCSR_SeqAIJ);CHKERRQ(ierr); 3507700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatReorderForNonzeroDiagonal_C","MatReorderForNonzeroDiagonal_SeqAIJ",MatReorderForNonzeroDiagonal_SeqAIJ);CHKERRQ(ierr); 3508700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatMatMult_seqdense_seqaij_C","MatMatMult_SeqDense_SeqAIJ",MatMatMult_SeqDense_SeqAIJ);CHKERRQ(ierr); 3509700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatMatMultSymbolic_seqdense_seqaij_C","MatMatMultSymbolic_SeqDense_SeqAIJ",MatMatMultSymbolic_SeqDense_SeqAIJ);CHKERRQ(ierr); 3510700c5bfcSBarry Smith ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatMatMultNumeric_seqdense_seqaij_C","MatMatMultNumeric_SeqDense_SeqAIJ",MatMatMultNumeric_SeqDense_SeqAIJ);CHKERRQ(ierr); 35114108e4d5SBarry Smith ierr = MatCreate_SeqAIJ_Inode(B);CHKERRQ(ierr); 351217667f90SBarry Smith ierr = PetscObjectChangeTypeName((PetscObject)B,MATSEQAIJ);CHKERRQ(ierr); 35133a40ed3dSBarry Smith PetscFunctionReturn(0); 351417ab2063SBarry Smith } 3515273d9f13SBarry Smith EXTERN_C_END 351617ab2063SBarry Smith 35174a2ae208SSatish Balay #undef __FUNCT__ 3518b24902e0SBarry Smith #define __FUNCT__ "MatDuplicateNoCreate_SeqAIJ" 3519b24902e0SBarry Smith /* 3520b24902e0SBarry Smith Given a matrix generated with MatGetFactor() duplicates all the information in A into B 3521b24902e0SBarry Smith */ 3522ace3abfcSBarry Smith PetscErrorCode MatDuplicateNoCreate_SeqAIJ(Mat C,Mat A,MatDuplicateOption cpvalues,PetscBool mallocmatspace) 352317ab2063SBarry Smith { 3524416022c9SBarry Smith Mat_SeqAIJ *c,*a = (Mat_SeqAIJ*)A->data; 35256849ba73SBarry Smith PetscErrorCode ierr; 3526d0f46423SBarry Smith PetscInt i,m = A->rmap->n; 352717ab2063SBarry Smith 35283a40ed3dSBarry Smith PetscFunctionBegin; 3529273d9f13SBarry Smith c = (Mat_SeqAIJ*)C->data; 3530273d9f13SBarry Smith 3531d5f3da31SBarry Smith C->factortype = A->factortype; 3532416022c9SBarry Smith c->row = 0; 3533416022c9SBarry Smith c->col = 0; 353482bf6240SBarry Smith c->icol = 0; 35356ad4291fSHong Zhang c->reallocs = 0; 353617ab2063SBarry Smith 35376ad4291fSHong Zhang C->assembled = PETSC_TRUE; 353817ab2063SBarry Smith 353926283091SBarry Smith ierr = PetscLayoutSetBlockSize(C->rmap,1);CHKERRQ(ierr); 354026283091SBarry Smith ierr = PetscLayoutSetBlockSize(C->cmap,1);CHKERRQ(ierr); 354126283091SBarry Smith ierr = PetscLayoutSetUp(C->rmap);CHKERRQ(ierr); 354226283091SBarry Smith ierr = PetscLayoutSetUp(C->cmap);CHKERRQ(ierr); 3543eec197d1SBarry Smith 354433b91e9fSSatish Balay ierr = PetscMalloc2(m,PetscInt,&c->imax,m,PetscInt,&c->ilen);CHKERRQ(ierr); 35459518dbb4SMatthew Knepley ierr = PetscLogObjectMemory(C, 2*m*sizeof(PetscInt));CHKERRQ(ierr); 354617ab2063SBarry Smith for (i=0; i<m; i++) { 3547416022c9SBarry Smith c->imax[i] = a->imax[i]; 3548416022c9SBarry Smith c->ilen[i] = a->ilen[i]; 354917ab2063SBarry Smith } 355017ab2063SBarry Smith 355117ab2063SBarry Smith /* allocate the matrix space */ 3552f77e22a1SHong Zhang if (mallocmatspace){ 3553a96a251dSBarry Smith ierr = PetscMalloc3(a->i[m],PetscScalar,&c->a,a->i[m],PetscInt,&c->j,m+1,PetscInt,&c->i);CHKERRQ(ierr); 35549518dbb4SMatthew Knepley ierr = PetscLogObjectMemory(C, a->i[m]*(sizeof(PetscScalar)+sizeof(PetscInt))+(m+1)*sizeof(PetscInt));CHKERRQ(ierr); 3555f1e2ffcdSBarry Smith c->singlemalloc = PETSC_TRUE; 355697f1f81fSBarry Smith ierr = PetscMemcpy(c->i,a->i,(m+1)*sizeof(PetscInt));CHKERRQ(ierr); 355717ab2063SBarry Smith if (m > 0) { 355897f1f81fSBarry Smith ierr = PetscMemcpy(c->j,a->j,(a->i[m])*sizeof(PetscInt));CHKERRQ(ierr); 3559be6bf707SBarry Smith if (cpvalues == MAT_COPY_VALUES) { 3560bfeeae90SHong Zhang ierr = PetscMemcpy(c->a,a->a,(a->i[m])*sizeof(PetscScalar));CHKERRQ(ierr); 3561be6bf707SBarry Smith } else { 3562bfeeae90SHong Zhang ierr = PetscMemzero(c->a,(a->i[m])*sizeof(PetscScalar));CHKERRQ(ierr); 356317ab2063SBarry Smith } 356408480c60SBarry Smith } 3565f77e22a1SHong Zhang } 356617ab2063SBarry Smith 35676ad4291fSHong Zhang c->ignorezeroentries = a->ignorezeroentries; 3568416022c9SBarry Smith c->roworiented = a->roworiented; 3569416022c9SBarry Smith c->nonew = a->nonew; 3570416022c9SBarry Smith if (a->diag) { 357197f1f81fSBarry Smith ierr = PetscMalloc((m+1)*sizeof(PetscInt),&c->diag);CHKERRQ(ierr); 357252e6d16bSBarry Smith ierr = PetscLogObjectMemory(C,(m+1)*sizeof(PetscInt));CHKERRQ(ierr); 357317ab2063SBarry Smith for (i=0; i<m; i++) { 3574416022c9SBarry Smith c->diag[i] = a->diag[i]; 357517ab2063SBarry Smith } 35763a40ed3dSBarry Smith } else c->diag = 0; 35776ad4291fSHong Zhang c->solve_work = 0; 35786ad4291fSHong Zhang c->saved_values = 0; 35796ad4291fSHong Zhang c->idiag = 0; 358071f1c65dSBarry Smith c->ssor_work = 0; 3581a9817697SBarry Smith c->keepnonzeropattern = a->keepnonzeropattern; 3582e6b907acSBarry Smith c->free_a = PETSC_TRUE; 3583e6b907acSBarry Smith c->free_ij = PETSC_TRUE; 35846ad4291fSHong Zhang c->xtoy = 0; 35856ad4291fSHong Zhang c->XtoY = 0; 35866ad4291fSHong Zhang 3587416022c9SBarry Smith c->nz = a->nz; 35888ed568f8SMatthew G Knepley c->maxnz = a->nz; /* Since we allocate exactly the right amount */ 3589273d9f13SBarry Smith C->preallocated = PETSC_TRUE; 3590754ec7b1SSatish Balay 35916ad4291fSHong Zhang c->compressedrow.use = a->compressedrow.use; 35926ad4291fSHong Zhang c->compressedrow.nrows = a->compressedrow.nrows; 3593cd6b891eSBarry Smith c->compressedrow.check = a->compressedrow.check; 3594cd6b891eSBarry Smith if (a->compressedrow.use){ 35956ad4291fSHong Zhang i = a->compressedrow.nrows; 35960e83c824SBarry Smith ierr = PetscMalloc2(i+1,PetscInt,&c->compressedrow.i,i,PetscInt,&c->compressedrow.rindex);CHKERRQ(ierr); 35976ad4291fSHong Zhang ierr = PetscMemcpy(c->compressedrow.i,a->compressedrow.i,(i+1)*sizeof(PetscInt));CHKERRQ(ierr); 35986ad4291fSHong Zhang ierr = PetscMemcpy(c->compressedrow.rindex,a->compressedrow.rindex,i*sizeof(PetscInt));CHKERRQ(ierr); 359927ea64f8SHong Zhang } else { 360027ea64f8SHong Zhang c->compressedrow.use = PETSC_FALSE; 360127ea64f8SHong Zhang c->compressedrow.i = PETSC_NULL; 360227ea64f8SHong Zhang c->compressedrow.rindex = PETSC_NULL; 36036ad4291fSHong Zhang } 360488e51ccdSHong Zhang C->same_nonzero = A->same_nonzero; 36054108e4d5SBarry Smith ierr = MatDuplicate_SeqAIJ_Inode(A,cpvalues,&C);CHKERRQ(ierr); 36064846f1f5SKris Buschelman 36077adad957SLisandro Dalcin ierr = PetscFListDuplicate(((PetscObject)A)->qlist,&((PetscObject)C)->qlist);CHKERRQ(ierr); 36083a40ed3dSBarry Smith PetscFunctionReturn(0); 360917ab2063SBarry Smith } 361017ab2063SBarry Smith 36114a2ae208SSatish Balay #undef __FUNCT__ 3612b24902e0SBarry Smith #define __FUNCT__ "MatDuplicate_SeqAIJ" 3613b24902e0SBarry Smith PetscErrorCode MatDuplicate_SeqAIJ(Mat A,MatDuplicateOption cpvalues,Mat *B) 3614b24902e0SBarry Smith { 3615b24902e0SBarry Smith PetscErrorCode ierr; 3616b24902e0SBarry Smith 3617b24902e0SBarry Smith PetscFunctionBegin; 3618b24902e0SBarry Smith ierr = MatCreate(((PetscObject)A)->comm,B);CHKERRQ(ierr); 36194b6263acSBarry Smith ierr = MatSetSizes(*B,A->rmap->n,A->cmap->n,A->rmap->n,A->cmap->n);CHKERRQ(ierr); 3620b24902e0SBarry Smith ierr = MatSetType(*B,MATSEQAIJ);CHKERRQ(ierr); 3621f77e22a1SHong Zhang ierr = MatDuplicateNoCreate_SeqAIJ(*B,A,cpvalues,PETSC_TRUE);CHKERRQ(ierr); 3622b24902e0SBarry Smith PetscFunctionReturn(0); 3623b24902e0SBarry Smith } 3624b24902e0SBarry Smith 3625b24902e0SBarry Smith #undef __FUNCT__ 36264a2ae208SSatish Balay #define __FUNCT__ "MatLoad_SeqAIJ" 3627112444f4SShri Abhyankar PetscErrorCode MatLoad_SeqAIJ(Mat newMat, PetscViewer viewer) 3628fbdbba38SShri Abhyankar { 3629fbdbba38SShri Abhyankar Mat_SeqAIJ *a; 3630fbdbba38SShri Abhyankar PetscErrorCode ierr; 3631fbdbba38SShri Abhyankar PetscInt i,sum,nz,header[4],*rowlengths = 0,M,N,rows,cols; 3632fbdbba38SShri Abhyankar int fd; 3633fbdbba38SShri Abhyankar PetscMPIInt size; 3634fbdbba38SShri Abhyankar MPI_Comm comm; 3635fbdbba38SShri Abhyankar 3636fbdbba38SShri Abhyankar PetscFunctionBegin; 3637fbdbba38SShri Abhyankar ierr = PetscObjectGetComm((PetscObject)viewer,&comm);CHKERRQ(ierr); 3638fbdbba38SShri Abhyankar ierr = MPI_Comm_size(comm,&size);CHKERRQ(ierr); 3639fbdbba38SShri Abhyankar if (size > 1) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"view must have one processor"); 3640fbdbba38SShri Abhyankar ierr = PetscViewerBinaryGetDescriptor(viewer,&fd);CHKERRQ(ierr); 3641fbdbba38SShri Abhyankar ierr = PetscBinaryRead(fd,header,4,PETSC_INT);CHKERRQ(ierr); 3642fbdbba38SShri Abhyankar if (header[0] != MAT_FILE_CLASSID) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_FILE_UNEXPECTED,"not matrix object in file"); 3643fbdbba38SShri Abhyankar M = header[1]; N = header[2]; nz = header[3]; 3644fbdbba38SShri Abhyankar 3645fbdbba38SShri Abhyankar if (nz < 0) { 3646fbdbba38SShri Abhyankar SETERRQ(PETSC_COMM_SELF,PETSC_ERR_FILE_UNEXPECTED,"Matrix stored in special format on disk,cannot load as SeqAIJ"); 3647fbdbba38SShri Abhyankar } 3648fbdbba38SShri Abhyankar 3649fbdbba38SShri Abhyankar /* read in row lengths */ 3650fbdbba38SShri Abhyankar ierr = PetscMalloc(M*sizeof(PetscInt),&rowlengths);CHKERRQ(ierr); 3651fbdbba38SShri Abhyankar ierr = PetscBinaryRead(fd,rowlengths,M,PETSC_INT);CHKERRQ(ierr); 3652fbdbba38SShri Abhyankar 3653fbdbba38SShri Abhyankar /* check if sum of rowlengths is same as nz */ 3654fbdbba38SShri Abhyankar for (i=0,sum=0; i< M; i++) sum +=rowlengths[i]; 3655fbdbba38SShri Abhyankar if (sum != nz) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_FILE_READ,"Inconsistant matrix data in file. no-nonzeros = %d, sum-row-lengths = %d\n",nz,sum); 3656fbdbba38SShri Abhyankar 3657fbdbba38SShri Abhyankar /* set global size if not set already*/ 3658f501eaabSShri Abhyankar if (newMat->rmap->n < 0 && newMat->rmap->N < 0 && newMat->cmap->n < 0 && newMat->cmap->N < 0) { 3659fbdbba38SShri Abhyankar ierr = MatSetSizes(newMat,PETSC_DECIDE,PETSC_DECIDE,M,N);CHKERRQ(ierr); 3660aabbc4fbSShri Abhyankar } else { 3661fbdbba38SShri Abhyankar /* if sizes and type are already set, check if the vector global sizes are correct */ 3662fbdbba38SShri Abhyankar ierr = MatGetSize(newMat,&rows,&cols);CHKERRQ(ierr); 3663f501eaabSShri Abhyankar if (M != rows || N != cols) SETERRQ4(PETSC_COMM_SELF,PETSC_ERR_FILE_UNEXPECTED, "Matrix in file of different length (%d, %d) than the input matrix (%d, %d)",M,N,rows,cols); 3664aabbc4fbSShri Abhyankar } 3665fbdbba38SShri Abhyankar ierr = MatSeqAIJSetPreallocation_SeqAIJ(newMat,0,rowlengths);CHKERRQ(ierr); 3666fbdbba38SShri Abhyankar a = (Mat_SeqAIJ*)newMat->data; 3667fbdbba38SShri Abhyankar 3668fbdbba38SShri Abhyankar ierr = PetscBinaryRead(fd,a->j,nz,PETSC_INT);CHKERRQ(ierr); 3669fbdbba38SShri Abhyankar 3670fbdbba38SShri Abhyankar /* read in nonzero values */ 3671fbdbba38SShri Abhyankar ierr = PetscBinaryRead(fd,a->a,nz,PETSC_SCALAR);CHKERRQ(ierr); 3672fbdbba38SShri Abhyankar 3673fbdbba38SShri Abhyankar /* set matrix "i" values */ 3674fbdbba38SShri Abhyankar a->i[0] = 0; 3675fbdbba38SShri Abhyankar for (i=1; i<= M; i++) { 3676fbdbba38SShri Abhyankar a->i[i] = a->i[i-1] + rowlengths[i-1]; 3677fbdbba38SShri Abhyankar a->ilen[i-1] = rowlengths[i-1]; 3678fbdbba38SShri Abhyankar } 3679fbdbba38SShri Abhyankar ierr = PetscFree(rowlengths);CHKERRQ(ierr); 3680fbdbba38SShri Abhyankar 3681fbdbba38SShri Abhyankar ierr = MatAssemblyBegin(newMat,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 3682fbdbba38SShri Abhyankar ierr = MatAssemblyEnd(newMat,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 3683fbdbba38SShri Abhyankar PetscFunctionReturn(0); 3684fbdbba38SShri Abhyankar } 3685fbdbba38SShri Abhyankar 3686fbdbba38SShri Abhyankar #undef __FUNCT__ 3687b9617806SBarry Smith #define __FUNCT__ "MatEqual_SeqAIJ" 3688ace3abfcSBarry Smith PetscErrorCode MatEqual_SeqAIJ(Mat A,Mat B,PetscBool * flg) 36897264ac53SSatish Balay { 36907264ac53SSatish Balay Mat_SeqAIJ *a = (Mat_SeqAIJ *)A->data,*b = (Mat_SeqAIJ *)B->data; 3691dfbe8321SBarry Smith PetscErrorCode ierr; 3692eeffb40dSHong Zhang #if defined(PETSC_USE_COMPLEX) 3693eeffb40dSHong Zhang PetscInt k; 3694eeffb40dSHong Zhang #endif 36957264ac53SSatish Balay 36963a40ed3dSBarry Smith PetscFunctionBegin; 3697bfeeae90SHong Zhang /* If the matrix dimensions are not equal,or no of nonzeros */ 3698d0f46423SBarry Smith if ((A->rmap->n != B->rmap->n) || (A->cmap->n != B->cmap->n) ||(a->nz != b->nz)) { 3699ca44d042SBarry Smith *flg = PETSC_FALSE; 3700ca44d042SBarry Smith PetscFunctionReturn(0); 3701bcd2baecSBarry Smith } 37027264ac53SSatish Balay 37037264ac53SSatish Balay /* if the a->i are the same */ 3704d0f46423SBarry Smith ierr = PetscMemcmp(a->i,b->i,(A->rmap->n+1)*sizeof(PetscInt),flg);CHKERRQ(ierr); 3705abc0a331SBarry Smith if (!*flg) PetscFunctionReturn(0); 37067264ac53SSatish Balay 37077264ac53SSatish Balay /* if a->j are the same */ 370897f1f81fSBarry Smith ierr = PetscMemcmp(a->j,b->j,(a->nz)*sizeof(PetscInt),flg);CHKERRQ(ierr); 3709abc0a331SBarry Smith if (!*flg) PetscFunctionReturn(0); 3710bcd2baecSBarry Smith 3711bcd2baecSBarry Smith /* if a->a are the same */ 3712eeffb40dSHong Zhang #if defined(PETSC_USE_COMPLEX) 3713eeffb40dSHong Zhang for (k=0; k<a->nz; k++){ 3714eeffb40dSHong Zhang if (PetscRealPart(a->a[k]) != PetscRealPart(b->a[k]) || PetscImaginaryPart(a->a[k]) != PetscImaginaryPart(b->a[k])){ 3715eeffb40dSHong Zhang *flg = PETSC_FALSE; 37163a40ed3dSBarry Smith PetscFunctionReturn(0); 3717eeffb40dSHong Zhang } 3718eeffb40dSHong Zhang } 3719eeffb40dSHong Zhang #else 3720eeffb40dSHong Zhang ierr = PetscMemcmp(a->a,b->a,(a->nz)*sizeof(PetscScalar),flg);CHKERRQ(ierr); 3721eeffb40dSHong Zhang #endif 3722eeffb40dSHong Zhang PetscFunctionReturn(0); 37237264ac53SSatish Balay } 372436db0b34SBarry Smith 37254a2ae208SSatish Balay #undef __FUNCT__ 37264a2ae208SSatish Balay #define __FUNCT__ "MatCreateSeqAIJWithArrays" 372705869f15SSatish Balay /*@ 372836db0b34SBarry Smith MatCreateSeqAIJWithArrays - Creates an sequential AIJ matrix using matrix elements (in CSR format) 372936db0b34SBarry Smith provided by the user. 373036db0b34SBarry Smith 3731c75a6043SHong Zhang Collective on MPI_Comm 373236db0b34SBarry Smith 373336db0b34SBarry Smith Input Parameters: 373436db0b34SBarry Smith + comm - must be an MPI communicator of size 1 373536db0b34SBarry Smith . m - number of rows 373636db0b34SBarry Smith . n - number of columns 373736db0b34SBarry Smith . i - row indices 373836db0b34SBarry Smith . j - column indices 373936db0b34SBarry Smith - a - matrix values 374036db0b34SBarry Smith 374136db0b34SBarry Smith Output Parameter: 374236db0b34SBarry Smith . mat - the matrix 374336db0b34SBarry Smith 374436db0b34SBarry Smith Level: intermediate 374536db0b34SBarry Smith 374636db0b34SBarry Smith Notes: 37470551d7c0SBarry Smith The i, j, and a arrays are not copied by this routine, the user must free these arrays 374836db0b34SBarry Smith once the matrix is destroyed 374936db0b34SBarry Smith 375036db0b34SBarry Smith You cannot set new nonzero locations into this matrix, that will generate an error. 375136db0b34SBarry Smith 3752bfeeae90SHong Zhang The i and j indices are 0 based 375336db0b34SBarry Smith 3754a4552177SSatish Balay The format which is used for the sparse matrix input, is equivalent to a 3755a4552177SSatish Balay row-major ordering.. i.e for the following matrix, the input data expected is 3756a4552177SSatish Balay as shown: 3757a4552177SSatish Balay 3758a4552177SSatish Balay 1 0 0 3759a4552177SSatish Balay 2 0 3 3760a4552177SSatish Balay 4 5 6 3761a4552177SSatish Balay 3762a4552177SSatish Balay i = {0,1,3,6} [size = nrow+1 = 3+1] 37639985e31cSBarry Smith j = {0,0,2,0,1,2} [size = nz = 6]; values must be sorted for each row 3764a4552177SSatish Balay v = {1,2,3,4,5,6} [size = nz = 6] 3765a4552177SSatish Balay 37669985e31cSBarry Smith 37672fb0ec9aSBarry Smith .seealso: MatCreate(), MatCreateMPIAIJ(), MatCreateSeqAIJ(), MatCreateMPIAIJWithArrays(), MatMPIAIJSetPreallocationCSR() 376836db0b34SBarry Smith 376936db0b34SBarry Smith @*/ 37707087cfbeSBarry Smith PetscErrorCode MatCreateSeqAIJWithArrays(MPI_Comm comm,PetscInt m,PetscInt n,PetscInt* i,PetscInt*j,PetscScalar *a,Mat *mat) 377136db0b34SBarry Smith { 3772dfbe8321SBarry Smith PetscErrorCode ierr; 3773cbcfb4deSHong Zhang PetscInt ii; 377436db0b34SBarry Smith Mat_SeqAIJ *aij; 3775cbcfb4deSHong Zhang #if defined(PETSC_USE_DEBUG) 3776cbcfb4deSHong Zhang PetscInt jj; 3777cbcfb4deSHong Zhang #endif 377836db0b34SBarry Smith 377936db0b34SBarry Smith PetscFunctionBegin; 3780a96a251dSBarry Smith if (i[0]) { 3781e32f2f54SBarry Smith SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"i (row indices) must start with 0"); 378236db0b34SBarry Smith } 3783f69a0ea3SMatthew Knepley ierr = MatCreate(comm,mat);CHKERRQ(ierr); 3784f69a0ea3SMatthew Knepley ierr = MatSetSizes(*mat,m,n,m,n);CHKERRQ(ierr); 3785ab93d7beSBarry Smith ierr = MatSetType(*mat,MATSEQAIJ);CHKERRQ(ierr); 3786ab93d7beSBarry Smith ierr = MatSeqAIJSetPreallocation_SeqAIJ(*mat,MAT_SKIP_ALLOCATION,0);CHKERRQ(ierr); 3787ab93d7beSBarry Smith aij = (Mat_SeqAIJ*)(*mat)->data; 3788ab93d7beSBarry Smith ierr = PetscMalloc2(m,PetscInt,&aij->imax,m,PetscInt,&aij->ilen);CHKERRQ(ierr); 3789ab93d7beSBarry Smith 379036db0b34SBarry Smith aij->i = i; 379136db0b34SBarry Smith aij->j = j; 379236db0b34SBarry Smith aij->a = a; 379336db0b34SBarry Smith aij->singlemalloc = PETSC_FALSE; 379436db0b34SBarry Smith aij->nonew = -1; /*this indicates that inserting a new value in the matrix that generates a new nonzero is an error*/ 3795e6b907acSBarry Smith aij->free_a = PETSC_FALSE; 3796e6b907acSBarry Smith aij->free_ij = PETSC_FALSE; 379736db0b34SBarry Smith 379836db0b34SBarry Smith for (ii=0; ii<m; ii++) { 379936db0b34SBarry Smith aij->ilen[ii] = aij->imax[ii] = i[ii+1] - i[ii]; 38002515c552SBarry Smith #if defined(PETSC_USE_DEBUG) 3801e32f2f54SBarry Smith if (i[ii+1] - i[ii] < 0) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Negative row length in i (row indices) row = %d length = %d",ii,i[ii+1] - i[ii]); 38029985e31cSBarry Smith for (jj=i[ii]+1; jj<i[ii+1]; jj++) { 3803e32f2f54SBarry Smith if (j[jj] < j[jj-1]) SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Column entry number %D (actual colum %D) in row %D is not sorted",jj-i[ii],j[jj],ii); 3804e32f2f54SBarry Smith if (j[jj] == j[jj]-1) SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Column entry number %D (actual colum %D) in row %D is identical to previous entry",jj-i[ii],j[jj],ii); 38059985e31cSBarry Smith } 380636db0b34SBarry Smith #endif 380736db0b34SBarry Smith } 38082515c552SBarry Smith #if defined(PETSC_USE_DEBUG) 380936db0b34SBarry Smith for (ii=0; ii<aij->i[m]; ii++) { 3810e32f2f54SBarry Smith if (j[ii] < 0) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Negative column index at location = %d index = %d",ii,j[ii]); 3811e32f2f54SBarry Smith if (j[ii] > n - 1) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Column index to large at location = %d index = %d",ii,j[ii]); 381236db0b34SBarry Smith } 381336db0b34SBarry Smith #endif 381436db0b34SBarry Smith 3815b65db4caSBarry Smith ierr = MatAssemblyBegin(*mat,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 3816b65db4caSBarry Smith ierr = MatAssemblyEnd(*mat,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 381736db0b34SBarry Smith PetscFunctionReturn(0); 381836db0b34SBarry Smith } 381936db0b34SBarry Smith 3820cc8ba8e1SBarry Smith #undef __FUNCT__ 3821ee4f033dSBarry Smith #define __FUNCT__ "MatSetColoring_SeqAIJ" 3822dfbe8321SBarry Smith PetscErrorCode MatSetColoring_SeqAIJ(Mat A,ISColoring coloring) 3823cc8ba8e1SBarry Smith { 3824dfbe8321SBarry Smith PetscErrorCode ierr; 3825cc8ba8e1SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 382636db0b34SBarry Smith 3827cc8ba8e1SBarry Smith PetscFunctionBegin; 38288ee2e534SBarry Smith if (coloring->ctype == IS_COLORING_GLOBAL) { 3829cc8ba8e1SBarry Smith ierr = ISColoringReference(coloring);CHKERRQ(ierr); 3830cc8ba8e1SBarry Smith a->coloring = coloring; 383112c595b3SBarry Smith } else if (coloring->ctype == IS_COLORING_GHOSTED) { 383297f1f81fSBarry Smith PetscInt i,*larray; 383312c595b3SBarry Smith ISColoring ocoloring; 383408b6dcc0SBarry Smith ISColoringValue *colors; 383512c595b3SBarry Smith 383612c595b3SBarry Smith /* set coloring for diagonal portion */ 38370e83c824SBarry Smith ierr = PetscMalloc(A->cmap->n*sizeof(PetscInt),&larray);CHKERRQ(ierr); 3838d0f46423SBarry Smith for (i=0; i<A->cmap->n; i++) { 383912c595b3SBarry Smith larray[i] = i; 384012c595b3SBarry Smith } 3841784ac674SJed Brown ierr = ISGlobalToLocalMappingApply(A->cmapping,IS_GTOLM_MASK,A->cmap->n,larray,PETSC_NULL,larray);CHKERRQ(ierr); 38420e83c824SBarry Smith ierr = PetscMalloc(A->cmap->n*sizeof(ISColoringValue),&colors);CHKERRQ(ierr); 3843d0f46423SBarry Smith for (i=0; i<A->cmap->n; i++) { 384412c595b3SBarry Smith colors[i] = coloring->colors[larray[i]]; 384512c595b3SBarry Smith } 384612c595b3SBarry Smith ierr = PetscFree(larray);CHKERRQ(ierr); 3847d0f46423SBarry Smith ierr = ISColoringCreate(PETSC_COMM_SELF,coloring->n,A->cmap->n,colors,&ocoloring);CHKERRQ(ierr); 384812c595b3SBarry Smith a->coloring = ocoloring; 384912c595b3SBarry Smith } 3850cc8ba8e1SBarry Smith PetscFunctionReturn(0); 3851cc8ba8e1SBarry Smith } 3852cc8ba8e1SBarry Smith 3853dcf5cc72SBarry Smith #if defined(PETSC_HAVE_ADIC) 3854ee4f033dSBarry Smith EXTERN_C_BEGIN 385529c1e371SBarry Smith #include "adic/ad_utils.h" 3856ee4f033dSBarry Smith EXTERN_C_END 3857cc8ba8e1SBarry Smith 3858cc8ba8e1SBarry Smith #undef __FUNCT__ 3859ee4f033dSBarry Smith #define __FUNCT__ "MatSetValuesAdic_SeqAIJ" 3860dfbe8321SBarry Smith PetscErrorCode MatSetValuesAdic_SeqAIJ(Mat A,void *advalues) 3861cc8ba8e1SBarry Smith { 3862cc8ba8e1SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 3863d0f46423SBarry Smith PetscInt m = A->rmap->n,*ii = a->i,*jj = a->j,nz,i,j,nlen; 38644440f671SBarry Smith PetscScalar *v = a->a,*values = ((PetscScalar*)advalues)+1; 386508b6dcc0SBarry Smith ISColoringValue *color; 3866cc8ba8e1SBarry Smith 3867cc8ba8e1SBarry Smith PetscFunctionBegin; 3868e32f2f54SBarry Smith if (!a->coloring) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Coloring not set for matrix"); 38694440f671SBarry Smith nlen = PetscADGetDerivTypeSize()/sizeof(PetscScalar); 3870cc8ba8e1SBarry Smith color = a->coloring->colors; 3871cc8ba8e1SBarry Smith /* loop over rows */ 3872cc8ba8e1SBarry Smith for (i=0; i<m; i++) { 3873cc8ba8e1SBarry Smith nz = ii[i+1] - ii[i]; 3874cc8ba8e1SBarry Smith /* loop over columns putting computed value into matrix */ 3875cc8ba8e1SBarry Smith for (j=0; j<nz; j++) { 3876cc8ba8e1SBarry Smith *v++ = values[color[*jj++]]; 3877cc8ba8e1SBarry Smith } 38784440f671SBarry Smith values += nlen; /* jump to next row of derivatives */ 3879ee4f033dSBarry Smith } 3880ee4f033dSBarry Smith PetscFunctionReturn(0); 3881ee4f033dSBarry Smith } 3882ee4f033dSBarry Smith #endif 3883ee4f033dSBarry Smith 3884ee4f033dSBarry Smith #undef __FUNCT__ 3885ee4f033dSBarry Smith #define __FUNCT__ "MatSetValuesAdifor_SeqAIJ" 388697f1f81fSBarry Smith PetscErrorCode MatSetValuesAdifor_SeqAIJ(Mat A,PetscInt nl,void *advalues) 3887ee4f033dSBarry Smith { 3888ee4f033dSBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 3889d0f46423SBarry Smith PetscInt m = A->rmap->n,*ii = a->i,*jj = a->j,nz,i,j; 389054f21887SBarry Smith MatScalar *v = a->a; 389154f21887SBarry Smith PetscScalar *values = (PetscScalar *)advalues; 389208b6dcc0SBarry Smith ISColoringValue *color; 3893ee4f033dSBarry Smith 3894ee4f033dSBarry Smith PetscFunctionBegin; 3895e32f2f54SBarry Smith if (!a->coloring) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Coloring not set for matrix"); 3896ee4f033dSBarry Smith color = a->coloring->colors; 3897ee4f033dSBarry Smith /* loop over rows */ 3898ee4f033dSBarry Smith for (i=0; i<m; i++) { 3899ee4f033dSBarry Smith nz = ii[i+1] - ii[i]; 3900ee4f033dSBarry Smith /* loop over columns putting computed value into matrix */ 3901ee4f033dSBarry Smith for (j=0; j<nz; j++) { 3902ee4f033dSBarry Smith *v++ = values[color[*jj++]]; 3903ee4f033dSBarry Smith } 3904ee4f033dSBarry Smith values += nl; /* jump to next row of derivatives */ 3905cc8ba8e1SBarry Smith } 3906cc8ba8e1SBarry Smith PetscFunctionReturn(0); 3907cc8ba8e1SBarry Smith } 390836db0b34SBarry Smith 390981824310SBarry Smith /* 391081824310SBarry Smith Special version for direct calls from Fortran 391181824310SBarry Smith */ 39127087cfbeSBarry Smith #include "private/fortranimpl.h" 391381824310SBarry Smith #if defined(PETSC_HAVE_FORTRAN_CAPS) 391481824310SBarry Smith #define matsetvaluesseqaij_ MATSETVALUESSEQAIJ 391581824310SBarry Smith #elif !defined(PETSC_HAVE_FORTRAN_UNDERSCORE) 391681824310SBarry Smith #define matsetvaluesseqaij_ matsetvaluesseqaij 391781824310SBarry Smith #endif 391881824310SBarry Smith 391981824310SBarry Smith /* Change these macros so can be used in void function */ 392081824310SBarry Smith #undef CHKERRQ 39217adad957SLisandro Dalcin #define CHKERRQ(ierr) CHKERRABORT(((PetscObject)A)->comm,ierr) 392281824310SBarry Smith #undef SETERRQ2 3923e32f2f54SBarry Smith #define SETERRQ2(comm,ierr,b,c,d) CHKERRABORT(comm,ierr) 392481824310SBarry Smith 392581824310SBarry Smith EXTERN_C_BEGIN 392681824310SBarry Smith #undef __FUNCT__ 392781824310SBarry Smith #define __FUNCT__ "matsetvaluesseqaij_" 39281f6cc5b2SSatish Balay void PETSC_STDCALL matsetvaluesseqaij_(Mat *AA,PetscInt *mm,const PetscInt im[],PetscInt *nn,const PetscInt in[],const PetscScalar v[],InsertMode *isis, PetscErrorCode *_ierr) 392981824310SBarry Smith { 393081824310SBarry Smith Mat A = *AA; 393181824310SBarry Smith PetscInt m = *mm, n = *nn; 393281824310SBarry Smith InsertMode is = *isis; 393381824310SBarry Smith Mat_SeqAIJ *a = (Mat_SeqAIJ*)A->data; 393481824310SBarry Smith PetscInt *rp,k,low,high,t,ii,row,nrow,i,col,l,rmax,N; 393581824310SBarry Smith PetscInt *imax,*ai,*ailen; 393681824310SBarry Smith PetscErrorCode ierr; 393781824310SBarry Smith PetscInt *aj,nonew = a->nonew,lastcol = -1; 393854f21887SBarry Smith MatScalar *ap,value,*aa; 3939ace3abfcSBarry Smith PetscBool ignorezeroentries = a->ignorezeroentries; 3940ace3abfcSBarry Smith PetscBool roworiented = a->roworiented; 394181824310SBarry Smith 394281824310SBarry Smith PetscFunctionBegin; 3943d9e2c085SLisandro Dalcin ierr = MatPreallocated(A);CHKERRQ(ierr); 394481824310SBarry Smith imax = a->imax; 394581824310SBarry Smith ai = a->i; 394681824310SBarry Smith ailen = a->ilen; 394781824310SBarry Smith aj = a->j; 394881824310SBarry Smith aa = a->a; 394981824310SBarry Smith 395081824310SBarry Smith for (k=0; k<m; k++) { /* loop over added rows */ 395181824310SBarry Smith row = im[k]; 395281824310SBarry Smith if (row < 0) continue; 395381824310SBarry Smith #if defined(PETSC_USE_DEBUG) 3954d0f46423SBarry Smith if (row >= A->rmap->n) SETERRABORT(((PetscObject)A)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Row too large"); 395581824310SBarry Smith #endif 395681824310SBarry Smith rp = aj + ai[row]; ap = aa + ai[row]; 395781824310SBarry Smith rmax = imax[row]; nrow = ailen[row]; 395881824310SBarry Smith low = 0; 395981824310SBarry Smith high = nrow; 396081824310SBarry Smith for (l=0; l<n; l++) { /* loop over added columns */ 396181824310SBarry Smith if (in[l] < 0) continue; 396281824310SBarry Smith #if defined(PETSC_USE_DEBUG) 3963d0f46423SBarry Smith if (in[l] >= A->cmap->n) SETERRABORT(((PetscObject)A)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Column too large"); 396481824310SBarry Smith #endif 396581824310SBarry Smith col = in[l]; 396681824310SBarry Smith if (roworiented) { 396781824310SBarry Smith value = v[l + k*n]; 396881824310SBarry Smith } else { 396981824310SBarry Smith value = v[k + l*m]; 397081824310SBarry Smith } 397181824310SBarry Smith if (value == 0.0 && ignorezeroentries && (is == ADD_VALUES)) continue; 397281824310SBarry Smith 397381824310SBarry Smith if (col <= lastcol) low = 0; else high = nrow; 397481824310SBarry Smith lastcol = col; 397581824310SBarry Smith while (high-low > 5) { 397681824310SBarry Smith t = (low+high)/2; 397781824310SBarry Smith if (rp[t] > col) high = t; 397881824310SBarry Smith else low = t; 397981824310SBarry Smith } 398081824310SBarry Smith for (i=low; i<high; i++) { 398181824310SBarry Smith if (rp[i] > col) break; 398281824310SBarry Smith if (rp[i] == col) { 398381824310SBarry Smith if (is == ADD_VALUES) ap[i] += value; 398481824310SBarry Smith else ap[i] = value; 398581824310SBarry Smith goto noinsert; 398681824310SBarry Smith } 398781824310SBarry Smith } 398881824310SBarry Smith if (value == 0.0 && ignorezeroentries) goto noinsert; 398981824310SBarry Smith if (nonew == 1) goto noinsert; 39907adad957SLisandro Dalcin if (nonew == -1) SETERRABORT(((PetscObject)A)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Inserting a new nonzero in the matrix"); 3991fef13f97SBarry Smith MatSeqXAIJReallocateAIJ(A,A->rmap->n,1,nrow,row,col,rmax,aa,ai,aj,rp,ap,imax,nonew,MatScalar); 399281824310SBarry Smith N = nrow++ - 1; a->nz++; high++; 399381824310SBarry Smith /* shift up all the later entries in this row */ 399481824310SBarry Smith for (ii=N; ii>=i; ii--) { 399581824310SBarry Smith rp[ii+1] = rp[ii]; 399681824310SBarry Smith ap[ii+1] = ap[ii]; 399781824310SBarry Smith } 399881824310SBarry Smith rp[i] = col; 399981824310SBarry Smith ap[i] = value; 400081824310SBarry Smith noinsert:; 400181824310SBarry Smith low = i + 1; 400281824310SBarry Smith } 400381824310SBarry Smith ailen[row] = nrow; 400481824310SBarry Smith } 400581824310SBarry Smith A->same_nonzero = PETSC_FALSE; 400681824310SBarry Smith PetscFunctionReturnVoid(); 400781824310SBarry Smith } 400881824310SBarry Smith EXTERN_C_END 400962298a1eSBarry Smith 4010