Skip to content
体验新版
项目
组织
正在加载...
登录
切换导航
打开侧边栏
dk131072
redis
提交
c41f94d2
R
redis
项目概览
dk131072
/
redis
与 Fork 源项目一致
从无法访问的项目Fork
通知
2
Star
0
Fork
0
代码
文件
提交
分支
Tags
贡献者
分支图
Diff
Issue
0
列表
看板
标记
里程碑
合并请求
0
Wiki
0
Wiki
分析
仓库
DevOps
项目成员
Pages
R
redis
项目概览
项目概览
详情
发布
仓库
仓库
文件
提交
分支
标签
贡献者
分支图
比较
Issue
0
Issue
0
列表
看板
标记
里程碑
合并请求
0
合并请求
0
Pages
分析
分析
仓库分析
DevOps
Wiki
0
Wiki
成员
成员
收起侧边栏
关闭侧边栏
动态
分支图
创建新Issue
提交
Issue看板
体验新版 GitCode,发现更多精彩内容 >>
提交
c41f94d2
编写于
7月 22, 2019
作者:
A
antirez
浏览文件
操作
浏览文件
下载
电子邮件补丁
差异文件
Client side caching: split invalidation into key / slot.
上级
09c06698
变更
3
隐藏空白更改
内联
并排
Showing
3 changed file
with
41 addition
and
16 deletion
+41
-16
src/server.c
src/server.c
+4
-0
src/server.h
src/server.h
+1
-0
src/tracking.c
src/tracking.c
+36
-16
未找到文件。
src/server.c
浏览文件 @
c41f94d2
...
...
@@ -3401,6 +3401,10 @@ int processCommand(client *c) {
}
}
/* Make sure to use a reasonable amount of memory for client side
* caching metadata. */
if
(
server
.
tracking_clients
)
trackingLimitUsedSlots
();
/* Don't accept write commands if there are problems persisting on disk
* and if this is a master instance. */
int
deny_write_type
=
writeCommandsDeniedByDiskError
();
...
...
src/server.h
浏览文件 @
c41f94d2
...
...
@@ -1639,6 +1639,7 @@ void disableTracking(client *c);
void
trackingRememberKeys
(
client
*
c
);
void
trackingInvalidateKey
(
robj
*
keyobj
);
void
trackingInvalidateKeysOnFlush
(
int
dbid
);
void
trackingLimitUsedSlots
(
void
);
/* List data type */
void
listTypeTryConversion
(
robj
*
subject
,
robj
*
value
);
...
...
src/tracking.c
浏览文件 @
c41f94d2
...
...
@@ -154,37 +154,43 @@ void sendTrackingMessage(client *c, long long hash) {
}
}
/* This function is called from signalModifiedKey() or other places in Redis
* when a key changes value. In the context of keys tracking, our task here is
* to send a notification to every client that may have keys about such caching
* slot. */
void
trackingInvalidateKey
(
robj
*
keyobj
)
{
if
(
TrackingTable
==
NULL
||
TrackingTableUsedSlots
==
0
)
return
;
sds
sdskey
=
keyobj
->
ptr
;
uint64_t
hash
=
crc64
(
0
,
(
unsigned
char
*
)
sdskey
,
sdslen
(
sdskey
))
&
(
TRACKING_TABLE_SIZE
-
1
);
if
(
TrackingTable
[
hash
]
==
NULL
)
return
;
/* Invalidates a caching slot: this is actually the low level implementation
* of the API that Redis calls externally, that is trackingInvalidateKey(). */
void
trackingInvalidateSlot
(
uint64_t
slot
)
{
if
(
TrackingTable
==
NULL
||
TrackingTable
[
slot
]
==
NULL
)
return
;
raxIterator
ri
;
raxStart
(
&
ri
,
TrackingTable
[
hash
]);
raxStart
(
&
ri
,
TrackingTable
[
slot
]);
raxSeek
(
&
ri
,
"^"
,
NULL
,
0
);
while
(
raxNext
(
&
ri
))
{
uint64_t
id
;
memcpy
(
&
id
,
ri
.
key
,
ri
.
key_len
);
client
*
c
=
lookupClientByID
(
id
);
if
(
c
==
NULL
||
!
(
c
->
flags
&
CLIENT_TRACKING
))
continue
;
sendTrackingMessage
(
c
,
hash
);
sendTrackingMessage
(
c
,
slot
);
}
raxStop
(
&
ri
);
/* Free the tracking table: we'll create the radix tree and populate it
* again if more keys will be modified in this
hash
slot. */
raxFree
(
TrackingTable
[
hash
]);
TrackingTable
[
hash
]
=
NULL
;
* again if more keys will be modified in this
caching
slot. */
raxFree
(
TrackingTable
[
slot
]);
TrackingTable
[
slot
]
=
NULL
;
TrackingTableUsedSlots
--
;
}
/* This function is called from signalModifiedKey() or other places in Redis
* when a key changes value. In the context of keys tracking, our task here is
* to send a notification to every client that may have keys about such caching
* slot. */
void
trackingInvalidateKey
(
robj
*
keyobj
)
{
if
(
TrackingTable
==
NULL
||
TrackingTableUsedSlots
==
0
)
return
;
sds
sdskey
=
keyobj
->
ptr
;
uint64_t
hash
=
crc64
(
0
,
(
unsigned
char
*
)
sdskey
,
sdslen
(
sdskey
))
&
(
TRACKING_TABLE_SIZE
-
1
);
trackingInvalidateSlot
(
hash
);
}
/* This function is called when one or all the Redis databases are flushed
* (dbid == -1 in case of FLUSHALL). Caching slots are not specific for
* each DB but are global: currently what we do is sending a special
...
...
@@ -235,3 +241,17 @@ void trackingInvalidateKeysOnFlush(int dbid) {
}
}
}
/* Tracking forces Redis to remember information about which client may have
* keys about certian caching slots. In workloads where there are a lot of
* reads, but keys are hardly modified, the amount of information we have
* to remember server side could be a lot: for each 16 millions of caching
* slots we may end with a radix tree containing many entries.
*
* So Redis allows the user to configure a maximum fill rate for the
* invalidation table. This function makes sure that we don't go over the
* specified fill rate: if we are over, we can just evict informations about
* random caching slots, and send invalidation messages to clients like if
* the key was modified. */
void
trackingLimitUsedSlots
(
void
)
{
}
编辑
预览
Markdown
is supported
0%
请重试
或
添加新附件
.
添加附件
取消
You are about to add
0
people
to the discussion. Proceed with caution.
先完成此消息的编辑!
取消
想要评论请
注册
或
登录