summaryrefslogtreecommitdiff
path: root/src/rio.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/rio.c')
-rw-r--r--src/rio.c20
1 files changed, 20 insertions, 0 deletions
diff --git a/src/rio.c b/src/rio.c
index de4713fec..eaf88d25f 100644
--- a/src/rio.c
+++ b/src/rio.c
@@ -151,6 +151,16 @@ static size_t rioFileWrite(rio *r, const void *buf, size_t len) {
#else
if (redis_fsync(fileno(r->io.file.fp)) == -1) return 0;
#endif
+ if (r->io.file.reclaim_cache) {
+ /* In Linux sync_file_range just issue a writeback request to
+ * OS, and when posix_fadvise is called, the dirty page may
+ * still be in flushing, which means it would be ignored by
+ * posix_fadvise.
+ *
+ * So we posix_fadvise the whole file, and the writeback-ed
+ * pages will have other chances to be reclaimed. */
+ reclaimFilePageCache(fileno(r->io.file.fp), 0, 0);
+ }
r->io.file.buffered = 0;
}
}
@@ -191,6 +201,7 @@ void rioInitWithFile(rio *r, FILE *fp) {
r->io.file.fp = fp;
r->io.file.buffered = 0;
r->io.file.autosync = 0;
+ r->io.file.reclaim_cache = 0;
}
/* ------------------- Connection implementation -------------------
@@ -439,6 +450,15 @@ void rioSetAutoSync(rio *r, off_t bytes) {
r->io.file.autosync = bytes;
}
+/* Set the file-based rio object to reclaim cache after every auto-sync.
+ * In the Linux implementation POSIX_FADV_DONTNEED skips the dirty
+ * pages, so if auto sync is unset this option will have no effect.
+ *
+ * This feature can reduce the cache footprint backed by the file. */
+void rioSetReclaimCache(rio *r, int enabled) {
+ r->io.file.reclaim_cache = enabled;
+}
+
/* Check the type of rio. */
uint8_t rioCheckType(rio *r) {
if (r->read == rioFileRead) {