source: dev/trunk/abdev/BasicCompiler_Common/DebugMiddleFile.cpp@ 279

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

sourceをObjectModuleに入れた

File size: 9.8 KB
Line 
1#include "stdafx.h"
2
3#include <jenga/include/smoothie/Smoothie.h>
4
5#include <Compiler.h>
6#include <Class.h>
7#include <Variable.h>
8
9#include "../BasicCompiler_Common/common.h"
10#include "../BasicCompiler_Common/DebugSection.h"
11
12#ifdef _AMD64_
13#include "../BasicCompiler64/opcode.h"
14#else
15#include "../BasicCompiler32/opcode.h"
16#endif
17
18#define MDLFILE_VER 0x70000003
19
20
21void SetLpIndex_DebugFile(char *buffer,int *p,const Type &type){
22 if(NATURAL_TYPE(type.GetBasicType())==DEF_OBJECT || NATURAL_TYPE(type.GetBasicType())==DEF_STRUCT){
23 lstrcpy(buffer+(*p),type.GetClass().GetName().c_str());
24 (*p)+=lstrlen(buffer+(*p))+1;
25 }
26 else{
27 *(LONG_PTR *)(buffer+(*p))=type.GetIndex();
28 (*p)+=sizeof(LONG_PTR);
29 }
30}
31
32
33void GetLpIndex_DebugFile(char *buffer,int *p,Type &type){
34 if(NATURAL_TYPE(type.GetBasicType())==DEF_OBJECT || NATURAL_TYPE(type.GetBasicType())==DEF_STRUCT){
35 char szClassName[VN_SIZE];
36 lstrcpy(szClassName,buffer+(*p));
37 (*p)+=lstrlen(buffer+(*p))+1;
38
39 type.SetClassPtr( compiler.GetObjectModule().meta.GetClasses().Find(szClassName) );
40 }
41 else{
42 type.SetIndex( *(LONG_PTR *)(buffer+(*p)) );
43 (*p)+=sizeof(LONG_PTR);
44 }
45}
46
47
48
49CDebugSection::~CDebugSection(){
50 if(dwImageBase) DeleteDebugInfo();
51 if(buffer){
52 HeapDefaultFree(buffer);
53 buffer=0;
54 }
55}
56void CDebugSection::make(void){
57 int i2,BufferSize;
58
59 if(buffer){
60 HeapDefaultFree(buffer);
61 buffer=0;
62 }
63
64 i2=0;
65
66 extern char *basbuf;
67 BufferSize=lstrlen(basbuf)+65535;
68 buffer=(char *)HeapAlloc(hHeap,0,BufferSize);
69
70 //デバッグ用ファイルのバージョン
71 *(long *)(buffer+i2)=MDLFILE_VER;
72 i2+=sizeof(long);
73
74 //プラットフォームのビット数
75 *(long *)(buffer+i2)=PLATFORM;
76 i2+=sizeof(long);
77
78
79 // オブジェクトモジュール
80 {
81 // テキストデータにシリアライズ
82 std::string textString;
83 compiler.GetObjectModule().WriteString( textString );
84
85 // サイズ
86 *(long *)(buffer+i2) = (long)textString.size();
87 i2+=sizeof(long);
88
89 //バッファが足りない場合は再確保
90 if(BufferSize<i2+(int)textString.size()+32768){
91 while( BufferSize<i2+(int)textString.size()+32768 )
92 {
93 BufferSize+=32768;
94 }
95
96 buffer=(char *)HeapReAlloc(hHeap,0,buffer,BufferSize);
97 }
98
99 // バッファ
100 memcpy( buffer+i2, textString.c_str(), textString.size() );
101 i2 += (int)textString.size();
102 }
103
104
105 ////////////////////////
106 // コードと行番号の関係
107 ////////////////////////
108 extern SourceLines oldSourceLines;
109
110 *(long *)(buffer+i2)=(long)oldSourceLines.size();
111 i2+=sizeof(long);
112 BOOST_FOREACH( const SourceLine &sourceLine, oldSourceLines )
113 {
114 *(long *)(buffer+i2) = sourceLine.GetLineNum();
115 i2+=sizeof(long);
116
117 *(long *)(buffer+i2) = sourceLine.GetNativeCodePos();
118 i2+=sizeof(long);
119
120 *(long *)(buffer+i2) = sourceLine.GetSourceCodePos();
121 i2+=sizeof(long);
122
123 *(long *)(buffer+i2) = sourceLine.GetCodeType();
124 i2+=sizeof(long);
125
126 //バッファが足りない場合は再確保
127 if(BufferSize<i2+32768){
128 BufferSize+=32768;
129 buffer=(char *)HeapReAlloc(hHeap,0,buffer,BufferSize);
130 }
131 }
132
133 //グローバル実行領域のサイズ
134 extern int GlobalOpBufferSize;
135 *(long *)(buffer+i2)=GlobalOpBufferSize;
136 i2+=sizeof(long);
137
138 length=i2;
139}
140
141char *CDebugSection::MakeSingleStepCode(void){
142 char *buffer;
143 buffer=(char *)HeapAlloc(hHeap,0,SizeOf_CodeSection);
144
145 memcpy(buffer,OpBuffer,SizeOf_CodeSection);
146
147 BOOST_FOREACH( const SourceLine &sourceLine, _oldSourceLines )
148 {
149 if(!(
150 sourceLine.IsInSystemProc()
151 || sourceLine.IsInDebugProc() ) )
152 {
153 //int 3
154 buffer[sourceLine.GetNativeCodePos()]=(char)0xCC;
155 }
156 }
157
158 return buffer;
159}
160BOOL CDebugSection::__load(void){
161 int i2,i3;
162
163 compiler.pCompilingClass = NULL;
164
165 i2=0;
166
167 //デバッグ用ファイルのバージョンをチェック
168 if(*(long *)(buffer+i2)<MDLFILE_VER){
169 HeapDefaultFree(buffer);
170 return 0;
171 }
172 i2+=sizeof(long);
173
174 //プラットフォームのビット数をチェック
175 if(*(long *)(buffer+i2)!=PLATFORM){
176 HeapDefaultFree(buffer);
177 return 0;
178 }
179 i2+=sizeof(long);
180
181 // オブジェクトモジュール
182 {
183 // サイズ
184 int size = *(long *)(buffer+i2);
185 i2 += sizeof(long);
186
187 // バッファ
188 const std::string textString( (const char *)(buffer + i2), size );
189 i2 += size;
190
191 // テキストデータからシリアライズ
192 this->objectModule.ReadString( textString );
193
194 compiler.SelectObjectModule( this->objectModule );
195 }
196
197
198 //コードと行番号の関係
199 int maxLineInfoNum = *(long *)(buffer+i2);
200 i2+=sizeof(long);
201 for(i3=0;i3<maxLineInfoNum;i3++){
202 int lineNum = *(long *)(buffer+i2);
203 i2+=sizeof(long);
204
205 int nativeCodePos = *(long *)(buffer+i2);
206 i2+=sizeof(long);
207
208 int sourceCodePos = *(long *)(buffer+i2);
209 i2+=sizeof(long);
210
211 DWORD sourceLineType = *(DWORD *)(buffer+i2);
212 i2+=sizeof(long);
213
214 _oldSourceLines.push_back( SourceLine( lineNum, nativeCodePos, sourceCodePos, sourceLineType ) );
215 }
216
217 //グローバル実行領域のサイズ
218 GlobalOpBufferSize=*(long *)(buffer+i2);
219 i2+=sizeof(long);
220
221
222 HeapDefaultFree(buffer);
223 buffer=0;
224
225
226 this->pSub_DebugSys_EndProc=GetSubHash("_DebugSys_EndProc");
227 if( this->pSub_DebugSys_EndProc == NULL )
228 {
229 MessageBox( 0, "_DebugSys_EndProcが見つからない", "ActiveBasic", MB_OK );
230 }
231
232
233 SingleStepCodeBuffer=MakeSingleStepCode();
234
235
236 /////////////////////////////
237 // ブレークポイントを適用
238 /////////////////////////////
239
240 //コードと行番号の関係
241 extern SourceLines oldSourceLines;
242 oldSourceLines = this->_oldSourceLines;
243
244 BreakStepCodeBuffer=pobj_DBBreakPoint->update(OpBuffer,SizeOf_CodeSection);
245
246 //プロセスメモリにコピー
247 extern HANDLE hDebugProcess;
248 SIZE_T accessBytes;
249 WriteProcessMemory(hDebugProcess,(void *)(ULONG_PTR)(dwImageBase+dwRVA_CodeSection),
250 BreakStepCodeBuffer,
251 SizeOf_CodeSection,&accessBytes);
252
253
254 return 1;
255}
256
257BOOL CDebugSection::load(HMODULE hModule){
258 if(buffer){
259 HeapDefaultFree(buffer);
260 buffer=0;
261 }
262
263
264 extern HANDLE hDebugProcess;
265 SIZE_T accessBytes;
266 IMAGE_DOS_HEADER ImageDosHeader;
267 ReadProcessMemory(hDebugProcess,hModule,&ImageDosHeader,sizeof(IMAGE_DOS_HEADER),&accessBytes);
268
269 int pe_size;
270#ifdef _AMD64_
271 IMAGE_NT_HEADERS64 pe_hdr;
272 pe_size=sizeof(IMAGE_NT_HEADERS64);
273#else
274 IMAGE_NT_HEADERS pe_hdr;
275 pe_size=sizeof(IMAGE_NT_HEADERS);
276#endif
277 ReadProcessMemory(hDebugProcess,(void *)(((ULONG_PTR)hModule)+ImageDosHeader.e_lfanew),&pe_hdr,pe_size,&accessBytes);
278
279 IMAGE_SECTION_HEADER *pSectionHdr;
280 pSectionHdr=(IMAGE_SECTION_HEADER *)HeapAlloc(hHeap,0,pe_hdr.FileHeader.NumberOfSections*sizeof(IMAGE_SECTION_HEADER));
281 ReadProcessMemory(hDebugProcess,
282 (void *)(((ULONG_PTR)hModule)+ImageDosHeader.e_lfanew+pe_size),
283 pSectionHdr,
284 pe_hdr.FileHeader.NumberOfSections*sizeof(IMAGE_SECTION_HEADER),
285 &accessBytes);
286
287 int i;
288 for(i=0;i<pe_hdr.FileHeader.NumberOfSections;i++){
289
290 //リライタブルセクション内の情報
291 if(lstrcmp((char *)pSectionHdr[i].Name,".data")==0){
292 dwRVA_RWSection=pSectionHdr[i].VirtualAddress;
293 }
294
295 //コードセクション内の情報
296 if(lstrcmp((char *)pSectionHdr[i].Name,".text")==0){
297 dwRVA_CodeSection=pSectionHdr[i].VirtualAddress;
298 SizeOf_CodeSection=pSectionHdr[i].SizeOfRawData;
299 }
300
301 //デバッグセクション内の情報
302 if(lstrcmp((char *)pSectionHdr[i].Name,".debug")==0){
303 length=pSectionHdr[i].Misc.VirtualSize;
304 buffer=(char *)HeapAlloc(hHeap,0,length+1);
305
306 ReadProcessMemory(hDebugProcess,
307 (void *)(((ULONG_PTR)hModule)+pSectionHdr[i].VirtualAddress),
308 buffer,
309 length,
310 &accessBytes);
311 buffer[length]=0;
312 }
313
314 }
315 HeapDefaultFree(pSectionHdr);
316
317 if(!buffer) return 0;
318
319
320 dwImageBase=(DWORD)(ULONG_PTR)hModule;
321
322
323
324 if(OpBuffer) free(OpBuffer);
325 OpBuffer=(char *)malloc(SizeOf_CodeSection);
326
327 ReadProcessMemory(hDebugProcess,
328 (void *)(ULONG_PTR)(dwImageBase+dwRVA_CodeSection),OpBuffer,
329 SizeOf_CodeSection,&accessBytes);
330
331
332 return __load();
333}
334
335void CDebugSection::choice(void){
336 //イメージベース
337 extern DWORD ImageBase;
338 ImageBase=this->dwImageBase;
339
340 //リライタブルセクションのRVA
341 extern int MemPos_RWSection;
342 MemPos_RWSection=this->dwRVA_RWSection;
343
344 //コードセクションのRVAとサイズ
345 extern int MemPos_CodeSection;
346 extern int FileSize_CodeSection;
347 MemPos_CodeSection=this->dwRVA_CodeSection;
348 FileSize_CodeSection=this->SizeOf_CodeSection;
349
350 // オブジェクトモジュール
351 compiler.SelectObjectModule( this->objectModule );
352
353 //コードと行番号の関係
354 extern SourceLines oldSourceLines;
355 oldSourceLines = this->_oldSourceLines;
356
357 //グローバル実行領域のサイズ
358 extern int GlobalOpBufferSize;
359 GlobalOpBufferSize=this->GlobalOpBufferSize;
360
361 extern const UserProc *pSub_DebugSys_EndProc;
362 pSub_DebugSys_EndProc=this->pSub_DebugSys_EndProc;
363
364 //ネイティブコードバッファ
365 extern char *OpBuffer;
366 OpBuffer=this->OpBuffer;
367}
368
369void CDebugSection::DeleteDebugInfo(void){
370 //コードバッファを解放
371 free(OpBuffer);
372 OpBuffer=0;
373
374 HeapDefaultFree(SingleStepCodeBuffer);
375 SingleStepCodeBuffer=0;
376
377 HeapDefaultFree(BreakStepCodeBuffer);
378 BreakStepCodeBuffer=0;
379}
380
381
382
383CDBDebugSection::CDBDebugSection(){
384 ppobj_ds=(CDebugSection **)HeapAlloc(hHeap,0,1);
385 num=0;
386}
387CDBDebugSection::~CDBDebugSection(){
388 int i;
389 for(i=0;i<num;i++){
390 delete ppobj_ds[i];
391 }
392 HeapDefaultFree(ppobj_ds);
393}
394
395BOOL CDBDebugSection::add(HMODULE hModule){
396 CDebugSection *pobj_d;
397 pobj_d=new CDebugSection();
398 if(!pobj_d->load(hModule)){
399 //デバッグ情報が存在しないとき
400 delete pobj_d;
401 return 0;
402 }
403
404 ppobj_ds=(CDebugSection **)HeapReAlloc(hHeap,0,ppobj_ds,(num+1)*sizeof(CDebugSection *));
405 ppobj_ds[num]=pobj_d;
406 num++;
407
408 return 1;
409}
410
411void CDBDebugSection::del(HMODULE hModule){
412 int i;
413 for(i=0;i<num;i++){
414 if((HMODULE)(ULONG_PTR)ppobj_ds[i]->dwImageBase==hModule){
415 delete ppobj_ds[i];
416
417 num--;
418 for(;i<num;i++){
419 ppobj_ds[i]=ppobj_ds[i+1];
420 }
421 break;
422 }
423 }
424}
425
426void CDBDebugSection::choice(int index){
427 pobj_now=ppobj_ds[index];
428 pobj_now->choice();
429}
430
431
432
433CDBDebugSection *pobj_DBDebugSection;
Note: See TracBrowser for help on using the repository browser.