Инициализация статических объектов в С++

115
29 сентября 2021, 12:20

Пусть есть программа:

int aaa;
class b {
    int bb;
public:
    b(){}
};
b bbb;
int main(){
    return 0;
}

Как известно, перед стартом main в переменную "aaa" будет записан ноль.

Вопросы:

  1. Будет ли записан ноль в поле "bb" объекта "bbb"?
  2. Будет ли вызван пустой конструктор класса "b" для объекта "bbb"? Или транслятор выбрасывает вызовы пустых конструкторов?

P.S. Вопрос не праздный. Нужно понять, можно ли избежать принудительного обнуления статических объектов и тем самым ускорить старт функции main.

UPD1:

Видимо надо сделать пояснения.

Вопрос связан с работой встроенных систем. То есть таких систем, в которых код зашит в ПЗУ и стартует из ПЗУ. В таких системах нельзя проинициализировать статические переменные при загрузке, так как код живет в ПЗУ, а в ОЗУ по старту лежит мусор. То есть никакие

bbb:
  .zero 4
aaa:
  .zero 4

в таких системах не прокатывают. И именно что до main должен запускаться отдельный код для обнуления статических переменных. Вместе с тем, если код для обнуления статических переменных работает слишком долго, то это тоже плохо. Как-то я общался с разработчиками систем защиты в энергетике. У них было требование, чтобы защита начинала работать после подачи питания не позднее чем через полпериода промышленной частоты в 50 Гц , то есть не позднее, чем 10 миллисекунд (чтобы отключить оборудование если на линии висит КЗ). Если питание подано, а процессор вместо работы заполняет нулями статические переменные, то это не очень хорошо.

Поэтому возник вопрос - как управлять процессом обнуления статических переменных и можно ли это делать с помощью классов с пустыми конструкторами. Похоже, что нельзя, во всяком случае для GCC и clang.

Answer 1

Тут многое отдается на откуп реализации. В приведенном примере переменные никак не используются, а их инициализация не имеет побочных эффектов, соответственно они могут быть спокойно выкинуты компилятором. Если же они все-таки используются то

  1. стандарт диктует, что статическая инициализация (в т.ч. обнуление) происходит строго до начала динамической инициализации:

6.8.3.2 Static initialization [basic.start.static]
2 ... All static initialization strongly happens before (6.8.2.1) any dynamic initialization.

  1. а динамическая инициализация происходит строго до первого использования какой-либо переменной из той же единицы трансляции, причем это может происходить в неопределенный момент уже после начала выполнения main:

6.8.3.3 Dynamic initialization of non-local variables [basic.start.dynamic]
4 It is implementation-defined whether the dynamic initialization of a non-local non-inline variable with static storage duration is sequenced before the first statement of main or is deferred. If it is deferred, it strongly happens before any non-initialization odr-use of any non-inline function or non-inline variable defined in the same translation unit as the variable to be initialized. 55 It is implementation-defined in which threads and at which points in the program such deferred dynamic initialization occurs.

READ ALSO
C++, volatile и strict aliasing rules

C++, volatile и strict aliasing rules

Подскажите, пожалуйста, законно ли использование спецификатора volatile для локального обхода требований строгих псевдонимов?

211
Логирование в консоль Catch2

Логирование в консоль Catch2

Почему Catch2 не логирует сообщения? В пустом TEST_CASE пишу INFO("42");После запуска в консоли получаю:

173
SVG маска и анимация при наведении

SVG маска и анимация при наведении

Я не очень хорошо знаком с SVG и маской, и я хотел бы знать, возможно ли, чтобы анимация, как на картинке, была бы при наведении мыши? (с JQuery или...

85
Запуск js из другого js

Запуск js из другого js

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

151