1// Written in the D programming language.
2
3/**
4 * Interface to C++ <typeinfo>
5 *
6 * Copyright: Copyright (c) 2016 D Language Foundation
7 * License:   $(HTTP boost.org/LICENSE_1_0.txt, Boost License 1.0).
8 * Authors:   $(HTTP digitalmars.com, Walter Bright)
9 * Source:    $(DRUNTIMESRC core/stdcpp/_typeinfo.d)
10 */
11
12module core.stdcpp.typeinfo;
13
14import core.attribute : weak;
15
16version (CppRuntime_DigitalMars)
17{
18    import core.stdcpp.exception;
19
20    extern (C++, "std"):
21
22    class type_info
23    {
24    @nogc:
25        void* pdata;
26
27    public:
28        //virtual ~this();
29        void dtor() { }     // reserve slot in vtbl[]
30
31        //bool operator==(const type_info rhs) const;
32        //bool operator!=(const type_info rhs) const;
33        final bool before(const type_info rhs) const nothrow;
34        final const(char)* name() const nothrow;
35    protected:
36        //type_info();
37    private:
38        //this(const type_info rhs);
39        //type_info operator=(const type_info rhs);
40    }
41
42    class bad_cast : exception
43    {
44    @nogc:
45        extern(D) this() nothrow { }
46        extern(D) this(const bad_cast) nothrow { }
47        //bad_cast operator=(const bad_cast) nothrow { return this; }
48        //virtual ~this() nothrow;
49        override const(char)* what() const nothrow;
50    }
51
52    class bad_typeid : exception
53    {
54    @nogc:
55        extern(D) this() nothrow { }
56        extern(D) this(const bad_typeid) nothrow { }
57        //bad_typeid operator=(const bad_typeid) nothrow { return this; }
58        //virtual ~this() nothrow;
59        override const (char)* what() const nothrow;
60    }
61}
62else version (CppRuntime_Microsoft)
63{
64    import core.stdcpp.exception;
65
66    extern (C++, "std"):
67
68    struct __type_info_node
69    {
70        void* _MemPtr;
71        __type_info_node* _Next;
72    }
73
74    extern __gshared __type_info_node __type_info_root_node;
75
76    class type_info
77    {
78    @nogc:
79        @weak ~this() nothrow {}
80        //bool operator==(const type_info rhs) const;
81        //bool operator!=(const type_info rhs) const;
82        final bool before(const type_info rhs) const nothrow;
83        final const(char)* name(__type_info_node* p = &__type_info_root_node) const nothrow;
84
85    private:
86        void* pdata;
87        char[1] _name;
88        //type_info operator=(const type_info rhs);
89    }
90
91    class bad_cast : exception
92    {
93    @nogc:
94        extern(D) this(const(char)* msg = "bad cast") nothrow { super(msg); }
95        //virtual ~this();
96    }
97
98    class bad_typeid : exception
99    {
100    @nogc:
101        extern(D) this(const(char)* msg = "bad typeid") nothrow { super(msg); }
102        //virtual ~this();
103    }
104}
105else version (CppRuntime_Gcc)
106{
107    import core.stdcpp.exception;
108
109    extern (C++, "__cxxabiv1")
110    {
111        extern(C++, class) struct __class_type_info;
112    }
113
114    extern (C++, "std"):
115
116    abstract class type_info
117    {
118    @nogc:
119        @weak ~this() {}
120        @weak final const(char)* name() const nothrow
121        {
122            return _name[0] == '*' ? _name + 1 : _name;
123        }
124        @weak final bool before(const type_info _arg) const nothrow
125        {
126            import core.stdc.string : strcmp;
127            return (_name[0] == '*' && _arg._name[0] == '*')
128                ? _name < _arg._name
129                : strcmp(_name, _arg._name) < 0;
130        }
131        //bool operator==(const type_info) const;
132        bool __is_pointer_p() const;
133        bool __is_function_p() const;
134        bool __do_catch(const type_info, void**, uint) const;
135        bool __do_upcast(const __class_type_info*, void**) const;
136
137    protected:
138        const(char)* _name;
139
140        extern(D) this(const(char)* name) { _name = name; }
141    }
142
143    class bad_cast : exception
144    {
145    @nogc:
146        extern(D) this() nothrow {}
147        //~this();
148        @weak override const(char)* what() const nothrow { return "bad cast"; }
149    }
150
151    class bad_typeid : exception
152    {
153    @nogc:
154        extern(D) this() nothrow {}
155        //~this();
156        @weak override const(char)* what() const nothrow { return "bad typeid"; }
157    }
158}
159else version (CppRuntime_Clang)
160{
161    import core.stdcpp.exception;
162
163    extern (C++, "std"):
164
165    abstract class type_info
166    {
167    @nogc:
168        @weak ~this() {}
169        @weak final const(char)* name() const nothrow
170        {
171            return __type_name;
172        }
173        @weak final bool before(const type_info __arg) const nothrow
174        {
175            return __type_name < __arg.__type_name;
176        }
177        //bool operator==(const type_info) const;
178
179    protected:
180        const(char)* __type_name;
181
182        extern(D) this(const(char)* __n) { __type_name = __n; }
183    }
184
185    class bad_cast : exception
186    {
187    @nogc:
188        extern(D) this() nothrow {}
189        //~this();
190        @weak override const(char)* what() const nothrow { return "bad cast"; }
191    }
192
193    class bad_typeid : exception
194    {
195    @nogc:
196        extern(D) this() nothrow {}
197        //~this();
198        @weak override const(char)* what() const nothrow { return "bad typeid"; }
199    }
200}
201else
202    static assert(0, "Missing std::type_info binding for this platform");
203