1 #include <petsc-private/fortranimpl.h> 2 #include <petscmat.h> 3 4 #if defined(PETSC_HAVE_FORTRAN_CAPS) 5 #define matdestroymatrices_ MATDESTROYMATRICES 6 #define matgetfactor_ MATGETFACTOR 7 #define matfactorgetsolverpackage_ MATFACTORGETSOLVERPACKAGE 8 #define matgetrowij_ MATGETROWIJ 9 #define matrestorerowij_ MATRESTOREROWIJ 10 #define matgetrow_ MATGETROW 11 #define matrestorerow_ MATRESTOREROW 12 #define matload_ MATLOAD 13 #define matview_ MATVIEW 14 #define matseqaijgetarray_ MATSEQAIJGETARRAY 15 #define matseqaijrestorearray MATSEQAIJRESTOREARRAY 16 #define matdensegetarray_ MATDENSEGETARRAY 17 #define matdenserestorearray_ MATDENSERESTOREARRAY 18 #define matconvert_ MATCONVERT 19 #define matgetsubmatrices_ MATGETSUBMATRICES 20 #define matzerorowscolumns_ MATZEROROWSCOLUMNS 21 #define matzerorowscolumnsis_ MATZEROROWSCOLUMNSIS 22 #define matzerorowsstencil_ MATZEROROWSSTENCIL 23 #define matzerorowscolumnsstencil_ MATZEROROWSCOLUMNSSTENCIL 24 #define matzerorows_ MATZEROROWS 25 #define matzerorowsis_ MATZEROROWSIS 26 #define matzerorowslocal_ MATZEROROWSLOCAL 27 #define matzerorowslocalis_ MATZEROROWSLOCALIS 28 #define matzerorowscolumnslocal_ MATZEROROWSCOLUMNSLOCAL 29 #define matzerorowscolumnslocalis_ MATZEROROWSCOLUMNSLOCALIS 30 #define matsetoptionsprefix_ MATSETOPTIONSPREFIX 31 #define matgetvecs_ MATGETVECS 32 #define matnullspaceremove_ MATNULLSPACEREMOVE 33 #define matgetinfo_ MATGETINFO 34 #define matlufactor_ MATLUFACTOR 35 #define matilufactor_ MATILUFACTOR 36 #define matlufactorsymbolic_ MATLUFACTORSYMBOLIC 37 #define matlufactornumeric_ MATLUFACTORNUMERIC 38 #define matcholeskyfactor_ MATCHOLESKYFACTOR 39 #define matcholeskyfactorsymbolic_ MATCHOLESKYFACTORSYMBOLIC 40 #define matcholeskyfactornumeric_ MATCHOLESKYFACTORNUMERIC 41 #define matilufactorsymbolic_ MATILUFACTORSYMBOLIC 42 #define maticcfactorsymbolic_ MATICCFACTORSYMBOLIC 43 #define maticcfactor_ MATICCFACTOR 44 #define matfactorinfoinitialize_ MATFACTORINFOINITIALIZE 45 #define matnullspacesetfunction_ MATNULLSPACESETFUNCTION 46 #define matfindnonzerorows_ MATFINDNONZEROROWS 47 #elif !defined(PETSC_HAVE_FORTRAN_UNDERSCORE) 48 #define matdestroymatrices_ matdestroymatrices_ 49 #define matgetfactor_ matgetfactor 50 #define matfactorgetsolverpackage_ matfactorgetsolverpackage 51 #define matgetvecs_ matgetvecs 52 #define matgetrowij_ matgetrowij 53 #define matrestorerowij_ matrestorerowij 54 #define matgetrow_ matgetrow 55 #define matrestorerow_ matrestorerow 56 #define matview_ matview 57 #define matload_ matload 58 #define matseqaijgetarray_ matseqaijgetarray 59 #define matseqaijrestorearray_ matseqaijrestorearray 60 #define matdensegetarray_ matdensegetarray 61 #define matdenserestorearray_ matdenserestorearray 62 #define matconvert_ matconvert 63 #define matgetsubmatrices_ matgetsubmatrices 64 #define matzerorowscolumns_ matzerorowscolumns 65 #define matzerorowscolumnsis_ matzerorowscolumnsis 66 #define matzerorowsstencil_ matzerorowsstencil 67 #define matzerorowscolumnsstencil_ matzerorowscolumnsstencil 68 #define matzerorows_ matzerorows 69 #define matzerorowsis_ matzerorowsis 70 #define matzerorowslocal_ matzerorowslocal 71 #define matzerorowslocalis_ matzerorowslocalis 72 #define matzerorowscolumnslocal_ matzerorowscolumnslocal 73 #define matzerorowscolumnslocalis_ matzerorowscolumnslocalis 74 #define matsetoptionsprefix_ matsetoptionsprefix 75 #define matnullspaceremove_ matnullspaceremove 76 #define matgetinfo_ matgetinfo 77 #define matlufactor_ matlufactor 78 #define matilufactor_ matilufactor 79 #define matlufactorsymbolic_ matlufactorsymbolic 80 #define matlufactornumeric_ matlufactornumeric 81 #define matcholeskyfactor_ matcholeskyfactor 82 #define matcholeskyfactorsymbolic_ matcholeskyfactorsymbolic 83 #define matcholeskyfactornumeric_ matcholeskyfactornumeric 84 #define matilufactorsymbolic_ matilufactorsymbolic 85 #define maticcfactorsymbolic_ maticcfactorsymbolic 86 #define maticcfactor_ maticcfactor 87 #define matfactorinfoinitialize_ matfactorinfoinitialize 88 #define matnullspacesetfunction_ matnullspacesetfunction 89 #define matfindnonzerorows_ matfindnonzerorows 90 #endif 91 92 EXTERN_C_BEGIN 93 94 static PetscErrorCode ournullfunction(MatNullSpace sp,Vec x,void *ctx) 95 { 96 PetscErrorCode ierr = 0; 97 (*(void (PETSC_STDCALL *)(MatNullSpace*,Vec*,void*,PetscErrorCode*))(((PetscObject)sp)->fortran_func_pointers[0]))(&sp,&x,ctx,&ierr);CHKERRQ(ierr); 98 return 0; 99 } 100 101 void PETSC_STDCALL matnullspacesetfunction_(MatNullSpace *sp, PetscErrorCode (*rem)(MatNullSpace,Vec,void*),void *ctx,PetscErrorCode *ierr) 102 { 103 PetscObjectAllocateFortranPointers(*sp,1); 104 ((PetscObject)*sp)->fortran_func_pointers[0] = (PetscVoidFunction)rem; 105 106 *ierr = MatNullSpaceSetFunction(*sp,ournullfunction,ctx); 107 } 108 109 void PETSC_STDCALL matgetvecs_(Mat *mat,Vec *right,Vec *left, int *ierr) 110 { 111 CHKFORTRANNULLOBJECT(right); 112 CHKFORTRANNULLOBJECT(left); 113 *ierr = MatGetVecs(*mat,right,left); 114 } 115 116 void PETSC_STDCALL matgetrowij_(Mat *B,PetscInt *shift,PetscBool *sym,PetscBool *blockcompressed,PetscInt *n,PetscInt *ia,size_t *iia, 117 PetscInt *ja,size_t *jja,PetscBool *done,PetscErrorCode *ierr) 118 { 119 const PetscInt *IA,*JA; 120 *ierr = MatGetRowIJ(*B,*shift,*sym,*blockcompressed,n,&IA,&JA,done);if (*ierr) return; 121 *iia = PetscIntAddressToFortran(ia,(PetscInt*)IA); 122 *jja = PetscIntAddressToFortran(ja,(PetscInt*)JA); 123 } 124 125 void PETSC_STDCALL matrestorerowij_(Mat *B,PetscInt *shift,PetscBool *sym,PetscBool *blockcompressed, PetscInt *n,PetscInt *ia,size_t *iia, 126 PetscInt *ja,size_t *jja,PetscBool *done,PetscErrorCode *ierr) 127 { 128 const PetscInt *IA = PetscIntAddressFromFortran(ia,*iia),*JA = PetscIntAddressFromFortran(ja,*jja); 129 *ierr = MatRestoreRowIJ(*B,*shift,*sym,*blockcompressed,n,&IA,&JA,done); 130 } 131 132 /* 133 This is a poor way of storing the column and value pointers 134 generated by MatGetRow() to be returned with MatRestoreRow() 135 but there is not natural,good place else to store them. Hence 136 Fortran programmers can only have one outstanding MatGetRows() 137 at a time. 138 */ 139 static PetscErrorCode matgetrowactive = 0; 140 static const PetscInt *my_ocols = 0; 141 static const PetscScalar *my_ovals = 0; 142 143 void PETSC_STDCALL matgetrow_(Mat *mat,PetscInt *row,PetscInt *ncols,PetscInt *cols,PetscScalar *vals,PetscErrorCode *ierr) 144 { 145 const PetscInt **oocols = &my_ocols; 146 const PetscScalar **oovals = &my_ovals; 147 148 if (matgetrowactive) { 149 PetscError(PETSC_COMM_SELF,__LINE__,"MatGetRow_Fortran",__FILE__,__SDIR__,PETSC_ERR_ARG_WRONGSTATE,PETSC_ERROR_INITIAL, 150 "Cannot have two MatGetRow() active simultaneously\n\ 151 call MatRestoreRow() before calling MatGetRow() a second time"); 152 *ierr = 1; 153 return; 154 } 155 156 CHKFORTRANNULLINTEGER(cols); if (!cols) oocols = NULL; 157 CHKFORTRANNULLSCALAR(vals); if (!vals) oovals = NULL; 158 159 *ierr = MatGetRow(*mat,*row,ncols,oocols,oovals); 160 if (*ierr) return; 161 162 if (oocols) { *ierr = PetscMemcpy(cols,my_ocols,(*ncols)*sizeof(PetscInt)); if (*ierr) return;} 163 if (oovals) { *ierr = PetscMemcpy(vals,my_ovals,(*ncols)*sizeof(PetscScalar)); if (*ierr) return;} 164 matgetrowactive = 1; 165 } 166 167 void PETSC_STDCALL matrestorerow_(Mat *mat,PetscInt *row,PetscInt *ncols,PetscInt *cols,PetscScalar *vals,PetscErrorCode *ierr) 168 { 169 const PetscInt **oocols = &my_ocols; 170 const PetscScalar **oovals = &my_ovals; 171 if (!matgetrowactive) { 172 PetscError(PETSC_COMM_SELF,__LINE__,"MatRestoreRow_Fortran",__FILE__,__SDIR__,PETSC_ERR_ARG_WRONGSTATE,PETSC_ERROR_INITIAL, 173 "Must call MatGetRow() first"); 174 *ierr = 1; 175 return; 176 } 177 CHKFORTRANNULLINTEGER(cols); if (!cols) oocols = NULL; 178 CHKFORTRANNULLSCALAR(vals); if (!vals) oovals = NULL; 179 180 *ierr = MatRestoreRow(*mat,*row,ncols,oocols,oovals); 181 matgetrowactive = 0; 182 } 183 184 void PETSC_STDCALL matview_(Mat *mat,PetscViewer *vin,PetscErrorCode *ierr) 185 { 186 PetscViewer v; 187 PetscPatchDefaultViewers_Fortran(vin,v); 188 *ierr = MatView(*mat,v); 189 } 190 191 void PETSC_STDCALL matload_(Mat *mat,PetscViewer *vin,PetscErrorCode *ierr) 192 { 193 PetscViewer v; 194 PetscPatchDefaultViewers_Fortran(vin,v); 195 *ierr = MatLoad(*mat,v); 196 } 197 198 void PETSC_STDCALL matseqaijgetarray_(Mat *mat,PetscScalar *fa,size_t *ia,PetscErrorCode *ierr) 199 { 200 PetscScalar *mm; 201 PetscInt m,n; 202 203 *ierr = MatSeqAIJGetArray(*mat,&mm); if (*ierr) return; 204 *ierr = MatGetSize(*mat,&m,&n); if (*ierr) return; 205 *ierr = PetscScalarAddressToFortran((PetscObject)*mat,1,fa,mm,m*n,ia); if (*ierr) return; 206 } 207 208 void PETSC_STDCALL matseqaijrestorearray_(Mat *mat,PetscScalar *fa,size_t *ia,PetscErrorCode *ierr) 209 { 210 PetscScalar *lx; 211 PetscInt m,n; 212 213 *ierr = MatGetSize(*mat,&m,&n); if (*ierr) return; 214 *ierr = PetscScalarAddressFromFortran((PetscObject)*mat,fa,*ia,m*n,&lx);if (*ierr) return; 215 *ierr = MatSeqAIJRestoreArray(*mat,&lx);if (*ierr) return; 216 } 217 218 void PETSC_STDCALL matdensegetarray_(Mat *mat,PetscScalar *fa,size_t *ia,PetscErrorCode *ierr) 219 { 220 PetscScalar *mm; 221 PetscInt m,n; 222 223 *ierr = MatDenseGetArray(*mat,&mm); if (*ierr) return; 224 *ierr = MatGetSize(*mat,&m,&n); if (*ierr) return; 225 *ierr = PetscScalarAddressToFortran((PetscObject)*mat,1,fa,mm,m*n,ia); if (*ierr) return; 226 } 227 228 void PETSC_STDCALL matdenserestorearray_(Mat *mat,PetscScalar *fa,size_t *ia,PetscErrorCode *ierr) 229 { 230 PetscScalar *lx; 231 PetscInt m,n; 232 233 *ierr = MatGetSize(*mat,&m,&n); if (*ierr) return; 234 *ierr = PetscScalarAddressFromFortran((PetscObject)*mat,fa,*ia,m*n,&lx);if (*ierr) return; 235 *ierr = MatDenseRestoreArray(*mat,&lx);if (*ierr) return; 236 } 237 238 void PETSC_STDCALL matfactorgetsolverpackage_(Mat *mat,CHAR name PETSC_MIXED_LEN(len),PetscErrorCode *ierr PETSC_END_LEN(len)) 239 { 240 const char *tname; 241 242 *ierr = MatFactorGetSolverPackage(*mat,&tname);if (*ierr) return; 243 if (name != PETSC_NULL_CHARACTER_Fortran) { 244 *ierr = PetscStrncpy(name,tname,len);if (*ierr) return; 245 } 246 FIXRETURNCHAR(PETSC_TRUE,name,len); 247 } 248 249 void PETSC_STDCALL matgetfactor_(Mat *mat,CHAR outtype PETSC_MIXED_LEN(len),MatFactorType *ftype,Mat *M,PetscErrorCode *ierr PETSC_END_LEN(len)) 250 { 251 char *t; 252 FIXCHAR(outtype,len,t); 253 *ierr = MatGetFactor(*mat,t,*ftype,M); 254 FREECHAR(outtype,t); 255 } 256 257 void PETSC_STDCALL matconvert_(Mat *mat,CHAR outtype PETSC_MIXED_LEN(len),MatReuse *reuse,Mat *M,PetscErrorCode *ierr PETSC_END_LEN(len)) 258 { 259 char *t; 260 FIXCHAR(outtype,len,t); 261 *ierr = MatConvert(*mat,t,*reuse,M); 262 FREECHAR(outtype,t); 263 } 264 265 /* 266 MatGetSubmatrices() is slightly different from C since the 267 Fortran provides the array to hold the submatrix objects,while in C that 268 array is allocated by the MatGetSubmatrices() 269 */ 270 void PETSC_STDCALL matgetsubmatrices_(Mat *mat,PetscInt *n,IS *isrow,IS *iscol,MatReuse *scall,Mat *smat,PetscErrorCode *ierr) 271 { 272 Mat *lsmat; 273 PetscInt i; 274 275 if (*scall == MAT_INITIAL_MATRIX) { 276 *ierr = MatGetSubMatrices(*mat,*n,isrow,iscol,*scall,&lsmat); 277 for (i=0; i<*n; i++) { 278 smat[i] = lsmat[i]; 279 } 280 *ierr = PetscFree(lsmat); 281 } else { 282 *ierr = MatGetSubMatrices(*mat,*n,isrow,iscol,*scall,&smat); 283 } 284 } 285 286 /* 287 MatDestroyMatrices() is slightly different from C since the 288 Fortran provides the array to hold the submatrix objects,while in C that 289 array is allocated by the MatGetSubmatrices() 290 */ 291 void PETSC_STDCALL matdestroymatrices_(Mat *mat,PetscInt *n,Mat *smat,PetscErrorCode *ierr) 292 { 293 PetscInt i; 294 295 for (i=0; i<*n; i++) { 296 *ierr = MatDestroy(&smat[i]);if (*ierr) return; 297 } 298 } 299 300 void PETSC_STDCALL matzerorowscolumns_(Mat *mat,PetscInt *numRows,PetscInt *rows,PetscScalar *diag,Vec *x,Vec *b,PetscErrorCode *ierr) 301 { 302 CHKFORTRANNULLOBJECTDEREFERENCE(x); 303 CHKFORTRANNULLOBJECTDEREFERENCE(b); 304 *ierr = MatZeroRowsColumns(*mat,*numRows,rows,*diag,*x,*b); 305 } 306 307 void PETSC_STDCALL matzerorowscolumnsis_(Mat *mat,IS *is,PetscScalar *diag,Vec *x,Vec *b,PetscErrorCode *ierr) 308 { 309 CHKFORTRANNULLOBJECTDEREFERENCE(x); 310 CHKFORTRANNULLOBJECTDEREFERENCE(b); 311 *ierr = MatZeroRowsColumnsIS(*mat,*is,*diag,*x,*b); 312 } 313 314 void PETSC_STDCALL matzerorowsstencil_(Mat *mat,PetscInt *numRows,MatStencil *rows,PetscScalar *diag,Vec *x,Vec *b,PetscErrorCode *ierr) 315 { 316 CHKFORTRANNULLOBJECTDEREFERENCE(x); 317 CHKFORTRANNULLOBJECTDEREFERENCE(b); 318 *ierr = MatZeroRowsStencil(*mat,*numRows,rows,*diag,*x,*b); 319 } 320 321 void PETSC_STDCALL matzerorowscolumnsstencil_(Mat *mat,PetscInt *numRows,MatStencil *rows,PetscScalar *diag,Vec *x,Vec *b,PetscErrorCode *ierr) 322 { 323 CHKFORTRANNULLOBJECTDEREFERENCE(x); 324 CHKFORTRANNULLOBJECTDEREFERENCE(b); 325 *ierr = MatZeroRowsColumnsStencil(*mat,*numRows,rows,*diag,*x,*b); 326 } 327 328 void PETSC_STDCALL matzerorows_(Mat *mat,PetscInt *numRows,PetscInt *rows,PetscScalar *diag,Vec *x,Vec *b,PetscErrorCode *ierr) 329 { 330 CHKFORTRANNULLOBJECTDEREFERENCE(x); 331 CHKFORTRANNULLOBJECTDEREFERENCE(b); 332 *ierr = MatZeroRows(*mat,*numRows,rows,*diag,*x,*b); 333 } 334 335 void PETSC_STDCALL matzerorowsis_(Mat *mat,IS *is,PetscScalar *diag,Vec *x,Vec *b,PetscErrorCode *ierr) 336 { 337 CHKFORTRANNULLOBJECTDEREFERENCE(x); 338 CHKFORTRANNULLOBJECTDEREFERENCE(b); 339 *ierr = MatZeroRowsIS(*mat,*is,*diag,*x,*b); 340 } 341 342 void PETSC_STDCALL matzerorowslocal_(Mat *mat,PetscInt *numRows,PetscInt *rows,PetscScalar *diag,Vec *x,Vec *b,PetscErrorCode *ierr) 343 { 344 CHKFORTRANNULLOBJECTDEREFERENCE(x); 345 CHKFORTRANNULLOBJECTDEREFERENCE(b); 346 *ierr = MatZeroRowsLocal(*mat,*numRows,rows,*diag,*x,*b); 347 } 348 349 void PETSC_STDCALL matzerorowslocalis_(Mat *mat,IS *is,PetscScalar *diag,Vec *x,Vec *b,PetscErrorCode *ierr) 350 { 351 CHKFORTRANNULLOBJECTDEREFERENCE(x); 352 CHKFORTRANNULLOBJECTDEREFERENCE(b); 353 *ierr = MatZeroRowsLocalIS(*mat,*is,*diag,*x,*b); 354 } 355 356 void PETSC_STDCALL matzerorowscolumnslocal_(Mat *mat,PetscInt *numRows,PetscInt *rows,PetscScalar *diag,Vec *x,Vec *b,PetscErrorCode *ierr) 357 { 358 CHKFORTRANNULLOBJECTDEREFERENCE(x); 359 CHKFORTRANNULLOBJECTDEREFERENCE(b); 360 *ierr = MatZeroRowsColumnsLocal(*mat,*numRows,rows,*diag,*x,*b); 361 } 362 363 void PETSC_STDCALL matzerorowscolumnslocalis_(Mat *mat,IS *is,PetscScalar *diag,Vec *x,Vec *b,PetscErrorCode *ierr) 364 { 365 CHKFORTRANNULLOBJECTDEREFERENCE(x); 366 CHKFORTRANNULLOBJECTDEREFERENCE(b); 367 *ierr = MatZeroRowsColumnsLocalIS(*mat,*is,*diag,*x,*b); 368 } 369 370 void PETSC_STDCALL matsetoptionsprefix_(Mat *mat,CHAR prefix PETSC_MIXED_LEN(len),PetscErrorCode *ierr PETSC_END_LEN(len)) 371 { 372 char *t; 373 374 FIXCHAR(prefix,len,t); 375 *ierr = MatSetOptionsPrefix(*mat,t); 376 FREECHAR(prefix,t); 377 } 378 379 void PETSC_STDCALL matnullspaceremove_(MatNullSpace *sp,Vec *vec,Vec *out,PetscErrorCode *ierr) 380 { 381 CHKFORTRANNULLOBJECT(out); 382 *ierr = MatNullSpaceRemove(*sp,*vec,out); 383 } 384 385 void PETSC_STDCALL matgetinfo_(Mat *mat,MatInfoType *flag,MatInfo *info, int *__ierr) 386 { 387 *__ierr = MatGetInfo(*mat,*flag,info); 388 } 389 390 void PETSC_STDCALL matlufactor_(Mat *mat,IS *row,IS *col, MatFactorInfo *info, int *__ierr) 391 { 392 *__ierr = MatLUFactor(*mat,*row,*col,info); 393 } 394 395 void PETSC_STDCALL matilufactor_(Mat *mat,IS *row,IS *col, MatFactorInfo *info, int *__ierr) 396 { 397 *__ierr = MatILUFactor(*mat,*row,*col,info); 398 } 399 400 void PETSC_STDCALL matlufactorsymbolic_(Mat *fact,Mat *mat,IS *row,IS *col, MatFactorInfo *info, int *__ierr) 401 { 402 *__ierr = MatLUFactorSymbolic(*fact,*mat,*row,*col,info); 403 } 404 405 void PETSC_STDCALL matlufactornumeric_(Mat *fact,Mat *mat, MatFactorInfo *info, int *__ierr) 406 { 407 *__ierr = MatLUFactorNumeric(*fact,*mat,info); 408 } 409 410 void PETSC_STDCALL matcholeskyfactor_(Mat *mat,IS *perm, MatFactorInfo *info, int *__ierr) 411 { 412 *__ierr = MatCholeskyFactor(*mat,*perm,info); 413 } 414 415 void PETSC_STDCALL matcholeskyfactorsymbolic_(Mat *fact,Mat *mat,IS *perm, MatFactorInfo *info, int *__ierr) 416 { 417 *__ierr = MatCholeskyFactorSymbolic(*fact,*mat,*perm,info); 418 } 419 420 void PETSC_STDCALL matcholeskyfactornumeric_(Mat *fact,Mat *mat, MatFactorInfo *info, int *__ierr) 421 { 422 *__ierr = MatCholeskyFactorNumeric(*fact,*mat,info); 423 } 424 425 void PETSC_STDCALL matilufactorsymbolic_(Mat *fact,Mat *mat,IS *row,IS *col, MatFactorInfo *info, int *__ierr) 426 { 427 *__ierr = MatILUFactorSymbolic(*fact,*mat,*row,*col,info); 428 } 429 430 void PETSC_STDCALL maticcfactorsymbolic_(Mat *fact,Mat *mat,IS *perm, MatFactorInfo *info, int *__ierr) 431 { 432 *__ierr = MatICCFactorSymbolic(*fact,*mat,*perm,info); 433 } 434 435 void PETSC_STDCALL maticcfactor_(Mat *mat,IS *row, MatFactorInfo *info, int *__ierr) 436 { 437 *__ierr = MatICCFactor(*mat,*row,info); 438 } 439 440 void PETSC_STDCALL matfactorinfoinitialize_(MatFactorInfo *info, int *__ierr) 441 { 442 *__ierr = MatFactorInfoInitialize(info); 443 } 444 445 EXTERN_C_END 446