A punção de tipos é feita através de uma união não especificada em C99 e ela é especificada em C11?
Várias respostas para a pergunta sobre estouro de pilhaObtendo os bits de precisão única IEEE para um flutuador sugerir usando umunion
estrutura para o tipo de punção (por exemplo: girando os bits de umfloat
dentro deuint32_t
):
union {
float f;
uint32_t u;
} un;
un.f = your_float;
uint32_t target = un.u;
No entanto, o valor douint32_t
O membro da união parece não ser especificado de acordo com o padrão C99 (pelo menos no draft n1124), onde a seção 6.2.6.1.7 declara:
Quando um valor é armazenado em um membro de um objeto do tipo union, os bytes da representação do objeto que não correspondem a esse membro, mas correspondem a outros membros, recebem valores não especificados.
Pelo menos uma nota de rodapé do rascunho do C11 n1570 parece implicar que este já não é o caso (ver nota de rodapé 95 no 6.5.2.3):
Se o membro usado para ler o conteúdo de um objeto de união não for o mesmo que o último membro usado para armazenar um valor no objeto, a parte apropriada da representação de objeto do valor será reinterpretada como uma representação de objeto no novo tipo como descrito em 6.2.6 (um processo às vezes chamado de '' type punning ''). Isso pode ser uma representação de armadilha.
No entanto, o texto da seção 6.2.6.1.7 é o mesmo no rascunho C99 como no rascunho C11.
Esse comportamento é realmente não especificado em C99? Foi especificado em C11? Eu percebo que a maioria dos compiladores parece suportar isso, mas seria bom saber se é especificado no padrão, ou apenas uma extensão muito comum.