source: dev/trunk/abdev/BasicCompiler_Common/Compile.cpp@ 182

Last change on this file since 182 was 182, checked in by dai_9181, 17 years ago
File size: 17.3 KB
Line 
1#include <jenga/include/smoothie/Smoothie.h>
2#include <jenga/include/smoothie/LexicalAnalysis.h>
3#include <jenga/include/smoothie/SmoothieException.h>
4
5#include <LexicalScopingImpl.h>
6#include <CodeGenerator.h>
7
8#include "../BasicCompiler_Common/common.h"
9
10#ifdef _AMD64_
11#include "../BasicCompiler64/opcode.h"
12#else
13#include "../BasicCompiler32/opcode.h"
14#endif
15
16#include <Exception.h>
17
18//ラベルアドレス
19LABEL *pLabelNames;
20int MaxLabelNum;
21
22//Continueアドレス
23DWORD dwContinueAddress;
24
25//Caseスケジュール
26DWORD *pCaseSchedule;
27int CaseScheduleNum;
28int NowCaseSchedule;
29
30//プロシージャ抜け出しスケジュール(Exit Sub/Function)
31DWORD *pExitSubSchedule;
32int ExitSubScheduleNum;
33
34//Goto未知ラベル スケジュール
35GOTOLABELSCHEDULE *pGotoLabelSchedule;
36int GotoLabelScheduleNum;
37
38//グローバル変数初期バッファ
39BYTE *initGlobalBuf;
40
41//With情報
42WITHINFO WithInfo;
43
44
45
46///////////////////////////////////////////////////
47// トークンを取得
48///////////////////////////////////////////////////
49void GetIdentifierToken( char *token, const char *source, int &pos ){
50 for( int i=0; ; i++, pos++ ){
51 if( ! IsVariableChar( source[pos] ) ){
52 token[i] = 0;
53 break;
54 }
55 token[i] = source[pos];
56 }
57}
58
59
60///////////////////////////////////////////////////
61// 対になっているステートメントを飛び越す
62// ※グローバル領域用
63///////////////////////////////////////////////////
64int JumpStatement(const char *source, int &pos){
65 if( source[pos] != 1 ) return 0;
66
67 if( ! IsCommandDelimitation( source[pos - 1] ) ){
68 //直前がコマンド区切りではない場合
69 return 0;
70 }
71
72 char cStatement = source[pos + 1];
73
74 char cEnd = GetEndXXXCommand( cStatement );
75 if( cEnd == 0 ) return 0;
76
77 pos += 2;
78 while( ! ( source[pos] == 1 && source[pos + 1] == cEnd ) ){
79
80 if( source[pos] == '\0' ){
81 char temporary[64];
82 GetDefaultNameFromES( cStatement, temporary );
83 SetError( 22, temporary, pos );
84 return -1;
85 }
86
87 pos++;
88 }
89 if( ! ( source[pos] == '\0' || source[pos + 2] == '\0' ) ){
90 pos += 2;
91 }
92
93 return 1;
94}
95
96
97void NextLine(void){
98 extern HANDLE hHeap;
99 extern int MaxLineInfoNum;
100 extern LINEINFO *pLineInfo;
101 if(MaxLineInfoNum){
102 if(pLineInfo[MaxLineInfoNum-1].TopObp==obp){
103 pLineInfo[MaxLineInfoNum-1].TopCp=cp;
104 return;
105 }
106 }
107 pLineInfo=(LINEINFO *)HeapReAlloc(hHeap,0,pLineInfo,(MaxLineInfoNum+1)*sizeof(LINEINFO));
108 pLineInfo[MaxLineInfoNum].TopCp=cp;
109 pLineInfo[MaxLineInfoNum].TopObp=obp;
110
111 extern BOOL bDebugSupportProc;
112 extern BOOL bSystemProc;
113 pLineInfo[MaxLineInfoNum].dwCodeType=0;
114 if(bDebugSupportProc)
115 pLineInfo[MaxLineInfoNum].dwCodeType|=CODETYPE_DEBUGPROC;
116 if(bSystemProc)
117 pLineInfo[MaxLineInfoNum].dwCodeType|=CODETYPE_SYSTEMPROC;
118
119 MaxLineInfoNum++;
120}
121
122void ChangeOpcode(char *Command){
123 extern HANDLE hHeap;
124 int i,i2;
125
126 if(Command[0]=='\0') return;
127 if(Command[0]=='*'&&IsVariableTopChar(Command[1])){
128 //Goto先ラベル
129 pLabelNames=(LABEL *)HeapReAlloc(hHeap,0,pLabelNames,(MaxLabelNum+1)*sizeof(LABEL));
130 pLabelNames[MaxLabelNum].pName=(char *)HeapAlloc(hHeap,0,lstrlen(Command+1)+1);
131 lstrcpy(pLabelNames[MaxLabelNum].pName,Command+1);
132 pLabelNames[MaxLabelNum].address=obp;
133 MaxLabelNum++;
134
135 //書き込みスケジュール
136 for(i=0;i<GotoLabelScheduleNum;i++){
137 if(lstrcmp(pGotoLabelSchedule[i].pName,Command+1)==0){
138 *((long *)(OpBuffer+pGotoLabelSchedule[i].pos))=obp-(pGotoLabelSchedule[i].pos+sizeof(long));
139
140 HeapDefaultFree(pGotoLabelSchedule[i].pName);
141
142 //詰める
143 GotoLabelScheduleNum--;
144 for(i2=i;i2<GotoLabelScheduleNum;i2++){
145 pGotoLabelSchedule[i2].pName=pGotoLabelSchedule[i2+1].pName;
146 pGotoLabelSchedule[i2].line=pGotoLabelSchedule[i2+1].line;
147 pGotoLabelSchedule[i2].pos=pGotoLabelSchedule[i2+1].pos;
148 }
149 i--;
150 continue;
151 }
152 }
153 return;
154 }
155 if(Command[0]==1){
156 switch(Command[1]){
157 case ESC_CONST:
158 OpcodeDim(Command+2, DIMFLAG_CONST);
159 break;
160
161 case ESC_TYPEDEF:
162 if( UserProc::IsLocalAreaCompiling() ){
163 // ローカル領域をコンパイルしているとき
164 SetError(65,"TypeDef",cp );
165 }
166
167 //既に収集済み
168 break;
169
170 case ESC_STATIC:
171 OpcodeDim(Command+2,DIMFLAG_STATIC);
172 break;
173
174 case ESC_IF:
175 OpcodeIf(Command+2);
176 break;
177 case ESC_EXITWHILE:
178 {
179 CScope *pScope = GetLexicalScopes().SearchScope( SCOPE_TYPE_WHILE );
180 if( !pScope ){
181 SetError(12,"Exit While",cp);
182 return;
183 }
184 pScope->Break();
185 }
186 break;
187 case ESC_EXITFOR:
188 {
189 CScope *pScope = GetLexicalScopes().SearchScope( SCOPE_TYPE_FOR );
190 if( !pScope ){
191 SetError(12,"Exit For",cp);
192 return;
193 }
194 pScope->Break();
195 }
196 break;
197 case ESC_EXITDO:
198 {
199 CScope *pScope = GetLexicalScopes().SearchScope( SCOPE_TYPE_DO );
200 if( !pScope ){
201 SetError(12,"Exit Do",cp);
202 return;
203 }
204 pScope->Break();
205 }
206 break;
207 case ESC_CONTINUE:
208 OpcodeContinue();
209 break;
210
211 case ESC_EXITSUB:
212 case ESC_EXITFUNCTION:
213 case ESC_EXITMACRO:
214 OpcodeExitSub();
215 break;
216
217 case ESC_SELECTCASE:
218 OpcodeSelect(Command+2);
219 break;
220 case ESC_CASE:
221 case ESC_CASEELSE:
222 OpcodeCase(Command+2);
223 break;
224
225 case ESC_WITH:
226 extern WITHINFO WithInfo;
227
228 WithInfo.ppName=(char **)HeapReAlloc(hHeap,0,WithInfo.ppName,(WithInfo.num+1)*sizeof(char **));
229 WithInfo.ppName[WithInfo.num]=(char *)HeapAlloc(hHeap,0,lstrlen(Command+2)+1);
230 lstrcpy(WithInfo.ppName[WithInfo.num],Command+2);
231
232 WithInfo.pWithCp=(int *)HeapReAlloc(hHeap,0,WithInfo.pWithCp,(WithInfo.num+1)*sizeof(int));
233 WithInfo.pWithCp[WithInfo.num]=cp;
234
235 WithInfo.num++;
236 break;
237 case ESC_ENDWITH:
238 if(WithInfo.num<=0){
239 SetError(12,"End With",cp);
240 return;
241 }
242 WithInfo.num--;
243 HeapDefaultFree(WithInfo.ppName[WithInfo.num]);
244 break;
245 case ESC_DECLARE:
246 if( UserProc::IsLocalAreaCompiling() ){
247 // ローカル領域をコンパイルしているとき
248 SetError(65,"Declare",cp );
249 }
250 break;
251
252 case ESC_NAMESPACE:
253 Smoothie::Temp::liveingNamespaceScopes.push_back( Command + 2 );
254 break;
255 case ESC_ENDNAMESPACE:
256 if( Smoothie::Temp::liveingNamespaceScopes.size() <= 0 ){
257 SetError(12,"End Namespace",cp);
258 }
259 Smoothie::Temp::liveingNamespaceScopes.pop_back();
260 break;
261 case ESC_IMPORTS:
262 Smoothie::Temp::importedNamespaces.Imports( Command + 2 );
263 break;
264 case ESC_CLEARNAMESPACEIMPORTED:
265 Smoothie::Temp::importedNamespaces.clear();
266 break;
267
268 //Tryによる例外処理
269 case ESC_TRY:
270 Exception::TryCommand();
271 break;
272 case ESC_CATCH:
273 Exception::CatchCommand();
274 break;
275 case ESC_FINALLY:
276 Exception::FinallyCommand();
277 break;
278 case ESC_ENDTRY:
279 Exception::EndTryCommand();
280 break;
281 case ESC_THROW:
282 Exception::ThrowCommand( Command + 2 );
283 break;
284
285 default:
286 char temporary[64];
287 GetDefaultNameFromES(Command[1],temporary);
288 SetError(30,temporary,cp);
289 break;
290 }
291 return;
292 }
293 switch(MAKEWORD(Command[1],Command[0])){
294 case COM_DIM:
295 OpcodeDim(Command+2,0);
296 break;
297 case COM_DELETE:
298 OpcodeDelete(Command+2, false);
299 break;
300 case COM_SWEEPINGDELETE:
301 OpcodeDelete(Command+2, true);
302 break;
303
304 case COM_GOTO:
305 OpcodeGoto(Command+2);
306 break;
307 case COM_WHILE:
308 OpcodeWhile(Command+2);
309 break;
310 case COM_FOR:
311 OpcodeFor(Command+2);
312 break;
313 case COM_DO:
314 OpcodeDo(Command+2);
315 break;
316
317 case COM_GOSUB:
318 OpcodeGosub(Command+2);
319 break;
320 case COM_RETURN:
321 OpcodeReturn(Command+2);
322 break;
323
324 case COM_SETDOUBLE:
325 OpcodeSetPtrData(Command+2,DEF_DOUBLE);
326 break;
327 case COM_SETSINGLE:
328 OpcodeSetPtrData(Command+2,DEF_SINGLE);
329 break;
330 case COM_SETQWORD:
331 OpcodeSetPtrData(Command+2,DEF_QWORD);
332 break;
333 case COM_SETDWORD:
334 OpcodeSetPtrData(Command+2,DEF_DWORD);
335 break;
336 case COM_SETWORD:
337 OpcodeSetPtrData(Command+2,DEF_WORD);
338 break;
339 case COM_SETBYTE:
340 OpcodeSetPtrData(Command+2,DEF_BYTE);
341 break;
342
343 case COM_DEBUG:
344 extern BOOL bDebugCompile;
345 //int 3
346 if(bDebugCompile) OpBuffer[obp++]=(char)0xCC;
347#if defined(_DEBUG)
348 else OpBuffer[obp++]=(char)0xCC;
349#endif
350 break;
351
352 case COM_LET:
353 OpcodeCalc(Command+2);
354 break;
355 default:
356 OpcodeOthers(Command);
357 break;
358 }
359}
360
361void GetGlobalDataForDll(void){
362 extern char *basbuf;
363 extern HANDLE hHeap;
364 int i2,BufferSize;
365 char *Command;
366 DWORD dwRetCode;
367
368 dwRetCode=0;
369 BufferSize=128;
370 Command=(char *)HeapAlloc(hHeap,0,BufferSize);
371 for(cp++,i2=0;;cp++,i2++){
372 if(i2>=BufferSize){
373 //バッファ領域が足りなくなった場合はバッファを増量する
374 BufferSize+=128;
375 Command=(char *)HeapReAlloc(hHeap,0,Command,BufferSize);
376 }
377 if(basbuf[cp]=='\"'){
378 Command[i2]=basbuf[cp];
379 for(cp++,i2++;;cp++,i2++){
380 if(i2>=BufferSize){
381 //バッファ領域が足りなくなった場合はバッファを増量する
382 BufferSize+=128;
383 Command=(char *)HeapReAlloc(hHeap,0,Command,BufferSize);
384 }
385 Command[i2]=basbuf[cp];
386 if(basbuf[cp]=='\"') break;
387 }
388 continue;
389 }
390 if(IsCommandDelimitation(basbuf[cp])){
391 Command[i2]=0;
392
393 if(Command[0]==1&&Command[1]==ESC_SUB){
394 i2=cp;
395 while(!(basbuf[cp]==1&&basbuf[cp+1]==ESC_ENDSUB)){
396 if(basbuf[cp]=='\0'){
397 SetError(22,"Sub",i2);
398 break;
399 }
400 cp++;
401 }
402 if(basbuf[cp+2]=='\0'||basbuf[cp]=='\0') break;
403 cp+=2;
404 i2=-1;
405 continue;
406 }
407 if(Command[0]==1&&Command[1]==ESC_FUNCTION){
408 i2=cp;
409 while(!(basbuf[cp]==1&&basbuf[cp+1]==ESC_ENDFUNCTION)){
410 if(basbuf[cp]=='\0'){
411 SetError(22,"Function",i2);
412 break;
413 }
414 cp++;
415 }
416 if(basbuf[cp+2]=='\0'||basbuf[cp]=='\0') break;
417 cp+=2;
418 i2=-1;
419 continue;
420 }
421 if(Command[0]==1&&Command[1]==ESC_MACRO){
422 i2=cp;
423 while(!(basbuf[cp]==1&&basbuf[cp+1]==ESC_ENDMACRO)){
424 if(basbuf[cp]=='\0'){
425 SetError(22,"Macro",i2);
426 break;
427 }
428 cp++;
429 }
430 if(basbuf[cp+2]=='\0'||basbuf[cp]=='\0') break;
431 cp+=2;
432 i2=-1;
433 continue;
434 }
435 if(Command[0]==1&&Command[1]==ESC_TYPE){
436 i2=cp;
437 while(!(basbuf[cp]==1&&basbuf[cp+1]==ESC_ENDTYPE)){
438 if(basbuf[cp]=='\0'){
439 SetError(22,"Type",i2);
440 break;
441 }
442 cp++;
443 }
444 if(basbuf[cp+2]=='\0'||basbuf[cp]=='\0') break;
445 cp+=2;
446 i2=-1;
447 continue;
448 }
449 if(Command[0]==1&&Command[1]==ESC_CLASS){
450 i2=cp;
451 while(!(basbuf[cp]==1&&basbuf[cp+1]==ESC_ENDCLASS)){
452 if(basbuf[cp]=='\0'){
453 SetError(22,"Class",i2);
454 break;
455 }
456 cp++;
457 }
458 if(basbuf[cp+2]=='\0'||basbuf[cp]=='\0') break;
459 cp+=2;
460 i2=-1;
461 continue;
462 }
463 if(Command[0]==1&&Command[1]==ESC_INTERFACE){
464 i2=cp;
465 while(!(basbuf[cp]==1&&basbuf[cp+1]==ESC_ENDINTERFACE)){
466 if(basbuf[cp]=='\0'){
467 SetError(22,"Interface",i2);
468 break;
469 }
470 cp++;
471 }
472 if(basbuf[cp+2]=='\0'||basbuf[cp]=='\0') break;
473 cp+=2;
474 i2=-1;
475 continue;
476 }
477
478 //DLLのグローバルデータに必要なコマンドだけ
479 if(MAKEWORD(Command[1],Command[0])==COM_DIM)
480 OpcodeDim(Command+2,0);
481
482 // ネイティブコードバッファの再確保
483 ReallocNativeCodeBuffer();
484
485 if(basbuf[cp]=='\0') break;
486 i2=-1;
487 continue;
488 }
489 Command[i2]=basbuf[cp];
490 }
491 HeapDefaultFree(Command);
492}
493DWORD CompileBuffer(char Return_Sequence,WORD Return_Command){
494 extern char *basbuf;
495 extern HANDLE hHeap;
496 int i,i2,i3,i4,BufferSize,ScopeStart;
497 char *Command,temporary[VN_SIZE],*temp2,temp3[32];
498 DWORD dwRetCode;
499
500 ScopeStart=cp;
501
502 dwRetCode=0;
503 BufferSize=128;
504 Command=(char *)HeapAlloc(hHeap,0,BufferSize);
505
506 for(cp++,i2=0;;cp++,i2++){
507 if(i2>=BufferSize){
508 //バッファ領域が足りなくなった場合はバッファを増量する
509 BufferSize+=128;
510 Command=(char *)HeapReAlloc(hHeap,0,Command,BufferSize);
511 }
512 if(basbuf[cp]=='\"'){
513 Command[i2]=basbuf[cp];
514 for(cp++,i2++;;cp++,i2++){
515 if(i2>=BufferSize){
516 //バッファ領域が足りなくなった場合はバッファを増量する
517 BufferSize+=128;
518 Command=(char *)HeapReAlloc(hHeap,0,Command,BufferSize);
519 }
520 Command[i2]=basbuf[cp];
521 if(basbuf[cp]=='\"') break;
522 }
523 continue;
524 }
525 if(IsCommandDelimitation(basbuf[cp])){
526 Command[i2]=0;
527
528 if(Command[0]==1&&Command[1]==ESC_LINENUM){
529 for(i=2,i2=0;;i++,i2++){
530 if(Command[i]==','){
531 temporary[i2]=0;
532 break;
533 }
534 temporary[i2]=Command[i];
535 }
536 i3=atoi(temporary);
537 i4=i+1;
538
539 //Goto先ラベル
540 pLabelNames=(LABEL *)HeapReAlloc(hHeap,0,pLabelNames,(MaxLabelNum+1)*sizeof(LABEL));
541 pLabelNames[MaxLabelNum].pName=0;
542 pLabelNames[MaxLabelNum].line=i3;
543 pLabelNames[MaxLabelNum].address=obp;
544 MaxLabelNum++;
545
546 //書き込みスケジュール
547 for(i=0;i<GotoLabelScheduleNum;i++){
548 if(pGotoLabelSchedule[i].pName==0&&
549 pGotoLabelSchedule[i].line==i3){
550 *((long *)(OpBuffer+pGotoLabelSchedule[i].pos))=obp-(pGotoLabelSchedule[i].pos+sizeof(long));
551
552 //詰める
553 GotoLabelScheduleNum--;
554 for(i2=i;i2<GotoLabelScheduleNum;i2++){
555 pGotoLabelSchedule[i2].pName=pGotoLabelSchedule[i2+1].pName;
556 pGotoLabelSchedule[i2].line=pGotoLabelSchedule[i2+1].line;
557 pGotoLabelSchedule[i2].pos=pGotoLabelSchedule[i2+1].pos;
558 }
559 i--;
560 }
561 }
562
563 temp2=(char *)HeapAlloc(hHeap,0,lstrlen(Command+i4)+1);
564 lstrcpy(temp2,Command+i4);
565 lstrcpy(Command,temp2);
566 HeapDefaultFree(temp2);
567 }
568
569 if(Command[0]==1&&
570 (((Command[1]==ESC_VIRTUAL||Command[1]==ESC_OVERRIDE)&&Command[2]==1&&(Command[3]==ESC_SUB||Command[3]==ESC_FUNCTION))||
571 Command[1]==ESC_SUB||
572 Command[1]==ESC_FUNCTION||
573 Command[1]==ESC_MACRO||
574 Command[1]==ESC_TYPE||
575 Command[1]==ESC_CLASS||
576 Command[1]==ESC_INTERFACE||
577 Command[1]==ESC_ENUM||
578 (Command[1]==ESC_CONST&&Command[2]==1&&Command[3]==ESC_ENUM)
579 )
580 ){
581 if(Command[1]==ESC_VIRTUAL||Command[1]==ESC_OVERRIDE||Command[1]==ESC_CONST){
582 GetDefaultNameFromES(Command[3],temporary);
583 }
584 else{
585 GetDefaultNameFromES(Command[1],temporary);
586 }
587 if(Return_Sequence){
588 SetError(12,temporary,cp);
589 break;
590 }
591
592 if(Command[1]==ESC_CONST) i3=GetEndXXXCommand(Command[3]);
593 else i3=GetEndXXXCommand(Command[1]);
594 for(i2=cp;;cp++){
595 if(basbuf[cp]==1){
596 if(basbuf[cp+1]==i3) break;
597 if(Command[1]==ESC_CLASS||Command[1]==ESC_INTERFACE){
598 //クラス、インターフェイスではSub、Functionの定義を可能にしておく
599 if(basbuf[cp+1]==ESC_MACRO||
600 basbuf[cp+1]==ESC_TYPE||
601 basbuf[cp+1]==ESC_CLASS||
602 basbuf[cp+1]==ESC_INTERFACE||
603 basbuf[cp+1]==ESC_ENUM){
604 GetDefaultNameFromES(basbuf[cp+1],temp3);
605 SetError(12,temp3,cp);
606 }
607 }
608 else{
609 if(basbuf[cp-1]!='*'&&(
610 basbuf[cp+1]==ESC_VIRTUAL||
611 basbuf[cp+1]==ESC_OVERRIDE||
612 basbuf[cp+1]==ESC_SUB||
613 basbuf[cp+1]==ESC_FUNCTION||
614 basbuf[cp+1]==ESC_MACRO||
615 basbuf[cp+1]==ESC_TYPE||
616 basbuf[cp+1]==ESC_CLASS||
617 basbuf[cp+1]==ESC_INTERFACE||
618 basbuf[cp+1]==ESC_ENUM)){
619 GetDefaultNameFromES(basbuf[cp+1],temp3);
620 SetError(12,temp3,cp);
621 }
622 }
623 }
624 if(basbuf[cp]=='\0'){
625 //error
626 //既にエラー発行済みのため、何もせずに抜ける
627 break;
628 }
629 }
630 if(basbuf[cp+2]=='\0'||basbuf[cp]=='\0') break;
631 cp+=2;
632 i2=-1;
633 continue;
634 }
635
636 if(Command[0]==0x10||Command[0]==0x11){
637 //Wend、Next、Loopなど
638 if(Return_Command==MAKEWORD(Command[1],Command[0])){
639 if(Return_Command==COM_NEXT){
640 //Nextの場合は、パラメータ(省略化)の整合性を判断する必要がある(OpcodeFor関数を参照)
641 extern char szNextVariable[VN_SIZE];
642 if(Command[2]) lstrcpy(szNextVariable,Command+2);
643 else szNextVariable[0]=0;
644 }
645 break;
646 }
647 }
648
649 NextLine();
650
651 if(Command[0]==1){
652 if(Return_Sequence==ESC_ENDIF&&Command[1]==ESC_ELSE){
653 dwRetCode=ESC_ELSE;
654 break;
655 }
656
657 if(Command[1]==Return_Sequence){
658 dwRetCode=Command[1];
659 break;
660 }
661 }
662
663 try
664 {
665 ChangeOpcode(Command);
666 }
667 catch( const SmoothieException &smoothieException )
668 {
669 SetError(
670 smoothieException.GetErrorCode(),
671 smoothieException.GetKeyword(),
672 smoothieException.GetNowLine()
673 );
674 }
675
676#ifdef _DEBUG
677 epi_check();
678#endif
679
680 //コンパイルを中断するとき
681 extern BOOL bStopCompile;
682 if(bStopCompile) return 0;
683
684 ReallocNativeCodeBuffer();
685
686 if(basbuf[cp]=='\0'){
687 switch(Return_Command){
688 case COM_WEND:
689 SetError(4,"\"While\" - \"Wend\" ",ScopeStart);
690 break;
691 case COM_NEXT:
692 SetError(4,"\"For\" - \"Next\" ",ScopeStart);
693 break;
694 case COM_LOOP:
695 SetError(4,"\"Do\" - \"Loop\" ",ScopeStart);
696 break;
697 }
698 switch(Return_Sequence){
699 case ESC_ENDSUB:
700 SetError(4,"\"Sub\" - \"End Sub\" ",ScopeStart);
701 break;
702 case ESC_ENDFUNCTION:
703 SetError(4,"\"Function\" - \"End Function\" ",ScopeStart);
704 break;
705 case ESC_ENDMACRO:
706 SetError(4,"\"Macro\" - \"End Macro\" ",ScopeStart);
707 break;
708 case ESC_ENDIF:
709 SetError(22,"If",ScopeStart);
710 break;
711 }
712 break;
713 }
714 i2=-1;
715 continue;
716 }
717 Command[i2]=basbuf[cp];
718 }
719 HeapDefaultFree(Command);
720
721 return dwRetCode;
722}
Note: See TracBrowser for help on using the repository browser.