Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can I copy a repeating pattern into a memory buffer?

Tags:

c

memcpy

I want write a repeating pattern of bytes into a block of memory. My idea is to write the first example of the pattern, and then copy it into the rest of the buffer. For example, if I start with this:

ptr: 123400000000

Afterward, I want it to look like this:

ptr: 123412341234

I thought I could use memcpy to write to intersecting regions, like this:

memcpy(ptr + 4, ptr, 8);

The standard does not specify what order the copy will happen in, so if some implementation makes it copy in reverse order, it can give different results:

ptr: 123412340000

or even combined results.

Is there any workaround that lets me still use memcpy, or do I have to implement my own for loop? Note that I cannot use memmove because it does exactly what I'm trying to avoid; it make the ptr be 123412340000, while I want 123412341234.

I program for Mac/iPhone(clang compiler) but a general answer will be good too.

like image 694
Dani Avatar asked Jun 12 '11 21:06

Dani


2 Answers

There is no standard function to repeat a pattern of bytes upon a memory range. You can use the memset_pattern* function family to get fixed-size patterns; if you need the size to vary, you'll have to roll your own.

// fills the 12 first bytes at `ptr` with the 4 first bytes of `ptr`
memset_pattern4(ptr, ptr, 12);

Be aware that memset_pattern4, memset_pattern8 and memset_pattern16 exist only on Mac OS/iOS, so don't use them for cross-platform development.

Otherwise, rolling a (cross-platform) function that does a byte-per-byte copy is pretty easy.

void byte_copy(void* into, void* from, size_t size)
{
    for (size_t i = 0; i < size; i++)
        into[i] = from[i];
}
like image 148
zneak Avatar answered Nov 29 '22 08:11

zneak


Here is what kernel.org says:

The memcpy() function copies n bytes from memory area src to memory area dest. The memory areas must not overlap. Use memmove(3) if the memory areas do overlap.

An here is what MSDN says:

If the source and destination overlap, the behavior of memcpy is undefined. Use memmove to handle overlapping regions.

like image 24
cnicutar Avatar answered Nov 29 '22 09:11

cnicutar