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