aboutsummaryrefslogtreecommitdiff
path: root/mapper.lv2/test
diff options
context:
space:
mode:
authorHanspeter Portner <dev@open-music-kontrollers.ch>2018-01-13 20:33:42 +0100
committerHanspeter Portner <dev@open-music-kontrollers.ch>2018-01-13 20:33:42 +0100
commit0c438ba3e8b2cb8802440ff23c577f45b64be406 (patch)
tree3dae640b91dbe719d5b6bb5da67ae3515da214f0 /mapper.lv2/test
parentec1ce1f04a580e93185fe9d62f02561b4c9f004b (diff)
parentdfb115976ca17515368316626508e0701da21736 (diff)
downloadsynthpod-0c438ba3e8b2cb8802440ff23c577f45b64be406.tar.xz
Merge commit 'dfb115976ca17515368316626508e0701da21736'
Diffstat (limited to 'mapper.lv2/test')
-rw-r--r--mapper.lv2/test/Makefile27
-rw-r--r--mapper.lv2/test/mapper_test.c111
2 files changed, 120 insertions, 18 deletions
diff --git a/mapper.lv2/test/Makefile b/mapper.lv2/test/Makefile
index b722b73a..2fdf6467 100644
--- a/mapper.lv2/test/Makefile
+++ b/mapper.lv2/test/Makefile
@@ -1,6 +1,7 @@
CC ?= clang
C_FLAGS ?= -I../ -Wall -Wextra -Wpedantic $(shell pkg-config --cflags lv2)
-LD_FLAGS ?= -lpthread
+LD_FLAGS ?= -lpthread -lm
+SEED ?= 1234567890
all: mapper_assert mapper_speed
@@ -11,20 +12,20 @@ mapper_speed: mapper_test.c ../mapper.lv2/mapper.h
$(CC) -std=c11 -O3 -o $@ $< $(C_FLAGS) $(LD_FLAGS)
test_assert: mapper_assert
- ./$< 1 0
- ./$< 2 1
- ./$< 4 0
- ./$< 8 1
- ./$< 16 0
- ./$< 32 1
+ ./$< 1 0 $(SEED)
+ ./$< 2 1 $(SEED)
+ ./$< 4 0 $(SEED)
+ ./$< 8 1 $(SEED)
+ ./$< 16 0 $(SEED)
+ ./$< 32 1 $(SEED)
test_speed: mapper_speed
- ./$< 1 0
- ./$< 2 1
- ./$< 4 0
- ./$< 8 1
- ./$< 16 0
- ./$< 32 1
+ ./$< 1 0 $(SEED)
+ ./$< 2 1 $(SEED)
+ ./$< 4 0 $(SEED)
+ ./$< 8 1 $(SEED)
+ ./$< 16 0 $(SEED)
+ ./$< 32 1 $(SEED)
test: test_assert test_speed
diff --git a/mapper.lv2/test/mapper_test.c b/mapper.lv2/test/mapper_test.c
index 212a5dc4..dc584fa2 100644
--- a/mapper.lv2/test/mapper_test.c
+++ b/mapper.lv2/test/mapper_test.c
@@ -23,8 +23,11 @@
#include <inttypes.h>
#include <pthread.h>
#include <assert.h>
+#include <math.h>
-#define MAX_URI_LEN 16
+#include "random.c"
+
+#define MAX_URI_LEN 46
#define MAX_ITEMS 0x100000 // 1M
typedef struct _rtmem_slot_t rtmem_slot_t;
@@ -52,7 +55,9 @@ struct _nrtmem_t {
// per-thread properties
struct _pool_t {
+ mapper_t *mapper;
pthread_t thread;
+ MT mersenne;
};
static rtmem_t *
@@ -61,7 +66,9 @@ rtmem_new(uint32_t rpools)
// create as many slots as worst case scenario dictates it
rtmem_t *rtmem = calloc(1, sizeof(rtmem_t) + (rpools*MAX_ITEMS)*sizeof(rtmem_slot_t));
if(!rtmem)
+ {
return NULL;
+ }
atomic_init(&rtmem->nalloc, 0);
atomic_init(&rtmem->nfree, 0);
@@ -128,7 +135,8 @@ static atomic_bool rolling = ATOMIC_VAR_INIT(false);
static void *
_thread(void *data)
{
- mapper_t *mapper = data;
+ pool_t *pool = data;
+ mapper_t *mapper = pool->mapper;
LV2_URID_Map *map = mapper_get_map(mapper);
LV2_URID_Unmap *unmap = mapper_get_unmap(mapper);
@@ -138,7 +146,29 @@ _thread(void *data)
char uri [MAX_URI_LEN];
for(uint32_t i = 0; i < MAX_ITEMS/2; i++)
{
- snprintf(uri, MAX_URI_LEN, "urn:hx:%08"PRIx32, i);
+ // generate UUID version 4 URN via mersenne twister random number generator
+ {
+ union {
+ uint8_t bytes [0x10];
+ uint32_t u32s [0x4];
+ } un;
+
+ for(unsigned i=0x0; i<0x4; i++)
+ {
+ un.u32s[i] = genrand_int32(&pool->mersenne);
+ }
+
+ un.bytes[6] = (un.bytes[6] & 0x0f) | 0x40; // set four most significant bits of 7th byte to 0b0100
+ un.bytes[8] = (un.bytes[8] & 0x3f) | 0x80; // set two most significant bits of 9th byte to 0b10
+
+ snprintf(uri, MAX_URI_LEN,
+ "urn:uuid:%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x",
+ un.bytes[0x0], un.bytes[0x1], un.bytes[0x2], un.bytes[0x3],
+ un.bytes[0x4], un.bytes[0x5],
+ un.bytes[0x6], un.bytes[0x7],
+ un.bytes[0x8], un.bytes[0x9],
+ un.bytes[0xa], un.bytes[0xb], un.bytes[0xc], un.bytes[0xd], un.bytes[0xe], un.bytes[0xf]);
+ }
const uint32_t urid1 = map->map(map->handle, uri);
assert(urid1);
@@ -165,6 +195,10 @@ main(int argc, char **argv)
const uint32_t n = atoi(argv[1]); // number of concurrent threads
const bool is_rt = atoi(argv[2]); // whether to use rt-memory
+ const uint64_t seed = (argc == 4) // get seed from command line or from time
+ ? atol(argv[3])
+ : time(NULL);
+
// create rt memory
rtmem_t *rtmem = rtmem_new(n);
assert(rtmem);
@@ -182,12 +216,16 @@ main(int argc, char **argv)
pool_t *pools = calloc(n, sizeof(pool_t));
assert(pools);
+ (void)genrand_res53; // to make pedantic compiler happy
+
// init/start threads
for(uint32_t p = 0; p < n; p++)
{
pool_t *pool = &pools[p];
- pthread_create(&pool->thread, NULL, _thread, mapper);
+ pool->mapper = mapper;
+ init_genrand(&pool->mersenne, seed);
+ pthread_create(&pool->thread, NULL, _thread, pool);
}
// signal rolling
@@ -218,6 +256,64 @@ main(int argc, char **argv)
const uint32_t tot_nfree = rt_nfree + nrt_nfree;
assert(tot_nalloc - tot_nfree == usage);
+ // distribution of fills/gaps
+ uint32_t fill_min = UINT32_MAX;
+ uint32_t fill_max = 0;
+ double fill_avg = 0;
+ uint32_t fill_n = 0;
+ for(uint32_t idx = 0, from = 0; idx < mapper->nitems; idx++)
+ {
+ mapper_item_t *item = &mapper->items[idx];
+
+ if(atomic_load_explicit(&item->val, memory_order_relaxed) == 0) // a gap is starting
+ {
+ const uint32_t fill = idx - from; // length of preceding fill
+
+ if(fill == 0)
+ {
+ continue; // ignore zero-length fills
+ }
+
+ if(fill < fill_min)
+ {
+ fill_min = fill;
+ }
+
+ if(fill > fill_max)
+ {
+ fill_max = fill;
+ }
+
+ fill_avg += fill;
+ fill_n += 1;
+ from = idx;
+ }
+ }
+
+ fill_avg /= fill_n;
+
+ double fill_dev = 0;
+ for(uint32_t idx = 0, from = 0; idx < mapper->nitems; idx++)
+ {
+ mapper_item_t *item = &mapper->items[idx];
+
+ if(atomic_load_explicit(&item->val, memory_order_relaxed) == 0) // a gap is starting
+ {
+ const uint32_t fill = idx - from; // length of preceding fill
+
+ if(fill == 0)
+ {
+ continue; // ignore zero-length fills
+ }
+
+ const uint32_t fill_diff = fill - fill_avg;
+ fill_dev += fill_diff*fill_diff;
+ from = idx;
+ }
+ }
+
+ fill_dev = sqrt(fill_dev / (fill_n - 1));
+
// free mapper
mapper_free(mapper);
@@ -235,12 +331,17 @@ main(int argc, char **argv)
// free rt memory
rtmem_free(rtmem);
- printf(
+ fprintf(stderr,
+ " fill-min : %"PRIu32"\n"
+ " fill-max : %"PRIu32"\n"
+ " fill-avg : %.2lf\n"
+ " fill-dev : %.2lf\n"
" rt-allocs : %"PRIu32"\n"
" rt-frees : %"PRIu32"\n"
" nrt-allocs: %"PRIu32"\n"
" nrt-frees : %"PRIu32"\n"
" collisions: %"PRIu32" (%.1f%% of total allocations -> +%.1f%% allocation overhead)\n",
+ fill_min, fill_max, fill_avg, fill_dev,
rt_nalloc, rt_nfree, nrt_nalloc, nrt_nfree,
tot_nfree, 100.f * tot_nfree / tot_nalloc, 100.f * tot_nfree / usage);