1
0
mirror of https://github.com/taigrr/bitcask synced 2025-01-18 04:03:17 -08:00

Optimized and increased read performance by ~2-3x by memory mapping the read-only datafiles

This commit is contained in:
James Mills
2019-03-23 13:35:55 +10:00
parent 711d08ce91
commit 53dc013215
4 changed files with 48 additions and 23 deletions

View File

@@ -8,7 +8,7 @@ import (
"sync"
"github.com/pkg/errors"
log "github.com/sirupsen/logrus"
"golang.org/x/exp/mmap"
pb "github.com/prologic/bitcask/internal/proto"
"github.com/prologic/bitcask/internal/streampb"
@@ -28,6 +28,7 @@ type Datafile struct {
id int
r *os.File
ra *mmap.ReaderAt
w *os.File
offset int64
dec *streampb.Decoder
@@ -37,6 +38,7 @@ type Datafile struct {
func NewDatafile(path string, id int, readonly bool) (*Datafile, error) {
var (
r *os.File
ra *mmap.ReaderAt
w *os.File
err error
)
@@ -59,6 +61,11 @@ func NewDatafile(path string, id int, readonly bool) (*Datafile, error) {
return nil, errors.Wrap(err, "error calling Stat()")
}
ra, err = mmap.Open(fn)
if err != nil {
return nil, err
}
offset := stat.Size()
dec := streampb.NewDecoder(r)
@@ -67,6 +74,7 @@ func NewDatafile(path string, id int, readonly bool) (*Datafile, error) {
return &Datafile{
id: id,
r: r,
ra: ra,
w: w,
offset: offset,
dec: dec,
@@ -84,6 +92,10 @@ func (df *Datafile) Name() string {
func (df *Datafile) Close() error {
if df.w == nil {
err := df.ra.Close()
if err != nil {
return err
}
return df.r.Close()
}
@@ -120,10 +132,15 @@ func (df *Datafile) Read() (e pb.Entry, n int64, err error) {
}
func (df *Datafile) ReadAt(index, size int64) (e pb.Entry, err error) {
log.WithField("index", index).WithField("size", size).Debug("ReadAt")
var n int
b := make([]byte, size)
n, err := df.r.ReadAt(b, index)
if df.w == nil {
n, err = df.ra.ReadAt(b, index)
} else {
n, err = df.r.ReadAt(b, index)
}
if err != nil {
return
}