From ccfd8cd2a8f065e776d061ed8758b5f83253e580 Mon Sep 17 00:00:00 2001 From: TsafrirA <113579969+TsafrirA@users.noreply.github.com> Date: Mon, 24 Jul 2023 15:32:04 +0300 Subject: [PATCH] Fix Pulse channel index validation (#10476) * Correct channel index validation * Add tests and release note. (cherry picked from commit 802a735ebea547d0d96339c2de4a10f04b0ab8a6) --- qiskit/pulse/channels.py | 2 +- ...l-validation-bug-fix-c06f8445cecc8478.yaml | 5 +++ test/python/pulse/test_channels.py | 36 +++++++++++++++++++ 3 files changed, 42 insertions(+), 1 deletion(-) create mode 100644 releasenotes/notes/channel-validation-bug-fix-c06f8445cecc8478.yaml diff --git a/qiskit/pulse/channels.py b/qiskit/pulse/channels.py index c88fddadd77..687b837700d 100644 --- a/qiskit/pulse/channels.py +++ b/qiskit/pulse/channels.py @@ -121,7 +121,7 @@ def _validate_index(self, index: Any) -> None: if index.is_integer(): index = int(index) - if not isinstance(index, (int, np.integer)) and index < 0: + if not isinstance(index, (int, np.integer)) or index < 0: raise PulseError("Channel index must be a nonnegative integer") @property diff --git a/releasenotes/notes/channel-validation-bug-fix-c06f8445cecc8478.yaml b/releasenotes/notes/channel-validation-bug-fix-c06f8445cecc8478.yaml new file mode 100644 index 00000000000..b68ae2a68df --- /dev/null +++ b/releasenotes/notes/channel-validation-bug-fix-c06f8445cecc8478.yaml @@ -0,0 +1,5 @@ +--- +fixes: + - | + Fixed a bug in :class:`.pulse.Channel` where index validation was done incorrectly and only + raised an error when the index was both non-integer and negative, instead of either. diff --git a/test/python/pulse/test_channels.py b/test/python/pulse/test_channels.py index 604202fb575..2ad0d08fe25 100644 --- a/test/python/pulse/test_channels.py +++ b/test/python/pulse/test_channels.py @@ -25,6 +25,7 @@ PulseChannel, RegisterSlot, SnapshotChannel, + PulseError, ) from qiskit.test import QiskitTestCase @@ -88,6 +89,13 @@ def test_default(self): self.assertEqual(memory_slot.name, "m123") self.assertTrue(isinstance(memory_slot, ClassicalIOChannel)) + def test_validation(self): + """Test channel validation""" + with self.assertRaises(PulseError): + MemorySlot(0.5) + with self.assertRaises(PulseError): + MemorySlot(-1) + class TestRegisterSlot(QiskitTestCase): """RegisterSlot tests.""" @@ -100,6 +108,13 @@ def test_default(self): self.assertEqual(register_slot.name, "c123") self.assertTrue(isinstance(register_slot, ClassicalIOChannel)) + def test_validation(self): + """Test channel validation""" + with self.assertRaises(PulseError): + RegisterSlot(0.5) + with self.assertRaises(PulseError): + RegisterSlot(-1) + class TestSnapshotChannel(QiskitTestCase): """SnapshotChannel tests.""" @@ -123,6 +138,13 @@ def test_default(self): self.assertEqual(drive_channel.index, 123) self.assertEqual(drive_channel.name, "d123") + def test_validation(self): + """Test channel validation""" + with self.assertRaises(PulseError): + DriveChannel(0.5) + with self.assertRaises(PulseError): + DriveChannel(-1) + class TestControlChannel(QiskitTestCase): """ControlChannel tests.""" @@ -134,6 +156,13 @@ def test_default(self): self.assertEqual(control_channel.index, 123) self.assertEqual(control_channel.name, "u123") + def test_validation(self): + """Test channel validation""" + with self.assertRaises(PulseError): + ControlChannel(0.5) + with self.assertRaises(PulseError): + ControlChannel(-1) + class TestMeasureChannel(QiskitTestCase): """MeasureChannel tests.""" @@ -145,6 +174,13 @@ def test_default(self): self.assertEqual(measure_channel.index, 123) self.assertEqual(measure_channel.name, "m123") + def test_validation(self): + """Test channel validation""" + with self.assertRaises(PulseError): + MeasureChannel(0.5) + with self.assertRaises(PulseError): + MeasureChannel(-1) + if __name__ == "__main__": unittest.main()