Skip to content

Commit 28b9d54

Browse files
committed
api: fixup complex dtype handling for mpi
1 parent 3f5eb5f commit 28b9d54

4 files changed

Lines changed: 30 additions & 12 deletions

File tree

devito/passes/clusters/derivatives.py

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,7 @@
77
from devito.ir import Backward, Forward, Interval, IterationSpace, Queue
88
from devito.passes.clusters.fusion import fuse
99
from devito.symbolics import BasicWrapperMixin, reuse_if_untouched, search, uxreplace
10+
from devito.symbolics.inspection import sympy_dtype
1011
from devito.tools import infer_dtype, timed_pass
1112
from devito.types import Eq, Inc, Indexed, Symbol
1213

@@ -170,12 +171,13 @@ def _(expr, c, ispace, weights, reusables, mapper, **kwargs):
170171

171172
# The Symbol that will hold the result of the IndexDerivative computation
172173
# NOTE: created before recursing so that we ultimately get a sound ordering
174+
dtype = sympy_dtype(ideriv)
173175
try:
174176
s = reusables.pop()
175-
assert np.can_cast(s.dtype, w.dtype)
177+
assert np.can_cast(s.dtype, dtype)
176178
except KeyError:
177179
name = sregistry.make_name(prefix='r')
178-
s = Symbol(name=name, dtype=w.dtype)
180+
s = Symbol(name=name, dtype=dtype)
179181

180182
# Go inside `expr` and recursively lower any nested IndexDerivatives
181183
expr, processed = _core(expr, c, ispace1, weights, reusables, mapper, **kwargs)

devito/passes/iet/engine.py

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -259,11 +259,13 @@ def wrapper(*args, **kwargs):
259259
try:
260260
# Pure function case
261261
graph, = args
262-
return maybe_timed(call(graph), func.__name__)(func, **kwargs)
262+
ietfunc = func
263263
except ValueError:
264264
# Instance method case
265265
self, graph = args
266-
return maybe_timed(call(graph), func.__name__)(partial(func, self), **kwargs)
266+
ietfunc = partial(func, self)
267+
268+
return maybe_timed(call(graph), func.__name__)(ietfunc, **kwargs)
267269

268270
return wrapper
269271

devito/tools/dtypes_lowering.py

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@
2626
dtype_mapper = {
2727
"int": np.int32,
2828
"float": np.float32,
29-
"double": np.float64
29+
"double": np.float64,
3030
}
3131

3232

@@ -98,6 +98,9 @@ def get_base_dtype(self, v, default=None):
9898
# Fallbacks
9999
dtypes_vector_mapper.update({(v, 1): v for v in dtype_mapper.values()})
100100

101+
# Complex
102+
dtypes_vector_mapper.update({(np.complex64, 1): np.complex64})
103+
dtypes_vector_mapper.update({(np.complex128, 1): np.complex128})
101104

102105
# *** Custom types escaping both the numpy and ctypes namespaces
103106

@@ -238,7 +241,11 @@ class c_restrict_void_p(ctypes.c_void_p):
238241

239242
ctypes_vector_mapper = {}
240243
for base_name, base_dtype in dtype_mapper.items():
241-
base_ctype = dtype_to_ctype(base_dtype)
244+
try:
245+
base_ctype = dtype_to_ctype(base_dtype)
246+
except NotImplementedError:
247+
# E.g., np.complex64
248+
continue
242249

243250
for count in counts:
244251
dtype = dtypes_vector_mapper[(base_dtype, count)]
@@ -250,7 +257,6 @@ class c_restrict_void_p(ctypes.c_void_p):
250257

251258
ctypes_vector_mapper[dtype] = ctype
252259

253-
254260
# *** ctypes lowering
255261

256262

tests/test_mpi.py

Lines changed: 13 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -2067,19 +2067,24 @@ def test_merge_smart_if_within_conditional(self, mode):
20672067
for n in FindNodes(Conditional).visit(op1):
20682068
assert len(FindNodes(HaloUpdateCall).visit(n)) == 0
20692069

2070+
@pytest.mark.parametrize('dtype', [np.float32, np.complex64])
20702071
@pytest.mark.parallel(mode=2)
2071-
def test_allreduce_time(self, mode):
2072+
def test_allreduce_time(self, dtype, mode):
20722073
space_order = 8
20732074
nx, ny = 11, 11
20742075

20752076
grid = Grid(shape=(nx, ny))
20762077
tt = grid.time_dim
20772078
nt = 10
20782079

2079-
ux = TimeFunction(name="ux", grid=grid, time_order=1, space_order=space_order)
2080-
g = TimeFunction(name="g", grid=grid, dimensions=(tt, ), shape=(nt,))
2080+
c = tt if dtype == np.float32 else tt + tt * 1j
2081+
2082+
ux = TimeFunction(name="ux", grid=grid, time_order=1, space_order=space_order,
2083+
dtype=dtype)
2084+
g = TimeFunction(name="g", grid=grid, dimensions=(tt, ), shape=(nt,),
2085+
dtype=dtype)
20812086

2082-
op = Operator([Eq(ux.forward, ux + tt), Inc(g, ux)], name="Op")
2087+
op = Operator([Eq(ux.forward, ux + c), Inc(g, ux)], name="Op")
20832088
assert_structure(op, ['t,x,y', 't'], 'txy')
20842089

20852090
# Reduce should be in time loop but not in space loop
@@ -2091,7 +2096,10 @@ def test_allreduce_time(self, mode):
20912096
assert len(FindNodes(Call).visit(i)) == 0
20922097

20932098
op.apply(time_m=0, time_M=nt-1)
2094-
assert np.isclose(np.max(g.data), 4356.0)
2099+
if dtype == np.float32:
2100+
assert np.isclose(np.max(g.data), 4356.0)
2101+
else:
2102+
assert np.isclose(np.max(g.data), 4356.0 + 4356.0j)
20952103

20962104
@pytest.mark.parallel(mode=2)
20972105
def test_multi_allreduce_time(self, mode):

0 commit comments

Comments
 (0)