summary refs log tree commit diff stats
diff options
context:
space:
mode:
-rw-r--r--compiler/sigmatch.nim23
-rw-r--r--tests/types/tissues_types.nim10
2 files changed, 31 insertions, 2 deletions
diff --git a/compiler/sigmatch.nim b/compiler/sigmatch.nim
index a0de33ed5..e831a2856 100644
--- a/compiler/sigmatch.nim
+++ b/compiler/sigmatch.nim
@@ -2311,6 +2311,9 @@ proc paramTypesMatchAux(m: var TCandidate, f, a: PType,
       if f.n != nil:
         # Forward to the varargs converter
         result = localConvMatch(c, m, f, a, arg)
+      elif f[0].kind == tyTyped:
+        inc m.genericMatches
+        result = arg
       else:
         r = typeRel(m, base(f), a)
         case r
@@ -2360,7 +2363,11 @@ proc paramTypesMatch*(m: var TCandidate, f, a: PType,
     var best = -1
     result = arg
     
-    if f.kind in {tyTyped, tyUntyped}:
+    var actingF = f
+    if f.kind == tyVarargs:
+      if m.calleeSym.kind in {skTemplate, skMacro}:
+        actingF = f[0]
+    if actingF.kind in {tyTyped, tyUntyped}:
       var
         bestScope = -1
         counts = 0
@@ -2376,6 +2383,7 @@ proc paramTypesMatch*(m: var TCandidate, f, a: PType,
       if best == -1:
         result = nil
       elif counts > 0:
+        m.genericMatches = 1
         best = -1
     else:
       # CAUTION: The order depends on the used hashing scheme. Thus it is
@@ -2497,6 +2505,9 @@ proc incrIndexType(t: PType) =
 template isVarargsUntyped(x): untyped =
   x.kind == tyVarargs and x[0].kind == tyUntyped
 
+template isVarargsTyped(x): untyped =
+  x.kind == tyVarargs and x[0].kind == tyTyped
+
 proc findFirstArgBlock(m: var TCandidate, n: PNode): int =
   # see https://github.com/nim-lang/RFCs/issues/405
   result = int.high
@@ -2671,7 +2682,15 @@ proc matchesAux(c: PContext, n, nOrig: PNode, m: var TCandidate, marker: var Int
                                     n[a], nOrig[a])
           if arg == nil:
             noMatch()
-          if m.baseTypeMatch:
+          if formal.typ.isVarargsTyped and m.calleeSym.kind in {skTemplate, skMacro}:
+            if container.isNil:
+              container = newNodeIT(nkBracket, n[a].info, arrayConstr(c, n.info))
+              setSon(m.call, formal.position + 1, implicitConv(nkHiddenStdConv, formal.typ, container, m, c))
+            else:
+              incrIndexType(container.typ)
+            container.add n[a]
+            f = max(f, formalLen - n.len + a + 1)
+          elif m.baseTypeMatch:
             assert formal.typ.kind == tyVarargs
             #assert(container == nil)
             if container.isNil:
diff --git a/tests/types/tissues_types.nim b/tests/types/tissues_types.nim
index 49c6d85ee..6bb1258f4 100644
--- a/tests/types/tissues_types.nim
+++ b/tests/types/tissues_types.nim
@@ -106,3 +106,13 @@ block:
     let t = Foo[float](x1: 1)
     doAssert t.x1 == 1
 
+block:
+  template s(d: varargs[typed])=discard
+
+  proc something(x:float)=discard
+  proc something(x:int)=discard
+  proc otherthing()=discard
+
+  s(something)
+  s(otherthing, something)
+  s(something, otherthing)