Skip to content

Commit 1765fd8

Browse files
committed
Interpolate: map dual argument to reference values for codegen
1 parent 6d080b1 commit 1765fd8

File tree

1 file changed

+19
-12
lines changed

1 file changed

+19
-12
lines changed

tsfc/driver.py

Lines changed: 19 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -211,20 +211,31 @@ def compile_expression_dual_evaluation(expression, to_element, ufl_element, *,
211211
if isinstance(to_element, (PhysicallyMappedElement, DirectlyDefinedElement)):
212212
raise NotImplementedError("Don't know how to interpolate onto zany spaces, sorry")
213213

214+
if domain is None:
215+
domain = extract_unique_domain(expression)
216+
assert domain is not None
217+
218+
if not isinstance(expression, ufl.Interpolate):
219+
expression = ufl.Interpolate(expression, ufl.FunctionSpace(domain, ufl_element))
220+
214221
orig_coefficients = extract_coefficients(expression)
215-
if isinstance(expression, ufl.Interpolate):
216-
v, operand = expression.argument_slots()
217-
else:
218-
operand = expression
219-
v = ufl.FunctionSpace(extract_unique_domain(operand), ufl_element)
222+
v, operand = expression.argument_slots()
223+
224+
# Map v into reference space
225+
if ufl_element.mapping() != "identity":
226+
Vref = ufl.FunctionSpace(domain, finat.ufl.WithMapping(ufl_element, "identity"))
227+
if isinstance(v, ufl.Cofunction):
228+
v = ufl.Cofunction(Vref.dual())
229+
else:
230+
v = ufl.Coargument(Vref.dual(), number=v.number())
220231

221-
# Map into reference space
232+
# Map operand into reference space
222233
operand = apply_mapping(operand, ufl_element, domain)
223234

224235
# Apply UFL preprocessing
225236
operand = ufl_utils.preprocess_expression(operand, complex_mode=complex_mode)
226237

227-
# Reconstructed Interpolate with mapped operand
238+
# Reconstructed Interpolate in the reference space
228239
expression = ufl.Interpolate(operand, v)
229240

230241
# Initialise kernel builder
@@ -238,18 +249,14 @@ def compile_expression_dual_evaluation(expression, to_element, ufl_element, *,
238249
for arg in arguments}
239250
assert len(argument_multiindices) == len(arguments)
240251

241-
# Replace coordinates (if any) unless otherwise specified by kwarg
242-
if domain is None:
243-
domain = extract_unique_domain(expression)
244-
assert domain is not None
245-
246252
# Collect required coefficients and determine numbering
247253
coefficients = extract_coefficients(expression)
248254
coefficient_numbers = tuple(map(orig_coefficients.index, coefficients))
249255
builder.set_coefficient_numbers(coefficient_numbers)
250256

251257
elements = [f.ufl_element() for f in (*coefficients, *arguments)]
252258

259+
# Replace coordinates (if any) unless otherwise specified by kwarg
253260
needs_external_coords = False
254261
if has_type(expression, GeometricQuantity) or any(map(fem.needs_coordinate_mapping, elements)):
255262
# Create a fake coordinate coefficient for a domain.

0 commit comments

Comments
 (0)