Автор работы: Пользователь скрыл имя, 04 Октября 2010 в 16:14, Не определен
Транслятор с псевдоязыка на Си
Министерство образования и науки Российской Федерации
Федеральное агентство по образованию
Южно-Уральский государственный университет
Кафедра
«Прикладная математика»
Курсовая работа
по дисциплине
«Методы трансляции»
Выполнил : Наумченкова Е.
Специальность: 230105
Группа: ММз – 307
Проверил: доцент кафедры Прикладной математики ЮурГУ
Демидов
Андрей Константинович
Челябинск
– 2010
СОДЕРЖАНИЕ
Список использованной литературы
1 Постановка задачи
Транслятор должен переводить указанный язык на подмножество языка Си
goto label;
if(переменная) goto label;
переменная=[переменная] операция переменная;
переменная [операция]=переменная;
scanf("%d",&mem[число]);
printf("%d",mem[число]);
printf("строка");
Где переменная: stack[top] или stack[top-число] или top или mem[число] или число
В результате должен получиться файл program.c:
#include <stdio.h>
int main()
{
int stack[1000],mem[1000],top=0;
/* код программы */
}
***********************
A2 B1 C4 F1 G4 H2
***********************
A. Комментарии:
2. // текст
до конца строки
B. Числа целые десятичные и
1. Восьмеричные,
начинающиеся с префикса 0
C. Строки (для вывода)
4. [текст]
[текст в [\] ]
D. Переменные - идентификатор, начин с буквы, затем буквы и цифры,
длиной до 10 символов
E. Выражения
Операции +, -, *, / и знаки сравнения >, <, =, !=, >=, <=,
круглые скобки, операция смена
знака -, обычный приоритет
F. Оператор присваивания
1. Переменная:=Выражение
G. Операторы ввода-вывода
4. GET IN переменная
GET OUT строка
GET OUT переменная
H. Сложные операторы
2. Операторы разделяются концом строки
IF выражение THEN
операторы
ENDIF
IF выражение THEN
операторы
ELSE
операторы
ENDIF
WHILE выражение
операторы
WEND
2 Лексический блок
Инструмент flex использует конфигурационный файл для создания исходного кода на C. Конфигурационный файл определяет набор символов, ожидающихся в анализируемом файле, а также действия, которые надо выполнить, когда файл будет проанализирован.
Содержание файла c.lex:
%{
#include "y.tab.h"
#include "util.h"
extern int yylval;
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int nlines=1;
%}
%%
"//".*\n nlines++;
0[0-7]* {sscanf(yytext,"%o",&yylval);
[0-9]+ {sscanf(yytext,"%d",&yylval);
\[(\\.|[^\]\n])*\] {
char *s;
int n,k=0,i;
n=strlen(yytext);
s=malloc(n * 2 + 1);
s[k++]='"';
for(i=1;i<n-1;i++)
{
if(yytext[i]=='"')
{s[k++]='\\'; s[k++]='"';}
else if(yytext[i]=='\\')
{s[k++]='\\'; s[k++]=yytext[++i];}
else s[k++]=yytext[i];
}
s[k++]='"';
s[k++]='\0';
yylval=(int)s;
return STRING;
}
":=" return ASSIGN;
"!=" return NE;
"<=" return LE;
">=" return GE;
GET return GET;
IN return IN;
OUT return OUT;
IF return IF;
THEN return THEN;
ENDIF return ENDIF;
ELSE return ELSE;
WHILE return WHILE;
WEND return WEND;
[ \t] ;
[A-Za-z][A-Za-z0-9]* {yylval=findid(yytext); return IDENT;}
\n { nlines++; return yytext[0];}
. return yytext[0];
%%
int yywrap(){return 1;}
3 Грамматический блок
Задачей анализатора Bison является сборка лексем в группы в соответствии с правилами грамматики. По мере выполнения этой задачи анализатор выполняет действия, сопоставленные используемым правилам грамматики. На вход подается файл грамматики Bison. Выходным текстом является исходный текст на C, осуществляющий разбор языка, описываемого грамматикой.
c.grm:
%start PROGRAM
%token ASSIGN NE LE GE NUMBER STRING IDENT
%token GET IN OUT ENDIF WEND IF ELSE WHILE THEN
%nonassoc '=' NE LE GE '<' '>'
%left '+' '-'
%left '*' '/'
%left UMINUS
%{
#include <stdio.h>
#include <string.h>
int root;
extern int nlines;
%}
%%
PROGRAM: operators
{ root=$1; }
;
operators: operator
{ $$=$1; }
| operators operator
{ $$=seq($1,$2); }
;
elsepart :
{ $$=emptystmt(); }
| ELSE '\n' operators
{ $$=$3; }
;
operator: '\n'
{ $$=emptystmt(); }
| IDENT ASSIGN expression '\n'
{ $$ = assignstmt($1, $3); }
| GET OUT STRING '\n'
{ $$ = printstr($3); }
| GET OUT expression '\n'
{$$ = printint($3); }
| GET IN IDENT '\n'
{$$ = scanvar($3); }
| IF expression THEN '\n' operators elsepart ENDIF '\n'
{ $$ = ifstmt($2, $5, $6); }
| WHILE expression operators WEND '\n'
{ $$ = whilestmt($2, $3); }
;
expression: expression '=' expression { $$ = $3; }
| expression NE expression { $$ = ne($1, $3); }
| expression '<' expression { $$ = lt($1, $3); }
| expression LE expression { $$ = le($1, $3); }
| expression '>' expression { $$ = gt($1, $3); }
| expression GE expression { $$ = ge($1, $3); }
| expression '+' expression { $$ = plus($1, $3); }
| expression '-' expression { $$ = minus($1, $3); }
| expression '*' expression { $$ = mult($1, $3); }
| expression '/' expression { $$ = divide ($1, $3); }
| '-' expression %prec UMINUS
{ $$ = neg($2); }
| '(' expression ')' { $$ = $2; }
| NUMBER { $$ = number($1); }
| IDENT { $$ = ident($1); }
;
%%
int yyerror(char *msg)
{
printf("Line %d: %s\n",nlines,msg);
exit(1);
}
int main(int argc, char *argv[])
{
if(argc>1)
freopen(argv[1],"r",stdin);
if(argc>2)
freopen(argv[2],"w",stdout);
yyparse();
printf(
"#include <stdio.h>\n"
"int main()\n"
"{\n"
" int stack[1000],mem[1000],top=0;\
generate(root);
printf(" ;\n}\n");
return 0;
}
4 Пример работы транслятора
Задача: найти наибольший общий делитель, сократить дробь.
Текст программы на входном языке находится в файле test2.prg:
GET OUT [Sokraschenie drobei\n]
GET OUT [Vvedite chislitel']
GET IN chisl
GET OUT [Vvedite znamenatel']
GET IN znam
M:=chisl
N:=znam
IF M>=N THEN
R:=M-N
ELSE
R:=N-M
ENDIF
WHILE R>0
IF N>=M THEN
N:=N-M
ELSE
M:=M-N
ENDIF
IF M>=N THEN
R:=M-N
ELSE
R:=N-M
ENDIF
WEND
chisl:=chisl/M
znam:=znam/M
GET OUT [NOD=]
GET OUT M
GET OUT [\ndrob' \n]
GET OUT chisl
GET OUT [\\]
GET OUT znam
Обработка транслятором:
Compiler test.prg >test2.c