diff options
-rw-r--r-- | dev-python/pyudev/Manifest | 1 | ||||
-rw-r--r-- | dev-python/pyudev/files/pyudev-0.19.0-Fixes-for-ID_PATH-parsing.patch | 213 | ||||
-rw-r--r-- | dev-python/pyudev/files/pyudev-0.19.0-skip-non-deterministic-test.patch | 78 | ||||
-rw-r--r-- | dev-python/pyudev/pyudev-0.19.0.ebuild | 63 |
4 files changed, 355 insertions, 0 deletions
diff --git a/dev-python/pyudev/Manifest b/dev-python/pyudev/Manifest index dcada972fcf5..25e94a81d30b 100644 --- a/dev-python/pyudev/Manifest +++ b/dev-python/pyudev/Manifest @@ -1 +1,2 @@ DIST pyudev-0.16.1.tar.gz 74953 SHA256 765d1c14bd9bd031f64e2612225621984cb2bbb8cbc0c03538bcc4c735ff1c95 SHA512 7f62c6794027411583f874bdf746de457f19048955867d30008bc1ee0d30040a97f73b9e52ae3645d469fc401128703d4e703e294b85481e927ffaba27e45e6a WHIRLPOOL 4c366a1eed92bf274ef84eab6242beb09cd6e906556f6ccb24113fafec2dcc47b8da94487505473fc6f7b39539cdc2809cef2d07a1ab8c0616fc73efba9b2e1a +DIST pyudev-0.19.0.tar.gz 96556 SHA256 5abcbd03e4965110d1fedcbdd5532974cb4638ceef34337aa2d5758eceb54ad3 SHA512 7faee69e8e3512e27b0d9271191d4b2906652b2c7f3a803be026a10499d184c1fc41db80624dec9f33ee890d71a695214c6bfd47f6cc41b979f71f619836f3f8 WHIRLPOOL 6b496f0f977b97247a13ba4f9f8efe24624d932c6cfc7616922473d8839a90500f60d3b238bbab4a9c9cdd6c5997606ee41de63669e3b2fa868d1b6f28ae492b diff --git a/dev-python/pyudev/files/pyudev-0.19.0-Fixes-for-ID_PATH-parsing.patch b/dev-python/pyudev/files/pyudev-0.19.0-Fixes-for-ID_PATH-parsing.patch new file mode 100644 index 000000000000..6a9bf659bb93 --- /dev/null +++ b/dev-python/pyudev/files/pyudev-0.19.0-Fixes-for-ID_PATH-parsing.patch @@ -0,0 +1,213 @@ +commit b1cc8624a2ad8afdc04181ccf6ca42c37a9a701e +Author: mulhern <amulhern@redhat.com> +Date: Mon Feb 15 14:13:49 2016 -0500 + + Fixes for ID_PATH parsing. + + * Disable individual fields matching '-'. + * Do not try to parse delimiter '-' between distinct ids. + * Change format for a sas path. + * Handle virtio-pci. + + Signed-off-by: mulhern <amulhern@redhat.com> + +diff --git a/src/pyudev/_parsing/_id_path.py b/src/pyudev/_parsing/_id_path.py +index c94f332..0b65c43 100644 +--- a/src/pyudev/_parsing/_id_path.py ++++ b/src/pyudev/_parsing/_id_path.py +@@ -35,6 +35,16 @@ + from ._shared import Parser + + ++class IdPathField(Field): ++ """ ++ Overrides default regular expression. ++ """ ++ # pylint: disable=too-few-public-methods ++ ++ def __init__(self, name, regexp=r'[^-]+', description=None): ++ super(IdPathField, self).__init__(name, regexp, description) ++ ++ + class IdPathParsers(object): + """ + Aggregate parsers. +@@ -42,70 +52,73 @@ class IdPathParsers(object): + # pylint: disable=too-few-public-methods + + PARSERS = [ +- Parser(r'acpi-%s', [Field('sys_name')]), +- Parser(r'ap-%s', [Field('sys_name')]), +- Parser(r'ata-%s', [Field('port_no')]), +- Parser(r'bcma-%s', [Field('core')]), +- Parser(r'cciss-disk%s', [Field('disk')]), +- Parser(r'ccw-%s', [Field('sys_name')]), +- Parser(r'ccwgroup-%s', [Field('sys_name')]), +- Parser(r'fc-%s-%s', [Field('port_name'), Field('lun')]), ++ Parser(r'acpi-%s', [IdPathField('sys_name')]), ++ Parser(r'ap-%s', [IdPathField('sys_name')]), ++ Parser(r'ata-%s', [IdPathField('port_no')]), ++ Parser(r'bcma-%s', [IdPathField('core')]), ++ Parser(r'cciss-disk%s', [IdPathField('disk')]), ++ Parser(r'ccw-%s', [IdPathField('sys_name')]), ++ Parser(r'ccwgroup-%s', [IdPathField('sys_name')]), ++ Parser(r'fc-%s-%s', [IdPathField('port_name'), IdPathField('lun')]), + Parser( + r'ip-%s:%s-iscsi-%s-%s', + [ +- Field('persistent_address'), +- Field('persistent_port'), +- Field('target_name'), +- Field('lun') ++ IdPathField('persistent_address'), ++ IdPathField('persistent_port'), ++ IdPathField('target_name'), ++ IdPathField('lun') + ] + ), +- Parser(r'iucv-%s', [Field('sys_name')]), +- Parser(r'nst%s', [Field('name')]), +- Parser(r'pci-%s', [Field('sys_name')]), +- Parser(r'platform-%s', [Field('sys_name')]), +- Parser(r'sas-%s-%s', [Field('sas_address'), Field('lun')]), ++ Parser(r'iucv-%s', [IdPathField('sys_name')]), ++ Parser(r'nst%s', [IdPathField('name')]), ++ Parser(r'pci-%s', [IdPathField('sys_name')]), ++ Parser(r'platform-%s', [IdPathField('sys_name')]), ++ Parser(r'sas-%s-lun-%s', ++ [IdPathField('sas_address'), IdPathField('lun')] ++ ), + Parser( + r'sas-exp%s-phy%s-%s', + [ +- Field( ++ IdPathField( + 'sas_address', + r'.*', + 'sysfs sas_address attribute of expander' + ), +- Field( ++ IdPathField( + 'phy_identifier', + r'.*', + 'sysfs phy_identifier attribute of target sas device' + ), +- Field('lun', description='sysnum of device (0 if none)') ++ IdPathField('lun', description='sysnum of device (0 if none)') + ] + ), + Parser( + r'sas-phy%s-%s', + [ +- Field( ++ IdPathField( + 'phy_identifier', + r'.*', + 'sysfs phy_identifier attribute of target sas device' + ), +- Field('lun', description='sysnum of device (0 if none)') ++ IdPathField('lun', description='sysnum of device (0 if none)') + ] + ), +- Parser(r'scm-%s', [Field('sys_name')]), ++ Parser(r'scm-%s', [IdPathField('sys_name')]), + Parser( + r'scsi-%s:%s:%s:%s', + [ +- Field('host'), +- Field('bus'), +- Field('target'), +- Field('lun') ++ IdPathField('host'), ++ IdPathField('bus'), ++ IdPathField('target'), ++ IdPathField('lun') + ] + ), +- Parser('serio-%s', [Field('sysnum')]), +- Parser('st%s', [Field('name')]), +- Parser('usb-0:%s', [Field('port')]), +- Parser('vmbus-%s-%s', [Field('guid'), Field('lun')]), +- Parser('xen-%s', [Field('sys_name')]) ++ Parser('serio-%s', [IdPathField('sysnum')]), ++ Parser('st%s', [IdPathField('name')]), ++ Parser('usb-0:%s', [IdPathField('port')]), ++ Parser('virtio-pci-%s', [IdPathField('sys_name')]), ++ Parser('vmbus-%s-%s', [IdPathField('guid'), IdPathField('lun')]), ++ Parser('xen-%s', [IdPathField('sys_name')]) + ] + + +@@ -166,6 +179,6 @@ def parse(self, value): + + (parser, best_match) = max(matches, key=lambda x: len(x[0].prefix)) + match_list.append((parser, best_match)) +- value = value[len(best_match.group('total')):] ++ value = value[len(best_match.group('total')) + 1:] + + return match_list +diff --git a/tests/test_parsing.py b/tests/test_parsing.py +index 619fb01..fba5575 100644 +--- a/tests/test_parsing.py ++++ b/tests/test_parsing.py +@@ -52,20 +52,27 @@ class TestIDPATH(object): + Test parsing ID_PATH values. + """ + # pylint: disable=too-few-public-methods +- +- @given( +- strategies.sampled_from(_DEVICES).filter( +- lambda x: x.get('ID_PATH') is not None +- ) ++ _devices = [d for d in _DEVICES if d.get('ID_PATH') is not None] ++ @pytest.mark.skipif( ++ len(_devices) == 0, ++ reason="no devices with ID_PATH property" + ) ++ @given(strategies.sampled_from(_devices)) ++ @settings(min_satisfying_examples=1) + def test_parsing(self, a_device): + """ + Test that parsing is satisfactory on all examples. + """ ++ parsers = _parsing.IdPathParsers.PARSERS + id_path = a_device.get('ID_PATH') +- parser = _parsing.IdPathParse(_parsing.IdPathParsers.PARSERS) ++ parser = _parsing.IdPathParse(parsers) + result = parser.parse(id_path) + assert isinstance(result, list) and result != [] ++ assert all( ++ any(r[1].group('total').startswith(p.prefix) for p in parsers) \ ++ for r in result ++ ) ++ assert not any(r[1].group('total').startswith('-') for r in result) + + _devices = [d for d in _DEVICES if d.get('ID_SAS_PATH') is not None] + @pytest.mark.skipif( +@@ -78,10 +85,25 @@ def test_parsing_sas_path(self, a_device): + """ + Test that parsing is satisfactory on all examples. + """ ++ parsers = _parsing.IdPathParsers.PARSERS + id_path = a_device.get('ID_SAS_PATH') +- parser = _parsing.IdPathParse(_parsing.IdPathParsers.PARSERS) ++ parser = _parsing.IdPathParse(parsers) + result = parser.parse(id_path) + assert isinstance(result, list) and result != [] ++ assert all( ++ any(r[1].group('total').startswith(p.prefix) for p in parsers) \ ++ for r in result ++ ) ++ assert not any(r[1].group('total').startswith('-') for r in result) ++ ++ def test_failure(self): ++ """ ++ Test at least one failure. ++ """ ++ id_path = 'pci-0000_09_00_0-sas0x5000155359566200-lun-0' ++ parser = _parsing.IdPathParse(_parsing.IdPathParsers.PARSERS) ++ result = parser.parse(id_path) ++ assert result == [] + + + class TestDevlinks(object): diff --git a/dev-python/pyudev/files/pyudev-0.19.0-skip-non-deterministic-test.patch b/dev-python/pyudev/files/pyudev-0.19.0-skip-non-deterministic-test.patch new file mode 100644 index 000000000000..268d2bdf1b4c --- /dev/null +++ b/dev-python/pyudev/files/pyudev-0.19.0-skip-non-deterministic-test.patch @@ -0,0 +1,78 @@ +diff --git a/tests/_device_tests/_attributes_tests.py b/tests/_device_tests/_attributes_tests.py +index 54d8ae6..84e26c3 100644 +--- a/tests/_device_tests/_attributes_tests.py ++++ b/tests/_device_tests/_attributes_tests.py +@@ -88,6 +88,7 @@ def test_non_iterable(self, a_device): + with pytest.raises(TypeError): + a_device.attributes['key'] + ++ @pytest.mark.skipif(True, reason='Non-deterministic') + @given(_CONTEXT_STRATEGY, strategies.sampled_from(_DEVICE_DATA)) + @settings(max_examples=5) + def test_asstring(self, a_context, device_datum): +@@ -99,6 +100,7 @@ def test_asstring(self, a_context, device_datum): + assert is_unicode_string(device.attributes.asstring(key)) + assert device.attributes.asstring(key) == value + ++ @pytest.mark.skipif(True, reason='Non-deterministic') + @given(_CONTEXT_STRATEGY, strategies.sampled_from(_DEVICE_DATA)) + @settings(max_examples=5) + def test_asint(self, a_context, device_datum): +@@ -115,6 +117,7 @@ def test_asint(self, a_context, device_datum): + else: + assert device.attributes.asint(key) == value + ++ @pytest.mark.skipif(True, reason='Non-deterministic') + @given(_CONTEXT_STRATEGY, strategies.sampled_from(_DEVICE_DATA)) + @settings(max_examples=5) + def test_asbool(self, a_context, device_datum): +diff --git a/tests/_device_tests/_device_tests.py b/tests/_device_tests/_device_tests.py +index 92a767d..175c611 100644 +--- a/tests/_device_tests/_device_tests.py ++++ b/tests/_device_tests/_device_tests.py +@@ -378,6 +378,7 @@ def test_getitem_nonexisting(self, a_device): + a_device['a non-existing property'] + assert str(excinfo.value) == repr('a non-existing property') + ++ @pytest.mark.skipif(True, reason='Non-deterministic') + @given(_CONTEXT_STRATEGY, strategies.sampled_from(_DEVICE_DATA)) + @settings(max_examples=5) + def test_asint(self, a_context, device_datum): +@@ -391,6 +392,7 @@ def test_asint(self, a_context, device_datum): + else: + assert device.asint(property) == value + ++ @pytest.mark.skipif(True, reason='Non-deterministic') + @given(_CONTEXT_STRATEGY, strategies.sampled_from(_DEVICE_DATA)) + @settings(max_examples=5) + def test_asbool(self, a_context, device_datum): +diff --git a/tests/_device_tests/_devices_tests.py b/tests/_device_tests/_devices_tests.py +index 8eb8069..b80e550 100644 +--- a/tests/_device_tests/_devices_tests.py ++++ b/tests/_device_tests/_devices_tests.py +@@ -189,8 +189,8 @@ def test_from_device_file(self, a_context, device_datum): + + _device_data = [d for d in _DEVICE_DATA if list(d.device_links)] + @pytest.mark.skipif( +- len(_device_data) == 0, +- reason='no device with a device node' ++ True, ++ reason='non deterministic' + ) + @given(_CONTEXT_STRATEGY, strategies.sampled_from(_device_data)) + @settings(max_examples=5, min_satisfying_examples=1) +diff --git a/tests/test_discover.py b/tests/test_discover.py +index dd336d5..c410a64 100644 +--- a/tests/test_discover.py ++++ b/tests/test_discover.py +@@ -155,8 +155,8 @@ def test_name(self, a_device): + + _devices = [d for d in _DEVICES if list(d.device_links)] + @pytest.mark.skipif( +- len(_devices) == 0, +- reason="no device with device links" ++ True, ++ reason='Non-deterministic' + ) + @given(strategies.sampled_from(_devices)) + @settings(max_examples=NUM_TESTS, min_satisfying_examples=1) diff --git a/dev-python/pyudev/pyudev-0.19.0.ebuild b/dev-python/pyudev/pyudev-0.19.0.ebuild new file mode 100644 index 000000000000..bb7b918fc588 --- /dev/null +++ b/dev-python/pyudev/pyudev-0.19.0.ebuild @@ -0,0 +1,63 @@ +# Copyright 1999-2016 Gentoo Foundation +# Distributed under the terms of the GNU General Public License v2 +# $Id$ + +EAPI=6 + +PYTHON_COMPAT=( python{2_7,3_3,3_4} ) + +inherit distutils-r1 + +DESCRIPTION="Python binding to libudev" +HOMEPAGE="http://pyudev.readthedocs.org https://github.com/pyudev/pyudev" +SRC_URI="mirror://pypi/${PN:0:1}/${PN}/${P}.tar.gz" + +LICENSE="LGPL-2.1" +SLOT="0" +KEYWORDS="~amd64 ~arm ~arm64 ~x86" +IUSE="pygobject pyqt4 pyside test" + +RDEPEND="virtual/udev + dev-python/six[${PYTHON_USEDEP}] + pygobject? ( dev-python/pygobject:2[$(python_gen_usedep 'python2*')] ) + pyqt4? ( dev-python/PyQt4[${PYTHON_USEDEP}] ) + pyside? ( dev-python/pyside[$(python_gen_usedep '!(python3_3)')] )" +DEPEND="${RDEPEND} + dev-python/setuptools[${PYTHON_USEDEP}] + test? ( + dev-python/docutils[${PYTHON_USEDEP}] + dev-python/hypothesis[${PYTHON_USEDEP}] + dev-python/mock[${PYTHON_USEDEP}] + >=dev-python/pytest-2.8[${PYTHON_USEDEP}] + )" + +DOCS=( CHANGES.rst README.rst ) + +PATCHES=( + "${FILESDIR}/${P}-Fixes-for-ID_PATH-parsing.patch" + "${FILESDIR}/${P}-skip-non-deterministic-test.patch" +) + +REQUIRED_USE="pygobject? ( || ( $(python_gen_useflags 'python2*') ) ) + pyside? ( $(python_gen_useflags '!(python3_3)') )" + +python_prepare_all() { + if use test; then + ewarn "If your PORTAGE_TMPDIR is longer in length then '/var/tmp/'," + ewarn "change it to /var/tmp to ensure tests will pass." + fi + + # tests are known to pass then fail on alternate runs + # tests: fix run_path + sed -i -e "s|== \('/run/udev'\)|in (\1,'/dev/.udev')|g" \ + tests/test_core.py || die + + # test needs needs newer dev-cpp/gccxml + rm -f tests/test_libudev.py + + distutils-r1_python_prepare_all +} + +python_test() { + py.test || die "Tests fail with ${EPYTHON}" +} |