diff --git a/artiq/compiler/embedding.py b/artiq/compiler/embedding.py index 1c08bbdfe..0b38e525d 100644 --- a/artiq/compiler/embedding.py +++ b/artiq/compiler/embedding.py @@ -88,18 +88,32 @@ class EmbeddingMap: self.subkernel_message_map[msg_type.name] = msg_id self.object_reverse_map[obj_id] = msg_id - self.preallocate_runtime_exception_names(["RuntimeError", - "RTIOUnderflow", - "RTIOOverflow", - "RTIODestinationUnreachable", - "DMAError", - "I2CError", - "CacheError", - "SPIError", - "0:ZeroDivisionError", - "0:IndexError", - "UnwrapNoneError", - "SubkernelError"]) + # Keep this list of exceptions in sync with `EXCEPTION_ID_LOOKUP` in `artiq.firmware.ksupport.eh_artiq`` + # The exceptions declared here should be defined in `artiq.coredeive.exceptions`` + # Without sync, test cases in artiq.test.coredevice.test_exceptions would fail + self.preallocate_runtime_exception_names([ + "RTIOUnderflow", + "RTIOOverflow", + "RTIODestinationUnreachable", + "DMAError", + "I2CError", + "CacheError", + "SPIError", + "SubkernelError", + + "0:AssertionError", + "0:AttributeError", + "0:IndexError", + "0:IOError", + "0:KeyError", + "0:NotImplementedError", + "0:OverflowError", + "0:RuntimeError", + "0:TimeoutError", + "0:TypeError", + "0:ValueError", + "0:ZeroDivisionError" + ]) def preallocate_runtime_exception_names(self, names): for i, name in enumerate(names): diff --git a/artiq/coredevice/exceptions.py b/artiq/coredevice/exceptions.py index 9db446e1d..7a928eb8b 100644 --- a/artiq/coredevice/exceptions.py +++ b/artiq/coredevice/exceptions.py @@ -6,12 +6,26 @@ import os from artiq import __artiq_dir__ as artiq_dir from artiq.coredevice.runtime import source_loader +""" +This file should provide class definition for all the exceptions declared in `EmbeddingMap` in artiq.compiler.embedding + +For python builtin exceptions, use the `builtins` module +For artiq specific exceptions, inherit from `Exception` class +""" -ZeroDivisionError = builtins.ZeroDivisionError -ValueError = builtins.ValueError -IndexError = builtins.IndexError -RuntimeError = builtins.RuntimeError AssertionError = builtins.AssertionError +AttributeError = builtins.AttributeError +IndexError = builtins.IndexError +IOError = builtins.IOError +KeyError = builtins.KeyError +NotImplementedError = builtins.NotImplementedError +OverflowError = builtins.OverflowError +RuntimeError = builtins.RuntimeError +TimeoutError = builtins.TimeoutError +TypeError = builtins.TypeError +ValueError = builtins.ValueError +ZeroDivisionError = builtins.ZeroDivisionError +OSError = builtins.OSError class CoreException: @@ -157,13 +171,13 @@ class SubkernelError(Exception): class ClockFailure(Exception): """Raised when RTIO PLL has lost lock.""" - + artiq_builtin = True class I2CError(Exception): """Raised when a I2C transaction fails.""" - pass + artiq_builtin = True class SPIError(Exception): """Raised when a SPI transaction fails.""" - pass + artiq_builtin = True diff --git a/artiq/firmware/ksupport/eh_artiq.rs b/artiq/firmware/ksupport/eh_artiq.rs index 04c6e723e..fbddb47ec 100644 --- a/artiq/firmware/ksupport/eh_artiq.rs +++ b/artiq/firmware/ksupport/eh_artiq.rs @@ -328,19 +328,28 @@ extern fn stop_fn(_version: c_int, } } -static EXCEPTION_ID_LOOKUP: [(&str, u32); 12] = [ - ("RuntimeError", 0), - ("RTIOUnderflow", 1), - ("RTIOOverflow", 2), - ("RTIODestinationUnreachable", 3), - ("DMAError", 4), - ("I2CError", 5), - ("CacheError", 6), - ("SPIError", 7), - ("ZeroDivisionError", 8), - ("IndexError", 9), - ("UnwrapNoneError", 10), - ("SubkernelError", 11) +// Must be kept in sync with `artq.compiler.embedding` +static EXCEPTION_ID_LOOKUP: [(&str, u32); 20] = [ + ("RTIOUnderflow", 0), + ("RTIOOverflow", 1), + ("RTIODestinationUnreachable", 2), + ("DMAError", 3), + ("I2CError", 4), + ("CacheError", 5), + ("SPIError", 6), + ("SubkernelError", 7), + ("AssertionError", 8), + ("AttributeError", 9), + ("IndexError", 10), + ("IOError", 11), + ("KeyError", 12), + ("NotImplementedError", 13), + ("OverflowError", 14), + ("RuntimeError", 15), + ("TimeoutError", 16), + ("TypeError", 17), + ("ValueError", 18), + ("ZeroDivisionError", 19), ]; pub fn get_exception_id(name: &str) -> u32 { diff --git a/artiq/test/lit/exceptions/catch_all.py b/artiq/test/lit/exceptions/catch_all.py index 1b4c38b8e..f3f497f12 100644 --- a/artiq/test/lit/exceptions/catch_all.py +++ b/artiq/test/lit/exceptions/catch_all.py @@ -8,7 +8,7 @@ def catch(f): except Exception as e: print(e) -# CHECK-L: 8(0, 0, 0) +# CHECK-L: 19(0, 0, 0) catch(lambda: 1/0) -# CHECK-L: 9(10, 1, 0) +# CHECK-L: 10(10, 1, 0) catch(lambda: [1.0][10]) diff --git a/artiq/test/lit/exceptions/catch_multi.py b/artiq/test/lit/exceptions/catch_multi.py index dbd8bcdec..72712785d 100644 --- a/artiq/test/lit/exceptions/catch_multi.py +++ b/artiq/test/lit/exceptions/catch_multi.py @@ -10,7 +10,7 @@ def catch(f): except IndexError as ie: print(ie) -# CHECK-L: 8(0, 0, 0) +# CHECK-L: 19(0, 0, 0) catch(lambda: 1/0) -# CHECK-L: 9(10, 1, 0) +# CHECK-L: 10(10, 1, 0) catch(lambda: [1.0][10]) diff --git a/artiq/test/lit/exceptions/reraise.py b/artiq/test/lit/exceptions/reraise.py index fd5eabd4a..ef3f02dd1 100644 --- a/artiq/test/lit/exceptions/reraise.py +++ b/artiq/test/lit/exceptions/reraise.py @@ -3,7 +3,7 @@ # REQUIRES: exceptions def f(): - # CHECK-L: Uncaught 8 + # CHECK-L: Uncaught 19 # CHECK-L: at input.py:${LINE:+1}: 1/0 diff --git a/artiq/test/lit/exceptions/reraise_update.py b/artiq/test/lit/exceptions/reraise_update.py index aac8cdae1..32e1d11dc 100644 --- a/artiq/test/lit/exceptions/reraise_update.py +++ b/artiq/test/lit/exceptions/reraise_update.py @@ -9,7 +9,7 @@ def g(): try: f() except Exception as e: - # CHECK-L: Uncaught 8 + # CHECK-L: Uncaught 19 # CHECK-L: at input.py:${LINE:+1}: raise e diff --git a/artiq/test/lit/exceptions/uncaught.py b/artiq/test/lit/exceptions/uncaught.py index 1d44d4b2a..a86f93b88 100644 --- a/artiq/test/lit/exceptions/uncaught.py +++ b/artiq/test/lit/exceptions/uncaught.py @@ -2,6 +2,6 @@ # RUN: OutputCheck %s --file-to-check=%t # REQUIRES: exceptions -# CHECK-L: Uncaught 8: cannot divide by zero (0, 0, 0) +# CHECK-L: Uncaught 19: cannot divide by zero (0, 0, 0) # CHECK-L: at input.py:${LINE:+1}: 1/0