annotate dmd/BaseClass.d @ 187:b0d41ff5e0df

Added expandability scheme outlined in http://www.dsource.org/forums/viewtopic.php?t=5659&sid=6f2150ff5b0bffcd47512a6a7608d218
author Abscissa
date Tue, 07 Jun 2011 23:37:34 -0400
parents e3afd1303184
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
1 module dmd.BaseClass;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
2
114
e28b18c23469 added a module dmd.common for commonly used stuff
Trass3r
parents: 4
diff changeset
3 import dmd.common;
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
4 import dmd.Type;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
5 import dmd.PROT;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
6 import dmd.ClassDeclaration;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
7 import dmd.Array;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
8 import dmd.TY;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
9 import dmd.TypeFunction;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
10 import dmd.Dsymbol;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
11 import dmd.FuncDeclaration;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
12 import dmd.ArrayTypes;
178
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
13 import dmd.Util;
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
14
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
15 import core.stdc.stdlib;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
16 import core.stdc.string;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
17
4
d706d958e4e8 Step 2 of restoring GC functionality.
korDen
parents: 2
diff changeset
18 import core.memory;
2
7427ded8caf7 Removed unreferenced modules
korDen
parents: 0
diff changeset
19
178
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
20 import dmd.TObject;
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
21
187
b0d41ff5e0df Added expandability scheme outlined in http://www.dsource.org/forums/viewtopic.php?t=5659&sid=6f2150ff5b0bffcd47512a6a7608d218
Abscissa
parents: 178
diff changeset
22 import dmd.DDMDExtensions;
b0d41ff5e0df Added expandability scheme outlined in http://www.dsource.org/forums/viewtopic.php?t=5659&sid=6f2150ff5b0bffcd47512a6a7608d218
Abscissa
parents: 178
diff changeset
23
178
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
24 class BaseClass : TObject
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
25 {
187
b0d41ff5e0df Added expandability scheme outlined in http://www.dsource.org/forums/viewtopic.php?t=5659&sid=6f2150ff5b0bffcd47512a6a7608d218
Abscissa
parents: 178
diff changeset
26 mixin insertMemberExtension!(typeof(this));
b0d41ff5e0df Added expandability scheme outlined in http://www.dsource.org/forums/viewtopic.php?t=5659&sid=6f2150ff5b0bffcd47512a6a7608d218
Abscissa
parents: 178
diff changeset
27
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
28 Type type; // (before semantic processing)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
29 PROT protection; // protection for the base interface
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
30
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
31 ClassDeclaration base;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
32 int offset; // 'this' pointer offset
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
33 Array vtbl; // for interfaces: Array of FuncDeclaration's
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
34 // making up the vtbl[]
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
35
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
36 //int baseInterfaces_dim;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
37 BaseClass[] baseInterfaces; // if BaseClass is an interface, these
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
38 // are a copy of the InterfaceDeclaration::interfaces
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
39
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
40 this()
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
41 {
178
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
42 register();
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
43
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
44 vtbl = new Array();
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
45 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
46
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
47 this(Type type, PROT protection)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
48 {
178
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
49 register();
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
50
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
51 //printf("BaseClass(this = %p, '%s')\n", this, type->toChars());
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
52 this.type = type;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
53 this.protection = protection;
178
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
54
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
55 vtbl = new Array();
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
56 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
57
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
58 /****************************************
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
59 * Fill in vtbl[] for base class based on member functions of class cd.
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
60 * Input:
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
61 * vtbl if !=null, fill it in
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
62 * newinstance !=0 means all entries must be filled in by members
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
63 * of cd, not members of any base classes of cd.
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
64 * Returns:
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
65 * true if any entries were filled in by members of cd (not exclusively
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
66 * by base classes)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
67 */
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
68 bool fillVtbl(ClassDeclaration cd, Array vtbl, int newinstance)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
69 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
70 ClassDeclaration id = base;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
71 int j;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
72 bool result = false;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
73
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
74 //printf("BaseClass.fillVtbl(this='%s', cd='%s')\n", base.toChars(), cd.toChars());
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
75 if (vtbl)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
76 vtbl.setDim(base.vtbl.dim);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
77
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
78 // first entry is ClassInfo reference
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
79 for (j = base.vtblOffset(); j < base.vtbl.dim; j++)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
80 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
81 FuncDeclaration ifd = (cast(Dsymbol)base.vtbl.data[j]).isFuncDeclaration();
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
82 FuncDeclaration fd;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
83 TypeFunction tf;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
84
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
85 //printf(" vtbl[%d] is '%s'\n", j, ifd ? ifd.toChars() : "null");
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
86
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
87 assert(ifd);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
88 // Find corresponding function in this class
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
89 tf = (ifd.type.ty == Tfunction) ? cast(TypeFunction)(ifd.type) : null;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
90 fd = cd.findFunc(ifd.ident, tf);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
91 if (fd && !fd.isAbstract())
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
92 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
93 //printf(" found\n");
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
94 // Check that calling conventions match
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
95 if (fd.linkage != ifd.linkage)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
96 fd.error("linkage doesn't match interface function");
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
97
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
98 // Check that it is current
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
99 if (newinstance &&
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
100 fd.toParent() != cd &&
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
101 ifd.toParent() == base
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
102 )
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
103 cd.error("interface function %s.%s is not implemented",
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
104 id.toChars(), ifd.ident.toChars());
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
105
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
106 if (fd.toParent() == cd)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
107 result = true;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
108 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
109 else
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
110 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
111 //printf(" not found\n");
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
112 // BUG: should mark this class as abstract?
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
113 if (!cd.isAbstract())
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
114 cd.error("interface function %s.%s isn't implemented", id.toChars(), ifd.ident.toChars());
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
115 fd = null;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
116 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
117 if (vtbl)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
118 vtbl.data[j] = cast(void*)fd;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
119 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
120
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
121 return result;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
122 }
178
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
123
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
124 void copyBaseInterfaces(BaseClasses vtblInterfaces)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
125 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
126 //printf("+copyBaseInterfaces(), %s\n", base.toChars());
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
127 // if (baseInterfaces_dim)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
128 // return;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
129
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
130 baseInterfaces.length = base.interfaces_dim;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
131
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
132 //printf("%s.copyBaseInterfaces()\n", base.toChars());
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
133 for (int i = 0; i < baseInterfaces.length; i++)
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
134 {
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
135 BaseClass b2 = base.interfaces[i];
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
136 assert(b2.vtbl.dim == 0); // should not be filled yet
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
137
178
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
138 BaseClass b = cloneThis(b2);
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
139 baseInterfaces[i] = b;
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
140
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
141 if (i) // single inheritance is i==0
125
767a01c2a272 BaseClasses -> Vector
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents: 114
diff changeset
142 vtblInterfaces.push(b); // only need for M.I.
0
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
143 b.copyBaseInterfaces(vtblInterfaces);
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
144 }
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
145 //printf("-copyBaseInterfaces\n");
10317f0c89a5 Initial commit
korDen
parents:
diff changeset
146 }
178
e3afd1303184 Many small bugs fixed
korDen
parents: 125
diff changeset
147 }