Spec-Zone.ru › GCC 10

Next: ARC Переменные-атрибуты, Up: Указание атрибутов переменных [Содержание][Индекс]

6.34.1 Общие атрибуты переменных ¶

Следующие атрибуты поддерживаются на большинстве платформ.

alias ("target")

Атрибут переменной alias заставляет объявление генерироваться как псевдоним для другого символа, известного как цель псевдонима. За исключением квалификаторов верхнего уровня, цель псевдонима должна иметь тот же тип, что и псевдоним. Например, следующее

int var_target;
extern int __attribute__ ((alias ("var_target"))) var_alias;

определяет var_alias как псевдоним переменной var_target.

Если цель псевдонима не определена в том же файле перевода, что и сам псевдоним, это ошибка.

Обратите внимание, что в отсутствие атрибута GCC предполагает, что разные объявления с внешней связью обозначают разные объекты. Использование как псевдонима, так и цели псевдонима для доступа к одному объекту в единице перевода без объявления псевдонима с этим атрибутом является неопределённым.

Данный атрибут требует поддержки в ассемблере и объектных файлах, и может быть недоступен на всех целевых платформах.

aligned ¶
aligned (alignment)

Атрибут aligned задаёт минимальное выравнивание для переменной или поля структуры, измеряемое в байтах. Если он указан, alignment должно быть целым числом, являющимся степенью двойки. Отсутствие аргумента alignment подразумевает максимальное выравнивание для целевой платформы, которое часто, но не всегда, составляет 8 или 16 байтов.

Например, объявление:

int x __attribute__ ((aligned (16))) = 0;

заставляет компилятор выделить глобальную переменную x на границе 16 байтов. На 68040 это можно использовать в сочетании с выражением asm, чтобы получить доступ к инструкции move16, которая требует операндов с выравниванием 16 байтов.

Вы также можете указать выравнивание полей структуры. Например, для создания пары слов с двойным выравниванием int, можно написать:

struct foo { int x[2] __attribute__ ((aligned (8))); };

Это альтернатива созданию объединения с членом double, что вынуждает объединение быть выровненным по границе двойного слова.

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

GCC также предоставляет специфичный для целевой платформы макрос __BIGGEST_ALIGNMENT__, который является максимальным выравниванием, когда-либо используемым для любого типа данных на целевой машине, для которой вы компилируете. Например, вы можете написать:

short array[3] __attribute__ ((aligned (__BIGGEST_ALIGNMENT__)));

Компилятор автоматически устанавливает выравнивание для объявленной переменной или поля в __BIGGEST_ALIGNMENT__. Это часто повышает эффективность операций копирования, поскольку компилятор может использовать инструкции копирования больших блоков памяти при выполнении копирования в или из переменных или полей, которые вы выровняли таким образом. Обратите внимание, что значение __BIGGEST_ALIGNMENT__ может меняться в зависимости от параметров командной строки.

При использовании с структурой или членом структуры атрибут aligned может только увеличить выравнивание; для его уменьшения необходимо указать атрибут packed. При использовании в качестве части typedef атрибут aligned может как увеличить, так и уменьшить выравнивание, а указание атрибута packed генерирует предупреждение.

Обратите внимание, что эффективность атрибутов aligned для статических переменных может быть ограничена внутренними ограничениями системного линкера и/или формата объектных файлов. На некоторых системах линкер может обеспечить выравнивание переменных только до определённого максимального значения. (Для некоторых линков максимальное поддерживаемое выравнивание может быть очень маленьким.) Если ваш линкер может выравнивать переменные только до максимального значения 8 байтов, то указание aligned(16) в __attribute__ всё равно даст вам только выравнивание в 8 байтов. Для получения дополнительной информации обратитесь к документации вашего линкера.

Переменные стека не затрагиваются ограничениями линкера; GCC может корректно выровнять их на любой платформе.

Атрибут aligned также может быть использован для функций (см. Общие атрибуты функций).

