예제 #1
0
int main(int argc, char **args)
{
  PetscErrorCode  ierr;
  ierr = PetscInitialize(&argc, &args, (char *) 0, ""); CHKERRQ(ierr);
  ierr = PetscPrintf(PETSC_COMM_WORLD, "Start %s\n", __FILE__); CHKERRQ(ierr);
  MPI_Comm comm = PETSC_COMM_WORLD;

  DA da;
  Mat mat;
  int MX = 100;
  int dof = 3;

  ierr = PetscPrintf(comm,"Started Assembly\n"); CHKERRQ(ierr);
  ierr = MatMake(MX,dof,&da, &mat); CHKERRQ(ierr);
  ierr = MatWrite("J",mat); CHKERRQ(ierr);
  ierr = PetscPrintf(comm,"Finished Assembly\n"); CHKERRQ(ierr);

  Vec rhs, sol;
  ierr = DACreateGlobalVector(da,&rhs); CHKERRQ(ierr);
  ierr = DACreateGlobalVector(da,&sol); CHKERRQ(ierr);

  int i,j;
  int xs,ys,xm,ym;
  Field **array;
  ierr = DAVecGetArray(da,rhs,&array); CHKERRQ(ierr);
  ierr = DAGetCorners(da,&xs,&ys,PETSC_NULL,&xm,&ym,PETSC_NULL); CHKERRQ(ierr);
  for (j = xs; j < xm; ++j) {
    for (i = ys; i < ym; ++i) {
      if( 3*MX/4 > i && i > MX/4 &&
          3*MX/4 > j && j > MX/4  )
      {
        array[j][i].u = 100.;
        array[j][i].v = 100.;
      }
    }
  }
  ierr = DAVecRestoreArray(da,rhs,&array); CHKERRQ(ierr);


  KSP ksp;
  ierr = KSPCreate(comm,&ksp); CHKERRQ(ierr);
  ierr = KSPSetType(ksp,KSPPREONLY); CHKERRQ(ierr);
  ierr = KSPSetOperators(ksp,mat,mat,DIFFERENT_NONZERO_PATTERN); CHKERRQ(ierr);
  ierr = KSPSetFromOptions(ksp);CHKERRQ(ierr);

  //Split pressure from velocity
  PC pc;
  ierr = KSPGetPC(ksp,&pc); CHKERRQ(ierr);
  ierr = PCSetType(pc, PCFIELDSPLIT); CHKERRQ(ierr);
  ierr = PCFieldSplitSetType(pc,PC_COMPOSITE_SCHUR); CHKERRQ(ierr);
  ierr = PCFieldSplitSetBlockSize(pc,3); CHKERRQ(ierr);
  ierr = PCFieldSplitSetFields(pc,2,(int[]){0,1}); CHKERRQ(ierr);
예제 #2
0
PETSC_EXTERN void PETSC_STDCALL  pcfieldsplitsettype_(PC pc,PCCompositeType *type, int *__ierr ){
*__ierr = PCFieldSplitSetType(
	(PC)PetscToPointer((pc) ),*type);
}
예제 #3
0
파일: FluidField.c 프로젝트: adrielb/DCell
PetscErrorCode FluidFieldSetup( FluidField f )
{
  PetscLogDouble t1,t2;
  PetscErrorCode ierr;

  PetscFunctionBegin;

  // Assemble viscous matricies
  ierr = FluidFieldMatAssemble( f ); CHKERRQ(ierr);

  ierr = PetscInfo3( 0, "Lengths: %e %e %e\n", f->lens.x, f->lens.y, f->lens.z ); CHKERRQ(ierr);
  ierr = PetscInfo3( 0,    "Size: %d %d %d\n", f->dims.x, f->dims.y, f->dims.z ); CHKERRQ(ierr);
  ierr = PetscInfo3( 0,      "dx: %e %e %e\n", f->dh.x,   f->dh.y,   f->dh.z ); CHKERRQ(ierr);

  ierr = PetscTime(&t1); CHKERRQ(ierr);

  // Create vectors
  ierr = GACreate( f->daV, &f->ga); CHKERRQ(ierr);
  ierr = DMCreateGlobalVector(f->daV,&f->rhs); CHKERRQ(ierr);
  ierr = VecDuplicate(f->rhs,&f->vel); CHKERRQ(ierr);
  ierr = VecDuplicate(f->rhs,&f->vel0); CHKERRQ(ierr);
//  ierr = DACreateGlobalVector(f->daE,&f->E); CHKERRQ(ierr);
  ierr = DMCreateGlobalVector(f->daB,&f->buf); CHKERRQ(ierr);

  // Set up the outer solver
  ierr = KSPCreate(f->comm,&f->ksp); CHKERRQ(ierr);
  ierr = KSPSetOperators(f->ksp,f->mat,f->mat, SAME_PRECONDITIONER); CHKERRQ(ierr);
  ierr = KSPSetType(f->ksp,KSPFGMRES); CHKERRQ(ierr);
  ierr = KSPSetInitialGuessNonzero(f->ksp,PETSC_TRUE); CHKERRQ(ierr);
  ierr = KSPSetTolerances(f->ksp,PETSC_DEFAULT,PETSC_DEFAULT,PETSC_DEFAULT,PETSC_DEFAULT); CHKERRQ(ierr);
  ierr = KSPSetFromOptions(f->ksp);CHKERRQ(ierr);

  // Split pressure from velocity [ u v w | p ]
  PC pc;
  ierr = KSPGetPC(f->ksp,&pc); CHKERRQ(ierr);
  ierr = PCSetType(pc, PCFIELDSPLIT); CHKERRQ(ierr);
  ierr = PCFieldSplitSetType(pc,PC_COMPOSITE_SCHUR); CHKERRQ(ierr);
  if( f->is3D ) {
	const PetscInt ufields[] = {U_FACE,V_FACE,W_FACE};
	const PetscInt pfields[] = {CELL_CENTER};
    ierr = PCFieldSplitSetBlockSize(pc,4); CHKERRQ(ierr);                  // [p u v w]
    ierr = PCFieldSplitSetFields(pc,"v",3,ufields,ufields); CHKERRQ(ierr); // [u v w]
    ierr = PCFieldSplitSetFields(pc,"p",1,pfields,pfields); CHKERRQ(ierr); // [ p ]
  } else {
	const PetscInt ufields[] = {U_FACE,V_FACE};
	const PetscInt pfields[] = {CELL_CENTER};
    ierr = PCFieldSplitSetBlockSize(pc,3); CHKERRQ(ierr);                      // [p u v]
    ierr = PCFieldSplitSetFields(pc,"v",2,ufields,ufields); CHKERRQ(ierr);  // [u v]
    ierr = PCFieldSplitSetFields(pc,"p",1,pfields,pfields); CHKERRQ(ierr);    // [ p ]
  }
  ierr = PCSetUp(pc); CHKERRQ(ierr);
  int nVelP;
  KSP *kspVelP;
  ierr = PCFieldSplitGetSubKSP(pc,&nVelP,&kspVelP); CHKERRQ(ierr);
  ierr = KSPSetTolerances(kspVelP[1],PETSC_DEFAULT,PETSC_DEFAULT,PETSC_DEFAULT,4); CHKERRQ(ierr);
  ierr = KSPSetType(kspVelP[1],KSPGMRES); CHKERRQ(ierr);
  ierr = KSPGetPC(kspVelP[1],&pc); CHKERRQ(ierr);
  ierr = PCSetType(pc,PCNONE); CHKERRQ(ierr);
  ierr = KSPSetFromOptions(kspVelP[1]);CHKERRQ(ierr);

  // Split velocity [u v w] into component matricies [u], [v], [w]
  ierr = KSPSetType(kspVelP[0],KSPPREONLY); CHKERRQ(ierr);
  ierr = KSPGetPC(kspVelP[0],&pc); CHKERRQ(ierr);
  ierr = PCSetType(pc, PCFIELDSPLIT); CHKERRQ(ierr);
  ierr = PCFieldSplitSetType(pc,PC_COMPOSITE_ADDITIVE); CHKERRQ(ierr);
  ierr = PCFieldSplitSetBlockSize(pc,f->is3D?3:2); CHKERRQ(ierr);
  ierr = PCSetUp(pc); CHKERRQ(ierr);

  /* Set solver for each velocity component
   * Split component velocity as parallel blocks along processors
   * Use direct solver for each block
   * TODO: use MG, w/FFT on coarse grid
   */

  ierr = PetscTime(&t2); CHKERRQ(ierr);
  ierr = PetscPrintf(PETSC_COMM_WORLD,"Finished Solver Setup: %f sec\n",t2-t1); CHKERRQ(ierr);

  PetscFunctionReturn(0);
}
예제 #4
0
void
SolverLinearPetsc<T>::setPetscPreconditionerType()
{

    int ierr = 0;
#if (PETSC_VERSION_MAJOR == 3) && (PETSC_VERSION_MINOR >= 2)
    ierr = PCFactorSetMatSolverPackage( M_pc,MATSOLVERUMFPACK );

    if ( ierr )
    {
        ierr = PCFactorSetMatSolverPackage( M_pc,MATSOLVERSUPERLU );

        if ( ierr )
        {
            ierr = PCFactorSetMatSolverPackage( M_pc,MATSOLVERPETSC );
        }
    }

#elif (PETSC_VERSION_MAJOR >= 3)
    ierr = PCFactorSetMatSolverPackage( M_pc,MAT_SOLVER_UMFPACK );

    if ( ierr )
    {
        ierr = PCFactorSetMatSolverPackage( M_pc,MAT_SOLVER_SUPERLU );

        if ( ierr )
        {
            ierr = PCFactorSetMatSolverPackage( M_pc,MAT_SOLVER_PETSC );
        }
    }

#endif
    DVLOG(2) << "[SolverLinearPetsc] preconditioner type:  " << this->preconditionerType() << "\n";

    switch ( this->preconditionerType() )
    {
    case IDENTITY_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCNONE );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

    case CHOLESKY_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCCHOLESKY );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

    case ICC_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCICC );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

    case ILU_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCILU );
        CHKERRABORT( this->worldComm().globalComm(),ierr );

        if ( this->vm().count( "pc-factor-levels" ) )
        {
            PCFactorSetLevels( M_pc,this->vm()["pc-factor-levels"].template as<int>() );
        }

        else
            PCFactorSetLevels( M_pc,3 );

        if ( this->vm().count( "pc-factor-fill" ) )
        {
            PCFactorSetFill( M_pc,this->vm()["pc-factor-fill"].template as<double>() );
        }

        else
            PCFactorSetFill( M_pc,40 );

        return;

    case LU_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCLU );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

    case ASM_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCASM );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

