Язык вывода компилятора - LLVM IR против C

Для написания компилятора, в чем преимущества и недостатки использования LLVM IR против C для целевого языка? Я знаю, что оба они используются, и я думаю, что конечный машинный код был бы похож, если бы я использовал clang для компиляции C. Так что еще нужно учитывать?

4 ответа

Решение

Я использовал LLVM IR для нескольких бэкэндов компилятора и работал с компиляторами, которые используют C как бэкэнд. Одна вещь, которую я нашел, которая дала преимущество LLVM IR, - то, что это напечатано. Трудно сделать абсолютно некорректный вывод, не получая ошибок от библиотек LLVM.

На мой взгляд, проще поддерживать тесную взаимосвязь между исходным кодом и IR для отладки.

Кроме того, вы получаете все классные инструменты командной строки LLVM для анализа и обработки IR, который излучает ваш интерфейс.

Преимущества LLVM:

  1. JIT - вы можете скомпилировать и запустить свой код динамически. Конечно, то же самое возможно с C (например, используя встроенный tcc), но это гораздо менее надежный и портативный вариант.
  2. Вы можете запустить свои собственные оптимизационные проходы по сгенерированному IR.
  3. Отражение бесплатно - проверка сгенерированного кода намного проще с LLVM.
  4. Библиотека LLVM не такая большая, как большинство компиляторов Си (не считая tcc, конечно).

Недостатки LLVM:

  1. Код не переносимый, его нужно немного изменить в зависимости от цели. Существует несколько переносимое подмножество LLVM, но это все еще хитрая практика.
  2. Зависимость времени выполнения от библиотек C++, может быть немного проблемой.

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

Я буду использовать LLVM для обозначения фреймворка и LLVM IR для обозначения целевого языка.

C Преимущества

  1. Кроссплатформенность
  2. Отладка (пожалуйста, прочтите ниже. Это частично относится к пункту 4.)
  3. Совместимость
  4. Легкость использования

Преимущества LLVM IR

  1. Производительность
  2. Возможности настройки
  3. Объем памяти
  4. Сильный набор текста / Безопасность

C

  1. Существуют компиляторы C для всевозможных встроенных систем, хотя в последнее время LLVM получил больше целей. Можно утверждать, что C имеет небольшое преимущество перед LLVM IR (Промежуточное представление) в этой категории.

  2. Основное преимущество использования C вместо LLVM заключается в том, что сгенерированный код находится на более высоком уровне по сравнению с LLVM. Используя стандартные отладчики, такие как GDB, можно утверждать, что легче рассуждать о поведении сгенерированного кода. Также проще использовать отладчик, такой как GDB, для создания отладчика для языка, скомпилированного для C.

  3. Третий момент. Совместимость сложнее. Однако у C есть стандартизованный двоичный интерфейс приложения. Таким образом, легче писать библиотеки и связывать эти библиотеки с другими программами, написанными на C и / или C +. Тем не менее, многие языки, такие как Java, предоставляют стандартизированные интерфейсы для C.

  4. Можно утверждать, что легче начать и заставить что-то работать, выбрав C

LLVM

  1. C - язык довольно высокого уровня, и, если он не написан, идиоматически, производительность может снизиться (в зависимости от целевого компилятора и предположений, которые делает этот компилятор). Есть несколько статей, например, Backend llVM для GHC, которые иллюстрируют некоторые недостатки C и преимущества LLVM IR как целевого языка.

  2. Поскольку LLVM (фреймворк) построен как набор многократно используемых модулей, легко написать проходы для целевого языка для вашего конкретного целевого языка. Также проще написать собственный сборщик мусора (с 2020 года для этого есть некоторая поддержка). В случае с C это тоже возможно, и есть некоторые сборщики мусора, такие как Boehm GC. Однако C не предназначен для использования в качестве промежуточного языка.

  3. Объем памяти. Сгенерированный код C занимает больше памяти по сравнению с битовым кодом LLVM. Если вы компилируете и связываете большую систему, вы, вероятно, получите преимущества по времени компиляции, ориентированные на LLVM.

  4. В то время как C - это слабо типизированный язык. LLVM IR - строго типизированный. Следовательно, можно утверждать, что безопаснее использовать LLVM IR.

Архитектуры и операционные системы, для которых явно нет CLANG, или для которых он находится в экспериментальном состоянии.

C более широко распространен, но LLVM IR позволяет ложно кормить двигатель LLVM. Не все пути к ИК одинаковы.

Другие вопросы по тегам