diff --git a/src/quicklist.c b/src/quicklist.c index adf9ba1d..9cb05252 100644 --- a/src/quicklist.c +++ b/src/quicklist.c @@ -671,6 +671,7 @@ int quicklistReplaceAtIndex(quicklist *quicklist, long index, void *data, /* quicklistIndex provides an uncompressed node */ entry.node->zl = ziplistDelete(entry.node->zl, &entry.zi); entry.node->zl = ziplistInsert(entry.node->zl, entry.zi, data, sz); + quicklistNodeUpdateSz(entry.node); quicklistCompress(quicklist, entry.node); return 1; } else { diff --git a/src/redismodule.h b/src/redismodule.h index f1aaea49..fd9e46dc 100644 --- a/src/redismodule.h +++ b/src/redismodule.h @@ -100,7 +100,7 @@ typedef void (*RedisModuleTypeFreeFunc)(void *value); void *REDISMODULE_API_FUNC(RedisModule_Alloc)(size_t bytes); void *REDISMODULE_API_FUNC(RedisModule_Realloc)(void *ptr, size_t bytes); void REDISMODULE_API_FUNC(RedisModule_Free)(void *ptr); -void REDISMODULE_API_FUNC(RedisModule_Calloc)(size_t nmemb, size_t size); +void *REDISMODULE_API_FUNC(RedisModule_Calloc)(size_t nmemb, size_t size); char *REDISMODULE_API_FUNC(RedisModule_Strdup)(const char *str); int REDISMODULE_API_FUNC(RedisModule_GetApi)(const char *, void *); int REDISMODULE_API_FUNC(RedisModule_CreateCommand)(RedisModuleCtx *ctx, const char *name, RedisModuleCmdFunc cmdfunc, const char *strflags, int firstkey, int lastkey, int keystep); diff --git a/tests/unit/type/list-3.tcl b/tests/unit/type/list-3.tcl index ece6ea2d..b5bd48cb 100644 --- a/tests/unit/type/list-3.tcl +++ b/tests/unit/type/list-3.tcl @@ -13,6 +13,50 @@ start_server { assert_equal [r lindex l 1] [lindex $mylist 1] } + test {Regression for quicklist #3343 bug} { + r del mylist + r lpush mylist 401 + r lpush mylist 392 + r rpush mylist [string repeat x 5105]"799" + r lset mylist -1 [string repeat x 1014]"702" + r lpop mylist + r lset mylist -1 [string repeat x 4149]"852" + r linsert mylist before 401 [string repeat x 9927]"12" + r lrange mylist 0 -1 + r ping ; # It's enough if the server is still alive + } {PONG} + + test {Stress tester for #3343-alike bugs} { + r del key + for {set j 0} {$j < 10000} {incr j} { + set op [randomInt 6] + set small_signed_count [expr 5-[randomInt 10]] + if {[randomInt 2] == 0} { + set ele [randomInt 1000] + } else { + set ele [string repeat x [randomInt 10000]][randomInt 1000] + } + switch $op { + 0 {r lpush key $ele} + 1 {r rpush key $ele} + 2 {r lpop key} + 3 {r rpop key} + 4 { + catch {r lset key $small_signed_count $ele} + } + 5 { + set otherele [randomInt 1000] + if {[randomInt 2] == 0} { + set where before + } else { + set where after + } + r linsert key $where $otherele $ele + } + } + } + } + tags {slow} { test {ziplist implementation: value encoding and backlink} { if {$::accurate} {set iterations 100} else {set iterations 10}