Генерация кода для операторов if - компиляторы - PullRequest
1 голос
/ 16 февраля 2011

Я занимаюсь разработкой компилятора для языка, подобного Си, и испытываю некоторые трудности на этапах семантического анализа и генерации кода. Мои вопросы следующие: 1) Для оператора if следующий синтаксис:

if (expression) then
statement1;
statement2;
else
statement3;
end if;

Теперь в моем целевом коде это должен быть трехадресный код с операторами go, поэтому он должен

look something like:
if (Rx)  // Rx is the register where the expression is evaluated and stored
go to X1 //for if part
X2 // for else part;

Итак, теперь мой вопрос: как мне сгенерировать адреса для операторов go?

2) Этот вопрос о семантическом анализе: Я был в состоянии построить и использовать таблицу символов для одной функции. Какой подход я должен использовать для создания таблиц символов для вызовов функций? Другими словами для разных лексических уровней? Я знаю, что это должно как-то включать несколько деревьев. Одно дерево для одной функции. Но как подходить к указанию на другое дерево где-то посередине программы?

Я новичок, и поэтому любые предложения / мысли будут с благодарностью.

Ответы [ 2 ]

1 голос
/ 16 февраля 2011

Это зависит от того, как и когда ваш компилятор будет генерировать код.

Если ваш компилятор генерирует код последовательно (от первой строки кода до последней), то единственное, что вы можете сделать, это запомнить места, куда вы хотите перейти (сохранить их в таблице), и исправьте код после того, как все было сгенерировано.

Если ваш компилятор генерирует код снизу вверх (от самого внутреннего оператора до самого внешнего оператора), и ваша базовая машина (физическая или виртуальная) поддерживает относительные переходы, то вы можете просто сгенерировать относительные переходы при генерации кода , Например.

Предположим, у вас есть этот кусок кода:

if (condition) then
   someexpressionsA
else
   someexpressionsB
endif;

Компиляция снизу вверх означает, что код будет сгенерирован следующим образом:

  • сначала код для некоторых выражений A
  • тогда код для некоторых выраженийB
  • затем код для оператора if-then-else-endif

Предположим, что наш компилятор сгенерировал код для некоторых выражений A, называемый codeblockA (то же самое для B). Тогда код для оператора if-then-else-endif можно записать так (псевдокод):

  • Проверить состояние
  • если условие ложно, перейти к следующему размеру (codeblockA + 1) инструкции
  • codeblockA
  • прыжок sizeof (кодовый блок B) далее
  • codeblockB

Все может стать сложнее, если условие содержит несколько условий (и, или, ...), но приведенный выше пример должен помочь вам начать работу.

0 голосов
/ 16 февраля 2011

Вы генерируете код немедленно, без прохода "ассемблер", который разрешает символьные метки?В этом случае вам необходимо создать таблицу со всеми метками и инструкциями ветвления, а затем повторно создать код, когда все метки будут сгенерированы.

...