xref: /petsc/src/mat/interface/matrix.c (revision fa6b8e389e8051670ac35c373b6c9ca09b68ef1f)
1 #define PETSCMAT_DLL
2 
3 /*
4    This is where the abstract matrix operations are defined
5 */
6 
7 #include "private/matimpl.h"        /*I "petscmat.h" I*/
8 #include "private/vecimpl.h"
9 
10 /* Logging support */
11 PetscClassId PETSCMAT_DLLEXPORT MAT_CLASSID;
12 PetscClassId PETSCMAT_DLLEXPORT MAT_FDCOLORING_CLASSID;
13 
14 PetscLogEvent  MAT_Mult, MAT_Mults, MAT_MultConstrained, MAT_MultAdd, MAT_MultTranspose;
15 PetscLogEvent  MAT_MultTransposeConstrained, MAT_MultTransposeAdd, MAT_Solve, MAT_Solves, MAT_SolveAdd, MAT_SolveTranspose, MAT_MatSolve;
16 PetscLogEvent  MAT_SolveTransposeAdd, MAT_SOR, MAT_ForwardSolve, MAT_BackwardSolve, MAT_LUFactor, MAT_LUFactorSymbolic;
17 PetscLogEvent  MAT_LUFactorNumeric, MAT_CholeskyFactor, MAT_CholeskyFactorSymbolic, MAT_CholeskyFactorNumeric, MAT_ILUFactor;
18 PetscLogEvent  MAT_ILUFactorSymbolic, MAT_ICCFactorSymbolic, MAT_Copy, MAT_Convert, MAT_Scale, MAT_AssemblyBegin;
19 PetscLogEvent  MAT_AssemblyEnd, MAT_SetValues, MAT_GetValues, MAT_GetRow, MAT_GetRowIJ, MAT_GetSubMatrices, MAT_GetColoring, MAT_GetOrdering, MAT_GetRedundantMatrix, MAT_GetSeqNonzeroStructure;
20 PetscLogEvent  MAT_IncreaseOverlap, MAT_Partitioning, MAT_ZeroEntries, MAT_Load, MAT_View, MAT_AXPY, MAT_FDColoringCreate;
21 PetscLogEvent  MAT_FDColoringApply,MAT_Transpose,MAT_FDColoringFunction;
22 PetscLogEvent  MAT_MatMult, MAT_MatMultSymbolic, MAT_MatMultNumeric;
23 PetscLogEvent  MAT_PtAP, MAT_PtAPSymbolic, MAT_PtAPNumeric;
24 PetscLogEvent  MAT_MatMultTranspose, MAT_MatMultTransposeSymbolic, MAT_MatMultTransposeNumeric;
25 PetscLogEvent  MAT_MultHermitianTranspose,MAT_MultHermitianTransposeAdd;
26 PetscLogEvent  MAT_Getsymtranspose, MAT_Getsymtransreduced, MAT_Transpose_SeqAIJ, MAT_GetBrowsOfAcols;
27 PetscLogEvent  MAT_GetBrowsOfAocols, MAT_Getlocalmat, MAT_Getlocalmatcondensed, MAT_Seqstompi, MAT_Seqstompinum, MAT_Seqstompisym;
28 PetscLogEvent  MAT_Applypapt, MAT_Applypapt_numeric, MAT_Applypapt_symbolic, MAT_GetSequentialNonzeroStructure;
29 
30 /* nasty global values for MatSetValue() */
31 PetscInt    PETSCMAT_DLLEXPORT MatSetValue_Row = 0;
32 PetscInt    PETSCMAT_DLLEXPORT MatSetValue_Column = 0;
33 PetscScalar PETSCMAT_DLLEXPORT MatSetValue_Value = 0.0;
34 
35 const char *const MatFactorTypes[] = {"NONE","LU","CHOLESKY","ILU","ICC","ILUDT","MatFactorType","MAT_FACTOR_",0};
36 
37 #undef __FUNCT__
38 #define __FUNCT__ "MatGetDiagonalBlock"
39 /*@
40    MatGetDiagonalBlock - Returns the part of the matrix associated with the on-process coupling
41 
42    Not Collective
43 
44    Input Parameters:
45 +  mat - the matrix
46 -  reuse - indicates you are passing in the a matrix and want it reused
47 
48    Output Parameters:
49 +   iscopy - indicates a copy of the diagonal matrix was created and you should use MatDestroy() on it
50 -   a - the diagonal part (which is a SEQUENTIAL matrix)
51 
52    Notes: see the manual page for MatCreateMPIAIJ() for more information on the "diagonal part" of the matrix
53 
54    Level: advanced
55 
56 @*/
57 PetscErrorCode PETSCMAT_DLLEXPORT MatGetDiagonalBlock(Mat A,PetscTruth *iscopy,MatReuse reuse,Mat *a)
58 {
59   PetscErrorCode ierr,(*f)(Mat,PetscTruth*,MatReuse,Mat*);
60   PetscMPIInt    size;
61 
62   PetscFunctionBegin;
63   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
64   PetscValidType(A,1);
65   PetscValidPointer(iscopy,2);
66   PetscValidPointer(a,3);
67   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
68   if (A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
69   ierr = MPI_Comm_size(((PetscObject)A)->comm,&size);CHKERRQ(ierr);
70   ierr = PetscObjectQueryFunction((PetscObject)A,"MatGetDiagonalBlock_C",(void (**)(void))&f);CHKERRQ(ierr);
71   if (f) {
72     ierr = (*f)(A,iscopy,reuse,a);CHKERRQ(ierr);
73   } else if (size == 1) {
74     *a = A;
75     *iscopy = PETSC_FALSE;
76   } else SETERRQ(((PetscObject)A)->comm,PETSC_ERR_SUP,"Cannot get diagonal part for this matrix");
77   PetscFunctionReturn(0);
78 }
79 
80 #undef __FUNCT__
81 #define __FUNCT__ "MatGetTrace"
82 /*@
83    MatGetTrace - Gets the trace of a matrix. The sum of the diagonal entries.
84 
85    Collective on Mat
86 
87    Input Parameters:
88 .  mat - the matrix
89 
90    Output Parameter:
91 .   trace - the sum of the diagonal entries
92 
93    Level: advanced
94 
95 @*/
96 PetscErrorCode  MatGetTrace(Mat mat,PetscScalar *trace)
97 {
98    PetscErrorCode ierr;
99    Vec            diag;
100 
101    PetscFunctionBegin;
102    ierr = MatGetVecs(mat,&diag,PETSC_NULL);CHKERRQ(ierr);
103    ierr = MatGetDiagonal(mat,diag);CHKERRQ(ierr);
104    ierr = VecSum(diag,trace);CHKERRQ(ierr);
105    ierr = VecDestroy(diag);CHKERRQ(ierr);
106    PetscFunctionReturn(0);
107 }
108 
109 #undef __FUNCT__
110 #define __FUNCT__ "MatRealPart"
111 /*@
112    MatRealPart - Zeros out the imaginary part of the matrix
113 
114    Collective on Mat
115 
116    Input Parameters:
117 .  mat - the matrix
118 
119    Level: advanced
120 
121 
122 .seealso: MatImaginaryPart()
123 @*/
124 PetscErrorCode PETSCMAT_DLLEXPORT MatRealPart(Mat mat)
125 {
126   PetscErrorCode ierr;
127 
128   PetscFunctionBegin;
129   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
130   PetscValidType(mat,1);
131   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
132   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
133   if (!mat->ops->realpart) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
134   ierr = MatPreallocated(mat);CHKERRQ(ierr);
135   ierr = (*mat->ops->realpart)(mat);CHKERRQ(ierr);
136   PetscFunctionReturn(0);
137 }
138 
139 #undef __FUNCT__
140 #define __FUNCT__ "MatGetGhosts"
141 /*@C
142    MatGetGhosts - Get the global index of all ghost nodes defined by the sparse matrix
143 
144    Collective on Mat
145 
146    Input Parameter:
147 .  mat - the matrix
148 
149    Output Parameters:
150 +   nghosts - number of ghosts (note for BAIJ matrices there is one ghost for each block)
151 -   ghosts - the global indices of the ghost points
152 
153    Notes: the nghosts and ghosts are suitable to pass into VecCreateGhost()
154 
155    Level: advanced
156 
157 @*/
158 PetscErrorCode PETSCMAT_DLLEXPORT MatGetGhosts(Mat mat,PetscInt *nghosts,const PetscInt *ghosts[])
159 {
160   PetscErrorCode ierr;
161 
162   PetscFunctionBegin;
163   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
164   PetscValidType(mat,1);
165   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
166   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
167   if (!mat->ops->getghosts) {
168     if (nghosts) *nghosts = 0;
169     if (ghosts) *ghosts = 0;
170   } else {
171     ierr = (*mat->ops->getghosts)(mat,nghosts,ghosts);CHKERRQ(ierr);
172   }
173   PetscFunctionReturn(0);
174 }
175 
176 
177 #undef __FUNCT__
178 #define __FUNCT__ "MatImaginaryPart"
179 /*@
180    MatImaginaryPart - Moves the imaginary part of the matrix to the real part and zeros the imaginary part
181 
182    Collective on Mat
183 
184    Input Parameters:
185 .  mat - the matrix
186 
187    Level: advanced
188 
189 
190 .seealso: MatRealPart()
191 @*/
192 PetscErrorCode PETSCMAT_DLLEXPORT MatImaginaryPart(Mat mat)
193 {
194   PetscErrorCode ierr;
195 
196   PetscFunctionBegin;
197   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
198   PetscValidType(mat,1);
199   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
200   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
201   if (!mat->ops->imaginarypart) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
202   ierr = MatPreallocated(mat);CHKERRQ(ierr);
203   ierr = (*mat->ops->imaginarypart)(mat);CHKERRQ(ierr);
204   PetscFunctionReturn(0);
205 }
206 
207 #undef __FUNCT__
208 #define __FUNCT__ "MatMissingDiagonal"
209 /*@
210    MatMissingDiagonal - Determine if sparse matrix is missing a diagonal entry (or block entry for BAIJ matrices)
211 
212    Collective on Mat
213 
214    Input Parameter:
215 .  mat - the matrix
216 
217    Output Parameters:
218 +  missing - is any diagonal missing
219 -  dd - first diagonal entry that is missing (optional)
220 
221    Level: advanced
222 
223 
224 .seealso: MatRealPart()
225 @*/
226 PetscErrorCode PETSCMAT_DLLEXPORT MatMissingDiagonal(Mat mat,PetscTruth *missing,PetscInt *dd)
227 {
228   PetscErrorCode ierr;
229 
230   PetscFunctionBegin;
231   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
232   PetscValidType(mat,1);
233   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
234   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
235   if (!mat->ops->missingdiagonal) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
236   ierr = (*mat->ops->missingdiagonal)(mat,missing,dd);CHKERRQ(ierr);
237   PetscFunctionReturn(0);
238 }
239 
240 #undef __FUNCT__
241 #define __FUNCT__ "MatGetRow"
242 /*@C
243    MatGetRow - Gets a row of a matrix.  You MUST call MatRestoreRow()
244    for each row that you get to ensure that your application does
245    not bleed memory.
246 
247    Not Collective
248 
249    Input Parameters:
250 +  mat - the matrix
251 -  row - the row to get
252 
253    Output Parameters:
254 +  ncols -  if not NULL, the number of nonzeros in the row
255 .  cols - if not NULL, the column numbers
256 -  vals - if not NULL, the values
257 
258    Notes:
259    This routine is provided for people who need to have direct access
260    to the structure of a matrix.  We hope that we provide enough
261    high-level matrix routines that few users will need it.
262 
263    MatGetRow() always returns 0-based column indices, regardless of
264    whether the internal representation is 0-based (default) or 1-based.
265 
266    For better efficiency, set cols and/or vals to PETSC_NULL if you do
267    not wish to extract these quantities.
268 
269    The user can only examine the values extracted with MatGetRow();
270    the values cannot be altered.  To change the matrix entries, one
271    must use MatSetValues().
272 
273    You can only have one call to MatGetRow() outstanding for a particular
274    matrix at a time, per processor. MatGetRow() can only obtain rows
275    associated with the given processor, it cannot get rows from the
276    other processors; for that we suggest using MatGetSubMatrices(), then
277    MatGetRow() on the submatrix. The row indix passed to MatGetRows()
278    is in the global number of rows.
279 
280    Fortran Notes:
281    The calling sequence from Fortran is
282 .vb
283    MatGetRow(matrix,row,ncols,cols,values,ierr)
284          Mat     matrix (input)
285          integer row    (input)
286          integer ncols  (output)
287          integer cols(maxcols) (output)
288          double precision (or double complex) values(maxcols) output
289 .ve
290    where maxcols >= maximum nonzeros in any row of the matrix.
291 
292 
293    Caution:
294    Do not try to change the contents of the output arrays (cols and vals).
295    In some cases, this may corrupt the matrix.
296 
297    Level: advanced
298 
299    Concepts: matrices^row access
300 
301 .seealso: MatRestoreRow(), MatSetValues(), MatGetValues(), MatGetSubMatrices(), MatGetDiagonal()
302 @*/
303 PetscErrorCode PETSCMAT_DLLEXPORT MatGetRow(Mat mat,PetscInt row,PetscInt *ncols,const PetscInt *cols[],const PetscScalar *vals[])
304 {
305   PetscErrorCode ierr;
306   PetscInt       incols;
307 
308   PetscFunctionBegin;
309   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
310   PetscValidType(mat,1);
311   if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
312   if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
313   if (!mat->ops->getrow) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
314   ierr = MatPreallocated(mat);CHKERRQ(ierr);
315   ierr = PetscLogEventBegin(MAT_GetRow,mat,0,0,0);CHKERRQ(ierr);
316   ierr = (*mat->ops->getrow)(mat,row,&incols,(PetscInt **)cols,(PetscScalar **)vals);CHKERRQ(ierr);
317   if (ncols) *ncols = incols;
318   ierr = PetscLogEventEnd(MAT_GetRow,mat,0,0,0);CHKERRQ(ierr);
319   PetscFunctionReturn(0);
320 }
321 
322 #undef __FUNCT__
323 #define __FUNCT__ "MatConjugate"
324 /*@
325    MatConjugate - replaces the matrix values with their complex conjugates
326 
327    Collective on Mat
328 
329    Input Parameters:
330 .  mat - the matrix
331 
332    Level: advanced
333 
334 .seealso:  VecConjugate()
335 @*/
336 PetscErrorCode PETSCMAT_DLLEXPORT MatConjugate(Mat mat)
337 {
338   PetscErrorCode ierr;
339 
340   PetscFunctionBegin;
341   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
342   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
343   if (!mat->ops->conjugate) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Not provided for this matrix format, send email to petsc-maint@mcs.anl.gov");
344   ierr = (*mat->ops->conjugate)(mat);CHKERRQ(ierr);
345   PetscFunctionReturn(0);
346 }
347 
348 #undef __FUNCT__
349 #define __FUNCT__ "MatRestoreRow"
350 /*@C
351    MatRestoreRow - Frees any temporary space allocated by MatGetRow().
352 
353    Not Collective
354 
355    Input Parameters:
356 +  mat - the matrix
357 .  row - the row to get
358 .  ncols, cols - the number of nonzeros and their columns
359 -  vals - if nonzero the column values
360 
361    Notes:
362    This routine should be called after you have finished examining the entries.
363 
364    Fortran Notes:
365    The calling sequence from Fortran is
366 .vb
367    MatRestoreRow(matrix,row,ncols,cols,values,ierr)
368       Mat     matrix (input)
369       integer row    (input)
370       integer ncols  (output)
371       integer cols(maxcols) (output)
372       double precision (or double complex) values(maxcols) output
373 .ve
374    Where maxcols >= maximum nonzeros in any row of the matrix.
375 
376    In Fortran MatRestoreRow() MUST be called after MatGetRow()
377    before another call to MatGetRow() can be made.
378 
379    Level: advanced
380 
381 .seealso:  MatGetRow()
382 @*/
383 PetscErrorCode PETSCMAT_DLLEXPORT MatRestoreRow(Mat mat,PetscInt row,PetscInt *ncols,const PetscInt *cols[],const PetscScalar *vals[])
384 {
385   PetscErrorCode ierr;
386 
387   PetscFunctionBegin;
388   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
389   PetscValidIntPointer(ncols,3);
390   if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
391   if (!mat->ops->restorerow) PetscFunctionReturn(0);
392   ierr = (*mat->ops->restorerow)(mat,row,ncols,(PetscInt **)cols,(PetscScalar **)vals);CHKERRQ(ierr);
393   PetscFunctionReturn(0);
394 }
395 
396 #undef __FUNCT__
397 #define __FUNCT__ "MatGetRowUpperTriangular"
398 /*@
399    MatGetRowUpperTriangular - Sets a flag to enable calls to MatGetRow() for matrix in MATSBAIJ format.
400    You should call MatRestoreRowUpperTriangular() after calling MatGetRow/MatRestoreRow() to disable the flag.
401 
402    Not Collective
403 
404    Input Parameters:
405 +  mat - the matrix
406 
407    Notes:
408    The flag is to ensure that users are aware of MatGetRow() only provides the upper trianglular part of the row for the matrices in MATSBAIJ format.
409 
410    Level: advanced
411 
412    Concepts: matrices^row access
413 
414 .seealso: MatRestoreRowRowUpperTriangular()
415 @*/
416 PetscErrorCode PETSCMAT_DLLEXPORT MatGetRowUpperTriangular(Mat mat)
417 {
418   PetscErrorCode ierr;
419 
420   PetscFunctionBegin;
421   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
422   PetscValidType(mat,1);
423   if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
424   if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
425   if (!mat->ops->getrowuppertriangular) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
426   ierr = MatPreallocated(mat);CHKERRQ(ierr);
427   ierr = (*mat->ops->getrowuppertriangular)(mat);CHKERRQ(ierr);
428   PetscFunctionReturn(0);
429 }
430 
431 #undef __FUNCT__
432 #define __FUNCT__ "MatRestoreRowUpperTriangular"
433 /*@
434    MatRestoreRowUpperTriangular - Disable calls to MatGetRow() for matrix in MATSBAIJ format.
435 
436    Not Collective
437 
438    Input Parameters:
439 +  mat - the matrix
440 
441    Notes:
442    This routine should be called after you have finished MatGetRow/MatRestoreRow().
443 
444 
445    Level: advanced
446 
447 .seealso:  MatGetRowUpperTriangular()
448 @*/
449 PetscErrorCode PETSCMAT_DLLEXPORT MatRestoreRowUpperTriangular(Mat mat)
450 {
451   PetscErrorCode ierr;
452 
453   PetscFunctionBegin;
454   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
455   if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
456   if (!mat->ops->restorerowuppertriangular) PetscFunctionReturn(0);
457   ierr = (*mat->ops->restorerowuppertriangular)(mat);CHKERRQ(ierr);
458   PetscFunctionReturn(0);
459 }
460 
461 #undef __FUNCT__
462 #define __FUNCT__ "MatSetOptionsPrefix"
463 /*@C
464    MatSetOptionsPrefix - Sets the prefix used for searching for all
465    Mat options in the database.
466 
467    Collective on Mat
468 
469    Input Parameter:
470 +  A - the Mat context
471 -  prefix - the prefix to prepend to all option names
472 
473    Notes:
474    A hyphen (-) must NOT be given at the beginning of the prefix name.
475    The first character of all runtime options is AUTOMATICALLY the hyphen.
476 
477    Level: advanced
478 
479 .keywords: Mat, set, options, prefix, database
480 
481 .seealso: MatSetFromOptions()
482 @*/
483 PetscErrorCode PETSCMAT_DLLEXPORT MatSetOptionsPrefix(Mat A,const char prefix[])
484 {
485   PetscErrorCode ierr;
486 
487   PetscFunctionBegin;
488   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
489   ierr = PetscObjectSetOptionsPrefix((PetscObject)A,prefix);CHKERRQ(ierr);
490   PetscFunctionReturn(0);
491 }
492 
493 #undef __FUNCT__
494 #define __FUNCT__ "MatAppendOptionsPrefix"
495 /*@C
496    MatAppendOptionsPrefix - Appends to the prefix used for searching for all
497    Mat options in the database.
498 
499    Collective on Mat
500 
501    Input Parameters:
502 +  A - the Mat context
503 -  prefix - the prefix to prepend to all option names
504 
505    Notes:
506    A hyphen (-) must NOT be given at the beginning of the prefix name.
507    The first character of all runtime options is AUTOMATICALLY the hyphen.
508 
509    Level: advanced
510 
511 .keywords: Mat, append, options, prefix, database
512 
513 .seealso: MatGetOptionsPrefix()
514 @*/
515 PetscErrorCode PETSCMAT_DLLEXPORT MatAppendOptionsPrefix(Mat A,const char prefix[])
516 {
517   PetscErrorCode ierr;
518 
519   PetscFunctionBegin;
520   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
521   ierr = PetscObjectAppendOptionsPrefix((PetscObject)A,prefix);CHKERRQ(ierr);
522   PetscFunctionReturn(0);
523 }
524 
525 #undef __FUNCT__
526 #define __FUNCT__ "MatGetOptionsPrefix"
527 /*@C
528    MatGetOptionsPrefix - Sets the prefix used for searching for all
529    Mat options in the database.
530 
531    Not Collective
532 
533    Input Parameter:
534 .  A - the Mat context
535 
536    Output Parameter:
537 .  prefix - pointer to the prefix string used
538 
539    Notes: On the fortran side, the user should pass in a string 'prefix' of
540    sufficient length to hold the prefix.
541 
542    Level: advanced
543 
544 .keywords: Mat, get, options, prefix, database
545 
546 .seealso: MatAppendOptionsPrefix()
547 @*/
548 PetscErrorCode PETSCMAT_DLLEXPORT MatGetOptionsPrefix(Mat A,const char *prefix[])
549 {
550   PetscErrorCode ierr;
551 
552   PetscFunctionBegin;
553   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
554   ierr = PetscObjectGetOptionsPrefix((PetscObject)A,prefix);CHKERRQ(ierr);
555   PetscFunctionReturn(0);
556 }
557 
558 #undef __FUNCT__
559 #define __FUNCT__ "MatSetUp"
560 /*@
561    MatSetUp - Sets up the internal matrix data structures for the later use.
562 
563    Collective on Mat
564 
565    Input Parameters:
566 .  A - the Mat context
567 
568    Notes:
569    For basic use of the Mat classes the user need not explicitly call
570    MatSetUp(), since these actions will happen automatically.
571 
572    Level: advanced
573 
574 .keywords: Mat, setup
575 
576 .seealso: MatCreate(), MatDestroy()
577 @*/
578 PetscErrorCode PETSCMAT_DLLEXPORT MatSetUp(Mat A)
579 {
580   PetscMPIInt    size;
581   PetscErrorCode ierr;
582 
583   PetscFunctionBegin;
584   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
585   if (!((PetscObject)A)->type_name) {
586     ierr = MPI_Comm_size(((PetscObject)A)->comm, &size);CHKERRQ(ierr);
587     if (size == 1) {
588       ierr = MatSetType(A, MATSEQAIJ);CHKERRQ(ierr);
589     } else {
590       ierr = MatSetType(A, MATMPIAIJ);CHKERRQ(ierr);
591     }
592   }
593   ierr = MatSetUpPreallocation(A);CHKERRQ(ierr);
594   PetscFunctionReturn(0);
595 }
596 
597 #undef __FUNCT__
598 #define __FUNCT__ "MatView"
599 /*@C
600    MatView - Visualizes a matrix object.
601 
602    Collective on Mat
603 
604    Input Parameters:
605 +  mat - the matrix
606 -  viewer - visualization context
607 
608   Notes:
609   The available visualization contexts include
610 +    PETSC_VIEWER_STDOUT_SELF - standard output (default)
611 .    PETSC_VIEWER_STDOUT_WORLD - synchronized standard
612         output where only the first processor opens
613         the file.  All other processors send their
614         data to the first processor to print.
615 -     PETSC_VIEWER_DRAW_WORLD - graphical display of nonzero structure
616 
617    The user can open alternative visualization contexts with
618 +    PetscViewerASCIIOpen() - Outputs matrix to a specified file
619 .    PetscViewerBinaryOpen() - Outputs matrix in binary to a
620          specified file; corresponding input uses MatLoad()
621 .    PetscViewerDrawOpen() - Outputs nonzero matrix structure to
622          an X window display
623 -    PetscViewerSocketOpen() - Outputs matrix to Socket viewer.
624          Currently only the sequential dense and AIJ
625          matrix types support the Socket viewer.
626 
627    The user can call PetscViewerSetFormat() to specify the output
628    format of ASCII printed objects (when using PETSC_VIEWER_STDOUT_SELF,
629    PETSC_VIEWER_STDOUT_WORLD and PetscViewerASCIIOpen).  Available formats include
630 +    PETSC_VIEWER_DEFAULT - default, prints matrix contents
631 .    PETSC_VIEWER_ASCII_MATLAB - prints matrix contents in Matlab format
632 .    PETSC_VIEWER_ASCII_DENSE - prints entire matrix including zeros
633 .    PETSC_VIEWER_ASCII_COMMON - prints matrix contents, using a sparse
634          format common among all matrix types
635 .    PETSC_VIEWER_ASCII_IMPL - prints matrix contents, using an implementation-specific
636          format (which is in many cases the same as the default)
637 .    PETSC_VIEWER_ASCII_INFO - prints basic information about the matrix
638          size and structure (not the matrix entries)
639 .    PETSC_VIEWER_ASCII_INFO_DETAIL - prints more detailed information about
640          the matrix structure
641 
642    Options Database Keys:
643 +  -mat_view_info - Prints info on matrix at conclusion of MatEndAssembly()
644 .  -mat_view_info_detailed - Prints more detailed info
645 .  -mat_view - Prints matrix in ASCII format
646 .  -mat_view_matlab - Prints matrix in Matlab format
647 .  -mat_view_draw - PetscDraws nonzero structure of matrix, using MatView() and PetscDrawOpenX().
648 .  -display <name> - Sets display name (default is host)
649 .  -draw_pause <sec> - Sets number of seconds to pause after display
650 .  -mat_view_socket - Sends matrix to socket, can be accessed from Matlab (see users manual)
651 .  -viewer_socket_machine <machine>
652 .  -viewer_socket_port <port>
653 .  -mat_view_binary - save matrix to file in binary format
654 -  -viewer_binary_filename <name>
655    Level: beginner
656 
657    Notes: see the manual page for MatLoad() for the exact format of the binary file when the binary
658       viewer is used.
659 
660       See bin/matlab/PetscBinaryRead.m for a Matlab code that can read in the binary file when the binary
661       viewer is used.
662 
663    Concepts: matrices^viewing
664    Concepts: matrices^plotting
665    Concepts: matrices^printing
666 
667 .seealso: PetscViewerSetFormat(), PetscViewerASCIIOpen(), PetscViewerDrawOpen(),
668           PetscViewerSocketOpen(), PetscViewerBinaryOpen(), MatLoad()
669 @*/
670 PetscErrorCode PETSCMAT_DLLEXPORT MatView(Mat mat,PetscViewer viewer)
671 {
672   PetscErrorCode    ierr;
673   PetscInt          rows,cols;
674   PetscTruth        iascii;
675   const MatType     cstr;
676   PetscViewerFormat format;
677 
678   PetscFunctionBegin;
679   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
680   PetscValidType(mat,1);
681   if (!viewer) {
682     ierr = PetscViewerASCIIGetStdout(((PetscObject)mat)->comm,&viewer);CHKERRQ(ierr);
683   }
684   PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,2);
685   PetscCheckSameComm(mat,1,viewer,2);
686   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ORDER,"Must call MatAssemblyBegin/End() before viewing matrix");
687   ierr = MatPreallocated(mat);CHKERRQ(ierr);
688 
689   ierr = PetscLogEventBegin(MAT_View,mat,viewer,0,0);CHKERRQ(ierr);
690   ierr = PetscTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr);
691   if (iascii) {
692     ierr = PetscViewerGetFormat(viewer,&format);CHKERRQ(ierr);
693     if (format == PETSC_VIEWER_ASCII_INFO || format == PETSC_VIEWER_ASCII_INFO_DETAIL) {
694       if (((PetscObject)mat)->prefix) {
695         ierr = PetscViewerASCIIPrintf(viewer,"Matrix Object:(%s)\n",((PetscObject)mat)->prefix);CHKERRQ(ierr);
696       } else {
697         ierr = PetscViewerASCIIPrintf(viewer,"Matrix Object:\n");CHKERRQ(ierr);
698       }
699       ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr);
700       ierr = MatGetType(mat,&cstr);CHKERRQ(ierr);
701       ierr = MatGetSize(mat,&rows,&cols);CHKERRQ(ierr);
702       ierr = PetscViewerASCIIPrintf(viewer,"type=%s, rows=%D, cols=%D\n",cstr,rows,cols);CHKERRQ(ierr);
703       if (mat->factortype) {
704         const MatSolverPackage solver;
705         ierr = MatFactorGetSolverPackage(mat,&solver);CHKERRQ(ierr);
706         ierr = PetscViewerASCIIPrintf(viewer,"package used to perform factorization: %s\n",solver);CHKERRQ(ierr);
707       }
708       if (mat->ops->getinfo) {
709         MatInfo info;
710         ierr = MatGetInfo(mat,MAT_GLOBAL_SUM,&info);CHKERRQ(ierr);
711         ierr = PetscViewerASCIIPrintf(viewer,"total: nonzeros=%D, allocated nonzeros=%D\n",(PetscInt)info.nz_used,(PetscInt)info.nz_allocated);CHKERRQ(ierr);
712         ierr = PetscViewerASCIIPrintf(viewer,"total number of mallocs used during MatSetValues calls =%D\n",(PetscInt)info.mallocs);CHKERRQ(ierr);
713       }
714     }
715   }
716   if (mat->ops->view) {
717     ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr);
718     ierr = (*mat->ops->view)(mat,viewer);CHKERRQ(ierr);
719     ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr);
720   } else if (!iascii) {
721     SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Viewer type %s not supported",((PetscObject)viewer)->type_name);
722   }
723   if (iascii) {
724     ierr = PetscViewerGetFormat(viewer,&format);CHKERRQ(ierr);
725     if (format == PETSC_VIEWER_ASCII_INFO || format == PETSC_VIEWER_ASCII_INFO_DETAIL) {
726       ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr);
727     }
728   }
729   ierr = PetscLogEventEnd(MAT_View,mat,viewer,0,0);CHKERRQ(ierr);
730   PetscFunctionReturn(0);
731 }
732 
733 #undef __FUNCT__
734 #define __FUNCT__ "MatScaleSystem"
735 /*@
736    MatScaleSystem - Scale a vector solution and right hand side to
737    match the scaling of a scaled matrix.
738 
739    Collective on Mat
740 
741    Input Parameter:
742 +  mat - the matrix
743 .  b - right hand side vector (or PETSC_NULL)
744 -  x - solution vector (or PETSC_NULL)
745 
746 
747    Notes:
748    For AIJ, and BAIJ matrix formats, the matrices are not
749    internally scaled, so this does nothing.
750 
751    The KSP methods automatically call this routine when required
752    (via PCPreSolve()) so it is rarely used directly.
753 
754    Level: Developer
755 
756    Concepts: matrices^scaling
757 
758 .seealso: MatUseScaledForm(), MatUnScaleSystem()
759 @*/
760 PetscErrorCode PETSCMAT_DLLEXPORT MatScaleSystem(Mat mat,Vec b,Vec x)
761 {
762   PetscErrorCode ierr;
763 
764   PetscFunctionBegin;
765   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
766   PetscValidType(mat,1);
767   ierr = MatPreallocated(mat);CHKERRQ(ierr);
768   if (x) {PetscValidHeaderSpecific(x,VEC_CLASSID,3);PetscCheckSameComm(mat,1,x,3);}
769   if (b) {PetscValidHeaderSpecific(b,VEC_CLASSID,2);PetscCheckSameComm(mat,1,b,2);}
770 
771   if (mat->ops->scalesystem) {
772     ierr = (*mat->ops->scalesystem)(mat,b,x);CHKERRQ(ierr);
773   }
774   PetscFunctionReturn(0);
775 }
776 
777 #undef __FUNCT__
778 #define __FUNCT__ "MatUnScaleSystem"
779 /*@
780    MatUnScaleSystem - Unscales a vector solution and right hand side to
781    match the original scaling of a scaled matrix.
782 
783    Collective on Mat
784 
785    Input Parameter:
786 +  mat - the matrix
787 .  b - right hand side vector (or PETSC_NULL)
788 -  x - solution vector (or PETSC_NULL)
789 
790 
791    Notes:
792    For AIJ and BAIJ matrix formats, the matrices are not
793    internally scaled, so this does nothing.
794 
795    The KSP methods automatically call this routine when required
796    (via PCPreSolve()) so it is rarely used directly.
797 
798    Level: Developer
799 
800 .seealso: MatUseScaledForm(), MatScaleSystem()
801 @*/
802 PetscErrorCode PETSCMAT_DLLEXPORT MatUnScaleSystem(Mat mat,Vec b,Vec x)
803 {
804   PetscErrorCode ierr;
805 
806   PetscFunctionBegin;
807   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
808   PetscValidType(mat,1);
809   ierr = MatPreallocated(mat);CHKERRQ(ierr);
810   if (x) {PetscValidHeaderSpecific(x,VEC_CLASSID,3);PetscCheckSameComm(mat,1,x,3);}
811   if (b) {PetscValidHeaderSpecific(b,VEC_CLASSID,2);PetscCheckSameComm(mat,1,b,2);}
812   if (mat->ops->unscalesystem) {
813     ierr = (*mat->ops->unscalesystem)(mat,b,x);CHKERRQ(ierr);
814   }
815   PetscFunctionReturn(0);
816 }
817 
818 #undef __FUNCT__
819 #define __FUNCT__ "MatUseScaledForm"
820 /*@
821    MatUseScaledForm - For matrix storage formats that scale the
822    matrix indicates matrix operations (MatMult() etc) are
823    applied using the scaled matrix.
824 
825    Collective on Mat
826 
827    Input Parameter:
828 +  mat - the matrix
829 -  scaled - PETSC_TRUE for applying the scaled, PETSC_FALSE for
830             applying the original matrix
831 
832    Notes:
833    For scaled matrix formats, applying the original, unscaled matrix
834    will be slightly more expensive
835 
836    Level: Developer
837 
838 .seealso: MatScaleSystem(), MatUnScaleSystem()
839 @*/
840 PetscErrorCode PETSCMAT_DLLEXPORT MatUseScaledForm(Mat mat,PetscTruth scaled)
841 {
842   PetscErrorCode ierr;
843 
844   PetscFunctionBegin;
845   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
846   PetscValidType(mat,1);
847   ierr = MatPreallocated(mat);CHKERRQ(ierr);
848   if (mat->ops->usescaledform) {
849     ierr = (*mat->ops->usescaledform)(mat,scaled);CHKERRQ(ierr);
850   }
851   PetscFunctionReturn(0);
852 }
853 
854 #undef __FUNCT__
855 #define __FUNCT__ "MatDestroy"
856 /*@
857    MatDestroy - Frees space taken by a matrix.
858 
859    Collective on Mat
860 
861    Input Parameter:
862 .  A - the matrix
863 
864    Level: beginner
865 
866 @*/
867 PetscErrorCode PETSCMAT_DLLEXPORT MatDestroy(Mat A)
868 {
869   PetscErrorCode ierr;
870   PetscFunctionBegin;
871   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
872   if (--((PetscObject)A)->refct > 0) PetscFunctionReturn(0);
873   ierr = MatPreallocated(A);CHKERRQ(ierr);
874   /* if memory was published with AMS then destroy it */
875   ierr = PetscObjectDepublish(A);CHKERRQ(ierr);
876   if (A->ops->destroy) {
877     ierr = (*A->ops->destroy)(A);CHKERRQ(ierr);
878   }
879   if (A->mapping) {
880     ierr = ISLocalToGlobalMappingDestroy(A->mapping);CHKERRQ(ierr);
881   }
882   if (A->bmapping) {
883     ierr = ISLocalToGlobalMappingDestroy(A->bmapping);CHKERRQ(ierr);
884   }
885 
886   if (A->spptr){ierr = PetscFree(A->spptr);CHKERRQ(ierr);}
887   ierr = PetscLayoutDestroy(A->rmap);CHKERRQ(ierr);
888   ierr = PetscLayoutDestroy(A->cmap);CHKERRQ(ierr);
889   ierr = PetscHeaderDestroy(A);CHKERRQ(ierr);
890   PetscFunctionReturn(0);
891 }
892 
893 #undef __FUNCT__
894 #define __FUNCT__ "MatValid"
895 /*@
896    MatValid - Checks whether a matrix object is valid.
897 
898    Collective on Mat
899 
900    Input Parameter:
901 .  m - the matrix to check
902 
903    Output Parameter:
904    flg - flag indicating matrix status, either
905    PETSC_TRUE if matrix is valid, or PETSC_FALSE otherwise.
906 
907    Level: developer
908 
909    Concepts: matrices^validity
910 @*/
911 PetscErrorCode PETSCMAT_DLLEXPORT MatValid(Mat m,PetscTruth *flg)
912 {
913   PetscFunctionBegin;
914   PetscValidIntPointer(flg,1);
915   if (!m)                                          *flg = PETSC_FALSE;
916   else if (((PetscObject)m)->classid != MAT_CLASSID) *flg = PETSC_FALSE;
917   else                                             *flg = PETSC_TRUE;
918   PetscFunctionReturn(0);
919 }
920 
921 #undef __FUNCT__
922 #define __FUNCT__ "MatSetValues"
923 /*@
924    MatSetValues - Inserts or adds a block of values into a matrix.
925    These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd()
926    MUST be called after all calls to MatSetValues() have been completed.
927 
928    Not Collective
929 
930    Input Parameters:
931 +  mat - the matrix
932 .  v - a logically two-dimensional array of values
933 .  m, idxm - the number of rows and their global indices
934 .  n, idxn - the number of columns and their global indices
935 -  addv - either ADD_VALUES or INSERT_VALUES, where
936    ADD_VALUES adds values to any existing entries, and
937    INSERT_VALUES replaces existing entries with new values
938 
939    Notes:
940    By default the values, v, are row-oriented. See MatSetOption() for other options.
941 
942    Calls to MatSetValues() with the INSERT_VALUES and ADD_VALUES
943    options cannot be mixed without intervening calls to the assembly
944    routines.
945 
946    MatSetValues() uses 0-based row and column numbers in Fortran
947    as well as in C.
948 
949    Negative indices may be passed in idxm and idxn, these rows and columns are
950    simply ignored. This allows easily inserting element stiffness matrices
951    with homogeneous Dirchlet boundary conditions that you don't want represented
952    in the matrix.
953 
954    Efficiency Alert:
955    The routine MatSetValuesBlocked() may offer much better efficiency
956    for users of block sparse formats (MATSEQBAIJ and MATMPIBAIJ).
957 
958    Level: beginner
959 
960    Concepts: matrices^putting entries in
961 
962 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(),
963           InsertMode, INSERT_VALUES, ADD_VALUES
964 @*/
965 PetscErrorCode PETSCMAT_DLLEXPORT MatSetValues(Mat mat,PetscInt m,const PetscInt idxm[],PetscInt n,const PetscInt idxn[],const PetscScalar v[],InsertMode addv)
966 {
967   PetscErrorCode ierr;
968 
969   PetscFunctionBegin;
970   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
971   PetscValidType(mat,1);
972   if (!m || !n) PetscFunctionReturn(0); /* no values to insert */
973   PetscValidIntPointer(idxm,3);
974   PetscValidIntPointer(idxn,5);
975   if (v) PetscValidDoublePointer(v,6);
976   ierr = MatPreallocated(mat);CHKERRQ(ierr);
977   if (mat->insertmode == NOT_SET_VALUES) {
978     mat->insertmode = addv;
979   }
980 #if defined(PETSC_USE_DEBUG)
981   else if (mat->insertmode != addv) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values");
982   if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
983 #endif
984 
985   if (mat->assembled) {
986     mat->was_assembled = PETSC_TRUE;
987     mat->assembled     = PETSC_FALSE;
988   }
989   ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
990   if (!mat->ops->setvalues) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
991   ierr = (*mat->ops->setvalues)(mat,m,idxm,n,idxn,v,addv);CHKERRQ(ierr);
992   ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
993   PetscFunctionReturn(0);
994 }
995 
996 
997 #undef __FUNCT__
998 #define __FUNCT__ "MatSetValuesRowLocal"
999 /*@
1000    MatSetValuesRowLocal - Inserts a row (block row for BAIJ matrices) of nonzero
1001         values into a matrix
1002 
1003    Not Collective
1004 
1005    Input Parameters:
1006 +  mat - the matrix
1007 .  row - the (block) row to set
1008 -  v - a logically two-dimensional array of values
1009 
1010    Notes:
1011    By the values, v, are column-oriented (for the block version) and sorted
1012 
1013    All the nonzeros in the row must be provided
1014 
1015    The matrix must have previously had its column indices set
1016 
1017    The row must belong to this process
1018 
1019    Level: intermediate
1020 
1021    Concepts: matrices^putting entries in
1022 
1023 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(),
1024           InsertMode, INSERT_VALUES, ADD_VALUES, MatSetValues(), MatSetValuesRow(), MatSetLocalToGlobalMapping()
1025 @*/
1026 PetscErrorCode PETSCMAT_DLLEXPORT MatSetValuesRowLocal(Mat mat,PetscInt row,const PetscScalar v[])
1027 {
1028   PetscErrorCode ierr;
1029 
1030   PetscFunctionBegin;
1031   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1032   PetscValidType(mat,1);
1033   PetscValidScalarPointer(v,2);
1034   ierr = MatSetValuesRow(mat, mat->mapping->indices[row],v);CHKERRQ(ierr);
1035   PetscFunctionReturn(0);
1036 }
1037 
1038 #undef __FUNCT__
1039 #define __FUNCT__ "MatSetValuesRow"
1040 /*@
1041    MatSetValuesRow - Inserts a row (block row for BAIJ matrices) of nonzero
1042         values into a matrix
1043 
1044    Not Collective
1045 
1046    Input Parameters:
1047 +  mat - the matrix
1048 .  row - the (block) row to set
1049 -  v - a logically two-dimensional array of values
1050 
1051    Notes:
1052    The values, v, are column-oriented for the block version.
1053 
1054    All the nonzeros in the row must be provided
1055 
1056    THE MATRIX MUSAT HAVE PREVIOUSLY HAD ITS COLUMN INDICES SET. IT IS RARE THAT THIS ROUTINE IS USED, usually MatSetValues() is used.
1057 
1058    The row must belong to this process
1059 
1060    Level: advanced
1061 
1062    Concepts: matrices^putting entries in
1063 
1064 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(),
1065           InsertMode, INSERT_VALUES, ADD_VALUES, MatSetValues()
1066 @*/
1067 PetscErrorCode PETSCMAT_DLLEXPORT MatSetValuesRow(Mat mat,PetscInt row,const PetscScalar v[])
1068 {
1069   PetscErrorCode ierr;
1070 
1071   PetscFunctionBegin;
1072   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1073   PetscValidType(mat,1);
1074   PetscValidScalarPointer(v,2);
1075 #if defined(PETSC_USE_DEBUG)
1076   if (mat->insertmode == ADD_VALUES) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add and insert values");
1077   if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1078 #endif
1079   mat->insertmode = INSERT_VALUES;
1080 
1081   if (mat->assembled) {
1082     mat->was_assembled = PETSC_TRUE;
1083     mat->assembled     = PETSC_FALSE;
1084   }
1085   ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
1086   if (!mat->ops->setvaluesrow) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
1087   ierr = (*mat->ops->setvaluesrow)(mat,row,v);CHKERRQ(ierr);
1088   ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
1089   PetscFunctionReturn(0);
1090 }
1091 
1092 #undef __FUNCT__
1093 #define __FUNCT__ "MatSetValuesStencil"
1094 /*@
1095    MatSetValuesStencil - Inserts or adds a block of values into a matrix.
1096      Using structured grid indexing
1097 
1098    Not Collective
1099 
1100    Input Parameters:
1101 +  mat - the matrix
1102 .  m - number of rows being entered
1103 .  idxm - grid coordinates (and component number when dof > 1) for matrix rows being entered
1104 .  n - number of columns being entered
1105 .  idxn - grid coordinates (and component number when dof > 1) for matrix columns being entered
1106 .  v - a logically two-dimensional array of values
1107 -  addv - either ADD_VALUES or INSERT_VALUES, where
1108    ADD_VALUES adds values to any existing entries, and
1109    INSERT_VALUES replaces existing entries with new values
1110 
1111    Notes:
1112    By default the values, v, are row-oriented.  See MatSetOption() for other options.
1113 
1114    Calls to MatSetValuesStencil() with the INSERT_VALUES and ADD_VALUES
1115    options cannot be mixed without intervening calls to the assembly
1116    routines.
1117 
1118    The grid coordinates are across the entire grid, not just the local portion
1119 
1120    MatSetValuesStencil() uses 0-based row and column numbers in Fortran
1121    as well as in C.
1122 
1123    For setting/accessing vector values via array coordinates you can use the DAVecGetArray() routine
1124 
1125    In order to use this routine you must either obtain the matrix with DAGetMatrix()
1126    or call MatSetLocalToGlobalMapping() and MatSetStencil() first.
1127 
1128    The columns and rows in the stencil passed in MUST be contained within the
1129    ghost region of the given process as set with DACreateXXX() or MatSetStencil(). For example,
1130    if you create a DA with an overlap of one grid level and on a particular process its first
1131    local nonghost x logical coordinate is 6 (so its first ghost x logical coordinate is 5) the
1132    first i index you can use in your column and row indices in MatSetStencil() is 5.
1133 
1134    In Fortran idxm and idxn should be declared as
1135 $     MatStencil idxm(4,m),idxn(4,n)
1136    and the values inserted using
1137 $    idxm(MatStencil_i,1) = i
1138 $    idxm(MatStencil_j,1) = j
1139 $    idxm(MatStencil_k,1) = k
1140 $    idxm(MatStencil_c,1) = c
1141    etc
1142 
1143    For periodic boundary conditions use negative indices for values to the left (below 0; that are to be
1144    obtained by wrapping values from right edge). For values to the right of the last entry using that index plus one
1145    etc to obtain values that obtained by wrapping the values from the left edge. This does not work for the DA_NONPERIODIC
1146    wrap.
1147 
1148    For indices that don't mean anything for your case (like the k index when working in 2d) or the c index when you have
1149    a single value per point) you can skip filling those indices.
1150 
1151    Inspired by the structured grid interface to the HYPRE package
1152    (http://www.llnl.gov/CASC/hypre)
1153 
1154    Efficiency Alert:
1155    The routine MatSetValuesBlockedStencil() may offer much better efficiency
1156    for users of block sparse formats (MATSEQBAIJ and MATMPIBAIJ).
1157 
1158    Level: beginner
1159 
1160    Concepts: matrices^putting entries in
1161 
1162 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal()
1163           MatSetValues(), MatSetValuesBlockedStencil(), MatSetStencil(), DAGetMatrix(), DAVecGetArray(), MatStencil
1164 @*/
1165 PetscErrorCode PETSCMAT_DLLEXPORT MatSetValuesStencil(Mat mat,PetscInt m,const MatStencil idxm[],PetscInt n,const MatStencil idxn[],const PetscScalar v[],InsertMode addv)
1166 {
1167   PetscErrorCode ierr;
1168   PetscInt       j,i,jdxm[128],jdxn[256],dim = mat->stencil.dim,*dims = mat->stencil.dims+1,tmp;
1169   PetscInt       *starts = mat->stencil.starts,*dxm = (PetscInt*)idxm,*dxn = (PetscInt*)idxn,sdim = dim - (1 - (PetscInt)mat->stencil.noc);
1170 
1171   PetscFunctionBegin;
1172   if (!m || !n) PetscFunctionReturn(0); /* no values to insert */
1173   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1174   PetscValidType(mat,1);
1175   PetscValidIntPointer(idxm,3);
1176   PetscValidIntPointer(idxn,5);
1177   PetscValidScalarPointer(v,6);
1178 
1179   if (m > 128) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Can only set 128 rows at a time; trying to set %D",m);
1180   if (n > 256) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Can only set 256 columns at a time; trying to set %D",n);
1181 
1182   for (i=0; i<m; i++) {
1183     for (j=0; j<3-sdim; j++) dxm++;
1184     tmp = *dxm++ - starts[0];
1185     for (j=0; j<dim-1; j++) {
1186       if ((*dxm++ - starts[j+1]) < 0 || tmp < 0) tmp = PETSC_MIN_INT;
1187       else                                       tmp = tmp*dims[j] + *(dxm-1) - starts[j+1];
1188     }
1189     if (mat->stencil.noc) dxm++;
1190     jdxm[i] = tmp;
1191   }
1192   for (i=0; i<n; i++) {
1193     for (j=0; j<3-sdim; j++) dxn++;
1194     tmp = *dxn++ - starts[0];
1195     for (j=0; j<dim-1; j++) {
1196       if ((*dxn++ - starts[j+1]) < 0 || tmp < 0) tmp = PETSC_MIN_INT;
1197       else                                       tmp = tmp*dims[j] + *(dxn-1) - starts[j+1];
1198     }
1199     if (mat->stencil.noc) dxn++;
1200     jdxn[i] = tmp;
1201   }
1202   ierr = MatSetValuesLocal(mat,m,jdxm,n,jdxn,v,addv);CHKERRQ(ierr);
1203   PetscFunctionReturn(0);
1204 }
1205 
1206 #undef __FUNCT__
1207 #define __FUNCT__ "MatSetValuesBlockedStencil"
1208 /*@C
1209    MatSetValuesBlockedStencil - Inserts or adds a block of values into a matrix.
1210      Using structured grid indexing
1211 
1212    Not Collective
1213 
1214    Input Parameters:
1215 +  mat - the matrix
1216 .  m - number of rows being entered
1217 .  idxm - grid coordinates for matrix rows being entered
1218 .  n - number of columns being entered
1219 .  idxn - grid coordinates for matrix columns being entered
1220 .  v - a logically two-dimensional array of values
1221 -  addv - either ADD_VALUES or INSERT_VALUES, where
1222    ADD_VALUES adds values to any existing entries, and
1223    INSERT_VALUES replaces existing entries with new values
1224 
1225    Notes:
1226    By default the values, v, are row-oriented and unsorted.
1227    See MatSetOption() for other options.
1228 
1229    Calls to MatSetValuesBlockedStencil() with the INSERT_VALUES and ADD_VALUES
1230    options cannot be mixed without intervening calls to the assembly
1231    routines.
1232 
1233    The grid coordinates are across the entire grid, not just the local portion
1234 
1235    MatSetValuesBlockedStencil() uses 0-based row and column numbers in Fortran
1236    as well as in C.
1237 
1238    For setting/accessing vector values via array coordinates you can use the DAVecGetArray() routine
1239 
1240    In order to use this routine you must either obtain the matrix with DAGetMatrix()
1241    or call MatSetBlockSize(), MatSetLocalToGlobalMapping() and MatSetStencil() first.
1242 
1243    The columns and rows in the stencil passed in MUST be contained within the
1244    ghost region of the given process as set with DACreateXXX() or MatSetStencil(). For example,
1245    if you create a DA with an overlap of one grid level and on a particular process its first
1246    local nonghost x logical coordinate is 6 (so its first ghost x logical coordinate is 5) the
1247    first i index you can use in your column and row indices in MatSetStencil() is 5.
1248 
1249    In Fortran idxm and idxn should be declared as
1250 $     MatStencil idxm(4,m),idxn(4,n)
1251    and the values inserted using
1252 $    idxm(MatStencil_i,1) = i
1253 $    idxm(MatStencil_j,1) = j
1254 $    idxm(MatStencil_k,1) = k
1255    etc
1256 
1257    Negative indices may be passed in idxm and idxn, these rows and columns are
1258    simply ignored. This allows easily inserting element stiffness matrices
1259    with homogeneous Dirchlet boundary conditions that you don't want represented
1260    in the matrix.
1261 
1262    Inspired by the structured grid interface to the HYPRE package
1263    (http://www.llnl.gov/CASC/hypre)
1264 
1265    Level: beginner
1266 
1267    Concepts: matrices^putting entries in
1268 
1269 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal()
1270           MatSetValues(), MatSetValuesStencil(), MatSetStencil(), DAGetMatrix(), DAVecGetArray(), MatStencil,
1271           MatSetBlockSize(), MatSetLocalToGlobalMapping()
1272 @*/
1273 PetscErrorCode PETSCMAT_DLLEXPORT MatSetValuesBlockedStencil(Mat mat,PetscInt m,const MatStencil idxm[],PetscInt n,const MatStencil idxn[],const PetscScalar v[],InsertMode addv)
1274 {
1275   PetscErrorCode ierr;
1276   PetscInt       j,i,jdxm[128],jdxn[256],dim = mat->stencil.dim,*dims = mat->stencil.dims+1,tmp;
1277   PetscInt       *starts = mat->stencil.starts,*dxm = (PetscInt*)idxm,*dxn = (PetscInt*)idxn,sdim = dim - (1 - (PetscInt)mat->stencil.noc);
1278 
1279   PetscFunctionBegin;
1280   if (!m || !n) PetscFunctionReturn(0); /* no values to insert */
1281   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1282   PetscValidType(mat,1);
1283   PetscValidIntPointer(idxm,3);
1284   PetscValidIntPointer(idxn,5);
1285   PetscValidScalarPointer(v,6);
1286 
1287   if (m > 128) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Can only set 128 rows at a time; trying to set %D",m);
1288   if (n > 128) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Can only set 256 columns at a time; trying to set %D",n);
1289 
1290   for (i=0; i<m; i++) {
1291     for (j=0; j<3-sdim; j++) dxm++;
1292     tmp = *dxm++ - starts[0];
1293     for (j=0; j<sdim-1; j++) {
1294       if ((*dxm++ - starts[j+1]) < 0 || tmp < 0) tmp = PETSC_MIN_INT;
1295       else                                      tmp = tmp*dims[j] + *(dxm-1) - starts[j+1];
1296     }
1297     dxm++;
1298     jdxm[i] = tmp;
1299   }
1300   for (i=0; i<n; i++) {
1301     for (j=0; j<3-sdim; j++) dxn++;
1302     tmp = *dxn++ - starts[0];
1303     for (j=0; j<sdim-1; j++) {
1304       if ((*dxn++ - starts[j+1]) < 0 || tmp < 0) tmp = PETSC_MIN_INT;
1305       else                                       tmp = tmp*dims[j] + *(dxn-1) - starts[j+1];
1306     }
1307     dxn++;
1308     jdxn[i] = tmp;
1309   }
1310   ierr = MatSetValuesBlockedLocal(mat,m,jdxm,n,jdxn,v,addv);CHKERRQ(ierr);
1311   PetscFunctionReturn(0);
1312 }
1313 
1314 #undef __FUNCT__
1315 #define __FUNCT__ "MatSetStencil"
1316 /*@
1317    MatSetStencil - Sets the grid information for setting values into a matrix via
1318         MatSetValuesStencil()
1319 
1320    Not Collective
1321 
1322    Input Parameters:
1323 +  mat - the matrix
1324 .  dim - dimension of the grid 1, 2, or 3
1325 .  dims - number of grid points in x, y, and z direction, including ghost points on your processor
1326 .  starts - starting point of ghost nodes on your processor in x, y, and z direction
1327 -  dof - number of degrees of freedom per node
1328 
1329 
1330    Inspired by the structured grid interface to the HYPRE package
1331    (www.llnl.gov/CASC/hyper)
1332 
1333    For matrices generated with DAGetMatrix() this routine is automatically called and so not needed by the
1334    user.
1335 
1336    Level: beginner
1337 
1338    Concepts: matrices^putting entries in
1339 
1340 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal()
1341           MatSetValues(), MatSetValuesBlockedStencil(), MatSetValuesStencil()
1342 @*/
1343 PetscErrorCode PETSCMAT_DLLEXPORT MatSetStencil(Mat mat,PetscInt dim,const PetscInt dims[],const PetscInt starts[],PetscInt dof)
1344 {
1345   PetscInt i;
1346 
1347   PetscFunctionBegin;
1348   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1349   PetscValidIntPointer(dims,3);
1350   PetscValidIntPointer(starts,4);
1351 
1352   mat->stencil.dim = dim + (dof > 1);
1353   for (i=0; i<dim; i++) {
1354     mat->stencil.dims[i]   = dims[dim-i-1];      /* copy the values in backwards */
1355     mat->stencil.starts[i] = starts[dim-i-1];
1356   }
1357   mat->stencil.dims[dim]   = dof;
1358   mat->stencil.starts[dim] = 0;
1359   mat->stencil.noc         = (PetscTruth)(dof == 1);
1360   PetscFunctionReturn(0);
1361 }
1362 
1363 #undef __FUNCT__
1364 #define __FUNCT__ "MatSetValuesBlocked"
1365 /*@
1366    MatSetValuesBlocked - Inserts or adds a block of values into a matrix.
1367 
1368    Not Collective
1369 
1370    Input Parameters:
1371 +  mat - the matrix
1372 .  v - a logically two-dimensional array of values
1373 .  m, idxm - the number of block rows and their global block indices
1374 .  n, idxn - the number of block columns and their global block indices
1375 -  addv - either ADD_VALUES or INSERT_VALUES, where
1376    ADD_VALUES adds values to any existing entries, and
1377    INSERT_VALUES replaces existing entries with new values
1378 
1379    Notes:
1380    The m and n count the NUMBER of blocks in the row direction and column direction,
1381    NOT the total number of rows/columns; for example, if the block size is 2 and
1382    you are passing in values for rows 2,3,4,5  then m would be 2 (not 4).
1383    The values in idxm would be 1 2; that is the first index for each block divided by
1384    the block size.
1385 
1386    Note that you must call MatSetBlockSize() when constructing this matrix (after
1387    preallocating it).
1388 
1389    By default the values, v, are row-oriented, so the layout of
1390    v is the same as for MatSetValues(). See MatSetOption() for other options.
1391 
1392    Calls to MatSetValuesBlocked() with the INSERT_VALUES and ADD_VALUES
1393    options cannot be mixed without intervening calls to the assembly
1394    routines.
1395 
1396    MatSetValuesBlocked() uses 0-based row and column numbers in Fortran
1397    as well as in C.
1398 
1399    Negative indices may be passed in idxm and idxn, these rows and columns are
1400    simply ignored. This allows easily inserting element stiffness matrices
1401    with homogeneous Dirchlet boundary conditions that you don't want represented
1402    in the matrix.
1403 
1404    Each time an entry is set within a sparse matrix via MatSetValues(),
1405    internal searching must be done to determine where to place the the
1406    data in the matrix storage space.  By instead inserting blocks of
1407    entries via MatSetValuesBlocked(), the overhead of matrix assembly is
1408    reduced.
1409 
1410    Example:
1411 $   Suppose m=n=2 and block size(bs) = 2 The array is
1412 $
1413 $   1  2  | 3  4
1414 $   5  6  | 7  8
1415 $   - - - | - - -
1416 $   9  10 | 11 12
1417 $   13 14 | 15 16
1418 $
1419 $   v[] should be passed in like
1420 $   v[] = [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16]
1421 $
1422 $  If you are not using row oriented storage of v (that is you called MatSetOption(mat,MAT_ROW_ORIENTED,PETSC_FALSE)) then
1423 $   v[] = [1,5,9,13,2,6,10,14,3,7,11,15,4,8,12,16]
1424 
1425    Level: intermediate
1426 
1427    Concepts: matrices^putting entries in blocked
1428 
1429 .seealso: MatSetBlockSize(), MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetValuesBlockedLocal()
1430 @*/
1431 PetscErrorCode PETSCMAT_DLLEXPORT MatSetValuesBlocked(Mat mat,PetscInt m,const PetscInt idxm[],PetscInt n,const PetscInt idxn[],const PetscScalar v[],InsertMode addv)
1432 {
1433   PetscErrorCode ierr;
1434 
1435   PetscFunctionBegin;
1436   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1437   PetscValidType(mat,1);
1438   if (!m || !n) PetscFunctionReturn(0); /* no values to insert */
1439   PetscValidIntPointer(idxm,3);
1440   PetscValidIntPointer(idxn,5);
1441   PetscValidScalarPointer(v,6);
1442   ierr = MatPreallocated(mat);CHKERRQ(ierr);
1443   if (mat->insertmode == NOT_SET_VALUES) {
1444     mat->insertmode = addv;
1445   }
1446 #if defined(PETSC_USE_DEBUG)
1447   else if (mat->insertmode != addv) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values");
1448   if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1449 #endif
1450 
1451   if (mat->assembled) {
1452     mat->was_assembled = PETSC_TRUE;
1453     mat->assembled     = PETSC_FALSE;
1454   }
1455   ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
1456   if (mat->ops->setvaluesblocked) {
1457     ierr = (*mat->ops->setvaluesblocked)(mat,m,idxm,n,idxn,v,addv);CHKERRQ(ierr);
1458   } else {
1459     PetscInt buf[4096],*ibufm=0,*ibufn=0;
1460     PetscInt i,j,*iidxm,*iidxn,bs=mat->rmap->bs;
1461     if ((m+n)*bs <= 4096) {
1462       iidxm = buf; iidxn = buf + m*bs;
1463     } else {
1464       ierr = PetscMalloc2(m*bs,PetscInt,&ibufm,n*bs,PetscInt,&ibufn);CHKERRQ(ierr);
1465       iidxm = ibufm; iidxn = ibufn;
1466     }
1467     for (i=0; i<m; i++) {
1468       for (j=0; j<bs; j++) {
1469 	iidxm[i*bs+j] = bs*idxm[i] + j;
1470       }
1471     }
1472     for (i=0; i<n; i++) {
1473       for (j=0; j<bs; j++) {
1474 	iidxn[i*bs+j] = bs*idxn[i] + j;
1475       }
1476     }
1477     ierr = MatSetValues(mat,bs*m,iidxm,bs*n,iidxn,v,addv);CHKERRQ(ierr);
1478     ierr = PetscFree2(ibufm,ibufn);CHKERRQ(ierr);
1479   }
1480   ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
1481   PetscFunctionReturn(0);
1482 }
1483 
1484 #undef __FUNCT__
1485 #define __FUNCT__ "MatGetValues"
1486 /*@
1487    MatGetValues - Gets a block of values from a matrix.
1488 
1489    Not Collective; currently only returns a local block
1490 
1491    Input Parameters:
1492 +  mat - the matrix
1493 .  v - a logically two-dimensional array for storing the values
1494 .  m, idxm - the number of rows and their global indices
1495 -  n, idxn - the number of columns and their global indices
1496 
1497    Notes:
1498    The user must allocate space (m*n PetscScalars) for the values, v.
1499    The values, v, are then returned in a row-oriented format,
1500    analogous to that used by default in MatSetValues().
1501 
1502    MatGetValues() uses 0-based row and column numbers in
1503    Fortran as well as in C.
1504 
1505    MatGetValues() requires that the matrix has been assembled
1506    with MatAssemblyBegin()/MatAssemblyEnd().  Thus, calls to
1507    MatSetValues() and MatGetValues() CANNOT be made in succession
1508    without intermediate matrix assembly.
1509 
1510    Negative row or column indices will be ignored and those locations in v[] will be
1511    left unchanged.
1512 
1513    Level: advanced
1514 
1515    Concepts: matrices^accessing values
1516 
1517 .seealso: MatGetRow(), MatGetSubMatrices(), MatSetValues()
1518 @*/
1519 PetscErrorCode PETSCMAT_DLLEXPORT MatGetValues(Mat mat,PetscInt m,const PetscInt idxm[],PetscInt n,const PetscInt idxn[],PetscScalar v[])
1520 {
1521   PetscErrorCode ierr;
1522 
1523   PetscFunctionBegin;
1524   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1525   PetscValidType(mat,1);
1526   PetscValidIntPointer(idxm,3);
1527   PetscValidIntPointer(idxn,5);
1528   PetscValidScalarPointer(v,6);
1529   if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1530   if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1531   if (!mat->ops->getvalues) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
1532   ierr = MatPreallocated(mat);CHKERRQ(ierr);
1533 
1534   ierr = PetscLogEventBegin(MAT_GetValues,mat,0,0,0);CHKERRQ(ierr);
1535   ierr = (*mat->ops->getvalues)(mat,m,idxm,n,idxn,v);CHKERRQ(ierr);
1536   ierr = PetscLogEventEnd(MAT_GetValues,mat,0,0,0);CHKERRQ(ierr);
1537   PetscFunctionReturn(0);
1538 }
1539 
1540 #undef __FUNCT__
1541 #define __FUNCT__ "MatSetLocalToGlobalMapping"
1542 /*@
1543    MatSetLocalToGlobalMapping - Sets a local-to-global numbering for use by
1544    the routine MatSetValuesLocal() to allow users to insert matrix entries
1545    using a local (per-processor) numbering.
1546 
1547    Not Collective
1548 
1549    Input Parameters:
1550 +  x - the matrix
1551 -  mapping - mapping created with ISLocalToGlobalMappingCreate()
1552              or ISLocalToGlobalMappingCreateIS()
1553 
1554    Level: intermediate
1555 
1556    Concepts: matrices^local to global mapping
1557    Concepts: local to global mapping^for matrices
1558 
1559 .seealso:  MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetValuesLocal()
1560 @*/
1561 PetscErrorCode PETSCMAT_DLLEXPORT MatSetLocalToGlobalMapping(Mat x,ISLocalToGlobalMapping mapping)
1562 {
1563   PetscErrorCode ierr;
1564   PetscFunctionBegin;
1565   PetscValidHeaderSpecific(x,MAT_CLASSID,1);
1566   PetscValidType(x,1);
1567   PetscValidHeaderSpecific(mapping,IS_LTOGM_CLASSID,2);
1568   if (x->mapping) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Mapping already set for matrix");
1569   ierr = MatPreallocated(x);CHKERRQ(ierr);
1570 
1571   if (x->ops->setlocaltoglobalmapping) {
1572     ierr = (*x->ops->setlocaltoglobalmapping)(x,mapping);CHKERRQ(ierr);
1573   } else {
1574     ierr = PetscObjectReference((PetscObject)mapping);CHKERRQ(ierr);
1575     if (x->mapping) { ierr = ISLocalToGlobalMappingDestroy(x->mapping);CHKERRQ(ierr); }
1576     x->mapping = mapping;
1577   }
1578   PetscFunctionReturn(0);
1579 }
1580 
1581 #undef __FUNCT__
1582 #define __FUNCT__ "MatSetLocalToGlobalMappingBlock"
1583 /*@
1584    MatSetLocalToGlobalMappingBlock - Sets a local-to-global numbering for use
1585    by the routine MatSetValuesBlockedLocal() to allow users to insert matrix
1586    entries using a local (per-processor) numbering.
1587 
1588    Not Collective
1589 
1590    Input Parameters:
1591 +  x - the matrix
1592 -  mapping - mapping created with ISLocalToGlobalMappingCreate() or
1593              ISLocalToGlobalMappingCreateIS()
1594 
1595    Level: intermediate
1596 
1597    Concepts: matrices^local to global mapping blocked
1598    Concepts: local to global mapping^for matrices, blocked
1599 
1600 .seealso:  MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetValuesBlockedLocal(),
1601            MatSetValuesBlocked(), MatSetValuesLocal()
1602 @*/
1603 PetscErrorCode PETSCMAT_DLLEXPORT MatSetLocalToGlobalMappingBlock(Mat x,ISLocalToGlobalMapping mapping)
1604 {
1605   PetscErrorCode ierr;
1606   PetscFunctionBegin;
1607   PetscValidHeaderSpecific(x,MAT_CLASSID,1);
1608   PetscValidType(x,1);
1609   PetscValidHeaderSpecific(mapping,IS_LTOGM_CLASSID,2);
1610   if (x->bmapping) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Mapping already set for matrix");
1611   ierr = PetscObjectReference((PetscObject)mapping);CHKERRQ(ierr);
1612   if (x->bmapping) { ierr = ISLocalToGlobalMappingDestroy(x->bmapping);CHKERRQ(ierr); }
1613   x->bmapping = mapping;
1614   PetscFunctionReturn(0);
1615 }
1616 
1617 #undef __FUNCT__
1618 #define __FUNCT__ "MatSetValuesLocal"
1619 /*@
1620    MatSetValuesLocal - Inserts or adds values into certain locations of a matrix,
1621    using a local ordering of the nodes.
1622 
1623    Not Collective
1624 
1625    Input Parameters:
1626 +  x - the matrix
1627 .  nrow, irow - number of rows and their local indices
1628 .  ncol, icol - number of columns and their local indices
1629 .  y -  a logically two-dimensional array of values
1630 -  addv - either INSERT_VALUES or ADD_VALUES, where
1631    ADD_VALUES adds values to any existing entries, and
1632    INSERT_VALUES replaces existing entries with new values
1633 
1634    Notes:
1635    Before calling MatSetValuesLocal(), the user must first set the
1636    local-to-global mapping by calling MatSetLocalToGlobalMapping().
1637 
1638    Calls to MatSetValuesLocal() with the INSERT_VALUES and ADD_VALUES
1639    options cannot be mixed without intervening calls to the assembly
1640    routines.
1641 
1642    These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd()
1643    MUST be called after all calls to MatSetValuesLocal() have been completed.
1644 
1645    Level: intermediate
1646 
1647    Concepts: matrices^putting entries in with local numbering
1648 
1649 .seealso:  MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetLocalToGlobalMapping(),
1650            MatSetValueLocal()
1651 @*/
1652 PetscErrorCode PETSCMAT_DLLEXPORT MatSetValuesLocal(Mat mat,PetscInt nrow,const PetscInt irow[],PetscInt ncol,const PetscInt icol[],const PetscScalar y[],InsertMode addv)
1653 {
1654   PetscErrorCode ierr;
1655   PetscInt       irowm[2048],icolm[2048];
1656 
1657   PetscFunctionBegin;
1658   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1659   PetscValidType(mat,1);
1660   if (!nrow || !ncol) PetscFunctionReturn(0); /* no values to insert */
1661   PetscValidIntPointer(irow,3);
1662   PetscValidIntPointer(icol,5);
1663   PetscValidScalarPointer(y,6);
1664   ierr = MatPreallocated(mat);CHKERRQ(ierr);
1665   if (mat->insertmode == NOT_SET_VALUES) {
1666     mat->insertmode = addv;
1667   }
1668 #if defined(PETSC_USE_DEBUG)
1669   else if (mat->insertmode != addv) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values");
1670   if (!mat->ops->setvalueslocal && (nrow > 2048 || ncol > 2048)) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_SUP,"Number column/row indices must be <= 2048: are %D %D",nrow,ncol);
1671   if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1672 #endif
1673 
1674   if (mat->assembled) {
1675     mat->was_assembled = PETSC_TRUE;
1676     mat->assembled     = PETSC_FALSE;
1677   }
1678   ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
1679   if (!mat->ops->setvalueslocal) {
1680     ierr = ISLocalToGlobalMappingApply(mat->mapping,nrow,irow,irowm);CHKERRQ(ierr);
1681     ierr = ISLocalToGlobalMappingApply(mat->mapping,ncol,icol,icolm);CHKERRQ(ierr);
1682     ierr = (*mat->ops->setvalues)(mat,nrow,irowm,ncol,icolm,y,addv);CHKERRQ(ierr);
1683   } else {
1684     ierr = (*mat->ops->setvalueslocal)(mat,nrow,irow,ncol,icol,y,addv);CHKERRQ(ierr);
1685   }
1686   mat->same_nonzero = PETSC_FALSE;
1687   ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
1688   PetscFunctionReturn(0);
1689 }
1690 
1691 #undef __FUNCT__
1692 #define __FUNCT__ "MatSetValuesBlockedLocal"
1693 /*@
1694    MatSetValuesBlockedLocal - Inserts or adds values into certain locations of a matrix,
1695    using a local ordering of the nodes a block at a time.
1696 
1697    Not Collective
1698 
1699    Input Parameters:
1700 +  x - the matrix
1701 .  nrow, irow - number of rows and their local indices
1702 .  ncol, icol - number of columns and their local indices
1703 .  y -  a logically two-dimensional array of values
1704 -  addv - either INSERT_VALUES or ADD_VALUES, where
1705    ADD_VALUES adds values to any existing entries, and
1706    INSERT_VALUES replaces existing entries with new values
1707 
1708    Notes:
1709    Before calling MatSetValuesBlockedLocal(), the user must first set the
1710    block size using MatSetBlockSize(), and the local-to-global mapping by
1711    calling MatSetLocalToGlobalMappingBlock(), where the mapping MUST be
1712    set for matrix blocks, not for matrix elements.
1713 
1714    Calls to MatSetValuesBlockedLocal() with the INSERT_VALUES and ADD_VALUES
1715    options cannot be mixed without intervening calls to the assembly
1716    routines.
1717 
1718    These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd()
1719    MUST be called after all calls to MatSetValuesBlockedLocal() have been completed.
1720 
1721    Level: intermediate
1722 
1723    Concepts: matrices^putting blocked values in with local numbering
1724 
1725 .seealso:  MatSetBlockSize(), MatSetLocalToGlobalMappingBlock(), MatAssemblyBegin(), MatAssemblyEnd(),
1726            MatSetValuesLocal(), MatSetLocalToGlobalMappingBlock(), MatSetValuesBlocked()
1727 @*/
1728 PetscErrorCode PETSCMAT_DLLEXPORT MatSetValuesBlockedLocal(Mat mat,PetscInt nrow,const PetscInt irow[],PetscInt ncol,const PetscInt icol[],const PetscScalar y[],InsertMode addv)
1729 {
1730   PetscErrorCode ierr;
1731   PetscInt       irowm[2048],icolm[2048];
1732 
1733   PetscFunctionBegin;
1734   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1735   PetscValidType(mat,1);
1736   if (!nrow || !ncol) PetscFunctionReturn(0); /* no values to insert */
1737   PetscValidIntPointer(irow,3);
1738   PetscValidIntPointer(icol,5);
1739   PetscValidScalarPointer(y,6);
1740   ierr = MatPreallocated(mat);CHKERRQ(ierr);
1741   if (mat->insertmode == NOT_SET_VALUES) {
1742     mat->insertmode = addv;
1743   }
1744 #if defined(PETSC_USE_DEBUG)
1745   else if (mat->insertmode != addv) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values");
1746   if (!mat->bmapping) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Local to global never set with MatSetLocalToGlobalMappingBlock()");
1747   if (nrow > 2048 || ncol > 2048) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_SUP,"Number column/row indices must be <= 2048: are %D %D",nrow,ncol);
1748   if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1749 #endif
1750 
1751   if (mat->assembled) {
1752     mat->was_assembled = PETSC_TRUE;
1753     mat->assembled     = PETSC_FALSE;
1754   }
1755   ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
1756   ierr = ISLocalToGlobalMappingApply(mat->bmapping,nrow,irow,irowm);CHKERRQ(ierr);
1757   ierr = ISLocalToGlobalMappingApply(mat->bmapping,ncol,icol,icolm);CHKERRQ(ierr);
1758   if (mat->ops->setvaluesblocked) {
1759     ierr = (*mat->ops->setvaluesblocked)(mat,nrow,irowm,ncol,icolm,y,addv);CHKERRQ(ierr);
1760   } else {
1761     PetscInt buf[4096],*ibufm=0,*ibufn=0;
1762     PetscInt i,j,*iirowm,*iicolm,bs=mat->rmap->bs;
1763     if ((nrow+ncol)*bs <= 4096) {
1764       iirowm = buf; iicolm = buf + nrow*bs;
1765     } else {
1766       ierr = PetscMalloc2(nrow*bs,PetscInt,&ibufm,ncol*bs,PetscInt,&ibufn);CHKERRQ(ierr);
1767       iirowm = ibufm; iicolm = ibufn;
1768     }
1769     for (i=0; i<nrow; i++) {
1770       for (j=0; j<bs; j++) {
1771 	iirowm[i*bs+j] = bs*irowm[i] + j;
1772       }
1773     }
1774     for (i=0; i<ncol; i++) {
1775       for (j=0; j<bs; j++) {
1776 	iicolm[i*bs+j] = bs*icolm[i] + j;
1777       }
1778     }
1779     ierr = MatSetValues(mat,bs*nrow,iirowm,bs*ncol,iicolm,y,addv);CHKERRQ(ierr);
1780     ierr = PetscFree2(ibufm,ibufn);CHKERRQ(ierr);
1781   }
1782   ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
1783   PetscFunctionReturn(0);
1784 }
1785 
1786 #undef __FUNCT__
1787 #define __FUNCT__ "MatMultDiagonalBlock"
1788 /*@
1789    MatMultDiagonalBlock - Computes the matrix-vector product, y = Dx. Where D is defined by the inode or block structure of the diagonal
1790 
1791    Collective on Mat and Vec
1792 
1793    Input Parameters:
1794 +  mat - the matrix
1795 -  x   - the vector to be multiplied
1796 
1797    Output Parameters:
1798 .  y - the result
1799 
1800    Notes:
1801    The vectors x and y cannot be the same.  I.e., one cannot
1802    call MatMult(A,y,y).
1803 
1804    Level: developer
1805 
1806    Concepts: matrix-vector product
1807 
1808 .seealso: MatMultTranspose(), MatMultAdd(), MatMultTransposeAdd()
1809 @*/
1810 PetscErrorCode PETSCMAT_DLLEXPORT MatMultDiagonalBlock(Mat mat,Vec x,Vec y)
1811 {
1812   PetscErrorCode ierr;
1813 
1814   PetscFunctionBegin;
1815   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1816   PetscValidType(mat,1);
1817   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
1818   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
1819 
1820   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1821   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1822   if (x == y) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors");
1823   ierr = MatPreallocated(mat);CHKERRQ(ierr);
1824 
1825   if (!mat->ops->multdiagonalblock) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_SUP,"This matrix type does not have a multiply defined");
1826   ierr = (*mat->ops->multdiagonalblock)(mat,x,y);CHKERRQ(ierr);
1827   ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr);
1828   PetscFunctionReturn(0);
1829 }
1830 
1831 /* --------------------------------------------------------*/
1832 #undef __FUNCT__
1833 #define __FUNCT__ "MatMult"
1834 /*@
1835    MatMult - Computes the matrix-vector product, y = Ax.
1836 
1837    Collective on Mat and Vec
1838 
1839    Input Parameters:
1840 +  mat - the matrix
1841 -  x   - the vector to be multiplied
1842 
1843    Output Parameters:
1844 .  y - the result
1845 
1846    Notes:
1847    The vectors x and y cannot be the same.  I.e., one cannot
1848    call MatMult(A,y,y).
1849 
1850    Level: beginner
1851 
1852    Concepts: matrix-vector product
1853 
1854 .seealso: MatMultTranspose(), MatMultAdd(), MatMultTransposeAdd()
1855 @*/
1856 PetscErrorCode PETSCMAT_DLLEXPORT MatMult(Mat mat,Vec x,Vec y)
1857 {
1858   PetscErrorCode ierr;
1859 
1860   PetscFunctionBegin;
1861   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1862   PetscValidType(mat,1);
1863   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
1864   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
1865 
1866   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1867   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1868   if (x == y) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors");
1869 #ifndef PETSC_HAVE_CONSTRAINTS
1870   if (mat->cmap->N != x->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N);
1871   if (mat->rmap->N != y->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->rmap->N,y->map->N);
1872   if (mat->rmap->n != y->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: local dim %D %D",mat->rmap->n,y->map->n);
1873 #endif
1874   ierr = MatPreallocated(mat);CHKERRQ(ierr);
1875 
1876   if (mat->nullsp) {
1877     ierr = MatNullSpaceRemove(mat->nullsp,x,&x);CHKERRQ(ierr);
1878   }
1879 
1880   if (!mat->ops->mult) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_SUP,"This matrix type does not have a multiply defined");
1881   ierr = PetscLogEventBegin(MAT_Mult,mat,x,y,0);CHKERRQ(ierr);
1882   ierr = (*mat->ops->mult)(mat,x,y);CHKERRQ(ierr);
1883   ierr = PetscLogEventEnd(MAT_Mult,mat,x,y,0);CHKERRQ(ierr);
1884 
1885   if (mat->nullsp) {
1886     ierr = MatNullSpaceRemove(mat->nullsp,y,PETSC_NULL);CHKERRQ(ierr);
1887   }
1888   ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr);
1889   PetscFunctionReturn(0);
1890 }
1891 
1892 #undef __FUNCT__
1893 #define __FUNCT__ "MatMultTranspose"
1894 /*@
1895    MatMultTranspose - Computes matrix transpose times a vector.
1896 
1897    Collective on Mat and Vec
1898 
1899    Input Parameters:
1900 +  mat - the matrix
1901 -  x   - the vector to be multilplied
1902 
1903    Output Parameters:
1904 .  y - the result
1905 
1906    Notes:
1907    The vectors x and y cannot be the same.  I.e., one cannot
1908    call MatMultTranspose(A,y,y).
1909 
1910    Level: beginner
1911 
1912    Concepts: matrix vector product^transpose
1913 
1914 .seealso: MatMult(), MatMultAdd(), MatMultTransposeAdd()
1915 @*/
1916 PetscErrorCode PETSCMAT_DLLEXPORT MatMultTranspose(Mat mat,Vec x,Vec y)
1917 {
1918   PetscErrorCode ierr;
1919 
1920   PetscFunctionBegin;
1921   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1922   PetscValidType(mat,1);
1923   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
1924   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
1925 
1926   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1927   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1928   if (x == y) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors");
1929 #ifndef PETSC_HAVE_CONSTRAINTS
1930   if (mat->rmap->N != x->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->rmap->N,x->map->N);
1931   if (mat->cmap->N != y->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->cmap->N,y->map->N);
1932 #endif
1933   ierr = MatPreallocated(mat);CHKERRQ(ierr);
1934 
1935   if (!mat->ops->multtranspose) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_SUP,"This matrix type does not have a multiply tranpose defined");
1936   ierr = PetscLogEventBegin(MAT_MultTranspose,mat,x,y,0);CHKERRQ(ierr);
1937   ierr = (*mat->ops->multtranspose)(mat,x,y);CHKERRQ(ierr);
1938   ierr = PetscLogEventEnd(MAT_MultTranspose,mat,x,y,0);CHKERRQ(ierr);
1939   ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr);
1940   PetscFunctionReturn(0);
1941 }
1942 
1943 #undef __FUNCT__
1944 #define __FUNCT__ "MatMultHermitianTranspose"
1945 /*@
1946    MatMultHermitianTranspose - Computes matrix Hermitian transpose times a vector.
1947 
1948    Collective on Mat and Vec
1949 
1950    Input Parameters:
1951 +  mat - the matrix
1952 -  x   - the vector to be multilplied
1953 
1954    Output Parameters:
1955 .  y - the result
1956 
1957    Notes:
1958    The vectors x and y cannot be the same.  I.e., one cannot
1959    call MatMultHermitianTranspose(A,y,y).
1960 
1961    Level: beginner
1962 
1963    Concepts: matrix vector product^transpose
1964 
1965 .seealso: MatMult(), MatMultAdd(), MatMultHermitianTransposeAdd(), MatMultTranspose()
1966 @*/
1967 PetscErrorCode PETSCMAT_DLLEXPORT MatMultHermitianTranspose(Mat mat,Vec x,Vec y)
1968 {
1969   PetscErrorCode ierr;
1970 
1971   PetscFunctionBegin;
1972   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
1973   PetscValidType(mat,1);
1974   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
1975   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
1976 
1977   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
1978   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
1979   if (x == y) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors");
1980 #ifndef PETSC_HAVE_CONSTRAINTS
1981   if (mat->rmap->N != x->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->rmap->N,x->map->N);
1982   if (mat->cmap->N != y->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->cmap->N,y->map->N);
1983 #endif
1984   ierr = MatPreallocated(mat);CHKERRQ(ierr);
1985 
1986   if (!mat->ops->multtranspose) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_SUP,"This matrix type does not have a multiply tranpose defined");
1987   ierr = PetscLogEventBegin(MAT_MultHermitianTranspose,mat,x,y,0);CHKERRQ(ierr);
1988   ierr = (*mat->ops->multhermitiantranspose)(mat,x,y);CHKERRQ(ierr);
1989   ierr = PetscLogEventEnd(MAT_MultHermitianTranspose,mat,x,y,0);CHKERRQ(ierr);
1990   ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr);
1991   PetscFunctionReturn(0);
1992 }
1993 
1994 #undef __FUNCT__
1995 #define __FUNCT__ "MatMultAdd"
1996 /*@
1997     MatMultAdd -  Computes v3 = v2 + A * v1.
1998 
1999     Collective on Mat and Vec
2000 
2001     Input Parameters:
2002 +   mat - the matrix
2003 -   v1, v2 - the vectors
2004 
2005     Output Parameters:
2006 .   v3 - the result
2007 
2008     Notes:
2009     The vectors v1 and v3 cannot be the same.  I.e., one cannot
2010     call MatMultAdd(A,v1,v2,v1).
2011 
2012     Level: beginner
2013 
2014     Concepts: matrix vector product^addition
2015 
2016 .seealso: MatMultTranspose(), MatMult(), MatMultTransposeAdd()
2017 @*/
2018 PetscErrorCode PETSCMAT_DLLEXPORT MatMultAdd(Mat mat,Vec v1,Vec v2,Vec v3)
2019 {
2020   PetscErrorCode ierr;
2021 
2022   PetscFunctionBegin;
2023   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2024   PetscValidType(mat,1);
2025   PetscValidHeaderSpecific(v1,VEC_CLASSID,2);
2026   PetscValidHeaderSpecific(v2,VEC_CLASSID,3);
2027   PetscValidHeaderSpecific(v3,VEC_CLASSID,4);
2028 
2029   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2030   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2031   if (mat->cmap->N != v1->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v1: global dim %D %D",mat->cmap->N,v1->map->N);
2032   /* if (mat->rmap->N != v2->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: global dim %D %D",mat->rmap->N,v2->map->N);
2033      if (mat->rmap->N != v3->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: global dim %D %D",mat->rmap->N,v3->map->N); */
2034   if (mat->rmap->n != v3->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: local dim %D %D",mat->rmap->n,v3->map->n);
2035   if (mat->rmap->n != v2->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: local dim %D %D",mat->rmap->n,v2->map->n);
2036   if (v1 == v3) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_IDN,"v1 and v3 must be different vectors");
2037   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2038 
2039   ierr = PetscLogEventBegin(MAT_MultAdd,mat,v1,v2,v3);CHKERRQ(ierr);
2040   ierr = (*mat->ops->multadd)(mat,v1,v2,v3);CHKERRQ(ierr);
2041   ierr = PetscLogEventEnd(MAT_MultAdd,mat,v1,v2,v3);CHKERRQ(ierr);
2042   ierr = PetscObjectStateIncrease((PetscObject)v3);CHKERRQ(ierr);
2043   PetscFunctionReturn(0);
2044 }
2045 
2046 #undef __FUNCT__
2047 #define __FUNCT__ "MatMultTransposeAdd"
2048 /*@
2049    MatMultTransposeAdd - Computes v3 = v2 + A' * v1.
2050 
2051    Collective on Mat and Vec
2052 
2053    Input Parameters:
2054 +  mat - the matrix
2055 -  v1, v2 - the vectors
2056 
2057    Output Parameters:
2058 .  v3 - the result
2059 
2060    Notes:
2061    The vectors v1 and v3 cannot be the same.  I.e., one cannot
2062    call MatMultTransposeAdd(A,v1,v2,v1).
2063 
2064    Level: beginner
2065 
2066    Concepts: matrix vector product^transpose and addition
2067 
2068 .seealso: MatMultTranspose(), MatMultAdd(), MatMult()
2069 @*/
2070 PetscErrorCode PETSCMAT_DLLEXPORT MatMultTransposeAdd(Mat mat,Vec v1,Vec v2,Vec v3)
2071 {
2072   PetscErrorCode ierr;
2073 
2074   PetscFunctionBegin;
2075   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2076   PetscValidType(mat,1);
2077   PetscValidHeaderSpecific(v1,VEC_CLASSID,2);
2078   PetscValidHeaderSpecific(v2,VEC_CLASSID,3);
2079   PetscValidHeaderSpecific(v3,VEC_CLASSID,4);
2080 
2081   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2082   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2083   if (!mat->ops->multtransposeadd) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2084   if (v1 == v3) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_IDN,"v1 and v3 must be different vectors");
2085   if (mat->rmap->N != v1->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v1: global dim %D %D",mat->rmap->N,v1->map->N);
2086   if (mat->cmap->N != v2->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: global dim %D %D",mat->cmap->N,v2->map->N);
2087   if (mat->cmap->N != v3->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: global dim %D %D",mat->cmap->N,v3->map->N);
2088   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2089 
2090   ierr = PetscLogEventBegin(MAT_MultTransposeAdd,mat,v1,v2,v3);CHKERRQ(ierr);
2091   ierr = (*mat->ops->multtransposeadd)(mat,v1,v2,v3);CHKERRQ(ierr);
2092   ierr = PetscLogEventEnd(MAT_MultTransposeAdd,mat,v1,v2,v3);CHKERRQ(ierr);
2093   ierr = PetscObjectStateIncrease((PetscObject)v3);CHKERRQ(ierr);
2094   PetscFunctionReturn(0);
2095 }
2096 
2097 #undef __FUNCT__
2098 #define __FUNCT__ "MatMultHermitianTransposeAdd"
2099 /*@
2100    MatMultHermitianTransposeAdd - Computes v3 = v2 + A^H * v1.
2101 
2102    Collective on Mat and Vec
2103 
2104    Input Parameters:
2105 +  mat - the matrix
2106 -  v1, v2 - the vectors
2107 
2108    Output Parameters:
2109 .  v3 - the result
2110 
2111    Notes:
2112    The vectors v1 and v3 cannot be the same.  I.e., one cannot
2113    call MatMultHermitianTransposeAdd(A,v1,v2,v1).
2114 
2115    Level: beginner
2116 
2117    Concepts: matrix vector product^transpose and addition
2118 
2119 .seealso: MatMultHermitianTranspose(), MatMultTranspose(), MatMultAdd(), MatMult()
2120 @*/
2121 PetscErrorCode PETSCMAT_DLLEXPORT MatMultHermitianTransposeAdd(Mat mat,Vec v1,Vec v2,Vec v3)
2122 {
2123   PetscErrorCode ierr;
2124 
2125   PetscFunctionBegin;
2126   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2127   PetscValidType(mat,1);
2128   PetscValidHeaderSpecific(v1,VEC_CLASSID,2);
2129   PetscValidHeaderSpecific(v2,VEC_CLASSID,3);
2130   PetscValidHeaderSpecific(v3,VEC_CLASSID,4);
2131 
2132   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2133   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2134   if (!mat->ops->multtransposeadd) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2135   if (v1 == v3) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_IDN,"v1 and v3 must be different vectors");
2136   if (mat->rmap->N != v1->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v1: global dim %D %D",mat->rmap->N,v1->map->N);
2137   if (mat->cmap->N != v2->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: global dim %D %D",mat->cmap->N,v2->map->N);
2138   if (mat->cmap->N != v3->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: global dim %D %D",mat->cmap->N,v3->map->N);
2139   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2140 
2141   ierr = PetscLogEventBegin(MAT_MultHermitianTransposeAdd,mat,v1,v2,v3);CHKERRQ(ierr);
2142   ierr = (*mat->ops->multhermitiantransposeadd)(mat,v1,v2,v3);CHKERRQ(ierr);
2143   ierr = PetscLogEventEnd(MAT_MultHermitianTransposeAdd,mat,v1,v2,v3);CHKERRQ(ierr);
2144   ierr = PetscObjectStateIncrease((PetscObject)v3);CHKERRQ(ierr);
2145   PetscFunctionReturn(0);
2146 }
2147 
2148 #undef __FUNCT__
2149 #define __FUNCT__ "MatMultConstrained"
2150 /*@
2151    MatMultConstrained - The inner multiplication routine for a
2152    constrained matrix P^T A P.
2153 
2154    Collective on Mat and Vec
2155 
2156    Input Parameters:
2157 +  mat - the matrix
2158 -  x   - the vector to be multilplied
2159 
2160    Output Parameters:
2161 .  y - the result
2162 
2163    Notes:
2164    The vectors x and y cannot be the same.  I.e., one cannot
2165    call MatMult(A,y,y).
2166 
2167    Level: beginner
2168 
2169 .keywords: matrix, multiply, matrix-vector product, constraint
2170 .seealso: MatMult(), MatMultTranspose(), MatMultAdd(), MatMultTransposeAdd()
2171 @*/
2172 PetscErrorCode PETSCMAT_DLLEXPORT MatMultConstrained(Mat mat,Vec x,Vec y)
2173 {
2174   PetscErrorCode ierr;
2175 
2176   PetscFunctionBegin;
2177   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2178   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
2179   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
2180   if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2181   if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2182   if (x == y) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors");
2183   if (mat->cmap->N != x->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N);
2184   if (mat->rmap->N != y->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->rmap->N,y->map->N);
2185   if (mat->rmap->n != y->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: local dim %D %D",mat->rmap->n,y->map->n);
2186 
2187   ierr = PetscLogEventBegin(MAT_MultConstrained,mat,x,y,0);CHKERRQ(ierr);
2188   ierr = (*mat->ops->multconstrained)(mat,x,y);CHKERRQ(ierr);
2189   ierr = PetscLogEventEnd(MAT_MultConstrained,mat,x,y,0);CHKERRQ(ierr);
2190   ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr);
2191 
2192   PetscFunctionReturn(0);
2193 }
2194 
2195 #undef __FUNCT__
2196 #define __FUNCT__ "MatMultTransposeConstrained"
2197 /*@
2198    MatMultTransposeConstrained - The inner multiplication routine for a
2199    constrained matrix P^T A^T P.
2200 
2201    Collective on Mat and Vec
2202 
2203    Input Parameters:
2204 +  mat - the matrix
2205 -  x   - the vector to be multilplied
2206 
2207    Output Parameters:
2208 .  y - the result
2209 
2210    Notes:
2211    The vectors x and y cannot be the same.  I.e., one cannot
2212    call MatMult(A,y,y).
2213 
2214    Level: beginner
2215 
2216 .keywords: matrix, multiply, matrix-vector product, constraint
2217 .seealso: MatMult(), MatMultTranspose(), MatMultAdd(), MatMultTransposeAdd()
2218 @*/
2219 PetscErrorCode PETSCMAT_DLLEXPORT MatMultTransposeConstrained(Mat mat,Vec x,Vec y)
2220 {
2221   PetscErrorCode ierr;
2222 
2223   PetscFunctionBegin;
2224   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2225   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
2226   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
2227   if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2228   if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2229   if (x == y) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors");
2230   if (mat->rmap->N != x->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N);
2231   if (mat->cmap->N != y->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->rmap->N,y->map->N);
2232 
2233   ierr = PetscLogEventBegin(MAT_MultConstrained,mat,x,y,0);CHKERRQ(ierr);
2234   ierr = (*mat->ops->multtransposeconstrained)(mat,x,y);CHKERRQ(ierr);
2235   ierr = PetscLogEventEnd(MAT_MultConstrained,mat,x,y,0);CHKERRQ(ierr);
2236   ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr);
2237 
2238   PetscFunctionReturn(0);
2239 }
2240 
2241 #undef __FUNCT__
2242 #define __FUNCT__ "MatGetFactorType"
2243 /*@C
2244    MatGetFactorType - gets the type of factorization it is
2245 
2246    Note Collective
2247    as the flag
2248 
2249    Input Parameters:
2250 .  mat - the matrix
2251 
2252    Output Parameters:
2253 .  t - the type, one of MAT_FACTOR_NONE, MAT_FACTOR_LU, MAT_FACTOR_CHOLESKY, MAT_FACTOR_ILU, MAT_FACTOR_ICC,MAT_FACTOR_ILUDT
2254 
2255     Level: intermediate
2256 
2257 .seealso:    MatFactorType, MatGetFactor()
2258 @*/
2259 PetscErrorCode PETSCMAT_DLLEXPORT MatGetFactorType(Mat mat,MatFactorType *t)
2260 {
2261   PetscFunctionBegin;
2262   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2263   PetscValidType(mat,1);
2264   *t = mat->factortype;
2265   PetscFunctionReturn(0);
2266 }
2267 
2268 /* ------------------------------------------------------------*/
2269 #undef __FUNCT__
2270 #define __FUNCT__ "MatGetInfo"
2271 /*@C
2272    MatGetInfo - Returns information about matrix storage (number of
2273    nonzeros, memory, etc.).
2274 
2275    Collective on Mat if MAT_GLOBAL_MAX or MAT_GLOBAL_SUM is used
2276    as the flag
2277 
2278    Input Parameters:
2279 .  mat - the matrix
2280 
2281    Output Parameters:
2282 +  flag - flag indicating the type of parameters to be returned
2283    (MAT_LOCAL - local matrix, MAT_GLOBAL_MAX - maximum over all processors,
2284    MAT_GLOBAL_SUM - sum over all processors)
2285 -  info - matrix information context
2286 
2287    Notes:
2288    The MatInfo context contains a variety of matrix data, including
2289    number of nonzeros allocated and used, number of mallocs during
2290    matrix assembly, etc.  Additional information for factored matrices
2291    is provided (such as the fill ratio, number of mallocs during
2292    factorization, etc.).  Much of this info is printed to PETSC_STDOUT
2293    when using the runtime options
2294 $       -info -mat_view_info
2295 
2296    Example for C/C++ Users:
2297    See the file ${PETSC_DIR}/include/petscmat.h for a complete list of
2298    data within the MatInfo context.  For example,
2299 .vb
2300       MatInfo info;
2301       Mat     A;
2302       double  mal, nz_a, nz_u;
2303 
2304       MatGetInfo(A,MAT_LOCAL,&info);
2305       mal  = info.mallocs;
2306       nz_a = info.nz_allocated;
2307 .ve
2308 
2309    Example for Fortran Users:
2310    Fortran users should declare info as a double precision
2311    array of dimension MAT_INFO_SIZE, and then extract the parameters
2312    of interest.  See the file ${PETSC_DIR}/include/finclude/petscmat.h
2313    a complete list of parameter names.
2314 .vb
2315       double  precision info(MAT_INFO_SIZE)
2316       double  precision mal, nz_a
2317       Mat     A
2318       integer ierr
2319 
2320       call MatGetInfo(A,MAT_LOCAL,info,ierr)
2321       mal = info(MAT_INFO_MALLOCS)
2322       nz_a = info(MAT_INFO_NZ_ALLOCATED)
2323 .ve
2324 
2325     Level: intermediate
2326 
2327     Concepts: matrices^getting information on
2328 
2329     Developer Note: fortran interface is not autogenerated as the f90
2330     interface defintion cannot be generated correctly [due to MatInfo]
2331 
2332 @*/
2333 PetscErrorCode PETSCMAT_DLLEXPORT MatGetInfo(Mat mat,MatInfoType flag,MatInfo *info)
2334 {
2335   PetscErrorCode ierr;
2336 
2337   PetscFunctionBegin;
2338   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2339   PetscValidType(mat,1);
2340   PetscValidPointer(info,3);
2341   if (!mat->ops->getinfo) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2342   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2343   ierr = (*mat->ops->getinfo)(mat,flag,info);CHKERRQ(ierr);
2344   PetscFunctionReturn(0);
2345 }
2346 
2347 /* ----------------------------------------------------------*/
2348 
2349 #undef __FUNCT__
2350 #define __FUNCT__ "MatLUFactor"
2351 /*@C
2352    MatLUFactor - Performs in-place LU factorization of matrix.
2353 
2354    Collective on Mat
2355 
2356    Input Parameters:
2357 +  mat - the matrix
2358 .  row - row permutation
2359 .  col - column permutation
2360 -  info - options for factorization, includes
2361 $          fill - expected fill as ratio of original fill.
2362 $          dtcol - pivot tolerance (0 no pivot, 1 full column pivoting)
2363 $                   Run with the option -info to determine an optimal value to use
2364 
2365    Notes:
2366    Most users should employ the simplified KSP interface for linear solvers
2367    instead of working directly with matrix algebra routines such as this.
2368    See, e.g., KSPCreate().
2369 
2370    This changes the state of the matrix to a factored matrix; it cannot be used
2371    for example with MatSetValues() unless one first calls MatSetUnfactored().
2372 
2373    Level: developer
2374 
2375    Concepts: matrices^LU factorization
2376 
2377 .seealso: MatLUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor(),
2378           MatGetOrdering(), MatSetUnfactored(), MatFactorInfo
2379 
2380     Developer Note: fortran interface is not autogenerated as the f90
2381     interface defintion cannot be generated correctly [due to MatFactorInfo]
2382 
2383 @*/
2384 PetscErrorCode PETSCMAT_DLLEXPORT MatLUFactor(Mat mat,IS row,IS col,const MatFactorInfo *info)
2385 {
2386   PetscErrorCode ierr;
2387 
2388   PetscFunctionBegin;
2389   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2390   if (row) PetscValidHeaderSpecific(row,IS_CLASSID,2);
2391   if (col) PetscValidHeaderSpecific(col,IS_CLASSID,3);
2392   PetscValidPointer(info,4);
2393   PetscValidType(mat,1);
2394   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2395   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2396   if (!mat->ops->lufactor) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2397   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2398 
2399   ierr = PetscLogEventBegin(MAT_LUFactor,mat,row,col,0);CHKERRQ(ierr);
2400   ierr = (*mat->ops->lufactor)(mat,row,col,info);CHKERRQ(ierr);
2401   ierr = PetscLogEventEnd(MAT_LUFactor,mat,row,col,0);CHKERRQ(ierr);
2402   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
2403   PetscFunctionReturn(0);
2404 }
2405 
2406 #undef __FUNCT__
2407 #define __FUNCT__ "MatILUFactor"
2408 /*@C
2409    MatILUFactor - Performs in-place ILU factorization of matrix.
2410 
2411    Collective on Mat
2412 
2413    Input Parameters:
2414 +  mat - the matrix
2415 .  row - row permutation
2416 .  col - column permutation
2417 -  info - structure containing
2418 $      levels - number of levels of fill.
2419 $      expected fill - as ratio of original fill.
2420 $      1 or 0 - indicating force fill on diagonal (improves robustness for matrices
2421                 missing diagonal entries)
2422 
2423    Notes:
2424    Probably really in-place only when level of fill is zero, otherwise allocates
2425    new space to store factored matrix and deletes previous memory.
2426 
2427    Most users should employ the simplified KSP interface for linear solvers
2428    instead of working directly with matrix algebra routines such as this.
2429    See, e.g., KSPCreate().
2430 
2431    Level: developer
2432 
2433    Concepts: matrices^ILU factorization
2434 
2435 .seealso: MatILUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor(), MatFactorInfo
2436 
2437     Developer Note: fortran interface is not autogenerated as the f90
2438     interface defintion cannot be generated correctly [due to MatFactorInfo]
2439 
2440 @*/
2441 PetscErrorCode PETSCMAT_DLLEXPORT MatILUFactor(Mat mat,IS row,IS col,const MatFactorInfo *info)
2442 {
2443   PetscErrorCode ierr;
2444 
2445   PetscFunctionBegin;
2446   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2447   if (row) PetscValidHeaderSpecific(row,IS_CLASSID,2);
2448   if (col) PetscValidHeaderSpecific(col,IS_CLASSID,3);
2449   PetscValidPointer(info,4);
2450   PetscValidType(mat,1);
2451   if (mat->rmap->N != mat->cmap->N) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONG,"matrix must be square");
2452   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2453   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2454   if (!mat->ops->ilufactor) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2455   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2456 
2457   ierr = PetscLogEventBegin(MAT_ILUFactor,mat,row,col,0);CHKERRQ(ierr);
2458   ierr = (*mat->ops->ilufactor)(mat,row,col,info);CHKERRQ(ierr);
2459   ierr = PetscLogEventEnd(MAT_ILUFactor,mat,row,col,0);CHKERRQ(ierr);
2460   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
2461   PetscFunctionReturn(0);
2462 }
2463 
2464 #undef __FUNCT__
2465 #define __FUNCT__ "MatLUFactorSymbolic"
2466 /*@C
2467    MatLUFactorSymbolic - Performs symbolic LU factorization of matrix.
2468    Call this routine before calling MatLUFactorNumeric().
2469 
2470    Collective on Mat
2471 
2472    Input Parameters:
2473 +  fact - the factor matrix obtained with MatGetFactor()
2474 .  mat - the matrix
2475 .  row, col - row and column permutations
2476 -  info - options for factorization, includes
2477 $          fill - expected fill as ratio of original fill.
2478 $          dtcol - pivot tolerance (0 no pivot, 1 full column pivoting)
2479 $                   Run with the option -info to determine an optimal value to use
2480 
2481 
2482    Notes:
2483    See the users manual for additional information about
2484    choosing the fill factor for better efficiency.
2485 
2486    Most users should employ the simplified KSP interface for linear solvers
2487    instead of working directly with matrix algebra routines such as this.
2488    See, e.g., KSPCreate().
2489 
2490    Level: developer
2491 
2492    Concepts: matrices^LU symbolic factorization
2493 
2494 .seealso: MatLUFactor(), MatLUFactorNumeric(), MatCholeskyFactor(), MatFactorInfo
2495 
2496     Developer Note: fortran interface is not autogenerated as the f90
2497     interface defintion cannot be generated correctly [due to MatFactorInfo]
2498 
2499 @*/
2500 PetscErrorCode PETSCMAT_DLLEXPORT MatLUFactorSymbolic(Mat fact,Mat mat,IS row,IS col,const MatFactorInfo *info)
2501 {
2502   PetscErrorCode ierr;
2503 
2504   PetscFunctionBegin;
2505   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2506   if (row) PetscValidHeaderSpecific(row,IS_CLASSID,2);
2507   if (col) PetscValidHeaderSpecific(col,IS_CLASSID,3);
2508   PetscValidPointer(info,4);
2509   PetscValidType(mat,1);
2510   PetscValidPointer(fact,5);
2511   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2512   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2513   if (!(fact)->ops->lufactorsymbolic) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Matrix type %s  symbolic LU",((PetscObject)mat)->type_name);
2514   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2515 
2516   ierr = PetscLogEventBegin(MAT_LUFactorSymbolic,mat,row,col,0);CHKERRQ(ierr);
2517   ierr = (fact->ops->lufactorsymbolic)(fact,mat,row,col,info);CHKERRQ(ierr);
2518   ierr = PetscLogEventEnd(MAT_LUFactorSymbolic,mat,row,col,0);CHKERRQ(ierr);
2519   ierr = PetscObjectStateIncrease((PetscObject)fact);CHKERRQ(ierr);
2520   PetscFunctionReturn(0);
2521 }
2522 
2523 #undef __FUNCT__
2524 #define __FUNCT__ "MatLUFactorNumeric"
2525 /*@C
2526    MatLUFactorNumeric - Performs numeric LU factorization of a matrix.
2527    Call this routine after first calling MatLUFactorSymbolic().
2528 
2529    Collective on Mat
2530 
2531    Input Parameters:
2532 +  fact - the factor matrix obtained with MatGetFactor()
2533 .  mat - the matrix
2534 -  info - options for factorization
2535 
2536    Notes:
2537    See MatLUFactor() for in-place factorization.  See
2538    MatCholeskyFactorNumeric() for the symmetric, positive definite case.
2539 
2540    Most users should employ the simplified KSP interface for linear solvers
2541    instead of working directly with matrix algebra routines such as this.
2542    See, e.g., KSPCreate().
2543 
2544    Level: developer
2545 
2546    Concepts: matrices^LU numeric factorization
2547 
2548 .seealso: MatLUFactorSymbolic(), MatLUFactor(), MatCholeskyFactor()
2549 
2550     Developer Note: fortran interface is not autogenerated as the f90
2551     interface defintion cannot be generated correctly [due to MatFactorInfo]
2552 
2553 @*/
2554 PetscErrorCode PETSCMAT_DLLEXPORT MatLUFactorNumeric(Mat fact,Mat mat,const MatFactorInfo *info)
2555 {
2556   PetscErrorCode ierr;
2557 
2558   PetscFunctionBegin;
2559   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2560   PetscValidType(mat,1);
2561   PetscValidPointer(fact,2);
2562   PetscValidHeaderSpecific(fact,MAT_CLASSID,2);
2563   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2564   if (mat->rmap->N != (fact)->rmap->N || mat->cmap->N != (fact)->cmap->N) {
2565     SETERRQ4(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Mat fact: global dimensions are different %D should = %D %D should = %D",mat->rmap->N,(fact)->rmap->N,mat->cmap->N,(fact)->cmap->N);
2566   }
2567   if (!(fact)->ops->lufactornumeric) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2568   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2569   ierr = PetscLogEventBegin(MAT_LUFactorNumeric,mat,fact,0,0);CHKERRQ(ierr);
2570   ierr = (fact->ops->lufactornumeric)(fact,mat,info);CHKERRQ(ierr);
2571   ierr = PetscLogEventEnd(MAT_LUFactorNumeric,mat,fact,0,0);CHKERRQ(ierr);
2572 
2573   ierr = MatView_Private(fact);CHKERRQ(ierr);
2574   ierr = PetscObjectStateIncrease((PetscObject)fact);CHKERRQ(ierr);
2575   PetscFunctionReturn(0);
2576 }
2577 
2578 #undef __FUNCT__
2579 #define __FUNCT__ "MatCholeskyFactor"
2580 /*@C
2581    MatCholeskyFactor - Performs in-place Cholesky factorization of a
2582    symmetric matrix.
2583 
2584    Collective on Mat
2585 
2586    Input Parameters:
2587 +  mat - the matrix
2588 .  perm - row and column permutations
2589 -  f - expected fill as ratio of original fill
2590 
2591    Notes:
2592    See MatLUFactor() for the nonsymmetric case.  See also
2593    MatCholeskyFactorSymbolic(), and MatCholeskyFactorNumeric().
2594 
2595    Most users should employ the simplified KSP interface for linear solvers
2596    instead of working directly with matrix algebra routines such as this.
2597    See, e.g., KSPCreate().
2598 
2599    Level: developer
2600 
2601    Concepts: matrices^Cholesky factorization
2602 
2603 .seealso: MatLUFactor(), MatCholeskyFactorSymbolic(), MatCholeskyFactorNumeric()
2604           MatGetOrdering()
2605 
2606     Developer Note: fortran interface is not autogenerated as the f90
2607     interface defintion cannot be generated correctly [due to MatFactorInfo]
2608 
2609 @*/
2610 PetscErrorCode PETSCMAT_DLLEXPORT MatCholeskyFactor(Mat mat,IS perm,const MatFactorInfo *info)
2611 {
2612   PetscErrorCode ierr;
2613 
2614   PetscFunctionBegin;
2615   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2616   PetscValidType(mat,1);
2617   PetscValidHeaderSpecific(perm,IS_CLASSID,2);
2618   PetscValidPointer(info,3);
2619   if (mat->rmap->N != mat->cmap->N) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONG,"Matrix must be square");
2620   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2621   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2622   if (!mat->ops->choleskyfactor) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2623   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2624 
2625   ierr = PetscLogEventBegin(MAT_CholeskyFactor,mat,perm,0,0);CHKERRQ(ierr);
2626   ierr = (*mat->ops->choleskyfactor)(mat,perm,info);CHKERRQ(ierr);
2627   ierr = PetscLogEventEnd(MAT_CholeskyFactor,mat,perm,0,0);CHKERRQ(ierr);
2628   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
2629   PetscFunctionReturn(0);
2630 }
2631 
2632 #undef __FUNCT__
2633 #define __FUNCT__ "MatCholeskyFactorSymbolic"
2634 /*@C
2635    MatCholeskyFactorSymbolic - Performs symbolic Cholesky factorization
2636    of a symmetric matrix.
2637 
2638    Collective on Mat
2639 
2640    Input Parameters:
2641 +  fact - the factor matrix obtained with MatGetFactor()
2642 .  mat - the matrix
2643 .  perm - row and column permutations
2644 -  info - options for factorization, includes
2645 $          fill - expected fill as ratio of original fill.
2646 $          dtcol - pivot tolerance (0 no pivot, 1 full column pivoting)
2647 $                   Run with the option -info to determine an optimal value to use
2648 
2649    Notes:
2650    See MatLUFactorSymbolic() for the nonsymmetric case.  See also
2651    MatCholeskyFactor() and MatCholeskyFactorNumeric().
2652 
2653    Most users should employ the simplified KSP interface for linear solvers
2654    instead of working directly with matrix algebra routines such as this.
2655    See, e.g., KSPCreate().
2656 
2657    Level: developer
2658 
2659    Concepts: matrices^Cholesky symbolic factorization
2660 
2661 .seealso: MatLUFactorSymbolic(), MatCholeskyFactor(), MatCholeskyFactorNumeric()
2662           MatGetOrdering()
2663 
2664     Developer Note: fortran interface is not autogenerated as the f90
2665     interface defintion cannot be generated correctly [due to MatFactorInfo]
2666 
2667 @*/
2668 PetscErrorCode PETSCMAT_DLLEXPORT MatCholeskyFactorSymbolic(Mat fact,Mat mat,IS perm,const MatFactorInfo *info)
2669 {
2670   PetscErrorCode ierr;
2671 
2672   PetscFunctionBegin;
2673   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2674   PetscValidType(mat,1);
2675   if (perm) PetscValidHeaderSpecific(perm,IS_CLASSID,2);
2676   PetscValidPointer(info,3);
2677   PetscValidPointer(fact,4);
2678   if (mat->rmap->N != mat->cmap->N) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONG,"Matrix must be square");
2679   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2680   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
2681   if (!(fact)->ops->choleskyfactorsymbolic) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2682   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2683 
2684   ierr = PetscLogEventBegin(MAT_CholeskyFactorSymbolic,mat,perm,0,0);CHKERRQ(ierr);
2685   ierr = (fact->ops->choleskyfactorsymbolic)(fact,mat,perm,info);CHKERRQ(ierr);
2686   ierr = PetscLogEventEnd(MAT_CholeskyFactorSymbolic,mat,perm,0,0);CHKERRQ(ierr);
2687   ierr = PetscObjectStateIncrease((PetscObject)fact);CHKERRQ(ierr);
2688   PetscFunctionReturn(0);
2689 }
2690 
2691 #undef __FUNCT__
2692 #define __FUNCT__ "MatCholeskyFactorNumeric"
2693 /*@C
2694    MatCholeskyFactorNumeric - Performs numeric Cholesky factorization
2695    of a symmetric matrix. Call this routine after first calling
2696    MatCholeskyFactorSymbolic().
2697 
2698    Collective on Mat
2699 
2700    Input Parameters:
2701 +  fact - the factor matrix obtained with MatGetFactor()
2702 .  mat - the initial matrix
2703 .  info - options for factorization
2704 -  fact - the symbolic factor of mat
2705 
2706 
2707    Notes:
2708    Most users should employ the simplified KSP interface for linear solvers
2709    instead of working directly with matrix algebra routines such as this.
2710    See, e.g., KSPCreate().
2711 
2712    Level: developer
2713 
2714    Concepts: matrices^Cholesky numeric factorization
2715 
2716 .seealso: MatCholeskyFactorSymbolic(), MatCholeskyFactor(), MatLUFactorNumeric()
2717 
2718     Developer Note: fortran interface is not autogenerated as the f90
2719     interface defintion cannot be generated correctly [due to MatFactorInfo]
2720 
2721 @*/
2722 PetscErrorCode PETSCMAT_DLLEXPORT MatCholeskyFactorNumeric(Mat fact,Mat mat,const MatFactorInfo *info)
2723 {
2724   PetscErrorCode ierr;
2725 
2726   PetscFunctionBegin;
2727   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2728   PetscValidType(mat,1);
2729   PetscValidPointer(fact,2);
2730   PetscValidHeaderSpecific(fact,MAT_CLASSID,2);
2731   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
2732   if (!(fact)->ops->choleskyfactornumeric) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2733   if (mat->rmap->N != (fact)->rmap->N || mat->cmap->N != (fact)->cmap->N) {
2734     SETERRQ4(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Mat fact: global dim %D should = %D %D should = %D",mat->rmap->N,(fact)->rmap->N,mat->cmap->N,(fact)->cmap->N);
2735   }
2736   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2737 
2738   ierr = PetscLogEventBegin(MAT_CholeskyFactorNumeric,mat,fact,0,0);CHKERRQ(ierr);
2739   ierr = (fact->ops->choleskyfactornumeric)(fact,mat,info);CHKERRQ(ierr);
2740   ierr = PetscLogEventEnd(MAT_CholeskyFactorNumeric,mat,fact,0,0);CHKERRQ(ierr);
2741 
2742   ierr = MatView_Private(fact);CHKERRQ(ierr);
2743   ierr = PetscObjectStateIncrease((PetscObject)fact);CHKERRQ(ierr);
2744   PetscFunctionReturn(0);
2745 }
2746 
2747 /* ----------------------------------------------------------------*/
2748 #undef __FUNCT__
2749 #define __FUNCT__ "MatSolve"
2750 /*@
2751    MatSolve - Solves A x = b, given a factored matrix.
2752 
2753    Collective on Mat and Vec
2754 
2755    Input Parameters:
2756 +  mat - the factored matrix
2757 -  b - the right-hand-side vector
2758 
2759    Output Parameter:
2760 .  x - the result vector
2761 
2762    Notes:
2763    The vectors b and x cannot be the same.  I.e., one cannot
2764    call MatSolve(A,x,x).
2765 
2766    Notes:
2767    Most users should employ the simplified KSP interface for linear solvers
2768    instead of working directly with matrix algebra routines such as this.
2769    See, e.g., KSPCreate().
2770 
2771    Level: developer
2772 
2773    Concepts: matrices^triangular solves
2774 
2775 .seealso: MatSolveAdd(), MatSolveTranspose(), MatSolveTransposeAdd()
2776 @*/
2777 PetscErrorCode PETSCMAT_DLLEXPORT MatSolve(Mat mat,Vec b,Vec x)
2778 {
2779   PetscErrorCode ierr;
2780 
2781   PetscFunctionBegin;
2782   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2783   PetscValidType(mat,1);
2784   PetscValidHeaderSpecific(b,VEC_CLASSID,2);
2785   PetscValidHeaderSpecific(x,VEC_CLASSID,3);
2786   PetscCheckSameComm(mat,1,b,2);
2787   PetscCheckSameComm(mat,1,x,3);
2788   if (x == b) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_IDN,"x and b must be different vectors");
2789   if (!mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
2790   if (mat->cmap->N != x->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N);
2791   if (mat->rmap->N != b->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->rmap->N,b->map->N);
2792   if (mat->rmap->n != b->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->rmap->n,b->map->n);
2793   if (!mat->rmap->N && !mat->cmap->N) PetscFunctionReturn(0);
2794   if (!mat->ops->solve) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2795   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2796 
2797   ierr = PetscLogEventBegin(MAT_Solve,mat,b,x,0);CHKERRQ(ierr);
2798   ierr = (*mat->ops->solve)(mat,b,x);CHKERRQ(ierr);
2799   ierr = PetscLogEventEnd(MAT_Solve,mat,b,x,0);CHKERRQ(ierr);
2800   ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr);
2801   PetscFunctionReturn(0);
2802 }
2803 
2804 #undef __FUNCT__
2805 #define __FUNCT__ "MatMatSolve_Basic"
2806 PetscErrorCode PETSCMAT_DLLEXPORT MatMatSolve_Basic(Mat A,Mat B,Mat X)
2807 {
2808   PetscErrorCode ierr;
2809   Vec            b,x;
2810   PetscInt       m,N,i;
2811   PetscScalar    *bb,*xx;
2812 
2813   PetscFunctionBegin;
2814   ierr = MatGetArray(B,&bb);CHKERRQ(ierr);
2815   ierr = MatGetArray(X,&xx);CHKERRQ(ierr);
2816   ierr = MatGetLocalSize(B,&m,PETSC_NULL);CHKERRQ(ierr);  /* number local rows */
2817   ierr = MatGetSize(B,PETSC_NULL,&N);CHKERRQ(ierr);       /* total columns in dense matrix */
2818   ierr = MatGetVecs(A,&x,&b);CHKERRQ(ierr);
2819   for (i=0; i<N; i++) {
2820     ierr = VecPlaceArray(b,bb + i*m);CHKERRQ(ierr);
2821     ierr = VecPlaceArray(x,xx + i*m);CHKERRQ(ierr);
2822     ierr = MatSolve(A,b,x);CHKERRQ(ierr);
2823     ierr = VecResetArray(x);CHKERRQ(ierr);
2824     ierr = VecResetArray(b);CHKERRQ(ierr);
2825   }
2826   ierr = VecDestroy(b);CHKERRQ(ierr);
2827   ierr = VecDestroy(x);CHKERRQ(ierr);
2828   ierr = MatRestoreArray(B,&bb);CHKERRQ(ierr);
2829   ierr = MatRestoreArray(X,&xx);CHKERRQ(ierr);
2830   PetscFunctionReturn(0);
2831 }
2832 
2833 #undef __FUNCT__
2834 #define __FUNCT__ "MatMatSolve"
2835 /*@
2836    MatMatSolve - Solves A X = B, given a factored matrix.
2837 
2838    Collective on Mat
2839 
2840    Input Parameters:
2841 +  mat - the factored matrix
2842 -  B - the right-hand-side matrix  (dense matrix)
2843 
2844    Output Parameter:
2845 .  X - the result matrix (dense matrix)
2846 
2847    Notes:
2848    The matrices b and x cannot be the same.  I.e., one cannot
2849    call MatMatSolve(A,x,x).
2850 
2851    Notes:
2852    Most users should usually employ the simplified KSP interface for linear solvers
2853    instead of working directly with matrix algebra routines such as this.
2854    See, e.g., KSPCreate(). However KSP can only solve for one vector (column of X)
2855    at a time.
2856 
2857    Level: developer
2858 
2859    Concepts: matrices^triangular solves
2860 
2861 .seealso: MatMatSolveAdd(), MatMatSolveTranspose(), MatMatSolveTransposeAdd(), MatLUFactor(), MatCholeskyFactor()
2862 @*/
2863 PetscErrorCode PETSCMAT_DLLEXPORT MatMatSolve(Mat A,Mat B,Mat X)
2864 {
2865   PetscErrorCode ierr;
2866 
2867   PetscFunctionBegin;
2868   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
2869   PetscValidType(A,1);
2870   PetscValidHeaderSpecific(B,MAT_CLASSID,2);
2871   PetscValidHeaderSpecific(X,MAT_CLASSID,3);
2872   PetscCheckSameComm(A,1,B,2);
2873   PetscCheckSameComm(A,1,X,3);
2874   if (X == B) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_IDN,"X and B must be different matrices");
2875   if (!A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
2876   if (A->cmap->N != X->rmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Mat A,Mat X: global dim %D %D",A->cmap->N,X->rmap->N);
2877   if (A->rmap->N != B->rmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Mat A,Mat B: global dim %D %D",A->rmap->N,B->rmap->N);
2878   if (A->rmap->n != B->rmap->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat A,Mat B: local dim %D %D",A->rmap->n,B->rmap->n);
2879   if (!A->rmap->N && !A->cmap->N) PetscFunctionReturn(0);
2880   ierr = MatPreallocated(A);CHKERRQ(ierr);
2881 
2882   ierr = PetscLogEventBegin(MAT_MatSolve,A,B,X,0);CHKERRQ(ierr);
2883   if (!A->ops->matsolve) {
2884     ierr = PetscInfo1(A,"Mat type %s using basic MatMatSolve",((PetscObject)A)->type_name);CHKERRQ(ierr);
2885     ierr = MatMatSolve_Basic(A,B,X);CHKERRQ(ierr);
2886   } else {
2887     ierr = (*A->ops->matsolve)(A,B,X);CHKERRQ(ierr);
2888   }
2889   ierr = PetscLogEventEnd(MAT_MatSolve,A,B,X,0);CHKERRQ(ierr);
2890   ierr = PetscObjectStateIncrease((PetscObject)X);CHKERRQ(ierr);
2891   PetscFunctionReturn(0);
2892 }
2893 
2894 
2895 #undef __FUNCT__
2896 #define __FUNCT__ "MatForwardSolve"
2897 /*@
2898    MatForwardSolve - Solves L x = b, given a factored matrix, A = LU, or
2899                             U^T*D^(1/2) x = b, given a factored symmetric matrix, A = U^T*D*U,
2900 
2901    Collective on Mat and Vec
2902 
2903    Input Parameters:
2904 +  mat - the factored matrix
2905 -  b - the right-hand-side vector
2906 
2907    Output Parameter:
2908 .  x - the result vector
2909 
2910    Notes:
2911    MatSolve() should be used for most applications, as it performs
2912    a forward solve followed by a backward solve.
2913 
2914    The vectors b and x cannot be the same,  i.e., one cannot
2915    call MatForwardSolve(A,x,x).
2916 
2917    For matrix in seqsbaij format with block size larger than 1,
2918    the diagonal blocks are not implemented as D = D^(1/2) * D^(1/2) yet.
2919    MatForwardSolve() solves U^T*D y = b, and
2920    MatBackwardSolve() solves U x = y.
2921    Thus they do not provide a symmetric preconditioner.
2922 
2923    Most users should employ the simplified KSP interface for linear solvers
2924    instead of working directly with matrix algebra routines such as this.
2925    See, e.g., KSPCreate().
2926 
2927    Level: developer
2928 
2929    Concepts: matrices^forward solves
2930 
2931 .seealso: MatSolve(), MatBackwardSolve()
2932 @*/
2933 PetscErrorCode PETSCMAT_DLLEXPORT MatForwardSolve(Mat mat,Vec b,Vec x)
2934 {
2935   PetscErrorCode ierr;
2936 
2937   PetscFunctionBegin;
2938   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
2939   PetscValidType(mat,1);
2940   PetscValidHeaderSpecific(b,VEC_CLASSID,2);
2941   PetscValidHeaderSpecific(x,VEC_CLASSID,3);
2942   PetscCheckSameComm(mat,1,b,2);
2943   PetscCheckSameComm(mat,1,x,3);
2944   if (x == b) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_IDN,"x and b must be different vectors");
2945   if (!mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
2946   if (!mat->ops->forwardsolve) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
2947   if (mat->cmap->N != x->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N);
2948   if (mat->rmap->N != b->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->rmap->N,b->map->N);
2949   if (mat->rmap->n != b->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->rmap->n,b->map->n);
2950   ierr = MatPreallocated(mat);CHKERRQ(ierr);
2951   ierr = PetscLogEventBegin(MAT_ForwardSolve,mat,b,x,0);CHKERRQ(ierr);
2952   ierr = (*mat->ops->forwardsolve)(mat,b,x);CHKERRQ(ierr);
2953   ierr = PetscLogEventEnd(MAT_ForwardSolve,mat,b,x,0);CHKERRQ(ierr);
2954   ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr);
2955   PetscFunctionReturn(0);
2956 }
2957 
2958 #undef __FUNCT__
2959 #define __FUNCT__ "MatBackwardSolve"
2960 /*@
2961    MatBackwardSolve - Solves U x = b, given a factored matrix, A = LU.
2962                              D^(1/2) U x = b, given a factored symmetric matrix, A = U^T*D*U,
2963 
2964    Collective on Mat and Vec
2965 
2966    Input Parameters:
2967 +  mat - the factored matrix
2968 -  b - the right-hand-side vector
2969 
2970    Output Parameter:
2971 .  x - the result vector
2972 
2973    Notes:
2974    MatSolve() should be used for most applications, as it performs
2975    a forward solve followed by a backward solve.
2976 
2977    The vectors b and x cannot be the same.  I.e., one cannot
2978    call MatBackwardSolve(A,x,x).
2979 
2980    For matrix in seqsbaij format with block size larger than 1,
2981    the diagonal blocks are not implemented as D = D^(1/2) * D^(1/2) yet.
2982    MatForwardSolve() solves U^T*D y = b, and
2983    MatBackwardSolve() solves U x = y.
2984    Thus they do not provide a symmetric preconditioner.
2985 
2986    Most users should employ the simplified KSP interface for linear solvers
2987    instead of working directly with matrix algebra routines such as this.
2988    See, e.g., KSPCreate().
2989 
2990    Level: developer
2991 
2992    Concepts: matrices^backward solves
2993 
2994 .seealso: MatSolve(), MatForwardSolve()
2995 @*/
2996 PetscErrorCode PETSCMAT_DLLEXPORT MatBackwardSolve(Mat mat,Vec b,Vec x)
2997 {
2998   PetscErrorCode ierr;
2999 
3000   PetscFunctionBegin;
3001   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3002   PetscValidType(mat,1);
3003   PetscValidHeaderSpecific(b,VEC_CLASSID,2);
3004   PetscValidHeaderSpecific(x,VEC_CLASSID,3);
3005   PetscCheckSameComm(mat,1,b,2);
3006   PetscCheckSameComm(mat,1,x,3);
3007   if (x == b) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_IDN,"x and b must be different vectors");
3008   if (!mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
3009   if (!mat->ops->backwardsolve) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
3010   if (mat->cmap->N != x->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N);
3011   if (mat->rmap->N != b->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->rmap->N,b->map->N);
3012   if (mat->rmap->n != b->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->rmap->n,b->map->n);
3013   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3014 
3015   ierr = PetscLogEventBegin(MAT_BackwardSolve,mat,b,x,0);CHKERRQ(ierr);
3016   ierr = (*mat->ops->backwardsolve)(mat,b,x);CHKERRQ(ierr);
3017   ierr = PetscLogEventEnd(MAT_BackwardSolve,mat,b,x,0);CHKERRQ(ierr);
3018   ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr);
3019   PetscFunctionReturn(0);
3020 }
3021 
3022 #undef __FUNCT__
3023 #define __FUNCT__ "MatSolveAdd"
3024 /*@
3025    MatSolveAdd - Computes x = y + inv(A)*b, given a factored matrix.
3026 
3027    Collective on Mat and Vec
3028 
3029    Input Parameters:
3030 +  mat - the factored matrix
3031 .  b - the right-hand-side vector
3032 -  y - the vector to be added to
3033 
3034    Output Parameter:
3035 .  x - the result vector
3036 
3037    Notes:
3038    The vectors b and x cannot be the same.  I.e., one cannot
3039    call MatSolveAdd(A,x,y,x).
3040 
3041    Most users should employ the simplified KSP interface for linear solvers
3042    instead of working directly with matrix algebra routines such as this.
3043    See, e.g., KSPCreate().
3044 
3045    Level: developer
3046 
3047    Concepts: matrices^triangular solves
3048 
3049 .seealso: MatSolve(), MatSolveTranspose(), MatSolveTransposeAdd()
3050 @*/
3051 PetscErrorCode PETSCMAT_DLLEXPORT MatSolveAdd(Mat mat,Vec b,Vec y,Vec x)
3052 {
3053   PetscScalar    one = 1.0;
3054   Vec            tmp;
3055   PetscErrorCode ierr;
3056 
3057   PetscFunctionBegin;
3058   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3059   PetscValidType(mat,1);
3060   PetscValidHeaderSpecific(y,VEC_CLASSID,2);
3061   PetscValidHeaderSpecific(b,VEC_CLASSID,3);
3062   PetscValidHeaderSpecific(x,VEC_CLASSID,4);
3063   PetscCheckSameComm(mat,1,b,2);
3064   PetscCheckSameComm(mat,1,y,2);
3065   PetscCheckSameComm(mat,1,x,3);
3066   if (x == b) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_IDN,"x and b must be different vectors");
3067   if (!mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
3068   if (mat->cmap->N != x->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N);
3069   if (mat->rmap->N != b->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->rmap->N,b->map->N);
3070   if (mat->rmap->N != y->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->rmap->N,y->map->N);
3071   if (mat->rmap->n != b->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->rmap->n,b->map->n);
3072   if (x->map->n != y->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Vec x,Vec y: local dim %D %D",x->map->n,y->map->n);
3073   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3074 
3075   ierr = PetscLogEventBegin(MAT_SolveAdd,mat,b,x,y);CHKERRQ(ierr);
3076   if (mat->ops->solveadd)  {
3077     ierr = (*mat->ops->solveadd)(mat,b,y,x);CHKERRQ(ierr);
3078   } else {
3079     /* do the solve then the add manually */
3080     if (x != y) {
3081       ierr = MatSolve(mat,b,x);CHKERRQ(ierr);
3082       ierr = VecAXPY(x,one,y);CHKERRQ(ierr);
3083     } else {
3084       ierr = VecDuplicate(x,&tmp);CHKERRQ(ierr);
3085       ierr = PetscLogObjectParent(mat,tmp);CHKERRQ(ierr);
3086       ierr = VecCopy(x,tmp);CHKERRQ(ierr);
3087       ierr = MatSolve(mat,b,x);CHKERRQ(ierr);
3088       ierr = VecAXPY(x,one,tmp);CHKERRQ(ierr);
3089       ierr = VecDestroy(tmp);CHKERRQ(ierr);
3090     }
3091   }
3092   ierr = PetscLogEventEnd(MAT_SolveAdd,mat,b,x,y);CHKERRQ(ierr);
3093   ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr);
3094   PetscFunctionReturn(0);
3095 }
3096 
3097 #undef __FUNCT__
3098 #define __FUNCT__ "MatSolveTranspose"
3099 /*@
3100    MatSolveTranspose - Solves A' x = b, given a factored matrix.
3101 
3102    Collective on Mat and Vec
3103 
3104    Input Parameters:
3105 +  mat - the factored matrix
3106 -  b - the right-hand-side vector
3107 
3108    Output Parameter:
3109 .  x - the result vector
3110 
3111    Notes:
3112    The vectors b and x cannot be the same.  I.e., one cannot
3113    call MatSolveTranspose(A,x,x).
3114 
3115    Most users should employ the simplified KSP interface for linear solvers
3116    instead of working directly with matrix algebra routines such as this.
3117    See, e.g., KSPCreate().
3118 
3119    Level: developer
3120 
3121    Concepts: matrices^triangular solves
3122 
3123 .seealso: MatSolve(), MatSolveAdd(), MatSolveTransposeAdd()
3124 @*/
3125 PetscErrorCode PETSCMAT_DLLEXPORT MatSolveTranspose(Mat mat,Vec b,Vec x)
3126 {
3127   PetscErrorCode ierr;
3128 
3129   PetscFunctionBegin;
3130   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3131   PetscValidType(mat,1);
3132   PetscValidHeaderSpecific(b,VEC_CLASSID,2);
3133   PetscValidHeaderSpecific(x,VEC_CLASSID,3);
3134   PetscCheckSameComm(mat,1,b,2);
3135   PetscCheckSameComm(mat,1,x,3);
3136   if (!mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
3137   if (x == b) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_IDN,"x and b must be different vectors");
3138   if (!mat->ops->solvetranspose) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Matrix type %s",((PetscObject)mat)->type_name);
3139   if (mat->rmap->N != x->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->rmap->N,x->map->N);
3140   if (mat->cmap->N != b->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->cmap->N,b->map->N);
3141   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3142   ierr = PetscLogEventBegin(MAT_SolveTranspose,mat,b,x,0);CHKERRQ(ierr);
3143   ierr = (*mat->ops->solvetranspose)(mat,b,x);CHKERRQ(ierr);
3144   ierr = PetscLogEventEnd(MAT_SolveTranspose,mat,b,x,0);CHKERRQ(ierr);
3145   ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr);
3146   PetscFunctionReturn(0);
3147 }
3148 
3149 #undef __FUNCT__
3150 #define __FUNCT__ "MatSolveTransposeAdd"
3151 /*@
3152    MatSolveTransposeAdd - Computes x = y + inv(Transpose(A)) b, given a
3153                       factored matrix.
3154 
3155    Collective on Mat and Vec
3156 
3157    Input Parameters:
3158 +  mat - the factored matrix
3159 .  b - the right-hand-side vector
3160 -  y - the vector to be added to
3161 
3162    Output Parameter:
3163 .  x - the result vector
3164 
3165    Notes:
3166    The vectors b and x cannot be the same.  I.e., one cannot
3167    call MatSolveTransposeAdd(A,x,y,x).
3168 
3169    Most users should employ the simplified KSP interface for linear solvers
3170    instead of working directly with matrix algebra routines such as this.
3171    See, e.g., KSPCreate().
3172 
3173    Level: developer
3174 
3175    Concepts: matrices^triangular solves
3176 
3177 .seealso: MatSolve(), MatSolveAdd(), MatSolveTranspose()
3178 @*/
3179 PetscErrorCode PETSCMAT_DLLEXPORT MatSolveTransposeAdd(Mat mat,Vec b,Vec y,Vec x)
3180 {
3181   PetscScalar    one = 1.0;
3182   PetscErrorCode ierr;
3183   Vec            tmp;
3184 
3185   PetscFunctionBegin;
3186   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3187   PetscValidType(mat,1);
3188   PetscValidHeaderSpecific(y,VEC_CLASSID,2);
3189   PetscValidHeaderSpecific(b,VEC_CLASSID,3);
3190   PetscValidHeaderSpecific(x,VEC_CLASSID,4);
3191   PetscCheckSameComm(mat,1,b,2);
3192   PetscCheckSameComm(mat,1,y,3);
3193   PetscCheckSameComm(mat,1,x,4);
3194   if (x == b) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_IDN,"x and b must be different vectors");
3195   if (!mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
3196   if (mat->rmap->N != x->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->rmap->N,x->map->N);
3197   if (mat->cmap->N != b->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->cmap->N,b->map->N);
3198   if (mat->cmap->N != y->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->cmap->N,y->map->N);
3199   if (x->map->n != y->map->n)   SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Vec x,Vec y: local dim %D %D",x->map->n,y->map->n);
3200   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3201 
3202   ierr = PetscLogEventBegin(MAT_SolveTransposeAdd,mat,b,x,y);CHKERRQ(ierr);
3203   if (mat->ops->solvetransposeadd) {
3204     ierr = (*mat->ops->solvetransposeadd)(mat,b,y,x);CHKERRQ(ierr);
3205   } else {
3206     /* do the solve then the add manually */
3207     if (x != y) {
3208       ierr = MatSolveTranspose(mat,b,x);CHKERRQ(ierr);
3209       ierr = VecAXPY(x,one,y);CHKERRQ(ierr);
3210     } else {
3211       ierr = VecDuplicate(x,&tmp);CHKERRQ(ierr);
3212       ierr = PetscLogObjectParent(mat,tmp);CHKERRQ(ierr);
3213       ierr = VecCopy(x,tmp);CHKERRQ(ierr);
3214       ierr = MatSolveTranspose(mat,b,x);CHKERRQ(ierr);
3215       ierr = VecAXPY(x,one,tmp);CHKERRQ(ierr);
3216       ierr = VecDestroy(tmp);CHKERRQ(ierr);
3217     }
3218   }
3219   ierr = PetscLogEventEnd(MAT_SolveTransposeAdd,mat,b,x,y);CHKERRQ(ierr);
3220   ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr);
3221   PetscFunctionReturn(0);
3222 }
3223 /* ----------------------------------------------------------------*/
3224 
3225 #undef __FUNCT__
3226 #define __FUNCT__ "MatSOR"
3227 /*@
3228    MatSOR - Computes relaxation (SOR, Gauss-Seidel) sweeps.
3229 
3230    Collective on Mat and Vec
3231 
3232    Input Parameters:
3233 +  mat - the matrix
3234 .  b - the right hand side
3235 .  omega - the relaxation factor
3236 .  flag - flag indicating the type of SOR (see below)
3237 .  shift -  diagonal shift
3238 .  its - the number of iterations
3239 -  lits - the number of local iterations
3240 
3241    Output Parameters:
3242 .  x - the solution (can contain an initial guess, use option SOR_ZERO_INITIAL_GUESS to indicate no guess)
3243 
3244    SOR Flags:
3245 .     SOR_FORWARD_SWEEP - forward SOR
3246 .     SOR_BACKWARD_SWEEP - backward SOR
3247 .     SOR_SYMMETRIC_SWEEP - SSOR (symmetric SOR)
3248 .     SOR_LOCAL_FORWARD_SWEEP - local forward SOR
3249 .     SOR_LOCAL_BACKWARD_SWEEP - local forward SOR
3250 .     SOR_LOCAL_SYMMETRIC_SWEEP - local SSOR
3251 .     SOR_APPLY_UPPER, SOR_APPLY_LOWER - applies
3252          upper/lower triangular part of matrix to
3253          vector (with omega)
3254 .     SOR_ZERO_INITIAL_GUESS - zero initial guess
3255 
3256    Notes:
3257    SOR_LOCAL_FORWARD_SWEEP, SOR_LOCAL_BACKWARD_SWEEP, and
3258    SOR_LOCAL_SYMMETRIC_SWEEP perform separate independent smoothings
3259    on each processor.
3260 
3261    Application programmers will not generally use MatSOR() directly,
3262    but instead will employ the KSP/PC interface.
3263 
3264    Notes: for BAIJ, SBAIJ, and AIJ matrices with Inodes this does a block SOR smoothing, otherwise it does a pointwise smoothing
3265 
3266    Notes for Advanced Users:
3267    The flags are implemented as bitwise inclusive or operations.
3268    For example, use (SOR_ZERO_INITIAL_GUESS | SOR_SYMMETRIC_SWEEP)
3269    to specify a zero initial guess for SSOR.
3270 
3271    Most users should employ the simplified KSP interface for linear solvers
3272    instead of working directly with matrix algebra routines such as this.
3273    See, e.g., KSPCreate().
3274 
3275 
3276    Level: developer
3277 
3278    Concepts: matrices^relaxation
3279    Concepts: matrices^SOR
3280    Concepts: matrices^Gauss-Seidel
3281 
3282 @*/
3283 PetscErrorCode PETSCMAT_DLLEXPORT MatSOR(Mat mat,Vec b,PetscReal omega,MatSORType flag,PetscReal shift,PetscInt its,PetscInt lits,Vec x)
3284 {
3285   PetscErrorCode ierr;
3286 
3287   PetscFunctionBegin;
3288   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3289   PetscValidType(mat,1);
3290   PetscValidHeaderSpecific(b,VEC_CLASSID,2);
3291   PetscValidHeaderSpecific(x,VEC_CLASSID,8);
3292   PetscCheckSameComm(mat,1,b,2);
3293   PetscCheckSameComm(mat,1,x,8);
3294   if (!mat->ops->sor) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
3295   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3296   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3297   if (mat->cmap->N != x->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N);
3298   if (mat->rmap->N != b->map->N) SETERRQ2(((PetscObject)mat)->comm,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->rmap->N,b->map->N);
3299   if (mat->rmap->n != b->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->rmap->n,b->map->n);
3300   if (its <= 0) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Relaxation requires global its %D positive",its);
3301   if (lits <= 0) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Relaxation requires local its %D positive",lits);
3302 
3303   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3304   ierr = PetscLogEventBegin(MAT_SOR,mat,b,x,0);CHKERRQ(ierr);
3305   ierr =(*mat->ops->sor)(mat,b,omega,flag,shift,its,lits,x);CHKERRQ(ierr);
3306   ierr = PetscLogEventEnd(MAT_SOR,mat,b,x,0);CHKERRQ(ierr);
3307   ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr);
3308   PetscFunctionReturn(0);
3309 }
3310 
3311 #undef __FUNCT__
3312 #define __FUNCT__ "MatCopy_Basic"
3313 /*
3314       Default matrix copy routine.
3315 */
3316 PetscErrorCode MatCopy_Basic(Mat A,Mat B,MatStructure str)
3317 {
3318   PetscErrorCode    ierr;
3319   PetscInt          i,rstart = 0,rend = 0,nz;
3320   const PetscInt    *cwork;
3321   const PetscScalar *vwork;
3322 
3323   PetscFunctionBegin;
3324   if (B->assembled) {
3325     ierr = MatZeroEntries(B);CHKERRQ(ierr);
3326   }
3327   ierr = MatGetOwnershipRange(A,&rstart,&rend);CHKERRQ(ierr);
3328   for (i=rstart; i<rend; i++) {
3329     ierr = MatGetRow(A,i,&nz,&cwork,&vwork);CHKERRQ(ierr);
3330     ierr = MatSetValues(B,1,&i,nz,cwork,vwork,INSERT_VALUES);CHKERRQ(ierr);
3331     ierr = MatRestoreRow(A,i,&nz,&cwork,&vwork);CHKERRQ(ierr);
3332   }
3333   ierr = MatAssemblyBegin(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
3334   ierr = MatAssemblyEnd(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
3335   ierr = PetscObjectStateIncrease((PetscObject)B);CHKERRQ(ierr);
3336   PetscFunctionReturn(0);
3337 }
3338 
3339 #undef __FUNCT__
3340 #define __FUNCT__ "MatCopy"
3341 /*@
3342    MatCopy - Copys a matrix to another matrix.
3343 
3344    Collective on Mat
3345 
3346    Input Parameters:
3347 +  A - the matrix
3348 -  str - SAME_NONZERO_PATTERN or DIFFERENT_NONZERO_PATTERN
3349 
3350    Output Parameter:
3351 .  B - where the copy is put
3352 
3353    Notes:
3354    If you use SAME_NONZERO_PATTERN then the two matrices had better have the
3355    same nonzero pattern or the routine will crash.
3356 
3357    MatCopy() copies the matrix entries of a matrix to another existing
3358    matrix (after first zeroing the second matrix).  A related routine is
3359    MatConvert(), which first creates a new matrix and then copies the data.
3360 
3361    Level: intermediate
3362 
3363    Concepts: matrices^copying
3364 
3365 .seealso: MatConvert(), MatDuplicate()
3366 
3367 @*/
3368 PetscErrorCode PETSCMAT_DLLEXPORT MatCopy(Mat A,Mat B,MatStructure str)
3369 {
3370   PetscErrorCode ierr;
3371   PetscInt       i;
3372 
3373   PetscFunctionBegin;
3374   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
3375   PetscValidHeaderSpecific(B,MAT_CLASSID,2);
3376   PetscValidType(A,1);
3377   PetscValidType(B,2);
3378   PetscCheckSameComm(A,1,B,2);
3379   ierr = MatPreallocated(B);CHKERRQ(ierr);
3380   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3381   if (A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3382   if (A->rmap->N != B->rmap->N || A->cmap->N != B->cmap->N) SETERRQ4(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Mat A,Mat B: global dim (%D,%D) (%D,%D)",A->rmap->N,B->rmap->N,A->cmap->N,B->cmap->N);
3383   ierr = MatPreallocated(A);CHKERRQ(ierr);
3384 
3385   ierr = PetscLogEventBegin(MAT_Copy,A,B,0,0);CHKERRQ(ierr);
3386   if (A->ops->copy) {
3387     ierr = (*A->ops->copy)(A,B,str);CHKERRQ(ierr);
3388   } else { /* generic conversion */
3389     ierr = MatCopy_Basic(A,B,str);CHKERRQ(ierr);
3390   }
3391   if (A->mapping) {
3392     if (B->mapping) {ierr = ISLocalToGlobalMappingDestroy(B->mapping);CHKERRQ(ierr);B->mapping = 0;}
3393     ierr = MatSetLocalToGlobalMapping(B,A->mapping);CHKERRQ(ierr);
3394   }
3395   if (A->bmapping) {
3396     if (B->bmapping) {ierr = ISLocalToGlobalMappingDestroy(B->bmapping);CHKERRQ(ierr);B->bmapping = 0;}
3397     ierr = MatSetLocalToGlobalMappingBlock(B,A->mapping);CHKERRQ(ierr);
3398   }
3399 
3400   B->stencil.dim = A->stencil.dim;
3401   B->stencil.noc = A->stencil.noc;
3402   for (i=0; i<=A->stencil.dim; i++) {
3403     B->stencil.dims[i]   = A->stencil.dims[i];
3404     B->stencil.starts[i] = A->stencil.starts[i];
3405   }
3406 
3407   ierr = PetscLogEventEnd(MAT_Copy,A,B,0,0);CHKERRQ(ierr);
3408   ierr = PetscObjectStateIncrease((PetscObject)B);CHKERRQ(ierr);
3409   PetscFunctionReturn(0);
3410 }
3411 
3412 #undef __FUNCT__
3413 #define __FUNCT__ "MatConvert"
3414 /*@C
3415    MatConvert - Converts a matrix to another matrix, either of the same
3416    or different type.
3417 
3418    Collective on Mat
3419 
3420    Input Parameters:
3421 +  mat - the matrix
3422 .  newtype - new matrix type.  Use MATSAME to create a new matrix of the
3423    same type as the original matrix.
3424 -  reuse - denotes if the destination matrix is to be created or reused.  Currently
3425    MAT_REUSE_MATRIX is only supported for inplace conversion, otherwise use
3426    MAT_INITIAL_MATRIX.
3427 
3428    Output Parameter:
3429 .  M - pointer to place new matrix
3430 
3431    Notes:
3432    MatConvert() first creates a new matrix and then copies the data from
3433    the first matrix.  A related routine is MatCopy(), which copies the matrix
3434    entries of one matrix to another already existing matrix context.
3435 
3436    Cannot be used to convert a sequential matrix to parallel or parallel to sequential,
3437    the MPI communicator of the generated matrix is always the same as the communicator
3438    of the input matrix.
3439 
3440    Level: intermediate
3441 
3442    Concepts: matrices^converting between storage formats
3443 
3444 .seealso: MatCopy(), MatDuplicate()
3445 @*/
3446 PetscErrorCode PETSCMAT_DLLEXPORT MatConvert(Mat mat, const MatType newtype,MatReuse reuse,Mat *M)
3447 {
3448   PetscErrorCode         ierr;
3449   PetscTruth             sametype,issame,flg;
3450   char                   convname[256],mtype[256];
3451   Mat                    B;
3452 
3453   PetscFunctionBegin;
3454   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3455   PetscValidType(mat,1);
3456   PetscValidPointer(M,3);
3457   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3458   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3459   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3460 
3461   ierr = PetscOptionsGetString(((PetscObject)mat)->prefix,"-matconvert_type",mtype,256,&flg);CHKERRQ(ierr);
3462   if (flg) {
3463     newtype = mtype;
3464   }
3465   ierr = PetscTypeCompare((PetscObject)mat,newtype,&sametype);CHKERRQ(ierr);
3466   ierr = PetscStrcmp(newtype,"same",&issame);CHKERRQ(ierr);
3467   if ((reuse == MAT_REUSE_MATRIX) && (mat != *M)) {
3468     SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_SUP,"MAT_REUSE_MATRIX only supported for in-place conversion currently");
3469   }
3470 
3471   if ((reuse == MAT_REUSE_MATRIX) && (issame || sametype)) PetscFunctionReturn(0);
3472 
3473   if ((sametype || issame) && (reuse==MAT_INITIAL_MATRIX) && mat->ops->duplicate) {
3474     ierr = (*mat->ops->duplicate)(mat,MAT_COPY_VALUES,M);CHKERRQ(ierr);
3475   } else {
3476     PetscErrorCode (*conv)(Mat, const MatType,MatReuse,Mat*)=PETSC_NULL;
3477     const char     *prefix[3] = {"seq","mpi",""};
3478     PetscInt       i;
3479     /*
3480        Order of precedence:
3481        1) See if a specialized converter is known to the current matrix.
3482        2) See if a specialized converter is known to the desired matrix class.
3483        3) See if a good general converter is registered for the desired class
3484           (as of 6/27/03 only MATMPIADJ falls into this category).
3485        4) See if a good general converter is known for the current matrix.
3486        5) Use a really basic converter.
3487     */
3488 
3489     /* 1) See if a specialized converter is known to the current matrix and the desired class */
3490     for (i=0; i<3; i++) {
3491       ierr = PetscStrcpy(convname,"MatConvert_");CHKERRQ(ierr);
3492       ierr = PetscStrcat(convname,((PetscObject)mat)->type_name);CHKERRQ(ierr);
3493       ierr = PetscStrcat(convname,"_");CHKERRQ(ierr);
3494       ierr = PetscStrcat(convname,prefix[i]);CHKERRQ(ierr);
3495       ierr = PetscStrcat(convname,newtype);CHKERRQ(ierr);
3496       ierr = PetscStrcat(convname,"_C");CHKERRQ(ierr);
3497       ierr = PetscObjectQueryFunction((PetscObject)mat,convname,(void (**)(void))&conv);CHKERRQ(ierr);
3498       if (conv) goto foundconv;
3499     }
3500 
3501     /* 2)  See if a specialized converter is known to the desired matrix class. */
3502     ierr = MatCreate(((PetscObject)mat)->comm,&B);CHKERRQ(ierr);
3503     ierr = MatSetSizes(B,mat->rmap->n,mat->cmap->n,mat->rmap->N,mat->cmap->N);CHKERRQ(ierr);
3504     ierr = MatSetType(B,newtype);CHKERRQ(ierr);
3505     for (i=0; i<3; i++) {
3506       ierr = PetscStrcpy(convname,"MatConvert_");CHKERRQ(ierr);
3507       ierr = PetscStrcat(convname,((PetscObject)mat)->type_name);CHKERRQ(ierr);
3508       ierr = PetscStrcat(convname,"_");CHKERRQ(ierr);
3509       ierr = PetscStrcat(convname,prefix[i]);CHKERRQ(ierr);
3510       ierr = PetscStrcat(convname,newtype);CHKERRQ(ierr);
3511       ierr = PetscStrcat(convname,"_C");CHKERRQ(ierr);
3512       ierr = PetscObjectQueryFunction((PetscObject)B,convname,(void (**)(void))&conv);CHKERRQ(ierr);
3513       if (conv) {
3514         ierr = MatDestroy(B);CHKERRQ(ierr);
3515         goto foundconv;
3516       }
3517     }
3518 
3519     /* 3) See if a good general converter is registered for the desired class */
3520     conv = B->ops->convertfrom;
3521     ierr = MatDestroy(B);CHKERRQ(ierr);
3522     if (conv) goto foundconv;
3523 
3524     /* 4) See if a good general converter is known for the current matrix */
3525     if (mat->ops->convert) {
3526       conv = mat->ops->convert;
3527     }
3528     if (conv) goto foundconv;
3529 
3530     /* 5) Use a really basic converter. */
3531     conv = MatConvert_Basic;
3532 
3533     foundconv:
3534     ierr = PetscLogEventBegin(MAT_Convert,mat,0,0,0);CHKERRQ(ierr);
3535     ierr = (*conv)(mat,newtype,reuse,M);CHKERRQ(ierr);
3536     ierr = PetscLogEventEnd(MAT_Convert,mat,0,0,0);CHKERRQ(ierr);
3537   }
3538   ierr = PetscObjectStateIncrease((PetscObject)*M);CHKERRQ(ierr);
3539   PetscFunctionReturn(0);
3540 }
3541 
3542 #undef __FUNCT__
3543 #define __FUNCT__ "MatFactorGetSolverPackage"
3544 /*@C
3545    MatFactorGetSolverPackage - Returns name of the package providing the factorization routines
3546 
3547    Not Collective
3548 
3549    Input Parameter:
3550 .  mat - the matrix, must be a factored matrix
3551 
3552    Output Parameter:
3553 .   type - the string name of the package (do not free this string)
3554 
3555    Notes:
3556       In Fortran you pass in a empty string and the package name will be copied into it.
3557     (Make sure the string is long enough)
3558 
3559    Level: intermediate
3560 
3561 .seealso: MatCopy(), MatDuplicate(), MatGetFactorAvailable(), MatGetFactor()
3562 @*/
3563 PetscErrorCode PETSCMAT_DLLEXPORT MatFactorGetSolverPackage(Mat mat, const MatSolverPackage *type)
3564 {
3565   PetscErrorCode         ierr;
3566   PetscErrorCode         (*conv)(Mat,const MatSolverPackage*);
3567 
3568   PetscFunctionBegin;
3569   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3570   PetscValidType(mat,1);
3571   if (!mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Only for factored matrix");
3572   ierr = PetscObjectQueryFunction((PetscObject)mat,"MatFactorGetSolverPackage_C",(void (**)(void))&conv);CHKERRQ(ierr);
3573   if (!conv) {
3574     *type = MATSOLVERPETSC;
3575   } else {
3576     ierr = (*conv)(mat,type);CHKERRQ(ierr);
3577   }
3578   PetscFunctionReturn(0);
3579 }
3580 
3581 #undef __FUNCT__
3582 #define __FUNCT__ "MatGetFactor"
3583 /*@C
3584    MatGetFactor - Returns a matrix suitable to calls to MatXXFactorSymbolic()
3585 
3586    Collective on Mat
3587 
3588    Input Parameters:
3589 +  mat - the matrix
3590 .  type - name of solver type, for example, spooles, superlu, plapack, petsc (to use PETSc's default)
3591 -  ftype - factor type, MAT_FACTOR_LU, MAT_FACTOR_CHOLESKY, MAT_FACTOR_ICC, MAT_FACTOR_ILU,
3592 
3593    Output Parameters:
3594 .  f - the factor matrix used with MatXXFactorSymbolic() calls
3595 
3596    Notes:
3597       Some PETSc matrix formats have alternative solvers available that are contained in alternative packages
3598      such as pastix, superlu, mumps, spooles etc.
3599 
3600       PETSc must have been ./configure to use the external solver, using the option --download-package
3601 
3602    Level: intermediate
3603 
3604 .seealso: MatCopy(), MatDuplicate(), MatGetFactorAvailable()
3605 @*/
3606 PetscErrorCode PETSCMAT_DLLEXPORT MatGetFactor(Mat mat, const MatSolverPackage type,MatFactorType ftype,Mat *f)
3607 {
3608   PetscErrorCode  ierr,(*conv)(Mat,MatFactorType,Mat*);
3609   char            convname[256];
3610 
3611   PetscFunctionBegin;
3612   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3613   PetscValidType(mat,1);
3614 
3615   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3616   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3617 
3618   ierr = PetscStrcpy(convname,"MatGetFactor_");CHKERRQ(ierr);
3619   ierr = PetscStrcat(convname,type);CHKERRQ(ierr);
3620   ierr = PetscStrcat(convname,"_C");CHKERRQ(ierr);
3621   ierr = PetscObjectQueryFunction((PetscObject)mat,convname,(void (**)(void))&conv);CHKERRQ(ierr);
3622   if (!conv) {
3623     PetscTruth flag;
3624     MPI_Comm   comm;
3625 
3626     ierr = PetscObjectGetComm((PetscObject)mat,&comm);CHKERRQ(ierr);
3627     ierr = PetscStrcasecmp(MATSOLVERPETSC,type,&flag);CHKERRQ(ierr);
3628     if (flag) {
3629       SETERRQ2(comm,PETSC_ERR_SUP,"Matrix format %s does not have a built-in PETSc %s",((PetscObject)mat)->type_name,MatFactorTypes[ftype]);
3630     } else {
3631       SETERRQ4(comm,PETSC_ERR_SUP,"Matrix format %s does not have a solver package %s for %s. Perhaps you must ./configure with --download-%s",((PetscObject)mat)->type_name,type,MatFactorTypes[ftype],type);
3632     }
3633   }
3634   ierr = (*conv)(mat,ftype,f);CHKERRQ(ierr);
3635   PetscFunctionReturn(0);
3636 }
3637 
3638 #undef __FUNCT__
3639 #define __FUNCT__ "MatGetFactorAvailable"
3640 /*@C
3641    MatGetFactorAvailable - Returns a a flag if matrix supports particular package and factor type
3642 
3643    Collective on Mat
3644 
3645    Input Parameters:
3646 +  mat - the matrix
3647 .  type - name of solver type, for example, spooles, superlu, plapack, petsc (to use PETSc's default)
3648 -  ftype - factor type, MAT_FACTOR_LU, MAT_FACTOR_CHOLESKY, MAT_FACTOR_ICC, MAT_FACTOR_ILU,
3649 
3650    Output Parameter:
3651 .    flg - PETSC_TRUE if the factorization is available
3652 
3653    Notes:
3654       Some PETSc matrix formats have alternative solvers available that are contained in alternative packages
3655      such as pastix, superlu, mumps, spooles etc.
3656 
3657       PETSc must have been ./configure to use the external solver, using the option --download-package
3658 
3659    Level: intermediate
3660 
3661 .seealso: MatCopy(), MatDuplicate(), MatGetFactor()
3662 @*/
3663 PetscErrorCode PETSCMAT_DLLEXPORT MatGetFactorAvailable(Mat mat, const MatSolverPackage type,MatFactorType ftype,PetscTruth *flg)
3664 {
3665   PetscErrorCode         ierr;
3666   char                   convname[256];
3667   PetscErrorCode         (*conv)(Mat,MatFactorType,PetscTruth*);
3668 
3669   PetscFunctionBegin;
3670   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3671   PetscValidType(mat,1);
3672 
3673   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3674   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3675 
3676   ierr = PetscStrcpy(convname,"MatGetFactorAvailable_");CHKERRQ(ierr);
3677   ierr = PetscStrcat(convname,type);CHKERRQ(ierr);
3678   ierr = PetscStrcat(convname,"_C");CHKERRQ(ierr);
3679   ierr = PetscObjectQueryFunction((PetscObject)mat,convname,(void (**)(void))&conv);CHKERRQ(ierr);
3680   if (!conv) {
3681     *flg = PETSC_FALSE;
3682   } else {
3683     ierr = (*conv)(mat,ftype,flg);CHKERRQ(ierr);
3684   }
3685   PetscFunctionReturn(0);
3686 }
3687 
3688 
3689 #undef __FUNCT__
3690 #define __FUNCT__ "MatDuplicate"
3691 /*@
3692    MatDuplicate - Duplicates a matrix including the non-zero structure.
3693 
3694    Collective on Mat
3695 
3696    Input Parameters:
3697 +  mat - the matrix
3698 -  op - either MAT_DO_NOT_COPY_VALUES or MAT_COPY_VALUES, cause it to copy the numerical values in the matrix
3699         MAT_SHARE_NONZERO_PATTERN to share the nonzero patterns with the previous matrix and not copy them.
3700 
3701    Output Parameter:
3702 .  M - pointer to place new matrix
3703 
3704    Level: intermediate
3705 
3706    Concepts: matrices^duplicating
3707 
3708     Notes: You cannot change the nonzero pattern for the parent or child matrix if you use MAT_SHARE_NONZERO_PATTERN.
3709 
3710 .seealso: MatCopy(), MatConvert()
3711 @*/
3712 PetscErrorCode PETSCMAT_DLLEXPORT MatDuplicate(Mat mat,MatDuplicateOption op,Mat *M)
3713 {
3714   PetscErrorCode ierr;
3715   Mat            B;
3716   PetscInt       i;
3717 
3718   PetscFunctionBegin;
3719   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3720   PetscValidType(mat,1);
3721   PetscValidPointer(M,3);
3722   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3723   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
3724   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3725 
3726   *M  = 0;
3727   if (!mat->ops->duplicate) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Not written for this matrix type");
3728   ierr = PetscLogEventBegin(MAT_Convert,mat,0,0,0);CHKERRQ(ierr);
3729   ierr = (*mat->ops->duplicate)(mat,op,M);CHKERRQ(ierr);
3730   B = *M;
3731   if (mat->mapping) {
3732     ierr = MatSetLocalToGlobalMapping(B,mat->mapping);CHKERRQ(ierr);
3733   }
3734   if (mat->bmapping) {
3735     ierr = MatSetLocalToGlobalMappingBlock(B,mat->bmapping);CHKERRQ(ierr);
3736   }
3737   ierr = PetscLayoutCopy(mat->rmap,&B->rmap);CHKERRQ(ierr);
3738   ierr = PetscLayoutCopy(mat->cmap,&B->cmap);CHKERRQ(ierr);
3739 
3740   B->stencil.dim = mat->stencil.dim;
3741   B->stencil.noc = mat->stencil.noc;
3742   for (i=0; i<=mat->stencil.dim; i++) {
3743     B->stencil.dims[i]   = mat->stencil.dims[i];
3744     B->stencil.starts[i] = mat->stencil.starts[i];
3745   }
3746 
3747   ierr = PetscLogEventEnd(MAT_Convert,mat,0,0,0);CHKERRQ(ierr);
3748   ierr = PetscObjectStateIncrease((PetscObject)B);CHKERRQ(ierr);
3749   PetscFunctionReturn(0);
3750 }
3751 
3752 #undef __FUNCT__
3753 #define __FUNCT__ "MatGetDiagonal"
3754 /*@
3755    MatGetDiagonal - Gets the diagonal of a matrix.
3756 
3757    Collective on Mat and Vec
3758 
3759    Input Parameters:
3760 +  mat - the matrix
3761 -  v - the vector for storing the diagonal
3762 
3763    Output Parameter:
3764 .  v - the diagonal of the matrix
3765 
3766    Level: intermediate
3767 
3768    Concepts: matrices^accessing diagonals
3769 
3770 .seealso: MatGetRow(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMaxAbs()
3771 @*/
3772 PetscErrorCode PETSCMAT_DLLEXPORT MatGetDiagonal(Mat mat,Vec v)
3773 {
3774   PetscErrorCode ierr;
3775 
3776   PetscFunctionBegin;
3777   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3778   PetscValidType(mat,1);
3779   PetscValidHeaderSpecific(v,VEC_CLASSID,2);
3780   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3781   if (!mat->ops->getdiagonal) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
3782   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3783 
3784   ierr = (*mat->ops->getdiagonal)(mat,v);CHKERRQ(ierr);
3785   ierr = PetscObjectStateIncrease((PetscObject)v);CHKERRQ(ierr);
3786   PetscFunctionReturn(0);
3787 }
3788 
3789 #undef __FUNCT__
3790 #define __FUNCT__ "MatGetRowMin"
3791 /*@
3792    MatGetRowMin - Gets the minimum value (of the real part) of each
3793         row of the matrix
3794 
3795    Collective on Mat and Vec
3796 
3797    Input Parameters:
3798 .  mat - the matrix
3799 
3800    Output Parameter:
3801 +  v - the vector for storing the maximums
3802 -  idx - the indices of the column found for each row (optional)
3803 
3804    Level: intermediate
3805 
3806    Notes: The result of this call are the same as if one converted the matrix to dense format
3807       and found the minimum value in each row (i.e. the implicit zeros are counted as zeros).
3808 
3809     This code is only implemented for a couple of matrix formats.
3810 
3811    Concepts: matrices^getting row maximums
3812 
3813 .seealso: MatGetDiagonal(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMaxAbs(),
3814           MatGetRowMax()
3815 @*/
3816 PetscErrorCode PETSCMAT_DLLEXPORT MatGetRowMin(Mat mat,Vec v,PetscInt idx[])
3817 {
3818   PetscErrorCode ierr;
3819 
3820   PetscFunctionBegin;
3821   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3822   PetscValidType(mat,1);
3823   PetscValidHeaderSpecific(v,VEC_CLASSID,2);
3824   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3825   if (!mat->ops->getrowmax) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
3826   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3827 
3828   ierr = (*mat->ops->getrowmin)(mat,v,idx);CHKERRQ(ierr);
3829   ierr = PetscObjectStateIncrease((PetscObject)v);CHKERRQ(ierr);
3830   PetscFunctionReturn(0);
3831 }
3832 
3833 #undef __FUNCT__
3834 #define __FUNCT__ "MatGetRowMinAbs"
3835 /*@
3836    MatGetRowMinAbs - Gets the minimum value (in absolute value) of each
3837         row of the matrix
3838 
3839    Collective on Mat and Vec
3840 
3841    Input Parameters:
3842 .  mat - the matrix
3843 
3844    Output Parameter:
3845 +  v - the vector for storing the minimums
3846 -  idx - the indices of the column found for each row (optional)
3847 
3848    Level: intermediate
3849 
3850    Notes: if a row is completely empty or has only 0.0 values then the idx[] value for that
3851     row is 0 (the first column).
3852 
3853     This code is only implemented for a couple of matrix formats.
3854 
3855    Concepts: matrices^getting row maximums
3856 
3857 .seealso: MatGetDiagonal(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMax(), MatGetRowMaxAbs(), MatGetRowMin()
3858 @*/
3859 PetscErrorCode PETSCMAT_DLLEXPORT MatGetRowMinAbs(Mat mat,Vec v,PetscInt idx[])
3860 {
3861   PetscErrorCode ierr;
3862 
3863   PetscFunctionBegin;
3864   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3865   PetscValidType(mat,1);
3866   PetscValidHeaderSpecific(v,VEC_CLASSID,2);
3867   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3868   if (!mat->ops->getrowminabs) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
3869   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3870   if (idx) {ierr = PetscMemzero(idx,mat->rmap->n*sizeof(PetscInt));CHKERRQ(ierr);}
3871 
3872   ierr = (*mat->ops->getrowminabs)(mat,v,idx);CHKERRQ(ierr);
3873   ierr = PetscObjectStateIncrease((PetscObject)v);CHKERRQ(ierr);
3874   PetscFunctionReturn(0);
3875 }
3876 
3877 #undef __FUNCT__
3878 #define __FUNCT__ "MatGetRowMax"
3879 /*@
3880    MatGetRowMax - Gets the maximum value (of the real part) of each
3881         row of the matrix
3882 
3883    Collective on Mat and Vec
3884 
3885    Input Parameters:
3886 .  mat - the matrix
3887 
3888    Output Parameter:
3889 +  v - the vector for storing the maximums
3890 -  idx - the indices of the column found for each row (optional)
3891 
3892    Level: intermediate
3893 
3894    Notes: The result of this call are the same as if one converted the matrix to dense format
3895       and found the minimum value in each row (i.e. the implicit zeros are counted as zeros).
3896 
3897     This code is only implemented for a couple of matrix formats.
3898 
3899    Concepts: matrices^getting row maximums
3900 
3901 .seealso: MatGetDiagonal(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMaxAbs(), MatGetRowMin()
3902 @*/
3903 PetscErrorCode PETSCMAT_DLLEXPORT MatGetRowMax(Mat mat,Vec v,PetscInt idx[])
3904 {
3905   PetscErrorCode ierr;
3906 
3907   PetscFunctionBegin;
3908   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3909   PetscValidType(mat,1);
3910   PetscValidHeaderSpecific(v,VEC_CLASSID,2);
3911   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3912   if (!mat->ops->getrowmax) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
3913   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3914 
3915   ierr = (*mat->ops->getrowmax)(mat,v,idx);CHKERRQ(ierr);
3916   ierr = PetscObjectStateIncrease((PetscObject)v);CHKERRQ(ierr);
3917   PetscFunctionReturn(0);
3918 }
3919 
3920 #undef __FUNCT__
3921 #define __FUNCT__ "MatGetRowMaxAbs"
3922 /*@
3923    MatGetRowMaxAbs - Gets the maximum value (in absolute value) of each
3924         row of the matrix
3925 
3926    Collective on Mat and Vec
3927 
3928    Input Parameters:
3929 .  mat - the matrix
3930 
3931    Output Parameter:
3932 +  v - the vector for storing the maximums
3933 -  idx - the indices of the column found for each row (optional)
3934 
3935    Level: intermediate
3936 
3937    Notes: if a row is completely empty or has only 0.0 values then the idx[] value for that
3938     row is 0 (the first column).
3939 
3940     This code is only implemented for a couple of matrix formats.
3941 
3942    Concepts: matrices^getting row maximums
3943 
3944 .seealso: MatGetDiagonal(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMax(), MatGetRowMin()
3945 @*/
3946 PetscErrorCode PETSCMAT_DLLEXPORT MatGetRowMaxAbs(Mat mat,Vec v,PetscInt idx[])
3947 {
3948   PetscErrorCode ierr;
3949 
3950   PetscFunctionBegin;
3951   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3952   PetscValidType(mat,1);
3953   PetscValidHeaderSpecific(v,VEC_CLASSID,2);
3954   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3955   if (!mat->ops->getrowmaxabs) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
3956   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3957   if (idx) {ierr = PetscMemzero(idx,mat->rmap->n*sizeof(PetscInt));CHKERRQ(ierr);}
3958 
3959   ierr = (*mat->ops->getrowmaxabs)(mat,v,idx);CHKERRQ(ierr);
3960   ierr = PetscObjectStateIncrease((PetscObject)v);CHKERRQ(ierr);
3961   PetscFunctionReturn(0);
3962 }
3963 
3964 #undef __FUNCT__
3965 #define __FUNCT__ "MatGetRowSum"
3966 /*@
3967    MatGetRowSum - Gets the sum of each row of the matrix
3968 
3969    Collective on Mat and Vec
3970 
3971    Input Parameters:
3972 .  mat - the matrix
3973 
3974    Output Parameter:
3975 .  v - the vector for storing the sum of rows
3976 
3977    Level: intermediate
3978 
3979    Notes: This code is slow since it is not currently specialized for different formats
3980 
3981    Concepts: matrices^getting row sums
3982 
3983 .seealso: MatGetDiagonal(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMax(), MatGetRowMin()
3984 @*/
3985 PetscErrorCode PETSCMAT_DLLEXPORT MatGetRowSum(Mat mat, Vec v)
3986 {
3987   PetscInt       start = 0, end = 0, row;
3988   PetscScalar   *array;
3989   PetscErrorCode ierr;
3990 
3991   PetscFunctionBegin;
3992   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
3993   PetscValidType(mat,1);
3994   PetscValidHeaderSpecific(v,VEC_CLASSID,2);
3995   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
3996   ierr = MatPreallocated(mat);CHKERRQ(ierr);
3997   ierr = MatGetOwnershipRange(mat, &start, &end);CHKERRQ(ierr);
3998   ierr = VecGetArray(v, &array);CHKERRQ(ierr);
3999   for(row = start; row < end; ++row) {
4000     PetscInt           ncols, col;
4001     const PetscInt    *cols;
4002     const PetscScalar *vals;
4003 
4004     array[row - start] = 0.0;
4005     ierr = MatGetRow(mat, row, &ncols, &cols, &vals);CHKERRQ(ierr);
4006     for(col = 0; col < ncols; col++) {
4007       array[row - start] += vals[col];
4008     }
4009     ierr = MatRestoreRow(mat, row, &ncols, &cols, &vals);CHKERRQ(ierr);
4010   }
4011   ierr = VecRestoreArray(v, &array);CHKERRQ(ierr);
4012   ierr = PetscObjectStateIncrease((PetscObject) v);CHKERRQ(ierr);
4013   PetscFunctionReturn(0);
4014 }
4015 
4016 #undef __FUNCT__
4017 #define __FUNCT__ "MatTranspose"
4018 /*@
4019    MatTranspose - Computes an in-place or out-of-place transpose of a matrix.
4020 
4021    Collective on Mat
4022 
4023    Input Parameter:
4024 +  mat - the matrix to transpose
4025 -  reuse - store the transpose matrix in the provided B
4026 
4027    Output Parameters:
4028 .  B - the transpose
4029 
4030    Notes:
4031      If you  pass in &mat for B the transpose will be done in place
4032 
4033    Level: intermediate
4034 
4035    Concepts: matrices^transposing
4036 
4037 .seealso: MatMultTranspose(), MatMultTransposeAdd(), MatIsTranspose(), MatReuse
4038 @*/
4039 PetscErrorCode PETSCMAT_DLLEXPORT MatTranspose(Mat mat,MatReuse reuse,Mat *B)
4040 {
4041   PetscErrorCode ierr;
4042 
4043   PetscFunctionBegin;
4044   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4045   PetscValidType(mat,1);
4046   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4047   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4048   if (!mat->ops->transpose) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
4049   ierr = MatPreallocated(mat);CHKERRQ(ierr);
4050 
4051   ierr = PetscLogEventBegin(MAT_Transpose,mat,0,0,0);CHKERRQ(ierr);
4052   ierr = (*mat->ops->transpose)(mat,reuse,B);CHKERRQ(ierr);
4053   ierr = PetscLogEventEnd(MAT_Transpose,mat,0,0,0);CHKERRQ(ierr);
4054   if (B) {ierr = PetscObjectStateIncrease((PetscObject)*B);CHKERRQ(ierr);}
4055   PetscFunctionReturn(0);
4056 }
4057 
4058 #undef __FUNCT__
4059 #define __FUNCT__ "MatIsTranspose"
4060 /*@
4061    MatIsTranspose - Test whether a matrix is another one's transpose,
4062         or its own, in which case it tests symmetry.
4063 
4064    Collective on Mat
4065 
4066    Input Parameter:
4067 +  A - the matrix to test
4068 -  B - the matrix to test against, this can equal the first parameter
4069 
4070    Output Parameters:
4071 .  flg - the result
4072 
4073    Notes:
4074    Only available for SeqAIJ/MPIAIJ matrices. The sequential algorithm
4075    has a running time of the order of the number of nonzeros; the parallel
4076    test involves parallel copies of the block-offdiagonal parts of the matrix.
4077 
4078    Level: intermediate
4079 
4080    Concepts: matrices^transposing, matrix^symmetry
4081 
4082 .seealso: MatTranspose(), MatIsSymmetric(), MatIsHermitian()
4083 @*/
4084 PetscErrorCode PETSCMAT_DLLEXPORT MatIsTranspose(Mat A,Mat B,PetscReal tol,PetscTruth *flg)
4085 {
4086   PetscErrorCode ierr,(*f)(Mat,Mat,PetscReal,PetscTruth*),(*g)(Mat,Mat,PetscReal,PetscTruth*);
4087 
4088   PetscFunctionBegin;
4089   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
4090   PetscValidHeaderSpecific(B,MAT_CLASSID,2);
4091   PetscValidPointer(flg,3);
4092   ierr = PetscObjectQueryFunction((PetscObject)A,"MatIsTranspose_C",(void (**)(void))&f);CHKERRQ(ierr);
4093   ierr = PetscObjectQueryFunction((PetscObject)B,"MatIsTranspose_C",(void (**)(void))&g);CHKERRQ(ierr);
4094   if (f && g) {
4095     if (f==g) {
4096       ierr = (*f)(A,B,tol,flg);CHKERRQ(ierr);
4097     } else {
4098       SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_NOTSAMETYPE,"Matrices do not have the same comparator for symmetry test");
4099     }
4100   }
4101   PetscFunctionReturn(0);
4102 }
4103 
4104 #undef __FUNCT__
4105 #define __FUNCT__ "MatHermitianTranspose"
4106 /*@
4107    MatHermitianTranspose - Computes an in-place or out-of-place transpose of a matrix in complex conjugate.
4108 
4109    Collective on Mat
4110 
4111    Input Parameter:
4112 +  mat - the matrix to transpose and complex conjugate
4113 -  reuse - store the transpose matrix in the provided B
4114 
4115    Output Parameters:
4116 .  B - the Hermitian
4117 
4118    Notes:
4119      If you  pass in &mat for B the Hermitian will be done in place
4120 
4121    Level: intermediate
4122 
4123    Concepts: matrices^transposing, complex conjugatex
4124 
4125 .seealso: MatTranspose(), MatMultTranspose(), MatMultTransposeAdd(), MatIsTranspose(), MatReuse
4126 @*/
4127 PetscErrorCode PETSCMAT_DLLEXPORT MatHermitianTranspose(Mat mat,MatReuse reuse,Mat *B)
4128 {
4129   PetscErrorCode ierr;
4130 
4131   PetscFunctionBegin;
4132   ierr = MatTranspose(mat,reuse,B);CHKERRQ(ierr);
4133 #if defined(PETSC_USE_COMPLEX)
4134   ierr = MatConjugate(*B);CHKERRQ(ierr);
4135 #endif
4136   PetscFunctionReturn(0);
4137 }
4138 
4139 #undef __FUNCT__
4140 #define __FUNCT__ "MatIsHermitianTranspose"
4141 /*@
4142    MatIsHermitianTranspose - Test whether a matrix is another one's Hermitian transpose,
4143 
4144    Collective on Mat
4145 
4146    Input Parameter:
4147 +  A - the matrix to test
4148 -  B - the matrix to test against, this can equal the first parameter
4149 
4150    Output Parameters:
4151 .  flg - the result
4152 
4153    Notes:
4154    Only available for SeqAIJ/MPIAIJ matrices. The sequential algorithm
4155    has a running time of the order of the number of nonzeros; the parallel
4156    test involves parallel copies of the block-offdiagonal parts of the matrix.
4157 
4158    Level: intermediate
4159 
4160    Concepts: matrices^transposing, matrix^symmetry
4161 
4162 .seealso: MatTranspose(), MatIsSymmetric(), MatIsHermitian(), MatIsTranspose()
4163 @*/
4164 PetscErrorCode PETSCMAT_DLLEXPORT MatIsHermitianTranspose(Mat A,Mat B,PetscReal tol,PetscTruth *flg)
4165 {
4166   PetscErrorCode ierr,(*f)(Mat,Mat,PetscReal,PetscTruth*),(*g)(Mat,Mat,PetscReal,PetscTruth*);
4167 
4168   PetscFunctionBegin;
4169   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
4170   PetscValidHeaderSpecific(B,MAT_CLASSID,2);
4171   PetscValidPointer(flg,3);
4172   ierr = PetscObjectQueryFunction((PetscObject)A,"MatIsHermitianTranspose_C",(void (**)(void))&f);CHKERRQ(ierr);
4173   ierr = PetscObjectQueryFunction((PetscObject)B,"MatIsHermitianTranspose_C",(void (**)(void))&g);CHKERRQ(ierr);
4174   if (f && g) {
4175     if (f==g) {
4176       ierr = (*f)(A,B,tol,flg);CHKERRQ(ierr);
4177     } else {
4178       SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_NOTSAMETYPE,"Matrices do not have the same comparator for Hermitian test");
4179     }
4180   }
4181   PetscFunctionReturn(0);
4182 }
4183 
4184 #undef __FUNCT__
4185 #define __FUNCT__ "MatPermute"
4186 /*@
4187    MatPermute - Creates a new matrix with rows and columns permuted from the
4188    original.
4189 
4190    Collective on Mat
4191 
4192    Input Parameters:
4193 +  mat - the matrix to permute
4194 .  row - row permutation, each processor supplies only the permutation for its rows
4195 -  col - column permutation, each processor needs the entire column permutation, that is
4196          this is the same size as the total number of columns in the matrix. It can often
4197          be obtained with ISAllGather() on the row permutation
4198 
4199    Output Parameters:
4200 .  B - the permuted matrix
4201 
4202    Level: advanced
4203 
4204    Concepts: matrices^permuting
4205 
4206 .seealso: MatGetOrdering(), ISAllGather()
4207 
4208 @*/
4209 PetscErrorCode PETSCMAT_DLLEXPORT MatPermute(Mat mat,IS row,IS col,Mat *B)
4210 {
4211   PetscErrorCode ierr;
4212 
4213   PetscFunctionBegin;
4214   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4215   PetscValidType(mat,1);
4216   PetscValidHeaderSpecific(row,IS_CLASSID,2);
4217   PetscValidHeaderSpecific(col,IS_CLASSID,3);
4218   PetscValidPointer(B,4);
4219   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4220   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4221   if (!mat->ops->permute) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"MatPermute not available for Mat type %s",((PetscObject)mat)->type_name);
4222   ierr = MatPreallocated(mat);CHKERRQ(ierr);
4223 
4224   ierr = (*mat->ops->permute)(mat,row,col,B);CHKERRQ(ierr);
4225   ierr = PetscObjectStateIncrease((PetscObject)*B);CHKERRQ(ierr);
4226   PetscFunctionReturn(0);
4227 }
4228 
4229 #undef __FUNCT__
4230 #define __FUNCT__ "MatPermuteSparsify"
4231 /*@
4232   MatPermuteSparsify - Creates a new matrix with rows and columns permuted from the
4233   original and sparsified to the prescribed tolerance.
4234 
4235   Collective on Mat
4236 
4237   Input Parameters:
4238 + A    - The matrix to permute
4239 . band - The half-bandwidth of the sparsified matrix, or PETSC_DECIDE
4240 . frac - The half-bandwidth as a fraction of the total size, or 0.0
4241 . tol  - The drop tolerance
4242 . rowp - The row permutation
4243 - colp - The column permutation
4244 
4245   Output Parameter:
4246 . B    - The permuted, sparsified matrix
4247 
4248   Level: advanced
4249 
4250   Note:
4251   The default behavior (band = PETSC_DECIDE and frac = 0.0) is to
4252   restrict the half-bandwidth of the resulting matrix to 5% of the
4253   total matrix size.
4254 
4255 .keywords: matrix, permute, sparsify
4256 
4257 .seealso: MatGetOrdering(), MatPermute()
4258 @*/
4259 PetscErrorCode PETSCMAT_DLLEXPORT MatPermuteSparsify(Mat A, PetscInt band, PetscReal frac, PetscReal tol, IS rowp, IS colp, Mat *B)
4260 {
4261   IS                irowp, icolp;
4262   const PetscInt    *rows, *cols;
4263   PetscInt          M, N, locRowStart = 0, locRowEnd = 0;
4264   PetscInt          nz, newNz;
4265   const PetscInt    *cwork;
4266   PetscInt          *cnew;
4267   const PetscScalar *vwork;
4268   PetscScalar       *vnew;
4269   PetscInt          bw, issize;
4270   PetscInt          row, locRow, newRow, col, newCol;
4271   PetscErrorCode    ierr;
4272 
4273   PetscFunctionBegin;
4274   PetscValidHeaderSpecific(A,    MAT_CLASSID,1);
4275   PetscValidHeaderSpecific(rowp, IS_CLASSID,5);
4276   PetscValidHeaderSpecific(colp, IS_CLASSID,6);
4277   PetscValidPointer(B,7);
4278   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE, "Not for unassembled matrix");
4279   if (A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE, "Not for factored matrix");
4280   if (!A->ops->permutesparsify) {
4281     ierr = MatGetSize(A, &M, &N);CHKERRQ(ierr);
4282     ierr = MatGetOwnershipRange(A, &locRowStart, &locRowEnd);CHKERRQ(ierr);
4283     ierr = ISGetSize(rowp, &issize);CHKERRQ(ierr);
4284     if (issize != M) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG, "Wrong size %D for row permutation, should be %D", issize, M);
4285     ierr = ISGetSize(colp, &issize);CHKERRQ(ierr);
4286     if (issize != N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG, "Wrong size %D for column permutation, should be %D", issize, N);
4287     ierr = ISInvertPermutation(rowp, 0, &irowp);CHKERRQ(ierr);
4288     ierr = ISGetIndices(irowp, &rows);CHKERRQ(ierr);
4289     ierr = ISInvertPermutation(colp, 0, &icolp);CHKERRQ(ierr);
4290     ierr = ISGetIndices(icolp, &cols);CHKERRQ(ierr);
4291     ierr = PetscMalloc(N*sizeof(PetscInt),&cnew);CHKERRQ(ierr);
4292     ierr = PetscMalloc(N*sizeof(PetscScalar),&vnew);CHKERRQ(ierr);
4293 
4294     /* Setup bandwidth to include */
4295     if (band == PETSC_DECIDE) {
4296       if (frac <= 0.0)
4297         bw = (PetscInt) (M * 0.05);
4298       else
4299         bw = (PetscInt) (M * frac);
4300     } else {
4301       if (band <= 0) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG, "Bandwidth must be a positive integer");
4302       bw = band;
4303     }
4304 
4305     /* Put values into new matrix */
4306     ierr = MatDuplicate(A, MAT_DO_NOT_COPY_VALUES, B);CHKERRQ(ierr);
4307     for(row = locRowStart, locRow = 0; row < locRowEnd; row++, locRow++) {
4308       ierr = MatGetRow(A, row, &nz, &cwork, &vwork);CHKERRQ(ierr);
4309       newRow   = rows[locRow]+locRowStart;
4310       for(col = 0, newNz = 0; col < nz; col++) {
4311         newCol = cols[cwork[col]];
4312         if ((newCol >= newRow - bw) && (newCol < newRow + bw) && (PetscAbsScalar(vwork[col]) >= tol)) {
4313           cnew[newNz] = newCol;
4314           vnew[newNz] = vwork[col];
4315           newNz++;
4316         }
4317       }
4318       ierr = MatSetValues(*B, 1, &newRow, newNz, cnew, vnew, INSERT_VALUES);CHKERRQ(ierr);
4319       ierr = MatRestoreRow(A, row, &nz, &cwork, &vwork);CHKERRQ(ierr);
4320     }
4321     ierr = PetscFree(cnew);CHKERRQ(ierr);
4322     ierr = PetscFree(vnew);CHKERRQ(ierr);
4323     ierr = MatAssemblyBegin(*B, MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
4324     ierr = MatAssemblyEnd(*B, MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
4325     ierr = ISRestoreIndices(irowp, &rows);CHKERRQ(ierr);
4326     ierr = ISRestoreIndices(icolp, &cols);CHKERRQ(ierr);
4327     ierr = ISDestroy(irowp);CHKERRQ(ierr);
4328     ierr = ISDestroy(icolp);CHKERRQ(ierr);
4329   } else {
4330     ierr = (*A->ops->permutesparsify)(A, band, frac, tol, rowp, colp, B);CHKERRQ(ierr);
4331   }
4332   ierr = PetscObjectStateIncrease((PetscObject)*B);CHKERRQ(ierr);
4333   PetscFunctionReturn(0);
4334 }
4335 
4336 #undef __FUNCT__
4337 #define __FUNCT__ "MatEqual"
4338 /*@
4339    MatEqual - Compares two matrices.
4340 
4341    Collective on Mat
4342 
4343    Input Parameters:
4344 +  A - the first matrix
4345 -  B - the second matrix
4346 
4347    Output Parameter:
4348 .  flg - PETSC_TRUE if the matrices are equal; PETSC_FALSE otherwise.
4349 
4350    Level: intermediate
4351 
4352    Concepts: matrices^equality between
4353 @*/
4354 PetscErrorCode PETSCMAT_DLLEXPORT MatEqual(Mat A,Mat B,PetscTruth *flg)
4355 {
4356   PetscErrorCode ierr;
4357 
4358   PetscFunctionBegin;
4359   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
4360   PetscValidHeaderSpecific(B,MAT_CLASSID,2);
4361   PetscValidType(A,1);
4362   PetscValidType(B,2);
4363   PetscValidIntPointer(flg,3);
4364   PetscCheckSameComm(A,1,B,2);
4365   ierr = MatPreallocated(B);CHKERRQ(ierr);
4366   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4367   if (!B->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4368   if (A->rmap->N != B->rmap->N || A->cmap->N != B->cmap->N) SETERRQ4(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Mat A,Mat B: global dim %D %D %D %D",A->rmap->N,B->rmap->N,A->cmap->N,B->cmap->N);
4369   if (!A->ops->equal) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)A)->type_name);
4370   if (!B->ops->equal) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)B)->type_name);
4371   if (A->ops->equal != B->ops->equal) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_INCOMP,"A is type: %s\nB is type: %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name);
4372   ierr = MatPreallocated(A);CHKERRQ(ierr);
4373 
4374   ierr = (*A->ops->equal)(A,B,flg);CHKERRQ(ierr);
4375   PetscFunctionReturn(0);
4376 }
4377 
4378 #undef __FUNCT__
4379 #define __FUNCT__ "MatDiagonalScale"
4380 /*@
4381    MatDiagonalScale - Scales a matrix on the left and right by diagonal
4382    matrices that are stored as vectors.  Either of the two scaling
4383    matrices can be PETSC_NULL.
4384 
4385    Collective on Mat
4386 
4387    Input Parameters:
4388 +  mat - the matrix to be scaled
4389 .  l - the left scaling vector (or PETSC_NULL)
4390 -  r - the right scaling vector (or PETSC_NULL)
4391 
4392    Notes:
4393    MatDiagonalScale() computes A = LAR, where
4394    L = a diagonal matrix (stored as a vector), R = a diagonal matrix (stored as a vector)
4395    The L scales the rows of the matrix, the R scales the columns of the matrix.
4396 
4397    Level: intermediate
4398 
4399    Concepts: matrices^diagonal scaling
4400    Concepts: diagonal scaling of matrices
4401 
4402 .seealso: MatScale()
4403 @*/
4404 PetscErrorCode PETSCMAT_DLLEXPORT MatDiagonalScale(Mat mat,Vec l,Vec r)
4405 {
4406   PetscErrorCode ierr;
4407 
4408   PetscFunctionBegin;
4409   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4410   PetscValidType(mat,1);
4411   if (!mat->ops->diagonalscale) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
4412   if (l) {PetscValidHeaderSpecific(l,VEC_CLASSID,2);PetscCheckSameComm(mat,1,l,2);}
4413   if (r) {PetscValidHeaderSpecific(r,VEC_CLASSID,3);PetscCheckSameComm(mat,1,r,3);}
4414   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4415   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4416   ierr = MatPreallocated(mat);CHKERRQ(ierr);
4417 
4418   ierr = PetscLogEventBegin(MAT_Scale,mat,0,0,0);CHKERRQ(ierr);
4419   ierr = (*mat->ops->diagonalscale)(mat,l,r);CHKERRQ(ierr);
4420   ierr = PetscLogEventEnd(MAT_Scale,mat,0,0,0);CHKERRQ(ierr);
4421   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
4422   PetscFunctionReturn(0);
4423 }
4424 
4425 #undef __FUNCT__
4426 #define __FUNCT__ "MatScale"
4427 /*@
4428     MatScale - Scales all elements of a matrix by a given number.
4429 
4430     Collective on Mat
4431 
4432     Input Parameters:
4433 +   mat - the matrix to be scaled
4434 -   a  - the scaling value
4435 
4436     Output Parameter:
4437 .   mat - the scaled matrix
4438 
4439     Level: intermediate
4440 
4441     Concepts: matrices^scaling all entries
4442 
4443 .seealso: MatDiagonalScale()
4444 @*/
4445 PetscErrorCode PETSCMAT_DLLEXPORT MatScale(Mat mat,PetscScalar a)
4446 {
4447   PetscErrorCode ierr;
4448 
4449   PetscFunctionBegin;
4450   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4451   PetscValidType(mat,1);
4452   if (a != 1.0 && !mat->ops->scale) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
4453   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4454   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4455   ierr = MatPreallocated(mat);CHKERRQ(ierr);
4456 
4457   ierr = PetscLogEventBegin(MAT_Scale,mat,0,0,0);CHKERRQ(ierr);
4458   if (a != 1.0) {
4459     ierr = (*mat->ops->scale)(mat,a);CHKERRQ(ierr);
4460     ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
4461   }
4462   ierr = PetscLogEventEnd(MAT_Scale,mat,0,0,0);CHKERRQ(ierr);
4463   PetscFunctionReturn(0);
4464 }
4465 
4466 #undef __FUNCT__
4467 #define __FUNCT__ "MatNorm"
4468 /*@
4469    MatNorm - Calculates various norms of a matrix.
4470 
4471    Collective on Mat
4472 
4473    Input Parameters:
4474 +  mat - the matrix
4475 -  type - the type of norm, NORM_1, NORM_FROBENIUS, NORM_INFINITY
4476 
4477    Output Parameters:
4478 .  nrm - the resulting norm
4479 
4480    Level: intermediate
4481 
4482    Concepts: matrices^norm
4483    Concepts: norm^of matrix
4484 @*/
4485 PetscErrorCode PETSCMAT_DLLEXPORT MatNorm(Mat mat,NormType type,PetscReal *nrm)
4486 {
4487   PetscErrorCode ierr;
4488 
4489   PetscFunctionBegin;
4490   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4491   PetscValidType(mat,1);
4492   PetscValidScalarPointer(nrm,3);
4493 
4494   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4495   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4496   if (!mat->ops->norm) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
4497   ierr = MatPreallocated(mat);CHKERRQ(ierr);
4498 
4499   ierr = (*mat->ops->norm)(mat,type,nrm);CHKERRQ(ierr);
4500   PetscFunctionReturn(0);
4501 }
4502 
4503 /*
4504      This variable is used to prevent counting of MatAssemblyBegin() that
4505    are called from within a MatAssemblyEnd().
4506 */
4507 static PetscInt MatAssemblyEnd_InUse = 0;
4508 #undef __FUNCT__
4509 #define __FUNCT__ "MatAssemblyBegin"
4510 /*@
4511    MatAssemblyBegin - Begins assembling the matrix.  This routine should
4512    be called after completing all calls to MatSetValues().
4513 
4514    Collective on Mat
4515 
4516    Input Parameters:
4517 +  mat - the matrix
4518 -  type - type of assembly, either MAT_FLUSH_ASSEMBLY or MAT_FINAL_ASSEMBLY
4519 
4520    Notes:
4521    MatSetValues() generally caches the values.  The matrix is ready to
4522    use only after MatAssemblyBegin() and MatAssemblyEnd() have been called.
4523    Use MAT_FLUSH_ASSEMBLY when switching between ADD_VALUES and INSERT_VALUES
4524    in MatSetValues(); use MAT_FINAL_ASSEMBLY for the final assembly before
4525    using the matrix.
4526 
4527    Level: beginner
4528 
4529    Concepts: matrices^assembling
4530 
4531 .seealso: MatAssemblyEnd(), MatSetValues(), MatAssembled()
4532 @*/
4533 PetscErrorCode PETSCMAT_DLLEXPORT MatAssemblyBegin(Mat mat,MatAssemblyType type)
4534 {
4535   PetscErrorCode ierr;
4536 
4537   PetscFunctionBegin;
4538   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4539   PetscValidType(mat,1);
4540   ierr = MatPreallocated(mat);CHKERRQ(ierr);
4541   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix.\nDid you forget to call MatSetUnfactored()?");
4542   if (mat->assembled) {
4543     mat->was_assembled = PETSC_TRUE;
4544     mat->assembled     = PETSC_FALSE;
4545   }
4546   if (!MatAssemblyEnd_InUse) {
4547     ierr = PetscLogEventBegin(MAT_AssemblyBegin,mat,0,0,0);CHKERRQ(ierr);
4548     if (mat->ops->assemblybegin){ierr = (*mat->ops->assemblybegin)(mat,type);CHKERRQ(ierr);}
4549     ierr = PetscLogEventEnd(MAT_AssemblyBegin,mat,0,0,0);CHKERRQ(ierr);
4550   } else {
4551     if (mat->ops->assemblybegin){ierr = (*mat->ops->assemblybegin)(mat,type);CHKERRQ(ierr);}
4552   }
4553   PetscFunctionReturn(0);
4554 }
4555 
4556 #undef __FUNCT__
4557 #define __FUNCT__ "MatAssembled"
4558 /*@
4559    MatAssembled - Indicates if a matrix has been assembled and is ready for
4560      use; for example, in matrix-vector product.
4561 
4562    Collective on Mat
4563 
4564    Input Parameter:
4565 .  mat - the matrix
4566 
4567    Output Parameter:
4568 .  assembled - PETSC_TRUE or PETSC_FALSE
4569 
4570    Level: advanced
4571 
4572    Concepts: matrices^assembled?
4573 
4574 .seealso: MatAssemblyEnd(), MatSetValues(), MatAssemblyBegin()
4575 @*/
4576 PetscErrorCode PETSCMAT_DLLEXPORT MatAssembled(Mat mat,PetscTruth *assembled)
4577 {
4578   PetscFunctionBegin;
4579   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4580   PetscValidType(mat,1);
4581   PetscValidPointer(assembled,2);
4582   *assembled = mat->assembled;
4583   PetscFunctionReturn(0);
4584 }
4585 
4586 #undef __FUNCT__
4587 #define __FUNCT__ "MatView_Private"
4588 /*
4589     Processes command line options to determine if/how a matrix
4590   is to be viewed. Called by MatAssemblyEnd() and MatLoad().
4591 */
4592 PetscErrorCode MatView_Private(Mat mat)
4593 {
4594   PetscErrorCode    ierr;
4595   PetscTruth        flg1 = PETSC_FALSE,flg2 = PETSC_FALSE,flg3 = PETSC_FALSE,flg4 = PETSC_FALSE,flg6 = PETSC_FALSE,flg7 = PETSC_FALSE,flg8 = PETSC_FALSE;
4596   static PetscTruth incall = PETSC_FALSE;
4597 #if defined(PETSC_USE_SOCKET_VIEWER)
4598   PetscTruth        flg5 = PETSC_FALSE;
4599 #endif
4600 
4601   PetscFunctionBegin;
4602   if (incall) PetscFunctionReturn(0);
4603   incall = PETSC_TRUE;
4604   ierr = PetscOptionsBegin(((PetscObject)mat)->comm,((PetscObject)mat)->prefix,"Matrix Options","Mat");CHKERRQ(ierr);
4605     ierr = PetscOptionsTruth("-mat_view_info","Information on matrix size","MatView",flg1,&flg1,PETSC_NULL);CHKERRQ(ierr);
4606     ierr = PetscOptionsTruth("-mat_view_info_detailed","Nonzeros in the matrix","MatView",flg2,&flg2,PETSC_NULL);CHKERRQ(ierr);
4607     ierr = PetscOptionsTruth("-mat_view","Print matrix to stdout","MatView",flg3,&flg3,PETSC_NULL);CHKERRQ(ierr);
4608     ierr = PetscOptionsTruth("-mat_view_matlab","Print matrix to stdout in a format Matlab can read","MatView",flg4,&flg4,PETSC_NULL);CHKERRQ(ierr);
4609 #if defined(PETSC_USE_SOCKET_VIEWER)
4610     ierr = PetscOptionsTruth("-mat_view_socket","Send matrix to socket (can be read from matlab)","MatView",flg5,&flg5,PETSC_NULL);CHKERRQ(ierr);
4611 #endif
4612     ierr = PetscOptionsTruth("-mat_view_binary","Save matrix to file in binary format","MatView",flg6,&flg6,PETSC_NULL);CHKERRQ(ierr);
4613     ierr = PetscOptionsTruth("-mat_view_draw","Draw the matrix nonzero structure","MatView",flg7,&flg7,PETSC_NULL);CHKERRQ(ierr);
4614   ierr = PetscOptionsEnd();CHKERRQ(ierr);
4615 
4616   if (flg1) {
4617     PetscViewer viewer;
4618 
4619     ierr = PetscViewerASCIIGetStdout(((PetscObject)mat)->comm,&viewer);CHKERRQ(ierr);
4620     ierr = PetscViewerPushFormat(viewer,PETSC_VIEWER_ASCII_INFO);CHKERRQ(ierr);
4621     ierr = MatView(mat,viewer);CHKERRQ(ierr);
4622     ierr = PetscViewerPopFormat(viewer);CHKERRQ(ierr);
4623   }
4624   if (flg2) {
4625     PetscViewer viewer;
4626 
4627     ierr = PetscViewerASCIIGetStdout(((PetscObject)mat)->comm,&viewer);CHKERRQ(ierr);
4628     ierr = PetscViewerPushFormat(viewer,PETSC_VIEWER_ASCII_INFO_DETAIL);CHKERRQ(ierr);
4629     ierr = MatView(mat,viewer);CHKERRQ(ierr);
4630     ierr = PetscViewerPopFormat(viewer);CHKERRQ(ierr);
4631   }
4632   if (flg3) {
4633     PetscViewer viewer;
4634 
4635     ierr = PetscViewerASCIIGetStdout(((PetscObject)mat)->comm,&viewer);CHKERRQ(ierr);
4636     ierr = MatView(mat,viewer);CHKERRQ(ierr);
4637   }
4638   if (flg4) {
4639     PetscViewer viewer;
4640 
4641     ierr = PetscViewerASCIIGetStdout(((PetscObject)mat)->comm,&viewer);CHKERRQ(ierr);
4642     ierr = PetscViewerPushFormat(viewer,PETSC_VIEWER_ASCII_MATLAB);CHKERRQ(ierr);
4643     ierr = MatView(mat,viewer);CHKERRQ(ierr);
4644     ierr = PetscViewerPopFormat(viewer);CHKERRQ(ierr);
4645   }
4646 #if defined(PETSC_USE_SOCKET_VIEWER)
4647   if (flg5) {
4648     ierr = MatView(mat,PETSC_VIEWER_SOCKET_(((PetscObject)mat)->comm));CHKERRQ(ierr);
4649     ierr = PetscViewerFlush(PETSC_VIEWER_SOCKET_(((PetscObject)mat)->comm));CHKERRQ(ierr);
4650   }
4651 #endif
4652   if (flg6) {
4653     ierr = MatView(mat,PETSC_VIEWER_BINARY_(((PetscObject)mat)->comm));CHKERRQ(ierr);
4654     ierr = PetscViewerFlush(PETSC_VIEWER_BINARY_(((PetscObject)mat)->comm));CHKERRQ(ierr);
4655   }
4656   if (flg7) {
4657     ierr = PetscOptionsGetTruth(((PetscObject)mat)->prefix,"-mat_view_contour",&flg8,PETSC_NULL);CHKERRQ(ierr);
4658     if (flg8) {
4659       PetscViewerPushFormat(PETSC_VIEWER_DRAW_(((PetscObject)mat)->comm),PETSC_VIEWER_DRAW_CONTOUR);CHKERRQ(ierr);
4660     }
4661     ierr = MatView(mat,PETSC_VIEWER_DRAW_(((PetscObject)mat)->comm));CHKERRQ(ierr);
4662     ierr = PetscViewerFlush(PETSC_VIEWER_DRAW_(((PetscObject)mat)->comm));CHKERRQ(ierr);
4663     if (flg8) {
4664       PetscViewerPopFormat(PETSC_VIEWER_DRAW_(((PetscObject)mat)->comm));CHKERRQ(ierr);
4665     }
4666   }
4667   incall = PETSC_FALSE;
4668   PetscFunctionReturn(0);
4669 }
4670 
4671 #undef __FUNCT__
4672 #define __FUNCT__ "MatAssemblyEnd"
4673 /*@
4674    MatAssemblyEnd - Completes assembling the matrix.  This routine should
4675    be called after MatAssemblyBegin().
4676 
4677    Collective on Mat
4678 
4679    Input Parameters:
4680 +  mat - the matrix
4681 -  type - type of assembly, either MAT_FLUSH_ASSEMBLY or MAT_FINAL_ASSEMBLY
4682 
4683    Options Database Keys:
4684 +  -mat_view_info - Prints info on matrix at conclusion of MatEndAssembly()
4685 .  -mat_view_info_detailed - Prints more detailed info
4686 .  -mat_view - Prints matrix in ASCII format
4687 .  -mat_view_matlab - Prints matrix in Matlab format
4688 .  -mat_view_draw - PetscDraws nonzero structure of matrix, using MatView() and PetscDrawOpenX().
4689 .  -display <name> - Sets display name (default is host)
4690 .  -draw_pause <sec> - Sets number of seconds to pause after display
4691 .  -mat_view_socket - Sends matrix to socket, can be accessed from Matlab (see users manual)
4692 .  -viewer_socket_machine <machine>
4693 .  -viewer_socket_port <port>
4694 .  -mat_view_binary - save matrix to file in binary format
4695 -  -viewer_binary_filename <name>
4696 
4697    Notes:
4698    MatSetValues() generally caches the values.  The matrix is ready to
4699    use only after MatAssemblyBegin() and MatAssemblyEnd() have been called.
4700    Use MAT_FLUSH_ASSEMBLY when switching between ADD_VALUES and INSERT_VALUES
4701    in MatSetValues(); use MAT_FINAL_ASSEMBLY for the final assembly before
4702    using the matrix.
4703 
4704    Level: beginner
4705 
4706 .seealso: MatAssemblyBegin(), MatSetValues(), PetscDrawOpenX(), MatView(), MatAssembled(), PetscViewerSocketOpen()
4707 @*/
4708 PetscErrorCode PETSCMAT_DLLEXPORT MatAssemblyEnd(Mat mat,MatAssemblyType type)
4709 {
4710   PetscErrorCode  ierr;
4711   static PetscInt inassm = 0;
4712   PetscTruth      flg = PETSC_FALSE;
4713 
4714   PetscFunctionBegin;
4715   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4716   PetscValidType(mat,1);
4717 
4718   inassm++;
4719   MatAssemblyEnd_InUse++;
4720   if (MatAssemblyEnd_InUse == 1) { /* Do the logging only the first time through */
4721     ierr = PetscLogEventBegin(MAT_AssemblyEnd,mat,0,0,0);CHKERRQ(ierr);
4722     if (mat->ops->assemblyend) {
4723       ierr = (*mat->ops->assemblyend)(mat,type);CHKERRQ(ierr);
4724     }
4725     ierr = PetscLogEventEnd(MAT_AssemblyEnd,mat,0,0,0);CHKERRQ(ierr);
4726   } else {
4727     if (mat->ops->assemblyend) {
4728       ierr = (*mat->ops->assemblyend)(mat,type);CHKERRQ(ierr);
4729     }
4730   }
4731 
4732   /* Flush assembly is not a true assembly */
4733   if (type != MAT_FLUSH_ASSEMBLY) {
4734     mat->assembled  = PETSC_TRUE; mat->num_ass++;
4735   }
4736   mat->insertmode = NOT_SET_VALUES;
4737   MatAssemblyEnd_InUse--;
4738   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
4739   if (!mat->symmetric_eternal) {
4740     mat->symmetric_set              = PETSC_FALSE;
4741     mat->hermitian_set              = PETSC_FALSE;
4742     mat->structurally_symmetric_set = PETSC_FALSE;
4743   }
4744   if (inassm == 1 && type != MAT_FLUSH_ASSEMBLY) {
4745     ierr = MatView_Private(mat);CHKERRQ(ierr);
4746     ierr = PetscOptionsGetTruth(((PetscObject)mat)->prefix,"-mat_is_symmetric",&flg,PETSC_NULL);CHKERRQ(ierr);
4747     if (flg) {
4748       PetscReal tol = 0.0;
4749       ierr = PetscOptionsGetReal(((PetscObject)mat)->prefix,"-mat_is_symmetric",&tol,PETSC_NULL);CHKERRQ(ierr);
4750       ierr = MatIsSymmetric(mat,tol,&flg);CHKERRQ(ierr);
4751       if (flg) {
4752         ierr = PetscPrintf(((PetscObject)mat)->comm,"Matrix is symmetric (tolerance %G)\n",tol);CHKERRQ(ierr);
4753       } else {
4754         ierr = PetscPrintf(((PetscObject)mat)->comm,"Matrix is not symmetric (tolerance %G)\n",tol);CHKERRQ(ierr);
4755       }
4756     }
4757   }
4758   inassm--;
4759   PetscFunctionReturn(0);
4760 }
4761 
4762 #undef __FUNCT__
4763 #define __FUNCT__ "MatSetOption"
4764 /*@
4765    MatSetOption - Sets a parameter option for a matrix. Some options
4766    may be specific to certain storage formats.  Some options
4767    determine how values will be inserted (or added). Sorted,
4768    row-oriented input will generally assemble the fastest. The default
4769    is row-oriented, nonsorted input.
4770 
4771    Collective on Mat
4772 
4773    Input Parameters:
4774 +  mat - the matrix
4775 .  option - the option, one of those listed below (and possibly others),
4776 -  flg - turn the option on (PETSC_TRUE) or off (PETSC_FALSE)
4777 
4778   Options Describing Matrix Structure:
4779 +    MAT_SYMMETRIC - symmetric in terms of both structure and value
4780 .    MAT_HERMITIAN - transpose is the complex conjugation
4781 .    MAT_STRUCTURALLY_SYMMETRIC - symmetric nonzero structure
4782 -    MAT_SYMMETRY_ETERNAL - if you would like the symmetry/Hermitian flag
4783                             you set to be kept with all future use of the matrix
4784                             including after MatAssemblyBegin/End() which could
4785                             potentially change the symmetry structure, i.e. you
4786                             KNOW the matrix will ALWAYS have the property you set.
4787 
4788 
4789    Options For Use with MatSetValues():
4790    Insert a logically dense subblock, which can be
4791 .    MAT_ROW_ORIENTED - row-oriented (default)
4792 
4793    Note these options reflect the data you pass in with MatSetValues(); it has
4794    nothing to do with how the data is stored internally in the matrix
4795    data structure.
4796 
4797    When (re)assembling a matrix, we can restrict the input for
4798    efficiency/debugging purposes.  These options include
4799 +    MAT_NEW_NONZERO_LOCATIONS - additional insertions will be
4800         allowed if they generate a new nonzero
4801 .    MAT_NEW_DIAGONALS - new diagonals will be allowed (for block diagonal format only)
4802 .    MAT_IGNORE_OFF_PROC_ENTRIES - drops off-processor entries
4803 .    MAT_NEW_NONZERO_LOCATION_ERR - generates an error for new matrix entry
4804 -    MAT_USE_HASH_TABLE - uses a hash table to speed up matrix assembly
4805 
4806    Notes:
4807    Some options are relevant only for particular matrix types and
4808    are thus ignored by others.  Other options are not supported by
4809    certain matrix types and will generate an error message if set.
4810 
4811    If using a Fortran 77 module to compute a matrix, one may need to
4812    use the column-oriented option (or convert to the row-oriented
4813    format).
4814 
4815    MAT_NEW_NONZERO_LOCATIONS set to PETSC_FALSE indicates that any add or insertion
4816    that would generate a new entry in the nonzero structure is instead
4817    ignored.  Thus, if memory has not alredy been allocated for this particular
4818    data, then the insertion is ignored. For dense matrices, in which
4819    the entire array is allocated, no entries are ever ignored.
4820    Set after the first MatAssemblyEnd()
4821 
4822    MAT_NEW_NONZERO_LOCATION_ERR indicates that any add or insertion
4823    that would generate a new entry in the nonzero structure instead produces
4824    an error. (Currently supported for AIJ and BAIJ formats only.)
4825    This is a useful flag when using SAME_NONZERO_PATTERN in calling
4826    KSPSetOperators() to ensure that the nonzero pattern truely does
4827    remain unchanged. Set after the first MatAssemblyEnd()
4828 
4829    MAT_NEW_NONZERO_ALLOCATION_ERR indicates that any add or insertion
4830    that would generate a new entry that has not been preallocated will
4831    instead produce an error. (Currently supported for AIJ and BAIJ formats
4832    only.) This is a useful flag when debugging matrix memory preallocation.
4833 
4834    MAT_IGNORE_OFF_PROC_ENTRIES indicates entries destined for
4835    other processors should be dropped, rather than stashed.
4836    This is useful if you know that the "owning" processor is also
4837    always generating the correct matrix entries, so that PETSc need
4838    not transfer duplicate entries generated on another processor.
4839 
4840    MAT_USE_HASH_TABLE indicates that a hash table be used to improve the
4841    searches during matrix assembly. When this flag is set, the hash table
4842    is created during the first Matrix Assembly. This hash table is
4843    used the next time through, during MatSetVaules()/MatSetVaulesBlocked()
4844    to improve the searching of indices. MAT_NEW_NONZERO_LOCATIONS flag
4845    should be used with MAT_USE_HASH_TABLE flag. This option is currently
4846    supported by MATMPIBAIJ format only.
4847 
4848    MAT_KEEP_NONZERO_PATTERN indicates when MatZeroRows() is called the zeroed entries
4849    are kept in the nonzero structure
4850 
4851    MAT_IGNORE_ZERO_ENTRIES - for AIJ/IS matrices this will stop zero values from creating
4852    a zero location in the matrix
4853 
4854    MAT_USE_INODES - indicates using inode version of the code - works with AIJ and
4855    ROWBS matrix types
4856 
4857    Level: intermediate
4858 
4859    Concepts: matrices^setting options
4860 
4861 @*/
4862 PetscErrorCode PETSCMAT_DLLEXPORT MatSetOption(Mat mat,MatOption op,PetscTruth flg)
4863 {
4864   PetscErrorCode ierr;
4865 
4866   PetscFunctionBegin;
4867   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4868   PetscValidType(mat,1);
4869   if (((int) op) < 0 || ((int) op) >= NUM_MAT_OPTIONS) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Options %d is out of range",(int)op);
4870   if (!((PetscObject)mat)->type_name) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_TYPENOTSET,"Cannot set options until type and size have been set, see MatSetType() and MatSetSizes()");
4871   ierr = MatPreallocated(mat);CHKERRQ(ierr);
4872   switch (op) {
4873   case MAT_SYMMETRIC:
4874     mat->symmetric                  = flg;
4875     if (flg) mat->structurally_symmetric = PETSC_TRUE;
4876     mat->symmetric_set              = PETSC_TRUE;
4877     mat->structurally_symmetric_set = flg;
4878     break;
4879   case MAT_HERMITIAN:
4880     mat->hermitian                  = flg;
4881     if (flg) mat->structurally_symmetric = PETSC_TRUE;
4882     mat->hermitian_set              = PETSC_TRUE;
4883     mat->structurally_symmetric_set = flg;
4884     break;
4885   case MAT_STRUCTURALLY_SYMMETRIC:
4886     mat->structurally_symmetric     = flg;
4887     mat->structurally_symmetric_set = PETSC_TRUE;
4888     break;
4889   case MAT_SYMMETRY_ETERNAL:
4890     mat->symmetric_eternal          = flg;
4891     break;
4892   default:
4893     break;
4894   }
4895   if (mat->ops->setoption) {
4896     ierr = (*mat->ops->setoption)(mat,op,flg);CHKERRQ(ierr);
4897   }
4898   PetscFunctionReturn(0);
4899 }
4900 
4901 #undef __FUNCT__
4902 #define __FUNCT__ "MatZeroEntries"
4903 /*@
4904    MatZeroEntries - Zeros all entries of a matrix.  For sparse matrices
4905    this routine retains the old nonzero structure.
4906 
4907    Collective on Mat
4908 
4909    Input Parameters:
4910 .  mat - the matrix
4911 
4912    Level: intermediate
4913 
4914    Concepts: matrices^zeroing
4915 
4916 .seealso: MatZeroRows()
4917 @*/
4918 PetscErrorCode PETSCMAT_DLLEXPORT MatZeroEntries(Mat mat)
4919 {
4920   PetscErrorCode ierr;
4921 
4922   PetscFunctionBegin;
4923   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4924   PetscValidType(mat,1);
4925   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4926   if (mat->insertmode != NOT_SET_VALUES) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for matrices where you have set values but not yet assembled");
4927   if (!mat->ops->zeroentries) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
4928   ierr = MatPreallocated(mat);CHKERRQ(ierr);
4929 
4930   ierr = PetscLogEventBegin(MAT_ZeroEntries,mat,0,0,0);CHKERRQ(ierr);
4931   ierr = (*mat->ops->zeroentries)(mat);CHKERRQ(ierr);
4932   ierr = PetscLogEventEnd(MAT_ZeroEntries,mat,0,0,0);CHKERRQ(ierr);
4933   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
4934   PetscFunctionReturn(0);
4935 }
4936 
4937 #undef __FUNCT__
4938 #define __FUNCT__ "MatZeroRows"
4939 /*@C
4940    MatZeroRows - Zeros all entries (except possibly the main diagonal)
4941    of a set of rows of a matrix.
4942 
4943    Collective on Mat
4944 
4945    Input Parameters:
4946 +  mat - the matrix
4947 .  numRows - the number of rows to remove
4948 .  rows - the global row indices
4949 -  diag - value put in all diagonals of eliminated rows (0.0 will even eliminate diagonal entry)
4950 
4951    Notes:
4952    For the AIJ and BAIJ matrix formats this removes the old nonzero structure,
4953    but does not release memory.  For the dense and block diagonal
4954    formats this does not alter the nonzero structure.
4955 
4956    If the option MatSetOption(mat,MAT_KEEP_NONZERO_PATTERN,PETSC_TRUE) the nonzero structure
4957    of the matrix is not changed (even for AIJ and BAIJ matrices) the values are
4958    merely zeroed.
4959 
4960    The user can set a value in the diagonal entry (or for the AIJ and
4961    row formats can optionally remove the main diagonal entry from the
4962    nonzero structure as well, by passing 0.0 as the final argument).
4963 
4964    For the parallel case, all processes that share the matrix (i.e.,
4965    those in the communicator used for matrix creation) MUST call this
4966    routine, regardless of whether any rows being zeroed are owned by
4967    them.
4968 
4969    Each processor can indicate any rows in the entire matrix to be zeroed (i.e. each process does NOT have to
4970    list only rows local to itself).
4971 
4972    Level: intermediate
4973 
4974    Concepts: matrices^zeroing rows
4975 
4976 .seealso: MatZeroRowsIS(), MatZeroEntries(), MatZeroRowsLocal(), MatSetOption()
4977 @*/
4978 PetscErrorCode PETSCMAT_DLLEXPORT MatZeroRows(Mat mat,PetscInt numRows,const PetscInt rows[],PetscScalar diag)
4979 {
4980   PetscErrorCode ierr;
4981 
4982   PetscFunctionBegin;
4983   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
4984   PetscValidType(mat,1);
4985   if (numRows) PetscValidIntPointer(rows,3);
4986   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
4987   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
4988   if (!mat->ops->zerorows) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
4989   ierr = MatPreallocated(mat);CHKERRQ(ierr);
4990 
4991   ierr = (*mat->ops->zerorows)(mat,numRows,rows,diag);CHKERRQ(ierr);
4992   ierr = MatView_Private(mat);CHKERRQ(ierr);
4993   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
4994   PetscFunctionReturn(0);
4995 }
4996 
4997 #undef __FUNCT__
4998 #define __FUNCT__ "MatZeroRowsIS"
4999 /*@C
5000    MatZeroRowsIS - Zeros all entries (except possibly the main diagonal)
5001    of a set of rows of a matrix.
5002 
5003    Collective on Mat
5004 
5005    Input Parameters:
5006 +  mat - the matrix
5007 .  is - index set of rows to remove
5008 -  diag - value put in all diagonals of eliminated rows
5009 
5010    Notes:
5011    For the AIJ and BAIJ matrix formats this removes the old nonzero structure,
5012    but does not release memory.  For the dense and block diagonal
5013    formats this does not alter the nonzero structure.
5014 
5015    If the option MatSetOption(mat,MAT_KEEP_NONZERO_PATTERN,PETSC_TRUE) the nonzero structure
5016    of the matrix is not changed (even for AIJ and BAIJ matrices) the values are
5017    merely zeroed.
5018 
5019    The user can set a value in the diagonal entry (or for the AIJ and
5020    row formats can optionally remove the main diagonal entry from the
5021    nonzero structure as well, by passing 0.0 as the final argument).
5022 
5023    For the parallel case, all processes that share the matrix (i.e.,
5024    those in the communicator used for matrix creation) MUST call this
5025    routine, regardless of whether any rows being zeroed are owned by
5026    them.
5027 
5028    Each processor should list the rows that IT wants zeroed
5029 
5030    Level: intermediate
5031 
5032    Concepts: matrices^zeroing rows
5033 
5034 .seealso: MatZeroRows(), MatZeroEntries(), MatZeroRowsLocal(), MatSetOption()
5035 @*/
5036 PetscErrorCode PETSCMAT_DLLEXPORT MatZeroRowsIS(Mat mat,IS is,PetscScalar diag)
5037 {
5038   PetscInt       numRows;
5039   const PetscInt *rows;
5040   PetscErrorCode ierr;
5041 
5042   PetscFunctionBegin;
5043   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5044   PetscValidType(mat,1);
5045   PetscValidHeaderSpecific(is,IS_CLASSID,2);
5046   ierr = ISGetLocalSize(is,&numRows);CHKERRQ(ierr);
5047   ierr = ISGetIndices(is,&rows);CHKERRQ(ierr);
5048   ierr = MatZeroRows(mat,numRows,rows,diag);CHKERRQ(ierr);
5049   ierr = ISRestoreIndices(is,&rows);CHKERRQ(ierr);
5050   PetscFunctionReturn(0);
5051 }
5052 
5053 #undef __FUNCT__
5054 #define __FUNCT__ "MatZeroRowsLocal"
5055 /*@C
5056    MatZeroRowsLocal - Zeros all entries (except possibly the main diagonal)
5057    of a set of rows of a matrix; using local numbering of rows.
5058 
5059    Collective on Mat
5060 
5061    Input Parameters:
5062 +  mat - the matrix
5063 .  numRows - the number of rows to remove
5064 .  rows - the global row indices
5065 -  diag - value put in all diagonals of eliminated rows
5066 
5067    Notes:
5068    Before calling MatZeroRowsLocal(), the user must first set the
5069    local-to-global mapping by calling MatSetLocalToGlobalMapping().
5070 
5071    For the AIJ matrix formats this removes the old nonzero structure,
5072    but does not release memory.  For the dense and block diagonal
5073    formats this does not alter the nonzero structure.
5074 
5075    If the option MatSetOption(mat,MAT_KEEP_NONZERO_PATTERN,PETSC_TRUE) the nonzero structure
5076    of the matrix is not changed (even for AIJ and BAIJ matrices) the values are
5077    merely zeroed.
5078 
5079    The user can set a value in the diagonal entry (or for the AIJ and
5080    row formats can optionally remove the main diagonal entry from the
5081    nonzero structure as well, by passing 0.0 as the final argument).
5082 
5083    Level: intermediate
5084 
5085    Concepts: matrices^zeroing
5086 
5087 .seealso: MatZeroRows(), MatZeroRowsLocalIS(), MatZeroEntries(), MatZeroRows(), MatSetLocalToGlobalMapping
5088 @*/
5089 PetscErrorCode PETSCMAT_DLLEXPORT MatZeroRowsLocal(Mat mat,PetscInt numRows,const PetscInt rows[],PetscScalar diag)
5090 {
5091   PetscErrorCode ierr;
5092 
5093   PetscFunctionBegin;
5094   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5095   PetscValidType(mat,1);
5096   if (numRows) PetscValidIntPointer(rows,3);
5097   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5098   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5099   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5100 
5101   if (mat->ops->zerorowslocal) {
5102     ierr = (*mat->ops->zerorowslocal)(mat,numRows,rows,diag);CHKERRQ(ierr);
5103   } else {
5104     IS             is, newis;
5105     const PetscInt *newRows;
5106 
5107     if (!mat->mapping) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Need to provide local to global mapping to matrix first");
5108     ierr = ISCreateGeneral(PETSC_COMM_SELF,numRows,rows,&is);CHKERRQ(ierr);
5109     ierr = ISLocalToGlobalMappingApplyIS(mat->mapping,is,&newis);CHKERRQ(ierr);
5110     ierr = ISGetIndices(newis,&newRows);CHKERRQ(ierr);
5111     ierr = (*mat->ops->zerorows)(mat,numRows,newRows,diag);CHKERRQ(ierr);
5112     ierr = ISRestoreIndices(newis,&newRows);CHKERRQ(ierr);
5113     ierr = ISDestroy(newis);CHKERRQ(ierr);
5114     ierr = ISDestroy(is);CHKERRQ(ierr);
5115   }
5116   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
5117   PetscFunctionReturn(0);
5118 }
5119 
5120 #undef __FUNCT__
5121 #define __FUNCT__ "MatZeroRowsLocalIS"
5122 /*@C
5123    MatZeroRowsLocalIS - Zeros all entries (except possibly the main diagonal)
5124    of a set of rows of a matrix; using local numbering of rows.
5125 
5126    Collective on Mat
5127 
5128    Input Parameters:
5129 +  mat - the matrix
5130 .  is - index set of rows to remove
5131 -  diag - value put in all diagonals of eliminated rows
5132 
5133    Notes:
5134    Before calling MatZeroRowsLocalIS(), the user must first set the
5135    local-to-global mapping by calling MatSetLocalToGlobalMapping().
5136 
5137    For the AIJ matrix formats this removes the old nonzero structure,
5138    but does not release memory.  For the dense and block diagonal
5139    formats this does not alter the nonzero structure.
5140 
5141    If the option MatSetOption(mat,MAT_KEEP_NONZERO_PATTERN,PETSC_TRUE) the nonzero structure
5142    of the matrix is not changed (even for AIJ and BAIJ matrices) the values are
5143    merely zeroed.
5144 
5145    The user can set a value in the diagonal entry (or for the AIJ and
5146    row formats can optionally remove the main diagonal entry from the
5147    nonzero structure as well, by passing 0.0 as the final argument).
5148 
5149    Level: intermediate
5150 
5151    Concepts: matrices^zeroing
5152 
5153 .seealso: MatZeroRows(), MatZeroRowsLocal(), MatZeroEntries(), MatZeroRows(), MatSetLocalToGlobalMapping
5154 @*/
5155 PetscErrorCode PETSCMAT_DLLEXPORT MatZeroRowsLocalIS(Mat mat,IS is,PetscScalar diag)
5156 {
5157   PetscErrorCode ierr;
5158   PetscInt       numRows;
5159   const PetscInt *rows;
5160 
5161   PetscFunctionBegin;
5162   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5163   PetscValidType(mat,1);
5164   PetscValidHeaderSpecific(is,IS_CLASSID,2);
5165   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5166   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5167   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5168 
5169   ierr = ISGetLocalSize(is,&numRows);CHKERRQ(ierr);
5170   ierr = ISGetIndices(is,&rows);CHKERRQ(ierr);
5171   ierr = MatZeroRowsLocal(mat,numRows,rows,diag);CHKERRQ(ierr);
5172   ierr = ISRestoreIndices(is,&rows);CHKERRQ(ierr);
5173   PetscFunctionReturn(0);
5174 }
5175 
5176 #undef __FUNCT__
5177 #define __FUNCT__ "MatGetSize"
5178 /*@
5179    MatGetSize - Returns the numbers of rows and columns in a matrix.
5180 
5181    Not Collective
5182 
5183    Input Parameter:
5184 .  mat - the matrix
5185 
5186    Output Parameters:
5187 +  m - the number of global rows
5188 -  n - the number of global columns
5189 
5190    Note: both output parameters can be PETSC_NULL on input.
5191 
5192    Level: beginner
5193 
5194    Concepts: matrices^size
5195 
5196 .seealso: MatGetLocalSize()
5197 @*/
5198 PetscErrorCode PETSCMAT_DLLEXPORT MatGetSize(Mat mat,PetscInt *m,PetscInt* n)
5199 {
5200   PetscFunctionBegin;
5201   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5202   if (m) *m = mat->rmap->N;
5203   if (n) *n = mat->cmap->N;
5204   PetscFunctionReturn(0);
5205 }
5206 
5207 #undef __FUNCT__
5208 #define __FUNCT__ "MatGetLocalSize"
5209 /*@
5210    MatGetLocalSize - Returns the number of rows and columns in a matrix
5211    stored locally.  This information may be implementation dependent, so
5212    use with care.
5213 
5214    Not Collective
5215 
5216    Input Parameters:
5217 .  mat - the matrix
5218 
5219    Output Parameters:
5220 +  m - the number of local rows
5221 -  n - the number of local columns
5222 
5223    Note: both output parameters can be PETSC_NULL on input.
5224 
5225    Level: beginner
5226 
5227    Concepts: matrices^local size
5228 
5229 .seealso: MatGetSize()
5230 @*/
5231 PetscErrorCode PETSCMAT_DLLEXPORT MatGetLocalSize(Mat mat,PetscInt *m,PetscInt* n)
5232 {
5233   PetscFunctionBegin;
5234   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5235   if (m) PetscValidIntPointer(m,2);
5236   if (n) PetscValidIntPointer(n,3);
5237   if (m) *m = mat->rmap->n;
5238   if (n) *n = mat->cmap->n;
5239   PetscFunctionReturn(0);
5240 }
5241 
5242 #undef __FUNCT__
5243 #define __FUNCT__ "MatGetOwnershipRangeColumn"
5244 /*@
5245    MatGetOwnershipRangeColumn - Returns the range of matrix columns owned by
5246    this processor.
5247 
5248    Not Collective, unless matrix has not been allocated, then collective on Mat
5249 
5250    Input Parameters:
5251 .  mat - the matrix
5252 
5253    Output Parameters:
5254 +  m - the global index of the first local column
5255 -  n - one more than the global index of the last local column
5256 
5257    Notes: both output parameters can be PETSC_NULL on input.
5258 
5259    Level: developer
5260 
5261    Concepts: matrices^column ownership
5262 
5263 .seealso:  MatGetOwnershipRange(), MatGetOwnershipRanges(), MatGetOwnershipRangesColumn()
5264 
5265 @*/
5266 PetscErrorCode PETSCMAT_DLLEXPORT MatGetOwnershipRangeColumn(Mat mat,PetscInt *m,PetscInt* n)
5267 {
5268   PetscErrorCode ierr;
5269 
5270   PetscFunctionBegin;
5271   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5272   PetscValidType(mat,1);
5273   if (m) PetscValidIntPointer(m,2);
5274   if (n) PetscValidIntPointer(n,3);
5275   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5276   if (m) *m = mat->cmap->rstart;
5277   if (n) *n = mat->cmap->rend;
5278   PetscFunctionReturn(0);
5279 }
5280 
5281 #undef __FUNCT__
5282 #define __FUNCT__ "MatGetOwnershipRange"
5283 /*@
5284    MatGetOwnershipRange - Returns the range of matrix rows owned by
5285    this processor, assuming that the matrix is laid out with the first
5286    n1 rows on the first processor, the next n2 rows on the second, etc.
5287    For certain parallel layouts this range may not be well defined.
5288 
5289    Not Collective, unless matrix has not been allocated, then collective on Mat
5290 
5291    Input Parameters:
5292 .  mat - the matrix
5293 
5294    Output Parameters:
5295 +  m - the global index of the first local row
5296 -  n - one more than the global index of the last local row
5297 
5298    Note: both output parameters can be PETSC_NULL on input.
5299 
5300    Level: beginner
5301 
5302    Concepts: matrices^row ownership
5303 
5304 .seealso:   MatGetOwnershipRanges(), MatGetOwnershipRangeColumn(), MatGetOwnershipRangesColumn()
5305 
5306 @*/
5307 PetscErrorCode PETSCMAT_DLLEXPORT MatGetOwnershipRange(Mat mat,PetscInt *m,PetscInt* n)
5308 {
5309   PetscErrorCode ierr;
5310 
5311   PetscFunctionBegin;
5312   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5313   PetscValidType(mat,1);
5314   if (m) PetscValidIntPointer(m,2);
5315   if (n) PetscValidIntPointer(n,3);
5316   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5317   if (m) *m = mat->rmap->rstart;
5318   if (n) *n = mat->rmap->rend;
5319   PetscFunctionReturn(0);
5320 }
5321 
5322 #undef __FUNCT__
5323 #define __FUNCT__ "MatGetOwnershipRanges"
5324 /*@C
5325    MatGetOwnershipRanges - Returns the range of matrix rows owned by
5326    each process
5327 
5328    Not Collective, unless matrix has not been allocated, then collective on Mat
5329 
5330    Input Parameters:
5331 .  mat - the matrix
5332 
5333    Output Parameters:
5334 .  ranges - start of each processors portion plus one more then the total length at the end
5335 
5336    Level: beginner
5337 
5338    Concepts: matrices^row ownership
5339 
5340 .seealso:   MatGetOwnershipRange(), MatGetOwnershipRangeColumn(), MatGetOwnershipRangesColumn()
5341 
5342 @*/
5343 PetscErrorCode PETSCMAT_DLLEXPORT MatGetOwnershipRanges(Mat mat,const PetscInt **ranges)
5344 {
5345   PetscErrorCode ierr;
5346 
5347   PetscFunctionBegin;
5348   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5349   PetscValidType(mat,1);
5350   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5351   ierr = PetscLayoutGetRanges(mat->rmap,ranges);CHKERRQ(ierr);
5352   PetscFunctionReturn(0);
5353 }
5354 
5355 #undef __FUNCT__
5356 #define __FUNCT__ "MatGetOwnershipRangesColumn"
5357 /*@C
5358    MatGetOwnershipRangesColumn - Returns the range of local columns for each process
5359 
5360    Not Collective, unless matrix has not been allocated, then collective on Mat
5361 
5362    Input Parameters:
5363 .  mat - the matrix
5364 
5365    Output Parameters:
5366 .  ranges - start of each processors portion plus one more then the total length at the end
5367 
5368    Level: beginner
5369 
5370    Concepts: matrices^column ownership
5371 
5372 .seealso:   MatGetOwnershipRange(), MatGetOwnershipRangeColumn(), MatGetOwnershipRanges()
5373 
5374 @*/
5375 PetscErrorCode PETSCMAT_DLLEXPORT MatGetOwnershipRangesColumn(Mat mat,const PetscInt **ranges)
5376 {
5377   PetscErrorCode ierr;
5378 
5379   PetscFunctionBegin;
5380   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5381   PetscValidType(mat,1);
5382   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5383   ierr = PetscLayoutGetRanges(mat->cmap,ranges);CHKERRQ(ierr);
5384   PetscFunctionReturn(0);
5385 }
5386 
5387 #undef __FUNCT__
5388 #define __FUNCT__ "MatILUFactorSymbolic"
5389 /*@C
5390    MatILUFactorSymbolic - Performs symbolic ILU factorization of a matrix.
5391    Uses levels of fill only, not drop tolerance. Use MatLUFactorNumeric()
5392    to complete the factorization.
5393 
5394    Collective on Mat
5395 
5396    Input Parameters:
5397 +  mat - the matrix
5398 .  row - row permutation
5399 .  column - column permutation
5400 -  info - structure containing
5401 $      levels - number of levels of fill.
5402 $      expected fill - as ratio of original fill.
5403 $      1 or 0 - indicating force fill on diagonal (improves robustness for matrices
5404                 missing diagonal entries)
5405 
5406    Output Parameters:
5407 .  fact - new matrix that has been symbolically factored
5408 
5409    Notes:
5410    See the users manual for additional information about
5411    choosing the fill factor for better efficiency.
5412 
5413    Most users should employ the simplified KSP interface for linear solvers
5414    instead of working directly with matrix algebra routines such as this.
5415    See, e.g., KSPCreate().
5416 
5417    Level: developer
5418 
5419   Concepts: matrices^symbolic LU factorization
5420   Concepts: matrices^factorization
5421   Concepts: LU^symbolic factorization
5422 
5423 .seealso: MatLUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor()
5424           MatGetOrdering(), MatFactorInfo
5425 
5426     Developer Note: fortran interface is not autogenerated as the f90
5427     interface defintion cannot be generated correctly [due to MatFactorInfo]
5428 
5429 @*/
5430 PetscErrorCode PETSCMAT_DLLEXPORT MatILUFactorSymbolic(Mat fact,Mat mat,IS row,IS col,const MatFactorInfo *info)
5431 {
5432   PetscErrorCode ierr;
5433 
5434   PetscFunctionBegin;
5435   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5436   PetscValidType(mat,1);
5437   PetscValidHeaderSpecific(row,IS_CLASSID,2);
5438   PetscValidHeaderSpecific(col,IS_CLASSID,3);
5439   PetscValidPointer(info,4);
5440   PetscValidPointer(fact,5);
5441   if (info->levels < 0) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Levels of fill negative %D",(PetscInt)info->levels);
5442   if (info->fill < 1.0) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Expected fill less than 1.0 %G",info->fill);
5443   if (!(fact)->ops->ilufactorsymbolic) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Matrix type %s  symbolic ILU",((PetscObject)mat)->type_name);
5444   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5445   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5446   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5447 
5448   ierr = PetscLogEventBegin(MAT_ILUFactorSymbolic,mat,row,col,0);CHKERRQ(ierr);
5449   ierr = (fact->ops->ilufactorsymbolic)(fact,mat,row,col,info);CHKERRQ(ierr);
5450   ierr = PetscLogEventEnd(MAT_ILUFactorSymbolic,mat,row,col,0);CHKERRQ(ierr);
5451   PetscFunctionReturn(0);
5452 }
5453 
5454 #undef __FUNCT__
5455 #define __FUNCT__ "MatICCFactorSymbolic"
5456 /*@C
5457    MatICCFactorSymbolic - Performs symbolic incomplete
5458    Cholesky factorization for a symmetric matrix.  Use
5459    MatCholeskyFactorNumeric() to complete the factorization.
5460 
5461    Collective on Mat
5462 
5463    Input Parameters:
5464 +  mat - the matrix
5465 .  perm - row and column permutation
5466 -  info - structure containing
5467 $      levels - number of levels of fill.
5468 $      expected fill - as ratio of original fill.
5469 
5470    Output Parameter:
5471 .  fact - the factored matrix
5472 
5473    Notes:
5474    Most users should employ the KSP interface for linear solvers
5475    instead of working directly with matrix algebra routines such as this.
5476    See, e.g., KSPCreate().
5477 
5478    Level: developer
5479 
5480   Concepts: matrices^symbolic incomplete Cholesky factorization
5481   Concepts: matrices^factorization
5482   Concepts: Cholsky^symbolic factorization
5483 
5484 .seealso: MatCholeskyFactorNumeric(), MatCholeskyFactor(), MatFactorInfo
5485 
5486     Developer Note: fortran interface is not autogenerated as the f90
5487     interface defintion cannot be generated correctly [due to MatFactorInfo]
5488 
5489 @*/
5490 PetscErrorCode PETSCMAT_DLLEXPORT MatICCFactorSymbolic(Mat fact,Mat mat,IS perm,const MatFactorInfo *info)
5491 {
5492   PetscErrorCode ierr;
5493 
5494   PetscFunctionBegin;
5495   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5496   PetscValidType(mat,1);
5497   PetscValidHeaderSpecific(perm,IS_CLASSID,2);
5498   PetscValidPointer(info,3);
5499   PetscValidPointer(fact,4);
5500   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5501   if (info->levels < 0) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Levels negative %D",(PetscInt) info->levels);
5502   if (info->fill < 1.0) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Expected fill less than 1.0 %G",info->fill);
5503   if (!(fact)->ops->iccfactorsymbolic) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Matrix type %s  symbolic ICC",((PetscObject)mat)->type_name);
5504   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5505   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5506 
5507   ierr = PetscLogEventBegin(MAT_ICCFactorSymbolic,mat,perm,0,0);CHKERRQ(ierr);
5508   ierr = (fact->ops->iccfactorsymbolic)(fact,mat,perm,info);CHKERRQ(ierr);
5509   ierr = PetscLogEventEnd(MAT_ICCFactorSymbolic,mat,perm,0,0);CHKERRQ(ierr);
5510   PetscFunctionReturn(0);
5511 }
5512 
5513 #undef __FUNCT__
5514 #define __FUNCT__ "MatGetArray"
5515 /*@C
5516    MatGetArray - Returns a pointer to the element values in the matrix.
5517    The result of this routine is dependent on the underlying matrix data
5518    structure, and may not even work for certain matrix types.  You MUST
5519    call MatRestoreArray() when you no longer need to access the array.
5520 
5521    Not Collective
5522 
5523    Input Parameter:
5524 .  mat - the matrix
5525 
5526    Output Parameter:
5527 .  v - the location of the values
5528 
5529 
5530    Fortran Note:
5531    This routine is used differently from Fortran, e.g.,
5532 .vb
5533         Mat         mat
5534         PetscScalar mat_array(1)
5535         PetscOffset i_mat
5536         PetscErrorCode ierr
5537         call MatGetArray(mat,mat_array,i_mat,ierr)
5538 
5539   C  Access first local entry in matrix; note that array is
5540   C  treated as one dimensional
5541         value = mat_array(i_mat + 1)
5542 
5543         [... other code ...]
5544         call MatRestoreArray(mat,mat_array,i_mat,ierr)
5545 .ve
5546 
5547    See the Fortran chapter of the users manual and
5548    petsc/src/mat/examples/tests for details.
5549 
5550    Level: advanced
5551 
5552    Concepts: matrices^access array
5553 
5554 .seealso: MatRestoreArray(), MatGetArrayF90(), MatGetRowIJ()
5555 @*/
5556 PetscErrorCode PETSCMAT_DLLEXPORT MatGetArray(Mat mat,PetscScalar *v[])
5557 {
5558   PetscErrorCode ierr;
5559 
5560   PetscFunctionBegin;
5561   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5562   PetscValidType(mat,1);
5563   PetscValidPointer(v,2);
5564   if (!mat->ops->getarray) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
5565   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5566   ierr = (*mat->ops->getarray)(mat,v);CHKERRQ(ierr);
5567   CHKMEMQ;
5568   PetscFunctionReturn(0);
5569 }
5570 
5571 #undef __FUNCT__
5572 #define __FUNCT__ "MatRestoreArray"
5573 /*@C
5574    MatRestoreArray - Restores the matrix after MatGetArray() has been called.
5575 
5576    Not Collective
5577 
5578    Input Parameter:
5579 +  mat - the matrix
5580 -  v - the location of the values
5581 
5582    Fortran Note:
5583    This routine is used differently from Fortran, e.g.,
5584 .vb
5585         Mat         mat
5586         PetscScalar mat_array(1)
5587         PetscOffset i_mat
5588         PetscErrorCode ierr
5589         call MatGetArray(mat,mat_array,i_mat,ierr)
5590 
5591   C  Access first local entry in matrix; note that array is
5592   C  treated as one dimensional
5593         value = mat_array(i_mat + 1)
5594 
5595         [... other code ...]
5596         call MatRestoreArray(mat,mat_array,i_mat,ierr)
5597 .ve
5598 
5599    See the Fortran chapter of the users manual and
5600    petsc/src/mat/examples/tests for details
5601 
5602    Level: advanced
5603 
5604 .seealso: MatGetArray(), MatRestoreArrayF90()
5605 @*/
5606 PetscErrorCode PETSCMAT_DLLEXPORT MatRestoreArray(Mat mat,PetscScalar *v[])
5607 {
5608   PetscErrorCode ierr;
5609 
5610   PetscFunctionBegin;
5611   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5612   PetscValidType(mat,1);
5613   PetscValidPointer(v,2);
5614 #if defined(PETSC_USE_DEBUG)
5615   CHKMEMQ;
5616 #endif
5617   if (!mat->ops->restorearray) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
5618   ierr = (*mat->ops->restorearray)(mat,v);CHKERRQ(ierr);
5619   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
5620   PetscFunctionReturn(0);
5621 }
5622 
5623 #undef __FUNCT__
5624 #define __FUNCT__ "MatGetSubMatrices"
5625 /*@C
5626    MatGetSubMatrices - Extracts several submatrices from a matrix. If submat
5627    points to an array of valid matrices, they may be reused to store the new
5628    submatrices.
5629 
5630    Collective on Mat
5631 
5632    Input Parameters:
5633 +  mat - the matrix
5634 .  n   - the number of submatrixes to be extracted (on this processor, may be zero)
5635 .  irow, icol - index sets of rows and columns to extract
5636 -  scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX
5637 
5638    Output Parameter:
5639 .  submat - the array of submatrices
5640 
5641    Notes:
5642    MatGetSubMatrices() can extract ONLY sequential submatrices
5643    (from both sequential and parallel matrices). Use MatGetSubMatrix()
5644    to extract a parallel submatrix.
5645 
5646    When extracting submatrices from a parallel matrix, each processor can
5647    form a different submatrix by setting the rows and columns of its
5648    individual index sets according to the local submatrix desired.
5649 
5650    When finished using the submatrices, the user should destroy
5651    them with MatDestroyMatrices().
5652 
5653    MAT_REUSE_MATRIX can only be used when the nonzero structure of the
5654    original matrix has not changed from that last call to MatGetSubMatrices().
5655 
5656    This routine creates the matrices in submat; you should NOT create them before
5657    calling it. It also allocates the array of matrix pointers submat.
5658 
5659    For BAIJ matrices the index sets must respect the block structure, that is if they
5660    request one row/column in a block, they must request all rows/columns that are in
5661    that block. For example, if the block size is 2 you cannot request just row 0 and
5662    column 0.
5663 
5664    Fortran Note:
5665    The Fortran interface is slightly different from that given below; it
5666    requires one to pass in  as submat a Mat (integer) array of size at least m.
5667 
5668    Level: advanced
5669 
5670    Concepts: matrices^accessing submatrices
5671    Concepts: submatrices
5672 
5673 .seealso: MatDestroyMatrices(), MatGetSubMatrix(), MatGetRow(), MatGetDiagonal(), MatReuse
5674 @*/
5675 PetscErrorCode PETSCMAT_DLLEXPORT MatGetSubMatrices(Mat mat,PetscInt n,const IS irow[],const IS icol[],MatReuse scall,Mat *submat[])
5676 {
5677   PetscErrorCode ierr;
5678   PetscInt        i;
5679   PetscTruth      eq;
5680 
5681   PetscFunctionBegin;
5682   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5683   PetscValidType(mat,1);
5684   if (n) {
5685     PetscValidPointer(irow,3);
5686     PetscValidHeaderSpecific(*irow,IS_CLASSID,3);
5687     PetscValidPointer(icol,4);
5688     PetscValidHeaderSpecific(*icol,IS_CLASSID,4);
5689   }
5690   PetscValidPointer(submat,6);
5691   if (n && scall == MAT_REUSE_MATRIX) {
5692     PetscValidPointer(*submat,6);
5693     PetscValidHeaderSpecific(**submat,MAT_CLASSID,6);
5694   }
5695   if (!mat->ops->getsubmatrices) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
5696   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5697   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5698   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5699 
5700   ierr = PetscLogEventBegin(MAT_GetSubMatrices,mat,0,0,0);CHKERRQ(ierr);
5701   ierr = (*mat->ops->getsubmatrices)(mat,n,irow,icol,scall,submat);CHKERRQ(ierr);
5702   ierr = PetscLogEventEnd(MAT_GetSubMatrices,mat,0,0,0);CHKERRQ(ierr);
5703   for (i=0; i<n; i++) {
5704     if (mat->symmetric || mat->structurally_symmetric || mat->hermitian) {
5705       ierr = ISEqual(irow[i],icol[i],&eq);CHKERRQ(ierr);
5706       if (eq) {
5707 	if (mat->symmetric){
5708 	  ierr = MatSetOption((*submat)[i],MAT_SYMMETRIC,PETSC_TRUE);CHKERRQ(ierr);
5709 	} else if (mat->hermitian) {
5710 	  ierr = MatSetOption((*submat)[i],MAT_HERMITIAN,PETSC_TRUE);CHKERRQ(ierr);
5711 	} else if (mat->structurally_symmetric) {
5712 	  ierr = MatSetOption((*submat)[i],MAT_STRUCTURALLY_SYMMETRIC,PETSC_TRUE);CHKERRQ(ierr);
5713 	}
5714       }
5715     }
5716   }
5717   PetscFunctionReturn(0);
5718 }
5719 
5720 #undef __FUNCT__
5721 #define __FUNCT__ "MatDestroyMatrices"
5722 /*@C
5723    MatDestroyMatrices - Destroys a set of matrices obtained with MatGetSubMatrices().
5724 
5725    Collective on Mat
5726 
5727    Input Parameters:
5728 +  n - the number of local matrices
5729 -  mat - the matrices (note that this is a pointer to the array of matrices, just to match the calling
5730                        sequence of MatGetSubMatrices())
5731 
5732    Level: advanced
5733 
5734     Notes: Frees not only the matrices, but also the array that contains the matrices
5735            In Fortran will not free the array.
5736 
5737 .seealso: MatGetSubMatrices()
5738 @*/
5739 PetscErrorCode PETSCMAT_DLLEXPORT MatDestroyMatrices(PetscInt n,Mat *mat[])
5740 {
5741   PetscErrorCode ierr;
5742   PetscInt       i;
5743 
5744   PetscFunctionBegin;
5745   if (n < 0) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Trying to destroy negative number of matrices %D",n);
5746   PetscValidPointer(mat,2);
5747   for (i=0; i<n; i++) {
5748     ierr = MatDestroy((*mat)[i]);CHKERRQ(ierr);
5749   }
5750   /* memory is allocated even if n = 0 */
5751   ierr = PetscFree(*mat);CHKERRQ(ierr);
5752   PetscFunctionReturn(0);
5753 }
5754 
5755 #undef __FUNCT__
5756 #define __FUNCT__ "MatGetSeqNonzeroStructure"
5757 /*@C
5758    MatGetSeqNonzeroStructure - Extracts the sequential nonzero structure from a matrix.
5759 
5760    Collective on Mat
5761 
5762    Input Parameters:
5763 .  mat - the matrix
5764 
5765    Output Parameter:
5766 .  matstruct - the sequential matrix with the nonzero structure of mat
5767 
5768   Level: intermediate
5769 
5770 .seealso: MatDestroySeqNonzeroStructure(), MatGetSubMatrices(), MatDestroyMatrices()
5771 @*/
5772 PetscErrorCode PETSCMAT_DLLEXPORT MatGetSeqNonzeroStructure(Mat mat,Mat *matstruct)
5773 {
5774   PetscErrorCode ierr;
5775 
5776   PetscFunctionBegin;
5777   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5778   PetscValidPointer(matstruct,2);
5779 
5780   PetscValidType(mat,1);
5781   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5782   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5783 
5784   if (!mat->ops->getseqnonzerostructure) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Not for matrix type %s\n",((PetscObject)mat)->type_name);
5785   ierr = PetscLogEventBegin(MAT_GetSeqNonzeroStructure,mat,0,0,0);CHKERRQ(ierr);
5786   ierr = (*mat->ops->getseqnonzerostructure)(mat,matstruct);CHKERRQ(ierr);
5787   ierr = PetscLogEventEnd(MAT_GetSeqNonzeroStructure,mat,0,0,0);CHKERRQ(ierr);
5788   PetscFunctionReturn(0);
5789 }
5790 
5791 #undef __FUNCT__
5792 #define __FUNCT__ "MatDestroySeqNonzeroStructure"
5793 /*@C
5794    MatDestroySeqNonzeroStructure - Destroys matrix obtained with MatGetSeqNonzeroStructure().
5795 
5796    Collective on Mat
5797 
5798    Input Parameters:
5799 .  mat - the matrix (note that this is a pointer to the array of matrices, just to match the calling
5800                        sequence of MatGetSequentialNonzeroStructure())
5801 
5802    Level: advanced
5803 
5804     Notes: Frees not only the matrices, but also the array that contains the matrices
5805 
5806 .seealso: MatGetSeqNonzeroStructure()
5807 @*/
5808 PetscErrorCode PETSCMAT_DLLEXPORT MatDestroySeqNonzeroStructure(Mat *mat)
5809 {
5810   PetscErrorCode ierr;
5811 
5812   PetscFunctionBegin;
5813   PetscValidPointer(mat,1);
5814   ierr = MatDestroy(*mat);CHKERRQ(ierr);
5815   PetscFunctionReturn(0);
5816 }
5817 
5818 #undef __FUNCT__
5819 #define __FUNCT__ "MatIncreaseOverlap"
5820 /*@
5821    MatIncreaseOverlap - Given a set of submatrices indicated by index sets,
5822    replaces the index sets by larger ones that represent submatrices with
5823    additional overlap.
5824 
5825    Collective on Mat
5826 
5827    Input Parameters:
5828 +  mat - the matrix
5829 .  n   - the number of index sets
5830 .  is  - the array of index sets (these index sets will changed during the call)
5831 -  ov  - the additional overlap requested
5832 
5833    Level: developer
5834 
5835    Concepts: overlap
5836    Concepts: ASM^computing overlap
5837 
5838 .seealso: MatGetSubMatrices()
5839 @*/
5840 PetscErrorCode PETSCMAT_DLLEXPORT MatIncreaseOverlap(Mat mat,PetscInt n,IS is[],PetscInt ov)
5841 {
5842   PetscErrorCode ierr;
5843 
5844   PetscFunctionBegin;
5845   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5846   PetscValidType(mat,1);
5847   if (n < 0) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Must have one or more domains, you have %D",n);
5848   if (n) {
5849     PetscValidPointer(is,3);
5850     PetscValidHeaderSpecific(*is,IS_CLASSID,3);
5851   }
5852   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
5853   if (mat->factortype)     SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
5854   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5855 
5856   if (!ov) PetscFunctionReturn(0);
5857   if (!mat->ops->increaseoverlap) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
5858   ierr = PetscLogEventBegin(MAT_IncreaseOverlap,mat,0,0,0);CHKERRQ(ierr);
5859   ierr = (*mat->ops->increaseoverlap)(mat,n,is,ov);CHKERRQ(ierr);
5860   ierr = PetscLogEventEnd(MAT_IncreaseOverlap,mat,0,0,0);CHKERRQ(ierr);
5861   PetscFunctionReturn(0);
5862 }
5863 
5864 #undef __FUNCT__
5865 #define __FUNCT__ "MatGetBlockSize"
5866 /*@
5867    MatGetBlockSize - Returns the matrix block size; useful especially for the
5868    block row and block diagonal formats.
5869 
5870    Not Collective
5871 
5872    Input Parameter:
5873 .  mat - the matrix
5874 
5875    Output Parameter:
5876 .  bs - block size
5877 
5878    Notes:
5879    Block row formats are MATSEQBAIJ, MATMPIBAIJ, MATSEQSBAIJ, MATMPISBAIJ
5880 
5881    Level: intermediate
5882 
5883    Concepts: matrices^block size
5884 
5885 .seealso: MatCreateSeqBAIJ(), MatCreateMPIBAIJ()
5886 @*/
5887 PetscErrorCode PETSCMAT_DLLEXPORT MatGetBlockSize(Mat mat,PetscInt *bs)
5888 {
5889   PetscErrorCode ierr;
5890 
5891   PetscFunctionBegin;
5892   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5893   PetscValidType(mat,1);
5894   PetscValidIntPointer(bs,2);
5895   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5896   *bs = mat->rmap->bs;
5897   PetscFunctionReturn(0);
5898 }
5899 
5900 #undef __FUNCT__
5901 #define __FUNCT__ "MatSetBlockSize"
5902 /*@
5903    MatSetBlockSize - Sets the matrix block size; for many matrix types you
5904      cannot use this and MUST set the blocksize when you preallocate the matrix
5905 
5906    Collective on Mat
5907 
5908    Input Parameters:
5909 +  mat - the matrix
5910 -  bs - block size
5911 
5912    Notes:
5913      For BAIJ matrices, this just checks that the block size agrees with the BAIJ size,
5914      it is not possible to change BAIJ block sizes after preallocation.
5915 
5916    Level: intermediate
5917 
5918    Concepts: matrices^block size
5919 
5920 .seealso: MatCreateSeqBAIJ(), MatCreateMPIBAIJ(), MatGetBlockSize()
5921 @*/
5922 PetscErrorCode PETSCMAT_DLLEXPORT MatSetBlockSize(Mat mat,PetscInt bs)
5923 {
5924   PetscErrorCode ierr;
5925 
5926   PetscFunctionBegin;
5927   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5928   PetscValidType(mat,1);
5929   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5930   if (bs < 1) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Block size %d, must be positive",bs);
5931   if (mat->ops->setblocksize) {
5932     ierr = (*mat->ops->setblocksize)(mat,bs);CHKERRQ(ierr);
5933   } else {
5934     SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_INCOMP,"Cannot set the blocksize for matrix type %s",((PetscObject)mat)->type_name);
5935   }
5936   PetscFunctionReturn(0);
5937 }
5938 
5939 #undef __FUNCT__
5940 #define __FUNCT__ "MatGetRowIJ"
5941 /*@C
5942     MatGetRowIJ - Returns the compressed row storage i and j indices for sequential matrices.
5943 
5944    Collective on Mat
5945 
5946     Input Parameters:
5947 +   mat - the matrix
5948 .   shift -  0 or 1 indicating we want the indices starting at 0 or 1
5949 .   symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
5950                 symmetrized
5951 -   inodecompressed - PETSC_TRUE or PETSC_FALSE  indicating if the nonzero structure of the
5952                  inodes or the nonzero elements is wanted. For BAIJ matrices the compressed version is
5953                  always used.
5954 
5955     Output Parameters:
5956 +   n - number of rows in the (possibly compressed) matrix
5957 .   ia - the row pointers [of length n+1]
5958 .   ja - the column indices
5959 -   done - indicates if the routine actually worked and returned appropriate ia[] and ja[] arrays; callers
5960            are responsible for handling the case when done == PETSC_FALSE and ia and ja are not set
5961 
5962     Level: developer
5963 
5964     Notes: You CANNOT change any of the ia[] or ja[] values.
5965 
5966            Use MatRestoreRowIJ() when you are finished accessing the ia[] and ja[] values
5967 
5968     Fortran Node
5969 
5970            In Fortran use
5971 $           PetscInt ia(1), ja(1)
5972 $           PetscOffset iia, jja
5973 $      call MatGetRowIJ(mat,shift,symmetric,inodecompressed,n,ia,iia,ja,jja,done,ierr)
5974 $
5975 $          or
5976 $
5977 $           PetscScalar, pointer :: xx_v(:)
5978 $    call  MatGetRowIJF90(mat,shift,symmetric,inodecompressed,n,ia,ja,done,ierr)
5979 
5980 
5981        Acess the ith and jth entries via ia(iia + i) and ja(jja + j)
5982 
5983 .seealso: MatGetColumnIJ(), MatRestoreRowIJ(), MatGetArray()
5984 @*/
5985 PetscErrorCode PETSCMAT_DLLEXPORT MatGetRowIJ(Mat mat,PetscInt shift,PetscTruth symmetric,PetscTruth inodecompressed,PetscInt *n,PetscInt *ia[],PetscInt* ja[],PetscTruth *done)
5986 {
5987   PetscErrorCode ierr;
5988 
5989   PetscFunctionBegin;
5990   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
5991   PetscValidType(mat,1);
5992   PetscValidIntPointer(n,4);
5993   if (ia) PetscValidIntPointer(ia,5);
5994   if (ja) PetscValidIntPointer(ja,6);
5995   PetscValidIntPointer(done,7);
5996   ierr = MatPreallocated(mat);CHKERRQ(ierr);
5997   if (!mat->ops->getrowij) *done = PETSC_FALSE;
5998   else {
5999     *done = PETSC_TRUE;
6000     ierr = PetscLogEventBegin(MAT_GetRowIJ,mat,0,0,0);CHKERRQ(ierr);
6001     ierr  = (*mat->ops->getrowij)(mat,shift,symmetric,inodecompressed,n,ia,ja,done);CHKERRQ(ierr);
6002     ierr = PetscLogEventEnd(MAT_GetRowIJ,mat,0,0,0);CHKERRQ(ierr);
6003   }
6004   PetscFunctionReturn(0);
6005 }
6006 
6007 #undef __FUNCT__
6008 #define __FUNCT__ "MatGetColumnIJ"
6009 /*@C
6010     MatGetColumnIJ - Returns the compressed column storage i and j indices for sequential matrices.
6011 
6012     Collective on Mat
6013 
6014     Input Parameters:
6015 +   mat - the matrix
6016 .   shift - 1 or zero indicating we want the indices starting at 0 or 1
6017 .   symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
6018                 symmetrized
6019 -   inodecompressed - PETSC_TRUE or PETSC_FALSE indicating if the nonzero structure of the
6020                  inodes or the nonzero elements is wanted. For BAIJ matrices the compressed version is
6021                  always used.
6022 
6023     Output Parameters:
6024 +   n - number of columns in the (possibly compressed) matrix
6025 .   ia - the column pointers
6026 .   ja - the row indices
6027 -   done - PETSC_TRUE or PETSC_FALSE, indicating whether the values have been returned
6028 
6029     Level: developer
6030 
6031 .seealso: MatGetRowIJ(), MatRestoreColumnIJ()
6032 @*/
6033 PetscErrorCode PETSCMAT_DLLEXPORT MatGetColumnIJ(Mat mat,PetscInt shift,PetscTruth symmetric,PetscTruth inodecompressed,PetscInt *n,PetscInt *ia[],PetscInt* ja[],PetscTruth *done)
6034 {
6035   PetscErrorCode ierr;
6036 
6037   PetscFunctionBegin;
6038   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6039   PetscValidType(mat,1);
6040   PetscValidIntPointer(n,4);
6041   if (ia) PetscValidIntPointer(ia,5);
6042   if (ja) PetscValidIntPointer(ja,6);
6043   PetscValidIntPointer(done,7);
6044   ierr = MatPreallocated(mat);CHKERRQ(ierr);
6045   if (!mat->ops->getcolumnij) *done = PETSC_FALSE;
6046   else {
6047     *done = PETSC_TRUE;
6048     ierr  = (*mat->ops->getcolumnij)(mat,shift,symmetric,inodecompressed,n,ia,ja,done);CHKERRQ(ierr);
6049   }
6050   PetscFunctionReturn(0);
6051 }
6052 
6053 #undef __FUNCT__
6054 #define __FUNCT__ "MatRestoreRowIJ"
6055 /*@C
6056     MatRestoreRowIJ - Call after you are completed with the ia,ja indices obtained with
6057     MatGetRowIJ().
6058 
6059     Collective on Mat
6060 
6061     Input Parameters:
6062 +   mat - the matrix
6063 .   shift - 1 or zero indicating we want the indices starting at 0 or 1
6064 .   symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
6065                 symmetrized
6066 -   inodecompressed -  PETSC_TRUE or PETSC_FALSE indicating if the nonzero structure of the
6067                  inodes or the nonzero elements is wanted. For BAIJ matrices the compressed version is
6068                  always used.
6069 
6070     Output Parameters:
6071 +   n - size of (possibly compressed) matrix
6072 .   ia - the row pointers
6073 .   ja - the column indices
6074 -   done - PETSC_TRUE or PETSC_FALSE indicated that the values have been returned
6075 
6076     Level: developer
6077 
6078 .seealso: MatGetRowIJ(), MatRestoreColumnIJ()
6079 @*/
6080 PetscErrorCode PETSCMAT_DLLEXPORT MatRestoreRowIJ(Mat mat,PetscInt shift,PetscTruth symmetric,PetscTruth inodecompressed,PetscInt *n,PetscInt *ia[],PetscInt* ja[],PetscTruth *done)
6081 {
6082   PetscErrorCode ierr;
6083 
6084   PetscFunctionBegin;
6085   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6086   PetscValidType(mat,1);
6087   if (ia) PetscValidIntPointer(ia,5);
6088   if (ja) PetscValidIntPointer(ja,6);
6089   PetscValidIntPointer(done,7);
6090   ierr = MatPreallocated(mat);CHKERRQ(ierr);
6091 
6092   if (!mat->ops->restorerowij) *done = PETSC_FALSE;
6093   else {
6094     *done = PETSC_TRUE;
6095     ierr  = (*mat->ops->restorerowij)(mat,shift,symmetric,inodecompressed,n,ia,ja,done);CHKERRQ(ierr);
6096   }
6097   PetscFunctionReturn(0);
6098 }
6099 
6100 #undef __FUNCT__
6101 #define __FUNCT__ "MatRestoreColumnIJ"
6102 /*@C
6103     MatRestoreColumnIJ - Call after you are completed with the ia,ja indices obtained with
6104     MatGetColumnIJ().
6105 
6106     Collective on Mat
6107 
6108     Input Parameters:
6109 +   mat - the matrix
6110 .   shift - 1 or zero indicating we want the indices starting at 0 or 1
6111 -   symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
6112                 symmetrized
6113 -   inodecompressed - PETSC_TRUE or PETSC_FALSE indicating if the nonzero structure of the
6114                  inodes or the nonzero elements is wanted. For BAIJ matrices the compressed version is
6115                  always used.
6116 
6117     Output Parameters:
6118 +   n - size of (possibly compressed) matrix
6119 .   ia - the column pointers
6120 .   ja - the row indices
6121 -   done - PETSC_TRUE or PETSC_FALSE indicated that the values have been returned
6122 
6123     Level: developer
6124 
6125 .seealso: MatGetColumnIJ(), MatRestoreRowIJ()
6126 @*/
6127 PetscErrorCode PETSCMAT_DLLEXPORT MatRestoreColumnIJ(Mat mat,PetscInt shift,PetscTruth symmetric,PetscTruth inodecompressed,PetscInt *n,PetscInt *ia[],PetscInt* ja[],PetscTruth *done)
6128 {
6129   PetscErrorCode ierr;
6130 
6131   PetscFunctionBegin;
6132   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6133   PetscValidType(mat,1);
6134   if (ia) PetscValidIntPointer(ia,5);
6135   if (ja) PetscValidIntPointer(ja,6);
6136   PetscValidIntPointer(done,7);
6137   ierr = MatPreallocated(mat);CHKERRQ(ierr);
6138 
6139   if (!mat->ops->restorecolumnij) *done = PETSC_FALSE;
6140   else {
6141     *done = PETSC_TRUE;
6142     ierr  = (*mat->ops->restorecolumnij)(mat,shift,symmetric,inodecompressed,n,ia,ja,done);CHKERRQ(ierr);
6143   }
6144   PetscFunctionReturn(0);
6145 }
6146 
6147 #undef __FUNCT__
6148 #define __FUNCT__ "MatColoringPatch"
6149 /*@C
6150     MatColoringPatch -Used inside matrix coloring routines that
6151     use MatGetRowIJ() and/or MatGetColumnIJ().
6152 
6153     Collective on Mat
6154 
6155     Input Parameters:
6156 +   mat - the matrix
6157 .   ncolors - max color value
6158 .   n   - number of entries in colorarray
6159 -   colorarray - array indicating color for each column
6160 
6161     Output Parameters:
6162 .   iscoloring - coloring generated using colorarray information
6163 
6164     Level: developer
6165 
6166 .seealso: MatGetRowIJ(), MatGetColumnIJ()
6167 
6168 @*/
6169 PetscErrorCode PETSCMAT_DLLEXPORT MatColoringPatch(Mat mat,PetscInt ncolors,PetscInt n,ISColoringValue colorarray[],ISColoring *iscoloring)
6170 {
6171   PetscErrorCode ierr;
6172 
6173   PetscFunctionBegin;
6174   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6175   PetscValidType(mat,1);
6176   PetscValidIntPointer(colorarray,4);
6177   PetscValidPointer(iscoloring,5);
6178   ierr = MatPreallocated(mat);CHKERRQ(ierr);
6179 
6180   if (!mat->ops->coloringpatch){
6181     ierr = ISColoringCreate(((PetscObject)mat)->comm,ncolors,n,colorarray,iscoloring);CHKERRQ(ierr);
6182   } else {
6183     ierr = (*mat->ops->coloringpatch)(mat,ncolors,n,colorarray,iscoloring);CHKERRQ(ierr);
6184   }
6185   PetscFunctionReturn(0);
6186 }
6187 
6188 
6189 #undef __FUNCT__
6190 #define __FUNCT__ "MatSetUnfactored"
6191 /*@
6192    MatSetUnfactored - Resets a factored matrix to be treated as unfactored.
6193 
6194    Collective on Mat
6195 
6196    Input Parameter:
6197 .  mat - the factored matrix to be reset
6198 
6199    Notes:
6200    This routine should be used only with factored matrices formed by in-place
6201    factorization via ILU(0) (or by in-place LU factorization for the MATSEQDENSE
6202    format).  This option can save memory, for example, when solving nonlinear
6203    systems with a matrix-free Newton-Krylov method and a matrix-based, in-place
6204    ILU(0) preconditioner.
6205 
6206    Note that one can specify in-place ILU(0) factorization by calling
6207 .vb
6208      PCType(pc,PCILU);
6209      PCFactorSeUseInPlace(pc);
6210 .ve
6211    or by using the options -pc_type ilu -pc_factor_in_place
6212 
6213    In-place factorization ILU(0) can also be used as a local
6214    solver for the blocks within the block Jacobi or additive Schwarz
6215    methods (runtime option: -sub_pc_factor_in_place).  See the discussion
6216    of these preconditioners in the users manual for details on setting
6217    local solver options.
6218 
6219    Most users should employ the simplified KSP interface for linear solvers
6220    instead of working directly with matrix algebra routines such as this.
6221    See, e.g., KSPCreate().
6222 
6223    Level: developer
6224 
6225 .seealso: PCFactorSetUseInPlace()
6226 
6227    Concepts: matrices^unfactored
6228 
6229 @*/
6230 PetscErrorCode PETSCMAT_DLLEXPORT MatSetUnfactored(Mat mat)
6231 {
6232   PetscErrorCode ierr;
6233 
6234   PetscFunctionBegin;
6235   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6236   PetscValidType(mat,1);
6237   ierr = MatPreallocated(mat);CHKERRQ(ierr);
6238   mat->factortype = MAT_FACTOR_NONE;
6239   if (!mat->ops->setunfactored) PetscFunctionReturn(0);
6240   ierr = (*mat->ops->setunfactored)(mat);CHKERRQ(ierr);
6241   PetscFunctionReturn(0);
6242 }
6243 
6244 /*MC
6245     MatGetArrayF90 - Accesses a matrix array from Fortran90.
6246 
6247     Synopsis:
6248     MatGetArrayF90(Mat x,{Scalar, pointer :: xx_v(:)},integer ierr)
6249 
6250     Not collective
6251 
6252     Input Parameter:
6253 .   x - matrix
6254 
6255     Output Parameters:
6256 +   xx_v - the Fortran90 pointer to the array
6257 -   ierr - error code
6258 
6259     Example of Usage:
6260 .vb
6261       PetscScalar, pointer xx_v(:)
6262       ....
6263       call MatGetArrayF90(x,xx_v,ierr)
6264       a = xx_v(3)
6265       call MatRestoreArrayF90(x,xx_v,ierr)
6266 .ve
6267 
6268     Notes:
6269     Not yet supported for all F90 compilers
6270 
6271     Level: advanced
6272 
6273 .seealso:  MatRestoreArrayF90(), MatGetArray(), MatRestoreArray()
6274 
6275     Concepts: matrices^accessing array
6276 
6277 M*/
6278 
6279 /*MC
6280     MatRestoreArrayF90 - Restores a matrix array that has been
6281     accessed with MatGetArrayF90().
6282 
6283     Synopsis:
6284     MatRestoreArrayF90(Mat x,{Scalar, pointer :: xx_v(:)},integer ierr)
6285 
6286     Not collective
6287 
6288     Input Parameters:
6289 +   x - matrix
6290 -   xx_v - the Fortran90 pointer to the array
6291 
6292     Output Parameter:
6293 .   ierr - error code
6294 
6295     Example of Usage:
6296 .vb
6297        PetscScalar, pointer xx_v(:)
6298        ....
6299        call MatGetArrayF90(x,xx_v,ierr)
6300        a = xx_v(3)
6301        call MatRestoreArrayF90(x,xx_v,ierr)
6302 .ve
6303 
6304     Notes:
6305     Not yet supported for all F90 compilers
6306 
6307     Level: advanced
6308 
6309 .seealso:  MatGetArrayF90(), MatGetArray(), MatRestoreArray()
6310 
6311 M*/
6312 
6313 
6314 #undef __FUNCT__
6315 #define __FUNCT__ "MatGetSubMatrix"
6316 /*@
6317     MatGetSubMatrix - Gets a single submatrix on the same number of processors
6318                       as the original matrix.
6319 
6320     Collective on Mat
6321 
6322     Input Parameters:
6323 +   mat - the original matrix
6324 .   isrow - parallel IS containing the rows this processor should obtain
6325 .   iscol - parallel IS containing all columns you wish to keep. Each process should list the columns that will be in IT's "diagonal part" in the new matrix.
6326 -   cll - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX
6327 
6328     Output Parameter:
6329 .   newmat - the new submatrix, of the same type as the old
6330 
6331     Level: advanced
6332 
6333     Notes:
6334     The submatrix will be able to be multiplied with vectors using the same layout as iscol.
6335 
6336     The rows in isrow will be sorted into the same order as the original matrix on each process.
6337 
6338       The first time this is called you should use a cll of MAT_INITIAL_MATRIX,
6339    the MatGetSubMatrix() routine will create the newmat for you. Any additional calls
6340    to this routine with a mat of the same nonzero structure and with a call of MAT_REUSE_MATRIX
6341    will reuse the matrix generated the first time.  You should call MatDestroy() on newmat when
6342    you are finished using it.
6343 
6344     The communicator of the newly obtained matrix is ALWAYS the same as the communicator of
6345     the input matrix.
6346 
6347     If iscol is PETSC_NULL then all columns are obtained (not supported in Fortran).
6348 
6349    Example usage:
6350    Consider the following 8x8 matrix with 34 non-zero values, that is
6351    assembled across 3 processors. Lets assume that proc0 owns 3 rows,
6352    proc1 owns 3 rows, proc2 owns 2 rows. This division can be shown
6353    as follows:
6354 
6355 .vb
6356             1  2  0  |  0  3  0  |  0  4
6357     Proc0   0  5  6  |  7  0  0  |  8  0
6358             9  0 10  | 11  0  0  | 12  0
6359     -------------------------------------
6360            13  0 14  | 15 16 17  |  0  0
6361     Proc1   0 18  0  | 19 20 21  |  0  0
6362             0  0  0  | 22 23  0  | 24  0
6363     -------------------------------------
6364     Proc2  25 26 27  |  0  0 28  | 29  0
6365            30  0  0  | 31 32 33  |  0 34
6366 .ve
6367 
6368     Suppose isrow = [0 1 | 4 | 5 6] and iscol = [1 2 | 3 4 5 | 6].  The resulting submatrix is
6369 
6370 .vb
6371             2  0  |  0  3  0  |  0
6372     Proc0   5  6  |  7  0  0  |  8
6373     -------------------------------
6374     Proc1  18  0  | 19 20 21  |  0
6375     -------------------------------
6376     Proc2  26 27  |  0  0 28  | 29
6377             0  0  | 31 32 33  |  0
6378 .ve
6379 
6380 
6381     Concepts: matrices^submatrices
6382 
6383 .seealso: MatGetSubMatrices()
6384 @*/
6385 PetscErrorCode PETSCMAT_DLLEXPORT MatGetSubMatrix(Mat mat,IS isrow,IS iscol,MatReuse cll,Mat *newmat)
6386 {
6387   PetscErrorCode ierr;
6388   PetscMPIInt    size;
6389   Mat            *local;
6390   IS             iscoltmp;
6391 
6392   PetscFunctionBegin;
6393   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6394   PetscValidHeaderSpecific(isrow,IS_CLASSID,2);
6395   if (iscol) PetscValidHeaderSpecific(iscol,IS_CLASSID,3);
6396   PetscValidPointer(newmat,5);
6397   if (cll == MAT_REUSE_MATRIX) PetscValidHeaderSpecific(*newmat,MAT_CLASSID,5);
6398   PetscValidType(mat,1);
6399   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
6400   ierr = MatPreallocated(mat);CHKERRQ(ierr);
6401   ierr = MPI_Comm_size(((PetscObject)mat)->comm,&size);CHKERRQ(ierr);
6402 
6403   if (!iscol) {
6404     ierr = ISCreateStride(((PetscObject)mat)->comm,mat->cmap->n,mat->cmap->rstart,1,&iscoltmp);CHKERRQ(ierr);
6405   } else {
6406     iscoltmp = iscol;
6407   }
6408 
6409   /* if original matrix is on just one processor then use submatrix generated */
6410   if (mat->ops->getsubmatrices && !mat->ops->getsubmatrix && size == 1 && cll == MAT_REUSE_MATRIX) {
6411     ierr = MatGetSubMatrices(mat,1,&isrow,&iscoltmp,MAT_REUSE_MATRIX,&newmat);CHKERRQ(ierr);
6412     if (!iscol) {ierr = ISDestroy(iscoltmp);CHKERRQ(ierr);}
6413     PetscFunctionReturn(0);
6414   } else if (mat->ops->getsubmatrices && !mat->ops->getsubmatrix && size == 1) {
6415     ierr    = MatGetSubMatrices(mat,1,&isrow,&iscoltmp,MAT_INITIAL_MATRIX,&local);CHKERRQ(ierr);
6416     *newmat = *local;
6417     ierr    = PetscFree(local);CHKERRQ(ierr);
6418     if (!iscol) {ierr = ISDestroy(iscoltmp);CHKERRQ(ierr);}
6419     PetscFunctionReturn(0);
6420   } else if (!mat->ops->getsubmatrix) {
6421     /* Create a new matrix type that implements the operation using the full matrix */
6422     switch (cll) {
6423       case MAT_INITIAL_MATRIX:
6424         ierr = MatCreateSubMatrix(mat,isrow,iscoltmp,newmat);CHKERRQ(ierr);
6425         break;
6426       case MAT_REUSE_MATRIX:
6427         ierr = MatSubMatrixUpdate(*newmat,mat,isrow,iscoltmp);CHKERRQ(ierr);
6428         break;
6429       default: SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_OUTOFRANGE,"Invalid MatReuse, must be either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX");
6430     }
6431     if (!iscol) {ierr = ISDestroy(iscoltmp);CHKERRQ(ierr);}
6432     PetscFunctionReturn(0);
6433   }
6434 
6435   if (!mat->ops->getsubmatrix) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
6436   ierr = (*mat->ops->getsubmatrix)(mat,isrow,iscoltmp,cll,newmat);CHKERRQ(ierr);
6437   if (!iscol) {ierr = ISDestroy(iscoltmp);CHKERRQ(ierr);}
6438   ierr = PetscObjectStateIncrease((PetscObject)*newmat);CHKERRQ(ierr);
6439   PetscFunctionReturn(0);
6440 }
6441 
6442 #undef __FUNCT__
6443 #define __FUNCT__ "MatStashSetInitialSize"
6444 /*@
6445    MatStashSetInitialSize - sets the sizes of the matrix stash, that is
6446    used during the assembly process to store values that belong to
6447    other processors.
6448 
6449    Not Collective
6450 
6451    Input Parameters:
6452 +  mat   - the matrix
6453 .  size  - the initial size of the stash.
6454 -  bsize - the initial size of the block-stash(if used).
6455 
6456    Options Database Keys:
6457 +   -matstash_initial_size <size> or <size0,size1,...sizep-1>
6458 -   -matstash_block_initial_size <bsize>  or <bsize0,bsize1,...bsizep-1>
6459 
6460    Level: intermediate
6461 
6462    Notes:
6463      The block-stash is used for values set with MatSetValuesBlocked() while
6464      the stash is used for values set with MatSetValues()
6465 
6466      Run with the option -info and look for output of the form
6467      MatAssemblyBegin_MPIXXX:Stash has MM entries, uses nn mallocs.
6468      to determine the appropriate value, MM, to use for size and
6469      MatAssemblyBegin_MPIXXX:Block-Stash has BMM entries, uses nn mallocs.
6470      to determine the value, BMM to use for bsize
6471 
6472    Concepts: stash^setting matrix size
6473    Concepts: matrices^stash
6474 
6475 .seealso: MatAssemblyBegin(), MatAssemblyEnd(), Mat, MatStashGetInfo()
6476 
6477 @*/
6478 PetscErrorCode PETSCMAT_DLLEXPORT MatStashSetInitialSize(Mat mat,PetscInt size, PetscInt bsize)
6479 {
6480   PetscErrorCode ierr;
6481 
6482   PetscFunctionBegin;
6483   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6484   PetscValidType(mat,1);
6485   ierr = MatStashSetInitialSize_Private(&mat->stash,size);CHKERRQ(ierr);
6486   ierr = MatStashSetInitialSize_Private(&mat->bstash,bsize);CHKERRQ(ierr);
6487   PetscFunctionReturn(0);
6488 }
6489 
6490 #undef __FUNCT__
6491 #define __FUNCT__ "MatInterpolateAdd"
6492 /*@
6493    MatInterpolateAdd - w = y + A*x or A'*x depending on the shape of
6494      the matrix
6495 
6496    Collective on Mat
6497 
6498    Input Parameters:
6499 +  mat   - the matrix
6500 .  x,y - the vectors
6501 -  w - where the result is stored
6502 
6503    Level: intermediate
6504 
6505    Notes:
6506     w may be the same vector as y.
6507 
6508     This allows one to use either the restriction or interpolation (its transpose)
6509     matrix to do the interpolation
6510 
6511     Concepts: interpolation
6512 
6513 .seealso: MatMultAdd(), MatMultTransposeAdd(), MatRestrict()
6514 
6515 @*/
6516 PetscErrorCode PETSCMAT_DLLEXPORT MatInterpolateAdd(Mat A,Vec x,Vec y,Vec w)
6517 {
6518   PetscErrorCode ierr;
6519   PetscInt       M,N;
6520 
6521   PetscFunctionBegin;
6522   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
6523   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
6524   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
6525   PetscValidHeaderSpecific(w,VEC_CLASSID,4);
6526   PetscValidType(A,1);
6527   ierr = MatPreallocated(A);CHKERRQ(ierr);
6528   ierr = MatGetSize(A,&M,&N);CHKERRQ(ierr);
6529   if (N > M) {
6530     ierr = MatMultTransposeAdd(A,x,y,w);CHKERRQ(ierr);
6531   } else {
6532     ierr = MatMultAdd(A,x,y,w);CHKERRQ(ierr);
6533   }
6534   PetscFunctionReturn(0);
6535 }
6536 
6537 #undef __FUNCT__
6538 #define __FUNCT__ "MatInterpolate"
6539 /*@
6540    MatInterpolate - y = A*x or A'*x depending on the shape of
6541      the matrix
6542 
6543    Collective on Mat
6544 
6545    Input Parameters:
6546 +  mat   - the matrix
6547 -  x,y - the vectors
6548 
6549    Level: intermediate
6550 
6551    Notes:
6552     This allows one to use either the restriction or interpolation (its transpose)
6553     matrix to do the interpolation
6554 
6555    Concepts: matrices^interpolation
6556 
6557 .seealso: MatMultAdd(), MatMultTransposeAdd(), MatRestrict()
6558 
6559 @*/
6560 PetscErrorCode PETSCMAT_DLLEXPORT MatInterpolate(Mat A,Vec x,Vec y)
6561 {
6562   PetscErrorCode ierr;
6563   PetscInt       M,N;
6564 
6565   PetscFunctionBegin;
6566   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
6567   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
6568   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
6569   PetscValidType(A,1);
6570   ierr = MatPreallocated(A);CHKERRQ(ierr);
6571   ierr = MatGetSize(A,&M,&N);CHKERRQ(ierr);
6572   if (N > M) {
6573     ierr = MatMultTranspose(A,x,y);CHKERRQ(ierr);
6574   } else {
6575     ierr = MatMult(A,x,y);CHKERRQ(ierr);
6576   }
6577   PetscFunctionReturn(0);
6578 }
6579 
6580 #undef __FUNCT__
6581 #define __FUNCT__ "MatRestrict"
6582 /*@
6583    MatRestrict - y = A*x or A'*x
6584 
6585    Collective on Mat
6586 
6587    Input Parameters:
6588 +  mat   - the matrix
6589 -  x,y - the vectors
6590 
6591    Level: intermediate
6592 
6593    Notes:
6594     This allows one to use either the restriction or interpolation (its transpose)
6595     matrix to do the restriction
6596 
6597    Concepts: matrices^restriction
6598 
6599 .seealso: MatMultAdd(), MatMultTransposeAdd(), MatInterpolate()
6600 
6601 @*/
6602 PetscErrorCode PETSCMAT_DLLEXPORT MatRestrict(Mat A,Vec x,Vec y)
6603 {
6604   PetscErrorCode ierr;
6605   PetscInt       M,N;
6606 
6607   PetscFunctionBegin;
6608   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
6609   PetscValidHeaderSpecific(x,VEC_CLASSID,2);
6610   PetscValidHeaderSpecific(y,VEC_CLASSID,3);
6611   PetscValidType(A,1);
6612   ierr = MatPreallocated(A);CHKERRQ(ierr);
6613 
6614   ierr = MatGetSize(A,&M,&N);CHKERRQ(ierr);
6615   if (N > M) {
6616     ierr = MatMult(A,x,y);CHKERRQ(ierr);
6617   } else {
6618     ierr = MatMultTranspose(A,x,y);CHKERRQ(ierr);
6619   }
6620   PetscFunctionReturn(0);
6621 }
6622 
6623 #undef __FUNCT__
6624 #define __FUNCT__ "MatNullSpaceAttach"
6625 /*@
6626    MatNullSpaceAttach - attaches a null space to a matrix.
6627         This null space will be removed from the resulting vector whenever
6628         MatMult() is called
6629 
6630    Collective on Mat
6631 
6632    Input Parameters:
6633 +  mat - the matrix
6634 -  nullsp - the null space object
6635 
6636    Level: developer
6637 
6638    Notes:
6639       Overwrites any previous null space that may have been attached
6640 
6641    Concepts: null space^attaching to matrix
6642 
6643 .seealso: MatCreate(), MatNullSpaceCreate()
6644 @*/
6645 PetscErrorCode PETSCMAT_DLLEXPORT MatNullSpaceAttach(Mat mat,MatNullSpace nullsp)
6646 {
6647   PetscErrorCode ierr;
6648 
6649   PetscFunctionBegin;
6650   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6651   PetscValidType(mat,1);
6652   PetscValidHeaderSpecific(nullsp,MAT_NULLSPACE_CLASSID,2);
6653   ierr = MatPreallocated(mat);CHKERRQ(ierr);
6654   ierr = PetscObjectReference((PetscObject)nullsp);CHKERRQ(ierr);
6655   if (mat->nullsp) { ierr = MatNullSpaceDestroy(mat->nullsp);CHKERRQ(ierr); }
6656   mat->nullsp = nullsp;
6657   PetscFunctionReturn(0);
6658 }
6659 
6660 #undef __FUNCT__
6661 #define __FUNCT__ "MatICCFactor"
6662 /*@C
6663    MatICCFactor - Performs in-place incomplete Cholesky factorization of matrix.
6664 
6665    Collective on Mat
6666 
6667    Input Parameters:
6668 +  mat - the matrix
6669 .  row - row/column permutation
6670 .  fill - expected fill factor >= 1.0
6671 -  level - level of fill, for ICC(k)
6672 
6673    Notes:
6674    Probably really in-place only when level of fill is zero, otherwise allocates
6675    new space to store factored matrix and deletes previous memory.
6676 
6677    Most users should employ the simplified KSP interface for linear solvers
6678    instead of working directly with matrix algebra routines such as this.
6679    See, e.g., KSPCreate().
6680 
6681    Level: developer
6682 
6683    Concepts: matrices^incomplete Cholesky factorization
6684    Concepts: Cholesky factorization
6685 
6686 .seealso: MatICCFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor()
6687 
6688     Developer Note: fortran interface is not autogenerated as the f90
6689     interface defintion cannot be generated correctly [due to MatFactorInfo]
6690 
6691 @*/
6692 PetscErrorCode PETSCMAT_DLLEXPORT MatICCFactor(Mat mat,IS row,const MatFactorInfo* info)
6693 {
6694   PetscErrorCode ierr;
6695 
6696   PetscFunctionBegin;
6697   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6698   PetscValidType(mat,1);
6699   if (row) PetscValidHeaderSpecific(row,IS_CLASSID,2);
6700   PetscValidPointer(info,3);
6701   if (mat->rmap->N != mat->cmap->N) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONG,"matrix must be square");
6702   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
6703   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
6704   if (!mat->ops->iccfactor) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
6705   ierr = MatPreallocated(mat);CHKERRQ(ierr);
6706   ierr = (*mat->ops->iccfactor)(mat,row,info);CHKERRQ(ierr);
6707   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
6708   PetscFunctionReturn(0);
6709 }
6710 
6711 #undef __FUNCT__
6712 #define __FUNCT__ "MatSetValuesAdic"
6713 /*@
6714    MatSetValuesAdic - Sets values computed with ADIC automatic differentiation into a matrix.
6715 
6716    Not Collective
6717 
6718    Input Parameters:
6719 +  mat - the matrix
6720 -  v - the values compute with ADIC
6721 
6722    Level: developer
6723 
6724    Notes:
6725      Must call MatSetColoring() before using this routine. Also this matrix must already
6726      have its nonzero pattern determined.
6727 
6728 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(),
6729           MatSetValues(), MatSetColoring(), MatSetValuesAdifor()
6730 @*/
6731 PetscErrorCode PETSCMAT_DLLEXPORT MatSetValuesAdic(Mat mat,void *v)
6732 {
6733   PetscErrorCode ierr;
6734 
6735   PetscFunctionBegin;
6736   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6737   PetscValidType(mat,1);
6738   PetscValidPointer(mat,2);
6739 
6740   if (!mat->assembled) {
6741     SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Matrix must be already assembled");
6742   }
6743   ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
6744   if (!mat->ops->setvaluesadic) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
6745   ierr = (*mat->ops->setvaluesadic)(mat,v);CHKERRQ(ierr);
6746   ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
6747   ierr = MatView_Private(mat);CHKERRQ(ierr);
6748   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
6749   PetscFunctionReturn(0);
6750 }
6751 
6752 
6753 #undef __FUNCT__
6754 #define __FUNCT__ "MatSetColoring"
6755 /*@
6756    MatSetColoring - Sets a coloring used by calls to MatSetValuesAdic()
6757 
6758    Not Collective
6759 
6760    Input Parameters:
6761 +  mat - the matrix
6762 -  coloring - the coloring
6763 
6764    Level: developer
6765 
6766 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(),
6767           MatSetValues(), MatSetValuesAdic()
6768 @*/
6769 PetscErrorCode PETSCMAT_DLLEXPORT MatSetColoring(Mat mat,ISColoring coloring)
6770 {
6771   PetscErrorCode ierr;
6772 
6773   PetscFunctionBegin;
6774   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6775   PetscValidType(mat,1);
6776   PetscValidPointer(coloring,2);
6777 
6778   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Matrix must be already assembled");
6779   if (!mat->ops->setcoloring) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
6780   ierr = (*mat->ops->setcoloring)(mat,coloring);CHKERRQ(ierr);
6781   PetscFunctionReturn(0);
6782 }
6783 
6784 #undef __FUNCT__
6785 #define __FUNCT__ "MatSetValuesAdifor"
6786 /*@
6787    MatSetValuesAdifor - Sets values computed with automatic differentiation into a matrix.
6788 
6789    Not Collective
6790 
6791    Input Parameters:
6792 +  mat - the matrix
6793 .  nl - leading dimension of v
6794 -  v - the values compute with ADIFOR
6795 
6796    Level: developer
6797 
6798    Notes:
6799      Must call MatSetColoring() before using this routine. Also this matrix must already
6800      have its nonzero pattern determined.
6801 
6802 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(),
6803           MatSetValues(), MatSetColoring()
6804 @*/
6805 PetscErrorCode PETSCMAT_DLLEXPORT MatSetValuesAdifor(Mat mat,PetscInt nl,void *v)
6806 {
6807   PetscErrorCode ierr;
6808 
6809   PetscFunctionBegin;
6810   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6811   PetscValidType(mat,1);
6812   PetscValidPointer(v,3);
6813 
6814   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Matrix must be already assembled");
6815   ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
6816   if (!mat->ops->setvaluesadifor) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
6817   ierr = (*mat->ops->setvaluesadifor)(mat,nl,v);CHKERRQ(ierr);
6818   ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr);
6819   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
6820   PetscFunctionReturn(0);
6821 }
6822 
6823 #undef __FUNCT__
6824 #define __FUNCT__ "MatDiagonalScaleLocal"
6825 /*@
6826    MatDiagonalScaleLocal - Scales columns of a matrix given the scaling values including the
6827          ghosted ones.
6828 
6829    Not Collective
6830 
6831    Input Parameters:
6832 +  mat - the matrix
6833 -  diag = the diagonal values, including ghost ones
6834 
6835    Level: developer
6836 
6837    Notes: Works only for MPIAIJ and MPIBAIJ matrices
6838 
6839 .seealso: MatDiagonalScale()
6840 @*/
6841 PetscErrorCode PETSCMAT_DLLEXPORT MatDiagonalScaleLocal(Mat mat,Vec diag)
6842 {
6843   PetscErrorCode ierr;
6844   PetscMPIInt    size;
6845 
6846   PetscFunctionBegin;
6847   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6848   PetscValidHeaderSpecific(diag,VEC_CLASSID,2);
6849   PetscValidType(mat,1);
6850 
6851   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Matrix must be already assembled");
6852   ierr = PetscLogEventBegin(MAT_Scale,mat,0,0,0);CHKERRQ(ierr);
6853   ierr = MPI_Comm_size(((PetscObject)mat)->comm,&size);CHKERRQ(ierr);
6854   if (size == 1) {
6855     PetscInt n,m;
6856     ierr = VecGetSize(diag,&n);CHKERRQ(ierr);
6857     ierr = MatGetSize(mat,0,&m);CHKERRQ(ierr);
6858     if (m == n) {
6859       ierr = MatDiagonalScale(mat,0,diag);CHKERRQ(ierr);
6860     } else {
6861       SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"Only supported for sequential matrices when no ghost points/periodic conditions");
6862     }
6863   } else {
6864     PetscErrorCode (*f)(Mat,Vec);
6865     ierr = PetscObjectQueryFunction((PetscObject)mat,"MatDiagonalScaleLocal_C",(void (**)(void))&f);CHKERRQ(ierr);
6866     if (f) {
6867       ierr = (*f)(mat,diag);CHKERRQ(ierr);
6868     } else {
6869       SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"Only supported for MPIAIJ and MPIBAIJ parallel matrices");
6870     }
6871   }
6872   ierr = PetscLogEventEnd(MAT_Scale,mat,0,0,0);CHKERRQ(ierr);
6873   ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr);
6874   PetscFunctionReturn(0);
6875 }
6876 
6877 #undef __FUNCT__
6878 #define __FUNCT__ "MatGetInertia"
6879 /*@
6880    MatGetInertia - Gets the inertia from a factored matrix
6881 
6882    Collective on Mat
6883 
6884    Input Parameter:
6885 .  mat - the matrix
6886 
6887    Output Parameters:
6888 +   nneg - number of negative eigenvalues
6889 .   nzero - number of zero eigenvalues
6890 -   npos - number of positive eigenvalues
6891 
6892    Level: advanced
6893 
6894    Notes: Matrix must have been factored by MatCholeskyFactor()
6895 
6896 
6897 @*/
6898 PetscErrorCode PETSCMAT_DLLEXPORT MatGetInertia(Mat mat,PetscInt *nneg,PetscInt *nzero,PetscInt *npos)
6899 {
6900   PetscErrorCode ierr;
6901 
6902   PetscFunctionBegin;
6903   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6904   PetscValidType(mat,1);
6905   if (!mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
6906   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Numeric factor mat is not assembled");
6907   if (!mat->ops->getinertia) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
6908   ierr = (*mat->ops->getinertia)(mat,nneg,nzero,npos);CHKERRQ(ierr);
6909   PetscFunctionReturn(0);
6910 }
6911 
6912 /* ----------------------------------------------------------------*/
6913 #undef __FUNCT__
6914 #define __FUNCT__ "MatSolves"
6915 /*@C
6916    MatSolves - Solves A x = b, given a factored matrix, for a collection of vectors
6917 
6918    Collective on Mat and Vecs
6919 
6920    Input Parameters:
6921 +  mat - the factored matrix
6922 -  b - the right-hand-side vectors
6923 
6924    Output Parameter:
6925 .  x - the result vectors
6926 
6927    Notes:
6928    The vectors b and x cannot be the same.  I.e., one cannot
6929    call MatSolves(A,x,x).
6930 
6931    Notes:
6932    Most users should employ the simplified KSP interface for linear solvers
6933    instead of working directly with matrix algebra routines such as this.
6934    See, e.g., KSPCreate().
6935 
6936    Level: developer
6937 
6938    Concepts: matrices^triangular solves
6939 
6940 .seealso: MatSolveAdd(), MatSolveTranspose(), MatSolveTransposeAdd(), MatSolve()
6941 @*/
6942 PetscErrorCode PETSCMAT_DLLEXPORT MatSolves(Mat mat,Vecs b,Vecs x)
6943 {
6944   PetscErrorCode ierr;
6945 
6946   PetscFunctionBegin;
6947   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
6948   PetscValidType(mat,1);
6949   if (x == b) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_IDN,"x and b must be different vectors");
6950   if (!mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix");
6951   if (!mat->rmap->N && !mat->cmap->N) PetscFunctionReturn(0);
6952 
6953   if (!mat->ops->solves) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
6954   ierr = MatPreallocated(mat);CHKERRQ(ierr);
6955   ierr = PetscLogEventBegin(MAT_Solves,mat,0,0,0);CHKERRQ(ierr);
6956   ierr = (*mat->ops->solves)(mat,b,x);CHKERRQ(ierr);
6957   ierr = PetscLogEventEnd(MAT_Solves,mat,0,0,0);CHKERRQ(ierr);
6958   PetscFunctionReturn(0);
6959 }
6960 
6961 #undef __FUNCT__
6962 #define __FUNCT__ "MatIsSymmetric"
6963 /*@
6964    MatIsSymmetric - Test whether a matrix is symmetric
6965 
6966    Collective on Mat
6967 
6968    Input Parameter:
6969 +  A - the matrix to test
6970 -  tol - difference between value and its transpose less than this amount counts as equal (use 0.0 for exact transpose)
6971 
6972    Output Parameters:
6973 .  flg - the result
6974 
6975    Level: intermediate
6976 
6977    Concepts: matrix^symmetry
6978 
6979 .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), MatIsSymmetricKnown()
6980 @*/
6981 PetscErrorCode PETSCMAT_DLLEXPORT MatIsSymmetric(Mat A,PetscReal tol,PetscTruth *flg)
6982 {
6983   PetscErrorCode ierr;
6984 
6985   PetscFunctionBegin;
6986   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
6987   PetscValidPointer(flg,2);
6988 
6989   if (!A->symmetric_set) {
6990     if (!A->ops->issymmetric) {
6991       const MatType mattype;
6992       ierr = MatGetType(A,&mattype);CHKERRQ(ierr);
6993       SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Matrix of type <%s> does not support checking for symmetric",mattype);
6994     }
6995     ierr = (*A->ops->issymmetric)(A,tol,flg);CHKERRQ(ierr);
6996     if (!tol) {
6997       A->symmetric_set = PETSC_TRUE;
6998       A->symmetric = *flg;
6999       if (A->symmetric) {
7000 	A->structurally_symmetric_set = PETSC_TRUE;
7001 	A->structurally_symmetric     = PETSC_TRUE;
7002       }
7003     }
7004   } else if (A->symmetric) {
7005     *flg = PETSC_TRUE;
7006   } else if (!tol) {
7007     *flg = PETSC_FALSE;
7008   } else {
7009     if (!A->ops->issymmetric) {
7010       const MatType mattype;
7011       ierr = MatGetType(A,&mattype);CHKERRQ(ierr);
7012       SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Matrix of type <%s> does not support checking for symmetric",mattype);
7013     }
7014     ierr = (*A->ops->issymmetric)(A,tol,flg);CHKERRQ(ierr);
7015   }
7016   PetscFunctionReturn(0);
7017 }
7018 
7019 #undef __FUNCT__
7020 #define __FUNCT__ "MatIsHermitian"
7021 /*@
7022    MatIsHermitian - Test whether a matrix is Hermitian
7023 
7024    Collective on Mat
7025 
7026    Input Parameter:
7027 +  A - the matrix to test
7028 -  tol - difference between value and its transpose less than this amount counts as equal (use 0.0 for exact Hermitian)
7029 
7030    Output Parameters:
7031 .  flg - the result
7032 
7033    Level: intermediate
7034 
7035    Concepts: matrix^symmetry
7036 
7037 .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), MatIsSymmetricKnown()
7038 @*/
7039 PetscErrorCode PETSCMAT_DLLEXPORT MatIsHermitian(Mat A,PetscReal tol,PetscTruth *flg)
7040 {
7041   PetscErrorCode ierr;
7042 
7043   PetscFunctionBegin;
7044   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7045   PetscValidPointer(flg,2);
7046 
7047   if (!A->hermitian_set) {
7048     if (!A->ops->ishermitian) {
7049       const MatType mattype;
7050       ierr = MatGetType(A,&mattype);CHKERRQ(ierr);
7051       SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Matrix of type <%s> does not support checking for hermitian",mattype);
7052     }
7053     ierr = (*A->ops->ishermitian)(A,tol,flg);CHKERRQ(ierr);
7054     if (!tol) {
7055       A->hermitian_set = PETSC_TRUE;
7056       A->hermitian = *flg;
7057       if (A->hermitian) {
7058 	A->structurally_symmetric_set = PETSC_TRUE;
7059 	A->structurally_symmetric     = PETSC_TRUE;
7060       }
7061     }
7062   } else if (A->hermitian) {
7063     *flg = PETSC_TRUE;
7064   } else if (!tol) {
7065     *flg = PETSC_FALSE;
7066   } else {
7067     if (!A->ops->ishermitian) {
7068       const MatType mattype;
7069       ierr = MatGetType(A,&mattype);CHKERRQ(ierr);
7070       SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Matrix of type <%s> does not support checking for hermitian",mattype);
7071     }
7072     ierr = (*A->ops->ishermitian)(A,tol,flg);CHKERRQ(ierr);
7073   }
7074   PetscFunctionReturn(0);
7075 }
7076 
7077 #undef __FUNCT__
7078 #define __FUNCT__ "MatIsSymmetricKnown"
7079 /*@
7080    MatIsSymmetricKnown - Checks the flag on the matrix to see if it is symmetric.
7081 
7082    Collective on Mat
7083 
7084    Input Parameter:
7085 .  A - the matrix to check
7086 
7087    Output Parameters:
7088 +  set - if the symmetric flag is set (this tells you if the next flag is valid)
7089 -  flg - the result
7090 
7091    Level: advanced
7092 
7093    Concepts: matrix^symmetry
7094 
7095    Note: Does not check the matrix values directly, so this may return unknown (set = PETSC_FALSE). Use MatIsSymmetric()
7096          if you want it explicitly checked
7097 
7098 .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), MatIsSymmetric()
7099 @*/
7100 PetscErrorCode PETSCMAT_DLLEXPORT MatIsSymmetricKnown(Mat A,PetscTruth *set,PetscTruth *flg)
7101 {
7102   PetscFunctionBegin;
7103   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7104   PetscValidPointer(set,2);
7105   PetscValidPointer(flg,3);
7106   if (A->symmetric_set) {
7107     *set = PETSC_TRUE;
7108     *flg = A->symmetric;
7109   } else {
7110     *set = PETSC_FALSE;
7111   }
7112   PetscFunctionReturn(0);
7113 }
7114 
7115 #undef __FUNCT__
7116 #define __FUNCT__ "MatIsHermitianKnown"
7117 /*@
7118    MatIsHermitianKnown - Checks the flag on the matrix to see if it is hermitian.
7119 
7120    Collective on Mat
7121 
7122    Input Parameter:
7123 .  A - the matrix to check
7124 
7125    Output Parameters:
7126 +  set - if the hermitian flag is set (this tells you if the next flag is valid)
7127 -  flg - the result
7128 
7129    Level: advanced
7130 
7131    Concepts: matrix^symmetry
7132 
7133    Note: Does not check the matrix values directly, so this may return unknown (set = PETSC_FALSE). Use MatIsHermitian()
7134          if you want it explicitly checked
7135 
7136 .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), MatIsSymmetric()
7137 @*/
7138 PetscErrorCode PETSCMAT_DLLEXPORT MatIsHermitianKnown(Mat A,PetscTruth *set,PetscTruth *flg)
7139 {
7140   PetscFunctionBegin;
7141   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7142   PetscValidPointer(set,2);
7143   PetscValidPointer(flg,3);
7144   if (A->hermitian_set) {
7145     *set = PETSC_TRUE;
7146     *flg = A->hermitian;
7147   } else {
7148     *set = PETSC_FALSE;
7149   }
7150   PetscFunctionReturn(0);
7151 }
7152 
7153 #undef __FUNCT__
7154 #define __FUNCT__ "MatIsStructurallySymmetric"
7155 /*@
7156    MatIsStructurallySymmetric - Test whether a matrix is structurally symmetric
7157 
7158    Collective on Mat
7159 
7160    Input Parameter:
7161 .  A - the matrix to test
7162 
7163    Output Parameters:
7164 .  flg - the result
7165 
7166    Level: intermediate
7167 
7168    Concepts: matrix^symmetry
7169 
7170 .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsSymmetric(), MatSetOption()
7171 @*/
7172 PetscErrorCode PETSCMAT_DLLEXPORT MatIsStructurallySymmetric(Mat A,PetscTruth *flg)
7173 {
7174   PetscErrorCode ierr;
7175 
7176   PetscFunctionBegin;
7177   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7178   PetscValidPointer(flg,2);
7179   if (!A->structurally_symmetric_set) {
7180     if (!A->ops->isstructurallysymmetric) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_SUP,"Matrix does not support checking for structural symmetric");
7181     ierr = (*A->ops->isstructurallysymmetric)(A,&A->structurally_symmetric);CHKERRQ(ierr);
7182     A->structurally_symmetric_set = PETSC_TRUE;
7183   }
7184   *flg = A->structurally_symmetric;
7185   PetscFunctionReturn(0);
7186 }
7187 
7188 #undef __FUNCT__
7189 #define __FUNCT__ "MatStashGetInfo"
7190 extern PetscErrorCode MatStashGetInfo_Private(MatStash*,PetscInt*,PetscInt*);
7191 /*@
7192    MatStashGetInfo - Gets how many values are currently in the vector stash, i.e. need
7193        to be communicated to other processors during the MatAssemblyBegin/End() process
7194 
7195     Not collective
7196 
7197    Input Parameter:
7198 .   vec - the vector
7199 
7200    Output Parameters:
7201 +   nstash   - the size of the stash
7202 .   reallocs - the number of additional mallocs incurred.
7203 .   bnstash   - the size of the block stash
7204 -   breallocs - the number of additional mallocs incurred.in the block stash
7205 
7206    Level: advanced
7207 
7208 .seealso: MatAssemblyBegin(), MatAssemblyEnd(), Mat, MatStashSetInitialSize()
7209 
7210 @*/
7211 PetscErrorCode PETSCMAT_DLLEXPORT MatStashGetInfo(Mat mat,PetscInt *nstash,PetscInt *reallocs,PetscInt *bnstash,PetscInt *breallocs)
7212 {
7213   PetscErrorCode ierr;
7214   PetscFunctionBegin;
7215   ierr = MatStashGetInfo_Private(&mat->stash,nstash,reallocs);CHKERRQ(ierr);
7216   ierr = MatStashGetInfo_Private(&mat->bstash,bnstash,breallocs);CHKERRQ(ierr);
7217   PetscFunctionReturn(0);
7218 }
7219 
7220 #undef __FUNCT__
7221 #define __FUNCT__ "MatGetVecs"
7222 /*@C
7223    MatGetVecs - Get vector(s) compatible with the matrix, i.e. with the same
7224      parallel layout
7225 
7226    Collective on Mat
7227 
7228    Input Parameter:
7229 .  mat - the matrix
7230 
7231    Output Parameter:
7232 +   right - (optional) vector that the matrix can be multiplied against
7233 -   left - (optional) vector that the matrix vector product can be stored in
7234 
7235   Level: advanced
7236 
7237 .seealso: MatCreate()
7238 @*/
7239 PetscErrorCode PETSCMAT_DLLEXPORT MatGetVecs(Mat mat,Vec *right,Vec *left)
7240 {
7241   PetscErrorCode ierr;
7242 
7243   PetscFunctionBegin;
7244   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
7245   PetscValidType(mat,1);
7246   ierr = MatPreallocated(mat);CHKERRQ(ierr);
7247   if (mat->ops->getvecs) {
7248     ierr = (*mat->ops->getvecs)(mat,right,left);CHKERRQ(ierr);
7249   } else {
7250     PetscMPIInt size;
7251     ierr = MPI_Comm_size(((PetscObject)mat)->comm, &size);CHKERRQ(ierr);
7252     if (right) {
7253       ierr = VecCreate(((PetscObject)mat)->comm,right);CHKERRQ(ierr);
7254       ierr = VecSetSizes(*right,mat->cmap->n,PETSC_DETERMINE);CHKERRQ(ierr);
7255       ierr = VecSetBlockSize(*right,mat->rmap->bs);CHKERRQ(ierr);
7256       if (size > 1) {
7257         /* New vectors uses Mat cmap and does not create a new one */
7258 	ierr = PetscLayoutDestroy((*right)->map);CHKERRQ(ierr);
7259 	(*right)->map = mat->cmap;
7260 	mat->cmap->refcnt++;
7261 
7262         ierr = VecSetType(*right,VECMPI);CHKERRQ(ierr);
7263       } else {ierr = VecSetType(*right,VECSEQ);CHKERRQ(ierr);}
7264     }
7265     if (left) {
7266       ierr = VecCreate(((PetscObject)mat)->comm,left);CHKERRQ(ierr);
7267       ierr = VecSetSizes(*left,mat->rmap->n,PETSC_DETERMINE);CHKERRQ(ierr);
7268       ierr = VecSetBlockSize(*left,mat->rmap->bs);CHKERRQ(ierr);
7269       if (size > 1) {
7270         /* New vectors uses Mat rmap and does not create a new one */
7271 	ierr = PetscLayoutDestroy((*left)->map);CHKERRQ(ierr);
7272 	(*left)->map = mat->rmap;
7273 	mat->rmap->refcnt++;
7274 
7275         ierr = VecSetType(*left,VECMPI);CHKERRQ(ierr);
7276       } else {ierr = VecSetType(*left,VECSEQ);CHKERRQ(ierr);}
7277     }
7278   }
7279   if (mat->mapping) {
7280     if (right) {ierr = VecSetLocalToGlobalMapping(*right,mat->mapping);CHKERRQ(ierr);}
7281     if (left) {ierr = VecSetLocalToGlobalMapping(*left,mat->mapping);CHKERRQ(ierr);}
7282   }
7283   if (mat->bmapping) {
7284     if (right) {ierr = VecSetLocalToGlobalMappingBlock(*right,mat->bmapping);CHKERRQ(ierr);}
7285     if (left) {ierr = VecSetLocalToGlobalMappingBlock(*left,mat->bmapping);CHKERRQ(ierr);}
7286   }
7287   PetscFunctionReturn(0);
7288 }
7289 
7290 #undef __FUNCT__
7291 #define __FUNCT__ "MatFactorInfoInitialize"
7292 /*@C
7293    MatFactorInfoInitialize - Initializes a MatFactorInfo data structure
7294      with default values.
7295 
7296    Not Collective
7297 
7298    Input Parameters:
7299 .    info - the MatFactorInfo data structure
7300 
7301 
7302    Notes: The solvers are generally used through the KSP and PC objects, for example
7303           PCLU, PCILU, PCCHOLESKY, PCICC
7304 
7305    Level: developer
7306 
7307 .seealso: MatFactorInfo
7308 
7309     Developer Note: fortran interface is not autogenerated as the f90
7310     interface defintion cannot be generated correctly [due to MatFactorInfo]
7311 
7312 @*/
7313 
7314 PetscErrorCode PETSCMAT_DLLEXPORT MatFactorInfoInitialize(MatFactorInfo *info)
7315 {
7316   PetscErrorCode ierr;
7317 
7318   PetscFunctionBegin;
7319   ierr = PetscMemzero(info,sizeof(MatFactorInfo));CHKERRQ(ierr);
7320   PetscFunctionReturn(0);
7321 }
7322 
7323 #undef __FUNCT__
7324 #define __FUNCT__ "MatPtAP"
7325 /*@
7326    MatPtAP - Creates the matrix projection C = P^T * A * P
7327 
7328    Collective on Mat
7329 
7330    Input Parameters:
7331 +  A - the matrix
7332 .  P - the projection matrix
7333 .  scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX
7334 -  fill - expected fill as ratio of nnz(C)/nnz(A)
7335 
7336    Output Parameters:
7337 .  C - the product matrix
7338 
7339    Notes:
7340    C will be created and must be destroyed by the user with MatDestroy().
7341 
7342    This routine is currently only implemented for pairs of AIJ matrices and classes
7343    which inherit from AIJ.
7344 
7345    Level: intermediate
7346 
7347 .seealso: MatPtAPSymbolic(), MatPtAPNumeric(), MatMatMult()
7348 @*/
7349 PetscErrorCode PETSCMAT_DLLEXPORT MatPtAP(Mat A,Mat P,MatReuse scall,PetscReal fill,Mat *C)
7350 {
7351   PetscErrorCode ierr;
7352 
7353   PetscFunctionBegin;
7354   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7355   PetscValidType(A,1);
7356   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7357   if (A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7358   PetscValidHeaderSpecific(P,MAT_CLASSID,2);
7359   PetscValidType(P,2);
7360   ierr = MatPreallocated(P);CHKERRQ(ierr);
7361   if (!P->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7362   if (P->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7363   PetscValidPointer(C,3);
7364   if (P->rmap->N!=A->cmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->rmap->N,A->cmap->N);
7365   if (fill < 1.0) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Expected fill=%G must be >= 1.0",fill);
7366   ierr = MatPreallocated(A);CHKERRQ(ierr);
7367 
7368   if (!A->ops->ptap) {
7369     const MatType mattype;
7370     ierr = MatGetType(A,&mattype);CHKERRQ(ierr);
7371     SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_SUP,"Matrix of type <%s> does not support PtAP",mattype);
7372   }
7373   ierr = PetscLogEventBegin(MAT_PtAP,A,P,0,0);CHKERRQ(ierr);
7374   ierr = (*A->ops->ptap)(A,P,scall,fill,C);CHKERRQ(ierr);
7375   ierr = PetscLogEventEnd(MAT_PtAP,A,P,0,0);CHKERRQ(ierr);
7376 
7377   PetscFunctionReturn(0);
7378 }
7379 
7380 #undef __FUNCT__
7381 #define __FUNCT__ "MatPtAPNumeric"
7382 /*@
7383    MatPtAPNumeric - Computes the matrix projection C = P^T * A * P
7384 
7385    Collective on Mat
7386 
7387    Input Parameters:
7388 +  A - the matrix
7389 -  P - the projection matrix
7390 
7391    Output Parameters:
7392 .  C - the product matrix
7393 
7394    Notes:
7395    C must have been created by calling MatPtAPSymbolic and must be destroyed by
7396    the user using MatDeatroy().
7397 
7398    This routine is currently only implemented for pairs of AIJ matrices and classes
7399    which inherit from AIJ.  C will be of type MATAIJ.
7400 
7401    Level: intermediate
7402 
7403 .seealso: MatPtAP(), MatPtAPSymbolic(), MatMatMultNumeric()
7404 @*/
7405 PetscErrorCode PETSCMAT_DLLEXPORT MatPtAPNumeric(Mat A,Mat P,Mat C)
7406 {
7407   PetscErrorCode ierr;
7408 
7409   PetscFunctionBegin;
7410   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7411   PetscValidType(A,1);
7412   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7413   if (A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7414   PetscValidHeaderSpecific(P,MAT_CLASSID,2);
7415   PetscValidType(P,2);
7416   ierr = MatPreallocated(P);CHKERRQ(ierr);
7417   if (!P->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7418   if (P->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7419   PetscValidHeaderSpecific(C,MAT_CLASSID,3);
7420   PetscValidType(C,3);
7421   ierr = MatPreallocated(C);CHKERRQ(ierr);
7422   if (C->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7423   if (P->cmap->N!=C->rmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->cmap->N,C->rmap->N);
7424   if (P->rmap->N!=A->cmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->rmap->N,A->cmap->N);
7425   if (A->rmap->N!=A->cmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix 'A' must be square, %D != %D",A->rmap->N,A->cmap->N);
7426   if (P->cmap->N!=C->cmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->cmap->N,C->cmap->N);
7427   ierr = MatPreallocated(A);CHKERRQ(ierr);
7428 
7429   ierr = PetscLogEventBegin(MAT_PtAPNumeric,A,P,0,0);CHKERRQ(ierr);
7430   ierr = (*A->ops->ptapnumeric)(A,P,C);CHKERRQ(ierr);
7431   ierr = PetscLogEventEnd(MAT_PtAPNumeric,A,P,0,0);CHKERRQ(ierr);
7432   PetscFunctionReturn(0);
7433 }
7434 
7435 #undef __FUNCT__
7436 #define __FUNCT__ "MatPtAPSymbolic"
7437 /*@
7438    MatPtAPSymbolic - Creates the (i,j) structure of the matrix projection C = P^T * A * P
7439 
7440    Collective on Mat
7441 
7442    Input Parameters:
7443 +  A - the matrix
7444 -  P - the projection matrix
7445 
7446    Output Parameters:
7447 .  C - the (i,j) structure of the product matrix
7448 
7449    Notes:
7450    C will be created and must be destroyed by the user with MatDestroy().
7451 
7452    This routine is currently only implemented for pairs of SeqAIJ matrices and classes
7453    which inherit from SeqAIJ.  C will be of type MATSEQAIJ.  The product is computed using
7454    this (i,j) structure by calling MatPtAPNumeric().
7455 
7456    Level: intermediate
7457 
7458 .seealso: MatPtAP(), MatPtAPNumeric(), MatMatMultSymbolic()
7459 @*/
7460 PetscErrorCode PETSCMAT_DLLEXPORT MatPtAPSymbolic(Mat A,Mat P,PetscReal fill,Mat *C)
7461 {
7462   PetscErrorCode ierr;
7463 
7464   PetscFunctionBegin;
7465   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7466   PetscValidType(A,1);
7467   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7468   if (A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7469   if (fill <1.0) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Expected fill=%G must be >= 1.0",fill);
7470   PetscValidHeaderSpecific(P,MAT_CLASSID,2);
7471   PetscValidType(P,2);
7472   ierr = MatPreallocated(P);CHKERRQ(ierr);
7473   if (!P->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7474   if (P->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7475   PetscValidPointer(C,3);
7476 
7477   if (P->rmap->N!=A->cmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->rmap->N,A->cmap->N);
7478   if (A->rmap->N!=A->cmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix 'A' must be square, %D != %D",A->rmap->N,A->cmap->N);
7479   ierr = MatPreallocated(A);CHKERRQ(ierr);
7480   ierr = PetscLogEventBegin(MAT_PtAPSymbolic,A,P,0,0);CHKERRQ(ierr);
7481   ierr = (*A->ops->ptapsymbolic)(A,P,fill,C);CHKERRQ(ierr);
7482   ierr = PetscLogEventEnd(MAT_PtAPSymbolic,A,P,0,0);CHKERRQ(ierr);
7483 
7484   ierr = MatSetBlockSize(*C,A->rmap->bs);CHKERRQ(ierr);
7485 
7486   PetscFunctionReturn(0);
7487 }
7488 
7489 #undef __FUNCT__
7490 #define __FUNCT__ "MatMatMult"
7491 /*@
7492    MatMatMult - Performs Matrix-Matrix Multiplication C=A*B.
7493 
7494    Collective on Mat
7495 
7496    Input Parameters:
7497 +  A - the left matrix
7498 .  B - the right matrix
7499 .  scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX
7500 -  fill - expected fill as ratio of nnz(C)/(nnz(A) + nnz(B)), use PETSC_DEFAULT if you do not have a good estimate
7501           if the result is a dense matrix this is irrelevent
7502 
7503    Output Parameters:
7504 .  C - the product matrix
7505 
7506    Notes:
7507    Unless scall is MAT_REUSE_MATRIX C will be created.
7508 
7509    MAT_REUSE_MATRIX can only be used if the matrices A and B have the same nonzero pattern as in the previous call
7510 
7511    To determine the correct fill value, run with -info and search for the string "Fill ratio" to see the value
7512    actually needed.
7513 
7514    If you have many matrices with the same non-zero structure to multiply, you
7515    should either
7516 $   1) use MAT_REUSE_MATRIX in all calls but the first or
7517 $   2) call MatMatMultSymbolic() once and then MatMatMultNumeric() for each product needed
7518 
7519    Level: intermediate
7520 
7521 .seealso: MatMatMultSymbolic(), MatMatMultNumeric(), MatPtAP()
7522 @*/
7523 PetscErrorCode PETSCMAT_DLLEXPORT MatMatMult(Mat A,Mat B,MatReuse scall,PetscReal fill,Mat *C)
7524 {
7525   PetscErrorCode ierr;
7526   PetscErrorCode (*fA)(Mat,Mat,MatReuse,PetscReal,Mat*);
7527   PetscErrorCode (*fB)(Mat,Mat,MatReuse,PetscReal,Mat*);
7528   PetscErrorCode (*mult)(Mat,Mat,MatReuse,PetscReal,Mat *)=PETSC_NULL;
7529 
7530   PetscFunctionBegin;
7531   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7532   PetscValidType(A,1);
7533   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7534   if (A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7535   PetscValidHeaderSpecific(B,MAT_CLASSID,2);
7536   PetscValidType(B,2);
7537   ierr = MatPreallocated(B);CHKERRQ(ierr);
7538   if (!B->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7539   if (B->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7540   PetscValidPointer(C,3);
7541   if (B->rmap->N!=A->cmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",B->rmap->N,A->cmap->N);
7542   if (scall == MAT_REUSE_MATRIX){
7543     PetscValidPointer(*C,5);
7544     PetscValidHeaderSpecific(*C,MAT_CLASSID,5);
7545   }
7546   if (fill == PETSC_DEFAULT || fill == PETSC_DECIDE) fill = 2.0;
7547   if (fill < 1.0) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Expected fill=%G must be >= 1.0",fill);
7548   ierr = MatPreallocated(A);CHKERRQ(ierr);
7549 
7550   fA = A->ops->matmult;
7551   fB = B->ops->matmult;
7552   if (fB == fA) {
7553     if (!fB) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_SUP,"MatMatMult not supported for B of type %s",((PetscObject)B)->type_name);
7554     mult = fB;
7555   } else {
7556     /* dispatch based on the type of A and B */
7557     char  multname[256];
7558     ierr = PetscStrcpy(multname,"MatMatMult_");CHKERRQ(ierr);
7559     ierr = PetscStrcat(multname,((PetscObject)A)->type_name);CHKERRQ(ierr);
7560     ierr = PetscStrcat(multname,"_");CHKERRQ(ierr);
7561     ierr = PetscStrcat(multname,((PetscObject)B)->type_name);CHKERRQ(ierr);
7562     ierr = PetscStrcat(multname,"_C");CHKERRQ(ierr); /* e.g., multname = "MatMatMult_seqdense_seqaij_C" */
7563     ierr = PetscObjectQueryFunction((PetscObject)B,multname,(void (**)(void))&mult);CHKERRQ(ierr);
7564     if (!mult) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_INCOMP,"MatMatMult requires A, %s, to be compatible with B, %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name);
7565   }
7566   ierr = PetscLogEventBegin(MAT_MatMult,A,B,0,0);CHKERRQ(ierr);
7567   ierr = (*mult)(A,B,scall,fill,C);CHKERRQ(ierr);
7568   ierr = PetscLogEventEnd(MAT_MatMult,A,B,0,0);CHKERRQ(ierr);
7569   PetscFunctionReturn(0);
7570 }
7571 
7572 #undef __FUNCT__
7573 #define __FUNCT__ "MatMatMultSymbolic"
7574 /*@
7575    MatMatMultSymbolic - Performs construction, preallocation, and computes the ij structure
7576    of the matrix-matrix product C=A*B.  Call this routine before calling MatMatMultNumeric().
7577 
7578    Collective on Mat
7579 
7580    Input Parameters:
7581 +  A - the left matrix
7582 .  B - the right matrix
7583 -  fill - expected fill as ratio of nnz(C)/(nnz(A) + nnz(B)), use PETSC_DEFAULT if you do not have a good estimate,
7584       if C is a dense matrix this is irrelevent
7585 
7586    Output Parameters:
7587 .  C - the product matrix
7588 
7589    Notes:
7590    Unless scall is MAT_REUSE_MATRIX C will be created.
7591 
7592    To determine the correct fill value, run with -info and search for the string "Fill ratio" to see the value
7593    actually needed.
7594 
7595    This routine is currently implemented for
7596     - pairs of AIJ matrices and classes which inherit from AIJ, C will be of type AIJ
7597     - pairs of AIJ (A) and Dense (B) matrix, C will be of type Dense.
7598     - pairs of Dense (A) and AIJ (B) matrix, C will be of type Dense.
7599 
7600    Level: intermediate
7601 
7602 .seealso: MatMatMult(), MatMatMultNumeric()
7603 @*/
7604 PetscErrorCode PETSCMAT_DLLEXPORT MatMatMultSymbolic(Mat A,Mat B,PetscReal fill,Mat *C)
7605 {
7606   PetscErrorCode ierr;
7607   PetscErrorCode (*Asymbolic)(Mat,Mat,PetscReal,Mat *);
7608   PetscErrorCode (*Bsymbolic)(Mat,Mat,PetscReal,Mat *);
7609   PetscErrorCode (*symbolic)(Mat,Mat,PetscReal,Mat *)=PETSC_NULL;
7610 
7611   PetscFunctionBegin;
7612   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7613   PetscValidType(A,1);
7614   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7615   if (A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7616 
7617   PetscValidHeaderSpecific(B,MAT_CLASSID,2);
7618   PetscValidType(B,2);
7619   ierr = MatPreallocated(B);CHKERRQ(ierr);
7620   if (!B->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7621   if (B->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7622   PetscValidPointer(C,3);
7623 
7624   if (B->rmap->N!=A->cmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",B->rmap->N,A->cmap->N);
7625   if (fill == PETSC_DEFAULT) fill = 2.0;
7626   if (fill < 1.0) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Expected fill=%G must be > 1.0",fill);
7627   ierr = MatPreallocated(A);CHKERRQ(ierr);
7628 
7629   Asymbolic = A->ops->matmultsymbolic;
7630   Bsymbolic = B->ops->matmultsymbolic;
7631   if (Asymbolic == Bsymbolic){
7632     if (!Bsymbolic) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_SUP,"C=A*B not implemented for B of type %s",((PetscObject)B)->type_name);
7633     symbolic = Bsymbolic;
7634   } else { /* dispatch based on the type of A and B */
7635     char  symbolicname[256];
7636     ierr = PetscStrcpy(symbolicname,"MatMatMultSymbolic_");CHKERRQ(ierr);
7637     ierr = PetscStrcat(symbolicname,((PetscObject)A)->type_name);CHKERRQ(ierr);
7638     ierr = PetscStrcat(symbolicname,"_");CHKERRQ(ierr);
7639     ierr = PetscStrcat(symbolicname,((PetscObject)B)->type_name);CHKERRQ(ierr);
7640     ierr = PetscStrcat(symbolicname,"_C");CHKERRQ(ierr);
7641     ierr = PetscObjectQueryFunction((PetscObject)B,symbolicname,(void (**)(void))&symbolic);CHKERRQ(ierr);
7642     if (!symbolic) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_INCOMP,"MatMatMultSymbolic requires A, %s, to be compatible with B, %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name);
7643   }
7644   ierr = PetscLogEventBegin(MAT_MatMultSymbolic,A,B,0,0);CHKERRQ(ierr);
7645   ierr = (*symbolic)(A,B,fill,C);CHKERRQ(ierr);
7646   ierr = PetscLogEventEnd(MAT_MatMultSymbolic,A,B,0,0);CHKERRQ(ierr);
7647   PetscFunctionReturn(0);
7648 }
7649 
7650 #undef __FUNCT__
7651 #define __FUNCT__ "MatMatMultNumeric"
7652 /*@
7653    MatMatMultNumeric - Performs the numeric matrix-matrix product.
7654    Call this routine after first calling MatMatMultSymbolic().
7655 
7656    Collective on Mat
7657 
7658    Input Parameters:
7659 +  A - the left matrix
7660 -  B - the right matrix
7661 
7662    Output Parameters:
7663 .  C - the product matrix, which was created by from MatMatMultSymbolic() or a call to MatMatMult().
7664 
7665    Notes:
7666    C must have been created with MatMatMultSymbolic().
7667 
7668    This routine is currently implemented for
7669     - pairs of AIJ matrices and classes which inherit from AIJ, C will be of type MATAIJ.
7670     - pairs of AIJ (A) and Dense (B) matrix, C will be of type Dense.
7671     - pairs of Dense (A) and AIJ (B) matrix, C will be of type Dense.
7672 
7673    Level: intermediate
7674 
7675 .seealso: MatMatMult(), MatMatMultSymbolic()
7676 @*/
7677 PetscErrorCode PETSCMAT_DLLEXPORT MatMatMultNumeric(Mat A,Mat B,Mat C)
7678 {
7679   PetscErrorCode ierr;
7680   PetscErrorCode (*Anumeric)(Mat,Mat,Mat);
7681   PetscErrorCode (*Bnumeric)(Mat,Mat,Mat);
7682   PetscErrorCode (*numeric)(Mat,Mat,Mat)=PETSC_NULL;
7683 
7684   PetscFunctionBegin;
7685   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7686   PetscValidType(A,1);
7687   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7688   if (A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7689 
7690   PetscValidHeaderSpecific(B,MAT_CLASSID,2);
7691   PetscValidType(B,2);
7692   ierr = MatPreallocated(B);CHKERRQ(ierr);
7693   if (!B->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7694   if (B->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7695 
7696   PetscValidHeaderSpecific(C,MAT_CLASSID,3);
7697   PetscValidType(C,3);
7698   ierr = MatPreallocated(C);CHKERRQ(ierr);
7699   if (!C->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7700   if (C->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7701 
7702   if (B->cmap->N!=C->cmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",B->cmap->N,C->cmap->N);
7703   if (B->rmap->N!=A->cmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",B->rmap->N,A->cmap->N);
7704   if (A->rmap->N!=C->rmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",A->rmap->N,C->rmap->N);
7705   ierr = MatPreallocated(A);CHKERRQ(ierr);
7706 
7707   Anumeric = A->ops->matmultnumeric;
7708   Bnumeric = B->ops->matmultnumeric;
7709   if (Anumeric == Bnumeric){
7710     if (!Bnumeric) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_SUP,"MatMatMultNumeric not supported for B of type %s",((PetscObject)B)->type_name);
7711     numeric = Bnumeric;
7712   } else {
7713     char  numericname[256];
7714     ierr = PetscStrcpy(numericname,"MatMatMultNumeric_");CHKERRQ(ierr);
7715     ierr = PetscStrcat(numericname,((PetscObject)A)->type_name);CHKERRQ(ierr);
7716     ierr = PetscStrcat(numericname,"_");CHKERRQ(ierr);
7717     ierr = PetscStrcat(numericname,((PetscObject)B)->type_name);CHKERRQ(ierr);
7718     ierr = PetscStrcat(numericname,"_C");CHKERRQ(ierr);
7719     ierr = PetscObjectQueryFunction((PetscObject)B,numericname,(void (**)(void))&numeric);CHKERRQ(ierr);
7720     if (!numeric)
7721       SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_INCOMP,"MatMatMultNumeric requires A, %s, to be compatible with B, %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name);
7722   }
7723   ierr = PetscLogEventBegin(MAT_MatMultNumeric,A,B,0,0);CHKERRQ(ierr);
7724   ierr = (*numeric)(A,B,C);CHKERRQ(ierr);
7725   ierr = PetscLogEventEnd(MAT_MatMultNumeric,A,B,0,0);CHKERRQ(ierr);
7726   PetscFunctionReturn(0);
7727 }
7728 
7729 #undef __FUNCT__
7730 #define __FUNCT__ "MatMatMultTranspose"
7731 /*@
7732    MatMatMultTranspose - Performs Matrix-Matrix Multiplication C=A^T*B.
7733 
7734    Collective on Mat
7735 
7736    Input Parameters:
7737 +  A - the left matrix
7738 .  B - the right matrix
7739 .  scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX
7740 -  fill - expected fill as ratio of nnz(C)/(nnz(A) + nnz(B)), use PETSC_DEFAULT if not known
7741 
7742    Output Parameters:
7743 .  C - the product matrix
7744 
7745    Notes:
7746    C will be created if MAT_INITIAL_MATRIX and must be destroyed by the user with MatDestroy().
7747 
7748    MAT_REUSE_MATRIX can only be used if the matrices A and B have the same nonzero pattern as in the previous call
7749 
7750   To determine the correct fill value, run with -info and search for the string "Fill ratio" to see the value
7751    actually needed.
7752 
7753    This routine is currently only implemented for pairs of SeqAIJ matrices and pairs of SeqDense matrices and classes
7754    which inherit from SeqAIJ.  C will be of type MATSEQAIJ.
7755 
7756    Level: intermediate
7757 
7758 .seealso: MatMatMultTransposeSymbolic(), MatMatMultTransposeNumeric(), MatPtAP()
7759 @*/
7760 PetscErrorCode PETSCMAT_DLLEXPORT MatMatMultTranspose(Mat A,Mat B,MatReuse scall,PetscReal fill,Mat *C)
7761 {
7762   PetscErrorCode ierr;
7763   PetscErrorCode (*fA)(Mat,Mat,MatReuse,PetscReal,Mat*);
7764   PetscErrorCode (*fB)(Mat,Mat,MatReuse,PetscReal,Mat*);
7765 
7766   PetscFunctionBegin;
7767   PetscValidHeaderSpecific(A,MAT_CLASSID,1);
7768   PetscValidType(A,1);
7769   if (!A->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7770   if (A->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7771   PetscValidHeaderSpecific(B,MAT_CLASSID,2);
7772   PetscValidType(B,2);
7773   ierr = MatPreallocated(B);CHKERRQ(ierr);
7774   if (!B->assembled) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7775   if (B->factortype) SETERRQ(((PetscObject)A)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7776   PetscValidPointer(C,3);
7777   if (B->rmap->N!=A->rmap->N) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",B->rmap->N,A->rmap->N);
7778   if (fill == PETSC_DEFAULT || fill == PETSC_DECIDE) fill = 2.0;
7779   if (fill < 1.0) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_ARG_SIZ,"Expected fill=%G must be > 1.0",fill);
7780   ierr = MatPreallocated(A);CHKERRQ(ierr);
7781 
7782   fA = A->ops->matmulttranspose;
7783   if (!fA) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_SUP,"MatMatMultTranspose not supported for A of type %s",((PetscObject)A)->type_name);
7784   fB = B->ops->matmulttranspose;
7785   if (!fB) SETERRQ1(((PetscObject)A)->comm,PETSC_ERR_SUP,"MatMatMultTranspose not supported for B of type %s",((PetscObject)B)->type_name);
7786   if (fB!=fA) SETERRQ2(((PetscObject)A)->comm,PETSC_ERR_ARG_INCOMP,"MatMatMultTranspose requires A, %s, to be compatible with B, %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name);
7787 
7788   ierr = PetscLogEventBegin(MAT_MatMultTranspose,A,B,0,0);CHKERRQ(ierr);
7789   ierr = (*A->ops->matmulttranspose)(A,B,scall,fill,C);CHKERRQ(ierr);
7790   ierr = PetscLogEventEnd(MAT_MatMultTranspose,A,B,0,0);CHKERRQ(ierr);
7791 
7792   PetscFunctionReturn(0);
7793 }
7794 
7795 #undef __FUNCT__
7796 #define __FUNCT__ "MatGetRedundantMatrix"
7797 /*@C
7798    MatGetRedundantMatrix - Create redundant matrices and put them into processors of subcommunicators.
7799 
7800    Collective on Mat
7801 
7802    Input Parameters:
7803 +  mat - the matrix
7804 .  nsubcomm - the number of subcommunicators (= number of redundant pareallel or sequential matrices)
7805 .  subcomm - MPI communicator split from the communicator where mat resides in
7806 .  mlocal_red - number of local rows of the redundant matrix
7807 -  reuse - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX
7808 
7809    Output Parameter:
7810 .  matredundant - redundant matrix
7811 
7812    Notes:
7813    MAT_REUSE_MATRIX can only be used when the nonzero structure of the
7814    original matrix has not changed from that last call to MatGetRedundantMatrix().
7815 
7816    This routine creates the duplicated matrices in subcommunicators; you should NOT create them before
7817    calling it.
7818 
7819    Only MPIAIJ matrix is supported.
7820 
7821    Level: advanced
7822 
7823    Concepts: subcommunicator
7824    Concepts: duplicate matrix
7825 
7826 .seealso: MatDestroy()
7827 @*/
7828 PetscErrorCode PETSCMAT_DLLEXPORT MatGetRedundantMatrix(Mat mat,PetscInt nsubcomm,MPI_Comm subcomm,PetscInt mlocal_red,MatReuse reuse,Mat *matredundant)
7829 {
7830   PetscErrorCode ierr;
7831 
7832   PetscFunctionBegin;
7833   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
7834   if (nsubcomm && reuse == MAT_REUSE_MATRIX) {
7835     PetscValidPointer(*matredundant,6);
7836     PetscValidHeaderSpecific(*matredundant,MAT_CLASSID,6);
7837   }
7838   if (!mat->ops->getredundantmatrix) SETERRQ1(((PetscObject)mat)->comm,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name);
7839   if (!mat->assembled) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix");
7840   if (mat->factortype) SETERRQ(((PetscObject)mat)->comm,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix");
7841   ierr = MatPreallocated(mat);CHKERRQ(ierr);
7842 
7843   ierr = PetscLogEventBegin(MAT_GetRedundantMatrix,mat,0,0,0);CHKERRQ(ierr);
7844   ierr = (*mat->ops->getredundantmatrix)(mat,nsubcomm,subcomm,mlocal_red,reuse,matredundant);CHKERRQ(ierr);
7845   ierr = PetscLogEventEnd(MAT_GetRedundantMatrix,mat,0,0,0);CHKERRQ(ierr);
7846   PetscFunctionReturn(0);
7847 }
7848