Spec-Zone.ru › GCC 13

3.23 Модули C++

Модули — это функция языка C++20. Как следует из названия, они предоставляют модульную систему компиляции, призванную обеспечить как более быструю сборку, так и лучшую изоляцию библиотек. Статья «Слияние модулей» https://wg21.link/p1103 предоставляет наиболее легко читаемый набор изменений в стандарт, хотя он не охватывает последующие изменения.

Поддержка модулей в G++ неполная. Помимо ошибок, известные отсутствующие части включают:

Частный фрагмент модуля

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

Правила видимости определения разделов

Сущности могут быть определены в разделах реализации, и эти определения недоступны за пределами модуля. Это не реализовано, и определения доступны для использования вне модуля.

Текстовое слияние доступных сущностей GM

Сущности могут быть многократно определены в разных единицах заголовков. Их необходимо дедуплицировать, и это реализовано при импорте или когда импорт переопределяет текстово определённую сущность. Однако обратное не реализовано — текстовое переопределение сущности, определённой в импортированной единице заголовка. Выдается ошибка переопределения.

Правила ссылки на локальный блок трансляции

Статьи p1815 (https://wg21.link/p1815) и p2003 (https://wg21.link/p2003) добавляют ограничения на то, на какие сущности может ссылаться экспортируемый регион (например, какие сущности может ссылаться экспортируемое определение шаблона). Эти ограничения не полностью реализованы.

Единицы заголовков стандартной библиотеки

Стандартная библиотека не предоставляется в виде импортируемых единиц заголовков. Если вы хотите импортировать такие единицы, вы должны предварительно их явно скомпилировать. Если вы не сделаете это тщательно, у вас могут появиться несколько объявлений, которые механизм модулей должен объединить — использование ресурсов компилятора может зависеть от того, как вы разделили файлы заголовков на единицы заголовков.

Модульная компиляция не включается только с помощью опции -std=c++20. Вы должны явно включить её с помощью опции -fmodules-ts. Она независима от выбранной версии языка, хотя в версиях до C++20, конечно, является расширением.

Новые постфиксы для файлов исходного кода не требуются и не поддерживаются. Если вы хотите использовать нестандартный постфикс (см. Параметры управления видом вывода), вам также необходимо указать опцию -x c++.2

Компиляция единицы интерфейса модуля создаёт дополнительный выходной файл (помимо объектного или машинного кода), называемый Compiled Module Interface (CMI). В нём кодируются экспортированные объявления модуля. Импорт модуля считывает CMI. Граф импорта представляет собой ориентированный ациклический граф (DAG). Вы должны скомпилировать импорты перед импортером.

Файлы заголовков могут сами компилироваться в единицы заголовков, что является переходной возможностью, направленной на ускорение компиляции. Для включения этого используется опция -fmodule-header, и подразумевает опцию -fmodules-ts. Эти CMIs имеют имена, соответствующие полному пути к исходному файлу заголовка, и могут быть полными путями, содержащими подкаталоги. Если файл заголовка находится по абсолютному пути, расположение CMI всё равно относительно корневого каталога CMI.

Поскольку у файлов заголовков часто нет постфикса, вам обычно нужно указать опцию -x, чтобы сообщить компилятору, что исходный файл — файл заголовка. Вы можете использовать -x c++-header, -x c++-user-header или -x c++-system-header. При использовании совместно с -fmodules-ts, все они подразумевают соответствующую опцию -fmodule-header. Последние два варианта используют пользовательский или системный путь включения для поиска указанного файла. Это позволяет, например, компилировать файлы заголовков стандартной библиотеки как единицы заголовков, не зная точно, где они установлены. Указание языка как одного из этих вариантов также запрещает вывод объектного файла, так как у файлов заголовков нет связанного объектного файла.

Опция -fmodule-only отключает генерацию связанного объектного файла при компиляции интерфейса модуля. Генерируется только CMI. Эта опция подразумевается при использовании опции -fmodule-header.

Опции -flang-info-include-translate и -flang-info-include-translate-not указывают, происходит ли трансляция включений или нет. Без аргумента первая укажет все трансляции включений. Вторая укажет все не трансляции файлов включений, не известные как преднамеренно текстовые. С аргументом запрашиваются сведения о трансляции включения файла заголовка с указанным постфиксом. Вы можете повторить этот формат для нескольких различных файлов заголовков. Эта опция может быть полезна для определения того, происходит ли трансляция включений — если она работает правильно, она ведёт себя так, как будто её нет.

Опция -flang-info-module-cmi может использоваться для определения того, откуда компилятор считывает CMI. Без этой опции компилятор молчит, когда такое чтение выполняется успешно. У этой опции есть необязательный аргумент, который ограничит уведомление только набором указанных модулей или единиц заголовков.

Опция -Winvalid-imported-macros заставляет все импортированные макросы разрешаться в конце компиляции. Без этого импортированные макросы разрешаются только при расширении или (повторном) определении. Эта опция обнаруживает конфликтующие определения импорта для всех макросов.

Подробности о семействе опций -fmodule-mapper см. в разделе Module Mapper.

  • Module Mapper
  • Module Preprocessing
  • Compiled Module Interface

Примечания

(2)

Некоторым пользователям нравится различать файлы интерфейса модуля с помощью нового постфикса, например, называя исходный файл module.cppm, что требует обучения всех инструментов новому постфиксу. Другой вариант, например, именования module-m.cpp, был бы менее инвазивным.

© Free Software Foundation
Licensed under the GNU Free Documentation License, Version 1.3.
https://gcc.gnu.org/onlinedocs/gcc-13.3.0/gcc/C_002b_002b-Modules.html

Spec-Zone.ru

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