Добавил:
Studfiles2
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз:
Предмет:
Файл:Курсовая работа2 / SLR_Grammar / Umsc_GenCode
.pas unit Umsc_GenCode;
{=}INTERFACE
procedure GenCode;
{=}IMPLEMENTATION
uses SysUtils, Graphics, xmldom, XMLIntf, msxmldom, XMLDoc,
Ufrm_Main, Udm_Grammar, Udm_Goto, Udm_Action;
function IsTerm( i_Goto: IXMLNode ): string;
begin
if i_Goto.Attributes['TYPE'] = 'term' then Result := 'true' else Result := 'false';
end;
function ToAction( i_Act: IXMLNode ): string;
begin
if i_Act.Attributes['ACTION'] = 'ACCEPT' then Result := '-2'
else if i_Act.Attributes['ACTION'] = 'SHIFT' then Result := '-1'
else Result := i_Act.Attributes['DATA'];
end;
procedure GenCode;
var Fout: text; FName: string; nSym, nSub: integer; SymNode, SubNode: IXMLNode;
FCount, GCount: integer;
begin
FName := ChangeFileExt( ExtractFileName(dm_Grammar.xml_Grammar.FileName), '' );
//===========================================================================
frm_Main.Log( 'Создание pascal.cpp', clGreen );
AssignFile( Fout, FName + '.cpp'); Rewrite( Fout );
writeln(Fout, '// File generated by SLR(1)-Grammer for grammar ' + FName);
writeln(Fout, '');
writeln(Fout, '// Including external dependecies');
writeln(Fout, '');
writeln(Fout, '#include "StdAfx.h"');
writeln(Fout, '#include "' + FName + '.h"');
writeln(Fout, '');
writeln(Fout, '// Terminals information for grammar automaton');
writeln(Fout, '');
writeln(Fout, 'ENUM_TOKENS ' + FName + '_Terms [] = {');
for nSym := 0 to dm_Grammar.node_Term.ChildNodes.Count - 1 do
begin
SymNode := dm_Grammar.node_Term.ChildNodes[nSym];
if nSym <> 0 then writeln(Fout,',');
write(Fout, SymNode.Attributes['NAME'] );
end;
writeln(Fout, '');
writeln(Fout, '};');
writeln(Fout, '');
writeln(Fout, '// Productions information for grammar automaton');
writeln(Fout, '');
writeln(Fout, 'RuleInfo ' + FName + '_Rules [] = {');
for nSym := 0 to dm_Grammar.node_Prod.ChildNodes.Count - 1 do
begin
SymNode := dm_Grammar.node_Prod.ChildNodes[nSym];
if nSym <> 0 then writeln(Fout,',');
write(Fout, '{ ' + SymNode.Attributes['START'] + ', ' + IntToStr( SymNode.ChildNodes.Count ) + ' }' );
end;
writeln(Fout, '');
writeln(Fout, '};');
writeln(Fout, '');
writeln(Fout, '// Goto table for grammar automaton');
writeln(Fout, '');
GCount := 0;
writeln(Fout, 'GInfo ' + FName + '_Goto [] = {');
for nSym := 0 to dm_Goto.xml_States.DocumentElement.ChildNodes.Count - 1 do
begin
SymNode := dm_Goto.xml_States.DocumentElement.ChildNodes[nSym];
for nSub := 0 to SymNode.ChildNodes.Count - 1 do
begin
SubNode := SymNode.ChildNodes[nSub];
if not((nSub = 0) and (nSym = 0)) then writeln(Fout,',');
write(Fout, '{ ' + SymNode.Attributes['NAME'] + ', ' +
IsTerm(SubNode) + ', ' + SubNode.Attributes['NAME'] + ', ' +
SubNode.Attributes['STNAME'] + ' }');
inc(GCount);
end;
end;
writeln(Fout, '');
writeln(Fout, '};');
writeln(Fout, '');
writeln(Fout, '// Action table for grammar automaton');
writeln(Fout, '');
FCount := 0;
writeln(Fout, 'FInfo ' + FName + '_Action [] = {');
for nSym := 0 to dm_Action.xml_Action.DocumentElement.ChildNodes.Count - 1 do
begin
SymNode := dm_Action.xml_Action.DocumentElement.ChildNodes[nSym];
for nSub := 0 to SymNode.ChildNodes.Count - 1 do
begin
SubNode := SymNode.ChildNodes[nSub];
if not((nSub = 0) and (nSym = 0)) then writeln(Fout,',');
write(Fout, '{ ' + SymNode.Attributes['NAME'] + ', ' +
SubNode.Attributes['NAME'] + ', ' + ToAction( SubNode ) + ' }');
inc(FCount);
end;
end;
writeln(Fout, '');
writeln(Fout, '};');
CloseFile( Fout );
//===========================================================================
frm_Main.Log( 'Создание pascal.h', clGreen );
AssignFile( Fout, FName + '.h'); Rewrite( Fout );
writeln(Fout, '// File generated by SLR(1)-Grammar for grammar ' + FName);
writeln(Fout, '');
writeln(Fout, '#include "SyntaxAn.h"');
writeln(Fout, '#include "Tokens.h"');
writeln(Fout, '');
writeln(Fout, '#define ' + FName + '_RulesCount ' + IntToStr( dm_Grammar.node_Prod.ChildNodes.Count ));
writeln(Fout, '#define ' + FName + '_FCount ' + IntToStr( FCount ));
writeln(Fout, '#define ' + FName + '_GCount ' + IntToStr( GCount ));
writeln(Fout, '');
writeln(Fout, '// Defining symbolics for nonterminals');
writeln(Fout, '');
for nSym := 0 to dm_Grammar.node_NTerm.ChildNodes.Count - 1 do
begin
SymNode := dm_Grammar.node_NTerm.ChildNodes[nSym];
writeln(Fout, '#define ' + SymNode.Attributes['NAME'] + ' ' + IntToStr(nSym));
end;
writeln(Fout, '');
writeln(Fout, '// Defining symbolics for automaton states');
writeln(Fout, '');
for nSym := 0 to dm_Goto.xml_States.DocumentElement.ChildNodes.Count - 1 do
begin
SymNode := dm_Goto.xml_States.DocumentElement.ChildNodes[nSym];
writeln(Fout, '#define ' + SymNode.Attributes['NAME'] +' ' + IntToStr(nSym));
end;
writeln(Fout, '');
writeln(Fout, '// Defining symbolics for grammar productions');
writeln(Fout, '');
for nSym := 0 to dm_Grammar.node_Prod.ChildNodes.Count - 1 do
begin
SymNode := dm_Grammar.node_Prod.ChildNodes[nSym];
write(Fout,'#define _' + SymNode.Attributes['START'] + '__');
for nSub := 0 to SymNode.ChildNodes.Count - 1 do
begin
SubNode := SymNode.ChildNodes[nSub];
write(Fout, {SubNode.Attributes['TYPE'] + }SubNode.Attributes['NAME'] + '_');
end;
writeln(Fout, ' ' + IntToStr(nSym));
end;
writeln(Fout, '');
writeln(Fout, '// Defining external links');
writeln(Fout, '');
writeln(Fout, 'extern ENUM_TOKENS ' + FName + '_Terms[];');
writeln(Fout, 'extern RuleInfo ' + FName + '_Rules[];');
writeln(Fout, 'extern GInfo ' + FName + '_Goto[];');
writeln(Fout, 'extern FInfo ' + FName + '_Action[];');
CloseFile( Fout );
//===========================================================================
end;
end.
{=}INTERFACE
procedure GenCode;
{=}IMPLEMENTATION
uses SysUtils, Graphics, xmldom, XMLIntf, msxmldom, XMLDoc,
Ufrm_Main, Udm_Grammar, Udm_Goto, Udm_Action;
function IsTerm( i_Goto: IXMLNode ): string;
begin
if i_Goto.Attributes['TYPE'] = 'term' then Result := 'true' else Result := 'false';
end;
function ToAction( i_Act: IXMLNode ): string;
begin
if i_Act.Attributes['ACTION'] = 'ACCEPT' then Result := '-2'
else if i_Act.Attributes['ACTION'] = 'SHIFT' then Result := '-1'
else Result := i_Act.Attributes['DATA'];
end;
procedure GenCode;
var Fout: text; FName: string; nSym, nSub: integer; SymNode, SubNode: IXMLNode;
FCount, GCount: integer;
begin
FName := ChangeFileExt( ExtractFileName(dm_Grammar.xml_Grammar.FileName), '' );
//===========================================================================
frm_Main.Log( 'Создание pascal.cpp', clGreen );
AssignFile( Fout, FName + '.cpp'); Rewrite( Fout );
writeln(Fout, '// File generated by SLR(1)-Grammer for grammar ' + FName);
writeln(Fout, '');
writeln(Fout, '// Including external dependecies');
writeln(Fout, '');
writeln(Fout, '#include "StdAfx.h"');
writeln(Fout, '#include "' + FName + '.h"');
writeln(Fout, '');
writeln(Fout, '// Terminals information for grammar automaton');
writeln(Fout, '');
writeln(Fout, 'ENUM_TOKENS ' + FName + '_Terms [] = {');
for nSym := 0 to dm_Grammar.node_Term.ChildNodes.Count - 1 do
begin
SymNode := dm_Grammar.node_Term.ChildNodes[nSym];
if nSym <> 0 then writeln(Fout,',');
write(Fout, SymNode.Attributes['NAME'] );
end;
writeln(Fout, '');
writeln(Fout, '};');
writeln(Fout, '');
writeln(Fout, '// Productions information for grammar automaton');
writeln(Fout, '');
writeln(Fout, 'RuleInfo ' + FName + '_Rules [] = {');
for nSym := 0 to dm_Grammar.node_Prod.ChildNodes.Count - 1 do
begin
SymNode := dm_Grammar.node_Prod.ChildNodes[nSym];
if nSym <> 0 then writeln(Fout,',');
write(Fout, '{ ' + SymNode.Attributes['START'] + ', ' + IntToStr( SymNode.ChildNodes.Count ) + ' }' );
end;
writeln(Fout, '');
writeln(Fout, '};');
writeln(Fout, '');
writeln(Fout, '// Goto table for grammar automaton');
writeln(Fout, '');
GCount := 0;
writeln(Fout, 'GInfo ' + FName + '_Goto [] = {');
for nSym := 0 to dm_Goto.xml_States.DocumentElement.ChildNodes.Count - 1 do
begin
SymNode := dm_Goto.xml_States.DocumentElement.ChildNodes[nSym];
for nSub := 0 to SymNode.ChildNodes.Count - 1 do
begin
SubNode := SymNode.ChildNodes[nSub];
if not((nSub = 0) and (nSym = 0)) then writeln(Fout,',');
write(Fout, '{ ' + SymNode.Attributes['NAME'] + ', ' +
IsTerm(SubNode) + ', ' + SubNode.Attributes['NAME'] + ', ' +
SubNode.Attributes['STNAME'] + ' }');
inc(GCount);
end;
end;
writeln(Fout, '');
writeln(Fout, '};');
writeln(Fout, '');
writeln(Fout, '// Action table for grammar automaton');
writeln(Fout, '');
FCount := 0;
writeln(Fout, 'FInfo ' + FName + '_Action [] = {');
for nSym := 0 to dm_Action.xml_Action.DocumentElement.ChildNodes.Count - 1 do
begin
SymNode := dm_Action.xml_Action.DocumentElement.ChildNodes[nSym];
for nSub := 0 to SymNode.ChildNodes.Count - 1 do
begin
SubNode := SymNode.ChildNodes[nSub];
if not((nSub = 0) and (nSym = 0)) then writeln(Fout,',');
write(Fout, '{ ' + SymNode.Attributes['NAME'] + ', ' +
SubNode.Attributes['NAME'] + ', ' + ToAction( SubNode ) + ' }');
inc(FCount);
end;
end;
writeln(Fout, '');
writeln(Fout, '};');
CloseFile( Fout );
//===========================================================================
frm_Main.Log( 'Создание pascal.h', clGreen );
AssignFile( Fout, FName + '.h'); Rewrite( Fout );
writeln(Fout, '// File generated by SLR(1)-Grammar for grammar ' + FName);
writeln(Fout, '');
writeln(Fout, '#include "SyntaxAn.h"');
writeln(Fout, '#include "Tokens.h"');
writeln(Fout, '');
writeln(Fout, '#define ' + FName + '_RulesCount ' + IntToStr( dm_Grammar.node_Prod.ChildNodes.Count ));
writeln(Fout, '#define ' + FName + '_FCount ' + IntToStr( FCount ));
writeln(Fout, '#define ' + FName + '_GCount ' + IntToStr( GCount ));
writeln(Fout, '');
writeln(Fout, '// Defining symbolics for nonterminals');
writeln(Fout, '');
for nSym := 0 to dm_Grammar.node_NTerm.ChildNodes.Count - 1 do
begin
SymNode := dm_Grammar.node_NTerm.ChildNodes[nSym];
writeln(Fout, '#define ' + SymNode.Attributes['NAME'] + ' ' + IntToStr(nSym));
end;
writeln(Fout, '');
writeln(Fout, '// Defining symbolics for automaton states');
writeln(Fout, '');
for nSym := 0 to dm_Goto.xml_States.DocumentElement.ChildNodes.Count - 1 do
begin
SymNode := dm_Goto.xml_States.DocumentElement.ChildNodes[nSym];
writeln(Fout, '#define ' + SymNode.Attributes['NAME'] +' ' + IntToStr(nSym));
end;
writeln(Fout, '');
writeln(Fout, '// Defining symbolics for grammar productions');
writeln(Fout, '');
for nSym := 0 to dm_Grammar.node_Prod.ChildNodes.Count - 1 do
begin
SymNode := dm_Grammar.node_Prod.ChildNodes[nSym];
write(Fout,'#define _' + SymNode.Attributes['START'] + '__');
for nSub := 0 to SymNode.ChildNodes.Count - 1 do
begin
SubNode := SymNode.ChildNodes[nSub];
write(Fout, {SubNode.Attributes['TYPE'] + }SubNode.Attributes['NAME'] + '_');
end;
writeln(Fout, ' ' + IntToStr(nSym));
end;
writeln(Fout, '');
writeln(Fout, '// Defining external links');
writeln(Fout, '');
writeln(Fout, 'extern ENUM_TOKENS ' + FName + '_Terms[];');
writeln(Fout, 'extern RuleInfo ' + FName + '_Rules[];');
writeln(Fout, 'extern GInfo ' + FName + '_Goto[];');
writeln(Fout, 'extern FInfo ' + FName + '_Action[];');
CloseFile( Fout );
//===========================================================================
end;
end.
Соседние файлы в папке SLR_Grammar