-
Notifications
You must be signed in to change notification settings - Fork 5
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
posts: add lsm-kv-separation-overview #5
Conversation
俺没太懂这里详细的流程是什么样子的,可以举个例子吗? |
比如 compaction 的时候要写入 key A,用户在 key A 写了新的数据。对 Titan 来说,要注册 WriteCallback,才能防止 compaction 写入的 key A 覆盖掉用户新写入的值。 对于 BadgerDB 来说,compaction 写入旧的数据也没有问题,因为所有的 key 都带 timestamp,最新的 key 在 get 时永远会被优先读到。 |
好的,感谢,话说 badger 分离大小是不是 1M 呀,瞅了眼代码: |
这个 PR 从 1KB 改到了 1MB(hypermodeinc/badger#1664 |
(但是你文章里面既不是 1KB 也不是 1MB 啊 ( ;´Д`) |
话说,我在想,如果不考虑 Sequence,Badger 的 GC 能不能只写前台,然后存在于 LSM 中的 key 被写入之后,记录 seq。等 seq 之前的快照都没了,再回收物理空间,是不是也可以做? |
我觉得是可以的,这样可以省掉一次读,但是有更大的写开销( |
感觉写没有吧,相当于回收空间由垃圾收集器积极回收变成了由最低 seq 的读者来触发回收? |
package main
import (
"sync/atomic"
"fmt"
"unsafe"
)
const (
maxHeight = 20
)
const (
offsetSize = int(unsafe.Sizeof(uint32(0)))
nodeAlign = int(unsafe.Sizeof(uint64(0))) - 1 // 这里是7
MaxNodeSize = int(unsafe.Sizeof(node{}))
defaultLevel = 20
)
type node struct {
value uint64
keyOffset uint32 // Immutable. No need to lock to access key.
keySize uint16 // Immutable. No need to lock to access key.
height uint16
tower [maxHeight]uint32
}
type Arena struct {
n uint32
buf []byte
}
func newArena(sz int64) *Arena {
return &Arena{
n: 1,
buf: make([]byte, sz),
}
}
func (a *Arena) alloc(sz uint32) uint32 {
return atomic.AddUint32(&a.n, sz) - sz
}
func (a *Arena) putNode(height int) uint32 {
unusedSize := (defaultLevel - height) * offsetSize
l := uint32(MaxNodeSize - unusedSize + nodeAlign) // 这里
n := a.alloc(l)
m := (n + uint32(nodeAlign)) & ^uint32(nodeAlign) // 还有这里计算 buf offset 看不太懂,这是通用做法吗
fmt.Println(m)
return m
}
func main() {
a := newArena(65535)
a.putNode(4)
a.putNode(3)
a.putNode(2)
a.putNode(1)
}
|
这里在扫描老的vlog时,已经判断key是否存在了。如果添加valid的key到LSM之前,再判断一次,是不是就没有你说的问题了? |
@jyizheng 是的,WiscKey 的 GC 描述应该是存在问题的。
应该有一些实现是这样的,不过问题就是读放大吧 |
只是想理解一下正确性的问题。对,这样实现会有读放大。请问哪些system是这样实现的? |
BadgerDB 实现了 MVCC,因此会出现需要把一个 key 的旧版本写回去的情况。 |
LevelDB也有MVCC? |
RocksDB+Titan/TerarkDB 的 ts 是不暴露给用户的,所以回写时只需要考虑最新版本。BadgerDB 的 managed mode 会暴露 ts,由用户指定 watermark 和 ts,所以 gc 的时候需要保留旧版本的 vptr。 |
那WiscKey的实现有问题吗?往LSM添加新的value地址时,需要再check key是否存在吗? |
从论文描述来看,我觉得不够完整。 |
No description provided.