From ed54420e214dc194ef5a0d1cdcfcd37c4c80b312 Mon Sep 17 00:00:00 2001 From: Jianpeng Ma Date: Tue, 20 Jan 2015 10:40:11 +0800 Subject: [PATCH] bufferlist: Add new func is_provided_buffer(const char *dst) Using this function to judge whether copy data from bufferlist to dst. It mainly used librados C interface to avoid copy data from librados to caller. Signed-off-by: Jianpeng Ma --- src/common/buffer.cc | 9 ++++++++- src/include/buffer.h | 1 + src/librados/librados.cc | 6 +++--- src/libradosstriper/libradosstriper.cc | 2 +- 4 files changed, 13 insertions(+), 5 deletions(-) diff --git a/src/common/buffer.cc b/src/common/buffer.cc index f819f039823ba..f705a0f87dca8 100644 --- a/src/common/buffer.cc +++ b/src/common/buffer.cc @@ -1315,6 +1315,13 @@ static simple_spinlock_t buffer_debug_lock = SIMPLE_SPINLOCK_INITIALIZER; return true; } + bool buffer::list::is_provided_buffer(const char *dst) const + { + if (_buffers.empty()) + return false; + return (is_contiguous() && (_buffers.front().c_str() == dst)); + } + bool buffer::list::is_aligned(unsigned align) const { for (std::list::const_iterator it = _buffers.begin(); @@ -1385,7 +1392,7 @@ static simple_spinlock_t buffer_debug_lock = SIMPLE_SPINLOCK_INITIALIZER; break; // done } } - + bool buffer::list::is_contiguous() const { return &(*_buffers.begin()) == &(*_buffers.rbegin()); diff --git a/src/include/buffer.h b/src/include/buffer.h index a1a273dd33177..6fbf481a74752 100644 --- a/src/include/buffer.h +++ b/src/include/buffer.h @@ -409,6 +409,7 @@ namespace buffer CEPH_BUFFER_API { bool contents_equal(const buffer::list& other) const; bool can_zero_copy() const; + bool is_provided_buffer(const char *dst) const; bool is_aligned(unsigned align) const; bool is_page_aligned() const; bool is_n_align_sized(unsigned align) const; diff --git a/src/librados/librados.cc b/src/librados/librados.cc index e66d17b638aca..be25564c36129 100644 --- a/src/librados/librados.cc +++ b/src/librados/librados.cc @@ -3095,7 +3095,7 @@ extern "C" int rados_read(rados_ioctx_t io, const char *o, char *buf, size_t len tracepoint(librados, rados_read_exit, -ERANGE, NULL); return -ERANGE; } - if (bl.c_str() != buf) + if (!bl.is_provided_buffer(buf)) bl.copy(0, bl.length(), buf); ret = bl.length(); // hrm :/ } @@ -3445,7 +3445,7 @@ extern "C" int rados_getxattr(rados_ioctx_t io, const char *o, const char *name, tracepoint(librados, rados_getxattr_exit, -ERANGE, buf, 0); return -ERANGE; } - if (bl.c_str() != buf) + if (!bl.is_provided_buffer(buf)) bl.copy(0, bl.length(), buf); ret = bl.length(); } @@ -4815,7 +4815,7 @@ public: } if (bytes_read) *bytes_read = out_bl.length(); - if (out_buf && out_bl.c_str() != out_buf) + if (out_buf && !out_bl.is_provided_buffer(out_buf)) out_bl.copy(0, out_bl.length(), out_buf); } }; diff --git a/src/libradosstriper/libradosstriper.cc b/src/libradosstriper/libradosstriper.cc index 969f2d814732f..352fe390baccb 100644 --- a/src/libradosstriper/libradosstriper.cc +++ b/src/libradosstriper/libradosstriper.cc @@ -395,7 +395,7 @@ extern "C" int rados_striper_read(rados_striper_t striper, if (ret >= 0) { if (bl.length() > len) return -ERANGE; - if (bl.c_str() != buf) + if (!bl.is_provided_buffer(buf)) bl.copy(0, bl.length(), buf); ret = bl.length(); // hrm :/ } -- 2.39.5