#if PETSC_VERSION_GREATER_OR_EQUAL_THAN( 3,2,0 )
    case GASM_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCGASM );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;
#endif

    case JACOBI_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCJACOBI );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

    case BLOCK_JACOBI_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCBJACOBI );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

    case SOR_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCSOR );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

    case EISENSTAT_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCEISENSTAT );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

#if !((PETSC_VERSION_MAJOR == 2) && (PETSC_VERSION_MINOR <= 1) && (PETSC_VERSION_SUBMINOR <= 1))

    case USER_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCMAT );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;
#endif

    case SHELL_PRECOND:
        ierr = PCSetType ( M_pc, ( char* ) PCSHELL );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

    case FIELDSPLIT_PRECOND:
        ierr = PCSetType( M_pc,( char* ) PCFIELDSPLIT );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        ierr = PCFieldSplitSetType( M_pc,PC_COMPOSITE_SCHUR );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

    case ML_PRECOND:
        ierr = PCSetType( M_pc,( char* ) PCML );
        CHKERRABORT( this->worldComm().globalComm(),ierr );
        return;

    default:
        std::cerr << "ERROR:  Unsupported PETSC Preconditioner: "
                  << this->preconditionerType()       << std::endl
                  << "Continuing with PETSC defaults" << std::endl;
    }

}
예제 #5
0
  ierr = PCFieldSplitSetFields(pc,2,(int[]){0,1}); CHKERRQ(ierr);
  ierr = PCFieldSplitSetFields(pc,1,(int[]){2}); CHKERRQ(ierr);
  ierr = PCSetUp(pc); CHKERRQ(ierr);

  //Split velocity into u-v component matricies
  int nVelP;
  KSP *kspVelP;
  ierr = PCFieldSplitGetSubKSP(pc,&nVelP,&kspVelP); CHKERRQ(ierr);
  ierr = KSPSetTolerances(kspVelP[1],1e-50,1e-3,PETSC_DEFAULT,PETSC_DEFAULT); CHKERRQ(ierr);
