From: Pieter Noordhuis Date: Mon, 17 Jan 2011 09:03:21 +0000 (+0100) Subject: Remove client from list of unblocked clients when it is free'd X-Git-Url: https://git.saurik.com/redis.git/commitdiff_plain/3bcffcbe5bc0acde311d0fb311f893400cd52e0e Remove client from list of unblocked clients when it is free'd --- diff --git a/src/networking.c b/src/networking.c index 55daff85..4c3db937 100644 --- a/src/networking.c +++ b/src/networking.c @@ -456,6 +456,13 @@ void freeClient(redisClient *c) { ln = listSearchKey(server.clients,c); redisAssert(ln != NULL); listDelNode(server.clients,ln); + /* When client was just unblocked because of a blocking operation, + * remove it from the list with unblocked clients. */ + if (c->flags & REDIS_UNBLOCKED) { + ln = listSearchKey(server.unblocked_clients,c); + redisAssert(ln != NULL); + listDelNode(server.unblocked_clients,ln); + } /* Remove from the list of clients waiting for swapped keys, or ready * to be restarted, but not yet woken up again. */ if (c->flags & REDIS_IO_WAIT) { diff --git a/src/redis.c b/src/redis.c index 5aabe3bc..af956e91 100644 --- a/src/redis.c +++ b/src/redis.c @@ -688,6 +688,7 @@ void beforeSleep(struct aeEventLoop *eventLoop) { redisAssert(ln != NULL); c = ln->value; listDelNode(server.unblocked_clients,ln); + c->flags &= ~REDIS_UNBLOCKED; /* Process remaining data in the input buffer. */ if (c->querybuf && sdslen(c->querybuf) > 0) diff --git a/src/redis.h b/src/redis.h index 3bfe4cd5..aa42e2c4 100644 --- a/src/redis.h +++ b/src/redis.h @@ -136,6 +136,8 @@ #define REDIS_IO_WAIT 32 /* The client is waiting for Virtual Memory I/O */ #define REDIS_DIRTY_CAS 64 /* Watched keys modified. EXEC will fail. */ #define REDIS_CLOSE_AFTER_REPLY 128 /* Close after writing entire reply. */ +#define REDIS_UNBLOCKED 256 /* This client was unblocked and is stored in + server.unblocked_clients */ /* Client request types */ #define REDIS_REQ_INLINE 1 diff --git a/src/t_list.c b/src/t_list.c index d5db6feb..1c658353 100644 --- a/src/t_list.c +++ b/src/t_list.c @@ -773,7 +773,8 @@ void unblockClientWaitingData(redisClient *c) { zfree(c->bpop.keys); c->bpop.keys = NULL; c->bpop.target = NULL; - c->flags &= (~REDIS_BLOCKED); + c->flags &= ~REDIS_BLOCKED; + c->flags |= REDIS_UNBLOCKED; server.bpop_blocked_clients--; listAddNodeTail(server.unblocked_clients,c); }