fixes #25262; proc v[T: typedesc]() = discard / v[0]() compiles even though 0 isn't a typedesc (#25558)

fixes #25262

```nim
if constraint != nil and constraint.kind == tyTypeDesc:
  n[i].typ = e.typ
else:
  n[i].typ = e.typ.skipTypes({tyTypeDesc})
```
at least when `constraint` is a typedesc, it should not skip
`tyTypeDesc`

```nim
if arg.kind != tyTypeDesc:
  arg = makeTypeDesc(m.c, arg)
```
Wrappers literals into typedesc, which can cause problems. Though, it
doesn't seem to be necessary

(cherry picked from commit bd709f9b4c)
This commit is contained in:
ringabout
2026-03-01 06:01:09 +08:00
committed by narimiran
parent f7a18fceba
commit dc8d538683
4 changed files with 16 additions and 4 deletions

View File

@@ -981,7 +981,7 @@ proc setGenericParams(c: PContext, n, expectedParams: PNode) =
if e.typ == nil:
n[i].typ() = errorType(c)
else:
n[i].typ() = e.typ.skipTypes({tyTypeDesc})
n[i].typ() = e.typ
proc explicitGenericInstantiation(c: PContext, n: PNode, s: PSym, doError: bool): PNode =
assert n.kind == nkBracketExpr

View File

@@ -160,8 +160,7 @@ proc matchGenericParam(m: var TCandidate, formal: PType, n: PNode) =
arg = newTypeS(tyStatic, m.c, son = evaluated.typ)
arg.n = evaluated
elif formalBase.kind == tyTypeDesc:
if arg.kind != tyTypeDesc:
arg = makeTypeDesc(m.c, arg)
discard # if arg is not tyTypeDesc, typeRel will report the mismatch
else:
arg = arg.skipTypes({tyTypeDesc})
let tm = typeRel(m, formal, arg)

View File

@@ -3,7 +3,7 @@ cmd: "nim check $options --hints:off $file"
action: "reject"
nimout:'''
tpointerprocs.nim(22, 11) Error: 'foo' doesn't have a concrete type, due to unspecified generic parameters.
tpointerprocs.nim(34, 14) Error: type mismatch: got <int>
tpointerprocs.nim(34, 14) Error: type mismatch: got <typedesc[int]>
but expected one of:
proc foo(x: int | float; y: int or string): float
first type mismatch at position: 2 in generic parameters

13
tests/typerel/t25262.nim Normal file
View File

@@ -0,0 +1,13 @@
discard """
errormsg: "type mismatch"
output: '''
t25262.nim(13, 5) Error: type mismatch: got <>
but expected one of:
proc v[T: typedesc]()
expression: v[0]()
'''
"""
proc v[T: typedesc]() = discard
v[0]()