Mercurial > projects > ddmd
annotate dmd/ComplexExp.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 |
rev | line source |
---|---|
72 | 1 module dmd.ComplexExp; |
2 | |
114 | 3 import dmd.common; |
72 | 4 import dmd.Expression; |
5 import dmd.InterState; | |
6 import dmd.Type; | |
7 import dmd.OutBuffer; | |
8 import dmd.Loc; | |
9 import dmd.Scope; | |
10 import dmd.IRState; | |
11 import dmd.HdrGenState; | |
0 | 12 import dmd.Type; |
13 import dmd.TOK; | |
14 import dmd.TY; | |
15 import dmd.Port; | |
16 import dmd.Complex; | |
129 | 17 import dmd.expression.Util; |
72 | 18 |
19 import dmd.backend.dt_t; | |
0 | 20 import dmd.backend.elem; |
21 import dmd.backend.Util; | |
22 import dmd.backend.TYM; | |
23 import dmd.backend.mTY; | |
72 | 24 |
187
b0d41ff5e0df
Added expandability scheme outlined in http://www.dsource.org/forums/viewtopic.php?t=5659&sid=6f2150ff5b0bffcd47512a6a7608d218
Abscissa
parents:
178
diff
changeset
|
25 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
|
26 |
0 | 27 class ComplexExp : Expression |
28 { | |
187
b0d41ff5e0df
Added expandability scheme outlined in http://www.dsource.org/forums/viewtopic.php?t=5659&sid=6f2150ff5b0bffcd47512a6a7608d218
Abscissa
parents:
178
diff
changeset
|
29 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
|
30 |
0 | 31 Complex!(real) value; |
32 | |
33 this(Loc loc, Complex!(real) value, Type type) | |
72 | 34 { |
178 | 35 register(); |
0 | 36 super(loc, TOK.TOKcomplex80, ComplexExp.sizeof); |
37 this.value = value; | |
38 this.type = type; | |
39 //printf("ComplexExp.ComplexExp(%s)\n", toChars()); | |
40 } | |
41 | |
72 | 42 override bool equals(Object o) |
0 | 43 { |
44 assert(false); | |
45 } | |
46 | |
72 | 47 override Expression semantic(Scope sc) |
0 | 48 { |
49 if (!type) | |
50 type = Type.tcomplex80; | |
51 else | |
52 type = type.semantic(loc, sc); | |
53 return this; | |
54 } | |
55 | |
72 | 56 override Expression interpret(InterState istate) |
0 | 57 { |
58 assert(false); | |
59 } | |
60 | |
72 | 61 override string toChars() |
0 | 62 { |
63 assert(false); | |
64 } | |
65 | |
72 | 66 override ulong toInteger() |
0 | 67 { |
68 return cast(ulong) toReal(); | |
69 } | |
70 | |
72 | 71 override ulong toUInteger() |
0 | 72 { |
73 return cast(long) toReal(); | |
74 } | |
75 | |
72 | 76 override real toReal() |
0 | 77 { |
78 return value.re; | |
79 } | |
80 | |
72 | 81 override real toImaginary() |
0 | 82 { |
83 return value.im; | |
84 } | |
85 | |
72 | 86 override Complex!(real) toComplex() |
0 | 87 { |
88 return value; | |
89 } | |
90 | |
72 | 91 override Expression castTo(Scope sc, Type t) |
0 | 92 { |
93 Expression e = this; | |
94 if (type != t) | |
95 { | |
96 if (type.iscomplex() && t.iscomplex()) | |
174 | 97 { |
0 | 98 e = copy(); |
99 e.type = t; | |
100 } | |
101 else | |
102 e = Expression.castTo(sc, t); | |
103 } | |
104 return e; | |
105 } | |
106 | |
72 | 107 override int isConst() |
0 | 108 { |
53 | 109 return 1; |
0 | 110 } |
111 | |
72 | 112 override bool isBool(bool result) |
0 | 113 { |
123 | 114 if (result) |
115 return value != Complex!(real).zero; | |
116 else | |
117 return value == Complex!(real).zero; | |
0 | 118 } |
119 | |
72 | 120 override void toCBuffer(OutBuffer buf, HdrGenState* hgs) |
0 | 121 { |
174 | 122 /* Print as: |
123 * (re+imi) | |
124 */ | |
125 version (IN_GCC) { | |
126 char buf1[sizeof(value) * 3 + 8 + 1]; | |
127 char buf2[sizeof(value) * 3 + 8 + 1]; | |
128 creall(value).format(buf1, sizeof(buf1)); | |
129 cimagl(value).format(buf2, sizeof(buf2)); | |
130 buf.printf("(%s+%si)", buf1, buf2); | |
131 } else { | |
132 buf.writeByte('('); | |
133 floatToBuffer(buf, type, value.re); | |
134 buf.writeByte('+'); | |
135 floatToBuffer(buf, type, value.im); | |
136 buf.writestring("i)"); | |
137 } | |
0 | 138 } |
139 | |
72 | 140 override void toMangleBuffer(OutBuffer buf) |
0 | 141 { |
129 | 142 buf.writeByte('c'); |
143 real r = toReal(); | |
144 realToMangleBuffer(buf, r); | |
145 buf.writeByte('c'); // separate the two | |
146 r = toImaginary(); | |
147 realToMangleBuffer(buf, r); | |
0 | 148 } |
174 | 149 |
0 | 150 version (_DH) { |
151 OutBuffer hexp; | |
152 } | |
153 | |
72 | 154 override elem* toElem(IRState* irs) |
0 | 155 { |
156 eve c; | |
157 tym_t ty; | |
158 | |
159 //printf("ComplexExp.toElem(%p) %s\n", this, toChars()); | |
160 | |
161 ///memset(&c, 0, c.sizeof); | |
162 | |
163 ty = type.totym(); | |
164 switch (tybasic(ty)) | |
165 { | |
166 case TYcfloat: | |
167 { | |
168 c.Vcfloat.re = cast(float) value.re; | |
169 if (Port.isSignallingNan(value.re)) { | |
170 (cast(uint*)&c.Vcfloat.re)[0] &= 0xFFBFFFFFL; | |
171 std.stdio.writeln("float.re is snan"); | |
172 } | |
173 c.Vcfloat.im = cast(float) value.im; | |
174 if (Port.isSignallingNan(value.im)) { | |
175 (cast(uint*)&c.Vcfloat.im)[0] &= 0xFFBFFFFFL; | |
176 std.stdio.writeln("float.im is snan"); | |
177 } | |
178 break; | |
179 } | |
180 | |
181 case TYcdouble: | |
182 { | |
183 c.Vcdouble.re = cast(double) value.re; | |
184 if (Port.isSignallingNan(value.re)) { | |
185 std.stdio.writeln("double.re is snan"); | |
186 (cast(uint*)&c.Vcdouble.re)[1] &= 0xFFF7FFFFL; | |
187 } | |
188 c.Vcdouble.im = cast(double) value.im; | |
189 if (Port.isSignallingNan(value.im)) { | |
190 (cast(uint*)&c.Vcdouble.im)[1] &= 0xFFF7FFFFL; | |
191 std.stdio.writeln("double.im is snan"); | |
192 } | |
193 break; | |
194 } | |
195 | |
196 case TYcldouble: | |
197 { | |
198 static if (true) { | |
199 c.Vcldouble = value; | |
200 } else { | |
201 { | |
202 ushort* p = cast(ushort*)&c.Vcldouble; | |
203 for (int i = 0; i < (LNGDBLSIZE*2)/2; i++) printf("%04x ", p[i]); | |
204 printf("\n"); | |
205 } | |
206 c.Vcldouble.im = im; | |
207 { | |
208 ushort* p = cast(ushort*)&c.Vcldouble; | |
209 for (int i = 0; i < (LNGDBLSIZE*2)/2; i++) printf("%04x ", p[i]); | |
210 printf("\n"); | |
211 } | |
212 c.Vcldouble.re = re; | |
213 { | |
214 ushort* p = cast(ushort*)&c.Vcldouble; | |
215 for (int i = 0; i < (LNGDBLSIZE*2)/2; i++) printf("%04x ", p[i]); | |
216 printf("\n"); | |
217 } | |
218 } | |
219 break; | |
220 } | |
221 | |
222 default: | |
223 assert(0); | |
224 } | |
225 return el_const(ty, &c); | |
226 } | |
174 | 227 |
175 | 228 static private __gshared char[6] zeropad; |
0 | 229 |
72 | 230 override dt_t** toDt(dt_t** pdt) |
0 | 231 { |
232 //printf("ComplexExp.toDt() '%s'\n", toChars()); | |
233 float fvalue; | |
234 double dvalue; | |
235 real evalue; | |
236 | |
237 switch (type.toBasetype().ty) | |
238 { | |
239 case Tcomplex32: | |
240 fvalue = value.re; | |
241 pdt = dtnbytes(pdt,4,cast(char*)&fvalue); | |
242 fvalue = value.im; | |
243 pdt = dtnbytes(pdt,4,cast(char*)&fvalue); | |
244 break; | |
245 | |
246 case Tcomplex64: | |
247 dvalue = value.re; | |
248 pdt = dtnbytes(pdt,8,cast(char*)&dvalue); | |
249 dvalue = value.im; | |
250 pdt = dtnbytes(pdt,8,cast(char*)&dvalue); | |
251 break; | |
252 | |
253 case Tcomplex80: | |
254 evalue = value.re; | |
255 pdt = dtnbytes(pdt,REALSIZE - REALPAD,cast(char*)&evalue); | |
256 pdt = dtnbytes(pdt,REALPAD,zeropad.ptr); | |
257 evalue = value.im; | |
258 pdt = dtnbytes(pdt,REALSIZE - REALPAD, cast(char*)&evalue); | |
259 pdt = dtnbytes(pdt,REALPAD,zeropad.ptr); | |
260 break; | |
261 | |
262 default: | |
263 assert(0); | |
264 break; | |
265 } | |
266 return pdt; | |
267 } | |
268 } | |
269 |