Mercurial > projects > ddmd
annotate dmd/Declaration.d @ 178:e3afd1303184
Many small bugs fixed
Made all classes derive from TObject to detect memory leaks (functionality is disabled for now)
Began work on overriding backend memory allocations (to avoid memory leaks)
author | korDen |
---|---|
date | Sun, 17 Oct 2010 07:42:00 +0400 |
parents | bc45b1c53019 |
children | cd48cb899aee |
rev | line source |
---|---|
0 | 1 module dmd.Declaration; |
2 | |
114 | 3 import dmd.common; |
0 | 4 import dmd.Dsymbol; |
5 import dmd.Type; | |
79 | 6 import dmd.TypedefDeclaration; |
0 | 7 import dmd.PROT; |
8 import dmd.LINK; | |
9 import dmd.Identifier; | |
79 | 10 import dmd.Json; |
0 | 11 import dmd.Scope; |
12 import dmd.Loc; | |
13 import dmd.STC; | |
14 import dmd.FuncDeclaration; | |
15 import dmd.VarDeclaration; | |
16 import dmd.OutBuffer; | |
17 | |
18 import std.stdio : writef; | |
19 | |
20 import core.stdc.ctype; | |
21 import core.stdc.stdio : sprintf; | |
22 | |
23 string mangle(Declaration sthis) | |
24 { | |
25 scope OutBuffer buf = new OutBuffer(); | |
26 | |
27 string id; | |
28 Dsymbol s = sthis; | |
29 | |
30 //printf(".mangle(%s)\n", sthis.toChars()); | |
31 do | |
32 { | |
33 //printf("mangle: s = %p, '%s', parent = %p\n", s, s.toChars(), s.parent); | |
34 if (s.ident) | |
35 { | |
36 FuncDeclaration fd = s.isFuncDeclaration(); | |
37 if (s !is sthis && fd) | |
38 { | |
39 id = mangle(fd); | |
40 buf.prependstring(id); | |
41 goto L1; | |
42 } | |
43 else | |
44 { | |
45 id = s.ident.toChars(); | |
46 int len = id.length; | |
47 char tmp[len.sizeof * 3 + 1]; | |
48 buf.prependstring(id); | |
49 len = sprintf(tmp.ptr, "%d".ptr, len); | |
50 buf.prependstring(tmp[0..len]); | |
51 } | |
52 } | |
53 else | |
54 buf.prependstring("0"); | |
55 s = s.parent; | |
56 } while (s); | |
57 | |
58 // buf.prependstring("_D"); | |
59 L1: | |
60 //printf("deco = '%s'\n", sthis.type.deco ? sthis.type.deco : "null"); | |
61 //printf("sthis.type = %s\n", sthis.type.toChars()); | |
62 FuncDeclaration fd = sthis.isFuncDeclaration(); | |
63 if (fd && (fd.needThis() || fd.isNested())) | |
64 buf.writeByte(Type.needThisPrefix()); | |
65 if (sthis.type.deco) | |
66 buf.writestring(sthis.type.deco); | |
67 else | |
68 { | |
96 | 69 debug |
70 { | |
0 | 71 if (!fd.inferRetType) |
72 writef("%s\n", fd.toChars()); | |
73 } | |
96 | 74 assert(fd && fd.inferRetType); |
0 | 75 } |
76 | |
77 id = buf.extractString(); | |
78 return id; | |
79 } | |
80 | |
81 class Declaration : Dsymbol | |
82 { | |
83 Type type; | |
84 Type originalType; // before semantic analysis | |
131
206db751bd4c
dmdfe 2.037 compiles now
Eldar Insafutdinov <e.insafutdinov@gmail.com>
parents:
129
diff
changeset
|
85 StorageClass storage_class = STC.STCundefined; |
0 | 86 PROT protection = PROT.PROTundefined; |
87 LINK linkage = LINK.LINKdefault; | |
88 int inuse; // used to detect cycles | |
89 | |
90 this(Identifier id) | |
91 { | |
178 | 92 register(); |
0 | 93 super(id); |
94 } | |
95 | |
72 | 96 override void semantic(Scope sc) |
0 | 97 { |
98 } | |
99 | |
72 | 100 override string kind() |
0 | 101 { |
102 assert(false); | |
103 } | |
104 | |
72 | 105 override uint size(Loc loc) |
0 | 106 { |
107 assert(false); | |
108 } | |
109 | |
110 /************************************* | |
111 * Check to see if declaration can be modified in this context (sc). | |
112 * Issue error if not. | |
113 */ | |
114 void checkModify(Loc loc, Scope sc, Type t) | |
115 { | |
116 if (sc.incontract && isParameter()) | |
117 error(loc, "cannot modify parameter '%s' in contract", toChars()); | |
118 | |
119 if (isCtorinit()) | |
120 { | |
121 // It's only modifiable if inside the right constructor | |
122 Dsymbol s = sc.func; | |
123 while (true) | |
124 { | |
125 FuncDeclaration fd = null; | |
126 if (s) | |
127 fd = s.isFuncDeclaration(); | |
128 if (fd && ((fd.isCtorDeclaration() && storage_class & STC.STCfield) || | |
129 (fd.isStaticCtorDeclaration() && !(storage_class & STC.STCfield))) && | |
130 fd.toParent() == toParent() | |
131 ) | |
132 { | |
133 VarDeclaration v = isVarDeclaration(); | |
134 assert(v); | |
135 v.ctorinit = 1; | |
136 //printf("setting ctorinit\n"); | |
137 } | |
138 else | |
139 { | |
140 if (s) | |
141 { | |
142 s = s.toParent2(); | |
143 continue; | |
144 } | |
145 else | |
146 { | |
147 string p = isStatic() ? "static " : ""; | |
148 error(loc, "can only initialize %sconst %s inside %sconstructor", p, toChars(), p); | |
149 } | |
150 } | |
151 break; | |
152 } | |
153 } | |
154 else | |
155 { | |
156 VarDeclaration v = isVarDeclaration(); | |
157 if (v && v.canassign == 0) | |
158 { | |
159 string p = null; | |
160 if (isConst()) | |
161 p = "const"; | |
135 | 162 else if (isImmutable()) |
0 | 163 p = "immutable"; |
164 else if (storage_class & STC.STCmanifest) | |
165 p = "enum"; | |
166 else if (!t.isAssignable()) | |
167 p = "struct with immutable members"; | |
168 if (p) | |
169 { | |
170 error(loc, "cannot modify %s", p); | |
171 } | |
172 } | |
173 } | |
174 } | |
175 | |
72 | 176 override void emitComment(Scope sc) |
0 | 177 { |
178 assert(false); | |
179 } | |
180 | |
79 | 181 override void toJsonBuffer(OutBuffer buf) |
182 { | |
183 //writef("Declaration.toJsonBuffer()\n"); | |
184 buf.writestring("{\n"); | |
185 | |
186 JsonProperty(buf, Pname, toChars()); | |
187 JsonProperty(buf, Pkind, kind()); | |
188 if (type) | |
189 JsonProperty(buf, Ptype, type.toChars()); | |
190 | |
191 if (comment) | |
192 JsonProperty(buf, Pcomment, comment); | |
193 | |
194 if (loc.linnum) | |
195 JsonProperty(buf, Pline, loc.linnum); | |
196 | |
197 TypedefDeclaration td = isTypedefDeclaration(); | |
198 if (td) | |
199 { | |
200 JsonProperty(buf, "base", td.basetype.toChars()); | |
201 } | |
202 | |
203 JsonRemoveComma(buf); | |
204 buf.writestring("}\n"); | |
205 } | |
206 | |
72 | 207 override void toDocBuffer(OutBuffer buf) |
0 | 208 { |
209 assert(false); | |
210 } | |
211 | |
72 | 212 override string mangle() |
14
2cc604139636
Implemented Linux support for ddmd. Some parts are a bit hacky to just "get it working", that said, druntime and phobos compile, and unittests pass.
Robert Clipsham <robert@octarineparrot.com>
parents:
0
diff
changeset
|
213 /+out (result) |
0 | 214 { |
215 try | |
216 { | |
217 int len = result.length; | |
218 | |
219 assert(len > 0); | |
220 //printf("mangle: '%s' => '%s'\n", toChars(), result); | |
221 for (int i = 0; i < len; i++) | |
222 { | |
223 assert(result[i] == '_' || result[i] == '@' || isalnum(result[i]) || result[i] & 0x80); | |
224 } | |
225 } catch { | |
226 writef("Incorrect mangle: '%s'\n", result); | |
227 assert(false); | |
228 } | |
229 } | |
14
2cc604139636
Implemented Linux support for ddmd. Some parts are a bit hacky to just "get it working", that said, druntime and phobos compile, and unittests pass.
Robert Clipsham <robert@octarineparrot.com>
parents:
0
diff
changeset
|
230 body+/ |
0 | 231 { |
22
fd4acc376c45
Implemented object file output and linking on linux.
Robert Clipsham <robert@octarineparrot.com>
parents:
16
diff
changeset
|
232 version(Bug3602) { writef( "Bug3602: Uncomment outblock when fixed\n" ); } |
0 | 233 //writef("Declaration.mangle(this = %p, '%s', parent = '%s', linkage = %d)\n", this, toChars(), parent ? parent.toChars() : "null", linkage); |
234 if (!parent || parent.isModule() || linkage == LINK.LINKcpp) // if at global scope | |
235 { | |
236 // If it's not a D declaration, no mangling | |
237 switch (linkage) | |
238 { | |
239 case LINK.LINKd: | |
240 break; | |
241 | |
242 case LINK.LINKc: | |
243 case LINK.LINKwindows: | |
244 case LINK.LINKpascal: | |
245 return ident.toChars(); | |
246 | |
247 case LINK.LINKcpp: | |
248 version (CPP_MANGLE) { | |
249 return cpp_mangle(this); | |
250 } else { | |
251 // Windows C++ mangling is done by C++ back end | |
252 return ident.toChars(); | |
253 } | |
254 | |
255 case LINK.LINKdefault: | |
256 error("forward declaration"); | |
257 return ident.toChars(); | |
258 | |
259 default: | |
260 writef("'%s', linkage = %d\n", toChars(), linkage); | |
261 assert(0); | |
262 } | |
263 } | |
264 | |
265 string p = .mangle(this); | |
266 scope OutBuffer buf = new OutBuffer(); | |
267 buf.writestring("_D"); | |
268 buf.writestring(p); | |
269 p = buf.toChars(); | |
270 buf.data = null; | |
271 //writef("Declaration.mangle(this = %p, '%s', parent = '%s', linkage = %d) = %s\n", this, toChars(), parent ? parent.toChars() : "null", linkage, p); | |
272 return p; | |
273 } | |
274 | |
139 | 275 bool isStatic() { return (storage_class & STC.STCstatic) != 0; } |
0 | 276 |
277 bool isStaticConstructor() | |
278 { | |
279 return false; | |
280 } | |
281 | |
282 bool isStaticDestructor() | |
283 { | |
284 return false; | |
285 } | |
286 | |
287 bool isDelete() | |
288 { | |
289 return false; | |
290 } | |
291 | |
292 bool isDataseg() | |
293 { | |
294 return false; | |
295 } | |
296 | |
297 bool isThreadlocal() | |
298 { | |
68
ee3a9f34dc48
final bits of codegen implementation to compile Phobos
korDen
parents:
22
diff
changeset
|
299 return false; |
0 | 300 } |
301 | |
302 bool isCodeseg() | |
303 { | |
304 return false; | |
305 } | |
306 | |
139 | 307 bool isCtorinit() { return (storage_class & STC.STCctorinit) != 0; } |
0 | 308 |
139 | 309 bool isFinal() { return (storage_class & STC.STCfinal) != 0; } |
0 | 310 |
311 bool isAbstract() { return (storage_class & STC.STCabstract) != 0; } | |
312 | |
313 bool isConst() { return (storage_class & STC.STCconst) != 0; } | |
314 | |
139 | 315 bool isImmutable() { return (storage_class & STC.STCimmutable) != 0; } |
0 | 316 |
139 | 317 bool isAuto() { return (storage_class & STC.STCauto) != 0; } |
0 | 318 |
139 | 319 bool isScope() { return (storage_class & (STC.STCscope | STC.STCauto)) != 0; } |
0 | 320 |
139 | 321 bool isSynchronized() { return (storage_class & STC.STCsynchronized) != 0; } |
0 | 322 |
139 | 323 bool isParameter() { return (storage_class & STC.STCparameter) != 0; } |
0 | 324 |
72 | 325 override bool isDeprecated() { return (storage_class & STC.STCdeprecated) != 0; } |
0 | 326 |
139 | 327 bool isOverride() { return (storage_class & STC.STCoverride) != 0; } |
0 | 328 |
139 | 329 bool isIn() { return (storage_class & STC.STCin) != 0; } |
0 | 330 |
139 | 331 bool isOut() { return (storage_class & STC.STCout) != 0; } |
0 | 332 |
139 | 333 bool isRef() { return (storage_class & STC.STCref) != 0; } |
0 | 334 |
72 | 335 override PROT prot() |
0 | 336 { |
337 return protection; | |
338 } | |
339 | |
72 | 340 override Declaration isDeclaration() { return this; } |
14
2cc604139636
Implemented Linux support for ddmd. Some parts are a bit hacky to just "get it working", that said, druntime and phobos compile, and unittests pass.
Robert Clipsham <robert@octarineparrot.com>
parents:
0
diff
changeset
|
341 } |