int64_t some = in->size - pos;
if (some > left)
some = left;
- auto& z = buffer::ptr_node::create(some);
- z.zero();
- bl->push_back(z);
+ auto z = buffer::ptr_node::create(some);
+ z->zero();
+ bl->push_back(std::move(z));
read += some;
pos += some;
left -= some;
rebuild(ptr_node::create(buffer::create(_len)));
}
- void buffer::list::rebuild(ptr_node& nb)
+ void buffer::list::rebuild(
+ std::unique_ptr<buffer::ptr_node, buffer::ptr_node::disposer> nb)
{
unsigned pos = 0;
for (auto& node : _buffers) {
- nb.copy_in(pos, node.length(), node.c_str(), false);
+ nb->copy_in(pos, node.length(), node.c_str(), false);
pos += node.length();
}
_memcopy_count += pos;
_buffers.clear_and_dispose(ptr_node::disposer());
- if (likely(nb.length())) {
- _buffers.push_back(nb);
- } else {
- ptr_node::disposer()(&nb);
+ if (likely(nb->length())) {
+ _buffers.push_back(*nb.release());
}
invalidate_crc();
last_p = begin();
buffer::create_aligned(unaligned._len, align_memory)));
_memcopy_count += unaligned._len;
}
- _buffers.insert(p, ptr_node::create(unaligned._buffers.front()));
+ _buffers.insert(p, *ptr_node::create(unaligned._buffers.front()).release());
}
last_p = begin();
{
_len += bl._len;
for (const auto& node : bl._buffers) {
- _buffers.push_back(ptr_node::create(node));
+ _buffers.push_back(*ptr_node::create(node).release());
}
}
void buffer::list::prepend_zero(unsigned len)
{
- auto& bp = ptr_node::create(len);
- bp.zero(false);
+ auto bp = ptr_node::create(len);
+ bp->zero(false);
_len += len;
- _buffers.push_front(bp);
+ _buffers.push_front(*bp.release());
}
void buffer::list::append_zero(unsigned len)
len -= need;
}
if (len) {
- auto& bp = ptr_node::create(buffer::create_page_aligned(len));
- bp.zero(false);
- _len += bp.length();
- _buffers.push_back(bp);
+ auto bp = ptr_node::create(buffer::create_page_aligned(len));
+ bp->zero(false);
+ push_back(std::move(bp));
}
}
// partial?
if (off + len < curbuf->length()) {
//cout << "copying partial of " << *curbuf << std::endl;
- _buffers.push_back( ptr_node::create( *curbuf, off, len ) );
+ _buffers.push_back(*ptr_node::create( *curbuf, off, len ).release());
_len += len;
break;
}
// through end
//cout << "copying end (all?) of " << *curbuf << std::endl;
unsigned howmuch = curbuf->length() - off;
- _buffers.push_back( ptr_node::create( *curbuf, off, howmuch ) );
+ _buffers.push_back(*ptr_node::create( *curbuf, off, howmuch ).release());
_len += howmuch;
len -= howmuch;
off = 0;
// add a reference to the front bit
// insert it before curbuf (which we'll hose)
//cout << "keeping front " << off << " of " << *curbuf << std::endl;
- _buffers.insert( curbuf, ptr_node::create( *curbuf, 0, off ) );
+ _buffers.insert( curbuf, *ptr_node::create( *curbuf, 0, off ).release());
_len += off;
}
ssize_t buffer::list::read_fd(int fd, size_t len)
{
- auto& bp = ptr_node::create(buffer::create(len));
- ssize_t ret = safe_read(fd, (void*)bp.c_str(), len);
+ auto bp = ptr_node::create(buffer::create(len));
+ ssize_t ret = safe_read(fd, (void*)bp->c_str(), len);
if (ret >= 0) {
- bp.set_length(ret);
- push_back(bp);
+ bp->set_length(ret);
+ push_back(std::move(bp));
}
return ret;
}
return is_hypercombined;
}
-buffer::ptr_node& buffer::ptr_node::create_hypercombined(
- buffer::raw* const r)
+std::unique_ptr<buffer::ptr_node, buffer::ptr_node::disposer>
+buffer::ptr_node::create_hypercombined(buffer::raw* const r)
{
if (likely(r->nref == 0)) {
- return *new (&r->bptr_storage) ptr_node(r);
+ return std::unique_ptr<buffer::ptr_node, buffer::ptr_node::disposer>(
+ new (&r->bptr_storage) ptr_node(r));
} else {
- return *new ptr_node(r);
+ return std::unique_ptr<buffer::ptr_node, buffer::ptr_node::disposer>(
+ new ptr_node(r));
}
}
class ptr_node : public ptr, public boost::intrusive::list_base_hook<> {
- template <class... Args>
- ptr_node(Args&&... args) : ptr(std::forward<Args>(args)...) {
- }
- ptr_node(const ptr_node&) = default;
-
- ptr& operator= (const ptr& p) = delete;
- ptr& operator= (ptr&& p) noexcept = delete;
- ptr_node& operator= (const ptr_node& p) = delete;
- ptr_node& operator= (ptr_node&& p) noexcept = delete;
- void swap(ptr& other) noexcept = delete;
- void swap(ptr_node& other) noexcept = delete;
-
public:
- ~ptr_node() = default;
-
- static bool dispose_if_hypercombined(ptr_node* delete_this);
- static ptr_node& create_hypercombined(raw* r);
-
- static ptr_node& create(raw* const r) {
- return create_hypercombined(r);
- }
- static ptr_node& create(const unsigned l) {
- return create_hypercombined(buffer::create(l));
- }
- template <class... Args>
- static ptr_node& create(Args&&... args) {
- return *new ptr_node(std::forward<Args>(args)...);
- }
-
struct cloner {
ptr_node* operator()(const ptr_node& clone_this) {
return new ptr_node(clone_this);
}
}
};
+
+ ~ptr_node() = default;
+
+ static std::unique_ptr<ptr_node, disposer> create(raw* const r) {
+ return create_hypercombined(r);
+ }
+ static std::unique_ptr<ptr_node, disposer> create(const unsigned l) {
+ return create_hypercombined(buffer::create(l));
+ }
+ template <class... Args>
+ static std::unique_ptr<ptr_node, disposer> create(Args&&... args) {
+ return std::unique_ptr<ptr_node, disposer>(
+ new ptr_node(std::forward<Args>(args)...));
+ }
+
+ private:
+ template <class... Args>
+ ptr_node(Args&&... args) : ptr(std::forward<Args>(args)...) {
+ }
+ ptr_node(const ptr_node&) = default;
+
+ ptr& operator= (const ptr& p) = delete;
+ ptr& operator= (ptr&& p) noexcept = delete;
+ ptr_node& operator= (const ptr_node& p) = delete;
+ ptr_node& operator= (ptr_node&& p) noexcept = delete;
+ void swap(ptr& other) noexcept = delete;
+ void swap(ptr_node& other) noexcept = delete;
+
+ static bool dispose_if_hypercombined(ptr_node* delete_this);
+ static std::unique_ptr<ptr_node, disposer> create_hypercombined(raw* r);
};
/*
* list - the useful bit!
void push_back(const ptr& bp) {
if (bp.length() == 0)
return;
- _buffers.push_back(ptr_node::create(bp));
+ _buffers.push_back(*ptr_node::create(bp).release());
_len += bp.length();
}
void push_back(ptr&& bp) {
if (bp.length() == 0)
return;
_len += bp.length();
- _buffers.push_back(ptr_node::create(std::move(bp)));
+ _buffers.push_back(*ptr_node::create(std::move(bp)).release());
}
- void push_back(ptr_node& bp) {
- if (bp.length() == 0)
+ void push_back(const ptr_node&) = delete;
+ void push_back(ptr_node&) = delete;
+ void push_back(ptr_node&&) = delete;
+ void push_back(std::unique_ptr<ptr_node, ptr_node::disposer> bp) {
+ if (bp->length() == 0)
return;
- _len += bp.length();
- _buffers.push_back(bp);
+ _len += bp->length();
+ _buffers.push_back(*bp.release());
}
void push_back(raw* const r) {
- _buffers.push_back(ptr_node::create(r));
+ _buffers.push_back(*ptr_node::create(r).release());
_len += _buffers.back().length();
}
bool is_contiguous() const;
void rebuild();
- void rebuild(ptr_node& nb);
+ void rebuild(std::unique_ptr<ptr_node, ptr_node::disposer> nb);
bool rebuild_aligned(unsigned align);
// max_buffers = 0 mean don't care _buffers.size(), other
// must make _buffers.size() <= max_buffers after rebuilding.
{
if (this != &bl) {
clear();
- decltype(_buffers)::const_iterator pb;
- for (pb = bl._buffers.begin(); pb != bl._buffers.end(); ++pb) {
- push_back(*pb);
+ for (const auto& pb : bl._buffers) {
+ push_back(static_cast<const ptr&>(pb));
}
}
}
});
auto gather_ctx = new C_Gather(m_dest->cct, end_op_ctx);
- auto& m_ptr = buffer::ptr_node::create(m_bl->length());
- m_bl->rebuild(m_ptr);
+ m_bl->rebuild(buffer::ptr_node::create(m_bl->length()));
size_t write_offset = 0;
size_t write_length = 0;
size_t offset = 0;
size_t length = m_bl->length();
+ const auto& m_ptr = m_bl->front();
while (offset < length) {
if (util::calc_sparse_extent(m_ptr,
m_sparse_size,
&write_offset,
&write_length,
&offset)) {
- auto& write_ptr = \
- buffer::ptr_node::create(m_ptr, write_offset, write_length);
bufferlist *write_bl = new bufferlist();
- write_bl->push_back(write_ptr);
+ write_bl->push_back(
+ buffer::ptr_node::create(m_ptr, write_offset, write_length));
Context *ctx = new C_CopyWrite(write_bl, gather_ctx->new_sub());
auto comp = io::AioCompletion::create(ctx);
_aio_log_start(ioc, off, len);
- auto& p = buffer::ptr_node::create(buffer::create_small_page_aligned(len));
+ auto p = buffer::ptr_node::create(buffer::create_small_page_aligned(len));
int r = ::pread(buffered ? fd_buffereds[WRITE_LIFE_NOT_SET] : fd_directs[WRITE_LIFE_NOT_SET],
- p.c_str(), len, off);
+ p->c_str(), len, off);
if (r < 0) {
r = -errno;
goto out;