Spec-Zone.ru › GCC 12

3.22 Использование предварительно скомпилированных заголовков

Часто в больших проектах много файлов заголовков, которые включаются в каждый исходный файл. Время, которое компилятор тратит на обработку этих файлов заголовков снова и снова, может составлять почти всё время, необходимое для сборки проекта. Для ускорения сборки GCC позволяет вам предварительно компилировать файл заголовка.

Чтобы создать файл предварительно скомпилированного заголовка, просто скомпилируйте его, как любой другой файл, при необходимости используя опцию -x, чтобы заставить драйвер обрабатывать его как файл заголовка C или C++. Возможно, вам потребуется использовать инструмент, такой как make для поддержания актуальности предварительно скомпилированного заголовка при изменении заголовков, которые он содержит.

Файл предварительно скомпилированного заголовка ищется, когда #include встречается в компиляции. При поиске включаемого файла (см. Путь поиска в Препроцессоре C) компилятор ищет предварительно скомпилированный заголовок в каждом каталоге перед тем, как искать файл включения в этом каталоге. Искомое имя — это имя, указанное в #include с добавленным ‘.gch’. Если предварительно скомпилированный файл заголовка не может быть использован, он игнорируется.

Например, если у вас #include "all.h", и у вас all.h.gch в той же директории, что и all.h, то предварительно скомпилированный файл заголовка используется, если это возможно, в противном случае используется исходный заголовок.

В качестве альтернативы, вы можете поместить предварительно скомпилированный файл заголовка в каталог и использовать -I для обеспечения того, чтобы этот каталог просматривался перед (или вместо) каталогом, содержащим исходный заголовок. Затем, если вы хотите убедиться, что предварительно скомпилированный файл заголовка всегда используется, вы можете поместить в этот каталог файл с тем же именем, что и исходный заголовок, содержащий команду #error.

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

Если вам нужно предварительно скомпилировать один и тот же файл заголовка для разных языков, целевых платформ или параметров компилятора, вы можете вместо этого создать каталог с именем, подобным all.h.gch, и поместить каждый предварительно скомпилированный заголовок в каталог, возможно, используя -o. Неважно, как вы назовете файлы в каталоге; каждый предварительно скомпилированный заголовок в каталоге рассматривается. Первый встреченный предварительно скомпилированный заголовок в каталоге, который является допустимым для данной компиляции, используется; они просматриваются без определенного порядка.

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

Файл предварительно скомпилированного заголовка может быть использован только при соблюдении следующих условий:

  • Только один предварительно скомпилированный заголовок может быть использован в конкретной компиляции.
  • Предварительно скомпилированный заголовок не может быть использован после того, как встречен первый токен C. Вы можете иметь директивы препроцессора перед предварительно скомпилированным заголовком; вы не можете включить предварительно скомпилированный заголовок изнутри другого заголовка.
  • Файл предварительно скомпилированного заголовка должен быть сгенерирован для того же языка, что и текущая компиляция. Вы не можете использовать предварительно скомпилированный заголовок C для компиляции C++.
  • Файл предварительно скомпилированного заголовка должен быть создан тем же бинарником компилятора, что и текущая компиляция.
  • Любые макросы, определенные до включения предварительно скомпилированного заголовка, должны быть определены таким же образом, как и при создании предварительно скомпилированного заголовка, или не должны влиять на предварительно скомпилированный заголовок, что обычно означает, что они вообще не появляются в предварительно скомпилированном заголовке.

    Опция -D является одним из способов определения макроса перед включением предварительно скомпилированного заголовка; использование #define также может это сделать. Существуют также некоторые опции, которые неявно определяют макросы, такие как -O и -Wdeprecated; то же правило применяется к макросам, определенным таким образом.

  • Если при использовании предварительно скомпилированного заголовка выводятся отладочные данные, используя -g или аналогичное, то такой же вид отладочных данных должен был выводиться при создании предварительно скомпилированного заголовка. Однако предварительно скомпилированный заголовок, созданный с использованием -g, может быть использован в компиляции, когда отладочная информация не выводится.
  • Обычно должны использоваться те же опции -m при создании и использовании предварительно скомпилированного заголовка. См. Параметры подмодели для случаев, когда это правило ослаблено.
  • Каждый из следующих параметров должен быть таким же при создании и использовании предварительно скомпилированного заголовка:
    -fexceptions
  • Некоторые другие параметры командной строки, начинающиеся с -f, -p или -O, должны быть определены таким же образом, как и при создании предварительно скомпилированного заголовка. В настоящее время неясно, какие параметры можно изменять, а какие нет; самый безопасный выбор — использовать точно такие же параметры при создании и использовании предварительно скомпилированного заголовка. Известно, что следующие параметры безопасны:
    -fmessage-length=  -fpreprocessed  -fsched-interblock 
    -fsched-spec  -fsched-spec-load  -fsched-spec-load-dangerous 
    -fsched-verbose=number  -fschedule-insns  -fvisibility= 
    -pedantic-errors
  • Случайная адресация пространства памяти (ASLR) может привести к тому, что файлы PCH не будут идентичны с бинарной точки зрения. Если вы полагаетесь на стабильное содержимое файлов PCH, отключите ASLR при создании файлов PCH.

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

Если вы используете разные параметры при создании и использовании предварительно скомпилированного заголовка, фактическое поведение является смесью поведения для этих параметров. Например, если вы используете -g для создания предварительно скомпилированного заголовка, но не при его использовании, вы можете или не можете получить отладочную информацию для процедур в предварительно скомпилированном заголовке.

Далее: Модули C++, Предыдущее: Переменные среды, Наверх: Вызов GCC [Оглавление][Индекс]

© Free Software Foundation
Licensed under the GNU Free Documentation License, Version 1.3.
https://gcc.gnu.org/onlinedocs/gcc-12.2.0/gcc/Precompiled-Headers.html

Spec-Zone.ru

Настройки Оффлайн Что нового Помощь О нас
Spec-Zone .ru
спецификации, руководства, описания, API