Hello community, here is the log from the commit of package python-numba for openSUSE:Factory checked in at 2020-05-28 09:15:33 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/python-numba (Old) and /work/SRC/openSUSE:Factory/.python-numba.new.3606 (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "python-numba" Thu May 28 09:15:33 2020 rev:26 rq:809224 version:0.49.1 Changes: -------- --- /work/SRC/openSUSE:Factory/python-numba/python-numba.changes 2020-04-28 22:31:48.677691170 +0200 +++ /work/SRC/openSUSE:Factory/.python-numba.new.3606/python-numba.changes 2020-05-28 09:16:07.748795226 +0200 @@ -1,0 +2,20 @@ +Wed May 27 07:24:32 UTC 2020 - [email protected] + +- version update to 0.49.1 + * PR #5587: Fixed #5586 Threading Implementation Typos + * PR #5592: Fixes #5583 Remove references to cffi_support from docs and examples + * PR #5614: Fix invalid type in resolve for comparison expr in parfors. + * PR #5624: Fix erroneous rewrite of predicate to bit const on prune. + * PR #5627: Fixes #5623, SSA local def scan based on invalid equality + assumption. + * PR #5629: Fixes naming error in array_exprs + * PR #5630: Fix #5570. Incorrect race variable detection due to SSA naming. + * PR #5638: Make literal_unroll function work as a freevar. + * PR #5648: Unset the memory manager after EMM Plugin tests + * PR #5651: Fix some SSA issues + * PR #5652: Pin to sphinx=2.4.4 to avoid problem with C declaration + * PR #5658: Fix unifying undefined first class function types issue + * PR #5669: Update example in 5m guide WRT SSA type stability. + * PR #5676: Restore ``numba.types`` as public API + +------------------------------------------------------------------- Old: ---- numba-0.49.0.tar.gz New: ---- numba-0.49.1.tar.gz ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ python-numba.spec ++++++ --- /var/tmp/diff_new_pack.a94aZG/_old 2020-05-28 09:16:08.612797265 +0200 +++ /var/tmp/diff_new_pack.a94aZG/_new 2020-05-28 09:16:08.628797303 +0200 @@ -27,7 +27,7 @@ %bcond_with test %endif Name: python-numba%{psuffix} -Version: 0.49.0 +Version: 0.49.1 Release: 0 Summary: NumPy-aware optimizing compiler for Python using LLVM License: BSD-2-Clause ++++++ numba-0.49.0.tar.gz -> numba-0.49.1.tar.gz ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/CHANGE_LOG new/numba-0.49.1/CHANGE_LOG --- old/numba-0.49.0/CHANGE_LOG 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/CHANGE_LOG 2020-05-08 16:22:43.000000000 +0200 @@ -1,3 +1,36 @@ +Version 0.49.1 (May 7, 2020) +---------------------------- + +This is a bugfix release for 0.49.0, it fixes some residual issues with SSA +form, a critical bug in the branch pruning logic and a number of other smaller +issues: + +* PR #5587: Fixed #5586 Threading Implementation Typos +* PR #5592: Fixes #5583 Remove references to cffi_support from docs and examples +* PR #5614: Fix invalid type in resolve for comparison expr in parfors. +* PR #5624: Fix erroneous rewrite of predicate to bit const on prune. +* PR #5627: Fixes #5623, SSA local def scan based on invalid equality + assumption. +* PR #5629: Fixes naming error in array_exprs +* PR #5630: Fix #5570. Incorrect race variable detection due to SSA naming. +* PR #5638: Make literal_unroll function work as a freevar. +* PR #5648: Unset the memory manager after EMM Plugin tests +* PR #5651: Fix some SSA issues +* PR #5652: Pin to sphinx=2.4.4 to avoid problem with C declaration +* PR #5658: Fix unifying undefined first class function types issue +* PR #5669: Update example in 5m guide WRT SSA type stability. +* PR #5676: Restore ``numba.types`` as public API + +Authors: + +* Graham Markall +* Juan Manuel Cruz Martinez +* Pearu Peterson +* Sean Law +* Stuart Archibald (core dev) +* Siu Kwan Lam (core dev) + + Version 0.49.0 (Apr 16, 2020) ----------------------------- diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/PKG-INFO new/numba-0.49.1/PKG-INFO --- old/numba-0.49.0/PKG-INFO 2020-04-17 16:49:38.000000000 +0200 +++ new/numba-0.49.1/PKG-INFO 2020-05-08 16:26:14.000000000 +0200 @@ -1,6 +1,6 @@ Metadata-Version: 1.2 Name: numba -Version: 0.49.0 +Version: 0.49.1 Summary: compiling Python code using LLVM Home-page: http://numba.github.com Author: Anaconda, Inc. diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/docs/source/developer/threading_implementation.rst new/numba-0.49.1/docs/source/developer/threading_implementation.rst --- old/numba-0.49.0/docs/source/developer/threading_implementation.rst 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/docs/source/developer/threading_implementation.rst 2020-05-08 16:22:43.000000000 +0200 @@ -18,9 +18,9 @@ The relevant source files referenced in this document are -- ``numba/npyufunc/tbbpool.cpp`` -- ``numba/npyufunc/omppool.cpp`` -- ``numba/npyufunc/workqueue.c`` +- ``numba/np/ufunc/tbbpool.cpp`` +- ``numba/np/ufunc/omppool.cpp`` +- ``numba/np/ufunc/workqueue.c`` These files contain the TBB, OpenMP, and workqueue threadpool implementations, respectively. Each includes the functions @@ -29,14 +29,14 @@ schedulers. Note that the basic thread local variable logic is duplicated in each of these files, and not shared between them. -- ``numba/npyufunc/parallel.py`` +- ``numba/np/ufunc/parallel.py`` This file contains the Python and JIT compatible wrappers for ``set_num_threads()``, ``get_num_threads()``, and ``get_thread_id()``, as well as the code that loads the above libraries into Python and launches the threadpool. -- ``numba/npyufunc/parfor.py`` +- ``numba/parfors/parfor_lowering.py`` This file contains the main logic for generating code for the parallel backend. The thread mask is accessed in this file in the code that generates @@ -47,7 +47,7 @@ -------------- As part of its design, Numba never launches new threads beyond the threads -that are launched initially with ``numba.npyufunc.parallel._launch_threads()`` +that are launched initially with ``numba.np.ufunc.parallel._launch_threads()`` when the first parallel execution is run. This is due to the way threads were already implemented in Numba prior to thread masking being implemented. This restriction was kept to keep the design simple, although it could be removed @@ -164,7 +164,7 @@ A private ``get_thread_id()`` function was added to each threading backend, which returns a unique ID for each thread. This can be accessed from Python by -``numba.npyufunc.parallel._get_thread_id()`` (it can also be used inside a +``numba.np.ufunc.parallel._get_thread_id()`` (it can also be used inside a JIT compiled function). The thread ID function is useful for testing that the thread masking behavior is correct, but it should not be used outside of the tests. For example, one can call ``set_num_threads(4)`` and then collect all @@ -212,7 +212,7 @@ # Pass num_threads through to the appropriate backend function here -See the code in ``numba/npyufunc/parfor.py``. +See the code in ``numba/parfors/parfor_lowering.py``. The guard against ``num_threads`` being <= 0 is not strictly necessary, but it can protect against accidentally incorrect behavior in case the thread masking diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/docs/source/reference/pysupported.rst new/numba-0.49.1/docs/source/reference/pysupported.rst --- old/numba-0.49.0/docs/source/reference/pysupported.rst 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/docs/source/reference/pysupported.rst 2020-05-08 16:22:43.000000000 +0200 @@ -1057,12 +1057,12 @@ only permitted to call functions that accept pointers to structs - passing a struct by value is unsupported. For registering a mapping, use: -.. function:: numba.cffi_support.register_type(cffi_type, numba_type) +.. function:: numba.core.typing.cffi_utils.register_type(cffi_type, numba_type) Out-of-line cffi modules must be registered with Numba prior to the use of any of their functions from within Numba-compiled functions: -.. function:: numba.cffi_support.register_module(mod) +.. function:: numba.core.typing.cffi_utils.register_module(mod) Register the cffi out-of-line module ``mod`` with Numba. diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/docs/source/user/5minguide.rst new/numba-0.49.1/docs/source/user/5minguide.rst --- old/numba-0.49.0/docs/source/user/5minguide.rst 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/docs/source/user/5minguide.rst 2020-05-08 16:22:43.000000000 +0200 @@ -62,7 +62,7 @@ @jit(nopython=True) # Set "nopython" mode for best performance, equivalent to @njit def go_fast(a): # Function is compiled to machine code when called the first time - trace = 0 + trace = 0.0 for i in range(a.shape[0]): # Numba likes loops trace += np.tanh(a[i, i]) # Numba likes NumPy functions return a + trace # Numba likes NumPy broadcasting @@ -130,7 +130,7 @@ @jit(nopython=True) def go_fast(a): # Function is compiled and runs in machine code - trace = 0 + trace = 0.0 for i in range(a.shape[0]): trace += np.tanh(a[i, i]) return a + trace diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/docs/source/user/cfunc.rst new/numba-0.49.1/docs/source/user/cfunc.rst --- old/numba-0.49.0/docs/source/user/cfunc.rst 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/docs/source/user/cfunc.rst 2020-05-08 16:22:43.000000000 +0200 @@ -126,15 +126,18 @@ For applications that have a lot of state, it is useful to pass data in C structures. To simplify the interoperability with C code, numba can convert a ``cffi`` type into a numba ``Record`` type using -``numba.cffi_support.map_type``:: +``numba.core.typing.cffi_utils.map_type``:: - from numba import cffi_support + from numba.core.typing import cffi_utils - nbtype = cffi_support.map_type(cffi_type, use_record_dtype=True) + nbtype = cffi_utils.map_type(cffi_type, use_record_dtype=True) .. note:: **use_record_dtype=True** is needed otherwise pointers to C structures are returned as void pointers. +.. note:: From v0.49 the ``numba.cffi_support`` module has been phased out + in favour of ``numba.core.typing.cffi_utils`` + For example:: @@ -158,7 +161,7 @@ ffi.cdef(src) # Get the function signature from *my_func* - sig = cffi_support.map_type(ffi.typeof('my_func'), use_record_dtype=True) + sig = cffi_utils.map_type(ffi.typeof('my_func'), use_record_dtype=True) # Make the cfunc from numba import cfunc, carray diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/_version.py new/numba-0.49.1/numba/_version.py --- old/numba-0.49.0/numba/_version.py 2020-04-17 16:49:38.000000000 +0200 +++ new/numba-0.49.1/numba/_version.py 2020-05-08 16:26:14.000000000 +0200 @@ -4,8 +4,8 @@ # unpacked source archive. Distribution tarballs contain a pre-generated copy # of this file. -version_version = '0.49.0' -version_full = '334e65cef19257faf1c6452bc0750df7d1ce76d8' +version_version = '0.49.1' +version_full = 'd2cac8597ad2aa4074147d9c7595f5b5e9919901' def get_versions(default={}, verbose=False): return {'version': version_version, 'full': version_full} diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/core/analysis.py new/numba-0.49.1/numba/core/analysis.py --- old/numba-0.49.0/numba/core/analysis.py 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/numba/core/analysis.py 2020-05-08 16:22:43.000000000 +0200 @@ -283,6 +283,10 @@ return loop +# Used to describe a nullified condition in dead branch pruning +nullified = namedtuple('nullified', 'condition, taken_br, rewrite_stmt') + + # Functions to manipulate IR def dead_branch_prune(func_ir, called_args): """ @@ -429,7 +433,8 @@ prune_stat, taken = prune(branch, condition, blk, *const_conds) if(prune_stat): # add the condition to the list of nullified conditions - nullified_conditions.append((condition, taken)) + nullified_conditions.append(nullified(condition, taken, + True)) else: # see if this is a branch on a constant value predicate resolved_const = Unknown() @@ -444,7 +449,8 @@ prune_stat, taken = prune_by_predicate(branch, condition, blk) if(prune_stat): # add the condition to the list of nullified conditions - nullified_conditions.append((condition, taken)) + nullified_conditions.append(nullified(condition, taken, + False)) # 'ERE BE DRAGONS... # It is the evaluation of the condition expression that often trips up type @@ -461,18 +467,22 @@ # completeness the func_ir._definitions and ._consts are also updated to # make the IR state self consistent. - deadcond = [x[0] for x in nullified_conditions] + deadcond = [x.condition for x in nullified_conditions] for _, cond, blk in branch_info: if cond in deadcond: for x in blk.body: if isinstance(x, ir.Assign) and x.value is cond: # rewrite the condition as a true/false bit - branch_bit = nullified_conditions[deadcond.index(cond)][1] - x.value = ir.Const(branch_bit, loc=x.loc) - # update the specific definition to the new const - defns = func_ir._definitions[x.target.name] - repl_idx = defns.index(cond) - defns[repl_idx] = x.value + nullified_info = nullified_conditions[deadcond.index(cond)] + # only do a rewrite of conditions, predicates need to retain + # their value as they may be used later. + if nullified_info.rewrite_stmt: + branch_bit = nullified_info.taken_br + x.value = ir.Const(branch_bit, loc=x.loc) + # update the specific definition to the new const + defns = func_ir._definitions[x.target.name] + repl_idx = defns.index(cond) + defns[repl_idx] = x.value # Remove dead blocks, this is safe as it relies on the CFG only. cfg = compute_cfg_from_blocks(func_ir.blocks) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/core/interpreter.py new/numba-0.49.1/numba/core/interpreter.py --- old/numba-0.49.0/numba/core/interpreter.py 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/numba/core/interpreter.py 2020-05-08 16:22:43.000000000 +0200 @@ -377,7 +377,7 @@ err = errors.NotDefinedError(e.name, loc=loc) if not config.FULL_TRACEBACKS: - raise value from None + raise err from None else: raise err diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/core/ssa.py new/numba-0.49.1/numba/core/ssa.py --- old/numba-0.49.0/numba/core/ssa.py 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/numba/core/ssa.py 2020-05-08 16:22:43.000000000 +0200 @@ -315,12 +315,13 @@ elif isinstance(rhs, ir.Var): newdef = self._fix_var(states, assign, [rhs]) # Has a replacement that is not the current variable - if newdef is not None and states['varname'] != newdef.target.name: - return ir.Assign( - target=assign.target, - value=newdef.target, - loc=assign.loc, - ) + if newdef is not None and newdef.target is not ir.UNDEFINED: + if states['varname'] != newdef.target.name: + return ir.Assign( + target=assign.target, + value=newdef.target, + loc=assign.loc, + ) return assign @@ -328,10 +329,11 @@ newdef = self._fix_var( states, stmt, stmt.list_vars(), ) - if newdef is not None and states['varname'] != newdef.target.name: - replmap = {states['varname']: newdef.target} - stmt = copy(stmt) - ir_utils.replace_vars_stmt(stmt, replmap) + if newdef is not None and newdef.target is not ir.UNDEFINED: + if states['varname'] != newdef.target.name: + replmap = {states['varname']: newdef.target} + stmt = copy(stmt) + ir_utils.replace_vars_stmt(stmt, replmap) return stmt def _fix_var(self, states, stmt, used_vars): @@ -430,15 +432,18 @@ return self._find_def_from_top(states, label, loc=loc) def _stmt_index(self, defstmt, block, stop=-1): - """Find the postitional index of the statement at ``block``. + """Find the positional index of the statement at ``block``. Assumptions: - no two statements can point to the same object. """ - try: - return block.body.index(defstmt, 0, stop) - except ValueError: - return len(block.body) + # Compare using id() as IR node equality is for semantic equivalence + # opposed to direct equality (the location and scope are not considered + # as part of the equality measure, this is important here). + for i in range(len(block.body))[:stop]: + if block.body[i] is defstmt: + return i + return len(block.body) def _warn_about_uninitialized_variable(varname, loc): diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/core/untyped_passes.py new/numba-0.49.1/numba/core/untyped_passes.py --- old/numba-0.49.0/numba/core/untyped_passes.py 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/numba/core/untyped_passes.py 2020-05-08 16:22:43.000000000 +0200 @@ -615,7 +615,7 @@ calls = [_ for _ in blk.find_exprs('call')] for call in calls: glbl = guard(get_definition, func_ir, call.func) - if glbl and isinstance(glbl, ir.Global): + if glbl and isinstance(glbl, (ir.Global, ir.FreeVar)): # find a literal_unroll if glbl.value is literal_unroll: if len(call.args) > 1: @@ -1285,7 +1285,8 @@ return False func_var = guard(get_definition, func_ir, call.func) func = guard(get_definition, func_ir, func_var) - if func is None or not isinstance(func, ir.Global): + if func is None or not isinstance(func, + (ir.Global, ir.FreeVar)): return False if (func.value is None or func.value not in self._accepted_calls): diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/core/utils.py new/numba-0.49.1/numba/core/utils.py --- old/numba-0.49.0/numba/core/utils.py 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/numba/core/utils.py 2020-05-08 16:22:43.000000000 +0200 @@ -12,6 +12,7 @@ import weakref import warnings from types import ModuleType +from importlib import import_module from collections.abc import Mapping import numpy as np @@ -533,7 +534,8 @@ if undefined_function is None: undefined_function = t else: - assert undefined_function == t + # Refuse to unify using function type + return dispatchers.update(t.dispatchers) else: if function is None: @@ -555,3 +557,38 @@ function = types.UndefinedFunctionType(mnargs, dispatchers) return function + + +class _RedirectSubpackage(ModuleType): + """Redirect a subpackage to a subpackage. + + This allows all references like: + + >>> from numba.old_subpackage import module + >>> module.item + + >>> import numba.old_subpackage.module + >>> numba.old_subpackage.module.item + + >>> from numba.old_subpackage.module import item + """ + def __init__(self, old_module_locals, new_module): + old_module = old_module_locals['__name__'] + super().__init__(old_module) + + new_mod_obj = import_module(new_module) + + # Map all sub-modules over + for k, v in new_mod_obj.__dict__.items(): + # Get attributes so that `subpackage.xyz` and + # `from subpackage import xyz` work + setattr(self, k, v) + if isinstance(v, ModuleType): + # Map modules into the interpreter so that + # `import subpackage.xyz` works + sys.modules[f"{old_module}.{k}"] = sys.modules[v.__name__] + + # copy across dunders so that package imports work too + for attr, value in old_module_locals.items(): + if attr.startswith('__') and attr.endswith('__'): + setattr(self, attr, value) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/cuda/tests/cudadrv/test_emm_plugins.py new/numba-0.49.1/numba/cuda/tests/cudadrv/test_emm_plugins.py --- old/numba-0.49.0/numba/cuda/tests/cudadrv/test_emm_plugins.py 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/numba/cuda/tests/cudadrv/test_emm_plugins.py 2020-05-08 16:22:43.000000000 +0200 @@ -110,10 +110,9 @@ cuda.set_memory_manager(DeviceOnlyEMMPlugin) def tearDown(self): - # Set the memory manager back to the Numba internal one for subsequent - # tests. + # Unset the memory manager for subsequent tests cuda.close() - cuda.set_memory_manager(cuda.cudadrv.driver.NumbaCUDAMemoryManager) + cuda.cudadrv.driver._memory_manager = None def test_memalloc(self): mgr = cuda.current_context().memory_manager diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/np/ufunc/array_exprs.py new/numba-0.49.1/numba/np/ufunc/array_exprs.py --- old/numba-0.49.0/numba/np/ufunc/array_exprs.py 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/numba/np/ufunc/array_exprs.py 2020-05-08 16:22:43.000000000 +0200 @@ -308,9 +308,11 @@ var_map = OrderedDict() for var in var_list: old_name = var.name - new_name = old_name.replace("$", "_").replace(".", "_") + new_name = var.scope.redefine(old_name, loc=var.loc).name + new_name = new_name.replace("$", "_").replace(".", "_") # Caller should ensure the names are unique - assert new_name not in var_map + if new_name in var_map: + raise AssertionError(f"{new_name!r} not unique") var_map[new_name] = var, old_name var.name = new_name param_names = list(var_map) @@ -337,17 +339,9 @@ expr_args = [var.name for var in expr_var_unique] # 1. Create an AST tree from the array expression. - with _legalize_parameter_names(expr_var_unique) as expr_params: - - if hasattr(ast, "arg"): - # Should be Python 3.x - ast_args = [ast.arg(param_name, None) - for param_name in expr_params] - else: - # Should be Python 2.x - ast_args = [ast.Name(param_name, ast.Param()) - for param_name in expr_params] + ast_args = [ast.arg(param_name, None) + for param_name in expr_params] # Parse a stub function to ensure the AST is populated with # reasonable defaults for the Python version. ast_module = ast.parse('def {0}(): return'.format(expr_name), diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/parfors/parfor.py new/numba-0.49.1/numba/parfors/parfor.py --- old/numba-0.49.0/numba/parfors/parfor.py 2020-04-17 16:49:29.000000000 +0200 +++ new/numba-0.49.1/numba/parfors/parfor.py 2020-05-08 16:22:43.000000000 +0200 @@ -2864,7 +2864,8 @@ el_typ1 = typemap[arg_vars[0].name] if len(arg_vars) == 2: el_typ2 = typemap[arg_vars[1].name] - func_typ = typingctx.resolve_function_type(op, (el_typ1, el_typ), {}) + func_typ = typingctx.resolve_function_type(op, (el_typ1, + el_typ2), {}) ir_expr = ir.Expr.binop(op, arg_vars[0], arg_vars[1], loc) if op == operator.truediv: func_typ, ir_expr = _gen_np_divide( @@ -3169,7 +3170,12 @@ dummy_block.body = block.body[:i] before_defs = compute_use_defs({0: dummy_block}).defmap[0] pre_defs |= before_defs - parfor.params = get_parfor_params_inner(parfor, pre_defs, options_fusion, fusion_info) | parfor.races + params = get_parfor_params_inner( + parfor, pre_defs, options_fusion, fusion_info, + ) + parfor.params, parfor.races = _combine_params_races_for_ssa_names( + block.scope, params, parfor.races, + ) parfor_ids.add(parfor.id) parfors.append(parfor) @@ -3177,6 +3183,30 @@ return parfor_ids, parfors +def _combine_params_races_for_ssa_names(scope, params, races): + """Returns `(params|races1, races1)`, where `races1` contains all variables + in `races` are NOT referring to the same unversioned (SSA) variables in + `params`. + """ + def unversion(k): + try: + return scope.get_exact(k).unversioned_name + except ir.NotDefinedError: + # XXX: it's a bug that something references an undefined name + return k + + races1 = set(races) + unver_params = list(map(unversion, params)) + + for rv in races: + if any(unversion(rv) == pv for pv in unver_params): + races1.discard(rv) + else: + break + + return params | races1, races1 + + def get_parfor_params_inner(parfor, pre_defs, options_fusion, fusion_info): blocks = wrap_parfor_blocks(parfor) cfg = compute_cfg_from_blocks(blocks) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/tests/test_analysis.py new/numba-0.49.1/numba/tests/test_analysis.py --- old/numba-0.49.0/numba/tests/test_analysis.py 2020-04-17 16:49:30.000000000 +0200 +++ new/numba-0.49.1/numba/tests/test_analysis.py 2020-05-08 16:22:43.000000000 +0200 @@ -697,7 +697,7 @@ def func(x): if const: - return 3.14159 + return 3.14159, const self.assert_prune(func, (types.NoneType('none'),), [prune], None) @@ -707,7 +707,7 @@ def func(x): if not const: - return 3.14159 + return 3.14159, const self.assert_prune(func, (types.NoneType('none'),), [prune], None) @@ -717,9 +717,9 @@ def func(x): if const: - return 3.14159 + return 3.14159, const else: - return 1.61803 + return 1.61803, const self.assert_prune(func, (types.NoneType('none'),), [prune], None) @@ -729,9 +729,9 @@ def func(x): if not const: - return 3.14159 + return 3.14159, const else: - return 1.61803 + return 1.61803, const self.assert_prune(func, (types.NoneType('none'),), [prune], None) @@ -746,7 +746,7 @@ def func(x): if c_test_single_if_global: - return 3.14159 + return 3.14159, c_test_single_if_global self.assert_prune(func, (types.NoneType('none'),), [prune], None) @@ -760,7 +760,7 @@ def func(x): if c_test_single_if_negate_global: - return 3.14159 + return 3.14159, c_test_single_if_negate_global self.assert_prune(func, (types.NoneType('none'),), [prune], None) @@ -774,9 +774,9 @@ def func(x): if c_test_single_if_else_global: - return 3.14159 + return 3.14159, c_test_single_if_else_global else: - return 1.61803 + return 1.61803, c_test_single_if_else_global self.assert_prune(func, (types.NoneType('none'),), [prune], None) @@ -789,12 +789,25 @@ def func(x): if not c_test_single_if_else_negate_global: - return 3.14159 + return 3.14159, c_test_single_if_else_negate_global else: - return 1.61803 + return 1.61803, c_test_single_if_else_negate_global self.assert_prune(func, (types.NoneType('none'),), [prune], None) + def test_issue_5618(self): + + @njit + def foo(): + values = np.zeros(1) + tmp = 666 + if tmp: + values[0] = tmp + return values + + self.assertPreciseEqual(foo.py_func()[0], 666.) + self.assertPreciseEqual(foo()[0], 666.) + class TestBranchPrunePostSemanticConstRewrites(TestBranchPruneBase): # Tests that semantic constants rewriting works by virtue of branch pruning diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/tests/test_array_exprs.py new/numba-0.49.1/numba/tests/test_array_exprs.py --- old/numba-0.49.0/numba/tests/test_array_exprs.py 2020-04-17 16:49:30.000000000 +0200 +++ new/numba-0.49.1/numba/tests/test_array_exprs.py 2020-05-08 16:22:43.000000000 +0200 @@ -467,6 +467,21 @@ self.assertIn("# u.1 = ", res) self.assertIn("# u.2 = ", res) + def test_issue_5599_name_collision(self): + # The original error will fail in lowering of the array_expr + @njit + def f(x): + arr = np.ones(x) + + for _ in range(2): + val = arr * arr + arr = arr.copy() + return arr + + got = f(5) + expect = f.py_func(5) + np.testing.assert_array_equal(got, expect) + class TestSemantics(MemoryLeakMixin, unittest.TestCase): diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/tests/test_function_type.py new/numba-0.49.1/numba/tests/test_function_type.py --- old/numba-0.49.0/numba/tests/test_function_type.py 2020-04-17 16:49:30.000000000 +0200 +++ new/numba-0.49.1/numba/tests/test_function_type.py 2020-05-08 16:22:44.000000000 +0200 @@ -1,5 +1,6 @@ import types as pytypes from numba import jit, njit, cfunc, types, int64, float64, float32, errors +from numba import literal_unroll from numba.core.config import IS_32BITS, IS_WIN32 import ctypes import warnings @@ -1072,3 +1073,28 @@ self.assertRegex( str(cm.exception), r'.*first-class function call cannot use keyword arguments') + + def test_issue_5615(self): + + @njit + def foo1(x): + return x + 1 + + @njit + def foo2(x): + return x + 2 + + @njit + def bar(fcs): + x = 0 + a = 10 + i, j = fcs[0] + x += i(j(a)) + for t in literal_unroll(fcs): + i, j = t + x += i(j(a)) + return x + + tup = ((foo1, foo2), (foo2, foo1)) + + self.assertEqual(bar(tup), 39) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/tests/test_mixed_tuple_unroller.py new/numba-0.49.1/numba/tests/test_mixed_tuple_unroller.py --- old/numba-0.49.0/numba/tests/test_mixed_tuple_unroller.py 2020-04-17 16:49:30.000000000 +0200 +++ new/numba-0.49.1/numba/tests/test_mixed_tuple_unroller.py 2020-05-08 16:22:44.000000000 +0200 @@ -1801,6 +1801,19 @@ ['a', '25', '0.23', 'None'], ) + def test_unroller_as_freevar(self): + mixed = (np.ones((1,)), np.ones((1, 1)), np.ones((1, 1, 1))) + from numba import literal_unroll as freevar_unroll + + @njit + def foo(): + out = 0 + for i in freevar_unroll(mixed): + out += i.ndim + return out + + self.assertEqual(foo(), foo.py_func()) + def capture(real_pass): """ Returns a compiler pass that captures the mutation state reported diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/tests/test_moved_modules.py new/numba-0.49.1/numba/tests/test_moved_modules.py --- old/numba-0.49.0/numba/tests/test_moved_modules.py 1970-01-01 01:00:00.000000000 +0100 +++ new/numba-0.49.1/numba/tests/test_moved_modules.py 2020-05-08 16:22:44.000000000 +0200 @@ -0,0 +1,30 @@ +"""Tests for moved modules and their redirection from old path +""" +from numba.tests.support import TestCase + + +class TestMovedModule(TestCase): + """Testing moved modules in Q1 2020 but were decided to kept as public API + """ + def tests_numba_types(self): + import numba.types + import numba.core.types as types + # The old module IS NOT the new module + self.assertIsNot(numba.types, types) + # Attribute access are there + self.assertIs(numba.types.intp, types.intp) + self.assertIs(numba.types.float64, types.float64) + self.assertIs(numba.types.Array, types.Array) + # Submodule access through old import path is possible + import numba.types.misc + self.assertIs(types.misc, numba.types.misc) + self.assertIs(types.misc.Optional, numba.types.misc.Optional) + # Import time code could be executed twice and causes the following to + # fail. + self.assertIs(types.StringLiteral, numba.types.misc.StringLiteral) + # Check numba.types.container + from numba.types import containers + self.assertIs(types.containers, containers) + self.assertIs(types.containers.Sequence, containers.Sequence) + from numba.types.containers import Sequence + self.assertIs(Sequence, containers.Sequence) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/tests/test_parfors.py new/numba-0.49.1/numba/tests/test_parfors.py --- old/numba-0.49.0/numba/tests/test_parfors.py 2020-04-17 16:49:30.000000000 +0200 +++ new/numba-0.49.1/numba/tests/test_parfors.py 2020-05-08 16:22:44.000000000 +0200 @@ -3428,6 +3428,26 @@ self.check(parallel_test, size, arr) + @skip_parfors_unsupported + def test_issue5570_ssa_races(self): + @njit(parallel=True) + def foo(src, method, out): + for i in prange(1): + for j in range(1): + out[i, j] = 1 + if method: + out += 1 + return out + + src = np.zeros((5,5)) + method = 57 + out = np.zeros((2, 2)) + + self.assertPreciseEqual( + foo(src, method, out), + foo.py_func(src, method, out) + ) + @skip_parfors_unsupported class TestParforsDiagnostics(TestParforsBase): diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/tests/test_refactor_moves.py new/numba-0.49.1/numba/tests/test_refactor_moves.py --- old/numba-0.49.0/numba/tests/test_refactor_moves.py 2020-04-17 16:49:30.000000000 +0200 +++ new/numba-0.49.1/numba/tests/test_refactor_moves.py 2020-05-08 16:22:44.000000000 +0200 @@ -399,15 +399,6 @@ with checker(fn): getattr(numba.typeconv, fn) - def test_numba_types(self): - checker = self.check_warning("numba.types", "numba.core.types") - with checker(): - import numba.types - - for fn in ("int64", "float64"): - with checker(fn): - getattr(numba.types, fn) - def test_aaaaa_numba_targets(self): # silly 'aaaaa' name to game test ordering, warnings only get triggered # once and the `TestAPIMoves_Q1_2020` hits numba.targets.* so this needs diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/tests/test_ssa.py new/numba-0.49.1/numba/tests/test_ssa.py --- old/numba-0.49.0/numba/tests/test_ssa.py 2020-04-17 16:49:30.000000000 +0200 +++ new/numba-0.49.1/numba/tests/test_ssa.py 2020-05-08 16:22:44.000000000 +0200 @@ -149,6 +149,57 @@ self.check_func(foo, np.array([1, 2])) + def test_unhandled_undefined(self): + def function1(arg1, arg2, arg3, arg4, arg5): + # This function is auto-generated. + if arg1: + var1 = arg2 + var2 = arg3 + var3 = var2 + var4 = arg1 + return + else: + if arg2: + if arg4: + var5 = arg4 # noqa: F841 + return + else: + var6 = var4 + return + return var6 + else: + if arg5: + if var1: + if arg5: + var1 = var6 + return + else: + var7 = arg2 # noqa: F841 + return arg2 + return + else: + if var2: + arg5 = arg2 + return arg1 + else: + var6 = var3 + return var4 + return + return + else: + var8 = var1 + return + return var8 + var9 = var3 # noqa: F841 + var10 = arg5 # noqa: F841 + return var1 + + # The argument values is not critical for re-creating the bug + # because the bug is in compile-time. + expect = function1(2, 3, 6, 0, 7) + got = njit(function1)(2, 3, 6, 0, 7) + self.assertEqual(expect, got) + class TestReportedSSAIssues(SSABaseTest): # Tests from issues @@ -370,3 +421,26 @@ res2 = jit(forceobj=True, looplift=False)(foo)(10, 10, data) np.testing.assert_array_equal(expect, res1) np.testing.assert_array_equal(expect, res2) + + def test_issue5623_equal_statements_in_same_bb(self): + + def foo(pred, stack): + i = 0 + c = 1 + + if pred is True: + stack[i] = c + i += 1 + stack[i] = c + i += 1 + + python = np.array([0, 666]) + foo(True, python) + + nb = np.array([0, 666]) + njit(foo)(True, nb) + + expect = np.array([1, 1]) + + np.testing.assert_array_equal(python, expect) + np.testing.assert_array_equal(nb, expect) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/numba-0.49.0/numba/types/__init__.py new/numba-0.49.1/numba/types/__init__.py --- old/numba-0.49.0/numba/types/__init__.py 2020-04-17 16:49:30.000000000 +0200 +++ new/numba-0.49.1/numba/types/__init__.py 2020-05-08 16:22:44.000000000 +0200 @@ -1,3 +1,3 @@ import sys -from numba.core.errors import _MovedModule -sys.modules[__name__] = _MovedModule(locals(), "numba.core.types") +from numba.core.utils import _RedirectSubpackage +sys.modules[__name__] = _RedirectSubpackage(locals(), "numba.core.types")
