|
7 | 7 | import math
|
8 | 8 | import operator
|
9 | 9 |
|
| 10 | +import dpnp |
10 | 11 | from numba.core import errors, ir, types, typing
|
11 | 12 | from numba.core.ir_utils import mk_unique_var
|
12 | 13 | from numba.core.typing import npydecl
|
13 | 14 | from numba.parfors import array_analysis, parfor
|
14 | 15 |
|
| 16 | +from numba_dpex.core.typing import dpnpdecl |
| 17 | + |
15 | 18 |
|
16 | 19 | def _ufunc_to_parfor_instr(
|
17 | 20 | typemap,
|
@@ -53,6 +56,39 @@ def _ufunc_to_parfor_instr(
|
53 | 56 | return el_typ
|
54 | 57 |
|
55 | 58 |
|
| 59 | +def get_dpnp_ufunc_typ(func): |
| 60 | + """get type of the incoming function from builtin registry""" |
| 61 | + for k, v in dpnpdecl.registry.globals: |
| 62 | + if k == func: |
| 63 | + return v |
| 64 | + raise RuntimeError("type for func ", func, " not found") |
| 65 | + |
| 66 | + |
| 67 | +def _gen_dpnp_divide(arg1, arg2, out_ir, typemap): |
| 68 | + """generate np.divide() instead of / for array_expr to get numpy error model |
| 69 | + like inf for division by zero (test_division_by_zero). |
| 70 | + """ |
| 71 | + scope = arg1.scope |
| 72 | + loc = arg1.loc |
| 73 | + g_np_var = ir.Var(scope, mk_unique_var("$np_g_var"), loc) |
| 74 | + typemap[g_np_var.name] = types.misc.Module(dpnp) |
| 75 | + g_np = ir.Global("dpnp", dpnp, loc) |
| 76 | + g_np_assign = ir.Assign(g_np, g_np_var, loc) |
| 77 | + # attr call: div_attr = getattr(g_np_var, divide) |
| 78 | + div_attr_call = ir.Expr.getattr(g_np_var, "divide", loc) |
| 79 | + attr_var = ir.Var(scope, mk_unique_var("$div_attr"), loc) |
| 80 | + func_var_typ = get_dpnp_ufunc_typ(dpnp.divide) |
| 81 | + typemap[attr_var.name] = func_var_typ |
| 82 | + attr_assign = ir.Assign(div_attr_call, attr_var, loc) |
| 83 | + # divide call: div_attr(arg1, arg2) |
| 84 | + div_call = ir.Expr.call(attr_var, [arg1, arg2], (), loc) |
| 85 | + func_typ = func_var_typ.get_call_type( |
| 86 | + typing.Context(), [typemap[arg1.name], typemap[arg2.name]], {} |
| 87 | + ) |
| 88 | + out_ir.extend([g_np_assign, attr_assign]) |
| 89 | + return func_typ, div_call |
| 90 | + |
| 91 | + |
56 | 92 | def _arrayexpr_tree_to_ir(
|
57 | 93 | func_ir,
|
58 | 94 | typingctx,
|
@@ -103,7 +139,8 @@ def _arrayexpr_tree_to_ir(
|
103 | 139 | )
|
104 | 140 | ir_expr = ir.Expr.binop(op, arg_vars[0], arg_vars[1], loc)
|
105 | 141 | if op == operator.truediv:
|
106 |
| - func_typ, ir_expr = parfor._gen_np_divide( |
| 142 | + # NUMBA_DPEX: is_dpnp_func check was added |
| 143 | + func_typ, ir_expr = _gen_dpnp_divide( |
107 | 144 | arg_vars[0], arg_vars[1], out_ir, typemap
|
108 | 145 | )
|
109 | 146 | else:
|
|
0 commit comments