You said it yourself: there are memory alignment restrictions on your particular processor, and buffer
is not aligned right to permit reading larger than a byte from it. The assignment is probably compiled into three moves of larger entities.
With memcpy()
, there are no alignment restrictions, it has to be able to copy between any two addresses, so it does whatever is needed to implement that. Probably copying byte-by-byte until the addresses are aligned, that's a common pattern.
As an aside, I find it clearer to write your code without array indexing:
extern const void *buffer;
const foo my_foo = *(const foo *) buffer;