source: dev/trunk/abdev/BasicCompiler64/NumOpe_TypeOperation.cpp@ 266

Last change on this file since 266 was 266, checked in by dai_9181, 17 years ago

BasicSourceのシリアライズがうまくいっていない

File size: 12.9 KB
Line 
1#include "stdafx.h"
2
3#include <jenga/include/smoothie/Smoothie.h>
4
5#include <Compiler.h>
6
7#include "../BasicCompiler_Common/common.h"
8#include "Opcode.h"
9
10void ExtendTypeTo64(int type,int reg){
11 if(type==DEF_LONG){
12 //movsxd reg64,reg32
13 compiler.codeGenerator.op_movsxd(reg,reg);
14 }
15 else if(type==DEF_DWORD){
16 //and reg,00000000FFFFFFFFh
17 }
18 else if(type==DEF_INTEGER || (Smoothie::IsUnicode()&&type==DEF_CHAR)){
19 //movsx reg64,reg16
20 compiler.codeGenerator.op_movsx64_FromReg16(reg,reg);
21 }
22 else if(type==DEF_WORD){
23 //and reg,000000000000FFFFh
24 compiler.codeGenerator.op_and64_value(reg,(int)0xFFFF);
25 }
26 else if(type==DEF_SBYTE || (Smoothie::IsUnicode()==false&&type==DEF_CHAR)){
27 //movsx reg64,reg8
28 compiler.codeGenerator.op_movsx64_FromReg8(reg,reg);
29 }
30 else if(type==DEF_BYTE || type==DEF_BOOLEAN){
31 //and reg,00000000000000FFh
32 compiler.codeGenerator.op_and64_value(reg,(int)0x00FF);
33 }
34}
35void ExtendTypeTo32(int type,int reg){
36 if(type==DEF_INTEGER || (Smoothie::IsUnicode()&&type==DEF_CHAR)){
37 //movsx reg32,reg16
38 compiler.codeGenerator.op_movsx32_FromReg16(reg,reg);
39 }
40 else if(type==DEF_WORD){
41 //and reg,0000FFFFh
42 compiler.codeGenerator.op_and32_value(reg,(int)0xFFFF);
43 }
44 else if(type==DEF_SBYTE || (Smoothie::IsUnicode()==false&&type==DEF_CHAR)){
45 //movsx reg32,reg8
46 compiler.codeGenerator.op_movsx32_FromReg8(reg,reg);
47 }
48 else if(type==DEF_BYTE || type==DEF_BOOLEAN){
49 //and reg,000000FFh
50 compiler.codeGenerator.op_and32_value(reg,(int)0xFF);
51 }
52}
53void ExtendTypeTo16(int type,int reg){
54 if(type==DEF_SBYTE || (Smoothie::IsUnicode()==false&&type==DEF_CHAR)){
55 //movsx reg16,reg8
56 compiler.codeGenerator.op_movsx16_FromReg8(reg,reg);
57 }
58 else if(type==DEF_BYTE){
59 //and reg,000000FFh
60 compiler.codeGenerator.op_and32_value(reg,(int)0xFF);
61 }
62}
63
64void ChangeTypeToXmm_Double(int type,int xmm_reg,int general_reg){
65 if(type==DEF_DOUBLE){
66 //なにもしない
67 }
68 else if(type==DEF_SINGLE){
69 //Single型
70
71 //cvtss2sd
72 compiler.codeGenerator.op_cvtss2sd(xmm_reg,xmm_reg);
73 }
74 else if(Is64Type(type)){
75 //64ビット整数型
76
77 //cvtsi2sd xmm_reg,reg
78 compiler.codeGenerator.op_cvtsi2sd_reg(sizeof(_int64),xmm_reg,general_reg);
79
80 if(type==DEF_QWORD){
81 //符号なし
82
83 //test reg,reg
84 compiler.codeGenerator.op_test(general_reg,general_reg);
85
86 //jge 9
87 compiler.codeGenerator.op_jge( 9 );
88
89 //addsd xmm_reg,qword ptr[offset] ※offset value:43f0000000000000
90 _int64 i64data=0x43f0000000000000;
91 long temp=compiler.GetObjectModule().dataTable.Add( i64data );
92 compiler.codeGenerator.PutOld(
93 (char)0xF2,
94 (char)0x0F,
95 (char)0x58,
96 (char)(0x04 | REGISTER_OPERAND(xmm_reg)<<3),
97 (char)0x25
98 );
99 compiler.codeGenerator.PutOld(
100 temp,
101 Schedule::DataTable
102 );
103 }
104 }
105 else if(type==DEF_DWORD){
106 //符号なし32ビット値
107
108 //64ビットにレジスタ値を拡張
109 ExtendTypeTo64(type,general_reg);
110
111 //cvtsi2sd xmm_reg,reg
112 compiler.codeGenerator.op_cvtsi2sd_reg(sizeof(_int64),xmm_reg,general_reg);
113 }
114 else{
115 //その他整数
116
117 //32ビットにレジスタ値を拡張
118 ExtendTypeTo32(type,general_reg);
119
120 //cvtsi2sd xmm_reg,reg
121 compiler.codeGenerator.op_cvtsi2sd_reg(sizeof(long),xmm_reg,general_reg);
122 }
123}
124void ChangeTypeToXmm_Single(int type,int xmm_reg,int general_reg){
125 if(type==DEF_DOUBLE){
126 //Double型
127
128 //cvtsd2ss
129 compiler.codeGenerator.op_cvtsd2ss(xmm_reg,xmm_reg);
130 }
131 else if(type==DEF_SINGLE){
132 //なにもしない
133 }
134 else if(Is64Type(type)){
135 //64ビット整数型
136
137 //cvtsi2ss xmm_reg,reg
138 compiler.codeGenerator.op_cvtsi2ss_reg(sizeof(_int64),xmm_reg,general_reg);
139
140 if(type==DEF_QWORD){
141 //符号なし
142
143 //test reg,reg
144 compiler.codeGenerator.op_test(general_reg,general_reg);
145
146 //jge 9
147 compiler.codeGenerator.op_jge( 9 );
148
149 //addss xmm_reg,dword ptr[offset] ※offset value:5f800000
150 long i32data=0x5f800000;
151 long temp=compiler.GetObjectModule().dataTable.Add( i32data );
152 compiler.codeGenerator.PutOld(
153 (char)0xF3,
154 (char)0x0F,
155 (char)0x58,
156 (char)(0x04 | REGISTER_OPERAND(xmm_reg)<<3),
157 (char)0x25
158 );
159 compiler.codeGenerator.PutOld(
160 temp,
161 Schedule::DataTable
162 );
163 }
164 }
165 else if(type==DEF_DWORD){
166 //符号なし32ビット値
167
168 //64ビットにレジスタ値を拡張
169 ExtendTypeTo64(type,general_reg);
170
171 //cvtsi2ss xmm_reg,reg
172 compiler.codeGenerator.op_cvtsi2ss_reg(sizeof(_int64),xmm_reg,general_reg);
173 }
174 else{
175 //その他整数
176
177 //32ビットにレジスタ値を拡張
178 ExtendTypeTo32(type,general_reg);
179
180 //cvtsi2ss xmm_reg,reg
181 compiler.codeGenerator.op_cvtsi2ss_reg(sizeof(long),xmm_reg,general_reg);
182 }
183}
184
185void ChangeTypeToWhole(int OldType,int NewType,int reg,int xmm_reg){
186 if(OldType==DEF_DOUBLE){
187 if(Is64Type(NewType)){
188 //cvttsd2si reg,xmm_reg
189 compiler.codeGenerator.op_cvttsd2si_xmm(sizeof(_int64),reg,xmm_reg);
190 }
191 else{
192 //cvttsd2si reg,xmm_reg
193 compiler.codeGenerator.op_cvttsd2si_xmm(sizeof(long),reg,xmm_reg);
194 }
195 }
196 else if(OldType==DEF_SINGLE){
197 if(Is64Type(NewType)){
198 //cvttss2si reg,xmm_reg
199 compiler.codeGenerator.op_cvttss2si_xmm(sizeof(_int64),reg,xmm_reg);
200 }
201 else{
202 //cvttss2si reg,xmm_reg
203 compiler.codeGenerator.op_cvttss2si_xmm(sizeof(long),reg,xmm_reg);
204 }
205 }
206 else{
207 //整数から整数へ変換
208
209 if(Is64Type(NewType)){
210 ExtendTypeTo64(OldType,reg);
211 }
212 else if(GetTypeSize(NewType,-1)==sizeof(long)){
213 ExtendTypeTo32(OldType,reg);
214 }
215 else if(GetTypeSize(NewType,-1)==sizeof(short)){
216 ExtendTypeTo16(OldType,reg);
217 }
218 }
219}
220
221
222
223/////////////////////////////////////////
224// 1つの項を適切なレジスタへセット
225/////////////////////////////////////////
226
227void SetOneTermToReg_RealCalc(int TermType,int *pXmmReg){
228 int xmm_reg;
229
230 if(IsRealNumberType(TermType)){
231 //実数型
232 xmm_reg=pobj_reg->GetLockingXmmReg();
233
234 if(xmm_reg==REG_XMM4){
235 if(TermType==DEF_DOUBLE){
236 //movlpd xmm4,qword ptr[rsp+offset] ※スタックフレームを利用
237 pobj_sf->pop(xmm_reg,sizeof(double));
238 }
239 if(TermType==DEF_SINGLE){
240 //movss xmm4,dword ptr[rsp+offset] ※スタックフレームを利用
241 pobj_sf->pop(xmm_reg,sizeof(float));
242 }
243 }
244 }
245 else{
246 SetError(300,NULL,cp);
247 }
248
249 *pXmmReg=xmm_reg;
250}
251void SetOneTermToReg_Whole64Calc(int TermType,int *pReg){
252 //1つの項を適切なレジスタへセット(64ビット整数演算用)
253 int reg;
254
255 reg=pobj_reg->GetLockingReg();
256
257 if(reg==REG_R14){
258 //mov r14,qword ptr[rsp+offset] ※スタックフレームを利用
259 pobj_sf->pop(REG_R14);
260 }
261
262 //レジスタ値を64ビットに拡張
263 ExtendTypeTo64(TermType,reg);
264
265 *pReg=reg;
266}
267void SetOneTermToReg_Whole32Calc(int TermType,int *pReg){
268 //1つの項を適切なレジスタへセット(32ビット整数演算用)
269 int reg;
270
271 reg=pobj_reg->GetLockingReg();
272
273 if(reg==REG_R14){
274 //mov r14,qword ptr[rsp+offset] ※スタックフレームを利用
275 pobj_sf->pop(REG_R14);
276 }
277
278 //レジスタ値を32ビットに拡張
279 ExtendTypeTo32(TermType,reg);
280
281 *pReg=reg;
282}
283
284
285
286/////////////////////////////////////////
287// 2つの項を適切なレジスタへセット
288/////////////////////////////////////////
289
290void SetTowTermToReg_RealCalc(int AnswerType,int *type,int sp,int *pXmmReg1,int *pXmmReg2){
291 //2つの項を適切なレジスタへセット(Double演算用)
292 int xmm_reg1,xmm_reg2,temp_reg;
293
294
295 ///////////////////
296 // 第2項
297 ///////////////////
298
299 if(IsRealNumberType(type[sp-1])){
300 //実数型
301 xmm_reg2=pobj_reg->UnlockXmmReg();
302
303 if(xmm_reg2==REG_XMM4){
304 xmm_reg2=REG_XMM5;
305
306 if(type[sp-1]==DEF_DOUBLE){
307 //movlpd xmm5,qword ptr[rsp+offset] ※スタックフレームを利用
308 pobj_sf->pop(xmm_reg2,sizeof(double));
309 }
310 if(type[sp-1]==DEF_SINGLE){
311 //movss xmm5,dword ptr[rsp+offset] ※スタックフレームを利用
312 pobj_sf->pop(xmm_reg2,sizeof(float));
313 }
314 }
315 else{
316 if(!IsRealNumberType(type[sp-2])){
317 if(type[sp-1]==DEF_DOUBLE){
318 //movsd xmm5,xmm_reg
319 compiler.codeGenerator.op_movsd_RR( REG_XMM5, xmm_reg2 );
320 }
321 if(type[sp-1]==DEF_SINGLE){
322 //movss xmm5,xmm_reg
323 compiler.codeGenerator.op_movss_RR( REG_XMM5, xmm_reg2 );
324 }
325
326 xmm_reg2=REG_XMM5;
327 }
328 }
329 }
330 else{
331 //整数値
332
333 temp_reg=pobj_reg->UnlockReg();
334
335 if(temp_reg==REG_R14){
336 //mov r14,qword ptr[rsp+offset] ※スタックフレームを利用
337 pobj_sf->pop(REG_R14);
338 }
339
340 xmm_reg2=REG_XMM5;
341 }
342
343 //汎用レジスタ(temp_reg)をXMMレジスタ(xmm_reg2)にコピー
344 if(AnswerType==DEF_DOUBLE)
345 ChangeTypeToXmm_Double(type[sp-1],xmm_reg2,temp_reg);
346 if(AnswerType==DEF_SINGLE)
347 ChangeTypeToXmm_Single(type[sp-1],xmm_reg2,temp_reg);
348
349
350 ///////////////////
351 // 第1項
352 ///////////////////
353
354 if(IsRealNumberType(type[sp-2])){
355 //実数
356 xmm_reg1=pobj_reg->GetLockingXmmReg();
357
358 if(xmm_reg1==REG_XMM4){
359 if(type[sp-2]==DEF_DOUBLE){
360 //movlpd xmm4,qword ptr[rsp+offset] ※スタックフレームを利用
361 pobj_sf->pop(xmm_reg1,sizeof(double));
362 }
363 if(type[sp-2]==DEF_SINGLE){
364 //movss xmm4,dword ptr[rsp+offset] ※スタックフレームを利用
365 pobj_sf->pop(xmm_reg1,sizeof(float));
366 }
367 }
368 }
369 else{
370 //整数
371
372 temp_reg=pobj_reg->UnlockReg();
373
374 if(temp_reg==REG_R14){
375 //mov r14,qword ptr[rsp+offset] ※スタックフレームを利用
376 pobj_sf->pop(REG_R14);
377 }
378
379 xmm_reg1=pobj_reg->LockXmmReg();
380 }
381
382 //汎用レジスタ(temp_reg)をXMMレジスタ(xmm_reg1)にコピー
383 if(AnswerType==DEF_DOUBLE)
384 ChangeTypeToXmm_Double(type[sp-2],xmm_reg1,temp_reg);
385 if(AnswerType==DEF_SINGLE)
386 ChangeTypeToXmm_Single(type[sp-2],xmm_reg1,temp_reg);
387
388
389 *pXmmReg1=xmm_reg1;
390 *pXmmReg2=xmm_reg2;
391}
392void SetTowTermToReg_Whole64Calc(int *type,int sp,int *pReg1,int *pReg2){
393 //2つの項を適切なレジスタへセット(64ビット整数演算用)
394 int reg1,reg2;
395
396 //////////////////
397 // 第2項
398 //////////////////
399 reg2=pobj_reg->UnlockReg();
400
401 if(reg2==REG_R14){
402 //mov r15,qword ptr[rsp+offset] ※スタックフレームを利用
403 pobj_sf->pop(REG_R15);
404
405 reg2=REG_R15;
406 }
407
408 //レジスタ値を64ビットに拡張
409 ExtendTypeTo64(type[sp-1],reg2);
410
411
412 //////////////////
413 // 第1項
414 //////////////////
415 reg1=pobj_reg->GetLockingReg();
416
417 if(reg1==REG_R14){
418 //mov r14,qword ptr[rsp+offset] ※スタックフレームを利用
419 pobj_sf->pop(REG_R14);
420 }
421
422 //レジスタ値を64ビットに拡張
423 ExtendTypeTo64(type[sp-2],reg1);
424
425
426 *pReg1=reg1;
427 *pReg2=reg2;
428}
429void SetTowTermToReg_Whole32Calc(int *type,int sp,int *pReg1,int *pReg2){
430 //2つの項を適切なレジスタへセット(32ビット整数演算用)
431 int reg1,reg2;
432
433 //////////////////
434 // 第2項
435 //////////////////
436 reg2=pobj_reg->UnlockReg();
437
438 if(reg2==REG_R14){
439 //mov r15,qword ptr[rsp+offset] ※スタックフレームを利用
440 pobj_sf->pop(REG_R15);
441
442 reg2=REG_R15;
443 }
444
445 //レジスタ値を32ビットに拡張
446 ExtendTypeTo32(type[sp-1],reg2);
447
448
449 //////////////////
450 // 第1項
451 //////////////////
452 reg1=pobj_reg->GetLockingReg();
453
454 if(reg1==REG_R14){
455 //mov r14,qword ptr[rsp+offset] ※スタックフレームを利用
456 pobj_sf->pop(REG_R14);
457 }
458
459 //レジスタ値を32ビットに拡張
460 ExtendTypeTo32(type[sp-2],reg1);
461
462
463 *pReg1=reg1;
464 *pReg2=reg2;
465}
466
467
468
469////////////////////////////
470// As 演算子によるキャスト
471////////////////////////////
472
473BOOL Calc_Cast(int *type,LONG_PTR *index_stack,int *pStackPointer){
474 //キャスト
475
476 int sp;
477 sp=*pStackPointer;
478
479 int CastType;
480 CastType=type[sp-1];
481 if((CastType&FLAG_CAST)==0){
482 SetError(47,NULL,cp);
483 return 0;
484 }
485 CastType=CastType&(~FLAG_CAST);
486
487 int xmm_reg,reg;
488
489 if(IsRealNumberType(CastType)){
490 //実数型へキャスト
491
492 if(IsRealNumberType(type[sp-2])){
493 SetOneTermToReg_RealCalc(type[sp-2],&xmm_reg);
494 }
495 else{
496 if(Is64Type(type[sp-2]))
497 SetOneTermToReg_Whole64Calc(type[sp-2],&reg);
498 else if(IsWholeNumberType(type[sp-2]))
499 SetOneTermToReg_Whole32Calc(type[sp-2],&reg);
500
501 pobj_reg->UnlockReg();
502
503 xmm_reg=pobj_reg->LockXmmReg();
504 }
505
506 if(CastType==DEF_DOUBLE){
507 //Double型にデータ変換
508 ChangeTypeToXmm_Double(type[sp-2],xmm_reg,reg);
509 }
510 else if(CastType==DEF_SINGLE){
511 //Single型にデータ変換
512 ChangeTypeToXmm_Single(type[sp-2],xmm_reg,reg);
513 }
514
515 if(xmm_reg==REG_XMM4){
516 //movsd qword ptr[rsp+offset],xmm4 ※スタックフレームを利用
517 pobj_sf->push(REG_XMM4,sizeof(double));
518 }
519 }
520 else{
521 //その他整数型へ変換
522
523 if(IsRealNumberType(type[sp-2])){
524 SetOneTermToReg_RealCalc(type[sp-2],&xmm_reg);
525
526 pobj_reg->UnlockXmmReg();
527
528 reg=pobj_reg->LockReg();
529
530 //整数型へデータ変換
531 ChangeTypeToWhole(type[sp-2],CastType,reg,xmm_reg);
532
533 if(reg==REG_R14){
534 //mov qword ptr[rsp+offset],r14 ※スタックフレームを利用
535 pobj_sf->push(REG_R14);
536 }
537 }
538 else{
539 reg=pobj_reg->GetLockingReg();
540
541 if(reg==REG_R14){
542 //mov r14,qword ptr[rsp+offset] ※スタックフレームを利用
543 pobj_sf->pop(REG_R14);
544 }
545
546 //整数型へデータ変換
547 ChangeTypeToWhole(type[sp-2],CastType,reg,0);
548
549 if(reg==REG_R14){
550 //mov qword ptr[rsp+offset],r14 ※スタックフレームを利用
551 pobj_sf->push(REG_R14);
552 }
553 }
554 }
555
556 type[sp-2]=CastType;
557 index_stack[sp-2]=index_stack[sp-1];
558
559 sp--;
560
561 *pStackPointer=sp;
562 return 1;
563}
Note: See TracBrowser for help on using the repository browser.