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