Peano
Loading...
Searching...
No Matches
kernel-dsl-benchmarks.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 os
4import sys
5import argparse
6import peano4
7import exahype2
8
9sys.path.insert(1,"/home/tvwh77/exahype/DSL/ExaHyPE") #this is for me to use the frontend on my machine, change for your own usage
10from exahype.frontend import general_builder
11from exahype.printers import cpp_printer
12
13
14build_modes = {
15 "Release": peano4.output.CompileMode.Release,
16 "Trace": peano4.output.CompileMode.Trace,
17 "Assert": peano4.output.CompileMode.Asserts,
18 "Stats": peano4.output.CompileMode.Stats,
19 "Debug": peano4.output.CompileMode.Debug,
20}
21build_mode = "Release"
22
23parser = argparse.ArgumentParser(
24 description="ExaHyPE 2 - Finite Volumes Rusanov Kernel Benchmarking Script"
25)
26parser.add_argument(
27 "-m",
28 "--build-mode",
29 dest="build_mode",
30 choices=build_modes.keys(),
31 default=build_mode,
32 help="|".join(build_modes.keys()),
33)
34parser.add_argument(
35 "-d",
36 "--dim",
37 dest="dim",
38 type=int,
39 required=True,
40 help="Number of space dimensions",
41)
42parser.add_argument(
43 "-t",
44 "--num-threads",
45 dest="num_threads",
46 type=int,
47 default=1,
48 help="Number of launching threads",
49)
50parser.add_argument(
51 "-p",
52 "--num-patches",
53 dest="num_patches",
54 nargs="+",
55 default=[32, 64, 128, 256, 512, 1024, 2048],
56 type=int,
57 help="Number of patches to study",
58)
59parser.add_argument(
60 "-ps",
61 "--patch-size",
62 dest="patch_size",
63 type=int,
64 required=True,
65 help="Number of finite volumes per axis (dimension) per patch",
66)
67parser.add_argument(
68 "-s",
69 "--samples",
70 dest="samples",
71 type=int,
72 default=10,
73 help="Number of samples per measurement",
74)
75parser.add_argument(
76 "-a",
77 "--accuracy",
78 dest="accuracy",
79 type=float,
80 default=0.0,
81 help="Floating point accuracy to which the different kernel variants have to match (absolute). Pass in 0 to disable correctness check. Pass in values < 0 to use machine epsilon (default).",
82)
83parser.add_argument(
84 "-e",
85 "--eval-eig",
86 dest="eval_eig",
87 action="store_true",
88 help="Evaluate max. eigenvalue",
89)
90parser.add_argument(
91 "-cpu",
92 "--cpu",
93 dest="eval_cpu",
94 action="store_true",
95 help="Evaluate host kernels",
96)
97parser.add_argument(
98 "-gpu",
99 "--gpu",
100 dest="eval_gpu",
101 action="store_true",
102 help="Evaluate device kernels",
103)
104parser.add_argument(
105 "-fpe",
106 "--fp-exception",
107 dest="enable_fpe",
108 action="store_true",
109 help="Enable a floating-point exception handler",
110)
111parser.add_argument(
112 "--no-make",
113 dest="no_make",
114 action="store_true",
115 help="Do not compile the code after generation",
116)
117args = parser.parse_args()
118
119if args.dim not in [2, 3]:
120 print("Error, dimension must be 2 or 3, you supplied {}".format(args.dim))
121 sys.exit(1)
122
123if args.build_mode not in build_modes:
124 print(
125 "Error, mode must be {} or {}, you supplied {}".format(
126 ", ".join(list(build_modes.keys())[:-1]),
127 list(build_modes.keys())[-1],
128 args.build_mode,
129 )
130 )
131 sys.exit(1)
132
133accuracy = args.accuracy
134if args.accuracy < 0:
135 import numpy
136
137 accuracy = default = numpy.finfo(float).eps
138
139executable_name = (
140 "kernel-benchmarks-fv-rusanov-"
141 + str(args.dim)
142 + "d-ps-"
143 + str(args.patch_size)
144 + "-"
145 + str(args.build_mode)
146)
147
148#DSL kernel generation
149kernel = general_builder(dim=args.dim,patch_size=args.patch_size,halo_size=1,n_real=args.dim+2,n_aux=0,n_patches=args.num_patches[0])
150
151Data = kernel.item('patchData',in_type='::exahype2::CellData&')
152timer = kernel.const('timingComputeKernel',in_type='::tarch::timing::Measurement&')
153
154Q_out = kernel.item('QOut',parent=Data)
155Q = kernel.item('QIn',parent=Data)
156Q_copy = kernel.item('Qcopy')
157
158tmp_flux = kernel.directional_item('tmp_flx')
159tmp_eig = kernel.directional_item('tmp_eigen',struct=False)
160tmp_n = kernel.directional_item('tmp_non_conserve_prod',struct=False)
161avgQ = kernel.directional_item('average_Q')
162deltaQ = kernel.directional_item('delta_Q')
163
164dt = kernel.const('dt',parent=Data)
165t = kernel.const('t',parent=Data)
166cellCentre = kernel.const('cellCentre',parent=Data)
167cellSize = kernel.const('cellSize',parent=Data)
168
169if args.dim == 2:
170 normal = kernel.directional_const('normal',[0,1])
171elif args.dim == 3:
172 normal = kernel.directional_const('normal',[0,1,2])
173
174Flux = kernel.function('flux',parent='benchmarks::exahype2::kernelbenchmarks::repositories::instanceOfFVRusanovSolver')
175Eigen = kernel.function('maxEigenvalue',parent='benchmarks::exahype2::kernelbenchmarks::repositories::instanceOfFVRusanovSolver')
176Max = kernel.function('max')
177Centre = kernel.function('getVolumeCentre',parent='exahype2::fv::')
178Size = kernel.function('getVolumeSize',parent='exahype2::fv::')
179ncp = kernel.function('nonconservativeProduct',parent='benchmarks::exahype2::kernelbenchmarks::repositories::instanceOfFVRusanovSolver')
180
181patch = kernel.all_items["patch"]
182patch_size = kernel.all_items["patch_size"]
183n_real = kernel.all_items["n_real"]
184n_aux = kernel.all_items["n_aux"]
185i = kernel.all_items["i"]
186j = kernel.all_items["j"]
187k = kernel.all_items["k"]
188
189if args.dim == 2:
190 x = Centre(cellCentre,cellSize,patch_size,{i,j})
191elif args.dim == 3:
192 x = Centre(cellCentre,cellSize,patch_size,{i,j,k})
193h = Size(cellSize,patch_size)
194
195kernel.single(Q_copy[0],Q[0])
196kernel.directional(tmp_eig[0],Eigen(Q[0],x,h,t,dt,normal))
197left = -Max(tmp_eig[-1],tmp_eig[0])*(Q[0]-Q[-1])
198right = -Max(tmp_eig[1],tmp_eig[0])*(Q[1]-Q[0])
199kernel.directional(Q_copy[0], Q_copy[0] + 0.5*dt*(left-right),struct=True)
200kernel.directional(Flux(Q[0],x,h,t,dt,normal,tmp_flux[0]))
201kernel.directional(Q_copy[0], Q_copy[0] + 0.5*dt*(tmp_flux[-1]-tmp_flux[1]))
202
203kernel.directional(avgQ[0],0.5*(Q[0]+Q[1]))
204kernel.directional(deltaQ[0],Q[1]-Q[0])
205kernel.directional(tmp_n[0],0)
206kernel.directional(ncp(avgQ[0],deltaQ[0],x,h,t,dt,normal,tmp_n[0]))
207kernel.directional(Q_copy[0], Q_copy[0] + 0.5*dt*(-tmp_n[-1]-tmp_n[0]))
208
209kernel.single(Q_out[0],Q_copy[0])
210
211cpp_printer(kernel).file('generated_kernel.cpp',header='Functions.h')
212
213
214my_project = exahype2.Project(
215 namespace=["benchmarks", "exahype2", "kernelbenchmarks"],
216 project_name="KernelBenchmarksFVRusanov",
217 directory=".",
218 executable=executable_name,
219)
220
222 name="FVRusanovSolver",
223 patch_size=args.patch_size,
224 unknowns={"rho": 1, "v": args.dim, "e": 1},
225 auxiliary_variables=0,
226 min_volume_h=0.001, # max_cell_size -> arbitrary value
227 max_volume_h=0.001, # min_cell_size -> arbitrary value
228 time_step_relaxation=0.5,
229 pde_terms_without_state=True,
230)
231
232my_solver.set_implementation(
233 initial_conditions="",
234 boundary_conditions=exahype2.solvers.PDETerms.Empty_Implementation,
235 flux="::applications::exahype2::euler::flux(Q, normal, F);",
236 eigenvalues="return ::applications::exahype2::euler::maxEigenvalue(Q, normal);",
237 refinement_criterion=exahype2.solvers.PDETerms.Empty_Implementation,
238 source_term="",
239 ncp="",
240)
241
242my_solver.add_user_solver_includes(
243 """
244#include "../../../../applications/exahype2/euler/EulerKernels.h"
245"""
246)
247
248my_project.add_solver(my_solver)
249
250my_project.set_global_simulation_parameters(
251 dimensions=args.dim,
252 size=[1.0, 1.0, 1.0][0 : args.dim],
253 offset=[0.0, 0.0, 0.0][0 : args.dim],
254 min_end_time=0.1,
255 max_end_time=0.1,
256 first_plot_time_stamp=0.0,
257 time_in_between_plots=0.0,
258 periodic_BC=[False, False, False],
259)
260
261my_project.set_Peano4_installation("../../../../", mode=build_modes[args.build_mode])
262my_project = my_project.generate_Peano4_project(verbose=True)
263
264my_project.output.makefile.add_cpp_file("KernelBenchmarksFVRusanov-main.cpp")
265
266my_project.constants.export_constexpr_with_type("Accuracy", str(accuracy), "double")
267my_project.constants.export_constexpr_with_type(
268 "NumberOfSamples", str(args.samples), "int"
269)
270formatted_num_patches = "{{{}}}".format(", ".join(str(val) for val in args.num_patches))
271my_project.constants.export_const_with_type(
272 "NumberOfPatchesToStudy",
273 str(formatted_num_patches),
274 "::tarch::la::Vector<%s, int>" % len(args.num_patches),
275)
276my_project.constants.export_constexpr_with_type(
277 "NumberOfLaunchingThreads", str(args.num_threads), "int"
278)
279
280#change to export what my function is called
281# my_project.constants.export_constexpr_with_type(
282# "time_step", str(args.num_threads), "int"
283# )
284#----
285
286if args.enable_fpe:
287 my_project.constants.export_boolean("EnableFPE", True)
288else:
289 my_project.constants.export_boolean("EnableFPE", False)
290
291my_project.constants.export_boolean("EvaluateFlux", True)
292my_project.constants.export_boolean("EvaluateNonconservativeProduct", False)
293my_project.constants.export_boolean("EvaluateSource", False)
294my_project.constants.export_boolean(
295 "EvaluateMaximumEigenvalueAfterTimeStep", True if args.eval_eig else False
296) # Reduction
297
298if args.eval_cpu == False and args.eval_gpu == False:
299 my_project.constants.export_boolean("EvaluateHostKernels", True)
300 my_project.constants.export_boolean("EvaluateDeviceKernels", True)
301else:
302 my_project.constants.export_boolean(
303 "EvaluateHostKernels", True if args.eval_cpu else False
304 )
305 my_project.constants.export_boolean(
306 "EvaluateDeviceKernels", True if args.eval_gpu else False
307 )
308
309my_project.constants.define_value("GAMMA", str(1.0))
310
311# add my generated cpp files
312# my_project.output.makefile.add_cpp_file("perfect_kernel.cpp")
313my_project.output.makefile.add_cpp_file("generated_kernel.cpp")
314my_project.output.makefile.add_cpp_file("Functions.cpp")
315
316my_project.build(
317 make=not args.no_make, make_clean_first=True, throw_away_data_after_build=True
318)
319
320print("Executable is ", executable_name)
321print("Clean object files via 'make clean'")
322print("Recompile the generated code via 'make -j'")
323print("Remove all generated code via 'make distclean'")
324print("Regenerate all code by running 'python3 kernel-benchmarks-fv-rusanov.py' again")
ExaHyPE 2 project.
Definition Project.py:14