Spec-Zone.ru › GCC 8

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

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

aligned (alignment)

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

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 байт. Обратитесь к документации вашего компоновщика за дополнительной информацией.

Атрибут 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 foo
{
  int i1;
  int i2;
  unsigned long long x __attribute__((warn_if_not_aligned(16)));
} __attribute__((aligned(16)));

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

cleanup (cleanup_function)

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

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

common
nocommon

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

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

deprecated
deprecated (msg)

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

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

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

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

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
}
mode (mode)

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

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

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)

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

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

приводит к тому, что компилятор устанавливает режим для foo, равный 16 байтам, разделённым на единицы размера int. При условии 32-битного целого типа (вектор из 4 единиц по 4 байта), соответствующий режим для foo равен V4SI.

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

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

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

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

visibility ("visibility_type")

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

weak

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

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

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

Spec-Zone.ru

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