From 969200a30c77bb0ee18b0c5eb4fdf5b557968ba7 Mon Sep 17 00:00:00 2001 From: Gui Hecheng Date: Tue, 21 Feb 2017 13:22:16 +0800 Subject: [PATCH] librbd: handle writesame request in AioImageRequestWQ Based on pr: https://github.com/ceph/ceph/pull/10019. Signed-off-by: Gui Hecheng Signed-off-by: Mingxin Liu --- src/librbd/io/ImageRequestWQ.cc | 55 +++++++++++++++++++++++++++++++++ src/librbd/io/ImageRequestWQ.h | 4 +++ src/librbd/io/Types.h | 1 + 3 files changed, 60 insertions(+) diff --git a/src/librbd/io/ImageRequestWQ.cc b/src/librbd/io/ImageRequestWQ.cc index 9999503d3e537..1ce121df70c10 100644 --- a/src/librbd/io/ImageRequestWQ.cc +++ b/src/librbd/io/ImageRequestWQ.cc @@ -93,6 +93,31 @@ int ImageRequestWQ::discard(uint64_t off, uint64_t len) { return len; } +ssize_t ImageRequestWQ::writesame(uint64_t off, uint64_t len, bufferlist &&bl, + int op_flags) { + CephContext *cct = m_image_ctx.cct; + ldout(cct, 20) << "writesame ictx=" << &m_image_ctx << ", off=" << off << ", " + << "len = " << len << ", data_len " << bl.length() << dendl; + + m_image_ctx.snap_lock.get_read(); + int r = clip_io(util::get_image_ctx(&m_image_ctx), off, &len); + m_image_ctx.snap_lock.put_read(); + if (r < 0) { + lderr(cct) << "invalid IO request: " << cpp_strerror(r) << dendl; + return r; + } + + C_SaferCond cond; + AioCompletion *c = AioCompletion::create(&cond); + aio_writesame(c, off, len, std::move(bl), op_flags, false); + + r = cond.wait(); + if (r < 0) { + return r; + } + return len; +} + void ImageRequestWQ::aio_read(AioCompletion *c, uint64_t off, uint64_t len, ReadResult &&read_result, int op_flags, bool native_async) { @@ -210,6 +235,36 @@ void ImageRequestWQ::aio_flush(AioCompletion *c, bool native_async) { } } +void ImageRequestWQ::aio_writesame(AioCompletion *c, uint64_t off, uint64_t len, + bufferlist &&bl, int op_flags, + bool native_async) { + c->init_time(&m_image_ctx, AIO_TYPE_WRITESAME); + CephContext *cct = m_image_ctx.cct; + ldout(cct, 20) << "aio_writesame: ictx=" << &m_image_ctx << ", " + << "completion=" << c << ", off=" << off << ", " + << "len=" << len << ", data_len = " << bl.length() << ", " + << "flags=" << op_flags << dendl; + + if (native_async && m_image_ctx.event_socket.is_valid()) { + c->set_event_notify(true); + } + + if (!start_in_flight_op(c)) { + return; + } + + RWLock::RLocker owner_locker(m_image_ctx.owner_lock); + if (m_image_ctx.non_blocking_aio || writes_blocked()) { + queue(new ImageWriteSameRequest<>(m_image_ctx, c, off, len, std::move(bl), + op_flags)); + } else { + c->start_op(); + ImageRequest<>::aio_writesame(&m_image_ctx, c, off, len, std::move(bl), + op_flags); + finish_in_flight_op(); + } +} + void ImageRequestWQ::shut_down(Context *on_shutdown) { assert(m_image_ctx.owner_lock.is_locked()); diff --git a/src/librbd/io/ImageRequestWQ.h b/src/librbd/io/ImageRequestWQ.h index 8bf10be4825d1..103a4f8c19db5 100644 --- a/src/librbd/io/ImageRequestWQ.h +++ b/src/librbd/io/ImageRequestWQ.h @@ -29,6 +29,7 @@ public: int op_flags); ssize_t write(uint64_t off, uint64_t len, bufferlist &&bl, int op_flags); int discard(uint64_t off, uint64_t len); + ssize_t writesame(uint64_t off, uint64_t len, bufferlist &&bl, int op_flags); void aio_read(AioCompletion *c, uint64_t off, uint64_t len, ReadResult &&read_result, int op_flags, bool native_async=true); @@ -37,8 +38,11 @@ public: void aio_discard(AioCompletion *c, uint64_t off, uint64_t len, bool native_async=true); void aio_flush(AioCompletion *c, bool native_async=true); + void aio_writesame(AioCompletion *c, uint64_t off, uint64_t len, + bufferlist &&bl, int op_flags, bool native_async=true); using ThreadPool::PointerWQ >::drain; + using ThreadPool::PointerWQ >::empty; void shut_down(Context *on_shutdown); diff --git a/src/librbd/io/Types.h b/src/librbd/io/Types.h index f80df9f3eff8c..1c3f967c0c723 100644 --- a/src/librbd/io/Types.h +++ b/src/librbd/io/Types.h @@ -19,6 +19,7 @@ typedef enum { AIO_TYPE_WRITE, AIO_TYPE_DISCARD, AIO_TYPE_FLUSH, + AIO_TYPE_WRITESAME, } aio_type_t; typedef std::vector > Extents; -- 2.39.5