xref: /petsc/src/mat/impls/dense/seq/dense.c (revision 2ffef20af2c47fa8de84ff175d9b4dd7f3672115)
1*2ffef20aSBarry Smith /*$Id: dense.c,v 1.206 2001/08/07 03:02:45 balay Exp bsmith $*/
267e560aaSBarry Smith /*
367e560aaSBarry Smith      Defines the basic matrix operations for sequential dense.
467e560aaSBarry Smith */
5289bc588SBarry Smith 
670f55243SBarry Smith #include "src/mat/impls/dense/seq/dense.h"
7b4c862e0SSatish Balay #include "petscblaslapack.h"
8289bc588SBarry Smith 
94a2ae208SSatish Balay #undef __FUNCT__
104a2ae208SSatish Balay #define __FUNCT__ "MatAXPY_SeqDense"
1187828ca2SBarry Smith int MatAXPY_SeqDense(PetscScalar *alpha,Mat X,Mat Y)
121987afe7SBarry Smith {
131987afe7SBarry Smith   Mat_SeqDense *x = (Mat_SeqDense*)X->data,*y = (Mat_SeqDense*)Y->data;
14273d9f13SBarry Smith   int          N = X->m*X->n,one = 1;
153a40ed3dSBarry Smith 
163a40ed3dSBarry Smith   PetscFunctionBegin;
171987afe7SBarry Smith   BLaxpy_(&N,alpha,x->v,&one,y->v,&one);
18b0a32e0cSBarry Smith   PetscLogFlops(2*N-1);
193a40ed3dSBarry Smith   PetscFunctionReturn(0);
201987afe7SBarry Smith }
211987afe7SBarry Smith 
224a2ae208SSatish Balay #undef __FUNCT__
234a2ae208SSatish Balay #define __FUNCT__ "MatGetInfo_SeqDense"
248f6be9afSLois Curfman McInnes int MatGetInfo_SeqDense(Mat A,MatInfoType flag,MatInfo *info)
25289bc588SBarry Smith {
264e220ebcSLois Curfman McInnes   Mat_SeqDense *a = (Mat_SeqDense*)A->data;
27273d9f13SBarry Smith   int          i,N = A->m*A->n,count = 0;
2887828ca2SBarry Smith   PetscScalar  *v = a->v;
293a40ed3dSBarry Smith 
303a40ed3dSBarry Smith   PetscFunctionBegin;
31289bc588SBarry Smith   for (i=0; i<N; i++) {if (*v != 0.0) count++; v++;}
324e220ebcSLois Curfman McInnes 
33273d9f13SBarry Smith   info->rows_global       = (double)A->m;
34273d9f13SBarry Smith   info->columns_global    = (double)A->n;
35273d9f13SBarry Smith   info->rows_local        = (double)A->m;
36273d9f13SBarry Smith   info->columns_local     = (double)A->n;
374e220ebcSLois Curfman McInnes   info->block_size        = 1.0;
384e220ebcSLois Curfman McInnes   info->nz_allocated      = (double)N;
394e220ebcSLois Curfman McInnes   info->nz_used           = (double)count;
404e220ebcSLois Curfman McInnes   info->nz_unneeded       = (double)(N-count);
414e220ebcSLois Curfman McInnes   info->assemblies        = (double)A->num_ass;
424e220ebcSLois Curfman McInnes   info->mallocs           = 0;
434e220ebcSLois Curfman McInnes   info->memory            = A->mem;
444e220ebcSLois Curfman McInnes   info->fill_ratio_given  = 0;
454e220ebcSLois Curfman McInnes   info->fill_ratio_needed = 0;
464e220ebcSLois Curfman McInnes   info->factor_mallocs    = 0;
474e220ebcSLois Curfman McInnes 
483a40ed3dSBarry Smith   PetscFunctionReturn(0);
49289bc588SBarry Smith }
50289bc588SBarry Smith 
514a2ae208SSatish Balay #undef __FUNCT__
524a2ae208SSatish Balay #define __FUNCT__ "MatScale_SeqDense"
5387828ca2SBarry Smith int MatScale_SeqDense(PetscScalar *alpha,Mat A)
5480cd9d93SLois Curfman McInnes {
55273d9f13SBarry Smith   Mat_SeqDense *a = (Mat_SeqDense*)A->data;
5680cd9d93SLois Curfman McInnes   int          one = 1,nz;
5780cd9d93SLois Curfman McInnes 
583a40ed3dSBarry Smith   PetscFunctionBegin;
59273d9f13SBarry Smith   nz = A->m*A->n;
6080cd9d93SLois Curfman McInnes   BLscal_(&nz,alpha,a->v,&one);
61b0a32e0cSBarry Smith   PetscLogFlops(nz);
623a40ed3dSBarry Smith   PetscFunctionReturn(0);
6380cd9d93SLois Curfman McInnes }
6480cd9d93SLois Curfman McInnes 
65289bc588SBarry Smith /* ---------------------------------------------------------------*/
666831982aSBarry Smith /* COMMENT: I have chosen to hide row permutation in the pivots,
676831982aSBarry Smith    rather than put it in the Mat->row slot.*/
684a2ae208SSatish Balay #undef __FUNCT__
694a2ae208SSatish Balay #define __FUNCT__ "MatLUFactor_SeqDense"
70e03a110bSBarry Smith int MatLUFactor_SeqDense(Mat A,IS row,IS col,MatLUInfo *minfo)
71289bc588SBarry Smith {
72c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
73b0a32e0cSBarry Smith   int          info,ierr;
7455659b69SBarry Smith 
753a40ed3dSBarry Smith   PetscFunctionBegin;
76289bc588SBarry Smith   if (!mat->pivots) {
77b0a32e0cSBarry Smith     ierr = PetscMalloc((A->m+1)*sizeof(int),&mat->pivots);CHKERRQ(ierr);
78b0a32e0cSBarry Smith     PetscLogObjectMemory(A,A->m*sizeof(int));
79289bc588SBarry Smith   }
80f1af5d2fSBarry Smith   A->factor = FACTOR_LU;
81273d9f13SBarry Smith   if (!A->m || !A->n) PetscFunctionReturn(0);
82ae7cfcebSSatish Balay #if defined(PETSC_MISSING_LAPACK_GETRF)
83ae7cfcebSSatish Balay   SETERRQ(PETSC_ERR_SUP,"GETRF - Lapack routine is unavilable.");
84ae7cfcebSSatish Balay #else
85273d9f13SBarry Smith   LAgetrf_(&A->m,&A->n,mat->v,&A->m,mat->pivots,&info);
8629bbc08cSBarry Smith   if (info<0) SETERRQ(PETSC_ERR_LIB,"Bad argument to LU factorization");
8729bbc08cSBarry Smith   if (info>0) SETERRQ(PETSC_ERR_MAT_LU_ZRPVT,"Bad LU factorization");
88*2ffef20aSBarry Smith #endif
89b0a32e0cSBarry Smith   PetscLogFlops((2*A->n*A->n*A->n)/3);
903a40ed3dSBarry Smith   PetscFunctionReturn(0);
91289bc588SBarry Smith }
926ee01492SSatish Balay 
934a2ae208SSatish Balay #undef __FUNCT__
944a2ae208SSatish Balay #define __FUNCT__ "MatDuplicate_SeqDense"
955609ef8eSBarry Smith int MatDuplicate_SeqDense(Mat A,MatDuplicateOption cpvalues,Mat *newmat)
9602cad45dSBarry Smith {
9702cad45dSBarry Smith   Mat_SeqDense *mat = (Mat_SeqDense*)A->data,*l;
9802cad45dSBarry Smith   int          ierr;
9902cad45dSBarry Smith   Mat          newi;
10002cad45dSBarry Smith 
1013a40ed3dSBarry Smith   PetscFunctionBegin;
102273d9f13SBarry Smith   ierr = MatCreateSeqDense(A->comm,A->m,A->n,PETSC_NULL,&newi);CHKERRQ(ierr);
10302cad45dSBarry Smith   l = (Mat_SeqDense*)newi->data;
1045609ef8eSBarry Smith   if (cpvalues == MAT_COPY_VALUES) {
10587828ca2SBarry Smith     ierr = PetscMemcpy(l->v,mat->v,A->m*A->n*sizeof(PetscScalar));CHKERRQ(ierr);
10602cad45dSBarry Smith   }
10702cad45dSBarry Smith   newi->assembled = PETSC_TRUE;
10802cad45dSBarry Smith   *newmat = newi;
1093a40ed3dSBarry Smith   PetscFunctionReturn(0);
11002cad45dSBarry Smith }
11102cad45dSBarry Smith 
1124a2ae208SSatish Balay #undef __FUNCT__
1134a2ae208SSatish Balay #define __FUNCT__ "MatLUFactorSymbolic_SeqDense"
114e03a110bSBarry Smith int MatLUFactorSymbolic_SeqDense(Mat A,IS row,IS col,MatLUInfo *info,Mat *fact)
115289bc588SBarry Smith {
1163a40ed3dSBarry Smith   int ierr;
1173a40ed3dSBarry Smith 
1183a40ed3dSBarry Smith   PetscFunctionBegin;
1195609ef8eSBarry Smith   ierr = MatDuplicate_SeqDense(A,MAT_DO_NOT_COPY_VALUES,fact);CHKERRQ(ierr);
1203a40ed3dSBarry Smith   PetscFunctionReturn(0);
121289bc588SBarry Smith }
1226ee01492SSatish Balay 
1234a2ae208SSatish Balay #undef __FUNCT__
1244a2ae208SSatish Balay #define __FUNCT__ "MatLUFactorNumeric_SeqDense"
1258f6be9afSLois Curfman McInnes int MatLUFactorNumeric_SeqDense(Mat A,Mat *fact)
126289bc588SBarry Smith {
12702cad45dSBarry Smith   Mat_SeqDense *mat = (Mat_SeqDense*)A->data,*l = (Mat_SeqDense*)(*fact)->data;
1283a40ed3dSBarry Smith   int          ierr;
1293a40ed3dSBarry Smith 
1303a40ed3dSBarry Smith   PetscFunctionBegin;
13102cad45dSBarry Smith   /* copy the numerical values */
13287828ca2SBarry Smith   ierr = PetscMemcpy(l->v,mat->v,A->m*A->n*sizeof(PetscScalar));CHKERRQ(ierr);
13302cad45dSBarry Smith   (*fact)->factor = 0;
134e03a110bSBarry Smith   ierr = MatLUFactor(*fact,0,0,PETSC_NULL);CHKERRQ(ierr);
1353a40ed3dSBarry Smith   PetscFunctionReturn(0);
136289bc588SBarry Smith }
1376ee01492SSatish Balay 
1384a2ae208SSatish Balay #undef __FUNCT__
1394a2ae208SSatish Balay #define __FUNCT__ "MatCholeskyFactorSymbolic_SeqDense"
140329f5518SBarry Smith int MatCholeskyFactorSymbolic_SeqDense(Mat A,IS row,PetscReal f,Mat *fact)
141289bc588SBarry Smith {
1423a40ed3dSBarry Smith   int ierr;
1433a40ed3dSBarry Smith 
1443a40ed3dSBarry Smith   PetscFunctionBegin;
1453a40ed3dSBarry Smith   ierr = MatConvert(A,MATSAME,fact);CHKERRQ(ierr);
1463a40ed3dSBarry Smith   PetscFunctionReturn(0);
147289bc588SBarry Smith }
1486ee01492SSatish Balay 
1494a2ae208SSatish Balay #undef __FUNCT__
1504a2ae208SSatish Balay #define __FUNCT__ "MatCholeskyFactor_SeqDense"
151329f5518SBarry Smith int MatCholeskyFactor_SeqDense(Mat A,IS perm,PetscReal f)
152289bc588SBarry Smith {
153c0bbcb79SLois Curfman McInnes   Mat_SeqDense  *mat = (Mat_SeqDense*)A->data;
154606d414cSSatish Balay   int           info,ierr;
15555659b69SBarry Smith 
1563a40ed3dSBarry Smith   PetscFunctionBegin;
157752f5567SLois Curfman McInnes   if (mat->pivots) {
158606d414cSSatish Balay     ierr = PetscFree(mat->pivots);CHKERRQ(ierr);
159b0a32e0cSBarry Smith     PetscLogObjectMemory(A,-A->m*sizeof(int));
160752f5567SLois Curfman McInnes     mat->pivots = 0;
161752f5567SLois Curfman McInnes   }
162273d9f13SBarry Smith   if (!A->m || !A->n) PetscFunctionReturn(0);
163ae7cfcebSSatish Balay #if defined(PETSC_MISSING_LAPACK_POTRF)
164ae7cfcebSSatish Balay   SETERRQ(PETSC_ERR_SUP,"POTRF - Lapack routine is unavilable.");
165ae7cfcebSSatish Balay #else
166273d9f13SBarry Smith   LApotrf_("L",&A->n,mat->v,&A->m,&info);
16729bbc08cSBarry Smith   if (info) SETERRQ1(PETSC_ERR_MAT_CH_ZRPVT,"Bad factorization: zero pivot in row %d",info-1);
168*2ffef20aSBarry Smith #endif
169c0bbcb79SLois Curfman McInnes   A->factor = FACTOR_CHOLESKY;
170b0a32e0cSBarry Smith   PetscLogFlops((A->n*A->n*A->n)/3);
1713a40ed3dSBarry Smith   PetscFunctionReturn(0);
172289bc588SBarry Smith }
173289bc588SBarry Smith 
1744a2ae208SSatish Balay #undef __FUNCT__
1750b4b3355SBarry Smith #define __FUNCT__ "MatCholeskyFactorNumeric_SeqDense"
1760b4b3355SBarry Smith int MatCholeskyFactorNumeric_SeqDense(Mat A,Mat *fact)
1770b4b3355SBarry Smith {
1780b4b3355SBarry Smith   int ierr;
1790b4b3355SBarry Smith 
1800b4b3355SBarry Smith   PetscFunctionBegin;
1810b4b3355SBarry Smith   ierr = MatCholeskyFactor_SeqDense(*fact,0,1.0);CHKERRQ(ierr);
1820b4b3355SBarry Smith   PetscFunctionReturn(0);
1830b4b3355SBarry Smith }
1840b4b3355SBarry Smith 
1850b4b3355SBarry Smith #undef __FUNCT__
1864a2ae208SSatish Balay #define __FUNCT__ "MatSolve_SeqDense"
1878f6be9afSLois Curfman McInnes int MatSolve_SeqDense(Mat A,Vec xx,Vec yy)
188289bc588SBarry Smith {
189c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
190a57ad546SLois Curfman McInnes   int          one = 1,info,ierr;
19187828ca2SBarry Smith   PetscScalar  *x,*y;
19267e560aaSBarry Smith 
1933a40ed3dSBarry Smith   PetscFunctionBegin;
194273d9f13SBarry Smith   if (!A->m || !A->n) PetscFunctionReturn(0);
1957a97a34bSBarry Smith   ierr = VecGetArray(xx,&x);CHKERRQ(ierr);
1967a97a34bSBarry Smith   ierr = VecGetArray(yy,&y);CHKERRQ(ierr);
19787828ca2SBarry Smith   ierr = PetscMemcpy(y,x,A->m*sizeof(PetscScalar));CHKERRQ(ierr);
198c0bbcb79SLois Curfman McInnes   if (A->factor == FACTOR_LU) {
199ae7cfcebSSatish Balay #if defined(PETSC_MISSING_LAPACK_GETRS)
200ae7cfcebSSatish Balay     SETERRQ(PETSC_ERR_SUP,"GETRS - Lapack routine is unavilable.");
201ae7cfcebSSatish Balay #else
202273d9f13SBarry Smith     LAgetrs_("N",&A->m,&one,mat->v,&A->m,mat->pivots,y,&A->m,&info);
203*2ffef20aSBarry Smith     if (info) SETERRQ(PETSC_ERR_LIB,"MBad solve");
204ae7cfcebSSatish Balay #endif
2057a97a34bSBarry Smith   } else if (A->factor == FACTOR_CHOLESKY){
206ae7cfcebSSatish Balay #if defined(PETSC_MISSING_LAPACK_POTRS)
207ae7cfcebSSatish Balay     SETERRQ(PETSC_ERR_SUP,"POTRS - Lapack routine is unavilable.");
208ae7cfcebSSatish Balay #else
209273d9f13SBarry Smith     LApotrs_("L",&A->m,&one,mat->v,&A->m,y,&A->m,&info);
210*2ffef20aSBarry Smith     if (info) SETERRQ(PETSC_ERR_LIB,"MBad solve");
211ae7cfcebSSatish Balay #endif
212289bc588SBarry Smith   }
21329bbc08cSBarry Smith   else SETERRQ(PETSC_ERR_ARG_WRONGSTATE,"Matrix must be factored to solve");
2147a97a34bSBarry Smith   ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr);
2157a97a34bSBarry Smith   ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr);
216b0a32e0cSBarry Smith   PetscLogFlops(2*A->n*A->n - A->n);
2173a40ed3dSBarry Smith   PetscFunctionReturn(0);
218289bc588SBarry Smith }
2196ee01492SSatish Balay 
2204a2ae208SSatish Balay #undef __FUNCT__
2214a2ae208SSatish Balay #define __FUNCT__ "MatSolveTranspose_SeqDense"
2227c922b88SBarry Smith int MatSolveTranspose_SeqDense(Mat A,Vec xx,Vec yy)
223da3a660dSBarry Smith {
224c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
2257a97a34bSBarry Smith   int          ierr,one = 1,info;
22687828ca2SBarry Smith   PetscScalar  *x,*y;
22767e560aaSBarry Smith 
2283a40ed3dSBarry Smith   PetscFunctionBegin;
229273d9f13SBarry Smith   if (!A->m || !A->n) PetscFunctionReturn(0);
2307a97a34bSBarry Smith   ierr = VecGetArray(xx,&x);CHKERRQ(ierr);
2317a97a34bSBarry Smith   ierr = VecGetArray(yy,&y);CHKERRQ(ierr);
23287828ca2SBarry Smith   ierr = PetscMemcpy(y,x,A->m*sizeof(PetscScalar));CHKERRQ(ierr);
233752f5567SLois Curfman McInnes   /* assume if pivots exist then use LU; else Cholesky */
234da3a660dSBarry Smith   if (mat->pivots) {
235ae7cfcebSSatish Balay #if defined(PETSC_MISSING_LAPACK_GETRS)
236ae7cfcebSSatish Balay     SETERRQ(PETSC_ERR_SUP,"GETRS - Lapack routine is unavilable.");
237ae7cfcebSSatish Balay #else
238273d9f13SBarry Smith     LAgetrs_("T",&A->m,&one,mat->v,&A->m,mat->pivots,y,&A->m,&info);
239*2ffef20aSBarry Smith     if (info) SETERRQ(PETSC_ERR_LIB,"Bad solve");
240ae7cfcebSSatish Balay #endif
2417a97a34bSBarry Smith   } else {
242ae7cfcebSSatish Balay #if defined(PETSC_MISSING_LAPACK_POTRS)
243ae7cfcebSSatish Balay     SETERRQ(PETSC_ERR_SUP,"POTRS - Lapack routine is unavilable.");
244ae7cfcebSSatish Balay #else
245273d9f13SBarry Smith     LApotrs_("L",&A->m,&one,mat->v,&A->m,y,&A->m,&info);
246*2ffef20aSBarry Smith     if (info) SETERRQ(PETSC_ERR_LIB,"Bad solve");
247ae7cfcebSSatish Balay #endif
248da3a660dSBarry Smith   }
2497a97a34bSBarry Smith   ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr);
2507a97a34bSBarry Smith   ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr);
251b0a32e0cSBarry Smith   PetscLogFlops(2*A->n*A->n - A->n);
2523a40ed3dSBarry Smith   PetscFunctionReturn(0);
253da3a660dSBarry Smith }
2546ee01492SSatish Balay 
2554a2ae208SSatish Balay #undef __FUNCT__
2564a2ae208SSatish Balay #define __FUNCT__ "MatSolveAdd_SeqDense"
2578f6be9afSLois Curfman McInnes int MatSolveAdd_SeqDense(Mat A,Vec xx,Vec zz,Vec yy)
258da3a660dSBarry Smith {
259c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
2607a97a34bSBarry Smith   int          ierr,one = 1,info;
26187828ca2SBarry Smith   PetscScalar  *x,*y,sone = 1.0;
262da3a660dSBarry Smith   Vec          tmp = 0;
26367e560aaSBarry Smith 
2643a40ed3dSBarry Smith   PetscFunctionBegin;
2657a97a34bSBarry Smith   ierr = VecGetArray(xx,&x);CHKERRQ(ierr);
2667a97a34bSBarry Smith   ierr = VecGetArray(yy,&y);CHKERRQ(ierr);
267273d9f13SBarry Smith   if (!A->m || !A->n) PetscFunctionReturn(0);
268da3a660dSBarry Smith   if (yy == zz) {
26978b31e54SBarry Smith     ierr = VecDuplicate(yy,&tmp);CHKERRQ(ierr);
270b0a32e0cSBarry Smith     PetscLogObjectParent(A,tmp);
27178b31e54SBarry Smith     ierr = VecCopy(yy,tmp);CHKERRQ(ierr);
272da3a660dSBarry Smith   }
27387828ca2SBarry Smith   ierr = PetscMemcpy(y,x,A->m*sizeof(PetscScalar));CHKERRQ(ierr);
274752f5567SLois Curfman McInnes   /* assume if pivots exist then use LU; else Cholesky */
275da3a660dSBarry Smith   if (mat->pivots) {
276ae7cfcebSSatish Balay #if defined(PETSC_MISSING_LAPACK_GETRS)
277ae7cfcebSSatish Balay     SETERRQ(PETSC_ERR_SUP,"GETRS - Lapack routine is unavilable.");
278ae7cfcebSSatish Balay #else
279273d9f13SBarry Smith     LAgetrs_("N",&A->m,&one,mat->v,&A->m,mat->pivots,y,&A->m,&info);
280*2ffef20aSBarry Smith     if (info) SETERRQ(PETSC_ERR_LIB,"Bad solve");
281ae7cfcebSSatish Balay #endif
282a8c6a408SBarry Smith   } else {
283ae7cfcebSSatish Balay #if defined(PETSC_MISSING_LAPACK_POTRS)
284ae7cfcebSSatish Balay     SETERRQ(PETSC_ERR_SUP,"POTRS - Lapack routine is unavilable.");
285ae7cfcebSSatish Balay #else
286273d9f13SBarry Smith     LApotrs_("L",&A->m,&one,mat->v,&A->m,y,&A->m,&info);
287*2ffef20aSBarry Smith     if (info) SETERRQ(PETSC_ERR_LIB,"Bad solve");
288ae7cfcebSSatish Balay #endif
289da3a660dSBarry Smith   }
290a8c6a408SBarry Smith   if (tmp) {ierr = VecAXPY(&sone,tmp,yy);CHKERRQ(ierr); ierr = VecDestroy(tmp);CHKERRQ(ierr);}
291a8c6a408SBarry Smith   else     {ierr = VecAXPY(&sone,zz,yy);CHKERRQ(ierr);}
2927a97a34bSBarry Smith   ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr);
2937a97a34bSBarry Smith   ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr);
294b0a32e0cSBarry Smith   PetscLogFlops(2*A->n*A->n);
2953a40ed3dSBarry Smith   PetscFunctionReturn(0);
296da3a660dSBarry Smith }
29767e560aaSBarry Smith 
2984a2ae208SSatish Balay #undef __FUNCT__
2994a2ae208SSatish Balay #define __FUNCT__ "MatSolveTransposeAdd_SeqDense"
3007c922b88SBarry Smith int MatSolveTransposeAdd_SeqDense(Mat A,Vec xx,Vec zz,Vec yy)
301da3a660dSBarry Smith {
302c0bbcb79SLois Curfman McInnes   Mat_SeqDense  *mat = (Mat_SeqDense*)A->data;
3036abc6512SBarry Smith   int           one = 1,info,ierr;
30487828ca2SBarry Smith   PetscScalar   *x,*y,sone = 1.0;
305da3a660dSBarry Smith   Vec           tmp;
30667e560aaSBarry Smith 
3073a40ed3dSBarry Smith   PetscFunctionBegin;
308273d9f13SBarry Smith   if (!A->m || !A->n) PetscFunctionReturn(0);
3097a97a34bSBarry Smith   ierr = VecGetArray(xx,&x);CHKERRQ(ierr);
3107a97a34bSBarry Smith   ierr = VecGetArray(yy,&y);CHKERRQ(ierr);
311da3a660dSBarry Smith   if (yy == zz) {
31278b31e54SBarry Smith     ierr = VecDuplicate(yy,&tmp);CHKERRQ(ierr);
313b0a32e0cSBarry Smith     PetscLogObjectParent(A,tmp);
31478b31e54SBarry Smith     ierr = VecCopy(yy,tmp);CHKERRQ(ierr);
315da3a660dSBarry Smith   }
31687828ca2SBarry Smith   ierr = PetscMemcpy(y,x,A->m*sizeof(PetscScalar));CHKERRQ(ierr);
317752f5567SLois Curfman McInnes   /* assume if pivots exist then use LU; else Cholesky */
318da3a660dSBarry Smith   if (mat->pivots) {
319ae7cfcebSSatish Balay #if defined(PETSC_MISSING_LAPACK_GETRS)
320ae7cfcebSSatish Balay     SETERRQ(PETSC_ERR_SUP,"GETRS - Lapack routine is unavilable.");
321ae7cfcebSSatish Balay #else
322273d9f13SBarry Smith     LAgetrs_("T",&A->m,&one,mat->v,&A->m,mat->pivots,y,&A->m,&info);
323*2ffef20aSBarry Smith     if (info) SETERRQ(PETSC_ERR_LIB,"Bad solve");
324ae7cfcebSSatish Balay #endif
3253a40ed3dSBarry Smith   } else {
326ae7cfcebSSatish Balay #if defined(PETSC_MISSING_LAPACK_POTRS)
327ae7cfcebSSatish Balay     SETERRQ(PETSC_ERR_SUP,"POTRS - Lapack routine is unavilable.");
328ae7cfcebSSatish Balay #else
329273d9f13SBarry Smith     LApotrs_("L",&A->m,&one,mat->v,&A->m,y,&A->m,&info);
330*2ffef20aSBarry Smith     if (info) SETERRQ(PETSC_ERR_LIB,"Bad solve");
331ae7cfcebSSatish Balay #endif
332da3a660dSBarry Smith   }
33390f02eecSBarry Smith   if (tmp) {
33490f02eecSBarry Smith     ierr = VecAXPY(&sone,tmp,yy);CHKERRQ(ierr);
33590f02eecSBarry Smith     ierr = VecDestroy(tmp);CHKERRQ(ierr);
3363a40ed3dSBarry Smith   } else {
33790f02eecSBarry Smith     ierr = VecAXPY(&sone,zz,yy);CHKERRQ(ierr);
33890f02eecSBarry Smith   }
3397a97a34bSBarry Smith   ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr);
3407a97a34bSBarry Smith   ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr);
341b0a32e0cSBarry Smith   PetscLogFlops(2*A->n*A->n);
3423a40ed3dSBarry Smith   PetscFunctionReturn(0);
343da3a660dSBarry Smith }
344289bc588SBarry Smith /* ------------------------------------------------------------------*/
3454a2ae208SSatish Balay #undef __FUNCT__
3464a2ae208SSatish Balay #define __FUNCT__ "MatRelax_SeqDense"
347329f5518SBarry Smith int MatRelax_SeqDense(Mat A,Vec bb,PetscReal omega,MatSORType flag,
348329f5518SBarry Smith                           PetscReal shift,int its,Vec xx)
349289bc588SBarry Smith {
350c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
35187828ca2SBarry Smith   PetscScalar  *x,*b,*v = mat->v,zero = 0.0,xt;
352273d9f13SBarry Smith   int          ierr,m = A->m,i;
353aa482453SBarry Smith #if !defined(PETSC_USE_COMPLEX)
354bc1b551cSSatish Balay   int          o = 1;
355bc1b551cSSatish Balay #endif
356289bc588SBarry Smith 
3573a40ed3dSBarry Smith   PetscFunctionBegin;
358289bc588SBarry Smith   if (flag & SOR_ZERO_INITIAL_GUESS) {
3593a40ed3dSBarry Smith     /* this is a hack fix, should have another version without the second BLdot */
360bbb6d6a8SBarry Smith     ierr = VecSet(&zero,xx);CHKERRQ(ierr);
361289bc588SBarry Smith   }
3627a97a34bSBarry Smith   ierr = VecGetArray(xx,&x);CHKERRQ(ierr);
3637a97a34bSBarry Smith   ierr = VecGetArray(bb,&b);CHKERRQ(ierr);
364289bc588SBarry Smith   while (its--) {
365289bc588SBarry Smith     if (flag & SOR_FORWARD_SWEEP){
366289bc588SBarry Smith       for (i=0; i<m; i++) {
367aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX)
368f1747703SBarry Smith         /* cannot use BLAS dot for complex because compiler/linker is
369f1747703SBarry Smith            not happy about returning a double complex */
370f1747703SBarry Smith         int    _i;
37187828ca2SBarry Smith         PetscScalar sum = b[i];
372f1747703SBarry Smith         for (_i=0; _i<m; _i++) {
3733f6de6efSSatish Balay           sum -= PetscConj(v[i+_i*m])*x[_i];
374f1747703SBarry Smith         }
375f1747703SBarry Smith         xt = sum;
376f1747703SBarry Smith #else
377289bc588SBarry Smith         xt = b[i]-BLdot_(&m,v+i,&m,x,&o);
378f1747703SBarry Smith #endif
37955a1b374SBarry Smith         x[i] = (1. - omega)*x[i] + omega*(xt+v[i + i*m]*x[i])/(v[i + i*m]+shift);
380289bc588SBarry Smith       }
381289bc588SBarry Smith     }
382289bc588SBarry Smith     if (flag & SOR_BACKWARD_SWEEP) {
383289bc588SBarry Smith       for (i=m-1; i>=0; i--) {
384aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX)
385f1747703SBarry Smith         /* cannot use BLAS dot for complex because compiler/linker is
386f1747703SBarry Smith            not happy about returning a double complex */
387f1747703SBarry Smith         int    _i;
38887828ca2SBarry Smith         PetscScalar sum = b[i];
389f1747703SBarry Smith         for (_i=0; _i<m; _i++) {
3903f6de6efSSatish Balay           sum -= PetscConj(v[i+_i*m])*x[_i];
391f1747703SBarry Smith         }
392f1747703SBarry Smith         xt = sum;
393f1747703SBarry Smith #else
394289bc588SBarry Smith         xt = b[i]-BLdot_(&m,v+i,&m,x,&o);
395f1747703SBarry Smith #endif
39655a1b374SBarry Smith         x[i] = (1. - omega)*x[i] + omega*(xt+v[i + i*m]*x[i])/(v[i + i*m]+shift);
397289bc588SBarry Smith       }
398289bc588SBarry Smith     }
399289bc588SBarry Smith   }
400600d6d0bSBarry Smith   ierr = VecRestoreArray(bb,&b);CHKERRQ(ierr);
4017a97a34bSBarry Smith   ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr);
4023a40ed3dSBarry Smith   PetscFunctionReturn(0);
403289bc588SBarry Smith }
404289bc588SBarry Smith 
405289bc588SBarry Smith /* -----------------------------------------------------------------*/
4064a2ae208SSatish Balay #undef __FUNCT__
4074a2ae208SSatish Balay #define __FUNCT__ "MatMultTranspose_SeqDense"
4087c922b88SBarry Smith int MatMultTranspose_SeqDense(Mat A,Vec xx,Vec yy)
409289bc588SBarry Smith {
410c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
41187828ca2SBarry Smith   PetscScalar  *v = mat->v,*x,*y;
412ea709b57SSatish Balay   int          ierr,_One=1;
413ea709b57SSatish Balay   PetscScalar  _DOne=1.0,_DZero=0.0;
4143a40ed3dSBarry Smith 
4153a40ed3dSBarry Smith   PetscFunctionBegin;
416273d9f13SBarry Smith   if (!A->m || !A->n) PetscFunctionReturn(0);
4177a97a34bSBarry Smith   ierr = VecGetArray(xx,&x);CHKERRQ(ierr);
4187a97a34bSBarry Smith   ierr = VecGetArray(yy,&y);CHKERRQ(ierr);
419273d9f13SBarry Smith   LAgemv_("T",&(A->m),&(A->n),&_DOne,v,&(A->m),x,&_One,&_DZero,y,&_One);
4207a97a34bSBarry Smith   ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr);
4217a97a34bSBarry Smith   ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr);
422b0a32e0cSBarry Smith   PetscLogFlops(2*A->m*A->n - A->n);
4233a40ed3dSBarry Smith   PetscFunctionReturn(0);
424289bc588SBarry Smith }
4256ee01492SSatish Balay 
4264a2ae208SSatish Balay #undef __FUNCT__
4274a2ae208SSatish Balay #define __FUNCT__ "MatMult_SeqDense"
42844cd7ae7SLois Curfman McInnes int MatMult_SeqDense(Mat A,Vec xx,Vec yy)
429289bc588SBarry Smith {
430c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
43187828ca2SBarry Smith   PetscScalar  *v = mat->v,*x,*y,_DOne=1.0,_DZero=0.0;
432329f5518SBarry Smith   int          ierr,_One=1;
4333a40ed3dSBarry Smith 
4343a40ed3dSBarry Smith   PetscFunctionBegin;
435273d9f13SBarry Smith   if (!A->m || !A->n) PetscFunctionReturn(0);
4367a97a34bSBarry Smith   ierr = VecGetArray(xx,&x);CHKERRQ(ierr);
4377a97a34bSBarry Smith   ierr = VecGetArray(yy,&y);CHKERRQ(ierr);
438273d9f13SBarry Smith   LAgemv_("N",&(A->m),&(A->n),&_DOne,v,&(A->m),x,&_One,&_DZero,y,&_One);
4397a97a34bSBarry Smith   ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr);
4407a97a34bSBarry Smith   ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr);
441b0a32e0cSBarry Smith   PetscLogFlops(2*A->m*A->n - A->m);
4423a40ed3dSBarry Smith   PetscFunctionReturn(0);
443289bc588SBarry Smith }
4446ee01492SSatish Balay 
4454a2ae208SSatish Balay #undef __FUNCT__
4464a2ae208SSatish Balay #define __FUNCT__ "MatMultAdd_SeqDense"
44744cd7ae7SLois Curfman McInnes int MatMultAdd_SeqDense(Mat A,Vec xx,Vec zz,Vec yy)
448289bc588SBarry Smith {
449c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
45087828ca2SBarry Smith   PetscScalar  *v = mat->v,*x,*y,_DOne=1.0;
451329f5518SBarry Smith   int          ierr,_One=1;
4523a40ed3dSBarry Smith 
4533a40ed3dSBarry Smith   PetscFunctionBegin;
454273d9f13SBarry Smith   if (!A->m || !A->n) PetscFunctionReturn(0);
455600d6d0bSBarry Smith   if (zz != yy) {ierr = VecCopy(zz,yy);CHKERRQ(ierr);}
4567a97a34bSBarry Smith   ierr = VecGetArray(xx,&x);CHKERRQ(ierr);
4577a97a34bSBarry Smith   ierr = VecGetArray(yy,&y);CHKERRQ(ierr);
458273d9f13SBarry Smith   LAgemv_("N",&(A->m),&(A->n),&_DOne,v,&(A->m),x,&_One,&_DOne,y,&_One);
4597a97a34bSBarry Smith   ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr);
4607a97a34bSBarry Smith   ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr);
461b0a32e0cSBarry Smith   PetscLogFlops(2*A->m*A->n);
4623a40ed3dSBarry Smith   PetscFunctionReturn(0);
463289bc588SBarry Smith }
4646ee01492SSatish Balay 
4654a2ae208SSatish Balay #undef __FUNCT__
4664a2ae208SSatish Balay #define __FUNCT__ "MatMultTransposeAdd_SeqDense"
4677c922b88SBarry Smith int MatMultTransposeAdd_SeqDense(Mat A,Vec xx,Vec zz,Vec yy)
468289bc588SBarry Smith {
469c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
47087828ca2SBarry Smith   PetscScalar  *v = mat->v,*x,*y;
4717a97a34bSBarry Smith   int          ierr,_One=1;
47287828ca2SBarry Smith   PetscScalar  _DOne=1.0;
4733a40ed3dSBarry Smith 
4743a40ed3dSBarry Smith   PetscFunctionBegin;
475273d9f13SBarry Smith   if (!A->m || !A->n) PetscFunctionReturn(0);
476600d6d0bSBarry Smith   if (zz != yy) {ierr = VecCopy(zz,yy);CHKERRQ(ierr);}
4777a97a34bSBarry Smith   ierr = VecGetArray(xx,&x);CHKERRQ(ierr);
4787a97a34bSBarry Smith   ierr = VecGetArray(yy,&y);CHKERRQ(ierr);
479273d9f13SBarry Smith   LAgemv_("T",&(A->m),&(A->n),&_DOne,v,&(A->m),x,&_One,&_DOne,y,&_One);
4807a97a34bSBarry Smith   ierr = VecRestoreArray(xx,&x);CHKERRQ(ierr);
4817a97a34bSBarry Smith   ierr = VecRestoreArray(yy,&y);CHKERRQ(ierr);
482b0a32e0cSBarry Smith   PetscLogFlops(2*A->m*A->n);
4833a40ed3dSBarry Smith   PetscFunctionReturn(0);
484289bc588SBarry Smith }
485289bc588SBarry Smith 
486289bc588SBarry Smith /* -----------------------------------------------------------------*/
4874a2ae208SSatish Balay #undef __FUNCT__
4884a2ae208SSatish Balay #define __FUNCT__ "MatGetRow_SeqDense"
48987828ca2SBarry Smith int MatGetRow_SeqDense(Mat A,int row,int *ncols,int **cols,PetscScalar **vals)
490289bc588SBarry Smith {
491c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
49287828ca2SBarry Smith   PetscScalar  *v;
493b0a32e0cSBarry Smith   int          i,ierr;
49467e560aaSBarry Smith 
4953a40ed3dSBarry Smith   PetscFunctionBegin;
496273d9f13SBarry Smith   *ncols = A->n;
497289bc588SBarry Smith   if (cols) {
498b0a32e0cSBarry Smith     ierr = PetscMalloc((A->n+1)*sizeof(int),cols);CHKERRQ(ierr);
499273d9f13SBarry Smith     for (i=0; i<A->n; i++) (*cols)[i] = i;
500289bc588SBarry Smith   }
501289bc588SBarry Smith   if (vals) {
50287828ca2SBarry Smith     ierr = PetscMalloc((A->n+1)*sizeof(PetscScalar),vals);CHKERRQ(ierr);
503289bc588SBarry Smith     v    = mat->v + row;
504273d9f13SBarry Smith     for (i=0; i<A->n; i++) {(*vals)[i] = *v; v += A->m;}
505289bc588SBarry Smith   }
5063a40ed3dSBarry Smith   PetscFunctionReturn(0);
507289bc588SBarry Smith }
5086ee01492SSatish Balay 
5094a2ae208SSatish Balay #undef __FUNCT__
5104a2ae208SSatish Balay #define __FUNCT__ "MatRestoreRow_SeqDense"
51187828ca2SBarry Smith int MatRestoreRow_SeqDense(Mat A,int row,int *ncols,int **cols,PetscScalar **vals)
512289bc588SBarry Smith {
513606d414cSSatish Balay   int ierr;
514606d414cSSatish Balay   PetscFunctionBegin;
515606d414cSSatish Balay   if (cols) {ierr = PetscFree(*cols);CHKERRQ(ierr);}
516606d414cSSatish Balay   if (vals) {ierr = PetscFree(*vals);CHKERRQ(ierr); }
5173a40ed3dSBarry Smith   PetscFunctionReturn(0);
518289bc588SBarry Smith }
519289bc588SBarry Smith /* ----------------------------------------------------------------*/
5204a2ae208SSatish Balay #undef __FUNCT__
5214a2ae208SSatish Balay #define __FUNCT__ "MatSetValues_SeqDense"
5228f6be9afSLois Curfman McInnes int MatSetValues_SeqDense(Mat A,int m,int *indexm,int n,
52387828ca2SBarry Smith                                     int *indexn,PetscScalar *v,InsertMode addv)
524289bc588SBarry Smith {
525c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
526289bc588SBarry Smith   int          i,j;
527d6dfbf8fSBarry Smith 
5283a40ed3dSBarry Smith   PetscFunctionBegin;
529289bc588SBarry Smith   if (!mat->roworiented) {
530dbb450caSBarry Smith     if (addv == INSERT_VALUES) {
531289bc588SBarry Smith       for (j=0; j<n; j++) {
5325ef9f2a5SBarry Smith         if (indexn[j] < 0) {v += m; continue;}
533aa482453SBarry Smith #if defined(PETSC_USE_BOPT_g)
53429bbc08cSBarry Smith         if (indexn[j] >= A->n) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Column too large");
53558804f6dSBarry Smith #endif
536289bc588SBarry Smith         for (i=0; i<m; i++) {
5375ef9f2a5SBarry Smith           if (indexm[i] < 0) {v++; continue;}
538aa482453SBarry Smith #if defined(PETSC_USE_BOPT_g)
53929bbc08cSBarry Smith           if (indexm[i] >= A->m) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Row too large");
54058804f6dSBarry Smith #endif
541273d9f13SBarry Smith           mat->v[indexn[j]*A->m + indexm[i]] = *v++;
542289bc588SBarry Smith         }
543289bc588SBarry Smith       }
5443a40ed3dSBarry Smith     } else {
545289bc588SBarry Smith       for (j=0; j<n; j++) {
5465ef9f2a5SBarry Smith         if (indexn[j] < 0) {v += m; continue;}
547aa482453SBarry Smith #if defined(PETSC_USE_BOPT_g)
54829bbc08cSBarry Smith         if (indexn[j] >= A->n) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Column too large");
54958804f6dSBarry Smith #endif
550289bc588SBarry Smith         for (i=0; i<m; i++) {
5515ef9f2a5SBarry Smith           if (indexm[i] < 0) {v++; continue;}
552aa482453SBarry Smith #if defined(PETSC_USE_BOPT_g)
55329bbc08cSBarry Smith           if (indexm[i] >= A->m) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Row too large");
55458804f6dSBarry Smith #endif
555273d9f13SBarry Smith           mat->v[indexn[j]*A->m + indexm[i]] += *v++;
556289bc588SBarry Smith         }
557289bc588SBarry Smith       }
558289bc588SBarry Smith     }
5593a40ed3dSBarry Smith   } else {
560dbb450caSBarry Smith     if (addv == INSERT_VALUES) {
561e8d4e0b9SBarry Smith       for (i=0; i<m; i++) {
5625ef9f2a5SBarry Smith         if (indexm[i] < 0) { v += n; continue;}
563aa482453SBarry Smith #if defined(PETSC_USE_BOPT_g)
56429bbc08cSBarry Smith         if (indexm[i] >= A->m) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Row too large");
56558804f6dSBarry Smith #endif
566e8d4e0b9SBarry Smith         for (j=0; j<n; j++) {
5675ef9f2a5SBarry Smith           if (indexn[j] < 0) { v++; continue;}
568aa482453SBarry Smith #if defined(PETSC_USE_BOPT_g)
56929bbc08cSBarry Smith           if (indexn[j] >= A->n) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Column too large");
57058804f6dSBarry Smith #endif
571273d9f13SBarry Smith           mat->v[indexn[j]*A->m + indexm[i]] = *v++;
572e8d4e0b9SBarry Smith         }
573e8d4e0b9SBarry Smith       }
5743a40ed3dSBarry Smith     } else {
575289bc588SBarry Smith       for (i=0; i<m; i++) {
5765ef9f2a5SBarry Smith         if (indexm[i] < 0) { v += n; continue;}
577aa482453SBarry Smith #if defined(PETSC_USE_BOPT_g)
57829bbc08cSBarry Smith         if (indexm[i] >= A->m) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Row too large");
57958804f6dSBarry Smith #endif
580289bc588SBarry Smith         for (j=0; j<n; j++) {
5815ef9f2a5SBarry Smith           if (indexn[j] < 0) { v++; continue;}
582aa482453SBarry Smith #if defined(PETSC_USE_BOPT_g)
58329bbc08cSBarry Smith           if (indexn[j] >= A->n) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Column too large");
58458804f6dSBarry Smith #endif
585273d9f13SBarry Smith           mat->v[indexn[j]*A->m + indexm[i]] += *v++;
586289bc588SBarry Smith         }
587289bc588SBarry Smith       }
588289bc588SBarry Smith     }
589e8d4e0b9SBarry Smith   }
5903a40ed3dSBarry Smith   PetscFunctionReturn(0);
591289bc588SBarry Smith }
592e8d4e0b9SBarry Smith 
5934a2ae208SSatish Balay #undef __FUNCT__
5944a2ae208SSatish Balay #define __FUNCT__ "MatGetValues_SeqDense"
59587828ca2SBarry Smith int MatGetValues_SeqDense(Mat A,int m,int *indexm,int n,int *indexn,PetscScalar *v)
596ae80bb75SLois Curfman McInnes {
597ae80bb75SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
598ae80bb75SLois Curfman McInnes   int          i,j;
59987828ca2SBarry Smith   PetscScalar  *vpt = v;
600ae80bb75SLois Curfman McInnes 
6013a40ed3dSBarry Smith   PetscFunctionBegin;
602ae80bb75SLois Curfman McInnes   /* row-oriented output */
603ae80bb75SLois Curfman McInnes   for (i=0; i<m; i++) {
604ae80bb75SLois Curfman McInnes     for (j=0; j<n; j++) {
605273d9f13SBarry Smith       *vpt++ = mat->v[indexn[j]*A->m + indexm[i]];
606ae80bb75SLois Curfman McInnes     }
607ae80bb75SLois Curfman McInnes   }
6083a40ed3dSBarry Smith   PetscFunctionReturn(0);
609ae80bb75SLois Curfman McInnes }
610ae80bb75SLois Curfman McInnes 
611289bc588SBarry Smith /* -----------------------------------------------------------------*/
612289bc588SBarry Smith 
613e090d566SSatish Balay #include "petscsys.h"
61488e32edaSLois Curfman McInnes 
615273d9f13SBarry Smith EXTERN_C_BEGIN
6164a2ae208SSatish Balay #undef __FUNCT__
6174a2ae208SSatish Balay #define __FUNCT__ "MatLoad_SeqDense"
618b0a32e0cSBarry Smith int MatLoad_SeqDense(PetscViewer viewer,MatType type,Mat *A)
61988e32edaSLois Curfman McInnes {
62088e32edaSLois Curfman McInnes   Mat_SeqDense *a;
62188e32edaSLois Curfman McInnes   Mat          B;
62288e32edaSLois Curfman McInnes   int          *scols,i,j,nz,ierr,fd,header[4],size;
62388e32edaSLois Curfman McInnes   int          *rowlengths = 0,M,N,*cols;
62487828ca2SBarry Smith   PetscScalar  *vals,*svals,*v,*w;
62519bcc07fSBarry Smith   MPI_Comm     comm = ((PetscObject)viewer)->comm;
62688e32edaSLois Curfman McInnes 
6273a40ed3dSBarry Smith   PetscFunctionBegin;
628d132466eSBarry Smith   ierr = MPI_Comm_size(comm,&size);CHKERRQ(ierr);
62929bbc08cSBarry Smith   if (size > 1) SETERRQ(PETSC_ERR_ARG_WRONG,"view must have one processor");
630b0a32e0cSBarry Smith   ierr = PetscViewerBinaryGetDescriptor(viewer,&fd);CHKERRQ(ierr);
6310752156aSBarry Smith   ierr = PetscBinaryRead(fd,header,4,PETSC_INT);CHKERRQ(ierr);
63229bbc08cSBarry Smith   if (header[0] != MAT_COOKIE) SETERRQ(PETSC_ERR_FILE_UNEXPECTED,"Not matrix object");
63388e32edaSLois Curfman McInnes   M = header[1]; N = header[2]; nz = header[3];
63488e32edaSLois Curfman McInnes 
63590ace30eSBarry Smith   if (nz == MATRIX_BINARY_FORMAT_DENSE) { /* matrix in file is dense */
63690ace30eSBarry Smith     ierr = MatCreateSeqDense(comm,M,N,PETSC_NULL,A);CHKERRQ(ierr);
63790ace30eSBarry Smith     B    = *A;
63890ace30eSBarry Smith     a    = (Mat_SeqDense*)B->data;
6394a41a4d3SSatish Balay     v    = a->v;
6404a41a4d3SSatish Balay     /* Allocate some temp space to read in the values and then flip them
6414a41a4d3SSatish Balay        from row major to column major */
64287828ca2SBarry Smith     ierr = PetscMalloc((M*N+1)*sizeof(PetscScalar),&w);CHKERRQ(ierr);
64390ace30eSBarry Smith     /* read in nonzero values */
6444a41a4d3SSatish Balay     ierr = PetscBinaryRead(fd,w,M*N,PETSC_SCALAR);CHKERRQ(ierr);
6454a41a4d3SSatish Balay     /* now flip the values and store them in the matrix*/
6464a41a4d3SSatish Balay     for (j=0; j<N; j++) {
6474a41a4d3SSatish Balay       for (i=0; i<M; i++) {
6484a41a4d3SSatish Balay         *v++ =w[i*N+j];
6494a41a4d3SSatish Balay       }
6504a41a4d3SSatish Balay     }
651606d414cSSatish Balay     ierr = PetscFree(w);CHKERRQ(ierr);
6526d4a8577SBarry Smith     ierr = MatAssemblyBegin(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
6536d4a8577SBarry Smith     ierr = MatAssemblyEnd(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
65490ace30eSBarry Smith   } else {
65588e32edaSLois Curfman McInnes     /* read row lengths */
656b0a32e0cSBarry Smith     ierr = PetscMalloc((M+1)*sizeof(int),&rowlengths);CHKERRQ(ierr);
6570752156aSBarry Smith     ierr = PetscBinaryRead(fd,rowlengths,M,PETSC_INT);CHKERRQ(ierr);
65888e32edaSLois Curfman McInnes 
65988e32edaSLois Curfman McInnes     /* create our matrix */
660b4fd4287SBarry Smith     ierr = MatCreateSeqDense(comm,M,N,PETSC_NULL,A);CHKERRQ(ierr);
66188e32edaSLois Curfman McInnes     B = *A;
66288e32edaSLois Curfman McInnes     a = (Mat_SeqDense*)B->data;
66388e32edaSLois Curfman McInnes     v = a->v;
66488e32edaSLois Curfman McInnes 
66588e32edaSLois Curfman McInnes     /* read column indices and nonzeros */
666b0a32e0cSBarry Smith     ierr = PetscMalloc((nz+1)*sizeof(int),&scols);CHKERRQ(ierr);
667b0a32e0cSBarry Smith     cols = scols;
6680752156aSBarry Smith     ierr = PetscBinaryRead(fd,cols,nz,PETSC_INT);CHKERRQ(ierr);
66987828ca2SBarry Smith     ierr = PetscMalloc((nz+1)*sizeof(PetscScalar),&svals);CHKERRQ(ierr);
670b0a32e0cSBarry Smith     vals = svals;
6710752156aSBarry Smith     ierr = PetscBinaryRead(fd,vals,nz,PETSC_SCALAR);CHKERRQ(ierr);
67288e32edaSLois Curfman McInnes 
67388e32edaSLois Curfman McInnes     /* insert into matrix */
67488e32edaSLois Curfman McInnes     for (i=0; i<M; i++) {
67588e32edaSLois Curfman McInnes       for (j=0; j<rowlengths[i]; j++) v[i+M*scols[j]] = svals[j];
67688e32edaSLois Curfman McInnes       svals += rowlengths[i]; scols += rowlengths[i];
67788e32edaSLois Curfman McInnes     }
678606d414cSSatish Balay     ierr = PetscFree(vals);CHKERRQ(ierr);
679606d414cSSatish Balay     ierr = PetscFree(cols);CHKERRQ(ierr);
680606d414cSSatish Balay     ierr = PetscFree(rowlengths);CHKERRQ(ierr);
68188e32edaSLois Curfman McInnes 
6826d4a8577SBarry Smith     ierr = MatAssemblyBegin(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
6836d4a8577SBarry Smith     ierr = MatAssemblyEnd(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
68490ace30eSBarry Smith   }
6853a40ed3dSBarry Smith   PetscFunctionReturn(0);
68688e32edaSLois Curfman McInnes }
687273d9f13SBarry Smith EXTERN_C_END
68888e32edaSLois Curfman McInnes 
689e090d566SSatish Balay #include "petscsys.h"
690932b0c3eSLois Curfman McInnes 
6914a2ae208SSatish Balay #undef __FUNCT__
6924a2ae208SSatish Balay #define __FUNCT__ "MatView_SeqDense_ASCII"
693b0a32e0cSBarry Smith static int MatView_SeqDense_ASCII(Mat A,PetscViewer viewer)
694289bc588SBarry Smith {
695932b0c3eSLois Curfman McInnes   Mat_SeqDense      *a = (Mat_SeqDense*)A->data;
696fb9695e5SSatish Balay   int               ierr,i,j;
697fb9695e5SSatish Balay   char              *name;
69887828ca2SBarry Smith   PetscScalar       *v;
699f3ef73ceSBarry Smith   PetscViewerFormat format;
700932b0c3eSLois Curfman McInnes 
7013a40ed3dSBarry Smith   PetscFunctionBegin;
702435da068SBarry Smith   ierr = PetscObjectGetName((PetscObject)A,&name);CHKERRQ(ierr);
703b0a32e0cSBarry Smith   ierr = PetscViewerGetFormat(viewer,&format);CHKERRQ(ierr);
704fb9695e5SSatish Balay   if (format == PETSC_VIEWER_ASCII_INFO || format == PETSC_VIEWER_ASCII_INFO_LONG) {
7053a40ed3dSBarry Smith     PetscFunctionReturn(0);  /* do nothing for now */
706fb9695e5SSatish Balay   } else if (format == PETSC_VIEWER_ASCII_COMMON) {
707b0a32e0cSBarry Smith     ierr = PetscViewerASCIIUseTabs(viewer,PETSC_NO);CHKERRQ(ierr);
708273d9f13SBarry Smith     for (i=0; i<A->m; i++) {
70944cd7ae7SLois Curfman McInnes       v = a->v + i;
710b0a32e0cSBarry Smith       ierr = PetscViewerASCIIPrintf(viewer,"row %d:",i);CHKERRQ(ierr);
711273d9f13SBarry Smith       for (j=0; j<A->n; j++) {
712aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX)
713329f5518SBarry Smith         if (PetscRealPart(*v) != 0.0 && PetscImaginaryPart(*v) != 0.0) {
714b0a32e0cSBarry Smith           ierr = PetscViewerASCIIPrintf(viewer," %d %g + %g i",j,PetscRealPart(*v),PetscImaginaryPart(*v));CHKERRQ(ierr);
715329f5518SBarry Smith         } else if (PetscRealPart(*v)) {
716b0a32e0cSBarry Smith           ierr = PetscViewerASCIIPrintf(viewer," %d %g ",j,PetscRealPart(*v));CHKERRQ(ierr);
7176831982aSBarry Smith         }
71880cd9d93SLois Curfman McInnes #else
7196831982aSBarry Smith         if (*v) {
720b0a32e0cSBarry Smith           ierr = PetscViewerASCIIPrintf(viewer," %d %g ",j,*v);CHKERRQ(ierr);
7216831982aSBarry Smith         }
72280cd9d93SLois Curfman McInnes #endif
723273d9f13SBarry Smith         v += A->m;
72480cd9d93SLois Curfman McInnes       }
725b0a32e0cSBarry Smith       ierr = PetscViewerASCIIPrintf(viewer,"\n");CHKERRQ(ierr);
72680cd9d93SLois Curfman McInnes     }
727b0a32e0cSBarry Smith     ierr = PetscViewerASCIIUseTabs(viewer,PETSC_YES);CHKERRQ(ierr);
7283a40ed3dSBarry Smith   } else {
729b0a32e0cSBarry Smith     ierr = PetscViewerASCIIUseTabs(viewer,PETSC_NO);CHKERRQ(ierr);
730aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX)
731ffac6cdbSBarry Smith     PetscTruth allreal = PETSC_TRUE;
73247989497SBarry Smith     /* determine if matrix has all real values */
73347989497SBarry Smith     v = a->v;
734273d9f13SBarry Smith     for (i=0; i<A->m*A->n; i++) {
735ffac6cdbSBarry Smith       if (PetscImaginaryPart(v[i])) { allreal = PETSC_FALSE; break ;}
73647989497SBarry Smith     }
73747989497SBarry Smith #endif
738fb9695e5SSatish Balay     if (format == PETSC_VIEWER_ASCII_MATLAB) {
7393a7fca6bSBarry Smith       ierr = PetscObjectGetName((PetscObject)A,&name);CHKERRQ(ierr);
740b0a32e0cSBarry Smith       ierr = PetscViewerASCIIPrintf(viewer,"%% Size = %d %d \n",A->m,A->n);CHKERRQ(ierr);
741fb9695e5SSatish Balay       ierr = PetscViewerASCIIPrintf(viewer,"%s = zeros(%d,%d);\n",name,A->m,A->n);CHKERRQ(ierr);
742fb9695e5SSatish Balay       ierr = PetscViewerASCIIPrintf(viewer,"%s = [\n",name);CHKERRQ(ierr);
743ffac6cdbSBarry Smith     }
744ffac6cdbSBarry Smith 
745273d9f13SBarry Smith     for (i=0; i<A->m; i++) {
746932b0c3eSLois Curfman McInnes       v = a->v + i;
747273d9f13SBarry Smith       for (j=0; j<A->n; j++) {
748aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX)
74947989497SBarry Smith         if (allreal) {
750b0a32e0cSBarry Smith           ierr = PetscViewerASCIIPrintf(viewer,"%6.4e ",PetscRealPart(*v));CHKERRQ(ierr); v += A->m;
75147989497SBarry Smith         } else {
752b0a32e0cSBarry Smith           ierr = PetscViewerASCIIPrintf(viewer,"%6.4e + %6.4e i ",PetscRealPart(*v),PetscImaginaryPart(*v));CHKERRQ(ierr); v += A->m;
75347989497SBarry Smith         }
754289bc588SBarry Smith #else
755b0a32e0cSBarry Smith         ierr = PetscViewerASCIIPrintf(viewer,"%6.4e ",*v);CHKERRQ(ierr); v += A->m;
756289bc588SBarry Smith #endif
757289bc588SBarry Smith       }
758b0a32e0cSBarry Smith       ierr = PetscViewerASCIIPrintf(viewer,"\n");CHKERRQ(ierr);
759289bc588SBarry Smith     }
760fb9695e5SSatish Balay     if (format == PETSC_VIEWER_ASCII_MATLAB) {
761b0a32e0cSBarry Smith       ierr = PetscViewerASCIIPrintf(viewer,"];\n");CHKERRQ(ierr);
762ffac6cdbSBarry Smith     }
763b0a32e0cSBarry Smith     ierr = PetscViewerASCIIUseTabs(viewer,PETSC_YES);CHKERRQ(ierr);
764da3a660dSBarry Smith   }
765b0a32e0cSBarry Smith   ierr = PetscViewerFlush(viewer);CHKERRQ(ierr);
7663a40ed3dSBarry Smith   PetscFunctionReturn(0);
767289bc588SBarry Smith }
768289bc588SBarry Smith 
7694a2ae208SSatish Balay #undef __FUNCT__
7704a2ae208SSatish Balay #define __FUNCT__ "MatView_SeqDense_Binary"
771b0a32e0cSBarry Smith static int MatView_SeqDense_Binary(Mat A,PetscViewer viewer)
772932b0c3eSLois Curfman McInnes {
773932b0c3eSLois Curfman McInnes   Mat_SeqDense      *a = (Mat_SeqDense*)A->data;
774273d9f13SBarry Smith   int               ict,j,n = A->n,m = A->m,i,fd,*col_lens,ierr,nz = m*n;
77587828ca2SBarry Smith   PetscScalar       *v,*anonz,*vals;
776f3ef73ceSBarry Smith   PetscViewerFormat format;
777932b0c3eSLois Curfman McInnes 
7783a40ed3dSBarry Smith   PetscFunctionBegin;
779b0a32e0cSBarry Smith   ierr = PetscViewerBinaryGetDescriptor(viewer,&fd);CHKERRQ(ierr);
78090ace30eSBarry Smith 
781b0a32e0cSBarry Smith   ierr = PetscViewerGetFormat(viewer,&format);CHKERRQ(ierr);
782fb9695e5SSatish Balay   if (format == PETSC_VIEWER_BINARY_NATIVE) {
78390ace30eSBarry Smith     /* store the matrix as a dense matrix */
784b0a32e0cSBarry Smith     ierr = PetscMalloc(4*sizeof(int),&col_lens);CHKERRQ(ierr);
78590ace30eSBarry Smith     col_lens[0] = MAT_COOKIE;
78690ace30eSBarry Smith     col_lens[1] = m;
78790ace30eSBarry Smith     col_lens[2] = n;
78890ace30eSBarry Smith     col_lens[3] = MATRIX_BINARY_FORMAT_DENSE;
7890752156aSBarry Smith     ierr = PetscBinaryWrite(fd,col_lens,4,PETSC_INT,1);CHKERRQ(ierr);
790606d414cSSatish Balay     ierr = PetscFree(col_lens);CHKERRQ(ierr);
79190ace30eSBarry Smith 
79290ace30eSBarry Smith     /* write out matrix, by rows */
79387828ca2SBarry Smith     ierr = PetscMalloc((m*n+1)*sizeof(PetscScalar),&vals);CHKERRQ(ierr);
79490ace30eSBarry Smith     v    = a->v;
79590ace30eSBarry Smith     for (i=0; i<m; i++) {
79690ace30eSBarry Smith       for (j=0; j<n; j++) {
79790ace30eSBarry Smith         vals[i + j*m] = *v++;
79890ace30eSBarry Smith       }
79990ace30eSBarry Smith     }
8000752156aSBarry Smith     ierr = PetscBinaryWrite(fd,vals,n*m,PETSC_SCALAR,0);CHKERRQ(ierr);
801606d414cSSatish Balay     ierr = PetscFree(vals);CHKERRQ(ierr);
80290ace30eSBarry Smith   } else {
803b0a32e0cSBarry Smith     ierr = PetscMalloc((4+nz)*sizeof(int),&col_lens);CHKERRQ(ierr);
804932b0c3eSLois Curfman McInnes     col_lens[0] = MAT_COOKIE;
805932b0c3eSLois Curfman McInnes     col_lens[1] = m;
806932b0c3eSLois Curfman McInnes     col_lens[2] = n;
807932b0c3eSLois Curfman McInnes     col_lens[3] = nz;
808932b0c3eSLois Curfman McInnes 
809932b0c3eSLois Curfman McInnes     /* store lengths of each row and write (including header) to file */
810932b0c3eSLois Curfman McInnes     for (i=0; i<m; i++) col_lens[4+i] = n;
8110752156aSBarry Smith     ierr = PetscBinaryWrite(fd,col_lens,4+m,PETSC_INT,1);CHKERRQ(ierr);
812932b0c3eSLois Curfman McInnes 
813932b0c3eSLois Curfman McInnes     /* Possibly should write in smaller increments, not whole matrix at once? */
814932b0c3eSLois Curfman McInnes     /* store column indices (zero start index) */
815932b0c3eSLois Curfman McInnes     ict = 0;
816932b0c3eSLois Curfman McInnes     for (i=0; i<m; i++) {
817932b0c3eSLois Curfman McInnes       for (j=0; j<n; j++) col_lens[ict++] = j;
818932b0c3eSLois Curfman McInnes     }
8190752156aSBarry Smith     ierr = PetscBinaryWrite(fd,col_lens,nz,PETSC_INT,0);CHKERRQ(ierr);
820606d414cSSatish Balay     ierr = PetscFree(col_lens);CHKERRQ(ierr);
821932b0c3eSLois Curfman McInnes 
822932b0c3eSLois Curfman McInnes     /* store nonzero values */
82387828ca2SBarry Smith     ierr = PetscMalloc((nz+1)*sizeof(PetscScalar),&anonz);CHKERRQ(ierr);
824932b0c3eSLois Curfman McInnes     ict  = 0;
825932b0c3eSLois Curfman McInnes     for (i=0; i<m; i++) {
826932b0c3eSLois Curfman McInnes       v = a->v + i;
827932b0c3eSLois Curfman McInnes       for (j=0; j<n; j++) {
828273d9f13SBarry Smith         anonz[ict++] = *v; v += A->m;
829932b0c3eSLois Curfman McInnes       }
830932b0c3eSLois Curfman McInnes     }
8310752156aSBarry Smith     ierr = PetscBinaryWrite(fd,anonz,nz,PETSC_SCALAR,0);CHKERRQ(ierr);
832606d414cSSatish Balay     ierr = PetscFree(anonz);CHKERRQ(ierr);
83390ace30eSBarry Smith   }
8343a40ed3dSBarry Smith   PetscFunctionReturn(0);
835932b0c3eSLois Curfman McInnes }
836932b0c3eSLois Curfman McInnes 
8374a2ae208SSatish Balay #undef __FUNCT__
8384a2ae208SSatish Balay #define __FUNCT__ "MatView_SeqDense_Draw_Zoom"
839b0a32e0cSBarry Smith int MatView_SeqDense_Draw_Zoom(PetscDraw draw,void *Aa)
840f1af5d2fSBarry Smith {
841f1af5d2fSBarry Smith   Mat               A = (Mat) Aa;
842f1af5d2fSBarry Smith   Mat_SeqDense      *a = (Mat_SeqDense*)A->data;
843fb9695e5SSatish Balay   int               m = A->m,n = A->n,color,i,j,ierr;
84487828ca2SBarry Smith   PetscScalar       *v = a->v;
845b0a32e0cSBarry Smith   PetscViewer       viewer;
846b0a32e0cSBarry Smith   PetscDraw         popup;
847329f5518SBarry Smith   PetscReal         xl,yl,xr,yr,x_l,x_r,y_l,y_r,scale,maxv = 0.0;
848f3ef73ceSBarry Smith   PetscViewerFormat format;
849f1af5d2fSBarry Smith 
850f1af5d2fSBarry Smith   PetscFunctionBegin;
851f1af5d2fSBarry Smith 
852f1af5d2fSBarry Smith   ierr = PetscObjectQuery((PetscObject)A,"Zoomviewer",(PetscObject*)&viewer);CHKERRQ(ierr);
853b0a32e0cSBarry Smith   ierr = PetscViewerGetFormat(viewer,&format);CHKERRQ(ierr);
854b0a32e0cSBarry Smith   ierr = PetscDrawGetCoordinates(draw,&xl,&yl,&xr,&yr);CHKERRQ(ierr);
855f1af5d2fSBarry Smith 
856f1af5d2fSBarry Smith   /* Loop over matrix elements drawing boxes */
857fb9695e5SSatish Balay   if (format != PETSC_VIEWER_DRAW_CONTOUR) {
858f1af5d2fSBarry Smith     /* Blue for negative and Red for positive */
859b0a32e0cSBarry Smith     color = PETSC_DRAW_BLUE;
860f1af5d2fSBarry Smith     for(j = 0; j < n; j++) {
861f1af5d2fSBarry Smith       x_l = j;
862f1af5d2fSBarry Smith       x_r = x_l + 1.0;
863f1af5d2fSBarry Smith       for(i = 0; i < m; i++) {
864f1af5d2fSBarry Smith         y_l = m - i - 1.0;
865f1af5d2fSBarry Smith         y_r = y_l + 1.0;
866f1af5d2fSBarry Smith #if defined(PETSC_USE_COMPLEX)
867329f5518SBarry Smith         if (PetscRealPart(v[j*m+i]) >  0.) {
868b0a32e0cSBarry Smith           color = PETSC_DRAW_RED;
869329f5518SBarry Smith         } else if (PetscRealPart(v[j*m+i]) <  0.) {
870b0a32e0cSBarry Smith           color = PETSC_DRAW_BLUE;
871f1af5d2fSBarry Smith         } else {
872f1af5d2fSBarry Smith           continue;
873f1af5d2fSBarry Smith         }
874f1af5d2fSBarry Smith #else
875f1af5d2fSBarry Smith         if (v[j*m+i] >  0.) {
876b0a32e0cSBarry Smith           color = PETSC_DRAW_RED;
877f1af5d2fSBarry Smith         } else if (v[j*m+i] <  0.) {
878b0a32e0cSBarry Smith           color = PETSC_DRAW_BLUE;
879f1af5d2fSBarry Smith         } else {
880f1af5d2fSBarry Smith           continue;
881f1af5d2fSBarry Smith         }
882f1af5d2fSBarry Smith #endif
883b0a32e0cSBarry Smith         ierr = PetscDrawRectangle(draw,x_l,y_l,x_r,y_r,color,color,color,color);CHKERRQ(ierr);
884f1af5d2fSBarry Smith       }
885f1af5d2fSBarry Smith     }
886f1af5d2fSBarry Smith   } else {
887f1af5d2fSBarry Smith     /* use contour shading to indicate magnitude of values */
888f1af5d2fSBarry Smith     /* first determine max of all nonzero values */
889f1af5d2fSBarry Smith     for(i = 0; i < m*n; i++) {
890f1af5d2fSBarry Smith       if (PetscAbsScalar(v[i]) > maxv) maxv = PetscAbsScalar(v[i]);
891f1af5d2fSBarry Smith     }
892b0a32e0cSBarry Smith     scale = (245.0 - PETSC_DRAW_BASIC_COLORS)/maxv;
893b0a32e0cSBarry Smith     ierr  = PetscDrawGetPopup(draw,&popup);CHKERRQ(ierr);
894b0a32e0cSBarry Smith     if (popup) {ierr  = PetscDrawScalePopup(popup,0.0,maxv);CHKERRQ(ierr);}
895f1af5d2fSBarry Smith     for(j = 0; j < n; j++) {
896f1af5d2fSBarry Smith       x_l = j;
897f1af5d2fSBarry Smith       x_r = x_l + 1.0;
898f1af5d2fSBarry Smith       for(i = 0; i < m; i++) {
899f1af5d2fSBarry Smith         y_l   = m - i - 1.0;
900f1af5d2fSBarry Smith         y_r   = y_l + 1.0;
901b0a32e0cSBarry Smith         color = PETSC_DRAW_BASIC_COLORS + (int)(scale*PetscAbsScalar(v[j*m+i]));
902b0a32e0cSBarry Smith         ierr  = PetscDrawRectangle(draw,x_l,y_l,x_r,y_r,color,color,color,color);CHKERRQ(ierr);
903f1af5d2fSBarry Smith       }
904f1af5d2fSBarry Smith     }
905f1af5d2fSBarry Smith   }
906f1af5d2fSBarry Smith   PetscFunctionReturn(0);
907f1af5d2fSBarry Smith }
908f1af5d2fSBarry Smith 
9094a2ae208SSatish Balay #undef __FUNCT__
9104a2ae208SSatish Balay #define __FUNCT__ "MatView_SeqDense_Draw"
911b0a32e0cSBarry Smith int MatView_SeqDense_Draw(Mat A,PetscViewer viewer)
912f1af5d2fSBarry Smith {
913b0a32e0cSBarry Smith   PetscDraw  draw;
914f1af5d2fSBarry Smith   PetscTruth isnull;
915329f5518SBarry Smith   PetscReal  xr,yr,xl,yl,h,w;
916f1af5d2fSBarry Smith   int        ierr;
917f1af5d2fSBarry Smith 
918f1af5d2fSBarry Smith   PetscFunctionBegin;
919b0a32e0cSBarry Smith   ierr = PetscViewerDrawGetDraw(viewer,0,&draw);CHKERRQ(ierr);
920b0a32e0cSBarry Smith   ierr = PetscDrawIsNull(draw,&isnull);CHKERRQ(ierr);
921f1af5d2fSBarry Smith   if (isnull == PETSC_TRUE) PetscFunctionReturn(0);
922f1af5d2fSBarry Smith 
923f1af5d2fSBarry Smith   ierr = PetscObjectCompose((PetscObject)A,"Zoomviewer",(PetscObject)viewer);CHKERRQ(ierr);
924273d9f13SBarry Smith   xr  = A->n; yr = A->m; h = yr/10.0; w = xr/10.0;
925f1af5d2fSBarry Smith   xr += w;    yr += h;  xl = -w;     yl = -h;
926b0a32e0cSBarry Smith   ierr = PetscDrawSetCoordinates(draw,xl,yl,xr,yr);CHKERRQ(ierr);
927b0a32e0cSBarry Smith   ierr = PetscDrawZoom(draw,MatView_SeqDense_Draw_Zoom,A);CHKERRQ(ierr);
928f1af5d2fSBarry Smith   ierr = PetscObjectCompose((PetscObject)A,"Zoomviewer",PETSC_NULL);CHKERRQ(ierr);
929f1af5d2fSBarry Smith   PetscFunctionReturn(0);
930f1af5d2fSBarry Smith }
931f1af5d2fSBarry Smith 
9324a2ae208SSatish Balay #undef __FUNCT__
9334a2ae208SSatish Balay #define __FUNCT__ "MatView_SeqDense"
934b0a32e0cSBarry Smith int MatView_SeqDense(Mat A,PetscViewer viewer)
935932b0c3eSLois Curfman McInnes {
936932b0c3eSLois Curfman McInnes   Mat_SeqDense *a = (Mat_SeqDense*)A->data;
937bcd2baecSBarry Smith   int          ierr;
938f1af5d2fSBarry Smith   PetscTruth   issocket,isascii,isbinary,isdraw;
939932b0c3eSLois Curfman McInnes 
9403a40ed3dSBarry Smith   PetscFunctionBegin;
941b0a32e0cSBarry Smith   ierr = PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_SOCKET,&issocket);CHKERRQ(ierr);
942b0a32e0cSBarry Smith   ierr = PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_ASCII,&isascii);CHKERRQ(ierr);
943fb9695e5SSatish Balay   ierr = PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_BINARY,&isbinary);CHKERRQ(ierr);
944fb9695e5SSatish Balay   ierr = PetscTypeCompare((PetscObject)viewer,PETSC_VIEWER_DRAW,&isdraw);CHKERRQ(ierr);
9450f5bd95cSBarry Smith 
9460f5bd95cSBarry Smith   if (issocket) {
947b0a32e0cSBarry Smith     ierr = PetscViewerSocketPutScalar(viewer,A->m,A->n,a->v);CHKERRQ(ierr);
9480f5bd95cSBarry Smith   } else if (isascii) {
9493a40ed3dSBarry Smith     ierr = MatView_SeqDense_ASCII(A,viewer);CHKERRQ(ierr);
9500f5bd95cSBarry Smith   } else if (isbinary) {
9513a40ed3dSBarry Smith     ierr = MatView_SeqDense_Binary(A,viewer);CHKERRQ(ierr);
952f1af5d2fSBarry Smith   } else if (isdraw) {
953f1af5d2fSBarry Smith     ierr = MatView_SeqDense_Draw(A,viewer);CHKERRQ(ierr);
9545cd90555SBarry Smith   } else {
95529bbc08cSBarry Smith     SETERRQ1(1,"Viewer type %s not supported by dense matrix",((PetscObject)viewer)->type_name);
956932b0c3eSLois Curfman McInnes   }
9573a40ed3dSBarry Smith   PetscFunctionReturn(0);
958932b0c3eSLois Curfman McInnes }
959289bc588SBarry Smith 
9604a2ae208SSatish Balay #undef __FUNCT__
9614a2ae208SSatish Balay #define __FUNCT__ "MatDestroy_SeqDense"
962c6e7dd08SBarry Smith int MatDestroy_SeqDense(Mat mat)
963289bc588SBarry Smith {
964ec8511deSBarry Smith   Mat_SeqDense *l = (Mat_SeqDense*)mat->data;
96590f02eecSBarry Smith   int          ierr;
96690f02eecSBarry Smith 
9673a40ed3dSBarry Smith   PetscFunctionBegin;
968aa482453SBarry Smith #if defined(PETSC_USE_LOG)
969b0a32e0cSBarry Smith   PetscLogObjectState((PetscObject)mat,"Rows %d Cols %d",mat->m,mat->n);
970a5a9c739SBarry Smith #endif
971606d414cSSatish Balay   if (l->pivots) {ierr = PetscFree(l->pivots);CHKERRQ(ierr);}
972606d414cSSatish Balay   if (!l->user_alloc) {ierr = PetscFree(l->v);CHKERRQ(ierr);}
973606d414cSSatish Balay   ierr = PetscFree(l);CHKERRQ(ierr);
9743a40ed3dSBarry Smith   PetscFunctionReturn(0);
975289bc588SBarry Smith }
976289bc588SBarry Smith 
9774a2ae208SSatish Balay #undef __FUNCT__
9784a2ae208SSatish Balay #define __FUNCT__ "MatTranspose_SeqDense"
9798f6be9afSLois Curfman McInnes int MatTranspose_SeqDense(Mat A,Mat *matout)
980289bc588SBarry Smith {
981c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
982549d3d68SSatish Balay   int          k,j,m,n,ierr;
98387828ca2SBarry Smith   PetscScalar  *v,tmp;
98448b35521SBarry Smith 
9853a40ed3dSBarry Smith   PetscFunctionBegin;
986273d9f13SBarry Smith   v = mat->v; m = A->m; n = A->n;
9877c922b88SBarry Smith   if (!matout) { /* in place transpose */
988d64ed03dSBarry Smith     if (m != n) { /* malloc temp to hold transpose */
98987828ca2SBarry Smith       PetscScalar *w;
99087828ca2SBarry Smith       ierr = PetscMalloc((m+1)*(n+1)*sizeof(PetscScalar),&w);CHKERRQ(ierr);
991d64ed03dSBarry Smith       for (j=0; j<m; j++) {
992d64ed03dSBarry Smith         for (k=0; k<n; k++) {
993d64ed03dSBarry Smith           w[k + j*n] = v[j + k*m];
994d64ed03dSBarry Smith         }
995d64ed03dSBarry Smith       }
99687828ca2SBarry Smith       ierr = PetscMemcpy(v,w,m*n*sizeof(PetscScalar));CHKERRQ(ierr);
997606d414cSSatish Balay       ierr = PetscFree(w);CHKERRQ(ierr);
998d64ed03dSBarry Smith     } else {
999d3e5ee88SLois Curfman McInnes       for (j=0; j<m; j++) {
1000289bc588SBarry Smith         for (k=0; k<j; k++) {
1001d3e5ee88SLois Curfman McInnes           tmp = v[j + k*n];
1002d3e5ee88SLois Curfman McInnes           v[j + k*n] = v[k + j*n];
1003d3e5ee88SLois Curfman McInnes           v[k + j*n] = tmp;
1004289bc588SBarry Smith         }
1005289bc588SBarry Smith       }
1006d64ed03dSBarry Smith     }
10073a40ed3dSBarry Smith   } else { /* out-of-place transpose */
1008d3e5ee88SLois Curfman McInnes     Mat          tmat;
1009ec8511deSBarry Smith     Mat_SeqDense *tmatd;
101087828ca2SBarry Smith     PetscScalar  *v2;
1011ea709b57SSatish Balay 
1012273d9f13SBarry Smith     ierr  = MatCreateSeqDense(A->comm,A->n,A->m,PETSC_NULL,&tmat);CHKERRQ(ierr);
1013ec8511deSBarry Smith     tmatd = (Mat_SeqDense*)tmat->data;
10140de55854SLois Curfman McInnes     v = mat->v; v2 = tmatd->v;
1015d3e5ee88SLois Curfman McInnes     for (j=0; j<n; j++) {
10160de55854SLois Curfman McInnes       for (k=0; k<m; k++) v2[j + k*n] = v[k + j*m];
1017d3e5ee88SLois Curfman McInnes     }
10186d4a8577SBarry Smith     ierr = MatAssemblyBegin(tmat,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
10196d4a8577SBarry Smith     ierr = MatAssemblyEnd(tmat,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
1020d3e5ee88SLois Curfman McInnes     *matout = tmat;
102148b35521SBarry Smith   }
10223a40ed3dSBarry Smith   PetscFunctionReturn(0);
1023289bc588SBarry Smith }
1024289bc588SBarry Smith 
10254a2ae208SSatish Balay #undef __FUNCT__
10264a2ae208SSatish Balay #define __FUNCT__ "MatEqual_SeqDense"
10278f6be9afSLois Curfman McInnes int MatEqual_SeqDense(Mat A1,Mat A2,PetscTruth *flg)
1028289bc588SBarry Smith {
1029c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat1 = (Mat_SeqDense*)A1->data;
1030c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat2 = (Mat_SeqDense*)A2->data;
1031273d9f13SBarry Smith   int          ierr,i;
103287828ca2SBarry Smith   PetscScalar  *v1 = mat1->v,*v2 = mat2->v;
1033273d9f13SBarry Smith   PetscTruth   flag;
10349ea5d5aeSSatish Balay 
10353a40ed3dSBarry Smith   PetscFunctionBegin;
1036273d9f13SBarry Smith   ierr = PetscTypeCompare((PetscObject)A2,MATSEQDENSE,&flag);CHKERRQ(ierr);
1037273d9f13SBarry Smith   if (!flag) SETERRQ(PETSC_ERR_SUP,"Matrices should be of type  MATSEQDENSE");
1038273d9f13SBarry Smith   if (A1->m != A2->m) {*flg = PETSC_FALSE; PetscFunctionReturn(0);}
1039273d9f13SBarry Smith   if (A1->n != A2->n) {*flg = PETSC_FALSE; PetscFunctionReturn(0);}
1040273d9f13SBarry Smith   for (i=0; i<A1->m*A1->n; i++) {
10413a40ed3dSBarry Smith     if (*v1 != *v2) {*flg = PETSC_FALSE; PetscFunctionReturn(0);}
1042289bc588SBarry Smith     v1++; v2++;
1043289bc588SBarry Smith   }
104477c4ece6SBarry Smith   *flg = PETSC_TRUE;
10453a40ed3dSBarry Smith   PetscFunctionReturn(0);
1046289bc588SBarry Smith }
1047289bc588SBarry Smith 
10484a2ae208SSatish Balay #undef __FUNCT__
10494a2ae208SSatish Balay #define __FUNCT__ "MatGetDiagonal_SeqDense"
10508f6be9afSLois Curfman McInnes int MatGetDiagonal_SeqDense(Mat A,Vec v)
1051289bc588SBarry Smith {
1052c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
10537a97a34bSBarry Smith   int          ierr,i,n,len;
105487828ca2SBarry Smith   PetscScalar  *x,zero = 0.0;
105544cd7ae7SLois Curfman McInnes 
10563a40ed3dSBarry Smith   PetscFunctionBegin;
10577a97a34bSBarry Smith   ierr = VecSet(&zero,v);CHKERRQ(ierr);
10587a97a34bSBarry Smith   ierr = VecGetSize(v,&n);CHKERRQ(ierr);
1059600d6d0bSBarry Smith   ierr = VecGetArray(v,&x);CHKERRQ(ierr);
1060273d9f13SBarry Smith   len = PetscMin(A->m,A->n);
1061273d9f13SBarry Smith   if (n != A->m) SETERRQ(PETSC_ERR_ARG_SIZ,"Nonconforming mat and vec");
106244cd7ae7SLois Curfman McInnes   for (i=0; i<len; i++) {
1063273d9f13SBarry Smith     x[i] = mat->v[i*A->m + i];
1064289bc588SBarry Smith   }
10657a97a34bSBarry Smith   ierr = VecRestoreArray(v,&x);CHKERRQ(ierr);
10663a40ed3dSBarry Smith   PetscFunctionReturn(0);
1067289bc588SBarry Smith }
1068289bc588SBarry Smith 
10694a2ae208SSatish Balay #undef __FUNCT__
10704a2ae208SSatish Balay #define __FUNCT__ "MatDiagonalScale_SeqDense"
10718f6be9afSLois Curfman McInnes int MatDiagonalScale_SeqDense(Mat A,Vec ll,Vec rr)
1072289bc588SBarry Smith {
1073c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
107487828ca2SBarry Smith   PetscScalar  *l,*r,x,*v;
1075273d9f13SBarry Smith   int          ierr,i,j,m = A->m,n = A->n;
107655659b69SBarry Smith 
10773a40ed3dSBarry Smith   PetscFunctionBegin;
107828988994SBarry Smith   if (ll) {
10797a97a34bSBarry Smith     ierr = VecGetSize(ll,&m);CHKERRQ(ierr);
1080600d6d0bSBarry Smith     ierr = VecGetArray(ll,&l);CHKERRQ(ierr);
1081273d9f13SBarry Smith     if (m != A->m) SETERRQ(PETSC_ERR_ARG_SIZ,"Left scaling vec wrong size");
1082da3a660dSBarry Smith     for (i=0; i<m; i++) {
1083da3a660dSBarry Smith       x = l[i];
1084da3a660dSBarry Smith       v = mat->v + i;
1085da3a660dSBarry Smith       for (j=0; j<n; j++) { (*v) *= x; v+= m;}
1086da3a660dSBarry Smith     }
10877a97a34bSBarry Smith     ierr = VecRestoreArray(ll,&l);CHKERRQ(ierr);
1088b0a32e0cSBarry Smith     PetscLogFlops(n*m);
1089da3a660dSBarry Smith   }
109028988994SBarry Smith   if (rr) {
10917a97a34bSBarry Smith     ierr = VecGetSize(rr,&n);CHKERRQ(ierr);
1092600d6d0bSBarry Smith     ierr = VecGetArray(rr,&r);CHKERRQ(ierr);
1093273d9f13SBarry Smith     if (n != A->n) SETERRQ(PETSC_ERR_ARG_SIZ,"Right scaling vec wrong size");
1094da3a660dSBarry Smith     for (i=0; i<n; i++) {
1095da3a660dSBarry Smith       x = r[i];
1096da3a660dSBarry Smith       v = mat->v + i*m;
1097da3a660dSBarry Smith       for (j=0; j<m; j++) { (*v++) *= x;}
1098da3a660dSBarry Smith     }
10997a97a34bSBarry Smith     ierr = VecRestoreArray(rr,&r);CHKERRQ(ierr);
1100b0a32e0cSBarry Smith     PetscLogFlops(n*m);
1101da3a660dSBarry Smith   }
11023a40ed3dSBarry Smith   PetscFunctionReturn(0);
1103289bc588SBarry Smith }
1104289bc588SBarry Smith 
11054a2ae208SSatish Balay #undef __FUNCT__
11064a2ae208SSatish Balay #define __FUNCT__ "MatNorm_SeqDense"
1107329f5518SBarry Smith int MatNorm_SeqDense(Mat A,NormType type,PetscReal *norm)
1108289bc588SBarry Smith {
1109c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
111087828ca2SBarry Smith   PetscScalar  *v = mat->v;
1111329f5518SBarry Smith   PetscReal    sum = 0.0;
1112289bc588SBarry Smith   int          i,j;
111355659b69SBarry Smith 
11143a40ed3dSBarry Smith   PetscFunctionBegin;
1115289bc588SBarry Smith   if (type == NORM_FROBENIUS) {
1116273d9f13SBarry Smith     for (i=0; i<A->n*A->m; i++) {
1117aa482453SBarry Smith #if defined(PETSC_USE_COMPLEX)
1118329f5518SBarry Smith       sum += PetscRealPart(PetscConj(*v)*(*v)); v++;
1119289bc588SBarry Smith #else
1120289bc588SBarry Smith       sum += (*v)*(*v); v++;
1121289bc588SBarry Smith #endif
1122289bc588SBarry Smith     }
1123289bc588SBarry Smith     *norm = sqrt(sum);
1124b0a32e0cSBarry Smith     PetscLogFlops(2*A->n*A->m);
11253a40ed3dSBarry Smith   } else if (type == NORM_1) {
1126289bc588SBarry Smith     *norm = 0.0;
1127273d9f13SBarry Smith     for (j=0; j<A->n; j++) {
1128289bc588SBarry Smith       sum = 0.0;
1129273d9f13SBarry Smith       for (i=0; i<A->m; i++) {
113033a8263dSBarry Smith         sum += PetscAbsScalar(*v);  v++;
1131289bc588SBarry Smith       }
1132289bc588SBarry Smith       if (sum > *norm) *norm = sum;
1133289bc588SBarry Smith     }
1134b0a32e0cSBarry Smith     PetscLogFlops(A->n*A->m);
11353a40ed3dSBarry Smith   } else if (type == NORM_INFINITY) {
1136289bc588SBarry Smith     *norm = 0.0;
1137273d9f13SBarry Smith     for (j=0; j<A->m; j++) {
1138289bc588SBarry Smith       v = mat->v + j;
1139289bc588SBarry Smith       sum = 0.0;
1140273d9f13SBarry Smith       for (i=0; i<A->n; i++) {
1141273d9f13SBarry Smith         sum += PetscAbsScalar(*v); v += A->m;
1142289bc588SBarry Smith       }
1143289bc588SBarry Smith       if (sum > *norm) *norm = sum;
1144289bc588SBarry Smith     }
1145b0a32e0cSBarry Smith     PetscLogFlops(A->n*A->m);
11463a40ed3dSBarry Smith   } else {
114729bbc08cSBarry Smith     SETERRQ(PETSC_ERR_SUP,"No two norm");
1148289bc588SBarry Smith   }
11493a40ed3dSBarry Smith   PetscFunctionReturn(0);
1150289bc588SBarry Smith }
1151289bc588SBarry Smith 
11524a2ae208SSatish Balay #undef __FUNCT__
11534a2ae208SSatish Balay #define __FUNCT__ "MatSetOption_SeqDense"
11548f6be9afSLois Curfman McInnes int MatSetOption_SeqDense(Mat A,MatOption op)
1155289bc588SBarry Smith {
1156c0bbcb79SLois Curfman McInnes   Mat_SeqDense *aij = (Mat_SeqDense*)A->data;
115767e560aaSBarry Smith 
11583a40ed3dSBarry Smith   PetscFunctionBegin;
1159b5a2b587SKris Buschelman   switch (op) {
1160b5a2b587SKris Buschelman   case MAT_ROW_ORIENTED:
1161b5a2b587SKris Buschelman     aij->roworiented = PETSC_TRUE;
1162b5a2b587SKris Buschelman     break;
1163b5a2b587SKris Buschelman   case MAT_COLUMN_ORIENTED:
1164b5a2b587SKris Buschelman     aij->roworiented = PETSC_FALSE;
1165b5a2b587SKris Buschelman     break;
1166b5a2b587SKris Buschelman   case MAT_ROWS_SORTED:
1167b5a2b587SKris Buschelman   case MAT_ROWS_UNSORTED:
1168b5a2b587SKris Buschelman   case MAT_COLUMNS_SORTED:
1169b5a2b587SKris Buschelman   case MAT_COLUMNS_UNSORTED:
1170b5a2b587SKris Buschelman   case MAT_NO_NEW_NONZERO_LOCATIONS:
1171b5a2b587SKris Buschelman   case MAT_YES_NEW_NONZERO_LOCATIONS:
1172b5a2b587SKris Buschelman   case MAT_NEW_NONZERO_LOCATION_ERR:
1173b5a2b587SKris Buschelman   case MAT_NO_NEW_DIAGONALS:
1174b5a2b587SKris Buschelman   case MAT_YES_NEW_DIAGONALS:
1175b5a2b587SKris Buschelman   case MAT_IGNORE_OFF_PROC_ENTRIES:
1176b5a2b587SKris Buschelman   case MAT_USE_HASH_TABLE:
1177d03495bdSKris Buschelman   case MAT_USE_SINGLE_PRECISION_SOLVES:
1178b0a32e0cSBarry Smith     PetscLogInfo(A,"MatSetOption_SeqDense:Option ignored\n");
1179b5a2b587SKris Buschelman     break;
1180b5a2b587SKris Buschelman   default:
118129bbc08cSBarry Smith     SETERRQ(PETSC_ERR_SUP,"unknown option");
11823a40ed3dSBarry Smith   }
11833a40ed3dSBarry Smith   PetscFunctionReturn(0);
1184289bc588SBarry Smith }
1185289bc588SBarry Smith 
11864a2ae208SSatish Balay #undef __FUNCT__
11874a2ae208SSatish Balay #define __FUNCT__ "MatZeroEntries_SeqDense"
11888f6be9afSLois Curfman McInnes int MatZeroEntries_SeqDense(Mat A)
11896f0a148fSBarry Smith {
1190ec8511deSBarry Smith   Mat_SeqDense *l = (Mat_SeqDense*)A->data;
1191549d3d68SSatish Balay   int          ierr;
11923a40ed3dSBarry Smith 
11933a40ed3dSBarry Smith   PetscFunctionBegin;
119487828ca2SBarry Smith   ierr = PetscMemzero(l->v,A->m*A->n*sizeof(PetscScalar));CHKERRQ(ierr);
11953a40ed3dSBarry Smith   PetscFunctionReturn(0);
11966f0a148fSBarry Smith }
11976f0a148fSBarry Smith 
11984a2ae208SSatish Balay #undef __FUNCT__
11994a2ae208SSatish Balay #define __FUNCT__ "MatGetBlockSize_SeqDense"
12008f6be9afSLois Curfman McInnes int MatGetBlockSize_SeqDense(Mat A,int *bs)
12014e220ebcSLois Curfman McInnes {
12023a40ed3dSBarry Smith   PetscFunctionBegin;
12034e220ebcSLois Curfman McInnes   *bs = 1;
12043a40ed3dSBarry Smith   PetscFunctionReturn(0);
12054e220ebcSLois Curfman McInnes }
12064e220ebcSLois Curfman McInnes 
12074a2ae208SSatish Balay #undef __FUNCT__
12084a2ae208SSatish Balay #define __FUNCT__ "MatZeroRows_SeqDense"
120987828ca2SBarry Smith int MatZeroRows_SeqDense(Mat A,IS is,PetscScalar *diag)
12106f0a148fSBarry Smith {
1211ec8511deSBarry Smith   Mat_SeqDense *l = (Mat_SeqDense*)A->data;
1212273d9f13SBarry Smith   int          n = A->n,i,j,ierr,N,*rows;
121387828ca2SBarry Smith   PetscScalar  *slot;
121455659b69SBarry Smith 
12153a40ed3dSBarry Smith   PetscFunctionBegin;
1216e03a110bSBarry Smith   ierr = ISGetLocalSize(is,&N);CHKERRQ(ierr);
121778b31e54SBarry Smith   ierr = ISGetIndices(is,&rows);CHKERRQ(ierr);
12186f0a148fSBarry Smith   for (i=0; i<N; i++) {
12196f0a148fSBarry Smith     slot = l->v + rows[i];
12206f0a148fSBarry Smith     for (j=0; j<n; j++) { *slot = 0.0; slot += n;}
12216f0a148fSBarry Smith   }
12226f0a148fSBarry Smith   if (diag) {
12236f0a148fSBarry Smith     for (i=0; i<N; i++) {
12246f0a148fSBarry Smith       slot = l->v + (n+1)*rows[i];
1225260925b8SBarry Smith       *slot = *diag;
12266f0a148fSBarry Smith     }
12276f0a148fSBarry Smith   }
1228260925b8SBarry Smith   ISRestoreIndices(is,&rows);
12293a40ed3dSBarry Smith   PetscFunctionReturn(0);
12306f0a148fSBarry Smith }
1231557bce09SLois Curfman McInnes 
12324a2ae208SSatish Balay #undef __FUNCT__
12334a2ae208SSatish Balay #define __FUNCT__ "MatGetOwnershipRange_SeqDense"
12348f6be9afSLois Curfman McInnes int MatGetOwnershipRange_SeqDense(Mat A,int *m,int *n)
1235d3e5ee88SLois Curfman McInnes {
12363a40ed3dSBarry Smith   PetscFunctionBegin;
12374c49b128SBarry Smith   if (m) *m = 0;
1238273d9f13SBarry Smith   if (n) *n = A->m;
12393a40ed3dSBarry Smith   PetscFunctionReturn(0);
1240d3e5ee88SLois Curfman McInnes }
1241d3e5ee88SLois Curfman McInnes 
12424a2ae208SSatish Balay #undef __FUNCT__
12434a2ae208SSatish Balay #define __FUNCT__ "MatGetArray_SeqDense"
124487828ca2SBarry Smith int MatGetArray_SeqDense(Mat A,PetscScalar **array)
124564e87e97SBarry Smith {
1246c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
12473a40ed3dSBarry Smith 
12483a40ed3dSBarry Smith   PetscFunctionBegin;
124964e87e97SBarry Smith   *array = mat->v;
12503a40ed3dSBarry Smith   PetscFunctionReturn(0);
125164e87e97SBarry Smith }
12520754003eSLois Curfman McInnes 
12534a2ae208SSatish Balay #undef __FUNCT__
12544a2ae208SSatish Balay #define __FUNCT__ "MatRestoreArray_SeqDense"
125587828ca2SBarry Smith int MatRestoreArray_SeqDense(Mat A,PetscScalar **array)
1256ff14e315SSatish Balay {
12573a40ed3dSBarry Smith   PetscFunctionBegin;
125809b544d4SBarry Smith   *array = 0; /* user cannot accidently use the array later */
12593a40ed3dSBarry Smith   PetscFunctionReturn(0);
1260ff14e315SSatish Balay }
12610754003eSLois Curfman McInnes 
12624a2ae208SSatish Balay #undef __FUNCT__
12634a2ae208SSatish Balay #define __FUNCT__ "MatGetSubMatrix_SeqDense"
12647b2a1423SBarry Smith static int MatGetSubMatrix_SeqDense(Mat A,IS isrow,IS iscol,int cs,MatReuse scall,Mat *B)
12650754003eSLois Curfman McInnes {
1266c0bbcb79SLois Curfman McInnes   Mat_SeqDense *mat = (Mat_SeqDense*)A->data;
1267273d9f13SBarry Smith   int          i,j,ierr,m = A->m,*irow,*icol,nrows,ncols;
126887828ca2SBarry Smith   PetscScalar  *av,*bv,*v = mat->v;
12690754003eSLois Curfman McInnes   Mat          newmat;
12700754003eSLois Curfman McInnes 
12713a40ed3dSBarry Smith   PetscFunctionBegin;
127278b31e54SBarry Smith   ierr = ISGetIndices(isrow,&irow);CHKERRQ(ierr);
127378b31e54SBarry Smith   ierr = ISGetIndices(iscol,&icol);CHKERRQ(ierr);
1274e03a110bSBarry Smith   ierr = ISGetLocalSize(isrow,&nrows);CHKERRQ(ierr);
1275e03a110bSBarry Smith   ierr = ISGetLocalSize(iscol,&ncols);CHKERRQ(ierr);
12760754003eSLois Curfman McInnes 
1277182d2002SSatish Balay   /* Check submatrixcall */
1278182d2002SSatish Balay   if (scall == MAT_REUSE_MATRIX) {
1279182d2002SSatish Balay     int n_cols,n_rows;
1280182d2002SSatish Balay     ierr = MatGetSize(*B,&n_rows,&n_cols);CHKERRQ(ierr);
128129bbc08cSBarry Smith     if (n_rows != nrows || n_cols != ncols) SETERRQ(PETSC_ERR_ARG_SIZ,"Reused submatrix wrong size");
1282182d2002SSatish Balay     newmat = *B;
1283182d2002SSatish Balay   } else {
12840754003eSLois Curfman McInnes     /* Create and fill new matrix */
1285b4fd4287SBarry Smith     ierr = MatCreateSeqDense(A->comm,nrows,ncols,PETSC_NULL,&newmat);CHKERRQ(ierr);
1286182d2002SSatish Balay   }
1287182d2002SSatish Balay 
1288182d2002SSatish Balay   /* Now extract the data pointers and do the copy,column at a time */
1289182d2002SSatish Balay   bv = ((Mat_SeqDense*)newmat->data)->v;
1290182d2002SSatish Balay 
1291182d2002SSatish Balay   for (i=0; i<ncols; i++) {
1292182d2002SSatish Balay     av = v + m*icol[i];
1293182d2002SSatish Balay     for (j=0; j<nrows; j++) {
1294182d2002SSatish Balay       *bv++ = av[irow[j]];
12950754003eSLois Curfman McInnes     }
12960754003eSLois Curfman McInnes   }
1297182d2002SSatish Balay 
1298182d2002SSatish Balay   /* Assemble the matrices so that the correct flags are set */
12996d4a8577SBarry Smith   ierr = MatAssemblyBegin(newmat,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
13006d4a8577SBarry Smith   ierr = MatAssemblyEnd(newmat,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr);
13010754003eSLois Curfman McInnes 
13020754003eSLois Curfman McInnes   /* Free work space */
130378b31e54SBarry Smith   ierr = ISRestoreIndices(isrow,&irow);CHKERRQ(ierr);
130478b31e54SBarry Smith   ierr = ISRestoreIndices(iscol,&icol);CHKERRQ(ierr);
1305182d2002SSatish Balay   *B = newmat;
13063a40ed3dSBarry Smith   PetscFunctionReturn(0);
13070754003eSLois Curfman McInnes }
13080754003eSLois Curfman McInnes 
13094a2ae208SSatish Balay #undef __FUNCT__
13104a2ae208SSatish Balay #define __FUNCT__ "MatGetSubMatrices_SeqDense"
13117b2a1423SBarry Smith int MatGetSubMatrices_SeqDense(Mat A,int n,IS *irow,IS *icol,MatReuse scall,Mat **B)
1312905e6a2fSBarry Smith {
1313905e6a2fSBarry Smith   int ierr,i;
1314905e6a2fSBarry Smith 
13153a40ed3dSBarry Smith   PetscFunctionBegin;
1316905e6a2fSBarry Smith   if (scall == MAT_INITIAL_MATRIX) {
1317b0a32e0cSBarry Smith     ierr = PetscMalloc((n+1)*sizeof(Mat),B);CHKERRQ(ierr);
1318905e6a2fSBarry Smith   }
1319905e6a2fSBarry Smith 
1320905e6a2fSBarry Smith   for (i=0; i<n; i++) {
13216a6a5d1dSBarry Smith     ierr = MatGetSubMatrix_SeqDense(A,irow[i],icol[i],PETSC_DECIDE,scall,&(*B)[i]);CHKERRQ(ierr);
1322905e6a2fSBarry Smith   }
13233a40ed3dSBarry Smith   PetscFunctionReturn(0);
1324905e6a2fSBarry Smith }
1325905e6a2fSBarry Smith 
13264a2ae208SSatish Balay #undef __FUNCT__
13274a2ae208SSatish Balay #define __FUNCT__ "MatCopy_SeqDense"
1328cb5b572fSBarry Smith int MatCopy_SeqDense(Mat A,Mat B,MatStructure str)
13294b0e389bSBarry Smith {
13304b0e389bSBarry Smith   Mat_SeqDense *a = (Mat_SeqDense*)A->data,*b = (Mat_SeqDense *)B->data;
13313a40ed3dSBarry Smith   int          ierr;
1332273d9f13SBarry Smith   PetscTruth   flag;
13333a40ed3dSBarry Smith 
13343a40ed3dSBarry Smith   PetscFunctionBegin;
1335273d9f13SBarry Smith   ierr = PetscTypeCompare((PetscObject)B,MATSEQDENSE,&flag);CHKERRQ(ierr);
1336273d9f13SBarry Smith   if (!flag) {
1337cb5b572fSBarry Smith     ierr = MatCopy_Basic(A,B,str);CHKERRQ(ierr);
13383a40ed3dSBarry Smith     PetscFunctionReturn(0);
13393a40ed3dSBarry Smith   }
1340273d9f13SBarry Smith   if (A->m != B->m || A->n != B->n) SETERRQ(PETSC_ERR_ARG_SIZ,"size(B) != size(A)");
134187828ca2SBarry Smith   ierr = PetscMemcpy(b->v,a->v,A->m*A->n*sizeof(PetscScalar));CHKERRQ(ierr);
1342273d9f13SBarry Smith   PetscFunctionReturn(0);
1343273d9f13SBarry Smith }
1344273d9f13SBarry Smith 
13454a2ae208SSatish Balay #undef __FUNCT__
13464a2ae208SSatish Balay #define __FUNCT__ "MatSetUpPreallocation_SeqDense"
1347273d9f13SBarry Smith int MatSetUpPreallocation_SeqDense(Mat A)
1348273d9f13SBarry Smith {
1349273d9f13SBarry Smith   int        ierr;
1350273d9f13SBarry Smith 
1351273d9f13SBarry Smith   PetscFunctionBegin;
1352273d9f13SBarry Smith   ierr =  MatSeqDenseSetPreallocation(A,0);CHKERRQ(ierr);
13533a40ed3dSBarry Smith   PetscFunctionReturn(0);
13544b0e389bSBarry Smith }
13554b0e389bSBarry Smith 
1356289bc588SBarry Smith /* -------------------------------------------------------------------*/
1357a5ae1ecdSBarry Smith static struct _MatOps MatOps_Values = {MatSetValues_SeqDense,
1358905e6a2fSBarry Smith        MatGetRow_SeqDense,
1359905e6a2fSBarry Smith        MatRestoreRow_SeqDense,
1360905e6a2fSBarry Smith        MatMult_SeqDense,
1361905e6a2fSBarry Smith        MatMultAdd_SeqDense,
13627c922b88SBarry Smith        MatMultTranspose_SeqDense,
13637c922b88SBarry Smith        MatMultTransposeAdd_SeqDense,
1364905e6a2fSBarry Smith        MatSolve_SeqDense,
1365905e6a2fSBarry Smith        MatSolveAdd_SeqDense,
13667c922b88SBarry Smith        MatSolveTranspose_SeqDense,
13677c922b88SBarry Smith        MatSolveTransposeAdd_SeqDense,
1368905e6a2fSBarry Smith        MatLUFactor_SeqDense,
1369905e6a2fSBarry Smith        MatCholeskyFactor_SeqDense,
1370ec8511deSBarry Smith        MatRelax_SeqDense,
1371ec8511deSBarry Smith        MatTranspose_SeqDense,
1372905e6a2fSBarry Smith        MatGetInfo_SeqDense,
1373905e6a2fSBarry Smith        MatEqual_SeqDense,
1374905e6a2fSBarry Smith        MatGetDiagonal_SeqDense,
1375905e6a2fSBarry Smith        MatDiagonalScale_SeqDense,
1376905e6a2fSBarry Smith        MatNorm_SeqDense,
1377905e6a2fSBarry Smith        0,
1378905e6a2fSBarry Smith        0,
1379905e6a2fSBarry Smith        0,
1380905e6a2fSBarry Smith        MatSetOption_SeqDense,
1381905e6a2fSBarry Smith        MatZeroEntries_SeqDense,
1382905e6a2fSBarry Smith        MatZeroRows_SeqDense,
1383905e6a2fSBarry Smith        MatLUFactorSymbolic_SeqDense,
1384905e6a2fSBarry Smith        MatLUFactorNumeric_SeqDense,
1385905e6a2fSBarry Smith        MatCholeskyFactorSymbolic_SeqDense,
1386905e6a2fSBarry Smith        MatCholeskyFactorNumeric_SeqDense,
1387273d9f13SBarry Smith        MatSetUpPreallocation_SeqDense,
1388273d9f13SBarry Smith        0,
1389905e6a2fSBarry Smith        MatGetOwnershipRange_SeqDense,
1390905e6a2fSBarry Smith        0,
1391905e6a2fSBarry Smith        0,
1392905e6a2fSBarry Smith        MatGetArray_SeqDense,
1393905e6a2fSBarry Smith        MatRestoreArray_SeqDense,
13945609ef8eSBarry Smith        MatDuplicate_SeqDense,
1395a5ae1ecdSBarry Smith        0,
1396a5ae1ecdSBarry Smith        0,
1397a5ae1ecdSBarry Smith        0,
1398a5ae1ecdSBarry Smith        0,
1399a5ae1ecdSBarry Smith        MatAXPY_SeqDense,
1400a5ae1ecdSBarry Smith        MatGetSubMatrices_SeqDense,
1401a5ae1ecdSBarry Smith        0,
14024b0e389bSBarry Smith        MatGetValues_SeqDense,
1403a5ae1ecdSBarry Smith        MatCopy_SeqDense,
1404a5ae1ecdSBarry Smith        0,
1405a5ae1ecdSBarry Smith        MatScale_SeqDense,
1406a5ae1ecdSBarry Smith        0,
1407a5ae1ecdSBarry Smith        0,
1408a5ae1ecdSBarry Smith        0,
1409a5ae1ecdSBarry Smith        MatGetBlockSize_SeqDense,
1410a5ae1ecdSBarry Smith        0,
1411a5ae1ecdSBarry Smith        0,
1412a5ae1ecdSBarry Smith        0,
1413a5ae1ecdSBarry Smith        0,
1414a5ae1ecdSBarry Smith        0,
1415a5ae1ecdSBarry Smith        0,
1416a5ae1ecdSBarry Smith        0,
1417a5ae1ecdSBarry Smith        0,
1418a5ae1ecdSBarry Smith        0,
1419a5ae1ecdSBarry Smith        0,
1420e03a110bSBarry Smith        MatDestroy_SeqDense,
1421e03a110bSBarry Smith        MatView_SeqDense,
14228a124369SBarry Smith        MatGetPetscMaps_Petsc};
142390ace30eSBarry Smith 
14244a2ae208SSatish Balay #undef __FUNCT__
14254a2ae208SSatish Balay #define __FUNCT__ "MatCreateSeqDense"
14264b828684SBarry Smith /*@C
1427fafbff53SBarry Smith    MatCreateSeqDense - Creates a sequential dense matrix that
1428d65003e9SLois Curfman McInnes    is stored in column major order (the usual Fortran 77 manner). Many
1429d65003e9SLois Curfman McInnes    of the matrix operations use the BLAS and LAPACK routines.
1430289bc588SBarry Smith 
1431db81eaa0SLois Curfman McInnes    Collective on MPI_Comm
1432db81eaa0SLois Curfman McInnes 
143320563c6bSBarry Smith    Input Parameters:
1434db81eaa0SLois Curfman McInnes +  comm - MPI communicator, set to PETSC_COMM_SELF
14350c775827SLois Curfman McInnes .  m - number of rows
143618f449edSLois Curfman McInnes .  n - number of columns
1437db81eaa0SLois Curfman McInnes -  data - optional location of matrix data.  Set data=PETSC_NULL for PETSc
1438dfc5480cSLois Curfman McInnes    to control all matrix memory allocation.
143920563c6bSBarry Smith 
144020563c6bSBarry Smith    Output Parameter:
144144cd7ae7SLois Curfman McInnes .  A - the matrix
144220563c6bSBarry Smith 
1443b259b22eSLois Curfman McInnes    Notes:
144418f449edSLois Curfman McInnes    The data input variable is intended primarily for Fortran programmers
144518f449edSLois Curfman McInnes    who wish to allocate their own matrix memory space.  Most users should
1446b4fd4287SBarry Smith    set data=PETSC_NULL.
144718f449edSLois Curfman McInnes 
1448027ccd11SLois Curfman McInnes    Level: intermediate
1449027ccd11SLois Curfman McInnes 
1450dbd7a890SLois Curfman McInnes .keywords: dense, matrix, LAPACK, BLAS
1451d65003e9SLois Curfman McInnes 
1452db81eaa0SLois Curfman McInnes .seealso: MatCreate(), MatCreateMPIDense(), MatSetValues()
145320563c6bSBarry Smith @*/
145487828ca2SBarry Smith int MatCreateSeqDense(MPI_Comm comm,int m,int n,PetscScalar *data,Mat *A)
1455289bc588SBarry Smith {
1456273d9f13SBarry Smith   int ierr;
14573b2fbd54SBarry Smith 
14583a40ed3dSBarry Smith   PetscFunctionBegin;
1459273d9f13SBarry Smith   ierr = MatCreate(comm,m,n,m,n,A);CHKERRQ(ierr);
1460273d9f13SBarry Smith   ierr = MatSetType(*A,MATSEQDENSE);CHKERRQ(ierr);
1461273d9f13SBarry Smith   ierr = MatSeqDenseSetPreallocation(*A,data);CHKERRQ(ierr);
1462273d9f13SBarry Smith   PetscFunctionReturn(0);
1463273d9f13SBarry Smith }
1464273d9f13SBarry Smith 
14654a2ae208SSatish Balay #undef __FUNCT__
14664a2ae208SSatish Balay #define __FUNCT__ "MatSeqDensePreallocation"
1467273d9f13SBarry Smith /*@C
1468273d9f13SBarry Smith    MatSeqDenseSetPreallocation - Sets the array used for storing the matrix elements
1469273d9f13SBarry Smith 
1470273d9f13SBarry Smith    Collective on MPI_Comm
1471273d9f13SBarry Smith 
1472273d9f13SBarry Smith    Input Parameters:
1473273d9f13SBarry Smith +  A - the matrix
1474273d9f13SBarry Smith -  data - the array (or PETSC_NULL)
1475273d9f13SBarry Smith 
1476273d9f13SBarry Smith    Notes:
1477273d9f13SBarry Smith    The data input variable is intended primarily for Fortran programmers
1478273d9f13SBarry Smith    who wish to allocate their own matrix memory space.  Most users should
1479273d9f13SBarry Smith    set data=PETSC_NULL.
1480273d9f13SBarry Smith 
1481273d9f13SBarry Smith    Level: intermediate
1482273d9f13SBarry Smith 
1483273d9f13SBarry Smith .keywords: dense, matrix, LAPACK, BLAS
1484273d9f13SBarry Smith 
1485273d9f13SBarry Smith .seealso: MatCreate(), MatCreateMPIDense(), MatSetValues()
1486273d9f13SBarry Smith @*/
148787828ca2SBarry Smith int MatSeqDenseSetPreallocation(Mat B,PetscScalar *data)
1488273d9f13SBarry Smith {
1489273d9f13SBarry Smith   Mat_SeqDense *b;
1490273d9f13SBarry Smith   int          ierr;
1491273d9f13SBarry Smith   PetscTruth   flg2;
1492273d9f13SBarry Smith 
1493273d9f13SBarry Smith   PetscFunctionBegin;
1494273d9f13SBarry Smith   ierr = PetscTypeCompare((PetscObject)B,MATSEQDENSE,&flg2);CHKERRQ(ierr);
1495273d9f13SBarry Smith   if (!flg2) PetscFunctionReturn(0);
1496273d9f13SBarry Smith   B->preallocated = PETSC_TRUE;
1497273d9f13SBarry Smith   b               = (Mat_SeqDense*)B->data;
1498273d9f13SBarry Smith   if (!data) {
149987828ca2SBarry Smith     ierr          = PetscMalloc((B->m*B->n+1)*sizeof(PetscScalar),&b->v);CHKERRQ(ierr);
150087828ca2SBarry Smith     ierr          = PetscMemzero(b->v,B->m*B->n*sizeof(PetscScalar));CHKERRQ(ierr);
1501273d9f13SBarry Smith     b->user_alloc = PETSC_FALSE;
150287828ca2SBarry Smith     PetscLogObjectMemory(B,B->n*B->m*sizeof(PetscScalar));
1503273d9f13SBarry Smith   } else { /* user-allocated storage */
1504273d9f13SBarry Smith     b->v          = data;
1505273d9f13SBarry Smith     b->user_alloc = PETSC_TRUE;
1506273d9f13SBarry Smith   }
1507273d9f13SBarry Smith   PetscFunctionReturn(0);
1508273d9f13SBarry Smith }
1509273d9f13SBarry Smith 
1510273d9f13SBarry Smith EXTERN_C_BEGIN
15114a2ae208SSatish Balay #undef __FUNCT__
15124a2ae208SSatish Balay #define __FUNCT__ "MatCreate_SeqDense"
1513273d9f13SBarry Smith int MatCreate_SeqDense(Mat B)
1514273d9f13SBarry Smith {
1515273d9f13SBarry Smith   Mat_SeqDense *b;
1516273d9f13SBarry Smith   int          ierr,size;
1517273d9f13SBarry Smith 
1518273d9f13SBarry Smith   PetscFunctionBegin;
1519273d9f13SBarry Smith   ierr = MPI_Comm_size(B->comm,&size);CHKERRQ(ierr);
152029bbc08cSBarry Smith   if (size > 1) SETERRQ(PETSC_ERR_ARG_WRONG,"Comm must be of size 1");
152155659b69SBarry Smith 
1522273d9f13SBarry Smith   B->m = B->M = PetscMax(B->m,B->M);
1523273d9f13SBarry Smith   B->n = B->N = PetscMax(B->n,B->N);
1524273d9f13SBarry Smith 
1525b0a32e0cSBarry Smith   ierr            = PetscNew(Mat_SeqDense,&b);CHKERRQ(ierr);
1526549d3d68SSatish Balay   ierr            = PetscMemzero(b,sizeof(Mat_SeqDense));CHKERRQ(ierr);
1527549d3d68SSatish Balay   ierr            = PetscMemcpy(B->ops,&MatOps_Values,sizeof(struct _MatOps));CHKERRQ(ierr);
152844cd7ae7SLois Curfman McInnes   B->factor       = 0;
152990f02eecSBarry Smith   B->mapping      = 0;
1530b0a32e0cSBarry Smith   PetscLogObjectMemory(B,sizeof(struct _p_Mat));
153144cd7ae7SLois Curfman McInnes   B->data         = (void*)b;
153218f449edSLois Curfman McInnes 
15338a124369SBarry Smith   ierr = PetscMapCreateMPI(B->comm,B->m,B->m,&B->rmap);CHKERRQ(ierr);
15348a124369SBarry Smith   ierr = PetscMapCreateMPI(B->comm,B->n,B->n,&B->cmap);CHKERRQ(ierr);
1535a5ae1ecdSBarry Smith 
153644cd7ae7SLois Curfman McInnes   b->pivots       = 0;
1537273d9f13SBarry Smith   b->roworiented  = PETSC_TRUE;
1538273d9f13SBarry Smith   b->v            = 0;
15394e220ebcSLois Curfman McInnes 
15403a40ed3dSBarry Smith   PetscFunctionReturn(0);
1541289bc588SBarry Smith }
1542273d9f13SBarry Smith EXTERN_C_END
15433b2fbd54SBarry Smith 
15443b2fbd54SBarry Smith 
15453b2fbd54SBarry Smith 
15463b2fbd54SBarry Smith 
1547