Используйте [[gnu::noinit]] со статической переменной-членом шаблона класса.C++

Программы на C++. Форум разработчиков
Ответить
Anonymous
 Используйте [[gnu::noinit]] со статической переменной-членом шаблона класса.

Сообщение Anonymous »

Я пытаюсь присвоить атрибут [[gnu::noinit]] статической переменной-члену шаблона класса:

Код: Выделить всё

template 
struct Instantiator {
static T obj;
};
template 
[[gnu::noinit]] T Instantiator::obj;

constinit int* p = & Instantiator::obj;
При компиляции с помощью GCC v15.2.0 для ARM EABI я получаю:

Код: Выделить всё

/tmp/cc25jMnj.s:19: Warning: setting incorrect section type for .noinit._ZN12InstantiatorIiE3objE
GCC генерирует сборку следующим образом:

Код: Выделить всё

        .weak   _ZN12InstantiatorIiE3objE
.section        .noinit._ZN12InstantiatorIiE3objE,"awG",%progbits,_ZN12InstantiatorIiE3objE,comdat
.align  2
.type   _ZN12InstantiatorIiE3objE, %object
.size   _ZN12InstantiatorIiE3objE, 4
_ZN12InstantiatorIiE3objE:
.space  4
Проблема в том, что GCC пытается установить атрибут раздела %progbits, что не имеет смысла для .noinit - очевидно, мне не нужны какие-либо данные инициализации в выходном разделе. Если я вручную изменю его на %nobits в исходном файле сборки, он будет работать нормально.
Как остановить GCC от выдачи атрибута %progbits и изменить его на %nobits?
Попробуйте здесь, в Compiler Explorer.
Мне также было бы неплохо, чтобы GCC выдавал такой код, т. е. без помещения символа в группу разделов и без назначения каких-либо атрибутов:

Код: Выделить всё

        .section        .noinit._ZN12InstantiatorIiE3objE,"aw"
Тогда создание экземпляра шаблона не должно быть помещено в заголовочный файл, и это нормально для меня.
История такова: я хочу использовать класс Instantiator как своего рода встроенный одноэлементный распределитель, т. е. Instantiator::obj должен быть статически выделенным объектом, который можно использовать в определении глобальной переменной, не требуя дополнительных строк для каждого использования. Тип T потенциально велик (например, буферы ввода-вывода), поэтому буферы не всегда нужно инициализировать при запуске (время запуска и энергопотребление имеют решающее значение). Я буду использовать Instantiator только из исходных файлов, поэтому проблем с несколькими определениями ожидать не приходится.

Подробнее здесь: https://stackoverflow.com/questions/798 ... s-template
Ответить

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

Вернуться в «C++»