source: dev/trunk/abdev/BasicCompiler_Common/src/CommonCodeGenerator.cpp@ 250

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

Selectステートメントのスケジュール機構をリファクタリング

File size: 6.7 KB
Line 
1#include "stdafx.h"
2
3#include <CodeGenerator.h>
4
5
6void CodeGenerator::ResolveExitSubSchedule()
7{
8 BOOST_FOREACH( long exitSubCodePosition, exitSubCodePositions )
9 {
10 pNativeCode->Overwrite( exitSubCodePosition, (long)( pNativeCode->GetSize()-(exitSubCodePosition+sizeof(long)) ) );
11 }
12
13 // TODO: 未完成
14 BOOST_FOREACH( long exitSubCodePositionOld, _exitSubCodePositions_ObpOld )
15 {
16 extern int obp;
17 pNativeCode->OverwriteOld( exitSubCodePositionOld, (long)( obp-(exitSubCodePositionOld+sizeof(long)) ) );
18 }
19}
20
21void CodeGenerator::CheckUnresolveSchedule()
22{
23 if( pertialSchedules.size() > 0 )
24 {
25 SetError();
26 }
27}
28
29
30// 分岐関連
31void CodeGenerator::opfix_JmpPertialSchedule( const PertialSchedule *pPertialSchedule )
32{
33 bool isSuccessful = false;
34
35 PertialSchedules::iterator it = pertialSchedules.begin();
36 while( it != pertialSchedules.end() )
37 {
38 if( (*it) == pPertialSchedule )
39 {
40 long newValue = pNativeCode->GetSize() - (pPertialSchedule->GetCodePos()+pPertialSchedule->GetTypeSize());
41
42 extern int obp;
43 long newValueOld = obp - (pPertialSchedule->GetObpOld()+pPertialSchedule->GetTypeSize());
44
45 if( pPertialSchedule->GetTypeSize() == sizeof(char) )
46 {
47 if( newValue < -128 || 127 < newValue )
48 {
49 // 範囲外
50 SetError();
51 }
52
53 pNativeCode->Overwrite( pPertialSchedule->GetCodePos(), (char)newValue );
54
55 // TODO: 未完成(用が無くなったら消す)
56 pNativeCode->OverwriteOld( pPertialSchedule->GetObpOld(), (char)newValueOld );
57 }
58 else if( pPertialSchedule->GetTypeSize() == sizeof(long) )
59 {
60 pNativeCode->Overwrite( pPertialSchedule->GetCodePos(), newValue );
61
62 // TODO: 未完成(用が無くなったら消す)
63 pNativeCode->OverwriteOld( pPertialSchedule->GetObpOld(), newValueOld );
64 }
65 else
66 {
67 SetError();
68 }
69
70 it = pertialSchedules.erase( it );
71 delete pPertialSchedule;
72
73 isSuccessful = true;
74 }
75 else
76 {
77 it++;
78 }
79 }
80
81 if( isSuccessful == false )
82 {
83 SetError();
84 }
85}
86const PertialSchedule *CodeGenerator::__jmp_op_format( char opcode, long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
87{
88 long beginCodePos = pNativeCode->GetSize();
89 {
90 // TODO: 未完成
91 extern int obp;
92 beginCodePos = obp;
93 }
94
95 if( opcode == (char)0xEB )
96 {
97 // jmp命令のとき
98 if( op_size == sizeof(char) )
99 {
100 pNativeCode->Put( (char)opcode );
101 }
102 else if( op_size == sizeof(long) )
103 {
104 pNativeCode->Put( (char)0xE9 );
105 }
106 else
107 {
108 SetError();
109 }
110 }
111 else
112 {
113 if( op_size == sizeof(char) )
114 {
115 pNativeCode->Put( (char)((char)0x70 | opcode) );
116 }
117 else if( op_size == sizeof(long) )
118 {
119 pNativeCode->Put( (char)0x0F );
120 pNativeCode->Put( (char)((char)0x80 | opcode) );
121 }
122 else
123 {
124 SetError();
125 }
126 }
127
128 const PertialSchedule *pPertialSchedule = NULL;
129 if( isPertialSchedule )
130 {
131 pertialSchedules.push_back( new PertialSchedule( pNativeCode->GetSize(), op_size ) );
132 pPertialSchedule = pertialSchedules[pertialSchedules.size()-1];
133 }
134
135 if( isSelfOpcodeOffset )
136 {
137 // 自分自身の命令サイズを考慮する場合
138 //offset += ( pNativeCode->GetSize() - beginCodePos ) + op_size;
139
140 // TODO: 未完成
141 extern int obp;
142 offset -= ( obp - beginCodePos ) + op_size;
143 }
144
145 if( op_size == sizeof(char) )
146 {
147 pNativeCode->Put( (char)offset );
148 }
149 else if( op_size == sizeof(long) )
150 {
151 pNativeCode->Put( offset );
152 }
153 else
154 {
155 SetError();
156 }
157
158 return pPertialSchedule;
159}
160const PertialSchedule *CodeGenerator::op_jle( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
161{
162 return __jmp_op_format( (char)0x0E, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
163}
164const PertialSchedule *CodeGenerator::op_jbe( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
165{
166 return __jmp_op_format( (char)0x06, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
167}
168const PertialSchedule *CodeGenerator::op_jge( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
169{
170 return __jmp_op_format( (char)0x0D, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
171}
172const PertialSchedule *CodeGenerator::op_jae( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
173{
174 return __jmp_op_format( (char)0x03, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
175}
176const PertialSchedule *CodeGenerator::op_jl( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
177{
178 return __jmp_op_format( (char)0x0C, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
179}
180const PertialSchedule *CodeGenerator::op_jb( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
181{
182 return __jmp_op_format( (char)0x02, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
183}
184const PertialSchedule *CodeGenerator::op_jg( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
185{
186 return __jmp_op_format( (char)0x0F, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
187}
188const PertialSchedule *CodeGenerator::op_ja( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
189{
190 return __jmp_op_format( (char)0x07, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
191}
192const PertialSchedule *CodeGenerator::op_jne( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
193{
194 return __jmp_op_format( (char)0x05, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
195}
196const PertialSchedule *CodeGenerator::op_je( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
197{
198 return __jmp_op_format( (char)0x04, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
199}
200const PertialSchedule *CodeGenerator::op_jmp( long offset, int op_size, bool isPertialSchedule, bool isSelfOpcodeOffset )
201{
202 return __jmp_op_format( (char)0xEB, offset, op_size, isPertialSchedule, isSelfOpcodeOffset );
203}
204void CodeGenerator::op_jmp_continue()
205{
206 //op_jmp( GetContinueCodePos()-(pNativeCode->GetSize()+sizeof(long)), sizeof(long) );
207
208 // TODO: 未完成(OpBuffer/obp廃止が整ったら上記のコードを有効にすべし)
209
210 if( GetContinueCodePosOld() == -1 )
211 {
212 SetError(12,"Continue",cp);
213 return;
214 }
215
216 extern int obp;
217 op_jmp( GetContinueCodePosOld()-obp, sizeof(long), false, true );
218}
219void CodeGenerator::op_jmp_exitsub()
220{
221 // オペコード
222 pNativeCode->Put( (char)0xE9 );
223
224 exitSubCodePositions.push_back( pNativeCode->GetSize() );
225
226 extern int obp;
227 _exitSubCodePositions_ObpOld.push_back( obp );
228
229 pNativeCode->Put( (long)0 );
230}
231void CodeGenerator::op_jmp_goto_schedule( const GotoLabelSchedule &gotoLabelSchedule )
232{
233 // オペコード
234 pNativeCode->Put( (char)0xE9 );
235
236 gotoLabelSchedules.push_back( gotoLabelSchedule );
237
238 pNativeCode->Put( (long)0 );
239}
Note: See TracBrowser for help on using the repository browser.