summary refs log tree commit diff stats
path: root/compiler/semstmts.nim
diff options
context:
space:
mode:
authorAndreas Rumpf <rumpf_a@web.de>2017-10-14 09:32:57 +0200
committerAndreas Rumpf <rumpf_a@web.de>2017-10-14 20:37:49 +0200
commit8780d25e038ed6ca6815f3ed4aa6a7a58416714b (patch)
treeffa8aa46e6821e084673f0278a47fac1423566ee /compiler/semstmts.nim
parent4eaa2bf15d1f59311b2fb7efac39cd652f9b2a42 (diff)
downloadNim-8780d25e038ed6ca6815f3ed4aa6a7a58416714b.tar.gz
minor refactorings for better destructors
Diffstat (limited to 'compiler/semstmts.nim')
-rw-r--r--compiler/semstmts.nim27
1 files changed, 24 insertions, 3 deletions
diff --git a/compiler/semstmts.nim b/compiler/semstmts.nim
index 3e6e918f1..c6e03cef3 100644
--- a/compiler/semstmts.nim
+++ b/compiler/semstmts.nim
@@ -1277,9 +1277,30 @@ proc maybeAddResult(c: PContext, s: PSym, n: PNode) =
 proc semOverride(c: PContext, s: PSym, n: PNode) =
   case s.name.s.normalize
   of "destroy", "=destroy":
-    doDestructorStuff(c, s, n)
-    if not newDestructors and not experimentalMode(c):
-      localError n.info, "use the {.experimental.} pragma to enable destructors"
+    if newDestructors:
+      let t = s.typ
+      var noError = false
+      if t.len == 2 and t.sons[0] == nil and t.sons[1].kind == tyVar:
+        var obj = t.sons[1].sons[0]
+        while true:
+          incl(obj.flags, tfHasAsgn)
+          if obj.kind == tyGenericBody: obj = obj.lastSon
+          elif obj.kind == tyGenericInvocation: obj = obj.sons[0]
+          else: break
+        if obj.kind in {tyObject, tyDistinct}:
+          if obj.destructor.isNil:
+            obj.destructor = s
+          else:
+            localError(n.info, errGenerated,
+              "cannot bind another '" & s.name.s & "' to: " & typeToString(obj))
+          noError = true
+      if not noError:
+        localError(n.info, errGenerated,
+          "signature for '" & s.name.s & "' must be proc[T: object](x: var T)")
+    else:
+      doDestructorStuff(c, s, n)
+      if not experimentalMode(c):
+        localError n.info, "use the {.experimental.} pragma to enable destructors"
     incl(s.flags, sfUsed)
   of "deepcopy", "=deepcopy":
     if s.typ.len == 2 and