6.31.1 Общие атрибуты функций
Следующие атрибуты поддерживаются на большинстве целевых платформ.
alias ("target")-
Атрибут
aliasзаставляет объявление быть сгенерированным как псевдоним для другого символа, который должен быть указан. Например,void __f () { /* Do something. */; } void f () __attribute__ ((weak, alias ("__f")));определяет ‘f’ как слабый псевдоним для ‘__f’. В C++, должно использоваться закодированное имя целевой платформы. Ошибка возникает, если ‘__f’ не определено в том же блоке трансляции.
Для использования этого атрибута требуется поддержка ассемблера и объектных файлов, и он может быть недоступен на всех целевых платформах.
aligned (alignment)-
Этот атрибут задаёт минимальное выравнивание функции, измеряемое в байтах.
Вы не можете использовать этот атрибут для уменьшения выравнивания функции, только для его увеличения. Однако, когда вы явно задаёте выравнивание функции, это переопределяет действие опции -falign-functions (см. Опции оптимизации) для этой функции.
Обратите внимание, что эффективность атрибутов
alignedможет быть ограничена внутренними ограничениями вашего компоновщика. На многих системах компоновщик может только организовать выравнивание функций до определённого максимального значения. (Для некоторых компоновщиков максимальное поддерживаемое выравнивание может быть очень маленьким.) См. документацию вашего компоновщика для получения дополнительной информации.Атрибут
alignedтакже может быть использован для переменных и полей (см. Атрибуты переменных). alloc_align-
Атрибут
alloc_alignиспользуется для указания компилятору, что возвращаемое значение функции указывает на память, где минимальное выравнивание возвращаемого указателя задаётся одним из параметров функции. GCC использует эту информацию для улучшения анализа выравнивания указателей.Параметр функции, обозначающий выравнивание выделенной памяти, задаётся одним целым числом, номер которого является аргументом атрибута. Нумерация аргументов начинается с единицы.
Например,
void* my_memalign(size_t, size_t) __attribute__((alloc_align(1)))
объявляет, что
my_memalignвозвращает память с минимальным выравниванием, заданным параметром 1. alloc_size-
Атрибут
alloc_sizeиспользуется для указания компилятору, что возвращаемое значение функции указывает на память, где размер задаётся одним или двумя параметрами функции. GCC использует эту информацию для повышения точности__builtin_object_size.Параметр(ы) функции, обозначающий(е) размер выделенной памяти, задаются одним или двумя целыми числами, передаваемыми в качестве аргументов атрибута. Размер выделенной памяти либо равен значению указанного параметра функции, либо равен произведению указанных параметров функции. Нумерация аргументов начинается с единицы.
Например,
void* my_calloc(size_t, size_t) __attribute__((alloc_size(1,2))) void* my_realloc(void*, size_t) __attribute__((alloc_size(2)))
объявляет, что
my_callocвозвращает память размера, заданного произведением параметра 1 и 2, и чтоmy_reallocвозвращает память размера, заданного параметром 2. always_inline-
Обычно функции не встраиваются, если не задана оптимизация. Для функций, объявленных встроенными, этот атрибут встраивает функцию независимо от любых ограничений, которые в противном случае применяются к встраиванию. Отсутствие встраивания такой функции диагностируется как ошибка. Обратите внимание, что если такая функция вызывается косвенно, компилятор может или не может её встроить в зависимости от уровня оптимизации, а отсутствие встраивания косвенного вызова может или не может быть диагностировано.
artificial-
Этот атрибут полезен для небольших встроенных обёртков, которые, если это возможно, должны отображаться во время отладки как единица. В зависимости от формата отладочной информации он либо помечает функцию как искусственную, либо использует расположение вызывающей функции для всех инструкций внутри встроенного тела.
assume_aligned-
Атрибут
assume_alignedиспользуется для указания компилятору, что возвращаемое значение функции указывает на память, где минимальное выравнивание возвращаемого указателя задаётся первым аргументом. Если атрибут имеет два аргумента, второй аргумент — смещение невыравнивания.Например
void* my_alloc1(size_t) __attribute__((assume_aligned(16))) void* my_alloc2(size_t) __attribute__((assume_aligned(32, 8)))
объявляет, что
my_alloc1возвращает указатель, выровненный на 16 байт, и чтоmy_alloc2возвращает указатель, значение которого по модулю 32 равно 8. bnd_instrument-
Атрибут
bnd_instrumentдля функций используется для информирования компилятора о том, что функция должна быть проинструментирована при компиляции с опцией -fchkp-instrument-marked-only. bnd_legacy-
Атрибут
bnd_legacyдля функций используется для информирования компилятора о том, что функция не должна быть проинструментирована при компиляции с опцией -fcheck-pointer-bounds. cold-
Атрибут
coldдля функций используется для информирования компилятора о том, что функция вряд ли будет выполнена. Функция оптимизируется для размера, а не для скорости, и на многих целевых платформах она размещается в специальном подраздёле секции кода, так что все холодные функции появляются близко друг к другу, улучшая локальность кода для нехолодных частей программы. Пути, ведущие к вызовам холодных функций внутри кода, отмечаются как маловероятные механизмом предсказания ветвлений. Поэтому полезно отмечать функции, используемые для обработки маловероятных условий, таких какperror, как холодные для улучшения оптимизации горячих функций, которые в редких случаях вызывают отмеченные функции.Когда доступен обратный отклик профилей, через -fprofile-use, холодные функции автоматически обнаруживаются, и этот атрибут игнорируется.
const-
Многие функции не проверяют никакие значения, кроме своих аргументов, и не оказывают никакого влияния, кроме возврата значения. Вызовы таких функций подходят для оптимизации, например, для исключения общих подвыражений. Атрибут
constнакладывает более строгие ограничения на определение функции, чем аналогичный атрибутpureниже, потому что он запрещает функции чтение глобальных переменных. Соответственно, наличие атрибута в объявлении функции позволяет GCC генерировать более эффективный код для некоторых вызовов функции.Обратите внимание, что функция, имеющая указательные аргументы и проверяющая данные, на которые указывают эти указатели, не должна быть объявлена
const. Аналогично, функция, вызывающая не-constфункцию, обычно не должна бытьconst. Посколькуconstфункция не может иметь побочных эффектов, для такой функции не имеет смысла возвращатьvoid. Объявление такой функции диагностируется. constructordestructorconstructor (priority)destructor (priority)-
Атрибут
constructorзаставляет функцию вызываться автоматически перед входом вmain (). Аналогично, атрибутdestructorзаставляет функцию вызываться автоматически после завершенияmain ()или вызоваexit (). Функции с этими атрибутами полезны для инициализации данных, которые неявно используются во время выполнения программы.Вы можете указать необязательный целочисленный приоритет для управления порядком выполнения функций конструкторов и деструкторов. Конструктор с меньшим номером приоритета выполняется перед конструктором с большим номером приоритета; обратные отношения сохраняются для деструкторов. Таким образом, если у вас есть конструктор, который выделяет ресурс, и деструктор, который освобождает тот же ресурс, обе функции обычно имеют одинаковый приоритет. Приоритеты функций конструкторов и деструкторов совпадают с приоритетами, заданными для объектов C++ на уровне пространства имён (см. Атрибуты C++). Однако в настоящее время порядок вызова конструкторов для объектов C++ со статической областью хранения и функций, помеченных атрибутом
constructor, не определён. При смешанных объявлениях атрибутinit_priorityможет быть использован для навязывания конкретного порядка. deprecateddeprecated (msg)-
Атрибут
deprecatedприводит к появлению предупреждения, если функция используется где-либо в исходном файле. Это полезно для выявления функций, которые, как ожидается, будут удалены в будущей версии программы. Предупреждение также включает местоположение объявления устаревшей функции, что позволяет пользователям легко найти дополнительную информацию о причинах устаревания функции или о том, что следует сделать вместо неё. Обратите внимание, что предупреждения возникают только при использовании:int old_fn () __attribute__ ((deprecated)); int old_fn (); int (*fn_ptr)() = old_fn;
приводит к появлению предупреждения на строке 3, но не на строке 2. Необязательный аргумент msg, который должен быть строкой, выводится в предупреждении, если он присутствует.
Атрибут
deprecatedтакже может использоваться для переменных и типов (см. Атрибуты переменных, см. Атрибуты типов). error ("message")warning ("message")-
Если атрибут
errorилиwarningиспользуется в объявлении функции, а вызов такой функции не исключается благодаря удалению неиспользуемого кода или другим оптимизациям, диагностируется ошибка или предупреждение (соответственно), содержащее сообщение. Это полезно для проверки во время компиляции, особенно вместе с__builtin_constant_pи встроенными функциями, где проверка аргументов встроенной функции невозможна с помощьюextern char [(condition) ? 1 : -1];трюков.Хотя возможно оставить функцию неопределённой и тем самым вызвать ошибку компоновки (для определения функции с сообщением в секции
.gnu.warning*), при использовании этих атрибутов проблема диагностируется раньше и с точным местоположением вызова, даже в присутствии встроенных функций или при отсутствии отладочной информации. externally_visible
-
Этот атрибут, прикреплённый к глобальной переменной или функции, аннулирует действие командной строки -fwhole-program, поэтому объект остаётся видимым вне текущей единицы компиляции.
Если -fwhole-program используется вместе с -flto и
goldиспользуется в качестве плагина компоновщика, атрибутыexternally_visibleавтоматически добавляются к функциям (но не переменным пока из-за текущей проблемыgold), к которым осуществляется доступ за пределами объектов LTO в соответствии с файлом разрешений, созданнымgold. Для других компоновщиков, которые не могут сгенерировать файл разрешений, явные атрибутыexternally_visibleвсё ещё необходимы. flatten-
В целом, встраивание в функцию ограничено. Для функции, помеченной этим атрибутом, каждый вызов внутри этой функции встраивается, если это возможно. Будет ли сама функция рассматриваться для встраивания, зависит от её размера и текущих параметров встраивания.
format (archetype, string-index, first-to-check)-
Атрибут
formatуказывает, что функция принимает аргументы в стилеprintf,scanf,strftimeилиstrfmon, которые должны быть проверены на тип по отношению к строке формата. Например, объявление:extern int my_printf (void *my_object, const char *my_format, ...) __attribute__ ((format (printf, 2, 3)));приводит к тому, что компилятор проверяет аргументы в вызовах к
my_printfна соответствие строке формата стиляprintfаргументmy_format.Параметр archetype определяет, как интерпретируется строка формата, и должен быть
printf,scanf,strftime,gnu_printf,gnu_scanf, илиgnu_strftimeилиstrfmon. (Вы также можете использовать__printf__,__scanf__,__strftime__или__strfmon__. На целевых платформах MinGW также присутствуютms_printf,ms_scanf, иms_strftime. Значения archetype, такие какprintf, относятся к форматам, принимаемым системной библиотекой C, в то время как значения, начинающиеся с ‘gnu_’, всегда относятся к форматам, принимаемым библиотекой GNU C. На целевых платформах Microsoft Windows значения, начинающиеся с ‘ms_’, относятся к форматам, принимаемым библиотекой msvcrt.dll. Параметр string-index указывает, какой аргумент является аргументом строки формата (начиная с 1), а first-to-check — номер первого аргумента, который нужно проверить по отношению к строке формата. Для функций, где аргументы недоступны для проверки (таких какvprintf), укажите третий параметр как ноль. В этом случае компилятор проверяет только соответствие строки формата. Для форматовstrftimeтретий параметр должен быть равен нулю. Поскольку у нестатических методов C++ есть неявный аргументthis, аргументы таких методов должны учитываться с двух, а не с одного, при указании значений для string-index и first-to-check.В приведенном выше примере строка формата (
my_format) является вторым аргументом функцииmy_print, а аргументы для проверки начинаются с третьего аргумента, поэтому правильными параметрами для атрибута формата являются 2 и 3.Атрибут
formatпозволяет идентифицировать собственные функции, принимающие строки формата в качестве аргументов, чтобы GCC мог проверять вызовы этих функций на наличие ошибок. Компилятор всегда (если не используется -ffreestanding или -fno-builtin) проверяет форматы стандартных функций библиотекиprintf,fprintf,sprintf,scanf,fscanf,sscanf,strftime,vprintf,vfprintfиvsprintf, когда такие предупреждения запрошены (с помощью -Wformat), поэтому нет необходимости изменять заголовочный файл stdio.h. В режиме C99 также проверяются функцииsnprintf,vsnprintf,vscanf,vfscanfиvsscanf. За исключением строго соответствия стандарту C, также проверяется функция X/Openstrfmon, а такжеprintf_unlockedиfprintf_unlocked. См. Параметры, контролирующие диалект C.Для диалектов Objective-C,
NSString(или__NSString__) распознаются в том же контексте. Объявления, включающие эти атрибуты формата, анализируются на правильность синтаксиса, однако результат проверки таких строк формата пока не определён и не выполняется этой версией компилятора.Целевая платформа также может предоставлять дополнительные типы проверок формата. См. Проверки формата, специфичные для конкретных целевых машин.
format_arg (string-index)-
Атрибут
format_argуказывает, что функция принимает строку формата для функции в стилеprintf,scanf,strftimeилиstrfmonи модифицирует её (например, для перевода на другой язык), поэтому результат можно передать функции в стилеprintf,scanf,strftimeилиstrfmon(при этом оставшиеся аргументы функции формата остаются такими же, как и для немодифицированной строки). Например, объявление:extern char * my_dgettext (char *my_domain, const char *my_format) __attribute__ ((format_arg (2)));приводит к тому, что компилятор проверяет аргументы в вызовах к функции типа
printf,scanf,strftimeилиstrfmon, строка формата аргумента которой является вызовом функцииmy_dgettext, на соответствие строке формата аргументаmy_format. Если атрибутformat_argне был указан, компилятор мог бы определить только то, что аргумент строки формата не является константой; это вызывало бы предупреждение при использовании -Wformat-nonliteral, но вызовы не могли бы быть проверены без атрибута.Параметр string-index указывает, какой аргумент является аргументом строки формата (начиная с одного). Поскольку у нестатических методов C++ есть неявный аргумент
this, аргументы таких методов должны учитываться с двух.Атрибут
format_argпозволяет идентифицировать собственные функции, изменяющие строки формата, чтобы GCC мог проверять вызовы функции типаprintf,scanf,strftimeилиstrfmon, операндами которых является вызов одной из ваших собственных функций. Компилятор всегда обрабатываетgettext,dgettext, иdcgettextтаким образом, за исключением случаев, когда строгое соответствие стандарту ISO C запрашивается с помощью -ansi или соответствующего параметра -std, или используются -ffreestanding или -fno-builtin. См. Параметры, контролирующие диалект C.Для диалектов Objective-C атрибут
format-argможет ссылаться на ссылкуNSStringдля совместимости с атрибутомformatвыше.Целевая платформа также может допускать дополнительные типы в атрибутах
format-arg. См. Проверки формата, специфичные для конкретных целевых машин. gnu_inline-
Этот атрибут следует использовать с функцией, которая также объявлена с ключевым словом
inline. Он сообщает GCC, что функция должна обрабатываться как определённая в режиме gnu90 даже при компиляции в режимах C99 или gnu99.Если функция объявлена как
extern, то это определение функции используется только для встраивания. Ни в коем случае функция не компилируется как автономная функция, даже если вы явно берёте её адрес. Такой адрес становится внешней ссылкой, как если бы вы только объявили функцию и не определили её. Это почти эквивалентно макросу. Для использования этого нужно поместить определение функции в заголовочный файл с этим атрибутом и поместить другую копию функции безexternв файл библиотеки. Определение в заголовочном файле приводит к тому, что большинство вызовов функции встраиваются. Если какие-либо вызовы функции остаются, они ссылаются на единственную копию в библиотеке. Обратите внимание, что два определения функций могут отличаться, хотя если они не имеют одинакового эффекта, поведение вашей программы может быть непредсказуемым.В C, если функция не является ни
extern, ниstatic, то функция компилируется как автономная функция, а также встраивается по возможности.Так GCC традиционно обрабатывал функции, объявленные
inline. Поскольку ISO C99 определяет другие семантику дляinline, этот атрибут функции предоставляется как переходный механизм и как полезная функция сама по себе. Этот атрибут доступен в GCC 4.1.3 и более поздних версиях. Он доступен, если определены одна из препроцессорных макросов__GNUC_GNU_INLINE__или__GNUC_STDC_INLINE__. См. Встроенная функция так же быстра, как макрос.В C++, этот атрибут никак не зависит от
extern, но для включения его специального поведения всё ещё требуется ключевое словоinline. hot-
Атрибут
hotдля функции используется для информирования компилятора о том, что функция является горячей точкой компилируемой программы. Функция оптимизируется более агрессивно, и на многих целевых платформах она помещается в специальный подраздёл секции текста, чтобы все горячие функции располагались близко друг к другу, улучшая локальность.Когда обратная связь профилей доступна через -fprofile-use, горячие функции автоматически обнаруживаются, и этот атрибут игнорируется.
ifunc ("resolver")
-
Атрибут
ifuncиспользуется для обозначения функции как косвенной функции, используя расширение типа символа STT_GNU_IFUNC к стандарту ELF. Это позволяет динамически определить значение символа во время загрузки и выбрать оптимизированную версию процедуры для конкретного процессора или других системных характеристик, определенных тогда. Чтобы использовать этот атрибут, сначала определите доступные реализации функций и функцию-разрешитель, которая возвращает указатель на выбранную функцию реализации. Объявления функций реализации должны соответствовать API реализуемой функции. Функция-разрешитель должна быть объявлена как функция без аргументов, возвращающая указатель на функцию того же типа, что и функция реализации. Например:void *my_memcpy (void *dst, const void *src, size_t len) { … return dst; } static void * (*resolve_memcpy (void))(void *, const void *, size_t) { return my_memcpy; // we will just always select this routine }Экспортируемый заголовочный файл, объявляющий функцию, вызываемую пользователем, будет содержать:
extern void *memcpy (void *, const void *, size_t);
позволяя пользователю вызывать
memcpyкак обычную функцию, не зная фактической реализации. Наконец, косвенная функция должна быть определена в том же блоке трансляции, что и функция-разрешитель:void *memcpy (void *, const void *, size_t) __attribute__ ((ifunc ("resolve_memcpy")));В C++, атрибут
ifuncпринимает строку, которая является искаженным именем функции-разрешителя. Функция-разрешитель C++ для нестатического члена-функции классаCдолжна быть объявлена для возврата указателя на функцию без параметров, принимающую указатель наCв качестве первого аргумента, за которым следуют те же аргументы, что и у функции реализации. G++ проверяет подписи двух функций и выводит предупреждение -Wattribute-alias для несовпадений. Чтобы подавить предупреждение о необходимой приведённой операции преобразования типа указателя на функцию реализации в тип соответствующей функции без параметров, используйте опцию -Wno-pmf-conversions. Например:class S { private: int debug_impl (int); int optimized_impl (int); typedef int Func (S*, int); static Func* resolver (); public: int interface (int); }; int S::debug_impl (int) { /* … */ } int S::optimized_impl (int) { /* … */ } S::Func* S::resolver () { int (S::*pimpl) (int) = getenv ("DEBUG") ? &S::debug_impl : &S::optimized_impl; // Cast triggers -Wno-pmf-conversions. return reinterpret_cast<Func*>(pimpl); } int S::interface (int) __attribute__ ((ifunc ("_ZN1S8resolverEv")));Косвенные функции не могут быть слабыми. Для использования этой функции требуются версии библиотек Binutils 2.20.1 или выше и GNU C Library 2.11.1 или выше.
interruptinterrupt_handler-
Многие бэкэнды GCC поддерживают атрибуты, указывающие, что функция является обработчиком прерываний, что сообщает компилятору сгенерировать последовательности входа и выхода из функции, отличающиеся от последовательностей обычных функций. Точная синтаксическая конструкция и поведение зависят от целевой платформы; см. следующие подзаголовки для получения подробностей.
leaf-
Вызовы внешних функций с этим атрибутом должны возвращаться в текущий блок компиляции только с помощью возврата или обработки исключений. В частности, функция-лист не может вызывать функции обратного вызова, переданные ей из текущего блока компиляции, напрямую вызывать функции, экспортированные этим блоком, или
longjmpв этот блок. Функции-листы все еще могут вызывать функции из других блоков компиляции, и поэтому они не обязательно являются листами в том смысле, что они не содержат вызовов функций вообще.Атрибут предназначен для функций библиотек, чтобы улучшить анализ потока данных. Компилятор принимает подсказку о том, что любые данные, не выходящие за пределы текущего блока компиляции, не могут быть использованы или изменены функцией-листом. Например, функция
sinявляется функцией-листом, но функцияqsort— нет.Обратите внимание, что функция-лист может косвенно выполнить обработчик сигнала, определённый в текущем блоке компиляции, который использует статические переменные. Аналогично, при наличии ленивой разрешения символов, функции-листы могут вызывать косвенные функции, функция-разрешитель или функция реализации которых определены в текущем блоке компиляции и используют статические переменные. Нет стандартно совместимого способа написания такого обработчика сигналов, функции-разрешителя или функции реализации, и лучше всего удалить атрибут
leafили отметить все такие статические переменныеvolatile. Наконец, для систем ELF, поддерживающих интерпозицию символов, следует позаботиться о том, чтобы функции, определённые в текущем блоке компиляции, не внедрялись неожиданно в другие символы на основе определённого режима стандартов и определённых макросов проверок функциональности; в противном случае будет добавлен непреднамеренный обратный вызов.Атрибут не оказывает никакого влияния на функции, определённые в текущем блоке компиляции. Это позволяет легко объединять несколько блоков компиляции в один, например, с помощью оптимизации на этапе компоновки. По этой причине атрибут не разрешен для типов для аннотирования косвенных вызовов.
malloc-
Это сообщает компилятору, что функция похожа на
malloc, т.е. что указатель P, возвращаемый функцией, не может быть связан с любым другим указателем, действующим во время возвращения функции, и, кроме того, никакие указатели на допустимые объекты не появляются в любом хранилище, адресуемом P.Использование этого атрибута может улучшить оптимизацию. Функции, такие как
mallocиcalloc, обладают этим свойством, поскольку они возвращают указатель на неинициализированное или обнулённое хранилище. Однако функции, такие какrealloc, не обладают этим свойством, поскольку они могут возвращать указатель на хранилище, содержащее указатели. no_icf-
Этот атрибут функции предотвращает объединение функции с другой семантически эквивалентной функцией.
no_instrument_function-
Если используется -finstrument-functions, то генерируются профилирующие вызовы функций при входе и выходе из большинства функций, скомпилированных пользователем. Функции с этим атрибутом не проходятся профилированием.
no_profile_instrument_function-
Атрибут
no_profile_instrument_functionдля функций используется для того, чтобы сообщить компилятору, что он не должен обрабатывать никакой профильной обратной связи, связанной с оптимизацией кода. no_reorder-
Не переупорядочивать функции или переменные, помеченные
no_reorder, относительно друг друга или утверждений ассемблера верхнего уровня в исполняемом файле. Фактический порядок в программе будет зависеть от командной строки компоновщика. Статические переменные, помеченные таким образом, также не удаляются. Это имеет аналогичный эффект, как опция -fno-toplevel-reorder, но применяется только к отмеченным символам. no_sanitize ("sanitize_option")-
Атрибут
no_sanitizeдля функций используется для того, чтобы сообщить компилятору, что он не должен выполнять санитизацию всех опций, упомянутых в sanitize_option. Список значений, приемлемых для опции -fsanitize, может быть предоставлен.void __attribute__ ((no_sanitize ("alignment", "object-size"))) f () { /* Do something. */; } void __attribute__ ((no_sanitize ("alignment,object-size"))) g () { /* Do something. */; } no_sanitize_addressno_address_safety_analysis-
Атрибут
no_sanitize_addressдля функций используется для того, чтобы сообщить компилятору, что он не должен проводить информирование о доступе к памяти в функции при компиляции с опцией -fsanitize=address.no_address_safety_analysisявляется устаревшим псевдонимом атрибутаno_sanitize_address, новый код должен использоватьno_sanitize_address. no_sanitize_thread-
Атрибут
no_sanitize_threadдля функций используется для того, чтобы сообщить компилятору, что он не должен проводить информирование о доступе к памяти в функции при компиляции с опцией -fsanitize=thread. no_sanitize_undefined-
Атрибут
no_sanitize_undefinedдля функций используется для того, чтобы сообщить компилятору, что он не должен проверять неопределённое поведение в функции при компиляции с опцией -fsanitize=undefined. no_split_stack-
Если используется -fsplit-stack, функции имеют небольшой пролог, который определяет, следует ли разделить стек. Функции с атрибутом
no_split_stackне имеют этого пролога и, следовательно, могут выполняться только с небольшим объёмом доступной памяти стека. no_stack_limit-
Этот атрибут локально переопределяет опции командной строки -fstack-limit-register и -fstack-limit-symbol; он имеет эффект отключения проверки предела стека в функции, к которой он применяется.
noclone-
Этот атрибут функции предотвращает рассмотрение функции для клонирования — механизма, создающего специализированные копии функций, который (в настоящее время) выполняется с помощью межпроцедурного постоянного распространения.
noinline-
Этот атрибут функции предотвращает рассмотрение функции для встраивания. Если у функции нет побочных эффектов, существуют оптимизации, отличные от встраивания, которые приводят к оптимизации вызовов функций, хотя вызов функции активен. Чтобы предотвратить оптимизацию таких вызовов, поместите
asm ("");(см. Расширенный ассемблер) в вызываемой функции, чтобы использовать её как особый побочный эффект.
noipa-
Отключить межпроцедурные оптимизации между функцией с этим атрибутом и её вызывающими функциями, как если бы тело функции было недоступно при оптимизации вызывающих функций, и вызывающие функции были недоступны при оптимизации тела. Этот атрибут подразумевает атрибуты
noinline,nocloneиno_icf. Однако этот атрибут не эквивалентен комбинации других атрибутов, потому что его цель состоит в подавлении существующих и будущих оптимизаций, использующих межпроцедурный анализ, включая те, для которых нет подходящего атрибута для их отключения по отдельности. Этот атрибут поддерживается в основном для целей тестирования компилятора. nonnull (arg-index, …)-
Атрибут
nonnullуказывает, что некоторые параметры функции должны быть указателями, отличными от нуля. Например, объявление:extern void * my_memcpy (void *dest, const void *src, size_t len) __attribute__((nonnull (1, 2)));заставляет компилятор проверять, что в вызовах
my_memcpy, аргументы dest и src не являются нулевыми. Если компилятор определяет, что в аргументе, помеченном как отличный от нуля, передаётся нулевой указатель, и опция -Wnonnull включена, выводится предупреждение. Компилятор также может выбрать оптимизацию на основе знания того, что определённые аргументы функции никогда не будут нулевыми.Если для атрибута
nonnullне указан список индексов аргументов, все аргументы-указатели отмечаются как отличные от нуля. Например, следующее объявление эквивалентно предыдущему примеру:extern void * my_memcpy (void *dest, const void *src, size_t len) __attribute__((nonnull)); noplt
-
Атрибут
nopltявляется аналогом опции -fno-plt. Вызовы функций, помеченных этим атрибутом в позиционно-независимом коде, не используют PLT./* Externally defined function foo. */ int foo () __attribute__ ((noplt)); int main (/* … */) { /* … */ foo (); /* … */ }
Атрибут
nopltдля функцииfooсообщает компилятору, что функцияfooопределена внешне и что вызовfooдолжен избегать PLT в позиционно-независимом коде.В позиционно-зависимом коде некоторые цели также преобразуют вызовы функций, помеченных как не использующие PLT, в использование GOT вместо этого.
noreturn-
Некоторые стандартные функции библиотеки, такие как
abortиexit, не могут вернуть значение. GCC автоматически знает об этом. Некоторые программы определяют свои собственные функции, которые никогда не возвращают значение. Вы можете объявить ихnoreturnчтобы сообщить компилятору об этом факте. Например,void fatal () __attribute__ ((noreturn)); void fatal (/* … */) { /* … */ /* Print error message. */ /* … */ exit (1); }
Ключевое слово
noreturnсообщает компилятору, что функцияfatalне может вернуть значение. Затем компилятор может оптимизировать, не учитывая то, что произойдёт, еслиfatalвсё же вернёт значение. Это немного улучшает код. Более важно, это помогает избежать ложных предупреждений об инициализированных переменных.Ключевое слово
noreturnне влияет на исключительный путь, когда он применим: функция, помеченнаяnoreturn, по-прежнему может вернуть значение вызывающей функции, выбросив исключение или вызвавlongjmp.Не предполагайте, что регистры, сохранённые вызывающей функцией, будут восстановлены перед вызовом функции
noreturn.Не имеет смысла, чтобы функция
noreturnимела тип возвращаемого значения, отличного отvoid. nothrow-
Атрибут
nothrowиспользуется для информирования компилятора о том, что функция не может генерировать исключение. Например, большинство функций в стандартной библиотеке C гарантированно не генерируют исключение, за исключениемqsortиbsearch, принимающих указатели на функции в качестве аргументов. optimize-
Атрибут
optimizeиспользуется для указания, что функция должна компилироваться с разными параметрами оптимизации, чем указанные в командной строке. Аргументы могут быть числами или строками. Числа предполагаются уровнями оптимизации. Строки, начинающиеся сO, предполагаются параметрами оптимизации, в то время как другие параметры предполагается использовать с префиксом-f. Также можно использовать директиву «#pragma GCC optimize» для установки параметров оптимизации, влияющих на несколько функций. Подробнее о директиве «#pragma GCC optimize» см. в разделе Параметры оптимизации для отдельных функций.Этот атрибут следует использовать только для отладки. Он не подходит для использования в производственном коде.
patchable_function_entry-
В случае, если сегмент текста целевого процессора может быть сделан доступным для записи во время выполнения, вставка в начало функции нескольких команд NOP может быть использована в качестве универсального инструмента для инструментов мониторинга.
Атрибут функции
patchable_function_entryможет быть использован для изменения количества команд NOP на любое желаемое значение. Синтаксис с двумя значениями такой же, как у командной строки -fpatchable-function-entry=N,M, генерирующей N команд NOP, с точкой входа в функцию перед M-ой командой NOP. M по умолчанию равно 0, если опущен, т.е. точка входа в функцию расположена перед первой командой NOP.Если вход в исполняемую функцию с возможностью исправления включён глобально с помощью опции командной строки -fpatchable-function-entry=N,M, то необходимо отключить мониторинг для всех функций, входящих в состав инфраструктуры мониторинга, с помощью атрибута
patchable_function_entry (0)для предотвращения рекурсии. pure-
Многие функции не имеют побочных эффектов, за исключением возвращаемого значения, и их возвращаемое значение зависит только от параметров и/или глобальных переменных. Вызовы таких функций могут быть подвержены оптимизации на основе общих подвыражений и циклов, как и арифметические операторы. Эти функции должны быть объявлены с атрибутом
pure. Например,int square (int) __attribute__ ((pure));
указывает, что гипотетическая функция
squareможет быть вызвана меньше раз, чем указано в программе.Некоторые типичные примеры чистых функций —
strlenилиmemcmp. Интересными нечистыми функциями являются функции с бесконечными циклами или те, которые зависят от переменных volatile памяти или других системных ресурсов, которые могут изменяться между двумя последовательными вызовами (например,feofв многопоточной среде).Атрибут
pureнакладывает похожие, но менее жёсткие ограничения на определение функции, чем атрибутconst: он позволяет функции считывать глобальные переменные. Использование обоих атрибутовpureиconstдля одной функции будет диагностировано. Поскольку функцияpureне может иметь побочных эффектов, не имеет смысла, чтобы такая функция возвращалаvoid. Объявление такой функции будет диагностировано. returns_nonnull-
Атрибут
returns_nonnullуказывает, что возвращаемое значение функции должно быть указателем, не равным NULL. Например, объявление:extern void * mymalloc (size_t len) __attribute__((returns_nonnull));
позволяет компилятору оптимизировать вызывающие функции на основе знания, что возвращаемое значение никогда не будет NULL.
returns_twice-
Атрибут
returns_twiceсообщает компилятору, что функция может вернуть значение более одного раза. Компилятор гарантирует, что все регистры будут освобождены перед вызовом такой функции, и выведет предупреждение о переменных, которые могут быть перезаписаны после второго возвращения из функции. Примеры таких функций —setjmpиvfork. Аналогичная функция, если она есть, может потребовать атрибутаnoreturn. section ("section-name")-
Обычно компилятор помещает сгенерированный код в сегмент
text. Однако иногда вам нужны дополнительные сегменты, или вам нужны определённые функции, которые появляются в специальных сегментах. Атрибутsectionуказывает, что функция находится в определённом сегменте. Например, объявление:extern void foobar (void) __attribute__ ((section ("bar")));помещает функцию
foobarв сегментbar.Некоторые форматы файлов не поддерживают произвольные сегменты, поэтому атрибут
sectionнедоступен на всех платформах. Если вам нужно отобразить всё содержимое модуля в определённый сегмент, рассмотрите использование средств компоновщика. sentinel-
Этот атрибут функции гарантирует, что параметр в вызове функции является явным
NULL. Атрибут валиден только для функций с переменным числом параметров. По умолчанию индикатор находится в позиции ноль, последнем параметре вызова функции. Если в атрибут добавлен необязательный целочисленный параметр позиции P, индикатор должен находиться в позиции P, считая с конца списка аргументов.__attribute__ ((sentinel)) is equivalent to __attribute__ ((sentinel(0)))
Атрибут автоматически устанавливается с позицией 0 для встроенных функций
execlиexeclp. Встроенная функцияexecleимеет атрибут, установленный с позицией 1.Валидный
NULLв данном контексте определяется как ноль с любым типом указателя. Если ваша система определяет макросNULLс целочисленным типом, вам нужно добавить явное приведение типов. GCC заменяетstddef.hна копию, которая переопределяет NULL соответствующим образом.Предупреждения о пропущенных или неправильных индикаторах включены с помощью -Wformat.
simdsimd("mask")-
Этот атрибут позволяет создать одну или несколько версий функции, которые могут обрабатывать несколько аргументов с использованием инструкций SIMD из одного вызова. Указание этого атрибута позволяет компилятору предположить, что такие версии доступны во время компоновки (присутствуют в том же или другом модуле трансляции). Сгенерированные версии зависят от платформы и описаны в соответствующем документе Vector ABI. Для целевой платформы x86_64 этот документ можно найти здесь.
Необязательный аргумент mask может иметь значение
notinbranchилиinbranch, и сообщает компилятору сгенерировать клоны без маски или с маской соответственно. По умолчанию генерируются все клоны.Если атрибут указан и
#pragma omp declare simdприсутствует в объявлении, а также указаны переключатели -fopenmp или -fopenmp-simd, то атрибут игнорируется. stack_protect-
Этот атрибут добавляет код защиты стека в функцию, если установлены флаги -fstack-protector, -fstack-protector-strong или -fstack-protector-explicit.
target (options)
-
Несколько целевых back-end реализуют атрибут
target, чтобы указать, что функция должна быть скомпилирована с различными целевыми параметрами, отличными от указанных в командной строке. Это можно использовать, например, для компиляции функций с другой архитектурой набора инструкций (ISA), отличной от стандартной. Также можно использовать псевдоним «#pragma GCC target», чтобы задать более одной функции параметры компиляции для определённых целей. Подробности о псевдониме «#pragma GCC target» см. в разделе Функциональные специфические параметры опций.Например, в x86 можно объявить одну функцию с атрибутом
target("sse4.1,arch=core2")и другую с атрибутомtarget("sse4a,arch=amdfam10"). Это эквивалентно компиляции первой функции с параметрами -msse4.1 и -march=core2, а второй — с параметрами -msse4a и -march=amdfam10. Вам необходимо убедиться, что функция вызывается только на машине, поддерживающей конкретную архитектуру набора инструкций (ISA), для которой она скомпилирована (например, используяcpuidв x86, чтобы определить используемые биты функции и семейство архитектуры).int core2_func (void) __attribute__ ((__target__ ("arch=core2"))); int sse3_func (void) __attribute__ ((__target__ ("sse3")));Можно использовать несколько строк, разделённых запятыми, для задания нескольких параметров, или разделить параметры запятой («,») внутри одной строки.
Поддерживаемые параметры специфичны для каждой цели; см. Атрибуты функций x86, Атрибуты функций PowerPC, Атрибуты функций ARM, Атрибуты функций AArch64, Атрибуты функций Nios II и Атрибуты функций S/390 для получения подробной информации.
target_clones (options)-
Атрибут
target_clonesиспользуется для указания того, что функция должна быть клонирована в несколько версий, скомпилированных с различными целевыми параметрами, отличными от указанных в командной строке. Поддерживаемые параметры и ограничения такие же, как и для атрибутаtarget.Например, в x86 можно скомпилировать функцию с
target_clones("sse4.1,avx"). GCC создаёт два клонированных функции, одну, скомпилированную с -msse4.1, а другую — с -mavx.В PowerPC можно скомпилировать функцию с
target_clones("cpu=power9,default"). GCC создаст два клонированных функции, одну, скомпилированную с -mcpu=power9, и другую — с параметрами по умолчанию. GCC должен быть настроен для использования GLIBC 2.23 или более поздней версии, чтобы использовать атрибутtarget_clones.Он также создаёт функцию-резолвер (см. атрибут
ifuncвыше), которая динамически выбирает подходящий клон для текущей архитектуры. Резолвер создаётся только при использовании функции с атрибутомtarget_clones. unused-
Этот атрибут, присоединённый к функции, означает, что функция может быть неиспользуемой. GCC не выдаёт предупреждение для этой функции.
used-
Этот атрибут, присоединённый к функции, означает, что код должен быть сгенерирован для функции, даже если функция, по-видимому, не ссылается. Это полезно, например, когда на функцию ссылаются только в ассемблерном коде встроенного типа.
При применении к члену-функции шаблона класса C++, атрибут также означает, что функция экземпляризируется, если сам класс экземпляризован.
visibility ("visibility_type")-
Этот атрибут влияет на связь объявления, к которому он присоединён. Он может быть применён к переменным (см. Общие атрибуты переменных) и типам (см. Общие атрибуты типов), а также к функциям.
Поддерживаются четыре значения visibility_type: default, hidden, protected или internal visibility.
void __attribute__ ((visibility ("protected"))) f () { /* Do something. */; } int i __attribute__ ((visibility ("hidden")));Возможные значения visibility_type соответствуют настройкам видимости в ELF gABI.
default-
Видимость по умолчанию — это обычный случай для формата файла объекта. Это значение доступно для атрибута видимости, чтобы переопределить другие параметры, которые могут изменить предполагаемую видимость сущностей.
В ELF видимость по умолчанию означает, что объявление видно другим модулям и, в общих библиотеках, означает, что объявленную сущность можно переопределить.
В Darwin видимость по умолчанию означает, что объявление видно другим модулям.
Видимость по умолчанию соответствует «внешней связи» в языке.
hidden-
Скрытая видимость указывает, что объявленная сущность имеет новый тип связи, которую мы называем «скрытой связью». Два объявления объекта со скрытой связью относятся к одному объекту, если они находятся в одном общем объекте.
internal-
Внутренняя видимость похожа на скрытую видимость, но с дополнительными семантиками, специфичными для процессора. Если не указано иное psABI, GCC определяет внутреннюю видимость так, что на функцию никогда не ссылается другой модуль. Сравните это со скрытыми функциями, которые, хотя и не могут быть непосредственно обработаны другими модулями, могут быть обработаны косвенно через указатели на функции. Указав, что к функции нельзя обратиться извне модуля, GCC может, например, пропустить загрузку регистра PIC, поскольку известно, что вызывающая функция загрузила правильное значение.
protected-
Защищённая видимость похожа на видимость по умолчанию, за исключением того, что она указывает, что ссылки внутри определяющего модуля привязаны к определению в этом модуле. То есть, объявленная сущность не может быть переопределена другим модулем.
Все виды видимости поддерживаются во многих, но не во всех, целевых системах ELF (поддерживаются, когда ассемблер поддерживает псевдооператор «.visibility»). Видимость по умолчанию поддерживается везде. Скрытая видимость поддерживается в целевых системах Darwin.
Атрибут видимости следует применять только к объявлениям, которые в противном случае имели бы внешнюю связь. Атрибут должен применяться последовательно, чтобы одна и та же сущность не объявлялась с различными параметрами атрибута.
В C++ атрибут видимости применяется к типам, а также к функциям и объектам, потому что в C++ типы имеют связь. Класс не должен иметь большей видимости, чем типы его нестатических данных-членов и базовые классы, и члены класса по умолчанию наследуют видимость своего класса. Также объявление без явной видимости ограничено видимостью его типа.
В C++ можно отмечать методы-члены и статические переменные-члены класса с атрибутом видимости. Это полезно, если известно, что определённый метод или статическая переменная-член должна использоваться только из одного общего объекта; тогда можно отметить её как скрытую, в то время как остальная часть класса имеет видимость по умолчанию. Необходимо соблюдать осторожность, чтобы избежать нарушения правила единого определения; например, обычно не имеет смысла помечать встроенный метод как скрытый, не отмечая весь класс как скрытый.
Объявление пространства имён C++ также может иметь атрибут видимости.
namespace nspace1 __attribute__ ((visibility ("protected"))) { /* Do something. */; }Этот атрибут применяется только к телу конкретного пространства имён, а не к другим определениям того же пространства имён; он эквивалентен использованию «#pragma GCC visibility» перед и после определения пространства имён (см. Псевдонимы видимости).
В C++, если аргумент шаблона имеет ограниченную видимость, это ограничение подразумевается для экземпляра шаблона. В противном случае экземпляры и специализации шаблонов по умолчанию имеют видимость своего шаблона.
Если и шаблон, и содержащий его класс имеют явную видимость, используется видимость шаблона.
warn_unused_result-
Атрибут
warn_unused_resultвызывает предупреждение, если вызывающая функция с этим атрибутом не использует возвращаемое значение. Это полезно для функций, где отсутствие проверки результата является либо проблемой безопасности, либо всегда является ошибкой, например,realloc.int fn () __attribute__ ((warn_unused_result)); int foo () { if (fn () < 0) return -1; fn (); return 0; }приводит к предупреждению на строке 5.
weak-
Атрибут
weakзаставляет объявление генерироваться как слабый символ, а не глобальный. Это в первую очередь полезно для определения функций библиотеки, которые могут быть переопределены в пользовательском коде, хотя также может быть использовано с объявлениями, не являющимися функциями. Слабые символы поддерживаются для целевых систем ELF, а также для целевых систем a.out при использовании GNU ассемблера и компоновщика. weakrefweakref ("target")-
Атрибут
weakrefотмечает объявление как слабую ссылку. Без аргументов он должен сопровождаться атрибутомalias, задающим целевой символ. Дополнительно, target может быть задан как аргумент дляweakref. В любом случаеweakrefнеявным образом отмечает объявление какweak. Без target, заданного как аргумент дляweakrefилиalias,weakrefэквивалентноweak.static int x() __attribute__ ((weakref ("y"))); /* is equivalent to... */ static int x() __attribute__ ((weak, weakref, alias ("y"))); /* and to... */ static int x() __attribute__ ((weakref)); static int x() __attribute__ ((alias ("y")));Слабая ссылка — это псевдоним, который сам по себе не требует определения для целевого символа. Если целевой символ ссылается только через слабые ссылки, то он становится
weakнеопределённым символом. Однако, если он прямо ссылается, то такие сильные ссылки имеют приоритет, и определение символа требуется, но не обязательно в том же модуле трансляции.Эффект эквивалентен перемещению всех ссылок на псевдоним в отдельный модуль трансляции, переименованию псевдонима в алиасируемый символ, объявлением его как слабого, компиляции двух отдельных модулей трансляции и выполнению перезагружаемой компоновки на них.
В настоящее время объявление, к которому прикреплён
weakref, может быть толькоstatic.
Далее: Атрибуты функций AArch64, Назад: Атрибуты функций [Оглавление][Указатель]
© Free Software Foundation
Licensed under the GNU Free Documentation License, Version 1.3.
https://gcc.gnu.org/onlinedocs/gcc-8.5.0/gcc/Common-Function-Attributes.html