I need to write a repeating pattern to memory (e.g. 0x11223344
), so that the whole memory looks like (in hex):
1122334411223344112233441122334411223344112233441122334411223344...
I can't figure out how to do it with memset()
because it takes only a single byte, not 4 bytes.
Any ideas?
memset() will blindly write to the specified address for the number of specified bytes, regardless of what it might be overwriting. It is up to the programmer to ensure that only valid memory is written to.
CPP. Note: We can use memset() to set all values as 0 or -1 for integral data types also. It will not work if we use it to set as other values. The reason is simple, memset works byte by byte.
memcpy() copies from one place to another. memset() just sets all pieces of memory to the same. For example here sets string length of the string str to * (or whatever second argument of the memset). Here copies the string length of the string src to dest.
The memset() function sets the first count bytes of dest to the value c. The value of c is converted to an unsigned character.
On OS X, one uses memset_pattern4( )
for this; I would expect other platforms to have similar APIs.
I don't know of a simple portable solution, other than just filling in the buffer with a loop (which is pretty darn simple).
An efficient way would be to cast the pointer to a pointer of the needed size in bytes (e.g. uint32_t
for 4 bytes) and fill with integers. It's a little ugly though.
char buf[256] = { 0, }; uint32_t * p = (uint32_t *) buf, i; for (i = 0; i < sizeof(buf) / sizeof(* p); i++) { p[i] = 0x11223344; }
Not tested!
Recursively copy the memory, using the area which you already filled as a template per iteration O(log(N)):
int fillLen = ...;
int blockSize = 4; // Size of your pattern
memmove(dest, srcPattern, blockSize);
char * start = dest;
char * current = dest + blockSize;
char * end = start + fillLen;
while(current + blockSize < end) {
memmove(current, start, blockSize);
current += blockSize;
blockSize *= 2;
}
// fill the rest
memmove(current, start, (int)end-current);
What I mean with O(log(N)) is that the runtime will be much faster than if you fill the memory manually since memmove()
usually uses special, hand-optimized assembler loops that are blazing fast.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With