xref: /petsc/src/mat/interface/matreg.c (revision fe998a80077c9ee0917a39496df43fc256e1b478)
1 
2 /*
3      Mechanism for register PETSc matrix types
4 */
5 #include <petsc-private/matimpl.h>      /*I "petscmat.h" I*/
6 
7 PetscBool MatRegisterAllCalled = PETSC_FALSE;
8 
9 /*
10    Contains the list of registered Mat routines
11 */
12 PetscFunctionList MatList = 0;
13 
14 #undef __FUNCT__
15 #define __FUNCT__ "MatSetType"
16 /*@C
17    MatSetType - Builds matrix object for a particular matrix type
18 
19    Collective on Mat
20 
21    Input Parameters:
22 +  mat      - the matrix object
23 -  matype   - matrix type
24 
25    Options Database Key:
26 .  -mat_type  <method> - Sets the type; use -help for a list
27     of available methods (for instance, seqaij)
28 
29    Notes:
30    See "${PETSC_DIR}/include/petscmat.h" for available methods
31 
32   Level: intermediate
33 
34 .keywords: Mat, MatType, set, method
35 
36 .seealso: PCSetType(), VecSetType(), MatCreate(), MatType, Mat
37 @*/
38 PetscErrorCode  MatSetType(Mat mat, MatType matype)
39 {
40   PetscErrorCode ierr,(*r)(Mat);
41   PetscBool      sametype,found;
42   MatBaseName    names = MatBaseNameList;
43 
44   PetscFunctionBegin;
45   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
46 
47   while (names) {
48     ierr = PetscStrcmp(matype,names->bname,&found);CHKERRQ(ierr);
49     if (found) {
50       PetscMPIInt size;
51       ierr = MPI_Comm_size(PetscObjectComm((PetscObject)mat),&size);CHKERRQ(ierr);
52       if (size == 1) matype = names->sname;
53       else matype = names->mname;
54       break;
55     }
56     names = names->next;
57   }
58 
59   ierr = PetscObjectTypeCompare((PetscObject)mat,matype,&sametype);CHKERRQ(ierr);
60   if (sametype) PetscFunctionReturn(0);
61 
62   ierr =  PetscFunctionListFind(MatList,matype,&r);CHKERRQ(ierr);
63   if (!r) SETERRQ1(PETSC_COMM_SELF,PETSC_ERR_ARG_UNKNOWN_TYPE,"Unknown Mat type given: %s",matype);
64 
65   /* free the old data structure if it existed */
66   if (mat->ops->destroy) {
67     ierr = (*mat->ops->destroy)(mat);CHKERRQ(ierr);
68 
69     mat->ops->destroy = NULL;
70   }
71   mat->preallocated = PETSC_FALSE;
72 
73   /* create the new data structure */
74   ierr = (*r)(mat);CHKERRQ(ierr);
75   PetscFunctionReturn(0);
76 }
77 
78 #undef __FUNCT__
79 #define __FUNCT__ "MatGetType"
80 /*@C
81    MatGetType - Gets the matrix type as a string from the matrix object.
82 
83    Not Collective
84 
85    Input Parameter:
86 .  mat - the matrix
87 
88    Output Parameter:
89 .  name - name of matrix type
90 
91    Level: intermediate
92 
93 .keywords: Mat, MatType, get, method, name
94 
95 .seealso: MatSetType()
96 @*/
97 PetscErrorCode  MatGetType(Mat mat,MatType *type)
98 {
99   PetscFunctionBegin;
100   PetscValidHeaderSpecific(mat,MAT_CLASSID,1);
101   PetscValidPointer(type,2);
102   *type = ((PetscObject)mat)->type_name;
103   PetscFunctionReturn(0);
104 }
105 
106 
107 #undef __FUNCT__
108 #define __FUNCT__ "MatRegister"
109 /*@C
110   MatRegister -  - Adds a new matrix type
111 
112    Not Collective
113 
114    Input Parameters:
115 +  name - name of a new user-defined matrix type
116 -  routine_create - routine to create method context
117 
118    Notes:
119    MatRegister() may be called multiple times to add several user-defined solvers.
120 
121    Sample usage:
122 .vb
123    MatRegister("my_mat",MyMatCreate);
124 .ve
125 
126    Then, your solver can be chosen with the procedural interface via
127 $     MatSetType(Mat,"my_mat")
128    or at runtime via the option
129 $     -mat_type my_mat
130 
131    Level: advanced
132 
133 .keywords: Mat, register
134 
135 .seealso: MatRegisterAll(), MatRegisterDestroy()
136 
137 
138   Level: advanced
139 @*/
140 PetscErrorCode  MatRegister(const char sname[],PetscErrorCode (*function)(Mat))
141 {
142   PetscErrorCode ierr;
143 
144   PetscFunctionBegin;
145   ierr = PetscFunctionListAdd(&MatList,sname,function);CHKERRQ(ierr);
146   PetscFunctionReturn(0);
147 }
148 
149 MatBaseName MatBaseNameList = 0;
150 
151 #undef __FUNCT__
152 #define __FUNCT__ "MatRegisterBaseName"
153 /*@C
154       MatRegisterBaseName - Registers a name that can be used for either a sequential or its corresponding parallel matrix type.
155 
156   Input Parameters:
157 +     bname - the basename, for example, MATAIJ
158 .     sname - the name of the sequential matrix type, for example, MATSEQAIJ
159 -     mname - the name of the parallel matrix type, for example, MATMPIAIJ
160 
161 
162   Level: advanced
163 @*/
164 PetscErrorCode  MatRegisterBaseName(const char bname[],const char sname[],const char mname[])
165 {
166   PetscErrorCode ierr;
167   MatBaseName    names;
168 
169   PetscFunctionBegin;
170   ierr = PetscNew(&names);CHKERRQ(ierr);
171   ierr = PetscStrallocpy(bname,&names->bname);CHKERRQ(ierr);
172   ierr = PetscStrallocpy(sname,&names->sname);CHKERRQ(ierr);
173   ierr = PetscStrallocpy(mname,&names->mname);CHKERRQ(ierr);
174   if (!MatBaseNameList) {
175     MatBaseNameList = names;
176   } else {
177     MatBaseName next = MatBaseNameList;
178     while (next->next) next = next->next;
179     next->next = names;
180   }
181   PetscFunctionReturn(0);
182 }
183 
184 
185 
186 
187 
188 
189 
190