1 2 /* 3 This is where the abstract matrix operations are defined 4 */ 5 6 #include <petsc-private/matimpl.h> /*I "petscmat.h" I*/ 7 #include <petsc-private/vecimpl.h> 8 9 /* Logging support */ 10 PetscClassId MAT_CLASSID; 11 PetscClassId MAT_FDCOLORING_CLASSID; 12 PetscClassId MAT_TRANSPOSECOLORING_CLASSID; 13 14 PetscLogEvent MAT_Mult, MAT_Mults, MAT_MultConstrained, MAT_MultAdd, MAT_MultTranspose; 15 PetscLogEvent MAT_MultTransposeConstrained, MAT_MultTransposeAdd, MAT_Solve, MAT_Solves, MAT_SolveAdd, MAT_SolveTranspose, MAT_MatSolve; 16 PetscLogEvent MAT_SolveTransposeAdd, MAT_SOR, MAT_ForwardSolve, MAT_BackwardSolve, MAT_LUFactor, MAT_LUFactorSymbolic; 17 PetscLogEvent MAT_LUFactorNumeric, MAT_CholeskyFactor, MAT_CholeskyFactorSymbolic, MAT_CholeskyFactorNumeric, MAT_ILUFactor; 18 PetscLogEvent MAT_ILUFactorSymbolic, MAT_ICCFactorSymbolic, MAT_Copy, MAT_Convert, MAT_Scale, MAT_AssemblyBegin; 19 PetscLogEvent MAT_AssemblyEnd, MAT_SetValues, MAT_GetValues, MAT_GetRow, MAT_GetRowIJ, MAT_GetSubMatrices, MAT_GetColoring, MAT_GetOrdering, MAT_GetRedundantMatrix, MAT_GetSeqNonzeroStructure; 20 PetscLogEvent MAT_IncreaseOverlap, MAT_Partitioning, MAT_Coarsen, MAT_ZeroEntries, MAT_Load, MAT_View, MAT_AXPY, MAT_FDColoringCreate; 21 PetscLogEvent MAT_FDColoringApply,MAT_Transpose,MAT_FDColoringFunction; 22 PetscLogEvent MAT_TransposeColoringCreate; 23 PetscLogEvent MAT_MatMult, MAT_MatMultSymbolic, MAT_MatMultNumeric; 24 PetscLogEvent MAT_PtAP, MAT_PtAPSymbolic, MAT_PtAPNumeric,MAT_RARt, MAT_RARtSymbolic, MAT_RARtNumeric; 25 PetscLogEvent MAT_MatTransposeMult, MAT_MatTransposeMultSymbolic, MAT_MatTransposeMultNumeric; 26 PetscLogEvent MAT_TransposeMatMult, MAT_TransposeMatMultSymbolic, MAT_TransposeMatMultNumeric; 27 PetscLogEvent MAT_MatMatMult, MAT_MatMatMultSymbolic, MAT_MatMatMultNumeric; 28 PetscLogEvent MAT_MultHermitianTranspose,MAT_MultHermitianTransposeAdd; 29 PetscLogEvent MAT_Getsymtranspose, MAT_Getsymtransreduced, MAT_Transpose_SeqAIJ, MAT_GetBrowsOfAcols; 30 PetscLogEvent MAT_GetBrowsOfAocols, MAT_Getlocalmat, MAT_Getlocalmatcondensed, MAT_Seqstompi, MAT_Seqstompinum, MAT_Seqstompisym; 31 PetscLogEvent MAT_Applypapt, MAT_Applypapt_numeric, MAT_Applypapt_symbolic, MAT_GetSequentialNonzeroStructure; 32 PetscLogEvent MAT_GetMultiProcBlock; 33 PetscLogEvent MAT_CUSPCopyToGPU, MAT_CUSPARSECopyToGPU, MAT_SetValuesBatch, MAT_SetValuesBatchI, MAT_SetValuesBatchII, MAT_SetValuesBatchIII, MAT_SetValuesBatchIV; 34 PetscLogEvent MAT_Merge; 35 36 const char *const MatFactorTypes[] = {"NONE","LU","CHOLESKY","ILU","ICC","ILUDT","MatFactorType","MAT_FACTOR_",0}; 37 38 #undef __FUNCT__ 39 #define __FUNCT__ "MatSetRandom" 40 /*@ 41 MatSetRandom - Sets all components of a matrix to random numbers. For sparse matrices that have been preallocated it randomly selects appropriate locations 42 43 Logically Collective on Vec 44 45 Input Parameters: 46 + x - the vector 47 - rctx - the random number context, formed by PetscRandomCreate(), or NULL and 48 it will create one internally. 49 50 Output Parameter: 51 . x - the vector 52 53 Example of Usage: 54 .vb 55 PetscRandomCreate(PETSC_COMM_WORLD,&rctx); 56 VecSetRandom(x,rctx); 57 PetscRandomDestroy(rctx); 58 .ve 59 60 Level: intermediate 61 62 Concepts: vector^setting to random 63 Concepts: random^vector 64 65 .seealso: MatZeroEntries(), MatSetValues(), PetscRandomCreate(), PetscRandomDestroy() 66 @*/ 67 PetscErrorCode MatSetRandom(Mat x,PetscRandom rctx) 68 { 69 PetscErrorCode ierr; 70 PetscRandom randObj = NULL; 71 72 PetscFunctionBegin; 73 PetscValidHeaderSpecific(x,MAT_CLASSID,1); 74 if (rctx) PetscValidHeaderSpecific(rctx,PETSC_RANDOM_CLASSID,2); 75 PetscValidType(x,1); 76 77 if (!rctx) { 78 MPI_Comm comm; 79 ierr = PetscObjectGetComm((PetscObject)x,&comm);CHKERRQ(ierr); 80 ierr = PetscRandomCreate(comm,&randObj);CHKERRQ(ierr); 81 ierr = PetscRandomSetFromOptions(randObj);CHKERRQ(ierr); 82 rctx = randObj; 83 } 84 85 ierr = PetscLogEventBegin(VEC_SetRandom,x,rctx,0,0);CHKERRQ(ierr); 86 ierr = (*x->ops->setrandom)(x,rctx);CHKERRQ(ierr); 87 ierr = PetscLogEventEnd(VEC_SetRandom,x,rctx,0,0);CHKERRQ(ierr); 88 89 x->assembled = PETSC_TRUE; 90 ierr = PetscRandomDestroy(&randObj);CHKERRQ(ierr); 91 PetscFunctionReturn(0); 92 } 93 94 95 #undef __FUNCT__ 96 #define __FUNCT__ "MatFindNonzeroRows" 97 /*@ 98 MatFindNonzeroRows - Locate all rows that are not completely zero in the matrix 99 100 Input Parameter: 101 . A - the matrix 102 103 Output Parameter: 104 . keptrows - the rows that are not completely zero 105 106 Level: intermediate 107 108 @*/ 109 PetscErrorCode MatFindNonzeroRows(Mat mat,IS *keptrows) 110 { 111 PetscErrorCode ierr; 112 113 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 114 PetscValidType(mat,1); 115 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 116 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 117 if (!mat->ops->findnonzerorows) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Not coded for this matrix type"); 118 ierr = (*mat->ops->findnonzerorows)(mat,keptrows);CHKERRQ(ierr); 119 PetscFunctionReturn(0); 120 } 121 122 #undef __FUNCT__ 123 #define __FUNCT__ "MatGetDiagonalBlock" 124 /*@ 125 MatGetDiagonalBlock - Returns the part of the matrix associated with the on-process coupling 126 127 Not Collective 128 129 Input Parameters: 130 . A - the matrix 131 132 Output Parameters: 133 . a - the diagonal part (which is a SEQUENTIAL matrix) 134 135 Notes: see the manual page for MatCreateAIJ() for more information on the "diagonal part" of the matrix. 136 137 Level: advanced 138 139 @*/ 140 PetscErrorCode MatGetDiagonalBlock(Mat A,Mat *a) 141 { 142 PetscErrorCode ierr,(*f)(Mat,Mat*); 143 PetscMPIInt size; 144 145 PetscFunctionBegin; 146 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 147 PetscValidType(A,1); 148 PetscValidPointer(a,3); 149 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 150 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 151 ierr = MPI_Comm_size(PetscObjectComm((PetscObject)A),&size);CHKERRQ(ierr); 152 ierr = PetscObjectQueryFunction((PetscObject)A,"MatGetDiagonalBlock_C",(void (**)(void))&f);CHKERRQ(ierr); 153 if (f) { 154 ierr = (*f)(A,a);CHKERRQ(ierr); 155 PetscFunctionReturn(0); 156 } else if (size == 1) { 157 *a = A; 158 } else { 159 MatType mattype; 160 ierr = MatGetType(A,&mattype);CHKERRQ(ierr); 161 SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"Matrix type %s does not support getting diagonal block",mattype); 162 } 163 PetscFunctionReturn(0); 164 } 165 166 #undef __FUNCT__ 167 #define __FUNCT__ "MatGetTrace" 168 /*@ 169 MatGetTrace - Gets the trace of a matrix. The sum of the diagonal entries. 170 171 Collective on Mat 172 173 Input Parameters: 174 . mat - the matrix 175 176 Output Parameter: 177 . trace - the sum of the diagonal entries 178 179 Level: advanced 180 181 @*/ 182 PetscErrorCode MatGetTrace(Mat mat,PetscScalar *trace) 183 { 184 PetscErrorCode ierr; 185 Vec diag; 186 187 PetscFunctionBegin; 188 ierr = MatGetVecs(mat,&diag,NULL);CHKERRQ(ierr); 189 ierr = MatGetDiagonal(mat,diag);CHKERRQ(ierr); 190 ierr = VecSum(diag,trace);CHKERRQ(ierr); 191 ierr = VecDestroy(&diag);CHKERRQ(ierr); 192 PetscFunctionReturn(0); 193 } 194 195 #undef __FUNCT__ 196 #define __FUNCT__ "MatRealPart" 197 /*@ 198 MatRealPart - Zeros out the imaginary part of the matrix 199 200 Logically Collective on Mat 201 202 Input Parameters: 203 . mat - the matrix 204 205 Level: advanced 206 207 208 .seealso: MatImaginaryPart() 209 @*/ 210 PetscErrorCode MatRealPart(Mat mat) 211 { 212 PetscErrorCode ierr; 213 214 PetscFunctionBegin; 215 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 216 PetscValidType(mat,1); 217 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 218 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 219 if (!mat->ops->realpart) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 220 MatCheckPreallocated(mat,1); 221 ierr = (*mat->ops->realpart)(mat);CHKERRQ(ierr); 222 #if defined(PETSC_HAVE_CUSP) 223 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 224 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 225 } 226 #endif 227 PetscFunctionReturn(0); 228 } 229 230 #undef __FUNCT__ 231 #define __FUNCT__ "MatGetGhosts" 232 /*@C 233 MatGetGhosts - Get the global index of all ghost nodes defined by the sparse matrix 234 235 Collective on Mat 236 237 Input Parameter: 238 . mat - the matrix 239 240 Output Parameters: 241 + nghosts - number of ghosts (note for BAIJ matrices there is one ghost for each block) 242 - ghosts - the global indices of the ghost points 243 244 Notes: the nghosts and ghosts are suitable to pass into VecCreateGhost() 245 246 Level: advanced 247 248 @*/ 249 PetscErrorCode MatGetGhosts(Mat mat,PetscInt *nghosts,const PetscInt *ghosts[]) 250 { 251 PetscErrorCode ierr; 252 253 PetscFunctionBegin; 254 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 255 PetscValidType(mat,1); 256 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 257 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 258 if (!mat->ops->getghosts) { 259 if (nghosts) *nghosts = 0; 260 if (ghosts) *ghosts = 0; 261 } else { 262 ierr = (*mat->ops->getghosts)(mat,nghosts,ghosts);CHKERRQ(ierr); 263 } 264 PetscFunctionReturn(0); 265 } 266 267 268 #undef __FUNCT__ 269 #define __FUNCT__ "MatImaginaryPart" 270 /*@ 271 MatImaginaryPart - Moves the imaginary part of the matrix to the real part and zeros the imaginary part 272 273 Logically Collective on Mat 274 275 Input Parameters: 276 . mat - the matrix 277 278 Level: advanced 279 280 281 .seealso: MatRealPart() 282 @*/ 283 PetscErrorCode MatImaginaryPart(Mat mat) 284 { 285 PetscErrorCode ierr; 286 287 PetscFunctionBegin; 288 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 289 PetscValidType(mat,1); 290 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 291 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 292 if (!mat->ops->imaginarypart) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 293 MatCheckPreallocated(mat,1); 294 ierr = (*mat->ops->imaginarypart)(mat);CHKERRQ(ierr); 295 #if defined(PETSC_HAVE_CUSP) 296 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 297 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 298 } 299 #endif 300 PetscFunctionReturn(0); 301 } 302 303 #undef __FUNCT__ 304 #define __FUNCT__ "MatMissingDiagonal" 305 /*@ 306 MatMissingDiagonal - Determine if sparse matrix is missing a diagonal entry (or block entry for BAIJ matrices) 307 308 Collective on Mat 309 310 Input Parameter: 311 . mat - the matrix 312 313 Output Parameters: 314 + missing - is any diagonal missing 315 - dd - first diagonal entry that is missing (optional) 316 317 Level: advanced 318 319 320 .seealso: MatRealPart() 321 @*/ 322 PetscErrorCode MatMissingDiagonal(Mat mat,PetscBool *missing,PetscInt *dd) 323 { 324 PetscErrorCode ierr; 325 326 PetscFunctionBegin; 327 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 328 PetscValidType(mat,1); 329 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 330 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 331 if (!mat->ops->missingdiagonal) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 332 ierr = (*mat->ops->missingdiagonal)(mat,missing,dd);CHKERRQ(ierr); 333 PetscFunctionReturn(0); 334 } 335 336 #undef __FUNCT__ 337 #define __FUNCT__ "MatGetRow" 338 /*@C 339 MatGetRow - Gets a row of a matrix. You MUST call MatRestoreRow() 340 for each row that you get to ensure that your application does 341 not bleed memory. 342 343 Not Collective 344 345 Input Parameters: 346 + mat - the matrix 347 - row - the row to get 348 349 Output Parameters: 350 + ncols - if not NULL, the number of nonzeros in the row 351 . cols - if not NULL, the column numbers 352 - vals - if not NULL, the values 353 354 Notes: 355 This routine is provided for people who need to have direct access 356 to the structure of a matrix. We hope that we provide enough 357 high-level matrix routines that few users will need it. 358 359 MatGetRow() always returns 0-based column indices, regardless of 360 whether the internal representation is 0-based (default) or 1-based. 361 362 For better efficiency, set cols and/or vals to NULL if you do 363 not wish to extract these quantities. 364 365 The user can only examine the values extracted with MatGetRow(); 366 the values cannot be altered. To change the matrix entries, one 367 must use MatSetValues(). 368 369 You can only have one call to MatGetRow() outstanding for a particular 370 matrix at a time, per processor. MatGetRow() can only obtain rows 371 associated with the given processor, it cannot get rows from the 372 other processors; for that we suggest using MatGetSubMatrices(), then 373 MatGetRow() on the submatrix. The row indix passed to MatGetRows() 374 is in the global number of rows. 375 376 Fortran Notes: 377 The calling sequence from Fortran is 378 .vb 379 MatGetRow(matrix,row,ncols,cols,values,ierr) 380 Mat matrix (input) 381 integer row (input) 382 integer ncols (output) 383 integer cols(maxcols) (output) 384 double precision (or double complex) values(maxcols) output 385 .ve 386 where maxcols >= maximum nonzeros in any row of the matrix. 387 388 389 Caution: 390 Do not try to change the contents of the output arrays (cols and vals). 391 In some cases, this may corrupt the matrix. 392 393 Level: advanced 394 395 Concepts: matrices^row access 396 397 .seealso: MatRestoreRow(), MatSetValues(), MatGetValues(), MatGetSubMatrices(), MatGetDiagonal() 398 @*/ 399 PetscErrorCode MatGetRow(Mat mat,PetscInt row,PetscInt *ncols,const PetscInt *cols[],const PetscScalar *vals[]) 400 { 401 PetscErrorCode ierr; 402 PetscInt incols; 403 404 PetscFunctionBegin; 405 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 406 PetscValidType(mat,1); 407 if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 408 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 409 if (!mat->ops->getrow) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 410 MatCheckPreallocated(mat,1); 411 ierr = PetscLogEventBegin(MAT_GetRow,mat,0,0,0);CHKERRQ(ierr); 412 ierr = (*mat->ops->getrow)(mat,row,&incols,(PetscInt**)cols,(PetscScalar**)vals);CHKERRQ(ierr); 413 if (ncols) *ncols = incols; 414 ierr = PetscLogEventEnd(MAT_GetRow,mat,0,0,0);CHKERRQ(ierr); 415 PetscFunctionReturn(0); 416 } 417 418 #undef __FUNCT__ 419 #define __FUNCT__ "MatConjugate" 420 /*@ 421 MatConjugate - replaces the matrix values with their complex conjugates 422 423 Logically Collective on Mat 424 425 Input Parameters: 426 . mat - the matrix 427 428 Level: advanced 429 430 .seealso: VecConjugate() 431 @*/ 432 PetscErrorCode MatConjugate(Mat mat) 433 { 434 #if defined(PETSC_USE_COMPLEX) 435 PetscErrorCode ierr; 436 437 PetscFunctionBegin; 438 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 439 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 440 if (!mat->ops->conjugate) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Not provided for this matrix format, send email to petsc-maint@mcs.anl.gov"); 441 ierr = (*mat->ops->conjugate)(mat);CHKERRQ(ierr); 442 #if defined(PETSC_HAVE_CUSP) 443 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 444 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 445 } 446 #endif 447 PetscFunctionReturn(0); 448 #else 449 return 0; 450 #endif 451 } 452 453 #undef __FUNCT__ 454 #define __FUNCT__ "MatRestoreRow" 455 /*@C 456 MatRestoreRow - Frees any temporary space allocated by MatGetRow(). 457 458 Not Collective 459 460 Input Parameters: 461 + mat - the matrix 462 . row - the row to get 463 . ncols, cols - the number of nonzeros and their columns 464 - vals - if nonzero the column values 465 466 Notes: 467 This routine should be called after you have finished examining the entries. 468 469 Fortran Notes: 470 The calling sequence from Fortran is 471 .vb 472 MatRestoreRow(matrix,row,ncols,cols,values,ierr) 473 Mat matrix (input) 474 integer row (input) 475 integer ncols (output) 476 integer cols(maxcols) (output) 477 double precision (or double complex) values(maxcols) output 478 .ve 479 Where maxcols >= maximum nonzeros in any row of the matrix. 480 481 In Fortran MatRestoreRow() MUST be called after MatGetRow() 482 before another call to MatGetRow() can be made. 483 484 Level: advanced 485 486 .seealso: MatGetRow() 487 @*/ 488 PetscErrorCode MatRestoreRow(Mat mat,PetscInt row,PetscInt *ncols,const PetscInt *cols[],const PetscScalar *vals[]) 489 { 490 PetscErrorCode ierr; 491 492 PetscFunctionBegin; 493 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 494 if (ncols) PetscValidIntPointer(ncols,3); 495 if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 496 if (!mat->ops->restorerow) PetscFunctionReturn(0); 497 ierr = (*mat->ops->restorerow)(mat,row,ncols,(PetscInt **)cols,(PetscScalar **)vals);CHKERRQ(ierr); 498 PetscFunctionReturn(0); 499 } 500 501 #undef __FUNCT__ 502 #define __FUNCT__ "MatGetRowUpperTriangular" 503 /*@ 504 MatGetRowUpperTriangular - Sets a flag to enable calls to MatGetRow() for matrix in MATSBAIJ format. 505 You should call MatRestoreRowUpperTriangular() after calling MatGetRow/MatRestoreRow() to disable the flag. 506 507 Not Collective 508 509 Input Parameters: 510 + mat - the matrix 511 512 Notes: 513 The flag is to ensure that users are aware of MatGetRow() only provides the upper trianglular part of the row for the matrices in MATSBAIJ format. 514 515 Level: advanced 516 517 Concepts: matrices^row access 518 519 .seealso: MatRestoreRowRowUpperTriangular() 520 @*/ 521 PetscErrorCode MatGetRowUpperTriangular(Mat mat) 522 { 523 PetscErrorCode ierr; 524 525 PetscFunctionBegin; 526 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 527 PetscValidType(mat,1); 528 if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 529 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 530 if (!mat->ops->getrowuppertriangular) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 531 MatCheckPreallocated(mat,1); 532 ierr = (*mat->ops->getrowuppertriangular)(mat);CHKERRQ(ierr); 533 PetscFunctionReturn(0); 534 } 535 536 #undef __FUNCT__ 537 #define __FUNCT__ "MatRestoreRowUpperTriangular" 538 /*@ 539 MatRestoreRowUpperTriangular - Disable calls to MatGetRow() for matrix in MATSBAIJ format. 540 541 Not Collective 542 543 Input Parameters: 544 + mat - the matrix 545 546 Notes: 547 This routine should be called after you have finished MatGetRow/MatRestoreRow(). 548 549 550 Level: advanced 551 552 .seealso: MatGetRowUpperTriangular() 553 @*/ 554 PetscErrorCode MatRestoreRowUpperTriangular(Mat mat) 555 { 556 PetscErrorCode ierr; 557 558 PetscFunctionBegin; 559 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 560 if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 561 if (!mat->ops->restorerowuppertriangular) PetscFunctionReturn(0); 562 ierr = (*mat->ops->restorerowuppertriangular)(mat);CHKERRQ(ierr); 563 PetscFunctionReturn(0); 564 } 565 566 #undef __FUNCT__ 567 #define __FUNCT__ "MatSetOptionsPrefix" 568 /*@C 569 MatSetOptionsPrefix - Sets the prefix used for searching for all 570 Mat options in the database. 571 572 Logically Collective on Mat 573 574 Input Parameter: 575 + A - the Mat context 576 - prefix - the prefix to prepend to all option names 577 578 Notes: 579 A hyphen (-) must NOT be given at the beginning of the prefix name. 580 The first character of all runtime options is AUTOMATICALLY the hyphen. 581 582 Level: advanced 583 584 .keywords: Mat, set, options, prefix, database 585 586 .seealso: MatSetFromOptions() 587 @*/ 588 PetscErrorCode MatSetOptionsPrefix(Mat A,const char prefix[]) 589 { 590 PetscErrorCode ierr; 591 592 PetscFunctionBegin; 593 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 594 ierr = PetscObjectSetOptionsPrefix((PetscObject)A,prefix);CHKERRQ(ierr); 595 PetscFunctionReturn(0); 596 } 597 598 #undef __FUNCT__ 599 #define __FUNCT__ "MatAppendOptionsPrefix" 600 /*@C 601 MatAppendOptionsPrefix - Appends to the prefix used for searching for all 602 Mat options in the database. 603 604 Logically Collective on Mat 605 606 Input Parameters: 607 + A - the Mat context 608 - prefix - the prefix to prepend to all option names 609 610 Notes: 611 A hyphen (-) must NOT be given at the beginning of the prefix name. 612 The first character of all runtime options is AUTOMATICALLY the hyphen. 613 614 Level: advanced 615 616 .keywords: Mat, append, options, prefix, database 617 618 .seealso: MatGetOptionsPrefix() 619 @*/ 620 PetscErrorCode MatAppendOptionsPrefix(Mat A,const char prefix[]) 621 { 622 PetscErrorCode ierr; 623 624 PetscFunctionBegin; 625 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 626 ierr = PetscObjectAppendOptionsPrefix((PetscObject)A,prefix);CHKERRQ(ierr); 627 PetscFunctionReturn(0); 628 } 629 630 #undef __FUNCT__ 631 #define __FUNCT__ "MatGetOptionsPrefix" 632 /*@C 633 MatGetOptionsPrefix - Sets the prefix used for searching for all 634 Mat options in the database. 635 636 Not Collective 637 638 Input Parameter: 639 . A - the Mat context 640 641 Output Parameter: 642 . prefix - pointer to the prefix string used 643 644 Notes: On the fortran side, the user should pass in a string 'prefix' of 645 sufficient length to hold the prefix. 646 647 Level: advanced 648 649 .keywords: Mat, get, options, prefix, database 650 651 .seealso: MatAppendOptionsPrefix() 652 @*/ 653 PetscErrorCode MatGetOptionsPrefix(Mat A,const char *prefix[]) 654 { 655 PetscErrorCode ierr; 656 657 PetscFunctionBegin; 658 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 659 ierr = PetscObjectGetOptionsPrefix((PetscObject)A,prefix);CHKERRQ(ierr); 660 PetscFunctionReturn(0); 661 } 662 663 #undef __FUNCT__ 664 #define __FUNCT__ "MatSetUp" 665 /*@ 666 MatSetUp - Sets up the internal matrix data structures for the later use. 667 668 Collective on Mat 669 670 Input Parameters: 671 . A - the Mat context 672 673 Notes: 674 If the user has not set preallocation for this matrix then a default preallocation that is likely to be inefficient is used. 675 676 If a suitable preallocation routine is used, this function does not need to be called. 677 678 See the Performance chapter of the PETSc users manual for how to preallocate matrices 679 680 Level: beginner 681 682 .keywords: Mat, setup 683 684 .seealso: MatCreate(), MatDestroy() 685 @*/ 686 PetscErrorCode MatSetUp(Mat A) 687 { 688 PetscMPIInt size; 689 PetscErrorCode ierr; 690 691 PetscFunctionBegin; 692 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 693 if (!((PetscObject)A)->type_name) { 694 ierr = MPI_Comm_size(PetscObjectComm((PetscObject)A), &size);CHKERRQ(ierr); 695 if (size == 1) { 696 ierr = MatSetType(A, MATSEQAIJ);CHKERRQ(ierr); 697 } else { 698 ierr = MatSetType(A, MATMPIAIJ);CHKERRQ(ierr); 699 } 700 } 701 if (!A->preallocated && A->ops->setup) { 702 ierr = PetscInfo(A,"Warning not preallocating matrix storage\n");CHKERRQ(ierr); 703 ierr = (*A->ops->setup)(A);CHKERRQ(ierr); 704 } 705 A->preallocated = PETSC_TRUE; 706 PetscFunctionReturn(0); 707 } 708 709 710 #undef __FUNCT__ 711 #define __FUNCT__ "MatView" 712 /*@C 713 MatView - Visualizes a matrix object. 714 715 Collective on Mat 716 717 Input Parameters: 718 + mat - the matrix 719 - viewer - visualization context 720 721 Notes: 722 The available visualization contexts include 723 + PETSC_VIEWER_STDOUT_SELF - standard output (default) 724 . PETSC_VIEWER_STDOUT_WORLD - synchronized standard 725 output where only the first processor opens 726 the file. All other processors send their 727 data to the first processor to print. 728 - PETSC_VIEWER_DRAW_WORLD - graphical display of nonzero structure 729 730 The user can open alternative visualization contexts with 731 + PetscViewerASCIIOpen() - Outputs matrix to a specified file 732 . PetscViewerBinaryOpen() - Outputs matrix in binary to a 733 specified file; corresponding input uses MatLoad() 734 . PetscViewerDrawOpen() - Outputs nonzero matrix structure to 735 an X window display 736 - PetscViewerSocketOpen() - Outputs matrix to Socket viewer. 737 Currently only the sequential dense and AIJ 738 matrix types support the Socket viewer. 739 740 The user can call PetscViewerSetFormat() to specify the output 741 format of ASCII printed objects (when using PETSC_VIEWER_STDOUT_SELF, 742 PETSC_VIEWER_STDOUT_WORLD and PetscViewerASCIIOpen). Available formats include 743 + PETSC_VIEWER_DEFAULT - default, prints matrix contents 744 . PETSC_VIEWER_ASCII_MATLAB - prints matrix contents in Matlab format 745 . PETSC_VIEWER_ASCII_DENSE - prints entire matrix including zeros 746 . PETSC_VIEWER_ASCII_COMMON - prints matrix contents, using a sparse 747 format common among all matrix types 748 . PETSC_VIEWER_ASCII_IMPL - prints matrix contents, using an implementation-specific 749 format (which is in many cases the same as the default) 750 . PETSC_VIEWER_ASCII_INFO - prints basic information about the matrix 751 size and structure (not the matrix entries) 752 . PETSC_VIEWER_ASCII_INFO_DETAIL - prints more detailed information about 753 the matrix structure 754 755 Options Database Keys: 756 + -mat_view ::ascii_info - Prints info on matrix at conclusion of MatEndAssembly() 757 . -mat_view ::ascii_info_detail - Prints more detailed info 758 . -mat_view - Prints matrix in ASCII format 759 . -mat_view ::ascii_matlab - Prints matrix in Matlab format 760 . -mat_view draw - PetscDraws nonzero structure of matrix, using MatView() and PetscDrawOpenX(). 761 . -display <name> - Sets display name (default is host) 762 . -draw_pause <sec> - Sets number of seconds to pause after display 763 . -mat_view socket - Sends matrix to socket, can be accessed from Matlab (see the <a href="../../docs/manual.pdf">users manual</a> for details). 764 . -viewer_socket_machine <machine> 765 . -viewer_socket_port <port> 766 . -mat_view binary - save matrix to file in binary format 767 - -viewer_binary_filename <name> 768 Level: beginner 769 770 Notes: see the manual page for MatLoad() for the exact format of the binary file when the binary 771 viewer is used. 772 773 See bin/matlab/PetscBinaryRead.m for a Matlab code that can read in the binary file when the binary 774 viewer is used. 775 776 One can use '-mat_view draw -draw_pause -1' to pause the graphical display of matrix nonzero structure. 777 And then use the following mouse functions: 778 left mouse: zoom in 779 middle mouse: zoom out 780 right mouse: continue with the simulation 781 782 Concepts: matrices^viewing 783 Concepts: matrices^plotting 784 Concepts: matrices^printing 785 786 .seealso: PetscViewerSetFormat(), PetscViewerASCIIOpen(), PetscViewerDrawOpen(), 787 PetscViewerSocketOpen(), PetscViewerBinaryOpen(), MatLoad() 788 @*/ 789 PetscErrorCode MatView(Mat mat,PetscViewer viewer) 790 { 791 PetscErrorCode ierr; 792 PetscInt rows,cols,bs; 793 PetscBool iascii; 794 PetscViewerFormat format; 795 796 PetscFunctionBegin; 797 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 798 PetscValidType(mat,1); 799 if (!viewer) { 800 ierr = PetscViewerASCIIGetStdout(PetscObjectComm((PetscObject)mat),&viewer);CHKERRQ(ierr); 801 } 802 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,2); 803 PetscCheckSameComm(mat,1,viewer,2); 804 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ORDER,"Must call MatAssemblyBegin/End() before viewing matrix"); 805 MatCheckPreallocated(mat,1); 806 807 ierr = PetscLogEventBegin(MAT_View,mat,viewer,0,0);CHKERRQ(ierr); 808 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&iascii);CHKERRQ(ierr); 809 if (iascii) { 810 ierr = PetscViewerGetFormat(viewer,&format);CHKERRQ(ierr); 811 if (format == PETSC_VIEWER_ASCII_INFO || format == PETSC_VIEWER_ASCII_INFO_DETAIL) { 812 ierr = PetscObjectPrintClassNamePrefixType((PetscObject)mat,viewer,"Matrix Object");CHKERRQ(ierr); 813 ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr); 814 ierr = MatGetSize(mat,&rows,&cols);CHKERRQ(ierr); 815 ierr = MatGetBlockSize(mat,&bs);CHKERRQ(ierr); 816 if (bs != 1) { 817 ierr = PetscViewerASCIIPrintf(viewer,"rows=%D, cols=%D, bs=%D\n",rows,cols,bs);CHKERRQ(ierr); 818 } else { 819 ierr = PetscViewerASCIIPrintf(viewer,"rows=%D, cols=%D\n",rows,cols);CHKERRQ(ierr); 820 } 821 if (mat->factortype) { 822 const MatSolverPackage solver; 823 ierr = MatFactorGetSolverPackage(mat,&solver);CHKERRQ(ierr); 824 ierr = PetscViewerASCIIPrintf(viewer,"package used to perform factorization: %s\n",solver);CHKERRQ(ierr); 825 } 826 if (mat->ops->getinfo) { 827 MatInfo info; 828 ierr = MatGetInfo(mat,MAT_GLOBAL_SUM,&info);CHKERRQ(ierr); 829 ierr = PetscViewerASCIIPrintf(viewer,"total: nonzeros=%lld, allocated nonzeros=%lld\n",(Petsc64bitInt)info.nz_used,(Petsc64bitInt)info.nz_allocated);CHKERRQ(ierr); 830 ierr = PetscViewerASCIIPrintf(viewer,"total number of mallocs used during MatSetValues calls =%D\n",(PetscInt)info.mallocs);CHKERRQ(ierr); 831 } 832 } 833 } 834 if (mat->ops->view) { 835 ierr = PetscViewerASCIIPushTab(viewer);CHKERRQ(ierr); 836 ierr = (*mat->ops->view)(mat,viewer);CHKERRQ(ierr); 837 ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr); 838 } else if (!iascii) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Viewer type %s not supported",((PetscObject)viewer)->type_name); 839 if (iascii) { 840 ierr = PetscViewerGetFormat(viewer,&format);CHKERRQ(ierr); 841 if (format == PETSC_VIEWER_ASCII_INFO || format == PETSC_VIEWER_ASCII_INFO_DETAIL) { 842 ierr = PetscViewerASCIIPopTab(viewer);CHKERRQ(ierr); 843 } 844 } 845 ierr = PetscLogEventEnd(MAT_View,mat,viewer,0,0);CHKERRQ(ierr); 846 PetscFunctionReturn(0); 847 } 848 849 #if defined(PETSC_USE_DEBUG) 850 #include <../src/sys/totalview/tv_data_display.h> 851 PETSC_UNUSED static int TV_display_type(const struct _p_Mat *mat) 852 { 853 TV_add_row("Local rows", "int", &mat->rmap->n); 854 TV_add_row("Local columns", "int", &mat->cmap->n); 855 TV_add_row("Global rows", "int", &mat->rmap->N); 856 TV_add_row("Global columns", "int", &mat->cmap->N); 857 TV_add_row("Typename", TV_ascii_string_type, ((PetscObject)mat)->type_name); 858 return TV_format_OK; 859 } 860 #endif 861 862 #undef __FUNCT__ 863 #define __FUNCT__ "MatLoad" 864 /*@C 865 MatLoad - Loads a matrix that has been stored in binary format 866 with MatView(). The matrix format is determined from the options database. 867 Generates a parallel MPI matrix if the communicator has more than one 868 processor. The default matrix type is AIJ. 869 870 Collective on PetscViewer 871 872 Input Parameters: 873 + newmat - the newly loaded matrix, this needs to have been created with MatCreate() 874 or some related function before a call to MatLoad() 875 - viewer - binary file viewer, created with PetscViewerBinaryOpen() 876 877 Options Database Keys: 878 Used with block matrix formats (MATSEQBAIJ, ...) to specify 879 block size 880 . -matload_block_size <bs> 881 882 Level: beginner 883 884 Notes: 885 If the Mat type has not yet been given then MATAIJ is used, call MatSetFromOptions() on the 886 Mat before calling this routine if you wish to set it from the options database. 887 888 MatLoad() automatically loads into the options database any options 889 given in the file filename.info where filename is the name of the file 890 that was passed to the PetscViewerBinaryOpen(). The options in the info 891 file will be ignored if you use the -viewer_binary_skip_info option. 892 893 If the type or size of newmat is not set before a call to MatLoad, PETSc 894 sets the default matrix type AIJ and sets the local and global sizes. 895 If type and/or size is already set, then the same are used. 896 897 In parallel, each processor can load a subset of rows (or the 898 entire matrix). This routine is especially useful when a large 899 matrix is stored on disk and only part of it is desired on each 900 processor. For example, a parallel solver may access only some of 901 the rows from each processor. The algorithm used here reads 902 relatively small blocks of data rather than reading the entire 903 matrix and then subsetting it. 904 905 Notes for advanced users: 906 Most users should not need to know the details of the binary storage 907 format, since MatLoad() and MatView() completely hide these details. 908 But for anyone who's interested, the standard binary matrix storage 909 format is 910 911 $ int MAT_FILE_CLASSID 912 $ int number of rows 913 $ int number of columns 914 $ int total number of nonzeros 915 $ int *number nonzeros in each row 916 $ int *column indices of all nonzeros (starting index is zero) 917 $ PetscScalar *values of all nonzeros 918 919 PETSc automatically does the byte swapping for 920 machines that store the bytes reversed, e.g. DEC alpha, freebsd, 921 linux, Windows and the paragon; thus if you write your own binary 922 read/write routines you have to swap the bytes; see PetscBinaryRead() 923 and PetscBinaryWrite() to see how this may be done. 924 925 .keywords: matrix, load, binary, input 926 927 .seealso: PetscViewerBinaryOpen(), MatView(), VecLoad() 928 929 @*/ 930 PetscErrorCode MatLoad(Mat newmat,PetscViewer viewer) 931 { 932 PetscErrorCode ierr; 933 PetscBool isbinary,flg; 934 935 PetscFunctionBegin; 936 PetscValidHeaderSpecific(newmat,MAT_CLASSID,1); 937 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,2); 938 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERBINARY,&isbinary);CHKERRQ(ierr); 939 if (!isbinary) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Invalid viewer; open viewer with PetscViewerBinaryOpen()"); 940 941 if (!((PetscObject)newmat)->type_name) { 942 ierr = MatSetType(newmat,MATAIJ);CHKERRQ(ierr); 943 } 944 945 if (!newmat->ops->load) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"MatLoad is not supported for type"); 946 ierr = PetscLogEventBegin(MAT_Load,viewer,0,0,0);CHKERRQ(ierr); 947 ierr = (*newmat->ops->load)(newmat,viewer);CHKERRQ(ierr); 948 ierr = PetscLogEventEnd(MAT_Load,viewer,0,0,0);CHKERRQ(ierr); 949 950 flg = PETSC_FALSE; 951 ierr = PetscOptionsGetBool(((PetscObject)newmat)->prefix,"-matload_symmetric",&flg,NULL);CHKERRQ(ierr); 952 if (flg) { 953 ierr = MatSetOption(newmat,MAT_SYMMETRIC,PETSC_TRUE);CHKERRQ(ierr); 954 ierr = MatSetOption(newmat,MAT_SYMMETRY_ETERNAL,PETSC_TRUE);CHKERRQ(ierr); 955 } 956 flg = PETSC_FALSE; 957 ierr = PetscOptionsGetBool(((PetscObject)newmat)->prefix,"-matload_spd",&flg,NULL);CHKERRQ(ierr); 958 if (flg) { 959 ierr = MatSetOption(newmat,MAT_SPD,PETSC_TRUE);CHKERRQ(ierr); 960 } 961 PetscFunctionReturn(0); 962 } 963 964 #undef __FUNCT__ 965 #define __FUNCT__ "MatDestroy" 966 /*@ 967 MatDestroy - Frees space taken by a matrix. 968 969 Collective on Mat 970 971 Input Parameter: 972 . A - the matrix 973 974 Level: beginner 975 976 @*/ 977 PetscErrorCode MatDestroy(Mat *A) 978 { 979 PetscErrorCode ierr; 980 981 PetscFunctionBegin; 982 if (!*A) PetscFunctionReturn(0); 983 PetscValidHeaderSpecific(*A,MAT_CLASSID,1); 984 if (--((PetscObject)(*A))->refct > 0) {*A = NULL; PetscFunctionReturn(0);} 985 986 ierr = PetscViewerDestroy(&(*A)->viewonassembly);CHKERRQ(ierr); 987 /* if memory was published with AMS then destroy it */ 988 ierr = PetscObjectDepublish(*A);CHKERRQ(ierr); 989 if ((*A)->ops->destroy) { 990 ierr = (*(*A)->ops->destroy)(*A);CHKERRQ(ierr); 991 } 992 ierr = MatNullSpaceDestroy(&(*A)->nullsp);CHKERRQ(ierr); 993 ierr = MatNullSpaceDestroy(&(*A)->nearnullsp);CHKERRQ(ierr); 994 ierr = PetscLayoutDestroy(&(*A)->rmap);CHKERRQ(ierr); 995 ierr = PetscLayoutDestroy(&(*A)->cmap);CHKERRQ(ierr); 996 ierr = PetscHeaderDestroy(A);CHKERRQ(ierr); 997 PetscFunctionReturn(0); 998 } 999 1000 #undef __FUNCT__ 1001 #define __FUNCT__ "MatSetValues" 1002 /*@ 1003 MatSetValues - Inserts or adds a block of values into a matrix. 1004 These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd() 1005 MUST be called after all calls to MatSetValues() have been completed. 1006 1007 Not Collective 1008 1009 Input Parameters: 1010 + mat - the matrix 1011 . v - a logically two-dimensional array of values 1012 . m, idxm - the number of rows and their global indices 1013 . n, idxn - the number of columns and their global indices 1014 - addv - either ADD_VALUES or INSERT_VALUES, where 1015 ADD_VALUES adds values to any existing entries, and 1016 INSERT_VALUES replaces existing entries with new values 1017 1018 Notes: 1019 If you create the matrix yourself (that is not with a call to DMCreateMatrix()) then you MUST call MatXXXXSetPreallocation() or 1020 MatSetUp() before using this routine 1021 1022 By default the values, v, are row-oriented. See MatSetOption() for other options. 1023 1024 Calls to MatSetValues() with the INSERT_VALUES and ADD_VALUES 1025 options cannot be mixed without intervening calls to the assembly 1026 routines. 1027 1028 MatSetValues() uses 0-based row and column numbers in Fortran 1029 as well as in C. 1030 1031 Negative indices may be passed in idxm and idxn, these rows and columns are 1032 simply ignored. This allows easily inserting element stiffness matrices 1033 with homogeneous Dirchlet boundary conditions that you don't want represented 1034 in the matrix. 1035 1036 Efficiency Alert: 1037 The routine MatSetValuesBlocked() may offer much better efficiency 1038 for users of block sparse formats (MATSEQBAIJ and MATMPIBAIJ). 1039 1040 Level: beginner 1041 1042 Concepts: matrices^putting entries in 1043 1044 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(), 1045 InsertMode, INSERT_VALUES, ADD_VALUES 1046 @*/ 1047 PetscErrorCode MatSetValues(Mat mat,PetscInt m,const PetscInt idxm[],PetscInt n,const PetscInt idxn[],const PetscScalar v[],InsertMode addv) 1048 { 1049 PetscErrorCode ierr; 1050 #if defined(PETSC_USE_DEBUG) 1051 PetscInt i,j; 1052 #endif 1053 1054 PetscFunctionBegin; 1055 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 1056 PetscValidType(mat,1); 1057 if (!m || !n) PetscFunctionReturn(0); /* no values to insert */ 1058 PetscValidIntPointer(idxm,3); 1059 PetscValidIntPointer(idxn,5); 1060 if (v) PetscValidScalarPointer(v,6); 1061 MatCheckPreallocated(mat,1); 1062 if (mat->insertmode == NOT_SET_VALUES) { 1063 mat->insertmode = addv; 1064 } 1065 #if defined(PETSC_USE_DEBUG) 1066 else if (mat->insertmode != addv) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values"); 1067 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 1068 if (!mat->ops->setvalues) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 1069 1070 if (v) { 1071 for (i=0; i<m; i++) { 1072 for (j=0; j<n; j++) { 1073 if (PetscIsInfOrNanScalar(v[i*n+j])) 1074 #if defined(PETSC_USE_COMPLEX) 1075 SETERRQ4(PETSC_COMM_SELF,PETSC_ERR_FP,"Inserting %G+iG at matrix entry (%D,%D)",PetscRealPart(v[i*n+j]),PetscImaginaryPart(v[i*n+j]),idxm[i],idxn[j]); 1076 #else 1077 SETERRQ3(PETSC_COMM_SELF,PETSC_ERR_FP,"Inserting %G at matrix entry (%D,%D)",(PetscReal)v[i*n+j],idxm[i],idxn[j]); 1078 #endif 1079 } 1080 } 1081 } 1082 #endif 1083 1084 if (mat->assembled) { 1085 mat->was_assembled = PETSC_TRUE; 1086 mat->assembled = PETSC_FALSE; 1087 } 1088 ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 1089 ierr = (*mat->ops->setvalues)(mat,m,idxm,n,idxn,v,addv);CHKERRQ(ierr); 1090 ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 1091 #if defined(PETSC_HAVE_CUSP) 1092 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 1093 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 1094 } 1095 #endif 1096 PetscFunctionReturn(0); 1097 } 1098 1099 1100 #undef __FUNCT__ 1101 #define __FUNCT__ "MatSetValuesRowLocal" 1102 /*@ 1103 MatSetValuesRowLocal - Inserts a row (block row for BAIJ matrices) of nonzero 1104 values into a matrix 1105 1106 Not Collective 1107 1108 Input Parameters: 1109 + mat - the matrix 1110 . row - the (block) row to set 1111 - v - a logically two-dimensional array of values 1112 1113 Notes: 1114 By the values, v, are column-oriented (for the block version) and sorted 1115 1116 All the nonzeros in the row must be provided 1117 1118 The matrix must have previously had its column indices set 1119 1120 The row must belong to this process 1121 1122 Level: intermediate 1123 1124 Concepts: matrices^putting entries in 1125 1126 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(), 1127 InsertMode, INSERT_VALUES, ADD_VALUES, MatSetValues(), MatSetValuesRow(), MatSetLocalToGlobalMapping() 1128 @*/ 1129 PetscErrorCode MatSetValuesRowLocal(Mat mat,PetscInt row,const PetscScalar v[]) 1130 { 1131 PetscErrorCode ierr; 1132 PetscInt globalrow; 1133 1134 PetscFunctionBegin; 1135 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 1136 PetscValidType(mat,1); 1137 PetscValidScalarPointer(v,2); 1138 ierr = ISLocalToGlobalMappingApply(mat->rmap->mapping,1,&row,&globalrow);CHKERRQ(ierr); 1139 ierr = MatSetValuesRow(mat,globalrow,v);CHKERRQ(ierr); 1140 #if defined(PETSC_HAVE_CUSP) 1141 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 1142 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 1143 } 1144 #endif 1145 PetscFunctionReturn(0); 1146 } 1147 1148 #undef __FUNCT__ 1149 #define __FUNCT__ "MatSetValuesRow" 1150 /*@ 1151 MatSetValuesRow - Inserts a row (block row for BAIJ matrices) of nonzero 1152 values into a matrix 1153 1154 Not Collective 1155 1156 Input Parameters: 1157 + mat - the matrix 1158 . row - the (block) row to set 1159 - v - a logically two-dimensional array of values 1160 1161 Notes: 1162 The values, v, are column-oriented for the block version. 1163 1164 All the nonzeros in the row must be provided 1165 1166 THE MATRIX MUSAT HAVE PREVIOUSLY HAD ITS COLUMN INDICES SET. IT IS RARE THAT THIS ROUTINE IS USED, usually MatSetValues() is used. 1167 1168 The row must belong to this process 1169 1170 Level: advanced 1171 1172 Concepts: matrices^putting entries in 1173 1174 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(), 1175 InsertMode, INSERT_VALUES, ADD_VALUES, MatSetValues() 1176 @*/ 1177 PetscErrorCode MatSetValuesRow(Mat mat,PetscInt row,const PetscScalar v[]) 1178 { 1179 PetscErrorCode ierr; 1180 1181 PetscFunctionBegin; 1182 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 1183 PetscValidType(mat,1); 1184 MatCheckPreallocated(mat,1); 1185 PetscValidScalarPointer(v,2); 1186 #if defined(PETSC_USE_DEBUG) 1187 if (mat->insertmode == ADD_VALUES) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add and insert values"); 1188 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 1189 #endif 1190 mat->insertmode = INSERT_VALUES; 1191 1192 if (mat->assembled) { 1193 mat->was_assembled = PETSC_TRUE; 1194 mat->assembled = PETSC_FALSE; 1195 } 1196 ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 1197 if (!mat->ops->setvaluesrow) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 1198 ierr = (*mat->ops->setvaluesrow)(mat,row,v);CHKERRQ(ierr); 1199 ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 1200 #if defined(PETSC_HAVE_CUSP) 1201 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 1202 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 1203 } 1204 #endif 1205 PetscFunctionReturn(0); 1206 } 1207 1208 #undef __FUNCT__ 1209 #define __FUNCT__ "MatSetValuesStencil" 1210 /*@ 1211 MatSetValuesStencil - Inserts or adds a block of values into a matrix. 1212 Using structured grid indexing 1213 1214 Not Collective 1215 1216 Input Parameters: 1217 + mat - the matrix 1218 . m - number of rows being entered 1219 . idxm - grid coordinates (and component number when dof > 1) for matrix rows being entered 1220 . n - number of columns being entered 1221 . idxn - grid coordinates (and component number when dof > 1) for matrix columns being entered 1222 . v - a logically two-dimensional array of values 1223 - addv - either ADD_VALUES or INSERT_VALUES, where 1224 ADD_VALUES adds values to any existing entries, and 1225 INSERT_VALUES replaces existing entries with new values 1226 1227 Notes: 1228 By default the values, v, are row-oriented. See MatSetOption() for other options. 1229 1230 Calls to MatSetValuesStencil() with the INSERT_VALUES and ADD_VALUES 1231 options cannot be mixed without intervening calls to the assembly 1232 routines. 1233 1234 The grid coordinates are across the entire grid, not just the local portion 1235 1236 MatSetValuesStencil() uses 0-based row and column numbers in Fortran 1237 as well as in C. 1238 1239 For setting/accessing vector values via array coordinates you can use the DMDAVecGetArray() routine 1240 1241 In order to use this routine you must either obtain the matrix with DMCreateMatrix() 1242 or call MatSetLocalToGlobalMapping() and MatSetStencil() first. 1243 1244 The columns and rows in the stencil passed in MUST be contained within the 1245 ghost region of the given process as set with DMDACreateXXX() or MatSetStencil(). For example, 1246 if you create a DMDA with an overlap of one grid level and on a particular process its first 1247 local nonghost x logical coordinate is 6 (so its first ghost x logical coordinate is 5) the 1248 first i index you can use in your column and row indices in MatSetStencil() is 5. 1249 1250 In Fortran idxm and idxn should be declared as 1251 $ MatStencil idxm(4,m),idxn(4,n) 1252 and the values inserted using 1253 $ idxm(MatStencil_i,1) = i 1254 $ idxm(MatStencil_j,1) = j 1255 $ idxm(MatStencil_k,1) = k 1256 $ idxm(MatStencil_c,1) = c 1257 etc 1258 1259 For periodic boundary conditions use negative indices for values to the left (below 0; that are to be 1260 obtained by wrapping values from right edge). For values to the right of the last entry using that index plus one 1261 etc to obtain values that obtained by wrapping the values from the left edge. This does not work for anything but the 1262 DMDA_BOUNDARY_PERIODIC boundary type. 1263 1264 For indices that don't mean anything for your case (like the k index when working in 2d) or the c index when you have 1265 a single value per point) you can skip filling those indices. 1266 1267 Inspired by the structured grid interface to the HYPRE package 1268 (http://www.llnl.gov/CASC/hypre) 1269 1270 Efficiency Alert: 1271 The routine MatSetValuesBlockedStencil() may offer much better efficiency 1272 for users of block sparse formats (MATSEQBAIJ and MATMPIBAIJ). 1273 1274 Level: beginner 1275 1276 Concepts: matrices^putting entries in 1277 1278 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal() 1279 MatSetValues(), MatSetValuesBlockedStencil(), MatSetStencil(), DMCreateMatrix(), DMDAVecGetArray(), MatStencil 1280 @*/ 1281 PetscErrorCode MatSetValuesStencil(Mat mat,PetscInt m,const MatStencil idxm[],PetscInt n,const MatStencil idxn[],const PetscScalar v[],InsertMode addv) 1282 { 1283 PetscErrorCode ierr; 1284 PetscInt buf[8192],*bufm=0,*bufn=0,*jdxm,*jdxn; 1285 PetscInt j,i,dim = mat->stencil.dim,*dims = mat->stencil.dims+1,tmp; 1286 PetscInt *starts = mat->stencil.starts,*dxm = (PetscInt*)idxm,*dxn = (PetscInt*)idxn,sdim = dim - (1 - (PetscInt)mat->stencil.noc); 1287 1288 PetscFunctionBegin; 1289 if (!m || !n) PetscFunctionReturn(0); /* no values to insert */ 1290 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 1291 PetscValidType(mat,1); 1292 PetscValidIntPointer(idxm,3); 1293 PetscValidIntPointer(idxn,5); 1294 PetscValidScalarPointer(v,6); 1295 1296 if ((m+n) <= (PetscInt)(sizeof(buf)/sizeof(PetscInt))) { 1297 jdxm = buf; jdxn = buf+m; 1298 } else { 1299 ierr = PetscMalloc2(m,PetscInt,&bufm,n,PetscInt,&bufn);CHKERRQ(ierr); 1300 jdxm = bufm; jdxn = bufn; 1301 } 1302 for (i=0; i<m; i++) { 1303 for (j=0; j<3-sdim; j++) dxm++; 1304 tmp = *dxm++ - starts[0]; 1305 for (j=0; j<dim-1; j++) { 1306 if ((*dxm++ - starts[j+1]) < 0 || tmp < 0) tmp = -1; 1307 else tmp = tmp*dims[j] + *(dxm-1) - starts[j+1]; 1308 } 1309 if (mat->stencil.noc) dxm++; 1310 jdxm[i] = tmp; 1311 } 1312 for (i=0; i<n; i++) { 1313 for (j=0; j<3-sdim; j++) dxn++; 1314 tmp = *dxn++ - starts[0]; 1315 for (j=0; j<dim-1; j++) { 1316 if ((*dxn++ - starts[j+1]) < 0 || tmp < 0) tmp = -1; 1317 else tmp = tmp*dims[j] + *(dxn-1) - starts[j+1]; 1318 } 1319 if (mat->stencil.noc) dxn++; 1320 jdxn[i] = tmp; 1321 } 1322 ierr = MatSetValuesLocal(mat,m,jdxm,n,jdxn,v,addv);CHKERRQ(ierr); 1323 ierr = PetscFree2(bufm,bufn);CHKERRQ(ierr); 1324 PetscFunctionReturn(0); 1325 } 1326 1327 #undef __FUNCT__ 1328 #define __FUNCT__ "MatSetValuesBlockedStencil" 1329 /*@C 1330 MatSetValuesBlockedStencil - Inserts or adds a block of values into a matrix. 1331 Using structured grid indexing 1332 1333 Not Collective 1334 1335 Input Parameters: 1336 + mat - the matrix 1337 . m - number of rows being entered 1338 . idxm - grid coordinates for matrix rows being entered 1339 . n - number of columns being entered 1340 . idxn - grid coordinates for matrix columns being entered 1341 . v - a logically two-dimensional array of values 1342 - addv - either ADD_VALUES or INSERT_VALUES, where 1343 ADD_VALUES adds values to any existing entries, and 1344 INSERT_VALUES replaces existing entries with new values 1345 1346 Notes: 1347 By default the values, v, are row-oriented and unsorted. 1348 See MatSetOption() for other options. 1349 1350 Calls to MatSetValuesBlockedStencil() with the INSERT_VALUES and ADD_VALUES 1351 options cannot be mixed without intervening calls to the assembly 1352 routines. 1353 1354 The grid coordinates are across the entire grid, not just the local portion 1355 1356 MatSetValuesBlockedStencil() uses 0-based row and column numbers in Fortran 1357 as well as in C. 1358 1359 For setting/accessing vector values via array coordinates you can use the DMDAVecGetArray() routine 1360 1361 In order to use this routine you must either obtain the matrix with DMCreateMatrix() 1362 or call MatSetBlockSize(), MatSetLocalToGlobalMapping() and MatSetStencil() first. 1363 1364 The columns and rows in the stencil passed in MUST be contained within the 1365 ghost region of the given process as set with DMDACreateXXX() or MatSetStencil(). For example, 1366 if you create a DMDA with an overlap of one grid level and on a particular process its first 1367 local nonghost x logical coordinate is 6 (so its first ghost x logical coordinate is 5) the 1368 first i index you can use in your column and row indices in MatSetStencil() is 5. 1369 1370 In Fortran idxm and idxn should be declared as 1371 $ MatStencil idxm(4,m),idxn(4,n) 1372 and the values inserted using 1373 $ idxm(MatStencil_i,1) = i 1374 $ idxm(MatStencil_j,1) = j 1375 $ idxm(MatStencil_k,1) = k 1376 etc 1377 1378 Negative indices may be passed in idxm and idxn, these rows and columns are 1379 simply ignored. This allows easily inserting element stiffness matrices 1380 with homogeneous Dirchlet boundary conditions that you don't want represented 1381 in the matrix. 1382 1383 Inspired by the structured grid interface to the HYPRE package 1384 (http://www.llnl.gov/CASC/hypre) 1385 1386 Level: beginner 1387 1388 Concepts: matrices^putting entries in 1389 1390 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal() 1391 MatSetValues(), MatSetValuesStencil(), MatSetStencil(), DMCreateMatrix(), DMDAVecGetArray(), MatStencil, 1392 MatSetBlockSize(), MatSetLocalToGlobalMapping() 1393 @*/ 1394 PetscErrorCode MatSetValuesBlockedStencil(Mat mat,PetscInt m,const MatStencil idxm[],PetscInt n,const MatStencil idxn[],const PetscScalar v[],InsertMode addv) 1395 { 1396 PetscErrorCode ierr; 1397 PetscInt buf[8192],*bufm=0,*bufn=0,*jdxm,*jdxn; 1398 PetscInt j,i,dim = mat->stencil.dim,*dims = mat->stencil.dims+1,tmp; 1399 PetscInt *starts = mat->stencil.starts,*dxm = (PetscInt*)idxm,*dxn = (PetscInt*)idxn,sdim = dim - (1 - (PetscInt)mat->stencil.noc); 1400 1401 PetscFunctionBegin; 1402 if (!m || !n) PetscFunctionReturn(0); /* no values to insert */ 1403 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 1404 PetscValidType(mat,1); 1405 PetscValidIntPointer(idxm,3); 1406 PetscValidIntPointer(idxn,5); 1407 PetscValidScalarPointer(v,6); 1408 1409 if ((m+n) <= (PetscInt)(sizeof(buf)/sizeof(PetscInt))) { 1410 jdxm = buf; jdxn = buf+m; 1411 } else { 1412 ierr = PetscMalloc2(m,PetscInt,&bufm,n,PetscInt,&bufn);CHKERRQ(ierr); 1413 jdxm = bufm; jdxn = bufn; 1414 } 1415 for (i=0; i<m; i++) { 1416 for (j=0; j<3-sdim; j++) dxm++; 1417 tmp = *dxm++ - starts[0]; 1418 for (j=0; j<sdim-1; j++) { 1419 if ((*dxm++ - starts[j+1]) < 0 || tmp < 0) tmp = -1; 1420 else tmp = tmp*dims[j] + *(dxm-1) - starts[j+1]; 1421 } 1422 dxm++; 1423 jdxm[i] = tmp; 1424 } 1425 for (i=0; i<n; i++) { 1426 for (j=0; j<3-sdim; j++) dxn++; 1427 tmp = *dxn++ - starts[0]; 1428 for (j=0; j<sdim-1; j++) { 1429 if ((*dxn++ - starts[j+1]) < 0 || tmp < 0) tmp = -1; 1430 else tmp = tmp*dims[j] + *(dxn-1) - starts[j+1]; 1431 } 1432 dxn++; 1433 jdxn[i] = tmp; 1434 } 1435 ierr = MatSetValuesBlockedLocal(mat,m,jdxm,n,jdxn,v,addv);CHKERRQ(ierr); 1436 ierr = PetscFree2(bufm,bufn);CHKERRQ(ierr); 1437 #if defined(PETSC_HAVE_CUSP) 1438 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 1439 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 1440 } 1441 #endif 1442 PetscFunctionReturn(0); 1443 } 1444 1445 #undef __FUNCT__ 1446 #define __FUNCT__ "MatSetStencil" 1447 /*@ 1448 MatSetStencil - Sets the grid information for setting values into a matrix via 1449 MatSetValuesStencil() 1450 1451 Not Collective 1452 1453 Input Parameters: 1454 + mat - the matrix 1455 . dim - dimension of the grid 1, 2, or 3 1456 . dims - number of grid points in x, y, and z direction, including ghost points on your processor 1457 . starts - starting point of ghost nodes on your processor in x, y, and z direction 1458 - dof - number of degrees of freedom per node 1459 1460 1461 Inspired by the structured grid interface to the HYPRE package 1462 (www.llnl.gov/CASC/hyper) 1463 1464 For matrices generated with DMCreateMatrix() this routine is automatically called and so not needed by the 1465 user. 1466 1467 Level: beginner 1468 1469 Concepts: matrices^putting entries in 1470 1471 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal() 1472 MatSetValues(), MatSetValuesBlockedStencil(), MatSetValuesStencil() 1473 @*/ 1474 PetscErrorCode MatSetStencil(Mat mat,PetscInt dim,const PetscInt dims[],const PetscInt starts[],PetscInt dof) 1475 { 1476 PetscInt i; 1477 1478 PetscFunctionBegin; 1479 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 1480 PetscValidIntPointer(dims,3); 1481 PetscValidIntPointer(starts,4); 1482 1483 mat->stencil.dim = dim + (dof > 1); 1484 for (i=0; i<dim; i++) { 1485 mat->stencil.dims[i] = dims[dim-i-1]; /* copy the values in backwards */ 1486 mat->stencil.starts[i] = starts[dim-i-1]; 1487 } 1488 mat->stencil.dims[dim] = dof; 1489 mat->stencil.starts[dim] = 0; 1490 mat->stencil.noc = (PetscBool)(dof == 1); 1491 PetscFunctionReturn(0); 1492 } 1493 1494 #undef __FUNCT__ 1495 #define __FUNCT__ "MatSetValuesBlocked" 1496 /*@ 1497 MatSetValuesBlocked - Inserts or adds a block of values into a matrix. 1498 1499 Not Collective 1500 1501 Input Parameters: 1502 + mat - the matrix 1503 . v - a logically two-dimensional array of values 1504 . m, idxm - the number of block rows and their global block indices 1505 . n, idxn - the number of block columns and their global block indices 1506 - addv - either ADD_VALUES or INSERT_VALUES, where 1507 ADD_VALUES adds values to any existing entries, and 1508 INSERT_VALUES replaces existing entries with new values 1509 1510 Notes: 1511 If you create the matrix yourself (that is not with a call to DMCreateMatrix()) then you MUST call 1512 MatXXXXSetPreallocation() or MatSetUp() before using this routine. 1513 1514 The m and n count the NUMBER of blocks in the row direction and column direction, 1515 NOT the total number of rows/columns; for example, if the block size is 2 and 1516 you are passing in values for rows 2,3,4,5 then m would be 2 (not 4). 1517 The values in idxm would be 1 2; that is the first index for each block divided by 1518 the block size. 1519 1520 Note that you must call MatSetBlockSize() when constructing this matrix (after 1521 preallocating it). 1522 1523 By default the values, v, are row-oriented, so the layout of 1524 v is the same as for MatSetValues(). See MatSetOption() for other options. 1525 1526 Calls to MatSetValuesBlocked() with the INSERT_VALUES and ADD_VALUES 1527 options cannot be mixed without intervening calls to the assembly 1528 routines. 1529 1530 MatSetValuesBlocked() uses 0-based row and column numbers in Fortran 1531 as well as in C. 1532 1533 Negative indices may be passed in idxm and idxn, these rows and columns are 1534 simply ignored. This allows easily inserting element stiffness matrices 1535 with homogeneous Dirchlet boundary conditions that you don't want represented 1536 in the matrix. 1537 1538 Each time an entry is set within a sparse matrix via MatSetValues(), 1539 internal searching must be done to determine where to place the the 1540 data in the matrix storage space. By instead inserting blocks of 1541 entries via MatSetValuesBlocked(), the overhead of matrix assembly is 1542 reduced. 1543 1544 Example: 1545 $ Suppose m=n=2 and block size(bs) = 2 The array is 1546 $ 1547 $ 1 2 | 3 4 1548 $ 5 6 | 7 8 1549 $ - - - | - - - 1550 $ 9 10 | 11 12 1551 $ 13 14 | 15 16 1552 $ 1553 $ v[] should be passed in like 1554 $ v[] = [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16] 1555 $ 1556 $ If you are not using row oriented storage of v (that is you called MatSetOption(mat,MAT_ROW_ORIENTED,PETSC_FALSE)) then 1557 $ v[] = [1,5,9,13,2,6,10,14,3,7,11,15,4,8,12,16] 1558 1559 Level: intermediate 1560 1561 Concepts: matrices^putting entries in blocked 1562 1563 .seealso: MatSetBlockSize(), MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetValuesBlockedLocal() 1564 @*/ 1565 PetscErrorCode MatSetValuesBlocked(Mat mat,PetscInt m,const PetscInt idxm[],PetscInt n,const PetscInt idxn[],const PetscScalar v[],InsertMode addv) 1566 { 1567 PetscErrorCode ierr; 1568 1569 PetscFunctionBegin; 1570 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 1571 PetscValidType(mat,1); 1572 if (!m || !n) PetscFunctionReturn(0); /* no values to insert */ 1573 PetscValidIntPointer(idxm,3); 1574 PetscValidIntPointer(idxn,5); 1575 PetscValidScalarPointer(v,6); 1576 MatCheckPreallocated(mat,1); 1577 if (mat->insertmode == NOT_SET_VALUES) { 1578 mat->insertmode = addv; 1579 } 1580 #if defined(PETSC_USE_DEBUG) 1581 else if (mat->insertmode != addv) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values"); 1582 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 1583 if (!mat->ops->setvaluesblocked && !mat->ops->setvalues) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 1584 #endif 1585 1586 if (mat->assembled) { 1587 mat->was_assembled = PETSC_TRUE; 1588 mat->assembled = PETSC_FALSE; 1589 } 1590 ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 1591 if (mat->ops->setvaluesblocked) { 1592 ierr = (*mat->ops->setvaluesblocked)(mat,m,idxm,n,idxn,v,addv);CHKERRQ(ierr); 1593 } else { 1594 PetscInt buf[8192],*bufr=0,*bufc=0,*iidxm,*iidxn; 1595 PetscInt i,j,bs=mat->rmap->bs; 1596 if ((m+n)*bs <= (PetscInt)(sizeof(buf)/sizeof(PetscInt))) { 1597 iidxm = buf; iidxn = buf + m*bs; 1598 } else { 1599 ierr = PetscMalloc2(m*bs,PetscInt,&bufr,n*bs,PetscInt,&bufc);CHKERRQ(ierr); 1600 iidxm = bufr; iidxn = bufc; 1601 } 1602 for (i=0; i<m; i++) { 1603 for (j=0; j<bs; j++) { 1604 iidxm[i*bs+j] = bs*idxm[i] + j; 1605 } 1606 } 1607 for (i=0; i<n; i++) { 1608 for (j=0; j<bs; j++) { 1609 iidxn[i*bs+j] = bs*idxn[i] + j; 1610 } 1611 } 1612 ierr = MatSetValues(mat,m*bs,iidxm,n*bs,iidxn,v,addv);CHKERRQ(ierr); 1613 ierr = PetscFree2(bufr,bufc);CHKERRQ(ierr); 1614 } 1615 ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 1616 #if defined(PETSC_HAVE_CUSP) 1617 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 1618 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 1619 } 1620 #endif 1621 PetscFunctionReturn(0); 1622 } 1623 1624 #undef __FUNCT__ 1625 #define __FUNCT__ "MatGetValues" 1626 /*@ 1627 MatGetValues - Gets a block of values from a matrix. 1628 1629 Not Collective; currently only returns a local block 1630 1631 Input Parameters: 1632 + mat - the matrix 1633 . v - a logically two-dimensional array for storing the values 1634 . m, idxm - the number of rows and their global indices 1635 - n, idxn - the number of columns and their global indices 1636 1637 Notes: 1638 The user must allocate space (m*n PetscScalars) for the values, v. 1639 The values, v, are then returned in a row-oriented format, 1640 analogous to that used by default in MatSetValues(). 1641 1642 MatGetValues() uses 0-based row and column numbers in 1643 Fortran as well as in C. 1644 1645 MatGetValues() requires that the matrix has been assembled 1646 with MatAssemblyBegin()/MatAssemblyEnd(). Thus, calls to 1647 MatSetValues() and MatGetValues() CANNOT be made in succession 1648 without intermediate matrix assembly. 1649 1650 Negative row or column indices will be ignored and those locations in v[] will be 1651 left unchanged. 1652 1653 Level: advanced 1654 1655 Concepts: matrices^accessing values 1656 1657 .seealso: MatGetRow(), MatGetSubMatrices(), MatSetValues() 1658 @*/ 1659 PetscErrorCode MatGetValues(Mat mat,PetscInt m,const PetscInt idxm[],PetscInt n,const PetscInt idxn[],PetscScalar v[]) 1660 { 1661 PetscErrorCode ierr; 1662 1663 PetscFunctionBegin; 1664 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 1665 PetscValidType(mat,1); 1666 if (!m || !n) PetscFunctionReturn(0); 1667 PetscValidIntPointer(idxm,3); 1668 PetscValidIntPointer(idxn,5); 1669 PetscValidScalarPointer(v,6); 1670 if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 1671 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 1672 if (!mat->ops->getvalues) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 1673 MatCheckPreallocated(mat,1); 1674 1675 ierr = PetscLogEventBegin(MAT_GetValues,mat,0,0,0);CHKERRQ(ierr); 1676 ierr = (*mat->ops->getvalues)(mat,m,idxm,n,idxn,v);CHKERRQ(ierr); 1677 ierr = PetscLogEventEnd(MAT_GetValues,mat,0,0,0);CHKERRQ(ierr); 1678 PetscFunctionReturn(0); 1679 } 1680 1681 #undef __FUNCT__ 1682 #define __FUNCT__ "MatSetValuesBatch" 1683 /*@ 1684 MatSetValuesBatch - Adds (ADD_VALUES) many blocks of values into a matrix at once. The blocks must all be square and 1685 the same size. Currently, this can only be called once and creates the given matrix. 1686 1687 Not Collective 1688 1689 Input Parameters: 1690 + mat - the matrix 1691 . nb - the number of blocks 1692 . bs - the number of rows (and columns) in each block 1693 . rows - a concatenation of the rows for each block 1694 - v - a concatenation of logically two-dimensional arrays of values 1695 1696 Notes: 1697 In the future, we will extend this routine to handle rectangular blocks, and to allow multiple calls for a given matrix. 1698 1699 Level: advanced 1700 1701 Concepts: matrices^putting entries in 1702 1703 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(), 1704 InsertMode, INSERT_VALUES, ADD_VALUES, MatSetValues() 1705 @*/ 1706 PetscErrorCode MatSetValuesBatch(Mat mat, PetscInt nb, PetscInt bs, PetscInt rows[], const PetscScalar v[]) 1707 { 1708 PetscErrorCode ierr; 1709 1710 PetscFunctionBegin; 1711 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 1712 PetscValidType(mat,1); 1713 PetscValidScalarPointer(rows,4); 1714 PetscValidScalarPointer(v,5); 1715 #if defined(PETSC_USE_DEBUG) 1716 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 1717 #endif 1718 1719 ierr = PetscLogEventBegin(MAT_SetValuesBatch,mat,0,0,0);CHKERRQ(ierr); 1720 if (mat->ops->setvaluesbatch) { 1721 ierr = (*mat->ops->setvaluesbatch)(mat,nb,bs,rows,v);CHKERRQ(ierr); 1722 } else { 1723 PetscInt b; 1724 for (b = 0; b < nb; ++b) { 1725 ierr = MatSetValues(mat, bs, &rows[b*bs], bs, &rows[b*bs], &v[b*bs*bs], ADD_VALUES);CHKERRQ(ierr); 1726 } 1727 } 1728 ierr = PetscLogEventEnd(MAT_SetValuesBatch,mat,0,0,0);CHKERRQ(ierr); 1729 PetscFunctionReturn(0); 1730 } 1731 1732 #undef __FUNCT__ 1733 #define __FUNCT__ "MatSetLocalToGlobalMapping" 1734 /*@ 1735 MatSetLocalToGlobalMapping - Sets a local-to-global numbering for use by 1736 the routine MatSetValuesLocal() to allow users to insert matrix entries 1737 using a local (per-processor) numbering. 1738 1739 Not Collective 1740 1741 Input Parameters: 1742 + x - the matrix 1743 . rmapping - row mapping created with ISLocalToGlobalMappingCreate() 1744 or ISLocalToGlobalMappingCreateIS() 1745 - cmapping - column mapping 1746 1747 Level: intermediate 1748 1749 Concepts: matrices^local to global mapping 1750 Concepts: local to global mapping^for matrices 1751 1752 .seealso: MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetValuesLocal() 1753 @*/ 1754 PetscErrorCode MatSetLocalToGlobalMapping(Mat x,ISLocalToGlobalMapping rmapping,ISLocalToGlobalMapping cmapping) 1755 { 1756 PetscErrorCode ierr; 1757 1758 PetscFunctionBegin; 1759 PetscValidHeaderSpecific(x,MAT_CLASSID,1); 1760 PetscValidType(x,1); 1761 PetscValidHeaderSpecific(rmapping,IS_LTOGM_CLASSID,2); 1762 PetscValidHeaderSpecific(cmapping,IS_LTOGM_CLASSID,3); 1763 1764 if (x->ops->setlocaltoglobalmapping) { 1765 ierr = (*x->ops->setlocaltoglobalmapping)(x,rmapping,cmapping);CHKERRQ(ierr); 1766 } else { 1767 ierr = PetscLayoutSetISLocalToGlobalMapping(x->rmap,rmapping);CHKERRQ(ierr); 1768 ierr = PetscLayoutSetISLocalToGlobalMapping(x->cmap,cmapping);CHKERRQ(ierr); 1769 } 1770 PetscFunctionReturn(0); 1771 } 1772 1773 #undef __FUNCT__ 1774 #define __FUNCT__ "MatSetLocalToGlobalMappingBlock" 1775 /*@ 1776 MatSetLocalToGlobalMappingBlock - Sets a local-to-global numbering for use 1777 by the routine MatSetValuesBlockedLocal() to allow users to insert matrix 1778 entries using a local (per-processor) numbering. 1779 1780 Not Collective 1781 1782 Input Parameters: 1783 + x - the matrix 1784 . rmapping - row mapping created with ISLocalToGlobalMappingCreate() or 1785 ISLocalToGlobalMappingCreateIS() 1786 - cmapping - column mapping 1787 1788 Level: intermediate 1789 1790 Concepts: matrices^local to global mapping blocked 1791 Concepts: local to global mapping^for matrices, blocked 1792 1793 .seealso: MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetValuesBlockedLocal(), 1794 MatSetValuesBlocked(), MatSetValuesLocal() 1795 @*/ 1796 PetscErrorCode MatSetLocalToGlobalMappingBlock(Mat x,ISLocalToGlobalMapping rmapping,ISLocalToGlobalMapping cmapping) 1797 { 1798 PetscErrorCode ierr; 1799 1800 PetscFunctionBegin; 1801 PetscValidHeaderSpecific(x,MAT_CLASSID,1); 1802 PetscValidType(x,1); 1803 PetscValidHeaderSpecific(rmapping,IS_LTOGM_CLASSID,2); 1804 PetscValidHeaderSpecific(cmapping,IS_LTOGM_CLASSID,3); 1805 1806 ierr = PetscLayoutSetISLocalToGlobalMappingBlock(x->rmap,rmapping);CHKERRQ(ierr); 1807 ierr = PetscLayoutSetISLocalToGlobalMappingBlock(x->cmap,cmapping);CHKERRQ(ierr); 1808 PetscFunctionReturn(0); 1809 } 1810 1811 #undef __FUNCT__ 1812 #define __FUNCT__ "MatGetLocalToGlobalMapping" 1813 /*@ 1814 MatGetLocalToGlobalMapping - Gets the local-to-global numbering set by MatSetLocalToGlobalMapping() 1815 1816 Not Collective 1817 1818 Input Parameters: 1819 . A - the matrix 1820 1821 Output Parameters: 1822 + rmapping - row mapping 1823 - cmapping - column mapping 1824 1825 Level: advanced 1826 1827 Concepts: matrices^local to global mapping 1828 Concepts: local to global mapping^for matrices 1829 1830 .seealso: MatSetValuesLocal(), MatGetLocalToGlobalMappingBlock() 1831 @*/ 1832 PetscErrorCode MatGetLocalToGlobalMapping(Mat A,ISLocalToGlobalMapping *rmapping,ISLocalToGlobalMapping *cmapping) 1833 { 1834 PetscFunctionBegin; 1835 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 1836 PetscValidType(A,1); 1837 if (rmapping) PetscValidPointer(rmapping,2); 1838 if (cmapping) PetscValidPointer(cmapping,3); 1839 if (rmapping) *rmapping = A->rmap->mapping; 1840 if (cmapping) *cmapping = A->cmap->mapping; 1841 PetscFunctionReturn(0); 1842 } 1843 1844 #undef __FUNCT__ 1845 #define __FUNCT__ "MatGetLocalToGlobalMappingBlock" 1846 /*@ 1847 MatGetLocalToGlobalMappingBlock - Gets the local-to-global numbering set by MatSetLocalToGlobalMappingBlock() 1848 1849 Not Collective 1850 1851 Input Parameters: 1852 . A - the matrix 1853 1854 Output Parameters: 1855 + rmapping - row mapping 1856 - cmapping - column mapping 1857 1858 Level: advanced 1859 1860 Concepts: matrices^local to global mapping blocked 1861 Concepts: local to global mapping^for matrices, blocked 1862 1863 .seealso: MatSetValuesBlockedLocal(), MatGetLocalToGlobalMapping() 1864 @*/ 1865 PetscErrorCode MatGetLocalToGlobalMappingBlock(Mat A,ISLocalToGlobalMapping *rmapping,ISLocalToGlobalMapping *cmapping) 1866 { 1867 PetscFunctionBegin; 1868 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 1869 PetscValidType(A,1); 1870 if (rmapping) PetscValidPointer(rmapping,2); 1871 if (cmapping) PetscValidPointer(cmapping,3); 1872 if (rmapping) *rmapping = A->rmap->bmapping; 1873 if (cmapping) *cmapping = A->cmap->bmapping; 1874 PetscFunctionReturn(0); 1875 } 1876 1877 #undef __FUNCT__ 1878 #define __FUNCT__ "MatSetValuesLocal" 1879 /*@ 1880 MatSetValuesLocal - Inserts or adds values into certain locations of a matrix, 1881 using a local ordering of the nodes. 1882 1883 Not Collective 1884 1885 Input Parameters: 1886 + x - the matrix 1887 . nrow, irow - number of rows and their local indices 1888 . ncol, icol - number of columns and their local indices 1889 . y - a logically two-dimensional array of values 1890 - addv - either INSERT_VALUES or ADD_VALUES, where 1891 ADD_VALUES adds values to any existing entries, and 1892 INSERT_VALUES replaces existing entries with new values 1893 1894 Notes: 1895 If you create the matrix yourself (that is not with a call to DMCreateMatrix()) then you MUST call MatXXXXSetPreallocation() or 1896 MatSetUp() before using this routine 1897 1898 If you create the matrix yourself (that is not with a call to DMCreateMatrix()) then you MUST call MatSetLocalToGlobalMapping() before using this routine 1899 1900 Calls to MatSetValuesLocal() with the INSERT_VALUES and ADD_VALUES 1901 options cannot be mixed without intervening calls to the assembly 1902 routines. 1903 1904 These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd() 1905 MUST be called after all calls to MatSetValuesLocal() have been completed. 1906 1907 Level: intermediate 1908 1909 Concepts: matrices^putting entries in with local numbering 1910 1911 .seealso: MatAssemblyBegin(), MatAssemblyEnd(), MatSetValues(), MatSetLocalToGlobalMapping(), 1912 MatSetValueLocal() 1913 @*/ 1914 PetscErrorCode MatSetValuesLocal(Mat mat,PetscInt nrow,const PetscInt irow[],PetscInt ncol,const PetscInt icol[],const PetscScalar y[],InsertMode addv) 1915 { 1916 PetscErrorCode ierr; 1917 1918 PetscFunctionBegin; 1919 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 1920 PetscValidType(mat,1); 1921 MatCheckPreallocated(mat,1); 1922 if (!nrow || !ncol) PetscFunctionReturn(0); /* no values to insert */ 1923 PetscValidIntPointer(irow,3); 1924 PetscValidIntPointer(icol,5); 1925 PetscValidScalarPointer(y,6); 1926 if (mat->insertmode == NOT_SET_VALUES) { 1927 mat->insertmode = addv; 1928 } 1929 #if defined(PETSC_USE_DEBUG) 1930 else if (mat->insertmode != addv) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values"); 1931 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 1932 if (!mat->ops->setvalueslocal && !mat->ops->setvalues) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 1933 #endif 1934 1935 if (mat->assembled) { 1936 mat->was_assembled = PETSC_TRUE; 1937 mat->assembled = PETSC_FALSE; 1938 } 1939 ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 1940 if (mat->ops->setvalueslocal) { 1941 ierr = (*mat->ops->setvalueslocal)(mat,nrow,irow,ncol,icol,y,addv);CHKERRQ(ierr); 1942 } else { 1943 PetscInt buf[8192],*bufr=0,*bufc=0,*irowm,*icolm; 1944 if ((nrow+ncol) <= (PetscInt)(sizeof(buf)/sizeof(PetscInt))) { 1945 irowm = buf; icolm = buf+nrow; 1946 } else { 1947 ierr = PetscMalloc2(nrow,PetscInt,&bufr,ncol,PetscInt,&bufc);CHKERRQ(ierr); 1948 irowm = bufr; icolm = bufc; 1949 } 1950 ierr = ISLocalToGlobalMappingApply(mat->rmap->mapping,nrow,irow,irowm);CHKERRQ(ierr); 1951 ierr = ISLocalToGlobalMappingApply(mat->cmap->mapping,ncol,icol,icolm);CHKERRQ(ierr); 1952 ierr = MatSetValues(mat,nrow,irowm,ncol,icolm,y,addv);CHKERRQ(ierr); 1953 ierr = PetscFree2(bufr,bufc);CHKERRQ(ierr); 1954 } 1955 ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 1956 #if defined(PETSC_HAVE_CUSP) 1957 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 1958 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 1959 } 1960 #endif 1961 PetscFunctionReturn(0); 1962 } 1963 1964 #undef __FUNCT__ 1965 #define __FUNCT__ "MatSetValuesBlockedLocal" 1966 /*@ 1967 MatSetValuesBlockedLocal - Inserts or adds values into certain locations of a matrix, 1968 using a local ordering of the nodes a block at a time. 1969 1970 Not Collective 1971 1972 Input Parameters: 1973 + x - the matrix 1974 . nrow, irow - number of rows and their local indices 1975 . ncol, icol - number of columns and their local indices 1976 . y - a logically two-dimensional array of values 1977 - addv - either INSERT_VALUES or ADD_VALUES, where 1978 ADD_VALUES adds values to any existing entries, and 1979 INSERT_VALUES replaces existing entries with new values 1980 1981 Notes: 1982 If you create the matrix yourself (that is not with a call to DMCreateMatrix()) then you MUST call MatXXXXSetPreallocation() or 1983 MatSetUp() before using this routine 1984 1985 If you create the matrix yourself (that is not with a call to DMCreateMatrix()) then you MUST call MatSetBlockSize() and MatSetLocalToGlobalMappingBlock() 1986 before using this routineBefore calling MatSetValuesLocal(), the user must first set the 1987 1988 Calls to MatSetValuesBlockedLocal() with the INSERT_VALUES and ADD_VALUES 1989 options cannot be mixed without intervening calls to the assembly 1990 routines. 1991 1992 These values may be cached, so MatAssemblyBegin() and MatAssemblyEnd() 1993 MUST be called after all calls to MatSetValuesBlockedLocal() have been completed. 1994 1995 Level: intermediate 1996 1997 Concepts: matrices^putting blocked values in with local numbering 1998 1999 .seealso: MatSetBlockSize(), MatSetLocalToGlobalMappingBlock(), MatAssemblyBegin(), MatAssemblyEnd(), 2000 MatSetValuesLocal(), MatSetLocalToGlobalMappingBlock(), MatSetValuesBlocked() 2001 @*/ 2002 PetscErrorCode MatSetValuesBlockedLocal(Mat mat,PetscInt nrow,const PetscInt irow[],PetscInt ncol,const PetscInt icol[],const PetscScalar y[],InsertMode addv) 2003 { 2004 PetscErrorCode ierr; 2005 2006 PetscFunctionBegin; 2007 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2008 PetscValidType(mat,1); 2009 MatCheckPreallocated(mat,1); 2010 if (!nrow || !ncol) PetscFunctionReturn(0); /* no values to insert */ 2011 PetscValidIntPointer(irow,3); 2012 PetscValidIntPointer(icol,5); 2013 PetscValidScalarPointer(y,6); 2014 if (mat->insertmode == NOT_SET_VALUES) { 2015 mat->insertmode = addv; 2016 } 2017 #if defined(PETSC_USE_DEBUG) 2018 else if (mat->insertmode != addv) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Cannot mix add values and insert values"); 2019 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2020 if (!mat->ops->setvaluesblockedlocal && !mat->ops->setvaluesblocked && !mat->ops->setvalueslocal && !mat->ops->setvalues) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 2021 #endif 2022 2023 if (mat->assembled) { 2024 mat->was_assembled = PETSC_TRUE; 2025 mat->assembled = PETSC_FALSE; 2026 } 2027 ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 2028 if (mat->ops->setvaluesblockedlocal) { 2029 ierr = (*mat->ops->setvaluesblockedlocal)(mat,nrow,irow,ncol,icol,y,addv);CHKERRQ(ierr); 2030 } else { 2031 PetscInt buf[8192],*bufr=0,*bufc=0,*irowm,*icolm; 2032 if (mat->rmap->bmapping && mat->cmap->bmapping) { 2033 if ((nrow+ncol) <= (PetscInt)(sizeof(buf)/sizeof(PetscInt))) { 2034 irowm = buf; icolm = buf + nrow; 2035 } else { 2036 ierr = PetscMalloc2(nrow,PetscInt,&bufr,ncol,PetscInt,&bufc);CHKERRQ(ierr); 2037 irowm = bufr; icolm = bufc; 2038 } 2039 ierr = ISLocalToGlobalMappingApply(mat->rmap->bmapping,nrow,irow,irowm);CHKERRQ(ierr); 2040 ierr = ISLocalToGlobalMappingApply(mat->cmap->bmapping,ncol,icol,icolm);CHKERRQ(ierr); 2041 ierr = MatSetValuesBlocked(mat,nrow,irowm,ncol,icolm,y,addv);CHKERRQ(ierr); 2042 ierr = PetscFree2(bufr,bufc);CHKERRQ(ierr); 2043 } else { 2044 PetscInt i,j,bs=mat->rmap->bs; 2045 if ((nrow+ncol)*bs <=(PetscInt)(sizeof(buf)/sizeof(PetscInt))) { 2046 irowm = buf; icolm = buf + nrow; 2047 } else { 2048 ierr = PetscMalloc2(nrow*bs,PetscInt,&bufr,ncol*bs,PetscInt,&bufc);CHKERRQ(ierr); 2049 irowm = bufr; icolm = bufc; 2050 } 2051 for (i=0; i<nrow; i++) { 2052 for (j=0; j<bs; j++) irowm[i*bs+j] = irow[i]*bs+j; 2053 } 2054 for (i=0; i<ncol; i++) { 2055 for (j=0; j<bs; j++) icolm[i*bs+j] = icol[i]*bs+j; 2056 } 2057 ierr = MatSetValuesLocal(mat,nrow*bs,irowm,ncol*bs,icolm,y,addv);CHKERRQ(ierr); 2058 ierr = PetscFree2(bufr,bufc);CHKERRQ(ierr); 2059 } 2060 } 2061 ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 2062 #if defined(PETSC_HAVE_CUSP) 2063 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 2064 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 2065 } 2066 #endif 2067 PetscFunctionReturn(0); 2068 } 2069 2070 #undef __FUNCT__ 2071 #define __FUNCT__ "MatMultDiagonalBlock" 2072 /*@ 2073 MatMultDiagonalBlock - Computes the matrix-vector product, y = Dx. Where D is defined by the inode or block structure of the diagonal 2074 2075 Collective on Mat and Vec 2076 2077 Input Parameters: 2078 + mat - the matrix 2079 - x - the vector to be multiplied 2080 2081 Output Parameters: 2082 . y - the result 2083 2084 Notes: 2085 The vectors x and y cannot be the same. I.e., one cannot 2086 call MatMult(A,y,y). 2087 2088 Level: developer 2089 2090 Concepts: matrix-vector product 2091 2092 .seealso: MatMultTranspose(), MatMultAdd(), MatMultTransposeAdd() 2093 @*/ 2094 PetscErrorCode MatMultDiagonalBlock(Mat mat,Vec x,Vec y) 2095 { 2096 PetscErrorCode ierr; 2097 2098 PetscFunctionBegin; 2099 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2100 PetscValidType(mat,1); 2101 PetscValidHeaderSpecific(x,VEC_CLASSID,2); 2102 PetscValidHeaderSpecific(y,VEC_CLASSID,3); 2103 2104 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2105 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2106 if (x == y) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors"); 2107 MatCheckPreallocated(mat,1); 2108 2109 if (!mat->ops->multdiagonalblock) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"This matrix type does not have a multiply defined"); 2110 ierr = (*mat->ops->multdiagonalblock)(mat,x,y);CHKERRQ(ierr); 2111 ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr); 2112 PetscFunctionReturn(0); 2113 } 2114 2115 /* --------------------------------------------------------*/ 2116 #undef __FUNCT__ 2117 #define __FUNCT__ "MatMult" 2118 /*@ 2119 MatMult - Computes the matrix-vector product, y = Ax. 2120 2121 Neighbor-wise Collective on Mat and Vec 2122 2123 Input Parameters: 2124 + mat - the matrix 2125 - x - the vector to be multiplied 2126 2127 Output Parameters: 2128 . y - the result 2129 2130 Notes: 2131 The vectors x and y cannot be the same. I.e., one cannot 2132 call MatMult(A,y,y). 2133 2134 Level: beginner 2135 2136 Concepts: matrix-vector product 2137 2138 .seealso: MatMultTranspose(), MatMultAdd(), MatMultTransposeAdd() 2139 @*/ 2140 PetscErrorCode MatMult(Mat mat,Vec x,Vec y) 2141 { 2142 PetscErrorCode ierr; 2143 2144 PetscFunctionBegin; 2145 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2146 PetscValidType(mat,1); 2147 PetscValidHeaderSpecific(x,VEC_CLASSID,2); 2148 PetscValidHeaderSpecific(y,VEC_CLASSID,3); 2149 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2150 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2151 if (x == y) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors"); 2152 #if !defined(PETSC_HAVE_CONSTRAINTS) 2153 if (mat->cmap->N != x->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N); 2154 if (mat->rmap->N != y->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->rmap->N,y->map->N); 2155 if (mat->rmap->n != y->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: local dim %D %D",mat->rmap->n,y->map->n); 2156 #endif 2157 VecValidValues(x,2,PETSC_TRUE); 2158 MatCheckPreallocated(mat,1); 2159 2160 if (!mat->ops->mult) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"This matrix type does not have a multiply defined"); 2161 ierr = PetscLogEventBegin(MAT_Mult,mat,x,y,0);CHKERRQ(ierr); 2162 ierr = (*mat->ops->mult)(mat,x,y);CHKERRQ(ierr); 2163 ierr = PetscLogEventEnd(MAT_Mult,mat,x,y,0);CHKERRQ(ierr); 2164 VecValidValues(y,3,PETSC_FALSE); 2165 PetscFunctionReturn(0); 2166 } 2167 2168 #undef __FUNCT__ 2169 #define __FUNCT__ "MatMultTranspose" 2170 /*@ 2171 MatMultTranspose - Computes matrix transpose times a vector. 2172 2173 Neighbor-wise Collective on Mat and Vec 2174 2175 Input Parameters: 2176 + mat - the matrix 2177 - x - the vector to be multilplied 2178 2179 Output Parameters: 2180 . y - the result 2181 2182 Notes: 2183 The vectors x and y cannot be the same. I.e., one cannot 2184 call MatMultTranspose(A,y,y). 2185 2186 For complex numbers this does NOT compute the Hermitian (complex conjugate) transpose multiple, 2187 use MatMultHermitianTranspose() 2188 2189 Level: beginner 2190 2191 Concepts: matrix vector product^transpose 2192 2193 .seealso: MatMult(), MatMultAdd(), MatMultTransposeAdd(), MatMultHermitianTranspose(), MatTranspose() 2194 @*/ 2195 PetscErrorCode MatMultTranspose(Mat mat,Vec x,Vec y) 2196 { 2197 PetscErrorCode ierr; 2198 2199 PetscFunctionBegin; 2200 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2201 PetscValidType(mat,1); 2202 PetscValidHeaderSpecific(x,VEC_CLASSID,2); 2203 PetscValidHeaderSpecific(y,VEC_CLASSID,3); 2204 2205 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2206 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2207 if (x == y) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors"); 2208 #if !defined(PETSC_HAVE_CONSTRAINTS) 2209 if (mat->rmap->N != x->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->rmap->N,x->map->N); 2210 if (mat->cmap->N != y->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->cmap->N,y->map->N); 2211 #endif 2212 VecValidValues(x,2,PETSC_TRUE); 2213 MatCheckPreallocated(mat,1); 2214 2215 if (!mat->ops->multtranspose) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"This matrix type does not have a multiply tranpose defined"); 2216 ierr = PetscLogEventBegin(MAT_MultTranspose,mat,x,y,0);CHKERRQ(ierr); 2217 ierr = (*mat->ops->multtranspose)(mat,x,y);CHKERRQ(ierr); 2218 ierr = PetscLogEventEnd(MAT_MultTranspose,mat,x,y,0);CHKERRQ(ierr); 2219 ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr); 2220 VecValidValues(y,3,PETSC_FALSE); 2221 PetscFunctionReturn(0); 2222 } 2223 2224 #undef __FUNCT__ 2225 #define __FUNCT__ "MatMultHermitianTranspose" 2226 /*@ 2227 MatMultHermitianTranspose - Computes matrix Hermitian transpose times a vector. 2228 2229 Neighbor-wise Collective on Mat and Vec 2230 2231 Input Parameters: 2232 + mat - the matrix 2233 - x - the vector to be multilplied 2234 2235 Output Parameters: 2236 . y - the result 2237 2238 Notes: 2239 The vectors x and y cannot be the same. I.e., one cannot 2240 call MatMultHermitianTranspose(A,y,y). 2241 2242 Also called the conjugate transpose, complex conjugate transpose, or adjoint. 2243 2244 For real numbers MatMultTranspose() and MatMultHermitianTranspose() are identical. 2245 2246 Level: beginner 2247 2248 Concepts: matrix vector product^transpose 2249 2250 .seealso: MatMult(), MatMultAdd(), MatMultHermitianTransposeAdd(), MatMultTranspose() 2251 @*/ 2252 PetscErrorCode MatMultHermitianTranspose(Mat mat,Vec x,Vec y) 2253 { 2254 PetscErrorCode ierr; 2255 Vec w; 2256 2257 PetscFunctionBegin; 2258 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2259 PetscValidType(mat,1); 2260 PetscValidHeaderSpecific(x,VEC_CLASSID,2); 2261 PetscValidHeaderSpecific(y,VEC_CLASSID,3); 2262 2263 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2264 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2265 if (x == y) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors"); 2266 #if !defined(PETSC_HAVE_CONSTRAINTS) 2267 if (mat->rmap->N != x->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->rmap->N,x->map->N); 2268 if (mat->cmap->N != y->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->cmap->N,y->map->N); 2269 #endif 2270 MatCheckPreallocated(mat,1); 2271 2272 ierr = PetscLogEventBegin(MAT_MultHermitianTranspose,mat,x,y,0);CHKERRQ(ierr); 2273 if (mat->ops->multhermitiantranspose) { 2274 ierr = (*mat->ops->multhermitiantranspose)(mat,x,y);CHKERRQ(ierr); 2275 } else { 2276 ierr = VecDuplicate(x,&w);CHKERRQ(ierr); 2277 ierr = VecCopy(x,w);CHKERRQ(ierr); 2278 ierr = VecConjugate(w);CHKERRQ(ierr); 2279 ierr = MatMultTranspose(mat,w,y);CHKERRQ(ierr); 2280 ierr = VecDestroy(&w);CHKERRQ(ierr); 2281 ierr = VecConjugate(y);CHKERRQ(ierr); 2282 } 2283 ierr = PetscLogEventEnd(MAT_MultHermitianTranspose,mat,x,y,0);CHKERRQ(ierr); 2284 ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr); 2285 PetscFunctionReturn(0); 2286 } 2287 2288 #undef __FUNCT__ 2289 #define __FUNCT__ "MatMultAdd" 2290 /*@ 2291 MatMultAdd - Computes v3 = v2 + A * v1. 2292 2293 Neighbor-wise Collective on Mat and Vec 2294 2295 Input Parameters: 2296 + mat - the matrix 2297 - v1, v2 - the vectors 2298 2299 Output Parameters: 2300 . v3 - the result 2301 2302 Notes: 2303 The vectors v1 and v3 cannot be the same. I.e., one cannot 2304 call MatMultAdd(A,v1,v2,v1). 2305 2306 Level: beginner 2307 2308 Concepts: matrix vector product^addition 2309 2310 .seealso: MatMultTranspose(), MatMult(), MatMultTransposeAdd() 2311 @*/ 2312 PetscErrorCode MatMultAdd(Mat mat,Vec v1,Vec v2,Vec v3) 2313 { 2314 PetscErrorCode ierr; 2315 2316 PetscFunctionBegin; 2317 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2318 PetscValidType(mat,1); 2319 PetscValidHeaderSpecific(v1,VEC_CLASSID,2); 2320 PetscValidHeaderSpecific(v2,VEC_CLASSID,3); 2321 PetscValidHeaderSpecific(v3,VEC_CLASSID,4); 2322 2323 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2324 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2325 if (mat->cmap->N != v1->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec v1: global dim %D %D",mat->cmap->N,v1->map->N); 2326 /* if (mat->rmap->N != v2->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: global dim %D %D",mat->rmap->N,v2->map->N); 2327 if (mat->rmap->N != v3->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: global dim %D %D",mat->rmap->N,v3->map->N); */ 2328 if (mat->rmap->n != v3->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: local dim %D %D",mat->rmap->n,v3->map->n); 2329 if (mat->rmap->n != v2->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: local dim %D %D",mat->rmap->n,v2->map->n); 2330 if (v1 == v3) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_IDN,"v1 and v3 must be different vectors"); 2331 MatCheckPreallocated(mat,1); 2332 2333 if (!mat->ops->multadd) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"No MatMultAdd() for matrix type '%s'",((PetscObject)mat)->type_name); 2334 ierr = PetscLogEventBegin(MAT_MultAdd,mat,v1,v2,v3);CHKERRQ(ierr); 2335 ierr = (*mat->ops->multadd)(mat,v1,v2,v3);CHKERRQ(ierr); 2336 ierr = PetscLogEventEnd(MAT_MultAdd,mat,v1,v2,v3);CHKERRQ(ierr); 2337 ierr = PetscObjectStateIncrease((PetscObject)v3);CHKERRQ(ierr); 2338 PetscFunctionReturn(0); 2339 } 2340 2341 #undef __FUNCT__ 2342 #define __FUNCT__ "MatMultTransposeAdd" 2343 /*@ 2344 MatMultTransposeAdd - Computes v3 = v2 + A' * v1. 2345 2346 Neighbor-wise Collective on Mat and Vec 2347 2348 Input Parameters: 2349 + mat - the matrix 2350 - v1, v2 - the vectors 2351 2352 Output Parameters: 2353 . v3 - the result 2354 2355 Notes: 2356 The vectors v1 and v3 cannot be the same. I.e., one cannot 2357 call MatMultTransposeAdd(A,v1,v2,v1). 2358 2359 Level: beginner 2360 2361 Concepts: matrix vector product^transpose and addition 2362 2363 .seealso: MatMultTranspose(), MatMultAdd(), MatMult() 2364 @*/ 2365 PetscErrorCode MatMultTransposeAdd(Mat mat,Vec v1,Vec v2,Vec v3) 2366 { 2367 PetscErrorCode ierr; 2368 2369 PetscFunctionBegin; 2370 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2371 PetscValidType(mat,1); 2372 PetscValidHeaderSpecific(v1,VEC_CLASSID,2); 2373 PetscValidHeaderSpecific(v2,VEC_CLASSID,3); 2374 PetscValidHeaderSpecific(v3,VEC_CLASSID,4); 2375 2376 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2377 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2378 if (!mat->ops->multtransposeadd) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 2379 if (v1 == v3) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_IDN,"v1 and v3 must be different vectors"); 2380 if (mat->rmap->N != v1->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec v1: global dim %D %D",mat->rmap->N,v1->map->N); 2381 if (mat->cmap->N != v2->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: global dim %D %D",mat->cmap->N,v2->map->N); 2382 if (mat->cmap->N != v3->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: global dim %D %D",mat->cmap->N,v3->map->N); 2383 MatCheckPreallocated(mat,1); 2384 2385 ierr = PetscLogEventBegin(MAT_MultTransposeAdd,mat,v1,v2,v3);CHKERRQ(ierr); 2386 ierr = (*mat->ops->multtransposeadd)(mat,v1,v2,v3);CHKERRQ(ierr); 2387 ierr = PetscLogEventEnd(MAT_MultTransposeAdd,mat,v1,v2,v3);CHKERRQ(ierr); 2388 ierr = PetscObjectStateIncrease((PetscObject)v3);CHKERRQ(ierr); 2389 PetscFunctionReturn(0); 2390 } 2391 2392 #undef __FUNCT__ 2393 #define __FUNCT__ "MatMultHermitianTransposeAdd" 2394 /*@ 2395 MatMultHermitianTransposeAdd - Computes v3 = v2 + A^H * v1. 2396 2397 Neighbor-wise Collective on Mat and Vec 2398 2399 Input Parameters: 2400 + mat - the matrix 2401 - v1, v2 - the vectors 2402 2403 Output Parameters: 2404 . v3 - the result 2405 2406 Notes: 2407 The vectors v1 and v3 cannot be the same. I.e., one cannot 2408 call MatMultHermitianTransposeAdd(A,v1,v2,v1). 2409 2410 Level: beginner 2411 2412 Concepts: matrix vector product^transpose and addition 2413 2414 .seealso: MatMultHermitianTranspose(), MatMultTranspose(), MatMultAdd(), MatMult() 2415 @*/ 2416 PetscErrorCode MatMultHermitianTransposeAdd(Mat mat,Vec v1,Vec v2,Vec v3) 2417 { 2418 PetscErrorCode ierr; 2419 2420 PetscFunctionBegin; 2421 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2422 PetscValidType(mat,1); 2423 PetscValidHeaderSpecific(v1,VEC_CLASSID,2); 2424 PetscValidHeaderSpecific(v2,VEC_CLASSID,3); 2425 PetscValidHeaderSpecific(v3,VEC_CLASSID,4); 2426 2427 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2428 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2429 if (!mat->ops->multhermitiantransposeadd) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 2430 if (v1 == v3) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_IDN,"v1 and v3 must be different vectors"); 2431 if (mat->rmap->N != v1->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec v1: global dim %D %D",mat->rmap->N,v1->map->N); 2432 if (mat->cmap->N != v2->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec v2: global dim %D %D",mat->cmap->N,v2->map->N); 2433 if (mat->cmap->N != v3->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec v3: global dim %D %D",mat->cmap->N,v3->map->N); 2434 MatCheckPreallocated(mat,1); 2435 2436 ierr = PetscLogEventBegin(MAT_MultHermitianTransposeAdd,mat,v1,v2,v3);CHKERRQ(ierr); 2437 ierr = (*mat->ops->multhermitiantransposeadd)(mat,v1,v2,v3);CHKERRQ(ierr); 2438 ierr = PetscLogEventEnd(MAT_MultHermitianTransposeAdd,mat,v1,v2,v3);CHKERRQ(ierr); 2439 ierr = PetscObjectStateIncrease((PetscObject)v3);CHKERRQ(ierr); 2440 PetscFunctionReturn(0); 2441 } 2442 2443 #undef __FUNCT__ 2444 #define __FUNCT__ "MatMultConstrained" 2445 /*@ 2446 MatMultConstrained - The inner multiplication routine for a 2447 constrained matrix P^T A P. 2448 2449 Neighbor-wise Collective on Mat and Vec 2450 2451 Input Parameters: 2452 + mat - the matrix 2453 - x - the vector to be multilplied 2454 2455 Output Parameters: 2456 . y - the result 2457 2458 Notes: 2459 The vectors x and y cannot be the same. I.e., one cannot 2460 call MatMult(A,y,y). 2461 2462 Level: beginner 2463 2464 .keywords: matrix, multiply, matrix-vector product, constraint 2465 .seealso: MatMult(), MatMultTranspose(), MatMultAdd(), MatMultTransposeAdd() 2466 @*/ 2467 PetscErrorCode MatMultConstrained(Mat mat,Vec x,Vec y) 2468 { 2469 PetscErrorCode ierr; 2470 2471 PetscFunctionBegin; 2472 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2473 PetscValidHeaderSpecific(x,VEC_CLASSID,2); 2474 PetscValidHeaderSpecific(y,VEC_CLASSID,3); 2475 if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2476 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2477 if (x == y) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors"); 2478 if (mat->cmap->N != x->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N); 2479 if (mat->rmap->N != y->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->rmap->N,y->map->N); 2480 if (mat->rmap->n != y->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: local dim %D %D",mat->rmap->n,y->map->n); 2481 2482 ierr = PetscLogEventBegin(MAT_MultConstrained,mat,x,y,0);CHKERRQ(ierr); 2483 ierr = (*mat->ops->multconstrained)(mat,x,y);CHKERRQ(ierr); 2484 ierr = PetscLogEventEnd(MAT_MultConstrained,mat,x,y,0);CHKERRQ(ierr); 2485 ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr); 2486 PetscFunctionReturn(0); 2487 } 2488 2489 #undef __FUNCT__ 2490 #define __FUNCT__ "MatMultTransposeConstrained" 2491 /*@ 2492 MatMultTransposeConstrained - The inner multiplication routine for a 2493 constrained matrix P^T A^T P. 2494 2495 Neighbor-wise Collective on Mat and Vec 2496 2497 Input Parameters: 2498 + mat - the matrix 2499 - x - the vector to be multilplied 2500 2501 Output Parameters: 2502 . y - the result 2503 2504 Notes: 2505 The vectors x and y cannot be the same. I.e., one cannot 2506 call MatMult(A,y,y). 2507 2508 Level: beginner 2509 2510 .keywords: matrix, multiply, matrix-vector product, constraint 2511 .seealso: MatMult(), MatMultTranspose(), MatMultAdd(), MatMultTransposeAdd() 2512 @*/ 2513 PetscErrorCode MatMultTransposeConstrained(Mat mat,Vec x,Vec y) 2514 { 2515 PetscErrorCode ierr; 2516 2517 PetscFunctionBegin; 2518 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2519 PetscValidHeaderSpecific(x,VEC_CLASSID,2); 2520 PetscValidHeaderSpecific(y,VEC_CLASSID,3); 2521 if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2522 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2523 if (x == y) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"x and y must be different vectors"); 2524 if (mat->rmap->N != x->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N); 2525 if (mat->cmap->N != y->map->N) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->rmap->N,y->map->N); 2526 2527 ierr = PetscLogEventBegin(MAT_MultConstrained,mat,x,y,0);CHKERRQ(ierr); 2528 ierr = (*mat->ops->multtransposeconstrained)(mat,x,y);CHKERRQ(ierr); 2529 ierr = PetscLogEventEnd(MAT_MultConstrained,mat,x,y,0);CHKERRQ(ierr); 2530 ierr = PetscObjectStateIncrease((PetscObject)y);CHKERRQ(ierr); 2531 PetscFunctionReturn(0); 2532 } 2533 2534 #undef __FUNCT__ 2535 #define __FUNCT__ "MatGetFactorType" 2536 /*@C 2537 MatGetFactorType - gets the type of factorization it is 2538 2539 Note Collective 2540 as the flag 2541 2542 Input Parameters: 2543 . mat - the matrix 2544 2545 Output Parameters: 2546 . t - the type, one of MAT_FACTOR_NONE, MAT_FACTOR_LU, MAT_FACTOR_CHOLESKY, MAT_FACTOR_ILU, MAT_FACTOR_ICC,MAT_FACTOR_ILUDT 2547 2548 Level: intermediate 2549 2550 .seealso: MatFactorType, MatGetFactor() 2551 @*/ 2552 PetscErrorCode MatGetFactorType(Mat mat,MatFactorType *t) 2553 { 2554 PetscFunctionBegin; 2555 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2556 PetscValidType(mat,1); 2557 *t = mat->factortype; 2558 PetscFunctionReturn(0); 2559 } 2560 2561 /* ------------------------------------------------------------*/ 2562 #undef __FUNCT__ 2563 #define __FUNCT__ "MatGetInfo" 2564 /*@C 2565 MatGetInfo - Returns information about matrix storage (number of 2566 nonzeros, memory, etc.). 2567 2568 Collective on Mat if MAT_GLOBAL_MAX or MAT_GLOBAL_SUM is used as the flag 2569 2570 Input Parameters: 2571 . mat - the matrix 2572 2573 Output Parameters: 2574 + flag - flag indicating the type of parameters to be returned 2575 (MAT_LOCAL - local matrix, MAT_GLOBAL_MAX - maximum over all processors, 2576 MAT_GLOBAL_SUM - sum over all processors) 2577 - info - matrix information context 2578 2579 Notes: 2580 The MatInfo context contains a variety of matrix data, including 2581 number of nonzeros allocated and used, number of mallocs during 2582 matrix assembly, etc. Additional information for factored matrices 2583 is provided (such as the fill ratio, number of mallocs during 2584 factorization, etc.). Much of this info is printed to PETSC_STDOUT 2585 when using the runtime options 2586 $ -info -mat_view ::ascii_info 2587 2588 Example for C/C++ Users: 2589 See the file ${PETSC_DIR}/include/petscmat.h for a complete list of 2590 data within the MatInfo context. For example, 2591 .vb 2592 MatInfo info; 2593 Mat A; 2594 double mal, nz_a, nz_u; 2595 2596 MatGetInfo(A,MAT_LOCAL,&info); 2597 mal = info.mallocs; 2598 nz_a = info.nz_allocated; 2599 .ve 2600 2601 Example for Fortran Users: 2602 Fortran users should declare info as a double precision 2603 array of dimension MAT_INFO_SIZE, and then extract the parameters 2604 of interest. See the file ${PETSC_DIR}/include/finclude/petscmat.h 2605 a complete list of parameter names. 2606 .vb 2607 double precision info(MAT_INFO_SIZE) 2608 double precision mal, nz_a 2609 Mat A 2610 integer ierr 2611 2612 call MatGetInfo(A,MAT_LOCAL,info,ierr) 2613 mal = info(MAT_INFO_MALLOCS) 2614 nz_a = info(MAT_INFO_NZ_ALLOCATED) 2615 .ve 2616 2617 Level: intermediate 2618 2619 Concepts: matrices^getting information on 2620 2621 Developer Note: fortran interface is not autogenerated as the f90 2622 interface defintion cannot be generated correctly [due to MatInfo] 2623 2624 .seealso: MatStashGetInfo() 2625 2626 @*/ 2627 PetscErrorCode MatGetInfo(Mat mat,MatInfoType flag,MatInfo *info) 2628 { 2629 PetscErrorCode ierr; 2630 2631 PetscFunctionBegin; 2632 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2633 PetscValidType(mat,1); 2634 PetscValidPointer(info,3); 2635 if (!mat->ops->getinfo) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 2636 MatCheckPreallocated(mat,1); 2637 ierr = (*mat->ops->getinfo)(mat,flag,info);CHKERRQ(ierr); 2638 PetscFunctionReturn(0); 2639 } 2640 2641 /* ----------------------------------------------------------*/ 2642 2643 #undef __FUNCT__ 2644 #define __FUNCT__ "MatLUFactor" 2645 /*@C 2646 MatLUFactor - Performs in-place LU factorization of matrix. 2647 2648 Collective on Mat 2649 2650 Input Parameters: 2651 + mat - the matrix 2652 . row - row permutation 2653 . col - column permutation 2654 - info - options for factorization, includes 2655 $ fill - expected fill as ratio of original fill. 2656 $ dtcol - pivot tolerance (0 no pivot, 1 full column pivoting) 2657 $ Run with the option -info to determine an optimal value to use 2658 2659 Notes: 2660 Most users should employ the simplified KSP interface for linear solvers 2661 instead of working directly with matrix algebra routines such as this. 2662 See, e.g., KSPCreate(). 2663 2664 This changes the state of the matrix to a factored matrix; it cannot be used 2665 for example with MatSetValues() unless one first calls MatSetUnfactored(). 2666 2667 Level: developer 2668 2669 Concepts: matrices^LU factorization 2670 2671 .seealso: MatLUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor(), 2672 MatGetOrdering(), MatSetUnfactored(), MatFactorInfo, MatGetFactor() 2673 2674 Developer Note: fortran interface is not autogenerated as the f90 2675 interface defintion cannot be generated correctly [due to MatFactorInfo] 2676 2677 @*/ 2678 PetscErrorCode MatLUFactor(Mat mat,IS row,IS col,const MatFactorInfo *info) 2679 { 2680 PetscErrorCode ierr; 2681 MatFactorInfo tinfo; 2682 2683 PetscFunctionBegin; 2684 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2685 if (row) PetscValidHeaderSpecific(row,IS_CLASSID,2); 2686 if (col) PetscValidHeaderSpecific(col,IS_CLASSID,3); 2687 if (info) PetscValidPointer(info,4); 2688 PetscValidType(mat,1); 2689 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2690 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2691 if (!mat->ops->lufactor) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 2692 MatCheckPreallocated(mat,1); 2693 if (!info) { 2694 ierr = MatFactorInfoInitialize(&tinfo);CHKERRQ(ierr); 2695 info = &tinfo; 2696 } 2697 2698 ierr = PetscLogEventBegin(MAT_LUFactor,mat,row,col,0);CHKERRQ(ierr); 2699 ierr = (*mat->ops->lufactor)(mat,row,col,info);CHKERRQ(ierr); 2700 ierr = PetscLogEventEnd(MAT_LUFactor,mat,row,col,0);CHKERRQ(ierr); 2701 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 2702 PetscFunctionReturn(0); 2703 } 2704 2705 #undef __FUNCT__ 2706 #define __FUNCT__ "MatILUFactor" 2707 /*@C 2708 MatILUFactor - Performs in-place ILU factorization of matrix. 2709 2710 Collective on Mat 2711 2712 Input Parameters: 2713 + mat - the matrix 2714 . row - row permutation 2715 . col - column permutation 2716 - info - structure containing 2717 $ levels - number of levels of fill. 2718 $ expected fill - as ratio of original fill. 2719 $ 1 or 0 - indicating force fill on diagonal (improves robustness for matrices 2720 missing diagonal entries) 2721 2722 Notes: 2723 Probably really in-place only when level of fill is zero, otherwise allocates 2724 new space to store factored matrix and deletes previous memory. 2725 2726 Most users should employ the simplified KSP interface for linear solvers 2727 instead of working directly with matrix algebra routines such as this. 2728 See, e.g., KSPCreate(). 2729 2730 Level: developer 2731 2732 Concepts: matrices^ILU factorization 2733 2734 .seealso: MatILUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor(), MatFactorInfo 2735 2736 Developer Note: fortran interface is not autogenerated as the f90 2737 interface defintion cannot be generated correctly [due to MatFactorInfo] 2738 2739 @*/ 2740 PetscErrorCode MatILUFactor(Mat mat,IS row,IS col,const MatFactorInfo *info) 2741 { 2742 PetscErrorCode ierr; 2743 2744 PetscFunctionBegin; 2745 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2746 if (row) PetscValidHeaderSpecific(row,IS_CLASSID,2); 2747 if (col) PetscValidHeaderSpecific(col,IS_CLASSID,3); 2748 PetscValidPointer(info,4); 2749 PetscValidType(mat,1); 2750 if (mat->rmap->N != mat->cmap->N) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONG,"matrix must be square"); 2751 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2752 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2753 if (!mat->ops->ilufactor) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 2754 MatCheckPreallocated(mat,1); 2755 2756 ierr = PetscLogEventBegin(MAT_ILUFactor,mat,row,col,0);CHKERRQ(ierr); 2757 ierr = (*mat->ops->ilufactor)(mat,row,col,info);CHKERRQ(ierr); 2758 ierr = PetscLogEventEnd(MAT_ILUFactor,mat,row,col,0);CHKERRQ(ierr); 2759 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 2760 PetscFunctionReturn(0); 2761 } 2762 2763 #undef __FUNCT__ 2764 #define __FUNCT__ "MatLUFactorSymbolic" 2765 /*@C 2766 MatLUFactorSymbolic - Performs symbolic LU factorization of matrix. 2767 Call this routine before calling MatLUFactorNumeric(). 2768 2769 Collective on Mat 2770 2771 Input Parameters: 2772 + fact - the factor matrix obtained with MatGetFactor() 2773 . mat - the matrix 2774 . row, col - row and column permutations 2775 - info - options for factorization, includes 2776 $ fill - expected fill as ratio of original fill. 2777 $ dtcol - pivot tolerance (0 no pivot, 1 full column pivoting) 2778 $ Run with the option -info to determine an optimal value to use 2779 2780 2781 Notes: 2782 See the <a href="../../docs/manual.pdf">users manual</a> for additional information about 2783 choosing the fill factor for better efficiency. 2784 2785 Most users should employ the simplified KSP interface for linear solvers 2786 instead of working directly with matrix algebra routines such as this. 2787 See, e.g., KSPCreate(). 2788 2789 Level: developer 2790 2791 Concepts: matrices^LU symbolic factorization 2792 2793 .seealso: MatLUFactor(), MatLUFactorNumeric(), MatCholeskyFactor(), MatFactorInfo 2794 2795 Developer Note: fortran interface is not autogenerated as the f90 2796 interface defintion cannot be generated correctly [due to MatFactorInfo] 2797 2798 @*/ 2799 PetscErrorCode MatLUFactorSymbolic(Mat fact,Mat mat,IS row,IS col,const MatFactorInfo *info) 2800 { 2801 PetscErrorCode ierr; 2802 2803 PetscFunctionBegin; 2804 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2805 if (row) PetscValidHeaderSpecific(row,IS_CLASSID,2); 2806 if (col) PetscValidHeaderSpecific(col,IS_CLASSID,3); 2807 if (info) PetscValidPointer(info,4); 2808 PetscValidType(mat,1); 2809 PetscValidPointer(fact,5); 2810 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2811 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2812 if (!(fact)->ops->lufactorsymbolic) { 2813 const MatSolverPackage spackage; 2814 ierr = MatFactorGetSolverPackage(fact,&spackage);CHKERRQ(ierr); 2815 SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Matrix type %s symbolic LU using solver package %s",((PetscObject)mat)->type_name,spackage); 2816 } 2817 MatCheckPreallocated(mat,2); 2818 2819 ierr = PetscLogEventBegin(MAT_LUFactorSymbolic,mat,row,col,0);CHKERRQ(ierr); 2820 ierr = (fact->ops->lufactorsymbolic)(fact,mat,row,col,info);CHKERRQ(ierr); 2821 ierr = PetscLogEventEnd(MAT_LUFactorSymbolic,mat,row,col,0);CHKERRQ(ierr); 2822 ierr = PetscObjectStateIncrease((PetscObject)fact);CHKERRQ(ierr); 2823 PetscFunctionReturn(0); 2824 } 2825 2826 #undef __FUNCT__ 2827 #define __FUNCT__ "MatLUFactorNumeric" 2828 /*@C 2829 MatLUFactorNumeric - Performs numeric LU factorization of a matrix. 2830 Call this routine after first calling MatLUFactorSymbolic(). 2831 2832 Collective on Mat 2833 2834 Input Parameters: 2835 + fact - the factor matrix obtained with MatGetFactor() 2836 . mat - the matrix 2837 - info - options for factorization 2838 2839 Notes: 2840 See MatLUFactor() for in-place factorization. See 2841 MatCholeskyFactorNumeric() for the symmetric, positive definite case. 2842 2843 Most users should employ the simplified KSP interface for linear solvers 2844 instead of working directly with matrix algebra routines such as this. 2845 See, e.g., KSPCreate(). 2846 2847 Level: developer 2848 2849 Concepts: matrices^LU numeric factorization 2850 2851 .seealso: MatLUFactorSymbolic(), MatLUFactor(), MatCholeskyFactor() 2852 2853 Developer Note: fortran interface is not autogenerated as the f90 2854 interface defintion cannot be generated correctly [due to MatFactorInfo] 2855 2856 @*/ 2857 PetscErrorCode MatLUFactorNumeric(Mat fact,Mat mat,const MatFactorInfo *info) 2858 { 2859 PetscErrorCode ierr; 2860 2861 PetscFunctionBegin; 2862 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2863 PetscValidType(mat,1); 2864 PetscValidPointer(fact,2); 2865 PetscValidHeaderSpecific(fact,MAT_CLASSID,2); 2866 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2867 if (mat->rmap->N != (fact)->rmap->N || mat->cmap->N != (fact)->cmap->N) SETERRQ4(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Mat fact: global dimensions are different %D should = %D %D should = %D",mat->rmap->N,(fact)->rmap->N,mat->cmap->N,(fact)->cmap->N); 2868 2869 if (!(fact)->ops->lufactornumeric) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s numeric LU",((PetscObject)mat)->type_name); 2870 MatCheckPreallocated(mat,2); 2871 ierr = PetscLogEventBegin(MAT_LUFactorNumeric,mat,fact,0,0);CHKERRQ(ierr); 2872 ierr = (fact->ops->lufactornumeric)(fact,mat,info);CHKERRQ(ierr); 2873 ierr = PetscLogEventEnd(MAT_LUFactorNumeric,mat,fact,0,0);CHKERRQ(ierr); 2874 2875 if (fact->viewonassembly) { 2876 ierr = PetscViewerPushFormat(fact->viewonassembly,fact->viewformatonassembly);CHKERRQ(ierr); 2877 ierr = MatView(fact,fact->viewonassembly);CHKERRQ(ierr); 2878 ierr = PetscViewerPopFormat(fact->viewonassembly);CHKERRQ(ierr); 2879 } 2880 ierr = PetscObjectStateIncrease((PetscObject)fact);CHKERRQ(ierr); 2881 PetscFunctionReturn(0); 2882 } 2883 2884 #undef __FUNCT__ 2885 #define __FUNCT__ "MatCholeskyFactor" 2886 /*@C 2887 MatCholeskyFactor - Performs in-place Cholesky factorization of a 2888 symmetric matrix. 2889 2890 Collective on Mat 2891 2892 Input Parameters: 2893 + mat - the matrix 2894 . perm - row and column permutations 2895 - f - expected fill as ratio of original fill 2896 2897 Notes: 2898 See MatLUFactor() for the nonsymmetric case. See also 2899 MatCholeskyFactorSymbolic(), and MatCholeskyFactorNumeric(). 2900 2901 Most users should employ the simplified KSP interface for linear solvers 2902 instead of working directly with matrix algebra routines such as this. 2903 See, e.g., KSPCreate(). 2904 2905 Level: developer 2906 2907 Concepts: matrices^Cholesky factorization 2908 2909 .seealso: MatLUFactor(), MatCholeskyFactorSymbolic(), MatCholeskyFactorNumeric() 2910 MatGetOrdering() 2911 2912 Developer Note: fortran interface is not autogenerated as the f90 2913 interface defintion cannot be generated correctly [due to MatFactorInfo] 2914 2915 @*/ 2916 PetscErrorCode MatCholeskyFactor(Mat mat,IS perm,const MatFactorInfo *info) 2917 { 2918 PetscErrorCode ierr; 2919 2920 PetscFunctionBegin; 2921 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2922 PetscValidType(mat,1); 2923 if (perm) PetscValidHeaderSpecific(perm,IS_CLASSID,2); 2924 if (info) PetscValidPointer(info,3); 2925 if (mat->rmap->N != mat->cmap->N) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONG,"Matrix must be square"); 2926 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2927 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2928 if (!mat->ops->choleskyfactor) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 2929 MatCheckPreallocated(mat,1); 2930 2931 ierr = PetscLogEventBegin(MAT_CholeskyFactor,mat,perm,0,0);CHKERRQ(ierr); 2932 ierr = (*mat->ops->choleskyfactor)(mat,perm,info);CHKERRQ(ierr); 2933 ierr = PetscLogEventEnd(MAT_CholeskyFactor,mat,perm,0,0);CHKERRQ(ierr); 2934 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 2935 PetscFunctionReturn(0); 2936 } 2937 2938 #undef __FUNCT__ 2939 #define __FUNCT__ "MatCholeskyFactorSymbolic" 2940 /*@C 2941 MatCholeskyFactorSymbolic - Performs symbolic Cholesky factorization 2942 of a symmetric matrix. 2943 2944 Collective on Mat 2945 2946 Input Parameters: 2947 + fact - the factor matrix obtained with MatGetFactor() 2948 . mat - the matrix 2949 . perm - row and column permutations 2950 - info - options for factorization, includes 2951 $ fill - expected fill as ratio of original fill. 2952 $ dtcol - pivot tolerance (0 no pivot, 1 full column pivoting) 2953 $ Run with the option -info to determine an optimal value to use 2954 2955 Notes: 2956 See MatLUFactorSymbolic() for the nonsymmetric case. See also 2957 MatCholeskyFactor() and MatCholeskyFactorNumeric(). 2958 2959 Most users should employ the simplified KSP interface for linear solvers 2960 instead of working directly with matrix algebra routines such as this. 2961 See, e.g., KSPCreate(). 2962 2963 Level: developer 2964 2965 Concepts: matrices^Cholesky symbolic factorization 2966 2967 .seealso: MatLUFactorSymbolic(), MatCholeskyFactor(), MatCholeskyFactorNumeric() 2968 MatGetOrdering() 2969 2970 Developer Note: fortran interface is not autogenerated as the f90 2971 interface defintion cannot be generated correctly [due to MatFactorInfo] 2972 2973 @*/ 2974 PetscErrorCode MatCholeskyFactorSymbolic(Mat fact,Mat mat,IS perm,const MatFactorInfo *info) 2975 { 2976 PetscErrorCode ierr; 2977 2978 PetscFunctionBegin; 2979 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 2980 PetscValidType(mat,1); 2981 if (perm) PetscValidHeaderSpecific(perm,IS_CLASSID,2); 2982 if (info) PetscValidPointer(info,3); 2983 PetscValidPointer(fact,4); 2984 if (mat->rmap->N != mat->cmap->N) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONG,"Matrix must be square"); 2985 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 2986 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 2987 if (!(fact)->ops->choleskyfactorsymbolic) { 2988 const MatSolverPackage spackage; 2989 ierr = MatFactorGetSolverPackage(fact,&spackage);CHKERRQ(ierr); 2990 SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s symbolic factor Cholesky using solver package %s",((PetscObject)mat)->type_name,spackage); 2991 } 2992 MatCheckPreallocated(mat,2); 2993 2994 ierr = PetscLogEventBegin(MAT_CholeskyFactorSymbolic,mat,perm,0,0);CHKERRQ(ierr); 2995 ierr = (fact->ops->choleskyfactorsymbolic)(fact,mat,perm,info);CHKERRQ(ierr); 2996 ierr = PetscLogEventEnd(MAT_CholeskyFactorSymbolic,mat,perm,0,0);CHKERRQ(ierr); 2997 ierr = PetscObjectStateIncrease((PetscObject)fact);CHKERRQ(ierr); 2998 PetscFunctionReturn(0); 2999 } 3000 3001 #undef __FUNCT__ 3002 #define __FUNCT__ "MatCholeskyFactorNumeric" 3003 /*@C 3004 MatCholeskyFactorNumeric - Performs numeric Cholesky factorization 3005 of a symmetric matrix. Call this routine after first calling 3006 MatCholeskyFactorSymbolic(). 3007 3008 Collective on Mat 3009 3010 Input Parameters: 3011 + fact - the factor matrix obtained with MatGetFactor() 3012 . mat - the initial matrix 3013 . info - options for factorization 3014 - fact - the symbolic factor of mat 3015 3016 3017 Notes: 3018 Most users should employ the simplified KSP interface for linear solvers 3019 instead of working directly with matrix algebra routines such as this. 3020 See, e.g., KSPCreate(). 3021 3022 Level: developer 3023 3024 Concepts: matrices^Cholesky numeric factorization 3025 3026 .seealso: MatCholeskyFactorSymbolic(), MatCholeskyFactor(), MatLUFactorNumeric() 3027 3028 Developer Note: fortran interface is not autogenerated as the f90 3029 interface defintion cannot be generated correctly [due to MatFactorInfo] 3030 3031 @*/ 3032 PetscErrorCode MatCholeskyFactorNumeric(Mat fact,Mat mat,const MatFactorInfo *info) 3033 { 3034 PetscErrorCode ierr; 3035 3036 PetscFunctionBegin; 3037 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3038 PetscValidType(mat,1); 3039 PetscValidPointer(fact,2); 3040 PetscValidHeaderSpecific(fact,MAT_CLASSID,2); 3041 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 3042 if (!(fact)->ops->choleskyfactornumeric) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s numeric factor Cholesky",((PetscObject)mat)->type_name); 3043 if (mat->rmap->N != (fact)->rmap->N || mat->cmap->N != (fact)->cmap->N) SETERRQ4(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Mat fact: global dim %D should = %D %D should = %D",mat->rmap->N,(fact)->rmap->N,mat->cmap->N,(fact)->cmap->N); 3044 MatCheckPreallocated(mat,2); 3045 3046 ierr = PetscLogEventBegin(MAT_CholeskyFactorNumeric,mat,fact,0,0);CHKERRQ(ierr); 3047 ierr = (fact->ops->choleskyfactornumeric)(fact,mat,info);CHKERRQ(ierr); 3048 ierr = PetscLogEventEnd(MAT_CholeskyFactorNumeric,mat,fact,0,0);CHKERRQ(ierr); 3049 3050 if (fact->viewonassembly) { 3051 ierr = PetscViewerPushFormat(fact->viewonassembly,fact->viewformatonassembly);CHKERRQ(ierr); 3052 ierr = MatView(fact,fact->viewonassembly);CHKERRQ(ierr); 3053 ierr = PetscViewerPopFormat(fact->viewonassembly);CHKERRQ(ierr); 3054 } 3055 ierr = PetscObjectStateIncrease((PetscObject)fact);CHKERRQ(ierr); 3056 PetscFunctionReturn(0); 3057 } 3058 3059 /* ----------------------------------------------------------------*/ 3060 #undef __FUNCT__ 3061 #define __FUNCT__ "MatSolve" 3062 /*@ 3063 MatSolve - Solves A x = b, given a factored matrix. 3064 3065 Neighbor-wise Collective on Mat and Vec 3066 3067 Input Parameters: 3068 + mat - the factored matrix 3069 - b - the right-hand-side vector 3070 3071 Output Parameter: 3072 . x - the result vector 3073 3074 Notes: 3075 The vectors b and x cannot be the same. I.e., one cannot 3076 call MatSolve(A,x,x). 3077 3078 Notes: 3079 Most users should employ the simplified KSP interface for linear solvers 3080 instead of working directly with matrix algebra routines such as this. 3081 See, e.g., KSPCreate(). 3082 3083 Level: developer 3084 3085 Concepts: matrices^triangular solves 3086 3087 .seealso: MatSolveAdd(), MatSolveTranspose(), MatSolveTransposeAdd() 3088 @*/ 3089 PetscErrorCode MatSolve(Mat mat,Vec b,Vec x) 3090 { 3091 PetscErrorCode ierr; 3092 3093 PetscFunctionBegin; 3094 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3095 PetscValidType(mat,1); 3096 PetscValidHeaderSpecific(b,VEC_CLASSID,2); 3097 PetscValidHeaderSpecific(x,VEC_CLASSID,3); 3098 PetscCheckSameComm(mat,1,b,2); 3099 PetscCheckSameComm(mat,1,x,3); 3100 if (x == b) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_IDN,"x and b must be different vectors"); 3101 if (!mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix"); 3102 if (mat->cmap->N != x->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N); 3103 if (mat->rmap->N != b->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->rmap->N,b->map->N); 3104 if (mat->rmap->n != b->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->rmap->n,b->map->n); 3105 if (!mat->rmap->N && !mat->cmap->N) PetscFunctionReturn(0); 3106 if (!mat->ops->solve) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 3107 MatCheckPreallocated(mat,1); 3108 3109 ierr = PetscLogEventBegin(MAT_Solve,mat,b,x,0);CHKERRQ(ierr); 3110 ierr = (*mat->ops->solve)(mat,b,x);CHKERRQ(ierr); 3111 ierr = PetscLogEventEnd(MAT_Solve,mat,b,x,0);CHKERRQ(ierr); 3112 ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr); 3113 PetscFunctionReturn(0); 3114 } 3115 3116 #undef __FUNCT__ 3117 #define __FUNCT__ "MatMatSolve_Basic" 3118 PetscErrorCode MatMatSolve_Basic(Mat A,Mat B,Mat X) 3119 { 3120 PetscErrorCode ierr; 3121 Vec b,x; 3122 PetscInt m,N,i; 3123 PetscScalar *bb,*xx; 3124 PetscBool flg; 3125 3126 PetscFunctionBegin; 3127 ierr = PetscObjectTypeCompareAny((PetscObject)B,&flg,MATSEQDENSE,MATMPIDENSE,NULL);CHKERRQ(ierr); 3128 if (!flg) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONG,"Matrix B must be MATDENSE matrix"); 3129 ierr = PetscObjectTypeCompareAny((PetscObject)X,&flg,MATSEQDENSE,MATMPIDENSE,NULL);CHKERRQ(ierr); 3130 if (!flg) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONG,"Matrix X must be MATDENSE matrix"); 3131 3132 ierr = MatDenseGetArray(B,&bb);CHKERRQ(ierr); 3133 ierr = MatDenseGetArray(X,&xx);CHKERRQ(ierr); 3134 ierr = MatGetLocalSize(B,&m,NULL);CHKERRQ(ierr); /* number local rows */ 3135 ierr = MatGetSize(B,NULL,&N);CHKERRQ(ierr); /* total columns in dense matrix */ 3136 ierr = MatGetVecs(A,&x,&b);CHKERRQ(ierr); 3137 for (i=0; i<N; i++) { 3138 ierr = VecPlaceArray(b,bb + i*m);CHKERRQ(ierr); 3139 ierr = VecPlaceArray(x,xx + i*m);CHKERRQ(ierr); 3140 ierr = MatSolve(A,b,x);CHKERRQ(ierr); 3141 ierr = VecResetArray(x);CHKERRQ(ierr); 3142 ierr = VecResetArray(b);CHKERRQ(ierr); 3143 } 3144 ierr = VecDestroy(&b);CHKERRQ(ierr); 3145 ierr = VecDestroy(&x);CHKERRQ(ierr); 3146 ierr = MatDenseRestoreArray(B,&bb);CHKERRQ(ierr); 3147 ierr = MatDenseRestoreArray(X,&xx);CHKERRQ(ierr); 3148 PetscFunctionReturn(0); 3149 } 3150 3151 #undef __FUNCT__ 3152 #define __FUNCT__ "MatMatSolve" 3153 /*@ 3154 MatMatSolve - Solves A X = B, given a factored matrix. 3155 3156 Neighbor-wise Collective on Mat 3157 3158 Input Parameters: 3159 + mat - the factored matrix 3160 - B - the right-hand-side matrix (dense matrix) 3161 3162 Output Parameter: 3163 . X - the result matrix (dense matrix) 3164 3165 Notes: 3166 The matrices b and x cannot be the same. I.e., one cannot 3167 call MatMatSolve(A,x,x). 3168 3169 Notes: 3170 Most users should usually employ the simplified KSP interface for linear solvers 3171 instead of working directly with matrix algebra routines such as this. 3172 See, e.g., KSPCreate(). However KSP can only solve for one vector (column of X) 3173 at a time. 3174 3175 When using SuperLU_Dist as a parallel solver PETSc will use the SuperLU_Dist functionality to solve multiple right hand sides simultaneously. For MUMPS 3176 it calls a separate solve for each right hand side since MUMPS does not yet support distributed right hand sides. 3177 3178 Since the resulting matrix X must always be dense we do not support sparse representation of the matrix B. 3179 3180 Level: developer 3181 3182 Concepts: matrices^triangular solves 3183 3184 .seealso: MatMatSolveAdd(), MatMatSolveTranspose(), MatMatSolveTransposeAdd(), MatLUFactor(), MatCholeskyFactor() 3185 @*/ 3186 PetscErrorCode MatMatSolve(Mat A,Mat B,Mat X) 3187 { 3188 PetscErrorCode ierr; 3189 3190 PetscFunctionBegin; 3191 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 3192 PetscValidType(A,1); 3193 PetscValidHeaderSpecific(B,MAT_CLASSID,2); 3194 PetscValidHeaderSpecific(X,MAT_CLASSID,3); 3195 PetscCheckSameComm(A,1,B,2); 3196 PetscCheckSameComm(A,1,X,3); 3197 if (X == B) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_IDN,"X and B must be different matrices"); 3198 if (!A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix"); 3199 if (A->cmap->N != X->rmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Mat A,Mat X: global dim %D %D",A->cmap->N,X->rmap->N); 3200 if (A->rmap->N != B->rmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Mat A,Mat B: global dim %D %D",A->rmap->N,B->rmap->N); 3201 if (A->rmap->n != B->rmap->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat A,Mat B: local dim %D %D",A->rmap->n,B->rmap->n); 3202 if (!A->rmap->N && !A->cmap->N) PetscFunctionReturn(0); 3203 MatCheckPreallocated(A,1); 3204 3205 ierr = PetscLogEventBegin(MAT_MatSolve,A,B,X,0);CHKERRQ(ierr); 3206 if (!A->ops->matsolve) { 3207 ierr = PetscInfo1(A,"Mat type %s using basic MatMatSolve",((PetscObject)A)->type_name);CHKERRQ(ierr); 3208 ierr = MatMatSolve_Basic(A,B,X);CHKERRQ(ierr); 3209 } else { 3210 ierr = (*A->ops->matsolve)(A,B,X);CHKERRQ(ierr); 3211 } 3212 ierr = PetscLogEventEnd(MAT_MatSolve,A,B,X,0);CHKERRQ(ierr); 3213 ierr = PetscObjectStateIncrease((PetscObject)X);CHKERRQ(ierr); 3214 PetscFunctionReturn(0); 3215 } 3216 3217 3218 #undef __FUNCT__ 3219 #define __FUNCT__ "MatForwardSolve" 3220 /*@ 3221 MatForwardSolve - Solves L x = b, given a factored matrix, A = LU, or 3222 U^T*D^(1/2) x = b, given a factored symmetric matrix, A = U^T*D*U, 3223 3224 Neighbor-wise Collective on Mat and Vec 3225 3226 Input Parameters: 3227 + mat - the factored matrix 3228 - b - the right-hand-side vector 3229 3230 Output Parameter: 3231 . x - the result vector 3232 3233 Notes: 3234 MatSolve() should be used for most applications, as it performs 3235 a forward solve followed by a backward solve. 3236 3237 The vectors b and x cannot be the same, i.e., one cannot 3238 call MatForwardSolve(A,x,x). 3239 3240 For matrix in seqsbaij format with block size larger than 1, 3241 the diagonal blocks are not implemented as D = D^(1/2) * D^(1/2) yet. 3242 MatForwardSolve() solves U^T*D y = b, and 3243 MatBackwardSolve() solves U x = y. 3244 Thus they do not provide a symmetric preconditioner. 3245 3246 Most users should employ the simplified KSP interface for linear solvers 3247 instead of working directly with matrix algebra routines such as this. 3248 See, e.g., KSPCreate(). 3249 3250 Level: developer 3251 3252 Concepts: matrices^forward solves 3253 3254 .seealso: MatSolve(), MatBackwardSolve() 3255 @*/ 3256 PetscErrorCode MatForwardSolve(Mat mat,Vec b,Vec x) 3257 { 3258 PetscErrorCode ierr; 3259 3260 PetscFunctionBegin; 3261 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3262 PetscValidType(mat,1); 3263 PetscValidHeaderSpecific(b,VEC_CLASSID,2); 3264 PetscValidHeaderSpecific(x,VEC_CLASSID,3); 3265 PetscCheckSameComm(mat,1,b,2); 3266 PetscCheckSameComm(mat,1,x,3); 3267 if (x == b) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_IDN,"x and b must be different vectors"); 3268 if (!mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix"); 3269 if (!mat->ops->forwardsolve) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 3270 if (mat->cmap->N != x->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N); 3271 if (mat->rmap->N != b->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->rmap->N,b->map->N); 3272 if (mat->rmap->n != b->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->rmap->n,b->map->n); 3273 MatCheckPreallocated(mat,1); 3274 ierr = PetscLogEventBegin(MAT_ForwardSolve,mat,b,x,0);CHKERRQ(ierr); 3275 ierr = (*mat->ops->forwardsolve)(mat,b,x);CHKERRQ(ierr); 3276 ierr = PetscLogEventEnd(MAT_ForwardSolve,mat,b,x,0);CHKERRQ(ierr); 3277 ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr); 3278 PetscFunctionReturn(0); 3279 } 3280 3281 #undef __FUNCT__ 3282 #define __FUNCT__ "MatBackwardSolve" 3283 /*@ 3284 MatBackwardSolve - Solves U x = b, given a factored matrix, A = LU. 3285 D^(1/2) U x = b, given a factored symmetric matrix, A = U^T*D*U, 3286 3287 Neighbor-wise Collective on Mat and Vec 3288 3289 Input Parameters: 3290 + mat - the factored matrix 3291 - b - the right-hand-side vector 3292 3293 Output Parameter: 3294 . x - the result vector 3295 3296 Notes: 3297 MatSolve() should be used for most applications, as it performs 3298 a forward solve followed by a backward solve. 3299 3300 The vectors b and x cannot be the same. I.e., one cannot 3301 call MatBackwardSolve(A,x,x). 3302 3303 For matrix in seqsbaij format with block size larger than 1, 3304 the diagonal blocks are not implemented as D = D^(1/2) * D^(1/2) yet. 3305 MatForwardSolve() solves U^T*D y = b, and 3306 MatBackwardSolve() solves U x = y. 3307 Thus they do not provide a symmetric preconditioner. 3308 3309 Most users should employ the simplified KSP interface for linear solvers 3310 instead of working directly with matrix algebra routines such as this. 3311 See, e.g., KSPCreate(). 3312 3313 Level: developer 3314 3315 Concepts: matrices^backward solves 3316 3317 .seealso: MatSolve(), MatForwardSolve() 3318 @*/ 3319 PetscErrorCode MatBackwardSolve(Mat mat,Vec b,Vec x) 3320 { 3321 PetscErrorCode ierr; 3322 3323 PetscFunctionBegin; 3324 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3325 PetscValidType(mat,1); 3326 PetscValidHeaderSpecific(b,VEC_CLASSID,2); 3327 PetscValidHeaderSpecific(x,VEC_CLASSID,3); 3328 PetscCheckSameComm(mat,1,b,2); 3329 PetscCheckSameComm(mat,1,x,3); 3330 if (x == b) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_IDN,"x and b must be different vectors"); 3331 if (!mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix"); 3332 if (!mat->ops->backwardsolve) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 3333 if (mat->cmap->N != x->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N); 3334 if (mat->rmap->N != b->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->rmap->N,b->map->N); 3335 if (mat->rmap->n != b->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->rmap->n,b->map->n); 3336 MatCheckPreallocated(mat,1); 3337 3338 ierr = PetscLogEventBegin(MAT_BackwardSolve,mat,b,x,0);CHKERRQ(ierr); 3339 ierr = (*mat->ops->backwardsolve)(mat,b,x);CHKERRQ(ierr); 3340 ierr = PetscLogEventEnd(MAT_BackwardSolve,mat,b,x,0);CHKERRQ(ierr); 3341 ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr); 3342 PetscFunctionReturn(0); 3343 } 3344 3345 #undef __FUNCT__ 3346 #define __FUNCT__ "MatSolveAdd" 3347 /*@ 3348 MatSolveAdd - Computes x = y + inv(A)*b, given a factored matrix. 3349 3350 Neighbor-wise Collective on Mat and Vec 3351 3352 Input Parameters: 3353 + mat - the factored matrix 3354 . b - the right-hand-side vector 3355 - y - the vector to be added to 3356 3357 Output Parameter: 3358 . x - the result vector 3359 3360 Notes: 3361 The vectors b and x cannot be the same. I.e., one cannot 3362 call MatSolveAdd(A,x,y,x). 3363 3364 Most users should employ the simplified KSP interface for linear solvers 3365 instead of working directly with matrix algebra routines such as this. 3366 See, e.g., KSPCreate(). 3367 3368 Level: developer 3369 3370 Concepts: matrices^triangular solves 3371 3372 .seealso: MatSolve(), MatSolveTranspose(), MatSolveTransposeAdd() 3373 @*/ 3374 PetscErrorCode MatSolveAdd(Mat mat,Vec b,Vec y,Vec x) 3375 { 3376 PetscScalar one = 1.0; 3377 Vec tmp; 3378 PetscErrorCode ierr; 3379 3380 PetscFunctionBegin; 3381 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3382 PetscValidType(mat,1); 3383 PetscValidHeaderSpecific(y,VEC_CLASSID,2); 3384 PetscValidHeaderSpecific(b,VEC_CLASSID,3); 3385 PetscValidHeaderSpecific(x,VEC_CLASSID,4); 3386 PetscCheckSameComm(mat,1,b,2); 3387 PetscCheckSameComm(mat,1,y,2); 3388 PetscCheckSameComm(mat,1,x,3); 3389 if (x == b) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_IDN,"x and b must be different vectors"); 3390 if (!mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix"); 3391 if (mat->cmap->N != x->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N); 3392 if (mat->rmap->N != b->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->rmap->N,b->map->N); 3393 if (mat->rmap->N != y->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->rmap->N,y->map->N); 3394 if (mat->rmap->n != b->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->rmap->n,b->map->n); 3395 if (x->map->n != y->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Vec x,Vec y: local dim %D %D",x->map->n,y->map->n); 3396 MatCheckPreallocated(mat,1); 3397 3398 ierr = PetscLogEventBegin(MAT_SolveAdd,mat,b,x,y);CHKERRQ(ierr); 3399 if (mat->ops->solveadd) { 3400 ierr = (*mat->ops->solveadd)(mat,b,y,x);CHKERRQ(ierr); 3401 } else { 3402 /* do the solve then the add manually */ 3403 if (x != y) { 3404 ierr = MatSolve(mat,b,x);CHKERRQ(ierr); 3405 ierr = VecAXPY(x,one,y);CHKERRQ(ierr); 3406 } else { 3407 ierr = VecDuplicate(x,&tmp);CHKERRQ(ierr); 3408 ierr = PetscLogObjectParent(mat,tmp);CHKERRQ(ierr); 3409 ierr = VecCopy(x,tmp);CHKERRQ(ierr); 3410 ierr = MatSolve(mat,b,x);CHKERRQ(ierr); 3411 ierr = VecAXPY(x,one,tmp);CHKERRQ(ierr); 3412 ierr = VecDestroy(&tmp);CHKERRQ(ierr); 3413 } 3414 } 3415 ierr = PetscLogEventEnd(MAT_SolveAdd,mat,b,x,y);CHKERRQ(ierr); 3416 ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr); 3417 PetscFunctionReturn(0); 3418 } 3419 3420 #undef __FUNCT__ 3421 #define __FUNCT__ "MatSolveTranspose" 3422 /*@ 3423 MatSolveTranspose - Solves A' x = b, given a factored matrix. 3424 3425 Neighbor-wise Collective on Mat and Vec 3426 3427 Input Parameters: 3428 + mat - the factored matrix 3429 - b - the right-hand-side vector 3430 3431 Output Parameter: 3432 . x - the result vector 3433 3434 Notes: 3435 The vectors b and x cannot be the same. I.e., one cannot 3436 call MatSolveTranspose(A,x,x). 3437 3438 Most users should employ the simplified KSP interface for linear solvers 3439 instead of working directly with matrix algebra routines such as this. 3440 See, e.g., KSPCreate(). 3441 3442 Level: developer 3443 3444 Concepts: matrices^triangular solves 3445 3446 .seealso: MatSolve(), MatSolveAdd(), MatSolveTransposeAdd() 3447 @*/ 3448 PetscErrorCode MatSolveTranspose(Mat mat,Vec b,Vec x) 3449 { 3450 PetscErrorCode ierr; 3451 3452 PetscFunctionBegin; 3453 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3454 PetscValidType(mat,1); 3455 PetscValidHeaderSpecific(b,VEC_CLASSID,2); 3456 PetscValidHeaderSpecific(x,VEC_CLASSID,3); 3457 PetscCheckSameComm(mat,1,b,2); 3458 PetscCheckSameComm(mat,1,x,3); 3459 if (!mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix"); 3460 if (x == b) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_IDN,"x and b must be different vectors"); 3461 if (!mat->ops->solvetranspose) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Matrix type %s",((PetscObject)mat)->type_name); 3462 if (mat->rmap->N != x->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->rmap->N,x->map->N); 3463 if (mat->cmap->N != b->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->cmap->N,b->map->N); 3464 MatCheckPreallocated(mat,1); 3465 ierr = PetscLogEventBegin(MAT_SolveTranspose,mat,b,x,0);CHKERRQ(ierr); 3466 ierr = (*mat->ops->solvetranspose)(mat,b,x);CHKERRQ(ierr); 3467 ierr = PetscLogEventEnd(MAT_SolveTranspose,mat,b,x,0);CHKERRQ(ierr); 3468 ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr); 3469 PetscFunctionReturn(0); 3470 } 3471 3472 #undef __FUNCT__ 3473 #define __FUNCT__ "MatSolveTransposeAdd" 3474 /*@ 3475 MatSolveTransposeAdd - Computes x = y + inv(Transpose(A)) b, given a 3476 factored matrix. 3477 3478 Neighbor-wise Collective on Mat and Vec 3479 3480 Input Parameters: 3481 + mat - the factored matrix 3482 . b - the right-hand-side vector 3483 - y - the vector to be added to 3484 3485 Output Parameter: 3486 . x - the result vector 3487 3488 Notes: 3489 The vectors b and x cannot be the same. I.e., one cannot 3490 call MatSolveTransposeAdd(A,x,y,x). 3491 3492 Most users should employ the simplified KSP interface for linear solvers 3493 instead of working directly with matrix algebra routines such as this. 3494 See, e.g., KSPCreate(). 3495 3496 Level: developer 3497 3498 Concepts: matrices^triangular solves 3499 3500 .seealso: MatSolve(), MatSolveAdd(), MatSolveTranspose() 3501 @*/ 3502 PetscErrorCode MatSolveTransposeAdd(Mat mat,Vec b,Vec y,Vec x) 3503 { 3504 PetscScalar one = 1.0; 3505 PetscErrorCode ierr; 3506 Vec tmp; 3507 3508 PetscFunctionBegin; 3509 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3510 PetscValidType(mat,1); 3511 PetscValidHeaderSpecific(y,VEC_CLASSID,2); 3512 PetscValidHeaderSpecific(b,VEC_CLASSID,3); 3513 PetscValidHeaderSpecific(x,VEC_CLASSID,4); 3514 PetscCheckSameComm(mat,1,b,2); 3515 PetscCheckSameComm(mat,1,y,3); 3516 PetscCheckSameComm(mat,1,x,4); 3517 if (x == b) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_IDN,"x and b must be different vectors"); 3518 if (!mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix"); 3519 if (mat->rmap->N != x->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->rmap->N,x->map->N); 3520 if (mat->cmap->N != b->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->cmap->N,b->map->N); 3521 if (mat->cmap->N != y->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec y: global dim %D %D",mat->cmap->N,y->map->N); 3522 if (x->map->n != y->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Vec x,Vec y: local dim %D %D",x->map->n,y->map->n); 3523 MatCheckPreallocated(mat,1); 3524 3525 ierr = PetscLogEventBegin(MAT_SolveTransposeAdd,mat,b,x,y);CHKERRQ(ierr); 3526 if (mat->ops->solvetransposeadd) { 3527 ierr = (*mat->ops->solvetransposeadd)(mat,b,y,x);CHKERRQ(ierr); 3528 } else { 3529 /* do the solve then the add manually */ 3530 if (x != y) { 3531 ierr = MatSolveTranspose(mat,b,x);CHKERRQ(ierr); 3532 ierr = VecAXPY(x,one,y);CHKERRQ(ierr); 3533 } else { 3534 ierr = VecDuplicate(x,&tmp);CHKERRQ(ierr); 3535 ierr = PetscLogObjectParent(mat,tmp);CHKERRQ(ierr); 3536 ierr = VecCopy(x,tmp);CHKERRQ(ierr); 3537 ierr = MatSolveTranspose(mat,b,x);CHKERRQ(ierr); 3538 ierr = VecAXPY(x,one,tmp);CHKERRQ(ierr); 3539 ierr = VecDestroy(&tmp);CHKERRQ(ierr); 3540 } 3541 } 3542 ierr = PetscLogEventEnd(MAT_SolveTransposeAdd,mat,b,x,y);CHKERRQ(ierr); 3543 ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr); 3544 PetscFunctionReturn(0); 3545 } 3546 /* ----------------------------------------------------------------*/ 3547 3548 #undef __FUNCT__ 3549 #define __FUNCT__ "MatSOR" 3550 /*@ 3551 MatSOR - Computes relaxation (SOR, Gauss-Seidel) sweeps. 3552 3553 Neighbor-wise Collective on Mat and Vec 3554 3555 Input Parameters: 3556 + mat - the matrix 3557 . b - the right hand side 3558 . omega - the relaxation factor 3559 . flag - flag indicating the type of SOR (see below) 3560 . shift - diagonal shift 3561 . its - the number of iterations 3562 - lits - the number of local iterations 3563 3564 Output Parameters: 3565 . x - the solution (can contain an initial guess, use option SOR_ZERO_INITIAL_GUESS to indicate no guess) 3566 3567 SOR Flags: 3568 . SOR_FORWARD_SWEEP - forward SOR 3569 . SOR_BACKWARD_SWEEP - backward SOR 3570 . SOR_SYMMETRIC_SWEEP - SSOR (symmetric SOR) 3571 . SOR_LOCAL_FORWARD_SWEEP - local forward SOR 3572 . SOR_LOCAL_BACKWARD_SWEEP - local forward SOR 3573 . SOR_LOCAL_SYMMETRIC_SWEEP - local SSOR 3574 . SOR_APPLY_UPPER, SOR_APPLY_LOWER - applies 3575 upper/lower triangular part of matrix to 3576 vector (with omega) 3577 . SOR_ZERO_INITIAL_GUESS - zero initial guess 3578 3579 Notes: 3580 SOR_LOCAL_FORWARD_SWEEP, SOR_LOCAL_BACKWARD_SWEEP, and 3581 SOR_LOCAL_SYMMETRIC_SWEEP perform separate independent smoothings 3582 on each processor. 3583 3584 Application programmers will not generally use MatSOR() directly, 3585 but instead will employ the KSP/PC interface. 3586 3587 Notes: for BAIJ, SBAIJ, and AIJ matrices with Inodes this does a block SOR smoothing, otherwise it does a pointwise smoothing 3588 3589 Notes for Advanced Users: 3590 The flags are implemented as bitwise inclusive or operations. 3591 For example, use (SOR_ZERO_INITIAL_GUESS | SOR_SYMMETRIC_SWEEP) 3592 to specify a zero initial guess for SSOR. 3593 3594 Most users should employ the simplified KSP interface for linear solvers 3595 instead of working directly with matrix algebra routines such as this. 3596 See, e.g., KSPCreate(). 3597 3598 Vectors x and b CANNOT be the same 3599 3600 Developer Note: We should add block SOR support for AIJ matrices with block size set to great than one and no inodes 3601 3602 Level: developer 3603 3604 Concepts: matrices^relaxation 3605 Concepts: matrices^SOR 3606 Concepts: matrices^Gauss-Seidel 3607 3608 @*/ 3609 PetscErrorCode MatSOR(Mat mat,Vec b,PetscReal omega,MatSORType flag,PetscReal shift,PetscInt its,PetscInt lits,Vec x) 3610 { 3611 PetscErrorCode ierr; 3612 3613 PetscFunctionBegin; 3614 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3615 PetscValidType(mat,1); 3616 PetscValidHeaderSpecific(b,VEC_CLASSID,2); 3617 PetscValidHeaderSpecific(x,VEC_CLASSID,8); 3618 PetscCheckSameComm(mat,1,b,2); 3619 PetscCheckSameComm(mat,1,x,8); 3620 if (!mat->ops->sor) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 3621 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 3622 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 3623 if (mat->cmap->N != x->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec x: global dim %D %D",mat->cmap->N,x->map->N); 3624 if (mat->rmap->N != b->map->N) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: global dim %D %D",mat->rmap->N,b->map->N); 3625 if (mat->rmap->n != b->map->n) SETERRQ2(PETSC_COMM_SELF,PETSC_ERR_ARG_SIZ,"Mat mat,Vec b: local dim %D %D",mat->rmap->n,b->map->n); 3626 if (its <= 0) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Relaxation requires global its %D positive",its); 3627 if (lits <= 0) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Relaxation requires local its %D positive",lits); 3628 if (b == x) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_IDN,"b and x vector cannot be the same"); 3629 3630 MatCheckPreallocated(mat,1); 3631 ierr = PetscLogEventBegin(MAT_SOR,mat,b,x,0);CHKERRQ(ierr); 3632 ierr =(*mat->ops->sor)(mat,b,omega,flag,shift,its,lits,x);CHKERRQ(ierr); 3633 ierr = PetscLogEventEnd(MAT_SOR,mat,b,x,0);CHKERRQ(ierr); 3634 ierr = PetscObjectStateIncrease((PetscObject)x);CHKERRQ(ierr); 3635 PetscFunctionReturn(0); 3636 } 3637 3638 #undef __FUNCT__ 3639 #define __FUNCT__ "MatCopy_Basic" 3640 /* 3641 Default matrix copy routine. 3642 */ 3643 PetscErrorCode MatCopy_Basic(Mat A,Mat B,MatStructure str) 3644 { 3645 PetscErrorCode ierr; 3646 PetscInt i,rstart = 0,rend = 0,nz; 3647 const PetscInt *cwork; 3648 const PetscScalar *vwork; 3649 3650 PetscFunctionBegin; 3651 if (B->assembled) { 3652 ierr = MatZeroEntries(B);CHKERRQ(ierr); 3653 } 3654 ierr = MatGetOwnershipRange(A,&rstart,&rend);CHKERRQ(ierr); 3655 for (i=rstart; i<rend; i++) { 3656 ierr = MatGetRow(A,i,&nz,&cwork,&vwork);CHKERRQ(ierr); 3657 ierr = MatSetValues(B,1,&i,nz,cwork,vwork,INSERT_VALUES);CHKERRQ(ierr); 3658 ierr = MatRestoreRow(A,i,&nz,&cwork,&vwork);CHKERRQ(ierr); 3659 } 3660 ierr = MatAssemblyBegin(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 3661 ierr = MatAssemblyEnd(B,MAT_FINAL_ASSEMBLY);CHKERRQ(ierr); 3662 ierr = PetscObjectStateIncrease((PetscObject)B);CHKERRQ(ierr); 3663 PetscFunctionReturn(0); 3664 } 3665 3666 #undef __FUNCT__ 3667 #define __FUNCT__ "MatCopy" 3668 /*@ 3669 MatCopy - Copys a matrix to another matrix. 3670 3671 Collective on Mat 3672 3673 Input Parameters: 3674 + A - the matrix 3675 - str - SAME_NONZERO_PATTERN or DIFFERENT_NONZERO_PATTERN 3676 3677 Output Parameter: 3678 . B - where the copy is put 3679 3680 Notes: 3681 If you use SAME_NONZERO_PATTERN then the two matrices had better have the 3682 same nonzero pattern or the routine will crash. 3683 3684 MatCopy() copies the matrix entries of a matrix to another existing 3685 matrix (after first zeroing the second matrix). A related routine is 3686 MatConvert(), which first creates a new matrix and then copies the data. 3687 3688 Level: intermediate 3689 3690 Concepts: matrices^copying 3691 3692 .seealso: MatConvert(), MatDuplicate() 3693 3694 @*/ 3695 PetscErrorCode MatCopy(Mat A,Mat B,MatStructure str) 3696 { 3697 PetscErrorCode ierr; 3698 PetscInt i; 3699 3700 PetscFunctionBegin; 3701 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 3702 PetscValidHeaderSpecific(B,MAT_CLASSID,2); 3703 PetscValidType(A,1); 3704 PetscValidType(B,2); 3705 PetscCheckSameComm(A,1,B,2); 3706 MatCheckPreallocated(B,2); 3707 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 3708 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 3709 if (A->rmap->N != B->rmap->N || A->cmap->N != B->cmap->N) SETERRQ4(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Mat A,Mat B: global dim (%D,%D) (%D,%D)",A->rmap->N,B->rmap->N,A->cmap->N,B->cmap->N); 3710 MatCheckPreallocated(A,1); 3711 3712 ierr = PetscLogEventBegin(MAT_Copy,A,B,0,0);CHKERRQ(ierr); 3713 if (A->ops->copy) { 3714 ierr = (*A->ops->copy)(A,B,str);CHKERRQ(ierr); 3715 } else { /* generic conversion */ 3716 ierr = MatCopy_Basic(A,B,str);CHKERRQ(ierr); 3717 } 3718 3719 B->stencil.dim = A->stencil.dim; 3720 B->stencil.noc = A->stencil.noc; 3721 for (i=0; i<=A->stencil.dim; i++) { 3722 B->stencil.dims[i] = A->stencil.dims[i]; 3723 B->stencil.starts[i] = A->stencil.starts[i]; 3724 } 3725 3726 ierr = PetscLogEventEnd(MAT_Copy,A,B,0,0);CHKERRQ(ierr); 3727 ierr = PetscObjectStateIncrease((PetscObject)B);CHKERRQ(ierr); 3728 PetscFunctionReturn(0); 3729 } 3730 3731 #undef __FUNCT__ 3732 #define __FUNCT__ "MatConvert" 3733 /*@C 3734 MatConvert - Converts a matrix to another matrix, either of the same 3735 or different type. 3736 3737 Collective on Mat 3738 3739 Input Parameters: 3740 + mat - the matrix 3741 . newtype - new matrix type. Use MATSAME to create a new matrix of the 3742 same type as the original matrix. 3743 - reuse - denotes if the destination matrix is to be created or reused. Currently 3744 MAT_REUSE_MATRIX is only supported for inplace conversion, otherwise use 3745 MAT_INITIAL_MATRIX. 3746 3747 Output Parameter: 3748 . M - pointer to place new matrix 3749 3750 Notes: 3751 MatConvert() first creates a new matrix and then copies the data from 3752 the first matrix. A related routine is MatCopy(), which copies the matrix 3753 entries of one matrix to another already existing matrix context. 3754 3755 Cannot be used to convert a sequential matrix to parallel or parallel to sequential, 3756 the MPI communicator of the generated matrix is always the same as the communicator 3757 of the input matrix. 3758 3759 Level: intermediate 3760 3761 Concepts: matrices^converting between storage formats 3762 3763 .seealso: MatCopy(), MatDuplicate() 3764 @*/ 3765 PetscErrorCode MatConvert(Mat mat, MatType newtype,MatReuse reuse,Mat *M) 3766 { 3767 PetscErrorCode ierr; 3768 PetscBool sametype,issame,flg; 3769 char convname[256],mtype[256]; 3770 Mat B; 3771 3772 PetscFunctionBegin; 3773 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3774 PetscValidType(mat,1); 3775 PetscValidPointer(M,3); 3776 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 3777 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 3778 MatCheckPreallocated(mat,1); 3779 ierr = MatSetOption(mat,MAT_NEW_NONZERO_LOCATION_ERR,PETSC_FALSE);CHKERRQ(ierr); 3780 3781 ierr = PetscOptionsGetString(((PetscObject)mat)->prefix,"-matconvert_type",mtype,256,&flg);CHKERRQ(ierr); 3782 if (flg) { 3783 newtype = mtype; 3784 } 3785 ierr = PetscObjectTypeCompare((PetscObject)mat,newtype,&sametype);CHKERRQ(ierr); 3786 ierr = PetscStrcmp(newtype,"same",&issame);CHKERRQ(ierr); 3787 if ((reuse == MAT_REUSE_MATRIX) && (mat != *M)) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"MAT_REUSE_MATRIX only supported for in-place conversion currently"); 3788 3789 if ((reuse == MAT_REUSE_MATRIX) && (issame || sametype)) PetscFunctionReturn(0); 3790 3791 if ((sametype || issame) && (reuse==MAT_INITIAL_MATRIX) && mat->ops->duplicate) { 3792 ierr = (*mat->ops->duplicate)(mat,MAT_COPY_VALUES,M);CHKERRQ(ierr); 3793 } else { 3794 PetscErrorCode (*conv)(Mat, MatType,MatReuse,Mat*)=NULL; 3795 const char *prefix[3] = {"seq","mpi",""}; 3796 PetscInt i; 3797 /* 3798 Order of precedence: 3799 1) See if a specialized converter is known to the current matrix. 3800 2) See if a specialized converter is known to the desired matrix class. 3801 3) See if a good general converter is registered for the desired class 3802 (as of 6/27/03 only MATMPIADJ falls into this category). 3803 4) See if a good general converter is known for the current matrix. 3804 5) Use a really basic converter. 3805 */ 3806 3807 /* 1) See if a specialized converter is known to the current matrix and the desired class */ 3808 for (i=0; i<3; i++) { 3809 ierr = PetscStrcpy(convname,"MatConvert_");CHKERRQ(ierr); 3810 ierr = PetscStrcat(convname,((PetscObject)mat)->type_name);CHKERRQ(ierr); 3811 ierr = PetscStrcat(convname,"_");CHKERRQ(ierr); 3812 ierr = PetscStrcat(convname,prefix[i]);CHKERRQ(ierr); 3813 ierr = PetscStrcat(convname,issame ? ((PetscObject)mat)->type_name : newtype);CHKERRQ(ierr); 3814 ierr = PetscStrcat(convname,"_C");CHKERRQ(ierr); 3815 ierr = PetscObjectQueryFunction((PetscObject)mat,convname,(void (**)(void))&conv);CHKERRQ(ierr); 3816 if (conv) goto foundconv; 3817 } 3818 3819 /* 2) See if a specialized converter is known to the desired matrix class. */ 3820 ierr = MatCreate(PetscObjectComm((PetscObject)mat),&B);CHKERRQ(ierr); 3821 ierr = MatSetSizes(B,mat->rmap->n,mat->cmap->n,mat->rmap->N,mat->cmap->N);CHKERRQ(ierr); 3822 ierr = MatSetType(B,newtype);CHKERRQ(ierr); 3823 for (i=0; i<3; i++) { 3824 ierr = PetscStrcpy(convname,"MatConvert_");CHKERRQ(ierr); 3825 ierr = PetscStrcat(convname,((PetscObject)mat)->type_name);CHKERRQ(ierr); 3826 ierr = PetscStrcat(convname,"_");CHKERRQ(ierr); 3827 ierr = PetscStrcat(convname,prefix[i]);CHKERRQ(ierr); 3828 ierr = PetscStrcat(convname,newtype);CHKERRQ(ierr); 3829 ierr = PetscStrcat(convname,"_C");CHKERRQ(ierr); 3830 ierr = PetscObjectQueryFunction((PetscObject)B,convname,(void (**)(void))&conv);CHKERRQ(ierr); 3831 if (conv) { 3832 ierr = MatDestroy(&B);CHKERRQ(ierr); 3833 goto foundconv; 3834 } 3835 } 3836 3837 /* 3) See if a good general converter is registered for the desired class */ 3838 conv = B->ops->convertfrom; 3839 ierr = MatDestroy(&B);CHKERRQ(ierr); 3840 if (conv) goto foundconv; 3841 3842 /* 4) See if a good general converter is known for the current matrix */ 3843 if (mat->ops->convert) { 3844 conv = mat->ops->convert; 3845 } 3846 if (conv) goto foundconv; 3847 3848 /* 5) Use a really basic converter. */ 3849 conv = MatConvert_Basic; 3850 3851 foundconv: 3852 ierr = PetscLogEventBegin(MAT_Convert,mat,0,0,0);CHKERRQ(ierr); 3853 ierr = (*conv)(mat,newtype,reuse,M);CHKERRQ(ierr); 3854 ierr = PetscLogEventEnd(MAT_Convert,mat,0,0,0);CHKERRQ(ierr); 3855 } 3856 ierr = PetscObjectStateIncrease((PetscObject)*M);CHKERRQ(ierr); 3857 3858 /* Copy Mat options */ 3859 if (mat->symmetric) {ierr = MatSetOption(*M,MAT_SYMMETRIC,PETSC_TRUE);CHKERRQ(ierr);} 3860 if (mat->hermitian) {ierr = MatSetOption(*M,MAT_HERMITIAN,PETSC_TRUE);CHKERRQ(ierr);} 3861 PetscFunctionReturn(0); 3862 } 3863 3864 #undef __FUNCT__ 3865 #define __FUNCT__ "MatFactorGetSolverPackage" 3866 /*@C 3867 MatFactorGetSolverPackage - Returns name of the package providing the factorization routines 3868 3869 Not Collective 3870 3871 Input Parameter: 3872 . mat - the matrix, must be a factored matrix 3873 3874 Output Parameter: 3875 . type - the string name of the package (do not free this string) 3876 3877 Notes: 3878 In Fortran you pass in a empty string and the package name will be copied into it. 3879 (Make sure the string is long enough) 3880 3881 Level: intermediate 3882 3883 .seealso: MatCopy(), MatDuplicate(), MatGetFactorAvailable(), MatGetFactor() 3884 @*/ 3885 PetscErrorCode MatFactorGetSolverPackage(Mat mat, const MatSolverPackage *type) 3886 { 3887 PetscErrorCode ierr, (*conv)(Mat,const MatSolverPackage*); 3888 3889 PetscFunctionBegin; 3890 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3891 PetscValidType(mat,1); 3892 if (!mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Only for factored matrix"); 3893 ierr = PetscObjectQueryFunction((PetscObject)mat,"MatFactorGetSolverPackage_C",(void (**)(void))&conv);CHKERRQ(ierr); 3894 if (!conv) { 3895 *type = MATSOLVERPETSC; 3896 } else { 3897 ierr = (*conv)(mat,type);CHKERRQ(ierr); 3898 } 3899 PetscFunctionReturn(0); 3900 } 3901 3902 #undef __FUNCT__ 3903 #define __FUNCT__ "MatGetFactor" 3904 /*@C 3905 MatGetFactor - Returns a matrix suitable to calls to MatXXFactorSymbolic() 3906 3907 Collective on Mat 3908 3909 Input Parameters: 3910 + mat - the matrix 3911 . type - name of solver type, for example, superlu, petsc (to use PETSc's default) 3912 - ftype - factor type, MAT_FACTOR_LU, MAT_FACTOR_CHOLESKY, MAT_FACTOR_ICC, MAT_FACTOR_ILU, 3913 3914 Output Parameters: 3915 . f - the factor matrix used with MatXXFactorSymbolic() calls 3916 3917 Notes: 3918 Some PETSc matrix formats have alternative solvers available that are contained in alternative packages 3919 such as pastix, superlu, mumps etc. 3920 3921 PETSc must have been ./configure to use the external solver, using the option --download-package 3922 3923 Level: intermediate 3924 3925 .seealso: MatCopy(), MatDuplicate(), MatGetFactorAvailable() 3926 @*/ 3927 PetscErrorCode MatGetFactor(Mat mat, const MatSolverPackage type,MatFactorType ftype,Mat *f) 3928 { 3929 PetscErrorCode ierr,(*conv)(Mat,MatFactorType,Mat*); 3930 char convname[256]; 3931 3932 PetscFunctionBegin; 3933 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3934 PetscValidType(mat,1); 3935 3936 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 3937 MatCheckPreallocated(mat,1); 3938 3939 ierr = PetscStrcpy(convname,"MatGetFactor_");CHKERRQ(ierr); 3940 ierr = PetscStrcat(convname,type);CHKERRQ(ierr); 3941 ierr = PetscStrcat(convname,"_C");CHKERRQ(ierr); 3942 ierr = PetscObjectQueryFunction((PetscObject)mat,convname,(void (**)(void))&conv);CHKERRQ(ierr); 3943 if (!conv) { 3944 PetscBool flag; 3945 MPI_Comm comm; 3946 3947 ierr = PetscObjectGetComm((PetscObject)mat,&comm);CHKERRQ(ierr); 3948 ierr = PetscStrcasecmp(MATSOLVERPETSC,type,&flag);CHKERRQ(ierr); 3949 if (flag) SETERRQ2(comm,PETSC_ERR_SUP,"Matrix format %s does not have a built-in PETSc %s",((PetscObject)mat)->type_name,MatFactorTypes[ftype]); 3950 else SETERRQ4(comm,PETSC_ERR_SUP,"Matrix format %s does not have a solver package %s for %s. Perhaps you must ./configure with --download-%s",((PetscObject)mat)->type_name,type,MatFactorTypes[ftype],type); 3951 } 3952 ierr = (*conv)(mat,ftype,f);CHKERRQ(ierr); 3953 PetscFunctionReturn(0); 3954 } 3955 3956 #undef __FUNCT__ 3957 #define __FUNCT__ "MatGetFactorAvailable" 3958 /*@C 3959 MatGetFactorAvailable - Returns a a flag if matrix supports particular package and factor type 3960 3961 Not Collective 3962 3963 Input Parameters: 3964 + mat - the matrix 3965 . type - name of solver type, for example, superlu, petsc (to use PETSc's default) 3966 - ftype - factor type, MAT_FACTOR_LU, MAT_FACTOR_CHOLESKY, MAT_FACTOR_ICC, MAT_FACTOR_ILU, 3967 3968 Output Parameter: 3969 . flg - PETSC_TRUE if the factorization is available 3970 3971 Notes: 3972 Some PETSc matrix formats have alternative solvers available that are contained in alternative packages 3973 such as pastix, superlu, mumps etc. 3974 3975 PETSc must have been ./configure to use the external solver, using the option --download-package 3976 3977 Level: intermediate 3978 3979 .seealso: MatCopy(), MatDuplicate(), MatGetFactor() 3980 @*/ 3981 PetscErrorCode MatGetFactorAvailable(Mat mat, const MatSolverPackage type,MatFactorType ftype,PetscBool *flg) 3982 { 3983 PetscErrorCode ierr, (*conv)(Mat,MatFactorType,PetscBool*); 3984 char convname[256]; 3985 3986 PetscFunctionBegin; 3987 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 3988 PetscValidType(mat,1); 3989 3990 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 3991 MatCheckPreallocated(mat,1); 3992 3993 ierr = PetscStrcpy(convname,"MatGetFactorAvailable_");CHKERRQ(ierr); 3994 ierr = PetscStrcat(convname,type);CHKERRQ(ierr); 3995 ierr = PetscStrcat(convname,"_C");CHKERRQ(ierr); 3996 ierr = PetscObjectQueryFunction((PetscObject)mat,convname,(void (**)(void))&conv);CHKERRQ(ierr); 3997 if (!conv) { 3998 *flg = PETSC_FALSE; 3999 } else { 4000 ierr = (*conv)(mat,ftype,flg);CHKERRQ(ierr); 4001 } 4002 PetscFunctionReturn(0); 4003 } 4004 4005 4006 #undef __FUNCT__ 4007 #define __FUNCT__ "MatDuplicate" 4008 /*@ 4009 MatDuplicate - Duplicates a matrix including the non-zero structure. 4010 4011 Collective on Mat 4012 4013 Input Parameters: 4014 + mat - the matrix 4015 - op - either MAT_DO_NOT_COPY_VALUES or MAT_COPY_VALUES, cause it to copy the numerical values in the matrix 4016 MAT_SHARE_NONZERO_PATTERN to share the nonzero patterns with the previous matrix and not copy them. 4017 4018 Output Parameter: 4019 . M - pointer to place new matrix 4020 4021 Level: intermediate 4022 4023 Concepts: matrices^duplicating 4024 4025 Notes: You cannot change the nonzero pattern for the parent or child matrix if you use MAT_SHARE_NONZERO_PATTERN. 4026 4027 .seealso: MatCopy(), MatConvert() 4028 @*/ 4029 PetscErrorCode MatDuplicate(Mat mat,MatDuplicateOption op,Mat *M) 4030 { 4031 PetscErrorCode ierr; 4032 Mat B; 4033 PetscInt i; 4034 4035 PetscFunctionBegin; 4036 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4037 PetscValidType(mat,1); 4038 PetscValidPointer(M,3); 4039 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4040 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 4041 MatCheckPreallocated(mat,1); 4042 4043 *M = 0; 4044 if (!mat->ops->duplicate) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Not written for this matrix type"); 4045 ierr = PetscLogEventBegin(MAT_Convert,mat,0,0,0);CHKERRQ(ierr); 4046 ierr = (*mat->ops->duplicate)(mat,op,M);CHKERRQ(ierr); 4047 B = *M; 4048 4049 B->stencil.dim = mat->stencil.dim; 4050 B->stencil.noc = mat->stencil.noc; 4051 for (i=0; i<=mat->stencil.dim; i++) { 4052 B->stencil.dims[i] = mat->stencil.dims[i]; 4053 B->stencil.starts[i] = mat->stencil.starts[i]; 4054 } 4055 4056 B->nooffproczerorows = mat->nooffproczerorows; 4057 B->nooffprocentries = mat->nooffprocentries; 4058 4059 ierr = PetscLogEventEnd(MAT_Convert,mat,0,0,0);CHKERRQ(ierr); 4060 ierr = PetscObjectStateIncrease((PetscObject)B);CHKERRQ(ierr); 4061 PetscFunctionReturn(0); 4062 } 4063 4064 #undef __FUNCT__ 4065 #define __FUNCT__ "MatGetDiagonal" 4066 /*@ 4067 MatGetDiagonal - Gets the diagonal of a matrix. 4068 4069 Logically Collective on Mat and Vec 4070 4071 Input Parameters: 4072 + mat - the matrix 4073 - v - the vector for storing the diagonal 4074 4075 Output Parameter: 4076 . v - the diagonal of the matrix 4077 4078 Level: intermediate 4079 4080 Note: 4081 Currently only correct in parallel for square matrices. 4082 4083 Concepts: matrices^accessing diagonals 4084 4085 .seealso: MatGetRow(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMaxAbs() 4086 @*/ 4087 PetscErrorCode MatGetDiagonal(Mat mat,Vec v) 4088 { 4089 PetscErrorCode ierr; 4090 4091 PetscFunctionBegin; 4092 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4093 PetscValidType(mat,1); 4094 PetscValidHeaderSpecific(v,VEC_CLASSID,2); 4095 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4096 if (!mat->ops->getdiagonal) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 4097 MatCheckPreallocated(mat,1); 4098 4099 ierr = (*mat->ops->getdiagonal)(mat,v);CHKERRQ(ierr); 4100 ierr = PetscObjectStateIncrease((PetscObject)v);CHKERRQ(ierr); 4101 PetscFunctionReturn(0); 4102 } 4103 4104 #undef __FUNCT__ 4105 #define __FUNCT__ "MatGetRowMin" 4106 /*@ 4107 MatGetRowMin - Gets the minimum value (of the real part) of each 4108 row of the matrix 4109 4110 Logically Collective on Mat and Vec 4111 4112 Input Parameters: 4113 . mat - the matrix 4114 4115 Output Parameter: 4116 + v - the vector for storing the maximums 4117 - idx - the indices of the column found for each row (optional) 4118 4119 Level: intermediate 4120 4121 Notes: The result of this call are the same as if one converted the matrix to dense format 4122 and found the minimum value in each row (i.e. the implicit zeros are counted as zeros). 4123 4124 This code is only implemented for a couple of matrix formats. 4125 4126 Concepts: matrices^getting row maximums 4127 4128 .seealso: MatGetDiagonal(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMaxAbs(), 4129 MatGetRowMax() 4130 @*/ 4131 PetscErrorCode MatGetRowMin(Mat mat,Vec v,PetscInt idx[]) 4132 { 4133 PetscErrorCode ierr; 4134 4135 PetscFunctionBegin; 4136 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4137 PetscValidType(mat,1); 4138 PetscValidHeaderSpecific(v,VEC_CLASSID,2); 4139 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4140 if (!mat->ops->getrowmax) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 4141 MatCheckPreallocated(mat,1); 4142 4143 ierr = (*mat->ops->getrowmin)(mat,v,idx);CHKERRQ(ierr); 4144 ierr = PetscObjectStateIncrease((PetscObject)v);CHKERRQ(ierr); 4145 PetscFunctionReturn(0); 4146 } 4147 4148 #undef __FUNCT__ 4149 #define __FUNCT__ "MatGetRowMinAbs" 4150 /*@ 4151 MatGetRowMinAbs - Gets the minimum value (in absolute value) of each 4152 row of the matrix 4153 4154 Logically Collective on Mat and Vec 4155 4156 Input Parameters: 4157 . mat - the matrix 4158 4159 Output Parameter: 4160 + v - the vector for storing the minimums 4161 - idx - the indices of the column found for each row (or NULL if not needed) 4162 4163 Level: intermediate 4164 4165 Notes: if a row is completely empty or has only 0.0 values then the idx[] value for that 4166 row is 0 (the first column). 4167 4168 This code is only implemented for a couple of matrix formats. 4169 4170 Concepts: matrices^getting row maximums 4171 4172 .seealso: MatGetDiagonal(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMax(), MatGetRowMaxAbs(), MatGetRowMin() 4173 @*/ 4174 PetscErrorCode MatGetRowMinAbs(Mat mat,Vec v,PetscInt idx[]) 4175 { 4176 PetscErrorCode ierr; 4177 4178 PetscFunctionBegin; 4179 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4180 PetscValidType(mat,1); 4181 PetscValidHeaderSpecific(v,VEC_CLASSID,2); 4182 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4183 if (!mat->ops->getrowminabs) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 4184 MatCheckPreallocated(mat,1); 4185 if (idx) {ierr = PetscMemzero(idx,mat->rmap->n*sizeof(PetscInt));CHKERRQ(ierr);} 4186 4187 ierr = (*mat->ops->getrowminabs)(mat,v,idx);CHKERRQ(ierr); 4188 ierr = PetscObjectStateIncrease((PetscObject)v);CHKERRQ(ierr); 4189 PetscFunctionReturn(0); 4190 } 4191 4192 #undef __FUNCT__ 4193 #define __FUNCT__ "MatGetRowMax" 4194 /*@ 4195 MatGetRowMax - Gets the maximum value (of the real part) of each 4196 row of the matrix 4197 4198 Logically Collective on Mat and Vec 4199 4200 Input Parameters: 4201 . mat - the matrix 4202 4203 Output Parameter: 4204 + v - the vector for storing the maximums 4205 - idx - the indices of the column found for each row (optional) 4206 4207 Level: intermediate 4208 4209 Notes: The result of this call are the same as if one converted the matrix to dense format 4210 and found the minimum value in each row (i.e. the implicit zeros are counted as zeros). 4211 4212 This code is only implemented for a couple of matrix formats. 4213 4214 Concepts: matrices^getting row maximums 4215 4216 .seealso: MatGetDiagonal(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMaxAbs(), MatGetRowMin() 4217 @*/ 4218 PetscErrorCode MatGetRowMax(Mat mat,Vec v,PetscInt idx[]) 4219 { 4220 PetscErrorCode ierr; 4221 4222 PetscFunctionBegin; 4223 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4224 PetscValidType(mat,1); 4225 PetscValidHeaderSpecific(v,VEC_CLASSID,2); 4226 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4227 if (!mat->ops->getrowmax) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 4228 MatCheckPreallocated(mat,1); 4229 4230 ierr = (*mat->ops->getrowmax)(mat,v,idx);CHKERRQ(ierr); 4231 ierr = PetscObjectStateIncrease((PetscObject)v);CHKERRQ(ierr); 4232 PetscFunctionReturn(0); 4233 } 4234 4235 #undef __FUNCT__ 4236 #define __FUNCT__ "MatGetRowMaxAbs" 4237 /*@ 4238 MatGetRowMaxAbs - Gets the maximum value (in absolute value) of each 4239 row of the matrix 4240 4241 Logically Collective on Mat and Vec 4242 4243 Input Parameters: 4244 . mat - the matrix 4245 4246 Output Parameter: 4247 + v - the vector for storing the maximums 4248 - idx - the indices of the column found for each row (or NULL if not needed) 4249 4250 Level: intermediate 4251 4252 Notes: if a row is completely empty or has only 0.0 values then the idx[] value for that 4253 row is 0 (the first column). 4254 4255 This code is only implemented for a couple of matrix formats. 4256 4257 Concepts: matrices^getting row maximums 4258 4259 .seealso: MatGetDiagonal(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMax(), MatGetRowMin() 4260 @*/ 4261 PetscErrorCode MatGetRowMaxAbs(Mat mat,Vec v,PetscInt idx[]) 4262 { 4263 PetscErrorCode ierr; 4264 4265 PetscFunctionBegin; 4266 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4267 PetscValidType(mat,1); 4268 PetscValidHeaderSpecific(v,VEC_CLASSID,2); 4269 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4270 if (!mat->ops->getrowmaxabs) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 4271 MatCheckPreallocated(mat,1); 4272 if (idx) {ierr = PetscMemzero(idx,mat->rmap->n*sizeof(PetscInt));CHKERRQ(ierr);} 4273 4274 ierr = (*mat->ops->getrowmaxabs)(mat,v,idx);CHKERRQ(ierr); 4275 ierr = PetscObjectStateIncrease((PetscObject)v);CHKERRQ(ierr); 4276 PetscFunctionReturn(0); 4277 } 4278 4279 #undef __FUNCT__ 4280 #define __FUNCT__ "MatGetRowSum" 4281 /*@ 4282 MatGetRowSum - Gets the sum of each row of the matrix 4283 4284 Logically Collective on Mat and Vec 4285 4286 Input Parameters: 4287 . mat - the matrix 4288 4289 Output Parameter: 4290 . v - the vector for storing the sum of rows 4291 4292 Level: intermediate 4293 4294 Notes: This code is slow since it is not currently specialized for different formats 4295 4296 Concepts: matrices^getting row sums 4297 4298 .seealso: MatGetDiagonal(), MatGetSubMatrices(), MatGetSubmatrix(), MatGetRowMax(), MatGetRowMin() 4299 @*/ 4300 PetscErrorCode MatGetRowSum(Mat mat, Vec v) 4301 { 4302 PetscInt start = 0, end = 0, row; 4303 PetscScalar *array; 4304 PetscErrorCode ierr; 4305 4306 PetscFunctionBegin; 4307 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4308 PetscValidType(mat,1); 4309 PetscValidHeaderSpecific(v,VEC_CLASSID,2); 4310 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4311 MatCheckPreallocated(mat,1); 4312 ierr = MatGetOwnershipRange(mat, &start, &end);CHKERRQ(ierr); 4313 ierr = VecGetArray(v, &array);CHKERRQ(ierr); 4314 for (row = start; row < end; ++row) { 4315 PetscInt ncols, col; 4316 const PetscInt *cols; 4317 const PetscScalar *vals; 4318 4319 array[row - start] = 0.0; 4320 4321 ierr = MatGetRow(mat, row, &ncols, &cols, &vals);CHKERRQ(ierr); 4322 for (col = 0; col < ncols; col++) { 4323 array[row - start] += vals[col]; 4324 } 4325 ierr = MatRestoreRow(mat, row, &ncols, &cols, &vals);CHKERRQ(ierr); 4326 } 4327 ierr = VecRestoreArray(v, &array);CHKERRQ(ierr); 4328 ierr = PetscObjectStateIncrease((PetscObject) v);CHKERRQ(ierr); 4329 PetscFunctionReturn(0); 4330 } 4331 4332 #undef __FUNCT__ 4333 #define __FUNCT__ "MatTranspose" 4334 /*@ 4335 MatTranspose - Computes an in-place or out-of-place transpose of a matrix. 4336 4337 Collective on Mat 4338 4339 Input Parameter: 4340 + mat - the matrix to transpose 4341 - reuse - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 4342 4343 Output Parameters: 4344 . B - the transpose 4345 4346 Notes: 4347 If you pass in &mat for B the transpose will be done in place, for example MatTranspose(mat,MAT_REUSE_MATRIX,&mat); 4348 4349 Consider using MatCreateTranspose() instead if you only need a matrix that behaves like the transpose, but don't need the storage to be changed. 4350 4351 Level: intermediate 4352 4353 Concepts: matrices^transposing 4354 4355 .seealso: MatMultTranspose(), MatMultTransposeAdd(), MatIsTranspose(), MatReuse 4356 @*/ 4357 PetscErrorCode MatTranspose(Mat mat,MatReuse reuse,Mat *B) 4358 { 4359 PetscErrorCode ierr; 4360 4361 PetscFunctionBegin; 4362 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4363 PetscValidType(mat,1); 4364 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4365 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 4366 if (!mat->ops->transpose) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 4367 MatCheckPreallocated(mat,1); 4368 4369 ierr = PetscLogEventBegin(MAT_Transpose,mat,0,0,0);CHKERRQ(ierr); 4370 ierr = (*mat->ops->transpose)(mat,reuse,B);CHKERRQ(ierr); 4371 ierr = PetscLogEventEnd(MAT_Transpose,mat,0,0,0);CHKERRQ(ierr); 4372 if (B) {ierr = PetscObjectStateIncrease((PetscObject)*B);CHKERRQ(ierr);} 4373 PetscFunctionReturn(0); 4374 } 4375 4376 #undef __FUNCT__ 4377 #define __FUNCT__ "MatIsTranspose" 4378 /*@ 4379 MatIsTranspose - Test whether a matrix is another one's transpose, 4380 or its own, in which case it tests symmetry. 4381 4382 Collective on Mat 4383 4384 Input Parameter: 4385 + A - the matrix to test 4386 - B - the matrix to test against, this can equal the first parameter 4387 4388 Output Parameters: 4389 . flg - the result 4390 4391 Notes: 4392 Only available for SeqAIJ/MPIAIJ matrices. The sequential algorithm 4393 has a running time of the order of the number of nonzeros; the parallel 4394 test involves parallel copies of the block-offdiagonal parts of the matrix. 4395 4396 Level: intermediate 4397 4398 Concepts: matrices^transposing, matrix^symmetry 4399 4400 .seealso: MatTranspose(), MatIsSymmetric(), MatIsHermitian() 4401 @*/ 4402 PetscErrorCode MatIsTranspose(Mat A,Mat B,PetscReal tol,PetscBool *flg) 4403 { 4404 PetscErrorCode ierr,(*f)(Mat,Mat,PetscReal,PetscBool*),(*g)(Mat,Mat,PetscReal,PetscBool*); 4405 4406 PetscFunctionBegin; 4407 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 4408 PetscValidHeaderSpecific(B,MAT_CLASSID,2); 4409 PetscValidPointer(flg,3); 4410 ierr = PetscObjectQueryFunction((PetscObject)A,"MatIsTranspose_C",(void (**)(void))&f);CHKERRQ(ierr); 4411 ierr = PetscObjectQueryFunction((PetscObject)B,"MatIsTranspose_C",(void (**)(void))&g);CHKERRQ(ierr); 4412 *flg = PETSC_FALSE; 4413 if (f && g) { 4414 if (f == g) { 4415 ierr = (*f)(A,B,tol,flg);CHKERRQ(ierr); 4416 } else SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_NOTSAMETYPE,"Matrices do not have the same comparator for symmetry test"); 4417 } else { 4418 MatType mattype; 4419 if (!f) { 4420 ierr = MatGetType(A,&mattype);CHKERRQ(ierr); 4421 } else { 4422 ierr = MatGetType(B,&mattype);CHKERRQ(ierr); 4423 } 4424 SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Matrix of type <%s> does not support checking for transpose",mattype); 4425 } 4426 PetscFunctionReturn(0); 4427 } 4428 4429 #undef __FUNCT__ 4430 #define __FUNCT__ "MatHermitianTranspose" 4431 /*@ 4432 MatHermitianTranspose - Computes an in-place or out-of-place transpose of a matrix in complex conjugate. 4433 4434 Collective on Mat 4435 4436 Input Parameter: 4437 + mat - the matrix to transpose and complex conjugate 4438 - reuse - store the transpose matrix in the provided B 4439 4440 Output Parameters: 4441 . B - the Hermitian 4442 4443 Notes: 4444 If you pass in &mat for B the Hermitian will be done in place 4445 4446 Level: intermediate 4447 4448 Concepts: matrices^transposing, complex conjugatex 4449 4450 .seealso: MatTranspose(), MatMultTranspose(), MatMultTransposeAdd(), MatIsTranspose(), MatReuse 4451 @*/ 4452 PetscErrorCode MatHermitianTranspose(Mat mat,MatReuse reuse,Mat *B) 4453 { 4454 PetscErrorCode ierr; 4455 4456 PetscFunctionBegin; 4457 ierr = MatTranspose(mat,reuse,B);CHKERRQ(ierr); 4458 #if defined(PETSC_USE_COMPLEX) 4459 ierr = MatConjugate(*B);CHKERRQ(ierr); 4460 #endif 4461 PetscFunctionReturn(0); 4462 } 4463 4464 #undef __FUNCT__ 4465 #define __FUNCT__ "MatIsHermitianTranspose" 4466 /*@ 4467 MatIsHermitianTranspose - Test whether a matrix is another one's Hermitian transpose, 4468 4469 Collective on Mat 4470 4471 Input Parameter: 4472 + A - the matrix to test 4473 - B - the matrix to test against, this can equal the first parameter 4474 4475 Output Parameters: 4476 . flg - the result 4477 4478 Notes: 4479 Only available for SeqAIJ/MPIAIJ matrices. The sequential algorithm 4480 has a running time of the order of the number of nonzeros; the parallel 4481 test involves parallel copies of the block-offdiagonal parts of the matrix. 4482 4483 Level: intermediate 4484 4485 Concepts: matrices^transposing, matrix^symmetry 4486 4487 .seealso: MatTranspose(), MatIsSymmetric(), MatIsHermitian(), MatIsTranspose() 4488 @*/ 4489 PetscErrorCode MatIsHermitianTranspose(Mat A,Mat B,PetscReal tol,PetscBool *flg) 4490 { 4491 PetscErrorCode ierr,(*f)(Mat,Mat,PetscReal,PetscBool*),(*g)(Mat,Mat,PetscReal,PetscBool*); 4492 4493 PetscFunctionBegin; 4494 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 4495 PetscValidHeaderSpecific(B,MAT_CLASSID,2); 4496 PetscValidPointer(flg,3); 4497 ierr = PetscObjectQueryFunction((PetscObject)A,"MatIsHermitianTranspose_C",(void (**)(void))&f);CHKERRQ(ierr); 4498 ierr = PetscObjectQueryFunction((PetscObject)B,"MatIsHermitianTranspose_C",(void (**)(void))&g);CHKERRQ(ierr); 4499 if (f && g) { 4500 if (f==g) { 4501 ierr = (*f)(A,B,tol,flg);CHKERRQ(ierr); 4502 } else SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_NOTSAMETYPE,"Matrices do not have the same comparator for Hermitian test"); 4503 } 4504 PetscFunctionReturn(0); 4505 } 4506 4507 #undef __FUNCT__ 4508 #define __FUNCT__ "MatPermute" 4509 /*@ 4510 MatPermute - Creates a new matrix with rows and columns permuted from the 4511 original. 4512 4513 Collective on Mat 4514 4515 Input Parameters: 4516 + mat - the matrix to permute 4517 . row - row permutation, each processor supplies only the permutation for its rows 4518 - col - column permutation, each processor supplies only the permutation for its columns 4519 4520 Output Parameters: 4521 . B - the permuted matrix 4522 4523 Level: advanced 4524 4525 Note: 4526 The index sets map from row/col of permuted matrix to row/col of original matrix. 4527 The index sets should be on the same communicator as Mat and have the same local sizes. 4528 4529 Concepts: matrices^permuting 4530 4531 .seealso: MatGetOrdering(), ISAllGather() 4532 4533 @*/ 4534 PetscErrorCode MatPermute(Mat mat,IS row,IS col,Mat *B) 4535 { 4536 PetscErrorCode ierr; 4537 4538 PetscFunctionBegin; 4539 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4540 PetscValidType(mat,1); 4541 PetscValidHeaderSpecific(row,IS_CLASSID,2); 4542 PetscValidHeaderSpecific(col,IS_CLASSID,3); 4543 PetscValidPointer(B,4); 4544 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4545 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 4546 if (!mat->ops->permute) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"MatPermute not available for Mat type %s",((PetscObject)mat)->type_name); 4547 MatCheckPreallocated(mat,1); 4548 4549 ierr = (*mat->ops->permute)(mat,row,col,B);CHKERRQ(ierr); 4550 ierr = PetscObjectStateIncrease((PetscObject)*B);CHKERRQ(ierr); 4551 PetscFunctionReturn(0); 4552 } 4553 4554 #undef __FUNCT__ 4555 #define __FUNCT__ "MatEqual" 4556 /*@ 4557 MatEqual - Compares two matrices. 4558 4559 Collective on Mat 4560 4561 Input Parameters: 4562 + A - the first matrix 4563 - B - the second matrix 4564 4565 Output Parameter: 4566 . flg - PETSC_TRUE if the matrices are equal; PETSC_FALSE otherwise. 4567 4568 Level: intermediate 4569 4570 Concepts: matrices^equality between 4571 @*/ 4572 PetscErrorCode MatEqual(Mat A,Mat B,PetscBool *flg) 4573 { 4574 PetscErrorCode ierr; 4575 4576 PetscFunctionBegin; 4577 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 4578 PetscValidHeaderSpecific(B,MAT_CLASSID,2); 4579 PetscValidType(A,1); 4580 PetscValidType(B,2); 4581 PetscValidIntPointer(flg,3); 4582 PetscCheckSameComm(A,1,B,2); 4583 MatCheckPreallocated(B,2); 4584 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4585 if (!B->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4586 if (A->rmap->N != B->rmap->N || A->cmap->N != B->cmap->N) SETERRQ4(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Mat A,Mat B: global dim %D %D %D %D",A->rmap->N,B->rmap->N,A->cmap->N,B->cmap->N); 4587 if (!A->ops->equal) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"Mat type %s",((PetscObject)A)->type_name); 4588 if (!B->ops->equal) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"Mat type %s",((PetscObject)B)->type_name); 4589 if (A->ops->equal != B->ops->equal) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_INCOMP,"A is type: %s\nB is type: %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name); 4590 MatCheckPreallocated(A,1); 4591 4592 ierr = (*A->ops->equal)(A,B,flg);CHKERRQ(ierr); 4593 PetscFunctionReturn(0); 4594 } 4595 4596 #undef __FUNCT__ 4597 #define __FUNCT__ "MatDiagonalScale" 4598 /*@ 4599 MatDiagonalScale - Scales a matrix on the left and right by diagonal 4600 matrices that are stored as vectors. Either of the two scaling 4601 matrices can be NULL. 4602 4603 Collective on Mat 4604 4605 Input Parameters: 4606 + mat - the matrix to be scaled 4607 . l - the left scaling vector (or NULL) 4608 - r - the right scaling vector (or NULL) 4609 4610 Notes: 4611 MatDiagonalScale() computes A = LAR, where 4612 L = a diagonal matrix (stored as a vector), R = a diagonal matrix (stored as a vector) 4613 The L scales the rows of the matrix, the R scales the columns of the matrix. 4614 4615 Level: intermediate 4616 4617 Concepts: matrices^diagonal scaling 4618 Concepts: diagonal scaling of matrices 4619 4620 .seealso: MatScale() 4621 @*/ 4622 PetscErrorCode MatDiagonalScale(Mat mat,Vec l,Vec r) 4623 { 4624 PetscErrorCode ierr; 4625 4626 PetscFunctionBegin; 4627 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4628 PetscValidType(mat,1); 4629 if (!mat->ops->diagonalscale) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 4630 if (l) {PetscValidHeaderSpecific(l,VEC_CLASSID,2);PetscCheckSameComm(mat,1,l,2);} 4631 if (r) {PetscValidHeaderSpecific(r,VEC_CLASSID,3);PetscCheckSameComm(mat,1,r,3);} 4632 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4633 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 4634 MatCheckPreallocated(mat,1); 4635 4636 ierr = PetscLogEventBegin(MAT_Scale,mat,0,0,0);CHKERRQ(ierr); 4637 ierr = (*mat->ops->diagonalscale)(mat,l,r);CHKERRQ(ierr); 4638 ierr = PetscLogEventEnd(MAT_Scale,mat,0,0,0);CHKERRQ(ierr); 4639 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 4640 #if defined(PETSC_HAVE_CUSP) 4641 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 4642 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 4643 } 4644 #endif 4645 PetscFunctionReturn(0); 4646 } 4647 4648 #undef __FUNCT__ 4649 #define __FUNCT__ "MatScale" 4650 /*@ 4651 MatScale - Scales all elements of a matrix by a given number. 4652 4653 Logically Collective on Mat 4654 4655 Input Parameters: 4656 + mat - the matrix to be scaled 4657 - a - the scaling value 4658 4659 Output Parameter: 4660 . mat - the scaled matrix 4661 4662 Level: intermediate 4663 4664 Concepts: matrices^scaling all entries 4665 4666 .seealso: MatDiagonalScale() 4667 @*/ 4668 PetscErrorCode MatScale(Mat mat,PetscScalar a) 4669 { 4670 PetscErrorCode ierr; 4671 4672 PetscFunctionBegin; 4673 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4674 PetscValidType(mat,1); 4675 if (a != (PetscScalar)1.0 && !mat->ops->scale) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 4676 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4677 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 4678 PetscValidLogicalCollectiveScalar(mat,a,2); 4679 MatCheckPreallocated(mat,1); 4680 4681 ierr = PetscLogEventBegin(MAT_Scale,mat,0,0,0);CHKERRQ(ierr); 4682 if (a != (PetscScalar)1.0) { 4683 ierr = (*mat->ops->scale)(mat,a);CHKERRQ(ierr); 4684 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 4685 } 4686 ierr = PetscLogEventEnd(MAT_Scale,mat,0,0,0);CHKERRQ(ierr); 4687 #if defined(PETSC_HAVE_CUSP) 4688 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 4689 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 4690 } 4691 #endif 4692 PetscFunctionReturn(0); 4693 } 4694 4695 #undef __FUNCT__ 4696 #define __FUNCT__ "MatNorm" 4697 /*@ 4698 MatNorm - Calculates various norms of a matrix. 4699 4700 Collective on Mat 4701 4702 Input Parameters: 4703 + mat - the matrix 4704 - type - the type of norm, NORM_1, NORM_FROBENIUS, NORM_INFINITY 4705 4706 Output Parameters: 4707 . nrm - the resulting norm 4708 4709 Level: intermediate 4710 4711 Concepts: matrices^norm 4712 Concepts: norm^of matrix 4713 @*/ 4714 PetscErrorCode MatNorm(Mat mat,NormType type,PetscReal *nrm) 4715 { 4716 PetscErrorCode ierr; 4717 4718 PetscFunctionBegin; 4719 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4720 PetscValidType(mat,1); 4721 PetscValidScalarPointer(nrm,3); 4722 4723 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 4724 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 4725 if (!mat->ops->norm) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 4726 MatCheckPreallocated(mat,1); 4727 4728 ierr = (*mat->ops->norm)(mat,type,nrm);CHKERRQ(ierr); 4729 PetscFunctionReturn(0); 4730 } 4731 4732 /* 4733 This variable is used to prevent counting of MatAssemblyBegin() that 4734 are called from within a MatAssemblyEnd(). 4735 */ 4736 static PetscInt MatAssemblyEnd_InUse = 0; 4737 #undef __FUNCT__ 4738 #define __FUNCT__ "MatAssemblyBegin" 4739 /*@ 4740 MatAssemblyBegin - Begins assembling the matrix. This routine should 4741 be called after completing all calls to MatSetValues(). 4742 4743 Collective on Mat 4744 4745 Input Parameters: 4746 + mat - the matrix 4747 - type - type of assembly, either MAT_FLUSH_ASSEMBLY or MAT_FINAL_ASSEMBLY 4748 4749 Notes: 4750 MatSetValues() generally caches the values. The matrix is ready to 4751 use only after MatAssemblyBegin() and MatAssemblyEnd() have been called. 4752 Use MAT_FLUSH_ASSEMBLY when switching between ADD_VALUES and INSERT_VALUES 4753 in MatSetValues(); use MAT_FINAL_ASSEMBLY for the final assembly before 4754 using the matrix. 4755 4756 ALL processes that share a matrix MUST call MatAssemblyBegin() and MatAssemblyEnd() the SAME NUMBER of times, and each time with the 4757 same flag of MAT_FLUSH_ASSEMBLY or MAT_FINAL_ASSEMBLY for all processes. Thus you CANNOT locally change from ADD_VALUES to INSERT_VALUES, that is 4758 a global collective operation requring all processes that share the matrix. 4759 4760 Space for preallocated nonzeros that is not filled by a call to MatSetValues() or a related routine are compressed 4761 out by assembly. If you intend to use that extra space on a subsequent assembly, be sure to insert explicit zeros 4762 before MAT_FINAL_ASSEMBLY so the space is not compressed out. 4763 4764 Level: beginner 4765 4766 Concepts: matrices^assembling 4767 4768 .seealso: MatAssemblyEnd(), MatSetValues(), MatAssembled() 4769 @*/ 4770 PetscErrorCode MatAssemblyBegin(Mat mat,MatAssemblyType type) 4771 { 4772 PetscErrorCode ierr; 4773 4774 PetscFunctionBegin; 4775 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4776 PetscValidType(mat,1); 4777 MatCheckPreallocated(mat,1); 4778 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix.\nDid you forget to call MatSetUnfactored()?"); 4779 if (mat->assembled) { 4780 mat->was_assembled = PETSC_TRUE; 4781 mat->assembled = PETSC_FALSE; 4782 } 4783 if (!MatAssemblyEnd_InUse) { 4784 ierr = PetscLogEventBegin(MAT_AssemblyBegin,mat,0,0,0);CHKERRQ(ierr); 4785 if (mat->ops->assemblybegin) {ierr = (*mat->ops->assemblybegin)(mat,type);CHKERRQ(ierr);} 4786 ierr = PetscLogEventEnd(MAT_AssemblyBegin,mat,0,0,0);CHKERRQ(ierr); 4787 } else if (mat->ops->assemblybegin) { 4788 ierr = (*mat->ops->assemblybegin)(mat,type);CHKERRQ(ierr); 4789 } 4790 PetscFunctionReturn(0); 4791 } 4792 4793 #undef __FUNCT__ 4794 #define __FUNCT__ "MatAssembled" 4795 /*@ 4796 MatAssembled - Indicates if a matrix has been assembled and is ready for 4797 use; for example, in matrix-vector product. 4798 4799 Not Collective 4800 4801 Input Parameter: 4802 . mat - the matrix 4803 4804 Output Parameter: 4805 . assembled - PETSC_TRUE or PETSC_FALSE 4806 4807 Level: advanced 4808 4809 Concepts: matrices^assembled? 4810 4811 .seealso: MatAssemblyEnd(), MatSetValues(), MatAssemblyBegin() 4812 @*/ 4813 PetscErrorCode MatAssembled(Mat mat,PetscBool *assembled) 4814 { 4815 PetscFunctionBegin; 4816 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4817 PetscValidType(mat,1); 4818 PetscValidPointer(assembled,2); 4819 *assembled = mat->assembled; 4820 PetscFunctionReturn(0); 4821 } 4822 4823 #undef __FUNCT__ 4824 #define __FUNCT__ "MatViewFromOptions" 4825 /* 4826 Processes command line options to determine if/how a matrix 4827 is to be viewed. Called by MatAssemblyEnd() and MatLoad(). 4828 */ 4829 PetscErrorCode MatViewFromOptions(Mat mat,const char optionname[]) 4830 { 4831 PetscErrorCode ierr; 4832 PetscViewer viewer; 4833 PetscBool flg; 4834 static PetscBool incall = PETSC_FALSE; 4835 PetscViewerFormat format; 4836 4837 PetscFunctionBegin; 4838 if (incall) PetscFunctionReturn(0); 4839 incall = PETSC_TRUE; 4840 ierr = PetscOptionsGetViewer(PetscObjectComm((PetscObject)mat),((PetscObject)mat)->prefix,optionname,&viewer,&format,&flg);CHKERRQ(ierr); 4841 if (flg) { 4842 ierr = PetscViewerPushFormat(viewer,format);CHKERRQ(ierr); 4843 ierr = MatView(mat,viewer);CHKERRQ(ierr); 4844 ierr = PetscViewerPopFormat(viewer);CHKERRQ(ierr); 4845 ierr = PetscViewerDestroy(&viewer);CHKERRQ(ierr); 4846 } 4847 incall = PETSC_FALSE; 4848 PetscFunctionReturn(0); 4849 } 4850 4851 #undef __FUNCT__ 4852 #define __FUNCT__ "MatAssemblyEnd" 4853 /*@ 4854 MatAssemblyEnd - Completes assembling the matrix. This routine should 4855 be called after MatAssemblyBegin(). 4856 4857 Collective on Mat 4858 4859 Input Parameters: 4860 + mat - the matrix 4861 - type - type of assembly, either MAT_FLUSH_ASSEMBLY or MAT_FINAL_ASSEMBLY 4862 4863 Options Database Keys: 4864 + -mat_view ::ascii_info - Prints info on matrix at conclusion of MatEndAssembly() 4865 . -mat_view ::ascii_info_detail - Prints more detailed info 4866 . -mat_view - Prints matrix in ASCII format 4867 . -mat_view ::ascii_matlab - Prints matrix in Matlab format 4868 . -mat_view draw - PetscDraws nonzero structure of matrix, using MatView() and PetscDrawOpenX(). 4869 . -display <name> - Sets display name (default is host) 4870 . -draw_pause <sec> - Sets number of seconds to pause after display 4871 . -mat_view socket - Sends matrix to socket, can be accessed from Matlab (See the <a href="../../docs/manual.pdf">users manual</a>) 4872 . -viewer_socket_machine <machine> 4873 . -viewer_socket_port <port> 4874 . -mat_view binary - save matrix to file in binary format 4875 - -viewer_binary_filename <name> 4876 4877 Notes: 4878 MatSetValues() generally caches the values. The matrix is ready to 4879 use only after MatAssemblyBegin() and MatAssemblyEnd() have been called. 4880 Use MAT_FLUSH_ASSEMBLY when switching between ADD_VALUES and INSERT_VALUES 4881 in MatSetValues(); use MAT_FINAL_ASSEMBLY for the final assembly before 4882 using the matrix. 4883 4884 Space for preallocated nonzeros that is not filled by a call to MatSetValues() or a related routine are compressed 4885 out by assembly. If you intend to use that extra space on a subsequent assembly, be sure to insert explicit zeros 4886 before MAT_FINAL_ASSEMBLY so the space is not compressed out. 4887 4888 Level: beginner 4889 4890 .seealso: MatAssemblyBegin(), MatSetValues(), PetscDrawOpenX(), PetscDrawCreate(), MatView(), MatAssembled(), PetscViewerSocketOpen() 4891 @*/ 4892 PetscErrorCode MatAssemblyEnd(Mat mat,MatAssemblyType type) 4893 { 4894 PetscErrorCode ierr; 4895 static PetscInt inassm = 0; 4896 PetscBool flg = PETSC_FALSE; 4897 4898 PetscFunctionBegin; 4899 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 4900 PetscValidType(mat,1); 4901 4902 inassm++; 4903 MatAssemblyEnd_InUse++; 4904 if (MatAssemblyEnd_InUse == 1) { /* Do the logging only the first time through */ 4905 ierr = PetscLogEventBegin(MAT_AssemblyEnd,mat,0,0,0);CHKERRQ(ierr); 4906 if (mat->ops->assemblyend) { 4907 ierr = (*mat->ops->assemblyend)(mat,type);CHKERRQ(ierr); 4908 } 4909 ierr = PetscLogEventEnd(MAT_AssemblyEnd,mat,0,0,0);CHKERRQ(ierr); 4910 } else if (mat->ops->assemblyend) { 4911 ierr = (*mat->ops->assemblyend)(mat,type);CHKERRQ(ierr); 4912 } 4913 4914 /* Flush assembly is not a true assembly */ 4915 if (type != MAT_FLUSH_ASSEMBLY) { 4916 mat->assembled = PETSC_TRUE; mat->num_ass++; 4917 } 4918 mat->insertmode = NOT_SET_VALUES; 4919 MatAssemblyEnd_InUse--; 4920 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 4921 if (!mat->symmetric_eternal) { 4922 mat->symmetric_set = PETSC_FALSE; 4923 mat->hermitian_set = PETSC_FALSE; 4924 mat->structurally_symmetric_set = PETSC_FALSE; 4925 } 4926 #if defined(PETSC_HAVE_CUSP) 4927 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 4928 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 4929 } 4930 #endif 4931 if (inassm == 1 && type != MAT_FLUSH_ASSEMBLY) { 4932 if (mat->viewonassembly) { 4933 ierr = PetscViewerPushFormat(mat->viewonassembly,mat->viewformatonassembly);CHKERRQ(ierr); 4934 ierr = MatView(mat,mat->viewonassembly);CHKERRQ(ierr); 4935 ierr = PetscViewerPopFormat(mat->viewonassembly);CHKERRQ(ierr); 4936 } 4937 4938 if (mat->checksymmetryonassembly) { 4939 ierr = MatIsSymmetric(mat,mat->checksymmetrytol,&flg);CHKERRQ(ierr); 4940 if (flg) { 4941 ierr = PetscPrintf(PetscObjectComm((PetscObject)mat),"Matrix is symmetric (tolerance %G)\n",mat->checksymmetrytol);CHKERRQ(ierr); 4942 } else { 4943 ierr = PetscPrintf(PetscObjectComm((PetscObject)mat),"Matrix is not symmetric (tolerance %G)\n",mat->checksymmetrytol);CHKERRQ(ierr); 4944 } 4945 } 4946 if (mat->nullsp && mat->checknullspaceonassembly) { 4947 ierr = MatNullSpaceTest(mat->nullsp,mat,NULL);CHKERRQ(ierr); 4948 } 4949 } 4950 inassm--; 4951 PetscFunctionReturn(0); 4952 } 4953 4954 #undef __FUNCT__ 4955 #define __FUNCT__ "MatSetOption" 4956 /*@ 4957 MatSetOption - Sets a parameter option for a matrix. Some options 4958 may be specific to certain storage formats. Some options 4959 determine how values will be inserted (or added). Sorted, 4960 row-oriented input will generally assemble the fastest. The default 4961 is row-oriented. 4962 4963 Logically Collective on Mat for certain operations, such as MAT_SPD, not collective for MAT_ROW_ORIENTED, see MatOption 4964 4965 Input Parameters: 4966 + mat - the matrix 4967 . option - the option, one of those listed below (and possibly others), 4968 - flg - turn the option on (PETSC_TRUE) or off (PETSC_FALSE) 4969 4970 Options Describing Matrix Structure: 4971 + MAT_SPD - symmetric positive definite 4972 - MAT_SYMMETRIC - symmetric in terms of both structure and value 4973 . MAT_HERMITIAN - transpose is the complex conjugation 4974 . MAT_STRUCTURALLY_SYMMETRIC - symmetric nonzero structure 4975 - MAT_SYMMETRY_ETERNAL - if you would like the symmetry/Hermitian flag 4976 you set to be kept with all future use of the matrix 4977 including after MatAssemblyBegin/End() which could 4978 potentially change the symmetry structure, i.e. you 4979 KNOW the matrix will ALWAYS have the property you set. 4980 4981 4982 Options For Use with MatSetValues(): 4983 Insert a logically dense subblock, which can be 4984 . MAT_ROW_ORIENTED - row-oriented (default) 4985 4986 Note these options reflect the data you pass in with MatSetValues(); it has 4987 nothing to do with how the data is stored internally in the matrix 4988 data structure. 4989 4990 When (re)assembling a matrix, we can restrict the input for 4991 efficiency/debugging purposes. These options include 4992 + MAT_NEW_NONZERO_LOCATIONS - additional insertions will be 4993 allowed if they generate a new nonzero 4994 . MAT_NEW_DIAGONALS - new diagonals will be allowed (for block diagonal format only) 4995 . MAT_IGNORE_OFF_PROC_ENTRIES - drops off-processor entries 4996 . MAT_NEW_NONZERO_LOCATION_ERR - generates an error for new matrix entry 4997 . MAT_USE_HASH_TABLE - uses a hash table to speed up matrix assembly 4998 + MAT_NO_OFF_PROC_ENTRIES - you know each process will only set values for its own rows, will generate an error if 4999 any process sets values for another process. This avoids all reductions in the MatAssembly routines and thus improves 5000 performance for very large process counts. 5001 5002 Notes: 5003 Some options are relevant only for particular matrix types and 5004 are thus ignored by others. Other options are not supported by 5005 certain matrix types and will generate an error message if set. 5006 5007 If using a Fortran 77 module to compute a matrix, one may need to 5008 use the column-oriented option (or convert to the row-oriented 5009 format). 5010 5011 MAT_NEW_NONZERO_LOCATIONS set to PETSC_FALSE indicates that any add or insertion 5012 that would generate a new entry in the nonzero structure is instead 5013 ignored. Thus, if memory has not alredy been allocated for this particular 5014 data, then the insertion is ignored. For dense matrices, in which 5015 the entire array is allocated, no entries are ever ignored. 5016 Set after the first MatAssemblyEnd() 5017 5018 MAT_NEW_NONZERO_LOCATION_ERR indicates that any add or insertion 5019 that would generate a new entry in the nonzero structure instead produces 5020 an error. (Currently supported for AIJ and BAIJ formats only.) 5021 This is a useful flag when using SAME_NONZERO_PATTERN in calling 5022 KSPSetOperators() to ensure that the nonzero pattern truely does 5023 remain unchanged. Set after the first MatAssemblyEnd() 5024 5025 MAT_NEW_NONZERO_ALLOCATION_ERR indicates that any add or insertion 5026 that would generate a new entry that has not been preallocated will 5027 instead produce an error. (Currently supported for AIJ and BAIJ formats 5028 only.) This is a useful flag when debugging matrix memory preallocation. 5029 5030 MAT_IGNORE_OFF_PROC_ENTRIES indicates entries destined for 5031 other processors should be dropped, rather than stashed. 5032 This is useful if you know that the "owning" processor is also 5033 always generating the correct matrix entries, so that PETSc need 5034 not transfer duplicate entries generated on another processor. 5035 5036 MAT_USE_HASH_TABLE indicates that a hash table be used to improve the 5037 searches during matrix assembly. When this flag is set, the hash table 5038 is created during the first Matrix Assembly. This hash table is 5039 used the next time through, during MatSetVaules()/MatSetVaulesBlocked() 5040 to improve the searching of indices. MAT_NEW_NONZERO_LOCATIONS flag 5041 should be used with MAT_USE_HASH_TABLE flag. This option is currently 5042 supported by MATMPIBAIJ format only. 5043 5044 MAT_KEEP_NONZERO_PATTERN indicates when MatZeroRows() is called the zeroed entries 5045 are kept in the nonzero structure 5046 5047 MAT_IGNORE_ZERO_ENTRIES - for AIJ/IS matrices this will stop zero values from creating 5048 a zero location in the matrix 5049 5050 MAT_USE_INODES - indicates using inode version of the code - works with AIJ and 5051 ROWBS matrix types 5052 5053 MAT_NO_OFF_PROC_ZERO_ROWS - you know each process will only zero its own rows. This avoids all reductions in the 5054 zero row routines and thus improves performance for very large process counts. 5055 5056 MAT_IGNORE_LOWER_TRIANGULAR - For SBAIJ matrices will ignore any insertions you make in the lower triangular 5057 part of the matrix (since they should match the upper triangular part). 5058 5059 Notes: Can only be called after MatSetSizes() and MatSetType() have been set. 5060 5061 Level: intermediate 5062 5063 Concepts: matrices^setting options 5064 5065 .seealso: MatOption, Mat 5066 5067 @*/ 5068 PetscErrorCode MatSetOption(Mat mat,MatOption op,PetscBool flg) 5069 { 5070 PetscErrorCode ierr; 5071 5072 PetscFunctionBegin; 5073 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5074 PetscValidType(mat,1); 5075 if (op > 0) PetscValidLogicalCollectiveEnum(mat,op,2); 5076 PetscValidLogicalCollectiveBool(mat,flg,3); 5077 5078 if (((int) op) <= MAT_OPTION_MIN || ((int) op) >= MAT_OPTION_MAX) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_OUTOFRANGE,"Options %d is out of range",(int)op); 5079 if (!((PetscObject)mat)->type_name) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_TYPENOTSET,"Cannot set options until type and size have been set, see MatSetType() and MatSetSizes()"); 5080 5081 switch (op) { 5082 case MAT_NO_OFF_PROC_ENTRIES: 5083 mat->nooffprocentries = flg; 5084 PetscFunctionReturn(0); 5085 break; 5086 case MAT_NO_OFF_PROC_ZERO_ROWS: 5087 mat->nooffproczerorows = flg; 5088 PetscFunctionReturn(0); 5089 break; 5090 case MAT_SPD: 5091 mat->spd_set = PETSC_TRUE; 5092 mat->spd = flg; 5093 if (flg) { 5094 mat->symmetric = PETSC_TRUE; 5095 mat->structurally_symmetric = PETSC_TRUE; 5096 mat->symmetric_set = PETSC_TRUE; 5097 mat->structurally_symmetric_set = PETSC_TRUE; 5098 } 5099 break; 5100 case MAT_SYMMETRIC: 5101 mat->symmetric = flg; 5102 if (flg) mat->structurally_symmetric = PETSC_TRUE; 5103 mat->symmetric_set = PETSC_TRUE; 5104 mat->structurally_symmetric_set = flg; 5105 break; 5106 case MAT_HERMITIAN: 5107 mat->hermitian = flg; 5108 if (flg) mat->structurally_symmetric = PETSC_TRUE; 5109 mat->hermitian_set = PETSC_TRUE; 5110 mat->structurally_symmetric_set = flg; 5111 break; 5112 case MAT_STRUCTURALLY_SYMMETRIC: 5113 mat->structurally_symmetric = flg; 5114 mat->structurally_symmetric_set = PETSC_TRUE; 5115 break; 5116 case MAT_SYMMETRY_ETERNAL: 5117 mat->symmetric_eternal = flg; 5118 break; 5119 default: 5120 break; 5121 } 5122 if (mat->ops->setoption) { 5123 ierr = (*mat->ops->setoption)(mat,op,flg);CHKERRQ(ierr); 5124 } 5125 PetscFunctionReturn(0); 5126 } 5127 5128 #undef __FUNCT__ 5129 #define __FUNCT__ "MatZeroEntries" 5130 /*@ 5131 MatZeroEntries - Zeros all entries of a matrix. For sparse matrices 5132 this routine retains the old nonzero structure. 5133 5134 Logically Collective on Mat 5135 5136 Input Parameters: 5137 . mat - the matrix 5138 5139 Level: intermediate 5140 5141 Notes: If the matrix was not preallocated then a default, likely poor preallocation will be set in the matrix, so this should be called after the preallocation phase. 5142 See the Performance chapter of the users manual for information on preallocating matrices. 5143 5144 Concepts: matrices^zeroing 5145 5146 .seealso: MatZeroRows() 5147 @*/ 5148 PetscErrorCode MatZeroEntries(Mat mat) 5149 { 5150 PetscErrorCode ierr; 5151 5152 PetscFunctionBegin; 5153 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5154 PetscValidType(mat,1); 5155 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 5156 if (mat->insertmode != NOT_SET_VALUES) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for matrices where you have set values but not yet assembled"); 5157 if (!mat->ops->zeroentries) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 5158 MatCheckPreallocated(mat,1); 5159 5160 ierr = PetscLogEventBegin(MAT_ZeroEntries,mat,0,0,0);CHKERRQ(ierr); 5161 ierr = (*mat->ops->zeroentries)(mat);CHKERRQ(ierr); 5162 ierr = PetscLogEventEnd(MAT_ZeroEntries,mat,0,0,0);CHKERRQ(ierr); 5163 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 5164 #if defined(PETSC_HAVE_CUSP) 5165 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 5166 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 5167 } 5168 #endif 5169 PetscFunctionReturn(0); 5170 } 5171 5172 #undef __FUNCT__ 5173 #define __FUNCT__ "MatZeroRowsColumns" 5174 /*@C 5175 MatZeroRowsColumns - Zeros all entries (except possibly the main diagonal) 5176 of a set of rows and columns of a matrix. 5177 5178 Collective on Mat 5179 5180 Input Parameters: 5181 + mat - the matrix 5182 . numRows - the number of rows to remove 5183 . rows - the global row indices 5184 . diag - value put in all diagonals of eliminated rows (0.0 will even eliminate diagonal entry) 5185 . x - optional vector of solutions for zeroed rows (other entries in vector are not used) 5186 - b - optional vector of right hand side, that will be adjusted by provided solution 5187 5188 Notes: 5189 This does not change the nonzero structure of the matrix, it merely zeros those entries in the matrix. 5190 5191 The user can set a value in the diagonal entry (or for the AIJ and 5192 row formats can optionally remove the main diagonal entry from the 5193 nonzero structure as well, by passing 0.0 as the final argument). 5194 5195 For the parallel case, all processes that share the matrix (i.e., 5196 those in the communicator used for matrix creation) MUST call this 5197 routine, regardless of whether any rows being zeroed are owned by 5198 them. 5199 5200 Each processor can indicate any rows in the entire matrix to be zeroed (i.e. each process does NOT have to 5201 list only rows local to itself). 5202 5203 The option MAT_NO_OFF_PROC_ZERO_ROWS does not apply to this routine. 5204 5205 Level: intermediate 5206 5207 Concepts: matrices^zeroing rows 5208 5209 .seealso: MatZeroRowsIS(), MatZeroRowsStencil(), MatZeroEntries(), MatZeroRowsLocal(), MatSetOption(), MatZeroRowsColumnsIS() 5210 @*/ 5211 PetscErrorCode MatZeroRowsColumns(Mat mat,PetscInt numRows,const PetscInt rows[],PetscScalar diag,Vec x,Vec b) 5212 { 5213 PetscErrorCode ierr; 5214 5215 PetscFunctionBegin; 5216 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5217 PetscValidType(mat,1); 5218 if (numRows) PetscValidIntPointer(rows,3); 5219 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 5220 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 5221 if (!mat->ops->zerorowscolumns) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 5222 MatCheckPreallocated(mat,1); 5223 5224 ierr = (*mat->ops->zerorowscolumns)(mat,numRows,rows,diag,x,b);CHKERRQ(ierr); 5225 if (mat->viewonassembly) { 5226 ierr = PetscViewerPushFormat(mat->viewonassembly,mat->viewformatonassembly);CHKERRQ(ierr); 5227 ierr = MatView(mat,mat->viewonassembly);CHKERRQ(ierr); 5228 ierr = PetscViewerPopFormat(mat->viewonassembly);CHKERRQ(ierr); 5229 } 5230 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 5231 #if defined(PETSC_HAVE_CUSP) 5232 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 5233 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 5234 } 5235 #endif 5236 PetscFunctionReturn(0); 5237 } 5238 5239 #undef __FUNCT__ 5240 #define __FUNCT__ "MatZeroRowsColumnsIS" 5241 /*@C 5242 MatZeroRowsColumnsIS - Zeros all entries (except possibly the main diagonal) 5243 of a set of rows and columns of a matrix. 5244 5245 Collective on Mat 5246 5247 Input Parameters: 5248 + mat - the matrix 5249 . is - the rows to zero 5250 . diag - value put in all diagonals of eliminated rows (0.0 will even eliminate diagonal entry) 5251 . x - optional vector of solutions for zeroed rows (other entries in vector are not used) 5252 - b - optional vector of right hand side, that will be adjusted by provided solution 5253 5254 Notes: 5255 This does not change the nonzero structure of the matrix, it merely zeros those entries in the matrix. 5256 5257 The user can set a value in the diagonal entry (or for the AIJ and 5258 row formats can optionally remove the main diagonal entry from the 5259 nonzero structure as well, by passing 0.0 as the final argument). 5260 5261 For the parallel case, all processes that share the matrix (i.e., 5262 those in the communicator used for matrix creation) MUST call this 5263 routine, regardless of whether any rows being zeroed are owned by 5264 them. 5265 5266 Each processor can indicate any rows in the entire matrix to be zeroed (i.e. each process does NOT have to 5267 list only rows local to itself). 5268 5269 The option MAT_NO_OFF_PROC_ZERO_ROWS does not apply to this routine. 5270 5271 Level: intermediate 5272 5273 Concepts: matrices^zeroing rows 5274 5275 .seealso: MatZeroRowsIS(), MatZeroRowsStencil(), MatZeroEntries(), MatZeroRowsLocal(), MatSetOption(), MatZeroRowsColumns() 5276 @*/ 5277 PetscErrorCode MatZeroRowsColumnsIS(Mat mat,IS is,PetscScalar diag,Vec x,Vec b) 5278 { 5279 PetscErrorCode ierr; 5280 PetscInt numRows; 5281 const PetscInt *rows; 5282 5283 PetscFunctionBegin; 5284 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5285 PetscValidHeaderSpecific(is,IS_CLASSID,2); 5286 PetscValidType(mat,1); 5287 PetscValidType(is,2); 5288 ierr = ISGetLocalSize(is,&numRows);CHKERRQ(ierr); 5289 ierr = ISGetIndices(is,&rows);CHKERRQ(ierr); 5290 ierr = MatZeroRowsColumns(mat,numRows,rows,diag,x,b);CHKERRQ(ierr); 5291 ierr = ISRestoreIndices(is,&rows);CHKERRQ(ierr); 5292 PetscFunctionReturn(0); 5293 } 5294 5295 #undef __FUNCT__ 5296 #define __FUNCT__ "MatZeroRows" 5297 /*@C 5298 MatZeroRows - Zeros all entries (except possibly the main diagonal) 5299 of a set of rows of a matrix. 5300 5301 Collective on Mat 5302 5303 Input Parameters: 5304 + mat - the matrix 5305 . numRows - the number of rows to remove 5306 . rows - the global row indices 5307 . diag - value put in all diagonals of eliminated rows (0.0 will even eliminate diagonal entry) 5308 . x - optional vector of solutions for zeroed rows (other entries in vector are not used) 5309 - b - optional vector of right hand side, that will be adjusted by provided solution 5310 5311 Notes: 5312 For the AIJ and BAIJ matrix formats this removes the old nonzero structure, 5313 but does not release memory. For the dense and block diagonal 5314 formats this does not alter the nonzero structure. 5315 5316 If the option MatSetOption(mat,MAT_KEEP_NONZERO_PATTERN,PETSC_TRUE) the nonzero structure 5317 of the matrix is not changed (even for AIJ and BAIJ matrices) the values are 5318 merely zeroed. 5319 5320 The user can set a value in the diagonal entry (or for the AIJ and 5321 row formats can optionally remove the main diagonal entry from the 5322 nonzero structure as well, by passing 0.0 as the final argument). 5323 5324 For the parallel case, all processes that share the matrix (i.e., 5325 those in the communicator used for matrix creation) MUST call this 5326 routine, regardless of whether any rows being zeroed are owned by 5327 them. 5328 5329 Each processor can indicate any rows in the entire matrix to be zeroed (i.e. each process does NOT have to 5330 list only rows local to itself). 5331 5332 You can call MatSetOption(mat,MAT_NO_OFF_PROC_ZERO_ROWS,PETSC_TRUE) if each process indicates only rows it 5333 owns that are to be zeroed. This saves a global synchronization in the implementation. 5334 5335 Level: intermediate 5336 5337 Concepts: matrices^zeroing rows 5338 5339 .seealso: MatZeroRowsIS(), MatZeroRowsStencil(), MatZeroEntries(), MatZeroRowsLocal(), MatSetOption() 5340 @*/ 5341 PetscErrorCode MatZeroRows(Mat mat,PetscInt numRows,const PetscInt rows[],PetscScalar diag,Vec x,Vec b) 5342 { 5343 PetscErrorCode ierr; 5344 5345 PetscFunctionBegin; 5346 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5347 PetscValidType(mat,1); 5348 if (numRows) PetscValidIntPointer(rows,3); 5349 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 5350 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 5351 if (!mat->ops->zerorows) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 5352 MatCheckPreallocated(mat,1); 5353 5354 ierr = (*mat->ops->zerorows)(mat,numRows,rows,diag,x,b);CHKERRQ(ierr); 5355 if (mat->viewonassembly) { 5356 ierr = PetscViewerPushFormat(mat->viewonassembly,mat->viewformatonassembly);CHKERRQ(ierr); 5357 ierr = MatView(mat,mat->viewonassembly);CHKERRQ(ierr); 5358 ierr = PetscViewerPopFormat(mat->viewonassembly);CHKERRQ(ierr); 5359 } 5360 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 5361 #if defined(PETSC_HAVE_CUSP) 5362 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 5363 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 5364 } 5365 #endif 5366 PetscFunctionReturn(0); 5367 } 5368 5369 #undef __FUNCT__ 5370 #define __FUNCT__ "MatZeroRowsIS" 5371 /*@C 5372 MatZeroRowsIS - Zeros all entries (except possibly the main diagonal) 5373 of a set of rows of a matrix. 5374 5375 Collective on Mat 5376 5377 Input Parameters: 5378 + mat - the matrix 5379 . is - index set of rows to remove 5380 . diag - value put in all diagonals of eliminated rows 5381 . x - optional vector of solutions for zeroed rows (other entries in vector are not used) 5382 - b - optional vector of right hand side, that will be adjusted by provided solution 5383 5384 Notes: 5385 For the AIJ and BAIJ matrix formats this removes the old nonzero structure, 5386 but does not release memory. For the dense and block diagonal 5387 formats this does not alter the nonzero structure. 5388 5389 If the option MatSetOption(mat,MAT_KEEP_NONZERO_PATTERN,PETSC_TRUE) the nonzero structure 5390 of the matrix is not changed (even for AIJ and BAIJ matrices) the values are 5391 merely zeroed. 5392 5393 The user can set a value in the diagonal entry (or for the AIJ and 5394 row formats can optionally remove the main diagonal entry from the 5395 nonzero structure as well, by passing 0.0 as the final argument). 5396 5397 For the parallel case, all processes that share the matrix (i.e., 5398 those in the communicator used for matrix creation) MUST call this 5399 routine, regardless of whether any rows being zeroed are owned by 5400 them. 5401 5402 Each processor can indicate any rows in the entire matrix to be zeroed (i.e. each process does NOT have to 5403 list only rows local to itself). 5404 5405 You can call MatSetOption(mat,MAT_NO_OFF_PROC_ZERO_ROWS,PETSC_TRUE) if each process indicates only rows it 5406 owns that are to be zeroed. This saves a global synchronization in the implementation. 5407 5408 Level: intermediate 5409 5410 Concepts: matrices^zeroing rows 5411 5412 .seealso: MatZeroRows(), MatZeroRowsStencil(), MatZeroEntries(), MatZeroRowsLocal(), MatSetOption() 5413 @*/ 5414 PetscErrorCode MatZeroRowsIS(Mat mat,IS is,PetscScalar diag,Vec x,Vec b) 5415 { 5416 PetscInt numRows; 5417 const PetscInt *rows; 5418 PetscErrorCode ierr; 5419 5420 PetscFunctionBegin; 5421 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5422 PetscValidType(mat,1); 5423 PetscValidHeaderSpecific(is,IS_CLASSID,2); 5424 ierr = ISGetLocalSize(is,&numRows);CHKERRQ(ierr); 5425 ierr = ISGetIndices(is,&rows);CHKERRQ(ierr); 5426 ierr = MatZeroRows(mat,numRows,rows,diag,x,b);CHKERRQ(ierr); 5427 ierr = ISRestoreIndices(is,&rows);CHKERRQ(ierr); 5428 PetscFunctionReturn(0); 5429 } 5430 5431 #undef __FUNCT__ 5432 #define __FUNCT__ "MatZeroRowsStencil" 5433 /*@C 5434 MatZeroRowsStencil - Zeros all entries (except possibly the main diagonal) 5435 of a set of rows of a matrix. These rows must be local to the process. 5436 5437 Collective on Mat 5438 5439 Input Parameters: 5440 + mat - the matrix 5441 . numRows - the number of rows to remove 5442 . rows - the grid coordinates (and component number when dof > 1) for matrix rows 5443 . diag - value put in all diagonals of eliminated rows (0.0 will even eliminate diagonal entry) 5444 . x - optional vector of solutions for zeroed rows (other entries in vector are not used) 5445 - b - optional vector of right hand side, that will be adjusted by provided solution 5446 5447 Notes: 5448 For the AIJ and BAIJ matrix formats this removes the old nonzero structure, 5449 but does not release memory. For the dense and block diagonal 5450 formats this does not alter the nonzero structure. 5451 5452 If the option MatSetOption(mat,MAT_KEEP_NONZERO_PATTERN,PETSC_TRUE) the nonzero structure 5453 of the matrix is not changed (even for AIJ and BAIJ matrices) the values are 5454 merely zeroed. 5455 5456 The user can set a value in the diagonal entry (or for the AIJ and 5457 row formats can optionally remove the main diagonal entry from the 5458 nonzero structure as well, by passing 0.0 as the final argument). 5459 5460 For the parallel case, all processes that share the matrix (i.e., 5461 those in the communicator used for matrix creation) MUST call this 5462 routine, regardless of whether any rows being zeroed are owned by 5463 them. 5464 5465 Each processor can indicate any rows in the entire matrix to be zeroed (i.e. each process does NOT have to 5466 list only rows local to itself). 5467 5468 The grid coordinates are across the entire grid, not just the local portion 5469 5470 In Fortran idxm and idxn should be declared as 5471 $ MatStencil idxm(4,m) 5472 and the values inserted using 5473 $ idxm(MatStencil_i,1) = i 5474 $ idxm(MatStencil_j,1) = j 5475 $ idxm(MatStencil_k,1) = k 5476 $ idxm(MatStencil_c,1) = c 5477 etc 5478 5479 For periodic boundary conditions use negative indices for values to the left (below 0; that are to be 5480 obtained by wrapping values from right edge). For values to the right of the last entry using that index plus one 5481 etc to obtain values that obtained by wrapping the values from the left edge. This does not work for anything but the 5482 DMDA_BOUNDARY_PERIODIC boundary type. 5483 5484 For indices that don't mean anything for your case (like the k index when working in 2d) or the c index when you have 5485 a single value per point) you can skip filling those indices. 5486 5487 Level: intermediate 5488 5489 Concepts: matrices^zeroing rows 5490 5491 .seealso: MatZeroRows(), MatZeroRowsIS(), MatZeroEntries(), MatZeroRowsLocal(), MatSetOption() 5492 @*/ 5493 PetscErrorCode MatZeroRowsStencil(Mat mat,PetscInt numRows,const MatStencil rows[],PetscScalar diag,Vec x,Vec b) 5494 { 5495 PetscInt dim = mat->stencil.dim; 5496 PetscInt sdim = dim - (1 - (PetscInt) mat->stencil.noc); 5497 PetscInt *dims = mat->stencil.dims+1; 5498 PetscInt *starts = mat->stencil.starts; 5499 PetscInt *dxm = (PetscInt*) rows; 5500 PetscInt *jdxm, i, j, tmp, numNewRows = 0; 5501 PetscErrorCode ierr; 5502 5503 PetscFunctionBegin; 5504 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5505 PetscValidType(mat,1); 5506 if (numRows) PetscValidIntPointer(rows,3); 5507 5508 ierr = PetscMalloc(numRows*sizeof(PetscInt), &jdxm);CHKERRQ(ierr); 5509 for (i = 0; i < numRows; ++i) { 5510 /* Skip unused dimensions (they are ordered k, j, i, c) */ 5511 for (j = 0; j < 3-sdim; ++j) dxm++; 5512 /* Local index in X dir */ 5513 tmp = *dxm++ - starts[0]; 5514 /* Loop over remaining dimensions */ 5515 for (j = 0; j < dim-1; ++j) { 5516 /* If nonlocal, set index to be negative */ 5517 if ((*dxm++ - starts[j+1]) < 0 || tmp < 0) tmp = PETSC_MIN_INT; 5518 /* Update local index */ 5519 else tmp = tmp*dims[j] + *(dxm-1) - starts[j+1]; 5520 } 5521 /* Skip component slot if necessary */ 5522 if (mat->stencil.noc) dxm++; 5523 /* Local row number */ 5524 if (tmp >= 0) { 5525 jdxm[numNewRows++] = tmp; 5526 } 5527 } 5528 ierr = MatZeroRowsLocal(mat,numNewRows,jdxm,diag,x,b);CHKERRQ(ierr); 5529 ierr = PetscFree(jdxm);CHKERRQ(ierr); 5530 PetscFunctionReturn(0); 5531 } 5532 5533 #undef __FUNCT__ 5534 #define __FUNCT__ "MatZeroRowsColumnsStencil" 5535 /*@C 5536 MatZeroRowsColumnsStencil - Zeros all row and column entries (except possibly the main diagonal) 5537 of a set of rows and columns of a matrix. 5538 5539 Collective on Mat 5540 5541 Input Parameters: 5542 + mat - the matrix 5543 . numRows - the number of rows/columns to remove 5544 . rows - the grid coordinates (and component number when dof > 1) for matrix rows 5545 . diag - value put in all diagonals of eliminated rows (0.0 will even eliminate diagonal entry) 5546 . x - optional vector of solutions for zeroed rows (other entries in vector are not used) 5547 - b - optional vector of right hand side, that will be adjusted by provided solution 5548 5549 Notes: 5550 For the AIJ and BAIJ matrix formats this removes the old nonzero structure, 5551 but does not release memory. For the dense and block diagonal 5552 formats this does not alter the nonzero structure. 5553 5554 If the option MatSetOption(mat,MAT_KEEP_NONZERO_PATTERN,PETSC_TRUE) the nonzero structure 5555 of the matrix is not changed (even for AIJ and BAIJ matrices) the values are 5556 merely zeroed. 5557 5558 The user can set a value in the diagonal entry (or for the AIJ and 5559 row formats can optionally remove the main diagonal entry from the 5560 nonzero structure as well, by passing 0.0 as the final argument). 5561 5562 For the parallel case, all processes that share the matrix (i.e., 5563 those in the communicator used for matrix creation) MUST call this 5564 routine, regardless of whether any rows being zeroed are owned by 5565 them. 5566 5567 Each processor can indicate any rows in the entire matrix to be zeroed (i.e. each process does NOT have to 5568 list only rows local to itself, but the row/column numbers are given in local numbering). 5569 5570 The grid coordinates are across the entire grid, not just the local portion 5571 5572 In Fortran idxm and idxn should be declared as 5573 $ MatStencil idxm(4,m) 5574 and the values inserted using 5575 $ idxm(MatStencil_i,1) = i 5576 $ idxm(MatStencil_j,1) = j 5577 $ idxm(MatStencil_k,1) = k 5578 $ idxm(MatStencil_c,1) = c 5579 etc 5580 5581 For periodic boundary conditions use negative indices for values to the left (below 0; that are to be 5582 obtained by wrapping values from right edge). For values to the right of the last entry using that index plus one 5583 etc to obtain values that obtained by wrapping the values from the left edge. This does not work for anything but the 5584 DMDA_BOUNDARY_PERIODIC boundary type. 5585 5586 For indices that don't mean anything for your case (like the k index when working in 2d) or the c index when you have 5587 a single value per point) you can skip filling those indices. 5588 5589 Level: intermediate 5590 5591 Concepts: matrices^zeroing rows 5592 5593 .seealso: MatZeroRows(), MatZeroRowsIS(), MatZeroEntries(), MatZeroRowsLocal(), MatSetOption() 5594 @*/ 5595 PetscErrorCode MatZeroRowsColumnsStencil(Mat mat,PetscInt numRows,const MatStencil rows[],PetscScalar diag,Vec x,Vec b) 5596 { 5597 PetscInt dim = mat->stencil.dim; 5598 PetscInt sdim = dim - (1 - (PetscInt) mat->stencil.noc); 5599 PetscInt *dims = mat->stencil.dims+1; 5600 PetscInt *starts = mat->stencil.starts; 5601 PetscInt *dxm = (PetscInt*) rows; 5602 PetscInt *jdxm, i, j, tmp, numNewRows = 0; 5603 PetscErrorCode ierr; 5604 5605 PetscFunctionBegin; 5606 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5607 PetscValidType(mat,1); 5608 if (numRows) PetscValidIntPointer(rows,3); 5609 5610 ierr = PetscMalloc(numRows*sizeof(PetscInt), &jdxm);CHKERRQ(ierr); 5611 for (i = 0; i < numRows; ++i) { 5612 /* Skip unused dimensions (they are ordered k, j, i, c) */ 5613 for (j = 0; j < 3-sdim; ++j) dxm++; 5614 /* Local index in X dir */ 5615 tmp = *dxm++ - starts[0]; 5616 /* Loop over remaining dimensions */ 5617 for (j = 0; j < dim-1; ++j) { 5618 /* If nonlocal, set index to be negative */ 5619 if ((*dxm++ - starts[j+1]) < 0 || tmp < 0) tmp = PETSC_MIN_INT; 5620 /* Update local index */ 5621 else tmp = tmp*dims[j] + *(dxm-1) - starts[j+1]; 5622 } 5623 /* Skip component slot if necessary */ 5624 if (mat->stencil.noc) dxm++; 5625 /* Local row number */ 5626 if (tmp >= 0) { 5627 jdxm[numNewRows++] = tmp; 5628 } 5629 } 5630 ierr = MatZeroRowsColumnsLocal(mat,numNewRows,jdxm,diag,x,b);CHKERRQ(ierr); 5631 ierr = PetscFree(jdxm);CHKERRQ(ierr); 5632 PetscFunctionReturn(0); 5633 } 5634 5635 #undef __FUNCT__ 5636 #define __FUNCT__ "MatZeroRowsLocal" 5637 /*@C 5638 MatZeroRowsLocal - Zeros all entries (except possibly the main diagonal) 5639 of a set of rows of a matrix; using local numbering of rows. 5640 5641 Collective on Mat 5642 5643 Input Parameters: 5644 + mat - the matrix 5645 . numRows - the number of rows to remove 5646 . rows - the global row indices 5647 . diag - value put in all diagonals of eliminated rows 5648 . x - optional vector of solutions for zeroed rows (other entries in vector are not used) 5649 - b - optional vector of right hand side, that will be adjusted by provided solution 5650 5651 Notes: 5652 Before calling MatZeroRowsLocal(), the user must first set the 5653 local-to-global mapping by calling MatSetLocalToGlobalMapping(). 5654 5655 For the AIJ matrix formats this removes the old nonzero structure, 5656 but does not release memory. For the dense and block diagonal 5657 formats this does not alter the nonzero structure. 5658 5659 If the option MatSetOption(mat,MAT_KEEP_NONZERO_PATTERN,PETSC_TRUE) the nonzero structure 5660 of the matrix is not changed (even for AIJ and BAIJ matrices) the values are 5661 merely zeroed. 5662 5663 The user can set a value in the diagonal entry (or for the AIJ and 5664 row formats can optionally remove the main diagonal entry from the 5665 nonzero structure as well, by passing 0.0 as the final argument). 5666 5667 You can call MatSetOption(mat,MAT_NO_OFF_PROC_ZERO_ROWS,PETSC_TRUE) if each process indicates only rows it 5668 owns that are to be zeroed. This saves a global synchronization in the implementation. 5669 5670 Level: intermediate 5671 5672 Concepts: matrices^zeroing 5673 5674 .seealso: MatZeroRows(), MatZeroRowsLocalIS(), MatZeroEntries(), MatZeroRows(), MatSetLocalToGlobalMapping 5675 @*/ 5676 PetscErrorCode MatZeroRowsLocal(Mat mat,PetscInt numRows,const PetscInt rows[],PetscScalar diag,Vec x,Vec b) 5677 { 5678 PetscErrorCode ierr; 5679 PetscMPIInt size; 5680 5681 PetscFunctionBegin; 5682 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5683 PetscValidType(mat,1); 5684 if (numRows) PetscValidIntPointer(rows,3); 5685 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 5686 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 5687 MatCheckPreallocated(mat,1); 5688 5689 ierr = MPI_Comm_size(PetscObjectComm((PetscObject)mat),&size);CHKERRQ(ierr); 5690 if (mat->ops->zerorowslocal) { 5691 ierr = (*mat->ops->zerorowslocal)(mat,numRows,rows,diag,x,b);CHKERRQ(ierr); 5692 } else if (size == 1) { 5693 ierr = (*mat->ops->zerorows)(mat,numRows,rows,diag,x,b);CHKERRQ(ierr); 5694 } else { 5695 IS is, newis; 5696 const PetscInt *newRows; 5697 5698 if (!mat->rmap->mapping) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Need to provide local to global mapping to matrix first"); 5699 ierr = ISCreateGeneral(PETSC_COMM_SELF,numRows,rows,PETSC_COPY_VALUES,&is);CHKERRQ(ierr); 5700 ierr = ISLocalToGlobalMappingApplyIS(mat->rmap->mapping,is,&newis);CHKERRQ(ierr); 5701 ierr = ISGetIndices(newis,&newRows);CHKERRQ(ierr); 5702 ierr = (*mat->ops->zerorows)(mat,numRows,newRows,diag,x,b);CHKERRQ(ierr); 5703 ierr = ISRestoreIndices(newis,&newRows);CHKERRQ(ierr); 5704 ierr = ISDestroy(&newis);CHKERRQ(ierr); 5705 ierr = ISDestroy(&is);CHKERRQ(ierr); 5706 } 5707 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 5708 #if defined(PETSC_HAVE_CUSP) 5709 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 5710 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 5711 } 5712 #endif 5713 PetscFunctionReturn(0); 5714 } 5715 5716 #undef __FUNCT__ 5717 #define __FUNCT__ "MatZeroRowsLocalIS" 5718 /*@C 5719 MatZeroRowsLocalIS - Zeros all entries (except possibly the main diagonal) 5720 of a set of rows of a matrix; using local numbering of rows. 5721 5722 Collective on Mat 5723 5724 Input Parameters: 5725 + mat - the matrix 5726 . is - index set of rows to remove 5727 . diag - value put in all diagonals of eliminated rows 5728 . x - optional vector of solutions for zeroed rows (other entries in vector are not used) 5729 - b - optional vector of right hand side, that will be adjusted by provided solution 5730 5731 Notes: 5732 Before calling MatZeroRowsLocalIS(), the user must first set the 5733 local-to-global mapping by calling MatSetLocalToGlobalMapping(). 5734 5735 For the AIJ matrix formats this removes the old nonzero structure, 5736 but does not release memory. For the dense and block diagonal 5737 formats this does not alter the nonzero structure. 5738 5739 If the option MatSetOption(mat,MAT_KEEP_NONZERO_PATTERN,PETSC_TRUE) the nonzero structure 5740 of the matrix is not changed (even for AIJ and BAIJ matrices) the values are 5741 merely zeroed. 5742 5743 The user can set a value in the diagonal entry (or for the AIJ and 5744 row formats can optionally remove the main diagonal entry from the 5745 nonzero structure as well, by passing 0.0 as the final argument). 5746 5747 You can call MatSetOption(mat,MAT_NO_OFF_PROC_ZERO_ROWS,PETSC_TRUE) if each process indicates only rows it 5748 owns that are to be zeroed. This saves a global synchronization in the implementation. 5749 5750 Level: intermediate 5751 5752 Concepts: matrices^zeroing 5753 5754 .seealso: MatZeroRows(), MatZeroRowsLocal(), MatZeroEntries(), MatZeroRows(), MatSetLocalToGlobalMapping 5755 @*/ 5756 PetscErrorCode MatZeroRowsLocalIS(Mat mat,IS is,PetscScalar diag,Vec x,Vec b) 5757 { 5758 PetscErrorCode ierr; 5759 PetscInt numRows; 5760 const PetscInt *rows; 5761 5762 PetscFunctionBegin; 5763 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5764 PetscValidType(mat,1); 5765 PetscValidHeaderSpecific(is,IS_CLASSID,2); 5766 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 5767 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 5768 MatCheckPreallocated(mat,1); 5769 5770 ierr = ISGetLocalSize(is,&numRows);CHKERRQ(ierr); 5771 ierr = ISGetIndices(is,&rows);CHKERRQ(ierr); 5772 ierr = MatZeroRowsLocal(mat,numRows,rows,diag,x,b);CHKERRQ(ierr); 5773 ierr = ISRestoreIndices(is,&rows);CHKERRQ(ierr); 5774 PetscFunctionReturn(0); 5775 } 5776 5777 #undef __FUNCT__ 5778 #define __FUNCT__ "MatZeroRowsColumnsLocal" 5779 /*@C 5780 MatZeroRowsColumnsLocal - Zeros all entries (except possibly the main diagonal) 5781 of a set of rows and columns of a matrix; using local numbering of rows. 5782 5783 Collective on Mat 5784 5785 Input Parameters: 5786 + mat - the matrix 5787 . numRows - the number of rows to remove 5788 . rows - the global row indices 5789 . diag - value put in all diagonals of eliminated rows 5790 . x - optional vector of solutions for zeroed rows (other entries in vector are not used) 5791 - b - optional vector of right hand side, that will be adjusted by provided solution 5792 5793 Notes: 5794 Before calling MatZeroRowsColumnsLocal(), the user must first set the 5795 local-to-global mapping by calling MatSetLocalToGlobalMapping(). 5796 5797 The user can set a value in the diagonal entry (or for the AIJ and 5798 row formats can optionally remove the main diagonal entry from the 5799 nonzero structure as well, by passing 0.0 as the final argument). 5800 5801 Level: intermediate 5802 5803 Concepts: matrices^zeroing 5804 5805 .seealso: MatZeroRows(), MatZeroRowsLocalIS(), MatZeroEntries(), MatZeroRows(), MatSetLocalToGlobalMapping 5806 @*/ 5807 PetscErrorCode MatZeroRowsColumnsLocal(Mat mat,PetscInt numRows,const PetscInt rows[],PetscScalar diag,Vec x,Vec b) 5808 { 5809 PetscErrorCode ierr; 5810 PetscMPIInt size; 5811 5812 PetscFunctionBegin; 5813 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5814 PetscValidType(mat,1); 5815 if (numRows) PetscValidIntPointer(rows,3); 5816 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 5817 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 5818 MatCheckPreallocated(mat,1); 5819 5820 ierr = MPI_Comm_size(PetscObjectComm((PetscObject)mat),&size);CHKERRQ(ierr); 5821 if (size == 1) { 5822 ierr = (*mat->ops->zerorowscolumns)(mat,numRows,rows,diag,x,b);CHKERRQ(ierr); 5823 } else { 5824 IS is, newis; 5825 const PetscInt *newRows; 5826 5827 if (!mat->cmap->mapping) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Need to provide local to global mapping to matrix first"); 5828 ierr = ISCreateGeneral(PETSC_COMM_SELF,numRows,rows,PETSC_COPY_VALUES,&is);CHKERRQ(ierr); 5829 ierr = ISLocalToGlobalMappingApplyIS(mat->cmap->mapping,is,&newis);CHKERRQ(ierr); 5830 ierr = ISGetIndices(newis,&newRows);CHKERRQ(ierr); 5831 ierr = (*mat->ops->zerorowscolumns)(mat,numRows,newRows,diag,x,b);CHKERRQ(ierr); 5832 ierr = ISRestoreIndices(newis,&newRows);CHKERRQ(ierr); 5833 ierr = ISDestroy(&newis);CHKERRQ(ierr); 5834 ierr = ISDestroy(&is);CHKERRQ(ierr); 5835 } 5836 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 5837 #if defined(PETSC_HAVE_CUSP) 5838 if (mat->valid_GPU_matrix != PETSC_CUSP_UNALLOCATED) { 5839 mat->valid_GPU_matrix = PETSC_CUSP_CPU; 5840 } 5841 #endif 5842 PetscFunctionReturn(0); 5843 } 5844 5845 #undef __FUNCT__ 5846 #define __FUNCT__ "MatZeroRowsColumnsLocalIS" 5847 /*@C 5848 MatZeroRowsColumnsLocalIS - Zeros all entries (except possibly the main diagonal) 5849 of a set of rows and columns of a matrix; using local numbering of rows. 5850 5851 Collective on Mat 5852 5853 Input Parameters: 5854 + mat - the matrix 5855 . is - index set of rows to remove 5856 . diag - value put in all diagonals of eliminated rows 5857 . x - optional vector of solutions for zeroed rows (other entries in vector are not used) 5858 - b - optional vector of right hand side, that will be adjusted by provided solution 5859 5860 Notes: 5861 Before calling MatZeroRowsColumnsLocalIS(), the user must first set the 5862 local-to-global mapping by calling MatSetLocalToGlobalMapping(). 5863 5864 The user can set a value in the diagonal entry (or for the AIJ and 5865 row formats can optionally remove the main diagonal entry from the 5866 nonzero structure as well, by passing 0.0 as the final argument). 5867 5868 Level: intermediate 5869 5870 Concepts: matrices^zeroing 5871 5872 .seealso: MatZeroRows(), MatZeroRowsLocal(), MatZeroEntries(), MatZeroRows(), MatSetLocalToGlobalMapping 5873 @*/ 5874 PetscErrorCode MatZeroRowsColumnsLocalIS(Mat mat,IS is,PetscScalar diag,Vec x,Vec b) 5875 { 5876 PetscErrorCode ierr; 5877 PetscInt numRows; 5878 const PetscInt *rows; 5879 5880 PetscFunctionBegin; 5881 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5882 PetscValidType(mat,1); 5883 PetscValidHeaderSpecific(is,IS_CLASSID,2); 5884 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 5885 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 5886 MatCheckPreallocated(mat,1); 5887 5888 ierr = ISGetLocalSize(is,&numRows);CHKERRQ(ierr); 5889 ierr = ISGetIndices(is,&rows);CHKERRQ(ierr); 5890 ierr = MatZeroRowsColumnsLocal(mat,numRows,rows,diag,x,b);CHKERRQ(ierr); 5891 ierr = ISRestoreIndices(is,&rows);CHKERRQ(ierr); 5892 PetscFunctionReturn(0); 5893 } 5894 5895 #undef __FUNCT__ 5896 #define __FUNCT__ "MatGetSize" 5897 /*@ 5898 MatGetSize - Returns the numbers of rows and columns in a matrix. 5899 5900 Not Collective 5901 5902 Input Parameter: 5903 . mat - the matrix 5904 5905 Output Parameters: 5906 + m - the number of global rows 5907 - n - the number of global columns 5908 5909 Note: both output parameters can be NULL on input. 5910 5911 Level: beginner 5912 5913 Concepts: matrices^size 5914 5915 .seealso: MatGetLocalSize() 5916 @*/ 5917 PetscErrorCode MatGetSize(Mat mat,PetscInt *m,PetscInt *n) 5918 { 5919 PetscFunctionBegin; 5920 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5921 if (m) *m = mat->rmap->N; 5922 if (n) *n = mat->cmap->N; 5923 PetscFunctionReturn(0); 5924 } 5925 5926 #undef __FUNCT__ 5927 #define __FUNCT__ "MatGetLocalSize" 5928 /*@ 5929 MatGetLocalSize - Returns the number of rows and columns in a matrix 5930 stored locally. This information may be implementation dependent, so 5931 use with care. 5932 5933 Not Collective 5934 5935 Input Parameters: 5936 . mat - the matrix 5937 5938 Output Parameters: 5939 + m - the number of local rows 5940 - n - the number of local columns 5941 5942 Note: both output parameters can be NULL on input. 5943 5944 Level: beginner 5945 5946 Concepts: matrices^local size 5947 5948 .seealso: MatGetSize() 5949 @*/ 5950 PetscErrorCode MatGetLocalSize(Mat mat,PetscInt *m,PetscInt *n) 5951 { 5952 PetscFunctionBegin; 5953 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5954 if (m) PetscValidIntPointer(m,2); 5955 if (n) PetscValidIntPointer(n,3); 5956 if (m) *m = mat->rmap->n; 5957 if (n) *n = mat->cmap->n; 5958 PetscFunctionReturn(0); 5959 } 5960 5961 #undef __FUNCT__ 5962 #define __FUNCT__ "MatGetOwnershipRangeColumn" 5963 /*@ 5964 MatGetOwnershipRangeColumn - Returns the range of matrix columns associated with rows of a vector one multiplies by that owned by 5965 this processor. (The columns of the "diagonal block") 5966 5967 Not Collective, unless matrix has not been allocated, then collective on Mat 5968 5969 Input Parameters: 5970 . mat - the matrix 5971 5972 Output Parameters: 5973 + m - the global index of the first local column 5974 - n - one more than the global index of the last local column 5975 5976 Notes: both output parameters can be NULL on input. 5977 5978 Level: developer 5979 5980 Concepts: matrices^column ownership 5981 5982 .seealso: MatGetOwnershipRange(), MatGetOwnershipRanges(), MatGetOwnershipRangesColumn() 5983 5984 @*/ 5985 PetscErrorCode MatGetOwnershipRangeColumn(Mat mat,PetscInt *m,PetscInt *n) 5986 { 5987 PetscFunctionBegin; 5988 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 5989 PetscValidType(mat,1); 5990 if (m) PetscValidIntPointer(m,2); 5991 if (n) PetscValidIntPointer(n,3); 5992 MatCheckPreallocated(mat,1); 5993 if (m) *m = mat->cmap->rstart; 5994 if (n) *n = mat->cmap->rend; 5995 PetscFunctionReturn(0); 5996 } 5997 5998 #undef __FUNCT__ 5999 #define __FUNCT__ "MatGetOwnershipRange" 6000 /*@ 6001 MatGetOwnershipRange - Returns the range of matrix rows owned by 6002 this processor, assuming that the matrix is laid out with the first 6003 n1 rows on the first processor, the next n2 rows on the second, etc. 6004 For certain parallel layouts this range may not be well defined. 6005 6006 Not Collective 6007 6008 Input Parameters: 6009 . mat - the matrix 6010 6011 Output Parameters: 6012 + m - the global index of the first local row 6013 - n - one more than the global index of the last local row 6014 6015 Note: Both output parameters can be NULL on input. 6016 $ This function requires that the matrix be preallocated. If you have not preallocated, consider using 6017 $ PetscSplitOwnership(MPI_Comm comm, PetscInt *n, PetscInt *N) 6018 $ and then MPI_Scan() to calculate prefix sums of the local sizes. 6019 6020 Level: beginner 6021 6022 Concepts: matrices^row ownership 6023 6024 .seealso: MatGetOwnershipRanges(), MatGetOwnershipRangeColumn(), MatGetOwnershipRangesColumn(), PetscSplitOwnership(), PetscSplitOwnershipBlock() 6025 6026 @*/ 6027 PetscErrorCode MatGetOwnershipRange(Mat mat,PetscInt *m,PetscInt *n) 6028 { 6029 PetscFunctionBegin; 6030 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6031 PetscValidType(mat,1); 6032 if (m) PetscValidIntPointer(m,2); 6033 if (n) PetscValidIntPointer(n,3); 6034 MatCheckPreallocated(mat,1); 6035 if (m) *m = mat->rmap->rstart; 6036 if (n) *n = mat->rmap->rend; 6037 PetscFunctionReturn(0); 6038 } 6039 6040 #undef __FUNCT__ 6041 #define __FUNCT__ "MatGetOwnershipRanges" 6042 /*@C 6043 MatGetOwnershipRanges - Returns the range of matrix rows owned by 6044 each process 6045 6046 Not Collective, unless matrix has not been allocated, then collective on Mat 6047 6048 Input Parameters: 6049 . mat - the matrix 6050 6051 Output Parameters: 6052 . ranges - start of each processors portion plus one more then the total length at the end 6053 6054 Level: beginner 6055 6056 Concepts: matrices^row ownership 6057 6058 .seealso: MatGetOwnershipRange(), MatGetOwnershipRangeColumn(), MatGetOwnershipRangesColumn() 6059 6060 @*/ 6061 PetscErrorCode MatGetOwnershipRanges(Mat mat,const PetscInt **ranges) 6062 { 6063 PetscErrorCode ierr; 6064 6065 PetscFunctionBegin; 6066 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6067 PetscValidType(mat,1); 6068 MatCheckPreallocated(mat,1); 6069 ierr = PetscLayoutGetRanges(mat->rmap,ranges);CHKERRQ(ierr); 6070 PetscFunctionReturn(0); 6071 } 6072 6073 #undef __FUNCT__ 6074 #define __FUNCT__ "MatGetOwnershipRangesColumn" 6075 /*@C 6076 MatGetOwnershipRangesColumn - Returns the range of matrix columns associated with rows of a vector one multiplies by that owned by 6077 this processor. (The columns of the "diagonal blocks" for each process) 6078 6079 Not Collective, unless matrix has not been allocated, then collective on Mat 6080 6081 Input Parameters: 6082 . mat - the matrix 6083 6084 Output Parameters: 6085 . ranges - start of each processors portion plus one more then the total length at the end 6086 6087 Level: beginner 6088 6089 Concepts: matrices^column ownership 6090 6091 .seealso: MatGetOwnershipRange(), MatGetOwnershipRangeColumn(), MatGetOwnershipRanges() 6092 6093 @*/ 6094 PetscErrorCode MatGetOwnershipRangesColumn(Mat mat,const PetscInt **ranges) 6095 { 6096 PetscErrorCode ierr; 6097 6098 PetscFunctionBegin; 6099 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6100 PetscValidType(mat,1); 6101 MatCheckPreallocated(mat,1); 6102 ierr = PetscLayoutGetRanges(mat->cmap,ranges);CHKERRQ(ierr); 6103 PetscFunctionReturn(0); 6104 } 6105 6106 #undef __FUNCT__ 6107 #define __FUNCT__ "MatGetOwnershipIS" 6108 /*@C 6109 MatGetOwnershipIS - Get row and column ownership as index sets 6110 6111 Not Collective 6112 6113 Input Arguments: 6114 . A - matrix of type Elemental 6115 6116 Output Arguments: 6117 + rows - rows in which this process owns elements 6118 . cols - columns in which this process owns elements 6119 6120 Level: intermediate 6121 6122 .seealso: MatGetOwnershipRange(), MatGetOwnershipRangeColumn(), MatSetValues(), MATELEMENTAL, MatSetValues() 6123 @*/ 6124 PetscErrorCode MatGetOwnershipIS(Mat A,IS *rows,IS *cols) 6125 { 6126 PetscErrorCode ierr,(*f)(Mat,IS*,IS*); 6127 6128 PetscFunctionBegin; 6129 MatCheckPreallocated(A,1); 6130 ierr = PetscObjectQueryFunction((PetscObject)A,"MatGetOwnershipIS_C",(PetscVoidStarFunction)&f);CHKERRQ(ierr); 6131 if (f) { 6132 ierr = (*f)(A,rows,cols);CHKERRQ(ierr); 6133 } else { /* Create a standard row-based partition, each process is responsible for ALL columns in their row block */ 6134 if (rows) {ierr = ISCreateStride(PETSC_COMM_SELF,A->rmap->n,A->rmap->rstart,1,rows);CHKERRQ(ierr);} 6135 if (cols) {ierr = ISCreateStride(PETSC_COMM_SELF,A->cmap->N,0,1,cols);CHKERRQ(ierr);} 6136 } 6137 PetscFunctionReturn(0); 6138 } 6139 6140 #undef __FUNCT__ 6141 #define __FUNCT__ "MatILUFactorSymbolic" 6142 /*@C 6143 MatILUFactorSymbolic - Performs symbolic ILU factorization of a matrix. 6144 Uses levels of fill only, not drop tolerance. Use MatLUFactorNumeric() 6145 to complete the factorization. 6146 6147 Collective on Mat 6148 6149 Input Parameters: 6150 + mat - the matrix 6151 . row - row permutation 6152 . column - column permutation 6153 - info - structure containing 6154 $ levels - number of levels of fill. 6155 $ expected fill - as ratio of original fill. 6156 $ 1 or 0 - indicating force fill on diagonal (improves robustness for matrices 6157 missing diagonal entries) 6158 6159 Output Parameters: 6160 . fact - new matrix that has been symbolically factored 6161 6162 Notes: 6163 See the <a href="../../docs/manual.pdf">users manual</a> for additional information about 6164 choosing the fill factor for better efficiency. 6165 6166 Most users should employ the simplified KSP interface for linear solvers 6167 instead of working directly with matrix algebra routines such as this. 6168 See, e.g., KSPCreate(). 6169 6170 Level: developer 6171 6172 Concepts: matrices^symbolic LU factorization 6173 Concepts: matrices^factorization 6174 Concepts: LU^symbolic factorization 6175 6176 .seealso: MatLUFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor() 6177 MatGetOrdering(), MatFactorInfo 6178 6179 Developer Note: fortran interface is not autogenerated as the f90 6180 interface defintion cannot be generated correctly [due to MatFactorInfo] 6181 6182 @*/ 6183 PetscErrorCode MatILUFactorSymbolic(Mat fact,Mat mat,IS row,IS col,const MatFactorInfo *info) 6184 { 6185 PetscErrorCode ierr; 6186 6187 PetscFunctionBegin; 6188 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6189 PetscValidType(mat,1); 6190 PetscValidHeaderSpecific(row,IS_CLASSID,2); 6191 PetscValidHeaderSpecific(col,IS_CLASSID,3); 6192 PetscValidPointer(info,4); 6193 PetscValidPointer(fact,5); 6194 if (info->levels < 0) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_OUTOFRANGE,"Levels of fill negative %D",(PetscInt)info->levels); 6195 if (info->fill < 1.0) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_OUTOFRANGE,"Expected fill less than 1.0 %G",info->fill); 6196 if (!(fact)->ops->ilufactorsymbolic) { 6197 const MatSolverPackage spackage; 6198 ierr = MatFactorGetSolverPackage(fact,&spackage);CHKERRQ(ierr); 6199 SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Matrix type %s symbolic ILU using solver package %s",((PetscObject)mat)->type_name,spackage); 6200 } 6201 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 6202 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 6203 MatCheckPreallocated(mat,2); 6204 6205 ierr = PetscLogEventBegin(MAT_ILUFactorSymbolic,mat,row,col,0);CHKERRQ(ierr); 6206 ierr = (fact->ops->ilufactorsymbolic)(fact,mat,row,col,info);CHKERRQ(ierr); 6207 ierr = PetscLogEventEnd(MAT_ILUFactorSymbolic,mat,row,col,0);CHKERRQ(ierr); 6208 PetscFunctionReturn(0); 6209 } 6210 6211 #undef __FUNCT__ 6212 #define __FUNCT__ "MatICCFactorSymbolic" 6213 /*@C 6214 MatICCFactorSymbolic - Performs symbolic incomplete 6215 Cholesky factorization for a symmetric matrix. Use 6216 MatCholeskyFactorNumeric() to complete the factorization. 6217 6218 Collective on Mat 6219 6220 Input Parameters: 6221 + mat - the matrix 6222 . perm - row and column permutation 6223 - info - structure containing 6224 $ levels - number of levels of fill. 6225 $ expected fill - as ratio of original fill. 6226 6227 Output Parameter: 6228 . fact - the factored matrix 6229 6230 Notes: 6231 Most users should employ the KSP interface for linear solvers 6232 instead of working directly with matrix algebra routines such as this. 6233 See, e.g., KSPCreate(). 6234 6235 Level: developer 6236 6237 Concepts: matrices^symbolic incomplete Cholesky factorization 6238 Concepts: matrices^factorization 6239 Concepts: Cholsky^symbolic factorization 6240 6241 .seealso: MatCholeskyFactorNumeric(), MatCholeskyFactor(), MatFactorInfo 6242 6243 Developer Note: fortran interface is not autogenerated as the f90 6244 interface defintion cannot be generated correctly [due to MatFactorInfo] 6245 6246 @*/ 6247 PetscErrorCode MatICCFactorSymbolic(Mat fact,Mat mat,IS perm,const MatFactorInfo *info) 6248 { 6249 PetscErrorCode ierr; 6250 6251 PetscFunctionBegin; 6252 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6253 PetscValidType(mat,1); 6254 PetscValidHeaderSpecific(perm,IS_CLASSID,2); 6255 PetscValidPointer(info,3); 6256 PetscValidPointer(fact,4); 6257 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 6258 if (info->levels < 0) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_OUTOFRANGE,"Levels negative %D",(PetscInt) info->levels); 6259 if (info->fill < 1.0) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_OUTOFRANGE,"Expected fill less than 1.0 %G",info->fill); 6260 if (!(fact)->ops->iccfactorsymbolic) { 6261 const MatSolverPackage spackage; 6262 ierr = MatFactorGetSolverPackage(fact,&spackage);CHKERRQ(ierr); 6263 SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Matrix type %s symbolic ICC using solver package %s",((PetscObject)mat)->type_name,spackage); 6264 } 6265 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 6266 MatCheckPreallocated(mat,2); 6267 6268 ierr = PetscLogEventBegin(MAT_ICCFactorSymbolic,mat,perm,0,0);CHKERRQ(ierr); 6269 ierr = (fact->ops->iccfactorsymbolic)(fact,mat,perm,info);CHKERRQ(ierr); 6270 ierr = PetscLogEventEnd(MAT_ICCFactorSymbolic,mat,perm,0,0);CHKERRQ(ierr); 6271 PetscFunctionReturn(0); 6272 } 6273 6274 #undef __FUNCT__ 6275 #define __FUNCT__ "MatGetSubMatrices" 6276 /*@C 6277 MatGetSubMatrices - Extracts several submatrices from a matrix. If submat 6278 points to an array of valid matrices, they may be reused to store the new 6279 submatrices. 6280 6281 Collective on Mat 6282 6283 Input Parameters: 6284 + mat - the matrix 6285 . n - the number of submatrixes to be extracted (on this processor, may be zero) 6286 . irow, icol - index sets of rows and columns to extract (must be sorted) 6287 - scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 6288 6289 Output Parameter: 6290 . submat - the array of submatrices 6291 6292 Notes: 6293 MatGetSubMatrices() can extract ONLY sequential submatrices 6294 (from both sequential and parallel matrices). Use MatGetSubMatrix() 6295 to extract a parallel submatrix. 6296 6297 Currently both row and column indices must be sorted to guarantee 6298 correctness with all matrix types. 6299 6300 When extracting submatrices from a parallel matrix, each processor can 6301 form a different submatrix by setting the rows and columns of its 6302 individual index sets according to the local submatrix desired. 6303 6304 When finished using the submatrices, the user should destroy 6305 them with MatDestroyMatrices(). 6306 6307 MAT_REUSE_MATRIX can only be used when the nonzero structure of the 6308 original matrix has not changed from that last call to MatGetSubMatrices(). 6309 6310 This routine creates the matrices in submat; you should NOT create them before 6311 calling it. It also allocates the array of matrix pointers submat. 6312 6313 For BAIJ matrices the index sets must respect the block structure, that is if they 6314 request one row/column in a block, they must request all rows/columns that are in 6315 that block. For example, if the block size is 2 you cannot request just row 0 and 6316 column 0. 6317 6318 Fortran Note: 6319 The Fortran interface is slightly different from that given below; it 6320 requires one to pass in as submat a Mat (integer) array of size at least m. 6321 6322 Level: advanced 6323 6324 Concepts: matrices^accessing submatrices 6325 Concepts: submatrices 6326 6327 .seealso: MatDestroyMatrices(), MatGetSubMatrix(), MatGetRow(), MatGetDiagonal(), MatReuse 6328 @*/ 6329 PetscErrorCode MatGetSubMatrices(Mat mat,PetscInt n,const IS irow[],const IS icol[],MatReuse scall,Mat *submat[]) 6330 { 6331 PetscErrorCode ierr; 6332 PetscInt i; 6333 PetscBool eq; 6334 6335 PetscFunctionBegin; 6336 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6337 PetscValidType(mat,1); 6338 if (n) { 6339 PetscValidPointer(irow,3); 6340 PetscValidHeaderSpecific(*irow,IS_CLASSID,3); 6341 PetscValidPointer(icol,4); 6342 PetscValidHeaderSpecific(*icol,IS_CLASSID,4); 6343 } 6344 PetscValidPointer(submat,6); 6345 if (n && scall == MAT_REUSE_MATRIX) { 6346 PetscValidPointer(*submat,6); 6347 PetscValidHeaderSpecific(**submat,MAT_CLASSID,6); 6348 } 6349 if (!mat->ops->getsubmatrices) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 6350 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 6351 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 6352 MatCheckPreallocated(mat,1); 6353 6354 ierr = PetscLogEventBegin(MAT_GetSubMatrices,mat,0,0,0);CHKERRQ(ierr); 6355 ierr = (*mat->ops->getsubmatrices)(mat,n,irow,icol,scall,submat);CHKERRQ(ierr); 6356 ierr = PetscLogEventEnd(MAT_GetSubMatrices,mat,0,0,0);CHKERRQ(ierr); 6357 for (i=0; i<n; i++) { 6358 if (mat->symmetric || mat->structurally_symmetric || mat->hermitian) { 6359 ierr = ISEqual(irow[i],icol[i],&eq);CHKERRQ(ierr); 6360 if (eq) { 6361 if (mat->symmetric) { 6362 ierr = MatSetOption((*submat)[i],MAT_SYMMETRIC,PETSC_TRUE);CHKERRQ(ierr); 6363 } else if (mat->hermitian) { 6364 ierr = MatSetOption((*submat)[i],MAT_HERMITIAN,PETSC_TRUE);CHKERRQ(ierr); 6365 } else if (mat->structurally_symmetric) { 6366 ierr = MatSetOption((*submat)[i],MAT_STRUCTURALLY_SYMMETRIC,PETSC_TRUE);CHKERRQ(ierr); 6367 } 6368 } 6369 } 6370 } 6371 PetscFunctionReturn(0); 6372 } 6373 6374 #undef __FUNCT__ 6375 #define __FUNCT__ "MatGetSubMatricesParallel" 6376 PetscErrorCode MatGetSubMatricesParallel(Mat mat,PetscInt n,const IS irow[],const IS icol[],MatReuse scall,Mat *submat[]) 6377 { 6378 PetscErrorCode ierr; 6379 PetscInt i; 6380 PetscBool eq; 6381 6382 PetscFunctionBegin; 6383 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6384 PetscValidType(mat,1); 6385 if (n) { 6386 PetscValidPointer(irow,3); 6387 PetscValidHeaderSpecific(*irow,IS_CLASSID,3); 6388 PetscValidPointer(icol,4); 6389 PetscValidHeaderSpecific(*icol,IS_CLASSID,4); 6390 } 6391 PetscValidPointer(submat,6); 6392 if (n && scall == MAT_REUSE_MATRIX) { 6393 PetscValidPointer(*submat,6); 6394 PetscValidHeaderSpecific(**submat,MAT_CLASSID,6); 6395 } 6396 if (!mat->ops->getsubmatricesparallel) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 6397 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 6398 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 6399 MatCheckPreallocated(mat,1); 6400 6401 ierr = PetscLogEventBegin(MAT_GetSubMatrices,mat,0,0,0);CHKERRQ(ierr); 6402 ierr = (*mat->ops->getsubmatricesparallel)(mat,n,irow,icol,scall,submat);CHKERRQ(ierr); 6403 ierr = PetscLogEventEnd(MAT_GetSubMatrices,mat,0,0,0);CHKERRQ(ierr); 6404 for (i=0; i<n; i++) { 6405 if (mat->symmetric || mat->structurally_symmetric || mat->hermitian) { 6406 ierr = ISEqual(irow[i],icol[i],&eq);CHKERRQ(ierr); 6407 if (eq) { 6408 if (mat->symmetric) { 6409 ierr = MatSetOption((*submat)[i],MAT_SYMMETRIC,PETSC_TRUE);CHKERRQ(ierr); 6410 } else if (mat->hermitian) { 6411 ierr = MatSetOption((*submat)[i],MAT_HERMITIAN,PETSC_TRUE);CHKERRQ(ierr); 6412 } else if (mat->structurally_symmetric) { 6413 ierr = MatSetOption((*submat)[i],MAT_STRUCTURALLY_SYMMETRIC,PETSC_TRUE);CHKERRQ(ierr); 6414 } 6415 } 6416 } 6417 } 6418 PetscFunctionReturn(0); 6419 } 6420 6421 #undef __FUNCT__ 6422 #define __FUNCT__ "MatDestroyMatrices" 6423 /*@C 6424 MatDestroyMatrices - Destroys a set of matrices obtained with MatGetSubMatrices(). 6425 6426 Collective on Mat 6427 6428 Input Parameters: 6429 + n - the number of local matrices 6430 - mat - the matrices (note that this is a pointer to the array of matrices, just to match the calling 6431 sequence of MatGetSubMatrices()) 6432 6433 Level: advanced 6434 6435 Notes: Frees not only the matrices, but also the array that contains the matrices 6436 In Fortran will not free the array. 6437 6438 .seealso: MatGetSubMatrices() 6439 @*/ 6440 PetscErrorCode MatDestroyMatrices(PetscInt n,Mat *mat[]) 6441 { 6442 PetscErrorCode ierr; 6443 PetscInt i; 6444 6445 PetscFunctionBegin; 6446 if (!*mat) PetscFunctionReturn(0); 6447 if (n < 0) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Trying to destroy negative number of matrices %D",n); 6448 PetscValidPointer(mat,2); 6449 for (i=0; i<n; i++) { 6450 ierr = MatDestroy(&(*mat)[i]);CHKERRQ(ierr); 6451 } 6452 /* memory is allocated even if n = 0 */ 6453 ierr = PetscFree(*mat);CHKERRQ(ierr); 6454 *mat = NULL; 6455 PetscFunctionReturn(0); 6456 } 6457 6458 #undef __FUNCT__ 6459 #define __FUNCT__ "MatGetSeqNonzeroStructure" 6460 /*@C 6461 MatGetSeqNonzeroStructure - Extracts the sequential nonzero structure from a matrix. 6462 6463 Collective on Mat 6464 6465 Input Parameters: 6466 . mat - the matrix 6467 6468 Output Parameter: 6469 . matstruct - the sequential matrix with the nonzero structure of mat 6470 6471 Level: intermediate 6472 6473 .seealso: MatDestroySeqNonzeroStructure(), MatGetSubMatrices(), MatDestroyMatrices() 6474 @*/ 6475 PetscErrorCode MatGetSeqNonzeroStructure(Mat mat,Mat *matstruct) 6476 { 6477 PetscErrorCode ierr; 6478 6479 PetscFunctionBegin; 6480 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6481 PetscValidPointer(matstruct,2); 6482 6483 PetscValidType(mat,1); 6484 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 6485 MatCheckPreallocated(mat,1); 6486 6487 if (!mat->ops->getseqnonzerostructure) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Not for matrix type %s\n",((PetscObject)mat)->type_name); 6488 ierr = PetscLogEventBegin(MAT_GetSeqNonzeroStructure,mat,0,0,0);CHKERRQ(ierr); 6489 ierr = (*mat->ops->getseqnonzerostructure)(mat,matstruct);CHKERRQ(ierr); 6490 ierr = PetscLogEventEnd(MAT_GetSeqNonzeroStructure,mat,0,0,0);CHKERRQ(ierr); 6491 PetscFunctionReturn(0); 6492 } 6493 6494 #undef __FUNCT__ 6495 #define __FUNCT__ "MatDestroySeqNonzeroStructure" 6496 /*@C 6497 MatDestroySeqNonzeroStructure - Destroys matrix obtained with MatGetSeqNonzeroStructure(). 6498 6499 Collective on Mat 6500 6501 Input Parameters: 6502 . mat - the matrix (note that this is a pointer to the array of matrices, just to match the calling 6503 sequence of MatGetSequentialNonzeroStructure()) 6504 6505 Level: advanced 6506 6507 Notes: Frees not only the matrices, but also the array that contains the matrices 6508 6509 .seealso: MatGetSeqNonzeroStructure() 6510 @*/ 6511 PetscErrorCode MatDestroySeqNonzeroStructure(Mat *mat) 6512 { 6513 PetscErrorCode ierr; 6514 6515 PetscFunctionBegin; 6516 PetscValidPointer(mat,1); 6517 ierr = MatDestroy(mat);CHKERRQ(ierr); 6518 PetscFunctionReturn(0); 6519 } 6520 6521 #undef __FUNCT__ 6522 #define __FUNCT__ "MatIncreaseOverlap" 6523 /*@ 6524 MatIncreaseOverlap - Given a set of submatrices indicated by index sets, 6525 replaces the index sets by larger ones that represent submatrices with 6526 additional overlap. 6527 6528 Collective on Mat 6529 6530 Input Parameters: 6531 + mat - the matrix 6532 . n - the number of index sets 6533 . is - the array of index sets (these index sets will changed during the call) 6534 - ov - the additional overlap requested 6535 6536 Level: developer 6537 6538 Concepts: overlap 6539 Concepts: ASM^computing overlap 6540 6541 .seealso: MatGetSubMatrices() 6542 @*/ 6543 PetscErrorCode MatIncreaseOverlap(Mat mat,PetscInt n,IS is[],PetscInt ov) 6544 { 6545 PetscErrorCode ierr; 6546 6547 PetscFunctionBegin; 6548 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6549 PetscValidType(mat,1); 6550 if (n < 0) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"Must have one or more domains, you have %D",n); 6551 if (n) { 6552 PetscValidPointer(is,3); 6553 PetscValidHeaderSpecific(*is,IS_CLASSID,3); 6554 } 6555 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 6556 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 6557 MatCheckPreallocated(mat,1); 6558 6559 if (!ov) PetscFunctionReturn(0); 6560 if (!mat->ops->increaseoverlap) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 6561 ierr = PetscLogEventBegin(MAT_IncreaseOverlap,mat,0,0,0);CHKERRQ(ierr); 6562 ierr = (*mat->ops->increaseoverlap)(mat,n,is,ov);CHKERRQ(ierr); 6563 ierr = PetscLogEventEnd(MAT_IncreaseOverlap,mat,0,0,0);CHKERRQ(ierr); 6564 PetscFunctionReturn(0); 6565 } 6566 6567 #undef __FUNCT__ 6568 #define __FUNCT__ "MatGetBlockSize" 6569 /*@ 6570 MatGetBlockSize - Returns the matrix block size; useful especially for the 6571 block row and block diagonal formats. 6572 6573 Not Collective 6574 6575 Input Parameter: 6576 . mat - the matrix 6577 6578 Output Parameter: 6579 . bs - block size 6580 6581 Notes: 6582 Block row formats are MATSEQBAIJ, MATMPIBAIJ, MATSEQSBAIJ, MATMPISBAIJ 6583 6584 Level: intermediate 6585 6586 Concepts: matrices^block size 6587 6588 .seealso: MatCreateSeqBAIJ(), MatCreateBAIJ(), MatGetBlockSizes() 6589 @*/ 6590 PetscErrorCode MatGetBlockSize(Mat mat,PetscInt *bs) 6591 { 6592 PetscFunctionBegin; 6593 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6594 PetscValidType(mat,1); 6595 PetscValidIntPointer(bs,2); 6596 MatCheckPreallocated(mat,1); 6597 *bs = mat->rmap->bs; 6598 PetscFunctionReturn(0); 6599 } 6600 6601 #undef __FUNCT__ 6602 #define __FUNCT__ "MatGetBlockSizes" 6603 /*@ 6604 MatGetBlockSizes - Returns the matrix block row and column sizes; 6605 useful especially for the block row and block diagonal formats. 6606 6607 Not Collective 6608 6609 Input Parameter: 6610 . mat - the matrix 6611 6612 Output Parameter: 6613 . rbs - row block size 6614 . cbs - coumn block size 6615 6616 Notes: 6617 Block row formats are MATSEQBAIJ, MATMPIBAIJ, MATSEQSBAIJ, MATMPISBAIJ 6618 6619 Level: intermediate 6620 6621 Concepts: matrices^block size 6622 6623 .seealso: MatCreateSeqBAIJ(), MatCreateBAIJ(), MatGetBlockSize() 6624 @*/ 6625 PetscErrorCode MatGetBlockSizes(Mat mat,PetscInt *rbs, PetscInt *cbs) 6626 { 6627 PetscFunctionBegin; 6628 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6629 PetscValidType(mat,1); 6630 if (rbs) PetscValidIntPointer(rbs,2); 6631 if (cbs) PetscValidIntPointer(cbs,3); 6632 MatCheckPreallocated(mat,1); 6633 if (rbs) *rbs = mat->rmap->bs; 6634 if (cbs) *cbs = mat->cmap->bs; 6635 PetscFunctionReturn(0); 6636 } 6637 6638 #undef __FUNCT__ 6639 #define __FUNCT__ "MatSetBlockSize" 6640 /*@ 6641 MatSetBlockSize - Sets the matrix block size. 6642 6643 Logically Collective on Mat 6644 6645 Input Parameters: 6646 + mat - the matrix 6647 - bs - block size 6648 6649 Notes: 6650 This must be called before MatSetUp() or MatXXXSetPreallocation() (or will default to 1) and the block size cannot be changed later 6651 6652 Level: intermediate 6653 6654 Concepts: matrices^block size 6655 6656 .seealso: MatCreateSeqBAIJ(), MatCreateBAIJ(), MatGetBlockSize() 6657 @*/ 6658 PetscErrorCode MatSetBlockSize(Mat mat,PetscInt bs) 6659 { 6660 PetscErrorCode ierr; 6661 6662 PetscFunctionBegin; 6663 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6664 PetscValidLogicalCollectiveInt(mat,bs,2); 6665 ierr = PetscLayoutSetBlockSize(mat->rmap,bs);CHKERRQ(ierr); 6666 ierr = PetscLayoutSetBlockSize(mat->cmap,bs);CHKERRQ(ierr); 6667 PetscFunctionReturn(0); 6668 } 6669 6670 #undef __FUNCT__ 6671 #define __FUNCT__ "MatSetBlockSizes" 6672 /*@ 6673 MatSetBlockSizes - Sets the matrix block row and column sizes. 6674 6675 Logically Collective on Mat 6676 6677 Input Parameters: 6678 + mat - the matrix 6679 - rbs - row block size 6680 - cbs - column block size 6681 6682 Notes: 6683 This must be called before MatSetUp() or MatXXXSetPreallocation() (or will default to 1) and the block size cannot be changed later 6684 6685 Level: intermediate 6686 6687 Concepts: matrices^block size 6688 6689 .seealso: MatCreateSeqBAIJ(), MatCreateBAIJ(), MatGetBlockSize() 6690 @*/ 6691 PetscErrorCode MatSetBlockSizes(Mat mat,PetscInt rbs,PetscInt cbs) 6692 { 6693 PetscErrorCode ierr; 6694 6695 PetscFunctionBegin; 6696 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6697 PetscValidLogicalCollectiveInt(mat,rbs,2); 6698 ierr = PetscLayoutSetBlockSize(mat->rmap,rbs);CHKERRQ(ierr); 6699 ierr = PetscLayoutSetBlockSize(mat->cmap,cbs);CHKERRQ(ierr); 6700 PetscFunctionReturn(0); 6701 } 6702 6703 #undef __FUNCT__ 6704 #define __FUNCT__ "MatGetRowIJ" 6705 /*@C 6706 MatGetRowIJ - Returns the compressed row storage i and j indices for sequential matrices. 6707 6708 Collective on Mat 6709 6710 Input Parameters: 6711 + mat - the matrix 6712 . shift - 0 or 1 indicating we want the indices starting at 0 or 1 6713 . symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be symmetrized 6714 - inodecompressed - PETSC_TRUE or PETSC_FALSE indicating if the nonzero structure of the 6715 inodes or the nonzero elements is wanted. For BAIJ matrices the compressed version is 6716 always used. 6717 6718 Output Parameters: 6719 + n - number of rows in the (possibly compressed) matrix 6720 . ia - the row pointers [of length n+1] 6721 . ja - the column indices 6722 - done - indicates if the routine actually worked and returned appropriate ia[] and ja[] arrays; callers 6723 are responsible for handling the case when done == PETSC_FALSE and ia and ja are not set 6724 6725 Level: developer 6726 6727 Notes: You CANNOT change any of the ia[] or ja[] values. 6728 6729 Use MatRestoreRowIJ() when you are finished accessing the ia[] and ja[] values 6730 6731 Fortran Node 6732 6733 In Fortran use 6734 $ PetscInt ia(1), ja(1) 6735 $ PetscOffset iia, jja 6736 $ call MatGetRowIJ(mat,shift,symmetric,inodecompressed,n,ia,iia,ja,jja,done,ierr) 6737 $ 6738 $ or 6739 $ 6740 $ PetscScalar, pointer :: xx_v(:) 6741 $ call MatGetRowIJF90(mat,shift,symmetric,inodecompressed,n,ia,ja,done,ierr) 6742 6743 6744 Acess the ith and jth entries via ia(iia + i) and ja(jja + j) 6745 6746 .seealso: MatGetColumnIJ(), MatRestoreRowIJ(), MatSeqAIJGetArray() 6747 @*/ 6748 PetscErrorCode MatGetRowIJ(Mat mat,PetscInt shift,PetscBool symmetric,PetscBool inodecompressed,PetscInt *n,const PetscInt *ia[],const PetscInt *ja[],PetscBool *done) 6749 { 6750 PetscErrorCode ierr; 6751 6752 PetscFunctionBegin; 6753 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6754 PetscValidType(mat,1); 6755 PetscValidIntPointer(n,4); 6756 if (ia) PetscValidIntPointer(ia,5); 6757 if (ja) PetscValidIntPointer(ja,6); 6758 PetscValidIntPointer(done,7); 6759 MatCheckPreallocated(mat,1); 6760 if (!mat->ops->getrowij) *done = PETSC_FALSE; 6761 else { 6762 *done = PETSC_TRUE; 6763 ierr = PetscLogEventBegin(MAT_GetRowIJ,mat,0,0,0);CHKERRQ(ierr); 6764 ierr = (*mat->ops->getrowij)(mat,shift,symmetric,inodecompressed,n,ia,ja,done);CHKERRQ(ierr); 6765 ierr = PetscLogEventEnd(MAT_GetRowIJ,mat,0,0,0);CHKERRQ(ierr); 6766 } 6767 PetscFunctionReturn(0); 6768 } 6769 6770 #undef __FUNCT__ 6771 #define __FUNCT__ "MatGetColumnIJ" 6772 /*@C 6773 MatGetColumnIJ - Returns the compressed column storage i and j indices for sequential matrices. 6774 6775 Collective on Mat 6776 6777 Input Parameters: 6778 + mat - the matrix 6779 . shift - 1 or zero indicating we want the indices starting at 0 or 1 6780 . symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be 6781 symmetrized 6782 - inodecompressed - PETSC_TRUE or PETSC_FALSE indicating if the nonzero structure of the 6783 inodes or the nonzero elements is wanted. For BAIJ matrices the compressed version is 6784 always used. 6785 6786 Output Parameters: 6787 + n - number of columns in the (possibly compressed) matrix 6788 . ia - the column pointers 6789 . ja - the row indices 6790 - done - PETSC_TRUE or PETSC_FALSE, indicating whether the values have been returned 6791 6792 Level: developer 6793 6794 .seealso: MatGetRowIJ(), MatRestoreColumnIJ() 6795 @*/ 6796 PetscErrorCode MatGetColumnIJ(Mat mat,PetscInt shift,PetscBool symmetric,PetscBool inodecompressed,PetscInt *n,const PetscInt *ia[],const PetscInt *ja[],PetscBool *done) 6797 { 6798 PetscErrorCode ierr; 6799 6800 PetscFunctionBegin; 6801 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6802 PetscValidType(mat,1); 6803 PetscValidIntPointer(n,4); 6804 if (ia) PetscValidIntPointer(ia,5); 6805 if (ja) PetscValidIntPointer(ja,6); 6806 PetscValidIntPointer(done,7); 6807 MatCheckPreallocated(mat,1); 6808 if (!mat->ops->getcolumnij) *done = PETSC_FALSE; 6809 else { 6810 *done = PETSC_TRUE; 6811 ierr = (*mat->ops->getcolumnij)(mat,shift,symmetric,inodecompressed,n,ia,ja,done);CHKERRQ(ierr); 6812 } 6813 PetscFunctionReturn(0); 6814 } 6815 6816 #undef __FUNCT__ 6817 #define __FUNCT__ "MatRestoreRowIJ" 6818 /*@C 6819 MatRestoreRowIJ - Call after you are completed with the ia,ja indices obtained with 6820 MatGetRowIJ(). 6821 6822 Collective on Mat 6823 6824 Input Parameters: 6825 + mat - the matrix 6826 . shift - 1 or zero indicating we want the indices starting at 0 or 1 6827 . symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be 6828 symmetrized 6829 - inodecompressed - PETSC_TRUE or PETSC_FALSE indicating if the nonzero structure of the 6830 inodes or the nonzero elements is wanted. For BAIJ matrices the compressed version is 6831 always used. 6832 6833 Output Parameters: 6834 + n - size of (possibly compressed) matrix 6835 . ia - the row pointers 6836 . ja - the column indices 6837 - done - PETSC_TRUE or PETSC_FALSE indicated that the values have been returned 6838 6839 Level: developer 6840 6841 .seealso: MatGetRowIJ(), MatRestoreColumnIJ() 6842 @*/ 6843 PetscErrorCode MatRestoreRowIJ(Mat mat,PetscInt shift,PetscBool symmetric,PetscBool inodecompressed,PetscInt *n,const PetscInt *ia[],const PetscInt *ja[],PetscBool *done) 6844 { 6845 PetscErrorCode ierr; 6846 6847 PetscFunctionBegin; 6848 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6849 PetscValidType(mat,1); 6850 if (ia) PetscValidIntPointer(ia,5); 6851 if (ja) PetscValidIntPointer(ja,6); 6852 PetscValidIntPointer(done,7); 6853 MatCheckPreallocated(mat,1); 6854 6855 if (!mat->ops->restorerowij) *done = PETSC_FALSE; 6856 else { 6857 *done = PETSC_TRUE; 6858 ierr = (*mat->ops->restorerowij)(mat,shift,symmetric,inodecompressed,n,ia,ja,done);CHKERRQ(ierr); 6859 } 6860 PetscFunctionReturn(0); 6861 } 6862 6863 #undef __FUNCT__ 6864 #define __FUNCT__ "MatRestoreColumnIJ" 6865 /*@C 6866 MatRestoreColumnIJ - Call after you are completed with the ia,ja indices obtained with 6867 MatGetColumnIJ(). 6868 6869 Collective on Mat 6870 6871 Input Parameters: 6872 + mat - the matrix 6873 . shift - 1 or zero indicating we want the indices starting at 0 or 1 6874 - symmetric - PETSC_TRUE or PETSC_FALSE indicating the matrix data structure should be 6875 symmetrized 6876 - inodecompressed - PETSC_TRUE or PETSC_FALSE indicating if the nonzero structure of the 6877 inodes or the nonzero elements is wanted. For BAIJ matrices the compressed version is 6878 always used. 6879 6880 Output Parameters: 6881 + n - size of (possibly compressed) matrix 6882 . ia - the column pointers 6883 . ja - the row indices 6884 - done - PETSC_TRUE or PETSC_FALSE indicated that the values have been returned 6885 6886 Level: developer 6887 6888 .seealso: MatGetColumnIJ(), MatRestoreRowIJ() 6889 @*/ 6890 PetscErrorCode MatRestoreColumnIJ(Mat mat,PetscInt shift,PetscBool symmetric,PetscBool inodecompressed,PetscInt *n,const PetscInt *ia[],const PetscInt *ja[],PetscBool *done) 6891 { 6892 PetscErrorCode ierr; 6893 6894 PetscFunctionBegin; 6895 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6896 PetscValidType(mat,1); 6897 if (ia) PetscValidIntPointer(ia,5); 6898 if (ja) PetscValidIntPointer(ja,6); 6899 PetscValidIntPointer(done,7); 6900 MatCheckPreallocated(mat,1); 6901 6902 if (!mat->ops->restorecolumnij) *done = PETSC_FALSE; 6903 else { 6904 *done = PETSC_TRUE; 6905 ierr = (*mat->ops->restorecolumnij)(mat,shift,symmetric,inodecompressed,n,ia,ja,done);CHKERRQ(ierr); 6906 } 6907 PetscFunctionReturn(0); 6908 } 6909 6910 #undef __FUNCT__ 6911 #define __FUNCT__ "MatColoringPatch" 6912 /*@C 6913 MatColoringPatch -Used inside matrix coloring routines that 6914 use MatGetRowIJ() and/or MatGetColumnIJ(). 6915 6916 Collective on Mat 6917 6918 Input Parameters: 6919 + mat - the matrix 6920 . ncolors - max color value 6921 . n - number of entries in colorarray 6922 - colorarray - array indicating color for each column 6923 6924 Output Parameters: 6925 . iscoloring - coloring generated using colorarray information 6926 6927 Level: developer 6928 6929 .seealso: MatGetRowIJ(), MatGetColumnIJ() 6930 6931 @*/ 6932 PetscErrorCode MatColoringPatch(Mat mat,PetscInt ncolors,PetscInt n,ISColoringValue colorarray[],ISColoring *iscoloring) 6933 { 6934 PetscErrorCode ierr; 6935 6936 PetscFunctionBegin; 6937 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6938 PetscValidType(mat,1); 6939 PetscValidIntPointer(colorarray,4); 6940 PetscValidPointer(iscoloring,5); 6941 MatCheckPreallocated(mat,1); 6942 6943 if (!mat->ops->coloringpatch) { 6944 ierr = ISColoringCreate(PetscObjectComm((PetscObject)mat),ncolors,n,colorarray,iscoloring);CHKERRQ(ierr); 6945 } else { 6946 ierr = (*mat->ops->coloringpatch)(mat,ncolors,n,colorarray,iscoloring);CHKERRQ(ierr); 6947 } 6948 PetscFunctionReturn(0); 6949 } 6950 6951 6952 #undef __FUNCT__ 6953 #define __FUNCT__ "MatSetUnfactored" 6954 /*@ 6955 MatSetUnfactored - Resets a factored matrix to be treated as unfactored. 6956 6957 Logically Collective on Mat 6958 6959 Input Parameter: 6960 . mat - the factored matrix to be reset 6961 6962 Notes: 6963 This routine should be used only with factored matrices formed by in-place 6964 factorization via ILU(0) (or by in-place LU factorization for the MATSEQDENSE 6965 format). This option can save memory, for example, when solving nonlinear 6966 systems with a matrix-free Newton-Krylov method and a matrix-based, in-place 6967 ILU(0) preconditioner. 6968 6969 Note that one can specify in-place ILU(0) factorization by calling 6970 .vb 6971 PCType(pc,PCILU); 6972 PCFactorSeUseInPlace(pc); 6973 .ve 6974 or by using the options -pc_type ilu -pc_factor_in_place 6975 6976 In-place factorization ILU(0) can also be used as a local 6977 solver for the blocks within the block Jacobi or additive Schwarz 6978 methods (runtime option: -sub_pc_factor_in_place). See the discussion 6979 of these preconditioners in the <a href="../../docs/manual.pdf#ch_pc">PC chapter of the users manual</a> for details on setting 6980 local solver options. 6981 6982 Most users should employ the simplified KSP interface for linear solvers 6983 instead of working directly with matrix algebra routines such as this. 6984 See, e.g., KSPCreate(). 6985 6986 Level: developer 6987 6988 .seealso: PCFactorSetUseInPlace() 6989 6990 Concepts: matrices^unfactored 6991 6992 @*/ 6993 PetscErrorCode MatSetUnfactored(Mat mat) 6994 { 6995 PetscErrorCode ierr; 6996 6997 PetscFunctionBegin; 6998 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 6999 PetscValidType(mat,1); 7000 MatCheckPreallocated(mat,1); 7001 mat->factortype = MAT_FACTOR_NONE; 7002 if (!mat->ops->setunfactored) PetscFunctionReturn(0); 7003 ierr = (*mat->ops->setunfactored)(mat);CHKERRQ(ierr); 7004 PetscFunctionReturn(0); 7005 } 7006 7007 /*MC 7008 MatDenseGetArrayF90 - Accesses a matrix array from Fortran90. 7009 7010 Synopsis: 7011 MatDenseGetArrayF90(Mat x,{Scalar, pointer :: xx_v(:,:)},integer ierr) 7012 7013 Not collective 7014 7015 Input Parameter: 7016 . x - matrix 7017 7018 Output Parameters: 7019 + xx_v - the Fortran90 pointer to the array 7020 - ierr - error code 7021 7022 Example of Usage: 7023 .vb 7024 PetscScalar, pointer xx_v(:,:) 7025 .... 7026 call MatDenseGetArrayF90(x,xx_v,ierr) 7027 a = xx_v(3) 7028 call MatDenseRestoreArrayF90(x,xx_v,ierr) 7029 .ve 7030 7031 Level: advanced 7032 7033 .seealso: MatDenseRestoreArrayF90(), MatDenseGetArray(), MatDenseRestoreArray() 7034 7035 Concepts: matrices^accessing array 7036 7037 M*/ 7038 7039 /*MC 7040 MatDenseRestoreArrayF90 - Restores a matrix array that has been 7041 accessed with MatGetArrayF90(). 7042 7043 Synopsis: 7044 MatDenseRestoreArrayF90(Mat x,{Scalar, pointer :: xx_v(:)},integer ierr) 7045 7046 Not collective 7047 7048 Input Parameters: 7049 + x - matrix 7050 - xx_v - the Fortran90 pointer to the array 7051 7052 Output Parameter: 7053 . ierr - error code 7054 7055 Example of Usage: 7056 .vb 7057 PetscScalar, pointer xx_v(:) 7058 .... 7059 call MatDenseGetArrayF90(x,xx_v,ierr) 7060 a = xx_v(3) 7061 call MatDenseRestoreArrayF90(x,xx_v,ierr) 7062 .ve 7063 7064 Level: advanced 7065 7066 .seealso: MatDenseGetArrayF90(), MatDenseGetArray(), MatDenseRestoreArray() 7067 7068 M*/ 7069 7070 7071 #undef __FUNCT__ 7072 #define __FUNCT__ "MatGetSubMatrix" 7073 /*@ 7074 MatGetSubMatrix - Gets a single submatrix on the same number of processors 7075 as the original matrix. 7076 7077 Collective on Mat 7078 7079 Input Parameters: 7080 + mat - the original matrix 7081 . isrow - parallel IS containing the rows this processor should obtain 7082 . iscol - parallel IS containing all columns you wish to keep. Each process should list the columns that will be in IT's "diagonal part" in the new matrix. 7083 - cll - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 7084 7085 Output Parameter: 7086 . newmat - the new submatrix, of the same type as the old 7087 7088 Level: advanced 7089 7090 Notes: 7091 The submatrix will be able to be multiplied with vectors using the same layout as iscol. 7092 7093 The rows in isrow will be sorted into the same order as the original matrix on each process. 7094 7095 The first time this is called you should use a cll of MAT_INITIAL_MATRIX, 7096 the MatGetSubMatrix() routine will create the newmat for you. Any additional calls 7097 to this routine with a mat of the same nonzero structure and with a call of MAT_REUSE_MATRIX 7098 will reuse the matrix generated the first time. You should call MatDestroy() on newmat when 7099 you are finished using it. 7100 7101 The communicator of the newly obtained matrix is ALWAYS the same as the communicator of 7102 the input matrix. 7103 7104 If iscol is NULL then all columns are obtained (not supported in Fortran). 7105 7106 Example usage: 7107 Consider the following 8x8 matrix with 34 non-zero values, that is 7108 assembled across 3 processors. Let's assume that proc0 owns 3 rows, 7109 proc1 owns 3 rows, proc2 owns 2 rows. This division can be shown 7110 as follows: 7111 7112 .vb 7113 1 2 0 | 0 3 0 | 0 4 7114 Proc0 0 5 6 | 7 0 0 | 8 0 7115 9 0 10 | 11 0 0 | 12 0 7116 ------------------------------------- 7117 13 0 14 | 15 16 17 | 0 0 7118 Proc1 0 18 0 | 19 20 21 | 0 0 7119 0 0 0 | 22 23 0 | 24 0 7120 ------------------------------------- 7121 Proc2 25 26 27 | 0 0 28 | 29 0 7122 30 0 0 | 31 32 33 | 0 34 7123 .ve 7124 7125 Suppose isrow = [0 1 | 4 | 6 7] and iscol = [1 2 | 3 4 5 | 6]. The resulting submatrix is 7126 7127 .vb 7128 2 0 | 0 3 0 | 0 7129 Proc0 5 6 | 7 0 0 | 8 7130 ------------------------------- 7131 Proc1 18 0 | 19 20 21 | 0 7132 ------------------------------- 7133 Proc2 26 27 | 0 0 28 | 29 7134 0 0 | 31 32 33 | 0 7135 .ve 7136 7137 7138 Concepts: matrices^submatrices 7139 7140 .seealso: MatGetSubMatrices() 7141 @*/ 7142 PetscErrorCode MatGetSubMatrix(Mat mat,IS isrow,IS iscol,MatReuse cll,Mat *newmat) 7143 { 7144 PetscErrorCode ierr; 7145 PetscMPIInt size; 7146 Mat *local; 7147 IS iscoltmp; 7148 7149 PetscFunctionBegin; 7150 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7151 PetscValidHeaderSpecific(isrow,IS_CLASSID,2); 7152 if (iscol) PetscValidHeaderSpecific(iscol,IS_CLASSID,3); 7153 PetscValidPointer(newmat,5); 7154 if (cll == MAT_REUSE_MATRIX) PetscValidHeaderSpecific(*newmat,MAT_CLASSID,5); 7155 PetscValidType(mat,1); 7156 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 7157 MatCheckPreallocated(mat,1); 7158 ierr = MPI_Comm_size(PetscObjectComm((PetscObject)mat),&size);CHKERRQ(ierr); 7159 7160 if (!iscol) { 7161 ierr = ISCreateStride(PetscObjectComm((PetscObject)mat),mat->cmap->n,mat->cmap->rstart,1,&iscoltmp);CHKERRQ(ierr); 7162 } else { 7163 iscoltmp = iscol; 7164 } 7165 7166 /* if original matrix is on just one processor then use submatrix generated */ 7167 if (mat->ops->getsubmatrices && !mat->ops->getsubmatrix && size == 1 && cll == MAT_REUSE_MATRIX) { 7168 ierr = MatGetSubMatrices(mat,1,&isrow,&iscoltmp,MAT_REUSE_MATRIX,&newmat);CHKERRQ(ierr); 7169 if (!iscol) {ierr = ISDestroy(&iscoltmp);CHKERRQ(ierr);} 7170 PetscFunctionReturn(0); 7171 } else if (mat->ops->getsubmatrices && !mat->ops->getsubmatrix && size == 1) { 7172 ierr = MatGetSubMatrices(mat,1,&isrow,&iscoltmp,MAT_INITIAL_MATRIX,&local);CHKERRQ(ierr); 7173 *newmat = *local; 7174 ierr = PetscFree(local);CHKERRQ(ierr); 7175 if (!iscol) {ierr = ISDestroy(&iscoltmp);CHKERRQ(ierr);} 7176 PetscFunctionReturn(0); 7177 } else if (!mat->ops->getsubmatrix) { 7178 /* Create a new matrix type that implements the operation using the full matrix */ 7179 switch (cll) { 7180 case MAT_INITIAL_MATRIX: 7181 ierr = MatCreateSubMatrix(mat,isrow,iscoltmp,newmat);CHKERRQ(ierr); 7182 break; 7183 case MAT_REUSE_MATRIX: 7184 ierr = MatSubMatrixUpdate(*newmat,mat,isrow,iscoltmp);CHKERRQ(ierr); 7185 break; 7186 default: SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_OUTOFRANGE,"Invalid MatReuse, must be either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX"); 7187 } 7188 if (!iscol) {ierr = ISDestroy(&iscoltmp);CHKERRQ(ierr);} 7189 PetscFunctionReturn(0); 7190 } 7191 7192 if (!mat->ops->getsubmatrix) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 7193 ierr = (*mat->ops->getsubmatrix)(mat,isrow,iscoltmp,cll,newmat);CHKERRQ(ierr); 7194 if (!iscol) {ierr = ISDestroy(&iscoltmp);CHKERRQ(ierr);} 7195 if (*newmat && cll == MAT_INITIAL_MATRIX) {ierr = PetscObjectStateIncrease((PetscObject)*newmat);CHKERRQ(ierr);} 7196 PetscFunctionReturn(0); 7197 } 7198 7199 #undef __FUNCT__ 7200 #define __FUNCT__ "MatStashSetInitialSize" 7201 /*@ 7202 MatStashSetInitialSize - sets the sizes of the matrix stash, that is 7203 used during the assembly process to store values that belong to 7204 other processors. 7205 7206 Not Collective 7207 7208 Input Parameters: 7209 + mat - the matrix 7210 . size - the initial size of the stash. 7211 - bsize - the initial size of the block-stash(if used). 7212 7213 Options Database Keys: 7214 + -matstash_initial_size <size> or <size0,size1,...sizep-1> 7215 - -matstash_block_initial_size <bsize> or <bsize0,bsize1,...bsizep-1> 7216 7217 Level: intermediate 7218 7219 Notes: 7220 The block-stash is used for values set with MatSetValuesBlocked() while 7221 the stash is used for values set with MatSetValues() 7222 7223 Run with the option -info and look for output of the form 7224 MatAssemblyBegin_MPIXXX:Stash has MM entries, uses nn mallocs. 7225 to determine the appropriate value, MM, to use for size and 7226 MatAssemblyBegin_MPIXXX:Block-Stash has BMM entries, uses nn mallocs. 7227 to determine the value, BMM to use for bsize 7228 7229 Concepts: stash^setting matrix size 7230 Concepts: matrices^stash 7231 7232 .seealso: MatAssemblyBegin(), MatAssemblyEnd(), Mat, MatStashGetInfo() 7233 7234 @*/ 7235 PetscErrorCode MatStashSetInitialSize(Mat mat,PetscInt size, PetscInt bsize) 7236 { 7237 PetscErrorCode ierr; 7238 7239 PetscFunctionBegin; 7240 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7241 PetscValidType(mat,1); 7242 ierr = MatStashSetInitialSize_Private(&mat->stash,size);CHKERRQ(ierr); 7243 ierr = MatStashSetInitialSize_Private(&mat->bstash,bsize);CHKERRQ(ierr); 7244 PetscFunctionReturn(0); 7245 } 7246 7247 #undef __FUNCT__ 7248 #define __FUNCT__ "MatInterpolateAdd" 7249 /*@ 7250 MatInterpolateAdd - w = y + A*x or A'*x depending on the shape of 7251 the matrix 7252 7253 Neighbor-wise Collective on Mat 7254 7255 Input Parameters: 7256 + mat - the matrix 7257 . x,y - the vectors 7258 - w - where the result is stored 7259 7260 Level: intermediate 7261 7262 Notes: 7263 w may be the same vector as y. 7264 7265 This allows one to use either the restriction or interpolation (its transpose) 7266 matrix to do the interpolation 7267 7268 Concepts: interpolation 7269 7270 .seealso: MatMultAdd(), MatMultTransposeAdd(), MatRestrict() 7271 7272 @*/ 7273 PetscErrorCode MatInterpolateAdd(Mat A,Vec x,Vec y,Vec w) 7274 { 7275 PetscErrorCode ierr; 7276 PetscInt M,N,Ny; 7277 7278 PetscFunctionBegin; 7279 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 7280 PetscValidHeaderSpecific(x,VEC_CLASSID,2); 7281 PetscValidHeaderSpecific(y,VEC_CLASSID,3); 7282 PetscValidHeaderSpecific(w,VEC_CLASSID,4); 7283 PetscValidType(A,1); 7284 MatCheckPreallocated(A,1); 7285 ierr = MatGetSize(A,&M,&N);CHKERRQ(ierr); 7286 ierr = VecGetSize(y,&Ny);CHKERRQ(ierr); 7287 if (M == Ny) { 7288 ierr = MatMultAdd(A,x,y,w);CHKERRQ(ierr); 7289 } else { 7290 ierr = MatMultTransposeAdd(A,x,y,w);CHKERRQ(ierr); 7291 } 7292 PetscFunctionReturn(0); 7293 } 7294 7295 #undef __FUNCT__ 7296 #define __FUNCT__ "MatInterpolate" 7297 /*@ 7298 MatInterpolate - y = A*x or A'*x depending on the shape of 7299 the matrix 7300 7301 Neighbor-wise Collective on Mat 7302 7303 Input Parameters: 7304 + mat - the matrix 7305 - x,y - the vectors 7306 7307 Level: intermediate 7308 7309 Notes: 7310 This allows one to use either the restriction or interpolation (its transpose) 7311 matrix to do the interpolation 7312 7313 Concepts: matrices^interpolation 7314 7315 .seealso: MatMultAdd(), MatMultTransposeAdd(), MatRestrict() 7316 7317 @*/ 7318 PetscErrorCode MatInterpolate(Mat A,Vec x,Vec y) 7319 { 7320 PetscErrorCode ierr; 7321 PetscInt M,N,Ny; 7322 7323 PetscFunctionBegin; 7324 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 7325 PetscValidHeaderSpecific(x,VEC_CLASSID,2); 7326 PetscValidHeaderSpecific(y,VEC_CLASSID,3); 7327 PetscValidType(A,1); 7328 MatCheckPreallocated(A,1); 7329 ierr = MatGetSize(A,&M,&N);CHKERRQ(ierr); 7330 ierr = VecGetSize(y,&Ny);CHKERRQ(ierr); 7331 if (M == Ny) { 7332 ierr = MatMult(A,x,y);CHKERRQ(ierr); 7333 } else { 7334 ierr = MatMultTranspose(A,x,y);CHKERRQ(ierr); 7335 } 7336 PetscFunctionReturn(0); 7337 } 7338 7339 #undef __FUNCT__ 7340 #define __FUNCT__ "MatRestrict" 7341 /*@ 7342 MatRestrict - y = A*x or A'*x 7343 7344 Neighbor-wise Collective on Mat 7345 7346 Input Parameters: 7347 + mat - the matrix 7348 - x,y - the vectors 7349 7350 Level: intermediate 7351 7352 Notes: 7353 This allows one to use either the restriction or interpolation (its transpose) 7354 matrix to do the restriction 7355 7356 Concepts: matrices^restriction 7357 7358 .seealso: MatMultAdd(), MatMultTransposeAdd(), MatInterpolate() 7359 7360 @*/ 7361 PetscErrorCode MatRestrict(Mat A,Vec x,Vec y) 7362 { 7363 PetscErrorCode ierr; 7364 PetscInt M,N,Ny; 7365 7366 PetscFunctionBegin; 7367 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 7368 PetscValidHeaderSpecific(x,VEC_CLASSID,2); 7369 PetscValidHeaderSpecific(y,VEC_CLASSID,3); 7370 PetscValidType(A,1); 7371 MatCheckPreallocated(A,1); 7372 7373 ierr = MatGetSize(A,&M,&N);CHKERRQ(ierr); 7374 ierr = VecGetSize(y,&Ny);CHKERRQ(ierr); 7375 if (M == Ny) { 7376 ierr = MatMult(A,x,y);CHKERRQ(ierr); 7377 } else { 7378 ierr = MatMultTranspose(A,x,y);CHKERRQ(ierr); 7379 } 7380 PetscFunctionReturn(0); 7381 } 7382 7383 #undef __FUNCT__ 7384 #define __FUNCT__ "MatGetNullSpace" 7385 /*@ 7386 MatGetNullSpace - retrieves the null space to a matrix. 7387 7388 Logically Collective on Mat and MatNullSpace 7389 7390 Input Parameters: 7391 + mat - the matrix 7392 - nullsp - the null space object 7393 7394 Level: developer 7395 7396 Notes: 7397 This null space is used by solvers. Overwrites any previous null space that may have been attached 7398 7399 Concepts: null space^attaching to matrix 7400 7401 .seealso: MatCreate(), MatNullSpaceCreate(), MatSetNearNullSpace() 7402 @*/ 7403 PetscErrorCode MatGetNullSpace(Mat mat, MatNullSpace *nullsp) 7404 { 7405 PetscFunctionBegin; 7406 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7407 PetscValidType(mat,1); 7408 PetscValidPointer(nullsp,2); 7409 *nullsp = mat->nullsp; 7410 PetscFunctionReturn(0); 7411 } 7412 7413 #undef __FUNCT__ 7414 #define __FUNCT__ "MatSetNullSpace" 7415 /*@ 7416 MatSetNullSpace - attaches a null space to a matrix. 7417 This null space will be removed from the resulting vector whenever 7418 MatMult() is called 7419 7420 Logically Collective on Mat and MatNullSpace 7421 7422 Input Parameters: 7423 + mat - the matrix 7424 - nullsp - the null space object 7425 7426 Level: advanced 7427 7428 Notes: 7429 This null space is used by solvers. Overwrites any previous null space that may have been attached 7430 7431 Concepts: null space^attaching to matrix 7432 7433 .seealso: MatCreate(), MatNullSpaceCreate(), MatSetNearNullSpace() 7434 @*/ 7435 PetscErrorCode MatSetNullSpace(Mat mat,MatNullSpace nullsp) 7436 { 7437 PetscErrorCode ierr; 7438 7439 PetscFunctionBegin; 7440 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7441 PetscValidType(mat,1); 7442 PetscValidHeaderSpecific(nullsp,MAT_NULLSPACE_CLASSID,2); 7443 MatCheckPreallocated(mat,1); 7444 ierr = PetscObjectReference((PetscObject)nullsp);CHKERRQ(ierr); 7445 ierr = MatNullSpaceDestroy(&mat->nullsp);CHKERRQ(ierr); 7446 7447 mat->nullsp = nullsp; 7448 PetscFunctionReturn(0); 7449 } 7450 7451 #undef __FUNCT__ 7452 #define __FUNCT__ "MatSetNearNullSpace" 7453 /*@ 7454 MatSetNearNullSpace - attaches a null space to a matrix. 7455 This null space will be used to provide near null space vectors to a multigrid preconditioner built from this matrix. 7456 7457 Logically Collective on Mat and MatNullSpace 7458 7459 Input Parameters: 7460 + mat - the matrix 7461 - nullsp - the null space object 7462 7463 Level: advanced 7464 7465 Notes: 7466 Overwrites any previous near null space that may have been attached 7467 7468 Concepts: null space^attaching to matrix 7469 7470 .seealso: MatCreate(), MatNullSpaceCreate(), MatSetNullSpace() 7471 @*/ 7472 PetscErrorCode MatSetNearNullSpace(Mat mat,MatNullSpace nullsp) 7473 { 7474 PetscErrorCode ierr; 7475 7476 PetscFunctionBegin; 7477 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7478 PetscValidType(mat,1); 7479 PetscValidHeaderSpecific(nullsp,MAT_NULLSPACE_CLASSID,2); 7480 MatCheckPreallocated(mat,1); 7481 ierr = PetscObjectReference((PetscObject)nullsp);CHKERRQ(ierr); 7482 ierr = MatNullSpaceDestroy(&mat->nearnullsp);CHKERRQ(ierr); 7483 7484 mat->nearnullsp = nullsp; 7485 PetscFunctionReturn(0); 7486 } 7487 7488 #undef __FUNCT__ 7489 #define __FUNCT__ "MatGetNearNullSpace" 7490 /*@ 7491 MatGetNearNullSpace -Get null space attached with MatSetNearNullSpace() 7492 7493 Not Collective 7494 7495 Input Parameters: 7496 . mat - the matrix 7497 7498 Output Parameters: 7499 . nullsp - the null space object, NULL if not set 7500 7501 Level: developer 7502 7503 Concepts: null space^attaching to matrix 7504 7505 .seealso: MatSetNearNullSpace(), MatGetNullSpace() 7506 @*/ 7507 PetscErrorCode MatGetNearNullSpace(Mat mat,MatNullSpace *nullsp) 7508 { 7509 PetscFunctionBegin; 7510 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7511 PetscValidType(mat,1); 7512 PetscValidPointer(nullsp,2); 7513 MatCheckPreallocated(mat,1); 7514 *nullsp = mat->nearnullsp; 7515 PetscFunctionReturn(0); 7516 } 7517 7518 #undef __FUNCT__ 7519 #define __FUNCT__ "MatICCFactor" 7520 /*@C 7521 MatICCFactor - Performs in-place incomplete Cholesky factorization of matrix. 7522 7523 Collective on Mat 7524 7525 Input Parameters: 7526 + mat - the matrix 7527 . row - row/column permutation 7528 . fill - expected fill factor >= 1.0 7529 - level - level of fill, for ICC(k) 7530 7531 Notes: 7532 Probably really in-place only when level of fill is zero, otherwise allocates 7533 new space to store factored matrix and deletes previous memory. 7534 7535 Most users should employ the simplified KSP interface for linear solvers 7536 instead of working directly with matrix algebra routines such as this. 7537 See, e.g., KSPCreate(). 7538 7539 Level: developer 7540 7541 Concepts: matrices^incomplete Cholesky factorization 7542 Concepts: Cholesky factorization 7543 7544 .seealso: MatICCFactorSymbolic(), MatLUFactorNumeric(), MatCholeskyFactor() 7545 7546 Developer Note: fortran interface is not autogenerated as the f90 7547 interface defintion cannot be generated correctly [due to MatFactorInfo] 7548 7549 @*/ 7550 PetscErrorCode MatICCFactor(Mat mat,IS row,const MatFactorInfo *info) 7551 { 7552 PetscErrorCode ierr; 7553 7554 PetscFunctionBegin; 7555 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7556 PetscValidType(mat,1); 7557 if (row) PetscValidHeaderSpecific(row,IS_CLASSID,2); 7558 PetscValidPointer(info,3); 7559 if (mat->rmap->N != mat->cmap->N) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONG,"matrix must be square"); 7560 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 7561 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 7562 if (!mat->ops->iccfactor) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 7563 MatCheckPreallocated(mat,1); 7564 ierr = (*mat->ops->iccfactor)(mat,row,info);CHKERRQ(ierr); 7565 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 7566 PetscFunctionReturn(0); 7567 } 7568 7569 #undef __FUNCT__ 7570 #define __FUNCT__ "MatSetValuesAdifor" 7571 /*@ 7572 MatSetValuesAdifor - Sets values computed with automatic differentiation into a matrix. 7573 7574 Not Collective 7575 7576 Input Parameters: 7577 + mat - the matrix 7578 . nl - leading dimension of v 7579 - v - the values compute with ADIFOR 7580 7581 Level: developer 7582 7583 Notes: 7584 Must call MatSetColoring() before using this routine. Also this matrix must already 7585 have its nonzero pattern determined. 7586 7587 .seealso: MatSetOption(), MatAssemblyBegin(), MatAssemblyEnd(), MatSetValuesBlocked(), MatSetValuesLocal(), 7588 MatSetValues(), MatSetColoring() 7589 @*/ 7590 PetscErrorCode MatSetValuesAdifor(Mat mat,PetscInt nl,void *v) 7591 { 7592 PetscErrorCode ierr; 7593 7594 PetscFunctionBegin; 7595 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7596 PetscValidType(mat,1); 7597 PetscValidPointer(v,3); 7598 7599 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Matrix must be already assembled"); 7600 ierr = PetscLogEventBegin(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 7601 if (!mat->ops->setvaluesadifor) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 7602 ierr = (*mat->ops->setvaluesadifor)(mat,nl,v);CHKERRQ(ierr); 7603 ierr = PetscLogEventEnd(MAT_SetValues,mat,0,0,0);CHKERRQ(ierr); 7604 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 7605 PetscFunctionReturn(0); 7606 } 7607 7608 #undef __FUNCT__ 7609 #define __FUNCT__ "MatDiagonalScaleLocal" 7610 /*@ 7611 MatDiagonalScaleLocal - Scales columns of a matrix given the scaling values including the 7612 ghosted ones. 7613 7614 Not Collective 7615 7616 Input Parameters: 7617 + mat - the matrix 7618 - diag = the diagonal values, including ghost ones 7619 7620 Level: developer 7621 7622 Notes: Works only for MPIAIJ and MPIBAIJ matrices 7623 7624 .seealso: MatDiagonalScale() 7625 @*/ 7626 PetscErrorCode MatDiagonalScaleLocal(Mat mat,Vec diag) 7627 { 7628 PetscErrorCode ierr; 7629 PetscMPIInt size; 7630 7631 PetscFunctionBegin; 7632 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7633 PetscValidHeaderSpecific(diag,VEC_CLASSID,2); 7634 PetscValidType(mat,1); 7635 7636 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Matrix must be already assembled"); 7637 ierr = PetscLogEventBegin(MAT_Scale,mat,0,0,0);CHKERRQ(ierr); 7638 ierr = MPI_Comm_size(PetscObjectComm((PetscObject)mat),&size);CHKERRQ(ierr); 7639 if (size == 1) { 7640 PetscInt n,m; 7641 ierr = VecGetSize(diag,&n);CHKERRQ(ierr); 7642 ierr = MatGetSize(mat,0,&m);CHKERRQ(ierr); 7643 if (m == n) { 7644 ierr = MatDiagonalScale(mat,0,diag);CHKERRQ(ierr); 7645 } else SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"Only supported for sequential matrices when no ghost points/periodic conditions"); 7646 } else { 7647 ierr = PetscUseMethod(mat,"MatDiagonalScaleLocal_C",(Mat,Vec),(mat,diag));CHKERRQ(ierr); 7648 } 7649 ierr = PetscLogEventEnd(MAT_Scale,mat,0,0,0);CHKERRQ(ierr); 7650 ierr = PetscObjectStateIncrease((PetscObject)mat);CHKERRQ(ierr); 7651 PetscFunctionReturn(0); 7652 } 7653 7654 #undef __FUNCT__ 7655 #define __FUNCT__ "MatGetInertia" 7656 /*@ 7657 MatGetInertia - Gets the inertia from a factored matrix 7658 7659 Collective on Mat 7660 7661 Input Parameter: 7662 . mat - the matrix 7663 7664 Output Parameters: 7665 + nneg - number of negative eigenvalues 7666 . nzero - number of zero eigenvalues 7667 - npos - number of positive eigenvalues 7668 7669 Level: advanced 7670 7671 Notes: Matrix must have been factored by MatCholeskyFactor() 7672 7673 7674 @*/ 7675 PetscErrorCode MatGetInertia(Mat mat,PetscInt *nneg,PetscInt *nzero,PetscInt *npos) 7676 { 7677 PetscErrorCode ierr; 7678 7679 PetscFunctionBegin; 7680 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7681 PetscValidType(mat,1); 7682 if (!mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix"); 7683 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Numeric factor mat is not assembled"); 7684 if (!mat->ops->getinertia) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 7685 ierr = (*mat->ops->getinertia)(mat,nneg,nzero,npos);CHKERRQ(ierr); 7686 PetscFunctionReturn(0); 7687 } 7688 7689 /* ----------------------------------------------------------------*/ 7690 #undef __FUNCT__ 7691 #define __FUNCT__ "MatSolves" 7692 /*@C 7693 MatSolves - Solves A x = b, given a factored matrix, for a collection of vectors 7694 7695 Neighbor-wise Collective on Mat and Vecs 7696 7697 Input Parameters: 7698 + mat - the factored matrix 7699 - b - the right-hand-side vectors 7700 7701 Output Parameter: 7702 . x - the result vectors 7703 7704 Notes: 7705 The vectors b and x cannot be the same. I.e., one cannot 7706 call MatSolves(A,x,x). 7707 7708 Notes: 7709 Most users should employ the simplified KSP interface for linear solvers 7710 instead of working directly with matrix algebra routines such as this. 7711 See, e.g., KSPCreate(). 7712 7713 Level: developer 7714 7715 Concepts: matrices^triangular solves 7716 7717 .seealso: MatSolveAdd(), MatSolveTranspose(), MatSolveTransposeAdd(), MatSolve() 7718 @*/ 7719 PetscErrorCode MatSolves(Mat mat,Vecs b,Vecs x) 7720 { 7721 PetscErrorCode ierr; 7722 7723 PetscFunctionBegin; 7724 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 7725 PetscValidType(mat,1); 7726 if (x == b) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_IDN,"x and b must be different vectors"); 7727 if (!mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Unfactored matrix"); 7728 if (!mat->rmap->N && !mat->cmap->N) PetscFunctionReturn(0); 7729 7730 if (!mat->ops->solves) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 7731 MatCheckPreallocated(mat,1); 7732 ierr = PetscLogEventBegin(MAT_Solves,mat,0,0,0);CHKERRQ(ierr); 7733 ierr = (*mat->ops->solves)(mat,b,x);CHKERRQ(ierr); 7734 ierr = PetscLogEventEnd(MAT_Solves,mat,0,0,0);CHKERRQ(ierr); 7735 PetscFunctionReturn(0); 7736 } 7737 7738 #undef __FUNCT__ 7739 #define __FUNCT__ "MatIsSymmetric" 7740 /*@ 7741 MatIsSymmetric - Test whether a matrix is symmetric 7742 7743 Collective on Mat 7744 7745 Input Parameter: 7746 + A - the matrix to test 7747 - tol - difference between value and its transpose less than this amount counts as equal (use 0.0 for exact transpose) 7748 7749 Output Parameters: 7750 . flg - the result 7751 7752 Notes: For real numbers MatIsSymmetric() and MatIsHermitian() return identical results 7753 7754 Level: intermediate 7755 7756 Concepts: matrix^symmetry 7757 7758 .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), MatIsSymmetricKnown() 7759 @*/ 7760 PetscErrorCode MatIsSymmetric(Mat A,PetscReal tol,PetscBool *flg) 7761 { 7762 PetscErrorCode ierr; 7763 7764 PetscFunctionBegin; 7765 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 7766 PetscValidPointer(flg,2); 7767 7768 if (!A->symmetric_set) { 7769 if (!A->ops->issymmetric) { 7770 MatType mattype; 7771 ierr = MatGetType(A,&mattype);CHKERRQ(ierr); 7772 SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Matrix of type <%s> does not support checking for symmetric",mattype); 7773 } 7774 ierr = (*A->ops->issymmetric)(A,tol,flg);CHKERRQ(ierr); 7775 if (!tol) { 7776 A->symmetric_set = PETSC_TRUE; 7777 A->symmetric = *flg; 7778 if (A->symmetric) { 7779 A->structurally_symmetric_set = PETSC_TRUE; 7780 A->structurally_symmetric = PETSC_TRUE; 7781 } 7782 } 7783 } else if (A->symmetric) { 7784 *flg = PETSC_TRUE; 7785 } else if (!tol) { 7786 *flg = PETSC_FALSE; 7787 } else { 7788 if (!A->ops->issymmetric) { 7789 MatType mattype; 7790 ierr = MatGetType(A,&mattype);CHKERRQ(ierr); 7791 SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Matrix of type <%s> does not support checking for symmetric",mattype); 7792 } 7793 ierr = (*A->ops->issymmetric)(A,tol,flg);CHKERRQ(ierr); 7794 } 7795 PetscFunctionReturn(0); 7796 } 7797 7798 #undef __FUNCT__ 7799 #define __FUNCT__ "MatIsHermitian" 7800 /*@ 7801 MatIsHermitian - Test whether a matrix is Hermitian 7802 7803 Collective on Mat 7804 7805 Input Parameter: 7806 + A - the matrix to test 7807 - tol - difference between value and its transpose less than this amount counts as equal (use 0.0 for exact Hermitian) 7808 7809 Output Parameters: 7810 . flg - the result 7811 7812 Level: intermediate 7813 7814 Concepts: matrix^symmetry 7815 7816 .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), 7817 MatIsSymmetricKnown(), MatIsSymmetric() 7818 @*/ 7819 PetscErrorCode MatIsHermitian(Mat A,PetscReal tol,PetscBool *flg) 7820 { 7821 PetscErrorCode ierr; 7822 7823 PetscFunctionBegin; 7824 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 7825 PetscValidPointer(flg,2); 7826 7827 if (!A->hermitian_set) { 7828 if (!A->ops->ishermitian) { 7829 MatType mattype; 7830 ierr = MatGetType(A,&mattype);CHKERRQ(ierr); 7831 SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Matrix of type <%s> does not support checking for hermitian",mattype); 7832 } 7833 ierr = (*A->ops->ishermitian)(A,tol,flg);CHKERRQ(ierr); 7834 if (!tol) { 7835 A->hermitian_set = PETSC_TRUE; 7836 A->hermitian = *flg; 7837 if (A->hermitian) { 7838 A->structurally_symmetric_set = PETSC_TRUE; 7839 A->structurally_symmetric = PETSC_TRUE; 7840 } 7841 } 7842 } else if (A->hermitian) { 7843 *flg = PETSC_TRUE; 7844 } else if (!tol) { 7845 *flg = PETSC_FALSE; 7846 } else { 7847 if (!A->ops->ishermitian) { 7848 MatType mattype; 7849 ierr = MatGetType(A,&mattype);CHKERRQ(ierr); 7850 SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Matrix of type <%s> does not support checking for hermitian",mattype); 7851 } 7852 ierr = (*A->ops->ishermitian)(A,tol,flg);CHKERRQ(ierr); 7853 } 7854 PetscFunctionReturn(0); 7855 } 7856 7857 #undef __FUNCT__ 7858 #define __FUNCT__ "MatIsSymmetricKnown" 7859 /*@ 7860 MatIsSymmetricKnown - Checks the flag on the matrix to see if it is symmetric. 7861 7862 Not Collective 7863 7864 Input Parameter: 7865 . A - the matrix to check 7866 7867 Output Parameters: 7868 + set - if the symmetric flag is set (this tells you if the next flag is valid) 7869 - flg - the result 7870 7871 Level: advanced 7872 7873 Concepts: matrix^symmetry 7874 7875 Note: Does not check the matrix values directly, so this may return unknown (set = PETSC_FALSE). Use MatIsSymmetric() 7876 if you want it explicitly checked 7877 7878 .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), MatIsSymmetric() 7879 @*/ 7880 PetscErrorCode MatIsSymmetricKnown(Mat A,PetscBool *set,PetscBool *flg) 7881 { 7882 PetscFunctionBegin; 7883 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 7884 PetscValidPointer(set,2); 7885 PetscValidPointer(flg,3); 7886 if (A->symmetric_set) { 7887 *set = PETSC_TRUE; 7888 *flg = A->symmetric; 7889 } else { 7890 *set = PETSC_FALSE; 7891 } 7892 PetscFunctionReturn(0); 7893 } 7894 7895 #undef __FUNCT__ 7896 #define __FUNCT__ "MatIsHermitianKnown" 7897 /*@ 7898 MatIsHermitianKnown - Checks the flag on the matrix to see if it is hermitian. 7899 7900 Not Collective 7901 7902 Input Parameter: 7903 . A - the matrix to check 7904 7905 Output Parameters: 7906 + set - if the hermitian flag is set (this tells you if the next flag is valid) 7907 - flg - the result 7908 7909 Level: advanced 7910 7911 Concepts: matrix^symmetry 7912 7913 Note: Does not check the matrix values directly, so this may return unknown (set = PETSC_FALSE). Use MatIsHermitian() 7914 if you want it explicitly checked 7915 7916 .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsStructurallySymmetric(), MatSetOption(), MatIsSymmetric() 7917 @*/ 7918 PetscErrorCode MatIsHermitianKnown(Mat A,PetscBool *set,PetscBool *flg) 7919 { 7920 PetscFunctionBegin; 7921 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 7922 PetscValidPointer(set,2); 7923 PetscValidPointer(flg,3); 7924 if (A->hermitian_set) { 7925 *set = PETSC_TRUE; 7926 *flg = A->hermitian; 7927 } else { 7928 *set = PETSC_FALSE; 7929 } 7930 PetscFunctionReturn(0); 7931 } 7932 7933 #undef __FUNCT__ 7934 #define __FUNCT__ "MatIsStructurallySymmetric" 7935 /*@ 7936 MatIsStructurallySymmetric - Test whether a matrix is structurally symmetric 7937 7938 Collective on Mat 7939 7940 Input Parameter: 7941 . A - the matrix to test 7942 7943 Output Parameters: 7944 . flg - the result 7945 7946 Level: intermediate 7947 7948 Concepts: matrix^symmetry 7949 7950 .seealso: MatTranspose(), MatIsTranspose(), MatIsHermitian(), MatIsSymmetric(), MatSetOption() 7951 @*/ 7952 PetscErrorCode MatIsStructurallySymmetric(Mat A,PetscBool *flg) 7953 { 7954 PetscErrorCode ierr; 7955 7956 PetscFunctionBegin; 7957 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 7958 PetscValidPointer(flg,2); 7959 if (!A->structurally_symmetric_set) { 7960 if (!A->ops->isstructurallysymmetric) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"Matrix does not support checking for structural symmetric"); 7961 ierr = (*A->ops->isstructurallysymmetric)(A,&A->structurally_symmetric);CHKERRQ(ierr); 7962 7963 A->structurally_symmetric_set = PETSC_TRUE; 7964 } 7965 *flg = A->structurally_symmetric; 7966 PetscFunctionReturn(0); 7967 } 7968 7969 #undef __FUNCT__ 7970 #define __FUNCT__ "MatStashGetInfo" 7971 extern PetscErrorCode MatStashGetInfo_Private(MatStash*,PetscInt*,PetscInt*); 7972 /*@ 7973 MatStashGetInfo - Gets how many values are currently in the matrix stash, i.e. need 7974 to be communicated to other processors during the MatAssemblyBegin/End() process 7975 7976 Not collective 7977 7978 Input Parameter: 7979 . vec - the vector 7980 7981 Output Parameters: 7982 + nstash - the size of the stash 7983 . reallocs - the number of additional mallocs incurred. 7984 . bnstash - the size of the block stash 7985 - breallocs - the number of additional mallocs incurred.in the block stash 7986 7987 Level: advanced 7988 7989 .seealso: MatAssemblyBegin(), MatAssemblyEnd(), Mat, MatStashSetInitialSize() 7990 7991 @*/ 7992 PetscErrorCode MatStashGetInfo(Mat mat,PetscInt *nstash,PetscInt *reallocs,PetscInt *bnstash,PetscInt *breallocs) 7993 { 7994 PetscErrorCode ierr; 7995 7996 PetscFunctionBegin; 7997 ierr = MatStashGetInfo_Private(&mat->stash,nstash,reallocs);CHKERRQ(ierr); 7998 ierr = MatStashGetInfo_Private(&mat->bstash,bnstash,breallocs);CHKERRQ(ierr); 7999 PetscFunctionReturn(0); 8000 } 8001 8002 #undef __FUNCT__ 8003 #define __FUNCT__ "MatGetVecs" 8004 /*@C 8005 MatGetVecs - Get vector(s) compatible with the matrix, i.e. with the same 8006 parallel layout 8007 8008 Collective on Mat 8009 8010 Input Parameter: 8011 . mat - the matrix 8012 8013 Output Parameter: 8014 + right - (optional) vector that the matrix can be multiplied against 8015 - left - (optional) vector that the matrix vector product can be stored in 8016 8017 Level: advanced 8018 8019 .seealso: MatCreate() 8020 @*/ 8021 PetscErrorCode MatGetVecs(Mat mat,Vec *right,Vec *left) 8022 { 8023 PetscErrorCode ierr; 8024 8025 PetscFunctionBegin; 8026 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 8027 PetscValidType(mat,1); 8028 MatCheckPreallocated(mat,1); 8029 if (mat->ops->getvecs) { 8030 ierr = (*mat->ops->getvecs)(mat,right,left);CHKERRQ(ierr); 8031 } else { 8032 PetscMPIInt size; 8033 ierr = MPI_Comm_size(PetscObjectComm((PetscObject)mat), &size);CHKERRQ(ierr); 8034 if (right) { 8035 ierr = VecCreate(PetscObjectComm((PetscObject)mat),right);CHKERRQ(ierr); 8036 ierr = VecSetSizes(*right,mat->cmap->n,PETSC_DETERMINE);CHKERRQ(ierr); 8037 ierr = VecSetBlockSize(*right,mat->rmap->bs);CHKERRQ(ierr); 8038 ierr = VecSetType(*right,VECSTANDARD);CHKERRQ(ierr); 8039 ierr = PetscLayoutReference(mat->cmap,&(*right)->map);CHKERRQ(ierr); 8040 } 8041 if (left) { 8042 ierr = VecCreate(PetscObjectComm((PetscObject)mat),left);CHKERRQ(ierr); 8043 ierr = VecSetSizes(*left,mat->rmap->n,PETSC_DETERMINE);CHKERRQ(ierr); 8044 ierr = VecSetBlockSize(*left,mat->rmap->bs);CHKERRQ(ierr); 8045 ierr = VecSetType(*left,VECSTANDARD);CHKERRQ(ierr); 8046 ierr = PetscLayoutReference(mat->rmap,&(*left)->map);CHKERRQ(ierr); 8047 } 8048 } 8049 PetscFunctionReturn(0); 8050 } 8051 8052 #undef __FUNCT__ 8053 #define __FUNCT__ "MatFactorInfoInitialize" 8054 /*@C 8055 MatFactorInfoInitialize - Initializes a MatFactorInfo data structure 8056 with default values. 8057 8058 Not Collective 8059 8060 Input Parameters: 8061 . info - the MatFactorInfo data structure 8062 8063 8064 Notes: The solvers are generally used through the KSP and PC objects, for example 8065 PCLU, PCILU, PCCHOLESKY, PCICC 8066 8067 Level: developer 8068 8069 .seealso: MatFactorInfo 8070 8071 Developer Note: fortran interface is not autogenerated as the f90 8072 interface defintion cannot be generated correctly [due to MatFactorInfo] 8073 8074 @*/ 8075 8076 PetscErrorCode MatFactorInfoInitialize(MatFactorInfo *info) 8077 { 8078 PetscErrorCode ierr; 8079 8080 PetscFunctionBegin; 8081 ierr = PetscMemzero(info,sizeof(MatFactorInfo));CHKERRQ(ierr); 8082 PetscFunctionReturn(0); 8083 } 8084 8085 #undef __FUNCT__ 8086 #define __FUNCT__ "MatPtAP" 8087 /*@ 8088 MatPtAP - Creates the matrix product C = P^T * A * P 8089 8090 Neighbor-wise Collective on Mat 8091 8092 Input Parameters: 8093 + A - the matrix 8094 . P - the projection matrix 8095 . scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 8096 - fill - expected fill as ratio of nnz(C)/(nnz(A) + nnz(P)) 8097 8098 Output Parameters: 8099 . C - the product matrix 8100 8101 Notes: 8102 C will be created and must be destroyed by the user with MatDestroy(). 8103 8104 This routine is currently only implemented for pairs of AIJ matrices and classes 8105 which inherit from AIJ. 8106 8107 Level: intermediate 8108 8109 .seealso: MatPtAPSymbolic(), MatPtAPNumeric(), MatMatMult(), MatRARt() 8110 @*/ 8111 PetscErrorCode MatPtAP(Mat A,Mat P,MatReuse scall,PetscReal fill,Mat *C) 8112 { 8113 PetscErrorCode ierr; 8114 PetscErrorCode (*fA)(Mat,Mat,MatReuse,PetscReal,Mat*); 8115 PetscErrorCode (*fP)(Mat,Mat,MatReuse,PetscReal,Mat*); 8116 PetscErrorCode (*ptap)(Mat,Mat,MatReuse,PetscReal,Mat*)=NULL; 8117 PetscBool viatranspose=PETSC_FALSE,viamatmatmatmult=PETSC_FALSE; 8118 8119 PetscFunctionBegin; 8120 ierr = PetscOptionsGetBool(((PetscObject)A)->prefix,"-matptap_viatranspose",&viatranspose,NULL);CHKERRQ(ierr); 8121 ierr = PetscOptionsGetBool(((PetscObject)A)->prefix,"-matptap_viamatmatmatmult",&viamatmatmatmult,NULL);CHKERRQ(ierr); 8122 8123 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8124 PetscValidType(A,1); 8125 MatCheckPreallocated(A,1); 8126 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8127 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8128 PetscValidHeaderSpecific(P,MAT_CLASSID,2); 8129 PetscValidType(P,2); 8130 MatCheckPreallocated(P,2); 8131 if (!P->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8132 if (P->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8133 8134 if (P->rmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->rmap->N,A->cmap->N); 8135 if (fill < 1.0) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Expected fill=%G must be >= 1.0",fill); 8136 8137 if (scall == MAT_REUSE_MATRIX) { 8138 PetscValidPointer(*C,5); 8139 PetscValidHeaderSpecific(*C,MAT_CLASSID,5); 8140 if (viatranspose || viamatmatmatmult) { 8141 Mat Pt; 8142 ierr = MatTranspose(P,MAT_INITIAL_MATRIX,&Pt);CHKERRQ(ierr); 8143 if (viamatmatmatmult) { 8144 ierr = MatMatMatMult(Pt,A,P,scall,fill,C);CHKERRQ(ierr); 8145 } else { 8146 Mat AP; 8147 ierr = MatMatMult(A,P,MAT_INITIAL_MATRIX,fill,&AP);CHKERRQ(ierr); 8148 ierr = MatMatMult(Pt,AP,scall,fill,C);CHKERRQ(ierr); 8149 ierr = MatDestroy(&AP);CHKERRQ(ierr); 8150 } 8151 ierr = MatDestroy(&Pt);CHKERRQ(ierr); 8152 } else { 8153 ierr = PetscLogEventBegin(MAT_PtAPNumeric,A,P,0,0);CHKERRQ(ierr); 8154 ierr = (*(*C)->ops->ptapnumeric)(A,P,*C);CHKERRQ(ierr); 8155 ierr = PetscLogEventEnd(MAT_PtAPNumeric,A,P,0,0);CHKERRQ(ierr); 8156 } 8157 PetscFunctionReturn(0); 8158 } 8159 8160 if (fill == PETSC_DEFAULT || fill == PETSC_DECIDE) fill = 2.0; 8161 if (fill < 1.0) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Expected fill=%G must be >= 1.0",fill); 8162 8163 fA = A->ops->ptap; 8164 fP = P->ops->ptap; 8165 if (fP == fA) { 8166 if (!fA) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"MatPtAP not supported for A of type %s",((PetscObject)A)->type_name); 8167 ptap = fA; 8168 } else { 8169 /* dispatch based on the type of A and P from their PetscObject's PetscFunctionLists. */ 8170 char ptapname[256]; 8171 ierr = PetscStrcpy(ptapname,"MatPtAP_");CHKERRQ(ierr); 8172 ierr = PetscStrcat(ptapname,((PetscObject)A)->type_name);CHKERRQ(ierr); 8173 ierr = PetscStrcat(ptapname,"_");CHKERRQ(ierr); 8174 ierr = PetscStrcat(ptapname,((PetscObject)P)->type_name);CHKERRQ(ierr); 8175 ierr = PetscStrcat(ptapname,"_C");CHKERRQ(ierr); /* e.g., ptapname = "MatPtAP_seqdense_seqaij_C" */ 8176 ierr = PetscObjectQueryFunction((PetscObject)P,ptapname,(void (**)(void))&ptap);CHKERRQ(ierr); 8177 if (!ptap) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_INCOMP,"MatPtAP requires A, %s, to be compatible with P, %s",((PetscObject)A)->type_name,((PetscObject)P)->type_name); 8178 } 8179 8180 if (viatranspose || viamatmatmatmult) { 8181 Mat Pt; 8182 ierr = MatTranspose(P,MAT_INITIAL_MATRIX,&Pt);CHKERRQ(ierr); 8183 if (viamatmatmatmult) { 8184 ierr = MatMatMatMult(Pt,A,P,scall,fill,C);CHKERRQ(ierr); 8185 ierr = PetscInfo(*C,"MatPtAP via MatMatMatMult\n");CHKERRQ(ierr); 8186 } else { 8187 Mat AP; 8188 ierr = MatMatMult(A,P,MAT_INITIAL_MATRIX,fill,&AP);CHKERRQ(ierr); 8189 ierr = MatMatMult(Pt,AP,scall,fill,C);CHKERRQ(ierr); 8190 ierr = MatDestroy(&AP);CHKERRQ(ierr); 8191 ierr = PetscInfo(*C,"MatPtAP via MatTranspose and MatMatMult\n");CHKERRQ(ierr); 8192 } 8193 ierr = MatDestroy(&Pt);CHKERRQ(ierr); 8194 } else { 8195 ierr = PetscLogEventBegin(MAT_PtAP,A,P,0,0);CHKERRQ(ierr); 8196 ierr = (*ptap)(A,P,scall,fill,C);CHKERRQ(ierr); 8197 ierr = PetscLogEventEnd(MAT_PtAP,A,P,0,0);CHKERRQ(ierr); 8198 } 8199 PetscFunctionReturn(0); 8200 } 8201 8202 #undef __FUNCT__ 8203 #define __FUNCT__ "MatPtAPNumeric" 8204 /*@ 8205 MatPtAPNumeric - Computes the matrix product C = P^T * A * P 8206 8207 Neighbor-wise Collective on Mat 8208 8209 Input Parameters: 8210 + A - the matrix 8211 - P - the projection matrix 8212 8213 Output Parameters: 8214 . C - the product matrix 8215 8216 Notes: 8217 C must have been created by calling MatPtAPSymbolic and must be destroyed by 8218 the user using MatDeatroy(). 8219 8220 This routine is currently only implemented for pairs of AIJ matrices and classes 8221 which inherit from AIJ. C will be of type MATAIJ. 8222 8223 Level: intermediate 8224 8225 .seealso: MatPtAP(), MatPtAPSymbolic(), MatMatMultNumeric() 8226 @*/ 8227 PetscErrorCode MatPtAPNumeric(Mat A,Mat P,Mat C) 8228 { 8229 PetscErrorCode ierr; 8230 8231 PetscFunctionBegin; 8232 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8233 PetscValidType(A,1); 8234 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8235 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8236 PetscValidHeaderSpecific(P,MAT_CLASSID,2); 8237 PetscValidType(P,2); 8238 MatCheckPreallocated(P,2); 8239 if (!P->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8240 if (P->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8241 PetscValidHeaderSpecific(C,MAT_CLASSID,3); 8242 PetscValidType(C,3); 8243 MatCheckPreallocated(C,3); 8244 if (C->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8245 if (P->cmap->N!=C->rmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->cmap->N,C->rmap->N); 8246 if (P->rmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->rmap->N,A->cmap->N); 8247 if (A->rmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix 'A' must be square, %D != %D",A->rmap->N,A->cmap->N); 8248 if (P->cmap->N!=C->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->cmap->N,C->cmap->N); 8249 MatCheckPreallocated(A,1); 8250 8251 ierr = PetscLogEventBegin(MAT_PtAPNumeric,A,P,0,0);CHKERRQ(ierr); 8252 ierr = (*C->ops->ptapnumeric)(A,P,C);CHKERRQ(ierr); 8253 ierr = PetscLogEventEnd(MAT_PtAPNumeric,A,P,0,0);CHKERRQ(ierr); 8254 PetscFunctionReturn(0); 8255 } 8256 8257 #undef __FUNCT__ 8258 #define __FUNCT__ "MatPtAPSymbolic" 8259 /*@ 8260 MatPtAPSymbolic - Creates the (i,j) structure of the matrix product C = P^T * A * P 8261 8262 Neighbor-wise Collective on Mat 8263 8264 Input Parameters: 8265 + A - the matrix 8266 - P - the projection matrix 8267 8268 Output Parameters: 8269 . C - the (i,j) structure of the product matrix 8270 8271 Notes: 8272 C will be created and must be destroyed by the user with MatDestroy(). 8273 8274 This routine is currently only implemented for pairs of SeqAIJ matrices and classes 8275 which inherit from SeqAIJ. C will be of type MATSEQAIJ. The product is computed using 8276 this (i,j) structure by calling MatPtAPNumeric(). 8277 8278 Level: intermediate 8279 8280 .seealso: MatPtAP(), MatPtAPNumeric(), MatMatMultSymbolic() 8281 @*/ 8282 PetscErrorCode MatPtAPSymbolic(Mat A,Mat P,PetscReal fill,Mat *C) 8283 { 8284 PetscErrorCode ierr; 8285 8286 PetscFunctionBegin; 8287 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8288 PetscValidType(A,1); 8289 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8290 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8291 if (fill <1.0) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Expected fill=%G must be >= 1.0",fill); 8292 PetscValidHeaderSpecific(P,MAT_CLASSID,2); 8293 PetscValidType(P,2); 8294 MatCheckPreallocated(P,2); 8295 if (!P->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8296 if (P->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8297 PetscValidPointer(C,3); 8298 8299 if (P->rmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",P->rmap->N,A->cmap->N); 8300 if (A->rmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix 'A' must be square, %D != %D",A->rmap->N,A->cmap->N); 8301 MatCheckPreallocated(A,1); 8302 ierr = PetscLogEventBegin(MAT_PtAPSymbolic,A,P,0,0);CHKERRQ(ierr); 8303 ierr = (*A->ops->ptapsymbolic)(A,P,fill,C);CHKERRQ(ierr); 8304 ierr = PetscLogEventEnd(MAT_PtAPSymbolic,A,P,0,0);CHKERRQ(ierr); 8305 8306 /* ierr = MatSetBlockSize(*C,A->rmap->bs);CHKERRQ(ierr); NO! this is not always true -ma */ 8307 PetscFunctionReturn(0); 8308 } 8309 8310 #undef __FUNCT__ 8311 #define __FUNCT__ "MatRARt" 8312 /*@ 8313 MatRARt - Creates the matrix product C = R * A * R^T 8314 8315 Neighbor-wise Collective on Mat 8316 8317 Input Parameters: 8318 + A - the matrix 8319 . R - the projection matrix 8320 . scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 8321 - fill - expected fill as ratio of nnz(C)/nnz(A) 8322 8323 Output Parameters: 8324 . C - the product matrix 8325 8326 Notes: 8327 C will be created and must be destroyed by the user with MatDestroy(). 8328 8329 This routine is currently only implemented for pairs of AIJ matrices and classes 8330 which inherit from AIJ. 8331 8332 Level: intermediate 8333 8334 .seealso: MatRARtSymbolic(), MatRARtNumeric(), MatMatMult(), MatPtAP() 8335 @*/ 8336 PetscErrorCode MatRARt(Mat A,Mat R,MatReuse scall,PetscReal fill,Mat *C) 8337 { 8338 PetscErrorCode ierr; 8339 8340 PetscFunctionBegin; 8341 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8342 PetscValidType(A,1); 8343 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8344 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8345 PetscValidHeaderSpecific(R,MAT_CLASSID,2); 8346 PetscValidType(R,2); 8347 MatCheckPreallocated(R,2); 8348 if (!R->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8349 if (R->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8350 PetscValidPointer(C,3); 8351 if (R->cmap->N!=A->rmap->N) SETERRQ2(PetscObjectComm((PetscObject)R),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",R->cmap->N,A->rmap->N); 8352 if (fill < 1.0) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Expected fill=%G must be >= 1.0",fill); 8353 MatCheckPreallocated(A,1); 8354 8355 if (!A->ops->rart) { 8356 MatType mattype; 8357 ierr = MatGetType(A,&mattype);CHKERRQ(ierr); 8358 SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"Matrix of type <%s> does not support RARt",mattype); 8359 } 8360 ierr = PetscLogEventBegin(MAT_RARt,A,R,0,0);CHKERRQ(ierr); 8361 ierr = (*A->ops->rart)(A,R,scall,fill,C);CHKERRQ(ierr); 8362 ierr = PetscLogEventEnd(MAT_RARt,A,R,0,0);CHKERRQ(ierr); 8363 PetscFunctionReturn(0); 8364 } 8365 8366 #undef __FUNCT__ 8367 #define __FUNCT__ "MatRARtNumeric" 8368 /*@ 8369 MatRARtNumeric - Computes the matrix product C = R * A * R^T 8370 8371 Neighbor-wise Collective on Mat 8372 8373 Input Parameters: 8374 + A - the matrix 8375 - R - the projection matrix 8376 8377 Output Parameters: 8378 . C - the product matrix 8379 8380 Notes: 8381 C must have been created by calling MatRARtSymbolic and must be destroyed by 8382 the user using MatDeatroy(). 8383 8384 This routine is currently only implemented for pairs of AIJ matrices and classes 8385 which inherit from AIJ. C will be of type MATAIJ. 8386 8387 Level: intermediate 8388 8389 .seealso: MatRARt(), MatRARtSymbolic(), MatMatMultNumeric() 8390 @*/ 8391 PetscErrorCode MatRARtNumeric(Mat A,Mat R,Mat C) 8392 { 8393 PetscErrorCode ierr; 8394 8395 PetscFunctionBegin; 8396 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8397 PetscValidType(A,1); 8398 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8399 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8400 PetscValidHeaderSpecific(R,MAT_CLASSID,2); 8401 PetscValidType(R,2); 8402 MatCheckPreallocated(R,2); 8403 if (!R->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8404 if (R->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8405 PetscValidHeaderSpecific(C,MAT_CLASSID,3); 8406 PetscValidType(C,3); 8407 MatCheckPreallocated(C,3); 8408 if (C->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8409 if (R->rmap->N!=C->rmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",R->rmap->N,C->rmap->N); 8410 if (R->cmap->N!=A->rmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",R->cmap->N,A->rmap->N); 8411 if (A->rmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix 'A' must be square, %D != %D",A->rmap->N,A->cmap->N); 8412 if (R->rmap->N!=C->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",R->rmap->N,C->cmap->N); 8413 MatCheckPreallocated(A,1); 8414 8415 ierr = PetscLogEventBegin(MAT_RARtNumeric,A,R,0,0);CHKERRQ(ierr); 8416 ierr = (*A->ops->rartnumeric)(A,R,C);CHKERRQ(ierr); 8417 ierr = PetscLogEventEnd(MAT_RARtNumeric,A,R,0,0);CHKERRQ(ierr); 8418 PetscFunctionReturn(0); 8419 } 8420 8421 #undef __FUNCT__ 8422 #define __FUNCT__ "MatRARtSymbolic" 8423 /*@ 8424 MatRARtSymbolic - Creates the (i,j) structure of the matrix product C = R * A * R^T 8425 8426 Neighbor-wise Collective on Mat 8427 8428 Input Parameters: 8429 + A - the matrix 8430 - R - the projection matrix 8431 8432 Output Parameters: 8433 . C - the (i,j) structure of the product matrix 8434 8435 Notes: 8436 C will be created and must be destroyed by the user with MatDestroy(). 8437 8438 This routine is currently only implemented for pairs of SeqAIJ matrices and classes 8439 which inherit from SeqAIJ. C will be of type MATSEQAIJ. The product is computed using 8440 this (i,j) structure by calling MatRARtNumeric(). 8441 8442 Level: intermediate 8443 8444 .seealso: MatRARt(), MatRARtNumeric(), MatMatMultSymbolic() 8445 @*/ 8446 PetscErrorCode MatRARtSymbolic(Mat A,Mat R,PetscReal fill,Mat *C) 8447 { 8448 PetscErrorCode ierr; 8449 8450 PetscFunctionBegin; 8451 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8452 PetscValidType(A,1); 8453 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8454 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8455 if (fill <1.0) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Expected fill=%G must be >= 1.0",fill); 8456 PetscValidHeaderSpecific(R,MAT_CLASSID,2); 8457 PetscValidType(R,2); 8458 MatCheckPreallocated(R,2); 8459 if (!R->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8460 if (R->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8461 PetscValidPointer(C,3); 8462 8463 if (R->cmap->N!=A->rmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",R->cmap->N,A->rmap->N); 8464 if (A->rmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix 'A' must be square, %D != %D",A->rmap->N,A->cmap->N); 8465 MatCheckPreallocated(A,1); 8466 ierr = PetscLogEventBegin(MAT_RARtSymbolic,A,R,0,0);CHKERRQ(ierr); 8467 ierr = (*A->ops->rartsymbolic)(A,R,fill,C);CHKERRQ(ierr); 8468 ierr = PetscLogEventEnd(MAT_RARtSymbolic,A,R,0,0);CHKERRQ(ierr); 8469 8470 ierr = MatSetBlockSize(*C,A->rmap->bs);CHKERRQ(ierr); 8471 PetscFunctionReturn(0); 8472 } 8473 8474 #undef __FUNCT__ 8475 #define __FUNCT__ "MatMatMult" 8476 /*@ 8477 MatMatMult - Performs Matrix-Matrix Multiplication C=A*B. 8478 8479 Neighbor-wise Collective on Mat 8480 8481 Input Parameters: 8482 + A - the left matrix 8483 . B - the right matrix 8484 . scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 8485 - fill - expected fill as ratio of nnz(C)/(nnz(A) + nnz(B)), use PETSC_DEFAULT if you do not have a good estimate 8486 if the result is a dense matrix this is irrelevent 8487 8488 Output Parameters: 8489 . C - the product matrix 8490 8491 Notes: 8492 Unless scall is MAT_REUSE_MATRIX C will be created. 8493 8494 MAT_REUSE_MATRIX can only be used if the matrices A and B have the same nonzero pattern as in the previous call 8495 8496 To determine the correct fill value, run with -info and search for the string "Fill ratio" to see the value 8497 actually needed. 8498 8499 If you have many matrices with the same non-zero structure to multiply, you 8500 should either 8501 $ 1) use MAT_REUSE_MATRIX in all calls but the first or 8502 $ 2) call MatMatMultSymbolic() once and then MatMatMultNumeric() for each product needed 8503 8504 Level: intermediate 8505 8506 .seealso: MatMatMultSymbolic(), MatMatMultNumeric(), MatTransposeMatMult(), MatMatTransposeMult(), MatPtAP() 8507 @*/ 8508 PetscErrorCode MatMatMult(Mat A,Mat B,MatReuse scall,PetscReal fill,Mat *C) 8509 { 8510 PetscErrorCode ierr; 8511 PetscErrorCode (*fA)(Mat,Mat,MatReuse,PetscReal,Mat*); 8512 PetscErrorCode (*fB)(Mat,Mat,MatReuse,PetscReal,Mat*); 8513 PetscErrorCode (*mult)(Mat,Mat,MatReuse,PetscReal,Mat*)=NULL; 8514 8515 PetscFunctionBegin; 8516 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8517 PetscValidType(A,1); 8518 MatCheckPreallocated(A,1); 8519 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8520 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8521 PetscValidHeaderSpecific(B,MAT_CLASSID,2); 8522 PetscValidType(B,2); 8523 MatCheckPreallocated(B,2); 8524 if (!B->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8525 if (B->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8526 PetscValidPointer(C,3); 8527 if (B->rmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",B->rmap->N,A->cmap->N); 8528 if (scall == MAT_REUSE_MATRIX) { 8529 PetscValidPointer(*C,5); 8530 PetscValidHeaderSpecific(*C,MAT_CLASSID,5); 8531 ierr = PetscLogEventBegin(MAT_MatMultNumeric,A,B,0,0);CHKERRQ(ierr); 8532 ierr = (*(*C)->ops->matmultnumeric)(A,B,*C);CHKERRQ(ierr); 8533 ierr = PetscLogEventEnd(MAT_MatMultNumeric,A,B,0,0);CHKERRQ(ierr); 8534 PetscFunctionReturn(0); 8535 } 8536 if (fill == PETSC_DEFAULT || fill == PETSC_DECIDE) fill = 2.0; 8537 if (fill < 1.0) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Expected fill=%G must be >= 1.0",fill); 8538 8539 fA = A->ops->matmult; 8540 fB = B->ops->matmult; 8541 if (fB == fA) { 8542 if (!fB) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"MatMatMult not supported for B of type %s",((PetscObject)B)->type_name); 8543 mult = fB; 8544 } else { 8545 /* dispatch based on the type of A and B from their PetscObject's PetscFunctionLists. */ 8546 char multname[256]; 8547 ierr = PetscStrcpy(multname,"MatMatMult_");CHKERRQ(ierr); 8548 ierr = PetscStrcat(multname,((PetscObject)A)->type_name);CHKERRQ(ierr); 8549 ierr = PetscStrcat(multname,"_");CHKERRQ(ierr); 8550 ierr = PetscStrcat(multname,((PetscObject)B)->type_name);CHKERRQ(ierr); 8551 ierr = PetscStrcat(multname,"_C");CHKERRQ(ierr); /* e.g., multname = "MatMatMult_seqdense_seqaij_C" */ 8552 ierr = PetscObjectQueryFunction((PetscObject)B,multname,(void (**)(void))&mult);CHKERRQ(ierr); 8553 if (!mult) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_INCOMP,"MatMatMult requires A, %s, to be compatible with B, %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name); 8554 } 8555 ierr = PetscLogEventBegin(MAT_MatMult,A,B,0,0);CHKERRQ(ierr); 8556 ierr = (*mult)(A,B,scall,fill,C);CHKERRQ(ierr); 8557 ierr = PetscLogEventEnd(MAT_MatMult,A,B,0,0);CHKERRQ(ierr); 8558 PetscFunctionReturn(0); 8559 } 8560 8561 #undef __FUNCT__ 8562 #define __FUNCT__ "MatMatMultSymbolic" 8563 /*@ 8564 MatMatMultSymbolic - Performs construction, preallocation, and computes the ij structure 8565 of the matrix-matrix product C=A*B. Call this routine before calling MatMatMultNumeric(). 8566 8567 Neighbor-wise Collective on Mat 8568 8569 Input Parameters: 8570 + A - the left matrix 8571 . B - the right matrix 8572 - fill - expected fill as ratio of nnz(C)/(nnz(A) + nnz(B)), use PETSC_DEFAULT if you do not have a good estimate, 8573 if C is a dense matrix this is irrelevent 8574 8575 Output Parameters: 8576 . C - the product matrix 8577 8578 Notes: 8579 Unless scall is MAT_REUSE_MATRIX C will be created. 8580 8581 To determine the correct fill value, run with -info and search for the string "Fill ratio" to see the value 8582 actually needed. 8583 8584 This routine is currently implemented for 8585 - pairs of AIJ matrices and classes which inherit from AIJ, C will be of type AIJ 8586 - pairs of AIJ (A) and Dense (B) matrix, C will be of type Dense. 8587 - pairs of Dense (A) and AIJ (B) matrix, C will be of type Dense. 8588 8589 Level: intermediate 8590 8591 Developers Note: There are ways to estimate the number of nonzeros in the resulting product, see for example, http://arxiv.org/abs/1006.4173 8592 We should incorporate them into PETSc. 8593 8594 .seealso: MatMatMult(), MatMatMultNumeric() 8595 @*/ 8596 PetscErrorCode MatMatMultSymbolic(Mat A,Mat B,PetscReal fill,Mat *C) 8597 { 8598 PetscErrorCode ierr; 8599 PetscErrorCode (*Asymbolic)(Mat,Mat,PetscReal,Mat*); 8600 PetscErrorCode (*Bsymbolic)(Mat,Mat,PetscReal,Mat*); 8601 PetscErrorCode (*symbolic)(Mat,Mat,PetscReal,Mat*)=NULL; 8602 8603 PetscFunctionBegin; 8604 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8605 PetscValidType(A,1); 8606 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8607 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8608 8609 PetscValidHeaderSpecific(B,MAT_CLASSID,2); 8610 PetscValidType(B,2); 8611 MatCheckPreallocated(B,2); 8612 if (!B->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8613 if (B->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8614 PetscValidPointer(C,3); 8615 8616 if (B->rmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",B->rmap->N,A->cmap->N); 8617 if (fill == PETSC_DEFAULT) fill = 2.0; 8618 if (fill < 1.0) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Expected fill=%G must be > 1.0",fill); 8619 MatCheckPreallocated(A,1); 8620 8621 Asymbolic = A->ops->matmultsymbolic; 8622 Bsymbolic = B->ops->matmultsymbolic; 8623 if (Asymbolic == Bsymbolic) { 8624 if (!Bsymbolic) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"C=A*B not implemented for B of type %s",((PetscObject)B)->type_name); 8625 symbolic = Bsymbolic; 8626 } else { /* dispatch based on the type of A and B */ 8627 char symbolicname[256]; 8628 ierr = PetscStrcpy(symbolicname,"MatMatMultSymbolic_");CHKERRQ(ierr); 8629 ierr = PetscStrcat(symbolicname,((PetscObject)A)->type_name);CHKERRQ(ierr); 8630 ierr = PetscStrcat(symbolicname,"_");CHKERRQ(ierr); 8631 ierr = PetscStrcat(symbolicname,((PetscObject)B)->type_name);CHKERRQ(ierr); 8632 ierr = PetscStrcat(symbolicname,"_C");CHKERRQ(ierr); 8633 ierr = PetscObjectQueryFunction((PetscObject)B,symbolicname,(void (**)(void))&symbolic);CHKERRQ(ierr); 8634 if (!symbolic) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_INCOMP,"MatMatMultSymbolic requires A, %s, to be compatible with B, %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name); 8635 } 8636 ierr = PetscLogEventBegin(MAT_MatMultSymbolic,A,B,0,0);CHKERRQ(ierr); 8637 ierr = (*symbolic)(A,B,fill,C);CHKERRQ(ierr); 8638 ierr = PetscLogEventEnd(MAT_MatMultSymbolic,A,B,0,0);CHKERRQ(ierr); 8639 PetscFunctionReturn(0); 8640 } 8641 8642 #undef __FUNCT__ 8643 #define __FUNCT__ "MatMatMultNumeric" 8644 /*@ 8645 MatMatMultNumeric - Performs the numeric matrix-matrix product. 8646 Call this routine after first calling MatMatMultSymbolic(). 8647 8648 Neighbor-wise Collective on Mat 8649 8650 Input Parameters: 8651 + A - the left matrix 8652 - B - the right matrix 8653 8654 Output Parameters: 8655 . C - the product matrix, which was created by from MatMatMultSymbolic() or a call to MatMatMult(). 8656 8657 Notes: 8658 C must have been created with MatMatMultSymbolic(). 8659 8660 This routine is currently implemented for 8661 - pairs of AIJ matrices and classes which inherit from AIJ, C will be of type MATAIJ. 8662 - pairs of AIJ (A) and Dense (B) matrix, C will be of type Dense. 8663 - pairs of Dense (A) and AIJ (B) matrix, C will be of type Dense. 8664 8665 Level: intermediate 8666 8667 .seealso: MatMatMult(), MatMatMultSymbolic() 8668 @*/ 8669 PetscErrorCode MatMatMultNumeric(Mat A,Mat B,Mat C) 8670 { 8671 PetscErrorCode ierr; 8672 8673 PetscFunctionBegin; 8674 ierr = MatMatMult(A,B,MAT_REUSE_MATRIX,0.0,&C);CHKERRQ(ierr); 8675 PetscFunctionReturn(0); 8676 } 8677 8678 #undef __FUNCT__ 8679 #define __FUNCT__ "MatMatTransposeMult" 8680 /*@ 8681 MatMatTransposeMult - Performs Matrix-Matrix Multiplication C=A*B^T. 8682 8683 Neighbor-wise Collective on Mat 8684 8685 Input Parameters: 8686 + A - the left matrix 8687 . B - the right matrix 8688 . scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 8689 - fill - expected fill as ratio of nnz(C)/(nnz(A) + nnz(B)), use PETSC_DEFAULT if not known 8690 8691 Output Parameters: 8692 . C - the product matrix 8693 8694 Notes: 8695 C will be created if MAT_INITIAL_MATRIX and must be destroyed by the user with MatDestroy(). 8696 8697 MAT_REUSE_MATRIX can only be used if the matrices A and B have the same nonzero pattern as in the previous call 8698 8699 To determine the correct fill value, run with -info and search for the string "Fill ratio" to see the value 8700 actually needed. 8701 8702 This routine is currently only implemented for pairs of SeqAIJ matrices. C will be of type MATSEQAIJ. 8703 8704 Level: intermediate 8705 8706 .seealso: MatMatTransposeMultSymbolic(), MatMatTransposeMultNumeric(), MatMatMult(), MatTransposeMatMult() MatPtAP() 8707 @*/ 8708 PetscErrorCode MatMatTransposeMult(Mat A,Mat B,MatReuse scall,PetscReal fill,Mat *C) 8709 { 8710 PetscErrorCode ierr; 8711 PetscErrorCode (*fA)(Mat,Mat,MatReuse,PetscReal,Mat*); 8712 PetscErrorCode (*fB)(Mat,Mat,MatReuse,PetscReal,Mat*); 8713 8714 PetscFunctionBegin; 8715 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8716 PetscValidType(A,1); 8717 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8718 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8719 PetscValidHeaderSpecific(B,MAT_CLASSID,2); 8720 PetscValidType(B,2); 8721 MatCheckPreallocated(B,2); 8722 if (!B->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8723 if (B->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8724 PetscValidPointer(C,3); 8725 if (B->cmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, AN %D != BN %D",A->cmap->N,B->cmap->N); 8726 if (fill == PETSC_DEFAULT || fill == PETSC_DECIDE) fill = 2.0; 8727 if (fill < 1.0) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Expected fill=%G must be > 1.0",fill); 8728 MatCheckPreallocated(A,1); 8729 8730 fA = A->ops->mattransposemult; 8731 if (!fA) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"MatMatTransposeMult not supported for A of type %s",((PetscObject)A)->type_name); 8732 fB = B->ops->mattransposemult; 8733 if (!fB) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"MatMatTransposeMult not supported for B of type %s",((PetscObject)B)->type_name); 8734 if (fB!=fA) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_INCOMP,"MatMatTransposeMult requires A, %s, to be compatible with B, %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name); 8735 8736 if (scall == MAT_INITIAL_MATRIX) { 8737 ierr = PetscLogEventBegin(MAT_MatTransposeMultSymbolic,A,B,0,0);CHKERRQ(ierr); 8738 ierr = (*A->ops->mattransposemultsymbolic)(A,B,fill,C);CHKERRQ(ierr); 8739 ierr = PetscLogEventEnd(MAT_MatTransposeMultSymbolic,A,B,0,0);CHKERRQ(ierr); 8740 } 8741 ierr = PetscLogEventBegin(MAT_MatTransposeMultNumeric,A,B,0,0);CHKERRQ(ierr); 8742 ierr = (*A->ops->mattransposemultnumeric)(A,B,*C);CHKERRQ(ierr); 8743 ierr = PetscLogEventEnd(MAT_MatTransposeMultNumeric,A,B,0,0);CHKERRQ(ierr); 8744 PetscFunctionReturn(0); 8745 } 8746 8747 #undef __FUNCT__ 8748 #define __FUNCT__ "MatTransposeMatMult" 8749 /*@ 8750 MatTransposeMatMult - Performs Matrix-Matrix Multiplication C=A^T*B. 8751 8752 Neighbor-wise Collective on Mat 8753 8754 Input Parameters: 8755 + A - the left matrix 8756 . B - the right matrix 8757 . scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 8758 - fill - expected fill as ratio of nnz(C)/(nnz(A) + nnz(B)), use PETSC_DEFAULT if not known 8759 8760 Output Parameters: 8761 . C - the product matrix 8762 8763 Notes: 8764 C will be created if MAT_INITIAL_MATRIX and must be destroyed by the user with MatDestroy(). 8765 8766 MAT_REUSE_MATRIX can only be used if the matrices A and B have the same nonzero pattern as in the previous call 8767 8768 To determine the correct fill value, run with -info and search for the string "Fill ratio" to see the value 8769 actually needed. 8770 8771 This routine is currently implemented for pairs of AIJ matrices and pairs of SeqDense matrices and classes 8772 which inherit from SeqAIJ. C will be of same type as the input matrices. 8773 8774 Level: intermediate 8775 8776 .seealso: MatTransposeMatMultSymbolic(), MatTransposeMatMultNumeric(), MatMatMult(), MatMatTransposeMult(), MatPtAP() 8777 @*/ 8778 PetscErrorCode MatTransposeMatMult(Mat A,Mat B,MatReuse scall,PetscReal fill,Mat *C) 8779 { 8780 PetscErrorCode ierr; 8781 PetscErrorCode (*fA)(Mat,Mat,MatReuse,PetscReal,Mat*); 8782 PetscErrorCode (*fB)(Mat,Mat,MatReuse,PetscReal,Mat*); 8783 PetscErrorCode (*transposematmult)(Mat,Mat,MatReuse,PetscReal,Mat*) = NULL; 8784 8785 PetscFunctionBegin; 8786 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8787 PetscValidType(A,1); 8788 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8789 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8790 PetscValidHeaderSpecific(B,MAT_CLASSID,2); 8791 PetscValidType(B,2); 8792 MatCheckPreallocated(B,2); 8793 if (!B->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8794 if (B->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8795 PetscValidPointer(C,3); 8796 if (B->rmap->N!=A->rmap->N) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",B->rmap->N,A->rmap->N); 8797 if (fill == PETSC_DEFAULT || fill == PETSC_DECIDE) fill = 2.0; 8798 if (fill < 1.0) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Expected fill=%G must be > 1.0",fill); 8799 MatCheckPreallocated(A,1); 8800 8801 fA = A->ops->transposematmult; 8802 if (!fA) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"MatTransposeMatMult not supported for A of type %s",((PetscObject)A)->type_name); 8803 fB = B->ops->transposematmult; 8804 if (!fB) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"MatTransposeMatMult not supported for B of type %s",((PetscObject)B)->type_name); 8805 if (fB==fA) { 8806 transposematmult = fA; 8807 } 8808 if (!transposematmult) SETERRQ2(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_INCOMP,"MatTransposeMatMult requires A, %s, to be compatible with B, %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name); 8809 ierr = PetscLogEventBegin(MAT_TransposeMatMult,A,B,0,0);CHKERRQ(ierr); 8810 ierr = (*transposematmult)(A,B,scall,fill,C);CHKERRQ(ierr); 8811 ierr = PetscLogEventEnd(MAT_TransposeMatMult,A,B,0,0);CHKERRQ(ierr); 8812 PetscFunctionReturn(0); 8813 } 8814 8815 #undef __FUNCT__ 8816 #define __FUNCT__ "MatMatMatMult" 8817 /*@ 8818 MatMatMatMult - Performs Matrix-Matrix-Matrix Multiplication D=A*B*C. 8819 8820 Neighbor-wise Collective on Mat 8821 8822 Input Parameters: 8823 + A - the left matrix 8824 . B - the middle matrix 8825 . C - the right matrix 8826 . scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 8827 - fill - expected fill as ratio of nnz(D)/(nnz(A) + nnz(B)+nnz(C)), use PETSC_DEFAULT if you do not have a good estimate 8828 if the result is a dense matrix this is irrelevent 8829 8830 Output Parameters: 8831 . D - the product matrix 8832 8833 Notes: 8834 Unless scall is MAT_REUSE_MATRIX D will be created. 8835 8836 MAT_REUSE_MATRIX can only be used if the matrices A, B and C have the same nonzero pattern as in the previous call 8837 8838 To determine the correct fill value, run with -info and search for the string "Fill ratio" to see the value 8839 actually needed. 8840 8841 If you have many matrices with the same non-zero structure to multiply, you 8842 should either 8843 $ 1) use MAT_REUSE_MATRIX in all calls but the first or 8844 $ 2) call MatMatMatMultSymbolic() once and then MatMatMatMultNumeric() for each product needed 8845 8846 Level: intermediate 8847 8848 .seealso: MatMatMult, MatPtAP() 8849 @*/ 8850 PetscErrorCode MatMatMatMult(Mat A,Mat B,Mat C,MatReuse scall,PetscReal fill,Mat *D) 8851 { 8852 PetscErrorCode ierr; 8853 PetscErrorCode (*fA)(Mat,Mat,Mat,MatReuse,PetscReal,Mat*); 8854 PetscErrorCode (*fB)(Mat,Mat,Mat,MatReuse,PetscReal,Mat*); 8855 PetscErrorCode (*fC)(Mat,Mat,Mat,MatReuse,PetscReal,Mat*); 8856 PetscErrorCode (*mult)(Mat,Mat,Mat,MatReuse,PetscReal,Mat*)=NULL; 8857 8858 PetscFunctionBegin; 8859 PetscValidHeaderSpecific(A,MAT_CLASSID,1); 8860 PetscValidType(A,1); 8861 MatCheckPreallocated(A,1); 8862 if (!A->assembled) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8863 if (A->factortype) SETERRQ(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8864 PetscValidHeaderSpecific(B,MAT_CLASSID,2); 8865 PetscValidType(B,2); 8866 MatCheckPreallocated(B,2); 8867 if (!B->assembled) SETERRQ(PetscObjectComm((PetscObject)B),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8868 if (B->factortype) SETERRQ(PetscObjectComm((PetscObject)B),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8869 PetscValidHeaderSpecific(C,MAT_CLASSID,3); 8870 PetscValidPointer(C,3); 8871 MatCheckPreallocated(C,3); 8872 if (!C->assembled) SETERRQ(PetscObjectComm((PetscObject)C),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8873 if (C->factortype) SETERRQ(PetscObjectComm((PetscObject)C),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8874 if (B->rmap->N!=A->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)B),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",B->rmap->N,A->cmap->N); 8875 if (C->rmap->N!=B->cmap->N) SETERRQ2(PetscObjectComm((PetscObject)C),PETSC_ERR_ARG_SIZ,"Matrix dimensions are incompatible, %D != %D",C->rmap->N,B->cmap->N); 8876 if (scall == MAT_REUSE_MATRIX) { 8877 PetscValidPointer(*D,6); 8878 PetscValidHeaderSpecific(*D,MAT_CLASSID,6); 8879 ierr = PetscLogEventBegin(MAT_MatMatMult,A,B,0,0);CHKERRQ(ierr); 8880 ierr = (*(*D)->ops->matmatmult)(A,B,C,scall,fill,D);CHKERRQ(ierr); 8881 ierr = PetscLogEventEnd(MAT_MatMatMult,A,B,0,0);CHKERRQ(ierr); 8882 PetscFunctionReturn(0); 8883 } 8884 if (fill == PETSC_DEFAULT || fill == PETSC_DECIDE) fill = 2.0; 8885 if (fill < 1.0) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_SIZ,"Expected fill=%G must be >= 1.0",fill); 8886 8887 fA = A->ops->matmatmult; 8888 fB = B->ops->matmatmult; 8889 fC = C->ops->matmatmult; 8890 if (fA == fB && fA == fC) { 8891 if (!fA) SETERRQ1(PetscObjectComm((PetscObject)A),PETSC_ERR_SUP,"MatMatMatMult not supported for A of type %s",((PetscObject)A)->type_name); 8892 mult = fA; 8893 } else { 8894 /* dispatch based on the type of A, B and C from their PetscObject's PetscFunctionLists. */ 8895 char multname[256]; 8896 ierr = PetscStrcpy(multname,"MatMatMatMult_");CHKERRQ(ierr); 8897 ierr = PetscStrcat(multname,((PetscObject)A)->type_name);CHKERRQ(ierr); 8898 ierr = PetscStrcat(multname,"_");CHKERRQ(ierr); 8899 ierr = PetscStrcat(multname,((PetscObject)B)->type_name);CHKERRQ(ierr); 8900 ierr = PetscStrcat(multname,"_");CHKERRQ(ierr); 8901 ierr = PetscStrcat(multname,((PetscObject)C)->type_name);CHKERRQ(ierr); 8902 ierr = PetscStrcat(multname,"_C");CHKERRQ(ierr); 8903 ierr = PetscObjectQueryFunction((PetscObject)B,multname,(void (**)(void))&mult);CHKERRQ(ierr); 8904 if (!mult) SETERRQ3(PetscObjectComm((PetscObject)A),PETSC_ERR_ARG_INCOMP,"MatMatMatMult requires A, %s, to be compatible with B, %s, C, %s",((PetscObject)A)->type_name,((PetscObject)B)->type_name,((PetscObject)C)->type_name); 8905 } 8906 ierr = PetscLogEventBegin(MAT_MatMatMult,A,B,0,0);CHKERRQ(ierr); 8907 ierr = (*mult)(A,B,C,scall,fill,D);CHKERRQ(ierr); 8908 ierr = PetscLogEventEnd(MAT_MatMatMult,A,B,0,0);CHKERRQ(ierr); 8909 PetscFunctionReturn(0); 8910 } 8911 8912 #undef __FUNCT__ 8913 #define __FUNCT__ "MatGetRedundantMatrix" 8914 /*@C 8915 MatGetRedundantMatrix - Create redundant matrices and put them into processors of subcommunicators. 8916 8917 Collective on Mat 8918 8919 Input Parameters: 8920 + mat - the matrix 8921 . nsubcomm - the number of subcommunicators (= number of redundant parallel or sequential matrices) 8922 . subcomm - MPI communicator split from the communicator where mat resides in 8923 . mlocal_red - number of local rows of the redundant matrix 8924 - reuse - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 8925 8926 Output Parameter: 8927 . matredundant - redundant matrix 8928 8929 Notes: 8930 MAT_REUSE_MATRIX can only be used when the nonzero structure of the 8931 original matrix has not changed from that last call to MatGetRedundantMatrix(). 8932 8933 This routine creates the duplicated matrices in subcommunicators; you should NOT create them before 8934 calling it. 8935 8936 Only MPIAIJ matrix is supported. 8937 8938 Level: advanced 8939 8940 Concepts: subcommunicator 8941 Concepts: duplicate matrix 8942 8943 .seealso: MatDestroy() 8944 @*/ 8945 PetscErrorCode MatGetRedundantMatrix(Mat mat,PetscInt nsubcomm,MPI_Comm subcomm,PetscInt mlocal_red,MatReuse reuse,Mat *matredundant) 8946 { 8947 PetscErrorCode ierr; 8948 8949 PetscFunctionBegin; 8950 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 8951 if (nsubcomm && reuse == MAT_REUSE_MATRIX) { 8952 PetscValidPointer(*matredundant,6); 8953 PetscValidHeaderSpecific(*matredundant,MAT_CLASSID,6); 8954 } 8955 if (!mat->ops->getredundantmatrix) SETERRQ1(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Mat type %s",((PetscObject)mat)->type_name); 8956 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 8957 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 8958 MatCheckPreallocated(mat,1); 8959 8960 ierr = PetscLogEventBegin(MAT_GetRedundantMatrix,mat,0,0,0);CHKERRQ(ierr); 8961 ierr = (*mat->ops->getredundantmatrix)(mat,nsubcomm,subcomm,mlocal_red,reuse,matredundant);CHKERRQ(ierr); 8962 ierr = PetscLogEventEnd(MAT_GetRedundantMatrix,mat,0,0,0);CHKERRQ(ierr); 8963 PetscFunctionReturn(0); 8964 } 8965 8966 #undef __FUNCT__ 8967 #define __FUNCT__ "MatGetMultiProcBlock" 8968 /*@C 8969 MatGetMultiProcBlock - Create multiple [bjacobi] 'parallel submatrices' from 8970 a given 'mat' object. Each submatrix can span multiple procs. 8971 8972 Collective on Mat 8973 8974 Input Parameters: 8975 + mat - the matrix 8976 . subcomm - the subcommunicator obtained by com_split(comm) 8977 - scall - either MAT_INITIAL_MATRIX or MAT_REUSE_MATRIX 8978 8979 Output Parameter: 8980 . subMat - 'parallel submatrices each spans a given subcomm 8981 8982 Notes: 8983 The submatrix partition across processors is dicated by 'subComm' a 8984 communicator obtained by com_split(comm). The comm_split 8985 is not restriced to be grouped with consequitive original ranks. 8986 8987 Due the comm_split() usage, the parallel layout of the submatrices 8988 map directly to the layout of the original matrix [wrt the local 8989 row,col partitioning]. So the original 'DiagonalMat' naturally maps 8990 into the 'DiagonalMat' of the subMat, hence it is used directly from 8991 the subMat. However the offDiagMat looses some columns - and this is 8992 reconstructed with MatSetValues() 8993 8994 Level: advanced 8995 8996 Concepts: subcommunicator 8997 Concepts: submatrices 8998 8999 .seealso: MatGetSubMatrices() 9000 @*/ 9001 PetscErrorCode MatGetMultiProcBlock(Mat mat, MPI_Comm subComm, MatReuse scall,Mat *subMat) 9002 { 9003 PetscErrorCode ierr; 9004 PetscMPIInt commsize,subCommSize; 9005 9006 PetscFunctionBegin; 9007 ierr = MPI_Comm_size(PetscObjectComm((PetscObject)mat),&commsize);CHKERRQ(ierr); 9008 ierr = MPI_Comm_size(subComm,&subCommSize);CHKERRQ(ierr); 9009 if (subCommSize > commsize) SETERRQ2(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_OUTOFRANGE,"CommSize %D < SubCommZize %D",commsize,subCommSize); 9010 9011 ierr = PetscLogEventBegin(MAT_GetMultiProcBlock,mat,0,0,0);CHKERRQ(ierr); 9012 ierr = (*mat->ops->getmultiprocblock)(mat,subComm,scall,subMat);CHKERRQ(ierr); 9013 ierr = PetscLogEventEnd(MAT_GetMultiProcBlock,mat,0,0,0);CHKERRQ(ierr); 9014 PetscFunctionReturn(0); 9015 } 9016 9017 #undef __FUNCT__ 9018 #define __FUNCT__ "MatGetLocalSubMatrix" 9019 /*@ 9020 MatGetLocalSubMatrix - Gets a reference to a submatrix specified in local numbering 9021 9022 Not Collective 9023 9024 Input Arguments: 9025 mat - matrix to extract local submatrix from 9026 isrow - local row indices for submatrix 9027 iscol - local column indices for submatrix 9028 9029 Output Arguments: 9030 submat - the submatrix 9031 9032 Level: intermediate 9033 9034 Notes: 9035 The submat should be returned with MatRestoreLocalSubMatrix(). 9036 9037 Depending on the format of mat, the returned submat may not implement MatMult(). Its communicator may be 9038 the same as mat, it may be PETSC_COMM_SELF, or some other subcomm of mat's. 9039 9040 The submat always implements MatSetValuesLocal(). If isrow and iscol have the same block size, then 9041 MatSetValuesBlockedLocal() will also be implemented. 9042 9043 .seealso: MatRestoreLocalSubMatrix(), MatCreateLocalRef() 9044 @*/ 9045 PetscErrorCode MatGetLocalSubMatrix(Mat mat,IS isrow,IS iscol,Mat *submat) 9046 { 9047 PetscErrorCode ierr; 9048 9049 PetscFunctionBegin; 9050 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 9051 PetscValidHeaderSpecific(isrow,IS_CLASSID,2); 9052 PetscValidHeaderSpecific(iscol,IS_CLASSID,3); 9053 PetscCheckSameComm(isrow,2,iscol,3); 9054 PetscValidPointer(submat,4); 9055 9056 if (mat->ops->getlocalsubmatrix) { 9057 ierr = (*mat->ops->getlocalsubmatrix)(mat,isrow,iscol,submat);CHKERRQ(ierr); 9058 } else { 9059 ierr = MatCreateLocalRef(mat,isrow,iscol,submat);CHKERRQ(ierr); 9060 } 9061 PetscFunctionReturn(0); 9062 } 9063 9064 #undef __FUNCT__ 9065 #define __FUNCT__ "MatRestoreLocalSubMatrix" 9066 /*@ 9067 MatRestoreLocalSubMatrix - Restores a reference to a submatrix specified in local numbering 9068 9069 Not Collective 9070 9071 Input Arguments: 9072 mat - matrix to extract local submatrix from 9073 isrow - local row indices for submatrix 9074 iscol - local column indices for submatrix 9075 submat - the submatrix 9076 9077 Level: intermediate 9078 9079 .seealso: MatGetLocalSubMatrix() 9080 @*/ 9081 PetscErrorCode MatRestoreLocalSubMatrix(Mat mat,IS isrow,IS iscol,Mat *submat) 9082 { 9083 PetscErrorCode ierr; 9084 9085 PetscFunctionBegin; 9086 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 9087 PetscValidHeaderSpecific(isrow,IS_CLASSID,2); 9088 PetscValidHeaderSpecific(iscol,IS_CLASSID,3); 9089 PetscCheckSameComm(isrow,2,iscol,3); 9090 PetscValidPointer(submat,4); 9091 if (*submat) { 9092 PetscValidHeaderSpecific(*submat,MAT_CLASSID,4); 9093 } 9094 9095 if (mat->ops->restorelocalsubmatrix) { 9096 ierr = (*mat->ops->restorelocalsubmatrix)(mat,isrow,iscol,submat);CHKERRQ(ierr); 9097 } else { 9098 ierr = MatDestroy(submat);CHKERRQ(ierr); 9099 } 9100 *submat = NULL; 9101 PetscFunctionReturn(0); 9102 } 9103 9104 /* --------------------------------------------------------*/ 9105 #undef __FUNCT__ 9106 #define __FUNCT__ "MatFindZeroDiagonals" 9107 /*@ 9108 MatFindZeroDiagonals - Finds all the rows of a matrix that have zero or no entry in the matrix 9109 9110 Collective on Mat 9111 9112 Input Parameter: 9113 . mat - the matrix 9114 9115 Output Parameter: 9116 . is - if any rows have zero diagonals this contains the list of them 9117 9118 Level: developer 9119 9120 Concepts: matrix-vector product 9121 9122 .seealso: MatMultTranspose(), MatMultAdd(), MatMultTransposeAdd() 9123 @*/ 9124 PetscErrorCode MatFindZeroDiagonals(Mat mat,IS *is) 9125 { 9126 PetscErrorCode ierr; 9127 9128 PetscFunctionBegin; 9129 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 9130 PetscValidType(mat,1); 9131 if (!mat->assembled) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 9132 if (mat->factortype) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 9133 9134 if (!mat->ops->findzerodiagonals) SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"This matrix type does not have a find zero diagonals defined"); 9135 ierr = (*mat->ops->findzerodiagonals)(mat,is);CHKERRQ(ierr); 9136 PetscFunctionReturn(0); 9137 } 9138 9139 #undef __FUNCT__ 9140 #define __FUNCT__ "MatInvertBlockDiagonal" 9141 /*@C 9142 MatInvertBlockDiagonal - Inverts the block diagonal entries. 9143 9144 Collective on Mat 9145 9146 Input Parameters: 9147 . mat - the matrix 9148 9149 Output Parameters: 9150 . values - the block inverses in column major order (FORTRAN-like) 9151 9152 Note: 9153 This routine is not available from Fortran. 9154 9155 Level: advanced 9156 @*/ 9157 PetscErrorCode MatInvertBlockDiagonal(Mat mat,const PetscScalar **values) 9158 { 9159 PetscErrorCode ierr; 9160 9161 PetscFunctionBegin; 9162 PetscValidHeaderSpecific(mat,MAT_CLASSID,1); 9163 if (!mat->assembled) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for unassembled matrix"); 9164 if (mat->factortype) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONGSTATE,"Not for factored matrix"); 9165 if (!mat->ops->invertblockdiagonal) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_SUP,"Not supported"); 9166 ierr = (*mat->ops->invertblockdiagonal)(mat,values);CHKERRQ(ierr); 9167 PetscFunctionReturn(0); 9168 } 9169 9170 #undef __FUNCT__ 9171 #define __FUNCT__ "MatTransposeColoringDestroy" 9172 /*@C 9173 MatTransposeColoringDestroy - Destroys a coloring context for matrix product C=A*B^T that was created 9174 via MatTransposeColoringCreate(). 9175 9176 Collective on MatTransposeColoring 9177 9178 Input Parameter: 9179 . c - coloring context 9180 9181 Level: intermediate 9182 9183 .seealso: MatTransposeColoringCreate() 9184 @*/ 9185 PetscErrorCode MatTransposeColoringDestroy(MatTransposeColoring *c) 9186 { 9187 PetscErrorCode ierr; 9188 MatTransposeColoring matcolor=*c; 9189 9190 PetscFunctionBegin; 9191 if (!matcolor) PetscFunctionReturn(0); 9192 if (--((PetscObject)matcolor)->refct > 0) {matcolor = 0; PetscFunctionReturn(0);} 9193 9194 ierr = PetscFree(matcolor->ncolumns);CHKERRQ(ierr); 9195 ierr = PetscFree(matcolor->nrows);CHKERRQ(ierr); 9196 ierr = PetscFree(matcolor->colorforrow);CHKERRQ(ierr); 9197 ierr = PetscFree2(matcolor->rows,matcolor->columnsforspidx);CHKERRQ(ierr); 9198 ierr = PetscFree(matcolor->colorforcol);CHKERRQ(ierr); 9199 ierr = PetscFree(matcolor->columns);CHKERRQ(ierr); 9200 ierr = PetscHeaderDestroy(c);CHKERRQ(ierr); 9201 PetscFunctionReturn(0); 9202 } 9203 9204 #undef __FUNCT__ 9205 #define __FUNCT__ "MatTransColoringApplySpToDen" 9206 /*@C 9207 MatTransColoringApplySpToDen - Given a symbolic matrix product C=A*B^T for which 9208 a MatTransposeColoring context has been created, computes a dense B^T by Apply 9209 MatTransposeColoring to sparse B. 9210 9211 Collective on MatTransposeColoring 9212 9213 Input Parameters: 9214 + B - sparse matrix B 9215 . Btdense - symbolic dense matrix B^T 9216 - coloring - coloring context created with MatTransposeColoringCreate() 9217 9218 Output Parameter: 9219 . Btdense - dense matrix B^T 9220 9221 Options Database Keys: 9222 + -mat_transpose_coloring_view - Activates basic viewing or coloring 9223 . -mat_transpose_coloring_view_draw - Activates drawing of coloring 9224 - -mat_transpose_coloring_view_info - Activates viewing of coloring info 9225 9226 Level: intermediate 9227 9228 .seealso: MatTransposeColoringCreate(), MatTransposeColoringDestroy() 9229 9230 .keywords: coloring 9231 @*/ 9232 PetscErrorCode MatTransColoringApplySpToDen(MatTransposeColoring coloring,Mat B,Mat Btdense) 9233 { 9234 PetscErrorCode ierr; 9235 9236 PetscFunctionBegin; 9237 PetscValidHeaderSpecific(B,MAT_CLASSID,1); 9238 PetscValidHeaderSpecific(Btdense,MAT_CLASSID,2); 9239 PetscValidHeaderSpecific(coloring,MAT_TRANSPOSECOLORING_CLASSID,3); 9240 9241 if (!B->ops->transcoloringapplysptoden) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Not supported for this matrix type %s",((PetscObject)B)->type_name); 9242 ierr = (B->ops->transcoloringapplysptoden)(coloring,B,Btdense);CHKERRQ(ierr); 9243 PetscFunctionReturn(0); 9244 } 9245 9246 #undef __FUNCT__ 9247 #define __FUNCT__ "MatTransColoringApplyDenToSp" 9248 /*@C 9249 MatTransColoringApplyDenToSp - Given a symbolic matrix product Csp=A*B^T for which 9250 a MatTransposeColoring context has been created and a dense matrix Cden=A*Btdense 9251 in which Btdens is obtained from MatTransColoringApplySpToDen(), recover sparse matrix 9252 Csp from Cden. 9253 9254 Collective on MatTransposeColoring 9255 9256 Input Parameters: 9257 + coloring - coloring context created with MatTransposeColoringCreate() 9258 - Cden - matrix product of a sparse matrix and a dense matrix Btdense 9259 9260 Output Parameter: 9261 . Csp - sparse matrix 9262 9263 Options Database Keys: 9264 + -mat_multtranspose_coloring_view - Activates basic viewing or coloring 9265 . -mat_multtranspose_coloring_view_draw - Activates drawing of coloring 9266 - -mat_multtranspose_coloring_view_info - Activates viewing of coloring info 9267 9268 Level: intermediate 9269 9270 .seealso: MatTransposeColoringCreate(), MatTransposeColoringDestroy(), MatTransColoringApplySpToDen() 9271 9272 .keywords: coloring 9273 @*/ 9274 PetscErrorCode MatTransColoringApplyDenToSp(MatTransposeColoring matcoloring,Mat Cden,Mat Csp) 9275 { 9276 PetscErrorCode ierr; 9277 9278 PetscFunctionBegin; 9279 PetscValidHeaderSpecific(matcoloring,MAT_TRANSPOSECOLORING_CLASSID,1); 9280 PetscValidHeaderSpecific(Cden,MAT_CLASSID,2); 9281 PetscValidHeaderSpecific(Csp,MAT_CLASSID,3); 9282 9283 if (!Csp->ops->transcoloringapplydentosp) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_SUP,"Not supported for this matrix type %s",((PetscObject)Csp)->type_name); 9284 ierr = (Csp->ops->transcoloringapplydentosp)(matcoloring,Cden,Csp);CHKERRQ(ierr); 9285 PetscFunctionReturn(0); 9286 } 9287 9288 #undef __FUNCT__ 9289 #define __FUNCT__ "MatTransposeColoringCreate" 9290 /*@C 9291 MatTransposeColoringCreate - Creates a matrix coloring context for matrix product C=A*B^T. 9292 9293 Collective on Mat 9294 9295 Input Parameters: 9296 + mat - the matrix product C 9297 - iscoloring - the coloring of the matrix; usually obtained with MatGetColoring() or DMCreateColoring() 9298 9299 Output Parameter: 9300 . color - the new coloring context 9301 9302 Level: intermediate 9303 9304 .seealso: MatTransposeColoringDestroy(), MatTransposeColoringSetFromOptions(), MatTransColoringApplySpToDen(), 9305 MatTransColoringApplyDenToSp(), MatTransposeColoringView(), 9306 @*/ 9307 PetscErrorCode MatTransposeColoringCreate(Mat mat,ISColoring iscoloring,MatTransposeColoring *color) 9308 { 9309 MatTransposeColoring c; 9310 MPI_Comm comm; 9311 PetscErrorCode ierr; 9312 9313 PetscFunctionBegin; 9314 ierr = PetscLogEventBegin(MAT_TransposeColoringCreate,mat,0,0,0);CHKERRQ(ierr); 9315 ierr = PetscObjectGetComm((PetscObject)mat,&comm);CHKERRQ(ierr); 9316 ierr = PetscHeaderCreate(c,_p_MatTransposeColoring,int,MAT_TRANSPOSECOLORING_CLASSID,"MatTransposeColoring","Matrix product C=A*B^T via coloring","Mat",comm,MatTransposeColoringDestroy,0);CHKERRQ(ierr); 9317 9318 c->ctype = iscoloring->ctype; 9319 if (mat->ops->transposecoloringcreate) { 9320 ierr = (*mat->ops->transposecoloringcreate)(mat,iscoloring,c);CHKERRQ(ierr); 9321 } else SETERRQ(PetscObjectComm((PetscObject)mat),PETSC_ERR_SUP,"Code not yet written for this matrix type"); 9322 9323 *color = c; 9324 ierr = PetscLogEventEnd(MAT_TransposeColoringCreate,mat,0,0,0);CHKERRQ(ierr); 9325 PetscFunctionReturn(0); 9326 } 9327