Line | Branch | Exec | Source |
---|---|---|---|
1 | /* | ||
2 | - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - | ||
3 | SLEPc - Scalable Library for Eigenvalue Problem Computations | ||
4 | Copyright (c) 2002-, Universitat Politecnica de Valencia, Spain | ||
5 | |||
6 | This file is part of SLEPc. | ||
7 | SLEPc is distributed under a 2-clause BSD license (see LICENSE). | ||
8 | - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - | ||
9 | */ | ||
10 | |||
11 | #pragma once | ||
12 | |||
13 | #include <slepcfn.h> | ||
14 | #include <slepc/private/slepcimpl.h> | ||
15 | |||
16 | /* SUBMANSEC = FN */ | ||
17 | |||
18 | SLEPC_EXTERN PetscBool FNRegisterAllCalled; | ||
19 | SLEPC_EXTERN PetscErrorCode FNRegisterAll(void); | ||
20 | SLEPC_EXTERN PetscLogEvent FN_Evaluate; | ||
21 | |||
22 | typedef struct _FNOps *FNOps; | ||
23 | |||
24 | struct _FNOps { | ||
25 | PetscErrorCode (*evaluatefunction)(FN,PetscScalar,PetscScalar*); | ||
26 | PetscErrorCode (*evaluatederivative)(FN,PetscScalar,PetscScalar*); | ||
27 | PetscErrorCode (*evaluatefunctionmat[FN_MAX_SOLVE])(FN,Mat,Mat); | ||
28 | PetscErrorCode (*evaluatefunctionmatcuda[FN_MAX_SOLVE])(FN,Mat,Mat); | ||
29 | PetscErrorCode (*evaluatefunctionmatvec[FN_MAX_SOLVE])(FN,Mat,Vec); | ||
30 | PetscErrorCode (*evaluatefunctionmatveccuda[FN_MAX_SOLVE])(FN,Mat,Vec); | ||
31 | PetscErrorCode (*setfromoptions)(FN,PetscOptionItems); | ||
32 | PetscErrorCode (*view)(FN,PetscViewer); | ||
33 | PetscErrorCode (*duplicate)(FN,MPI_Comm,FN*); | ||
34 | PetscErrorCode (*destroy)(FN); | ||
35 | }; | ||
36 | |||
37 | #define FN_MAX_W 6 | ||
38 | |||
39 | struct _p_FN { | ||
40 | PETSCHEADER(struct _FNOps); | ||
41 | /*------------------------- User parameters --------------------------*/ | ||
42 | PetscScalar alpha; /* inner scaling (argument) */ | ||
43 | PetscScalar beta; /* outer scaling (result) */ | ||
44 | PetscInt method; /* the method to compute matrix functions */ | ||
45 | FNParallelType pmode; /* parallel mode (redundant or synchronized) */ | ||
46 | |||
47 | /*---------------------- Cached data and workspace -------------------*/ | ||
48 | Mat W[FN_MAX_W]; /* workspace matrices */ | ||
49 | PetscInt nw; /* number of allocated W matrices */ | ||
50 | PetscInt cw; /* current W matrix */ | ||
51 | void *data; | ||
52 | }; | ||
53 | |||
54 | /* | ||
55 | FN_AllocateWorkMat - Allocate a work Mat of the same dimension of A and copy | ||
56 | its contents. The work matrix is returned in M and should be freed with | ||
57 | FN_FreeWorkMat(). | ||
58 | */ | ||
59 | 9609 | static inline PetscErrorCode FN_AllocateWorkMat(FN fn,Mat A,Mat *M) | |
60 | { | ||
61 | 9609 | PetscInt n,na; | |
62 | 9609 | PetscBool create=PETSC_FALSE; | |
63 | |||
64 |
1/2✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
|
9609 | PetscFunctionBegin; |
65 | 9609 | *M = NULL; | |
66 |
1/4✗ Branch 0 not taken.
✓ Branch 1 taken 50 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
|
9609 | PetscCheck(fn->cw<FN_MAX_W,PETSC_COMM_SELF,PETSC_ERR_SUP,"Too many requested work matrices %" PetscInt_FMT,fn->cw); |
67 |
2/2✓ Branch 0 taken 50 times.
✓ Branch 1 taken 40 times.
|
9609 | if (fn->nw<=fn->cw) { |
68 | 1443 | create=PETSC_TRUE; | |
69 | 1443 | fn->nw++; | |
70 | } else { | ||
71 |
4/6✓ Branch 0 taken 8 times.
✓ Branch 1 taken 32 times.
✓ Branch 2 taken 8 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 8 times.
|
8166 | PetscCall(MatGetSize(fn->W[fn->cw],&n,NULL)); |
72 |
4/6✓ Branch 0 taken 8 times.
✓ Branch 1 taken 32 times.
✓ Branch 2 taken 8 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 8 times.
|
8166 | PetscCall(MatGetSize(A,&na,NULL)); |
73 |
2/2✓ Branch 0 taken 30 times.
✓ Branch 1 taken 40 times.
|
8166 | if (n!=na) { |
74 |
4/6✓ Branch 0 taken 6 times.
✓ Branch 1 taken 24 times.
✓ Branch 2 taken 6 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 6 times.
|
4170 | PetscCall(MatDestroy(&fn->W[fn->cw])); |
75 | create=PETSC_TRUE; | ||
76 | } | ||
77 | } | ||
78 |
4/6✓ Branch 0 taken 10 times.
✓ Branch 1 taken 40 times.
✓ Branch 2 taken 10 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 10 times.
|
5613 | if (create) PetscCall(MatDuplicate(A,MAT_COPY_VALUES,&fn->W[fn->cw])); |
79 |
4/6✓ Branch 0 taken 8 times.
✓ Branch 1 taken 32 times.
✓ Branch 2 taken 8 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 8 times.
|
3996 | else PetscCall(MatCopy(A,fn->W[fn->cw],SAME_NONZERO_PATTERN)); |
80 | 9609 | *M = fn->W[fn->cw]; | |
81 | 9609 | fn->cw++; | |
82 |
6/12✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 10 times.
✓ Branch 4 taken 10 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 10 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 10 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 10 times.
|
9609 | PetscFunctionReturn(PETSC_SUCCESS); |
83 | } | ||
84 | |||
85 | /* | ||
86 | FN_FreeWorkMat - Release a work matrix created with FN_AllocateWorkMat(). | ||
87 | */ | ||
88 | 9609 | static inline PetscErrorCode FN_FreeWorkMat(FN fn,Mat *M) | |
89 | { | ||
90 |
1/2✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
|
9609 | PetscFunctionBegin; |
91 |
1/4✗ Branch 0 not taken.
✓ Branch 1 taken 50 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
|
9609 | PetscCheck(fn->cw,PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"There are no work matrices"); |
92 | 9609 | fn->cw--; | |
93 |
1/4✗ Branch 0 not taken.
✓ Branch 1 taken 50 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
|
9609 | PetscCheck(fn->W[fn->cw]==*M,PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Work matrices must be freed in the reverse order of their creation"); |
94 | 9609 | *M = NULL; | |
95 |
6/12✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 10 times.
✓ Branch 4 taken 10 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 10 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 10 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 10 times.
|
9609 | PetscFunctionReturn(PETSC_SUCCESS); |
96 | } | ||
97 | |||
98 | SLEPC_INTERN PetscErrorCode FNSqrtmSchur(FN,PetscBLASInt,PetscScalar*,PetscBLASInt,PetscBool); | ||
99 | SLEPC_INTERN PetscErrorCode FNSqrtmDenmanBeavers(FN,PetscBLASInt,PetscScalar*,PetscBLASInt,PetscBool); | ||
100 | SLEPC_INTERN PetscErrorCode FNSqrtmNewtonSchulz(FN,PetscBLASInt,PetscScalar*,PetscBLASInt,PetscBool); | ||
101 | SLEPC_INTERN PetscErrorCode FNSqrtmSadeghi(FN,PetscBLASInt,PetscScalar*,PetscBLASInt); | ||
102 | SLEPC_INTERN PetscErrorCode SlepcNormAm(PetscBLASInt,PetscScalar*,PetscInt,PetscScalar*,PetscRandom,PetscReal*); | ||
103 | SLEPC_INTERN PetscErrorCode FNEvaluateFunctionMat_Private(FN,Mat,Mat,PetscBool); | ||
104 | SLEPC_INTERN PetscErrorCode FNEvaluateFunctionMatVec_Private(FN,Mat,Vec,PetscBool); | ||
105 | SLEPC_INTERN PetscErrorCode FNEvaluateFunctionMat_Exp_Higham(FN,Mat,Mat); /* used in FNPHI */ | ||
106 | #if defined(PETSC_HAVE_CUDA) | ||
107 | SLEPC_INTERN PetscErrorCode FNSqrtmDenmanBeavers_CUDAm(FN,PetscBLASInt,PetscScalar*,PetscBLASInt,PetscBool); | ||
108 | SLEPC_INTERN PetscErrorCode FNSqrtmNewtonSchulz_CUDA(FN,PetscBLASInt,PetscScalar*,PetscBLASInt,PetscBool); | ||
109 | SLEPC_INTERN PetscErrorCode FNSqrtmSadeghi_CUDAm(FN,PetscBLASInt,PetscScalar*,PetscBLASInt); | ||
110 | #endif | ||
111 |