//  ierr = KSPSetType(kspVelP[1],KSPCG); CHKERRQ(ierr);
  ierr = KSPGetPC(kspVelP[1],&pc); CHKERRQ(ierr);
  ierr = PCSetType(pc,PCNONE); CHKERRQ(ierr);
  ierr = KSPSetType(kspVelP[0],KSPPREONLY); CHKERRQ(ierr);
  ierr = KSPGetPC(kspVelP[0],&pc); CHKERRQ(ierr);
  ierr = PCSetType(pc, PCFIELDSPLIT); CHKERRQ(ierr);
  ierr = PCFieldSplitSetType(pc,PC_COMPOSITE_ADDITIVE); CHKERRQ(ierr);
  ierr = PCFieldSplitSetBlockSize(pc,2); CHKERRQ(ierr);
  ierr = PCSetUp(pc); CHKERRQ(ierr);

  //Set solver for each velocity component
  int nVel;
  KSP *kspVel;
  ierr = PCFieldSplitGetSubKSP(pc,&nVel,&kspVel); CHKERRQ(ierr);
  for( i = 0; i < nVel; i++ ) {
    // Direct Method
    ierr = KSPSetType(kspVel[i],KSPPREONLY); CHKERRQ(ierr);
    ierr = KSPGetPC(kspVel[i],&pc); CHKERRQ(ierr);
    ierr = PCSetType(pc,PCCHOLESKY); CHKERRQ(ierr);
    ierr = PCFactorSetMatOrderingType(pc,MATORDERING_ND); CHKERRQ(ierr);
    ierr = PCSetUp(pc); CHKERRQ(ierr);
    //