From c1e7a82e975d97e054b769d615c36efb287d7488 Mon Sep 17 00:00:00 2001 From: whitequark Date: Thu, 16 Jul 2015 14:58:40 +0300 Subject: [PATCH] Add IndexError and ValueError builtins. --- artiq/compiler/builtins.py | 16 +++++++++++++++- artiq/compiler/prelude.py | 2 ++ artiq/compiler/transforms/inferencer.py | 20 +++++++++++++++++++- 3 files changed, 36 insertions(+), 2 deletions(-) diff --git a/artiq/compiler/builtins.py b/artiq/compiler/builtins.py index 4675c458c..c349baac5 100644 --- a/artiq/compiler/builtins.py +++ b/artiq/compiler/builtins.py @@ -43,8 +43,16 @@ class TRange(types.TMono): ]) class TException(types.TMono): + def __init__(self, name="Exception"): + super().__init__(name) + +class TIndexError(types.TMono): def __init__(self): - super().__init__("Exception") + super().__init__("IndexError") + +class TValueError(types.TMono): + def __init__(self): + super().__init__("ValueError") def fn_bool(): return types.TConstructor("bool") @@ -61,6 +69,12 @@ def fn_list(): def fn_Exception(): return types.TExceptionConstructor("Exception") +def fn_IndexError(): + return types.TExceptionConstructor("IndexError") + +def fn_ValueError(): + return types.TExceptionConstructor("ValueError") + def fn_range(): return types.TBuiltinFunction("range") diff --git a/artiq/compiler/prelude.py b/artiq/compiler/prelude.py index d024c2423..98432b753 100644 --- a/artiq/compiler/prelude.py +++ b/artiq/compiler/prelude.py @@ -13,6 +13,8 @@ def globals(): "list": builtins.fn_list(), "range": builtins.fn_range(), "Exception": builtins.fn_Exception(), + "IndexError": builtins.fn_IndexError(), + "ValueError": builtins.fn_ValueError(), "len": builtins.fn_len(), "round": builtins.fn_round(), "syscall": builtins.fn_syscall(), diff --git a/artiq/compiler/transforms/inferencer.py b/artiq/compiler/transforms/inferencer.py index 5400da937..9e927d60f 100644 --- a/artiq/compiler/transforms/inferencer.py +++ b/artiq/compiler/transforms/inferencer.py @@ -432,7 +432,25 @@ class Inferencer(algorithm.Visitor): node.func.loc, notes=valid_forms) self.engine.process(diag) - if types.is_builtin(typ, "bool"): + if types.is_exn_constructor(typ): + exns = { + "IndexError": builtins.TIndexError, + "ValueError": builtins.TValueError, + } + for exn in exns: + if types.is_exn_constructor(typ, exn): + valid_forms = lambda: [ + valid_form("{exn}() -> {exn}".format(exn=exn)) + ] + + if len(node.args) == 0 and len(node.keywords) == 0: + pass # False + else: + diagnose(valid_forms()) + + self._unify(node.type, exns[exn](), + node.loc, None) + elif types.is_builtin(typ, "bool"): valid_forms = lambda: [ valid_form("bool() -> bool"), valid_form("bool(x:'a) -> bool")