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