1 /**
2  This module contains implementations for destroying instances of types
3 
4   Copyright: Copyright Digital Mars 2000 - 2019.
5   License: Distributed under the
6        $(LINK2 http://www.boost.org/LICENSE_1_0.txt, Boost Software License 1.0).
7      (See accompanying file LICENSE)
8   Source: $(DRUNTIMESRC core/_internal/_destruction.d)
9 */
10 module core.internal.destruction;
11 
12 // compiler frontend lowers dynamic array deconstruction to this
__ArrayDtor(T)13 void __ArrayDtor(T)(scope T[] a)
14 {
15     foreach_reverse (ref T e; a)
16         e.__xdtor();
17 }
18 
destructRecurse(E,size_t n)19 public void destructRecurse(E, size_t n)(ref E[n] arr)
20 {
21     import core.internal.traits : hasElaborateDestructor;
22 
23     static if (hasElaborateDestructor!E)
24     {
25         foreach_reverse (ref elem; arr)
26             destructRecurse(elem);
27     }
28 }
29 
30 public void destructRecurse(S)(ref S s)
31     if (is(S == struct))
32 {
33     static if (__traits(hasMember, S, "__xdtor") &&
34             // Bugzilla 14746: Check that it's the exact member of S.
35             __traits(isSame, S, __traits(parent, s.__xdtor)))
36         s.__xdtor();
37 }
38 
39 // Test static struct
40 nothrow @safe @nogc unittest
41 {
42     static int i = 0;
~thisS43     static struct S { ~this() nothrow @safe @nogc { i = 42; } }
44     S s;
45     destructRecurse(s);
46     assert(i == 42);
47 }
48