Так же, как и для лабораторных работ № 2 и 3, модули, реализующие генератор списка триад, в лабораторной работе № 4 разделены на две группы:
• модули, программный код которых не зависит от входного языка;
• модули, программный код которых зависит от входного языка.
В первую группу входят модули:
• Triads – описывает структуры данных для представления триад;
• TrdOpt – реализует два алгоритма оптимизации: методом свертки объектного кода и методом исключения лишних операций;
• FormLab4 – описывает интерфейс с пользователем.
Во вторую группу входят модули:
• TrdType – описывает допустимые типы триад и их текстовое представление;
• TrdMake – строит список триад на основе дерева синтаксического разбора;
• TrdCal с – обеспечивает вычисление значений для триад разных типов при свертке объектного кода.
Такое разбиение на модули позволяет использовать те же самые структуры данных для организации нового генератора списка триад при изменении входного языка.
Кроме этих модулей для реализации лабораторной работы № 4 используются следующие программные модули:
• TblElem и FncTree – позволяют работать с комбинированной таблицей идентификаторов (созданы при выполнении лабораторной работы № 1);
• LexType, LexElem, и LexAuto – обеспечивают работу лексического распознавателя (созданы при выполнении лабораторной работы № 2);
• SyntRule и SyntSymb – обеспечивают работу синтаксического распознавателя (созданы при выполнении лабораторной работы № 3).
Кратко опишем содержание программных модулей, используемых для организации генератора списка триад.
Модуль TrdType содержит структуры данных, которые описывают допустимые типы триад.
Он содержит следующие важные типы данных и переменные:
• TTriadType – перечисление всех возможных типов триад;
• TriadStr – массив строковых обозначений для всех типов триад;
• TriaD1ineSet – множество тех триад, которые являются линейными операциями (оно важно для оптимизации и для порождения кода).
Модуль Triads содержит структуры данных, которые описывают триады и список триад. Эти структуры зависят от реализации компилятора, но не зависят от входного языка.
Он содержит следующие важные структуры данных:
• TOperand – описывает операнд триады;
• TTriad – описывает триаду и все связанные с нею данные;
• TTriaD1ist – описывает список триад.
Структура TOperand описывает операнд триады. Она содержит следующие данные:
• ОрТуре – тип операнда, который может принимать три значения:
– OPC0NST – константа;
– OPVAR – переменная (идентификатор);
– OPLINK – ссылка на другую триаду;
• и дополнительную информацию по операнду:
– ConstVal – значение (для константы);
– VarLink – ссылка на таблицу идентификаторов (для переменной);
– TriadNum – номер триады (для ссылки на триаду).
Один из вопросов, который необходимо было решить при реализации операндов триад, состоял в следующем: что использовать для описания ссылки на триаду – непосредственно ссылку на тип данных (указатель) или номер триады в списке?
Оба варианта имеют свои преимущества и недостатки:
• при использовании указателя легче осуществлять доступ к триаде (не надо выбирать ее из списка), не надо менять указатели при перемещении триад в списке, но при удалении любой триады из списка нужно корректно менять все указатели на эту триаду, какие только есть;
• при использовании номера триады легче порождать список триад по дереву разбора, но при любом перемещении и удалении триад из списка нужно пересчитывать все номера.
Какой вариант выбрать, решает разработчик компилятора. В данном случае автор выбрал второй вариант (номер триады, а не указатель на нее), поскольку наглядная иллюстрация алгоритмов оптимизации требует удаления триад, а перестановка указателей при каждом удалении намного сложнее, чем изменение номеров (этот недостаток оказался решающим). Но поскольку в реальном компиляторе не нужно иллюстрировать работу алгоритмов оптимизации выводом списка триад (достаточно просто не порождать код для триад с типами С и same), в этом случае указатели, по мнению автора, были бы предпочтительнее.
Структура TTriad описывает триаду и все связанные с ней данные. Она содержит следующие поля данных:
• TriadType – тип триады (один из перечисленных в типе TTriadType в модуле TrdType);
• Operands – массив операндов триады (из двух операндов типа TOperand);
• Info – дополнительная информация о триаде для алгоритмов оптимизации;
• IsLinked – флаг, сигнализирующий о том, что на триаду имеется ссылка из другой триады, обеспечивающей передачу управления (типа IF или JMP).
Для хранения дополнительной информации можно было использовать один из двух подходов: хранить ее непосредственно в самой триаде или хранить внутри триады только ссылку (указатель), а саму дополнительную информацию размещать во внешней структуре данных.