Remove the tracking state from the client 'c'. Note that there is not much * to do for us here, if not to decrement the counter of the clients in * tracking mode, because we just store the ID of the client in the tracking * table, so we'll remove the ID reference in a lazy way. Otherwise when a * client with many entries in the table is removed, it would cost a lot of * time to do the cleanup
| 65 | * client with many entries in the table is removed, it would cost a lot of |
| 66 | * time to do the cleanup. */ |
| 67 | void disableTracking(client *c) { |
| 68 | /* If this client is in broadcasting mode, we need to unsubscribe it |
| 69 | * from all the prefixes it is registered to. */ |
| 70 | if (c->flags & CLIENT_TRACKING_BCAST) { |
| 71 | raxIterator ri; |
| 72 | raxStart(&ri,c->client_tracking_prefixes); |
| 73 | raxSeek(&ri,"^",NULL,0); |
| 74 | while(raxNext(&ri)) { |
| 75 | bcastState *bs = raxFind(PrefixTable,ri.key,ri.key_len); |
| 76 | serverAssert(bs != raxNotFound); |
| 77 | raxRemove(bs->clients,(unsigned char*)&c,sizeof(c),NULL); |
| 78 | /* Was it the last client? Remove the prefix from the |
| 79 | * table. */ |
| 80 | if (raxSize(bs->clients) == 0) { |
| 81 | raxFree(bs->clients); |
| 82 | raxFree(bs->keys); |
| 83 | zfree(bs); |
| 84 | raxRemove(PrefixTable,ri.key,ri.key_len,NULL); |
| 85 | } |
| 86 | } |
| 87 | raxStop(&ri); |
| 88 | raxFree(c->client_tracking_prefixes); |
| 89 | c->client_tracking_prefixes = NULL; |
| 90 | } |
| 91 | |
| 92 | /* Clear flags and adjust the count. */ |
| 93 | if (c->flags & CLIENT_TRACKING) { |
| 94 | server.tracking_clients--; |
| 95 | c->flags &= ~(CLIENT_TRACKING|CLIENT_TRACKING_BROKEN_REDIR| |
| 96 | CLIENT_TRACKING_BCAST|CLIENT_TRACKING_OPTIN| |
| 97 | CLIENT_TRACKING_OPTOUT|CLIENT_TRACKING_CACHING| |
| 98 | CLIENT_TRACKING_NOLOOP); |
| 99 | } |
| 100 | } |
| 101 | |
| 102 | static int stringCheckPrefix(unsigned char *s1, size_t s1_len, unsigned char *s2, size_t s2_len) { |
| 103 | size_t min_length = s1_len < s2_len ? s1_len : s2_len; |