Beispiel #1
0
    def make_func(self, discr, boundary_tag=None):
        from pymbolic import var

        def make_vec(basename):
            from hedge.tools import make_obj_array
            return make_obj_array(
                    [var("%s%d" % (basename, i)) for i in range(self.dimensions)])

        from hedge.optemplate.primitives import ScalarParameter
        from hedge.optemplate.tools import make_sym_vector

        x = make_sym_vector("x", discr.dimensions)
        fields = make_sym_vector("fields", self.arg_count)
        exprs = self.expressions_getter(
                t=ScalarParameter("t"), x=x, fields=fields)

        from hedge.optemplate.mappers.type_inference import (
                type_info, NodalRepresentation)
        type_hints = {}
        if boundary_tag is not None:
            my_vec_type = type_info.BoundaryVector(
                    boundary_tag, NodalRepresentation())
        else:
            my_vec_type = type_info.VolumeVector(
                    NodalRepresentation())

        for x_i in x:
            type_hints[x_i] = my_vec_type

        for f_i in fields:
            type_hints[f_i] = my_vec_type

        return discr.compile(exprs, type_hints=type_hints)
Beispiel #2
0
    def make_func(self, discr, boundary_tag=None):
        from pymbolic import var

        def make_vec(basename):
            from hedge.tools import make_obj_array
            return make_obj_array(
                [var("%s%d" % (basename, i)) for i in range(self.dimensions)])

        from hedge.optemplate.primitives import ScalarParameter
        from hedge.optemplate.tools import make_sym_vector

        x = make_sym_vector("x", discr.dimensions)
        fields = make_sym_vector("fields", self.arg_count)
        exprs = self.expressions_getter(t=ScalarParameter("t"),
                                        x=x,
                                        fields=fields)

        from hedge.optemplate.mappers.type_inference import (
            type_info, NodalRepresentation)
        type_hints = {}
        if boundary_tag is not None:
            my_vec_type = type_info.BoundaryVector(boundary_tag,
                                                   NodalRepresentation())
        else:
            my_vec_type = type_info.VolumeVector(NodalRepresentation())

        for x_i in x:
            type_hints[x_i] = my_vec_type

        for f_i in fields:
            type_hints[f_i] = my_vec_type

        return discr.compile(exprs, type_hints=type_hints)
Beispiel #3
0
    def make_bc_info(self, bc_name, tag, state, state0=None):
        """
        :param state0: The boundary 'free-stream' state around which the
          BC is linearized.
        """
        if state0 is None:
            state0 = make_sym_vector(bc_name, self.dimensions+2)

        state0 = cse(to_bdry_quad(state0))

        rho0 = self.rho(state0)
        p0 = self.cse_p(state0)
        u0 = self.cse_u(state0)

        c0 = (self.equation_of_state.gamma * p0 / rho0)**0.5

        from hedge.optemplate import BoundarizeOperator
        bdrize_op = BoundarizeOperator(tag)

        class SingleBCInfo(Record):
            pass

        return SingleBCInfo(
            rho0=rho0, p0=p0, u0=u0, c0=c0,

            # notation: suffix "m" for "minus", i.e. "interior"
            drhom=cse(self.rho(cse(to_bdry_quad(bdrize_op(state)))) 
                - rho0, "drhom"),
            dumvec=cse(self.cse_u(cse(to_bdry_quad(bdrize_op(state)))) 
                - u0, "dumvec"),
            dpm=cse(self.cse_p(cse(to_bdry_quad(bdrize_op(state)))) 
                - p0, "dpm"))
Beispiel #4
0
 def noslip_state(self, state):
     from hedge.optemplate import make_normal
     state0 = join_fields(make_sym_vector("bc_q_noslip", 2),
                          [0] * self.dimensions)
     normal = make_normal(self.noslip_tag, self.dimensions)
     bc = self.make_bc_info("bc_q_noslip", self.noslip_tag, state, state0)
     return self.inflow_state_inner(normal, bc, "noslip")
