In addition to Booboo's answer, you can try the following which answers your question
How can I get GCC to optimize this into a move?
Just cast each shifted bit-field expression to unsigned short
unsigned short from_half(half h){ return (unsigned short)h.mantissa | (unsigned short)(h.exponent << 10) | (unsigned short)(h.sign << 15);}
It results in:
from_half: mov eax, edi ret
Why isn't it optimized that way already?
I am not sure I have a solid answer on this one. Apparently the intermediate promotion of the bit-fields to int
confuses the optimizer... But this is just a guess.