guppylang-internals 0.24.0__py3-none-any.whl → 0.25.0__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (39) hide show
  1. guppylang_internals/__init__.py +1 -1
  2. guppylang_internals/ast_util.py +21 -0
  3. guppylang_internals/cfg/bb.py +20 -0
  4. guppylang_internals/cfg/builder.py +101 -3
  5. guppylang_internals/checker/core.py +4 -0
  6. guppylang_internals/checker/errors/generic.py +32 -1
  7. guppylang_internals/checker/errors/type_errors.py +14 -0
  8. guppylang_internals/checker/expr_checker.py +46 -10
  9. guppylang_internals/checker/func_checker.py +1 -1
  10. guppylang_internals/checker/linearity_checker.py +65 -0
  11. guppylang_internals/checker/modifier_checker.py +116 -0
  12. guppylang_internals/checker/stmt_checker.py +48 -1
  13. guppylang_internals/compiler/core.py +90 -53
  14. guppylang_internals/compiler/expr_compiler.py +49 -114
  15. guppylang_internals/compiler/modifier_compiler.py +174 -0
  16. guppylang_internals/compiler/stmt_compiler.py +15 -8
  17. guppylang_internals/definition/custom.py +35 -1
  18. guppylang_internals/definition/declaration.py +3 -4
  19. guppylang_internals/definition/parameter.py +8 -3
  20. guppylang_internals/definition/pytket_circuits.py +13 -41
  21. guppylang_internals/definition/struct.py +7 -4
  22. guppylang_internals/definition/ty.py +3 -3
  23. guppylang_internals/experimental.py +5 -0
  24. guppylang_internals/nodes.py +124 -0
  25. guppylang_internals/std/_internal/compiler/array.py +94 -282
  26. guppylang_internals/std/_internal/compiler/tket_exts.py +9 -2
  27. guppylang_internals/tracing/unpacking.py +19 -20
  28. guppylang_internals/tys/arg.py +18 -3
  29. guppylang_internals/tys/builtin.py +2 -5
  30. guppylang_internals/tys/const.py +33 -4
  31. guppylang_internals/tys/param.py +31 -16
  32. guppylang_internals/tys/parsing.py +8 -21
  33. guppylang_internals/tys/qubit.py +27 -0
  34. guppylang_internals/tys/subst.py +8 -26
  35. guppylang_internals/tys/ty.py +31 -21
  36. {guppylang_internals-0.24.0.dist-info → guppylang_internals-0.25.0.dist-info}/METADATA +3 -3
  37. {guppylang_internals-0.24.0.dist-info → guppylang_internals-0.25.0.dist-info}/RECORD +39 -36
  38. {guppylang_internals-0.24.0.dist-info → guppylang_internals-0.25.0.dist-info}/WHEEL +0 -0
  39. {guppylang_internals-0.24.0.dist-info → guppylang_internals-0.25.0.dist-info}/licenses/LICENCE +0 -0
@@ -177,13 +177,10 @@ def _array_to_hugr(args: Sequence[Argument], ctx: ToHugrContext) -> ht.Type:
177
177
  assert isinstance(ty_arg, TypeArg)
178
178
  assert isinstance(len_arg, ConstArg)
179
179
 
180
- # Linear elements are turned into an optional to enable unsafe indexing.
181
- # See `ArrayGetitemCompiler` for details.
182
- # Same also for classical arrays, see https://github.com/CQCL/guppylang/issues/629
183
- elem_ty = ht.Option(ty_arg.ty.to_hugr(ctx))
180
+ elem_ty = ty_arg.ty.to_hugr(ctx)
184
181
  hugr_arg = len_arg.to_hugr(ctx)
185
182
 
186
- return hugr.std.collections.value_array.ValueArray(elem_ty, hugr_arg)
183
+ return hugr.std.collections.borrow_array.BorrowArray(elem_ty, hugr_arg)
187
184
 
188
185
 
189
186
  def _frozenarray_to_hugr(args: Sequence[Argument], ctx: ToHugrContext) -> ht.Type:
@@ -8,6 +8,7 @@ from guppylang_internals.tys.var import BoundVar, ExistentialVar
8
8
 
9
9
  if TYPE_CHECKING:
10
10
  from guppylang_internals.tys.arg import ConstArg
11
+ from guppylang_internals.tys.subst import Subst
11
12
  from guppylang_internals.tys.ty import Type
12
13
 
13
14
 
@@ -39,6 +40,11 @@ class ConstBase(Transformable["Const"], ABC):
39
40
  """The existential type variables contained in this constant."""
40
41
  return set()
41
42
 
43
+ @property
44
+ def bound_vars(self) -> set[BoundVar]:
45
+ """The bound type variables contained in this constant."""
46
+ return self.ty.bound_vars
47
+
42
48
  def __str__(self) -> str:
43
49
  from guppylang_internals.tys.printing import TypePrinter
44
50
 
@@ -48,16 +54,18 @@ class ConstBase(Transformable["Const"], ABC):
48
54
  """Accepts a visitor on this constant."""
49
55
  visitor.visit(self)
50
56
 
51
- def transform(self, transformer: Transformer, /) -> "Const":
52
- """Accepts a transformer on this constant."""
53
- return transformer.transform(self) or self.cast()
54
-
55
57
  def to_arg(self) -> "ConstArg":
56
58
  """Wraps this constant into a type argument."""
57
59
  from guppylang_internals.tys.arg import ConstArg
58
60
 
59
61
  return ConstArg(self.cast())
60
62
 
63
+ def substitute(self, subst: "Subst") -> "Const":
64
+ """Substitutes existential variables in this constant."""
65
+ from guppylang_internals.tys.subst import Substituter
66
+
67
+ return self.transform(Substituter(subst))
68
+
61
69
 
62
70
  @dataclass(frozen=True)
63
71
  class ConstValue(ConstBase):
@@ -74,6 +82,10 @@ class ConstValue(ConstBase):
74
82
  """Casts an implementor of `ConstBase` into a `Const`."""
75
83
  return self
76
84
 
85
+ def transform(self, transformer: Transformer, /) -> "Const":
86
+ """Accepts a transformer on this constant."""
87
+ return transformer.transform(self) or self
88
+
77
89
 
78
90
  @dataclass(frozen=True)
79
91
  class BoundConstVar(BoundVar, ConstBase):
@@ -84,10 +96,21 @@ class BoundConstVar(BoundVar, ConstBase):
84
96
  `BoundConstVar(idx=0)`.
85
97
  """
86
98
 
99
+ @property
100
+ def bound_vars(self) -> set[BoundVar]:
101
+ """The bound type variables contained in this constant."""
102
+ return {self} | self.ty.bound_vars
103
+
87
104
  def cast(self) -> "Const":
88
105
  """Casts an implementor of `ConstBase` into a `Const`."""
89
106
  return self
90
107
 
108
+ def transform(self, transformer: Transformer, /) -> "Const":
109
+ """Accepts a transformer on this constant."""
110
+ return transformer.transform(self) or BoundConstVar(
111
+ transformer.transform(self.ty) or self.ty, self.display_name, self.idx
112
+ )
113
+
91
114
 
92
115
  @dataclass(frozen=True)
93
116
  class ExistentialConstVar(ExistentialVar, ConstBase):
@@ -110,5 +133,11 @@ class ExistentialConstVar(ExistentialVar, ConstBase):
110
133
  """Casts an implementor of `ConstBase` into a `Const`."""
111
134
  return self
112
135
 
136
+ def transform(self, transformer: Transformer, /) -> "Const":
137
+ """Accepts a transformer on this constant."""
138
+ return transformer.transform(self) or ExistentialConstVar(
139
+ transformer.transform(self.ty) or self.ty, self.display_name, self.id
140
+ )
141
+
113
142
 
114
143
  Const: TypeAlias = ConstValue | BoundConstVar | ExistentialConstVar
@@ -1,6 +1,6 @@
1
1
  from abc import ABC, abstractmethod
2
2
  from collections.abc import Sequence
3
- from dataclasses import dataclass, field
3
+ from dataclasses import dataclass, field, replace
4
4
  from typing import TYPE_CHECKING, TypeAlias
5
5
 
6
6
  from hugr import tys as ht
@@ -17,9 +17,9 @@ from guppylang_internals.tys.errors import WrongNumberOfTypeArgsError
17
17
  from guppylang_internals.tys.var import ExistentialVar
18
18
 
19
19
  if TYPE_CHECKING:
20
+ from guppylang_internals.tys.subst import PartialInst
20
21
  from guppylang_internals.tys.ty import Type
21
22
 
22
-
23
23
  # We define the `Parameter` type as a union of all `ParameterBase` subclasses defined
24
24
  # below. This models an algebraic data type and enables exhaustiveness checking in
25
25
  # pattern matches etc.
@@ -74,6 +74,10 @@ class ParameterBase(ToHugr[ht.TypeParam], ABC):
74
74
  parameter.
75
75
  """
76
76
 
77
+ @abstractmethod
78
+ def instantiate_bounds(self, inst: "PartialInst") -> Self:
79
+ """Instantiates bound variables mentioned in parameter bounds"""
80
+
77
81
 
78
82
  @dataclass(frozen=True)
79
83
  class TypeParam(ParameterBase):
@@ -142,10 +146,17 @@ class TypeParam(ParameterBase):
142
146
  BoundTypeVar(self.name, idx, self.must_be_copyable, self.must_be_droppable)
143
147
  )
144
148
 
149
+ def instantiate_bounds(self, inst: "PartialInst") -> "TypeParam":
150
+ """Instantiates bound variables mentioned in parameter bounds"""
151
+ # For now, type parameters don't have any bounds that could be instantiated
152
+ return self
153
+
145
154
  def to_hugr(self, ctx: ToHugrContext) -> ht.TypeParam:
146
155
  """Computes the Hugr representation of the parameter."""
147
156
  return ht.TypeTypeParam(
148
- bound=ht.TypeBound.Linear if self.can_be_linear else ht.TypeBound.Copyable
157
+ bound=ht.TypeBound.Copyable
158
+ if self.must_be_copyable
159
+ else ht.TypeBound.Linear
149
160
  )
150
161
 
151
162
  def __str__(self) -> str:
@@ -157,18 +168,12 @@ class TypeParam(ParameterBase):
157
168
  class ConstParam(ParameterBase):
158
169
  """A parameter of kind constant. Used to define fixed-size arrays etc."""
159
170
 
160
- ty: "Type"
171
+ ty: "Type" = field(hash=False)
161
172
 
162
173
  #: Marker to annotate if this parameter was implicitly generated by a `@comptime`
163
174
  #: annotated argument in a function signature.
164
175
  from_comptime_arg: bool = field(default=False, kw_only=True)
165
176
 
166
- def __post_init__(self) -> None:
167
- if self.ty.unsolved_vars:
168
- raise InternalGuppyError(
169
- "Attempted to create constant param with unsolved type"
170
- )
171
-
172
177
  def with_idx(self, idx: int) -> "ConstParam":
173
178
  """Returns a copy of the parameter with a new index."""
174
179
  return ConstParam(idx, self.name, self.ty)
@@ -178,13 +183,16 @@ class ConstParam(ParameterBase):
178
183
 
179
184
  Raises a user error if the argument is not valid.
180
185
  """
186
+ from guppylang_internals.tys.ty import unify
187
+
181
188
  match arg:
182
189
  case ConstArg(const):
183
- if const.ty != self.ty:
190
+ subst = unify(const.ty, self.ty, {})
191
+ if subst is None:
184
192
  raise GuppyTypeError(
185
193
  TypeMismatchError(loc, self.ty, const.ty, kind="argument")
186
194
  )
187
- return arg
195
+ return ConstArg(replace(const, ty=const.ty.substitute(subst)))
188
196
  case TypeArg(ty=ty):
189
197
  err = ExpectedError(
190
198
  loc, f"expression of type `{self.ty}`", got=f"type `{ty}`"
@@ -208,6 +216,13 @@ class ConstParam(ParameterBase):
208
216
  idx = self.idx
209
217
  return ConstArg(BoundConstVar(self.ty, self.name, idx))
210
218
 
219
+ def instantiate_bounds(self, inst: "PartialInst") -> "ConstParam":
220
+ """Instantiates bound variables mentioned in parameter bounds"""
221
+ from guppylang_internals.tys.subst import Instantiator
222
+
223
+ instantiator = Instantiator(inst)
224
+ return replace(self, ty=self.ty.transform(instantiator))
225
+
211
226
  def to_hugr(self, ctx: ToHugrContext) -> ht.TypeParam:
212
227
  """Computes the Hugr representation of the parameter."""
213
228
  from guppylang_internals.tys.ty import NumericType
@@ -231,6 +246,7 @@ def check_all_args(
231
246
  args: Sequence[Argument],
232
247
  type_name: str,
233
248
  loc: AstNode | None = None,
249
+ arg_locs: Sequence[AstNode] | None = None,
234
250
  ) -> None:
235
251
  """Checks a list of arguments against the given parameters.
236
252
 
@@ -245,7 +261,6 @@ def check_all_args(
245
261
  raise GuppyError(WrongNumberOfTypeArgsError(loc, exp, act, type_name))
246
262
 
247
263
  # Now check that the kinds match up
248
- for param, arg in zip(params, args, strict=True):
249
- # TODO: The error location is bad. We want the location of `arg`, not of the
250
- # whole thing.
251
- param.check_arg(arg, loc)
264
+ for i, (param, arg) in enumerate(zip(params, args, strict=True)):
265
+ arg_loc = arg_locs[i] if arg_locs else loc
266
+ param.instantiate_bounds(args).check_arg(arg, arg_loc)
@@ -39,7 +39,6 @@ from guppylang_internals.tys.errors import (
39
39
  WrongNumberOfTypeArgsError,
40
40
  )
41
41
  from guppylang_internals.tys.param import ConstParam, Parameter, TypeParam
42
- from guppylang_internals.tys.subst import BoundVarFinder
43
42
  from guppylang_internals.tys.ty import (
44
43
  FuncInput,
45
44
  FunctionType,
@@ -295,7 +294,13 @@ def check_function_arg(
295
294
 
296
295
  if sys.version_info >= (3, 12):
297
296
 
298
- def parse_parameter(node: ast.type_param, idx: int, globals: Globals) -> Parameter:
297
+ def parse_parameter(
298
+ node: ast.type_param,
299
+ idx: int,
300
+ globals: Globals,
301
+ param_var_mapping: dict[str, Parameter],
302
+ allow_free_vars: bool = False,
303
+ ) -> Parameter:
299
304
  """Parses a `Variable: Bound` generic type parameter declaration."""
300
305
  if isinstance(node, ast.TypeVarTuple | ast.ParamSpec):
301
306
  raise GuppyError(UnsupportedError(node, "Variadic generic parameters"))
@@ -331,18 +336,10 @@ if sys.version_info >= (3, 12):
331
336
  # parameters, so we pass an empty dict as the `param_var_mapping`.
332
337
  # TODO: In the future we might want to allow stuff like
333
338
  # `def foo[T, XS: array[T, 42]]` and so on
334
- ctx = TypeParsingCtx(globals, param_var_mapping={})
339
+ ctx = TypeParsingCtx(globals, param_var_mapping, allow_free_vars)
335
340
  ty = type_from_ast(bound, ctx)
336
341
  if not ty.copyable or not ty.droppable:
337
342
  raise GuppyError(LinearConstParamError(bound, ty))
338
-
339
- # TODO: For now we can only do `nat` const args since they lower to
340
- # Hugr bounded nats. Extend to arbitrary types via monomorphization.
341
- # See https://github.com/CQCL/guppylang/issues/1008
342
- if ty != NumericType(NumericType.Kind.Nat):
343
- raise GuppyError(
344
- UnsupportedError(bound, f"`{ty}` generic parameters")
345
- )
346
343
  return ConstParam(idx, node.name, ty)
347
344
 
348
345
 
@@ -363,16 +360,6 @@ def type_with_flags_from_ast(
363
360
  flags |= InputFlags.Comptime
364
361
  if not ty.copyable or not ty.droppable:
365
362
  raise GuppyError(LinearComptimeError(node.right, ty))
366
- # For now, we don't allow comptime annotations on generic inputs
367
- # TODO: In the future we might want to allow stuff like
368
- # `def foo[T: (Copy, Discard](x: T @comptime)`.
369
- # Also see the todo in `parse_parameter`.
370
- var_finder = BoundVarFinder()
371
- ty.visit(var_finder)
372
- if var_finder.bound_vars:
373
- raise GuppyError(
374
- UnsupportedError(node.left, "Generic comptime arguments")
375
- )
376
363
  case _:
377
364
  raise GuppyError(InvalidFlagError(node.right))
378
365
  return ty, flags
@@ -0,0 +1,27 @@
1
+ import functools
2
+ from typing import cast
3
+
4
+ from guppylang_internals.definition.ty import TypeDef
5
+ from guppylang_internals.tys.ty import Type
6
+
7
+
8
+ @functools.cache
9
+ def qubit_ty() -> Type:
10
+ """Returns the qubit type. Beware that this function imports guppylang definitions,
11
+ so, if called before the definitions are registered,
12
+ it might result in circular imports.
13
+ """
14
+ from guppylang.defs import GuppyDefinition
15
+ from guppylang.std.quantum import qubit
16
+
17
+ assert isinstance(qubit, GuppyDefinition)
18
+ qubit_ty = cast(TypeDef, qubit.wrapped).check_instantiate([])
19
+ return qubit_ty
20
+
21
+
22
+ def is_qubit_ty(ty: Type) -> bool:
23
+ """Checks if the given type is the qubit type.
24
+ This function results in circular imports if called
25
+ before qubit types are registered.
26
+ """
27
+ return ty == qubit_ty()
@@ -4,7 +4,7 @@ from typing import Any
4
4
 
5
5
  from guppylang_internals.error import InternalGuppyError
6
6
  from guppylang_internals.tys.arg import Argument, ConstArg, TypeArg
7
- from guppylang_internals.tys.common import Transformer, Visitor
7
+ from guppylang_internals.tys.common import Transformer
8
8
  from guppylang_internals.tys.const import (
9
9
  BoundConstVar,
10
10
  Const,
@@ -18,7 +18,7 @@ from guppylang_internals.tys.ty import (
18
18
  Type,
19
19
  TypeBase,
20
20
  )
21
- from guppylang_internals.tys.var import BoundVar, ExistentialVar
21
+ from guppylang_internals.tys.var import ExistentialVar
22
22
 
23
23
  Subst = dict[ExistentialVar, Type | Const]
24
24
  Inst = Sequence[Argument]
@@ -51,7 +51,8 @@ class Substituter(Transformer):
51
51
  class Instantiator(Transformer):
52
52
  """Type transformer that instantiates bound variables."""
53
53
 
54
- def __init__(self, inst: Inst) -> None:
54
+ def __init__(self, inst: PartialInst, allow_partial: bool = False) -> None:
55
+ self.allow_partial = allow_partial
55
56
  self.inst = inst
56
57
 
57
58
  @functools.singledispatchmethod
@@ -63,6 +64,8 @@ class Instantiator(Transformer):
63
64
  # Instantiate if type for the index is available
64
65
  if ty.idx < len(self.inst):
65
66
  arg = self.inst[ty.idx]
67
+ if arg is None and self.allow_partial:
68
+ return None
66
69
  assert isinstance(arg, TypeArg)
67
70
  return arg.ty
68
71
 
@@ -76,6 +79,8 @@ class Instantiator(Transformer):
76
79
  # Instantiate if const value for the index is available
77
80
  if c.idx < len(self.inst):
78
81
  arg = self.inst[c.idx]
82
+ if arg is None and self.allow_partial:
83
+ return None
79
84
  assert isinstance(arg, ConstArg)
80
85
  return arg.const
81
86
 
@@ -87,26 +92,3 @@ class Instantiator(Transformer):
87
92
  if ty.parametrized:
88
93
  raise InternalGuppyError("Tried to instantiate under binder")
89
94
  return None
90
-
91
-
92
- class BoundVarFinder(Visitor):
93
- """Type visitor that looks for occurrences of bound variables."""
94
-
95
- bound_vars: set[BoundVar]
96
-
97
- def __init__(self) -> None:
98
- self.bound_vars = set()
99
-
100
- @functools.singledispatchmethod
101
- def visit(self, ty: Any) -> bool: # type: ignore[override]
102
- return False
103
-
104
- @visit.register
105
- def _transform_BoundTypeVar(self, ty: BoundTypeVar) -> bool:
106
- self.bound_vars.add(ty)
107
- return False
108
-
109
- @visit.register
110
- def _transform_BoundConstVar(self, c: BoundConstVar) -> bool:
111
- self.bound_vars.add(c)
112
- return False
@@ -57,14 +57,11 @@ class TypeBase(ToHugr[ht.Type], Transformable["Type"], ABC):
57
57
  return not self.copyable and self.droppable
58
58
 
59
59
  @cached_property
60
- @abstractmethod
61
60
  def hugr_bound(self) -> ht.TypeBound:
62
- """The Hugr bound of this type, i.e. `Any`, `Copyable`, or `Equatable`.
63
-
64
- This needs to be specified explicitly, since opaque nonlinear types in a Hugr
65
- extension could be either declared as copyable or equatable. If we don't get the
66
- bound exactly right during serialisation, the Hugr validator will complain.
67
- """
61
+ """The Hugr bound of this type, i.e. `Any` or `Copyable`."""
62
+ if self.linear or self.affine:
63
+ return ht.TypeBound.Linear
64
+ return ht.TypeBound.Copyable
68
65
 
69
66
  @abstractmethod
70
67
  def cast(self) -> "Type":
@@ -79,6 +76,11 @@ class TypeBase(ToHugr[ht.Type], Transformable["Type"], ABC):
79
76
  """The existential type variables contained in this type."""
80
77
  return set()
81
78
 
79
+ @cached_property
80
+ def bound_vars(self) -> set[BoundVar]:
81
+ """The bound type variables contained in this type."""
82
+ return set()
83
+
82
84
  def substitute(self, subst: "Subst") -> "Type":
83
85
  """Substitutes existential variables in this type."""
84
86
  from guppylang_internals.tys.subst import Substituter
@@ -158,13 +160,17 @@ class ParametrizedTypeBase(TypeBase, ABC):
158
160
  """The existential type variables contained in this type."""
159
161
  return set().union(*(arg.unsolved_vars for arg in self.args))
160
162
 
163
+ @cached_property
164
+ def bound_vars(self) -> set[BoundVar]:
165
+ """The bound type variables contained in this type."""
166
+ return set().union(*(arg.bound_vars for arg in self.args))
167
+
161
168
  @cached_property
162
169
  def hugr_bound(self) -> ht.TypeBound:
163
- """The Hugr bound of this type, i.e. `Any`, `Copyable`, or `Equatable`."""
164
- if self.linear:
165
- return ht.TypeBound.Linear
170
+ """The Hugr bound of this type, i.e. `Any` or `Copyable`."""
166
171
  return ht.TypeBound.join(
167
- *(arg.ty.hugr_bound for arg in self.args if isinstance(arg, TypeArg))
172
+ super().hugr_bound,
173
+ *(arg.ty.hugr_bound for arg in self.args if isinstance(arg, TypeArg)),
168
174
  )
169
175
 
170
176
  def visit(self, visitor: Visitor) -> None:
@@ -187,14 +193,10 @@ class BoundTypeVar(TypeBase, BoundVar):
187
193
  copyable: bool
188
194
  droppable: bool
189
195
 
190
- @cached_property
191
- def hugr_bound(self) -> ht.TypeBound:
192
- """The Hugr bound of this type, i.e. `Any`, `Copyable`, or `Equatable`."""
193
- if self.linear:
194
- return ht.TypeBound.Linear
195
- # We're conservative and don't require equatability for non-linear variables.
196
- # This is fine since Guppy doesn't use the equatable feature anyways.
197
- return ht.TypeBound.Copyable
196
+ @property
197
+ def bound_vars(self) -> set[BoundVar]:
198
+ """The bound type variables contained in this type."""
199
+ return {self}
198
200
 
199
201
  def cast(self) -> "Type":
200
202
  """Casts an implementor of `TypeBase` into a `Type`."""
@@ -426,6 +428,14 @@ class FunctionType(ParametrizedTypeBase):
426
428
  """Whether the function is parametrized."""
427
429
  return len(self.params) > 0
428
430
 
431
+ @cached_property
432
+ def bound_vars(self) -> set[BoundVar]:
433
+ """The bound type variables contained in this type."""
434
+ if self.parametrized:
435
+ # Ensures that we don't look inside quantifiers
436
+ return set()
437
+ return super().bound_vars
438
+
429
439
  def cast(self) -> "Type":
430
440
  """Casts an implementor of `TypeBase` into a `Type`."""
431
441
  return self
@@ -506,7 +516,7 @@ class FunctionType(ParametrizedTypeBase):
506
516
  # However, we have to down-shift the de Bruijn index.
507
517
  if arg is None:
508
518
  param = param.with_idx(len(remaining_params))
509
- remaining_params.append(param)
519
+ remaining_params.append(param.instantiate_bounds(full_inst))
510
520
  arg = param.to_bound()
511
521
 
512
522
  # Set the `preserve` flag for instantiated tuples and None
@@ -651,7 +661,7 @@ class OpaqueType(ParametrizedTypeBase):
651
661
 
652
662
  @property
653
663
  def hugr_bound(self) -> ht.TypeBound:
654
- """The Hugr bound of this type, i.e. `Any`, `Copyable`, or `Equatable`."""
664
+ """The Hugr bound of this type, i.e. `Any` or `Copyable`."""
655
665
  if self.defn.bound is not None:
656
666
  return self.defn.bound
657
667
  return super().hugr_bound
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: guppylang-internals
3
- Version: 0.24.0
3
+ Version: 0.25.0
4
4
  Summary: Compiler internals for `guppylang` package.
5
5
  Author-email: Mark Koch <mark.koch@quantinuum.com>, TKET development team <tket-support@quantinuum.com>
6
6
  Maintainer-email: Mark Koch <mark.koch@quantinuum.com>, TKET development team <tket-support@quantinuum.com>
@@ -219,8 +219,8 @@ Classifier: Programming Language :: Python :: 3.13
219
219
  Classifier: Programming Language :: Python :: 3.14
220
220
  Classifier: Topic :: Software Development :: Compilers
221
221
  Requires-Python: <4,>=3.10
222
- Requires-Dist: hugr~=0.13.1
223
- Requires-Dist: tket-exts~=0.11.0
222
+ Requires-Dist: hugr~=0.14.1
223
+ Requires-Dist: tket-exts~=0.12.0
224
224
  Requires-Dist: typing-extensions<5,>=4.9.0
225
225
  Provides-Extra: pytket
226
226
  Requires-Dist: pytket>=1.34; extra == 'pytket'
@@ -1,54 +1,56 @@
1
- guppylang_internals/__init__.py,sha256=DGSTdGFDWX6LAry7XIDSqKcMw7qI9NIEAI_aS2gLKcc,130
2
- guppylang_internals/ast_util.py,sha256=Y_7MoilGpahv7tJ1xN5nVGIELZlhk-5h_9AbI3qixZg,11839
1
+ guppylang_internals/__init__.py,sha256=EgbPDr6Utan7jHefvmK8YWd_y5KDx9mb6kOXetg5X_4,130
2
+ guppylang_internals/ast_util.py,sha256=WHa7axpGrdsjzQk3iw3reDzYlcmsx0HsNH4Qbqwjjig,12531
3
3
  guppylang_internals/decorator.py,sha256=AWfPMMXzq5YC8nfB6DOwnRsrWKztuUK19n8APllgQ2w,10928
4
4
  guppylang_internals/diagnostic.py,sha256=VCpIhyVD8KPtk0GDYMa8XH0lKVsRbsWNu_ucE2jQT2I,18395
5
5
  guppylang_internals/dummy_decorator.py,sha256=LXTXrdcrr55YzerX3qrHS23q6S9pVdpUAvhprWzKH6E,2330
6
6
  guppylang_internals/engine.py,sha256=enloUzh4-2Ac0L7UCIzsMvsjzHvWIy8MvDoT2xhPdKk,10625
7
7
  guppylang_internals/error.py,sha256=fjHsbglnH9GtcsLF4sSry7FTjrLoiyQ-L1JS3uGirx0,3393
8
- guppylang_internals/experimental.py,sha256=ad3Ti6ncUdQA6MiXRyj45GvzlSx3Ww7PhrEpnrb79kI,2937
8
+ guppylang_internals/experimental.py,sha256=yERQgpT7P-x0-nr4gU4PdUCntByQwF2I9rfjpWtgqn4,3115
9
9
  guppylang_internals/ipython_inspect.py,sha256=rY2DpSpSBrRk0IZmuoz7jh35kGZHQnHLAQQFdb_-WnI,931
10
- guppylang_internals/nodes.py,sha256=Wvf12iU6rhx7RgqbbtcGPkiJwtQjgt6NMkYzmzZPAHc,9580
10
+ guppylang_internals/nodes.py,sha256=rJMtAJL_eRnrI6MZkweAWs1gYteCP3HSZM9BEkyAW7Q,12803
11
11
  guppylang_internals/py.typed,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
12
12
  guppylang_internals/span.py,sha256=8rWzAAipWunhhyCp44qdUAPmOfAXkEMvicK0PYc3tTg,4986
13
13
  guppylang_internals/cfg/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
14
14
  guppylang_internals/cfg/analysis.py,sha256=fD3cY0bZ85iNWcmLAXFaXwcdCfB7gzssKjYfsm1J-wQ,8365
15
- guppylang_internals/cfg/bb.py,sha256=k2ww5WpFkM_1G7Y_1FzSzBlf7Z83X2j1qFpBIK95dlo,7877
16
- guppylang_internals/cfg/builder.py,sha256=9WExlNvZkO0NcTgr4zATxk7Oys8Uas2me1leeDTwR1Y,23779
15
+ guppylang_internals/cfg/bb.py,sha256=TxV5yHRqiH86lvLR0g4EZ4fs7S6Axoof1l0TIAZArJM,8591
16
+ guppylang_internals/cfg/builder.py,sha256=UJXLzCNEA8nKCrRV3Y2AhMVwncbiHFD5m4t8zIKD5Ag,27630
17
17
  guppylang_internals/cfg/cfg.py,sha256=G6wTHtyRYcBN7FIwyIQnt3akVjM-Rl37PEXAaujplMg,4355
18
18
  guppylang_internals/checker/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
19
19
  guppylang_internals/checker/cfg_checker.py,sha256=SH_89mAQLNBVesERm9alJJ2h0xzQFzCA5uKBD2VfJms,13472
20
- guppylang_internals/checker/core.py,sha256=PI4vLkv_u799Ae0JpKsN4JIV8Toxf16DRyRg1V4Q2lM,18006
21
- guppylang_internals/checker/expr_checker.py,sha256=AuSWTLu3rBGIq8Uw-Vj-nS0aLDI4VUuXqIEiP2PoNWg,58199
22
- guppylang_internals/checker/func_checker.py,sha256=rp7_W79f5wqkB4qv5qrP3hGYJXpW3L1mpeeSGtxYJAI,15906
23
- guppylang_internals/checker/linearity_checker.py,sha256=cHvJSqFKWpkLqO7uAwz7OBmxtAi8ZN_K7afMrspkXy4,34719
24
- guppylang_internals/checker/stmt_checker.py,sha256=J1LT6rae8a_p2pbdHKJQTZdeDkZak017icotWWyBQHA,18827
20
+ guppylang_internals/checker/core.py,sha256=MHCHleEKRvI5mCV5w4VGdM51qjqHLb-2hFDpjG_tvCM,18188
21
+ guppylang_internals/checker/expr_checker.py,sha256=G9NrLmr3vv9XZp0l5N5lOdMZdyCOWgwYhTYrlaxVEZA,59706
22
+ guppylang_internals/checker/func_checker.py,sha256=e9FrEe72Y-KUchXtGljRUTr1tA4uwKVRv8uQVlInicA,15925
23
+ guppylang_internals/checker/linearity_checker.py,sha256=3RcJvXxgVZYsDijXpxubekpF1-XnNqKqaKF58VXorYg,37463
24
+ guppylang_internals/checker/modifier_checker.py,sha256=REzu1DVVutKlGAas2Gu8HKdPN83QlY9XHyxrotdF8vM,4042
25
+ guppylang_internals/checker/stmt_checker.py,sha256=paUBaAwx3QRpJAonND8wBpO4FxcNb4iPXMzImB11T9A,20785
25
26
  guppylang_internals/checker/errors/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
26
27
  guppylang_internals/checker/errors/comptime_errors.py,sha256=ee42lnVjXbjqirjp6vYaRvbKKexeNV08px1Kqu9eXn8,3436
27
- guppylang_internals/checker/errors/generic.py,sha256=485uhGANlWiKZrYpD0Fjh3lCqnL3QwqROzGZhwsiSug,1183
28
+ guppylang_internals/checker/errors/generic.py,sha256=r-BiSrmJh9jfXlxE029GMQ8yj30_qOTW2RAQsd3HYzs,2050
28
29
  guppylang_internals/checker/errors/linearity.py,sha256=VLGvwzfW6uljNjYUEIxNkgt6s3q9-yo1O22BoTiS4Xs,8922
29
- guppylang_internals/checker/errors/type_errors.py,sha256=1rEl8nVnveJXLc4CRKmNw2inKnWkXr3u6Iy3scepNSU,10221
30
+ guppylang_internals/checker/errors/type_errors.py,sha256=KUmcpN3tGLI_8BogcGKfV_N5BO7yqEBPgyHmf8hk-3M,10619
30
31
  guppylang_internals/checker/errors/wasm.py,sha256=tRpNhC8IZBkv6Nkn_dMRwGpDdZklv7UZdlYBu4WqI1A,874
31
32
  guppylang_internals/compiler/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
32
33
  guppylang_internals/compiler/cfg_compiler.py,sha256=nGQmPYhXzicZ16_-8sgFC-sfLxMFEDSGd1Xf0j7LTK0,9039
33
- guppylang_internals/compiler/core.py,sha256=W1k_vQR3hePw97SQiR9mB2gxtMq_ht25eD4B7u93JNg,29000
34
- guppylang_internals/compiler/expr_compiler.py,sha256=KJyR22YjSz9ya3Ug_w4Esgnar3NOQ1zyLoWQR_e-s9E,41282
34
+ guppylang_internals/compiler/core.py,sha256=mw7mQXQoBrt28NxjQ-3JSKhYVyVsDC21YVDaAaDtWBo,31518
35
+ guppylang_internals/compiler/expr_compiler.py,sha256=Km9ne1yd6A9ykpZvNMtZyktPagjJCHoZWEpx2M8i7gY,38600
35
36
  guppylang_internals/compiler/func_compiler.py,sha256=0bo28RNsFZDYmllle-yFUXKC0UJsLl2TVjr3gvDMJVA,3377
36
37
  guppylang_internals/compiler/hugr_extension.py,sha256=eFUcxzBZoVzXV-AqEOJlh_rJkyuS3vFv1WKGOHjloJs,7966
38
+ guppylang_internals/compiler/modifier_compiler.py,sha256=3KtA0YvMpj_JTCQAOH2leRQPFX1nyxFppAdEPWcjuk0,6315
37
39
  guppylang_internals/compiler/qtm_platform_extension.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
38
- guppylang_internals/compiler/stmt_compiler.py,sha256=Td1-xgrYtQMstpy_qh90baCvwYXRk95M7SOJ7qyXO2s,9201
40
+ guppylang_internals/compiler/stmt_compiler.py,sha256=cdOgqzRVP1hYeGbGftgY8LlFRHLWdgFPjlhK-khoMvw,9340
39
41
  guppylang_internals/definition/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
40
42
  guppylang_internals/definition/common.py,sha256=Me7gpCTzOqDv7eRv6Wo5ynsMYy6MEDpeX9uY2acYRDI,6927
41
43
  guppylang_internals/definition/const.py,sha256=71QVX3xqSaC0u4bsYHPbR_0Csz1Es-P7HHGxbTZXfNI,2283
42
- guppylang_internals/definition/custom.py,sha256=eozLnrEFvOknYuJZnnar4jSV3V09V5qbCC7rzhHjWt0,17929
43
- guppylang_internals/definition/declaration.py,sha256=xZOyWgivJou8smL4wpIXWXuAzHwtcBfhTJ6LNrS8T-c,5894
44
+ guppylang_internals/definition/custom.py,sha256=V3KU92rIonEdWyCwt3Rfkblic-XH-V0moGCTws3Sgbc,19539
45
+ guppylang_internals/definition/declaration.py,sha256=rmZdYHTTxjALfWmEfoNMVQ9hBmeV3o3VNXm9gcs3ubc,5883
44
46
  guppylang_internals/definition/extern.py,sha256=hEajRYaapKIfX9J7scnusQHc1e_bCxB4oUVWZ-D4c8o,2878
45
47
  guppylang_internals/definition/function.py,sha256=oz-4dk5gyc0sYIPbAmTgpbxl5dokjb8oPX1wM22z2EI,10969
46
48
  guppylang_internals/definition/overloaded.py,sha256=UQ64waMp48gEVDCqEzuJFrRoNJ9saUIRUAynF3T-Gz8,5132
47
- guppylang_internals/definition/parameter.py,sha256=dKAWQ6hQlqatXgcryiK27igxBsY5GrcB_9SucU2v4TE,2727
48
- guppylang_internals/definition/pytket_circuits.py,sha256=6zne7lrmP-vAYJfUtamRqsXcZEXwFzfFYxZelAeJQcs,18203
49
- guppylang_internals/definition/struct.py,sha256=zLAT75WgL6tzqxuRvscYCRnilngWOfOlfEnXEN-3jVo,15334
49
+ guppylang_internals/definition/parameter.py,sha256=l60l-yO34gpeuKZ5D3ru8CS8wnQGuoAgqIUP1CrfOF8,2789
50
+ guppylang_internals/definition/pytket_circuits.py,sha256=m_TlUATO7ijHv3O0Dm7FhbalRBufQ4sJ_kxRo500Bdo,16952
51
+ guppylang_internals/definition/struct.py,sha256=YLFgCN9G2IufS2Z7X-nsUz6DxBMYa6MCtw-YwSAQniw,15534
50
52
  guppylang_internals/definition/traced.py,sha256=hMHnrLKdbMvmmzmcJRvOCR-WiPHJ3x5ji0am436HNTQ,5592
51
- guppylang_internals/definition/ty.py,sha256=Aw7kgDOGv3crRoESUlAeR_2ovX8kV0qhGhuHlGOLf1s,2081
53
+ guppylang_internals/definition/ty.py,sha256=5Jt7twY8v1cE7noZ_RYfo0X55KYV6JI0itdHW9vvZs0,2085
52
54
  guppylang_internals/definition/value.py,sha256=tgkp-brIAauGXMqe68Fnwvz_bfdThdwJ_rzsGMbw95w,3452
53
55
  guppylang_internals/definition/wasm.py,sha256=Op8IpiKRZkNX-90UBp7uu3nCxx2VkbKKxHz-DZQuWs0,1987
54
56
  guppylang_internals/std/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
@@ -59,7 +61,7 @@ guppylang_internals/std/_internal/debug.py,sha256=hRgUM-35Mm0oZ1EPjr3RRTejaSD0Nb
59
61
  guppylang_internals/std/_internal/util.py,sha256=vkLUfIOwmRsjHbUmh-Gt4ykCUGZtQ2D6pLqpH-h-FbY,8299
60
62
  guppylang_internals/std/_internal/compiler/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
61
63
  guppylang_internals/std/_internal/compiler/arithmetic.py,sha256=_Nf-P3GwTp-ZVLz62Hz9ModD74R41hKqutNGmp5Mn6g,4287
62
- guppylang_internals/std/_internal/compiler/array.py,sha256=bzL_CRDgXVLWYY6o02dHzrKrnNW3H62axHkpr1Q__wA,20819
64
+ guppylang_internals/std/_internal/compiler/array.py,sha256=PepiCUthF0ebHF2eUUXSkRT_NPNS6gqqKiOhm0sv90c,13485
63
65
  guppylang_internals/std/_internal/compiler/either.py,sha256=LzLSfsafwVAgaeX8d91IRmrxK6kx0YC_MtGSBEgBsbs,4716
64
66
  guppylang_internals/std/_internal/compiler/frozenarray.py,sha256=BZMSSYTieqcFaAXGTR0nw2b7eN5LK2Et4vNZSBFRcyI,2361
65
67
  guppylang_internals/std/_internal/compiler/futures.py,sha256=nIaxXCGj4BPI_to_Q87gQEqN94Q8hb09ICkODZVOJrQ,1095
@@ -70,7 +72,7 @@ guppylang_internals/std/_internal/compiler/prelude.py,sha256=fwWWNDNUggFrtIG1JeQ
70
72
  guppylang_internals/std/_internal/compiler/qsystem.py,sha256=dKSpvpxF7WRfWuDj0u7zShEhTL6mkAr9pQNyYVoa8vM,1940
71
73
  guppylang_internals/std/_internal/compiler/quantum.py,sha256=gXuB1vpRl8ipgwwEYPCgoMPiqPUJ908Msl09jJFdWxg,3930
72
74
  guppylang_internals/std/_internal/compiler/tket_bool.py,sha256=ceO9BBF3HhjNAkc4dObJBH13Kpn08-pSaksjl3yoOa4,1207
73
- guppylang_internals/std/_internal/compiler/tket_exts.py,sha256=NteaIlCn4K0LoXwUCCLh39w7hoPdmpmdQ39_7P4ezKU,1381
75
+ guppylang_internals/std/_internal/compiler/tket_exts.py,sha256=dvs9lgruCCvXno7aShwdLJs0dQHjjCxmPYODGEo66yU,1572
74
76
  guppylang_internals/std/_internal/compiler/wasm.py,sha256=1G8EzrnN3Yv12hIdv2XOg4Hq-QlvRYl7-4QbZYLYyM4,5727
75
77
  guppylang_internals/tracing/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
76
78
  guppylang_internals/tracing/builtins_mock.py,sha256=iKgrs626DVhdN7nJroKBLstWGwkr7PzJI4CrgqkMyTA,2963
@@ -78,21 +80,22 @@ guppylang_internals/tracing/frozenlist.py,sha256=sINk-PZTw4dNThF5GK9AZxAeX5ap-g_
78
80
  guppylang_internals/tracing/function.py,sha256=K2rEey0awOxwfljGk4uezRmXode7rgOKQY1VN94wOIo,7901
79
81
  guppylang_internals/tracing/object.py,sha256=WLALkgqCMXOmPOydb4Rkg7OxRweSke1f9YU_JohMaiE,19748
80
82
  guppylang_internals/tracing/state.py,sha256=J-fG0dZh9IeB6hpLfyp5IwqS2TW0Zr8XloMmuIHWS6Q,2083
81
- guppylang_internals/tracing/unpacking.py,sha256=i3qFl__DIdm8uuRfHNdisSLLxZ6hSe_8SFUTs8Bhv5Q,9075
83
+ guppylang_internals/tracing/unpacking.py,sha256=6Df9h4pFS6mebyU3VR5DfO87Rs_QbTdSkLMNjpaM0Xc,8728
82
84
  guppylang_internals/tracing/util.py,sha256=zzVUeY7Ax4v_ZQh7QmckYaOWsg7BRZg6-oX4VWmytDU,3054
83
85
  guppylang_internals/tys/__init__.py,sha256=47DEQpj8HBSa-_TImW-5JCeuQeRkm5NMpJWZG3hSuFU,0
84
- guppylang_internals/tys/arg.py,sha256=4mtfDHtybV8d6cpK-B_Sdc6FTIsVd2udJYvOGtepa3A,3892
85
- guppylang_internals/tys/builtin.py,sha256=iLhqxXM4v66erI22-k__Xc_86ANw9_d7acUyrLq-yMM,12763
86
+ guppylang_internals/tys/arg.py,sha256=zrZm_6TnXS-tFvk5xRk40ayu8z99OQ_35L9oMp6hGNM,4417
87
+ guppylang_internals/tys/builtin.py,sha256=9QY_ayWxiwWkeTC2erIicbq4ZMbzETw0PbIl8hBu0XQ,12544
86
88
  guppylang_internals/tys/common.py,sha256=kCJDzSquUdztV5zEINE0Lxigawux9te0lmzd0Oa70J0,3575
87
- guppylang_internals/tys/const.py,sha256=MiD46lybIqkiXEh_7ekipYanIe7MahDwY8c-PWY0s3c,3718
89
+ guppylang_internals/tys/const.py,sha256=kl15uOriJFLUpoodb75f4dl3HYYa6OuKWA2B0vheVPY,4876
88
90
  guppylang_internals/tys/errors.py,sha256=Llc1CXDqkXW6Hi-cpMJaTLKweSN2a2E4sHpXapC0VRA,5514
89
- guppylang_internals/tys/param.py,sha256=9GsfJ4Hjt4FkjgC4lFirUjE7oVkqTD-ACV0LJWstswI,9340
90
- guppylang_internals/tys/parsing.py,sha256=A7zwXvXLFze8wtxI0Am1VqG98ddgGw7vqevo_29qCoQ,16863
91
+ guppylang_internals/tys/param.py,sha256=NXNDp8yrxbCkCo6oWCnjGg1ZoJ-F0leR5aUIj2eZQrc,10165
92
+ guppylang_internals/tys/parsing.py,sha256=Dn7VPvmbjAHCXlC54TiUYDvDZA4HNkqabscm44wMi3c,15956
91
93
  guppylang_internals/tys/printing.py,sha256=F60SZsvqDRNMQSbgNDfBDt2pYQH2ueaZo7ObmUa2fLE,5961
92
- guppylang_internals/tys/subst.py,sha256=REFbw2POB6wGw-NBOZ4K4T6gE5FZe6nQ_VjcUmhOxCs,3430
93
- guppylang_internals/tys/ty.py,sha256=ejvC8fg-BpaCf0Cs9sZIBjaKW2yQwapOG_KbThCkoKg,30973
94
+ guppylang_internals/tys/qubit.py,sha256=Mp1hW9fMBtzrN2U7BTYUmH-FzFw08EUMIcSYZFCsK30,820
95
+ guppylang_internals/tys/subst.py,sha256=fMIh7jNMMNiKjlr3WMxAwY_ovX1qTaz_c5foruYkLPs,3049
96
+ guppylang_internals/tys/ty.py,sha256=AKoiEXH35ZQooKA5LDT6zzoV4uDRaNFOHBN0JJjtn2g,31110
94
97
  guppylang_internals/tys/var.py,sha256=zACXv2IvGrqjDryC6lMyZpNnDb3SBRM2SlTOyq6WJdo,1173
95
- guppylang_internals-0.24.0.dist-info/METADATA,sha256=FN7OX-_6P1uO-j0DFz0aTf4Y56RV4pOAuwNQvNRSzFc,14808
96
- guppylang_internals-0.24.0.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
97
- guppylang_internals-0.24.0.dist-info/licenses/LICENCE,sha256=xx0jnfkXJvxRnG63LTGOxlggYnIysveWIZ6H3PNdCrQ,11357
98
- guppylang_internals-0.24.0.dist-info/RECORD,,
98
+ guppylang_internals-0.25.0.dist-info/METADATA,sha256=4BWfyYCyPcZwe3SzpNToowtCNtH498OMi-Kxx-MNQ7w,14808
99
+ guppylang_internals-0.25.0.dist-info/WHEEL,sha256=qtCwoSJWgHk21S1Kb4ihdzI2rlJ1ZKaIurTj_ngOhyQ,87
100
+ guppylang_internals-0.25.0.dist-info/licenses/LICENCE,sha256=xx0jnfkXJvxRnG63LTGOxlggYnIysveWIZ6H3PNdCrQ,11357
101
+ guppylang_internals-0.25.0.dist-info/RECORD,,