From: antirez Date: Sat, 17 Apr 2010 10:54:49 +0000 (+0200) Subject: Merge branch 'hash' of git://github.com/pietern/redis X-Git-Url: https://git.saurik.com/redis.git/commitdiff_plain/4e8dbaf463cefe1710283bfefbccc3db37af5c5a?hp=-c Merge branch 'hash' of git://github.com/pietern/redis --- 4e8dbaf463cefe1710283bfefbccc3db37af5c5a diff --combined redis.c index 14a0e7e0,6a952b01..63679fc7 --- a/redis.c +++ b/redis.c @@@ -2775,6 -2775,23 +2775,23 @@@ static robj *createStringObject(char *p return createObject(REDIS_STRING,sdsnewlen(ptr,len)); } + static robj *createStringObjectFromLongLong(long long value) { + robj *o; + if (value >= 0 && value < REDIS_SHARED_INTEGERS) { + incrRefCount(shared.integers[value]); + o = shared.integers[value]; + } else { + o = createObject(REDIS_STRING, NULL); + if (value >= LONG_MIN && value <= LONG_MAX) { + o->encoding = REDIS_ENCODING_INT; + o->ptr = (void*)((long)value); + } else { + o->ptr = sdscatprintf(sdsempty(),"%lld",value); + } + } + return o; + } + static robj *dupStringObject(robj *o) { assert(o->encoding == REDIS_ENCODING_RAW); return createStringObject(o->ptr,sdslen(o->ptr)); @@@ -2841,7 -2858,7 +2858,7 @@@ static void freeHashObject(robj *o) zfree(o->ptr); break; default: - redisAssert(0); + redisPanic("Unknown hash encoding type"); break; } } @@@ -2881,7 -2898,7 +2898,7 @@@ static void decrRefCount(void *obj) case REDIS_SET: freeSetObject(o); break; case REDIS_ZSET: freeZsetObject(o); break; case REDIS_HASH: freeHashObject(o); break; - default: redisAssert(0); break; + default: redisPanic("Unknown object type"); break; } if (server.vm_enabled) pthread_mutex_lock(&server.obj_freelist_mutex); if (listLength(server.objfreelist) > REDIS_OBJFREELIST_MAX || @@@ -3411,7 -3428,7 +3428,7 @@@ static int rdbSaveObject(FILE *fp, rob dictReleaseIterator(di); } } else { - redisAssert(0); + redisPanic("Unknown object type"); } return 0; } @@@ -3632,7 -3649,7 +3649,7 @@@ static robj *rdbLoadIntegerObject(FILE val = (int32_t)v; } else { val = 0; /* anti-warning */ - redisAssert(0); + redisPanic("Unknown RDB integer encoding type"); } return createObject(REDIS_STRING,sdscatprintf(sdsempty(),"%lld",val)); } @@@ -3671,7 -3688,7 +3688,7 @@@ static robj *rdbLoadStringObject(FILE*f case REDIS_RDB_ENC_LZF: return rdbLoadLzfStringObject(fp); default: - redisAssert(0); + redisPanic("Unknown RDB encoding type"); } } @@@ -3793,7 -3810,7 +3810,7 @@@ static robj *rdbLoadObject(int type, FI } } } else { - redisAssert(0); + redisPanic("Unknown object type"); } return o; } @@@ -5607,7 -5624,7 +5624,7 @@@ inline static void zunionInterAggregate *target = val > *target ? val : *target; } else { /* safety net */ - redisAssert(0 != 0); + redisPanic("Unknown ZUNION/INTER aggregate type"); } } @@@ -6068,6 -6085,14 +6085,14 @@@ static void hashTryConversion(robj *sub } } + /* Encode given objects in-place when the hash uses a dict. */ + static void hashTryObjectEncoding(robj *subject, robj **o1, robj **o2) { + if (subject->encoding == REDIS_ENCODING_HT) { + if (o1) *o1 = tryObjectEncoding(*o1); + if (o2) *o2 = tryObjectEncoding(*o2); + } + } + /* Get the value from a hash identified by key. Returns either a string * object or NULL if the value cannot be found. The refcount of the object * is always increased by 1 when the value was found. */ @@@ -6126,7 -6151,6 +6151,6 @@@ static int hashSet(robj *o, robj *key, if (zipmapLen(o->ptr) > server.hash_max_zipmap_entries) convertToRealHash(o); } else { - value = tryObjectEncoding(value); if (dictReplace(o->ptr,key,value)) { /* Insert */ incrRefCount(key); @@@ -6250,6 -6274,7 +6274,7 @@@ static void hsetCommand(redisClient *c if ((o = hashLookupWriteOrCreate(c,c->argv[1])) == NULL) return; hashTryConversion(o,c->argv,2,3); + hashTryObjectEncoding(o,&c->argv[2], &c->argv[3]); update = hashSet(o,c->argv[2],c->argv[3]); addReply(c, update ? shared.czero : shared.cone); server.dirty++; @@@ -6263,6 -6288,7 +6288,7 @@@ static void hsetnxCommand(redisClient * if (hashExists(o, c->argv[2])) { addReply(c, shared.czero); } else { + hashTryObjectEncoding(o,&c->argv[2], &c->argv[3]); hashSet(o,c->argv[2],c->argv[3]); addReply(c, shared.cone); server.dirty++; @@@ -6281,9 -6307,11 +6307,11 @@@ static void hmsetCommand(redisClient *c if ((o = hashLookupWriteOrCreate(c,c->argv[1])) == NULL) return; hashTryConversion(o,c->argv,2,c->argc-1); for (i = 2; i < c->argc; i += 2) { + hashTryObjectEncoding(o,&c->argv[i], &c->argv[i+1]); hashSet(o,c->argv[i],c->argv[i+1]); } addReply(c, shared.ok); + server.dirty++; } static void hincrbyCommand(redisClient *c) { @@@ -6305,7 -6333,8 +6333,8 @@@ } value += incr; - new = createObject(REDIS_STRING,sdscatprintf(sdsempty(),"%lld",value)); + new = createStringObjectFromLongLong(value); + hashTryObjectEncoding(o,&c->argv[2],NULL); hashSet(o,c->argv[2],new); decrRefCount(new); addReplyLongLong(c,value); @@@ -6666,7 -6695,7 +6695,7 @@@ static void sortCommand(redisClient *c case REDIS_LIST: vectorlen = listLength((list*)sortval->ptr); break; case REDIS_SET: vectorlen = dictSize((dict*)sortval->ptr); break; case REDIS_ZSET: vectorlen = dictSize(((zset*)sortval->ptr)->dict); break; - default: vectorlen = 0; redisAssert(0); /* Avoid GCC warning */ + default: vectorlen = 0; redisPanic("Bad SORT type"); /* Avoid GCC warning */ } vector = zmalloc(sizeof(redisSortObject)*vectorlen); j = 0; @@@ -8215,7 -8244,7 +8244,7 @@@ static int rewriteAppendOnlyFile(char * dictReleaseIterator(di); } } else { - redisAssert(0); + redisPanic("Unknown object type"); } /* Save the expire time */ if (expiretime != -1) {