Beispiel #5
0
 def noslip_state(self, state):
     from hedge.optemplate import make_normal
     state0 = join_fields(
         make_sym_vector("bc_q_noslip", 2),
         [0]*self.dimensions)
     normal = make_normal(self.noslip_tag, self.dimensions)
     bc = self.make_bc_info("bc_q_noslip", self.noslip_tag, state, state0)
     return self.inflow_state_inner(normal, bc, "noslip")
Beispiel #6
0
    def bind_characteristic_velocity(self, discr):
        state = make_sym_vector("q", self.dimensions+2)

        compiled = discr.compile(
                self.characteristic_velocity_optemplate(state))

        def do(q):
            return compiled(q=q)

        return do
Beispiel #7
0
    def bind_characteristic_velocity(self, discr):
        state = make_sym_vector("q", self.dimensions + 2)

        compiled = discr.compile(
            self.characteristic_velocity_optemplate(state))

        def do(q):
            return compiled(q=q)

        return do
Beispiel #8
0
    def get_conservative_boundary_conditions(self):
        state = self.state()

        from hedge.optemplate import BoundarizeOperator
        return {
                self.supersonic_inflow_tag:
                make_sym_vector("bc_q_supersonic_in", self.dimensions+2),
                self.supersonic_outflow_tag:
                BoundarizeOperator(self.supersonic_outflow_tag)(
                            (state)),
                self.wall_tag: self.wall_state(state),
                }
Beispiel #9
0
    def get_conservative_boundary_conditions(self):
        state = self.state()

        from hedge.optemplate import BoundarizeOperator
        return {
            self.supersonic_inflow_tag:
            make_sym_vector("bc_q_supersonic_in", self.dimensions + 2),
            self.supersonic_outflow_tag:
            BoundarizeOperator(self.supersonic_outflow_tag)((state)),
            self.wall_tag:
            self.wall_state(state),
        }
Beispiel #10
0
    def make_bc_info(self, bc_name, tag, state, state0=None):
        """
        :param state0: The boundary 'free-stream' state around which the
          BC is linearized.
        """
        if state0 is None:
            state0 = make_sym_vector(bc_name, self.dimensions + 2)

        state0 = cse(to_bdry_quad(state0))

        rho0 = self.rho(state0)
        p0 = self.cse_p(state0)
        u0 = self.cse_u(state0)

        c0 = (self.equation_of_state.gamma * p0 / rho0)**0.5

        from hedge.optemplate import BoundarizeOperator
        bdrize_op = BoundarizeOperator(tag)

        class SingleBCInfo(Record):
            pass

        return SingleBCInfo(
            rho0=rho0,
            p0=p0,
            u0=u0,
            c0=c0,

            # notation: suffix "m" for "minus", i.e. "interior"
            drhom=cse(
                self.rho(cse(to_bdry_quad(bdrize_op(state)))) - rho0, "drhom"),
            dumvec=cse(
                self.cse_u(cse(to_bdry_quad(bdrize_op(state)))) - u0,
                "dumvec"),
            dpm=cse(
                self.cse_p(cse(to_bdry_quad(bdrize_op(state)))) - p0, "dpm"))
