Friday, 4 February 2011

memcpy: Minor "D'uh" moment on my part, and warning to the wise.

In all the years of writing C code, how did I not spot this.

I know memcpy is not safe if src and dst overlap. I know I should use memmove.
This is not news...

Somehow I managed to not take in this detail when dst is ahead of src in memory.
Somehow I have got away with that for god knows how many years.

Just so you know, some versions of gcc are now optimising to copy from right hand back to left hand or some such, in some cases. i.e. memcpy is not safe if src and dst overlap, either way.

Just one of those silly mistakes from the earliest days of learning C code, many decades ago, which somehow had not caused any problems, until today!

Some global editing has been going on this morning to make sure I am not caught out by it again. I feel so stupid. I may have to go and get a new copy of K&R and re-read it :-)

5 comments:

  1. #define memcpy memmove

    Done :p

    (Note: I don't actually advocate doing this, before the pedants start..)

    ReplyDelete
  2. Don't doubt I considered that for a moment...

    Hopefully I am not alone in this oversight - anyone else not realise it, do fess up to make me feel a bit better... :-)

    ReplyDelete
  3. I write/maintain a widely used C/C++ compiler for a living, and yeah, memcpy is something we spend a lot of effort on optimising on each new platform we support (customers jump up and down a lot if we don't...). That can lead to all sorts of strange ways to copy :-)

    I also get to see some horrendous code sent our way when customers think our compiler doesn't generate the code they think it should... You are not alone!

    ReplyDelete
  4. You are not alone - see https://bugzilla.redhat.com/show_bug.cgi?id=638477.

    As it happens, I was aware of this gotcha from a decidedly different perspective - I encountered an evil memcpy exploiting a feature of the (FPGA-based) memory controller to queue copies of entire pages (with optional offsets leaving blank space in the destination pages), and then go in and fill in the bits that couldn't be done by the memory controller.

    No ordering whatsoever in the memcpy, as the memory controller could (and did) reorder the copies to allow for DRAM banking and the like.

    ReplyDelete
  5. Indeed, and I fully see the point of optimising memcpy in such ways - makes perfect sense.

    And no, I did not even blame the compiler or even start digging through the assembly code generated, I checked the manual first and went looking for a 2x4 to hit myself with.

    I am just really annoyed that, with many decades of experience, this early misunderstanding has stuck with me so long. Thankful such things are very rare.

    We learn something new every day.

    ReplyDelete