From 2069a9ac7cd7dc3dad7086d4d6bc49517c9cc695 Mon Sep 17 00:00:00 2001 From: etotmeni Date: Wed, 2 Dec 2020 09:05:07 -0600 Subject: [PATCH 1/5] Controllable fallback --- numba_dppy/config.py | 3 + numba_dppy/dppl_lowerer.py | 3 +- numba_dppy/target_dispatcher.py | 5 ++ .../tests/dppl/test_controllable_fallback.py | 86 +++++++++++++++++++ 4 files changed, 96 insertions(+), 1 deletion(-) create mode 100644 numba_dppy/tests/dppl/test_controllable_fallback.py diff --git a/numba_dppy/config.py b/numba_dppy/config.py index 880d18d7b5..3969ca7206 100644 --- a/numba_dppy/config.py +++ b/numba_dppy/config.py @@ -34,3 +34,6 @@ def _readenv(): ... # Turn SPIRV-VALIDATION ON/OFF switch SPIRV_VAL = _readenv("NUMBA_DPPY_SPIRV_VAL", int, 0) + +# Fallback to CPU +FALLBACK_OPTION = _readenv("NUMBA_DPPY_FALLBACK_OPTION", int, 0) diff --git a/numba_dppy/dppl_lowerer.py b/numba_dppy/dppl_lowerer.py index 51fb072551..2683d761ca 100644 --- a/numba_dppy/dppl_lowerer.py +++ b/numba_dppy/dppl_lowerer.py @@ -1172,7 +1172,8 @@ def lower(self): if numba_dppy.compiler.DEBUG: print("Failed to lower parfor on DPPL-device. Due to:\n", e) lowering.lower_extensions[parfor.Parfor].pop() - if (lowering.lower_extensions[parfor.Parfor][-1] == numba.parfors.parfor_lowering._lower_parfor_parallel): + if ((lowering.lower_extensions[parfor.Parfor][-1] == numba.parfors.parfor_lowering._lower_parfor_parallel) and + numba_dppy.config.FALLBACK_OPTION == 1): self.cpu_lower.lower() self.base_lower = self.cpu_lower else: diff --git a/numba_dppy/target_dispatcher.py b/numba_dppy/target_dispatcher.py index 40b9d589d9..3176413517 100644 --- a/numba_dppy/target_dispatcher.py +++ b/numba_dppy/target_dispatcher.py @@ -1,6 +1,7 @@ from numba.core import registry, serialize, dispatcher from numba import types from numba.core.errors import UnsupportedError +import numba_dppy import dpctl from numba.core.compiler_lock import global_compiler_lock @@ -59,6 +60,10 @@ def get_current_disp(self): target = self.__target parallel = self.__parallel offload = isinstance(parallel, dict) and parallel.get('offload') is True + fallback = isinstance(parallel, dict) and parallel.get('fallback') + + if fallback: + numba_dppy.config.FALLBACK_OPTION = 1 if (dpctl.is_in_device_context() or offload): if not self.__is_with_context_target(target): diff --git a/numba_dppy/tests/dppl/test_controllable_fallback.py b/numba_dppy/tests/dppl/test_controllable_fallback.py new file mode 100644 index 0000000000..b4b75e282a --- /dev/null +++ b/numba_dppy/tests/dppl/test_controllable_fallback.py @@ -0,0 +1,86 @@ +from __future__ import print_function, division, absolute_import + +import numpy as np + +import numba +import numba_dppy, numba_dppy as dppl +from numba_dppy.testing import unittest +from numba_dppy.testing import DPPLTestCase +from numba.tests.support import captured_stderr +import dpctl +import sys +import io + + +@unittest.skipUnless(dpctl.has_gpu_queues(), 'test only on GPU system') +class TestDPPLFallback(DPPLTestCase): + def test_dppl_fallback_true(self): + @numba.jit + def fill_value(i): + return i + + def inner_call_fallback(): + x = 10 + a = np.empty(shape=x, dtype=np.float32) + + for i in numba.prange(x): + a[i] = fill_value(i) + + return a + + with captured_stderr() as msg_fallback_true: + dppl = numba.njit(parallel={'offload':True, 'fallback':True})(inner_call_fallback) + dppl_fallback_true = dppl() + + ref_result = inner_call_fallback() + + np.testing.assert_array_equal(dppl_fallback_true, ref_result) + self.assertTrue('Failed to lower parfor on DPPL-device' in msg_fallback_true.getvalue()) + + @unittest.expectedFailure + def test_dppl_fallback_false(self): + @numba.jit + def fill_value(i): + return i + + def inner_call_fallback(): + x = 10 + a = np.empty(shape=x, dtype=np.float32) + + for i in numba.prange(x): + a[i] = fill_value(i) + + return a + + dppl = numba.njit(parallel={'offload':True, 'fallback':False})(inner_call_fallback) + dppl_fallback_false = dppl() + + ref_result = inner_call_fallback() + + not np.testing.assert_array_equal(dppl_fallback_false, ref_result) + + @unittest.expectedFailure + def test_dppl_fallback_non(self): + @numba.jit + def fill_value(i): + return i + + def inner_call_fallback(): + x = 10 + a = np.empty(shape=x, dtype=np.float32) + + for i in numba.prange(x): + a[i] = fill_value(i) + + return a + + dppl = numba.njit(parallel={'offload':True})(inner_call_fallback) + dppl_fallback_non = dppl() + + ref_result = inner_call_fallback() + + not np.testing.assert_array_equal(dppl_fallback_non, ref_result) + + +if __name__ == '__main__': + unittest.main() From be7378f5cbd1baf81f6657468a299ff7e78ffa63 Mon Sep 17 00:00:00 2001 From: etotmeni Date: Thu, 10 Dec 2020 10:56:30 -0600 Subject: [PATCH 2/5] change default behaviour --- numba_dppy/config.py | 2 +- numba_dppy/target_dispatcher.py | 4 -- .../tests/test_controllable_fallback.py | 44 +++++++------------ 3 files changed, 16 insertions(+), 34 deletions(-) diff --git a/numba_dppy/config.py b/numba_dppy/config.py index 3969ca7206..a15c2aa085 100644 --- a/numba_dppy/config.py +++ b/numba_dppy/config.py @@ -36,4 +36,4 @@ def _readenv(): ... SPIRV_VAL = _readenv("NUMBA_DPPY_SPIRV_VAL", int, 0) # Fallback to CPU -FALLBACK_OPTION = _readenv("NUMBA_DPPY_FALLBACK_OPTION", int, 0) +FALLBACK_OPTION = _readenv("NUMBA_DPPY_FALLBACK_OPTION", int, 1) diff --git a/numba_dppy/target_dispatcher.py b/numba_dppy/target_dispatcher.py index 5f487f2830..a37f6ae507 100644 --- a/numba_dppy/target_dispatcher.py +++ b/numba_dppy/target_dispatcher.py @@ -60,10 +60,6 @@ def get_current_disp(self): target = self.__target parallel = self.__parallel offload = isinstance(parallel, dict) and parallel.get('offload') is True - fallback = isinstance(parallel, dict) and parallel.get('fallback') - - if fallback: - numba_dppy.config.FALLBACK_OPTION = 1 if (dpctl.is_in_device_context() or offload): if not self.__is_with_context_target(target): diff --git a/numba_dppy/tests/test_controllable_fallback.py b/numba_dppy/tests/test_controllable_fallback.py index b4b75e282a..79ac1955c1 100644 --- a/numba_dppy/tests/test_controllable_fallback.py +++ b/numba_dppy/tests/test_controllable_fallback.py @@ -3,9 +3,9 @@ import numpy as np import numba -import numba_dppy, numba_dppy as dppl +import numba_dppy from numba_dppy.testing import unittest -from numba_dppy.testing import DPPLTestCase +from numba_dppy.testing import DPPYTestCase from numba.tests.support import captured_stderr import dpctl import sys @@ -13,7 +13,7 @@ @unittest.skipUnless(dpctl.has_gpu_queues(), 'test only on GPU system') -class TestDPPLFallback(DPPLTestCase): +class TestDPPYFallback(DPPYTestCase): def test_dppl_fallback_true(self): @numba.jit def fill_value(i): @@ -28,14 +28,16 @@ def inner_call_fallback(): return a + numba_dppy.compiler.DEBUG = 1 with captured_stderr() as msg_fallback_true: - dppl = numba.njit(parallel={'offload':True, 'fallback':True})(inner_call_fallback) + dppl = numba.njit(parallel=True)(inner_call_fallback) dppl_fallback_true = dppl() ref_result = inner_call_fallback() + numba_dppy.compiler.DEBUG = 0 np.testing.assert_array_equal(dppl_fallback_true, ref_result) - self.assertTrue('Failed to lower parfor on DPPL-device' in msg_fallback_true.getvalue()) + self.assertTrue('Failed to lower parfor on DPPY-device' in msg_fallback_true.getvalue()) @unittest.expectedFailure def test_dppl_fallback_false(self): @@ -52,34 +54,18 @@ def inner_call_fallback(): return a - dppl = numba.njit(parallel={'offload':True, 'fallback':False})(inner_call_fallback) - dppl_fallback_false = dppl() + numba_dppy.compiler.DEBUG = 1 + numba_dppy.config.FALLBACK_OPTION = 0 + with captured_stderr() as msg_fallback_true: + dppl = numba.njit(parallel={'offload':True, 'fallback':False})(inner_call_fallback) + dppl_fallback_false = dppl() ref_result = inner_call_fallback() + numba_dppy.config.FALLBACK_OPTION = 1 + numba_dppy.compiler.DEBUG = 0 not np.testing.assert_array_equal(dppl_fallback_false, ref_result) - - @unittest.expectedFailure - def test_dppl_fallback_non(self): - @numba.jit - def fill_value(i): - return i - - def inner_call_fallback(): - x = 10 - a = np.empty(shape=x, dtype=np.float32) - - for i in numba.prange(x): - a[i] = fill_value(i) - - return a - - dppl = numba.njit(parallel={'offload':True})(inner_call_fallback) - dppl_fallback_non = dppl() - - ref_result = inner_call_fallback() - - not np.testing.assert_array_equal(dppl_fallback_non, ref_result) + not self.assertTrue('Failed to lower parfor on DPPY-device' in msg_fallback_true.getvalue()) if __name__ == '__main__': From 354b089e1d9cb4b019f1f016a5b456b8dbabbe4b Mon Sep 17 00:00:00 2001 From: etotmeni Date: Fri, 11 Dec 2020 06:32:12 -0600 Subject: [PATCH 3/5] Fix tests --- .../tests/test_controllable_fallback.py | 32 +++++++++++-------- 1 file changed, 18 insertions(+), 14 deletions(-) diff --git a/numba_dppy/tests/test_controllable_fallback.py b/numba_dppy/tests/test_controllable_fallback.py index 79ac1955c1..1a50b8797e 100644 --- a/numba_dppy/tests/test_controllable_fallback.py +++ b/numba_dppy/tests/test_controllable_fallback.py @@ -30,8 +30,9 @@ def inner_call_fallback(): numba_dppy.compiler.DEBUG = 1 with captured_stderr() as msg_fallback_true: - dppl = numba.njit(parallel=True)(inner_call_fallback) - dppl_fallback_true = dppl() + with dpctl.device_context("opencl:gpu") as gpu_queue: + dppl = numba.njit(parallel=True)(inner_call_fallback) + dppl_fallback_true = dppl() ref_result = inner_call_fallback() numba_dppy.compiler.DEBUG = 0 @@ -54,18 +55,21 @@ def inner_call_fallback(): return a - numba_dppy.compiler.DEBUG = 1 - numba_dppy.config.FALLBACK_OPTION = 0 - with captured_stderr() as msg_fallback_true: - dppl = numba.njit(parallel={'offload':True, 'fallback':False})(inner_call_fallback) - dppl_fallback_false = dppl() - - ref_result = inner_call_fallback() - numba_dppy.config.FALLBACK_OPTION = 1 - numba_dppy.compiler.DEBUG = 0 - - not np.testing.assert_array_equal(dppl_fallback_false, ref_result) - not self.assertTrue('Failed to lower parfor on DPPY-device' in msg_fallback_true.getvalue()) + try: + numba_dppy.compiler.DEBUG = 1 + numba_dppy.config.FALLBACK_OPTION = 0 + with captured_stderr() as msg_fallback_true: + with dpctl.device_context("opencl:gpu") as gpu_queue: + dppl = numba.njit(parallel=True)(inner_call_fallback) + dppl_fallback_false = dppl() + + finally: + ref_result = inner_call_fallback() + numba_dppy.config.FALLBACK_OPTION = 1 + numba_dppy.compiler.DEBUG = 0 + + not np.testing.assert_array_equal(dppl_fallback_false, ref_result) + not self.assertTrue('Failed to lower parfor on DPPY-device' in msg_fallback_true.getvalue()) if __name__ == '__main__': From 17bf0db774491efc2de4e175fdc4db5cd41cfeb9 Mon Sep 17 00:00:00 2001 From: etotmeni Date: Fri, 11 Dec 2020 07:30:48 -0600 Subject: [PATCH 4/5] Small fixes --- numba_dppy/config.py | 3 +-- numba_dppy/dppy_lowerer.py | 2 +- numba_dppy/target_dispatcher.py | 1 - numba_dppy/tests/test_controllable_fallback.py | 12 ++++-------- 4 files changed, 6 insertions(+), 12 deletions(-) diff --git a/numba_dppy/config.py b/numba_dppy/config.py index a15c2aa085..76849ba00c 100644 --- a/numba_dppy/config.py +++ b/numba_dppy/config.py @@ -35,5 +35,4 @@ def _readenv(): ... # Turn SPIRV-VALIDATION ON/OFF switch SPIRV_VAL = _readenv("NUMBA_DPPY_SPIRV_VAL", int, 0) -# Fallback to CPU -FALLBACK_OPTION = _readenv("NUMBA_DPPY_FALLBACK_OPTION", int, 1) +FALLBACK_ON_CPU = _readenv("NUMBA_DPPY_FALLBACK_ON_CPU", int, 1) diff --git a/numba_dppy/dppy_lowerer.py b/numba_dppy/dppy_lowerer.py index 379470928a..b7f591d296 100644 --- a/numba_dppy/dppy_lowerer.py +++ b/numba_dppy/dppy_lowerer.py @@ -1172,7 +1172,7 @@ def lower(self): print("Failed to lower parfor on DPPY-device. Due to:\n", e) lowering.lower_extensions[parfor.Parfor].pop() if ((lowering.lower_extensions[parfor.Parfor][-1] == numba.parfors.parfor_lowering._lower_parfor_parallel) and - numba_dppy.config.FALLBACK_OPTION == 1): + numba_dppy.config.FALLBACK_ON_CPU == 1): self.cpu_lower.lower() self.base_lower = self.cpu_lower else: diff --git a/numba_dppy/target_dispatcher.py b/numba_dppy/target_dispatcher.py index a37f6ae507..dde38eb75b 100644 --- a/numba_dppy/target_dispatcher.py +++ b/numba_dppy/target_dispatcher.py @@ -1,7 +1,6 @@ from numba.core import registry, serialize, dispatcher from numba import types from numba.core.errors import UnsupportedError -import numba_dppy import dpctl from numba.core.compiler_lock import global_compiler_lock diff --git a/numba_dppy/tests/test_controllable_fallback.py b/numba_dppy/tests/test_controllable_fallback.py index 1a50b8797e..ba7ff2caff 100644 --- a/numba_dppy/tests/test_controllable_fallback.py +++ b/numba_dppy/tests/test_controllable_fallback.py @@ -1,5 +1,3 @@ -from __future__ import print_function, division, absolute_import - import numpy as np import numba @@ -8,13 +6,11 @@ from numba_dppy.testing import DPPYTestCase from numba.tests.support import captured_stderr import dpctl -import sys -import io @unittest.skipUnless(dpctl.has_gpu_queues(), 'test only on GPU system') class TestDPPYFallback(DPPYTestCase): - def test_dppl_fallback_true(self): + def test_dppy_fallback_true(self): @numba.jit def fill_value(i): return i @@ -41,7 +37,7 @@ def inner_call_fallback(): self.assertTrue('Failed to lower parfor on DPPY-device' in msg_fallback_true.getvalue()) @unittest.expectedFailure - def test_dppl_fallback_false(self): + def test_dppy_fallback_false(self): @numba.jit def fill_value(i): return i @@ -57,7 +53,7 @@ def inner_call_fallback(): try: numba_dppy.compiler.DEBUG = 1 - numba_dppy.config.FALLBACK_OPTION = 0 + numba_dppy.config.FALLBACK_ON_CPU = 0 with captured_stderr() as msg_fallback_true: with dpctl.device_context("opencl:gpu") as gpu_queue: dppl = numba.njit(parallel=True)(inner_call_fallback) @@ -65,7 +61,7 @@ def inner_call_fallback(): finally: ref_result = inner_call_fallback() - numba_dppy.config.FALLBACK_OPTION = 1 + numba_dppy.config.FALLBACK_ON_CPU = 1 numba_dppy.compiler.DEBUG = 0 not np.testing.assert_array_equal(dppl_fallback_false, ref_result) From 34121dbc132963b3d7a85843d525d539fbc5c732 Mon Sep 17 00:00:00 2001 From: etotmeni Date: Fri, 11 Dec 2020 07:41:35 -0600 Subject: [PATCH 5/5] Dppl to dppy --- numba_dppy/tests/test_controllable_fallback.py | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/numba_dppy/tests/test_controllable_fallback.py b/numba_dppy/tests/test_controllable_fallback.py index ba7ff2caff..45405b9958 100644 --- a/numba_dppy/tests/test_controllable_fallback.py +++ b/numba_dppy/tests/test_controllable_fallback.py @@ -27,13 +27,13 @@ def inner_call_fallback(): numba_dppy.compiler.DEBUG = 1 with captured_stderr() as msg_fallback_true: with dpctl.device_context("opencl:gpu") as gpu_queue: - dppl = numba.njit(parallel=True)(inner_call_fallback) - dppl_fallback_true = dppl() + dppy = numba.njit(parallel=True)(inner_call_fallback) + dppy_fallback_true = dppy() ref_result = inner_call_fallback() numba_dppy.compiler.DEBUG = 0 - np.testing.assert_array_equal(dppl_fallback_true, ref_result) + np.testing.assert_array_equal(dppy_fallback_true, ref_result) self.assertTrue('Failed to lower parfor on DPPY-device' in msg_fallback_true.getvalue()) @unittest.expectedFailure @@ -56,15 +56,15 @@ def inner_call_fallback(): numba_dppy.config.FALLBACK_ON_CPU = 0 with captured_stderr() as msg_fallback_true: with dpctl.device_context("opencl:gpu") as gpu_queue: - dppl = numba.njit(parallel=True)(inner_call_fallback) - dppl_fallback_false = dppl() + dppy = numba.njit(parallel=True)(inner_call_fallback) + dppy_fallback_false = dppy() finally: ref_result = inner_call_fallback() numba_dppy.config.FALLBACK_ON_CPU = 1 numba_dppy.compiler.DEBUG = 0 - not np.testing.assert_array_equal(dppl_fallback_false, ref_result) + not np.testing.assert_array_equal(dppy_fallback_false, ref_result) not self.assertTrue('Failed to lower parfor on DPPY-device' in msg_fallback_true.getvalue())