Главная Случайная страница Контакты | Мы поможем в написании вашей работы! | ||
|
Задача состоит в том, чтобы реализовать в языке C0 операции ++ и – – языка C (увеличение и уменьшение переменной на 1).
Для включения новых операций в грамматику C0 необходимо добавить правило: терм::= ++ имя | имя ++ | -- имя | имя --
Операции увеличения и уменьшения на 1 можно реализовать следующим объектным кодом.
; ++ имя; имя ++; -- имя; имя --
INC адрес MOV AX,адрес DEC адрес MOV AX,адрес
MOV AX,адрес INC адрес MOV AX,адрес DEC адрес
Для глобальной переменной адрес - это имя, для локальной переменной адрес записывается в виде: смещение[BP].
Если операция в выражении не последняя, а промежуточная, добавляется команда вталкивания результата в стек: PUSH AX.
В трансляторе C0 добавятся новые значения лексемы uvel и umen, что потребует изменения: описаний типа tipleks и глобальных переменных tpr, st2, значения nvir множества начальных лексем выражения, подпрограммы чтения лексемы chleks. Новые лексемы uvel и umen будут вставлены в описание типа tipleks между лексемами plus и prisv, чтобы попасть в диапазон операций для вычисления приоритета в строке 387. В массив tpr с таблицей приоритетов (строка 80) добавятся приоритеты новых операций (как в языке С). В подпрограмму operac добавляется генерация кода для новых операций.
Таким образом, потребуются следующие изменения текста транслятора C0.
Заменить строки:
79 /* пpиоpитеты: + - * / % ==!= < > <= >= (),; ++ -- = */
80 int tpr[16]= { 5,5,6,6,6,3, 3, 4,4,4, 4, 0,1,1,1,7, 7, 2 };
84 mravn,bravn,lskob,pskob,zpt,tchzpt,uvel,umen,prisv,
85 flskob,fpskob,ifsl,intsl,retsl,whilesl};
102 long int st2[27]= /* st2[i]=2**i (i=0..26) */
105 8388608,16777216,33554432,67108864};
133 nvir=st2[ident]|st2[chislo]|st2[minus]|st2[lskob]|st2[uvel]|st2[umen];
Вставить после строки 458:
char kop[3]; /* код операции: INC или DEC */
Заменить строку:
460 if (*t1<=1 && t2==1 && op!=prisv && op!=uvel && op!=umen)
Вставить после строки 489:
else if (op==uvel || op==umen) /* ++ или -- */
{ kop = (op==uvel)? "INC": "DEC";
if (*t1 == 0) /*нет 1-го операнда: префиксная оп-ция */
if(t2==3 && tabim[z2].vidob==1) /*2-й оп-д - пер-я*/
{ fprintf(fvih,"\t%s\t%s\n",kop,adrper(z2));
zopreg(z2,t2,"AX");
}
else oshibka(16); /* неверный тип операнда */
else
if(t2==0&&*t1==3&&tabim[*z1].vidob==1)/*имя++|имя--*/
{ zopreg(*z1,*t1,"AX");
fprintf(fvih,"\t%s\t%s\n",kop,adrper(*z1));
}
else oshibka(16); /* неверный тип операнда */
}
Вставить после строки 620:
else if (*usim=='+' || *usim=='-') /* + или - или ++ или -- */
{ c=*usim;
if (chsim() == c) /* ++ или -- */
{ if (c == '+') leksema=uvel; /* ++ */
else leksema=umen; /* -- */
chsim(); /* чтение символа след. лексемы */
}
else
leksema=leksim[c]; /* + или - */
}
Тестами послужат операторы-выражения с операциями ++ и --. Кроме ++ и --, требуются операции + и -, чтобы проверить правильность чтения этих лексем. Поскольку + и - имеют более низкий приоритет, для проверки учета приоритетов желательны также операции более высокого приоритета, чем ++ и -- (унарная операция изменения знака “-“).
Тестом может быть, например, программа со следующим фрагментом:
++x; y++; -x--; --y; x=-y+++5; x=++y+5; y=--x-5; x=y---5;
Объектный код этого фрагмента (считая x глобальной переменной, а y - локальной переменной со смещением -2) записан в три колонки:
; ++x; INC WORD PTR 2[BP] MOV AX,x
INC x PUSH AX PUSH AX
MOV AX,x MOV BX,5 MOV BX,5
; y++; POP AX POP AX
MOV AX,-2[BP] ADD AX,BX SUB AX,BX
INC WORD PTR -2[BP] PUSH AX PUSH AX
; -x--; POP AX POP AX
MOV AX,x MOV x,AX MOV -2[BP],AX
NEG AX; x=++y+5;; x=y---5;
PUSH AX INC WORD PTR -2[BP] MOV AX,-2[BP]
POP AX MOV AX,-2[BP] DEC WORD PTR -2[BP]
DEC x PUSH AX PUSH AX
; --y; MOV BX,5 MOV BX,5
DEC WORD PTR -2[BP] POP AX POP AX
MOV AX,-2[BP] ADD AX,BX SUB AX,BX
; x=-y+++5; PUSH AX PUSH AX
MOV AX,-2[BP] POP AX POP AX
NEG AX MOV x,AX MOV x,AX
PUSH AX; y=--x-5;
POP AX DEC x
Необходимо проверить не только текстуальную правильность получаемого объектного кода, но и корректность его выполнения, например, в следующей тестовой программе на расширенном языке С0.
int x;
print(z)
{ putn(z); putchar(32);
}
main()
{ int y;
x = 5; y=9;
++x; print(x);
y++; print(y);
-x--; print(x);
--y; print(y);
x=-y+++5; print(x); print(y);
x=++y+5; print(x); print(y);
y=--x-5; print(x); print(y);
x=y---5; print(x); print(y);
}
Определите самостоятельно ожидаемый результат исполнения этой тестовой программы.
Порядок выполнения работы
1. Разработать изменения грамматики и семантики языка и транслятора C0, необходимые для реализации заданной преподавателем дополнительной возможности языка C0.
2. Изменения транслятора описать с указанием номеров вставляемых, заменяемых и удаляемых строк его текста (в порядке возрастания номеров) и сопроводить кратким пояснением основных идей, как показано в приведенном выше примере.
3. Разработать тесты и провести комплексную отладку измененного транслятора.
4. Составить отчет, включающий описание изменений языка и транслятора, отладочные средства и результаты отладки.
5. Сдать работу, ответив на вопросы преподавателя по транслятору С0 и представленному отчету.
Дата публикования: 2015-03-29; Прочитано: 218 | Нарушение авторского права страницы | Мы поможем в написании вашей работы!