#include /*I "petscmat.h" I*/ PetscErrorCode MatConvert_Shell(Mat oldmat, MatType newtype,MatReuse reuse,Mat *newmat) { Mat mat; Vec in,out; MPI_Comm comm; PetscScalar *array; PetscInt *dnnz,*onnz,*dnnzu,*onnzu; PetscInt cst,Nbs,mbs,nbs,rbs,cbs; PetscInt im,i,m,n,M,N,*rows,start; PetscErrorCode ierr; PetscFunctionBegin; ierr = PetscObjectGetComm((PetscObject)oldmat,&comm);CHKERRQ(ierr); ierr = MatGetOwnershipRange(oldmat,&start,NULL);CHKERRQ(ierr); ierr = MatGetOwnershipRangeColumn(oldmat,&cst,NULL);CHKERRQ(ierr); ierr = MatCreateVecs(oldmat,&in,&out);CHKERRQ(ierr); ierr = MatGetLocalSize(oldmat,&m,&n);CHKERRQ(ierr); ierr = MatGetSize(oldmat,&M,&N);CHKERRQ(ierr); ierr = PetscMalloc1(m,&rows);CHKERRQ(ierr); ierr = MatCreate(comm,&mat);CHKERRQ(ierr); ierr = MatSetSizes(mat,m,n,M,N);CHKERRQ(ierr); ierr = MatSetType(mat,newtype);CHKERRQ(ierr); ierr = MatSetBlockSizesFromMats(mat,oldmat,oldmat);CHKERRQ(ierr); ierr = MatGetBlockSizes(mat,&rbs,&cbs);CHKERRQ(ierr); mbs = m/rbs; nbs = n/cbs; Nbs = N/cbs; cst = cst/cbs; ierr = PetscMalloc4(mbs,&dnnz,mbs,&onnz,mbs,&dnnzu,mbs,&onnzu);CHKERRQ(ierr); for (i=0; irmap->n,A->cmap->n,A->rmap->N,A->cmap->N,A,&M);CHKERRQ(ierr); ierr = MatSetBlockSizesFromMats(M,A,A);CHKERRQ(ierr); ierr = MatShellSetOperation(M,MATOP_MULT, (void (*)(void))MatMult_CF);CHKERRQ(ierr); ierr = MatShellSetOperation(M,MATOP_MULT_TRANSPOSE,(void (*)(void))MatMultTranspose_CF);CHKERRQ(ierr); ierr = MatShellSetOperation(M,MATOP_GET_DIAGONAL, (void (*)(void))MatGetDiagonal_CF);CHKERRQ(ierr); ierr = MatShellSetOperation(M,MATOP_DESTROY, (void (*)(void))MatDestroy_CF);CHKERRQ(ierr); *B = M; } else SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"Not implemented"); PetscFunctionReturn(0); }