Beispiel #11
0
    def op_template(self, sensor_scaling=None, viscosity_only=False):
        u = self.cse_u
        rho = self.cse_rho
        rho_u = self.rho_u
        p = self.p
        e = self.e

        # {{{ artificial diffusion
        def make_artificial_diffusion():
            if self.artificial_viscosity_mode not in ["diffusion"]:
                return 0

            dq = self.grad_of_state()

            return make_obj_array([
                self.div(
                    to_vol_quad(self.sensor())*to_vol_quad(dq[i]),
                    to_int_face_quad(self.sensor())*to_int_face_quad(dq[i])) 
                for i in range(dq.shape[0])])
        # }}}

        # {{{ state setup

        volq_flux = self.flux(self.volq_state())
        faceq_flux = self.flux(self.faceq_state())

        from hedge.optemplate.primitives import CFunction
        sqrt = CFunction("sqrt")

        speed = self.characteristic_velocity_optemplate(self.state())

        has_viscosity = not is_zero(self.get_mu(self.state(), to_quad_op=None))

        # }}}

        # {{{ operator assembly -----------------------------------------------
        from hedge.flux.tools import make_lax_friedrichs_flux
        from hedge.optemplate.operators import InverseMassOperator

        from hedge.optemplate.tools import make_stiffness_t

        primitive_bcs_as_quad_conservative = dict(
                (tag, self.primitive_to_conservative(to_bdry_quad(bc)))
                for tag, bc in 
                self.get_primitive_boundary_conditions().iteritems())

        def get_bc_tuple(tag):
            state = self.state()
            bc = make_obj_array([
                self.get_boundary_condition_for(tag, s_i) for s_i in state])
            return tag, bc, self.flux(bc)

        first_order_part = InverseMassOperator()(
                numpy.dot(make_stiffness_t(self.dimensions), volq_flux)
                - make_lax_friedrichs_flux(
                    wave_speed=cse(to_int_face_quad(speed), "emax_c"),

                    state=self.faceq_state(), fluxes=faceq_flux,
                    bdry_tags_states_and_fluxes=[
                        get_bc_tuple(tag) for tag in self.get_boundary_tags()],
                    strong=False))

        if viscosity_only:
            first_order_part = 0*first_order_part

        result = join_fields(
                first_order_part 
                + self.make_second_order_part()
                + make_artificial_diffusion()
                + self.make_extra_terms(),
                 speed)

        if self.source is not None:
            result = result + join_fields(
                    make_sym_vector("source_vect", len(self.state())),
                    # extra field for speed
                    0)

        return result
Beispiel #12
0
 def state(self):
     return make_sym_vector("q", self.dimensions+2)
Beispiel #13
0
    def op_template(self, sensor_scaling=None, viscosity_only=False):
        u = self.cse_u
        rho = self.cse_rho
        rho_u = self.rho_u
        p = self.p
        e = self.e

        # {{{ artificial diffusion
        def make_artificial_diffusion():
            if self.artificial_viscosity_mode not in ["diffusion"]:
                return 0

            dq = self.grad_of_state()

            return make_obj_array([
                self.div(
                    to_vol_quad(self.sensor()) * to_vol_quad(dq[i]),
                    to_int_face_quad(self.sensor()) * to_int_face_quad(dq[i]))
                for i in range(dq.shape[0])
            ])

        # }}}

        # {{{ state setup

        volq_flux = self.flux(self.volq_state())
        faceq_flux = self.flux(self.faceq_state())

        from hedge.optemplate.primitives import CFunction
        sqrt = CFunction("sqrt")

        speed = self.characteristic_velocity_optemplate(self.state())

        has_viscosity = not is_zero(self.get_mu(self.state(), to_quad_op=None))

        # }}}

        # {{{ operator assembly -----------------------------------------------
        from hedge.flux.tools import make_lax_friedrichs_flux
        from hedge.optemplate.operators import InverseMassOperator

        from hedge.optemplate.tools import make_stiffness_t

        primitive_bcs_as_quad_conservative = dict(
            (tag, self.primitive_to_conservative(to_bdry_quad(bc))) for tag, bc
            in self.get_primitive_boundary_conditions().iteritems())

        def get_bc_tuple(tag):
            state = self.state()
            bc = make_obj_array(
                [self.get_boundary_condition_for(tag, s_i) for s_i in state])
            return tag, bc, self.flux(bc)

        first_order_part = InverseMassOperator()(
            numpy.dot(make_stiffness_t(self.dimensions), volq_flux) -
            make_lax_friedrichs_flux(
                wave_speed=cse(to_int_face_quad(speed), "emax_c"),
                state=self.faceq_state(),
                fluxes=faceq_flux,
                bdry_tags_states_and_fluxes=[
                    get_bc_tuple(tag) for tag in self.get_boundary_tags()
                ],
                strong=False))

        if viscosity_only:
            first_order_part = 0 * first_order_part

        result = join_fields(
            first_order_part + self.make_second_order_part() +
            make_artificial_diffusion() + self.make_extra_terms(), speed)

        if self.source is not None:
            result = result + join_fields(
                make_sym_vector("source_vect", len(self.state())),
                # extra field for speed
                0)

        return result
Beispiel #14
0
 def state(self):
     return make_sym_vector("q", self.dimensions + 2)