warn_if_not_aligned (alignment) ¶

Этот атрибут задаёт порог для поля структуры, измеряемый в байтах. Если поле структуры выровнено ниже порога, будет выведено предупреждение. Например, объявление:

struct foo
{
  int i1;
  int i2;
  unsigned long long x __attribute__ ((warn_if_not_aligned (16)));
};

заставляет компилятор выводить предупреждение о struct foo, подобное ‘предупреждение: выравнивание 8 для 'struct foo' меньше 16’. Компилятор также выводит предупреждение, подобное ‘предупреждение: смещение 'x' 8 в 'struct foo' не выровнено по 16’, когда поле структуры имеет невыровненное смещение:

struct __attribute__ ((aligned (16))) foo
{
  int i1;
  int i2;
  unsigned long long x __attribute__ ((warn_if_not_aligned (16)));
};

Это предупреждение можно отключить с помощью -Wno-if-not-aligned. Атрибут warn_if_not_aligned также может быть использован для типов (см. Общие атрибуты типов).

alloc_size (position)
alloc_size (position-1, position-2)

Атрибут alloc_size переменной может быть применён к объявлению указателя на функцию, возвращающую указатель и принимающую по крайней мере один аргумент целочисленного типа. Он указывает, что возвращаемый указатель указывает на объект, размер которого задаётся аргументом функции в позиции position-1 или произведением аргументов в позициях position-1 и position-2. Значимые размеры являются положительными значениями, меньшими PTRDIFF_MAX. Другие размеры диагностируются при обнаружении. GCC использует эту информацию для улучшения результатов __builtin_object_size.

Например, следующие объявления

typedef __attribute__ ((alloc_size (1, 2))) void*
  (*calloc_ptr) (size_t, size_t);
typedef __attribute__ ((alloc_size (1))) void*
  (*malloc_ptr) (size_t);

указывает, что calloc_ptr — это указатель на функцию, которая, подобно стандартной C-функции calloc, возвращает объект, размер которого задаётся произведением аргументов 1 и 2, и аналогично, что malloc_ptr, подобно стандартной C-функции malloc, возвращает объект, размер которого задаётся аргументом 1 функции.

cleanup (cleanup_function)

Атрибут cleanup выполняет функцию, когда переменная выходит из области видимости. Этот атрибут может быть применён только к переменным автоматического типа в области функции; он не может быть применён к параметрам или переменным со статической длительностью хранения. Функция должна принимать один параметр — указатель на тип, совместимый с переменной. Возвращаемое значение функции (если есть) игнорируется.

Если включён -fexceptions, то cleanup_function выполняется во время восстановления стека, происходящего во время обработки исключения. Обратите внимание, что атрибут cleanup не позволяет перехватить исключение, а только выполнить действие. Неопределено, что произойдёт, если cleanup_function не вернётся нормально.

common
nocommon

Атрибут common просит GCC разместить переменную в общем хранилище. Атрибут nocommon просит сделать обратное — выделить память для неё напрямую.

Эти атрибуты переопределяют значения, выбранные флагами -fno-common и -fcommon соответственно.

copy
copy (variable)

Атрибут copy применяет набор атрибутов, с которым была объявлена переменная variable, к объявлению переменной, к которой применяется атрибут. Атрибут предназначен для библиотек, которые определяют псевдонимы, ожидающие специфицировать тот же набор атрибутов, что и алиасируемые символы. Атрибут copy может использоваться с переменными, функциями или типами. Однако, тип символа, к которому применяется атрибут (либо переменная, либо функция), должен совпадать с типом символа, к которому относится аргумент. Атрибут copy копирует только синтаксические и семантические атрибуты, но не атрибуты, влияющие на связь или видимость символа, такие как alias, visibility, или weak. Атрибут deprecated также не копируется. См. Общие атрибуты функций. См. Общие атрибуты типов.

deprecated
deprecated (msg)

