summary refs log tree commit diff stats
path: root/compiler/sigmatch.nim
diff options
context:
space:
mode:
Diffstat (limited to 'compiler/sigmatch.nim')
-rw-r--r--compiler/sigmatch.nim43
1 files changed, 31 insertions, 12 deletions
diff --git a/compiler/sigmatch.nim b/compiler/sigmatch.nim
index e5bf08097..4a3773ed8 100644
--- a/compiler/sigmatch.nim
+++ b/compiler/sigmatch.nim
@@ -1,6 +1,6 @@
 #
 #
-#           The Nimrod Compiler
+#           The Nim Compiler
 #        (c) Copyright 2013 Andreas Rumpf
 #
 #    See the file "copying.txt", included in this
@@ -12,7 +12,8 @@
 
 import 
   intsets, ast, astalgo, semdata, types, msgs, renderer, lookups, semtypinst,
-  magicsys, condsyms, idents, lexer, options, parampatterns, strutils, trees
+  magicsys, condsyms, idents, lexer, options, parampatterns, strutils, trees,
+  nimfix.pretty
 
 when not defined(noDocgen):
   import docgen
@@ -21,6 +22,7 @@ type
   TCandidateState* = enum 
     csEmpty, csMatch, csNoMatch
 
+  CandidateErrors* = seq[PSym]
   TCandidate* {.final.} = object
     c*: PContext
     exactMatches*: int       # also misused to prefer iters over procs
@@ -44,7 +46,7 @@ type
                              # a distrinct type
     typedescMatched: bool
     inheritancePenalty: int  # to prefer closest father object type
-    errors*: seq[string]     # additional clarifications to be displayed to the
+    errors*: CandidateErrors # additional clarifications to be displayed to the
                              # user if overload resolution fails
 
   TTypeRelation* = enum      # order is important!
@@ -201,16 +203,17 @@ proc writeMatches*(c: TCandidate) =
   writeln(stdout, "intconv matches: " & $c.intConvMatches)
   writeln(stdout, "generic matches: " & $c.genericMatches)
 
-proc argTypeToString(arg: PNode): string =
+proc argTypeToString(arg: PNode; prefer: TPreferedDesc): string =
   if arg.kind in nkSymChoices:
-    result = typeToString(arg[0].typ)
+    result = typeToString(arg[0].typ, prefer)
     for i in 1 .. <arg.len:
       result.add(" | ")
-      result.add typeToString(arg[i].typ)
+      result.add typeToString(arg[i].typ, prefer)
   else:
-    result = arg.typ.typeToString
+    result = arg.typ.typeToString(prefer)
 
-proc describeArgs*(c: PContext, n: PNode, startIdx = 1): string =
+proc describeArgs*(c: PContext, n: PNode, startIdx = 1;
+                   prefer: TPreferedDesc = preferName): string =
   result = ""
   for i in countup(startIdx, n.len - 1):
     var arg = n.sons[i]
@@ -226,7 +229,7 @@ proc describeArgs*(c: PContext, n: PNode, startIdx = 1): string =
         arg = c.semOperand(c, n.sons[i])
         n.sons[i] = arg
     if arg.typ.kind == tyError: return
-    add(result, argTypeToString(arg))
+    add(result, argTypeToString(arg, prefer))
     if i != sonsLen(n) - 1: add(result, ", ")
 
 proc typeRel*(c: var TCandidate, f, aOrig: PType, doBind = true): TTypeRelation
@@ -479,8 +482,8 @@ proc matchUserTypeClass*(c: PContext, m: var TCandidate,
     dummyParam.typ = dummyType
     addDecl(c, dummyParam)
 
-  var checkedBody = c.semTryExpr(c, body.n[3].copyTree, bufferErrors = false)
-  m.errors = bufferedMsgs
+  var checkedBody = c.semTryExpr(c, body.n[3].copyTree)
+  #m.errors = bufferedMsgs
   clearBufferedMsgs()
   if checkedBody == nil: return isNone
 
@@ -1272,6 +1275,7 @@ proc paramTypesMatch*(m: var TCandidate, f, a: PType,
     else: 
       # only one valid interpretation found:
       markUsed(arg.info, arg.sons[best].sym)
+      styleCheckUse(arg.info, arg.sons[best].sym)
       result = paramTypesMatchAux(m, f, arg.sons[best].typ, arg.sons[best],
                                   argOrig)
 
@@ -1319,7 +1323,7 @@ proc incrIndexType(t: PType) =
   inc t.sons[0].n.sons[1].intVal
 
 proc matchesAux(c: PContext, n, nOrig: PNode,
-                m: var TCandidate, marker: var TIntSet) = 
+                m: var TCandidate, marker: var IntSet) = 
   template checkConstraint(n: expr) {.immediate, dirty.} =
     if not formal.constraint.isNil:
       if matchNodeKinds(formal.constraint, n):
@@ -1480,8 +1484,23 @@ proc argtypeMatches*(c: PContext, f, a: PType): bool =
   # instantiate generic converters for that
   result = res != nil
 
+proc instDeepCopy*(c: PContext; dc: PSym; t: PType; info: TLineInfo): PSym {.
+                    procvar.} =
+  var m: TCandidate
+  initCandidate(c, m, dc.typ)
+  var f = dc.typ.sons[1]
+  if f.kind in {tyRef, tyPtr}: f = f.lastSon
+  if typeRel(m, f, t) == isNone:
+    localError(info, errGenerated, "cannot instantiate 'deepCopy'")
+  else:
+    result = c.semGenerateInstance(c, dc, m.bindings, info)
+    assert sfFromGeneric in result.flags
+
 include suggest
 
+when not declared(tests):
+  template tests(s: stmt) {.immediate.} = discard
+
 tests:
   var dummyOwner = newSym(skModule, getIdent("test_module"), nil, UnknownLineInfo())