source: dev/trunk/ab5.0/abdev/ab_common/src/Lexical/Source.cpp@ 635

Last change on this file since 635 was 635, checked in by dai_9181, 16 years ago

リファクタリング(ヒープ制御をstlに置き換え)

File size: 20.2 KB
Line 
1#include "stdafx.h"
2
3const std::string BasicSource::generateDirectiveName = "#generate";
4
5
6class CDefine{
7 std::vector<std::string> names;
8public:
9 void Free();
10 void Init( bool isDebug, bool isDll, bool isUnicode, int majorVer );
11
12 BOOL add(char *name);
13 BOOL undef(char *name);
14 BOOL check(char *name);
15 void preprocessor_ifdef(char *buffer,bool isNot);
16 void DirectiveIfdef(char *buffer);
17};
18CDefine objDefine;
19
20
21//////////////////////////////////////
22// #requireの管理
23//////////////////////////////////////
24class CRequireFiles{
25 Jenga::Common::Strings filepaths;
26public:
27
28 void clear(){
29 filepaths.clear();
30 }
31 bool IsIncluded( const char *includeFilePath ){
32 // '/' → '\\'
33 char tempPath[MAX_PATH];
34 lstrcpy( tempPath, includeFilePath );
35 for( int i=0; tempPath[i]; i++ ){
36 if( tempPath[i] == '/' ){
37 tempPath[i] = '\\';
38 }
39 }
40
41 BOOST_FOREACH( const std::string &filepath, filepaths )
42 {
43 if( lstrcmpi( filepath.c_str(), tempPath ) == 0 )
44 {
45 return true;
46 }
47 }
48 return false;
49 }
50 void Add( const char *includeFilePath ){
51 // '/' → '\\'
52 char tempPath[MAX_PATH];
53 lstrcpy( tempPath, includeFilePath );
54 for( int i=0; tempPath[i]; i++ ){
55 if( tempPath[i] == '/' ){
56 tempPath[i] = '\\';
57 }
58 }
59
60 //既に読み込まれているとき
61 if( IsIncluded( tempPath ) ) return;
62
63 //追加
64 filepaths.push_back( tempPath );
65 }
66};
67CRequireFiles requireFiles;
68
69
70//////////////////////////////////////
71// #define間するクラス
72//////////////////////////////////////
73
74void CDefine::Init( bool isDebug, bool isDll, bool isUnicode, int majorVer )
75{
76 names.clear();
77
78 if( isDebug )
79 {
80 add("_DEBUG");
81 }
82
83#ifdef _AMD64_
84 add("_WIN64");
85#endif
86
87 if( isDll )
88 {
89 add("_DLL");
90 }
91
92 if( isUnicode )
93 {
94 add( "UNICODE" );
95 }
96
97 char temporary[255];
98 sprintf(temporary,"_AB_VER%d",majorVer);
99 add(temporary);
100}
101BOOL CDefine::add(char *name)
102{
103 //重複チェック
104 if(check(name)) return 0;
105
106 //追加
107 names.push_back( name );
108
109 return 1;
110}
111BOOL CDefine::undef(char *name){
112 std::vector<std::string>::iterator i = names.begin();
113 BOOST_FOREACH( const std::string &temp, names ){
114 if( temp == name ){
115 names.erase( i );
116 return 1;
117 }
118 i++;
119 }
120
121 return 0;
122}
123BOOL CDefine::check(char *name){
124
125 //重複チェック
126 BOOST_FOREACH( const std::string &temp, names ){
127 if( temp == name ){
128 return 1;
129 }
130 }
131 return 0;
132}
133
134int Search_endif(char *buffer,int i, int *pLine = 0){
135 for(;;i++){
136 if(buffer[i]=='\0') break;
137
138 if( buffer[i] == '\n' ){
139 if( pLine ){
140 (*pLine)++;
141 }
142 }
143
144 if(buffer[i-1]=='\n'){
145 if(memicmp(buffer+i,"#ifdef",6)==0||memicmp(buffer+i,"#ifndef",7)==0){
146 i=Search_endif(buffer,i+6, pLine);
147 if(buffer[i]=='\0') break;
148 continue;
149 }
150 else if(memicmp(buffer+i,"#endif",6)==0){
151 break;
152 }
153 }
154 }
155 return i;
156}
157
158void CDefine::preprocessor_ifdef(char *buffer,bool isNot){
159 int i,i2,i3;
160 char temporary[VN_SIZE];
161
162 if(isNot) i=lstrlen("#ifndef");
163 else i=lstrlen("#ifdef");
164 while(buffer[i]==' '||buffer[i]=='\t') i++;
165
166 for(i2=0;;i++,i2++){
167 if(buffer[i]=='\n'||buffer[i]=='\0'){
168 temporary[i2]=0;
169 break;
170 }
171 temporary[i2]=buffer[i];
172 }
173
174 int sw=0;
175 if(check(temporary)) sw=1;
176
177 if(isNot){
178 //#ifndefのとき(反対にする)
179 if(sw) sw=0;
180 else sw=1;
181 }
182
183 //#ifdefの行を消去
184 Text::SlideString(buffer+i,-i);
185 i=0;
186
187 BOOL bElse=0;
188 if(sw){
189 //TRUEのとき
190
191 //#else、#endifを探索
192 for(;;i++){
193 if(buffer[i]=='\0') break;
194
195 if(i==0||buffer[i-1]=='\n'){
196 if(memicmp(buffer+i,"#ifdef",6)==0||memicmp(buffer+i,"#ifndef",7)==0){
197 i=Search_endif(buffer,i+6);
198 if(buffer[i]=='\0') break;
199 continue;
200 }
201 else if(memicmp(buffer+i,"#else",5)==0){
202 i2=5;
203 bElse=1;
204 break;
205 }
206 else if(memicmp(buffer+i,"#endif",6)==0){
207 i2=6;
208 bElse=0;
209 break;
210 }
211 }
212 }
213
214 //行を消去
215 Text::SlideString(buffer+i+i2,-i2);
216
217 if(bElse){
218 //#elseがある場合はその区間を消去
219
220 for(i2=i,i3=0;;i2++){
221 if(buffer[i2]=='\0') break;
222
223 if(buffer[i2]=='\n') i3++;
224
225 if(i2==0||buffer[i2-1]=='\n'){
226 if(memicmp(buffer+i2,"#ifdef",6)==0||memicmp(buffer+i2,"#ifndef",7)==0){
227 i2=Search_endif(buffer,i2+6, &i3 );
228 if(buffer[i2]=='\0') break;
229 continue;
230 }
231 if(memicmp(buffer+i2,"#endif",6)==0){
232 i2+=6;
233 break;
234 }
235 }
236 }
237
238 //ソースコード区間を消去し、改行コードを挿入
239 Text::SlideString(buffer+i2,i-i2+i3);
240 memset(buffer+i,'\n',i3);
241 }
242 }
243 else{
244 //FALSEのとき
245
246 //#else、#endifを探索
247 for(i2=i,i3=0;;i2++){
248 if(buffer[i2]=='\0') break;
249
250 if(buffer[i2]=='\n') i3++;
251
252 if(i2==0||buffer[i2-1]=='\n'){
253 if(memicmp(buffer+i2,"#ifdef",6)==0||memicmp(buffer+i2,"#ifndef",7)==0){
254 i2=Search_endif(buffer,i2+6, &i3 );
255 if(buffer[i2]=='\0') break;
256 continue;
257 }
258 else if(memicmp(buffer+i2,"#else",5)==0){
259 i2+=5;
260 bElse=1;
261 break;
262 }
263 else if(memicmp(buffer+i2,"#endif",6)==0){
264 i2+=6;
265 bElse=0;
266 break;
267 }
268 }
269 }
270
271 //ソースコード区間を消去し、改行コードを挿入
272 Text::SlideString(buffer+i2,i-i2+i3);
273 memset(buffer+i,'\n',i3);
274
275 if(bElse){
276 //#endifを探索
277 for(;;i++){
278 if(buffer[i]=='\0') break;
279
280 if(i==0||buffer[i-1]=='\n'){
281 if(memicmp(buffer+i,"#ifdef",6)==0||memicmp(buffer+i,"#ifndef",7)==0){
282 i=Search_endif(buffer,i+6);
283 if(buffer[i]=='\0') break;
284 continue;
285 }
286 else if(memicmp(buffer+i,"#endif",6)==0){
287 i2=6;
288 bElse=0;
289 break;
290 }
291 }
292 }
293
294 //行を消去
295 Text::SlideString(buffer+i+i2,-i2);
296 }
297 }
298}
299
300
301void CDefine::DirectiveIfdef(char *buffer){
302 int i,i2,i3,sw;
303 char temporary[VN_SIZE];
304
305 for(i=0;;i++){
306 if(buffer[i]=='\0') break;
307
308 if(i==0||(i>=1&&buffer[i-1]=='\n')){
309 sw=0;
310 if(memicmp(buffer+i,"#define",7)==0){
311 i2=i+7;
312 while(buffer[i2]==' '||buffer[i2]=='\t') i2++;
313
314 for(i3=0;;i2++,i3++){
315 if(buffer[i2]=='\n'||buffer[i2]=='\0'){
316 temporary[i3]=0;
317 break;
318 }
319 temporary[i3]=buffer[i2];
320 }
321
322 add(temporary);
323
324 i2-=i;
325
326 //ディレクティブを消去
327 Text::SlideString(buffer+i+i2,-i2);
328 }
329 if(memicmp(buffer+i,"#undef",6)==0){
330 i2=i+7;
331 while(buffer[i2]==' '||buffer[i2]=='\t') i2++;
332
333 for(i3=0;;i2++,i3++){
334 if(buffer[i2]=='\n'||buffer[i2]=='\0'){
335 temporary[i3]=0;
336 break;
337 }
338 temporary[i3]=buffer[i2];
339 }
340
341 undef(temporary);
342
343 i2-=i;
344
345 //ディレクティブを消去
346 Text::SlideString(buffer+i+i2,-i2);
347 }
348 else if(memicmp(buffer+i,"#ifdef",6)==0){
349 preprocessor_ifdef(buffer+i,false);
350 continue;
351 }
352 else if(memicmp(buffer+i,"#ifndef",7)==0){
353 preprocessor_ifdef(buffer+i,true);
354 continue;
355 }
356 else continue;
357 }
358 }
359}
360
361
362
363
364bool Text::ReadFile( const std::string &filePath ){
365 //ファイルオープン
366 HANDLE hFile=CreateFile(filePath.c_str(),GENERIC_READ,0,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);
367 if(hFile==INVALID_HANDLE_VALUE){
368 return false;
369 }
370
371 length = GetFileSize( hFile, NULL );
372
373 buffer = (char *)realloc( buffer, length + 1 );
374
375 //読み込み
376 DWORD dwAccBytes;
377 ::ReadFile(hFile,buffer,length,&dwAccBytes,0);
378 buffer[dwAccBytes]=0;
379
380 //ファイルクローズ
381 CloseHandle(hFile);
382
383 return true;
384}
385
386void BasicSource::ChangeReturnLineChar(){
387 int i,i2;
388
389 bool isMustChange = false;
390 for( i=0; ; i++ ){
391 if( buffer[i] == '\0' ){
392 break;
393 }
394 if( buffer[i]=='\n' )
395 {
396 if( i>0 )
397 {
398 if( buffer[i-1] == '\r' )
399 {
400 isMustChange = true;
401 }
402 }
403 }
404 }
405
406 if( !isMustChange )
407 {
408 // 改行コードの変換は必要ない
409 return;
410 }
411
412#ifdef _DEBUG
413 //改行コードの整合性チェック
414 for( i=0; ; i++ ){
415 if( buffer[i] == '\0' ){
416 break;
417 }
418 if( buffer[i]!='\r' && buffer[i+1]=='\n'
419 || buffer[i]=='\r' && buffer[i+1]!='\n' ){
420 char temporary[255];
421 strncpy( temporary, buffer + i-100, 130 );
422 temporary[130] = 0;
423 for(int i2=0; ;i2++){
424 if(temporary[i2]=='\r') temporary[i2]='A';
425 if(temporary[i2]=='\n') temporary[i2]='B';
426 if(temporary[i2]=='\0') break;
427 }
428
429 extern HWND hOwnerEditor;
430 MessageBox( hOwnerEditor, temporary, "改行コードの整合性チェック", MB_OK | MB_ICONEXCLAMATION );
431 }
432 }
433#endif
434
435 //改行コードのCRLFをLFに変換
436 for(i=0,i2=0;;i++,i2++){
437 if(buffer[i]=='\r'&&buffer[i+1]=='\n') i++;
438 buffer[i2]=buffer[i];
439 if(buffer[i]=='\0') break;
440 }
441
442 length = i;
443}
444
445void BasicSource::RemoveComments(){
446 int i,i2,i3,IsStr;
447 char *temporary;
448 temporary=(char *)GlobalAlloc(GMEM_FIXED,lstrlen(buffer)+1);
449 for(i=0,i2=0,i3=0,IsStr=0;;i++,i2++){
450 if(buffer[i]=='\"') IsStr^=1;
451 if(buffer[i]=='\n'||buffer[i]=='\0'){
452 i2--;
453 while(temporary[i2]==' '||temporary[i2]=='\t') i2--;
454 i2++;
455
456 if(i3){
457 //複数行に渡る注釈文の中に改行が存在するとき
458 memset(temporary+i2,'\n',i3);
459 i2+=i3;
460 i3=0;
461 }
462 }
463 if(buffer[i]=='\''&&IsStr==0){
464 //注釈文
465 i2--;
466 while(temporary[i2]==' '||temporary[i2]=='\t') i2--;
467 i2++;
468 while(buffer[i]!='\n'&&buffer[i]!='\0') i++;
469 }
470 if(buffer[i]=='/'&&buffer[i+1]=='*'&&IsStr==0){
471 //注釈文(複数行)
472 i+=2;
473 i3=0;
474 while(!(buffer[i]=='*'&&buffer[i+1]=='/')){
475 if(buffer[i]=='\n') i3++;
476 if(buffer[i]=='\0') break;
477 i++;
478 }
479 if(buffer[i]){
480 i+=2;
481 }
482 i--;
483 i2--;
484 continue;
485 }
486 temporary[i2]=buffer[i];
487 if(buffer[i]=='\0') break;
488 }
489 lstrcpy(buffer,temporary);
490 GlobalFree(temporary);
491}
492
493bool BasicSource::ReadFile_InIncludeDirective( const std::string &filePath ){
494 if( !Text::ReadFile( filePath ) ){
495 return false;
496 }
497
498 // 改行コードをCRLFからLFに変換
499 ChangeReturnLineChar();
500
501 // コメントを削除
502 RemoveComments();
503
504 // #ifdefディレクティブを処理
505 objDefine.DirectiveIfdef( buffer );
506
507 // アンダーバーによる改行を正規表現に戻す
508 RemoveReturnLineUnderbar();
509
510 // ダミー改行をセット
511 Realloc( length + 2 );
512 Text::SlideString( buffer, 2 );
513 buffer[0] = '\n';
514 buffer[1] = '\n';
515
516 return true;
517}
518
519void BasicSource::DirectiveIncludeOrRequire( const std::string &mainSourceFilePath, const std::string &includeDirPath )
520{
521 int i,i2,i3,sw1,LineNum,FileLayer[255],layer,LastFileByte[255];
522 char temporary[MAX_PATH],temp2[MAX_PATH+255],*LayerDir[255];
523
524 layer=0;
525 FileLayer[layer]=0;
526 LastFileByte[layer]=GetLength();
527 LineNum=0;
528
529 if( includedFilesRelation.GetLineCounts() != 0 )
530 {
531 Jenga::Throw( "インクルードファイル構造の初期値が不正" );
532 }
533
534 // メインソースコード
535 FileLayer[layer] = includedFilesRelation.AddFile( mainSourceFilePath );
536
537 //参照ディレクトリ
538 std::string mainSourceFileDir = Jenga::Common::Path::ExtractDirPath( mainSourceFilePath );
539 LayerDir[0]=(char *)malloc(mainSourceFileDir.size()+1);
540 lstrcpy(LayerDir[0],mainSourceFileDir.c_str());
541
542 for(i=0;;i++){
543 if(buffer[i]=='\0'){
544 break;
545 }
546 if(buffer[i]=='\n'){
547 includedFilesRelation.AddLine( FileLayer[layer] );
548 }
549 if(i>LastFileByte[layer]){
550 free(LayerDir[layer]);
551 LayerDir[layer]=0;
552 layer--;
553 }
554 if((buffer[i-1]=='\n'||i==0)&&buffer[i]=='#'){
555 bool isRequire = false;
556 if(memcmp( buffer + i + 1, "include", 7 ) == 0
557 || memcmp( buffer + i + 1, "require", 7 ) == 0){
558
559 //#requireの場合
560 if( buffer[i + 1] == 'r' ) isRequire = true;
561
562 i2=i+8;
563 while(buffer[i2]==' '||buffer[i2]=='\t') i2++;
564
565 if(buffer[i2]=='\"') sw1=0;
566 else if(buffer[i2]=='<') sw1=1;
567 i2++;
568
569 for(i3=0;;i2++,i3++){
570 if((buffer[i2]=='\"'&&sw1==0)||(buffer[i2]=='>'&&sw1==1)||buffer[i2]=='\n'||buffer[i2]=='\0'){
571 temporary[i3]=0;
572 break;
573 }
574 temporary[i3]=buffer[i2];
575 }
576 while(buffer[i2]!='\n'&&buffer[i2]!='\0') i2++;
577
578 if(sw1){
579 sprintf(temp2,"%s\\%s", includeDirPath.c_str(), temporary );
580 lstrcpy(temporary,temp2);
581 }
582 else{
583 Jenga::Common::Directory dir( LayerDir[layer] );
584 lstrcpy( temporary, dir.GetFullPath( temporary ).c_str() );
585 }
586 }
587 else if(memcmp(buffer+i+1,"prompt",6)==0){
588 i2=i+7;
589 sprintf(temporary,"%s\\basic\\prompt.sbp", includeDirPath.c_str() );
590 }
591 else if(memcmp(buffer+i+1,"N88BASIC",8)==0){
592 i2=i+9;
593 sprintf(temporary,"%s\\basic\\prompt.sbp", includeDirPath.c_str() );
594 }
595 else if(memcmp(buffer+i+1,"console",7)==0){
596 //サブシステム タイプをCUIに変更
597 extern unsigned short TypeOfSubSystem;
598 TypeOfSubSystem=IMAGE_SUBSYSTEM_WINDOWS_CUI;
599
600 i2=i+8;
601 sprintf(temporary,"%s\\basic\\dos_console.sbp", includeDirPath.c_str() );
602 }
603 else continue;
604
605 if( !Jenga::Common::Path( temporary ).IsExistFile() )
606 {
607 this->cannotIncludePath = temporary;
608 this->cannotIncludeSourcePos = i;
609 includedFilesRelation.AddLine( FileLayer[layer] );
610 break;
611 }
612
613 if( i == 0 && Jenga::Common::Path(temporary).GetFileName() == "basic" )
614 {
615 }
616 else
617 {
618 //ディレクティブが消えるため、一行減ってしまうのを防ぐ(basic.sbpを除く)
619 Text::SlideString(buffer+i2,1);
620 buffer[i2]='\n';
621 for(i3=0;i3<=layer;i3++) LastFileByte[i3]++;
622 }
623
624 layer++;
625 FileLayer[layer] = includedFilesRelation.AddFile( temporary );
626
627 //#requireの場合では、既に読み込まれているファイルは読み込まないようにする
628 bool isFake = false;
629 if( isRequire ){
630 if( requireFiles.IsIncluded( temporary ) ){
631 //既に読み込まれているとき
632 isFake = true;
633 }
634 }
635
636 BasicSource source;
637
638 if( isFake ){
639 //既に読み込まれているときは空データ
640 source.SetBuffer( "" );
641 }
642 else{
643 //取り込まれたファイルを収集する
644 requireFiles.Add( temporary );
645
646 //インクルードファイルを読み込む
647 if( !source.ReadFile_InIncludeDirective( temporary ) )
648 {
649 throw;
650 }
651 }
652
653 i3=lstrlen(buffer)+source.GetLength();
654 Realloc( i3 );
655 Text::SlideString(buffer+i2,source.GetLength()+(i-i2));
656 memcpy(buffer+i,source.GetBuffer(),source.GetLength());
657
658 //新しい参照ディレクトリをセット
659 char temp4[MAX_PATH];
660 _splitpath(temporary,temp2,temp4,0,0);
661 lstrcat(temp2,temp4);
662 LayerDir[layer]=(char *)malloc(lstrlen(temp2)+1);
663 lstrcpy(LayerDir[layer],temp2);
664
665 //ファイル範囲をスライド
666 LastFileByte[layer]=i+source.GetLength()-1;
667 for(i3=0;i3<layer;i3++) LastFileByte[i3]+=source.GetLength()+(i-i2);
668
669 i--;
670 }
671 }
672
673 free(LayerDir[0]);
674
675 length = lstrlen(buffer);
676}
677
678int KillReturnCode_InParameter(char *buffer,int *pRnum,char cBeginPare,char cEndPare){
679 int i,i2,i3,IsStr;
680
681 //カッコ'('直下の改行
682 while(buffer[0]=='\n'){
683 Text::SlideString(buffer+1,-1);
684 (*pRnum)++;
685 }
686
687 for(i=0,IsStr=0;;i++){
688 if(IsDBCSLeadByte(buffer[i])&&buffer[i+1]){
689 i++;
690 continue;
691 }
692
693 if(buffer[i]=='\"') IsStr^=1;
694
695 if(buffer[i]=='\0') break; //エラー
696 if(buffer[i]=='\n'){
697 i2=0;
698 i3=0;
699 while(buffer[i+i2]=='\n'){
700 i2++;
701 i3++;
702 while(buffer[i+i2]==' '||buffer[i+i2]=='\t') i2++;
703 }
704 while(buffer[i+i2]==' '||buffer[i+i2]=='\t') i2++;
705
706 if(buffer[i+i2]==cEndPare){
707 Text::SlideString(buffer+i+i2,-i2);
708 (*pRnum)+=i3;
709 break;
710 }
711
712 //エラー
713 break;
714 }
715
716 if(buffer[i]=='('&&IsStr==0){
717 i++;
718 i2=KillReturnCode_InParameter(buffer+i,pRnum,'(',')');
719 i+=i2;
720 if(buffer[i]!=')') break;
721 continue;
722 }
723 if(buffer[i]=='['&&IsStr==0){
724 i++;
725 i2=KillReturnCode_InParameter(buffer+i,pRnum,'[',']');
726 i+=i2;
727 if(buffer[i]!=']') break;
728 continue;
729 }
730 if(buffer[i]==cEndPare&&IsStr==0) break;
731
732 if(buffer[i]==','&&buffer[i+1]=='\n'&&IsStr==0){
733 i++;
734 while(buffer[i]=='\n'){
735 Text::SlideString(buffer+i+1,-1);
736 (*pRnum)++;
737 }
738 i--;
739 }
740 }
741 return i;
742}
743void BasicSource::RemoveReturnLineUnderbar(){
744 int i,i2;
745
746 //アンダーバーによる改行
747 for(i=0;;i++){
748 i2=0;
749 while(buffer[i]=='_'&&buffer[i+1]=='\n'){
750 i2++;
751 Text::SlideString(buffer+i+2,-2);
752 while(buffer[i]=='\n'){
753 Text::SlideString(buffer+i+1,-1);
754 i2++;
755 }
756 for(;;i++){
757 if(buffer[i]=='_'&&buffer[i+1]=='\n') break;
758 if(buffer[i]=='\n'||buffer[i]=='\0'){
759 Text::SlideString(buffer+i,i2);
760 memset(buffer+i,'\n',i2);
761 break;
762 }
763 }
764 }
765 if(buffer[i]=='\0') break;
766 }
767
768 //カッコ内パラメータの改行
769 int IsStr,rnum;
770 for(i=0,IsStr=0,rnum=0;;i++){
771 if(IsDBCSLeadByte(buffer[i])&&buffer[i+1]){
772 i++;
773 continue;
774 }
775 if(buffer[i]=='\0') break;
776 if(buffer[i]=='\n'){
777 if(rnum){
778 Text::SlideString(buffer+i+1,rnum);
779 memset(buffer+i+1,'\n',rnum);
780 rnum=0;
781 }
782 }
783 if(buffer[i]=='\"') IsStr^=1;
784 if(buffer[i]=='('&&IsStr==0){
785 i++;
786 i2=KillReturnCode_InParameter(buffer+i,&rnum,'(',')');
787 i+=i2;
788 if(buffer[i]!=')') break;
789 }
790 if(buffer[i]=='['&&IsStr==0){
791 i++;
792 i2=KillReturnCode_InParameter(buffer+i,&rnum,'[',']');
793 i+=i2;
794 if(buffer[i]!=']') break;
795 }
796 }
797
798 length = lstrlen(buffer);
799}
800
801void BasicSource::Initialize( const std::string &source )
802{
803 Clear();
804 Add( source );
805
806 // 改行コードをCRLFからLFに変換
807 ChangeReturnLineChar();
808
809 // コメントを削除
810 RemoveComments();
811
812 //最終行には文字を含ませないようにする
813 if( lstrlen(buffer)>0 && buffer[lstrlen(buffer)-1] != '\n' )
814 {
815 Realloc( length + 1 );
816 lstrcat( buffer, "\n" );
817 }
818
819 // アンダーバーによる改行を正規表現に戻す
820 RemoveReturnLineUnderbar();
821}
822
823void BasicSource::SetBuffer( const char *buffer ){
824 this->buffer = (char *)calloc( lstrlen(buffer) + 1, 1 );
825 lstrcpy( this->buffer, buffer );
826 length = lstrlen(buffer);
827
828 // ダミー改行をセット
829 Realloc( length + 2 );
830 Text::SlideString( this->buffer, 2 );
831 this->buffer[0] = '\n';
832 this->buffer[1] = '\n';
833}
834
835bool BasicSource::ReadFile( const std::string &filePath, bool isDebug, bool isDll, bool isUnicode, int majorVer, const std::string &mainSourceFilePath, const std::string &includeDirPath )
836{
837 if( !Text::ReadFile( filePath ) ){
838 return false;
839 }
840
841 // 改行コードをCRLFからLFに変換
842 ChangeReturnLineChar();
843
844 // basic.sbpをインクルード
845 //const char *headCode = "#include <basic.sbp>\n";
846 const char *headCode = "";
847 Realloc( length + lstrlen(headCode) );
848 Text::SlideString( buffer, lstrlen(headCode) );
849 memcpy( buffer, headCode, lstrlen(headCode) );
850
851 // #defineと#requireを初期化
852 // TODO: バージョン番号の識別子defineが未完成
853 objDefine.Init( isDebug, isDll, isUnicode, majorVer );
854 requireFiles.clear();
855
856 // コメントを削除
857 RemoveComments();
858
859 // #ifdefディレクティブを処理
860 objDefine.DirectiveIfdef( buffer );
861
862 //最終行には文字を含ませないようにする
863 Realloc( length + 1 );
864 lstrcat( buffer, "\n" );
865
866 // #include / #require ディレクティブを処理
867 DirectiveIncludeOrRequire( mainSourceFilePath, includeDirPath );
868
869 // アンダーバーによる改行を正規表現に戻す
870 RemoveReturnLineUnderbar();
871
872 // ダミー改行をセット
873 Realloc( length + 2 );
874 Text::SlideString( buffer, 2 );
875 buffer[0] = '\n';
876 buffer[1] = '\n';
877
878 extern char *basbuf;
879 basbuf = GetBuffer();
880
881 return true;
882}
883
884void BasicSource::Addition( const char *buffer ){
885 Realloc( length + lstrlen(buffer) );
886 lstrcat( this->buffer, buffer );
887}
888
889bool BasicSource::GetLineInfo( int sourceCodePos, int &line, std::string &filePath ) const
890{
891 int i2,i3,i4,i5;
892
893 const char *buffer = GetBuffer();
894 int i = sourceCodePos;
895
896 if(buffer[i]=='\n') i--;
897 for(i3=0,i2=0;i3<i;i3++){
898 if(buffer[i3]=='\n') i2++;
899 if(buffer[i3]=='\0') return 0;
900 }
901
902 if( includedFilesRelation.GetLineCounts() < i2 )
903 {
904 //Jenga::Throw( "BasicSource::GetLineInfoメソッドで不正な行の情報を取得しようとした" );
905
906 //ファイル・行番号を特定できなかった場合
907 line = -1;
908 filePath = "";
909 return false;
910 }
911
912 i4=0;
913 while( includedFilesRelation.GetFileNumber( i2 ) != includedFilesRelation.GetFileNumber( i4 ) )
914 {
915 i4++;
916 }
917 for(i3=0,i5=0;i5<i4;i3++){
918 if(buffer[i3]=='\n') i5++;
919 if(buffer[i3]=='\0') return 0;
920 }
921 for(i5=0;i4<i2;i3++){
922 if(buffer[i3]=='\n'){
923 i4++;
924 i5++;
925 if( includedFilesRelation.GetFileNumber( i2 ) < includedFilesRelation.GetFileNumber( i4 ) )
926 {
927 for( ;includedFilesRelation.GetFileNumber( i2 ) != includedFilesRelation.GetFileNumber( i4 ); i3++ ){
928 if(buffer[i3]=='\n') i4++;
929 }
930 }
931 }
932 if(buffer[i3]=='\0') return 0;
933 }
934
935 //行番号をセット
936 line = i5;
937
938 //ファイル名をセット
939 filePath = includedFilesRelation.GetFilePath( i2 );
940
941 return 1;
942}
Note: See TracBrowser for help on using the repository browser.