2 * Copyright (C) 2004-2006 by Digital Mars, www.digitalmars.com
3 * Written by Walter Bright
5 * This software is provided 'as-is', without any express or implied
6 * warranty. In no event will the authors be held liable for any damages
7 * arising from the use of this software.
9 * Permission is granted to anyone to use this software for any purpose,
10 * including commercial applications, and to alter it and redistribute it
11 * freely, in both source and binary form, subject to the following
14 * o The origin of this software must not be misrepresented; you must not
15 * claim that you wrote the original software. If you use this software
16 * in a product, an acknowledgment in the product documentation would be
17 * appreciated but is not required.
18 * o Altered source versions must be plainly marked as such, and must not
19 * be misrepresented as being the original software.
20 * o This notice may not be removed or altered from any source
25 * Modified by Sean Kelly for use with the D Runtime Project
32 /******************************************
34 * If it is an Object, return that Object.
35 * If it is an interface, return the Object implementing the interface.
36 * If it is null, return null.
37 * Else, undefined crash
40 Object _d_toObject(void* p)
46 ClassInfo oc = o.classinfo;
47 Interface *pi = **cast(Interface ***)p;
49 /* Interface.offset lines up with ClassInfo.name.ptr,
50 * so we rely on pointers never being less than 64K,
51 * and Objects never being greater.
53 if (pi.offset < 0x10000)
55 //printf("\tpi.offset = %d\n", pi.offset);
56 o = cast(Object)(p - pi.offset);
63 /*************************************
64 * Attempts to cast Object o to class c.
65 * Returns o if successful, null if not.
68 Object _d_interface_cast(void* p, ClassInfo c)
71 //printf("_d_interface_cast(p = %p, c = '%.*s')\n", p, c.name);
74 Interface *pi = **cast(Interface ***)p;
76 //printf("\tpi.offset = %d\n", pi.offset);
77 o = cast(Object)(p - pi.offset);
78 return _d_dynamic_cast(o, c);
83 Object _d_dynamic_cast(Object o, ClassInfo c)
87 //printf("_d_dynamic_cast(o = %p, c = '%.*s')\n", o, c.name);
92 if (_d_isbaseof2(oc, c, offset))
94 //printf("\toffset = %d\n", offset);
95 o = cast(Object)(cast(void*)o + offset);
100 //printf("\tresult = %p\n", o);
104 int _d_isbaseof2(ClassInfo oc, ClassInfo c, inout size_t offset)
113 for (i = 0; i < oc.interfaces.length; i++)
117 ic = oc.interfaces[i].classinfo;
119 { offset = oc.interfaces[i].offset;
123 for (i = 0; i < oc.interfaces.length; i++)
127 ic = oc.interfaces[i].classinfo;
128 if (_d_isbaseof2(ic, c, offset))
129 { offset = oc.interfaces[i].offset;
138 int _d_isbaseof(ClassInfo oc, ClassInfo c)
147 for (i = 0; i < oc.interfaces.length; i++)
151 ic = oc.interfaces[i].classinfo;
152 if (ic is c || _d_isbaseof(ic, c))
160 /*********************************
161 * Find the vtbl[] associated with Interface ic.
164 void *_d_interface_vtbl(ClassInfo ic, Object o)
168 //printf("__d_interface_vtbl(o = %p, ic = %p)\n", o, ic);
173 for (i = 0; i < oc.interfaces.length; i++)
177 oic = oc.interfaces[i].classinfo;
180 return cast(void *)oc.interfaces[i].vtbl;