erro de link ao compilar operação atômica gcc no modo de 32 bits
Pergunta
Eu tenho o seguinte programa:
~/test> cat test.cc
int main()
{
int i = 3;
int j = __sync_add_and_fetch(&i, 1);
return 0;
}
Estou compilando este programa usando o GCC 4.2.2 em Linux rodando em um multi-CPU de 64 bits máquina Intel:
~/test> uname --all
Linux doom 2.6.9-67.ELsmp #1 SMP Wed Nov 7 13:56:44 EST 2007 x86_64 x86_64 x86_64 GNU/Linux
Quando eu compilar o programa no modo de 64 bits, ele compila e ligações bem:
~/test> /share/tools/gcc-4.2.2/bin/g++ test.cc
~/test>
Quando eu compilá-lo no modo de 32 bits, eu recebo o seguinte erro:
~/test> /share/tools/gcc-4.2.2/bin/g++ -m32 test.cc
/tmp/ccEVHGkB.o(.text+0x27): In function `main':
: undefined reference to `__sync_add_and_fetch_4'
collect2: ld returned 1 exit status
~/test>
Embora eu nunca vai realmente executar em um processador de 32 bits, eu preciso de um executável de 32 bits para que eu possa ligar com algumas bibliotecas de 32 bits.
As minhas 2 questões são:
-
Por que recebo um erro de link quando eu compilar no modo de 32 bits?
-
Existe alguma maneira de obter o programa para compilar e link, enquanto continuam sendo capazes de ligação com uma biblioteca de 32 bits?
Solução
A partir do href="http://gcc.gnu.org/onlinedocs/gcc-4.1.0/gcc/Atomic-Builtins.html#Atomic-Builtins" rel="noreferrer"> página GCC :
Nem todas as operações são apoiadas por todos os processadores de destino. Se um determinado operação não pode ser implementado no alvo processador, um aviso será gerada uma chamada e um externo função será gerado. o função externa irá transportar a mesma nomear como o builtin, com um sufixo '_n' adicional em que n é o tamanho do tipo de dados.
A julgar pela sua saída do compilador, que refere-se a __sync_add_and_fetch_4
, é isso que está acontecendo. Por alguma razão, GCC não está gerando a função externa corretamente.
Este é provavelmente por isso que você está recebendo apenas um erro no modo de 32 bits - quando compilar para o modo de 64 bits, ele compila para o seu processador mais de perto. Ao compilar para 32 bits, pode muito bem estar usando um arco genérico (i386, por exemplo) que não suporta esses recursos. Tente especificar uma arquitetura específica para a sua família chip (Xeon, Core 2, etc.) via -mcpu e ver se isso funciona.
Se não, você vai ter que descobrir por que o GCC não está incluindo a função apropriada que deve ser geradora.
Outras dicas
A resposta de Dan Udey estava perto, perto o suficiente, de fato, para permitir-me a encontrar a solução real.
De acordo com a página do manual "-mcpu" é um sinônimo preterido para "otimizar para uma CPU particular (mas ainda rodar em CPUs mais velhos, embora menos ideal)" "-mtune" e significa apenas. Eu tentei isso, e isso não resolveu o problema.
No entanto, "-march =" significa "gerar código para uma determinada CPU (e não correr em CPUs mais velhos)". Quando eu tentei isso, ele resolveu o problema:. Especificando um CPU de i486 ou melhor se livrou do erro de link
~/test> /share/tools/gcc-4.2.2/bin/g++ -m32 test.cc
/tmp/ccYnYLj6.o(.text+0x27): In function `main':
: undefined reference to `__sync_add_and_fetch_4'
collect2: ld returned 1 exit status
~/test> /share/tools/gcc-4.2.2/bin/g++ -m32 -march=i386 test.cc
/tmp/ccOr3ww8.o(.text+0x22): In function `main':
: undefined reference to `__sync_add_and_fetch_4'
collect2: ld returned 1 exit status
~/test> /share/tools/gcc-4.2.2/bin/g++ -m32 -march=i486 test.cc
~/test> /share/tools/gcc-4.2.2/bin/g++ -m32 -march=pentium test.cc