Skip to content
Snippets Groups Projects
Commit aa074ae4 authored by Dominic Kempf's avatar Dominic Kempf
Browse files

Rip out measure_specific details

parent 9c12ecc4
No related branches found
No related tags found
No related merge requests found
...@@ -5,6 +5,7 @@ from dune.perftool.generation import (base_class, ...@@ -5,6 +5,7 @@ from dune.perftool.generation import (base_class,
class_basename, class_basename,
class_member, class_member,
constructor_parameter, constructor_parameter,
global_context,
include_file, include_file,
initializer_list, initializer_list,
symbol, symbol,
...@@ -43,16 +44,45 @@ def define_initree(name): ...@@ -43,16 +44,45 @@ def define_initree(name):
return "const Dune::ParameterTree& {};".format(name) return "const Dune::ParameterTree& {};".format(name)
def ufl_measure_to_pdelab_measure(which):
return {'cell': 'Volume',
'exterior_facet': 'Boundary',
'interior_facet': 'Skeleton',
}.get(which)
@class_member(classtag="operator", access=AccessModifier.PUBLIC) @class_member(classtag="operator", access=AccessModifier.PUBLIC)
def enum_pattern(which): def _enum_pattern(which):
return "enum {{ doPattern{} = true }};".format(which) return "enum {{ doPattern{} = true }};".format(which)
def enum_pattern():
from dune.perftool.generation import get_global_context_value
integral_type = get_global_context_value("integral_type")
return _enum_pattern(ufl_measure_to_pdelab_measure(integral_type))
def _pattern_baseclass(measure):
return base_class('Dune::PDELab::Full{}Pattern'.format(measure), classtag="operator")
def pattern_baseclass():
from dune.perftool.generation import get_global_context_value
integral_type = get_global_context_value("integral_type")
return _pattern_baseclass(ufl_measure_to_pdelab_measure(integral_type))
@class_member(classtag="operator", access=AccessModifier.PUBLIC) @class_member(classtag="operator", access=AccessModifier.PUBLIC)
def enum_alpha(which): def _enum_alpha(which):
return "enum {{ doAlpha{} = true }};".format(which) return "enum {{ doAlpha{} = true }};".format(which)
def enum_alpha():
from dune.perftool.generation import get_global_context_value
integral_type = get_global_context_value("integral_type")
return _enum_alpha(ufl_measure_to_pdelab_measure(integral_type))
@symbol @symbol
def name_initree_member(): def name_initree_member():
define_initree("_iniParams") define_initree("_iniParams")
...@@ -81,58 +111,26 @@ def class_type_from_cache(classtag): ...@@ -81,58 +111,26 @@ def class_type_from_cache(classtag):
return basename, basename + tparam_str return basename, basename + tparam_str
@memoize def assembly_routine_signature():
def measure_specific_details(measure): from dune.perftool.generation import get_global_context_value
# The return dictionary that this memoized method will grant direct access to. integral_type = get_global_context_value("integral_type")
ret = {} form_type = get_global_context_value("form_type")
def numerical_jacobian(which): aj = "alpha" if form_type == 'residual' else "jacobian"
if get_option("numerical_jacobian"):
# Add a base class if integral_type == 'cell':
_, loptype = class_type_from_cache("operator") return ['template<typename EG, typename LFSU, typename X, typename LFSV, typename R>',
base_class("Dune::PDELab::NumericalJacobian{}<{}>".format(which, loptype), classtag="operator") 'void {}_volume(const EG& eg, const LFSU& lfsu, const X& x, const LFSV& lfsv, R& r) const'.format(aj)]
# Add the initializer list for that base class if integral_type == 'exterior_facet':
ini = name_initree_member() return ['template<typename IG, typename LFSV0, typename X, typename LFSV1, typename R>',
ini_constructor = name_initree_constructor_param() 'void {}_boundary(const IG& ig, const LFSV0& lfsv0, const X& x, const LFSV1& lfsv1, R& r) const'.format(aj)]
initializer_list("Dune::PDELab::NumericalJacobian{}<{}>".format(which, loptype),
["{}.get<double>(\"numerical_epsilon.{}\", 1e-9)".format(ini_constructor, ini, which.lower())], if integral_type == 'interior_facet':
classtag="operator") return ['template<typename IG, typename LFSV0_S, typename X, typename LFSV1_S, typename LFSV0_N, typename R, typename LFSV1_N>',
'void {}_skeleton(const IG& ig, const LFSV0_S& lfsv0_s, const X& x_s, const LFSV1_S& lfsv1_s, const LFSV0_N& lfsv0_n, const X& x_n, const LFSV1_N& lfsv1_n, R& r_s, R& r_n) const'.format(aj)]
if measure == "cell":
base_class('Dune::PDELab::FullVolumePattern', classtag="operator") assert False
numerical_jacobian("Volume")
enum_pattern("Volume")
enum_alpha("Volume")
ret["residual_signature"] = ['template<typename EG, typename LFSU, typename X, typename LFSV, typename R>',
'void alpha_volume(const EG& eg, const LFSU& lfsu, const X& x, const LFSV& lfsv, R& r) const']
ret["jacobian_signature"] = ['template<typename EG, typename LFSU, typename X, typename LFSV, typename J>',
'void jacobian_volume(const EG& eg, const LFSU& lfsu, const X& x, const LFSV& lfsv, J& jac) const']
if measure == "exterior_facet":
base_class('Dune::PDELab::FullBoundaryPattern', classtag="operator")
numerical_jacobian("Boundary")
enum_pattern("Boundary")
enum_alpha("Boundary")
ret["residual_signature"] = ['template<typename IG, typename LFSV0, typename X, typename LFSV1, typename R>',
'void alpha_boundary(const IG& ig, const LFSV0& lfsv0, const X& x, const LFSV1& lfsv1, R& r) const']
ret["jacobian_signature"] = ['template<typename IG, typename LFSV0, typename X, typename LFSV1, typename J>',
'void jacobian_boundary(const IG& ig, const LFSV0& lfsv0, const X& x, const LFSV1& lfsv1, J& jac) const']
if measure == "interior_facet":
base_class('Dune::PDELab::FullSkeletonPattern', classtag="operator")
numerical_jacobian("Skeleton")
enum_pattern("Skeleton")
enum_alpha("Skeleton")
ret["residual_signature"] = ['template<typename IG, typename LFSV0_S, typename X, typename LFSV1_S, typename LFSV0_N, typename R, typename LFSV1_N>',
'void alpha_skeleton(const IG& ig, const LFSV0_S& lfsv0_s, const X& x_s, const LFSV1_S& lfsv1_s, const LFSV0_N& lfsv0_n, const X& x_n, const LFSV1_N& lfsv1_n, R& r_s, R& r_n) const']
ret["jacobian_signature"] = ['template<typename IG, typename LFSV0_S, typename X, typename LFSV1_S, typename LFSV0_N, typename LFSV1_N, typename Jac>',
'void jacobian_skeleton(const IG& ig, const LFSV0_S& lfsv0_s, const X& x_s, const LFSV1_S& lfsv1_s, const LFSV0_N& lfsv0_n, const X& x_n, const LFSV1_N& lfsv1_n, Jac& jac_ss, Jac& jac_sn, Jac& jac_ns, Jac& jac_nn) const']
return ret
def generate_kernel(integral): def generate_kernel(integral):
...@@ -141,9 +139,6 @@ def generate_kernel(integral): ...@@ -141,9 +139,6 @@ def generate_kernel(integral):
subdomain_id = integral.subdomain_id() subdomain_id = integral.subdomain_id()
subdomain_data = integral.subdomain_data() subdomain_data = integral.subdomain_data()
# Get the measure specifics
specifics = measure_specific_details(measure)
# Now split the given integrand into accumulation expressions # Now split the given integrand into accumulation expressions
from dune.perftool.ufl.transformations.extract_accumulation_terms import split_into_accumulation_terms from dune.perftool.ufl.transformations.extract_accumulation_terms import split_into_accumulation_terms
accterms = split_into_accumulation_terms(integrand) accterms = split_into_accumulation_terms(integrand)
...@@ -245,23 +240,44 @@ def generate_localoperator_kernels(formdata, namedata): ...@@ -245,23 +240,44 @@ def generate_localoperator_kernels(formdata, namedata):
from dune.perftool.generation import global_context from dune.perftool.generation import global_context
with global_context(formdata=formdata, namedata=namedata): with global_context(formdata=formdata, namedata=namedata):
# Generate the necessary residual methods with global_context(form_type='residual'):
for integral in form.integrals(): # Generate the necessary residual methods
kernel = generate_kernel(integral) for integral in form.integrals():
operator_kernels[(integral.integral_type(), 'residual')] = kernel with global_context(integral_type=integral.integral_type()):
enum_pattern()
pattern_baseclass()
enum_alpha()
kernel = generate_kernel(integral)
# Maybe add numerical differentiation
if get_option("numerical_jacobian"):
include_file("dune/pdelab/localoperator/defaultimp.hh", filetag="operatorfile")
_, loptype = class_type_from_cache("operator")
which = ufl_measure_to_pdelab_measure(integral.integral_type())
base_class("Dune::PDELab::NumericalJacobian{}<{}>".format(which, loptype), classtag="operator")
# Add the initializer list for that base class
ini = name_initree_member()
ini_constructor = name_initree_constructor_param()
initializer_list("Dune::PDELab::NumericalJacobian{}<{}>".format(which, loptype),
["{}.get<double>(\"numerical_epsilon.{}\", 1e-9)".format(ini_constructor, ini, which.lower())],
classtag="operator",
)
operator_kernels[(integral.integral_type(), 'residual')] = kernel
# Generate the necessary jacobian methods # Generate the necessary jacobian methods
from dune.perftool.options import get_option if not get_option("numerical_jacobian"):
if get_option("numerical_jacobian"):
include_file("dune/pdelab/localoperator/defaultimp.hh", filetag="operatorfile")
else:
from ufl import derivative from ufl import derivative
from ufl.algorithms import expand_derivatives from ufl.algorithms import expand_derivatives
jacform = expand_derivatives(derivative(form, form.coefficients()[0])) jacform = expand_derivatives(derivative(form, form.coefficients()[0]))
for integral in jacform.integrals(): with global_context(form_type="jacobian"):
kernel = generate_kernel(integral) for integral in jacform.integrals():
operator_kernels[(integral.integral_type(), 'jacobian')] = kernel with global_context(integral_type=integral.integral_type()):
kernel = generate_kernel(integral)
operator_kernels[(integral.integral_type(), 'jacobian')] = kernel
# TODO: JacobianApply for matrix-free computations. # TODO: JacobianApply for matrix-free computations.
...@@ -274,8 +290,10 @@ def generate_localoperator_file(kernels): ...@@ -274,8 +290,10 @@ def generate_localoperator_file(kernels):
# Make generables from the given kernels # Make generables from the given kernels
for method, kernel in kernels.items(): for method, kernel in kernels.items():
signature = measure_specific_details(method[0])["{}_signature".format(method[1])] it, ft = method
operator_methods.append(AssemblyMethod(signature, kernel)) with global_context(integral_type=it, form_type=ft):
signature = assembly_routine_signature()
operator_methods.append(AssemblyMethod(signature, kernel))
# Write the file! # Write the file!
from dune.perftool.file import generate_file from dune.perftool.file import generate_file
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment