summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--compiler/semstmts.nim9
-rw-r--r--compiler/semtypes.nim9
-rwxr-xr-xtests/types/thard_tyforward.nim22
3 files changed, 36 insertions, 4 deletions
diff --git a/compiler/semstmts.nim b/compiler/semstmts.nim
index c7f27f0a2..a1c3bd001 100644
--- a/compiler/semstmts.nim
+++ b/compiler/semstmts.nim
@@ -851,9 +851,12 @@ proc typeSectionFinalPass(c: PContext, n: PNode) =
         # type aliases are hard:
         var t = semTypeNode(c, x, nil)
         assert t != nil
-        if t.kind in {tyObject, tyEnum, tyDistinct}:
-          assert s.typ != nil
-          if s.typ.kind != tyAlias:
+        if s.typ != nil and s.typ.kind != tyAlias:
+          if t.kind in {tyProc, tyGenericInst} and not t.isMetaType:
+            assignType(s.typ, t)
+            s.typ.id = t.id
+          elif t.kind in {tyObject, tyEnum, tyDistinct}:
+            assert s.typ != nil
             assignType(s.typ, t)
             s.typ.id = t.id     # same id
       checkConstructedType(s.info, s.typ)
diff --git a/compiler/semtypes.nim b/compiler/semtypes.nim
index 5bc9bbd78..8efd2f943 100644
--- a/compiler/semtypes.nim
+++ b/compiler/semtypes.nim
@@ -893,7 +893,13 @@ proc liftParamType(c: PContext, procKind: TSymKind, genericParams: PNode,
       let lifted = liftingWalk(paramType.sons[i])
       if lifted != nil: paramType.sons[i] = lifted
 
-    if paramType.base.lastSon.kind == tyUserTypeClass:
+    let body = paramType.base
+    if body.kind == tyForward:
+      # this may happen for proc type appearing in a type section
+      # before one of its param types
+      return
+
+    if body.lastSon.kind == tyUserTypeClass:
       let expanded = instGenericContainer(c, info, paramType,
                                           allowMetaTypes = true)
       result = liftingWalk(expanded, true)
@@ -1067,6 +1073,7 @@ proc semBlockType(c: PContext, n: PNode, prev: PType): PType =
 
 proc semGenericParamInInvocation(c: PContext, n: PNode): PType =
   result = semTypeNode(c, n, nil)
+  n.typ = makeTypeDesc(c, result)
 
 proc semObjectTypeForInheritedGenericInst(c: PContext, n: PNode, t: PType) =
   var
diff --git a/tests/types/thard_tyforward.nim b/tests/types/thard_tyforward.nim
new file mode 100755
index 000000000..7131cd64b
--- /dev/null
+++ b/tests/types/thard_tyforward.nim
@@ -0,0 +1,22 @@
+type
+  Bar[T] = Foo[T, T]
+  Baz[T] = proc (x: Foo[T, T])
+  
+  GenericAlias[T] = Foo[T]
+  GenericAlias2[T] = Foo[Baz[T]]
+  
+  Concrete1 = Foo[int, float]
+  Concrete2 = proc(x: proc(a: Foo[int, float]))
+  
+  Foo[T, U] = object
+    x: T
+    y: U
+
+var
+  x1: Bar[float]
+  x2: Baz[int]
+  x3: Concrete1
+  x4: Concrete2
+  x5: GenericAlias[int]
+  x6: GenericAlias2[string]
+