Атрибут deprecated приводит к предупреждению, если переменная используется где-либо в исходном файле. Это полезно для выявления переменных, которые, как ожидается, будут удалены в будущей версии программы. Предупреждение также включает местоположение объявления устаревшей переменной, что позволяет пользователям легко найти дополнительную информацию о том, почему переменная устарела или что они должны сделать вместо этого. Обратите внимание, что предупреждение возникает только при использовании:

extern int old_var __attribute__ ((deprecated));
extern int old_var;
int new_fn () { return old_var; }

приводит к предупреждению на строке 3, но не на строке 2. Необязательный аргумент msg, который должен быть строкой, выводится в предупреждении, если он присутствует.

Атрибут deprecated также может быть использован для функций и типов (см. Общие атрибуты функций, см. Общие атрибуты типов).

Сообщение, прикреплённое к атрибуту, зависит от настройки опции -fmessage-length.

mode (mode)

Этот атрибут задаёт тип данных для объявления — тип, соответствующий режиму mode. Это позволяет вам запросить целочисленный или плавающий тип в соответствии с его шириной.

См. Режимы машины в «Внутреннем представлении GNU компилятора GCC», для списка возможных ключевых слов для mode. Вы также можете указать режим byte или __byte__ для обозначения режима соответствующего однобайтовому целому числу, word или __word__ для режима одного слова целого числа и pointer или __pointer__ для режима, используемого для представления указателей.

nonstring

Атрибут переменной nonstring указывает, что объявление объекта или члена типа массив char, signed char, или unsigned char, или указатель на такой тип, предназначен для хранения массивов символов, которые необязательно содержат завершающий NUL. Это полезно для обнаружения использования таких массивов или указателей с функциями, которые ожидают NUL-завершённые строки и для предотвращения предупреждений, когда такой массив или указатель используется в качестве аргумента функции ограниченной обработки строк, такой как strncpy. Например, без атрибута GCC выдаст предупреждение для вызова strncpy ниже, потому что он может обрезать копирование без добавления завершающего NUL символа. Использование атрибута позволяет подавить предупреждение. Однако, когда массив объявлен с атрибутом, вызов strlen диагностируется, потому что при отсутствии в массиве NUL-завершённой строки вызов является неопределённым. Для копирования, сравнения или поиска нестроковых массивов символов используйте функции memcpy, memcmp, memchr, и другие функции, работающие с массивами байтов. Кроме того, вызов strnlen и strndup с такими массивами безопасен при условии указания подходящего предела и не диагностируется.

struct Data
{
  char name [32] __attribute__ ((nonstring));
};

int f (struct Data *pd, const char *s)
{
  strncpy (pd->name, s, sizeof pd->name);
  …
  return strlen (pd->name);   // unsafe, gets a warning
}
packed

Атрибут packed указывает, что член структуры должен иметь наименьшее возможное выравнивание — один бит для битового поля и один байт в противном случае, если большее значение не указано с помощью атрибута aligned. Атрибут не применяется к объектам, не являющимся членами структуры.

Например, в структуре ниже, массив членов x упакован таким образом, что он сразу следует за a без промежуточного заполнения:

struct foo
{
  char a;
  int x[2] __attribute__ ((packed));
};

Примечание: Серии GCC 4.1, 4.2 и 4.3 игнорируют атрибут packed для битовых полей типа char. Это было исправлено в GCC 4.4, но изменение может привести к различиям в структуре расположения. См. документацию для -Wpacked-bitfield-compat для получения дополнительной информации.

section ("section-name")

Обычно компилятор помещает сгенерированные объекты в секции, такие как data и bss. Однако иногда вам нужны дополнительные секции или вам нужно, чтобы определённые переменные появлялись в специальных секциях, например, для сопоставления со специальным оборудованием. Атрибут section указывает, что переменная (или функция) находится в определённой секции. Например, эта небольшая программа использует несколько конкретных имён секций:

