Skip to content

Commit 2ec82c4

Browse files
author
Maksym Pavlenko
authored
Merge pull request containerd#10128 from xinyangge-db/lockless_sync
Perform file sync outside of lock on Commit
2 parents 0aa610c + 4167416 commit 2ec82c4

File tree

3 files changed

+27
-0
lines changed

3 files changed

+27
-0
lines changed

core/content/content.go

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -165,6 +165,11 @@ type Writer interface {
165165
Truncate(size int64) error
166166
}
167167

168+
type Syncer interface {
169+
// Sync flushes the in-flight writes to the disk (when applicable)
170+
Sync() error
171+
}
172+
168173
// Opt is used to alter the mutable properties of content
169174
type Opt func(*Info) error
170175

core/metadata/content.go

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -574,6 +574,13 @@ func (nw *namespacedWriter) Commit(ctx context.Context, size int64, expected dig
574574

575575
var innerErr error
576576

577+
// We pre-sync the in-flight writes to the disk. This avoids the [subsequent fp.Sync() call]
578+
// (https://github.com/containerd/containerd/blob/c4c3c6ea568ce0cfbcf754863abadeea37d77c8f/plugins/content/local/writer.go#L95)
579+
// from taking too long (10s+) while holding the metadata database lock as in the following
580+
// `update` transaction. We intentionally ignore any error on Sync() because it will be
581+
// handled by the subsequent `fp.Sync` anyway.
582+
nw.Sync()
583+
577584
if err := update(ctx, nw.db, func(tx *bolt.Tx) error {
578585
dgst, err := nw.commit(ctx, tx, size, expected, opts...)
579586
if err != nil {
@@ -599,6 +606,13 @@ func (nw *namespacedWriter) Commit(ctx context.Context, size int64, expected dig
599606
return innerErr
600607
}
601608

609+
func (nw *namespacedWriter) Sync() error {
610+
if syncer, ok := nw.w.(content.Syncer); ok {
611+
return syncer.Sync()
612+
}
613+
return nil
614+
}
615+
602616
func (nw *namespacedWriter) commit(ctx context.Context, tx *bolt.Tx, size int64, expected digest.Digest, opts ...content.Opt) (digest.Digest, error) {
603617
var base content.Info
604618
for _, opt := range opts {

plugins/content/local/writer.go

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -206,3 +206,11 @@ func (w *writer) Truncate(size int64) error {
206206
}
207207
return w.fp.Truncate(0)
208208
}
209+
210+
func (w *writer) Sync() error {
211+
if w.fp != nil {
212+
return w.fp.Sync()
213+
}
214+
215+
return nil
216+
}

0 commit comments

Comments
 (0)