From 95f68f7b0fc4ffc700361484b6c792a8e03f3a13 Mon Sep 17 00:00:00 2001 From: antirez Date: Thu, 22 Nov 2012 15:50:00 +0100 Subject: [PATCH] EVALSHA is now case insensitive. EVALSHA used to crash if the SHA1 was not lowercase (Issue #783). Fixed using a case insensitive dictionary type for the sha -> script map used for replication of scripts. --- src/redis.c | 13 ++++++++++++- src/redis.h | 1 + src/scripting.c | 2 +- tests/unit/scripting.tcl | 4 ++++ 4 files changed, 18 insertions(+), 2 deletions(-) diff --git a/src/redis.c b/src/redis.c index 77dc174d..e3db30f7 100644 --- a/src/redis.c +++ b/src/redis.c @@ -393,7 +393,8 @@ int dictSdsKeyCompare(void *privdata, const void *key1, return memcmp(key1, key2, l1) == 0; } -/* A case insensitive version used for the command lookup table. */ +/* A case insensitive version used for the command lookup table and other + * places where case insensitive non binary-safe comparison is needed. */ int dictSdsKeyCaseCompare(void *privdata, const void *key1, const void *key2) { @@ -508,6 +509,16 @@ dictType dbDictType = { dictRedisObjectDestructor /* val destructor */ }; +/* server.lua_scripts sha (as sds string) -> scripts (as robj) cache. */ +dictType shaScriptObjectDictType = { + dictSdsCaseHash, /* hash function */ + NULL, /* key dup */ + NULL, /* val dup */ + dictSdsKeyCaseCompare, /* key compare */ + dictSdsDestructor, /* key destructor */ + dictRedisObjectDestructor /* val destructor */ +}; + /* Db->expires */ dictType keyptrDictType = { dictSdsHash, /* hash function */ diff --git a/src/redis.h b/src/redis.h index a091e990..b51a482f 100644 --- a/src/redis.h +++ b/src/redis.h @@ -890,6 +890,7 @@ extern dictType setDictType; extern dictType zsetDictType; extern dictType clusterNodesDictType; extern dictType dbDictType; +extern dictType shaScriptObjectDictType; extern double R_Zero, R_PosInf, R_NegInf, R_Nan; extern dictType hashDictType; diff --git a/src/scripting.c b/src/scripting.c index 23404338..d614f42a 100644 --- a/src/scripting.c +++ b/src/scripting.c @@ -532,7 +532,7 @@ void scriptingInit(void) { /* Initialize a dictionary we use to map SHAs to scripts. * This is useful for replication, as we need to replicate EVALSHA * as EVAL, so we need to remember the associated script. */ - server.lua_scripts = dictCreate(&dbDictType,NULL); + server.lua_scripts = dictCreate(&shaScriptObjectDictType,NULL); /* Register the redis commands table and fields */ lua_newtable(lua); diff --git a/tests/unit/scripting.tcl b/tests/unit/scripting.tcl index f96d0fc6..f1df11f3 100644 --- a/tests/unit/scripting.tcl +++ b/tests/unit/scripting.tcl @@ -47,6 +47,10 @@ start_server {tags {"scripting"}} { r evalsha 9bd632c7d33e571e9f24556ebed26c3479a87129 0 } {myval} + test {EVALSHA - Can we call a SHA1 in uppercase?} { + r evalsha 9BD632C7D33E571E9F24556EBED26C3479A87129 0 + } {myval} + test {EVALSHA - Do we get an error on invalid SHA1?} { catch {r evalsha NotValidShaSUM 0} e set _ $e -- 2.45.2