Peano
Loading...
Searching...
No Matches
SolverToCPPFiles.py
Go to the documentation of this file.
1# This file is part of the ExaHyPE2 project. For conditions of distribution and
2# use, please see the copyright notice at www.peano-framework.org
3import peano4.api
5
6import dastgen2
7
8import os
9import sys
10
11from .Solver import Solver
12
13
15 TEMPLATE_ABSTRACT_HEADER_FILE = """
16// This file is part of the ExaHyPE2 project. For conditions of distribution and
17// use, please see the copyright notice at www.peano-framework.org
18#pragma once
19
20#include "exahype2/RefinementControl.h"
21#include "exahype2/Solver.h"
22#include "tarch/la/Vector.h"
23#include "tarch/accelerator/accelerator.h"
24#include "tarch/NonCriticalAssertions.h"
25
26#include "peano4/utils/Globals.h"
27
28#include "Constants.h"
29
30
31{% for item in NAMESPACE -%}
32 namespace {{ item }} {
33 {# Empty line here #}
34{%- endfor %}
35 class {{CLASSNAME}};
36
37{% for item in NAMESPACE -%}
38 }
39{%- endfor %}
40
41
42class {{NAMESPACE | join("::")}}::{{CLASSNAME}}: public ::exahype2::Solver {
43 public:
44 {{CLASSNAME}}();
45
46 static constexpr int NumberOfUnknowns = {{NUMBER_OF_UNKNOWNS}};
47 static constexpr int NumberOfAuxiliaryVariables = {{NUMBER_OF_AUXILIARY_VARIABLES}};
48 static constexpr int PatchSize = {{PATCH_SIZE}};
49 static constexpr int HaloSize = {{HALO_SIZE}};
50
51 {{VARIABLES}}
52
53 {{PDE_TERM_DECLARATIONS}}
54
55 {{ADDITIONAL_METHOD_DECLARATIONS}}
56
57 protected:
58 static tarch::logging::Log _log;
59
60 {{ADDITIONAL_ATTRIBUTES}}
61};
62
63{# Empty line here #}
64"""
65
66 TEMPLATE_ABSTRACT_CPP_FILE = """
67#include "{{CLASSNAME}}.h"
68#include "exahype2/RefinementControl.h"
69{{USER_SOLVER_INCLUDES}}
70
71tarch::logging::Log {{NAMESPACE | join("::")}}::{{CLASSNAME}}::_log( "{{NAMESPACE | join("::")}}::{{CLASSNAME}}" );
72
73
74{{NAMESPACE | join("::")}}::{{CLASSNAME}}::{{CLASSNAME}}() {
75}
76
77
78{{PDE_TERM_DEFINITIONS}}
79
80{{ADDITIONAL_METHOD_DEFINITIONS}}
81"""
82
83 TEMPLATE_SOLVER_HEADER_FILE = """
84// This file has been generated by the ExaHyPE2 api which is part
85// of the ExaHyPE2 project. For conditions of distribution and
86// use of ExaHyPE2, please see the copyright notice at
87// www.peano-framework.org. However, this file is only a suggestion
88// and can be freely changed by the ExaHyPE 2 user who might decide
89// to apply their own copyright.
90#pragma once
91
92#include "Abstract{{CLASSNAME}}.h"
93
94
95{% for item in NAMESPACE -%}
96 namespace {{ item }} {
97 {# Empty line here #}
98{%- endfor %}
99 class {{CLASSNAME}};
100
101{% for item in NAMESPACE -%}
102 }
103{%- endfor %}
104
105
106class {{NAMESPACE | join("::")}}::{{CLASSNAME}}: public {{NAMESPACE | join("::")}}::Abstract{{CLASSNAME}} {
107 public:
108 {{CLASSNAME}}() = default;
109
110 {{PDE_TERM_STUB_DECLARATIONS}}
111};
112
113{# Empty line here #}
114"""
115
116 TEMPLATE_SOLVER_CPP_FILE = """
117#include "{{CLASSNAME}}.h"
118
119
120{{PDE_TERM_STUB_DEFINITIONS}}
121"""
122
123 """!
124
125 Default implementation that takes a solver and maps it onto two C++ classes:
126 An abstract base class and a class for the user to implement it.
127
128 The user class is only generated if at least one PDE term lacks an
129 implementation (@see Solver.requires_user_class). It is never
130 overwritten once it exists, and it is added to the Makefile as a
131 non-generated file. Without it, the solver repository instantiates
132 the abstract base class directly.
133
134 """
135
136 def __init__(self, solver: Solver):
137 super().__init__(solver)
138
139 def _variables_declaration(self) -> str:
140 """!
141
142 Nested struct Variables with the position of each named variable
143 within Q, or the empty string if the solver's variables carry no
144 names. User code (and code injected from Python) then can write
145 Q[Variables::rho] instead of Q[0].
146
147 """
148 if not self._solver._variable_positions:
149 return ""
150 constants = "\n".join(
151 f" static constexpr int {variable_name} = {position};"
152 for variable_name, position in self._solver._variable_positions.items()
153 )
154 return (
155 "/**\n"
156 " * Positions of the named unknowns and auxiliary variables within Q\n"
157 " */\n"
158 " struct Variables {\n" + constants + "\n };"
159 )
160
162 self,
163 exahype2_project,
164 peano_project,
165 ):
166 """!
167
168 Dump the solver into actual C++ classes.
169
170 """
171 class_name = "Abstract" + self._solver.name
172 templatefile_prefix = (
173 os.path.realpath(__file__).replace(".pyc", "").replace(".py", "")
174 )
175
176 peano4.api.Logger().log(
177 "Map class {} onto C++ class {} using {}".format(
178 self._solver.name, class_name, templatefile_prefix
179 )
180 )
181
182 qualified_class_name = "::".join(peano_project.namespace) + "::" + class_name
183
184 local_d = {
185 "NUMBER_OF_UNKNOWNS": self._solver._unknowns,
186 "NUMBER_OF_AUXILIARY_VARIABLES": self._solver._auxiliary_variables,
187 "PATCH_SIZE": self._solver.numerical_scheme.patch_size,
188 "HALO_SIZE": self._solver.numerical_scheme.halo_size,
189 "USER_SOLVER_INCLUDES": self._solver.user_solver_includes,
190 "VARIABLES": self._variables_declaration(),
191 "PDE_TERM_DECLARATIONS": "\n".join(
192 term.generator.generate_declaration() for term in self._solver.pde_terms
193 ),
194 "PDE_TERM_DEFINITIONS": "\n".join(
195 term.generator.generate_out_of_class_definitions(qualified_class_name)
196 for term in self._solver.pde_terms
197 ),
198 "ADDITIONAL_ATTRIBUTES": "\n".join(
199 self._solver._abstract_solver_attributes
200 ),
201 "ADDITIONAL_METHOD_DECLARATIONS": "\n".join(
202 declaration
203 for declaration, definition_generator in self._solver._abstract_solver_methods
204 ),
205 "ADDITIONAL_METHOD_DEFINITIONS": "\n".join(
206 definition_generator(qualified_class_name)
207 for declaration, definition_generator in self._solver._abstract_solver_methods
208 ),
209 }
210
211 generated_files = (
213 headerfile_template=self.TEMPLATE_ABSTRACT_HEADER_FILE,
214 cppfile_template=self.TEMPLATE_ABSTRACT_CPP_FILE,
215 classname=class_name,
216 namespace=peano_project.namespace,
217 subdirectory=peano_project.subdirectory,
218 dictionary=local_d,
219 default_overwrite=True,
220 apply_iteratively=False,
221 )
222 )
223 peano_project.output.add(generated_files)
224 peano_project.output.makefile.add_cpp_file(
225 peano_project.subdirectory + class_name + ".cpp", generated=True
226 )
227
228 if not self._solver.requires_user_class:
229 return
230
231 solver_class_name = self._solver.name
232 qualified_solver_class_name = (
233 "::".join(peano_project.namespace) + "::" + solver_class_name
234 )
235
236 solver_local_d = {
237 "PDE_TERM_STUB_DECLARATIONS": "\n".join(
238 term.generator.generate_stub_declaration()
239 for term in self._solver.pde_terms
240 ),
241 "PDE_TERM_STUB_DEFINITIONS": "\n".join(
242 term.generator.generate_stub_definition(qualified_solver_class_name)
243 for term in self._solver.pde_terms
244 ),
245 }
246
247 solver_generated_files = (
249 headerfile_template=self.TEMPLATE_SOLVER_HEADER_FILE,
250 cppfile_template=self.TEMPLATE_SOLVER_CPP_FILE,
251 classname=solver_class_name,
252 namespace=peano_project.namespace,
253 subdirectory=peano_project.subdirectory,
254 dictionary=solver_local_d,
255 default_overwrite=False,
256 apply_iteratively=False,
257 )
258 )
259 peano_project.output.add(solver_generated_files)
260 # Not flagged as generated: the user owns these files, so the
261 # Makefile's clean targets must not delete them.
262 peano_project.output.makefile.add_h_file(
263 peano_project.subdirectory + solver_class_name + ".h", generated=False
264 )
265 peano_project.output.makefile.add_cpp_file(
266 peano_project.subdirectory + solver_class_name + ".cpp", generated=False
267 )
str _variables_declaration(self)
Nested struct Variables with the position of each named variable within Q, or the empty string if the...
construct_output(self, exahype2_project, peano_project)
Dump the solver into actual C++ classes.
Turns a Solver into actual classes.
Definition Solver.py:44
Singleton logger for the Peano 4 Python API.
Definition Logger.py:37