From b877b5f98680b58ffe8b1fae7ae1a8eb4f31b8d1 Mon Sep 17 00:00:00 2001 From: Jay Pipes Date: Thu, 23 Nov 2017 10:01:50 -0500 Subject: [PATCH 1/2] Adds support for variable-length rand string Adds a new random generator of variable-length strings: ```lua s = sysbench.rand.varstring(10, 100) ``` "s" will be a string containing ASCII characters from '0' to 'z', inclusive. It will be a length between 10 and 100 characters long. Addresses GH Issue #17 --- src/lua/internal/sysbench.rand.lua | 10 ++++++++++ src/sb_rand.c | 26 +++++++++++++++++++++++++ src/sb_rand.h | 1 + tests/t/api_rand.t | 31 +++++++++++++++++++----------- 4 files changed, 57 insertions(+), 11 deletions(-) diff --git a/src/lua/internal/sysbench.rand.lua b/src/lua/internal/sysbench.rand.lua index df6198d..2ff6766 100644 --- a/src/lua/internal/sysbench.rand.lua +++ b/src/lua/internal/sysbench.rand.lua @@ -32,6 +32,7 @@ uint32_t sb_rand_pareto(uint32_t, uint32_t); uint32_t sb_rand_zipfian(uint32_t, uint32_t); uint32_t sb_rand_unique(void); void sb_rand_str(const char *, char *); +void sb_rand_varstr(char *, uint32_t, uint32_t); double sb_rand_uniform_double(void); ]] @@ -74,6 +75,15 @@ function sysbench.rand.string(fmt) return ffi.string(buf, buflen) end +function sysbench.rand.varstring(min_len, max_len) + assert(min_len <= max_len) + assert(max_len > 0) + local buflen = max_len + local buf = ffi.new("uint8_t[?]", buflen) + local nchars = ffi.C.sb_rand_varstr(buf, min_len, max_len) + return ffi.string(buf, nchars) +end + function sysbench.rand.uniform_double() return ffi.C.sb_rand_uniform_double() end diff --git a/src/sb_rand.c b/src/sb_rand.c index 9088a3b..5e89892 100644 --- a/src/sb_rand.c +++ b/src/sb_rand.c @@ -343,6 +343,32 @@ void sb_rand_str(const char *fmt, char *buf) } } +/* + Generates a random string of ASCII characters between '0' and 'z' of a length + between min and max. buf should have enough room for max len bytes. Returns + the number of characters written into the buffer. + */ + +uint32_t sb_rand_varstr(char *buf, uint32_t min_len, uint32_t max_len) +{ + unsigned int i; + uint32_t num_chars; + if (max_len == 0) { + return; /* we can't be sure buf is long enough to populate, so be safe */ + } + if (min_len > max_len) + { + min_len = 1; + } + + num_chars = sb_rand_uniform(min_len, max_len); + for (i=0; i < num_chars; i++) + { + buf[i] = sb_rand_uniform('0', 'z'); + } + return num_chars; +} + /* Unique random sequence generator. This is based on public domain code from https://github.com/preshing/RandomSequence diff --git a/src/sb_rand.h b/src/sb_rand.h index d900204..32f7634 100644 --- a/src/sb_rand.h +++ b/src/sb_rand.h @@ -71,5 +71,6 @@ uint32_t sb_rand_pareto(uint32_t, uint32_t); uint32_t sb_rand_zipfian(uint32_t, uint32_t); uint32_t sb_rand_unique(void); void sb_rand_str(const char *, char *); +uint32_t sb_rand_varstr(char *, uint32_t, uint32_t); #endif /* SB_RAND_H */ diff --git a/tests/t/api_rand.t b/tests/t/api_rand.t index 45b39c3..7847bf4 100644 --- a/tests/t/api_rand.t +++ b/tests/t/api_rand.t @@ -7,8 +7,14 @@ PRNG Lua API tests $ cat >$CRAMTMP/api_rand.lua < ffi.cdef[[int printf(const char *fmt, ...);]] > function init() - > for k, v in pairs(sysbench.rand) do - > print(string.format("sysbench.rand.%s", k)) + > -- Ensure a consistent sort order... + > mod_funcs = {} + > for f in pairs(sysbench.rand) do + > table.insert(mod_funcs, f) + > end + > table.sort(mod_funcs) + > for i, f in ipairs(mod_funcs) do + > print(string.format("sysbench.rand.%s", f)) > end > end > function event() @@ -16,6 +22,7 @@ PRNG Lua API tests > print("sysbench.rand.unique(0, 4294967295) = " .. sysbench.rand.unique(0, 4294967295)) > ffi.C.printf("sysbench.rand.uniform_uint64() = %llu\n", sysbench.rand.uniform_uint64()) > print([[sysbench.rand.string("abc-###-@@@-xyz") = ]] .. sysbench.rand.string("abc-###-@@@-xyz")) + > print([[sysbench.rand.varstring(1, 23) = ]] .. sysbench.rand.varstring(1, 23)) > print("sysbench.rand.uniform(0, 99) = " .. sysbench.rand.uniform(0, 99)) > print("sysbench.rand.gaussian(0, 99) = " .. sysbench.rand.gaussian(0, 99)) > print("sysbench.rand.special(0, 99) = " .. sysbench.rand.special(0, 99)) @@ -25,20 +32,22 @@ PRNG Lua API tests > EOF $ sysbench $SB_ARGS $CRAMTMP/api_rand.lua run - sysbench.rand.uniform - sysbench.rand.special - sysbench.rand.zipfian - sysbench.rand.unique - sysbench.rand.gaussian - sysbench.rand.uniform_uint64 - sysbench.rand.uniform_double - sysbench.rand.pareto - sysbench.rand.string sysbench.rand.default + sysbench.rand.gaussian + sysbench.rand.pareto + sysbench.rand.special + sysbench.rand.string + sysbench.rand.uniform + sysbench.rand.uniform_double + sysbench.rand.uniform_uint64 + sysbench.rand.unique + sysbench.rand.varstring + sysbench.rand.zipfian sysbench.rand.default\(0, 99\) = [0-9]{1,2} (re) sysbench.rand.unique\(0, 4294967295\) = [0-9]{1,10} (re) sysbench.rand.uniform_uint64\(\) = [0-9]+ (re) sysbench.rand.string\(".*"\) = abc-[0-9]{3}-[a-z]{3}-xyz (re) + sysbench.rand.varstring\(1, 23\) = [0-z]{1,23} (re) sysbench.rand.uniform\(0, 99\) = [0-9]{1,2} (re) sysbench.rand.gaussian\(0, 99\) = [0-9]{1,2} (re) sysbench.rand.special\(0, 99\) = [0-9]{1,2} (re) From 185e8bc8534aaa949ecb8ade0e0b2f35773d22bb Mon Sep 17 00:00:00 2001 From: Jay Pipes Date: Sat, 25 Nov 2017 08:54:34 -0500 Subject: [PATCH 2/2] Return 0 when max_len == 0 --- src/sb_rand.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/sb_rand.c b/src/sb_rand.c index 5e89892..712335b 100644 --- a/src/sb_rand.c +++ b/src/sb_rand.c @@ -354,7 +354,7 @@ uint32_t sb_rand_varstr(char *buf, uint32_t min_len, uint32_t max_len) unsigned int i; uint32_t num_chars; if (max_len == 0) { - return; /* we can't be sure buf is long enough to populate, so be safe */ + return 0; /* we can't be sure buf is long enough to populate, so be safe */ } if (min_len > max_len) {