expires: refactoring judgment about whether a key is expired

Calling lookupKey*() many times to search a key in one command
may get different result.

That's because lookupKey*() calls expireIfNeeded(), and delete
the key when reach the expire time. So we can get an robj before
the expire time, but a NULL after the expire time.

The worst is that may lead to Redis crash, for example
`RPOPLPUSH foo foo` the first time we get a list form `foo` and
hold the pointer, but when we get `foo` again it's expired and
deleted. Now we hold a freed memory, when execute rpoplpushHandlePush()
redis crash.

To fix it, we can refactor the judgment about whether a key is expired,
using the same basetime `server.cmd_start_mstime` instead of calling
mstime() everytime.
This commit is contained in:
zhaozhao.zz
2019-11-04 20:32:19 +08:00
committed by antirez
parent fdaea2a7a7
commit e542132b07
3 changed files with 3 additions and 1 deletions

View File

@ -3596,6 +3596,7 @@ int processCommand(client *c) {
queueMultiCommand(c);
addReply(c,shared.queued);
} else {
server.cmd_start_mstime = mstime();
call(c,CMD_CALL_FULL);
c->woff = server.master_repl_offset;
if (listLength(server.ready_keys))