cmemmove

implementing memmove without copying the source data


I need to implement myself the standard c function memmove.

void *memmove(void *str1, const void *str2, size_t n)

Can I avoid copying the source (pointed by str2) into a temporary buffer before doing the actual copy ?

Thanks!


Solution

  • The description of memmove says that

    Copying takes place as if the n characters from the object pointed to by s2 are first copied into a temporary array of n characters that does not overlap the objects pointed to by s1 and s2, and then the n characters from the temporary array are copied into the object pointed to by s1.

    Now the "as if" part tells that this is just used to explain the observable behaviour, and not that it is how an implementation actually has to do it.

    But then comes the fun fact: it is actually not possible to implement memmove in portable standard C without copying the entire source into a temporary buffer in most cases (you could avoid doing a copy altogether if src == dest).

    If you do character-by-character copy, you could check which pointer comes first in memory, i.e. if target > source it means that you would need to copy in reverse, i.e. starting from n - 1 and copying backwards.

    The caveat is that using target > source is strictly conforming only if both pointers point to members of the same array. This isn't just theoretical - x86 real mode segmented memory models for example can make pointer comparison difficult.

    With the caveat in mind, you could just cast both to uintptr_t for the comparison and hope for the best (and fear for the worst). I believe converting to uintptr_t wouldn't work on x86 real mode (i.e. the "640 kilobytes should be enough for anyone" mode), but who'd want to program for it anyway.