diff --git a/doc/source/tools.rst b/doc/source/tools.rst index f9cf05de0b6fa6f4f3a3e69b1e1abf90acc33145..048d5c7d3c0f9548afc17e485e2427e3d3f5ae37 100644 --- a/doc/source/tools.rst +++ b/doc/source/tools.rst @@ -98,8 +98,7 @@ Testing The following two environment variables are also supported to control device/platform choice:: - PYOPENCL_TEST_PLATFORM_BLACKLIST=nvidia,intel - PYOPENCL_TEST_DEVICE_BLACKLIST=nvidia:260,intel:i5 + PYOPENCL_TEST=0:0,1;intel=i5,i7 Device Characterization ----------------------- diff --git a/pyopencl/tools.py b/pyopencl/tools.py index 8e1accbbc0e06e6bd1caccb6cdec643719b96af6..02b43ca87e113b8e08590c18f886339b8a9c53c3 100644 --- a/pyopencl/tools.py +++ b/pyopencl/tools.py @@ -126,41 +126,60 @@ def pytest_generate_tests_for_pyopencl(metafunc): def __str__(self): return "<context factory for %s>" % self.device - platform_blacklist = [] - device_blacklist = [] - import os - bl_string = os.environ.get("PYOPENCL_TEST_PLATFORM_BLACKLIST", "") - if bl_string: - platform_blacklist = [s.lower() for s in bl_string.split(",")] - bl_string = os.environ.get("PYOPENCL_TEST_DEVICE_BLACKLIST", "") - if bl_string: - for s in bl_string.split(","): - vendor_name, device_name = s.split(":") - device_blacklist.append((vendor_name.lower(), device_name.lower())) + dev_string = os.environ.get("PYOPENCL_TEST", None) + + def find_cl_obj(objs, identifier): + try: + num = int(identifier) + except Exception: + pass + else: + return objs[num] + + found = False + for obj in objs: + if identifier.lower() in (obj.name + ' ' + obj.vendor).lower(): + return obj + if not found: + raise RuntimeError("object '%s' not found" % identifier) + + if dev_string: + # PYOPENCL_TEST=0:0,1;intel:i5 + + test_plat_and_dev = [] # list of tuples (platform, [device, device, ...]) + + for entry in dev_string.split(";"): + lhsrhs = entry.split(":") - from pytools import any + if len(lhsrhs) == 1: + platform = find_cl_obj(cl.get_platforms(), lhsrhs[0]) + test_plat_and_dev.append((platform, platform.get_devices())) + + elif len(lhsrhs) != 2: + raise RuntimeError("invalid syntax of PYOPENCL_TEST") + else: + plat_str, dev_strs = lhsrhs + + platform = find_cl_obj(cl.get_platforms(), plat_str) + devs = platform.get_devices() + test_plat_and_dev.append( + (platform, [find_cl_obj(devs, dev_id) for dev_id in dev_strs.split(",")])) + else: + test_plat_and_dev = [ + (platform, platform.get_devices()) + for platform in cl.get_platforms()] if ("device" in metafunc.funcargnames or "ctx_factory" in metafunc.funcargnames or "ctx_getter" in metafunc.funcargnames): arg_dict = {} - for platform in cl.get_platforms(): + for platform, plat_devs in test_plat_and_dev: if "platform" in metafunc.funcargnames: arg_dict["platform"] = platform - platform_ish = (platform.name + ' ' + platform.vendor).lower() - if any(bl_plat in platform_ish for bl_plat in platform_blacklist): - continue - - for device in platform.get_devices(): - - device_ish = (device.name + ' ' + platform.vendor).lower() - if any(bl_plat in platform_ish and bl_dev in device_ish - for bl_plat, bl_dev in device_blacklist): - continue - + for device in plat_devs: if "device" in metafunc.funcargnames: arg_dict["device"] = device @@ -178,12 +197,7 @@ def pytest_generate_tests_for_pyopencl(metafunc): for arg, value in arg_dict.iteritems())) elif "platform" in metafunc.funcargnames: - for platform in cl.get_platforms(): - - platform_ish = (platform.name + ' ' + platform.vendor).lower() - if any(bl_plat in platform_ish for bl_plat in platform_blacklist): - continue - + for platform, plat_devs in test_plat_and_dev: metafunc.addcall( funcargs=dict(platform=platform), id=str(platform))