Почему g++ все еще требует -latomic
В 29.5. Атомные типы рабочего стандарта С++ Standard в ноябре 2014 года:
- Существует общий шаблонный шаблон. Тип аргумента шаблона T должен быть тривиально скопируемым (3.9). [Примечание. Невозможно использовать аргументы типа, которые также не могут быть статически инициализированы. -end note]
Итак - насколько я могу судить - это:
#include <atomic>
struct Message {
unsigned long int a;
unsigned long int b;
};
std::atomic<Message> sharedState;
int main() {
Message tmp{1,2};
sharedState.store(tmp);
Message tmp2=sharedState.load();
}
должен быть вполне допустимым стандартным кодом С++ 14 (а также С++ 11). Однако, если я не связываю libatomic
вручную, команда
g++ -std=c++14 <filename>
дает - по крайней мере, на Fedora 22 (gcc 5.1) - следующую ошибку связывания:
/tmp/ccdiWWQi.o: In function `std::atomic<Message>::store(Message, std::memory_order)':
main.cpp:(.text._ZNSt6atomicI7MessageE5storeES0_St12memory_order[_ZNSt6atomicI7MessageE5storeES0_St12memory_order]+0x3f): undefined reference to `__atomic_store_16'
/tmp/ccdiWWQi.o: In function `std::atomic<Message>::load(std::memory_order) const':
main.cpp:(.text._ZNKSt6atomicI7MessageE4loadESt12memory_order[_ZNKSt6atomicI7MessageE4loadESt12memory_order]+0x1c): undefined reference to `__atomic_load_16'
collect2: error: ld returned 1 exit status
Если я пишу
g++ -std=c++14 -latomic <filename>
все в порядке.
Я знаю, что стандарт ничего не говорит о флажках или библиотеках компилятора, которые должны быть включены, но до сих пор я думал, что любой стандартный сопоставимый код одного файла может быть скомпилирован с помощью первой команды.
Так почему же это не относится к моему примеру? Существует ли рациональное, почему -latomic
по-прежнему необходимо, или это просто то, что еще не было обработано сторонними компиляторами?
Ответы
Ответ 1
Соответствующие чтения на главной странице GCC о том, как и почему GCC делает вызовы библиотеки в определенных случаях в отношении <atomic>
в первую очередь.
GCC и libstdС++ только связаны друг с другом. libatomic
является доменом библиотеки, а не компилятором, и вы можете использовать GCC с другой библиотекой (которая может предоставить необходимые определения для <atomic>
в ее основном правиле или под другим именем), поэтому GCC не может просто предположим -latomic
.
Также:
GCC 4.7 не включает реализацию библиотеки, поскольку API не был прочно установлен.
На той же странице утверждается, что GCC 4.8 предоставляет такую библиотечную реализацию, но планы являются первыми жертвами войны. Я предполагаю, что причина для -latomic
, которая по-прежнему необходима, может быть найдена в этой окрестности.
Кроме того,...
... до сих пор я думал, что любой стандартный сопоставимый код одного файла может быть скомпилирован с помощью первой команды.
... -lm
существует довольно давно, если вы используете математические функции.
Ответ 2
Я знаю, что стандарт ничего не говорит о флажках или библиотеках компилятора, которые должны быть включены
Right.
но до сих пор я думал, что любой стандартный сопоставимый код одного файла может быть скомпилирован с помощью первой команды.
Ну, нет. Как вы только что сказали, нет особых оснований предполагать это. Также подумайте, что расширения GCC включены по умолчанию.
При этом кажется очевидным, что намерение состоит в том, чтобы сделать -latomic
частью по умолчанию для среды выполнения, когда она немного успокоилась.
Ответ 3
g++
- это оболочка для gcc
, которая добавляет правильные библиотеки С++. Очевидно, что в этом списке отсутствует -latomic
. Не проблема основного компилятора, а просто небольшая ошибка в обертке.