xref: /petsc/src/mat/impls/aij/seq/umfpack/umfpack.c (revision 9f42a82ab117685d629089f63335d2ae3b9ced74)
1be1d678aSKris Buschelman #define PETSCMAT_DLL
21677d0b8SKris Buschelman 
31677d0b8SKris Buschelman /*
42d4e2982SHong Zhang    Provides an interface to the UMFPACKv5.1 sparse solver
52d4e2982SHong Zhang 
62d4e2982SHong Zhang    This interface uses the "UF_long version" of the UMFPACK API
72d4e2982SHong Zhang    (*_dl_* and *_zl_* routines, instead of *_di_* and *_zi_* routines)
82d4e2982SHong Zhang    so that UMFPACK can address more than 2Gb of memory on 64 bit
92d4e2982SHong Zhang    machines.
102d4e2982SHong Zhang 
112d4e2982SHong Zhang    If sizeof(UF_long) == 32 the interface only allocates the memory
122d4e2982SHong Zhang    necessary for UMFPACK's working arrays (W, Wi and possibly
132d4e2982SHong Zhang    perm_c). If sizeof(UF_long) == 64, in addition to allocating the
142d4e2982SHong Zhang    working arrays, the interface also has to re-allocate the matrix
152d4e2982SHong Zhang    index arrays (ai and aj, which must be stored as UF_long).
162d4e2982SHong Zhang 
172d4e2982SHong Zhang    The interface is implemented for both real and complex
182d4e2982SHong Zhang    arithmetic. Complex numbers are assumed to be in packed format,
192d4e2982SHong Zhang    which requires UMFPACK >= 4.4.
202d4e2982SHong Zhang 
212d4e2982SHong Zhang    We thank Christophe Geuzaine <geuzaine@acm.caltech.edu> for upgrading this interface to the UMFPACKv5.1
221677d0b8SKris Buschelman */
231677d0b8SKris Buschelman 
241677d0b8SKris Buschelman #include "src/mat/impls/aij/seq/aij.h"
251677d0b8SKris Buschelman 
261677d0b8SKris Buschelman EXTERN_C_BEGIN
271677d0b8SKris Buschelman #include "umfpack.h"
281677d0b8SKris Buschelman EXTERN_C_END
291677d0b8SKris Buschelman 
301677d0b8SKris Buschelman typedef struct {
311677d0b8SKris Buschelman   void         *Symbolic, *Numeric;
321677d0b8SKris Buschelman   double       Info[UMFPACK_INFO], Control[UMFPACK_CONTROL],*W;
332d4e2982SHong Zhang   UF_long      *Wi,*ai,*aj,*perm_c;
341677d0b8SKris Buschelman   PetscScalar  *av;
351677d0b8SKris Buschelman   MatStructure flg;
361677d0b8SKris Buschelman   PetscTruth   PetscMatOdering;
371677d0b8SKris Buschelman 
381677d0b8SKris Buschelman   /* A few function pointers for inheritance */
396849ba73SBarry Smith   PetscErrorCode (*MatDuplicate)(Mat,MatDuplicateOption,Mat*);
406849ba73SBarry Smith   PetscErrorCode (*MatView)(Mat,PetscViewer);
416849ba73SBarry Smith   PetscErrorCode (*MatAssemblyEnd)(Mat,MatAssemblyType);
426849ba73SBarry Smith   PetscErrorCode (*MatLUFactorSymbolic)(Mat,IS,IS,MatFactorInfo*,Mat*);
436849ba73SBarry Smith   PetscErrorCode (*MatDestroy)(Mat);
441677d0b8SKris Buschelman 
451677d0b8SKris Buschelman   /* Flag to clean up UMFPACK objects during Destroy */
461677d0b8SKris Buschelman   PetscTruth CleanUpUMFPACK;
47f0c56d0fSKris Buschelman } Mat_UMFPACK;
48f0c56d0fSKris Buschelman 
49dfbe8321SBarry Smith EXTERN PetscErrorCode MatDuplicate_UMFPACK(Mat,MatDuplicateOption,Mat*);
50d844382dSKris Buschelman 
51d844382dSKris Buschelman EXTERN_C_BEGIN
52d844382dSKris Buschelman #undef __FUNCT__
53d844382dSKris Buschelman #define __FUNCT__ "MatConvert_UMFPACK_SeqAIJ"
5475179d2cSHong Zhang PetscErrorCode PETSCMAT_DLLEXPORT MatConvert_UMFPACK_SeqAIJ(Mat A,MatType type,MatReuse reuse,Mat *newmat)
556849ba73SBarry Smith {
56dfbe8321SBarry Smith   PetscErrorCode ierr;
57d844382dSKris Buschelman   Mat         B=*newmat;
58f0c56d0fSKris Buschelman   Mat_UMFPACK *lu=(Mat_UMFPACK*)A->spptr;
59d844382dSKris Buschelman 
60d844382dSKris Buschelman   PetscFunctionBegin;
61ceb03754SKris Buschelman   if (reuse == MAT_INITIAL_MATRIX) {
62d844382dSKris Buschelman     ierr = MatDuplicate(A,MAT_COPY_VALUES,&B);CHKERRQ(ierr);
63f0c56d0fSKris Buschelman   }
64d844382dSKris Buschelman   /* Reset the original function pointers */
65901853e0SKris Buschelman   B->ops->duplicate        = lu->MatDuplicate;
66901853e0SKris Buschelman   B->ops->view             = lu->MatView;
67901853e0SKris Buschelman   B->ops->assemblyend      = lu->MatAssemblyEnd;
68901853e0SKris Buschelman   B->ops->lufactorsymbolic = lu->MatLUFactorSymbolic;
69901853e0SKris Buschelman   B->ops->destroy          = lu->MatDestroy;
70901853e0SKris Buschelman 
71901853e0SKris Buschelman   ierr = PetscObjectComposeFunction((PetscObject)B,"MatConvert_seqaij_umfpack_C","",PETSC_NULL);CHKERRQ(ierr);
72901853e0SKris Buschelman   ierr = PetscObjectComposeFunction((PetscObject)B,"MatConvert_umfpack_seqaij_C","",PETSC_NULL);CHKERRQ(ierr);
73901853e0SKris Buschelman 
74d844382dSKris Buschelman   ierr = PetscObjectChangeTypeName((PetscObject)B,MATSEQAIJ);CHKERRQ(ierr);
75d844382dSKris Buschelman   *newmat = B;
76d844382dSKris Buschelman   PetscFunctionReturn(0);
77d844382dSKris Buschelman }
78d844382dSKris Buschelman EXTERN_C_END
791677d0b8SKris Buschelman 
801677d0b8SKris Buschelman #undef __FUNCT__
81f0c56d0fSKris Buschelman #define __FUNCT__ "MatDestroy_UMFPACK"
82dfbe8321SBarry Smith PetscErrorCode MatDestroy_UMFPACK(Mat A)
83dfbe8321SBarry Smith {
84dfbe8321SBarry Smith   PetscErrorCode ierr;
85f0c56d0fSKris Buschelman   Mat_UMFPACK *lu=(Mat_UMFPACK*)A->spptr;
861677d0b8SKris Buschelman 
871677d0b8SKris Buschelman   PetscFunctionBegin;
88fb731535SKris Buschelman   if (lu->CleanUpUMFPACK) {
892d4e2982SHong Zhang #if defined(PETSC_USE_COMPLEX)
902d4e2982SHong Zhang     umfpack_zl_free_symbolic(&lu->Symbolic);
912d4e2982SHong Zhang     umfpack_zl_free_numeric(&lu->Numeric);
922d4e2982SHong Zhang #else
932d4e2982SHong Zhang     umfpack_dl_free_symbolic(&lu->Symbolic);
942d4e2982SHong Zhang     umfpack_dl_free_numeric(&lu->Numeric);
952d4e2982SHong Zhang #endif
961677d0b8SKris Buschelman     ierr = PetscFree(lu->Wi);CHKERRQ(ierr);
971677d0b8SKris Buschelman     ierr = PetscFree(lu->W);CHKERRQ(ierr);
982d4e2982SHong Zhang     if(sizeof(UF_long) != sizeof(int)){
992d4e2982SHong Zhang       ierr = PetscFree(lu->ai);CHKERRQ(ierr);
1002d4e2982SHong Zhang       ierr = PetscFree(lu->aj);CHKERRQ(ierr);
1012d4e2982SHong Zhang     }
1021677d0b8SKris Buschelman     if (lu->PetscMatOdering) {
1031677d0b8SKris Buschelman       ierr = PetscFree(lu->perm_c);CHKERRQ(ierr);
1041677d0b8SKris Buschelman     }
1051677d0b8SKris Buschelman   }
106ceb03754SKris Buschelman   ierr = MatConvert_UMFPACK_SeqAIJ(A,MATSEQAIJ,MAT_REUSE_MATRIX,&A);CHKERRQ(ierr);
107d844382dSKris Buschelman   ierr = (*A->ops->destroy)(A);CHKERRQ(ierr);
1081677d0b8SKris Buschelman   PetscFunctionReturn(0);
1091677d0b8SKris Buschelman }
1101677d0b8SKris Buschelman 
1111677d0b8SKris Buschelman #undef __FUNCT__
112f0c56d0fSKris Buschelman #define __FUNCT__ "MatSolve_UMFPACK"
1136849ba73SBarry Smith PetscErrorCode MatSolve_UMFPACK(Mat A,Vec b,Vec x)
1146849ba73SBarry Smith {
115f0c56d0fSKris Buschelman   Mat_UMFPACK *lu = (Mat_UMFPACK*)A->spptr;
1161677d0b8SKris Buschelman   PetscScalar *av=lu->av,*ba,*xa;
117dfbe8321SBarry Smith   PetscErrorCode ierr;
1182d4e2982SHong Zhang   UF_long     *ai=lu->ai,*aj=lu->aj,status;
1191677d0b8SKris Buschelman 
1201677d0b8SKris Buschelman   PetscFunctionBegin;
1212d4e2982SHong Zhang   /* solve Ax = b by umfpack_*_wsolve */
1221677d0b8SKris Buschelman   /* ----------------------------------*/
1232d4e2982SHong Zhang 
1242d4e2982SHong Zhang #if defined(PETSC_USE_COMPLEX)
1252d4e2982SHong Zhang   ierr = VecConjugate(b);
1262d4e2982SHong Zhang #endif
1272d4e2982SHong Zhang 
1281677d0b8SKris Buschelman   ierr = VecGetArray(b,&ba);
1291677d0b8SKris Buschelman   ierr = VecGetArray(x,&xa);
1301677d0b8SKris Buschelman 
1312d4e2982SHong Zhang #if defined(PETSC_USE_COMPLEX)
1322d4e2982SHong Zhang   status = umfpack_zl_wsolve(UMFPACK_At,ai,aj,(double*)av,NULL,(double*)xa,NULL,(double*)ba,NULL,
1332d4e2982SHong Zhang 			     lu->Numeric,lu->Control,lu->Info,lu->Wi,lu->W);
1342d4e2982SHong Zhang   umfpack_zl_report_info(lu->Control, lu->Info);
1351677d0b8SKris Buschelman   if (status < 0){
1362d4e2982SHong Zhang     umfpack_zl_report_status(lu->Control, status);
1372d4e2982SHong Zhang     SETERRQ(PETSC_ERR_LIB,"umfpack_zl_wsolve failed");
1381677d0b8SKris Buschelman   }
1392d4e2982SHong Zhang #else
1402d4e2982SHong Zhang   status = umfpack_dl_wsolve(UMFPACK_At,ai,aj,av,xa,ba,
1412d4e2982SHong Zhang 			     lu->Numeric,lu->Control,lu->Info,lu->Wi,lu->W);
1422d4e2982SHong Zhang   umfpack_dl_report_info(lu->Control, lu->Info);
1432d4e2982SHong Zhang   if (status < 0){
1442d4e2982SHong Zhang     umfpack_dl_report_status(lu->Control, status);
1452d4e2982SHong Zhang     SETERRQ(PETSC_ERR_LIB,"umfpack_dl_wsolve failed");
1462d4e2982SHong Zhang   }
1472d4e2982SHong Zhang #endif
1481677d0b8SKris Buschelman 
1491677d0b8SKris Buschelman   ierr = VecRestoreArray(b,&ba);
1501677d0b8SKris Buschelman   ierr = VecRestoreArray(x,&xa);
1512a325a84SHong Zhang 
1522d4e2982SHong Zhang #if defined(PETSC_USE_COMPLEX)
1532d4e2982SHong Zhang   ierr = VecConjugate(b);
1545b2a9f60SHong Zhang   ierr = VecConjugate(x);
1552d4e2982SHong Zhang #endif
1562d4e2982SHong Zhang 
1571677d0b8SKris Buschelman   PetscFunctionReturn(0);
1581677d0b8SKris Buschelman }
1591677d0b8SKris Buschelman 
1601677d0b8SKris Buschelman #undef __FUNCT__
161f0c56d0fSKris Buschelman #define __FUNCT__ "MatLUFactorNumeric_UMFPACK"
162af281ebdSHong Zhang PetscErrorCode MatLUFactorNumeric_UMFPACK(Mat A,MatFactorInfo *info,Mat *F)
1636849ba73SBarry Smith {
164f0c56d0fSKris Buschelman   Mat_UMFPACK *lu=(Mat_UMFPACK*)(*F)->spptr;
1656849ba73SBarry Smith   PetscErrorCode ierr;
1662d4e2982SHong Zhang   UF_long     *ai=lu->ai,*aj=lu->aj,m=A->rmap.n,status;
1671677d0b8SKris Buschelman   PetscScalar *av=lu->av;
1681677d0b8SKris Buschelman 
1691677d0b8SKris Buschelman   PetscFunctionBegin;
1701677d0b8SKris Buschelman   /* numeric factorization of A' */
1711677d0b8SKris Buschelman   /* ----------------------------*/
1722d4e2982SHong Zhang 
1732d4e2982SHong Zhang #if defined(PETSC_USE_COMPLEX)
1742a325a84SHong Zhang   if (lu->flg == SAME_NONZERO_PATTERN && lu->Numeric){
1752d4e2982SHong Zhang     umfpack_zl_free_numeric(&lu->Numeric);
1762a325a84SHong Zhang   }
1772d4e2982SHong Zhang   status = umfpack_zl_numeric(ai,aj,(double*)av,NULL,lu->Symbolic,&lu->Numeric,lu->Control,lu->Info);
178*9f42a82aSMatthew Knepley   if (status < 0) {
179*9f42a82aSMatthew Knepley     umfpack_zl_report_status(lu->Control, status);
180*9f42a82aSMatthew Knepley     SETERRQ(PETSC_ERR_LIB,"umfpack_zl_numeric failed");
181*9f42a82aSMatthew Knepley   }
1821677d0b8SKris Buschelman   /* report numeric factorization of A' when Control[PRL] > 3 */
1832d4e2982SHong Zhang   (void) umfpack_zl_report_numeric(lu->Numeric, lu->Control);
1842d4e2982SHong Zhang #else
1852d4e2982SHong Zhang   if (lu->flg == SAME_NONZERO_PATTERN && lu->Numeric){
1862d4e2982SHong Zhang     umfpack_dl_free_numeric(&lu->Numeric);
1872d4e2982SHong Zhang   }
1882d4e2982SHong Zhang   status = umfpack_dl_numeric(ai,aj,av,lu->Symbolic,&lu->Numeric,lu->Control,lu->Info);
189*9f42a82aSMatthew Knepley   if (status < 0) {
190*9f42a82aSMatthew Knepley     umfpack_zl_report_status(lu->Control, status);
191*9f42a82aSMatthew Knepley     SETERRQ(PETSC_ERR_LIB,"umfpack_dl_numeric failed");
192*9f42a82aSMatthew Knepley   }
1932d4e2982SHong Zhang   /* report numeric factorization of A' when Control[PRL] > 3 */
1942d4e2982SHong Zhang   (void) umfpack_dl_report_numeric(lu->Numeric, lu->Control);
1952d4e2982SHong Zhang #endif
1961677d0b8SKris Buschelman 
1971677d0b8SKris Buschelman   if (lu->flg == DIFFERENT_NONZERO_PATTERN){  /* first numeric factorization */
1981677d0b8SKris Buschelman     /* allocate working space to be used by Solve */
1992d4e2982SHong Zhang     ierr = PetscMalloc(m * sizeof(UF_long), &lu->Wi);CHKERRQ(ierr);
2002d4e2982SHong Zhang #if defined(PETSC_USE_COMPLEX)
2012d4e2982SHong Zhang     ierr = PetscMalloc(2*5*m * sizeof(double), &lu->W);CHKERRQ(ierr);
2022d4e2982SHong Zhang #else
2031677d0b8SKris Buschelman     ierr = PetscMalloc(5*m * sizeof(double), &lu->W);CHKERRQ(ierr);
2042d4e2982SHong Zhang #endif
2051677d0b8SKris Buschelman   }
2062d4e2982SHong Zhang 
2072a325a84SHong Zhang   lu->flg = SAME_NONZERO_PATTERN;
2082a325a84SHong Zhang   lu->CleanUpUMFPACK = PETSC_TRUE;
2091677d0b8SKris Buschelman   PetscFunctionReturn(0);
2101677d0b8SKris Buschelman }
2111677d0b8SKris Buschelman 
2121677d0b8SKris Buschelman /*
2131677d0b8SKris Buschelman    Note the r permutation is ignored
2141677d0b8SKris Buschelman */
2151677d0b8SKris Buschelman #undef __FUNCT__
216f0c56d0fSKris Buschelman #define __FUNCT__ "MatLUFactorSymbolic_UMFPACK"
2176849ba73SBarry Smith PetscErrorCode MatLUFactorSymbolic_UMFPACK(Mat A,IS r,IS c,MatFactorInfo *info,Mat *F)
2186849ba73SBarry Smith {
219e1b4c3a1SKris Buschelman   Mat         B;
2201677d0b8SKris Buschelman   Mat_SeqAIJ  *mat=(Mat_SeqAIJ*)A->data;
221f0c56d0fSKris Buschelman   Mat_UMFPACK *lu;
222dfbe8321SBarry Smith   PetscErrorCode ierr;
2232d4e2982SHong Zhang   int         i,m=A->rmap.n,n=A->cmap.n,*ra,idx;
2242d4e2982SHong Zhang   UF_long     status;
2252d4e2982SHong Zhang 
2261677d0b8SKris Buschelman   PetscScalar *av=mat->a;
2270f6efc10SHong Zhang   const char  *strategy[]={"AUTO","UNSYMMETRIC","SYMMETRIC","2BY2"},
2280f6efc10SHong Zhang               *scale[]={"NONE","SUM","MAX"};
2290f6efc10SHong Zhang   PetscTruth  flg;
2301677d0b8SKris Buschelman 
2311677d0b8SKris Buschelman   PetscFunctionBegin;
2321677d0b8SKris Buschelman   /* Create the factorization matrix F */
2337adad957SLisandro Dalcin   ierr = MatCreate(((PetscObject)A)->comm,&B);CHKERRQ(ierr);
234f69a0ea3SMatthew Knepley   ierr = MatSetSizes(B,PETSC_DECIDE,PETSC_DECIDE,m,n);CHKERRQ(ierr);
2357adad957SLisandro Dalcin   ierr = MatSetType(B,((PetscObject)A)->type_name);CHKERRQ(ierr);
236e1b4c3a1SKris Buschelman   ierr = MatSeqAIJSetPreallocation(B,0,PETSC_NULL);CHKERRQ(ierr);
2371677d0b8SKris Buschelman 
238f0c56d0fSKris Buschelman   B->ops->lufactornumeric = MatLUFactorNumeric_UMFPACK;
239f0c56d0fSKris Buschelman   B->ops->solve           = MatSolve_UMFPACK;
240e1b4c3a1SKris Buschelman   B->factor               = FACTOR_LU;
24194b7f48cSBarry Smith   B->assembled            = PETSC_TRUE;  /* required by -ksp_view */
2421677d0b8SKris Buschelman 
243f0c56d0fSKris Buschelman   lu = (Mat_UMFPACK*)(B->spptr);
2441677d0b8SKris Buschelman 
2451677d0b8SKris Buschelman   /* initializations */
2461677d0b8SKris Buschelman   /* ------------------------------------------------*/
2471677d0b8SKris Buschelman   /* get the default control parameters */
2482d4e2982SHong Zhang #if defined(PETSC_USE_COMPLEX)
2492d4e2982SHong Zhang   umfpack_zl_defaults(lu->Control);
2502d4e2982SHong Zhang #else
2512d4e2982SHong Zhang   umfpack_dl_defaults(lu->Control);
2522d4e2982SHong Zhang #endif
2531677d0b8SKris Buschelman   lu->perm_c = PETSC_NULL;  /* use defaul UMFPACK col permutation */
2540f6efc10SHong Zhang   lu->Control[UMFPACK_IRSTEP] = 0; /* max num of iterative refinement steps to attempt */
2551677d0b8SKris Buschelman 
2567adad957SLisandro Dalcin   ierr = PetscOptionsBegin(((PetscObject)A)->comm,((PetscObject)A)->prefix,"UMFPACK Options","Mat");CHKERRQ(ierr);
2571677d0b8SKris Buschelman   /* Control parameters used by reporting routiones */
2581677d0b8SKris Buschelman   ierr = PetscOptionsReal("-mat_umfpack_prl","Control[UMFPACK_PRL]","None",lu->Control[UMFPACK_PRL],&lu->Control[UMFPACK_PRL],PETSC_NULL);CHKERRQ(ierr);
2591677d0b8SKris Buschelman 
2601677d0b8SKris Buschelman   /* Control parameters for symbolic factorization */
2610f6efc10SHong Zhang   ierr = PetscOptionsEList("-mat_umfpack_strategy","ordering and pivoting strategy","None",strategy,4,strategy[0],&idx,&flg);CHKERRQ(ierr);
2620f6efc10SHong Zhang   if (flg) {
2630f6efc10SHong Zhang     switch (idx){
2640f6efc10SHong Zhang     case 0: lu->Control[UMFPACK_STRATEGY] = UMFPACK_STRATEGY_AUTO; break;
2650f6efc10SHong Zhang     case 1: lu->Control[UMFPACK_STRATEGY] = UMFPACK_STRATEGY_UNSYMMETRIC; break;
2660f6efc10SHong Zhang     case 2: lu->Control[UMFPACK_STRATEGY] = UMFPACK_STRATEGY_SYMMETRIC; break;
2670f6efc10SHong Zhang     case 3: lu->Control[UMFPACK_STRATEGY] = UMFPACK_STRATEGY_2BY2; break;
2680f6efc10SHong Zhang     }
2690f6efc10SHong Zhang   }
2701677d0b8SKris Buschelman   ierr = PetscOptionsReal("-mat_umfpack_dense_col","Control[UMFPACK_DENSE_COL]","None",lu->Control[UMFPACK_DENSE_COL],&lu->Control[UMFPACK_DENSE_COL],PETSC_NULL);CHKERRQ(ierr);
2711677d0b8SKris Buschelman   ierr = PetscOptionsReal("-mat_umfpack_dense_row","Control[UMFPACK_DENSE_ROW]","None",lu->Control[UMFPACK_DENSE_ROW],&lu->Control[UMFPACK_DENSE_ROW],PETSC_NULL);CHKERRQ(ierr);
2720f6efc10SHong Zhang   ierr = PetscOptionsReal("-mat_umfpack_amd_dense","Control[UMFPACK_AMD_DENSE]","None",lu->Control[UMFPACK_AMD_DENSE],&lu->Control[UMFPACK_AMD_DENSE],PETSC_NULL);CHKERRQ(ierr);
2731677d0b8SKris Buschelman   ierr = PetscOptionsReal("-mat_umfpack_block_size","Control[UMFPACK_BLOCK_SIZE]","None",lu->Control[UMFPACK_BLOCK_SIZE],&lu->Control[UMFPACK_BLOCK_SIZE],PETSC_NULL);CHKERRQ(ierr);
2740f6efc10SHong Zhang   ierr = PetscOptionsReal("-mat_umfpack_2by2_tolerance","Control[UMFPACK_2BY2_TOLERANCE]","None",lu->Control[UMFPACK_2BY2_TOLERANCE],&lu->Control[UMFPACK_2BY2_TOLERANCE],PETSC_NULL);CHKERRQ(ierr);
2750f6efc10SHong Zhang   ierr = PetscOptionsReal("-mat_umfpack_fixq","Control[UMFPACK_FIXQ]","None",lu->Control[UMFPACK_FIXQ],&lu->Control[UMFPACK_FIXQ],PETSC_NULL);CHKERRQ(ierr);
2760f6efc10SHong Zhang   ierr = PetscOptionsReal("-mat_umfpack_aggressive","Control[UMFPACK_AGGRESSIVE]","None",lu->Control[UMFPACK_AGGRESSIVE],&lu->Control[UMFPACK_AGGRESSIVE],PETSC_NULL);CHKERRQ(ierr);
2771677d0b8SKris Buschelman 
2781677d0b8SKris Buschelman   /* Control parameters used by numeric factorization */
2791677d0b8SKris Buschelman   ierr = PetscOptionsReal("-mat_umfpack_pivot_tolerance","Control[UMFPACK_PIVOT_TOLERANCE]","None",lu->Control[UMFPACK_PIVOT_TOLERANCE],&lu->Control[UMFPACK_PIVOT_TOLERANCE],PETSC_NULL);CHKERRQ(ierr);
2800f6efc10SHong Zhang   ierr = PetscOptionsReal("-mat_umfpack_sym_pivot_tolerance","Control[UMFPACK_SYM_PIVOT_TOLERANCE]","None",lu->Control[UMFPACK_SYM_PIVOT_TOLERANCE],&lu->Control[UMFPACK_SYM_PIVOT_TOLERANCE],PETSC_NULL);CHKERRQ(ierr);
2810f6efc10SHong Zhang   ierr = PetscOptionsEList("-mat_umfpack_scale","Control[UMFPACK_SCALE]","None",scale,3,scale[0],&idx,&flg);CHKERRQ(ierr);
2820f6efc10SHong Zhang   if (flg) {
2830f6efc10SHong Zhang     switch (idx){
2840f6efc10SHong Zhang     case 0: lu->Control[UMFPACK_SCALE] = UMFPACK_SCALE_NONE; break;
2850f6efc10SHong Zhang     case 1: lu->Control[UMFPACK_SCALE] = UMFPACK_SCALE_SUM; break;
2860f6efc10SHong Zhang     case 2: lu->Control[UMFPACK_SCALE] = UMFPACK_SCALE_MAX; break;
2870f6efc10SHong Zhang     }
2880f6efc10SHong Zhang   }
2891677d0b8SKris Buschelman   ierr = PetscOptionsReal("-mat_umfpack_alloc_init","Control[UMFPACK_ALLOC_INIT]","None",lu->Control[UMFPACK_ALLOC_INIT],&lu->Control[UMFPACK_ALLOC_INIT],PETSC_NULL);CHKERRQ(ierr);
2900f6efc10SHong Zhang   ierr = PetscOptionsReal("-mat_umfpack_front_alloc_init","Control[UMFPACK_FRONT_ALLOC_INIT]","None",lu->Control[UMFPACK_FRONT_ALLOC_INIT],&lu->Control[UMFPACK_ALLOC_INIT],PETSC_NULL);CHKERRQ(ierr);
2910f6efc10SHong Zhang   ierr = PetscOptionsReal("-mat_umfpack_droptol","Control[UMFPACK_DROPTOL]","None",lu->Control[UMFPACK_DROPTOL],&lu->Control[UMFPACK_DROPTOL],PETSC_NULL);CHKERRQ(ierr);
2921677d0b8SKris Buschelman 
2931677d0b8SKris Buschelman   /* Control parameters used by solve */
2941677d0b8SKris Buschelman   ierr = PetscOptionsReal("-mat_umfpack_irstep","Control[UMFPACK_IRSTEP]","None",lu->Control[UMFPACK_IRSTEP],&lu->Control[UMFPACK_IRSTEP],PETSC_NULL);CHKERRQ(ierr);
2951677d0b8SKris Buschelman 
2960f6efc10SHong Zhang   /* use Petsc mat ordering (note: size is for the transpose, and PETSc r = Umfpack perm_c) */
2972401956bSBarry Smith   ierr = PetscOptionsHasName(PETSC_NULL,"-pc_factor_mat_ordering_type",&lu->PetscMatOdering);CHKERRQ(ierr);
2981677d0b8SKris Buschelman   if (lu->PetscMatOdering) {
2990f6efc10SHong Zhang     ierr = ISGetIndices(r,&ra);CHKERRQ(ierr);
3002d4e2982SHong Zhang     ierr = PetscMalloc(m*sizeof(UF_long),&lu->perm_c);CHKERRQ(ierr);
3012d4e2982SHong Zhang     /* we cannot simply memcpy on 64 bit archs */
3022d4e2982SHong Zhang     for(i = 0; i < m; i++) lu->perm_c[i] = ra[i];
3030f6efc10SHong Zhang     ierr = ISRestoreIndices(r,&ra);CHKERRQ(ierr);
3041677d0b8SKris Buschelman   }
3051677d0b8SKris Buschelman   PetscOptionsEnd();
3061677d0b8SKris Buschelman 
3072d4e2982SHong Zhang   if(sizeof(UF_long) != sizeof(int)){
3082d4e2982SHong Zhang     /* we cannot directly use mat->i and mat->j on 64 bit archs */
3092d4e2982SHong Zhang     ierr = PetscMalloc((m+1)*sizeof(UF_long),&lu->ai);CHKERRQ(ierr);
3102d4e2982SHong Zhang     ierr = PetscMalloc(mat->nz*sizeof(UF_long),&lu->aj);CHKERRQ(ierr);
3112d4e2982SHong Zhang     for(i = 0; i < m + 1; i++) lu->ai[i] = mat->i[i];
3122d4e2982SHong Zhang     for(i = 0; i < mat->nz; i++) lu->aj[i] = mat->j[i];
3132d4e2982SHong Zhang   }
3142d4e2982SHong Zhang   else{
3152d4e2982SHong Zhang     lu->ai = (UF_long*)mat->i;
3162d4e2982SHong Zhang     lu->aj = (UF_long*)mat->j;
3172d4e2982SHong Zhang   }
3182d4e2982SHong Zhang 
3191677d0b8SKris Buschelman   /* print the control parameters */
3202d4e2982SHong Zhang #if defined(PETSC_USE_COMPLEX)
3212d4e2982SHong Zhang   if(lu->Control[UMFPACK_PRL] > 1) umfpack_zl_report_control(lu->Control);
3222d4e2982SHong Zhang #else
3232d4e2982SHong Zhang   if(lu->Control[UMFPACK_PRL] > 1) umfpack_dl_report_control(lu->Control);
3242d4e2982SHong Zhang #endif
3251677d0b8SKris Buschelman 
3261677d0b8SKris Buschelman   /* symbolic factorization of A' */
3271677d0b8SKris Buschelman   /* ---------------------------------------------------------------------- */
3282d4e2982SHong Zhang #if defined(PETSC_USE_COMPLEX)
3290f6efc10SHong Zhang   if (lu->PetscMatOdering) { /* use Petsc row ordering */
3302d4e2982SHong Zhang     status = umfpack_zl_qsymbolic(n,m,lu->ai,lu->aj,(double*)av,NULL,
3312d4e2982SHong Zhang 				  lu->perm_c,&lu->Symbolic,lu->Control,lu->Info);
3320f6efc10SHong Zhang   } else { /* use Umfpack col ordering */
3332d4e2982SHong Zhang     status = umfpack_zl_symbolic(n,m,lu->ai,lu->aj,(double*)av,NULL,
3342d4e2982SHong Zhang 				 &lu->Symbolic,lu->Control,lu->Info);
3350f6efc10SHong Zhang   }
3361677d0b8SKris Buschelman   if (status < 0){
3372d4e2982SHong Zhang     umfpack_zl_report_info(lu->Control, lu->Info);
3382d4e2982SHong Zhang     umfpack_zl_report_status(lu->Control, status);
3392d4e2982SHong Zhang     SETERRQ(PETSC_ERR_LIB,"umfpack_dl_symbolic failed");
3401677d0b8SKris Buschelman   }
3411677d0b8SKris Buschelman   /* report sumbolic factorization of A' when Control[PRL] > 3 */
3422d4e2982SHong Zhang   (void) umfpack_zl_report_symbolic(lu->Symbolic, lu->Control);
3432d4e2982SHong Zhang #else
3442d4e2982SHong Zhang   if (lu->PetscMatOdering) { /* use Petsc row ordering */
3452d4e2982SHong Zhang     status = umfpack_dl_qsymbolic(n,m,lu->ai,lu->aj,av,
3462d4e2982SHong Zhang 				  lu->perm_c,&lu->Symbolic,lu->Control,lu->Info);
3472d4e2982SHong Zhang   } else { /* use Umfpack col ordering */
3482d4e2982SHong Zhang     status = umfpack_dl_symbolic(n,m,lu->ai,lu->aj,av,
3492d4e2982SHong Zhang 				 &lu->Symbolic,lu->Control,lu->Info);
3502d4e2982SHong Zhang   }
3512d4e2982SHong Zhang   if (status < 0){
3522d4e2982SHong Zhang     umfpack_dl_report_info(lu->Control, lu->Info);
3532d4e2982SHong Zhang     umfpack_dl_report_status(lu->Control, status);
3542d4e2982SHong Zhang     SETERRQ(PETSC_ERR_LIB,"umfpack_dl_symbolic failed");
3552d4e2982SHong Zhang   }
3562d4e2982SHong Zhang   /* report sumbolic factorization of A' when Control[PRL] > 3 */
3572d4e2982SHong Zhang   (void) umfpack_dl_report_symbolic(lu->Symbolic, lu->Control);
3582d4e2982SHong Zhang #endif
3591677d0b8SKris Buschelman 
3601677d0b8SKris Buschelman   lu->flg = DIFFERENT_NONZERO_PATTERN;
3611677d0b8SKris Buschelman   lu->av  = av;
362e1b4c3a1SKris Buschelman   lu->CleanUpUMFPACK = PETSC_TRUE;
363e1b4c3a1SKris Buschelman   *F = B;
3641677d0b8SKris Buschelman   PetscFunctionReturn(0);
3651677d0b8SKris Buschelman }
3661677d0b8SKris Buschelman 
3671677d0b8SKris Buschelman #undef __FUNCT__
368f0c56d0fSKris Buschelman #define __FUNCT__ "MatAssemblyEnd_UMFPACK"
3696849ba73SBarry Smith PetscErrorCode MatAssemblyEnd_UMFPACK(Mat A,MatAssemblyType mode)
3706849ba73SBarry Smith {
371dfbe8321SBarry Smith   PetscErrorCode ierr;
372f0c56d0fSKris Buschelman   Mat_UMFPACK *lu=(Mat_UMFPACK*)(A->spptr);
373d844382dSKris Buschelman 
3741677d0b8SKris Buschelman   PetscFunctionBegin;
375d844382dSKris Buschelman   ierr = (*lu->MatAssemblyEnd)(A,mode);CHKERRQ(ierr);
376d844382dSKris Buschelman   lu->MatLUFactorSymbolic  = A->ops->lufactorsymbolic;
377f0c56d0fSKris Buschelman   A->ops->lufactorsymbolic = MatLUFactorSymbolic_UMFPACK;
3781677d0b8SKris Buschelman   PetscFunctionReturn(0);
3791677d0b8SKris Buschelman }
3801677d0b8SKris Buschelman 
38194b7f48cSBarry Smith /* used by -ksp_view */
3821677d0b8SKris Buschelman #undef __FUNCT__
383f0c56d0fSKris Buschelman #define __FUNCT__ "MatFactorInfo_UMFPACK"
3846849ba73SBarry Smith PetscErrorCode MatFactorInfo_UMFPACK(Mat A,PetscViewer viewer)
3856849ba73SBarry Smith {
386f0c56d0fSKris Buschelman   Mat_UMFPACK *lu= (Mat_UMFPACK*)A->spptr;
387dfbe8321SBarry Smith   PetscErrorCode ierr;
388f0c56d0fSKris Buschelman 
3891677d0b8SKris Buschelman   PetscFunctionBegin;
3901677d0b8SKris Buschelman   /* check if matrix is UMFPACK type */
391f0c56d0fSKris Buschelman   if (A->ops->solve != MatSolve_UMFPACK) PetscFunctionReturn(0);
3921677d0b8SKris Buschelman 
3931677d0b8SKris Buschelman   ierr = PetscViewerASCIIPrintf(viewer,"UMFPACK run parameters:\n");CHKERRQ(ierr);
3941677d0b8SKris Buschelman   /* Control parameters used by reporting routiones */
3951677d0b8SKris Buschelman   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_PRL]: %g\n",lu->Control[UMFPACK_PRL]);CHKERRQ(ierr);
3961677d0b8SKris Buschelman 
3971677d0b8SKris Buschelman   /* Control parameters used by symbolic factorization */
3980f6efc10SHong Zhang   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_STRATEGY]: %g\n",lu->Control[UMFPACK_STRATEGY]);CHKERRQ(ierr);
3991677d0b8SKris Buschelman   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_DENSE_COL]: %g\n",lu->Control[UMFPACK_DENSE_COL]);CHKERRQ(ierr);
4001677d0b8SKris Buschelman   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_DENSE_ROW]: %g\n",lu->Control[UMFPACK_DENSE_ROW]);CHKERRQ(ierr);
4010f6efc10SHong Zhang   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_AMD_DENSE]: %g\n",lu->Control[UMFPACK_AMD_DENSE]);CHKERRQ(ierr);
4021677d0b8SKris Buschelman   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_BLOCK_SIZE]: %g\n",lu->Control[UMFPACK_BLOCK_SIZE]);CHKERRQ(ierr);
4030f6efc10SHong Zhang   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_2BY2_TOLERANCE]: %g\n",lu->Control[UMFPACK_2BY2_TOLERANCE]);CHKERRQ(ierr);
4040f6efc10SHong Zhang   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_FIXQ]: %g\n",lu->Control[UMFPACK_FIXQ]);CHKERRQ(ierr);
4050f6efc10SHong Zhang   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_AGGRESSIVE]: %g\n",lu->Control[UMFPACK_AGGRESSIVE]);CHKERRQ(ierr);
4061677d0b8SKris Buschelman 
4071677d0b8SKris Buschelman   /* Control parameters used by numeric factorization */
4081677d0b8SKris Buschelman   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_PIVOT_TOLERANCE]: %g\n",lu->Control[UMFPACK_PIVOT_TOLERANCE]);CHKERRQ(ierr);
4090f6efc10SHong Zhang   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_SYM_PIVOT_TOLERANCE]: %g\n",lu->Control[UMFPACK_SYM_PIVOT_TOLERANCE]);CHKERRQ(ierr);
4100f6efc10SHong Zhang   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_SCALE]: %g\n",lu->Control[UMFPACK_SCALE]);CHKERRQ(ierr);
4111677d0b8SKris Buschelman   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_ALLOC_INIT]: %g\n",lu->Control[UMFPACK_ALLOC_INIT]);CHKERRQ(ierr);
4120f6efc10SHong Zhang   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_DROPTOL]: %g\n",lu->Control[UMFPACK_DROPTOL]);CHKERRQ(ierr);
4131677d0b8SKris Buschelman 
4141677d0b8SKris Buschelman   /* Control parameters used by solve */
4151677d0b8SKris Buschelman   ierr = PetscViewerASCIIPrintf(viewer,"  Control[UMFPACK_IRSTEP]: %g\n",lu->Control[UMFPACK_IRSTEP]);CHKERRQ(ierr);
4161677d0b8SKris Buschelman 
4171677d0b8SKris Buschelman   /* mat ordering */
4181677d0b8SKris Buschelman   if(!lu->PetscMatOdering) ierr = PetscViewerASCIIPrintf(viewer,"  UMFPACK default matrix ordering is used (not the PETSc matrix ordering) \n");CHKERRQ(ierr);
4191677d0b8SKris Buschelman 
4201677d0b8SKris Buschelman   PetscFunctionReturn(0);
4211677d0b8SKris Buschelman }
4221677d0b8SKris Buschelman 
423d844382dSKris Buschelman #undef __FUNCT__
424f0c56d0fSKris Buschelman #define __FUNCT__ "MatView_UMFPACK"
4256849ba73SBarry Smith PetscErrorCode MatView_UMFPACK(Mat A,PetscViewer viewer)
4266849ba73SBarry Smith {
427dfbe8321SBarry Smith   PetscErrorCode ierr;
42832077d6dSBarry Smith   PetscTruth        iascii;
429d844382dSKris Buschelman   PetscViewerFormat format;
430f0c56d0fSKris Buschelman   Mat_UMFPACK       *lu=(Mat_UMFPACK*)(A->spptr);
431d844382dSKris Buschelman 
432d844382dSKris Buschelman   PetscFunctionBegin;
433d844382dSKris Buschelman   ierr = (*lu->MatView)(A,viewer);CHKERRQ(ierr);
434d844382dSKris Buschelman 
43532077d6dSBarry Smith   ierr = PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&iascii);CHKERRQ(ierr);
43632077d6dSBarry Smith   if (iascii) {
437d844382dSKris Buschelman     ierr = PetscViewerGetFormat(viewer,&format);CHKERRQ(ierr);
4382f59403fSHong Zhang     if (format == PETSC_VIEWER_ASCII_INFO) {
439f0c56d0fSKris Buschelman       ierr = MatFactorInfo_UMFPACK(A,viewer);CHKERRQ(ierr);
440d844382dSKris Buschelman     }
441d844382dSKris Buschelman   }
442d844382dSKris Buschelman   PetscFunctionReturn(0);
443d844382dSKris Buschelman }
444d844382dSKris Buschelman 
445d844382dSKris Buschelman EXTERN_C_BEGIN
446d844382dSKris Buschelman #undef __FUNCT__
447d844382dSKris Buschelman #define __FUNCT__ "MatConvert_SeqAIJ_UMFPACK"
44875179d2cSHong Zhang PetscErrorCode PETSCMAT_DLLEXPORT MatConvert_SeqAIJ_UMFPACK(Mat A,MatType type,MatReuse reuse,Mat *newmat)
4496849ba73SBarry Smith {
450dfbe8321SBarry Smith   PetscErrorCode ierr;
451d844382dSKris Buschelman   Mat            B=*newmat;
452f0c56d0fSKris Buschelman   Mat_UMFPACK    *lu;
453d844382dSKris Buschelman 
454d844382dSKris Buschelman   PetscFunctionBegin;
455ceb03754SKris Buschelman   if (reuse == MAT_INITIAL_MATRIX) {
456d844382dSKris Buschelman     ierr = MatDuplicate(A,MAT_COPY_VALUES,&B);CHKERRQ(ierr);
457d844382dSKris Buschelman   }
458bebc3af9SBarry Smith   B->ops->matsolve = 0;
459d844382dSKris Buschelman 
46038f2d2fdSLisandro Dalcin   ierr = PetscNewLog(B,Mat_UMFPACK,&lu);CHKERRQ(ierr);
461f0c56d0fSKris Buschelman   lu->MatDuplicate         = A->ops->duplicate;
462d844382dSKris Buschelman   lu->MatView              = A->ops->view;
463d844382dSKris Buschelman   lu->MatAssemblyEnd       = A->ops->assemblyend;
464d844382dSKris Buschelman   lu->MatLUFactorSymbolic  = A->ops->lufactorsymbolic;
465d844382dSKris Buschelman   lu->MatDestroy           = A->ops->destroy;
466d844382dSKris Buschelman   lu->CleanUpUMFPACK       = PETSC_FALSE;
467d844382dSKris Buschelman 
468d844382dSKris Buschelman   B->spptr                 = (void*)lu;
469f0c56d0fSKris Buschelman   B->ops->duplicate        = MatDuplicate_UMFPACK;
470f0c56d0fSKris Buschelman   B->ops->view             = MatView_UMFPACK;
471f0c56d0fSKris Buschelman   B->ops->assemblyend      = MatAssemblyEnd_UMFPACK;
472f0c56d0fSKris Buschelman   B->ops->lufactorsymbolic = MatLUFactorSymbolic_UMFPACK;
473f0c56d0fSKris Buschelman   B->ops->destroy          = MatDestroy_UMFPACK;
474d844382dSKris Buschelman 
475d844382dSKris Buschelman   ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatConvert_seqaij_umfpack_C",
476d844382dSKris Buschelman                                            "MatConvert_SeqAIJ_UMFPACK",MatConvert_SeqAIJ_UMFPACK);CHKERRQ(ierr);
477d844382dSKris Buschelman   ierr = PetscObjectComposeFunctionDynamic((PetscObject)B,"MatConvert_umfpack_seqaij_C",
478d844382dSKris Buschelman                                            "MatConvert_UMFPACK_SeqAIJ",MatConvert_UMFPACK_SeqAIJ);CHKERRQ(ierr);
4791e2582c4SBarry Smith   ierr = PetscInfo(A,"Using UMFPACK for SeqAIJ LU factorization and solves.\n");CHKERRQ(ierr);
480d844382dSKris Buschelman   ierr = PetscObjectChangeTypeName((PetscObject)B,MATUMFPACK);CHKERRQ(ierr);
481d844382dSKris Buschelman   *newmat = B;
482d844382dSKris Buschelman   PetscFunctionReturn(0);
483d844382dSKris Buschelman }
484d844382dSKris Buschelman EXTERN_C_END
485d844382dSKris Buschelman 
486f0c56d0fSKris Buschelman #undef __FUNCT__
487f0c56d0fSKris Buschelman #define __FUNCT__ "MatDuplicate_UMFPACK"
4886849ba73SBarry Smith PetscErrorCode MatDuplicate_UMFPACK(Mat A, MatDuplicateOption op, Mat *M)
4896849ba73SBarry Smith {
490dfbe8321SBarry Smith   PetscErrorCode ierr;
4918f340917SKris Buschelman   Mat_UMFPACK *lu=(Mat_UMFPACK*)A->spptr;
4928f340917SKris Buschelman 
493f0c56d0fSKris Buschelman   PetscFunctionBegin;
4948f340917SKris Buschelman   ierr = (*lu->MatDuplicate)(A,op,M);CHKERRQ(ierr);
4953f953163SKris Buschelman   ierr = PetscMemcpy((*M)->spptr,lu,sizeof(Mat_UMFPACK));CHKERRQ(ierr);
496f0c56d0fSKris Buschelman   PetscFunctionReturn(0);
497f0c56d0fSKris Buschelman }
498f0c56d0fSKris Buschelman 
4992f71e704SKris Buschelman /*MC
500fafad747SKris Buschelman   MATUMFPACK - MATUMFPACK = "umfpack" - A matrix type providing direct solvers (LU) for sequential matrices
5012f71e704SKris Buschelman   via the external package UMFPACK.
5022f71e704SKris Buschelman 
5032f71e704SKris Buschelman   If UMFPACK is installed (see the manual for
5042f71e704SKris Buschelman   instructions on how to declare the existence of external packages),
5052f71e704SKris Buschelman   a matrix type can be constructed which invokes UMFPACK solvers.
5062f71e704SKris Buschelman   After calling MatCreate(...,A), simply call MatSetType(A,UMFPACK).
5072f71e704SKris Buschelman 
5082f71e704SKris Buschelman   This matrix inherits from MATSEQAIJ.  As a result, MatSeqAIJSetPreallocation is
50928b08bd3SKris Buschelman   supported for this matrix type.  One can also call MatConvert for an inplace conversion to or from
51028b08bd3SKris Buschelman   the MATSEQAIJ type without data copy.
5112f71e704SKris Buschelman 
5122f71e704SKris Buschelman   Consult UMFPACK documentation for more information about the Control parameters
5132f71e704SKris Buschelman   which correspond to the options database keys below.
5142f71e704SKris Buschelman 
5152f71e704SKris Buschelman   Options Database Keys:
5160bad9183SKris Buschelman + -mat_type umfpack - sets the matrix type to "umfpack" during a call to MatSetFromOptions()
5172f71e704SKris Buschelman . -mat_umfpack_prl - UMFPACK print level: Control[UMFPACK_PRL]
5182f71e704SKris Buschelman . -mat_umfpack_dense_col <alpha_c> - UMFPACK dense column threshold: Control[UMFPACK_DENSE_COL]
5192f71e704SKris Buschelman . -mat_umfpack_block_size <bs> - UMFPACK block size for BLAS-Level 3 calls: Control[UMFPACK_BLOCK_SIZE]
5202f71e704SKris Buschelman . -mat_umfpack_pivot_tolerance <delta> - UMFPACK partial pivot tolerance: Control[UMFPACK_PIVOT_TOLERANCE]
5212f71e704SKris Buschelman . -mat_umfpack_alloc_init <delta> - UMFPACK factorized matrix allocation modifier: Control[UMFPACK_ALLOC_INIT]
5222f71e704SKris Buschelman - -mat_umfpack_irstep <maxit> - UMFPACK maximum number of iterative refinement steps: Control[UMFPACK_IRSTEP]
5232f71e704SKris Buschelman 
5242f71e704SKris Buschelman    Level: beginner
5252f71e704SKris Buschelman 
5262f71e704SKris Buschelman .seealso: PCLU
5272f71e704SKris Buschelman M*/
5282f71e704SKris Buschelman 
5291677d0b8SKris Buschelman EXTERN_C_BEGIN
5301677d0b8SKris Buschelman #undef __FUNCT__
531f0c56d0fSKris Buschelman #define __FUNCT__ "MatCreate_UMFPACK"
532be1d678aSKris Buschelman PetscErrorCode PETSCMAT_DLLEXPORT MatCreate_UMFPACK(Mat A)
533dfbe8321SBarry Smith {
534dfbe8321SBarry Smith   PetscErrorCode ierr;
5351677d0b8SKris Buschelman 
5361677d0b8SKris Buschelman   PetscFunctionBegin;
5371677d0b8SKris Buschelman   ierr = MatSetType(A,MATSEQAIJ);CHKERRQ(ierr);
538ceb03754SKris Buschelman   ierr = MatConvert_SeqAIJ_UMFPACK(A,MATUMFPACK,MAT_REUSE_MATRIX,&A);CHKERRQ(ierr);
5391677d0b8SKris Buschelman   PetscFunctionReturn(0);
5401677d0b8SKris Buschelman }
5411677d0b8SKris Buschelman EXTERN_C_END
5422d4e2982SHong Zhang 
5432d4e2982SHong Zhang 
5442d4e2982SHong Zhang 
545