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