#include <stdio.h>
#include <string.h>
#include "libpmem.h"
#include "unittest.h"
#define CACHELINE 64
#define N_BYTES 8192
typedef void *(*mem_fn)(void *, const void *, size_t);
static void
check_func(void *dest, void *src, size_t len, mem_fn mem_func)
{
memset(dest, 1, len);
memset(src, 0, len);
mem_func(dest, src, len);
if (memcmp(dest, src, len))
UT_FATAL("memcpy/memmove failed");
}
static void
check_memmove(void *dest, void *src, size_t len)
{
check_func(dest, src, len, pmem_memmove_persist);
}
static void
check_memcpy(void *dest, void *src, size_t len)
{
check_func(dest, src, len, pmem_memcpy_persist);
}
static void
check_memset(void *dest, size_t len)
{
char *buff = MALLOC(sizeof(char) * len);
memset(buff, 1, len);
pmem_memset_persist(dest, 1, len);
if (memcmp(dest, buff, len))
UT_FATAL("memset failed");
FREE(buff);
}
int
main(int argc, char *argv[])
{
START(argc, argv, "pmem_movnt_align");
if (argc != 2)
UT_FATAL("usage: %s type", argv[0]);
char type = argv[1][0];
char *src, *dst;
size_t s;
switch (type) {
case 'C':
src = MMAP_ANON_ALIGNED(N_BYTES, 0);
dst = MMAP_ANON_ALIGNED(N_BYTES, 0);
if (src == NULL || dst == NULL)
UT_FATAL("!mmap");
check_memcpy(dst, src, 0);
for (s = 0; s < CACHELINE; s++)
check_memcpy(dst, src, N_BYTES - s);
for (s = 0; s < CACHELINE; s++)
check_memcpy(dst + s, src, N_BYTES - s);
for (s = 0; s < CACHELINE; s++)
check_memcpy(dst + s, src + s, N_BYTES - 2 * s);
MUNMAP_ANON_ALIGNED(src, N_BYTES);
MUNMAP_ANON_ALIGNED(dst, N_BYTES);
break;
case 'B':
src = MMAP_ANON_ALIGNED(2 * N_BYTES - 4096, 0);
dst = src + N_BYTES - 4096;
if (src == NULL)
UT_FATAL("!mmap");
check_memmove(dst, src, 0);
for (s = 0; s < CACHELINE; s++)
check_memmove(dst, src, N_BYTES - s);
for (s = 0; s < CACHELINE; s++)
check_memmove(dst + s, src, N_BYTES - s);
for (s = 0; s < CACHELINE; s++)
check_memmove(dst + s, src + s, N_BYTES - 2 * s);
MUNMAP_ANON_ALIGNED(src, 2 * N_BYTES - 4096);
break;
case 'F':
dst = MMAP_ANON_ALIGNED(2 * N_BYTES - 4096, 0);
src = dst + N_BYTES - 4096;
if (src == NULL)
UT_FATAL("!mmap");
check_memmove(dst, src, 0);
for (s = 0; s < CACHELINE; s++)
check_memmove(dst, src, N_BYTES - s);
for (s = 0; s < CACHELINE; s++)
check_memmove(dst + s, src, N_BYTES - s);
for (s = 0; s < CACHELINE; s++)
check_memmove(dst + s, src + s, N_BYTES - 2 * s);
MUNMAP_ANON_ALIGNED(dst, 2 * N_BYTES - 4096);
break;
case 'S':
dst = MMAP_ANON_ALIGNED(N_BYTES, 0);
if (dst == NULL)
UT_FATAL("!mmap");
check_memset(dst, 0);
for (s = 0; s < CACHELINE; s++)
check_memset(dst, N_BYTES - s);
for (s = 0; s < CACHELINE; s++)
check_memset(dst + s, N_BYTES - s);
for (s = 0; s < CACHELINE; s++)
check_memset(dst + s, N_BYTES - 2 * s);
MUNMAP_ANON_ALIGNED(dst, N_BYTES);
break;
default:
UT_FATAL("!wrong type of test");
break;
}
DONE(NULL);
}