Подтвердить что ты не робот

Модули С++ и С++ ABI

Я читал о предложении модулей С++ (последний проект), но я не совсем понимаю, какие проблемы (цели) решить.

Является ли его целью предоставить модуль, построенный одним компилятором, для использования любым другим компилятором (например, в той же ОС/архитектуре)? То есть, составляет ли предложение количество для стандартизации С++ ABI?

Если нет, есть ли еще какое-то предложение, которое будет стандартизировать С++ ABI и позволить компиляторам взаимодействовать?

4b9b3361

Ответ 1

Предварительно скомпилированные заголовки (PCH) - это специальные файлы, которые могут быть созданы некоторыми компиляторами для файла .cpp. То, что они есть, это именно то, что: предварительно скомпилированный исходный код. Это исходный код, который был передан через компилятор и встроен в формат, зависящий от компилятора.

PCHs обычно используются для ускорения компиляции. Вы помещаете обычно используемые заголовки в PCH, а затем просто включаете PCH. Когда вы выполняете #include на PCH, ваш компилятор фактически не выполняет обычную работу #include. Вместо этого они загружают эти предварительно скомпилированные символы непосредственно в компилятор. Не работает препроцессор С++. Отсутствует компилятор С++. Нет #, включая миллион разных файлов. Загружается один файл, и символы отображаются полностью в рабочей области вашего компилятора.

Я упоминаю все это, потому что модули являются PCH в их идеальной форме. PCH - это в основном гигантский взлом, построенный поверх системы, которая не позволяет использовать реальные модули. Назначение модулей в конечном итоге - возможность взять файл, сгенерировать файл модуля, специфичный для компилятора, который содержит символы, а затем другой файл загружает этот модуль по мере необходимости. Символы предварительно скомпилированы, поэтому снова не нужно # включать кучу вещей, запускать компилятор и т.д. В вашем коде сказано import thing.foo, и оно появляется.

Посмотрите на любой из стандартных библиотек библиотеки STL. Возьмите <map>, например. Коэффициенты хороши, что этот файл является либо гигантским, либо имеет много #include других файлов, которые делают полученный файл гигантским. Это много синтаксического анализа на С++, который должен произойти. Это должно произойти для каждого .cpp файла с #include <map>. Каждый раз, когда вы компилируете исходный файл, компилятор должен перекомпилировать то же самое. Над. И более. И снова.

Изменяется ли <map> между компиляциями? Нет, но ваш компилятор не может этого знать. Поэтому он должен продолжать перекомпилировать его. Каждый раз, когда вы касаетесь файла .cpp, он должен скомпилировать каждый заголовок, который включает этот .cpp файл. Даже если вы не касались этих заголовков или исходных файлов, которые затрагивают эти заголовки.

Файлы PCH были способом обойти эту проблему. Но они ограничены, потому что они просто хак. Вы можете включить только один файл на .cpp, потому что это должно быть первое, что включено в .cpp файлы. И поскольку есть только один PCH, если вы делаете что-то, что изменяет PCH (например, добавляет ему новый заголовок), вам нужно перекомпилировать все в этом PCH.

Модули практически не имеют ничего общего с кросс-компилятором ABI (хотя наличие одного из них было бы неплохо, а модули могли бы немного упростить его определение). Их основная цель - ускорить время компиляции.

Ответ 2

Модули - это то, что предлагают Java, С# и многие другие современные языки. Они значительно сокращают время компиляции просто потому, что код, который в сегодняшнем заголовке не нужно разбирать снова и снова, каждый раз, когда он включается. Когда вы скажете #include <vector>, содержимое <vector> будет скопировано в текущий файл. #include действительно есть не что иное, как копирование и вставка.

В мире модулей вы просто говорите import std.vector;, например, и компилятор загружает таблицу запроса/символа этого модуля. Файл модуля имеет формат, позволяющий компилятору разбирать и использовать его. Он также анализируется только один раз, когда модуль компилируется. После этого созданный компилятором файл модуля запрашивается только для необходимой информации.

Поскольку файлы модулей генерируются компилятором, они будут довольно тесно связаны с внутренним представлением компилятора кода С++ (AST) и, как таковое, скорее всего, не будут переносимыми (например, сегодня .o/.so/.a, из-за перебора имени и т.д.).

Ответ 3

Модули на С++ должны быть в первую очередь лучше, чем сегодняшние решения, то есть когда библиотека состоит из файла *.so и *.h с API. Они должны решить проблемы, которые сегодня имеют #includes, то есть:

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

Несмотря на то, что говорит Xeo, модули не существуют на Java или С#. Фактически, на этих языках "загрузка модулей" опирается на "хорошо", здесь у вас есть CLASSPATH и поиск через него, чтобы найти любые модули, которые могут предоставлять символы, которые фактически использует исходный файл ". Объявление" import "в Java вообще не является" запросом модуля "- так же, как" использование "в С++ (" import ns.ns2. * "В Java такое же, как" использование пространства имен ns:: ns2" в С++), Я не думаю, что такое решение можно использовать в С++. Ближайшее приближение, которое я могу себе представить, это пакеты в Vala или модули в Tcl (версии 8.5).

Я предполагаю, что модули С++ скорее не могут быть кросс-платформенными, так и динамически загруженными (для них требуется специальный загрузчик динамического модуля С++ - это не невозможно, но сегодня трудно определить). Они определенно зависят от платформы и также должны быть настроены по запросу. Но стабильный С++ ABI практически необходим только в пределах одной системы, как и сейчас с С++ ABI.