struct duart a __attribute__ ((section ("DUART_A"))) = { 0 };
struct duart b __attribute__ ((section ("DUART_B"))) = { 0 };
char stack[10000] __attribute__ ((section ("STACK"))) = { 0 };
int init_data __attribute__ ((section ("INITDATA")));

main()
{
  /* Initialize stack pointer */
  init_sp (stack + sizeof (stack));

  /* Initialize initialized data */
  memcpy (&init_data, &data, &edata - &data);

  /* Turn on the serial ports */
  init_duart (&a);
  init_duart (&b);
}

Используйте атрибут section с глобальными переменными, а не с локальными переменными, как показано в примере.

Вы можете использовать атрибут section с инициализированными или неинициализированными глобальными переменными, но компоновщик требует, чтобы каждый объект был определён один раз, за исключением того, что неинициализированные переменные предварительно помещаются в секцию common (или bss) и могут быть многократно «определены». Использование атрибута section изменяет секцию, в которую попадает переменная, и может привести к ошибке компоновщика, если у неинициализированной переменной есть несколько определений. Вы можете принудительно инициализировать переменную с помощью флага -fno-common или атрибута nocommon.

Некоторые форматы файлов не поддерживают произвольные секции, поэтому атрибут section недоступен на всех платформах. Если вам нужно сопоставить всё содержимое модуля с конкретной секцией, воспользуйтесь средствами компоновщика.

tls_model ("tls_model")

Атрибут tls_model задаёт модель локального хранения потока (см. Локальное хранилище потоков) для конкретной переменной __thread, переопределяя командную строку -ftls-model= на уровне переменной. Аргумент tls_model должен быть одним из global-dynamic, local-dynamic, initial-exec или local-exec.

Не все целевые платформы поддерживают этот атрибут.

unused

Этот атрибут, прикреплённый к переменной, означает, что переменная может быть неиспользуемой. GCC не генерирует предупреждение для этой переменной.

used

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

При применении к статическому члену данных шаблона C++ класс атрибут также означает, что член будет экземпляризирован, если сам класс будет экземпляризирован.

vector_size (bytes)

Этот атрибут определяет размер вектора для типа объявленной переменной, измеряемый в байтах. Тип, к которому он применяется, называется базовым типом. Аргумент bytes должен быть положительной степенью двойки, кратной размеру базового типа. Например, объявление:

int foo __attribute__ ((vector_size (16)));

приводит к тому, что компилятор устанавливает режим для foo, в 16 байт, разделённых на единицы размером int. Предполагая 32-битный int, тип foo — это вектор из четырёх единиц по четыре байта каждая, а соответствующий режим foo — V4SI. См. Использование векторных инструкций через встроенные функции для получения подробностей о работе с векторными переменными.

Этот атрибут применим только к целочисленным и плавающим скалярам, хотя массивы, указатели и значения возвращаемых функций допускаются в сочетании с этой конструкцией.

Агрегаты с этим атрибутом некорректны, даже если их размер совпадает с соответствующим скаляром. Например, объявление:

struct S { int a; };
struct S  __attribute__ ((vector_size (16))) foo;

некорректно, даже если размер структуры совпадает с размером int.

visibility ("visibility_type")

Этот атрибут влияет на связь объявления, к которому он прикреплён. Атрибут visibility описан в Общие атрибуты функций.

weak

Атрибут weak описан в Общие атрибуты функций.

noinit

Любые данные с атрибутом noinit не будут инициализированы кодом начальной загрузки C-runtime или загрузчиком программы. Неинициализация данных таким образом может сократить время запуска программы. Этот атрибут специфичен для целевых платформ ELF и полагается на компоновщик для размещения таких данных в нужном месте.

Далее: Атрибуты переменных ARC, Наверх: Указание атрибутов переменных [Оглавление][Индекс]

© Free Software Foundation
Licensed under the GNU Free Documentation License, Version 1.3.
https://gcc.gnu.org/onlinedocs/gcc-10.5.0/gcc/Common-Variable-Attributes.html

Spec-Zone.ru

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