def my_box_mesh(boundary_tagger): from hedge.mesh.generator import make_rect_mesh from math import pi return make_rect_mesh( b=(2*pi, 3), max_area=0.4, #periodicity=(True, False), # meshpy doesn't do periodic at the moment (5/2014) periodicity=(False, False), subdivisions=(5, 10), boundary_tagger=boundary_tagger, )
def my_box_mesh(boundary_tagger): from hedge.mesh.generator import make_rect_mesh from math import pi return make_rect_mesh( b=(2 * pi, 3), max_area=0.4, #periodicity=(True, False), # meshpy doesn't do periodic at the moment (5/2014) periodicity=(False, False), subdivisions=(5, 10), boundary_tagger=boundary_tagger, )
def main(write_output=True): from math import sin, exp, sqrt # noqa from hedge.mesh.generator import make_rect_mesh mesh = make_rect_mesh(a=(-0.5, -0.5), b=(0.5, 0.5), max_area=0.008) from hedge.backends.jit import Discretization discr = Discretization(mesh, order=4) from hedge.visualization import VtkVisualizer vis = VtkVisualizer(discr, None, "fld") source_center = np.array([0.1, 0.22]) source_width = 0.05 source_omega = 3 import hedge.optemplate as sym sym_x = sym.nodes(2) sym_source_center_dist = sym_x - source_center from hedge.models.wave import StrongWaveOperator from hedge.mesh import TAG_ALL, TAG_NONE op = StrongWaveOperator( -0.1, discr.dimensions, source_f=sym.CFunction("sin")( source_omega * sym.ScalarParameter("t")) * sym.CFunction("exp")( -np.dot(sym_source_center_dist, sym_source_center_dist) / source_width**2), dirichlet_tag=TAG_NONE, neumann_tag=TAG_NONE, radiation_tag=TAG_ALL, flux_type="upwind") from hedge.tools import join_fields fields = join_fields( discr.volume_zeros(), [discr.volume_zeros() for i in range(discr.dimensions)]) from hedge.timestep.runge_kutta import LSRK4TimeStepper stepper = LSRK4TimeStepper() dt = op.estimate_timestep(discr, stepper=stepper, fields=fields) nsteps = int(10 / dt) print "dt=%g nsteps=%d" % (dt, nsteps) rhs = op.bind(discr) for step in range(nsteps): t = step * dt if step % 10 == 0 and write_output: print step, t, discr.norm(fields[0]) visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [ ("u", fields[0]), ("v", fields[1:]), ], time=t, step=step) visf.close() fields = stepper(fields, t, dt, rhs) vis.close()
def main(write_output=True, dir_tag=TAG_NONE, neu_tag=TAG_NONE, rad_tag=TAG_ALL, flux_type_arg="upwind"): from math import sin, cos, pi, exp, sqrt # noqa from hedge.backends import guess_run_context rcon = guess_run_context() dim = 2 if dim == 1: if rcon.is_head_rank: from hedge.mesh.generator import make_uniform_1d_mesh mesh = make_uniform_1d_mesh(-10, 10, 500) elif dim == 2: from hedge.mesh.generator import make_rect_mesh if rcon.is_head_rank: mesh = make_rect_mesh(a=(-1, -1), b=(1, 1), max_area=0.003) elif dim == 3: if rcon.is_head_rank: from hedge.mesh.generator import make_ball_mesh mesh = make_ball_mesh(max_volume=0.0005) else: raise RuntimeError("bad number of dimensions") if rcon.is_head_rank: print "%d elements" % len(mesh.elements) mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() discr = rcon.make_discretization(mesh_data, order=4) from hedge.timestep.runge_kutta import LSRK4TimeStepper stepper = LSRK4TimeStepper() from hedge.visualization import VtkVisualizer if write_output: vis = VtkVisualizer(discr, rcon, "fld") source_center = np.array([0.7, 0.4]) source_width = 1 / 16 source_omega = 3 import hedge.optemplate as sym sym_x = sym.nodes(2) sym_source_center_dist = sym_x - source_center from hedge.models.wave import VariableVelocityStrongWaveOperator op = VariableVelocityStrongWaveOperator( c=sym.If(sym.Comparison(np.dot(sym_x, sym_x), "<", 0.4**2), 1, 0.5), dimensions=discr.dimensions, source=sym.CFunction("sin")(source_omega * sym.ScalarParameter("t")) * sym.CFunction("exp")( -np.dot(sym_source_center_dist, sym_source_center_dist) / source_width**2), dirichlet_tag=dir_tag, neumann_tag=neu_tag, radiation_tag=rad_tag, flux_type=flux_type_arg) from hedge.tools import join_fields fields = join_fields( discr.volume_zeros(), [discr.volume_zeros() for i in range(discr.dimensions)]) # {{{ diagnostics setup from pytools.log import LogManager, \ add_general_quantities, \ add_simulation_quantities, \ add_run_info if write_output: log_file_name = "wave.dat" else: log_file_name = None logmgr = LogManager(log_file_name, "w", rcon.communicator) add_run_info(logmgr) add_general_quantities(logmgr) add_simulation_quantities(logmgr) discr.add_instrumentation(logmgr) from pytools.log import IntervalTimer vis_timer = IntervalTimer("t_vis", "Time spent visualizing") logmgr.add_quantity(vis_timer) stepper.add_instrumentation(logmgr) from hedge.log import LpNorm u_getter = lambda: fields[0] logmgr.add_quantity(LpNorm(u_getter, discr, 1, name="l1_u")) logmgr.add_quantity(LpNorm(u_getter, discr, name="l2_u")) logmgr.add_watches(["step.max", "t_sim.max", "l2_u", "t_step.max"]) # }}} # {{{ timestep loop rhs = op.bind(discr) try: from hedge.timestep.stability import \ approximate_rk4_relative_imag_stability_region max_dt = (1 / discr.compile(op.max_eigenvalue_expr())() * discr.dt_non_geometric_factor() * discr.dt_geometric_factor() * approximate_rk4_relative_imag_stability_region(stepper)) if flux_type_arg == "central": max_dt *= 0.25 from hedge.timestep import times_and_steps step_it = times_and_steps(final_time=3, logmgr=logmgr, max_dt_getter=lambda t: max_dt) for step, t, dt in step_it: if step % 10 == 0 and write_output: visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [ ("u", fields[0]), ("v", fields[1:]), ], time=t, step=step) visf.close() fields = stepper(fields, t, dt, rhs) assert discr.norm(fields) < 1 finally: if write_output: vis.close() logmgr.close() discr.close()
def run_convergence_test_advec(dtype, debug_output=False): """Test whether 2/3D advection actually converges""" from hedge.mesh.generator import make_ball_mesh, make_box_mesh, make_rect_mesh from hedge.timestep import RK4TimeStepper from hedge.tools import EOCRecorder from math import sin, pi, sqrt from hedge.models.advection import StrongAdvectionOperator from hedge.data import TimeDependentGivenFunction from hedge.visualization import SiloVisualizer from hedge.backends import guess_run_context rcon = guess_run_context(["mpi"]) # note: x component must remain zero because x-periodicity is used v = numpy.array([0.0,0.9,0.3]) def f(x): return sin(x) def u_analytic(x, el, t): return f((numpy.dot(-v[:dims],x)/la.norm(v[:dims])+t*la.norm(v[:dims]))) def boundary_tagger(vertices, el, face_nr, points): face_normal = el.face_normals[face_nr] if numpy.dot(face_normal, v[:len(face_normal)]) < 0: return ["inflow"] else: return ["outflow"] for i_mesh, mesh in enumerate([ # 2D semiperiodic make_rect_mesh(b=(2*pi,3), max_area=0.4, periodicity=(True, False), subdivisions=(5,10), boundary_tagger=boundary_tagger, ), # 3D x-periodic make_box_mesh((0,0,0), (2*pi, 2, 2), max_volume=0.4, periodicity=(True, False, False), boundary_tagger=boundary_tagger, ), # non-periodic make_ball_mesh(r=pi, boundary_tagger=boundary_tagger, max_volume=0.7), ]): for flux_type in StrongAdvectionOperator.flux_types: for random_partition in [True, False]: eoc_rec = EOCRecorder() if random_partition: # Distribute elements randomly across nodes. # This is bad, efficiency-wise, but it puts stress # on the parallel implementation, which is desired here. # Another main point of this is to force the code to split # a periodic face pair across nodes. from random import choice partition = [choice(rcon.ranks) for el in mesh.elements] else: partition = None for order in [1,2,3,4]: if rcon.is_head_rank: mesh_data = rcon.distribute_mesh(mesh, partition) else: mesh_data = rcon.receive_mesh() dims = mesh.points.shape[1] discr = rcon.make_discretization(mesh_data, order=order, default_scalar_type=dtype) op = StrongAdvectionOperator(v[:dims], inflow_u=TimeDependentGivenFunction(u_analytic), flux_type=flux_type) if debug_output: vis = SiloVisualizer(discr, rcon) u = discr.interpolate_volume_function( lambda x, el: u_analytic(x, el, 0)) ic = u.copy() if debug_output and rcon.is_head_rank: print "#elements=%d" % len(mesh.elements) test_name = "test-%s-o%d-m%d-r%s" % ( flux_type, order, i_mesh, random_partition) rhs = op.bind(discr) stepper = RK4TimeStepper(dtype=dtype) from hedge.timestep import times_and_steps final_time = 1 step_it = times_and_steps( final_time=final_time, max_dt_getter=lambda t: op.estimate_timestep(discr, stepper=stepper, t=t, fields=u)) for step, t, dt in step_it: u = stepper(u, t, dt, rhs) assert u.dtype == dtype u_true = discr.interpolate_volume_function( lambda x, el: u_analytic(x, el, final_time)) error = u-u_true l2_error = discr.norm(error) if debug_output: visf = vis.make_file(test_name+"-final") vis.add_data(visf, [ ("u", u), ("u_true", u_true), ("ic", ic)]) visf.close() eoc_rec.add_data_point(order, l2_error) if debug_output and rcon.is_head_rank: print "%s\n%s\n" % (flux_type.upper(), "-" * len(flux_type)) print eoc_rec.pretty_print(abscissa_label="Poly. Order", error_label="L2 Error") assert eoc_rec.estimate_order_of_convergence()[0,1] > 3 assert eoc_rec.estimate_order_of_convergence(2)[-1,1] > 7
def main(): from hedge.backends import guess_run_context rcon = guess_run_context() from hedge.tools import to_obj_array if rcon.is_head_rank: from hedge.mesh.generator import make_rect_mesh mesh = make_rect_mesh((-5, -5), (5, 5), max_area=0.01) mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() for order in [1]: discr = rcon.make_discretization(mesh_data, order=order, default_scalar_type=numpy.float64) from hedge.visualization import SiloVisualizer, VtkVisualizer vis = VtkVisualizer(discr, rcon, "Sod2D-%d" % order) #vis = SiloVisualizer(discr, rcon) sod_field = Sod(gamma=1.4) fields = sod_field.volume_interpolant(0, discr) from hedge.models.gas_dynamics import GasDynamicsOperator from hedge.mesh import TAG_ALL op = GasDynamicsOperator(dimensions=2, gamma=sod_field.gamma, mu=0.0, prandtl=sod_field.prandtl, bc_inflow=sod_field, bc_outflow=sod_field, bc_noslip=sod_field, inflow_tag=TAG_ALL, source=None) euler_ex = op.bind(discr) max_eigval = [0] def rhs(t, q): ode_rhs, speed = euler_ex(t, q) max_eigval[0] = speed return ode_rhs rhs(0, fields) if rcon.is_head_rank: print "---------------------------------------------" print "order %d" % order print "---------------------------------------------" print "#elements=", len(mesh.elements) # limiter setup ------------------------------------------------------------ from hedge.models.gas_dynamics import SlopeLimiter1NEuler limiter = SlopeLimiter1NEuler(discr, sod_field.gamma, 2, op) # integrator setup--------------------------------------------------------- from hedge.timestep import SSPRK3TimeStepper, RK4TimeStepper stepper = SSPRK3TimeStepper(limiter=limiter) #stepper = SSPRK3TimeStepper() #stepper = RK4TimeStepper() # diagnostics setup --------------------------------------------------- from pytools.log import LogManager, add_general_quantities, \ add_simulation_quantities, add_run_info logmgr = LogManager("euler-%d.dat" % order, "w", rcon.communicator) add_run_info(logmgr) add_general_quantities(logmgr) add_simulation_quantities(logmgr) discr.add_instrumentation(logmgr) stepper.add_instrumentation(logmgr) logmgr.add_watches(["step.max", "t_sim.max", "t_step.max"]) # filter setup------------------------------------------------------------- from hedge.discretization import Filter, ExponentialFilterResponseFunction mode_filter = Filter( discr, ExponentialFilterResponseFunction(min_amplification=0.9, order=4)) # timestep loop ------------------------------------------------------- try: from hedge.timestep import times_and_steps step_it = times_and_steps( final_time=1.0, logmgr=logmgr, max_dt_getter=lambda t: op.estimate_timestep( discr, stepper=stepper, t=t, max_eigenvalue=max_eigval[0])) for step, t, dt in step_it: if step % 5 == 0: #if False: visf = vis.make_file("vortex-%d-%04d" % (order, step)) #true_fields = vortex.volume_interpolant(t, discr) #from pyvisfile.silo import DB_VARTYPE_VECTOR vis.add_data( visf, [ ("rho", discr.convert_volume(op.rho(fields), kind="numpy")), ("e", discr.convert_volume(op.e(fields), kind="numpy")), ("rho_u", discr.convert_volume(op.rho_u(fields), kind="numpy")), ("u", discr.convert_volume(op.u(fields), kind="numpy")), #("true_rho", op.rho(true_fields)), #("true_e", op.e(true_fields)), #("true_rho_u", op.rho_u(true_fields)), #("true_u", op.u(true_fields)), #("rhs_rho", op.rho(rhs_fields)), #("rhs_e", op.e(rhs_fields)), #("rhs_rho_u", op.rho_u(rhs_fields)), ], #expressions=[ #("diff_rho", "rho-true_rho"), #("diff_e", "e-true_e"), #("diff_rho_u", "rho_u-true_rho_u", DB_VARTYPE_VECTOR), #("p", "0.4*(e- 0.5*(rho_u*u))"), #], time=t, step=step) visf.close() fields = stepper(fields, t, dt, rhs) # fields = limiter(fields) # fields = mode_filter(fields) assert not numpy.isnan(numpy.sum(fields[0])) finally: vis.close() logmgr.close() discr.close() # not solution, just to check against when making code changes true_fields = sod_field.volume_interpolant(t, discr) print discr.norm(fields - true_fields)
def main(): from hedge.backends import guess_run_context rcon = guess_run_context() from hedge.tools import to_obj_array if rcon.is_head_rank: from hedge.mesh.generator import make_rect_mesh mesh = make_rect_mesh((-5, -5), (5, 5), max_area=0.01) mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() for order in [1]: discr = rcon.make_discretization(mesh_data, order=order, default_scalar_type=numpy.float64) from hedge.visualization import SiloVisualizer, VtkVisualizer vis = VtkVisualizer(discr, rcon, "Sod2D-%d" % order) # vis = SiloVisualizer(discr, rcon) sod_field = Sod(gamma=1.4) fields = sod_field.volume_interpolant(0, discr) from hedge.models.gas_dynamics import GasDynamicsOperator from hedge.mesh import TAG_ALL op = GasDynamicsOperator( dimensions=2, gamma=sod_field.gamma, mu=0.0, prandtl=sod_field.prandtl, bc_inflow=sod_field, bc_outflow=sod_field, bc_noslip=sod_field, inflow_tag=TAG_ALL, source=None, ) euler_ex = op.bind(discr) max_eigval = [0] def rhs(t, q): ode_rhs, speed = euler_ex(t, q) max_eigval[0] = speed return ode_rhs rhs(0, fields) if rcon.is_head_rank: print "---------------------------------------------" print "order %d" % order print "---------------------------------------------" print "#elements=", len(mesh.elements) # limiter setup ------------------------------------------------------------ from hedge.models.gas_dynamics import SlopeLimiter1NEuler limiter = SlopeLimiter1NEuler(discr, sod_field.gamma, 2, op) # integrator setup--------------------------------------------------------- from hedge.timestep import SSPRK3TimeStepper, RK4TimeStepper stepper = SSPRK3TimeStepper(limiter=limiter) # stepper = SSPRK3TimeStepper() # stepper = RK4TimeStepper() # diagnostics setup --------------------------------------------------- from pytools.log import LogManager, add_general_quantities, add_simulation_quantities, add_run_info logmgr = LogManager("euler-%d.dat" % order, "w", rcon.communicator) add_run_info(logmgr) add_general_quantities(logmgr) add_simulation_quantities(logmgr) discr.add_instrumentation(logmgr) stepper.add_instrumentation(logmgr) logmgr.add_watches(["step.max", "t_sim.max", "t_step.max"]) # filter setup------------------------------------------------------------- from hedge.discretization import Filter, ExponentialFilterResponseFunction mode_filter = Filter(discr, ExponentialFilterResponseFunction(min_amplification=0.9, order=4)) # timestep loop ------------------------------------------------------- try: from hedge.timestep import times_and_steps step_it = times_and_steps( final_time=1.0, logmgr=logmgr, max_dt_getter=lambda t: op.estimate_timestep(discr, stepper=stepper, t=t, max_eigenvalue=max_eigval[0]), ) for step, t, dt in step_it: if step % 5 == 0: # if False: visf = vis.make_file("vortex-%d-%04d" % (order, step)) # true_fields = vortex.volume_interpolant(t, discr) # from pyvisfile.silo import DB_VARTYPE_VECTOR vis.add_data( visf, [ ("rho", discr.convert_volume(op.rho(fields), kind="numpy")), ("e", discr.convert_volume(op.e(fields), kind="numpy")), ("rho_u", discr.convert_volume(op.rho_u(fields), kind="numpy")), ("u", discr.convert_volume(op.u(fields), kind="numpy")), # ("true_rho", op.rho(true_fields)), # ("true_e", op.e(true_fields)), # ("true_rho_u", op.rho_u(true_fields)), # ("true_u", op.u(true_fields)), # ("rhs_rho", op.rho(rhs_fields)), # ("rhs_e", op.e(rhs_fields)), # ("rhs_rho_u", op.rho_u(rhs_fields)), ], # expressions=[ # ("diff_rho", "rho-true_rho"), # ("diff_e", "e-true_e"), # ("diff_rho_u", "rho_u-true_rho_u", DB_VARTYPE_VECTOR), # ("p", "0.4*(e- 0.5*(rho_u*u))"), # ], time=t, step=step, ) visf.close() fields = stepper(fields, t, dt, rhs) # fields = limiter(fields) # fields = mode_filter(fields) assert not numpy.isnan(numpy.sum(fields[0])) finally: vis.close() logmgr.close() discr.close() # not solution, just to check against when making code changes true_fields = sod_field.volume_interpolant(t, discr) print discr.norm(fields - true_fields)
def main(write_output=True, dir_tag=TAG_NONE, neu_tag=TAG_NONE, rad_tag=TAG_ALL, flux_type_arg="upwind", dtype=np.float64, debug=[]): from math import sin, cos, pi, exp, sqrt # noqa from hedge.backends import guess_run_context rcon = guess_run_context() dim = 2 if dim == 1: if rcon.is_head_rank: from hedge.mesh.generator import make_uniform_1d_mesh mesh = make_uniform_1d_mesh(-10, 10, 500) elif dim == 2: from hedge.mesh.generator import make_rect_mesh if rcon.is_head_rank: mesh = make_rect_mesh(a=(-0.5, -0.5), b=(0.5, 0.5), max_area=0.008) elif dim == 3: if rcon.is_head_rank: from hedge.mesh.generator import make_ball_mesh mesh = make_ball_mesh(max_volume=0.0005) else: raise RuntimeError("bad number of dimensions") if rcon.is_head_rank: print "%d elements" % len(mesh.elements) mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() from hedge.timestep.runge_kutta import LSRK4TimeStepper stepper = LSRK4TimeStepper(dtype=dtype) from hedge.models.wave import StrongWaveOperator from hedge.mesh import TAG_ALL, TAG_NONE # noqa source_center = np.array([0.1, 0.22]) source_width = 0.05 source_omega = 3 import hedge.optemplate as sym sym_x = sym.nodes(2) sym_source_center_dist = sym_x - source_center op = StrongWaveOperator( -1, dim, source_f=sym.CFunction("sin")( source_omega * sym.ScalarParameter("t")) * sym.CFunction("exp")( -np.dot(sym_source_center_dist, sym_source_center_dist) / source_width**2), dirichlet_tag=dir_tag, neumann_tag=neu_tag, radiation_tag=rad_tag, flux_type=flux_type_arg) discr = rcon.make_discretization(mesh_data, order=4, debug=debug, default_scalar_type=dtype, tune_for=op.op_template()) from hedge.visualization import VtkVisualizer if write_output: vis = VtkVisualizer(discr, rcon, "fld") from hedge.tools import join_fields fields = join_fields( discr.volume_zeros(dtype=dtype), [discr.volume_zeros(dtype=dtype) for i in range(discr.dimensions)]) # {{{ diagnostics setup from pytools.log import LogManager, \ add_general_quantities, \ add_simulation_quantities, \ add_run_info if write_output: log_file_name = "wave.dat" else: log_file_name = None logmgr = LogManager(log_file_name, "w", rcon.communicator) add_run_info(logmgr) add_general_quantities(logmgr) add_simulation_quantities(logmgr) discr.add_instrumentation(logmgr) from pytools.log import IntervalTimer vis_timer = IntervalTimer("t_vis", "Time spent visualizing") logmgr.add_quantity(vis_timer) stepper.add_instrumentation(logmgr) from hedge.log import LpNorm u_getter = lambda: fields[0] logmgr.add_quantity(LpNorm(u_getter, discr, 1, name="l1_u")) logmgr.add_quantity(LpNorm(u_getter, discr, name="l2_u")) logmgr.add_watches(["step.max", "t_sim.max", "l2_u", "t_step.max"]) # }}} # {{{ timestep loop rhs = op.bind(discr) try: from hedge.timestep import times_and_steps step_it = times_and_steps( final_time=4, logmgr=logmgr, max_dt_getter=lambda t: op.estimate_timestep( discr, stepper=stepper, t=t, fields=fields)) for step, t, dt in step_it: if step % 10 == 0 and write_output: visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [ ("u", discr.convert_volume(fields[0], kind="numpy")), ("v", discr.convert_volume(fields[1:], kind="numpy")), ], time=t, step=step) visf.close() fields = stepper(fields, t, dt, rhs) assert discr.norm(fields) < 1 assert fields[0].dtype == dtype finally: if write_output: vis.close() logmgr.close() discr.close()
def main(write_output=True, dtype=np.float32): from hedge.backends import guess_run_context rcon = guess_run_context() from hedge.mesh.generator import make_rect_mesh if rcon.is_head_rank: h_fac = 1 mesh = make_rect_mesh(a=(0, 0), b=(1, 1), max_area=h_fac**2 * 1e-4, periodicity=(True, True), subdivisions=(int(70 / h_fac), int(70 / h_fac))) from hedge.models.gas_dynamics.lbm import \ D2Q9LBMMethod, LatticeBoltzmannOperator op = LatticeBoltzmannOperator(D2Q9LBMMethod(), lbm_delta_t=0.001, nu=1e-4) if rcon.is_head_rank: print "%d elements" % len(mesh.elements) mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() discr = rcon.make_discretization(mesh_data, order=3, default_scalar_type=dtype, debug=["cuda_no_plan"]) from hedge.timestep.runge_kutta import LSRK4TimeStepper stepper = LSRK4TimeStepper( dtype=dtype, #vector_primitive_factory=discr.get_vector_primitive_factory() ) from hedge.visualization import VtkVisualizer if write_output: vis = VtkVisualizer(discr, rcon, "fld") from hedge.data import CompiledExpressionData def ic_expr(t, x, fields): from hedge.optemplate import CFunction from pymbolic.primitives import IfPositive from pytools.obj_array import make_obj_array tanh = CFunction("tanh") sin = CFunction("sin") rho = 1 u0 = 0.05 w = 0.05 delta = 0.05 from hedge.optemplate.primitives import make_common_subexpression as cse u = cse( make_obj_array([ IfPositive(x[1] - 1 / 2, u0 * tanh(4 * (3 / 4 - x[1]) / w), u0 * tanh(4 * (x[1] - 1 / 4) / w)), u0 * delta * sin(2 * np.pi * (x[0] + 1 / 4)) ]), "u") return make_obj_array([ op.method.f_equilibrium(rho, alpha, u) for alpha in range(len(op.method)) ]) # timestep loop ----------------------------------------------------------- stream_rhs = op.bind_rhs(discr) collision_update = op.bind(discr, op.collision_update) get_rho = op.bind(discr, op.rho) get_rho_u = op.bind(discr, op.rho_u) f_bar = CompiledExpressionData(ic_expr).volume_interpolant(0, discr) from hedge.discretization import ExponentialFilterResponseFunction from hedge.optemplate.operators import FilterOperator mode_filter = FilterOperator( ExponentialFilterResponseFunction(min_amplification=0.9, order=4))\ .bind(discr) final_time = 1000 try: lbm_dt = op.lbm_delta_t dg_dt = op.estimate_timestep(discr, stepper=stepper) print dg_dt dg_steps_per_lbm_step = int(np.ceil(lbm_dt / dg_dt)) dg_dt = lbm_dt / dg_steps_per_lbm_step lbm_steps = int(final_time // op.lbm_delta_t) for step in xrange(lbm_steps): t = step * lbm_dt if step % 100 == 0 and write_output: visf = vis.make_file("fld-%04d" % step) rho = get_rho(f_bar) rho_u = get_rho_u(f_bar) vis.add_data( visf, [("fbar%d" % i, discr.convert_volume(f_bar_i, "numpy")) for i, f_bar_i in enumerate(f_bar)] + [ ("rho", discr.convert_volume(rho, "numpy")), ("rho_u", discr.convert_volume(rho_u, "numpy")), ], time=t, step=step) visf.close() print "step=%d, t=%f" % (step, t) f_bar = collision_update(f_bar) for substep in range(dg_steps_per_lbm_step): f_bar = stepper(f_bar, t + substep * dg_dt, dg_dt, stream_rhs) #f_bar = mode_filter(f_bar) finally: if write_output: vis.close() discr.close()
def main(write_output=True, \ dir_tag=TAG_NONE, \ neu_tag=TAG_NONE,\ rad_tag=TAG_ALL, flux_type_arg="upwind"): from math import sin, cos, pi, exp, sqrt from hedge.backends import guess_run_context rcon = guess_run_context() dim = 2 if dim == 1: if rcon.is_head_rank: from hedge.mesh.generator import make_uniform_1d_mesh mesh = make_uniform_1d_mesh(-10, 10, 500) elif dim == 2: from hedge.mesh.generator import make_rect_mesh if rcon.is_head_rank: mesh = make_rect_mesh(a=(-1,-1),b=(1,1),max_area=0.003) elif dim == 3: if rcon.is_head_rank: from hedge.mesh.generator import make_ball_mesh mesh = make_ball_mesh(max_volume=0.0005) else: raise RuntimeError, "bad number of dimensions" if rcon.is_head_rank: print "%d elements" % len(mesh.elements) mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() discr = rcon.make_discretization(mesh_data, order=4) from hedge.timestep import RK4TimeStepper stepper = RK4TimeStepper() from hedge.visualization import VtkVisualizer if write_output: vis = VtkVisualizer(discr, rcon, "fld") def source_u(x, el): x = x - numpy.array([0.7, 0.4]) return exp(-numpy.dot(x, x)*256) def c_speed(x, el): if la.norm(x) < 0.4: return 1 else: return 0.5 from hedge.models.wave import VariableVelocityStrongWaveOperator from hedge.data import \ TimeIntervalGivenFunction, \ make_tdep_given from hedge.mesh import TAG_ALL, TAG_NONE op = VariableVelocityStrongWaveOperator( make_tdep_given(c_speed), discr.dimensions, source=TimeIntervalGivenFunction( make_tdep_given(source_u), 0, 0.1), dirichlet_tag=dir_tag, neumann_tag=neu_tag, radiation_tag=rad_tag, flux_type=flux_type_arg ) from hedge.tools import join_fields fields = join_fields(discr.volume_zeros(), [discr.volume_zeros() for i in range(discr.dimensions)]) # diagnostics setup ------------------------------------------------------- from pytools.log import LogManager, \ add_general_quantities, \ add_simulation_quantities, \ add_run_info if write_output: log_file_name = "wave.dat" else: log_file_name = None logmgr = LogManager(log_file_name, "w", rcon.communicator) add_run_info(logmgr) add_general_quantities(logmgr) add_simulation_quantities(logmgr) discr.add_instrumentation(logmgr) from pytools.log import IntervalTimer vis_timer = IntervalTimer("t_vis", "Time spent visualizing") logmgr.add_quantity(vis_timer) stepper.add_instrumentation(logmgr) from hedge.log import Integral, LpNorm u_getter = lambda: fields[0] logmgr.add_quantity(LpNorm(u_getter, discr, 1, name="l1_u")) logmgr.add_quantity(LpNorm(u_getter, discr, name="l2_u")) logmgr.add_watches(["step.max", "t_sim.max", "l2_u", "t_step.max"]) # timestep loop ----------------------------------------------------------- rhs = op.bind(discr) try: dt = op.estimate_timestep(discr, stepper=stepper, fields=fields) if flux_type_arg == "central": dt *= 0.25 from hedge.timestep import times_and_steps step_it = times_and_steps(final_time=3, logmgr=logmgr, max_dt_getter=lambda t: dt) for step, t, dt in step_it: if step % 10 == 0 and write_output: visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [ ("u", fields[0]), ("v", fields[1:]), ("c", op.c.volume_interpolant(0, discr)), ], time=t, step=step) visf.close() fields = stepper(fields, t, dt, rhs) assert discr.norm(fields) < 1 finally: if write_output: vis.close() logmgr.close() discr.close()
def main(write_output=True): from math import sin, exp, sqrt from hedge.mesh.generator import make_rect_mesh mesh = make_rect_mesh(a=(-0.5,-0.5),b=(0.5,0.5),max_area=0.008) from hedge.backends.jit import Discretization discr = Discretization(mesh, order=4) from hedge.visualization import VtkVisualizer vis = VtkVisualizer(discr, None, "fld") def source_u(x, el): x = x - numpy.array([0.1,0.22]) return exp(-numpy.dot(x, x)*128) from hedge.data import \ make_tdep_given, \ TimeHarmonicGivenFunction, \ TimeIntervalGivenFunction from hedge.models.wave import StrongWaveOperator from hedge.mesh import TAG_ALL, TAG_NONE op = StrongWaveOperator(-1, discr.dimensions, source_f=TimeIntervalGivenFunction( TimeHarmonicGivenFunction( make_tdep_given(source_u), omega=10), 0, 1), dirichlet_tag=TAG_NONE, neumann_tag=TAG_NONE, radiation_tag=TAG_ALL, flux_type="upwind") from hedge.tools import join_fields fields = join_fields(discr.volume_zeros(), [discr.volume_zeros() for i in range(discr.dimensions)]) from hedge.timestep import RK4TimeStepper stepper = RK4TimeStepper() dt = op.estimate_timestep(discr, stepper=stepper, fields=fields) nsteps = int(1/dt) print "dt=%g nsteps=%d" % (dt, nsteps) rhs = op.bind(discr) for step in range(nsteps): t = step*dt if step % 50 == 0 and write_output: print step, t, discr.norm(fields[0]) visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [ ("u", fields[0]), ("v", fields[1:]), ], time=t, step=step) visf.close() fields = stepper(fields, t, dt, rhs) vis.close()
def main(write_output=True, dir_tag=TAG_NONE, neu_tag=TAG_NONE, rad_tag=TAG_ALL, flux_type_arg="upwind", dtype=np.float64, debug=[]): from math import sin, cos, pi, exp, sqrt # noqa from hedge.backends import guess_run_context rcon = guess_run_context() dim = 2 if dim == 1: if rcon.is_head_rank: from hedge.mesh.generator import make_uniform_1d_mesh mesh = make_uniform_1d_mesh(-10, 10, 500) elif dim == 2: from hedge.mesh.generator import make_rect_mesh if rcon.is_head_rank: mesh = make_rect_mesh(a=(-0.5, -0.5), b=(0.5, 0.5), max_area=0.008) elif dim == 3: if rcon.is_head_rank: from hedge.mesh.generator import make_ball_mesh mesh = make_ball_mesh(max_volume=0.0005) else: raise RuntimeError("bad number of dimensions") if rcon.is_head_rank: print "%d elements" % len(mesh.elements) mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() from hedge.timestep.runge_kutta import LSRK4TimeStepper stepper = LSRK4TimeStepper(dtype=dtype) from hedge.models.wave import StrongWaveOperator from hedge.mesh import TAG_ALL, TAG_NONE # noqa source_center = np.array([0.1, 0.22]) source_width = 0.05 source_omega = 3 import hedge.optemplate as sym sym_x = sym.nodes(2) sym_source_center_dist = sym_x - source_center op = StrongWaveOperator(-1, dim, source_f= sym.CFunction("sin")(source_omega*sym.ScalarParameter("t")) * sym.CFunction("exp")( -np.dot(sym_source_center_dist, sym_source_center_dist) / source_width**2), dirichlet_tag=dir_tag, neumann_tag=neu_tag, radiation_tag=rad_tag, flux_type=flux_type_arg ) discr = rcon.make_discretization(mesh_data, order=4, debug=debug, default_scalar_type=dtype, tune_for=op.op_template()) from hedge.visualization import VtkVisualizer if write_output: vis = VtkVisualizer(discr, rcon, "fld") from hedge.tools import join_fields fields = join_fields(discr.volume_zeros(dtype=dtype), [discr.volume_zeros(dtype=dtype) for i in range(discr.dimensions)]) # {{{ diagnostics setup from pytools.log import LogManager, \ add_general_quantities, \ add_simulation_quantities, \ add_run_info if write_output: log_file_name = "wave.dat" else: log_file_name = None logmgr = LogManager(log_file_name, "w", rcon.communicator) add_run_info(logmgr) add_general_quantities(logmgr) add_simulation_quantities(logmgr) discr.add_instrumentation(logmgr) from pytools.log import IntervalTimer vis_timer = IntervalTimer("t_vis", "Time spent visualizing") logmgr.add_quantity(vis_timer) stepper.add_instrumentation(logmgr) from hedge.log import LpNorm u_getter = lambda: fields[0] logmgr.add_quantity(LpNorm(u_getter, discr, 1, name="l1_u")) logmgr.add_quantity(LpNorm(u_getter, discr, name="l2_u")) logmgr.add_watches(["step.max", "t_sim.max", "l2_u", "t_step.max"]) # }}} # {{{ timestep loop rhs = op.bind(discr) try: from hedge.timestep import times_and_steps step_it = times_and_steps( final_time=4, logmgr=logmgr, max_dt_getter=lambda t: op.estimate_timestep(discr, stepper=stepper, t=t, fields=fields)) for step, t, dt in step_it: if step % 10 == 0 and write_output: visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [ ("u", discr.convert_volume(fields[0], kind="numpy")), ("v", discr.convert_volume(fields[1:], kind="numpy")), ], time=t, step=step) visf.close() fields = stepper(fields, t, dt, rhs) assert discr.norm(fields) < 1 assert fields[0].dtype == dtype finally: if write_output: vis.close() logmgr.close() discr.close()
def main(write_output=True, flux_type_arg="upwind", #case = CenteredStationaryTestCase(), #case = OffCenterStationaryTestCase(), #case = OffCenterMigratingTestCase(), case = ExactTestCase(), ): from hedge.backends import guess_run_context rcon = guess_run_context() order = 3 if rcon.is_head_rank: if True: from hedge.mesh.generator import make_uniform_1d_mesh mesh = make_uniform_1d_mesh(case.a, case.b, 20, periodic=True) else: from hedge.mesh.generator import make_rect_mesh print (pi*2)/(11*5*2) mesh = make_rect_mesh((-pi, -1), (pi, 1), periodicity=(True, True), subdivisions=(11,5), max_area=(pi*2)/(11*5*2) ) if rcon.is_head_rank: mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() discr = rcon.make_discretization(mesh_data, order=order, quad_min_degrees={"quad": 3*order}) if write_output: from hedge.visualization import VtkVisualizer vis = VtkVisualizer(discr, rcon, "fld") # operator setup ---------------------------------------------------------- from hedge.second_order import IPDGSecondDerivative from hedge.models.burgers import BurgersOperator op = BurgersOperator(mesh.dimensions, viscosity_scheme=IPDGSecondDerivative()) if rcon.is_head_rank: print "%d elements" % len(discr.mesh.elements) # exact solution ---------------------------------------------------------- import pymbolic var = pymbolic.var u = discr.interpolate_volume_function(lambda x, el: case.u0(x[0])) # diagnostics setup ------------------------------------------------------- from pytools.log import LogManager, \ add_general_quantities, \ add_simulation_quantities, \ add_run_info if write_output: log_file_name = "burgers.dat" else: log_file_name = None logmgr = LogManager(log_file_name, "w", rcon.communicator) add_run_info(logmgr) add_general_quantities(logmgr) add_simulation_quantities(logmgr) discr.add_instrumentation(logmgr) from hedge.log import LpNorm u_getter = lambda: u logmgr.add_quantity(LpNorm(u_getter, discr, p=1, name="l1_u")) logmgr.add_watches(["step.max", "t_sim.max", "l1_u", "t_step.max"]) # timestep loop ----------------------------------------------------------- rhs = op.bind(discr) from hedge.timestep.runge_kutta import ODE45TimeStepper, LSRK4TimeStepper stepper = ODE45TimeStepper() stepper.add_instrumentation(logmgr) try: from hedge.timestep import times_and_steps # for visc=0.01 #stab_fac = 0.1 # RK4 #stab_fac = 1.6 # dumka3(3), central #stab_fac = 3 # dumka3(4), central #stab_fac = 0.01 # RK4 stab_fac = 0.2 # dumka3(3), central #stab_fac = 3 # dumka3(4), central dt = stab_fac*op.estimate_timestep(discr, stepper=LSRK4TimeStepper(), t=0, fields=u) step_it = times_and_steps( final_time=case.final_time, logmgr=logmgr, max_dt_getter=lambda t: dt) from hedge.optemplate import InverseVandermondeOperator inv_vdm = InverseVandermondeOperator().bind(discr) for step, t, dt in step_it: if step % 3 == 0 and write_output: if hasattr(case, "u_exact"): extra_fields = [ ("u_exact", discr.interpolate_volume_function( lambda x, el: case.u_exact(x[0], t)))] else: extra_fields = [] visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [ ("u", u), ] + extra_fields, time=t, step=step) visf.close() u = stepper(u, t, dt, rhs) if isinstance(case, ExactTestCase): assert discr.norm(u, 1) < 50 finally: if write_output: vis.close() logmgr.save()
def main(write_output=True, flux_type_arg="central", use_quadrature=True, final_time=20): from math import sin, cos, pi, sqrt from hedge.backends import guess_run_context rcon = guess_run_context() # mesh setup -------------------------------------------------------------- if rcon.is_head_rank: #from hedge.mesh.generator import make_disk_mesh #mesh = make_disk_mesh() from hedge.mesh.generator import make_rect_mesh mesh = make_rect_mesh(a=(-1, -1), b=(1, 1), max_area=0.008) if rcon.is_head_rank: mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() # space-time-dependent-velocity-field ------------------------------------- # simple vortex class TimeDependentVField: """ `TimeDependentVField` is a callable expecting `(x, t)` representing space and time `x` is of the length of the spatial dimension and `t` is the time.""" shape = (2, ) def __call__(self, pt, el, t): x, y = pt # Correction-Factor to make the speed zero on the on the boundary #fac = (1-x**2)*(1-y**2) fac = 1. return numpy.array([-y * fac, x * fac]) * cos(pi * t) class VField: """ `VField` is a callable expecting `(x)` representing space `x` is of the length of the spatial dimension.""" shape = (2, ) def __call__(self, pt, el): x, y = pt # Correction-Factor to make the speed zero on the on the boundary #fac = (1-x**2)*(1-y**2) fac = 1. return numpy.array([-y * fac, x * fac]) # space-time-dependent State BC (optional)----------------------------------- class TimeDependentBc_u: """ space and time dependent BC for state u""" def __call__(self, pt, el, t): x, y = pt if t <= 0.5: if x > 0: return 1 else: return 0 else: return 0 class Bc_u: """ Only space dependent BC for state u""" def __call__(seld, pt, el): x, y = pt if x > 0: return 1 else: return 0 # operator setup ---------------------------------------------------------- # In the operator setup it is possible to switch between a only space # dependent velocity field `VField` or a time and space dependent # `TimeDependentVField`. # For `TimeDependentVField`: advec_v=TimeDependentGivenFunction(VField()) # For `VField`: advec_v=TimeConstantGivenFunction(GivenFunction(VField())) # Same for the Bc_u Function! If you don't define Bc_u then the BC for u = 0. from hedge.data import \ ConstantGivenFunction, \ TimeConstantGivenFunction, \ TimeDependentGivenFunction, \ GivenFunction from hedge.models.advection import VariableCoefficientAdvectionOperator op = VariableCoefficientAdvectionOperator( mesh.dimensions, #advec_v=TimeDependentGivenFunction( # TimeDependentVField()), advec_v=TimeConstantGivenFunction(GivenFunction(VField())), #bc_u_f=TimeDependentGivenFunction( # TimeDependentBc_u()), bc_u_f=TimeConstantGivenFunction(GivenFunction(Bc_u())), flux_type=flux_type_arg) # discretization setup ---------------------------------------------------- order = 5 if use_quadrature: quad_min_degrees = {"quad": 3 * order} else: quad_min_degrees = {} discr = rcon.make_discretization( mesh_data, order=order, default_scalar_type=numpy.float64, debug=["cuda_no_plan"], quad_min_degrees=quad_min_degrees, tune_for=op.op_template(), ) vis_discr = discr # visualization setup ----------------------------------------------------- from hedge.visualization import VtkVisualizer if write_output: vis = VtkVisualizer(vis_discr, rcon, "fld") # initial condition ------------------------------------------------------- if True: def initial(pt, el): # Gauss pulse from math import exp x = (pt - numpy.array([0.3, 0.5])) * 8 return exp(-numpy.dot(x, x)) else: def initial(pt, el): # Rectangle x, y = pt if abs(x) < 0.5 and abs(y) < 0.2: return 2 else: return 1 u = discr.interpolate_volume_function(initial) # timestep setup ---------------------------------------------------------- from hedge.timestep.runge_kutta import LSRK4TimeStepper stepper = LSRK4TimeStepper( vector_primitive_factory=discr.get_vector_primitive_factory()) if rcon.is_head_rank: print "%d elements" % len(discr.mesh.elements) # filter setup------------------------------------------------------------- from hedge.discretization import ExponentialFilterResponseFunction from hedge.optemplate.operators import FilterOperator mode_filter = FilterOperator( ExponentialFilterResponseFunction(min_amplification=0.9,order=4))\ .bind(discr) # diagnostics setup ------------------------------------------------------- from pytools.log import LogManager, \ add_general_quantities, \ add_simulation_quantities, \ add_run_info if write_output: log_file_name = "space-dep.dat" else: log_file_name = None logmgr = LogManager(log_file_name, "w", rcon.communicator) add_run_info(logmgr) add_general_quantities(logmgr) add_simulation_quantities(logmgr) discr.add_instrumentation(logmgr) stepper.add_instrumentation(logmgr) from hedge.log import Integral, LpNorm u_getter = lambda: u logmgr.add_quantity(Integral(u_getter, discr, name="int_u")) logmgr.add_quantity(LpNorm(u_getter, discr, p=1, name="l1_u")) logmgr.add_quantity(LpNorm(u_getter, discr, name="l2_u")) logmgr.add_watches(["step.max", "t_sim.max", "l2_u", "t_step.max"]) # Initialize v for data output: v = op.advec_v.volume_interpolant(0, discr) # timestep loop ----------------------------------------------------------- rhs = op.bind(discr) try: from hedge.timestep import times_and_steps step_it = times_and_steps(final_time=final_time, logmgr=logmgr, max_dt_getter=lambda t: op.estimate_timestep( discr, stepper=stepper, t=t, fields=u)) for step, t, dt in step_it: if step % 10 == 0 and write_output: visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [("u", discr.convert_volume(u, kind="numpy")), ("v", discr.convert_volume(v, kind="numpy"))], time=t, step=step) visf.close() u = stepper(u, t, dt, rhs) # We're feeding in a discontinuity through the BCs. # Quadrature does not help with shock capturing-- # therefore we do need to filter here, regardless # of whether quadrature is enabled. u = mode_filter(u) assert discr.norm(u) < 10 finally: if write_output: vis.close() logmgr.close() discr.close()
def test_cuda_volume_quadrature(): from hedge.mesh.generator import make_rect_mesh mesh = make_rect_mesh(a=(-1,-1),b=(1,1),max_area=0.08) from hedge.backends import guess_run_context cpu_rcon = guess_run_context(['jit']) gpu_rcon = guess_run_context(['cuda']) order = 4 quad_min_degrees = {"quad": 3*order} cpu_discr, gpu_discr = [ rcon.make_discretization(mesh, order=order, default_scalar_type=numpy.float64, debug=["cuda_no_plan", "cuda_no_microblock", ], quad_min_degrees=quad_min_degrees ) for rcon in [cpu_rcon, gpu_rcon]] from math import sin, cos def f(x, el): return sin(x[0])*cos(x[1]) cpu_field, gpu_field = [ discr.interpolate_volume_function(f) for discr in [cpu_discr, gpu_discr]] def make_optemplate(): from hedge.optemplate.operators import QuadratureGridUpsampler from hedge.optemplate import Field, make_stiffness_t u = Field("u") qu = QuadratureGridUpsampler("quad")(u) return make_stiffness_t(2)[0](Field("intercept")(qu)) saved_vectors = [] def intercept(x): saved_vectors.append(x) return x for discr in [cpu_discr, gpu_discr]: discr.add_function("intercept", intercept) opt = make_optemplate() cpu_bound, gpu_bound = [discr.compile(make_optemplate()) for discr in [cpu_discr, gpu_discr]] cpu_result = cpu_bound(u=cpu_field) gpu_result = gpu_bound(u=gpu_field) cpu_ivec, gpu_ivec = saved_vectors gpu_ivec_on_host = gpu_ivec.get()[gpu_discr._gpu_volume_embedding("quad")] ierr = cpu_ivec-gpu_ivec_on_host assert la.norm(ierr) < 5e-15 gpu_result_on_host = gpu_discr.convert_volume(gpu_result, kind="numpy") err = cpu_result-gpu_result_on_host assert la.norm(err) < 2e-14 cpu_discr.close() gpu_discr.close()
def main(write_output=True, flux_type_arg="central", use_quadrature=True, final_time=20): from math import sin, cos, pi, sqrt from hedge.backends import guess_run_context rcon = guess_run_context() # mesh setup -------------------------------------------------------------- if rcon.is_head_rank: #from hedge.mesh.generator import make_disk_mesh #mesh = make_disk_mesh() from hedge.mesh.generator import make_rect_mesh mesh = make_rect_mesh(a=(-1,-1),b=(1,1),max_area=0.008) if rcon.is_head_rank: mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() # space-time-dependent-velocity-field ------------------------------------- # simple vortex class TimeDependentVField: """ `TimeDependentVField` is a callable expecting `(x, t)` representing space and time `x` is of the length of the spatial dimension and `t` is the time.""" shape = (2,) def __call__(self, pt, el, t): x, y = pt # Correction-Factor to make the speed zero on the on the boundary #fac = (1-x**2)*(1-y**2) fac = 1. return numpy.array([-y*fac, x*fac]) * cos(pi*t) class VField: """ `VField` is a callable expecting `(x)` representing space `x` is of the length of the spatial dimension.""" shape = (2,) def __call__(self, pt, el): x, y = pt # Correction-Factor to make the speed zero on the on the boundary #fac = (1-x**2)*(1-y**2) fac = 1. return numpy.array([-y*fac, x*fac]) # space-time-dependent State BC (optional)----------------------------------- class TimeDependentBc_u: """ space and time dependent BC for state u""" def __call__(self, pt, el, t): x, y = pt if t <= 0.5: if x > 0: return 1 else: return 0 else: return 0 class Bc_u: """ Only space dependent BC for state u""" def __call__(seld, pt, el): x, y = pt if x > 0: return 1 else: return 0 # operator setup ---------------------------------------------------------- # In the operator setup it is possible to switch between a only space # dependent velocity field `VField` or a time and space dependent # `TimeDependentVField`. # For `TimeDependentVField`: advec_v=TimeDependentGivenFunction(VField()) # For `VField`: advec_v=TimeConstantGivenFunction(GivenFunction(VField())) # Same for the Bc_u Function! If you don't define Bc_u then the BC for u = 0. from hedge.data import \ ConstantGivenFunction, \ TimeConstantGivenFunction, \ TimeDependentGivenFunction, \ GivenFunction from hedge.models.advection import VariableCoefficientAdvectionOperator op = VariableCoefficientAdvectionOperator(mesh.dimensions, #advec_v=TimeDependentGivenFunction( # TimeDependentVField()), advec_v=TimeConstantGivenFunction( GivenFunction(VField())), #bc_u_f=TimeDependentGivenFunction( # TimeDependentBc_u()), bc_u_f=TimeConstantGivenFunction( GivenFunction(Bc_u())), flux_type=flux_type_arg) # discretization setup ---------------------------------------------------- order = 5 if use_quadrature: quad_min_degrees = {"quad": 3*order} else: quad_min_degrees = {} discr = rcon.make_discretization(mesh_data, order=order, default_scalar_type=numpy.float64, debug=["cuda_no_plan"], quad_min_degrees=quad_min_degrees, tune_for=op.op_template(), ) vis_discr = discr # visualization setup ----------------------------------------------------- from hedge.visualization import VtkVisualizer if write_output: vis = VtkVisualizer(vis_discr, rcon, "fld") # initial condition ------------------------------------------------------- if True: def initial(pt, el): # Gauss pulse from math import exp x = (pt-numpy.array([0.3, 0.5]))*8 return exp(-numpy.dot(x, x)) else: def initial(pt, el): # Rectangle x, y = pt if abs(x) < 0.5 and abs(y) < 0.2: return 2 else: return 1 u = discr.interpolate_volume_function(initial) # timestep setup ---------------------------------------------------------- from hedge.timestep.runge_kutta import LSRK4TimeStepper stepper = LSRK4TimeStepper( vector_primitive_factory=discr.get_vector_primitive_factory()) if rcon.is_head_rank: print "%d elements" % len(discr.mesh.elements) # filter setup------------------------------------------------------------- from hedge.discretization import ExponentialFilterResponseFunction from hedge.optemplate.operators import FilterOperator mode_filter = FilterOperator( ExponentialFilterResponseFunction(min_amplification=0.9,order=4))\ .bind(discr) # diagnostics setup ------------------------------------------------------- from pytools.log import LogManager, \ add_general_quantities, \ add_simulation_quantities, \ add_run_info if write_output: log_file_name = "space-dep.dat" else: log_file_name = None logmgr = LogManager(log_file_name, "w", rcon.communicator) add_run_info(logmgr) add_general_quantities(logmgr) add_simulation_quantities(logmgr) discr.add_instrumentation(logmgr) stepper.add_instrumentation(logmgr) from hedge.log import Integral, LpNorm u_getter = lambda: u logmgr.add_quantity(Integral(u_getter, discr, name="int_u")) logmgr.add_quantity(LpNorm(u_getter, discr, p=1, name="l1_u")) logmgr.add_quantity(LpNorm(u_getter, discr, name="l2_u")) logmgr.add_watches(["step.max", "t_sim.max", "l2_u", "t_step.max"]) # Initialize v for data output: v = op.advec_v.volume_interpolant(0, discr) # timestep loop ----------------------------------------------------------- rhs = op.bind(discr) try: from hedge.timestep import times_and_steps step_it = times_and_steps( final_time=final_time, logmgr=logmgr, max_dt_getter=lambda t: op.estimate_timestep(discr, stepper=stepper, t=t, fields=u)) for step, t, dt in step_it: if step % 10 == 0 and write_output: visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [ ("u", discr.convert_volume(u, kind="numpy")), ("v", discr.convert_volume(v, kind="numpy")) ], time=t, step=step) visf.close() u = stepper(u, t, dt, rhs) # We're feeding in a discontinuity through the BCs. # Quadrature does not help with shock capturing-- # therefore we do need to filter here, regardless # of whether quadrature is enabled. u = mode_filter(u) assert discr.norm(u) < 10 finally: if write_output: vis.close() logmgr.close() discr.close()
#case = OffCenterMigratingTestCase(), case=ExactTestCase(), ): from hedge.backends import guess_run_context rcon = guess_run_context() order = 3 if rcon.is_head_rank: if True: from hedge.mesh.generator import make_uniform_1d_mesh mesh = make_uniform_1d_mesh(case.a, case.b, 20, periodic=True) else: from hedge.mesh.generator import make_rect_mesh print(pi * 2) / (11 * 5 * 2) mesh = make_rect_mesh((-pi, -1), (pi, 1), periodicity=(True, True), subdivisions=(11, 5), max_area=(pi * 2) / (11 * 5 * 2)) if rcon.is_head_rank: mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() discr = rcon.make_discretization(mesh_data, order=order, quad_min_degrees={"quad": 3 * order}) if write_output: from hedge.visualization import VtkVisualizer vis = VtkVisualizer(discr, rcon, "fld")
def main(write_output=True, dir_tag=TAG_NONE, neu_tag=TAG_NONE, rad_tag=TAG_ALL, flux_type_arg="upwind"): from math import sin, cos, pi, exp, sqrt # noqa from hedge.backends import guess_run_context rcon = guess_run_context() dim = 2 if dim == 1: if rcon.is_head_rank: from hedge.mesh.generator import make_uniform_1d_mesh mesh = make_uniform_1d_mesh(-10, 10, 500) elif dim == 2: from hedge.mesh.generator import make_rect_mesh if rcon.is_head_rank: mesh = make_rect_mesh(a=(-1, -1), b=(1, 1), max_area=0.003) elif dim == 3: if rcon.is_head_rank: from hedge.mesh.generator import make_ball_mesh mesh = make_ball_mesh(max_volume=0.0005) else: raise RuntimeError("bad number of dimensions") if rcon.is_head_rank: print "%d elements" % len(mesh.elements) mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() discr = rcon.make_discretization(mesh_data, order=4) from hedge.timestep.runge_kutta import LSRK4TimeStepper stepper = LSRK4TimeStepper() from hedge.visualization import VtkVisualizer if write_output: vis = VtkVisualizer(discr, rcon, "fld") source_center = np.array([0.7, 0.4]) source_width = 1/16 source_omega = 3 import hedge.optemplate as sym sym_x = sym.nodes(2) sym_source_center_dist = sym_x - source_center from hedge.models.wave import VariableVelocityStrongWaveOperator op = VariableVelocityStrongWaveOperator( c=sym.If(sym.Comparison( np.dot(sym_x, sym_x), "<", 0.4**2), 1, 0.5), dimensions=discr.dimensions, source= sym.CFunction("sin")(source_omega*sym.ScalarParameter("t")) * sym.CFunction("exp")( -np.dot(sym_source_center_dist, sym_source_center_dist) / source_width**2), dirichlet_tag=dir_tag, neumann_tag=neu_tag, radiation_tag=rad_tag, flux_type=flux_type_arg ) from hedge.tools import join_fields fields = join_fields(discr.volume_zeros(), [discr.volume_zeros() for i in range(discr.dimensions)]) # {{{ diagnostics setup from pytools.log import LogManager, \ add_general_quantities, \ add_simulation_quantities, \ add_run_info if write_output: log_file_name = "wave.dat" else: log_file_name = None logmgr = LogManager(log_file_name, "w", rcon.communicator) add_run_info(logmgr) add_general_quantities(logmgr) add_simulation_quantities(logmgr) discr.add_instrumentation(logmgr) from pytools.log import IntervalTimer vis_timer = IntervalTimer("t_vis", "Time spent visualizing") logmgr.add_quantity(vis_timer) stepper.add_instrumentation(logmgr) from hedge.log import LpNorm u_getter = lambda: fields[0] logmgr.add_quantity(LpNorm(u_getter, discr, 1, name="l1_u")) logmgr.add_quantity(LpNorm(u_getter, discr, name="l2_u")) logmgr.add_watches(["step.max", "t_sim.max", "l2_u", "t_step.max"]) # }}} # {{{ timestep loop rhs = op.bind(discr) try: from hedge.timestep.stability import \ approximate_rk4_relative_imag_stability_region max_dt = ( 1/discr.compile(op.max_eigenvalue_expr())() * discr.dt_non_geometric_factor() * discr.dt_geometric_factor() * approximate_rk4_relative_imag_stability_region(stepper)) if flux_type_arg == "central": max_dt *= 0.25 from hedge.timestep import times_and_steps step_it = times_and_steps(final_time=3, logmgr=logmgr, max_dt_getter=lambda t: max_dt) for step, t, dt in step_it: if step % 10 == 0 and write_output: visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [ ("u", fields[0]), ("v", fields[1:]), ], time=t, step=step) visf.close() fields = stepper(fields, t, dt, rhs) assert discr.norm(fields) < 1 finally: if write_output: vis.close() logmgr.close() discr.close()
def main(write_output=True): from math import sin, exp, sqrt # noqa from hedge.mesh.generator import make_rect_mesh mesh = make_rect_mesh(a=(-0.5, -0.5), b=(0.5, 0.5), max_area=0.008) from hedge.backends.jit import Discretization discr = Discretization(mesh, order=4) from hedge.visualization import VtkVisualizer vis = VtkVisualizer(discr, None, "fld") source_center = np.array([0.1, 0.22]) source_width = 0.05 source_omega = 3 import hedge.optemplate as sym sym_x = sym.nodes(2) sym_source_center_dist = sym_x - source_center from hedge.models.wave import StrongWaveOperator from hedge.mesh import TAG_ALL, TAG_NONE op = StrongWaveOperator(-0.1, discr.dimensions, source_f= sym.CFunction("sin")(source_omega*sym.ScalarParameter("t")) * sym.CFunction("exp")( -np.dot(sym_source_center_dist, sym_source_center_dist) / source_width**2), dirichlet_tag=TAG_NONE, neumann_tag=TAG_NONE, radiation_tag=TAG_ALL, flux_type="upwind") from hedge.tools import join_fields fields = join_fields(discr.volume_zeros(), [discr.volume_zeros() for i in range(discr.dimensions)]) from hedge.timestep.runge_kutta import LSRK4TimeStepper stepper = LSRK4TimeStepper() dt = op.estimate_timestep(discr, stepper=stepper, fields=fields) nsteps = int(10/dt) print "dt=%g nsteps=%d" % (dt, nsteps) rhs = op.bind(discr) for step in range(nsteps): t = step*dt if step % 10 == 0 and write_output: print step, t, discr.norm(fields[0]) visf = vis.make_file("fld-%04d" % step) vis.add_data(visf, [("u", fields[0]), ("v", fields[1:]), ], time=t, step=step) visf.close() fields = stepper(fields, t, dt, rhs) vis.close()
def main(write_output=True, dtype=np.float32): from hedge.backends import guess_run_context rcon = guess_run_context() from hedge.mesh.generator import make_rect_mesh if rcon.is_head_rank: h_fac = 1 mesh = make_rect_mesh(a=(0,0),b=(1,1), max_area=h_fac**2*1e-4, periodicity=(True,True), subdivisions=(int(70/h_fac), int(70/h_fac))) from hedge.models.gas_dynamics.lbm import \ D2Q9LBMMethod, LatticeBoltzmannOperator op = LatticeBoltzmannOperator( D2Q9LBMMethod(), lbm_delta_t=0.001, nu=1e-4) if rcon.is_head_rank: print "%d elements" % len(mesh.elements) mesh_data = rcon.distribute_mesh(mesh) else: mesh_data = rcon.receive_mesh() discr = rcon.make_discretization(mesh_data, order=3, default_scalar_type=dtype, debug=["cuda_no_plan"]) from hedge.timestep.runge_kutta import LSRK4TimeStepper stepper = LSRK4TimeStepper(dtype=dtype, #vector_primitive_factory=discr.get_vector_primitive_factory() ) from hedge.visualization import VtkVisualizer if write_output: vis = VtkVisualizer(discr, rcon, "fld") from hedge.data import CompiledExpressionData def ic_expr(t, x, fields): from hedge.optemplate import CFunction from pymbolic.primitives import IfPositive from pytools.obj_array import make_obj_array tanh = CFunction("tanh") sin = CFunction("sin") rho = 1 u0 = 0.05 w = 0.05 delta = 0.05 from hedge.optemplate.primitives import make_common_subexpression as cse u = cse(make_obj_array([ IfPositive(x[1]-1/2, u0*tanh(4*(3/4-x[1])/w), u0*tanh(4*(x[1]-1/4)/w)), u0*delta*sin(2*np.pi*(x[0]+1/4))]), "u") return make_obj_array([ op.method.f_equilibrium(rho, alpha, u) for alpha in range(len(op.method)) ]) # timestep loop ----------------------------------------------------------- stream_rhs = op.bind_rhs(discr) collision_update = op.bind(discr, op.collision_update) get_rho = op.bind(discr, op.rho) get_rho_u = op.bind(discr, op.rho_u) f_bar = CompiledExpressionData(ic_expr).volume_interpolant(0, discr) from hedge.discretization import ExponentialFilterResponseFunction from hedge.optemplate.operators import FilterOperator mode_filter = FilterOperator( ExponentialFilterResponseFunction(min_amplification=0.9, order=4))\ .bind(discr) final_time = 1000 try: lbm_dt = op.lbm_delta_t dg_dt = op.estimate_timestep(discr, stepper=stepper) print dg_dt dg_steps_per_lbm_step = int(np.ceil(lbm_dt / dg_dt)) dg_dt = lbm_dt / dg_steps_per_lbm_step lbm_steps = int(final_time // op.lbm_delta_t) for step in xrange(lbm_steps): t = step*lbm_dt if step % 100 == 0 and write_output: visf = vis.make_file("fld-%04d" % step) rho = get_rho(f_bar) rho_u = get_rho_u(f_bar) vis.add_data(visf, [ ("fbar%d" %i, discr.convert_volume(f_bar_i, "numpy")) for i, f_bar_i in enumerate(f_bar)]+ [ ("rho", discr.convert_volume(rho, "numpy")), ("rho_u", discr.convert_volume(rho_u, "numpy")), ], time=t, step=step) visf.close() print "step=%d, t=%f" % (step, t) f_bar = collision_update(f_bar) for substep in range(dg_steps_per_lbm_step): f_bar = stepper(f_bar, t + substep*dg_dt, dg_dt, stream_rhs) #f_bar = mode_filter(f_bar) finally: if write_output: vis.close() discr.close()
def test_cuda_volume_quadrature(): from hedge.mesh.generator import make_rect_mesh mesh = make_rect_mesh(a=(-1, -1), b=(1, 1), max_area=0.08) from hedge.backends import guess_run_context cpu_rcon = guess_run_context(['jit']) gpu_rcon = guess_run_context(['cuda']) order = 4 quad_min_degrees = {"quad": 3 * order} cpu_discr, gpu_discr = [ rcon.make_discretization(mesh, order=order, default_scalar_type=numpy.float64, debug=[ "cuda_no_plan", "cuda_no_microblock", ], quad_min_degrees=quad_min_degrees) for rcon in [cpu_rcon, gpu_rcon] ] from math import sin, cos def f(x, el): return sin(x[0]) * cos(x[1]) cpu_field, gpu_field = [ discr.interpolate_volume_function(f) for discr in [cpu_discr, gpu_discr] ] def make_optemplate(): from hedge.optemplate.operators import QuadratureGridUpsampler from hedge.optemplate import Field, make_stiffness_t u = Field("u") qu = QuadratureGridUpsampler("quad")(u) return make_stiffness_t(2)[0](Field("intercept")(qu)) saved_vectors = [] def intercept(x): saved_vectors.append(x) return x for discr in [cpu_discr, gpu_discr]: discr.add_function("intercept", intercept) opt = make_optemplate() cpu_bound, gpu_bound = [ discr.compile(make_optemplate()) for discr in [cpu_discr, gpu_discr] ] cpu_result = cpu_bound(u=cpu_field) gpu_result = gpu_bound(u=gpu_field) cpu_ivec, gpu_ivec = saved_vectors gpu_ivec_on_host = gpu_ivec.get()[gpu_discr._gpu_volume_embedding( "quad")] ierr = cpu_ivec - gpu_ivec_on_host assert la.norm(ierr) < 5e-15 gpu_result_on_host = gpu_discr.convert_volume(gpu_result, kind="numpy") err = cpu_result - gpu_result_on_host assert la.norm(err) < 2e-14 cpu_discr.close() gpu_discr.close()