xref: /petsc/src/mat/interface/matrix.c (revision 90f02eec332fcca4c33b4e7b21cabed76bf0614e)
1 
2 #ifndef lint
3 static char vcid[] = "$Id: matrix.c,v 1.206 1996/10/29 18:24:15 bsmith Exp bsmith $";
4 #endif
5 
6 /*
7    This is where the abstract matrix operations are defined
8 */
9 
10 #include "petsc.h"
11 #include "src/mat/matimpl.h"        /*I "mat.h" I*/
12 #include "src/vec/vecimpl.h"
13 #include "pinclude/pviewer.h"
14 #include "draw.h"
15 
16 
17 /*@C
18    MatGetRow - Gets a row of a matrix.  You MUST call MatRestoreRow()
19    for each row that you get to ensure that your application does
20    not bleed memory.
21 
22    Input Parameters:
23 .  mat - the matrix
24 .  row - the row to get
25 
26    Output Parameters:
27 .  ncols -  the number of nonzeros in the row
28 .  cols - if nonzero, the column numbers
29 .  vals - if nonzero, the values
30 
31    Notes:
32    This routine is provided for people who need to have direct access
33    to the structure of a matrix.  We hope that we provide enough
34    high-level matrix routines that few users will need it.
35 
36    For better efficiency, set cols and/or vals to PETSC_NULL if you do
37    not wish to extract these quantities.
38 
39    The user can only examine the values extracted with MatGetRow();
40    the values cannot be altered.  To change the matrix entries, one
41    must use MatSetValues().
42 
43    Caution:
44    Do not try to change the contents of the output arrays (cols and vals).
45    In some cases, this may corrupt the matrix.
46 
47 .keywords: matrix, row, get, extract
48 
49 .seealso: MatRestoreRow(), MatSetValues()
50 @*/
51 int MatGetRow(Mat mat,int row,int *ncols,int **cols,Scalar **vals)
52 {
53   int   ierr;
54   PetscValidHeaderSpecific(mat,MAT_COOKIE);
55   PetscValidIntPointer(ncols);
56   if (!mat->assembled) SETERRQ(1,"MatGetRow:Not for unassembled matrix");
57   if (mat->factor) SETERRQ(1,"MatGetRow:Not for factored matrix");
58   if (!mat->ops.getrow) SETERRQ(PETSC_ERR_SUP,"MatGetRow");
59   PLogEventBegin(MAT_GetRow,mat,0,0,0);
60   ierr = (*mat->ops.getrow)(mat,row,ncols,cols,vals); CHKERRQ(ierr);
61   PLogEventEnd(MAT_GetRow,mat,0,0,0);
62   return 0;
63 }
64 
65 /*@C
66    MatRestoreRow - Frees any temporary space allocated by MatGetRow().
67 
68    Input Parameters:
69 .  mat - the matrix
70 .  row - the row to get
71 .  ncols, cols - the number of nonzeros and their columns
72 .  vals - if nonzero the column values
73 
74 .keywords: matrix, row, restore
75 
76 .seealso:  MatGetRow()
77 @*/
78 int MatRestoreRow(Mat mat,int row,int *ncols,int **cols,Scalar **vals)
79 {
80   PetscValidHeaderSpecific(mat,MAT_COOKIE);
81   PetscValidIntPointer(ncols);
82   if (!mat->assembled) SETERRQ(1,"MatRestoreRow:Not for unassembled matrix");
83   if (!mat->ops.restorerow) return 0;
84   return (*mat->ops.restorerow)(mat,row,ncols,cols,vals);
85 }
86 /*@
87    MatView - Visualizes a matrix object.
88 
89    Input Parameters:
90 .  mat - the matrix
91 .  ptr - visualization context
92 
93    Notes:
94    The available visualization contexts include
95 $     VIEWER_STDOUT_SELF - standard output (default)
96 $     VIEWER_STDOUT_WORLD - synchronized standard
97 $       output where only the first processor opens
98 $       the file.  All other processors send their
99 $       data to the first processor to print.
100 
101    The user can open alternative vistualization contexts with
102 $    ViewerFileOpenASCII() - output to a specified file
103 $    ViewerFileOpenBinary() - output in binary to a
104 $         specified file; corresponding input uses MatLoad()
105 $    ViewerDrawOpenX() - output nonzero matrix structure to
106 $         an X window display
107 $    ViewerMatlabOpen() - output matrix to Matlab viewer.
108 $         Currently only the sequential dense and AIJ
109 $         matrix types support the Matlab viewer.
110 
111    The user can call ViewerSetFormat() to specify the output
112    format of ASCII printed objects (when using VIEWER_STDOUT_SELF,
113    VIEWER_STDOUT_WORLD and ViewerFileOpenASCII).  Available formats include
114 $    VIEWER_FORMAT_ASCII_DEFAULT - default, prints matrix contents
115 $    VIEWER_FORMAT_ASCII_MATLAB - Matlab format
116 $    VIEWER_FORMAT_ASCII_IMPL - implementation-specific format
117 $      (which is in many cases the same as the default)
118 $    VIEWER_FORMAT_ASCII_INFO - basic information about the matrix
119 $      size and structure (not the matrix entries)
120 $    VIEWER_FORMAT_ASCII_INFO_LONG - more detailed information about the
121 $      matrix structure
122 
123 .keywords: matrix, view, visualize, output, print, write, draw
124 
125 .seealso: ViewerSetFormat(), ViewerFileOpenASCII(), ViewerDrawOpenX(),
126           ViewerMatlabOpen(), ViewerFileOpenBinary(), MatLoad()
127 @*/
128 int MatView(Mat mat,Viewer viewer)
129 {
130   int          format, ierr, rows, cols;
131   FILE         *fd;
132   char         *cstr;
133   ViewerType   vtype;
134   MPI_Comm     comm = mat->comm;
135 
136   PetscValidHeaderSpecific(mat,MAT_COOKIE);
137   if (viewer) PetscValidHeaderSpecific(viewer,VIEWER_COOKIE);
138   if (!mat->assembled) SETERRQ(1,"MatView:Not for unassembled matrix");
139 
140   if (!viewer) {
141     viewer = VIEWER_STDOUT_SELF;
142   }
143 
144   ierr = ViewerGetType(viewer,&vtype);
145   if (vtype == ASCII_FILE_VIEWER || vtype == ASCII_FILES_VIEWER) {
146     ierr = ViewerGetFormat(viewer,&format); CHKERRQ(ierr);
147     ierr = ViewerASCIIGetPointer(viewer,&fd); CHKERRQ(ierr);
148     if (format == VIEWER_FORMAT_ASCII_INFO || format == VIEWER_FORMAT_ASCII_INFO_LONG) {
149       PetscFPrintf(comm,fd,"Matrix Object:\n");
150       ierr = MatGetType(mat,PETSC_NULL,&cstr); CHKERRQ(ierr);
151       ierr = MatGetSize(mat,&rows,&cols); CHKERRQ(ierr);
152       PetscFPrintf(comm,fd,"  type=%s, rows=%d, cols=%d\n",cstr,rows,cols);
153       if (mat->ops.getinfo) {
154         MatInfo info;
155         ierr = MatGetInfo(mat,MAT_GLOBAL_SUM,&info); CHKERRQ(ierr);
156         PetscFPrintf(comm,fd,"  total: nonzeros=%d, allocated nonzeros=%d\n",
157                      (int)info.nz_used,(int)info.nz_allocated);
158       }
159     }
160   }
161   if (mat->view) {ierr = (*mat->view)((PetscObject)mat,viewer); CHKERRQ(ierr);}
162   return 0;
163 }
164 
165 /*@C
166    MatDestroy - Frees space taken by a matrix.
167 
168    Input Parameter:
169 .  mat - the matrix
170 
171 .keywords: matrix, destroy
172 @*/
173 int MatDestroy(Mat mat)
174 {
175   int ierr;
176   PetscValidHeaderSpecific(mat,MAT_COOKIE);
177   ierr = (*mat->destroy)((PetscObject)mat); CHKERRQ(ierr);
178   return 0;
179 }
180 /*@
181    MatValid - Checks whether a matrix object is valid.
182 
183    Input Parameter:
184 .  m - the matrix to check
185 
186    Output Parameter:
187    flg - flag indicating matrix status, either
188 $     PETSC_TRUE if matrix is valid;
189 $     PETSC_FALSE otherwise.
190 
191 .keywords: matrix, valid
192 @*/
193 int MatValid(Mat m,PetscTruth *flg)
194 {
195   PetscValidIntPointer(flg);
196   if (!m)                           *flg = PETSC_FALSE;
197   else if (m->cookie != MAT_COOKIE) *flg = PETSC_FALSE;
198   else                              *flg = PETSC_TRUE;
199   return 0;
200 }
201 
202 /*@
203    MatSetValues - Inserts or adds a block of values into a matrix.
204    These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd()
205    MUST be called after all calls to MatSetValues() have been completed.
206 
207    Input Parameters:
208 .  mat - the matrix
209 .  v - a logically two-dimensional array of values
210 .  m, indexm - the number of rows and their global indices
211 .  n, indexn - the number of columns and their global indices
212 .  addv - either ADD_VALUES or INSERT_VALUES, where
213 $     ADD_VALUES - adds values to any existing entries
214 $     INSERT_VALUES - replaces existing entries with new values
215 
216    Notes:
217    By default the values, v, are row-oriented and unsorted.
218    See MatSetOptions() for other options.
219 
220    Calls to MatSetValues() with the INSERT_VALUES and ADD_VALUES
221    options cannot be mixed without intervening calls to the assembly
222    routines.
223 
224 .keywords: matrix, insert, add, set, values
225 
226 .seealso: MatSetOptions(), MatAssemblyBegin(), MatAssemblyEnd()
227 @*/
228 int MatSetValues(Mat mat,int m,int *idxm,int n,int *idxn,Scalar *v,InsertMode addv)
229 {
230   int ierr;
231   PetscValidHeaderSpecific(mat,MAT_COOKIE);
232   if (!m || !n) return 0; /* no values to insert */
233   PetscValidIntPointer(idxm);
234   PetscValidIntPointer(idxn);
235   PetscValidScalarPointer(v);
236   if (mat->factor) SETERRQ(1,"MatSetValues:Not for factored matrix");
237 
238   if (mat->assembled) {
239     mat->was_assembled = PETSC_TRUE;
240     mat->assembled     = PETSC_FALSE;
241   }
242   PLogEventBegin(MAT_SetValues,mat,0,0,0);
243   ierr = (*mat->ops.setvalues)(mat,m,idxm,n,idxn,v,addv);CHKERRQ(ierr);
244   PLogEventEnd(MAT_SetValues,mat,0,0,0);
245   return 0;
246 }
247 
248 /*@
249    MatGetValues - Gets a block of values from a matrix.
250 
251    Input Parameters:
252 .  mat - the matrix
253 .  v - a logically two-dimensional array for storing the values
254 .  m, indexm - the number of rows and their global indices
255 .  n, indexn - the number of columns and their global indices
256 
257    Notes:
258    The user must allocate space (m*n Scalars) for the values, v.
259    The values, v, are then returned in a row-oriented format,
260    analogous to that used by default in MatSetValues().
261 
262 .keywords: matrix, get, values
263 
264 .seealso: MatGetRow(), MatGetSubmatrices(), MatSetValues()
265 @*/
266 int MatGetValues(Mat mat,int m,int *idxm,int n,int *idxn,Scalar *v)
267 {
268   int ierr;
269 
270   PetscValidHeaderSpecific(mat,MAT_COOKIE);
271   PetscValidIntPointer(idxm);
272   PetscValidIntPointer(idxn);
273   PetscValidScalarPointer(v);
274   if (!mat->assembled) SETERRQ(1,"MatGetValues:Not for unassembled matrix");
275   if (mat->factor) SETERRQ(1,"MatGetValues:Not for factored matrix");
276   if (!mat->ops.getvalues) SETERRQ(PETSC_ERR_SUP,"MatGetValues");
277 
278   PLogEventBegin(MAT_GetValues,mat,0,0,0);
279   ierr = (*mat->ops.getvalues)(mat,m,idxm,n,idxn,v); CHKERRQ(ierr);
280   PLogEventEnd(MAT_GetValues,mat,0,0,0);
281   return 0;
282 }
283 
284 /*@
285    MatSetLocalToGlobalMapping - Sets a local numbering to global numbering used
286      by the routine MatSetValuesLocal() to allow users to insert matrices entries
287      using a local (per-processor) numbering.
288 
289    Input Parameters:
290 .  x - the matrix
291 .  n - number of local indices
292 .  indices - global index for each local index
293 
294 .keywords: matrix, set, values, local ordering
295 
296 .seealso:  MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetValuesLocal()
297 @*/
298 int MatSetLocalToGlobalMapping(Mat x, int n,int *indices)
299 {
300   int ierr;
301   PetscValidHeaderSpecific(x,MAT_COOKIE);
302   PetscValidIntPointer(indices);
303 
304   if (x->mapping) {
305     SETERRQ(1,"MatSetLocalToGlobalMapping:Mapping already set for matrix");
306   }
307 
308   ierr = ISLocalToGlobalMappingCreate(n,indices,&x->mapping);CHKERRQ(ierr);
309   return 0;
310 }
311 
312 /*@
313    MatSetValuesLocal - Inserts or adds values into certain locations of a matrix,
314         using a local ordering of the nodes.
315 
316    Input Parameters:
317 .  x - matrix to insert in
318 .  nrow - number of row elements to add
319 .  irow - row indices where to add
320 .  ncol - number of column elements to add
321 .  icol - column indices where to add
322 .  y - array of values
323 .  iora - either INSERT_VALUES or ADD_VALUES
324 
325    Notes:
326    Calls to MatSetValuesLocal() with the INSERT_VALUES and ADD_VALUES
327    options cannot be mixed without intervening calls to the assembly
328    routines.
329    These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd()
330    MUST be called after all calls to MatSetValuesLocal() have been completed.
331 
332 .keywords: matrix, set, values, local ordering
333 
334 .seealso:  MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetLocalToGlobalMapping()
335 @*/
336 int MatSetValuesLocal(Mat x,int nrow,int *irow,int ncol, int *icol,Scalar *y,InsertMode iora)
337 {
338   int ierr,irowm[128],icolm[128];
339 
340   PetscValidHeaderSpecific(x,MAT_COOKIE);
341   PetscValidIntPointer(irow);
342   PetscValidIntPointer(icol);
343   PetscValidScalarPointer(y);
344   if (!x->mapping) {
345     SETERRQ(1,"MatSetValuesLocal:Local to global never set with MatSetLocalToGlobalMapping");
346   }
347   if (nrow > 128 || ncol > 128) {
348     SETERRQ(1,"MatSetValuesLocal:Number indices must be <= 128");
349   }
350   if (x->factor) SETERRQ(1,"MatSetValues:Not for factored matrix");
351 
352   if (x->assembled) {
353     x->was_assembled = PETSC_TRUE;
354     x->assembled     = PETSC_FALSE;
355   }
356   PLogEventBegin(MAT_SetValues,x,0,0,0);
357   ISLocalToGlobalMappingApply(x->mapping,nrow,irow,irowm);
358   ISLocalToGlobalMappingApply(x->mapping,ncol,icol,icolm);
359   ierr = (*x->ops.setvalues)(x,nrow,irowm,ncol,icolm,y,iora);CHKERRQ(ierr);
360   PLogEventEnd(MAT_SetValues,x,0,0,0);
361   return 0;
362 }
363 
364 /* --------------------------------------------------------*/
365 /*@
366    MatMult - Computes the matrix-vector product, y = Ax.
367 
368    Input Parameters:
369 .  mat - the matrix
370 .  x   - the vector to be multilplied
371 
372    Output Parameters:
373 .  y - the result
374 
375    Notes:
376    The vectors x and y cannot be the same.  I.e., one cannot
377    call MatMult(A,y,y).
378 
379 .keywords: matrix, multiply, matrix-vector product
380 
381 .seealso: MatMultTrans(), MatMultAdd(), MatMultTransAdd()
382 @*/
383 int MatMult(Mat mat,Vec x,Vec y)
384 {
385   int ierr;
386   PetscValidHeaderSpecific(mat,MAT_COOKIE);
387   PetscValidHeaderSpecific(x,VEC_COOKIE);PetscValidHeaderSpecific(y,VEC_COOKIE);
388   if (!mat->assembled) SETERRQ(1,"MatMult:Not for unassembled matrix");
389   if (mat->factor) SETERRQ(1,"MatMult:Not for factored matrix");
390   if (x == y) SETERRQ(1,"MatMult:x and y must be different vectors");
391   if (mat->N != x->N) SETERRQ(PETSC_ERR_SIZ,"MatMult:Mat mat,Vec x: global dim");
392   if (mat->M != y->N) SETERRQ(PETSC_ERR_SIZ,"MatMult:Mat mat,Vec y: global dim");
393   if (mat->m != y->n) SETERRQ(PETSC_ERR_SIZ,"MatMult:Mat mat,Vec y: local dim");
394 
395   PLogEventBegin(MAT_Mult,mat,x,y,0);
396   ierr = (*mat->ops.mult)(mat,x,y); CHKERRQ(ierr);
397   PLogEventEnd(MAT_Mult,mat,x,y,0);
398 
399   return 0;
400 }
401 /*@
402    MatMultTrans - Computes matrix transpose times a vector.
403 
404    Input Parameters:
405 .  mat - the matrix
406 .  x   - the vector to be multilplied
407 
408    Output Parameters:
409 .  y - the result
410 
411    Notes:
412    The vectors x and y cannot be the same.  I.e., one cannot
413    call MatMultTrans(A,y,y).
414 
415 .keywords: matrix, multiply, matrix-vector product, transpose
416 
417 .seealso: MatMult(), MatMultAdd(), MatMultTransAdd()
418 @*/
419 int MatMultTrans(Mat mat,Vec x,Vec y)
420 {
421   int ierr;
422   PetscValidHeaderSpecific(mat,MAT_COOKIE);
423   PetscValidHeaderSpecific(x,VEC_COOKIE); PetscValidHeaderSpecific(y,VEC_COOKIE);
424   if (!mat->assembled) SETERRQ(1,"MatMultTrans:Not for unassembled matrix");
425   if (mat->factor) SETERRQ(1,"MatMult:Not for factored matrix");
426   if (x == y) SETERRQ(1,"MatMultTrans:x and y must be different vectors");
427   if (mat->M != x->N) SETERRQ(PETSC_ERR_SIZ,"MatMultTrans:Mat mat,Vec x: global dim");
428   if (mat->N != y->N) SETERRQ(PETSC_ERR_SIZ,"MatMultTrans:Mat mat,Vec y: global dim");
429   PLogEventBegin(MAT_MultTrans,mat,x,y,0);
430   ierr = (*mat->ops.multtrans)(mat,x,y); CHKERRQ(ierr);
431   PLogEventEnd(MAT_MultTrans,mat,x,y,0);
432   return 0;
433 }
434 /*@
435     MatMultAdd -  Computes v3 = v2 + A * v1.
436 
437     Input Parameters:
438 .   mat - the matrix
439 .   v1, v2 - the vectors
440 
441     Output Parameters:
442 .   v3 - the result
443 
444    Notes:
445    The vectors v1 and v3 cannot be the same.  I.e., one cannot
446    call MatMultAdd(A,v1,v2,v1).
447 
448 .keywords: matrix, multiply, matrix-vector product, add
449 
450 .seealso: MatMultTrans(), MatMult(), MatMultTransAdd()
451 @*/
452 int MatMultAdd(Mat mat,Vec v1,Vec v2,Vec v3)
453 {
454   int ierr;
455   PetscValidHeaderSpecific(mat,MAT_COOKIE);PetscValidHeaderSpecific(v1,VEC_COOKIE);
456   PetscValidHeaderSpecific(v2,VEC_COOKIE); PetscValidHeaderSpecific(v3,VEC_COOKIE);
457   if (!mat->assembled) SETERRQ(1,"MatMultAdd:Not for unassembled matrix");
458   if (mat->factor) SETERRQ(1,"MatMult:Not for factored matrix");
459   if (mat->N != v1->N) SETERRQ(PETSC_ERR_SIZ,"MatMultAdd:Mat mat,Vec v1: global dim");
460   if (mat->M != v2->N) SETERRQ(PETSC_ERR_SIZ,"MatMultAdd:Mat mat,Vec v2: global dim");
461   if (mat->M != v3->N) SETERRQ(PETSC_ERR_SIZ,"MatMultAdd:Mat mat,Vec v3: global dim");
462   if (mat->m != v3->n) SETERRQ(PETSC_ERR_SIZ,"MatMultAdd:Mat mat,Vec v3: local dim");
463   if (mat->m != v2->n) SETERRQ(PETSC_ERR_SIZ,"MatMultAdd:Mat mat,Vec v2: local dim");
464   if (v1 == v3) SETERRQ(1,"MatMultAdd:v1 and v3 must be different vectors");
465 
466   PLogEventBegin(MAT_MultAdd,mat,v1,v2,v3);
467   ierr = (*mat->ops.multadd)(mat,v1,v2,v3); CHKERRQ(ierr);
468   PLogEventEnd(MAT_MultAdd,mat,v1,v2,v3);
469   return 0;
470 }
471 /*@
472    MatMultTransAdd - Computes v3 = v2 + A' * v1.
473 
474    Input Parameters:
475 .  mat - the matrix
476 .  v1, v2 - the vectors
477 
478    Output Parameters:
479 .  v3 - the result
480 
481    Notes:
482    The vectors v1 and v3 cannot be the same.  I.e., one cannot
483    call MatMultTransAdd(A,v1,v2,v1).
484 
485 .keywords: matrix, multiply, matrix-vector product, transpose, add
486 
487 .seealso: MatMultTrans(), MatMultAdd(), MatMult()
488 @*/
489 int MatMultTransAdd(Mat mat,Vec v1,Vec v2,Vec v3)
490 {
491   int ierr;
492   PetscValidHeaderSpecific(mat,MAT_COOKIE);PetscValidHeaderSpecific(v1,VEC_COOKIE);
493   PetscValidHeaderSpecific(v2,VEC_COOKIE);PetscValidHeaderSpecific(v3,VEC_COOKIE);
494   if (!mat->assembled) SETERRQ(1,"MatMultTransAdd:Not for unassembled matrix");
495   if (mat->factor) SETERRQ(1,"MatMult:Not for factored matrix");
496   if (!mat->ops.multtransadd) SETERRQ(PETSC_ERR_SUP,"MatMultTransAdd");
497   if (v1 == v3) SETERRQ(1,"MatMultTransAdd:v1 and v3 must be different vectors");
498   if (mat->M != v1->N) SETERRQ(PETSC_ERR_SIZ,"MatMultTransAdd:Mat mat,Vec v1: global dim");
499   if (mat->N != v2->N) SETERRQ(PETSC_ERR_SIZ,"MatMultTransAdd:Mat mat,Vec v2: global dim");
500   if (mat->N != v3->N) SETERRQ(PETSC_ERR_SIZ,"MatMultTransAdd:Mat mat,Vec v3: global dim");
501 
502   PLogEventBegin(MAT_MultTransAdd,mat,v1,v2,v3);
503   ierr = (*mat->ops.multtransadd)(mat,v1,v2,v3); CHKERRQ(ierr);
504   PLogEventEnd(MAT_MultTransAdd,mat,v1,v2,v3);
505   return 0;
506 }
507 /* ------------------------------------------------------------*/
508 /*@C
509    MatGetInfo - Returns information about matrix storage (number of
510    nonzeros, memory, etc.).
511 
512    Input Parameters:
513 .  mat - the matrix
514 
515    Output Parameters:
516 .  flag - flag indicating the type of parameters to be returned
517 $    flag = MAT_LOCAL: local matrix
518 $    flag = MAT_GLOBAL_MAX: maximum over all processors
519 $    flag = MAT_GLOBAL_SUM: sum over all processors
520 .  info - matrix information context
521 
522    Notes:
523    The MatInfo context contains a variety of matrix data, including
524    number of nonzeros allocated and used, number of mallocs during
525    matrix assembly, etc.  Additional information for factored matrices
526    is provided (such as the fill ratio, number of mallocs during
527    factorization, etc.).  Much of this info is printed to STDOUT
528    when using the runtime options
529 $       -log_info -mat_view_info
530 
531    Example for C/C++ Users:
532    See the file $(PETSC_DIR)/include/mat.h for a complete list of
533    data within the MatInfo context.  For example,
534 $
535 $      MatInfo *info;
536 $      Mat     A;
537 $      double  mal, nz_a, nz_u;
538 $
539 $      MatGetInfo(A,MAT_LOCAL,&info);
540 $      mal  = info->mallocs;
541 $      nz_a = info->nz_allocated;
542 $
543 
544    Example for Fortran Users:
545    Fortran users should declare info as a double precision
546    array of dimension MAT_INFO_SIZE, and then extract the parameters
547    of interest.  See the file $(PETSC_DIR)/include/FINCLUDE/mat.h
548    a complete list of parameter names.
549 $
550 $      double  precision info(MAT_INFO_SIZE)
551 $      double  precision mal, nz_a
552 $      Mat     A
553 $      integer ierr
554 $
555 $      call MatGetInfo(A,MAT_LOCAL,info,ierr)
556 $      mal = info(MAT_INFO_MALLOCS)
557 $      nz_a = info(MAT_INFO_NZ_ALLOCATED)
558 $
559 
560 .keywords: matrix, get, info, storage, nonzeros, memory, fill
561 @*/
562 int MatGetInfo(Mat mat,MatInfoType flag,MatInfo *info)
563 {
564   PetscValidHeaderSpecific(mat,MAT_COOKIE);
565   PetscValidPointer(info);
566   if (!mat->ops.getinfo) SETERRQ(PETSC_ERR_SUP,"MatGetInfo");
567   return  (*mat->ops.getinfo)(mat,flag,info);
568 }
569 /* ----------------------------------------------------------*/
570 /*@
571    MatILUDTFactor - Performs a drop tolerance ILU factorization.
572 
573    Input Parameters:
574 .  mat - the matrix
575 .  dt  - the drop tolerance
576 .  maxnz - the maximum number of nonzeros per row allowed?
577 .  row - row permutation
578 .  col - column permutation
579 
580    Output Parameters:
581 .  fact - the factored matrix
582 
583 .keywords: matrix, factor, LU, in-place
584 
585 .seealso: MatLUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor()
586 @*/
587 int MatILUDTFactor(Mat mat,double dt,int maxnz,IS row,IS col,Mat *fact)
588 {
589   int ierr;
590   PetscValidHeaderSpecific(mat,MAT_COOKIE);
591   PetscValidPointer(fact);
592   if (!mat->assembled) SETERRQ(1,"MatILUDTFactor:Not for unassembled matrix");
593   if (mat->factor) SETERRQ(1,"MatILUDTFactor:Not for factored matrix");
594   if (!mat->ops.iludtfactor) SETERRQ(PETSC_ERR_SUP,"MatILUDTFactor");
595 
596   PLogEventBegin(MAT_ILUFactor,mat,row,col,0);
597   ierr = (*mat->ops.iludtfactor)(mat,dt,maxnz,row,col,fact); CHKERRQ(ierr);
598   PLogEventEnd(MAT_ILUFactor,mat,row,col,0);
599 
600   return 0;
601 }
602 
603 /*@
604    MatLUFactor - Performs in-place LU factorization of matrix.
605 
606    Input Parameters:
607 .  mat - the matrix
608 .  row - row permutation
609 .  col - column permutation
610 .  f - expected fill as ratio of original fill.
611 
612 .keywords: matrix, factor, LU, in-place
613 
614 .seealso: MatLUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor()
615 @*/
616 int MatLUFactor(Mat mat,IS row,IS col,double f)
617 {
618   int ierr;
619   PetscValidHeaderSpecific(mat,MAT_COOKIE);
620   if (mat->M != mat->N) SETERRQ(1,"MatLUFactor:matrix must be square");
621   if (!mat->assembled) SETERRQ(1,"MatLUFactor:Not for unassembled matrix");
622   if (mat->factor) SETERRQ(1,"MatLUFactor:Not for factored matrix");
623   if (!mat->ops.lufactor) SETERRQ(PETSC_ERR_SUP,"MatLUFactor");
624 
625   PLogEventBegin(MAT_LUFactor,mat,row,col,0);
626   ierr = (*mat->ops.lufactor)(mat,row,col,f); CHKERRQ(ierr);
627   PLogEventEnd(MAT_LUFactor,mat,row,col,0);
628   return 0;
629 }
630 /*@
631    MatILUFactor - Performs in-place ILU factorization of matrix.
632 
633    Input Parameters:
634 .  mat - the matrix
635 .  row - row permutation
636 .  col - column permutation
637 .  f - expected fill as ratio of original fill.
638 .  level - number of levels of fill.
639 
640    Note: probably really only in-place when level is zero.
641 .keywords: matrix, factor, ILU, in-place
642 
643 .seealso: MatILUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor()
644 @*/
645 int MatILUFactor(Mat mat,IS row,IS col,double f,int level)
646 {
647   int ierr;
648   PetscValidHeaderSpecific(mat,MAT_COOKIE);
649   if (mat->M != mat->N) SETERRQ(1,"MatILUFactor:matrix must be square");
650   if (!mat->assembled) SETERRQ(1,"MatILUFactor:Not for unassembled matrix");
651   if (mat->factor) SETERRQ(1,"MatILUFactor:Not for factored matrix");
652   if (!mat->ops.ilufactor) SETERRQ(PETSC_ERR_SUP,"MatILUFactor");
653 
654   PLogEventBegin(MAT_ILUFactor,mat,row,col,0);
655   ierr = (*mat->ops.ilufactor)(mat,row,col,f,level); CHKERRQ(ierr);
656   PLogEventEnd(MAT_ILUFactor,mat,row,col,0);
657   return 0;
658 }
659 
660 /*@
661    MatLUFactorSymbolic - Performs symbolic LU factorization of matrix.
662    Call this routine before calling MatLUFactorNumeric().
663 
664    Input Parameters:
665 .  mat - the matrix
666 .  row, col - row and column permutations
667 .  f - expected fill as ratio of the original number of nonzeros,
668        for example 3.0; choosing this parameter well can result in
669        more efficient use of time and space.
670 
671    Output Parameter:
672 .  fact - new matrix that has been symbolically factored
673 
674    Options Database Key:
675 $     -mat_lu_fill <f>, where f is the fill ratio
676 
677    Notes:
678    See the file $(PETSC_DIR)/Performace for additional information about
679    choosing the fill factor for better efficiency.
680 
681 .keywords: matrix, factor, LU, symbolic, fill
682 
683 .seealso: MatLUFactor(), MatLUFactorNumeric(), MatCholeskyFactor()
684 @*/
685 int MatLUFactorSymbolic(Mat mat,IS row,IS col,double f,Mat *fact)
686 {
687   int ierr,flg;
688   PetscValidHeaderSpecific(mat,MAT_COOKIE);
689   if (mat->M != mat->N) SETERRQ(1,"MatLUFactorSymbolic:matrix must be square");
690   if (!fact) SETERRQ(1,"MatLUFactorSymbolic:Missing factor matrix argument");
691   if (!mat->assembled) SETERRQ(1,"MatLUFactorSymbolic:Not for unassembled matrix");
692   if (mat->factor) SETERRQ(1,"MatLUFactorSymbolic:Not for factored matrix");
693   if (!mat->ops.lufactorsymbolic) SETERRQ(PETSC_ERR_SUP,"MatLUFactorSymbolic");
694 
695   ierr = OptionsGetDouble(PETSC_NULL,"-mat_lu_fill",&f,&flg); CHKERRQ(ierr);
696   PLogEventBegin(MAT_LUFactorSymbolic,mat,row,col,0);
697   ierr = (*mat->ops.lufactorsymbolic)(mat,row,col,f,fact); CHKERRQ(ierr);
698   PLogEventEnd(MAT_LUFactorSymbolic,mat,row,col,0);
699   return 0;
700 }
701 /*@
702    MatLUFactorNumeric - Performs numeric LU factorization of a matrix.
703    Call this routine after first calling MatLUFactorSymbolic().
704 
705    Input Parameters:
706 .  mat - the matrix
707 .  row, col - row and  column permutations
708 
709    Output Parameters:
710 .  fact - symbolically factored matrix that must have been generated
711           by MatLUFactorSymbolic()
712 
713    Notes:
714    See MatLUFactor() for in-place factorization.  See
715    MatCholeskyFactorNumeric() for the symmetric, positive definite case.
716 
717 .keywords: matrix, factor, LU, numeric
718 
719 .seealso: MatLUFactorSymbolic(), MatLUFactor(), MatCholeskyFactor()
720 @*/
721 int MatLUFactorNumeric(Mat mat,Mat *fact)
722 {
723   int ierr,flg;
724 
725   PetscValidHeaderSpecific(mat,MAT_COOKIE);
726   if (!fact) SETERRQ(1,"MatLUFactorNumeric:Missing factor matrix argument");
727   PetscValidHeaderSpecific(*fact,MAT_COOKIE);
728   if (!mat->assembled) SETERRQ(1,"MatLUFactorNumeric:Not for unassembled matrix");
729   if (mat->M != (*fact)->M || mat->N != (*fact)->N)
730     SETERRQ(PETSC_ERR_SIZ,"MatLUFactorNumeric:Mat mat,Mat *fact: global dim");
731   if (!mat->ops.lufactornumeric) SETERRQ(PETSC_ERR_SUP,"MatLUFactorNumeric");
732 
733   PLogEventBegin(MAT_LUFactorNumeric,mat,*fact,0,0);
734   ierr = (*mat->ops.lufactornumeric)(mat,fact); CHKERRQ(ierr);
735   PLogEventEnd(MAT_LUFactorNumeric,mat,*fact,0,0);
736   ierr = OptionsHasName(PETSC_NULL,"-mat_view_draw",&flg); CHKERRQ(ierr);
737   if (flg) {
738     Viewer  viewer;
739     ierr = ViewerDrawOpenX((*fact)->comm,0,0,0,0,300,300,&viewer);CHKERRQ(ierr);
740     ierr = MatView(*fact,viewer); CHKERRQ(ierr);
741     ierr = ViewerFlush(viewer); CHKERRQ(ierr);
742     ierr = ViewerDestroy(viewer); CHKERRQ(ierr);
743   }
744   return 0;
745 }
746 
747 /*@
748    MatCholeskyFactor - Performs in-place Cholesky factorization of a
749    symmetric matrix.
750 
751    Input Parameters:
752 .  mat - the matrix
753 .  perm - row and column permutations
754 .  f - expected fill as ratio of original fill
755 
756    Notes:
757    See MatLUFactor() for the nonsymmetric case.  See also
758    MatCholeskyFactorSymbolic(), and MatCholeskyFactorNumeric().
759 
760 .keywords: matrix, factor, in-place, Cholesky
761 
762 .seealso: MatLUFactor(), MatCholeskyFactorSymbolic(), MatCholeskyFactorNumeric()
763 @*/
764 int MatCholeskyFactor(Mat mat,IS perm,double f)
765 {
766   int ierr;
767   PetscValidHeaderSpecific(mat,MAT_COOKIE);
768   if (mat->M != mat->N) SETERRQ(1,"MatCholeskyFactor:matrix must be square");
769   if (!mat->assembled) SETERRQ(1,"MatCholeskyFactor:Not for unassembled matrix");
770   if (mat->factor) SETERRQ(1,"MatCholeskyFactor:Not for factored matrix");
771   if (!mat->ops.choleskyfactor) SETERRQ(PETSC_ERR_SUP,"MatCholeskyFactor");
772 
773   PLogEventBegin(MAT_CholeskyFactor,mat,perm,0,0);
774   ierr = (*mat->ops.choleskyfactor)(mat,perm,f); CHKERRQ(ierr);
775   PLogEventEnd(MAT_CholeskyFactor,mat,perm,0,0);
776   return 0;
777 }
778 
779 /*@
780    MatCholeskyFactorSymbolic - Performs symbolic Cholesky factorization
781    of a symmetric matrix.
782 
783    Input Parameters:
784 .  mat - the matrix
785 .  perm - row and column permutations
786 .  f - expected fill as ratio of original
787 
788    Output Parameter:
789 .  fact - the factored matrix
790 
791    Notes:
792    See MatLUFactorSymbolic() for the nonsymmetric case.  See also
793    MatCholeskyFactor() and MatCholeskyFactorNumeric().
794 
795 .keywords: matrix, factor, factorization, symbolic, Cholesky
796 
797 .seealso: MatLUFactorSymbolic(), MatCholeskyFactor(), MatCholeskyFactorNumeric()
798 @*/
799 int MatCholeskyFactorSymbolic(Mat mat,IS perm,double f,Mat *fact)
800 {
801   int ierr;
802   PetscValidHeaderSpecific(mat,MAT_COOKIE);
803   PetscValidPointer(fact);
804   if (mat->M != mat->N) SETERRQ(1,"MatCholeskyFactorSymbolic:matrix must be square");
805   if (!mat->assembled) SETERRQ(1,"MatCholeskyFactorSymbolic:Not for unassembled matrix");
806   if (mat->factor) SETERRQ(1,"MatCholeskyFactorSymbolic:Not for factored matrix");
807   if (!mat->ops.choleskyfactorsymbolic)SETERRQ(PETSC_ERR_SUP,"MatCholeskyFactorSymbolic");
808 
809   PLogEventBegin(MAT_CholeskyFactorSymbolic,mat,perm,0,0);
810   ierr = (*mat->ops.choleskyfactorsymbolic)(mat,perm,f,fact); CHKERRQ(ierr);
811   PLogEventEnd(MAT_CholeskyFactorSymbolic,mat,perm,0,0);
812   return 0;
813 }
814 
815 /*@
816    MatCholeskyFactorNumeric - Performs numeric Cholesky factorization
817    of a symmetric matrix. Call this routine after first calling
818    MatCholeskyFactorSymbolic().
819 
820    Input Parameter:
821 .  mat - the initial matrix
822 
823    Output Parameter:
824 .  fact - the factored matrix
825 
826 .keywords: matrix, factor, numeric, Cholesky
827 
828 .seealso: MatCholeskyFactorSymbolic(), MatCholeskyFactor(), MatLUFactorNumeric()
829 @*/
830 int MatCholeskyFactorNumeric(Mat mat,Mat *fact)
831 {
832   int ierr;
833   PetscValidHeaderSpecific(mat,MAT_COOKIE);
834   if (!fact) SETERRQ(1,"MatCholeskyFactorNumeric:Missing factor matrix argument");
835   if (!mat->ops.choleskyfactornumeric) SETERRQ(PETSC_ERR_SUP,"MatCholeskyFactorNumeric");
836   if (!mat->assembled) SETERRQ(1,"MatCholeskyFactorNumeric:Not for unassembled matrix");
837   if (mat->M != (*fact)->M || mat->N != (*fact)->N)
838     SETERRQ(PETSC_ERR_SIZ,"MatCholeskyFactorNumeric:Mat mat,Mat *fact: global dim");
839 
840   PLogEventBegin(MAT_CholeskyFactorNumeric,mat,*fact,0,0);
841   ierr = (*mat->ops.choleskyfactornumeric)(mat,fact); CHKERRQ(ierr);
842   PLogEventEnd(MAT_CholeskyFactorNumeric,mat,*fact,0,0);
843   return 0;
844 }
845 
846 /* ----------------------------------------------------------------*/
847 /*@
848    MatSolve - Solves A x = b, given a factored matrix.
849 
850    Input Parameters:
851 .  mat - the factored matrix
852 .  b - the right-hand-side vector
853 
854    Output Parameter:
855 .  x - the result vector
856 
857    Notes:
858    The vectors b and x cannot be the same.  I.e., one cannot
859    call MatSolve(A,x,x).
860 
861 .keywords: matrix, linear system, solve, LU, Cholesky, triangular solve
862 
863 .seealso: MatSolveAdd(), MatSolveTrans(), MatSolveTransAdd()
864 @*/
865 int MatSolve(Mat mat,Vec b,Vec x)
866 {
867   int ierr;
868   PetscValidHeaderSpecific(mat,MAT_COOKIE);
869   PetscValidHeaderSpecific(b,VEC_COOKIE); PetscValidHeaderSpecific(x,VEC_COOKIE);
870   if (x == b) SETERRQ(1,"MatSolve:x and b must be different vectors");
871   if (!mat->factor) SETERRQ(1,"MatSolve:Unfactored matrix");
872   if (mat->N != x->N) SETERRQ(PETSC_ERR_SIZ,"MatSolve:Mat mat,Vec x: global dim");
873   if (mat->M != b->N) SETERRQ(PETSC_ERR_SIZ,"MatSolve:Mat mat,Vec b: global dim");
874   if (mat->m != b->n) SETERRQ(PETSC_ERR_SIZ,"MatSolve:Mat mat,Vec b: local dim");
875 
876   if (!mat->ops.solve) SETERRQ(PETSC_ERR_SUP,"MatSolve");
877   PLogEventBegin(MAT_Solve,mat,b,x,0);
878   ierr = (*mat->ops.solve)(mat,b,x); CHKERRQ(ierr);
879   PLogEventEnd(MAT_Solve,mat,b,x,0);
880   return 0;
881 }
882 
883 /* @
884    MatForwardSolve - Solves L x = b, given a factored matrix, A = LU.
885 
886    Input Parameters:
887 .  mat - the factored matrix
888 .  b - the right-hand-side vector
889 
890    Output Parameter:
891 .  x - the result vector
892 
893    Notes:
894    MatSolve() should be used for most applications, as it performs
895    a forward solve followed by a backward solve.
896 
897    The vectors b and x cannot be the same.  I.e., one cannot
898    call MatForwardSolve(A,x,x).
899 
900 .keywords: matrix, forward, LU, Cholesky, triangular solve
901 
902 .seealso: MatSolve(), MatBackwardSolve()
903 @ */
904 int MatForwardSolve(Mat mat,Vec b,Vec x)
905 {
906   int ierr;
907   PetscValidHeaderSpecific(mat,MAT_COOKIE);
908   PetscValidHeaderSpecific(b,VEC_COOKIE);  PetscValidHeaderSpecific(x,VEC_COOKIE);
909   if (x == b) SETERRQ(1,"MatForwardSolve:x and b must be different vectors");
910   if (!mat->factor) SETERRQ(1,"MatForwardSolve:Unfactored matrix");
911   if (!mat->ops.forwardsolve) SETERRQ(PETSC_ERR_SUP,"MatForwardSolve");
912   if (mat->N != x->N) SETERRQ(PETSC_ERR_SIZ,"MatForwardSolve:Mat mat,Vec x: global dim");
913   if (mat->M != b->N) SETERRQ(PETSC_ERR_SIZ,"MatForwardSolve:Mat mat,Vec b: global dim");
914   if (mat->m != b->n) SETERRQ(PETSC_ERR_SIZ,"MatForwardSolve:Mat mat,Vec b: local dim");
915 
916   PLogEventBegin(MAT_ForwardSolve,mat,b,x,0);
917   ierr = (*mat->ops.forwardsolve)(mat,b,x); CHKERRQ(ierr);
918   PLogEventEnd(MAT_ForwardSolve,mat,b,x,0);
919   return 0;
920 }
921 
922 /* @
923    MatBackwardSolve - Solves U x = b, given a factored matrix, A = LU.
924 
925    Input Parameters:
926 .  mat - the factored matrix
927 .  b - the right-hand-side vector
928 
929    Output Parameter:
930 .  x - the result vector
931 
932    Notes:
933    MatSolve() should be used for most applications, as it performs
934    a forward solve followed by a backward solve.
935 
936    The vectors b and x cannot be the same.  I.e., one cannot
937    call MatBackwardSolve(A,x,x).
938 
939 .keywords: matrix, backward, LU, Cholesky, triangular solve
940 
941 .seealso: MatSolve(), MatForwardSolve()
942 @ */
943 int MatBackwardSolve(Mat mat,Vec b,Vec x)
944 {
945   int ierr;
946   PetscValidHeaderSpecific(mat,MAT_COOKIE);
947   PetscValidHeaderSpecific(b,VEC_COOKIE);  PetscValidHeaderSpecific(x,VEC_COOKIE);
948   if (x == b) SETERRQ(1,"MatBackwardSolve:x and b must be different vectors");
949   if (!mat->factor) SETERRQ(1,"MatBackwardSolve:Unfactored matrix");
950   if (!mat->ops.backwardsolve) SETERRQ(PETSC_ERR_SUP,"MatBackwardSolve");
951   if (mat->N != x->N) SETERRQ(PETSC_ERR_SIZ,"MatBackwardSolve:Mat mat,Vec x: global dim");
952   if (mat->M != b->N) SETERRQ(PETSC_ERR_SIZ,"MatBackwardSolve:Mat mat,Vec b: global dim");
953   if (mat->m != b->n) SETERRQ(PETSC_ERR_SIZ,"MatBackwardSolve:Mat mat,Vec b: local dim");
954 
955   PLogEventBegin(MAT_BackwardSolve,mat,b,x,0);
956   ierr = (*mat->ops.backwardsolve)(mat,b,x); CHKERRQ(ierr);
957   PLogEventEnd(MAT_BackwardSolve,mat,b,x,0);
958   return 0;
959 }
960 
961 /*@
962    MatSolveAdd - Computes x = y + inv(A)*b, given a factored matrix.
963 
964    Input Parameters:
965 .  mat - the factored matrix
966 .  b - the right-hand-side vector
967 .  y - the vector to be added to
968 
969    Output Parameter:
970 .  x - the result vector
971 
972    Notes:
973    The vectors b and x cannot be the same.  I.e., one cannot
974    call MatSolveAdd(A,x,y,x).
975 
976 .keywords: matrix, linear system, solve, LU, Cholesky, add
977 
978 .seealso: MatSolve(), MatSolveTrans(), MatSolveTransAdd()
979 @*/
980 int MatSolveAdd(Mat mat,Vec b,Vec y,Vec x)
981 {
982   Scalar one = 1.0;
983   Vec    tmp;
984   int    ierr;
985   PetscValidHeaderSpecific(mat,MAT_COOKIE);PetscValidHeaderSpecific(y,VEC_COOKIE);
986   PetscValidHeaderSpecific(b,VEC_COOKIE);  PetscValidHeaderSpecific(x,VEC_COOKIE);
987   if (x == b) SETERRQ(1,"MatSolveAdd:x and b must be different vectors");
988   if (!mat->factor) SETERRQ(1,"MatSolveAdd:Unfactored matrix");
989   if (mat->N != x->N) SETERRQ(PETSC_ERR_SIZ,"MatSolveAdd:Mat mat,Vec x: global dim");
990   if (mat->M != b->N) SETERRQ(PETSC_ERR_SIZ,"MatSolveAdd:Mat mat,Vec b: global dim");
991   if (mat->M != y->N) SETERRQ(PETSC_ERR_SIZ,"MatSolveAdd:Mat mat,Vec y: global dim");
992   if (mat->m != b->n) SETERRQ(PETSC_ERR_SIZ,"MatSolveAdd:Mat mat,Vec b: local dim");
993   if (x->n != y->n) SETERRQ(PETSC_ERR_SIZ,"MatSolveAdd:Vec x,Vec y: local dim");
994 
995   PLogEventBegin(MAT_SolveAdd,mat,b,x,y);
996   if (mat->ops.solveadd)  {
997     ierr = (*mat->ops.solveadd)(mat,b,y,x); CHKERRQ(ierr);
998   }
999   else {
1000     /* do the solve then the add manually */
1001     if (x != y) {
1002       ierr = MatSolve(mat,b,x); CHKERRQ(ierr);
1003       ierr = VecAXPY(&one,y,x); CHKERRQ(ierr);
1004     }
1005     else {
1006       ierr = VecDuplicate(x,&tmp); CHKERRQ(ierr);
1007       PLogObjectParent(mat,tmp);
1008       ierr = VecCopy(x,tmp); CHKERRQ(ierr);
1009       ierr = MatSolve(mat,b,x); CHKERRQ(ierr);
1010       ierr = VecAXPY(&one,tmp,x); CHKERRQ(ierr);
1011       ierr = VecDestroy(tmp); CHKERRQ(ierr);
1012     }
1013   }
1014   PLogEventEnd(MAT_SolveAdd,mat,b,x,y);
1015   return 0;
1016 }
1017 
1018 /*@
1019    MatSolveTrans - Solves A' x = b, given a factored matrix.
1020 
1021    Input Parameters:
1022 .  mat - the factored matrix
1023 .  b - the right-hand-side vector
1024 
1025    Output Parameter:
1026 .  x - the result vector
1027 
1028    Notes:
1029    The vectors b and x cannot be the same.  I.e., one cannot
1030    call MatSolveTrans(A,x,x).
1031 
1032 .keywords: matrix, linear system, solve, LU, Cholesky, transpose
1033 
1034 .seealso: MatSolve(), MatSolveAdd(), MatSolveTransAdd()
1035 @*/
1036 int MatSolveTrans(Mat mat,Vec b,Vec x)
1037 {
1038   int ierr;
1039   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1040   PetscValidHeaderSpecific(b,VEC_COOKIE);  PetscValidHeaderSpecific(x,VEC_COOKIE);
1041   if (!mat->factor) SETERRQ(1,"MatSolveTrans:Unfactored matrix");
1042   if (x == b) SETERRQ(1,"MatSolveTrans:x and b must be different vectors");
1043   if (!mat->ops.solvetrans) SETERRQ(PETSC_ERR_SUP,"MatSolveTrans");
1044   if (mat->M != x->N) SETERRQ(PETSC_ERR_SIZ,"MatSolveTrans:Mat mat,Vec x: global dim");
1045   if (mat->N != b->N) SETERRQ(PETSC_ERR_SIZ,"MatSolveTrans:Mat mat,Vec b: global dim");
1046 
1047   PLogEventBegin(MAT_SolveTrans,mat,b,x,0);
1048   ierr = (*mat->ops.solvetrans)(mat,b,x); CHKERRQ(ierr);
1049   PLogEventEnd(MAT_SolveTrans,mat,b,x,0);
1050   return 0;
1051 }
1052 
1053 /*@
1054    MatSolveTransAdd - Computes x = y + inv(trans(A)) b, given a
1055                       factored matrix.
1056 
1057    Input Parameters:
1058 .  mat - the factored matrix
1059 .  b - the right-hand-side vector
1060 .  y - the vector to be added to
1061 
1062    Output Parameter:
1063 .  x - the result vector
1064 
1065    Notes:
1066    The vectors b and x cannot be the same.  I.e., one cannot
1067    call MatSolveTransAdd(A,x,y,x).
1068 
1069 .keywords: matrix, linear system, solve, LU, Cholesky, transpose, add
1070 
1071 .seealso: MatSolve(), MatSolveAdd(), MatSolveTrans()
1072 @*/
1073 int MatSolveTransAdd(Mat mat,Vec b,Vec y,Vec x)
1074 {
1075   Scalar one = 1.0;
1076   int    ierr;
1077   Vec    tmp;
1078   PetscValidHeaderSpecific(mat,MAT_COOKIE);PetscValidHeaderSpecific(y,VEC_COOKIE);
1079   PetscValidHeaderSpecific(b,VEC_COOKIE);  PetscValidHeaderSpecific(x,VEC_COOKIE);
1080   if (x == b) SETERRQ(1,"MatSolveTransAdd:x and b must be different vectors");
1081   if (!mat->factor) SETERRQ(1,"MatSolveTransAdd:Unfactored matrix");
1082   if (mat->M != x->N) SETERRQ(PETSC_ERR_SIZ,"MatSolveTransAdd:Mat mat,Vec x: global dim");
1083   if (mat->N != b->N) SETERRQ(PETSC_ERR_SIZ,"MatSolveTransAdd:Mat mat,Vec b: global dim");
1084   if (mat->N != y->N) SETERRQ(PETSC_ERR_SIZ,"MatSolveTransAdd:Mat mat,Vec y: global dim");
1085   if (x->n != y->n) SETERRQ(PETSC_ERR_SIZ,"MatSolveTransAdd:Vec x,Vec y: local dim");
1086 
1087   PLogEventBegin(MAT_SolveTransAdd,mat,b,x,y);
1088   if (mat->ops.solvetransadd) {
1089     ierr = (*mat->ops.solvetransadd)(mat,b,y,x); CHKERRQ(ierr);
1090   }
1091   else {
1092     /* do the solve then the add manually */
1093     if (x != y) {
1094       ierr = MatSolveTrans(mat,b,x); CHKERRQ(ierr);
1095       ierr = VecAXPY(&one,y,x); CHKERRQ(ierr);
1096     }
1097     else {
1098       ierr = VecDuplicate(x,&tmp); CHKERRQ(ierr);
1099       PLogObjectParent(mat,tmp);
1100       ierr = VecCopy(x,tmp); CHKERRQ(ierr);
1101       ierr = MatSolveTrans(mat,b,x); CHKERRQ(ierr);
1102       ierr = VecAXPY(&one,tmp,x); CHKERRQ(ierr);
1103       ierr = VecDestroy(tmp); CHKERRQ(ierr);
1104     }
1105   }
1106   PLogEventEnd(MAT_SolveTransAdd,mat,b,x,y);
1107   return 0;
1108 }
1109 /* ----------------------------------------------------------------*/
1110 
1111 /*@
1112    MatRelax - Computes one relaxation sweep.
1113 
1114    Input Parameters:
1115 .  mat - the matrix
1116 .  b - the right hand side
1117 .  omega - the relaxation factor
1118 .  flag - flag indicating the type of SOR, one of
1119 $     SOR_FORWARD_SWEEP
1120 $     SOR_BACKWARD_SWEEP
1121 $     SOR_SYMMETRIC_SWEEP (SSOR method)
1122 $     SOR_LOCAL_FORWARD_SWEEP
1123 $     SOR_LOCAL_BACKWARD_SWEEP
1124 $     SOR_LOCAL_SYMMETRIC_SWEEP (local SSOR)
1125 $     SOR_APPLY_UPPER, SOR_APPLY_LOWER - applies
1126 $       upper/lower triangular part of matrix to
1127 $       vector (with omega)
1128 $     SOR_ZERO_INITIAL_GUESS - zero initial guess
1129 .  shift -  diagonal shift
1130 .  its - the number of iterations
1131 
1132    Output Parameters:
1133 .  x - the solution (can contain an initial guess)
1134 
1135    Notes:
1136    SOR_LOCAL_FORWARD_SWEEP, SOR_LOCAL_BACKWARD_SWEEP, and
1137    SOR_LOCAL_SYMMETRIC_SWEEP perform seperate independent smoothings
1138    on each processor.
1139 
1140    Application programmers will not generally use MatRelax() directly,
1141    but instead will employ the SLES/PC interface.
1142 
1143    Notes for Advanced Users:
1144    The flags are implemented as bitwise inclusive or operations.
1145    For example, use (SOR_ZERO_INITIAL_GUESS | SOR_SYMMETRIC_SWEEP)
1146    to specify a zero initial guess for SSOR.
1147 
1148 .keywords: matrix, relax, relaxation, sweep
1149 @*/
1150 int MatRelax(Mat mat,Vec b,double omega,MatSORType flag,double shift,
1151              int its,Vec x)
1152 {
1153   int ierr;
1154   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1155   PetscValidHeaderSpecific(b,VEC_COOKIE);  PetscValidHeaderSpecific(x,VEC_COOKIE);
1156   if (!mat->ops.relax) SETERRQ(PETSC_ERR_SUP,"MatRelax");
1157   if (!mat->assembled) SETERRQ(1,"MatRelax:Not for unassembled matrix");
1158   if (mat->factor) SETERRQ(1,"MatRelax:Not for factored matrix");
1159   if (mat->N != x->N) SETERRQ(PETSC_ERR_SIZ,"MatRelax:Mat mat,Vec x: global dim");
1160   if (mat->M != b->N) SETERRQ(PETSC_ERR_SIZ,"MatRelax:Mat mat,Vec b: global dim");
1161   if (mat->m != b->n) SETERRQ(PETSC_ERR_SIZ,"MatRelax:Mat mat,Vec b: local dim");
1162 
1163   PLogEventBegin(MAT_Relax,mat,b,x,0);
1164   ierr =(*mat->ops.relax)(mat,b,omega,flag,shift,its,x); CHKERRQ(ierr);
1165   PLogEventEnd(MAT_Relax,mat,b,x,0);
1166   return 0;
1167 }
1168 
1169 /*
1170       Default matrix copy routine.
1171 */
1172 int MatCopy_Basic(Mat A,Mat B)
1173 {
1174   int    ierr,i,rstart,rend,nz,*cwork;
1175   Scalar *vwork;
1176 
1177   ierr = MatZeroEntries(B); CHKERRQ(ierr);
1178   ierr = MatGetOwnershipRange(A,&rstart,&rend); CHKERRQ(ierr);
1179   for (i=rstart; i<rend; i++) {
1180     ierr = MatGetRow(A,i,&nz,&cwork,&vwork); CHKERRQ(ierr);
1181     ierr = MatSetValues(B,1,&i,nz,cwork,vwork,INSERT_VALUES); CHKERRQ(ierr);
1182     ierr = MatRestoreRow(A,i,&nz,&cwork,&vwork); CHKERRQ(ierr);
1183   }
1184   ierr = MatAssemblyBegin(B,MAT_FINAL_ASSEMBLY); CHKERRQ(ierr);
1185   ierr = MatAssemblyEnd(B,MAT_FINAL_ASSEMBLY); CHKERRQ(ierr);
1186   return 0;
1187 }
1188 
1189 /*@C
1190    MatCopy - Copys a matrix to another matrix.
1191 
1192    Input Parameters:
1193 .  A - the matrix
1194 
1195    Output Parameter:
1196 .  B - where the copy is put
1197 
1198    Notes:
1199    MatCopy() copies the matrix entries of a matrix to another existing
1200    matrix (after first zeroing the second matrix).  A related routine is
1201    MatConvert(), which first creates a new matrix and then copies the data.
1202 
1203 .keywords: matrix, copy, convert
1204 
1205 .seealso: MatConvert()
1206 @*/
1207 int MatCopy(Mat A,Mat B)
1208 {
1209   int ierr;
1210   PetscValidHeaderSpecific(A,MAT_COOKIE); PetscValidHeaderSpecific(B,MAT_COOKIE);
1211   if (!A->assembled) SETERRQ(1,"MatCopy:Not for unassembled matrix");
1212   if (A->factor) SETERRQ(1,"MatCopy:Not for factored matrix");
1213   if (A->M != B->M || A->N != B->N) SETERRQ(PETSC_ERR_SIZ,"MatCopy:Mat A,Mat B: global dim");
1214 
1215   PLogEventBegin(MAT_Copy,A,B,0,0);
1216   if (A->ops.copy) {
1217     ierr = (*A->ops.copy)(A,B); CHKERRQ(ierr);
1218   }
1219   else { /* generic conversion */
1220     ierr = MatCopy_Basic(A,B); CHKERRQ(ierr);
1221   }
1222   PLogEventEnd(MAT_Copy,A,B,0,0);
1223   return 0;
1224 }
1225 
1226 /*@C
1227    MatConvert - Converts a matrix to another matrix, either of the same
1228    or different type.
1229 
1230    Input Parameters:
1231 .  mat - the matrix
1232 .  newtype - new matrix type.  Use MATSAME to create a new matrix of the
1233    same type as the original matrix.
1234 
1235    Output Parameter:
1236 .  M - pointer to place new matrix
1237 
1238    Notes:
1239    MatConvert() first creates a new matrix and then copies the data from
1240    the first matrix.  A related routine is MatCopy(), which copies the matrix
1241    entries of one matrix to another already existing matrix context.
1242 
1243 .keywords: matrix, copy, convert
1244 
1245 .seealso: MatCopy()
1246 @*/
1247 int MatConvert(Mat mat,MatType newtype,Mat *M)
1248 {
1249   int ierr;
1250   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1251   if (!M) SETERRQ(1,"MatConvert:Bad new matrix address");
1252   if (!mat->assembled) SETERRQ(1,"MatConvert:Not for unassembled matrix");
1253   if (mat->factor) SETERRQ(1,"MatConvert:Not for factored matrix");
1254 
1255   PLogEventBegin(MAT_Convert,mat,0,0,0);
1256   if (newtype == mat->type || newtype == MATSAME) {
1257     if (mat->ops.convertsametype) { /* customized copy */
1258       ierr = (*mat->ops.convertsametype)(mat,M,COPY_VALUES); CHKERRQ(ierr);
1259     }
1260     else { /* generic conversion */
1261       ierr = MatConvert_Basic(mat,newtype,M); CHKERRQ(ierr);
1262     }
1263   }
1264   else if (mat->ops.convert) { /* customized conversion */
1265     ierr = (*mat->ops.convert)(mat,newtype,M); CHKERRQ(ierr);
1266   }
1267   else { /* generic conversion */
1268     ierr = MatConvert_Basic(mat,newtype,M); CHKERRQ(ierr);
1269   }
1270   PLogEventEnd(MAT_Convert,mat,0,0,0);
1271   return 0;
1272 }
1273 
1274 /*@
1275    MatGetDiagonal - Gets the diagonal of a matrix.
1276 
1277    Input Parameters:
1278 .  mat - the matrix
1279 .  v - the vector for storing the diagonal
1280 
1281    Output Parameter:
1282 .  v - the diagonal of the matrix
1283 
1284 .keywords: matrix, get, diagonal
1285 @*/
1286 int MatGetDiagonal(Mat mat,Vec v)
1287 {
1288   PetscValidHeaderSpecific(mat,MAT_COOKIE);PetscValidHeaderSpecific(v,VEC_COOKIE);
1289   if (!mat->assembled) SETERRQ(1,"MatGetDiagonal:Not for unassembled matrix");
1290   if (mat->factor) SETERRQ(1,"MatGetDiagonal:Not for factored matrix");
1291   if (!mat->ops.getdiagonal) SETERRQ(PETSC_ERR_SUP,"MatGetDiagonal");
1292   return (*mat->ops.getdiagonal)(mat,v);
1293 }
1294 
1295 /*@C
1296    MatTranspose - Computes an in-place or out-of-place transpose of a matrix.
1297 
1298    Input Parameter:
1299 .  mat - the matrix to transpose
1300 
1301    Output Parameters:
1302 .  B - the transpose (or pass in PETSC_NULL for an in-place transpose)
1303 
1304 .keywords: matrix, transpose
1305 
1306 .seealso: MatMultTrans(), MatMultTransAdd()
1307 @*/
1308 int MatTranspose(Mat mat,Mat *B)
1309 {
1310   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1311   if (!mat->assembled) SETERRQ(1,"MatTranspose:Not for unassembled matrix");
1312   if (mat->factor) SETERRQ(1,"MatTranspose:Not for factored matrix");
1313   if (!mat->ops.transpose) SETERRQ(PETSC_ERR_SUP,"MatTranspose");
1314   return (*mat->ops.transpose)(mat,B);
1315 }
1316 
1317 /*@
1318    MatEqual - Compares two matrices.
1319 
1320    Input Parameters:
1321 .  A - the first matrix
1322 .  B - the second matrix
1323 
1324    Output Parameter:
1325 .  flg : PETSC_TRUE if the matrices are equal;
1326          PETSC_FALSE otherwise.
1327 
1328 .keywords: matrix, equal, equivalent
1329 @*/
1330 int MatEqual(Mat A,Mat B,PetscTruth *flg)
1331 {
1332   PetscValidHeaderSpecific(A,MAT_COOKIE); PetscValidHeaderSpecific(B,MAT_COOKIE);
1333   PetscValidIntPointer(flg);
1334   if (!A->assembled) SETERRQ(1,"MatEqual:Not for unassembled matrix");
1335   if (!B->assembled) SETERRQ(1,"MatEqual:Not for unassembled matrix");
1336   if (A->M != B->M || A->N != B->N) SETERRQ(PETSC_ERR_SIZ,"MatCopy:Mat A,Mat B: global dim");
1337   if (!A->ops.equal) SETERRQ(PETSC_ERR_SUP,"MatEqual");
1338   return (*A->ops.equal)(A,B,flg);
1339 }
1340 
1341 /*@
1342    MatDiagonalScale - Scales a matrix on the left and right by diagonal
1343    matrices that are stored as vectors.  Either of the two scaling
1344    matrices can be PETSC_NULL.
1345 
1346    Input Parameters:
1347 .  mat - the matrix to be scaled
1348 .  l - the left scaling vector (or PETSC_NULL)
1349 .  r - the right scaling vector (or PETSC_NULL)
1350 
1351    Notes:
1352    MatDiagonalScale() computes A <- LAR, where
1353 $      L = a diagonal matrix
1354 $      R = a diagonal matrix
1355 
1356 .keywords: matrix, diagonal, scale
1357 
1358 .seealso: MatDiagonalScale()
1359 @*/
1360 int MatDiagonalScale(Mat mat,Vec l,Vec r)
1361 {
1362   int ierr;
1363   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1364   if (!mat->ops.diagonalscale) SETERRQ(PETSC_ERR_SUP,"MatDiagonalScale");
1365   if (l) PetscValidHeaderSpecific(l,VEC_COOKIE);
1366   if (r) PetscValidHeaderSpecific(r,VEC_COOKIE);
1367   if (!mat->assembled) SETERRQ(1,"MatDiagonalScale:Not for unassembled matrix");
1368   if (mat->factor) SETERRQ(1,"MatDiagonalScale:Not for factored matrix");
1369 
1370   PLogEventBegin(MAT_Scale,mat,0,0,0);
1371   ierr = (*mat->ops.diagonalscale)(mat,l,r); CHKERRQ(ierr);
1372   PLogEventEnd(MAT_Scale,mat,0,0,0);
1373   return 0;
1374 }
1375 
1376 /*@
1377     MatScale - Scales all elements of a matrix by a given number.
1378 
1379     Input Parameters:
1380 .   mat - the matrix to be scaled
1381 .   a  - the scaling value
1382 
1383     Output Parameter:
1384 .   mat - the scaled matrix
1385 
1386 .keywords: matrix, scale
1387 
1388 .seealso: MatDiagonalScale()
1389 @*/
1390 int MatScale(Scalar *a,Mat mat)
1391 {
1392   int ierr;
1393   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1394   PetscValidScalarPointer(a);
1395   if (!mat->ops.scale) SETERRQ(PETSC_ERR_SUP,"MatScale");
1396   if (!mat->assembled) SETERRQ(1,"MatScale:Not for unassembled matrix");
1397   if (mat->factor) SETERRQ(1,"MatScale:Not for factored matrix");
1398 
1399   PLogEventBegin(MAT_Scale,mat,0,0,0);
1400   ierr = (*mat->ops.scale)(a,mat); CHKERRQ(ierr);
1401   PLogEventEnd(MAT_Scale,mat,0,0,0);
1402   return 0;
1403 }
1404 
1405 /*@
1406    MatNorm - Calculates various norms of a matrix.
1407 
1408    Input Parameters:
1409 .  mat - the matrix
1410 .  type - the type of norm, NORM_1, NORM_2, NORM_FROBENIUS, NORM_INFINITY
1411 
1412    Output Parameters:
1413 .  norm - the resulting norm
1414 
1415 .keywords: matrix, norm, Frobenius
1416 @*/
1417 int MatNorm(Mat mat,NormType type,double *norm)
1418 {
1419   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1420   PetscValidScalarPointer(norm);
1421 
1422   if (!norm) SETERRQ(1,"MatNorm:bad addess for value");
1423   if (!mat->assembled) SETERRQ(1,"MatNorm:Not for unassembled matrix");
1424   if (mat->factor) SETERRQ(1,"MatNorm:Not for factored matrix");
1425   if (!mat->ops.norm) SETERRQ(PETSC_ERR_SUP,"MatNorm:Not for this matrix type");
1426   return (*mat->ops.norm)(mat,type,norm);
1427 }
1428 
1429 /*
1430      This variable is used to prevent counting of MatAssemblyBegin() that
1431    are called from within a MatAssemblyEnd().
1432 */
1433 static int MatAssemblyEnd_InUse = 0;
1434 /*@
1435    MatAssemblyBegin - Begins assembling the matrix.  This routine should
1436    be called after completing all calls to MatSetValues().
1437 
1438    Input Parameters:
1439 .  mat - the matrix
1440 .  type - type of assembly, either MAT_FLUSH_ASSEMBLY or MAT_FINAL_ASSEMBLY
1441 
1442    Notes:
1443    MatSetValues() generally caches the values.  The matrix is ready to
1444    use only after MatAssemblyBegin() and MatAssemblyEnd() have been called.
1445    Use MAT_FLUSH_ASSEMBLY when switching between ADD_VALUES and INSERT_VALUES
1446    in MatSetValues(); use MAT_FINAL_ASSEMBLY for the final assembly before
1447    using the matrix.
1448 
1449 .keywords: matrix, assembly, assemble, begin
1450 
1451 .seealso: MatAssemblyEnd(), MatSetValues()
1452 @*/
1453 int MatAssemblyBegin(Mat mat,MatAssemblyType type)
1454 {
1455   int ierr;
1456   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1457   if (mat->factor) SETERRQ(1,"MatAssemblyBegin:Not for factored matrix");
1458   if (mat->assembled) {
1459     mat->was_assembled = PETSC_TRUE;
1460     mat->assembled     = PETSC_FALSE;
1461   }
1462   if (!MatAssemblyEnd_InUse) {
1463     PLogEventBegin(MAT_AssemblyBegin,mat,0,0,0);
1464     if (mat->ops.assemblybegin){ierr = (*mat->ops.assemblybegin)(mat,type);CHKERRQ(ierr);}
1465     PLogEventEnd(MAT_AssemblyBegin,mat,0,0,0);
1466   } else {
1467     if (mat->ops.assemblybegin){ierr = (*mat->ops.assemblybegin)(mat,type);CHKERRQ(ierr);}
1468   }
1469   return 0;
1470 }
1471 
1472 /*@
1473    MatAssemblyEnd - Completes assembling the matrix.  This routine should
1474    be called after MatAssemblyBegin().
1475 
1476    Input Parameters:
1477 .  mat - the matrix
1478 .  type - type of assembly, either MAT_FLUSH_ASSEMBLY or MAT_FINAL_ASSEMBLY
1479 
1480    Options Database Keys:
1481 $  -mat_view_info : Prints info on matrix at
1482 $      conclusion of MatEndAssembly()
1483 $  -mat_view_info_detailed: Prints more detailed info.
1484 $  -mat_view : Prints matrix in ASCII format.
1485 $  -mat_view_matlab : Prints matrix in Matlab format.
1486 $  -mat_view_draw : Draws nonzero structure of matrix,
1487 $      using MatView() and DrawOpenX().
1488 $  -display <name> : Set display name (default is host)
1489 $  -draw_pause <sec> : Set number of seconds to pause after display
1490 
1491    Notes:
1492    MatSetValues() generally caches the values.  The matrix is ready to
1493    use only after MatAssemblyBegin() and MatAssemblyEnd() have been called.
1494    Use MAT_FLUSH_ASSEMBLY when switching between ADD_VALUES and INSERT_VALUES
1495    in MatSetValues(); use MAT_FINAL_ASSEMBLY for the final assembly before
1496    using the matrix.
1497 
1498 .keywords: matrix, assembly, assemble, end
1499 
1500 .seealso: MatAssemblyBegin(), MatSetValues(), DrawOpenX(), MatView()
1501 @*/
1502 int MatAssemblyEnd(Mat mat,MatAssemblyType type)
1503 {
1504   int        ierr,flg;
1505   static int inassm = 0;
1506 
1507   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1508   inassm++;
1509   MatAssemblyEnd_InUse++;
1510   PLogEventBegin(MAT_AssemblyEnd,mat,0,0,0);
1511   if (mat->ops.assemblyend) {
1512     ierr = (*mat->ops.assemblyend)(mat,type); CHKERRQ(ierr);
1513   }
1514   mat->assembled = PETSC_TRUE; mat->num_ass++;
1515   PLogEventEnd(MAT_AssemblyEnd,mat,0,0,0);
1516   MatAssemblyEnd_InUse--;
1517 
1518   if (inassm == 1) {
1519     ierr = OptionsHasName(PETSC_NULL,"-mat_view_info",&flg); CHKERRQ(ierr);
1520     if (flg) {
1521       Viewer viewer;
1522       ierr = ViewerFileOpenASCII(mat->comm,"stdout",&viewer);CHKERRQ(ierr);
1523       ierr = ViewerSetFormat(viewer,VIEWER_FORMAT_ASCII_INFO,0);CHKERRQ(ierr);
1524       ierr = MatView(mat,viewer); CHKERRQ(ierr);
1525       ierr = ViewerDestroy(viewer); CHKERRQ(ierr);
1526     }
1527     ierr = OptionsHasName(PETSC_NULL,"-mat_view_info_detailed",&flg);CHKERRQ(ierr);
1528     if (flg) {
1529       Viewer viewer;
1530       ierr = ViewerFileOpenASCII(mat->comm,"stdout",&viewer);CHKERRQ(ierr);
1531       ierr = ViewerSetFormat(viewer,VIEWER_FORMAT_ASCII_INFO_LONG,0);CHKERRQ(ierr);
1532       ierr = MatView(mat,viewer); CHKERRQ(ierr);
1533       ierr = ViewerDestroy(viewer); CHKERRQ(ierr);
1534     }
1535     ierr = OptionsHasName(PETSC_NULL,"-mat_view",&flg); CHKERRQ(ierr);
1536     if (flg) {
1537       Viewer viewer;
1538       ierr = ViewerFileOpenASCII(mat->comm,"stdout",&viewer);CHKERRQ(ierr);
1539       ierr = MatView(mat,viewer); CHKERRQ(ierr);
1540       ierr = ViewerDestroy(viewer); CHKERRQ(ierr);
1541     }
1542     ierr = OptionsHasName(PETSC_NULL,"-mat_view_matlab",&flg); CHKERRQ(ierr);
1543     if (flg) {
1544       Viewer viewer;
1545       ierr = ViewerFileOpenASCII(mat->comm,"stdout",&viewer);CHKERRQ(ierr);
1546       ierr = ViewerSetFormat(viewer,VIEWER_FORMAT_ASCII_MATLAB,"M");CHKERRQ(ierr);
1547       ierr = MatView(mat,viewer); CHKERRQ(ierr);
1548       ierr = ViewerDestroy(viewer); CHKERRQ(ierr);
1549     }
1550     ierr = OptionsHasName(PETSC_NULL,"-mat_view_draw",&flg); CHKERRQ(ierr);
1551     if (flg) {
1552       Viewer    viewer;
1553       ierr = ViewerDrawOpenX(mat->comm,0,0,0,0,300,300,&viewer); CHKERRQ(ierr);
1554       ierr = MatView(mat,viewer); CHKERRQ(ierr);
1555       ierr = ViewerFlush(viewer); CHKERRQ(ierr);
1556       ierr = ViewerDestroy(viewer); CHKERRQ(ierr);
1557     }
1558   }
1559   inassm--;
1560   return 0;
1561 }
1562 
1563 /*@
1564    MatCompress - Tries to store the matrix in as little space as
1565    possible.  May fail if memory is already fully used, since it
1566    tries to allocate new space.
1567 
1568    Input Parameters:
1569 .  mat - the matrix
1570 
1571 .keywords: matrix, compress
1572 @*/
1573 int MatCompress(Mat mat)
1574 {
1575   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1576   if (mat->ops.compress) return (*mat->ops.compress)(mat);
1577   return 0;
1578 }
1579 
1580 /*@
1581    MatSetOption - Sets a parameter option for a matrix. Some options
1582    may be specific to certain storage formats.  Some options
1583    determine how values will be inserted (or added). Sorted,
1584    row-oriented input will generally assemble the fastest. The default
1585    is row-oriented, nonsorted input.
1586 
1587    Input Parameters:
1588 .  mat - the matrix
1589 .  option - the option, one of the following:
1590 $    MAT_ROW_ORIENTED
1591 $    MAT_COLUMN_ORIENTED,
1592 $    MAT_ROWS_SORTED,
1593 $    MAT_COLUMNS_SORTED,
1594 $    MAT_NO_NEW_NONZERO_LOCATIONS,
1595 $    MAT_YES_NEW_NONZERO_LOCATIONS,
1596 $    MAT_SYMMETRIC,
1597 $    MAT_STRUCTURALLY_SYMMETRIC,
1598 $    MAT_NO_NEW_DIAGONALS,
1599 $    MAT_YES_NEW_DIAGONALS,
1600 $    MAT_IGNORE_OFF_PROCESSOR_ENTRIES
1601 $    and possibly others.
1602 
1603    Notes:
1604    Some options are relevant only for particular matrix types and
1605    are thus ignored by others.  Other options are not supported by
1606    certain matrix types and will generate an error message if set.
1607 
1608    If using a Fortran 77 module to compute a matrix, one may need to
1609    use the column-oriented option (or convert to the row-oriented
1610    format).
1611 
1612    MAT_NO_NEW_NONZERO_LOCATIONS indicates that any add or insertion
1613    that will generate a new entry in the nonzero structure is ignored.
1614    What this means is if memory is not allocated for this particular
1615    lot, then the insertion is ignored. For dense matrices, where
1616    the entire array is allocated, no entries are ever ignored.
1617 
1618    MAT_IGNORE_OFF_PROCESSOR_ENTRIES indicates entries destined for
1619    other processors are dropped, rather then stashed.
1620 
1621 .keywords: matrix, option, row-oriented, column-oriented, sorted, nonzero
1622 @*/
1623 int MatSetOption(Mat mat,MatOption op)
1624 {
1625   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1626   if (mat->ops.setoption) return (*mat->ops.setoption)(mat,op);
1627   return 0;
1628 }
1629 
1630 /*@
1631    MatZeroEntries - Zeros all entries of a matrix.  For sparse matrices
1632    this routine retains the old nonzero structure.
1633 
1634    Input Parameters:
1635 .  mat - the matrix
1636 
1637 .keywords: matrix, zero, entries
1638 
1639 .seealso: MatZeroRows()
1640 @*/
1641 int MatZeroEntries(Mat mat)
1642 {
1643   int ierr;
1644   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1645   if (mat->factor) SETERRQ(1,"MatZeroEntries:Not for factored matrix");
1646   if (!mat->ops.zeroentries) SETERRQ(PETSC_ERR_SUP,"MatZeroEntries");
1647 
1648   PLogEventBegin(MAT_ZeroEntries,mat,0,0,0);
1649   ierr = (*mat->ops.zeroentries)(mat); CHKERRQ(ierr);
1650   PLogEventEnd(MAT_ZeroEntries,mat,0,0,0);
1651   return 0;
1652 }
1653 
1654 /*@
1655    MatZeroRows - Zeros all entries (except possibly the main diagonal)
1656    of a set of rows of a matrix.
1657 
1658    Input Parameters:
1659 .  mat - the matrix
1660 .  is - index set of rows to remove
1661 .  diag - pointer to value put in all diagonals of eliminated rows.
1662           Note that diag is not a pointer to an array, but merely a
1663           pointer to a single value.
1664 
1665    Notes:
1666    For the AIJ matrix formats this removes the old nonzero structure,
1667    but does not release memory.  For the dense and block diagonal
1668    formats this does not alter the nonzero structure.
1669 
1670    The user can set a value in the diagonal entry (or for the AIJ and
1671    row formats can optionally remove the main diagonal entry from the
1672    nonzero structure as well, by passing a null pointer as the final
1673    argument).
1674 
1675 .keywords: matrix, zero, rows, boundary conditions
1676 
1677 .seealso: MatZeroEntries(),
1678 @*/
1679 int MatZeroRows(Mat mat,IS is, Scalar *diag)
1680 {
1681   int ierr;
1682 
1683   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1684   PetscValidHeaderSpecific(is,IS_COOKIE);
1685   if (diag) PetscValidScalarPointer(diag);
1686   if (!mat->assembled) SETERRQ(1,"MatZeroRows:Not for unassembled matrix");
1687   if (mat->factor) SETERRQ(1,"MatZeroRows:Not for factored matrix");
1688   if (!mat->ops.zerorows) SETERRQ(PETSC_ERR_SUP,"MatZeroRows");
1689 
1690   ierr = (*mat->ops.zerorows)(mat,is,diag); CHKERRQ(ierr);
1691   return 0;
1692 }
1693 
1694 /*@
1695    MatZeroRowsLocal - Zeros all entries (except possibly the main diagonal)
1696    of a set of rows of a matrix; using local numbering of rows.
1697 
1698    Input Parameters:
1699 .  mat - the matrix
1700 .  is - index set of rows to remove
1701 .  diag - pointer to value put in all diagonals of eliminated rows.
1702           Note that diag is not a pointer to an array, but merely a
1703           pointer to a single value.
1704 
1705    Notes:
1706    For the AIJ matrix formats this removes the old nonzero structure,
1707    but does not release memory.  For the dense and block diagonal
1708    formats this does not alter the nonzero structure.
1709 
1710    The user can set a value in the diagonal entry (or for the AIJ and
1711    row formats can optionally remove the main diagonal entry from the
1712    nonzero structure as well, by passing a null pointer as the final
1713    argument).
1714 
1715 .keywords: matrix, zero, rows, boundary conditions
1716 
1717 .seealso: MatZeroEntries(),
1718 @*/
1719 int MatZeroRowsLocal(Mat mat,IS is, Scalar *diag)
1720 {
1721   int ierr;
1722   IS  newis;
1723 
1724   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1725   PetscValidHeaderSpecific(is,IS_COOKIE);
1726   if (diag) PetscValidScalarPointer(diag);
1727   if (!mat->assembled) SETERRQ(1,"MatZeroRows:Not for unassembled matrix");
1728   if (mat->factor) SETERRQ(1,"MatZeroRows:Not for factored matrix");
1729   if (!mat->ops.zerorows) SETERRQ(PETSC_ERR_SUP,"MatZeroRows");
1730 
1731   ierr = ISLocalToGlobalMappingApplyIS(mat->mapping,is,&newis); CHKERRQ(ierr);
1732   ierr =  (*mat->ops.zerorows)(mat,newis,diag); CHKERRQ(ierr);
1733   ierr = ISDestroy(newis);
1734   return 0;
1735 }
1736 
1737 /*@
1738    MatGetSize - Returns the numbers of rows and columns in a matrix.
1739 
1740    Input Parameter:
1741 .  mat - the matrix
1742 
1743    Output Parameters:
1744 .  m - the number of global rows
1745 .  n - the number of global columns
1746 
1747 .keywords: matrix, dimension, size, rows, columns, global, get
1748 
1749 .seealso: MatGetLocalSize()
1750 @*/
1751 int MatGetSize(Mat mat,int *m,int* n)
1752 {
1753   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1754   PetscValidIntPointer(m);
1755   PetscValidIntPointer(n);
1756   return (*mat->ops.getsize)(mat,m,n);
1757 }
1758 
1759 /*@
1760    MatGetLocalSize - Returns the number of rows and columns in a matrix
1761    stored locally.  This information may be implementation dependent, so
1762    use with care.
1763 
1764    Input Parameters:
1765 .  mat - the matrix
1766 
1767    Output Parameters:
1768 .  m - the number of local rows
1769 .  n - the number of local columns
1770 
1771 .keywords: matrix, dimension, size, local, rows, columns, get
1772 
1773 .seealso: MatGetSize()
1774 @*/
1775 int MatGetLocalSize(Mat mat,int *m,int* n)
1776 {
1777   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1778   PetscValidIntPointer(m);
1779   PetscValidIntPointer(n);
1780   return (*mat->ops.getlocalsize)(mat,m,n);
1781 }
1782 
1783 /*@
1784    MatGetOwnershipRange - Returns the range of matrix rows owned by
1785    this processor, assuming that the matrix is laid out with the first
1786    n1 rows on the first processor, the next n2 rows on the second, etc.
1787    For certain parallel layouts this range may not be well defined.
1788 
1789    Input Parameters:
1790 .  mat - the matrix
1791 
1792    Output Parameters:
1793 .  m - the first local row
1794 .  n - one more then the last local row
1795 
1796 .keywords: matrix, get, range, ownership
1797 @*/
1798 int MatGetOwnershipRange(Mat mat,int *m,int* n)
1799 {
1800   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1801   PetscValidIntPointer(m);
1802   PetscValidIntPointer(n);
1803   if (!mat->ops.getownershiprange) SETERRQ(PETSC_ERR_SUP,"MatGetOwnershipRange");
1804   return (*mat->ops.getownershiprange)(mat,m,n);
1805 }
1806 
1807 /*@
1808    MatILUFactorSymbolic - Performs symbolic ILU factorization of a matrix.
1809    Uses levels of fill only, not drop tolerance. Use MatLUFactorNumeric()
1810    to complete the factorization.
1811 
1812    Input Parameters:
1813 .  mat - the matrix
1814 .  row - row permutation
1815 .  column - column permutation
1816 .  fill - number of levels of fill
1817 .  f - expected fill as ratio of the original number of nonzeros,
1818        for example 3.0; choosing this parameter well can result in
1819        more efficient use of time and space.
1820 
1821    Output Parameters:
1822 .  fact - new matrix that has been symbolically factored
1823 
1824    Options Database Key:
1825 $   -mat_ilu_fill <f>, where f is the fill ratio
1826 
1827    Notes:
1828    See the file $(PETSC_DIR)/Performace for additional information about
1829    choosing the fill factor for better efficiency.
1830 
1831 .keywords: matrix, factor, incomplete, ILU, symbolic, fill
1832 
1833 .seealso: MatLUFactorSymbolic(), MatLUFactorNumeric()
1834 @*/
1835 int MatILUFactorSymbolic(Mat mat,IS row,IS col,double f,int fill,Mat *fact)
1836 {
1837   int ierr,flg;
1838 
1839   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1840   if (fill < 0) SETERRQ(1,"MatILUFactorSymbolic:Levels of fill negative");
1841   if (!fact) SETERRQ(1,"MatILUFactorSymbolic:Fact argument is missing");
1842   if (!mat->ops.ilufactorsymbolic) SETERRQ(PETSC_ERR_SUP,"MatILUFactorSymbolic");
1843   if (!mat->assembled) SETERRQ(1,"MatILUFactorSymbolic:Not for unassembled matrix");
1844   if (mat->factor) SETERRQ(1,"MatILUFactorSymbolic:Not for factored matrix");
1845 
1846   ierr = OptionsGetDouble(PETSC_NULL,"-mat_ilu_fill",&f,&flg); CHKERRQ(ierr);
1847   PLogEventBegin(MAT_ILUFactorSymbolic,mat,row,col,0);
1848   ierr = (*mat->ops.ilufactorsymbolic)(mat,row,col,f,fill,fact); CHKERRQ(ierr);
1849   PLogEventEnd(MAT_ILUFactorSymbolic,mat,row,col,0);
1850   return 0;
1851 }
1852 
1853 /*@
1854    MatIncompleteCholeskyFactorSymbolic - Performs symbolic incomplete
1855    Cholesky factorization for a symmetric matrix.  Use
1856    MatCholeskyFactorNumeric() to complete the factorization.
1857 
1858    Input Parameters:
1859 .  mat - the matrix
1860 .  perm - row and column permutation
1861 .  fill - levels of fill
1862 .  f - expected fill as ratio of original fill
1863 
1864    Output Parameter:
1865 .  fact - the factored matrix
1866 
1867    Note:  Currently only no-fill factorization is supported.
1868 
1869 .keywords: matrix, factor, incomplete, ICC, Cholesky, symbolic, fill
1870 
1871 .seealso: MatCholeskyFactorNumeric(), MatCholeskyFactor()
1872 @*/
1873 int MatIncompleteCholeskyFactorSymbolic(Mat mat,IS perm,double f,int fill,
1874                                         Mat *fact)
1875 {
1876   int ierr;
1877   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1878   if (mat->factor) SETERRQ(1,"MatIncompleteCholeskyFactorSymbolic:Not for factored matrix");
1879   if (fill < 0) SETERRQ(1,"MatIncompleteCholeskyFactorSymbolic:Fill negative");
1880   if (!fact) SETERRQ(1,"MatIncompleteCholeskyFactorSymbolic:Missing fact argument");
1881   if (!mat->ops.incompletecholeskyfactorsymbolic)
1882      SETERRQ(PETSC_ERR_SUP,"MatIncompleteCholeskyFactorSymbolic");
1883   if (!mat->assembled)
1884      SETERRQ(1,"MatIncompleteCholeskyFactorSymbolic:Not for unassembled matrix");
1885 
1886   PLogEventBegin(MAT_IncompleteCholeskyFactorSymbolic,mat,perm,0,0);
1887   ierr = (*mat->ops.incompletecholeskyfactorsymbolic)(mat,perm,f,fill,fact);CHKERRQ(ierr);
1888   PLogEventEnd(MAT_IncompleteCholeskyFactorSymbolic,mat,perm,0,0);
1889   return 0;
1890 }
1891 
1892 /*@C
1893    MatGetArray - Returns a pointer to the element values in the matrix.
1894    This routine  is implementation dependent, and may not even work for
1895    certain matrix types. You MUST call MatRestoreArray() when you no
1896    longer need to access the array.
1897 
1898    Input Parameter:
1899 .  mat - the matrix
1900 
1901    Output Parameter:
1902 .  v - the location of the values
1903 
1904    Fortran Note:
1905    The Fortran interface is slightly different from that given below.
1906    See the Fortran chapter of the users manual and
1907    petsc/src/mat/examples for details.
1908 
1909 .keywords: matrix, array, elements, values
1910 
1911 .seeaols: MatRestoreArray()
1912 @*/
1913 int MatGetArray(Mat mat,Scalar **v)
1914 {
1915   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1916   if (!v) SETERRQ(1,"MatGetArray:Bad input, array pointer location");
1917   if (!mat->ops.getarray) SETERRQ(PETSC_ERR_SUP,"MatGetArray");
1918   return (*mat->ops.getarray)(mat,v);
1919 }
1920 
1921 /*@C
1922    MatRestoreArray - Restores the matrix after MatGetArray has been called.
1923 
1924    Input Parameter:
1925 .  mat - the matrix
1926 .  v - the location of the values
1927 
1928    Fortran Note:
1929    The Fortran interface is slightly different from that given below.
1930    See the users manual and petsc/src/mat/examples for details.
1931 
1932 .keywords: matrix, array, elements, values, resrore
1933 
1934 .seealso: MatGetArray()
1935 @*/
1936 int MatRestoreArray(Mat mat,Scalar **v)
1937 {
1938   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1939   if (!v) SETERRQ(1,"MatRestoreArray:Bad input, array pointer location");
1940   if (!mat->ops.restorearray) SETERRQ(PETSC_ERR_SUP,"MatResroreArray");
1941   return (*mat->ops.restorearray)(mat,v);
1942 }
1943 
1944 /*@C
1945    MatGetSubMatrices - Extracts several submatrices from a matrix. If submat
1946    points to an array of valid matrices, it may be reused.
1947 
1948    Input Parameters:
1949 .  mat - the matrix
1950 .  irow, icol - index sets of rows and columns to extract
1951 .  scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX
1952 
1953    Output Parameter:
1954 .  submat - the array of submatrices
1955 
1956    Limitations:
1957    Currently, MatGetSubMatrices() can extract only sequential submatrices
1958    (from both sequential and parallel matrices).
1959 
1960    Notes:
1961    When extracting submatrices from a parallel matrix, each processor can
1962    form a different submatrix by setting the rows and columns of its
1963    individual index sets according to the local submatrix desired.
1964 
1965    When finished using the submatrices, the user should destroy
1966    them with MatDestroySubMatrices().
1967 
1968 .keywords: matrix, get, submatrix, submatrices
1969 
1970 .seealso: MatDestroyMatrices()
1971 @*/
1972 int MatGetSubMatrices(Mat mat,int n,IS *irow,IS *icol,MatGetSubMatrixCall scall,
1973                       Mat **submat)
1974 {
1975   int ierr;
1976   PetscValidHeaderSpecific(mat,MAT_COOKIE);
1977   if (!mat->ops.getsubmatrices) SETERRQ(PETSC_ERR_SUP,"MatGetSubMatrices");
1978   if (!mat->assembled) SETERRQ(1,"MatGetSubMatrices:Not for unassembled matrix");
1979 
1980   PLogEventBegin(MAT_GetSubMatrices,mat,0,0,0);
1981   ierr = (*mat->ops.getsubmatrices)(mat,n,irow,icol,scall,submat); CHKERRQ(ierr);
1982   PLogEventEnd(MAT_GetSubMatrices,mat,0,0,0);
1983 
1984   return 0;
1985 }
1986 
1987 /*@C
1988    MatDestroyMatrices - Destroys a set of matrices obtained with MatGetSubMatrices().
1989 
1990    Input Parameters:
1991 .  n - the number of local matrices
1992 .  mat - the matrices
1993 
1994 .keywords: matrix, destroy, submatrix, submatrices
1995 
1996 .seealso: MatGetSubMatrices()
1997 @*/
1998 int MatDestroyMatrices(int n,Mat **mat)
1999 {
2000   int ierr,i;
2001 
2002   PetscValidPointer(mat);
2003   for ( i=0; i<n; i++ ) {
2004     ierr = MatDestroy((*mat)[i]); CHKERRQ(ierr);
2005   }
2006   PetscFree(*mat);
2007   return 0;
2008 }
2009 
2010 /*@
2011    MatIncreaseOverlap - Given a set of submatrices indicated by index sets,
2012    replaces the index by larger ones that represent submatrices with more
2013    overlap.
2014 
2015    Input Parameters:
2016 .  mat - the matrix
2017 .  n   - the number of index sets
2018 .  is  - the array of pointers to index sets
2019 .  ov  - the additional overlap requested
2020 
2021 .keywords: matrix, overlap, Schwarz
2022 
2023 .seealso: MatGetSubMatrices()
2024 @*/
2025 int MatIncreaseOverlap(Mat mat,int n, IS *is,int ov)
2026 {
2027   int ierr;
2028   PetscValidHeaderSpecific(mat,MAT_COOKIE);
2029   if (!mat->assembled) SETERRQ(1,"MatIncreaseOverlap:Not for unassembled matrix");
2030   if (mat->factor)     SETERRQ(1,"MatIncreaseOverlap:Not for factored matrix");
2031 
2032   if (ov == 0) return 0;
2033   if (!mat->ops.increaseoverlap) SETERRQ(PETSC_ERR_SUP,"MatIncreaseOverlap");
2034   PLogEventBegin(MAT_IncreaseOverlap,mat,0,0,0);
2035   ierr = (*mat->ops.increaseoverlap)(mat,n,is,ov); CHKERRQ(ierr);
2036   PLogEventEnd(MAT_IncreaseOverlap,mat,0,0,0);
2037   return 0;
2038 }
2039 
2040 /*@
2041    MatPrintHelp - Prints all the options for the matrix.
2042 
2043    Input Parameter:
2044 .  mat - the matrix
2045 
2046    Options Database Keys:
2047 $  -help, -h
2048 
2049 .keywords: mat, help
2050 
2051 .seealso: MatCreate(), MatCreateXXX()
2052 @*/
2053 int MatPrintHelp(Mat mat)
2054 {
2055   static int called = 0;
2056   MPI_Comm   comm;
2057   PetscValidHeaderSpecific(mat,MAT_COOKIE);
2058 
2059   comm = mat->comm;
2060   if (!called) {
2061     PetscPrintf(comm,"General matrix options:\n");
2062     PetscPrintf(comm,"  -mat_view_info : view basic matrix info during MatAssemblyEnd()\n");
2063     PetscPrintf(comm,"  -mat_view_info_detailed : view detailed matrix info during MatAssemblyEnd()\n");
2064     PetscPrintf(comm,"  -mat_view_draw : draw nonzero matrix structure during MatAssemblyEnd()\n");
2065     PetscPrintf(comm,"      -draw_pause <sec> : set seconds of display pause\n");
2066     PetscPrintf(comm,"      -display <name> : set alternate display\n");
2067     called = 1;
2068   }
2069   if (mat->ops.printhelp) (*mat->ops.printhelp)(mat);
2070   return 0;
2071 }
2072 
2073 /*@
2074    MatGetBlockSize - Returns the matrix block size; useful especially for the
2075    block row and block diagonal formats.
2076 
2077    Input Parameter:
2078 .  mat - the matrix
2079 
2080    Output Parameter:
2081 .  bs - block size
2082 
2083    Notes:
2084 $  block diagonal formats: MATSEQBDIAG, MATMPIBDIAG
2085 $  block row formats: MATSEQBAIJ, MATMPIBAIJ
2086 
2087 .keywords: matrix, get, block, size
2088 
2089 .seealso: MatCreateSeqBAIJ(), MatCreateMPIBAIJ(), MatCreateSeqBDiag(), MatCreateMPIBDiag()
2090 @*/
2091 int MatGetBlockSize(Mat mat,int *bs)
2092 {
2093   PetscValidHeaderSpecific(mat,MAT_COOKIE);
2094   PetscValidIntPointer(bs);
2095   if (!mat->ops.getblocksize) SETERRQ(PETSC_ERR_SUP,"MatGetBlockSize");
2096   return (*mat->ops.getblocksize)(mat,bs);
2097 }
2098 
2099 /*@C
2100       MatGetRowIJ - Returns the compress row storage i and j indices for sequential matrices.
2101                  EXPERTS ONLY.
2102 
2103   Input Parameters:
2104 .   mat - the matrix
2105 .   shift - 1 or zero indicating we want the indices starting at 0 or 1
2106 .   symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
2107                 symmetrized
2108 
2109   Output Parameters:
2110 .   n - number of rows and columns in the (possibly compressed) matrix
2111 .   ia - the row indices
2112 .   ja - the column indices
2113 .   done - PETSC_TRUE or PETSC_FALSE indicated that the values have been returned
2114 @*/
2115 int MatGetRowIJ(Mat mat,int shift,PetscTruth symmetric,int *n,int **ia,int** ja,PetscTruth *done)
2116 {
2117   int ierr;
2118   PetscValidHeaderSpecific(mat,MAT_COOKIE);
2119   if (ia) PetscValidIntPointer(ia);
2120   if (ja) PetscValidIntPointer(ja);
2121   PetscValidIntPointer(done);
2122   if (!mat->ops.getrowij) *done = PETSC_FALSE;
2123   else {
2124     *done = PETSC_TRUE;
2125     ierr  = (*mat->ops.getrowij)(mat,shift,symmetric,n,ia,ja,done); CHKERRQ(ierr);
2126   }
2127   return 0;
2128 }
2129 
2130 /*@C
2131       MatGetColumnIJ - Returns the compress Column storage i and j indices for sequential matrices.
2132                  EXPERTS ONLY.
2133 
2134   Input Parameters:
2135 .   mat - the matrix
2136 .   shift - 1 or zero indicating we want the indices starting at 0 or 1
2137 .   symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
2138                 symmetrized
2139 
2140   Output Parameters:
2141 .   n - number of Columns and columns in the (possibly compressed) matrix
2142 .   ia - the Column indices
2143 .   ja - the column indices
2144 .   done - PETSC_TRUE or PETSC_FALSE indicated that the values have been returned
2145 @*/
2146 int MatGetColumnIJ(Mat mat,int shift,PetscTruth symmetric,int *n,int **ia,int** ja,PetscTruth *done)
2147 {
2148   int ierr;
2149   PetscValidHeaderSpecific(mat,MAT_COOKIE);
2150   if (ia) PetscValidIntPointer(ia);
2151   if (ja) PetscValidIntPointer(ja);
2152   PetscValidIntPointer(done);
2153 
2154   if (!mat->ops.getcolumnij) *done = PETSC_FALSE;
2155   else {
2156     *done = PETSC_TRUE;
2157     ierr  = (*mat->ops.getcolumnij)(mat,shift,symmetric,n,ia,ja,done); CHKERRQ(ierr);
2158   }
2159   return 0;
2160 }
2161 
2162 /*@C
2163       MatRestoreRowIJ - Call after you are completed with the ia,ja indices obtained with
2164                      MatGetRowIJ(). EXPERTS ONLY.
2165 
2166   Input Parameters:
2167 .   mat - the matrix
2168 .   shift - 1 or zero indicating we want the indices starting at 0 or 1
2169 .   symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
2170                 symmetrized
2171 
2172   Output Parameters:
2173 .   n - size of (possibly compressed) matrix
2174 .   ia - the row indices
2175 .   ja - the column indices
2176 .   done - PETSC_TRUE or PETSC_FALSE indicated that the values have been returned
2177 @*/
2178 int MatRestoreRowIJ(Mat mat,int shift,PetscTruth symmetric,int *n,int **ia,int** ja,PetscTruth *done)
2179 {
2180   int ierr;
2181   PetscValidHeaderSpecific(mat,MAT_COOKIE);
2182   if (ia) PetscValidIntPointer(ia);
2183   if (ja) PetscValidIntPointer(ja);
2184   PetscValidIntPointer(done);
2185 
2186   if (!mat->ops.restorerowij) *done = PETSC_FALSE;
2187   else {
2188     *done = PETSC_TRUE;
2189     ierr  = (*mat->ops.restorerowij)(mat,shift,symmetric,n,ia,ja,done); CHKERRQ(ierr);
2190   }
2191   return 0;
2192 }
2193 
2194 /*@C
2195       MatRestoreColumnIJ - Call after you are completed with the ia,ja indices obtained with
2196                      MatGetColumnIJ(). EXPERTS ONLY.
2197 
2198   Input Parameters:
2199 .   mat - the matrix
2200 .   shift - 1 or zero indicating we want the indices starting at 0 or 1
2201 .   symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be
2202                 symmetrized
2203 
2204   Output Parameters:
2205 .   n - size of (possibly compressed) matrix
2206 .   ia - the Column indices
2207 .   ja - the column indices
2208 .   done - PETSC_TRUE or PETSC_FALSE indicated that the values have been returned
2209 @*/
2210 int MatRestoreColumnIJ(Mat mat,int shift,PetscTruth symmetric,int *n,int **ia,int** ja,PetscTruth *done)
2211 {
2212   int ierr;
2213   PetscValidHeaderSpecific(mat,MAT_COOKIE);
2214   if (ia) PetscValidIntPointer(ia);
2215   if (ja) PetscValidIntPointer(ja);
2216   PetscValidIntPointer(done);
2217 
2218   if (!mat->ops.restorecolumnij) *done = PETSC_FALSE;
2219   else {
2220     *done = PETSC_TRUE;
2221     ierr  = (*mat->ops.restorecolumnij)(mat,shift,symmetric,n,ia,ja,done); CHKERRQ(ierr);
2222   }
2223   return 0;
2224 }
2225 
2226 /*@C
2227       MatColoringPatch - EXPERTS ONLY, used inside matrix coloring routines that
2228           use matGetRowIJ() and/or MatGetColumnIJ().
2229 
2230   Input Parameters:
2231 .   mat - the matrix
2232 .   n   - number of colors
2233 .   colorarray - array indicating color for each column
2234 
2235   Output Parameters:
2236 .   iscoloring - coloring generated using colorarray information
2237 
2238 @*/
2239 int MatColoringPatch(Mat mat,int n,int *colorarray,ISColoring *iscoloring)
2240 {
2241   int ierr;
2242   PetscValidHeaderSpecific(mat,MAT_COOKIE);
2243   PetscValidIntPointer(colorarray);
2244 
2245   if (!mat->ops.coloringpatch) {SETERRQ(PETSC_ERR_SUP,"MatColoringPatch");}
2246   else {
2247     ierr  = (*mat->ops.coloringpatch)(mat,n,colorarray,iscoloring); CHKERRQ(ierr);
2248   }
2249   return 0;
2250 }
2251 
2252 
2253