Mercurial > projects > ldc
annotate dmd/cast.c @ 1138:4c8bb03e4fbc
Update DtoConstFP() to be correct after LLVM r67562, which changed the way the
APFloat constructor expects its i80 APInts to be formatted. (They're now
actually consistent with the x87 format)
author | Frits van Bommel <fvbommel wxs.nl> |
---|---|
date | Tue, 24 Mar 2009 15:24:59 +0100 |
parents | eeb8b95ea92e |
children | e961851fb8be |
rev | line source |
---|---|
159 | 1 |
336 | 2 // Copyright (c) 1999-2008 by Digital Mars |
159 | 3 // All Rights Reserved |
4 // written by Walter Bright | |
5 // http://www.digitalmars.com | |
6 // License for redistribution is by either the Artistic License | |
7 // in artistic.txt, or the GNU General Public License in gnu.txt. | |
8 // See the included readme.txt for details. | |
9 | |
10 #include <stdio.h> | |
11 #include <assert.h> | |
12 | |
1103
b30fe7e1dbb9
- Updated to DMD frontend 1.041.
Tomas Lindquist Olsen <tomas.l.olsen gmail.com>
parents:
846
diff
changeset
|
13 #include "rmem.h" |
159 | 14 |
15 #include "expression.h" | |
16 #include "mtype.h" | |
17 #include "utf.h" | |
18 #include "declaration.h" | |
19 #include "aggregate.h" | |
20 | |
21 /* ==================== implicitCast ====================== */ | |
22 | |
23 /************************************** | |
24 * Do an implicit cast. | |
25 * Issue error if it can't be done. | |
26 */ | |
27 | |
28 Expression *Expression::implicitCastTo(Scope *sc, Type *t) | |
29 { | |
30 //printf("implicitCastTo(%s) => %s\n", type->toChars(), t->toChars()); | |
31 if (implicitConvTo(t)) | |
846
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
32 { TY tyfrom = type->toBasetype()->ty; |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
33 TY tyto = t->toBasetype()->ty; |
159 | 34 if (global.params.warnings && |
846
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
35 Type::impcnvWarn[tyfrom][tyto] && |
159 | 36 op != TOKint64) |
37 { | |
38 Expression *e = optimize(WANTflags | WANTvalue); | |
39 | |
40 if (e->op == TOKint64) | |
41 return e->implicitCastTo(sc, t); | |
42 | |
846
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
43 if (tyfrom == Tint32 && |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
44 (op == TOKadd || op == TOKmin || |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
45 op == TOKand || op == TOKor || op == TOKxor) |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
46 ) |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
47 { |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
48 /* This is really only a semi-kludge fix, |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
49 * we really should look at the operands of op |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
50 * and see if they are narrower types. |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
51 * For example, b=b|b and b=b|7 and s=b+b should be allowed, |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
52 * but b=b|i should be an error. |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
53 */ |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
54 ; |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
55 } |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
56 else |
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
57 { |
1133
eeb8b95ea92e
Cleanup DMD 1.041 merge.
Tomas Lindquist Olsen <tomas.l.olsen gmail.com>
parents:
1103
diff
changeset
|
58 warning("implicit conversion of expression (%s) of type %s to %s can cause loss of data", |
eeb8b95ea92e
Cleanup DMD 1.041 merge.
Tomas Lindquist Olsen <tomas.l.olsen gmail.com>
parents:
1103
diff
changeset
|
59 toChars(), type->toChars(), t->toChars()); |
846
bc982f1ad106
Merged DMD 1.037 frontend
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
717
diff
changeset
|
60 } |
159 | 61 } |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
62 #if DMDV2 |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
63 if (match == MATCHconst && t == type->constOf()) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
64 { |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
65 Expression *e = copy(); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
66 e->type = t; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
67 return e; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
68 } |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
69 #endif |
159 | 70 return castTo(sc, t); |
71 } | |
72 | |
73 Expression *e = optimize(WANTflags | WANTvalue); | |
74 if (e != this) | |
75 return e->implicitCastTo(sc, t); | |
76 | |
77 #if 0 | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
78 printf("ty = %d\n", type->ty); |
159 | 79 print(); |
80 type->print(); | |
81 printf("to:\n"); | |
82 t->print(); | |
83 printf("%p %p type: %s to: %s\n", type->deco, t->deco, type->deco, t->deco); | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
84 //printf("%p %p %p\n", type->nextOf()->arrayOf(), type, t); |
159 | 85 fflush(stdout); |
86 #endif | |
87 if (!t->deco) | |
88 { /* Can happen with: | |
89 * enum E { One } | |
90 * class A | |
91 * { static void fork(EDG dg) { dg(E.One); } | |
92 * alias void delegate(E) EDG; | |
93 * } | |
94 * Should eventually make it work. | |
95 */ | |
96 error("forward reference to type %s", t->toChars()); | |
97 } | |
98 else if (t->reliesOnTident()) | |
99 error("forward reference to type %s", t->reliesOnTident()->toChars()); | |
100 | |
101 error("cannot implicitly convert expression (%s) of type %s to %s", | |
102 toChars(), type->toChars(), t->toChars()); | |
103 return castTo(sc, t); | |
104 } | |
105 | |
106 /******************************************* | |
107 * Return !=0 if we can implicitly convert this to type t. | |
108 * Don't do the actual cast. | |
109 */ | |
110 | |
111 MATCH Expression::implicitConvTo(Type *t) | |
112 { | |
113 #if 0 | |
114 printf("Expression::implicitConvTo(this=%s, type=%s, t=%s)\n", | |
115 toChars(), type->toChars(), t->toChars()); | |
116 #endif | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
117 //static int nest; if (++nest == 10) halt(); |
159 | 118 if (!type) |
119 { error("%s is not an expression", toChars()); | |
120 type = Type::terror; | |
121 } | |
122 if (t->ty == Tbit && isBit()) | |
123 return MATCHconvert; | |
124 Expression *e = optimize(WANTvalue | WANTflags); | |
125 if (e != this) | |
126 { //printf("optimzed to %s\n", e->toChars()); | |
127 return e->implicitConvTo(t); | |
128 } | |
129 MATCH match = type->implicitConvTo(t); | |
130 if (match) | |
131 return match; | |
132 #if 0 | |
133 Type *tb = t->toBasetype(); | |
134 if (tb->ty == Tdelegate) | |
135 { TypeDelegate *td = (TypeDelegate *)tb; | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
136 TypeFunction *tf = (TypeFunction *)td->nextOf(); |
159 | 137 |
138 if (!tf->varargs && | |
139 !(tf->arguments && tf->arguments->dim) | |
140 ) | |
141 { | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
142 match = type->implicitConvTo(tf->nextOf()); |
159 | 143 if (match) |
144 return match; | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
145 if (tf->nextOf()->toBasetype()->ty == Tvoid) |
159 | 146 return MATCHconvert; |
147 } | |
148 } | |
149 #endif | |
150 return MATCHnomatch; | |
151 } | |
152 | |
153 | |
154 MATCH IntegerExp::implicitConvTo(Type *t) | |
155 { | |
156 #if 0 | |
157 printf("IntegerExp::implicitConvTo(this=%s, type=%s, t=%s)\n", | |
158 toChars(), type->toChars(), t->toChars()); | |
159 #endif | |
160 if (type->equals(t)) | |
161 return MATCHexact; | |
162 | |
163 enum TY ty = type->toBasetype()->ty; | |
164 enum TY toty = t->toBasetype()->ty; | |
165 | |
166 if (type->implicitConvTo(t) == MATCHnomatch && t->ty == Tenum) | |
167 { | |
168 return MATCHnomatch; | |
169 } | |
170 | |
171 switch (ty) | |
172 { | |
173 case Tbit: | |
174 case Tbool: | |
175 value &= 1; | |
176 ty = Tint32; | |
177 break; | |
178 | |
179 case Tint8: | |
180 value = (signed char)value; | |
181 ty = Tint32; | |
182 break; | |
183 | |
184 case Tchar: | |
185 case Tuns8: | |
186 value &= 0xFF; | |
187 ty = Tint32; | |
188 break; | |
189 | |
190 case Tint16: | |
191 value = (short)value; | |
192 ty = Tint32; | |
193 break; | |
194 | |
195 case Tuns16: | |
196 case Twchar: | |
197 value &= 0xFFFF; | |
198 ty = Tint32; | |
199 break; | |
200 | |
201 case Tint32: | |
202 value = (int)value; | |
203 break; | |
204 | |
205 case Tuns32: | |
206 case Tdchar: | |
207 value &= 0xFFFFFFFF; | |
208 ty = Tuns32; | |
209 break; | |
210 | |
211 default: | |
212 break; | |
213 } | |
214 | |
215 // Only allow conversion if no change in value | |
216 switch (toty) | |
217 { | |
218 case Tbit: | |
219 case Tbool: | |
220 if ((value & 1) != value) | |
221 goto Lno; | |
222 goto Lyes; | |
223 | |
224 case Tint8: | |
225 if ((signed char)value != value) | |
226 goto Lno; | |
227 goto Lyes; | |
228 | |
229 case Tchar: | |
230 case Tuns8: | |
231 //printf("value = %llu %llu\n", (integer_t)(unsigned char)value, value); | |
232 if ((unsigned char)value != value) | |
233 goto Lno; | |
234 goto Lyes; | |
235 | |
236 case Tint16: | |
237 if ((short)value != value) | |
238 goto Lno; | |
239 goto Lyes; | |
240 | |
241 case Tuns16: | |
242 if ((unsigned short)value != value) | |
243 goto Lno; | |
244 goto Lyes; | |
245 | |
246 case Tint32: | |
247 if (ty == Tuns32) | |
248 { | |
249 } | |
250 else if ((int)value != value) | |
251 goto Lno; | |
252 goto Lyes; | |
253 | |
254 case Tuns32: | |
255 if (ty == Tint32) | |
256 { | |
257 } | |
258 else if ((unsigned)value != value) | |
259 goto Lno; | |
260 goto Lyes; | |
261 | |
262 case Tdchar: | |
263 if (value > 0x10FFFFUL) | |
264 goto Lno; | |
265 goto Lyes; | |
266 | |
267 case Twchar: | |
268 if ((unsigned short)value != value) | |
269 goto Lno; | |
270 goto Lyes; | |
271 | |
272 case Tfloat32: | |
273 { | |
274 volatile float f; | |
275 if (type->isunsigned()) | |
276 { | |
277 f = (float)value; | |
278 if (f != value) | |
279 goto Lno; | |
280 } | |
281 else | |
282 { | |
283 f = (float)(long long)value; | |
284 if (f != (long long)value) | |
285 goto Lno; | |
286 } | |
287 goto Lyes; | |
288 } | |
289 | |
290 case Tfloat64: | |
291 { | |
292 volatile double f; | |
293 if (type->isunsigned()) | |
294 { | |
295 f = (double)value; | |
296 if (f != value) | |
297 goto Lno; | |
298 } | |
299 else | |
300 { | |
301 f = (double)(long long)value; | |
302 if (f != (long long)value) | |
303 goto Lno; | |
304 } | |
305 goto Lyes; | |
306 } | |
307 | |
308 case Tfloat80: | |
309 { | |
310 volatile long double f; | |
311 if (type->isunsigned()) | |
312 { | |
313 f = (long double)value; | |
314 if (f != value) | |
315 goto Lno; | |
316 } | |
317 else | |
318 { | |
319 f = (long double)(long long)value; | |
320 if (f != (long long)value) | |
321 goto Lno; | |
322 } | |
323 goto Lyes; | |
324 } | |
325 } | |
326 return Expression::implicitConvTo(t); | |
327 | |
328 Lyes: | |
329 //printf("MATCHconvert\n"); | |
330 return MATCHconvert; | |
331 | |
332 Lno: | |
333 //printf("MATCHnomatch\n"); | |
334 return MATCHnomatch; | |
335 } | |
336 | |
337 MATCH NullExp::implicitConvTo(Type *t) | |
338 { | |
339 #if 0 | |
717
a26b0c5d5942
Merged DMD 1.036.
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
664
diff
changeset
|
340 printf("NullExp::implicitConvTo(this=%s, type=%s, t=%s, committed = %d)\n", |
a26b0c5d5942
Merged DMD 1.036.
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
664
diff
changeset
|
341 toChars(), type->toChars(), t->toChars(), committed); |
159 | 342 #endif |
343 if (this->type->equals(t)) | |
344 return MATCHexact; | |
345 // NULL implicitly converts to any pointer type or dynamic array | |
346 if (type->ty == Tpointer && type->next->ty == Tvoid) | |
347 { | |
348 if (t->ty == Ttypedef) | |
349 t = ((TypeTypedef *)t)->sym->basetype; | |
350 if (t->ty == Tpointer || t->ty == Tarray || | |
351 t->ty == Taarray || t->ty == Tclass || | |
352 t->ty == Tdelegate) | |
353 return committed ? MATCHconvert : MATCHexact; | |
354 } | |
355 return Expression::implicitConvTo(t); | |
356 } | |
357 | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
358 #if DMDV2 |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
359 MATCH StructLiteralExp::implicitConvTo(Type *t) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
360 { |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
361 #if 0 |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
362 printf("StructLiteralExp::implicitConvTo(this=%s, type=%s, t=%s)\n", |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
363 toChars(), type->toChars(), t->toChars()); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
364 #endif |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
365 MATCH m = Expression::implicitConvTo(t); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
366 if (m != MATCHnomatch) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
367 return m; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
368 if (type->ty == t->ty && type->ty == Tstruct && |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
369 ((TypeStruct *)type)->sym == ((TypeStruct *)t)->sym) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
370 { |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
371 m = MATCHconst; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
372 for (int i = 0; i < elements->dim; i++) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
373 { Expression *e = (Expression *)elements->data[i]; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
374 Type *te = e->type; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
375 if (t->mod == 0) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
376 te = te->mutableOf(); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
377 else |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
378 { assert(t->mod == MODinvariant); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
379 te = te->invariantOf(); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
380 } |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
381 MATCH m2 = e->implicitConvTo(te); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
382 //printf("\t%s => %s, match = %d\n", e->toChars(), te->toChars(), m2); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
383 if (m2 < m) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
384 m = m2; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
385 } |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
386 } |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
387 return m; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
388 } |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
389 #endif |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
390 |
159 | 391 MATCH StringExp::implicitConvTo(Type *t) |
392 { MATCH m; | |
393 | |
394 #if 0 | |
395 printf("StringExp::implicitConvTo(this=%s, committed=%d, type=%s, t=%s)\n", | |
396 toChars(), committed, type->toChars(), t->toChars()); | |
397 #endif | |
398 if (!committed) | |
399 { | |
400 if (!committed && t->ty == Tpointer && t->next->ty == Tvoid) | |
401 { | |
402 return MATCHnomatch; | |
403 } | |
404 if (type->ty == Tsarray || type->ty == Tarray || type->ty == Tpointer) | |
405 { | |
406 if (type->next->ty == Tchar) | |
407 { | |
408 switch (t->ty) | |
409 { | |
410 case Tsarray: | |
411 if (type->ty == Tsarray && | |
412 ((TypeSArray *)type)->dim->toInteger() != | |
413 ((TypeSArray *)t)->dim->toInteger()) | |
414 return MATCHnomatch; | |
415 goto L1; | |
416 case Tarray: | |
417 goto L1; | |
418 case Tpointer: | |
419 L1: | |
420 if (t->next->ty == Tchar) | |
421 return MATCHexact; | |
422 else if (t->next->ty == Twchar) | |
423 return MATCHexact; | |
424 else if (t->next->ty == Tdchar) | |
425 return MATCHexact; | |
426 break; | |
427 } | |
428 } | |
429 } | |
430 } | |
431 return Expression::implicitConvTo(t); | |
432 #if 0 | |
433 m = (MATCH)type->implicitConvTo(t); | |
434 if (m) | |
435 { | |
436 return m; | |
437 } | |
438 | |
439 return MATCHnomatch; | |
440 #endif | |
441 } | |
442 | |
443 MATCH ArrayLiteralExp::implicitConvTo(Type *t) | |
444 { MATCH result = MATCHexact; | |
445 | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
446 #if 0 |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
447 printf("ArrayLiteralExp::implicitConvTo(this=%s, type=%s, t=%s)\n", |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
448 toChars(), type->toChars(), t->toChars()); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
449 #endif |
159 | 450 Type *typeb = type->toBasetype(); |
451 Type *tb = t->toBasetype(); | |
452 if ((tb->ty == Tarray || tb->ty == Tsarray) && | |
453 (typeb->ty == Tarray || typeb->ty == Tsarray)) | |
454 { | |
455 if (tb->ty == Tsarray) | |
456 { TypeSArray *tsa = (TypeSArray *)tb; | |
457 if (elements->dim != tsa->dim->toInteger()) | |
458 result = MATCHnomatch; | |
459 } | |
460 | |
461 for (int i = 0; i < elements->dim; i++) | |
462 { Expression *e = (Expression *)elements->data[i]; | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
463 MATCH m = (MATCH)e->implicitConvTo(tb->nextOf()); |
159 | 464 if (m < result) |
465 result = m; // remember worst match | |
466 if (result == MATCHnomatch) | |
467 break; // no need to check for worse | |
468 } | |
469 return result; | |
470 } | |
471 else | |
472 return Expression::implicitConvTo(t); | |
473 } | |
474 | |
475 MATCH AssocArrayLiteralExp::implicitConvTo(Type *t) | |
476 { MATCH result = MATCHexact; | |
477 | |
478 Type *typeb = type->toBasetype(); | |
479 Type *tb = t->toBasetype(); | |
480 if (tb->ty == Taarray && typeb->ty == Taarray) | |
481 { | |
482 for (size_t i = 0; i < keys->dim; i++) | |
483 { Expression *e = (Expression *)keys->data[i]; | |
484 MATCH m = (MATCH)e->implicitConvTo(((TypeAArray *)tb)->key); | |
485 if (m < result) | |
486 result = m; // remember worst match | |
487 if (result == MATCHnomatch) | |
488 break; // no need to check for worse | |
489 e = (Expression *)values->data[i]; | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
490 m = (MATCH)e->implicitConvTo(tb->nextOf()); |
159 | 491 if (m < result) |
492 result = m; // remember worst match | |
493 if (result == MATCHnomatch) | |
494 break; // no need to check for worse | |
495 } | |
496 return result; | |
497 } | |
498 else | |
499 return Expression::implicitConvTo(t); | |
500 } | |
501 | |
502 MATCH AddrExp::implicitConvTo(Type *t) | |
503 { | |
504 #if 0 | |
505 printf("AddrExp::implicitConvTo(this=%s, type=%s, t=%s)\n", | |
506 toChars(), type->toChars(), t->toChars()); | |
507 #endif | |
508 MATCH result; | |
509 | |
510 result = type->implicitConvTo(t); | |
511 //printf("\tresult = %d\n", result); | |
512 | |
513 if (result == MATCHnomatch) | |
514 { | |
515 // Look for pointers to functions where the functions are overloaded. | |
516 VarExp *ve; | |
517 FuncDeclaration *f; | |
518 | |
519 t = t->toBasetype(); | |
520 if (type->ty == Tpointer && type->next->ty == Tfunction && | |
521 t->ty == Tpointer && t->next->ty == Tfunction && | |
522 e1->op == TOKvar) | |
523 { | |
524 ve = (VarExp *)e1; | |
525 f = ve->var->isFuncDeclaration(); | |
526 if (f && f->overloadExactMatch(t->next)) | |
527 result = MATCHexact; | |
528 } | |
529 } | |
530 //printf("\tresult = %d\n", result); | |
531 return result; | |
532 } | |
533 | |
534 MATCH SymOffExp::implicitConvTo(Type *t) | |
535 { | |
536 #if 0 | |
537 printf("SymOffExp::implicitConvTo(this=%s, type=%s, t=%s)\n", | |
538 toChars(), type->toChars(), t->toChars()); | |
539 #endif | |
540 MATCH result; | |
541 | |
542 result = type->implicitConvTo(t); | |
543 //printf("\tresult = %d\n", result); | |
544 | |
545 if (result == MATCHnomatch) | |
546 { | |
547 // Look for pointers to functions where the functions are overloaded. | |
548 FuncDeclaration *f; | |
549 | |
550 t = t->toBasetype(); | |
551 if (type->ty == Tpointer && type->next->ty == Tfunction && | |
552 t->ty == Tpointer && t->next->ty == Tfunction) | |
553 { | |
554 f = var->isFuncDeclaration(); | |
555 if (f && f->overloadExactMatch(t->next)) | |
556 result = MATCHexact; | |
557 } | |
558 } | |
559 //printf("\tresult = %d\n", result); | |
560 return result; | |
561 } | |
562 | |
563 MATCH DelegateExp::implicitConvTo(Type *t) | |
564 { | |
565 #if 0 | |
566 printf("DelegateExp::implicitConvTo(this=%s, type=%s, t=%s)\n", | |
567 toChars(), type->toChars(), t->toChars()); | |
568 #endif | |
569 MATCH result; | |
570 | |
571 result = type->implicitConvTo(t); | |
572 | |
573 if (result == 0) | |
574 { | |
575 // Look for pointers to functions where the functions are overloaded. | |
576 FuncDeclaration *f; | |
577 | |
578 t = t->toBasetype(); | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
579 if (type->ty == Tdelegate && type->nextOf()->ty == Tfunction && |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
580 t->ty == Tdelegate && t->nextOf()->ty == Tfunction) |
159 | 581 { |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
582 if (func && func->overloadExactMatch(t->nextOf())) |
159 | 583 result = MATCHexact; |
584 } | |
585 } | |
586 return result; | |
587 } | |
588 | |
589 MATCH CondExp::implicitConvTo(Type *t) | |
590 { | |
591 MATCH m1; | |
592 MATCH m2; | |
593 | |
594 m1 = e1->implicitConvTo(t); | |
595 m2 = e2->implicitConvTo(t); | |
596 | |
597 // Pick the worst match | |
598 return (m1 < m2) ? m1 : m2; | |
599 } | |
600 | |
601 | |
602 /* ==================== castTo ====================== */ | |
603 | |
604 /************************************** | |
605 * Do an explicit cast. | |
606 */ | |
607 | |
608 Expression *Expression::castTo(Scope *sc, Type *t) | |
609 { | |
610 //printf("Expression::castTo(this=%s, t=%s)\n", toChars(), t->toChars()); | |
611 #if 0 | |
612 printf("Expression::castTo(this=%s, type=%s, t=%s)\n", | |
613 toChars(), type->toChars(), t->toChars()); | |
614 #endif | |
615 if (type == t) | |
616 return this; | |
617 Expression *e = this; | |
618 Type *tb = t->toBasetype(); | |
619 Type *typeb = type->toBasetype(); | |
620 if (tb != typeb) | |
621 { | |
622 // Do (type *) cast of (type [dim]) | |
623 if (tb->ty == Tpointer && | |
624 typeb->ty == Tsarray | |
625 ) | |
626 { | |
627 //printf("Converting [dim] to *\n"); | |
628 | |
629 if (typeb->size(loc) == 0) | |
630 e = new NullExp(loc); | |
631 else | |
632 e = new AddrExp(loc, e); | |
633 } | |
634 #if 0 | |
635 else if (tb->ty == Tdelegate && type->ty != Tdelegate) | |
636 { | |
637 TypeDelegate *td = (TypeDelegate *)tb; | |
638 TypeFunction *tf = (TypeFunction *)td->nextOf(); | |
639 return toDelegate(sc, tf->nextOf()); | |
640 } | |
641 #endif | |
642 else | |
643 { | |
644 e = new CastExp(loc, e, tb); | |
645 } | |
646 } | |
647 else | |
648 { | |
649 e = e->copy(); // because of COW for assignment to e->type | |
650 } | |
651 assert(e != this); | |
652 e->type = t; | |
653 //printf("Returning: %s\n", e->toChars()); | |
654 return e; | |
655 } | |
656 | |
657 | |
658 Expression *RealExp::castTo(Scope *sc, Type *t) | |
659 { Expression *e = this; | |
660 if (type != t) | |
661 { | |
662 if ((type->isreal() && t->isreal()) || | |
663 (type->isimaginary() && t->isimaginary()) | |
664 ) | |
665 { e = copy(); | |
666 e->type = t; | |
667 } | |
668 else | |
669 e = Expression::castTo(sc, t); | |
670 } | |
671 return e; | |
672 } | |
673 | |
674 | |
675 Expression *ComplexExp::castTo(Scope *sc, Type *t) | |
676 { Expression *e = this; | |
677 if (type != t) | |
678 { | |
679 if (type->iscomplex() && t->iscomplex()) | |
680 { e = copy(); | |
681 e->type = t; | |
682 } | |
683 else | |
684 e = Expression::castTo(sc, t); | |
685 } | |
686 return e; | |
687 } | |
688 | |
689 | |
690 Expression *NullExp::castTo(Scope *sc, Type *t) | |
691 { NullExp *e; | |
692 Type *tb; | |
693 | |
694 //printf("NullExp::castTo(t = %p)\n", t); | |
695 if (type == t) | |
696 { | |
697 committed = 1; | |
698 return this; | |
699 } | |
700 e = (NullExp *)copy(); | |
701 e->committed = 1; | |
702 tb = t->toBasetype(); | |
703 e->type = type->toBasetype(); | |
704 if (tb != e->type) | |
705 { | |
706 // NULL implicitly converts to any pointer type or dynamic array | |
707 if (e->type->ty == Tpointer && e->type->nextOf()->ty == Tvoid && | |
708 (tb->ty == Tpointer || tb->ty == Tarray || tb->ty == Taarray || | |
709 tb->ty == Tdelegate)) | |
710 { | |
711 #if 0 | |
712 if (tb->ty == Tdelegate) | |
713 { TypeDelegate *td = (TypeDelegate *)tb; | |
714 TypeFunction *tf = (TypeFunction *)td->nextOf(); | |
715 | |
716 if (!tf->varargs && | |
717 !(tf->arguments && tf->arguments->dim) | |
718 ) | |
719 { | |
720 return Expression::castTo(sc, t); | |
721 } | |
722 } | |
723 #endif | |
724 } | |
725 else | |
726 { | |
727 return e->Expression::castTo(sc, t); | |
728 } | |
729 } | |
730 e->type = t; | |
731 return e; | |
732 } | |
733 | |
734 Expression *StringExp::castTo(Scope *sc, Type *t) | |
735 { | |
736 /* This follows copy-on-write; any changes to 'this' | |
737 * will result in a copy. | |
738 * The this->string member is considered immutable. | |
739 */ | |
740 StringExp *se; | |
741 Type *tb; | |
742 int copied = 0; | |
743 | |
744 //printf("StringExp::castTo(t = %s), '%s' committed = %d\n", t->toChars(), toChars(), committed); | |
745 | |
746 if (!committed && t->ty == Tpointer && t->nextOf()->ty == Tvoid) | |
747 { | |
748 error("cannot convert string literal to void*"); | |
749 } | |
750 | |
751 se = this; | |
752 if (!committed) | |
753 { se = (StringExp *)copy(); | |
754 se->committed = 1; | |
755 copied = 1; | |
756 } | |
757 | |
758 if (type == t) | |
759 { | |
760 return se; | |
761 } | |
762 | |
763 tb = t->toBasetype(); | |
764 //printf("\ttype = %s\n", type->toChars()); | |
765 if (tb->ty == Tdelegate && type->toBasetype()->ty != Tdelegate) | |
766 return Expression::castTo(sc, t); | |
767 | |
768 Type *typeb = type->toBasetype(); | |
769 if (typeb == tb) | |
770 { | |
771 if (!copied) | |
772 { se = (StringExp *)copy(); | |
773 copied = 1; | |
774 } | |
775 se->type = t; | |
776 return se; | |
777 } | |
778 | |
779 if (tb->ty != Tsarray && tb->ty != Tarray && tb->ty != Tpointer) | |
780 { if (!copied) | |
781 { se = (StringExp *)copy(); | |
782 copied = 1; | |
783 } | |
784 goto Lcast; | |
785 } | |
786 if (typeb->ty != Tsarray && typeb->ty != Tarray && typeb->ty != Tpointer) | |
787 { if (!copied) | |
788 { se = (StringExp *)copy(); | |
789 copied = 1; | |
790 } | |
791 goto Lcast; | |
792 } | |
793 | |
794 if (typeb->nextOf()->size() == tb->nextOf()->size()) | |
795 { | |
796 if (!copied) | |
797 { se = (StringExp *)copy(); | |
798 copied = 1; | |
799 } | |
800 if (tb->ty == Tsarray) | |
801 goto L2; // handle possible change in static array dimension | |
802 se->type = t; | |
803 return se; | |
804 } | |
805 | |
806 if (committed) | |
807 goto Lcast; | |
808 | |
809 #define X(tf,tt) ((tf) * 256 + (tt)) | |
810 { | |
811 OutBuffer buffer; | |
812 size_t newlen = 0; | |
813 int tfty = typeb->nextOf()->toBasetype()->ty; | |
814 int ttty = tb->nextOf()->toBasetype()->ty; | |
815 switch (X(tfty, ttty)) | |
816 { | |
817 case X(Tchar, Tchar): | |
818 case X(Twchar,Twchar): | |
819 case X(Tdchar,Tdchar): | |
820 break; | |
821 | |
822 case X(Tchar, Twchar): | |
823 for (size_t u = 0; u < len;) | |
824 { unsigned c; | |
825 char *p = utf_decodeChar((unsigned char *)se->string, len, &u, &c); | |
826 if (p) | |
827 error("%s", p); | |
828 else | |
829 buffer.writeUTF16(c); | |
830 } | |
831 newlen = buffer.offset / 2; | |
832 buffer.writeUTF16(0); | |
833 goto L1; | |
834 | |
835 case X(Tchar, Tdchar): | |
836 for (size_t u = 0; u < len;) | |
837 { unsigned c; | |
838 char *p = utf_decodeChar((unsigned char *)se->string, len, &u, &c); | |
839 if (p) | |
840 error("%s", p); | |
841 buffer.write4(c); | |
842 newlen++; | |
843 } | |
844 buffer.write4(0); | |
845 goto L1; | |
846 | |
847 case X(Twchar,Tchar): | |
848 for (size_t u = 0; u < len;) | |
849 { unsigned c; | |
850 char *p = utf_decodeWchar((unsigned short *)se->string, len, &u, &c); | |
851 if (p) | |
852 error("%s", p); | |
853 else | |
854 buffer.writeUTF8(c); | |
855 } | |
856 newlen = buffer.offset; | |
857 buffer.writeUTF8(0); | |
858 goto L1; | |
859 | |
860 case X(Twchar,Tdchar): | |
861 for (size_t u = 0; u < len;) | |
862 { unsigned c; | |
863 char *p = utf_decodeWchar((unsigned short *)se->string, len, &u, &c); | |
864 if (p) | |
865 error("%s", p); | |
866 buffer.write4(c); | |
867 newlen++; | |
868 } | |
869 buffer.write4(0); | |
870 goto L1; | |
871 | |
872 case X(Tdchar,Tchar): | |
873 for (size_t u = 0; u < len; u++) | |
874 { | |
875 unsigned c = ((unsigned *)se->string)[u]; | |
876 if (!utf_isValidDchar(c)) | |
877 error("invalid UCS-32 char \\U%08x", c); | |
878 else | |
879 buffer.writeUTF8(c); | |
880 newlen++; | |
881 } | |
882 newlen = buffer.offset; | |
883 buffer.writeUTF8(0); | |
884 goto L1; | |
885 | |
886 case X(Tdchar,Twchar): | |
887 for (size_t u = 0; u < len; u++) | |
888 { | |
889 unsigned c = ((unsigned *)se->string)[u]; | |
890 if (!utf_isValidDchar(c)) | |
891 error("invalid UCS-32 char \\U%08x", c); | |
892 else | |
893 buffer.writeUTF16(c); | |
894 newlen++; | |
895 } | |
896 newlen = buffer.offset / 2; | |
897 buffer.writeUTF16(0); | |
898 goto L1; | |
899 | |
900 L1: | |
901 if (!copied) | |
902 { se = (StringExp *)copy(); | |
903 copied = 1; | |
904 } | |
905 se->string = buffer.extractData(); | |
906 se->len = newlen; | |
907 se->sz = tb->nextOf()->size(); | |
908 break; | |
909 | |
910 default: | |
911 assert(typeb->nextOf()->size() != tb->nextOf()->size()); | |
912 goto Lcast; | |
913 } | |
914 } | |
915 #undef X | |
916 L2: | |
917 assert(copied); | |
918 | |
919 // See if need to truncate or extend the literal | |
920 if (tb->ty == Tsarray) | |
921 { | |
922 int dim2 = ((TypeSArray *)tb)->dim->toInteger(); | |
923 | |
924 //printf("dim from = %d, to = %d\n", se->len, dim2); | |
925 | |
926 // Changing dimensions | |
927 if (dim2 != se->len) | |
928 { | |
929 // Copy when changing the string literal | |
930 unsigned newsz = se->sz; | |
931 void *s; | |
932 int d; | |
933 | |
934 d = (dim2 < se->len) ? dim2 : se->len; | |
935 s = (unsigned char *)mem.malloc((dim2 + 1) * newsz); | |
936 memcpy(s, se->string, d * newsz); | |
937 // Extend with 0, add terminating 0 | |
938 memset((char *)s + d * newsz, 0, (dim2 + 1 - d) * newsz); | |
939 se->string = s; | |
940 se->len = dim2; | |
941 } | |
942 } | |
943 se->type = t; | |
944 return se; | |
945 | |
946 Lcast: | |
947 Expression *e = new CastExp(loc, se, t); | |
948 e->type = t; // so semantic() won't be run on e | |
949 return e; | |
950 } | |
951 | |
952 Expression *AddrExp::castTo(Scope *sc, Type *t) | |
953 { | |
954 Type *tb; | |
955 | |
956 #if 0 | |
957 printf("AddrExp::castTo(this=%s, type=%s, t=%s)\n", | |
958 toChars(), type->toChars(), t->toChars()); | |
959 #endif | |
960 Expression *e = this; | |
961 | |
962 tb = t->toBasetype(); | |
963 type = type->toBasetype(); | |
964 if (tb != type) | |
965 { | |
966 // Look for pointers to functions where the functions are overloaded. | |
967 VarExp *ve; | |
968 FuncDeclaration *f; | |
969 | |
970 if (type->ty == Tpointer && type->next->ty == Tfunction && | |
971 tb->ty == Tpointer && tb->next->ty == Tfunction && | |
972 e1->op == TOKvar) | |
973 { | |
974 ve = (VarExp *)e1; | |
975 f = ve->var->isFuncDeclaration(); | |
976 if (f) | |
977 { | |
978 f = f->overloadExactMatch(tb->next); | |
979 if (f) | |
980 { | |
981 e = new VarExp(loc, f); | |
982 e->type = f->type; | |
983 e = new AddrExp(loc, e); | |
984 e->type = t; | |
985 return e; | |
986 } | |
987 } | |
988 } | |
989 e = Expression::castTo(sc, t); | |
990 } | |
991 e->type = t; | |
992 return e; | |
993 } | |
994 | |
995 | |
996 Expression *TupleExp::castTo(Scope *sc, Type *t) | |
997 { TupleExp *e = (TupleExp *)copy(); | |
998 e->exps = (Expressions *)exps->copy(); | |
999 for (size_t i = 0; i < e->exps->dim; i++) | |
1000 { Expression *ex = (Expression *)e->exps->data[i]; | |
1001 ex = ex->castTo(sc, t); | |
1002 e->exps->data[i] = (void *)ex; | |
1003 } | |
1004 return e; | |
1005 } | |
1006 | |
1007 | |
1008 Expression *ArrayLiteralExp::castTo(Scope *sc, Type *t) | |
1009 { | |
1010 #if 0 | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1011 printf("ArrayLiteralExp::castTo(this=%s, type=%s, => %s)\n", |
159 | 1012 toChars(), type->toChars(), t->toChars()); |
1013 #endif | |
1014 if (type == t) | |
1015 return this; | |
1016 ArrayLiteralExp *e = this; | |
1017 Type *typeb = type->toBasetype(); | |
1018 Type *tb = t->toBasetype(); | |
1019 if ((tb->ty == Tarray || tb->ty == Tsarray) && | |
1020 (typeb->ty == Tarray || typeb->ty == Tsarray) && | |
1021 // Not trying to convert non-void[] to void[] | |
1022 !(tb->nextOf()->toBasetype()->ty == Tvoid && typeb->nextOf()->toBasetype()->ty != Tvoid)) | |
1023 { | |
1024 if (tb->ty == Tsarray) | |
1025 { TypeSArray *tsa = (TypeSArray *)tb; | |
1026 if (elements->dim != tsa->dim->toInteger()) | |
1027 goto L1; | |
1028 } | |
1029 | |
1030 e = (ArrayLiteralExp *)copy(); | |
1031 e->elements = (Expressions *)elements->copy(); | |
1032 for (int i = 0; i < elements->dim; i++) | |
1033 { Expression *ex = (Expression *)elements->data[i]; | |
1034 ex = ex->castTo(sc, tb->nextOf()); | |
1035 e->elements->data[i] = (void *)ex; | |
1036 } | |
1037 e->type = t; | |
1038 return e; | |
1039 } | |
1040 if (tb->ty == Tpointer && typeb->ty == Tsarray) | |
1041 { | |
1042 e = (ArrayLiteralExp *)copy(); | |
1043 e->type = typeb->nextOf()->pointerTo(); | |
1044 } | |
1045 L1: | |
1046 return e->Expression::castTo(sc, t); | |
1047 } | |
1048 | |
1049 Expression *AssocArrayLiteralExp::castTo(Scope *sc, Type *t) | |
1050 { | |
1051 if (type == t) | |
1052 return this; | |
1053 AssocArrayLiteralExp *e = this; | |
1054 Type *typeb = type->toBasetype(); | |
1055 Type *tb = t->toBasetype(); | |
1056 if (tb->ty == Taarray && typeb->ty == Taarray && | |
1057 tb->nextOf()->toBasetype()->ty != Tvoid) | |
1058 { | |
1059 e = (AssocArrayLiteralExp *)copy(); | |
1060 e->keys = (Expressions *)keys->copy(); | |
1061 e->values = (Expressions *)values->copy(); | |
1062 assert(keys->dim == values->dim); | |
1063 for (size_t i = 0; i < keys->dim; i++) | |
1064 { Expression *ex = (Expression *)values->data[i]; | |
1065 ex = ex->castTo(sc, tb->nextOf()); | |
1066 e->values->data[i] = (void *)ex; | |
1067 | |
1068 ex = (Expression *)keys->data[i]; | |
1069 ex = ex->castTo(sc, ((TypeAArray *)tb)->index); | |
1070 e->keys->data[i] = (void *)ex; | |
1071 } | |
1072 e->type = t; | |
1073 return e; | |
1074 } | |
1075 L1: | |
1076 return e->Expression::castTo(sc, t); | |
1077 } | |
1078 | |
1079 Expression *SymOffExp::castTo(Scope *sc, Type *t) | |
1080 { | |
1081 Type *tb; | |
1082 | |
1083 #if 0 | |
1084 printf("SymOffExp::castTo(this=%s, type=%s, t=%s)\n", | |
1085 toChars(), type->toChars(), t->toChars()); | |
1086 #endif | |
1087 Expression *e = this; | |
1088 | |
1089 tb = t->toBasetype(); | |
1090 type = type->toBasetype(); | |
1091 if (tb != type) | |
1092 { | |
1093 // Look for pointers to functions where the functions are overloaded. | |
1094 FuncDeclaration *f; | |
1095 | |
1096 if (type->ty == Tpointer && type->next->ty == Tfunction && | |
1097 tb->ty == Tpointer && tb->next->ty == Tfunction) | |
1098 { | |
1099 f = var->isFuncDeclaration(); | |
1100 if (f) | |
1101 { | |
1102 f = f->overloadExactMatch(tb->next); | |
1103 if (f) | |
1104 { | |
1105 e = new SymOffExp(loc, f, 0); | |
1106 e->type = t; | |
1107 return e; | |
1108 } | |
1109 } | |
1110 } | |
1111 e = Expression::castTo(sc, t); | |
1112 } | |
1113 e->type = t; | |
1114 return e; | |
1115 } | |
1116 | |
1117 Expression *DelegateExp::castTo(Scope *sc, Type *t) | |
1118 { | |
1119 Type *tb; | |
1120 #if 0 | |
1121 printf("DelegateExp::castTo(this=%s, type=%s, t=%s)\n", | |
1122 toChars(), type->toChars(), t->toChars()); | |
1123 #endif | |
1124 Expression *e = this; | |
1125 static char msg[] = "cannot form delegate due to covariant return type"; | |
1126 | |
1127 tb = t->toBasetype(); | |
1128 type = type->toBasetype(); | |
1129 if (tb != type) | |
1130 { | |
1131 // Look for delegates to functions where the functions are overloaded. | |
1132 FuncDeclaration *f; | |
1133 | |
1134 if (type->ty == Tdelegate && type->next->ty == Tfunction && | |
1135 tb->ty == Tdelegate && tb->next->ty == Tfunction) | |
1136 { | |
1137 if (func) | |
1138 { | |
1139 f = func->overloadExactMatch(tb->next); | |
1140 if (f) | |
1141 { int offset; | |
1142 if (f->tintro && f->tintro->next->isBaseOf(f->type->next, &offset) && offset) | |
1143 error("%s", msg); | |
1144 e = new DelegateExp(loc, e1, f); | |
1145 e->type = t; | |
1146 return e; | |
1147 } | |
1148 if (func->tintro) | |
1149 error("%s", msg); | |
1150 } | |
1151 } | |
1152 e = Expression::castTo(sc, t); | |
1153 } | |
1154 else | |
1155 { int offset; | |
1156 | |
1157 if (func->tintro && func->tintro->next->isBaseOf(func->type->next, &offset) && offset) | |
1158 error("%s", msg); | |
1159 } | |
1160 e->type = t; | |
1161 return e; | |
1162 } | |
1163 | |
1164 Expression *CondExp::castTo(Scope *sc, Type *t) | |
1165 { | |
1166 Expression *e = this; | |
1167 | |
1168 if (type != t) | |
1169 { | |
1170 if (1 || e1->op == TOKstring || e2->op == TOKstring) | |
1171 { e = new CondExp(loc, econd, e1->castTo(sc, t), e2->castTo(sc, t)); | |
1172 e->type = t; | |
1173 } | |
1174 else | |
1175 e = Expression::castTo(sc, t); | |
1176 } | |
1177 return e; | |
1178 } | |
1179 | |
1180 /* ==================== ====================== */ | |
1181 | |
1182 /**************************************** | |
1183 * Scale addition/subtraction to/from pointer. | |
1184 */ | |
1185 | |
1186 Expression *BinExp::scaleFactor(Scope *sc) | |
1187 { d_uns64 stride; | |
1188 Type *t1b = e1->type->toBasetype(); | |
1189 Type *t2b = e2->type->toBasetype(); | |
1190 | |
1191 if (t1b->ty == Tpointer && t2b->isintegral()) | |
1192 { // Need to adjust operator by the stride | |
1193 // Replace (ptr + int) with (ptr + (int * stride)) | |
1194 Type *t = Type::tptrdiff_t; | |
1195 | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1196 stride = t1b->nextOf()->size(loc); |
159 | 1197 if (!t->equals(t2b)) |
1198 e2 = e2->castTo(sc, t); | |
664
eef8ac26c66c
Some missed LLVMDC -> LDC.
Christian Kamm <kamm incasoftware de>
parents:
510
diff
changeset
|
1199 // LDC: llvm uses typesafe pointer arithmetic |
159 | 1200 #if !IN_LLVM |
1201 if (t1b->next->isbit()) | |
1202 // BUG: should add runtime check for misaligned offsets | |
1203 // This perhaps should be done by rewriting as &p[i] | |
1204 // and letting back end do it. | |
1205 e2 = new UshrExp(loc, e2, new IntegerExp(0, 3, t)); | |
1206 else | |
1207 e2 = new MulExp(loc, e2, new IntegerExp(0, stride, t)); | |
1208 #endif | |
1209 e2->type = t; | |
1210 type = e1->type; | |
1211 } | |
1212 else if (t2b->ty == Tpointer && t1b->isintegral()) | |
1213 { // Need to adjust operator by the stride | |
1214 // Replace (int + ptr) with (ptr + (int * stride)) | |
1215 Type *t = Type::tptrdiff_t; | |
1216 Expression *e; | |
1217 | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1218 stride = t2b->nextOf()->size(loc); |
159 | 1219 if (!t->equals(t1b)) |
1220 e = e1->castTo(sc, t); | |
1221 else | |
1222 e = e1; | |
1223 #if !IN_LLVM | |
1224 if (t2b->next->isbit()) | |
1225 // BUG: should add runtime check for misaligned offsets | |
1226 e = new UshrExp(loc, e, new IntegerExp(0, 3, t)); | |
1227 else | |
1228 e = new MulExp(loc, e, new IntegerExp(0, stride, t)); | |
1229 #endif | |
1230 e->type = t; | |
1231 type = e2->type; | |
1232 e1 = e2; | |
1233 e2 = e; | |
1234 } | |
1235 return this; | |
1236 } | |
1237 | |
1238 /************************************ | |
1239 * Bring leaves to common type. | |
1240 */ | |
1241 | |
1242 Expression *BinExp::typeCombine(Scope *sc) | |
1243 { | |
1244 Type *t1; | |
1245 Type *t2; | |
1246 Type *t; | |
1247 TY ty; | |
1248 | |
1249 //printf("BinExp::typeCombine()\n"); | |
1250 //dump(0); | |
1251 | |
1252 e1 = e1->integralPromotions(sc); | |
1253 e2 = e2->integralPromotions(sc); | |
1254 | |
1255 // BUG: do toBasetype() | |
1256 t1 = e1->type; | |
1257 t2 = e2->type; | |
1258 assert(t1); | |
1259 | |
1260 //if (t1) printf("\tt1 = %s\n", t1->toChars()); | |
1261 //if (t2) printf("\tt2 = %s\n", t2->toChars()); | |
1262 #ifdef DEBUG | |
1263 if (!t2) printf("\te2 = '%s'\n", e2->toChars()); | |
1264 #endif | |
1265 assert(t2); | |
1266 | |
1267 Type *t1b = t1->toBasetype(); | |
1268 Type *t2b = t2->toBasetype(); | |
1269 | |
1270 ty = (TY)Type::impcnvResult[t1b->ty][t2b->ty]; | |
1271 if (ty != Terror) | |
1272 { TY ty1; | |
1273 TY ty2; | |
1274 | |
1275 ty1 = (TY)Type::impcnvType1[t1b->ty][t2b->ty]; | |
1276 ty2 = (TY)Type::impcnvType2[t1b->ty][t2b->ty]; | |
1277 | |
1278 if (t1b->ty == ty1) // if no promotions | |
1279 { | |
1280 if (t1 == t2) | |
1281 { | |
1282 if (!type) | |
1283 type = t1; | |
1284 return this; | |
1285 } | |
1286 | |
1287 if (t1b == t2b) | |
1288 { | |
1289 if (!type) | |
1290 type = t1b; | |
1291 return this; | |
1292 } | |
1293 } | |
1294 | |
1295 if (!type) | |
1296 type = Type::basic[ty]; | |
1297 | |
1298 t1 = Type::basic[ty1]; | |
1299 t2 = Type::basic[ty2]; | |
1300 e1 = e1->castTo(sc, t1); | |
1301 e2 = e2->castTo(sc, t2); | |
1302 #if 0 | |
1303 if (type != Type::basic[ty]) | |
1304 { t = type; | |
1305 type = Type::basic[ty]; | |
1306 return castTo(sc, t); | |
1307 } | |
1308 #endif | |
1309 //printf("after typeCombine():\n"); | |
1310 //dump(0); | |
1311 //printf("ty = %d, ty1 = %d, ty2 = %d\n", ty, ty1, ty2); | |
1312 return this; | |
1313 } | |
1314 | |
1315 t = t1; | |
1316 if (t1 == t2) | |
1317 { | |
1318 if ((t1->ty == Tstruct || t1->ty == Tclass) && | |
1319 (op == TOKmin || op == TOKadd)) | |
1320 goto Lincompatible; | |
1321 } | |
1322 else if (t1->isintegral() && t2->isintegral()) | |
1323 { | |
1324 printf("t1 = %s, t2 = %s\n", t1->toChars(), t2->toChars()); | |
1325 int sz1 = t1->size(); | |
1326 int sz2 = t2->size(); | |
1327 int sign1 = t1->isunsigned() == 0; | |
1328 int sign2 = t2->isunsigned() == 0; | |
1329 | |
1330 if (sign1 == sign2) | |
1331 { | |
1332 if (sz1 < sz2) | |
1333 goto Lt2; | |
1334 else | |
1335 goto Lt1; | |
1336 } | |
1337 if (!sign1) | |
1338 { | |
1339 if (sz1 >= sz2) | |
1340 goto Lt1; | |
1341 else | |
1342 goto Lt2; | |
1343 } | |
1344 else | |
1345 { | |
1346 if (sz2 >= sz1) | |
1347 goto Lt2; | |
1348 else | |
1349 goto Lt1; | |
1350 } | |
1351 } | |
1352 else if (t1->ty == Tpointer && t2->ty == Tpointer) | |
1353 { | |
1354 // Bring pointers to compatible type | |
1355 Type *t1n = t1->next; | |
1356 Type *t2n = t2->next; | |
1357 | |
1358 //t1->print(); | |
1359 //t2->print(); | |
1360 //if (t1n == t2n) *(char *)0 = 0; | |
1361 assert(t1n != t2n); | |
1362 if (t1n->ty == Tvoid) // pointers to void are always compatible | |
1363 t = t2; | |
1364 else if (t2n->ty == Tvoid) | |
1365 ; | |
1366 else if (t1n->ty == Tclass && t2n->ty == Tclass) | |
1367 { ClassDeclaration *cd1 = t1n->isClassHandle(); | |
1368 ClassDeclaration *cd2 = t2n->isClassHandle(); | |
1369 int offset; | |
1370 | |
1371 if (cd1->isBaseOf(cd2, &offset)) | |
1372 { | |
1373 if (offset) | |
1374 e2 = e2->castTo(sc, t); | |
1375 } | |
1376 else if (cd2->isBaseOf(cd1, &offset)) | |
1377 { | |
1378 t = t2; | |
1379 if (offset) | |
1380 e1 = e1->castTo(sc, t); | |
1381 } | |
1382 else | |
1383 goto Lincompatible; | |
1384 } | |
1385 else | |
1386 goto Lincompatible; | |
1387 } | |
1388 else if ((t1->ty == Tsarray || t1->ty == Tarray) && | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1389 e2->op == TOKnull && t2->ty == Tpointer && t2->nextOf()->ty == Tvoid) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1390 { /* (T[n] op void*) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1391 * (T[] op void*) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1392 */ |
159 | 1393 goto Lx1; |
1394 } | |
1395 else if ((t2->ty == Tsarray || t2->ty == Tarray) && | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1396 e1->op == TOKnull && t1->ty == Tpointer && t1->nextOf()->ty == Tvoid) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1397 { /* (void* op T[n]) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1398 * (void* op T[]) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1399 */ |
159 | 1400 goto Lx2; |
1401 } | |
1402 else if ((t1->ty == Tsarray || t1->ty == Tarray) && t1->implicitConvTo(t2)) | |
1403 { | |
1404 goto Lt2; | |
1405 } | |
1406 else if ((t2->ty == Tsarray || t2->ty == Tarray) && t2->implicitConvTo(t1)) | |
1407 { | |
1408 goto Lt1; | |
1409 } | |
1410 else if (t1->ty == Tclass || t2->ty == Tclass) | |
336 | 1411 { |
1412 while (1) | |
159 | 1413 { |
336 | 1414 int i1 = e2->implicitConvTo(t1); |
1415 int i2 = e1->implicitConvTo(t2); | |
1416 | |
1417 if (i1 && i2) | |
1418 { | |
1419 // We have the case of class vs. void*, so pick class | |
1420 if (t1->ty == Tpointer) | |
1421 i1 = 0; | |
1422 else if (t2->ty == Tpointer) | |
1423 i2 = 0; | |
1424 } | |
159 | 1425 |
336 | 1426 if (i2) |
1427 { | |
1428 goto Lt2; | |
1429 } | |
1430 else if (i1) | |
1431 { | |
1432 goto Lt1; | |
1433 } | |
1434 else if (t1->ty == Tclass && t2->ty == Tclass) | |
1435 { TypeClass *tc1 = (TypeClass *)t1; | |
1436 TypeClass *tc2 = (TypeClass *)t2; | |
1437 | |
1438 /* Pick 'tightest' type | |
1439 */ | |
1440 ClassDeclaration *cd1 = tc1->sym->baseClass; | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1441 ClassDeclaration *cd2 = tc2->sym->baseClass; |
336 | 1442 |
1443 if (cd1 && cd2) | |
1444 { t1 = cd1->type; | |
1445 t2 = cd2->type; | |
1446 } | |
1447 else if (cd1) | |
1448 t1 = cd1->type; | |
1449 else if (cd2) | |
1450 t2 = cd2->type; | |
1451 else | |
1452 goto Lincompatible; | |
1453 } | |
1454 else | |
1455 goto Lincompatible; | |
159 | 1456 } |
1457 } | |
1458 else if ((e1->op == TOKstring || e1->op == TOKnull) && e1->implicitConvTo(t2)) | |
1459 { | |
1460 goto Lt2; | |
1461 } | |
1462 //else if (e2->op == TOKstring) { printf("test2\n"); } | |
1463 else if ((e2->op == TOKstring || e2->op == TOKnull) && e2->implicitConvTo(t1)) | |
1464 { | |
1465 goto Lt1; | |
1466 } | |
1467 else if (t1->ty == Tsarray && t2->ty == Tsarray && | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1468 e2->implicitConvTo(t1->nextOf()->arrayOf())) |
159 | 1469 { |
1470 Lx1: | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1471 t = t1->nextOf()->arrayOf(); |
159 | 1472 e1 = e1->castTo(sc, t); |
1473 e2 = e2->castTo(sc, t); | |
1474 } | |
1475 else if (t1->ty == Tsarray && t2->ty == Tsarray && | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1476 e1->implicitConvTo(t2->nextOf()->arrayOf())) |
159 | 1477 { |
1478 Lx2: | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1479 t = t2->nextOf()->arrayOf(); |
159 | 1480 e1 = e1->castTo(sc, t); |
1481 e2 = e2->castTo(sc, t); | |
1482 } | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1483 else if (t1->isintegral() && t2->isintegral()) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1484 { |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1485 assert(0); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1486 } |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1487 else if (e1->op == TOKslice && t1->ty == Tarray && |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1488 e2->implicitConvTo(t1->nextOf())) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1489 { // T[] op T |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1490 e2 = e2->castTo(sc, t1->nextOf()); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1491 t = t1->nextOf()->arrayOf(); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1492 } |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1493 else if (e2->op == TOKslice && t2->ty == Tarray && |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1494 e1->implicitConvTo(t2->nextOf())) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1495 { // T op T[] |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1496 e1 = e1->castTo(sc, t2->nextOf()); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1497 t = t2->nextOf()->arrayOf(); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1498 |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1499 //printf("test %s\n", e->toChars()); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1500 e1 = e1->optimize(WANTvalue); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1501 if (isCommutative() && e1->isConst()) |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1502 { /* Swap operands to minimize number of functions generated |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1503 */ |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1504 //printf("swap %s\n", e->toChars()); |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1505 Expression *tmp = e1; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1506 e1 = e2; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1507 e2 = tmp; |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1508 } |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1509 } |
159 | 1510 else |
1511 { | |
1512 Lincompatible: | |
1513 incompatibleTypes(); | |
1514 } | |
1515 Lret: | |
1516 if (!type) | |
1517 type = t; | |
1518 //dump(0); | |
1519 return this; | |
1520 | |
1521 | |
1522 Lt1: | |
1523 e2 = e2->castTo(sc, t1); | |
1524 t = t1; | |
1525 goto Lret; | |
1526 | |
1527 Lt2: | |
1528 e1 = e1->castTo(sc, t2); | |
1529 t = t2; | |
1530 goto Lret; | |
1531 } | |
1532 | |
1533 /*********************************** | |
1534 * Do integral promotions (convertchk). | |
1535 * Don't convert <array of> to <pointer to> | |
1536 */ | |
1537 | |
1538 Expression *Expression::integralPromotions(Scope *sc) | |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1539 { |
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1540 Expression *e = this; |
159 | 1541 |
510
6aee82889553
Merged DMD 1.034, array operations are not yet implemented ;)
Tomas Lindquist Olsen <tomas.l.olsen@gmail.com>
parents:
336
diff
changeset
|
1542 //printf("integralPromotions %s %s\n", e->toChars(), e->type->toChars()); |
159 | 1543 switch (type->toBasetype()->ty) |
1544 { | |
1545 case Tvoid: | |
1546 error("void has no value"); | |
1547 break; | |
1548 | |
1549 case Tint8: | |
1550 case Tuns8: | |
1551 case Tint16: | |
1552 case Tuns16: | |
1553 case Tbit: | |
1554 case Tbool: | |
1555 case Tchar: | |
1556 case Twchar: | |
1557 e = e->castTo(sc, Type::tint32); | |
1558 break; | |
1559 | |
1560 case Tdchar: | |
1561 e = e->castTo(sc, Type::tuns32); | |
1562 break; | |
1563 } | |
1564 return e; | |
1565 } | |
1566 |