diff options
author | Andreas Rumpf <rumpf_a@web.de> | 2024-06-09 08:16:05 +0200 |
---|---|---|
committer | GitHub <noreply@github.com> | 2024-06-09 08:16:05 +0200 |
commit | 56c95758b2777a36c8608a7b9950ba5ce8ce0b65 (patch) | |
tree | a71a603085e4fb75e7fd21b48bfb5fb94ffb5e6d | |
parent | c7ee16182eb54b6f426358fee359280278d0b780 (diff) | |
download | Nim-56c95758b2777a36c8608a7b9950ba5ce8ce0b65.tar.gz |
fixes #23445; fixes #23418 [backport] (#23699)
-rw-r--r-- | compiler/seminst.nim | 3 | ||||
-rw-r--r-- | compiler/types.nim | 10 | ||||
-rw-r--r-- | tests/metatype/twrong_same_type.nim | 28 |
3 files changed, 40 insertions, 1 deletions
diff --git a/compiler/seminst.nim b/compiler/seminst.nim index e9b46c382..92f8664fe 100644 --- a/compiler/seminst.nim +++ b/compiler/seminst.nim @@ -396,6 +396,7 @@ proc generateInstance(c: PContext, fn: PSym, pt: TypeMapping, for _, param in paramTypes(result.typ): entry.concreteTypes[i] = param inc i + #echo "INSTAN ", fn.name.s, " ", typeToString(result.typ), " ", entry.concreteTypes.len if tfTriggersCompileTime in result.typ.flags: incl(result.flags, sfCompileTime) n[genericParamsPos] = c.graph.emptyNode @@ -424,7 +425,9 @@ proc generateInstance(c: PContext, fn: PSym, pt: TypeMapping, if result.magic notin {mSlice, mTypeOf}: # 'toOpenArray' is special and it is allowed to return 'openArray': paramsTypeCheck(c, result.typ) + #echo "INSTAN ", fn.name.s, " ", typeToString(result.typ), " <-- NEW PROC!", " ", entry.concreteTypes.len else: + #echo "INSTAN ", fn.name.s, " ", typeToString(result.typ), " <-- CACHED! ", typeToString(oldPrc.typ), " ", entry.concreteTypes.len result = oldPrc popProcCon(c) popInfoContext(c.config) diff --git a/compiler/types.nim b/compiler/types.nim index e5ce0aea1..880f811dd 100644 --- a/compiler/types.nim +++ b/compiler/types.nim @@ -1316,9 +1316,17 @@ proc sameTypeAux(x, y: PType, c: var TSameTypeClosure): bool = result = sameTypeOrNilAux(a.elementType, b.elementType, c) and sameValue(a.n[0], b.n[0]) and sameValue(a.n[1], b.n[1]) - of tyGenericInst, tyAlias, tyInferred, tyIterable: + of tyAlias, tyInferred, tyIterable: cycleCheck() result = sameTypeAux(a.skipModifier, b.skipModifier, c) + of tyGenericInst: + # BUG #23445 + # The type system must distinguish between `T[int] = object #[empty]#` + # and `T[float] = object #[empty]#`! + cycleCheck() + for ff, aa in underspecifiedPairs(a, b, 1, -1): + if not sameTypeAux(ff, aa, c): return false + result = sameTypeAux(a.skipModifier, b.skipModifier, c) of tyNone: result = false of tyConcept: result = exprStructuralEquivalent(a.n, b.n) diff --git a/tests/metatype/twrong_same_type.nim b/tests/metatype/twrong_same_type.nim new file mode 100644 index 000000000..ea903b7a3 --- /dev/null +++ b/tests/metatype/twrong_same_type.nim @@ -0,0 +1,28 @@ +# bug #23418 + +template mapIt*(x: untyped): untyped = + type OutType {.gensym.} = typeof(x) #typeof(x, typeOfProc) + newSeq[OutType](5) + +type F[E] = object + +proc start(v: int): F[(ValueError,)] = discard +proc stop(v: int): F[tuple[]] = discard + +assert $typeof(mapIt(start(9))) == "seq[F[(ValueError,)]]" +assert $typeof(mapIt(stop(9))) == "seq[F[tuple[]]]" + +# bug #23445 + +type F2[T; I: static int] = distinct int + +proc start2(v: int): F2[void, 22] = discard +proc stop2(v: int): F2[void, 33] = discard + +var a = mapIt(start2(5)) + +assert $type(a) == "seq[F2[system.void, 22]]", $type(a) + +var b = mapIt(stop2(5)) + +assert $type(b) == "seq[F2[system.void, 33]]", $type(b) |