summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--configure.ac5
-rw-r--r--src/os/FileStore.cc41
-rw-r--r--src/os/FileStore.h4
3 files changed, 46 insertions, 4 deletions
diff --git a/configure.ac b/configure.ac
index 515243d24c0..81422145975 100644
--- a/configure.ac
+++ b/configure.ac
@@ -339,6 +339,11 @@ AC_CHECK_FUNC([sync_file_range],
[AC_DEFINE([HAVE_SYNC_FILE_RANGE], [], [sync_file_range(2) is supported])],
[])
+# fallocate
+AC_CHECK_FUNC([fallocate],
+ [AC_DEFINE([HAVE_FALLOCATE], [], [fallocate(2) is supported])],
+ [])
+
# Checks for typedefs, structures, and compiler characteristics.
#AC_HEADER_STDBOOL
diff --git a/src/os/FileStore.cc b/src/os/FileStore.cc
index acaeda8a134..f56b59839bb 100644
--- a/src/os/FileStore.cc
+++ b/src/os/FileStore.cc
@@ -2887,11 +2887,44 @@ int FileStore::_write(coll_t cid, const hobject_t& oid,
int FileStore::_zero(coll_t cid, const hobject_t& oid, uint64_t offset, size_t len)
{
+ dout(15) << "zero " << cid << "/" << oid << " " << offset << "~" << len << dendl;
+ int ret = 0;
+
+#ifdef HAVE_FALLOCATE
+# if !defined(DARWIN) && !defined(__FreeBSD__)
+ // first try to punch a hole.
+ int fd = lfn_open(cid, oid, O_RDONLY);
+ if (fd < 0) {
+ ret = -errno;
+ goto out;
+ }
+
+ // first try fallocate
+ ret = fallocate(fd, FALLOC_FL_PUNCH_HOLE, offset, len);
+ if (ret < 0)
+ ret = -errno;
+ TEMP_FAILURE_RETRY(::close(fd));
+
+ if (ret == 0)
+ goto out; // yay!
+ if (ret != -EOPNOTSUPP)
+ goto out; // some other error
+# endif
+#endif
+
+ // lame, kernel is old and doesn't support it.
// write zeros.. yuck!
- bufferptr bp(len);
- bufferlist bl;
- bl.push_back(bp);
- return _write(cid, oid, offset, len, bl);
+ dout(20) << "zero FALLOC_FL_PUNCH_HOLE not supported, falling back to writing zeros" << dendl;
+ {
+ bufferptr bp(len);
+ bufferlist bl;
+ bl.push_back(bp);
+ ret = _write(cid, oid, offset, len, bl);
+ }
+
+ out:
+ dout(20) << "zero " << cid << "/" << oid << " " << offset << "~" << len << " = " << ret << dendl;
+ return ret;
}
int FileStore::_clone(coll_t cid, const hobject_t& oldoid, const hobject_t& newoid)
diff --git a/src/os/FileStore.h b/src/os/FileStore.h
index 72bcaaad1b8..a9e3f6cc8b4 100644
--- a/src/os/FileStore.h
+++ b/src/os/FileStore.h
@@ -37,6 +37,10 @@ using namespace std;
#include <ext/hash_map>
using namespace __gnu_cxx;
+// from include/linux/falloc.h:
+#ifndef FALLOC_FL_PUNCH_HOLE
+# define FALLOC_FL_PUNCH_HOLE 0x2
+#endif
class FileStore : public JournalingObjectStore,
public md_config_obs_t